From cde3afdcd98cb6bab4b9c170402512dd75978a59 Mon Sep 17 00:00:00 2001 From: darken Date: Wed, 26 Jan 2022 01:01:01 +0100 Subject: [PATCH] Average RSSI --- .../eu/darken/capod/pods/core/PodDevice.kt | 4 +- .../darken/capod/pods/core/apple/ApplePods.kt | 55 ++++++++++--------- .../pods/core/apple/UnknownAppleDevice.kt | 8 ++- .../pods/core/apple/airpods/AirPodsGen1.kt | 12 ++-- .../pods/core/apple/airpods/AirPodsGen2.kt | 10 ++-- .../pods/core/apple/airpods/AirPodsGen3.kt | 10 ++-- .../pods/core/apple/airpods/AirPodsMax.kt | 6 +- .../pods/core/apple/airpods/AirPodsPro.kt | 10 ++-- .../capod/pods/core/apple/beats/BeatsFlex.kt | 8 ++- .../capod/pods/core/apple/beats/BeatsSolo3.kt | 8 ++- .../pods/core/apple/beats/BeatsStudio3.kt | 8 ++- .../capod/pods/core/apple/beats/BeatsX.kt | 8 ++- .../pods/core/apple/beats/PowerBeats3.kt | 8 ++- .../pods/core/apple/beats/PowerBeatsPro.kt | 10 ++-- 14 files changed, 96 insertions(+), 69 deletions(-) diff --git a/app/src/main/java/eu/darken/capod/pods/core/PodDevice.kt b/app/src/main/java/eu/darken/capod/pods/core/PodDevice.kt index 84728592..064ab2a3 100644 --- a/app/src/main/java/eu/darken/capod/pods/core/PodDevice.kt +++ b/app/src/main/java/eu/darken/capod/pods/core/PodDevice.kt @@ -20,8 +20,10 @@ interface PodDevice { val scanResult: BleScanResult + val rssiHistory: List + val rssi: Int - get() = scanResult.rssi + get() = rssiHistory.sum() / rssiHistory.size /** * This is not correct but it works ¯\_(ツ)_/¯ diff --git a/app/src/main/java/eu/darken/capod/pods/core/apple/ApplePods.kt b/app/src/main/java/eu/darken/capod/pods/core/apple/ApplePods.kt index a85dc981..af86b446 100644 --- a/app/src/main/java/eu/darken/capod/pods/core/apple/ApplePods.kt +++ b/app/src/main/java/eu/darken/capod/pods/core/apple/ApplePods.kt @@ -67,6 +67,7 @@ interface ApplePods : PodDevice { val identifier: PodDevice.Id, val scanResult: BleScanResult, val message: ProximityPairing.Message, + val rssiHistory: List = emptyList() ) { val address: String get() = scanResult.address @@ -85,46 +86,46 @@ interface ApplePods : PodDevice { private val knownDevs = mutableMapOf() - internal fun recognizeDevice(scanResult: BleScanResult, message: ProximityPairing.Message): PodDevice.Id { + internal fun recognizeDevice(scanResult: BleScanResult, message: ProximityPairing.Message): KnownDevice { val address = scanResult.address - var identifier: PodDevice.Id? = null + var recognizedDevice: KnownDevice? = knownDevs.values + .firstOrNull { it.address == address } + ?.also { log(tag, VERBOSE) { "recognizeDevice: Recovered previous ID via address: $it" } } - knownDevs.values.firstOrNull { it.address == address }?.let { - log(tag, VERBOSE) { "recognizeDevice: Recovered previous ID via address: $it" } - knownDevs[it.identifier] = it.copy( - scanResult = scanResult, - message = message, - ) - identifier = it.identifier - } - - if (identifier == null) { + if (recognizedDevice == null) { val currentMarkers = message.getRecogMarkers() - knownDevs.values + recognizedDevice = knownDevs.values .firstOrNull { it.message.getRecogMarkers() == currentMarkers } - ?.let { + ?.also { log(tag, DEBUG) { "recognizeDevice: Close match based similarity markers." } log(tag, DEBUG) { "recognizeDevice: Old marker: ${it.message.getRecogMarkers()}" } log(tag, DEBUG) { "recognizeDevice: New marker: $currentMarkers" } - knownDevs[it.identifier] = it.copy( - scanResult = scanResult, - message = message, - ) - identifier = it.identifier } } - if (identifier == null) { + recognizedDevice = if (recognizedDevice == null) { log(tag, VERBOSE) { "recognizeDevice: Mapping as new device" } - identifier = PodDevice.Id() + KnownDevice( + identifier = PodDevice.Id(), + scanResult = scanResult, + message = message, + rssiHistory = listOf(scanResult.rssi) + ) + } else { + recognizedDevice.copy( + scanResult = scanResult, + message = message, + rssiHistory = recognizedDevice.rssiHistory + .toMutableList() + .let { + if (it.size > 2) it.removeAt(0) + it.plus(scanResult.rssi) + } + ) } - knownDevs[identifier!!] = KnownDevice( - identifier = identifier!!, - scanResult = scanResult, - message = message - ) + knownDevs[recognizedDevice.identifier] = recognizedDevice knownDevs.values.toList().forEach { knownDevice -> if (knownDevice.isOlderThan(Duration.ofSeconds(20))) { @@ -133,7 +134,7 @@ interface ApplePods : PodDevice { } } - return identifier!! + return recognizedDevice } data class ModelInfo( diff --git a/app/src/main/java/eu/darken/capod/pods/core/apple/UnknownAppleDevice.kt b/app/src/main/java/eu/darken/capod/pods/core/apple/UnknownAppleDevice.kt index 8dcfc8fb..4d7ff023 100644 --- a/app/src/main/java/eu/darken/capod/pods/core/apple/UnknownAppleDevice.kt +++ b/app/src/main/java/eu/darken/capod/pods/core/apple/UnknownAppleDevice.kt @@ -13,7 +13,8 @@ data class UnknownAppleDevice( override val identifier: PodDevice.Id = PodDevice.Id(), override val lastSeenAt: Instant = Instant.now(), override val scanResult: BleScanResult, - override val proximityMessage: ProximityPairing.Message + override val proximityMessage: ProximityPairing.Message, + override val rssiHistory: List ) : ApplePods { override val model: PodDevice.Model = PodDevice.Model.UNKNOWN @@ -27,12 +28,13 @@ data class UnknownAppleDevice( scanResult: BleScanResult, proximityMessage: ProximityPairing.Message, ): ApplePods { - val identifier = recognizeDevice(scanResult, proximityMessage) + val recognized = recognizeDevice(scanResult, proximityMessage) return UnknownAppleDevice( - identifier = identifier, + identifier = recognized.identifier, scanResult = scanResult, proximityMessage = proximityMessage, + rssiHistory = recognized.rssiHistory, ) } } diff --git a/app/src/main/java/eu/darken/capod/pods/core/apple/airpods/AirPodsGen1.kt b/app/src/main/java/eu/darken/capod/pods/core/apple/airpods/AirPodsGen1.kt index 4874d806..6b231e93 100644 --- a/app/src/main/java/eu/darken/capod/pods/core/apple/airpods/AirPodsGen1.kt +++ b/app/src/main/java/eu/darken/capod/pods/core/apple/airpods/AirPodsGen1.kt @@ -14,7 +14,8 @@ data class AirPodsGen1 constructor( override val lastSeenAt: Instant = Instant.now(), override val scanResult: BleScanResult, override val proximityMessage: ProximityPairing.Message, - private val cachedBatteryPercentage: Float? + private val cachedBatteryPercentage: Float?, + override val rssiHistory: List ) : DualApplePods { override val model: PodDevice.Model = PodDevice.Model.AIRPODS_GEN1 @@ -28,16 +29,17 @@ data class AirPodsGen1 constructor( proximityMessage.getModelInfo().full == DEVICE_CODE override fun create(scanResult: BleScanResult, proximityMessage: ProximityPairing.Message): ApplePods { - val identifier = recognizeDevice(scanResult, proximityMessage) + val recognized = recognizeDevice(scanResult, proximityMessage) val device = AirPodsGen1( - identifier = identifier, + identifier = recognized.identifier, scanResult = scanResult, proximityMessage = proximityMessage, - cachedBatteryPercentage = cachedValues[identifier]?.caseBatteryPercentage + cachedBatteryPercentage = cachedValues[recognized.identifier]?.caseBatteryPercentage, + rssiHistory = recognized.rssiHistory, ) - cachedValues[identifier] = ValueCache( + cachedValues[recognized.identifier] = ValueCache( caseBatteryPercentage = device.batteryCasePercent ) diff --git a/app/src/main/java/eu/darken/capod/pods/core/apple/airpods/AirPodsGen2.kt b/app/src/main/java/eu/darken/capod/pods/core/apple/airpods/AirPodsGen2.kt index e914aa7a..cb2e23ca 100644 --- a/app/src/main/java/eu/darken/capod/pods/core/apple/airpods/AirPodsGen2.kt +++ b/app/src/main/java/eu/darken/capod/pods/core/apple/airpods/AirPodsGen2.kt @@ -15,6 +15,7 @@ data class AirPodsGen2 constructor( override val scanResult: BleScanResult, override val proximityMessage: ProximityPairing.Message, private val cachedBatteryPercentage: Float?, + override val rssiHistory: List, ) : DualApplePods { override val model: PodDevice.Model = PodDevice.Model.AIRPODS_GEN2 @@ -28,16 +29,17 @@ data class AirPodsGen2 constructor( proximityMessage.getModelInfo().full == DEVICE_CODE override fun create(scanResult: BleScanResult, proximityMessage: ProximityPairing.Message): ApplePods { - val identifier = recognizeDevice(scanResult, proximityMessage) + val recognized = recognizeDevice(scanResult, proximityMessage) val device = AirPodsGen2( - identifier = identifier, + identifier = recognized.identifier, scanResult = scanResult, proximityMessage = proximityMessage, - cachedBatteryPercentage = cachedValues[identifier]?.caseBatteryPercentage + cachedBatteryPercentage = cachedValues[recognized.identifier]?.caseBatteryPercentage, + rssiHistory = recognized.rssiHistory, ) - cachedValues[identifier] = ValueCache( + cachedValues[recognized.identifier] = ValueCache( caseBatteryPercentage = device.batteryCasePercent ) diff --git a/app/src/main/java/eu/darken/capod/pods/core/apple/airpods/AirPodsGen3.kt b/app/src/main/java/eu/darken/capod/pods/core/apple/airpods/AirPodsGen3.kt index 73c87ed9..7a7a8fc2 100644 --- a/app/src/main/java/eu/darken/capod/pods/core/apple/airpods/AirPodsGen3.kt +++ b/app/src/main/java/eu/darken/capod/pods/core/apple/airpods/AirPodsGen3.kt @@ -15,6 +15,7 @@ data class AirPodsGen3 constructor( override val scanResult: BleScanResult, override val proximityMessage: ProximityPairing.Message, private val cachedBatteryPercentage: Float?, + override val rssiHistory: List, ) : DualApplePods { override val model: PodDevice.Model = PodDevice.Model.AIRPODS_GEN3 @@ -27,16 +28,17 @@ data class AirPodsGen3 constructor( proximityMessage.getModelInfo().full == DEVICE_CODE override fun create(scanResult: BleScanResult, proximityMessage: ProximityPairing.Message): ApplePods { - val identifier = recognizeDevice(scanResult, proximityMessage) + val recognized = recognizeDevice(scanResult, proximityMessage) val device = AirPodsGen3( - identifier = identifier, + identifier = recognized.identifier, scanResult = scanResult, proximityMessage = proximityMessage, - cachedBatteryPercentage = cachedValues[identifier]?.caseBatteryPercentage + cachedBatteryPercentage = cachedValues[recognized.identifier]?.caseBatteryPercentage, + rssiHistory = recognized.rssiHistory, ) - cachedValues[identifier] = ValueCache( + cachedValues[recognized.identifier] = ValueCache( caseBatteryPercentage = device.batteryCasePercent ) diff --git a/app/src/main/java/eu/darken/capod/pods/core/apple/airpods/AirPodsMax.kt b/app/src/main/java/eu/darken/capod/pods/core/apple/airpods/AirPodsMax.kt index de88c6fe..b01f0cc4 100644 --- a/app/src/main/java/eu/darken/capod/pods/core/apple/airpods/AirPodsMax.kt +++ b/app/src/main/java/eu/darken/capod/pods/core/apple/airpods/AirPodsMax.kt @@ -14,6 +14,7 @@ data class AirPodsMax( override val lastSeenAt: Instant = Instant.now(), override val scanResult: BleScanResult, override val proximityMessage: ProximityPairing.Message, + override val rssiHistory: List, ) : SingleApplePods { override val model: PodDevice.Model = PodDevice.Model.AIRPODS_MAX @@ -24,12 +25,13 @@ data class AirPodsMax( proximityMessage.getModelInfo().dirty == DEVICE_CODE_DIRTY override fun create(scanResult: BleScanResult, proximityMessage: ProximityPairing.Message): ApplePods { - val identifier = recognizeDevice(scanResult, proximityMessage) + val recognized = recognizeDevice(scanResult, proximityMessage) return AirPodsMax( - identifier = identifier, + identifier = recognized.identifier, scanResult = scanResult, proximityMessage = proximityMessage, + rssiHistory = recognized.rssiHistory, ) } diff --git a/app/src/main/java/eu/darken/capod/pods/core/apple/airpods/AirPodsPro.kt b/app/src/main/java/eu/darken/capod/pods/core/apple/airpods/AirPodsPro.kt index 35713722..8c8adc14 100644 --- a/app/src/main/java/eu/darken/capod/pods/core/apple/airpods/AirPodsPro.kt +++ b/app/src/main/java/eu/darken/capod/pods/core/apple/airpods/AirPodsPro.kt @@ -15,6 +15,7 @@ data class AirPodsPro( override val scanResult: BleScanResult, override val proximityMessage: ProximityPairing.Message, private val cachedBatteryPercentage: Float?, + override val rssiHistory: List, ) : DualApplePods { override val model: PodDevice.Model = PodDevice.Model.AIRPODS_PRO @@ -28,16 +29,17 @@ data class AirPodsPro( proximityMessage.getModelInfo().full == DEVICE_CODE override fun create(scanResult: BleScanResult, proximityMessage: ProximityPairing.Message): ApplePods { - val identifier = recognizeDevice(scanResult, proximityMessage) + val recognized = recognizeDevice(scanResult, proximityMessage) val device = AirPodsPro( - identifier = identifier, + identifier = recognized.identifier, scanResult = scanResult, proximityMessage = proximityMessage, - cachedBatteryPercentage = cachedValues[identifier]?.caseBatteryPercentage + cachedBatteryPercentage = cachedValues[recognized.identifier]?.caseBatteryPercentage, + rssiHistory = recognized.rssiHistory, ) - cachedValues[identifier] = ValueCache( + cachedValues[recognized.identifier] = ValueCache( caseBatteryPercentage = device.batteryCasePercent ) diff --git a/app/src/main/java/eu/darken/capod/pods/core/apple/beats/BeatsFlex.kt b/app/src/main/java/eu/darken/capod/pods/core/apple/beats/BeatsFlex.kt index 53756911..be35feb4 100644 --- a/app/src/main/java/eu/darken/capod/pods/core/apple/beats/BeatsFlex.kt +++ b/app/src/main/java/eu/darken/capod/pods/core/apple/beats/BeatsFlex.kt @@ -13,7 +13,8 @@ data class BeatsFlex( override val identifier: PodDevice.Id = PodDevice.Id(), override val lastSeenAt: Instant = Instant.now(), override val scanResult: BleScanResult, - override val proximityMessage: ProximityPairing.Message + override val proximityMessage: ProximityPairing.Message, + override val rssiHistory: List, ) : BasicSingleApplePods { override val model: PodDevice.Model = PodDevice.Model.BEATS_FLEX @@ -24,12 +25,13 @@ data class BeatsFlex( proximityMessage.getModelInfo().full == DEVICE_CODE override fun create(scanResult: BleScanResult, proximityMessage: ProximityPairing.Message): ApplePods { - val identifier = recognizeDevice(scanResult, proximityMessage) + val recognized = recognizeDevice(scanResult, proximityMessage) return BeatsFlex( - identifier = identifier, + identifier = recognized.identifier, scanResult = scanResult, proximityMessage = proximityMessage, + rssiHistory = recognized.rssiHistory, ) } diff --git a/app/src/main/java/eu/darken/capod/pods/core/apple/beats/BeatsSolo3.kt b/app/src/main/java/eu/darken/capod/pods/core/apple/beats/BeatsSolo3.kt index 29c5b6d8..dd322ec4 100644 --- a/app/src/main/java/eu/darken/capod/pods/core/apple/beats/BeatsSolo3.kt +++ b/app/src/main/java/eu/darken/capod/pods/core/apple/beats/BeatsSolo3.kt @@ -13,7 +13,8 @@ data class BeatsSolo3( override val identifier: PodDevice.Id = PodDevice.Id(), override val lastSeenAt: Instant = Instant.now(), override val scanResult: BleScanResult, - override val proximityMessage: ProximityPairing.Message + override val proximityMessage: ProximityPairing.Message, + override val rssiHistory: List, ) : BasicSingleApplePods { override val model: PodDevice.Model = PodDevice.Model.BEATS_SOLO_3 @@ -24,12 +25,13 @@ data class BeatsSolo3( proximityMessage.getModelInfo().full == DEVICE_CODE override fun create(scanResult: BleScanResult, proximityMessage: ProximityPairing.Message): ApplePods { - val identifier = recognizeDevice(scanResult, proximityMessage) + val recognized = recognizeDevice(scanResult, proximityMessage) return BeatsSolo3( - identifier = identifier, + identifier = recognized.identifier, scanResult = scanResult, proximityMessage = proximityMessage, + rssiHistory = recognized.rssiHistory, ) } diff --git a/app/src/main/java/eu/darken/capod/pods/core/apple/beats/BeatsStudio3.kt b/app/src/main/java/eu/darken/capod/pods/core/apple/beats/BeatsStudio3.kt index 99e53b83..f31205f8 100644 --- a/app/src/main/java/eu/darken/capod/pods/core/apple/beats/BeatsStudio3.kt +++ b/app/src/main/java/eu/darken/capod/pods/core/apple/beats/BeatsStudio3.kt @@ -13,7 +13,8 @@ data class BeatsStudio3( override val identifier: PodDevice.Id = PodDevice.Id(), override val lastSeenAt: Instant = Instant.now(), override val scanResult: BleScanResult, - override val proximityMessage: ProximityPairing.Message + override val proximityMessage: ProximityPairing.Message, + override val rssiHistory: List, ) : BasicSingleApplePods { override val model: PodDevice.Model = PodDevice.Model.BEATS_STUDIO_3 @@ -24,12 +25,13 @@ data class BeatsStudio3( proximityMessage.getModelInfo().dirty == DEVICE_CODE_DIRTY override fun create(scanResult: BleScanResult, proximityMessage: ProximityPairing.Message): ApplePods { - val identifier = recognizeDevice(scanResult, proximityMessage) + val recognized = recognizeDevice(scanResult, proximityMessage) return BeatsStudio3( - identifier = identifier, + identifier = recognized.identifier, scanResult = scanResult, proximityMessage = proximityMessage, + rssiHistory = recognized.rssiHistory, ) } diff --git a/app/src/main/java/eu/darken/capod/pods/core/apple/beats/BeatsX.kt b/app/src/main/java/eu/darken/capod/pods/core/apple/beats/BeatsX.kt index 57c13d3f..09e4db69 100644 --- a/app/src/main/java/eu/darken/capod/pods/core/apple/beats/BeatsX.kt +++ b/app/src/main/java/eu/darken/capod/pods/core/apple/beats/BeatsX.kt @@ -13,7 +13,8 @@ data class BeatsX( override val identifier: PodDevice.Id = PodDevice.Id(), override val lastSeenAt: Instant = Instant.now(), override val scanResult: BleScanResult, - override val proximityMessage: ProximityPairing.Message + override val proximityMessage: ProximityPairing.Message, + override val rssiHistory: List, ) : BasicSingleApplePods { override val model: PodDevice.Model = PodDevice.Model.BEATS_X @@ -24,12 +25,13 @@ data class BeatsX( proximityMessage.getModelInfo().full == DEVICE_CODE override fun create(scanResult: BleScanResult, proximityMessage: ProximityPairing.Message): ApplePods { - val identifier = recognizeDevice(scanResult, proximityMessage) + val recognized = recognizeDevice(scanResult, proximityMessage) return BeatsX( - identifier = identifier, + identifier = recognized.identifier, scanResult = scanResult, proximityMessage = proximityMessage, + rssiHistory = recognized.rssiHistory, ) } diff --git a/app/src/main/java/eu/darken/capod/pods/core/apple/beats/PowerBeats3.kt b/app/src/main/java/eu/darken/capod/pods/core/apple/beats/PowerBeats3.kt index 16787800..7e4c2086 100644 --- a/app/src/main/java/eu/darken/capod/pods/core/apple/beats/PowerBeats3.kt +++ b/app/src/main/java/eu/darken/capod/pods/core/apple/beats/PowerBeats3.kt @@ -13,7 +13,8 @@ data class PowerBeats3( override val identifier: PodDevice.Id = PodDevice.Id(), override val lastSeenAt: Instant = Instant.now(), override val scanResult: BleScanResult, - override val proximityMessage: ProximityPairing.Message + override val proximityMessage: ProximityPairing.Message, + override val rssiHistory: List, ) : BasicSingleApplePods { override val model: PodDevice.Model = PodDevice.Model.POWERBEATS_3 @@ -23,12 +24,13 @@ data class PowerBeats3( proximityMessage.getModelInfo().full == DEVICE_CODE override fun create(scanResult: BleScanResult, proximityMessage: ProximityPairing.Message): ApplePods { - val identifier = recognizeDevice(scanResult, proximityMessage) + val recognized = recognizeDevice(scanResult, proximityMessage) return PowerBeats3( - identifier = identifier, + identifier = recognized.identifier, scanResult = scanResult, proximityMessage = proximityMessage, + rssiHistory = recognized.rssiHistory, ) } } diff --git a/app/src/main/java/eu/darken/capod/pods/core/apple/beats/PowerBeatsPro.kt b/app/src/main/java/eu/darken/capod/pods/core/apple/beats/PowerBeatsPro.kt index 07fb9ea4..28a78a36 100644 --- a/app/src/main/java/eu/darken/capod/pods/core/apple/beats/PowerBeatsPro.kt +++ b/app/src/main/java/eu/darken/capod/pods/core/apple/beats/PowerBeatsPro.kt @@ -15,6 +15,7 @@ data class PowerBeatsPro( override val scanResult: BleScanResult, override val proximityMessage: ProximityPairing.Message, private val cachedBatteryPercentage: Float?, + override val rssiHistory: List, ) : DualApplePods { override val model: PodDevice.Model = PodDevice.Model.POWERBEATS_PRO @@ -28,16 +29,17 @@ data class PowerBeatsPro( proximityMessage.getModelInfo().dirty == DEVICE_CODE_DIRTY override fun create(scanResult: BleScanResult, proximityMessage: ProximityPairing.Message): ApplePods { - val identifier = recognizeDevice(scanResult, proximityMessage) + val recognized = recognizeDevice(scanResult, proximityMessage) val device = PowerBeatsPro( - identifier = identifier, + identifier = recognized.identifier, scanResult = scanResult, proximityMessage = proximityMessage, - cachedBatteryPercentage = cachedValues[identifier]?.caseBatteryPercentage + cachedBatteryPercentage = cachedValues[recognized.identifier]?.caseBatteryPercentage, + rssiHistory = recognized.rssiHistory, ) - cachedValues[identifier] = ValueCache( + cachedValues[recognized.identifier] = ValueCache( caseBatteryPercentage = device.batteryCasePercent )