我在哪里可以更改着色器制服并调用 GL 函数?
Where i can change shader uniforms and call GL Functions?
我只是想用 GLSurfaceView 编写简单的 android 应用程序,但我遇到了一个问题。
我编写了一个简单的着色器程序,并在其中放置了一个浮点参数。这是我的
顶点着色器:
attribute vec2 vPosition;
attribute vec2 vTexCoord;
varying vec2 texCoord;
void main(){
texCoord = vTexCoord;
gl_Position = vec4 ( vPosition.x, vPosition.y, 0.0, 1.0 );
}
片段着色器:
precision mediump float;
uniform samplerExternalOES sTexture;
uniform float myParam;
varying vec2 texCoord;
void main(){
gl_FragColor = texture2D(sTexture,texCoord);
gl_FragColor.r = gl_FragColor.r*myParam.x;
}
一切都很好。
我获得了访问 myParam 的句柄(int paramHandle - 我的 class 的成员):
public void onSurfaceCreated(....){
....
paramHandle= GLES20.glGetUniformLocation(shaderProgram,"myParam");
....
}
现在我想改变 myParam 并观察屏幕上的图像发生了什么。对于这个任务,我需要调用:
GLES20.glUseProgram(myShaderProgram);
GLES20.glUniform1f(paramHandle, new_value);
所以:如果我尝试更改这些函数中的 myParam 值:
onSurfaceCreated(...)、onSurfaceChanged(...) 或 onDrawFrame(...)
我可以在屏幕上看到这个变化,所以我觉得 myParam 值被改变了。
但是如果我想使用按钮设置 maParam 值,例如在单击按钮时调用函数 setMyParamValue:
public void setMyParamValue(float newValue){
GLES20.glUseProgram(myShaderProgram);
GLES20.glUniform1f(paramHandle, new_value);
}
好像什么都没发生
有人可以向我解释一下它是如何工作的吗?为什么我不能在我的函数中设置统一值?
渲染发生在与 UI 事件传递来源不同的线程上。 openGL 调用应该只发生在渲染线程中。
您应该将这些调用转发给您传递给 queueEvent
的可运行对象:
public void setMyParamValue(final float newValue){
queueEvent(new Runnable(){
public void run(){
GLES20.glUseProgram(myShaderProgram);
GLES20.glUniform1f(paramHandle, new_value);
}
});
}
run()
中的代码将在渲染线程中执行。
我只是想用 GLSurfaceView 编写简单的 android 应用程序,但我遇到了一个问题。 我编写了一个简单的着色器程序,并在其中放置了一个浮点参数。这是我的
顶点着色器:
attribute vec2 vPosition;
attribute vec2 vTexCoord;
varying vec2 texCoord;
void main(){
texCoord = vTexCoord;
gl_Position = vec4 ( vPosition.x, vPosition.y, 0.0, 1.0 );
}
片段着色器:
precision mediump float;
uniform samplerExternalOES sTexture;
uniform float myParam;
varying vec2 texCoord;
void main(){
gl_FragColor = texture2D(sTexture,texCoord);
gl_FragColor.r = gl_FragColor.r*myParam.x;
}
一切都很好。
我获得了访问 myParam 的句柄(int paramHandle - 我的 class 的成员):
public void onSurfaceCreated(....){
....
paramHandle= GLES20.glGetUniformLocation(shaderProgram,"myParam");
....
}
现在我想改变 myParam 并观察屏幕上的图像发生了什么。对于这个任务,我需要调用:
GLES20.glUseProgram(myShaderProgram);
GLES20.glUniform1f(paramHandle, new_value);
所以:如果我尝试更改这些函数中的 myParam 值:
onSurfaceCreated(...)、onSurfaceChanged(...) 或 onDrawFrame(...)
我可以在屏幕上看到这个变化,所以我觉得 myParam 值被改变了。
但是如果我想使用按钮设置 maParam 值,例如在单击按钮时调用函数 setMyParamValue:
public void setMyParamValue(float newValue){
GLES20.glUseProgram(myShaderProgram);
GLES20.glUniform1f(paramHandle, new_value);
}
好像什么都没发生
有人可以向我解释一下它是如何工作的吗?为什么我不能在我的函数中设置统一值?
渲染发生在与 UI 事件传递来源不同的线程上。 openGL 调用应该只发生在渲染线程中。
您应该将这些调用转发给您传递给 queueEvent
的可运行对象:
public void setMyParamValue(final float newValue){
queueEvent(new Runnable(){
public void run(){
GLES20.glUseProgram(myShaderProgram);
GLES20.glUniform1f(paramHandle, new_value);
}
});
}
run()
中的代码将在渲染线程中执行。