Search in sources :

Example 31 with BgReading

use of com.eveningoutpost.dexdrip.Models.BgReading in project xDrip-plus by jamorham.

the class ListenerService method resetDataToLatest.

private boolean resetDataToLatest(DataMap dataMap, Context context) {
    // KS
    if (dataMap != null) {
        Double dmTimestamp = dataMap.getDouble("timestamp");
        Log.d(TAG, "resetDataToLatest dataMap.datetime=" + JoH.dateTimeText(dmTimestamp.longValue()) + " dataMap.sgvDouble=" + dataMap.getDouble("sgvDouble"));
        // ensure database has already been initialized
        Sensor.InitDb(context);
        final BgReading last = BgReading.last();
        if (last != null) {
            long bgTimestamp = last.timestamp;
            Log.d(TAG, "resetDataToLatest last.timestamp=" + JoH.dateTimeText(bgTimestamp) + " last.calculated_value=" + last.calculated_value);
            if (bgTimestamp > dmTimestamp) {
                dataMap(dataMap, last, mPrefs, new com.eveningoutpost.dexdrip.UtilityModels.BgGraphBuilder(context));
                return true;
            }
        }
    }
    return false;
}
Also used : BgReading(com.eveningoutpost.dexdrip.Models.BgReading)

Example 32 with BgReading

use of com.eveningoutpost.dexdrip.Models.BgReading in project xDrip-plus by jamorham.

the class ListenerService method syncBgData.

