簡體   English   中英

使應用服務在后台不可見

[英]Making app service work invisible in background

我有一個無限運行后台服務的應用程序,同時還隱藏了應用程序圖標並將其隱藏在后台堆棧中,因此在運行時用戶不會看到它:

       val componentName = ComponentName(this, FullscreenActivity::class.java)
       p.setComponentEnabledSetting(
           componentName,
           PackageManager.COMPONENT_ENABLED_STATE_DISABLED,
           PackageManager.DONT_KILL_APP
       )

這就是我從片段啟動服務的方式:

parentFragment?.activity?.startService(
                    Intent(
                        requireParentFragment().requireActivity().applicationContext,
                        RescueService::class.java
                    ).addFlags(Intent.FLAG_ACTIVITY_NEW_TASK)
                )

它成功地從后台隱藏圖標和應用程序並且服務繼續運行,當我按下手機上的方形按鈕以顯示后台應用程序正在運行時,我沒有看到我想要的應用程序,但是如果我點擊“ X”按鈕清除所有后台應用程序它也會殺死我的應用程序並且我的服務會死掉,即使應用程序沒有像我提到的那樣出現在那里。

任何想法是什么讓服務在完成后死亡? 因為幾天前我對我的應用程序進行了一些更改之前並沒有發生這種情況..

我所做的更改之一是將我的Service變成LifecycleService因為我需要我的服務來觀察需要LifecycleOwner的 livedata。這可能是我的服務在清除后台堆棧時死亡的原因嗎?

歡迎所有建議!

EDIT1 - 這是我使用WorkManager執行語音錄制的TestService 。我調用hideApp()從手機中隱藏圖標並使應用程序在后台不可見:

class RecordingWork(
    context: Context,
    params: WorkerParameters
) : CoroutineWorker(context, params) {

    override val coroutineContext = Dispatchers.Main
    override suspend fun doWork(): Result {

        mSpeechRecognizer.startListening(mSpeechRecognizerIntent)
        return Result.success()
    }
}

private lateinit var mSpeechRecognizer: SpeechRecognizer
private val mSpeechRecognizerIntent = Intent(RecognizerIntent.ACTION_RECOGNIZE_SPEECH)

class TestService : Service() {

    private lateinit var workManager: WorkManager

    override fun onStartCommand(intent: Intent?, flags: Int, startId: Int): Int {
        Log.d("TestService", "onStartCommand called")
        hideApp()
        prepareVoiceRecording()
        workManager = WorkManager.getInstance(applicationContext)
        workManager.enqueue(OneTimeWorkRequestBuilder<RecordingWork>().build())

        return START_REDELIVER_INTENT
    }

    override fun onBind(intent: Intent?): IBinder? {
        return null
    }

    fun prepareVoiceRecording() {
        mSpeechRecognizer = SpeechRecognizer.createSpeechRecognizer(applicationContext)
        mSpeechRecognizerIntent.putExtra(
            RecognizerIntent.EXTRA_LANGUAGE_MODEL,
            RecognizerIntent.LANGUAGE_MODEL_FREE_FORM
        )
        mSpeechRecognizerIntent.putExtra(
            RecognizerIntent.EXTRA_LANGUAGE,
            Locale.getDefault()
        )
        mSpeechRecognizer.setRecognitionListener(
            object : RecognitionListener {

                @RequiresApi(Build.VERSION_CODES.M)
                override fun onError(i: Int) {
                    Log.d(TAG, "onErrorCalled error is $i")
                    if (i == SpeechRecognizer.ERROR_NETWORK || i == SpeechRecognizer.ERROR_SPEECH_TIMEOUT || i == SpeechRecognizer.ERROR_NO_MATCH) {
                        Log.d(TAG, "error triggered")
                        mSpeechRecognizer.destroy()
                        prepareVoiceRecording()
                        workManager.enqueue(OneTimeWorkRequestBuilder<RecordingWork>().build())

                    }
                }

                @RequiresApi(Build.VERSION_CODES.M)
                override fun onResults(bundle: Bundle) {
                    Log.d(TAG, "onResults Called")
                    //getting all the matches
                    val matches = bundle
                        .getStringArrayList(SpeechRecognizer.RESULTS_RECOGNITION)!!
                    workManager.enqueue(OneTimeWorkRequestBuilder<RecordingWork>().build())
                }

 private fun hideApp() {
        val componentName = ComponentName(
            this,
            WelcomeScreenActivity::class.java
        )
        packageManager.setComponentEnabledSetting(
            componentName,
            PackageManager.COMPONENT_ENABLED_STATE_DISABLED,
            PackageManager.DONT_KILL_APP
        )
    }

該服務確實可以通過每次重新安排 Worker 來重復錄制語音。 但是在清除 backstack 時這個服務也會死掉(即使應用程序因為hideApp()沒有出現在那里)

使用 workManager 進行長時間運行的后台任務(某些設備,如小米手機,如果您不這樣做,操作系統會殺死您的應用程序,您需要將應用程序列入白名單以節省電量)和隱藏應用程序圖標在 android X 中不起作用(僅限系統應用程序可以隱藏他們的圖標)

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM