我有一个后台线程,它会休眠1/10秒,然后重新循环。我希望它能使屏幕无效,这样它就会重新绘制并做一个简单的动画。我唯一能使屏幕无效的方法似乎是在Runnable中执行,这假设会有很多开销。
有没有一种方法可以在不使用可运行程序的情况下使线程内的屏幕无效??
Android SDK有一个内置的API用于此目的-View.postInvalidate():
public void postInvalidate()
导致在事件循环的后续循环中发生失效。使用此选项可使非UI线程中的视图无效。
只有当此视图附加到窗口时,才能从UI线程外部调用此方法。
另请参见
invalidate() postInvalidateDelayed(long)
从后台线程调用任何与UI相关的API都是不合法的。因此,您需要使用Runnable
。
如果后台线程所做的唯一事情就是睡眠,那么您可能可以在不使用线程的情况下,通过使用CountDownTimer
类来实现同样的效果。或者,您可以使用Handler.postAtTime()
API来计划Runnable
在未来的某个毫秒数内在UI线程上运行(同样,不使用单独的线程)。
我实际上认为开销可以忽略不计。但您可以使用AsyncTask
,如下所示:
new AsyncTask<Void, Void, Void>() {
/* (non-Javadoc)
* @see android.os.AsyncTask#doInBackground(Params[])
*/
@Override
protected Void doInBackground(Void... params) {
while(true) { //probably want some other challenge here
Thread.sleep(1000 / 10);
publishProgress();
}
return null;
}
/* (non-Javadoc)
* @see android.os.AsyncTask#onProgressUpdate(Progress[])
*/
@Override
protected void onProgressUpdate(Void... values) {
super.onProgressUpdate(values);
mMyView.invalidate();
}
}.execute();
这很好,因为onProgressUpdate会自动在UIThread上运行,所以你不必每次都创建一个新的可运行程序。。。
尝试向线程中的处理程序发送消息,并在handleMessage中使其无效。这可能会奏效。或者像Salil Pandit所说的那样使用AsyncTask。我认为Async更好。