52 lines
15 KiB
HTML
52 lines
15 KiB
HTML
<!doctype html><html lang="en"><head><meta charset="utf-8"><meta name="viewport" content="width=device-width,initial-scale=1,shrink-to-fit=no"><meta name="description" content=""><title>Beer Gravity Monitor</title><link href="https://cdn.jsdelivr.net/npm/bootstrap@5.1.3/dist/css/bootstrap.min.css" rel="stylesheet" integrity="sha384-1BmE4kWBq78iYhFldvKuhfTAU6auU8tT94WrHftjDbrCEXSU1oBoqyl2QvZ6jIW3" crossorigin="anonymous"><style>.row-margin-10{margin-top:1em}</style></head><body class="py-4"><script src="https://cdn.jsdelivr.net/npm/bootstrap@5.1.3/dist/js/bootstrap.bundle.min.js" integrity="sha384-ka7Sk0Gln4gmtz2MlQnikT1wXgYsOg+OMhuP+IlRH9sENBO0LRn5q+8nbTov4+1p" crossorigin="anonymous"></script><script src="https://code.jquery.com/jquery-3.6.0.min.js" integrity="sha256-/xUj+3OJU5yExlq6GSYGSHk7tPXikynS7ogEvDej/m4=" crossorigin="anonymous"></script><script src="https://cdn.jsdelivr.net/npm/chart.js"></script><nav class="navbar navbar-expand-lg navbar-dark bg-primary"><div class="container"><a class="navbar-brand" href="/index.htm">Beer Gravity Monitor</a> <button class="navbar-toggler" type="button" data-bs-toggle="collapse" data-bs-target="#navbarNav" aria-controls="navbarNav" aria-expanded="false" aria-label="Toggle navigation"><span class="navbar-toggler-icon"></span></button><div class="collapse navbar-collapse" id="navbarNav"><ul class="navbar-nav"><li class="nav-item"><a class="nav-link" href="/index.htm">Home</a></li><li class="nav-item dropdown"><a class="nav-link dropdown-toggle" href="#" role="button" data-bs-toggle="dropdown" aria-expanded="false">Configuration</a><ul class="dropdown-menu"><li><a class="dropdown-item" href="/config.htm">Configuration</a></li><li><a class="dropdown-item" href="/format.htm">Format editor</a></li><li><a class="dropdown-item" href="/test.htm">Test push</a></li><li><a class="dropdown-item" href="/firmware.htm">Upload firmware</a></li></ul></li><li class="nav-item"><a class="nav-link active" href="#">Calibration</a></li><li class="nav-item"><a class="nav-link" href="/about.htm">About</a></li></ul></div><div class="spinner-border text-light" id="spinner" role="status"></div></div></nav><!-- START BODY --><div class="container row-margin-10"><div class="alert alert-success alert-dismissible hide fade d-none" role="alert"><div id="alert"></div><button type="button" class="btn-close" data-bs-dismiss="alert" aria-label="Close"></button></div><script type="text/javascript">function showError(s){$(".alert").removeClass("alert-success").addClass("alert-danger").removeClass("hide").addClass("show").removeClass("d-none"),$("#alert").text(s)}function showSuccess(s){$(".alert").addClass("alert-success").removeClass("alert-danger").removeClass("hide").addClass("show").removeClass("d-none"),$("#alert").text(s)}$("#alert-btn").click(function(s){$(".alert").addClass("hide").removeClass("show").addClass("d-none")})</script><div class="accordion" id="accordion"><div class="accordion-item"><h2 class="accordion-header" id="headingFormula"><button class="accordion-button" type="button" data-bs-toggle="collapse" data-bs-target="#collapseFormula" aria-expanded="true" aria-controls="collapseFormula"><b>Formula calculation</b></button></h2><div id="collapseFormula" class="accordion-collapse collapse show" aria-labelledby="headingFormula" data-bs-parent="#accordion"><div class="accordion-body"><form action="/api/formula" method="post"><input type="text" name="gravity-format" id="gravity-format" hidden> <input type="text" name="id" id="id" hidden><div class="row mb-3">Here you can create your gravity formula by entering angles/tilt and the corresponding gravity. These values will be saved for future use. Angles with 0 (zero) will be skipped. The values below will be used to check the formula and if the deviation is more than 1.5SG / 0.38P on any of the provided points then the forumla will be rejected. On the bottom of the page you can see a graph over the entered values + values calcualated by the formula.</div><div class="row"><label class="col-sm-1 col-form-label">#</label> <label class="col-sm-4 col-form-label">Angle/Tilt</label> <label class="col-sm-4 col-form-label" id="gravity-header">Gravity</label></div><div class="row mb-3"><label for="angle1" class="col-sm-1 col-form-label">1.</label><div class="col-sm-4"><input type="number" min="0" max="90" step="0.001" class="form-control" name="a1" id="a1" data-bs-toggle="tooltip" title="Enter the angle for the gravity. Zero value will be ignored"></div><input hidden type="number" name="g1" id="g1"><div class="col-sm-4"><input disabled type="number" class="form-control" name="g1a" id="g1a" data-bs-toggle="tooltip" title="The first value is reserved for water gravity."></div></div><div class="row mb-3"><label for="angle2" class="col-sm-1 col-form-label">2.</label><div class="col-sm-4"><input type="number" min="0" max="90" step="0.001" class="form-control" name="a2" id="a2" data-bs-toggle="tooltip" title="Enter the angle for the gravity. Zero value will be ignored"></div><div class="col-sm-4"><input type="number" min="0" max="26" step="0.0001" class="form-control" name="g2" id="g2" data-bs-toggle="tooltip" title="Enter the gravity for the angle."></div></div><div class="row mb-3"><label for="angle3" class="col-sm-1 col-form-label">3.</label><div class="col-sm-4"><input type="number" min="0" max="90" step="0.001" class="form-control" name="a3" id="a3" data-bs-toggle="tooltip" title="Enter the angle for the gravity. Zero value will be ignored"></div><div class="col-sm-4"><input type="number" min="0" max="26" step="0.0001" class="form-control" name="g3" id="g3" data-bs-toggle="tooltip" title="Enter the gravity for the angle."></div></div><div class="row mb-3"><label for="angle4" class="col-sm-1 col-form-label">4.</label><div class="col-sm-4"><input type="number" min="0" max="90" step="0.001" class="form-control" name="a4" id="a4" data-bs-toggle="tooltip" title="Enter the angle for the gravity. Zero value will be ignored"></div><div class="col-sm-4"><input type="number" min="0" max="26" step="0.0001" class="form-control" name="g4" id="g4" data-bs-toggle="tooltip" title="Enter the gravity for the angle."></div></div><div class="row mb-3"><label for="angle5" class="col-sm-1 col-form-label">5.</label><div class="col-sm-4"><input type="number" min="0" max="90" step="0.001" class="form-control" name="a5" id="a5" data-bs-toggle="tooltip" title="Enter the angle for the gravity. Zero value will be ignored"></div><div class="col-sm-4"><input type="number" min="0" max="26" step="0.0001" class="form-control" name="g5" id="g5" data-bs-toggle="tooltip" title="Enter the gravity for the angle."></div></div><div class="row mb-3"><label for="angle6" class="col-sm-1 col-form-label">6.</label><div class="col-sm-4"><input type="number" min="0" max="90" step="0.001" class="form-control" name="a6" id="a6" data-bs-toggle="tooltip" title="Enter the angle for the gravity. Zero value will be ignored"></div><div class="col-sm-4"><input type="number" min="0" max="26" step="0.0001" class="form-control" name="g6" id="g6" data-bs-toggle="tooltip" title="Enter the gravity for the angle."></div></div><div class="row mb-3"><label for="angle7" class="col-sm-1 col-form-label">7.</label><div class="col-sm-4"><input type="number" min="0" max="90" step="0.001" class="form-control" name="a7" id="a7" data-bs-toggle="tooltip" title="Enter the angle for the gravity. Zero value will be ignored"></div><div class="col-sm-4"><input type="number" min="0" max="26" step="0.0001" class="form-control" name="g7" id="g7" data-bs-toggle="tooltip" title="Enter the gravity for the angle."></div></div><div class="row mb-3"><label for="angle8" class="col-sm-1 col-form-label">8.</label><div class="col-sm-4"><input type="number" min="0" max="90" step="0.001" class="form-control" name="a8" id="a8" data-bs-toggle="tooltip" title="Enter the angle for the gravity. Zero value will be ignored"></div><div class="col-sm-4"><input type="number" min="0" max="26" step="0.0001" class="form-control" name="g8" id="g8" data-bs-toggle="tooltip" title="Enter the gravity for the angle."></div></div><div class="row mb-3"><label for="angle9" class="col-sm-1 col-form-label">9.</label><div class="col-sm-4"><input type="number" min="0" max="90" step="0.001" class="form-control" name="a9" id="a9" data-bs-toggle="tooltip" title="Enter the angle for the gravity. Zero value will be ignored"></div><div class="col-sm-4"><input type="number" min="0" max="26" step="0.0001" class="form-control" name="g9" id="g9" data-bs-toggle="tooltip" title="Enter the gravity for the angle."></div></div><div class="row mb-3"><label for="angle10" class="col-sm-1 col-form-label">10.</label><div class="col-sm-4"><input type="number" min="0" max="90" step="0.001" class="form-control" name="a10" id="a10" data-bs-toggle="tooltip" title="Enter the angle for the gravity. Zero value will be ignored"></div><div class="col-sm-4"><input type="number" min="0" max="26" step="0.0001" class="form-control" name="g10" id="g10" data-bs-toggle="tooltip" title="Enter the gravity for the angle."></div></div><div class="row mb-3"><div class="col-sm-8 offset-sm-1"><button type="submit" class="btn btn-primary" id="calculate-btn" data-bs-toggle="tooltip" title="Save the values and try to create a formula">Save & Create</button></div></div><hr class="my-2"><div class="row"><label for="calculate-btn" class="col-sm-2 col-form-label">Current angle:</label> <label for="calculate-btn" class="col-sm-2 col-form-label" id="angle"></label></div><div class="row"><label for="calculate-btn" class="col-sm-2 col-form-label">Formula:</label> <label for="calculate-btn" class="col-sm-8 col-form-label" id="formula">Loading...</label></div></form></div></div></div><div class="accordion-item"><h2 class="accordion-header" id="headingGraph"><button class="accordion-button collapsed" type="button" data-bs-toggle="collapse" data-bs-target="#collapseGraph" aria-expanded="false" aria-controls="collapseGraph"><b>Formula graph</b></button></h2><div id="collapseGraph" class="accordion-collapse collapse" aria-labelledby="headingGraph" data-bs-parent="#accordion"><div class="accordion-body"><canvas id="gravityChart"></canvas></div></div></div></div></div><script type="text/javascript">var chartDataForm = [];
|
|
var chartDataCalc = [];
|
|
|
|
const dataSetChart = {
|
|
datasets: [{
|
|
label: 'Raw data',
|
|
borderColor: 'blue',
|
|
backgroundColor: 'blue',
|
|
data: chartDataForm
|
|
}, {
|
|
label: 'Calculated',
|
|
borderColor: 'green',
|
|
backgroundColor: 'green',
|
|
data: chartDataCalc
|
|
}]
|
|
}
|
|
|
|
const configChart = {
|
|
type: 'line',
|
|
data: dataSetChart,
|
|
options: {
|
|
responsive: true,
|
|
interaction: {
|
|
intersect: false,
|
|
},
|
|
scales: {
|
|
x: {
|
|
display: true,
|
|
type: 'linear',
|
|
grace: '5%',
|
|
title: {
|
|
display: true,
|
|
text: 'Angle/Tilt'
|
|
},
|
|
ticks: {
|
|
crossAlign: 'far'
|
|
},
|
|
suggestedMin: 25
|
|
},
|
|
y: {
|
|
display: true,
|
|
title: {
|
|
display: true,
|
|
text: 'Gravity'
|
|
},
|
|
suggestedMin: 1.000
|
|
}
|
|
}
|
|
}
|
|
};
|
|
|
|
var myChart = 0;</script><script type="text/javascript">function convertToPlato(a){return 259-259/a}function convertToSG(a){return 259/(259-a)}function setAngleDecimal(a){this.value=parseFloat(this.value).toFixed(2),populateChart()}function setGravityDecimal(a){isPlato()?this.value=parseFloat(this.value).toFixed(1):this.value=parseFloat(this.value).toFixed(4),populateChart()}function populateChartForm(a,t){0!=a&&chartDataForm.push({x:parseFloat(a),y:parseFloat(t)}),chartDataForm.sort(function(a,t){return a.x-t.x})}function populateChartCalc(a,t){chartDataCalc.push({x:parseFloat(a),y:parseFloat(t)})}function isPlato(){return"P"==$("#gravity-format").text()}function populateChart(){for(chartDataCalc.length=0,i=25;i<80;i+=5){var formula=$("#formula").text(),angle=i.toString();formula=formula.replaceAll("tilt^3",angle+"*"+angle+"*"+angle),formula=formula.replaceAll("tilt^2",angle+"*"+angle),formula=formula.replaceAll("tilt",angle);var g=eval(formula);isPlato()&&(g=convertToPlato(g)),populateChartCalc(i,g)}chartDataForm.length=0,populateChartForm($("#a1").val(),$("#g1").val()),populateChartForm($("#a2").val(),$("#g2").val()),populateChartForm($("#a3").val(),$("#g3").val()),populateChartForm($("#a4").val(),$("#g4").val()),populateChartForm($("#a5").val(),$("#g5").val()),populateChartForm($("#a6").val(),$("#g6").val()),populateChartForm($("#a7").val(),$("#g7").val()),populateChartForm($("#a8").val(),$("#g8").val()),populateChartForm($("#a9").val(),$("#g9").val()),populateChartForm($("#a10").val(),$("#g10").val()),myChart&&myChart.destroy(),myChart=new Chart(document.getElementById("gravityChart"),configChart)}function setButtonDisabled(a){$("#calculate-btn").prop("disabled",a)}function getConfig(){setButtonDisabled(!0);var a="/api/formula";$("#spinner").show(),$.getJSON(a,function(a){console.log(a),$("#id").val(a.id),$("#angle").text(a.angle),$("#formula").text(a["gravity-formula"]),$("#gravity-format").text(a["gravity-format"]),isPlato()?($("#gravity-header").text("Gravity (Plato):"),$("#g1").val(parseFloat(a.g1).toFixed(1)),$("#g1a").val("0.0"),$("#g2").val(parseFloat(a.g2).toFixed(1)),$("#g3").val(parseFloat(a.g3).toFixed(1)),$("#g4").val(parseFloat(a.g4).toFixed(1)),$("#g5").val(parseFloat(a.g5).toFixed(1)),$("#g6").val(parseFloat(a.g6).toFixed(1)),$("#g7").val(parseFloat(a.g7).toFixed(1)),$("#g8").val(parseFloat(a.g8).toFixed(1)),$("#g9").val(parseFloat(a.g9).toFixed(1)),$("#g10").val(parseFloat(a.g10).toFixed(1))):($("#gravity-header").text("Gravity (SG):"),$("#g1").val(parseFloat(a.g1).toFixed(4)),$("#g1a").val("1.0000"),$("#g2").val(parseFloat(a.g2).toFixed(4)),$("#g3").val(parseFloat(a.g3).toFixed(4)),$("#g4").val(parseFloat(a.g4).toFixed(4)),$("#g5").val(parseFloat(a.g5).toFixed(4)),$("#g6").val(parseFloat(a.g6).toFixed(4)),$("#g7").val(parseFloat(a.g7).toFixed(4)),$("#g8").val(parseFloat(a.g8).toFixed(4)),$("#g9").val(parseFloat(a.g9).toFixed(4)),$("#g10").val(parseFloat(a.g10).toFixed(4))),$("#a1").val(parseFloat(a.a1).toFixed(2)),$("#a2").val(parseFloat(a.a2).toFixed(2)),$("#a3").val(parseFloat(a.a3).toFixed(2)),$("#a4").val(parseFloat(a.a4).toFixed(2)),$("#a5").val(parseFloat(a.a5).toFixed(2)),$("#a6").val(parseFloat(a.a6).toFixed(2)),$("#a7").val(parseFloat(a.a7).toFixed(2)),$("#a8").val(parseFloat(a.a8).toFixed(2)),$("#a9").val(parseFloat(a.a9).toFixed(2)),$("#a10").val(parseFloat(a.a10).toFixed(2)),""!=a.error&&showError(a.error),populateChart()}).fail(function(){showError("Unable to get data from the device.")}).always(function(){$("#spinner").hide(),setButtonDisabled(!1)})}g1.onchange=setGravityDecimal,g2.onchange=setGravityDecimal,g3.onchange=setGravityDecimal,g4.onchange=setGravityDecimal,g5.onchange=setGravityDecimal,g6.onchange=setGravityDecimal,g7.onchange=setGravityDecimal,g8.onchange=setGravityDecimal,g9.onchange=setGravityDecimal,g10.onchange=setGravityDecimal,a1.onchange=setAngleDecimal,a2.onchange=setAngleDecimal,a3.onchange=setAngleDecimal,a4.onchange=setAngleDecimal,a5.onchange=setAngleDecimal,a6.onchange=setAngleDecimal,a7.onchange=setAngleDecimal,a8.onchange=setAngleDecimal,a9.onchange=setAngleDecimal,a10.onchange=setAngleDecimal,window.onload=getConfig,setButtonDisabled(!0)</script><!-- START FOOTER --><div class="container themed-container bg-primary text-light row-margin-10">(C) Copyright 2021-22 Magnus Persson</div></body></html> |