UNPKG

@hotnipi/node-red-dashboard-2-ui-gauge-linear

Version:
822 lines (751 loc) 35.1 kB
<script type="text/javascript"> RED.nodes.registerType('ui-gauge-linear', { category: RED._('@flowfuse/node-red-dashboard/ui-base:ui-base.label.category'), color: RED._('@flowfuse/node-red-dashboard/ui-base:ui-base.colors.dark'), defaults: { name: { value: "" }, group: { type: 'ui-group', required: true }, order: { value: 0 }, width: { value: 0, validate: function (v) { const width = v || 0 const currentGroup = $('#node-input-group').val() || this.group const groupNode = RED.nodes.node(currentGroup) const valid = !groupNode || +width <= +groupNode.width $('#node-input-size').toggleClass('input-error', !valid) return valid } }, height: { value: 0 }, min: { value: 0, required: true, validate:function(v) { const max=Number($("#node-input-max").length ? $("#node-input-max").val() : this.max) return (RED.validators.number()(v) && Number(v) !== max) }, }, max: { value: 10, validate:function(v) { const min=Number($("#node-input-min").length ? $("#node-input-min").val() : this.min) return (RED.validators.number()(v) && Number(v) !== min) }, }, ticks: { value: [], validate:function(tx) { const unique = [...new Set(tx.map(t => t.value))] const min = Number($("#node-input-min").length ? $("#node-input-min").val() : this.min) const max = Number($("#node-input-max").length ? $("#node-input-max").val() : this.max) let isValid = true if (tx.length != unique.length) { isValid = false } tx.forEach((tc) => { isValid = isValid && (Number(tc.value) > min && Number(tc.value) < max) }) return isValid }, }, colors:{ value:[] }, zeroCrossColors:{ value:["#ff4c16","#00e300"] }, mode:{ value:"default", required: true }, bar:{ value:"segmented", required: true }, minLabel: {value: ""}, maxLabel: {value: ""}, label: {value: "Gauge Linear"}, icon:{value:""}, unit: {value: "°C"}, dim: {value: 0.2}, property: { value: "payload", required: true }, decimals:{ value:2, validate:function(v) { return (RED.validators.number()(v) && Number(v) >= 0 && Number(v) < 18) }, }, zeros:{value:true}, myclass: {value: ""}, }, inputs: 1, outputs: 0, icon: "font-awesome/fa-ellipsis-h", paletteLabel: "gauge linear", label: function() { return this.name || "gauge linear"; }, oneditprepare: function () { let node = this const COLORS = ["#00e300","#00e300","#00e300","#00e300","#00e300","#00e300","#00e300","#00e300","#00e300","#00e300","#00e300","#00e300","#00e300","#00e300","#ffa916","#ffa916","#ffa916","#ffa916","#ff4c16","#ff4c16"] let defaultColors = COLORS.map((c,i) => { return {color:c,size:COLORS.length-i} }) if (RED.nodes.subflow(this.z)) { // change inputs from hidden to text & display them $('#node-input-width').attr('type', 'text') $('#node-input-height').attr('type', 'text') $('div.form-row.nr-db-ui-element-sizer-row').hide() $('div.form-row.nr-db-ui-manual-size-row').show() } else { // not in a subflow, use the elementSizer $('div.form-row.nr-db-ui-element-sizer-row').show() $('div.form-row.nr-db-ui-manual-size-row').hide() $('#node-input-size').elementSizer({ width: '#node-input-width', height: '#node-input-height', group: '#node-input-group' }) } if (this.property === undefined) { $("#node-input-property").val("payload"); } $("#node-input-property").typedInput({ default: 'msg', types: ['msg'] }); if (this.bar === undefined) { $("#node-input-bar").val("segmented"); } if (this.decimals === undefined) { $("#node-input-decimals").val(2); } let tickList = $("#node-input-ticks-container") tickList.editableList({ addItem: function(container, i, tick) { let isNew = false if (!tick.hasOwnProperty("value")) { isNew = true tick = {value: "", label: ""} } const row = $('<div/>', { class: 'form-row gauge-linear-list-item-row', style: 'margin-bottom: 0;' }).appendTo(container) const valueFiled = $('<input/>', { type: 'text', required: true, style: 'width:80px; margin-bottom: 0;', class: 'node-input-tick-value' }).appendTo(row) valueFiled.val(tick.value) valueFiled.on("change keyup paste", function() { validateTicks(tickList) fillLimits() createSolidBarItems() }); const labelFiled = $('<input/>', { type: 'text', style: 'width:80px; margin-bottom: 0;', class: 'node-input-tick-label' }).appendTo(row) labelFiled.val(tick.label) labelFiled.on("change keyup paste", function() { fillLimits() }); if (isNew) { validateTicks(tickList) fillLimits() createSolidBarItems() } }, sortable: true, removable: true, height: 'auto', scrollOnAdd: true, addButton: 'add tick', header: $('<div>').append( $.parseHTML( "<div class='gauge-linear-list-item-row' style='margin-left:24px;'><div>Value</div><div style='width:30%; display:inline-grid;'>Label</div></div>" ) ), removeItem: function(data) { validateTicks(tickList) fillLimits() createSolidBarItems() }, sortItems: function(items) { validateTicks(tickList) createSolidBarItems() } }) this.ticks = this.ticks || [] tickList.editableList('addItems', this.ticks) validateTicks(tickList) $("#node-input-max").change(function(){ validateTicks(tickList) hideOrShowTickFields() fillLimits() createSolidBarItems() }) $("#node-input-min").change(function(){ validateTicks(tickList) hideOrShowTickFields() fillLimits() createSolidBarItems() }) $("#node-input-maxLabel").change(function(){ fillLimits() }) $("#node-input-minLabel").change(function(){ fillLimits() }) $('#node-input-bar').change(function(){ if($('#node-input-bar option:selected').val() == 'segmented'){ $('.gauge-linear-bar-edit-outcome-segmented').show() $('#gauge-linear-dim-row').show() $('.gauge-linear-bar-edit-buttons').show() $('.gauge-linear-bar-edit-outcome-solid').hide() hideOrShowTickFields() fillLimits() hideOrShowZeroRange() } else{ $('.gauge-linear-bar-edit-outcome-segmented').hide() $('#gauge-linear-dim-row').hide() $('.gauge-linear-bar-edit-buttons').hide() $('.gauge-linear-bar-edit-outcome-solid').show() } }) this.colors = this.colors.length == 0 ? defaultColors : this.colors this.colors.forEach(c => { createSegmentedBarItem(c) }) createSolidBarItems(this.colors) if($('#node-input-bar').val() == 'segmented'){ $('.gauge-linear-bar-edit-outcome-segmented').show() $('.gauge-linear-bar-edit-outcome-solid').hide() } else{ $('.gauge-linear-bar-edit-outcome-segmented').hide() $('.gauge-linear-bar-edit-outcome-solid').show() } $("#gauge-linear-color").val(COLORS[0]) $("#gauge-linear-bar-edit-add").on("click",function( event ) { createSegmentedBarItem($("#gauge-linear-color").val()) }) $("#gauge-linear-bar-edit-remove").on("click",function( event ) { removeSegmentedBarItem() }) $('#node-input-mode').change(function(){ hideOrShowTickFields() fillLimits() createSolidBarItems() hideOrShowZeroRange() }) $("#gauge-linear-zero-color-negative").text(this.zeroCrossColors[0]) $("#gauge-linear-zero-color-positive").text(this.zeroCrossColors[1]) $('#gauge-linear-zero-range').change(function(){ const side = $(this).val() fillBarWithColor($("#gauge-linear-zero-color-"+side).text()) $("#gauge-linear-color").val($("#gauge-linear-zero-color-"+side).text()) fillLimits() }) hideOrShowZeroRange() setTimeout(()=>{ favouriteColorList() },100) }, oneditsave: function() { let ticks = $("#node-input-ticks-container").editableList('items'); var node = this; node.ticks = []; ticks.each(function(i) { node.ticks.push({ value: $(this).find('.node-input-tick-value').val(), label: $(this).find('.node-input-tick-label').val() }) }); node.ticks.sort((a,b) => a.value - b.value) node.colors = []; let cells if($('#node-input-bar option:selected').val() == 'segmented'){ cells = $(".gauge-linear-bar-edit-outcome-segmented").children() }else{ cells = $(".gauge-linear-bar-edit-outcome-solid").children() } cells.each(function(i){ node.colors.push({size:parseFloat($(this).css('max-width')),color:$(this).css('background-color')}) }) node.zeroCrossColors = []; node.zeroCrossColors.push($("#gauge-linear-zero-color-negative").text()) node.zeroCrossColors.push($("#gauge-linear-zero-color-positive").text()) }, }) function getSolidColors(){ let cells = $(".gauge-linear-bar-edit-outcome-solid").children() let colors = [] cells.each(function(i){ colors.push($(this).css('background-color')) }) return colors } function validateTicks(tickList) { const valueFields = tickList.find(".node-input-tick-value") const max = Number($("#node-input-max").val()) const min = Number($("#node-input-min").val()) valueFields.each(function() { let valid = Number(this.value) < max && Number(this.value) > min if (!valid) { $(this).css('border', '1px solid rgb(214, 97, 95)'); } else { $(this).css('border', ''); } }) } function createSolidBarItems(initialColors){ let colors = [] if(initialColors){ colors = [...initialColors] } let co let cells = $(".gauge-linear-bar-edit-outcome-solid").children() cells.each(function(i){ co={size:parseFloat($(this).css('max-width')),color:$(this).css('background-color')} colors.push(co) }) // colors.sort((a,b) => a.size - b.size) $('.gauge-linear-bar-edit-outcome-solid').empty() let ticks = [] const zeroCross = $('#node-input-mode').val() == "zeroCross"; const side = $('#gauge-linear-zero-range').val() const getPosition = function (tv) { const mi = Number($("#node-input-min").val()) const ma = Number($("#node-input-max").val()) if(zeroCross){ let v = Math.abs(tv) let t = side == 'negative' ? Math.abs(mi) : ma return Math.floor((v / t) * 100); } return Math.floor(((tv - mi) / (ma - mi)) * 100) } const getColor = (idx) => { if(colors.length == 0){ return {color:"#00e300"} } if(idx > colors.length-1){ return {color:"#00e300"} } return colors[idx] } const tickItems = $("#node-input-ticks-container").editableList('items'); tickItems.each(function(i) { ticks.push( getPosition(Number($(this).find('.node-input-tick-value').val())) ) }); ticks.sort((a,b) => b-a) let item if(zeroCross == false){ ticks.forEach((tick,i) => { item = $("<div class='gauge-linear-bar-item-solid' style='max-width:"+tick+"%; background-color:"+getColor(i+1).color+";'></div>") item.appendTo(".gauge-linear-bar-edit-outcome-solid") item.on( "mousemove", function( event ) { if(event.buttons == 1){ $(this).css("background-color",$("#gauge-linear-color").val()) } return false; }) }) } item = $("<div class='gauge-linear-bar-item-solid' style='max-width:100%; background-color:"+getColor(0).color+";'></div>") item.on( "mousemove", function( event ) { if(event.buttons == 1){ $(this).css("background-color",$("#gauge-linear-color").val()) if(zeroCross){ const side = $('#gauge-linear-zero-range').val() $("#gauge-linear-zero-color-"+side).text($("#gauge-linear-color").val()) } } return false; }) item.prependTo(".gauge-linear-bar-edit-outcome-solid") } function createSegmentedBarItem(color){ if($(".gauge-linear-bar-edit-outcome-segmented").children().length == 60){ return } const item = $("<div class='gauge-linear-bar-item' style='background-color:"+color.color+";'></div>") item.appendTo(".gauge-linear-bar-edit-outcome-segmented") item.on( "mousemove", function( event ) { if(event.buttons == 1){ $(this).css("background-color",$("#gauge-linear-color").val()) maybeApplyForMore($("#gauge-linear-color").val()) } return false; }) updateCellCount($(".gauge-linear-bar-edit-outcome-segmented").children().length) } function removeSegmentedBarItem(){ if($(".gauge-linear-bar-edit-outcome-segmented").children().length == 2){ return } $(".gauge-linear-bar-edit-outcome-segmented").find("div:last").remove(); updateCellCount($(".gauge-linear-bar-edit-outcome-segmented").children().length) } function maybeApplyForMore(color){ const shouldApply = $('#node-input-mode').val() == "zeroCross"; const side = $('#gauge-linear-zero-range').val() if(shouldApply){ fillBarWithColor(color) $('#gauge-linear-zero-color-'+side).text(color) } } function fillBarWithColor(color){ let items = $(".gauge-linear-bar-edit-outcome-segmented").children() items.each(function(i){ $(this).css("background-color",color) }) items = $('.gauge-linear-bar-edit-outcome-solid').children() items.each(function(i){ $(this).css("background-color",color) }) } function updateCellCount(count){ $(".gauge-linear-bar-edit-cell-count").text(count) } function favouriteColorList(){ let cells if($('#node-input-bar option:selected').val() == 'segmented'){ cells = $(".gauge-linear-bar-edit-outcome-segmented").children() }else{ cells = $(".gauge-linear-bar-edit-outcome-solid").children() } let list = [] cells.each(function(i){ let c = rgbToHex($(this).css('background-color')) if(list.indexOf(c) == -1){ list.push(c) } }) let some = ["#00e300","#ffa916","#ff4c16"] some.map(c => { if(list.indexOf(c) == -1){ list.push(c) } }) $('#gauge-linear-color-favourite').empty() list.forEach(color => { $('#gauge-linear-color-favourite').append("<option value='" + color + "'>"); }) } function fillLimits(){ let ticks = [] const zeroCross = $('#node-input-mode').val() == "zeroCross"; const side = $('#gauge-linear-zero-range').val() if(zeroCross){ ticks.push({value:0,label:0}) } else{ ticks.push({value:$("#node-input-min").val(),label:$("#node-input-minLabel").val()}) } const getPosition = function (tv) { const mi = Number($("#node-input-min").val()) const ma = Number($("#node-input-max").val()) if(zeroCross){ let v = Math.abs(tv) let t = side == 'negative' ? Math.abs(mi) : ma return Math.floor((v / t) * 100)+'%'; } return Math.floor(((tv - mi) / (ma - mi)) * 100)+'%' } const tickItems = $("#node-input-ticks-container").editableList('items'); tickItems.each(function(i) { ticks.push({ value: $(this).find('.node-input-tick-value').val(), label: $(this).find('.node-input-tick-label').val(), pos: getPosition(Number($(this).find('.node-input-tick-value').val())) }) }); if(zeroCross && side == "negative"){ ticks.push({value:$("#node-input-min").val(),label:$("#node-input-minLabel").val()}) } else{ ticks.push({value:$("#node-input-max").val(),label:$("#node-input-maxLabel").val()}) } $('.gauge-linear-bar-edit-limits').empty() ticks.forEach(tick => { let tickval = tick.label == "" ? tick.value : tick.label let ticksAllowed = true if($('#node-input-mode option:selected').val() == 'zeroCross'){ const max = Math.abs(Number($("#node-input-max").val())) const min = Math.abs(Number($("#node-input-min").val())) ticksAllowed = (max - min == 0) } if(tick.pos){ if(ticksAllowed){ if(zeroCross && side == "negative"){ tickval *=-1 } $("<div class='gauge-linear-tick-item' style='left:"+tick.pos+"'>"+tickval+"</div>").appendTo('.gauge-linear-bar-edit-limits') } } else{ $("<div class='gauge-linear-tick-item'>"+tickval+"</div>").appendTo('.gauge-linear-bar-edit-limits') } }) } function hideOrShowTickFields(){ if($('#node-input-mode option:selected').val() == 'zeroCross'){ const max = Math.abs(Number($("#node-input-max").val())) const min = Math.abs(Number($("#node-input-min").val())) const balanced = max - min if(balanced != 0){ $("#gauge-linear-ticks-row").hide() } else{ $("#gauge-linear-ticks-row").show() } }else { $("#gauge-linear-ticks-row").show() } } function hideOrShowZeroRange(){ $('.gauge-linear-zerorange').hide() if($('#node-input-mode').val() == "zeroCross" ){ $('.gauge-linear-zerorange').show() const side = $('#gauge-linear-zero-range').val() fillBarWithColor($("#gauge-linear-zero-color-"+side).text()) $("#gauge-linear-color").val($("#gauge-linear-zero-color-"+side).text()) } } function rgbToHex(a){ a=a.replace(/[^\d,]/g,"").split(","); return"#"+((1<<24)+(+a[0]<<16)+(+a[1]<<8)+ +a[2]).toString(16).slice(1) } </script> <style> .gauge-linear-grid-row{ display:grid; grid-template-columns: 6ch 80px 1fr; gap:.5rem; } .gauge-linear-list-item-row{ display:grid; grid-template-columns: 80px 1fr; gap:.5rem; } .gauge-linear-list-flexy-row{ display:inline-flex; align-items: center; } .gauge-linear-bar-edit-container{ border: 1px solid var(--red-ui-form-input-border-color); border-radius: 4px; padding:5px; } .gauge-linear-bar-edit-controls > div{ padding-bottom:4px; } .gauge-linear-bar-edit-controls select{ width: auto; } .gauge-linear-bar-edit-cell-count{ display: inline-block; height: 24px; line-height: 24px; padding: 0px 6px; border-radius: 2px; border: 1px solid var(--red-ui-form-input-border-color); color: var(--red-ui-workspace-button-color) !important; font-size: 14px; user-select: none; } .gauge-linear-bar-edit-buttons{ padding-top: 8px; } .gauge-linear-bar-edit-outcome-segmented{ display:flex; } .gauge-linear-bar-edit-outcome-solid{ display:block; height:20px; position: relative; margin-bottom: 2px; } .gauge-linear-bar-item{ height: 20px; width: 100%; max-width:100%; border: 1px solid black; background-color: red; } .gauge-linear-bar-item-solid{ height: 20px; width: 100%; position: absolute; left:0; top:0; border: 1px solid black; background-color: red; } .gauge-linear-bar-edit-limits { display: block; position: relative; font-size: smaller; line-height: 1; user-select: none; padding-top: 2px; height: .5rem; } .gauge-linear-tick-item { position: absolute; transform: translate(-50%, 0); } .gauge-linear-tick-item:first-child { left: 0; transform: translate(0, 0); } .gauge-linear-tick-item:last-child { right: 0; transform: translate(0, 0); } .gauge-linear-bar-edit-hidden{ display:none; } </style> <script type="text/html" data-template-name="ui-gauge-linear"> <div class="form-row"> <label for="node-input-name"><i class="fa fa-tag"></i> <span data-i18n="node-red:common.label.name"></label> <input type="text" id="node-input-name" placeholder="Name"> </div> <div class="form-row"> <label for="node-input-group"><i class="fa fa-table"></i> <span data-i18n="ui-gauge-linear.label.group"></label> <input type="text" id="node-input-group"> </div> <!-- <div class="form-row"> <label><i class="fa fa-object-group"></i> <span data-i18n="ui-gauge-linear.label.size"></label> <input type="hidden" id="node-input-width"> <input type="hidden" id="node-input-height"> <button class="editor-button" id="node-input-size"></button> </div> --> <div class="form-row nr-db-ui-element-sizer-row"> <label><i class="fa fa-object-group"></i> <span data-i18n="ui-gauge-linear.label.size"></label> <button class="editor-button" id="node-input-size"></button> </div> <div class="form-row nr-db-ui-manual-size-row"> <label><i class="fa fa-arrows-h"></i> <span data-i18n="ui-gauge-linear.label.width"></label> <input type="hidden" id="node-input-width"> </div> <div class="form-row nr-db-ui-manual-size-row"> <label><i class="fa fa-arrows-v"></i> <span data-i18n="ui-gauge-linear.label.height"></label> <input type="hidden" id="node-input-height"> </div> <div class="form-row"> <label for="node-input-label"><i class="fa fa-hand"></i> <span data-i18n="ui-gauge-linear.label.label"></span></label> <input type="text" id="node-input-label" value="Gauge Linear"> </div> <div class="form-row"> <label for="node-input-property"><i class="fa fa-arrow-right"></i> <span data-i18n="ui-gauge-linear.label.input"></span></label> <input type="text" id="node-input-property" style="min-width:261px;"/> </div> <div class="form-row" > <label><i class="fa fa-list"></i> <span data-i18n="ui-gauge-linear.label.limits"></span></label> <div class="red-ui-editableList-border"> <div class="red-ui-editableList-header gauge-linear-grid-row" style="padding-left:15px"> <div></div><div><span data-i18n="ui-gauge-linear.label.value"></span></div><div><span data-i18n="ui-gauge-linear.label.label"></span></div> </div> <div class="red-ui-editableList-container"> <div class="red-ui-editableList-container gauge-linear-grid-row" style="border-bottom: 1px solid var(--red-ui-form-input-border-color);"> <label for="node-input-min" style="align-self: center; margin: 0; width: unset;"><span data-i18n="ui-gauge-linear.label.min"></span>:</label> <input type="text" id="node-input-min" style="width:80px;"> <input type="text" id="node-input-minLabel" style="width:80px;"> </div> <div class="red-ui-editableList-container gauge-linear-grid-row" style="padding-top: 8px;"> <label for="node-input-max" style="align-self: center; margin: 0; width: unset;"><span data-i18n="ui-gauge-linear.label.max"></span>:</label> <input type="text" id="node-input-max" style="width:80px;"> <input type="text" id="node-input-maxLabel" style="width:80px;"> </div> </div> </div> </div> <div class="form-row node-input-ticks-container-row" id="gauge-linear-ticks-row"> <label><i class="fa fa-list"></i> <span data-i18n="ui-gauge-linear.label.ticks"></span></label> <ol id="node-input-ticks-container"></ol> </div> <div class="form-row"> <label for='node-input-bar'><i class='fa fa-gear'></i> <span data-i18n="ui-gauge-linear.label.bar"></span></label> <select id='node-input-bar'> <option value='segmented' data-i18n="ui-gauge-linear.label.segmented"></option> <option value='solid' data-i18n="ui-gauge-linear.label.solid"></option> </select> </div> <div class="form-row"> <div class="gauge-linear-bar-edit-container"> <div class="gauge-linear-bar-edit"> <div class="gauge-linear-bar-edit-controls"> <div> <label for='node-input-mode'><i class='fa fa-list'></i> <span data-i18n="ui-gauge-linear.label.select"></span></label> <select id='node-input-mode'> <option value='default' data-i18n="ui-gauge-linear.label.default"></option> <option value='fullBar' data-i18n="ui-gauge-linear.label.fullbar"></option> <option value='zeroCross' data-i18n="ui-gauge-linear.label.cross"></option> </select> </div> <div> <label for="gauge-linear-color"><i class="fa fa-paint-brush"></i> <span data-i18n="ui-gauge-linear.label.pick"></span></label> <input type="color" id="gauge-linear-color" list="gauge-linear-color-favourite" style="width:80px;"> <datalist id="gauge-linear-color-favourite"></datalist> <label class='gauge-linear-zerorange' for='gauge-linear-zero-range' style="width:30px;text-align: center;"> <span data-i18n="ui-gauge-linear.label.for"></span></label> <select id='gauge-linear-zero-range' class='gauge-linear-zerorange'> <option value='positive' data-i18n="ui-gauge-linear.label.positive"></option> <option value='negative' data-i18n="ui-gauge-linear.label.negative"></option> </select> </div> </div> <p><span data-i18n="ui-gauge-linear.label.hint"></span></p> <div class="gauge-linear-bar-edit-outcome-segmented"></div> <div class="gauge-linear-bar-edit-outcome-solid"></div> <div class="gauge-linear-bar-edit-limits"></div> <div class="gauge-linear-bar-edit-buttons"> <button type="button" id="gauge-linear-bar-edit-remove" class="red-ui-button red-ui-button-small" data-i18n="ui-gauge-linear.label.remove"></button> <span class="gauge-linear-bar-edit-cell-count"></span> <button type="button" id="gauge-linear-bar-edit-add" class="red-ui-button red-ui-button-small" data-i18n="ui-gauge-linear.label.add"></button> </div> <div class="gauge-linear-bar-edit-hidden"> <span id="gauge-linear-zero-color-positive"></span><span id="gauge-linear-zero-color-negative"></span> </div> </div> </div> </div> <div class="form-row"> <label for="node-input-decimals"><i class="fa fa-hand"></i><span data-i18n="ui-gauge-linear.label.decimals"></span></label> <div class="gauge-linear-list-flexy-row"> <div> <input type="number" id="node-input-decimals" value="2" min="0" max="17" step="1"> </div> <div> <label style="width:auto" for="node-input-zeros"> <span data-i18n="ui-gauge-linear.label.zeros"></span></label> <input type="checkbox" checked id="node-input-zeros" style="display: inline-block; width: auto; margin: 0px 0px 0px 4px;"> </div> </div> </div> <div class="form-row"> <label for="node-input-icon"><i class="fa fa-hand"></i><span data-i18n="ui-gauge-linear.label.icon"></span></label> <input type="text" id="node-input-icon"> </div> <div class="form-row"> <label for="node-input-unit"><i class="fa fa-hand"></i><span data-i18n="ui-gauge-linear.label.unit"></span></label> <input type="text" id="node-input-unit"> </div> <div class="form-row" id="gauge-linear-dim-row"> <label for="node-input-dim"><i class="fa fa-hand"></i><span data-i18n="ui-gauge-linear.label.dim"></span></label> <input type="number" id="node-input-dim" value="0.2" min="0" max="0.9" step="0.1"> </div> <div class="form-row"> <label for="node-input-myclass"><i class="fa fa-hand"></i><span data-i18n="ui-gauge-linear.label.class"></span></label> <input type="text" id="node-input-myclass"> </div> <div class="form-row"> <a href="https://buymeacoffee.com/hotnipi" target="_blank"><i class="fa fa-coffee"></i><span style="margin-left:4px;" data-i18n="ui-gauge-linear.label.coffee"></span></label></a> </div> </script>