[Edge] Virtual UDP Sender. Eases sending WiZ lights control commands

I made a simple UDP sender able to send unicast text messages to the local network from automations. Does not receive anything.

It is designed to locally control certain features of WiZ lights not available through SmartThings integrations. E.g. this routine activates the Deep dive dynamic colour in a couple lights :dolphin::man_surfing:

Installation and use

  • Install the driver from mocelet-shared channel at https://bestow-regional.api.smartthings.com/invite/Kr2zNDg0Wr2A
  • In SmartThings app go to add new devices and Scan nearby so the UDP Sender device appears.
  • To send UDP messages create automations with the device. Write the input in the Advanced input action or, from the advanced website, in the runCommands action.
  • There is a generic ip:port message input format and syntactic sugar to craft WiZ setPilot commands.

Sending WiZ control commands

:warning: Make sure your lights have static IPs! You can achieve that by setting static reservations in the DHCP configuration of your router.

You may be familiar with the WiZ UDP code generator that tells you the message to send, mind it’s a bit outdated. Well, you can use those codes from automations now.

For instance, to activate the Deep dive dynamic scene at 100% brightness in a WiZ bulb, this generic syntax will work:

192.168.1.44:38899 {"id":1,"method":"setPilot","params":{"sceneId":23,"speed":145,"dimming":100}}

Syntactic sugar for the setPilot command avoids boilerplate. This is equivalent, you only have to write the magic keyword, the IP and the value of the params attribute:

pilot 192.168.1.44 {"sceneId":23,"speed":145,"dimming":100}

Supports multiple addresses, comma separated, no spaces. They are sent as close in time as possible to avoid popcorn effect:

pilot 192.168.1.44,192.168.1.45,192.168.1.46 {"sceneId":23,"speed":145,"dimming":100}

Useful info

Some more examples

Turn on: pilot 192.168.1.44 {"state":true}

Turn off: pilot 192.168.1.44 {"state":false}

3000K 75%: pilot 192.168.1.44 {"temp":3000,"dimming":75}

Extra-low brightness orange-ish: pilot 192.168.1.44 {"r":1,"g":0,"b":0,"w":1,"c":0,"dimming": 1}

2 Likes

Apparently the scene will remain on for now.

Is there a way to end the scene or do I turn off the lamp and the scene will stop running?

1 Like

The dynamic scene when activated is the current mode, unless you change the colour or temperature will remain there.

It’s exactly like if you used the WiZ app to pick that dynamic mode.

BTW in Matter there’s kind of a bug, if the light was in, let’s say, 2700K, you change to a dynamic mode and then want to go back to 2700K, the Matter part of the light thinks it’s still in 2700K and won’t do anything :smiley: I have some routines that change the temperature to something like 2750K and 2700K just to trigger an actual change in case it was in a dynamic mode.

1 Like

Now this works for me

The Wiz bulb can be turned on and off via UDP Sender.

This is a good backup connection. The main connection is using Matter WiFi.

1 Like

Also using Rules API rule (AWA)

  {
    "if": {
      "equals": {
        "left": {
          "device": {
            "devices": [
              "-- ID Virtual Switch --"
            ],
            "component": "main",
            "capability": "switch",
            "attribute": "switch",
            "trigger": "Always"
          }
        },
        "right": {
          "string": "on"
        }
      },
      "then": [
        {
          "command": {
            "devices": [
              "-- ID Virtual UDP Sender --"
            ],
            "commands": [
              {
                "component": "main",
                "capability": "panelorange55982.advancedControl",
                "command": "runCommands",
                "arguments": [
                  {
                    "string": "pilot 192.168.1.44 {\"state\":true}"
                  }
                ]
              }
            ]
          }
        }
      ],
      "else": [
        {
          "command": {
            "devices": [
              "-- ID Virtual UDP Sender --"
            ],
            "commands": [
              {
                "component": "main",
                "capability": "panelorange55982.advancedControl",
                "command": "runCommands",
                "arguments": [
                  {
                    "string": "pilot 192.168.1.44 {\"state\":false}"
                  }
                ]
              }
            ]
          }
        }
      ]
    }
  }
