Splitted system config into Web, NTP, GPIO and Debugging

This commit is contained in:
Gunnar Skjold 2020-08-05 13:45:10 +02:00
parent 603f2925ce
commit 6479fd6a63
13 changed files with 450 additions and 180 deletions

1
.gitignore vendored
View File

@ -11,3 +11,4 @@ platformio-user.ini
/src/web/root
/src/AmsToMqttBridge.ino.cpp
/test
/web/test.html

View File

@ -7,4 +7,4 @@ paragraph=HAN support
category=Sensors
url=https://github.com/roarfred/AmsToMqttBridge
architectures=*
depends=Timezone
depends=Timezone,mbedtls

View File

@ -309,6 +309,8 @@ void AmsConfiguration::clearMeter() {
setDistributionSystem(0);
setMainFuse(0);
setProductionCapacity(0);
setMeterEncryptionKey(nullptr);
setMeterAuthenticationKey(nullptr);
setSubstituteMissing(false);
setSendUnknown(false);
}
@ -500,6 +502,16 @@ void AmsConfiguration::setTempSensorPin(uint8_t tempSensorPin) {
}
}
uint8_t AmsConfiguration::getTempAnalogSensorPin() {
return config.tempAnalogSensorPin;
}
void AmsConfiguration::setTempAnalogSensorPin(uint8_t tempAnalogSensorPin) {
if(!pinUsed(tempAnalogSensorPin)) {
config.tempAnalogSensorPin = tempAnalogSensorPin;
}
}
uint8_t AmsConfiguration::getVccPin() {
return config.vccPin;
}
@ -544,12 +556,88 @@ void AmsConfiguration::ackDomoChange() {
domoChanged = false;
}
bool AmsConfiguration::isMdnsEnable() {
return config.mDnsEnable;
}
void AmsConfiguration::setMdnsEnable(bool mdnsEnable) {
config.mDnsEnable = mdnsEnable;
}
bool AmsConfiguration::isNtpEnable() {
return config.ntpEnable;
}
void AmsConfiguration::setNtpEnable(bool ntpEnable) {
if(config.ntpEnable != ntpEnable) {
if(!ntpEnable) {
wifiChanged = true;
} else {
ntpChanged = true;
}
config.ntpEnable = ntpEnable;
}
}
bool AmsConfiguration::isNtpDhcp() {
return config.ntpDhcp;
}
void AmsConfiguration::setNtpDhcp(bool ntpDhcp) {
ntpChanged |= config.ntpDhcp != ntpDhcp;
config.ntpDhcp = ntpDhcp;
}
int32_t AmsConfiguration::getNtpOffset() {
return config.ntpOffset * 10;
}
void AmsConfiguration::setNtpOffset(uint32_t ntpOffset) {
ntpChanged |= config.ntpOffset != ntpOffset/10;
config.ntpOffset = ntpOffset == 0 ? 0 : ntpOffset / 10;
}
int32_t AmsConfiguration::getNtpSummerOffset() {
return config.ntpSummerOffset * 10;
}
void AmsConfiguration::setNtpSummerOffset(uint32_t ntpSummerOffset) {
ntpChanged |= config.ntpSummerOffset != ntpSummerOffset/10;
config.ntpSummerOffset = ntpSummerOffset == 0 ? 0 : ntpSummerOffset / 10;
}
char* AmsConfiguration::getNtpServer() {
return config.ntpServer;
}
void AmsConfiguration::setNtpServer(const char* ntpServer) {
strcpy(config.ntpServer, ntpServer);
}
bool AmsConfiguration::isNtpChanged() {
return ntpChanged;
}
void AmsConfiguration::ackNtpChange() {
ntpChanged = false;
}
void AmsConfiguration::clearNtp() {
setNtpEnable(true);
setNtpDhcp(true);
setNtpOffset(3600);
setNtpSummerOffset(3600);
setNtpServer("pool.ntp.org");
}
void AmsConfiguration::clear() {
clearMeter();
clearWifi();
clearMqtt();
clearAuth();
clearDomo();
clearNtp();
int address = EEPROM_CONFIG_ADDRESS;
@ -863,6 +951,7 @@ void AmsConfiguration::print(Print* debugger)
debugger->printf("Vcc pin: %i\r\n", this->getVccPin());
debugger->printf("Vcc multiplier: %f\r\n", this->getVccMultiplier());
debugger->printf("Vcc offset: %f\r\n", this->getVccOffset());
debugger->printf("Vcc boot limit: %f\r\n", this->getVccBootLimit());
if(this->getDomoELIDX() > 0) {
@ -873,5 +962,13 @@ void AmsConfiguration::print(Print* debugger)
debugger->printf("Domoticz CL1IDX: %i\r\n", this->getDomoCL1IDX());
}
debugger->printf("NTP: %s\r\n", this->isNtpEnable() ? "Yes" : "No");
if(this->isNtpEnable()) {
debugger->printf("NTP offset: %i\r\n", this->getNtpOffset());
debugger->printf("NTP summer offset: %i\r\n", this->getNtpSummerOffset());
debugger->printf("NTP server: %s\r\n", this->getNtpServer());
debugger->printf("NTP DHCP: %s\r\n", this->isNtpDhcp() ? "Yes" : "No");
}
debugger->println("-----------------------------------------------");
}

