bthrm - Reimplement viewer app with layout

master
Martin Boonk 2022-12-01 22:49:02 +01:00
parent 6b6dc4b14e
commit 1530ed3915
1 changed files with 139 additions and 52 deletions

View File

@ -1,5 +1,9 @@
var intervalInt; var intervalInt;
var intervalBt; var intervalBt;
var intervalAgg;
const BPM_FONT_SIZE="19%";
const VALUE_TIMEOUT=3000;
var BODY_LOCS = { var BODY_LOCS = {
0: 'Other', 0: 'Other',
@ -7,40 +11,123 @@ var BODY_LOCS = {
2: 'Wrist', 2: 'Wrist',
3: 'Finger', 3: 'Finger',
4: 'Hand', 4: 'Hand',
5: 'Ear Lobe', 5: 'Earlobe',
6: 'Foot', 6: 'Foot',
};
var Layout = require("Layout");
function border(l,c) {
g.setColor(c).drawLine(l.x+l.w*0.05, l.y-4, l.x+l.w*0.95, l.y-4);
c++;
} }
function clear(y){ function getRow(id, text, additionalInfo){
g.reset(); let additional = [];
g.clearRect(0,y,g.getWidth(),y+75); let l = {
} type:"h", c: [
{
function draw(y, type, event) { type:"v",
clear(y); width: g.getWidth()*0.4,
var px = g.getWidth()/2; c: [
var str = event.bpm + ""; {type:"txt", halign:1, font:"8%", label:text, id:id+"text" },
g.reset(); {type:"txt", halign:1, font:BPM_FONT_SIZE, label:"--", id:id, bgCol: g.theme.bg }
g.setFontAlign(0,0); ]
g.setFontVector(40).drawString(str,px,y+20); },{
str = "Event: " + type; type:undefined, fillx:1
if (type === "HRM") { },{
str += " Confidence: " + event.confidence; type:"v",
g.setFontVector(12).drawString(str,px,y+40); valign: -1,
str = " Source: " + (event.src ? event.src : "internal"); width: g.getWidth()*0.45,
g.setFontVector(12).drawString(str,px,y+50); c: additional
},{
type:undefined, width:g.getWidth()*0.05
} }
if (type === "BTHRM"){ ]
if (event.battery) str += " Bat: " + (event.battery ? event.battery : ""); };
g.setFontVector(12).drawString(str,px,y+40); for (let i of additionalInfo){
str= ""; let label = {type:"txt", font:"6x8", label:i + ":" };
if (event.location) str += "Loc: " + BODY_LOCS[event.location]; let value = {type:"txt", font:"6x8", label:"--", id:id + i };
if (event.rr && event.rr.length > 0) str += " RR: " + event.rr.join(","); additional.push({type:"h", halign:-1, c:[ label, {type:undefined, fillx:1}, value ]});
g.setFontVector(12).drawString(str,px,y+50); }
str= "";
if (event.contact) str += " Contact: " + event.contact; return l;
if (event.energy) str += " kJoule: " + event.energy.toFixed(0); }
g.setFontVector(12).drawString(str,px,y+60);
var layout = new Layout( {
type:"v", c: [
getRow("int", "INT", ["Confidence"]),
getRow("agg", "HRM", ["Confidence", "Source"]),
getRow("bt", "BT", ["Battery","Location","Contact", "RR", "Energy"]),
{ type:undefined, height:8 } //dummy to protect debug output
]
}, {
lazy:true
});
var int,agg,bt;
var firstEvent = true;
var drawTimeout;
function draw(){
if (drawTimeout) clearTimeout(drawTimeout);
drawTimeout = setTimeout(function() {
drawTimeout = undefined;
draw();
}, 1000);
if (!(int || agg || bt)) return;
if (firstEvent) {
g.clearRect(Bangle.appRect);
firstEvent = false;
}
if (int){
layout.int.label = int.bpm;
if (!isNaN(int.confidence)) layout.intConfidence.label = int.confidence;
} else {
layout.int.label = "--";
layout.intConfidence.label = "--";
}
if (agg){
layout.agg.label = agg.bpm;
if (!isNaN(agg.confidence)) layout.aggConfidence.label = agg.confidence;
if (agg.src) layout.aggSource.label = agg.src;
} else {
layout.agg.label = "--";
layout.aggConfidence.label = "--";
layout.aggSource.label = "--";
}
if (bt) {
layout.bt.label = bt.bpm;
if (bt.battery) layout.btBattery.label = bt.battery;
if (bt.rr) layout.btRR.label = bt.rr.join(",");
if (bt.location) layout.btLocation.label = BODY_LOCS[bt.location];
if (bt.contact !== undefined) layout.btContact.label = bt.contact ? "Yes":"No";
if (bt.energy) layout.btEnergy.label = bt.energy.toFixed(0) + "kJ";
} else {
layout.bt.label = "--";
layout.btBattery.label = "--";
layout.btRR.label = "--";
layout.btLocation.label = "--";
layout.btContact.label = "--";
layout.btEnergy.label = "--";
}
layout.update();
layout.render();
let first = true;
for (let c of layout.l.c){
if (first) {
first = false;
continue;
}
if (c.type && c.type == "h")
border(c,g.theme.fg);
} }
} }
@ -57,11 +144,7 @@ function showStatusInfo(txt) {
} }
function onBtHrm(e) { function onBtHrm(e) {
if (firstEventBt){ bt = e;
clear(24);
firstEventBt = false;
}
draw(100, "BTHRM", e);
if (e.bpm === 0){ if (e.bpm === 0){
Bangle.buzz(100,0.2); Bangle.buzz(100,0.2);
} }
@ -69,34 +152,37 @@ function onBtHrm(e) {
clearInterval(intervalBt); clearInterval(intervalBt);
} }
intervalBt = setInterval(()=>{ intervalBt = setInterval(()=>{
clear(100); bt = undefined;
}, 2000); }, VALUE_TIMEOUT);
} }
function onHrm(e) { function onInt(e) {
if (firstEventInt){ int = e;
clear(24);
firstEventInt = false;
}
draw(24, "HRM", e);
if (intervalInt){ if (intervalInt){
clearInterval(intervalInt); clearInterval(intervalInt);
} }
intervalInt = setInterval(()=>{ intervalInt = setInterval(()=>{
clear(24); int = undefined;
}, 2000); }, VALUE_TIMEOUT);
}
function onAgg(e) {
agg = e;
if (intervalAgg){
clearInterval(intervalAgg);
}
intervalAgg = setInterval(()=>{
agg = undefined;
}, VALUE_TIMEOUT);
} }
var settings = require('Storage').readJSON("bthrm.json", true) || {}; var settings = require('Storage').readJSON("bthrm.json", true) || {};
Bangle.on('BTHRM', onBtHrm); Bangle.on('BTHRM', onBtHrm);
Bangle.on('HRM_int', onInt);
Bangle.on('HRM', onAgg);
if (settings.replace){
Bangle.on('HRM_int', onHrm);
} else {
Bangle.on('HRM', onHrm);
}
Bangle.setHRMPower(1,'bthrm'); Bangle.setHRMPower(1,'bthrm');
if (!(settings.startWithHrm)){ if (!(settings.startWithHrm)){
@ -108,10 +194,11 @@ Bangle.loadWidgets();
Bangle.drawWidgets(); Bangle.drawWidgets();
if (Bangle.setBTHRMPower){ if (Bangle.setBTHRMPower){
g.reset().setFont("6x8",2).setFontAlign(0,0); g.reset().setFont("6x8",2).setFontAlign(0,0);
g.drawString("Please wait...",g.getWidth()/2,g.getHeight()/2 - 24); g.drawString("Please wait...",g.getWidth()/2,g.getHeight()/2);
draw();
} else { } else {
g.reset().setFont("6x8",2).setFontAlign(0,0); g.reset().setFont("6x8",2).setFontAlign(0,0);
g.drawString("BTHRM disabled",g.getWidth()/2,g.getHeight()/2 + 32); g.drawString("BTHRM disabled",g.getWidth()/2,g.getHeight()/2);
} }
E.on('kill', ()=>Bangle.setBTHRMPower(0,'bthrm')); E.on('kill', ()=>Bangle.setBTHRMPower(0,'bthrm'));