Merge remote-tracking branch 'milosremote/dev' into tdds-again-merged

This commit is contained in:
AdrianLxM 2018-03-26 08:39:24 +02:00
commit a5d0ec45cc
153 changed files with 3089 additions and 1682 deletions

View file

@ -47,6 +47,11 @@ def generateGitBuild = { ->
return stringBuilder.toString() return stringBuilder.toString()
} }
tasks.matching {it instanceof Test}.all {
testLogging.events = ["failed", "skipped"]
testLogging.exceptionFormat = "full"
}
android { android {
compileSdkVersion 27 compileSdkVersion 27
buildToolsVersion "${supportLibraryVersion}" buildToolsVersion "${supportLibraryVersion}"
@ -57,7 +62,7 @@ android {
targetSdkVersion 23 targetSdkVersion 23
multiDexEnabled true multiDexEnabled true
versionCode 1500 versionCode 1500
version "1.60-dev" version "1.60a-dev"
buildConfigField "String", "VERSION", '"' + version + '"' buildConfigField "String", "VERSION", '"' + version + '"'
buildConfigField "String", "BUILDVERSION", generateGitBuild() buildConfigField "String", "BUILDVERSION", generateGitBuild()
@ -97,21 +102,6 @@ android {
buildConfigField "boolean", "APS", "true" buildConfigField "boolean", "APS", "true"
buildConfigField "boolean", "PUMPDRIVERS", "true" buildConfigField "boolean", "PUMPDRIVERS", "true"
buildConfigField "boolean", "NSCLIENTOLNY", "false" buildConfigField "boolean", "NSCLIENTOLNY", "false"
buildConfigField "boolean", "CLOSEDLOOP", "true"
buildConfigField "boolean", "G5UPLOADER", "false"
buildConfigField "boolean", "PUMPCONTROL", "false"
}
openloop {
dimension "standard"
resValue "string", "app_name", "AndroidAPS"
versionName version
manifestPlaceholders = [
appIcon: "@mipmap/blueowl"
]
buildConfigField "boolean", "APS", "true"
buildConfigField "boolean", "PUMPDRIVERS", "true"
buildConfigField "boolean", "NSCLIENTOLNY", "false"
buildConfigField "boolean", "CLOSEDLOOP", "false"
buildConfigField "boolean", "G5UPLOADER", "false" buildConfigField "boolean", "G5UPLOADER", "false"
buildConfigField "boolean", "PUMPCONTROL", "false" buildConfigField "boolean", "PUMPCONTROL", "false"
} }
@ -125,7 +115,6 @@ android {
buildConfigField "boolean", "APS", "false" buildConfigField "boolean", "APS", "false"
buildConfigField "boolean", "PUMPDRIVERS", "true" buildConfigField "boolean", "PUMPDRIVERS", "true"
buildConfigField "boolean", "NSCLIENTOLNY", "false" buildConfigField "boolean", "NSCLIENTOLNY", "false"
buildConfigField "boolean", "CLOSEDLOOP", "false"
buildConfigField "boolean", "G5UPLOADER", "false" buildConfigField "boolean", "G5UPLOADER", "false"
buildConfigField "boolean", "PUMPCONTROL", "true" buildConfigField "boolean", "PUMPCONTROL", "true"
} }
@ -139,7 +128,6 @@ android {
buildConfigField "boolean", "APS", "false" buildConfigField "boolean", "APS", "false"
buildConfigField "boolean", "PUMPDRIVERS", "false" buildConfigField "boolean", "PUMPDRIVERS", "false"
buildConfigField "boolean", "NSCLIENTOLNY", "true" buildConfigField "boolean", "NSCLIENTOLNY", "true"
buildConfigField "boolean", "CLOSEDLOOP", "false"
buildConfigField "boolean", "G5UPLOADER", "false" buildConfigField "boolean", "G5UPLOADER", "false"
buildConfigField "boolean", "PUMPCONTROL", "false" buildConfigField "boolean", "PUMPCONTROL", "false"
} }
@ -153,7 +141,6 @@ android {
buildConfigField "boolean", "APS", "false" buildConfigField "boolean", "APS", "false"
buildConfigField "boolean", "PUMPDRIVERS", "false" buildConfigField "boolean", "PUMPDRIVERS", "false"
buildConfigField "boolean", "NSCLIENTOLNY", "false" buildConfigField "boolean", "NSCLIENTOLNY", "false"
buildConfigField "boolean", "CLOSEDLOOP", "false"
buildConfigField "boolean", "G5UPLOADER", "true" buildConfigField "boolean", "G5UPLOADER", "true"
buildConfigField "boolean", "PUMPCONTROL", "false" buildConfigField "boolean", "PUMPCONTROL", "false"
} }

View file

@ -24,7 +24,7 @@ public class Config {
public static final boolean SMSCOMMUNICATORENABLED = !BuildConfig.NSCLIENTOLNY && !BuildConfig.G5UPLOADER; public static final boolean SMSCOMMUNICATORENABLED = !BuildConfig.NSCLIENTOLNY && !BuildConfig.G5UPLOADER;
public static final boolean displayDeviationSlope = true; public static final boolean displayDeviationSlope = false;
public static final boolean detailedLog = true; public static final boolean detailedLog = true;
public static final boolean logFunctionCalls = true; public static final boolean logFunctionCalls = true;

View file

@ -12,10 +12,11 @@ public class Constants {
public static final double defaultDIA = 3d; public static final double defaultDIA = 3d;
public static final double basalAbsoluteOnlyForCheckLimit = 10101010d; public static final Double REALLYHIGHBASALRATE = 1111111d;
public static final Integer basalPercentOnlyForCheckLimit = 10101010; public static final Integer REALLYHIGHPERCENTBASALRATE = 1111111;
public static final double bolusOnlyForCheckLimit = 10101010d; public static final double REALLYHIGHBOLUS = 1111111d;
public static final Integer carbsOnlyForCheckLimit = 10101010; public static final Integer REALLYHIGHCARBS = 1111111;
public static final double REALLYHIGHIOB = 1111111d;
public static final Integer notificationID = 556677; public static final Integer notificationID = 556677;

View file

@ -25,12 +25,12 @@ import java.util.ArrayList;
import ch.qos.logback.classic.LoggerContext; import ch.qos.logback.classic.LoggerContext;
import info.nightscout.androidaps.Services.Intents; import info.nightscout.androidaps.Services.Intents;
import info.nightscout.androidaps.data.ConstraintChecker;
import info.nightscout.androidaps.db.DatabaseHelper; import info.nightscout.androidaps.db.DatabaseHelper;
import info.nightscout.androidaps.interfaces.InsulinInterface; import info.nightscout.androidaps.interfaces.InsulinInterface;
import info.nightscout.androidaps.interfaces.PluginBase; import info.nightscout.androidaps.interfaces.PluginBase;
import info.nightscout.androidaps.plugins.Actions.ActionsFragment; import info.nightscout.androidaps.plugins.Actions.ActionsFragment;
import info.nightscout.androidaps.plugins.Careportal.CareportalPlugin; import info.nightscout.androidaps.plugins.Careportal.CareportalPlugin;
import info.nightscout.androidaps.plugins.ConfigBuilder.ConfigBuilderFragment;
import info.nightscout.androidaps.plugins.ConfigBuilder.ConfigBuilderPlugin; import info.nightscout.androidaps.plugins.ConfigBuilder.ConfigBuilderPlugin;
import info.nightscout.androidaps.plugins.ConstraintsObjectives.ObjectivesPlugin; import info.nightscout.androidaps.plugins.ConstraintsObjectives.ObjectivesPlugin;
import info.nightscout.androidaps.plugins.ConstraintsSafety.SafetyPlugin; import info.nightscout.androidaps.plugins.ConstraintsSafety.SafetyPlugin;
@ -42,7 +42,7 @@ import info.nightscout.androidaps.plugins.Insulin.InsulinOrefRapidActingPlugin;
import info.nightscout.androidaps.plugins.Insulin.InsulinOrefUltraRapidActingPlugin; import info.nightscout.androidaps.plugins.Insulin.InsulinOrefUltraRapidActingPlugin;
import info.nightscout.androidaps.plugins.IobCobCalculator.IobCobCalculatorPlugin; import info.nightscout.androidaps.plugins.IobCobCalculator.IobCobCalculatorPlugin;
import info.nightscout.androidaps.plugins.Loop.LoopPlugin; import info.nightscout.androidaps.plugins.Loop.LoopPlugin;
import info.nightscout.androidaps.plugins.NSClientInternal.NSClientInternalPlugin; import info.nightscout.androidaps.plugins.NSClientInternal.NSClientPlugin;
import info.nightscout.androidaps.plugins.NSClientInternal.receivers.AckAlarmReceiver; import info.nightscout.androidaps.plugins.NSClientInternal.receivers.AckAlarmReceiver;
import info.nightscout.androidaps.plugins.OpenAPSAMA.OpenAPSAMAPlugin; import info.nightscout.androidaps.plugins.OpenAPSAMA.OpenAPSAMAPlugin;
import info.nightscout.androidaps.plugins.OpenAPSMA.OpenAPSMAPlugin; import info.nightscout.androidaps.plugins.OpenAPSMA.OpenAPSMAPlugin;
@ -59,7 +59,7 @@ import info.nightscout.androidaps.plugins.PumpDanaR.DanaRPlugin;
import info.nightscout.androidaps.plugins.PumpDanaRKorean.DanaRKoreanPlugin; import info.nightscout.androidaps.plugins.PumpDanaRKorean.DanaRKoreanPlugin;
import info.nightscout.androidaps.plugins.PumpDanaRS.DanaRSPlugin; import info.nightscout.androidaps.plugins.PumpDanaRS.DanaRSPlugin;
import info.nightscout.androidaps.plugins.PumpDanaRv2.DanaRv2Plugin; import info.nightscout.androidaps.plugins.PumpDanaRv2.DanaRv2Plugin;
import info.nightscout.androidaps.plugins.PumpInsight.InsightPumpPlugin; import info.nightscout.androidaps.plugins.PumpInsight.InsightPlugin;
import info.nightscout.androidaps.plugins.PumpMDI.MDIPlugin; import info.nightscout.androidaps.plugins.PumpMDI.MDIPlugin;
import info.nightscout.androidaps.plugins.PumpVirtual.VirtualPumpPlugin; import info.nightscout.androidaps.plugins.PumpVirtual.VirtualPumpPlugin;
import info.nightscout.androidaps.plugins.SensitivityAAPS.SensitivityAAPSPlugin; import info.nightscout.androidaps.plugins.SensitivityAAPS.SensitivityAAPSPlugin;
@ -79,7 +79,6 @@ import info.nightscout.androidaps.receivers.KeepAliveReceiver;
import info.nightscout.androidaps.receivers.NSAlarmReceiver; import info.nightscout.androidaps.receivers.NSAlarmReceiver;
import info.nightscout.utils.FabricPrivacy; import info.nightscout.utils.FabricPrivacy;
import info.nightscout.utils.NSUpload; import info.nightscout.utils.NSUpload;
import info.nightscout.utils.SP;
import io.fabric.sdk.android.Fabric; import io.fabric.sdk.android.Fabric;
@ -93,6 +92,7 @@ public class MainApp extends Application {
private static DatabaseHelper sDatabaseHelper = null; private static DatabaseHelper sDatabaseHelper = null;
private static ConfigBuilderPlugin sConfigBuilder = null; private static ConfigBuilderPlugin sConfigBuilder = null;
private static ConstraintChecker sConstraintsChecker = null;
private static ArrayList<PluginBase> pluginsList = null; private static ArrayList<PluginBase> pluginsList = null;
@ -109,6 +109,7 @@ public class MainApp extends Application {
super.onCreate(); super.onCreate();
sInstance = this; sInstance = this;
sResources = getResources(); sResources = getResources();
sConstraintsChecker = new ConstraintChecker(this);
try { try {
if (FabricPrivacy.fabricEnabled()) { if (FabricPrivacy.fabricEnabled()) {
@ -154,7 +155,7 @@ public class MainApp extends Application {
if (Config.HWPUMPS) pluginsList.add(DanaRv2Plugin.getPlugin()); if (Config.HWPUMPS) pluginsList.add(DanaRv2Plugin.getPlugin());
if (Config.HWPUMPS) pluginsList.add(DanaRSPlugin.getPlugin()); if (Config.HWPUMPS) pluginsList.add(DanaRSPlugin.getPlugin());
pluginsList.add(CareportalPlugin.getPlugin()); pluginsList.add(CareportalPlugin.getPlugin());
if (Config.HWPUMPS && engineeringMode) pluginsList.add(InsightPumpPlugin.getPlugin()); // <-- Enable Insight plugin here if (Config.HWPUMPS && engineeringMode) pluginsList.add(InsightPlugin.getPlugin()); // <-- Enable Insight plugin here
if (Config.HWPUMPS && engineeringMode) pluginsList.add(ComboPlugin.getPlugin()); // <-- Enable Combo plugin here if (Config.HWPUMPS && engineeringMode) pluginsList.add(ComboPlugin.getPlugin()); // <-- Enable Combo plugin here
if (Config.MDI) pluginsList.add(MDIPlugin.getPlugin()); if (Config.MDI) pluginsList.add(MDIPlugin.getPlugin());
if (Config.VIRTUALPUMP) pluginsList.add(VirtualPumpPlugin.getPlugin()); if (Config.VIRTUALPUMP) pluginsList.add(VirtualPumpPlugin.getPlugin());
@ -184,20 +185,21 @@ public class MainApp extends Application {
pluginsList.add(WearPlugin.initPlugin(this)); pluginsList.add(WearPlugin.initPlugin(this));
pluginsList.add(StatuslinePlugin.initPlugin(this)); pluginsList.add(StatuslinePlugin.initPlugin(this));
pluginsList.add(new PersistentNotificationPlugin(this)); pluginsList.add(new PersistentNotificationPlugin(this));
pluginsList.add(NSClientInternalPlugin.getPlugin()); pluginsList.add(NSClientPlugin.getPlugin());
pluginsList.add(sConfigBuilder = ConfigBuilderFragment.getPlugin()); pluginsList.add(sConfigBuilder = ConfigBuilderPlugin.getPlugin());
MainApp.getConfigBuilder().initialize(); MainApp.getConfigBuilder().initialize();
} }
NSUpload.uploadAppStart(); NSUpload.uploadAppStart();
if (Config.NSCLIENT) if (Config.NSCLIENT)
FabricPrivacy.getInstance().logCustom(new CustomEvent("AppStart-NSClient")); FabricPrivacy.getInstance().logCustom(new CustomEvent("AppStart-NSClient"));
else if (Config.G5UPLOADER) else if (Config.G5UPLOADER)
FabricPrivacy.getInstance().logCustom(new CustomEvent("AppStart-G5Uploader")); FabricPrivacy.getInstance().logCustom(new CustomEvent("AppStart-G5Uploader"));
else if (Config.PUMPCONTROL) else if (Config.PUMPCONTROL)
FabricPrivacy.getInstance().logCustom(new CustomEvent("AppStart-PumpControl")); FabricPrivacy.getInstance().logCustom(new CustomEvent("AppStart-PumpControl"));
else if (MainApp.getConfigBuilder().isClosedModeEnabled()) else if (MainApp.getConstraintChecker().isClosedLoopAllowed().value())
FabricPrivacy.getInstance().logCustom(new CustomEvent("AppStart-ClosedLoop")); FabricPrivacy.getInstance().logCustom(new CustomEvent("AppStart-ClosedLoop"));
else else
FabricPrivacy.getInstance().logCustom(new CustomEvent("AppStart-OpenLoop")); FabricPrivacy.getInstance().logCustom(new CustomEvent("AppStart-OpenLoop"));
@ -293,6 +295,10 @@ public class MainApp extends Application {
return sConfigBuilder; return sConfigBuilder;
} }
public static ConstraintChecker getConstraintChecker() {
return sConstraintsChecker;
}
public static ArrayList<PluginBase> getPluginsList() { public static ArrayList<PluginBase> getPluginsList() {
return pluginsList; return pluginsList;
} }
@ -382,6 +388,8 @@ public class MainApp extends Application {
} }
public static boolean isEngineeringModeOrRelease() { public static boolean isEngineeringModeOrRelease() {
if (!BuildConfig.APS)
return true;
return engineeringMode || !devBranch; return engineeringMode || !devBranch;
} }

View file

@ -14,14 +14,14 @@ import android.text.TextUtils;
import info.nightscout.androidaps.events.EventPreferenceChange; import info.nightscout.androidaps.events.EventPreferenceChange;
import info.nightscout.androidaps.events.EventRefreshGui; import info.nightscout.androidaps.events.EventRefreshGui;
import info.nightscout.androidaps.interfaces.PluginBase; import info.nightscout.androidaps.interfaces.PluginBase;
import info.nightscout.androidaps.plugins.OpenAPSSMB.OpenAPSSMBPlugin;
import info.nightscout.androidaps.plugins.Careportal.CareportalPlugin; import info.nightscout.androidaps.plugins.Careportal.CareportalPlugin;
import info.nightscout.androidaps.plugins.ConstraintsSafety.SafetyPlugin; import info.nightscout.androidaps.plugins.ConstraintsSafety.SafetyPlugin;
import info.nightscout.androidaps.plugins.Insulin.InsulinOrefFreePeakPlugin; import info.nightscout.androidaps.plugins.Insulin.InsulinOrefFreePeakPlugin;
import info.nightscout.androidaps.plugins.Loop.LoopPlugin; import info.nightscout.androidaps.plugins.Loop.LoopPlugin;
import info.nightscout.androidaps.plugins.NSClientInternal.NSClientInternalPlugin; import info.nightscout.androidaps.plugins.NSClientInternal.NSClientPlugin;
import info.nightscout.androidaps.plugins.OpenAPSAMA.OpenAPSAMAPlugin; import info.nightscout.androidaps.plugins.OpenAPSAMA.OpenAPSAMAPlugin;
import info.nightscout.androidaps.plugins.OpenAPSMA.OpenAPSMAPlugin; import info.nightscout.androidaps.plugins.OpenAPSMA.OpenAPSMAPlugin;
import info.nightscout.androidaps.plugins.OpenAPSSMB.OpenAPSSMBPlugin;
import info.nightscout.androidaps.plugins.PumpDanaR.DanaRPlugin; import info.nightscout.androidaps.plugins.PumpDanaR.DanaRPlugin;
import info.nightscout.androidaps.plugins.PumpDanaRKorean.DanaRKoreanPlugin; import info.nightscout.androidaps.plugins.PumpDanaRKorean.DanaRKoreanPlugin;
import info.nightscout.androidaps.plugins.PumpDanaRS.DanaRSPlugin; import info.nightscout.androidaps.plugins.PumpDanaRS.DanaRSPlugin;
@ -65,7 +65,7 @@ public class PreferencesActivity extends PreferenceActivity implements SharedPre
if (key.equals("short_tabtitles")) { if (key.equals("short_tabtitles")) {
MainApp.bus().post(new EventRefreshGui()); MainApp.bus().post(new EventRefreshGui());
} }
if (key.equals("openapsama_useautosens") && SP.getBoolean("openapsama_useautosens", false)) { if (key.equals(MainApp.gs(R.string.key_openapsama_useautosens)) && SP.getBoolean(R.string.key_openapsama_useautosens, false)) {
OKDialog.show(this, MainApp.sResources.getString(R.string.configbuilder_sensitivity), MainApp.sResources.getString(R.string.sensitivity_warning), null); OKDialog.show(this, MainApp.sResources.getString(R.string.configbuilder_sensitivity), MainApp.sResources.getString(R.string.sensitivity_warning), null);
} }
updatePrefSummary(myPreferenceFragment.getPreference(key)); updatePrefSummary(myPreferenceFragment.getPreference(key));
@ -173,7 +173,7 @@ public class PreferencesActivity extends PreferenceActivity implements SharedPre
addPreferencesFromResourceIfEnabled(InsulinOrefFreePeakPlugin.getPlugin(), PluginBase.INSULIN); addPreferencesFromResourceIfEnabled(InsulinOrefFreePeakPlugin.getPlugin(), PluginBase.INSULIN);
addPreferencesFromResourceIfEnabled(NSClientInternalPlugin.getPlugin(), PluginBase.GENERAL); addPreferencesFromResourceIfEnabled(NSClientPlugin.getPlugin(), PluginBase.GENERAL);
addPreferencesFromResourceIfEnabled(SmsCommunicatorPlugin.getPlugin(), PluginBase.GENERAL); addPreferencesFromResourceIfEnabled(SmsCommunicatorPlugin.getPlugin(), PluginBase.GENERAL);
if (!Config.NSCLIENT && !Config.G5UPLOADER) { if (!Config.NSCLIENT && !Config.G5UPLOADER) {

View file

@ -64,31 +64,31 @@ public class DataService extends IntentService {
if (Config.logFunctionCalls) if (Config.logFunctionCalls)
log.debug("onHandleIntent " + BundleLogger.log(intent.getExtras())); log.debug("onHandleIntent " + BundleLogger.log(intent.getExtras()));
if (ConfigBuilderPlugin.getActiveBgSource().getClass().equals(SourceXdripPlugin.class)) { if (ConfigBuilderPlugin.getPlugin().getActiveBgSource().getClass().equals(SourceXdripPlugin.class)) {
xDripEnabled = true; xDripEnabled = true;
nsClientEnabled = false; nsClientEnabled = false;
mm640gEnabled = false; mm640gEnabled = false;
glimpEnabled = false; glimpEnabled = false;
dexcomG5Enabled = false; dexcomG5Enabled = false;
} else if (ConfigBuilderPlugin.getActiveBgSource().getClass().equals(SourceNSClientPlugin.class)) { } else if (ConfigBuilderPlugin.getPlugin().getActiveBgSource().getClass().equals(SourceNSClientPlugin.class)) {
xDripEnabled = false; xDripEnabled = false;
nsClientEnabled = true; nsClientEnabled = true;
mm640gEnabled = false; mm640gEnabled = false;
glimpEnabled = false; glimpEnabled = false;
dexcomG5Enabled = false; dexcomG5Enabled = false;
} else if (ConfigBuilderPlugin.getActiveBgSource().getClass().equals(SourceMM640gPlugin.class)) { } else if (ConfigBuilderPlugin.getPlugin().getActiveBgSource().getClass().equals(SourceMM640gPlugin.class)) {
xDripEnabled = false; xDripEnabled = false;
nsClientEnabled = false; nsClientEnabled = false;
mm640gEnabled = true; mm640gEnabled = true;
glimpEnabled = false; glimpEnabled = false;
dexcomG5Enabled = false; dexcomG5Enabled = false;
} else if (ConfigBuilderPlugin.getActiveBgSource().getClass().equals(SourceGlimpPlugin.class)) { } else if (ConfigBuilderPlugin.getPlugin().getActiveBgSource().getClass().equals(SourceGlimpPlugin.class)) {
xDripEnabled = false; xDripEnabled = false;
nsClientEnabled = false; nsClientEnabled = false;
mm640gEnabled = false; mm640gEnabled = false;
glimpEnabled = true; glimpEnabled = true;
dexcomG5Enabled = false; dexcomG5Enabled = false;
} else if (ConfigBuilderPlugin.getActiveBgSource().getClass().equals(SourceDexcomG5Plugin.class)) { } else if (ConfigBuilderPlugin.getPlugin().getActiveBgSource().getClass().equals(SourceDexcomG5Plugin.class)) {
xDripEnabled = false; xDripEnabled = false;
nsClientEnabled = false; nsClientEnabled = false;
mm640gEnabled = false; mm640gEnabled = false;
@ -192,7 +192,7 @@ public class DataService extends IntentService {
bgReading.date = bundle.getLong(Intents.EXTRA_TIMESTAMP); bgReading.date = bundle.getLong(Intents.EXTRA_TIMESTAMP);
bgReading.raw = bundle.getDouble(Intents.EXTRA_RAW); bgReading.raw = bundle.getDouble(Intents.EXTRA_RAW);
MainApp.getDbHelper().createIfNotExists(bgReading, "XDRIP", xDripEnabled); MainApp.getDbHelper().createIfNotExists(bgReading, "XDRIP");
} }
private void handleNewDataFromGlimp(Intent intent) { private void handleNewDataFromGlimp(Intent intent) {
@ -206,7 +206,7 @@ public class DataService extends IntentService {
bgReading.date = bundle.getLong("myTimestamp"); bgReading.date = bundle.getLong("myTimestamp");
bgReading.raw = 0; bgReading.raw = 0;
MainApp.getDbHelper().createIfNotExists(bgReading, "GLIMP", glimpEnabled); MainApp.getDbHelper().createIfNotExists(bgReading, "GLIMP");
} }
private void handleNewDataFromDexcomG5(Intent intent) { private void handleNewDataFromDexcomG5(Intent intent) {
@ -229,7 +229,7 @@ public class DataService extends IntentService {
bgReading.direction = json.getString("m_trend"); bgReading.direction = json.getString("m_trend");
bgReading.date = json.getLong("m_time") * 1000L; bgReading.date = json.getLong("m_time") * 1000L;
bgReading.raw = 0; bgReading.raw = 0;
boolean isNew = MainApp.getDbHelper().createIfNotExists(bgReading, "DexcomG5", dexcomG5Enabled); boolean isNew = MainApp.getDbHelper().createIfNotExists(bgReading, "DexcomG5");
if (isNew && SP.getBoolean(R.string.key_dexcomg5_nsupload, false)) { if (isNew && SP.getBoolean(R.string.key_dexcomg5_nsupload, false)) {
NSUpload.uploadBg(bgReading); NSUpload.uploadBg(bgReading);
} }
@ -268,7 +268,7 @@ public class DataService extends IntentService {
bgReading.date = json_object.getLong("date"); bgReading.date = json_object.getLong("date");
bgReading.raw = json_object.getDouble("sgv"); bgReading.raw = json_object.getDouble("sgv");
MainApp.getDbHelper().createIfNotExists(bgReading, "MM640g", mm640gEnabled); MainApp.getDbHelper().createIfNotExists(bgReading, "MM640g");
break; break;
default: default:
log.debug("Unknown entries type: " + type); log.debug("Unknown entries type: " + type);
@ -425,7 +425,7 @@ public class DataService extends IntentService {
JSONObject sgvJson = new JSONObject(sgvstring); JSONObject sgvJson = new JSONObject(sgvstring);
NSSgv nsSgv = new NSSgv(sgvJson); NSSgv nsSgv = new NSSgv(sgvJson);
BgReading bgReading = new BgReading(nsSgv); BgReading bgReading = new BgReading(nsSgv);
MainApp.getDbHelper().createIfNotExists(bgReading, "NS", nsClientEnabled); MainApp.getDbHelper().createIfNotExists(bgReading, "NS");
} }
if (bundles.containsKey("sgvs")) { if (bundles.containsKey("sgvs")) {
@ -435,7 +435,7 @@ public class DataService extends IntentService {
JSONObject sgvJson = jsonArray.getJSONObject(i); JSONObject sgvJson = jsonArray.getJSONObject(i);
NSSgv nsSgv = new NSSgv(sgvJson); NSSgv nsSgv = new NSSgv(sgvJson);
BgReading bgReading = new BgReading(nsSgv); BgReading bgReading = new BgReading(nsSgv);
MainApp.getDbHelper().createIfNotExists(bgReading, "NS", nsClientEnabled); MainApp.getDbHelper().createIfNotExists(bgReading, "NS");
} }
} }
} catch (Exception e) { } catch (Exception e) {

View file

@ -0,0 +1,197 @@
package info.nightscout.androidaps.data;
import java.util.ArrayList;
import info.nightscout.androidaps.Constants;
import info.nightscout.androidaps.MainApp;
import info.nightscout.androidaps.interfaces.BgSourceInterface;
import info.nightscout.androidaps.interfaces.Constraint;
import info.nightscout.androidaps.interfaces.ConstraintsInterface;
import info.nightscout.androidaps.interfaces.PluginBase;
import info.nightscout.androidaps.plugins.ConfigBuilder.ConfigBuilderPlugin;
/**
* Created by mike on 19.03.2018.
*/
public class ConstraintChecker implements ConstraintsInterface {
private MainApp mainApp;
public ConstraintChecker(MainApp mainApp) {
this.mainApp = mainApp;
}
public Constraint<Boolean> isLoopInvokationAllowed() {
return isLoopInvokationAllowed(new Constraint<>(true));
}
public Constraint<Boolean> isClosedLoopAllowed() {
return isClosedLoopAllowed(new Constraint<>(true));
}
public Constraint<Boolean> isAutosensModeEnabled() {
return isAutosensModeEnabled(new Constraint<>(true));
}
public Constraint<Boolean> isAMAModeEnabled() {
return isAMAModeEnabled(new Constraint<>(true));
}
public Constraint<Boolean> isSMBModeEnabled() {
return isSMBModeEnabled(new Constraint<>(true));
}
public Constraint<Boolean> isAdvancedFilteringEnabled() {
return isAdvancedFilteringEnabled(new Constraint<>(true));
}
public Constraint<Double> getMaxBasalAllowed(Profile profile) {
return applyBasalConstraints(new Constraint<>(Constants.REALLYHIGHBASALRATE), profile);
}
public Constraint<Integer> getMaxBasalPercentAllowed(Profile profile) {
return applyBasalPercentConstraints(new Constraint<>(Constants.REALLYHIGHPERCENTBASALRATE), profile);
}
public Constraint<Double> getMaxBolusAllowed() {
return applyBolusConstraints(new Constraint<>(Constants.REALLYHIGHBOLUS));
}
public Constraint<Integer> getMaxCarbsAllowed() {
return applyCarbsConstraints(new Constraint<>(Constants.REALLYHIGHCARBS));
}
public Constraint<Double> getMaxIOBAllowed() {
return applyMaxIOBConstraints(new Constraint<>(Constants.REALLYHIGHIOB));
}
@Override
public Constraint<Boolean> isLoopInvokationAllowed(Constraint<Boolean> value) {
ArrayList<PluginBase> constraintsPlugins = mainApp.getSpecificPluginsListByInterface(ConstraintsInterface.class);
for (PluginBase p : constraintsPlugins) {
ConstraintsInterface constraint = (ConstraintsInterface) p;
if (!p.isEnabled(PluginBase.CONSTRAINTS)) continue;
constraint.isLoopInvokationAllowed(value);
}
return value;
}
@Override
public Constraint<Boolean> isClosedLoopAllowed(Constraint<Boolean> value) {
ArrayList<PluginBase> constraintsPlugins = mainApp.getSpecificPluginsListByInterface(ConstraintsInterface.class);
for (PluginBase p : constraintsPlugins) {
ConstraintsInterface constraint = (ConstraintsInterface) p;
if (!p.isEnabled(PluginBase.CONSTRAINTS)) continue;
constraint.isClosedLoopAllowed(value);
}
return value;
}
@Override
public Constraint<Boolean> isAutosensModeEnabled(Constraint<Boolean> value) {
ArrayList<PluginBase> constraintsPlugins = mainApp.getSpecificPluginsListByInterface(ConstraintsInterface.class);
for (PluginBase p : constraintsPlugins) {
ConstraintsInterface constraint = (ConstraintsInterface) p;
if (!p.isEnabled(PluginBase.CONSTRAINTS)) continue;
constraint.isAutosensModeEnabled(value);
}
return value;
}
@Override
public Constraint<Boolean> isAMAModeEnabled(Constraint<Boolean> value) {
ArrayList<PluginBase> constraintsPlugins = mainApp.getSpecificPluginsListByInterface(ConstraintsInterface.class);
for (PluginBase p : constraintsPlugins) {
ConstraintsInterface constrain = (ConstraintsInterface) p;
if (!p.isEnabled(PluginBase.CONSTRAINTS)) continue;
constrain.isAMAModeEnabled(value);
}
return value;
}
@Override
public Constraint<Boolean> isSMBModeEnabled(Constraint<Boolean> value) {
ArrayList<PluginBase> constraintsPlugins = mainApp.getSpecificPluginsListByInterface(ConstraintsInterface.class);
for (PluginBase p : constraintsPlugins) {
ConstraintsInterface constraint = (ConstraintsInterface) p;
if (!p.isEnabled(PluginBase.CONSTRAINTS)) continue;
constraint.isSMBModeEnabled(value);
}
return value;
}
@Override
public Constraint<Boolean> isAdvancedFilteringEnabled(Constraint<Boolean> value) {
ArrayList<PluginBase> constraintsPlugins = mainApp.getSpecificPluginsListByInterface(ConstraintsInterface.class);
for (PluginBase p : constraintsPlugins) {
ConstraintsInterface constraint = (ConstraintsInterface) p;
if (!p.isEnabled(PluginBase.CONSTRAINTS)) continue;
constraint.isAdvancedFilteringEnabled(value);
}
return value;
}
@Override
public Constraint<Double> applyBasalConstraints(Constraint<Double> absoluteRate, Profile profile) {
ArrayList<PluginBase> constraintsPlugins = mainApp.getSpecificPluginsListByInterface(ConstraintsInterface.class);
for (PluginBase p : constraintsPlugins) {
ConstraintsInterface constraint = (ConstraintsInterface) p;
if (!p.isEnabled(PluginBase.CONSTRAINTS)) continue;
constraint.applyBasalConstraints(absoluteRate, profile);
}
return absoluteRate;
}
@Override
public Constraint<Integer> applyBasalPercentConstraints(Constraint<Integer> percentRate, Profile profile) {
ArrayList<PluginBase> constraintsPlugins = mainApp.getSpecificPluginsListByInterface(ConstraintsInterface.class);
for (PluginBase p : constraintsPlugins) {
ConstraintsInterface constrain = (ConstraintsInterface) p;
if (!p.isEnabled(PluginBase.CONSTRAINTS)) continue;
constrain.applyBasalPercentConstraints(percentRate, profile);
}
return percentRate;
}
@Override
public Constraint<Double> applyBolusConstraints(Constraint<Double> insulin) {
ArrayList<PluginBase> constraintsPlugins = mainApp.getSpecificPluginsListByInterface(ConstraintsInterface.class);
for (PluginBase p : constraintsPlugins) {
ConstraintsInterface constrain = (ConstraintsInterface) p;
if (!p.isEnabled(PluginBase.CONSTRAINTS)) continue;
constrain.applyBolusConstraints(insulin);
}
return insulin;
}
@Override
public Constraint<Integer> applyCarbsConstraints(Constraint<Integer> carbs) {
ArrayList<PluginBase> constraintsPlugins = mainApp.getSpecificPluginsListByInterface(ConstraintsInterface.class);
for (PluginBase p : constraintsPlugins) {
ConstraintsInterface constrain = (ConstraintsInterface) p;
if (!p.isEnabled(PluginBase.CONSTRAINTS)) continue;
constrain.applyCarbsConstraints(carbs);
}
return carbs;
}
@Override
public Constraint<Double> applyMaxIOBConstraints(Constraint<Double> maxIob) {
ArrayList<PluginBase> constraintsPlugins = mainApp.getSpecificPluginsListByInterface(ConstraintsInterface.class);
for (PluginBase p : constraintsPlugins) {
ConstraintsInterface constrain = (ConstraintsInterface) p;
if (!p.isEnabled(PluginBase.CONSTRAINTS)) continue;
constrain.applyMaxIOBConstraints(maxIob);
}
return maxIob;
}
}

View file

@ -16,7 +16,15 @@ import info.nightscout.androidaps.interfaces.Interval;
public abstract class Intervals<T extends Interval> { public abstract class Intervals<T extends Interval> {
LongSparseArray<T> rawData = new LongSparseArray<T>(); // oldest at index 0 LongSparseArray<T> rawData; // oldest at index 0
public Intervals() {
rawData = new LongSparseArray<T>();
}
public Intervals(LongSparseArray<T> data) {
rawData = data;
}
public synchronized Intervals reset() { public synchronized Intervals reset() {
rawData = new LongSparseArray<T>(); rawData = new LongSparseArray<T>();
@ -27,8 +35,7 @@ public abstract class Intervals<T extends Interval> {
/** /**
* The List must be sorted by `T.start()` in ascending order * The List must be sorted by `T.start()` in ascending order
* */
* */
public synchronized void add(List<T> list) { public synchronized void add(List<T> list) {
for (T interval : list) { for (T interval : list) {
rawData.put(interval.start(), interval); rawData.put(interval.start(), interval);
@ -37,7 +44,6 @@ public abstract class Intervals<T extends Interval> {
} }
public synchronized List<T> getList() { public synchronized List<T> getList() {
List<T> list = new ArrayList<>(); List<T> list = new ArrayList<>();
for (int i = 0; i < rawData.size(); i++) for (int i = 0; i < rawData.size(); i++)
@ -47,7 +53,7 @@ public abstract class Intervals<T extends Interval> {
public synchronized List<T> getReversedList() { public synchronized List<T> getReversedList() {
List<T> list = new ArrayList<>(); List<T> list = new ArrayList<>();
for (int i = rawData.size() -1; i>=0; i--) for (int i = rawData.size() - 1; i >= 0; i--)
list.add(rawData.valueAt(i)); list.add(rawData.valueAt(i));
return list; return list;
} }
@ -86,5 +92,4 @@ public abstract class Intervals<T extends Interval> {
} }
} }

View file

@ -2,7 +2,9 @@ package info.nightscout.androidaps.data;
import android.support.annotation.Nullable; import android.support.annotation.Nullable;
import android.support.v4.util.LongSparseArray;
import info.nightscout.androidaps.db.TemporaryBasal;
import info.nightscout.androidaps.interfaces.Interval; import info.nightscout.androidaps.interfaces.Interval;
/** /**
@ -11,6 +13,18 @@ import info.nightscout.androidaps.interfaces.Interval;
public class NonOverlappingIntervals<T extends Interval> extends Intervals<T> { public class NonOverlappingIntervals<T extends Interval> extends Intervals<T> {
public NonOverlappingIntervals() {
super();
}
public NonOverlappingIntervals(LongSparseArray<T> data) {
super(data);
}
public NonOverlappingIntervals (Intervals<T> other) {
rawData = other.rawData.clone();
}
protected synchronized void merge() { protected synchronized void merge() {
for (int index = 0; index < rawData.size() - 1; index++) { for (int index = 0; index < rawData.size() - 1; index++) {
Interval i = rawData.valueAt(index); Interval i = rawData.valueAt(index);
@ -27,4 +41,5 @@ public class NonOverlappingIntervals<T extends Interval> extends Intervals<T> {
if (index >= 0) return rawData.valueAt(index); if (index >= 0) return rawData.valueAt(index);
return null; return null;
} }
} }

View file

@ -22,7 +22,15 @@ import info.nightscout.utils.DateUtil;
public class ProfileIntervals<T extends Interval> { public class ProfileIntervals<T extends Interval> {
private static Logger log = LoggerFactory.getLogger(ProfileIntervals.class); private static Logger log = LoggerFactory.getLogger(ProfileIntervals.class);
private LongSparseArray<T> rawData = new LongSparseArray<>(); // oldest at index 0 private LongSparseArray<T> rawData; // oldest at index 0
public ProfileIntervals () {
rawData = new LongSparseArray<>();
}
public ProfileIntervals (ProfileIntervals<T> other) {
rawData = other.rawData.clone();
}
public synchronized ProfileIntervals reset() { public synchronized ProfileIntervals reset() {
rawData = new LongSparseArray<>(); rawData = new LongSparseArray<>();
@ -58,7 +66,7 @@ public class ProfileIntervals<T extends Interval> {
if (index >= 0) return rawData.valueAt(index); if (index >= 0) return rawData.valueAt(index);
// if we request data older than first record, use oldest instead // if we request data older than first record, use oldest instead
if (rawData.size() > 0) { if (rawData.size() > 0) {
log.debug("Requested profile for time: " + DateUtil.dateAndTimeString(time) + ". Providing oldest record: " + rawData.valueAt(0).toString()); //log.debug("Requested profile for time: " + DateUtil.dateAndTimeString(time) + ". Providing oldest record: " + rawData.valueAt(0).toString());
return rawData.valueAt(0); return rawData.valueAt(0);
} }
return null; return null;
@ -117,4 +125,9 @@ public class ProfileIntervals<T extends Interval> {
public synchronized T getReversed(int index) { public synchronized T getReversed(int index) {
return rawData.valueAt(size() - 1 - index); return rawData.valueAt(size() - 1 - index);
} }
@Override
public String toString() {
return rawData.toString();
}
} }

View file

@ -97,19 +97,23 @@ public class PumpEnactResult {
if (bolusDelivered > 0) { if (bolusDelivered > 0) {
ret += "\n" + MainApp.sResources.getString(R.string.enacted) + ": " + enacted; ret += "\n" + MainApp.sResources.getString(R.string.enacted) + ": " + enacted;
ret += "\n" + MainApp.sResources.getString(R.string.comment) + ": " + comment; ret += "\n" + MainApp.sResources.getString(R.string.comment) + ": " + comment;
ret += "\n" + MainApp.sResources.getString(R.string.smb_shortname) + ": " + bolusDelivered + "U"; ret += "\n" + MainApp.sResources.getString(R.string.smb_shortname)
+ ": " + bolusDelivered + " " + MainApp.gs(R.string.insulin_unit_shortname);
} else if (isTempCancel) { } else if (isTempCancel) {
ret += "\n" + MainApp.sResources.getString(R.string.enacted) + ": " + enacted; ret += "\n" + MainApp.sResources.getString(R.string.enacted) + ": " + enacted;
ret += "\n" + MainApp.sResources.getString(R.string.comment) + ": " + comment + "\n" + if (!comment.isEmpty())
MainApp.sResources.getString(R.string.canceltemp); ret += "\n" + MainApp.sResources.getString(R.string.comment) + ": " + comment;
ret += MainApp.sResources.getString(R.string.canceltemp);
} else if (isPercent) { } else if (isPercent) {
ret += "\n" + MainApp.sResources.getString(R.string.enacted) + ": " + enacted; ret += "\n" + MainApp.sResources.getString(R.string.enacted) + ": " + enacted;
ret += "\n" + MainApp.sResources.getString(R.string.comment) + ": " + comment; if (!comment.isEmpty())
ret += "\n" + MainApp.sResources.getString(R.string.comment) + ": " + comment;
ret += "\n" + MainApp.sResources.getString(R.string.duration) + ": " + duration + " min"; ret += "\n" + MainApp.sResources.getString(R.string.duration) + ": " + duration + " min";
ret += "\n" + MainApp.sResources.getString(R.string.percent) + ": " + percent + "%"; ret += "\n" + MainApp.sResources.getString(R.string.percent) + ": " + percent + "%";
} else { } else {
ret += "\n" + MainApp.sResources.getString(R.string.enacted) + ": " + enacted; ret += "\n" + MainApp.sResources.getString(R.string.enacted) + ": " + enacted;
ret += "\n" + MainApp.sResources.getString(R.string.comment) + ": " + comment; if (!comment.isEmpty())
ret += "\n" + MainApp.sResources.getString(R.string.comment) + ": " + comment;
ret += "\n" + MainApp.sResources.getString(R.string.duration) + ": " + duration + " min"; ret += "\n" + MainApp.sResources.getString(R.string.duration) + ": " + duration + " min";
ret += "\n" + MainApp.sResources.getString(R.string.absolute) + ": " + absolute + " U/h"; ret += "\n" + MainApp.sResources.getString(R.string.absolute) + ": " + absolute + " U/h";
} }
@ -126,26 +130,26 @@ public class PumpEnactResult {
} else if (enacted) { } else if (enacted) {
if (bolusDelivered > 0) { if (bolusDelivered > 0) {
ret += "<br><b>" + MainApp.sResources.getString(R.string.enacted) + "</b>: " + enacted; ret += "<br><b>" + MainApp.sResources.getString(R.string.enacted) + "</b>: " + enacted;
ret += "<br><b>" + MainApp.sResources.getString(R.string.comment) + "</b>: " + comment; if (!comment.isEmpty())
ret += "<br><b>" + MainApp.sResources.getString(R.string.smb_shortname) + "</b>: " + bolusDelivered + "U"; ret += "<br><b>" + MainApp.sResources.getString(R.string.comment) + "</b>: " + comment;
ret += "<br><b>" + MainApp.sResources.getString(R.string.smb_shortname) + "</b>: " + bolusDelivered + " " + MainApp.gs(R.string.insulin_unit_shortname);
} else if (isTempCancel) { } else if (isTempCancel) {
ret += "<br><b>" + MainApp.sResources.getString(R.string.enacted) + "</b>: " + enacted; ret += "<br><b>" + MainApp.sResources.getString(R.string.enacted) + "</b>: " + enacted;
ret += "<br><b>" + MainApp.sResources.getString(R.string.comment) + "</b>: " + comment + ret += "<br><b>" + MainApp.sResources.getString(R.string.comment) + "</b>: " + comment +
"<br>" + MainApp.sResources.getString(R.string.canceltemp); "<br>" + MainApp.sResources.getString(R.string.canceltemp);
} else if (isPercent && percent != -1) { } else if (isPercent && percent != -1) {
ret += "<br><b>" + MainApp.sResources.getString(R.string.enacted) + "</b>: " + enacted; ret += "<br><b>" + MainApp.sResources.getString(R.string.enacted) + "</b>: " + enacted;
ret += "<br><b>" + MainApp.sResources.getString(R.string.comment) + "</b>: " + comment; if (!comment.isEmpty())
ret += "<br><b>" + MainApp.sResources.getString(R.string.comment) + "</b>: " + comment;
ret += "<br><b>" + MainApp.sResources.getString(R.string.duration) + "</b>: " + duration + " min"; ret += "<br><b>" + MainApp.sResources.getString(R.string.duration) + "</b>: " + duration + " min";
ret += "<br><b>" + MainApp.sResources.getString(R.string.percent) + "</b>: " + percent + "%"; ret += "<br><b>" + MainApp.sResources.getString(R.string.percent) + "</b>: " + percent + "%";
} else if (absolute != -1) { } else if (absolute != -1) {
ret += "<br><b>" + MainApp.sResources.getString(R.string.enacted) + "</b>: " + enacted; ret += "<br><b>" + MainApp.sResources.getString(R.string.enacted) + "</b>: " + enacted;
ret += "<br><b>" + MainApp.sResources.getString(R.string.comment) + "</b>: " + comment; if (!comment.isEmpty())
ret += "<br><b>" + MainApp.sResources.getString(R.string.comment) + "</b>: " + comment;
ret += "<br><b>" + MainApp.sResources.getString(R.string.duration) + "</b>: " + duration + " min"; ret += "<br><b>" + MainApp.sResources.getString(R.string.duration) + "</b>: " + duration + " min";
ret += "<br><b>" + MainApp.sResources.getString(R.string.absolute) + "</b>: " + DecimalFormatter.to2Decimal(absolute) + " U/h"; ret += "<br><b>" + MainApp.sResources.getString(R.string.absolute) + "</b>: " + DecimalFormatter.to2Decimal(absolute) + " U/h";
} }
if (bolusDelivered > 0) {
ret += "<br><b>" + MainApp.sResources.getString(R.string.bolus) + "</b>: " + DecimalFormatter.to2Decimal(bolusDelivered) + " U";
}
} else { } else {
ret += "<br><b>" + MainApp.sResources.getString(R.string.comment) + "</b>: " + comment; ret += "<br><b>" + MainApp.sResources.getString(R.string.comment) + "</b>: " + comment;
} }

View file

@ -8,6 +8,7 @@ import android.support.annotation.Nullable;
import com.j256.ormlite.android.apptools.OrmLiteSqliteOpenHelper; import com.j256.ormlite.android.apptools.OrmLiteSqliteOpenHelper;
import com.j256.ormlite.dao.CloseableIterator; import com.j256.ormlite.dao.CloseableIterator;
import com.j256.ormlite.dao.Dao; import com.j256.ormlite.dao.Dao;
import com.j256.ormlite.dao.DaoManager;
import com.j256.ormlite.stmt.PreparedQuery; import com.j256.ormlite.stmt.PreparedQuery;
import com.j256.ormlite.stmt.QueryBuilder; import com.j256.ormlite.stmt.QueryBuilder;
import com.j256.ormlite.stmt.Where; import com.j256.ormlite.stmt.Where;
@ -246,7 +247,7 @@ public class DatabaseHelper extends OrmLiteSqliteOpenHelper {
log.error("Unhandled exception", e); log.error("Unhandled exception", e);
} }
VirtualPumpPlugin.setFakingStatus(true); VirtualPumpPlugin.setFakingStatus(true);
scheduleBgChange(null, false, false); // trigger refresh scheduleBgChange(null); // trigger refresh
scheduleTemporaryBasalChange(); scheduleTemporaryBasalChange();
scheduleTreatmentChange(null); scheduleTreatmentChange(null);
scheduleExtendedBolusChange(); scheduleExtendedBolusChange();
@ -384,14 +385,14 @@ public class DatabaseHelper extends OrmLiteSqliteOpenHelper {
} }
// ------------------- BgReading handling ----------------------- // ------------------- BgReading handling -----------------------
public boolean createIfNotExists(BgReading bgReading, String from, boolean isFromActiveBgSource) { public boolean createIfNotExists(BgReading bgReading, String from) {
try { try {
bgReading.date = roundDateToSec(bgReading.date); bgReading.date = roundDateToSec(bgReading.date);
BgReading old = getDaoBgReadings().queryForId(bgReading.date); BgReading old = getDaoBgReadings().queryForId(bgReading.date);
if (old == null) { if (old == null) {
getDaoBgReadings().create(bgReading); getDaoBgReadings().create(bgReading);
log.debug("BG: New record from: " + from + " " + bgReading.toString()); log.debug("BG: New record from: " + from + " " + bgReading.toString());
scheduleBgChange(bgReading, true, isFromActiveBgSource); scheduleBgChange(bgReading);
return true; return true;
} }
if (!old.isEqual(bgReading)) { if (!old.isEqual(bgReading)) {
@ -399,7 +400,7 @@ public class DatabaseHelper extends OrmLiteSqliteOpenHelper {
old.copyFrom(bgReading); old.copyFrom(bgReading);
getDaoBgReadings().update(old); getDaoBgReadings().update(old);
log.debug("BG: Updating record from: " + from + " New data: " + old.toString()); log.debug("BG: Updating record from: " + from + " New data: " + old.toString());
scheduleBgChange(bgReading, false, isFromActiveBgSource); scheduleBgChange(bgReading);
return false; return false;
} }
} catch (SQLException e) { } catch (SQLException e) {
@ -417,11 +418,11 @@ public class DatabaseHelper extends OrmLiteSqliteOpenHelper {
} }
} }
private static void scheduleBgChange(@Nullable final BgReading bgReading, boolean isNew, boolean isFromActiveBgSource) { private static void scheduleBgChange(@Nullable final BgReading bgReading) {
class PostRunnable implements Runnable { class PostRunnable implements Runnable {
public void run() { public void run() {
log.debug("Firing EventNewBg"); log.debug("Firing EventNewBg");
MainApp.bus().post(new EventNewBG(bgReading, isNew, isFromActiveBgSource)); MainApp.bus().post(new EventNewBG(bgReading));
scheduledBgPost = null; scheduledBgPost = null;
} }
} }

View file

@ -128,7 +128,7 @@ public class Treatment implements DataPointWithLabelInterface {
@Override @Override
public String getLabel() { public String getLabel() {
String label = ""; String label = "";
if (insulin > 0) label += DecimalFormatter.to2Decimal(insulin) + "U"; if (insulin > 0) label += DecimalFormatter.toPumpSupportedBolus(insulin) + "U";
if (carbs > 0) if (carbs > 0)
label += "~" + DecimalFormatter.to0Decimal(carbs) + "g"; label += "~" + DecimalFormatter.to0Decimal(carbs) + "g";
return label; return label;
@ -149,7 +149,7 @@ public class Treatment implements DataPointWithLabelInterface {
@Override @Override
public float getSize() { public float getSize() {
return 10; return 2;
} }
@Override @Override

View file

@ -10,17 +10,8 @@ import info.nightscout.androidaps.db.BgReading;
public class EventNewBG extends EventLoop { public class EventNewBG extends EventLoop {
@Nullable @Nullable
public final BgReading bgReading; public final BgReading bgReading;
public final boolean isNew;
public final boolean isFromActiveBgSource;
/** Whether the BgReading is current (enough to use for treatment decisions). */ public EventNewBG(BgReading bgReading) {
public boolean isCurrent() {
return bgReading != null && bgReading.date + 9 * 60 * 1000 > System.currentTimeMillis();
}
public EventNewBG(@Nullable BgReading bgReading, boolean isNew, boolean isFromActiveBgSource) {
this.bgReading = bgReading; this.bgReading = bgReading;
this.isNew = isNew;
this.isFromActiveBgSource = isFromActiveBgSource;
} }
} }

View file

@ -0,0 +1,117 @@
package info.nightscout.androidaps.interfaces;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import java.util.ArrayList;
import java.util.List;
/**
* Created by mike on 19.03.2018.
*/
public class Constraint<T extends Comparable> {
private static Logger log = LoggerFactory.getLogger(Constraint.class);
T value;
T originalValue;
List<String> reasons = new ArrayList<>();
List<String> mostLimiting = new ArrayList<>();
public Constraint(T value) {
this.value = value;
this.originalValue = value;
}
public T value() {
return value;
}
public T originalValue() {
return originalValue;
}
public Constraint<T> set(T value) {
this.value = value;
this.originalValue = value;
return this;
}
public Constraint<T> set(T value, String reason, Object from) {
this.value = value;
addReason(reason, from);
addMostLimingReason(reason, from);
return this;
}
public Constraint<T> setIfSmaller(T value, String reason, Object from) {
if (value.compareTo(this.value) < 0) {
this.value = value;
mostLimiting.clear();
addMostLimingReason(reason, from);
}
if (value.compareTo(this.originalValue) < 0) {
addReason(reason, from);
}
return this;
}
public Constraint<T> setIfGreater(T value, String reason, Object from) {
if (value.compareTo(this.value) > 0) {
this.value = value;
mostLimiting.clear();
addMostLimingReason(reason, from);
}
if (value.compareTo(this.originalValue) > 0) {
addReason(reason, from);
}
return this;
}
public Constraint addReason(String reason, Object from) {
reasons.add(from.getClass().getSimpleName().replace("Plugin", "") + ": " + reason);
return this;
}
public Constraint addMostLimingReason(String reason, Object from) {
mostLimiting.add(from.getClass().getSimpleName().replace("Plugin", "") + ": " + reason);
return this;
}
public String getReasons() {
StringBuilder sb = new StringBuilder();
int count = 0;
for (String r : reasons) {
if (count++ != 0) sb.append("\n");
sb.append(r);
}
log.debug("Limiting origial value: " + originalValue + " to " + value + ". Reason: " + sb.toString());
return sb.toString();
}
public List<String> getReasonList() {
return reasons;
}
public String getMostLimitedReasons() {
StringBuilder sb = new StringBuilder();
int count = 0;
for (String r : mostLimiting) {
if (count++ != 0) sb.append("\n");
sb.append(r);
}
log.debug("Limiting origial value: " + originalValue + " to " + value + ". Reason: " + sb.toString());
return sb.toString();
}
public List<String> getMostLimitedReasonList() {
return mostLimiting;
}
public void copyReasons(Constraint<?> another) {
for (String s: another.getReasonList()) {
reasons.add(s);
}
}
}

View file

@ -1,30 +1,54 @@
package info.nightscout.androidaps.interfaces; package info.nightscout.androidaps.interfaces;
import info.nightscout.androidaps.plugins.Loop.APSResult; import info.nightscout.androidaps.data.Profile;
/** /**
* Created by mike on 15.06.2016. * Created by mike on 15.06.2016.
*/ */
public interface ConstraintsInterface { public interface ConstraintsInterface {
boolean isLoopEnabled(); default Constraint<Boolean> isLoopInvokationAllowed(Constraint<Boolean> value) {
return value;
}
boolean isClosedModeEnabled(); default Constraint<Boolean> isClosedLoopAllowed(Constraint<Boolean> value) {
return value;
}
boolean isAutosensModeEnabled(); default Constraint<Boolean> isAutosensModeEnabled(Constraint<Boolean> value) {
return value;
}
boolean isAMAModeEnabled(); default Constraint<Boolean> isAMAModeEnabled(Constraint<Boolean> value) {
return value;
}
boolean isSMBModeEnabled(); default Constraint<Boolean> isSMBModeEnabled(Constraint<Boolean> value) {
return value;
}
Double applyBasalConstraints(Double absoluteRate); default Constraint<Boolean> isAdvancedFilteringEnabled(Constraint<Boolean> value) {
return value;
}
Integer applyBasalConstraints(Integer percentRate); default Constraint<Double> applyBasalConstraints(Constraint<Double> absoluteRate, Profile profile) {
return absoluteRate;
}
Double applyBolusConstraints(Double insulin); default Constraint<Integer> applyBasalPercentConstraints(Constraint<Integer> percentRate, Profile profile) {
return percentRate;
}
Integer applyCarbsConstraints(Integer carbs); default Constraint<Double> applyBolusConstraints(Constraint<Double> insulin) {
return insulin;
}
Double applyMaxIOBConstraints(Double maxIob); default Constraint<Integer> applyCarbsConstraints(Constraint<Integer> carbs) {
return carbs;
}
default Constraint<Double> applyMaxIOBConstraints(Constraint<Double> maxIob) {
return maxIob;
};
} }

View file

@ -28,7 +28,7 @@ public interface PluginBase {
boolean canBeHidden(int type); boolean canBeHidden(int type);
boolean hasFragment(); boolean hasFragment();
boolean showInList(int type); boolean showInList(int type);
void setFragmentEnabled(int type, boolean fragmentEnabled); void setPluginEnabled(int type, boolean fragmentEnabled);
void setFragmentVisible(int type, boolean fragmentVisible); void setFragmentVisible(int type, boolean fragmentVisible);
int getPreferencesId(); int getPreferencesId();
} }

View file

@ -35,8 +35,8 @@ public interface PumpInterface {
PumpEnactResult deliverTreatment(DetailedBolusInfo detailedBolusInfo); PumpEnactResult deliverTreatment(DetailedBolusInfo detailedBolusInfo);
void stopBolusDelivering(); void stopBolusDelivering();
PumpEnactResult setTempBasalAbsolute(Double absoluteRate, Integer durationInMinutes, boolean enforceNew); PumpEnactResult setTempBasalAbsolute(Double absoluteRate, Integer durationInMinutes, Profile profile, boolean enforceNew);
PumpEnactResult setTempBasalPercent(Integer percent, Integer durationInMinutes, boolean enforceNew); PumpEnactResult setTempBasalPercent(Integer percent, Integer durationInMinutes, Profile profile, boolean enforceNew);
PumpEnactResult setExtendedBolus(Double insulin, Integer durationInMinutes); PumpEnactResult setExtendedBolus(Double insulin, Integer durationInMinutes);
//some pumps might set a very short temp close to 100% as cancelling a temp can be noisy //some pumps might set a very short temp close to 100% as cancelling a temp can be noisy
//when the cancel request is requested by the user (forced), the pump should always do a real cancel //when the cancel request is requested by the user (forced), the pump should always do a real cancel

View file

@ -126,7 +126,7 @@ public class ActionsFragment extends SubscriberFragment implements View.OnClickL
activity.runOnUiThread(new Runnable() { activity.runOnUiThread(new Runnable() {
@Override @Override
public void run() { public void run() {
if (MainApp.getConfigBuilder().getActiveProfileInterface().getProfile() == null) { if (MainApp.getConfigBuilder().getProfile() == null) {
tempTarget.setVisibility(View.GONE); tempTarget.setVisibility(View.GONE);
profileSwitch.setVisibility(View.GONE); profileSwitch.setVisibility(View.GONE);
extendedBolus.setVisibility(View.GONE); extendedBolus.setVisibility(View.GONE);

View file

@ -65,7 +65,7 @@ public class ActionsPlugin implements PluginBase {
} }
@Override @Override
public void setFragmentEnabled(int type, boolean fragmentEnabled) { public void setPluginEnabled(int type, boolean fragmentEnabled) {
if (type == GENERAL) this.fragmentEnabled = fragmentEnabled; if (type == GENERAL) this.fragmentEnabled = fragmentEnabled;
} }

View file

@ -1,11 +1,11 @@
package info.nightscout.androidaps.plugins.Actions.dialogs; package info.nightscout.androidaps.plugins.Actions.dialogs;
import android.content.Context; import android.content.Context;
import android.content.DialogInterface;
import android.content.Intent; import android.content.Intent;
import android.os.Bundle; import android.os.Bundle;
import android.support.v4.app.DialogFragment; import android.support.v4.app.DialogFragment;
import android.support.v7.app.AlertDialog; import android.support.v7.app.AlertDialog;
import android.text.Html;
import android.view.LayoutInflater; import android.view.LayoutInflater;
import android.view.View; import android.view.View;
import android.view.View.OnClickListener; import android.view.View.OnClickListener;
@ -13,24 +13,31 @@ import android.view.ViewGroup;
import android.view.Window; import android.view.Window;
import android.view.WindowManager; import android.view.WindowManager;
import android.widget.Button; import android.widget.Button;
import android.widget.CheckBox;
import com.crashlytics.android.answers.CustomEvent; import com.crashlytics.android.answers.CustomEvent;
import com.google.common.base.Joiner;
import org.slf4j.Logger; import org.slf4j.Logger;
import org.slf4j.LoggerFactory; import org.slf4j.LoggerFactory;
import java.text.DecimalFormat;
import info.nightscout.androidaps.Constants; import info.nightscout.androidaps.Constants;
import java.text.DecimalFormat;
import java.util.LinkedList;
import java.util.List;
import info.nightscout.androidaps.MainApp; import info.nightscout.androidaps.MainApp;
import info.nightscout.androidaps.R; import info.nightscout.androidaps.R;
import info.nightscout.androidaps.data.DetailedBolusInfo; import info.nightscout.androidaps.data.DetailedBolusInfo;
import info.nightscout.androidaps.db.CareportalEvent;
import info.nightscout.androidaps.db.Source; import info.nightscout.androidaps.db.Source;
import info.nightscout.androidaps.interfaces.Constraint;
import info.nightscout.androidaps.plugins.ConfigBuilder.ConfigBuilderPlugin; import info.nightscout.androidaps.plugins.ConfigBuilder.ConfigBuilderPlugin;
import info.nightscout.androidaps.plugins.Overview.Dialogs.ErrorHelperActivity; import info.nightscout.androidaps.plugins.Overview.Dialogs.ErrorHelperActivity;
import info.nightscout.androidaps.queue.Callback; import info.nightscout.androidaps.queue.Callback;
import info.nightscout.utils.DecimalFormatter; import info.nightscout.utils.DecimalFormatter;
import info.nightscout.utils.FabricPrivacy; import info.nightscout.utils.FabricPrivacy;
import info.nightscout.utils.NSUpload;
import info.nightscout.utils.NumberPicker; import info.nightscout.utils.NumberPicker;
import info.nightscout.utils.SP; import info.nightscout.utils.SP;
import info.nightscout.utils.SafeParse; import info.nightscout.utils.SafeParse;
@ -38,13 +45,13 @@ import info.nightscout.utils.SafeParse;
public class FillDialog extends DialogFragment implements OnClickListener { public class FillDialog extends DialogFragment implements OnClickListener {
private static Logger log = LoggerFactory.getLogger(FillDialog.class); private static Logger log = LoggerFactory.getLogger(FillDialog.class);
Button deliverButton;
double amount1 = 0d; double amount1 = 0d;
double amount2 = 0d; double amount2 = 0d;
double amount3 = 0d; double amount3 = 0d;
NumberPicker editInsulin; NumberPicker editInsulin;
CheckBox pumpSiteChangeCheckbox;
CheckBox insulinCartridgeChangeCheckbox;
public FillDialog() { public FillDialog() {
} }
@ -54,22 +61,24 @@ public class FillDialog extends DialogFragment implements OnClickListener {
Bundle savedInstanceState) { Bundle savedInstanceState) {
View view = inflater.inflate(R.layout.actions_fill_dialog, null, false); View view = inflater.inflate(R.layout.actions_fill_dialog, null, false);
deliverButton = (Button) view.findViewById(R.id.treatments_newtreatment_deliverbutton); view.findViewById(R.id.ok).setOnClickListener(this);
view.findViewById(R.id.cancel).setOnClickListener(this);
deliverButton.setOnClickListener(this);
getDialog().getWindow().requestFeature(Window.FEATURE_NO_TITLE); getDialog().getWindow().requestFeature(Window.FEATURE_NO_TITLE);
getDialog().getWindow().setSoftInputMode(WindowManager.LayoutParams.SOFT_INPUT_STATE_HIDDEN); getDialog().getWindow().setSoftInputMode(WindowManager.LayoutParams.SOFT_INPUT_STATE_HIDDEN);
Double maxInsulin = MainApp.getConfigBuilder().applyBolusConstraints(Constants.bolusOnlyForCheckLimit); pumpSiteChangeCheckbox = view.findViewById(R.id.catheter_change);
insulinCartridgeChangeCheckbox = view.findViewById(R.id.cartridge_change);
Double maxInsulin = MainApp.getConstraintChecker().getMaxBolusAllowed().value();
double bolusstep = ConfigBuilderPlugin.getActivePump().getPumpDescription().bolusStep; double bolusstep = ConfigBuilderPlugin.getActivePump().getPumpDescription().bolusStep;
editInsulin = (NumberPicker) view.findViewById(R.id.treatments_newtreatment_insulinamount); editInsulin = view.findViewById(R.id.treatments_newtreatment_insulinamount);
editInsulin.setParams(0d, 0d, maxInsulin, bolusstep, new DecimalFormat("0.00"), false); editInsulin.setParams(0d, 0d, maxInsulin, bolusstep, DecimalFormatter.pumpSupportedBolusFormat(), false);
//setup preset buttons //setup preset buttons
Button button1 = (Button) view.findViewById(R.id.fill_preset_button1); Button button1 = (Button) view.findViewById(R.id.fill_preset_button1);
Button button2 = (Button) view.findViewById(R.id.fill_preset_button2); Button button2 = (Button) view.findViewById(R.id.fill_preset_button2);
Button button3 = (Button) view.findViewById(R.id.fill_preset_button3); Button button3 = (Button) view.findViewById(R.id.fill_preset_button3);
View divider = view.findViewById(R.id.fill_preset_divider);
amount1 = SP.getDouble("fill_button1", 0.3); amount1 = SP.getDouble("fill_button1", 0.3);
amount2 = SP.getDouble("fill_button2", 0d); amount2 = SP.getDouble("fill_button2", 0d);
@ -77,103 +86,109 @@ public class FillDialog extends DialogFragment implements OnClickListener {
if (amount1 > 0) { if (amount1 > 0) {
button1.setVisibility(View.VISIBLE); button1.setVisibility(View.VISIBLE);
button1.setText(DecimalFormatter.to2Decimal(amount1) + "U"); button1.setText(DecimalFormatter.toPumpSupportedBolus(amount1)); // + "U");
button1.setOnClickListener(this); button1.setOnClickListener(this);
} else { } else {
button1.setVisibility(View.GONE); button1.setVisibility(View.GONE);
} }
if (amount2 > 0) { if (amount2 > 0) {
button2.setVisibility(View.VISIBLE); button2.setVisibility(View.VISIBLE);
button2.setText(DecimalFormatter.to2Decimal(amount2) + "U"); button2.setText(DecimalFormatter.toPumpSupportedBolus(amount2)); // + "U");
button2.setOnClickListener(this); button2.setOnClickListener(this);
} else { } else {
button2.setVisibility(View.GONE); button2.setVisibility(View.GONE);
} }
if (amount3 > 0) { if (amount3 > 0) {
button3.setVisibility(View.VISIBLE); button3.setVisibility(View.VISIBLE);
button3.setText(DecimalFormatter.to2Decimal(amount3) + "U"); button3.setText(DecimalFormatter.toPumpSupportedBolus(amount3)); // + "U");
button3.setOnClickListener(this); button3.setOnClickListener(this);
} else { } else {
button3.setVisibility(View.GONE); button3.setVisibility(View.GONE);
} }
if (button1.getVisibility() == View.GONE && button2.getVisibility() == View.GONE && button3.getVisibility() == View.GONE) {
divider.setVisibility(View.GONE);
}
setCancelable(true); setCancelable(true);
getDialog().setCanceledOnTouchOutside(false); getDialog().setCanceledOnTouchOutside(false);
return view; return view;
} }
@Override
public void onResume() {
super.onResume();
if (getDialog() != null)
getDialog().getWindow().setLayout(ViewGroup.LayoutParams.MATCH_PARENT, ViewGroup.LayoutParams.WRAP_CONTENT);
}
@Override @Override
public void onClick(View view) { public void onClick(View view) {
switch (view.getId()) { switch (view.getId()) {
case R.id.treatments_newtreatment_deliverbutton: case R.id.ok:
Double insulin = SafeParse.stringToDouble(editInsulin.getText().toString()); confirmAndDeliver();
confirmAndDeliver(insulin); break;
case R.id.cancel:
dismiss();
break; break;
case R.id.fill_preset_button1: case R.id.fill_preset_button1:
confirmAndDeliver(amount1); editInsulin.setValue(amount1);
break; break;
case R.id.fill_preset_button2: case R.id.fill_preset_button2:
confirmAndDeliver(amount2); editInsulin.setValue(amount2);
break; break;
case R.id.fill_preset_button3: case R.id.fill_preset_button3:
confirmAndDeliver(amount3); editInsulin.setValue(amount3);
break; break;
} }
} }
private void confirmAndDeliver(Double insulin) { private void confirmAndDeliver() {
try { try {
Double insulin = SafeParse.stringToDouble(editInsulin.getText());
String confirmMessage = getString(R.string.fillwarning) + "\n"; List<String> confirmMessage = new LinkedList<>();
Double insulinAfterConstraints = MainApp.getConfigBuilder().applyBolusConstraints(insulin); Double insulinAfterConstraints = MainApp.getConstraintChecker().applyBolusConstraints(new Constraint<>(insulin)).value();
confirmMessage += getString(R.string.bolus) + ": " + insulinAfterConstraints + "U"; if (insulinAfterConstraints > 0) {
if (insulinAfterConstraints - insulin != 0) confirmMessage.add(MainApp.gs(R.string.fillwarning));
confirmMessage += "\n" + getString(R.string.constraintapllied); confirmMessage.add("");
confirmMessage.add(MainApp.gs(R.string.bolus) + ": " + "<font color='" + MainApp.gc(R.color.colorCarbsButton) + "'>" + insulinAfterConstraints + "U" + "</font>");
if (!insulinAfterConstraints.equals(insulin))
confirmMessage.add("<font color='" + MainApp.sResources.getColor(R.color.low) + "'>" + MainApp.gs(R.string.bolusconstraintapplied) + "</font>");
}
if (pumpSiteChangeCheckbox.isChecked())
confirmMessage.add("" + "<font color='" + MainApp.sResources.getColor(R.color.high) + "'>" + getString(R.string.record_pump_site_change) + "</font>");
if (insulinCartridgeChangeCheckbox.isChecked())
confirmMessage.add("" + "<font color='" + MainApp.sResources.getColor(R.color.high) + "'>" + getString(R.string.record_insulin_cartridge_change) + "</font>");
final Double finalInsulinAfterConstraints = insulinAfterConstraints; final Double finalInsulinAfterConstraints = insulinAfterConstraints;
final Context context = getContext(); final Context context = getContext();
AlertDialog.Builder builder = new AlertDialog.Builder(context); AlertDialog.Builder builder = new AlertDialog.Builder(context);
builder.setTitle(this.getContext().getString(R.string.confirmation)); if (confirmMessage.isEmpty())
builder.setMessage(confirmMessage); confirmMessage.add(MainApp.gs(R.string.no_action_selected));
builder.setPositiveButton(getString(R.string.primefill), new DialogInterface.OnClickListener() {
public void onClick(DialogInterface dialog, int id) { builder.setTitle(MainApp.gs(R.string.confirmation));
if (finalInsulinAfterConstraints > 0) { builder.setMessage(Html.fromHtml(Joiner.on("<br/>").join(confirmMessage)));
DetailedBolusInfo detailedBolusInfo = new DetailedBolusInfo(); builder.setPositiveButton(getString(R.string.primefill), (dialog, id) -> {
detailedBolusInfo.insulin = finalInsulinAfterConstraints; if (finalInsulinAfterConstraints > 0) {
detailedBolusInfo.context = context; DetailedBolusInfo detailedBolusInfo = new DetailedBolusInfo();
detailedBolusInfo.source = Source.USER; detailedBolusInfo.insulin = finalInsulinAfterConstraints;
detailedBolusInfo.isValid = false; // do not count it in IOB (for pump history) detailedBolusInfo.context = context;
ConfigBuilderPlugin.getCommandQueue().bolus(detailedBolusInfo, new Callback() { detailedBolusInfo.source = Source.USER;
@Override detailedBolusInfo.isValid = false; // do not count it in IOB (for pump history)
public void run() { ConfigBuilderPlugin.getCommandQueue().bolus(detailedBolusInfo, new Callback() {
if (!result.success) { @Override
Intent i = new Intent(MainApp.instance(), ErrorHelperActivity.class); public void run() {
i.putExtra("soundid", R.raw.boluserror); if (!result.success) {
i.putExtra("status", result.comment); Intent i = new Intent(MainApp.instance(), ErrorHelperActivity.class);
i.putExtra("title", MainApp.sResources.getString(R.string.treatmentdeliveryerror)); i.putExtra("soundid", R.raw.boluserror);
i.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK); i.putExtra("status", result.comment);
MainApp.instance().startActivity(i); i.putExtra("title", MainApp.sResources.getString(R.string.treatmentdeliveryerror));
} i.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
MainApp.instance().startActivity(i);
} }
}); }
FabricPrivacy.getInstance().logCustom(new CustomEvent("Fill")); });
} FabricPrivacy.getInstance().logCustom(new CustomEvent("Fill"));
} }
long now = System.currentTimeMillis();
if (pumpSiteChangeCheckbox.isChecked()) NSUpload.uploadEvent(CareportalEvent.SITECHANGE, now);
if (insulinCartridgeChangeCheckbox.isChecked()) NSUpload.uploadEvent(CareportalEvent.INSULINCHANGE, now + 1000);
}); });
builder.setNegativeButton(getString(R.string.cancel), null); builder.setNegativeButton(getString(R.string.cancel), null);
builder.show(); builder.show();

View file

@ -17,9 +17,9 @@ import org.slf4j.LoggerFactory;
import java.text.DecimalFormat; import java.text.DecimalFormat;
import info.nightscout.androidaps.Constants;
import info.nightscout.androidaps.MainApp; import info.nightscout.androidaps.MainApp;
import info.nightscout.androidaps.R; import info.nightscout.androidaps.R;
import info.nightscout.androidaps.interfaces.Constraint;
import info.nightscout.androidaps.plugins.ConfigBuilder.ConfigBuilderPlugin; import info.nightscout.androidaps.plugins.ConfigBuilder.ConfigBuilderPlugin;
import info.nightscout.androidaps.plugins.Overview.Dialogs.ErrorHelperActivity; import info.nightscout.androidaps.plugins.Overview.Dialogs.ErrorHelperActivity;
import info.nightscout.androidaps.queue.Callback; import info.nightscout.androidaps.queue.Callback;
@ -43,7 +43,7 @@ public class NewExtendedBolusDialog extends DialogFragment implements View.OnCli
View view = inflater.inflate(R.layout.overview_newextendedbolus_dialog, container, false); View view = inflater.inflate(R.layout.overview_newextendedbolus_dialog, container, false);
Double maxInsulin = MainApp.getConfigBuilder().applyBolusConstraints(Constants.bolusOnlyForCheckLimit); Double maxInsulin = MainApp.getConstraintChecker().getMaxBolusAllowed().value();
editInsulin = (NumberPicker) view.findViewById(R.id.overview_newextendedbolus_insulin); editInsulin = (NumberPicker) view.findViewById(R.id.overview_newextendedbolus_insulin);
editInsulin.setParams(0d, 0d, maxInsulin, 0.1d, new DecimalFormat("0.00"), false); editInsulin.setParams(0d, 0d, maxInsulin, 0.1d, new DecimalFormat("0.00"), false);
@ -70,7 +70,7 @@ public class NewExtendedBolusDialog extends DialogFragment implements View.OnCli
String confirmMessage = getString(R.string.setextendedbolusquestion); String confirmMessage = getString(R.string.setextendedbolusquestion);
Double insulinAfterConstraint = MainApp.getConfigBuilder().applyBolusConstraints(insulin); Double insulinAfterConstraint = MainApp.getConstraintChecker().applyBolusConstraints(new Constraint<>(insulin)).value();
confirmMessage += " " + insulinAfterConstraint + " U "; confirmMessage += " " + insulinAfterConstraint + " U ";
confirmMessage += getString(R.string.duration) + " " + durationInMinutes + "min ?"; confirmMessage += getString(R.string.duration) + " " + durationInMinutes + "min ?";
if (insulinAfterConstraint - insulin != 0d) if (insulinAfterConstraint - insulin != 0d)

View file

@ -22,6 +22,7 @@ import java.text.DecimalFormat;
import info.nightscout.androidaps.MainApp; import info.nightscout.androidaps.MainApp;
import info.nightscout.androidaps.R; import info.nightscout.androidaps.R;
import info.nightscout.androidaps.data.Profile; import info.nightscout.androidaps.data.Profile;
import info.nightscout.androidaps.interfaces.Constraint;
import info.nightscout.androidaps.interfaces.PumpDescription; import info.nightscout.androidaps.interfaces.PumpDescription;
import info.nightscout.androidaps.plugins.ConfigBuilder.ConfigBuilderPlugin; import info.nightscout.androidaps.plugins.ConfigBuilder.ConfigBuilderPlugin;
import info.nightscout.androidaps.plugins.Overview.Dialogs.ErrorHelperActivity; import info.nightscout.androidaps.plugins.Overview.Dialogs.ErrorHelperActivity;
@ -117,17 +118,21 @@ public class NewTempBasalDialog extends DialogFragment implements View.OnClickLi
final boolean setAsPercent = percentRadio.isChecked(); final boolean setAsPercent = percentRadio.isChecked();
int durationInMinutes = SafeParse.stringToInt(duration.getText()); int durationInMinutes = SafeParse.stringToInt(duration.getText());
Profile profile = MainApp.getConfigBuilder().getProfile();
if (profile == null)
return;
String confirmMessage = getString(R.string.setbasalquestion); String confirmMessage = getString(R.string.setbasalquestion);
if (setAsPercent) { if (setAsPercent) {
int basalPercentInput = SafeParse.stringToInt(basalPercent.getText()); int basalPercentInput = SafeParse.stringToInt(basalPercent.getText());
percent = MainApp.getConfigBuilder().applyBasalConstraints(basalPercentInput); percent = MainApp.getConstraintChecker().applyBasalPercentConstraints(new Constraint<>(basalPercentInput), profile).value();
confirmMessage += "\n" + percent + "% "; confirmMessage += "\n" + percent + "% ";
confirmMessage += "\n" + getString(R.string.duration) + " " + durationInMinutes + "min ?"; confirmMessage += "\n" + getString(R.string.duration) + " " + durationInMinutes + "min ?";
if (percent != basalPercentInput) if (percent != basalPercentInput)
confirmMessage += "\n" + getString(R.string.constraintapllied); confirmMessage += "\n" + getString(R.string.constraintapllied);
} else { } else {
Double basalAbsoluteInput = SafeParse.stringToDouble(basalAbsolute.getText()); Double basalAbsoluteInput = SafeParse.stringToDouble(basalAbsolute.getText());
absolute = MainApp.getConfigBuilder().applyBasalConstraints(basalAbsoluteInput); absolute = MainApp.getConstraintChecker().applyBasalConstraints(new Constraint<>(basalAbsoluteInput), profile).value();
confirmMessage += "\n" + absolute + " U/h "; confirmMessage += "\n" + absolute + " U/h ";
confirmMessage += "\n" + getString(R.string.duration) + " " + durationInMinutes + "min ?"; confirmMessage += "\n" + getString(R.string.duration) + " " + durationInMinutes + "min ?";
if (absolute - basalAbsoluteInput != 0d) if (absolute - basalAbsoluteInput != 0d)
@ -157,9 +162,9 @@ public class NewTempBasalDialog extends DialogFragment implements View.OnClickLi
} }
}; };
if (setAsPercent) { if (setAsPercent) {
ConfigBuilderPlugin.getCommandQueue().tempBasalPercent(finalBasalPercent, finalDurationInMinutes, true, callback); ConfigBuilderPlugin.getCommandQueue().tempBasalPercent(finalBasalPercent, finalDurationInMinutes, true, profile, callback);
} else { } else {
ConfigBuilderPlugin.getCommandQueue().tempBasalAbsolute(finalBasal, finalDurationInMinutes, true, callback); ConfigBuilderPlugin.getCommandQueue().tempBasalAbsolute(finalBasal, finalDurationInMinutes, true, profile, callback);
} }
FabricPrivacy.getInstance().logCustom(new CustomEvent("TempBasal")); FabricPrivacy.getInstance().logCustom(new CustomEvent("TempBasal"));
} }

View file

@ -71,7 +71,7 @@ public class CareportalPlugin implements PluginBase {
} }
@Override @Override
public void setFragmentEnabled(int type, boolean fragmentEnabled) { public void setPluginEnabled(int type, boolean fragmentEnabled) {
if (type == GENERAL) this.fragmentEnabled = fragmentEnabled; if (type == GENERAL) this.fragmentEnabled = fragmentEnabled;
} }

View file

@ -51,15 +51,16 @@ import info.nightscout.androidaps.db.ProfileSwitch;
import info.nightscout.androidaps.db.Source; import info.nightscout.androidaps.db.Source;
import info.nightscout.androidaps.db.TempTarget; import info.nightscout.androidaps.db.TempTarget;
import info.nightscout.androidaps.events.EventNewBasalProfile; import info.nightscout.androidaps.events.EventNewBasalProfile;
import info.nightscout.androidaps.interfaces.Constraint;
import info.nightscout.androidaps.plugins.Careportal.OptionsToShow; import info.nightscout.androidaps.plugins.Careportal.OptionsToShow;
import info.nightscout.androidaps.plugins.ConfigBuilder.ConfigBuilderPlugin; import info.nightscout.androidaps.plugins.ConfigBuilder.ConfigBuilderPlugin;
import info.nightscout.androidaps.plugins.Overview.Dialogs.ErrorHelperActivity; import info.nightscout.androidaps.plugins.Overview.Dialogs.ErrorHelperActivity;
import info.nightscout.androidaps.queue.Callback; import info.nightscout.androidaps.queue.Callback;
import info.nightscout.utils.FabricPrivacy;
import info.nightscout.utils.DateUtil; import info.nightscout.utils.DateUtil;
import info.nightscout.utils.FabricPrivacy;
import info.nightscout.utils.HardLimits;
import info.nightscout.utils.NSUpload; import info.nightscout.utils.NSUpload;
import info.nightscout.utils.NumberPicker; import info.nightscout.utils.NumberPicker;
import info.nightscout.utils.OKDialog;
import info.nightscout.utils.SP; import info.nightscout.utils.SP;
import info.nightscout.utils.SafeParse; import info.nightscout.utils.SafeParse;
import info.nightscout.utils.Translator; import info.nightscout.utils.Translator;
@ -108,6 +109,8 @@ public class NewNSTreatmentDialog extends DialogFragment implements View.OnClick
Date eventTime; Date eventTime;
private static Integer seconds = null;
public void setOptions(OptionsToShow options, int event) { public void setOptions(OptionsToShow options, int event) {
this.options = options; this.options = options;
this.event = MainApp.sResources.getString(event); this.event = MainApp.sResources.getString(event);
@ -115,6 +118,10 @@ public class NewNSTreatmentDialog extends DialogFragment implements View.OnClick
public NewNSTreatmentDialog() { public NewNSTreatmentDialog() {
super(); super();
if (seconds == null) {
seconds = new Double(Math.random() * 59).intValue();
}
} }
@Override @Override
@ -272,11 +279,11 @@ public class NewNSTreatmentDialog extends DialogFragment implements View.OnClick
} }
}); });
Integer maxCarbs = MainApp.getConfigBuilder().applyCarbsConstraints(Constants.carbsOnlyForCheckLimit); Integer maxCarbs = MainApp.getConstraintChecker().getMaxCarbsAllowed().value();
editCarbs = (NumberPicker) view.findViewById(R.id.careportal_newnstreatment_carbsinput); editCarbs = (NumberPicker) view.findViewById(R.id.careportal_newnstreatment_carbsinput);
editCarbs.setParams(0d, 0d, (double) maxCarbs, 1d, new DecimalFormat("0"), false); editCarbs.setParams(0d, 0d, (double) maxCarbs, 1d, new DecimalFormat("0"), false);
Double maxInsulin = MainApp.getConfigBuilder().applyBolusConstraints(Constants.bolusOnlyForCheckLimit); Double maxInsulin = MainApp.getConstraintChecker().getMaxBolusAllowed().value();
editInsulin = (NumberPicker) view.findViewById(R.id.careportal_newnstreatment_insulininput); editInsulin = (NumberPicker) view.findViewById(R.id.careportal_newnstreatment_insulininput);
editInsulin.setParams(0d, 0d, maxInsulin, 0.05d, new DecimalFormat("0.00"), false); editInsulin.setParams(0d, 0d, maxInsulin, 0.05d, new DecimalFormat("0.00"), false);
@ -303,7 +310,9 @@ public class NewNSTreatmentDialog extends DialogFragment implements View.OnClick
} }
}; };
Integer maxPercent = MainApp.getConfigBuilder().applyBasalConstraints(Constants.basalPercentOnlyForCheckLimit); Integer maxPercent = 200;
if (profile != null)
maxPercent = MainApp.getConstraintChecker().getMaxBasalPercentAllowed(profile).value();
editPercent = (NumberPicker) view.findViewById(R.id.careportal_newnstreatment_percentinput); editPercent = (NumberPicker) view.findViewById(R.id.careportal_newnstreatment_percentinput);
editPercent.setParams(0d, 0d, (double) maxPercent, 5d, new DecimalFormat("0"), true, percentTextWatcher); editPercent.setParams(0d, 0d, (double) maxPercent, 5d, new DecimalFormat("0"), true, percentTextWatcher);
@ -325,7 +334,9 @@ public class NewNSTreatmentDialog extends DialogFragment implements View.OnClick
} }
}; };
Double maxAbsolute = MainApp.getConfigBuilder().applyBasalConstraints(Constants.basalAbsoluteOnlyForCheckLimit); Double maxAbsolute = HardLimits.maxBasal();
if (profile != null)
maxAbsolute = MainApp.getConstraintChecker().getMaxBasalAllowed(profile).value();
editAbsolute = (NumberPicker) view.findViewById(R.id.careportal_newnstreatment_absoluteinput); editAbsolute = (NumberPicker) view.findViewById(R.id.careportal_newnstreatment_absoluteinput);
editAbsolute.setParams(0d, 0d, maxAbsolute, 0.05d, new DecimalFormat("0.00"), true, absoluteTextWatcher); editAbsolute.setParams(0d, 0d, maxAbsolute, 0.05d, new DecimalFormat("0.00"), true, absoluteTextWatcher);
@ -419,8 +430,8 @@ public class NewNSTreatmentDialog extends DialogFragment implements View.OnClick
long millis = eventTime.getTime() - (150 * 1000L); // 2,5 * 60 * 1000 long millis = eventTime.getTime() - (150 * 1000L); // 2,5 * 60 * 1000
List<BgReading> data = MainApp.getDbHelper().getBgreadingsDataFromTime(millis, true); List<BgReading> data = MainApp.getDbHelper().getBgreadingsDataFromTime(millis, true);
if ((data.size() > 0) && if ((data.size() > 0) &&
(data.get(0).date > millis - 7 * 60 * 1000L) && (data.get(0).date > millis - 7 * 60 * 1000L) &&
(data.get(0).date < millis + 7 * 60 * 1000L)) { (data.get(0).date < millis + 7 * 60 * 1000L)) {
editBg.setValue(Profile.fromMgdlToUnits(data.get(0).value, profile != null ? profile.getUnits() : Constants.MGDL)); editBg.setValue(Profile.fromMgdlToUnits(data.get(0).value, profile != null ? profile.getUnits() : Constants.MGDL));
} }
} }
@ -438,7 +449,7 @@ public class NewNSTreatmentDialog extends DialogFragment implements View.OnClick
public void onTimeSet(RadialPickerLayout view, int hourOfDay, int minute, int second) { public void onTimeSet(RadialPickerLayout view, int hourOfDay, int minute, int second) {
eventTime.setHours(hourOfDay); eventTime.setHours(hourOfDay);
eventTime.setMinutes(minute); eventTime.setMinutes(minute);
eventTime.setSeconds(second); eventTime.setSeconds(this.seconds++); // randomize seconds to prevent creating record of the same time, if user choose time manually
timeButton.setText(DateUtil.timeString(eventTime)); timeButton.setText(DateUtil.timeString(eventTime));
updateBGforDateTime(); updateBGforDateTime();
} }

View file

@ -4,7 +4,7 @@ package info.nightscout.androidaps.plugins.ConfigBuilder;
import android.content.Context; import android.content.Context;
import android.content.Intent; import android.content.Intent;
import android.os.Bundle; import android.os.Bundle;
import android.support.v4.app.Fragment; import android.support.annotation.NonNull;
import android.view.LayoutInflater; import android.view.LayoutInflater;
import android.view.View; import android.view.View;
import android.view.ViewGroup; import android.view.ViewGroup;
@ -17,11 +17,13 @@ import android.widget.ListAdapter;
import android.widget.ListView; import android.widget.ListView;
import android.widget.TextView; import android.widget.TextView;
import com.crashlytics.android.answers.CustomEvent; import com.crashlytics.android.answers.CustomEvent;
import java.util.ArrayList; import java.util.ArrayList;
import butterknife.BindView;
import butterknife.ButterKnife;
import butterknife.OnClick;
import info.nightscout.androidaps.MainApp; import info.nightscout.androidaps.MainApp;
import info.nightscout.androidaps.PreferencesActivity; import info.nightscout.androidaps.PreferencesActivity;
import info.nightscout.androidaps.R; import info.nightscout.androidaps.R;
@ -35,6 +37,7 @@ import info.nightscout.androidaps.interfaces.PluginBase;
import info.nightscout.androidaps.interfaces.ProfileInterface; import info.nightscout.androidaps.interfaces.ProfileInterface;
import info.nightscout.androidaps.interfaces.PumpInterface; import info.nightscout.androidaps.interfaces.PumpInterface;
import info.nightscout.androidaps.interfaces.SensitivityInterface; import info.nightscout.androidaps.interfaces.SensitivityInterface;
import info.nightscout.androidaps.plugins.Common.SubscriberFragment;
import info.nightscout.androidaps.plugins.Insulin.InsulinFastactingPlugin; import info.nightscout.androidaps.plugins.Insulin.InsulinFastactingPlugin;
import info.nightscout.androidaps.plugins.ProfileNS.NSProfilePlugin; import info.nightscout.androidaps.plugins.ProfileNS.NSProfilePlugin;
import info.nightscout.androidaps.plugins.PumpVirtual.VirtualPumpPlugin; import info.nightscout.androidaps.plugins.PumpVirtual.VirtualPumpPlugin;
@ -43,33 +46,46 @@ import info.nightscout.utils.FabricPrivacy;
import info.nightscout.utils.PasswordProtection; import info.nightscout.utils.PasswordProtection;
public class ConfigBuilderFragment extends Fragment { public class ConfigBuilderFragment extends SubscriberFragment {
static ConfigBuilderPlugin configBuilderPlugin = new ConfigBuilderPlugin();
static public ConfigBuilderPlugin getPlugin() {
return configBuilderPlugin;
}
@BindView(R.id.configbuilder_insulinlistview)
ListView insulinListView; ListView insulinListView;
@BindView(R.id.configbuilder_sensitivitylistview)
ListView sensitivityListView; ListView sensitivityListView;
@BindView(R.id.configbuilder_bgsourcelistview)
ListView bgsourceListView; ListView bgsourceListView;
@BindView(R.id.configbuilder_bgsourcelabel)
TextView bgsourceLabel; TextView bgsourceLabel;
@BindView(R.id.configbuilder_pumplistview)
ListView pumpListView; ListView pumpListView;
@BindView(R.id.configbuilder_pumplabel)
TextView pumpLabel; TextView pumpLabel;
@BindView(R.id.configbuilder_looplistview)
ListView loopListView; ListView loopListView;
@BindView(R.id.configbuilder_looplabel)
TextView loopLabel; TextView loopLabel;
@BindView(R.id.configbuilder_treatmentslistview)
ListView treatmentsListView; ListView treatmentsListView;
@BindView(R.id.configbuilder_treatmentslabel)
TextView treatmentsLabel; TextView treatmentsLabel;
@BindView(R.id.configbuilder_profilelistview)
ListView profileListView; ListView profileListView;
@BindView(R.id.configbuilder_profilelabel)
TextView profileLabel; TextView profileLabel;
@BindView(R.id.configbuilder_apslistview)
ListView apsListView; ListView apsListView;
@BindView(R.id.configbuilder_apslabel)
TextView apsLabel; TextView apsLabel;
@BindView(R.id.configbuilder_constraintslistview)
ListView constraintsListView; ListView constraintsListView;
@BindView(R.id.configbuilder_constraintslabel)
TextView constraintsLabel; TextView constraintsLabel;
@BindView(R.id.configbuilder_generallistview)
ListView generalListView; ListView generalListView;
@BindView(R.id.configbuilder_mainlayout)
LinearLayout mainLayout; LinearLayout mainLayout;
@BindView(R.id.configbuilder_unlock)
Button unlock; Button unlock;
PluginCustomAdapter insulinDataAdapter = null; PluginCustomAdapter insulinDataAdapter = null;
@ -84,51 +100,17 @@ public class ConfigBuilderFragment extends Fragment {
PluginCustomAdapter generalDataAdapter = null; PluginCustomAdapter generalDataAdapter = null;
@Override @Override
public View onCreateView(LayoutInflater inflater, ViewGroup container, public View onCreateView(@NonNull LayoutInflater inflater, ViewGroup container,
Bundle savedInstanceState) { Bundle savedInstanceState) {
try { try {
View view = inflater.inflate(R.layout.configbuilder_fragment, container, false); View view = inflater.inflate(R.layout.configbuilder_fragment, container, false);
insulinListView = (ListView) view.findViewById(R.id.configbuilder_insulinlistview); unbinder = ButterKnife.bind(this, view);
sensitivityListView = (ListView) view.findViewById(R.id.configbuilder_sensitivitylistview);
bgsourceListView = (ListView) view.findViewById(R.id.configbuilder_bgsourcelistview);
bgsourceLabel = (TextView) view.findViewById(R.id.configbuilder_bgsourcelabel);
pumpListView = (ListView) view.findViewById(R.id.configbuilder_pumplistview);
pumpLabel = (TextView) view.findViewById(R.id.configbuilder_pumplabel);
loopListView = (ListView) view.findViewById(R.id.configbuilder_looplistview);
loopLabel = (TextView) view.findViewById(R.id.configbuilder_looplabel);
treatmentsListView = (ListView) view.findViewById(R.id.configbuilder_treatmentslistview);
treatmentsLabel = (TextView) view.findViewById(R.id.configbuilder_treatmentslabel);
profileListView = (ListView) view.findViewById(R.id.configbuilder_profilelistview);
profileLabel = (TextView) view.findViewById(R.id.configbuilder_profilelabel);
apsListView = (ListView) view.findViewById(R.id.configbuilder_apslistview);
apsLabel = (TextView) view.findViewById(R.id.configbuilder_apslabel);
constraintsListView = (ListView) view.findViewById(R.id.configbuilder_constraintslistview);
constraintsLabel = (TextView) view.findViewById(R.id.configbuilder_constraintslabel);
generalListView = (ListView) view.findViewById(R.id.configbuilder_generallistview);
mainLayout = (LinearLayout) view.findViewById(R.id.configbuilder_mainlayout); if (PasswordProtection.isLocked("settings_password"))
unlock = (Button) view.findViewById(R.id.configbuilder_unlock);
setViews();
if (PasswordProtection.isLocked("settings_password")) {
mainLayout.setVisibility(View.GONE); mainLayout.setVisibility(View.GONE);
unlock.setOnClickListener(new View.OnClickListener() { else
@Override
public void onClick(View v) {
PasswordProtection.QueryPassword(getContext(), R.string.settings_password, "settings_password", new Runnable() {
@Override
public void run() {
mainLayout.setVisibility(View.VISIBLE);
unlock.setVisibility(View.GONE);
}
}, null);
}
});
} else {
unlock.setVisibility(View.GONE); unlock.setVisibility(View.GONE);
}
return view; return view;
} catch (Exception e) { } catch (Exception e) {
FabricPrivacy.logException(e); FabricPrivacy.logException(e);
@ -137,7 +119,18 @@ public class ConfigBuilderFragment extends Fragment {
return null; return null;
} }
void setViews() { @OnClick(R.id.configbuilder_unlock)
public void onClickUnlock() {
PasswordProtection.QueryPassword(getContext(), R.string.settings_password, "settings_password", () -> {
mainLayout.setVisibility(View.VISIBLE);
unlock.setVisibility(View.GONE);
}, null);
}
@Override
protected void updateGUI() {
insulinDataAdapter = new PluginCustomAdapter(getContext(), R.layout.configbuilder_simpleitem, MainApp.getSpecificPluginsVisibleInListByInterface(InsulinInterface.class, PluginBase.INSULIN), PluginBase.INSULIN); insulinDataAdapter = new PluginCustomAdapter(getContext(), R.layout.configbuilder_simpleitem, MainApp.getSpecificPluginsVisibleInListByInterface(InsulinInterface.class, PluginBase.INSULIN), PluginBase.INSULIN);
insulinListView.setAdapter(insulinDataAdapter); insulinListView.setAdapter(insulinDataAdapter);
setListViewHeightBasedOnChildren(insulinListView); setListViewHeightBasedOnChildren(insulinListView);
@ -182,7 +175,6 @@ public class ConfigBuilderFragment extends Fragment {
generalDataAdapter = new PluginCustomAdapter(getContext(), R.layout.configbuilder_simpleitem, MainApp.getSpecificPluginsVisibleInList(PluginBase.GENERAL), PluginBase.GENERAL); generalDataAdapter = new PluginCustomAdapter(getContext(), R.layout.configbuilder_simpleitem, MainApp.getSpecificPluginsVisibleInList(PluginBase.GENERAL), PluginBase.GENERAL);
generalListView.setAdapter(generalDataAdapter); generalListView.setAdapter(generalDataAdapter);
setListViewHeightBasedOnChildren(generalListView); setListViewHeightBasedOnChildren(generalListView);
} }
/* /*
@ -194,8 +186,8 @@ public class ConfigBuilderFragment extends Fragment {
private ArrayList<PluginBase> pluginList; private ArrayList<PluginBase> pluginList;
final private int type; final private int type;
public PluginCustomAdapter(Context context, int textViewResourceId, PluginCustomAdapter(Context context, int textViewResourceId,
ArrayList<PluginBase> pluginList, int type) { ArrayList<PluginBase> pluginList, int type) {
super(context, textViewResourceId, pluginList); super(context, textViewResourceId, pluginList);
this.pluginList = new ArrayList<>(); this.pluginList = new ArrayList<>();
this.pluginList.addAll(pluginList); this.pluginList.addAll(pluginList);
@ -209,10 +201,11 @@ public class ConfigBuilderFragment extends Fragment {
ImageView settings; ImageView settings;
} }
@NonNull
@Override @Override
public View getView(int position, View view, ViewGroup parent) { public View getView(int position, View view, @NonNull ViewGroup parent) {
PluginViewHolder holder = null; PluginViewHolder holder;
PluginBase plugin = pluginList.get(position); PluginBase plugin = pluginList.get(position);
if (view == null) { if (view == null) {
@ -231,60 +224,45 @@ public class ConfigBuilderFragment extends Fragment {
view.setTag(holder); view.setTag(holder);
holder.checkboxEnabled.setOnClickListener(new View.OnClickListener() { holder.checkboxEnabled.setOnClickListener(v -> {
public void onClick(View v) { CheckBox cb = (CheckBox) v;
CheckBox cb = (CheckBox) v; PluginBase plugin1 = (PluginBase) cb.getTag();
PluginBase plugin = (PluginBase) cb.getTag(); plugin1.setPluginEnabled(type, cb.isChecked());
plugin.setFragmentEnabled(type, cb.isChecked()); plugin1.setFragmentVisible(type, cb.isChecked());
plugin.setFragmentVisible(type, cb.isChecked()); onEnabledCategoryChanged(plugin1, type);
onEnabledCategoryChanged(plugin, type); ConfigBuilderPlugin.getPlugin().storeSettings();
configBuilderPlugin.storeSettings(); MainApp.bus().post(new EventRefreshGui());
MainApp.bus().post(new EventRefreshGui()); MainApp.bus().post(new EventConfigBuilderChange());
MainApp.bus().post(new EventConfigBuilderChange()); ConfigBuilderPlugin.getPlugin().logPluginStatus();
getPlugin().logPluginStatus(); FabricPrivacy.getInstance().logCustom(new CustomEvent("ConfigurationChange"));
FabricPrivacy.getInstance().logCustom(new CustomEvent("ConfigurationChange"));
}
}); });
holder.checkboxVisible.setOnClickListener(new View.OnClickListener() { holder.checkboxVisible.setOnClickListener(v -> {
public void onClick(View v) { CheckBox cb = (CheckBox) v;
CheckBox cb = (CheckBox) v; PluginBase plugin12 = (PluginBase) cb.getTag();
PluginBase plugin = (PluginBase) cb.getTag(); plugin12.setFragmentVisible(type, cb.isChecked());
plugin.setFragmentVisible(type, cb.isChecked()); ConfigBuilderPlugin.getPlugin().storeSettings();
configBuilderPlugin.storeSettings(); MainApp.bus().post(new EventRefreshGui());
MainApp.bus().post(new EventRefreshGui()); ConfigBuilderPlugin.getPlugin().logPluginStatus();
getPlugin().logPluginStatus();
}
}); });
holder.settings.setOnClickListener(new View.OnClickListener() { holder.settings.setOnClickListener(v -> {
public void onClick(View v) { final PluginBase plugin13 = (PluginBase) v.getTag();
final PluginBase plugin = (PluginBase) v.getTag(); PasswordProtection.QueryPassword(getContext(), R.string.settings_password, "settings_password", () -> {
PasswordProtection.QueryPassword(getContext(), R.string.settings_password, "settings_password", new Runnable() { Intent i = new Intent(getContext(), PreferencesActivity.class);
@Override i.putExtra("id", plugin13.getPreferencesId());
public void run() { startActivity(i);
Intent i = new Intent(getContext(), PreferencesActivity.class); }, null);
i.putExtra("id", plugin.getPreferencesId());
startActivity(i);
}
}, null);
}
}); });
holder.name.setOnLongClickListener(new View.OnLongClickListener() { holder.name.setOnLongClickListener(v -> {
@Override final PluginBase plugin14 = (PluginBase) v.getTag();
public boolean onLongClick(View v) { PasswordProtection.QueryPassword(getContext(), R.string.settings_password, "settings_password", () -> {
final PluginBase plugin = (PluginBase) v.getTag(); Intent i = new Intent(getContext(), PreferencesActivity.class);
PasswordProtection.QueryPassword(getContext(), R.string.settings_password, "settings_password", new Runnable() { i.putExtra("id", plugin14.getPreferencesId());
@Override startActivity(i);
public void run() { }, null);
Intent i = new Intent(getContext(), PreferencesActivity.class); return false;
i.putExtra("id", plugin.getPreferencesId());
startActivity(i);
}
}, null);
return false;
}
}); });
} else { } else {
@ -316,8 +294,8 @@ public class ConfigBuilderFragment extends Fragment {
if (type == PluginBase.INSULIN || type == PluginBase.PUMP || type == PluginBase.TREATMENT || type == PluginBase.PROFILE || type == PluginBase.SENSITIVITY) if (type == PluginBase.INSULIN || type == PluginBase.PUMP || type == PluginBase.TREATMENT || type == PluginBase.PROFILE || type == PluginBase.SENSITIVITY)
if (pluginList.size() < 2) { if (pluginList.size() < 2) {
holder.checkboxEnabled.setEnabled(false); holder.checkboxEnabled.setEnabled(false);
plugin.setFragmentEnabled(type, true); plugin.setPluginEnabled(type, true);
getPlugin().storeSettings(); ConfigBuilderPlugin.getPlugin().storeSettings();
} }
// Constraints cannot be disabled // Constraints cannot be disabled
@ -390,23 +368,23 @@ public class ConfigBuilderFragment extends Fragment {
if (p.getName().equals(changedPlugin.getName())) { if (p.getName().equals(changedPlugin.getName())) {
// this is new selected // this is new selected
} else { } else {
p.setFragmentEnabled(type, false); p.setPluginEnabled(type, false);
p.setFragmentVisible(type, false); p.setFragmentVisible(type, false);
} }
} }
} else { // enable first plugin in list } else { // enable first plugin in list
if (type == PluginBase.PUMP) if (type == PluginBase.PUMP)
MainApp.getSpecificPlugin(VirtualPumpPlugin.class).setFragmentEnabled(type, true); VirtualPumpPlugin.getPlugin().setPluginEnabled(type, true);
else if (type == PluginBase.INSULIN) else if (type == PluginBase.INSULIN)
MainApp.getSpecificPlugin(InsulinFastactingPlugin.class).setFragmentEnabled(type, true); InsulinFastactingPlugin.getPlugin().setPluginEnabled(type, true);
else if (type == PluginBase.SENSITIVITY) else if (type == PluginBase.SENSITIVITY)
MainApp.getSpecificPlugin(SensitivityOref0Plugin.class).setFragmentEnabled(type, true); SensitivityOref0Plugin.getPlugin().setPluginEnabled(type, true);
else if (type == PluginBase.PROFILE) else if (type == PluginBase.PROFILE)
MainApp.getSpecificPlugin(NSProfilePlugin.class).setFragmentEnabled(type, true); NSProfilePlugin.getPlugin().setPluginEnabled(type, true);
else else
pluginsInCategory.get(0).setFragmentEnabled(type, true); pluginsInCategory.get(0).setPluginEnabled(type, true);
} }
setViews(); updateGUI();
} }
} }

View file

@ -4,14 +4,15 @@ import android.content.SharedPreferences;
import android.preference.PreferenceManager; import android.preference.PreferenceManager;
import android.support.annotation.Nullable; import android.support.annotation.Nullable;
import org.json.JSONException; import com.crashlytics.android.answers.CustomEvent;
import org.json.JSONObject;
import org.slf4j.Logger; import org.slf4j.Logger;
import org.slf4j.LoggerFactory; import org.slf4j.LoggerFactory;
import java.util.ArrayList; import java.util.ArrayList;
import java.util.List; import java.util.List;
import info.nightscout.androidaps.BuildConfig;
import info.nightscout.androidaps.Config; import info.nightscout.androidaps.Config;
import info.nightscout.androidaps.Constants; import info.nightscout.androidaps.Constants;
import info.nightscout.androidaps.MainApp; import info.nightscout.androidaps.MainApp;
@ -22,6 +23,7 @@ import info.nightscout.androidaps.data.IobTotal;
import info.nightscout.androidaps.data.MealData; import info.nightscout.androidaps.data.MealData;
import info.nightscout.androidaps.data.Profile; import info.nightscout.androidaps.data.Profile;
import info.nightscout.androidaps.data.ProfileIntervals; import info.nightscout.androidaps.data.ProfileIntervals;
import info.nightscout.androidaps.data.ProfileStore;
import info.nightscout.androidaps.data.PumpEnactResult; import info.nightscout.androidaps.data.PumpEnactResult;
import info.nightscout.androidaps.db.CareportalEvent; import info.nightscout.androidaps.db.CareportalEvent;
import info.nightscout.androidaps.db.ExtendedBolus; import info.nightscout.androidaps.db.ExtendedBolus;
@ -33,7 +35,7 @@ import info.nightscout.androidaps.db.Treatment;
import info.nightscout.androidaps.events.EventAppInitialized; import info.nightscout.androidaps.events.EventAppInitialized;
import info.nightscout.androidaps.interfaces.APSInterface; import info.nightscout.androidaps.interfaces.APSInterface;
import info.nightscout.androidaps.interfaces.BgSourceInterface; import info.nightscout.androidaps.interfaces.BgSourceInterface;
import info.nightscout.androidaps.interfaces.ConstraintsInterface; import info.nightscout.androidaps.interfaces.Constraint;
import info.nightscout.androidaps.interfaces.InsulinInterface; import info.nightscout.androidaps.interfaces.InsulinInterface;
import info.nightscout.androidaps.interfaces.PluginBase; import info.nightscout.androidaps.interfaces.PluginBase;
import info.nightscout.androidaps.interfaces.ProfileInterface; import info.nightscout.androidaps.interfaces.ProfileInterface;
@ -43,22 +45,29 @@ import info.nightscout.androidaps.interfaces.TreatmentsInterface;
import info.nightscout.androidaps.plugins.Loop.APSResult; import info.nightscout.androidaps.plugins.Loop.APSResult;
import info.nightscout.androidaps.plugins.Loop.LoopPlugin; import info.nightscout.androidaps.plugins.Loop.LoopPlugin;
import info.nightscout.androidaps.plugins.Overview.events.EventDismissNotification; import info.nightscout.androidaps.plugins.Overview.events.EventDismissNotification;
import info.nightscout.androidaps.plugins.Overview.events.EventNewNotification;
import info.nightscout.androidaps.plugins.Overview.notifications.Notification; import info.nightscout.androidaps.plugins.Overview.notifications.Notification;
import info.nightscout.androidaps.plugins.PumpVirtual.VirtualPumpPlugin; import info.nightscout.androidaps.plugins.PumpVirtual.VirtualPumpPlugin;
import info.nightscout.androidaps.queue.Callback; import info.nightscout.androidaps.queue.Callback;
import info.nightscout.androidaps.queue.CommandQueue; import info.nightscout.androidaps.queue.CommandQueue;
import info.nightscout.utils.FabricPrivacy;
import info.nightscout.utils.NSUpload; import info.nightscout.utils.NSUpload;
import info.nightscout.utils.SP;
import info.nightscout.utils.ToastUtils; import info.nightscout.utils.ToastUtils;
/** /**
* Created by mike on 05.08.2016. * Created by mike on 05.08.2016.
*/ */
public class ConfigBuilderPlugin implements PluginBase, ConstraintsInterface, TreatmentsInterface { public class ConfigBuilderPlugin implements PluginBase, TreatmentsInterface {
private static Logger log = LoggerFactory.getLogger(ConfigBuilderPlugin.class); private static Logger log = LoggerFactory.getLogger(ConfigBuilderPlugin.class);
private static BgSourceInterface activeBgSource; private static ConfigBuilderPlugin configBuilderPlugin;
static public ConfigBuilderPlugin getPlugin() {
if (configBuilderPlugin == null)
configBuilderPlugin = new ConfigBuilderPlugin();
return configBuilderPlugin;
}
private BgSourceInterface activeBgSource;
private static PumpInterface activePump; private static PumpInterface activePump;
private static ProfileInterface activeProfile; private static ProfileInterface activeProfile;
private static TreatmentsInterface activeTreatments; private static TreatmentsInterface activeTreatments;
@ -132,7 +141,7 @@ public class ConfigBuilderPlugin implements PluginBase, ConstraintsInterface, Tr
} }
@Override @Override
public void setFragmentEnabled(int type, boolean fragmentEnabled) { public void setPluginEnabled(int type, boolean fragmentEnabled) {
// Always enabled // Always enabled
} }
@ -182,7 +191,7 @@ public class ConfigBuilderPlugin implements PluginBase, ConstraintsInterface, Tr
String settingEnabled = "ConfigBuilder_" + type + "_" + p.getClass().getSimpleName() + "_Enabled"; String settingEnabled = "ConfigBuilder_" + type + "_" + p.getClass().getSimpleName() + "_Enabled";
String settingVisible = "ConfigBuilder_" + type + "_" + p.getClass().getSimpleName() + "_Visible"; String settingVisible = "ConfigBuilder_" + type + "_" + p.getClass().getSimpleName() + "_Visible";
if (SP.contains(settingEnabled)) if (SP.contains(settingEnabled))
p.setFragmentEnabled(type, SP.getBoolean(settingEnabled, true)); p.setPluginEnabled(type, SP.getBoolean(settingEnabled, true));
if (SP.contains(settingVisible)) if (SP.contains(settingVisible))
p.setFragmentVisible(type, SP.getBoolean(settingVisible, true) && SP.getBoolean(settingEnabled, true)); p.setFragmentVisible(type, SP.getBoolean(settingVisible, true) && SP.getBoolean(settingEnabled, true));
} catch (Exception e) { } catch (Exception e) {
@ -197,7 +206,7 @@ public class ConfigBuilderPlugin implements PluginBase, ConstraintsInterface, Tr
return commandQueue; return commandQueue;
} }
public static BgSourceInterface getActiveBgSource() { public BgSourceInterface getActiveBgSource() {
return activeBgSource; return activeBgSource;
} }
@ -342,7 +351,7 @@ public class ConfigBuilderPlugin implements PluginBase, ConstraintsInterface, Tr
found = p; found = p;
} else if (p.isEnabled(type)) { } else if (p.isEnabled(type)) {
// set others disabled // set others disabled
p.setFragmentEnabled(type, false); p.setPluginEnabled(type, false);
} }
} }
// If none enabled, enable first one // If none enabled, enable first one
@ -355,10 +364,14 @@ public class ConfigBuilderPlugin implements PluginBase, ConstraintsInterface, Tr
* expect absolute request and allow both absolute and percent response based on pump capabilities * expect absolute request and allow both absolute and percent response based on pump capabilities
*/ */
public void applyTBRRequest(APSResult request, Profile profile, Callback callback) { public void applyTBRRequest(APSResult request, Profile profile, Callback callback) {
PumpInterface pump = getActivePump(); if (!request.tempBasalRequested) {
request.rate = applyBasalConstraints(request.rate); return;
}
long now = System.currentTimeMillis(); PumpInterface pump = getActivePump();
request.rateConstraint = new Constraint<>(request.rate);
request.rate = MainApp.getConstraintChecker().applyBasalConstraints(request.rateConstraint, profile).value();
if (!pump.isInitialized()) { if (!pump.isInitialized()) {
log.debug("applyAPSRequest: " + MainApp.sResources.getString(R.string.pumpNotInitialized)); log.debug("applyAPSRequest: " + MainApp.sResources.getString(R.string.pumpNotInitialized));
@ -379,37 +392,55 @@ public class ConfigBuilderPlugin implements PluginBase, ConstraintsInterface, Tr
if (Config.logCongigBuilderActions) if (Config.logCongigBuilderActions)
log.debug("applyAPSRequest: " + request.toString()); log.debug("applyAPSRequest: " + request.toString());
if (request.tempBasalReqested) { long now = System.currentTimeMillis();
TemporaryBasal activeTemp = getTempBasalFromHistory(now); TemporaryBasal activeTemp = getTempBasalFromHistory(now);
if ((request.rate == 0 && request.duration == 0) || Math.abs(request.rate - pump.getBaseBasalRate()) < pump.getPumpDescription().basalStep) { if ((request.rate == 0 && request.duration == 0) || Math.abs(request.rate - pump.getBaseBasalRate()) < pump.getPumpDescription().basalStep) {
if (activeTemp != null) { if (activeTemp != null) {
if (Config.logCongigBuilderActions)
log.debug("applyAPSRequest: cancelTempBasal()");
getCommandQueue().cancelTempBasal(false, callback);
} else {
if (Config.logCongigBuilderActions)
log.debug("applyAPSRequest: Basal set correctly");
if (callback != null) {
callback.result(new PumpEnactResult().absolute(request.rate).duration(0).enacted(false).success(true).comment("Basal set correctly")).run();
}
}
} else if (activeTemp != null
&& activeTemp.getPlannedRemainingMinutes() > 5
&& Math.abs(request.rate - activeTemp.tempBasalConvertedToAbsolute(now, profile)) < pump.getPumpDescription().basalStep) {
if (Config.logCongigBuilderActions) if (Config.logCongigBuilderActions)
log.debug("applyAPSRequest: Temp basal set correctly"); log.debug("applyAPSRequest: cancelTempBasal()");
if (callback != null) { getCommandQueue().cancelTempBasal(false, callback);
callback.result(new PumpEnactResult().absolute(activeTemp.tempBasalConvertedToAbsolute(now, profile)).duration(activeTemp.getPlannedRemainingMinutes()).enacted(false).success(true).comment("Temp basal set correctly")).run();
}
} else { } else {
if (Config.logCongigBuilderActions) if (Config.logCongigBuilderActions)
log.debug("applyAPSRequest: setTempBasalAbsolute()"); log.debug("applyAPSRequest: Basal set correctly");
getCommandQueue().tempBasalAbsolute(request.rate, request.duration, false, callback); if (callback != null) {
callback.result(new PumpEnactResult().absolute(request.rate).duration(0)
.enacted(false).success(true).comment(MainApp.gs(R.string.basal_set_correctly))).run();
}
} }
} else if (activeTemp != null
&& activeTemp.getPlannedRemainingMinutes() > 5
&& request.duration - activeTemp.getPlannedRemainingMinutes() < 30
&& Math.abs(request.rate - activeTemp.tempBasalConvertedToAbsolute(now, profile)) < pump.getPumpDescription().basalStep) {
if (Config.logCongigBuilderActions)
log.debug("applyAPSRequest: Temp basal set correctly");
if (callback != null) {
callback.result(new PumpEnactResult().absolute(activeTemp.tempBasalConvertedToAbsolute(now, profile))
.enacted(false).success(true).duration(activeTemp.getPlannedRemainingMinutes())
.comment(MainApp.gs(R.string.let_temp_basal_run))).run();
}
} else {
if (Config.logCongigBuilderActions)
log.debug("applyAPSRequest: setTempBasalAbsolute()");
getCommandQueue().tempBasalAbsolute(request.rate, request.duration, false, profile, callback);
} }
} }
public void applySMBRequest(APSResult request, Callback callback) { public void applySMBRequest(APSResult request, Callback callback) {
if (!request.bolusRequested) {
return;
}
long lastBolusTime = getLastBolusTime();
if (lastBolusTime != 0 && lastBolusTime + 3 * 60 * 1000 > System.currentTimeMillis()) {
log.debug("SMB requested but still in 3 min interval");
if (callback != null) {
callback.result(new PumpEnactResult()
.comment(MainApp.gs(R.string.smb_frequency_exceeded))
.enacted(false).success(false)).run();
}
return;
}
PumpInterface pump = getActivePump(); PumpInterface pump = getActivePump();
if (!pump.isInitialized()) { if (!pump.isInitialized()) {
@ -431,148 +462,16 @@ public class ConfigBuilderPlugin implements PluginBase, ConstraintsInterface, Tr
if (Config.logCongigBuilderActions) if (Config.logCongigBuilderActions)
log.debug("applySMBRequest: " + request.toString()); log.debug("applySMBRequest: " + request.toString());
if (request.bolusRequested) { // deliver SMB
long lastBolusTime = getLastBolusTime(); DetailedBolusInfo detailedBolusInfo = new DetailedBolusInfo();
if (lastBolusTime != 0 && lastBolusTime + 3 * 60 * 1000 > System.currentTimeMillis()) { detailedBolusInfo.eventType = CareportalEvent.CORRECTIONBOLUS;
log.debug("SMB requsted but still in 3 min interval"); detailedBolusInfo.insulin = request.smb;
} else { detailedBolusInfo.isSMB = true;
DetailedBolusInfo detailedBolusInfo = new DetailedBolusInfo(); detailedBolusInfo.source = Source.USER;
detailedBolusInfo.eventType = CareportalEvent.CORRECTIONBOLUS; detailedBolusInfo.deliverAt = request.deliverAt;
detailedBolusInfo.insulin = request.smb; if (Config.logCongigBuilderActions)
detailedBolusInfo.isSMB = true; log.debug("applyAPSRequest: bolus()");
detailedBolusInfo.source = Source.USER; getCommandQueue().bolus(detailedBolusInfo, callback);
detailedBolusInfo.deliverAt = request.deliverAt;
getCommandQueue().bolus(detailedBolusInfo, callback);
}
}
}
/**
* Constraints interface
**/
@Override
public boolean isLoopEnabled() {
boolean result = true;
ArrayList<PluginBase> constraintsPlugins = MainApp.getSpecificPluginsListByInterface(ConstraintsInterface.class);
for (PluginBase p : constraintsPlugins) {
ConstraintsInterface constrain = (ConstraintsInterface) p;
if (!p.isEnabled(PluginBase.CONSTRAINTS)) continue;
result = result && constrain.isLoopEnabled();
}
return result;
}
@Override
public boolean isClosedModeEnabled() {
boolean result = true;
ArrayList<PluginBase> constraintsPlugins = MainApp.getSpecificPluginsListByInterface(ConstraintsInterface.class);
for (PluginBase p : constraintsPlugins) {
ConstraintsInterface constrain = (ConstraintsInterface) p;
if (!p.isEnabled(PluginBase.CONSTRAINTS)) continue;
result = result && constrain.isClosedModeEnabled();
}
return result;
}
@Override
public boolean isAutosensModeEnabled() {
boolean result = true;
ArrayList<PluginBase> constraintsPlugins = MainApp.getSpecificPluginsListByInterface(ConstraintsInterface.class);
for (PluginBase p : constraintsPlugins) {
ConstraintsInterface constrain = (ConstraintsInterface) p;
if (!p.isEnabled(PluginBase.CONSTRAINTS)) continue;
result = result && constrain.isAutosensModeEnabled();
}
return result;
}
@Override
public boolean isAMAModeEnabled() {
boolean result = SP.getBoolean("openapsama_useautosens", false);
ArrayList<PluginBase> constraintsPlugins = MainApp.getSpecificPluginsListByInterface(ConstraintsInterface.class);
for (PluginBase p : constraintsPlugins) {
ConstraintsInterface constrain = (ConstraintsInterface) p;
if (!p.isEnabled(PluginBase.CONSTRAINTS)) continue;
result = result && constrain.isAMAModeEnabled();
}
return result;
}
@Override
public boolean isSMBModeEnabled() {
boolean result = true; // TODO update for SMB // SP.getBoolean("openapsama_useautosens", false);
ArrayList<PluginBase> constraintsPlugins = MainApp.getSpecificPluginsListByInterface(ConstraintsInterface.class);
for (PluginBase p : constraintsPlugins) {
ConstraintsInterface constrain = (ConstraintsInterface) p;
if (!p.isEnabled(PluginBase.CONSTRAINTS)) continue;
result = result && constrain.isSMBModeEnabled();
}
return result;
}
@Override
public Double applyBasalConstraints(Double absoluteRate) {
Double rateAfterConstrain = absoluteRate;
ArrayList<PluginBase> constraintsPlugins = MainApp.getSpecificPluginsListByInterface(ConstraintsInterface.class);
for (PluginBase p : constraintsPlugins) {
ConstraintsInterface constrain = (ConstraintsInterface) p;
if (!p.isEnabled(PluginBase.CONSTRAINTS)) continue;
rateAfterConstrain = Math.min(constrain.applyBasalConstraints(absoluteRate), rateAfterConstrain);
}
return rateAfterConstrain;
}
@Override
public Integer applyBasalConstraints(Integer percentRate) {
Integer rateAfterConstrain = percentRate;
ArrayList<PluginBase> constraintsPlugins = MainApp.getSpecificPluginsListByInterface(ConstraintsInterface.class);
for (PluginBase p : constraintsPlugins) {
ConstraintsInterface constrain = (ConstraintsInterface) p;
if (!p.isEnabled(PluginBase.CONSTRAINTS)) continue;
rateAfterConstrain = Math.min(constrain.applyBasalConstraints(percentRate), rateAfterConstrain);
}
return rateAfterConstrain;
}
@Override
public Double applyBolusConstraints(Double insulin) {
Double insulinAfterConstrain = insulin;
ArrayList<PluginBase> constraintsPlugins = MainApp.getSpecificPluginsListByInterface(ConstraintsInterface.class);
for (PluginBase p : constraintsPlugins) {
ConstraintsInterface constrain = (ConstraintsInterface) p;
if (!p.isEnabled(PluginBase.CONSTRAINTS)) continue;
insulinAfterConstrain = Math.min(constrain.applyBolusConstraints(insulin), insulinAfterConstrain);
}
return insulinAfterConstrain;
}
@Override
public Integer applyCarbsConstraints(Integer carbs) {
Integer carbsAfterConstrain = carbs;
ArrayList<PluginBase> constraintsPlugins = MainApp.getSpecificPluginsListByInterface(ConstraintsInterface.class);
for (PluginBase p : constraintsPlugins) {
ConstraintsInterface constrain = (ConstraintsInterface) p;
if (!p.isEnabled(PluginBase.CONSTRAINTS)) continue;
carbsAfterConstrain = Math.min(constrain.applyCarbsConstraints(carbs), carbsAfterConstrain);
}
return carbsAfterConstrain;
}
@Override
public Double applyMaxIOBConstraints(Double maxIob) {
Double maxIobAfterConstrain = maxIob;
ArrayList<PluginBase> constraintsPlugins = MainApp.getSpecificPluginsListByInterface(ConstraintsInterface.class);
for (PluginBase p : constraintsPlugins) {
ConstraintsInterface constrain = (ConstraintsInterface) p;
if (!p.isEnabled(PluginBase.CONSTRAINTS)) continue;
maxIobAfterConstrain = Math.min(constrain.applyMaxIOBConstraints(maxIob), maxIobAfterConstrain);
}
return maxIobAfterConstrain;
} }
// ****** Treatments interface ***** // ****** Treatments interface *****
@ -767,9 +666,12 @@ public class ConfigBuilderPlugin implements PluginBase, ConstraintsInterface, Tr
if (profileSwitch.profileJson != null) { if (profileSwitch.profileJson != null) {
return customized ? profileSwitch.getCustomizedName() : profileSwitch.profileName; return customized ? profileSwitch.getCustomizedName() : profileSwitch.profileName;
} else { } else {
Profile profile = activeProfile.getProfile().getSpecificProfile(profileSwitch.profileName); ProfileStore profileStore = activeProfile.getProfile();
if (profile != null) if (profileStore != null) {
return profileSwitch.profileName; Profile profile = profileStore.getSpecificProfile(profileSwitch.profileName);
if (profile != null)
return profileSwitch.profileName;
}
} }
} }
return MainApp.gs(R.string.noprofileselected); return MainApp.gs(R.string.noprofileselected);
@ -806,13 +708,21 @@ public class ConfigBuilderPlugin implements PluginBase, ConstraintsInterface, Tr
return profile; return profile;
} }
} }
if (getProfileSwitchesFromHistory().size() > 0) {
FabricPrivacy.getInstance().logCustom(new CustomEvent("CatchedError")
.putCustomAttribute("buildversion", BuildConfig.BUILDVERSION)
.putCustomAttribute("version", BuildConfig.VERSION)
.putCustomAttribute("time", time)
.putCustomAttribute("getProfileSwitchesFromHistory", getProfileSwitchesFromHistory().toString())
);
}
log.debug("getProfile at the end: returning null"); log.debug("getProfile at the end: returning null");
return null; return null;
} }
public void disconnectPump(int durationInMinutes) { public void disconnectPump(int durationInMinutes, Profile profile) {
getActiveLoop().disconnectTo(System.currentTimeMillis() + durationInMinutes * 60 * 1000L); getActiveLoop().disconnectTo(System.currentTimeMillis() + durationInMinutes * 60 * 1000L);
getCommandQueue().tempBasalPercent(0, durationInMinutes, true, new Callback() { getCommandQueue().tempBasalPercent(0, durationInMinutes, true, profile, new Callback() {
@Override @Override
public void run() { public void run() {
if (!result.success) { if (!result.success) {

View file

@ -10,18 +10,18 @@ import java.util.ArrayList;
import java.util.Date; import java.util.Date;
import java.util.List; import java.util.List;
import info.nightscout.androidaps.BuildConfig;
import info.nightscout.androidaps.Config; import info.nightscout.androidaps.Config;
import info.nightscout.androidaps.MainApp; import info.nightscout.androidaps.MainApp;
import info.nightscout.androidaps.R; import info.nightscout.androidaps.R;
import info.nightscout.androidaps.db.DatabaseHelper; import info.nightscout.androidaps.db.DatabaseHelper;
import info.nightscout.androidaps.interfaces.APSInterface; import info.nightscout.androidaps.interfaces.APSInterface;
import info.nightscout.androidaps.interfaces.Constraint;
import info.nightscout.androidaps.interfaces.ConstraintsInterface; import info.nightscout.androidaps.interfaces.ConstraintsInterface;
import info.nightscout.androidaps.interfaces.PluginBase; import info.nightscout.androidaps.interfaces.PluginBase;
import info.nightscout.androidaps.plugins.ConfigBuilder.ConfigBuilderPlugin; import info.nightscout.androidaps.plugins.ConfigBuilder.ConfigBuilderPlugin;
import info.nightscout.androidaps.plugins.ConstraintsSafety.SafetyPlugin; import info.nightscout.androidaps.plugins.ConstraintsSafety.SafetyPlugin;
import info.nightscout.androidaps.plugins.Loop.LoopPlugin; import info.nightscout.androidaps.plugins.Loop.LoopPlugin;
import info.nightscout.androidaps.plugins.NSClientInternal.NSClientInternalPlugin; import info.nightscout.androidaps.plugins.NSClientInternal.NSClientPlugin;
import info.nightscout.androidaps.plugins.PumpVirtual.VirtualPumpPlugin; import info.nightscout.androidaps.plugins.PumpVirtual.VirtualPumpPlugin;
import info.nightscout.utils.SP; import info.nightscout.utils.SP;
@ -67,7 +67,7 @@ public class ObjectivesPlugin implements PluginBase, ConstraintsInterface {
@Override @Override
public String getNameShort() { public String getNameShort() {
String name = MainApp.sResources.getString(R.string.objectives_shortname); String name = MainApp.gs(R.string.objectives_shortname);
if (!name.trim().isEmpty()) { if (!name.trim().isEmpty()) {
//only if translation exists //only if translation exists
return name; return name;
@ -102,7 +102,7 @@ public class ObjectivesPlugin implements PluginBase, ConstraintsInterface {
} }
@Override @Override
public void setFragmentEnabled(int type, boolean fragmentEnabled) { public void setPluginEnabled(int type, boolean fragmentEnabled) {
} }
@Override @Override
@ -115,7 +115,7 @@ public class ObjectivesPlugin implements PluginBase, ConstraintsInterface {
return -1; return -1;
} }
class Objective { public class Objective {
Integer num; Integer num;
String objective; String objective;
String gate; String gate;
@ -131,6 +131,18 @@ public class ObjectivesPlugin implements PluginBase, ConstraintsInterface {
this.durationInDays = durationInDays; this.durationInDays = durationInDays;
this.accomplished = accomplished; this.accomplished = accomplished;
} }
public void setStarted(Date started) {
this.started = started;
}
boolean isStarted() {
return started.getTime() > 0;
}
boolean isFinished() {
return accomplished.getTime() != 0;
}
} }
// Objective 0 // Objective 0
@ -168,27 +180,28 @@ public class ObjectivesPlugin implements PluginBase, ConstraintsInterface {
if (usedAPS != null && ((PluginBase) usedAPS).isEnabled(PluginBase.APS)) if (usedAPS != null && ((PluginBase) usedAPS).isEnabled(PluginBase.APS))
apsEnabled = true; apsEnabled = true;
return new RequirementResult(hasBGData && bgIsAvailableInNS && pumpStatusIsAvailableInNS && NSClientInternalPlugin.getPlugin().hasWritePermission() && LoopPlugin.getPlugin().isEnabled(PluginBase.LOOP) && apsEnabled && vpUploadNeeded, return new RequirementResult(hasBGData && bgIsAvailableInNS && pumpStatusIsAvailableInNS && NSClientPlugin.getPlugin().hasWritePermission() && LoopPlugin.getPlugin().isEnabled(PluginBase.LOOP) && apsEnabled && vpUploadNeeded,
MainApp.sResources.getString(R.string.objectives_bgavailableinns) + ": " + yesOrNo(bgIsAvailableInNS) MainApp.gs(R.string.objectives_bgavailableinns) + ": " + yesOrNo(bgIsAvailableInNS)
+ "\n" + MainApp.sResources.getString(R.string.nsclienthaswritepermission) + ": " + yesOrNo(NSClientInternalPlugin.getPlugin().hasWritePermission()) + "\n" + MainApp.gs(R.string.nsclienthaswritepermission) + ": " + yesOrNo(NSClientPlugin.getPlugin().hasWritePermission())
+ (isVirtualPump ? "\n" + MainApp.sResources.getString(R.string.virtualpump_uploadstatus_title) + ": " + yesOrNo(vpUploadEnabled) : "") + (isVirtualPump ? "\n" + MainApp.gs(R.string.virtualpump_uploadstatus_title) + ": " + yesOrNo(vpUploadEnabled) : "")
+ "\n" + MainApp.sResources.getString(R.string.objectives_pumpstatusavailableinns) + ": " + yesOrNo(pumpStatusIsAvailableInNS) + "\n" + MainApp.gs(R.string.objectives_pumpstatusavailableinns) + ": " + yesOrNo(pumpStatusIsAvailableInNS)
+ "\n" + MainApp.sResources.getString(R.string.hasbgdata) + ": " + yesOrNo(hasBGData) + "\n" + MainApp.gs(R.string.hasbgdata) + ": " + yesOrNo(hasBGData)
+ "\n" + MainApp.sResources.getString(R.string.loopenabled) + ": " + yesOrNo(LoopPlugin.getPlugin().isEnabled(PluginBase.LOOP)) + "\n" + MainApp.gs(R.string.loopenabled) + ": " + yesOrNo(LoopPlugin.getPlugin().isEnabled(PluginBase.LOOP))
+ "\n" + MainApp.sResources.getString(R.string.apsselected) + ": " + yesOrNo(apsEnabled) + "\n" + MainApp.gs(R.string.apsselected) + ": " + yesOrNo(apsEnabled)
); );
case 1: case 1:
return new RequirementResult(manualEnacts >= manualEnactsNeeded, return new RequirementResult(manualEnacts >= manualEnactsNeeded,
MainApp.sResources.getString(R.string.objectives_manualenacts) + ": " + manualEnacts + "/" + manualEnactsNeeded); MainApp.gs(R.string.objectives_manualenacts) + ": " + manualEnacts + "/" + manualEnactsNeeded);
case 2: case 2:
return new RequirementResult(true, ""); return new RequirementResult(true, "");
case 3: case 3:
boolean closedModeEnabled = SafetyPlugin.getPlugin().isClosedModeEnabled(); Constraint<Boolean> closedLoopEnabled = new Constraint<>(true);
return new RequirementResult(closedModeEnabled, MainApp.sResources.getString(R.string.closedmodeenabled) + ": " + yesOrNo(closedModeEnabled)); SafetyPlugin.getPlugin().isClosedLoopAllowed(closedLoopEnabled);
return new RequirementResult(closedLoopEnabled.value(), MainApp.gs(R.string.closedmodeenabled) + ": " + yesOrNo(closedLoopEnabled.value()));
case 4: case 4:
double maxIOB = MainApp.getConfigBuilder().applyMaxIOBConstraints(1000d); double maxIOB = MainApp.getConstraintChecker().getMaxIOBAllowed().value();
boolean maxIobSet = maxIOB > 0; boolean maxIobSet = maxIOB > 0;
return new RequirementResult(maxIobSet, MainApp.sResources.getString(R.string.maxiobset) + ": " + yesOrNo(maxIobSet)); return new RequirementResult(maxIobSet, MainApp.gs(R.string.maxiobset) + ": " + yesOrNo(maxIobSet));
default: default:
return new RequirementResult(true, ""); return new RequirementResult(true, "");
} }
@ -202,49 +215,49 @@ public class ObjectivesPlugin implements PluginBase, ConstraintsInterface {
objectives = new ArrayList<>(); objectives = new ArrayList<>();
objectives.add(new Objective(0, objectives.add(new Objective(0,
MainApp.sResources.getString(R.string.objectives_0_objective), MainApp.gs(R.string.objectives_0_objective),
MainApp.sResources.getString(R.string.objectives_0_gate), MainApp.gs(R.string.objectives_0_gate),
new Date(0), new Date(0),
0, // 0 day 0, // 0 day
new Date(0))); new Date(0)));
objectives.add(new Objective(1, objectives.add(new Objective(1,
MainApp.sResources.getString(R.string.objectives_1_objective), MainApp.gs(R.string.objectives_1_objective),
MainApp.sResources.getString(R.string.objectives_1_gate), MainApp.gs(R.string.objectives_1_gate),
new Date(0), new Date(0),
7, // 7 days 7, // 7 days
new Date(0))); new Date(0)));
objectives.add(new Objective(2, objectives.add(new Objective(2,
MainApp.sResources.getString(R.string.objectives_2_objective), MainApp.gs(R.string.objectives_2_objective),
MainApp.sResources.getString(R.string.objectives_2_gate), MainApp.gs(R.string.objectives_2_gate),
new Date(0), new Date(0),
0, // 0 days 0, // 0 days
new Date(0))); new Date(0)));
objectives.add(new Objective(3, objectives.add(new Objective(3,
MainApp.sResources.getString(R.string.objectives_3_objective), MainApp.gs(R.string.objectives_3_objective),
MainApp.sResources.getString(R.string.objectives_3_gate), MainApp.gs(R.string.objectives_3_gate),
new Date(0), new Date(0),
5, // 5 days 5, // 5 days
new Date(0))); new Date(0)));
objectives.add(new Objective(4, objectives.add(new Objective(4,
MainApp.sResources.getString(R.string.objectives_4_objective), MainApp.gs(R.string.objectives_4_objective),
MainApp.sResources.getString(R.string.objectives_4_gate), MainApp.gs(R.string.objectives_4_gate),
new Date(0), new Date(0),
1, 1,
new Date(0))); new Date(0)));
objectives.add(new Objective(5, objectives.add(new Objective(5,
MainApp.sResources.getString(R.string.objectives_5_objective), MainApp.gs(R.string.objectives_5_objective),
MainApp.sResources.getString(R.string.objectives_5_gate), MainApp.gs(R.string.objectives_5_gate),
new Date(0), new Date(0),
7, 7,
new Date(0))); new Date(0)));
objectives.add(new Objective(6, objectives.add(new Objective(6,
MainApp.sResources.getString(R.string.objectives_6_objective), MainApp.gs(R.string.objectives_6_objective),
"", "",
new Date(0), new Date(0),
28, 28,
new Date(0))); new Date(0)));
objectives.add(new Objective(7, objectives.add(new Objective(7,
MainApp.sResources.getString(R.string.objectives_7_objective), MainApp.gs(R.string.objectives_7_objective),
"", "",
new Date(0), new Date(0),
28, 28,
@ -294,60 +307,45 @@ public class ObjectivesPlugin implements PluginBase, ConstraintsInterface {
* Constraints interface * Constraints interface
**/ **/
@Override @Override
public boolean isLoopEnabled() { public Constraint<Boolean> isLoopInvokationAllowed(Constraint<Boolean> value) {
return objectives.get(0).started.getTime() > 0; if (!objectives.get(0).isStarted())
value.set(false, String.format(MainApp.gs(R.string.objectivenotstarted), 1), this);
return value;
} }
@Override @Override
public boolean isClosedModeEnabled() { public Constraint<Boolean> isClosedLoopAllowed(Constraint<Boolean> value) {
return objectives.get(3).started.getTime() > 0; if (!objectives.get(3).isStarted())
value.set(false, String.format(MainApp.gs(R.string.objectivenotstarted), 4), this);
return value;
} }
@Override @Override
public boolean isAutosensModeEnabled() { public Constraint<Boolean> isAutosensModeEnabled(Constraint<Boolean> value) {
return objectives.get(5).started.getTime() > 0; if (!objectives.get(5).isStarted())
value.set(false, String.format(MainApp.gs(R.string.objectivenotstarted), 6), this);
return value;
} }
@Override @Override
public boolean isAMAModeEnabled() { public Constraint<Boolean> isAMAModeEnabled(Constraint<Boolean> value) {
return objectives.get(6).started.getTime() > 0; if (!objectives.get(6).isStarted())
value.set(false, String.format(MainApp.gs(R.string.objectivenotstarted), 7), this);
return value;
} }
@Override @Override
public boolean isSMBModeEnabled() { public Constraint<Boolean> isSMBModeEnabled(Constraint<Boolean> value) {
return objectives.get(7).started.getTime() > 0; if (!objectives.get(7).isStarted())
value.set(false, String.format(MainApp.gs(R.string.objectivenotstarted), 8), this);
return value;
} }
@Override @Override
public Double applyMaxIOBConstraints(Double maxIob) { public Constraint<Double> applyMaxIOBConstraints(Constraint<Double> maxIob) {
if (objectives.get(3).started.getTime() > 0 && objectives.get(3).accomplished.getTime() == 0) { if (objectives.get(3).isStarted() && !objectives.get(3).isFinished())
if (Config.logConstraintsChanges) maxIob.set(0d, String.format(MainApp.gs(R.string.objectivenotfinished), 4), this);
log.debug("Limiting maxIOB " + maxIob + " to " + 0 + "U"); return maxIob;
return 0d;
} else {
return maxIob;
}
} }
@Override
public Double applyBasalConstraints(Double absoluteRate) {
return absoluteRate;
}
@Override
public Integer applyBasalConstraints(Integer percentRate) {
return percentRate;
}
@Override
public Double applyBolusConstraints(Double insulin) {
return insulin;
}
@Override
public Integer applyCarbsConstraints(Integer carbs) {
return carbs;
}
} }

View file

@ -3,17 +3,19 @@ package info.nightscout.androidaps.plugins.ConstraintsSafety;
import org.slf4j.Logger; import org.slf4j.Logger;
import org.slf4j.LoggerFactory; import org.slf4j.LoggerFactory;
import java.util.Objects;
import info.nightscout.androidaps.BuildConfig;
import info.nightscout.androidaps.Config;
import info.nightscout.androidaps.Constants;
import info.nightscout.androidaps.MainApp; import info.nightscout.androidaps.MainApp;
import info.nightscout.androidaps.R; import info.nightscout.androidaps.R;
import info.nightscout.androidaps.data.ConstraintChecker;
import info.nightscout.androidaps.data.Profile; import info.nightscout.androidaps.data.Profile;
import info.nightscout.androidaps.interfaces.BgSourceInterface;
import info.nightscout.androidaps.interfaces.Constraint;
import info.nightscout.androidaps.interfaces.ConstraintsInterface; import info.nightscout.androidaps.interfaces.ConstraintsInterface;
import info.nightscout.androidaps.interfaces.PluginBase; import info.nightscout.androidaps.interfaces.PluginBase;
import info.nightscout.androidaps.plugins.ConfigBuilder.ConfigBuilderPlugin; import info.nightscout.androidaps.plugins.ConfigBuilder.ConfigBuilderPlugin;
import info.nightscout.androidaps.plugins.OpenAPSAMA.OpenAPSAMAPlugin;
import info.nightscout.androidaps.plugins.OpenAPSMA.OpenAPSMAPlugin;
import info.nightscout.androidaps.plugins.OpenAPSSMB.OpenAPSSMBPlugin;
import info.nightscout.utils.DecimalFormatter;
import info.nightscout.utils.HardLimits; import info.nightscout.utils.HardLimits;
import info.nightscout.utils.Round; import info.nightscout.utils.Round;
import info.nightscout.utils.SP; import info.nightscout.utils.SP;
@ -79,7 +81,7 @@ public class SafetyPlugin implements PluginBase, ConstraintsInterface {
} }
@Override @Override
public void setFragmentEnabled(int type, boolean fragmentEnabled) { public void setPluginEnabled(int type, boolean fragmentEnabled) {
} }
@ -92,142 +94,133 @@ public class SafetyPlugin implements PluginBase, ConstraintsInterface {
return R.xml.pref_safety; return R.xml.pref_safety;
} }
@Override
public boolean isLoopEnabled() {
return ConfigBuilderPlugin.getActivePump().getPumpDescription().isTempBasalCapable;
}
/** /**
* Constraints interface * Constraints interface
**/ **/
@Override @Override
public boolean isClosedModeEnabled() { public Constraint<Boolean> isLoopInvokationAllowed(Constraint<Boolean> value) {
if (!MainApp.isEngineeringModeOrRelease()) return false; if (!ConfigBuilderPlugin.getActivePump().getPumpDescription().isTempBasalCapable)
value.set(false, MainApp.gs(R.string.pumpisnottempbasalcapable), this);
return value;
}
@Override
public Constraint<Boolean> isClosedLoopAllowed(Constraint<Boolean> value) {
if (!MainApp.isEngineeringModeOrRelease())
value.set(false, MainApp.gs(R.string.closed_loop_disabled_on_dev_branch), this);
String mode = SP.getString("aps_mode", "open"); String mode = SP.getString("aps_mode", "open");
return mode.equals("closed") && BuildConfig.CLOSEDLOOP; if (!mode.equals("closed"))
value.set(false, MainApp.gs(R.string.closedmodedisabledinpreferences), this);
return value;
} }
@Override @Override
public boolean isAutosensModeEnabled() { public Constraint<Boolean> isAutosensModeEnabled(Constraint<Boolean> value) {
return true; boolean enabled = SP.getBoolean(R.string.key_openapsama_useautosens, false);
if (!enabled)
value.set(false, MainApp.gs(R.string.autosensdisabledinpreferences), this);
return value;
} }
@Override @Override
public boolean isAMAModeEnabled() { public Constraint<Boolean> isSMBModeEnabled(Constraint<Boolean> value) {
return true; boolean enabled = SP.getBoolean(R.string.key_use_smb, false);
if (!enabled)
value.set(false, MainApp.gs(R.string.smbdisabledinpreferences), this);
ConstraintChecker constraintChecker = MainApp.getConstraintChecker();
Constraint<Boolean> closedLoop = constraintChecker.isClosedLoopAllowed();
if (!closedLoop.value())
value.set(false, MainApp.gs(R.string.smbnotallowedinopenloopmode), this);
return value;
} }
@Override @Override
public boolean isSMBModeEnabled() { public Constraint<Boolean> isAdvancedFilteringEnabled(Constraint<Boolean> value) {
return true; BgSourceInterface bgSource = MainApp.getConfigBuilder().getActiveBgSource();
if (bgSource != null) {
if (!bgSource.advancedFilteringSupported())
value.set(false, MainApp.gs(R.string.smbalwaysdisabled), this);
}
return value;
} }
@Override @Override
public Double applyBasalConstraints(Double absoluteRate) { public Constraint<Double> applyBasalConstraints(Constraint<Double> absoluteRate, Profile profile) {
Double origAbsoluteRate = absoluteRate;
Double maxBasal = SP.getDouble("openapsma_max_basal", 1d);
Profile profile = MainApp.getConfigBuilder().getProfile(); absoluteRate.setIfGreater(0d, String.format(MainApp.gs(R.string.limitingbasalratio), 0d, MainApp.gs(R.string.itmustbepositivevalue)), this);
if (profile == null) return absoluteRate;
if (absoluteRate < 0) absoluteRate = 0d; double maxBasal = SP.getDouble(R.string.key_openapsma_max_basal, 1d);
absoluteRate.setIfSmaller(maxBasal, String.format(MainApp.gs(R.string.limitingbasalratio), maxBasal, MainApp.gs(R.string.maxvalueinpreferences)), this);
Double maxBasalMult = SP.getDouble("openapsama_current_basal_safety_multiplier", 4d);
Integer maxBasalFromDaily = SP.getInt("openapsama_max_daily_safety_multiplier", 3);
// Check percentRate but absolute rate too, because we know real current basal in pump // Check percentRate but absolute rate too, because we know real current basal in pump
Double origRate = absoluteRate; Double maxBasalMult = SP.getDouble(R.string.key_openapsama_current_basal_safety_multiplier, 4d);
if (absoluteRate > maxBasal) { double maxFromBasalMult = Math.floor(maxBasalMult * profile.getBasal() * 100) / 100;
absoluteRate = maxBasal; absoluteRate.setIfSmaller(maxFromBasalMult, String.format(MainApp.gs(R.string.limitingbasalratio), maxFromBasalMult, MainApp.gs(R.string.maxbasalmultiplier)), this);
if (Config.logConstraintsChanges && origAbsoluteRate != Constants.basalAbsoluteOnlyForCheckLimit)
log.debug("Limiting rate " + origRate + " by maxBasal preference to " + absoluteRate + "U/h"); Double maxBasalFromDaily = SP.getDouble(R.string.key_openapsama_max_daily_safety_multiplier, 3d);
} double maxFromDaily = Math.floor(profile.getMaxDailyBasal() * maxBasalFromDaily * 100) / 100;
if (absoluteRate > maxBasalMult * profile.getBasal()) { absoluteRate.setIfSmaller(maxFromDaily, String.format(MainApp.gs(R.string.limitingbasalratio), maxFromDaily, MainApp.gs(R.string.maxdailybasalmultiplier)), this);
absoluteRate = Math.floor(maxBasalMult * profile.getBasal() * 100) / 100;
if (Config.logConstraintsChanges && origAbsoluteRate != Constants.basalAbsoluteOnlyForCheckLimit) absoluteRate.setIfSmaller(HardLimits.maxBasal(), String.format(MainApp.gs(R.string.limitingbasalratio), HardLimits.maxBasal(), MainApp.gs(R.string.hardlimit)), this);
log.debug("Limiting rate " + origRate + " by maxBasalMult to " + absoluteRate + "U/h");
}
if (absoluteRate > profile.getMaxDailyBasal() * maxBasalFromDaily) {
absoluteRate = profile.getMaxDailyBasal() * maxBasalFromDaily;
if (Config.logConstraintsChanges && origAbsoluteRate != Constants.basalAbsoluteOnlyForCheckLimit)
log.debug("Limiting rate " + origRate + " by 3 * maxDailyBasal to " + absoluteRate + "U/h");
}
return absoluteRate; return absoluteRate;
} }
@Override @Override
public Integer applyBasalConstraints(Integer percentRate) { public Constraint<Integer> applyBasalPercentConstraints(Constraint<Integer> percentRate, Profile profile) {
Integer origPercentRate = percentRate;
Double maxBasal = SP.getDouble("openapsma_max_basal", 1d);
Profile profile = MainApp.getConfigBuilder().getProfile();
if (profile == null) return percentRate;
Double currentBasal = profile.getBasal(); Double currentBasal = profile.getBasal();
Double absoluteRate = currentBasal * ((double) percentRate.originalValue() / 100);
Double absoluteRate = currentBasal * ((double) percentRate / 100); percentRate.addReason("Percent rate " + percentRate.originalValue() + "% recalculated to " + DecimalFormatter.to2Decimal(absoluteRate) + " U/h with current basal " + DecimalFormatter.to2Decimal(currentBasal) + " U/h", this);
if (Config.logConstraintsChanges) Constraint<Double> absoluteConstraint = new Constraint<>(absoluteRate);
log.debug("Percent rate " + percentRate + "% recalculated to " + absoluteRate + "U/h with current basal " + currentBasal + "U/h"); applyBasalConstraints(absoluteConstraint, profile);
percentRate.copyReasons(absoluteConstraint);
if (absoluteRate < 0) absoluteRate = 0d; Integer percentRateAfterConst = Double.valueOf(absoluteConstraint.value() / currentBasal * 100).intValue();
Double maxBasalMult = SP.getDouble("openapsama_current_basal_safety_multiplier", 4d);
Integer maxBasalFromDaily = SP.getInt("openapsama_max_daily_safety_multiplier", 3);
// Check percentRate but absolute rate too, because we know real current basal in pump
Double origRate = absoluteRate;
if (absoluteRate > maxBasal) {
absoluteRate = maxBasal;
if (Config.logConstraintsChanges && !Objects.equals(origPercentRate, Constants.basalPercentOnlyForCheckLimit))
log.debug("Limiting rate " + origRate + " by maxBasal preference to " + absoluteRate + "U/h");
}
if (absoluteRate > maxBasalMult * profile.getBasal()) {
absoluteRate = Math.floor(maxBasalMult * profile.getBasal() * 100) / 100;
if (Config.logConstraintsChanges && !Objects.equals(origPercentRate, Constants.basalPercentOnlyForCheckLimit))
log.debug("Limiting rate " + origRate + " by maxBasalMult to " + absoluteRate + "U/h");
}
if (absoluteRate > profile.getMaxDailyBasal() * maxBasalFromDaily) {
absoluteRate = profile.getMaxDailyBasal() * maxBasalFromDaily;
if (Config.logConstraintsChanges && !Objects.equals(origPercentRate, Constants.basalPercentOnlyForCheckLimit))
log.debug("Limiting rate " + origRate + " by 3 * maxDailyBasal to " + absoluteRate + "U/h");
}
Integer percentRateAfterConst = new Double(absoluteRate / currentBasal * 100).intValue();
if (percentRateAfterConst < 100) if (percentRateAfterConst < 100)
percentRateAfterConst = Round.ceilTo((double) percentRateAfterConst, 10d).intValue(); percentRateAfterConst = Round.ceilTo((double) percentRateAfterConst, 10d).intValue();
else percentRateAfterConst = Round.floorTo((double) percentRateAfterConst, 10d).intValue(); else percentRateAfterConst = Round.floorTo((double) percentRateAfterConst, 10d).intValue();
if (Config.logConstraintsChanges && !Objects.equals(origPercentRate, Constants.basalPercentOnlyForCheckLimit)) percentRate.set(percentRateAfterConst, String.format(MainApp.gs(R.string.limitingpercentrate), percentRateAfterConst, MainApp.gs(R.string.pumplimit)), this);
log.debug("Recalculated percent rate " + percentRate + "% to " + percentRateAfterConst + "%");
return percentRateAfterConst; return percentRate;
} }
@Override @Override
public Double applyBolusConstraints(Double insulin) { public Constraint<Double> applyBolusConstraints(Constraint<Double> insulin) {
try { insulin.setIfGreater(0d, String.format(MainApp.gs(R.string.limitingbolus), 0d, MainApp.gs(R.string.itmustbepositivevalue)), this);
Double maxBolus = SP.getDouble("treatmentssafety_maxbolus", 3d);
if (insulin < 0) insulin = 0d; Double maxBolus = SP.getDouble(R.string.key_treatmentssafety_maxbolus, 3d);
if (insulin > maxBolus) insulin = maxBolus; insulin.setIfSmaller(maxBolus, String.format(MainApp.gs(R.string.limitingbolus), maxBolus, MainApp.gs(R.string.maxvalueinpreferences)), this);
} catch (Exception e) {
insulin = 0d; insulin.setIfSmaller(HardLimits.maxBolus(), String.format(MainApp.gs(R.string.limitingbolus), HardLimits.maxBolus(), MainApp.gs(R.string.hardlimit)), this);
}
if (insulin > HardLimits.maxBolus()) insulin = HardLimits.maxBolus();
return insulin; return insulin;
} }
@Override @Override
public Integer applyCarbsConstraints(Integer carbs) { public Constraint<Integer> applyCarbsConstraints(Constraint<Integer> carbs) {
try { carbs.setIfGreater(0, String.format(MainApp.gs(R.string.limitingcarbs), 0, MainApp.gs(R.string.itmustbepositivevalue)), this);
Integer maxCarbs = SP.getInt("treatmentssafety_maxcarbs", 48);
Integer maxCarbs = SP.getInt(R.string.key_treatmentssafety_maxcarbs, 48);
carbs.setIfSmaller(maxCarbs, String.format(MainApp.gs(R.string.limitingcarbs), maxCarbs, MainApp.gs(R.string.maxvalueinpreferences)), this);
if (carbs < 0) carbs = 0;
if (carbs > maxCarbs) carbs = maxCarbs;
} catch (Exception e) {
carbs = 0;
}
return carbs; return carbs;
} }
@Override @Override
public Double applyMaxIOBConstraints(Double maxIob) { public Constraint<Double> applyMaxIOBConstraints(Constraint<Double> maxIob) {
double maxIobPref = SP.getDouble(R.string.key_openapsma_max_iob, 1.5d);
maxIob.setIfSmaller(maxIobPref, String.format(MainApp.gs(R.string.limitingiob), maxIobPref, MainApp.gs(R.string.maxvalueinpreferences)), this);
if (OpenAPSMAPlugin.getPlugin().isEnabled(PluginBase.APS))
maxIob.setIfSmaller(HardLimits.maxIobAMA(), String.format(MainApp.gs(R.string.limitingiob), HardLimits.maxIobAMA(), MainApp.gs(R.string.hardlimit)), this);
if (OpenAPSAMAPlugin.getPlugin().isEnabled(PluginBase.APS))
maxIob.setIfSmaller(HardLimits.maxIobAMA(), String.format(MainApp.gs(R.string.limitingiob), HardLimits.maxIobAMA(), MainApp.gs(R.string.hardlimit)), this);
if (OpenAPSSMBPlugin.getPlugin().isEnabled(PluginBase.APS))
maxIob.setIfSmaller(HardLimits.maxIobSMB(), String.format(MainApp.gs(R.string.limitingiob), HardLimits.maxIobSMB(), MainApp.gs(R.string.hardlimit)), this);
return maxIob; return maxIob;
} }

View file

@ -73,7 +73,7 @@ public class FoodPlugin implements PluginBase {
} }
@Override @Override
public void setFragmentEnabled(int type, boolean fragmentEnabled) { public void setPluginEnabled(int type, boolean fragmentEnabled) {
if (type == GENERAL) this.fragmentEnabled = fragmentEnabled; if (type == GENERAL) this.fragmentEnabled = fragmentEnabled;
} }

View file

@ -71,7 +71,7 @@ public class InsulinFastactingPlugin implements PluginBase, InsulinInterface {
} }
@Override @Override
public void setFragmentEnabled(int type, boolean fragmentEnabled) { public void setPluginEnabled(int type, boolean fragmentEnabled) {
if (type == INSULIN) this.fragmentEnabled = fragmentEnabled; if (type == INSULIN) this.fragmentEnabled = fragmentEnabled;
} }

View file

@ -72,7 +72,7 @@ public class InsulinFastactingProlongedPlugin implements PluginBase, InsulinInte
} }
@Override @Override
public void setFragmentEnabled(int type, boolean fragmentEnabled) { public void setPluginEnabled(int type, boolean fragmentEnabled) {
if (type == INSULIN) this.fragmentEnabled = fragmentEnabled; if (type == INSULIN) this.fragmentEnabled = fragmentEnabled;
} }

View file

@ -59,7 +59,7 @@ public class InsulinOrefFreePeakPlugin extends InsulinOrefBasePlugin {
} }
@Override @Override
public void setFragmentEnabled(int type, boolean fragmentEnabled) { public void setPluginEnabled(int type, boolean fragmentEnabled) {
if (type == INSULIN) this.fragmentEnabled = fragmentEnabled; if (type == INSULIN) this.fragmentEnabled = fragmentEnabled;
} }

View file

@ -58,7 +58,7 @@ public class InsulinOrefRapidActingPlugin extends InsulinOrefBasePlugin {
} }
@Override @Override
public void setFragmentEnabled(int type, boolean fragmentEnabled) { public void setPluginEnabled(int type, boolean fragmentEnabled) {
if (type == INSULIN) this.fragmentEnabled = fragmentEnabled; if (type == INSULIN) this.fragmentEnabled = fragmentEnabled;
} }

View file

@ -58,7 +58,7 @@ public class InsulinOrefUltraRapidActingPlugin extends InsulinOrefBasePlugin {
} }
@Override @Override
public void setFragmentEnabled(int type, boolean fragmentEnabled) { public void setPluginEnabled(int type, boolean fragmentEnabled) {
if (type == INSULIN) this.fragmentEnabled = fragmentEnabled; if (type == INSULIN) this.fragmentEnabled = fragmentEnabled;
} }

View file

@ -64,7 +64,8 @@ public class AutosensData {
public double slopeFromMaxDeviation = 0; public double slopeFromMaxDeviation = 0;
public double slopeFromMinDeviation = 999; public double slopeFromMinDeviation = 999;
public String log(long time) { @Override
public String toString() {
return "AutosensData: " + new Date(time).toLocaleString() + " " + pastSensitivity + " Delta=" + delta + " avgDelta=" + avgDelta + " Bgi=" + bgi + " Deviation=" + deviation + " avgDeviation=" + avgDeviation + " Absorbed=" + absorbed + " CarbsFromBolus=" + carbsFromBolus + " COB=" + cob + " autosensRatio=" + autosensRatio + " slopeFromMaxDeviation=" + slopeFromMaxDeviation + " slopeFromMinDeviation =" + slopeFromMinDeviation ; return "AutosensData: " + new Date(time).toLocaleString() + " " + pastSensitivity + " Delta=" + delta + " avgDelta=" + avgDelta + " Bgi=" + bgi + " Deviation=" + deviation + " avgDeviation=" + avgDeviation + " Absorbed=" + absorbed + " CarbsFromBolus=" + carbsFromBolus + " COB=" + cob + " autosensRatio=" + autosensRatio + " slopeFromMaxDeviation=" + slopeFromMaxDeviation + " slopeFromMinDeviation =" + slopeFromMinDeviation ;
} }

View file

@ -117,7 +117,7 @@ public class IobCobCalculatorPlugin implements PluginBase {
} }
@Override @Override
public void setFragmentEnabled(int type, boolean fragmentEnabled) { public void setPluginEnabled(int type, boolean fragmentEnabled) {
} }
@ -531,8 +531,6 @@ public class IobCobCalculatorPlugin implements PluginBase {
@Subscribe @Subscribe
public void onEventNewBG(EventNewBG ev) { public void onEventNewBG(EventNewBG ev) {
if (!ev.isFromActiveBgSource)
return;
if (this != getPlugin()) { if (this != getPlugin()) {
log.debug("Ignoring event for non default instance"); log.debug("Ignoring event for non default instance");
return; return;

View file

@ -4,6 +4,9 @@ import android.content.Context;
import android.os.PowerManager; import android.os.PowerManager;
import android.support.v4.util.LongSparseArray; import android.support.v4.util.LongSparseArray;
import com.crashlytics.android.Crashlytics;
import com.crashlytics.android.answers.CustomEvent;
import org.slf4j.Logger; import org.slf4j.Logger;
import org.slf4j.LoggerFactory; import org.slf4j.LoggerFactory;
@ -11,6 +14,7 @@ import java.util.ArrayList;
import java.util.Date; import java.util.Date;
import java.util.List; import java.util.List;
import info.nightscout.androidaps.BuildConfig;
import info.nightscout.androidaps.Config; import info.nightscout.androidaps.Config;
import info.nightscout.androidaps.Constants; import info.nightscout.androidaps.Constants;
import info.nightscout.androidaps.MainApp; import info.nightscout.androidaps.MainApp;
@ -22,6 +26,7 @@ import info.nightscout.androidaps.events.Event;
import info.nightscout.androidaps.plugins.IobCobCalculator.events.EventAutosensCalculationFinished; import info.nightscout.androidaps.plugins.IobCobCalculator.events.EventAutosensCalculationFinished;
import info.nightscout.androidaps.queue.QueueThread; import info.nightscout.androidaps.queue.QueueThread;
import info.nightscout.utils.DateUtil; import info.nightscout.utils.DateUtil;
import info.nightscout.utils.FabricPrivacy;
/** /**
* Created by mike on 23.01.2018. * Created by mike on 23.01.2018.
@ -151,21 +156,34 @@ public class IobCobThread extends Thread {
AutosensData hourAgoData = iobCobCalculatorPlugin.getAutosensData(hourago); AutosensData hourAgoData = iobCobCalculatorPlugin.getAutosensData(hourago);
if (hourAgoData != null) { if (hourAgoData != null) {
int initialIndex = autosensDataTable.indexOfKey(hourAgoData.time); int initialIndex = autosensDataTable.indexOfKey(hourAgoData.time);
log.debug(">>>>> bucketed_data.size()=" + bucketed_data.size() + " i=" + i + "hourAgoData=" + hourAgoData.toString());
int past = 1;
try {
for (; past < 12; past++) {
AutosensData ad = autosensDataTable.valueAt(initialIndex + past);
double deviationSlope = (ad.avgDeviation - avgDeviation) / (ad.time - bgTime) * 1000 * 60 * 5;
if (ad.avgDeviation > maxDeviation) {
slopeFromMaxDeviation = Math.min(0, deviationSlope);
maxDeviation = ad.avgDeviation;
}
if (ad.avgDeviation < minDeviation) {
slopeFromMinDeviation = Math.max(0, deviationSlope);
minDeviation = ad.avgDeviation;
}
for (int past = 1; past < 12; past++) { //if (Config.logAutosensData)
AutosensData ad = autosensDataTable.valueAt(initialIndex + past); // log.debug("Deviations: " + new Date(bgTime) + new Date(ad.time) + " avgDeviation=" + avgDeviation + " deviationSlope=" + deviationSlope + " slopeFromMaxDeviation=" + slopeFromMaxDeviation + " slopeFromMinDeviation=" + slopeFromMinDeviation);
double deviationSlope = (ad.avgDeviation - avgDeviation) / (ad.time - bgTime) * 1000 * 60 * 5;
if (ad.avgDeviation > maxDeviation) {
slopeFromMaxDeviation = Math.min(0, deviationSlope);
maxDeviation = ad.avgDeviation;
} }
if (ad.avgDeviation < minDeviation) { } catch (Exception e) {
slopeFromMinDeviation = Math.max(0, deviationSlope); log.error("Unhandled exception", e);
minDeviation = ad.avgDeviation; FabricPrivacy.logException(e);
} FabricPrivacy.getInstance().logCustom(new CustomEvent("CatchedError")
.putCustomAttribute("buildversion", BuildConfig.BUILDVERSION)
//if (Config.logAutosensData) .putCustomAttribute("version", BuildConfig.VERSION)
// log.debug("Deviations: " + new Date(bgTime) + new Date(ad.time) + " avgDeviation=" + avgDeviation + " deviationSlope=" + deviationSlope + " slopeFromMaxDeviation=" + slopeFromMaxDeviation + " slopeFromMinDeviation=" + slopeFromMinDeviation); .putCustomAttribute("autosensDataTable", iobCobCalculatorPlugin.getAutosensDataTable().toString())
.putCustomAttribute("for_data", ">>>>> bucketed_data.size()=" + bucketed_data.size() + " i=" + i + "hourAgoData=" + hourAgoData.toString())
.putCustomAttribute("past", past)
);
} }
} }
} }
@ -228,7 +246,7 @@ public class IobCobThread extends Thread {
log.debug("Running detectSensitivity from: " + DateUtil.dateAndTimeString(oldestTimeWithData) + " to: " + DateUtil.dateAndTimeString(bgTime)); log.debug("Running detectSensitivity from: " + DateUtil.dateAndTimeString(oldestTimeWithData) + " to: " + DateUtil.dateAndTimeString(bgTime));
autosensData.autosensRatio = iobCobCalculatorPlugin.detectSensitivity(oldestTimeWithData, bgTime).ratio; autosensData.autosensRatio = iobCobCalculatorPlugin.detectSensitivity(oldestTimeWithData, bgTime).ratio;
if (Config.logAutosensData) if (Config.logAutosensData)
log.debug(autosensData.log(bgTime)); log.debug(autosensData.toString());
} }
} }
MainApp.bus().post(new EventAutosensCalculationFinished(cause)); MainApp.bus().post(new EventAutosensCalculationFinished(cause));

View file

@ -17,6 +17,7 @@ import info.nightscout.androidaps.MainApp;
import info.nightscout.androidaps.R; import info.nightscout.androidaps.R;
import info.nightscout.androidaps.data.IobTotal; import info.nightscout.androidaps.data.IobTotal;
import info.nightscout.androidaps.db.BgReading; import info.nightscout.androidaps.db.BgReading;
import info.nightscout.androidaps.interfaces.Constraint;
import info.nightscout.androidaps.interfaces.PumpInterface; import info.nightscout.androidaps.interfaces.PumpInterface;
import info.nightscout.androidaps.plugins.ConfigBuilder.ConfigBuilderPlugin; import info.nightscout.androidaps.plugins.ConfigBuilder.ConfigBuilderPlugin;
import info.nightscout.utils.DecimalFormatter; import info.nightscout.utils.DecimalFormatter;
@ -31,7 +32,7 @@ public class APSResult {
public String reason; public String reason;
public double rate; public double rate;
public int duration; public int duration;
public boolean tempBasalReqested = false; public boolean tempBasalRequested = false;
public boolean bolusRequested = false; public boolean bolusRequested = false;
public IobTotal iob; public IobTotal iob;
public JSONObject json = new JSONObject(); public JSONObject json = new JSONObject();
@ -39,6 +40,11 @@ public class APSResult {
public double smb = 0d; // super micro bolus in units public double smb = 0d; // super micro bolus in units
public long deliverAt = 0; public long deliverAt = 0;
public Constraint<Double> inputConstraints;
public Constraint<Double> rateConstraint;
public Constraint<Double> smbConstraint;
@Override @Override
public String toString() { public String toString() {
final PumpInterface pump = ConfigBuilderPlugin.getActivePump(); final PumpInterface pump = ConfigBuilderPlugin.getActivePump();
@ -56,7 +62,7 @@ public class APSResult {
// smb // smb
if (smb != 0) if (smb != 0)
ret += ("SMB: " + DecimalFormatter.to2Decimal(smb) + " U\n"); ret += ("SMB: " + DecimalFormatter.toPumpSupportedBolus(smb) + " U\n");
// reason // reason
ret += MainApp.sResources.getString(R.string.reason) + ": " + reason; ret += MainApp.sResources.getString(R.string.reason) + ": " + reason;
@ -76,12 +82,12 @@ public class APSResult {
ret = MainApp.sResources.getString(R.string.let_temp_basal_run) + "<br>"; ret = MainApp.sResources.getString(R.string.let_temp_basal_run) + "<br>";
else else
ret = "<b>" + MainApp.sResources.getString(R.string.rate) + "</b>: " + DecimalFormatter.to2Decimal(rate) + " U/h " + ret = "<b>" + MainApp.sResources.getString(R.string.rate) + "</b>: " + DecimalFormatter.to2Decimal(rate) + " U/h " +
"(" + DecimalFormatter.to2Decimal(rate / pump.getBaseBasalRate() * 100) + "%) <br>" + "(" + DecimalFormatter.to2Decimal(rate / pump.getBaseBasalRate() * 100) + "%) <br>" +
"<b>" + MainApp.sResources.getString(R.string.duration) + "</b>: " + DecimalFormatter.to2Decimal(duration) + " min<br>"; "<b>" + MainApp.sResources.getString(R.string.duration) + "</b>: " + DecimalFormatter.to2Decimal(duration) + " min<br>";
// smb // smb
if (smb != 0) if (smb != 0)
ret += ("<b>" + "SMB" + "</b>: " + DecimalFormatter.to2Decimal(smb) + " U<br>"); ret += ("<b>" + "SMB" + "</b>: " + DecimalFormatter.toPumpSupportedBolus(smb) + " U<br>");
// reason // reason
ret += "<b>" + MainApp.sResources.getString(R.string.reason) + "</b>: " + reason.replace("<", "&lt;").replace(">", "&gt;"); ret += "<b>" + MainApp.sResources.getString(R.string.reason) + "</b>: " + reason.replace("<", "&lt;").replace(">", "&gt;");
@ -98,9 +104,15 @@ public class APSResult {
newResult.reason = reason; newResult.reason = reason;
newResult.rate = rate; newResult.rate = rate;
newResult.duration = duration; newResult.duration = duration;
newResult.tempBasalReqested = tempBasalReqested; newResult.tempBasalRequested = tempBasalRequested;
newResult.bolusRequested = bolusRequested; newResult.bolusRequested = bolusRequested;
newResult.iob = iob; newResult.iob = iob;
newResult.json = json;
newResult.hasPredictions = hasPredictions;
newResult.smb = smb;
newResult.deliverAt = deliverAt;
newResult.rateConstraint = rateConstraint;
newResult.smbConstraint = smbConstraint;
return newResult; return newResult;
} }
@ -216,6 +228,6 @@ public class APSResult {
} }
public boolean isChangeRequested() { public boolean isChangeRequested() {
return tempBasalReqested || bolusRequested; return tempBasalRequested || bolusRequested;
} }
} }

View file

@ -20,6 +20,7 @@ import butterknife.ButterKnife;
import butterknife.OnClick; import butterknife.OnClick;
import info.nightscout.androidaps.MainApp; import info.nightscout.androidaps.MainApp;
import info.nightscout.androidaps.R; import info.nightscout.androidaps.R;
import info.nightscout.androidaps.interfaces.Constraint;
import info.nightscout.androidaps.plugins.Common.SubscriberFragment; import info.nightscout.androidaps.plugins.Common.SubscriberFragment;
import info.nightscout.androidaps.plugins.Loop.events.EventLoopSetLastRunGui; import info.nightscout.androidaps.plugins.Loop.events.EventLoopSetLastRunGui;
import info.nightscout.androidaps.plugins.Loop.events.EventLoopUpdateGui; import info.nightscout.androidaps.plugins.Loop.events.EventLoopUpdateGui;
@ -40,6 +41,8 @@ public class LoopFragment extends SubscriberFragment {
TextView requestView; TextView requestView;
@BindView(R.id.loop_constraintsprocessed) @BindView(R.id.loop_constraintsprocessed)
TextView constraintsProcessedView; TextView constraintsProcessedView;
@BindView(R.id.loop_constraints)
TextView constraintsView;
@BindView(R.id.loop_tbrsetbypump) @BindView(R.id.loop_tbrsetbypump)
TextView tbrSetByPumpView; TextView tbrSetByPumpView;
@BindView(R.id.loop_smbsetbypump) @BindView(R.id.loop_smbsetbypump)
@ -85,14 +88,26 @@ public class LoopFragment extends SubscriberFragment {
Activity activity = getActivity(); Activity activity = getActivity();
if (activity != null) if (activity != null)
activity.runOnUiThread(() -> { activity.runOnUiThread(() -> {
if (LoopPlugin.lastRun != null) { LoopPlugin.LastRun lastRun = LoopPlugin.lastRun;
requestView.setText(LoopPlugin.lastRun.request != null ? LoopPlugin.lastRun.request.toSpanned() : ""); if (lastRun != null) {
constraintsProcessedView.setText(LoopPlugin.lastRun.constraintsProcessed != null ? LoopPlugin.lastRun.constraintsProcessed.toSpanned() : ""); requestView.setText(lastRun.request != null ? lastRun.request.toSpanned() : "");
sourceView.setText(LoopPlugin.lastRun.source != null ? LoopPlugin.lastRun.source : ""); constraintsProcessedView.setText(lastRun.constraintsProcessed != null ? lastRun.constraintsProcessed.toSpanned() : "");
lastRunView.setText(LoopPlugin.lastRun.lastAPSRun != null && LoopPlugin.lastRun.lastAPSRun.getTime() != 0 ? LoopPlugin.lastRun.lastAPSRun.toLocaleString() : ""); sourceView.setText(lastRun.source != null ? lastRun.source : "");
lastEnactView.setText(LoopPlugin.lastRun.lastEnact != null && LoopPlugin.lastRun.lastEnact.getTime() != 0 ? LoopPlugin.lastRun.lastEnact.toLocaleString() : ""); lastRunView.setText(lastRun.lastAPSRun != null && lastRun.lastAPSRun.getTime() != 0 ? lastRun.lastAPSRun.toLocaleString() : "");
tbrSetByPumpView.setText(LoopPlugin.lastRun.tbrSetByPump != null ? LoopPlugin.lastRun.tbrSetByPump.toSpanned() : ""); lastEnactView.setText(lastRun.lastEnact != null && lastRun.lastEnact.getTime() != 0 ? lastRun.lastEnact.toLocaleString() : "");
smbSetByPumpView.setText(LoopPlugin.lastRun.smbSetByPump != null ? LoopPlugin.lastRun.smbSetByPump.toSpanned() : ""); tbrSetByPumpView.setText(lastRun.tbrSetByPump != null ? lastRun.tbrSetByPump.toSpanned() : "");
smbSetByPumpView.setText(lastRun.smbSetByPump != null ? lastRun.smbSetByPump.toSpanned() : "");
String constraints = "";
if (lastRun.constraintsProcessed != null) {
Constraint<Double> allConstraints = new Constraint<>(0d);
if (lastRun.constraintsProcessed.rateConstraint != null)
allConstraints.copyReasons(lastRun.constraintsProcessed.rateConstraint);
if (lastRun.constraintsProcessed.smbConstraint != null)
allConstraints.copyReasons(lastRun.constraintsProcessed.smbConstraint);
constraints = allConstraints.getMostLimitedReasons();
}
constraintsView.setText(constraints);
} }
}); });
} }

View file

@ -23,13 +23,12 @@ import info.nightscout.androidaps.MainApp;
import info.nightscout.androidaps.R; import info.nightscout.androidaps.R;
import info.nightscout.androidaps.data.Profile; import info.nightscout.androidaps.data.Profile;
import info.nightscout.androidaps.data.PumpEnactResult; import info.nightscout.androidaps.data.PumpEnactResult;
import info.nightscout.androidaps.db.BgReading;
import info.nightscout.androidaps.events.EventNewBG; import info.nightscout.androidaps.events.EventNewBG;
import info.nightscout.androidaps.events.EventTreatmentChange; import info.nightscout.androidaps.events.EventTreatmentChange;
import info.nightscout.androidaps.interfaces.APSInterface; import info.nightscout.androidaps.interfaces.APSInterface;
import info.nightscout.androidaps.interfaces.ConstraintsInterface;
import info.nightscout.androidaps.interfaces.PluginBase; import info.nightscout.androidaps.interfaces.PluginBase;
import info.nightscout.androidaps.interfaces.PumpInterface; import info.nightscout.androidaps.interfaces.PumpInterface;
import info.nightscout.androidaps.interfaces.Constraint;
import info.nightscout.androidaps.plugins.ConfigBuilder.ConfigBuilderPlugin; import info.nightscout.androidaps.plugins.ConfigBuilder.ConfigBuilderPlugin;
import info.nightscout.androidaps.plugins.IobCobCalculator.events.EventAutosensCalculationFinished; import info.nightscout.androidaps.plugins.IobCobCalculator.events.EventAutosensCalculationFinished;
import info.nightscout.androidaps.plugins.Loop.events.EventLoopSetLastRunGui; import info.nightscout.androidaps.plugins.Loop.events.EventLoopSetLastRunGui;
@ -47,7 +46,7 @@ import info.nightscout.utils.SP;
public class LoopPlugin implements PluginBase { public class LoopPlugin implements PluginBase {
private static Logger log = LoggerFactory.getLogger(LoopPlugin.class); private static Logger log = LoggerFactory.getLogger(LoopPlugin.class);
private static LoopPlugin loopPlugin; protected static LoopPlugin loopPlugin;
public static LoopPlugin getPlugin() { public static LoopPlugin getPlugin() {
if (loopPlugin == null) { if (loopPlugin == null) {
@ -56,7 +55,7 @@ public class LoopPlugin implements PluginBase {
return loopPlugin; return loopPlugin;
} }
private boolean fragmentEnabled = false; private boolean pluginEnabled = false;
private boolean fragmentVisible = false; private boolean fragmentVisible = false;
private long loopSuspendedTill = 0L; // end of manual loop suspend private long loopSuspendedTill = 0L; // end of manual loop suspend
@ -95,12 +94,12 @@ public class LoopPlugin implements PluginBase {
@Override @Override
public String getName() { public String getName() {
return MainApp.instance().getString(R.string.loop); return MainApp.instance().gs(R.string.loop);
} }
@Override @Override
public String getNameShort() { public String getNameShort() {
String name = MainApp.sResources.getString(R.string.loop_shortname); String name = MainApp.gs(R.string.loop_shortname);
if (!name.trim().isEmpty()) { if (!name.trim().isEmpty()) {
//only if translation exists //only if translation exists
return name; return name;
@ -112,7 +111,7 @@ public class LoopPlugin implements PluginBase {
@Override @Override
public boolean isEnabled(int type) { public boolean isEnabled(int type) {
boolean pumpCapable = ConfigBuilderPlugin.getActivePump() == null || ConfigBuilderPlugin.getActivePump().getPumpDescription().isTempBasalCapable; boolean pumpCapable = ConfigBuilderPlugin.getActivePump() == null || ConfigBuilderPlugin.getActivePump().getPumpDescription().isTempBasalCapable;
return type == LOOP && fragmentEnabled && pumpCapable; return type == LOOP && pluginEnabled && pumpCapable;
} }
@Override @Override
@ -137,8 +136,8 @@ public class LoopPlugin implements PluginBase {
} }
@Override @Override
public void setFragmentEnabled(int type, boolean fragmentEnabled) { public void setPluginEnabled(int type, boolean pluginEnabled) {
if (type == LOOP) this.fragmentEnabled = fragmentEnabled; if (type == LOOP) this.pluginEnabled = pluginEnabled;
} }
@Override @Override
@ -153,19 +152,15 @@ public class LoopPlugin implements PluginBase {
@Subscribe @Subscribe
public void onStatusEvent(final EventTreatmentChange ev) { public void onStatusEvent(final EventTreatmentChange ev) {
if (ev.treatment == null || !ev.treatment.isSMB){ if (ev.treatment == null || !ev.treatment.isSMB) {
invoke("EventTreatmentChange", true); invoke("EventTreatmentChange", true);
} }
} }
@Subscribe @Subscribe
public void onStatusEvent(final EventAutosensCalculationFinished ev) { public void onStatusEvent(final EventAutosensCalculationFinished ev) {
if (!(ev.cause instanceof EventNewBG)) if (ev.cause instanceof EventNewBG) {
return; invoke(ev.getClass().getSimpleName() + "(" + ev.cause.getClass().getSimpleName() + ")", true);
EventNewBG bgEv = (EventNewBG) ev.cause;
if (bgEv.isNew && bgEv.isFromActiveBgSource && bgEv.isCurrent()) {
invoke("New BG", true);
} }
} }
@ -260,10 +255,12 @@ public class LoopPlugin implements PluginBase {
try { try {
if (Config.logFunctionCalls) if (Config.logFunctionCalls)
log.debug("invoke from " + initiator); log.debug("invoke from " + initiator);
ConstraintsInterface constraintsInterface = MainApp.getConfigBuilder(); Constraint<Boolean> loopEnabled = MainApp.getConstraintChecker().isLoopInvokationAllowed();
if (!constraintsInterface.isLoopEnabled()) {
log.debug(MainApp.sResources.getString(R.string.loopdisabled)); if (!loopEnabled.value()) {
MainApp.bus().post(new EventLoopSetLastRunGui(MainApp.sResources.getString(R.string.loopdisabled))); String message = MainApp.sResources.getString(R.string.loopdisabled) + "\n" + loopEnabled.getReasons();
log.debug(message);
MainApp.bus().post(new EventLoopSetLastRunGui(message));
return; return;
} }
final PumpInterface pump = ConfigBuilderPlugin.getActivePump(); final PumpInterface pump = ConfigBuilderPlugin.getActivePump();
@ -297,8 +294,10 @@ public class LoopPlugin implements PluginBase {
// check rate for constrais // check rate for constrais
final APSResult resultAfterConstraints = result.clone(); final APSResult resultAfterConstraints = result.clone();
resultAfterConstraints.rate = constraintsInterface.applyBasalConstraints(resultAfterConstraints.rate); resultAfterConstraints.rateConstraint = new Constraint<>(resultAfterConstraints.rate);
resultAfterConstraints.smb = constraintsInterface.applyBolusConstraints(resultAfterConstraints.smb); resultAfterConstraints.rate = MainApp.getConstraintChecker().applyBasalConstraints(resultAfterConstraints.rateConstraint, profile).value();
resultAfterConstraints.smbConstraint = new Constraint<>(resultAfterConstraints.smb);
resultAfterConstraints.smb = MainApp.getConstraintChecker().applyBolusConstraints(resultAfterConstraints.smbConstraint).value();
// safety check for multiple SMBs // safety check for multiple SMBs
long lastBolusTime = TreatmentsPlugin.getPlugin().getLastBolusTime(); long lastBolusTime = TreatmentsPlugin.getPlugin().getLastBolusTime();
@ -329,11 +328,16 @@ public class LoopPlugin implements PluginBase {
return; return;
} }
if (constraintsInterface.isClosedModeEnabled()) { Constraint<Boolean> closedLoopEnabled = MainApp.getConstraintChecker().isClosedLoopAllowed();
if (closedLoopEnabled.value()) {
if (result.isChangeRequested()) { if (result.isChangeRequested()) {
final PumpEnactResult waiting = new PumpEnactResult(); final PumpEnactResult waiting = new PumpEnactResult();
waiting.queued = true; waiting.queued = true;
lastRun.tbrSetByPump = waiting; if (resultAfterConstraints.tempBasalRequested)
lastRun.tbrSetByPump = waiting;
if (resultAfterConstraints.bolusRequested)
lastRun.smbSetByPump = waiting;
MainApp.bus().post(new EventLoopUpdateGui()); MainApp.bus().post(new EventLoopUpdateGui());
FabricPrivacy.getInstance().logCustom(new CustomEvent("APSRequest")); FabricPrivacy.getInstance().logCustom(new CustomEvent("APSRequest"));
MainApp.getConfigBuilder().applyTBRRequest(resultAfterConstraints, profile, new Callback() { MainApp.getConfigBuilder().applyTBRRequest(resultAfterConstraints, profile, new Callback() {

View file

@ -7,7 +7,6 @@ import android.content.Context;
import android.content.DialogInterface; import android.content.DialogInterface;
import android.graphics.Paint; import android.graphics.Paint;
import android.os.Bundle; import android.os.Bundle;
import android.support.v4.app.Fragment;
import android.text.Html; import android.text.Html;
import android.text.Spanned; import android.text.Spanned;
import android.view.LayoutInflater; import android.view.LayoutInflater;
@ -34,8 +33,8 @@ import info.nightscout.androidaps.plugins.NSClientInternal.events.EventNSClientU
import info.nightscout.utils.FabricPrivacy; import info.nightscout.utils.FabricPrivacy;
import info.nightscout.utils.SP; import info.nightscout.utils.SP;
public class NSClientInternalFragment extends SubscriberFragment implements View.OnClickListener, CompoundButton.OnCheckedChangeListener { public class NSClientFragment extends SubscriberFragment implements View.OnClickListener, CompoundButton.OnCheckedChangeListener {
private static Logger log = LoggerFactory.getLogger(NSClientInternalFragment.class); private static Logger log = LoggerFactory.getLogger(NSClientFragment.class);
private TextView logTextView; private TextView logTextView;
private TextView queueTextView; private TextView queueTextView;
@ -58,10 +57,10 @@ public class NSClientInternalFragment extends SubscriberFragment implements View
logScrollview = (ScrollView) view.findViewById(R.id.nsclientinternal_logscrollview); logScrollview = (ScrollView) view.findViewById(R.id.nsclientinternal_logscrollview);
autoscrollCheckbox = (CheckBox) view.findViewById(R.id.nsclientinternal_autoscroll); autoscrollCheckbox = (CheckBox) view.findViewById(R.id.nsclientinternal_autoscroll);
autoscrollCheckbox.setChecked(NSClientInternalPlugin.getPlugin().autoscroll); autoscrollCheckbox.setChecked(NSClientPlugin.getPlugin().autoscroll);
autoscrollCheckbox.setOnCheckedChangeListener(this); autoscrollCheckbox.setOnCheckedChangeListener(this);
pausedCheckbox = (CheckBox) view.findViewById(R.id.nsclientinternal_paused); pausedCheckbox = (CheckBox) view.findViewById(R.id.nsclientinternal_paused);
pausedCheckbox.setChecked(NSClientInternalPlugin.getPlugin().paused); pausedCheckbox.setChecked(NSClientPlugin.getPlugin().paused);
pausedCheckbox.setOnCheckedChangeListener(this); pausedCheckbox.setOnCheckedChangeListener(this);
logTextView = (TextView) view.findViewById(R.id.nsclientinternal_log); logTextView = (TextView) view.findViewById(R.id.nsclientinternal_log);
queueTextView = (TextView) view.findViewById(R.id.nsclientinternal_queue); queueTextView = (TextView) view.findViewById(R.id.nsclientinternal_queue);
@ -101,11 +100,11 @@ public class NSClientInternalFragment extends SubscriberFragment implements View
FabricPrivacy.getInstance().logCustom(new CustomEvent("NSClientRestart")); FabricPrivacy.getInstance().logCustom(new CustomEvent("NSClientRestart"));
break; break;
case R.id.nsclientinternal_delivernow: case R.id.nsclientinternal_delivernow:
NSClientInternalPlugin.getPlugin().resend("GUI"); NSClientPlugin.getPlugin().resend("GUI");
FabricPrivacy.getInstance().logCustom(new CustomEvent("NSClientDeliverNow")); FabricPrivacy.getInstance().logCustom(new CustomEvent("NSClientDeliverNow"));
break; break;
case R.id.nsclientinternal_clearlog: case R.id.nsclientinternal_clearlog:
NSClientInternalPlugin.getPlugin().clearLog(); NSClientPlugin.getPlugin().clearLog();
break; break;
case R.id.nsclientinternal_clearqueue: case R.id.nsclientinternal_clearqueue:
final Context context = getContext(); final Context context = getContext();
@ -124,7 +123,7 @@ public class NSClientInternalFragment extends SubscriberFragment implements View
builder.show(); builder.show();
break; break;
case R.id.nsclientinternal_showqueue: case R.id.nsclientinternal_showqueue:
MainApp.bus().post(new EventNSClientNewLog("QUEUE", NSClientInternalPlugin.getPlugin().queue().textList())); MainApp.bus().post(new EventNSClientNewLog("QUEUE", NSClientPlugin.getPlugin().queue().textList()));
FabricPrivacy.getInstance().logCustom(new CustomEvent("NSClientShowQueue")); FabricPrivacy.getInstance().logCustom(new CustomEvent("NSClientShowQueue"));
break; break;
} }
@ -135,14 +134,14 @@ public class NSClientInternalFragment extends SubscriberFragment implements View
switch (buttonView.getId()) { switch (buttonView.getId()) {
case R.id.nsclientinternal_paused: case R.id.nsclientinternal_paused:
SP.putBoolean(R.string.key_nsclientinternal_paused, isChecked); SP.putBoolean(R.string.key_nsclientinternal_paused, isChecked);
NSClientInternalPlugin.getPlugin().paused = isChecked; NSClientPlugin.getPlugin().paused = isChecked;
MainApp.bus().post(new EventPreferenceChange(R.string.key_nsclientinternal_paused)); MainApp.bus().post(new EventPreferenceChange(R.string.key_nsclientinternal_paused));
updateGUI(); updateGUI();
FabricPrivacy.getInstance().logCustom(new CustomEvent("NSClientPause")); FabricPrivacy.getInstance().logCustom(new CustomEvent("NSClientPause"));
break; break;
case R.id.nsclientinternal_autoscroll: case R.id.nsclientinternal_autoscroll:
SP.putBoolean(R.string.key_nsclientinternal_autoscroll, isChecked); SP.putBoolean(R.string.key_nsclientinternal_autoscroll, isChecked);
NSClientInternalPlugin.getPlugin().autoscroll = isChecked; NSClientPlugin.getPlugin().autoscroll = isChecked;
updateGUI(); updateGUI();
break; break;
} }
@ -160,15 +159,15 @@ public class NSClientInternalFragment extends SubscriberFragment implements View
activity.runOnUiThread(new Runnable() { activity.runOnUiThread(new Runnable() {
@Override @Override
public void run() { public void run() {
NSClientInternalPlugin.updateLog(); NSClientPlugin.getPlugin().updateLog();
logTextView.setText(NSClientInternalPlugin.textLog); logTextView.setText(NSClientPlugin.getPlugin().textLog);
if (NSClientInternalPlugin.getPlugin().autoscroll) { if (NSClientPlugin.getPlugin().autoscroll) {
logScrollview.fullScroll(ScrollView.FOCUS_DOWN); logScrollview.fullScroll(ScrollView.FOCUS_DOWN);
} }
urlTextView.setText(NSClientInternalPlugin.getPlugin().url()); urlTextView.setText(NSClientPlugin.getPlugin().url());
Spanned queuetext = Html.fromHtml(MainApp.sResources.getString(R.string.queue) + " <b>" + UploadQueue.size() + "</b>"); Spanned queuetext = Html.fromHtml(MainApp.sResources.getString(R.string.queue) + " <b>" + UploadQueue.size() + "</b>");
queueTextView.setText(queuetext); queueTextView.setText(queuetext);
statusTextView.setText(NSClientInternalPlugin.getPlugin().status); statusTextView.setText(NSClientPlugin.getPlugin().status);
} }
}); });
} }

View file

@ -31,25 +31,25 @@ import info.nightscout.androidaps.plugins.NSClientInternal.services.NSClientServ
import info.nightscout.utils.SP; import info.nightscout.utils.SP;
import info.nightscout.utils.ToastUtils; import info.nightscout.utils.ToastUtils;
public class NSClientInternalPlugin implements PluginBase { public class NSClientPlugin implements PluginBase {
private static Logger log = LoggerFactory.getLogger(NSClientInternalPlugin.class); private static Logger log = LoggerFactory.getLogger(NSClientPlugin.class);
static NSClientInternalPlugin nsClientInternalPlugin; static NSClientPlugin nsClientPlugin;
static public NSClientInternalPlugin getPlugin() { static public NSClientPlugin getPlugin() {
if (nsClientInternalPlugin == null) { if (nsClientPlugin == null) {
nsClientInternalPlugin = new NSClientInternalPlugin(); nsClientPlugin = new NSClientPlugin();
} }
return nsClientInternalPlugin; return nsClientPlugin;
} }
private boolean fragmentEnabled = true; private boolean fragmentEnabled = true;
private boolean fragmentVisible = true; private boolean fragmentVisible = true;
static public Handler handler; public Handler handler;
private static List<EventNSClientNewLog> listLog = new ArrayList<>(); private final List<EventNSClientNewLog> listLog = new ArrayList<>();
static Spanned textLog = Html.fromHtml(""); Spanned textLog = Html.fromHtml("");
public boolean paused = false; public boolean paused = false;
boolean autoscroll = true; boolean autoscroll = true;
@ -58,13 +58,13 @@ public class NSClientInternalPlugin implements PluginBase {
public NSClientService nsClientService = null; public NSClientService nsClientService = null;
NSClientInternalPlugin() { NSClientPlugin() {
MainApp.bus().register(this); MainApp.bus().register(this);
paused = SP.getBoolean(R.string.key_nsclientinternal_paused, false); paused = SP.getBoolean(R.string.key_nsclientinternal_paused, false);
autoscroll = SP.getBoolean(R.string.key_nsclientinternal_autoscroll, true); autoscroll = SP.getBoolean(R.string.key_nsclientinternal_autoscroll, true);
if (handler == null) { if (handler == null) {
HandlerThread handlerThread = new HandlerThread(NSClientInternalPlugin.class.getSimpleName() + "Handler"); HandlerThread handlerThread = new HandlerThread(NSClientPlugin.class.getSimpleName() + "Handler");
handlerThread.start(); handlerThread.start();
handler = new Handler(handlerThread.getLooper()); handler = new Handler(handlerThread.getLooper());
} }
@ -81,7 +81,7 @@ public class NSClientInternalPlugin implements PluginBase {
@Override @Override
public String getFragmentClass() { public String getFragmentClass() {
return NSClientInternalFragment.class.getName(); return NSClientFragment.class.getName();
} }
@Override @Override
@ -126,7 +126,7 @@ public class NSClientInternalPlugin implements PluginBase {
} }
@Override @Override
public void setFragmentEnabled(int type, boolean fragmentEnabled) { public void setPluginEnabled(int type, boolean fragmentEnabled) {
if (type == GENERAL) this.fragmentEnabled = fragmentEnabled; if (type == GENERAL) this.fragmentEnabled = fragmentEnabled;
} }
@ -177,7 +177,9 @@ public class NSClientInternalPlugin implements PluginBase {
handler.post(new Runnable() { handler.post(new Runnable() {
@Override @Override
public void run() { public void run() {
listLog = new ArrayList<>(); synchronized (listLog) {
listLog.clear();
}
MainApp.bus().post(new EventNSClientUpdateGUI()); MainApp.bus().post(new EventNSClientUpdateGUI());
} }
}); });
@ -187,22 +189,25 @@ public class NSClientInternalPlugin implements PluginBase {
handler.post(new Runnable() { handler.post(new Runnable() {
@Override @Override
public void run() { public void run() {
listLog.add(ev); synchronized (listLog) {
// remove the first line if log is too large listLog.add(ev);
if (listLog.size() >= Constants.MAX_LOG_LINES) { // remove the first line if log is too large
listLog.remove(0); if (listLog.size() >= Constants.MAX_LOG_LINES) {
listLog.remove(0);
}
} }
MainApp.bus().post(new EventNSClientUpdateGUI()); MainApp.bus().post(new EventNSClientUpdateGUI());
} }
}); });
} }
static synchronized void updateLog() { synchronized void updateLog() {
try { try {
StringBuilder newTextLog = new StringBuilder(); StringBuilder newTextLog = new StringBuilder();
List<EventNSClientNewLog> temporaryList = new ArrayList<>(listLog); synchronized (listLog) {
for (EventNSClientNewLog log : temporaryList) { for (EventNSClientNewLog log : listLog) {
newTextLog.append(log.toPreparedHtml()); newTextLog.append(log.toPreparedHtml());
}
} }
textLog = Html.fromHtml(newTextLog.toString()); textLog = Html.fromHtml(newTextLog.toString());
} catch (OutOfMemoryError e) { } catch (OutOfMemoryError e) {

View file

@ -48,7 +48,7 @@ public class UploadQueue {
public void run() { public void run() {
log.debug("QUEUE adding: " + dbr.data); log.debug("QUEUE adding: " + dbr.data);
MainApp.getDbHelper().create(dbr); MainApp.getDbHelper().create(dbr);
NSClientInternalPlugin plugin = MainApp.getSpecificPlugin(NSClientInternalPlugin.class); NSClientPlugin plugin = NSClientPlugin.getPlugin();
if (plugin != null) { if (plugin != null) {
plugin.resend("newdata"); plugin.resend("newdata");
} }

View file

@ -6,19 +6,13 @@ import android.content.Intent;
import android.os.Bundle; import android.os.Bundle;
import android.os.PowerManager; import android.os.PowerManager;
import org.json.JSONException;
import org.json.JSONObject;
import org.slf4j.Logger; import org.slf4j.Logger;
import org.slf4j.LoggerFactory; import org.slf4j.LoggerFactory;
import java.util.Date;
import info.nightscout.androidaps.MainApp; import info.nightscout.androidaps.MainApp;
import info.nightscout.androidaps.R; import info.nightscout.androidaps.R;
import info.nightscout.androidaps.db.DbRequest;
import info.nightscout.androidaps.interfaces.PluginBase; import info.nightscout.androidaps.interfaces.PluginBase;
import info.nightscout.androidaps.plugins.NSClientInternal.NSClientInternalPlugin; import info.nightscout.androidaps.plugins.NSClientInternal.NSClientPlugin;
import info.nightscout.androidaps.plugins.NSClientInternal.UploadQueue;
import info.nightscout.androidaps.plugins.NSClientInternal.data.AlarmAck; import info.nightscout.androidaps.plugins.NSClientInternal.data.AlarmAck;
import info.nightscout.androidaps.plugins.NSClientInternal.services.NSClientService; import info.nightscout.androidaps.plugins.NSClientInternal.services.NSClientService;
import info.nightscout.utils.SP; import info.nightscout.utils.SP;
@ -32,8 +26,8 @@ public class AckAlarmReceiver extends BroadcastReceiver {
PowerManager powerManager = (PowerManager) context.getSystemService(Context.POWER_SERVICE); PowerManager powerManager = (PowerManager) context.getSystemService(Context.POWER_SERVICE);
PowerManager.WakeLock wakeLock = powerManager.newWakeLock(PowerManager.PARTIAL_WAKE_LOCK, PowerManager.WakeLock wakeLock = powerManager.newWakeLock(PowerManager.PARTIAL_WAKE_LOCK,
AckAlarmReceiver.class.getSimpleName()); AckAlarmReceiver.class.getSimpleName());
NSClientInternalPlugin nsClientInternalPlugin = MainApp.getSpecificPlugin(NSClientInternalPlugin.class); NSClientPlugin nsClientPlugin = MainApp.getSpecificPlugin(NSClientPlugin.class);
if (!nsClientInternalPlugin.isEnabled(PluginBase.GENERAL)) { if (!nsClientPlugin.isEnabled(PluginBase.GENERAL)) {
return; return;
} }
if (SP.getBoolean(R.string.key_ns_noupload, false)) { if (SP.getBoolean(R.string.key_ns_noupload, false)) {
@ -53,7 +47,7 @@ public class AckAlarmReceiver extends BroadcastReceiver {
ack.group = bundles.getString("group"); ack.group = bundles.getString("group");
ack.silenceTime = bundles.getLong("silenceTime"); ack.silenceTime = bundles.getLong("silenceTime");
NSClientService nsClientService = nsClientInternalPlugin.nsClientService; NSClientService nsClientService = nsClientPlugin.nsClientService;
if (nsClientService != null) if (nsClientService != null)
nsClientService.sendAlarmAck(ack); nsClientService.sendAlarmAck(ack);

View file

@ -15,7 +15,7 @@ import info.nightscout.androidaps.MainApp;
import info.nightscout.androidaps.R; import info.nightscout.androidaps.R;
import info.nightscout.androidaps.db.DbRequest; import info.nightscout.androidaps.db.DbRequest;
import info.nightscout.androidaps.interfaces.PluginBase; import info.nightscout.androidaps.interfaces.PluginBase;
import info.nightscout.androidaps.plugins.NSClientInternal.NSClientInternalPlugin; import info.nightscout.androidaps.plugins.NSClientInternal.NSClientPlugin;
import info.nightscout.androidaps.plugins.NSClientInternal.UploadQueue; import info.nightscout.androidaps.plugins.NSClientInternal.UploadQueue;
import info.nightscout.androidaps.plugins.NSClientInternal.broadcasts.BroadcastTreatment; import info.nightscout.androidaps.plugins.NSClientInternal.broadcasts.BroadcastTreatment;
import info.nightscout.utils.DateUtil; import info.nightscout.utils.DateUtil;
@ -105,8 +105,8 @@ public class DBAccessReceiver extends BroadcastReceiver {
} }
public boolean shouldUpload() { public boolean shouldUpload() {
NSClientInternalPlugin nsClientInternalPlugin = MainApp.getSpecificPlugin(NSClientInternalPlugin.class); NSClientPlugin nsClientPlugin = MainApp.getSpecificPlugin(NSClientPlugin.class);
return nsClientInternalPlugin.isEnabled(PluginBase.GENERAL) && !SP.getBoolean(R.string.key_ns_noupload, false); return nsClientPlugin.isEnabled(PluginBase.GENERAL) && !SP.getBoolean(R.string.key_ns_noupload, false);
} }
public void genereateTreatmentOfflineBroadcast(DbRequest request) { public void genereateTreatmentOfflineBroadcast(DbRequest request) {

View file

@ -34,7 +34,7 @@ import info.nightscout.androidaps.events.EventAppExit;
import info.nightscout.androidaps.events.EventConfigBuilderChange; import info.nightscout.androidaps.events.EventConfigBuilderChange;
import info.nightscout.androidaps.events.EventPreferenceChange; import info.nightscout.androidaps.events.EventPreferenceChange;
import info.nightscout.androidaps.interfaces.PluginBase; import info.nightscout.androidaps.interfaces.PluginBase;
import info.nightscout.androidaps.plugins.NSClientInternal.NSClientInternalPlugin; import info.nightscout.androidaps.plugins.NSClientInternal.NSClientPlugin;
import info.nightscout.androidaps.plugins.NSClientInternal.UploadQueue; import info.nightscout.androidaps.plugins.NSClientInternal.UploadQueue;
import info.nightscout.androidaps.plugins.NSClientInternal.acks.NSAddAck; import info.nightscout.androidaps.plugins.NSClientInternal.acks.NSAddAck;
import info.nightscout.androidaps.plugins.NSClientInternal.acks.NSAuthAck; import info.nightscout.androidaps.plugins.NSClientInternal.acks.NSAuthAck;
@ -180,7 +180,7 @@ public class NSClientService extends Service {
@Subscribe @Subscribe
public void onStatusEvent(EventConfigBuilderChange ev) { public void onStatusEvent(EventConfigBuilderChange ev) {
if (nsEnabled != MainApp.getSpecificPlugin(NSClientInternalPlugin.class).isEnabled(PluginBase.GENERAL)) { if (nsEnabled != MainApp.getSpecificPlugin(NSClientPlugin.class).isEnabled(PluginBase.GENERAL)) {
latestDateInReceivedData = 0; latestDateInReceivedData = 0;
destroy(); destroy();
initialize(); initialize();
@ -202,7 +202,7 @@ public class NSClientService extends Service {
nsAPIhashCode = Hashing.sha1().hashString(nsAPISecret, Charsets.UTF_8).toString(); nsAPIhashCode = Hashing.sha1().hashString(nsAPISecret, Charsets.UTF_8).toString();
MainApp.bus().post(new EventNSClientStatus("Initializing")); MainApp.bus().post(new EventNSClientStatus("Initializing"));
if (MainApp.getSpecificPlugin(NSClientInternalPlugin.class).paused) { if (MainApp.getSpecificPlugin(NSClientPlugin.class).paused) {
MainApp.bus().post(new EventNSClientNewLog("NSCLIENT", "paused")); MainApp.bus().post(new EventNSClientNewLog("NSCLIENT", "paused"));
MainApp.bus().post(new EventNSClientStatus("Paused")); MainApp.bus().post(new EventNSClientStatus("Paused"));
} else if (!nsEnabled) { } else if (!nsEnabled) {
@ -313,7 +313,7 @@ public class NSClientService extends Service {
} }
public void readPreferences() { public void readPreferences() {
nsEnabled = MainApp.getSpecificPlugin(NSClientInternalPlugin.class).isEnabled(PluginBase.GENERAL); nsEnabled = MainApp.getSpecificPlugin(NSClientPlugin.class).isEnabled(PluginBase.GENERAL);
nsURL = SP.getString(R.string.key_nsclientinternal_url, ""); nsURL = SP.getString(R.string.key_nsclientinternal_url, "");
nsAPISecret = SP.getString(R.string.key_nsclientinternal_api_secret, ""); nsAPISecret = SP.getString(R.string.key_nsclientinternal_api_secret, "");
nsDevice = SP.getString("careportal_enteredby", ""); nsDevice = SP.getString("careportal_enteredby", "");

View file

@ -21,6 +21,7 @@ import java.lang.reflect.InvocationTargetException;
import info.nightscout.androidaps.Config; import info.nightscout.androidaps.Config;
import info.nightscout.androidaps.Constants; import info.nightscout.androidaps.Constants;
import info.nightscout.androidaps.MainApp; import info.nightscout.androidaps.MainApp;
import info.nightscout.androidaps.R;
import info.nightscout.androidaps.data.GlucoseStatus; import info.nightscout.androidaps.data.GlucoseStatus;
import info.nightscout.androidaps.data.IobTotal; import info.nightscout.androidaps.data.IobTotal;
import info.nightscout.androidaps.data.MealData; import info.nightscout.androidaps.data.MealData;
@ -205,8 +206,8 @@ public class DetermineBasalAdapterAMAJS {
mProfile.put("target_bg", targetBg); mProfile.put("target_bg", targetBg);
mProfile.put("carb_ratio", profile.getIc()); mProfile.put("carb_ratio", profile.getIc());
mProfile.put("sens", Profile.toMgdl(profile.getIsf(), units)); mProfile.put("sens", Profile.toMgdl(profile.getIsf(), units));
mProfile.put("max_daily_safety_multiplier", SP.getInt("openapsama_max_daily_safety_multiplier", 3)); mProfile.put("max_daily_safety_multiplier", SP.getInt(R.string.key_openapsama_max_daily_safety_multiplier, 3));
mProfile.put("current_basal_safety_multiplier", SP.getDouble("openapsama_current_basal_safety_multiplier", 4d)); mProfile.put("current_basal_safety_multiplier", SP.getDouble(R.string.key_openapsama_current_basal_safety_multiplier, 4d));
mProfile.put("skip_neutral_temps", true); mProfile.put("skip_neutral_temps", true);
mProfile.put("current_basal", basalrate); mProfile.put("current_basal", basalrate);
mProfile.put("temptargetSet", tempTargetSet); mProfile.put("temptargetSet", tempTargetSet);
@ -250,7 +251,7 @@ public class DetermineBasalAdapterAMAJS {
mMealData.put("boluses", mealData.boluses); mMealData.put("boluses", mealData.boluses);
mMealData.put("mealCOB", mealData.mealCOB); mMealData.put("mealCOB", mealData.mealCOB);
if (MainApp.getConfigBuilder().isAMAModeEnabled()) { if (MainApp.getConstraintChecker().isAutosensModeEnabled().value()) {
mAutosensData = new JSONObject(); mAutosensData = new JSONObject();
mAutosensData.put("ratio", autosensDataRatio); mAutosensData.put("ratio", autosensDataRatio);
} else { } else {

View file

@ -22,7 +22,7 @@ public class DetermineBasalResultAMA extends APSResult {
json = j; json = j;
if (result.containsKey("error")) { if (result.containsKey("error")) {
reason = result.get("error").toString(); reason = result.get("error").toString();
tempBasalReqested = false; tempBasalRequested = false;
rate = -1; rate = -1;
duration = -1; duration = -1;
} else { } else {
@ -32,17 +32,17 @@ public class DetermineBasalResultAMA extends APSResult {
if (result.containsKey("rate")) { if (result.containsKey("rate")) {
rate = (Double) result.get("rate"); rate = (Double) result.get("rate");
if (rate < 0d) rate = 0d; if (rate < 0d) rate = 0d;
tempBasalReqested = true; tempBasalRequested = true;
} else { } else {
rate = -1; rate = -1;
tempBasalReqested = false; tempBasalRequested = false;
} }
if (result.containsKey("duration")) { if (result.containsKey("duration")) {
duration = ((Double) result.get("duration")).intValue(); duration = ((Double) result.get("duration")).intValue();
//changeRequested as above //changeRequested as above
} else { } else {
duration = -1; duration = -1;
tempBasalReqested = false; tempBasalRequested = false;
} }
} }
bolusRequested = false; bolusRequested = false;
@ -58,7 +58,7 @@ public class DetermineBasalResultAMA extends APSResult {
newResult.reason = reason; newResult.reason = reason;
newResult.rate = rate; newResult.rate = rate;
newResult.duration = duration; newResult.duration = duration;
newResult.tempBasalReqested = tempBasalReqested; newResult.tempBasalRequested = tempBasalRequested;
newResult.rate = rate; newResult.rate = rate;
newResult.duration = duration; newResult.duration = duration;

View file

@ -8,6 +8,7 @@ import java.io.IOException;
import java.util.Date; import java.util.Date;
import info.nightscout.androidaps.Config; import info.nightscout.androidaps.Config;
import info.nightscout.androidaps.Constants;
import info.nightscout.androidaps.MainApp; import info.nightscout.androidaps.MainApp;
import info.nightscout.androidaps.R; import info.nightscout.androidaps.R;
import info.nightscout.androidaps.data.GlucoseStatus; import info.nightscout.androidaps.data.GlucoseStatus;
@ -17,6 +18,7 @@ import info.nightscout.androidaps.data.Profile;
import info.nightscout.androidaps.db.TempTarget; import info.nightscout.androidaps.db.TempTarget;
import info.nightscout.androidaps.db.TemporaryBasal; import info.nightscout.androidaps.db.TemporaryBasal;
import info.nightscout.androidaps.interfaces.APSInterface; import info.nightscout.androidaps.interfaces.APSInterface;
import info.nightscout.androidaps.interfaces.Constraint;
import info.nightscout.androidaps.interfaces.PluginBase; import info.nightscout.androidaps.interfaces.PluginBase;
import info.nightscout.androidaps.interfaces.PumpInterface; import info.nightscout.androidaps.interfaces.PumpInterface;
import info.nightscout.androidaps.plugins.ConfigBuilder.ConfigBuilderPlugin; import info.nightscout.androidaps.plugins.ConfigBuilder.ConfigBuilderPlugin;
@ -74,7 +76,7 @@ public class OpenAPSAMAPlugin implements PluginBase, APSInterface {
@Override @Override
public boolean isEnabled(int type) { public boolean isEnabled(int type) {
boolean pumpCapable = ConfigBuilderPlugin.getActivePump() == null || ConfigBuilderPlugin.getActivePump().getPumpDescription().isTempBasalCapable; boolean pumpCapable = ConfigBuilderPlugin.getActivePump() == null || ConfigBuilderPlugin.getActivePump() != null && ConfigBuilderPlugin.getActivePump().getPumpDescription().isTempBasalCapable;
return type == APS && fragmentEnabled && pumpCapable; return type == APS && fragmentEnabled && pumpCapable;
} }
@ -110,7 +112,7 @@ public class OpenAPSAMAPlugin implements PluginBase, APSInterface {
} }
@Override @Override
public void setFragmentEnabled(int type, boolean fragmentEnabled) { public void setPluginEnabled(int type, boolean fragmentEnabled) {
if (type == APS) this.fragmentEnabled = fragmentEnabled; if (type == APS) this.fragmentEnabled = fragmentEnabled;
} }
@ -173,8 +175,7 @@ public class OpenAPSAMAPlugin implements PluginBase, APSInterface {
String units = profile.getUnits(); String units = profile.getUnits();
double maxIob = SP.getDouble("openapsma_max_iob", 1.5d); double maxBasal = MainApp.getConstraintChecker().getMaxBasalAllowed(profile).value();
double maxBasal = SP.getDouble("openapsma_max_basal", 1d);
double minBg = Profile.toMgdl(profile.getTargetLow(), units); double minBg = Profile.toMgdl(profile.getTargetLow(), units);
double maxBg = Profile.toMgdl(profile.getTargetHigh(), units); double maxBg = Profile.toMgdl(profile.getTargetHigh(), units);
double targetBg = Profile.toMgdl(profile.getTarget(), units); double targetBg = Profile.toMgdl(profile.getTarget(), units);
@ -191,7 +192,7 @@ public class OpenAPSAMAPlugin implements PluginBase, APSInterface {
MealData mealData = MainApp.getConfigBuilder().getMealData(); MealData mealData = MainApp.getConfigBuilder().getMealData();
Profiler.log(log, "getMealData()", startPart); Profiler.log(log, "getMealData()", startPart);
maxIob = MainApp.getConfigBuilder().applyMaxIOBConstraints(maxIob); double maxIob = MainApp.getConstraintChecker().getMaxIOBAllowed().value();
minBg = HardLimits.verifyHardLimits(minBg, "minBg", HardLimits.VERY_HARD_LIMIT_MIN_BG[0], HardLimits.VERY_HARD_LIMIT_MIN_BG[1]); minBg = HardLimits.verifyHardLimits(minBg, "minBg", HardLimits.VERY_HARD_LIMIT_MIN_BG[0], HardLimits.VERY_HARD_LIMIT_MIN_BG[1]);
maxBg = HardLimits.verifyHardLimits(maxBg, "maxBg", HardLimits.VERY_HARD_LIMIT_MAX_BG[0], HardLimits.VERY_HARD_LIMIT_MAX_BG[1]); maxBg = HardLimits.verifyHardLimits(maxBg, "maxBg", HardLimits.VERY_HARD_LIMIT_MAX_BG[0], HardLimits.VERY_HARD_LIMIT_MAX_BG[1]);
@ -207,9 +208,6 @@ public class OpenAPSAMAPlugin implements PluginBase, APSInterface {
} }
maxIob = HardLimits.verifyHardLimits(maxIob, "maxIob", 0, HardLimits.maxIobAMA());
maxBasal = HardLimits.verifyHardLimits(maxBasal, "max_basal", 0.1, HardLimits.maxBasal());
if (!HardLimits.checkOnlyHardLimits(profile.getDia(), "dia", HardLimits.MINDIA, HardLimits.MAXDIA)) if (!HardLimits.checkOnlyHardLimits(profile.getDia(), "dia", HardLimits.MINDIA, HardLimits.MAXDIA))
return; return;
if (!HardLimits.checkOnlyHardLimits(profile.getIcTimeFromMidnight(profile.secondsFromMidnight()), "carbratio", HardLimits.MINIC, HardLimits.MAXIC)) if (!HardLimits.checkOnlyHardLimits(profile.getIcTimeFromMidnight(profile.secondsFromMidnight()), "carbratio", HardLimits.MINIC, HardLimits.MAXIC))
@ -222,7 +220,7 @@ public class OpenAPSAMAPlugin implements PluginBase, APSInterface {
return; return;
startPart = new Date(); startPart = new Date();
if (MainApp.getConfigBuilder().isAMAModeEnabled()) { if (MainApp.getConstraintChecker().isAutosensModeEnabled().value()) {
lastAutosensResult = IobCobCalculatorPlugin.getPlugin().detectSensitivityWithLock(IobCobCalculatorPlugin.oldestDataAvailable(), System.currentTimeMillis()); lastAutosensResult = IobCobCalculatorPlugin.getPlugin().detectSensitivityWithLock(IobCobCalculatorPlugin.oldestDataAvailable(), System.currentTimeMillis());
} else { } else {
lastAutosensResult = new AutosensResult(); lastAutosensResult = new AutosensResult();
@ -246,17 +244,17 @@ public class OpenAPSAMAPlugin implements PluginBase, APSInterface {
Profiler.log(log, "AMA calculation", start); Profiler.log(log, "AMA calculation", start);
// Fix bug determine basal // Fix bug determine basal
if (determineBasalResultAMA.rate == 0d && determineBasalResultAMA.duration == 0 && !MainApp.getConfigBuilder().isTempBasalInProgress()) if (determineBasalResultAMA.rate == 0d && determineBasalResultAMA.duration == 0 && !MainApp.getConfigBuilder().isTempBasalInProgress())
determineBasalResultAMA.tempBasalReqested = false; determineBasalResultAMA.tempBasalRequested = false;
// limit requests on openloop mode // limit requests on openloop mode
if (!MainApp.getConfigBuilder().isClosedModeEnabled()) { if (!MainApp.getConstraintChecker().isClosedLoopAllowed().value()) {
long now = System.currentTimeMillis(); long now = System.currentTimeMillis();
TemporaryBasal activeTemp = MainApp.getConfigBuilder().getTempBasalFromHistory(now); TemporaryBasal activeTemp = MainApp.getConfigBuilder().getTempBasalFromHistory(now);
if (activeTemp != null && determineBasalResultAMA.rate == 0 && determineBasalResultAMA.duration == 0) { if (activeTemp != null && determineBasalResultAMA.rate == 0 && determineBasalResultAMA.duration == 0) {
// going to cancel // going to cancel
} else if (activeTemp != null && Math.abs(determineBasalResultAMA.rate - activeTemp.tempBasalConvertedToAbsolute(now, profile)) < 0.1) { } else if (activeTemp != null && Math.abs(determineBasalResultAMA.rate - activeTemp.tempBasalConvertedToAbsolute(now, profile)) < 0.1) {
determineBasalResultAMA.tempBasalReqested = false; determineBasalResultAMA.tempBasalRequested = false;
} else if (activeTemp == null && Math.abs(determineBasalResultAMA.rate - ConfigBuilderPlugin.getActivePump().getBaseBasalRate()) < 0.1) } else if (activeTemp == null && Math.abs(determineBasalResultAMA.rate - ConfigBuilderPlugin.getActivePump().getBaseBasalRate()) < 0.1)
determineBasalResultAMA.tempBasalReqested = false; determineBasalResultAMA.tempBasalRequested = false;
} }
determineBasalResultAMA.iob = iobArray[0]; determineBasalResultAMA.iob = iobArray[0];

View file

@ -20,7 +20,7 @@ public class DetermineBasalResultMA extends APSResult {
json = j; json = j;
if (result.containsKey("error")) { if (result.containsKey("error")) {
reason = (String) result.get("error"); reason = (String) result.get("error");
tempBasalReqested = false; tempBasalRequested = false;
rate = -1; rate = -1;
duration = -1; duration = -1;
mealAssist = ""; mealAssist = "";
@ -31,17 +31,17 @@ public class DetermineBasalResultMA extends APSResult {
if (result.containsKey("rate")) { if (result.containsKey("rate")) {
rate = (Double) result.get("rate"); rate = (Double) result.get("rate");
if (rate < 0d) rate = 0d; if (rate < 0d) rate = 0d;
tempBasalReqested = true; tempBasalRequested = true;
} else { } else {
rate = -1; rate = -1;
tempBasalReqested = false; tempBasalRequested = false;
} }
if (result.containsKey("duration")) { if (result.containsKey("duration")) {
duration = ((Double) result.get("duration")).intValue(); duration = ((Double) result.get("duration")).intValue();
//changeRequested as above //changeRequested as above
} else { } else {
duration = -1; duration = -1;
tempBasalReqested = false; tempBasalRequested = false;
} }
if (result.containsKey("mealAssist")) { if (result.containsKey("mealAssist")) {
mealAssist = result.get("mealAssist").toString(); mealAssist = result.get("mealAssist").toString();
@ -58,10 +58,10 @@ public class DetermineBasalResultMA extends APSResult {
newResult.reason = new String(reason); newResult.reason = new String(reason);
newResult.rate = rate; newResult.rate = rate;
newResult.duration = duration; newResult.duration = duration;
newResult.tempBasalReqested = isChangeRequested(); newResult.tempBasalRequested = isChangeRequested();
newResult.rate = rate; newResult.rate = rate;
newResult.duration = duration; newResult.duration = duration;
newResult.tempBasalReqested = isChangeRequested(); newResult.tempBasalRequested = isChangeRequested();
try { try {
newResult.json = new JSONObject(json.toString()); newResult.json = new JSONObject(json.toString());

View file

@ -8,6 +8,7 @@ import java.io.IOException;
import java.util.Date; import java.util.Date;
import info.nightscout.androidaps.Config; import info.nightscout.androidaps.Config;
import info.nightscout.androidaps.Constants;
import info.nightscout.androidaps.MainApp; import info.nightscout.androidaps.MainApp;
import info.nightscout.androidaps.R; import info.nightscout.androidaps.R;
import info.nightscout.androidaps.data.GlucoseStatus; import info.nightscout.androidaps.data.GlucoseStatus;
@ -17,6 +18,7 @@ import info.nightscout.androidaps.data.Profile;
import info.nightscout.androidaps.db.TempTarget; import info.nightscout.androidaps.db.TempTarget;
import info.nightscout.androidaps.db.TemporaryBasal; import info.nightscout.androidaps.db.TemporaryBasal;
import info.nightscout.androidaps.interfaces.APSInterface; import info.nightscout.androidaps.interfaces.APSInterface;
import info.nightscout.androidaps.interfaces.Constraint;
import info.nightscout.androidaps.interfaces.PluginBase; import info.nightscout.androidaps.interfaces.PluginBase;
import info.nightscout.androidaps.interfaces.PumpInterface; import info.nightscout.androidaps.interfaces.PumpInterface;
import info.nightscout.androidaps.plugins.ConfigBuilder.ConfigBuilderPlugin; import info.nightscout.androidaps.plugins.ConfigBuilder.ConfigBuilderPlugin;
@ -29,7 +31,6 @@ import info.nightscout.utils.HardLimits;
import info.nightscout.utils.Profiler; import info.nightscout.utils.Profiler;
import info.nightscout.utils.Round; import info.nightscout.utils.Round;
import info.nightscout.utils.SP; import info.nightscout.utils.SP;
import info.nightscout.utils.SafeParse;
import static info.nightscout.utils.HardLimits.checkOnlyHardLimits; import static info.nightscout.utils.HardLimits.checkOnlyHardLimits;
import static info.nightscout.utils.HardLimits.verifyHardLimits; import static info.nightscout.utils.HardLimits.verifyHardLimits;
@ -75,13 +76,13 @@ public class OpenAPSMAPlugin implements PluginBase, APSInterface {
@Override @Override
public boolean isEnabled(int type) { public boolean isEnabled(int type) {
boolean pumpCapable = ConfigBuilderPlugin.getActivePump() == null || ConfigBuilderPlugin.getActivePump().getPumpDescription().isTempBasalCapable; boolean pumpCapable = ConfigBuilderPlugin.getActivePump() == null || ConfigBuilderPlugin.getActivePump() != null && ConfigBuilderPlugin.getActivePump().getPumpDescription().isTempBasalCapable;
return type == APS && fragmentEnabled && pumpCapable; return type == APS && fragmentEnabled && pumpCapable;
} }
@Override @Override
public boolean isVisibleInTabs(int type) { public boolean isVisibleInTabs(int type) {
boolean pumpCapable = ConfigBuilderPlugin.getActivePump() == null || ConfigBuilderPlugin.getActivePump().getPumpDescription().isTempBasalCapable; boolean pumpCapable = ConfigBuilderPlugin.getActivePump() == null || ConfigBuilderPlugin.getActivePump() != null && ConfigBuilderPlugin.getActivePump().getPumpDescription().isTempBasalCapable;
return type == APS && fragmentVisible && pumpCapable; return type == APS && fragmentVisible && pumpCapable;
} }
@ -111,7 +112,7 @@ public class OpenAPSMAPlugin implements PluginBase, APSInterface {
} }
@Override @Override
public void setFragmentEnabled(int type, boolean fragmentEnabled) { public void setPluginEnabled(int type, boolean fragmentEnabled) {
if (type == APS) this.fragmentEnabled = fragmentEnabled; if (type == APS) this.fragmentEnabled = fragmentEnabled;
} }
@ -174,8 +175,8 @@ public class OpenAPSMAPlugin implements PluginBase, APSInterface {
String units = profile.getUnits(); String units = profile.getUnits();
double maxIob = SP.getDouble("openapsma_max_iob", 1.5d); double maxBasal = MainApp.getConstraintChecker().getMaxBasalAllowed(profile).value();
double maxBasal = SafeParse.stringToDouble(SP.getString("openapsma_max_basal", "1"));
double minBg = Profile.toMgdl(profile.getTargetLow(), units); double minBg = Profile.toMgdl(profile.getTargetLow(), units);
double maxBg = Profile.toMgdl(profile.getTargetHigh(), units); double maxBg = Profile.toMgdl(profile.getTargetHigh(), units);
double targetBg = Profile.toMgdl(profile.getTarget(), units); double targetBg = Profile.toMgdl(profile.getTarget(), units);
@ -193,7 +194,7 @@ public class OpenAPSMAPlugin implements PluginBase, APSInterface {
MealData mealData = MainApp.getConfigBuilder().getMealData(); MealData mealData = MainApp.getConfigBuilder().getMealData();
maxIob = MainApp.getConfigBuilder().applyMaxIOBConstraints(maxIob); double maxIob = MainApp.getConstraintChecker().getMaxIOBAllowed().value();
Profiler.log(log, "MA data gathering", start); Profiler.log(log, "MA data gathering", start);
minBg = verifyHardLimits(minBg, "minBg", HardLimits.VERY_HARD_LIMIT_MIN_BG[0], HardLimits.VERY_HARD_LIMIT_MIN_BG[1]); minBg = verifyHardLimits(minBg, "minBg", HardLimits.VERY_HARD_LIMIT_MIN_BG[0], HardLimits.VERY_HARD_LIMIT_MIN_BG[1]);
@ -207,9 +208,6 @@ public class OpenAPSMAPlugin implements PluginBase, APSInterface {
targetBg = verifyHardLimits(tempTarget.target(), "targetBg", HardLimits.VERY_HARD_LIMIT_TEMP_TARGET_BG[0], HardLimits.VERY_HARD_LIMIT_TEMP_TARGET_BG[1]); targetBg = verifyHardLimits(tempTarget.target(), "targetBg", HardLimits.VERY_HARD_LIMIT_TEMP_TARGET_BG[0], HardLimits.VERY_HARD_LIMIT_TEMP_TARGET_BG[1]);
} }
maxIob = verifyHardLimits(maxIob, "maxIob", 0, HardLimits.maxIobAMA());
maxBasal = verifyHardLimits(maxBasal, "max_basal", 0.1, HardLimits.maxBasal());
if (!checkOnlyHardLimits(profile.getDia(), "dia", HardLimits.MINDIA, HardLimits.MAXDIA)) if (!checkOnlyHardLimits(profile.getDia(), "dia", HardLimits.MINDIA, HardLimits.MAXDIA))
return; return;
if (!checkOnlyHardLimits(profile.getIcTimeFromMidnight(profile.secondsFromMidnight()), "carbratio", HardLimits.MINIC, HardLimits.MAXIC)) if (!checkOnlyHardLimits(profile.getIcTimeFromMidnight(profile.secondsFromMidnight()), "carbratio", HardLimits.MINIC, HardLimits.MAXIC))
@ -235,16 +233,16 @@ public class OpenAPSMAPlugin implements PluginBase, APSInterface {
DetermineBasalResultMA determineBasalResultMA = determineBasalAdapterMAJS.invoke(); DetermineBasalResultMA determineBasalResultMA = determineBasalAdapterMAJS.invoke();
// Fix bug determinef basal // Fix bug determinef basal
if (determineBasalResultMA.rate == 0d && determineBasalResultMA.duration == 0 && !MainApp.getConfigBuilder().isTempBasalInProgress()) if (determineBasalResultMA.rate == 0d && determineBasalResultMA.duration == 0 && !MainApp.getConfigBuilder().isTempBasalInProgress())
determineBasalResultMA.tempBasalReqested = false; determineBasalResultMA.tempBasalRequested = false;
// limit requests on openloop mode // limit requests on openloop mode
if (!MainApp.getConfigBuilder().isClosedModeEnabled()) { if (!MainApp.getConstraintChecker().isClosedLoopAllowed().value()) {
TemporaryBasal activeTemp = MainApp.getConfigBuilder().getTempBasalFromHistory(now); TemporaryBasal activeTemp = MainApp.getConfigBuilder().getTempBasalFromHistory(now);
if (activeTemp != null && determineBasalResultMA.rate == 0 && determineBasalResultMA.duration == 0) { if (activeTemp != null && determineBasalResultMA.rate == 0 && determineBasalResultMA.duration == 0) {
// going to cancel // going to cancel
} else if (activeTemp != null && Math.abs(determineBasalResultMA.rate - activeTemp.tempBasalConvertedToAbsolute(now, profile)) < 0.1) { } else if (activeTemp != null && Math.abs(determineBasalResultMA.rate - activeTemp.tempBasalConvertedToAbsolute(now, profile)) < 0.1) {
determineBasalResultMA.tempBasalReqested = false; determineBasalResultMA.tempBasalRequested = false;
} else if (activeTemp == null && Math.abs(determineBasalResultMA.rate - ConfigBuilderPlugin.getActivePump().getBaseBasalRate()) < 0.1) } else if (activeTemp == null && Math.abs(determineBasalResultMA.rate - ConfigBuilderPlugin.getActivePump().getBaseBasalRate()) < 0.1)
determineBasalResultMA.tempBasalReqested = false; determineBasalResultMA.tempBasalRequested = false;
} }
determineBasalResultMA.iob = iobTotal; determineBasalResultMA.iob = iobTotal;

View file

@ -27,12 +27,10 @@ import info.nightscout.androidaps.data.IobTotal;
import info.nightscout.androidaps.data.MealData; import info.nightscout.androidaps.data.MealData;
import info.nightscout.androidaps.data.Profile; import info.nightscout.androidaps.data.Profile;
import info.nightscout.androidaps.db.TemporaryBasal; import info.nightscout.androidaps.db.TemporaryBasal;
import info.nightscout.androidaps.interfaces.PluginBase;
import info.nightscout.androidaps.plugins.ConfigBuilder.ConfigBuilderPlugin; import info.nightscout.androidaps.plugins.ConfigBuilder.ConfigBuilderPlugin;
import info.nightscout.androidaps.plugins.IobCobCalculator.IobCobCalculatorPlugin; import info.nightscout.androidaps.plugins.IobCobCalculator.IobCobCalculatorPlugin;
import info.nightscout.androidaps.plugins.Loop.ScriptReader; import info.nightscout.androidaps.plugins.Loop.ScriptReader;
import info.nightscout.androidaps.plugins.OpenAPSMA.LoggerCallback; import info.nightscout.androidaps.plugins.OpenAPSMA.LoggerCallback;
import info.nightscout.androidaps.plugins.SourceDexcomG5.SourceDexcomG5Plugin;
import info.nightscout.utils.SP; import info.nightscout.utils.SP;
import info.nightscout.utils.SafeParse; import info.nightscout.utils.SafeParse;
@ -48,6 +46,7 @@ public class DetermineBasalAdapterSMBJS {
private JSONObject mCurrentTemp; private JSONObject mCurrentTemp;
private JSONObject mAutosensData = null; private JSONObject mAutosensData = null;
private boolean mMicrobolusAllowed; private boolean mMicrobolusAllowed;
private boolean mSMBAlwaysAllowed;
private String storedCurrentTemp = null; private String storedCurrentTemp = null;
private String storedIobData = null; private String storedIobData = null;
@ -57,6 +56,7 @@ public class DetermineBasalAdapterSMBJS {
private String storedMeal_data = null; private String storedMeal_data = null;
private String storedAutosens_data = null; private String storedAutosens_data = null;
private String storedMicroBolusAllowed = null; private String storedMicroBolusAllowed = null;
private String storedSMBAlwaysAllowed = null;
private String scriptDebug = ""; private String scriptDebug = "";
@ -84,6 +84,7 @@ public class DetermineBasalAdapterSMBJS {
log.debug("Autosens data: " + (storedAutosens_data = "undefined")); log.debug("Autosens data: " + (storedAutosens_data = "undefined"));
log.debug("Reservoir data: " + "undefined"); log.debug("Reservoir data: " + "undefined");
log.debug("MicroBolusAllowed: " + (storedMicroBolusAllowed = "" + mMicrobolusAllowed)); log.debug("MicroBolusAllowed: " + (storedMicroBolusAllowed = "" + mMicrobolusAllowed));
log.debug("SMBAlwaysAllowed: " + (storedSMBAlwaysAllowed = "" + mSMBAlwaysAllowed));
DetermineBasalResultSMB determineBasalResultSMB = null; DetermineBasalResultSMB determineBasalResultSMB = null;
@ -212,7 +213,8 @@ public class DetermineBasalAdapterSMBJS {
MealData mealData, MealData mealData,
double autosensDataRatio, double autosensDataRatio,
boolean tempTargetSet, boolean tempTargetSet,
boolean microBolusAllowed boolean microBolusAllowed,
boolean smbAlwaysAllowed
) throws JSONException { ) throws JSONException {
String units = profile.getUnits(); String units = profile.getUnits();
@ -229,8 +231,8 @@ public class DetermineBasalAdapterSMBJS {
mProfile.put("target_bg", targetBg); mProfile.put("target_bg", targetBg);
mProfile.put("carb_ratio", profile.getIc()); mProfile.put("carb_ratio", profile.getIc());
mProfile.put("sens", Profile.toMgdl(profile.getIsf(), units)); mProfile.put("sens", Profile.toMgdl(profile.getIsf(), units));
mProfile.put("max_daily_safety_multiplier", SP.getInt("openapsama_max_daily_safety_multiplier", 3)); mProfile.put("max_daily_safety_multiplier", SP.getInt(R.string.key_openapsama_max_daily_safety_multiplier, 3));
mProfile.put("current_basal_safety_multiplier", SP.getDouble("openapsama_current_basal_safety_multiplier", 4d)); mProfile.put("current_basal_safety_multiplier", SP.getDouble(R.string.key_openapsama_current_basal_safety_multiplier, 4d));
mProfile.put("high_temptarget_raises_sensitivity", SMBDefaults.high_temptarget_raises_sensitivity); mProfile.put("high_temptarget_raises_sensitivity", SMBDefaults.high_temptarget_raises_sensitivity);
mProfile.put("low_temptarget_lowers_sensitivity", SMBDefaults.low_temptarget_lowers_sensitivity); mProfile.put("low_temptarget_lowers_sensitivity", SMBDefaults.low_temptarget_lowers_sensitivity);
@ -246,12 +248,11 @@ public class DetermineBasalAdapterSMBJS {
mProfile.put("remainingCarbsCap", SMBDefaults.remainingCarbsCap); mProfile.put("remainingCarbsCap", SMBDefaults.remainingCarbsCap);
mProfile.put("enableUAM", SP.getBoolean(R.string.key_use_uam, false)); mProfile.put("enableUAM", SP.getBoolean(R.string.key_use_uam, false));
mProfile.put("A52_risk_enable", SMBDefaults.A52_risk_enable); mProfile.put("A52_risk_enable", SMBDefaults.A52_risk_enable);
boolean SMBEnabled = SP.getBoolean(R.string.key_use_smb, false) && MainApp.getConfigBuilder().isClosedModeEnabled(); mProfile.put("enableSMB_with_COB", SP.getBoolean(R.string.key_enableSMB_with_COB, false));
mProfile.put("enableSMB_with_COB", SMBEnabled && SP.getBoolean(R.string.key_enableSMB_with_COB, false)); mProfile.put("enableSMB_with_temptarget", SP.getBoolean(R.string.key_enableSMB_with_temptarget, false));
mProfile.put("enableSMB_with_temptarget", SMBEnabled && SP.getBoolean(R.string.key_enableSMB_with_temptarget, false)); mProfile.put("allowSMB_with_high_temptarget", SP.getBoolean(R.string.key_allowSMB_with_high_temptarget, false));
mProfile.put("allowSMB_with_high_temptarget", SMBEnabled && SP.getBoolean(R.string.key_allowSMB_with_high_temptarget, false)); mProfile.put("enableSMB_always", SP.getBoolean(R.string.key_enableSMB_always, false) && smbAlwaysAllowed);
mProfile.put("enableSMB_always", SMBEnabled && SP.getBoolean(R.string.key_enableSMB_always, false) && ConfigBuilderPlugin.getActiveBgSource().advancedFilteringSupported()); mProfile.put("enableSMB_after_carbs", SP.getBoolean(R.string.key_enableSMB_after_carbs, false) && smbAlwaysAllowed);
mProfile.put("enableSMB_after_carbs", SMBEnabled && SP.getBoolean(R.string.key_enableSMB_after_carbs, false) && ConfigBuilderPlugin.getActiveBgSource().advancedFilteringSupported());
mProfile.put("maxSMBBasalMinutes", SP.getInt("key_smbmaxminutes", SMBDefaults.maxSMBBasalMinutes)); mProfile.put("maxSMBBasalMinutes", SP.getInt("key_smbmaxminutes", SMBDefaults.maxSMBBasalMinutes));
mProfile.put("carbsReqThreshold", SMBDefaults.carbsReqThreshold); mProfile.put("carbsReqThreshold", SMBDefaults.carbsReqThreshold);
@ -302,7 +303,7 @@ public class DetermineBasalAdapterSMBJS {
mMealData.put("lastCarbTime", mealData.lastCarbTime); mMealData.put("lastCarbTime", mealData.lastCarbTime);
if (MainApp.getConfigBuilder().isAMAModeEnabled()) { if (MainApp.getConstraintChecker().isAutosensModeEnabled().value()) {
mAutosensData = new JSONObject(); mAutosensData = new JSONObject();
mAutosensData.put("ratio", autosensDataRatio); mAutosensData.put("ratio", autosensDataRatio);
} else { } else {
@ -310,6 +311,7 @@ public class DetermineBasalAdapterSMBJS {
mAutosensData.put("ratio", 1.0); mAutosensData.put("ratio", 1.0);
} }
mMicrobolusAllowed = microBolusAllowed; mMicrobolusAllowed = microBolusAllowed;
mSMBAlwaysAllowed = smbAlwaysAllowed;
} }

View file

@ -35,7 +35,7 @@ public class DetermineBasalResultSMB extends APSResult {
if (result.has("carbsReq")) carbsReq = result.getDouble("carbsReq"); if (result.has("carbsReq")) carbsReq = result.getDouble("carbsReq");
if (result.has("rate") && result.has("duration")) { if (result.has("rate") && result.has("duration")) {
tempBasalReqested = true; tempBasalRequested = true;
rate = result.getDouble("rate"); rate = result.getDouble("rate");
if (rate < 0d) rate = 0d; if (rate < 0d) rate = 0d;
duration = result.getInt("duration"); duration = result.getInt("duration");
@ -74,7 +74,7 @@ public class DetermineBasalResultSMB extends APSResult {
newResult.reason = reason; newResult.reason = reason;
newResult.rate = rate; newResult.rate = rate;
newResult.duration = duration; newResult.duration = duration;
newResult.tempBasalReqested = tempBasalReqested; newResult.tempBasalRequested = tempBasalRequested;
newResult.bolusRequested = bolusRequested; newResult.bolusRequested = bolusRequested;
newResult.rate = rate; newResult.rate = rate;
newResult.duration = duration; newResult.duration = duration;

View file

@ -16,6 +16,9 @@ import org.json.JSONException;
import org.slf4j.Logger; import org.slf4j.Logger;
import org.slf4j.LoggerFactory; import org.slf4j.LoggerFactory;
import butterknife.BindView;
import butterknife.ButterKnife;
import butterknife.OnClick;
import info.nightscout.androidaps.MainApp; import info.nightscout.androidaps.MainApp;
import info.nightscout.androidaps.R; import info.nightscout.androidaps.R;
import info.nightscout.androidaps.plugins.Common.SubscriberFragment; import info.nightscout.androidaps.plugins.Common.SubscriberFragment;
@ -24,19 +27,32 @@ import info.nightscout.androidaps.plugins.OpenAPSMA.events.EventOpenAPSUpdateRes
import info.nightscout.utils.FabricPrivacy; import info.nightscout.utils.FabricPrivacy;
import info.nightscout.utils.JSONFormatter; import info.nightscout.utils.JSONFormatter;
public class OpenAPSSMBFragment extends SubscriberFragment implements View.OnClickListener { public class OpenAPSSMBFragment extends SubscriberFragment {
private static Logger log = LoggerFactory.getLogger(OpenAPSSMBFragment.class); private static Logger log = LoggerFactory.getLogger(OpenAPSSMBFragment.class);
@BindView(R.id.openapsma_run)
Button run; Button run;
@BindView(R.id.openapsma_lastrun)
TextView lastRunView; TextView lastRunView;
@BindView(R.id.openapsma_constraints)
TextView constraintsView;
@BindView(R.id.openapsma_glucosestatus)
TextView glucoseStatusView; TextView glucoseStatusView;
@BindView(R.id.openapsma_currenttemp)
TextView currentTempView; TextView currentTempView;
@BindView(R.id.openapsma_iobdata)
TextView iobDataView; TextView iobDataView;
@BindView(R.id.openapsma_profile)
TextView profileView; TextView profileView;
@BindView(R.id.openapsma_mealdata)
TextView mealDataView; TextView mealDataView;
@BindView(R.id.openapsma_autosensdata)
TextView autosensDataView; TextView autosensDataView;
@BindView(R.id.openapsma_result)
TextView resultView; TextView resultView;
@BindView(R.id.openapsma_scriptdebugdata)
TextView scriptdebugView; TextView scriptdebugView;
@BindView(R.id.openapsma_request)
TextView requestView; TextView requestView;
@Override @Override
@ -44,32 +60,14 @@ public class OpenAPSSMBFragment extends SubscriberFragment implements View.OnCli
Bundle savedInstanceState) { Bundle savedInstanceState) {
View view = inflater.inflate(R.layout.openapsama_fragment, container, false); View view = inflater.inflate(R.layout.openapsama_fragment, container, false);
run = (Button) view.findViewById(R.id.openapsma_run); unbinder = ButterKnife.bind(this, view);
run.setOnClickListener(this);
lastRunView = (TextView) view.findViewById(R.id.openapsma_lastrun);
glucoseStatusView = (TextView) view.findViewById(R.id.openapsma_glucosestatus);
currentTempView = (TextView) view.findViewById(R.id.openapsma_currenttemp);
iobDataView = (TextView) view.findViewById(R.id.openapsma_iobdata);
profileView = (TextView) view.findViewById(R.id.openapsma_profile);
mealDataView = (TextView) view.findViewById(R.id.openapsma_mealdata);
autosensDataView = (TextView) view.findViewById(R.id.openapsma_autosensdata);
scriptdebugView = (TextView) view.findViewById(R.id.openapsma_scriptdebugdata);
resultView = (TextView) view.findViewById(R.id.openapsma_result);
requestView = (TextView) view.findViewById(R.id.openapsma_request);
updateGUI();
return view; return view;
} }
@Override @OnClick(R.id.openapsma_run)
public void onClick(View view) { public void onRunClick() {
switch (view.getId()) { OpenAPSSMBPlugin.getPlugin().invoke("OpenAPSSMB button");
case R.id.openapsma_run: FabricPrivacy.getInstance().logCustom(new CustomEvent("OpenAPS_SMB_Run"));
OpenAPSSMBPlugin.getPlugin().invoke("OpenAPSSMB button");
FabricPrivacy.getInstance().logCustom(new CustomEvent("OpenAPS_SMB_Run"));
break;
}
} }
@Subscribe @Subscribe
@ -109,6 +107,8 @@ public class OpenAPSSMBFragment extends SubscriberFragment implements View.OnCli
profileView.setText(JSONFormatter.format(determineBasalAdapterSMBJS.getProfileParam())); profileView.setText(JSONFormatter.format(determineBasalAdapterSMBJS.getProfileParam()));
mealDataView.setText(JSONFormatter.format(determineBasalAdapterSMBJS.getMealDataParam())); mealDataView.setText(JSONFormatter.format(determineBasalAdapterSMBJS.getMealDataParam()));
scriptdebugView.setText(determineBasalAdapterSMBJS.getScriptDebug()); scriptdebugView.setText(determineBasalAdapterSMBJS.getScriptDebug());
if (lastAPSResult != null && lastAPSResult.inputConstraints != null)
constraintsView.setText(lastAPSResult.inputConstraints.getReasons());
} }
if (plugin.lastAPSRun != null) { if (plugin.lastAPSRun != null) {
lastRunView.setText(plugin.lastAPSRun.toLocaleString()); lastRunView.setText(plugin.lastAPSRun.toLocaleString());

View file

@ -8,6 +8,7 @@ import java.io.IOException;
import java.util.Date; import java.util.Date;
import info.nightscout.androidaps.Config; import info.nightscout.androidaps.Config;
import info.nightscout.androidaps.Constants;
import info.nightscout.androidaps.MainApp; import info.nightscout.androidaps.MainApp;
import info.nightscout.androidaps.R; import info.nightscout.androidaps.R;
import info.nightscout.androidaps.data.GlucoseStatus; import info.nightscout.androidaps.data.GlucoseStatus;
@ -17,6 +18,7 @@ import info.nightscout.androidaps.data.Profile;
import info.nightscout.androidaps.db.TempTarget; import info.nightscout.androidaps.db.TempTarget;
import info.nightscout.androidaps.db.TemporaryBasal; import info.nightscout.androidaps.db.TemporaryBasal;
import info.nightscout.androidaps.interfaces.APSInterface; import info.nightscout.androidaps.interfaces.APSInterface;
import info.nightscout.androidaps.interfaces.Constraint;
import info.nightscout.androidaps.interfaces.PluginBase; import info.nightscout.androidaps.interfaces.PluginBase;
import info.nightscout.androidaps.interfaces.PumpInterface; import info.nightscout.androidaps.interfaces.PumpInterface;
import info.nightscout.androidaps.plugins.ConfigBuilder.ConfigBuilderPlugin; import info.nightscout.androidaps.plugins.ConfigBuilder.ConfigBuilderPlugin;
@ -79,7 +81,7 @@ public class OpenAPSSMBPlugin implements PluginBase, APSInterface {
@Override @Override
public boolean isEnabled(int type) { public boolean isEnabled(int type) {
boolean pumpCapable = ConfigBuilderPlugin.getActivePump() == null || ConfigBuilderPlugin.getActivePump().getPumpDescription().isTempBasalCapable; boolean pumpCapable = ConfigBuilderPlugin.getActivePump() == null || ConfigBuilderPlugin.getActivePump() != null && ConfigBuilderPlugin.getActivePump().getPumpDescription().isTempBasalCapable;
return type == APS && fragmentEnabled && pumpCapable; return type == APS && fragmentEnabled && pumpCapable;
} }
@ -115,7 +117,7 @@ public class OpenAPSSMBPlugin implements PluginBase, APSInterface {
} }
@Override @Override
public void setFragmentEnabled(int type, boolean fragmentEnabled) { public void setPluginEnabled(int type, boolean fragmentEnabled) {
if (type == APS) this.fragmentEnabled = fragmentEnabled; if (type == APS) this.fragmentEnabled = fragmentEnabled;
} }
@ -178,8 +180,11 @@ public class OpenAPSSMBPlugin implements PluginBase, APSInterface {
String units = profile.getUnits(); String units = profile.getUnits();
double maxIob = SP.getDouble("openapsma_max_iob", 1.5d); Constraint<Double> inputConstraints = new Constraint<>(0d); // fake. only for collecting all results
double maxBasal = SP.getDouble("openapsma_max_basal", 1d);
Constraint<Double> maxBasalConstraint = MainApp.getConstraintChecker().getMaxBasalAllowed(profile);
inputConstraints.copyReasons(maxBasalConstraint);
double maxBasal = maxBasalConstraint.value();
double minBg = Profile.toMgdl(profile.getTargetLow(), units); double minBg = Profile.toMgdl(profile.getTargetLow(), units);
double maxBg = Profile.toMgdl(profile.getTargetHigh(), units); double maxBg = Profile.toMgdl(profile.getTargetHigh(), units);
double targetBg = Profile.toMgdl(profile.getTarget(), units); double targetBg = Profile.toMgdl(profile.getTarget(), units);
@ -196,7 +201,7 @@ public class OpenAPSSMBPlugin implements PluginBase, APSInterface {
MealData mealData = MainApp.getConfigBuilder().getMealData(); MealData mealData = MainApp.getConfigBuilder().getMealData();
Profiler.log(log, "getMealData()", startPart); Profiler.log(log, "getMealData()", startPart);
maxIob = MainApp.getConfigBuilder().applyMaxIOBConstraints(maxIob); double maxIob = MainApp.getConstraintChecker().getMaxIOBAllowed().value();
minBg = verifyHardLimits(minBg, "minBg", HardLimits.VERY_HARD_LIMIT_MIN_BG[0], HardLimits.VERY_HARD_LIMIT_MIN_BG[1]); minBg = verifyHardLimits(minBg, "minBg", HardLimits.VERY_HARD_LIMIT_MIN_BG[0], HardLimits.VERY_HARD_LIMIT_MIN_BG[1]);
maxBg = verifyHardLimits(maxBg, "maxBg", HardLimits.VERY_HARD_LIMIT_MAX_BG[0], HardLimits.VERY_HARD_LIMIT_MAX_BG[1]); maxBg = verifyHardLimits(maxBg, "maxBg", HardLimits.VERY_HARD_LIMIT_MAX_BG[0], HardLimits.VERY_HARD_LIMIT_MAX_BG[1]);
@ -212,9 +217,6 @@ public class OpenAPSSMBPlugin implements PluginBase, APSInterface {
} }
maxIob = verifyHardLimits(maxIob, "maxIob", 0, HardLimits.maxIobSMB());
maxBasal = verifyHardLimits(maxBasal, "max_basal", 0.1, HardLimits.maxBasal());
if (!checkOnlyHardLimits(profile.getDia(), "dia", HardLimits.MINDIA, HardLimits.MAXDIA)) return; if (!checkOnlyHardLimits(profile.getDia(), "dia", HardLimits.MINDIA, HardLimits.MAXDIA)) return;
if (!checkOnlyHardLimits(profile.getIcTimeFromMidnight(profile.secondsFromMidnight()), "carbratio", HardLimits.MINIC, HardLimits.MAXIC)) if (!checkOnlyHardLimits(profile.getIcTimeFromMidnight(profile.secondsFromMidnight()), "carbratio", HardLimits.MINIC, HardLimits.MAXIC))
return; return;
@ -224,11 +226,20 @@ public class OpenAPSSMBPlugin implements PluginBase, APSInterface {
if (!checkOnlyHardLimits(pump.getBaseBasalRate(), "current_basal", 0.01, HardLimits.maxBasal())) return; if (!checkOnlyHardLimits(pump.getBaseBasalRate(), "current_basal", 0.01, HardLimits.maxBasal())) return;
startPart = new Date(); startPart = new Date();
if (MainApp.getConfigBuilder().isAMAModeEnabled()) { if (MainApp.getConstraintChecker().isAutosensModeEnabled().value()) {
lastAutosensResult = IobCobCalculatorPlugin.getPlugin().detectSensitivityWithLock(IobCobCalculatorPlugin.oldestDataAvailable(), System.currentTimeMillis()); lastAutosensResult = IobCobCalculatorPlugin.getPlugin().detectSensitivityWithLock(IobCobCalculatorPlugin.oldestDataAvailable(), System.currentTimeMillis());
} else { } else {
lastAutosensResult = new AutosensResult(); lastAutosensResult = new AutosensResult();
} }
Constraint<Boolean> smbAllowed = new Constraint<>(true);
MainApp.getConstraintChecker().isSMBModeEnabled(smbAllowed);
inputConstraints.copyReasons(smbAllowed);
Constraint<Boolean> smbAlwaysEnabled = new Constraint<>(true);
MainApp.getConstraintChecker().isAdvancedFilteringEnabled(smbAlwaysEnabled);
inputConstraints.copyReasons(smbAlwaysEnabled);
Profiler.log(log, "detectSensitivityandCarbAbsorption()", startPart); Profiler.log(log, "detectSensitivityandCarbAbsorption()", startPart);
Profiler.log(log, "SMB data gathering", start); Profiler.log(log, "SMB data gathering", start);
@ -237,7 +248,8 @@ public class OpenAPSSMBPlugin implements PluginBase, APSInterface {
determineBasalAdapterSMBJS.setData(profile, maxIob, maxBasal, minBg, maxBg, targetBg, ConfigBuilderPlugin.getActivePump().getBaseBasalRate(), iobArray, glucoseStatus, mealData, determineBasalAdapterSMBJS.setData(profile, maxIob, maxBasal, minBg, maxBg, targetBg, ConfigBuilderPlugin.getActivePump().getBaseBasalRate(), iobArray, glucoseStatus, mealData,
lastAutosensResult.ratio, //autosensDataRatio lastAutosensResult.ratio, //autosensDataRatio
isTempTarget, isTempTarget,
true //microBolusAllowed smbAllowed.value(),
smbAlwaysEnabled.value()
); );
} catch (JSONException e) { } catch (JSONException e) {
log.error(e.getMessage()); log.error(e.getMessage());
@ -251,16 +263,16 @@ public class OpenAPSSMBPlugin implements PluginBase, APSInterface {
// TODO still needed with oref1? // TODO still needed with oref1?
// Fix bug determine basal // Fix bug determine basal
if (determineBasalResultSMB.rate == 0d && determineBasalResultSMB.duration == 0 && !MainApp.getConfigBuilder().isTempBasalInProgress()) if (determineBasalResultSMB.rate == 0d && determineBasalResultSMB.duration == 0 && !MainApp.getConfigBuilder().isTempBasalInProgress())
determineBasalResultSMB.tempBasalReqested = false; determineBasalResultSMB.tempBasalRequested = false;
// limit requests on openloop mode // limit requests on openloop mode
if (!MainApp.getConfigBuilder().isClosedModeEnabled()) { if (!MainApp.getConstraintChecker().isClosedLoopAllowed().value()) {
TemporaryBasal activeTemp = MainApp.getConfigBuilder().getTempBasalFromHistory(now); TemporaryBasal activeTemp = MainApp.getConfigBuilder().getTempBasalFromHistory(now);
if (activeTemp != null && determineBasalResultSMB.rate == 0 && determineBasalResultSMB.duration == 0) { if (activeTemp != null && determineBasalResultSMB.rate == 0 && determineBasalResultSMB.duration == 0) {
// going to cancel // going to cancel
} else if (activeTemp != null && Math.abs(determineBasalResultSMB.rate - activeTemp.tempBasalConvertedToAbsolute(now, profile)) < 0.1) { } else if (activeTemp != null && Math.abs(determineBasalResultSMB.rate - activeTemp.tempBasalConvertedToAbsolute(now, profile)) < 0.1) {
determineBasalResultSMB.tempBasalReqested = false; determineBasalResultSMB.tempBasalRequested = false;
} else if (activeTemp == null && Math.abs(determineBasalResultSMB.rate - ConfigBuilderPlugin.getActivePump().getBaseBasalRate()) < 0.1) } else if (activeTemp == null && Math.abs(determineBasalResultSMB.rate - ConfigBuilderPlugin.getActivePump().getBaseBasalRate()) < 0.1)
determineBasalResultSMB.tempBasalReqested = false; determineBasalResultSMB.tempBasalRequested = false;
} }
determineBasalResultSMB.iob = iobArray[0]; determineBasalResultSMB.iob = iobArray[0];
@ -271,6 +283,8 @@ public class OpenAPSSMBPlugin implements PluginBase, APSInterface {
log.error("Unhandled exception", e); log.error("Unhandled exception", e);
} }
determineBasalResultSMB.inputConstraints = inputConstraints;
lastDetermineBasalAdapterSMBJS = determineBasalAdapterSMBJS; lastDetermineBasalAdapterSMBJS = determineBasalAdapterSMBJS;
lastAPSResult = determineBasalResultSMB; lastAPSResult = determineBasalResultSMB;
lastAPSRun = new Date(now); lastAPSRun = new Date(now);

View file

@ -43,6 +43,7 @@ import info.nightscout.androidaps.data.Profile;
import info.nightscout.androidaps.db.CareportalEvent; import info.nightscout.androidaps.db.CareportalEvent;
import info.nightscout.androidaps.db.Source; import info.nightscout.androidaps.db.Source;
import info.nightscout.androidaps.db.TempTarget; import info.nightscout.androidaps.db.TempTarget;
import info.nightscout.androidaps.interfaces.Constraint;
import info.nightscout.androidaps.plugins.ConfigBuilder.ConfigBuilderPlugin; import info.nightscout.androidaps.plugins.ConfigBuilder.ConfigBuilderPlugin;
import info.nightscout.androidaps.queue.Callback; import info.nightscout.androidaps.queue.Callback;
import info.nightscout.utils.DateUtil; import info.nightscout.utils.DateUtil;
@ -120,7 +121,7 @@ public class NewCarbsDialog extends DialogFragment implements OnClickListener, D
getDialog().getWindow().requestFeature(Window.FEATURE_NO_TITLE); getDialog().getWindow().requestFeature(Window.FEATURE_NO_TITLE);
getDialog().getWindow().setSoftInputMode(WindowManager.LayoutParams.SOFT_INPUT_STATE_HIDDEN); getDialog().getWindow().setSoftInputMode(WindowManager.LayoutParams.SOFT_INPUT_STATE_HIDDEN);
maxCarbs = MainApp.getConfigBuilder().applyCarbsConstraints(Constants.carbsOnlyForCheckLimit); maxCarbs = MainApp.getConstraintChecker().getMaxCarbsAllowed().value();
editCarbs = view.findViewById(R.id.newcarb_carbsamount); editCarbs = view.findViewById(R.id.newcarb_carbsamount);
@ -303,7 +304,7 @@ public class NewCarbsDialog extends DialogFragment implements OnClickListener, D
okClicked = true; okClicked = true;
try { try {
final Integer carbs = SafeParse.stringToInt(editCarbs.getText()); final Integer carbs = SafeParse.stringToInt(editCarbs.getText());
Integer carbsAfterConstraints = MainApp.getConfigBuilder().applyCarbsConstraints(carbs); Integer carbsAfterConstraints = MainApp.getConstraintChecker().applyCarbsConstraints(new Constraint<>(carbs)).value();
List<String> actions = new LinkedList<>(); List<String> actions = new LinkedList<>();
if (carbs > 0) if (carbs > 0)

View file

@ -44,9 +44,11 @@ import info.nightscout.androidaps.data.Profile;
import info.nightscout.androidaps.db.CareportalEvent; import info.nightscout.androidaps.db.CareportalEvent;
import info.nightscout.androidaps.db.Source; import info.nightscout.androidaps.db.Source;
import info.nightscout.androidaps.db.TempTarget; import info.nightscout.androidaps.db.TempTarget;
import info.nightscout.androidaps.interfaces.Constraint;
import info.nightscout.androidaps.plugins.ConfigBuilder.ConfigBuilderPlugin; import info.nightscout.androidaps.plugins.ConfigBuilder.ConfigBuilderPlugin;
import info.nightscout.androidaps.queue.Callback; import info.nightscout.androidaps.queue.Callback;
import info.nightscout.utils.DateUtil; import info.nightscout.utils.DateUtil;
import info.nightscout.utils.DecimalFormatter;
import info.nightscout.utils.NumberPicker; import info.nightscout.utils.NumberPicker;
import info.nightscout.utils.SP; import info.nightscout.utils.SP;
import info.nightscout.utils.SafeParse; import info.nightscout.utils.SafeParse;
@ -119,11 +121,11 @@ public class NewInsulinDialog extends DialogFragment implements OnClickListener,
getDialog().getWindow().requestFeature(Window.FEATURE_NO_TITLE); getDialog().getWindow().requestFeature(Window.FEATURE_NO_TITLE);
getDialog().getWindow().setSoftInputMode(WindowManager.LayoutParams.SOFT_INPUT_STATE_HIDDEN); getDialog().getWindow().setSoftInputMode(WindowManager.LayoutParams.SOFT_INPUT_STATE_HIDDEN);
maxInsulin = MainApp.getConfigBuilder().applyBolusConstraints(Constants.bolusOnlyForCheckLimit); maxInsulin = MainApp.getConstraintChecker().getMaxBolusAllowed().value();
editInsulin = (NumberPicker) view.findViewById(R.id.treatments_newinsulin_amount); editInsulin = (NumberPicker) view.findViewById(R.id.treatments_newinsulin_amount);
editInsulin.setParams(0d, 0d, maxInsulin, ConfigBuilderPlugin.getActivePump().getPumpDescription().bolusStep, new DecimalFormat("0.00"), false, textWatcher); editInsulin.setParams(0d, 0d, maxInsulin, ConfigBuilderPlugin.getActivePump().getPumpDescription().bolusStep, DecimalFormatter.pumpSupportedBolusFormat(), false, textWatcher);
dateButton = (TextView) view.findViewById(R.id.newinsulin_eventdate); dateButton = (TextView) view.findViewById(R.id.newinsulin_eventdate);
timeButton = (TextView) view.findViewById(R.id.newinsulin_eventtime); timeButton = (TextView) view.findViewById(R.id.newinsulin_eventtime);
@ -159,7 +161,8 @@ public class NewInsulinDialog extends DialogFragment implements OnClickListener,
} }
private String toSignedString(double value) { private String toSignedString(double value) {
return value > 0 ? "+" + value : String.valueOf(value); String formatted = DecimalFormatter.toPumpSupportedBolus(value);
return value > 0 ? "+" + formatted : formatted;
} }
@Override @Override
@ -223,7 +226,7 @@ public class NewInsulinDialog extends DialogFragment implements OnClickListener,
try { try {
Double insulin = SafeParse.stringToDouble(editInsulin.getText()); Double insulin = SafeParse.stringToDouble(editInsulin.getText());
Double insulinAfterConstraints = MainApp.getConfigBuilder().applyBolusConstraints(insulin); Double insulinAfterConstraints = MainApp.getConstraintChecker().applyBolusConstraints(new Constraint<>(insulin)).value();
List<String> actions = new LinkedList<>(); List<String> actions = new LinkedList<>();
if (insulin > 0) { if (insulin > 0) {

View file

@ -31,6 +31,7 @@ import info.nightscout.androidaps.R;
import info.nightscout.androidaps.data.DetailedBolusInfo; import info.nightscout.androidaps.data.DetailedBolusInfo;
import info.nightscout.androidaps.db.CareportalEvent; import info.nightscout.androidaps.db.CareportalEvent;
import info.nightscout.androidaps.db.Source; import info.nightscout.androidaps.db.Source;
import info.nightscout.androidaps.interfaces.Constraint;
import info.nightscout.androidaps.plugins.ConfigBuilder.ConfigBuilderPlugin; import info.nightscout.androidaps.plugins.ConfigBuilder.ConfigBuilderPlugin;
import info.nightscout.androidaps.queue.Callback; import info.nightscout.androidaps.queue.Callback;
import info.nightscout.utils.FabricPrivacy; import info.nightscout.utils.FabricPrivacy;
@ -95,8 +96,8 @@ public class NewTreatmentDialog extends DialogFragment implements OnClickListene
getDialog().getWindow().requestFeature(Window.FEATURE_NO_TITLE); getDialog().getWindow().requestFeature(Window.FEATURE_NO_TITLE);
getDialog().getWindow().setSoftInputMode(WindowManager.LayoutParams.SOFT_INPUT_STATE_HIDDEN); getDialog().getWindow().setSoftInputMode(WindowManager.LayoutParams.SOFT_INPUT_STATE_HIDDEN);
maxCarbs = MainApp.getConfigBuilder().applyCarbsConstraints(Constants.carbsOnlyForCheckLimit); maxCarbs = MainApp.getConstraintChecker().getMaxCarbsAllowed().value();
maxInsulin = MainApp.getConfigBuilder().applyBolusConstraints(Constants.bolusOnlyForCheckLimit); maxInsulin = MainApp.getConstraintChecker().getMaxBolusAllowed().value();
editCarbs = (NumberPicker) view.findViewById(R.id.treatments_newtreatment_carbsamount); editCarbs = (NumberPicker) view.findViewById(R.id.treatments_newtreatment_carbsamount);
editInsulin = (NumberPicker) view.findViewById(R.id.treatments_newtreatment_insulinamount); editInsulin = (NumberPicker) view.findViewById(R.id.treatments_newtreatment_insulinamount);
@ -128,8 +129,8 @@ public class NewTreatmentDialog extends DialogFragment implements OnClickListene
String confirmMessage = MainApp.gs(R.string.entertreatmentquestion) + "<br/>"; String confirmMessage = MainApp.gs(R.string.entertreatmentquestion) + "<br/>";
Double insulinAfterConstraints = MainApp.getConfigBuilder().applyBolusConstraints(insulin); Double insulinAfterConstraints = MainApp.getConstraintChecker().applyBolusConstraints(new Constraint<>(insulin)).value();
Integer carbsAfterConstraints = MainApp.getConfigBuilder().applyCarbsConstraints(carbs); Integer carbsAfterConstraints = MainApp.getConstraintChecker().applyCarbsConstraints(new Constraint<>(carbs)).value();
if (insulin > 0) { if (insulin > 0) {
confirmMessage += MainApp.gs(R.string.bolus) + ": " + "<font color='" + MainApp.gc(R.color.colorCarbsButton) + "'>" + insulinAfterConstraints + "U" + "</font>"; confirmMessage += MainApp.gs(R.string.bolus) + ": " + "<font color='" + MainApp.gc(R.color.colorCarbsButton) + "'>" + insulinAfterConstraints + "U" + "</font>";

View file

@ -52,16 +52,17 @@ import info.nightscout.androidaps.db.TempTarget;
import info.nightscout.androidaps.events.EventFeatureRunning; import info.nightscout.androidaps.events.EventFeatureRunning;
import info.nightscout.androidaps.events.EventNewBG; import info.nightscout.androidaps.events.EventNewBG;
import info.nightscout.androidaps.events.EventRefreshOverview; import info.nightscout.androidaps.events.EventRefreshOverview;
import info.nightscout.androidaps.interfaces.Constraint;
import info.nightscout.androidaps.plugins.ConfigBuilder.ConfigBuilderPlugin; import info.nightscout.androidaps.plugins.ConfigBuilder.ConfigBuilderPlugin;
import info.nightscout.androidaps.plugins.IobCobCalculator.AutosensData; import info.nightscout.androidaps.plugins.IobCobCalculator.AutosensData;
import info.nightscout.androidaps.plugins.IobCobCalculator.IobCobCalculatorPlugin; import info.nightscout.androidaps.plugins.IobCobCalculator.IobCobCalculatorPlugin;
import info.nightscout.androidaps.plugins.IobCobCalculator.events.EventAutosensCalculationFinished; import info.nightscout.androidaps.plugins.IobCobCalculator.events.EventAutosensCalculationFinished;
import info.nightscout.androidaps.plugins.Loop.LoopPlugin; import info.nightscout.androidaps.plugins.Loop.LoopPlugin;
import info.nightscout.androidaps.queue.Callback; import info.nightscout.androidaps.queue.Callback;
import info.nightscout.utils.FabricPrivacy;
import info.nightscout.utils.BolusWizard; import info.nightscout.utils.BolusWizard;
import info.nightscout.utils.DateUtil; import info.nightscout.utils.DateUtil;
import info.nightscout.utils.DecimalFormatter; import info.nightscout.utils.DecimalFormatter;
import info.nightscout.utils.FabricPrivacy;
import info.nightscout.utils.NumberPicker; import info.nightscout.utils.NumberPicker;
import info.nightscout.utils.SP; import info.nightscout.utils.SP;
import info.nightscout.utils.SafeParse; import info.nightscout.utils.SafeParse;
@ -142,16 +143,14 @@ public class WizardDialog extends DialogFragment implements OnClickListener, Com
@Subscribe @Subscribe
public void onStatusEvent(final EventNewBG e) { public void onStatusEvent(final EventNewBG e) {
if (e.isFromActiveBgSource && e.isNew && e.isCurrent()) { Activity activity = getActivity();
Activity activity = getActivity(); if (activity != null)
if (activity != null) activity.runOnUiThread(new Runnable() {
activity.runOnUiThread(new Runnable() { @Override
@Override public void run() {
public void run() { calculateInsulin();
calculateInsulin(); }
} });
});
}
} }
@Subscribe @Subscribe
@ -238,13 +237,13 @@ public class WizardDialog extends DialogFragment implements OnClickListener, Com
superbolusCheckbox.setVisibility(SP.getBoolean(R.string.key_usesuperbolus, false) ? View.VISIBLE : View.GONE); superbolusCheckbox.setVisibility(SP.getBoolean(R.string.key_usesuperbolus, false) ? View.VISIBLE : View.GONE);
Integer maxCarbs = MainApp.getConfigBuilder().applyCarbsConstraints(Constants.carbsOnlyForCheckLimit); Integer maxCarbs = MainApp.getConstraintChecker().getMaxCarbsAllowed().value();
Double maxCorrection = MainApp.getConfigBuilder().applyBolusConstraints(Constants.bolusOnlyForCheckLimit); Double maxCorrection = MainApp.getConstraintChecker().getMaxBolusAllowed().value();
editBg.setParams(0d, 0d, 500d, 0.1d, new DecimalFormat("0.0"), false, textWatcher); editBg.setParams(0d, 0d, 500d, 0.1d, new DecimalFormat("0.0"), false, textWatcher);
editCarbs.setParams(0d, 0d, (double) maxCarbs, 1d, new DecimalFormat("0"), false, textWatcher); editCarbs.setParams(0d, 0d, (double) maxCarbs, 1d, new DecimalFormat("0"), false, textWatcher);
double bolusstep = ConfigBuilderPlugin.getActivePump().getPumpDescription().bolusStep; double bolusstep = ConfigBuilderPlugin.getActivePump().getPumpDescription().bolusStep;
editCorr.setParams(0d, -maxCorrection, maxCorrection, bolusstep, new DecimalFormat("0.00"), false, textWatcher); editCorr.setParams(0d, -maxCorrection, maxCorrection, bolusstep, DecimalFormatter.pumpSupportedBolusFormat(), false, textWatcher);
editCarbTime.setParams(0d, -60d, 60d, 5d, new DecimalFormat("0"), false); editCarbTime.setParams(0d, -60d, 60d, 5d, new DecimalFormat("0"), false);
initDialog(); initDialog();
@ -261,19 +260,13 @@ public class WizardDialog extends DialogFragment implements OnClickListener, Com
} }
private void saveCheckedStates() { private void saveCheckedStates() {
//SP.putBoolean(getString(R.string.key_wizard_include_bg), bgCheckbox.isChecked());
SP.putBoolean(getString(R.string.key_wizard_include_cob), cobCheckbox.isChecked()); SP.putBoolean(getString(R.string.key_wizard_include_cob), cobCheckbox.isChecked());
SP.putBoolean(getString(R.string.key_wizard_include_trend_bg), bgtrendCheckbox.isChecked()); SP.putBoolean(getString(R.string.key_wizard_include_trend_bg), bgtrendCheckbox.isChecked());
//SP.putBoolean(getString(R.string.key_wizard_include_bolus_iob), bolusIobCheckbox.isChecked());
//SP.putBoolean(getString(R.string.key_wizard_include_basal_iob), basalIobCheckbox.isChecked());
} }
private void loadCheckedStates() { private void loadCheckedStates() {
//bgCheckbox.setChecked(SP.getBoolean(getString(R.string.key_wizard_include_bg), true));
bgtrendCheckbox.setChecked(SP.getBoolean(getString(R.string.key_wizard_include_trend_bg), false)); bgtrendCheckbox.setChecked(SP.getBoolean(getString(R.string.key_wizard_include_trend_bg), false));
cobCheckbox.setChecked(SP.getBoolean(getString(R.string.key_wizard_include_cob), false)); cobCheckbox.setChecked(SP.getBoolean(getString(R.string.key_wizard_include_cob), false));
//bolusIobCheckbox.setChecked(SP.getBoolean(getString(R.string.key_wizard_include_bolus_iob), true));
//basalIobCheckbox.setChecked(SP.getBoolean(getString(R.string.key_wizard_include_basal_iob), true));
} }
@Override @Override
@ -298,13 +291,15 @@ public class WizardDialog extends DialogFragment implements OnClickListener, Com
return; return;
} }
okClicked = true; okClicked = true;
if (calculatedTotalInsulin > 0d || calculatedCarbs > 0d) { final Profile profile = MainApp.getConfigBuilder().getProfile();
if (profile != null && (calculatedTotalInsulin > 0d || calculatedCarbs > 0d)) {
DecimalFormat formatNumber2decimalplaces = new DecimalFormat("0.00"); DecimalFormat formatNumber2decimalplaces = new DecimalFormat("0.00");
String confirmMessage = getString(R.string.entertreatmentquestion); String confirmMessage = getString(R.string.entertreatmentquestion);
Double insulinAfterConstraints = MainApp.getConfigBuilder().applyBolusConstraints(calculatedTotalInsulin); Double insulinAfterConstraints = MainApp.getConstraintChecker().applyBolusConstraints(new Constraint<>(calculatedTotalInsulin)).value();
Integer carbsAfterConstraints = MainApp.getConfigBuilder().applyCarbsConstraints(calculatedCarbs); Integer carbsAfterConstraints = MainApp.getConstraintChecker().applyCarbsConstraints(new Constraint<>(calculatedCarbs)).value();
confirmMessage += "<br/>" + getString(R.string.bolus) + ": " + "<font color='" + MainApp.sResources.getColor(R.color.bolus) + "'>" + formatNumber2decimalplaces.format(insulinAfterConstraints) + "U" + "</font>"; confirmMessage += "<br/>" + getString(R.string.bolus) + ": " + "<font color='" + MainApp.sResources.getColor(R.color.bolus) + "'>" + formatNumber2decimalplaces.format(insulinAfterConstraints) + "U" + "</font>";
confirmMessage += "<br/>" + getString(R.string.carbs) + ": " + carbsAfterConstraints + "g"; confirmMessage += "<br/>" + getString(R.string.carbs) + ": " + carbsAfterConstraints + "g";
@ -343,7 +338,7 @@ public class WizardDialog extends DialogFragment implements OnClickListener, Com
activeloop.superBolusTo(System.currentTimeMillis() + 2 * 60L * 60 * 1000); activeloop.superBolusTo(System.currentTimeMillis() + 2 * 60L * 60 * 1000);
MainApp.bus().post(new EventRefreshOverview("WizardDialog")); MainApp.bus().post(new EventRefreshOverview("WizardDialog"));
} }
ConfigBuilderPlugin.getCommandQueue().tempBasalPercent(0, 120, true, new Callback() { ConfigBuilderPlugin.getCommandQueue().tempBasalPercent(0, 120, true, profile, new Callback() {
@Override @Override
public void run() { public void run() {
if (!result.success) { if (!result.success) {
@ -460,13 +455,15 @@ public class WizardDialog extends DialogFragment implements OnClickListener, Com
Double c_bg = SafeParse.stringToDouble(editBg.getText()); Double c_bg = SafeParse.stringToDouble(editBg.getText());
Integer c_carbs = SafeParse.stringToInt(editCarbs.getText()); Integer c_carbs = SafeParse.stringToInt(editCarbs.getText());
Double c_correction = SafeParse.stringToDouble(editCorr.getText()); Double c_correction = SafeParse.stringToDouble(editCorr.getText());
Double corrAfterConstraint = MainApp.getConfigBuilder().applyBolusConstraints(c_correction); Double corrAfterConstraint = c_correction;
if (c_correction > 0)
c_correction = MainApp.getConstraintChecker().applyBolusConstraints(new Constraint<>(c_correction)).value();
if (c_correction - corrAfterConstraint != 0) { // c_correction != corrAfterConstraint doesn't work if (c_correction - corrAfterConstraint != 0) { // c_correction != corrAfterConstraint doesn't work
editCorr.setValue(0d); editCorr.setValue(0d);
ToastUtils.showToastInUiThread(MainApp.instance().getApplicationContext(), getString(R.string.bolusconstraintapplied)); ToastUtils.showToastInUiThread(MainApp.instance().getApplicationContext(), getString(R.string.bolusconstraintapplied));
return; return;
} }
Integer carbsAfterConstraint = MainApp.getConfigBuilder().applyCarbsConstraints(c_carbs); Integer carbsAfterConstraint = MainApp.getConstraintChecker().applyCarbsConstraints(new Constraint<>(c_carbs)).value();
if (c_carbs - carbsAfterConstraint != 0) { if (c_carbs - carbsAfterConstraint != 0) {
editCarbs.setValue(0d); editCarbs.setValue(0d);
ToastUtils.showToastInUiThread(MainApp.instance().getApplicationContext(), getString(R.string.carbsconstraintapplied)); ToastUtils.showToastInUiThread(MainApp.instance().getApplicationContext(), getString(R.string.carbsconstraintapplied));
@ -533,7 +530,7 @@ public class WizardDialog extends DialogFragment implements OnClickListener, Com
} }
if (calculatedTotalInsulin > 0d || calculatedCarbs > 0d) { if (calculatedTotalInsulin > 0d || calculatedCarbs > 0d) {
String insulinText = calculatedTotalInsulin > 0d ? (DecimalFormatter.to2Decimal(calculatedTotalInsulin) + "U") : ""; String insulinText = calculatedTotalInsulin > 0d ? (DecimalFormatter.toPumpSupportedBolus(calculatedTotalInsulin) + "U") : "";
String carbsText = calculatedCarbs > 0d ? (DecimalFormatter.to0Decimal(calculatedCarbs) + "g") : ""; String carbsText = calculatedCarbs > 0d ? (DecimalFormatter.to0Decimal(calculatedCarbs) + "g") : "";
total.setText(MainApp.gs(R.string.result) + ": " + insulinText + " " + carbsText); total.setText(MainApp.gs(R.string.result) + ": " + insulinText + " " + carbsText);
okButton.setVisibility(View.VISIBLE); okButton.setVisibility(View.VISIBLE);

View file

@ -87,6 +87,7 @@ import info.nightscout.androidaps.events.EventTreatmentChange;
import info.nightscout.androidaps.interfaces.PluginBase; import info.nightscout.androidaps.interfaces.PluginBase;
import info.nightscout.androidaps.interfaces.PumpDescription; import info.nightscout.androidaps.interfaces.PumpDescription;
import info.nightscout.androidaps.interfaces.PumpInterface; import info.nightscout.androidaps.interfaces.PumpInterface;
import info.nightscout.androidaps.interfaces.Constraint;
import info.nightscout.androidaps.plugins.Careportal.CareportalFragment; import info.nightscout.androidaps.plugins.Careportal.CareportalFragment;
import info.nightscout.androidaps.plugins.Careportal.Dialogs.NewNSTreatmentDialog; import info.nightscout.androidaps.plugins.Careportal.Dialogs.NewNSTreatmentDialog;
import info.nightscout.androidaps.plugins.Careportal.OptionsToShow; import info.nightscout.androidaps.plugins.Careportal.OptionsToShow;
@ -287,13 +288,16 @@ public class OverviewFragment extends Fragment implements View.OnClickListener,
llm = new LinearLayoutManager(view.getContext()); llm = new LinearLayoutManager(view.getContext());
notificationsView.setLayoutManager(llm); notificationsView.setLayoutManager(llm);
float scaledDensity = getResources().getDisplayMetrics().scaledDensity;
int axisWidth = (int) Math.round(scaledDensity * scaledDensity * scaledDensity * 6);
bgGraph.getGridLabelRenderer().setGridColor(MainApp.sResources.getColor(R.color.graphgrid)); bgGraph.getGridLabelRenderer().setGridColor(MainApp.sResources.getColor(R.color.graphgrid));
bgGraph.getGridLabelRenderer().reloadStyles(); bgGraph.getGridLabelRenderer().reloadStyles();
iobGraph.getGridLabelRenderer().setGridColor(MainApp.sResources.getColor(R.color.graphgrid)); iobGraph.getGridLabelRenderer().setGridColor(MainApp.sResources.getColor(R.color.graphgrid));
iobGraph.getGridLabelRenderer().reloadStyles(); iobGraph.getGridLabelRenderer().reloadStyles();
iobGraph.getGridLabelRenderer().setHorizontalLabelsVisible(false); iobGraph.getGridLabelRenderer().setHorizontalLabelsVisible(false);
bgGraph.getGridLabelRenderer().setLabelVerticalWidth(50); bgGraph.getGridLabelRenderer().setLabelVerticalWidth(axisWidth);
iobGraph.getGridLabelRenderer().setLabelVerticalWidth(50); iobGraph.getGridLabelRenderer().setLabelVerticalWidth(axisWidth);
iobGraph.getGridLabelRenderer().setNumVerticalLabels(5); iobGraph.getGridLabelRenderer().setNumVerticalLabels(5);
rangeToDisplay = SP.getInt(R.string.key_rangetodisplay, 6); rangeToDisplay = SP.getInt(R.string.key_rangetodisplay, 6);
@ -439,7 +443,7 @@ public class OverviewFragment extends Fragment implements View.OnClickListener,
if (v == apsModeView) { if (v == apsModeView) {
final LoopPlugin activeloop = ConfigBuilderPlugin.getActiveLoop(); final LoopPlugin activeloop = ConfigBuilderPlugin.getActiveLoop();
final PumpDescription pumpDescription = ConfigBuilderPlugin.getActivePump().getPumpDescription(); final PumpDescription pumpDescription = ConfigBuilderPlugin.getActivePump().getPumpDescription();
if (activeloop == null) if (activeloop == null || !MainApp.getConfigBuilder().isProfileValid("ContexMenuCreation"))
return; return;
menu.setHeaderTitle(MainApp.sResources.getString(R.string.loop)); menu.setHeaderTitle(MainApp.sResources.getString(R.string.loop));
if (activeloop.isEnabled(PluginBase.LOOP)) { if (activeloop.isEnabled(PluginBase.LOOP)) {
@ -473,9 +477,12 @@ public class OverviewFragment extends Fragment implements View.OnClickListener,
@Override @Override
public boolean onContextItemSelected(MenuItem item) { public boolean onContextItemSelected(MenuItem item) {
final Profile profile = MainApp.getConfigBuilder().getProfile();
if (profile == null)
return true;
final LoopPlugin activeloop = ConfigBuilderPlugin.getActiveLoop(); final LoopPlugin activeloop = ConfigBuilderPlugin.getActiveLoop();
if (item.getTitle().equals(MainApp.sResources.getString(R.string.disableloop))) { if (item.getTitle().equals(MainApp.sResources.getString(R.string.disableloop))) {
activeloop.setFragmentEnabled(PluginBase.LOOP, false); activeloop.setPluginEnabled(PluginBase.LOOP, false);
activeloop.setFragmentVisible(PluginBase.LOOP, false); activeloop.setFragmentVisible(PluginBase.LOOP, false);
MainApp.getConfigBuilder().storeSettings(); MainApp.getConfigBuilder().storeSettings();
updateGUI("suspendmenu"); updateGUI("suspendmenu");
@ -490,7 +497,7 @@ public class OverviewFragment extends Fragment implements View.OnClickListener,
NSUpload.uploadOpenAPSOffline(24 * 60); // upload 24h, we don't know real duration NSUpload.uploadOpenAPSOffline(24 * 60); // upload 24h, we don't know real duration
return true; return true;
} else if (item.getTitle().equals(MainApp.sResources.getString(R.string.enableloop))) { } else if (item.getTitle().equals(MainApp.sResources.getString(R.string.enableloop))) {
activeloop.setFragmentEnabled(PluginBase.LOOP, true); activeloop.setPluginEnabled(PluginBase.LOOP, true);
activeloop.setFragmentVisible(PluginBase.LOOP, true); activeloop.setFragmentVisible(PluginBase.LOOP, true);
MainApp.getConfigBuilder().storeSettings(); MainApp.getConfigBuilder().storeSettings();
updateGUI("suspendmenu"); updateGUI("suspendmenu");
@ -526,23 +533,23 @@ public class OverviewFragment extends Fragment implements View.OnClickListener,
updateGUI("suspendmenu"); updateGUI("suspendmenu");
return true; return true;
} else if (item.getTitle().equals(MainApp.sResources.getString(R.string.disconnectpumpfor15m))) { } else if (item.getTitle().equals(MainApp.sResources.getString(R.string.disconnectpumpfor15m))) {
MainApp.getConfigBuilder().disconnectPump(15); MainApp.getConfigBuilder().disconnectPump(15, profile);
updateGUI("suspendmenu"); updateGUI("suspendmenu");
return true; return true;
} else if (item.getTitle().equals(MainApp.sResources.getString(R.string.disconnectpumpfor30m))) { } else if (item.getTitle().equals(MainApp.sResources.getString(R.string.disconnectpumpfor30m))) {
MainApp.getConfigBuilder().disconnectPump(30); MainApp.getConfigBuilder().disconnectPump(30, profile);
updateGUI("suspendmenu"); updateGUI("suspendmenu");
return true; return true;
} else if (item.getTitle().equals(MainApp.sResources.getString(R.string.disconnectpumpfor1h))) { } else if (item.getTitle().equals(MainApp.sResources.getString(R.string.disconnectpumpfor1h))) {
MainApp.getConfigBuilder().disconnectPump(60); MainApp.getConfigBuilder().disconnectPump(60, profile);
updateGUI("suspendmenu"); updateGUI("suspendmenu");
return true; return true;
} else if (item.getTitle().equals(MainApp.sResources.getString(R.string.disconnectpumpfor2h))) { } else if (item.getTitle().equals(MainApp.sResources.getString(R.string.disconnectpumpfor2h))) {
MainApp.getConfigBuilder().disconnectPump(120); MainApp.getConfigBuilder().disconnectPump(120, profile);
updateGUI("suspendmenu"); updateGUI("suspendmenu");
return true; return true;
} else if (item.getTitle().equals(MainApp.sResources.getString(R.string.disconnectpumpfor3h))) { } else if (item.getTitle().equals(MainApp.sResources.getString(R.string.disconnectpumpfor3h))) {
MainApp.getConfigBuilder().disconnectPump(180); MainApp.getConfigBuilder().disconnectPump(180, profile);
updateGUI("suspendmenu"); updateGUI("suspendmenu");
return true; return true;
} else if (item.getTitle().equals(MainApp.sResources.getString(R.string.careportal_profileswitch))) { } else if (item.getTitle().equals(MainApp.sResources.getString(R.string.careportal_profileswitch))) {
@ -723,8 +730,8 @@ public class OverviewFragment extends Fragment implements View.OnClickListener,
DecimalFormat formatNumber2decimalplaces = new DecimalFormat("0.00"); DecimalFormat formatNumber2decimalplaces = new DecimalFormat("0.00");
String confirmMessage = getString(R.string.entertreatmentquestion); String confirmMessage = getString(R.string.entertreatmentquestion);
Double insulinAfterConstraints = MainApp.getConfigBuilder().applyBolusConstraints(wizard.calculatedTotalInsulin); Double insulinAfterConstraints = MainApp.getConstraintChecker().applyBolusConstraints(new Constraint<>(wizard.calculatedTotalInsulin)).value();
Integer carbsAfterConstraints = MainApp.getConfigBuilder().applyCarbsConstraints(quickWizardEntry.carbs()); Integer carbsAfterConstraints = MainApp.getConstraintChecker().applyCarbsConstraints(new Constraint<>(quickWizardEntry.carbs())).value();
confirmMessage += "\n" + getString(R.string.bolus) + ": " + formatNumber2decimalplaces.format(insulinAfterConstraints) + "U"; confirmMessage += "\n" + getString(R.string.bolus) + ": " + formatNumber2decimalplaces.format(insulinAfterConstraints) + "U";
confirmMessage += "\n" + getString(R.string.carbs) + ": " + carbsAfterConstraints + "g"; confirmMessage += "\n" + getString(R.string.carbs) + ": " + carbsAfterConstraints + "g";
@ -760,7 +767,7 @@ public class OverviewFragment extends Fragment implements View.OnClickListener,
activeloop.superBolusTo(System.currentTimeMillis() + 2 * 60L * 60 * 1000); activeloop.superBolusTo(System.currentTimeMillis() + 2 * 60L * 60 * 1000);
MainApp.bus().post(new EventRefreshOverview("WizardDialog")); MainApp.bus().post(new EventRefreshOverview("WizardDialog"));
} }
ConfigBuilderPlugin.getCommandQueue().tempBasalPercent(0, 120, true, new Callback() { ConfigBuilderPlugin.getCommandQueue().tempBasalPercent(0, 120, true, profile, new Callback() {
@Override @Override
public void run() { public void run() {
if (!result.success) { if (!result.success) {
@ -1016,6 +1023,8 @@ public class OverviewFragment extends Fragment implements View.OnClickListener,
} }
} }
Constraint<Boolean> closedLoopEnabled = MainApp.getConstraintChecker().isClosedLoopAllowed();
// open loop mode // open loop mode
final LoopPlugin.LastRun finalLastRun = LoopPlugin.lastRun; final LoopPlugin.LastRun finalLastRun = LoopPlugin.lastRun;
if (Config.APS && pump.getPumpDescription().isTempBasalCapable) { if (Config.APS && pump.getPumpDescription().isTempBasalCapable) {
@ -1036,7 +1045,7 @@ public class OverviewFragment extends Fragment implements View.OnClickListener,
apsModeView.setText(MainApp.sResources.getString(R.string.pumpsuspended)); apsModeView.setText(MainApp.sResources.getString(R.string.pumpsuspended));
apsModeView.setTextColor(Color.WHITE); apsModeView.setTextColor(Color.WHITE);
} else if (activeloop != null && activeloop.isEnabled(activeloop.getType())) { } else if (activeloop != null && activeloop.isEnabled(activeloop.getType())) {
if (MainApp.getConfigBuilder().isClosedModeEnabled()) { if (closedLoopEnabled.value()) {
apsModeView.setText(MainApp.sResources.getString(R.string.closedloop)); apsModeView.setText(MainApp.sResources.getString(R.string.closedloop));
} else { } else {
apsModeView.setText(MainApp.sResources.getString(R.string.openloop)); apsModeView.setText(MainApp.sResources.getString(R.string.openloop));
@ -1066,7 +1075,7 @@ public class OverviewFragment extends Fragment implements View.OnClickListener,
// **** Temp button **** // **** Temp button ****
if (acceptTempLayout != null) { if (acceptTempLayout != null) {
boolean showAcceptButton = !MainApp.getConfigBuilder().isClosedModeEnabled(); // Open mode needed boolean showAcceptButton = !closedLoopEnabled.value(); // Open mode needed
showAcceptButton = showAcceptButton && finalLastRun != null && finalLastRun.lastAPSRun != null; // aps result must exist showAcceptButton = showAcceptButton && finalLastRun != null && finalLastRun.lastAPSRun != null; // aps result must exist
showAcceptButton = showAcceptButton && (finalLastRun.lastOpenModeAccept == null || finalLastRun.lastOpenModeAccept.getTime() < finalLastRun.lastAPSRun.getTime()); // never accepted or before last result showAcceptButton = showAcceptButton && (finalLastRun.lastOpenModeAccept == null || finalLastRun.lastOpenModeAccept.getTime() < finalLastRun.lastAPSRun.getTime()); // never accepted or before last result
showAcceptButton = showAcceptButton && finalLastRun.constraintsProcessed.isChangeRequested(); // change is requested showAcceptButton = showAcceptButton && finalLastRun.constraintsProcessed.isChangeRequested(); // change is requested
@ -1160,7 +1169,7 @@ public class OverviewFragment extends Fragment implements View.OnClickListener,
extendedBolusView.setText(extendedBolusText); extendedBolusView.setText(extendedBolusText);
} }
if (extendedBolusText.equals("")) if (extendedBolusText.equals(""))
extendedBolusView.setVisibility(View.GONE); extendedBolusView.setVisibility(View.INVISIBLE);
else else
extendedBolusView.setVisibility(View.VISIBLE); extendedBolusView.setVisibility(View.VISIBLE);
} }
@ -1188,7 +1197,7 @@ public class OverviewFragment extends Fragment implements View.OnClickListener,
quickWizardButton.setVisibility(View.VISIBLE); quickWizardButton.setVisibility(View.VISIBLE);
String text = quickWizardEntry.buttonText() + "\n" + DecimalFormatter.to0Decimal(quickWizardEntry.carbs()) + "g"; String text = quickWizardEntry.buttonText() + "\n" + DecimalFormatter.to0Decimal(quickWizardEntry.carbs()) + "g";
BolusWizard wizard = quickWizardEntry.doCalc(profile, tempTarget, lastBG, false); BolusWizard wizard = quickWizardEntry.doCalc(profile, tempTarget, lastBG, false);
text += " " + DecimalFormatter.to2Decimal(wizard.calculatedTotalInsulin) + "U"; text += " " + DecimalFormatter.toPumpSupportedBolus(wizard.calculatedTotalInsulin) + "U";
quickWizardButton.setText(text); quickWizardButton.setText(text);
if (wizard.calculatedTotalInsulin <= 0) if (wizard.calculatedTotalInsulin <= 0)
quickWizardButton.setVisibility(View.GONE); quickWizardButton.setVisibility(View.GONE);

View file

@ -96,7 +96,7 @@ public class OverviewPlugin implements PluginBase {
} }
@Override @Override
public void setFragmentEnabled(int type, boolean fragmentEnabled) { public void setPluginEnabled(int type, boolean fragmentEnabled) {
// Always enabled // Always enabled
} }

View file

@ -245,6 +245,7 @@ public class GraphData {
value = (profile.getTargetLow(time) + profile.getTargetHigh(time)) / 2; value = (profile.getTargetLow(time) + profile.getTargetHigh(time)) / 2;
} else { } else {
value = tt.target(); value = tt.target();
value = Profile.fromMgdlToUnits(value, profile.getUnits());
} }
if (lastTarget > 0 && lastTarget != value) { if (lastTarget > 0 && lastTarget != value) {
targetsSeriesArray.add(new DataPoint(time, lastTarget)); targetsSeriesArray.add(new DataPoint(time, lastTarget));

View file

@ -48,11 +48,11 @@ import java.util.Iterator;
*/ */
public class PointsWithLabelGraphSeries<E extends DataPointWithLabelInterface> extends BaseSeries<E> { public class PointsWithLabelGraphSeries<E extends DataPointWithLabelInterface> extends BaseSeries<E> {
// Default spSize // Default spSize
int spSize = 12; int spSize = 14;
// Convert the sp to pixels // Convert the sp to pixels
Context context = MainApp.instance().getApplicationContext(); Context context = MainApp.instance().getApplicationContext();
float scaledTextSize = spSize * context.getResources().getDisplayMetrics().scaledDensity; float scaledTextSize = spSize * context.getResources().getDisplayMetrics().scaledDensity;
float scaledPxSize = context.getResources().getDisplayMetrics().scaledDensity * 1.5f; float scaledPxSize = context.getResources().getDisplayMetrics().scaledDensity * 3f;
/** /**
* choose a predefined shape to render for * choose a predefined shape to render for
@ -233,9 +233,10 @@ public class PointsWithLabelGraphSeries<E extends DataPointWithLabelInterface> e
} else if (value.getShape() == Shape.SMB) { } else if (value.getShape() == Shape.SMB) {
mPaint.setStrokeWidth(2); mPaint.setStrokeWidth(2);
Point[] points = new Point[3]; Point[] points = new Point[3];
points[0] = new Point((int)endX, (int)(endY-value.getSize())); float size = value.getSize() * scaledPxSize;
points[1] = new Point((int)(endX+value.getSize()), (int)(endY+value.getSize()*0.67)); points[0] = new Point((int)endX, (int)(endY-size));
points[2] = new Point((int)(endX-value.getSize()), (int)(endY+value.getSize()*0.67)); points[1] = new Point((int)(endX+size), (int)(endY+size*0.67));
points[2] = new Point((int)(endX-size), (int)(endY+size*0.67));
mPaint.setStyle(Paint.Style.FILL_AND_STROKE); mPaint.setStyle(Paint.Style.FILL_AND_STROKE);
drawArrows(points, canvas, mPaint); drawArrows(points, canvas, mPaint);
} else if (value.getShape() == Shape.EXTENDEDBOLUS) { } else if (value.getShape() == Shape.EXTENDEDBOLUS) {

View file

@ -94,7 +94,7 @@ public class PersistentNotificationPlugin implements PluginBase {
} }
@Override @Override
public void setFragmentEnabled(int type, boolean fragmentEnabled) { public void setPluginEnabled(int type, boolean fragmentEnabled) {
if (getType() == type) { if (getType() == type) {
this.fragmentEnabled = fragmentEnabled; this.fragmentEnabled = fragmentEnabled;
enableDisableNotification(fragmentEnabled); enableDisableNotification(fragmentEnabled);
@ -255,8 +255,7 @@ public class PersistentNotificationPlugin implements PluginBase {
@Subscribe @Subscribe
public void onStatusEvent(final EventNewBG ev) { public void onStatusEvent(final EventNewBG ev) {
if (ev.isFromActiveBgSource && ev.isNew && ev.isCurrent()) updateNotification();
updateNotification();
} }
@Subscribe @Subscribe

View file

@ -107,7 +107,7 @@ public class LocalProfilePlugin implements PluginBase, ProfileInterface {
} }
@Override @Override
public void setFragmentEnabled(int type, boolean fragmentEnabled) { public void setPluginEnabled(int type, boolean fragmentEnabled) {
if (type == PROFILE) this.fragmentEnabled = fragmentEnabled; if (type == PROFILE) this.fragmentEnabled = fragmentEnabled;
} }

View file

@ -96,7 +96,7 @@ public class NSProfilePlugin implements PluginBase, ProfileInterface {
} }
@Override @Override
public void setFragmentEnabled(int type, boolean fragmentEnabled) { public void setPluginEnabled(int type, boolean fragmentEnabled) {
if (type == PROFILE) this.fragmentEnabled = fragmentEnabled; if (type == PROFILE) this.fragmentEnabled = fragmentEnabled;
} }

View file

@ -102,7 +102,7 @@ public class SimpleProfilePlugin implements PluginBase, ProfileInterface {
} }
@Override @Override
public void setFragmentEnabled(int type, boolean fragmentEnabled) { public void setPluginEnabled(int type, boolean fragmentEnabled) {
if (type == PROFILE) this.fragmentEnabled = fragmentEnabled; if (type == PROFILE) this.fragmentEnabled = fragmentEnabled;
} }

View file

@ -233,7 +233,7 @@ public class ComboFragment extends SubscriberFragment implements View.OnClickLis
// reservoir // reservoir
int reservoirLevel = plugin.getPump().reservoirLevel; int reservoirLevel = plugin.getPump().reservoirLevel;
if (reservoirLevel != -1) { if (reservoirLevel != -1) {
reservoirView.setText(reservoirLevel + " " + MainApp.sResources.getString(R.string.treatments_wizard_unit_label)); reservoirView.setText(reservoirLevel + " " + MainApp.sResources.getString(R.string.insulin_unit_shortname));
} else if (ps.insulinState == PumpState.LOW) { } else if (ps.insulinState == PumpState.LOW) {
reservoirView.setText(MainApp.gs(R.string.combo_reservoir_low)); reservoirView.setText(MainApp.gs(R.string.combo_reservoir_low));
} else if (ps.insulinState == PumpState.EMPTY) { } else if (ps.insulinState == PumpState.EMPTY) {
@ -275,7 +275,7 @@ public class ComboFragment extends SubscriberFragment implements View.OnClickLis
if (bolus != null) { if (bolus != null) {
long agoMsc = System.currentTimeMillis() - bolus.timestamp; long agoMsc = System.currentTimeMillis() - bolus.timestamp;
double bolusMinAgo = agoMsc / 60d / 1000d; double bolusMinAgo = agoMsc / 60d / 1000d;
String unit = MainApp.gs(R.string.treatments_wizard_unit_label); String unit = MainApp.gs(R.string.insulin_unit_shortname);
String ago; String ago;
if ((agoMsc < 60 * 1000)) { if ((agoMsc < 60 * 1000)) {
ago = MainApp.gs(R.string.combo_pump_connected_now); ago = MainApp.gs(R.string.combo_pump_connected_now);

View file

@ -4,7 +4,6 @@ import android.os.SystemClock;
import android.support.annotation.NonNull; import android.support.annotation.NonNull;
import android.support.annotation.Nullable; import android.support.annotation.Nullable;
import com.crashlytics.android.answers.Answers;
import com.crashlytics.android.answers.CustomEvent; import com.crashlytics.android.answers.CustomEvent;
import org.json.JSONObject; import org.json.JSONObject;
@ -36,6 +35,7 @@ import info.nightscout.androidaps.interfaces.ConstraintsInterface;
import info.nightscout.androidaps.interfaces.PluginBase; import info.nightscout.androidaps.interfaces.PluginBase;
import info.nightscout.androidaps.interfaces.PumpDescription; import info.nightscout.androidaps.interfaces.PumpDescription;
import info.nightscout.androidaps.interfaces.PumpInterface; import info.nightscout.androidaps.interfaces.PumpInterface;
import info.nightscout.androidaps.interfaces.Constraint;
import info.nightscout.androidaps.plugins.ConfigBuilder.ConfigBuilderPlugin; import info.nightscout.androidaps.plugins.ConfigBuilder.ConfigBuilderPlugin;
import info.nightscout.androidaps.plugins.Overview.events.EventDismissNotification; import info.nightscout.androidaps.plugins.Overview.events.EventDismissNotification;
import info.nightscout.androidaps.plugins.Overview.events.EventNewNotification; import info.nightscout.androidaps.plugins.Overview.events.EventNewNotification;
@ -225,7 +225,7 @@ public class ComboPlugin implements PluginBase, PumpInterface, ConstraintsInterf
} }
@Override @Override
public void setFragmentEnabled(int type, boolean fragmentEnabled) { public void setPluginEnabled(int type, boolean fragmentEnabled) {
if (type == PUMP) this.fragmentEnabled = fragmentEnabled; if (type == PUMP) this.fragmentEnabled = fragmentEnabled;
} }
@ -428,7 +428,7 @@ public class ComboPlugin implements PluginBase, PumpInterface, ConstraintsInterf
return; return;
} }
pump.basalProfile = readBasalResult.basalProfile; pump.basalProfile = readBasalResult.basalProfile;
validBasalRateProfileSelectedOnPump = true; setValidBasalRateProfileSelectedOnPump(true);
pump.initialized = true; pump.initialized = true;
MainApp.bus().post(new EventInitializationChanged()); MainApp.bus().post(new EventInitializationChanged());
@ -750,7 +750,7 @@ public class ComboPlugin implements PluginBase, PumpInterface, ConstraintsInterf
* the new value (and thus still has the old duration of e.g. 1 min) expires?) * the new value (and thus still has the old duration of e.g. 1 min) expires?)
*/ */
@Override @Override
public PumpEnactResult setTempBasalAbsolute(Double absoluteRate, Integer durationInMinutes, boolean force) { public PumpEnactResult setTempBasalAbsolute(Double absoluteRate, Integer durationInMinutes, Profile profile, boolean force) {
log.debug("setTempBasalAbsolute called with a rate of " + absoluteRate + " for " + durationInMinutes + " min."); log.debug("setTempBasalAbsolute called with a rate of " + absoluteRate + " for " + durationInMinutes + " min.");
int unroundedPercentage = Double.valueOf(absoluteRate / getBaseBasalRate() * 100).intValue(); int unroundedPercentage = Double.valueOf(absoluteRate / getBaseBasalRate() * 100).intValue();
int roundedPercentage = (int) (Math.round(absoluteRate / getBaseBasalRate() * 10) * 10); int roundedPercentage = (int) (Math.round(absoluteRate / getBaseBasalRate() * 10) * 10);
@ -768,7 +768,7 @@ public class ComboPlugin implements PluginBase, PumpInterface, ConstraintsInterf
* is or isn't running at the moment * is or isn't running at the moment
*/ */
@Override @Override
public PumpEnactResult setTempBasalPercent(Integer percent, final Integer durationInMinutes, boolean forceNew) { public PumpEnactResult setTempBasalPercent(Integer percent, final Integer durationInMinutes, Profile profile, boolean forceNew) {
return setTempBasalPercent(percent, durationInMinutes); return setTempBasalPercent(percent, durationInMinutes);
} }
@ -929,7 +929,7 @@ public class ComboPlugin implements PluginBase, PumpInterface, ConstraintsInterf
if (commandResult.success) { if (commandResult.success) {
pump.lastSuccessfulCmdTime = System.currentTimeMillis(); pump.lastSuccessfulCmdTime = System.currentTimeMillis();
if (validBasalRateProfileSelectedOnPump && commandResult.state.unsafeUsageDetected == PumpState.UNSUPPORTED_BASAL_RATE_PROFILE) { if (validBasalRateProfileSelectedOnPump && commandResult.state.unsafeUsageDetected == PumpState.UNSUPPORTED_BASAL_RATE_PROFILE) {
validBasalRateProfileSelectedOnPump = false; setValidBasalRateProfileSelectedOnPump(false);
Notification n = new Notification(Notification.COMBO_PUMP_ALARM, Notification n = new Notification(Notification.COMBO_PUMP_ALARM,
MainApp.gs(R.string.combo_force_disabled_notification), MainApp.gs(R.string.combo_force_disabled_notification),
Notification.URGENT); Notification.URGENT);
@ -949,6 +949,10 @@ public class ComboPlugin implements PluginBase, PumpInterface, ConstraintsInterf
return commandResult; return commandResult;
} }
public void setValidBasalRateProfileSelectedOnPump(boolean value) {
validBasalRateProfileSelectedOnPump = value;
}
/** /**
* Returns the command result of running ReadPumpState if it wasn't successful, indicating * Returns the command result of running ReadPumpState if it wasn't successful, indicating
* an error condition. Returns null otherwise. * an error condition. Returns null otherwise.
@ -1457,52 +1461,16 @@ public class ComboPlugin implements PluginBase, PumpInterface, ConstraintsInterf
private boolean validBasalRateProfileSelectedOnPump = true; private boolean validBasalRateProfileSelectedOnPump = true;
@Override @Override
public boolean isLoopEnabled() { public Constraint<Boolean> isLoopInvokationAllowed(Constraint<Boolean> value) {
return validBasalRateProfileSelectedOnPump; if (!validBasalRateProfileSelectedOnPump)
value.set(false, MainApp.gs(R.string.novalidbasalrate), this);
return value;
} }
@Override @Override
public boolean isClosedModeEnabled() { public Constraint<Double> applyMaxIOBConstraints(Constraint<Double> maxIob) {
return true; if (lowSuspendOnlyLoopEnforcedUntil > System.currentTimeMillis())
} maxIob.setIfSmaller(0d, String.format(MainApp.gs(R.string.limitingmaxiob), 0d, MainApp.gs(R.string.unsafeusage)), this);
return maxIob;
@Override
public boolean isAutosensModeEnabled() {
return true;
}
@Override
public boolean isAMAModeEnabled() {
return true;
}
@Override
public boolean isSMBModeEnabled() {
return true;
}
@Override
public Double applyBasalConstraints(Double absoluteRate) {
return absoluteRate;
}
@Override
public Integer applyBasalConstraints(Integer percentRate) {
return percentRate;
}
@Override
public Double applyBolusConstraints(Double insulin) {
return insulin;
}
@Override
public Integer applyCarbsConstraints(Integer carbs) {
return carbs;
}
@Override
public Double applyMaxIOBConstraints(Double maxIob) {
return lowSuspendOnlyLoopEnforcedUntil < System.currentTimeMillis() ? maxIob : 0;
} }
} }

View file

@ -7,11 +7,9 @@ import org.json.JSONObject;
import org.slf4j.Logger; import org.slf4j.Logger;
import java.util.Date; import java.util.Date;
import java.util.Objects;
import info.nightscout.androidaps.BuildConfig; import info.nightscout.androidaps.BuildConfig;
import info.nightscout.androidaps.Config; import info.nightscout.androidaps.Config;
import info.nightscout.androidaps.Constants;
import info.nightscout.androidaps.MainApp; import info.nightscout.androidaps.MainApp;
import info.nightscout.androidaps.R; import info.nightscout.androidaps.R;
import info.nightscout.androidaps.data.Profile; import info.nightscout.androidaps.data.Profile;
@ -19,18 +17,17 @@ import info.nightscout.androidaps.data.ProfileStore;
import info.nightscout.androidaps.data.PumpEnactResult; import info.nightscout.androidaps.data.PumpEnactResult;
import info.nightscout.androidaps.db.ExtendedBolus; import info.nightscout.androidaps.db.ExtendedBolus;
import info.nightscout.androidaps.db.TemporaryBasal; import info.nightscout.androidaps.db.TemporaryBasal;
import info.nightscout.androidaps.interfaces.Constraint;
import info.nightscout.androidaps.interfaces.ConstraintsInterface; import info.nightscout.androidaps.interfaces.ConstraintsInterface;
import info.nightscout.androidaps.interfaces.DanaRInterface; import info.nightscout.androidaps.interfaces.DanaRInterface;
import info.nightscout.androidaps.interfaces.PluginBase; import info.nightscout.androidaps.interfaces.PluginBase;
import info.nightscout.androidaps.interfaces.ProfileInterface; import info.nightscout.androidaps.interfaces.ProfileInterface;
import info.nightscout.androidaps.interfaces.PumpDescription; import info.nightscout.androidaps.interfaces.PumpDescription;
import info.nightscout.androidaps.interfaces.PumpInterface; import info.nightscout.androidaps.interfaces.PumpInterface;
import info.nightscout.androidaps.plugins.ConfigBuilder.ConfigBuilderPlugin;
import info.nightscout.androidaps.plugins.Overview.events.EventDismissNotification; import info.nightscout.androidaps.plugins.Overview.events.EventDismissNotification;
import info.nightscout.androidaps.plugins.Overview.events.EventNewNotification; import info.nightscout.androidaps.plugins.Overview.events.EventNewNotification;
import info.nightscout.androidaps.plugins.Overview.notifications.Notification; import info.nightscout.androidaps.plugins.Overview.notifications.Notification;
import info.nightscout.androidaps.plugins.ProfileNS.NSProfilePlugin; import info.nightscout.androidaps.plugins.ProfileNS.NSProfilePlugin;
import info.nightscout.androidaps.plugins.PumpDanaR.comm.RecordTypes;
import info.nightscout.androidaps.plugins.PumpDanaR.services.AbstractDanaRExecutionService; import info.nightscout.androidaps.plugins.PumpDanaR.services.AbstractDanaRExecutionService;
import info.nightscout.utils.DateUtil; import info.nightscout.utils.DateUtil;
import info.nightscout.utils.DecimalFormatter; import info.nightscout.utils.DecimalFormatter;
@ -108,16 +105,16 @@ public abstract class AbstractDanaRPlugin implements PluginBase, PumpInterface,
} }
@Override @Override
public void setFragmentEnabled(int type, boolean fragmentEnabled) { public void setPluginEnabled(int type, boolean fragmentEnabled) {
if (type == PluginBase.PROFILE) if (type == PluginBase.PROFILE)
mPluginProfileEnabled = fragmentEnabled; mPluginProfileEnabled = fragmentEnabled;
else if (type == PluginBase.PUMP) else if (type == PluginBase.PUMP)
mPluginPumpEnabled = fragmentEnabled; mPluginPumpEnabled = fragmentEnabled;
// if pump profile was enabled need to switch to another too // if pump profile was enabled need to switch to another too
if (type == PluginBase.PUMP && !fragmentEnabled && mPluginProfileEnabled) { if (type == PluginBase.PUMP && !fragmentEnabled && mPluginProfileEnabled) {
setFragmentEnabled(PluginBase.PROFILE, false); setPluginEnabled(PluginBase.PROFILE, false);
setFragmentVisible(PluginBase.PROFILE, false); setFragmentVisible(PluginBase.PROFILE, false);
NSProfilePlugin.getPlugin().setFragmentEnabled(PluginBase.PROFILE, true); NSProfilePlugin.getPlugin().setPluginEnabled(PluginBase.PROFILE, true);
NSProfilePlugin.getPlugin().setFragmentVisible(PluginBase.PROFILE, true); NSProfilePlugin.getPlugin().setFragmentVisible(PluginBase.PROFILE, true);
} }
} }
@ -215,10 +212,9 @@ public abstract class AbstractDanaRPlugin implements PluginBase, PumpInterface,
} }
@Override @Override
public PumpEnactResult setTempBasalPercent(Integer percent, Integer durationInMinutes, boolean enforceNew) { public PumpEnactResult setTempBasalPercent(Integer percent, Integer durationInMinutes, Profile profile, boolean enforceNew) {
PumpEnactResult result = new PumpEnactResult(); PumpEnactResult result = new PumpEnactResult();
ConfigBuilderPlugin configBuilderPlugin = MainApp.getConfigBuilder(); percent = MainApp.getConstraintChecker().applyBasalPercentConstraints(new Constraint<>(percent), profile).value();
percent = configBuilderPlugin.applyBasalConstraints(percent);
if (percent < 0) { if (percent < 0) {
result.isTempCancel = false; result.isTempCancel = false;
result.enacted = false; result.enacted = false;
@ -230,7 +226,7 @@ public abstract class AbstractDanaRPlugin implements PluginBase, PumpInterface,
if (percent > getPumpDescription().maxTempPercent) if (percent > getPumpDescription().maxTempPercent)
percent = getPumpDescription().maxTempPercent; percent = getPumpDescription().maxTempPercent;
long now = System.currentTimeMillis(); long now = System.currentTimeMillis();
TemporaryBasal runningTB = MainApp.getConfigBuilder().getRealTempBasalFromHistory(now); TemporaryBasal runningTB = MainApp.getConfigBuilder().getRealTempBasalFromHistory(now);
if (runningTB != null && runningTB.percentRate == percent && !enforceNew) { if (runningTB != null && runningTB.percentRate == percent && !enforceNew) {
result.enacted = false; result.enacted = false;
result.success = true; result.success = true;
@ -266,8 +262,7 @@ public abstract class AbstractDanaRPlugin implements PluginBase, PumpInterface,
@Override @Override
public PumpEnactResult setExtendedBolus(Double insulin, Integer durationInMinutes) { public PumpEnactResult setExtendedBolus(Double insulin, Integer durationInMinutes) {
ConfigBuilderPlugin configBuilderPlugin = MainApp.getConfigBuilder(); insulin = MainApp.getConstraintChecker().applyBolusConstraints(new Constraint<>(insulin)).value();
insulin = configBuilderPlugin.applyBolusConstraints(insulin);
// needs to be rounded // needs to be rounded
int durationInHalfHours = Math.max(durationInMinutes / 30, 1); int durationInHalfHours = Math.max(durationInMinutes / 30, 1);
insulin = Round.roundTo(insulin, getPumpDescription().extendedBolusStep); insulin = Round.roundTo(insulin, getPumpDescription().extendedBolusStep);
@ -294,7 +289,8 @@ public abstract class AbstractDanaRPlugin implements PluginBase, PumpInterface,
result.isTempCancel = false; result.isTempCancel = false;
result.duration = pump.extendedBolusRemainingMinutes; result.duration = pump.extendedBolusRemainingMinutes;
result.absolute = pump.extendedBolusAbsoluteRate; result.absolute = pump.extendedBolusAbsoluteRate;
if (! SP.getBoolean("danar_useextended", false)) result.bolusDelivered = pump.extendedBolusAmount; if (!SP.getBoolean("danar_useextended", false))
result.bolusDelivered = pump.extendedBolusAmount;
result.isPercent = false; result.isPercent = false;
if (Config.logPumpActions) if (Config.logPumpActions)
log.debug("setExtendedBolus: OK"); log.debug("setExtendedBolus: OK");
@ -437,85 +433,27 @@ public abstract class AbstractDanaRPlugin implements PluginBase, PumpInterface,
*/ */
@Override @Override
public PumpEnactResult loadTDDs() { public Constraint<Double> applyBasalConstraints(Constraint<Double> absoluteRate, Profile profile) {
return loadHistory(RecordTypes.RECORD_TYPE_DAILY); if (pump != null)
} absoluteRate.setIfSmaller(pump.maxBasal, String.format(MainApp.gs(R.string.limitingbasalratio), pump.maxBasal, MainApp.gs(R.string.pumplimit)), this);
@Override
public boolean isLoopEnabled() {
return true;
}
@Override
public boolean isClosedModeEnabled() {
return true;
}
@Override
public boolean isAutosensModeEnabled() {
return true;
}
@Override
public boolean isAMAModeEnabled() {
return true;
}
@Override
public boolean isSMBModeEnabled() {
return true;
}
@SuppressWarnings("PointlessBooleanExpression")
@Override
public Double applyBasalConstraints(Double absoluteRate) {
double origAbsoluteRate = absoluteRate;
if (pump != null) {
if (absoluteRate > pump.maxBasal) {
absoluteRate = pump.maxBasal;
if (Config.logConstraintsChanges && origAbsoluteRate != Constants.basalAbsoluteOnlyForCheckLimit)
log.debug("Limiting rate " + origAbsoluteRate + "U/h by pump constraint to " + absoluteRate + "U/h");
}
}
return absoluteRate; return absoluteRate;
} }
@SuppressWarnings("PointlessBooleanExpression")
@Override @Override
public Integer applyBasalConstraints(Integer percentRate) { public Constraint<Integer> applyBasalPercentConstraints(Constraint<Integer> percentRate, Profile profile) {
Integer origPercentRate = percentRate; percentRate.setIfGreater(0, String.format(MainApp.gs(R.string.limitingpercentrate), 0, MainApp.gs(R.string.itmustbepositivevalue)), this);
if (percentRate < 0) percentRate = 0; percentRate.setIfSmaller(getPumpDescription().maxTempPercent, String.format(MainApp.gs(R.string.limitingpercentrate), getPumpDescription().maxTempPercent, MainApp.gs(R.string.pumplimit)), this);
if (percentRate > getPumpDescription().maxTempPercent)
percentRate = getPumpDescription().maxTempPercent;
if (!Objects.equals(percentRate, origPercentRate) && Config.logConstraintsChanges && !Objects.equals(origPercentRate, Constants.basalPercentOnlyForCheckLimit))
log.debug("Limiting percent rate " + origPercentRate + "% to " + percentRate + "%");
return percentRate; return percentRate;
} }
@SuppressWarnings("PointlessBooleanExpression")
@Override @Override
public Double applyBolusConstraints(Double insulin) { public Constraint<Double> applyBolusConstraints(Constraint<Double> insulin) {
double origInsulin = insulin; if (pump != null)
if (pump != null) { insulin.setIfSmaller(pump.maxBolus, String.format(MainApp.gs(R.string.limitingbolus), pump.maxBolus, MainApp.gs(R.string.pumplimit)), this);
if (insulin > pump.maxBolus) {
insulin = pump.maxBolus;
if (Config.logConstraintsChanges && origInsulin != Constants.bolusOnlyForCheckLimit)
log.debug("Limiting bolus " + origInsulin + "U by pump constraint to " + insulin + "U");
}
}
return insulin; return insulin;
} }
@Override
public Integer applyCarbsConstraints(Integer carbs) {
return carbs;
}
@Override
public Double applyMaxIOBConstraints(Double maxIob) {
return maxIob;
}
@Nullable @Nullable
@Override @Override
public ProfileStore getProfile() { public ProfileStore getProfile() {

View file

@ -14,14 +14,15 @@ import info.nightscout.androidaps.Config;
import info.nightscout.androidaps.MainApp; import info.nightscout.androidaps.MainApp;
import info.nightscout.androidaps.R; import info.nightscout.androidaps.R;
import info.nightscout.androidaps.data.DetailedBolusInfo; import info.nightscout.androidaps.data.DetailedBolusInfo;
import info.nightscout.androidaps.data.Profile;
import info.nightscout.androidaps.data.PumpEnactResult; import info.nightscout.androidaps.data.PumpEnactResult;
import info.nightscout.androidaps.db.ExtendedBolus; import info.nightscout.androidaps.db.ExtendedBolus;
import info.nightscout.androidaps.db.TemporaryBasal; import info.nightscout.androidaps.db.TemporaryBasal;
import info.nightscout.androidaps.db.Treatment; import info.nightscout.androidaps.db.Treatment;
import info.nightscout.androidaps.events.EventAppExit; import info.nightscout.androidaps.events.EventAppExit;
import info.nightscout.androidaps.events.EventPreferenceChange; import info.nightscout.androidaps.events.EventPreferenceChange;
import info.nightscout.androidaps.interfaces.Constraint;
import info.nightscout.androidaps.interfaces.PumpDescription; import info.nightscout.androidaps.interfaces.PumpDescription;
import info.nightscout.androidaps.plugins.ConfigBuilder.ConfigBuilderPlugin;
import info.nightscout.androidaps.plugins.PumpDanaR.services.DanaRExecutionService; import info.nightscout.androidaps.plugins.PumpDanaR.services.DanaRExecutionService;
import info.nightscout.utils.Round; import info.nightscout.utils.Round;
import info.nightscout.utils.SP; import info.nightscout.utils.SP;
@ -131,8 +132,7 @@ public class DanaRPlugin extends AbstractDanaRPlugin {
@Override @Override
public PumpEnactResult deliverTreatment(DetailedBolusInfo detailedBolusInfo) { public PumpEnactResult deliverTreatment(DetailedBolusInfo detailedBolusInfo) {
ConfigBuilderPlugin configBuilderPlugin = MainApp.getConfigBuilder(); detailedBolusInfo.insulin = MainApp.getConstraintChecker().applyBolusConstraints(new Constraint<>(detailedBolusInfo.insulin)).value();
detailedBolusInfo.insulin = configBuilderPlugin.applyBolusConstraints(detailedBolusInfo.insulin);
if (detailedBolusInfo.insulin > 0 || detailedBolusInfo.carbs > 0) { if (detailedBolusInfo.insulin > 0 || detailedBolusInfo.carbs > 0) {
Treatment t = new Treatment(); Treatment t = new Treatment();
t.isSMB = detailedBolusInfo.isSMB; t.isSMB = detailedBolusInfo.isSMB;
@ -162,7 +162,7 @@ public class DanaRPlugin extends AbstractDanaRPlugin {
// This is called from APS // This is called from APS
@Override @Override
public PumpEnactResult setTempBasalAbsolute(Double absoluteRate, Integer durationInMinutes, boolean enforceNew) { public PumpEnactResult setTempBasalAbsolute(Double absoluteRate, Integer durationInMinutes, Profile profile, boolean enforceNew) {
// Recheck pump status if older than 30 min // Recheck pump status if older than 30 min
//This should not be needed while using queue because connection should be done before calling this //This should not be needed while using queue because connection should be done before calling this
//if (pump.lastConnection.getTime() + 30 * 60 * 1000L < System.currentTimeMillis()) { //if (pump.lastConnection.getTime() + 30 * 60 * 1000L < System.currentTimeMillis()) {
@ -171,8 +171,7 @@ public class DanaRPlugin extends AbstractDanaRPlugin {
PumpEnactResult result = new PumpEnactResult(); PumpEnactResult result = new PumpEnactResult();
ConfigBuilderPlugin configBuilderPlugin = MainApp.getConfigBuilder(); absoluteRate = MainApp.getConstraintChecker().applyBasalConstraints(new Constraint<>(absoluteRate), profile).value();
absoluteRate = configBuilderPlugin.applyBasalConstraints(absoluteRate);
final boolean doTempOff = getBaseBasalRate() - absoluteRate == 0d; final boolean doTempOff = getBaseBasalRate() - absoluteRate == 0d;
final boolean doLowTemp = absoluteRate < getBaseBasalRate(); final boolean doLowTemp = absoluteRate < getBaseBasalRate();
@ -250,7 +249,7 @@ public class DanaRPlugin extends AbstractDanaRPlugin {
// Convert duration from minutes to hours // Convert duration from minutes to hours
if (Config.logPumpActions) if (Config.logPumpActions)
log.debug("setTempBasalAbsolute: Setting temp basal " + percentRate + "% for " + durationInMinutes + " mins (doLowTemp || doHighTemp)"); log.debug("setTempBasalAbsolute: Setting temp basal " + percentRate + "% for " + durationInMinutes + " mins (doLowTemp || doHighTemp)");
return setTempBasalPercent(percentRate, durationInMinutes, false); return setTempBasalPercent(percentRate, durationInMinutes, profile, false);
} }
if (doExtendedTemp) { if (doExtendedTemp) {
// Check if some temp is already in progress // Check if some temp is already in progress
@ -269,7 +268,7 @@ public class DanaRPlugin extends AbstractDanaRPlugin {
Integer durationInHalfHours = Math.max(durationInMinutes / 30, 1); Integer durationInHalfHours = Math.max(durationInMinutes / 30, 1);
// We keep current basal running so need to sub current basal // We keep current basal running so need to sub current basal
Double extendedRateToSet = absoluteRate - getBaseBasalRate(); Double extendedRateToSet = absoluteRate - getBaseBasalRate();
extendedRateToSet = configBuilderPlugin.applyBasalConstraints(extendedRateToSet); extendedRateToSet = MainApp.getConstraintChecker().applyBasalConstraints(new Constraint<>(extendedRateToSet), profile).value();
// needs to be rounded to 0.1 // needs to be rounded to 0.1
extendedRateToSet = Round.roundTo(extendedRateToSet, pumpDescription.extendedBolusStep * 2); // *2 because of halfhours extendedRateToSet = Round.roundTo(extendedRateToSet, pumpDescription.extendedBolusStep * 2); // *2 because of halfhours

View file

@ -3,9 +3,9 @@ package info.nightscout.androidaps.plugins.PumpDanaR.comm;
import org.slf4j.Logger; import org.slf4j.Logger;
import org.slf4j.LoggerFactory; import org.slf4j.LoggerFactory;
import info.nightscout.androidaps.BuildConfig;
import info.nightscout.androidaps.Config; import info.nightscout.androidaps.Config;
import info.nightscout.androidaps.MainApp; import info.nightscout.androidaps.MainApp;
import info.nightscout.androidaps.interfaces.Constraint;
import info.nightscout.utils.HardLimits; import info.nightscout.utils.HardLimits;
public class MsgBolusStart extends MessageBase { public class MsgBolusStart extends MessageBase {
@ -19,9 +19,7 @@ public class MsgBolusStart extends MessageBase {
this(); this();
// HARDCODED LIMIT // HARDCODED LIMIT
amount = MainApp.getConfigBuilder().applyBolusConstraints(amount); amount = MainApp.getConstraintChecker().applyBolusConstraints(new Constraint<>(amount)).value();
if (amount < 0) amount = 0d;
if (amount > HardLimits.maxBolus()) amount = HardLimits.maxBolus();
AddParamInt((int) (amount * 100)); AddParamInt((int) (amount * 100));

View file

@ -5,6 +5,7 @@ import org.slf4j.LoggerFactory;
import info.nightscout.androidaps.Config; import info.nightscout.androidaps.Config;
import info.nightscout.androidaps.MainApp; import info.nightscout.androidaps.MainApp;
import info.nightscout.androidaps.interfaces.Constraint;
import info.nightscout.utils.HardLimits; import info.nightscout.utils.HardLimits;
public class MsgBolusStartWithSpeed extends MessageBase { public class MsgBolusStartWithSpeed extends MessageBase {
@ -18,9 +19,7 @@ public class MsgBolusStartWithSpeed extends MessageBase {
this(); this();
// HARDCODED LIMIT // HARDCODED LIMIT
amount = MainApp.getConfigBuilder().applyBolusConstraints(amount); amount = MainApp.getConstraintChecker().applyBolusConstraints(new Constraint<>(amount)).value();
if (amount < 0) amount = 0d;
if (amount > HardLimits.maxBolus()) amount = HardLimits.maxBolus();
AddParamInt((int) (amount * 100)); AddParamInt((int) (amount * 100));
AddParamByte((byte) speed); AddParamByte((byte) speed);

View file

@ -31,17 +31,17 @@ public class MsgInitConnStatusTime extends MessageBase {
MainApp.bus().post(new EventNewNotification(notification)); MainApp.bus().post(new EventNewNotification(notification));
MainApp.getSpecificPlugin(DanaRPlugin.class).disconnect("Wrong Model"); MainApp.getSpecificPlugin(DanaRPlugin.class).disconnect("Wrong Model");
log.debug("Wrong model selected. Switching to Korean DanaR"); log.debug("Wrong model selected. Switching to Korean DanaR");
MainApp.getSpecificPlugin(DanaRKoreanPlugin.class).setFragmentEnabled(PluginBase.PUMP, true); MainApp.getSpecificPlugin(DanaRKoreanPlugin.class).setPluginEnabled(PluginBase.PUMP, true);
MainApp.getSpecificPlugin(DanaRKoreanPlugin.class).setFragmentVisible(PluginBase.PUMP, true); MainApp.getSpecificPlugin(DanaRKoreanPlugin.class).setFragmentVisible(PluginBase.PUMP, true);
MainApp.getSpecificPlugin(DanaRPlugin.class).setFragmentEnabled(PluginBase.PUMP, false); MainApp.getSpecificPlugin(DanaRPlugin.class).setPluginEnabled(PluginBase.PUMP, false);
MainApp.getSpecificPlugin(DanaRPlugin.class).setFragmentVisible(PluginBase.PUMP, false); MainApp.getSpecificPlugin(DanaRPlugin.class).setFragmentVisible(PluginBase.PUMP, false);
DanaRPump.reset(); // mark not initialized DanaRPump.reset(); // mark not initialized
//If profile coming from pump, switch it as well //If profile coming from pump, switch it as well
if(MainApp.getSpecificPlugin(DanaRPlugin.class).isEnabled(PluginBase.PROFILE)){ if(MainApp.getSpecificPlugin(DanaRPlugin.class).isEnabled(PluginBase.PROFILE)){
(MainApp.getSpecificPlugin(DanaRPlugin.class)).setFragmentEnabled(PluginBase.PROFILE, false); (MainApp.getSpecificPlugin(DanaRPlugin.class)).setPluginEnabled(PluginBase.PROFILE, false);
(MainApp.getSpecificPlugin(DanaRKoreanPlugin.class)).setFragmentEnabled(PluginBase.PROFILE, true); (MainApp.getSpecificPlugin(DanaRKoreanPlugin.class)).setPluginEnabled(PluginBase.PROFILE, true);
} }
MainApp.getConfigBuilder().storeSettings(); MainApp.getConfigBuilder().storeSettings();

View file

@ -3,9 +3,9 @@ package info.nightscout.androidaps.plugins.PumpDanaR.comm;
import org.slf4j.Logger; import org.slf4j.Logger;
import org.slf4j.LoggerFactory; import org.slf4j.LoggerFactory;
import info.nightscout.androidaps.BuildConfig;
import info.nightscout.androidaps.Config; import info.nightscout.androidaps.Config;
import info.nightscout.androidaps.MainApp; import info.nightscout.androidaps.MainApp;
import info.nightscout.androidaps.interfaces.Constraint;
import info.nightscout.utils.HardLimits; import info.nightscout.utils.HardLimits;
public class MsgSetExtendedBolusStart extends MessageBase { public class MsgSetExtendedBolusStart extends MessageBase {
@ -21,9 +21,7 @@ public class MsgSetExtendedBolusStart extends MessageBase {
// HARDCODED LIMITS // HARDCODED LIMITS
if (halfhours < 1) halfhours = 1; if (halfhours < 1) halfhours = 1;
if (halfhours > 16) halfhours = 16; if (halfhours > 16) halfhours = 16;
amount = MainApp.getConfigBuilder().applyBolusConstraints(amount); amount = MainApp.getConstraintChecker().applyBolusConstraints(new Constraint<>(amount)).value();
if (amount < 0d) amount = 0d;
if (amount > HardLimits.maxBolus()) amount = HardLimits.maxBolus();
AddParamInt((int) (amount * 100)); AddParamInt((int) (amount * 100));
AddParamByte(halfhours); AddParamByte(halfhours);

View file

@ -14,14 +14,15 @@ import info.nightscout.androidaps.Config;
import info.nightscout.androidaps.MainApp; import info.nightscout.androidaps.MainApp;
import info.nightscout.androidaps.R; import info.nightscout.androidaps.R;
import info.nightscout.androidaps.data.DetailedBolusInfo; import info.nightscout.androidaps.data.DetailedBolusInfo;
import info.nightscout.androidaps.data.Profile;
import info.nightscout.androidaps.data.PumpEnactResult; import info.nightscout.androidaps.data.PumpEnactResult;
import info.nightscout.androidaps.db.ExtendedBolus; import info.nightscout.androidaps.db.ExtendedBolus;
import info.nightscout.androidaps.db.TemporaryBasal; import info.nightscout.androidaps.db.TemporaryBasal;
import info.nightscout.androidaps.db.Treatment; import info.nightscout.androidaps.db.Treatment;
import info.nightscout.androidaps.events.EventAppExit; import info.nightscout.androidaps.events.EventAppExit;
import info.nightscout.androidaps.events.EventPreferenceChange; import info.nightscout.androidaps.events.EventPreferenceChange;
import info.nightscout.androidaps.interfaces.Constraint;
import info.nightscout.androidaps.interfaces.PumpDescription; import info.nightscout.androidaps.interfaces.PumpDescription;
import info.nightscout.androidaps.plugins.ConfigBuilder.ConfigBuilderPlugin;
import info.nightscout.androidaps.plugins.PumpDanaR.AbstractDanaRPlugin; import info.nightscout.androidaps.plugins.PumpDanaR.AbstractDanaRPlugin;
import info.nightscout.androidaps.plugins.PumpDanaRKorean.services.DanaRKoreanExecutionService; import info.nightscout.androidaps.plugins.PumpDanaRKorean.services.DanaRKoreanExecutionService;
import info.nightscout.utils.Round; import info.nightscout.utils.Round;
@ -132,8 +133,7 @@ public class DanaRKoreanPlugin extends AbstractDanaRPlugin {
@Override @Override
public PumpEnactResult deliverTreatment(DetailedBolusInfo detailedBolusInfo) { public PumpEnactResult deliverTreatment(DetailedBolusInfo detailedBolusInfo) {
ConfigBuilderPlugin configBuilderPlugin = MainApp.getConfigBuilder(); detailedBolusInfo.insulin = MainApp.getConstraintChecker().applyBolusConstraints(new Constraint<>(detailedBolusInfo.insulin)).value();
detailedBolusInfo.insulin = configBuilderPlugin.applyBolusConstraints(detailedBolusInfo.insulin);
if (detailedBolusInfo.insulin > 0 || detailedBolusInfo.carbs > 0) { if (detailedBolusInfo.insulin > 0 || detailedBolusInfo.carbs > 0) {
Treatment t = new Treatment(); Treatment t = new Treatment();
t.isSMB = detailedBolusInfo.isSMB; t.isSMB = detailedBolusInfo.isSMB;
@ -163,7 +163,7 @@ public class DanaRKoreanPlugin extends AbstractDanaRPlugin {
// This is called from APS // This is called from APS
@Override @Override
public PumpEnactResult setTempBasalAbsolute(Double absoluteRate, Integer durationInMinutes, boolean enforceNew) { public PumpEnactResult setTempBasalAbsolute(Double absoluteRate, Integer durationInMinutes, Profile profile, boolean enforceNew) {
// Recheck pump status if older than 30 min // Recheck pump status if older than 30 min
//This should not be needed while using queue because connection should be done before calling this //This should not be needed while using queue because connection should be done before calling this
//if (pump.lastConnection.getTime() + 30 * 60 * 1000L < System.currentTimeMillis()) { //if (pump.lastConnection.getTime() + 30 * 60 * 1000L < System.currentTimeMillis()) {
@ -172,8 +172,7 @@ public class DanaRKoreanPlugin extends AbstractDanaRPlugin {
PumpEnactResult result = new PumpEnactResult(); PumpEnactResult result = new PumpEnactResult();
ConfigBuilderPlugin configBuilderPlugin = MainApp.getConfigBuilder(); absoluteRate = MainApp.getConstraintChecker().applyBasalConstraints(new Constraint<>(absoluteRate), profile).value();
absoluteRate = configBuilderPlugin.applyBasalConstraints(absoluteRate);
final boolean doTempOff = getBaseBasalRate() - absoluteRate == 0d; final boolean doTempOff = getBaseBasalRate() - absoluteRate == 0d;
final boolean doLowTemp = absoluteRate < getBaseBasalRate(); final boolean doLowTemp = absoluteRate < getBaseBasalRate();
@ -251,7 +250,7 @@ public class DanaRKoreanPlugin extends AbstractDanaRPlugin {
// Convert duration from minutes to hours // Convert duration from minutes to hours
if (Config.logPumpActions) if (Config.logPumpActions)
log.debug("setTempBasalAbsolute: Setting temp basal " + percentRate + "% for " + durationInMinutes + " mins (doLowTemp || doHighTemp)"); log.debug("setTempBasalAbsolute: Setting temp basal " + percentRate + "% for " + durationInMinutes + " mins (doLowTemp || doHighTemp)");
return setTempBasalPercent(percentRate, durationInMinutes, false); return setTempBasalPercent(percentRate, durationInMinutes, profile,false);
} }
if (doExtendedTemp) { if (doExtendedTemp) {
// Check if some temp is already in progress // Check if some temp is already in progress
@ -270,7 +269,7 @@ public class DanaRKoreanPlugin extends AbstractDanaRPlugin {
Integer durationInHalfHours = Math.max(durationInMinutes / 30, 1); Integer durationInHalfHours = Math.max(durationInMinutes / 30, 1);
// We keep current basal running so need to sub current basal // We keep current basal running so need to sub current basal
Double extendedRateToSet = absoluteRate - getBaseBasalRate(); Double extendedRateToSet = absoluteRate - getBaseBasalRate();
extendedRateToSet = configBuilderPlugin.applyBasalConstraints(extendedRateToSet); extendedRateToSet = MainApp.getConstraintChecker().applyBasalConstraints(new Constraint<>(extendedRateToSet), profile).value();
// needs to be rounded to 0.1 // needs to be rounded to 0.1
extendedRateToSet = Round.roundTo(extendedRateToSet, pumpDescription.extendedBolusStep * 2); // *2 because of halfhours extendedRateToSet = Round.roundTo(extendedRateToSet, pumpDescription.extendedBolusStep * 2); // *2 because of halfhours

View file

@ -33,17 +33,17 @@ public class MsgInitConnStatusTime_k extends MessageBase {
MainApp.bus().post(new EventNewNotification(notification)); MainApp.bus().post(new EventNewNotification(notification));
DanaRKoreanPlugin.getPlugin().disconnect("Wrong Model"); DanaRKoreanPlugin.getPlugin().disconnect("Wrong Model");
log.debug("Wrong model selected. Switching to export DanaR"); log.debug("Wrong model selected. Switching to export DanaR");
MainApp.getSpecificPlugin(DanaRKoreanPlugin.class).setFragmentEnabled(PluginBase.PUMP, false); MainApp.getSpecificPlugin(DanaRKoreanPlugin.class).setPluginEnabled(PluginBase.PUMP, false);
MainApp.getSpecificPlugin(DanaRKoreanPlugin.class).setFragmentVisible(PluginBase.PUMP, false); MainApp.getSpecificPlugin(DanaRKoreanPlugin.class).setFragmentVisible(PluginBase.PUMP, false);
MainApp.getSpecificPlugin(DanaRPlugin.class).setFragmentEnabled(PluginBase.PUMP, true); MainApp.getSpecificPlugin(DanaRPlugin.class).setPluginEnabled(PluginBase.PUMP, true);
MainApp.getSpecificPlugin(DanaRPlugin.class).setFragmentVisible(PluginBase.PUMP, true); MainApp.getSpecificPlugin(DanaRPlugin.class).setFragmentVisible(PluginBase.PUMP, true);
DanaRPump.reset(); // mark not initialized DanaRPump.reset(); // mark not initialized
//If profile coming from pump, switch it as well //If profile coming from pump, switch it as well
if (MainApp.getSpecificPlugin(DanaRKoreanPlugin.class).isEnabled(PluginBase.PROFILE)) { if (MainApp.getSpecificPlugin(DanaRKoreanPlugin.class).isEnabled(PluginBase.PROFILE)) {
(MainApp.getSpecificPlugin(DanaRKoreanPlugin.class)).setFragmentEnabled(PluginBase.PROFILE, false); (MainApp.getSpecificPlugin(DanaRKoreanPlugin.class)).setPluginEnabled(PluginBase.PROFILE, false);
(MainApp.getSpecificPlugin(DanaRPlugin.class)).setFragmentEnabled(PluginBase.PROFILE, true); (MainApp.getSpecificPlugin(DanaRPlugin.class)).setPluginEnabled(PluginBase.PROFILE, true);
} }
MainApp.getConfigBuilder().storeSettings(); MainApp.getConfigBuilder().storeSettings();

View file

@ -15,11 +15,9 @@ import org.slf4j.Logger;
import org.slf4j.LoggerFactory; import org.slf4j.LoggerFactory;
import java.util.Date; import java.util.Date;
import java.util.Objects;
import info.nightscout.androidaps.BuildConfig; import info.nightscout.androidaps.BuildConfig;
import info.nightscout.androidaps.Config; import info.nightscout.androidaps.Config;
import info.nightscout.androidaps.Constants;
import info.nightscout.androidaps.MainApp; import info.nightscout.androidaps.MainApp;
import info.nightscout.androidaps.R; import info.nightscout.androidaps.R;
import info.nightscout.androidaps.data.DetailedBolusInfo; import info.nightscout.androidaps.data.DetailedBolusInfo;
@ -30,17 +28,17 @@ import info.nightscout.androidaps.db.ExtendedBolus;
import info.nightscout.androidaps.db.TemporaryBasal; import info.nightscout.androidaps.db.TemporaryBasal;
import info.nightscout.androidaps.db.Treatment; import info.nightscout.androidaps.db.Treatment;
import info.nightscout.androidaps.events.EventAppExit; import info.nightscout.androidaps.events.EventAppExit;
import info.nightscout.androidaps.interfaces.Constraint;
import info.nightscout.androidaps.interfaces.ConstraintsInterface; import info.nightscout.androidaps.interfaces.ConstraintsInterface;
import info.nightscout.androidaps.interfaces.DanaRInterface; import info.nightscout.androidaps.interfaces.DanaRInterface;
import info.nightscout.androidaps.interfaces.PluginBase; import info.nightscout.androidaps.interfaces.PluginBase;
import info.nightscout.androidaps.interfaces.ProfileInterface; import info.nightscout.androidaps.interfaces.ProfileInterface;
import info.nightscout.androidaps.interfaces.PumpDescription; import info.nightscout.androidaps.interfaces.PumpDescription;
import info.nightscout.androidaps.interfaces.PumpInterface; import info.nightscout.androidaps.interfaces.PumpInterface;
import info.nightscout.androidaps.plugins.ConfigBuilder.ConfigBuilderPlugin;
import info.nightscout.androidaps.plugins.ConfigBuilder.DetailedBolusInfoStorage; import info.nightscout.androidaps.plugins.ConfigBuilder.DetailedBolusInfoStorage;
import info.nightscout.androidaps.plugins.Overview.notifications.Notification;
import info.nightscout.androidaps.plugins.Overview.events.EventDismissNotification; import info.nightscout.androidaps.plugins.Overview.events.EventDismissNotification;
import info.nightscout.androidaps.plugins.Overview.events.EventNewNotification; import info.nightscout.androidaps.plugins.Overview.events.EventNewNotification;
import info.nightscout.androidaps.plugins.Overview.notifications.Notification;
import info.nightscout.androidaps.plugins.ProfileNS.NSProfilePlugin; import info.nightscout.androidaps.plugins.ProfileNS.NSProfilePlugin;
import info.nightscout.androidaps.plugins.PumpDanaR.DanaRFragment; import info.nightscout.androidaps.plugins.PumpDanaR.DanaRFragment;
import info.nightscout.androidaps.plugins.PumpDanaR.DanaRPump; import info.nightscout.androidaps.plugins.PumpDanaR.DanaRPump;
@ -116,16 +114,16 @@ public class DanaRSPlugin implements PluginBase, PumpInterface, DanaRInterface,
} }
@Override @Override
public void setFragmentEnabled(int type, boolean fragmentEnabled) { public void setPluginEnabled(int type, boolean fragmentEnabled) {
if (type == PluginBase.PROFILE) if (type == PluginBase.PROFILE)
this.fragmentProfileEnabled = fragmentEnabled; this.fragmentProfileEnabled = fragmentEnabled;
else if (type == PluginBase.PUMP) else if (type == PluginBase.PUMP)
this.fragmentPumpEnabled = fragmentEnabled; this.fragmentPumpEnabled = fragmentEnabled;
// if pump profile was enabled need to switch to another too // if pump profile was enabled need to switch to another too
if (type == PluginBase.PUMP && !fragmentEnabled && this.fragmentProfileEnabled) { if (type == PluginBase.PUMP && !fragmentEnabled && this.fragmentProfileEnabled) {
setFragmentEnabled(PluginBase.PROFILE, false); setPluginEnabled(PluginBase.PROFILE, false);
setFragmentVisible(PluginBase.PROFILE, false); setFragmentVisible(PluginBase.PROFILE, false);
MainApp.getSpecificPlugin(NSProfilePlugin.class).setFragmentEnabled(PluginBase.PROFILE, true); MainApp.getSpecificPlugin(NSProfilePlugin.class).setPluginEnabled(PluginBase.PROFILE, true);
MainApp.getSpecificPlugin(NSProfilePlugin.class).setFragmentVisible(PluginBase.PROFILE, true); MainApp.getSpecificPlugin(NSProfilePlugin.class).setFragmentVisible(PluginBase.PROFILE, true);
} }
} }
@ -275,77 +273,28 @@ public class DanaRSPlugin implements PluginBase, PumpInterface, DanaRInterface,
// Constraints interface // Constraints interface
@Override @Override
public boolean isLoopEnabled() { public Constraint<Double> applyBasalConstraints(Constraint<Double> absoluteRate, Profile profile) {
return true; if (pump != null)
} absoluteRate.setIfSmaller(pump.maxBasal, String.format(MainApp.gs(R.string.limitingbasalratio), pump.maxBasal, MainApp.gs(R.string.pumplimit)), this);
@Override
public boolean isClosedModeEnabled() {
return true;
}
@Override
public boolean isAutosensModeEnabled() {
return true;
}
@Override
public boolean isAMAModeEnabled() {
return true;
}
@Override
public boolean isSMBModeEnabled() {
return true;
}
@Override
public Double applyBasalConstraints(Double absoluteRate) {
double origAbsoluteRate = absoluteRate;
if (pump != null) {
if (absoluteRate > pump.maxBasal) {
absoluteRate = pump.maxBasal;
if (Config.logConstraintsChanges && origAbsoluteRate != Constants.basalAbsoluteOnlyForCheckLimit)
log.debug("Limiting rate " + origAbsoluteRate + "U/h by pump constraint to " + absoluteRate + "U/h");
}
}
return absoluteRate; return absoluteRate;
} }
@Override @Override
public Integer applyBasalConstraints(Integer percentRate) { public Constraint<Integer> applyBasalPercentConstraints(Constraint<Integer> percentRate, Profile profile) {
Integer origPercentRate = percentRate; percentRate.setIfGreater(0, String.format(MainApp.gs(R.string.limitingpercentrate), 0, MainApp.gs(R.string.itmustbepositivevalue)), this);
if (percentRate < 0) percentRate = 0; percentRate.setIfSmaller(getPumpDescription().maxTempPercent, String.format(MainApp.gs(R.string.limitingpercentrate), getPumpDescription().maxTempPercent, MainApp.gs(R.string.pumplimit)), this);
if (percentRate > getPumpDescription().maxTempPercent)
percentRate = getPumpDescription().maxTempPercent;
if (!Objects.equals(percentRate, origPercentRate) && Config.logConstraintsChanges && !Objects.equals(origPercentRate, Constants.basalPercentOnlyForCheckLimit))
log.debug("Limiting percent rate " + origPercentRate + "% to " + percentRate + "%");
return percentRate; return percentRate;
} }
@Override @Override
public Double applyBolusConstraints(Double insulin) { public Constraint<Double> applyBolusConstraints(Constraint<Double> insulin) {
double origInsulin = insulin; if (pump != null)
if (pump != null) { insulin.setIfSmaller(pump.maxBolus, String.format(MainApp.gs(R.string.limitingbolus), pump.maxBolus, MainApp.gs(R.string.pumplimit)), this);
if (insulin > pump.maxBolus) {
insulin = pump.maxBolus;
if (Config.logConstraintsChanges && origInsulin != Constants.bolusOnlyForCheckLimit)
log.debug("Limiting bolus " + origInsulin + "U by pump constraint to " + insulin + "U");
}
}
return insulin; return insulin;
} }
@Override
public Integer applyCarbsConstraints(Integer carbs) {
return carbs;
}
@Override
public Double applyMaxIOBConstraints(Double maxIob) {
return maxIob;
}
// Profile interface // Profile interface
@Nullable @Nullable
@ -451,8 +400,7 @@ public class DanaRSPlugin implements PluginBase, PumpInterface, DanaRInterface,
@Override @Override
public synchronized PumpEnactResult deliverTreatment(DetailedBolusInfo detailedBolusInfo) { public synchronized PumpEnactResult deliverTreatment(DetailedBolusInfo detailedBolusInfo) {
ConfigBuilderPlugin configBuilderPlugin = MainApp.getConfigBuilder(); detailedBolusInfo.insulin = MainApp.getConstraintChecker().applyBolusConstraints(new Constraint<>(detailedBolusInfo.insulin)).value();
detailedBolusInfo.insulin = configBuilderPlugin.applyBolusConstraints(detailedBolusInfo.insulin);
if (detailedBolusInfo.insulin > 0 || detailedBolusInfo.carbs > 0) { if (detailedBolusInfo.insulin > 0 || detailedBolusInfo.carbs > 0) {
int preferencesSpeed = SP.getInt(R.string.key_danars_bolusspeed, 0); int preferencesSpeed = SP.getInt(R.string.key_danars_bolusspeed, 0);
int speed = 12; int speed = 12;
@ -514,7 +462,7 @@ public class DanaRSPlugin implements PluginBase, PumpInterface, DanaRInterface,
// This is called from APS // This is called from APS
@Override @Override
public synchronized PumpEnactResult setTempBasalAbsolute(Double absoluteRate, Integer durationInMinutes, boolean enforceNew) { public synchronized PumpEnactResult setTempBasalAbsolute(Double absoluteRate, Integer durationInMinutes, Profile profile, boolean enforceNew) {
// Recheck pump status if older than 30 min // Recheck pump status if older than 30 min
//This should not be needed while using queue because connection should be done before calling this //This should not be needed while using queue because connection should be done before calling this
@ -524,8 +472,7 @@ public class DanaRSPlugin implements PluginBase, PumpInterface, DanaRInterface,
PumpEnactResult result = new PumpEnactResult(); PumpEnactResult result = new PumpEnactResult();
ConfigBuilderPlugin configBuilderPlugin = MainApp.getConfigBuilder(); absoluteRate = MainApp.getConstraintChecker().applyBasalConstraints(new Constraint<>(absoluteRate), profile).value();
absoluteRate = configBuilderPlugin.applyBasalConstraints(absoluteRate);
final boolean doTempOff = getBaseBasalRate() - absoluteRate == 0d; final boolean doTempOff = getBaseBasalRate() - absoluteRate == 0d;
final boolean doLowTemp = absoluteRate < getBaseBasalRate(); final boolean doLowTemp = absoluteRate < getBaseBasalRate();
@ -595,10 +542,9 @@ public class DanaRSPlugin implements PluginBase, PumpInterface, DanaRInterface,
} }
@Override @Override
public synchronized PumpEnactResult setTempBasalPercent(Integer percent, Integer durationInMinutes, boolean enforceNew) { public synchronized PumpEnactResult setTempBasalPercent(Integer percent, Integer durationInMinutes, Profile profile, boolean enforceNew) {
PumpEnactResult result = new PumpEnactResult(); PumpEnactResult result = new PumpEnactResult();
ConfigBuilderPlugin configBuilderPlugin = MainApp.getConfigBuilder(); percent = MainApp.getConstraintChecker().applyBasalPercentConstraints(new Constraint<>(percent), profile).value();
percent = configBuilderPlugin.applyBasalConstraints(percent);
if (percent < 0) { if (percent < 0) {
result.isTempCancel = false; result.isTempCancel = false;
result.enacted = false; result.enacted = false;
@ -673,8 +619,7 @@ public class DanaRSPlugin implements PluginBase, PumpInterface, DanaRInterface,
@Override @Override
public synchronized PumpEnactResult setExtendedBolus(Double insulin, Integer durationInMinutes) { public synchronized PumpEnactResult setExtendedBolus(Double insulin, Integer durationInMinutes) {
ConfigBuilderPlugin configBuilderPlugin = MainApp.getConfigBuilder(); insulin = MainApp.getConstraintChecker().applyBolusConstraints(new Constraint<>(insulin)).value();
insulin = configBuilderPlugin.applyBolusConstraints(insulin);
// needs to be rounded // needs to be rounded
int durationInHalfHours = Math.max(durationInMinutes / 30, 1); int durationInHalfHours = Math.max(durationInMinutes / 30, 1);
insulin = Round.roundTo(insulin, getPumpDescription().extendedBolusStep); insulin = Round.roundTo(insulin, getPumpDescription().extendedBolusStep);

View file

@ -1,11 +1,13 @@
package info.nightscout.androidaps.plugins.PumpDanaRS.comm; package info.nightscout.androidaps.plugins.PumpDanaRS.comm;
import com.cozmo.danar.util.BleCommandUtil;
import org.slf4j.Logger; import org.slf4j.Logger;
import org.slf4j.LoggerFactory; import org.slf4j.LoggerFactory;
import info.nightscout.androidaps.Config; import info.nightscout.androidaps.Config;
import info.nightscout.androidaps.MainApp; import info.nightscout.androidaps.MainApp;
import com.cozmo.danar.util.BleCommandUtil; import info.nightscout.androidaps.interfaces.Constraint;
import info.nightscout.utils.HardLimits; import info.nightscout.utils.HardLimits;
public class DanaRS_Packet_Bolus_Set_Step_Bolus_Start extends DanaRS_Packet { public class DanaRS_Packet_Bolus_Set_Step_Bolus_Start extends DanaRS_Packet {
@ -26,9 +28,7 @@ public class DanaRS_Packet_Bolus_Set_Step_Bolus_Start extends DanaRS_Packet {
this(); this();
// HARDCODED LIMIT // HARDCODED LIMIT
amount = MainApp.getConfigBuilder().applyBolusConstraints(amount); amount = MainApp.getConstraintChecker().applyBolusConstraints(new Constraint<>(amount)).value();
if (amount < 0) amount = 0d;
if (amount > HardLimits.maxBolus()) amount = HardLimits.maxBolus();
this.amount = amount; this.amount = amount;
this.speed = speed; this.speed = speed;

View file

@ -14,12 +14,13 @@ import info.nightscout.androidaps.Config;
import info.nightscout.androidaps.MainApp; import info.nightscout.androidaps.MainApp;
import info.nightscout.androidaps.R; import info.nightscout.androidaps.R;
import info.nightscout.androidaps.data.DetailedBolusInfo; import info.nightscout.androidaps.data.DetailedBolusInfo;
import info.nightscout.androidaps.data.Profile;
import info.nightscout.androidaps.data.PumpEnactResult; import info.nightscout.androidaps.data.PumpEnactResult;
import info.nightscout.androidaps.db.TemporaryBasal; import info.nightscout.androidaps.db.TemporaryBasal;
import info.nightscout.androidaps.db.Treatment; import info.nightscout.androidaps.db.Treatment;
import info.nightscout.androidaps.events.EventAppExit; import info.nightscout.androidaps.events.EventAppExit;
import info.nightscout.androidaps.interfaces.Constraint;
import info.nightscout.androidaps.interfaces.PumpDescription; import info.nightscout.androidaps.interfaces.PumpDescription;
import info.nightscout.androidaps.plugins.ConfigBuilder.ConfigBuilderPlugin;
import info.nightscout.androidaps.plugins.ConfigBuilder.DetailedBolusInfoStorage; import info.nightscout.androidaps.plugins.ConfigBuilder.DetailedBolusInfoStorage;
import info.nightscout.androidaps.plugins.PumpDanaR.AbstractDanaRPlugin; import info.nightscout.androidaps.plugins.PumpDanaR.AbstractDanaRPlugin;
import info.nightscout.androidaps.plugins.PumpDanaRv2.services.DanaRv2ExecutionService; import info.nightscout.androidaps.plugins.PumpDanaRv2.services.DanaRv2ExecutionService;
@ -121,8 +122,7 @@ public class DanaRv2Plugin extends AbstractDanaRPlugin {
// Pump interface // Pump interface
@Override @Override
public PumpEnactResult deliverTreatment(DetailedBolusInfo detailedBolusInfo) { public PumpEnactResult deliverTreatment(DetailedBolusInfo detailedBolusInfo) {
ConfigBuilderPlugin configBuilderPlugin = MainApp.getConfigBuilder(); detailedBolusInfo.insulin = MainApp.getConstraintChecker().applyBolusConstraints(new Constraint<>(detailedBolusInfo.insulin)).value();
detailedBolusInfo.insulin = configBuilderPlugin.applyBolusConstraints(detailedBolusInfo.insulin);
if (detailedBolusInfo.insulin > 0 || detailedBolusInfo.carbs > 0) { if (detailedBolusInfo.insulin > 0 || detailedBolusInfo.carbs > 0) {
// v2 stores end time for bolus, we need to adjust time // v2 stores end time for bolus, we need to adjust time
// default delivery speed is 12 sec/U // default delivery speed is 12 sec/U
@ -185,7 +185,7 @@ public class DanaRv2Plugin extends AbstractDanaRPlugin {
// This is called from APS // This is called from APS
@Override @Override
public PumpEnactResult setTempBasalAbsolute(Double absoluteRate, Integer durationInMinutes, boolean enforceNew) { public PumpEnactResult setTempBasalAbsolute(Double absoluteRate, Integer durationInMinutes, Profile profile, boolean enforceNew) {
// Recheck pump status if older than 30 min // Recheck pump status if older than 30 min
//This should not be needed while using queue because connection should be done before calling this //This should not be needed while using queue because connection should be done before calling this
//if (pump.lastConnection.getTime() + 30 * 60 * 1000L < System.currentTimeMillis()) { //if (pump.lastConnection.getTime() + 30 * 60 * 1000L < System.currentTimeMillis()) {
@ -194,8 +194,7 @@ public class DanaRv2Plugin extends AbstractDanaRPlugin {
PumpEnactResult result = new PumpEnactResult(); PumpEnactResult result = new PumpEnactResult();
ConfigBuilderPlugin configBuilderPlugin = MainApp.getConfigBuilder(); absoluteRate = MainApp.getConstraintChecker().applyBasalConstraints(new Constraint<>(absoluteRate), profile).value();
absoluteRate = configBuilderPlugin.applyBasalConstraints(absoluteRate);
final boolean doTempOff = getBaseBasalRate() - absoluteRate == 0d; final boolean doTempOff = getBaseBasalRate() - absoluteRate == 0d;
final boolean doLowTemp = absoluteRate < getBaseBasalRate(); final boolean doLowTemp = absoluteRate < getBaseBasalRate();
@ -263,10 +262,9 @@ public class DanaRv2Plugin extends AbstractDanaRPlugin {
} }
@Override @Override
public PumpEnactResult setTempBasalPercent(Integer percent, Integer durationInMinutes, boolean enforceNew) { public PumpEnactResult setTempBasalPercent(Integer percent, Integer durationInMinutes, Profile profile, boolean enforceNew) {
PumpEnactResult result = new PumpEnactResult(); PumpEnactResult result = new PumpEnactResult();
ConfigBuilderPlugin configBuilderPlugin = MainApp.getConfigBuilder(); percent = MainApp.getConstraintChecker().applyBasalPercentConstraints(new Constraint<>(percent), profile).value();
percent = configBuilderPlugin.applyBasalConstraints(percent);
if (percent < 0) { if (percent < 0) {
result.isTempCancel = false; result.isTempCancel = false;
result.enacted = false; result.enacted = false;

View file

@ -3,8 +3,6 @@ package info.nightscout.androidaps.plugins.PumpDanaRv2.comm;
import org.slf4j.Logger; import org.slf4j.Logger;
import org.slf4j.LoggerFactory; import org.slf4j.LoggerFactory;
import java.util.Date;
import info.nightscout.androidaps.Config; import info.nightscout.androidaps.Config;
import info.nightscout.androidaps.MainApp; import info.nightscout.androidaps.MainApp;
import info.nightscout.androidaps.R; import info.nightscout.androidaps.R;
@ -45,17 +43,17 @@ public class MsgCheckValue_v2 extends MessageBase {
MainApp.bus().post(new EventNewNotification(notification)); MainApp.bus().post(new EventNewNotification(notification));
MainApp.getSpecificPlugin(DanaRPlugin.class).disconnect("Wrong Model"); MainApp.getSpecificPlugin(DanaRPlugin.class).disconnect("Wrong Model");
log.debug("Wrong model selected. Switching to Korean DanaR"); log.debug("Wrong model selected. Switching to Korean DanaR");
MainApp.getSpecificPlugin(DanaRKoreanPlugin.class).setFragmentEnabled(PluginBase.PUMP, true); MainApp.getSpecificPlugin(DanaRKoreanPlugin.class).setPluginEnabled(PluginBase.PUMP, true);
MainApp.getSpecificPlugin(DanaRKoreanPlugin.class).setFragmentVisible(PluginBase.PUMP, true); MainApp.getSpecificPlugin(DanaRKoreanPlugin.class).setFragmentVisible(PluginBase.PUMP, true);
MainApp.getSpecificPlugin(DanaRPlugin.class).setFragmentEnabled(PluginBase.PUMP, false); MainApp.getSpecificPlugin(DanaRPlugin.class).setPluginEnabled(PluginBase.PUMP, false);
MainApp.getSpecificPlugin(DanaRPlugin.class).setFragmentVisible(PluginBase.PUMP, false); MainApp.getSpecificPlugin(DanaRPlugin.class).setFragmentVisible(PluginBase.PUMP, false);
DanaRPump.reset(); // mark not initialized DanaRPump.reset(); // mark not initialized
//If profile coming from pump, switch it as well //If profile coming from pump, switch it as well
if(MainApp.getSpecificPlugin(DanaRPlugin.class).isEnabled(PluginBase.PROFILE)){ if(MainApp.getSpecificPlugin(DanaRPlugin.class).isEnabled(PluginBase.PROFILE)){
(MainApp.getSpecificPlugin(DanaRPlugin.class)).setFragmentEnabled(PluginBase.PROFILE, false); (MainApp.getSpecificPlugin(DanaRPlugin.class)).setPluginEnabled(PluginBase.PROFILE, false);
(MainApp.getSpecificPlugin(DanaRKoreanPlugin.class)).setFragmentEnabled(PluginBase.PROFILE, true); (MainApp.getSpecificPlugin(DanaRKoreanPlugin.class)).setPluginEnabled(PluginBase.PROFILE, true);
} }
MainApp.getConfigBuilder().storeSettings(); MainApp.getConfigBuilder().storeSettings();
@ -70,15 +68,15 @@ public class MsgCheckValue_v2 extends MessageBase {
MainApp.bus().post(new EventNewNotification(notification)); MainApp.bus().post(new EventNewNotification(notification));
DanaRKoreanPlugin.getPlugin().disconnect("Wrong Model"); DanaRKoreanPlugin.getPlugin().disconnect("Wrong Model");
log.debug("Wrong model selected. Switching to non APS DanaR"); log.debug("Wrong model selected. Switching to non APS DanaR");
(MainApp.getSpecificPlugin(DanaRv2Plugin.class)).setFragmentEnabled(PluginBase.PUMP, false); (MainApp.getSpecificPlugin(DanaRv2Plugin.class)).setPluginEnabled(PluginBase.PUMP, false);
(MainApp.getSpecificPlugin(DanaRv2Plugin.class)).setFragmentVisible(PluginBase.PUMP, false); (MainApp.getSpecificPlugin(DanaRv2Plugin.class)).setFragmentVisible(PluginBase.PUMP, false);
(MainApp.getSpecificPlugin(DanaRPlugin.class)).setFragmentEnabled(PluginBase.PUMP, true); (MainApp.getSpecificPlugin(DanaRPlugin.class)).setPluginEnabled(PluginBase.PUMP, true);
(MainApp.getSpecificPlugin(DanaRPlugin.class)).setFragmentVisible(PluginBase.PUMP, true); (MainApp.getSpecificPlugin(DanaRPlugin.class)).setFragmentVisible(PluginBase.PUMP, true);
//If profile coming from pump, switch it as well //If profile coming from pump, switch it as well
if(MainApp.getSpecificPlugin(DanaRv2Plugin.class).isEnabled(PluginBase.PROFILE)){ if(MainApp.getSpecificPlugin(DanaRv2Plugin.class).isEnabled(PluginBase.PROFILE)){
(MainApp.getSpecificPlugin(DanaRv2Plugin.class)).setFragmentEnabled(PluginBase.PROFILE, false); (MainApp.getSpecificPlugin(DanaRv2Plugin.class)).setPluginEnabled(PluginBase.PROFILE, false);
(MainApp.getSpecificPlugin(DanaRPlugin.class)).setFragmentEnabled(PluginBase.PROFILE, true); (MainApp.getSpecificPlugin(DanaRPlugin.class)).setPluginEnabled(PluginBase.PROFILE, true);
} }
MainApp.getConfigBuilder().storeSettings(); MainApp.getConfigBuilder().storeSettings();

View file

@ -8,7 +8,7 @@ import java.util.UUID;
import java.util.concurrent.ConcurrentHashMap; import java.util.concurrent.ConcurrentHashMap;
import info.nightscout.androidaps.MainApp; import info.nightscout.androidaps.MainApp;
import info.nightscout.androidaps.plugins.PumpInsight.events.EventInsightPumpCallback; import info.nightscout.androidaps.plugins.PumpInsight.events.EventInsightCallback;
import static info.nightscout.androidaps.plugins.PumpInsight.utils.Helpers.getWakeLock; import static info.nightscout.androidaps.plugins.PumpInsight.utils.Helpers.getWakeLock;
import static info.nightscout.androidaps.plugins.PumpInsight.utils.Helpers.msSince; import static info.nightscout.androidaps.plugins.PumpInsight.utils.Helpers.msSince;
@ -22,11 +22,11 @@ import static info.nightscout.androidaps.plugins.PumpInsight.utils.Helpers.tsl;
* *
*/ */
public class InsightPumpAsyncAdapter { public class InsightAsyncAdapter {
private final ConcurrentHashMap<UUID, EventInsightPumpCallback> commandResults = new ConcurrentHashMap<>(); private final ConcurrentHashMap<UUID, EventInsightCallback> commandResults = new ConcurrentHashMap<>();
InsightPumpAsyncAdapter() { InsightAsyncAdapter() {
MainApp.bus().register(this); MainApp.bus().register(this);
} }
@ -36,7 +36,7 @@ public class InsightPumpAsyncAdapter {
} }
@Subscribe @Subscribe
public void onStatusEvent(final EventInsightPumpCallback ev) { public void onStatusEvent(final EventInsightCallback ev) {
log("Received callback event: " + ev.toString()); log("Received callback event: " + ev.toString());
commandResults.put(ev.request_uuid, ev); commandResults.put(ev.request_uuid, ev);
} }

View file

@ -19,14 +19,14 @@ import java.util.List;
import info.nightscout.androidaps.R; import info.nightscout.androidaps.R;
import info.nightscout.androidaps.plugins.Common.SubscriberFragment; import info.nightscout.androidaps.plugins.Common.SubscriberFragment;
import info.nightscout.androidaps.plugins.PumpInsight.events.EventInsightPumpUpdateGui; import info.nightscout.androidaps.plugins.PumpInsight.events.EventInsightUpdateGui;
import info.nightscout.androidaps.plugins.PumpInsight.utils.StatusItem; import info.nightscout.androidaps.plugins.PumpInsight.utils.StatusItem;
import info.nightscout.androidaps.plugins.PumpInsight.utils.ui.StatusItemViewAdapter; import info.nightscout.androidaps.plugins.PumpInsight.utils.ui.StatusItemViewAdapter;
import info.nightscout.utils.FabricPrivacy; import info.nightscout.utils.FabricPrivacy;
public class InsightPumpFragment extends SubscriberFragment { public class InsightFragment extends SubscriberFragment {
private static final Logger log = LoggerFactory.getLogger(InsightPumpFragment.class); private static final Logger log = LoggerFactory.getLogger(InsightFragment.class);
private static final Handler sLoopHandler = new Handler(); private static final Handler sLoopHandler = new Handler();
private static volatile boolean refresh = false; private static volatile boolean refresh = false;
private static volatile boolean pending = false; private static volatile boolean pending = false;
@ -88,7 +88,7 @@ public class InsightPumpFragment extends SubscriberFragment {
@Subscribe @Subscribe
public void onStatusEvent(final EventInsightPumpUpdateGui ev) { public void onStatusEvent(final EventInsightUpdateGui ev) {
updateGUI(); updateGUI();
} }
@ -99,8 +99,8 @@ public class InsightPumpFragment extends SubscriberFragment {
activity.runOnUiThread(new Runnable() { activity.runOnUiThread(new Runnable() {
@Override @Override
public void run() { public void run() {
final InsightPumpPlugin insightPumpPlugin = InsightPumpPlugin.getPlugin(); final InsightPlugin insightPlugin = InsightPlugin.getPlugin();
final List<StatusItem> l = insightPumpPlugin.getStatusItems(refresh); final List<StatusItem> l = insightPlugin.getStatusItems(refresh);
holder.removeAllViews(); holder.removeAllViews();

View file

@ -1,10 +1,5 @@
package info.nightscout.androidaps.plugins.PumpInsight; package info.nightscout.androidaps.plugins.PumpInsight;
import android.os.Handler;
import android.util.Log;
import com.j256.ormlite.stmt.query.In;
import org.json.JSONException; import org.json.JSONException;
import org.json.JSONObject; import org.json.JSONObject;
import org.slf4j.Logger; import org.slf4j.Logger;
@ -27,11 +22,11 @@ import info.nightscout.androidaps.db.ExtendedBolus;
import info.nightscout.androidaps.db.Source; import info.nightscout.androidaps.db.Source;
import info.nightscout.androidaps.db.TemporaryBasal; import info.nightscout.androidaps.db.TemporaryBasal;
import info.nightscout.androidaps.db.Treatment; import info.nightscout.androidaps.db.Treatment;
import info.nightscout.androidaps.interfaces.Constraint;
import info.nightscout.androidaps.interfaces.ConstraintsInterface; import info.nightscout.androidaps.interfaces.ConstraintsInterface;
import info.nightscout.androidaps.interfaces.PluginBase; import info.nightscout.androidaps.interfaces.PluginBase;
import info.nightscout.androidaps.interfaces.PumpDescription; import info.nightscout.androidaps.interfaces.PumpDescription;
import info.nightscout.androidaps.interfaces.PumpInterface; import info.nightscout.androidaps.interfaces.PumpInterface;
import info.nightscout.androidaps.plugins.Overview.events.EventDismissBolusprogressIfRunning;
import info.nightscout.androidaps.plugins.Overview.events.EventDismissNotification; import info.nightscout.androidaps.plugins.Overview.events.EventDismissNotification;
import info.nightscout.androidaps.plugins.Overview.events.EventNewNotification; import info.nightscout.androidaps.plugins.Overview.events.EventNewNotification;
import info.nightscout.androidaps.plugins.Overview.events.EventOverviewBolusProgress; import info.nightscout.androidaps.plugins.Overview.events.EventOverviewBolusProgress;
@ -41,8 +36,8 @@ import info.nightscout.androidaps.plugins.PumpInsight.connector.Connector;
import info.nightscout.androidaps.plugins.PumpInsight.connector.SetTBRTaskRunner; import info.nightscout.androidaps.plugins.PumpInsight.connector.SetTBRTaskRunner;
import info.nightscout.androidaps.plugins.PumpInsight.connector.StatusTaskRunner; import info.nightscout.androidaps.plugins.PumpInsight.connector.StatusTaskRunner;
import info.nightscout.androidaps.plugins.PumpInsight.connector.WriteBasalProfileTaskRunner; import info.nightscout.androidaps.plugins.PumpInsight.connector.WriteBasalProfileTaskRunner;
import info.nightscout.androidaps.plugins.PumpInsight.events.EventInsightPumpCallback; import info.nightscout.androidaps.plugins.PumpInsight.events.EventInsightCallback;
import info.nightscout.androidaps.plugins.PumpInsight.events.EventInsightPumpUpdateGui; import info.nightscout.androidaps.plugins.PumpInsight.events.EventInsightUpdateGui;
import info.nightscout.androidaps.plugins.PumpInsight.history.HistoryReceiver; import info.nightscout.androidaps.plugins.PumpInsight.history.HistoryReceiver;
import info.nightscout.androidaps.plugins.PumpInsight.history.LiveHistory; import info.nightscout.androidaps.plugins.PumpInsight.history.LiveHistory;
import info.nightscout.androidaps.plugins.PumpInsight.utils.Helpers; import info.nightscout.androidaps.plugins.PumpInsight.utils.Helpers;
@ -70,26 +65,25 @@ import static info.nightscout.androidaps.plugins.PumpInsight.history.PumpIdCache
/** /**
* Created by jamorham on 23/01/2018. * Created by jamorham on 23/01/2018.
* * <p>
* Connects to SightRemote app service using SightParser library * Connects to SightRemote app service using SightParser library
* * <p>
* SightRemote and SightParser created by Tebbe Ubben * SightRemote and SightParser created by Tebbe Ubben
* * <p>
* Original proof of concept SightProxy by jamorham * Original proof of concept SightProxy by jamorham
*
*/ */
@SuppressWarnings("AccessStaticViaInstance") @SuppressWarnings("AccessStaticViaInstance")
public class InsightPumpPlugin implements PluginBase, PumpInterface, ConstraintsInterface { public class InsightPlugin implements PluginBase, PumpInterface, ConstraintsInterface {
private static final long BUSY_WAIT_TIME = 20000; private static final long BUSY_WAIT_TIME = 20000;
static Integer batteryPercent = 0; static Integer batteryPercent = 0;
static Integer reservoirInUnits = 0; static Integer reservoirInUnits = 0;
static boolean initialized = false; static boolean initialized = false;
private static volatile boolean update_pending = false; private static volatile boolean update_pending = false;
private static Logger log = LoggerFactory.getLogger(InsightPumpPlugin.class); private static Logger log = LoggerFactory.getLogger(InsightPlugin.class);
private static volatile InsightPumpPlugin plugin; private static volatile InsightPlugin plugin;
private final InsightPumpAsyncAdapter async = new InsightPumpAsyncAdapter(); private final InsightAsyncAdapter async = new InsightAsyncAdapter();
private StatusTaskRunner.Result statusResult; private StatusTaskRunner.Result statusResult;
private long statusResultTime = -1; private long statusResultTime = -1;
private Date lastDataTime = new Date(0); private Date lastDataTime = new Date(0);
@ -102,8 +96,8 @@ public class InsightPumpPlugin implements PluginBase, PumpInterface, Constraints
private volatile boolean connector_enabled = false; private volatile boolean connector_enabled = false;
private List<BRProfileBlock.ProfileBlock> profileBlocks; private List<BRProfileBlock.ProfileBlock> profileBlocks;
private InsightPumpPlugin() { private InsightPlugin() {
log("InsightPumpPlugin instantiated"); log("InsightPlugin instantiated");
pumpDescription.isBolusCapable = true; pumpDescription.isBolusCapable = true;
pumpDescription.bolusStep = 0.05d; // specification says 0.05U up to 2U then 0.1U @ 2-5U 0.2U @ 10-20U 0.5U 10-20U (are these just UI restrictions?) pumpDescription.bolusStep = 0.05d; // specification says 0.05U up to 2U then 0.1U @ 2-5U 0.2U @ 10-20U 0.5U 10-20U (are these just UI restrictions?)
@ -135,7 +129,7 @@ public class InsightPumpPlugin implements PluginBase, PumpInterface, Constraints
} }
public static InsightPumpPlugin getPlugin() { public static InsightPlugin getPlugin() {
if (plugin == null) { if (plugin == null) {
createInstance(); createInstance();
} }
@ -145,7 +139,7 @@ public class InsightPumpPlugin implements PluginBase, PumpInterface, Constraints
private static synchronized void createInstance() { private static synchronized void createInstance() {
if (plugin == null) { if (plugin == null) {
log("creating instance"); log("creating instance");
plugin = new InsightPumpPlugin(); plugin = new InsightPlugin();
} }
} }
@ -156,10 +150,10 @@ public class InsightPumpPlugin implements PluginBase, PumpInterface, Constraints
private static void updateGui() { private static void updateGui() {
update_pending = false; update_pending = false;
MainApp.bus().post(new EventInsightPumpUpdateGui()); MainApp.bus().post(new EventInsightUpdateGui());
} }
private static void pushCallbackEvent(EventInsightPumpCallback e) { private static void pushCallbackEvent(EventInsightCallback e) {
MainApp.bus().post(e); MainApp.bus().post(e);
} }
@ -190,7 +184,7 @@ public class InsightPumpPlugin implements PluginBase, PumpInterface, Constraints
@Override @Override
public String getFragmentClass() { public String getFragmentClass() {
return InsightPumpFragment.class.getName(); return InsightFragment.class.getName();
} }
@Override @Override
@ -237,7 +231,7 @@ public class InsightPumpPlugin implements PluginBase, PumpInterface, Constraints
} }
@Override @Override
public void setFragmentEnabled(int type, boolean fragmentEnabled) { public void setPluginEnabled(int type, boolean fragmentEnabled) {
if (type == PUMP) { if (type == PUMP) {
if (fragmentEnabled) { if (fragmentEnabled) {
enableConnector(); enableConnector();
@ -302,7 +296,7 @@ public class InsightPumpPlugin implements PluginBase, PumpInterface, Constraints
@Override @Override
public void connect(String reason) { public void connect(String reason) {
log("InsightPumpPlugin::connect()"); log("InsightPlugin::connect()");
try { try {
if (!connector.isPumpConnected()) { if (!connector.isPumpConnected()) {
if (Helpers.ratelimit("insight-connect-timer", 40)) { if (Helpers.ratelimit("insight-connect-timer", 40)) {
@ -324,7 +318,7 @@ public class InsightPumpPlugin implements PluginBase, PumpInterface, Constraints
@Override @Override
public void disconnect(String reason) { public void disconnect(String reason) {
log("InsightPumpPlugin::disconnect()"); log("InsightPlugin::disconnect()");
try { try {
if (!SP.getBoolean("insight_always_connected", false)) { if (!SP.getBoolean("insight_always_connected", false)) {
log("Requesting disconnect"); log("Requesting disconnect");
@ -339,7 +333,7 @@ public class InsightPumpPlugin implements PluginBase, PumpInterface, Constraints
@Override @Override
public void stopConnecting() { public void stopConnecting() {
log("InsightPumpPlugin::stopConnecting()"); log("InsightPlugin::stopConnecting()");
try { try {
if (isConnecting()) { if (isConnecting()) {
if (!SP.getBoolean("insight_always_connected", false)) { if (!SP.getBoolean("insight_always_connected", false)) {
@ -367,7 +361,7 @@ public class InsightPumpPlugin implements PluginBase, PumpInterface, Constraints
Mstatus mstatus = async.busyWaitForCommandResult(uuid, BUSY_WAIT_TIME); Mstatus mstatus = async.busyWaitForCommandResult(uuid, BUSY_WAIT_TIME);
if (mstatus.success()) { if (mstatus.success()) {
log("GOT STATUS RESULT!!! PARTY WOOHOO!!!"); log("GOT STATUS RESULT!!! PARTY WOOHOO!!!");
statusResult = (StatusTaskRunner.Result) mstatus.getResponseObject(); setStatusResult((StatusTaskRunner.Result) mstatus.getResponseObject());
statusResultTime = Helpers.tsl(); statusResultTime = Helpers.tsl();
processStatusResult(); processStatusResult();
updateGui(); updateGui();
@ -387,6 +381,10 @@ public class InsightPumpPlugin implements PluginBase, PumpInterface, Constraints
} }
} }
public void setStatusResult(StatusTaskRunner.Result result) {
this.statusResult = result;
}
@Override @Override
public PumpEnactResult setNewBasalProfile(Profile profile) { public PumpEnactResult setNewBasalProfile(Profile profile) {
PumpEnactResult result = new PumpEnactResult(); PumpEnactResult result = new PumpEnactResult();
@ -402,7 +400,8 @@ public class InsightPumpPlugin implements PluginBase, PumpInterface, Constraints
for (int i = 0; i < profile.getBasalValues().length; i++) { for (int i = 0; i < profile.getBasalValues().length; i++) {
Profile.BasalValue basalValue = profile.getBasalValues()[i]; Profile.BasalValue basalValue = profile.getBasalValues()[i];
Profile.BasalValue nextValue = null; Profile.BasalValue nextValue = null;
if (profile.getBasalValues().length > i + 1) nextValue = profile.getBasalValues()[i + 1]; if (profile.getBasalValues().length > i + 1)
nextValue = profile.getBasalValues()[i + 1];
profileBlocks.add(new BRProfileBlock.ProfileBlock((((nextValue != null ? nextValue.timeAsSeconds : 24 * 60 * 60) - basalValue.timeAsSeconds) / 60), Helpers.roundDouble(basalValue.value, 2))); profileBlocks.add(new BRProfileBlock.ProfileBlock((((nextValue != null ? nextValue.timeAsSeconds : 24 * 60 * 60) - basalValue.timeAsSeconds) / 60), Helpers.roundDouble(basalValue.value, 2)));
log("setNewBasalProfile: " + basalValue.value + " for " + Integer.toString(((nextValue != null ? nextValue.timeAsSeconds : 24 * 60 * 60) - basalValue.timeAsSeconds) / 60)); log("setNewBasalProfile: " + basalValue.value + " for " + Integer.toString(((nextValue != null ? nextValue.timeAsSeconds : 24 * 60 * 60) - basalValue.timeAsSeconds) / 60));
} }
@ -432,12 +431,15 @@ public class InsightPumpPlugin implements PluginBase, PumpInterface, Constraints
BRProfileBlock.ProfileBlock profileBlock = profileBlocks.get(i); BRProfileBlock.ProfileBlock profileBlock = profileBlocks.get(i);
Profile.BasalValue basalValue = profile.getBasalValues()[i]; Profile.BasalValue basalValue = profile.getBasalValues()[i];
Profile.BasalValue nextValue = null; Profile.BasalValue nextValue = null;
if (profile.getBasalValues().length > i + 1) nextValue = profile.getBasalValues()[i + 1]; if (profile.getBasalValues().length > i + 1)
nextValue = profile.getBasalValues()[i + 1];
log("isThisProfileSet - Comparing block: Pump: " + profileBlock.getAmount() + " for " + profileBlock.getDuration() log("isThisProfileSet - Comparing block: Pump: " + profileBlock.getAmount() + " for " + profileBlock.getDuration()
+ " Profile: " + basalValue.value + " for " + Integer.toString(((nextValue != null ? nextValue.timeAsSeconds : 24 * 60 * 60) - basalValue.timeAsSeconds) / 60)); + " Profile: " + basalValue.value + " for " + Integer.toString(((nextValue != null ? nextValue.timeAsSeconds : 24 * 60 * 60) - basalValue.timeAsSeconds) / 60));
if (profileBlock.getDuration() * 60 != (nextValue != null ? nextValue.timeAsSeconds : 24 * 60 * 60) - basalValue.timeAsSeconds) return false; if (profileBlock.getDuration() * 60 != (nextValue != null ? nextValue.timeAsSeconds : 24 * 60 * 60) - basalValue.timeAsSeconds)
return false;
//Allow a little imprecision due to rounding errors //Allow a little imprecision due to rounding errors
if (Math.abs(profileBlock.getAmount() - Helpers.roundDouble(basalValue.value, 2)) >= 0.01D) return false; if (Math.abs(profileBlock.getAmount() - Helpers.roundDouble(basalValue.value, 2)) >= 0.01D)
return false;
} }
return true; return true;
} }
@ -524,9 +526,12 @@ public class InsightPumpPlugin implements PluginBase, PumpInterface, Constraints
final EventOverviewBolusProgress bolusingEvent = EventOverviewBolusProgress.getInstance(); final EventOverviewBolusProgress bolusingEvent = EventOverviewBolusProgress.getInstance();
ActiveBolusesMessage activeBolusesMessage = (ActiveBolusesMessage) mstatus.getResponseObject(); ActiveBolusesMessage activeBolusesMessage = (ActiveBolusesMessage) mstatus.getResponseObject();
ActiveBolus activeBolus = null; ActiveBolus activeBolus = null;
if (activeBolusesMessage.getBolus1() != null && activeBolusesMessage.getBolus1().getBolusID() == bolusingEvent.bolusId) activeBolus = activeBolusesMessage.getBolus1(); if (activeBolusesMessage.getBolus1() != null && activeBolusesMessage.getBolus1().getBolusID() == bolusingEvent.bolusId)
else if (activeBolusesMessage.getBolus2() != null && activeBolusesMessage.getBolus2().getBolusID() == bolusingEvent.bolusId) activeBolus = activeBolusesMessage.getBolus2(); activeBolus = activeBolusesMessage.getBolus1();
else if (activeBolusesMessage.getBolus3() != null && activeBolusesMessage.getBolus3().getBolusID() == bolusingEvent.bolusId) activeBolus = activeBolusesMessage.getBolus3(); else if (activeBolusesMessage.getBolus2() != null && activeBolusesMessage.getBolus2().getBolusID() == bolusingEvent.bolusId)
activeBolus = activeBolusesMessage.getBolus2();
else if (activeBolusesMessage.getBolus3() != null && activeBolusesMessage.getBolus3().getBolusID() == bolusingEvent.bolusId)
activeBolus = activeBolusesMessage.getBolus3();
if (activeBolus == null) break; if (activeBolus == null) break;
else { else {
bolusingEvent.percent = (int) (100D / activeBolus.getInitialAmount() * (activeBolus.getInitialAmount() - activeBolus.getLeftoverAmount())); bolusingEvent.percent = (int) (100D / activeBolus.getInitialAmount() * (activeBolus.getInitialAmount() - activeBolus.getLeftoverAmount()));
@ -555,7 +560,7 @@ public class InsightPumpPlugin implements PluginBase, PumpInterface, Constraints
// Temporary Basals // Temporary Basals
@Override @Override
public PumpEnactResult setTempBasalAbsolute(Double absoluteRate, Integer durationInMinutes, boolean enforceNew) { public PumpEnactResult setTempBasalAbsolute(Double absoluteRate, Integer durationInMinutes, Profile profile, boolean enforceNew) {
absoluteRate = Helpers.roundDouble(absoluteRate, 3); absoluteRate = Helpers.roundDouble(absoluteRate, 3);
log("Set TBR absolute: " + absoluteRate); log("Set TBR absolute: " + absoluteRate);
final double base_basal = getBaseBasalRate(); final double base_basal = getBaseBasalRate();
@ -575,7 +580,6 @@ public class InsightPumpPlugin implements PluginBase, PumpInterface, Constraints
if (percent_amount > 250) percent_amount = 250; if (percent_amount > 250) percent_amount = 250;
final SetTBRTaskRunner task = new SetTBRTaskRunner(connector.getServiceConnector(), percent_amount, durationInMinutes); final SetTBRTaskRunner task = new SetTBRTaskRunner(connector.getServiceConnector(), percent_amount, durationInMinutes);
final UUID cmd = aSyncTaskRunner(task, "Set TBR abs: " + absoluteRate + " " + durationInMinutes + "m"); final UUID cmd = aSyncTaskRunner(task, "Set TBR abs: " + absoluteRate + " " + durationInMinutes + "m");
@ -619,7 +623,7 @@ public class InsightPumpPlugin implements PluginBase, PumpInterface, Constraints
@Override @Override
public PumpEnactResult setTempBasalPercent(Integer percent, Integer durationInMinutes, boolean enforceNew) { public PumpEnactResult setTempBasalPercent(Integer percent, Integer durationInMinutes, Profile profile, boolean enforceNew) {
log("Set TBR %"); log("Set TBR %");
percent = (int) Math.round(((double) percent) / 10d) * 10; percent = (int) Math.round(((double) percent) / 10d) * 10;
@ -1014,7 +1018,7 @@ public class InsightPumpPlugin implements PluginBase, PumpInterface, Constraints
// if (!isConnected()) return false; // if (!isConnected()) return false;
//if (isBusy()) return false; //if (isBusy()) return false;
log("asyncSinglecommand called: " + name); log("asyncSinglecommand called: " + name);
final EventInsightPumpCallback event = new EventInsightPumpCallback(); final EventInsightCallback event = new EventInsightCallback();
new Thread() { new Thread() {
@Override @Override
public void run() { public void run() {
@ -1053,7 +1057,7 @@ public class InsightPumpPlugin implements PluginBase, PumpInterface, Constraints
// if (!isConnected()) return false; // if (!isConnected()) return false;
//if (isBusy()) return false; //if (isBusy()) return false;
log("asyncTaskRunner called: " + name); log("asyncTaskRunner called: " + name);
final EventInsightPumpCallback event = new EventInsightPumpCallback(); final EventInsightCallback event = new EventInsightCallback();
new Thread() { new Thread() {
@Override @Override
public void run() { public void run() {
@ -1092,54 +1096,26 @@ public class InsightPumpPlugin implements PluginBase, PumpInterface, Constraints
// Constraints // Constraints
@Override @Override
public boolean isLoopEnabled() { public Constraint<Double> applyBasalConstraints(Constraint<Double> absoluteRate, Profile profile) {
return true; if (statusResult != null) {
absoluteRate.setIfSmaller(statusResult.maximumBasalAmount, String.format(MainApp.gs(R.string.limitingbasalratio), statusResult.maximumBasalAmount, MainApp.gs(R.string.pumplimit)), this);
}
return absoluteRate;
} }
@Override @Override
public boolean isClosedModeEnabled() { public Constraint<Integer> applyBasalPercentConstraints(Constraint<Integer> percentRate, Profile profile) {
return true; percentRate.setIfGreater(0, String.format(MainApp.gs(R.string.limitingpercentrate), 0, MainApp.gs(R.string.itmustbepositivevalue)), this);
percentRate.setIfSmaller(getPumpDescription().maxTempPercent, String.format(MainApp.gs(R.string.limitingpercentrate), getPumpDescription().maxTempPercent, MainApp.gs(R.string.pumplimit)), this);
return percentRate;
} }
@Override @Override
public boolean isAutosensModeEnabled() { public Constraint<Double> applyBolusConstraints(Constraint<Double> insulin) {
return true; if (statusResult != null)
insulin.setIfSmaller(statusResult.maximumBolusAmount, String.format(MainApp.gs(R.string.limitingbolus), statusResult.maximumBolusAmount, MainApp.gs(R.string.pumplimit)), this);
return insulin;
} }
@Override
public boolean isAMAModeEnabled() {
return true;
}
@Override
public boolean isSMBModeEnabled() {
return true;
}
@Override
public Double applyBasalConstraints(Double absoluteRate) {
return Math.min(absoluteRate, statusResult != null ? statusResult.maximumBasalAmount : 0);
}
@Override
public Integer applyBasalConstraints(Integer percentRate) {
return Math.min(percentRate, pumpDescription.maxTempPercent);
}
@Override
public Double applyBolusConstraints(Double insulin) {
return Math.min(insulin, statusResult != null ? statusResult.maximumBolusAmount : 0);
}
@Override
public Integer applyCarbsConstraints(Integer carbs) {
return carbs;
}
@Override
public Double applyMaxIOBConstraints(Double maxIob) {
return maxIob;
}
} }

View file

@ -1,6 +1,6 @@
package info.nightscout.androidaps.plugins.PumpInsight; package info.nightscout.androidaps.plugins.PumpInsight;
import info.nightscout.androidaps.plugins.PumpInsight.events.EventInsightPumpCallback; import info.nightscout.androidaps.plugins.PumpInsight.events.EventInsightCallback;
/** /**
* Created by jamorham on 01/02/2018. * Created by jamorham on 01/02/2018.
@ -11,7 +11,7 @@ import info.nightscout.androidaps.plugins.PumpInsight.events.EventInsightPumpCal
class Mstatus { class Mstatus {
Cstatus cstatus = Cstatus.UNKNOWN; Cstatus cstatus = Cstatus.UNKNOWN;
EventInsightPumpCallback event; EventInsightCallback event;
// comment field preparation for results // comment field preparation for results
String getCommandComment() { String getCommandComment() {

View file

@ -14,7 +14,7 @@ import java.util.Map;
import info.nightscout.androidaps.MainApp; import info.nightscout.androidaps.MainApp;
import info.nightscout.androidaps.R; import info.nightscout.androidaps.R;
import info.nightscout.androidaps.events.EventFeatureRunning; import info.nightscout.androidaps.events.EventFeatureRunning;
import info.nightscout.androidaps.plugins.PumpInsight.events.EventInsightPumpUpdateGui; import info.nightscout.androidaps.plugins.PumpInsight.events.EventInsightUpdateGui;
import info.nightscout.androidaps.plugins.PumpInsight.history.HistoryReceiver; import info.nightscout.androidaps.plugins.PumpInsight.history.HistoryReceiver;
import info.nightscout.androidaps.plugins.PumpInsight.history.LiveHistory; import info.nightscout.androidaps.plugins.PumpInsight.history.LiveHistory;
import info.nightscout.androidaps.plugins.PumpInsight.utils.Helpers; import info.nightscout.androidaps.plugins.PumpInsight.utils.Helpers;
@ -76,7 +76,7 @@ public class Connector {
extendKeepAliveIfActive(); extendKeepAliveIfActive();
} }
MainApp.bus().post(new EventInsightPumpUpdateGui()); MainApp.bus().post(new EventInsightUpdateGui());
} else { } else {
log("Same status as before: " + status); log("Same status as before: " + status);
} }

View file

@ -7,7 +7,7 @@ import info.nightscout.androidaps.events.Event;
/** /**
* Created by jamorham on 23/01/2018. * Created by jamorham on 23/01/2018.
*/ */
public class EventInsightPumpCallback extends Event { public class EventInsightCallback extends Event {
public UUID request_uuid; public UUID request_uuid;
public boolean success = false; public boolean success = false;
@ -15,7 +15,7 @@ public class EventInsightPumpCallback extends Event {
public int response_id = -1; public int response_id = -1;
public Object response_object = null; public Object response_object = null;
public EventInsightPumpCallback() { public EventInsightCallback() {
request_uuid = UUID.randomUUID(); request_uuid = UUID.randomUUID();
} }

View file

@ -5,5 +5,5 @@ import info.nightscout.androidaps.events.EventUpdateGui;
/** /**
* Created by jamorham on 23/01/2018. * Created by jamorham on 23/01/2018.
*/ */
public class EventInsightPumpUpdateGui extends EventUpdateGui { public class EventInsightUpdateGui extends EventUpdateGui {
} }

View file

@ -90,7 +90,7 @@ public class MDIPlugin implements PluginBase, PumpInterface {
} }
@Override @Override
public void setFragmentEnabled(int type, boolean fragmentEnabled) { public void setPluginEnabled(int type, boolean fragmentEnabled) {
if (type == PUMP) this.fragmentEnabled = fragmentEnabled; if (type == PUMP) this.fragmentEnabled = fragmentEnabled;
} }
@ -201,7 +201,7 @@ public class MDIPlugin implements PluginBase, PumpInterface {
} }
@Override @Override
public PumpEnactResult setTempBasalAbsolute(Double absoluteRate, Integer durationInMinutes, boolean enforceNew) { public PumpEnactResult setTempBasalAbsolute(Double absoluteRate, Integer durationInMinutes, Profile profile, boolean enforceNew) {
PumpEnactResult result = new PumpEnactResult(); PumpEnactResult result = new PumpEnactResult();
result.success = false; result.success = false;
result.comment = MainApp.instance().getString(R.string.pumperror); result.comment = MainApp.instance().getString(R.string.pumperror);
@ -211,7 +211,7 @@ public class MDIPlugin implements PluginBase, PumpInterface {
} }
@Override @Override
public PumpEnactResult setTempBasalPercent(Integer percent, Integer durationInMinutes, boolean enforceNew) { public PumpEnactResult setTempBasalPercent(Integer percent, Integer durationInMinutes, Profile profile, boolean enforceNew) {
PumpEnactResult result = new PumpEnactResult(); PumpEnactResult result = new PumpEnactResult();
result.success = false; result.success = false;
result.comment = MainApp.instance().getString(R.string.pumperror); result.comment = MainApp.instance().getString(R.string.pumperror);

View file

@ -98,7 +98,7 @@ public class VirtualPumpPlugin implements PluginBase, PumpInterface {
pumpDescription.basalStep = 0.01d; pumpDescription.basalStep = 0.01d;
pumpDescription.basalMinimumRate = 0.01d; pumpDescription.basalMinimumRate = 0.01d;
pumpDescription.isRefillingCapable = false; pumpDescription.isRefillingCapable = true;
pumpDescription.storesCarbInfo = false; pumpDescription.storesCarbInfo = false;
pumpDescription.is30minBasalRatesCapable = true; pumpDescription.is30minBasalRatesCapable = true;
@ -151,7 +151,7 @@ public class VirtualPumpPlugin implements PluginBase, PumpInterface {
} }
@Override @Override
public void setFragmentEnabled(int type, boolean fragmentEnabled) { public void setPluginEnabled(int type, boolean fragmentEnabled) {
if (type == PUMP) this.fragmentEnabled = fragmentEnabled; if (type == PUMP) this.fragmentEnabled = fragmentEnabled;
} }
@ -296,7 +296,7 @@ public class VirtualPumpPlugin implements PluginBase, PumpInterface {
} }
@Override @Override
public PumpEnactResult setTempBasalAbsolute(Double absoluteRate, Integer durationInMinutes, boolean enforceNew) { public PumpEnactResult setTempBasalAbsolute(Double absoluteRate, Integer durationInMinutes, Profile profile, boolean enforceNew) {
TreatmentsInterface treatmentsInterface = MainApp.getConfigBuilder(); TreatmentsInterface treatmentsInterface = MainApp.getConfigBuilder();
TemporaryBasal tempBasal = new TemporaryBasal(); TemporaryBasal tempBasal = new TemporaryBasal();
tempBasal.date = System.currentTimeMillis(); tempBasal.date = System.currentTimeMillis();
@ -320,7 +320,7 @@ public class VirtualPumpPlugin implements PluginBase, PumpInterface {
} }
@Override @Override
public PumpEnactResult setTempBasalPercent(Integer percent, Integer durationInMinutes, boolean enforceNew) { public PumpEnactResult setTempBasalPercent(Integer percent, Integer durationInMinutes, Profile profile, boolean enforceNew) {
TreatmentsInterface treatmentsInterface = MainApp.getConfigBuilder(); TreatmentsInterface treatmentsInterface = MainApp.getConfigBuilder();
PumpEnactResult result = new PumpEnactResult(); PumpEnactResult result = new PumpEnactResult();
if (MainApp.getConfigBuilder().isTempBasalInProgress()) { if (MainApp.getConfigBuilder().isTempBasalInProgress()) {

View file

@ -88,7 +88,7 @@ public class SensitivityAAPSPlugin implements PluginBase, SensitivityInterface{
} }
@Override @Override
public void setFragmentEnabled(int type, boolean fragmentEnabled) { public void setPluginEnabled(int type, boolean fragmentEnabled) {
if (type == SENSITIVITY) this.fragmentEnabled = fragmentEnabled; if (type == SENSITIVITY) this.fragmentEnabled = fragmentEnabled;
} }

View file

@ -87,7 +87,7 @@ public class SensitivityOref0Plugin implements PluginBase, SensitivityInterface
} }
@Override @Override
public void setFragmentEnabled(int type, boolean fragmentEnabled) { public void setPluginEnabled(int type, boolean fragmentEnabled) {
if (type == SENSITIVITY) this.fragmentEnabled = fragmentEnabled; if (type == SENSITIVITY) this.fragmentEnabled = fragmentEnabled;
} }

View file

@ -84,7 +84,7 @@ public class SensitivityWeightedAveragePlugin implements PluginBase, Sensitivity
} }
@Override @Override
public void setFragmentEnabled(int type, boolean fragmentEnabled) { public void setPluginEnabled(int type, boolean fragmentEnabled) {
if (type == SENSITIVITY) this.fragmentEnabled = fragmentEnabled; if (type == SENSITIVITY) this.fragmentEnabled = fragmentEnabled;
} }

View file

@ -29,11 +29,12 @@ import info.nightscout.androidaps.db.DatabaseHelper;
import info.nightscout.androidaps.db.Source; import info.nightscout.androidaps.db.Source;
import info.nightscout.androidaps.events.EventPreferenceChange; import info.nightscout.androidaps.events.EventPreferenceChange;
import info.nightscout.androidaps.events.EventRefreshOverview; import info.nightscout.androidaps.events.EventRefreshOverview;
import info.nightscout.androidaps.interfaces.Constraint;
import info.nightscout.androidaps.interfaces.PluginBase; import info.nightscout.androidaps.interfaces.PluginBase;
import info.nightscout.androidaps.plugins.ConfigBuilder.ConfigBuilderPlugin; import info.nightscout.androidaps.plugins.ConfigBuilder.ConfigBuilderPlugin;
import info.nightscout.androidaps.plugins.Loop.LoopPlugin; import info.nightscout.androidaps.plugins.Loop.LoopPlugin;
import info.nightscout.androidaps.plugins.Overview.notifications.Notification;
import info.nightscout.androidaps.plugins.Overview.events.EventNewNotification; import info.nightscout.androidaps.plugins.Overview.events.EventNewNotification;
import info.nightscout.androidaps.plugins.Overview.notifications.Notification;
import info.nightscout.androidaps.plugins.PumpDanaR.DanaRPlugin; import info.nightscout.androidaps.plugins.PumpDanaR.DanaRPlugin;
import info.nightscout.androidaps.plugins.PumpDanaRKorean.DanaRKoreanPlugin; import info.nightscout.androidaps.plugins.PumpDanaRKorean.DanaRKoreanPlugin;
import info.nightscout.androidaps.plugins.SmsCommunicator.events.EventNewSMS; import info.nightscout.androidaps.plugins.SmsCommunicator.events.EventNewSMS;
@ -176,7 +177,7 @@ public class SmsCommunicatorPlugin implements PluginBase {
} }
@Override @Override
public void setFragmentEnabled(int type, boolean fragmentEnabled) { public void setPluginEnabled(int type, boolean fragmentEnabled) {
if (type == GENERAL) this.fragmentEnabled = fragmentEnabled; if (type == GENERAL) this.fragmentEnabled = fragmentEnabled;
} }
@ -285,7 +286,7 @@ public class SmsCommunicatorPlugin implements PluginBase {
case "STOP": case "STOP":
LoopPlugin loopPlugin = MainApp.getSpecificPlugin(LoopPlugin.class); LoopPlugin loopPlugin = MainApp.getSpecificPlugin(LoopPlugin.class);
if (loopPlugin != null && loopPlugin.isEnabled(PluginBase.LOOP)) { if (loopPlugin != null && loopPlugin.isEnabled(PluginBase.LOOP)) {
loopPlugin.setFragmentEnabled(PluginBase.LOOP, false); loopPlugin.setPluginEnabled(PluginBase.LOOP, false);
ConfigBuilderPlugin.getCommandQueue().cancelTempBasal(true, new Callback() { ConfigBuilderPlugin.getCommandQueue().cancelTempBasal(true, new Callback() {
@Override @Override
public void run() { public void run() {
@ -303,7 +304,7 @@ public class SmsCommunicatorPlugin implements PluginBase {
case "START": case "START":
loopPlugin = MainApp.getSpecificPlugin(LoopPlugin.class); loopPlugin = MainApp.getSpecificPlugin(LoopPlugin.class);
if (loopPlugin != null && !loopPlugin.isEnabled(PluginBase.LOOP)) { if (loopPlugin != null && !loopPlugin.isEnabled(PluginBase.LOOP)) {
loopPlugin.setFragmentEnabled(PluginBase.LOOP, true); loopPlugin.setPluginEnabled(PluginBase.LOOP, true);
reply = MainApp.sResources.getString(R.string.smscommunicator_loophasbeenenabled); reply = MainApp.sResources.getString(R.string.smscommunicator_loophasbeenenabled);
sendSMS(new Sms(receivedSms.phoneNumber, reply, new Date())); sendSMS(new Sms(receivedSms.phoneNumber, reply, new Date()));
MainApp.bus().post(new EventRefreshOverview("SMS_LOOP_START")); MainApp.bus().post(new EventRefreshOverview("SMS_LOOP_START"));
@ -418,18 +419,24 @@ public class SmsCommunicatorPlugin implements PluginBase {
} }
} else { } else {
tempBasal = SafeParse.stringToDouble(splited[1]); tempBasal = SafeParse.stringToDouble(splited[1]);
tempBasal = MainApp.getConfigBuilder().applyBasalConstraints(tempBasal); Profile profile = MainApp.getConfigBuilder().getProfile();
if (remoteCommandsAllowed) { if (profile == null) {
passCode = generatePasscode(); reply = MainApp.sResources.getString(R.string.noprofile);
reply = String.format(MainApp.sResources.getString(R.string.smscommunicator_basalreplywithcode), tempBasal, passCode);
receivedSms.processed = true;
resetWaitingMessages();
sendSMS(tempBasalWaitingForConfirmation = new Sms(receivedSms.phoneNumber, reply, new Date(), passCode));
tempBasalWaitingForConfirmation.tempBasal = tempBasal;
FabricPrivacy.getInstance().logCustom(new CustomEvent("SMS_Basal"));
} else {
reply = MainApp.sResources.getString(R.string.smscommunicator_remotebasalnotallowed);
sendSMS(new Sms(receivedSms.phoneNumber, reply, new Date())); sendSMS(new Sms(receivedSms.phoneNumber, reply, new Date()));
} else {
tempBasal = MainApp.getConstraintChecker().applyBasalConstraints(new Constraint<>(tempBasal), profile).value();
if (remoteCommandsAllowed) {
passCode = generatePasscode();
reply = String.format(MainApp.sResources.getString(R.string.smscommunicator_basalreplywithcode), tempBasal, passCode);
receivedSms.processed = true;
resetWaitingMessages();
sendSMS(tempBasalWaitingForConfirmation = new Sms(receivedSms.phoneNumber, reply, new Date(), passCode));
tempBasalWaitingForConfirmation.tempBasal = tempBasal;
FabricPrivacy.getInstance().logCustom(new CustomEvent("SMS_Basal"));
} else {
reply = MainApp.sResources.getString(R.string.smscommunicator_remotebasalnotallowed);
sendSMS(new Sms(receivedSms.phoneNumber, reply, new Date()));
}
} }
} }
} }
@ -443,7 +450,7 @@ public class SmsCommunicatorPlugin implements PluginBase {
sendSMS(new Sms(receivedSms.phoneNumber, reply, new Date())); sendSMS(new Sms(receivedSms.phoneNumber, reply, new Date()));
} else if (splited.length > 1) { } else if (splited.length > 1) {
amount = SafeParse.stringToDouble(splited[1]); amount = SafeParse.stringToDouble(splited[1]);
amount = MainApp.getConfigBuilder().applyBolusConstraints(amount); amount = MainApp.getConstraintChecker().applyBolusConstraints(new Constraint<>(amount)).value();
if (amount > 0d && remoteCommandsAllowed) { if (amount > 0d && remoteCommandsAllowed) {
passCode = generatePasscode(); passCode = generatePasscode();
reply = String.format(MainApp.sResources.getString(R.string.smscommunicator_bolusreplywithcode), amount, passCode); reply = String.format(MainApp.sResources.getString(R.string.smscommunicator_bolusreplywithcode), amount, passCode);
@ -503,20 +510,22 @@ public class SmsCommunicatorPlugin implements PluginBase {
} else if (tempBasalWaitingForConfirmation != null && !tempBasalWaitingForConfirmation.processed && } else if (tempBasalWaitingForConfirmation != null && !tempBasalWaitingForConfirmation.processed &&
tempBasalWaitingForConfirmation.confirmCode.equals(splited[0]) && System.currentTimeMillis() - tempBasalWaitingForConfirmation.date.getTime() < CONFIRM_TIMEOUT) { tempBasalWaitingForConfirmation.confirmCode.equals(splited[0]) && System.currentTimeMillis() - tempBasalWaitingForConfirmation.date.getTime() < CONFIRM_TIMEOUT) {
tempBasalWaitingForConfirmation.processed = true; tempBasalWaitingForConfirmation.processed = true;
ConfigBuilderPlugin.getCommandQueue().tempBasalAbsolute(tempBasalWaitingForConfirmation.tempBasal, 30, true, new Callback() { Profile profile = MainApp.getConfigBuilder().getProfile();
@Override if (profile != null)
public void run() { ConfigBuilderPlugin.getCommandQueue().tempBasalAbsolute(tempBasalWaitingForConfirmation.tempBasal, 30, true, profile, new Callback() {
if (result.success) { @Override
String reply = String.format(MainApp.sResources.getString(R.string.smscommunicator_tempbasalset), result.absolute, result.duration); public void run() {
reply += "\n" + ConfigBuilderPlugin.getActivePump().shortStatus(true); if (result.success) {
sendSMSToAllNumbers(new Sms(receivedSms.phoneNumber, reply, new Date())); String reply = String.format(MainApp.sResources.getString(R.string.smscommunicator_tempbasalset), result.absolute, result.duration);
} else { reply += "\n" + ConfigBuilderPlugin.getActivePump().shortStatus(true);
String reply = MainApp.sResources.getString(R.string.smscommunicator_tempbasalfailed); sendSMSToAllNumbers(new Sms(receivedSms.phoneNumber, reply, new Date()));
reply += "\n" + ConfigBuilderPlugin.getActivePump().shortStatus(true); } else {
sendSMS(new Sms(receivedSms.phoneNumber, reply, new Date())); String reply = MainApp.sResources.getString(R.string.smscommunicator_tempbasalfailed);
reply += "\n" + ConfigBuilderPlugin.getActivePump().shortStatus(true);
sendSMS(new Sms(receivedSms.phoneNumber, reply, new Date()));
}
} }
} });
});
} else if (cancelTempBasalWaitingForConfirmation != null && !cancelTempBasalWaitingForConfirmation.processed && } else if (cancelTempBasalWaitingForConfirmation != null && !cancelTempBasalWaitingForConfirmation.processed &&
cancelTempBasalWaitingForConfirmation.confirmCode.equals(splited[0]) && System.currentTimeMillis() - cancelTempBasalWaitingForConfirmation.date.getTime() < CONFIRM_TIMEOUT) { cancelTempBasalWaitingForConfirmation.confirmCode.equals(splited[0]) && System.currentTimeMillis() - cancelTempBasalWaitingForConfirmation.date.getTime() < CONFIRM_TIMEOUT) {
cancelTempBasalWaitingForConfirmation.processed = true; cancelTempBasalWaitingForConfirmation.processed = true;

View file

@ -68,7 +68,7 @@ public class SourceDexcomG5Plugin implements PluginBase, BgSourceInterface {
} }
@Override @Override
public void setFragmentEnabled(int type, boolean fragmentEnabled) { public void setPluginEnabled(int type, boolean fragmentEnabled) {
if (type == BGSOURCE) this.fragmentEnabled = fragmentEnabled; if (type == BGSOURCE) this.fragmentEnabled = fragmentEnabled;
} }

View file

@ -68,7 +68,7 @@ public class SourceGlimpPlugin implements PluginBase, BgSourceInterface {
} }
@Override @Override
public void setFragmentEnabled(int type, boolean fragmentEnabled) { public void setPluginEnabled(int type, boolean fragmentEnabled) {
if (type == BGSOURCE) this.fragmentEnabled = fragmentEnabled; if (type == BGSOURCE) this.fragmentEnabled = fragmentEnabled;
} }

View file

@ -68,7 +68,7 @@ public class SourceMM640gPlugin implements PluginBase, BgSourceInterface {
} }
@Override @Override
public void setFragmentEnabled(int type, boolean fragmentEnabled) { public void setPluginEnabled(int type, boolean fragmentEnabled) {
if (type == BGSOURCE) this.fragmentEnabled = fragmentEnabled; if (type == BGSOURCE) this.fragmentEnabled = fragmentEnabled;
} }

View file

@ -70,7 +70,7 @@ public class SourceNSClientPlugin implements PluginBase, BgSourceInterface {
} }
@Override @Override
public void setFragmentEnabled(int type, boolean fragmentEnabled) { public void setPluginEnabled(int type, boolean fragmentEnabled) {
if (type == BGSOURCE) this.fragmentEnabled = fragmentEnabled; if (type == BGSOURCE) this.fragmentEnabled = fragmentEnabled;
} }

View file

@ -69,7 +69,7 @@ public class SourceXdripPlugin implements PluginBase, BgSourceInterface {
} }
@Override @Override
public void setFragmentEnabled(int type, boolean fragmentEnabled) { public void setPluginEnabled(int type, boolean fragmentEnabled) {
if (type == BGSOURCE) this.fragmentEnabled = fragmentEnabled; if (type == BGSOURCE) this.fragmentEnabled = fragmentEnabled;
} }

Some files were not shown because too many files have changed in this diff Show more