Layout module now allows 'soft' buttons to be cycled through and selected using up/down on Bangle.js 1
|
@ -99,12 +99,12 @@ function startRecord(force) {
|
|||
{type:"txt", id:"time", font:"6x8:2", label:" - ", pad:5, bgCol:g.theme.bg},
|
||||
{type:"txt", font:"6x8:2", label:"RECORDING", bgCol:"#f00", pad:5, fillx:1},
|
||||
]
|
||||
},[ // Buttons...
|
||||
},{btns:[ // Buttons...
|
||||
{label:"STOP", cb:()=>{
|
||||
Bangle.removeListener('accel', accelHandler);
|
||||
showMenu();
|
||||
}}
|
||||
]);
|
||||
]});
|
||||
layout.render();
|
||||
|
||||
// now start writing
|
||||
|
|
|
@ -40,7 +40,7 @@ const layout = new Layout({
|
|||
{height: 40},
|
||||
{id: "date", type: "txt", font: "10%", valign: 1},
|
||||
],
|
||||
}, false, {lazy: true});
|
||||
}, {lazy: true});
|
||||
// adjustments based on screen size and whether we display am/pm
|
||||
let thickness; // bar thickness, same as time font "pixel block" size
|
||||
if (is12Hour) {
|
||||
|
|
|
@ -68,7 +68,7 @@ function onGPS(fix) {
|
|||
{type:"txt", font:"6x8", label:"", fillx:true, id:"time" },
|
||||
{type:"txt", font:"6x8", label:"", fillx:true, id:"sat" },
|
||||
{type:"txt", font:"6x8", label:"", fillx:true, id:"maidenhead" },
|
||||
]},[],{lazy:true});
|
||||
]},{lazy:true});
|
||||
} else {
|
||||
layout = new Layout( {
|
||||
type:"v", c: [
|
||||
|
@ -80,7 +80,7 @@ function onGPS(fix) {
|
|||
{type:"txt", font:"6x8", pad:3, label:"Satellites" }
|
||||
]},
|
||||
{type:"txt", font:"6x8", label:"", id:"progress" }
|
||||
]},[],{lazy:true});
|
||||
]},{lazy:true});
|
||||
}
|
||||
g.clearRect(0,24,g.getWidth(),g.getHeight());
|
||||
layout.render();
|
||||
|
|
|
@ -23,7 +23,7 @@ function onGPS(fix) {
|
|||
{type:"txt", font:"10%", label:fix.satellites, pad:2, id:"sat" },
|
||||
{type:"txt", font:"6x8", pad:3, label:"Satellites" }
|
||||
]},
|
||||
]},[],{lazy:true});
|
||||
]},{lazy:true});
|
||||
} else {
|
||||
layout = new Layout( {
|
||||
type:"v", c: [
|
||||
|
@ -34,7 +34,7 @@ function onGPS(fix) {
|
|||
{type:"txt", font:"10%", label:fix.satellites, pad:2, id:"sat" },
|
||||
{type:"txt", font:"6x8", pad:3, label:"Satellites" }
|
||||
]},
|
||||
]},[],{lazy:true});
|
||||
]},{lazy:true});
|
||||
}
|
||||
g.clearRect(0,24,g.getWidth(),g.getHeight());
|
||||
layout.render();
|
||||
|
|
|
@ -35,7 +35,7 @@ var layout = new Layout({type:"v", bgCol: g.theme.bg, c: [
|
|||
{type: "txt", font: "6x8", pad: 4, id: "updateTime", label: "15 minutes ago"},
|
||||
]},
|
||||
{filly: 1},
|
||||
]}, null, {lazy: true});
|
||||
]}, {lazy: true});
|
||||
|
||||
function formatDuration(millis) {
|
||||
let pluralize = (n, w) => n + " " + w + (n == 1 ? "" : "s");
|
||||
|
|
|
@ -4,7 +4,7 @@ Usage:
|
|||
|
||||
```
|
||||
var Layout = require("Layout");
|
||||
var layout = new Layout( layoutObject, btns, options )
|
||||
var layout = new Layout( layoutObject, options )
|
||||
layout.render(optionalObject);
|
||||
```
|
||||
|
||||
|
@ -47,15 +47,13 @@ layoutObject has:
|
|||
* A `filly` int to choose if the object should fill available space in y. 0=no, 1=yes, 2=2x more space
|
||||
* `width` and `height` fields to optionally specify minimum size
|
||||
|
||||
btns is an array of objects containing:
|
||||
|
||||
* `label` - the text on the button
|
||||
* `cb` - a callback function
|
||||
* `cbl` - a callback function for long presses
|
||||
|
||||
options is an object containing:
|
||||
|
||||
* `lazy` - a boolean specifying whether to enable automatic lazy rendering
|
||||
* `btns` - array of objects containing:
|
||||
* `label` - the text on the button
|
||||
* `cb` - a callback function
|
||||
* `cbl` - a callback function for long presses
|
||||
|
||||
If automatic lazy rendering is enabled, calls to `layout.render()` will attempt to automatically
|
||||
determine what objects have changed or moved, clear their previous locations, and re-render just those objects.
|
||||
|
@ -78,9 +76,8 @@ Other functions:
|
|||
*/
|
||||
|
||||
|
||||
function Layout(layout, buttons, options) {
|
||||
function Layout(layout, options) {
|
||||
this._l = this.l = layout;
|
||||
this.b = buttons;
|
||||
// Do we have >1 physical buttons?
|
||||
this.physBtns = (process.env.HWVERSION==2) ? 1 : 3;
|
||||
this.yOffset = Object.keys(global.WIDGETS).length ? 24 : 0;
|
||||
|
@ -88,7 +85,43 @@ function Layout(layout, buttons, options) {
|
|||
options = options || {};
|
||||
this.lazy = options.lazy || false;
|
||||
|
||||
if (buttons) {
|
||||
var btnList;
|
||||
if (process.env.HWVERSION!=2) {
|
||||
// no touchscreen, find any buttons in 'layout'
|
||||
btnList = [];
|
||||
function btnRecurser(l) {
|
||||
if (l.type=="btn") btnList.push(l);
|
||||
if (l.c) l.c.forEach(btnRecurser);
|
||||
}
|
||||
btnRecurser(layout);
|
||||
if (btnList.length) { // there are buttons in 'layout'
|
||||
// disable physical buttons - use them for back/next/select
|
||||
this.physBtns = 0;
|
||||
this.buttons = btnList;
|
||||
this.selectedButton = -1;
|
||||
Bangle.setUI("updown", dir=>{
|
||||
var s = this.selectedButton, l=this.buttons.length;
|
||||
if (dir===undefined && this.buttons[s])
|
||||
return this.buttons[s].cb();
|
||||
if (this.buttons[s]) {
|
||||
delete this.buttons[s].selected;
|
||||
this.render(this.buttons[s]);
|
||||
}
|
||||
s += dir;
|
||||
if (s<0) s+=lh;
|
||||
if (s>=l) s-=l;
|
||||
if (this.buttons[s]) {
|
||||
this.buttons[s].selected = 1;
|
||||
this.render(this.buttons[s]);
|
||||
}
|
||||
this.selectedButton = s;
|
||||
});
|
||||
}
|
||||
}
|
||||
|
||||
if (options.btns) {
|
||||
var buttons = options.btns;
|
||||
this.b = buttons;
|
||||
if (this.physBtns >= buttons.length) {
|
||||
// Handler for button watch events
|
||||
function pressHandler(btn,e) {
|
||||
|
@ -114,12 +147,14 @@ function Layout(layout, buttons, options) {
|
|||
{type:"v", pad:1, filly:1, c: buttons.map(b=>(b.type="txt",b.font="6x8",b.height=btnHeight,b.r=1,b))}
|
||||
]};
|
||||
} else {
|
||||
let btnHeight = Math.floor((g.getHeight()-this.yOffset) / buttons.length);
|
||||
this._l.width = g.getWidth()-20; // button width
|
||||
// add 'soft' buttons
|
||||
this._l.width = g.getWidth()-32; // button width
|
||||
this._l = {type:"h", c: [
|
||||
this._l,
|
||||
{type:"v", c: buttons.map(b=>(b.type="btn",b.h=btnHeight,b.w=32,b.r=1,b))}
|
||||
{type:"v", c: buttons.map(b=>(b.type="btn",b.filly=1,b.width=32,b.r=1,b))}
|
||||
]};
|
||||
// if we're selecting with physical buttons, add these to the list
|
||||
if (btnList) btnList.push.apply(btnList, this._l.c[1].c);
|
||||
}
|
||||
}
|
||||
if (process.env.HWVERSION==2) {
|
||||
|
@ -233,7 +268,7 @@ Layout.prototype.render = function (l) {
|
|||
x,y+h-5,
|
||||
x,y+4
|
||||
];
|
||||
g.setColor(g.theme.bgH).fillPoly(poly).setColor(l.selected ? g.theme.fgH : g.theme.fg).drawPoly(poly).setFont("4x6",2).setFontAlign(0,0,l.r).drawString(l.label,l.x+l.w/2,l.y+l.h/2);
|
||||
g.setColor(l.selected?g.theme.bgH:g.theme.bg2).fillPoly(poly).setColor(l.selected ? g.theme.fgH : g.theme.fg2).drawPoly(poly).setFont("6x8",2).setFontAlign(0,0,l.r).drawString(l.label,l.x+l.w/2,l.y+l.h/2);
|
||||
}, "img":function(l){
|
||||
g.drawImage(l.src(), l.x + (0|l.pad), l.y + (0|l.pad));
|
||||
}, "custom":function(l){
|
||||
|
@ -347,8 +382,8 @@ Layout.prototype.update = function() {
|
|||
l._w = g.stringWidth(l.label);
|
||||
}
|
||||
}, "btn": function(l) {
|
||||
l._h = 24;
|
||||
l._w = 14 + l.label.length*8;
|
||||
l._h = 32;
|
||||
l._w = 20 + l.label.length*12;
|
||||
}, "img": function(l) {
|
||||
var src = l.src(); // get width and height out of image
|
||||
if (src[0]) {
|
||||
|
@ -407,5 +442,3 @@ Layout.prototype.clear = function(l) {
|
|||
if (l.bgCol!==undefined) g.setBgColor(l.bgCol);
|
||||
g.clearRect(l.x,l.y,l.x+l.w-1,l.y+l.h-1);
|
||||
};
|
||||
|
||||
exports = Layout;
|
||||
|
|
|
@ -19,7 +19,7 @@ SRCBMP=$SRCDIR/`basename $SRCJS .js`.bmp
|
|||
echo "TEST $SRCJS ($SRCBMP)"
|
||||
|
||||
cat ../../modules/Layout.js > $TESTJS
|
||||
echo 'Bangle = {};BTN1=0;process.env = process.env;process.env.HWVERSION=2;' >> $TESTJS
|
||||
echo 'Bangle = { setUI : function(){} };BTN1=0;process.env = process.env;process.env.HWVERSION=2;' >> $TESTJS
|
||||
echo 'g = Graphics.createArrayBuffer(176,176,4);' >> $TESTJS
|
||||
cat $SRCJS >> $TESTJS || exit 1
|
||||
echo 'layout.render()' >> $TESTJS
|
||||
|
@ -39,5 +39,3 @@ else
|
|||
echo Files are the same
|
||||
exit 0
|
||||
fi
|
||||
|
||||
|
||||
|
|
|
@ -6,8 +6,8 @@ var layout = new Layout({ type: "v", c: [
|
|||
{type:"txt", id:"time", font:"6x8:2", label:" - ", pad:5},
|
||||
{type:"txt", font:"6x8:2", label:"RECORDING", bgCol:"#f00", pad:5, fillx:1},
|
||||
]
|
||||
},[ // Buttons...
|
||||
}{btns:[ // Buttons...
|
||||
{label:"STOP", cb:()=>{}}
|
||||
]);
|
||||
]});
|
||||
layout.samples.label = "123";
|
||||
layout.time.label = "123s";
|
||||
|
|
After Width: | Height: | Size: 28 KiB |
|
@ -0,0 +1,9 @@
|
|||
var BTN2 = 1, BTN3=2;
|
||||
process.env = process.env;process.env.HWVERSION=1;
|
||||
g = Graphics.createArrayBuffer(240,240,4);
|
||||
|
||||
var layout = new Layout({ type: "v", c: [
|
||||
{type:"txt", font:"6x8", label:"A test"},
|
||||
]},{btns:[ // Buttons...
|
||||
{label:"STOP", cb:()=>{}},
|
||||
]});
|
After Width: | Height: | Size: 15 KiB |
|
@ -0,0 +1,6 @@
|
|||
|
||||
var layout = new Layout({ type: "v", c: [
|
||||
{type:"txt", font:"6x8", label:"A test"},
|
||||
]},{btns:[ // Buttons...
|
||||
{label:"STOP", cb:()=>{}},
|
||||
]});
|
After Width: | Height: | Size: 28 KiB |
|
@ -0,0 +1,11 @@
|
|||
var BTN2 = 1, BTN3=2;
|
||||
process.env = process.env;process.env.HWVERSION=1;
|
||||
g = Graphics.createArrayBuffer(240,240,4);
|
||||
|
||||
var layout = new Layout({ type: "v", c: [
|
||||
{type:"txt", font:"6x8", label:"A test"},
|
||||
]},{btns:[ // Buttons...
|
||||
{label:"A", cb:()=>{}},
|
||||
{label:"STOP", cb:()=>{}},
|
||||
{label:"B", cb:()=>{}},
|
||||
]});
|
After Width: | Height: | Size: 15 KiB |
|
@ -0,0 +1,8 @@
|
|||
|
||||
var layout = new Layout({ type: "v", c: [
|
||||
{type:"txt", font:"6x8", label:"A test"},
|
||||
]},{btns:[ // Buttons...
|
||||
{label:"A", cb:()=>{}},
|
||||
{label:"STOP", cb:()=>{}},
|
||||
{label:"B", cb:()=>{}},
|
||||
]});
|
After Width: | Height: | Size: 28 KiB |
|
@ -0,0 +1,17 @@
|
|||
var BTN2 = 1, BTN3=2;
|
||||
process.env = process.env;process.env.HWVERSION=1;
|
||||
g = Graphics.createArrayBuffer(240,240,4);
|
||||
|
||||
/* When displaying OSD buttons on Bangle.js 1 we should turn
|
||||
the side buttons into 'soft' buttons and then use the physical
|
||||
buttons for up/down selection */
|
||||
|
||||
var layout = new Layout({ type: "v", c: [
|
||||
{type:"txt", font:"6x8", label:"A test"},
|
||||
{type:"btn", label:"Button 1"},
|
||||
{type:"btn", label:"Button 2"}
|
||||
]},{btns:[ // Buttons...
|
||||
{label:"A", cb:()=>{}},
|
||||
{label:"STOP", cb:()=>{}},
|
||||
{label:"B", cb:()=>{}},
|
||||
]});
|
After Width: | Height: | Size: 15 KiB |
|
@ -0,0 +1,10 @@
|
|||
|
||||
var layout = new Layout({ type: "v", c: [
|
||||
{type:"txt", font:"6x8", label:"A test"},
|
||||
{type:"btn", label:"Button 1"},
|
||||
{type:"btn", label:"Button 2"}
|
||||
]},{btns:[ // Buttons...
|
||||
{label:"A", cb:()=>{}},
|
||||
{label:"STOP", cb:()=>{}},
|
||||
{label:"B", cb:()=>{}},
|
||||
]});
|
Before Width: | Height: | Size: 15 KiB After Width: | Height: | Size: 15 KiB |
Before Width: | Height: | Size: 15 KiB After Width: | Height: | Size: 15 KiB |