diff options
-rw-r--r-- | index.html | 19 | ||||
-rw-r--r-- | script.js | 129 | ||||
-rw-r--r-- | styles.css | 94 |
3 files changed, 182 insertions, 60 deletions
@@ -2,7 +2,9 @@ <html lang="en" dir="ltr"> <head> <meta charset="utf-8"> - <meta name="viewport" content="width=device-width, initial-scale=1, shrink-to-fit=no"> + <meta name="viewport" content="width=device-width, initial-scale=1, shrink-to-fit=no,initial-scale=1.0, maximum-scale=1.0, user-scalable=no"> + <meta name="HandheldFriendly" content="true" /> + <title>HOVER:BIT Controller</title> <link rel="canonical" rel="https://jakobst1n.github.io/hoverbit-ble/"> <link rel="stylesheet" type="text/css" href="styles.css"> @@ -10,6 +12,9 @@ <link href="https://fonts.googleapis.com/icon?family=Material+Icons" rel="stylesheet"> <script type="text/javascript" src="microbit.umd.js"></script> + + <link rel="preconnect" href="https://fonts.gstatic.com"> + <link href="https://fonts.googleapis.com/css2?family=Kufam&display=swap" rel="stylesheet"> </head> <body> @@ -18,7 +23,6 @@ <div class="info-device"> <span class="connection"> <i class="material-icons">bluetooth</i> - <span class="connection-status">Disconnected</span> </span> <span class="battery"> <i class="material-icons">battery_std</i> @@ -26,7 +30,6 @@ </span> <span class="arm"> <i class="material-icons">warning</i> - <span class="arm-status">Disarmed</span> </span> <span class="ping"> <i class="material-icons">settings_input_antenna</i> @@ -36,18 +39,20 @@ <div class="options"> <button id="btn_connect">Connect</button> - <button style="display:none;" id="btn_disconnect">Disconnect</button> - <button style="display:none;" id="btn_arm">Arm</button> - <button style="display:none;" id="btn_disarm">Disarm</button> - <button style="display:none;" id="btn_sticky">Sticky controls</button> + <button id="btn_disconnect">Disconnect</button> + <button id="btn_arm">Arm</button> + <button id="btn_disarm">Disarm</button> + <button id="btn_sticky">Sticky controls</button> </div> <div class="throttle"> <div class="throttle-thumb"></div> + <div class="throttle-indicator"></div> </div> <div class="rudder"> <div class="rudder-thumb"></div> + <div class="rudder-indicator"></div> </div> <div class="log"> @@ -8,11 +8,47 @@ let rudderElement = document.querySelector(".rudder"); const hoverControlModule = () => { let _throttle = 0; + let _throttleAcc = 0; let _rudder = 0; + let _rudderAcc = 0; let _arm = false; + let _armAcc = false; + + const acc = (accString) => { + accString.match(/[A-Z][-,0-9]+/g).forEach((item, i) => { + switch (item.substring(0, 1)) { + case "T": + _throttleAcc = parseInt(item.substring(1, item.length)); + document.querySelector(".throttle-indicator").style["bottom"] = _throttleAcc + "%"; + break; + case "R": + _rudderAcc = parseInt(item.substring(1, item.length)); + document.querySelector(".rudder-indicator").style.left = (((_rudderAcc+90) * (100)) / (180)) + "%"; + break; + case "A": + _armAcc = parseInt(item.substring(1, item.length)) == 1; + if (_armAcc) { + document.body.classList.add("armed"); + } else { + document.body.classList.remove("armed"); + } + break; + case "S": + break; + default: + console.log(`Unkown acc: ${item}`); + } + }); + } + + const reset = () => { + setArm(0); + setThrottle(0); + setRudder(0); + } const setThrottle = (throttle) => { - if (!_arm) { return; } + if (!_armAcc) { return; } if (throttle > 100) { throttle = 100; } if (throttle < 0) { throttle = 0; } _throttle = throttle; @@ -22,7 +58,7 @@ const hoverControlModule = () => { const getThrottle = () => _throttle; const setRudder = (rudder) => { - if (!_arm) { return; } + if (!_armAcc) { return; } if (rudder > 90) { rudder = 90; } if (rudder < -90) { rudder = -90; } _rudder = rudder; @@ -48,6 +84,8 @@ const hoverControlModule = () => { const getArm = () => _arm; return { + acc, + reset, setThrottle, getThrottle, setRudder, @@ -59,17 +97,23 @@ const hoverControlModule = () => { let hoverControl = hoverControlModule(); window.onload = () => { - throttleElement.addEventListener('mousedown', on_pointer_hold_throttle,false); - document.body.addEventListener('mouseup', on_pointer_release_throttle, false); - - throttleElement.addEventListener('touchstart', on_pointer_hold_throttle,false); - document.body.addEventListener('touchend', on_pointer_release_throttle, false); - - rudderElement.addEventListener('mousedown', on_pointer_hold_rudder,false); - document.body.addEventListener('mouseup', on_pointer_release_rudder, false); - - rudderElement.addEventListener('touchstart', on_pointer_hold_rudder,false); - document.body.addEventListener('touchend', on_pointer_release_rudder, false); + addEventListener("touchstart", (touch) => { + addEventListener("touchmove", (touch => { + console.log(touch); + }), true); + }, false); + + // throttleElement.addEventListener('mousedown', on_pointer_hold_throttle,false); + // document.body.addEventListener('mouseup', on_pointer_release_throttle, false); + // + // throttleElement.addEventListener('touchstart', on_pointer_hold_throttle,false); + // document.body.addEventListener('touchend', on_pointer_release_throttle, false); + // + // rudderElement.addEventListener('mousedown', on_pointer_hold_rudder,false); + // document.body.addEventListener('mouseup', on_pointer_release_rudder, false); + // + // rudderElement.addEventListener('touchstart', on_pointer_hold_rudder,false); + // document.body.addEventListener('touchend', on_pointer_release_rudder, false); }; function on_pointer_hold_throttle() { @@ -140,20 +184,10 @@ let bDev; document.getElementById("btn_arm").addEventListener("click", () => { hoverControl.setArm(true); - document.querySelector(".arm").classList.add("armed"); - document.querySelector(".arm-status").innerHTML = "ARMED"; - document.querySelector("#btn_sticky").style.display = "block"; - document.querySelector("#btn_disarm").style.display = "block"; - document.querySelector("#btn_arm").style.display = "none"; }); document.getElementById("btn_disarm").addEventListener("click", () => { hoverControl.setArm(false); - document.querySelector(".arm").classList.remove("armed"); - document.querySelector(".arm-status").innerHTML = "DISARMED"; - document.querySelector("#btn_sticky").style.display = "none"; - document.querySelector("#btn_disarm").style.display = "none"; - document.querySelector("#btn_arm").style.display = "block"; }); document.getElementById("btn_sticky").addEventListener("click", () => { @@ -174,21 +208,14 @@ document.getElementById("btn_connect").onclick = async () => { let connCheckInterval = setInterval(() => { if (device) { if (device.gatt.connected) { - document.querySelector("#btn_disconnect").style.display = "block"; - document.querySelector("#btn_connect").style.display = "none"; - - document.querySelector(".info-device").classList.add("connected"); - document.querySelector(".connection-status").innerHTML = "CONNECTED"; + document.body.classList.add("connected"); + // document.querySelector(".connection-status").innerHTML = "CONNECTED"; } else { - hoverControl = hoverControlModule(); - document.querySelector("#btn_sticky").style.display = "none"; - document.querySelector("#btn_disarm").style.display = "none"; - document.querySelector("#btn_arm").style.display = "none"; - document.querySelector("#btn_disconnect").style.display = "none"; - document.querySelector("#btn_connect").style.display = "block"; - document.querySelector(".info-device").classList.remove("connected"); - document.querySelector(".connection-status").innerHTML = "DISCONNECTED"; - clearInterval(connCheckInterval); + hoverControl.reset(); + document.body.classList.remove("connected"); + document.body.classList.remove("armed"); + // document.querySelector(".connection-status").innerHTML = "DISCONNECTED"; + // clearInterval(connCheckInterval); device.gatt.disconnect(); } } else { @@ -199,18 +226,15 @@ document.getElementById("btn_connect").onclick = async () => { }, 500); if (device) { - hoverControl = hoverControlModule(); + hoverControl.reset(); const services = await microbit.getServices(device); - document.querySelector("#btn_arm").style.display = "block"; - document.querySelector("#btn_disconnect").addEventListener("click", () => { + hoverControl.setArm(0); + hoverControl.setThrottle(0); + hoverControl.setRudder(0); + device.gatt.disconnect(); - document.querySelector("#btn_sticky").style.display = "none"; - document.querySelector("#btn_disarm").style.display = "none"; - document.querySelector("#btn_arm").style.display = "none"; - document.querySelector("#btn_disconnect").style.display = "none"; - document.querySelector("#btn_disconnect").onclick = null; }); if (services.deviceInformationService) { @@ -223,8 +247,17 @@ document.getElementById("btn_connect").onclick = async () => { var newone = elm.cloneNode(true); elm.parentNode.replaceChild(newone, elm); - document.querySelector(".battery-status").innerHTML = event.detail + "mV"; - // console.log(event); + if ((event.detail).indexOf(":") != -1) { + let parts = (event.detail).split(":"); + if (parts[0] == "B") { + document.querySelector(".battery-status").innerHTML = parts[1] + "mV"; + } else if (parts[0] == "ACC") { + console.log(parts[1]); + hoverControl.acc(parts[1]); + } else { console.log(parts); } + } else { + console.log(`Received unknown: ${event.detail}`); + } }); let sendCommands = setInterval(async() => { @@ -238,7 +271,7 @@ document.getElementById("btn_connect").onclick = async () => { ":"; await services.uartService.sendText(command); } else { - clearInterval(sendCommands); + // clearInterval(sendCommands); device.gatt.disconnect(); } } @@ -5,6 +5,7 @@ html, body { height: 100%; */ font-family: monospace; overflow: hidden; + font-family: 'Kufam', cursive; } body { @@ -22,15 +23,25 @@ body { } .info-device i { - font-size: 15px; + font-size: 18px; } .connection { display: flex; - align-items: center; + align-items: flex-start; color: #c32222; } +.connection:after { + display: block; + content: "DISCONNECTED"; +} + +.connected .connection:after { + display: block; + content: "CONNECTED"; +} + .connected .connection { color: #008000; } @@ -43,7 +54,7 @@ body { display: none; margin-left: 5px; /* display: flex; */ - align-items: center; + align-items: start; color: #4a4a4a; } @@ -55,15 +66,25 @@ body { display: none; margin-left: 5px; /* display: flex; */ - align-items: center; + align-items: start; color: #c32222; } +.arm:after { + content: 'DISARMED'; + display: block; +} + +.armed .arm:after { + content: 'ARMED'; + display: block; +} + .connected .arm { display: flex; } -.arm.armed { +.armed .arm { color: #008000; } @@ -98,6 +119,7 @@ body { } .options button { + display: none; margin-top: 5px; border: 1px solid black; background-color: #b5b5b5; @@ -105,6 +127,16 @@ body { width: 120px; } +.armed .options button { + display: block; +} + +#btn_connect { display: block; } +.connected #btn_connect { display: none; } +.connected #btn_disconnect { display: block; } +.connected #btn_arm { display: block; } +.armed #btn_arm { display: none; } + .throttle { position: absolute; top: 10px; @@ -126,6 +158,32 @@ body { background-color: green; } +.throttle-indicator { + position: absolute; + width: 40px; + height: 0px; + bottom: 0; + /* border: 4px solid black; */ +} + +.throttle-indicator:before { + content: " "; + background-color: black; + width: 20px; + height: 1px; + position: absolute; + left: 0; +} + +.throttle-indicator:after { + content: " "; + background-color: black; + width: 20px; + height: 1px; + position: absolute; + right: 0; +} + .rudder { position: absolute; bottom: 10px; @@ -148,3 +206,29 @@ body { height: 40px; background-color: yellow; } + +.rudder-indicator { + position: absolute; + width: 0px; + height: 40px; + left: 50%; + bottom: 0; +} + +.rudder-indicator:before { + content: " "; + background-color: black; + width: 1px; + height: 20px; + position: absolute; + top: 0; +} + +.rudder-indicator:after { + content: " "; + background-color: black; + width: 1px; + height: 20px; + position: absolute; + bottom: 0; +} |