View File

@ -58,6 +58,17 @@ struct ConfigObject {
uint16_t domoVL2IDX;
uint16_t domoVL3IDX;
uint16_t domoCL1IDX;
bool mDnsEnable;
bool ntpEnable;
bool ntpDhcp;
int16_t ntpOffset;
int16_t ntpSummerOffset;
char ntpServer[64];
uint8_t tempAnalogSensorPin;
int8_t tempSensorInternal; // -128 = disabled, -1 = analog, 0-127 = digital sensor index
uint8_t tempSensorCount;
};
struct ConfigObject82 {
@ -228,6 +239,8 @@ public:
uint8_t getTempSensorPin();
void setTempSensorPin(uint8_t tempSensorPin);
uint8_t getTempAnalogSensorPin();
void setTempAnalogSensorPin(uint8_t tempSensorPin);
uint8_t getVccPin();
void setVccPin(uint8_t vccPin);
double getVccOffset();
@ -254,6 +267,24 @@ public:
bool isDomoChanged();
void ackDomoChange();
bool isMdnsEnable();
void setMdnsEnable(bool mdnsEnable);
bool isNtpEnable();
void setNtpEnable(bool ntpEnable);
bool isNtpDhcp();
void setNtpDhcp(bool ntpDhcp);
int32_t getNtpOffset();
void setNtpOffset(uint32_t ntpOffset);
int32_t getNtpSummerOffset();
void setNtpSummerOffset(uint32_t ntpSummerOffset);
char* getNtpServer();
void setNtpServer(const char* ntpServer);
void clearNtp();
bool isNtpChanged();
void ackNtpChange();
void clear();
protected:
@ -311,12 +342,21 @@ private:
0, // VL1IDX
0, // VL2IDX
0, // VL3IDX
0 // CL1IDX
// 822 bytes
0, // CL1IDX
true, // mDNS
true, // NTP
true, // NTP DHCP
360, // Timezone (*10)
360, // Summertime offset (*10)
"pool.ntp.org", // NTP server
0xFF, // Analog temp sensor
0xFF, // Internal temp sensor
0, // Temp sensor count
// 900 bytes
};
bool wifiChanged, mqttChanged, meterChanged = true, domoChanged;
bool wifiChanged, mqttChanged, meterChanged = true, domoChanged, ntpChanged;
const int EEPROM_SIZE = 1024; // Config size + 4 bytes for config version
const int EEPROM_SIZE = 904; // Config size + 4 bytes for config version
const int EEPROM_CHECK_SUM = 83; // Used to check if config is stored. Change if structure changes
const int EEPROM_CONFIG_ADDRESS = 0;

View File