private synchronized void syncBgData(DataMap dataMap, Context context) {
    // KS
    Log.d(TAG, "syncBGData");
    boolean changed = false;
    int battery = dataMap.getInt("battery");
    ArrayList<DataMap> entries = dataMap.getDataMapArrayList("entries");
    Log.d(TAG, "syncBGData add BgReading Table battery=" + battery);
    if (entries != null) {
        Gson gson = new GsonBuilder().excludeFieldsWithoutExposeAnnotation().registerTypeAdapter(Date.class, new DateTypeAdapter()).serializeSpecialFloatingPointValues().create();
        Log.d(TAG, "syncBGData add BgReading Table entries count=" + entries.size());
        // ensure database has already been initialized
        Sensor.InitDb(context);
        Sensor sensor = Sensor.currentSensor();
        if (sensor != null) {
            for (DataMap entry : entries) {
                if (entry != null) {
                    String bgrecord = entry.getString("bgs");
                    if (bgrecord != null) {
                        BgReading bgData = gson.fromJson(bgrecord, BgReading.class);
                        /*    // TODO this is a hack to use display glucose but it is incomplete regarding delta
                            if (bgData.dg_mgdl > 0) {
                                bgData.calculated_value = bgData.dg_mgdl;
                                bgData.calculated_value_slope = bgData.dg_slope;
                                // TODO delta missing???
                            }
*/
                        BgReading exists = BgReading.getForTimestampExists(bgData.timestamp);
                        exists = exists != null ? exists : BgReading.findByUuid(bgData.uuid);
                        String calibrationUuid = entry.getString("calibrationUuid");
                        if (exists != null) {
                            Log.d(TAG, "syncBGData BG already exists for uuid=" + bgData.uuid + " timestamp=" + bgData.timestamp + " timeString=" + JoH.dateTimeText(bgData.timestamp));
                            Log.d(TAG, "syncBGData exists timeString=" + JoH.dateTimeText(exists.timestamp) + "  exists.calibration.uuid=" + exists.calibration.uuid + " exists=" + exists.toS());
                            exists.filtered_calculated_value = bgData.filtered_calculated_value;
                            exists.calculated_value = bgData.calculated_value;
                            exists.hide_slope = bgData.hide_slope;
                            exists.filtered_data = bgData.filtered_data;
                            exists.raw_data = bgData.raw_data;
                            exists.raw_calculated = bgData.raw_calculated;
                            exists.calculated_value_slope = bgData.calculated_value_slope;
                            exists.age_adjusted_raw_value = bgData.age_adjusted_raw_value;
                            exists.calibration_flag = bgData.calibration_flag;
                            exists.ignoreForStats = bgData.ignoreForStats;
                            exists.time_since_sensor_started = bgData.time_since_sensor_started;
                            exists.ra = bgData.ra;
                            exists.rb = bgData.rb;
                            exists.rc = bgData.rc;
                            exists.a = bgData.a;
                            exists.b = bgData.b;
                            exists.c = bgData.c;
                            exists.noise = bgData.noise;
                            exists.time_since_sensor_started = bgData.time_since_sensor_started;
                            Calibration calibration = Calibration.byuuid(calibrationUuid);
                            calibration = calibration != null ? calibration : Calibration.byuuid(exists.calibration_uuid);
                            if (calibration != null) {
                                exists.calibration = calibration;
                                exists.calibration_uuid = calibration.uuid;
                                exists.sensor = sensor;
                                exists.sensor_uuid = sensor.uuid;
                                if (exists.calculated_value != bgData.calculated_value) {
                                    changed = true;
                                }
                                exists.save();
                            } else {
                                Log.e(TAG, "syncBGData existing BgReading calibrationUuid not found by byuuid; calibrationUuid=" + calibrationUuid + " bgData.calibration_uuid=" + bgData.calibration_uuid + " bgData.uuid=" + bgData.uuid + " timeString=" + JoH.dateTimeText(bgData.timestamp));
                            }
                        } else {
                            Calibration calibration = Calibration.byuuid(calibrationUuid);
                            calibration = calibration != null ? calibration : Calibration.byuuid(bgData.calibration_uuid);
                            if (calibration != null) {
                                Log.d(TAG, "syncBGData add BG; does NOT exist for uuid=" + bgData.uuid + " timestamp=" + bgData.timestamp + " timeString=" + JoH.dateTimeText(bgData.timestamp));
                                bgData.calibration = calibration;
                                bgData.calibration_uuid = calibration.uuid;
                                bgData.sensor = sensor;
                                bgData.sensor_uuid = sensor.uuid;
                                changed = true;
                                bgData.save();
                            } else {
                                Log.e(TAG, "syncBGData new BgReading calibrationUuid not found by byuuid; calibrationUuid=" + calibrationUuid + " bgData.calibration_uuid=" + bgData.calibration_uuid + " bgData.uuid=" + bgData.uuid + " timeString=" + JoH.dateTimeText(bgData.timestamp));
                            }
                        }
                    }
                }
            }
        } else {
            Log.d(TAG, "syncBGData No Active Sensor!! Request WEARABLE_INITDB_PATH");
            sendData(WEARABLE_INITDB_PATH, null);
        }
    }
    if (changed) {
        // otherwise, wait for doBackground ACTION_RESEND
        Log.d(TAG, "syncBGData BG data has changed, refresh watchface, phone battery=" + battery);
        resendData(getApplicationContext(), battery);
        CustomComplicationProviderService.refresh();
    } else
        Log.d(TAG, "syncBGData BG data has NOT changed, do not refresh watchface, phone battery=" + battery);
}
Also used : DateTypeAdapter(com.google.gson.internal.bind.DateTypeAdapter) GsonBuilder(com.google.gson.GsonBuilder) Gson(com.google.gson.Gson) BgReading(com.eveningoutpost.dexdrip.Models.BgReading) Calibration(com.eveningoutpost.dexdrip.Models.Calibration) DataMap(com.google.android.gms.wearable.DataMap) Sensor(com.eveningoutpost.dexdrip.Models.Sensor)

Example 33 with BgReading

use of com.eveningoutpost.dexdrip.Models.BgReading in project xDrip-plus by jamorham.

the class xDripWidget method displayCurrentInfo.

