Add weighting factors to a calculation

I'm building a new garden auto-watering system, to water certain plants whilst I'm away on holiday (unless they're ^%&* cancelled again :rage:).

I want this version to calculate the length of time the irrigator should run for, and be influenced by the weather, such as wind-speed, temperature, rain & humidity, and increase/decrease the irrigation time accordingly.

Can anyone suggest a way to combine these weighting factors in javascript?

For example, if the temperature is greater than 30C, the weighting factor would be more, than if the temp was below 25C.
The same for windspeed, etc.

I can apply weighting to individual criteria, but combining them together is more problematic - but maybe I'm overthinking this.

Of course I realise that I would have to fine tune the model, after a best-guess start!

I were speaking to on of the top tomato farming guys in the country, it is actually very complex the way they calculate the watering schedule.

They take their weather records from the last 10 years, have some really complex excel spreadsheet, prediction for the next week, put it in the mixer and them have the schedule for the next week.

Then twice a week they dig a 4 holes in per hectare, stick their hands in the soil and and see if their excel mixer were correct and refresh from there.

Your approach will be most probably be something like the water geyser control.

I am waiting for some really nice soil capacitance probe to arrive and then I want to star with a vegetable patch irrigation project.

Measurements and control will all be via LoRaWAN via TTN (probe, pressure, valve control, weather station(done already))

Node-red for control and DB mangment

InfluxDB and mySQL

Grafana for monitoring.

I've not had a lot of luck with soil capacitance probes, that's why I'm changing my flows.
Maybe you will have better luck than me (or better quality probes).

I am going to use one of these - https://aquacheck.co.za/soil-moisture-probes/

You need to measure at several depth intervals.

Paul you could do something like. This flow could also be written in a function node, each range can give weight and some weight could have more affect depending on setting, to the final output. the output can then be used to increase time.

say output is 80 then time * ( 80/100) would decrease time, or if output is 120,then time * (120/100)would increase time.

[{"id":"851b0ec6.672868","type":"inject","z":"bf9e1e33.030598","name":"","props":[{"p":"payload"},{"p":"topic","vt":"str"}],"repeat":"","crontab":"","once":false,"onceDelay":0.1,"topic":"humidity","payload":"50","payloadType":"num","x":140,"y":3280,"wires":[["513218b9.90c418"]]},{"id":"513218b9.90c418","type":"range","z":"bf9e1e33.030598","minin":"40","maxin":"90","minout":"100","maxout":"0","action":"scale","round":false,"property":"payload","name":"","x":400,"y":3260,"wires":[["f8741230.4606c"]]},{"id":"7df6e0bf.e3bfb","type":"inject","z":"bf9e1e33.030598","name":"","props":[{"p":"payload"},{"p":"topic","vt":"str"}],"repeat":"","crontab":"","once":false,"onceDelay":0.1,"topic":"humidity","payload":"80","payloadType":"num","x":140,"y":3240,"wires":[["513218b9.90c418"]]},{"id":"f8741230.4606c","type":"join","z":"bf9e1e33.030598","name":"","mode":"custom","build":"object","property":"payload","propertyType":"msg","key":"topic","joiner":"\\n","joinerType":"str","accumulate":true,"timeout":"","count":"4","reduceRight":false,"reduceExp":"","reduceInit":"","reduceInitType":"","reduceFixup":"","x":450,"y":3400,"wires":[["1ba34784.9f37f"]]},{"id":"54d1d3fa.341894","type":"range","z":"bf9e1e33.030598","minin":"0","maxin":"5","minout":"100","maxout":"0","action":"scale","round":false,"property":"payload","name":"","x":301.33331298828125,"y":3354.333251953125,"wires":[["f8741230.4606c"]]},{"id":"2fa7baad.3fa3de","type":"range","z":"bf9e1e33.030598","minin":"10","maxin":"30","minout":"0","maxout":"100","action":"scale","round":false,"property":"payload","name":"","x":320,"y":3460,"wires":[["f8741230.4606c"]]},{"id":"d43a0089.f567c8","type":"range","z":"bf9e1e33.030598","minin":"0","maxin":"60","minout":"0","maxout":"100","action":"scale","round":false,"property":"payload","name":"","x":320,"y":3540,"wires":[["f8741230.4606c"]]},{"id":"1ba34784.9f37f","type":"change","z":"bf9e1e33.030598","name":"","rules":[{"t":"set","p":"payload","pt":"msg","to":"$round($average($$.payload.*))","tot":"jsonata"}],"action":"","property":"","from":"","to":"","reg":false,"x":650,"y":3400,"wires":[["c7dafb11.d8889"]]},{"id":"d75ed79f.0a47d8","type":"inject","z":"bf9e1e33.030598","name":"","props":[{"p":"payload"},{"p":"topic","vt":"str"}],"repeat":"","crontab":"","once":false,"onceDelay":0.1,"topic":"rain","payload":"0","payloadType":"num","x":130,"y":3340,"wires":[["54d1d3fa.341894"]]},{"id":"3008e103.c0a25e","type":"inject","z":"bf9e1e33.030598","name":"","props":[{"p":"payload"},{"p":"topic","vt":"str"}],"repeat":"","crontab":"","once":false,"onceDelay":0.1,"topic":"rain","payload":"10","payloadType":"num","x":140,"y":3380,"wires":[["54d1d3fa.341894"]]},{"id":"93435961.047cd8","type":"inject","z":"bf9e1e33.030598","name":"","props":[{"p":"payload"},{"p":"topic","vt":"str"}],"repeat":"","crontab":"","once":false,"onceDelay":0.1,"topic":"temp","payload":"20","payloadType":"num","x":140,"y":3440,"wires":[["2fa7baad.3fa3de"]]},{"id":"dabbb79.bd98dc8","type":"inject","z":"bf9e1e33.030598","name":"","props":[{"p":"payload"},{"p":"topic","vt":"str"}],"repeat":"","crontab":"","once":false,"onceDelay":0.1,"topic":"temp","payload":"30","payloadType":"num","x":140,"y":3480,"wires":[["2fa7baad.3fa3de"]]},{"id":"c0da89bc.4309c8","type":"inject","z":"bf9e1e33.030598","name":"","props":[{"p":"payload"},{"p":"topic","vt":"str"}],"repeat":"","crontab":"","once":false,"onceDelay":0.1,"topic":"wind","payload":"5","payloadType":"num","x":140,"y":3540,"wires":[["d43a0089.f567c8"]]},{"id":"cf7eb895.076f2","type":"inject","z":"bf9e1e33.030598","name":"","props":[{"p":"payload"},{"p":"topic","vt":"str"}],"repeat":"","crontab":"","once":false,"onceDelay":0.1,"topic":"wind","payload":"30","payloadType":"num","x":140,"y":3580,"wires":[["d43a0089.f567c8"]]},{"id":"c7dafb11.d8889","type":"debug","z":"bf9e1e33.030598","name":"","active":true,"tosidebar":true,"console":false,"tostatus":false,"complete":"false","statusVal":"","statusType":"auto","x":680,"y":3460,"wires":[]}]
1 Like

Perfect!
That's a great solution @E1cid, thank you.
I've converted the range calcs into javascript, and also removed 'rain' for the moment.

function convertRange(value, r1, r2) {
    return (value - r1[0]) * (r2[1] - r2[0]) / (r1[1] - r1[0]) + r2[0];
}
if (msg.topic == "wind"){
    msg.payload = convertRange(msg.payload, [0, 50], [0, 120])
    node.send(msg)
}
if (msg.topic == "humidity") {
    msg.payload = convertRange(msg.payload, [20, 80], [120, 0])
    node.send(msg)
}
if (msg.topic == "temp") {
    msg.payload = convertRange(msg.payload, [10, 30], [0, 150])
    node.send(msg)
}

I'm now simulating weather scenarios, to find a good starting point for the calculations.

Thanks again :grin: