Philips Dynalite (DyNet)
Control of Philips / Signify Dynalite lighting systems over the DyNet 1 binary protocol, reached through a Dynalite Ethernet gateway that bridges the DyNet trunk onto TCP. Drives area presets and individual channel levels, and — because DyNet is a broadcast bus — tracks state passively, so a wall-panel press updates GEM without polling.
Dynalite is the lighting control platform behind a very large share of commercial fit-outs (hotels, offices, hospitals, retail) in EMEA and APAC. This driver targets the third-party integration path, not commissioning: the area/channel map is authored in System Builder by the Dynalite engineer and transcribed into GEM zone addresses.
Prerequisites
- A Dynalite Ethernet gateway on the LAN — PDEG, PDEB, PDDEG-S, or a PDTS v2 touchscreen acting as a bridge — with a DyNet-over-TCP port enabled.
- The System Builder project (or a printed schedule) giving the area and channel numbers for each load. There is no discovery on DyNet; this map has to come from the commissioning engineer.
- Network reachability from GEM to the gateway on the configured port (50000 by default).
Dynalite gateways can serve either raw DyNet frames or the human-readable DyNet Text protocol on a given port. This driver speaks binary DyNet 1 only. If the port is configured for DyNet Text the socket will connect happily and then nothing will work — see Troubleshooting.
Setup steps
- In System Builder, open the gateway's port configuration and confirm the connection type is TCPv4 and the protocol is raw DyNet. Note the port number — the default is
50000. - Go to System → Devices → Add Device and choose the Philips Dynalite (DyNet) driver (registry key
philips_dynalite). - Set Gateway IP (
ip) to the gateway's LAN address, and Gateway TCP Port (port) if it is not 50000. - Leave Join Byte (
join) at255unless the Dynalite engineer has assigned a filtered join level for third-party control. - Create one Zone per load under the Lights subsystem, and set the zone Address per the zone address format below.
- From the Script Console, run
get_levelagainst a channel zone (orget_presetagainst an area zone) and watch the device log for an inbound report frame. That round trip confirms the gateway is bridging the trunk in both directions.
Zone address format
| Address form | Example | Meaning |
|---|---|---|
area.channel | 2.3 | Area 2, channel 3 — a single dimmable or switched load. The usual case. |
area.* (or area.all) | 2.* | Every channel in area 2. Sends the broadcast channel byte 0xFF. |
area | 2 | Area-wide zone with no channel. Driven by preset recall and the area-level opcodes. |
Channels are 1-based in GEM and in System Builder; the driver converts to the 0-based value DyNet puts on the wire. Areas are 0–255, where area 0 is the global broadcast area — sending to it affects every area on the network, so use it deliberately.
Attribute reference
| Scope | Attribute | Direction | Notes |
|---|---|---|---|
| device | ip | required | LAN address of the Dynalite Ethernet gateway. |
| device | port | optional | DyNet-over-TCP port. Default 50000. |
| device | join | optional | Join byte stamped on every outgoing frame. Default 255. |
| device | default_fade | optional | Fade in seconds applied when a command carries no fade argument. Default 1. |
| device | status_interval | optional | Resync sweep in ms. Default 60000. |
| device | command_throttle | optional | Minimum ms between outgoing frames. Default 150. |
| zone | level | runtime | Current level, 0–100 percent. Written by the driver. |
| zone | state | runtime | on / off, derived from level. Written by the driver. |
| zone | preset | runtime | Last preset seen for the area. Written by the driver. |
Commands
| Command | Arguments | Notes |
|---|---|---|
on | address | Fades to 100%. |
off | address | Fades to 0%. An area-only address uses the area-off opcode instead. |
set_level | address, level, fade | level is 0–100 percent. fade in seconds, optional. |
stop_fade | address | Halts an in-progress fade and holds the current level. |
preset | address, preset, fade | Recalls an area preset. 1-based — preset 4 is 4. |
area_off | address, fade | Sends every channel in the area to 0%. |
get_level | address | Requests the channel's current level. |
get_preset | address | Requests the area's current preset. |
get_zones | — | Reports the Dynalite zones configured in GEM and re-polls each. |
raw_packet | area, data1, opcode, data2, data3 | Escape hatch for opcodes this driver does not wrap. Decimal values; join and checksum are added for you. |
Protocol notes
A DyNet 1 logical message is a fixed 8 bytes:
[0x1C] [Area] [Data1] [OpCode] [Data2] [Data3] [Join] [Checksum]
The checksum is the negative 8-bit two's complement sum of the first seven bytes. Worked example — recall preset 4 in area 1 over 2 seconds:
1C 01 03 65 64 00 FF 18
^^ preset 4, sent 0-based as 3
^^ opcode 0x65, linear preset
^^ ^^ fade word 0x0064 = 100 x 20ms = 2s
^^ join
^^ checksum
Two encoding details are worth knowing when reading logs:
- Levels are inverted.
0x01is 100% and0xFFis 0%. The driver converts to and from percent, so integrators only ever see 0–100. - Fade times use different units per opcode. Preset and area fades use a 16-bit word in 20 ms units. Channel fades carry a single rate byte, so the driver picks the opcode to match the requested duration:
0x71up to 25.5 s (0.1 s steps),0x72up to 255 s (1 s steps),0x73up to 22 min (1 min steps).
Opcodes decoded from the bus: 0x60 report channel level, 0x62 report preset, 0x65 linear preset, 0x00–0x03 and 0x0A–0x0D classic presets 1–8, 0x04 area off, 0x71/0x72/0x73 channel fades, 0x79 area fade.
Known limitations
- No discovery.
get_zonesreports what GEM already has configured. DyNet offers no way to enumerate areas, channels, or preset names — that lives in the System Builder project. - Logical frames only. Device-addressed frames (sync
0x5C) and longer DyNet 2 messages are skipped by the resync scan rather than misparsed. Systems driven purely over DyNet 2 are out of scope for this driver. - Preset names are not available. Presets are addressed by number. Names are a System Builder concept and never appear on the wire.
- A channel report does not update an
area.*zone. If you address a zone as2.*, per-channel reports for area 2 will not write to it — only area-wide frames will. Usearea.channelzones where you want per-load feedback. - Area-off fade units are assumed. The 16-bit fade word on the area-off opcode (
0x04) is sent in the same 20 ms units as preset fades. This is consistent with the documented preset behaviour but has not been confirmed against hardware; if area-off fades come out wrong, useset_levelwith an explicit fade instead.
Troubleshooting
| Symptom | Check |
|---|---|
| Socket connects, commands do nothing | The gateway port is almost certainly serving DyNet Text rather than raw DyNet. Fix the port mode in System Builder — this driver speaks binary frames only. |
| Commands work, state never updates | The gateway may be bridging one way only. Run get_level on a channel zone and look for an inbound 0x60 frame in the device log. If nothing arrives, revisit the gateway's trunk configuration. |
| Some channels ignore commands | Those channels are probably filtered by join. Ask the Dynalite engineer which join level third-party control should use, and set the join attribute to match. |
| Levels look inverted | Something upstream is passing raw DyNet bytes instead of percent. Pass 0–100 to set_level and let the driver do the conversion. |
| Commands drop under load | Raise command_throttle. The trunk behind the gateway is a slow serial bus; below roughly 100 ms frames start getting lost. |
| Preset recalls but levels lag | Expected. A preset changes levels without the controller reporting each one, so the driver re-requests channel levels about a second later. |
Related
- Devices — device and attribute administration.
- Zones — zone creation and address assignment.