diff --git a/app/src/main/java/info/nightscout/androidaps/MainApp.kt b/app/src/main/java/info/nightscout/androidaps/MainApp.kt index c3c7c58292..3f0134f640 100644 --- a/app/src/main/java/info/nightscout/androidaps/MainApp.kt +++ b/app/src/main/java/info/nightscout/androidaps/MainApp.kt @@ -136,7 +136,7 @@ class MainApp : DaggerApplication() { ) WorkManager.getInstance(this).enqueueUniquePeriodicWork( KeepAliveWorker.KA_0, - ExistingPeriodicWorkPolicy.REPLACE, + ExistingPeriodicWorkPolicy.UPDATE, PeriodicWorkRequest.Builder(KeepAliveWorker::class.java, 15, TimeUnit.MINUTES) .setInputData(Data.Builder().putString("schedule", KeepAliveWorker.KA_0).build()) .setInitialDelay(5, TimeUnit.SECONDS) diff --git a/build.gradle b/build.gradle index cf55d71710..68d70c3ac3 100644 --- a/build.gradle +++ b/build.gradle @@ -7,10 +7,10 @@ buildscript { rxjava_version = '3.1.6' rxandroid_version = '3.0.2' rxkotlin_version = '3.0.1' - room_version = '2.5.1' + room_version = '2.5.2' lifecycle_version = '2.6.1' - dagger_version = '2.46.1' - coroutines_version = '1.7.1' + dagger_version = '2.47' + coroutines_version = '1.7.2' activity_version = '1.7.2' fragmentktx_version = '1.6.0' ormLite_version = '4.46' @@ -22,7 +22,8 @@ buildscript { constraintlayout_version = '2.1.4' preferencektx_version = '1.2.0' commonslang3_version = '3.12.0' - commonscodec_version = '1.15' + commonscodec_version = '1.16.0' + guava_version = '32.0.1-jre' jodatime_version = '2.10.14' work_version = '2.8.1' tink_version = '1.9.0' @@ -59,7 +60,7 @@ buildscript { dependencies { classpath 'com.android.tools.build:gradle:7.4.2' classpath 'com.google.gms:google-services:4.3.15' - classpath 'com.google.firebase:firebase-crashlytics-gradle:2.9.6' + classpath 'com.google.firebase:firebase-crashlytics-gradle:2.9.7' // NOTE: Do not place your application dependencies here; they belong // in the individual module build.gradle files @@ -75,7 +76,7 @@ buildscript { plugins { // Test Gradle build, keep disabled under normal circumstances // id "com.osacky.doctor" version "0.8.1" - id "org.jlleitschuh.gradle.ktlint" version "11.4.0" + id "org.jlleitschuh.gradle.ktlint" version "11.5.0" id 'org.barfuin.gradle.jacocolog' version '3.1.0' id 'org.jetbrains.kotlin.android' version "$kotlin_version" apply false } diff --git a/core/main/build.gradle b/core/main/build.gradle index b0e45f16e4..5a53aeae96 100644 --- a/core/main/build.gradle +++ b/core/main/build.gradle @@ -23,7 +23,7 @@ dependencies { api "org.jetbrains.kotlin:kotlin-stdlib-jdk8:$kotlin_version" - api 'com.google.guava:guava:32.0.1-jre' + api "com.google.guava:guava:$guava_version" api "androidx.activity:activity-ktx:$activity_version" api "androidx.appcompat:appcompat:$appcompat_version" diff --git a/core/main/src/main/res/drawable/ic_cp_heart_rate.xml b/core/main/src/main/res/drawable/ic_cp_heart_rate.xml new file mode 100644 index 0000000000..07f1fa61d0 --- /dev/null +++ b/core/main/src/main/res/drawable/ic_cp_heart_rate.xml @@ -0,0 +1,6 @@ + + + diff --git a/core/utils/build.gradle b/core/utils/build.gradle index 893687d51b..74dfc1e8ee 100644 --- a/core/utils/build.gradle +++ b/core/utils/build.gradle @@ -22,7 +22,7 @@ dependencies { implementation project(':app-wear-shared:shared') //Firebase - api platform('com.google.firebase:firebase-bom:32.1.1') + api platform('com.google.firebase:firebase-bom:32.2.0') api "com.google.firebase:firebase-analytics-ktx" api "com.google.firebase:firebase-crashlytics-ktx" // StatsActivity not in use now diff --git a/plugins/automation/src/main/java/info/nightscout/automation/AutomationPlugin.kt b/plugins/automation/src/main/java/info/nightscout/automation/AutomationPlugin.kt index caaaea9eeb..422ff20022 100644 --- a/plugins/automation/src/main/java/info/nightscout/automation/AutomationPlugin.kt +++ b/plugins/automation/src/main/java/info/nightscout/automation/AutomationPlugin.kt @@ -31,6 +31,7 @@ import info.nightscout.automation.triggers.TriggerBolusAgo import info.nightscout.automation.triggers.TriggerCOB import info.nightscout.automation.triggers.TriggerConnector import info.nightscout.automation.triggers.TriggerDelta +import info.nightscout.automation.triggers.TriggerHeartRate import info.nightscout.automation.triggers.TriggerIob import info.nightscout.automation.triggers.TriggerLocation import info.nightscout.automation.triggers.TriggerProfilePercent @@ -41,6 +42,7 @@ import info.nightscout.automation.triggers.TriggerTempTargetValue import info.nightscout.automation.triggers.TriggerTime import info.nightscout.automation.triggers.TriggerTimeRange import info.nightscout.automation.triggers.TriggerWifiSsid +import info.nightscout.automation.ui.TimerUtil import info.nightscout.core.utils.fabric.FabricPrivacy import info.nightscout.interfaces.Config import info.nightscout.interfaces.GlucoseUnit @@ -53,7 +55,6 @@ import info.nightscout.interfaces.plugin.PluginBase import info.nightscout.interfaces.plugin.PluginDescription import info.nightscout.interfaces.plugin.PluginType import info.nightscout.interfaces.queue.Callback -import info.nightscout.automation.ui.TimerUtil import info.nightscout.rx.AapsSchedulers import info.nightscout.rx.bus.RxBus import info.nightscout.rx.events.EventBTChange @@ -406,6 +407,7 @@ class AutomationPlugin @Inject constructor( TriggerBolusAgo(injector), TriggerPumpLastConnection(injector), TriggerBTDevice(injector), + TriggerHeartRate(injector), ) } diff --git a/plugins/automation/src/main/java/info/nightscout/automation/di/AutomationModule.kt b/plugins/automation/src/main/java/info/nightscout/automation/di/AutomationModule.kt index e1d98ebc4e..a0dcd300eb 100644 --- a/plugins/automation/src/main/java/info/nightscout/automation/di/AutomationModule.kt +++ b/plugins/automation/src/main/java/info/nightscout/automation/di/AutomationModule.kt @@ -38,6 +38,7 @@ import info.nightscout.automation.triggers.TriggerCOB import info.nightscout.automation.triggers.TriggerConnector import info.nightscout.automation.triggers.TriggerDelta import info.nightscout.automation.triggers.TriggerDummy +import info.nightscout.automation.triggers.TriggerHeartRate import info.nightscout.automation.triggers.TriggerIob import info.nightscout.automation.triggers.TriggerLocation import info.nightscout.automation.triggers.TriggerProfilePercent @@ -75,6 +76,7 @@ abstract class AutomationModule { @ContributesAndroidInjector abstract fun triggerConnectorInjector(): TriggerConnector @ContributesAndroidInjector abstract fun triggerDeltaInjector(): TriggerDelta @ContributesAndroidInjector abstract fun triggerDummyInjector(): TriggerDummy + @ContributesAndroidInjector abstract fun triggerHeartRateInjector(): TriggerHeartRate @ContributesAndroidInjector abstract fun triggerIobInjector(): TriggerIob @ContributesAndroidInjector abstract fun triggerLocationInjector(): TriggerLocation @ContributesAndroidInjector abstract fun triggerProfilePercentInjector(): TriggerProfilePercent diff --git a/plugins/automation/src/main/java/info/nightscout/automation/triggers/Trigger.kt b/plugins/automation/src/main/java/info/nightscout/automation/triggers/Trigger.kt index d696ea9841..98bf38b5bb 100644 --- a/plugins/automation/src/main/java/info/nightscout/automation/triggers/Trigger.kt +++ b/plugins/automation/src/main/java/info/nightscout/automation/triggers/Trigger.kt @@ -95,6 +95,7 @@ abstract class Trigger(val injector: HasAndroidInjector) { TriggerConnector::class.java.simpleName -> TriggerConnector(injector).fromJSON(data.toString()) TriggerDelta::class.java.simpleName -> TriggerDelta(injector).fromJSON(data.toString()) TriggerDummy::class.java.simpleName -> TriggerDummy(injector).fromJSON(data.toString()) + TriggerHeartRate::class.java.simpleName -> TriggerHeartRate(injector).fromJSON(data.toString()) TriggerLocation::class.java.simpleName -> TriggerLocation(injector).fromJSON(data.toString()) TriggerProfilePercent::class.java.simpleName -> TriggerProfilePercent(injector).fromJSON(data.toString()) TriggerPumpLastConnection::class.java.simpleName -> TriggerPumpLastConnection(injector).fromJSON(data.toString()) diff --git a/plugins/automation/src/main/java/info/nightscout/automation/triggers/TriggerHeartRate.kt b/plugins/automation/src/main/java/info/nightscout/automation/triggers/TriggerHeartRate.kt new file mode 100644 index 0000000000..57309bb9f7 --- /dev/null +++ b/plugins/automation/src/main/java/info/nightscout/automation/triggers/TriggerHeartRate.kt @@ -0,0 +1,79 @@ +package info.nightscout.automation.triggers + +import android.widget.LinearLayout +import androidx.annotation.VisibleForTesting +import com.google.common.base.Optional +import dagger.android.HasAndroidInjector +import info.nightscout.automation.R +import info.nightscout.automation.elements.Comparator +import info.nightscout.automation.elements.InputDouble +import info.nightscout.automation.elements.LabelWithElement +import info.nightscout.automation.elements.LayoutBuilder +import info.nightscout.automation.elements.StaticLabel +import info.nightscout.interfaces.utils.JsonHelper +import info.nightscout.rx.logging.LTag +import org.json.JSONObject +import java.text.DecimalFormat + +class TriggerHeartRate(injector: HasAndroidInjector) : Trigger(injector) { + + @VisibleForTesting val averageHeartRateDurationMillis = 330 * 1000L + private val minValue = 30 + private val maxValue = 250 + var heartRate: InputDouble = InputDouble(80.0, minValue.toDouble(), maxValue.toDouble(), 10.0, DecimalFormat("1")) + var comparator: Comparator = Comparator(rh).apply { + value = Comparator.Compare.IS_EQUAL_OR_GREATER + } + + override fun shouldRun(): Boolean { + if (comparator.value == Comparator.Compare.IS_NOT_AVAILABLE) { + aapsLogger.info(LTag.AUTOMATION, "HR ready, no limit set ${friendlyDescription()}") + return true + } + val start = dateUtil.now() - averageHeartRateDurationMillis + val hrs = repository.getHeartRatesFromTime(start) + val duration = hrs.takeUnless { it.isEmpty() }?.sumOf { hr -> hr.duration } ?: 0L + if (duration == 0L) { + aapsLogger.info(LTag.AUTOMATION, "HR not ready, no heart rate measured for ${friendlyDescription()}") + return false + } + val hr = hrs.sumOf { hr -> hr.beatsPerMinute * hr.duration } / duration.toDouble() + return comparator.value.check(hr, heartRate.value).also { + aapsLogger.info(LTag.AUTOMATION, "HR ${if (it) "" else "not "}ready for $hr for ${friendlyDescription()}") + } + } + + override fun dataJSON(): JSONObject = + JSONObject() + .put("heartRate", heartRate.value) + .put("comparator", comparator.value.toString()) + + override fun fromJSON(data: String): Trigger { + val d = JSONObject(data) + heartRate.setValue(JsonHelper.safeGetDouble(d, "heartRate")) + comparator.setValue(Comparator.Compare.valueOf(JsonHelper.safeGetString(d, "comparator")!!)) + return this + } + + override fun friendlyName(): Int = R.string.triggerHeartRate + + override fun friendlyDescription(): String = + rh.gs(R.string.triggerHeartRateDesc, rh.gs(comparator.value.stringRes), heartRate.value) + + override fun icon(): Optional = Optional.of(info.nightscout.core.main.R.drawable.ic_cp_heart_rate) + + override fun duplicate(): Trigger { + return TriggerHeartRate(injector).also { o -> + o.heartRate.setValue(heartRate.value) + o.comparator.setValue(comparator.value) + } + } + + override fun generateDialog(root: LinearLayout) { + LayoutBuilder() + .add(StaticLabel(rh, R.string.triggerHeartRate, this)) + .add(comparator) + .add(LabelWithElement(rh, rh.gs(R.string.triggerHeartRate) + ": ", "", heartRate)) + .build(root) + } +} diff --git a/plugins/automation/src/main/res/values/strings.xml b/plugins/automation/src/main/res/values/strings.xml index aff3deb360..a4df0e3e1a 100644 --- a/plugins/automation/src/main/res/values/strings.xml +++ b/plugins/automation/src/main/res/values/strings.xml @@ -94,6 +94,8 @@ Last bolus time %1$s %2$s min ago COB COB %1$s %2$.0f + Heart Rate + HR %1$s %2$.0f IOB [U]: Dist [m]: Recurring time diff --git a/plugins/automation/src/test/java/info/nightscout/automation/triggers/TriggerHeartRateTest.kt b/plugins/automation/src/test/java/info/nightscout/automation/triggers/TriggerHeartRateTest.kt new file mode 100644 index 0000000000..84c4e2b9fb --- /dev/null +++ b/plugins/automation/src/test/java/info/nightscout/automation/triggers/TriggerHeartRateTest.kt @@ -0,0 +1,126 @@ +package info.nightscout.automation.triggers + +import info.nightscout.automation.R +import info.nightscout.automation.elements.Comparator +import info.nightscout.database.entities.HeartRate +import org.json.JSONObject +import org.junit.Assert.assertEquals +import org.junit.Assert.assertFalse +import org.junit.Assert.assertNotSame +import org.junit.Assert.assertTrue +import org.junit.jupiter.api.BeforeEach +import org.junit.jupiter.api.Test +import org.mockito.Mockito.verify +import org.mockito.Mockito.verifyNoMoreInteractions +import org.mockito.Mockito.`when` + +class TriggerHeartRateTest : TriggerTestBase() { + + private var now = 1000L + + @BeforeEach + fun mock() { + `when`(dateUtil.now()).thenReturn(now) + } + + @Test + fun friendlyName() { + assertEquals(R.string.triggerHeartRate, TriggerHeartRate(injector).friendlyName()) + } + + @Test + fun friendlyDescription() { + val t = TriggerHeartRate(injector) + `when`(rh.gs(Comparator.Compare.IS_EQUAL_OR_GREATER.stringRes)).thenReturn(">") + `when`(rh.gs(R.string.triggerHeartRateDesc, ">", 80.0)).thenReturn("test") + assertEquals("test", t.friendlyDescription()) + } + + @Test + fun duplicate() { + val t = TriggerHeartRate(injector).apply { + heartRate.value = 100.0 + comparator.value = Comparator.Compare.IS_GREATER + } + val dup = t.duplicate() as TriggerHeartRate + assertNotSame(t, dup) + assertEquals(100.0, dup.heartRate.value, 0.01) + assertEquals(Comparator.Compare.IS_GREATER, dup.comparator.value) + + } + + @Test + fun shouldRunNotAvailable() { + val t = TriggerHeartRate(injector).apply { comparator.value = Comparator.Compare.IS_NOT_AVAILABLE } + assertTrue(t.shouldRun()) + verifyNoMoreInteractions(repository) + } + + @Test + fun shouldRunNoHeartRate() { + val t = TriggerHeartRate(injector).apply { + heartRate.value = 100.0 + comparator.value = Comparator.Compare.IS_GREATER + } + `when`(repository.getHeartRatesFromTime(now - t.averageHeartRateDurationMillis)).thenReturn(emptyList()) + assertFalse(t.shouldRun()) + verify(repository).getHeartRatesFromTime(now - t.averageHeartRateDurationMillis) + verifyNoMoreInteractions(repository) + } + + @Test + fun shouldRunBelowThreshold() { + val t = TriggerHeartRate(injector).apply { + heartRate.value = 100.0 + comparator.value = Comparator.Compare.IS_GREATER + } + val hrs = listOf( + HeartRate(duration = 300_000, timestamp = now - 300_000, beatsPerMinute = 80.0, device = "test"), + HeartRate(duration = 300_000, timestamp = now, beatsPerMinute = 60.0, device = "test"), + ) + `when`(repository.getHeartRatesFromTime(now - t.averageHeartRateDurationMillis)).thenReturn(hrs) + assertFalse(t.shouldRun()) + verify(repository).getHeartRatesFromTime(now - t.averageHeartRateDurationMillis) + verifyNoMoreInteractions(repository) + } + + @Test + fun shouldRunTrigger() { + val t = TriggerHeartRate(injector).apply { + heartRate.value = 100.0 + comparator.value = Comparator.Compare.IS_GREATER + } + val hrs = listOf( + HeartRate(duration = 300_000, timestamp = now, beatsPerMinute = 120.0, device = "test"), + ) + `when`(repository.getHeartRatesFromTime(now - t.averageHeartRateDurationMillis)).thenReturn(hrs) + assertTrue(t.shouldRun()) + verify(repository).getHeartRatesFromTime(now - t.averageHeartRateDurationMillis) + verifyNoMoreInteractions(repository) + } + + @Test + fun toJSON() { + val t = TriggerHeartRate(injector).apply { + heartRate.value = 100.0 + comparator.value = Comparator.Compare.IS_GREATER + } + assertEquals(Comparator.Compare.IS_GREATER, t.comparator.value) + + assertEquals( + """{"data":{"comparator":"IS_GREATER","heartRate":100},"type":"TriggerHeartRate"}""".trimMargin(), + t.toJSON() + ) + } + + @Test + fun fromJSON() { + val t = TriggerDummy(injector).instantiate( + JSONObject( + """{"data":{"comparator":"IS_GREATER","heartRate":100},"type":"TriggerHeartRate"}""" + ) + ) as TriggerHeartRate + assertEquals(Comparator.Compare.IS_GREATER, t.comparator.value) + assertEquals(100.0, t.heartRate.value, 0.01) + } +} \ No newline at end of file diff --git a/plugins/main/src/main/res/values-ru-rRU/strings.xml b/plugins/main/src/main/res/values-ru-rRU/strings.xml index d939f16953..f0c6de0fb5 100644 --- a/plugins/main/src/main/res/values-ru-rRU/strings.xml +++ b/plugins/main/src/main/res/values-ru-rRU/strings.xml @@ -253,6 +253,7 @@ Прогнозирование Терапия + Частота сердечных сокращений Линия отклонения Активность Влияние ГК @@ -270,6 +271,7 @@ НАДО ЛИНОТКЛН НАЗНАЧ + ЧСС ЧУВСТВ Масштаб графика График @@ -323,6 +325,7 @@ г ч Активный профиль не установлен! + Профиль:\n\nСдвиг по времени: %1$d$\nПроцент: %2$d%%\" %1$.2fед%1$.0f%% Профиль не загружен Применять только в режиме APS! diff --git a/plugins/sync/src/main/java/info/nightscout/plugins/sync/openhumans/OpenHumansUploaderPlugin.kt b/plugins/sync/src/main/java/info/nightscout/plugins/sync/openhumans/OpenHumansUploaderPlugin.kt index be227e5b92..411b971bad 100644 --- a/plugins/sync/src/main/java/info/nightscout/plugins/sync/openhumans/OpenHumansUploaderPlugin.kt +++ b/plugins/sync/src/main/java/info/nightscout/plugins/sync/openhumans/OpenHumansUploaderPlugin.kt @@ -563,7 +563,7 @@ class OpenHumansUploaderPlugin @Inject internal constructor( .setBackoffCriteria(BackoffPolicy.LINEAR, 20, TimeUnit.MINUTES) .setInitialDelay(if (delay) 1 else 0, TimeUnit.DAYS) .build() - WorkManager.getInstance(context).enqueueUniquePeriodicWork(WORK_NAME_PERIODIC, if (replace) ExistingPeriodicWorkPolicy.REPLACE else ExistingPeriodicWorkPolicy.KEEP, workRequest) + WorkManager.getInstance(context).enqueueUniquePeriodicWork(WORK_NAME_PERIODIC, if (replace) ExistingPeriodicWorkPolicy.UPDATE else ExistingPeriodicWorkPolicy.KEEP, workRequest) } internal fun uploadNow() { diff --git a/pump/combo/build.gradle b/pump/combo/build.gradle index bec7f9b0d8..ba1ec7d6b8 100644 --- a/pump/combo/build.gradle +++ b/pump/combo/build.gradle @@ -23,6 +23,6 @@ dependencies { implementation project(':app-wear-shared:shared') // RuffyScripter - api 'com.google.guava:guava:32.0.1-jre' + api "com.google.guava:guava:$guava_version" } \ No newline at end of file diff --git a/pump/combov2/src/main/res/values/strings.xml b/pump/combov2/src/main/res/values/strings.xml index 1d7557ae9e..947df4df66 100644 --- a/pump/combov2/src/main/res/values/strings.xml +++ b/pump/combov2/src/main/res/values/strings.xml @@ -110,7 +110,7 @@ buttons at the same time to cancel pairing)\n Set emulated 100% TBR Letting ongoing emulated 100% TBR finish Ignoring redundant 100% TBR request - Unexpected limit encountered while adjusting TBR: target percentage was %1$d%%, hit a limit at %1$d%% + Unexpected limit encountered while adjusting TBR: target percentage was %1$d%%, hit a limit at %2$d%% Cannot set absolute TBR if base basal rate is zero Pair AndroidAPS and Android with a currently unpaired Accu-Chek Combo pump Unpair AndroidAPS and Android from the currently paired Accu-Chek Combo pump diff --git a/pump/diaconn/src/main/java/info/nightscout/pump/diaconn/DiaconnG8Pump.kt b/pump/diaconn/src/main/java/info/nightscout/pump/diaconn/DiaconnG8Pump.kt index 9ee19f4c8c..4eceb897f2 100644 --- a/pump/diaconn/src/main/java/info/nightscout/pump/diaconn/DiaconnG8Pump.kt +++ b/pump/diaconn/src/main/java/info/nightscout/pump/diaconn/DiaconnG8Pump.kt @@ -21,13 +21,14 @@ class DiaconnG8Pump @Inject constructor( ) { var isPumpLogUploadFailed: Boolean = false - //var bleResultInfo: Pair = Pair(null, false) var bolusConfirmMessage: Byte = 0 + var isReadyToBolus: Boolean = false var maxBolusePerDay: Double = 0.0 var pumpIncarnationNum: Int = 65536 var isPumpVersionGe2_63: Boolean = false // is pumpVersion higher then 2.63 + var isPumpVersionGe3_53: Boolean = false // is pumpVersion higher then 3.42 var insulinWarningGrade: Int =0 var insulinWarningProcess: Int =0 var insulinWarningRemain: Int =0 @@ -363,6 +364,11 @@ class DiaconnG8Pump @Inject constructor( var otpNumber = 0 + var bolusingSetAmount = 0.0 + var bolusingInjAmount = 0.0 + var bolusingSpeed = 0 + var bolusingInjProgress = 0 + companion object { // User settings const val ALARM = 0 diff --git a/pump/diaconn/src/main/java/info/nightscout/pump/diaconn/di/DiaconnG8PacketModule.kt b/pump/diaconn/src/main/java/info/nightscout/pump/diaconn/di/DiaconnG8PacketModule.kt index 0c80964704..0aa758cf58 100644 --- a/pump/diaconn/src/main/java/info/nightscout/pump/diaconn/di/DiaconnG8PacketModule.kt +++ b/pump/diaconn/src/main/java/info/nightscout/pump/diaconn/di/DiaconnG8PacketModule.kt @@ -43,6 +43,7 @@ import info.nightscout.pump.diaconn.packet.InjectionCancelSettingResponsePacket import info.nightscout.pump.diaconn.packet.InjectionExtendedBolusResultReportPacket import info.nightscout.pump.diaconn.packet.InjectionExtendedBolusSettingPacket import info.nightscout.pump.diaconn.packet.InjectionExtendedBolusSettingResponsePacket +import info.nightscout.pump.diaconn.packet.InjectionProgressReportPacket import info.nightscout.pump.diaconn.packet.InjectionSnackInquirePacket import info.nightscout.pump.diaconn.packet.InjectionSnackInquireResponsePacket import info.nightscout.pump.diaconn.packet.InjectionSnackResultReportPacket @@ -150,6 +151,7 @@ abstract class DiaconnG8PacketModule { @ContributesAndroidInjector abstract fun contributesBigAPSMainInfoInquireResponsePacket(): BigAPSMainInfoInquireResponsePacket @ContributesAndroidInjector abstract fun contributesSerialNumInquirePacket(): SerialNumInquirePacket @ContributesAndroidInjector abstract fun contributesSerialNumInquireResponsePacket(): SerialNumInquireResponsePacket + @ContributesAndroidInjector abstract fun contributesInjectionProgressReportPacket(): InjectionProgressReportPacket } diff --git a/pump/diaconn/src/main/java/info/nightscout/pump/diaconn/packet/BigAPSMainInfoInquireResponsePacket.kt b/pump/diaconn/src/main/java/info/nightscout/pump/diaconn/packet/BigAPSMainInfoInquireResponsePacket.kt index 975e8edade..7e63db4267 100644 --- a/pump/diaconn/src/main/java/info/nightscout/pump/diaconn/packet/BigAPSMainInfoInquireResponsePacket.kt +++ b/pump/diaconn/src/main/java/info/nightscout/pump/diaconn/packet/BigAPSMainInfoInquireResponsePacket.kt @@ -215,6 +215,7 @@ class BigAPSMainInfoInquireResponsePacket( //incarnation no 처리 diaconnG8Pump.isPumpVersionGe2_63 = PumpLogUtil.isPumpVersionGe(sp.getString(rh.gs(R.string.pumpversion), ""), 2, 63) + diaconnG8Pump.isPumpVersionGe3_53 = PumpLogUtil.isPumpVersionGe(sp.getString(rh.gs(R.string.pumpversion), ""), 3, 53) aapsLogger.debug(LTag.PUMPCOMM, "result > " + diaconnG8Pump.result) aapsLogger.debug(LTag.PUMPCOMM, "systemRemainInsulin > " + diaconnG8Pump.systemRemainInsulin) diff --git a/pump/diaconn/src/main/java/info/nightscout/pump/diaconn/packet/BigMainInfoInquireResponsePacket.kt b/pump/diaconn/src/main/java/info/nightscout/pump/diaconn/packet/BigMainInfoInquireResponsePacket.kt index ce67dc789d..1354b1915b 100644 --- a/pump/diaconn/src/main/java/info/nightscout/pump/diaconn/packet/BigMainInfoInquireResponsePacket.kt +++ b/pump/diaconn/src/main/java/info/nightscout/pump/diaconn/packet/BigMainInfoInquireResponsePacket.kt @@ -214,6 +214,7 @@ class BigMainInfoInquireResponsePacket( //incarnation no 처리 diaconnG8Pump.isPumpVersionGe2_63 = PumpLogUtil.isPumpVersionGe(sp.getString(rh.gs(R.string.pumpversion), ""), 2, 63) + diaconnG8Pump.isPumpVersionGe3_53 = PumpLogUtil.isPumpVersionGe(sp.getString(rh.gs(R.string.pumpversion), ""), 3, 53) aapsLogger.debug(LTag.PUMPCOMM, "result > " + diaconnG8Pump.result) aapsLogger.debug(LTag.PUMPCOMM, "systemRemainInsulin > " + diaconnG8Pump.systemRemainInsulin) diff --git a/pump/diaconn/src/main/java/info/nightscout/pump/diaconn/packet/DiaconnG8ResponseMessageHashTable.kt b/pump/diaconn/src/main/java/info/nightscout/pump/diaconn/packet/DiaconnG8ResponseMessageHashTable.kt index f72fbeb8d2..35ce96fc24 100644 --- a/pump/diaconn/src/main/java/info/nightscout/pump/diaconn/packet/DiaconnG8ResponseMessageHashTable.kt +++ b/pump/diaconn/src/main/java/info/nightscout/pump/diaconn/packet/DiaconnG8ResponseMessageHashTable.kt @@ -48,5 +48,6 @@ class DiaconnG8ResponseMessageHashTable @Inject constructor(val injector: HasAnd put(BatteryWarningReportPacket(injector)) put(InjectionBlockReportPacket(injector)) put(BolusSpeedSettingReportPacket(injector)) + put(InjectionProgressReportPacket(injector)) } } diff --git a/pump/diaconn/src/main/java/info/nightscout/pump/diaconn/packet/InjectionProgressReportPacket.kt b/pump/diaconn/src/main/java/info/nightscout/pump/diaconn/packet/InjectionProgressReportPacket.kt new file mode 100644 index 0000000000..9e0de742e4 --- /dev/null +++ b/pump/diaconn/src/main/java/info/nightscout/pump/diaconn/packet/InjectionProgressReportPacket.kt @@ -0,0 +1,53 @@ +package info.nightscout.pump.diaconn.packet + +import dagger.android.HasAndroidInjector +import info.nightscout.pump.diaconn.DiaconnG8Pump +import info.nightscout.rx.bus.RxBus +import info.nightscout.rx.logging.LTag +import info.nightscout.shared.interfaces.ResourceHelper +import javax.inject.Inject + +/** + * InjectionProgressReportPacket + */ +class InjectionProgressReportPacket(injector: HasAndroidInjector) : DiaconnG8Packet(injector ) { + + @Inject lateinit var diaconnG8Pump: DiaconnG8Pump + @Inject lateinit var rxBus: RxBus + @Inject lateinit var rh: ResourceHelper + + init { + msgType = 0xEA.toByte() + aapsLogger.debug(LTag.PUMPCOMM, "InjectionProgressReportPacket init ") + } + + override fun handleMessage(data: ByteArray?) { + val defectCheck = defect(data) + if (defectCheck != 0) { + aapsLogger.debug(LTag.PUMPCOMM, "InjectionProgressReportPacket Got some Error") + failed = true + return + } else failed = false + + val bufferData = prefixDecode(data) + val setAmount = getShortToInt(bufferData) /100.0 + val injAmount = getShortToInt(bufferData)/100.0 + val speed = getByteToInt(bufferData); + val injProgress = getByteToInt(bufferData) + + diaconnG8Pump.bolusingSetAmount = setAmount + diaconnG8Pump.bolusingInjAmount = injAmount + diaconnG8Pump.bolusingSpeed = speed + diaconnG8Pump.bolusingInjProgress = injProgress + + aapsLogger.debug(LTag.PUMPCOMM, "bolusingSetAmount --> ${diaconnG8Pump.bolusingSetAmount}") + aapsLogger.debug(LTag.PUMPCOMM, "bolusingInjAmount --> ${diaconnG8Pump.bolusingInjAmount}") + aapsLogger.debug(LTag.PUMPCOMM, "bolusingSpeed --> ${diaconnG8Pump.bolusingSpeed}") + aapsLogger.debug(LTag.PUMPCOMM, "bolusingInjProgress --> ${diaconnG8Pump.bolusingInjProgress}") + } + + override fun getFriendlyName(): String { + return "PUMP_INJECTION_PROGRESS_REPORT" + + } +} \ No newline at end of file diff --git a/pump/diaconn/src/main/java/info/nightscout/pump/diaconn/service/DiaconnG8Service.kt b/pump/diaconn/src/main/java/info/nightscout/pump/diaconn/service/DiaconnG8Service.kt index 907b4c90c4..88859f33d6 100644 --- a/pump/diaconn/src/main/java/info/nightscout/pump/diaconn/service/DiaconnG8Service.kt +++ b/pump/diaconn/src/main/java/info/nightscout/pump/diaconn/service/DiaconnG8Service.kt @@ -322,6 +322,7 @@ class DiaconnG8Service : DaggerService() { for (i in 0 until loopSize) { val startLogNo: Int = start + i * pumpLogPageSize val endLogNo: Int = startLogNo + min(end - startLogNo, pumpLogPageSize) + aapsLogger.debug(LTag.PUMPCOMM, "pumplog request : $startLogNo ~ $endLogNo") val msg = BigLogInquirePacket(injector, startLogNo, endLogNo, 100) sendMessage(msg, 500) } @@ -500,15 +501,27 @@ class DiaconnG8Service : DaggerService() { val bolusDurationInMSec = (insulin * speed * 1000).toLong() val expectedEnd = bolusStart + bolusDurationInMSec + 3500L val totalwaitTime = (expectedEnd - System.currentTimeMillis()) / 1000 + // reset bolus progress history + diaconnG8Pump.bolusingInjProgress = 0 + diaconnG8Pump.bolusingSetAmount = 0.0 + diaconnG8Pump.bolusingInjAmount = 0.0 + if (diaconnG8Pump.isReadyToBolus) { + var progressPecent = 0 while (!diaconnG8Pump.bolusDone) { - val waitTime = (expectedEnd - System.currentTimeMillis()) / 1000 - bolusingEvent.status = String.format(rh.gs(R.string.waitingforestimatedbolusend), if (waitTime < 0) 0 else waitTime) - var progressPecent = 0 - if (totalwaitTime > waitTime && totalwaitTime > 0) { - progressPecent = ((totalwaitTime - waitTime) * 100 / totalwaitTime).toInt() + if(diaconnG8Pump.isPumpVersionGe3_53) { + progressPecent = diaconnG8Pump.bolusingInjProgress + //bolusingEvent.status = String.format(rh.gs(R.string.waitingforestimatedbolusend), progressPecent) + bolusingEvent.status = "볼러스 주입중 ${diaconnG8Pump.bolusingInjAmount}U / ${diaconnG8Pump.bolusingSetAmount}U (${progressPecent}%)" + bolusingEvent.percent = min(progressPecent, 100) + } else { + val waitTime = (expectedEnd - System.currentTimeMillis()) / 1000 + bolusingEvent.status = String.format(rh.gs(R.string.waitingforestimatedbolusend), if (waitTime < 0) 0 else waitTime) + if (totalwaitTime > waitTime && totalwaitTime > 0) { + progressPecent = ((totalwaitTime - waitTime) * 100 / totalwaitTime).toInt() + } + bolusingEvent.percent = min(progressPecent, 100) } - bolusingEvent.percent = min(progressPecent, 100) rxBus.send(bolusingEvent) SystemClock.sleep(200) } @@ -522,7 +535,9 @@ class DiaconnG8Service : DaggerService() { rxBus.send(EventPumpStatusChanged(rh.gs(R.string.gettingbolusstatus))) sendMessage(InjectionSnackInquirePacket(injector), 2000) // last bolus // 볼러스 결과 보고패킷에서 처리함. - bolusingEvent.percent = 100 + if(!diaconnG8Pump.isPumpVersionGe3_53) { + bolusingEvent.percent = 100 + } rxBus.send(EventPumpStatusChanged(rh.gs(info.nightscout.shared.R.string.disconnecting))) } }) @@ -549,29 +564,39 @@ class DiaconnG8Service : DaggerService() { // temp state check sendMessage(TempBasalInquirePacket(injector)) + val result : DiaconnG8Packet + if(diaconnG8Pump.isPumpVersionGe3_53) { + val tbrPacket = TempBasalSettingPacket(injector, 3, ((durationInHours * 60) / 15).toInt(), ((absoluteRate * 100) + 1000).toInt()) + sendMessage(tbrPacket, 100) + result = tbrPacket + if (!processConfirm(tbrPacket.msgType)) return false + } else { - if (diaconnG8Pump.tbStatus == 1) { - rxBus.send(EventPumpStatusChanged(rh.gs(R.string.stoppingtempbasal))) - val msgPacket = TempBasalSettingPacket(injector, 2, diaconnG8Pump.tbTime, diaconnG8Pump.tbInjectRateRatio) - // tempbasal stop - sendMessage(msgPacket, 100) + if (diaconnG8Pump.tbStatus == 1) { + rxBus.send(EventPumpStatusChanged(rh.gs(R.string.stoppingtempbasal))) + val tbrPacket = TempBasalSettingPacket(injector, 2, diaconnG8Pump.tbTime, diaconnG8Pump.tbInjectRateRatio) + // tempbasal stop + sendMessage(tbrPacket, 100) + // otp process + if (!processConfirm(tbrPacket.msgType)) return false + diaconnG8Pump.tempBasalStart = dateUtil.now() + } + rxBus.send(EventPumpStatusChanged(rh.gs(R.string.settingtempbasal))) + val tbInjectRate = ((absoluteRate * 100) + 1000).toInt() + val tbrPacket = TempBasalSettingPacket(injector, 1, ((durationInHours * 60) / 15).toInt(), tbInjectRate) + sendMessage(tbrPacket, 100) + result = tbrPacket // otp process - if (!processConfirm(msgPacket.msgType)) return false - diaconnG8Pump.tempBasalStart = dateUtil.now() + if (!processConfirm(tbrPacket.msgType)) return false + // pump tempbasal status inquire } - rxBus.send(EventPumpStatusChanged(rh.gs(R.string.settingtempbasal))) - val tbInjectRate = ((absoluteRate * 100) + 1000).toInt() - val msgTBR = TempBasalSettingPacket(injector, 1, ((durationInHours * 60) / 15).toInt(), tbInjectRate) - sendMessage(msgTBR, 100) - // otp process - if (!processConfirm(msgTBR.msgType)) return false - // pump tempbasal status inquire + sendMessage(TempBasalInquirePacket(injector)) loadHistory() val tbr = pumpSync.expectedPumpState().temporaryBasal diaconnG8Pump.fromTemporaryBasal(tbr) rxBus.send(EventPumpStatusChanged(EventPumpStatusChanged.Status.DISCONNECTING)) - return msgTBR.success() + return result.success() } fun tempBasalShortDuration(absoluteRate: Double, durationInMinutes: Int): Boolean { @@ -581,28 +606,40 @@ class DiaconnG8Service : DaggerService() { } // temp state check + val result:DiaconnG8Packet sendMessage(TempBasalInquirePacket(injector)) - if (diaconnG8Pump.tbStatus == 1) { - rxBus.send(EventPumpStatusChanged(rh.gs(R.string.stoppingtempbasal))) - val msgPacket = TempBasalSettingPacket(injector, 2, diaconnG8Pump.tbTime, diaconnG8Pump.tbInjectRateRatio) - // tempbasal stop - sendMessage(msgPacket, 100) + if(diaconnG8Pump.isPumpVersionGe3_53) { + rxBus.send(EventPumpStatusChanged(rh.gs(R.string.settingtempbasal))) + val tbrSettingPacket = TempBasalSettingPacket(injector, 3, 2, ((absoluteRate * 100) + 1000).toInt()) + sendMessage(tbrSettingPacket, 100) + result=tbrSettingPacket // otp process - if (!processConfirm(msgPacket.msgType)) return false - SystemClock.sleep(500) + if (!processConfirm(tbrSettingPacket.msgType)) return false + sendMessage(TempBasalInquirePacket(injector)) + } else { + if (diaconnG8Pump.tbStatus == 1) { + rxBus.send(EventPumpStatusChanged(rh.gs(R.string.stoppingtempbasal))) + val tbrPacket = TempBasalSettingPacket(injector, 2, diaconnG8Pump.tbTime, diaconnG8Pump.tbInjectRateRatio) + // tempbasal stop + sendMessage(tbrPacket, 100) + // otp process + if (!processConfirm(tbrPacket.msgType)) return false + SystemClock.sleep(500) + } + rxBus.send(EventPumpStatusChanged(rh.gs(R.string.settingtempbasal))) + val tbInjectRate = absoluteRate * 100 + 1000 + val msgTBR = TempBasalSettingPacket(injector, 1, 2, tbInjectRate.toInt()) + sendMessage(msgTBR, 100) + result=msgTBR + // otp process + if (!processConfirm(msgTBR.msgType)) return false } - rxBus.send(EventPumpStatusChanged(rh.gs(R.string.settingtempbasal))) - val tbInjectRate = absoluteRate * 100 + 1000 - val msgTBR = TempBasalSettingPacket(injector, 1, 2, tbInjectRate.toInt()) - sendMessage(msgTBR, 100) - // otp process - if (!processConfirm(msgTBR.msgType)) return false sendMessage(TempBasalInquirePacket(injector)) loadHistory() val tbr = pumpSync.expectedPumpState().temporaryBasal diaconnG8Pump.fromTemporaryBasal(tbr) rxBus.send(EventPumpStatusChanged(EventPumpStatusChanged.Status.DISCONNECTING)) - return msgTBR.success() + return result.success() } fun tempBasalStop(): Boolean { diff --git a/pump/eopatch/build.gradle b/pump/eopatch/build.gradle index ae132348f6..103398f843 100644 --- a/pump/eopatch/build.gradle +++ b/pump/eopatch/build.gradle @@ -29,7 +29,7 @@ dependencies { implementation project(':core:utils') implementation project(':core:ui') - api 'com.google.guava:guava:32.0.1-jre' + api "com.google.guava:guava:$guava_version" //RxAndroidBle implementation "com.polidea.rxandroidble3:rxandroidble:1.17.2" diff --git a/pump/eopatch/src/main/java/info/nightscout/androidaps/plugins/pump/eopatch/alarm/AlarmManager.kt b/pump/eopatch/src/main/java/info/nightscout/androidaps/plugins/pump/eopatch/alarm/AlarmManager.kt index f06a256a75..8fddeb9418 100644 --- a/pump/eopatch/src/main/java/info/nightscout/androidaps/plugins/pump/eopatch/alarm/AlarmManager.kt +++ b/pump/eopatch/src/main/java/info/nightscout/androidaps/plugins/pump/eopatch/alarm/AlarmManager.kt @@ -22,7 +22,6 @@ import info.nightscout.interfaces.notifications.Notification import info.nightscout.interfaces.plugin.ActivePlugin import info.nightscout.interfaces.pump.PumpSync import info.nightscout.interfaces.pump.defs.PumpType -import info.nightscout.interfaces.queue.CommandQueue import info.nightscout.interfaces.ui.UiInteraction import info.nightscout.rx.AapsSchedulers import info.nightscout.rx.bus.RxBus @@ -51,7 +50,6 @@ interface IAlarmManager { class AlarmManager @Inject constructor() : IAlarmManager { @Inject lateinit var patchManager: IPatchManager @Inject lateinit var activePlugin: ActivePlugin - @Inject lateinit var commandQueue: CommandQueue @Inject lateinit var aapsLogger: AAPSLogger @Inject lateinit var resourceHelper: ResourceHelper @Inject lateinit var rxBus: RxBus @@ -71,6 +69,7 @@ class AlarmManager @Inject constructor() : IAlarmManager { private var compositeDisposable: CompositeDisposable = CompositeDisposable() private var alarmDisposable: Disposable? = null + @Suppress("unused") @Inject fun onInit() { mAlarmProcess = AlarmProcess(patchManager, rxBus) @@ -150,7 +149,7 @@ class AlarmManager @Inject constructor() : IAlarmManager { context.startActivity(i) } - private fun showNotification(alarmCode: AlarmCode, timeOffset: Long = 0L) { + private fun showNotification(alarmCode: AlarmCode) { var alarmMsg = resourceHelper.gs(alarmCode.resId) if (alarmCode == B000) { val expireTimeValue = pm.getPatchWakeupTimestamp() + TimeUnit.HOURS.toMillis(84) @@ -171,21 +170,25 @@ class AlarmManager @Inject constructor() : IAlarmManager { else Single.just(IAlarmProcess.ALARM_HANDLED) } .subscribe { ret -> - if (ret == IAlarmProcess.ALARM_HANDLED) { - if (alarmCode == B001) { - pumpSync.syncStopTemporaryBasalWithPumpId( - timestamp = dateUtil.now(), - endPumpId = dateUtil.now(), - pumpType = PumpType.EOFLOW_EOPATCH2, - pumpSerial = patchManager.patchConfig.patchSerialNumber - ) + when (ret) { + IAlarmProcess.ALARM_HANDLED -> { + if (alarmCode == B001) { + pumpSync.syncStopTemporaryBasalWithPumpId( + timestamp = dateUtil.now(), + endPumpId = dateUtil.now(), + pumpType = PumpType.EOFLOW_EOPATCH2, + pumpSerial = patchManager.patchConfig.patchSerialNumber + ) + } + updateState(alarmCode, AlarmState.HANDLE) } - updateState(alarmCode, AlarmState.HANDLE) - }else if(ret == IAlarmProcess.ALARM_HANDLED_BUT_NEED_STOP_BEEP){ - pm.getAlarms().needToStopBeep.add(alarmCode) - updateState(alarmCode, AlarmState.HANDLE) - } else { - showNotification(alarmCode) + + IAlarmProcess.ALARM_HANDLED_BUT_NEED_STOP_BEEP -> { + pm.getAlarms().needToStopBeep.add(alarmCode) + updateState(alarmCode, AlarmState.HANDLE) + } + + else -> showNotification(alarmCode) } } ) diff --git a/pump/eopatch/src/main/java/info/nightscout/androidaps/plugins/pump/eopatch/alarm/AlarmProcess.kt b/pump/eopatch/src/main/java/info/nightscout/androidaps/plugins/pump/eopatch/alarm/AlarmProcess.kt index bf596bf026..04b7e1e234 100644 --- a/pump/eopatch/src/main/java/info/nightscout/androidaps/plugins/pump/eopatch/alarm/AlarmProcess.kt +++ b/pump/eopatch/src/main/java/info/nightscout/androidaps/plugins/pump/eopatch/alarm/AlarmProcess.kt @@ -63,16 +63,16 @@ interface IAlarmProcess { class AlarmProcess(val patchManager: IPatchManager, val rxBus: RxBus) : IAlarmProcess { override fun doAction(context: Context, code: AlarmCode): Single { return when (code) { - B001 -> resumeBasalAction(context) + B001 -> resumeBasalAction(context) A002, A003, A004, A005, A018, A019, A020, A022, A023, A034, A041, A042, A043, A044, A106, A107, A108, A116, - A117, A118 -> patchDeactivationAction(context) - A007 -> inappropriateTemperatureAction(context) - A016 -> needleInsertionErrorAction(context) - B000 -> Single.just(IAlarmProcess.ALARM_HANDLED) - B003, B005, B006, B018 -> stopAeBeepAction(context, code) - B012 -> Single.just(IAlarmProcess.ALARM_HANDLED) + A117, A118 -> patchDeactivationAction(context) + A007 -> inappropriateTemperatureAction(context) + A016 -> needleInsertionErrorAction(context) + B000 -> Single.just(IAlarmProcess.ALARM_HANDLED) + B003, B005, B006, B018 -> stopAeBeepAction(code) + B012 -> Single.just(IAlarmProcess.ALARM_HANDLED) } } @@ -146,20 +146,20 @@ class AlarmProcess(val patchManager: IPatchManager, val rxBus: RxBus) : IAlarmPr patchManager.temperature .map(TemperatureResponse::getTemperature) .map { temp -> (temp >= EopatchActivity.NORMAL_TEMPERATURE_MIN && temp <= EopatchActivity.NORMAL_TEMPERATURE_MAX) } - .filter{ok -> ok} + .filter { ok -> ok } .flatMap { patchManager.resumeBasal().map { it.isSuccess.takeOne(IAlarmProcess.ALARM_HANDLED, IAlarmProcess.ALARM_UNHANDLED) }.toMaybe() } .defaultIfEmpty(IAlarmProcess.ALARM_UNHANDLED) } } - private fun stopAeBeepAction(context: Context, alarm: AlarmCode): Single { - if (patchManager.patchConnectionState.isConnected) { - return patchManager.stopAeBeep(alarm.aeCode) + private fun stopAeBeepAction(alarm: AlarmCode): Single { + return if (patchManager.patchConnectionState.isConnected) { + patchManager.stopAeBeep(alarm.aeCode) .map { obj: PatchBooleanResponse -> obj.isSuccess } .onErrorReturn { false } .flatMap { Single.just(it.takeOne(IAlarmProcess.ALARM_HANDLED, IAlarmProcess.ALARM_HANDLED_BUT_NEED_STOP_BEEP)) } - }else{ - return Single.just(IAlarmProcess.ALARM_HANDLED_BUT_NEED_STOP_BEEP) + } else { + Single.just(IAlarmProcess.ALARM_HANDLED_BUT_NEED_STOP_BEEP) } } } \ No newline at end of file diff --git a/pump/eopatch/src/main/res/values-es-rES/strings_alarm.xml b/pump/eopatch/src/main/res/values-es-rES/strings_alarm.xml index d8f265e4d1..86830f54d4 100644 --- a/pump/eopatch/src/main/res/values-es-rES/strings_alarm.xml +++ b/pump/eopatch/src/main/res/values-es-rES/strings_alarm.xml @@ -22,7 +22,7 @@ Error del parche\nEl parche ha sido desactivado y se ha detenido la entrega de insulina. Cambia el parche ahora. Error del parche\nEl parche ha sido desactivado y se ha detenido la entrega de insulina. Cambia el parche ahora. Error del parche\nEl parche ha sido desactivado y se ha detenido la entrega de insulina. Cambia el parche ahora. - La vida útil del parche expira %s. Prepárate para cambiar el parche. + La vida útil del parche expira el %s. Prepárate para cambiar el parche. Fin de la suspensión de insulina\nPulsa en \'Reanudar\' para reanudar la entrega de insulina. Reservorio bajo\nReemplaza el parche pronto. La vida útil del parche ha expirado\nCambia el parche ahora. diff --git a/pump/eopatch/src/main/res/values-no-rNO/strings_alarm.xml b/pump/eopatch/src/main/res/values-no-rNO/strings_alarm.xml index 61862d1424..a68bfa0a63 100644 --- a/pump/eopatch/src/main/res/values-no-rNO/strings_alarm.xml +++ b/pump/eopatch/src/main/res/values-no-rNO/strings_alarm.xml @@ -1,2 +1,32 @@ - + + Tomt reservoar\nPatch er deaktivert og tilførselen av insulin stoppet. Skift patch nå. + Patch utløpt\nPatch er deaktivert og tilførselen av insulin stoppet. Skift patch nå. + Blokkering oppdaget\nPatch er deaktivert og tilførselen av insulin stoppet. Skift patch nå. + Feil i oppstart selvtest\nPatch har blitt deaktivert. Bytt patch nå. + Upassende temperatur\nInsulintilførsel eller \'Aktiver patch\' prosess har stoppet. Unngå ekstrem temperatur nå. + Feil ved innsetting av kanyle\nSjekk knott-posisjon og trykk på \"Prøv på nytt\". + Patch batteri feil\nPatch er deaktivert og tilførselen\nav insulin stoppet. Skift patch nå. + Patch batteri feil\nPatch er deaktivert og tilførselen av insulin stoppet. Skift patch nå. + Patch aktiveringsfeil\n\'Aktiver patch prosess har utløpt. Trykk på \'Bekreft\' for å deaktivere gjeldende patch. Skift patch. + Patch feil\nPatch er deaktivert og tilførselen av insulin stoppet. Skift patch nå. + Patch feil\nPatch er deaktivert og tilførselen\nav insulin stoppet. Skift patch nå. + Patch feil\nPatch er deaktivert og tilførselen av insulin stoppet. Skift patch nå. + Patch feil\nPatch er deaktivert og tilførselen av insulin stoppet. Skift patch nå. + Patch feil\nPatch er deaktivert og tilførselen av insulin stoppet. Skift patch nå. + Patch feil\nPatch er deaktivert og tilførselen av insulin stoppet. Skift patch nå. + Patch feil\nPatch er deaktivert og tilførselen av insulin stoppet. Skift patch nå. + Patch feil\nPatch er deaktivert og tilførselen av insulin stoppet. Skift patch nå. + Patch feil\nPatch er deaktivert og tilførselen av insulin stoppet. Skift patch nå. + Patch feil\nPatch er deaktivert og tilførselen av insulin stoppet. Skift patch nå. + Patch feil\nPatch er deaktivert og tilførselen av insulin stoppet. Skift patch nå. + Patch feil\nPatch er deaktivert og tilførselen av insulin stoppet. Skift patch nå. + Patch feil\nPatch er deaktivert og tilførselen av insulin stoppet. Skift patch nå. + Patch levetid utløper %s. Gjør deg klar til å bytte pach. + Slutten på insulin suspendering\nTrykk \'gjenopptatt\' for å starte insulintilførselen på nytt. + Lavt reservoarnivå\nBytt patch snart. + Patch levetid er utløpt\nBytt patch nå. + Patch levetid utløper snart\nBytt patch nå. + Ufullstendig aktivering av Patch\nFullfør \'Aktiver patch\' prosessen. + Patch lavt batterinivå\nVær klar til å bytte patch. + diff --git a/pump/eopatch/src/main/res/values-ru-rRU/strings.xml b/pump/eopatch/src/main/res/values-ru-rRU/strings.xml index e0e569483d..0ca3f7db4b 100644 --- a/pump/eopatch/src/main/res/values-ru-rRU/strings.xml +++ b/pump/eopatch/src/main/res/values-ru-rRU/strings.xml @@ -27,9 +27,9 @@ 1 час 30 мин 2 часа \u0020 - Для перехода на новый Patch, Завершите пользование Patch\'ем. Подача инсулина этим Patch\'ем будет отменена. + Для перехода на новый Patch, авершите пользование Патч-помпой. Подача инсулина этой Патч-помпой будет отменена. Пользование Patch\'ем завершено. - Patch был отключен.\nЗавершить пользование Patch\'ем\nУдалите Patch с тела. + Patch деактивирован.\nЗавершите пользование Patch\'ем\nУдалите Patch с тела. Подается болюс. Отменить подачу инсулина и завершить пользование Patch\'ем? Подается временный базал. Отменить подачу инсулина и завершить пользование Patch\'ем? Подается болюс и временный базал. Отменить подачу инсулина и завершить пользование Patch\'ем? diff --git a/pump/eopatch/src/main/res/values-ru-rRU/strings_alarm.xml b/pump/eopatch/src/main/res/values-ru-rRU/strings_alarm.xml index 61862d1424..37aa070131 100644 --- a/pump/eopatch/src/main/res/values-ru-rRU/strings_alarm.xml +++ b/pump/eopatch/src/main/res/values-ru-rRU/strings_alarm.xml @@ -1,2 +1,32 @@ - + + Резервуар пуст\n POD деактивирован, подача инсулина прекращена. Замените POD. + Истек срок POD\n POD деактивирован, подача инсулина прекращена. Замените POD. + Закупорка\n POD деактивирован, подача инсулина прекращена. Замените POD. + Ошибка самотестирования при включении\n POD деактивирован. Замените POD. + Неверная температура\nПодача инсулина или процесс активации POD остановлен. Приведите темрературу к норме. + Ошибка ввода иглы\n Проверьте положение активатора и нажмите \"Повтор\". + Ошибка батареи POD\n POD деактивирован, \nподача инсулина прекращена. Замените POD. + Ошибка батареи POD\n POD деактивирован, подача инсулина прекращена. Замените POD. + Ошибка активации POD\n\'Время активации истекло. Нажмите \'Подтвердить\', чтобы деактивировать POD. Замените POD. + Ошибка батареи Патч-помпы\nПатч-помпа деактивирована, подача инсулина прекращена. Замените Патч-помпу. + Ошибка Патч-помпы\nПатч-помпа деактивирована и\nподача инсулина прекращена. Замените Патч-помпу. + Ошибка Патч-помпы\nПатч-помпа деактивирована, подача инсулина прекращена. Замените Патч-помпу. + Ошибка Патч-помпы\nПатч-помпа деактивирована, подача инсулина прекращена. Замените Патч-помпу. + Ошибка Патч-помпы\nПатч-помпа деактивирована, подача инсулина прекращена. Замените Патч-помпу. + Ошибка Патч-помпы\nПатч-помпа деактивирована, подача инсулина прекращена. Замените Патч-помпу. + Ошибка Патч-помпы\nПатч-помпа деактивирована, подача инсулина прекращена. Замените Патч-помпу. + Ошибка Патч-помпы\nПатч-помпа деактивирована, подача инсулина прекращена. Замените Патч-помпу. + Ошибка Патч-помпы\nПатч-помпа деактивирована, подача инсулина прекращена. Замените Патч-помпу. + Ошибка Патч-помпы\nПатч-помпа деактивирована, подача инсулина прекращена. Замените Патч-помпу. + Ошибка Патч-помпы\nПатч-помпа деактивирована, подача инсулина прекращена. Замените Патч-помпу. + Ошибка Патч-помпы\nПатч-помпа деактивирована, подача инсулина прекращена. Замените Патч-помпу. + Ошибка Патч-помпы\nПатч-помпа деактивирована, подача инсулина прекращена. Замените Патч-помпу. + Срок действия патч-помпы истекает %s. Будьте готовы заменить патч-помпу. + Приостановка подачи инсулина завершена\nНажмите \'Возобновить\' для перезапуска подачи инсулина. + Резервуар почти пуст\nБудьте готовы вскоре замените патч-помпу. + Срок службы Патч-помпы истёк\nЗамените Патч-помпу. + Срок работы Патч-помпы вскоре истечет\nЗамените Патч-помпу. + Неполная активация Патч-помпы\nЗавершите процесс активации Патч-помпы. + Низкий уровень заряда батареи\nБудьте готовы заменить Патч-помпу. + diff --git a/pump/omnipod-dash/src/main/res/values-ru-rRU/strings.xml b/pump/omnipod-dash/src/main/res/values-ru-rRU/strings.xml index 3141c418fe..10c75991d0 100644 --- a/pump/omnipod-dash/src/main/res/values-ru-rRU/strings.xml +++ b/pump/omnipod-dash/src/main/res/values-ru-rRU/strings.xml @@ -6,6 +6,7 @@ Журнал помпы Описание + Количество Источник Дата Тип: @@ -30,8 +31,10 @@ Команда не отправлена Команда не получена помпой Состояние команды неясно + %1$.2f ед/ч, %2$d минут %1$.2f ед Введение инсулина приостановлено + Всего подано: %1$.2f ед Потеряно соединение с подом Вводится еще один болюс В резервуаре недостаточно инсулина @@ -44,6 +47,7 @@ Не удалось установить новый базовый профиль. Подача инсулина приостановлена Возможно не удалось задать базальный профиль. Подача инсулина может быть приостановлена! Обновите вручную состояние Pod на вкладке Omnipod и при необходимости возобновите процесс подачи. Статус подачи болюса неясен. Обновите статус pod, чтобы подтвердить или отклонить. + Неожиданное состояние врем базала! Если перед этим подавался врем базал, то он отменен. Проверьте кол-во поданного инсулина и журнал событий POD Выполняется проверка статуса подачи Установка врем базала могла иметь сбой. Если временный базал запущен ранее, он был отменен. Вручную обновите статус Pod на вкладке Omnipod. Результат отмены временного базала неясен diff --git a/wear/src/main/res/values-ru-rRU/strings.xml b/wear/src/main/res/values-ru-rRU/strings.xml index 04558bc81a..db94f8ded6 100644 --- a/wear/src/main/res/values-ru-rRU/strings.xml +++ b/wear/src/main/res/values-ru-rRU/strings.xml @@ -193,4 +193,5 @@ старые !старое! !ошибка! + Частота сердечных сокращений