kopia lustrzana https://github.com/meshtastic/Meshtastic-Android
feat: Initial implementation of low battery notifications for nodes (#1653)
* Add initial implementation of low battery notifications for locally-connected and favorite nodes * Hopefully make detekt happy * detekt pls. * Deduplicate some of the code * detekt'dpull/1659/head
rodzic
f7731f0c98
commit
c7c29cb1c1
|
@ -213,6 +213,9 @@ class MeshService : Service(), Logging {
|
|||
private var locationFlow: Job? = null
|
||||
private var mqttMessageFlow: Job? = null
|
||||
|
||||
private val batteryPercentUnsupported = 0.0
|
||||
private val batteryPercentLowThreshold = 20.0
|
||||
|
||||
private fun getSenderName(packet: DataPacket?): String {
|
||||
val name = nodeDBbyID[packet?.from]?.user?.longName
|
||||
return name ?: getString(R.string.unknown_username)
|
||||
|
@ -939,7 +942,16 @@ class MeshService : Service(), Logging {
|
|||
}
|
||||
updateNodeInfo(fromNum) {
|
||||
when {
|
||||
t.hasDeviceMetrics() -> it.deviceTelemetry = t
|
||||
t.hasDeviceMetrics() -> {
|
||||
it.deviceTelemetry = t
|
||||
val isRemote = (fromNum != myNodeNum)
|
||||
if (fromNum == myNodeNum || (isRemote && it.isFavorite)) {
|
||||
if (t.deviceMetrics.voltage > batteryPercentUnsupported &&
|
||||
t.deviceMetrics.batteryLevel < batteryPercentLowThreshold) {
|
||||
serviceNotifications.showOrUpdateLowBatteryNotification(it, isRemote)
|
||||
}
|
||||
}
|
||||
}
|
||||
t.hasEnvironmentMetrics() -> it.environmentTelemetry = t
|
||||
t.hasPowerMetrics() -> it.powerTelemetry = t
|
||||
}
|
||||
|
|
|
@ -65,6 +65,8 @@ class MeshServiceNotifications(
|
|||
createMessageNotificationChannel()
|
||||
createAlertNotificationChannel()
|
||||
createNewNodeNotificationChannel()
|
||||
createLowBatteryNotificationChannel()
|
||||
createLowBatteryRemoteNotificationChannel()
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -173,6 +175,60 @@ class MeshServiceNotifications(
|
|||
return channelId
|
||||
}
|
||||
|
||||
@RequiresApi(Build.VERSION_CODES.O)
|
||||
private fun createLowBatteryNotificationChannel(): String {
|
||||
val channelId = "low_battery"
|
||||
if (notificationManager.getNotificationChannel(channelId) == null) {
|
||||
val channelName = context.getString(R.string.meshtastic_low_battery_notifications)
|
||||
val channel = NotificationChannel(
|
||||
channelId,
|
||||
channelName,
|
||||
NotificationManager.IMPORTANCE_HIGH
|
||||
).apply {
|
||||
lightColor = notificationLightColor
|
||||
lockscreenVisibility = Notification.VISIBILITY_PUBLIC
|
||||
setShowBadge(true)
|
||||
setSound(
|
||||
RingtoneManager.getDefaultUri(RingtoneManager.TYPE_NOTIFICATION),
|
||||
AudioAttributes.Builder()
|
||||
.setUsage(AudioAttributes.USAGE_NOTIFICATION)
|
||||
.setContentType(AudioAttributes.CONTENT_TYPE_SONIFICATION)
|
||||
.build()
|
||||
)
|
||||
}
|
||||
notificationManager.createNotificationChannel(channel)
|
||||
}
|
||||
return channelId
|
||||
}
|
||||
|
||||
// FIXME, Once we get a dedicated settings page in the app, this function should be removed and
|
||||
// the feature should be implemented in the regular low battery notification stuff
|
||||
@RequiresApi(Build.VERSION_CODES.O)
|
||||
private fun createLowBatteryRemoteNotificationChannel(): String {
|
||||
val channelId = "low_battery_remote"
|
||||
if (notificationManager.getNotificationChannel(channelId) == null) {
|
||||
val channelName = context.getString(R.string.meshtastic_low_battery_temporary_remote_notifications)
|
||||
val channel = NotificationChannel(
|
||||
channelId,
|
||||
channelName,
|
||||
NotificationManager.IMPORTANCE_HIGH
|
||||
).apply {
|
||||
lightColor = notificationLightColor
|
||||
lockscreenVisibility = Notification.VISIBILITY_PUBLIC
|
||||
setShowBadge(true)
|
||||
setSound(
|
||||
RingtoneManager.getDefaultUri(RingtoneManager.TYPE_NOTIFICATION),
|
||||
AudioAttributes.Builder()
|
||||
.setUsage(AudioAttributes.USAGE_NOTIFICATION)
|
||||
.setContentType(AudioAttributes.CONTENT_TYPE_SONIFICATION)
|
||||
.build()
|
||||
)
|
||||
}
|
||||
notificationManager.createNotificationChannel(channel)
|
||||
}
|
||||
return channelId
|
||||
}
|
||||
|
||||
private val channelId: String by lazy {
|
||||
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.O) {
|
||||
createNotificationChannel()
|
||||
|
@ -209,6 +265,24 @@ class MeshServiceNotifications(
|
|||
}
|
||||
}
|
||||
|
||||
private val lowBatteryChannelId: String by lazy {
|
||||
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.O) {
|
||||
createLowBatteryNotificationChannel()
|
||||
} else {
|
||||
""
|
||||
}
|
||||
}
|
||||
|
||||
// FIXME, Once we get a dedicated settings page in the app, this function should be removed and
|
||||
// the feature should be implemented in the regular low battery notification stuff
|
||||
private val lowBatteryRemoteChannelId: String by lazy {
|
||||
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.O) {
|
||||
createLowBatteryRemoteNotificationChannel()
|
||||
} else {
|
||||
""
|
||||
}
|
||||
}
|
||||
|
||||
private fun LocalStats?.formatToString(): String = this?.allFields?.mapNotNull { (k, v) ->
|
||||
when (k.name) {
|
||||
"num_online_nodes", "num_total_nodes" -> return@mapNotNull null
|
||||
|
@ -258,6 +332,13 @@ class MeshServiceNotifications(
|
|||
)
|
||||
}
|
||||
|
||||
fun showOrUpdateLowBatteryNotification(node: NodeEntity, isRemote: Boolean) {
|
||||
notificationManager.notify(
|
||||
node.num, // show unique notifications
|
||||
createLowBatteryNotification(node, isRemote)
|
||||
)
|
||||
}
|
||||
|
||||
private val openAppIntent: PendingIntent by lazy {
|
||||
PendingIntent.getActivity(
|
||||
context,
|
||||
|
@ -409,4 +490,51 @@ class MeshServiceNotifications(
|
|||
}
|
||||
return newNodeSeenNotificationBuilder.build()
|
||||
}
|
||||
|
||||
lateinit var lowBatteryRemoteNotificationBuilder: NotificationCompat.Builder
|
||||
lateinit var lowBatteryNotificationBuilder: NotificationCompat.Builder
|
||||
private fun createLowBatteryNotification(node: NodeEntity, isRemote: Boolean): Notification {
|
||||
val tempNotificationBuilder: NotificationCompat.Builder = if (isRemote) {
|
||||
if (!::lowBatteryRemoteNotificationBuilder.isInitialized) {
|
||||
lowBatteryRemoteNotificationBuilder = commonBuilder(lowBatteryChannelId)
|
||||
}
|
||||
lowBatteryRemoteNotificationBuilder
|
||||
} else {
|
||||
if (!::lowBatteryNotificationBuilder.isInitialized) {
|
||||
lowBatteryNotificationBuilder = commonBuilder(lowBatteryRemoteChannelId)
|
||||
}
|
||||
lowBatteryNotificationBuilder
|
||||
}
|
||||
with(tempNotificationBuilder) {
|
||||
priority = NotificationCompat.PRIORITY_DEFAULT
|
||||
setCategory(Notification.CATEGORY_STATUS)
|
||||
setAutoCancel(true)
|
||||
setShowWhen(true)
|
||||
setOnlyAlertOnce(true)
|
||||
setWhen(System.currentTimeMillis())
|
||||
setContentTitle(
|
||||
context.getString(R.string.low_battery_title).format(
|
||||
node.shortName
|
||||
)
|
||||
)
|
||||
val message = context.getString(R.string.low_battery_message).format(
|
||||
node.longName,
|
||||
node.deviceMetrics.batteryLevel
|
||||
)
|
||||
message.let {
|
||||
setContentText(it)
|
||||
setStyle(
|
||||
NotificationCompat.BigTextStyle()
|
||||
.bigText(it),
|
||||
)
|
||||
}
|
||||
}
|
||||
if (isRemote) {
|
||||
lowBatteryRemoteNotificationBuilder = tempNotificationBuilder
|
||||
return lowBatteryRemoteNotificationBuilder.build()
|
||||
} else {
|
||||
lowBatteryNotificationBuilder = tempNotificationBuilder
|
||||
return lowBatteryNotificationBuilder.build()
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
@ -337,4 +337,8 @@
|
|||
<string name="are_you_sure">Are you sure?</string>
|
||||
<string name="router_role_confirmation_text"><![CDATA[I have read the <a href="https://meshtastic.org/docs/configuration/radio/device/#roles">Device Role Documentation</a> and the blog post about <a href="http://meshtastic.org/blog/choosing-the-right-device-role">Choosing The Right Device Role</a>.]]></string>
|
||||
<string name="i_know_what_i_m_doing">I know what I\'m doing.</string>
|
||||
<string name="low_battery_message">Node %s has a low battery (%d%%)</string>
|
||||
<string name="meshtastic_low_battery_notifications">Low battery notifications</string>
|
||||
<string name="low_battery_title">Low battery: %s</string>
|
||||
<string name="meshtastic_low_battery_temporary_remote_notifications">Low battery notifications (favorite nodes)</string>
|
||||
</resources>
|
||||
|
|
Ładowanie…
Reference in New Issue