private static void displayCurrentInfo(AppWidgetManager appWidgetManager, int appWidgetId, Context context, RemoteViews views) {
    BgGraphBuilder bgGraphBuilder = new BgGraphBuilder(context);
    BgReading lastBgreading = BgReading.lastNoSenssor();
    final boolean showLines = Pref.getBoolean("widget_range_lines", false);
    final boolean showExstraStatus = Pref.getBoolean("extra_status_line", false) && Pref.getBoolean("widget_status_line", false);
    if (lastBgreading != null) {
        double estimate = 0;
        double estimated_delta = -9999;
        try {
            int height = appWidgetManager.getAppWidgetOptions(appWidgetId).getInt(AppWidgetManager.OPTION_APPWIDGET_MAX_HEIGHT);
            int width = appWidgetManager.getAppWidgetOptions(appWidgetId).getInt(AppWidgetManager.OPTION_APPWIDGET_MAX_WIDTH);
            views.setImageViewBitmap(R.id.widgetGraph, new BgSparklineBuilder(context).setBgGraphBuilder(bgGraphBuilder).setBackgroundColor(ColorCache.getCol(ColorCache.X.color_widget_chart_background)).setHeight(height).setWidth(width).showHighLine(showLines).showLowLine(showLines).build());
            final BestGlucose.DisplayGlucose dg = (use_best_glucose) ? BestGlucose.getDisplayGlucose() : null;
            estimate = (dg != null) ? dg.mgdl : lastBgreading.calculated_value;
            String extrastring = "";
            String slope_arrow = (dg != null) ? dg.delta_arrow : lastBgreading.slopeArrow();
            String stringEstimate;
            if (dg == null) {
                // if not using best glucose helper
                if (BestGlucose.compensateNoise()) {
                    // this needs scaling based on noise intensity
                    estimate = BgGraphBuilder.best_bg_estimate;
                    estimated_delta = BgGraphBuilder.best_bg_estimate - BgGraphBuilder.last_bg_estimate;
                    // delta by minute
                    slope_arrow = BgReading.slopeToArrowSymbol(estimated_delta / (BgGraphBuilder.DEXCOM_PERIOD / 60000));
                    // currentBgValueText.setTypeface(null, Typeface.ITALIC);
                    // warning symbol !
                    extrastring = " \u26A0";
                }
                // TODO functionize this check as it is in multiple places
                if (Pref.getBooleanDefaultFalse("display_glucose_from_plugin") && (PluggableCalibration.getCalibrationPluginFromPreferences() != null)) {
                    extrastring += " " + context.getString(R.string.p_in_circle);
                }
            } else {
                // TODO make a couple of getters in dg for these functions
                extrastring = " " + dg.extra_string + ((dg.from_plugin) ? " " + context.getString(R.string.p_in_circle) : "");
                estimated_delta = dg.delta_mgdl;
                // TODO properly illustrate + standardize warning level
                if (dg.warning > 1)
                    slope_arrow = "";
            }
            // TODO use dg stale calculation and/or preformatted text
            if ((new Date().getTime()) - Home.stale_data_millis() - lastBgreading.timestamp > 0) {
                // estimate = lastBgreading.calculated_value;
                Log.d(TAG, "old value, estimate " + estimate);
                stringEstimate = bgGraphBuilder.unitized_string(estimate);
                // views.setTextViewText(R.id.widgetArrow, "--");
                slope_arrow = "--";
                views.setInt(R.id.widgetBg, "setPaintFlags", Paint.STRIKE_THRU_TEXT_FLAG | Paint.ANTI_ALIAS_FLAG);
            } else {
                // estimate = lastBgreading.calculated_value;
                stringEstimate = bgGraphBuilder.unitized_string(estimate);
                if (lastBgreading.hide_slope) {
                    slope_arrow = "--";
                }
                Log.d(TAG, "newish value, estimate " + stringEstimate + slope_arrow);
                views.setInt(R.id.widgetBg, "setPaintFlags", 0);
            }
            if (Sensor.isActive() || Home.get_follower()) {
                views.setTextViewText(R.id.widgetBg, stringEstimate);
                views.setTextViewText(R.id.widgetArrow, slope_arrow);
            } else {
                views.setTextViewText(R.id.widgetBg, "");
                views.setTextViewText(R.id.widgetArrow, "");
            }
            // is it really necessary to read this data once here and again in unitizedDeltaString?
            // couldn't we just use the unitizedDeltaString to detect the error condition?
            List<BgReading> bgReadingList = BgReading.latest(2, Home.get_follower());
            if (estimated_delta == -9999) {
                // use original delta
                if (bgReadingList != null && bgReadingList.size() == 2) {
                    views.setTextViewText(R.id.widgetDelta, bgGraphBuilder.unitizedDeltaString(true, true, Home.get_follower()));
                } else {
                    views.setTextViewText(R.id.widgetDelta, "--");
                }
            } else {
                // use compensated estimate
                views.setTextViewText(R.id.widgetDelta, bgGraphBuilder.unitizedDeltaStringRaw(true, true, estimated_delta));
            }
            // TODO use dg preformatted localized string
            int timeAgo = (int) Math.floor((new Date().getTime() - lastBgreading.timestamp) / (1000 * 60));
            if (timeAgo == 1) {
                views.setTextViewText(R.id.readingAge, timeAgo + " Minute ago" + extrastring);
            } else {
                views.setTextViewText(R.id.readingAge, timeAgo + " Minutes ago" + extrastring);
            }
            if (timeAgo > 15) {
                views.setTextColor(R.id.readingAge, Color.parseColor("#FFBB33"));
            } else {
                views.setTextColor(R.id.readingAge, Color.WHITE);
            }
            if (showExstraStatus) {
                views.setTextViewText(R.id.widgetStatusLine, Home.extraStatusLine());
                views.setViewVisibility(R.id.widgetStatusLine, View.VISIBLE);
            } else {
                views.setTextViewText(R.id.widgetStatusLine, "");
                views.setViewVisibility(R.id.widgetStatusLine, View.GONE);
            }
            if (bgGraphBuilder.unitized(estimate) <= bgGraphBuilder.lowMark) {
                views.setTextColor(R.id.widgetBg, Color.parseColor("#C30909"));
                views.setTextColor(R.id.widgetDelta, Color.parseColor("#C30909"));
                views.setTextColor(R.id.widgetArrow, Color.parseColor("#C30909"));
            } else if (bgGraphBuilder.unitized(estimate) >= bgGraphBuilder.highMark) {
                views.setTextColor(R.id.widgetBg, Color.parseColor("#FFBB33"));
                views.setTextColor(R.id.widgetDelta, Color.parseColor("#FFBB33"));
                views.setTextColor(R.id.widgetArrow, Color.parseColor("#FFBB33"));
            } else {
                views.setTextColor(R.id.widgetBg, Color.WHITE);
                views.setTextColor(R.id.widgetDelta, Color.WHITE);
                views.setTextColor(R.id.widgetArrow, Color.WHITE);
            }
        } catch (RuntimeException e) {
            Log.e(TAG, "Got exception in displaycurrentinfo: " + e);
        }
    }
}
Also used : BgSparklineBuilder(com.eveningoutpost.dexdrip.UtilityModels.BgSparklineBuilder) BgReading(com.eveningoutpost.dexdrip.Models.BgReading) Paint(android.graphics.Paint) Date(java.util.Date) BgGraphBuilder(com.eveningoutpost.dexdrip.UtilityModels.BgGraphBuilder)

