mirror of
https://github.com/bckelley/cgm-remote-monitor.git
synced 2026-08-24 03:14:12 -05:00
Fix all issues from ESLint (#4730)
* Cherry picks the ES language changes from #4690 * Fix small issues found in linting * * Fix all but one eslint complaint in the bundled code * Add eslint and js-beautify rc files into the repo
This commit is contained in:
@@ -0,0 +1,14 @@
|
||||
module.exports = {
|
||||
"plugins": [ ],
|
||||
"extends": [
|
||||
"eslint:recommended"
|
||||
],
|
||||
"parser": "babel-eslint",
|
||||
"env": {
|
||||
"browser": true,
|
||||
"commonjs": true,
|
||||
"es6": true,
|
||||
"node": true,
|
||||
"jquery": true
|
||||
}
|
||||
};
|
||||
@@ -0,0 +1,16 @@
|
||||
{
|
||||
"indent_size": 2
|
||||
, "indent_char": " "
|
||||
, "comma_first": true
|
||||
, "keep-array-indentation": true
|
||||
, "space_after_named_function": true
|
||||
, "space_after_anon_function": true
|
||||
, "end_with_newline": true
|
||||
, "brace_style": "collapse,preserve-inline"
|
||||
, "space_in_brace": true
|
||||
, "space-in-paren": false
|
||||
, "break-chained-methods": false
|
||||
, "max-preserve-newlines": 2
|
||||
, "space-after-anon-function": false
|
||||
, "indent-empty-lines": false
|
||||
}
|
||||
@@ -57,7 +57,7 @@ cleanstatusdb.actions[0].code = function deleteRecords(client, callback) {
|
||||
callback();
|
||||
}
|
||||
return;
|
||||
};
|
||||
}
|
||||
|
||||
$status.hide().text(translate('Deleting records ...')).fadeIn('slow');
|
||||
$.ajax({
|
||||
@@ -83,11 +83,11 @@ cleanstatusdb.actions[1].init = function init(client, callback) {
|
||||
|
||||
$status.hide();
|
||||
|
||||
var numDays = '<br/>'
|
||||
+ '<label for="admin_devicestatus_days">'
|
||||
+ translate('Number of Days to Keep:')
|
||||
+ ' <input id="admin_devicestatus_days" value="30" size="3" min="1"/>'
|
||||
+ '</label>';
|
||||
var numDays = '<br/>' +
|
||||
'<label for="admin_devicestatus_days">' +
|
||||
translate('Number of Days to Keep:') +
|
||||
' <input id="admin_devicestatus_days" value="30" size="3" min="1"/>' +
|
||||
'</label>';
|
||||
|
||||
$('#admin_' + cleanstatusdb.name + '_1_html').html(numDays);
|
||||
|
||||
|
||||
@@ -18,6 +18,7 @@ futureitems.actions = [
|
||||
, description: 'This task find and remove treatments in the future.'
|
||||
, buttonLabel: 'Remove treatments in the future'
|
||||
}
|
||||
|
||||
, {
|
||||
name: 'Find and remove entries in the future'
|
||||
, description: 'This task find and remove CGM data in the future created by uploader with wrong date/time.'
|
||||
@@ -58,7 +59,7 @@ futureitems.actions[0].init = function init(client, callback) {
|
||||
for (var t = 0; t < treatments.length; t++) {
|
||||
showOneTreatment(treatments[t], table);
|
||||
}
|
||||
};
|
||||
}
|
||||
|
||||
$status.hide().text(translate('Loading database ...')).fadeIn('slow');
|
||||
var nowiso = new Date().toISOString();
|
||||
@@ -89,7 +90,7 @@ futureitems.actions[0].code = function deleteRecords(client, callback) {
|
||||
callback();
|
||||
}
|
||||
return;
|
||||
};
|
||||
}
|
||||
|
||||
function deleteRecordById (_id) {
|
||||
$.ajax({
|
||||
@@ -144,7 +145,7 @@ futureitems.actions[1].code = function deleteRecords(client, callback) {
|
||||
callback();
|
||||
}
|
||||
return;
|
||||
};
|
||||
}
|
||||
|
||||
function deteleteRecordById (_id) {
|
||||
$.ajax({
|
||||
@@ -158,7 +159,6 @@ futureitems.actions[1].code = function deleteRecords(client, callback) {
|
||||
});
|
||||
}
|
||||
|
||||
|
||||
$status.hide().text(translate('Deleting records ...')).fadeIn('slow');
|
||||
for (var i = 0; i < futureitems.entriesrecords.length; i++) {
|
||||
deteleteRecordById(futureitems.entriesrecords[i]._id);
|
||||
|
||||
+22
-19
@@ -1,5 +1,7 @@
|
||||
'use strict';
|
||||
|
||||
const _ = require('lodash');
|
||||
|
||||
var roles = {
|
||||
name: 'roles'
|
||||
, label: 'Roles - Groups of People, Devices, etc'
|
||||
@@ -90,19 +92,18 @@ function reload (client, callback) {
|
||||
|
||||
function genDialog (client) {
|
||||
var ret =
|
||||
'<div id="editroledialog" style="display:none" title="' + client.translate('Edit Role') + '">'
|
||||
+ ' <label for="edrole_name">'
|
||||
+ client.translate('Name')
|
||||
+ ' <input id="edrole_name" placeholder="' + client.translate('admin, school, family, etc') + '"/>'
|
||||
+ ' </label>'
|
||||
+ ' <br>'
|
||||
+ ' <label for="edrole_permissions">' + client.translate('Permissions') + '</label>'
|
||||
+ ' <textarea id="edrole_permissions" rows="3" style="width:300px"></textarea><br>'
|
||||
+ ' <br>'
|
||||
+ ' <label for="edrole_notes">' + client.translate('Additional Notes, Comments') + '</label>'
|
||||
+ ' <textarea id="edrole_notes" style="width:300px"></textarea><br>'
|
||||
+ ' </div>'
|
||||
;
|
||||
'<div id="editroledialog" style="display:none" title="' + client.translate('Edit Role') + '">' +
|
||||
' <label for="edrole_name">' +
|
||||
client.translate('Name') +
|
||||
' <input id="edrole_name" placeholder="' + client.translate('admin, school, family, etc') + '"/>' +
|
||||
' </label>' +
|
||||
' <br>' +
|
||||
' <label for="edrole_permissions">' + client.translate('Permissions') + '</label>' +
|
||||
' <textarea id="edrole_permissions" rows="3" style="width:300px"></textarea><br>' +
|
||||
' <br>' +
|
||||
' <label for="edrole_notes">' + client.translate('Additional Notes, Comments') + '</label>' +
|
||||
' <textarea id="edrole_notes" style="width:300px"></textarea><br>' +
|
||||
' </div>';
|
||||
|
||||
return $(ret);
|
||||
}
|
||||
@@ -112,9 +113,10 @@ function openDialog (role, client) {
|
||||
width: 360
|
||||
, height: 360
|
||||
, buttons: [
|
||||
{ text: client.translate('Save'),
|
||||
class: 'leftButton',
|
||||
click: function() {
|
||||
{
|
||||
text: client.translate('Save')
|
||||
, class: 'leftButton'
|
||||
, click: function() {
|
||||
|
||||
role.name = $('#edrole_name').val();
|
||||
role.permissions =
|
||||
@@ -131,9 +133,10 @@ function openDialog (role, client) {
|
||||
$(self).dialog('close');
|
||||
});
|
||||
}
|
||||
},
|
||||
{ text: client.translate('Cancel'),
|
||||
click: function () { $( this ).dialog('close'); }
|
||||
}
|
||||
, {
|
||||
text: client.translate('Cancel')
|
||||
, click: function() { $(this).dialog('close'); }
|
||||
}
|
||||
]
|
||||
, open: function() {
|
||||
|
||||
@@ -1,5 +1,7 @@
|
||||
'use strict';
|
||||
|
||||
const _ = require('lodash');
|
||||
|
||||
var subjects = {
|
||||
name: 'subjects'
|
||||
, label: 'Subjects - People, Devices, etc'
|
||||
@@ -89,21 +91,20 @@ function reload (client, callback) {
|
||||
|
||||
function genDialog (client) {
|
||||
var ret =
|
||||
'<div id="editsubjectdialog" style="display:none" title="' + client.translate('Edit Subject') + '">'
|
||||
+ ' <label for="edsub_name">'
|
||||
+ client.translate('Name')
|
||||
+ ' <input id="edsub_name" placeholder="' + client.translate('person, device, etc') + '"/>'
|
||||
+ ' </label>'
|
||||
+ ' <br>'
|
||||
+ ' <label for="edsub_roles">'
|
||||
+ client.translate('Roles')
|
||||
+ ' <input id="edsub_roles" placeholder="' + client.translate('role1, role2') + '"/>'
|
||||
+ ' </label>'
|
||||
+ ' <br>'
|
||||
+ ' <label for="edsub_notes">' + client.translate('Additional Notes, Comments') + '</label>'
|
||||
+ ' <textarea id="edsub_notes" style="width:300px"></textarea><br>'
|
||||
+ ' </div>'
|
||||
;
|
||||
'<div id="editsubjectdialog" style="display:none" title="' + client.translate('Edit Subject') + '">' +
|
||||
' <label for="edsub_name">' +
|
||||
client.translate('Name') +
|
||||
' <input id="edsub_name" placeholder="' + client.translate('person, device, etc') + '"/>' +
|
||||
' </label>' +
|
||||
' <br>' +
|
||||
' <label for="edsub_roles">' +
|
||||
client.translate('Roles') +
|
||||
' <input id="edsub_roles" placeholder="' + client.translate('role1, role2') + '"/>' +
|
||||
' </label>' +
|
||||
' <br>' +
|
||||
' <label for="edsub_notes">' + client.translate('Additional Notes, Comments') + '</label>' +
|
||||
' <textarea id="edsub_notes" style="width:300px"></textarea><br>' +
|
||||
' </div>';
|
||||
|
||||
return $(ret);
|
||||
}
|
||||
@@ -113,9 +114,10 @@ function openDialog (subject, client) {
|
||||
width: 360
|
||||
, height: 300
|
||||
, buttons: [
|
||||
{ text: client.translate('Save'),
|
||||
class: 'leftButton',
|
||||
click: function() {
|
||||
{
|
||||
text: client.translate('Save')
|
||||
, class: 'leftButton'
|
||||
, click: function() {
|
||||
subject.name = $('#edsub_name').val();
|
||||
subject.roles =
|
||||
_.chain($('#edsub_roles').val().toLowerCase().split(/[;, ]/))
|
||||
@@ -130,9 +132,10 @@ function openDialog (subject, client) {
|
||||
$(self).dialog('close');
|
||||
});
|
||||
}
|
||||
},
|
||||
{ text: client.translate('Cancel'),
|
||||
click: function () { $( this ).dialog('close'); }
|
||||
}
|
||||
, {
|
||||
text: client.translate('Cancel')
|
||||
, click: function() { $(this).dialog('close'); }
|
||||
}
|
||||
]
|
||||
, open: function() {
|
||||
|
||||
+19
-18
@@ -35,15 +35,14 @@ function init(client, $) {
|
||||
}
|
||||
|
||||
function isProfileEnabled (profiles) {
|
||||
return client.settings.enable.indexOf('profile') > -1
|
||||
&& client.settings.extendedSettings.profile
|
||||
&& client.settings.extendedSettings.profile.multiple
|
||||
&& profiles.length > 1;
|
||||
return client.settings.enable.indexOf('profile') > -1 &&
|
||||
client.settings.extendedSettings.profile &&
|
||||
client.settings.extendedSettings.profile.multiple &&
|
||||
profiles.length > 1;
|
||||
}
|
||||
|
||||
function isTouch () {
|
||||
try { document.createEvent('TouchEvent'); return true; }
|
||||
catch (e) { return false; }
|
||||
try { document.createEvent('TouchEvent'); return true; } catch (e) { return false; }
|
||||
}
|
||||
|
||||
function setDateAndTime (time) {
|
||||
@@ -236,8 +235,8 @@ function init(client, $) {
|
||||
$('#bc_bg').css('background-color', '');
|
||||
}
|
||||
$('#bc_inzulinbg').text(record.insulinbg.toFixed(2));
|
||||
$('#bc_inzulinbg').attr('title',
|
||||
'Target BG range: '+targetBGLow + ' - ' + targetBGHigh +
|
||||
$('#bc_inzulinbg').attr('title'
|
||||
, 'Target BG range: ' + targetBGLow + ' - ' + targetBGHigh +
|
||||
'\nISF: ' + isf +
|
||||
'\nBG diff: ' + record.bgdiff.toFixed(1)
|
||||
);
|
||||
@@ -351,7 +350,6 @@ function init(client, $) {
|
||||
return;
|
||||
}
|
||||
|
||||
|
||||
// Calculate event time from date & time
|
||||
record.eventTime = new Date();
|
||||
if ($('#bc_othertime').is(':checked')) {
|
||||
@@ -515,6 +513,7 @@ function init(client, $) {
|
||||
function buildConfirmText (data) {
|
||||
var text = [
|
||||
translate('Please verify that the data entered is correct') + ': '
|
||||
|
||||
, translate('Event Type') + ': ' + translate(data.eventType)
|
||||
];
|
||||
|
||||
@@ -541,8 +540,8 @@ function init(client, $) {
|
||||
function confirmPost (data) {
|
||||
if (window.confirm(buildConfirmText(data))) {
|
||||
$.ajax({
|
||||
method: 'POST',
|
||||
url: '/api/v1/treatments/'
|
||||
method: 'POST'
|
||||
, url: '/api/v1/treatments/'
|
||||
, headers: client.headers()
|
||||
, data: data
|
||||
}).done(function treatmentSaved (response) {
|
||||
@@ -653,7 +652,7 @@ function init(client, $) {
|
||||
for (var i = 0; i < records.length; i++) {
|
||||
var r = records[i];
|
||||
$('#bc_quickpick').append('<option value="' + i + '">' + r.name + ' (' + r.carbs + ' g)</option>');
|
||||
};
|
||||
}
|
||||
$('#bc_quickpick').val(-1);
|
||||
$('#bc_quickpick').change(quickpickChange);
|
||||
};
|
||||
@@ -721,8 +720,9 @@ function init(client, $) {
|
||||
width: 640
|
||||
, height: 400
|
||||
, buttons: [
|
||||
{ text: translate('Add'),
|
||||
click: function() {
|
||||
{
|
||||
text: translate('Add')
|
||||
, click: function() {
|
||||
var index = $('#bc_data').val();
|
||||
var portions = parseFloat($('#bc_addportions').val().replace(',', '.'));
|
||||
if (index !== null && !isNaN(portions) && portions > 0) {
|
||||
@@ -732,10 +732,11 @@ function init(client, $) {
|
||||
boluscalc.calculateInsulin();
|
||||
}
|
||||
}
|
||||
},
|
||||
{ text: translate('Reload database'),
|
||||
class: 'leftButton',
|
||||
click: boluscalc.loadFoodDatabase
|
||||
}
|
||||
, {
|
||||
text: translate('Reload database')
|
||||
, class: 'leftButton'
|
||||
, click: boluscalc.loadFoodDatabase
|
||||
}
|
||||
]
|
||||
, open: function() {
|
||||
|
||||
@@ -117,34 +117,32 @@ function init (client, serverSettings, $) {
|
||||
}
|
||||
|
||||
function storeInBrowser (data) {
|
||||
for (var k in data) {
|
||||
if (data.hasOwnProperty(k)) {
|
||||
Object.keys(data).forEach(k => {
|
||||
storage.set(k, data[k]);
|
||||
}
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
storeInBrowser({
|
||||
units: $('input:radio[name=units-browser]:checked').val(),
|
||||
alarmUrgentHigh: $('#alarm-urgenthigh-browser').prop('checked'),
|
||||
alarmHigh: $('#alarm-high-browser').prop('checked'),
|
||||
alarmLow: $('#alarm-low-browser').prop('checked'),
|
||||
alarmUrgentLow: $('#alarm-urgentlow-browser').prop('checked'),
|
||||
alarmTimeagoWarn: $('#alarm-timeagowarn-browser').prop('checked'),
|
||||
alarmTimeagoWarnMins: parseInt($('#alarm-timeagowarnmins-browser').val()) || 15,
|
||||
alarmTimeagoUrgent: $('#alarm-timeagourgent-browser').prop('checked'),
|
||||
alarmTimeagoUrgentMins: parseInt($('#alarm-timeagourgentmins-browser').val()) || 30,
|
||||
nightMode: $('#nightmode-browser').prop('checked'),
|
||||
editMode: $('#editmode-browser').prop('checked'),
|
||||
showRawbg: $('input:radio[name=show-rawbg]:checked').val(),
|
||||
customTitle: $('input#customTitle').prop('value'),
|
||||
theme: $('input:radio[name=theme-browser]:checked').val(),
|
||||
timeFormat: parseInt($('input:radio[name=timeformat-browser]:checked').val()),
|
||||
language: $('#language').val(),
|
||||
scaleY: $('#scaleY').val(),
|
||||
basalrender: $('#basalrender').val(),
|
||||
showPlugins: checkedPluginNames(),
|
||||
storageVersion: STORAGE_VERSION
|
||||
units: $('input:radio[name=units-browser]:checked').val()
|
||||
, alarmUrgentHigh: $('#alarm-urgenthigh-browser').prop('checked')
|
||||
, alarmHigh: $('#alarm-high-browser').prop('checked')
|
||||
, alarmLow: $('#alarm-low-browser').prop('checked')
|
||||
, alarmUrgentLow: $('#alarm-urgentlow-browser').prop('checked')
|
||||
, alarmTimeagoWarn: $('#alarm-timeagowarn-browser').prop('checked')
|
||||
, alarmTimeagoWarnMins: parseInt($('#alarm-timeagowarnmins-browser').val()) || 15
|
||||
, alarmTimeagoUrgent: $('#alarm-timeagourgent-browser').prop('checked')
|
||||
, alarmTimeagoUrgentMins: parseInt($('#alarm-timeagourgentmins-browser').val()) || 30
|
||||
, nightMode: $('#nightmode-browser').prop('checked')
|
||||
, editMode: $('#editmode-browser').prop('checked')
|
||||
, showRawbg: $('input:radio[name=show-rawbg]:checked').val()
|
||||
, customTitle: $('input#customTitle').prop('value')
|
||||
, theme: $('input:radio[name=theme-browser]:checked').val()
|
||||
, timeFormat: parseInt($('input:radio[name=timeformat-browser]:checked').val())
|
||||
, language: $('#language').val()
|
||||
, scaleY: $('#scaleY').val()
|
||||
, basalrender: $('#basalrender').val()
|
||||
, showPlugins: checkedPluginNames()
|
||||
, storageVersion: STORAGE_VERSION
|
||||
});
|
||||
|
||||
event.preventDefault();
|
||||
@@ -213,5 +211,4 @@ function init (client, serverSettings, $) {
|
||||
return settings;
|
||||
}
|
||||
|
||||
|
||||
module.exports = init;
|
||||
|
||||
@@ -13,9 +13,9 @@ function init ($) {
|
||||
$('#drawer').find('.tip').tooltip();
|
||||
}
|
||||
$.fn.tooltip.defaults = {
|
||||
fade: true,
|
||||
gravity: 'n',
|
||||
opacity: 0.75
|
||||
fade: true
|
||||
, gravity: 'n'
|
||||
, opacity: 0.75
|
||||
};
|
||||
|
||||
var querystring = queryParms();
|
||||
@@ -49,11 +49,11 @@ function init ($) {
|
||||
window.location.href = url;
|
||||
}
|
||||
|
||||
|
||||
function queryParms () {
|
||||
var params = {};
|
||||
if (location.search) {
|
||||
location.search.substr(1).split('&').forEach(function(item) {
|
||||
// eslint-disable-next-line no-useless-escape
|
||||
params[item.split('=')[0]] = item.split('=')[1].replace(/[_\+]/g, ' ');
|
||||
});
|
||||
}
|
||||
@@ -61,8 +61,7 @@ function init ($) {
|
||||
}
|
||||
|
||||
function isTouch () {
|
||||
try { document.createEvent('TouchEvent'); return true; }
|
||||
catch (e) { return false; }
|
||||
try { document.createEvent('TouchEvent'); return true; } catch (e) { return false; }
|
||||
}
|
||||
|
||||
function closeLastOpenedDrawer (callback) {
|
||||
@@ -114,7 +113,6 @@ function init ($) {
|
||||
style.width = '350px';
|
||||
}
|
||||
|
||||
|
||||
$(id).css(style);
|
||||
});
|
||||
|
||||
|
||||
@@ -33,9 +33,9 @@ client.render = function render(xhr) {
|
||||
|
||||
// Convert BG to mmol/L if necessary.
|
||||
if (window.serverSettings.settings.units == 'mmol') {
|
||||
var displayValue = Nightscout.units.mgdlToMMOL(rec.sgv);
|
||||
var displayValue = window.Nightscout.units.mgdlToMMOL(rec.sgv);
|
||||
} else {
|
||||
var displayValue = rec.sgv;
|
||||
displayValue = rec.sgv;
|
||||
}
|
||||
|
||||
// Insert the BG value text.
|
||||
@@ -53,8 +53,8 @@ client.render = function render(xhr) {
|
||||
|
||||
// Generate and insert the clock.
|
||||
let timeDivisor = (client.settings.timeFormat) ? client.settings.timeFormat : 12;
|
||||
let today = new Date(),
|
||||
h = today.getHours() % timeDivisor;
|
||||
let today = new Date()
|
||||
, h = today.getHours() % timeDivisor;
|
||||
if (timeDivisor == 12) {
|
||||
h = (h == 0) ? 12 : h; // In the case of 00:xx, change to 12:xx for 12h time
|
||||
}
|
||||
@@ -65,6 +65,8 @@ client.render = function render(xhr) {
|
||||
if (m < 10) m = "0" + m;
|
||||
$('#clock').text(h + ":" + m);
|
||||
|
||||
// defined in the template this is loaded into
|
||||
// eslint-disable-next-line no-undef
|
||||
if (clockFace == 'clock-color') {
|
||||
|
||||
var bgHigh = window.serverSettings.settings.thresholds.bgHigh;
|
||||
|
||||
+11
-16
@@ -60,6 +60,7 @@ client.init = function init(callback) {
|
||||
console.log('Application appears to be online');
|
||||
$('#centerMessagePanel').hide();
|
||||
client.load(serverSettings, callback);
|
||||
// eslint-disable-next-line no-unused-vars
|
||||
}).fail(function fail (jqXHR, textStatus, errorThrown) {
|
||||
|
||||
// check if we couldn't reach the server at all, show offline message
|
||||
@@ -94,15 +95,13 @@ client.load = function load(serverSettings, callback) {
|
||||
, FORMAT_TIME_12_COMPACT = '%-I:%M'
|
||||
, FORMAT_TIME_24 = '%H:%M%'
|
||||
, FORMAT_TIME_12_SCALE = '%-I %p'
|
||||
, FORMAT_TIME_24_SCALE = '%H'
|
||||
;
|
||||
, FORMAT_TIME_24_SCALE = '%H';
|
||||
|
||||
var history = 48;
|
||||
|
||||
var chart
|
||||
, socket
|
||||
, isInitialData = false
|
||||
, prevSGV
|
||||
, opacity = { current: 1, DAY: 1, NIGHT: 0.5 }
|
||||
, clientAlarms = {}
|
||||
, alarmInProgress = false
|
||||
@@ -111,8 +110,7 @@ client.load = function load(serverSettings, callback) {
|
||||
, currentAnnouncement
|
||||
, alarmSound = 'alarm.mp3'
|
||||
, urgentAlarmSound = 'alarm2.mp3'
|
||||
, previousNotifyTimestamp
|
||||
;
|
||||
, previousNotifyTimestamp;
|
||||
|
||||
client.entryToDate = function entryToDate (entry) { return new Date(entry.mills); };
|
||||
|
||||
@@ -130,8 +128,7 @@ client.load = function load(serverSettings, callback) {
|
||||
, minorPills = $('.bgStatus .minorPills')
|
||||
, statusPills = $('.status .statusPills')
|
||||
, primary = $('.primary')
|
||||
, editButton = $('#editbutton')
|
||||
;
|
||||
, editButton = $('#editbutton');
|
||||
|
||||
client.tooltip = d3.select('body').append('div')
|
||||
.attr('class', 'tooltip')
|
||||
@@ -250,8 +247,8 @@ client.load = function load(serverSettings, callback) {
|
||||
|
||||
client.dataExtent = function dataExtent () {
|
||||
return client.entries.length > 0 ?
|
||||
d3.extent(client.entries, client.entryToDate)
|
||||
: d3.extent([new Date(client.now - times.hours(history).msecs), new Date(client.now)]);
|
||||
d3.extent(client.entries, client.entryToDate) :
|
||||
d3.extent([new Date(client.now - times.hours(history).msecs), new Date(client.now)]);
|
||||
};
|
||||
|
||||
client.bottomOfPills = function bottomOfPills () {
|
||||
@@ -758,8 +755,8 @@ client.load = function load(serverSettings, callback) {
|
||||
}
|
||||
|
||||
function isStale (status) {
|
||||
return client.settings.alarmTimeagoWarn && status === 'warn'
|
||||
|| client.settings.alarmTimeagoUrgent && status === 'urgent';
|
||||
return client.settings.alarmTimeagoWarn && status === 'warn' ||
|
||||
client.settings.alarmTimeagoUrgent && status === 'urgent';
|
||||
}
|
||||
|
||||
function notAcked (alarm) {
|
||||
@@ -888,10 +885,10 @@ client.load = function load(serverSettings, callback) {
|
||||
}
|
||||
});
|
||||
|
||||
|
||||
////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
|
||||
// Client-side code to connect to server and handle incoming data
|
||||
////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
|
||||
// eslint-disable-next-line no-undef
|
||||
client.socket = socket = io.connect();
|
||||
|
||||
socket.on('dataUpdate', dataUpdate);
|
||||
@@ -993,8 +990,7 @@ client.load = function load(serverSettings, callback) {
|
||||
socket.on('notification', function(notify) {
|
||||
console.log('notification from server:', notify);
|
||||
|
||||
if (notify.timestamp && previousNotifyTimestamp != notify.timestamp)
|
||||
{
|
||||
if (notify.timestamp && previousNotifyTimestamp != notify.timestamp) {
|
||||
previousNotifyTimestamp = notify.timestamp;
|
||||
client.plugins.visualizeAlarm(client.sbx, notify, notify.title + ' ' + notify.message);
|
||||
} else {
|
||||
@@ -1131,10 +1127,9 @@ client.load = function load(serverSettings, callback) {
|
||||
}
|
||||
|
||||
if (client.ddata.sgvs) {
|
||||
// change the next line so that it uses the prediction if the signal gets lost (max 1/2 hr)
|
||||
// TODO change the next line so that it uses the prediction if the signal gets lost (max 1/2 hr)
|
||||
client.ctx.data.lastUpdated = lastUpdated;
|
||||
client.latestSGV = client.ddata.sgvs[client.ddata.sgvs.length - 1];
|
||||
prevSGV = client.ddata.sgvs[client.ddata.sgvs.length - 2];
|
||||
}
|
||||
|
||||
client.ddata.inRetroMode = false;
|
||||
|
||||
@@ -7,19 +7,19 @@ var TWO_DAYS = 172800000;
|
||||
function mergeDataUpdate (isDelta, cachedDataArray, receivedDataArray, maxAge) {
|
||||
|
||||
function nsArrayDiff (oldArray, newArray) {
|
||||
var seen = {};
|
||||
var seen = [];
|
||||
var l = oldArray.length;
|
||||
|
||||
for (var i = 0; i < l; i++) {
|
||||
if (oldArray[i] !== null) {
|
||||
seen[oldArray[i].mills] = true;
|
||||
seen.push(oldArray[i].mills);
|
||||
}
|
||||
}
|
||||
|
||||
var result = [];
|
||||
l = newArray.length;
|
||||
for (var j = 0; j < l; j++) {
|
||||
if (!seen.hasOwnProperty(newArray[j].mills)) {
|
||||
if (!seen.includes(newArray[j].mills)) {
|
||||
result.push(newArray[j]); //console.log('delta data found');
|
||||
}
|
||||
}
|
||||
|
||||
+124
-133
@@ -406,8 +406,7 @@ function init (client, d3) {
|
||||
, R2 = R1
|
||||
// R3/R4 determine how far from the treatment dot the labels are placed
|
||||
, R3 = R1 + 8 / opts.scale
|
||||
, R4 = R1 + 25 / opts.scale
|
||||
;
|
||||
, R4 = R1 + 25 / opts.scale;
|
||||
|
||||
return {
|
||||
R1: R1
|
||||
@@ -421,14 +420,14 @@ function init (client, d3) {
|
||||
function prepareArc (treatment, radius) {
|
||||
var arc_data = [
|
||||
// white carb half-circle on top
|
||||
{ 'element': '', 'color': 'white', 'start': -1.5708, 'end': 1.5708, 'inner': 0, 'outer': radius.R1 },
|
||||
{ 'element': '', 'color': 'transparent', 'start': -1.5708, 'end': 1.5708, 'inner': radius.R2, 'outer': radius.R3 },
|
||||
{ 'element': '', 'color': 'white', 'start': -1.5708, 'end': 1.5708, 'inner': 0, 'outer': radius.R1 }
|
||||
, { 'element': '', 'color': 'transparent', 'start': -1.5708, 'end': 1.5708, 'inner': radius.R2, 'outer': radius.R3 },
|
||||
// blue insulin half-circle on bottom
|
||||
{ 'element': '', 'color': '#0099ff', 'start': 1.5708, 'end': 4.7124, 'inner': 0, 'outer': radius.R1 },
|
||||
// these form a very short transparent arc along the bottom of an insulin treatment to position the label
|
||||
// these used to be semicircles from 1.5708 to 4.7124, but that made the tooltip target too big
|
||||
{ 'element': '', 'color': 'transparent', 'start': 3.1400, 'end': 3.1432, 'inner': radius.R2, 'outer': radius.R3 },
|
||||
{ 'element': '', 'color': 'transparent', 'start': 3.1400, 'end': 3.1432, 'inner': radius.R2, 'outer': radius.R4 }
|
||||
{ 'element': '', 'color': 'transparent', 'start': 3.1400, 'end': 3.1432, 'inner': radius.R2, 'outer': radius.R3 }
|
||||
, { 'element': '', 'color': 'transparent', 'start': 3.1400, 'end': 3.1432, 'inner': radius.R2, 'outer': radius.R4 }
|
||||
];
|
||||
|
||||
arc_data[0].outlineOnly = !treatment.carbs;
|
||||
@@ -550,96 +549,96 @@ function init (client, d3) {
|
||||
.style('top', (d3.event.pageY ? d3.event.pageY + 15 : 40) + 'px');
|
||||
|
||||
deleteRect = {
|
||||
x: 0,
|
||||
y: 0,
|
||||
width: 50,
|
||||
height: chart().yScale(chart().yScale.domain()[0])
|
||||
x: 0
|
||||
, y: 0
|
||||
, width: 50
|
||||
, height: chart().yScale(chart().yScale.domain()[0])
|
||||
};
|
||||
chart().drag.append('rect')
|
||||
.attr({
|
||||
class:'drag-droparea',
|
||||
x: deleteRect.x,
|
||||
y: deleteRect.y,
|
||||
width: deleteRect.width,
|
||||
height: deleteRect.height,
|
||||
fill: 'red',
|
||||
opacity: 0.4,
|
||||
rx: 10,
|
||||
ry: 10
|
||||
class: 'drag-droparea'
|
||||
, x: deleteRect.x
|
||||
, y: deleteRect.y
|
||||
, width: deleteRect.width
|
||||
, height: deleteRect.height
|
||||
, fill: 'red'
|
||||
, opacity: 0.4
|
||||
, rx: 10
|
||||
, ry: 10
|
||||
});
|
||||
chart().drag.append('text')
|
||||
.attr({
|
||||
class:'drag-droparea',
|
||||
x: deleteRect.x + deleteRect.width / 2,
|
||||
y: deleteRect.y + deleteRect.height / 2,
|
||||
'font-size': 15,
|
||||
'font-weight': 'bold',
|
||||
fill: 'red',
|
||||
'text-anchor': 'middle',
|
||||
dy: '.35em',
|
||||
transform: 'rotate(-90 ' + (deleteRect.x + deleteRect.width / 2) + ',' + (deleteRect.y + deleteRect.height / 2) + ')'
|
||||
class: 'drag-droparea'
|
||||
, x: deleteRect.x + deleteRect.width / 2
|
||||
, y: deleteRect.y + deleteRect.height / 2
|
||||
, 'font-size': 15
|
||||
, 'font-weight': 'bold'
|
||||
, fill: 'red'
|
||||
, 'text-anchor': 'middle'
|
||||
, dy: '.35em'
|
||||
, transform: 'rotate(-90 ' + (deleteRect.x + deleteRect.width / 2) + ',' + (deleteRect.y + deleteRect.height / 2) + ')'
|
||||
})
|
||||
.text(translate('Remove'));
|
||||
|
||||
if (treatment.insulin && treatment.carbs) {
|
||||
carbsRect = {
|
||||
x: 0,
|
||||
y: 0,
|
||||
width: chart().charts.attr('width'),
|
||||
height: 50
|
||||
x: 0
|
||||
, y: 0
|
||||
, width: chart().charts.attr('width')
|
||||
, height: 50
|
||||
};
|
||||
insulinRect = {
|
||||
x: 0,
|
||||
y: chart().yScale(chart().yScale.domain()[0]) - 50,
|
||||
width: chart().charts.attr('width'),
|
||||
height: 50
|
||||
x: 0
|
||||
, y: chart().yScale(chart().yScale.domain()[0]) - 50
|
||||
, width: chart().charts.attr('width')
|
||||
, height: 50
|
||||
};
|
||||
chart().drag.append('rect')
|
||||
.attr({
|
||||
class:'drag-droparea',
|
||||
x: carbsRect.x,
|
||||
y: carbsRect.y,
|
||||
width: carbsRect.width,
|
||||
height: carbsRect.height,
|
||||
fill: 'white',
|
||||
opacity: 0.4,
|
||||
rx: 10,
|
||||
ry: 10
|
||||
class: 'drag-droparea'
|
||||
, x: carbsRect.x
|
||||
, y: carbsRect.y
|
||||
, width: carbsRect.width
|
||||
, height: carbsRect.height
|
||||
, fill: 'white'
|
||||
, opacity: 0.4
|
||||
, rx: 10
|
||||
, ry: 10
|
||||
});
|
||||
chart().drag.append('text')
|
||||
.attr({
|
||||
class:'drag-droparea',
|
||||
x: carbsRect.x + carbsRect.width / 2,
|
||||
y: carbsRect.y + carbsRect.height / 2,
|
||||
'font-size': 15,
|
||||
'font-weight': 'bold',
|
||||
fill: 'white',
|
||||
'text-anchor': 'middle',
|
||||
dy: '.35em'
|
||||
class: 'drag-droparea'
|
||||
, x: carbsRect.x + carbsRect.width / 2
|
||||
, y: carbsRect.y + carbsRect.height / 2
|
||||
, 'font-size': 15
|
||||
, 'font-weight': 'bold'
|
||||
, fill: 'white'
|
||||
, 'text-anchor': 'middle'
|
||||
, dy: '.35em'
|
||||
})
|
||||
.text(translate('Move carbs'));
|
||||
chart().drag.append('rect')
|
||||
.attr({
|
||||
class:'drag-droparea',
|
||||
x: insulinRect.x,
|
||||
y: insulinRect.y,
|
||||
width: insulinRect.width,
|
||||
height: insulinRect.height,
|
||||
fill: '#0099ff',
|
||||
opacity: 0.4,
|
||||
rx: 10,
|
||||
ry: 10
|
||||
class: 'drag-droparea'
|
||||
, x: insulinRect.x
|
||||
, y: insulinRect.y
|
||||
, width: insulinRect.width
|
||||
, height: insulinRect.height
|
||||
, fill: '#0099ff'
|
||||
, opacity: 0.4
|
||||
, rx: 10
|
||||
, ry: 10
|
||||
});
|
||||
chart().drag.append('text')
|
||||
.attr({
|
||||
class:'drag-droparea',
|
||||
x: insulinRect.x + insulinRect.width / 2,
|
||||
y: insulinRect.y + insulinRect.height / 2,
|
||||
'font-size': 15,
|
||||
'font-weight': 'bold',
|
||||
fill: '#0099ff',
|
||||
'text-anchor': 'middle',
|
||||
dy: '.35em'
|
||||
class: 'drag-droparea'
|
||||
, x: insulinRect.x + insulinRect.width / 2
|
||||
, y: insulinRect.y + insulinRect.height / 2
|
||||
, 'font-size': 15
|
||||
, 'font-weight': 'bold'
|
||||
, fill: '#0099ff'
|
||||
, 'text-anchor': 'middle'
|
||||
, dy: '.35em'
|
||||
})
|
||||
.text(translate('Move insulin'));
|
||||
}
|
||||
@@ -670,22 +669,22 @@ function init (client, d3) {
|
||||
newTime = new Date(chart().xScale.invert(x));
|
||||
var minDiff = times.msecs(newTime.getTime() - treatment.mills).mins.toFixed(0);
|
||||
client.tooltip.html(
|
||||
'<b>' + translate('Operation') + ':</b> ' + translate(operation) + '<br>'
|
||||
+ '<b>' + translate('New time') + ':</b> ' + newTime.toLocaleTimeString() + '<br>'
|
||||
+ '<b>' + translate('Difference') + ':</b> ' + (minDiff > 0 ? '+' : '') + minDiff + ' ' + translate('mins')
|
||||
'<b>' + translate('Operation') + ':</b> ' + translate(operation) + '<br>' +
|
||||
'<b>' + translate('New time') + ':</b> ' + newTime.toLocaleTimeString() + '<br>' +
|
||||
'<b>' + translate('Difference') + ':</b> ' + (minDiff > 0 ? '+' : '') + minDiff + ' ' + translate('mins')
|
||||
);
|
||||
|
||||
chart().drag.selectAll('.arrow').remove();
|
||||
chart().drag.append('line')
|
||||
.attr({
|
||||
'class':'arrow',
|
||||
'marker-end':'url(#arrow)',
|
||||
'x1': chart().xScale(new Date(treatment.mills)),
|
||||
'y1': chart().yScale(client.sbx.scaleEntry(treatment)),
|
||||
'x2': x,
|
||||
'y2': y,
|
||||
'stroke-width': 2,
|
||||
'stroke': 'white'
|
||||
'class': 'arrow'
|
||||
, 'marker-end': 'url(#arrow)'
|
||||
, 'x1': chart().xScale(new Date(treatment.mills))
|
||||
, 'y1': chart().yScale(client.sbx.scaleEntry(treatment))
|
||||
, 'x2': x
|
||||
, 'y2': y
|
||||
, 'stroke-width': 2
|
||||
, 'stroke': 'white'
|
||||
});
|
||||
|
||||
})
|
||||
@@ -697,13 +696,12 @@ function init (client, d3) {
|
||||
case 'Move':
|
||||
if (window.confirm(translate('Change treatment time to %1 ?', { params: [newTime.toLocaleTimeString()] }))) {
|
||||
client.socket.emit(
|
||||
'dbUpdate',
|
||||
{
|
||||
collection: 'treatments',
|
||||
_id: treatment._id,
|
||||
data: { created_at: newTime.toISOString() }
|
||||
},
|
||||
function callback(result) {
|
||||
'dbUpdate', {
|
||||
collection: 'treatments'
|
||||
, _id: treatment._id
|
||||
, data: { created_at: newTime.toISOString() }
|
||||
}
|
||||
, function callback (result) {
|
||||
console.log(result);
|
||||
chart().drag.selectAll('.arrow').transition().duration(5000).style('opacity', 0).remove();
|
||||
}
|
||||
@@ -715,13 +713,12 @@ function init (client, d3) {
|
||||
case 'Remove insulin':
|
||||
if (window.confirm(translate('Remove insulin from treatment ?'))) {
|
||||
client.socket.emit(
|
||||
'dbUpdateUnset',
|
||||
{
|
||||
collection: 'treatments',
|
||||
_id: treatment._id,
|
||||
data: { insulin: 1 }
|
||||
},
|
||||
function callback(result) {
|
||||
'dbUpdateUnset', {
|
||||
collection: 'treatments'
|
||||
, _id: treatment._id
|
||||
, data: { insulin: 1 }
|
||||
}
|
||||
, function callback (result) {
|
||||
console.log(result);
|
||||
chart().drag.selectAll('.arrow').transition().duration(5000).style('opacity', 0).remove();
|
||||
}
|
||||
@@ -733,13 +730,12 @@ function init (client, d3) {
|
||||
case 'Remove carbs':
|
||||
if (window.confirm(translate('Remove carbs from treatment ?'))) {
|
||||
client.socket.emit(
|
||||
'dbUpdateUnset',
|
||||
{
|
||||
collection: 'treatments',
|
||||
_id: treatment._id,
|
||||
data: { carbs: 1 }
|
||||
},
|
||||
function callback(result) {
|
||||
'dbUpdateUnset', {
|
||||
collection: 'treatments'
|
||||
, _id: treatment._id
|
||||
, data: { carbs: 1 }
|
||||
}
|
||||
, function callback (result) {
|
||||
console.log(result);
|
||||
chart().drag.selectAll('.arrow').transition().duration(5000).style('opacity', 0).remove();
|
||||
}
|
||||
@@ -751,12 +747,11 @@ function init (client, d3) {
|
||||
case 'Remove':
|
||||
if (window.confirm(translate('Remove treatment ?'))) {
|
||||
client.socket.emit(
|
||||
'dbRemove',
|
||||
{
|
||||
collection: 'treatments',
|
||||
_id: treatment._id
|
||||
},
|
||||
function callback(result) {
|
||||
'dbRemove', {
|
||||
collection: 'treatments'
|
||||
, _id: treatment._id
|
||||
}
|
||||
, function callback (result) {
|
||||
console.log(result);
|
||||
chart().drag.selectAll('.arrow').transition().duration(5000).style('opacity', 0).remove();
|
||||
}
|
||||
@@ -768,11 +763,10 @@ function init (client, d3) {
|
||||
case 'Move insulin':
|
||||
if (window.confirm(translate('Change insulin time to %1 ?', { params: [newTime.toLocaleTimeString()] }))) {
|
||||
client.socket.emit(
|
||||
'dbUpdateUnset',
|
||||
{
|
||||
collection: 'treatments',
|
||||
_id: treatment._id,
|
||||
data: { insulin: 1 }
|
||||
'dbUpdateUnset', {
|
||||
collection: 'treatments'
|
||||
, _id: treatment._id
|
||||
, data: { insulin: 1 }
|
||||
}
|
||||
);
|
||||
newTreatment = _.cloneDeep(treatment);
|
||||
@@ -781,12 +775,11 @@ function init (client, d3) {
|
||||
delete newTreatment.carbs;
|
||||
newTreatment.created_at = newTime.toISOString();
|
||||
client.socket.emit(
|
||||
'dbAdd',
|
||||
{
|
||||
collection: 'treatments',
|
||||
data: newTreatment
|
||||
},
|
||||
function callback(result) {
|
||||
'dbAdd', {
|
||||
collection: 'treatments'
|
||||
, data: newTreatment
|
||||
}
|
||||
, function callback (result) {
|
||||
console.log(result);
|
||||
chart().drag.selectAll('.arrow').transition().duration(5000).style('opacity', 0).remove();
|
||||
}
|
||||
@@ -798,11 +791,10 @@ function init (client, d3) {
|
||||
case 'Move carbs':
|
||||
if (window.confirm(translate('Change carbs time to %1 ?', { params: [newTime.toLocaleTimeString()] }))) {
|
||||
client.socket.emit(
|
||||
'dbUpdateUnset',
|
||||
{
|
||||
collection: 'treatments',
|
||||
_id: treatment._id,
|
||||
data: { carbs: 1 }
|
||||
'dbUpdateUnset', {
|
||||
collection: 'treatments'
|
||||
, _id: treatment._id
|
||||
, data: { carbs: 1 }
|
||||
}
|
||||
);
|
||||
newTreatment = _.cloneDeep(treatment);
|
||||
@@ -811,12 +803,11 @@ function init (client, d3) {
|
||||
delete newTreatment.insulin;
|
||||
newTreatment.created_at = newTime.toISOString();
|
||||
client.socket.emit(
|
||||
'dbAdd',
|
||||
{
|
||||
collection: 'treatments',
|
||||
data: newTreatment
|
||||
},
|
||||
function callback(result) {
|
||||
'dbAdd', {
|
||||
collection: 'treatments'
|
||||
, data: newTreatment
|
||||
}
|
||||
, function callback (result) {
|
||||
console.log(result);
|
||||
chart().drag.selectAll('.arrow').transition().duration(5000).style('opacity', 0).remove();
|
||||
}
|
||||
@@ -895,7 +886,7 @@ function init (client, d3) {
|
||||
chart().focus.selectAll('.draggable-treatment').remove();
|
||||
|
||||
_.forEach(client.ddata.treatments, function eachTreatment (d) {
|
||||
if (Number(d.insulin) > 0 || Number(d.carbs) > 0) { treatmentCount += 1; };
|
||||
if (Number(d.insulin) > 0 || Number(d.carbs) > 0) { treatmentCount += 1; }
|
||||
});
|
||||
|
||||
// add treatment bubbles
|
||||
@@ -906,7 +897,7 @@ function init (client, d3) {
|
||||
, treatments: treatmentCount
|
||||
}, client.sbx.data.profile.getCarbRatio(new Date()));
|
||||
});
|
||||
};
|
||||
}
|
||||
|
||||
renderer.drawTreatment = function drawTreatment (treatment, opts, carbratio) {
|
||||
if (!treatment.carbs && !treatment.insulin) {
|
||||
@@ -929,7 +920,7 @@ function init (client, d3) {
|
||||
var arc = prepareArc(treatment, radius);
|
||||
var treatmentDots = appendTreatments(treatment, arc);
|
||||
appendLabels(treatmentDots, arc, opts);
|
||||
};
|
||||
}
|
||||
|
||||
renderer.addBasals = function addBasals (client) {
|
||||
|
||||
|
||||
@@ -11,6 +11,7 @@ var ONE_DAY = 86400000,
|
||||
function uniq(a) {
|
||||
var seen = {};
|
||||
return a.filter(function(item) {
|
||||
// eslint-disable-next-line no-prototype-builtins
|
||||
return seen.hasOwnProperty(item.mills) ? false : (seen[item.mills] = true);
|
||||
});
|
||||
}
|
||||
|
||||
+16
-17
@@ -8,15 +8,15 @@ var DEVICE_TYPE_FIELDS = ['uploader', 'pump', 'openaps', 'loop', 'xdripjs'];
|
||||
function init () {
|
||||
|
||||
var ddata = {
|
||||
sgvs: [],
|
||||
treatments: [],
|
||||
mbgs: [],
|
||||
cals: [],
|
||||
profiles: [],
|
||||
devicestatus: [],
|
||||
food: [],
|
||||
activity: [],
|
||||
lastUpdated: 0
|
||||
sgvs: []
|
||||
, treatments: []
|
||||
, mbgs: []
|
||||
, cals: []
|
||||
, profiles: []
|
||||
, devicestatus: []
|
||||
, food: []
|
||||
, activity: []
|
||||
, lastUpdated: 0
|
||||
};
|
||||
|
||||
ddata.clone = function clone () {
|
||||
@@ -34,8 +34,8 @@ function init() {
|
||||
|
||||
ddata.splitRecent = function splitRecent (time, cutoff, max, treatmentsToo) {
|
||||
var result = {
|
||||
first: {},
|
||||
rest: {}
|
||||
first: {}
|
||||
, rest: {}
|
||||
};
|
||||
|
||||
function recent (item) {
|
||||
@@ -67,13 +67,12 @@ function init() {
|
||||
result.first.cals = ddata.cals;
|
||||
|
||||
var profiles = _.cloneDeep(ddata.profiles);
|
||||
if (profiles && profiles[0])
|
||||
for (var k in profiles[0].store) {
|
||||
if (profiles[0].store.hasOwnProperty(k)) {
|
||||
if (profiles && profiles[0]) {
|
||||
Object.keys(profiles[0].store).forEach(k => {
|
||||
if (k.indexOf('@@@@@') > 0) {
|
||||
delete profiles[0].store[k];
|
||||
}
|
||||
}
|
||||
})
|
||||
}
|
||||
result.first.profiles = profiles;
|
||||
|
||||
@@ -99,8 +98,8 @@ function init() {
|
||||
})
|
||||
.map(function toDeviceTypeKey (key) {
|
||||
return {
|
||||
device: status.device,
|
||||
type: key
|
||||
device: status.device
|
||||
, type: key
|
||||
};
|
||||
})
|
||||
.value();
|
||||
|
||||
+23
-393
@@ -834,7 +834,6 @@ function init() {
|
||||
,dk: 'Noter indeholder'
|
||||
,fi: 'Merkinnät sisältävät'
|
||||
,nb: 'Notater inneholder'
|
||||
,he: 'הערות מכילות'
|
||||
,pl: 'Zawierają uwagi'
|
||||
,ru: 'Примечания содержат'
|
||||
,sk: 'Poznámky obsahujú'
|
||||
@@ -1460,7 +1459,6 @@ function init() {
|
||||
,sv: 'temp basal måste vara synlig för denna rapport'
|
||||
,de: 'temporäre Basalraten müssen für diesen Report sichtbar sein'
|
||||
,fi: 'tämä raportti vaatii, että basaalien piirto on päällä'
|
||||
,he: 'חובה לאפשר רמה בזלית זמנית כדי לרות דוח זה'
|
||||
,bg: 'временните базали трябва да са показани за да се покаже тази това'
|
||||
,hr: 'temp bazali moraju biti prikazani kako bi se vidio ovaj izvještaj'
|
||||
,he: 'חובה לאפשר רמה בזלית זמנית כדי לרות דוח זה'
|
||||
@@ -1469,7 +1467,6 @@ function init() {
|
||||
}
|
||||
,'Weekly success' : {
|
||||
cs: 'Statistika po týdnech'
|
||||
,he: 'הצלחה שבועית'
|
||||
,de: 'Wöchentlicher Erfolg'
|
||||
,es: 'Resultados semanales'
|
||||
,fr: 'Résultat hebdomadaire'
|
||||
@@ -1747,7 +1744,6 @@ function init() {
|
||||
cs: 'Normální'
|
||||
,de: 'Normal'
|
||||
,es: 'Normal'
|
||||
,he: 'נורמלי '
|
||||
,fr: 'Normale'
|
||||
,el: 'Εντός Στόχου'
|
||||
,pt: 'Normal'
|
||||
@@ -1871,7 +1867,6 @@ function init() {
|
||||
}
|
||||
,'Glucose Percentile report' : {
|
||||
cs: 'Tabulka percentil glykémií'
|
||||
,he: 'דוח אחוזוני גלוקוזה'
|
||||
,de: 'Glukose-Perzentil Bericht'
|
||||
,es: 'Informe de percetiles de glucemia'
|
||||
,fr: 'Rapport percentiles Glycémie'
|
||||
@@ -2196,7 +2191,6 @@ function init() {
|
||||
}
|
||||
,'Weekly Success' : {
|
||||
cs: 'Týdenní úspěšnost'
|
||||
,he: 'הצלחה שבועית '
|
||||
,de: 'Wöchtlicher Erfolg'
|
||||
,es: 'Resultados semanales'
|
||||
,fr: 'Réussite hebdomadaire'
|
||||
@@ -2263,7 +2257,6 @@ function init() {
|
||||
,dk: 'Anvender gemt API-nøgle'
|
||||
,fi: 'Tallennettu salainen API-tarkiste käytössä'
|
||||
,nb: 'Bruker lagret API nøkkel'
|
||||
,he: 'עורך אוכל'
|
||||
,pl: 'Korzystając z zapisanego poufnego hasha API'
|
||||
,ru: 'Применение сохраненного пароля API'
|
||||
,sk: 'Používam uložený API hash heslo'
|
||||
@@ -2275,7 +2268,6 @@ function init() {
|
||||
}
|
||||
,'No API secret hash stored yet. You need to enter API secret.' : {
|
||||
cs: 'Není uložený žádný hash API hesla. Musíte zadat API heslo.'
|
||||
,he: 'הכנס את סיסמת ממשק תכנות יישומים הסודית'
|
||||
,de: 'Keine API-Prüfsumme gespeichert. Bitte API-Prüfsumme eingeben.'
|
||||
,es: 'No se ha almacenado ningún hash todavía. Debe introducir su secreto API.'
|
||||
,fr: 'Pas de secret API existant. Vous devez en entrer un.'
|
||||
@@ -2302,7 +2294,6 @@ function init() {
|
||||
}
|
||||
,'Database loaded' : {
|
||||
cs: 'Databáze načtena'
|
||||
,he: 'אגר מידע נטען '
|
||||
,de: 'Datenbank geladen'
|
||||
,es: 'Base de datos cargada'
|
||||
,fr: 'Base de données chargée'
|
||||
@@ -2496,7 +2487,6 @@ function init() {
|
||||
,pl: 'IG'
|
||||
,ru: 'ГИ'
|
||||
,sk: 'GI'
|
||||
,he: 'GI'
|
||||
,nl: 'Glycemische index '
|
||||
,ko: '혈당 지수'
|
||||
,tr: 'GI-Glisemik İndeks'
|
||||
@@ -2638,7 +2628,6 @@ function init() {
|
||||
,ro: 'Cheia API trebuie să aibă mai mult de 12 caractere'
|
||||
,bg: 'Вашата АPI парола трябва да е дълга поне 12 символа'
|
||||
,hr: 'Vaš tajni API mora sadržavati barem 12 znakova'
|
||||
,he:' הסיסמא הסודית חייבת להיות באורך של 12 תווים לפחות'
|
||||
,sv: 'Hemlig API-nyckel måsta innehålla 12 tecken'
|
||||
,it: 'il vostro API secreto deve essere lungo almeno 12 caratteri'
|
||||
,ja: 'APIシークレットは12文字以上の長さが必要です'
|
||||
@@ -2673,7 +2662,6 @@ function init() {
|
||||
,nb: 'Ugyldig API nøkkel'
|
||||
,pl: 'Błędny klucz API'
|
||||
,ru: 'Плохой пароль API'
|
||||
,he: ' הסיסמא הסודית אינה חוקית'
|
||||
,sk: 'Nesprávne API heslo'
|
||||
,nl: 'Onjuist API wachtwoord'
|
||||
,ko: '잘못된 API secret'
|
||||
@@ -2699,7 +2687,6 @@ function init() {
|
||||
,fi: 'API salaisuus talletettu'
|
||||
,nb: 'API nøkkel lagret'
|
||||
,pl: 'Poufne klucz API zapisane'
|
||||
,he: ' הסיסמא הסודית נשמרה'
|
||||
,ru: 'Хэш пароля API сохранен'
|
||||
,sk: 'Hash API hesla uložený'
|
||||
,nl: 'API wachtwoord opgeslagen'
|
||||
@@ -2750,7 +2737,6 @@ function init() {
|
||||
,dk: 'Ikke indlæst'
|
||||
,fi: 'Ei ladattu'
|
||||
,nb: 'Ikke lest'
|
||||
,he: 'לא נטען'
|
||||
,pl: 'Nie załadowany'
|
||||
,ru: 'Не загружено'
|
||||
,sk: 'Nenačítaný'
|
||||
@@ -2773,7 +2759,6 @@ function init() {
|
||||
,sv: 'Födoämneseditor'
|
||||
,it: 'NS - Database Alimenti'
|
||||
,ja: '食事編集'
|
||||
,he: 'עורך מזון'
|
||||
,dk: 'Mad editor'
|
||||
,fi: 'Muokkaa ruokia'
|
||||
,nb: 'Mat editor'
|
||||
@@ -2973,7 +2958,6 @@ function init() {
|
||||
,ro: 'Cheia API'
|
||||
,bg: 'Твоята API парола'
|
||||
,hr: 'Vaš tajni API'
|
||||
,he: 'הסיסמא הסודית שלך'
|
||||
,it: 'Il tuo API secreto'
|
||||
,ja: 'あなたのAPI Secret'
|
||||
,dk: 'Din API-nøgle'
|
||||
@@ -3005,7 +2989,6 @@ function init() {
|
||||
,dk: 'Gemme hash på denne computer (brug kun på privat computer)'
|
||||
,fi: 'Tallenna avain tälle tietokoneelle (käytä vain omalla tietokoneellasi)'
|
||||
,nb: 'Lagre hash på denne pc (bruk kun på privat pc)'
|
||||
,he:'שמור סיסמא הסודית על המחשב ( יש להשתמש רק על מחשב פרטי)'
|
||||
,pl: 'Zapisz na tym komputerze (korzystaj tylko na komputerach prywatnych)'
|
||||
,ru: 'Сохранить хеш на этом ПК (только для личных компьютеров)'
|
||||
,sk: 'Uložiť hash na tomto počítači (Používajte iba na súkromných počítačoch)'
|
||||
@@ -7692,7 +7675,7 @@ function init() {
|
||||
cs: 'Odstraňování záznamů ...'
|
||||
,he: 'מוחק רשומות ... '
|
||||
,nb: 'Fjerner elementer...'
|
||||
,fr: 'Effacement d\événements...'
|
||||
,fr: 'Effacement dévénements...'
|
||||
,ro: 'Se șterg înregistrările...'
|
||||
,el: 'Αφαίρεση Εγγραφών'
|
||||
,de: 'Entferne Einträge ...'
|
||||
@@ -7714,29 +7697,7 @@ function init() {
|
||||
,zh_tw: '正在刪除記錄...'
|
||||
}
|
||||
,'%1 records deleted' : {
|
||||
cs: '%1 records deleted'
|
||||
,he: '%1 records deleted'
|
||||
,nb: '%1 records deleted'
|
||||
,fr: '%1 records deleted'
|
||||
,ro: '%1 records deleted'
|
||||
,el: '%1 records deleted'
|
||||
,de: '%1 records deleted'
|
||||
,es: '%1 records deleted'
|
||||
,dk: '%1 records deleted'
|
||||
,sv: '%1 records deleted'
|
||||
,bg: '%1 records deleted'
|
||||
,hr: 'obrisano %1 zapisa'
|
||||
,it: '%1 records deleted'
|
||||
,fi: '%1 records deleted'
|
||||
,pl: '%1 records deleted'
|
||||
,pt: '%1 records deleted'
|
||||
,ru: '%1 records deleted'
|
||||
,sk: '%1 records deleted'
|
||||
,nl: '%1 records deleted'
|
||||
,ko: '%1 records deleted'
|
||||
,tr: '%1 records deleted'
|
||||
,zh_cn: '%1 records deleted'
|
||||
,zh_tw: '%1 records deleted'
|
||||
hr: 'obrisano %1 zapisa'
|
||||
}
|
||||
,'Clean Mongo status database' : {
|
||||
cs: 'Vyčištění Mongo databáze statusů'
|
||||
@@ -7906,379 +7867,49 @@ function init() {
|
||||
,zh_cn: '所有记录已经被清除'
|
||||
}
|
||||
,'Delete all documents from devicestatus collection older than 30 days' : {
|
||||
cs: 'Delete all documents from devicestatus collection older than 30 days'
|
||||
,he: 'Delete all documents from devicestatus collection older than 30 days'
|
||||
,nb: 'Delete all documents from devicestatus collection older than 30 days'
|
||||
,fr: 'Delete all documents from devicestatus collection older than 30 days'
|
||||
,ro: 'Delete all documents from devicestatus collection older than 30 days'
|
||||
,el: 'Delete all documents from devicestatus collection older than 30 days'
|
||||
,de: 'Delete all documents from devicestatus collection older than 30 days'
|
||||
,es: 'Delete all documents from devicestatus collection older than 30 days'
|
||||
,dk: 'Delete all documents from devicestatus collection older than 30 days'
|
||||
,sv: 'Delete all documents from devicestatus collection older than 30 days'
|
||||
,bg: 'Delete all documents from devicestatus collection older than 30 days'
|
||||
,hr: 'Obriši sve statuse starije od 30 dana'
|
||||
,it: 'Delete all documents from devicestatus collection older than 30 days'
|
||||
,fi: 'Delete all documents from devicestatus collection older than 30 days'
|
||||
,pl: 'Delete all documents from devicestatus collection older than 30 days'
|
||||
,pt: 'Delete all documents from devicestatus collection older than 30 days'
|
||||
,ru: 'Delete all documents from devicestatus collection older than 30 days'
|
||||
,sk: 'Delete all documents from devicestatus collection older than 30 days'
|
||||
,nl: 'Delete all documents from devicestatus collection older than 30 days'
|
||||
,ko: 'Delete all documents from devicestatus collection older than 30 days'
|
||||
,tr: 'Delete all documents from devicestatus collection older than 30 days'
|
||||
,zh_cn: 'Delete all documents from devicestatus collection older than 30 days'
|
||||
,zh_tw: 'Delete all documents from devicestatus collection older than 30 days'
|
||||
hr: 'Obriši sve statuse starije od 30 dana'
|
||||
}
|
||||
,'Number of Days to Keep:' : {
|
||||
cs: 'Number of Days to Keep:'
|
||||
,he: 'Number of Days to Keep:'
|
||||
,nb: 'Number of Days to Keep:'
|
||||
,fr: 'Number of Days to Keep:'
|
||||
,ro: 'Number of Days to Keep:'
|
||||
,el: 'Number of Days to Keep:'
|
||||
,de: 'Number of Days to Keep:'
|
||||
,es: 'Number of Days to Keep:'
|
||||
,dk: 'Number of Days to Keep:'
|
||||
,sv: 'Number of Days to Keep:'
|
||||
,bg: 'Number of Days to Keep:'
|
||||
,hr: 'Broj dana za sačuvati:'
|
||||
,it: 'Number of Days to Keep:'
|
||||
,fi: 'Number of Days to Keep:'
|
||||
,pl: 'Number of Days to Keep:'
|
||||
,pt: 'Number of Days to Keep:'
|
||||
,ru: 'Number of Days to Keep:'
|
||||
,sk: 'Number of Days to Keep:'
|
||||
,nl: 'Number of Days to Keep:'
|
||||
,ko: 'Number of Days to Keep:'
|
||||
,tr: 'Number of Days to Keep:'
|
||||
,zh_cn: 'Number of Days to Keep:'
|
||||
,zh_tw: 'Number of Days to Keep:'
|
||||
hr: 'Broj dana za sačuvati:'
|
||||
}
|
||||
,'This task removes all documents from devicestatus collection that are older than 30 days. Useful when uploader battery status is not properly updated.' : {
|
||||
cs: 'This task removes all documents from devicestatus collection that are older than 30 days. Useful when uploader battery status is not properly updated.'
|
||||
,he: 'This task removes all documents from devicestatus collection that are older than 30 days. Useful when uploader battery status is not properly updated.'
|
||||
,nb: 'This task removes all documents from devicestatus collection that are older than 30 days. Useful when uploader battery status is not properly updated.'
|
||||
,fr: 'This task removes all documents from devicestatus collection that are older than 30 days. Useful when uploader battery status is not properly updated.'
|
||||
,ro: 'This task removes all documents from devicestatus collection that are older than 30 days. Useful when uploader battery status is not properly updated.'
|
||||
,el: 'This task removes all documents from devicestatus collection that are older than 30 days. Useful when uploader battery status is not properly updated.'
|
||||
,de: 'This task removes all documents from devicestatus collection that are older than 30 days. Useful when uploader battery status is not properly updated.'
|
||||
,es: 'This task removes all documents from devicestatus collection that are older than 30 days. Useful when uploader battery status is not properly updated.'
|
||||
,dk: 'This task removes all documents from devicestatus collection that are older than 30 days. Useful when uploader battery status is not properly updated.'
|
||||
,sv: 'This task removes all documents from devicestatus collection that are older than 30 days. Useful when uploader battery status is not properly updated.'
|
||||
,bg: 'This task removes all documents from devicestatus collection that are older than 30 days. Useful when uploader battery status is not properly updated.'
|
||||
,hr: 'Ovo uklanja sve statuse starije od 30 dana. Korisno kada se status baterije uploadera ne osvježava ispravno.'
|
||||
,it: 'This task removes all documents from devicestatus collection that are older than 30 days. Useful when uploader battery status is not properly updated.'
|
||||
,fi: 'This task removes all documents from devicestatus collection that are older than 30 days. Useful when uploader battery status is not properly updated.'
|
||||
,pl: 'This task removes all documents from devicestatus collection that are older than 30 days. Useful when uploader battery status is not properly updated.'
|
||||
,pt: 'This task removes all documents from devicestatus collection that are older than 30 days. Useful when uploader battery status is not properly updated.'
|
||||
,ru: 'This task removes all documents from devicestatus collection that are older than 30 days. Useful when uploader battery status is not properly updated.'
|
||||
,sk: 'This task removes all documents from devicestatus collection that are older than 30 days. Useful when uploader battery status is not properly updated.'
|
||||
,nl: 'This task removes all documents from devicestatus collection that are older than 30 days. Useful when uploader battery status is not properly updated.'
|
||||
,ko: 'This task removes all documents from devicestatus collection that are older than 30 days. Useful when uploader battery status is not properly updated.'
|
||||
,tr: 'This task removes all documents from devicestatus collection that are older than 30 days. Useful when uploader battery status is not properly updated.'
|
||||
,zh_cn: 'This task removes all documents from devicestatus collection that are older than 30 days. Useful when uploader battery status is not properly updated.'
|
||||
,zh_tw: 'This task removes all documents from devicestatus collection that are older than 30 days. Useful when uploader battery status is not properly updated.'
|
||||
hr: 'Ovo uklanja sve statuse starije od 30 dana. Korisno kada se status baterije uploadera ne osvježava ispravno.'
|
||||
}
|
||||
,'Delete old documents from devicestatus collection?' : {
|
||||
cs: 'Delete old documents from devicestatus collection?'
|
||||
,he: 'Delete old documents from devicestatus collection?'
|
||||
,nb: 'Delete old documents from devicestatus collection?'
|
||||
,fr: 'Delete old documents from devicestatus collection?'
|
||||
,ro: 'Delete old documents from devicestatus collection?'
|
||||
,el: 'Delete old documents from devicestatus collection?'
|
||||
,de: 'Delete old documents from devicestatus collection?'
|
||||
,es: 'Delete old documents from devicestatus collection?'
|
||||
,dk: 'Delete old documents from devicestatus collection?'
|
||||
,sv: 'Delete old documents from devicestatus collection?'
|
||||
,bg: 'Delete old documents from devicestatus collection?'
|
||||
,hr: 'Obriši stare statuse'
|
||||
,it: 'Delete old documents from devicestatus collection?'
|
||||
,fi: 'Delete old documents from devicestatus collection?'
|
||||
,pl: 'Delete old documents from devicestatus collection?'
|
||||
,pt: 'Delete old documents from devicestatus collection?'
|
||||
,ru: 'Delete old documents from devicestatus collection?'
|
||||
,sk: 'Delete old documents from devicestatus collection?'
|
||||
,nl: 'Delete old documents from devicestatus collection?'
|
||||
,ko: 'Delete old documents from devicestatus collection?'
|
||||
,tr: 'Delete old documents from devicestatus collection?'
|
||||
,zh_cn: 'Delete old documents from devicestatus collection?'
|
||||
,zh_tw: 'Delete old documents from devicestatus collection?'
|
||||
hr: 'Obriši stare statuse'
|
||||
}
|
||||
,'Clean Mongo entries (glucose entries) database' : {
|
||||
cs: 'Clean Mongo entries (glucose entries) database'
|
||||
,he: 'Clean Mongo entries (glucose entries) database'
|
||||
,nb: 'Clean Mongo entries (glucose entries) database'
|
||||
,fr: 'Clean Mongo entries (glucose entries) database'
|
||||
,ro: 'Clean Mongo entries (glucose entries) database'
|
||||
,el: 'Clean Mongo entries (glucose entries) database'
|
||||
,de: 'Clean Mongo entries (glucose entries) database'
|
||||
,es: 'Clean Mongo entries (glucose entries) database'
|
||||
,dk: 'Clean Mongo entries (glucose entries) database'
|
||||
,sv: 'Clean Mongo entries (glucose entries) database'
|
||||
,bg: 'Clean Mongo entries (glucose entries) database'
|
||||
,hr: 'Obriši GUK zapise iz baze'
|
||||
,it: 'Clean Mongo entries (glucose entries) database'
|
||||
,fi: 'Clean Mongo entries (glucose entries) database'
|
||||
,pl: 'Clean Mongo entries (glucose entries) database'
|
||||
,pt: 'Clean Mongo entries (glucose entries) database'
|
||||
,ru: 'Clean Mongo entries (glucose entries) database'
|
||||
,sk: 'Clean Mongo entries (glucose entries) database'
|
||||
,nl: 'Clean Mongo entries (glucose entries) database'
|
||||
,ko: 'Clean Mongo entries (glucose entries) database'
|
||||
,tr: 'Clean Mongo entries (glucose entries) database'
|
||||
,zh_cn: 'Clean Mongo entries (glucose entries) database'
|
||||
,zh_tw: 'Clean Mongo entries (glucose entries) database'
|
||||
hr: 'Obriši GUK zapise iz baze'
|
||||
}
|
||||
,'Delete all documents from entries collection older than 180 days' : {
|
||||
cs: 'Delete all documents from entries collection older than 180 days'
|
||||
,he: 'Delete all documents from entries collection older than 180 days'
|
||||
,nb: 'Delete all documents from entries collection older than 180 days'
|
||||
,fr: 'Delete all documents from entries collection older than 180 days'
|
||||
,ro: 'Delete all documents from entries collection older than 180 days'
|
||||
,el: 'Delete all documents from entries collection older than 180 days'
|
||||
,de: 'Delete all documents from entries collection older than 180 days'
|
||||
,es: 'Delete all documents from entries collection older than 180 days'
|
||||
,dk: 'Delete all documents from entries collection older than 180 days'
|
||||
,sv: 'Delete all documents from entries collection older than 180 days'
|
||||
,bg: 'Delete all documents from entries collection older than 180 days'
|
||||
,hr: 'Obriši sve zapise starije od 180 dana'
|
||||
,it: 'Delete all documents from entries collection older than 180 days'
|
||||
,fi: 'Delete all documents from entries collection older than 180 days'
|
||||
,pl: 'Delete all documents from entries collection older than 180 days'
|
||||
,pt: 'Delete all documents from entries collection older than 180 days'
|
||||
,ru: 'Delete all documents from entries collection older than 180 days'
|
||||
,sk: 'Delete all documents from entries collection older than 180 days'
|
||||
,nl: 'Delete all documents from entries collection older than 180 days'
|
||||
,ko: 'Delete all documents from entries collection older than 180 days'
|
||||
,tr: 'Delete all documents from entries collection older than 180 days'
|
||||
,zh_cn: 'Delete all documents from entries collection older than 180 days'
|
||||
,zh_tw: 'Delete all documents from entries collection older than 180 days'
|
||||
hr: 'Obriši sve zapise starije od 180 dana'
|
||||
}
|
||||
,'This task removes all documents from entries collection that are older than 180 days. Useful when uploader battery status is not properly updated.' : {
|
||||
cs: 'This task removes all documents from entries collection that are older than 180 days. Useful when uploader battery status is not properly updated.'
|
||||
,he: 'This task removes all documents from entries collection that are older than 180 days. Useful when uploader battery status is not properly updated.'
|
||||
,nb: 'This task removes all documents from entries collection that are older than 180 days. Useful when uploader battery status is not properly updated.'
|
||||
,fr: 'This task removes all documents from entries collection that are older than 180 days. Useful when uploader battery status is not properly updated.'
|
||||
,ro: 'This task removes all documents from entries collection that are older than 180 days. Useful when uploader battery status is not properly updated.'
|
||||
,el: 'This task removes all documents from entries collection that are older than 180 days. Useful when uploader battery status is not properly updated.'
|
||||
,de: 'This task removes all documents from entries collection that are older than 180 days. Useful when uploader battery status is not properly updated.'
|
||||
,es: 'This task removes all documents from entries collection that are older than 180 days. Useful when uploader battery status is not properly updated.'
|
||||
,dk: 'This task removes all documents from entries collection that are older than 180 days. Useful when uploader battery status is not properly updated.'
|
||||
,sv: 'This task removes all documents from entries collection that are older than 180 days. Useful when uploader battery status is not properly updated.'
|
||||
,bg: 'This task removes all documents from entries collection that are older than 180 days. Useful when uploader battery status is not properly updated.'
|
||||
,hr: 'Ovo briše sve zapise starije od 180 dana. Korisno kada se status baterije uploadera ne osvježava.'
|
||||
,it: 'This task removes all documents from entries collection that are older than 180 days. Useful when uploader battery status is not properly updated.'
|
||||
,fi: 'This task removes all documents from entries collection that are older than 180 days. Useful when uploader battery status is not properly updated.'
|
||||
,pl: 'This task removes all documents from entries collection that are older than 180 days. Useful when uploader battery status is not properly updated.'
|
||||
,pt: 'This task removes all documents from entries collection that are older than 180 days. Useful when uploader battery status is not properly updated.'
|
||||
,ru: 'This task removes all documents from entries collection that are older than 180 days. Useful when uploader battery status is not properly updated.'
|
||||
,sk: 'This task removes all documents from entries collection that are older than 180 days. Useful when uploader battery status is not properly updated.'
|
||||
,nl: 'This task removes all documents from entries collection that are older than 180 days. Useful when uploader battery status is not properly updated.'
|
||||
,ko: 'This task removes all documents from entries collection that are older than 180 days. Useful when uploader battery status is not properly updated.'
|
||||
,tr: 'This task removes all documents from entries collection that are older than 180 days. Useful when uploader battery status is not properly updated.'
|
||||
,zh_cn: 'This task removes all documents from entries collection that are older than 180 days. Useful when uploader battery status is not properly updated.'
|
||||
,zh_tw: 'This task removes all documents from entries collection that are older than 180 days. Useful when uploader battery status is not properly updated.'
|
||||
hr: 'Ovo briše sve zapise starije od 180 dana. Korisno kada se status baterije uploadera ne osvježava.'
|
||||
}
|
||||
,'Delete old documents' : {
|
||||
cs: 'Delete old documents'
|
||||
,he: 'Delete old documents'
|
||||
,nb: 'Delete old documents'
|
||||
,fr: 'Delete old documents'
|
||||
,ro: 'Delete old documents'
|
||||
,el: 'Delete old documents'
|
||||
,de: 'Delete old documents'
|
||||
,es: 'Delete old documents'
|
||||
,dk: 'Delete old documents'
|
||||
,sv: 'Delete old documents'
|
||||
,bg: 'Delete old documents'
|
||||
,hr: 'Obriši stare zapise'
|
||||
,it: 'Delete old documents'
|
||||
,fi: 'Delete old documents'
|
||||
,pl: 'Delete old documents'
|
||||
,pt: 'Delete old documents'
|
||||
,ru: 'Delete old documents'
|
||||
,sk: 'Delete old documents'
|
||||
,nl: 'Delete old documents'
|
||||
,ko: 'Delete old documents'
|
||||
,tr: 'Delete old documents'
|
||||
,zh_cn: 'Delete old documents'
|
||||
,zh_tw: 'Delete old documents'
|
||||
hr: 'Obriši stare zapise'
|
||||
}
|
||||
,'Delete old documents from entries collection?' : {
|
||||
cs: 'Delete old documents from entries collection?'
|
||||
,he: 'Delete old documents from entries collection?'
|
||||
,nb: 'Delete old documents from entries collection?'
|
||||
,fr: 'Delete old documents from entries collection?'
|
||||
,ro: 'Delete old documents from entries collection?'
|
||||
,el: 'Delete old documents from entries collection?'
|
||||
,de: 'Delete old documents from entries collection?'
|
||||
,es: 'Delete old documents from entries collection?'
|
||||
,dk: 'Delete old documents from entries collection?'
|
||||
,sv: 'Delete old documents from entries collection?'
|
||||
,bg: 'Delete old documents from entries collection?'
|
||||
,hr: 'Obriši stare zapise?'
|
||||
,it: 'Delete old documents from entries collection?'
|
||||
,fi: 'Delete old documents from entries collection?'
|
||||
,pl: 'Delete old documents from entries collection?'
|
||||
,pt: 'Delete old documents from entries collection?'
|
||||
,ru: 'Delete old documents from entries collection?'
|
||||
,sk: 'Delete old documents from entries collection?'
|
||||
,nl: 'Delete old documents from entries collection?'
|
||||
,ko: 'Delete old documents from entries collection?'
|
||||
,tr: 'Delete old documents from entries collection?'
|
||||
,zh_cn: 'Delete old documents from entries collection?'
|
||||
,zh_tw: 'Delete old documents from entries collection?'
|
||||
hr: 'Obriši stare zapise?'
|
||||
}
|
||||
,'%1 is not a valid number' : {
|
||||
cs: '%1 is not a valid number'
|
||||
,he: '%1 is not a valid number'
|
||||
,nb: '%1 is not a valid number'
|
||||
,fr: '%1 is not a valid number'
|
||||
,ro: '%1 is not a valid number'
|
||||
,el: '%1 is not a valid number'
|
||||
,de: '%1 is not a valid number'
|
||||
,es: '%1 is not a valid number'
|
||||
,dk: '%1 is not a valid number'
|
||||
,sv: '%1 is not a valid number'
|
||||
,bg: '%1 is not a valid number'
|
||||
,hr: '%1 nije valjan broj'
|
||||
,it: '%1 is not a valid number'
|
||||
,fi: '%1 is not a valid number'
|
||||
,pl: '%1 is not a valid number'
|
||||
,pt: '%1 is not a valid number'
|
||||
,ru: '%1 is not a valid number'
|
||||
,sk: '%1 is not a valid number'
|
||||
,nl: '%1 is not a valid number'
|
||||
,ko: '%1 is not a valid number'
|
||||
,tr: '%1 is not a valid number'
|
||||
,zh_cn: '%1 is not a valid number'
|
||||
,zh_tw: '%1 is not a valid number'
|
||||
hr: '%1 nije valjan broj'
|
||||
}
|
||||
,'%1 is not a valid number - must be more than 2' : {
|
||||
cs: '%1 is not a valid number - must be more than 2'
|
||||
,he: '%1 is not a valid number - must be more than 2'
|
||||
,nb: '%1 is not a valid number - must be more than 2'
|
||||
,fr: '%1 is not a valid number - must be more than 2'
|
||||
,ro: '%1 is not a valid number - must be more than 2'
|
||||
,el: '%1 is not a valid number - must be more than 2'
|
||||
,de: '%1 is not a valid number - must be more than 2'
|
||||
,es: '%1 is not a valid number - must be more than 2'
|
||||
,dk: '%1 is not a valid number - must be more than 2'
|
||||
,sv: '%1 is not a valid number - must be more than 2'
|
||||
,bg: '%1 is not a valid number - must be more than 2'
|
||||
,hr: '%1 nije valjan broj - mora biti veći od 2'
|
||||
,it: '%1 is not a valid number - must be more than 2'
|
||||
,fi: '%1 is not a valid number - must be more than 2'
|
||||
,pl: '%1 is not a valid number - must be more than 2'
|
||||
,pt: '%1 is not a valid number - must be more than 2'
|
||||
,ru: '%1 is not a valid number - must be more than 2'
|
||||
,sk: '%1 is not a valid number - must be more than 2'
|
||||
,nl: '%1 is not a valid number - must be more than 2'
|
||||
,ko: '%1 is not a valid number - must be more than 2'
|
||||
,tr: '%1 is not a valid number - must be more than 2'
|
||||
,zh_cn: '%1 is not a valid number - must be more than 2'
|
||||
,zh_tw: '%1 is not a valid number - must be more than 2'
|
||||
hr: '%1 nije valjan broj - mora biti veći od 2'
|
||||
}
|
||||
,'Clean Mongo treatments database' : {
|
||||
cs: 'Clean Mongo treatments database'
|
||||
,he: 'Clean Mongo treatments database'
|
||||
,nb: 'Clean Mongo treatments database'
|
||||
,fr: 'Clean Mongo treatments database'
|
||||
,ro: 'Clean Mongo treatments database'
|
||||
,el: 'Clean Mongo treatments database'
|
||||
,de: 'Clean Mongo treatments database'
|
||||
,es: 'Clean Mongo treatments database'
|
||||
,dk: 'Clean Mongo treatments database'
|
||||
,sv: 'Clean Mongo treatments database'
|
||||
,bg: 'Clean Mongo treatments database'
|
||||
,hr: 'Obriši tretmane iz baze'
|
||||
,it: 'Clean Mongo treatments database'
|
||||
,fi: 'Clean Mongo treatments database'
|
||||
,pl: 'Clean Mongo treatments database'
|
||||
,pt: 'Clean Mongo treatments database'
|
||||
,ru: 'Clean Mongo treatments database'
|
||||
,sk: 'Clean Mongo treatments database'
|
||||
,nl: 'Clean Mongo treatments database'
|
||||
,ko: 'Clean Mongo treatments database'
|
||||
,tr: 'Clean Mongo treatments database'
|
||||
,zh_cn: 'Clean Mongo treatments database'
|
||||
,zh_tw: 'Clean Mongo treatments database'
|
||||
hr: 'Obriši tretmane iz baze'
|
||||
}
|
||||
,'Delete all documents from treatments collection older than 180 days' : {
|
||||
cs: 'Delete all documents from treatments collection older than 180 days'
|
||||
,he: 'Delete all documents from treatments collection older than 180 days'
|
||||
,nb: 'Delete all documents from treatments collection older than 180 days'
|
||||
,fr: 'Delete all documents from treatments collection older than 180 days'
|
||||
,ro: 'Delete all documents from treatments collection older than 180 days'
|
||||
,el: 'Delete all documents from treatments collection older than 180 days'
|
||||
,de: 'Delete all documents from treatments collection older than 180 days'
|
||||
,es: 'Delete all documents from treatments collection older than 180 days'
|
||||
,dk: 'Delete all documents from treatments collection older than 180 days'
|
||||
,sv: 'Delete all documents from treatments collection older than 180 days'
|
||||
,bg: 'Delete all documents from treatments collection older than 180 days'
|
||||
,hr: 'Obriši tretmane starije od 180 dana iz baze'
|
||||
,it: 'Delete all documents from treatments collection older than 180 days'
|
||||
,fi: 'Delete all documents from treatments collection older than 180 days'
|
||||
,pl: 'Delete all documents from treatments collection older than 180 days'
|
||||
,pt: 'Delete all documents from treatments collection older than 180 days'
|
||||
,ru: 'Delete all documents from treatments collection older than 180 days'
|
||||
,sk: 'Delete all documents from treatments collection older than 180 days'
|
||||
,nl: 'Delete all documents from treatments collection older than 180 days'
|
||||
,ko: 'Delete all documents from treatments collection older than 180 days'
|
||||
,tr: 'Delete all documents from treatments collection older than 180 days'
|
||||
,zh_cn: 'Delete all documents from treatments collection older than 180 days'
|
||||
,zh_tw: 'Delete all documents from treatments collection older than 180 days'
|
||||
hr: 'Obriši tretmane starije od 180 dana iz baze'
|
||||
}
|
||||
,'This task removes all documents from treatments collection that are older than 180 days. Useful when uploader battery status is not properly updated.' : {
|
||||
cs: 'This task removes all documents from treatments collection that are older than 180 days. Useful when uploader battery status is not properly updated.'
|
||||
,he: 'This task removes all documents from treatments collection that are older than 180 days. Useful when uploader battery status is not properly updated.'
|
||||
,nb: 'This task removes all documents from treatments collection that are older than 180 days. Useful when uploader battery status is not properly updated.'
|
||||
,fr: 'This task removes all documents from treatments collection that are older than 180 days. Useful when uploader battery status is not properly updated.'
|
||||
,ro: 'This task removes all documents from treatments collection that are older than 180 days. Useful when uploader battery status is not properly updated.'
|
||||
,el: 'This task removes all documents from treatments collection that are older than 180 days. Useful when uploader battery status is not properly updated.'
|
||||
,de: 'This task removes all documents from treatments collection that are older than 180 days. Useful when uploader battery status is not properly updated.'
|
||||
,es: 'This task removes all documents from treatments collection that are older than 180 days. Useful when uploader battery status is not properly updated.'
|
||||
,dk: 'This task removes all documents from treatments collection that are older than 180 days. Useful when uploader battery status is not properly updated.'
|
||||
,sv: 'This task removes all documents from treatments collection that are older than 180 days. Useful when uploader battery status is not properly updated.'
|
||||
,bg: 'This task removes all documents from treatments collection that are older than 180 days. Useful when uploader battery status is not properly updated.'
|
||||
,hr: 'Ovo briše sve tretmane starije od 180 dana iz baze. Korisno kada se status baterije uploadera ne osvježava.'
|
||||
,it: 'This task removes all documents from treatments collection that are older than 180 days. Useful when uploader battery status is not properly updated.'
|
||||
,fi: 'This task removes all documents from treatments collection that are older than 180 days. Useful when uploader battery status is not properly updated.'
|
||||
,pl: 'This task removes all documents from treatments collection that are older than 180 days. Useful when uploader battery status is not properly updated.'
|
||||
,pt: 'This task removes all documents from treatments collection that are older than 180 days. Useful when uploader battery status is not properly updated.'
|
||||
,ru: 'This task removes all documents from treatments collection that are older than 180 days. Useful when uploader battery status is not properly updated.'
|
||||
,sk: 'This task removes all documents from treatments collection that are older than 180 days. Useful when uploader battery status is not properly updated.'
|
||||
,nl: 'This task removes all documents from treatments collection that are older than 180 days. Useful when uploader battery status is not properly updated.'
|
||||
,ko: 'This task removes all documents from treatments collection that are older than 180 days. Useful when uploader battery status is not properly updated.'
|
||||
,tr: 'This task removes all documents from treatments collection that are older than 180 days. Useful when uploader battery status is not properly updated.'
|
||||
,zh_cn: 'This task removes all documents from treatments collection that are older than 180 days. Useful when uploader battery status is not properly updated.'
|
||||
,zh_tw: 'This task removes all documents from treatments collection that are older than 180 days. Useful when uploader battery status is not properly updated.'
|
||||
hr: 'Ovo briše sve tretmane starije od 180 dana iz baze. Korisno kada se status baterije uploadera ne osvježava.'
|
||||
}
|
||||
,'Delete old documents from treatments collection?' : {
|
||||
cs: 'Delete old documents from treatments collection?'
|
||||
,he: 'Delete old documents from treatments collection?'
|
||||
,nb: 'Delete old documents from treatments collection?'
|
||||
,fr: 'Delete old documents from treatments collection?'
|
||||
,ro: 'Delete old documents from treatments collection?'
|
||||
,el: 'Delete old documents from treatments collection?'
|
||||
,de: 'Delete old documents from treatments collection?'
|
||||
,es: 'Delete old documents from treatments collection?'
|
||||
,dk: 'Delete old documents from treatments collection?'
|
||||
,sv: 'Delete old documents from treatments collection?'
|
||||
,bg: 'Delete old documents from treatments collection?'
|
||||
,hr: 'Obriši stare tretmane?'
|
||||
,it: 'Delete old documents from treatments collection?'
|
||||
,fi: 'Delete old documents from treatments collection?'
|
||||
,pl: 'Delete old documents from treatments collection?'
|
||||
,pt: 'Delete old documents from treatments collection?'
|
||||
,ru: 'Delete old documents from treatments collection?'
|
||||
,sk: 'Delete old documents from treatments collection?'
|
||||
,nl: 'Delete old documents from treatments collection?'
|
||||
,ko: 'Delete old documents from treatments collection?'
|
||||
,tr: 'Delete old documents from treatments collection?'
|
||||
,zh_cn: 'Delete old documents from treatments collection?'
|
||||
,zh_tw: 'Delete old documents from treatments collection?'
|
||||
hr: 'Obriši stare tretmane?'
|
||||
}
|
||||
,'Admin Tools' : {
|
||||
cs: 'Nástroje pro správu'
|
||||
@@ -10106,7 +9737,7 @@ function init() {
|
||||
}
|
||||
,'Profile is going to be saved in newer format used in Nightscout 0.9.0 and above and will not be usable in older versions anymore.\nAre you sure?' : {
|
||||
cs: 'Profil bude uložen v novějším formátu používaném v Nightscoutu 0.9.0 a novějších. Již nebude použitelný se starší verzí.\nJste si jistý?'
|
||||
,he: 'הפרופיל עומד להישמר בתבנית חדשה יותר בשימוש ב- Nightscout 0.9.0 ומעלה ולא יהיה ניתן להשתמש בו בגרסאות ישנות יותר. \ האם אתה בטוח? '
|
||||
,he: 'הפרופיל עומד להישמר בתבנית חדשה יותר בשימוש ב- Nightscout 0.9.0 ומעלה ולא יהיה ניתן להשתמש בו בגרסאות ישנות יותר. \n האם אתה בטוח? '
|
||||
,el: 'Το προφίλ πρόκειται να αποθηκευτεί με τη νέα του μορφή (έκδοση Nighscout 0.9.0 και πάνω) και δεν πρόκειται να μπορεί να χρησιμοποιηθεί σε παλαιότερες εκδόσεις. \nΕίστε σίγουροι?'
|
||||
,fr: 'Le profil va être sauvegardé dans un nouveau format utilisé par Nightscout 0.9.0 et suivants, et il ne pourra plus être utilisé par les versions antérieures. \nÊtes-vous sûr?'
|
||||
,ro: 'Profilul va fi salvat într-un format nou, folosit în Nightscout 0.9.0 și superior și nu va mai fi posibilă folosirea pentru versiunile mai vechi.\nSunteți de acord?'
|
||||
@@ -10130,7 +9761,7 @@ function init() {
|
||||
}
|
||||
,'Wrong profile setting.\nNo profile defined to displayed time.\nRedirecting to profile editor to create new profile.' : {
|
||||
cs: 'Chybě nastavený profil.\nNení definovaný žádný platný profil k času zobrazení.\nProvádím přesměrování na editor profilu.'
|
||||
,he: 'הגדרת פרופיל שגוי. \ N פרופיל מוגדר לזמן המוצג. מפנה מחדש לעורך פרופיל כדי ליצור פרופיל חדש. '
|
||||
,he: 'הגדרת פרופיל שגוי. \n פרופיל מוגדר לזמן המוצג. מפנה מחדש לעורך פרופיל כדי ליצור פרופיל חדש. '
|
||||
,el: 'Λάθος προφίλ. Παρακαλώ δημιουργήστε ένα νέο προφίλ'
|
||||
,fr: 'Erreur de réglage de profil. \nAucun profil défini pour indiquer l\'heure. \nRedirection vers la création d\'un nouveau profil. '
|
||||
,de: 'Falsche Profileinstellung.\nKein Profil festgelegt zur angezeigten Zeit.\n Weiter zum Profileditor, um ein neues Profil zu erstellen.'
|
||||
@@ -10709,7 +10340,6 @@ function init() {
|
||||
,nb: 'Hver enkelt rolle vil ha en eller flere rettigheter. <em>*</em>-rettigheten er wildcard. Rettigheter settes hierarkisk med <em>:</em> som separator.'
|
||||
,fi: 'Jokaisella roolilla on yksi tai useampia oikeuksia. <em>*</em> on jokeri (tunnistuu kaikkina oikeuksina), oikeudet ovat hierarkia joka käyttää <em>:</em> merkkiä erottimena.'
|
||||
,de: 'Jede Rolle hat eine oder mehrere Berechtigungen. Die <em>*</em> Berechtigung ist ein Platzhalter, Berechtigungen sind hierachrchisch mit <em>:</em> als Separator.'
|
||||
,sv: 'Hver rolle vil have en eller flere rettigheder. <em>*</em> er en joker, rettigheder sættes hierakisk med <em>:</em> som skilletegn.'
|
||||
,es: 'Cada Rol tiene uno o más permisos. El permiso <em>*</em> es un marcador de posición y los permisos son jerárquicos con <em>:</em> como separador.'
|
||||
,pt: 'Cada função terá uma ou mais permissões. A permissão <em>*</em> é um wildcard, permissões são uma hierarquia utilizando <em>*</em> como um separador.'
|
||||
,sk: 'Každá rola má 1 alebo viac oprávnení. Oprávnenie <em>*</em> je zástupný znak, oprávnenia sú hierarchie používajúce <em>:</em> ako oddelovač.'
|
||||
@@ -11994,7 +11624,6 @@ function init() {
|
||||
,sk: 'Nadbytok inzulínu o %1U viac ako je potrebné na dosiahnutie spodnej cieľovej hranice. Neráta sa so sacharidmi.'
|
||||
,ko: '낮은 혈당 목표에 도달하기 위해 필요한 인슐린양보다 %1U의 인슐린 양이 초과 되었고 탄수화물 양이 초과되지 않았습니다.'
|
||||
,it: 'L\'eccesso d\'insulina equivalente %1U più che necessari per raggiungere l\'obiettivo basso, non rappresentano i carboidrati.'
|
||||
,nl: 'Overschot insuline %1U meer dan nodig om het laag doel te bereiken, geen rekening gehouden met KH'
|
||||
,tr: 'Fazla insülin: Karbonhidratları dikkate alınmadan, alt hedefe ulaşmak için gerekenden %1U\'den daha fazla' //???
|
||||
,zh_cn: '胰岛素超过至血糖下限目标所需剂量%1单位,不计算碳水化合物'
|
||||
, pl: 'Nadmiar insuliny, %1J więcej niż potrzeba, aby osiągnąć cel dolnej granicy, nie biorąc pod uwagę węglowodanów'
|
||||
@@ -12427,7 +12056,7 @@ function init() {
|
||||
,sv: 'Applicerad'
|
||||
,nb: 'Satt inn'
|
||||
,fi: 'Asetettu'
|
||||
,es: 'Insertar'
|
||||
,es: 'Insertado'
|
||||
,pt: 'Inserido'
|
||||
,sk: 'Zavedený'
|
||||
,ko: '삽입된'
|
||||
@@ -12453,7 +12082,7 @@ function init() {
|
||||
,nb: 'Nål alder'
|
||||
,fi: 'KIKÄ'
|
||||
,pt: 'ICAT'
|
||||
,es: 'Carb.desde'
|
||||
,es: 'Cánula desde'
|
||||
,sk: 'SET'
|
||||
,ko: '주입세트사용기간'
|
||||
,it: 'CAGE'
|
||||
@@ -12477,7 +12106,7 @@ function init() {
|
||||
,nb: 'Aktive karbohydrater'
|
||||
,fi: 'AH'
|
||||
,pt: 'COB'
|
||||
,es: 'Carbohidratos activos'
|
||||
,es: 'Carb. activos'
|
||||
,sk: 'SACH'
|
||||
,ko: 'COB'
|
||||
,it: 'COB'
|
||||
@@ -14490,6 +14119,7 @@ function init() {
|
||||
}
|
||||
if (options && options.params) {
|
||||
for (var i = 0; i < options.params.length; i++) {
|
||||
// eslint-disable-next-line no-useless-escape
|
||||
var r = new RegExp('\%' + (i+1), 'g');
|
||||
translated = translated.replace(r, options.params[i]);
|
||||
}
|
||||
|
||||
@@ -107,13 +107,8 @@ function init (env, ctx) {
|
||||
return _.last(sorted);
|
||||
};
|
||||
|
||||
notifications.registerGroup = function registerGroup (group) {
|
||||
if (groups.indexOf(group) < 0) {
|
||||
groups.push(group);
|
||||
}
|
||||
};
|
||||
|
||||
notifications.requestNotify = function requestNotify (notify) {
|
||||
// eslint-disable-next-line no-prototype-builtins
|
||||
if (!notify.hasOwnProperty('level') || !notify.title || !notify.message || !notify.plugin) {
|
||||
console.error(new Error('Unable to request notification, since the notify isn\'t complete: ' + JSON.stringify(notify)));
|
||||
return;
|
||||
|
||||
+1
-2
@@ -15,6 +15,7 @@ var AR = [-0.723, 1.716];
|
||||
//TODO: move this to css
|
||||
var AR2_COLOR = 'cyan';
|
||||
|
||||
// eslint-disable-next-line no-unused-vars
|
||||
function init (ctx) {
|
||||
|
||||
var ar2 = {
|
||||
@@ -284,7 +285,6 @@ function pushPoint(result) {
|
||||
return next;
|
||||
}
|
||||
|
||||
|
||||
function ar2Point (next, options) {
|
||||
var step = options.step || 0;
|
||||
var coneFactor = options.coneFactor || 0;
|
||||
@@ -301,7 +301,6 @@ function ar2Point(next, options) {
|
||||
};
|
||||
}
|
||||
|
||||
|
||||
function buildDebug (prop, sbx) {
|
||||
return prop.forecast && {
|
||||
forecast: {
|
||||
|
||||
@@ -8,6 +8,7 @@ function init() {
|
||||
, pluginType: 'drawer'
|
||||
};
|
||||
|
||||
// eslint-disable-next-line no-unused-vars
|
||||
careportal.getEventTypes = function getEventTypes (sbx) {
|
||||
|
||||
//TODO: use sbx and new CAREPORTAL_EVENTTYPE_GROUPS="core temps combo dad sensor site etc"
|
||||
|
||||
+10
-13
@@ -24,7 +24,7 @@ function init(ctx) {
|
||||
|
||||
cob.cobTotal = function cobTotal (treatments, devicestatus, profile, time, spec_profile) {
|
||||
|
||||
if (!profile || !profile.hasData()) {
|
||||
if (!profile || !profile.hasData()) {
|
||||
console.warn('For the COB plugin to function you need a treatment profile');
|
||||
return {};
|
||||
}
|
||||
@@ -219,8 +219,8 @@ function init(ctx) {
|
||||
var netCarbImpact = Math.max(0, rawCarbImpact - liverCarbImpact);
|
||||
var totalImpact = netCarbImpact - insulinImpact;
|
||||
return {
|
||||
netCarbImpact: netCarbImpact,
|
||||
totalImpact: totalImpact
|
||||
netCarbImpact: netCarbImpact
|
||||
, totalImpact: totalImpact
|
||||
};
|
||||
};
|
||||
|
||||
@@ -241,26 +241,23 @@ function init(ctx) {
|
||||
decayedBy.setMinutes(decayedBy.getMinutes() + Math.max(delay, minutesleft) + treatment.carbs / carbs_min);
|
||||
if (delay > minutesleft) {
|
||||
initialCarbs = parseInt(treatment.carbs);
|
||||
}
|
||||
else {
|
||||
} else {
|
||||
initialCarbs = parseInt(treatment.carbs) + minutesleft * carbs_min;
|
||||
}
|
||||
var startDecay = new Date(carbTime);
|
||||
startDecay.setMinutes(carbTime.getMinutes() + delay);
|
||||
if (time < lastDecayedBy || time > startDecay) {
|
||||
isDecaying = 1;
|
||||
}
|
||||
else {
|
||||
} else {
|
||||
isDecaying = 0;
|
||||
}
|
||||
return {
|
||||
initialCarbs: initialCarbs,
|
||||
decayedBy: decayedBy,
|
||||
isDecaying: isDecaying,
|
||||
carbTime: carbTime
|
||||
initialCarbs: initialCarbs
|
||||
, decayedBy: decayedBy
|
||||
, isDecaying: isDecaying
|
||||
, carbTime: carbTime
|
||||
};
|
||||
}
|
||||
else {
|
||||
} else {
|
||||
return '';
|
||||
}
|
||||
};
|
||||
|
||||
@@ -9,8 +9,8 @@ var _map = require('lodash/map');
|
||||
|
||||
function init (ctx) {
|
||||
|
||||
var allPlugins = [],
|
||||
enabledPlugins = [];
|
||||
var allPlugins = []
|
||||
, enabledPlugins = [];
|
||||
|
||||
function plugins (name) {
|
||||
if (name) {
|
||||
@@ -105,16 +105,15 @@ function init(ctx) {
|
||||
enabledPlugins.push(plugin);
|
||||
}
|
||||
});
|
||||
|
||||
};
|
||||
|
||||
plugins.isPluginEnabled = function isPluginEnabled (pluginName) {
|
||||
var p = _.find(enabledPlugins, 'name', pluginName);
|
||||
var p = _find(enabledPlugins, 'name', pluginName);
|
||||
return (p !== null);
|
||||
}
|
||||
|
||||
plugins.getPlugin = function getPlugin (pluginName) {
|
||||
return _.find(enabledPlugins, 'name', pluginName);
|
||||
return _find(enabledPlugins, 'name', pluginName);
|
||||
}
|
||||
|
||||
plugins.eachPlugin = function eachPlugin (f) {
|
||||
|
||||
+3
-9
@@ -262,7 +262,7 @@ function init(ctx) {
|
||||
var canceled = prop.lastEnacted.rate === 0 && prop.lastEnacted.duration === 0;
|
||||
|
||||
var valueParts = [
|
||||
, '<b>Temp Basal' + (canceled ? ' Canceled' : ' Started') + '</b>'
|
||||
'<b>Temp Basal' + (canceled ? ' Canceled' : ' Started') + '</b>'
|
||||
, canceled ? '' : ' ' + prop.lastEnacted.rate.toFixed(2) + 'U/hour for ' + prop.lastEnacted.duration + 'm'
|
||||
, valueString(', ', prop.lastEnacted.reason)
|
||||
];
|
||||
@@ -284,7 +284,9 @@ function init(ctx) {
|
||||
var iob = prop.lastLoop.iob;
|
||||
valueParts = valueParts.concat([
|
||||
', IOB: '
|
||||
|
||||
, sbx.roundInsulinForDisplayFormat(iob.iob) + 'U'
|
||||
|
||||
, iob.basaliob ? ', Basal IOB ' + sbx.roundInsulinForDisplayFormat(iob.basaliob) + 'U' : ''
|
||||
]);
|
||||
}
|
||||
@@ -294,7 +296,6 @@ function init(ctx) {
|
||||
|
||||
function concatCOB (valueParts) {
|
||||
if (prop.lastLoop && prop.lastLoop.cob) {
|
||||
var cob = prop.lastLoop.cob;
|
||||
var cob = prop.lastLoop.cob.cob;
|
||||
cob = Math.round(cob);
|
||||
valueParts = valueParts.concat([
|
||||
@@ -364,12 +365,6 @@ function init(ctx) {
|
||||
if (predicted.values) {
|
||||
points = points.concat(_.map(predicted.values, toPoints(startTime, 0)));
|
||||
}
|
||||
// if (prop.lastPredBGs.IOB) {
|
||||
// points = points.concat(_.map(prop.lastPredBGs.IOB, toPoints(moment, 3000)));
|
||||
// }
|
||||
// if (prop.lastPredBGs.COB) {
|
||||
// points = points.concat(_.map(prop.lastPredBGs.COB, toPoints(moment, 7000)));
|
||||
// }
|
||||
}
|
||||
|
||||
return points;
|
||||
@@ -523,5 +518,4 @@ function init(ctx) {
|
||||
|
||||
}
|
||||
|
||||
|
||||
module.exports = init;
|
||||
|
||||
+32
-9
@@ -27,7 +27,6 @@ function init(ctx) {
|
||||
return _.isEmpty(list) || _.isEmpty(list[0]);
|
||||
}
|
||||
|
||||
|
||||
var fields = cleanList(sbx.extendedSettings.fields);
|
||||
fields = isEmpty(fields) ? ['status-symbol', 'status-label', 'iob', 'meal-assist', 'rssi'] : fields;
|
||||
|
||||
@@ -122,8 +121,7 @@ function init(ctx) {
|
||||
};
|
||||
|
||||
if (moments.notEnacted && (
|
||||
(moments.enacted && moments.notEnacted.isAfter(moments.enacted)) || (!moments.enacted && moments.notEnacted.isAfter(recent)))
|
||||
) {
|
||||
(moments.enacted && moments.notEnacted.isAfter(moments.enacted)) || (!moments.enacted && moments.notEnacted.isAfter(recent)))) {
|
||||
status.symbol = 'x';
|
||||
status.code = 'notenacted';
|
||||
status.label = 'Not Enacted';
|
||||
@@ -240,18 +238,43 @@ function init(ctx) {
|
||||
{
|
||||
val: 'Temporary Target'
|
||||
, name: 'Temporary Target'
|
||||
, bg: false, insulin: false, carbs: false, prebolus: false, duration: true, percent: false, absolute: false, profile: false, split: false
|
||||
, targets: true, reasons: reasonconf
|
||||
, bg: false
|
||||
, insulin: false
|
||||
, carbs: false
|
||||
, prebolus: false
|
||||
, duration: true
|
||||
, percent: false
|
||||
, absolute: false
|
||||
, profile: false
|
||||
, split: false
|
||||
, targets: true
|
||||
, reasons: reasonconf
|
||||
}
|
||||
, {
|
||||
val: 'Temporary Target Cancel'
|
||||
, name: 'Temporary Target Cancel'
|
||||
, bg: false, insulin: false, carbs: false, prebolus: false, duration: false, percent: false, absolute: false, profile: false, split: false
|
||||
, bg: false
|
||||
, insulin: false
|
||||
, carbs: false
|
||||
, prebolus: false
|
||||
, duration: false
|
||||
, percent: false
|
||||
, absolute: false
|
||||
, profile: false
|
||||
, split: false
|
||||
}
|
||||
, {
|
||||
val: 'OpenAPS Offline'
|
||||
, name: 'OpenAPS Offline'
|
||||
, bg: false, insulin: false, carbs: false, prebolus: false, duration: true, percent: false, absolute: false, profile: false, split: false
|
||||
, bg: false
|
||||
, insulin: false
|
||||
, carbs: false
|
||||
, prebolus: false
|
||||
, duration: true
|
||||
, percent: false
|
||||
, absolute: false
|
||||
, profile: false
|
||||
, split: false
|
||||
}
|
||||
];
|
||||
};
|
||||
@@ -464,8 +487,8 @@ function init(ctx) {
|
||||
var response = translate('alexaOpenAPSForecast', {
|
||||
params: [
|
||||
sbx.properties.openaps.lastEventualBG
|
||||
]}
|
||||
);
|
||||
]
|
||||
});
|
||||
next('Loop Forecast', response);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -1,10 +1,6 @@
|
||||
'use strict';
|
||||
|
||||
var levels = require('../levels');
|
||||
var times = require('../times');
|
||||
|
||||
var lastEntryValue;
|
||||
var lastTime;
|
||||
var lastMinutes;
|
||||
var lastEntryTime;
|
||||
|
||||
@@ -78,7 +74,7 @@ function init(ctx) {
|
||||
lastMinutes = timeMinutes;
|
||||
|
||||
var lastEntryString = translate('Last entry {0} minutes ago');
|
||||
var sayIt = lastEntryString.replace('{0}', timeMinutes);
|
||||
sayIt = lastEntryString.replace('{0}', timeMinutes);
|
||||
speech.say(sayIt);
|
||||
}
|
||||
}
|
||||
|
||||
+7
-22
@@ -240,7 +240,7 @@ function init (profileData) {
|
||||
if (treatment.profileJson && !profile.data[0].store[treatment.profile]) {
|
||||
if (treatment.profile.indexOf("@@@@@") < 0)
|
||||
treatment.profile += "@@@@@" + treatment.mills;
|
||||
var json = JSON.parse(treatment.profileJson);
|
||||
let json = JSON.parse(treatment.profileJson);
|
||||
profile.data[0].store[treatment.profile] = json;
|
||||
}
|
||||
}
|
||||
@@ -250,7 +250,7 @@ function init (profileData) {
|
||||
if (treatment.profileJson && !profile.data[0].store[treatment.profile]) {
|
||||
if (treatment.profile.indexOf("@@@@@") < 0)
|
||||
treatment.profile += "@@@@@" + treatment.mills;
|
||||
var json = JSON.parse(treatment.profileJson);
|
||||
let json = JSON.parse(treatment.profileJson);
|
||||
profile.data[0].store[treatment.profile] = json;
|
||||
}
|
||||
}
|
||||
@@ -277,7 +277,8 @@ function init (profileData) {
|
||||
}
|
||||
|
||||
// Binary search for events for O(log n) performance
|
||||
var first = 0, last = profile.tempbasaltreatments.length - 1;
|
||||
var first = 0
|
||||
, last = profile.tempbasaltreatments.length - 1;
|
||||
|
||||
while (first <= last) {
|
||||
var i = first + Math.floor((last - first) / 2);
|
||||
@@ -349,29 +350,13 @@ function init (profileData) {
|
||||
var current = profile.activeProfileToTime();
|
||||
profiles.push(current);
|
||||
|
||||
for (var key in profile.data[0].store) {
|
||||
if (profile.data[0].store.hasOwnProperty(key) && key !== current) {
|
||||
if (key.indexOf('@@@@@') < 0)
|
||||
profiles.push(key);
|
||||
}
|
||||
}
|
||||
Object.keys(profile.data[0].store).forEach(key => {
|
||||
if (key !== current && key.indexOf('@@@@@') < 0) profiles.push(key);
|
||||
})
|
||||
}
|
||||
return profiles;
|
||||
};
|
||||
|
||||
// get original store without added profiles fro profileSwitches
|
||||
profile.getProfileStore = function getProfileStore () {
|
||||
var newprofiledata = _.clone(profile.data[0]);
|
||||
for (var key in profile.data[0].store) {
|
||||
if (profile.data[0].store.hasOwnProperty(key)) {
|
||||
if (key.indexOf('@@@@@') < 0)
|
||||
store[key] = profile.data[0].store[key];
|
||||
}
|
||||
}
|
||||
return store;
|
||||
};
|
||||
|
||||
|
||||
if (profileData) { profile.loadData(profileData); }
|
||||
// init treatments array
|
||||
profile.updateTreatments([], []);
|
||||
|
||||
@@ -17,10 +17,9 @@ module.exports = init;
|
||||
calibrations.html = function html (client) {
|
||||
var translate = client.translate;
|
||||
var ret =
|
||||
'<h2>' + translate('Calibrations') + '</h2>'
|
||||
+ '<div style="width:50%;height:500px;float:left;overflow:scroll;overflow-x:hidden;" id="calibrations-list"></div>'
|
||||
+ '<div style="width:48%;float:right;" id="calibrations-chart"></div>'
|
||||
;
|
||||
'<h2>' + translate('Calibrations') + '</h2>' +
|
||||
'<div style="width:50%;height:500px;float:left;overflow:scroll;overflow-x:hidden;" id="calibrations-list"></div>' +
|
||||
'<div style="width:48%;float:right;" id="calibrations-chart"></div>';
|
||||
return ret;
|
||||
};
|
||||
|
||||
@@ -58,7 +57,6 @@ calibrations.report = function report_calibrations(datastorage,sorteddaystoshow)
|
||||
});
|
||||
mbgs.forEach(function(mbg) { calcmbg(mbg); });
|
||||
|
||||
|
||||
var events = treatments.concat(cals).concat(mbgs).sort(function(a, b) { return a.mills - b.mills; });
|
||||
|
||||
var colors = ['Aqua', 'Blue', 'Brown', 'Chartreuse', 'Coral', 'CornflowerBlue', 'DarkCyan', 'DarkMagenta', 'DarkOrange', 'Fuchsia', 'Green', 'Yellow'];
|
||||
@@ -90,7 +88,7 @@ calibrations.report = function report_calibrations(datastorage,sorteddaystoshow)
|
||||
html += JSON.stringify(e);
|
||||
}
|
||||
html += '</td></tr>';
|
||||
};
|
||||
}
|
||||
|
||||
html += '</table>';
|
||||
|
||||
|
||||
@@ -15,25 +15,23 @@ module.exports = init;
|
||||
dailystats.html = function html (client) {
|
||||
var translate = client.translate;
|
||||
var ret =
|
||||
'<h2>' + translate('Daily stats report') + '</h2>'
|
||||
+ '<div id="dailystats-report"></div>'
|
||||
;
|
||||
'<h2>' + translate('Daily stats report') + '</h2>' +
|
||||
'<div id="dailystats-report"></div>';
|
||||
return ret;
|
||||
};
|
||||
|
||||
dailystats.css =
|
||||
'#dailystats-placeholder .tdborder {'
|
||||
+ ' width:80px;'
|
||||
+ ' border: 1px #ccc solid;'
|
||||
+ ' margin: 0;'
|
||||
+ ' padding: 1px;'
|
||||
+ ' text-align:center;'
|
||||
+ '}'
|
||||
+ '#dailystats-placeholder .inlinepiechart {'
|
||||
+ ' width: 2.0in;'
|
||||
+ ' height: 0.9in;'
|
||||
+ '}'
|
||||
;
|
||||
'#dailystats-placeholder .tdborder {' +
|
||||
' width:80px;' +
|
||||
' border: 1px #ccc solid;' +
|
||||
' margin: 0;' +
|
||||
' padding: 1px;' +
|
||||
' text-align:center;' +
|
||||
'}' +
|
||||
'#dailystats-placeholder .inlinepiechart {' +
|
||||
' width: 2.0in;' +
|
||||
' height: 0.9in;' +
|
||||
'}';
|
||||
|
||||
dailystats.report = function report_dailystats (datastorage, sorteddaystoshow, options) {
|
||||
var Nightscout = window.Nightscout;
|
||||
@@ -73,10 +71,10 @@ dailystats.report = function report_dailystats(datastorage,sorteddaystoshow,opti
|
||||
|
||||
if (daysRecords.length === 0) {
|
||||
$('<td/>').appendTo(tr);
|
||||
$('<td class=\"tdborder\" style=\"width:160px\">' + report_plugins.utils.localeDate(day) + '</td>').appendTo(tr);
|
||||
$('<td class=\"tdborder\"colspan="10">'+translate('No data available')+'</td>').appendTo(tr);
|
||||
$('<td class="tdborder" style="width:160px">' + report_plugins.utils.localeDate(day) + '</td>').appendTo(tr);
|
||||
$('<td class="tdborder"colspan="10">' + translate('No data available') + '</td>').appendTo(tr);
|
||||
table.append(tr);
|
||||
return;;
|
||||
return;
|
||||
}
|
||||
|
||||
minForDay = daysRecords[0].sgv;
|
||||
@@ -101,53 +99,52 @@ dailystats.report = function report_dailystats(datastorage,sorteddaystoshow,opti
|
||||
sum += record.sgv;
|
||||
return out;
|
||||
}, {
|
||||
lows: 0,
|
||||
normal: 0,
|
||||
highs: 0
|
||||
lows: 0
|
||||
, normal: 0
|
||||
, highs: 0
|
||||
});
|
||||
var average = sum / daysRecords.length;
|
||||
|
||||
var bgValues = daysRecords.map(function(r) { return r.sgv; });
|
||||
$('<td><div id=\"dailystat-chart-' + day.toString() + '\" class=\"inlinepiechart\"></div></td>').appendTo(tr);
|
||||
$('<td><div id="dailystat-chart-' + day.toString() + '" class="inlinepiechart"></div></td>').appendTo(tr);
|
||||
|
||||
$('<td class=\"tdborder\" style=\"width:160px\">' + report_plugins.utils.localeDate(day) + '</td>').appendTo(tr);
|
||||
$('<td class=\"tdborder\">' + Math.round((100 * stats.lows) / daysRecords.length) + '%</td>').appendTo(tr);
|
||||
$('<td class=\"tdborder\">' + Math.round((100 * stats.normal) / daysRecords.length) + '%</td>').appendTo(tr);
|
||||
$('<td class=\"tdborder\">' + Math.round((100 * stats.highs) / daysRecords.length) + '%</td>').appendTo(tr);
|
||||
$('<td class=\"tdborder\">' + daysRecords.length +'</td>').appendTo(tr);
|
||||
$('<td class=\"tdborder\">' + minForDay +'</td>').appendTo(tr);
|
||||
$('<td class=\"tdborder\">' + maxForDay +'</td>').appendTo(tr);
|
||||
$('<td class=\"tdborder\">' + average.toFixed(1) +'</td>').appendTo(tr);
|
||||
$('<td class=\"tdborder\">' + ss.standard_deviation(bgValues).toFixed(1) + '</td>').appendTo(tr);
|
||||
$('<td class=\"tdborder\">' + ss.quantile(bgValues, 0.25).toFixed(1) + '</td>').appendTo(tr);
|
||||
$('<td class=\"tdborder\">' + ss.quantile(bgValues, 0.5).toFixed(1) + '</td>').appendTo(tr);
|
||||
$('<td class=\"tdborder\">' + ss.quantile(bgValues, 0.75).toFixed(1) + '</td>').appendTo(tr);
|
||||
$('<td class="tdborder" style="width:160px">' + report_plugins.utils.localeDate(day) + '</td>').appendTo(tr);
|
||||
$('<td class="tdborder">' + Math.round((100 * stats.lows) / daysRecords.length) + '%</td>').appendTo(tr);
|
||||
$('<td class="tdborder">' + Math.round((100 * stats.normal) / daysRecords.length) + '%</td>').appendTo(tr);
|
||||
$('<td class="tdborder">' + Math.round((100 * stats.highs) / daysRecords.length) + '%</td>').appendTo(tr);
|
||||
$('<td class="tdborder">' + daysRecords.length + '</td>').appendTo(tr);
|
||||
$('<td class="tdborder">' + minForDay + '</td>').appendTo(tr);
|
||||
$('<td class="tdborder">' + maxForDay + '</td>').appendTo(tr);
|
||||
$('<td class="tdborder">' + average.toFixed(1) + '</td>').appendTo(tr);
|
||||
$('<td class="tdborder">' + ss.standard_deviation(bgValues).toFixed(1) + '</td>').appendTo(tr);
|
||||
$('<td class="tdborder">' + ss.quantile(bgValues, 0.25).toFixed(1) + '</td>').appendTo(tr);
|
||||
$('<td class="tdborder">' + ss.quantile(bgValues, 0.5).toFixed(1) + '</td>').appendTo(tr);
|
||||
$('<td class="tdborder">' + ss.quantile(bgValues, 0.75).toFixed(1) + '</td>').appendTo(tr);
|
||||
|
||||
table.append(tr);
|
||||
var inrange = [
|
||||
{
|
||||
label: translate('Low'),
|
||||
data: Math.round(stats.lows * 1000 / daysRecords.length) / 10
|
||||
},
|
||||
{
|
||||
label: translate('In Range'),
|
||||
data: Math.round(stats.normal * 1000 / daysRecords.length) / 10
|
||||
},
|
||||
{
|
||||
label: translate('High'),
|
||||
data: Math.round(stats.highs * 1000 / daysRecords.length) / 10
|
||||
label: translate('Low')
|
||||
, data: Math.round(stats.lows * 1000 / daysRecords.length) / 10
|
||||
}
|
||||
, {
|
||||
label: translate('In Range')
|
||||
, data: Math.round(stats.normal * 1000 / daysRecords.length) / 10
|
||||
}
|
||||
, {
|
||||
label: translate('High')
|
||||
, data: Math.round(stats.highs * 1000 / daysRecords.length) / 10
|
||||
}
|
||||
];
|
||||
$.plot(
|
||||
'#dailystat-chart-' + day.toString(),
|
||||
inrange,
|
||||
{
|
||||
'#dailystat-chart-' + day.toString()
|
||||
, inrange, {
|
||||
series: {
|
||||
pie: {
|
||||
show: true
|
||||
}
|
||||
},
|
||||
colors: ['#f88', '#8f8', '#ff8']
|
||||
}
|
||||
, colors: ['#f88', '#8f8', '#ff8']
|
||||
}
|
||||
);
|
||||
});
|
||||
|
||||
@@ -20,51 +20,50 @@ module.exports = init;
|
||||
daytoday.html = function html (client) {
|
||||
var translate = client.translate;
|
||||
var ret =
|
||||
'<h2>' + translate('Day to day') + '</h2>'
|
||||
+ '<b>' + translate('To see this report, press SHOW while in this view') + '</b><br>'
|
||||
+ translate('Display') + ': '
|
||||
+ '<input type="checkbox" id="rp_optionsinsulin" checked><span style="color:blue;opacity:0.5">'+translate('Insulin')+'</span>'
|
||||
+ '<input type="checkbox" id="rp_optionscarbs" checked><span style="color:red;opacity:0.5">'+translate('Carbs')+'</span>'
|
||||
+ '<input type="checkbox" id="rp_optionsbasal" checked><span style="color:#0099ff;opacity:0.5">'+translate('Basal rate')+'</span>'
|
||||
+ '<input type="checkbox" id="rp_optionsnotes">'+translate('Notes')
|
||||
+ '<input type="checkbox" id="rp_optionsfood" checked>'+translate('Food')
|
||||
+ '<input type="checkbox" id="rp_optionsraw"><span style="color:gray;opacity:1">'+translate('Raw')+'</span>'
|
||||
+ '<input type="checkbox" id="rp_optionsiob"><span style="color:blue;opacity:0.5">'+translate('IOB')+'</span>'
|
||||
+ '<input type="checkbox" id="rp_optionscob"><span style="color:red;opacity:0.5">'+translate('COB')+'</span>'
|
||||
+ '<input type="checkbox" id="rp_optionspredicted"><span style="color:sienna;opacity:0.5">'+translate('Predictions')+'</span>'
|
||||
+ '<input type="checkbox" id="rp_optionsopenaps"><span style="color:sienna;opacity:0.5">'+translate('OpenAPS')+'</span>'
|
||||
+ '<input type="checkbox" id="rp_optionsdistribution" checked><span style="color:blue;opacity:0.5">'+translate('Insulin distribution')+'</span>'
|
||||
+ ' '+translate('Size')
|
||||
+ ' <select id="rp_size">'
|
||||
+ ' <option x="800" y="250">800x250px</option>'
|
||||
+ ' <option x="1000" y="300" selected>1000x300px</option>'
|
||||
+ ' <option x="1200" y="400">1200x400px</option>'
|
||||
+ ' <option x="1550" y="600">1550x600px</option>'
|
||||
+ ' <option x="2400" y="800">2400x800px</option>'
|
||||
+ '</select>'
|
||||
+ '<br>'
|
||||
+ translate('Scale') + ': '
|
||||
+ '<input type="radio" name="rp_scale" id="rp_linear" checked>'
|
||||
+ translate('Linear')
|
||||
+ '<input type="radio" name="rp_scale" id="rp_log">'
|
||||
+ translate('Logarithmic')
|
||||
+ '<div id="rp_predictedSettings" style="display:none">'
|
||||
+ translate('Truncate predictions: ')
|
||||
+ '<input type="checkbox" id="rp_optionsPredictedTruncate" checked>'
|
||||
+ '<br>'
|
||||
+ translate('Predictions offset') + ': '
|
||||
+ '<b><label id="rp_predictedOffset"></label> minutes</b>'
|
||||
+ ' '
|
||||
+ '<input type="button" onclick="predictMoreBackward();" value="' + translate('-30 min')+'">'
|
||||
+ '<input type="button" onclick="predictBackward();" value="' + translate('-5 min')+'">'
|
||||
+ '<input type="button" onclick="predictResetToZero();" value="' + translate('Zero')+'">'
|
||||
+ '<input type="button" onclick="predictForward();" value="' + translate('+5 min')+'">'
|
||||
+ '<input type="button" onclick="predictMoreForward();" value="' + translate('+30 min')+'">'
|
||||
+ '</div>'
|
||||
+ '<br>'
|
||||
+ '<div id="daytodaycharts">'
|
||||
+ '</div>'
|
||||
;
|
||||
'<h2>' + translate('Day to day') + '</h2>' +
|
||||
'<b>' + translate('To see this report, press SHOW while in this view') + '</b><br>' +
|
||||
translate('Display') + ': ' +
|
||||
'<input type="checkbox" id="rp_optionsinsulin" checked><span style="color:blue;opacity:0.5">' + translate('Insulin') + '</span>' +
|
||||
'<input type="checkbox" id="rp_optionscarbs" checked><span style="color:red;opacity:0.5">' + translate('Carbs') + '</span>' +
|
||||
'<input type="checkbox" id="rp_optionsbasal" checked><span style="color:#0099ff;opacity:0.5">' + translate('Basal rate') + '</span>' +
|
||||
'<input type="checkbox" id="rp_optionsnotes">' + translate('Notes') +
|
||||
'<input type="checkbox" id="rp_optionsfood" checked>' + translate('Food') +
|
||||
'<input type="checkbox" id="rp_optionsraw"><span style="color:gray;opacity:1">' + translate('Raw') + '</span>' +
|
||||
'<input type="checkbox" id="rp_optionsiob"><span style="color:blue;opacity:0.5">' + translate('IOB') + '</span>' +
|
||||
'<input type="checkbox" id="rp_optionscob"><span style="color:red;opacity:0.5">' + translate('COB') + '</span>' +
|
||||
'<input type="checkbox" id="rp_optionspredicted"><span style="color:sienna;opacity:0.5">' + translate('Predictions') + '</span>' +
|
||||
'<input type="checkbox" id="rp_optionsopenaps"><span style="color:sienna;opacity:0.5">' + translate('OpenAPS') + '</span>' +
|
||||
'<input type="checkbox" id="rp_optionsdistribution" checked><span style="color:blue;opacity:0.5">' + translate('Insulin distribution') + '</span>' +
|
||||
' ' + translate('Size') +
|
||||
' <select id="rp_size">' +
|
||||
' <option x="800" y="250">800x250px</option>' +
|
||||
' <option x="1000" y="300" selected>1000x300px</option>' +
|
||||
' <option x="1200" y="400">1200x400px</option>' +
|
||||
' <option x="1550" y="600">1550x600px</option>' +
|
||||
' <option x="2400" y="800">2400x800px</option>' +
|
||||
'</select>' +
|
||||
'<br>' +
|
||||
translate('Scale') + ': ' +
|
||||
'<input type="radio" name="rp_scale" id="rp_linear" checked>' +
|
||||
translate('Linear') +
|
||||
'<input type="radio" name="rp_scale" id="rp_log">' +
|
||||
translate('Logarithmic') +
|
||||
'<div id="rp_predictedSettings" style="display:none">' +
|
||||
translate('Truncate predictions: ') +
|
||||
'<input type="checkbox" id="rp_optionsPredictedTruncate" checked>' +
|
||||
'<br>' +
|
||||
translate('Predictions offset') + ': ' +
|
||||
'<b><label id="rp_predictedOffset"></label> minutes</b>' +
|
||||
' ' +
|
||||
'<input type="button" onclick="predictMoreBackward();" value="' + translate('-30 min') + '">' +
|
||||
'<input type="button" onclick="predictBackward();" value="' + translate('-5 min') + '">' +
|
||||
'<input type="button" onclick="predictResetToZero();" value="' + translate('Zero') + '">' +
|
||||
'<input type="button" onclick="predictForward();" value="' + translate('+5 min') + '">' +
|
||||
'<input type="button" onclick="predictMoreForward();" value="' + translate('+30 min') + '">' +
|
||||
'</div>' +
|
||||
'<br>' +
|
||||
'<div id="daytodaycharts">' +
|
||||
'</div>';
|
||||
return ret;
|
||||
};
|
||||
|
||||
@@ -102,18 +101,17 @@ daytoday.report = function report_daytoday(datastorage,sorteddaystoshow,options)
|
||||
var proteinAverage = proteinSum / datastorage.alldays;
|
||||
var fatAverage = fatSum / datastorage.alldays;
|
||||
|
||||
|
||||
if (options.insulindistribution)
|
||||
$('#daytodaycharts').append('<br><br><b>' + translate('TDD average') + ':</b> ' + tddAverage.toFixed(1) + 'U <b>'
|
||||
+ translate('Carbs average') + ':</b> ' + carbsAverage.toFixed(0) + 'g'
|
||||
+ translate('Protein average') + ':</b> ' + proteinAverage.toFixed(0) + 'g'
|
||||
+ translate('Fat average') + ':</b> ' + fatAverage.toFixed(0) + 'g'
|
||||
$('#daytodaycharts').append('<br><br><b>' + translate('TDD average') + ':</b> ' + tddAverage.toFixed(1) + 'U <b>' +
|
||||
translate('Carbs average') + ':</b> ' + carbsAverage.toFixed(0) + 'g' +
|
||||
translate('Protein average') + ':</b> ' + proteinAverage.toFixed(0) + 'g' +
|
||||
translate('Fat average') + ':</b> ' + fatAverage.toFixed(0) + 'g'
|
||||
);
|
||||
|
||||
function timeTicks (n, i) {
|
||||
var t12 = [
|
||||
'12am', '', '2am', '', '4am', '', '6am', '', '8am', '', '10am', '',
|
||||
'12pm', '', '2pm', '', '4pm', '', '6pm', '', '8pm', '', '10pm', '', '12am'
|
||||
'12am', '', '2am', '', '4am', '', '6am', '', '8am', '', '10am', ''
|
||||
, '12pm', '', '2pm', '', '4pm', '', '6pm', '', '8pm', '', '10pm', '', '12am'
|
||||
];
|
||||
if (Nightscout.client.settings.timeFormat === 24) {
|
||||
return ('00' + i).slice(-2);
|
||||
@@ -264,10 +262,6 @@ daytoday.report = function report_daytoday(datastorage,sorteddaystoshow,options)
|
||||
.attr('stroke', 'grey');
|
||||
});
|
||||
|
||||
// bind up the context chart data to an array of circles
|
||||
var contextCircles = context.selectAll('circle')
|
||||
.data(data.sgv);
|
||||
|
||||
function prepareContextCircles (sel) {
|
||||
var badData = [];
|
||||
sel.attr('cx', function(d) {
|
||||
@@ -300,9 +294,9 @@ daytoday.report = function report_daytoday(datastorage,sorteddaystoshow,options)
|
||||
.on('mouseover', function(d) {
|
||||
if (options.openAps && d.openaps) {
|
||||
client.tooltip.transition().duration(TOOLTIP_TRANS_MS).style('opacity', .9);
|
||||
var text = '<b>BG:</b> ' + d.openaps.suggested.bg
|
||||
+ ', ' + d.openaps.suggested.reason
|
||||
+ (d.openaps.suggested.mealAssist ? ' <b>Meal Assist:</b> ' + d.openaps.suggested.mealAssist : '');
|
||||
var text = '<b>BG:</b> ' + d.openaps.suggested.bg +
|
||||
', ' + d.openaps.suggested.reason +
|
||||
(d.openaps.suggested.mealAssist ? ' <b>Meal Assist:</b> ' + d.openaps.suggested.mealAssist : '');
|
||||
client.tooltip.html(text)
|
||||
.style('left', (d3.event.pageX) + 'px')
|
||||
.style('top', (d3.event.pageY + 15) + 'px');
|
||||
@@ -340,7 +334,7 @@ daytoday.report = function report_daytoday(datastorage,sorteddaystoshow,options)
|
||||
|
||||
var predictions = [];
|
||||
if (data && data.devicestatus) {
|
||||
for (var i = data.devicestatus.length - 1; i >= 0; i--) {
|
||||
for (i = data.devicestatus.length - 1; i >= 0; i--) {
|
||||
if (data.devicestatus[i].loop && data.devicestatus[i].loop.predicted) {
|
||||
predictions.push(data.devicestatus[i].loop.predicted);
|
||||
} else if (data.devicestatus[i].openaps && data.devicestatus[i].openaps.suggested && data.devicestatus[i].openaps.suggested.predBGs) {
|
||||
@@ -363,10 +357,11 @@ daytoday.report = function report_daytoday(datastorage,sorteddaystoshow,options)
|
||||
// Iterate over all treatments, find the predictions for each and add them to the predicted array p
|
||||
for (var treatmentsIndex = 0; treatmentsIndex < treatmentsTimestamps.length; treatmentsIndex++) {
|
||||
var timestamp = treatmentsTimestamps[treatmentsIndex];
|
||||
// TODO / BUG: predictedOffset is not set
|
||||
var predictedIndex = findPredicted(predictions, timestamp, predictedOffset); // Find predictions offset before or after timestamp
|
||||
|
||||
if (predictedIndex != null) {
|
||||
var entry = predictions[predictedIndex]; // Start entry
|
||||
entry = predictions[predictedIndex]; // Start entry
|
||||
var d = moment(entry.startDate);
|
||||
var end = moment().endOf('day');
|
||||
if (options.predictedTruncate) {
|
||||
@@ -409,7 +404,7 @@ daytoday.report = function report_daytoday(datastorage,sorteddaystoshow,options)
|
||||
}
|
||||
}
|
||||
} else { // If offset is positive or zero, start searching from last prediction going backward
|
||||
for (var i = predictions.length - 1; i > 0; i--) {
|
||||
for (i = predictions.length - 1; i > 0; i--) {
|
||||
if (predictions[i] && predictions[i].startDate && moment(predictions[i].startDate) >= ts) {
|
||||
predicted = i;
|
||||
}
|
||||
@@ -420,7 +415,6 @@ daytoday.report = function report_daytoday(datastorage,sorteddaystoshow,options)
|
||||
//
|
||||
// PREDICTIONS ENDS
|
||||
|
||||
|
||||
// bind up the context chart data to an array of circles
|
||||
var contextData = (options.predicted ? data.sgv.concat(preparePredictedData()) : data.sgv);
|
||||
var contextCircles = context.selectAll('circle').data(contextData);
|
||||
@@ -433,7 +427,8 @@ daytoday.report = function report_daytoday(datastorage,sorteddaystoshow,options)
|
||||
|
||||
var to = moment(day).add(1, 'days');
|
||||
var from = moment(day);
|
||||
var iobpolyline = '', cobpolyline = '';
|
||||
var iobpolyline = ''
|
||||
, cobpolyline = '';
|
||||
|
||||
// basals data
|
||||
var linedata = [];
|
||||
@@ -502,7 +497,8 @@ daytoday.report = function report_daytoday(datastorage,sorteddaystoshow,options)
|
||||
if (tempPart > 0) {
|
||||
positiveTemps += tempPart;
|
||||
data.netBasalPositive[hournow] += tempPart;
|
||||
} if (tempPart < 0) {
|
||||
}
|
||||
if (tempPart < 0) {
|
||||
negativeTemps += tempPart;
|
||||
data.netBasalNegative[hournow] += tempPart;
|
||||
}
|
||||
@@ -552,8 +548,8 @@ daytoday.report = function report_daytoday(datastorage,sorteddaystoshow,options)
|
||||
|
||||
// Draw IOB from devicestatuses if available
|
||||
if (iobStatusAvailable) {
|
||||
var lastdate = 0;
|
||||
var previousdate = 0;
|
||||
lastdate = 0;
|
||||
previousdate = 0;
|
||||
var iobArray = client.plugins('iob').IOBDeviceStatusesInTimeRange(datastorage.devicestatus, from.valueOf(), to.valueOf());
|
||||
_.each(iobArray, function drawCob (point) {
|
||||
if (previousdate !== 0 && point.mills - previousdate > times.mins(15).msecs) {
|
||||
@@ -678,7 +674,6 @@ daytoday.report = function report_daytoday(datastorage,sorteddaystoshow,options)
|
||||
});
|
||||
}
|
||||
|
||||
|
||||
data.treatments.forEach(function(treatment) {
|
||||
// Calculate bolus stats
|
||||
if (treatment.insulin) {
|
||||
@@ -922,11 +917,11 @@ daytoday.report = function report_daytoday(datastorage,sorteddaystoshow,options)
|
||||
|
||||
var chartData = [
|
||||
{
|
||||
label: translate('Basal'),
|
||||
count: totalBasalInsulin,
|
||||
pct: (totalBasalInsulin / totalDailyInsulin * 100).toFixed(0)
|
||||
},
|
||||
{label: translate('Bolus'), count: bolusInsulin, pct: (bolusInsulin / totalDailyInsulin * 100).toFixed(0)}
|
||||
label: translate('Basal')
|
||||
, count: totalBasalInsulin
|
||||
, pct: (totalBasalInsulin / totalDailyInsulin * 100).toFixed(0)
|
||||
}
|
||||
, { label: translate('Bolus'), count: bolusInsulin, pct: (bolusInsulin / totalDailyInsulin * 100).toFixed(0) }
|
||||
];
|
||||
|
||||
// Insulin distribution chart
|
||||
|
||||
@@ -65,8 +65,7 @@ glucosedistribution.html = function html(client) {
|
||||
'20<input type="checkbox" id="glucosedistribution-20" checked>' +
|
||||
'21<input type="checkbox" id="glucosedistribution-21" checked>' +
|
||||
'22<input type="checkbox" id="glucosedistribution-22" checked>' +
|
||||
'23<input type="checkbox" id="glucosedistribution-23" checked>'
|
||||
;
|
||||
'23<input type="checkbox" id="glucosedistribution-23" checked>';
|
||||
return ret;
|
||||
};
|
||||
|
||||
@@ -132,13 +131,13 @@ glucosedistribution.report = function report_glucosedistribution(datastorage, so
|
||||
|
||||
// Filter data for noise
|
||||
// data cleaning pass 0 - remove duplicates and non-sgv entries, sort
|
||||
var seen = {};
|
||||
var seen = [];
|
||||
data = data.filter(function(item) {
|
||||
if (!item.sgv || !item.bgValue || !item.displayTime || item.bgValue < 39) {
|
||||
if (!item.sgv || !item.bgValue || !item.displayTime || item.bgValue < 39) {
|
||||
console.log(item);
|
||||
return false;
|
||||
}
|
||||
return seen.hasOwnProperty(item.displayTime) ? false : (seen[item.displayTime] = true);
|
||||
return seen.includes(item.displayTime) ? false : (seen[item.displayTime] = true);
|
||||
});
|
||||
|
||||
data.sort(function(a, b) {
|
||||
@@ -148,7 +147,7 @@ glucosedistribution.report = function report_glucosedistribution(datastorage, so
|
||||
var glucose_data = [data[0]];
|
||||
|
||||
// data cleaning pass 1 - add interpolated missing points
|
||||
for (var i = 0; i <= data.length - 2; i++) {
|
||||
for (i = 0; i <= data.length - 2; i++) {
|
||||
var entry = data[i];
|
||||
var nextEntry = data[i + 1];
|
||||
|
||||
@@ -186,12 +185,12 @@ glucosedistribution.report = function report_glucosedistribution(datastorage, so
|
||||
|
||||
const maxGap = (5 * 60 * 1000) + 10000;
|
||||
|
||||
for (var i = 1; i <= glucose_data.length - 2; i++) {
|
||||
var entry = glucose_data[i];
|
||||
var nextEntry = glucose_data[i + 1];
|
||||
for (i = 1; i <= glucose_data.length - 2; i++) {
|
||||
let entry = glucose_data[i];
|
||||
let nextEntry = glucose_data[i + 1];
|
||||
|
||||
var timeDelta = nextEntry.displayTime.getTime() - entry.displayTime.getTime();
|
||||
var timeDelta2 = entry.displayTime.getTime() - prevEntry.displayTime.getTime();
|
||||
let timeDelta = nextEntry.displayTime.getTime() - entry.displayTime.getTime();
|
||||
let timeDelta2 = entry.displayTime.getTime() - prevEntry.displayTime.getTime();
|
||||
|
||||
if (timeDelta > maxGap || timeDelta2 > maxGap) {
|
||||
glucose_data2.push(entry);
|
||||
@@ -212,7 +211,7 @@ glucosedistribution.report = function report_glucosedistribution(datastorage, so
|
||||
const d = (nextEntry.bgValue - prevEntry.bgValue) / 2;
|
||||
const interpolatedValue = prevEntry.bgValue + d;
|
||||
|
||||
var newEntry = {
|
||||
let newEntry = {
|
||||
sgv: displayUnits === 'mmol' ? interpolatedValue / 18 : interpolatedValue
|
||||
, bgValue: interpolatedValue
|
||||
, displayTime: entry.displayTime
|
||||
@@ -237,10 +236,10 @@ glucosedistribution.report = function report_glucosedistribution(datastorage, so
|
||||
});
|
||||
|
||||
var timeTotal = 0;
|
||||
for (var i = 1; i <= glucose_data.length - 2; i++) {
|
||||
var entry = glucose_data[i];
|
||||
var nextEntry = glucose_data[i + 1];
|
||||
var timeDelta = nextEntry.displayTime.getTime() - entry.displayTime.getTime();
|
||||
for (i = 1; i <= glucose_data.length - 2; i++) {
|
||||
let entry = glucose_data[i];
|
||||
let nextEntry = glucose_data[i + 1];
|
||||
let timeDelta = nextEntry.displayTime.getTime() - entry.displayTime.getTime();
|
||||
if (timeDelta < maxGap) {
|
||||
timeTotal += timeDelta;
|
||||
}
|
||||
@@ -357,11 +356,10 @@ glucosedistribution.report = function report_glucosedistribution(datastorage, so
|
||||
var glucoseTotal = 0;
|
||||
var deltaTotal = 0;
|
||||
|
||||
for (var i = 0; i <= glucose_data.length - 2; i++) {
|
||||
var entry = glucose_data[i];
|
||||
var nextEntry = glucose_data[i + 1];
|
||||
|
||||
var timeDelta = nextEntry.displayTime.getTime() - entry.displayTime.getTime();
|
||||
for (i = 0; i <= glucose_data.length - 2; i++) {
|
||||
const entry = glucose_data[i];
|
||||
const nextEntry = glucose_data[i + 1];
|
||||
const timeDelta = nextEntry.displayTime.getTime() - entry.displayTime.getTime();
|
||||
|
||||
// Use maxGap constant
|
||||
if (timeDelta == 0 || timeDelta > maxGap) { // 6 * 60 * 1000) {
|
||||
|
||||
@@ -17,22 +17,21 @@ module.exports = init;
|
||||
hourlystats.html = function html (client) {
|
||||
var translate = client.translate;
|
||||
var ret =
|
||||
'<h2>' + translate('Hourly stats') + '</h2>'
|
||||
+ '<div id="hourlystats-overviewchart"></div>'
|
||||
+ '<div id="hourlystats-report"></div>'
|
||||
;
|
||||
'<h2>' + translate('Hourly stats') + '</h2>' +
|
||||
'<div id="hourlystats-overviewchart"></div>' +
|
||||
'<div id="hourlystats-report"></div>';
|
||||
return ret;
|
||||
};
|
||||
|
||||
hourlystats.css =
|
||||
'#hourlystats-overviewchart {'
|
||||
+ ' width: 100%;'
|
||||
+ ' min-width: 6.5in;'
|
||||
+ ' height: 5in;'
|
||||
+ '}'
|
||||
+ '#hourlystats-placeholder td {'
|
||||
+ ' text-align:center;'
|
||||
+ '}';
|
||||
'#hourlystats-overviewchart {' +
|
||||
' width: 100%;' +
|
||||
' min-width: 6.5in;' +
|
||||
' height: 5in;' +
|
||||
'}' +
|
||||
'#hourlystats-placeholder td {' +
|
||||
' text-align:center;' +
|
||||
'}';
|
||||
|
||||
hourlystats.report = function report_hourlystats (datastorage, sorteddaystoshow, options) {
|
||||
//console.log(window);
|
||||
@@ -89,15 +88,15 @@ hourlystats.report = function report_hourlystats(datastorage, sorteddaystoshow,
|
||||
return r.sgv;
|
||||
}));
|
||||
stats.push([
|
||||
new Date(d),
|
||||
ss.quantile(pivotedByHour[hour].map(function (r) {
|
||||
new Date(d)
|
||||
, ss.quantile(pivotedByHour[hour].map(function(r) {
|
||||
return r.sgv;
|
||||
}), 0.25),
|
||||
ss.quantile(pivotedByHour[hour].map(function (r) {
|
||||
}), 0.25)
|
||||
, ss.quantile(pivotedByHour[hour].map(function(r) {
|
||||
return r.sgv;
|
||||
}), 0.75),
|
||||
avg - dev,
|
||||
avg + dev
|
||||
}), 0.75)
|
||||
, avg - dev
|
||||
, avg + dev
|
||||
]);
|
||||
var tmp;
|
||||
$('<td>' + display + '</td>').appendTo(tr);
|
||||
@@ -106,12 +105,15 @@ hourlystats.report = function report_hourlystats(datastorage, sorteddaystoshow,
|
||||
$('<td>' + Math.min.apply(Math, pivotedByHour[hour].map(function(r) {
|
||||
return r.sgv;
|
||||
})) + '</td>').appendTo(tr);
|
||||
// eslint-disable-next-line no-cond-assign
|
||||
$('<td>' + ((tmp = ss.quantile(pivotedByHour[hour].map(function(r) {
|
||||
return r.sgv;
|
||||
}), 0.25)) ? tmp.toFixed(1) : 0) + '</td>').appendTo(tr);
|
||||
// eslint-disable-next-line no-cond-assign
|
||||
$('<td>' + ((tmp = ss.quantile(pivotedByHour[hour].map(function(r) {
|
||||
return r.sgv;
|
||||
}), 0.5)) ? tmp.toFixed(1) : 0) + '</td>').appendTo(tr);
|
||||
// eslint-disable-next-line no-cond-assign
|
||||
$('<td>' + ((tmp = ss.quantile(pivotedByHour[hour].map(function(r) {
|
||||
return r.sgv;
|
||||
}), 0.75)) ? tmp.toFixed(1) : 0) + '</td>').appendTo(tr);
|
||||
@@ -126,28 +128,27 @@ hourlystats.report = function report_hourlystats(datastorage, sorteddaystoshow,
|
||||
report.append(table);
|
||||
|
||||
$.plot(
|
||||
'#hourlystats-overviewchart',
|
||||
[{
|
||||
data: stats,
|
||||
candle: true
|
||||
}],
|
||||
{
|
||||
'#hourlystats-overviewchart'
|
||||
, [{
|
||||
data: stats
|
||||
, candle: true
|
||||
}], {
|
||||
series: {
|
||||
candle: true,
|
||||
lines: false //Somehow it draws lines if you dont disable this. Should investigate and fix this ;)
|
||||
},
|
||||
xaxis: {
|
||||
mode: 'time',
|
||||
timeFormat: '%h:00',
|
||||
min: 0,
|
||||
max: times.hours(24).msecs - times.secs(1).msecs
|
||||
},
|
||||
yaxis: {
|
||||
min: 0,
|
||||
max: options.units === 'mmol' ? 22 : 400,
|
||||
show: true
|
||||
},
|
||||
grid: {
|
||||
candle: true
|
||||
, lines: false //Somehow it draws lines if you dont disable this. Should investigate and fix this ;)
|
||||
}
|
||||
, xaxis: {
|
||||
mode: 'time'
|
||||
, timeFormat: '%h:00'
|
||||
, min: 0
|
||||
, max: times.hours(24).msecs - times.secs(1).msecs
|
||||
}
|
||||
, yaxis: {
|
||||
min: 0
|
||||
, max: options.units === 'mmol' ? 22 : 400
|
||||
, show: true
|
||||
}
|
||||
, grid: {
|
||||
show: true
|
||||
}
|
||||
}
|
||||
|
||||
+148
-143
@@ -47,19 +47,19 @@ loopalyzer.html = function html(client) {
|
||||
ret += '<input type="number" style="width: 3.5em" value="10" id="rp_loopalyzermincarbs">' + ' ' + translate('g carbs');
|
||||
ret += ' ' + translate('consumed between');
|
||||
ret += ' <select id="rp_loopalyzert1">';
|
||||
for (var i=0; i<24; i++) {
|
||||
var H=(i<10?'0':'') + i;
|
||||
for (let i = 0; i < 24; i++) {
|
||||
const H = (i < 10 ? '0' : '') + i;
|
||||
ret += ' <option t1="' + H + ':00"' + (i == 6 ? ' selected' : '') + '>' + H + ':00</option>';
|
||||
ret += ' <option t1="' + H + ':30">' + H + ':30</option>';
|
||||
}
|
||||
ret += '</select>';
|
||||
ret += ' ' + translate('and');
|
||||
ret += ' <select id="rp_loopalyzert2">';
|
||||
for (var i=0; i<24; i++) {
|
||||
var H=(i<10?'0':'') + i;
|
||||
for (let i = 0; i < 24; i++) {
|
||||
const H = (i < 10 ? '0' : '') + i;
|
||||
ret += ' <option t2="' + H + ':00"' + (i == 9 ? ' selected' : '') + '>' + H + ':00</option>';
|
||||
ret += ' <option t2="' + H + ':30">' + H + ':30</option>';
|
||||
};
|
||||
}
|
||||
ret += '</select>';
|
||||
ret += '</span>'; /* timeShift */
|
||||
ret += '<br/><br/>';
|
||||
@@ -81,19 +81,18 @@ loopalyzer.html = function html(client) {
|
||||
};
|
||||
|
||||
loopalyzer.css =
|
||||
'#loopalyzer-charts, #loopalyzer-profiles { padding: 20px; } '
|
||||
+ '#loopalyzer-basal, #loopalyzer-bg, #loopalyzer-tempbasal, #loopalyzer-iob, #loopalyzer-cob, #loopalyzer-profiles {'
|
||||
+ ' width: 100%;'
|
||||
+ ' height: 100%;'
|
||||
+ '}'
|
||||
+ '#loopalyzer-profiles-table table { margin: 0 10px; border-collapse: collapse; border: 0px; }'
|
||||
+ '#loopalyzer-profiles-table td { vertical-align: top; }'
|
||||
+ '#loopalyzer-profiles-table td table { margin: 0 10px; border-collapse: collapse; border: 0px; }'
|
||||
+ '#loopalyzer-profiles-table td caption { text-align: left; font-weight: bold; }'
|
||||
+ '#loopalyzer-profiles-table td th { background-color: #4CAF50; color: white; }'
|
||||
+ '#loopalyzer-profiles-table td td { text-align: right; vertical-align: top; padding: 0 1px; }'
|
||||
+ '#loopalyzer-profiles-table td td td { padding: 1px 8px; }'
|
||||
;
|
||||
'#loopalyzer-charts, #loopalyzer-profiles { padding: 20px; } ' +
|
||||
'#loopalyzer-basal, #loopalyzer-bg, #loopalyzer-tempbasal, #loopalyzer-iob, #loopalyzer-cob, #loopalyzer-profiles {' +
|
||||
' width: 100%;' +
|
||||
' height: 100%;' +
|
||||
'}' +
|
||||
'#loopalyzer-profiles-table table { margin: 0 10px; border-collapse: collapse; border: 0px; }' +
|
||||
'#loopalyzer-profiles-table td { vertical-align: top; }' +
|
||||
'#loopalyzer-profiles-table td table { margin: 0 10px; border-collapse: collapse; border: 0px; }' +
|
||||
'#loopalyzer-profiles-table td caption { text-align: left; font-weight: bold; }' +
|
||||
'#loopalyzer-profiles-table td th { background-color: #4CAF50; color: white; }' +
|
||||
'#loopalyzer-profiles-table td td { text-align: right; vertical-align: top; padding: 0 1px; }' +
|
||||
'#loopalyzer-profiles-table td td td { padding: 1px 8px; }';
|
||||
|
||||
loopalyzer.prepareHtml = function loopalyzerPrepareHtml () {
|
||||
// $('#loopalyzer-charts').append($('<table><tr><td><div id="loopalyzerchart"></div></td><td><div id="loopalyzerstatchart"></td></tr></table>'));
|
||||
@@ -111,12 +110,12 @@ loopalyzer.getSGVs = function(datastorage, daysToShow) {
|
||||
// Loop thru the days to show, for each day find the matching SGVs and insert into the bins entry array
|
||||
daysToShow.forEach(function(day) {
|
||||
var entries = []; // Array with all SGVs for this day, we'll fill this and then insert into the bins later
|
||||
for (var i=0; i<288; i++) entries.push(NaN); // Fill the array with NaNs so we have something in case we don't find an SGV
|
||||
for (let i = 0; i < 288; i++) entries.push(NaN); // Fill the array with NaNs so we have something in case we don't find an SGV
|
||||
var fromDate = moment(day);
|
||||
var toDate = moment(day);
|
||||
fromDate.set({ 'hours': 0, 'minutes': 0, 'seconds': 0, 'milliseconds': 0 });
|
||||
toDate.set({ 'hours': 0, 'minutes': 5, 'seconds': 0, 'milliseconds': 0 }); // toDate is 5 mins ahead
|
||||
for (var i=0; i<288; i++) {
|
||||
for (let i = 0; i < 288; i++) {
|
||||
var found = false;
|
||||
data.some(function(record) {
|
||||
var recDate = moment(record.displayTime);
|
||||
@@ -199,7 +198,8 @@ loopalyzer.getIOBs = function(datastorage, daysToShow, profile, client, treatmen
|
||||
if (daysToShow.length === 1) loopalyzer.fillNanWithTreatments(iobs, treatments);
|
||||
|
||||
// Loop thru these entries and where no IOB has been found, interpolate between nearby to get a continuous array
|
||||
var startIndex = 0, stopIndex = 0;
|
||||
var startIndex = 0
|
||||
, stopIndex = 0;
|
||||
while (startIndex < iobs.length && isNaN(iobs[startIndex])) {
|
||||
startIndex++; // Advance start to the first real number
|
||||
}
|
||||
@@ -261,7 +261,10 @@ loopalyzer.getCOBs = function(datastorage, daysToShow, profile, client, treatmen
|
||||
if (daysToShow.length === 1) loopalyzer.fillNanWithTreatments(cobs, treatments);
|
||||
|
||||
// Loop thru these entries and where no COB has been found, interpolate between nearby to get a continuous array
|
||||
var startIndex=0, stopIndex=0, k=0, m=0;
|
||||
var startIndex = 0
|
||||
, stopIndex = 0
|
||||
, k = 0
|
||||
, m = 0;
|
||||
|
||||
while (startIndex < cobs.length && isNaN(cobs[startIndex])) {
|
||||
startIndex++; // Advance start to the first real number
|
||||
@@ -315,8 +318,10 @@ loopalyzer.fillNanWithTreatments = function(array, treatments) {
|
||||
var stop = index;
|
||||
|
||||
// Now move left and right until we find real numbers, so not NaN
|
||||
while (start-- >=0 && isNaN(array[start])) {};
|
||||
while (stop++ <array.length && isNaN(array[stop])) {};
|
||||
// eslint-disable-next-line no-empty
|
||||
while (start-- >= 0 && isNaN(array[start])) {}
|
||||
// eslint-disable-next-line no-empty
|
||||
while (stop++ < array.length && isNaN(array[stop])) {}
|
||||
// var gap = stop - start;
|
||||
// if (isNaN(array[start]) || isNaN(array[stop]) || gap > interpolationGap || (gap < interpolationGap && array[start]<array[stop])) {
|
||||
// if ( isNaN(array[start]) || isNaN(array[stop]) || (array[start] < array[stop] && (gap >= interpolationGap || array[start]==0)) ) {
|
||||
@@ -421,13 +426,13 @@ loopalyzer.findPredicted = function(predictions, timestamp, offset) {
|
||||
var ts = moment(timestamp).add(offset, 'minutes');
|
||||
var predicted = null;
|
||||
if (offset && offset < 0) { // If offset is negative, start searching from first prediction going forward
|
||||
for (var i = 0; i < predictions.length; i++) {
|
||||
for (let i = 0; i < predictions.length; i++) {
|
||||
if (predictions[i] && predictions[i].startDate && moment(predictions[i].startDate) <= ts) {
|
||||
predicted = i;
|
||||
}
|
||||
}
|
||||
} else { // If offset is positive or zero, start searching from last prediction going backward
|
||||
for (var i = predictions.length - 1; i > 0; i--) {
|
||||
for (let i = predictions.length - 1; i > 0; i--) {
|
||||
if (predictions[i] && predictions[i].startDate && moment(predictions[i].startDate) >= ts) {
|
||||
predicted = i;
|
||||
}
|
||||
@@ -436,7 +441,6 @@ loopalyzer.findPredicted = function(predictions, timestamp, offset) {
|
||||
return predicted;
|
||||
}
|
||||
|
||||
|
||||
loopalyzer.getPredictions = function(datastorage, daysToShow, client) {
|
||||
|
||||
if (!datastorage.devicestatus)
|
||||
@@ -494,7 +498,7 @@ loopalyzer.getPredictions = function(datastorage, daysToShow, client) {
|
||||
}
|
||||
}
|
||||
}
|
||||
for (var i=0; i<288; i++) {
|
||||
for (let i = 0; i < 288; i++) {
|
||||
bins[i][1].push(p[i]);
|
||||
}
|
||||
})
|
||||
@@ -503,7 +507,6 @@ loopalyzer.getPredictions = function(datastorage, daysToShow, client) {
|
||||
//
|
||||
// PREDICTIONS ENDS
|
||||
|
||||
|
||||
// VARIOUS UTILITY FUNCTIONS //
|
||||
|
||||
/* Create an empty bins array with date stamps for today */
|
||||
@@ -529,7 +532,10 @@ loopalyzer.addArrayToBins = function(bins, values) {
|
||||
|
||||
/* Fill all NaNs in an array by interpolating between adjacent values */
|
||||
loopalyzer.interpolateArray = function(values, allowNegative) {
|
||||
var startIndex=0, stopIndex=0, k=0, m=0;
|
||||
var startIndex = 0
|
||||
, stopIndex = 0
|
||||
, k = 0
|
||||
, m = 0;
|
||||
|
||||
while (isNaN(values[startIndex])) {
|
||||
startIndex++; // Advance start to the first real number
|
||||
@@ -586,7 +592,7 @@ loopalyzer.avg = function(xBins) {
|
||||
var sum = 0;
|
||||
var count = 0;
|
||||
entry[1].forEach(function(value) {
|
||||
if (value && value != NaN) {
|
||||
if (value && !isNaN(value)) {
|
||||
sum += value;
|
||||
count++;
|
||||
}
|
||||
@@ -608,17 +614,17 @@ loopalyzer.timeShiftBins = function(bins, timeShift) {
|
||||
})
|
||||
var minutesBy5 = Math.floor(minutes / 5);
|
||||
if (minutesBy5 > 0) {
|
||||
var count = 288-minutesBy5;
|
||||
let count = 288 - minutesBy5;
|
||||
// If minutes>0 it means we should shift forward in time
|
||||
// Example: Shift by 15 mins = 3 buckets
|
||||
// bin : 0 1 2 3 4 5 6 7 8 9 10
|
||||
// tempBin: NaN NaN NaN 0 1 2 3 4 5 6 7
|
||||
for (var i=0; i<count; i++) {
|
||||
for (let i = 0; i < count; i++) {
|
||||
tempBin[i + minutesBy5] = bins[i][1][dayIndex];
|
||||
}
|
||||
}
|
||||
if (minutesBy5 < 0) {
|
||||
var count = 288+minutesBy5;
|
||||
let count = 288 + minutesBy5;
|
||||
// If minutes<0 it means we should shift backward in time
|
||||
// Example: Shift by 15 mins = 3 buckets
|
||||
// bin : 0 1 2 3 4 5 6 7 8 9 10
|
||||
@@ -628,7 +634,7 @@ loopalyzer.timeShiftBins = function(bins, timeShift) {
|
||||
}
|
||||
}
|
||||
// Put the shifted data back into original bins variable (pass by pointer)
|
||||
for (var i=0; i<288; i++) {
|
||||
for (let i = 0; i < 288; i++) {
|
||||
bins[i][1][dayIndex] = tempBin[i];
|
||||
}
|
||||
}
|
||||
@@ -726,6 +732,7 @@ loopalyzer.renderProfilesTable = function (datastoreProfiles, daysToShow, client
|
||||
if (store) {
|
||||
for (var key in store) {
|
||||
if (laDebug) console.log('profile ' + key);
|
||||
// eslint-disable-next-line no-prototype-builtins
|
||||
if (store.hasOwnProperty(key)) {
|
||||
var defaultProfile = store[key];
|
||||
newEntry.profileName = key;
|
||||
@@ -887,7 +894,6 @@ loopalyzer.report = function(datastorage,sorteddaystoshow,options) {
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
loopalyzer.generateReport = function(datastorage, daysToShow, options) {
|
||||
var Nightscout = window.Nightscout;
|
||||
var client = Nightscout.client;
|
||||
@@ -950,7 +956,8 @@ loopalyzer.generateReport = function(datastorage,daysToShow,options) {
|
||||
var timeShiftStartTime = null; // If timeShifting this is the average time the meals were eaten
|
||||
var timeShiftStopTime = null; // and this is the start + DIA according to profile
|
||||
var doTimeShift = false;
|
||||
daysToShow.forEach(function(){ timeShifts.push(0); firstCarbs.push(NaN) });
|
||||
daysToShow.forEach(function() { timeShifts.push(0);
|
||||
firstCarbs.push(NaN) });
|
||||
|
||||
// Check to see if we are doing timeShift or not
|
||||
if ($("#rp_loopalyzertimeshift").is(":checked") && daysToShow.length > 1) {
|
||||
@@ -995,13 +1002,16 @@ loopalyzer.generateReport = function(datastorage,daysToShow,options) {
|
||||
})
|
||||
|
||||
// Calculate the average starting time, in minutes after midnight
|
||||
var averageMinutesAfterMidnight = 0, sum = 0, count = 0;
|
||||
var sum = 0
|
||||
, count = 0;
|
||||
|
||||
firstCarbs.forEach(function(minutesAfterMidnight) {
|
||||
if (minutesAfterMidnight) { // Avoid NaN
|
||||
sum += minutesAfterMidnight;
|
||||
count++;
|
||||
}
|
||||
});
|
||||
|
||||
var averageMinutesAfterMidnight = Math.round(sum / count);
|
||||
|
||||
var dia = profile.getDIA();
|
||||
@@ -1068,56 +1078,54 @@ loopalyzer.generateReport = function(datastorage,daysToShow,options) {
|
||||
var borderWidth = 1;
|
||||
var labelWidth = 25;
|
||||
var xaxisCfg = {
|
||||
mode: 'time',
|
||||
timezone: 'browser',
|
||||
timeformat: '%H:%M',
|
||||
tickColor: tickColor,
|
||||
tickSize: [1, "hour"],
|
||||
font: { size: 0 }
|
||||
mode: 'time'
|
||||
, timezone: 'browser'
|
||||
, timeformat: '%H:%M'
|
||||
, tickColor: tickColor
|
||||
, tickSize: [1, "hour"]
|
||||
, font: { size: 0 }
|
||||
};
|
||||
|
||||
var hiddenAxis = {
|
||||
position: "right",
|
||||
show: true,
|
||||
labelWidth: 10,
|
||||
tickColor: "#FFFFFF",
|
||||
font: { size: 0}
|
||||
position: "right"
|
||||
, show: true
|
||||
, labelWidth: 10
|
||||
, tickColor: "#FFFFFF"
|
||||
, font: { size: 0 }
|
||||
}
|
||||
|
||||
// For drawing the carbs and insulin treatments
|
||||
var markings = [];
|
||||
var markingColor = "#000000";
|
||||
|
||||
|
||||
// Chart 1: Basal
|
||||
markings = [];
|
||||
if (doTimeShift)
|
||||
markings.push({ xaxis: { from: timeShiftStartTime.toDate(), to: timeShiftStopTime.toDate() }, color: timeShiftBackgroundColor });
|
||||
var chartBasalData = [{
|
||||
data: basalsAvg,
|
||||
label: translate('Basal profile'),
|
||||
id: 'basals',
|
||||
color: basalColor,
|
||||
points: { show: false },
|
||||
bars: { show: true, fill: true, barWidth: barWidth },
|
||||
yaxis: 1
|
||||
data: basalsAvg
|
||||
, label: translate('Basal profile')
|
||||
, id: 'basals'
|
||||
, color: basalColor
|
||||
, points: { show: false }
|
||||
, bars: { show: true, fill: true, barWidth: barWidth }
|
||||
, yaxis: 1
|
||||
}];
|
||||
var chartBasalOptions = {
|
||||
xaxis: xaxisCfg,
|
||||
yaxes: [{
|
||||
tickColor: tickColor,
|
||||
labelWidth: labelWidth,
|
||||
tickFormatter: function(val,axis) { return tickFormatter(val,axis); }
|
||||
},
|
||||
hiddenAxis],
|
||||
grid: {
|
||||
borderWidth: borderWidth,
|
||||
markings: markings
|
||||
xaxis: xaxisCfg
|
||||
, yaxes: [{
|
||||
tickColor: tickColor
|
||||
, labelWidth: labelWidth
|
||||
, tickFormatter: function(val, axis) { return tickFormatter(val, axis); }
|
||||
}
|
||||
, hiddenAxis]
|
||||
, grid: {
|
||||
borderWidth: borderWidth
|
||||
, markings: markings
|
||||
}
|
||||
};
|
||||
$.plot('#loopalyzer-basal', chartBasalData, chartBasalOptions);
|
||||
|
||||
|
||||
// Chart 2: Blood glucose
|
||||
markings = [];
|
||||
if (doTimeShift)
|
||||
@@ -1125,41 +1133,40 @@ loopalyzer.generateReport = function(datastorage,daysToShow,options) {
|
||||
markings.push({ yaxis: { from: low, to: high }, color: glucoseRangeColor });
|
||||
|
||||
var chartBGData = [{
|
||||
label: translate('Blood glucose'),
|
||||
data: sgvAvg,
|
||||
id: 'glucose',
|
||||
color: glucoseColor,
|
||||
points: { show: false },
|
||||
lines: { show: true }
|
||||
label: translate('Blood glucose')
|
||||
, data: sgvAvg
|
||||
, id: 'glucose'
|
||||
, color: glucoseColor
|
||||
, points: { show: false }
|
||||
, lines: { show: true }
|
||||
}];
|
||||
if (predictionsAvg && predictionsAvg.length > 0) {
|
||||
chartBGData.push({
|
||||
label: translate('Predictions'),
|
||||
data: predictionsAvg,
|
||||
id: 'predictions',
|
||||
color: predictionsColor,
|
||||
points: { show: true, fill: true, radius: 0.75, fillColor: predictionsColor },
|
||||
lines: { show: false }
|
||||
label: translate('Predictions')
|
||||
, data: predictionsAvg
|
||||
, id: 'predictions'
|
||||
, color: predictionsColor
|
||||
, points: { show: true, fill: true, radius: 0.75, fillColor: predictionsColor }
|
||||
, lines: { show: false }
|
||||
});
|
||||
}
|
||||
var chartBGOptions = {
|
||||
xaxis: xaxisCfg,
|
||||
yaxes: [{
|
||||
min: 0,
|
||||
max: options.units === 'mmol' ? 20 : 400,
|
||||
tickColor: tickColor,
|
||||
labelWidth: labelWidth,
|
||||
tickFormatter: function(val,axis) { return tickFormatter(val,axis); }
|
||||
},
|
||||
hiddenAxis],
|
||||
grid: {
|
||||
borderWidth: borderWidth,
|
||||
markings: markings
|
||||
xaxis: xaxisCfg
|
||||
, yaxes: [{
|
||||
min: 0
|
||||
, max: options.units === 'mmol' ? 20 : 400
|
||||
, tickColor: tickColor
|
||||
, labelWidth: labelWidth
|
||||
, tickFormatter: function(val, axis) { return tickFormatter(val, axis); }
|
||||
}
|
||||
, hiddenAxis]
|
||||
, grid: {
|
||||
borderWidth: borderWidth
|
||||
, markings: markings
|
||||
}
|
||||
};
|
||||
$.plot('#loopalyzer-bg', chartBGData, chartBGOptions);
|
||||
|
||||
|
||||
// Chart 3: Delta temp basals
|
||||
markings = [];
|
||||
if (doTimeShift)
|
||||
@@ -1167,29 +1174,28 @@ loopalyzer.generateReport = function(datastorage,daysToShow,options) {
|
||||
markings.push({ yaxis: { from: 0, to: 0 }, color: insulinColor, lineWidth: 2 });
|
||||
|
||||
var chartTempBasalData = [{
|
||||
data: tempBasalsAvg,
|
||||
label: translate('Temp basal delta'),
|
||||
id: 'tempBasals',
|
||||
color: insulinColor,
|
||||
points: { show: false },
|
||||
bars: { show: true, barWidth: barWidth }
|
||||
data: tempBasalsAvg
|
||||
, label: translate('Temp basal delta')
|
||||
, id: 'tempBasals'
|
||||
, color: insulinColor
|
||||
, points: { show: false }
|
||||
, bars: { show: true, barWidth: barWidth }
|
||||
}];
|
||||
var chartTempBasalOptions = {
|
||||
xaxis: xaxisCfg,
|
||||
yaxes: [{
|
||||
tickColor: tickColor,
|
||||
labelWidth: labelWidth,
|
||||
tickFormatter: function(val,axis) { return tickFormatter(val,axis); }
|
||||
},
|
||||
hiddenAxis],
|
||||
grid: {
|
||||
borderWidth: borderWidth,
|
||||
markings: markings
|
||||
xaxis: xaxisCfg
|
||||
, yaxes: [{
|
||||
tickColor: tickColor
|
||||
, labelWidth: labelWidth
|
||||
, tickFormatter: function(val, axis) { return tickFormatter(val, axis); }
|
||||
}
|
||||
, hiddenAxis]
|
||||
, grid: {
|
||||
borderWidth: borderWidth
|
||||
, markings: markings
|
||||
}
|
||||
};
|
||||
$.plot('#loopalyzer-tempbasal', chartTempBasalData, chartTempBasalOptions);
|
||||
|
||||
|
||||
// Chart 4: IOB
|
||||
markings = [];
|
||||
if (doTimeShift)
|
||||
@@ -1204,29 +1210,28 @@ loopalyzer.generateReport = function(datastorage,daysToShow,options) {
|
||||
})
|
||||
|
||||
var chartIOBData = [{
|
||||
data: iobAvg,
|
||||
label: translate('IOB'),
|
||||
id: 'iobs',
|
||||
color: insulinColor,
|
||||
points: { show: false },
|
||||
bars: { show: true, fill: true, barWidth: barWidth }
|
||||
data: iobAvg
|
||||
, label: translate('IOB')
|
||||
, id: 'iobs'
|
||||
, color: insulinColor
|
||||
, points: { show: false }
|
||||
, bars: { show: true, fill: true, barWidth: barWidth }
|
||||
}];
|
||||
var chartIOBOptions = {
|
||||
xaxis: xaxisCfg,
|
||||
yaxes: [{
|
||||
tickColor: tickColor,
|
||||
labelWidth: labelWidth,
|
||||
tickFormatter: function(val,axis) { return tickFormatter(val,axis); }
|
||||
},
|
||||
hiddenAxis],
|
||||
grid: {
|
||||
borderWidth: borderWidth,
|
||||
markings: markings
|
||||
xaxis: xaxisCfg
|
||||
, yaxes: [{
|
||||
tickColor: tickColor
|
||||
, labelWidth: labelWidth
|
||||
, tickFormatter: function(val, axis) { return tickFormatter(val, axis); }
|
||||
}
|
||||
, hiddenAxis]
|
||||
, grid: {
|
||||
borderWidth: borderWidth
|
||||
, markings: markings
|
||||
}
|
||||
};
|
||||
$.plot('#loopalyzer-iob', chartIOBData, chartIOBOptions);
|
||||
|
||||
|
||||
// Chart 5: COB
|
||||
markings = [];
|
||||
if (doTimeShift)
|
||||
@@ -1242,24 +1247,24 @@ loopalyzer.generateReport = function(datastorage,daysToShow,options) {
|
||||
delete xaxisCfg.font; // Remove the font config so HH:MM is shown on the last chart
|
||||
|
||||
var chartCOBData = [{
|
||||
data: cobAvg,
|
||||
label: translate('COB'),
|
||||
id: 'cobs',
|
||||
color: carbColor,
|
||||
points: { show: false },
|
||||
bars: { show: true, fil: true, barWidth: barWidth }
|
||||
data: cobAvg
|
||||
, label: translate('COB')
|
||||
, id: 'cobs'
|
||||
, color: carbColor
|
||||
, points: { show: false }
|
||||
, bars: { show: true, fil: true, barWidth: barWidth }
|
||||
}];
|
||||
var chartCOBOptions = {
|
||||
xaxis: xaxisCfg,
|
||||
yaxes: [{
|
||||
tickColor: tickColor,
|
||||
labelWidth: labelWidth,
|
||||
tickFormatter: function(val,axis) { return tickFormatter(val,axis); }
|
||||
},
|
||||
hiddenAxis],
|
||||
grid: {
|
||||
borderWidth: borderWidth,
|
||||
markings: markings
|
||||
xaxis: xaxisCfg
|
||||
, yaxes: [{
|
||||
tickColor: tickColor
|
||||
, labelWidth: labelWidth
|
||||
, tickFormatter: function(val, axis) { return tickFormatter(val, axis); }
|
||||
}
|
||||
, hiddenAxis]
|
||||
, grid: {
|
||||
borderWidth: borderWidth
|
||||
, markings: markings
|
||||
}
|
||||
};
|
||||
$.plot('#loopalyzer-cob', chartCOBData, chartCOBOptions);
|
||||
|
||||
@@ -15,23 +15,22 @@ module.exports = init;
|
||||
profiles.html = function html (client) {
|
||||
var translate = client.translate;
|
||||
var ret =
|
||||
'<h2>' + translate('Profiles') + '</h2>'
|
||||
+ '<br>' + translate('Database records') + ' '
|
||||
+ '<br><select id="profiles-databaserecords"></select>'
|
||||
+ '<br><span id="profiles-default"></span>'
|
||||
+ '<div id="profiles-chart">'
|
||||
+ '</div>'
|
||||
;
|
||||
'<h2>' + translate('Profiles') + '</h2>' +
|
||||
'<br>' + translate('Database records') + ' ' +
|
||||
'<br><select id="profiles-databaserecords"></select>' +
|
||||
'<br><span id="profiles-default"></span>' +
|
||||
'<div id="profiles-chart">' +
|
||||
'</div>';
|
||||
return ret;
|
||||
};
|
||||
|
||||
profiles.css =
|
||||
'#profiles-chart {'
|
||||
+ ' width: 100%;'
|
||||
+ ' height: 100%;'
|
||||
+ '}'
|
||||
;
|
||||
'#profiles-chart {' +
|
||||
' width: 100%;' +
|
||||
' height: 100%;' +
|
||||
'}';
|
||||
|
||||
// eslint-disable-next-line no-unused-vars
|
||||
profiles.report = function report_profiles (datastorage, sorteddaystoshow, options) {
|
||||
var Nightscout = window.Nightscout;
|
||||
var client = Nightscout.client;
|
||||
@@ -58,11 +57,10 @@ profiles.report = function report_profiles(datastorage, sorteddaystoshow, option
|
||||
var tr = $('<tr>');
|
||||
|
||||
$('#profiles-default').val(currentrecord.defaultProfile);
|
||||
for (var key in currentrecord.store) {
|
||||
if (currentrecord.store.hasOwnProperty(key)) {
|
||||
tr.append(displayRecord(currentrecord.store[key], key))
|
||||
}
|
||||
}
|
||||
|
||||
Object.keys(currentrecord.store).forEach(key => {
|
||||
tr.append(displayRecord(currentrecord.store[key], key));
|
||||
});
|
||||
|
||||
table.append(tr);
|
||||
|
||||
|
||||
@@ -17,39 +17,33 @@ module.exports = init;
|
||||
success.html = function html (client) {
|
||||
var translate = client.translate;
|
||||
var ret =
|
||||
'<h2>' + translate('Weekly Success') + '</h2>'
|
||||
+ '<div id="success-grid"></div>'
|
||||
;
|
||||
'<h2>' + translate('Weekly Success') + '</h2>' +
|
||||
'<div id="success-grid"></div>';
|
||||
return ret;
|
||||
};
|
||||
|
||||
success.css =
|
||||
'#success-placeholder td {'+
|
||||
' border: 1px #ccc solid;'+
|
||||
' margin: 0;'+
|
||||
' padding: 1px;'+
|
||||
' text-align:center;'+
|
||||
'}'+
|
||||
'#success-placeholder .bad {'+
|
||||
' background-color: #fcc;'+
|
||||
'}'+
|
||||
|
||||
'#success-placeholder .good {'+
|
||||
' background-color: #cfc;'+
|
||||
'}'+
|
||||
|
||||
'#success-placeholder th:first-child {'+
|
||||
' width: 30%;'+
|
||||
'}'+
|
||||
'#success-placeholder th {'+
|
||||
' width: 10%;'+
|
||||
'}'+
|
||||
'#success-placeholder table {'+
|
||||
' width: 100%;'+
|
||||
'}'
|
||||
;
|
||||
|
||||
|
||||
`#success-placeholder td {
|
||||
border: 1px #ccc solid;
|
||||
margin: 0;
|
||||
padding: 1px;
|
||||
text-align:center;
|
||||
}
|
||||
#success-placeholder .bad {
|
||||
background-color: #fcc;
|
||||
}
|
||||
#success-placeholder .good {
|
||||
background-color: #cfc;
|
||||
}
|
||||
#success-placeholder th:first-child {
|
||||
width: 30%;
|
||||
}
|
||||
#success-placeholder th {
|
||||
width: 10%;
|
||||
}
|
||||
#success-placeholder table {
|
||||
width: 100%;
|
||||
}`;
|
||||
|
||||
success.report = function report_success (datastorage, sorteddaystoshow, options) {
|
||||
var Nightscout = window.Nightscout;
|
||||
@@ -58,8 +52,8 @@ success.report = function report_success(datastorage, sorteddaystoshow, options)
|
||||
|
||||
var ss = require('simple-statistics');
|
||||
|
||||
var low = options.targetLow,
|
||||
high = options.targetHigh;
|
||||
var low = options.targetLow
|
||||
, high = options.targetHigh;
|
||||
|
||||
var data = datastorage.allstatsrecords;
|
||||
|
||||
@@ -96,21 +90,21 @@ success.report = function report_success(datastorage, sorteddaystoshow, options)
|
||||
}, 0);
|
||||
};
|
||||
var averages = {
|
||||
percentLow: 0,
|
||||
percentInRange: 0,
|
||||
percentHigh: 0,
|
||||
standardDeviation: 0,
|
||||
lowerQuartile: 0,
|
||||
upperQuartile: 0,
|
||||
average: 0
|
||||
percentLow: 0
|
||||
, percentInRange: 0
|
||||
, percentHigh: 0
|
||||
, standardDeviation: 0
|
||||
, lowerQuartile: 0
|
||||
, upperQuartile: 0
|
||||
, average: 0
|
||||
};
|
||||
quarters = dim(quarters).map(function(blank, n) {
|
||||
var starting = new Date(now - (n+1) * period),
|
||||
ending = new Date(now - n * period);
|
||||
var starting = new Date(now - (n + 1) * period)
|
||||
, ending = new Date(now - n * period);
|
||||
return {
|
||||
starting: starting,
|
||||
ending: ending,
|
||||
records: data.filter(function(record) {
|
||||
starting: starting
|
||||
, ending: ending
|
||||
, records: data.filter(function(record) {
|
||||
return record.displayTime > starting && record.displayTime <= ending;
|
||||
})
|
||||
};
|
||||
@@ -178,38 +172,38 @@ success.report = function report_success(datastorage, sorteddaystoshow, options)
|
||||
}).map(function(quarter) {
|
||||
var INVERT = true;
|
||||
return '<tr>' + [
|
||||
quarter.starting.toLocaleDateString() + ' - ' + quarter.ending.toLocaleDateString(),
|
||||
{
|
||||
klass: lowComparison(quarter, averages, 'percentLow'),
|
||||
text: Math.round(quarter.percentLow) + '%'
|
||||
},
|
||||
{
|
||||
klass: lowComparison(quarter, averages, 'percentInRange', INVERT),
|
||||
text: Math.round(quarter.percentInRange) + '%'
|
||||
},
|
||||
{
|
||||
klass: lowComparison(quarter, averages, 'percentHigh'),
|
||||
text: Math.round(quarter.percentHigh) + '%'
|
||||
},
|
||||
{
|
||||
klass: lowComparison(quarter, averages, 'standardDeviation'),
|
||||
text: (quarter.standardDeviation > 10? Math.round(quarter.standardDeviation): quarter.standardDeviation.toFixed(1))
|
||||
},
|
||||
{
|
||||
klass: lowQuartileEvaluation(quarter, averages),
|
||||
text: quarter.lowerQuartile
|
||||
},
|
||||
{
|
||||
klass: lowComparison(quarter, averages, 'average'),
|
||||
text: quarter.average.toFixed(1)
|
||||
},
|
||||
{
|
||||
klass: upperQuartileEvaluation(quarter, averages),
|
||||
text: quarter.upperQuartile
|
||||
quarter.starting.toLocaleDateString() + ' - ' + quarter.ending.toLocaleDateString()
|
||||
, {
|
||||
klass: lowComparison(quarter, averages, 'percentLow')
|
||||
, text: Math.round(quarter.percentLow) + '%'
|
||||
}
|
||||
, {
|
||||
klass: lowComparison(quarter, averages, 'percentInRange', INVERT)
|
||||
, text: Math.round(quarter.percentInRange) + '%'
|
||||
}
|
||||
, {
|
||||
klass: lowComparison(quarter, averages, 'percentHigh')
|
||||
, text: Math.round(quarter.percentHigh) + '%'
|
||||
}
|
||||
, {
|
||||
klass: lowComparison(quarter, averages, 'standardDeviation')
|
||||
, text: (quarter.standardDeviation > 10 ? Math.round(quarter.standardDeviation) : quarter.standardDeviation.toFixed(1))
|
||||
}
|
||||
, {
|
||||
klass: lowQuartileEvaluation(quarter, averages)
|
||||
, text: quarter.lowerQuartile
|
||||
}
|
||||
, {
|
||||
klass: lowComparison(quarter, averages, 'average')
|
||||
, text: quarter.average.toFixed(1)
|
||||
}
|
||||
, {
|
||||
klass: upperQuartileEvaluation(quarter, averages)
|
||||
, text: quarter.upperQuartile
|
||||
}
|
||||
].map(function(v) {
|
||||
if (typeof v === 'object') {
|
||||
return '<td class=\"' + v.klass + '\">' + v.text + '</td>';
|
||||
return '<td class="' + v.klass + '">' + v.text + '</td>';
|
||||
} else {
|
||||
return '<td>' + v + '</td>';
|
||||
}
|
||||
|
||||
+2
-7
@@ -116,7 +116,7 @@ function init ( ) {
|
||||
* @param setter
|
||||
*/
|
||||
sbx.offerProperty = function offerProperty (name, setter) {
|
||||
if (!sbx.properties.hasOwnProperty(name)) {
|
||||
if (!Object.keys(sbx.properties).includes(name)) {
|
||||
var value = setter();
|
||||
if (value) {
|
||||
sbx.properties[name] = value;
|
||||
@@ -272,14 +272,10 @@ function init ( ) {
|
||||
if (sbx.properties.roundingStyle === 'medtronic') {
|
||||
var denominator = 0.1;
|
||||
var digits = 1;
|
||||
if (insulin > 0.5 && iob < 1) {
|
||||
if (insulin <= 0.5) {
|
||||
denominator = 0.05;
|
||||
digits = 2;
|
||||
}
|
||||
if (insulin <= 0.5) {
|
||||
denominator = 0.025;
|
||||
digits = 3;
|
||||
}
|
||||
return (Math.floor(insulin / denominator) * denominator).toFixed(digits);
|
||||
}
|
||||
|
||||
@@ -299,4 +295,3 @@ function init ( ) {
|
||||
}
|
||||
|
||||
module.exports = init;
|
||||
|
||||
|
||||
@@ -28,6 +28,7 @@ CACHE MANIFEST
|
||||
/css/main.css?v=<%= locals.cachebuster %>
|
||||
/bundle/js/bundle.app.js?v=<%= locals.cachebuster %>
|
||||
/bundle/js/bundle.clock.js?v=<%= locals.cachebuster %>
|
||||
/bundle/js/bundle.report.js?v=<%= locals.cachebuster %>
|
||||
/socket.io/socket.io.js?v=<%= locals.cachebuster %>
|
||||
/js/client.js?v=<%= locals.cachebuster %>
|
||||
/images/logo2.png
|
||||
|
||||
+1
-1
@@ -115,7 +115,7 @@ if (process.env.NODE_ENV == 'development') {
|
||||
rules.unshift({
|
||||
enforce: "pre",
|
||||
test: /\.js$/,
|
||||
exclude: /node_modules/,
|
||||
exclude: [/node_modules/, /bundle/],
|
||||
loader: "eslint-loader",
|
||||
options: {
|
||||
emitWarning: true,
|
||||
|
||||
Reference in New Issue
Block a user