Tutorials:Controlling devices with multiple switches
Consider the situation where you have two doors into a room, each with a light switch next to it, or a switch at the top and bottom of a flight of stairs. Either switch needs to be able to control one or more common lights (say you want to be able to turn the lights on at one side of the room, walk to the door on the far side and turn the lights off with the switch next to that door). In real life, this trick is done using some clever wiring - I wanted to try doing it in dromed using nothing but fnords. What I ended up with is this (borrowing some symbols from digital electronics):
(As a side note, this is actually an implementation of an exclusive-OR gate..)
The "Any" object is a RequireAnyTrap (an OR gate), the two "All" objects are RequireAllTraps (AND gates) and Inv is an Inverter. S1 and S2 are the input switches, O is the output (which may be one or more objects). To set this up in Dromed:
- Place your two switches, call them S1 and S2.
- Add the objects you want to control - lights, doors, whatever.
- Add one RequireAnyTrap fnord and rename it Any.
- Add two RequireAllTrap fnords and call them All1 and All2.
- Add one Inverter fnord, call it Inv.
- Add a ControlDevice link from S1 to Any.
- Add a ControlDevice link from S1 to All1.
- Add a ControlDevice link from S2 to Any.
- Add a ControlDevice link from S2 to All1.
- Add a ControlDevice link from Any to All2 (line a on the diagram).
- Add a ControlDevice link from All1 to Inv (line b on the diagram).
- Add a ControlDevice link from Inv to All2 (line c on the diagram).
- Add ControlDevice links from All2 to all the controlled objects.
Note that, to keep object counts down, you can apply the TrapRequireAll, TrapRequireAny, and TrapInverter scripts to any 'spare' objects you have around that do not already have scripts on them, and use them instead of dedicated fnords.
So, how does this work? To begin with, have a look at this truth table:
Now, say that initially both switches are off (line 1 in the table). You enter the room and frob S1. Now S1 is on and S2 is off (line 2 in the table). At this point, the output of the RequireAnyTrap is On, the output of All 1 is off, but the Inverter changes this to On. So now All2 is seeing On at both of its inputs, so it send out On to the controlled devices.
Now say that you walk across the room and leave, frobbing S2 on the way out. Now we move to line 4: both S1 and S2 are on. The RequireAnyTrap outputs On, All 1 outputs On, but now the Inverter changes that to Off, so All 2 is now seeing one On and one Off - so it sends an Off to the controlled objects.
Some time later you come back into the room via the door next to S1. Remember that S1 and S2 are still both On. You frob S1, moving from line 4 to line 3 in the table.
There are only two issues you need to keep in mind when using this method:
- if you want your light (or whatever) to be on when the level starts, you need to set one of the switches on and the other off. It doesn't matter which, but they can not be both on or off when the light is on (see the table above!)
- the Inverter needs to be "primed" with a TurnOff at the start of the level before the system works properly. This only needs to be done once, and can be done as part of initialising other on-start effects (see this page at The Dromesday Book for how to do this - I usually stick NVRelayTrap on a spare object, set its design note to
NVRelayTrapOn="Sim";NVRelayTrapTOn="TurnOff", and then link it to the inverter).