2 Likes

The rule example showcasing how to escape the JSON is a great addition, thanks!

Some notes regarding switching on/off the lights with UDP messages instead of the integrations:

  • Compared to the cloud integration for non-Matter bulbs, it is local obviously. Plus you can control lights not even added to SmartThings.
  • The “on” is compatible with WiZ rhythms since the UDPs are the same sent by WiZ app. If you turn it on from Matter it uses the OnLevel attribute of Matter but not the rhythms.
  • The UDP doesn’t have the “Off with effect” of Matter that I looove for the motion controlled lights.
  • A single UDP command can set both brightness and colour, avoiding “flashes” of the last state. In Matter they are two commands since brightness control and colour control are independent features.
  • The UDP packet could get lost, Matter has retransmission mechanisms.

While I use the UDP Sender mostly to avoid a cloud automation invoking Google Home to recall a dynamic mode, I believe it’s going to be useful in more cases. The example of low brightness for instance achieves a low brightness that I believe cannot be achieved via Matter.

I have an older Wiz bulb that does not support Matter communication.

@mocelet
Do you have any information on whether this UDP communication also works with older bulbs?

It does with every WiZ bulb, you don’t even need to have it added to SmartThings as long as you have the IP address. But I didn’t really want to create a WiZ integration :rofl:

1 Like

New version 2026-03-25

My WiZ lights are Matter so there’s already local control but, reading the comments and since you may have older bulbs around, I’ve added a nice little perk: now you can link @TapioX ‘s Virtual Dimmer to this UDP Sender so it locally controls brightness and on/off state of those non-Matter WiZ lights where the only SmartThings integration is cloud-based.

The new capability panelorange55982.wizDimmerMirror is meant to be used by mirroring rules to pass the switch and level values of the Virtual Dimmer. Internally it just creates the pilot strings to send the “state” true or false or the “dimming” params to the IPs you provide in the rule (one or more, comma separated with no spaces just like in the input strings).

Rule to copy on/off state

[
  {
    "if": {
      "changes": {
        "operand": {
          "device": {
            "devices": [
              "VIRTUAL-DIMMER-ID-HERE"
            ],
            "component": "main",
            "capability": "switch",
            "attribute": "switch"
          }
        }
      },
      "then": [
        {
          "command": {
            "devices": [
              "UDP-SENDER-ID-HERE"
            ],
            "commands": [
              {
                "component": "main",
                "capability": "panelorange55982.wizDimmerMirror",
                "command": "setSwitch",
                "arguments": [
                  {
                    "string": "192.X.X.X"
                  },
                  {
                    "device": {
                      "devices": [
                        "VIRTUAL-DIMMER-ID-HERE"
                      ],
                      "component": "main",
                      "capability": "switch",
                      "attribute": "switch"
                    }
                  }
                ]
              }
            ]
          }
        }
      ]
    }
  }
]

Rule to copy dimmer level when changes or turns on

[
  {
    "if": {
      "or": [
        {
          "changes": {
            "operand": {
              "device": {
                "devices": [
                  "VIRTUAL-DIMMER-ID-HERE"
                ],
                "component": "main",
                "capability": "switchLevel",
                "attribute": "level",
                "trigger": "Always"
              }
            }
          }
        },
        {
          "equals": {
            "left": {
              "device": {
                "devices": [
                  "VIRTUAL-DIMMER-ID-HERE"
                ],
                "component": "main",
                "capability": "switch",
                "attribute": "switch",
                "trigger": "Always"
              }
            },
            "right": {
              "string": "on"
            }
          }
        }
      ],
      "then": [
        {
          "command": {
            "devices": [
              "UDP-SENDER-ID-HERE"
            ],
            "commands": [
              {
                "component": "main",
                "capability": "panelorange55982.wizDimmerMirror",
                "command": "setLevel",
                "arguments": [
                  {
                    "string": "192.X.X.X"
                  },
                  {
                    "device": {
                      "devices": [
                        "VIRTUAL-DIMMER-ID-HERE"
                      ],
                      "component": "main",
                      "capability": "switchLevel",
                      "attribute": "level"
                    }
                  }
                ]
              }
            ]
          }
        }
      ]
    }
  }
]
1 Like

