Merge remote-tracking branch 'nightscout/dev' into medtrum-activate-patch2
This commit is contained in:
commit
404365aed2
|
@ -5,7 +5,7 @@ version: 2.1
|
|||
# Orbs are reusable packages of CircleCI configuration that you may share across projects, enabling you to create encapsulated, parameterized commands, jobs, and executors that can be used across multiple projects.
|
||||
orbs:
|
||||
android: circleci/android@1.0.3
|
||||
codecov: codecov/codecov@1.2.0
|
||||
codecov: codecov/codecov@3.2.4
|
||||
|
||||
jobs:
|
||||
# Below is the definition of your job to build and test your app, you can rename and customize it as you want.
|
||||
|
@ -45,4 +45,4 @@ workflows:
|
|||
# For more details on extending your workflow, see the configuration docs: https://circleci.com/docs/2.0/configuration-reference/#workflows
|
||||
dotests:
|
||||
jobs:
|
||||
- build-and-test
|
||||
- build-and-test
|
||||
|
|
|
@ -16,8 +16,12 @@ fun PackageManager.safeGetInstalledPackages(flags: Int): List<PackageInfo> =
|
|||
* Safe version of queryBroadcastReceivers depending on Android version running
|
||||
*/
|
||||
fun PackageManager.safeQueryBroadcastReceivers(intent: Intent, flags: Int): List<ResolveInfo> =
|
||||
if (android.os.Build.VERSION.SDK_INT >= android.os.Build.VERSION_CODES.TIRAMISU) queryBroadcastReceivers(intent, PackageManager.ResolveInfoFlags.of(flags.toLong()))
|
||||
else @Suppress("DEPRECATION") queryBroadcastReceivers(intent, flags)
|
||||
try {
|
||||
if (android.os.Build.VERSION.SDK_INT >= android.os.Build.VERSION_CODES.TIRAMISU) queryBroadcastReceivers(intent, PackageManager.ResolveInfoFlags.of(flags.toLong()))
|
||||
else @Suppress("DEPRECATION") queryBroadcastReceivers(intent, flags)
|
||||
} catch (ignored: Exception) {
|
||||
emptyList()
|
||||
}
|
||||
|
||||
/**
|
||||
* Safe version of getPackageInfo depending on Android version running
|
||||
|
|
|
@ -111,7 +111,7 @@ android {
|
|||
defaultConfig {
|
||||
multiDexEnabled true
|
||||
versionCode 1500
|
||||
version "3.2.0-dev-i-medtrum"
|
||||
version "3.2.0-dev-j-medtrum"
|
||||
buildConfigField "String", "VERSION", '"' + version + '"'
|
||||
buildConfigField "String", "BUILDVERSION", '"' + generateGitBuild() + '-' + generateDate() + '"'
|
||||
buildConfigField "String", "REMOTE", '"' + generateGitRemote() + '"'
|
||||
|
|
|
@ -24,6 +24,7 @@ import android.widget.TextView
|
|||
import androidx.appcompat.app.ActionBarDrawerToggle
|
||||
import androidx.appcompat.widget.Toolbar
|
||||
import androidx.core.view.GravityCompat
|
||||
import androidx.core.view.MenuCompat
|
||||
import androidx.viewpager2.widget.ViewPager2
|
||||
import com.google.android.material.dialog.MaterialAlertDialogBuilder
|
||||
import com.google.android.material.tabs.TabLayoutMediator
|
||||
|
@ -302,7 +303,7 @@ class MainActivity : DaggerAppCompatActivityWithResult() {
|
|||
|
||||
override fun onCreateOptionsMenu(menu: Menu): Boolean {
|
||||
super.onCreateOptionsMenu(menu)
|
||||
menu.setGroupDividerEnabled(true)
|
||||
MenuCompat.setGroupDividerEnabled(menu, true)
|
||||
this.menu = menu
|
||||
menuInflater.inflate(R.menu.menu_main, menu)
|
||||
pluginPreferencesMenuItem = menu.findItem(R.id.nav_plugin_preferences)
|
||||
|
@ -477,4 +478,4 @@ class MainActivity : DaggerAppCompatActivityWithResult() {
|
|||
ToastUtils.okToast(context, context.getString(info.nightscout.core.ui.R.string.password_set))
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
|
@ -11,9 +11,9 @@ import android.widget.TextView
|
|||
import com.google.android.material.datepicker.MaterialDatePicker
|
||||
import com.jjoe64.graphview.GraphView
|
||||
import dagger.android.HasAndroidInjector
|
||||
import dagger.android.support.DaggerAppCompatActivity
|
||||
import info.nightscout.androidaps.databinding.ActivityHistorybrowseBinding
|
||||
import info.nightscout.core.events.EventIobCalculationProgress
|
||||
import info.nightscout.core.ui.activities.TranslatedDaggerAppCompatActivity
|
||||
import info.nightscout.core.utils.fabric.FabricPrivacy
|
||||
import info.nightscout.core.workflow.CalculationWorkflow
|
||||
import info.nightscout.interfaces.Config
|
||||
|
@ -42,7 +42,7 @@ import java.util.GregorianCalendar
|
|||
import javax.inject.Inject
|
||||
import kotlin.math.min
|
||||
|
||||
class HistoryBrowseActivity : DaggerAppCompatActivity() {
|
||||
class HistoryBrowseActivity : TranslatedDaggerAppCompatActivity() {
|
||||
|
||||
@Inject lateinit var historyBrowserData: HistoryBrowserData
|
||||
@Inject lateinit var injector: HasAndroidInjector
|
||||
|
|
|
@ -1,6 +1,5 @@
|
|||
package info.nightscout.androidaps.activities
|
||||
|
||||
import android.content.Context
|
||||
import android.os.Bundle
|
||||
import android.view.Menu
|
||||
import android.view.MenuItem
|
||||
|
@ -10,7 +9,6 @@ import androidx.preference.PreferenceScreen
|
|||
import info.nightscout.androidaps.R
|
||||
import info.nightscout.androidaps.databinding.ActivityPreferencesBinding
|
||||
import info.nightscout.configuration.activities.DaggerAppCompatActivityWithResult
|
||||
import info.nightscout.core.ui.locale.LocaleHelper
|
||||
|
||||
class PreferencesActivity : DaggerAppCompatActivityWithResult(), PreferenceFragmentCompat.OnPreferenceStartScreenCallback {
|
||||
|
||||
|
@ -66,10 +64,6 @@ class PreferencesActivity : DaggerAppCompatActivityWithResult(), PreferenceFragm
|
|||
return true
|
||||
}
|
||||
|
||||
override fun attachBaseContext(newBase: Context) {
|
||||
super.attachBaseContext(LocaleHelper.wrap(newBase))
|
||||
}
|
||||
|
||||
override fun onOptionsItemSelected(item: MenuItem): Boolean =
|
||||
when (item.itemId) {
|
||||
android.R.id.home -> {
|
||||
|
|
|
@ -191,7 +191,7 @@ class KeepAliveWorker(
|
|||
}
|
||||
if (loop.isDisconnected) {
|
||||
// do nothing if pump is disconnected
|
||||
} else if (runningProfile == null || ((!pump.isThisProfileSet(requestedProfile) || !requestedProfile.isEqual(runningProfile)) && !commandQueue.isRunning(Command.CommandType.BASAL_PROFILE))) {
|
||||
} else if (runningProfile == null || ((!pump.isThisProfileSet(requestedProfile) || !requestedProfile.isEqual(runningProfile) || (runningProfile is ProfileSealed.EPS && runningProfile.value.originalEnd < dateUtil.now())) && !commandQueue.isRunning(Command.CommandType.BASAL_PROFILE))) {
|
||||
rxBus.send(EventProfileSwitchChanged())
|
||||
} else if (isStatusOutdated && !pump.isBusy()) {
|
||||
lastReadStatus = now
|
||||
|
|
32
build.gradle
32
build.gradle
|
@ -2,22 +2,22 @@
|
|||
|
||||
buildscript {
|
||||
ext {
|
||||
kotlin_version = '1.8.10'
|
||||
core_version = '1.9.0'
|
||||
kotlin_version = '1.8.21'
|
||||
core_version = '1.10.1'
|
||||
rxjava_version = '3.1.6'
|
||||
rxandroid_version = '3.0.2'
|
||||
rxkotlin_version = '3.0.1'
|
||||
room_version = '2.5.1'
|
||||
lifecycle_version = '2.5.1'
|
||||
dagger_version = '2.45'
|
||||
coroutines_version = '1.6.4'
|
||||
activity_version = '1.6.1'
|
||||
fragmentktx_version = '1.5.6'
|
||||
lifecycle_version = '2.6.1'
|
||||
dagger_version = '2.46.1'
|
||||
coroutines_version = '1.7.1'
|
||||
activity_version = '1.7.1'
|
||||
fragmentktx_version = '1.5.7'
|
||||
ormLite_version = '4.46'
|
||||
gson_version = '2.10.1'
|
||||
nav_version = '2.5.3'
|
||||
appcompat_version = '1.6.1'
|
||||
material_version = '1.8.0'
|
||||
material_version = '1.9.0'
|
||||
gridlayout_version = '1.0.0'
|
||||
constraintlayout_version = '2.1.4'
|
||||
preferencektx_version = '1.2.0'
|
||||
|
@ -25,17 +25,17 @@ buildscript {
|
|||
commonscodec_version = '1.15'
|
||||
jodatime_version = '2.10.14'
|
||||
work_version = '2.8.1'
|
||||
tink_version = '1.8.0'
|
||||
tink_version = '1.9.0'
|
||||
json_version = '20220320'
|
||||
joda_version = '2.12.1.1'
|
||||
joda_version = '2.12.5'
|
||||
swipe_version = '1.1.0'
|
||||
|
||||
junit_version = '4.13.2'
|
||||
junit_jupiter_version = '5.9.2'
|
||||
junit_jupiter_version = '5.9.3'
|
||||
mockito_version = '4.6.1'
|
||||
dexmaker_version = '1.2'
|
||||
retrofit2_version = '2.9.0'
|
||||
okhttp3_version = '4.10.0'
|
||||
okhttp3_version = '4.11.0'
|
||||
byteBuddy_version = '1.12.8'
|
||||
|
||||
androidx_junit_version = '1.1.4'
|
||||
|
@ -49,7 +49,7 @@ buildscript {
|
|||
play_services_location_version = '21.0.1'
|
||||
|
||||
kotlinx_datetime_version = '0.4.0'
|
||||
kotlinx_serialization_version = '1.5.0'
|
||||
kotlinx_serialization_version = '1.5.1'
|
||||
}
|
||||
repositories {
|
||||
google()
|
||||
|
@ -58,8 +58,8 @@ buildscript {
|
|||
}
|
||||
dependencies {
|
||||
classpath 'com.android.tools.build:gradle:7.4.2'
|
||||
classpath 'com.google.gms:google-services:4.3.14'
|
||||
classpath 'com.google.firebase:firebase-crashlytics-gradle:2.9.4'
|
||||
classpath 'com.google.gms:google-services:4.3.15'
|
||||
classpath 'com.google.firebase:firebase-crashlytics-gradle:2.9.5'
|
||||
|
||||
// NOTE: Do not place your application dependencies here; they belong
|
||||
// in the individual module build.gradle files
|
||||
|
@ -75,7 +75,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.3.1"
|
||||
id "org.jlleitschuh.gradle.ktlint" version "11.3.2"
|
||||
id 'org.barfuin.gradle.jacocolog' version '3.1.0'
|
||||
id 'org.jetbrains.kotlin.android' version "$kotlin_version" apply false
|
||||
}
|
||||
|
|
|
@ -25,7 +25,6 @@ interface CommandQueue {
|
|||
fun extendedBolus(insulin: Double, durationInMinutes: Int, callback: Callback?): Boolean
|
||||
fun cancelTempBasal(enforceNew: Boolean, callback: Callback?): Boolean
|
||||
fun cancelExtended(callback: Callback?): Boolean
|
||||
fun setProfile(profile: Profile, hasNsId: Boolean, callback: Callback?): Boolean
|
||||
fun readStatus(reason: String, callback: Callback?): Boolean
|
||||
fun statusInQueue(): Boolean
|
||||
fun loadHistory(type: Byte, callback: Callback?): Boolean
|
||||
|
|
|
@ -292,14 +292,11 @@ class NSAndroidClientImpl(
|
|||
lastModified = response.body()?.lastModified
|
||||
)
|
||||
} else throw UnknownResponseNightscoutException()
|
||||
} else if (response.code() in 400..499) {
|
||||
return@callWrapper CreateUpdateResponse(
|
||||
response = response.code(),
|
||||
identifier = null,
|
||||
errorResponse = response.errorBody()?.string() ?: response.message()
|
||||
)
|
||||
} else
|
||||
throw UnsuccessfullNightscoutException(response.errorBody()?.string() ?: response.message())
|
||||
} else return@callWrapper CreateUpdateResponse(
|
||||
response = response.code(),
|
||||
identifier = null,
|
||||
errorResponse = response.errorBody()?.string() ?: response.message()
|
||||
)
|
||||
}
|
||||
|
||||
override suspend fun createTreatment(nsTreatment: NSTreatment): CreateUpdateResponse = callWrapper(dispatcher) {
|
||||
|
|
|
@ -4,7 +4,7 @@ import android.content.Context
|
|||
import dagger.android.support.DaggerAppCompatActivity
|
||||
import info.nightscout.core.ui.locale.LocaleHelper
|
||||
|
||||
open class DialogAppCompatActivity : DaggerAppCompatActivity() {
|
||||
open class TranslatedDaggerAppCompatActivity : DaggerAppCompatActivity() {
|
||||
override fun attachBaseContext(newBase: Context) {
|
||||
super.attachBaseContext(LocaleHelper.wrap(newBase))
|
||||
}
|
|
@ -82,7 +82,7 @@
|
|||
<string name="bluetooth">Bluetooth</string>
|
||||
<string name="btwatchdog_title">BT Watchdog</string>
|
||||
<string name="btwatchdog_summary">Vienai sekundei išjungia telefono bluetooth, jei ryšys su pompa nutrūksta. Gali būti veiksminga kai kuriems telefonų modeliams, turintiems BT problemų.</string>
|
||||
<string name="virtualpump_resultok">Gerai</string>
|
||||
<string name="virtualpump_resultok">OK</string>
|
||||
<string name="pump_time_updated">Pompos laikas pakeistas</string>
|
||||
<string name="exit">Išeiti</string>
|
||||
<string name="removerecord">Ištrinti įrašą</string>
|
||||
|
@ -232,7 +232,7 @@
|
|||
<string name="hypo">Hipo</string>
|
||||
<string name="activity">Aktyvumas</string>
|
||||
<string name="wear">Išmanieji laikrodžiai</string>
|
||||
<string name="automation">Automatiškai</string>
|
||||
<string name="automation">Automatizacija</string>
|
||||
<string name="custom">Pasirinktinis</string>
|
||||
<string name="loop">Ciklas</string>
|
||||
<string name="ns">NS</string>
|
||||
|
@ -525,7 +525,7 @@
|
|||
<!-- Dialogs-->
|
||||
<string name="confirmation">Patvirtinimas</string>
|
||||
<string name="message">Pranešimas</string>
|
||||
<string name="ok">Gerai</string>
|
||||
<string name="ok">OK</string>
|
||||
<string name="cancel">Atšaukti</string>
|
||||
<string name="dismiss">ATMESTI</string>
|
||||
<string name="yes">Taip</string>
|
||||
|
|
|
@ -22,7 +22,7 @@ dependencies {
|
|||
implementation project(':app-wear-shared:shared')
|
||||
|
||||
//Firebase
|
||||
api platform('com.google.firebase:firebase-bom:31.2.3')
|
||||
api platform('com.google.firebase:firebase-bom:32.0.0')
|
||||
api "com.google.firebase:firebase-analytics-ktx"
|
||||
api "com.google.firebase:firebase-crashlytics-ktx"
|
||||
// StatsActivity not in use now
|
||||
|
|
|
@ -5,6 +5,7 @@ import android.view.ActionMode
|
|||
import android.view.Menu
|
||||
import android.view.MenuInflater
|
||||
import android.view.MenuItem
|
||||
import androidx.core.view.MenuCompat
|
||||
import androidx.fragment.app.Fragment
|
||||
import androidx.fragment.app.FragmentActivity
|
||||
import info.nightscout.shared.interfaces.ResourceHelper
|
||||
|
@ -68,7 +69,7 @@ class ActionModeHelper<T>(val rh: ResourceHelper, val activity: FragmentActivity
|
|||
} else if (fragment?.isResumed == true) {
|
||||
menu.add(Menu.FIRST, R.id.nav_remove_items, 0, rh.gs(R.string.remove_items)).setShowAsAction(MenuItem.SHOW_AS_ACTION_NEVER)
|
||||
menu.add(Menu.FIRST, R.id.nav_sort_items, 0, rh.gs(R.string.sort_items)).setShowAsAction(MenuItem.SHOW_AS_ACTION_NEVER)
|
||||
menu.setGroupDividerEnabled(true)
|
||||
MenuCompat.setGroupDividerEnabled(menu, true)
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
@ -7,6 +7,7 @@ plugins {
|
|||
}
|
||||
|
||||
apply from: "${project.rootDir}/core/main/android_dependencies.gradle"
|
||||
apply from: "${project.rootDir}/core/main/test_dependencies.gradle"
|
||||
|
||||
android {
|
||||
|
||||
|
@ -30,4 +31,4 @@ dependencies {
|
|||
allOpen {
|
||||
// allows mocking for classes w/o directly opening them for release builds
|
||||
annotation 'info.nightscout.database.annotations.DbOpenForTesting'
|
||||
}
|
||||
}
|
||||
|
|
|
@ -0,0 +1,44 @@
|
|||
package info.nightscout.database.entities
|
||||
|
||||
import androidx.room.Embedded
|
||||
import androidx.room.Entity
|
||||
import androidx.room.Index
|
||||
import androidx.room.PrimaryKey
|
||||
import info.nightscout.database.entities.embedments.InterfaceIDs
|
||||
import info.nightscout.database.entities.interfaces.DBEntryWithTimeAndDuration
|
||||
import info.nightscout.database.entities.interfaces.TraceableDBEntry
|
||||
import java.util.*
|
||||
|
||||
/** Heart rate values measured by a user smart watch or the like. */
|
||||
@Entity(
|
||||
tableName = TABLE_HEART_RATE,
|
||||
indices = [Index("id"), Index("timestamp")]
|
||||
)
|
||||
data class HeartRate(
|
||||
@PrimaryKey(autoGenerate = true)
|
||||
override var id: Long = 0,
|
||||
/** Duration milliseconds */
|
||||
override var duration: Long,
|
||||
/** Milliseconds since the epoch. End of the sampling period, i.e. the value is
|
||||
* sampled from timestamp-duration to timestamp. */
|
||||
override var timestamp: Long,
|
||||
var beatsPerMinute: Double,
|
||||
/** Source device that measured the heart rate. */
|
||||
var device: String,
|
||||
override var utcOffset: Long = TimeZone.getDefault().getOffset(timestamp).toLong(),
|
||||
override var version: Int = 0,
|
||||
override var dateCreated: Long = -1,
|
||||
override var isValid: Boolean = true,
|
||||
override var referenceId: Long? = null,
|
||||
@Embedded
|
||||
override var interfaceIDs_backing: InterfaceIDs? = null
|
||||
) : TraceableDBEntry, DBEntryWithTimeAndDuration {
|
||||
|
||||
fun contentEqualsTo(other: HeartRate): Boolean {
|
||||
return this === other || (
|
||||
duration == other.duration &&
|
||||
timestamp == other.timestamp &&
|
||||
beatsPerMinute == other.beatsPerMinute &&
|
||||
isValid == other.isValid)
|
||||
}
|
||||
}
|
|
@ -8,6 +8,7 @@ const val TABLE_CARBS = "carbs"
|
|||
const val TABLE_DEVICE_STATUS = "deviceStatus"
|
||||
const val TABLE_EFFECTIVE_PROFILE_SWITCHES = "effectiveProfileSwitches"
|
||||
const val TABLE_EXTENDED_BOLUSES = "extendedBoluses"
|
||||
const val TABLE_HEART_RATE = "heartRate"
|
||||
const val TABLE_GLUCOSE_VALUES = "glucoseValues"
|
||||
const val TABLE_FOODS = "foods"
|
||||
const val TABLE_MULTIWAVE_BOLUS_LINKS = "multiwaveBolusLinks"
|
||||
|
|
|
@ -8,6 +8,7 @@ import info.nightscout.database.entities.Carbs
|
|||
import info.nightscout.database.entities.EffectiveProfileSwitch
|
||||
import info.nightscout.database.entities.ExtendedBolus
|
||||
import info.nightscout.database.entities.GlucoseValue
|
||||
import info.nightscout.database.entities.HeartRate
|
||||
import info.nightscout.database.entities.MultiwaveBolusLink
|
||||
import info.nightscout.database.entities.OfflineEvent
|
||||
import info.nightscout.database.entities.PreferenceChange
|
||||
|
@ -35,5 +36,6 @@ data class NewEntries(
|
|||
val temporaryTarget: List<TemporaryTarget>,
|
||||
val therapyEvents: List<TherapyEvent>,
|
||||
val totalDailyDoses: List<TotalDailyDose>,
|
||||
val versionChanges: List<VersionChange>
|
||||
)
|
||||
val versionChanges: List<VersionChange>,
|
||||
val heartRates: List<HeartRate>,
|
||||
)
|
||||
|
|
|
@ -0,0 +1,36 @@
|
|||
package info.nightscout.database.entities
|
||||
|
||||
import org.junit.Assert.assertFalse
|
||||
import org.junit.Assert.assertTrue
|
||||
import org.junit.jupiter.api.Test
|
||||
|
||||
class HeartRateTest {
|
||||
@Test
|
||||
fun contentEqualsTo_equals() {
|
||||
val hr1 = createHeartRate()
|
||||
assertTrue(hr1.contentEqualsTo(hr1))
|
||||
assertTrue(hr1.contentEqualsTo(hr1.copy()))
|
||||
assertTrue(hr1.contentEqualsTo(hr1.copy (id = 2, version = 2, dateCreated = 1L, referenceId = 4L)))
|
||||
}
|
||||
|
||||
@Test
|
||||
fun contentEqualsTo_notEquals() {
|
||||
val hr1 = createHeartRate()
|
||||
assertFalse(hr1.contentEqualsTo(hr1.copy(duration = 60_001L)))
|
||||
assertFalse(hr1.contentEqualsTo(hr1.copy(timestamp = 2L)))
|
||||
assertFalse(hr1.contentEqualsTo(hr1.copy(duration = 60_001L)))
|
||||
assertFalse(hr1.contentEqualsTo(hr1.copy(beatsPerMinute = 100.0)))
|
||||
assertFalse(hr1.contentEqualsTo(hr1.copy(isValid = false)))
|
||||
}
|
||||
|
||||
companion object {
|
||||
|
||||
fun createHeartRate(timestamp: Long? = null, beatsPerMinute: Double = 80.0) =
|
||||
HeartRate(
|
||||
timestamp = timestamp ?: System.currentTimeMillis(),
|
||||
duration = 60_0000L,
|
||||
beatsPerMinute = beatsPerMinute,
|
||||
device = "T",
|
||||
)
|
||||
}
|
||||
}
|
|
@ -8,6 +8,8 @@ plugins {
|
|||
|
||||
apply from: "${project.rootDir}/core/main/android_dependencies.gradle"
|
||||
apply from: "${project.rootDir}/core/main/android_module_dependencies.gradle"
|
||||
apply from: "${project.rootDir}/core/main/test_dependencies.gradle"
|
||||
apply from: "${project.rootDir}/core/main/jacoco_global.gradle"
|
||||
|
||||
android {
|
||||
|
||||
|
@ -20,6 +22,9 @@ android {
|
|||
}
|
||||
}
|
||||
}
|
||||
sourceSets {
|
||||
androidTest.assets.srcDirs += files("$projectDir/schemas")
|
||||
}
|
||||
}
|
||||
|
||||
dependencies {
|
||||
|
@ -44,9 +49,11 @@ dependencies {
|
|||
|
||||
api "com.google.dagger:dagger-android:$dagger_version"
|
||||
api "com.google.dagger:dagger-android-support:$dagger_version"
|
||||
|
||||
androidTestImplementation "androidx.room:room-testing:$room_version"
|
||||
}
|
||||
|
||||
allOpen {
|
||||
// allows mocking for classes w/o directly opening them for release builds
|
||||
annotation 'info.nightscout.database.annotations.DbOpenForTesting'
|
||||
}
|
||||
}
|
||||
|
|
|
@ -2,7 +2,7 @@
|
|||
"formatVersion": 1,
|
||||
"database": {
|
||||
"version": 23,
|
||||
"identityHash": "173734db5f4f35f6295ed953d8124794",
|
||||
"identityHash": "a3ee37800b6cda170d0ea64799ed7876",
|
||||
"entities": [
|
||||
{
|
||||
"tableName": "apsResults",
|
||||
|
@ -3689,12 +3689,153 @@
|
|||
]
|
||||
}
|
||||
]
|
||||
},
|
||||
{
|
||||
"tableName": "heartRate",
|
||||
"createSql": "CREATE TABLE IF NOT EXISTS `${TABLE_NAME}` (`id` INTEGER PRIMARY KEY AUTOINCREMENT NOT NULL, `duration` INTEGER NOT NULL, `timestamp` INTEGER NOT NULL, `beatsPerMinute` REAL NOT NULL, `device` TEXT NOT NULL, `utcOffset` INTEGER NOT NULL, `version` INTEGER NOT NULL, `dateCreated` INTEGER NOT NULL, `isValid` INTEGER NOT NULL, `referenceId` INTEGER, `nightscoutSystemId` TEXT, `nightscoutId` TEXT, `pumpType` TEXT, `pumpSerial` TEXT, `temporaryId` INTEGER, `pumpId` INTEGER, `startId` INTEGER, `endId` INTEGER)",
|
||||
"fields": [
|
||||
{
|
||||
"fieldPath": "id",
|
||||
"columnName": "id",
|
||||
"affinity": "INTEGER",
|
||||
"notNull": true
|
||||
},
|
||||
{
|
||||
"fieldPath": "duration",
|
||||
"columnName": "duration",
|
||||
"affinity": "INTEGER",
|
||||
"notNull": true
|
||||
},
|
||||
{
|
||||
"fieldPath": "timestamp",
|
||||
"columnName": "timestamp",
|
||||
"affinity": "INTEGER",
|
||||
"notNull": true
|
||||
},
|
||||
{
|
||||
"fieldPath": "beatsPerMinute",
|
||||
"columnName": "beatsPerMinute",
|
||||
"affinity": "REAL",
|
||||
"notNull": true
|
||||
},
|
||||
{
|
||||
"fieldPath": "device",
|
||||
"columnName": "device",
|
||||
"affinity": "TEXT",
|
||||
"notNull": true
|
||||
},
|
||||
{
|
||||
"fieldPath": "utcOffset",
|
||||
"columnName": "utcOffset",
|
||||
"affinity": "INTEGER",
|
||||
"notNull": true
|
||||
},
|
||||
{
|
||||
"fieldPath": "version",
|
||||
"columnName": "version",
|
||||
"affinity": "INTEGER",
|
||||
"notNull": true
|
||||
},
|
||||
{
|
||||
"fieldPath": "dateCreated",
|
||||
"columnName": "dateCreated",
|
||||
"affinity": "INTEGER",
|
||||
"notNull": true
|
||||
},
|
||||
{
|
||||
"fieldPath": "isValid",
|
||||
"columnName": "isValid",
|
||||
"affinity": "INTEGER",
|
||||
"notNull": true
|
||||
},
|
||||
{
|
||||
"fieldPath": "referenceId",
|
||||
"columnName": "referenceId",
|
||||
"affinity": "INTEGER",
|
||||
"notNull": false
|
||||
},
|
||||
{
|
||||
"fieldPath": "interfaceIDs_backing.nightscoutSystemId",
|
||||
"columnName": "nightscoutSystemId",
|
||||
"affinity": "TEXT",
|
||||
"notNull": false
|
||||
},
|
||||
{
|
||||
"fieldPath": "interfaceIDs_backing.nightscoutId",
|
||||
"columnName": "nightscoutId",
|
||||
"affinity": "TEXT",
|
||||
"notNull": false
|
||||
},
|
||||
{
|
||||
"fieldPath": "interfaceIDs_backing.pumpType",
|
||||
"columnName": "pumpType",
|
||||
"affinity": "TEXT",
|
||||
"notNull": false
|
||||
},
|
||||
{
|
||||
"fieldPath": "interfaceIDs_backing.pumpSerial",
|
||||
"columnName": "pumpSerial",
|
||||
"affinity": "TEXT",
|
||||
"notNull": false
|
||||
},
|
||||
{
|
||||
"fieldPath": "interfaceIDs_backing.temporaryId",
|
||||
"columnName": "temporaryId",
|
||||
"affinity": "INTEGER",
|
||||
"notNull": false
|
||||
},
|
||||
{
|
||||
"fieldPath": "interfaceIDs_backing.pumpId",
|
||||
"columnName": "pumpId",
|
||||
"affinity": "INTEGER",
|
||||
"notNull": false
|
||||
},
|
||||
{
|
||||
"fieldPath": "interfaceIDs_backing.startId",
|
||||
"columnName": "startId",
|
||||
"affinity": "INTEGER",
|
||||
"notNull": false
|
||||
},
|
||||
{
|
||||
"fieldPath": "interfaceIDs_backing.endId",
|
||||
"columnName": "endId",
|
||||
"affinity": "INTEGER",
|
||||
"notNull": false
|
||||
}
|
||||
],
|
||||
"primaryKey": {
|
||||
"autoGenerate": true,
|
||||
"columnNames": [
|
||||
"id"
|
||||
]
|
||||
},
|
||||
"indices": [
|
||||
{
|
||||
"name": "index_heartRate_id",
|
||||
"unique": false,
|
||||
"columnNames": [
|
||||
"id"
|
||||
],
|
||||
"orders": [],
|
||||
"createSql": "CREATE INDEX IF NOT EXISTS `index_heartRate_id` ON `${TABLE_NAME}` (`id`)"
|
||||
},
|
||||
{
|
||||
"name": "index_heartRate_timestamp",
|
||||
"unique": false,
|
||||
"columnNames": [
|
||||
"timestamp"
|
||||
],
|
||||
"orders": [],
|
||||
"createSql": "CREATE INDEX IF NOT EXISTS `index_heartRate_timestamp` ON `${TABLE_NAME}` (`timestamp`)"
|
||||
}
|
||||
],
|
||||
"foreignKeys": []
|
||||
}
|
||||
],
|
||||
"views": [],
|
||||
"setupQueries": [
|
||||
"CREATE TABLE IF NOT EXISTS room_master_table (id INTEGER PRIMARY KEY,identity_hash TEXT)",
|
||||
"INSERT OR REPLACE INTO room_master_table (id,identity_hash) VALUES(42, '173734db5f4f35f6295ed953d8124794')"
|
||||
"INSERT OR REPLACE INTO room_master_table (id,identity_hash) VALUES(42, 'a3ee37800b6cda170d0ea64799ed7876')"
|
||||
]
|
||||
}
|
||||
}
|
File diff suppressed because it is too large
Load diff
|
@ -0,0 +1,108 @@
|
|||
package info.nightscout.database.impl
|
||||
|
||||
import android.content.Context
|
||||
import androidx.room.Room
|
||||
import androidx.room.testing.MigrationTestHelper
|
||||
import androidx.sqlite.db.SupportSQLiteDatabase
|
||||
import androidx.test.core.app.ApplicationProvider
|
||||
import androidx.test.ext.junit.runners.AndroidJUnit4
|
||||
import androidx.test.platform.app.InstrumentationRegistry
|
||||
import info.nightscout.database.entities.HeartRate
|
||||
import info.nightscout.database.entities.TABLE_HEART_RATE
|
||||
import org.junit.Assert.assertEquals
|
||||
import org.junit.Assert.assertFalse
|
||||
import org.junit.Assert.assertTrue
|
||||
import org.junit.Test
|
||||
import org.junit.runner.RunWith
|
||||
|
||||
@RunWith(AndroidJUnit4::class)
|
||||
internal class HeartRateDaoTest {
|
||||
|
||||
private val context = ApplicationProvider.getApplicationContext<Context>()
|
||||
private fun createDatabase() =
|
||||
Room.inMemoryDatabaseBuilder(context, AppDatabase::class.java).build()
|
||||
|
||||
private fun getDbObjects(supportDb: SupportSQLiteDatabase, type: String): Set<String> {
|
||||
val names = mutableSetOf<String>()
|
||||
supportDb.query("SELECT name FROM sqlite_master WHERE type = '$type'").use { c ->
|
||||
while (c.moveToNext()) names.add(c.getString(0))
|
||||
}
|
||||
return names
|
||||
}
|
||||
|
||||
private fun getTableNames(db: SupportSQLiteDatabase) = getDbObjects(db, "table")
|
||||
private fun getIndexNames(db: SupportSQLiteDatabase) = getDbObjects(db, "index")
|
||||
|
||||
private fun insertAndFind(database: AppDatabase) {
|
||||
val hr1 = createHeartRate()
|
||||
val id = database.heartRateDao.insert(hr1)
|
||||
val hr2 = database.heartRateDao.findById(id)
|
||||
assertTrue(hr1.contentEqualsTo(hr2!!))
|
||||
}
|
||||
|
||||
@Test
|
||||
fun new_insertAndFind() {
|
||||
createDatabase().use { db -> insertAndFind(db) }
|
||||
}
|
||||
|
||||
@Test
|
||||
fun migrate_createsTableAndIndices() {
|
||||
val helper = MigrationTestHelper(
|
||||
InstrumentationRegistry.getInstrumentation(),
|
||||
AppDatabase::class.java
|
||||
)
|
||||
val startVersion = 22
|
||||
val supportDb = helper.createDatabase(TEST_DB_NAME, startVersion)
|
||||
assertFalse(getTableNames(supportDb).contains(TABLE_HEART_RATE))
|
||||
DatabaseModule().migrations.filter { m -> m.startVersion >= startVersion }.forEach { m -> m.migrate(supportDb) }
|
||||
assertTrue(getTableNames(supportDb).contains(TABLE_HEART_RATE))
|
||||
assertTrue(getIndexNames(supportDb).contains("index_heartRate_id"))
|
||||
assertTrue(getIndexNames(supportDb).contains("index_heartRate_timestamp"))
|
||||
}
|
||||
|
||||
@Test
|
||||
fun migrate_insertAndFind() {
|
||||
val helper = MigrationTestHelper(
|
||||
InstrumentationRegistry.getInstrumentation(),
|
||||
AppDatabase::class.java
|
||||
)
|
||||
// Create the database for version 22 (that's missing the heartRate table).
|
||||
// helper.createDatabase removes the db file if it already exists.
|
||||
val supportDb = helper.createDatabase(TEST_DB_NAME, 22)
|
||||
assertFalse(getTableNames(supportDb).contains(TABLE_HEART_RATE))
|
||||
// Room.databaseBuilder will use the previously created db file that has version 22.
|
||||
Room.databaseBuilder(ApplicationProvider.getApplicationContext(), AppDatabase::class.java, TEST_DB_NAME)
|
||||
.addMigrations(*DatabaseModule().migrations)
|
||||
.build().use { db -> insertAndFind(db) }
|
||||
}
|
||||
|
||||
@Test
|
||||
fun getFromTime() {
|
||||
createDatabase().use { db ->
|
||||
val dao = db.heartRateDao
|
||||
val timestamp = System.currentTimeMillis()
|
||||
val hr1 = createHeartRate(timestamp = timestamp, beatsPerMinute = 80.0)
|
||||
val hr2 = createHeartRate(timestamp = timestamp + 1, beatsPerMinute = 150.0)
|
||||
dao.insertNewEntry(hr1)
|
||||
dao.insertNewEntry(hr2)
|
||||
|
||||
assertEquals(listOf(hr1, hr2), dao.getFromTime(timestamp))
|
||||
assertEquals(listOf(hr2), dao.getFromTime(timestamp + 1))
|
||||
assertTrue(dao.getFromTime(timestamp + 2).isEmpty())
|
||||
}
|
||||
}
|
||||
|
||||
companion object {
|
||||
|
||||
private const val TEST_DB_NAME = "testDatabase"
|
||||
|
||||
fun createHeartRate(timestamp: Long? = null, beatsPerMinute: Double = 80.0) =
|
||||
HeartRate(
|
||||
timestamp = timestamp ?: System.currentTimeMillis(),
|
||||
duration = 60_0000L,
|
||||
beatsPerMinute = beatsPerMinute,
|
||||
device = "T",
|
||||
)
|
||||
|
||||
}
|
||||
}
|
|
@ -0,0 +1,57 @@
|
|||
package info.nightscout.database.impl.transactions
|
||||
|
||||
import android.content.Context
|
||||
import androidx.room.Room
|
||||
import androidx.test.core.app.ApplicationProvider
|
||||
import androidx.test.ext.junit.runners.AndroidJUnit4
|
||||
import info.nightscout.database.impl.AppDatabase
|
||||
import info.nightscout.database.impl.AppRepository
|
||||
import info.nightscout.database.impl.HeartRateDaoTest
|
||||
import org.junit.After
|
||||
import org.junit.Assert.assertEquals
|
||||
import org.junit.Assert.assertNotEquals
|
||||
import org.junit.Assert.assertTrue
|
||||
import org.junit.Before
|
||||
import org.junit.Test
|
||||
import org.junit.runner.RunWith
|
||||
|
||||
@RunWith(AndroidJUnit4::class)
|
||||
class InsertOrUpdateHeartRateTransactionTest {
|
||||
|
||||
private val context = ApplicationProvider.getApplicationContext<Context>()
|
||||
private lateinit var db: AppDatabase
|
||||
private lateinit var repo: AppRepository
|
||||
|
||||
@Before
|
||||
fun setupUp() {
|
||||
db = Room.inMemoryDatabaseBuilder(context, AppDatabase::class.java).build()
|
||||
repo = AppRepository(db)
|
||||
}
|
||||
|
||||
@After
|
||||
fun shutdown() {
|
||||
db.close()
|
||||
}
|
||||
|
||||
@Test
|
||||
fun createNewEntry() {
|
||||
val hr1 = HeartRateDaoTest.createHeartRate()
|
||||
val result = repo.runTransactionForResult(InsertOrUpdateHeartRateTransaction(hr1)).blockingGet()
|
||||
assertEquals(listOf(hr1), result.inserted)
|
||||
assertTrue(result.updated.isEmpty())
|
||||
}
|
||||
|
||||
@Test
|
||||
fun updateEntry() {
|
||||
val hr1 = HeartRateDaoTest.createHeartRate()
|
||||
val id = db.heartRateDao.insertNewEntry(hr1)
|
||||
assertNotEquals(0, id)
|
||||
val hr2 = hr1.copy(id = id, beatsPerMinute = 181.0)
|
||||
val result = repo.runTransactionForResult(InsertOrUpdateHeartRateTransaction(hr2)).blockingGet()
|
||||
assertEquals(listOf(hr2), result.updated)
|
||||
assertTrue(result.inserted.isEmpty())
|
||||
|
||||
val hr3 = db.heartRateDao.findById(id)!!
|
||||
assertTrue(hr2.contentEqualsTo(hr3))
|
||||
}
|
||||
}
|
|
@ -33,6 +33,7 @@ import info.nightscout.database.entities.EffectiveProfileSwitch
|
|||
import info.nightscout.database.entities.ExtendedBolus
|
||||
import info.nightscout.database.entities.Food
|
||||
import info.nightscout.database.entities.GlucoseValue
|
||||
import info.nightscout.database.entities.HeartRate
|
||||
import info.nightscout.database.entities.MultiwaveBolusLink
|
||||
import info.nightscout.database.entities.OfflineEvent
|
||||
import info.nightscout.database.entities.PreferenceChange
|
||||
|
@ -43,18 +44,20 @@ import info.nightscout.database.entities.TherapyEvent
|
|||
import info.nightscout.database.entities.TotalDailyDose
|
||||
import info.nightscout.database.entities.UserEntry
|
||||
import info.nightscout.database.entities.VersionChange
|
||||
import info.nightscout.database.impl.daos.HeartRateDao
|
||||
import java.io.Closeable
|
||||
|
||||
const val DATABASE_VERSION = 23
|
||||
const val DATABASE_VERSION = 24
|
||||
|
||||
@Database(version = DATABASE_VERSION,
|
||||
entities = [APSResult::class, Bolus::class, BolusCalculatorResult::class, Carbs::class,
|
||||
EffectiveProfileSwitch::class, ExtendedBolus::class, GlucoseValue::class, ProfileSwitch::class,
|
||||
TemporaryBasal::class, TemporaryTarget::class, TherapyEvent::class, TotalDailyDose::class, APSResultLink::class,
|
||||
MultiwaveBolusLink::class, PreferenceChange::class, VersionChange::class, UserEntry::class,
|
||||
Food::class, DeviceStatus::class, OfflineEvent::class],
|
||||
Food::class, DeviceStatus::class, OfflineEvent::class, HeartRate::class],
|
||||
exportSchema = true)
|
||||
@TypeConverters(Converters::class)
|
||||
internal abstract class AppDatabase : RoomDatabase() {
|
||||
internal abstract class AppDatabase : Closeable, RoomDatabase() {
|
||||
|
||||
abstract val glucoseValueDao: GlucoseValueDao
|
||||
|
||||
|
@ -96,4 +99,5 @@ internal abstract class AppDatabase : RoomDatabase() {
|
|||
|
||||
abstract val offlineEventDao: OfflineEventDao
|
||||
|
||||
}
|
||||
abstract val heartRateDao: HeartRateDao
|
||||
}
|
||||
|
|
|
@ -101,6 +101,7 @@ import kotlin.math.roundToInt
|
|||
//database.foodDao.deleteOlderThan(than)
|
||||
removed.add(Pair("DeviceStatus", database.deviceStatusDao.deleteOlderThan(than)))
|
||||
removed.add(Pair("OfflineEvent", database.offlineEventDao.deleteOlderThan(than)))
|
||||
removed.add(Pair("HeartRate", database.heartRateDao.deleteOlderThan(than)))
|
||||
|
||||
if (deleteTrackedChanges) {
|
||||
removed.add(Pair("GlucoseValue", database.glucoseValueDao.deleteTrackedChanges()))
|
||||
|
@ -119,6 +120,7 @@ import kotlin.math.roundToInt
|
|||
removed.add(Pair("ApsResult", database.apsResultDao.deleteTrackedChanges()))
|
||||
//database.foodDao.deleteHistory()
|
||||
removed.add(Pair("OfflineEvent", database.offlineEventDao.deleteTrackedChanges()))
|
||||
removed.add(Pair("HeartRate", database.heartRateDao.deleteTrackedChanges()))
|
||||
}
|
||||
val ret = StringBuilder()
|
||||
removed
|
||||
|
@ -930,6 +932,8 @@ import kotlin.math.roundToInt
|
|||
fun getLastOfflineEventId(): Long? =
|
||||
database.offlineEventDao.getLastId()
|
||||
|
||||
fun getHeartRatesFromTime(timeMillis: Long) = database.heartRateDao.getFromTime(timeMillis)
|
||||
|
||||
suspend fun collectNewEntriesSince(since: Long, until: Long, limit: Int, offset: Int) = NewEntries(
|
||||
apsResults = database.apsResultDao.getNewEntriesSince(since, until, limit, offset),
|
||||
apsResultLinks = database.apsResultLinkDao.getNewEntriesSince(since, until, limit, offset),
|
||||
|
@ -948,6 +952,7 @@ import kotlin.math.roundToInt
|
|||
therapyEvents = database.therapyEventDao.getNewEntriesSince(since, until, limit, offset),
|
||||
totalDailyDoses = database.totalDailyDoseDao.getNewEntriesSince(since, until, limit, offset),
|
||||
versionChanges = database.versionChangeDao.getNewEntriesSince(since, until, limit, offset),
|
||||
heartRates = database.heartRateDao.getNewEntriesSince(since, until, limit, offset),
|
||||
)
|
||||
}
|
||||
|
||||
|
@ -956,4 +961,3 @@ inline fun <reified T : Any> Maybe<T>.toWrappedSingle(): Single<ValueWrapper<T>>
|
|||
this.map { ValueWrapper.Existing(it) as ValueWrapper<T> }
|
||||
.switchIfEmpty(Maybe.just(ValueWrapper.Absent()))
|
||||
.toSingle()
|
||||
|
||||
|
|
|
@ -1,12 +1,14 @@
|
|||
package info.nightscout.database.impl
|
||||
|
||||
import android.content.Context
|
||||
import androidx.annotation.VisibleForTesting
|
||||
import androidx.room.Room
|
||||
import androidx.room.RoomDatabase.Callback
|
||||
import androidx.room.migration.Migration
|
||||
import androidx.sqlite.db.SupportSQLiteDatabase
|
||||
import dagger.Module
|
||||
import dagger.Provides
|
||||
import info.nightscout.database.entities.TABLE_HEART_RATE
|
||||
import javax.inject.Qualifier
|
||||
import javax.inject.Singleton
|
||||
|
||||
|
@ -22,13 +24,7 @@ open class DatabaseModule {
|
|||
internal fun provideAppDatabase(context: Context, @DbFileName fileName: String) =
|
||||
Room
|
||||
.databaseBuilder(context, AppDatabase::class.java, fileName)
|
||||
// .addMigrations(migration5to6)
|
||||
// .addMigrations(migration6to7)
|
||||
// .addMigrations(migration7to8)
|
||||
// .addMigrations(migration11to12)
|
||||
.addMigrations(migration20to21)
|
||||
.addMigrations(migration21to22)
|
||||
.addMigrations(migration22to23)
|
||||
.addMigrations(*migrations)
|
||||
.addCallback(object : Callback() {
|
||||
override fun onOpen(db: SupportSQLiteDatabase) {
|
||||
super.onOpen(db)
|
||||
|
@ -89,4 +85,36 @@ open class DatabaseModule {
|
|||
}
|
||||
}
|
||||
|
||||
}
|
||||
private val migration23to24 = object : Migration(23, 24) {
|
||||
override fun migrate(database: SupportSQLiteDatabase) {
|
||||
database.execSQL(
|
||||
"""CREATE TABLE IF NOT EXISTS `$TABLE_HEART_RATE` (
|
||||
`id` INTEGER PRIMARY KEY AUTOINCREMENT NOT NULL,
|
||||
`duration` INTEGER NOT NULL,
|
||||
`timestamp` INTEGER NOT NULL,
|
||||
`beatsPerMinute` REAL NOT NULL,
|
||||
`device` TEXT NOT NULL,
|
||||
`utcOffset` INTEGER NOT NULL,
|
||||
`version` INTEGER NOT NULL,
|
||||
`dateCreated` INTEGER NOT NULL,
|
||||
`isValid` INTEGER NOT NULL,
|
||||
`referenceId` INTEGER,
|
||||
`nightscoutSystemId` TEXT,
|
||||
`nightscoutId` TEXT,
|
||||
`pumpType` TEXT,
|
||||
`pumpSerial` TEXT,
|
||||
`temporaryId` INTEGER,
|
||||
`pumpId` INTEGER, `startId` INTEGER,
|
||||
`endId` INTEGER)""".trimIndent()
|
||||
)
|
||||
database.execSQL("""CREATE INDEX IF NOT EXISTS `index_heartRate_id` ON `$TABLE_HEART_RATE` (`id`)""")
|
||||
database.execSQL("""CREATE INDEX IF NOT EXISTS `index_heartRate_timestamp` ON `$TABLE_HEART_RATE` (`timestamp`)""")
|
||||
// Custom indexes must be dropped on migration to pass room schema checking after upgrade
|
||||
dropCustomIndexes(database)
|
||||
}
|
||||
}
|
||||
|
||||
/** List of all migrations for easy reply in tests. */
|
||||
@VisibleForTesting
|
||||
internal val migrations = arrayOf(migration20to21, migration21to22, migration22to23, migration23to24)
|
||||
}
|
||||
|
|
|
@ -41,6 +41,8 @@ import info.nightscout.database.impl.daos.delegated.DelegatedTotalDailyDoseDao
|
|||
import info.nightscout.database.impl.daos.delegated.DelegatedUserEntryDao
|
||||
import info.nightscout.database.impl.daos.delegated.DelegatedVersionChangeDao
|
||||
import info.nightscout.database.entities.interfaces.DBEntry
|
||||
import info.nightscout.database.impl.daos.HeartRateDao
|
||||
import info.nightscout.database.impl.daos.delegated.DelegatedHeartRateDao
|
||||
|
||||
internal class DelegatedAppDatabase(val changes: MutableList<DBEntry>, val database: AppDatabase) {
|
||||
|
||||
|
@ -64,5 +66,6 @@ internal class DelegatedAppDatabase(val changes: MutableList<DBEntry>, val datab
|
|||
val foodDao: FoodDao = DelegatedFoodDao(changes, database.foodDao)
|
||||
val deviceStatusDao: DeviceStatusDao = DelegatedDeviceStatusDao(changes, database.deviceStatusDao)
|
||||
val offlineEventDao: OfflineEventDao = DelegatedOfflineEventDao(changes, database.offlineEventDao)
|
||||
val heartRateDao: HeartRateDao = DelegatedHeartRateDao(changes, database.heartRateDao)
|
||||
fun clearAllTables() = database.clearAllTables()
|
||||
}
|
||||
}
|
||||
|
|
|
@ -0,0 +1,28 @@
|
|||
package info.nightscout.database.impl.daos
|
||||
|
||||
import androidx.room.Dao
|
||||
import androidx.room.Query
|
||||
import info.nightscout.database.entities.HeartRate
|
||||
import info.nightscout.database.entities.TABLE_HEART_RATE
|
||||
|
||||
@Dao
|
||||
internal interface HeartRateDao : TraceableDao<HeartRate> {
|
||||
|
||||
@Query("SELECT * FROM $TABLE_HEART_RATE WHERE id = :id")
|
||||
override fun findById(id: Long): HeartRate?
|
||||
|
||||
@Query("DELETE FROM $TABLE_HEART_RATE")
|
||||
override fun deleteAllEntries()
|
||||
|
||||
@Query("DELETE FROM $TABLE_HEART_RATE WHERE timestamp < :than")
|
||||
override fun deleteOlderThan(than: Long): Int
|
||||
|
||||
@Query("DELETE FROM $TABLE_HEART_RATE WHERE referenceId IS NOT NULL")
|
||||
override fun deleteTrackedChanges(): Int
|
||||
|
||||
@Query("SELECT * FROM $TABLE_HEART_RATE WHERE timestamp >= :timestamp ORDER BY timestamp")
|
||||
fun getFromTime(timestamp: Long): List<HeartRate>
|
||||
|
||||
@Query("SELECT * FROM $TABLE_HEART_RATE WHERE timestamp > :since AND timestamp <= :until LIMIT :limit OFFSET :offset")
|
||||
fun getNewEntriesSince(since: Long, until: Long, limit: Int, offset: Int): List<HeartRate>
|
||||
}
|
|
@ -0,0 +1,20 @@
|
|||
package info.nightscout.database.impl.daos.delegated
|
||||
|
||||
import info.nightscout.database.entities.HeartRate
|
||||
import info.nightscout.database.entities.interfaces.DBEntry
|
||||
import info.nightscout.database.impl.daos.HeartRateDao
|
||||
|
||||
internal class DelegatedHeartRateDao(
|
||||
changes: MutableList<DBEntry>,
|
||||
private val dao:HeartRateDao): DelegatedDao(changes), HeartRateDao by dao {
|
||||
|
||||
override fun insertNewEntry(entry: HeartRate): Long {
|
||||
changes.add(entry)
|
||||
return dao.insertNewEntry(entry)
|
||||
}
|
||||
|
||||
override fun updateExistingEntry(entry: HeartRate): Long {
|
||||
changes.add(entry)
|
||||
return dao.updateExistingEntry(entry)
|
||||
}
|
||||
}
|
|
@ -0,0 +1,20 @@
|
|||
package info.nightscout.database.impl.transactions
|
||||
|
||||
import info.nightscout.database.entities.HeartRate
|
||||
|
||||
class InsertOrUpdateHeartRateTransaction(private val heartRate: HeartRate):
|
||||
Transaction<InsertOrUpdateHeartRateTransaction.TransactionResult>() {
|
||||
|
||||
override fun run(): TransactionResult {
|
||||
val existing = if (heartRate.id == 0L) null else database.heartRateDao.findById(heartRate.id)
|
||||
return if (existing == null) {
|
||||
database.heartRateDao.insertNewEntry(heartRate).let {
|
||||
TransactionResult(listOf(heartRate), emptyList()) }
|
||||
} else {
|
||||
database.heartRateDao.updateExistingEntry(heartRate)
|
||||
TransactionResult(emptyList(), listOf(heartRate))
|
||||
}
|
||||
}
|
||||
|
||||
data class TransactionResult(val inserted: List<HeartRate>, val updated: List<HeartRate>)
|
||||
}
|
|
@ -24,3 +24,11 @@ android.useAndroidX=true
|
|||
android.nonTransitiveRClass=true
|
||||
# Cache is causeing issues with CircleCI nad maybe Studio 2021
|
||||
# org.gradle.unsafe.configuration-cache=true
|
||||
|
||||
# After migration to kotlin 1.8.21
|
||||
#e: org.jetbrains.kotlin.backend.common.BackendException: Backend Internal error: Exception during psi2ir
|
||||
# File being compiled: (37,18) in /home/circleci/project/core/interfaces/src/main/java/info/nightscout/interfaces/pump/defs/PumpCapability.kt
|
||||
# The root cause org.jetbrains.kotlin.psi2ir.generators.ErrorExpressionException was thrown at: org.jetbrains.kotlin.psi2ir.generators.ErrorExpressionGenerator.generateErrorCall(ErrorExpressionGenerator.kt:100)
|
||||
# null: KtCallExpression
|
||||
# https://youtrack.jetbrains.com/issue/KT-58027
|
||||
kapt.use.jvm.ir=false
|
||||
|
|
|
@ -71,7 +71,7 @@ class ProfileFunctionImpl @Inject constructor(
|
|||
override fun getProfileNameWithRemainingTime(): String =
|
||||
getProfileName(System.currentTimeMillis(), customized = true, showRemainingTime = true)
|
||||
|
||||
fun getProfileName(time: Long, customized: Boolean, showRemainingTime: Boolean): String {
|
||||
private fun getProfileName(time: Long, customized: Boolean, showRemainingTime: Boolean): String {
|
||||
var profileName = rh.gs(info.nightscout.core.ui.R.string.no_profile_set)
|
||||
|
||||
val profileSwitch = repository.getEffectiveProfileSwitchActiveAt(time).blockingGet()
|
||||
|
|
|
@ -113,12 +113,13 @@ class CommandQueueImplementation @Inject constructor(
|
|||
return@subscribe
|
||||
}
|
||||
aapsLogger.debug(LTag.PROFILE, "onEventProfileSwitchChanged")
|
||||
val effective = repository.getEffectiveProfileSwitchActiveAt(dateUtil.now()).blockingGet()
|
||||
profileFunction.getRequestedProfile()?.let {
|
||||
setProfile(ProfileSealed.PS(it), it.interfaceIDs.nightscoutId != null, object : Callback() {
|
||||
override fun run() {
|
||||
if (!result.success) {
|
||||
uiInteraction.runAlarm(result.comment, rh.gs(info.nightscout.core.ui.R.string.failed_update_basal_profile), info.nightscout.core.ui.R.raw.boluserror)
|
||||
} else if (result.enacted) {
|
||||
} else if (result.enacted || effective is ValueWrapper.Existing && effective.value.originalEnd < dateUtil.now() && effective.value.originalDuration != 0L) {
|
||||
val nonCustomized = ProfileSealed.PS(it).convertToNonCustomizedProfile(dateUtil)
|
||||
EffectiveProfileSwitch(
|
||||
timestamp = dateUtil.now(),
|
||||
|
@ -421,7 +422,7 @@ class CommandQueueImplementation @Inject constructor(
|
|||
}
|
||||
|
||||
// returns true if command is queued
|
||||
override fun setProfile(profile: Profile, hasNsId: Boolean, callback: Callback?): Boolean {
|
||||
fun setProfile(profile: ProfileSealed, hasNsId: Boolean, callback: Callback?): Boolean {
|
||||
if (isRunning(CommandType.BASAL_PROFILE)) {
|
||||
aapsLogger.debug(LTag.PUMPQUEUE, "Command is already executed")
|
||||
callback?.result(PumpEnactResult(injector).success(true).enacted(false))?.run()
|
||||
|
|
|
@ -3,7 +3,7 @@
|
|||
<string name="alert_r7_description"><![CDATA[Kiekis: <b>%1$d%%</b>\nTrukmė: <b>%2$s h</b>]]></string>
|
||||
<string name="alert_w31_description"><![CDATA[Rezervuaro tūris: <b>%1$s U</b>]]></string>
|
||||
<string name="alert_w32_description">Pakeiskite bateriją.</string>
|
||||
<string name="alert_w33_description">Nustatykite laiką/datą.</string>
|
||||
<string name="alert_w33_description">Nustatyti laiką/datą.</string>
|
||||
<string name="alert_w34_description">Kreipkitės į Accu-Chek palaikymo tarnybą.</string>
|
||||
<string name="alert_w36_description"><![CDATA[Kiekis: <b>%1$d%%</b><br/>Trukmė: <b>%2$s h</b>]]></string>
|
||||
<string name="alert_w38_description"><![CDATA[Suprogramuota: <b>%1$s U</b><br/>Suleista: <b>%2$s U</b>]]></string>
|
||||
|
@ -16,8 +16,8 @@
|
|||
<string name="alert_m26_description">Pakeiskite rezervuarą.</string>
|
||||
<string name="alert_m27_description">Iš naujo paleiskite duomenų atsisiuntimą.</string>
|
||||
<string name="alert_m28_description">Patikrinkite pompos statusą.</string>
|
||||
<string name="alert_m29_description">Nustatykite baterijos tipą.</string>
|
||||
<string name="alert_m30_description">Nustatykite rezervuaro tipą.</string>
|
||||
<string name="alert_m29_description">Nustatyti baterijos tipą.</string>
|
||||
<string name="alert_m30_description">Nustatyti rezervuaro tipą.</string>
|
||||
<string name="alert_e6_description">Pakeiskite bateriją ir rezervuarą.</string>
|
||||
<string name="alert_e10_description">Pakeiskite rezervuarą.</string>
|
||||
<string name="alert_e13_description">Pakeiskite kalbą.</string>
|
||||
|
|
|
@ -10,6 +10,7 @@ import android.view.MenuInflater
|
|||
import android.view.MenuItem
|
||||
import android.view.View
|
||||
import android.view.ViewGroup
|
||||
import androidx.core.view.MenuCompat
|
||||
import androidx.core.view.MenuProvider
|
||||
import androidx.lifecycle.Lifecycle
|
||||
import dagger.android.support.DaggerFragment
|
||||
|
@ -72,7 +73,7 @@ class OpenAPSFragment : DaggerFragment(), MenuProvider {
|
|||
|
||||
override fun onCreateMenu(menu: Menu, inflater: MenuInflater) {
|
||||
menu.add(Menu.FIRST, ID_MENU_RUN, 0, rh.gs(R.string.openapsma_run)).setShowAsAction(MenuItem.SHOW_AS_ACTION_NEVER)
|
||||
menu.setGroupDividerEnabled(true)
|
||||
MenuCompat.setGroupDividerEnabled(menu, true)
|
||||
}
|
||||
|
||||
override fun onMenuItemSelected(item: MenuItem): Boolean =
|
||||
|
|
|
@ -9,6 +9,7 @@ import android.view.MenuInflater
|
|||
import android.view.MenuItem
|
||||
import android.view.View
|
||||
import android.view.ViewGroup
|
||||
import androidx.core.view.MenuCompat
|
||||
import androidx.core.view.MenuProvider
|
||||
import androidx.lifecycle.Lifecycle
|
||||
import dagger.android.support.DaggerFragment
|
||||
|
@ -74,7 +75,7 @@ class LoopFragment : DaggerFragment(), MenuProvider {
|
|||
|
||||
override fun onCreateMenu(menu: Menu, inflater: MenuInflater) {
|
||||
menu.add(Menu.FIRST, ID_MENU_RUN, 0, rh.gs(R.string.run_now)).setShowAsAction(MenuItem.SHOW_AS_ACTION_NEVER)
|
||||
menu.setGroupDividerEnabled(true)
|
||||
MenuCompat.setGroupDividerEnabled(menu, true)
|
||||
}
|
||||
|
||||
override fun onMenuItemSelected(item: MenuItem): Boolean =
|
||||
|
@ -169,4 +170,4 @@ class LoopFragment : DaggerFragment(), MenuProvider {
|
|||
binding.smbsetbypump.text = ""
|
||||
binding.swipeRefresh.isRefreshing = false
|
||||
}
|
||||
}
|
||||
}
|
|
@ -16,6 +16,7 @@ import android.widget.ImageView
|
|||
import android.widget.LinearLayout
|
||||
import androidx.annotation.DrawableRes
|
||||
import androidx.core.util.forEach
|
||||
import androidx.core.view.MenuCompat
|
||||
import androidx.core.view.MenuProvider
|
||||
import androidx.lifecycle.Lifecycle
|
||||
import androidx.recyclerview.widget.ItemTouchHelper
|
||||
|
@ -97,7 +98,7 @@ class AutomationFragment : DaggerFragment(), OnStartDragListener, MenuProvider {
|
|||
actionHelper.onCreateOptionsMenu(menu, inflater)
|
||||
menu.add(Menu.FIRST, ID_MENU_ADD, 0, rh.gs(R.string.add_automation)).setShowAsAction(MenuItem.SHOW_AS_ACTION_NEVER)
|
||||
menu.add(Menu.FIRST, ID_MENU_RUN, 0, rh.gs(R.string.run_automations)).setShowAsAction(MenuItem.SHOW_AS_ACTION_NEVER)
|
||||
menu.setGroupDividerEnabled(true)
|
||||
MenuCompat.setGroupDividerEnabled(menu, true)
|
||||
}
|
||||
|
||||
override fun onMenuItemSelected(item: MenuItem): Boolean =
|
||||
|
@ -309,4 +310,4 @@ class AutomationFragment : DaggerFragment(), OnStartDragListener, MenuProvider {
|
|||
}
|
||||
}.show(childFragmentManager, "EditEventDialog")
|
||||
}
|
||||
}
|
||||
}
|
|
@ -27,13 +27,13 @@
|
|||
<string name="sendsmsactionlabel">Siųsti SMS: %1$s</string>
|
||||
<string name="sendsmsactiondescription">Siųsti SMS į visus numerius</string>
|
||||
<string name="sendsmsactiontext">Išsiųsti SMS žinutę su tekstu</string>
|
||||
<string name="starttemptarget">Nustatykite laikiną tikslą</string>
|
||||
<string name="islesser">mažesnis nei</string>
|
||||
<string name="isequalorlesser">lygus arba mažesnis nei</string>
|
||||
<string name="isequal">yra lygus</string>
|
||||
<string name="isequalorgreater">yra lygus arba didesnis nei</string>
|
||||
<string name="isgreater">didesnis nei</string>
|
||||
<string name="isnotavailable">negalimas</string>
|
||||
<string name="starttemptarget">Pradėti laikiną tikslą</string>
|
||||
<string name="islesser">mažiau nei</string>
|
||||
<string name="isequalorlesser">lygu arba mažiau nei</string>
|
||||
<string name="isequal">lygu</string>
|
||||
<string name="isequalorgreater">lygu arba daugiau nei</string>
|
||||
<string name="isgreater">daugiau nei</string>
|
||||
<string name="isnotavailable">nėra duomenų</string>
|
||||
<string name="glucoseisnotavailable">Glikemija nepasiekiama</string>
|
||||
<string name="glucosecomparedmgdl">Glikemija %1$s %2$.0f %3$s</string>
|
||||
<string name="glucosecomparedmmol">Glikemija %1$s %2$.1f %3$s</string>
|
||||
|
|
|
@ -22,16 +22,16 @@ class TriggerWifiSsidTest : TriggerTestBase() {
|
|||
@Test fun shouldRunTest() {
|
||||
val e = EventNetworkChange()
|
||||
`when`(receiverStatusStore.lastNetworkEvent).thenReturn(e)
|
||||
var t: TriggerWifiSsid = TriggerWifiSsid(injector).setValue("aSSID").comparator(Comparator.Compare.IS_EQUAL)
|
||||
var t: TriggerWifiSsid = TriggerWifiSsid(injector).setValue("aSSID 1").comparator(Comparator.Compare.IS_EQUAL)
|
||||
e.wifiConnected = false
|
||||
Assert.assertFalse(t.shouldRun())
|
||||
e.wifiConnected = true
|
||||
e.ssid = "otherSSID"
|
||||
Assert.assertFalse(t.shouldRun())
|
||||
e.wifiConnected = true
|
||||
e.ssid = "aSSID"
|
||||
e.ssid = "aSSID 1"
|
||||
Assert.assertTrue(t.shouldRun())
|
||||
t = TriggerWifiSsid(injector).setValue("aSSID").comparator(Comparator.Compare.IS_NOT_AVAILABLE)
|
||||
t = TriggerWifiSsid(injector).setValue("aSSID 1").comparator(Comparator.Compare.IS_NOT_AVAILABLE)
|
||||
e.wifiConnected = false
|
||||
Assert.assertTrue(t.shouldRun())
|
||||
|
||||
|
|
|
@ -1,12 +1,10 @@
|
|||
package info.nightscout.configuration.activities
|
||||
|
||||
import android.content.Context
|
||||
import android.content.Intent
|
||||
import android.os.Bundle
|
||||
import android.view.Menu
|
||||
import android.view.MenuItem
|
||||
import info.nightscout.configuration.R
|
||||
import info.nightscout.core.ui.locale.LocaleHelper
|
||||
import info.nightscout.interfaces.plugin.ActivePlugin
|
||||
import info.nightscout.interfaces.plugin.PluginBase
|
||||
import info.nightscout.interfaces.protection.ProtectionCheck
|
||||
|
@ -60,8 +58,4 @@ class SingleFragmentActivity : DaggerAppCompatActivityWithResult() {
|
|||
if (plugin?.preferencesId != -1) menuInflater.inflate(R.menu.menu_single_fragment, menu)
|
||||
return super.onCreateOptionsMenu(menu)
|
||||
}
|
||||
|
||||
override fun attachBaseContext(newBase: Context) {
|
||||
super.attachBaseContext(LocaleHelper.wrap(newBase))
|
||||
}
|
||||
}
|
|
@ -5,14 +5,14 @@ import android.view.View
|
|||
import android.widget.CheckBox
|
||||
import android.widget.LinearLayout
|
||||
import android.widget.TextView
|
||||
import dagger.android.support.DaggerAppCompatActivity
|
||||
import info.nightscout.configuration.R
|
||||
import info.nightscout.configuration.databinding.ActivityLogsettingBinding
|
||||
import info.nightscout.core.ui.activities.TranslatedDaggerAppCompatActivity
|
||||
import info.nightscout.rx.interfaces.L
|
||||
import info.nightscout.rx.interfaces.LogElement
|
||||
import javax.inject.Inject
|
||||
|
||||
class LogSettingActivity : DaggerAppCompatActivity() {
|
||||
class LogSettingActivity : TranslatedDaggerAppCompatActivity() {
|
||||
|
||||
@Inject lateinit var l: L
|
||||
|
||||
|
|
|
@ -1,6 +1,5 @@
|
|||
package info.nightscout.configuration.maintenance.activities
|
||||
|
||||
import android.content.Context
|
||||
import android.content.Intent
|
||||
import android.os.Bundle
|
||||
import android.view.LayoutInflater
|
||||
|
@ -10,12 +9,11 @@ import android.view.ViewGroup
|
|||
import androidx.fragment.app.FragmentActivity
|
||||
import androidx.recyclerview.widget.LinearLayoutManager
|
||||
import androidx.recyclerview.widget.RecyclerView
|
||||
import dagger.android.support.DaggerAppCompatActivity
|
||||
import info.nightscout.configuration.R
|
||||
import info.nightscout.configuration.databinding.MaintenanceImportListActivityBinding
|
||||
import info.nightscout.configuration.databinding.MaintenanceImportListItemBinding
|
||||
import info.nightscout.configuration.maintenance.PrefsFileContract
|
||||
import info.nightscout.core.ui.locale.LocaleHelper
|
||||
import info.nightscout.core.ui.activities.TranslatedDaggerAppCompatActivity
|
||||
import info.nightscout.interfaces.maintenance.PrefFileListProvider
|
||||
import info.nightscout.interfaces.maintenance.PrefsFile
|
||||
import info.nightscout.interfaces.maintenance.PrefsMetadataKey
|
||||
|
@ -23,7 +21,7 @@ import info.nightscout.interfaces.maintenance.PrefsStatus
|
|||
import info.nightscout.shared.interfaces.ResourceHelper
|
||||
import javax.inject.Inject
|
||||
|
||||
class PrefImportListActivity : DaggerAppCompatActivity() {
|
||||
class PrefImportListActivity : TranslatedDaggerAppCompatActivity() {
|
||||
|
||||
@Inject lateinit var rh: ResourceHelper
|
||||
@Inject lateinit var prefFileListProvider: PrefFileListProvider
|
||||
|
@ -116,8 +114,4 @@ class PrefImportListActivity : DaggerAppCompatActivity() {
|
|||
}
|
||||
return super.onOptionsItemSelected(item)
|
||||
}
|
||||
|
||||
override fun attachBaseContext(newBase: Context) {
|
||||
super.attachBaseContext(LocaleHelper.wrap(newBase))
|
||||
}
|
||||
}
|
|
@ -9,6 +9,7 @@ import android.widget.TextView
|
|||
import dagger.android.HasAndroidInjector
|
||||
import info.nightscout.configuration.setupwizard.SWNumberValidator
|
||||
import info.nightscout.core.ui.elements.NumberPicker
|
||||
import info.nightscout.interfaces.Constants
|
||||
import info.nightscout.interfaces.GlucoseUnit
|
||||
import info.nightscout.interfaces.profile.Profile
|
||||
import info.nightscout.interfaces.profile.ProfileFunction
|
||||
|
@ -16,12 +17,15 @@ import info.nightscout.shared.SafeParse
|
|||
import java.text.DecimalFormat
|
||||
import javax.inject.Inject
|
||||
|
||||
class SWEditNumberWithUnits(injector: HasAndroidInjector, private val init: Double, private val min: Double, private val max: Double) : SWItem(injector, Type.UNIT_NUMBER) {
|
||||
class SWEditNumberWithUnits(injector: HasAndroidInjector, private val init: Double, private val minMmol: Double, private val maxMmol: Double) : SWItem(injector, Type.UNIT_NUMBER) {
|
||||
|
||||
@Inject lateinit var profileFunction: ProfileFunction
|
||||
|
||||
private val validator: SWNumberValidator =
|
||||
SWNumberValidator { value -> value in min..max }
|
||||
if (profileFunction.getUnits() == GlucoseUnit.MMOL)
|
||||
SWNumberValidator { value -> value in minMmol..maxMmol }
|
||||
else
|
||||
SWNumberValidator { value -> value in minMmol * Constants.MMOLL_TO_MGDL..maxMmol * Constants.MMOLL_TO_MGDL }
|
||||
private var updateDelay = 0
|
||||
|
||||
override fun generateDialog(layout: LinearLayout) {
|
||||
|
@ -44,7 +48,10 @@ class SWEditNumberWithUnits(injector: HasAndroidInjector, private val init: Doub
|
|||
var initValue = sp.getDouble(preferenceId, init)
|
||||
initValue = Profile.toCurrentUnits(profileFunction.getUnits(), initValue)
|
||||
val numberPicker = NumberPicker(context)
|
||||
if (profileFunction.getUnits() == GlucoseUnit.MMOL) numberPicker.setParams(initValue, min, max, 0.1, DecimalFormat("0.0"), false, null, watcher) else numberPicker.setParams(initValue, min * 18, max * 18, 1.0, DecimalFormat("0"), false, null, watcher)
|
||||
if (profileFunction.getUnits() == GlucoseUnit.MMOL)
|
||||
numberPicker.setParams(initValue, minMmol, maxMmol, 0.1, DecimalFormat("0.0"), false, null, watcher)
|
||||
else
|
||||
numberPicker.setParams(initValue, minMmol * Constants.MMOLL_TO_MGDL, maxMmol * Constants.MMOLL_TO_MGDL, 1.0, DecimalFormat("0"), false, null, watcher)
|
||||
|
||||
layout.addView(numberPicker)
|
||||
val c = TextView(context)
|
||||
|
|
|
@ -3,7 +3,7 @@
|
|||
android:layout_width="match_parent"
|
||||
android:layout_height="match_parent"
|
||||
android:orientation="vertical"
|
||||
tools:context=".constraints.objectives.ObjectivesFragment">
|
||||
tools:context="info.nightscout.plugins.constraints.objectives.ObjectivesFragment">
|
||||
|
||||
<LinearLayout
|
||||
android:layout_width="match_parent"
|
||||
|
|
|
@ -18,7 +18,6 @@
|
|||
<string name="objectives_autosens_objective">Pas basale en verhoudings aan as nodig, en dan aktiveer auto-sens</string>
|
||||
<string name="objectives_autosens_gate">1 week suksesvolle dagtyd lus met gereelde karb toevoegings</string>
|
||||
<string name="objectives_smb_objective">Skakel bykomende nutsfunskies aan vir bedags gebruik, soos bv. SMB</string>
|
||||
<string name="objectives_smb_gate">Jy moet asb die wiki lees en verhoog maksIAB om SMBs te laat werk! \'n Goeie begin is maksIAB = gemiddelde ete bolus + 3 x maks daaglikse basale</string>
|
||||
<string name="objectives_manualenacts">Per hand aksies</string>
|
||||
<string name="accomplished">Bereik: %1$s</string>
|
||||
<string name="objectives_useprofileswitch">Stel profiel 90% vir 10 min (Lang-pers profiel naam op Oorsig)</string>
|
||||
|
|
|
@ -24,7 +24,6 @@
|
|||
<string name="objectives_autosens_gate">Една седмица успешно дневно използване с редовно въвеждане на въглехидрати</string>
|
||||
<string name="objectives_autosens_learned">Ако вашият резултат от autosens не се колебае около 100%, вашият профил вероятно е грешен.</string>
|
||||
<string name="objectives_smb_objective">Добавяне на допълнителни функции за използване през деня, като SMB</string>
|
||||
<string name="objectives_smb_gate">Трябва да прочетете wiki и увеличите maxIOB за да може SMB да работи добре! Добро начало е maxIOB = средния болус за хранене + 3 пъти най-големия базал от профила</string>
|
||||
<string name="objectives_smb_learned">Използването на SMB трябва да е вашата основна цел. Алгоритъмът Oref1 е създаден, за да ви помогне и с вашите болуси. Не трябва да давате пълен болус за вашата храна, а само част от него и оставете AAPS да ви даде останалото, ако е необходимо. По този начин имате по-голям диапазон за грешно изчислени въглехидрати. Знаете ли, че можете да зададете процент от резултата от болус калкулатора, за да намалите размера на болуса?</string>
|
||||
<string name="objectives_auto_objective">Разрешаване на автоматизация</string>
|
||||
<string name="objectives_auto_gate">Прочетете документацията за това как работи автоматизацията. Настройте първите си прости правила. Нека AAPS показва само известия. Когато сте сигурни, автоматизацията се задейства в точното време, за да заменете известяването с реални действия. (https: //androidaps.readthedocs.io/en/latest/EN/Usage/Automation.html)</string>
|
||||
|
|
|
@ -18,7 +18,6 @@
|
|||
<string name="objectives_autosens_objective">Ajustar basals i ràtios si cal, i després activar auto-sens</string>
|
||||
<string name="objectives_autosens_gate">1 setmana d\'èxit en mode llaç tancat durant el dia, amb introducció regular de carbohidrats</string>
|
||||
<string name="objectives_smb_objective">Activant funcions addicionals d\'ús diurn, com l\'SMB (super micro bolus)</string>
|
||||
<string name="objectives_smb_gate">Heu de llegir la wiki i augmentar la maxIOB per a què l\'SMB funcioni correctament! Una bona manera de començar és amb maxIOB = bolus d\'àpat mig + 3 x màxima basal diària</string>
|
||||
<string name="objectives_auto_objective">Activant l\'automatització</string>
|
||||
<string name="objectives_manualenacts">Activació manual</string>
|
||||
<string name="accomplished">Completat: %1$s</string>
|
||||
|
|
|
@ -24,7 +24,7 @@
|
|||
<string name="objectives_autosens_gate">Jeden týden úspěšného používání s běžným příjmem sacharidů</string>
|
||||
<string name="objectives_autosens_learned">Pokud váš výsledek autosens neosciluje kolem 100%, nastavení Vašeho profilu pravděpodobně špatné.</string>
|
||||
<string name="objectives_smb_objective">Povolit další funkce pro běžné používání jako SMB</string>
|
||||
<string name="objectives_smb_gate">Přečíst si dokumentaci a zvýšit maximální IOB, aby mohlo SMB fungovat. Pro začátek se dá použít velikost běžného bolusu + 3x maximální denní bazál</string>
|
||||
<string name="objectives_smb_gate">Přečíst si dokumentaci a zvýšit maximání IOB, aby mohlo SMB fungovat. Pro začátek se dá použít velikost běžného bolusu + 3x maximální denní bazál</string>
|
||||
<string name="objectives_smb_learned">Použití SMB je vaším cílem. Oref1 algoritmus byl navržen tak, aby vám pomohl i s vašimi bolusy. Neměli byste dávat úplný bolus pro vaše jídlo, ale jen jeho část a nechtat AAPS v případě potřeby dát zbytek. Takto máte větší rezervu pro špatně vypočtené sacharidy. Věděli jste, že můžete nastavit procento bolusové kalkulačky pro snížení velikosti bolusu?</string>
|
||||
<string name="objectives_auto_objective">Povolení automatizace</string>
|
||||
<string name="objectives_auto_gate">Přečtěte si na wiki, jak automatizace funguje. Nejdříve nastavte pouze jednoduchá pravidla. Namísto provádění akcí nechte AAPS zobrazovat pouze oznámení. Pokud jste si jistí, že je automatizace spouštěna v pravý čas, můžete oznámení nahradit prováděním akce. (https://wiki.aaps.app/cs/latest/Usage/Automation.html)</string>
|
||||
|
|
|
@ -18,7 +18,6 @@
|
|||
<string name="objectives_autosens_objective">Justér om nødvendigt basaler og forhold og aktivér derefter auto-sens</string>
|
||||
<string name="objectives_autosens_gate">1 uges vellykket looping i dagtimerne med alle måltider tastet ind</string>
|
||||
<string name="objectives_smb_objective">Aktivering af yderligere funktioner til brug i dagtimerne, såsom SMB</string>
|
||||
<string name="objectives_smb_gate">Du skal læse wikien og hæve maxIOB for at få SMB\'er til at fungere fint! En god start er maxIOB=gennemsnitlig måltidsbolus + 3 x max daglig basal</string>
|
||||
<string name="objectives_auto_objective">Aktiverer automatisering</string>
|
||||
<string name="objectives_manualenacts">Manuelle handlinger</string>
|
||||
<string name="accomplished">Udført: %1$s</string>
|
||||
|
|
|
@ -24,8 +24,6 @@
|
|||
<string name="objectives_autosens_gate">Loope eine Woche tagsüber mit regelmäßiger Kohlenhydrat-Eingabe</string>
|
||||
<string name="objectives_autosens_learned">Wenn Ihr Autosens Ergebnis nicht stündlich schwankt, um die angestrebten 100 % ist das verwendete Profil wahrscheinlich falsch.</string>
|
||||
<string name="objectives_smb_objective">Aktiviere zusätzliche Funktionen für die Nutzung tagsüber wie z. B. SMB</string>
|
||||
<string name="objectives_smb_gate">Lies das Wiki und erhöhe maxIOB, damit der SMB gut funktioniert. Ein guter Anfang ist
|
||||
die Formel maxIOB = durchschnittlicher Essensbolus + 3 x höchste Basalrate</string>
|
||||
<string name="objectives_smb_learned">Die Verwendung von SMB ist Dein Ziel. Der Oref1-Algorithmus wurde entwickelt, um Dir auch mit Boli zu helfen. Du solltest nicht den vollen Bolus für Dein Essen geben, sondern nur einen Teil davon abgeben und es AAPS überlassen bei Bedarf den notwendigen Rest entsprechend dem Blutzuckerverlauf zugeben zu lassen. Auf diese Weise hast Du mehr Platz für falsch berechnete Kohlenhydrate. Wusstest Du, dass Du einen Prozentsatz bei Verwendung des Bolusrechners festlegen kannst, um die Größe des Bolus zu reduzieren?</string>
|
||||
<string name="objectives_auto_objective">Automatisierung aktivieren</string>
|
||||
<string name="objectives_auto_gate">Lies in der Dokumentation nach, wie die Automation funktioniert. Richte Dir erst einfache Regeln ein. Zunächst sollte AAPS keine Änderungen vornehmen, sondern Dir nur eine Benachrichtigung anzeigen. Wenn Du Dir sicher bist, dass die Automation im richtigen Moment angetriggert wird, dann kannst Du die Benachrichtigung durch eine Aktion ersetzen (https://androidaps.readthedocs.io/de/latest/CROWDIN/de/Usage/Automation.html)</string>
|
||||
|
|
|
@ -18,7 +18,6 @@
|
|||
<string name="objectives_autosens_objective">Ρυθμίστε τον βασικό ρυθμό και τις αναλογίες αν χρειάζεται, και μετά ενεργοποιήστε το auto-sens</string>
|
||||
<string name="objectives_autosens_gate">1 επιτυχής εβδομάδα ημερήσιου κυκλώματος με κανονική εισαγωγή υδατανθράκων</string>
|
||||
<string name="objectives_smb_objective">Ενεργοποιώντας επιπρόσθετα χαρακτηριστικά για χρήση κατά την ημέρα, όπως το SMB</string>
|
||||
<string name="objectives_smb_gate">Πρέπει να διαβάσετε τον οδηγό wiki και να αυξήσετε το ανώτατο όριο του IOB για να μπορέσει να λειτουργήσει σωστά το SMB! Μια καλή αρχή είναι μέγιστο IOB= μέσο bolus γεύματος + 3 x το μέγιστο ημερήσιο βασικού ρυθμού</string>
|
||||
<string name="objectives_manualenacts">Ξεκινήστε χειροκίνητα</string>
|
||||
<string name="accomplished">Επιτεύχθηκε: %1$s</string>
|
||||
<string name="objectives_useprofileswitch">Θέστε το προφίλ στο 90% για 10 λεπτά (Παρατεταμένο πάτημα του προφίλ στην Επισκόπηση)</string>
|
||||
|
|
|
@ -24,7 +24,7 @@
|
|||
<string name="objectives_autosens_gate">Una semana con éxito en bucle cerrado durante el día con entrada regular de carbohidratos</string>
|
||||
<string name="objectives_autosens_learned">Si el resultado de tu autosens no oscila en torno al 100% es probable que tu perfil esté equivocado.</string>
|
||||
<string name="objectives_smb_objective">Habilitar funciones adicionales para uso durante el día como SMB</string>
|
||||
<string name="objectives_smb_gate">¡Debes leer el wiki y subir maxIOB para que SMB funcione bien! Para comenzar un buen valor sería maxIOB = bolo de comida medio + 3 x máximo basal diario</string>
|
||||
<string name="objectives_smb_gate">Debes leer la wiki y aumentar el valor de maxIOB para que SMB funcione bien. Un buen comienzo sería maxIOB = bolo de comida promedio + 3x máxima basal diaria</string>
|
||||
<string name="objectives_smb_learned">Utilizar SMB es su objetivo. El algoritmo Oref1 fue diseñado para ayudarle también con sus bolos. No debe dar un bolo completo para su comida, sino sólo una parte y dejar que AAPS le dé el resto si es necesario. De esta forma tendrás más espacio para los carbohidratos mal calculados. ¿Sabías que puedes establecer un porcentaje del resultado de la calculadora de bolo para reducir el tamaño del bolo?</string>
|
||||
<string name="objectives_auto_objective">Activar automatización</string>
|
||||
<string name="objectives_auto_gate">Lee la documentación sobre el funcionamiento de la automatización. Configure sus primeras reglas simples. En lugar de una acción, deja que AAPS muestre sólo una notificación. Cuando esté seguro de que la automatización se activa en el momento adecuado, sustituya la notificación por una acción real. (https://wiki.aaps.app/en/latest/Usage/Automation.html)</string>
|
||||
|
|
|
@ -24,7 +24,6 @@
|
|||
<string name="objectives_autosens_gate">1 semaine de Boucle Fermée en journée en saisissant régulièrement les glucides</string>
|
||||
<string name="objectives_autosens_learned">Si le résultat de votre autosens n\'est pas autour de 100%, votre profil est probablement erroné.</string>
|
||||
<string name="objectives_smb_objective">Activation de fonctionnalités supplémentaires pour l\'utilisation en journée, telles que la fonction SMB</string>
|
||||
<string name="objectives_smb_gate">Lisez le wiki et augmentez le maxIA pour que les SMBs fonctionnent correctement ! Un bon début est maxIA = moyenne des Bolus Repas + 3 x maximum débit Basal quotidien</string>
|
||||
<string name="objectives_smb_learned">L\'utilisation de SMB est votre objectif. L\'algorithme Oref1 a été conçu pour vous aider également avec vos bolus. Vous ne devriez pas donner un bolus complet pour votre nourriture, mais seulement une partie de celui-ci et laisser AAPS vous donner le reste si nécessaire. De cette façon, vous avez plus de latitude pour les glucides mal calculés. Saviez-vous que vous pouvez définir un pourcentage à appliquer au résultat de la calculatrice de bolus pour réduire la taille du bolus ?</string>
|
||||
<string name="objectives_auto_objective">Activation de l\'automatisation</string>
|
||||
<string name="objectives_auto_gate">Lisez la documentation sur le fonctionnement de l\'automatisation fonctionne. Configurez vos premières règles simples. Au lieu de mettre une action, configurez une notification. Quand vous êtes sûr que l\'automatisation est déclenchée au bon moment, remplacez la notification par une action réelle. (https://wiki.aaps.app/fr/latest/Usage/Automation.html)</string>
|
||||
|
|
|
@ -24,7 +24,7 @@
|
|||
<string name="objectives_autosens_gate">שבוע של הפעלה מוצלחת של הלולאה במשך שעות היום, עם רישום ערכי פחמימות בקביעות</string>
|
||||
<string name="objectives_autosens_learned">אם תוצאת הזיהוי האוטומטי שלכם לא מתנודדת סביב 100%, כנראה שהפרופיל טעון שיפור.</string>
|
||||
<string name="objectives_smb_objective">הפעלת פונקציות נוספות לשימוש במשך היום, כגון סופר מיקרו בולוסים (SMB)</string>
|
||||
<string name="objectives_smb_gate">חובה לקרוא את הויקי ולהעלות את ערך ה-maxIOB כדי להפעיל את ה- SMB כראוי. התחלה טובה תהיה maxIOB=בולוס ממוצע + 3 פעמים ערך הבזאלי היומי המקסימלי</string>
|
||||
<string name="objectives_smb_gate">חובה לקרוא את הויקי ולהעלות את ערך האינסולין הפעיל המרבי (maxIOB) כדי להפעיל את ה- SMB כראוי. התחלה טובה תהיה maxIOB=בולוס ארוחה טיפוסי + 3 פעמים ערך הבזאלי המקסימלי ביממה</string>
|
||||
<string name="objectives_smb_learned">שימוש ב-SMB הוא המטרה שלכם. אלגוריתם Oref1 תוכנן לעזור גם עם הבולוסים שלכם. אתם לא צריכים להזריק בולוס מלא למזון שלכם אלא רק על חלק ממנו ולתת ל-AAPS לטפל בשאר במידת הצורך. כך קל יותר להכיל טעויות בספירת פחמימות. הידעתם שאפשר להגדיר אחוז מתוצאת מחשבון הבולוס כדי להקטין את גודל הבולוס?</string>
|
||||
<string name="objectives_auto_objective">הפעלת אוטומציה</string>
|
||||
<string name="objectives_auto_gate">קראו את המסמכים על אופן הפעולה של אוטומציות. הגדירו את התנאים הפשוטים הראשונים שלכם. במקום פעולה תנו ל-AAPS להציג הודעה בלבד. כאשר אתם בטוחים שהאוטומציה מופעלת בזמן הנכון, החליפו את ההודעה בפעולה אמיתית. (https://wiki.aaps.app/he/latest/Usage/Automation.html)</string>
|
||||
|
|
|
@ -18,7 +18,6 @@
|
|||
<string name="objectives_autosens_objective">필요하면 Basal과 비율을 조절하고, auto-sens를 활성화합니다</string>
|
||||
<string name="objectives_autosens_gate">섭취한 탄수화물양을 입력하고 1주일동안 낮시간대에 loop를 성공적으로 사용하여 봅니다</string>
|
||||
<string name="objectives_smb_objective">낮시간대에 SMB(Super Micro Bolus)같은 추가기능을 활성화해 사용해봅니다</string>
|
||||
<string name="objectives_smb_gate">SMB가 잘 작동하게 하기위해서 wiki를 반드시 읽은 다음 maxIOB 값을 올려보세요! maxIOB=평균 식사 Bolus + 3 x 최대하루 Basal이면 적당한 시작값입니다</string>
|
||||
<string name="objectives_auto_objective">자동화 사용</string>
|
||||
<string name="objectives_manualenacts">수동 주입</string>
|
||||
<string name="accomplished">완료: %1$s</string>
|
||||
|
|
|
@ -24,7 +24,6 @@
|
|||
<string name="objectives_autosens_gate">1 savaitę praleiskite sėkmingai naudodami uždarąjį ciklą dienos metu ir įvesdami visus valgomus angliavandenius</string>
|
||||
<string name="objectives_autosens_learned">Jei Jūsų autosens rezultatai nesvyruoja apie 100%, tikėtina, kad profilis turi klaidų.</string>
|
||||
<string name="objectives_smb_objective">Dienos metu aktyvuokite papildomas funkcijas, tokias kaip SMB (Super Mikro Bolusas)</string>
|
||||
<string name="objectives_smb_gate">Norėdami, kad SMB veiktų gerai, turite perskaityti dokumentaciją ir padidinti max AIO! Pradžiai patartina skaičiuoti taip: maxAIO=(didžiausia valandinė bazė x 3) + vidutinis bolusas</string>
|
||||
<string name="objectives_smb_learned">SMB yra Jūsų tikslas. Oref1 algoritmas sukurtas taip, kad taptų Jums pagalba su bolusavimu. Jūs galite nesileisti viso boluso maistui, susileiskite dalį, o AAPS padarys likusį darbą, jei reikės. Taip išvengsite klaidų dėl neteisingai apskaičiuotų AV. Ar žinote, kad galite skaičiuotuve nurodyti, kiek % apskaičiuoto boluso suleisti?</string>
|
||||
<string name="objectives_auto_objective">Automatizavimo įjungimas</string>
|
||||
<string name="objectives_auto_gate">Perskaitykite dokumentaciją apie automatizacijos veikimą. Nustatykite kelias paprastas taisykles. Nustatykite, kad AAPS tik parodytų pranešimą, o ne atliktų realų veiksmą. Kai įsitikinsite, kad automatizacija suveikia reikalingu metu, vietoj pranešimo įjunkite veiksmą. (https://wiki.aaps.app/en/latest/Usage/Automation.html)</string>
|
||||
|
@ -40,7 +39,7 @@
|
|||
<string name="objectives_usedisconnectpump">Imituokite maudynes duše. Atjunkite pompą 1 valandai (ilgai paspauskite Atviras Ciklas)</string>
|
||||
<string name="objectives_usereconnectpump">... ir iš naujo prisijunkite tuo pačiu būdu</string>
|
||||
<string name="objectives_usetemptarget">Nustatykite 10 min trukmės laikiną tikslą (ilgai spausti ant dabartinio tikslo)</string>
|
||||
<string name="objectives_useactions">Konfigūracijoje įjunkite Veiksmų įskiepį, nustatykite jį matomą ir jo turinio rodymą viršutiniame meniu</string>
|
||||
<string name="objectives_useactions">Konfigūracijoje įjunkite Veiksmų įskiepį, padarykite jį ir jo turinį matomą viršutiniame meniu</string>
|
||||
<string name="objectives_useloop">Parodyti Ciklo įskiepio turinį</string>
|
||||
<string name="objectives_usescale">Panaudokite vaizdo dydžio keitimo funkciją ilgai spaudžiant ant glikemijos kreivės</string>
|
||||
<string name="objectives_exam_objective">Patvirtinkite savo žinias</string>
|
||||
|
|
|
@ -24,7 +24,6 @@
|
|||
<string name="objectives_autosens_gate">Gedurende 1 week succesvol overdag loopen met regelmatige invoer van koolhydraten</string>
|
||||
<string name="objectives_autosens_learned">Als het resultaat van autosens zich niet rond de 100% beweegt dan is je profiel waarschijnlijk niet juist.</string>
|
||||
<string name="objectives_smb_objective">Activeren van extra functies overdag zoals SMB (super micro bolus)</string>
|
||||
<string name="objectives_smb_gate">Lees de wiki en verhoog maxIOB om SMB goed werkend te krijgen. Een goed begin is maxIOB=gemiddelde maaltijdbolus + 3 x max dagelijkse basaal</string>
|
||||
<string name="objectives_smb_learned">Het gebruik van SMB is het uiteindelijke doel. Het Oref1 algoritme is ontworpen om je ook te helpen met je bolussen. Je hoeft geen volledige bolus te geven voor jouw voeding, maar slechts een deel ervan en AAPS zal de rest geven als dat nodig is. Op deze manier heb je meer ruimte voor verkeerd berekende koolhydraten. Wist je dat je een percentage in de bolus calculator kan instellen om de hoeveelheid bolus te verminderen?</string>
|
||||
<string name="objectives_auto_objective">Automatisering inschakelen</string>
|
||||
<string name="objectives_auto_gate">Lees eerst de documentatie over hoe automatisering werkt. Maak daarna je eerste simpele regels, waarbij je in plaats van acties eerst gebruikt maakt van de notificaties. Wanneer je er dan zeker van bent, dat je automatisering op de goede momenten wordt geactiveerd, kan je de noticifcatie omzetten naar een echte actie.
|
||||
|
|
|
@ -24,7 +24,6 @@
|
|||
<string name="objectives_autosens_gate">1 tydzień sukcesu w działaniu pętli w ciągu dnia z regularnym wprowadzaniem spożywanych węglowodanów</string>
|
||||
<string name="objectives_autosens_learned">Jeśli wynik autosens nie oscyluje w okolicach 100%, prawdopodobnie Twój profil nie jest poprawny.</string>
|
||||
<string name="objectives_smb_objective">Włączanie dodatkowych funkcji do użytku, jak SMB (Super Mikro Bolusy)</string>
|
||||
<string name="objectives_smb_gate">Musisz przeczytać wiki i zwiększyć maxIOB, aby SMB działało dobrze! Dobrym początkiem jest maxIOB = średni bolus + 3 x maks. dzienna dawka bazowa</string>
|
||||
<string name="objectives_smb_learned">Używanie SMB jest Twoim celem. Algorytm Oref1 został zaprojektowany, aby pomóc Ci również w bolusach. Nie należy podawać pełnego bolusa do jedzenia, ale tylko jego część, a w razie potrzeby pozostawić resztę AAPS. W ten sposób masz więcej miejsca na błędnie obliczone węglowodany. Czy wiesz, że można w kalkulatorze ustawić procent wyniku bolusa, aby zmniejszyć rozmiar bolusa?</string>
|
||||
<string name="objectives_auto_objective">Włączanie automatyzacji</string>
|
||||
<string name="objectives_auto_gate">Przeczytaj dokumentację dotyczącą działania automatyzacji. Skonfiguruj swoje pierwsze proste zasady. Zamiast wykonania działania niech AAPS wyświetli tylko powiadomienie. Gdy masz pewność, że automatyzacja zostaje uruchomiona we właściwym czasie, zastąp powiadomienie rzeczywistą akcją. (https://wiki.aaps.app/en/latest/Usage/Automation.html)</string>
|
||||
|
|
|
@ -24,7 +24,6 @@
|
|||
<string name="objectives_autosens_gate">1 semana de looping durante o dia com sucesso com entrada regular de carboidratos</string>
|
||||
<string name="objectives_autosens_learned">Se o resultado do seu autosens não está oscilando por volta de 100% seu perfil provavelmente está errado.</string>
|
||||
<string name="objectives_smb_objective">Activando recursos adicionais para uso durante o dia, como SMB</string>
|
||||
<string name="objectives_smb_gate">Deverá ler a wiki e aumentar a IA máx para que os SMBs funcionem corretamente! Inicialmente poderá considerar maxIA=média dos bólus + 3 x a basal diária máxima</string>
|
||||
<string name="objectives_smb_learned">Usar SMB é o seu objetivo. O algoritmo Oref1 foi projetado para ajudá-lo também com seus bolus. Você não deve dar bolus completo para sua comida, apenas parte dela e deixar o AAPS lhe dar o resto, se necessário. Desta forma, você tem mais espaço para carboidratos mal calculado. Você sabia que pode definir uma porcentagem do resultado da calculadora de bolus para reduzir o tamanho do bolus?</string>
|
||||
<string name="objectives_auto_objective">Ativando a automação</string>
|
||||
<string name="objectives_auto_gate">Leia os documentos de como a automação funciona. Configure suas primeiras regras simples. Em vez de efetuar uma ação deixe AAPS apresentar apenas uma notificação. Quando você tiver certeza de que a automação é acionada no momento certo substitua a notificação por uma ação real. (https://wiki.aaps.app/en/latest/Usage/Automation.html)</string>
|
||||
|
|
|
@ -18,7 +18,6 @@
|
|||
<string name="objectives_autosens_objective">Ajuste as basais e os rácios, se necessário, e, em seguida, active o auto-sens</string>
|
||||
<string name="objectives_autosens_gate">1 semana de looping durante o dia com sucesso com entrada regular de hidratos de carbono</string>
|
||||
<string name="objectives_smb_objective">Activando recursos adicionais para uso durante o dia, como SMB</string>
|
||||
<string name="objectives_smb_gate">Deverá ler a wiki e aumentar a IA máx para que os SMBs funcionem devidamente! Inicialmente poderá considerar maxIA=média dos bólus + 3 x a basal máxima</string>
|
||||
<string name="objectives_auto_objective">A ativar a automatização</string>
|
||||
<string name="objectives_manualenacts">Execução manual</string>
|
||||
<string name="accomplished">Concluído: %1$s</string>
|
||||
|
|
|
@ -18,7 +18,6 @@
|
|||
<string name="objectives_autosens_objective">Ajustarea bazalelor și a factorilor dacă este necesar și apoi activarea auto-sens</string>
|
||||
<string name="objectives_autosens_gate">O săptămână de buclă închisă încheiată cu succes în condițiile introducerii regulate a carbohidraților</string>
|
||||
<string name="objectives_smb_objective">Se activează opțiuni pentru uzul în timpul zilei, cum ar fi SMB</string>
|
||||
<string name="objectives_smb_gate">Trebuie sa citiți wiki și să măriți maxIOB pentru a obține SMB corect! Un start bun este maxIOB=media bolusurilor + 3x maxima bazalei din zi</string>
|
||||
<string name="objectives_auto_objective">Activarea automatizării</string>
|
||||
<string name="objectives_manualenacts">Acțiuni manuale</string>
|
||||
<string name="accomplished">Îndeplinit: %1$s</string>
|
||||
|
|
|
@ -5,8 +5,8 @@
|
|||
<string name="nth_objective">Цель %1$d</string>
|
||||
<string name="objectivenotstarted">Цель %1$d не начата</string>
|
||||
<string name="objectivenotfinished">Цель %1$d не завершена</string>
|
||||
<string name="objectives_0_objective">Настройка визуализации и мониторинга, анализ базала и коэффициентов</string>
|
||||
<string name="objectives_0_gate">Убедитесь, что величина ГК и данные по инсулину помпы передаются в Nightscout</string>
|
||||
<string name="objectives_0_objective">Настройка интеграции с Nightscout, анализ базала и коэффициентов</string>
|
||||
<string name="objectives_0_gate">Убедитесь, что данные о гликемии и подаваемом AAPSом инсулине отображаются в Nightscout и актуальны</string>
|
||||
<string name="objectives_0_learned">Вы сделали базовую настройку экосистемы AAPS. Nightscout не нужен для работы AAPS, но может быть полезен для отчетов и мониторинга других пациентов. Необходимости в постоянном подключении к NS нет, если вы используете NS только для себя. Вы можете установить загрузку, например, только на домашний wifi, чтобы сэкономить заряд батареи.</string>
|
||||
<string name="objectives_openloop_objective">Старт незамкнутого цикла</string>
|
||||
<string name="objectives_openloop_gate">Начинайте работу в режиме незамкнутого цикла и ручной подстройки величины временного базала. Установите и применяйте временные цели и временные цели по умолчанию (напр. углеводы при нагрузке или купировании гипо)</string>
|
||||
|
@ -14,9 +14,9 @@
|
|||
<string name="objectives_maxbasal_objective">Глубже понимаем работу системы в режиме незамкнутого цикла, включая ее рекомендации по временным базалам</string>
|
||||
<string name="objectives_maxbasal_gate">На основе накопленного опыта, определяем максимальную величину базала и задаем ее в помпе и в настройки AndroidAPS</string>
|
||||
<string name="objectives_maxbasal_learned">Примите меры предосторожности и корректируйте, если необходимо, параметры безопасности.</string>
|
||||
<string name="objectives_maxiobzero_objective">Начинаем замыкать цикл с прекращением подачи инсулина при низком значении Ск (режим Low Glucose Suspend)</string>
|
||||
<string name="objectives_maxiobzero_objective">Начинаем замыкать цикл с прекращением подачи инсулина при низком значении ГК (режим Low Glucose Suspend)</string>
|
||||
<string name="objectives_maxiobzero_gate">Работа в замкнутом цикле с макс активным инсулином IOB = 0 на протяжении нескольких дней избегая событий типа приостановка на низких ГК Low Suspend</string>
|
||||
<string name="objectives_maxiobzero_learned">Установка MaxIOB на нуль предотвращает от гипо и не добавит инсулина выше базальной скорости (за исключением отрицательных значений IOB)</string>
|
||||
<string name="objectives_maxiobzero_learned">Установка MaxIOB на нуль предотвращает гипо и не добавит инсулина выше базальной скорости (за исключением отрицательных значений IOB)</string>
|
||||
<string name="objectives_maxiob_objective">Настройка замкнутого цикла с поднятием макс величины IOB выше 0 и постепенным понижением целевой ГК</string>
|
||||
<string name="objectives_maxiob_gate">Работа несколько дней и по кр мере одну ночь без срабатывания оповещений о низкой ГК</string>
|
||||
<string name="objectives_maxiob_learned">Обновляйте MaxIOB по мере взросления ребенка. Не допускайте, чтобы система подавала больше инсулина, чем вы можете покрыть едой = действительно, плохая идея выставлять высокие значения.</string>
|
||||
|
@ -24,7 +24,7 @@
|
|||
<string name="objectives_autosens_gate">1 неделя успешной дневной работы с регулярным введением углеводов</string>
|
||||
<string name="objectives_autosens_learned">Если результаты autosense не колеблются около 100%, то возможно ваш профиль неверный.</string>
|
||||
<string name="objectives_smb_objective">Активация таких доп функций для дневного времени как супер микро болюс SMB</string>
|
||||
<string name="objectives_smb_gate">Прочтите wiki и увеличьте maxIOB чтобы супер микро болюс SMB заработал как положено! Хорошее начало – maxIOB = средний болюс на еду + троекратный максимальный суточный базал</string>
|
||||
<string name="objectives_smb_gate">Прочтите статью wiki и увеличивайте maxIOB так, чтобы SMB заработал как положено! Для начала рассчитайте maxIOB как средний болюс на еду + макс. суточная базальная скорость*3</string>
|
||||
<string name="objectives_smb_learned">Ваша цель - это использование СМБ. Алгоритм Oref1 предназначен также, чтобы помочь вам с болюсами. Вы не должны подавать полный болюс на еду, а только часть его, предоставив AAPS подать при необходимости остальную часть болюса. Таким образом вы можете иметь большее пространство для ошибки в подсчетах углеводов. Вы знаете, что можно установить проценты для уменьшения размера болюса?</string>
|
||||
<string name="objectives_auto_objective">Включение автоматизации</string>
|
||||
<string name="objectives_auto_gate">Прочтите документацию по автоматизации. Настройте свои первые простые правила. Вместо действия позвольте AAPS только выводить уведомления. Если вы уверены, что автоматизация инициируется в нужное время, замените уведомление реальными действиями. (https://wiki.aaps.app/en/latest/Usage/Automation.html)</string>
|
||||
|
@ -49,9 +49,9 @@
|
|||
<string name="objectives_exam_learned_prerequisites2">AAPS может работать в автономном режиме.</string>
|
||||
<string name="objectives_exam_learned_basaltest">Следует пересмотреть и обновить профиль. Лучший профиль = лучшие результаты.</string>
|
||||
<string name="objectives_exam_learned_dia">Продолжительность действия инсулина DIA в AAPS имеет иное значение (время до полного поглощения инсулина), чем в классической помповой терапии (время до поглощения основной массы инсулина).</string>
|
||||
<string name="objectives_exam_learned_isf">Вы изучили понятие чувствительность к инсулину ISF, и как она влияет на коррекцию ГК.</string>
|
||||
<string name="objectives_exam_learned_ic">Вы изучили понятие углеводный коэффициент IC и как он влияет на количество инсулина, необходимого для покрытия углеводов.</string>
|
||||
<string name="objectives_exam_learned_hypott">Временная цель Hypo используется только для предотвращения чрезмерной коррекции после гипо, когда накапливается отрицательный IOB. Необходимо принять дополнительные меры, чтобы предотвратить ситуацию в будущем.</string>
|
||||
<string name="objectives_exam_learned_isf">Вы изучили понятие чувствительность к инсулину ISF и то, как она влияет на коррекцию ГК.</string>
|
||||
<string name="objectives_exam_learned_ic">Вы изучили понятие углеводный коэффициент IC и то, как он влияет на количество инсулина, необходимого для покрытия углеводов.</string>
|
||||
<string name="objectives_exam_learned_hypott">Временная цель Гипо используется только для предотвращения чрезмерной коррекции после гипо, когда накапливается отрицательный IOB. Необходимо принять дополнительные меры, чтобы предотвратить ситуацию в будущем.</string>
|
||||
<string name="objectives_exam_learned_profileswitch">Использование процентов не повлияет на целевую ГК, а только на базу, ISF и IC таким образом, чтобы дать больше инсулина (выше 100%%) или меньше инсулина (ниже 100%%).</string>
|
||||
<string name="objectives_exam_learned_profileswitchtime">Используя сдвиг по времени, можно адаптировать профиль к нерегулярным событиям типа позднего пробуждения.</string>
|
||||
<string name="objectives_exam_learned_profileswitch4">Редактирование профиля не является достаточным для внесения изменений. Все еще нужно переключиться на этот профиль и активировать изменения.</string>
|
||||
|
|
|
@ -18,7 +18,6 @@
|
|||
<string name="objectives_autosens_objective">Justera basaler och kvoter om det behövs. Aktivera sedan autosens</string>
|
||||
<string name="objectives_autosens_gate">1 veckas lyckad looping dagtid, där alla måltider lagts in</string>
|
||||
<string name="objectives_smb_objective">Aktiverar ytterligare funktioner för användning dagtid, t ex SMB</string>
|
||||
<string name="objectives_smb_gate">Du måste läsa på wikin och öka max IOB för att få SMB att fungera bra. En bra start är att sätta max IOB till din genomsnittliga måltidsbolus plus 3 gånger den högsta basalen du har under ett dygn</string>
|
||||
<string name="objectives_auto_objective">Aktivera automatisering</string>
|
||||
<string name="objectives_manualenacts">Manuella justeringar</string>
|
||||
<string name="accomplished">Utfört: %1$s</string>
|
||||
|
|
|
@ -18,7 +18,6 @@
|
|||
<string name="objectives_autosens_objective">必要时调整胰岛素基础率和比率,然后再启用auto-sens胰岛素敏感系数自动调整功能</string>
|
||||
<string name="objectives_autosens_gate">规律的进行碳水记录,成功在一个星期的白天开启闭环</string>
|
||||
<string name="objectives_smb_objective">在白天启用额外的功能,例如微型大剂量 SMB</string>
|
||||
<string name="objectives_smb_gate">你应该阅读wiki指南,以调整 maxIOB(活性胰岛素的最大值) 设置,让SMB(微型大剂量) 更好的工作。建议是 maxIOB值=餐时剂量的平均值+基础率的最大值的3倍。</string>
|
||||
<string name="objectives_auto_objective">启用自动操作功能插件</string>
|
||||
<string name="objectives_manualenacts">手动执行</string>
|
||||
<string name="accomplished">已完成: %1$s</string>
|
||||
|
|
|
@ -26,7 +26,7 @@
|
|||
<string name="objectives_autosens_gate">1 week successful daytime looping with regular carb entry</string>
|
||||
<string name="objectives_autosens_learned">If your autosens result is not oscillating around 100% your profile probably wrong.</string>
|
||||
<string name="objectives_smb_objective">Enabling additional features for daytime use, such as SMB</string>
|
||||
<string name="objectives_smb_gate">You must read the wiki and rise maxIOB to get SMBs working fine! A good start is maxIOB=average mealbolus + 3 x max daily basal</string>
|
||||
<string name="objectives_smb_gate">You must read the wiki and raise maxIOB to get SMBs working fine! A good start is maxIOB=average mealbolus + 3 x max daily basal</string>
|
||||
<string name="objectives_smb_learned">Using SMB is your goal. Oref1 algorithm was designed to help you with your boluses as well. You should not give full bolus for your food but only part of it and let AAPS give you the rest if needed. This way you have more space for miscalculated carbs. Did you know that you can set a percentage of bolus calculator result to reduce the size of bolus?</string>
|
||||
<string name="objectives_auto_objective">Enabling automation</string>
|
||||
<string name="objectives_auto_gate">Read the docs on how automation works. Set up your first simple rules. Instead of action let AAPS display only notification. When you are sure automation is triggered at the right time replace notification by real action. (https://wiki.aaps.app/en/latest/Usage/Automation.html)</string>
|
||||
|
|
|
@ -1,9 +1,7 @@
|
|||
package info.nightscout.plugins.general.actions
|
||||
|
||||
import android.content.Context
|
||||
import android.content.Intent
|
||||
import android.os.Bundle
|
||||
import android.util.DisplayMetrics
|
||||
import android.view.LayoutInflater
|
||||
import android.view.View
|
||||
import android.view.ViewGroup
|
||||
|
@ -59,7 +57,6 @@ class ActionsFragment : DaggerFragment() {
|
|||
@Inject lateinit var sp: SP
|
||||
@Inject lateinit var dateUtil: DateUtil
|
||||
@Inject lateinit var profileFunction: ProfileFunction
|
||||
@Inject lateinit var ctx: Context
|
||||
@Inject lateinit var rh: ResourceHelper
|
||||
@Inject lateinit var statusLightHandler: StatusLightHandler
|
||||
@Inject lateinit var fabricPrivacy: FabricPrivacy
|
||||
|
@ -78,31 +75,22 @@ class ActionsFragment : DaggerFragment() {
|
|||
|
||||
private val pumpCustomActions = HashMap<String, CustomAction>()
|
||||
private val pumpCustomButtons = ArrayList<SingleClickButton>()
|
||||
private lateinit var dm: DisplayMetrics
|
||||
|
||||
private var _binding: ActionsFragmentBinding? = null
|
||||
|
||||
// This property is only valid between onCreateView and onDestroyView.
|
||||
private val binding get() = _binding!!
|
||||
|
||||
override fun onCreateView(inflater: LayoutInflater, container: ViewGroup?, savedInstanceState: Bundle?): View {
|
||||
//check screen width
|
||||
dm = DisplayMetrics()
|
||||
if (android.os.Build.VERSION.SDK_INT >= android.os.Build.VERSION_CODES.R) {
|
||||
@Suppress("DEPRECATION")
|
||||
activity?.display?.getRealMetrics(dm)
|
||||
} else {
|
||||
@Suppress("DEPRECATION")
|
||||
activity?.windowManager?.defaultDisplay?.getMetrics(dm)
|
||||
}
|
||||
_binding = ActionsFragmentBinding.inflate(inflater, container, false)
|
||||
return binding.root
|
||||
}
|
||||
override fun onCreateView(inflater: LayoutInflater, container: ViewGroup?, savedInstanceState: Bundle?): View =
|
||||
ActionsFragmentBinding.inflate(inflater, container, false).also { _binding = it }.root
|
||||
|
||||
override fun onViewCreated(view: View, savedInstanceState: Bundle?) {
|
||||
super.onViewCreated(view, savedInstanceState)
|
||||
|
||||
skinProvider.activeSkin().preProcessLandscapeActionsLayout(dm, binding)
|
||||
val screenWidth = activity?.window?.decorView?.width ?: 0
|
||||
val screenHeight = activity?.window?.decorView?.height ?: 0
|
||||
val isLandscape = screenHeight < screenWidth
|
||||
skinProvider.activeSkin().preProcessLandscapeActionsLayout(isLandscape, binding)
|
||||
|
||||
binding.profileSwitch.setOnClickListener {
|
||||
activity?.let { activity ->
|
||||
|
@ -285,7 +273,7 @@ class ActionsFragment : DaggerFragment() {
|
|||
binding.tddStats.visibility = pump.pumpDescription.supportsTDDs.toVisibility()
|
||||
val isPatchPump = pump.pumpDescription.isPatchPump
|
||||
binding.status.apply {
|
||||
cannulaOrPatch.text = if (isPatchPump) rh.gs(R.string.patch_pump) else rh.gs(R.string.cannula)
|
||||
cannulaOrPatch.text = if (cannulaOrPatch.text.isEmpty()) "" else if (isPatchPump) rh.gs(R.string.patch_pump) else rh.gs(R.string.cannula)
|
||||
val imageResource = if (isPatchPump) info.nightscout.core.main.R.drawable.ic_patch_pump_outline else R.drawable.ic_cp_age_cannula
|
||||
cannulaOrPatch.setCompoundDrawablesWithIntrinsicBounds(imageResource, 0, 0, 0)
|
||||
batteryLayout.visibility = (!isPatchPump || pump.pumpDescription.useHardwareLink).toVisibility()
|
||||
|
@ -293,7 +281,11 @@ class ActionsFragment : DaggerFragment() {
|
|||
cannulaUsage.visibility = isPatchPump.not().toVisibility()
|
||||
|
||||
if (!config.NSCLIENT) {
|
||||
statusLightHandler.updateStatusLights(cannulaAge, cannulaUsage, insulinAge, reservoirLevel, sensorAge, sensorLevel, pbAge, batteryLevel)
|
||||
statusLightHandler.updateStatusLights(
|
||||
cannulaAge, cannulaUsage, insulinAge,
|
||||
reservoirLevel, sensorAge, sensorLevel,
|
||||
pbAge, pbLevel
|
||||
)
|
||||
sensorLevelLabel.text = if (activeBgSource.sensorBatteryLevel == -1) "" else rh.gs(R.string.level_label)
|
||||
} else {
|
||||
statusLightHandler.updateStatusLights(cannulaAge, cannulaUsage, insulinAge, null, sensorAge, null, pbAge, null)
|
||||
|
|
|
@ -188,7 +188,7 @@ class OverviewFragment : DaggerFragment(), View.OnClickListener, OnLongClickList
|
|||
smallHeight = screenHeight <= Constants.SMALL_HEIGHT
|
||||
val landscape = screenHeight < screenWidth
|
||||
|
||||
skinProvider.activeSkin().preProcessLandscapeOverviewLayout(dm, binding, landscape, rh.gb(info.nightscout.shared.R.bool.isTablet), smallHeight)
|
||||
skinProvider.activeSkin().preProcessLandscapeOverviewLayout(binding, landscape, rh.gb(info.nightscout.shared.R.bool.isTablet), smallHeight)
|
||||
binding.nsclientCard.visibility = config.NSCLIENT.toVisibility()
|
||||
|
||||
binding.notifications.setHasFixedSize(false)
|
||||
|
@ -841,11 +841,7 @@ class OverviewFragment : DaggerFragment(), View.OnClickListener, OnLongClickList
|
|||
if (it.value.originalPercentage != 100 || it.value.originalTimeshift != 0L || it.value.originalDuration != 0L)
|
||||
info.nightscout.core.ui.R.attr.ribbonWarningColor
|
||||
else info.nightscout.core.ui.R.attr.ribbonDefaultColor
|
||||
} else if (it is ProfileSealed.PS) {
|
||||
info.nightscout.core.ui.R.attr.ribbonDefaultColor
|
||||
} else {
|
||||
info.nightscout.core.ui.R.attr.ribbonDefaultColor
|
||||
}
|
||||
} else info.nightscout.core.ui.R.attr.ribbonDefaultColor
|
||||
} ?: info.nightscout.core.ui.R.attr.ribbonCriticalColor
|
||||
|
||||
val profileTextColor = profile?.let {
|
||||
|
@ -853,11 +849,7 @@ class OverviewFragment : DaggerFragment(), View.OnClickListener, OnLongClickList
|
|||
if (it.value.originalPercentage != 100 || it.value.originalTimeshift != 0L || it.value.originalDuration != 0L)
|
||||
info.nightscout.core.ui.R.attr.ribbonTextWarningColor
|
||||
else info.nightscout.core.ui.R.attr.ribbonTextDefaultColor
|
||||
} else if (it is ProfileSealed.PS) {
|
||||
info.nightscout.core.ui.R.attr.ribbonTextDefaultColor
|
||||
} else {
|
||||
info.nightscout.core.ui.R.attr.ribbonTextDefaultColor
|
||||
}
|
||||
} else info.nightscout.core.ui.R.attr.ribbonTextDefaultColor
|
||||
} ?: info.nightscout.core.ui.R.attr.ribbonTextDefaultColor
|
||||
setRibbon(binding.activeProfile, profileTextColor, profileBackgroundColor, profileFunction.getProfileNameWithRemainingTime())
|
||||
}
|
||||
|
@ -899,14 +891,12 @@ class OverviewFragment : DaggerFragment(), View.OnClickListener, OnLongClickList
|
|||
binding.statusLightsLayout.apply {
|
||||
cannulaOrPatch.setImageResource(if (isPatchPump) info.nightscout.core.main.R.drawable.ic_patch_pump_outline else R.drawable.ic_cp_age_cannula)
|
||||
cannulaOrPatch.contentDescription = rh.gs(if (isPatchPump) R.string.statuslights_patch_pump_age else R.string.statuslights_cannula_age)
|
||||
cannulaOrPatch.scaleX = if (isPatchPump) 1.4f else 2f
|
||||
cannulaOrPatch.scaleY = cannulaOrPatch.scaleX
|
||||
insulinAge.visibility = isPatchPump.not().toVisibility()
|
||||
batteryLayout.visibility = (!isPatchPump || pump.pumpDescription.useHardwareLink).toVisibility()
|
||||
pbAge.visibility = (pump.pumpDescription.isBatteryReplaceable || pump.isBatteryChangeLoggingEnabled()).toVisibility()
|
||||
val useBatteryLevel = (pump.model() == PumpType.OMNIPOD_EROS)
|
||||
|| (pump.model() != PumpType.ACCU_CHEK_COMBO && pump.model() != PumpType.OMNIPOD_DASH)
|
||||
batteryLevel.visibility = useBatteryLevel.toVisibility()
|
||||
pbLevel.visibility = useBatteryLevel.toVisibility()
|
||||
statusLightsLayout.visibility = (sp.getBoolean(R.string.key_show_statuslights, true) || config.NSCLIENT).toVisibility()
|
||||
}
|
||||
statusLightHandler.updateStatusLights(
|
||||
|
@ -917,7 +907,7 @@ class OverviewFragment : DaggerFragment(), View.OnClickListener, OnLongClickList
|
|||
binding.statusLightsLayout.sensorAge,
|
||||
null,
|
||||
binding.statusLightsLayout.pbAge,
|
||||
binding.statusLightsLayout.batteryLevel
|
||||
binding.statusLightsLayout.pbLevel
|
||||
)
|
||||
}
|
||||
|
||||
|
|
|
@ -12,7 +12,7 @@ import android.view.View
|
|||
import android.view.WindowManager
|
||||
import com.google.common.primitives.Ints.min
|
||||
import com.google.zxing.qrcode.decoder.ErrorCorrectionLevel
|
||||
import dagger.android.support.DaggerAppCompatActivity
|
||||
import info.nightscout.core.ui.activities.TranslatedDaggerAppCompatActivity
|
||||
import info.nightscout.core.ui.dialogs.OKDialog
|
||||
import info.nightscout.core.ui.toast.ToastUtils
|
||||
import info.nightscout.core.utils.fabric.FabricPrivacy
|
||||
|
@ -28,7 +28,7 @@ import info.nightscout.shared.interfaces.ResourceHelper
|
|||
import net.glxn.qrgen.android.QRCode
|
||||
import javax.inject.Inject
|
||||
|
||||
class SmsCommunicatorOtpActivity : DaggerAppCompatActivity() {
|
||||
class SmsCommunicatorOtpActivity : TranslatedDaggerAppCompatActivity() {
|
||||
|
||||
@Inject lateinit var fabricPrivacy: FabricPrivacy
|
||||
@Inject lateinit var smsCommunicator: SmsCommunicator
|
||||
|
|
|
@ -255,6 +255,7 @@ class ProfilePlugin @Inject constructor(
|
|||
isEdited = false
|
||||
createAndStoreConvertedProfile()
|
||||
aapsLogger.debug(LTag.PROFILE, "Accepted ${profiles.size} profiles")
|
||||
storeSettings()
|
||||
rxBus.send(EventLocalProfileChanged())
|
||||
} else
|
||||
aapsLogger.debug(LTag.PROFILE, "ProfileStore not accepted")
|
||||
|
|
|
@ -1,6 +1,5 @@
|
|||
package info.nightscout.plugins.skins
|
||||
|
||||
import android.util.DisplayMetrics
|
||||
import info.nightscout.interfaces.Config
|
||||
import info.nightscout.plugins.R
|
||||
import info.nightscout.plugins.databinding.OverviewFragmentBinding
|
||||
|
@ -14,8 +13,8 @@ class SkinClassic @Inject constructor(private val config: Config) : SkinInterfac
|
|||
override val mainGraphHeight: Int get() = 200
|
||||
override val secondaryGraphHeight: Int get() = 100
|
||||
|
||||
override fun preProcessLandscapeOverviewLayout(dm: DisplayMetrics, binding: OverviewFragmentBinding, isLandscape: Boolean, isTablet: Boolean, isSmallHeight: Boolean) {
|
||||
super.preProcessLandscapeOverviewLayout(dm, binding, isLandscape, isTablet, isSmallHeight)
|
||||
override fun preProcessLandscapeOverviewLayout(binding: OverviewFragmentBinding, isLandscape: Boolean, isTablet: Boolean, isSmallHeight: Boolean) {
|
||||
super.preProcessLandscapeOverviewLayout(binding, isLandscape, isTablet, isSmallHeight)
|
||||
if (!config.NSCLIENT && (isSmallHeight || isLandscape)) moveButtonsLayout(binding.root)
|
||||
}
|
||||
}
|
||||
|
|
|
@ -1,6 +1,5 @@
|
|||
package info.nightscout.plugins.skins
|
||||
|
||||
import android.util.DisplayMetrics
|
||||
import android.util.TypedValue.COMPLEX_UNIT_PX
|
||||
import android.view.View
|
||||
import android.widget.LinearLayout
|
||||
|
@ -18,16 +17,11 @@ interface SkinInterface {
|
|||
val secondaryGraphHeight: Int // in dp
|
||||
|
||||
// no pre processing by default
|
||||
fun preProcessLandscapeActionsLayout(dm: DisplayMetrics, binding: ActionsFragmentBinding) {
|
||||
fun preProcessLandscapeActionsLayout(isLandscape: Boolean, binding: ActionsFragmentBinding) {
|
||||
}
|
||||
|
||||
fun preProcessLandscapeOverviewLayout(dm: DisplayMetrics, binding: OverviewFragmentBinding, isLandscape: Boolean, isTablet: Boolean, isSmallHeight: Boolean) {
|
||||
// pre-process landscape mode
|
||||
val screenWidth = dm.widthPixels
|
||||
val screenHeight = dm.heightPixels
|
||||
val landscape = screenHeight < screenWidth
|
||||
|
||||
if (landscape) {
|
||||
fun preProcessLandscapeOverviewLayout(binding: OverviewFragmentBinding, isLandscape: Boolean, isTablet: Boolean, isSmallHeight: Boolean) {
|
||||
if (isLandscape) {
|
||||
val iobLayout = binding.infoLayout.iobLayout
|
||||
val iobLayoutParams = iobLayout.layoutParams as ConstraintLayout.LayoutParams
|
||||
val timeLayout = binding.infoLayout.timeLayout
|
||||
|
@ -59,7 +53,7 @@ interface SkinInterface {
|
|||
for (v in texts) v.setTextSize(COMPLEX_UNIT_PX, v.textSize * 1.3f)
|
||||
}
|
||||
binding.statusLightsLayout.apply {
|
||||
val texts = listOf(cannulaAge, insulinAge, reservoirLevel, sensorAge, pbAge, batteryLevel)
|
||||
val texts = listOf(cannulaAge, insulinAge, reservoirLevel, sensorAge, pbAge, pbLevel)
|
||||
for (v in texts) v.setTextSize(COMPLEX_UNIT_PX, v.textSize * 1.3f)
|
||||
}
|
||||
timeLayout.orientation = LinearLayout.HORIZONTAL
|
||||
|
|
|
@ -1,6 +1,5 @@
|
|||
package info.nightscout.plugins.skins
|
||||
|
||||
import android.util.DisplayMetrics
|
||||
import info.nightscout.interfaces.Config
|
||||
import info.nightscout.plugins.R
|
||||
import info.nightscout.plugins.databinding.OverviewFragmentBinding
|
||||
|
@ -14,8 +13,8 @@ class SkinLargeDisplay @Inject constructor(private val config: Config) : SkinInt
|
|||
override val mainGraphHeight: Int get() = 400
|
||||
override val secondaryGraphHeight: Int get() = 150
|
||||
|
||||
override fun preProcessLandscapeOverviewLayout(dm: DisplayMetrics, binding: OverviewFragmentBinding, isLandscape: Boolean, isTablet: Boolean, isSmallHeight: Boolean) {
|
||||
super.preProcessLandscapeOverviewLayout(dm, binding, isLandscape, isTablet, isSmallHeight)
|
||||
override fun preProcessLandscapeOverviewLayout(binding: OverviewFragmentBinding, isLandscape: Boolean, isTablet: Boolean, isSmallHeight: Boolean) {
|
||||
super.preProcessLandscapeOverviewLayout(binding, isLandscape, isTablet, isSmallHeight)
|
||||
if (!config.NSCLIENT && (isSmallHeight || isLandscape)) moveButtonsLayout(binding.root)
|
||||
}
|
||||
}
|
||||
|
|
|
@ -1,6 +1,5 @@
|
|||
package info.nightscout.plugins.skins
|
||||
|
||||
import android.util.DisplayMetrics
|
||||
import android.view.View.GONE
|
||||
import android.view.ViewGroup
|
||||
import info.nightscout.interfaces.Config
|
||||
|
@ -17,27 +16,26 @@ class SkinLowRes @Inject constructor(private val config: Config) : SkinInterface
|
|||
override val mainGraphHeight: Int get() = 200
|
||||
override val secondaryGraphHeight: Int get() = 100
|
||||
|
||||
override fun preProcessLandscapeActionsLayout(dm: DisplayMetrics, binding: ActionsFragmentBinding) {
|
||||
val screenWidth = dm.widthPixels
|
||||
val screenHeight = dm.heightPixels
|
||||
val isLandscape = screenHeight < screenWidth
|
||||
|
||||
override fun preProcessLandscapeActionsLayout(isLandscape: Boolean, binding: ActionsFragmentBinding) {
|
||||
if (!isLandscape) {
|
||||
binding.status.apply {
|
||||
sensorAgeLabel.visibility = GONE
|
||||
sensorLabel.text = ""
|
||||
sensorAgeLabel.visibility = GONE
|
||||
sensorLevelLabel.visibility = GONE
|
||||
insulinAgeLabel.visibility = GONE
|
||||
insulinLabel.text = ""
|
||||
insulinLevelLabel.visibility = GONE
|
||||
cannulaOrPatch.text = ""
|
||||
cannulaAgeLabel.visibility = GONE
|
||||
cannulaUsageLabel.visibility = GONE
|
||||
pbLabel.text = ""
|
||||
pbAgeLabel.visibility = GONE
|
||||
pbLevelLabel.visibility = GONE
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
override fun preProcessLandscapeOverviewLayout(dm: DisplayMetrics, binding: OverviewFragmentBinding, isLandscape: Boolean, isTablet: Boolean, isSmallHeight: Boolean) {
|
||||
override fun preProcessLandscapeOverviewLayout(binding: OverviewFragmentBinding, isLandscape: Boolean, isTablet: Boolean, isSmallHeight: Boolean) {
|
||||
if (!config.NSCLIENT && isLandscape) moveButtonsLayout(binding.root)
|
||||
|
||||
binding.apply {
|
||||
|
|
|
@ -12,6 +12,7 @@
|
|||
android:focusable="true">
|
||||
|
||||
<TextView
|
||||
android:id="@+id/sensor_label"
|
||||
android:layout_width="wrap_content"
|
||||
android:layout_height="25dp"
|
||||
android:gravity="center_vertical"
|
||||
|
@ -84,6 +85,7 @@
|
|||
android:focusable="true">
|
||||
|
||||
<TextView
|
||||
android:id="@+id/insulin_label"
|
||||
android:layout_width="wrap_content"
|
||||
android:layout_height="25dp"
|
||||
android:gravity="center_vertical"
|
||||
|
@ -272,7 +274,7 @@
|
|||
android:textSize="14sp" />
|
||||
|
||||
<TextView
|
||||
android:id="@+id/battery_level"
|
||||
android:id="@+id/pb_level"
|
||||
android:layout_width="wrap_content"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_marginEnd="20dp"
|
||||
|
|
|
@ -127,7 +127,7 @@
|
|||
app:alignItems="stretch"
|
||||
app:flexDirection="row"
|
||||
app:flexWrap="wrap"
|
||||
app:justifyContent="center">
|
||||
app:justifyContent="space_around">
|
||||
|
||||
<TextView
|
||||
android:id="@+id/pump"
|
||||
|
|
|
@ -1,32 +1,32 @@
|
|||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
|
||||
<com.google.android.flexbox.FlexboxLayout xmlns:android="http://schemas.android.com/apk/res/android"
|
||||
xmlns:app="http://schemas.android.com/apk/res-auto"
|
||||
xmlns:tools="http://schemas.android.com/tools"
|
||||
android:id="@+id/status_lights_layout"
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_marginTop="3dp"
|
||||
android:layout_marginBottom="3dp"
|
||||
android:orientation="horizontal"
|
||||
android:layout_marginTop="-3dp"
|
||||
android:layout_marginBottom="-3dp"
|
||||
android:paddingTop="4dp"
|
||||
android:paddingBottom="4dp"
|
||||
android:baselineAligned="false">
|
||||
app:alignContent="stretch"
|
||||
app:alignItems="stretch"
|
||||
app:flexDirection="row"
|
||||
app:flexWrap="wrap"
|
||||
app:justifyContent="space_around">
|
||||
|
||||
<LinearLayout
|
||||
android:layout_width="wrap_content"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_weight="1"
|
||||
android:focusable="true"
|
||||
android:gravity="center_horizontal"
|
||||
android:gravity="center"
|
||||
tools:ignore="UseCompoundDrawables">
|
||||
|
||||
<ImageView
|
||||
android:id="@+id/cannula_or_patch"
|
||||
android:layout_width="38dp"
|
||||
android:layout_height="fill_parent"
|
||||
android:layout_width="28dp"
|
||||
android:layout_height="28dp"
|
||||
android:contentDescription="@string/statuslights_cannula_age"
|
||||
android:scaleX="2"
|
||||
android:scaleY="2"
|
||||
app:srcCompat="@drawable/ic_cp_age_cannula" />
|
||||
|
||||
<TextView
|
||||
|
@ -40,23 +40,20 @@
|
|||
|
||||
<LinearLayout
|
||||
android:layout_width="wrap_content"
|
||||
android:layout_height="fill_parent"
|
||||
android:layout_weight="1"
|
||||
android:layout_height="wrap_content"
|
||||
android:focusable="true"
|
||||
android:gravity="center_horizontal">
|
||||
android:gravity="center">
|
||||
|
||||
<ImageView
|
||||
android:layout_width="26dp"
|
||||
android:layout_height="fill_parent"
|
||||
android:layout_width="28dp"
|
||||
android:layout_height="28dp"
|
||||
android:contentDescription="@string/a11y_insulin_label"
|
||||
android:scaleX="1.7"
|
||||
android:scaleY="1.7"
|
||||
app:srcCompat="@drawable/ic_cp_age_insulin" />
|
||||
|
||||
<TextView
|
||||
android:id="@+id/insulin_age"
|
||||
android:layout_width="wrap_content"
|
||||
android:layout_height="fill_parent"
|
||||
android:layout_height="wrap_content"
|
||||
android:lines="1"
|
||||
tools:text="12h" />
|
||||
|
||||
|
@ -73,18 +70,15 @@
|
|||
|
||||
<LinearLayout
|
||||
android:layout_width="wrap_content"
|
||||
android:layout_height="fill_parent"
|
||||
android:layout_weight="1"
|
||||
android:layout_height="wrap_content"
|
||||
android:focusable="true"
|
||||
android:gravity="center_horizontal"
|
||||
android:gravity="center"
|
||||
tools:ignore="UseCompoundDrawables">
|
||||
|
||||
<ImageView
|
||||
android:layout_width="28dp"
|
||||
android:layout_height="fill_parent"
|
||||
android:layout_height="28dp"
|
||||
android:contentDescription="@string/sensor_label"
|
||||
android:scaleX="1.6"
|
||||
android:scaleY="1.6"
|
||||
app:srcCompat="@drawable/ic_cp_age_sensor" />
|
||||
|
||||
<TextView
|
||||
|
@ -99,31 +93,28 @@
|
|||
<LinearLayout
|
||||
android:id="@+id/battery_layout"
|
||||
android:layout_width="wrap_content"
|
||||
android:layout_height="fill_parent"
|
||||
android:layout_weight="1"
|
||||
android:layout_height="wrap_content"
|
||||
android:focusable="true"
|
||||
android:gravity="center_horizontal">
|
||||
android:gravity="center">
|
||||
|
||||
<ImageView
|
||||
android:layout_width="32dp"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_width="28dp"
|
||||
android:layout_height="28dp"
|
||||
android:contentDescription="@string/battery_label"
|
||||
android:scaleX="1.8"
|
||||
android:scaleY="1.8"
|
||||
app:srcCompat="@drawable/ic_cp_age_battery" />
|
||||
|
||||
<TextView
|
||||
android:id="@+id/pb_age"
|
||||
android:layout_width="wrap_content"
|
||||
android:layout_height="fill_parent"
|
||||
android:layout_height="wrap_content"
|
||||
android:lines="1"
|
||||
android:text="-"
|
||||
tools:ignore="HardcodedText" />
|
||||
|
||||
<TextView
|
||||
android:id="@+id/battery_level"
|
||||
android:id="@+id/pb_level"
|
||||
android:layout_width="wrap_content"
|
||||
android:layout_height="fill_parent"
|
||||
android:layout_height="wrap_content"
|
||||
android:lines="1"
|
||||
android:paddingStart="2dp"
|
||||
android:paddingEnd="0dp"
|
||||
|
@ -131,4 +122,4 @@
|
|||
|
||||
</LinearLayout>
|
||||
|
||||
</LinearLayout>
|
||||
</com.google.android.flexbox.FlexboxLayout>
|
||||
|
|
|
@ -141,7 +141,6 @@
|
|||
<string name="error_in_basal_values">Грешка в базалните стойности</string>
|
||||
<string name="error_in_target_values">Грешка в стойностите за цел</string>
|
||||
<string name="error_in_isf_values">Грешка в стойностите за чувствителност (ISF)</string>
|
||||
<string name="profile_name_contains_dot">Името на профила съдържа точка.\nТова не се поддържа от НС.\nПрофилът не е качен в НС.</string>
|
||||
<string name="invalid_profile_not_accepted">Невалиден профил %1$s не приет от NS</string>
|
||||
<string name="view">Изглед</string>
|
||||
<string name="errors">Грешки</string>
|
||||
|
|
|
@ -128,7 +128,6 @@
|
|||
<string name="error_in_basal_values">Error en els valors de basal</string>
|
||||
<string name="error_in_target_values">Error en els valors de l\'objectiu </string>
|
||||
<string name="error_in_isf_values">Error en els valors de ISF</string>
|
||||
<string name="profile_name_contains_dot">El nom del perfil conté punts.\nAixò NS no ho permet.\nPerfil no enviat a NS.</string>
|
||||
<string name="invalid_profile_not_accepted">Perfil invàlid %1$s no acceptat de NS</string>
|
||||
<string name="view">Vista</string>
|
||||
<string name="errors">Errors</string>
|
||||
|
|
|
@ -141,7 +141,7 @@
|
|||
<string name="error_in_basal_values">Chyba v hodnotách bazálu</string>
|
||||
<string name="error_in_target_values">Chyba v hodnotách cílové gl.</string>
|
||||
<string name="error_in_isf_values">Chyba v hodnotách inz. citlivosti</string>
|
||||
<string name="profile_name_contains_dot">Název profilu obsahuje tečky.\nToto není v NS podporováno.\nProfil není přenesen do NS.</string>
|
||||
<string name="profile_name_contains_dot">Některý název profilu obsahuje tečky.\nToto není v NS podporováno.\nProfily nebudou přeneseny do NS.</string>
|
||||
<string name="invalid_profile_not_accepted">Neplatný profil %1$s nebyl přijat z NS</string>
|
||||
<string name="view">Zobrazit</string>
|
||||
<string name="errors">Chyby</string>
|
||||
|
|
|
@ -137,7 +137,6 @@
|
|||
<string name="error_in_basal_values">Fejl i basal rate værdier</string>
|
||||
<string name="error_in_target_values">Fejl i målværdier</string>
|
||||
<string name="error_in_isf_values">Fejl i ISF-værdier</string>
|
||||
<string name="profile_name_contains_dot">Profilnavn indeholder punktum.\nDette understøttes ikke af NS.\nProfilen er ikke uploadet til NS.</string>
|
||||
<string name="invalid_profile_not_accepted">Ugyldig profil %1$s blev ikke accepteret fra NS</string>
|
||||
<string name="view">Vis</string>
|
||||
<string name="errors">Fejl</string>
|
||||
|
|
|
@ -141,7 +141,6 @@
|
|||
<string name="error_in_basal_values">Fehler in den Basalwerten</string>
|
||||
<string name="error_in_target_values">Fehler in den Zielwerten</string>
|
||||
<string name="error_in_isf_values">Fehler in ISF-Werten</string>
|
||||
<string name="profile_name_contains_dot">Profilname enthält Punkte.\nDies wird von NS nicht unterstützt.\nProfil wird nicht zu NS hochgeladen.</string>
|
||||
<string name="invalid_profile_not_accepted">Ungültiges Profil %1$s wurde von NS nicht akzeptiert</string>
|
||||
<string name="view">Ansicht</string>
|
||||
<string name="errors">Fehler</string>
|
||||
|
|
|
@ -141,7 +141,7 @@
|
|||
<string name="error_in_basal_values">Error en valores basales</string>
|
||||
<string name="error_in_target_values">Error en los valores de objetivo</string>
|
||||
<string name="error_in_isf_values">Error en valores ISF</string>
|
||||
<string name="profile_name_contains_dot">El nombre de perfil contiene puntos.\nEsto no está permitido por NS.\nEl perfil no se cargará en NS.</string>
|
||||
<string name="profile_name_contains_dot">Algunos nombres de perfiles contienen puntos.\nEsto no está soportado por NS.\nLos perfiles no serán subidos a NS.</string>
|
||||
<string name="invalid_profile_not_accepted">Perfil no válido %1$s no aceptado desde Nightscout</string>
|
||||
<string name="view">Vista</string>
|
||||
<string name="errors">Errores</string>
|
||||
|
|
|
@ -141,7 +141,7 @@
|
|||
<string name="error_in_basal_values">Erreur dans les valeurs de basal</string>
|
||||
<string name="error_in_target_values">Erreur dans les valeurs cibles</string>
|
||||
<string name="error_in_isf_values">Erreur dans les valeurs de SI</string>
|
||||
<string name="profile_name_contains_dot">Le nom du profil contient des points.\nCe n\'est pas pris en charge par NS.\nLe profil n\'est pas remonté dans NS.</string>
|
||||
<string name="profile_name_contains_dot">Certains noms de profil contiennent des points.\nCeci n\'est pas supporté par NS.\nLes profils ne seront pas téléchargés vers NS.</string>
|
||||
<string name="invalid_profile_not_accepted">Profil %1$s non valide, refusé par NS</string>
|
||||
<string name="view">Vue</string>
|
||||
<string name="errors">Erreurs</string>
|
||||
|
|
|
@ -94,7 +94,6 @@
|
|||
<string name="error_in_basal_values">Pogreška u bazalnim vrijednostima</string>
|
||||
<string name="error_in_target_values">Pogreška u ciljanim vrijednostima</string>
|
||||
<string name="error_in_isf_values">Pogreška u ISF vrijednostima</string>
|
||||
<string name="profile_name_contains_dot">Naziv profila sadrži točke.\nNS to ne podržava.\nProfil nije učitan u NS.</string>
|
||||
<string name="invalid_profile_not_accepted">Nevažeći profil %1$s nije prihvaćen od NS-a</string>
|
||||
<string name="view">Pogled</string>
|
||||
<string name="errors">Greške</string>
|
||||
|
|
|
@ -141,7 +141,7 @@
|
|||
<string name="error_in_basal_values">Errore nei valori della basale</string>
|
||||
<string name="error_in_target_values">Errore nei valori del target</string>
|
||||
<string name="error_in_isf_values">Errore nei valori ISF</string>
|
||||
<string name="profile_name_contains_dot">Il nome profilo contiene dei punti.\nQuesto non è supportato da NS.\nIl profilo non viene caricato in NS.</string>
|
||||
<string name="profile_name_contains_dot">Alcuni nomi profilo contengono punti.\nQuesto non è supportato da NS.\nI profili non verranno caricati su NS.</string>
|
||||
<string name="invalid_profile_not_accepted">Profilo %1$s non valido - non accettato da NS</string>
|
||||
<string name="view">Vista</string>
|
||||
<string name="errors">Errori</string>
|
||||
|
|
|
@ -141,7 +141,6 @@
|
|||
<string name="error_in_basal_values">שגיאה בערכי המינון הבזאלי</string>
|
||||
<string name="error_in_target_values">שגיאה בערכי המטרה</string>
|
||||
<string name="error_in_isf_values">שגיאה בערכי יחס התיקון</string>
|
||||
<string name="profile_name_contains_dot">שם הפרופיל מכיל נקודות.\nשם כזה אינו נתמך ע\"י Nightscout \n הפרופיל לא הועלה ל-Nightscout.</string>
|
||||
<string name="invalid_profile_not_accepted">הפרופיל הבלתי חוקי %1$s מ-Nightscout לא מאושר</string>
|
||||
<string name="view">תצוגה</string>
|
||||
<string name="errors">שגיאות</string>
|
||||
|
|
|
@ -123,7 +123,6 @@
|
|||
<string name="save_or_reset_changes_first">우선 현재 변경사항을을 저장하거나 재설정하세요</string>
|
||||
<string name="delete_current_profile">현재 프로파일을 삭제 하시겠습니까?</string>
|
||||
<string name="units_colon">단위:</string>
|
||||
<string name="profile_name_contains_dot">프로파일명에 점을 포함하고 있습니다.\n이는 NS에서 지원하지 않습니다.\n프로파일이 NS에 업로드되지 않습니다.</string>
|
||||
<string name="errors">에러</string>
|
||||
<string name="profile_name">프로파일명:</string>
|
||||
<string name="a11y_delete_current_profile">현재 프로파일을 삭제 하시겠습니까</string>
|
||||
|
|
|
@ -130,7 +130,7 @@
|
|||
<!-- Profile -->
|
||||
<string name="localprofile">Profilis</string>
|
||||
<string name="localprofile_shortname">VP</string>
|
||||
<string name="description_profile_local">Nustatykite vietinį profilį.</string>
|
||||
<string name="description_profile_local">Nustatyti vietinį profilį.</string>
|
||||
<string name="a11y_add_new_to_list">pridėti naują į sąrašą</string>
|
||||
<string name="do_you_want_switch_profile">Ar norite pakeisti profilį ir atsisakyti pakeitimų, atliktų dabartiniame profilyje?</string>
|
||||
<string name="save_or_reset_changes_first">Pirmiausia išsaugoti arba anuliuoti dabartinius pokyčius</string>
|
||||
|
@ -141,7 +141,7 @@
|
|||
<string name="error_in_basal_values">Bazės reikšmių klaida</string>
|
||||
<string name="error_in_target_values">Tikslinės glikemijos reikšmės klaida</string>
|
||||
<string name="error_in_isf_values">JIF reikšmės klaida</string>
|
||||
<string name="profile_name_contains_dot">Profilio pavadinime yra taškų.\nŠios funkcijos NS nepalaiko.\nProfilis neįkeltas į NS.</string>
|
||||
<string name="profile_name_contains_dot">Profilio pavadinime yra taškų.\nŠios funkcijos NS nepalaiko.\nProfilis nebus įkeltas į NS.</string>
|
||||
<string name="invalid_profile_not_accepted">Neteisingas profilis %1$s nepriimtas iš NS</string>
|
||||
<string name="view">Rodymas</string>
|
||||
<string name="errors">Klaidos</string>
|
||||
|
@ -206,7 +206,7 @@
|
|||
<string name="dexcom_app_not_installed">Dexcom app neįdiegta.</string>
|
||||
<string name="dexcom_app_not_detected">Atnaujinkite savo Dexcom programėlės versiją</string>
|
||||
<string name="error_starting_cgm">Nepavyko paleisti NGJ programos. Įsitikinkite, kad ji įdiegta.</string>
|
||||
<string name="not_available_full">Negalimas</string>
|
||||
<string name="not_available_full">Nėra duomenų</string>
|
||||
<string name="constraints_violation">Apribojimų pažeidimas</string>
|
||||
<string name="change_your_input">Pakeiskite įvestus duomenis!</string>
|
||||
<string name="openaps">AtviraDKS</string>
|
||||
|
|
|
@ -141,7 +141,6 @@
|
|||
<string name="error_in_basal_values">Fout in basaal waarden</string>
|
||||
<string name="error_in_target_values">Fout in streefdoel</string>
|
||||
<string name="error_in_isf_values">Fout in ISF waarden</string>
|
||||
<string name="profile_name_contains_dot">Profielnaam bevat punten.\nDit wordt niet ondersteund door NS.\nProfiel is niet geüpload naar NS.</string>
|
||||
<string name="invalid_profile_not_accepted">Ongeldig profiel %1$s niet geaccepteerd door NS</string>
|
||||
<string name="view">Weergeven</string>
|
||||
<string name="errors">Foutmeldingen</string>
|
||||
|
|
|
@ -141,7 +141,7 @@
|
|||
<string name="error_in_basal_values">Feil i basalverdiene</string>
|
||||
<string name="error_in_target_values">Feil i BS målverdier</string>
|
||||
<string name="error_in_isf_values">Feil i IF verdien</string>
|
||||
<string name="profile_name_contains_dot">Profilnavnet inneholder prikker.\nDette støttes ikke av NS.\nProfilen er ikke lastet opp til NS.</string>
|
||||
<string name="profile_name_contains_dot">Noen av profilnavnene inneholder punktum.\nDette støttes ikke av NS.\nProfilen er ikke lastet opp til NS.</string>
|
||||
<string name="invalid_profile_not_accepted">Ugyldig profil %1$s ikke akseptert fra NS</string>
|
||||
<string name="view">Visning</string>
|
||||
<string name="errors">Feil</string>
|
||||
|
|
|
@ -141,7 +141,7 @@
|
|||
<string name="error_in_basal_values">Błąd w wartościach bazy</string>
|
||||
<string name="error_in_target_values">Błąd w wartościach docelowych</string>
|
||||
<string name="error_in_isf_values">Błąd w wartościach ISF</string>
|
||||
<string name="profile_name_contains_dot">Nazwa profilu zawiera kropki.\nTo nie jest obsługiwane przez NS.\nProfil nie zostanie przesyłany do NS.</string>
|
||||
<string name="profile_name_contains_dot">Nazwa któregoś z profili zawiera kropki.\nTo nie jest obsługiwane przez NS.\nProfile nie zostaną przesłane do NS.</string>
|
||||
<string name="invalid_profile_not_accepted">Błędny profil %1$s nie został zaakceptowany z NS</string>
|
||||
<string name="view">Podgląd</string>
|
||||
<string name="errors">Błędy</string>
|
||||
|
|
|
@ -138,7 +138,6 @@
|
|||
<string name="error_in_basal_values">Erro nos valores da basal</string>
|
||||
<string name="error_in_target_values">Erro nos valores de alvo</string>
|
||||
<string name="error_in_isf_values">Erro nos valores de FSI</string>
|
||||
<string name="profile_name_contains_dot">Nome do perfil contém pontos.\nIsso não é suportado pelo NS.\nPerfil não foi enviado para o NS.</string>
|
||||
<string name="invalid_profile_not_accepted">Perfil inválido %1$s não aceito do NS</string>
|
||||
<string name="view">Visualização</string>
|
||||
<string name="errors">Erros</string>
|
||||
|
|
|
@ -128,7 +128,6 @@
|
|||
<string name="error_in_basal_values">Erro nos valores da basal</string>
|
||||
<string name="error_in_target_values">Erros no valor alvo</string>
|
||||
<string name="error_in_isf_values">Erro nos valores do FSI</string>
|
||||
<string name="profile_name_contains_dot">Nome do perfil contém pontos.\nIsso não é suportado pelo NS.\nPerfil não é enviado para o NS.</string>
|
||||
<string name="invalid_profile_not_accepted">Perfil inválido %1$s não aceite do NS</string>
|
||||
<string name="view">Ver</string>
|
||||
<string name="errors">Erros</string>
|
||||
|
|
|
@ -129,7 +129,6 @@
|
|||
<string name="error_in_basal_values">Eroare in valorile ratei bazale</string>
|
||||
<string name="error_in_target_values">Eroare in valorile tinta</string>
|
||||
<string name="error_in_isf_values">Eroare in valorile ISF</string>
|
||||
<string name="profile_name_contains_dot">Numele profilului conține puncte.\nAcest lucru nu este permis de NS.\nProfilul nu a fost înregistrat în NS.</string>
|
||||
<string name="invalid_profile_not_accepted">Profilul invalid din NS %1$s nu este acceptat</string>
|
||||
<string name="view">Vizualizare</string>
|
||||
<string name="errors">Erori</string>
|
||||
|
|
|
@ -141,7 +141,7 @@
|
|||
<string name="error_in_basal_values">Ошибка в величине базала</string>
|
||||
<string name="error_in_target_values">Ошибка в целевых значениях</string>
|
||||
<string name="error_in_isf_values">Ошибка в значении фактора чувствительности к инсулину ISF</string>
|
||||
<string name="profile_name_contains_dot">Имя профиля содержит точки.\nЭто не поддерживается NS.\nПрофиль не выгружен в NS.</string>
|
||||
<string name="profile_name_contains_dot">В некоторых наименованиях профиля содержатся точки.\nЭто не поддерживается NS.\nПрофиль не выгружен в NS.</string>
|
||||
<string name="invalid_profile_not_accepted">Неверный профиль %1$s не принят из NS</string>
|
||||
<string name="view">Смотреть</string>
|
||||
<string name="errors">Ошибки</string>
|
||||
|
|
|
@ -141,7 +141,7 @@
|
|||
<string name="error_in_basal_values">Chyba v hodnotách bazálu</string>
|
||||
<string name="error_in_target_values">Chyba v cieľových hodnotách</string>
|
||||
<string name="error_in_isf_values">Chyba v hodnotách citlivosti</string>
|
||||
<string name="profile_name_contains_dot">Názov profilu obsahuje bodky.\nToto nie je v NS podporované.\nProfil nie je prenesený do NS.</string>
|
||||
<string name="profile_name_contains_dot">Názov profilu obsahuje bodky.\nToto nie je v NS podporované.\nProfil nebude prenesený do NS.</string>
|
||||
<string name="invalid_profile_not_accepted">Neplatný profil %1$s nebol akceptovaný z NS</string>
|
||||
<string name="view">Zobraziť</string>
|
||||
<string name="errors">Chyby</string>
|
||||
|
|
|
@ -129,7 +129,6 @@
|
|||
<string name="error_in_basal_values">Fel i basaldoser</string>
|
||||
<string name="error_in_target_values">Fel i målvärden</string>
|
||||
<string name="error_in_isf_values">Fel i korrektionskvoter</string>
|
||||
<string name="profile_name_contains_dot">Profilnamnet innehåller punkter.\nDetta stöds inte av NS.\nProfil överförs inte till NS.</string>
|
||||
<string name="invalid_profile_not_accepted">Ogiltig profil %1$s från NS accepteras inte</string>
|
||||
<string name="view">Visa</string>
|
||||
<string name="errors">Fel</string>
|
||||
|
|
|
@ -141,7 +141,7 @@
|
|||
<string name="error_in_basal_values">Bazal değerlerde hata</string>
|
||||
<string name="error_in_target_values">Hedef değerlerde hata</string>
|
||||
<string name="error_in_isf_values">ISF değerinde hata</string>
|
||||
<string name="profile_name_contains_dot">Profil adı noktalar içeriyor.\nBu NS tarafından desteklenmiyor.\n Profil NS\'a yüklenmez.</string>
|
||||
<string name="profile_name_contains_dot">Profil adlarından bazıları noktalar içeriyor.\nBu, NS tarafından desteklenmiyor.\nProfiller NS\'ye yüklenmeyecek.</string>
|
||||
<string name="invalid_profile_not_accepted">Geçersiz profil %1$s NS tarafından kabul edilmiyor</string>
|
||||
<string name="view">Görünüm</string>
|
||||
<string name="errors">Hatalar</string>
|
||||
|
|
|
@ -135,7 +135,6 @@
|
|||
<string name="error_in_basal_values">基础率数值错误</string>
|
||||
<string name="error_in_target_values">目标数值错误</string>
|
||||
<string name="error_in_isf_values">ISF数值错误</string>
|
||||
<string name="profile_name_contains_dot">配置文件名称包含点。\n这不受 NS 支持。\n配置未上载到 NS。</string>
|
||||
<string name="invalid_profile_not_accepted">不接受来自NS的无效配置文件%1$s</string>
|
||||
<string name="view">查看</string>
|
||||
<string name="errors">错误</string>
|
||||
|
|
Some files were not shown because too many files have changed in this diff Show more
Loading…
Reference in a new issue