Android - 加载drawables而不跳帧
Posted
技术标签:
【中文标题】Android - 加载drawables而不跳帧【英文标题】:Android - Loading drawables without skipping frames 【发布时间】:2016-05-08 13:39:29 【问题描述】:好的,所以我在活动中使用可绘制的 PNG(1200 x 1920, 30kb)作为背景。我的 XML 代码的 sn-p 如下所示。我的问题是应用程序跳帧并且响应滞后。谁能告诉我为什么会这样,或者解决我的问题的好方法?我仍然希望能够使用这个 PNG 文件作为背景。谢谢
XML 片段:
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools"
android:layout_
android:layout_
android:background="@drawable/MY_PNG_BACKGROUND"
tools:context=".MainActivity">
Logcat 消息:
I/Choreographer: Skipped 53 frames! The application may be doing too much work on its main thread.
我看过的东西:
Imageview skipped frames(如果有人能告诉我如何在 XML 中而不是在 Java 中以编程方式进行操作,这可能对我有用) background images causing frames to be skipped【问题讨论】:
“谁能告诉我为什么会这样”——解码一个 9MB 的图像不会很快(其中 9MB 是指使用的堆空间量)。这不仅需要花一点时间,而且可能会触发一个或多个GC_FOR_ALLOC
调用以释放内存以便能够处理图像。另外,由于您选择将其放在可绘制资源中,Android 可能会重新采样图像以处理屏幕密度差异。而且,最重要的是,绝大多数 Android 设备的屏幕分辨率较低,无法使用如此大的高分辨率图像。
对不起,我忘了提到所提到的 PNG 是用于平板电脑视图的。唯一的解决方案是拥有更小/更少分辨率的背景吗? @CommonsWare
我建议您首先确认问题的确切性质,例如使用 Android Studio 进行方法跟踪并查看您将时间花在哪里。 53 帧几乎是主应用程序线程上占用的整整一秒。然后,查找紧接在您的 Choreographer
之前的其他 LogCat 消息(例如,GC_FOR_ALLOC
),以尝试确定这是否是您的问题的一部分。您可能尝试在后台线程上预加载此图像,尽管我从未尝试过将其用于资源。另外,请确保此资源位于 res/drawable-nodpi/
或 res/drawable-anydpi/
。
好的,我在图形方面遇到了很多麻烦,所以我可能会考虑预加载图像。如果您碰巧知道这样做的好方法并想将其放入答案中,我可以将其标记为正确。感谢@CommonsWare 的帮助
【参考方案1】:
感谢 cmets 中 CommonsWare 的一些帮助,我能够解决这个问题。我在后台使用 AsyncTask 在我的 java 类中预加载了 drawable。这是一个代码示例:
public class MainActivity extends Activity
@Override
protected void onCreate(Bundle savedInstanceState)
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
//Calling the task to be done in the background, in this case loading the drawable
new LoadDrawable().execute();
private class LoadDrawable extends AsyncTask<Drawable, Void, Drawable>
@Override
protected Drawable doInBackground(Drawable... params)
//Loading the drawable in the background
final Drawable image = getResources().getDrawable(R.drawable.my_drawable);
//After the drawable is loaded, onPostExecute is called
return image;
@Override
protected void onPostExecute(Drawable loaded)
//Hide the progress bar
ProgressBar progress = (ProgressBar) findViewById(R.id.progress_bar);
progress.setVisibility(View.GONE);
//Set the layout background with your loaded drawable
RelativeLayout layout = (RelativeLayout) findViewById(R.id.my_layout);
layout.setBackgroundDrawable(loaded);
@Override
protected void onPreExecute()
@Override
protected void onProgressUpdate(Void... values)
【讨论】:
我尝试了同样的方法,但仍然有非常明显的滞后以上是关于Android - 加载drawables而不跳帧的主要内容,如果未能解决你的问题,请参考以下文章
android ImageLoader 混淆加载drawable出现黑色图片的解决方案