【发布时间】:2014-12-07 22:16:48
【问题描述】:
我正在为 android 制作动态壁纸,我将解释它是如何工作的,因为我相信它与问题有关,很抱歉这个问题很长,但我需要解释一切,因为问题很难描述。
我正在使用 OpenGLES 2.0,我有一个 GLSurfaceView 和一个壁纸服务实现,我将它传递给我的渲染器以调用绘图方法,就像大多数 OpenGL 动态壁纸一样。
我实现渲染器的方式是:在墙纸服务中,我有一个独立的线程,它将每 X 秒调用一次绘制方法,GLSurfaceView 设置为 RENDERMODE_WHEN_DIRTY,因此这个更新线程决定了何时进行绘制。
此外,服务中还有一个暂停和恢复方法,当可见性发生变化时。因此,即使我退出壁纸,该服务也会运行,并保留所有内容的状态,直到它恢复为止。
现在解决这个问题,正如您在此处所见:
但是当我失去焦点并重新回到壁纸时,我会按下 android 壁纸选择器上的后退按钮,或者更改壁纸然后返回。事物的alpha值会上升。
这里有 2 个网格,左侧的初始 alpha 值为 0.1,右侧的初始 alpha 值为 0.5。
现在,当我离开并返回时,将调用 GLSurfaceView onVisibilityChanged 方法,它按预期工作,但正如您所见,alpha 值会由于某种原因而增加,并且在我离开和返回时继续增加:
1次 2次
我设置网格绘制的方式是在我的片段着色器中,我将在绘制网格之前设置制服的值,并且该制服将乘以纹理颜色。
这是片段着色器:
precision mediump float;
uniform vec4 u_color;
uniform sampler2D u_texture;
varying vec2 v_textcoord;
void main()
{
gl_FragColor = u_color * texture2D(u_texture, v_textcoord);
}
当然在绘制网格之前我设置了混合和混合函数:
GLES20.glEnable(GLES20.GL_BLEND);
GLES20.glBlendFunc(GLES20.GL_SRC_ALPHA, GLES20.GL_ONE_MINUS_SRC_ALPHA);
GLES20.glUniform4f(DayAndNightRenderer.BaseShader.GetUniform("u_color"), color.r, color.g, color.b, 0.5f);
texture.Bind();
mesh.Draw(GLES20.GL_TRIANGLE_FAN, DayAndNightRenderer.BaseShader);
GLES20.glDisable(GLES20.GL_BLEND);
还有网格绘制,即使绘制之前设置了颜色统一:
GLES20.glUniformMatrix4fv(shader.GetUniform("u_transmat"), 1, false, Transform.GetProjectedTransformationMatrix().ToFloatBuffer());
GLES20.glEnableVertexAttribArray(shader.GetAttribute("a_pos"));
GLES20.glEnableVertexAttribArray(shader.GetAttribute("a_textcoord"));
GLES20.glBindBuffer(GLES20.GL_ARRAY_BUFFER, VBO[0]);
GLES20.glVertexAttribPointer(shader.GetAttribute("a_pos"), 3, GLES20.GL_FLOAT, false, Vertex.SIZE, 0);
GLES20.glVertexAttribPointer(shader.GetAttribute("a_textcoord"), 3, GLES20.GL_FLOAT, false, Vertex.SIZE, Vertex.POS_SIZE);
GLES20.glBindBuffer(GLES20.GL_ELEMENT_ARRAY_BUFFER, IBO[0]);
GLES20.glDrawElements(primitive, size, GLES20.GL_UNSIGNED_INT, 0);
GLES20.glDisableVertexAttribArray(shader.GetAttribute("a_textcoord"));
GLES20.glDisableVertexAttribArray(shader.GetAttribute("a_pos"));
到目前为止我尝试过的事情:
- 更改混合函数似乎不会影响添加到 alpha 值的错误
- 在焦点丢失之间重新加载着色器
- 清除帧缓冲区,我设置了 GLES20.glClearColor(0f, 0f, 0f, 0f);开始并调用 GLES20.glClear(GL10.GL_COLOR_BUFFER_BIT | GL10.GL_DEPTH_BUFFER_BIT);每一帧
上述方法均无效,而且它不是我用来设置累积 alpha 的变量,事物的 alpha 设置为常数,正如您在我设置颜色统一的代码中看到的那样。
我不知道是什么原因造成的,它真的只是在失去壁纸的焦点并回到它时才会发生,在第一次运行时没有返回,它完美地绘制了所有内容。
顺便说一下onVisibilityChanged方法:
@Override
public void onVisibilityChanged(boolean visible)
{
super.onVisibilityChanged(visible);
if (hassetrenderer)
{
if (visible)
{
OpenGLES2WallpaperService.updatehandler.Start();
glsurfaceview.onResume();
Log.i("DN", "State: running");
}
else
{
OpenGLES2WallpaperService.updatehandler.Stop();
glsurfaceview.onPause();
Log.i("DN", "State: not running");
}
}
}
【问题讨论】:
标签: java android opengl-es live-wallpaper blending