My Wiz bulb (not Matter) that I bought about 3 years ago also works. The bulb may be much older.

I first installed the bulb in the Wiz V2 app and then I got the IP address from the router.

1 Like

WiZ v2 app also has the IP information but it’s well hidden: in the device screen, three dots menu, Settings, click the arrow pointing down near the name, Device info, scroll down to see IP address and MAC address.

BTW if you bought it 3 years ago must be really old stock to not be Matter enabled, have you double checked in Settings - Integrations section of WiZ app that Matter is not available for that bulb?

1 Like

Yes That’s probably why they sold the bulbs at a discount.

I didn’t understand enough about Matter compatibility back then.


Old bulb’s Model 27147 is different

Matter support is not mentioned for the old bulb in the Integration list.

1 Like

New version 2026-03-26 introduces integer placeholders for inputs. Thanks to @TapioX for the idea!

For Rules API users, there is a new capability panelorange55982.integerInterpolator and interpolate command that allows you to write the input just like you would do normally but being able to include up to five optional integer fields that you refer in the input like $int1 up to $int5.

Example and use cases

A typical input like pilot 192.168.1.44 {"sceneId":23,"speed":145} to set a dynamic colour can be expressed as:

pilot 192.168.1.44 {"sceneId":$int1,"speed":145}

Then you can pass the id as the int1 argument of the interpolate command. The benefit is being able to pass the value from another device using a rule to copy it.

Since it is generic you can use it for things other than WiZ lights but, for WiZ lights opens more automation options:

  • A fun example I used for testing is passing the dimmer level of a virtual dimmer to the previous input (mind the escaping in the JSON rule). The regular dynamic scenes go from 1 to thirty something, you can quickly pick let’s say, 23% brightness for the Deep Dive dynamic scene. And use smart buttons to step the brightness 1% more or less to go to the next or previous scene.
  • I don’t have WiZ dual-zone lamps so can’t test it but now you should be able to link virtual dimmers to the individual zones of the lamp. Apparently it’s just a matter of adding a "devices":1 or "devices":2 parameter so the input would be like pilot 192.168.1.44 {"devices":1,"dimming":$int1} and if it’s another format or they changed it doesn’t matter given it is generic.

This is the fun example of the dimmer level to change scenes, just the then part so you get the idea of how it would look. You can use a virtual counter, the scene switcher or anything that has an integer attribute:

      "then": [
        {
          "command": {
            "devices": [
              "UDP-SENDER-ID"
            ],
            "commands": [
              {
                "component": "main",
                "capability": "panelorange55982.integerInterpolator",
                "command": "interpolate",
                "arguments": [
                  {
                    "string": "pilot 192.168.1.44 {\"sceneId\":$int1}"
                  },
                  {
                    "device": {
                      "devices": [
                        "DEVICE-TO-COPY-ID"
                      ],
                      "component": "main",
                      "capability": "switchLevel",
                      "attribute": "level"
                    }
                  }
                ]
              }
            ]
          }
        }
      ]

1 Like

New version 2026-03-27

Being a UDP Sender it needed to support Wake On LAN. Mind there are already drivers like PC Control offering remote control features, WoL included.

The syntax is wol broadcast_ip mac_address, for instance:

wol 255.255.255.255 bc-5f-f3-35-55-d9

The hex data can be written without separators, in upper case or with spaces.

Today I actually published two updates, both feature WoL but the second one being 2026-03-27T15:08 was refactored to include generic hex data sending and WiZ improvements I’ll talk about at a later date.