Skip to content

Instantly share code, notes, and snippets.

@saper-2
Created October 30, 2019 23:51
Show Gist options
  • Save saper-2/e5491caf993999bbc509dedfba29679c to your computer and use it in GitHub Desktop.
Save saper-2/e5491caf993999bbc509dedfba29679c to your computer and use it in GitHub Desktop.
Jak sie dogadac z tasmota przez http
<html>
<head>
<meta charset="UTF-8"> <!-- kodowanie UTF-8 tego pliku teksotwego -->
<!-- sciągnij z https://jquery.com/download/ najnowszy "compressed, production jQuery x.y.z" ,
wrzuć sciągnięty plik 'jquery-x.y.z.min.js' do tego samego katalogu co ten plik html.
Ah, jak klikniesz "Download ...." to otworzy się strona z "tekstem" - po prostu uzyj Plik->Zapisz aby zapisać 'jquery-x.y.z.min.js' :)
Dla innych ludzi którzy dotrą do tego :) : popraw wersję jquery jak będziesz ściągał ("x.y.z" to będzie numer wersji) w tagu poniżej "script src=...."
-->
<script type="text/javascript" src="jquery-3.4.1.min.js"></script>
<script>
var images = [
// off
"data:image/png;base64, iVBORw0KGgoAAAANSUhEUgAAACIAAAAiCAYAAAA6RwvCAAAAAXNSR0IArs4c6QAAAARnQU1BAACxjwv8YQUAAAAJcEhZcwAADsMAAA7DAcdvqGQAAAAYdEVYdFNvZnR3YXJlAHBhaW50Lm5ldCA0LjEuNWRHWFIAAAKLSURBVFhHzZituqMwEIbPxdWgUKgoFAZVhUJVYaqiuIAqVA2qCoVCYapQqKqqVd8OCbQEJkB/nt0jXsHkm8w0TMKkPwB+BaxxK21bo8hz5JcKTduSiddtgTXauBYpDoEHZ7fDzobjwt9LnKvXEmONU5pzDOEwQddwQ8hiW0Ks8UGTI/aYAC/iBBLljWbkYvSwxo7bJYbHTPo+PmT9h6bm47HGex4t18HbCBwtycwMKOOVJBwIKsasqElu+tZUzEkoVvwF5LVzNX2NB9xzRAtF6cVnko30Nm4lZOCycyiEJJnpYzyUscM70q9IqjtJTOc1miy0ro5/MnfT07FN4TMOtqXcirXenAi5+m1a93AoLKsRZq+vxJQq8di5/fS5Kr24QMzVhp8+hJ9hmX9UK1po2Snh+fPVGLhKMZu/O1tO/UGnRA0roneoNPzEL3OVELMYO0Q6iE4kj+aCnX9Sgu9Rsq9H6J2wkIhOdTLZZ0gxj+MmFQ39gkSGOErwPxMxXg17onpHJfgeF0TTGISQDQ33idxO/kww3lpfoUrgzmI4iEsapXEtsmyt8cn3KfzJHUIfVUMiqHHkOjH6HlxG34O3aU/8dyx8fs0f4jblXg+1eV8oWna3dK+loNFe83RY6EWGyn6HPLK0FpOexHBq2aLViERVlaFfI9vbmqNnkQ4Yjh38Mva4wabrwZWuH0uNtxNdSGb6GA+KlXZR4XgI9gnS7pY3kEkcQn+lXyWYNrFjZlA0GcK1ZN5BJNAd5zzmzPDgTs3MFy5XA06QQt8kmFgEaxxTyoA5EV/BQ3zWx/gSrHHGrUYWr91XprgIDhuvHwRrXEJdovYBPHd6PjhwXR/h4fV/AjpY478HP38BbMa1la/cOikAAAAASUVORK5CYII=",
// on
"data:image/png;base64, iVBORw0KGgoAAAANSUhEUgAAACIAAAAiCAYAAAA6RwvCAAAAAXNSR0IArs4c6QAAAARnQU1BAACxjwv8YQUAAAAJcEhZcwAADsMAAA7DAcdvqGQAAAAYdEVYdFNvZnR3YXJlAHBhaW50Lm5ldCA0LjEuNWRHWFIAAACySURBVFhH7dghDsJAFIThHm5NFaoKVdUroKpW4fcMVaiaHgBVVcUVqjgA6rGBpCHTSfYFQRAjPjP7xK+3MrOvPdbFxhQtptFu97yQGy86uixna0KwsOnssuYXdutAR4+h/Yx4q/s5P/H7Ejp6pOM+JJym/MTvS+jooRCkEKQQpBCkEKQQpBCkEKQQpBCkEKQQpBD0NyFzX+9C2uH1HUDvS+joNXSHLaKJ1zzxOw86/p5VTyt4wvYCakmwAAAAAElFTkSuQmCC",
// toggle
"data:image/png;base64, iVBORw0KGgoAAAANSUhEUgAAACIAAAAiCAYAAAA6RwvCAAAAAXNSR0IArs4c6QAAAARnQU1BAACxjwv8YQUAAAAJcEhZcwAADsMAAA7DAcdvqGQAAAAYdEVYdFNvZnR3YXJlAHBhaW50Lm5ldCA0LjEuNWRHWFIAAAKvSURBVFhHzZetlrMwEIZ7cRhUFCoKhYmqQqGqMFVRXEAVqgaFqlpVVVPFBaxCVc1O+Ck/eUOB/c6eTzx7tpN3JkMyk8CBiHZzKwoqeso7m7BuDdDo4padKAp88jxvET9UlObbEoPGOddEkg8m/IwgpW8cAscdA409VZFQACfYiB+RvtccEs9jgEZDmQQ46C8I9YND4/mgsYg/18FeZIprxzKUK5IQUUI6t/e+zFJS8rO/1E/Ld/KjLuLFogySnGXTAIhXVdI5EjBGi6Rzk8vgMwSoS4p95GSQlH59s2xwXEOVK/eDSc2SQfv+53F2FaekdiUHp57i3damTfHeL62yug6d9HZI4Gr4FBe47VDi48Bjnlpa2obgzMOtpvlTXxUU+nHxFs7R0tZ7W/W8km0TdYlcFRK5t8SwNRG6JXCLRNfOjQhuS3hpBC42J8LAebqiPVClSc4HmaDtLxjQsCeRIgY+XkxlI3ie4X3SxrSD9exJBBetopxr/EDcXvbgXybS1uKByv8lkSeuEWXWaxZozK5E4KEZk/Hioz0nZQ3yGZJ88bAdrGdPIpcQ+IiUh7r2hUE7gYvNiTge2FPtRdqI7im6Kd3Hu2FrIq5jPry0l2krfOAW9gL3qsBljs2JAPSu1fBCavPoE2EyFJhx3Tc1d9v0yHZfCXD1mHHst3jpuna93n0/ckrjmOKTprJ6scnW5Mr1xjZNfOaEHFpElLFk0K7h7Fhlw7wrJ45UFwtvaYaAjtpRByPyU0gC+neA2pv8aHAccHN8EZIy29JzjChYfIgeXEuTHz01vzv8kw8ri9BZ0Jah5/XIKFr1hCsJ+CivODKYywCNY66//uITFOnl68IAjXPMd4o+bv0Q90mu/A4yQOMS9zKj1BSmELPEfBJNAaeU3ZpCgP4uoPHvocMPLKszn7THokoAAAAASUVORK5CYII="
];
//http://<espeasyip>/control?cmd=<command>
// globalne zmienne
// adres espEasy
var espip = "192.168.2.155";
function get_power_status(ip) {
// sprawdzmy czy argumenty nie są "null" (czyli funkcja zostałą wywołana bez przekazanych argumentów)
if (typeof(ip) === "undefined") return;
// dodatkowe sprawdzenie
// ajax request
// zwróć uwagę na sposób zapisu funkcji które są wywoływane po request'cie
$.ajax({
url: "http://"+ip+"/cm?cmnd=Power0",
dataType: "json" // spodziewamy się odpowiedzi w fomracie json
}) // <<-- tutaj nie ma średnika, ponieważ chcemy aby zostały wywołane funkcje w done lub fail :)
// to jest wywoływane jeśli request się udał (http result code = 200)
.done(function(data) {
// ustawmy zawartość tagu ze statusem
// debug, uzyteczne jak nie jestes pewien co dostajesz :) , mozesz uzyc Developers Tools i tam krok po kroku
// analizować skrypt JS i podglądać jakie są dane w jakich zmiennych ^u^
//console.log("Status led: ");
//console.log(data);
if (typeof(data.POWER1) != "undefined") update_relay_status(1, data.POWER1); else update_relay_status(1, "?");
if (typeof(data.POWER2) != "undefined") update_relay_status(2, data.POWER2); else update_relay_status(2, "?");
if (typeof(data.POWER3) != "undefined") update_relay_status(3, data.POWER3); else update_relay_status(3, "?");
if (typeof(data.POWER4) != "undefined") update_relay_status(4, data.POWER4); else update_relay_status(4, "?");
})
// jeśli będzie jakiś błąd (e.g. brak urządzenia , zły IP, etc...) to to się wykona:
.fail(function(jqxhr, text, err) {
console.log("AJAX query error! text="+text+" , error="+err);
console.log(jqxhr);
$("#led-status").html("ERROR: "+text);
// zmieniamy kolor :)
$("#led-status").css("background-color","#ff4000");
})
; // tutaj jest koniec definicji .ajax(.........)
}
function get_sensor_bme280(ip) {
// sprawdzmy czy argumenty nie są "null" (czyli funkcja zostałą wywołana bez przekazanych argumentów)
if (typeof(ip) === "undefined") return;
// dodatkowe sprawdzenie
// ajax request
// zwróć uwagę na sposób zapisu funkcji które są wywoływane po request'cie
$.ajax({
url: "http://"+ip+"/cm?cmnd=Status 8",
dataType: "json" // spodziewamy się odpowiedzi w fomracie json
}) // <<-- tutaj nie ma średnika, ponieważ chcemy aby zostały wywołane funkcje w done lub fail :)
// to jest wywoływane jeśli request się udał (http result code = 200)
.done(function(data) {
// ustawmy zawartość tagu ze statusem
// debug, uzyteczne jak nie jestes pewien co dostajesz :) , mozesz uzyc Developers Tools i tam krok po kroku
// analizować skrypt JS i podglądać jakie są dane w jakich zmiennych ^u^
//console.log("Status led: ");
//console.log(data);
if (typeof(data.StatusSNS) != "undefined") {
update_sensor_data(data.StatusSNS);
}
})
// jeśli będzie jakiś błąd (e.g. brak urządzenia , zły IP, etc...) to to się wykona:
.fail(function(jqxhr, text, err) {
console.log("AJAX query error! text="+text+" , error="+err);
console.log(jqxhr);
$("#led-status").html("ERROR: "+text);
// zmieniamy kolor :)
$("#led-status").css("background-color","#ff4000");
})
; // tutaj jest koniec definicji .ajax(.........)
}
function update_sensor_data(sns) {
if (typeof(sns.BME280) == "undefined") {
//alert("No BME280 data!");
$("#sens_time").html("!!:!!");
$("#temp").html("!!.!");
$("#humi").html("!!.!");
$("#press").html("!!!");
return;
}
$("#sens_time").html(sns.Time);
$("#temp").html(sns.BME280.Temperature);
$("#humi").html( sns.BME280.Humidity);
$("#press").html(sns.BME280.Pressure);
}
// aktualizuj stan w oknie przeglądarki
// state: ON, OFF, CHANGE, ERROR, ?
function update_relay_status(rl_num, state) {
if (typeof(rl_num) === "undefined") { console.log("rl_num - indefined."); return; }
if (typeof(state) === "undefined") { console.log("state - indefined."); return; }
// sprawdź czy rl_num w zakresie (relay1..4)
if (rl_num < 1 || rl_num > 4) { console.log("rl_num ("+rl_num+") out of range!"); return; }
// on
if (state == "ON") {
$("#srl"+rl_num)
.html("&nbsp;<img style='height: 14px' src='"+images[1]+"'/>&nbsp;")
//.html("&#x23FD;") // unicode v9.0 , symbol: &#x23FD; "Power on" - seems not supported in FF 60.9
.css("background-color","#79ff4c")
.attr("title",rl_num+": On")
;
// off
} else if (state == "OFF") {
$("#srl"+rl_num)
.html("&#x2B58;")
.css("background-color","#ff9673")
.attr("title",rl_num+": Off")
;
} else if (state == "CHANGE") {
$("#srl"+rl_num)
.html("&#128472;")
.css("background-color","#99ccff")
.attr("title",rl_num+": Changing")
;
} else if (state == "ERROR") {
$("#srl"+rl_num)
.html("&#9888;")
.css("background-color","#ff4000")
.attr("title",rl_num+": Error!")
;
} else if (state == "Blink ON") {
$("#srl"+rl_num)
.html("&#9728;")
.css("background-color","#ff73ff")
.attr("title",rl_num+": Blink on!")
;
} else if (state == "Blink OFF") {
$("#srl"+rl_num)
.html("&#128711;")
.css("background-color","#b973ff")
.attr("title",rl_num+": Blink off!")
;
// unknown
} else {
$("#srl"+rl_num)
.html("&#11217;")
.css("background-color","#ffff26")
.attr("title",rl_num+": Bump, unknown: "+state)
;
}
}
// ustaw stan przekaźnika
// state: 0=OFF, 1=ON, 2=Toggle, 3=Blink on, 4=Blink off
function set_power_status(ip,rl,state) {
// sprawdzmy czy argumenty nie są "null" (czyli funkcja zostałą wywołana bez przekazanych argumentów)
if (typeof(rl) === "undefined") return;
if (typeof(ip) === "undefined") return;
if (typeof(state) === "undefined") return;
// dodatkowe sprawdzenie
if (state < 0 || state > 4) return;
if (!Number.isInteger(rl)) {
alert("rl nie jest liczbą!");
return;
}
if (rl<1 || rl>4) {
alert("rl ("+rl+") poza zakresem!");
return;
}
// zmień ikonkę na "zmianę"
update_relay_status(rl,"CHANGE");
// ajax request - praktycznie kopiuj-wklej z "get_status" :)
// zwróć uwagę na sposób zapisu funkcji które są wywoływane po request'cie
$.ajax({
url: "http://"+ip+"/cm?cmnd=Power"+rl+" "+state, // dodajemy state do url :)
dataType: "json" // spodziewamy się odpowiedzi w fomracie json
})
// to jest wywoływane jeśli request się udał (http result code = 200)
.done(function(data) {
// ustawmy zawartość tagu span ze statusem
// debug, uzyteczne jak nie jestes pewien co dostajesz :) , mozesz uzyc Developers Tools i tam krok po kroku
// analizować skrypt JS i podglądać jakie są dane w jakich zmiennych ^u^
//console.log("Status led: ");
//console.log(data);
// aktualizacja tag'a ze stanem
update_relay_status(rl,data["POWER"+rl]);
})
// jeśli będzie jakiś błąd (e.g. brak urządzenia , zły IP, etc...) to to się wykona:
.fail(function(jqxhr, text, err) {
console.log("AJAX query error! text="+text+" , error="+err);
console.log(jqxhr);
update_relay_status(rl,"ERROR");
})
; // tutaj jest koniec definicji .ajax(.........)
}
// load all statuses
function getstatuses() {
get_sensor_bme280(espip);
get_power_status(espip);
}
// i kolejny fajny "feature" z jQuery, możemy wywołać z łatwością funkcję po pełnym załądowaniu dokumentu :) (bez uzycia body onload=....)
// mozna to zadeklarować w różnych miejscach i wiele razy wywołując inne funkcje
$(document).ready(function() {
//ledstatus(); // (^o^)
// kolejny pięknie brutalny feature jQuery :D
// - "przypinamy" jedną funkcję na kliknięcie dowolnego buttona w obrębie <form>
// , i wyciągamy z klikniętego elementu data-id i -state ktore definiują zachowanie buttona :D
// zawęzamy przypięcie event'u do button'ów (tag <input> z type=`button`) znajdujących w tagu <form> z name="control" :
$("form[name=control] input[type=button]").click(function(e) {
// wyiągamy id i state
var id = $(this).data("id");
var state = $(this).data("state");
//console.log("id="+id+";state="+state);
// i sterujemy tasmotą :)
set_power_status(espip,id, state);
// zabezpieczenie aby przeglądarka przypadkiem nie spróbowała wysłać formularza
e.preventDefault();
return false;
});
get_sensor_bme280(espip);
get_power_status(espip);
});
</script>
<style type="text/css">
.rl-state {
min-width: 30px;
line-height: 24px;
font-size: 18px;
display: inline-block;
text-align: center;
}
#temp, #humi, #press {
font-family: monospace;
font-size: 18px;
}
</style>
</head>
<body>
<!-- STatus led'a -->
<div style="line-height: 35px;">
Status 1 2 3 4:
<span class="rl-state" style="background-color: #ffff26;" id="srl1">?</span>&nbsp;
<span class="rl-state" style="background-color: #ffff26;" id="srl2">?</span>&nbsp;
<span class="rl-state" style="background-color: #ffff26;" id="srl3">?</span>&nbsp;
<span class="rl-state" style="background-color: #ffff26;" id="srl4">?</span>
</div>
<div style="line-height: 35px;">
<b>Sensor BME280: </b><span id="temp">--.-</span>&#8451; &nbsp; <span id="humi">--.-</span>% &nbsp; <span id="press">---</span>&#13169; &nbsp; <span style="font-size: 10px">&#9202;:<span id="sens_time">--:--</span></span>
</div>
<!-- input'y pownny być w form tagu, onsubmit=return false - zapobiega wysłaniu formularza -->
<form name="control" onsubmit="return false;">
<div>Relay 1:
<input type="button" data-id="1" data-state="1" value="ON">
<input type="button" data-id="1" data-state="0" value="OFF">
<input type="button" data-id="1" data-state="2" value="Toggle">
<input type="button" data-id="1" data-state="3" value="Blink ON">
<input type="button" data-id="1" data-state="4" value="Blink OFF">
</div>
<div>Relay 2:
<input type="button" data-id="2" data-state="1" value="ON">
<input type="button" data-id="2" data-state="0" value="OFF">
<input type="button" data-id="2" data-state="2" value="Toggle">
<input type="button" data-id="2" data-state="3" value="Blink ON">
<input type="button" data-id="2" data-state="4" value="Blink OFF">
</div>
<div>Relay 3:
<input type="button" data-id="3" data-state="1" value="ON">
<input type="button" data-id="3" data-state="0" value="OFF">
<input type="button" data-id="3" data-state="2" value="Toggle">
<input type="button" data-id="3" data-state="3" value="Blink ON">
<input type="button" data-id="3" data-state="4" value="Blink OFF">
</div>
<div>Relay 4:
<input type="button" data-id="4" data-state="1" value="ON">
<input type="button" data-id="4" data-state="0" value="OFF">
<input type="button" data-id="4" data-state="2" value="Toggle">
<input type="button" data-id="4" data-state="3" value="Blink ON">
<input type="button" data-id="4" data-state="4" value="Blink OFF">
</div>
<br />
<br />
<input type="button" value="Status" onClick="getstatuses();">
<br />
<br />
<b>Tasmota Template:</b>
<pre>{"NAME":"test-tasmota","GPIO":[90,0,18,0,6,5,0,0,24,23,29,21,56],"FLAG":0,"BASE":18}</pre>
</body>
</html>
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment