我该如何在线程中显示Toast消息?
我该如何在线程中显示Toast消息?
你可以通过调用Activity
的runOnUiThread
方法来实现:
activity.runOnUiThread(new Runnable() {
public void run() {
Toast.makeText(activity, "Hello", Toast.LENGTH_SHORT).show();
}
});
Activity
实例,你可以使用简单的辅助类代替,参见这里:https://dev59.com/tXXYa4cB1Zd3GeqP-MYG#18280318。 - Oleksii K.Thread
/AsyncTask
中使用MyActivity.this.runOnUiThread()
可以正常工作。 - Anthony Atkinson我喜欢在我的活动中有一个名为showToast
的方法,我可以从任何地方调用它...
public void showToast(final String toast)
{
runOnUiThread(() -> Toast.makeText(MyActivity.this, toast, Toast.LENGTH_SHORT).show());
}
然后我最频繁地在任何线程中从MyActivity
中调用它,像这样...
showToast(getString(R.string.MyMessage));
这与其他答案类似,但更新了可用的新API并且更加简洁。另外,不假设您处于Activity上下文中。
public class MyService extends AnyContextSubclass {
public void postToastMessage(final String message) {
Handler handler = new Handler(Looper.getMainLooper());
handler.post(new Runnable() {
@Override
public void run() {
Toast.makeText(getContext(), message, Toast.LENGTH_LONG).show();
}
});
}
}
一种适用于几乎任何地方的方法,包括你没有Activity
或View
的地方,是获取一个指向主线程的Handler
,然后显示toast:
public void toast(final Context context, final String text) {
Handler handler = new Handler(Looper.getMainLooper());
handler.post(new Runnable() {
public void run() {
Toast.makeText(context, text, Toast.LENGTH_LONG).show();
}
});
}
这种方法的优势在于它适用于任何Context
,包括Service
和Application
。
Activity activity = // reference to an Activity
// or
View view = // reference to a View
activity.runOnUiThread(new Runnable() {
@Override
public void run() {
showToast(activity);
}
});
// or
view.post(new Runnable() {
@Override
public void run() {
showToast(view.getContext());
}
});
private void showToast(Context ctx) {
Toast.makeText(ctx, "Hi!", Toast.LENGTH_SHORT).show();
}
HandlerThread
创建一个Handler:requestHandler
responseHandler
,并重写handleMessage
方法post
一个Runnable
任务到requestHandler
Runnable
任务中,在responseHandler
上调用sendMessage
sendMessage
结果会调用responseHandler
中的handleMessage
。Message
中获取属性并处理它,更新UI示例代码:
/* Handler thread */
HandlerThread handlerThread = new HandlerThread("HandlerThread");
handlerThread.start();
Handler requestHandler = new Handler(handlerThread.getLooper());
final Handler responseHandler = new Handler(Looper.getMainLooper()) {
@Override
public void handleMessage(Message msg) {
//txtView.setText((String) msg.obj);
Toast.makeText(MainActivity.this,
"Runnable on HandlerThread is completed and got result:"+(String)msg.obj,
Toast.LENGTH_LONG)
.show();
}
};
for ( int i=0; i<5; i++) {
Runnable myRunnable = new Runnable() {
@Override
public void run() {
try {
/* Add your business logic here and construct the
Messgae which should be handled in UI thread. For
example sake, just sending a simple Text here*/
String text = "" + (++rId);
Message msg = new Message();
msg.obj = text.toString();
responseHandler.sendMessage(msg);
System.out.println(text.toString());
} catch (Exception err) {
err.printStackTrace();
}
}
};
requestHandler.post(myRunnable);
}
有用的文章:
handler.sendMessage();
post()
方法handler.post();
runOnUiThread()
view.post()
您可以使用 Looper
发送 Toast
消息。请访问此链接了解更多详情。
public void showToastInThread(final Context context,final String str){
Looper.prepare();
MessageQueue queue = Looper.myQueue();
queue.addIdleHandler(new IdleHandler() {
int mReqCount = 0;
@Override
public boolean queueIdle() {
if (++mReqCount == 2) {
Looper.myLooper().quit();
return false;
} else
return true;
}
});
Toast.makeText(context, str,Toast.LENGTH_LONG).show();
Looper.loop();
}
它被称为线程中的上下文。可以从要显示toast的Activity
中获取Activity.getContext()
。
我基于mjaggard的回答提出了以下方法:
public static void toastAnywhere(final String text) {
Handler handler = new Handler(Looper.getMainLooper());
handler.post(new Runnable() {
public void run() {
Toast.makeText(SuperApplication.getInstance().getApplicationContext(), text,
Toast.LENGTH_LONG).show();
}
});
}
对我很有帮助。
使用runOnUiThread的Kotlin代码
runOnUiThread(
object : Runnable {
override fun run() {
Toast.makeText(applicationContext, "Calling from runOnUiThread()", Toast.LENGTH_SHORT)
}
}
)