I was going to suggest modifying the above code slightly to use a value returned from StateChangesEvent.Await() but that seems to return an empty tuple instead of the agent I expected. So to modify it it needs a bit of an awkward workaround but I think something like below would work. This could technically not have exactly the same functionality as StateChangesEvent but might still be what you want.
settings_playerhealth_device := class(creative_device):
@editable
HealthSwitches: []switch_device = array{}
OnBegin<override>()<suspends>:void=
for (Index->HealthSwitch : HealthSwitches):
spawn {AwaitSwitchStateChange(HealthSwitch, Index)}
AwaitSwitchStateChange(HealthSwitch:switch_device, Index:int)<suspends>:void=
loop:
InstigatorAgent := race:
HealthSwitch.TurnedOffEvent.Await()
HealthSwitch.TurnedOnEvent.Await()
Print("Health switch at index {Index} changed")
I used the TurnedOffEvent and TurnedOnEvent which do return the instigator.