Example 34 with BgReading

use of com.eveningoutpost.dexdrip.Models.BgReading in project xDrip-plus by jamorham.

the class CustomComplicationProviderService method onComplicationUpdate.

/*
     * Called when the complication needs updated data from your provider. There are four scenarios
     * when this will happen:
     *
     *   1. An active watch face complication is changed to use this provider
     *   2. A complication using this provider becomes active
     *   3. The period of time you specified in the manifest has elapsed (UPDATE_PERIOD_SECONDS)
     *   4. You triggered an update from your own class via the
     *       ProviderUpdateRequester.requestUpdate() method.
     */
@Override
public void onComplicationUpdate(int complicationId, int dataType, ComplicationManager complicationManager) {
    Log.d(TAG, "onComplicationUpdate() id: " + complicationId);
    // Create Tap Action so that the user can trigger an update by tapping the complication.
    final ComponentName thisProvider = new ComponentName(this, getClass());
    // We pass the complication id, so we can only update the specific complication tapped.
    final PendingIntent complicationPendingIntent = ComplicationTapBroadcastReceiver.getToggleIntent(this, thisProvider, complicationId);
    String numberText = "";
    BgReading bgReading = BgReading.last(false);
    if ((bgReading == null) || (JoH.msSince(bgReading.timestamp) >= FRESH_MS)) {
        try {
            // we may be in another process!
            ActiveAndroid.clearCache();
        } catch (Exception e) {
            Log.d(TAG, "Couldn't clear cache: " + e);
        }
        bgReading = BgReading.last(false);
    }
    boolean is_stale = false;
    if (bgReading == null) {
        numberText = "null";
    } else {
        if (JoH.msSince(bgReading.timestamp) < STALE_MS) {
            numberText = bgReading.displayValue(this) + " " + bgReading.displaySlopeArrow();
        } else {
            numberText = "old " + niceTimeSinceBgReading(bgReading);
            is_stale = true;
        }
    }
    Log.d(TAG, "Returning complication text: " + numberText);
    COMPLICATION_STATE state = COMPLICATION_STATE.get_enum((int) PersistentStore.getLong(ComplicationTapBroadcastReceiver.COMPLICATION_STORE));
    if (state == null)
        state = COMPLICATION_STATE.DELTA;
    ComplicationData complicationData = null;
    switch(dataType) {
        case ComplicationData.TYPE_SHORT_TEXT:
            final ComplicationData.Builder builder = new ComplicationData.Builder(ComplicationData.TYPE_SHORT_TEXT).setShortText(ComplicationText.plainText(numberText)).setTapAction(complicationPendingIntent);
            UserError.Log.d(TAG, "TYPE_SHORT_TEXT Current complication state:" + state);
            switch(state) {
                case DELTA:
                    builder.setShortTitle(ComplicationText.plainText(getDeltaText(bgReading, is_stale)));
                    break;
                case AGO:
                    builder.setShortTitle(ComplicationText.plainText(niceTimeSinceBgReading(bgReading)));
                    break;
                default:
                    builder.setShortTitle(ComplicationText.plainText("ERR!"));
            }
            complicationData = builder.build();
            break;
        case ComplicationData.TYPE_LONG_TEXT:
            String numberTextLong = numberText + " " + getDeltaText(bgReading, is_stale) + " (" + niceTimeSinceBgReading(bgReading) + ")";
            Log.d(TAG, "Returning complication text Long: " + numberTextLong);
            // Loop status by @gregorybel
            String externalStatusString = PersistentStore.getString("remote-status-string");
            Log.d(TAG, "Returning complication status: " + externalStatusString);
            final ComplicationData.Builder builderLong = new ComplicationData.Builder(ComplicationData.TYPE_LONG_TEXT).setLongTitle(ComplicationText.plainText(numberTextLong)).setLongText(ComplicationText.plainText(externalStatusString)).setTapAction(complicationPendingIntent);
            UserError.Log.d(TAG, "TYPE_LONG_TEXT Current complication state:" + state);
            complicationData = builderLong.build();
            break;
        default:
            if (Log.isLoggable(TAG, Log.WARN)) {
                Log.w(TAG, "Unexpected complication type " + dataType);
            }
    }
    if (complicationData != null) {
        complicationManager.updateComplicationData(complicationId, complicationData);
    } else {
        // If no data is sent, we still need to inform the ComplicationManager, so the update
        // job can finish and the wake lock isn't held any longer than necessary.
        complicationManager.noUpdateRequired(complicationId);
    }
}
Also used : ComponentName(android.content.ComponentName) PendingIntent(android.app.PendingIntent) BgGraphBuilder.unitizedDeltaString(com.eveningoutpost.dexdrip.UtilityModels.BgGraphBuilder.unitizedDeltaString) BgReading(com.eveningoutpost.dexdrip.Models.BgReading) ComplicationData(android.support.wearable.complications.ComplicationData)

