diff --git a/src/editor/index.js b/src/editor/index.js index 2606e8a..35d6a87 100644 --- a/src/editor/index.js +++ b/src/editor/index.js @@ -11,10 +11,13 @@ return Number.isFinite(v) ? v : null; }; - // Set a numeric input's value, or blank if not finite. + // Set a numeric input's value, or blank if not finite. Accepts numeric + // strings (Node-RED's auto-form-binding stores form values as strings). ns.setNumberField = (id, val) => { const el = document.getElementById(id); - if (el) el.value = Number.isFinite(val) ? val : ''; + if (!el) return; + const num = typeof val === 'number' ? val : parseFloat(val); + el.value = Number.isFinite(num) ? num : ''; }; // Add input + change listeners to a list of node-input-* ids. diff --git a/src/editor/oneditprepare.js b/src/editor/oneditprepare.js index cce5100..b5da8cf 100644 --- a/src/editor/oneditprepare.js +++ b/src/editor/oneditprepare.js @@ -68,11 +68,14 @@ ns.setNumberField('node-input-stopLevel', node.stopLevel); // holdLevel defaults to startLevel when omitted (no hold band). Show // the saved value if there is one; otherwise mirror startLevel so the - // user immediately sees the "no hold band" baseline. + // user immediately sees the "no hold band" baseline. Coerce to Number + // because Node-RED form-bind stores numeric inputs as strings. + const holdNum = parseFloat(node.holdLevel); ns.setNumberField('node-input-holdLevel', - Number.isFinite(node.holdLevel) ? node.holdLevel : node.startLevel); + Number.isFinite(holdNum) ? holdNum : node.startLevel); + const deadZoneNum = parseFloat(node.deadZoneKeepAlivePercent); ns.setNumberField('node-input-deadZoneKeepAlivePercent', - Number.isFinite(node.deadZoneKeepAlivePercent) ? node.deadZoneKeepAlivePercent : 1); + Number.isFinite(deadZoneNum) ? deadZoneNum : 1); ns.setNumberField('node-input-maxLevel', node.maxLevel); ns.setNumberField('node-input-logCurveFactor', node.logCurveFactor); ns.setNumberField('node-input-shiftLevel', node.shiftLevel); diff --git a/src/editor/oneditsave.js b/src/editor/oneditsave.js index 8ba082f..9e03259 100644 --- a/src/editor/oneditsave.js +++ b/src/editor/oneditsave.js @@ -50,6 +50,15 @@ node.logCurveFactor = parseNum('node-input-logCurveFactor'); node.startLevel = parseNum('node-input-startLevel'); node.maxLevel = parseNum('node-input-maxLevel'); + // Persist as numbers — Node-RED's auto-form-binding would store these as + // strings, and oneditprepare's setNumberField rejects non-Number values, + // so the input would blank out on reopen. + const stopLevelVal = parseNum('node-input-stopLevel'); + node.stopLevel = Number.isFinite(stopLevelVal) ? stopLevelVal : null; + const holdLevelVal = parseNum('node-input-holdLevel'); + if (Number.isFinite(holdLevelVal)) node.holdLevel = holdLevelVal; + const deadZoneVal = parseNum('node-input-deadZoneKeepAlivePercent'); + if (Number.isFinite(deadZoneVal)) node.deadZoneKeepAlivePercent = deadZoneVal; // minLevel is no longer a user input — it's the derived dryRunLevel // (outflowLevel × (1 + dryRunThresholdPercent/100)). The runtime still // uses node.minLevel as the unconditional STOP threshold; we set it