forked from marva/sumorobot-web
remove multiple robots and remote control from control panel
This commit is contained in:
parent
6fc62fad71
commit
aaed346a9a
39
index.html
39
index.html
@ -6,6 +6,7 @@
|
||||
<link rel="stylesheet" href="styles.css">
|
||||
<link rel="stylesheet" href="bootstrap.min.css">
|
||||
<link rel="shortcut icon" type="image/png" href="logo.png"/>
|
||||
<link href="https://fonts.googleapis.com/css?family=Orbitron" rel="stylesheet">
|
||||
<script src="jquery.min.js" type="text/javascript" charset="utf-8"></script>
|
||||
<script src="bootstrap.min.js" type="text/javascript" charset="utf-8"></script>
|
||||
<script src="blockly_compressed.js" type="text/javascript" charset="utf-8"></script>
|
||||
@ -24,35 +25,11 @@
|
||||
RoboKoding logo
|
||||
</object>
|
||||
<div class="input-group">
|
||||
<span class="input-group-addon robot-nr">1</span>
|
||||
<input type="text" class="form-control robot-id" placeholder="ID" />
|
||||
<span class="input-group-addon addon-no-border robot-nr">2</span>
|
||||
<input type="text" class="form-control robot-id" placeholder="ID" />
|
||||
<span class="input-group-addon addon-no-border robot-nr">3</span>
|
||||
<input type="text" class="form-control robot-id" placeholder="ID" />
|
||||
<span class="input-group-addon addon-no-border robot-nr">4</span>
|
||||
<input type="text" class="form-control robot-id" placeholder="ID" />
|
||||
<span class="input-group-addon addon-no-border robot-nr">5</span>
|
||||
<input type="text" class="form-control robot-id" placeholder="ID" />
|
||||
<span class="input-group-addon" id="robot-label">robot name</span>
|
||||
<input type="text" class="form-control" id="robot-id" placeholder="sumo-ID" />
|
||||
</div>
|
||||
<div class="btn-group btn-group-justified btn-group-robot" role="group" aria-label="robots">
|
||||
<a href="#" class="btn btn-lg btn-robot-nr">1</a>
|
||||
<a href="#" class="btn btn-lg btn-robot-nr">2</a>
|
||||
<a href="#" class="btn btn-lg btn-robot-nr">3</a>
|
||||
<a href="#" class="btn btn-lg btn-robot-nr">4</a>
|
||||
<a href="#" class="btn btn-lg btn-robot-nr">5</a>
|
||||
<a href="#" class="btn btn-lg btn-robot-add">+</a>
|
||||
</div>
|
||||
<div class="remote-label">
|
||||
<div class="btn-group form-check-label" data-toggle="buttons">
|
||||
<label class="btn btn-primary active" id="remote-disabled">
|
||||
<input type="radio" name="remote" autocomplete="off" checked> Disabled
|
||||
</label>
|
||||
<label class="btn btn-primary" id="remote-enabled">
|
||||
<input type="radio" name="remote" autocomplete="off"> Enabled
|
||||
</label>
|
||||
</div>
|
||||
Remote control
|
||||
<div class="btn-group btn-group-robot" role="group" aria-label="robots">
|
||||
<a href="#" class="btn btn-lg btn-robot-go">GO!</a>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
@ -84,9 +61,9 @@
|
||||
<block type="sumorobot_line"></block>
|
||||
</xml>
|
||||
|
||||
<div class="btn-group btn-group-justified btn-group-control">
|
||||
<a href="#" class="btn btn-lg btn-success btn-start">Start</a>
|
||||
<a href="#" class="btn btn-lg btn-danger btn-stop">Stop</a>
|
||||
<div class="btn-group d-flex btn-group-control" role="group">
|
||||
<a href="#" class="btn btn-lg btn-success btn-start w-100">Start</a>
|
||||
<a href="#" class="btn btn-lg btn-danger btn-stop w-100">Stop</a>
|
||||
</div>
|
||||
</body>
|
||||
</html>
|
||||
|
112
styles.css
112
styles.css
@ -1,15 +1,12 @@
|
||||
html, body {
|
||||
height: 100%;
|
||||
font-family: "Orbitron" !important;
|
||||
}
|
||||
body {
|
||||
overflow: hidden;
|
||||
background-color: #fff;
|
||||
font-family: sans-serif;
|
||||
}
|
||||
/* logo object */
|
||||
object.logo {
|
||||
width: 45%;
|
||||
}
|
||||
/* the whole interface is in the table */
|
||||
table.blockly-table {
|
||||
height: 95%;
|
||||
@ -21,47 +18,25 @@ span.has-error {
|
||||
border-color: #a94442 !important;
|
||||
background-color: #f2dede !important;
|
||||
}
|
||||
span.addon-no-border {
|
||||
border-left: 0px !important;
|
||||
border-right: 0px !important;
|
||||
}
|
||||
span.input-group-addon {
|
||||
padding: 0.5vw 1vw !important;
|
||||
}
|
||||
/* form items */
|
||||
label.btn-primary {
|
||||
border-width: 3px !important;
|
||||
}
|
||||
input.form-control {
|
||||
padding: 0.5vw 1vw !important;
|
||||
}
|
||||
input.has-error {
|
||||
border-color: #a94442 !important;
|
||||
}
|
||||
/* buttons */
|
||||
a.btn-robot-nr, a.btn-robot-add {
|
||||
font-size: 10vw !important;
|
||||
border: 3px solid rgba(0, 0, 0, 0.1) !important;
|
||||
/* robot connect button */
|
||||
a.btn-robot-go, a.btn-robot-go:hover {
|
||||
color: #3768d8;
|
||||
}
|
||||
a.btn-robot-add {
|
||||
opacity: 0.5;
|
||||
}
|
||||
a.btn-selected {
|
||||
border-color: #fc3 !important;
|
||||
}
|
||||
a.btn-success {
|
||||
/* start code button */
|
||||
a.btn-start {
|
||||
border-width: 3px !important;
|
||||
border-color: #4cae4c !important;
|
||||
background-color: #44CC00 !important;
|
||||
}
|
||||
a.btn-danger {
|
||||
/* stop code button */
|
||||
a.btn-stop {
|
||||
border-width: 3px !important;
|
||||
border-color: #d43f3a !important;
|
||||
background-color: #b80000 !important;
|
||||
}
|
||||
a.btn-danger.disabled {
|
||||
background-color: #ee4d4d !important;
|
||||
}
|
||||
.btn:hover, .btn.hover {
|
||||
border-width: 3px;
|
||||
border-color: #fc3 !important;
|
||||
@ -70,18 +45,9 @@ a.btn-danger.disabled {
|
||||
.goog-menuitem-content {
|
||||
font-size: 2em !important;
|
||||
}
|
||||
/* remote control enabler container */
|
||||
div.form-check-label {
|
||||
font-size: 5vw;
|
||||
}
|
||||
/* remote control enabler label container */
|
||||
div.remote-label {
|
||||
font-size: 4vw;
|
||||
margin-top: 1vw;
|
||||
font-weight: bold;
|
||||
}
|
||||
/* start and stop button group */
|
||||
div.btn-group-control {
|
||||
width: 100%;
|
||||
z-index: 35;
|
||||
bottom: 0px;
|
||||
position: fixed !important;
|
||||
@ -115,27 +81,87 @@ div#stream {
|
||||
}
|
||||
/* for mobile and tablet screen */
|
||||
@media screen and (max-width: 1000px) {
|
||||
/* logo object */
|
||||
object.logo {
|
||||
width: 100%;
|
||||
}
|
||||
/* control panel robot name input */
|
||||
div.input-group {
|
||||
width: 100%;
|
||||
margin-left: auto;
|
||||
margin-right: auto;
|
||||
}
|
||||
span.input-group-addon {
|
||||
font-size: 7vw;
|
||||
padding: 0.5vw 0.5vw !important;
|
||||
}
|
||||
input.form-control {
|
||||
font-size: 7vw;
|
||||
padding: 0.5vw 0.5vw !important;
|
||||
}
|
||||
/* robot connect button */
|
||||
div.btn-group-robot {
|
||||
width: 100%;
|
||||
}
|
||||
a.btn-robot-go {
|
||||
width: 100%;
|
||||
font-size: 30vw !important;
|
||||
border: 3px solid rgba(0, 0, 0, 0.1) !important;
|
||||
}
|
||||
/* Blockly workspace */
|
||||
td#blocklyArea {
|
||||
width: 100%;
|
||||
height: 100%;
|
||||
}
|
||||
/* Blockly code area */
|
||||
td#blocklyCodeArea {
|
||||
display: none;
|
||||
}
|
||||
/* ace editor */
|
||||
div#blocklyCode {
|
||||
display: none;
|
||||
}
|
||||
}
|
||||
/* for desktop screen */
|
||||
@media screen and (min-width: 768px) {
|
||||
/* logo object */
|
||||
object.logo {
|
||||
width: 45%;
|
||||
}
|
||||
/* control panel robot name input */
|
||||
div.input-group {
|
||||
width: 35%;
|
||||
margin-left: auto;
|
||||
margin-right: auto;
|
||||
}
|
||||
span.input-group-addon {
|
||||
font-size: 2vw;
|
||||
padding: 0.5vw 0.5vw !important;
|
||||
}
|
||||
input.form-control {
|
||||
font-size: 2vw;
|
||||
padding: 0.5vw 0.5vw !important;
|
||||
}
|
||||
/* robot connect button */
|
||||
div.btn-group-robot {
|
||||
width: 35%;
|
||||
}
|
||||
a.btn-robot-go {
|
||||
width: 100%;
|
||||
font-size: 10vw !important;
|
||||
border: 3px solid rgba(0, 0, 0, 0.1) !important;
|
||||
}
|
||||
/* Blockly workspace */
|
||||
td#blocklyArea {
|
||||
width: 60%;
|
||||
height: 100%;
|
||||
}
|
||||
/* Blockly code area */
|
||||
td#blocklyCodeArea {
|
||||
width: 40%;
|
||||
height: 100%;
|
||||
}
|
||||
/* ace editor */
|
||||
div#blocklyCode {
|
||||
width: 100%;
|
||||
height: 100%;
|
||||
|
135
sumorobot.js
135
sumorobot.js
@ -86,52 +86,24 @@ Sumorobot.prototype.close = function() {
|
||||
this.websocket.close();
|
||||
};
|
||||
|
||||
/* function to set local storage */
|
||||
function getLocalStorageItem(item) {
|
||||
/* when the local storage doesn't exist, return empty string */
|
||||
if (typeof(Storage) === "undefined") return "";
|
||||
/* otherwise return item from the local storage*/
|
||||
return localStorage.getItem(item);
|
||||
}
|
||||
|
||||
/* function to set local storage */
|
||||
function setLocalStorageItem(item, value) {
|
||||
/* when local storage doesn't exist, return */
|
||||
if (typeof(Storage) === "undefined") return;
|
||||
/* otherwise set the item to the local storage */
|
||||
localStorage.setItem(item, value)
|
||||
}
|
||||
|
||||
window.onload = function() {
|
||||
/* function to update the control panel */
|
||||
function updateControlPanel() {
|
||||
/* hide all buttons and text fields */
|
||||
$(".robot-id, .robot-nr, .btn-robot-nr").hide();
|
||||
/* show the first button and text field */
|
||||
$(".robot-id:eq(0), .robot-nr:eq(0), .btn-robot-nr:eq(0)").show();
|
||||
|
||||
/* adjust the buttons and text fields to be in the middle */
|
||||
$(".input-group, .btn-group-robot").css("width", "20%");
|
||||
$(".input-group, .btn-group-robot").css("margin-left", "40%");
|
||||
|
||||
/* hide the robot add button */
|
||||
$(".btn-robot-add").hide();
|
||||
|
||||
/* populate robots IDs and buttons */
|
||||
for (var i = 0; i < 5; i++) {
|
||||
var id = getLocalStorageItem("sumorobot.robotID" + i);
|
||||
if (id) {
|
||||
$(".robot-id:eq(" + i + ")").val(id);
|
||||
$(".robot-id:eq(" + i + "), .robot-nr:eq(" + i + "), .btn-robot-nr:eq(" + i + ")").show();
|
||||
$(".input-group, .btn-group-robot").css("width", 20 + (i * 20) + "%");
|
||||
$(".input-group, .btn-group-robot").css("margin-left", 40 - (i * 10) + "%");
|
||||
} else {
|
||||
/* when no robots yet added */
|
||||
if (i != 0) {
|
||||
/* show the robot add button */
|
||||
$(".btn-robot-add").show();
|
||||
$(".btn-group-robot").css("width", 20 + (i * 20) + "%");
|
||||
$(".input-group, .btn-group-robot").css("margin-left", 40 - (i * 10) + "%");
|
||||
/* add click listener to the robot add button */
|
||||
$(".btn-robot-add").click(function() {
|
||||
$(".robot-id:eq(" + i + "), .robot-nr:eq(" + i + "), .btn-robot-nr:eq(" + i + ")").show();
|
||||
$(".input-group, .btn-group-robot").css("width", 20 + (i * 20) + "%");
|
||||
$(".input-group, .btn-group-robot").css("margin-left", 40 - (i * 10) + "%");
|
||||
$(this).hide();
|
||||
});
|
||||
}
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/* load the control panel */
|
||||
updateControlPanel();
|
||||
|
||||
$("#robot-id").val(getLocalStorageItem("sumorobot.robotId"));
|
||||
/* load ace editor */
|
||||
pythonEditor = ace.edit("blocklyCode");
|
||||
/* set the style */
|
||||
@ -356,22 +328,6 @@ window.onload = function() {
|
||||
onresize();
|
||||
Blockly.svgResize(workspace);
|
||||
|
||||
/* function to set local storage */
|
||||
function getLocalStorageItem(item) {
|
||||
/* when the local storage doesn't exist, return empty string */
|
||||
if (typeof(Storage) === "undefined") return "";
|
||||
/* otherwise return item from the local storage*/
|
||||
return localStorage.getItem(item);
|
||||
}
|
||||
|
||||
/* function to set local storage */
|
||||
function setLocalStorageItem(item, value) {
|
||||
/* when local storage doesn't exist, return */
|
||||
if (typeof(Storage) === "undefined") return;
|
||||
/* otherwise set the item to the local storage */
|
||||
localStorage.setItem(item, value)
|
||||
}
|
||||
|
||||
/* retrieve the blocks */
|
||||
var xml = Blockly.Xml.textToDom(getLocalStorageItem("sumorobot.blockly"));
|
||||
/* resume the blocks */
|
||||
@ -454,23 +410,7 @@ window.onload = function() {
|
||||
case 40: // down
|
||||
if (remoteControl) sumorobot.send("backward");
|
||||
break;
|
||||
case 49: // 1
|
||||
$(".btn-robot-nr:eq(0)").click();
|
||||
break;
|
||||
case 50: // 2
|
||||
$(".btn-robot-nr:eq(1)").click();
|
||||
break;
|
||||
case 51: // 3
|
||||
$(".btn-robot-nr:eq(2)").click();
|
||||
break;
|
||||
case 52: // 4
|
||||
$(".btn-robot-nr:eq(3)").click();
|
||||
break;
|
||||
case 53: // 5
|
||||
$(".btn-robot-nr:eq(4)").click();
|
||||
break;
|
||||
case 67: // c
|
||||
updateControlPanel();
|
||||
$("#panel").toggle();
|
||||
break;
|
||||
case 76: // l
|
||||
@ -505,10 +445,8 @@ window.onload = function() {
|
||||
}
|
||||
break;
|
||||
case 82: // r
|
||||
if (remoteControl)
|
||||
$("#remote-disabled").click();
|
||||
else
|
||||
$("#remote-enabled").click();
|
||||
/* toggle remote control */
|
||||
remoteControl = !remoteControl;
|
||||
break;
|
||||
case 83: // s
|
||||
$(".btn-stop").addClass("hover");
|
||||
@ -536,11 +474,6 @@ window.onload = function() {
|
||||
}
|
||||
});
|
||||
|
||||
/* start button listener */
|
||||
$(".btn-close").click(function() {
|
||||
$("#stream").hide();
|
||||
});
|
||||
|
||||
/* start button listener */
|
||||
$(".btn-start").click(function() {
|
||||
sumostart = true;
|
||||
@ -562,32 +495,18 @@ window.onload = function() {
|
||||
workspace.highlightBlock(lastHighlighted, false);
|
||||
});
|
||||
|
||||
/* remote control enable listener */
|
||||
$("#remote-enabled").click(function() {
|
||||
remoteControl = true;
|
||||
});
|
||||
|
||||
/* remote control disable listener */
|
||||
$("#remote-disabled").click(function() {
|
||||
remoteControl = false;
|
||||
});
|
||||
|
||||
/* robot number button listener */
|
||||
$(".btn-robot-nr").click(function() {
|
||||
$(".btn-robot-go").click(function() {
|
||||
/* extract and validate the selected robot ID */
|
||||
var index = $(".btn-robot-nr").index($(this));
|
||||
var robotID = $(".robot-id:eq(" + index + ")").val();
|
||||
if (robotID.trim() === "") {
|
||||
$(".robot-nr:eq(" + index + "), .robot-id:eq(" + index + ")").addClass("has-error");
|
||||
var robotId = $("#robot-id").val().trim();
|
||||
if (robotId === "" || /^(sumo-[a-f0-9]{6})$/.test(robotId) == false) {
|
||||
$("#robot-id, #robot-label").addClass("has-error");
|
||||
return;
|
||||
} else {
|
||||
$(".robot-nr:eq(" + index + "), .robot-id:eq(" + index + ")").removeClass("has-error");
|
||||
$("#robot-id, #robot-label").removeClass("has-error");
|
||||
}
|
||||
/* highlight the selected robot button */
|
||||
$(".btn-robot-nr").removeClass("btn-selected");
|
||||
$(this).addClass("btn-selected");
|
||||
/* update robot IDs in local storage */
|
||||
setLocalStorageItem("sumorobot.robotID" + index, robotID);
|
||||
setLocalStorageItem("sumorobot.robotId", robotId);
|
||||
/* in case there is a open connection */
|
||||
if (sumorobot && blockHighlight) {
|
||||
/* close the connections */
|
||||
@ -595,9 +514,9 @@ window.onload = function() {
|
||||
blockHighlight.close();
|
||||
}
|
||||
/* connect to the selected robots WebSocket */
|
||||
sumorobot = new Sumorobot("ws://" + robotServer + ":80/p2p/browser/" + robotID + "/");
|
||||
sumorobot = new Sumorobot("ws://" + robotServer + ":80/p2p/browser/" + robotId + "/");
|
||||
/* connect to the other block highlight WebSocket */
|
||||
blockHighlight = new WebSocket("ws://" + robotServer + ":80/p2p/browser/" + robotID + "-highlight/");
|
||||
blockHighlight = new WebSocket("ws://" + robotServer + ":80/p2p/browser/" + robotId + "-highlight/");
|
||||
/* when there is a message from the WebSocket */
|
||||
blockHighlight.onmessage = function(evt) {
|
||||
/* when scope is received */
|
||||
|
Loading…
Reference in New Issue
Block a user