Android 应用程序上的 GPU 工件
GPU Artifacts on Android app
我有一个应用程序有一个非常奇怪的问题。有时,在启动应用程序时,所有片段都会遇到此问题。看起来 GPU 正在用它做一些奇特的事情。
在下面的动画 Gif 中,您可以清楚地看到具有上述工件的 PreferenceFragment。
编辑 1。看起来我有一个特定的片段,一旦 "draws" 在屏幕上出现错误。使用 .replace
切换片段实际上不会 "clean" 问题。
我该如何调试它?
看起来像是来自 GPU 的垃圾。
您需要查看的第一件事是您的 window 背景(然后是各种全屏布局背景)。
它可能被定义为 null 或另一个类似的问题。
好的,我的问题是因为我有我的主题
<item name="android:windowBackground">@color/dark</color>
其中 dark
是设置为 #313131
的颜色项目
然后我有一个视图,我用它作为其他一些内容的封面来使底层视图变暗,如下所示:
<FrameLayout
android:layout_width="match_parent"
android:layout_height="200dp">
<ImageView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_gravity="center"
android:src="@drawable/mydrawable"
/>
<View
android:id="@+id/coverview"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:background="@color/dark"/>
</FrameLayout>
以编程方式,我必须使用 coverView.getBackground().setAlpha((int)(0.6f*255));
设置封面视图的 alpha
令人惊讶的是,这个新的 alpha 值也被应用到 window 背景并产生了很多你在我的问题中看到的伪影(即使在切换片段后封面视图不再在查看树)
默认情况下,从同一资源加载的所有可绘制实例共享一个公共状态。因此我的代码是错误的,我需要在应用新的 alpha 值之前在后台调用 .mutate。
除了我错了@调用 .setAlpha
而没有调用 .mutate()
GPU 闪烁对我来说仍然是一个谜.
为什么GPU会闪烁?正如 Christophe here:
所指出的
the GPU flickers cause the background is now translucent and the
system tries to blend it with what was currently in the empty buffer
(mostly garbage).
为了展示 bug 问题,我创建了一个 github 存储库,其中包含一个展示该问题的示例项目:https://github.com/vekexasia/gpuflickering-background-alpha
解决方法:几个。如果您想使用相同的方法(这也会导致过度绘制),您应该以编程方式设置颜色,然后为其设置 alpha 值。像这样:
coverView.setBackground(new ColorDrawable(getResources().getColor(R.color.dark)));
更好的方法是应用 ColorFilter to the ImageView or if you're using Picasso
use a Transformation
另一种方法是在 .setAlpha()
之前调用 .mutate()
我有一个应用程序有一个非常奇怪的问题。有时,在启动应用程序时,所有片段都会遇到此问题。看起来 GPU 正在用它做一些奇特的事情。 在下面的动画 Gif 中,您可以清楚地看到具有上述工件的 PreferenceFragment。
编辑 1。看起来我有一个特定的片段,一旦 "draws" 在屏幕上出现错误。使用 .replace
切换片段实际上不会 "clean" 问题。
我该如何调试它?
看起来像是来自 GPU 的垃圾。
您需要查看的第一件事是您的 window 背景(然后是各种全屏布局背景)。
它可能被定义为 null 或另一个类似的问题。
好的,我的问题是因为我有我的主题
<item name="android:windowBackground">@color/dark</color>
其中 dark
是设置为 #313131
然后我有一个视图,我用它作为其他一些内容的封面来使底层视图变暗,如下所示:
<FrameLayout
android:layout_width="match_parent"
android:layout_height="200dp">
<ImageView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_gravity="center"
android:src="@drawable/mydrawable"
/>
<View
android:id="@+id/coverview"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:background="@color/dark"/>
</FrameLayout>
以编程方式,我必须使用 coverView.getBackground().setAlpha((int)(0.6f*255));
令人惊讶的是,这个新的 alpha 值也被应用到 window 背景并产生了很多你在我的问题中看到的伪影(即使在切换片段后封面视图不再在查看树)
默认情况下,从同一资源加载的所有可绘制实例共享一个公共状态。因此我的代码是错误的,我需要在应用新的 alpha 值之前在后台调用 .mutate。
除了我错了@调用 ..setAlpha
而没有调用 .mutate()
GPU 闪烁对我来说仍然是一个谜
为什么GPU会闪烁?正如 Christophe here:
所指出的the GPU flickers cause the background is now translucent and the system tries to blend it with what was currently in the empty buffer (mostly garbage).
为了展示 bug 问题,我创建了一个 github 存储库,其中包含一个展示该问题的示例项目:https://github.com/vekexasia/gpuflickering-background-alpha
解决方法:几个。如果您想使用相同的方法(这也会导致过度绘制),您应该以编程方式设置颜色,然后为其设置 alpha 值。像这样:
coverView.setBackground(new ColorDrawable(getResources().getColor(R.color.dark)));
更好的方法是应用 ColorFilter to the ImageView or if you're using Picasso
use a Transformation
另一种方法是在 .setAlpha()
.mutate()