我正在进行Android OpenGL ES实验,以了解它在不同手机上的表现。在我的Logcat中,我得到标记为“SharedBufferStack”的日志消息,其中包含以下任一行
dequeue:tail = 0,head = 1,avail = 2,queued = 0
dequeue:tail = 1,head = 0,avail = 2,queued = 0
重复几次,即使我单独留下应用程序(没有触摸或按钮按下并阻止其进入睡眠状态)。我想知道是什么导致它,即使它不是一个错误。它会影响性能吗?
更重要的是,我该如何删除它?
我正在使用带有Android SDK的标准Eclipse
答案 0 :(得分:0)
TLDR版本:在OpenGL ES的onDrawFrame()中调用Thread.sleep()引起。
通过查看下面链接中的代码,我想到了一些。 https://android.googlesource.com/platform/frameworks/native/+/9cce325fae8adcf7560a28eef394489f09bad74d/libs/surfaceflinger_client/SharedBufferStack.cpp
所以这个SharedBufferStack是Android的SurfaceFlinger的一部分,在http://rahulonblog.blogspot.sg/2013/06/an-overview-of-surfaceflinger.html描述
Surfaceflinger:它是一个系统范围的表面组合函数,它驻留在android框架中。它从不同的应用程序获取数据(表面),可以是2D或3D,最后将其组合以获得将被馈送到存储器的主表面(这是帧缓冲器)。 Surfaceflinger根据它们的位置,大小和其他参数合成所有表面,尽管这种合成是由OpenGL(由Surfaceflinger调用)完成的,但我们需要Surfaceflinger来计算相关参数,如重叠函数。
这意味着SharedBufferStack用于不同的应用程序来共享图形界面的内存(如果我错了,请纠正我)。
在第281和282行结束时,它会调用LOGW(Logcat调用的警告)。
LOGW("dequeue: tail=%d, head=%d, avail=%d, queued=%d",
tail, stack.head, stack.available, stack.queued);
如果您读取功能块的其余部分,则SharedBufferClient :: dequeue会尝试警告堆栈为空/接近空。
如果我疯狂猜测,我认为“图形”堆栈至少需要有一些东西,否则它无法显示。我仍然不知道为什么它在tail = 0和stack.head = 1时调用stack.head == tail。我看不出它实际上是一个堆栈。
===更新1
显然经过更多的测试后,碰巧是我的Thread.sleep,我在OpenGL ES循环的onDrawFrame中调用。由于RENDERMODE_CONTINUOUSLY无法正确控制帧速率(因为我想将其限制为每秒30帧而不是让它快速运行),我让线程在剩余的时间内休眠。
Thread.sleep(16 - diffTime);
如果我是正确的,请睡觉opengl线程。显然它会导致上面的消息出现并且听起来不太好,因为您将图形线程从堆栈中取出。我认为我可以做的一种方法是运行一个单独的线程,调用onDrawFrame来使用RENDERMODE_WHEN_DIRTY进行渲染。另一种方法是让它以尽可能快的速度运行,但每隔0.017(60 fps)间隔调用一次逻辑循环或控制器,以获取动画和其他东西。
===更新2
我做了一个允许尽可能快地渲染图像的那个,但是用时间来找出运行逻辑的时间。