Example 35 with BgReading

use of com.eveningoutpost.dexdrip.Models.BgReading in project xDrip-plus by jamorham.

the class BgGraphBuilder method oldunitizedDeltaString.

public String oldunitizedDeltaString(boolean showUnit, boolean highGranularity) {
    List<BgReading> last2 = BgReading.latest(2);
    if (last2.size() < 2 || last2.get(0).timestamp - last2.get(1).timestamp > MAX_SLOPE_MINUTES * 60 * 1000) {
        // don't show delta if there are not enough values or the values are more than 20 mintes apart
        return "???";
    }
    double value = BgReading.currentSlope() * 5 * 60 * 1000;
    if (Math.abs(value) > 100) {
        // a delta > 100 will not happen with real BG values -> problematic sensor data
        return "ERR";
    }
    // TODO: allow localization from os settings once pebble doesn't require english locale
    DecimalFormat df = new DecimalFormat("#", new DecimalFormatSymbols(Locale.ENGLISH));
    String delta_sign = "";
    if (value > 0) {
        delta_sign = "+";
    }
    if (doMgdl) {
        if (highGranularity) {
            df.setMaximumFractionDigits(1);
        } else {
            df.setMaximumFractionDigits(0);
        }
        return delta_sign + df.format(unitized(value)) + (showUnit ? " mg/dl" : "");
    } else {
        if (highGranularity) {
            df.setMaximumFractionDigits(2);
        } else {
            df.setMaximumFractionDigits(1);
        }
        df.setMinimumFractionDigits(1);
        df.setMinimumIntegerDigits(1);
        return delta_sign + df.format(unitized(value)) + (showUnit ? " mmol/l" : "");
    }
}
Also used : DecimalFormatSymbols(java.text.DecimalFormatSymbols) DecimalFormat(java.text.DecimalFormat) BgReading(com.eveningoutpost.dexdrip.Models.BgReading)

Aggregations

BgReading (com.eveningoutpost.dexdrip.Models.BgReading)66 Date (java.util.Date)26 Calibration (com.eveningoutpost.dexdrip.Models.Calibration)20 Sensor (com.eveningoutpost.dexdrip.Models.Sensor)16 ArrayList (java.util.ArrayList)14 DataMap (com.google.android.gms.wearable.DataMap)12 Intent (android.content.Intent)8 Treatments (com.eveningoutpost.dexdrip.Models.Treatments)8 IOException (java.io.IOException)8 JSONException (org.json.JSONException)8 PendingIntent (android.app.PendingIntent)6 Paint (android.graphics.Paint)6 BloodTest (com.eveningoutpost.dexdrip.Models.BloodTest)6 TransmitterData (com.eveningoutpost.dexdrip.Models.TransmitterData)6 BgGraphBuilder (com.eveningoutpost.dexdrip.UtilityModels.BgGraphBuilder)6 CalibrationAbstract (com.eveningoutpost.dexdrip.calibrations.CalibrationAbstract)6 DecimalFormat (java.text.DecimalFormat)6 JSONArray (org.json.JSONArray)6 Point (android.graphics.Point)4 SpannableString (android.text.SpannableString)4