代码之家  ›  专栏  ›  技术社区  ›  SkAppCoding

Adroid Kotlin广播接收器被调用两次

  •  1
  • SkAppCoding  · 技术社区  · 7 月前

    我实现了一个BroadcastReceiver。问题是,如果它被触发,它总是会被调用两次。我不明白为什么。我希望你能帮助我。

    舱单是我登记接收人的唯一地方。我没有在代码中再次注册它。

    报警是在主活动的onCreate方法中安排的

    enter image description here

    AndroidManifest.xml:

    <receiver android:name=".alarmManager.domain.AlarmReceiver"/>
    

    主活动onCreate():

    setContent {
        WorkingTimeCalculatorTheme {
            WorkingTimeCalculator()
    
            //Day Reminder Alarm
            val scheduler = AndroidAlarmSchedulerImpl(LocalContext.current)
    
            val localTimeReminder = LocalTime.of(10, 30)
            val nowNanos = LocalTime.now().toNanoOfDay()
            val notificationNanos = localTimeReminder.toNanoOfDay()
            val localDateReminder =
                LocalDate.now().plusDays(if (notificationNanos <= nowNanos) 1 else 0)
    
            val alarmItem: AlarmItem = AlarmItem(
                time = LocalDateTime.now()
                    .plusSeconds(5),//LocalDateTime.of(localDateReminder, localTimeReminder),
                title = stringResource(R.string.EnterWorkingHours),
                message = stringResource(R.string.PleaseSetTheTimesForThisDay),
                notificationType = NotificationType.DayUnchangedReminder.value
            )
            alarmItem.let(scheduler::schedule)
        }
    }
    

    报警时间表Impl:

    class AndroidAlarmSchedulerImpl(
        private val context: Context
    ) : AlarmScheduler {
    
        private val alarmManager = context.getSystemService(AlarmManager::class.java)
    
        override fun schedule(item: AlarmItem) {
            val intent = Intent(context, AlarmReceiver::class.java).apply {
                putExtra("EXTRA_TITLE", item.title)
                putExtra("EXTRA_MESSAGE", item.message)
                putExtra("EXTRA_NOTIFICATION_TYPE", item.notificationType)
            }
            alarmManager.setRepeating(
                AlarmManager.RTC_WAKEUP,
                item.time.atZone(ZoneId.systemDefault()).toEpochSecond() * 1000,
                60000, //AlarmManager.INTERVAL_DAY,
                PendingIntent.getBroadcast(
                    context,
                    item.hashCode(),
                    intent,
                    PendingIntent.FLAG_UPDATE_CURRENT or PendingIntent.FLAG_IMMUTABLE
                )
    
            )
        }
    
        override fun cancel(item: AlarmItem) {
            alarmManager.cancel(
                PendingIntent.getBroadcast(
                    context,
                    item.hashCode(),
                    Intent(context, AlarmReceiver::class.java),
                    PendingIntent.FLAG_UPDATE_CURRENT or PendingIntent.FLAG_IMMUTABLE
                )
            )
        }
    }
    

    报警接收器:

    @AndroidEntryPoint
    class AlarmReceiver : BroadcastReceiver() {
    
        @Inject
        lateinit var addDayReminderNotificationSingleton: AddDayReminderNotification
    
        override fun onReceive(context: Context?, intent: Intent?) {
            var title = intent?.getStringExtra("EXTRA_TITLE") ?: return
            title += "\n${LocalDate.now().toDateString()}"
            val message = intent.getStringExtra("EXTRA_MESSAGE") ?: return
            val notificationType =
                NotificationType.fromValue(intent.getIntExtra("EXTRA_NOTIFICATION_TYPE", 0))?.value
    
            Log.d("AlarmTest", "BroadCastReceiver Called")
    
            val notification = Notification(
                id = null,
                date = LocalDate.now(),
                time = LocalTime.now(),
                title = title,
                description = message,
                unread = true,
                notificationType = notificationType ?: 0
            )
            if (::addDayReminderNotificationSingleton.isInitialized) {
                CoroutineScope(Dispatchers.IO).launch {
                    addDayReminderNotificationSingleton.addNotification(context, notification)
                }
            } else {
                Log.e("AlarmReceiver", "addDayReminderNotificationSingleton is not initialized")
            }
    
    
        }
    }
    
    1 回复  |  直到 7 月前
        1
  •  1
  •   CommonsWare    7 月前

    您每次都在安排闹钟 WorkingTimeCalculatorTheme() 重组。要么:

    • 将此逻辑移动到其他更好地控制生命周期的地方,例如存储库或视图模型中,或
    • 使用 LaunchedEffect() or DisposableEffect() 在可堆肥的创作过程中,只安排做一次那项工作

    第一种选择是 极大地 对于类似的事情来说,它更优越 AlarmManager 警报。