Dim lights based on current intensity

Hi,

I am new to Node-Red and have been able to do basic automations with home assistant. However, I am having trouble formatting a function to dim lights. Basically, I want to determine the current brightness of the light and dim it by 10%.

I don't know much about writing code and was wondering if someone could help me. So far, I found something for lowering the volume on another automation and tried to use it, but I think that it's not formatted correctly.

This is my basic flow for testing the dimming effect:

here is the details for the light (Lutron) from debug (complete message) object:

topic: "light.master_bedroom_rope_light"
payload: "on"
_msgid: "1bcb0f89.f9fed"
data: object
attributes: object
Device ID: "8"
Zone ID: "5"
brightness: 206
friendly_name: "Master Bedroom Rope Light"
supported_features: 1
context: object
entity_id: "light.master_bedroom_rope_light"
last_changed: "2018-11-28T16:31:25.318192+00:00"
last_updated: "2018-11-28T16:31:26.053885+00:00"
state: "on"

here is the data of the function node:


old_brightness = parseFloat(brightness);
new_brightness = old_brightness - 30;

newmsg.payload = { data: { 'entity_id': 'light.master_bedroom_rope_light','brightness': new_brightness } }

return newmsg;

The error I am getting is "ReferenceError: brightness is not defined (line 3, col 29)".

Also, I am not sure if I should (and how to) set a minimum brightness, say the lights are at a brightness of 20, and the formula does 20-30, will it cause a problem, because it will give a brightness of -10?

Any help is appreciated!

Thanks

That should be message.something It is not easy to see from your post, but possibly msg.data.brightness. If you hover over that field in the debug window some little buttons appear. Click one of them and it will say Path Copied, then paste that into the code to see what the path to the property is.
[Edit] Also you don't need to create a new message, just do

msg.payload = ...
return msg

Theres a great page in the docs that explains what Colin is suggesting

https://nodered.org/docs/user-guide/messages

Thanks for the quick replies. I tried to change the brightness with the correct path (msg.data.attributes.brightness), but it did not work.

Luckily, I did find a solution that worked from reddit Get Brightness of Light in Node Red

I basically took this format and modified it to dim instead of increasing the brightness of the light.

Here is what I used, in case someone else is looking for this:

newmsg = {};

    brightness = msg.data.attributes.brightness - 30;
    if (brightness < 30)
    { msg.payload = "off";}


msg.data = {"brightness":brightness};

newmsg.payload = { data: {"brightness":brightness} };

return newmsg;

I really appreciated you guys helping me solve this!

Just pointing out that that line does nothing as you never use msg again.
However, generally it is considered best practice to pass on the message that comes in rather than creating a new one, so unless you need all the other attributes of the message to be empty then it would be usual to do

msg.data = {"brightness":brightness};
return msg;

@Colin ok thanks, I am new to all of this. To keep the previous attributes, should I also start with msg = {} instead of newmsg = {}?

No, that will set msg to an empty object. All you need to do is to set msg.data and leave everything else as it is. This assumes of course that whatever you are feeding it into is not affected by any properties other than msg.data.

Ok, thanks, good to know. I will try that!

So I tried to remove msg.data = {"brightness":brightness}; and it stops the function and gives me the error "local state cache missing, sending empty payload". Maybe it is needed to move it to the payload?

I did change everything from newmsg to msg. Here is my new function node:

    brightness = msg.data.attributes.brightness - 30;
    if (brightness < 30)
    { msg.payload = "off";}

msg.data = {"brightness":brightness};

msg.payload = { data: {"brightness":brightness} };

return msg;

Are you sure that removing the msg.data line gives that error, and putting it back fixes it? If so I don't understand how your original code shown below worked

msg.data = {"brightness":brightness};
newmsg.payload = { data: {"brightness":brightness} };
return newmsg;

as that passes on newmsg, and that message does not have the property data set.
Can you just double check exactly what you now have and what works and what doesn't?
Are you passing the message on to node-red-contrib-home-assistant? Google suggests that it is that node that is generating the error.

You are right, I retested without that line and it works fine.

I did noticed today that I had connection issues with the node-red-contrib-home-assistant pallet and homeassistant. That might have been my problem... I uninstalled it and installed the node-red-contrib-home-assistant-websocket pallet instead and it seems more stable. That may have been the issue.