From 56baf7bdc9887f6cf83c155a391c4c0ec9788e29 Mon Sep 17 00:00:00 2001 From: Ronin0000 <89286474+Ronin0000@users.noreply.github.com> Date: Mon, 11 Apr 2022 07:31:58 -0700 Subject: [PATCH 01/63] Update metadata.json --- apps/lcars/metadata.json | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/apps/lcars/metadata.json b/apps/lcars/metadata.json index 7155442f8..5f3eaa971 100644 --- a/apps/lcars/metadata.json +++ b/apps/lcars/metadata.json @@ -3,7 +3,7 @@ "name": "LCARS Clock", "shortName":"LCARS", "icon": "lcars.png", - "version":"0.20", + "version":"0.21", "readme": "README.md", "supports": ["BANGLEJS2"], "description": "Library Computer Access Retrieval System (LCARS) clock.", From d50e525f7ff77975128041af2311193dabe1047d Mon Sep 17 00:00:00 2001 From: Ronin0000 <89286474+Ronin0000@users.noreply.github.com> Date: Mon, 11 Apr 2022 07:32:32 -0700 Subject: [PATCH 02/63] Update ChangeLog --- apps/lcars/ChangeLog | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/apps/lcars/ChangeLog b/apps/lcars/ChangeLog index 4935fe714..9c17376bb 100644 --- a/apps/lcars/ChangeLog +++ b/apps/lcars/ChangeLog @@ -17,4 +17,5 @@ 0.17: Settings for mph/kph and other minor improvements. 0.18: Fullscreen mode can now be enabled or disabled in the settings. 0.19: Alarms can not go bigger than 100. -0.20: Use alarm for alarm functionality instead of own implementation. \ No newline at end of file +0.20: Use alarm for alarm functionality instead of own implementation. +0.21: Add custom theming. From 4e9c59646edf06c4f647531527675337a0c624a9 Mon Sep 17 00:00:00 2001 From: Ronin0000 <89286474+Ronin0000@users.noreply.github.com> Date: Mon, 11 Apr 2022 07:33:11 -0700 Subject: [PATCH 03/63] Update lcars.app.js --- apps/lcars/lcars.app.js | 804 ++++++---------------------------------- 1 file changed, 106 insertions(+), 698 deletions(-) diff --git a/apps/lcars/lcars.app.js b/apps/lcars/lcars.app.js index 577955d2e..f714c3a7a 100644 --- a/apps/lcars/lcars.app.js +++ b/apps/lcars/lcars.app.js @@ -1,705 +1,113 @@ -const TIMER_IDX = "lcars"; -const SETTINGS_FILE = "lcars.setting.json"; -const locale = require('locale'); -const storage = require('Storage'); -let settings = { - alarm: -1, - dataRow1: "Steps", - dataRow2: "Temp", - dataRow3: "Battery", - speed: "kph", - fullscreen: false, -}; -let saved_settings = storage.readJSON(SETTINGS_FILE, 1) || settings; -for (const key in saved_settings) { - settings[key] = saved_settings[key] -} +(function(back) { + const SETTINGS_FILE = "lcars.setting.json"; -/* - * Colors to use - */ -let cBlue = "#0094FF"; -let cOrange = "#FF9900"; -let cPurple = "#FF00DC"; -let cWhite = "#FFFFFF"; -let cBlack = "#000000"; -let cGrey = "#424242"; - -/* - * Global lcars variables - */ -let lcarsViewPos = 0; -// let hrmValue = 0; -var plotMonth = false; - - -/* - * Requirements and globals - */ - - -var bgLeftFullscreen = { - width : 27, height : 176, bpp : 3, - transparent : 0, - buffer : require("heatshrink").decompress(atob("AAUM2XLlgCCwAJBBAuy4EAmQIF5cggAIGlmwgYIG2XIF42wF4ImGF4ImHJoQmGJoQdJhZNHNY47CgRNGBIJZHHgRiGBIRQ/KH5QCAFCh/eX5Q/KAwdCAGVbtu27YCCoAJBkuWrNlAQRGCiwRDAQPQBIMJCIYCBsAJBgomEtu0WoQmEy1YBIMBHYttIwQ7FyxQ/KHFlFAQ7F2weCHYplKChRTCCg5TCHw5TMAD0GzVp0wCCBBGaBIMaBAtpwECBA2mwEJBAugDgMmCIwJBF5EABAtoeQQvGCYQdPJoI7LMQzTCLJKAGzAJBO4xQ/KGQA8UP7y/KH5QnAHih/eX5Q/GQ4JCGRJlKCgxTDBAwgCCg5TCHwxTCNA4A==")) -}; - -var bgLeftNotFullscreen = { - width : 27, height : 152, bpp : 3, - transparent : 0, - buffer : require("heatshrink").decompress(atob("AAUM2XLlgCCwAJBBAuy4EAmQIF5cggAIGlmwgYIG2XIF42wF4ImGF4ImHJoQmGJoQdJhZNHNY47CgRNGBIJZHHgRiGBIRQ/KH5QCAGVbtu27YCCoAJBkuWrNlAQRkCiwRDAQPQBIMJCIYCBsAJBgomEtu0WoQmEy1YBIMBHYttIwQ7FyxQ/KHFlFAQ7F2weCHYplKChRTCCg5TCHw5TMAD0GzVp0wCCBBGaBIMaBAtpwECBA2mwEJBAugDgMmCIwJBF5EABAtoeQQvGCYQdPJoI7LMQzTCLJKAGzAJBO4xQ/KGQA8UP7y/KH5QnAHih/eX5Q/GQ4JCGRJlKCgxTDBAwgCCg5TCHwxTCNA4A=")) -}; - -var bgRightFullscreen = { - width : 27, height : 176, bpp : 3, - transparent : 0, - buffer : require("heatshrink").decompress(atob("lmy5YCDBIUyBAmy5AJBhYUG2EAhgIFAQMAgQIGCgQABCg4ABEAwUNFI2AKZHAKZEgGRZTGOIUDQxJxGKH5Q/agwAnUP7y/KH4yGeVYAJrdt23bAQVABIMly1ZsoCCMgUWCIYCB6AJBhIRDAQNgBIMFEwlt2i1CEwmWrAJBgI7FtpGCHYuWKH5QxEwpQDlo7F0A7IqBZBEwo7BCIwCBJo53CJoxiCJpIAdgOmzVpAQR/CgAIEAQJ2CBAoCBBIMmCg1oD4QLGFQUCCjQ+CKYw+CKY4JCKYwoCGRMaGREJDoroCgwdFzBlLKH5QvAHih/eX5Q/KE4A8UP7y/KH5QGDpg7HJoxZCCIx3CJowmCF4yACJox/CgAA=")) -}; - -var bgRightNotFullscreen = { - width : 27, height : 152, bpp : 3, - transparent : 0, - buffer : require("heatshrink").decompress(atob("lmy5YCDBIUyBAmy5AJBhYUG2EAhgIFAQMAgQIGCgQABCg4ABEAwUNFI2AKZHAKZEgGRZTGOIUDQxJxGKH5Q/agwAxrdt23bAQVABIMly1ZsoCCMgUWCIYCB6AJBhIRDAQNgBIMFEwlt2i1CEwmWrAJBgI7FtpGCHYuWKH5QxEwpQDlo7F0A7IqBZBEwo7BCIwCBJo53CJoxiCJpIAdgOmzVpAQR/CgAIEAQJ2CBAoCBBIMmCg1oD4QLGFQUCCjQ+CKYw+CKY4JCKYwoCGRMaGREJDoroCgwdFzBlLKH5QvAHih/eX5Q/KE4A8UP7y/KH5QGDpg7HJoxZCCIx3CJowmCF4yACJox/CgA=")) -}; - -var bgLeft = settings.fullscreen ? bgLeftFullscreen : bgLeftNotFullscreen; -var bgRight= settings.fullscreen ? bgRightFullscreen : bgRightNotFullscreen; - -var iconEarth = { - width : 50, height : 50, bpp : 3, - buffer : require("heatshrink").decompress(atob("AFtx48ECBsDwU5k/yhARLjgjBjlzAQMQEZcIkOP/fn31IEZgCBnlz58cEpM4geugEgwU/8+WNZJHDuHHvgmBCQ8goEOnVgJoMnyV58mACItHI4X8uAFBuVHnnz4BuGxk4////Egz3IkmWvPgNw8f/prB//BghTC+AjE7848eMjNnzySBwUJkmf/BuGuPDAQIjBiPHhhTCSQnjMo0ITANJn44Dg8MuFBggCCiFBcAJ0Bv5xEh+ITo2OhHkyf/OIQdBWwVHhgjBNwUE+fP/5EEgePMoYLBhMgyVJk/+BQQdC688I4XxOIc8v//NAvr+QEBj/5NwKVBy1/QYUciPBhk1EAJrC+KeC489QYaMBgU/8BNB9+ChEjz1Jkn/QYMBDQIgCcYTCCiP/nlzJQmenMAgV4//uy/9wRaB/1J8iVCcAfHjt9TYYICnhKCgRKBw159/v//r927OIeeoASBDQccvv3791KYVDBYPLJQeCnPnz//AAP6ocEjEkXgMgJQtz79fLAP8KYkccAcJ8Gf/f/xu/cAMQ4eP5MlyQRCMolx40YsOGBAPfnnzU4KVDpKMBvz8Dh0/8me7IICgkxJQXPIgZTD58sEgcJk+eNoONnFBhk4/5uB/pcDg5KD+4mEv4CBXISVDhEn31/8/+mH7x//JQK5CAAMB4JBCnnxJQf/+fJEgkAa4L+CAQOOjMn/1bXIRxDJQXx58f//Hhlz/88EgsChMgz/Zs/+nfkyV/8huDOI6SD498NwoACi1Z8+S/Plz17/+QCI7jC+ZxBmfPnojIAAMDcYWSp//2wRJEwq2GABECjMgNYwAmA=")) -}; - -var iconSaturn = { - width : 50, height : 50, bpp : 3, - transparent : 1, - buffer : require("heatshrink").decompress(atob("AH4A/AEkQuPHCJ0ChEAwARNjAjBjgjOhs06Q2OEYVx4ARMhEggUMkANIDoIgBoEEgEBNxJEC6ZrBAAMwNxAjDNYcHNxIjB7dtEwIHBwRoKj158+cuPEjlwCRAjC23bpu0wRNDAAsHEYWeEwaSJ6YjCAQUNSRQjEzxQBWZMNEYlsmg2JWAIjCz95SoJuJggjDtuw6dMG5JKCz998wFBJRVNEYW0yaVBJRNhJQN9+4pCzhKJmBKC4YpB/fINxIgCzFxSoQ3J4ENm3CAQPb98wbpEcAQMYWwKYBNxMDXgc2/fv3g2IEAOAgAjBjy5CEhEMfYICBgfPnjdLjj+CgMHiC3JknDhhoINw4jCAB0IJQIANR4QjPAH4A/AFA")) -}; - -var iconMoon = { - width : 50, height : 50, bpp : 3, - transparent : 1, - buffer : require("heatshrink").decompress(atob("AH4AQjlx44CCCZsg8eOkHDwAQKEYgmPhEgEQM48AOIgMHEYoCB4ATI8UAmH/x04JoRuJsImHuBKLn37EwZuIgEQOI8cEpXj/yYBhE8+YNGgkYoJxITBUPnAaC///nC+FjBuIOJZEB8YeCh/8AoYACoMEEAnEjhQDPQJKJ/DCDAoi5DoLdHAoMQgLjFWYPOnngh02IwXzwDjEgPGEYS8BI4MBYoSVG4fP/nghkAgZrDkngJQqSG4gvBg4sBQgkImHihEAWwP8ZBMBEYl5/+cSoVAGQIUFh04weJn///0gj/OEw5KEz45BzhuCTYQAEgePB4IACAoJuBnAQEa4XHjxKB//xFgWHJQsCRgMDEonipwjENwUBDQNx8+evvn/hTDLw3igE+EgZxB8UOXIvEJQUfEYOfv53DEQkgga5BJQvzx84cAj+CDoNh8/eEYJKDuCSEcocnEon+/7xEgFBIIcfB4Mf/IICXI2DgDdBAAn758gCIq5Dv4zBvJuIOIfjEgvP/ARHgwdCB4P3AoTdFAAk4EYk8SQgAFTALaDSQwAGh08//vnDmBABYmEEZYAzA==")) -}; - -var iconMars = { - width : 50, height : 50, bpp : 3, - transparent : 1, - buffer : require("heatshrink").decompress(atob("AH4ATjlwCJ+Dh0wwAQMg0cuPHjFhCZkDps0yVJkmQCBMEjFx42atOmzQmLhMkEYQCCCREQoOGEYmmzB0IEY4CBkARGoJKBEYQCEzgSGkGSpAjDyYCCphuGiFhJQgCD8ASFgRHGAQKbB6BuHJRGeOIsINxEk6dNmARDgMEjQjHAQPnVQojIyZKB6YSDNwK5FAQt54BuDXJIjBEwK5EgxKKXgq5BJRdgXIojJAQJKMcAM0EwM2JUApDoCVFExa7FkGCgAmIkAREEwUEjAmHCIgABhEggQmFpACBCIojBEwRQCzVhwkQU4YADgQmBwQCCI4IFBCAojFAQojGJQQjDAQgRGEZICBEo4gFyUIkilFJQUYEAZrBAQMYNw5KDSQSbCNwwABgOGEwgCBsPACQ5xGwdNnARJcAVh48evvnCJK8Chs+/fv33gCRcB48cuPHCBYA/ADAA==")) -}; - -var iconSatellite = { - width : 50, height : 50, bpp : 3, - transparent : 2, - buffer : require("heatshrink").decompress(atob("pMkyQC/ATGXhIRPyNl0gmPjlwCJ9ly1aCJ1c+fHJR1Hy1ZJR1I+fPnlx6QRLpe+/JKBr5KMuYjBJQMdCJce/fvJQW0CJUlEYQCBSpvvJQbXJjl0NwnzNxGQwEOnHhgF78+WqQyIrFx48cAQXz4ShJgAABh0+8cP//9LJEhg4jDuP3//0LhGQgYlBgeAn///5cIy8MuAmDCIP/9I4HkmCEYMOgHfCQWkCI0cuBuDgF/CIP+CI1Ny1IkeAgHANwIAB/QRFrj7BhkxEwQRC/4RFpbXDgSVBg4RCSorXDI4MJAQMfCIP8cwImDn37fwN58+kwHgLgSVFub7CI4NyBAJKDLgkuEYX78+evKtCLg0jEYRKC58JMoRcFkwjDJQTFDl65EkojEAQMdcwn/+gFC3YjEJQLXEpYRDWwQmEdI6SHAQO0CJUkx4jDF4gCIJQgRMXIjCEARIjCCJ2XEYPKCJqJBJQIROcAUpCJ0kybaDARtdCKAC2kAA=")) -}; - -var iconCharging = { - width : 50, height : 50, bpp : 3, - transparent : 5, - buffer : require("heatshrink").decompress(atob("23btugAwUBtoICARG0h048eODQYCJ6P/AAUCCJfbo4SDxYRLtEcuPHjlwgoRJ7RnIloUHoYjDAQfAExEAwUIkACEkSAIEYwCBhZKH6EIJI0CJRFHEY0BJRWBSgf//0AJRYSE4BKLj4SE8BKLv4RD/hK/JS2AXY0gXwRKG4cMmACCJQMAg8csEFJQsBAwfasEAm379u0gFbcBfHzgFBz1xMQZKBjY/D0E2+BOChu26yVEEYdww+cgAFCg+cgIfB6RKF4HbgEIkGChEAthfCJQ0eEAIjBBAMxk6GCJQtgtyVBwRKBAQMbHAJKGXIIFCgACBhl54qVG2E+EAJKBJoWAm0WJQ6SCXgdxFgMLJQvYjeAEAUwFIUitEtJQ14NwUHgEwKYZKGwOwNYX7XgWCg3CJQ5rB4MevPnAoPDJRJrCgEG/ECAoNsJRUwoEesIIBiJKI3CVDti/CJRKVDiJHBSo0YsOGjED8AjBcAcIgdhcAXAPIUAcAYIBcA4dBAQUG8BrBgBuCgOwcBEeXIK2BBAIFBgRqBGoYAChq8CcYUE4FbUYOACQsHzgjDgwFBCIImBAQsDtwYD7cAloRI22B86YBw5QBgoRJ7dAgYEDCJaeBJoMcsARMAQNoJIIRE6A")) -}; - -var iconNoBattery = { - text: "NO BAT", - width : 50, height : 50, bpp : 3, - transparent : 1, - buffer : require("heatshrink").decompress(atob("kmSpIC/AWMyoQIFsmECJFJhMmA4QXByVICIwODAQ4RRFIQGD5JVLkIGDzJqMyAGDph8MiRKGyApEAoZKFyYIDQwMkSQNkQZABBhIIOOJRuEL5gRIAUKACVQMhmUSNYNDQYJTBBwYFByGTkOE5FJWYNMknCAQKYCiaSCpmGochDoSYBhMwTAZrChILBhmEzKPBF4ImBTAREBDoMmEwJVDoYjBycJFgWEJQRuLJQ1kmQCCjJlCBYbjCagaDBwyDBmBuBF4TjJAUQKINBChCDQxZBcZIIQF4NIgEAgKSDiQmEVQKMBoARBAAMCSQLLBVoxqKL4gaCChVCNwoRKOIo4CJIgABBoSMHpIRFgDdJOIJUBCAUJRgJuEAQb+DIIgRIAX4C/ASOQA")) -}; - -// Font to use: -// -Graphics.prototype.setFontAntonioMedium = function(scale) { - // Actual height 20 (19 - 0) - g.setFontCustom(atob("AAAAAAAAAAAAAAAAAAAA//mP/5gAAAAAAAAAAAAA/gAMAAAAAA/gAPAAAEIIBP+H/8D+IYBP+H/8D+IABCAAwIAfnwP8+PHh448eP3+B4fAAAAAAAH/AD/4AwGAMBgD/4Af8GAAPgAPgAfgAfAAfAA+AAOP/AH/4BgGAYBgH/4A/8AAAAAAAAAQAA/B+f4/+GMPhjv/4/h8Dg/gAcYwAAPwADgAAAAAAAAB//8///sAAaAACAAAMAAb//+f//AAAAAAAbAAGwAA4AA/wADgABsAAbAAAAAAAgAAMAAPwAD8AAMAADAAAAAAAAAAHAAB/AAOAAAAAAAAMAADAAAwAAMAACAAAAAAAAAABgAAYAAAAAAAAA4AD+AP+A/4A/gAOAAAAAAAAAH//j//8wADMAAz//8f/+AAAAAAAMAADAABgAA//+P//gAAAAAAAAAAAAAfgfP4fzAfswfDP/gx/gMAAAHgPj4D8wMDMHAz//8f3+AAEAAAAADwAH8APzA/AwP//j//4AAwAAAD/Hw/x+MwBjOAYz/+Mf/AAAAAAAH//j//8wYDMGAz9/8fP+AAcDAAAwAAMAfjB/4z/wP+AD4AAwAAAAOB/f4///MHAzBwM///H9/gAAAAAAH/Pj/78wGDMBgz//8f/+AAAAAAADhwA4cAAAAAAAAAAAAAADh/A4fgAAAAOAAHwABsAA7gAccAGDAAAAANgADYAA2AANgADYAA2AAAAAAAABgwAccADuAAbAAHwAA4AAAAHwAD8c4/POMHAD/wAfwAAAAAAAAD/wD//B4B4Y/HMf8zMBMyATMwczP+M4BzHwcgf+AA+AAAAAAD4A/+P/8D+DA/4wH/+AB/4AAeAAAAAAA//+P//jBgYwYGP//j//4PH4AAAAAAAf/+P//zgAcwADP4fz+P4Ph8AAAAAAA//+P//jAAYwAGPADj//4P/4AAAAAAA//+P//jBgYwYGMGBgAAAAAAP//j//4wYAMGADBgAAAAAAAA//w///PAHzAQM4MHP7/x+/8AAAAAAD//4//+AGAABgAAYAP//j//4AAAAAAAAAA//+P//gAAAAAAAAAAAHwAB+AABgAAY//+P//AAAAAAAAAAD//4//+APgAf+Afj8PgPjAAYAAAAAAD//4//+AABgAAYAAGAAAAAAA//+P//j/gAD/wAB/gAP4B/4P/AD//4//+AAAAAAAAAAP//j//4P4AAfwAA/g//+P//gAAAAAAAAAA//g//+PAHjAAY4AOP//h//wAAAAAAD//4//+MDADAwA4cAP/AB/gAAAAAAAA//g//+PAHjAAc4APv//5//yAAAAAAD//4//+MGADBgA48AP//h+f4AAAAAAB+Pw/z+MOBjBwY/P+Hx/AAHgwAAMAAD//4//+MAADAAAAAAP//D//4AAOAABgAA4//+P//AAAAwAAP8AD//AA/+AAfgP/4//gPwAAAAA+AAP/4Af/4AD+A//j/wA/wAD/+AA/4B/+P/+D+AAAAAMADj8P4P/4A/4B//w+A+MABgAAA4AAPwAB/gAB/+A//j/gA+AAMAAAAAYwB+MH/jf+Y/8GPwBjAAAAAAP//7//+wABsAAYAAAAAAPAAD/gAH/gAD/gAD4AACAAADAAGwABv//7//+AAAA=="), 32, atob("BQUHCAgVCQQFBQkHBQcFBwgICAgICAgICAgFBQcHBwgPCQkJCQcHCQoFCQkHDQoJCQkJCAYJCQ0ICAcGBwY="), 20+(scale<<8)+(1<<16)); -}; - -Graphics.prototype.setFontAntonioLarge = function(scale) { - // Actual height 39 (39 - 1) - g.setFontCustom(atob("AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAB8AAAAAAPgAAAAAB8AAAAAAHgAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAABgAAAAAD8AAAAAH/gAAAAP/8AAAAf//gAAA///AAAB//+AAAD//8AAAH//4AAAP//wAAAB//gAAAAP/AAAAAB+AAAAAAMAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAH///AAAf////8AP/////4B//////Af/////8D8AAAAfgeAAAAA8DwAAAAHgeAAAAA8D//////gf/////8B//////AP/////wAf////8AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA8AAAAAAHgAAAAAA8AAAAAAPgAAAAAB4AAAAAAf/////gP/////8B//////gP/////8B//////gAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA/wAAAAD/+AAP8A//wAP/gP/+AH/8D//wD//gfgAA//8DwAAf+HgeAAP/A8DwAH/gHgfgP/wA8D///4AHgP//+AA8A///AAHgB//AAAcAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAD4AA/gAD/AAH/gA/4AA/+AP/AAH/4D/4AA//gfgA4AB8DwAPAAHgeAB4AA8DwAPgAHgfAD+AB8D//////gP/////4B//5//+AD/+H//gAH/AH/wAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAP4AAAAAP/AAAAAP/4AAAAP//AAAAP/x4AAAf/wPAAAf/gB4AAf/AAPAAP/AAB4AB//////gP/////8B//////gP/////8AAAAAPAAAAAAB4AAAAAAPAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAP//wD/AB///Af+AP//4D/4B///Af/gP//4B/8B4D4AAPgPAeAAA8B4DwAAHgPAfAAB8B4D////gPAf///4B4B////APAD///gAAAD//gAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAB///AAAP////4AH/////wB//////Af/////8D8APAA/geADwAB8DwAeAAHgeADwAA8D4AeAAPgf/j+AH8B/8f///gP/h///4Af8H//+AAPgP//AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAB4AAAAAAPAAAAAAB4AAAABgPAAAA/8B4AAB//gPAAD//8B4AH///gPAH///8B4P//+AAPH//wAAB///gAAAP//AAAAB/+AAAAAP+AAAAAB+AAAAAAOAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA/4A/+AAf/w//+AP//v//4B//////Af/////8D4AfwAPgeAB8AA8DwAHAAHgeAB8AA8D4Af4APgf/////8B//////AP//v//4A//4//8AA/4A/+AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAH/+AAAAD//+D/gB///4f+AP///j/4D///8f/gfAAHgB8DwAA8AHgeAAHgA8DwAA8AHgfgAHgB8D//////gP/////4A/////+AD/////gAD////AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAPwAfgAAB+AD8AAAPwAfgAAB+AD8AAAPwAfgAAAAAAAAAAAAAAAAAAAAAAAA=="), 46, atob("DBATExMTExMTExMTCw=="), 45+(scale<<8)+(1<<16)); -}; - - -/* - * Draw watch face - */ -var drawTimeout; -function queueDraw() { - - // Faster updates during alarm to ensure that it is - // shown correctly... - var timeout = isAlarmEnabled() ? 10000 : 60000; - - if (drawTimeout) clearTimeout(drawTimeout); - drawTimeout = setTimeout(function() { - drawTimeout = undefined; - draw(); - }, timeout - (Date.now() % timeout)); -} - -/** - * This function plots a data row in LCARS style. - * Note: It can be called async and therefore, the text alignment and - * font is set each time the function is called. - */ -function printRow(text, value, y, c){ - g.setFontAntonioMedium(); - g.setFontAlign(-1,-1,0); - - // Print background - g.setColor(c); - g.setFontAlign(-1,-1,0); - g.fillRect(80, y-2, 165 ,y+18); - g.fillCircle(163, y+8, 10); - g.setColor(cBlack); - g.drawString(text, 135, y); - - // Plot text - width = g.stringWidth(value); - g.setColor(cBlack); - g.fillRect(130-width-8, y-2, 130, y+18); - g.setColor(c); - g.setFontAlign(1,-1,0); - g.drawString(value, 126, y); -} - - -function drawData(key, y, c){ - try{ - _drawData(key, y, c); - } catch(ex){ - // Show last error - next try hopefully works. - } -} - - -function _drawData(key, y, c){ - key = key.toUpperCase() - var text = key; - var value = "ERR"; - var should_print= true; - - if(key == "STEPS"){ - text = "STEP"; - value = getSteps(); - - } else if(key == "BATTERY"){ - text = "BAT"; - value = E.getBattery() + "%"; - - } else if (key == "VREF"){ - value = E.getAnalogVRef().toFixed(2) + "V"; - - } else if(key == "HRM"){ - value = Math.round(Bangle.getHealthStatus("day").bpm); - - } else if (key == "TEMP"){ - var weather = getWeather(); - value = weather.temp; - - } else if (key == "HUMIDITY"){ - text = "HUM"; - var weather = getWeather(); - value = weather.hum; - - } else if (key == "WIND"){ - text = "WND"; - var weather = getWeather(); - value = weather.wind; - - } else if (key == "ALTITUDE"){ - should_print= false; - text = "ALT"; - - // Immediately print something - avoid that its empty - printRow(text, "", y, c); - Bangle.getPressure().then(function(data){ - if(data && data.altitude){ - value = Math.round(data.altitude); - printRow(text, value, y, c); - } - }) - - } else if(key == "CORET"){ - value = locale.temp(parseInt(E.getTemperature())); + // initialize with default settings... + const storage = require('Storage') + let settings = { + alarm: -1, + dataRow1: "Battery", + dataRow2: "Steps", + dataRow3: "Temp", + speed: "kph", + fullscreen: false, + themeColor1: "Orange", + themeColor1BG: "#FF9900", + themeColor2: "Purple", + themeColor2BG: "#FF00DC", + themeColor3: "Cyan", + themeColor3BG: "#0094FF", + }; + let saved_settings = storage.readJSON(SETTINGS_FILE, 1) || settings; + for (const key in saved_settings) { + settings[key] = saved_settings[key] } - // Print for all datapoints that are not async - if(should_print){ - printRow(text, value, y, c); - } -} - -function drawHorizontalBgLine(color, x1, x2, y, h){ - g.setColor(color); - - for(var i=0; i{ - data[h.day]+=h.bpm; - if (h.bpm) cnt[h.day]++; - }); - require("graph").drawBar(g, data, { - axes : true, - minx: 1, - gridx : 5, - gridy : 100, - width : 140, - height : 50, - x: 5, - y: 25 - }); - - // Plot step graph - var data = new Uint16Array(32); - health.readDailySummaries(new Date(), h=>data[h.day]+=h.steps/1000); - var gridY = parseInt(Math.max.apply(Math, data)/2); - gridY = gridY <= 0 ? 1 : gridY; - require("graph").drawBar(g, data, { - axes : true, - minx: 1, - gridx : 5, - gridy : gridY, - width : 140, - height : 50, - x: 5, - y: 115 - }); - - g.setFontAlign(1, 1, 0); - g.setFontAntonioMedium(); - g.setColor(cWhite); - - if(settings.fullscreen){ - g.drawString("M-HRM", 154, 27); - g.drawString("M-STEPS [K]", 154, 115); - } else { - g.drawString("MONTH", 154, 115); + E.showMenu({ + '': { 'title': 'LCARS Clock' }, + '< Back': back, + 'Row 1': { + value: 0 | dataOptions.indexOf(settings.dataRow1), + min: 0, max: 8, + format: v => dataOptions[v], + onchange: v => { + settings.dataRow1 = dataOptions[v]; + save(); + }, + }, + 'Row 2': { + value: 0 | dataOptions.indexOf(settings.dataRow2), + min: 0, max: 8, + format: v => dataOptions[v], + onchange: v => { + settings.dataRow2 = dataOptions[v]; + save(); + }, + }, + 'Row 3': { + value: 0 | dataOptions.indexOf(settings.dataRow3), + min: 0, max: 8, + format: v => dataOptions[v], + onchange: v => { + settings.dataRow3 = dataOptions[v]; + save(); + }, + }, + 'Full Screen': { + value: settings.fullscreen, + format: () => (settings.fullscreen ? 'Yes' : 'No'), + onchange: () => { + settings.fullscreen = !settings.fullscreen; + save(); + }, + }, + 'Speed': { + value: 0 | speedOptions.indexOf(settings.speed), + min: 0, max: 1, + format: v => speedOptions[v], + onchange: v => { + settings.speed = speedOptions[v]; + save(); + }, + }, + 'Theme Color 1': { + value: 0 | color_options.indexOf(settings.themeColor1), + min: 0, max: 7, + format: v => color_options[v], + onchange: v => { + settings.themeColor1 = color_options[v]; + settings.themeColor1BG = bg_code[v]; + save(); + }, + }, + 'Theme Color 2': { + value: 0 | color_options.indexOf(settings.themeColor2), + min: 0, max: 7, + format: v => color_options[v], + onchange: v => { + settings.themeColor2 = color_options[v]; + settings.themeColor2BG = bg_code[v]; + save(); + }, + }, + 'Theme Color 3': { + value: 0 | color_options.indexOf(settings.themeColor3), + min: 0, max: 7, + format: v => color_options[v], + onchange: v => { + settings.themeColor3 = color_options[v]; + settings.themeColor3BG = bg_code[v]; + save(); + }, } - - // Plot day - } else { - var data = new Uint16Array(24); - var cnt = new Uint8Array(24); - health.readDay(new Date(), h=>{ - data[h.hr]+=h.bpm; - if (h.bpm) cnt[h.hr]++; - }); - require("graph").drawBar(g, data, { - axes : true, - minx: 1, - gridx : 4, - gridy : 100, - width : 140, - height : 50, - x: 5, - y: 25 - }); - - // Plot step graph - var data = new Uint16Array(24); - health.readDay(new Date(), h=>data[h.hr]+=h.steps); - var gridY = parseInt(Math.max.apply(Math, data)/1000)*1000; - gridY = gridY <= 0 ? 1000 : gridY; - require("graph").drawBar(g, data, { - axes : true, - minx: 1, - gridx : 4, - gridy : gridY, - width : 140, - height : 50, - x: 5, - y: 115 - }); - - g.setFontAlign(1, 1, 0); - g.setFontAntonioMedium(); - g.setColor(cWhite); - - if(settings.fullscreen){ - g.drawString("D-HRM", 154, 27); - g.drawString("D-STEPS", 154, 115); - } else { - g.drawString("DAY", 154, 115); - } - } -} - -function draw(){ - // Queue draw first to ensure that its called in one minute again. - queueDraw(); - - // Next draw the watch face - g.reset(); - g.clearRect(0, 0, g.getWidth(), g.getHeight()); - - // Draw current lcars position - if(lcarsViewPos == 0){ - drawPosition0(); - } else if (lcarsViewPos == 1) { - drawPosition1(); - } - - // After drawing the watch face, we can draw the widgets - if(settings.fullscreen){ - for (let wd of WIDGETS) {wd.draw=()=>{};wd.area="";} - } else { - Bangle.drawWidgets(); - } -} - - -/* - * Step counter via widget - */ -function getSteps() { - try{ - if (WIDGETS.wpedom !== undefined) { - return WIDGETS.wpedom.getSteps(); - } else if (WIDGETS.activepedom !== undefined) { - return WIDGETS.activepedom.getSteps(); - } - } catch(ex) { - // In case we failed, we can only show 0 steps. - } - - return 0; -} - - -function getWeather(){ - var weatherJson; - - try { - weatherJson = storage.readJSON('weather.json'); - } catch(ex) { - // Return default - } - - if(weatherJson === undefined){ - return { - temp: "-", - hum: "-", - txt: "-", - wind: "-", - wdir: "-", - wrose: "-" - }; - } - - var weather = weatherJson.weather; - - // Temperature - weather.temp = locale.temp(weather.temp-273.15); - - // Humidity - weather.hum = weather.hum + "%"; - - // Wind - const wind = locale.speed(weather.wind).match(/^(\D*\d*)(.*)$/); - var speedFactor = settings.speed == "kph" ? 1.0 : 1.0 / 1.60934; - weather.wind = Math.round(wind[1] * speedFactor); - - return weather -} - - -/* - * Handle alarm - */ -function isAlarmEnabled(){ - try{ - var alarm = require('sched'); - var alarmObj = alarm.getAlarm(TIMER_IDX); - if(alarmObj===undefined || !alarmObj.on){ - return false; - } - - return true; - - } catch(ex){ } - return false; -} - -function getAlarmMinutes(){ - if(!isAlarmEnabled()){ - return -1; - } - - var alarm = require('sched'); - var alarmObj = alarm.getAlarm(TIMER_IDX); - return Math.round(alarm.getTimeToAlarm(alarmObj)/(60*1000)); -} - -function increaseAlarm(){ - try{ - var minutes = isAlarmEnabled() ? getAlarmMinutes() : 0; - var alarm = require('sched') - alarm.setAlarm(TIMER_IDX, { - timer : (minutes+5)*60*1000, - }); - alarm.reload(); - } catch(ex){ } -} - -function decreaseAlarm(){ - try{ - var minutes = getAlarmMinutes(); - minutes -= 5; - - var alarm = require('sched') - alarm.setAlarm(TIMER_IDX, undefined); - - if(minutes > 0){ - alarm.setAlarm(TIMER_IDX, { - timer : minutes*60*1000, - }); - } - - alarm.reload(); - } catch(ex){ } -} - - -/* - * Listeners - */ -Bangle.on('lcdPower',on=>{ - if (on) { - // Whenever we connect to Gadgetbridge, reading data from - // health failed. Therefore, we update only partially... - drawInfo(); - drawState(); - } else { // stop draw timer - if (drawTimeout) clearTimeout(drawTimeout); - drawTimeout = undefined; - } -}); - -Bangle.on('lock', function(isLocked) { - drawInfo(); -}); - -Bangle.on('charging',function(charging) { - drawState(); -}); - - -function feedback(){ - Bangle.buzz(40, 0.3); -} - -// Touch gestures to control clock. We don't use swipe to be compatible with the bangle ecosystem -Bangle.on('touch', function(btn, e){ - var left = parseInt(g.getWidth() * 0.2); - var right = g.getWidth() - left; - var upper = parseInt(g.getHeight() * 0.2); - var lower = g.getHeight() - upper; - - var is_left = e.x < left; - var is_right = e.x > right; - var is_upper = e.y < upper; - var is_lower = e.y > lower; - - if(is_left && lcarsViewPos == 1){ - feedback(); - lcarsViewPos = 0; - draw(); - return; - - } else if(is_right && lcarsViewPos == 0){ - feedback(); - lcarsViewPos = 1; - draw(); - return; - } - - if(lcarsViewPos == 0){ - if(is_upper){ - feedback(); - increaseAlarm(); - drawState(); - return; - } if(is_lower){ - feedback(); - decreaseAlarm(); - drawState(); - return; - } - } else if (lcarsViewPos == 1 && (is_upper || is_lower) && plotMonth != is_lower){ - feedback(); - plotMonth = is_lower; - draw(); - return; - } -}); - - -/* - * Lets start widgets, listen for btn etc. - */ -// Show launcher when middle button pressed -Bangle.setUI("clock"); -Bangle.loadWidgets(); - -// Clear the screen once, at startup and draw clock -g.setTheme({bg:"#000",fg:"#fff",dark:true}).clear(); -draw(); + }); +}) From c5509992b9cfd533d9bdcbf6e8657b26994f3a1c Mon Sep 17 00:00:00 2001 From: Ronin0000 <89286474+Ronin0000@users.noreply.github.com> Date: Mon, 11 Apr 2022 07:34:03 -0700 Subject: [PATCH 04/63] Update lcars.app.js --- apps/lcars/lcars.app.js | 811 ++++++++++++++++++++++++++++++++++------ 1 file changed, 706 insertions(+), 105 deletions(-) diff --git a/apps/lcars/lcars.app.js b/apps/lcars/lcars.app.js index f714c3a7a..7cdd6749e 100644 --- a/apps/lcars/lcars.app.js +++ b/apps/lcars/lcars.app.js @@ -1,113 +1,714 @@ -(function(back) { - const SETTINGS_FILE = "lcars.setting.json"; +const SETTINGS_FILE = "lcars.setting.json"; +const locale = require('locale'); +const storage = require('Storage') +let settings = { + alarm: -1, + dataRow1: "Steps", + dataRow2: "Temp", + dataRow3: "Battery", + speed: "kph", + fullscreen: false, + themeColor1: "Orange", + themeColor1BG: "#FF9900", + themeColor2: "Purple", + themeColor2BG: "#FF00DC", + themeColor3: "Cyan", + themeColor3BG: "#0094FF", +}; +let saved_settings = storage.readJSON(SETTINGS_FILE, 1) || settings; +for (const key in saved_settings) { + settings[key] = saved_settings[key] +} - // initialize with default settings... - const storage = require('Storage') - let settings = { - alarm: -1, - dataRow1: "Battery", - dataRow2: "Steps", - dataRow3: "Temp", - speed: "kph", - fullscreen: false, - themeColor1: "Orange", - themeColor1BG: "#FF9900", - themeColor2: "Purple", - themeColor2BG: "#FF00DC", - themeColor3: "Cyan", - themeColor3BG: "#0094FF", - }; - let saved_settings = storage.readJSON(SETTINGS_FILE, 1) || settings; - for (const key in saved_settings) { - settings[key] = saved_settings[key] +/* + * Colors to use + */ +let cBlue = settings.themeColor1BG; +let cOrange = settings.themeColor2BG; +let cPurple = settings.themeColor3BG; +let cWhite = "#FFFFFF"; +let cBlack = "#000000"; +let cGrey = "#424242"; + +/* + * Global lcars variables + */ +let lcarsViewPos = 0; +// let hrmValue = 0; +var plotMonth = false; + + +/* + * Requirements and globals + */ + + +var bgLeftFullscreen = { + width : 27, height : 176, bpp : 3, + transparent : 0, + buffer : require("heatshrink").decompress(atob("AAUM2XLlgCCwAJBBAuy4EAmQIF5cggAIGlmwgYIG2XIF42wF4ImGF4ImHJoQmGJoQdJhZNHNY47CgRNGBIJZHHgRiGBIRQ/KH5QCAFCh/eX5Q/KAwdCAGVbtu27YCCoAJBkuWrNlAQRGCiwRDAQPQBIMJCIYCBsAJBgomEtu0WoQmEy1YBIMBHYttIwQ7FyxQ/KHFlFAQ7F2weCHYplKChRTCCg5TCHw5TMAD0GzVp0wCCBBGaBIMaBAtpwECBA2mwEJBAugDgMmCIwJBF5EABAtoeQQvGCYQdPJoI7LMQzTCLJKAGzAJBO4xQ/KGQA8UP7y/KH5QnAHih/eX5Q/GQ4JCGRJlKCgxTDBAwgCCg5TCHwxTCNA4A==")) +}; + +var bgLeftNotFullscreen = { + width : 27, height : 152, bpp : 3, + transparent : 0, + buffer : require("heatshrink").decompress(atob("AAUM2XLlgCCwAJBBAuy4EAmQIF5cggAIGlmwgYIG2XIF42wF4ImGF4ImHJoQmGJoQdJhZNHNY47CgRNGBIJZHHgRiGBIRQ/KH5QCAGVbtu27YCCoAJBkuWrNlAQRkCiwRDAQPQBIMJCIYCBsAJBgomEtu0WoQmEy1YBIMBHYttIwQ7FyxQ/KHFlFAQ7F2weCHYplKChRTCCg5TCHw5TMAD0GzVp0wCCBBGaBIMaBAtpwECBA2mwEJBAugDgMmCIwJBF5EABAtoeQQvGCYQdPJoI7LMQzTCLJKAGzAJBO4xQ/KGQA8UP7y/KH5QnAHih/eX5Q/GQ4JCGRJlKCgxTDBAwgCCg5TCHwxTCNA4A=")) +}; + +var bgRightFullscreen = { + width : 27, height : 176, bpp : 3, + transparent : 0, + buffer : require("heatshrink").decompress(atob("lmy5YCDBIUyBAmy5AJBhYUG2EAhgIFAQMAgQIGCgQABCg4ABEAwUNFI2AKZHAKZEgGRZTGOIUDQxJxGKH5Q/agwAnUP7y/KH4yGeVYAJrdt23bAQVABIMly1ZsoCCMgUWCIYCB6AJBhIRDAQNgBIMFEwlt2i1CEwmWrAJBgI7FtpGCHYuWKH5QxEwpQDlo7F0A7IqBZBEwo7BCIwCBJo53CJoxiCJpIAdgOmzVpAQR/CgAIEAQJ2CBAoCBBIMmCg1oD4QLGFQUCCjQ+CKYw+CKY4JCKYwoCGRMaGREJDoroCgwdFzBlLKH5QvAHih/eX5Q/KE4A8UP7y/KH5QGDpg7HJoxZCCIx3CJowmCF4yACJox/CgAA=")) +}; + +var bgRightNotFullscreen = { + width : 27, height : 152, bpp : 3, + transparent : 0, + buffer : require("heatshrink").decompress(atob("lmy5YCDBIUyBAmy5AJBhYUG2EAhgIFAQMAgQIGCgQABCg4ABEAwUNFI2AKZHAKZEgGRZTGOIUDQxJxGKH5Q/agwAxrdt23bAQVABIMly1ZsoCCMgUWCIYCB6AJBhIRDAQNgBIMFEwlt2i1CEwmWrAJBgI7FtpGCHYuWKH5QxEwpQDlo7F0A7IqBZBEwo7BCIwCBJo53CJoxiCJpIAdgOmzVpAQR/CgAIEAQJ2CBAoCBBIMmCg1oD4QLGFQUCCjQ+CKYw+CKY4JCKYwoCGRMaGREJDoroCgwdFzBlLKH5QvAHih/eX5Q/KE4A8UP7y/KH5QGDpg7HJoxZCCIx3CJowmCF4yACJox/CgA=")) +}; + +var bgLeft = settings.fullscreen ? bgLeftFullscreen : bgLeftNotFullscreen; +var bgRight= settings.fullscreen ? bgRightFullscreen : bgRightNotFullscreen; + +var iconEarth = { + width : 50, height : 50, bpp : 3, + buffer : require("heatshrink").decompress(atob("AFtx48ECBsDwU5k/yhARLjgjBjlzAQMQEZcIkOP/fn31IEZgCBnlz58cEpM4geugEgwU/8+WNZJHDuHHvgmBCQ8goEOnVgJoMnyV58mACItHI4X8uAFBuVHnnz4BuGxk4////Egz3IkmWvPgNw8f/prB//BghTC+AjE7848eMjNnzySBwUJkmf/BuGuPDAQIjBiPHhhTCSQnjMo0ITANJn44Dg8MuFBggCCiFBcAJ0Bv5xEh+ITo2OhHkyf/OIQdBWwVHhgjBNwUE+fP/5EEgePMoYLBhMgyVJk/+BQQdC688I4XxOIc8v//NAvr+QEBj/5NwKVBy1/QYUciPBhk1EAJrC+KeC489QYaMBgU/8BNB9+ChEjz1Jkn/QYMBDQIgCcYTCCiP/nlzJQmenMAgV4//uy/9wRaB/1J8iVCcAfHjt9TYYICnhKCgRKBw159/v//r927OIeeoASBDQccvv3791KYVDBYPLJQeCnPnz//AAP6ocEjEkXgMgJQtz79fLAP8KYkccAcJ8Gf/f/xu/cAMQ4eP5MlyQRCMolx40YsOGBAPfnnzU4KVDpKMBvz8Dh0/8me7IICgkxJQXPIgZTD58sEgcJk+eNoONnFBhk4/5uB/pcDg5KD+4mEv4CBXISVDhEn31/8/+mH7x//JQK5CAAMB4JBCnnxJQf/+fJEgkAa4L+CAQOOjMn/1bXIRxDJQXx58f//Hhlz/88EgsChMgz/Zs/+nfkyV/8huDOI6SD498NwoACi1Z8+S/Plz17/+QCI7jC+ZxBmfPnojIAAMDcYWSp//2wRJEwq2GABECjMgNYwAmA=")) +}; + +var iconSaturn = { + width : 50, height : 50, bpp : 3, + transparent : 1, + buffer : require("heatshrink").decompress(atob("AH4A/AEkQuPHCJ0ChEAwARNjAjBjgjOhs06Q2OEYVx4ARMhEggUMkANIDoIgBoEEgEBNxJEC6ZrBAAMwNxAjDNYcHNxIjB7dtEwIHBwRoKj158+cuPEjlwCRAjC23bpu0wRNDAAsHEYWeEwaSJ6YjCAQUNSRQjEzxQBWZMNEYlsmg2JWAIjCz95SoJuJggjDtuw6dMG5JKCz998wFBJRVNEYW0yaVBJRNhJQN9+4pCzhKJmBKC4YpB/fINxIgCzFxSoQ3J4ENm3CAQPb98wbpEcAQMYWwKYBNxMDXgc2/fv3g2IEAOAgAjBjy5CEhEMfYICBgfPnjdLjj+CgMHiC3JknDhhoINw4jCAB0IJQIANR4QjPAH4A/AFA")) +}; + +var iconMoon = { + width : 50, height : 50, bpp : 3, + transparent : 1, + buffer : require("heatshrink").decompress(atob("AH4AQjlx44CCCZsg8eOkHDwAQKEYgmPhEgEQM48AOIgMHEYoCB4ATI8UAmH/x04JoRuJsImHuBKLn37EwZuIgEQOI8cEpXj/yYBhE8+YNGgkYoJxITBUPnAaC///nC+FjBuIOJZEB8YeCh/8AoYACoMEEAnEjhQDPQJKJ/DCDAoi5DoLdHAoMQgLjFWYPOnngh02IwXzwDjEgPGEYS8BI4MBYoSVG4fP/nghkAgZrDkngJQqSG4gvBg4sBQgkImHihEAWwP8ZBMBEYl5/+cSoVAGQIUFh04weJn///0gj/OEw5KEz45BzhuCTYQAEgePB4IACAoJuBnAQEa4XHjxKB//xFgWHJQsCRgMDEonipwjENwUBDQNx8+evvn/hTDLw3igE+EgZxB8UOXIvEJQUfEYOfv53DEQkgga5BJQvzx84cAj+CDoNh8/eEYJKDuCSEcocnEon+/7xEgFBIIcfB4Mf/IICXI2DgDdBAAn758gCIq5Dv4zBvJuIOIfjEgvP/ARHgwdCB4P3AoTdFAAk4EYk8SQgAFTALaDSQwAGh08//vnDmBABYmEEZYAzA==")) +}; + +var iconMars = { + width : 50, height : 50, bpp : 3, + transparent : 1, + buffer : require("heatshrink").decompress(atob("AH4ATjlwCJ+Dh0wwAQMg0cuPHjFhCZkDps0yVJkmQCBMEjFx42atOmzQmLhMkEYQCCCREQoOGEYmmzB0IEY4CBkARGoJKBEYQCEzgSGkGSpAjDyYCCphuGiFhJQgCD8ASFgRHGAQKbB6BuHJRGeOIsINxEk6dNmARDgMEjQjHAQPnVQojIyZKB6YSDNwK5FAQt54BuDXJIjBEwK5EgxKKXgq5BJRdgXIojJAQJKMcAM0EwM2JUApDoCVFExa7FkGCgAmIkAREEwUEjAmHCIgABhEggQmFpACBCIojBEwRQCzVhwkQU4YADgQmBwQCCI4IFBCAojFAQojGJQQjDAQgRGEZICBEo4gFyUIkilFJQUYEAZrBAQMYNw5KDSQSbCNwwABgOGEwgCBsPACQ5xGwdNnARJcAVh48evvnCJK8Chs+/fv33gCRcB48cuPHCBYA/ADAA==")) +}; + +var iconSatellite = { + width : 50, height : 50, bpp : 3, + transparent : 2, + buffer : require("heatshrink").decompress(atob("pMkyQC/ATGXhIRPyNl0gmPjlwCJ9ly1aCJ1c+fHJR1Hy1ZJR1I+fPnlx6QRLpe+/JKBr5KMuYjBJQMdCJce/fvJQW0CJUlEYQCBSpvvJQbXJjl0NwnzNxGQwEOnHhgF78+WqQyIrFx48cAQXz4ShJgAABh0+8cP//9LJEhg4jDuP3//0LhGQgYlBgeAn///5cIy8MuAmDCIP/9I4HkmCEYMOgHfCQWkCI0cuBuDgF/CIP+CI1Ny1IkeAgHANwIAB/QRFrj7BhkxEwQRC/4RFpbXDgSVBg4RCSorXDI4MJAQMfCIP8cwImDn37fwN58+kwHgLgSVFub7CI4NyBAJKDLgkuEYX78+evKtCLg0jEYRKC58JMoRcFkwjDJQTFDl65EkojEAQMdcwn/+gFC3YjEJQLXEpYRDWwQmEdI6SHAQO0CJUkx4jDF4gCIJQgRMXIjCEARIjCCJ2XEYPKCJqJBJQIROcAUpCJ0kybaDARtdCKAC2kAA=")) +}; + +var iconCharging = { + width : 50, height : 50, bpp : 3, + transparent : 5, + buffer : require("heatshrink").decompress(atob("23btugAwUBtoICARG0h048eODQYCJ6P/AAUCCJfbo4SDxYRLtEcuPHjlwgoRJ7RnIloUHoYjDAQfAExEAwUIkACEkSAIEYwCBhZKH6EIJI0CJRFHEY0BJRWBSgf//0AJRYSE4BKLj4SE8BKLv4RD/hK/JS2AXY0gXwRKG4cMmACCJQMAg8csEFJQsBAwfasEAm379u0gFbcBfHzgFBz1xMQZKBjY/D0E2+BOChu26yVEEYdww+cgAFCg+cgIfB6RKF4HbgEIkGChEAthfCJQ0eEAIjBBAMxk6GCJQtgtyVBwRKBAQMbHAJKGXIIFCgACBhl54qVG2E+EAJKBJoWAm0WJQ6SCXgdxFgMLJQvYjeAEAUwFIUitEtJQ14NwUHgEwKYZKGwOwNYX7XgWCg3CJQ5rB4MevPnAoPDJRJrCgEG/ECAoNsJRUwoEesIIBiJKI3CVDti/CJRKVDiJHBSo0YsOGjED8AjBcAcIgdhcAXAPIUAcAYIBcA4dBAQUG8BrBgBuCgOwcBEeXIK2BBAIFBgRqBGoYAChq8CcYUE4FbUYOACQsHzgjDgwFBCIImBAQsDtwYD7cAloRI22B86YBw5QBgoRJ7dAgYEDCJaeBJoMcsARMAQNoJIIRE6A")) +}; + +var iconNoBattery = { + text: "NO BAT", + width : 50, height : 50, bpp : 3, + transparent : 1, + buffer : require("heatshrink").decompress(atob("kmSpIC/AWMyoQIFsmECJFJhMmA4QXByVICIwODAQ4RRFIQGD5JVLkIGDzJqMyAGDph8MiRKGyApEAoZKFyYIDQwMkSQNkQZABBhIIOOJRuEL5gRIAUKACVQMhmUSNYNDQYJTBBwYFByGTkOE5FJWYNMknCAQKYCiaSCpmGochDoSYBhMwTAZrChILBhmEzKPBF4ImBTAREBDoMmEwJVDoYjBycJFgWEJQRuLJQ1kmQCCjJlCBYbjCagaDBwyDBmBuBF4TjJAUQKINBChCDQxZBcZIIQF4NIgEAgKSDiQmEVQKMBoARBAAMCSQLLBVoxqKL4gaCChVCNwoRKOIo4CJIgABBoSMHpIRFgDdJOIJUBCAUJRgJuEAQb+DIIgRIAX4C/ASOQA")) +}; + +// Font to use: +// +Graphics.prototype.setFontAntonioMedium = function(scale) { + // Actual height 20 (19 - 0) + g.setFontCustom(atob("AAAAAAAAAAAAAAAAAAAA//mP/5gAAAAAAAAAAAAA/gAMAAAAAA/gAPAAAEIIBP+H/8D+IYBP+H/8D+IABCAAwIAfnwP8+PHh448eP3+B4fAAAAAAAH/AD/4AwGAMBgD/4Af8GAAPgAPgAfgAfAAfAA+AAOP/AH/4BgGAYBgH/4A/8AAAAAAAAAQAA/B+f4/+GMPhjv/4/h8Dg/gAcYwAAPwADgAAAAAAAAB//8///sAAaAACAAAMAAb//+f//AAAAAAAbAAGwAA4AA/wADgABsAAbAAAAAAAgAAMAAPwAD8AAMAADAAAAAAAAAAHAAB/AAOAAAAAAAAMAADAAAwAAMAACAAAAAAAAAABgAAYAAAAAAAAA4AD+AP+A/4A/gAOAAAAAAAAAH//j//8wADMAAz//8f/+AAAAAAAMAADAABgAA//+P//gAAAAAAAAAAAAAfgfP4fzAfswfDP/gx/gMAAAHgPj4D8wMDMHAz//8f3+AAEAAAAADwAH8APzA/AwP//j//4AAwAAAD/Hw/x+MwBjOAYz/+Mf/AAAAAAAH//j//8wYDMGAz9/8fP+AAcDAAAwAAMAfjB/4z/wP+AD4AAwAAAAOB/f4///MHAzBwM///H9/gAAAAAAH/Pj/78wGDMBgz//8f/+AAAAAAADhwA4cAAAAAAAAAAAAAADh/A4fgAAAAOAAHwABsAA7gAccAGDAAAAANgADYAA2AANgADYAA2AAAAAAAABgwAccADuAAbAAHwAA4AAAAHwAD8c4/POMHAD/wAfwAAAAAAAAD/wD//B4B4Y/HMf8zMBMyATMwczP+M4BzHwcgf+AA+AAAAAAD4A/+P/8D+DA/4wH/+AB/4AAeAAAAAAA//+P//jBgYwYGP//j//4PH4AAAAAAAf/+P//zgAcwADP4fz+P4Ph8AAAAAAA//+P//jAAYwAGPADj//4P/4AAAAAAA//+P//jBgYwYGMGBgAAAAAAP//j//4wYAMGADBgAAAAAAAA//w///PAHzAQM4MHP7/x+/8AAAAAAD//4//+AGAABgAAYAP//j//4AAAAAAAAAA//+P//gAAAAAAAAAAAHwAB+AABgAAY//+P//AAAAAAAAAAD//4//+APgAf+Afj8PgPjAAYAAAAAAD//4//+AABgAAYAAGAAAAAAA//+P//j/gAD/wAB/gAP4B/4P/AD//4//+AAAAAAAAAAP//j//4P4AAfwAA/g//+P//gAAAAAAAAAA//g//+PAHjAAY4AOP//h//wAAAAAAD//4//+MDADAwA4cAP/AB/gAAAAAAAA//g//+PAHjAAc4APv//5//yAAAAAAD//4//+MGADBgA48AP//h+f4AAAAAAB+Pw/z+MOBjBwY/P+Hx/AAHgwAAMAAD//4//+MAADAAAAAAP//D//4AAOAABgAA4//+P//AAAAwAAP8AD//AA/+AAfgP/4//gPwAAAAA+AAP/4Af/4AD+A//j/wA/wAD/+AA/4B/+P/+D+AAAAAMADj8P4P/4A/4B//w+A+MABgAAA4AAPwAB/gAB/+A//j/gA+AAMAAAAAYwB+MH/jf+Y/8GPwBjAAAAAAP//7//+wABsAAYAAAAAAPAAD/gAH/gAD/gAD4AACAAADAAGwABv//7//+AAAA=="), 32, atob("BQUHCAgVCQQFBQkHBQcFBwgICAgICAgICAgFBQcHBwgPCQkJCQcHCQoFCQkHDQoJCQkJCAYJCQ0ICAcGBwY="), 20+(scale<<8)+(1<<16)); +}; + +Graphics.prototype.setFontAntonioLarge = function(scale) { + // Actual height 39 (39 - 1) + g.setFontCustom(atob("AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAB8AAAAAAPgAAAAAB8AAAAAAHgAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAABgAAAAAD8AAAAAH/gAAAAP/8AAAAf//gAAA///AAAB//+AAAD//8AAAH//4AAAP//wAAAB//gAAAAP/AAAAAB+AAAAAAMAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAH///AAAf////8AP/////4B//////Af/////8D8AAAAfgeAAAAA8DwAAAAHgeAAAAA8D//////gf/////8B//////AP/////wAf////8AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA8AAAAAAHgAAAAAA8AAAAAAPgAAAAAB4AAAAAAf/////gP/////8B//////gP/////8B//////gAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA/wAAAAD/+AAP8A//wAP/gP/+AH/8D//wD//gfgAA//8DwAAf+HgeAAP/A8DwAH/gHgfgP/wA8D///4AHgP//+AA8A///AAHgB//AAAcAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAD4AA/gAD/AAH/gA/4AA/+AP/AAH/4D/4AA//gfgA4AB8DwAPAAHgeAB4AA8DwAPgAHgfAD+AB8D//////gP/////4B//5//+AD/+H//gAH/AH/wAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAP4AAAAAP/AAAAAP/4AAAAP//AAAAP/x4AAAf/wPAAAf/gB4AAf/AAPAAP/AAB4AB//////gP/////8B//////gP/////8AAAAAPAAAAAAB4AAAAAAPAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAP//wD/AB///Af+AP//4D/4B///Af/gP//4B/8B4D4AAPgPAeAAA8B4DwAAHgPAfAAB8B4D////gPAf///4B4B////APAD///gAAAD//gAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAB///AAAP////4AH/////wB//////Af/////8D8APAA/geADwAB8DwAeAAHgeADwAA8D4AeAAPgf/j+AH8B/8f///gP/h///4Af8H//+AAPgP//AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAB4AAAAAAPAAAAAAB4AAAABgPAAAA/8B4AAB//gPAAD//8B4AH///gPAH///8B4P//+AAPH//wAAB///gAAAP//AAAAB/+AAAAAP+AAAAAB+AAAAAAOAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA/4A/+AAf/w//+AP//v//4B//////Af/////8D4AfwAPgeAB8AA8DwAHAAHgeAB8AA8D4Af4APgf/////8B//////AP//v//4A//4//8AA/4A/+AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAH/+AAAAD//+D/gB///4f+AP///j/4D///8f/gfAAHgB8DwAA8AHgeAAHgA8DwAA8AHgfgAHgB8D//////gP/////4A/////+AD/////gAD////AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAPwAfgAAB+AD8AAAPwAfgAAB+AD8AAAPwAfgAAAAAAAAAAAAAAAAAAAAAAAA=="), 46, atob("DBATExMTExMTExMTCw=="), 45+(scale<<8)+(1<<16)); +}; + + +/* + * Draw watch face + */ +var drawTimeout; +function queueDraw() { + if (drawTimeout) clearTimeout(drawTimeout); + drawTimeout = setTimeout(function() { + drawTimeout = undefined; + draw(); + }, 60000 - (Date.now() % 60000)); +} + +/** + * This function plots a data row in LCARS style. + * Note: It can be called async and therefore, the text alignment and + * font is set each time the function is called. + */ +function printRow(text, value, y, c){ + g.setFontAntonioMedium(); + g.setFontAlign(-1,-1,0); + + // Print background + g.setColor(c); + g.setFontAlign(-1,-1,0); + g.fillRect(80, y-2, 165 ,y+18); + g.fillCircle(163, y+8, 10); + g.setColor(cBlack); + g.drawString(text, 135, y); + + // Plot text + width = g.stringWidth(value); + g.setColor(cBlack); + g.fillRect(130-width-8, y-2, 130, y+18); + g.setColor(c); + g.setFontAlign(1,-1,0); + g.drawString(value, 126, y); +} + + +function drawData(key, y, c){ + try{ + _drawData(key, y, c); + } catch(ex){ + // Show last error - next try hopefully works. + } +} + + +function _drawData(key, y, c){ + key = key.toUpperCase() + var text = key; + var value = "ERR"; + var should_print= true; + + if(key == "STEPS"){ + text = "STEP"; + value = getSteps(); + + } else if(key == "BATTERY"){ + text = "BAT"; + value = E.getBattery() + "%"; + + } else if (key == "VREF"){ + value = E.getAnalogVRef().toFixed(2) + "V"; + + } else if(key == "HRM"){ + value = Math.round(Bangle.getHealthStatus("day").bpm); + + } else if (key == "TEMP"){ + var weather = getWeather(); + value = weather.temp; + + } else if (key == "HUMIDITY"){ + text = "HUM"; + var weather = getWeather(); + value = weather.hum; + + } else if (key == "WIND"){ + text = "WND"; + var weather = getWeather(); + value = weather.wind; + + } else if (key == "ALTITUDE"){ + should_print= false; + text = "ALT"; + + // Immediately print something - avoid that its empty + printRow(text, "", y, c); + Bangle.getPressure().then(function(data){ + if(data && data.altitude){ + value = Math.round(data.altitude); + printRow(text, value, y, c); + } + }) + + } else if(key == "CORET"){ + value = locale.temp(parseInt(E.getTemperature())); } - function save() { - storage.write(SETTINGS_FILE, settings) + // Print for all datapoints that are not async + if(should_print){ + printRow(text, value, y, c); + } +} + +function drawHorizontalBgLine(color, x1, x2, y, h){ + g.setColor(color); + + for(var i=0; i dataOptions[v], - onchange: v => { - settings.dataRow1 = dataOptions[v]; - save(); - }, - }, - 'Row 2': { - value: 0 | dataOptions.indexOf(settings.dataRow2), - min: 0, max: 8, - format: v => dataOptions[v], - onchange: v => { - settings.dataRow2 = dataOptions[v]; - save(); - }, - }, - 'Row 3': { - value: 0 | dataOptions.indexOf(settings.dataRow3), - min: 0, max: 8, - format: v => dataOptions[v], - onchange: v => { - settings.dataRow3 = dataOptions[v]; - save(); - }, - }, - 'Full Screen': { - value: settings.fullscreen, - format: () => (settings.fullscreen ? 'Yes' : 'No'), - onchange: () => { - settings.fullscreen = !settings.fullscreen; - save(); - }, - }, - 'Speed': { - value: 0 | speedOptions.indexOf(settings.speed), - min: 0, max: 1, - format: v => speedOptions[v], - onchange: v => { - settings.speed = speedOptions[v]; - save(); - }, - }, - 'Theme Color 1': { - value: 0 | color_options.indexOf(settings.themeColor1), - min: 0, max: 7, - format: v => color_options[v], - onchange: v => { - settings.themeColor1 = color_options[v]; - settings.themeColor1BG = bg_code[v]; - save(); - }, - }, - 'Theme Color 2': { - value: 0 | color_options.indexOf(settings.themeColor2), - min: 0, max: 7, - format: v => color_options[v], - onchange: v => { - settings.themeColor2 = color_options[v]; - settings.themeColor2BG = bg_code[v]; - save(); - }, - }, - 'Theme Color 3': { - value: 0 | color_options.indexOf(settings.themeColor3), - min: 0, max: 7, - format: v => color_options[v], - onchange: v => { - settings.themeColor3 = color_options[v]; - settings.themeColor3BG = bg_code[v]; - save(); - }, + if(NRF.getSecurityStatus().connected){ + g.drawString("CONN", 128, 33); + } else { + g.drawString("NOCON", 128, 33); + } + if(Bangle.isLocked()){ + g.setColor(cPurple); + g.drawString("LOCK", 128, 53); + } +} + +function drawState(){ + if(lcarsViewPos != 0){ + return; + } + + g.clearRect(20, 93, 75, 170); + g.setFontAlign(0, 0, 0); + g.setFontAntonioMedium(); + + if(!isAlarmEnabled()){ + var bat = E.getBattery(); + var current = new Date(); + var hours = current.getHours(); + var iconImg = + Bangle.isCharging() ? iconCharging : + bat < 30 ? iconNoBattery : + Bangle.isGPSOn() ? iconSatellite : + hours % 4 == 0 ? iconSaturn : + hours % 4 == 1 ? iconMars : + hours % 4 == 2 ? iconMoon : + iconEarth; + g.drawImage(iconImg, 23, 118); + g.setColor(cWhite); + g.drawString("STATUS", 23+26, 108); + } else { + // Alarm within symbol + g.setColor(cOrange); + g.drawString("ALARM", 23+26, 108); + g.setColor(cWhite); + g.setFontAntonioLarge(); + g.drawString(getAlarmMinutes(), 23+26, 108+35); + } + + g.setFontAlign(-1, -1, 0); +} + + +function drawPosition0(){ + // Draw background image + var offset = settings.fullscreen ? 0 : 24; + g.drawImage(bgLeft, 0, offset); + drawHorizontalBgLine(cBlue, 25, 120, offset, 4); + drawHorizontalBgLine(cBlue, 130, 176, offset, 4); + drawHorizontalBgLine(cPurple, 20, 70, 80, 4); + drawHorizontalBgLine(cPurple, 80, 176, 80, 4); + drawHorizontalBgLine(cOrange, 35, 110, 87, 4); + drawHorizontalBgLine(cOrange, 120, 176, 87, 4); + + // The last line is a battery indicator too + var bat = E.getBattery() / 100.0; + var batStart = 19; + var batWidth = 172 - batStart; + var batX2 = parseInt(batWidth * bat + batStart); + drawHorizontalBgLine(cOrange, batStart, batX2, 171, 5); + drawHorizontalBgLine(cGrey, batX2, 172, 171, 5); + for(var i=0; i+batStart<=172; i+=parseInt(batWidth/4)){ + drawHorizontalBgLine(cBlack, batStart+i, batStart+i+3, 168, 8) + } + + // Draw Infos + drawInfo(); + + // Write time + g.setFontAlign(-1, -1, 0); + g.setColor(cWhite); + var currentDate = new Date(); + var timeStr = locale.time(currentDate,1); + g.setFontAntonioLarge(); + if(settings.fullscreen){ + g.drawString(timeStr, 27, 10); + } else { + g.drawString(timeStr, 27, 33); + } + + // Write date + g.setColor(cWhite); + g.setFontAntonioMedium(); + if(settings.fullscreen){ + var dayStr = locale.dow(currentDate, true).toUpperCase(); + dayStr += " " + currentDate.getDate(); + dayStr += " " + locale.month(currentDate, 1).toUpperCase(); + g.drawString(dayStr, 30, 56); + } else { + var dayStr = locale.dow(currentDate, true).toUpperCase(); + var date = currentDate.getDate(); + g.drawString(dayStr, 128, 35); + g.drawString(date, 128, 55); + } + + // Draw data + g.setFontAlign(-1, -1, 0); + g.setColor(cWhite); + drawData(settings.dataRow1, 97, cOrange); + drawData(settings.dataRow2, 122, cPurple); + drawData(settings.dataRow3, 147, cBlue); + + // Draw state + drawState(); +} + +function drawPosition1(){ + // Draw background image + var offset = settings.fullscreen ? 0 : 24; + g.drawImage(bgRight, 149, offset); + if(settings.fullscreen){ + drawHorizontalBgLine(cBlue, 0, 140, offset, 4); + } + drawHorizontalBgLine(cPurple, 0, 80, 80, 4); + drawHorizontalBgLine(cPurple, 90, 150, 80, 4); + drawHorizontalBgLine(cOrange, 0, 50, 87, 4); + drawHorizontalBgLine(cOrange, 60, 140, 87, 4); + drawHorizontalBgLine(cOrange, 0, 150, 171, 5); + + // Draw steps bars + g.setColor(cWhite); + let health; + + try { + health = require("health"); + } catch(ex) { + g.setFontAntonioMedium(); + g.drawString("MODULE HEALTH", 20, 110); + g.drawString("REQUIRED.", 20, 130); + g.drawString("MODULE HEALTH", 20, 20); + g.drawString("REQUIRED.", 20, 40); + return; + } + + // Plot HRM graph + if(plotMonth){ + var data = new Uint16Array(32); + var cnt = new Uint8Array(32); + health.readDailySummaries(new Date(), h=>{ + data[h.day]+=h.bpm; + if (h.bpm) cnt[h.day]++; + }); + require("graph").drawBar(g, data, { + axes : true, + minx: 1, + gridx : 5, + gridy : 100, + width : 140, + height : 50, + x: 5, + y: 25 + }); + + // Plot step graph + var data = new Uint16Array(32); + health.readDailySummaries(new Date(), h=>data[h.day]+=h.steps/1000); + var gridY = parseInt(Math.max.apply(Math, data)/2); + gridY = gridY <= 0 ? 1 : gridY; + require("graph").drawBar(g, data, { + axes : true, + minx: 1, + gridx : 5, + gridy : gridY, + width : 140, + height : 50, + x: 5, + y: 115 + }); + + g.setFontAlign(1, 1, 0); + g.setFontAntonioMedium(); + g.setColor(cWhite); + + if(settings.fullscreen){ + g.drawString("M-HRM", 154, 27); + g.drawString("M-STEPS [K]", 154, 115); + } else { + g.drawString("MONTH", 154, 115); } + + // Plot day + } else { + var data = new Uint16Array(24); + var cnt = new Uint8Array(24); + health.readDay(new Date(), h=>{ + data[h.hr]+=h.bpm; + if (h.bpm) cnt[h.hr]++; + }); + require("graph").drawBar(g, data, { + axes : true, + minx: 1, + gridx : 4, + gridy : 100, + width : 140, + height : 50, + x: 5, + y: 25 + }); + + // Plot step graph + var data = new Uint16Array(24); + health.readDay(new Date(), h=>data[h.hr]+=h.steps); + var gridY = parseInt(Math.max.apply(Math, data)/1000)*1000; + gridY = gridY <= 0 ? 1000 : gridY; + require("graph").drawBar(g, data, { + axes : true, + minx: 1, + gridx : 4, + gridy : gridY, + width : 140, + height : 50, + x: 5, + y: 115 + }); + + g.setFontAlign(1, 1, 0); + g.setFontAntonioMedium(); + g.setColor(cWhite); + + if(settings.fullscreen){ + g.drawString("D-HRM", 154, 27); + g.drawString("D-STEPS", 154, 115); + } else { + g.drawString("DAY", 154, 115); + } + } +} + +function draw(){ + // Queue draw first to ensure that its called in one minute again. + queueDraw(); + + // First handle alarm to show this correctly afterwards + handleAlarm(); + + // Next draw the watch face + g.reset(); + g.clearRect(0, 0, g.getWidth(), g.getHeight()); + + // Draw current lcars position + if(lcarsViewPos == 0){ + drawPosition0(); + } else if (lcarsViewPos == 1) { + drawPosition1(); + } + + // After drawing the watch face, we can draw the widgets + if(settings.fullscreen){ + for (let wd of WIDGETS) {wd.draw=()=>{};wd.area="";} + } else { + Bangle.drawWidgets(); + } +} + + +/* + * Step counter via widget + */ +function getSteps() { + try{ + if (WIDGETS.wpedom !== undefined) { + return WIDGETS.wpedom.getSteps(); + } else if (WIDGETS.activepedom !== undefined) { + return WIDGETS.activepedom.getSteps(); + } + } catch(ex) { + // In case we failed, we can only show 0 steps. + } + + return 0; +} + + +function getWeather(){ + var weatherJson; + + try { + weatherJson = storage.readJSON('weather.json'); + } catch(ex) { + // Return default + } + + if(weatherJson === undefined){ + return { + temp: "-", + hum: "-", + txt: "-", + wind: "-", + wdir: "-", + wrose: "-" + }; + } + + var weather = weatherJson.weather; + + // Temperature + weather.temp = locale.temp(weather.temp-273.15); + + // Humidity + weather.hum = weather.hum + "%"; + + // Wind + const wind = locale.speed(weather.wind).match(/^(\D*\d*)(.*)$/); + var speedFactor = settings.speed == "kph" ? 1.0 : 1.0 / 1.60934; + weather.wind = Math.round(wind[1] * speedFactor); + + return weather +} + + +/* + * Handle alarm + */ +function getCurrentTimeInMinutes(){ + return Math.floor(Date.now() / (1000*60)); +} + +function isAlarmEnabled(){ + return settings.alarm >= 0; +} + +function getAlarmMinutes(){ + var currentTime = getCurrentTimeInMinutes(); + return settings.alarm - currentTime; +} + +function handleAlarm(){ + if(!isAlarmEnabled()){ + return; + } + + if(getAlarmMinutes() > 0){ + return; + } + + // Alarm + var t = 300; + Bangle.buzz(t, 1) + .then(() => new Promise(resolve => setTimeout(resolve, t))) + .then(() => Bangle.buzz(t, 1)) + .then(() => new Promise(resolve => setTimeout(resolve, t))) + .then(() => Bangle.buzz(t, 1)) + .then(() => new Promise(resolve => setTimeout(resolve, t))) + .then(() => Bangle.buzz(t, 1)) + .then(() => new Promise(resolve => setTimeout(resolve, 5E3))) + .then(() => { + // Update alarm state to disabled + settings.alarm = -1; + storage.writeJSON(SETTINGS_FILE, settings); }); -}) +} + + +/* + * Listeners + */ +Bangle.on('lcdPower',on=>{ + if (on) { + // Whenever we connect to Gadgetbridge, reading data from + // health failed. Therefore, we update only partially... + drawInfo(); + drawState(); + } else { // stop draw timer + if (drawTimeout) clearTimeout(drawTimeout); + drawTimeout = undefined; + } +}); + +Bangle.on('lock', function(isLocked) { + drawInfo(); +}); + +Bangle.on('charging',function(charging) { + drawState(); +}); + + +function increaseAlarm(){ + if(isAlarmEnabled() && getAlarmMinutes() < 95){ + settings.alarm += 5; + } else { + settings.alarm = getCurrentTimeInMinutes() + 5; + } + + storage.writeJSON(SETTINGS_FILE, settings); +} + + +function decreaseAlarm(){ + if(isAlarmEnabled() && (settings.alarm-5 > getCurrentTimeInMinutes())){ + settings.alarm -= 5; + } else { + settings.alarm = -1; + } + + storage.writeJSON(SETTINGS_FILE, settings); +} + +function feedback(){ + Bangle.buzz(40, 0.3); +} + +// Touch gestures to control clock. We don't use swipe to be compatible with the bangle ecosystem +Bangle.on('touch', function(btn, e){ + var left = parseInt(g.getWidth() * 0.2); + var right = g.getWidth() - left; + var upper = parseInt(g.getHeight() * 0.2); + var lower = g.getHeight() - upper; + + var is_left = e.x < left; + var is_right = e.x > right; + var is_upper = e.y < upper; + var is_lower = e.y > lower; + + if(is_left && lcarsViewPos == 1){ + feedback(); + lcarsViewPos = 0; + draw(); + return; + + } else if(is_right && lcarsViewPos == 0){ + feedback(); + lcarsViewPos = 1; + draw(); + return; + } + + if(lcarsViewPos == 0){ + if(is_upper){ + feedback(); + increaseAlarm(); + drawState(); + return; + } if(is_lower){ + feedback(); + decreaseAlarm(); + drawState(); + return; + } + } else if (lcarsViewPos == 1 && (is_upper || is_lower) && plotMonth != is_lower){ + feedback(); + plotMonth = is_lower; + draw(); + return; + } +}); + + +/* + * Lets start widgets, listen for btn etc. + */ +// Show launcher when middle button pressed +Bangle.setUI("clock"); +Bangle.loadWidgets(); + +// Clear the screen once, at startup and draw clock +g.setTheme({bg:"#000",fg:"#fff",dark:true}).clear(); +draw(); From b364c4f26653bb109d317c56708f21ee631393a3 Mon Sep 17 00:00:00 2001 From: Ronin0000 <89286474+Ronin0000@users.noreply.github.com> Date: Mon, 11 Apr 2022 07:34:14 -0700 Subject: [PATCH 05/63] Update lcars.settings.js --- apps/lcars/lcars.settings.js | 39 ++++++++++++++++++++++++++++++++++++ 1 file changed, 39 insertions(+) diff --git a/apps/lcars/lcars.settings.js b/apps/lcars/lcars.settings.js index 75add1ece..f714c3a7a 100644 --- a/apps/lcars/lcars.settings.js +++ b/apps/lcars/lcars.settings.js @@ -10,6 +10,12 @@ dataRow3: "Temp", speed: "kph", fullscreen: false, + themeColor1: "Orange", + themeColor1BG: "#FF9900", + themeColor2: "Purple", + themeColor2BG: "#FF00DC", + themeColor3: "Cyan", + themeColor3BG: "#0094FF", }; let saved_settings = storage.readJSON(SETTINGS_FILE, 1) || settings; for (const key in saved_settings) { @@ -20,8 +26,11 @@ storage.write(SETTINGS_FILE, settings) } + var dataOptions = ["Steps", "Battery", "VREF", "HRM", "Temp", "Humidity", "Wind", "Altitude", "CoreT"]; var speedOptions = ["kph", "mph"]; + var color_options = ['Green','Orange','Cyan','Purple','Red','Blue','Yellow','White']; + var bg_code = ['#0f0','#FF9900','#0094FF','#FF00DC','#f00','#00f','#ffef00','#FFFFFF']; E.showMenu({ '': { 'title': 'LCARS Clock' }, @@ -69,6 +78,36 @@ settings.speed = speedOptions[v]; save(); }, + }, + 'Theme Color 1': { + value: 0 | color_options.indexOf(settings.themeColor1), + min: 0, max: 7, + format: v => color_options[v], + onchange: v => { + settings.themeColor1 = color_options[v]; + settings.themeColor1BG = bg_code[v]; + save(); + }, + }, + 'Theme Color 2': { + value: 0 | color_options.indexOf(settings.themeColor2), + min: 0, max: 7, + format: v => color_options[v], + onchange: v => { + settings.themeColor2 = color_options[v]; + settings.themeColor2BG = bg_code[v]; + save(); + }, + }, + 'Theme Color 3': { + value: 0 | color_options.indexOf(settings.themeColor3), + min: 0, max: 7, + format: v => color_options[v], + onchange: v => { + settings.themeColor3 = color_options[v]; + settings.themeColor3BG = bg_code[v]; + save(); + }, } }); }) From 3eea59ac5ac5b12cb8fa7a66ecec6fd3e1641954 Mon Sep 17 00:00:00 2001 From: Ronin0000 <89286474+Ronin0000@users.noreply.github.com> Date: Mon, 11 Apr 2022 07:35:45 -0700 Subject: [PATCH 06/63] Update README.md --- apps/lcars/README.md | 2 ++ 1 file changed, 2 insertions(+) diff --git a/apps/lcars/README.md b/apps/lcars/README.md index 7024e8edf..65e31b3cc 100644 --- a/apps/lcars/README.md +++ b/apps/lcars/README.md @@ -19,6 +19,7 @@ the "sched" app must be installed on your device. * Tap on top/bottom of screen 1 to activate an alarm. Depends on widtmr. * The lower orange line indicates the battery level. * Display graphs (day or month) for steps + hrm on the second screen. + * Customizable theming colors in the settings menu of the app. ## Data that can be configured * Steps - Steps loaded via the wpedom app. @@ -43,3 +44,4 @@ Access different screens via tap on the left/ right side of the screen ## Contributors - [Adam Schmalhofer](https://github.com/adamschmalhofer) - [Jon Warrington](https://github.com/BartokW) +- [Ronin Stegner](https://github.com/Ronin0000) From e2e9b69b24a6ba97ad0c9ffe8d7c6f2031c17303 Mon Sep 17 00:00:00 2001 From: Eskild Hustvedt Date: Wed, 13 Apr 2022 19:16:08 +0200 Subject: [PATCH 07/63] Allow quiet mode to optionally override message auto-open --- apps/messages/lib.js | 11 +++++++++-- apps/messages/settings.js | 5 +++++ 2 files changed, 14 insertions(+), 2 deletions(-) diff --git a/apps/messages/lib.js b/apps/messages/lib.js index 7d49d4c64..f584c9e93 100644 --- a/apps/messages/lib.js +++ b/apps/messages/lib.js @@ -56,9 +56,16 @@ exports.pushMessage = function(event) { } // otherwise load messages/show widget var loadMessages = Bangle.CLOCK || event.important; - // first, buzz var quiet = (require('Storage').readJSON('setting.json',1)||{}).quiet; - var unlockWatch = (require('Storage').readJSON('messages.settings.json',1)||{}).unlockWatch; + var appSettings = require('Storage').readJSON('messages.settings.json',1)||{}; + var unlockWatch = appSettings.unlockWatch; + var quietNoAutOpn = appSettings.quietNoAutOpn; + delete appSettings; + // don't auto-open messages in quiet mode if quietNoAutOpn is true + if(quiet && quietNoAutOpn) { + loadMessages = false; + } + // first, buzz if (!quiet && loadMessages && global.WIDGETS && WIDGETS.messages){ WIDGETS.messages.buzz(); if(unlockWatch != false){ diff --git a/apps/messages/settings.js b/apps/messages/settings.js index cc0030ec5..adea36f12 100644 --- a/apps/messages/settings.js +++ b/apps/messages/settings.js @@ -53,6 +53,11 @@ format: v => v?/*LANG*/'Yes':/*LANG*/'No', onchange: v => updateSetting("flash", v) }, + /*LANG*/'Quiet mode disables auto-open': { + value: !!settings().quietNoAutOpn, + format: v => v?/*LANG*/'Yes':/*LANG*/'No', + onchange: v => updateSetting("quietNoAutOpn", v) + }, }; E.showMenu(mainmenu); }) From 52a7d85115e52d08369f79b69ff7966c1b4dbc9c Mon Sep 17 00:00:00 2001 From: Ronin0000 <89286474+Ronin0000@users.noreply.github.com> Date: Wed, 13 Apr 2022 15:07:38 -0700 Subject: [PATCH 08/63] Update lcars.app.js --- apps/lcars/lcars.app.js | 33 ++++++++++++++++++++++++++++----- 1 file changed, 28 insertions(+), 5 deletions(-) diff --git a/apps/lcars/lcars.app.js b/apps/lcars/lcars.app.js index 7cdd6749e..2704ea09d 100644 --- a/apps/lcars/lcars.app.js +++ b/apps/lcars/lcars.app.js @@ -23,9 +23,9 @@ for (const key in saved_settings) { /* * Colors to use */ -let cBlue = settings.themeColor1BG; -let cOrange = settings.themeColor2BG; -let cPurple = settings.themeColor3BG; +let cBlue = settings.themeColor3BG; +let cOrange = settings.themeColor1BG; +let cPurple = settings.themeColor2BG; let cWhite = "#FFFFFF"; let cBlack = "#000000"; let cGrey = "#424242"; @@ -38,6 +38,24 @@ let lcarsViewPos = 0; var plotMonth = false; +function convert24to16(input) +{ + let RGB888 = parseInt(input.replace(/^#/, ''), 16); + let r = (RGB888 & 0xFF0000) >> 16; + let g = (RGB888 & 0xFF00) >> 8; + let b = RGB888 & 0xFF; + + r = (r * 249 + 1014) >> 11; + g = (g * 253 + 505) >> 10; + b = (b * 249 + 1014) >> 11; + let RGB565 = 0; + RGB565 = RGB565 | (r << 11); + RGB565 = RGB565 | (g << 5); + RGB565 = RGB565 | b; + + return "0x"+RGB565.toString(16); +} + /* * Requirements and globals */ @@ -46,13 +64,17 @@ var plotMonth = false; var bgLeftFullscreen = { width : 27, height : 176, bpp : 3, transparent : 0, - buffer : require("heatshrink").decompress(atob("AAUM2XLlgCCwAJBBAuy4EAmQIF5cggAIGlmwgYIG2XIF42wF4ImGF4ImHJoQmGJoQdJhZNHNY47CgRNGBIJZHHgRiGBIRQ/KH5QCAFCh/eX5Q/KAwdCAGVbtu27YCCoAJBkuWrNlAQRGCiwRDAQPQBIMJCIYCBsAJBgomEtu0WoQmEy1YBIMBHYttIwQ7FyxQ/KHFlFAQ7F2weCHYplKChRTCCg5TCHw5TMAD0GzVp0wCCBBGaBIMaBAtpwECBA2mwEJBAugDgMmCIwJBF5EABAtoeQQvGCYQdPJoI7LMQzTCLJKAGzAJBO4xQ/KGQA8UP7y/KH5QnAHih/eX5Q/GQ4JCGRJlKCgxTDBAwgCCg5TCHwxTCNA4A==")) + buffer : require("heatshrink").decompress(atob("AAUM2XLlgCCwAJBBAuy4EAmQIF5cggAIGlmwgYIG2XIF42wF4ImGF4ImHJoQmGJoQdJhZNHNY47CgRNGBIJZHHgRiGBIRQ/KH5QCAFCh/eX5Q/KAwdCAGVbtu27YCCoAJBkuWrNlAQRGCiwRDAQPQBIMJCIYCBsAJBgomEtu0WoQmEy1YBIMBHYttIwQ7FyxQ/KHFlFAQ7F2weCHYplKChRTCCg5TCHw5TMAD0GzVp0wCCBBGaBIMaBAtpwECBA2mwEJBAugDgMmCIwJBF5EABAtoeQQvGCYQdPJoI7LMQzTCLJKAGzAJBO4xQ/KGQA8UP7y/KH5QnAHih/eX5Q/GQ4JCGRJlKCgxTDBAwgCCg5TCHwxTCNA4A==")), +// pallet: }; +var gray = convert24to16(cBlue); +var palette1 = new Uint16Array([0x0000,gray,0x0000,gray,0x0000,0x0000,0x0000,0x0000,0x0000,0x0000,0x0000,0x0000,0x0000,0x0000,0x0000,0x0000],0,1); var bgLeftNotFullscreen = { width : 27, height : 152, bpp : 3, transparent : 0, - buffer : require("heatshrink").decompress(atob("AAUM2XLlgCCwAJBBAuy4EAmQIF5cggAIGlmwgYIG2XIF42wF4ImGF4ImHJoQmGJoQdJhZNHNY47CgRNGBIJZHHgRiGBIRQ/KH5QCAGVbtu27YCCoAJBkuWrNlAQRkCiwRDAQPQBIMJCIYCBsAJBgomEtu0WoQmEy1YBIMBHYttIwQ7FyxQ/KHFlFAQ7F2weCHYplKChRTCCg5TCHw5TMAD0GzVp0wCCBBGaBIMaBAtpwECBA2mwEJBAugDgMmCIwJBF5EABAtoeQQvGCYQdPJoI7LMQzTCLJKAGzAJBO4xQ/KGQA8UP7y/KH5QnAHih/eX5Q/GQ4JCGRJlKCgxTDBAwgCCg5TCHwxTCNA4A=")) + buffer : require("heatshrink").decompress(atob("AAUM2XLlgCCwAJBBAuy4EAmQIF5cggAIGlmwgYIG2XIF42wF4ImGF4ImHJoQmGJoQdJhZNHNY47CgRNGBIJZHHgRiGBIRQ/KH5QCAGVbtu27YCCoAJBkuWrNlAQRkCiwRDAQPQBIMJCIYCBsAJBgomEtu0WoQmEy1YBIMBHYttIwQ7FyxQ/KHFlFAQ7F2weCHYplKChRTCCg5TCHw5TMAD0GzVp0wCCBBGaBIMaBAtpwECBA2mwEJBAugDgMmCIwJBF5EABAtoeQQvGCYQdPJoI7LMQzTCLJKAGzAJBO4xQ/KGQA8UP7y/KH5QnAHih/eX5Q/GQ4JCGRJlKCgxTDBAwgCCg5TCHwxTCNA4A=")), + palette: palette1 }; var bgRightFullscreen = { @@ -712,3 +734,4 @@ Bangle.loadWidgets(); // Clear the screen once, at startup and draw clock g.setTheme({bg:"#000",fg:"#fff",dark:true}).clear(); draw(); +console.log(bgLeftNotFullscreen); From bfa81d976613251edee2d0a2e5015e57e98d5456 Mon Sep 17 00:00:00 2001 From: Ronin0000 <89286474+Ronin0000@users.noreply.github.com> Date: Wed, 13 Apr 2022 15:34:50 -0700 Subject: [PATCH 09/63] Delete bg_right_small.png --- apps/lcars/bg_right_small.png | Bin 769 -> 0 bytes 1 file changed, 0 insertions(+), 0 deletions(-) delete mode 100644 apps/lcars/bg_right_small.png diff --git a/apps/lcars/bg_right_small.png b/apps/lcars/bg_right_small.png deleted file mode 100644 index df9d32b3853d8b2cabc83ef116f4179bfd5a48b0..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 769 zcmV+c1OEJpP)1^@s674VWH00004b3#c}2nYxW zdp7D}Ov?G*@oL+#TtdH7YQ(oT@B{0l-qvSc}))HbDiNVgNw(Jp^o?AdE4_7-Nhv#@JrMI2_Yh zHmMSe+@vzb7-Nhv#@MdJ`uk-iC1%33ubeq|Z^XGU}=XYQ>hyq?BSPDUa9z z0f3<1a3Kh=`IzNHwqdEqzVbgIa_qrfpYQ(sGm&hN`+CytMdY}k(FXL9;x&B=KDlhHczsoxTe zf1D15E=z+SdGgBgqw9(%psK%bAZ^prigLB7Nqt5IzRBFFsv8*iW{BlNS@El>PS@!~ zV%_}DlMobP2-69oYh9P9Fuk+$uqjrxw)TPw^EW5nTVI+W+?Bhhm1B%C#u#Iau|0xu zIHs{|<+O148i0zDVB9w{#u#IaF~%5UjO|ve+-iWXb)7?5ndLan{~60(KNE>KH-sR$ zInE~*j4{R-V~jDz*iNvtqBK)M>6!5Lf}L(A5^**(4o*^Gj@8wthLz2BbhsND2iK_} zZT6P`SSt11)`w33K-ZO)fT~UbJ2Ur-%-ms_?C({;riREM^_B27N^XJ^87 zA`B5w)ot%$lT@aqLpOdnolj2n^<{zKg5!PxC40_mtXBDF00000NkvXXu0mjfJ_~X1 From ec3291f3cf97a108d2b22729eae28f49d97cb5d4 Mon Sep 17 00:00:00 2001 From: Ronin0000 <89286474+Ronin0000@users.noreply.github.com> Date: Wed, 13 Apr 2022 15:34:56 -0700 Subject: [PATCH 10/63] Delete bg_left.png --- apps/lcars/bg_left.png | Bin 795 -> 0 bytes 1 file changed, 0 insertions(+), 0 deletions(-) delete mode 100644 apps/lcars/bg_left.png diff --git a/apps/lcars/bg_left.png b/apps/lcars/bg_left.png deleted file mode 100644 index 91c2bb6f7b7f83376ff41b83632819f239358246..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 795 zcmV+$1LXXPP)Lu@Z};XF?e>1+Kn$_>ce=9Pi+wv|?prf!_UgoA*PqAR;0Q5z%b*wr#QIW|?7DXB`WO z%tr&|L5E%C#LQ2Gh*GsW#jLp5NE($b9rB=*a#ddue-I}cpM(`96HM6pf*hi&({4!# zMnqIzE`A7dh_+UHE+@9(jS&b)WnUrf;lz`gzuxi#RaLe{Ro#&k>|I5LbwO22-LBT& z%>Wz1-c(obJ#qa0$E^Y@ldu~lk?60fImZnV#jPx=>v@_Mp5#Unu#tv_i~{G~Z(NOI zG5vxo9PUoQUio}kCq3`sdd!7sTDWhhu5Onh=IrWPhzwpU;R25w4SpG{tjt-f_GcQ3>bghM!iN9H z!jV;@SAT8oA$M`hSV}M=qNuKCYg%|ZCD?KX{QiPtC83d&V9R;k*r;0O<}SKjtq-?~ Z{RF94z^`^=I%EI<002ovPDHLkV1n^vZ1eyC From c4f6ca38248d1eb9ea5e8a4eb9de29d712df6bbc Mon Sep 17 00:00:00 2001 From: Ronin0000 <89286474+Ronin0000@users.noreply.github.com> Date: Wed, 13 Apr 2022 15:35:02 -0700 Subject: [PATCH 11/63] Delete bg_left_small.png --- apps/lcars/bg_left_small.png | Bin 772 -> 0 bytes 1 file changed, 0 insertions(+), 0 deletions(-) delete mode 100644 apps/lcars/bg_left_small.png diff --git a/apps/lcars/bg_left_small.png b/apps/lcars/bg_left_small.png deleted file mode 100644 index bfdb110d972360313d426b22ac78a7ee9a82b403..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 772 zcmV+f1N;1mP)1^@s674VWH00004b3#c}2nYxW zdOiP_0cN8)Um%OM2;H5eOAQ356ie zyf-x;e2riP67(p=WOt^~qbu;C5L(bnl(~OBh{2f5-U3V12Bnt29%?bS-Rsh`HQ{{U zwsSe3{qFsZoy%nmHc8U+s?uaU^KG-^3JFsy%-jvuHtuzO#z0iD5BJ8ajv6j5VV`Wlc`pTn2b^O;$;F9g)9sc?wK^&WH<{{J2_S1X7CVFyMi^m)5k^=! zV-$*J7>5MfkjlV9Ln>i}5k?qcgq1BeILIrs>ZoG@fc9vhdo*emFfr{90sy62oldK` z)o@7gp;3OAbH1T3%RUGb%}&mWiV5ayeFhd57&Gfjf&l=uwz8iLENs|suEoR(-WVPa z*BxkpeVBMr^Uqs8+RSF1n(0J@0VeFzJRgsz|0s_SgdkvS}^a%t&>R-KjV6awtzQI0Ue2qTOz z!u}IRp=gGMWceymuQi9y_e2w;xsfo!2qTOz!U!X5r(*g@L^_AkX?^_%z%WWHO8JDn z>+MB(AZOrw#p?B@G%>odAdE1=2qTOz!v0|4sC*5pSy+;snwYS#@DvLZMP+ijr)Q5U zW(@>ZL$Mn+Eb!QI@7Gv+driLD-)Sf;NlsBzRR33tkqx8QRCo6gN7K-3NiYC_uq0KB zqOw>LES;z<*PpQY;w8b-dDGu7=u@f74!i&HcClY%5W35joUtAN0000 Date: Wed, 13 Apr 2022 15:35:07 -0700 Subject: [PATCH 12/63] Delete bg_right.png --- apps/lcars/bg_right.png | Bin 791 -> 0 bytes 1 file changed, 0 insertions(+), 0 deletions(-) delete mode 100644 apps/lcars/bg_right.png diff --git a/apps/lcars/bg_right.png b/apps/lcars/bg_right.png deleted file mode 100644 index 6e23a5d6ebc0687268a27c368507b63ed435d2b1..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 791 zcmV+y1L*vTP)u=77?@_KC=}5|wjz5wZD`KUTKmqT@jSO- z-kr~UXW!lZ&hG38gr$UnEH1q+^tPY>YBwfF1q1-z;&TavrJU^?Epi-7rrce>jIfk% z@4qZ$}v#kR_%l%g*pk2wJWfKa{RR1o0sbG8+742wST<^BmN#~wcL6$zAz#zwJe zwO;f;mWML|KF(pKyFDn@PMq5hF&77_q&I<)#~8 z8Z8%)laqEF^M597uOAPETpL0t`Ei^l7Q~1VBSwrEvE5)XO;h$~j@VT2X39=C9tycC zDtpIOVTCIz&nzpOZff#WRQ9f`f{f|bsuR)ZcSkQi0RYp~>ioJs0qo+$B9j<1cYHN^ z-}~gUW0+}bo*KPx+pTq!PyOksV3`O)_;r29J$#f@X2b%wez;su&vbPqfc})@egR7% V)8R{}8ms^S002ovPDHLkV1jhMZOi}w From e67f2fe6c3a071f991897b1c3e3a40e1b2f3bee2 Mon Sep 17 00:00:00 2001 From: Ronin0000 <89286474+Ronin0000@users.noreply.github.com> Date: Wed, 13 Apr 2022 15:43:14 -0700 Subject: [PATCH 13/63] Add files via upload --- apps/lcars/bg_left.png | Bin 0 -> 789 bytes apps/lcars/bg_left_small.png | Bin 0 -> 760 bytes apps/lcars/bg_right.png | Bin 0 -> 771 bytes apps/lcars/bg_right_small.png | Bin 0 -> 742 bytes 4 files changed, 0 insertions(+), 0 deletions(-) create mode 100644 apps/lcars/bg_left.png create mode 100644 apps/lcars/bg_left_small.png create mode 100644 apps/lcars/bg_right.png create mode 100644 apps/lcars/bg_right_small.png diff --git a/apps/lcars/bg_left.png b/apps/lcars/bg_left.png new file mode 100644 index 0000000000000000000000000000000000000000..3bae5e458ab84a8aa5164c058f8e1afd52a53ef7 GIT binary patch literal 789 zcmeAS@N?(olHy`uVBq!ia0vp^(m=d{gAGXj;}@*}QY^(zo*^7SP{WbZ0pv3l2e~^j ztUD+35+s@K=Eakt5%+dZboOlr z0k`t-qSWcj#4|oif130E|Gh_cTl7@=Ilnl0ZtT?WT6^2;ZfLv7rY%LXwL&Im7$3?e zmYCd{IK%bWCW8*KE*U^J> zy4vH%diAI0_GuV<=Uoe!cu#HFCLg})*=LMnJ>nFr8LF5HfGRPW&*(@xeYp6yZPfH~lz1$t`b3e#?iF)Jt1dY+$l1 z(U@nrKi2D(w(=r%2Tkd%2eumky&%M&eSuT3`7=B78iNA^Zc3< zMk`)?yZn5w~jYrJq<*R}e_x7$K- zu`}P$~a79e4YP;~i&vpO)ED!s2FC|D#_U@lWwidt$E~tv~ lDxK8z^EdyN?c7d(*lg4KH%vAt^#vwf22WQ%mvv4FO#o=+UcdkV literal 0 HcmV?d00001 diff --git a/apps/lcars/bg_left_small.png b/apps/lcars/bg_left_small.png new file mode 100644 index 0000000000000000000000000000000000000000..8223a1898641255ebc932f777f5bc9871e74990b GIT binary patch literal 760 zcmeAS@N?(olHy`uVBq!ia0vp^(m*_egAGWEewd^Tq*#ibJVQ8upoSx*1ITAA4sv&5 zSa(k5B}g*e(btiIVPik{pF~z5pR>RtvY3H^?+6GpPSxfE8pl-Y>Eakt5%+d>boOlr z0k`t-qSWcj#4|oif130E|Gh_cTl7@=Ik&VX={qfFsn}Te`CkH_HGJq3 zu#$S~aYjj}xch~|^_dfd`xn(|{92p%ZKXiaA(y_Ww8%xRTxueTnyF&{qxjW|Y|@rp zpZMYaxvsg+fhp7Orkc)bnzAu=`4Bk<4XZJ|#l=s8M# zKYn)|U)21~iV2b|(;N|m#f{g>4=tMw@)~c5iH0e(`yDN2YfKf0fD!*&3{5f^Z;4s# z@>{+|a;JFL+i@StU3(aca~{>qN5)hn9V` zoct}%DpRES`KOn2N+0%h33JUmxuW~v;?%0$TO;j0|C+OgTiEsIuTPie-Ie^6yLRT% z*}WAXpP9N!yt%}W1SC{-< z{d40CjlA5NDZg#%|Nmug{rhoQqrq-jSJ9Z?Z#mYl%gKN8Yw^QvLF?u9rzib-XzN;$ z#m&9>KKK8p2KA5DP2FccTh!Cte19f?-?isD7Ph)e)I5)VdaQoyHoM|Kh8L+VdrbTH RtN^A?22WQ%mvv4FO#lJHRD%Ej literal 0 HcmV?d00001 diff --git a/apps/lcars/bg_right.png b/apps/lcars/bg_right.png new file mode 100644 index 0000000000000000000000000000000000000000..a87cf31d1f4e62fdc874d11f9f924dfcb81f9540 GIT binary patch literal 771 zcmeAS@N?(olHy`uVBq!ia0vp^(m=d{gAGXj;}@*}QY^(zo*^7SP{WbZ0pv3l2e~^j ztUD+35+s@K=B8H*3G@3oKm!k3(zvPRq|i5ox}wOw`wl&&Xia*{l{P5>zER zJEL{;nRyz|yt(>*eZ8T)vUIll&J(Y?Ihx9uPpy0ZYU6~isw)e;xIg_`*!gCn>(1J< zdo&h&Iey0FTgQR>^KKfiniFWT`j}Y+TVtvKg4k6pps*)RU`Kw-0V58bW*E_~>Ro^C z>N}Ug8Bk6o-KXvL-$%Y#@#T25M&fZ(LQRC^iGZ!K~ORFc|{M#%& z(aok`X5+sPe%IH`Y!{APdTK%Lp#_^%Vm-IjUecb{dH0{rtCj4PskU!RjWsq|{8OJ9 z@RDWm#Ll?hb7$UloIjT`bH&#e4rjOhW0#4naer8mv&i?s()-p@murkN&oa)tX|=QJ zEq9x<@X9m)&ir{bqxN5t-c8}YHkIx}F4kW1KSX&%Pq+N3+yD5iu*Q{Xb6Jh%*O)3- zZ+cl$o>sMQZ^7r|rDi4jVicEOdigt2c$#B^Bny14`r!y*WUU2)AHmhqlvP6x*H23Sc8^ohGxgJ+&Cc3jTDGF%>@>lj-U26-jx39 zRtvY3H^?+6GpPSxfE8po9F>Eakt5%+dhbp9;| z0k`zpgKkWh+BN?FzrQ7G>6R~wr-GHXPF=Od@j=XoySHPjXE!7}-}>7VVBKzUYa^@r zX6vR%8O6>k{kBH>o)vwayKdHgHl!&-`6nC{1+S< zIg7DlZZ6{{)eAB?Qr$t{(%a5?tvcR)=AC?-VCIp_8470cbr(#tpBr|p2}-?Snivo{ z$!yZT{3_QuH{PCanpib4{Muzl^Jb;)Mf)dlPVFO7iZq|y?Ep_tuw0McE!zW z{s$(ymOnY4rgn=h?$_eUl53xRJ}2{FX6~fb-|g~^3@4s?Q~7Lm^3RWxcc%2)&z+#d zCHz*S_JOX1)}xj?26sL`k4t^hda2Icm=OA%VW85K$@FFr}=;pj3}_#bo_O;@uu{T|D5aj7fH*S^Z2CrPZhsA zbLwl;kS{-;YICmtx1DkB&4S~HuTGt}N9yW|my-`q__Jr}gD+QHR_V%kg{?_0I-V?S zdcfO$=g+|ZKXWItDebQP-FHf7z3Rc6Gc9koy%4{>srfPI{N4ayT4eBa^>bP0l+XkK D%gRdO literal 0 HcmV?d00001 From 1a74b211637b566f50b7acd541ed5d896d28c026 Mon Sep 17 00:00:00 2001 From: Ronin0000 <89286474+Ronin0000@users.noreply.github.com> Date: Wed, 13 Apr 2022 15:44:21 -0700 Subject: [PATCH 14/63] Update lcars.settings.js --- apps/lcars/lcars.settings.js | 6 ------ 1 file changed, 6 deletions(-) diff --git a/apps/lcars/lcars.settings.js b/apps/lcars/lcars.settings.js index f714c3a7a..1873bb103 100644 --- a/apps/lcars/lcars.settings.js +++ b/apps/lcars/lcars.settings.js @@ -10,11 +10,8 @@ dataRow3: "Temp", speed: "kph", fullscreen: false, - themeColor1: "Orange", themeColor1BG: "#FF9900", - themeColor2: "Purple", themeColor2BG: "#FF00DC", - themeColor3: "Cyan", themeColor3BG: "#0094FF", }; let saved_settings = storage.readJSON(SETTINGS_FILE, 1) || settings; @@ -84,7 +81,6 @@ min: 0, max: 7, format: v => color_options[v], onchange: v => { - settings.themeColor1 = color_options[v]; settings.themeColor1BG = bg_code[v]; save(); }, @@ -94,7 +90,6 @@ min: 0, max: 7, format: v => color_options[v], onchange: v => { - settings.themeColor2 = color_options[v]; settings.themeColor2BG = bg_code[v]; save(); }, @@ -104,7 +99,6 @@ min: 0, max: 7, format: v => color_options[v], onchange: v => { - settings.themeColor3 = color_options[v]; settings.themeColor3BG = bg_code[v]; save(); }, From 8396d96e9a5591e48adf51e0f384c7e80d3d0cb2 Mon Sep 17 00:00:00 2001 From: Ronin0000 <89286474+Ronin0000@users.noreply.github.com> Date: Wed, 13 Apr 2022 15:56:25 -0700 Subject: [PATCH 15/63] Update lcars.settings.js --- apps/lcars/lcars.settings.js | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/apps/lcars/lcars.settings.js b/apps/lcars/lcars.settings.js index 1873bb103..830907fc5 100644 --- a/apps/lcars/lcars.settings.js +++ b/apps/lcars/lcars.settings.js @@ -77,7 +77,7 @@ }, }, 'Theme Color 1': { - value: 0 | color_options.indexOf(settings.themeColor1), + value: 0 | bg_code.indexOf(settings.themeColor1BG), min: 0, max: 7, format: v => color_options[v], onchange: v => { @@ -86,7 +86,7 @@ }, }, 'Theme Color 2': { - value: 0 | color_options.indexOf(settings.themeColor2), + value: 0 | bg_code.indexOf(settings.themeColor2BG), min: 0, max: 7, format: v => color_options[v], onchange: v => { @@ -95,7 +95,7 @@ }, }, 'Theme Color 3': { - value: 0 | color_options.indexOf(settings.themeColor3), + value: 0 | bg_code.indexOf(settings.themeColor3BG), min: 0, max: 7, format: v => color_options[v], onchange: v => { From 2192e9ff40565345249f4b0d7128e5cbb5dfaedf Mon Sep 17 00:00:00 2001 From: Ronin0000 <89286474+Ronin0000@users.noreply.github.com> Date: Wed, 13 Apr 2022 16:06:42 -0700 Subject: [PATCH 16/63] Update lcars.app.js --- apps/lcars/lcars.app.js | 91 +++++++++++++++++++++++++---------------- 1 file changed, 55 insertions(+), 36 deletions(-) diff --git a/apps/lcars/lcars.app.js b/apps/lcars/lcars.app.js index 2704ea09d..a3a3b452b 100644 --- a/apps/lcars/lcars.app.js +++ b/apps/lcars/lcars.app.js @@ -8,11 +8,8 @@ let settings = { dataRow3: "Battery", speed: "kph", fullscreen: false, - themeColor1: "Orange", themeColor1BG: "#FF9900", - themeColor2: "Purple", themeColor2BG: "#FF00DC", - themeColor3: "Cyan", themeColor3BG: "#0094FF", }; let saved_settings = storage.readJSON(SETTINGS_FILE, 1) || settings; @@ -23,9 +20,9 @@ for (const key in saved_settings) { /* * Colors to use */ -let cBlue = settings.themeColor3BG; -let cOrange = settings.themeColor1BG; -let cPurple = settings.themeColor2BG; +let color1 = settings.themeColor3BG; +let color2 = settings.themeColor1BG; +let color3 = settings.themeColor2BG; let cWhite = "#FFFFFF"; let cBlack = "#000000"; let cGrey = "#424242"; @@ -56,37 +53,59 @@ function convert24to16(input) return "0x"+RGB565.toString(16); } -/* - * Requirements and globals - */ +var color1C = convert24to16(color1); +var color2C = convert24to16(color2); +var color3C = convert24to16(color3); +/* +* Requirements and globals +*/ + +var colorPalette = new Uint16Array([ + 0x0000, // not used + color2C, // second + color3C, // third + 0x0000, // not used + color1C, // first + 0x0000, // not used + 0x0000, // not used + 0x0000, // not used + 0x0000, // not used + 0x0000, // not used + 0x0000, // not used + 0x0000, // not used + 0x0000, // not used + 0x0000, // not used + 0x0000, // not used + 0x0000 // not used +],0,1); var bgLeftFullscreen = { width : 27, height : 176, bpp : 3, transparent : 0, - buffer : require("heatshrink").decompress(atob("AAUM2XLlgCCwAJBBAuy4EAmQIF5cggAIGlmwgYIG2XIF42wF4ImGF4ImHJoQmGJoQdJhZNHNY47CgRNGBIJZHHgRiGBIRQ/KH5QCAFCh/eX5Q/KAwdCAGVbtu27YCCoAJBkuWrNlAQRGCiwRDAQPQBIMJCIYCBsAJBgomEtu0WoQmEy1YBIMBHYttIwQ7FyxQ/KHFlFAQ7F2weCHYplKChRTCCg5TCHw5TMAD0GzVp0wCCBBGaBIMaBAtpwECBA2mwEJBAugDgMmCIwJBF5EABAtoeQQvGCYQdPJoI7LMQzTCLJKAGzAJBO4xQ/KGQA8UP7y/KH5QnAHih/eX5Q/GQ4JCGRJlKCgxTDBAwgCCg5TCHwxTCNA4A==")), -// pallet: + buffer : require("heatshrink").decompress((atob("/4AB+VJkmSAQV///+BAtJn//5IIFkmf/4IGyVP/gIGpMnF41PHIImGF4ImHJoQmGJoIdK8hNHNY47C/JNGBIJZGyYJBQA5GCKH5Q/KAQAoUP7y/KH5QGDoQAy0hGF34JB6RGFr4JB9JkFl4JB+gdFy4JB/QdFpYJB/odFkqrCS4xGCWoyDCKH5Q1GShlJChQLCCg5TCHw5TMAD35FAoIIkgJB8hGGv/8Mg8/+QIFp4cB5IRGBIIvI/4IFybyCF4wTCDp5NBHZZiGz4JBLJKAGk4JBO4xQ/KGQA8UP7y/KH5QnAHih/eX5Q/GQ4JCGRJlKCgxTDBAwgCCg5TCHwxTCNA4"))), + palette: colorPalette }; -var gray = convert24to16(cBlue); -var palette1 = new Uint16Array([0x0000,gray,0x0000,gray,0x0000,0x0000,0x0000,0x0000,0x0000,0x0000,0x0000,0x0000,0x0000,0x0000,0x0000,0x0000],0,1); var bgLeftNotFullscreen = { width : 27, height : 152, bpp : 3, transparent : 0, - buffer : require("heatshrink").decompress(atob("AAUM2XLlgCCwAJBBAuy4EAmQIF5cggAIGlmwgYIG2XIF42wF4ImGF4ImHJoQmGJoQdJhZNHNY47CgRNGBIJZHHgRiGBIRQ/KH5QCAGVbtu27YCCoAJBkuWrNlAQRkCiwRDAQPQBIMJCIYCBsAJBgomEtu0WoQmEy1YBIMBHYttIwQ7FyxQ/KHFlFAQ7F2weCHYplKChRTCCg5TCHw5TMAD0GzVp0wCCBBGaBIMaBAtpwECBA2mwEJBAugDgMmCIwJBF5EABAtoeQQvGCYQdPJoI7LMQzTCLJKAGzAJBO4xQ/KGQA8UP7y/KH5QnAHih/eX5Q/GQ4JCGRJlKCgxTDBAwgCCg5TCHwxTCNA4A=")), - palette: palette1 + buffer : require("heatshrink").decompress((atob("/4AB+VJkmSAQV///+BAtJn//5IIFkmf/4IGyVP/gIGpMnF41PHIImGF4ImHJoQmGJoIdK8hNHNY47C/JNGBIJZGyYJBQA5GCKH5Q/KAQAy0hGF34JB6RGFr4JB9JkFl4JB+gdFy4JB/QdFpYJB/odFkqrCS4xGCWoyhCKH5Q1GShlJChQLCCg5TCHw5TMAD35FAoIIkgJB8hGGv/8Mg8/+QIFp4cB5IRGBIIvI/4IFybyCF4wTCDp5NBHZZiGz4JBLJKAGk4JBO4xQ/KGQA8UP7y/KH5QnAHih/eX5Q/GQ4JCGRJlKCgxTDBAwgCCg5TCHwxTCNA4A=="))), + palette: colorPalette }; var bgRightFullscreen = { width : 27, height : 176, bpp : 3, transparent : 0, - buffer : require("heatshrink").decompress(atob("lmy5YCDBIUyBAmy5AJBhYUG2EAhgIFAQMAgQIGCgQABCg4ABEAwUNFI2AKZHAKZEgGRZTGOIUDQxJxGKH5Q/agwAnUP7y/KH4yGeVYAJrdt23bAQVABIMly1ZsoCCMgUWCIYCB6AJBhIRDAQNgBIMFEwlt2i1CEwmWrAJBgI7FtpGCHYuWKH5QxEwpQDlo7F0A7IqBZBEwo7BCIwCBJo53CJoxiCJpIAdgOmzVpAQR/CgAIEAQJ2CBAoCBBIMmCg1oD4QLGFQUCCjQ+CKYw+CKY4JCKYwoCGRMaGREJDoroCgwdFzBlLKH5QvAHih/eX5Q/KE4A8UP7y/KH5QGDpg7HJoxZCCIx3CJowmCF4yACJox/CgAA=")) + buffer : require("heatshrink").decompress((atob("yVJkgCCyf/AAPJBAYCBk4JB8gUFyVP//yBAoCB//5BAwUCAAIUHAAIgGChopGv5TIn5TIz4yLKYxxC/iGI/xxGKH5Q/agwAnUP7y/KH4yGeVYAJ0hGF34JB6RGFr4JB9JkFl4JB+gdFy4JB/QdFpYJB/odFkp4CS4xGCWoyhCKH5QuDoxQCDpI7GDoJZGHYIRGLIQvGO4QvGMQRNJADv+GIqTC/5PGz4JBJ41JBIPJCg2TD4QLGn4JB/gUaHwRTGHwRTHBIRTGNAQyJ8gyI+QdFp4JB/IdFk5lLKH5QvAHih/eX5Q/KE4A8UP7y/KH5QGDpg7HJoxZCCIx3CJowmCF4yACJoyJC/4A=="))), + palette: colorPalette }; var bgRightNotFullscreen = { width : 27, height : 152, bpp : 3, transparent : 0, - buffer : require("heatshrink").decompress(atob("lmy5YCDBIUyBAmy5AJBhYUG2EAhgIFAQMAgQIGCgQABCg4ABEAwUNFI2AKZHAKZEgGRZTGOIUDQxJxGKH5Q/agwAxrdt23bAQVABIMly1ZsoCCMgUWCIYCB6AJBhIRDAQNgBIMFEwlt2i1CEwmWrAJBgI7FtpGCHYuWKH5QxEwpQDlo7F0A7IqBZBEwo7BCIwCBJo53CJoxiCJpIAdgOmzVpAQR/CgAIEAQJ2CBAoCBBIMmCg1oD4QLGFQUCCjQ+CKYw+CKY4JCKYwoCGRMaGREJDoroCgwdFzBlLKH5QvAHih/eX5Q/KE4A8UP7y/KH5QGDpg7HJoxZCCIx3CJowmCF4yACJox/CgA=")) + buffer : require("heatshrink").decompress((atob("yVJkgCCyf/AAPJBAYCBk4JB8gUFyVP//yBAoCB//5BAwUCAAIUHAAIgGChopGv5TIn5TIz4yLKYxxC/iGI/xxGKH5Q/agwAx0hGF34JB6RGFr4JB9JkFl4JB+gdFy4JB/QdFpYJB/odFkqrCS4xGCWoyhCKH5QuDoxQCDpI7GDoJZGHYIRGLIQvGO4QvGMQRNJADv+GIqTC/5PGz4JBJ41JBIPJCg2TD4QLGn4JB/gUaHwRTGHwRTHBIRTGNAQyJ8gyI+QdFp4JB/IdFk5lLKH5QvAHih/eX5Q/KE4A8UP7y/KH5QGDpg7HJoxZCCIx3CJowmCF4yACJoyJC/4A="))), + palette: colorPalette }; var bgLeft = settings.fullscreen ? bgLeftFullscreen : bgLeftNotFullscreen; @@ -267,7 +286,7 @@ function drawInfo(){ } g.setFontAntonioMedium(); - g.setColor(cOrange); + g.setColor(color2); g.clearRect(120, 10, g.getWidth(), 75); g.drawString("LCARS", 128, 13); @@ -277,7 +296,7 @@ function drawInfo(){ g.drawString("NOCON", 128, 33); } if(Bangle.isLocked()){ - g.setColor(cPurple); + g.setColor(color3); g.drawString("LOCK", 128, 53); } } @@ -308,7 +327,7 @@ function drawState(){ g.drawString("STATUS", 23+26, 108); } else { // Alarm within symbol - g.setColor(cOrange); + g.setColor(color2); g.drawString("ALARM", 23+26, 108); g.setColor(cWhite); g.setFontAntonioLarge(); @@ -323,19 +342,19 @@ function drawPosition0(){ // Draw background image var offset = settings.fullscreen ? 0 : 24; g.drawImage(bgLeft, 0, offset); - drawHorizontalBgLine(cBlue, 25, 120, offset, 4); - drawHorizontalBgLine(cBlue, 130, 176, offset, 4); - drawHorizontalBgLine(cPurple, 20, 70, 80, 4); - drawHorizontalBgLine(cPurple, 80, 176, 80, 4); - drawHorizontalBgLine(cOrange, 35, 110, 87, 4); - drawHorizontalBgLine(cOrange, 120, 176, 87, 4); + drawHorizontalBgLine(color1, 25, 120, offset, 4); + drawHorizontalBgLine(color1, 130, 176, offset, 4); + drawHorizontalBgLine(color3, 20, 70, 80, 4); + drawHorizontalBgLine(color3, 80, 176, 80, 4); + drawHorizontalBgLine(color2, 35, 110, 87, 4); + drawHorizontalBgLine(color2, 120, 176, 87, 4); // The last line is a battery indicator too var bat = E.getBattery() / 100.0; var batStart = 19; var batWidth = 172 - batStart; var batX2 = parseInt(batWidth * bat + batStart); - drawHorizontalBgLine(cOrange, batStart, batX2, 171, 5); + drawHorizontalBgLine(color2, batStart, batX2, 171, 5); drawHorizontalBgLine(cGrey, batX2, 172, 171, 5); for(var i=0; i+batStart<=172; i+=parseInt(batWidth/4)){ drawHorizontalBgLine(cBlack, batStart+i, batStart+i+3, 168, 8) @@ -374,9 +393,9 @@ function drawPosition0(){ // Draw data g.setFontAlign(-1, -1, 0); g.setColor(cWhite); - drawData(settings.dataRow1, 97, cOrange); - drawData(settings.dataRow2, 122, cPurple); - drawData(settings.dataRow3, 147, cBlue); + drawData(settings.dataRow1, 97, color2); + drawData(settings.dataRow2, 122, color3); + drawData(settings.dataRow3, 147, color1); // Draw state drawState(); @@ -387,13 +406,13 @@ function drawPosition1(){ var offset = settings.fullscreen ? 0 : 24; g.drawImage(bgRight, 149, offset); if(settings.fullscreen){ - drawHorizontalBgLine(cBlue, 0, 140, offset, 4); + drawHorizontalBgLine(color1, 0, 140, offset, 4); } - drawHorizontalBgLine(cPurple, 0, 80, 80, 4); - drawHorizontalBgLine(cPurple, 90, 150, 80, 4); - drawHorizontalBgLine(cOrange, 0, 50, 87, 4); - drawHorizontalBgLine(cOrange, 60, 140, 87, 4); - drawHorizontalBgLine(cOrange, 0, 150, 171, 5); + drawHorizontalBgLine(color3, 0, 80, 80, 4); + drawHorizontalBgLine(color3, 90, 150, 80, 4); + drawHorizontalBgLine(color2, 0, 50, 87, 4); + drawHorizontalBgLine(color2, 60, 140, 87, 4); + drawHorizontalBgLine(color2, 0, 150, 171, 5); // Draw steps bars g.setColor(cWhite); From e272e718419ee5a60918edcfab0303759c2d1873 Mon Sep 17 00:00:00 2001 From: Ronin0000 <89286474+Ronin0000@users.noreply.github.com> Date: Wed, 13 Apr 2022 16:12:17 -0700 Subject: [PATCH 17/63] Update lcars.app.js --- apps/lcars/lcars.app.js | 80 ++++++++++++++++------------------------- 1 file changed, 31 insertions(+), 49 deletions(-) diff --git a/apps/lcars/lcars.app.js b/apps/lcars/lcars.app.js index a3a3b452b..c1b17d0d1 100644 --- a/apps/lcars/lcars.app.js +++ b/apps/lcars/lcars.app.js @@ -612,39 +612,44 @@ function getCurrentTimeInMinutes(){ return Math.floor(Date.now() / (1000*60)); } -function isAlarmEnabled(){ - return settings.alarm >= 0; -} - function getAlarmMinutes(){ - var currentTime = getCurrentTimeInMinutes(); - return settings.alarm - currentTime; + if(!isAlarmEnabled()){ + return -1; + } + + var alarm = require('sched'); + var alarmObj = alarm.getAlarm(TIMER_IDX); + return Math.round(alarm.getTimeToAlarm(alarmObj)/(60*1000)); } -function handleAlarm(){ - if(!isAlarmEnabled()){ - return; +function increaseAlarm(){ + try{ + var minutes = isAlarmEnabled() ? getAlarmMinutes() : 0; + var alarm = require('sched') + alarm.setAlarm(TIMER_IDX, { + timer : (minutes+5)*60*1000, + }); + alarm.reload(); + } catch(ex){ } +} + +function decreaseAlarm(){ + try{ + var minutes = getAlarmMinutes(); + minutes -= 5; + + var alarm = require('sched') + alarm.setAlarm(TIMER_IDX, undefined); } - if(getAlarmMinutes() > 0){ - return; + if(minutes > 0){ + alarm.setAlarm(TIMER_IDX, { + timer : minutes*60*1000, + }); } - // Alarm - var t = 300; - Bangle.buzz(t, 1) - .then(() => new Promise(resolve => setTimeout(resolve, t))) - .then(() => Bangle.buzz(t, 1)) - .then(() => new Promise(resolve => setTimeout(resolve, t))) - .then(() => Bangle.buzz(t, 1)) - .then(() => new Promise(resolve => setTimeout(resolve, t))) - .then(() => Bangle.buzz(t, 1)) - .then(() => new Promise(resolve => setTimeout(resolve, 5E3))) - .then(() => { - // Update alarm state to disabled - settings.alarm = -1; - storage.writeJSON(SETTINGS_FILE, settings); - }); + alarm.reload(); + } catch(ex){ } } @@ -671,28 +676,6 @@ Bangle.on('charging',function(charging) { drawState(); }); - -function increaseAlarm(){ - if(isAlarmEnabled() && getAlarmMinutes() < 95){ - settings.alarm += 5; - } else { - settings.alarm = getCurrentTimeInMinutes() + 5; - } - - storage.writeJSON(SETTINGS_FILE, settings); -} - - -function decreaseAlarm(){ - if(isAlarmEnabled() && (settings.alarm-5 > getCurrentTimeInMinutes())){ - settings.alarm -= 5; - } else { - settings.alarm = -1; - } - - storage.writeJSON(SETTINGS_FILE, settings); -} - function feedback(){ Bangle.buzz(40, 0.3); } @@ -753,4 +736,3 @@ Bangle.loadWidgets(); // Clear the screen once, at startup and draw clock g.setTheme({bg:"#000",fg:"#fff",dark:true}).clear(); draw(); -console.log(bgLeftNotFullscreen); From 69496ba1a5c5347a25c3ac339634fd6f3b63fd27 Mon Sep 17 00:00:00 2001 From: Ronin0000 <89286474+Ronin0000@users.noreply.github.com> Date: Wed, 13 Apr 2022 16:15:49 -0700 Subject: [PATCH 18/63] Update lcars.app.js --- apps/lcars/lcars.app.js | 36 ++++++++++++++++++++++++------------ 1 file changed, 24 insertions(+), 12 deletions(-) diff --git a/apps/lcars/lcars.app.js b/apps/lcars/lcars.app.js index c1b17d0d1..63b10a922 100644 --- a/apps/lcars/lcars.app.js +++ b/apps/lcars/lcars.app.js @@ -171,11 +171,16 @@ Graphics.prototype.setFontAntonioLarge = function(scale) { */ var drawTimeout; function queueDraw() { + + // Faster updates during alarm to ensure that it is + // shown correctly... + var timeout = isAlarmEnabled() ? 10000 : 60000; + if (drawTimeout) clearTimeout(drawTimeout); drawTimeout = setTimeout(function() { drawTimeout = undefined; draw(); - }, 60000 - (Date.now() % 60000)); + }, timeout - (Date.now() % timeout)); } /** @@ -527,9 +532,6 @@ function draw(){ // Queue draw first to ensure that its called in one minute again. queueDraw(); - // First handle alarm to show this correctly afterwards - handleAlarm(); - // Next draw the watch face g.reset(); g.clearRect(0, 0, g.getWidth(), g.getHeight()); @@ -608,8 +610,18 @@ function getWeather(){ /* * Handle alarm */ -function getCurrentTimeInMinutes(){ - return Math.floor(Date.now() / (1000*60)); +function isAlarmEnabled(){ + try{ + var alarm = require('sched'); + var alarmObj = alarm.getAlarm(TIMER_IDX); + if(alarmObj===undefined || !alarmObj.on){ + return false; + } + + return true; + + } catch(ex){ } + return false; } function getAlarmMinutes(){ @@ -640,13 +652,13 @@ function decreaseAlarm(){ var alarm = require('sched') alarm.setAlarm(TIMER_IDX, undefined); - } + - if(minutes > 0){ - alarm.setAlarm(TIMER_IDX, { - timer : minutes*60*1000, - }); - } + if(minutes > 0){ + alarm.setAlarm(TIMER_IDX, { + timer : minutes*60*1000, + }); + } alarm.reload(); } catch(ex){ } From 3e7e1c19e548cb54a1bfc4aab27f29bd93b8d2ab Mon Sep 17 00:00:00 2001 From: Ronin0000 <89286474+Ronin0000@users.noreply.github.com> Date: Wed, 13 Apr 2022 16:17:46 -0700 Subject: [PATCH 19/63] Update lcars.app.js --- apps/lcars/lcars.app.js | 5 ++--- 1 file changed, 2 insertions(+), 3 deletions(-) diff --git a/apps/lcars/lcars.app.js b/apps/lcars/lcars.app.js index 63b10a922..3210d6832 100644 --- a/apps/lcars/lcars.app.js +++ b/apps/lcars/lcars.app.js @@ -652,13 +652,12 @@ function decreaseAlarm(){ var alarm = require('sched') alarm.setAlarm(TIMER_IDX, undefined); - - if(minutes > 0){ + if(minutes > 0){ alarm.setAlarm(TIMER_IDX, { timer : minutes*60*1000, }); - } + } alarm.reload(); } catch(ex){ } From 6c0f16a45f7b72bc643ceb12833c09ad00e8d624 Mon Sep 17 00:00:00 2001 From: Eskild Hustvedt Date: Tue, 19 Apr 2022 14:09:52 +0200 Subject: [PATCH 20/63] Bumped to 0.32 for quiet mode auto-open setting --- apps/messages/ChangeLog | 1 + apps/messages/metadata.json | 2 +- 2 files changed, 2 insertions(+), 1 deletion(-) diff --git a/apps/messages/ChangeLog b/apps/messages/ChangeLog index 3e676c21e..75b171579 100644 --- a/apps/messages/ChangeLog +++ b/apps/messages/ChangeLog @@ -44,3 +44,4 @@ 0.29: Fix message list overwrites on Bangle.js 1 (fix #1642) 0.30: Add new Icons (Youtube, Twitch, MS TODO, Teams, Snapchat, Signal, Post & DHL, Nina, Lieferando, Kalender, Discord, Corona Warn, Bibel) 0.31: Option to disable icon flashing +0.32: Added an option to allow quiet mode to override message auto-open diff --git a/apps/messages/metadata.json b/apps/messages/metadata.json index 5c1e67702..7886a7b30 100644 --- a/apps/messages/metadata.json +++ b/apps/messages/metadata.json @@ -1,7 +1,7 @@ { "id": "messages", "name": "Messages", - "version": "0.31", + "version": "0.32", "description": "App to display notifications from iOS and Gadgetbridge/Android", "icon": "app.png", "type": "app", From c4529d5c0a527c10b63c1403aefb6cacb29ad7a1 Mon Sep 17 00:00:00 2001 From: sir-indy <53864146+sir-indy@users.noreply.github.com> Date: Tue, 19 Apr 2022 13:22:53 +0100 Subject: [PATCH 21/63] Step counter widget (#2) * Create README.md * Add files via upload * Update metadata.json --- apps/widstep/ChangeLog | 1 + apps/widstep/README.md | 4 +++ apps/widstep/icons8-winter-boots-48.png | Bin 0 -> 1359 bytes apps/widstep/metadata.json | 15 ++++++++++ apps/widstep/widstep-dark.png | Bin 0 -> 3910 bytes apps/widstep/widstep-light.png | Bin 0 -> 3834 bytes apps/widstep/widstep.wid.js | 36 ++++++++++++++++++++++++ 7 files changed, 56 insertions(+) create mode 100644 apps/widstep/ChangeLog create mode 100644 apps/widstep/README.md create mode 100644 apps/widstep/icons8-winter-boots-48.png create mode 100644 apps/widstep/metadata.json create mode 100644 apps/widstep/widstep-dark.png create mode 100644 apps/widstep/widstep-light.png create mode 100644 apps/widstep/widstep.wid.js diff --git a/apps/widstep/ChangeLog b/apps/widstep/ChangeLog new file mode 100644 index 000000000..55cda0f21 --- /dev/null +++ b/apps/widstep/ChangeLog @@ -0,0 +1 @@ +0.01: New widget diff --git a/apps/widstep/README.md b/apps/widstep/README.md new file mode 100644 index 000000000..3441755e3 --- /dev/null +++ b/apps/widstep/README.md @@ -0,0 +1,4 @@ +# Step counter widget +This is my step counter widget. There are many like it, but this one is mine. +Designed to be as narrow as possible, but still easy to read, by sacrificing accuracy and only showing to the nearest 100 steps (0.1k). +Shows a subtle fill colour in the background for progress to the goal. The goal is picked up from the health tracker settings. diff --git a/apps/widstep/icons8-winter-boots-48.png b/apps/widstep/icons8-winter-boots-48.png new file mode 100644 index 0000000000000000000000000000000000000000..7dceceef03b8ef0f6bcb33d7665a6ce948171d71 GIT binary patch literal 1359 zcmV-V1+e;wP)1ra;L`?Keltif}y2K#G7%=h0Ck1>WXi98Sc_PG6K*gBGr0Vv<%@RxN7I!Xj$}mxZ>XEt}fh7U}^2D5vkZrIr}8R&O5D02n{G%pt^dwR6GLNdmlPv90|U z>jB88PzK~vXn90V-*Eu14_&oz}1S1N^4E^AMBC(FeE z1Agm0bFMiT4IaD|$e5-8#jdV7$-e#s!XpLulnLhXf0!@S34W5ebdaNB?L^*xZo|XL}h)0#~^IvL$d6@d4TMJw96hE1&>)BkY6F#^f&e3#9CJ9tHY;r{zzrbO z-Y&*76l@Am?C5mj($HE&r2@od857q>PaitfH=To@rf>`E&7C`4f&1j3^Rs3@Xg-3DC{L>nXQB}+V?hnqqlA9(enlG5@605EfB5|g*CXJw?K zt{xtL8T5F3eBZmhYY9P4yZd6eD=>BQhC@>o_$sQAOeQiGZwgSfx4ZD|Ph~I|gDk~X ze|GqtA5Zp*^#F!nJb37lY#m>K8-M|}ZRXA-X6{S^0NlP(_^YaM``Q?k*;q>PU0osu z1_NLWARusi{S?5)T%BHwX#hRDJA44vFK!b=0XDk>H4RO;86JkJ$SDmF0uV5G-4aH^ zF{sikR9S|ut4dF>^GQdcdOmdGf|_jrrZv#Br}JqLe6`e>@|t>hO3M(NiC|)Uge%?{ zpxC`|xSKENWl#WICcvmc$T$o(P6Rr1=IW>!bqx6Y;GQR5<_+R~6IXF3 zQUQbz_^PV2bucXmAs>di+lx&7;LNSy3CHe6plcc&&O#IxS@{RveU!wB^BJ>FUI3<1 z0{~+TQxmtKt11!+J!|jMfiOH}*2miioT-GPk!eIDD{{#E2MjPhit|>$o{o4;pc&O` z0vS7%E{=l2Ki0KvGkw>Yu0TikUXsxDy8zSmxTeHaIiabls!Eck%to0a#{^YYoOY*k zjUd`A{V<}0Y9-|r(b~oqzqh=STZ=ryRJ7SV03h1zC@A8V1gciAfg(vzWyw&a*{D1l zm6cd58CMkOdR$0on$s{02VZ^)9)aCWLJibzUvCn6xR0snI z1K7&I2C@ktBLvZgBDV)cZVv_EnZLMG02Iz&0LWQ@5n!%hl>+H;0C1|S_LW5BPt8Qq z3&21t6%A?_^a`(SdvNc)o&Efmr#5rPFL{o@_ACH+p~V4Q>*{)C;h^;i&oxdFvy1l} zdv5O!kL`KkyT!fBwJj#q_(jhW0e%ezgIX{c)Bw7*qx<;=p3`~q*g^QL$AG#*&GS&`M%A5ur4cA`PR|T9N!|EJ^xL(!|!OeX3%Naxo)q zRflV>QmS^YTBhirrQ4{T8tb@9tC;BRnfuy{`{JJCIp^7b&-eMA&w0*szE?@aQ!pu2 zDF_4tbFe443VStSRhAGJwr_Io5<*4FUN!jCa=*^R~~ zOZ}0L`frQLzUD=%!)DsMH&#OIFKwC6h7<1+^VU?h7eyNR@)SZ7|2yB!`d3^lJT4Qh z?Soa>ejP*iz1aN0;L)8zWSh7B#`Z*Lo9mQU`b?D4v74D6f^4@7gDgiTK5o^P7OrD| z#lD@H_vp&!j6Qu6Gk#=s*z@?bNSU^5ta>l=*x~}sCHR)n+->(N^ak_TJD~5VNO(Xb__~<)dglAAH+9ctFoO_t}WLs^>I)&PLq>U zG9$1m)YP z=iL;*pUem?dNDX)1cts$8=!l0-_%5RY8-UMfiL^xs1}#UQy8WFxV6inI|7pr0esDZ zMZ#u9qDvL#FxxT3udhYf3_5X1rS|JF(7llq5|vY*`^=x3V3_;VkvITIOV>D;CRx6Y zrY!!;Tja)0mRVCzrsMBR{^dS%ms?*yY1ldxf<-?+gJ>FDj`b3I!Q};Inx?VawV#awP^(|7p(7QVok1jf&UW)FGLCb<0Yj?i=-1y?kJqmw&$|x+b~I#wW~Ne%yGz;Q+?IK(d$+8`L}U5H*4GAnQxC2r7O+K zBE=?ur1Qn8P`LSezl_{@v$bO<2R0T@49rXUogj#*TKj>{?ScPntXil>8j9RR7F?N? z2v(>(T^Pb8040>+=GKiqs=JP&1BVc*sJNVcJ&F%|G;jI5(?LMBpX^o%TN<>p@>oLk zt<3!#rSa+^j)Lo;P6mpkWmje)xsrB`Y13QdV+74P(2^i` z*h06?_-@grZcK2}^96YG@L)-o5;Nh)Apmt$@4Udq^o-n>DM*pZGM}E&fy|9J`hkId zrqroA2t<-Y6aG%;oSn=mj4(8r$_N0^yfCKl_kutytawZ^B?Mr@1ArhJ9gkS5Z$`jr zR6N4N#97~&c@nrlvyT9QZzG6ql!y=tmWr^ll(OKN3kAXeHW|(f3#GHnd3eMpU31}h zcNv3#e+prT;1TDXN$`^l5P%z_jnVojTORF_A;MA$ZUIsQ&0Pt0pCyDdJmLbI%{0eg zxLhupYlLQiK^Oxp7K_n0#26Z)gb^rKIGs)Aq3A5FU5Wo_5C9ehq%qkv1|7buNe*Ce z*mwj&xDWpbC&zTEBVE!hto6i5f>|e4c#{0PTaqWq~o`UyZ*FLU25!h4k{_Fbx z!X@=zF9pzr28t_mN|avgkkDmGGVMKC5QqYMw~CAeYVw4OFB}NgZuVDy&$L!bfJ@kh z@7&)(tsVpv@EJX-?d?aWpa>g+n_mW?ZkMeL-8Q_&4v^6yRoi^zZM(b7$PXs8RLYD} zIJZn4_uqx?A_#yYPzIFA}@64 ReY9mz(M8MLB$`1?#%;?r29@PIV@!j&G&7npqax&*+O<*} zlY27d66KeTN-`^~WSV4AN>&#P5v^Lk(XX?=zy0z1<9Ckdoag>|-p}W}&U2pgPWSb8 z*U>W70suhA(}U=*?9G(bSW`pUzRE8+4ghMd!hm3&Kg0*w99ASfh6?iH*i?`zphp6L zp#Ms4bk%_Es+7g(b)m;SGFBr~g(`!Dyr<^f1D-hsgv2(}lZ=qnuj4lcz7IPlp8gtz zkd$3YjjhX&%*t_7db6?HWr_FarzD<-KQ)eh@UG6=^{)5h;MYPQw=BaC^1ovn<|GXJ z>scA;+Ce|85;2o*Y!zRG2l0eMM1eN!=`q=6tH6mp(=uAobV&P7%V{TMW_-iDx$!Mx z`pzI6?H+F7+RGS?g11e6tEL2js~ohWw#OOR7`O*IEbJ9tf}=yWTx)!tT(8<)aJF=P zRK3Nk2S+DzHg`tdd~%2;w({AZ#zi~ShP5>Njn(YV+oZB?v+T4)Dm82=Zs?@d-fqc! zkORx{yL0-f|502I?y+53RahuLL2|oFS`yw?7Q5IZ33bA=NPij5Bj2rlOx;>oeyTH3 zClX%0^~BIbS+kk<`hOkI&Jc-o-p`5weTb2Q-3a=gB(_)J>(&yag%1-;Gh3|bTHh0=2^$}M z>DHHTKM9EfP3kg7I=9Wt;73Ww?htH=_sPNdNG*L5nY9pU`-k2gX>v+{yU^JuW(!_u z)kY$jy4><~T~l6o1w)UL(z%fj4c}~NtX3P&z_iXE=py}|E2HR=-hP^Cx(=C(&b*e6 ztErpEi8=<|bJVYC#Fo6I_@su~UWc-Q^VxAVHg61!yE>@)-Ni_`@o!~^>t2J3=pkrg zB1pW=XnImjMaRtISzc&%*5IFJ&21$2t15X25atC9pALXC%6zIV4|T%bXdB-b^;H

Rv!x&QQG@HEMGwvCn_>@}?r)gpm_T$yVTlVa4bpW=i?ZwSr+AZ@FFmCJVcp>dk2f zpNCRfKB-+yGdG%)e@tVT_MZ_wMk-Fb?QgHPdDV^Gqg5M}0}K5Mh8f2)kja_={MFg^ z(qF`t{XVVq^k-*9?I!sEcMw;D{FTs)I!g3QF~1@@a6*J_;low7I6GH`} zQ@!9DVv;mAhoxQX0K2CLN1sD!ij zQ33{A`QZS7gOh*_QKG3lkW8h~nU09bUvD8mdW0h)XuB82i|s-^NcRwOsC$Lp0Tf|0 z1s8#E+NtFrz$*n9R2~Eh7%@yPUf_uMtczEUmzL28@N)<++7S`#R)`*>2paUl&67NrR`y!#7IU)}7cx*fx&FAw`{B0-}hla-Da5yx^8f|TjR7N1V zaZDa0Kr*@JOA`OlAX2#$4xP=TvzXwLCPZe%@*EKe(4P-0PvJcvt_z37c0{;AF Date: Tue, 19 Apr 2022 15:10:51 +0100 Subject: [PATCH 22/63] Update metadata.json --- apps/widstep/metadata.json | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/apps/widstep/metadata.json b/apps/widstep/metadata.json index 09e0efac9..ea108e0f1 100644 --- a/apps/widstep/metadata.json +++ b/apps/widstep/metadata.json @@ -3,12 +3,14 @@ "name": "Step counter widget", "version": "0.01", "description": "Step counter widget, narrow but clearly readable", + "readme": "README.md", "icon": "icons8-winter-boots-48.png", + "screenshots": [{"url":"widstep-light.png"},{"url":"widstep-dark.png"}], "type": "widget", "tags": "widget,health", "supports": ["BANGLEJS","BANGLEJS2"], "dependencies" : {"health":"app"}, - "allow_emulator":true, + "allow_emulator":false, "storage": [ {"name":"widstep.wid.js","url":"widstep.wid.js"} ] From 207dfadc58deb18c16061bd14a41874b53e54107 Mon Sep 17 00:00:00 2001 From: sir-indy <53864146+sir-indy@users.noreply.github.com> Date: Tue, 19 Apr 2022 15:14:38 +0100 Subject: [PATCH 23/63] Update README.md --- apps/widstep/README.md | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/apps/widstep/README.md b/apps/widstep/README.md index 3441755e3..498f2ebd9 100644 --- a/apps/widstep/README.md +++ b/apps/widstep/README.md @@ -2,3 +2,7 @@ This is my step counter widget. There are many like it, but this one is mine. Designed to be as narrow as possible, but still easy to read, by sacrificing accuracy and only showing to the nearest 100 steps (0.1k). Shows a subtle fill colour in the background for progress to the goal. The goal is picked up from the health tracker settings. + + +![](widstep-light.png) +![](widstep-dark.png) From beb81356bc1598499fe6cc9ffc94ef321be4d9cb Mon Sep 17 00:00:00 2001 From: sir-indy <53864146+sir-indy@users.noreply.github.com> Date: Tue, 19 Apr 2022 15:24:32 +0100 Subject: [PATCH 24/63] Update app.js --- apps/health/app.js | 5 +++++ 1 file changed, 5 insertions(+) diff --git a/apps/health/app.js b/apps/health/app.js index 64640603e..415edb7c5 100644 --- a/apps/health/app.js +++ b/apps/health/app.js @@ -31,6 +31,11 @@ function menuSettings() { min : 0, max : 3, format : v=>["Off","3 mins","10 mins","Always"][v], onchange : v => { s.hrm=v;setSettings(s); } + }, + "Daily Step Goal":{ + value : 0|s.stepGoal, + min : 0, max : 20000, step : 100, + onchange : v => { s.stepGoal=v;setSettings(s); } } }); } From 08045075cc7c61c04a2b799f16a4fa5e074cadd1 Mon Sep 17 00:00:00 2001 From: sir-indy <53864146+sir-indy@users.noreply.github.com> Date: Tue, 19 Apr 2022 15:25:08 +0100 Subject: [PATCH 25/63] Update metadata.json --- apps/health/metadata.json | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/apps/health/metadata.json b/apps/health/metadata.json index 8bb986c57..5d096dc07 100644 --- a/apps/health/metadata.json +++ b/apps/health/metadata.json @@ -1,7 +1,7 @@ { "id": "health", "name": "Health Tracking", - "version": "0.11", + "version": "0.12", "description": "Logs health data and provides an app to view it", "icon": "app.png", "tags": "tool,system,health", From f318fb005d1af5617849a434e8a7221cd4dab9ba Mon Sep 17 00:00:00 2001 From: sir-indy <53864146+sir-indy@users.noreply.github.com> Date: Tue, 19 Apr 2022 15:25:35 +0100 Subject: [PATCH 26/63] Update ChangeLog --- apps/health/ChangeLog | 1 + 1 file changed, 1 insertion(+) diff --git a/apps/health/ChangeLog b/apps/health/ChangeLog index 1e4864af8..7dbb9c458 100644 --- a/apps/health/ChangeLog +++ b/apps/health/ChangeLog @@ -10,3 +10,4 @@ 0.09: Fix file naming so months are 1-based (not 0) (fix #1119) 0.10: Adds additional 3 minute setting for HRM 0.11: Pre-minified boot&lib - folds constants and saves RAM +0.12: Add setting for Daily Step Goal From c74cd9bf367817905531b1a8059c6bcd7c6cfa6b Mon Sep 17 00:00:00 2001 From: sir-indy <53864146+sir-indy@users.noreply.github.com> Date: Tue, 19 Apr 2022 15:25:58 +0100 Subject: [PATCH 27/63] Update app.js --- apps/health/app.js | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/apps/health/app.js b/apps/health/app.js index 415edb7c5..ae5a313f6 100644 --- a/apps/health/app.js +++ b/apps/health/app.js @@ -33,7 +33,7 @@ function menuSettings() { onchange : v => { s.hrm=v;setSettings(s); } }, "Daily Step Goal":{ - value : 0|s.stepGoal, + value : 10000|s.stepGoal, min : 0, max : 20000, step : 100, onchange : v => { s.stepGoal=v;setSettings(s); } } From e04f574f928569fc1bf60b6cf26bef6194aed26e Mon Sep 17 00:00:00 2001 From: sir-indy <53864146+sir-indy@users.noreply.github.com> Date: Tue, 19 Apr 2022 15:28:04 +0100 Subject: [PATCH 28/63] Update README.md --- apps/health/README.md | 1 + 1 file changed, 1 insertion(+) diff --git a/apps/health/README.md b/apps/health/README.md index f44854e3e..c6b379c0a 100644 --- a/apps/health/README.md +++ b/apps/health/README.md @@ -24,6 +24,7 @@ Stores: * **Off** - Don't turn HRM on, but record heart rate if the HRM was turned on by another app/widget * **10 Min** - Turn HRM on every 10 minutes (for each heath entry) and turn it off after 2 minutes, or when a good reading is found * **Always** - Keep HRM on all the time (more accurate recording, but reduces battery life to ~36 hours) +* **Daily Step Goal** - Default 10000, daily step goal for pedometer apps to use ## Technical Info From 702cd09f793e600e62205564c085c2d20123f547 Mon Sep 17 00:00:00 2001 From: sir-indy <53864146+sir-indy@users.noreply.github.com> Date: Tue, 19 Apr 2022 16:19:05 +0100 Subject: [PATCH 29/63] Update widstep.wid.js --- apps/widstep/widstep.wid.js | 10 +++++----- 1 file changed, 5 insertions(+), 5 deletions(-) diff --git a/apps/widstep/widstep.wid.js b/apps/widstep/widstep.wid.js index 84c7bf843..0499384d7 100644 --- a/apps/widstep/widstep.wid.js +++ b/apps/widstep/widstep.wid.js @@ -1,9 +1,9 @@ -let settings; +let wsSettings; function loadSettings() { - settings = require('Storage').readJSON("health.json", 1) || {}; - if( settings.stepGoal === undefined ) { - settings.stepGoal = 10000; + wsSettings = require('Storage').readJSON("health.json", 1) || {}; + if( wsSettings.stepGoal === undefined ) { + wsSettings.stepGoal = 10000; } } @@ -20,7 +20,7 @@ WIDGETS["widstep"]={area:"tl", sortorder:-1, width:28, g.setColor(g.theme.bg); g.fillRect(this.x, this.y, this.x + this.width, this.y + 23); g.setColor(g.theme.dark ? '#00f' : '#0ff'); - var progress = this.width * Math.min(steps/settings.stepGoal, 1); + var progress = this.width * Math.min(steps/wsSettings.stepGoal, 1); g.fillRect(this.x+1, this.y+1, this.x + progress -1, this.y + 23); g.setColor(g.theme.fg); g.setFontAlign(0, -1); From ea95dbfbf43366d83cd0336f460d896f6fad7c8d Mon Sep 17 00:00:00 2001 From: sir-indy <53864146+sir-indy@users.noreply.github.com> Date: Tue, 19 Apr 2022 16:20:01 +0100 Subject: [PATCH 30/63] Update widstep.wid.js --- apps/widstep/widstep.wid.js | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/apps/widstep/widstep.wid.js b/apps/widstep/widstep.wid.js index 0499384d7..79e3fe766 100644 --- a/apps/widstep/widstep.wid.js +++ b/apps/widstep/widstep.wid.js @@ -14,8 +14,8 @@ Bangle.on('lcdPower', function(on) { WIDGETS["widstep"]={area:"tl", sortorder:-1, width:28, draw:function() { if (!Bangle.isLCDOn()) return; // dont redraw if LCD is off - //var steps = Bangle.getHealthStatus("day").steps; - var steps = 5285; + var steps = Bangle.getHealthStatus("day").steps; + //var steps = 5285; g.reset(); g.setColor(g.theme.bg); g.fillRect(this.x, this.y, this.x + this.width, this.y + 23); From 20f9f2ad86c27a88076b3c2215353fec7e1715f1 Mon Sep 17 00:00:00 2001 From: sir-indy <53864146+sir-indy@users.noreply.github.com> Date: Tue, 19 Apr 2022 16:26:56 +0100 Subject: [PATCH 31/63] Update README.md --- apps/widstep/README.md | 5 +++-- 1 file changed, 3 insertions(+), 2 deletions(-) diff --git a/apps/widstep/README.md b/apps/widstep/README.md index 498f2ebd9..c41b025cd 100644 --- a/apps/widstep/README.md +++ b/apps/widstep/README.md @@ -1,6 +1,7 @@ # Step counter widget -This is my step counter widget. There are many like it, but this one is mine. -Designed to be as narrow as possible, but still easy to read, by sacrificing accuracy and only showing to the nearest 100 steps (0.1k). +This is my step counter. There are many like it, but this one is mine. + +A pedometer widget designed to be as narrow as possible, but still easy to read, by sacrificing accuracy and only showing to the nearest 100 steps (0.1k). Shows a subtle fill colour in the background for progress to the goal. The goal is picked up from the health tracker settings. From aedb3a0b2600be62a2e254cbd24dd3d3aceec43a Mon Sep 17 00:00:00 2001 From: sir-indy <53864146+sir-indy@users.noreply.github.com> Date: Tue, 19 Apr 2022 16:36:17 +0100 Subject: [PATCH 32/63] Update app.js --- apps/health/app.js | 13 +++++++------ 1 file changed, 7 insertions(+), 6 deletions(-) diff --git a/apps/health/app.js b/apps/health/app.js index ae5a313f6..7b52216b0 100644 --- a/apps/health/app.js +++ b/apps/health/app.js @@ -31,11 +31,6 @@ function menuSettings() { min : 0, max : 3, format : v=>["Off","3 mins","10 mins","Always"][v], onchange : v => { s.hrm=v;setSettings(s); } - }, - "Daily Step Goal":{ - value : 10000|s.stepGoal, - min : 0, max : 20000, step : 100, - onchange : v => { s.stepGoal=v;setSettings(s); } } }); } @@ -43,11 +38,17 @@ function menuSettings() { function menuStepCount() { swipe_enabled = false; clearButton(); + var s=getSettings(); E.showMenu({ "":{title:"Step Counting"}, "< Back":()=>menuMain(), "per hour":()=>stepsPerHour(), - "per day":()=>stepsPerDay() + "per day":()=>stepsPerDay(), + "Daily Step Goal":{ + value : 10000|s.stepGoal, + min : 0, max : 20000, step : 100, + onchange : v => { s.stepGoal=v;setSettings(s); } + } }); } From 4a960430487c1f710309b9b1b6d0fc2a2f4d4aef Mon Sep 17 00:00:00 2001 From: sir-indy <53864146+sir-indy@users.noreply.github.com> Date: Tue, 19 Apr 2022 17:04:56 +0100 Subject: [PATCH 33/63] Update app.js --- apps/health/app.js | 16 ++++++++-------- 1 file changed, 8 insertions(+), 8 deletions(-) diff --git a/apps/health/app.js b/apps/health/app.js index 7b52216b0..75e46a1e8 100644 --- a/apps/health/app.js +++ b/apps/health/app.js @@ -2,8 +2,8 @@ function getSettings() { return require("Storage").readJSON("health.json",1)||{}; } -function setSettings(s) { - require("Storage").writeJSON("health.json",s); +function setSettings(healthSettings) { + require("Storage").writeJSON("health.json",healthSettings); } function menuMain() { @@ -22,15 +22,15 @@ function menuMain() { function menuSettings() { swipe_enabled = false; clearButton(); - var s=getSettings(); + var healthSettings=getSettings(); E.showMenu({ "":{title:"Health Tracking"}, "< Back":()=>menuMain(), "Heart Rt":{ - value : 0|s.hrm, + value : 0|healthSettings.hrm, min : 0, max : 3, format : v=>["Off","3 mins","10 mins","Always"][v], - onchange : v => { s.hrm=v;setSettings(s); } + onchange : v => { healthSettings.hrm=v;setSettings(healthSettings); } } }); } @@ -38,16 +38,16 @@ function menuSettings() { function menuStepCount() { swipe_enabled = false; clearButton(); - var s=getSettings(); + var healthSettings=getSettings(); E.showMenu({ "":{title:"Step Counting"}, "< Back":()=>menuMain(), "per hour":()=>stepsPerHour(), "per day":()=>stepsPerDay(), "Daily Step Goal":{ - value : 10000|s.stepGoal, + value : 10000|healthSettings.stepGoal, min : 0, max : 20000, step : 100, - onchange : v => { s.stepGoal=v;setSettings(s); } + onchange : v => { healthSettings.stepGoal=v;setSettings(healthSettings); } } }); } From f0ba8ac6eaf6988177d3b7d9025fb7d831712f82 Mon Sep 17 00:00:00 2001 From: sir-indy <53864146+sir-indy@users.noreply.github.com> Date: Tue, 19 Apr 2022 20:35:04 +0100 Subject: [PATCH 34/63] Update app.js --- apps/health/app.js | 34 ++++++++++++---------------------- 1 file changed, 12 insertions(+), 22 deletions(-) diff --git a/apps/health/app.js b/apps/health/app.js index 75e46a1e8..20c7f9fd7 100644 --- a/apps/health/app.js +++ b/apps/health/app.js @@ -2,8 +2,8 @@ function getSettings() { return require("Storage").readJSON("health.json",1)||{}; } -function setSettings(healthSettings) { - require("Storage").writeJSON("health.json",healthSettings); +function setSettings(s) { + require("Storage").writeJSON("health.json",s); } function menuMain() { @@ -15,39 +15,22 @@ function menuMain() { "Step Counting":()=>menuStepCount(), "Movement":()=>menuMovement(), "Heart Rate":()=>menuHRM(), - "Settings":()=>menuSettings() - }); -} - -function menuSettings() { - swipe_enabled = false; - clearButton(); - var healthSettings=getSettings(); - E.showMenu({ - "":{title:"Health Tracking"}, - "< Back":()=>menuMain(), - "Heart Rt":{ - value : 0|healthSettings.hrm, - min : 0, max : 3, - format : v=>["Off","3 mins","10 mins","Always"][v], - onchange : v => { healthSettings.hrm=v;setSettings(healthSettings); } - } }); } function menuStepCount() { swipe_enabled = false; clearButton(); - var healthSettings=getSettings(); + var s=getSettings(); E.showMenu({ "":{title:"Step Counting"}, "< Back":()=>menuMain(), "per hour":()=>stepsPerHour(), "per day":()=>stepsPerDay(), "Daily Step Goal":{ - value : 10000|healthSettings.stepGoal, + value : (s.stepGoal ? s.stepGoal : 10000), min : 0, max : 20000, step : 100, - onchange : v => { healthSettings.stepGoal=v;setSettings(healthSettings); } + onchange : v => { s.stepGoal=v;setSettings(s); } } }); } @@ -66,11 +49,18 @@ function menuMovement() { function menuHRM() { swipe_enabled = false; clearButton(); + var s=getSettings(); E.showMenu({ "":{title:"Heart Rate"}, "< Back":()=>menuMain(), "per hour":()=>hrmPerHour(), "per day":()=>hrmPerDay(), + "Log interval":{ + value : 0|s.hrm, + min : 0, max : 3, + format : v=>["Off","3 mins","10 mins","Always"][v], + onchange : v => { s.hrm=v;setSettings(s); } + } }); } From 2db18d66785e9fb73408924db378636995c481c6 Mon Sep 17 00:00:00 2001 From: Ronin0000 <89286474+Ronin0000@users.noreply.github.com> Date: Tue, 19 Apr 2022 16:37:24 -0700 Subject: [PATCH 35/63] Update appb2.js --- apps/choozi/appb2.js | 8 +++----- 1 file changed, 3 insertions(+), 5 deletions(-) diff --git a/apps/choozi/appb2.js b/apps/choozi/appb2.js index d5c542be3..5f217f638 100644 --- a/apps/choozi/appb2.js +++ b/apps/choozi/appb2.js @@ -1,6 +1,3 @@ -//g.setTheme({fg : 0xFFFF, fg2 : 0xFFFF,bg2 : 0x0007,fgH : 0xFFFF,bgH : 0x02F7,dark : true}); - - /* Choozi - Choose people or things at random using Bangle.js. * Inspired by the "Chwazi" Android app * @@ -77,7 +74,7 @@ function arc(minR, maxR, minAngle, maxAngle) { inside.push(centreY+s*minR); outside.unshift(centreY+s*maxR); outside.unshift(centreX+c*maxR); - + var vertices = inside.concat(outside); g.fillPoly(vertices, true); } @@ -133,6 +130,7 @@ function animateChoice(target) { g.fillCircle(x, y, ballSize); oldx=x; oldy=y; + g.flip(); } } @@ -154,7 +152,7 @@ function choose() { // draw the current value of N in the middle of the screen, with // up/down arrows function drawN() { - g.setColor('#000000'); + g.setColor(g.theme.fg); g.setFont("Vector",fontSize); g.drawString(N,centreX-g.stringWidth(N)/2+4,centreY-fontSize/2); if (N < maxN) From fd7d0db7e98a642576a7484614a8905a4bb1f4b6 Mon Sep 17 00:00:00 2001 From: Ronin0000 <89286474+Ronin0000@users.noreply.github.com> Date: Tue, 19 Apr 2022 16:37:54 -0700 Subject: [PATCH 36/63] Update ChangeLog --- apps/choozi/ChangeLog | 1 + 1 file changed, 1 insertion(+) diff --git a/apps/choozi/ChangeLog b/apps/choozi/ChangeLog index 7aabe5c89..03f7ef832 100644 --- a/apps/choozi/ChangeLog +++ b/apps/choozi/ChangeLog @@ -1,2 +1,3 @@ 0.01: New App! 0.02: Support Bangle.js 2 +0.03: Fix bug for Bangle.js 2 where g.flip was not being called. From beff9975fc516e3721a49282ffc9872c7e49106a Mon Sep 17 00:00:00 2001 From: Ronin0000 <89286474+Ronin0000@users.noreply.github.com> Date: Tue, 19 Apr 2022 16:38:03 -0700 Subject: [PATCH 37/63] Update metadata.json --- apps/choozi/metadata.json | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/apps/choozi/metadata.json b/apps/choozi/metadata.json index a10448ed5..79af76fa2 100644 --- a/apps/choozi/metadata.json +++ b/apps/choozi/metadata.json @@ -1,7 +1,7 @@ { "id": "choozi", "name": "Choozi", - "version": "0.02", + "version": "0.03", "description": "Choose people or things at random using Bangle.js.", "icon": "app.png", "tags": "tool", From 5a86b8e4d09454ac951136aad1333ad64cdb45c7 Mon Sep 17 00:00:00 2001 From: Ronin0000 <89286474+Ronin0000@users.noreply.github.com> Date: Tue, 19 Apr 2022 16:46:04 -0700 Subject: [PATCH 38/63] Update lcars.settings.js --- apps/lcars/lcars.settings.js | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/apps/lcars/lcars.settings.js b/apps/lcars/lcars.settings.js index 830907fc5..2656a54ab 100644 --- a/apps/lcars/lcars.settings.js +++ b/apps/lcars/lcars.settings.js @@ -27,7 +27,7 @@ var dataOptions = ["Steps", "Battery", "VREF", "HRM", "Temp", "Humidity", "Wind", "Altitude", "CoreT"]; var speedOptions = ["kph", "mph"]; var color_options = ['Green','Orange','Cyan','Purple','Red','Blue','Yellow','White']; - var bg_code = ['#0f0','#FF9900','#0094FF','#FF00DC','#f00','#00f','#ffef00','#FFFFFF']; + var bg_code = ['#00ff00','#FF9900','#0094FF','#FF00DC','#ff0000','#0000ff','#ffef00','#FFFFFF']; E.showMenu({ '': { 'title': 'LCARS Clock' }, From 28546c15d14d3e090693e3fd997486df8efd7eb3 Mon Sep 17 00:00:00 2001 From: Gordon Williams Date: Wed, 20 Apr 2022 09:58:41 +0100 Subject: [PATCH 39/63] Revert "main.css: Force line break for smaller resolutions" --- css/main.css | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/css/main.css b/css/main.css index a986df22e..f4850babe 100644 --- a/css/main.css +++ b/css/main.css @@ -81,7 +81,7 @@ a.btn.btn-link.dropdown-toggle { min-height: 8em; } -.tile-content { position: relative; word-break: break-all; } +.tile-content { position: relative; } .link-github { position:absolute; top: 36px; From 51c285b39cf9adc6fb8010f94ee7438d816648d4 Mon Sep 17 00:00:00 2001 From: sir-indy <53864146+sir-indy@users.noreply.github.com> Date: Wed, 20 Apr 2022 12:38:09 +0100 Subject: [PATCH 40/63] Update widstep.wid.js --- apps/widstep/widstep.wid.js | 14 +++----------- 1 file changed, 3 insertions(+), 11 deletions(-) diff --git a/apps/widstep/widstep.wid.js b/apps/widstep/widstep.wid.js index 79e3fe766..39c825521 100644 --- a/apps/widstep/widstep.wid.js +++ b/apps/widstep/widstep.wid.js @@ -1,11 +1,4 @@ -let wsSettings; - -function loadSettings() { - wsSettings = require('Storage').readJSON("health.json", 1) || {}; - if( wsSettings.stepGoal === undefined ) { - wsSettings.stepGoal = 10000; - } -} +let wsSettingsGoal; Bangle.on('step', function(s) { WIDGETS["widstep"].draw(); }); Bangle.on('lcdPower', function(on) { @@ -15,12 +8,11 @@ WIDGETS["widstep"]={area:"tl", sortorder:-1, width:28, draw:function() { if (!Bangle.isLCDOn()) return; // dont redraw if LCD is off var steps = Bangle.getHealthStatus("day").steps; - //var steps = 5285; g.reset(); g.setColor(g.theme.bg); g.fillRect(this.x, this.y, this.x + this.width, this.y + 23); g.setColor(g.theme.dark ? '#00f' : '#0ff'); - var progress = this.width * Math.min(steps/wsSettings.stepGoal, 1); + var progress = this.width * Math.min(steps/wsSettingsGoal, 1); g.fillRect(this.x+1, this.y+1, this.x + progress -1, this.y + 23); g.setColor(g.theme.fg); g.setFontAlign(0, -1); @@ -29,7 +21,7 @@ WIDGETS["widstep"]={area:"tl", sortorder:-1, width:28, g.setFont('4x6').drawString('steps', this.x+this.width/2, this.y + 2); //g.drawRect(this.x, this.y, this.x + this.width, this.y + 23); }, reload:function() { - loadSettings(); + wsSettingsGoal = (require('Storage').readJSON("health.json", 1) || {}).stepGoal || 10000; WIDGETS["widstep"].draw(); } }; From 7621776a833a18057feb5ed53d702bc3ff9adb5a Mon Sep 17 00:00:00 2001 From: sir-indy <53864146+sir-indy@users.noreply.github.com> Date: Wed, 20 Apr 2022 12:39:41 +0100 Subject: [PATCH 41/63] Update app.js --- apps/health/app.js | 37 +++++++++++++++++++++++-------------- 1 file changed, 23 insertions(+), 14 deletions(-) diff --git a/apps/health/app.js b/apps/health/app.js index 20c7f9fd7..efd18c4e1 100644 --- a/apps/health/app.js +++ b/apps/health/app.js @@ -15,23 +15,39 @@ function menuMain() { "Step Counting":()=>menuStepCount(), "Movement":()=>menuMovement(), "Heart Rate":()=>menuHRM(), + "Settings":()=>menuSettings() + }); +} + +function menuSettings() { + swipe_enabled = false; + clearButton(); + var s=getSettings(); + E.showMenu({ + "":{title:"Health Tracking"}, + "< Back":()=>menuMain(), + "Heart Rt":{ + value : 0|s.hrm, + min : 0, max : 3, + format : v=>["Off","3 mins","10 mins","Always"][v], + onchange : v => { s.hrm=v;setSettings(s); } + }, + "Daily Step Goal":{ + value : (s.stepGoal ? s.stepGoal : 10000), + min : 0, max : 20000, step : 100, + onchange : v => { s.stepGoal=v;setSettings(s); } + } }); } function menuStepCount() { swipe_enabled = false; clearButton(); - var s=getSettings(); E.showMenu({ "":{title:"Step Counting"}, "< Back":()=>menuMain(), "per hour":()=>stepsPerHour(), - "per day":()=>stepsPerDay(), - "Daily Step Goal":{ - value : (s.stepGoal ? s.stepGoal : 10000), - min : 0, max : 20000, step : 100, - onchange : v => { s.stepGoal=v;setSettings(s); } - } + "per day":()=>stepsPerDay() }); } @@ -49,18 +65,11 @@ function menuMovement() { function menuHRM() { swipe_enabled = false; clearButton(); - var s=getSettings(); E.showMenu({ "":{title:"Heart Rate"}, "< Back":()=>menuMain(), "per hour":()=>hrmPerHour(), "per day":()=>hrmPerDay(), - "Log interval":{ - value : 0|s.hrm, - min : 0, max : 3, - format : v=>["Off","3 mins","10 mins","Always"][v], - onchange : v => { s.hrm=v;setSettings(s); } - } }); } From 7bfe23d809627ca5d690419f133477977bcf4330 Mon Sep 17 00:00:00 2001 From: sir-indy <53864146+sir-indy@users.noreply.github.com> Date: Wed, 20 Apr 2022 12:48:28 +0100 Subject: [PATCH 42/63] Update widstep.wid.js --- apps/widstep/widstep.wid.js | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-) diff --git a/apps/widstep/widstep.wid.js b/apps/widstep/widstep.wid.js index 39c825521..1defcb146 100644 --- a/apps/widstep/widstep.wid.js +++ b/apps/widstep/widstep.wid.js @@ -1,4 +1,4 @@ -let wsSettingsGoal; +let wsSettingsGoal = 10000; Bangle.on('step', function(s) { WIDGETS["widstep"].draw(); }); Bangle.on('lcdPower', function(on) { @@ -25,4 +25,3 @@ WIDGETS["widstep"]={area:"tl", sortorder:-1, width:28, WIDGETS["widstep"].draw(); } }; -loadSettings(); From b0a43413c8d828acc5376d8f21795aae4db224fb Mon Sep 17 00:00:00 2001 From: Alessandro Cocco Date: Wed, 20 Apr 2022 14:12:46 +0200 Subject: [PATCH 43/63] [Scheduler] Export new functions - newDefaultAlarm - newDefaultTimer - get/setSettings --- apps/sched/README.md | 25 +++++++++++++------- apps/sched/lib.js | 55 ++++++++++++++++++++++++++++++++++++++++++++ 2 files changed, 72 insertions(+), 8 deletions(-) diff --git a/apps/sched/README.md b/apps/sched/README.md index ed08139eb..319778067 100644 --- a/apps/sched/README.md +++ b/apps/sched/README.md @@ -53,21 +53,27 @@ use too much RAM. It can be used as follows: ``` -// add/update an existing alarm +// Get a new alarm with default values +let alarm = require("sched").newDefaultAlarm(); + +// Get a new timer with default values +let timer = require("sched").newDefaultTimer(); + +// Add/update an existing alarm require("sched").setAlarm("mytimer", { msg : "Wake up", - timer : 10*60*1000, // 10 Minutes + timer : 10 * 60 * 1000 // 10 minutes }); // Ensure the widget and alarm timer updates to schedule the new alarm properly require("sched").reload(); // Get the time to the next alarm for us -var timeToNext = require("sched").getTimeToAlarm(require("sched").getAlarm("mytimer")); -// timeToNext===undefined if no alarm or alarm disabled +let timeToNext = require("sched").getTimeToAlarm(require("sched").getAlarm("mytimer")); +// timeToNext === undefined if no alarm or alarm disabled -// delete an alarm +// Delete an alarm require("sched").setAlarm("mytimer", undefined); -// reload after deleting... +// Reload after deleting require("sched").reload(); // Or add an alarm that runs your own code - in this case @@ -76,12 +82,15 @@ require("sched").reload(); require("sched").setAlarm("customrunner", { appid : "myapp", js : "load('setting.app.js')", - timer : 1*60*1000, // 1 Minute + timer : 1 * 60 * 1000 // 1 minute }); // If you have been specifying `appid` you can also find any alarms that // your app has created with the following: -require("sched").getAlarms().filter(a=>a.appid=="myapp"); +require("sched").getAlarms().filter(a => a.appid == "myapp"); + +// Get the scheduler settings +let settings = require("sched").getSettings(); ``` If your app requires alarms, you can specify that the alarms app needs to diff --git a/apps/sched/lib.js b/apps/sched/lib.js index 48094c86f..bfad1ac2d 100644 --- a/apps/sched/lib.js +++ b/apps/sched/lib.js @@ -52,3 +52,58 @@ exports.reload = function() { Bangle.drawWidgets(); } }; +// Factory that creates a new alarm with default values +exports.newDefaultAlarm = function () { + const settings = exports.getSettings(); + + let alarm = { + t: 12 * 3600000, // Default to 12:00 + on: true, + rp: false, // repeat not the default + as: settings.defaultAutoSnooze || false, + dow: 0b1111111, + last: 0, + vibrate: settings.defaultAlarmPattern, + }; + + delete settings; + + return alarm; +} +// Factory that creates a new timer with default values +exports.newDefaultTimer = function () { + const settings = exports.getSettings(); + + let timer = { + timer: 5 * 60 * 1000, // 5 minutes + on: true, + rp: false, + as: false, + dow: 0b1111111, + last: 0, + vibrate: settings.defaultTimerPattern + } + + delete settings; + + return timer; +}; +// Return the scheduler settings +exports.getSettings = function () { + return Object.assign( + { + unlockAtBuzz: false, + defaultSnoozeMillis: 600000, // 10 minutes + defaultAutoSnooze: false, + buzzCount: 10, + buzzIntervalMillis: 3000, // 3 seconds + defaultAlarmPattern: "..", + defaultTimerPattern: ".." + }, + require("Storage").readJSON("sched.settings.json", true) || {} + ); +} +// Write the updated settings back to storage +exports.setSettings = function(settings) { + require("Storage").writeJSON("sched.settings.json", settings); +}; \ No newline at end of file From a84c1d4f771a5f405b921d7783fc4b4671635922 Mon Sep 17 00:00:00 2001 From: Alessandro Cocco Date: Wed, 20 Apr 2022 14:13:33 +0200 Subject: [PATCH 44/63] [Scheduler] Add Settings page --- apps/sched/README.md | 11 ++++++- apps/sched/settings.js | 72 ++++++++++++++++++++++++++++++++++++++++++ 2 files changed, 82 insertions(+), 1 deletion(-) create mode 100644 apps/sched/settings.js diff --git a/apps/sched/README.md b/apps/sched/README.md index 319778067..47507fc14 100644 --- a/apps/sched/README.md +++ b/apps/sched/README.md @@ -8,8 +8,17 @@ Other apps can use this to provide alarm functionality. App --- -The Alarm app allows you to add/modify any running timers. +The **Alarms & Timers** app allows you to add/modify any running alarms and timers. +Global Settings +--------------- + +- `Unlock at Buzz` - If `Yes` the alarm/timer will unlock the watch +- `Default Auto Snooze` - Default _Auto Snooze_ value for newly created alarms (_Alarms_ only) +- `Default Snooze` - Default _Snooze_ value for newly created alarms/timers +- `Buzz Count` - The number of buzzes before the watch goes silent +- `Buzz Interval` - The interval between one buzz and the next +- `Default Alarm/Timer Pattern` - Default vibration pattern for newly created alarms/timers Internals / Library ------------------- diff --git a/apps/sched/settings.js b/apps/sched/settings.js new file mode 100644 index 000000000..642e43b43 --- /dev/null +++ b/apps/sched/settings.js @@ -0,0 +1,72 @@ +(function (back) { + let settings = require("sched").getSettings(); + + E.showMenu({ + "": { "title": /*LANG*/"Scheduler" }, + + /*LANG*/"< Back": () => back(), + + /*LANG*/"Unlock at Buzz": { + value: settings.unlockAtBuzz, + format: v => v ? /*LANG*/"Yes" : /*LANG*/"No", + onchange: v => { + settings.unlockAtBuzz = v; + require("sched").setSettings(settings); + } + }, + + /*LANG*/"Default Auto Snooze": { + value: settings.defaultAutoSnooze, + format: v => v ? /*LANG*/"Yes" : /*LANG*/"No", + onchange: v => { + settings.defaultAutoSnooze = v; + require("sched").setSettings(settings); + } + }, + + /*LANG*/"Default Snooze": { + value: settings.defaultSnoozeMillis / 60000, + min: 5, + max: 30, + step: 5, + format: v => v + /*LANG*/" min", + onchange: v => { + settings.defaultSnoozeMillis = v * 60000; + require("sched").setSettings(settings); + } + }, + + /*LANG*/"Buzz Count": { + value: settings.buzzCount, + min: 5, + max: 15, + step: 1, + onchange: v => { + settings.buzzCount = v; + require("sched").setSettings(settings); + } + }, + + /*LANG*/"Buzz Interval": { + value: settings.buzzIntervalMillis / 1000, + min: 1, + max: 5, + step: 1, + format: v => v + /*LANG*/"s", + onchange: v => { + settings.buzzIntervalMillis = v * 1000; + require("sched").setSettings(settings); + } + }, + + /*LANG*/"Default Alarm Pattern": require("buzz_menu").pattern(settings.defaultAlarmPattern, v => { + settings.defaultAlarmPattern = v; + require("sched").setSettings(settings); + }), + + /*LANG*/"Default Timer Pattern": require("buzz_menu").pattern(settings.defaultTimerPattern, v => { + settings.defaultTimerPattern = v; + require("sched").setSettings(settings); + }) + }); +}); From 9c9b48ce39df58bd7c5df43283d3233a432a956a Mon Sep 17 00:00:00 2001 From: Alessandro Cocco Date: Wed, 20 Apr 2022 14:14:35 +0200 Subject: [PATCH 45/63] [Scheduler] Integrate the new settings into the code --- apps/sched/sched.js | 44 ++++++++++++++++++++++++++++++-------------- 1 file changed, 30 insertions(+), 14 deletions(-) diff --git a/apps/sched/sched.js b/apps/sched/sched.js index 9096fe4bf..83f03ac01 100644 --- a/apps/sched/sched.js +++ b/apps/sched/sched.js @@ -18,7 +18,9 @@ function formatTime(t) { } function showAlarm(alarm) { - var msg = ""; + const settings = require("sched").getSettings(); + + let msg = ""; msg += alarm.timer ? formatTime(alarm.timer) : formatTime(alarm.t); if (alarm.msg) { msg += "\n"+alarm.msg; @@ -28,9 +30,12 @@ function showAlarm(alarm) { else msg = atob("AC0swgF97///RcEpMlVVVVVVf9VVVVVVVVX/9VVf9VVf/1VVV///1Vf9VX///VVX///VWqqlV///1Vf//9aqqqqpf//9V///2qqqqqqn///V///6qqqqqqr///X//+qqoAAKqqv//3//6qoAAAAKqr//3//qqAAAAAAqq//3/+qoAADwAAKqv/3/+qgAADwAACqv/3/aqAAADwAAAqp/19qoAAADwAAAKqfV1qgAAADwAAACqXVWqgAAADwAAACqlVWqAAAADwAAAAqlVWqAAAADwAAAAqlVWqAAAADwAAAAqlVaoAAAADwAAAAKpVaoAAAADwAAAAKpVaoAAAADwAAAAKpVaoAAAAOsAAAAKpVaoAAAAOsAAAAKpVaoAAAAL/AAAAKpVaoAAAAgPwAAAKpVaoAAACAD8AAAKpVWqAAAIAA/AAAqlVWqAAAgAAPwAAqlVWqAACAAADwAAqlVWqgAIAAAAAACqlVVqgAgAAAAAACqVVVqoAAAAAAAAKqVVVaqAAAAAAAAqpVVVWqgAAAAAACqlVVVWqoAAAAAAKqlVVVVqqAAAAAAqqVVVVVaqoAAAAKqpVVVVVeqqoAAKqqtVVVVV/6qqqqqqr/VVVVX/2qqqqqqn/1VVVf/VaqqqqpV/9VVVf9VVWqqlVVf9VVVf1VVVVVVVVX9VQ==")+" "+msg; } + Bangle.loadWidgets(); Bangle.drawWidgets(); - var buzzCount = 10; + + let buzzCount = settings.buzzCount; + E.showPrompt(msg,{ title:alarm.timer ? /*LANG*/"TIMER!" : /*LANG*/"ALARM!", buttons : {/*LANG*/"Snooze":true,/*LANG*/"Ok":false} // default is sleep so it'll come back in 10 mins @@ -38,7 +43,7 @@ function showAlarm(alarm) { buzzCount = 0; if (sleep) { if(alarm.ot===undefined) alarm.ot = alarm.t; - alarm.t += 10*60*1000; // 10 minutes + alarm.t += settings.defaultSnoozeMillis; } else { if (!alarm.timer) alarm.last = (new Date()).getDate(); if (alarm.ot!==undefined) { @@ -51,24 +56,35 @@ function showAlarm(alarm) { require("sched").setAlarms(alarms); load(); }); + function buzz() { - require("buzz").pattern(alarm.vibrate===undefined?"..":alarm.vibrate).then(function() { - if (buzzCount--) - setTimeout(buzz, 3000); - else if(alarm.as) { // auto-snooze - buzzCount = 10; - setTimeout(buzz, 600000); + if (settings.unlockAtBuzz) { + Bangle.setLocked(false); + } + + require("buzz").pattern(alarm.vibrate === undefined ? ".." : alarm.vibrate).then(() => { + if (buzzCount--) { + setTimeout(buzz, settings.buzzIntervalMillis); + } else if (alarm.as) { // auto-snooze + buzzCount = settings.buzzCount; + setTimeout(buzz, settings.defaultSnoozeMillis); } }); } - if ((require('Storage').readJSON('setting.json',1)||{}).quiet>1) return; + + if ((require("Storage").readJSON("setting.json", 1) || {}).quiet > 1) + return; + buzz(); } // Check for alarms -var alarms = require("sched").getAlarms(); -var active = require("sched").getActiveAlarms(alarms); -if (active.length) // if there's an alarm, show it +let alarms = require("sched").getAlarms(); +let active = require("sched").getActiveAlarms(alarms); +if (active.length) { + // if there's an alarm, show it showAlarm(active[0]); -else // otherwise just go back to default app +} else { + // otherwise just go back to default app setTimeout(load, 100); +} From cb0913468f0793d4ef62fa4596279b14545bfaf1 Mon Sep 17 00:00:00 2001 From: Alessandro Cocco Date: Wed, 20 Apr 2022 14:15:23 +0200 Subject: [PATCH 46/63] [Scheduler] Update metadata & changelog --- apps/sched/ChangeLog | 1 + apps/sched/metadata.json | 7 ++++--- 2 files changed, 5 insertions(+), 3 deletions(-) diff --git a/apps/sched/ChangeLog b/apps/sched/ChangeLog index a2d6c370f..0f935caf8 100644 --- a/apps/sched/ChangeLog +++ b/apps/sched/ChangeLog @@ -2,3 +2,4 @@ 0.02: Fix scheduling of other alarms if there is a pending alarm from the past (fix #1667) 0.03: Fix `getTimeToAlarm` for a timer already used at same day, don't set `last` for timers. 0.04: Fix `getTimeToAlarm` to check for next dow if alarm.t lower currentTime. +0.05: Export new functions (`newDefaultAlarm/Timer`), add Settings page diff --git a/apps/sched/metadata.json b/apps/sched/metadata.json index ffa346a44..3454d2397 100644 --- a/apps/sched/metadata.json +++ b/apps/sched/metadata.json @@ -1,7 +1,7 @@ { "id": "sched", "name": "Scheduler", - "version": "0.04", + "version": "0.05", "description": "Scheduling library for alarms and timers", "icon": "app.png", "type": "scheduler", @@ -12,7 +12,8 @@ {"name":"sched.boot.js","url":"boot.js"}, {"name":"sched.js","url":"sched.js"}, {"name":"sched.img","url":"app-icon.js","evaluate":true}, - {"name":"sched","url":"lib.js"} + {"name":"sched","url":"lib.js"}, + {"name":"sched.settings.js","url":"settings.js"} ], - "data": [{"name":"sched.json"}] + "data": [{"name":"sched.json"}, {"name":"sched.settings.json"}] } From bcae05d257aaf016cc5a101dbb19d0096aa6d90e Mon Sep 17 00:00:00 2001 From: Alessandro Cocco Date: Wed, 20 Apr 2022 14:18:11 +0200 Subject: [PATCH 47/63] [Alarms & Timers] Update labels and add LANG placeholders --- apps/alarm/app.js | 26 +++++++++++++------------- 1 file changed, 13 insertions(+), 13 deletions(-) diff --git a/apps/alarm/app.js b/apps/alarm/app.js index b9404358e..ccf1d7bf0 100644 --- a/apps/alarm/app.js +++ b/apps/alarm/app.js @@ -39,7 +39,7 @@ function showMainMenu() { // Timer img "\0"+atob("DhKBAP////MDDAwwMGGBzgPwB4AeAPwHOBhgwMMzDez////w") // Alarm img "\0"+atob("FBSBAABgA4YcMPDGP8Zn/mx/48//PP/zD/8A//AP/wD/8A//AP/wH/+D//w//8AAAADwAAYA") const menu = { - '': { 'title': 'Alarm/Timer' }, + '': { 'title': /*LANG*/'Alarms&Timers' }, /*LANG*/'< Back' : ()=>{load();}, /*LANG*/'New Alarm': ()=>editAlarm(-1), /*LANG*/'New Timer': ()=>editTimer(-1) @@ -76,13 +76,13 @@ function showMainMenu() { function editDOW(dow, onchange) { const menu = { '': { 'title': /*LANG*/'Days of Week' }, - '< Back' : () => onchange(dow) + /*LANG*/'< Back' : () => onchange(dow) }; for (var i = 0; i < 7; i++) (i => { var dayOfWeek = require("locale").dow({ getDay: () => i }); menu[dayOfWeek] = { value: !!(dow&(1< v ? "Yes" : "No", + format: v => v ? /*LANG*/"Yes" : /*LANG*/"No", onchange: v => v ? dow |= 1< showMainMenu(), + /*LANG*/'< Back' : () => showMainMenu(), /*LANG*/'Hours': { value: t.hrs, min : 0, max : 23, wrap : true, onchange: v => t.hrs=v @@ -117,23 +117,23 @@ function editAlarm(alarmIndex, alarm) { }, /*LANG*/'Enabled': { value: a.on, - format: v=>v?"On":"Off", + format: v => v ? /*LANG*/"On" : /*LANG*/"Off", onchange: v=>a.on=v }, /*LANG*/'Repeat': { value: a.rp, - format: v=>v?"Yes":"No", - onchange: v=>a.rp=v + format: v => v ? /*LANG*/"Yes" : /*LANG*/"No", + onchange: v => a.rp = v }, /*LANG*/'Days': { value: "SMTWTFS".split("").map((d,n)=>a.dow&(1< editDOW(a.dow, d=>{a.dow=d;editAlarm(alarmIndex,a)}) }, /*LANG*/'Vibrate': require("buzz_menu").pattern(a.vibrate, v => a.vibrate=v ), - /*LANG*/'Auto snooze': { + /*LANG*/'Auto Snooze': { value: a.as, - format: v=>v?"Yes":"No", - onchange: v=>a.as=v + format: v => v ? /*LANG*/"Yes" : /*LANG*/"No", + onchange: v => a.as = v } }; menu[/*LANG*/"Save"] = function() { @@ -171,7 +171,7 @@ function editTimer(alarmIndex, alarm) { const menu = { '': { 'title': /*LANG*/'Timer' }, - '< Back' : () => showMainMenu(), + /*LANG*/'< Back' : () => showMainMenu(), /*LANG*/'Hours': { value: t.hrs, min : 0, max : 23, wrap : true, onchange: v => t.hrs=v @@ -182,8 +182,8 @@ function editTimer(alarmIndex, alarm) { }, /*LANG*/'Enabled': { value: a.on, - format: v=>v?"On":"Off", - onchange: v=>a.on=v + format: v => v ? /*LANG*/"On" : /*LANG*/"Off", + onchange: v => a.on = v }, /*LANG*/'Vibrate': require("buzz_menu").pattern(a.vibrate, v => a.vibrate=v ), }; From c5e28b96eca668350057bf91a737bafce8dc1542 Mon Sep 17 00:00:00 2001 From: Alessandro Cocco Date: Wed, 20 Apr 2022 14:23:13 +0200 Subject: [PATCH 48/63] [Alarms & Timers] Integrate with new 'sched' factories Minor code clean up (let instead of var, whitespaces between operators, etc.) --- apps/alarm/app.js | 48 ++++++++++++++++------------------------------- 1 file changed, 16 insertions(+), 32 deletions(-) diff --git a/apps/alarm/app.js b/apps/alarm/app.js index ccf1d7bf0..1fc32ecb9 100644 --- a/apps/alarm/app.js +++ b/apps/alarm/app.js @@ -1,28 +1,28 @@ Bangle.loadWidgets(); Bangle.drawWidgets(); -var alarms = require("sched").getAlarms(); // An array of alarm objects (see sched/README.md) +let alarms = require("sched").getAlarms(); // time in ms -> { hrs, mins } function decodeTime(t) { - t = 0|t; // sanitise - var hrs = 0|(t/3600000); - return { hrs : hrs, mins : Math.round((t-hrs*3600000)/60000) }; + t = 0 | t; // sanitise + let hrs = 0 | (t / 3600000); + return { hrs: hrs, mins: Math.round((t - hrs * 3600000) / 60000) }; } // time in { hrs, mins } -> ms function encodeTime(o) { - return o.hrs*3600000 + o.mins*60000; + return o.hrs * 3600000 + o.mins * 60000; } function formatTime(t) { - var o = decodeTime(t); - return o.hrs+":"+("0"+o.mins).substr(-2); + let o = decodeTime(t); + return o.hrs + ":" + ("0" + o.mins).substr(-2); } function getCurrentTime() { - var time = new Date(); + let time = new Date(); return ( time.getHours() * 3600000 + time.getMinutes() * 60000 + @@ -78,8 +78,8 @@ function editDOW(dow, onchange) { '': { 'title': /*LANG*/'Days of Week' }, /*LANG*/'< Back' : () => onchange(dow) }; - for (var i = 0; i < 7; i++) (i => { - var dayOfWeek = require("locale").dow({ getDay: () => i }); + for (let i = 0; i < 7; i++) (i => { + let dayOfWeek = require("locale").dow({ getDay: () => i }); menu[dayOfWeek] = { value: !!(dow&(1< v ? /*LANG*/"Yes" : /*LANG*/"No", @@ -90,19 +90,11 @@ function editDOW(dow, onchange) { } function editAlarm(alarmIndex, alarm) { - var newAlarm = alarmIndex<0; - var a = { - t : 12*3600000, // 12 o clock default - on : true, - rp : false, // repeat not the default - as : false, - dow : 0b1111111, - last : 0, - vibrate : ".." - } + let newAlarm = alarmIndex < 0; + let a = require("sched").newDefaultAlarm(); if (!newAlarm) Object.assign(a, alarms[alarmIndex]); if (alarm) Object.assign(a,alarm); - var t = decodeTime(a.t); + let t = decodeTime(a.t); const menu = { '': { 'title': /*LANG*/'Alarm' }, @@ -155,19 +147,11 @@ function editAlarm(alarmIndex, alarm) { } function editTimer(alarmIndex, alarm) { - var newAlarm = alarmIndex<0; - var a = { - timer : 5*60*1000, // 5 minutes - on : true, - rp : false, - as : false, - dow : 0b1111111, - last : 0, - vibrate : ".." - } + let newAlarm = alarmIndex < 0; + let a = require("sched").newDefaultTimer(); if (!newAlarm) Object.assign(a, alarms[alarmIndex]); if (alarm) Object.assign(a,alarm); - var t = decodeTime(a.timer); + let t = decodeTime(a.timer); const menu = { '': { 'title': /*LANG*/'Timer' }, From cfff375e566c2529c6ed48593e8ec5540a485f01 Mon Sep 17 00:00:00 2001 From: Alessandro Cocco Date: Wed, 20 Apr 2022 14:23:45 +0200 Subject: [PATCH 49/63] [Alarms & Timers] Update metadata & changelog --- apps/alarm/ChangeLog | 1 + apps/alarm/metadata.json | 4 ++-- 2 files changed, 3 insertions(+), 2 deletions(-) diff --git a/apps/alarm/ChangeLog b/apps/alarm/ChangeLog index fcafc386f..3f56f4c20 100644 --- a/apps/alarm/ChangeLog +++ b/apps/alarm/ChangeLog @@ -18,3 +18,4 @@ 0.17: Moving alarm internals to 'sched' library 0.18: Cope with >1 identical alarm at once (#1667) 0.19: Ensure rescheduled alarms that already fired have 'last' reset +0.20: Use the new 'sched' factories to initialize new alarms/timers diff --git a/apps/alarm/metadata.json b/apps/alarm/metadata.json index 9636257ca..db36b3ca9 100644 --- a/apps/alarm/metadata.json +++ b/apps/alarm/metadata.json @@ -1,8 +1,8 @@ { "id": "alarm", - "name": "Alarm & Timer", + "name": "Alarms & Timers", "shortName": "Alarms", - "version": "0.19", + "version": "0.20", "description": "Set alarms and timers on your Bangle", "icon": "app.png", "tags": "tool,alarm,widget", From 2e5f198d666379ae7dac0efbedcba7861ee0da77 Mon Sep 17 00:00:00 2001 From: Alessandro Cocco Date: Mon, 18 Apr 2022 22:03:37 +0200 Subject: [PATCH 50/63] [Launcher] Update labels - Shorten settings title - Change menu items to Camel Case --- apps/launch/settings.js | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/apps/launch/settings.js b/apps/launch/settings.js index 60422e75c..3364864bd 100644 --- a/apps/launch/settings.js +++ b/apps/launch/settings.js @@ -8,7 +8,7 @@ require("Storage").write("launch.json",settings); } const appMenu = { - "": {"title": /*LANG*/"Launcher Settings"}, + "": { "title": /*LANG*/"Launcher" }, /*LANG*/"< Back": back, /*LANG*/"Font": { value: fonts.includes(settings.font)? fonts.indexOf(settings.font) : fonts.indexOf("12x20"), @@ -16,12 +16,12 @@ onchange: (m) => {save("font", fonts[m])}, format: v => fonts[v] }, - /*LANG*/"Vector font size": { + /*LANG*/"Vector Font Size": { value: settings.vectorsize || 10, min:10, max: 20,step:1,wrap:true, onchange: (m) => {save("vectorsize", m)} }, - /*LANG*/"Show clocks": { + /*LANG*/"Show Clocks": { value: settings.showClocks == true, format: v => v ? /*LANG*/"Yes" : /*LANG*/"No", onchange: (m) => {save("showClocks", m)} From 7afa90710fafd9546df2d5eca4465144be25e7b7 Mon Sep 17 00:00:00 2001 From: Alessandro Cocco Date: Mon, 18 Apr 2022 22:05:07 +0200 Subject: [PATCH 51/63] [Launcher] Add new "fullscreen" option --- apps/launch/settings.js | 12 ++++++++++-- 1 file changed, 10 insertions(+), 2 deletions(-) diff --git a/apps/launch/settings.js b/apps/launch/settings.js index 3364864bd..5d37e1c1b 100644 --- a/apps/launch/settings.js +++ b/apps/launch/settings.js @@ -1,6 +1,9 @@ // make sure to enclose the function in parentheses (function(back) { - let settings = Object.assign({ showClocks: true }, require("Storage").readJSON("launch.json", true) || {}); + let settings = Object.assign({ + showClocks: true, + fullscreen: false + }, require("Storage").readJSON("launch.json", true) || {}); let fonts = g.getFonts(); function save(key, value) { @@ -24,7 +27,12 @@ /*LANG*/"Show Clocks": { value: settings.showClocks == true, format: v => v ? /*LANG*/"Yes" : /*LANG*/"No", - onchange: (m) => {save("showClocks", m)} + onchange: (m) => { save("showClocks", m) } + }, + /*LANG*/"Fullscreen": { + value: settings.fullscreen == true, + format: v => v ? /*LANG*/"Yes" : /*LANG*/"No", + onchange: (m) => { save("fullscreen", m) } } }; E.showMenu(appMenu); From c2a5d13bd63a741c790b51db83166db6eb0eec1d Mon Sep 17 00:00:00 2001 From: Alessandro Cocco Date: Mon, 18 Apr 2022 22:05:59 +0200 Subject: [PATCH 52/63] [Launcher] Load & draw widgets iff not in fullscreen mode --- apps/launch/app.js | 12 +++++++++--- 1 file changed, 9 insertions(+), 3 deletions(-) diff --git a/apps/launch/app.js b/apps/launch/app.js index 4ceabe751..556e61bfd 100644 --- a/apps/launch/app.js +++ b/apps/launch/app.js @@ -2,7 +2,10 @@ var s = require("Storage"); var scaleval = 1; var vectorval = 20; var font = g.getFonts().includes("12x20") ? "12x20" : "6x8:2"; -let settings = Object.assign({ showClocks: true }, s.readJSON("launch.json", true) || {}); +let settings = Object.assign({ + showClocks: true, + fullscreen: false +}, s.readJSON("launch.json", true) || {}); if ("vectorsize" in settings) { vectorval = parseInt(settings.vectorsize); @@ -44,8 +47,11 @@ function drawApp(i, r) { } g.clear(); -Bangle.loadWidgets(); -Bangle.drawWidgets(); + +if (!settings.fullscreen) { + Bangle.loadWidgets(); + Bangle.drawWidgets(); +} E.showScroller({ h : 64*scaleval, c : apps.length, From 7c96e04d050ba1b4c31c18fe33fba9a361a68cde Mon Sep 17 00:00:00 2001 From: Alessandro Cocco Date: Mon, 18 Apr 2022 22:06:45 +0200 Subject: [PATCH 53/63] [Launcher] Update metadata & changelog --- apps/launch/ChangeLog | 1 + apps/launch/metadata.json | 2 +- 2 files changed, 2 insertions(+), 1 deletion(-) diff --git a/apps/launch/ChangeLog b/apps/launch/ChangeLog index b8c198d50..7248f69c3 100644 --- a/apps/launch/ChangeLog +++ b/apps/launch/ChangeLog @@ -12,3 +12,4 @@ 0.11: Merge Bangle.js 1 and 2 launchers, again 0.12: Add an option to hide clocks from the app list (fix #1015) Add /*LANG*/ tags for internationalisation +0.13: Add fullscreen mode diff --git a/apps/launch/metadata.json b/apps/launch/metadata.json index 96bbf104b..ab218412d 100644 --- a/apps/launch/metadata.json +++ b/apps/launch/metadata.json @@ -2,7 +2,7 @@ "id": "launch", "name": "Launcher", "shortName": "Launcher", - "version": "0.12", + "version": "0.13", "description": "This is needed to display a menu allowing you to choose your own applications. You can replace this with a customised launcher.", "icon": "app.png", "type": "launch", From c377a4f194670f65e8e1b61c1616f6fa97b51973 Mon Sep 17 00:00:00 2001 From: sir-indy <53864146+sir-indy@users.noreply.github.com> Date: Wed, 20 Apr 2022 14:32:23 +0100 Subject: [PATCH 54/63] Update app.js --- apps/health/app.js | 17 +++++++++-------- 1 file changed, 9 insertions(+), 8 deletions(-) diff --git a/apps/health/app.js b/apps/health/app.js index efd18c4e1..e39590e2d 100644 --- a/apps/health/app.js +++ b/apps/health/app.js @@ -2,8 +2,8 @@ function getSettings() { return require("Storage").readJSON("health.json",1)||{}; } -function setSettings(s) { - require("Storage").writeJSON("health.json",s); +function setSettings(healthSettings) { + require("Storage").writeJSON("health.json",healthSettings); } function menuMain() { @@ -22,20 +22,21 @@ function menuMain() { function menuSettings() { swipe_enabled = false; clearButton(); - var s=getSettings(); + var healthSettings=getSettings(); + //print(healthSettings); E.showMenu({ "":{title:"Health Tracking"}, "< Back":()=>menuMain(), "Heart Rt":{ - value : 0|s.hrm, + value : 0|healthSettings.hrm, min : 0, max : 3, format : v=>["Off","3 mins","10 mins","Always"][v], - onchange : v => { s.hrm=v;setSettings(s); } + onchange : v => { healthSettings.hrm=v;setSettings(healthSettings); } }, "Daily Step Goal":{ - value : (s.stepGoal ? s.stepGoal : 10000), + value : (healthSettings.stepGoal ? healthSettings.stepGoal : 10000), min : 0, max : 20000, step : 100, - onchange : v => { s.stepGoal=v;setSettings(s); } + onchange : v => { healthSettings.stepGoal=v;setSettings(healthSettings); } } }); } @@ -204,7 +205,7 @@ function drawBarChart() { for (bar = 1; bar < 10; bar++) { if (bar == 5) { g.setFont('6x8', 2); - g.setFontAlign(0,-1) + g.setFontAlign(0,-1); g.setColor(g.theme.fg); g.drawString(chart_label + " " + (chart_index + bar -1) + " " + chart_data[chart_index + bar - 1], g.getWidth()/2, 150); g.setColor("#00f"); From a7bab80dc3108f416b9fb1bf769d844c062a1049 Mon Sep 17 00:00:00 2001 From: Eskild Hustvedt Date: Wed, 20 Apr 2022 15:39:11 +0200 Subject: [PATCH 55/63] Allow timeouts to run on the message list screen Stops the app from displaying a message that then gets removed and after that permanently "hanging" on the message screen. --- apps/messages/ChangeLog | 1 + apps/messages/app.js | 2 -- apps/messages/metadata.json | 2 +- 3 files changed, 2 insertions(+), 3 deletions(-) diff --git a/apps/messages/ChangeLog b/apps/messages/ChangeLog index 75b171579..a96f125d3 100644 --- a/apps/messages/ChangeLog +++ b/apps/messages/ChangeLog @@ -45,3 +45,4 @@ 0.30: Add new Icons (Youtube, Twitch, MS TODO, Teams, Snapchat, Signal, Post & DHL, Nina, Lieferando, Kalender, Discord, Corona Warn, Bibel) 0.31: Option to disable icon flashing 0.32: Added an option to allow quiet mode to override message auto-open +0.33: Timeout from the message list screen if the message being displayed is removed and there is a timer going diff --git a/apps/messages/app.js b/apps/messages/app.js index 821813108..617801f61 100644 --- a/apps/messages/app.js +++ b/apps/messages/app.js @@ -470,8 +470,6 @@ function checkMessages(options) { // no new messages - go to clock? if (options.clockIfAllRead && newMessages.length==0) return load(); - // we don't have to time out of this screen... - cancelReloadTimeout(); active = "main"; // Otherwise show a menu E.showScroller({ diff --git a/apps/messages/metadata.json b/apps/messages/metadata.json index 7886a7b30..228e44d35 100644 --- a/apps/messages/metadata.json +++ b/apps/messages/metadata.json @@ -1,7 +1,7 @@ { "id": "messages", "name": "Messages", - "version": "0.32", + "version": "0.33", "description": "App to display notifications from iOS and Gadgetbridge/Android", "icon": "app.png", "type": "app", From 09bd9bb252ace4c8aed40993d38ba06f2dbd33c2 Mon Sep 17 00:00:00 2001 From: sir-indy <53864146+sir-indy@users.noreply.github.com> Date: Wed, 20 Apr 2022 15:15:55 +0100 Subject: [PATCH 56/63] Update widstep.wid.js Looks like reload was never being called, so just read in the important setting at the top of the file. --- apps/widstep/widstep.wid.js | 7 ++----- 1 file changed, 2 insertions(+), 5 deletions(-) diff --git a/apps/widstep/widstep.wid.js b/apps/widstep/widstep.wid.js index 1defcb146..74c5a59ea 100644 --- a/apps/widstep/widstep.wid.js +++ b/apps/widstep/widstep.wid.js @@ -1,4 +1,4 @@ -let wsSettingsGoal = 10000; +let wsSettingsGoal = (require('Storage').readJSON("health.json", 1) || {}).stepGoal || 10000; Bangle.on('step', function(s) { WIDGETS["widstep"].draw(); }); Bangle.on('lcdPower', function(on) { @@ -8,6 +8,7 @@ WIDGETS["widstep"]={area:"tl", sortorder:-1, width:28, draw:function() { if (!Bangle.isLCDOn()) return; // dont redraw if LCD is off var steps = Bangle.getHealthStatus("day").steps; + print('draw', wsSettingsGoal, steps); g.reset(); g.setColor(g.theme.bg); g.fillRect(this.x, this.y, this.x + this.width, this.y + 23); @@ -19,9 +20,5 @@ WIDGETS["widstep"]={area:"tl", sortorder:-1, width:28, var steps_k = (steps/1000).toFixed(1) + 'k'; g.setFont('6x15').drawString(steps_k, this.x+this.width/2, this.y + 10); g.setFont('4x6').drawString('steps', this.x+this.width/2, this.y + 2); - //g.drawRect(this.x, this.y, this.x + this.width, this.y + 23); - }, reload:function() { - wsSettingsGoal = (require('Storage').readJSON("health.json", 1) || {}).stepGoal || 10000; - WIDGETS["widstep"].draw(); } }; From f59f2872e6b2d7beb85b97d7f9f74f903109e898 Mon Sep 17 00:00:00 2001 From: sir-indy <53864146+sir-indy@users.noreply.github.com> Date: Wed, 20 Apr 2022 15:16:19 +0100 Subject: [PATCH 57/63] Update widstep.wid.js Remove stray print statement! --- apps/widstep/widstep.wid.js | 1 - 1 file changed, 1 deletion(-) diff --git a/apps/widstep/widstep.wid.js b/apps/widstep/widstep.wid.js index 74c5a59ea..6ad971af7 100644 --- a/apps/widstep/widstep.wid.js +++ b/apps/widstep/widstep.wid.js @@ -8,7 +8,6 @@ WIDGETS["widstep"]={area:"tl", sortorder:-1, width:28, draw:function() { if (!Bangle.isLCDOn()) return; // dont redraw if LCD is off var steps = Bangle.getHealthStatus("day").steps; - print('draw', wsSettingsGoal, steps); g.reset(); g.setColor(g.theme.bg); g.fillRect(this.x, this.y, this.x + this.width, this.y + 23); From d8bfad06ae46a018c3a7ede4779c52e1345f7782 Mon Sep 17 00:00:00 2001 From: David Peer Date: Wed, 20 Apr 2022 17:03:15 +0200 Subject: [PATCH 58/63] LCARS V0.22 - Fixed alarm and use build in steps function as fallback. --- apps/lcars/ChangeLog | 1 + apps/lcars/README.md | 3 +-- apps/lcars/lcars.app.js | 22 +++++++++++++--------- apps/lcars/metadata.json | 2 +- 4 files changed, 16 insertions(+), 12 deletions(-) diff --git a/apps/lcars/ChangeLog b/apps/lcars/ChangeLog index 9c17376bb..e622feb1f 100644 --- a/apps/lcars/ChangeLog +++ b/apps/lcars/ChangeLog @@ -19,3 +19,4 @@ 0.19: Alarms can not go bigger than 100. 0.20: Use alarm for alarm functionality instead of own implementation. 0.21: Add custom theming. +0.22: Fix alarm and add build in function for step counting. \ No newline at end of file diff --git a/apps/lcars/README.md b/apps/lcars/README.md index 65e31b3cc..6d4b18b9a 100644 --- a/apps/lcars/README.md +++ b/apps/lcars/README.md @@ -1,8 +1,7 @@ # LCARS clock A simple LCARS inspired clock. -Note: To display the steps, the wpedom app is required. To show weather data -such as temperature, humidity or window you BangleJS must be connected +To show weather data such as temperature, humidity or window you BangleJS must be connected with Gadgetbride and the weather app must be installed. To use the timer the "sched" app must be installed on your device. diff --git a/apps/lcars/lcars.app.js b/apps/lcars/lcars.app.js index 3210d6832..aa50fb348 100644 --- a/apps/lcars/lcars.app.js +++ b/apps/lcars/lcars.app.js @@ -1,3 +1,4 @@ +const TIMER_IDX = "lcars"; const SETTINGS_FILE = "lcars.setting.json"; const locale = require('locale'); const storage = require('Storage') @@ -35,7 +36,7 @@ let lcarsViewPos = 0; var plotMonth = false; -function convert24to16(input) +function convert24to16(input) { let RGB888 = parseInt(input.replace(/^#/, ''), 16); let r = (RGB888 & 0xFF0000) >> 16; @@ -171,7 +172,7 @@ Graphics.prototype.setFontAntonioLarge = function(scale) { */ var drawTimeout; function queueDraw() { - + // Faster updates during alarm to ensure that it is // shown correctly... var timeout = isAlarmEnabled() ? 10000 : 60000; @@ -556,17 +557,20 @@ function draw(){ * Step counter via widget */ function getSteps() { + var steps = 0; try{ if (WIDGETS.wpedom !== undefined) { - return WIDGETS.wpedom.getSteps(); + steps = WIDGETS.wpedom.getSteps(); } else if (WIDGETS.activepedom !== undefined) { - return WIDGETS.activepedom.getSteps(); + steps = WIDGETS.activepedom.getSteps(); + } else { + steps = Bangle.getHealthStatus("day").steps; } } catch(ex) { // In case we failed, we can only show 0 steps. } - return 0; + return steps; } @@ -639,7 +643,7 @@ function increaseAlarm(){ var minutes = isAlarmEnabled() ? getAlarmMinutes() : 0; var alarm = require('sched') alarm.setAlarm(TIMER_IDX, { - timer : (minutes+5)*60*1000, + timer : (minutes+5)*60*1000, }); alarm.reload(); } catch(ex){ } @@ -654,9 +658,9 @@ function decreaseAlarm(){ alarm.setAlarm(TIMER_IDX, undefined); if(minutes > 0){ - alarm.setAlarm(TIMER_IDX, { - timer : minutes*60*1000, - }); + alarm.setAlarm(TIMER_IDX, { + timer : minutes*60*1000, + }); } alarm.reload(); diff --git a/apps/lcars/metadata.json b/apps/lcars/metadata.json index 5f3eaa971..40da1b37f 100644 --- a/apps/lcars/metadata.json +++ b/apps/lcars/metadata.json @@ -3,7 +3,7 @@ "name": "LCARS Clock", "shortName":"LCARS", "icon": "lcars.png", - "version":"0.21", + "version":"0.22", "readme": "README.md", "supports": ["BANGLEJS2"], "description": "Library Computer Access Retrieval System (LCARS) clock.", From a02e6d79c4af51639f255d1b5ea79b8de148145e Mon Sep 17 00:00:00 2001 From: David Peer Date: Wed, 20 Apr 2022 17:05:05 +0200 Subject: [PATCH 59/63] Use same data for settings otherwise settings change after first save. --- apps/lcars/lcars.settings.js | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/apps/lcars/lcars.settings.js b/apps/lcars/lcars.settings.js index 2656a54ab..c948c7763 100644 --- a/apps/lcars/lcars.settings.js +++ b/apps/lcars/lcars.settings.js @@ -5,9 +5,9 @@ const storage = require('Storage') let settings = { alarm: -1, - dataRow1: "Battery", - dataRow2: "Steps", - dataRow3: "Temp", + dataRow1: "Steps", + dataRow2: "Temp", + dataRow3: "Battery", speed: "kph", fullscreen: false, themeColor1BG: "#FF9900", @@ -23,7 +23,7 @@ storage.write(SETTINGS_FILE, settings) } - + var dataOptions = ["Steps", "Battery", "VREF", "HRM", "Temp", "Humidity", "Wind", "Altitude", "CoreT"]; var speedOptions = ["kph", "mph"]; var color_options = ['Green','Orange','Cyan','Purple','Red','Blue','Yellow','White']; From 058beeae94fb397e7bfecdc11a5a4d29351b9082 Mon Sep 17 00:00:00 2001 From: David Peer Date: Wed, 20 Apr 2022 17:09:33 +0200 Subject: [PATCH 60/63] Better stability for weather --- apps/lcars/lcars.app.js | 49 +++++++++++++++++++---------------------- 1 file changed, 23 insertions(+), 26 deletions(-) diff --git a/apps/lcars/lcars.app.js b/apps/lcars/lcars.app.js index aa50fb348..590ae56bb 100644 --- a/apps/lcars/lcars.app.js +++ b/apps/lcars/lcars.app.js @@ -579,38 +579,35 @@ function getWeather(){ try { weatherJson = storage.readJSON('weather.json'); + var weather = weatherJson.weather; + + // Temperature + weather.temp = locale.temp(weather.temp-273.15); + + // Humidity + weather.hum = weather.hum + "%"; + + // Wind + const wind = locale.speed(weather.wind).match(/^(\D*\d*)(.*)$/); + var speedFactor = settings.speed == "kph" ? 1.0 : 1.0 / 1.60934; + weather.wind = Math.round(wind[1] * speedFactor); + + return weather + } catch(ex) { // Return default } - if(weatherJson === undefined){ - return { - temp: "-", - hum: "-", - txt: "-", - wind: "-", - wdir: "-", - wrose: "-" - }; - } - - var weather = weatherJson.weather; - - // Temperature - weather.temp = locale.temp(weather.temp-273.15); - - // Humidity - weather.hum = weather.hum + "%"; - - // Wind - const wind = locale.speed(weather.wind).match(/^(\D*\d*)(.*)$/); - var speedFactor = settings.speed == "kph" ? 1.0 : 1.0 / 1.60934; - weather.wind = Math.round(wind[1] * speedFactor); - - return weather + return { + temp: " ? ", + hum: " ? ", + txt: " ? ", + wind: " ? ", + wdir: " ? ", + wrose: " ? " + }; } - /* * Handle alarm */ From 945bc31b366b4693c1c1e07cd2e5aafb412c0637 Mon Sep 17 00:00:00 2001 From: David Peer Date: Wed, 20 Apr 2022 17:15:10 +0200 Subject: [PATCH 61/63] Fix info alignment --- apps/lcars/lcars.app.js | 3 +++ 1 file changed, 3 insertions(+) diff --git a/apps/lcars/lcars.app.js b/apps/lcars/lcars.app.js index 590ae56bb..072eead54 100644 --- a/apps/lcars/lcars.app.js +++ b/apps/lcars/lcars.app.js @@ -291,6 +291,9 @@ function drawInfo(){ return; } + // Draw Infor is called from different sources so + // we have to ensure that the alignment is always the same. + g.setFontAlign(-1, -1, 0); g.setFontAntonioMedium(); g.setColor(color2); g.clearRect(120, 10, g.getWidth(), 75); From f8a2c280fe6c1f8bb42bf4151423ce09606fc1e9 Mon Sep 17 00:00:00 2001 From: David Peer Date: Wed, 20 Apr 2022 17:24:11 +0200 Subject: [PATCH 62/63] Show last healt status for HRM --- apps/lcars/lcars.app.js | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/apps/lcars/lcars.app.js b/apps/lcars/lcars.app.js index 072eead54..92c4e8e7c 100644 --- a/apps/lcars/lcars.app.js +++ b/apps/lcars/lcars.app.js @@ -238,7 +238,7 @@ function _drawData(key, y, c){ value = E.getAnalogVRef().toFixed(2) + "V"; } else if(key == "HRM"){ - value = Math.round(Bangle.getHealthStatus("day").bpm); + value = Math.round(Bangle.getHealthStatus("last").bpm); } else if (key == "TEMP"){ var weather = getWeather(); From 088453d8ce5ffbd0ae8f30d0f3af76ca691d2bf4 Mon Sep 17 00:00:00 2001 From: David Peer Date: Wed, 20 Apr 2022 17:24:50 +0200 Subject: [PATCH 63/63] HRM as default --- apps/lcars/lcars.app.js | 2 +- apps/lcars/lcars.settings.js | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/apps/lcars/lcars.app.js b/apps/lcars/lcars.app.js index 92c4e8e7c..07ca51fd9 100644 --- a/apps/lcars/lcars.app.js +++ b/apps/lcars/lcars.app.js @@ -5,7 +5,7 @@ const storage = require('Storage') let settings = { alarm: -1, dataRow1: "Steps", - dataRow2: "Temp", + dataRow2: "HRM", dataRow3: "Battery", speed: "kph", fullscreen: false, diff --git a/apps/lcars/lcars.settings.js b/apps/lcars/lcars.settings.js index c948c7763..b64feb30e 100644 --- a/apps/lcars/lcars.settings.js +++ b/apps/lcars/lcars.settings.js @@ -6,7 +6,7 @@ let settings = { alarm: -1, dataRow1: "Steps", - dataRow2: "Temp", + dataRow2: "HRM", dataRow3: "Battery", speed: "kph", fullscreen: false,