这个问题可能看起来很宽泛,但我会尽力总结一下。
因此,我正在 Play 商店 Multi Timer Free 上复制示例应用程序
应用程序用于设置多个计时器。
我几乎已经完成了该应用程序。但我面临着电池优化和警报管理器的一些问题,特别是华为和荣耀(中国Andorid操作系统)。我的前台服务在一段时间后停止工作。
问题: 即使没有电池优化白名单,上面提到的示例应用程序也能非常出色地工作。解决这个问题的办法是什么?
我几乎尝试了下面链接中提到的所有内容。但没有运气
Doze mode - do foreground services continue to run?
How to handle background services in ANDROID O?
How to turn off battery optimization on Huawei devices
How to turn off battery optimization on the Huawei devices
How to turn off battery optimization on Huawei devices
Huawei device killing my foreground service, even with dontkillmyapp.com's solution
Optimize for Doze and App Standby
Android M startActivity battery optimization
Battery optimizations (wakelocks) on Huawei EMUI 4.0+
service killed when app cloes just in huawei device
Oreo (8.1) cannot start activity on lock screen
Creating a never ending background service in Android > 7
How does doze mode affect background/foreground services, with/without partial/full wakelocks?
What to do if alarms or sleep tracking don’t work?
Sample Code, When pressed device lock/unlock button, I want a simple TOAST to be shown when SCREEN_ON broadcast is received. This works fine for some time.
But in Huawei device => After killing the app by swipe -> after a 1 - 2 minutes my toast will stop working.
package com.demo.forgroundservicedemo
import android.content.Intent
import android.os.IBinder
import androidx.core.app.NotificationCompat
import android.os.Build
import android.app.*
import android.app.NotificationManager
import android.app.NotificationChannel
import android.content.BroadcastReceiver
import android.content.Context
import android.content.IntentFilter
import android.graphics.Color
import android.util.Log
import androidx.annotation.RequiresApi
import android.os.SystemClock
import android.app.AlarmManager
import android.app.PendingIntent
import android.widget.Toast
class ForegroundService : Service() {
override fun onCreate() {
Log.e("ForegroundService", "onCreate called")
super.onCreate()
}
@RequiresApi(Build.VERSION_CODES.O)
private fun startMyOwnForeground() {
val NOTIFICATION_CHANNEL_ID = CONST.CHANNELID
val channelName = CONST.channelName
val chan = NotificationChannel(
NOTIFICATION_CHANNEL_ID,
channelName,
NotificationManager.IMPORTANCE_NONE
)
chan.lightColor = Color.BLUE
chan.lockscreenVisibility = Notification.VISIBILITY_PRIVATE
val manager = getSystemService(Context.NOTIFICATION_SERVICE) as NotificationManager
manager.createNotificationChannel(chan)
val notificationIntent = Intent(this, MainActivity::class.java)
notificationIntent.flags = Intent.FLAG_ACTIVITY_CLEAR_TOP or Intent.FLAG_ACTIVITY_SINGLE_TOP
val intent = PendingIntent.getActivity(
this, 0,
notificationIntent, 0
)
val notificationBuilder = NotificationCompat.Builder(this, NOTIFICATION_CHANNEL_ID)
notificationBuilder.setContentIntent(intent)
val notification = notificationBuilder.setOngoing(true)
.setSmallIcon(R.mipmap.ic_launcher)
.setContentTitle(CONST.serviceTitle)
.setPriority(NotificationManager.IMPORTANCE_MIN)
.setCategory(Notification.CATEGORY_SERVICE)
.setAutoCancel(false)
.build()
notification.flags = notification.flags or Notification.FLAG_AUTO_CANCEL
startForeground(2, notification)
}
override fun onStartCommand(intent: Intent?, flags: Int, startId: Int): Int {
Log.e("ForegroundService", "onStartCommand called")
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.O) {
Log.e("SDK_INT", ">= Build.VERSION_CODES.O")
startMyOwnForeground()
} else {
startForeground(1, Notification())
}
registerBroadcastReceiver()
return START_STICKY
}
override fun onDestroy() {
Log.e("ForegroundService", "onDestroy called")
super.onDestroy()
}
override fun onBind(intent: Intent?): IBinder? {
return null
}
private var mPowerKeyReceiver: BroadcastReceiver? = null
private fun registerBroadcastReceiver() {
Log.e("registerBroadcast", "called")
val theFilter = IntentFilter()
/** System Defined Broadcast */
theFilter.addAction(Intent.ACTION_SCREEN_ON)
//theFilter.addAction(Intent.ACTION_SCREEN_OFF)
mPowerKeyReceiver = object : BroadcastReceiver() {
override fun onReceive(context: Context?, intent: Intent?) {
Log.e("onReceive", "onReceive called")
val strAction = intent!!.action
if (strAction == Intent.ACTION_SCREEN_ON) {
Toast.makeText(context, "SCREEN ON", Toast.LENGTH_LONG).show()
}
}
}
applicationContext.registerReceiver(mPowerKeyReceiver, theFilter)
}
private fun unregisterReceiver() {
val apiLevel = Build.VERSION.SDK_INT
if (apiLevel >= 7) {
try {
applicationContext.unregisterReceiver(mPowerKeyReceiver)
} catch (e: IllegalArgumentException) {
mPowerKeyReceiver = null
}
} else {
applicationContext.unregisterReceiver(mPowerKeyReceiver)
mPowerKeyReceiver = null
}
}
override fun onTaskRemoved(rootIntent: Intent?) {
super.onTaskRemoved(rootIntent)
Log.e("onTaskRemoved", "onTaskRemoved called")
unregisterReceiver()
val restartService = Intent(
applicationContext,
this.javaClass
)
restartService.setPackage(packageName)
val restartServicePI = PendingIntent.getService(
applicationContext, 1, restartService,
PendingIntent.FLAG_ONE_SHOT
)
val alarmService =
applicationContext.getSystemService(Context.ALARM_SERVICE) as AlarmManager
alarmService.setExactAndAllowWhileIdle(
AlarmManager.ELAPSED_REALTIME,
SystemClock.elapsedRealtime() + 500,
restartServicePI
)
}
}
最佳答案
也许问题是您在安排闹钟时没有setRepeating
?
我基本上做同样的事情(当屏幕打开时更新小部件),我这样做:
alarmManager.setRepeating(AlarmManager.RTC, System.currentTimeMillis() + 1000, interval, pendingIntent)
关于android - 华为、荣耀手机电池优化、前台服务,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/59857099/