如何在主Activity完成后从服务显示Toast?

Ale*_*ber 13 service android toast android-service android-toast

更新: 我不同意这是一个重复 - 因为我正在寻找一种方法退出主应用程序,仍然显示从服务Toast.

一个非常简单的测试应用程序中我有2个按钮:

截图

单击任何按钮将运行带有相应操作字符串的服务("打开"或"闪烁") -

OpenActivity.java:

public class OpenActivity extends Activity {
    private Intent mServiceIntent;

    @Override
    public void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_open);
        mServiceIntent = new Intent(this, RegionService.class);
   }

    public void openCar(View v) {
        mServiceIntent.setAction("open");
        startService(mServiceIntent);
    }
Run Code Online (Sandbox Code Playgroud)

RegionService.java:

public class RegionService extends IntentService {
    private static final String TAG = "RegionService";

    @Override
    protected void onHandleIntent(Intent intent) {
        Log.d(TAG, "Received an intent: " + intent);
        String action = intent.getAction();
        Log.d(TAG, "Received an action: " + action);

        if(action.equals("open")) {
            Toast.makeText(this, 
                    getString(R.string.car_opened), 
                    Toast.LENGTH_SHORT).show();
        } 
Run Code Online (Sandbox Code Playgroud)

不幸的是我的应用崩溃了:

D/RegionService(24506): Received an intent: Intent { act=open cmp=de.afarber.mynotification/.RegionService }

D/RegionService(24506): Received an action: open

W/MessageQueue(24506): Handler (android.os.Handler) {422768a8} sending message to a Handler on a dead thread
W/MessageQueue(24506): java.lang.RuntimeException: Handler (android.os.Handler) {422768a8} sending message to a Handler on a dead thread
W/MessageQueue(24506):  at android.os.MessageQueue.enqueueMessage(MessageQueue.java:320)
W/MessageQueue(24506):  at android.os.Handler.enqueueMessage(Handler.java:626)
W/MessageQueue(24506):  at android.os.Handler.sendMessageAtTime(Handler.java:595)
W/MessageQueue(24506):  at android.os.Handler.sendMessageDelayed(Handler.java:566)
W/MessageQueue(24506):  at android.os.Handler.post(Handler.java:326)
W/MessageQueue(24506):  at android.widget.Toast$TN.hide(Toast.java:370)
W/MessageQueue(24506):  at android.app.ITransientNotification$Stub.onTransact(ITransientNotification.java:54)
W/MessageQueue(24506):  at android.os.Binder.execTransact(Binder.java:412)
W/MessageQueue(24506):  at dalvik.system.NativeStart.run(Native Method)
Run Code Online (Sandbox Code Playgroud)

作为Android编程新手,我想知道如何以正确的方式显示来自服务的Toast

我想我已经在Android Home上看过Toasts(即设备屏幕上没有活动,但仍然有Toasts).

我的背景:我想从我的服务中监控一个信标设备并显示一些文本Toast - 即使我的应用程序已关闭.

kal*_*pvs 38

OnHandleIntent将在一个differant中运行,Thread 所以你Toast在一个不允许在android中的线程中显示

所以改变你的代码就像这样

Handler handler = new Handler(Looper.getMainLooper());
handler.post(new Runnable() {

    @Override
    public void run() {
         Toast.makeText(getApplicationContext(), 
                       getString(R.string.car_opened), 
                       Toast.LENGTH_SHORT).show();              
    }
});
Run Code Online (Sandbox Code Playgroud)

服务中的这个死线程

IntentService将创建一个线程来处理新的intent,并在任务完成后立即终止它.因此,Toast将不受死线控制.

当屏幕上显示toast时,您应该在控制台中看到一些例外.


Lit*_*ild 5

IntentService有一些限制:

它无法直接与您的用户界面交互.要将结果放在UI中,您必须将它们发送到活动.

一切都发生在后台线程而不是UI线程上,所以你需要一种不同的方式,如下所示:

@Override 
public void onCreate() { 
    super.onCreate(); 
    mHandler = new Handler(); 
} 

@Override 
protected void onHandleIntent(Intent intent) {
    mHandler.post(new Runnable() {            
        @Override 
        public void run() { 
            Toast.makeText(MyIntentService.this, "Hello Toast!", Toast.LENGTH_LONG).show();                
        } 
    }); 
} 
Run Code Online (Sandbox Code Playgroud)

来源:在IntentService中创建的Toast永远不会消失