@ -22,19 +22,7 @@
#include <ArduinoJson.h>
#include <MQTT.h>
#include <DNSServer.h>
// Tz.h does not exist for esp32, need to include time.h, timezone offsets to be given given in sec.
#define NTP_SERVER "pool.ntp.org" // put your local NTP server here
#if defined(ESP8266)
#include <TZ.h>
#define MYTZ TZ_Europe_Oslo
#elif defined(ESP32)
#include <time.h>
#define TZ 1 // (utc+) TZ in hours
#define DST_MN 60 // use 60mn for summer time in some countries
#define GMT_OFFSET_SEC 3600 * TZ // Do not change here...
#define DAYLIGHT_OFFSET_SEC 60 * DST_MN // Do not change here...
#endif
#include <lwip/apps/sntp.h>
#if defined(ESP8266)
ADC_MODE(ADC_VCC);
@ -257,13 +245,11 @@ void setup() {
if(config.hasConfig()) {
if(Debug.isActive(RemoteDebug::INFO)) config.print(&Debug);
if(config.isNtpEnable()) {
configTime(config.getNtpOffset(), config.getNtpSummerOffset(), config.getNtpServer());
sntp_servermode_dhcp(config.isNtpDhcp() ? 1 : 0);
}
WiFi_connect();
#if defined(ESP8266)
configTime(MYTZ, NTP_SERVER);
#elif defined(ESP32)
configTime(GMT_OFFSET_SEC, DAYLIGHT_OFFSET_SEC, NTP_SERVER);
#endif
//sntp_servermode_dhcp(0); // 0: disable obtaining SNTP servers from DHCP (enabled by default)
} else {
if(Debug.isActive(RemoteDebug::INFO)) {
debugI("No configuration, booting AP");
@ -274,6 +260,7 @@ void setup() {
ws.setup(&config, &mqtt);
}
int buttonTimer = 0;
bool buttonActive = false;
unsigned long longPressTime = 5000;
@ -350,6 +337,13 @@ void loop() {
MDNS.addService("http", "tcp", 80);
}
}
if(config.isNtpChanged()) {
if(config.isNtpEnable()) {
configTime(config.getNtpOffset(), config.getNtpSummerOffset(), config.getNtpServer());
sntp_servermode_dhcp(config.isNtpDhcp() ? 1 : 0);
}
config.ackNtpChange();
}
#if defined ESP8266
MDNS.update();
#endif

View File

@ -12,7 +12,9 @@
#include "root/configmqtt_html.h"
#include "root/configweb_html.h"
#include "root/configdomoticz_html.h"
#include "root/configsystem_html.h"
#include "root/ntp_html.h"
#include "root/gpio_html.h"
#include "root/debugging_html.h"
#include "root/restartwait_html.h"
#include "root/boot_css.h"
#include "root/gaugemeter_js.h"
@ -47,7 +49,10 @@ void AmsWebServer::setup(AmsConfiguration* config, MQTTClient* mqtt) {
server.on("/save", HTTP_POST, std::bind(&AmsWebServer::handleSave, this));
server.on("/config-system", HTTP_GET, std::bind(&AmsWebServer::configSystemHtml, this));
server.on("/ntp", HTTP_GET, std::bind(&AmsWebServer::configNtpHtml, this));
server.on("/gpio", HTTP_GET, std::bind(&AmsWebServer::configGpioHtml, this));
server.on("/debugging", HTTP_GET, std::bind(&AmsWebServer::configDebugHtml, this));
server.on("/firmware", HTTP_GET, std::bind(&AmsWebServer::firmwareHtml, this));
server.on("/firmware", HTTP_POST, std::bind(&AmsWebServer::uploadPost, this), std::bind(&AmsWebServer::firmwareUpload, this));
server.on("/upgrade", HTTP_GET, std::bind(&AmsWebServer::firmwareDownload, this));
@ -767,7 +772,7 @@ void AmsWebServer::handleSave() {
}
}
if(server.hasArg("sysConfig") && server.arg("sysConfig") == "true") {
if(server.hasArg("gpioConfig") && server.arg("gpioConfig") == "true") {
// Unset all pins to avoid conflicts if GPIO have been swapped between pins
config->setLedPin(0xFF);
config->setLedPinRed(0xFF);
@ -775,6 +780,7 @@ void AmsWebServer::handleSave() {
config->setLedPinBlue(0xFF);
config->setApPin(0xFF);
config->setTempSensorPin(0xFF);
config->setTempAnalogSensorPin(0xFF);
config->setVccPin(0xFF);
config->setHanPin(server.hasArg("hanPin") && !server.arg("hanPin").isEmpty() ? server.arg("hanPin").toInt() : 3);
@ -786,11 +792,14 @@ void AmsWebServer::handleSave() {
config->setLedRgbInverted(server.hasArg("ledRgbInverted") && server.arg("ledRgbInverted") == "true");
config->setApPin(server.hasArg("apPin") && !server.arg("apPin").isEmpty() ? server.arg("apPin").toInt() : 0xFF);
config->setTempSensorPin(server.hasArg("tempSensorPin") && !server.arg("tempSensorPin").isEmpty() ?server.arg("tempSensorPin").toInt() : 0xFF);
config->setTempAnalogSensorPin(server.hasArg("tempAnalogSensorPin") && !server.arg("tempAnalogSensorPin").isEmpty() ?server.arg("tempAnalogSensorPin").toInt() : 0xFF);
config->setVccPin(server.hasArg("vccPin") && !server.arg("vccPin").isEmpty() ? server.arg("vccPin").toInt() : 0xFF);
config->setVccOffset(server.hasArg("vccOffset") && !server.arg("vccOffset").isEmpty() ? server.arg("vccOffset").toDouble() : 0.0);
config->setVccMultiplier(server.hasArg("vccMultiplier") && !server.arg("vccMultiplier").isEmpty() ? server.arg("vccMultiplier").toDouble() : 1.0);
config->setVccBootLimit(server.hasArg("vccBootLimit") && !server.arg("vccBootLimit").isEmpty() ? server.arg("vccBootLimit").toDouble() : 0.0);
}
if(server.hasArg("debugConfig") && server.arg("debugConfig") == "true") {
config->setDebugTelnet(server.hasArg("debugTelnet") && server.arg("debugTelnet") == "true");
config->setDebugSerial(server.hasArg("debugSerial") && server.arg("debugSerial") == "true");
config->setDebugLevel(server.arg("debugLevel").toInt());
@ -808,6 +817,24 @@ void AmsWebServer::handleSave() {
}
}
if(server.hasArg("ntpConfig") && server.arg("ntpConfig") == "true") {
config->setNtpEnable(server.hasArg("ntpEnable") && server.arg("ntpEnable") == "true");
config->setNtpDhcp(server.hasArg("ntpDhcp") && server.arg("ntpDhcp") == "true");
if(server.hasArg("ntpOffset") && !server.arg("ntpOffset").isEmpty()) {
int offset = server.arg("ntpOffset").toInt();
config->setNtpOffset(offset);
if(server.hasArg("ntpSummerOffset") && !server.arg("ntpSummerOffset").isEmpty()) {
int summerOffset = server.arg("ntpSummerOffset").toInt();
config->setNtpSummerOffset(summerOffset);
} else {
config->setNtpSummerOffset(0);
}
} else {
config->setNtpOffset(0);
}
config->setNtpServer(server.arg("ntpServer").c_str());
}
printI("Saving configuration now...");
if (debugger->isActive(RemoteDebug::DEBUG)) config->print(debugger);
@ -835,13 +862,43 @@ void AmsWebServer::handleSave() {
}
}
void AmsWebServer::configSystemHtml() {
printD("Serving /config-system.html over http...");
void AmsWebServer::configNtpHtml() {
printD("Serving /ntp.html over http...");
if(!checkSecurity(1))
return;
String html = String((const __FlashStringHelper*) CONFIGSYSTEM_HTML);
String html = String((const __FlashStringHelper*) NTP_HTML);
html.replace("${config.ntpEnable}", config->isNtpEnable() ? "checked" : "");
for(int i = (3600*-13); i<(3600*15); i+=3600) {
html.replace("${config.ntpOffset" + String(i) + "}", config->getNtpOffset() == i ? "selected" : "");
}
for(int i = 0; i<(3600*3); i+=3600) {
html.replace("${config.ntpSummerOffset" + String(i) + "}", config->getNtpSummerOffset() == i ? "selected" : "");
}
html.replace("${config.ntpServer}", config->getNtpServer());
html.replace("${config.ntpDhcp}", config->isNtpDhcp() ? "checked" : "");
server.sendHeader("Cache-Control", "no-cache, no-store, must-revalidate");
server.sendHeader("Pragma", "no-cache");
server.setContentLength(html.length() + HEAD_HTML_LEN + FOOT_HTML_LEN);
server.send_P(200, "text/html", HEAD_HTML);
server.sendContent(html);
server.sendContent_P(FOOT_HTML);
}
void AmsWebServer::configGpioHtml() {
printD("Serving /gpio.html over http...");
if(!checkSecurity(1))
return;
String html = String((const __FlashStringHelper*) GPIO_HTML);
#if defined(ESP32)
html.replace("${gpio.max}", "39");
@ -865,6 +922,23 @@ void AmsWebServer::configSystemHtml() {
html.replace("${config.vccMultiplier}", config->getVccMultiplier() > 0 ? String(config->getVccMultiplier(), 2) : "");
html.replace("${config.vccBootLimit}", config->getVccBootLimit() > 0.0 ? String(config->getVccBootLimit(), 1) : "");
server.sendHeader("Cache-Control", "no-cache, no-store, must-revalidate");
server.sendHeader("Pragma", "no-cache");
server.setContentLength(html.length() + HEAD_HTML_LEN + FOOT_HTML_LEN);
server.send_P(200, "text/html", HEAD_HTML);
server.sendContent(html);
server.sendContent_P(FOOT_HTML);
}
void AmsWebServer::configDebugHtml() {
printD("Serving /debugging.html over http...");
if(!checkSecurity(1))
return;
String html = String((const __FlashStringHelper*) DEBUGGING_HTML);
html.replace("${config.debugTelnet}", config->isDebugTelnet() ? "checked" : "");
html.replace("${config.debugSerial}", config->isDebugSerial() ? "checked" : "");
html.replace("${config.debugLevel}", String(config->getDebugLevel()));

View File

@ -65,6 +65,9 @@ private:
void configMqttHtml();
void configWebHtml();
void configDomoticzHtml();
void configNtpHtml();
void configGpioHtml();
void configDebugHtml();
void bootCss();
void gaugemeterJs();
void githubSvg();
@ -73,7 +76,6 @@ private:
void handleSetup();
void handleSave();
void configSystemHtml();
String getSerialSelectOptions(int selected);
void firmwareHtml();
void firmwareUpload();

View File

@ -99,6 +99,13 @@ $(function() {
$(this).next('.custom-file-label').html(fileName);
})
// For NTP
$('#ntpEnable').on('change', function() {
var inputs = $('.ntp-config');
inputs.prop('disabled', !$(this).is(':checked'));
});
$('#ntpEnable').trigger('change');
switch(window.location.pathname) {
case '/config-meter':
$('#config-meter-link').addClass('active');
@ -114,9 +121,9 @@ $(function() {
$('#config-mqtt-link').addClass('active');
break;
case '/config-web':
$('#config-web-link').addClass('active');
break;
case '/config-system':
case '/ntp':
case '/gpio':
case '/debugging':
case '/firmware':
case '/reset':
$('#config-system-link').addClass('active');

View File

@ -1,142 +0,0 @@
<div class="alert alert-warning">!!WARNING!!<br/>Do not change anything here unless you know exactly what you are doing! Changing things here could cause the device to stop responding</div>
<form method="post" action="/save">
<input type="hidden" name="sysConfig" value="true"/>
<div class="my-3 p-3 bg-white rounded shadow">
<h6>GPIO settings</h6>
<div class="row">
<div class="col-xl-2 col-md-3 col-sm-6 col-6">
<div class="m-2 input-group input-group-sm">
<div class="input-group-prepend">
<span class="input-group-text">HAN</span>
</div>
<select name="hanPin" class="form-control">
${options.han}
</select>
</div>
</div>
<div class="col-xl-2 col-lg-3 col-md-4 col-sm-5 col-6">
<div class="m-2 input-group input-group-sm">
<div class="input-group-prepend">
<span class="input-group-text">LED</span>
</div>
<input name="ledPin" type="number" min="2" max="${gpio.max}" class="form-control" value="${config.ledPin}"/>
<div class="input-group-append" title="Inverted">
<label class="input-group-text">
<input type="checkbox" name="ledInverted" value="true" ${config.ledInverted}/> inv
</label>
</div>
</div>
</div>
<div class="col-xl-3 col-lg-4 col-md-6">
<div class="m-2 input-group input-group-sm">
<div class="input-group-prepend">
<span class="input-group-text">RGB</span>
</div>
<input name="ledPinRed" type="number" min="2" max="${gpio.max}" class="form-control" value="${config.ledPinRed}"/>
<input name="ledPinGreen" type="number" min="2" max="${gpio.max}" class="form-control" value="${config.ledPinGreen}"/>
<input name="ledPinBlue" type="number" min="2" max="${gpio.max}" class="form-control" value="${config.ledPinBlue}"/>
<div class="input-group-append" title="Inverted">
<label class="input-group-text">
<input type="checkbox" name="ledRgbInverted" value="true" ${config.ledRgbInverted}/> inv
</label>
</div>
</div>
</div>
<div class="col-lg-2 col-md-3 col-sm-6 col-6">
<div class="m-2 input-group input-group-sm">
<div class="input-group-prepend">
<span class="input-group-text">AP button</span>
</div>
<input name="apPin" type="number" min="0" max="${gpio.max}" class="form-control" value="${config.apPin}"/>
</div>
</div>
<div class="col-xl-2 col-lg-3 col-md-4 col-sm-6 col-6">
<div class="m-2 input-group input-group-sm">
<div class="input-group-prepend">
<span class="input-group-text">Temperature</span>
</div>
<input name="tempSensorPin" type="number" min="0" max="${gpio.max}" class="form-control" value="${config.tempSensorPin}"/>
</div>
</div>
<div class="col-xl-6 col-lg-8">
<div class="row p-2">
<div class="col-sm-3 col-5">
<div class="input-group input-group-sm">
<div class="input-group-prepend">
<span class="input-group-text">Vcc</span>
</div>
<input name="vccPin" type="number" min="0" max="${gpio.max}" class="form-control" value="${config.vccPin}"/>
</div>
</div>
<div class="col-sm-4 col-7">
<div class="input-group input-group-sm">
<div class="input-group-prepend">
<span class="input-group-text">Offset</span>
</div>
<input type="number" min="0.1" max="3.5" step="0.01" class="form-control" name="vccOffset" value="${config.vccOffset}" />
</div>
</div>
<div class="col-sm-4 col-7">
<div class="input-group input-group-sm">
<div class="input-group-prepend">
<span class="input-group-text">Multiplier</span>
</div>
<input type="number" min="0.1" max="10" step="0.01" class="form-control" name="vccMultiplier" value="${config.vccMultiplier}" />
</div>
</div>
<div class="col-sm-4 col-7">
<div class="input-group input-group-sm">
<div class="input-group-prepend">
<span class="input-group-text">Boot limit</span>
</div>
<input type="number" min="2.5" max="3.5" step="0.1" class="form-control" name="vccBootLimit" value="${config.vccBootLimit}" />
</div>
</div>
</div>
</div>
</div>
</div>
<div class="my-3 p-3 bg-white rounded shadow">
<h6>Debugger</h6>
<div class="row">
<div class="col-xl-2 col-md-3">
<label><input type="checkbox" name="debugTelnet" value="true" ${config.debugTelnet}/> Telnet debugger</label>
</div>
<div class="col-xl-2 col-md-3">
<label><input type="checkbox" name="debugSerial" value="true" ${config.debugSerial}/> Serial debugger</label>
</div>
<div class="col-xl-3 col-md-4">
<div class="row form-group">
<label class="col-6">Debug level</label>
<div class="col-6">
<select class="form-control form-control-sm" name="debugLevel">
<option value="2" ${config.debugLevel2}>Debug</option>
<option value="3" ${config.debugLevel3}>Info</option>
<option value="4" ${config.debugLevel4}>Warning</option>
<option value="5" ${config.debugLevel5}>Error</option>
</select>
</div>
</div>
</div>
</div>
</div>
<div class="my-3 p-3 bg-white rounded shadow">
<div class="row">
<div class="col-6">
<a href="/firmware" class="btn btn-sm btn-outline-secondary">Upload firmware</a>
</div>
<div class="col-6 text-right">
<a href="/reset" class="btn btn-sm btn-danger">Factory reset</a>
</div>
</div>
</div>
<hr/>
<div class="row form-group">
<div class="col-6">
<a href="/" class="btn btn-outline-secondary">Back</a>
</div>
<div class="col-6 text-right">
<button class="btn btn-primary">Save</button>
</div>
</div>
</form>

37
web/debugging.html Normal file
View File

@ -0,0 +1,37 @@
<div class="alert alert-warning">!!NOTE!!<br/>Telnet debugging is not considered safe and should be switched off when not in use</div>
<form method="post" action="/save">
<input type="hidden" name="debugConfig" value="true"/>
<div class="my-3 p-3 bg-white rounded shadow">
<h6>Debugging</h6>
<div class="row">
<div class="col-xl-2 col-md-3">
<label><input type="checkbox" name="debugTelnet" value="true" ${config.debugTelnet}/> Telnet debugger</label>
</div>
<div class="col-xl-2 col-md-3">
<label><input type="checkbox" name="debugSerial" value="true" ${config.debugSerial}/> Serial debugger</label>
</div>
<div class="col-xl-3 col-md-4">
<div class="row form-group">
<label class="col-6">Debug level</label>
<div class="col-6">
<select class="form-control form-control-sm" name="debugLevel">
<option value="2" ${config.debugLevel2}>Debug</option>
<option value="3" ${config.debugLevel3}>Info</option>
<option value="4" ${config.debugLevel4}>Warning</option>
<option value="5" ${config.debugLevel5}>Error</option>
</select>
</div>
</div>
</div>
</div>
</div>
<hr/>
<div class="row form-group">
<div class="col-6">
<a href="/" class="btn btn-outline-secondary">Back</a>
</div>
<div class="col-6 text-right">
<button class="btn btn-primary">Save</button>
</div>
</div>
</form>

92
web/gpio.html Normal file
View File

@ -0,0 +1,92 @@
<div class="alert alert-warning">!!WARNING!!<br/>Do not change anything here unless you know exactly what you are doing! Changing things here could cause the device to stop responding</div>
<form method="post" action="/save">
<input type="hidden" name="gpioConfig" value="true"/>
<div class="my-3 p-3 bg-white rounded shadow">
<h6>GPIO settings</h6>
<div class="d-flex flex-row flex-wrap">
<div class="m-2 input-group input-group-sm" style="width: 150px;">
<div class="input-group-prepend">
<span class="input-group-text">HAN</span>
</div>
<select name="hanPin" class="form-control">
${options.han}
</select>
</div>
<div class="m-2 input-group input-group-sm" style="width: 150px;">
<div class="input-group-prepend">
<span class="input-group-text">LED</span>
</div>
<input name="ledPin" type="number" min="2" max="${gpio.max}" class="form-control" value="${config.ledPin}"/>
<div class="input-group-append" title="Inverted">
<label class="input-group-text">
<input type="checkbox" name="ledInverted" value="true" ${config.ledInverted}/> inv
</label>
</div>
</div>
<div class="m-2 input-group input-group-sm" style="width: 250px;">
<div class="input-group-prepend">
<span class="input-group-text">RGB</span>
</div>
<input name="ledPinRed" type="number" min="2" max="${gpio.max}" class="form-control" value="${config.ledPinRed}"/>
<input name="ledPinGreen" type="number" min="2" max="${gpio.max}" class="form-control" value="${config.ledPinGreen}"/>
<input name="ledPinBlue" type="number" min="2" max="${gpio.max}" class="form-control" value="${config.ledPinBlue}"/>
<div class="input-group-append" title="Inverted">
<label class="input-group-text">
<input type="checkbox" name="ledRgbInverted" value="true" ${config.ledRgbInverted}/> inv
</label>
</div>
</div>
<div class="m-2 input-group input-group-sm" style="width: 130px;">
<div class="input-group-prepend">
<span class="input-group-text">AP button</span>
</div>
<input name="apPin" type="number" min="0" max="${gpio.max}" class="form-control" value="${config.apPin}"/>
</div>
<div class="m-2 input-group input-group-sm" style="width: 150px;">
<div class="input-group-prepend">
<span class="input-group-text">Temperature</span>
</div>
<input name="tempSensorPin" type="number" min="0" max="${gpio.max}" class="form-control" value="${config.tempSensorPin}"/>
</div>
<div class="m-2 input-group input-group-sm" style="width: 150px;">
<div class="input-group-prepend">
<span class="input-group-text">Analog temp</span>
</div>
<input name="tempAnalogSensorPin" type="number" min="0" max="${gpio.max}" class="form-control" value="${config.tempAnalogSensorPin}"/>
</div>
<div class="m-2 input-group input-group-sm" style="width: 100px;">
<div class="input-group-prepend">
<span class="input-group-text">Vcc</span>
</div>
<input name="vccPin" type="number" min="0" max="${gpio.max}" class="form-control" value="${config.vccPin}"/>
</div>
<div class="m-2 input-group input-group-sm" style="width: 140px;">
<div class="input-group-prepend">
<span class="input-group-text">Multiplier</span>
</div>
<input type="number" min="0.1" max="10" step="0.01" class="form-control" name="vccMultiplier" value="${config.vccMultiplier}" />
</div>
<div class="m-2 input-group input-group-sm" style="width: 120px;">
<div class="input-group-prepend">
<span class="input-group-text">Offset</span>
</div>
<input type="number" min="0.1" max="3.5" step="0.01" class="form-control" name="vccOffset" value="${config.vccOffset}" />
</div>
<div class="m-2 input-group input-group-sm" style="width: 130px;">
<div class="input-group-prepend">
<span class="input-group-text">Boot limit</span>
</div>
<input type="number" min="2.5" max="3.5" step="0.1" class="form-control" name="vccBootLimit" value="${config.vccBootLimit}" />
</div>
</div>
</div>
<hr/>
<div class="row form-group">
<div class="col-6">
<a href="/" class="btn btn-outline-secondary">Back</a>
</div>
<div class="col-6 text-right">
<button class="btn btn-primary">Save</button>
</div>
</div>
</form>

View File

@ -53,6 +53,9 @@
<a href="/" class=""><h6 class="navbar-brand">AMS reader <small id="swVersion" data-url="https://api.github.com/repos/gskjold/AmsToMqttBridge/releases">${version}</small></h6></a>
<div class="navbar-nav-scroll">
<ul class="navbar-nav bd-navbar-nav flex-row">
<li class="nav-item">
<a id="config-temp-link" class="nav-link" href="/temperature">Temp<span class="d-none d-sm-inline">erature</span></a>
</li>
<li class="nav-item">
<a id="config-meter-link" class="nav-link" href="/config-meter">Meter</a>
</li>
@ -63,10 +66,21 @@
<a id="config-mqtt-link" class="nav-link" href="/config-mqtt">MQTT</a>
</li>
<li class="nav-item">
<a id="config-web-link" class="nav-link" href="/config-web">Web</a>
</li>
<li class="nav-item">
<a id="config-system-link" class="nav-link" href="/config-system">System</a>
<div class="dropdown">
<a class="dropdown-toggle nav-link" href="#" role="button" id="config-system-link" data-toggle="dropdown" aria-haspopup="true" aria-expanded="false">
System
</a>
<div class="dropdown-menu" aria-labelledby="config-system-link">
<a class="dropdown-item" href="/config-web">Web</a>
<a class="dropdown-item" href="/ntp">NTP</a>
<a class="dropdown-item" href="/gpio">GPIO</a>
<div class="dropdown-divider"></div>
<a class="dropdown-item" href="/debugging">Debugging</a>
<a class="dropdown-item" href="/firmware">Firmware</a>
<a class="dropdown-item text-danger" href="/reset">Factory reset</a>
</div>
</div>
</li>
</ul>
</div>

54
web/ntp.html Normal file
View File

@ -0,0 +1,54 @@
<form method="post" action="/save">
<input type="hidden" name="ntpConfig" value="true"/>
<div class="my-3 p-3 bg-white rounded shadow">
<h6>NTP</h6>
<label class="m-2"><input id="ntpEnable" type="checkbox" name="ntpEnable" value="true" ${config.ntpEnable}/> Enable</label>
<div class="row">
<div class="col-xl-2 col-lg-3 col-md-4 col-sm-5">
<div class="m-2 input-group input-group-sm">
<div class="input-group-prepend">
<span class="input-group-text">Timezone</span>
</div>
<select id="ntpOffset" class="form-control ntp-config" name="ntpOffset">
<option value="0" ${config.ntpOffset0}>UTC</option>
<option value="3600" ${config.ntpOffset3600}>UTC+1</option>
<option value="7200" ${config.ntpOffset7200}>UTC+2</option>
</select>
</div>
</div>
<div class="col-xl-3 col-lg-4 col-md-5 col-sm-7">
<div class="m-2 input-group input-group-sm">
<div class="input-group-prepend">
<span class="input-group-text">Summertime offset</span>
</div>
<select id="ntpSummerOffset" class="form-control ntp-config" name="ntpSummerOffset">
<option value="0" ${config.ntpSummerOffset0}>Disabled</option>
<option value="3600" ${config.ntpSummerOffset3600}>+1hr</option>
</select>
</div>
</div>
<div class="col-xl-4 col-lg-5 col-md-6">
<div class="m-2 input-group input-group-sm">
<div class="input-group-prepend">
<span class="input-group-text">Server</span>
</div>
<input type="text" class="form-control ntp-config" name="ntpServer" value="${config.ntpServer}" maxlength="64"/>
</div>
</div>
<div class="col-lg-4 col-md-5 col-sm-6">
<div class="m-2">
<label class="small"><input type="checkbox" name="ntpDhcp" value="true" ${config.ntpDhcp} class="ntp-config"/> Obtain NTP server from DHCP</label>
</div>
</div>
</div>
</div>
<hr/>
<div class="row form-group">
<div class="col-6">
<a href="/" class="btn btn-outline-secondary">Back</a>
</div>
<div class="col-6 text-right">
<button class="btn btn-primary">Save</button>
</div>
</div>
</form>