So I was able to find a code example on this page: Zoom Rooms display systems on/off – Zoom Support in the projector on/off examples. Part of it looks like this:
"rules": {
"operation_time_started": [
"proj_left.power.on",
"proj_right.power.on"
],
"operation_time_ended": [
"proj_left.power.off",
"proj_right.power.off"
],
"meeting_started": [
"tv_left.power.on",
"tv_right.power.on"
],
"user_customized_event1": [
"screen_left.motor.up"
],
"user_customized_event2": [
"screen_left.motor.down"
],
"user_customized_event3": [
"screen_right.motor.up"
],
"user_customized_event4": [
"screen_right.motor.down"
]
},
"response_filters": [
{
"name": "user_customized_filter1",
"filter_regex": "(.|\r|\n)*d %1POWR=0(.|\r|\n)*",
"trigger_event": "user_customized_event1"
},
{
"name": "user_customized_filter2",
"filter_regex": "(.|\r|\n)*d %1POWR=1(.|\r|\n)*",
"trigger_event": "user_customized_event2"
},
{
"name": "user_customized_filter3",
"filter_regex": "(.|\r|\n)*d %1POWR=0(.|\r|\n)*",
"trigger_event": "user_customized_event3"
},
{
"name": "user_customized_filter4",
"filter_regex": "(.|\r|\n)*d %1POWR=1(.|\r|\n)*",
"trigger_event": "user_customized_event4"
}
]
}
Also, in each adapter, after methods, there's a response_filter section which must associate a filter with an adapter. It would have been clearer with less generic names.
Seems simple enough if you know regex (which I did a few decades ago). I think (.|\r|\n)*d %1POWR=0(.|\r|\n)* means (any character or carriage return or line feed) followed by "d%POWR=0" followed (any character or carriage return or line feed) will trigger the event.
I assume an example of how it works might be:
Zoom sends a power off command to the projector. The projector responds with a confirmation like "d%POWR=0". This matches the filter which triggers the event, which raises the projector screen.
I look forward to hearing about clever ways to use this.