将startForeground()与意图服务一起使用 [英] Using startForeground() with an Intent Service

查看:595
本文介绍了将startForeground()与意图服务一起使用的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我正在尝试保持一项对屏幕开/关更改做出反应的服务.该服务将在一段时间内运行良好,但最终将被终止.我现在正尝试使用startForeground()来保持该进程运行,但是它似乎仍在消亡.我知道没有办法可以使进程永远存活,没有错误,但是我觉得我一定做错了,因为添加startForeground()不会增加进程的寿命.另外,作为附带说明,由于未调用unregisterReceiver()(除非通过用户手动按下按钮进行手动操作),Logcat抱怨存在泄漏..但是,由于我要完成的工作性质,接收方需要运行,直到明确告知要停止为止.

I am trying to keep alive a service that reacts to screen on/off changes. The service would work perfectly for awhile, but then eventually it would be killed. I am now attempting to use startForeground() to keep the process alive, but it still seems to be dying. I understand that there is no way to keep a process alive forever, without error, but I feel like I must be doing something wrong, as adding startForeground() added no extra life to the process. Also, as a side note, Logcat complains about a leak, as unregisterReceiver() is not called (except manually by a button press from the user).. however, due to the nature of what I am trying to accomplish, the receiver needs to run until explicitly told to stop.

有什么建议吗?

相关代码:

public class UpdateService extends IntentService {

        public UpdateService() {
        super(null);

    }

        @Override
        protected void onHandleIntent(Intent intent) {

            final int myID = 1234;


            Intent notificationintent = new Intent(this, Main.class);
            notificationintent.setFlags(Intent.FLAG_ACTIVITY_CLEAR_TOP | Intent.FLAG_ACTIVITY_SINGLE_TOP);
            PendingIntent pendIntent = PendingIntent.getActivity(this, 0, notificationintent, 0);


            Notification notice = new Notification(R.drawable.icon_image, "***********", System.currentTimeMillis());


            notice.setLatestEventInfo(this, "*************", "***********", pendIntent);

            notice.flags |= Notification.FLAG_NO_CLEAR;
            startForeground(myID, notice);

            boolean screenOn = intent.getBooleanExtra("screen_state", false);


// Blah Blah Blah......


        }

        @Override
        public IBinder onBind(Intent arg0) {
            // TODO Auto-generated method stub
            return null;
        }

}

推荐答案

(已更新)我想可能存在以下情况:

(Updated) I suppose there are the following possible cases:

1) <> IntentService的文档状态:

该服务根据需要启动,依次使用 工作线程,并在工作耗尽时自行停止.

the service is started as needed, handles each Intent in turn using a worker thread, and stops itself when it runs out of work.

因此,可能是您的服务通常在onHandleIntent()完成后停止了(特别是,正如您提到的,startForeground()并没有增加进程的寿命).

So, it might be that your service is normally stopped after onHandleIntent() is finished (especially, as you mentioned that startForeground() added no extra life to the process).

2),您可能会尝试检查它是否与睡眠的设备有关(或者您可能正在按计划启动设备并唤醒设备-在这种情况下,您可能需要获取 WakeLock )

2) You might try to check if it's somehow can be related to device going to sleep (or maybe you are starting your service by schedule and awkening device - in this case you might need to acquire WakeLock)

3)在极少数情况下,系统仍然可以终止前台进程-因此,如果您在onHandleIntent()中进行了大量分配(确实很多)和其他工作(而不是"Blah Blah Blah")-您可能会遇到它-但我认为情况并非如此.

3) In the very rare cases, the system still can kill foreground process - so if you do a lot of allocations (really lot) and some other work in onHandleIntent() (instead of "Blah Blah Blah" at your code) - you might run into it - but I suppose it's not the case.

问题的标题是将startForeground()与IntentService一起使用"-也想澄清一下: 我相信没有什么(架构,最佳做法,android框架,IntentService的Java文档)可以阻止您将Intent服务作为前台运行.当然,您需要仔细考虑其用法以及您是否确实需要前台服务.可以在此处获得一些建议.有关示例代码,请参见下文. (如果您将多个作业/意图排队到IntentService中,则示例代码最终可能会显示多个通知,因此根据您的需要,可能会有更好的解决方案.)

As question's title is "Using startForeground() with an IntentService" - would like to clarify that too: I believe nothing (architecture, best practices, android framework, java docs for IntentService) prevents you from running your intent service as a foreground. Of course you need to thought out carefully its usage and whether you actually need a foreground service. Some ideas are available here. For sample code see below. (Sample code can end up showing multiple notifications if you queued multiple jobs/intents into IntentService, so there might be better solution depending on your need.)

public class ForegroundService extends IntentService {

    private static final String TAG = "FrgrndSrv";

    public ForegroundService() {
        super(TAG);
    }

    @Override
    protected void onHandleIntent(Intent intent) {

        Notification.Builder builder = new Notification.Builder(getBaseContext())
                .setSmallIcon(R.drawable.ic_foreground_service)
                .setTicker("Your Ticker") // use something from something from R.string
                .setContentTitle("Your content title") // use something from something from
                .setContentText("Your content text") // use something from something from
                .setProgress(0, 0, true); // display indeterminate progress

        startForeground(1, builder.build());
        try {
            doIntesiveWork();
        } finally {
            stopForeground(true);
        }
    }

    protected void doIntesiveWork() {
        // Below should be your logic that takes lots of time
        try {
            Thread.sleep(10000);
        } catch (InterruptedException e) {
            e.printStackTrace();
        }
    }
}

这篇关于将startForeground()与意图服务一起使用的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