From da447b8afee5e4fb76dc89a4a653846a0151b458 Mon Sep 17 00:00:00 2001 From: Milos Kozak Date: Mon, 16 Sep 2019 15:49:45 +0200 Subject: [PATCH] LocalProfile allow more profiles --- .../activities/PreferencesActivity.java | 2 +- .../configBuilder/ProfileFunctions.java | 4 + .../profile/local/LocalProfileFragment.kt | 105 +++++--- .../profile/local/LocalProfilePlugin.kt | 246 ++++++++++++++---- .../main/res/layout/localprofile_fragment.xml | 15 +- app/src/main/res/values/arrays.xml | 9 + app/src/main/res/values/strings.xml | 3 + .../{pref_language.xml => pref_general.xml} | 10 + 8 files changed, 298 insertions(+), 96 deletions(-) rename app/src/main/res/xml/{pref_language.xml => pref_general.xml} (65%) diff --git a/app/src/main/java/info/nightscout/androidaps/activities/PreferencesActivity.java b/app/src/main/java/info/nightscout/androidaps/activities/PreferencesActivity.java index 941366f8f0..91093f5bf8 100644 --- a/app/src/main/java/info/nightscout/androidaps/activities/PreferencesActivity.java +++ b/app/src/main/java/info/nightscout/androidaps/activities/PreferencesActivity.java @@ -145,8 +145,8 @@ public class PreferencesActivity extends PreferenceActivity implements SharedPre if (!Config.NSCLIENT) { addPreferencesFromResource(R.xml.pref_password); } + addPreferencesFromResource(R.xml.pref_general); addPreferencesFromResource(R.xml.pref_age); - addPreferencesFromResource(R.xml.pref_language); addPreferencesFromResource(R.xml.pref_overview); diff --git a/app/src/main/java/info/nightscout/androidaps/plugins/configBuilder/ProfileFunctions.java b/app/src/main/java/info/nightscout/androidaps/plugins/configBuilder/ProfileFunctions.java index 025d8dac1e..93767bc662 100644 --- a/app/src/main/java/info/nightscout/androidaps/plugins/configBuilder/ProfileFunctions.java +++ b/app/src/main/java/info/nightscout/androidaps/plugins/configBuilder/ProfileFunctions.java @@ -116,6 +116,10 @@ public class ProfileFunctions { return getProfile(System.currentTimeMillis()); } + public static String getSystemUnits() { + return SP.getString(R.string.key_units, Constants.MGDL); + } + public String getProfileUnits() { Profile profile = getProfile(); return profile != null ? profile.getUnits() : Constants.MGDL; diff --git a/app/src/main/java/info/nightscout/androidaps/plugins/profile/local/LocalProfileFragment.kt b/app/src/main/java/info/nightscout/androidaps/plugins/profile/local/LocalProfileFragment.kt index 54cd41ee45..a47726c033 100644 --- a/app/src/main/java/info/nightscout/androidaps/plugins/profile/local/LocalProfileFragment.kt +++ b/app/src/main/java/info/nightscout/androidaps/plugins/profile/local/LocalProfileFragment.kt @@ -7,19 +7,21 @@ import android.text.TextWatcher import android.view.LayoutInflater import android.view.View import android.view.ViewGroup +import android.widget.AdapterView +import android.widget.ArrayAdapter import androidx.fragment.app.Fragment +import info.nightscout.androidaps.Constants import info.nightscout.androidaps.MainApp import info.nightscout.androidaps.R +import info.nightscout.androidaps.data.Profile import info.nightscout.androidaps.events.EventInitializationChanged import info.nightscout.androidaps.plugins.bus.RxBus import info.nightscout.androidaps.plugins.configBuilder.ConfigBuilderPlugin +import info.nightscout.androidaps.plugins.configBuilder.ProfileFunctions import info.nightscout.androidaps.plugins.general.careportal.CareportalFragment import info.nightscout.androidaps.plugins.general.careportal.Dialogs.NewNSTreatmentDialog import info.nightscout.androidaps.plugins.insulin.InsulinOrefBasePlugin.MIN_DIA -import info.nightscout.androidaps.utils.DecimalFormatter -import info.nightscout.androidaps.utils.FabricPrivacy -import info.nightscout.androidaps.utils.SafeParse -import info.nightscout.androidaps.utils.TimeListEdit +import info.nightscout.androidaps.utils.* import io.reactivex.android.schedulers.AndroidSchedulers import io.reactivex.disposables.CompositeDisposable import kotlinx.android.synthetic.main.localprofile_fragment.* @@ -29,6 +31,7 @@ class LocalProfileFragment : Fragment() { private var disposable: CompositeDisposable = CompositeDisposable() private var basalView: TimeListEdit? = null + private var spinner: SpinnerHelper? = null private val save = Runnable { doEdit() @@ -39,7 +42,7 @@ class LocalProfileFragment : Fragment() { override fun afterTextChanged(s: Editable) {} override fun beforeTextChanged(s: CharSequence, start: Int, count: Int, after: Int) {} override fun onTextChanged(s: CharSequence, start: Int, before: Int, count: Int) { - LocalProfilePlugin.dia = SafeParse.stringToDouble(localprofile_dia.text.toString()) + LocalProfilePlugin.currentProfile().dia = SafeParse.stringToDouble(localprofile_dia.text.toString()) doEdit() } } @@ -57,35 +60,71 @@ class LocalProfileFragment : Fragment() { override fun onViewCreated(view: View, savedInstanceState: Bundle?) { super.onViewCreated(view, savedInstanceState) + build() + } + + fun build() { val pumpDescription = ConfigBuilderPlugin.getPlugin().activePump?.pumpDescription ?: return + val units = ProfileFunctions.getSystemUnits() - localprofile_dia.setParams(LocalProfilePlugin.dia, MIN_DIA, 12.0, 0.1, DecimalFormat("0.0"), false, localprofile_save, textWatch) - TimeListEdit(context, view, R.id.localprofile_ic, MainApp.gs(R.string.nsprofileview_ic_label) + ":", LocalProfilePlugin.ic, null, 0.5, 50.0, 0.1, DecimalFormat("0.0"), save) - TimeListEdit(context, view, R.id.localprofile_isf, MainApp.gs(R.string.nsprofileview_isf_label) + ":", LocalProfilePlugin.isf, null, 0.5, 500.0, 0.1, DecimalFormat("0.0"), save) - basalView = TimeListEdit(context, view, R.id.localprofile_basal, MainApp.gs(R.string.nsprofileview_basal_label) + ": " + sumLabel(), LocalProfilePlugin.basal, null, pumpDescription.basalMinimumRate, 10.0, 0.01, DecimalFormat("0.00"), save) - TimeListEdit(context, view, R.id.localprofile_target, MainApp.gs(R.string.nsprofileview_target_label) + ":", LocalProfilePlugin.targetLow, LocalProfilePlugin.targetHigh, 3.0, 200.0, 0.1, DecimalFormat("0.0"), save) - - - if (!pumpDescription.isTempBasalCapable) { - localprofile_basal.visibility = View.GONE + localprofile_name.setText(LocalProfilePlugin.currentProfile().name) + localprofile_dia.setParams(LocalProfilePlugin.currentProfile().dia, HardLimits.MINDIA, HardLimits.MAXDIA, 0.1, DecimalFormat("0.0"), false, localprofile_save, textWatch) + TimeListEdit(context, view, R.id.localprofile_ic, MainApp.gs(R.string.nsprofileview_ic_label) + ":", LocalProfilePlugin.currentProfile().ic, null, HardLimits.MINIC, HardLimits.MAXIC, 0.1, DecimalFormat("0.0"), save) + basalView = TimeListEdit(context, view, R.id.localprofile_basal, MainApp.gs(R.string.nsprofileview_basal_label) + ": " + sumLabel(), LocalProfilePlugin.currentProfile().basal, null, pumpDescription.basalMinimumRate, 10.0, 0.01, DecimalFormat("0.00"), save) + if (units == Constants.MGDL) { + TimeListEdit(context, view, R.id.localprofile_isf, MainApp.gs(R.string.nsprofileview_isf_label) + ":", LocalProfilePlugin.currentProfile().isf, null, HardLimits.MINISF, HardLimits.MAXISF, 1.0, DecimalFormat("0"), save) + TimeListEdit(context, view, R.id.localprofile_target, MainApp.gs(R.string.nsprofileview_target_label) + ":", LocalProfilePlugin.currentProfile().targetLow, LocalProfilePlugin.currentProfile().targetHigh, HardLimits.VERY_HARD_LIMIT_TARGET_BG[0].toDouble(), HardLimits.VERY_HARD_LIMIT_TARGET_BG[1].toDouble(), 1.0, DecimalFormat("0"), save) + } else { + TimeListEdit(context, view, R.id.localprofile_isf, MainApp.gs(R.string.nsprofileview_isf_label) + ":", LocalProfilePlugin.currentProfile().isf, null, Profile.fromMgdlToUnits(HardLimits.MINISF, Constants.MMOL), Profile.fromMgdlToUnits(HardLimits.MAXISF, Constants.MMOL), 0.1, DecimalFormat("0.0"), save) + TimeListEdit(context, view, R.id.localprofile_target, MainApp.gs(R.string.nsprofileview_target_label) + ":", LocalProfilePlugin.currentProfile().targetLow, LocalProfilePlugin.currentProfile().targetHigh, Profile.fromMgdlToUnits(HardLimits.VERY_HARD_LIMIT_TARGET_BG[0].toDouble(), Constants.MMOL), Profile.fromMgdlToUnits(HardLimits.VERY_HARD_LIMIT_TARGET_BG[1].toDouble(), Constants.MMOL), 0.1, DecimalFormat("0.0"), save) } - localprofile_mgdl.isChecked = LocalProfilePlugin.mgdl - localprofile_mmol.isChecked = LocalProfilePlugin.mmol + // Spinner + spinner = SpinnerHelper(view?.findViewById(R.id.localprofile_spinner)) + val profileList: ArrayList = LocalProfilePlugin.profile?.profileList + ?: ArrayList() + context?.let { context -> + val adapter = ArrayAdapter(context, R.layout.spinner_centered, profileList) + spinner?.adapter = adapter + spinner?.setSelection(LocalProfilePlugin.currentProfileIndex) + } ?: return + spinner?.setOnItemSelectedListener(object : AdapterView.OnItemSelectedListener { + override fun onNothingSelected(parent: AdapterView<*>?) { + } - localprofile_mgdl.setOnClickListener { - LocalProfilePlugin.mgdl = localprofile_mgdl.isChecked - LocalProfilePlugin.mmol = !LocalProfilePlugin.mgdl - localprofile_mmol.isChecked = LocalProfilePlugin.mmol - doEdit() + override fun onItemSelected(parent: AdapterView<*>?, view: View?, position: Int, id: Long) { + if (LocalProfilePlugin.isEdited) { + context?.let { context -> + OKDialog.show(context, MainApp.gs(R.string.confirmation), MainApp.gs(R.string.doyouwantswitchprofile)) { + LocalProfilePlugin.currentProfileIndex = position + build() + } + } + } else { + LocalProfilePlugin.currentProfileIndex = position + build() + } + } + }) + + localprofile_profile_add.setOnClickListener { + LocalProfilePlugin.addNewProfile() + build() } - localprofile_mmol.setOnClickListener { - LocalProfilePlugin.mmol = localprofile_mmol.isChecked - LocalProfilePlugin.mgdl = !LocalProfilePlugin.mmol - localprofile_mgdl.isChecked = LocalProfilePlugin.mgdl - doEdit() + + localprofile_profile_remove.setOnClickListener { + LocalProfilePlugin.removeCurrentProfile() + build() } + // this is probably not possible because it leads to invalid profile + // if (!pumpDescription.isTempBasalCapable) localprofile_basal.visibility = View.GONE + + localprofile_mgdl.isChecked = LocalProfilePlugin.currentProfile().mgdl + localprofile_mmol.isChecked = !LocalProfilePlugin.currentProfile().mgdl + localprofile_mgdl.isEnabled = false + localprofile_mmol.isEnabled = false + localprofile_profileswitch.setOnClickListener { val newDialog = NewNSTreatmentDialog() val profileSwitch = CareportalFragment.PROFILESWITCHDIRECT @@ -96,13 +135,13 @@ class LocalProfileFragment : Fragment() { localprofile_reset.setOnClickListener { LocalProfilePlugin.loadSettings() - localprofile_mgdl.isChecked = LocalProfilePlugin.mgdl - localprofile_mmol.isChecked = LocalProfilePlugin.mmol - localprofile_dia.setParams(LocalProfilePlugin.dia, MIN_DIA, 12.0, 0.1, DecimalFormat("0.0"), false, localprofile_save, textWatch) - TimeListEdit(context, view, R.id.localprofile_ic, MainApp.gs(R.string.nsprofileview_ic_label) + ":", LocalProfilePlugin.ic, null, 0.5, 50.0, 0.1, DecimalFormat("0.0"), save) - TimeListEdit(context, view, R.id.localprofile_isf, MainApp.gs(R.string.nsprofileview_isf_label) + ":", LocalProfilePlugin.isf, null, 0.5, 500.0, 0.1, DecimalFormat("0.0"), save) - basalView = TimeListEdit(context, view, R.id.localprofile_basal, MainApp.gs(R.string.nsprofileview_basal_label) + ": " + sumLabel(), LocalProfilePlugin.basal, null, pumpDescription.basalMinimumRate, 10.0, 0.01, DecimalFormat("0.00"), save) - TimeListEdit(context, view, R.id.localprofile_target, MainApp.gs(R.string.nsprofileview_target_label) + ":", LocalProfilePlugin.targetLow, LocalProfilePlugin.targetHigh, 3.0, 200.0, 0.1, DecimalFormat("0.0"), save) + localprofile_mgdl.isChecked = LocalProfilePlugin.currentProfile().mgdl + localprofile_mmol.isChecked = !LocalProfilePlugin.currentProfile().mgdl + localprofile_dia.setParams(LocalProfilePlugin.currentProfile().dia, MIN_DIA, 12.0, 0.1, DecimalFormat("0.0"), false, localprofile_save, textWatch) + TimeListEdit(context, view, R.id.localprofile_ic, MainApp.gs(R.string.nsprofileview_ic_label) + ":", LocalProfilePlugin.currentProfile().ic, null, 0.5, 50.0, 0.1, DecimalFormat("0.0"), save) + TimeListEdit(context, view, R.id.localprofile_isf, MainApp.gs(R.string.nsprofileview_isf_label) + ":", LocalProfilePlugin.currentProfile().isf, null, 0.5, 500.0, 0.1, DecimalFormat("0.0"), save) + basalView = TimeListEdit(context, view, R.id.localprofile_basal, MainApp.gs(R.string.nsprofileview_basal_label) + ": " + sumLabel(), LocalProfilePlugin.currentProfile().basal, null, pumpDescription.basalMinimumRate, 10.0, 0.01, DecimalFormat("0.00"), save) + TimeListEdit(context, view, R.id.localprofile_target, MainApp.gs(R.string.nsprofileview_target_label) + ":", LocalProfilePlugin.currentProfile().targetLow, LocalProfilePlugin.currentProfile().targetHigh, 3.0, 200.0, 0.1, DecimalFormat("0.0"), save) updateGUI() } diff --git a/app/src/main/java/info/nightscout/androidaps/plugins/profile/local/LocalProfilePlugin.kt b/app/src/main/java/info/nightscout/androidaps/plugins/profile/local/LocalProfilePlugin.kt index e9ead3e4d0..859154ca6a 100644 --- a/app/src/main/java/info/nightscout/androidaps/plugins/profile/local/LocalProfilePlugin.kt +++ b/app/src/main/java/info/nightscout/androidaps/plugins/profile/local/LocalProfilePlugin.kt @@ -11,16 +11,17 @@ import info.nightscout.androidaps.interfaces.PluginType import info.nightscout.androidaps.interfaces.ProfileInterface import info.nightscout.androidaps.logging.L import info.nightscout.androidaps.plugins.bus.RxBus +import info.nightscout.androidaps.plugins.configBuilder.ProfileFunctions +import info.nightscout.androidaps.utils.DateUtil import info.nightscout.androidaps.utils.DecimalFormatter import info.nightscout.androidaps.utils.SP import org.json.JSONArray import org.json.JSONException import org.json.JSONObject import org.slf4j.LoggerFactory +import java.util.* +import kotlin.collections.ArrayList -/** - * Created by mike on 05.08.2016. - */ object LocalProfilePlugin : PluginBase(PluginDescription() .mainType(PluginType.PROFILE) .fragmentClass(LocalProfileFragment::class.java.name) @@ -36,15 +37,28 @@ object LocalProfilePlugin : PluginBase(PluginDescription() private const val DEFAULTARRAY = "[{\"time\":\"00:00\",\"timeAsSeconds\":0,\"value\":0}]" + class SingleProfile { + internal var name: String? = null + internal var mgdl: Boolean = false + internal var dia: Double = Constants.defaultDIA + internal var ic: JSONArray? = null + internal var isf: JSONArray? = null + internal var basal: JSONArray? = null + internal var targetLow: JSONArray? = null + internal var targetHigh: JSONArray? = null + } + var isEdited: Boolean = false - internal var mgdl: Boolean = false - internal var mmol: Boolean = false - internal var dia: Double? = null - internal var ic: JSONArray? = null - internal var isf: JSONArray? = null - internal var basal: JSONArray? = null - internal var targetLow: JSONArray? = null - internal var targetHigh: JSONArray? = null + var profiles: ArrayList = ArrayList() + + internal var numOfProfiles = 0 + internal var currentProfileIndex = 0 + + init { + loadSettings() + } + + fun currentProfile() = profiles[currentProfileIndex] @Synchronized fun isValidEditState(): Boolean { @@ -52,20 +66,22 @@ object LocalProfilePlugin : PluginBase(PluginDescription() ?: false } - init { - loadSettings() - } - @Synchronized fun storeSettings() { - SP.putBoolean(LOCAL_PROFILE + "mmol", mmol) - SP.putBoolean(LOCAL_PROFILE + "mgdl", mgdl) - SP.putString(LOCAL_PROFILE + "dia", dia.toString()) - SP.putString(LOCAL_PROFILE + "ic", ic.toString()) - SP.putString(LOCAL_PROFILE + "isf", isf.toString()) - SP.putString(LOCAL_PROFILE + "basal", basal.toString()) - SP.putString(LOCAL_PROFILE + "targetlow", targetLow.toString()) - SP.putString(LOCAL_PROFILE + "targethigh", targetHigh.toString()) + for (i in 0 until numOfProfiles) { + profiles[i].run { + val LOCAL_PROFILE_NUMBERED = LOCAL_PROFILE + "_" + i + "_" + SP.putString(LOCAL_PROFILE_NUMBERED + "name", name) + SP.putBoolean(LOCAL_PROFILE_NUMBERED + "mgdl", mgdl) + SP.putDouble(LOCAL_PROFILE_NUMBERED + "dia", dia) + SP.putString(LOCAL_PROFILE_NUMBERED + "ic", ic.toString()) + SP.putString(LOCAL_PROFILE_NUMBERED + "isf", isf.toString()) + SP.putString(LOCAL_PROFILE_NUMBERED + "basal", basal.toString()) + SP.putString(LOCAL_PROFILE_NUMBERED + "targetlow", targetLow.toString()) + SP.putString(LOCAL_PROFILE_NUMBERED + "targethigh", targetHigh.toString()) + } + } + SP.putInt(LOCAL_PROFILE + "_profiles", numOfProfiles) createAndStoreConvertedProfile() isEdited = false @@ -76,61 +92,146 @@ object LocalProfilePlugin : PluginBase(PluginDescription() @Synchronized fun loadSettings() { + if (SP.contains(LOCAL_PROFILE + "mgdl")) { + doConversion() + return + } + + numOfProfiles = SP.getInt(LOCAL_PROFILE + "_profiles", 0) + profiles.clear() + numOfProfiles = Math.max(numOfProfiles, 1) // create at least one default profile if none exists + + for (i in 0 until numOfProfiles) { + val p = SingleProfile() + val LOCAL_PROFILE_NUMBERED = LOCAL_PROFILE + "_" + i + "_" + + p.name = SP.getString(LOCAL_PROFILE_NUMBERED + "name", LOCAL_PROFILE + i) + p.mgdl = SP.getBoolean(LOCAL_PROFILE_NUMBERED + "mgdl", false) + p.dia = SP.getDouble(LOCAL_PROFILE_NUMBERED + "dia", Constants.defaultDIA) + try { + p.ic = JSONArray(SP.getString(LOCAL_PROFILE_NUMBERED + "ic", DEFAULTARRAY)) + } catch (e1: JSONException) { + try { + p.ic = JSONArray(DEFAULTARRAY) + } catch (ignored: JSONException) { + } + log.error("Exception", e1) + } + + try { + p.isf = JSONArray(SP.getString(LOCAL_PROFILE_NUMBERED + "isf", DEFAULTARRAY)) + } catch (e1: JSONException) { + try { + p.isf = JSONArray(DEFAULTARRAY) + } catch (ignored: JSONException) { + } + log.error("Exception", e1) + } + + try { + p.basal = JSONArray(SP.getString(LOCAL_PROFILE_NUMBERED + "basal", DEFAULTARRAY)) + } catch (e1: JSONException) { + try { + p.basal = JSONArray(DEFAULTARRAY) + } catch (ignored: JSONException) { + } + log.error("Exception", e1) + } + + try { + p.targetLow = JSONArray(SP.getString(LOCAL_PROFILE_NUMBERED + "targetlow", DEFAULTARRAY)) + } catch (e1: JSONException) { + try { + p.targetLow = JSONArray(DEFAULTARRAY) + } catch (ignored: JSONException) { + } + log.error("Exception", e1) + } + + try { + p.targetHigh = JSONArray(SP.getString(LOCAL_PROFILE_NUMBERED + "targethigh", DEFAULTARRAY)) + } catch (e1: JSONException) { + try { + p.targetHigh = JSONArray(DEFAULTARRAY) + } catch (ignored: JSONException) { + } + log.error("Exception", e1) + } + + profiles.add(p) + } + isEdited = false + createAndStoreConvertedProfile() + } + + @Synchronized + private fun doConversion() { // conversion from 2.3 to 2.4 format if (L.isEnabled(L.PROFILE)) log.debug("Loading stored settings") + val p = SingleProfile() - mgdl = SP.getBoolean(LOCAL_PROFILE + "mgdl", false) - mmol = SP.getBoolean(LOCAL_PROFILE + "mmol", true) - dia = SP.getDouble(LOCAL_PROFILE + "dia", Constants.defaultDIA) + p.mgdl = SP.getBoolean(LOCAL_PROFILE + "mgdl", ProfileFunctions.getSystemUnits() == Constants.MGDL) + p.dia = SP.getDouble(LOCAL_PROFILE + "dia", Constants.defaultDIA) try { - ic = JSONArray(SP.getString(LOCAL_PROFILE + "ic", DEFAULTARRAY)) + p.ic = JSONArray(SP.getString(LOCAL_PROFILE + "ic", DEFAULTARRAY)) } catch (e1: JSONException) { try { - ic = JSONArray(DEFAULTARRAY) + p.ic = JSONArray(DEFAULTARRAY) } catch (ignored: JSONException) { } - } try { - isf = JSONArray(SP.getString(LOCAL_PROFILE + "isf", DEFAULTARRAY)) + p.isf = JSONArray(SP.getString(LOCAL_PROFILE + "isf", DEFAULTARRAY)) } catch (e1: JSONException) { try { - isf = JSONArray(DEFAULTARRAY) + p.isf = JSONArray(DEFAULTARRAY) } catch (ignored: JSONException) { } - } try { - basal = JSONArray(SP.getString(LOCAL_PROFILE + "basal", DEFAULTARRAY)) + p.basal = JSONArray(SP.getString(LOCAL_PROFILE + "basal", DEFAULTARRAY)) } catch (e1: JSONException) { try { - basal = JSONArray(DEFAULTARRAY) + p.basal = JSONArray(DEFAULTARRAY) } catch (ignored: JSONException) { } - } try { - targetLow = JSONArray(SP.getString(LOCAL_PROFILE + "targetlow", DEFAULTARRAY)) + p.targetLow = JSONArray(SP.getString(LOCAL_PROFILE + "targetlow", DEFAULTARRAY)) } catch (e1: JSONException) { try { - targetLow = JSONArray(DEFAULTARRAY) + p.targetLow = JSONArray(DEFAULTARRAY) } catch (ignored: JSONException) { } - } try { - targetHigh = JSONArray(SP.getString(LOCAL_PROFILE + "targethigh", DEFAULTARRAY)) + p.targetHigh = JSONArray(SP.getString(LOCAL_PROFILE + "targethigh", DEFAULTARRAY)) } catch (e1: JSONException) { try { - targetHigh = JSONArray(DEFAULTARRAY) + p.targetHigh = JSONArray(DEFAULTARRAY) } catch (ignored: JSONException) { } - } + p.name = LOCAL_PROFILE + + SP.remove(LOCAL_PROFILE + "mgdl") + SP.remove(LOCAL_PROFILE + "mmol") + SP.remove(LOCAL_PROFILE + "dia") + SP.remove(LOCAL_PROFILE + "ic") + SP.remove(LOCAL_PROFILE + "isf") + SP.remove(LOCAL_PROFILE + "basal") + SP.remove(LOCAL_PROFILE + "targetlow") + SP.remove(LOCAL_PROFILE + "targethigh") + + currentProfileIndex = 0 + numOfProfiles = 1 + profiles.clear() + profiles.add(p) + storeSettings() isEdited = false createAndStoreConvertedProfile() @@ -178,22 +279,61 @@ object LocalProfilePlugin : PluginBase(PluginDescription() rawProfile = createProfileStore() } + fun addNewProfile() { + var free = 0 + for (i in 1..10000) { + if (rawProfile?.getSpecificProfile(LOCAL_PROFILE + i) == null) { + free = i; + break + } + } + val p = SingleProfile() + p.name = LOCAL_PROFILE + free + p.mgdl = ProfileFunctions.getSystemUnits() == Constants.MGDL + p.dia = Constants.defaultDIA + p.ic = JSONArray(DEFAULTARRAY) + p.isf = JSONArray(DEFAULTARRAY) + p.basal = JSONArray(DEFAULTARRAY) + p.targetLow = JSONArray(DEFAULTARRAY) + p.targetHigh = JSONArray(DEFAULTARRAY) + profiles.add(p) + currentProfileIndex = profiles.size - 1 + numOfProfiles++ + createAndStoreConvertedProfile() + storeSettings() + } + + fun removeCurrentProfile() { + profiles.removeAt(currentProfileIndex) + numOfProfiles-- + if (profiles.size == 0) addNewProfile() + currentProfileIndex = 0 + createAndStoreConvertedProfile() + storeSettings() + } + fun createProfileStore(): ProfileStore { val json = JSONObject() val store = JSONObject() - val profile = JSONObject() try { - json.put("defaultProfile", LOCAL_PROFILE) + for (i in 0 until numOfProfiles) { + profiles[i].run { + val profile = JSONObject() + profile.put("dia", dia) + profile.put("carbratio", ic) + profile.put("sens", isf) + profile.put("basal", basal) + profile.put("target_low", targetLow) + profile.put("target_high", targetHigh) + profile.put("units", if (mgdl) Constants.MGDL else Constants.MMOL) + profile.put("timezone", TimeZone.getDefault().id) + store.put(name, profile) + } + } + json.put("defaultProfile", currentProfile().name) + json.put("startDate", DateUtil.toISOAsUTC(DateUtil.now())) json.put("store", store) - profile.put("dia", dia) - profile.put("carbratio", ic) - profile.put("sens", isf) - profile.put("basal", basal) - profile.put("target_low", targetLow) - profile.put("target_high", targetHigh) - profile.put("units", if (mgdl) Constants.MGDL else Constants.MMOL) - store.put(LOCAL_PROFILE, profile) } catch (e: JSONException) { log.error("Unhandled exception", e) } @@ -202,11 +342,11 @@ object LocalProfilePlugin : PluginBase(PluginDescription() } override fun getProfile(): ProfileStore? { - return if (rawProfile?.defaultProfile?.isValid(MainApp.gs(R.string.localprofile)) != true) null else rawProfile + return rawProfile } override fun getUnits(): String { - return if (mgdl) Constants.MGDL else Constants.MMOL + return if (currentProfile().mgdl) Constants.MGDL else Constants.MMOL } override fun getProfileName(): String { diff --git a/app/src/main/res/layout/localprofile_fragment.xml b/app/src/main/res/layout/localprofile_fragment.xml index 49fd413115..19770a7257 100644 --- a/app/src/main/res/layout/localprofile_fragment.xml +++ b/app/src/main/res/layout/localprofile_fragment.xml @@ -35,32 +35,29 @@ android:textAppearance="?android:attr/textAppearanceMedium" /> diff --git a/app/src/main/res/values/arrays.xml b/app/src/main/res/values/arrays.xml index 864835bd87..1184f37e54 100644 --- a/app/src/main/res/values/arrays.xml +++ b/app/src/main/res/values/arrays.xml @@ -10,6 +10,15 @@ open + + mg/dL + mmol/L + + + mg/dl + mmol + + @string/en_lang @string/af_lang diff --git a/app/src/main/res/values/strings.xml b/app/src/main/res/values/strings.xml index f12ac4b06b..3570604990 100644 --- a/app/src/main/res/values/strings.xml +++ b/app/src/main/res/values/strings.xml @@ -1606,5 +1606,8 @@ min Profile name: Selected: + Units + units + Do you want to switch profile and discard changes made to current profile? diff --git a/app/src/main/res/xml/pref_language.xml b/app/src/main/res/xml/pref_general.xml similarity index 65% rename from app/src/main/res/xml/pref_language.xml rename to app/src/main/res/xml/pref_general.xml index 981de2b346..f1bcbdb858 100644 --- a/app/src/main/res/xml/pref_language.xml +++ b/app/src/main/res/xml/pref_general.xml @@ -1,13 +1,23 @@ + + + + + \ No newline at end of file