Having previously created a Border Router and a Six Channel LED Dimmer for my custom Myha home automation system, the next item on the list was to create a Myha version of the touch switch that I’d previously made for the Rako system. This was actually the third version of the touch switch as I’d made two Rako versions, the first using an official Rako switch contact module and the second communicating directly over the air after I’d reverse engineered the RAKO protocol.

As this was version three, the bulk of the hardware design was already fairly well proven and little had to change, mostly it was just a case of changing the radio and firmware. However, this was the first version to be installed in a wall, and this is where a few surprises were to be found.

The Sensor

Myha Touch Sensor Assembled

Myha Touch Sensor

Like the previous versions, the touch switch uses a capacitive sensor that is fixed to the back of a wall tile. This sensor consists of a large copper pad connected to an Atmel AT42QT1011 single button touch sensor IC. When the IC senses a touch through the wall tile, it sets its output pin high. This pin is simply connected to ground via a current limiting resistor so that when a touch is sensed the current consumption of the sensor increases from less than 1mA to 10mA. This allows the sensor to be connected by just two wires, using the same wires that supply the 5V needed to power it, to also signal the touch events.

The only difference between the sensor for this version and the sensor from the previous versions is the removal of the LED and its bypass capacitor, which serve no purpose when the sensor is installed, so removing them just improves reliability. Also, as I was getting the other boards made, I took the opportunity to get the sensor board professionally manufactured instead of the home etching job from the previous versions.

The Controller

Myha Touch Controller Assembled

Myha Touch Controller

The controller also remains very similar to the previous versions. It uses a 1 ohm shunt resistor in series with the remote sensor, and with this and a specialised current monitoring op-amp it is able to monitor the current consumption of the remote sensor. The current consumption of the sensor varies from less than 1mA when it’s not being touched to around 10mA when it is being touched, and as a result, the voltage drop across the shunt resistor varies from less than 1mV to around 10mV. The current monitor has a fixed gain and amplifies the voltage drop across the shunt resistor by fifty times, so the output of the current monitor rises from around 50mV to 500mV when the sensor is touched.

The output of the current monitor is fed into one side of the microcontroller’s analog voltage comparator, and the other side of the comparator is fed with a 250mV reference voltage which is derived from the 3.3V supply by a simple voltage divider. The microcontroller is the biggest departure from the previous versions, the Atmel ATTINY861 that was used in both previous versions was replaced with the Atmel Zigbit module that I’ve used in all of the Myha devices, and along with it have come the same Microchip MAC address EEPROM, ISP header and UART header that the other devices have had.

The final change from the previous versions was the power supply, both of the previous versions used linear regulators, but with this version I changed to a self contained switching regulator module. This change was made because I intend to power the controller from the same 12V supply that powers the LEDs in my bathroom light, which means dropping from 12V all the way to 3.3V, which isn’t very efficient when using a linear regulator. Unlike the linear regulator that it replaces, the switching regulator doesn’t have an enable pin, so I’ve also had to add a logic level MOSFET on the low side of the sensor to allow it to be power cycled by the microcontroller.

The Firmware

Touch Sensor Heartbeat

Touch Sensor Heartbeat

The firmware for this version is of course completely different from the others. Not only does the Myha version add a complete IPv6 networking stack (thanks to the Contiki operating system), but it’s operating principle is almost the exact opposite of the Rako versions. The Rako versions of the switch were configured to send specific commands to a specific device when they were operated, in contrast, the Myha version simply publishes its state whenever it changes, it is then up to other interested devices to subscribe to these state changes.

As with all Myha devices, the touch switch publishes its state to MQTT topics, and all of those topics start with the device’s MAC address followed by the sub-device ID. The touch switch has two main topics:

  • [mac_address]/1/press
  • [mac_address]/1/hold

The press topic is published whenever the switch’s pressed state changes, it has a value of “1” when the switch is being touched and a value of “0” when it’s not being touched.

The hold topic is published whenever the switch’s hold state changes, this happens when the switch is touched for a long time, which is currently defined as anything longer than 0.5 seconds. When the switch is touched for a long time the topic’s value is set to the current duration of the hold in microseconds, and the value is updated several times per second until the switch is released. When the switch is released the topic’s value is updated to be the final hold duration but with a minus sign prepended.

The reason for providing a duration instead of simply “1” and “0” for held and not-held, is to allow multiple devices that might be subscribed to the hold topic to stay in sync with each other. I’m planning on having the switch behave the same as the other light switches in the house, which is to have a single press toggle the on / off state, and a hold to dim up or down. If there are multiple devices subscribed to the switch and they all start to dim up when receiving the hold event, then the relative brightness will depend on the exact timing of their reception of the hold event messages, which will lead to them all changing by a slightly different amount. This error would then accumulate every time the lights are dimmed, until they are totally out of sync with each other. By adding the hold duration to the messages they can correct for delays, and by having the final duration in the release message they can correct the final brightness level and stay in perfect sync with each other.

The code, which can be found on github should be fairly self explanatory, the only part which might need some explanation is the filtering of the comparator output.

The Atmel touch sensor IC adds a heartbeat to the output to show that it is operating, which is visible as a periodic drop in the output while the sensor is being touched. Without any filtering this makes it look like the switch is being briefly released several times per second. To ignore the heartbeat and any other noise that might occur, the output of the comparator is filtered. This is done by sampling the output in a timer interrupt, which is configured to trigger approximately 4,000 times per second, and putting the current value into a rolling average.

  static uint16_t x = 0;
  // Filter the input to ignore the heartbeat and other noise
  // It takes 5 sequential 1's to go from zero to 248
  // It takes 5 sequential 0's to go from 256 to 8
  // We're called roughly 4,000 times per second so a change
  // in state has to hold steady for a little over 1mS to be
  // counted.
  x += ((ACSR & BIT(ACO)) ? 0 : 256);
  x >>= 1;
  if(x >= 248 && value == 0)
    value = 1;
    duration = 0;
  else if(x <= 8 && value == 1)
    value = 0;
    duration = 0;
    if((duration & 0x7f) == 0 && value == 1)


Touch Switch Wired In Touch Switch Siliconed To Tile Light Switch Tile

The sensor was to be installed behind a 10mm thick porcelain tile on my bathroom wall. Before installing the sensor, I coated it with acrylic conformal coating to protect it from the tile adhesive. After that I attached it to the back of a tile using silicone sealant as an adhesive, and also to ensure that there was no air gap between the sensor and the tile. This is necessary as any air gaps greatly reduce the sensitivity due to the very low dielectric constant of air (1) compared to porcelain (6-8).

After 24 hours, once the sealant was fully cured and the sensor was firmly attached to the tile, I covered the back of it with tile adhesive and attached it to the wall. I then waited for 24 hours for the adhesive to dry, after which I powered up the sensor, touched the tile, and… it didn’t work!

The output of the sensor was permanently high. My initial thought was that maybe the tile adhesive was still wet and conducting current between the supply wires, the ends of which weren’t covered by the conformal coating. However, after attaching my oscilloscope to the output, I was able to see that there were heartbeat pulses visible, which meant that the touch controller was operating correctly, but apparently sensing a touch. Still thinking this might be due to damp adhesive, I tried poking the probes of my multimeter into the adhesive, and found that if I pushed hard enough it read just under 1Mohm from one side of the tile to the other. This seemed likely to be the reason for the false sensing.

I then tested the resistance of the adhesive daily, and over the next week it gradually rose until it passed 10Mohm and then finally, I couldn’t get a reading any more. By this time the sensor had stopped registering a permanent touch, which confirmed the wet adhesive theory. However, when I touched the tile it wasn’t detected.

Hoping that it might still be dampness that was the issue, I waited another week, but after that it still wouldn’t sense a touch. So, the worst case scenario had happened and I had to find a way to get the tile back out without damaging those around it.


Siwtch Tile Removal 1 Siwtch Tile Removal 2 Siwtch Tile Removal 2

This is where having very hard porcelain tiles is a distinct disadvantage, I tried breaking a scrap of tile by placing the point of a thick wood screw on it and hitting it with a hammer, this resulted in some sparks, a scratched tile and a bent screw!

So, on to plan B, which was to use a 30mm diamond hole cutter to remove a large part of the middle of the tile so that I could get behind it to lever it off of the wall. As the photos above show I covered the surrounding tiles in scraps of thin plywood to protect them. I then used another thicker piece of plywood with a 30mm hole in it as a guide to hold the cutter in place while the bit got started into the tile, though even with this it was hard to stop the cutter dancing around all over the front of the tile.

It ended up taking nearly two hours to cut two overlapping holes, not helped by having to constantly dunk the cutter in water to cool it, which half the time resulted in it falling out of the drill chuck as it contracted. But, after removing the centre of the tile, it was then quite easy to prise it out, especially as most of its area was only held in by silicone sealant.

Notably, the adhesive behind was still very damp. I guess non-porous tiles at the front and semi-waterproof cement render at the back make it hard for moisture to escape.


Deja Vu bathroom-touch-switch-box bathroom-touch-switch-bubblewrap

With hindsight, I think the sensing problem is fairly obvious. The sensor works by sensing the characteristics of a capacitor that is formed by the large copper pad on the board and the power supply ground. As well as by a person touching it, the sensor can be activated by touching it with a grounded wire. When the sensor was fixed to the wall there was tile adhesive, presumably with a fairly high dielectric constant, connecting the ground wire to the sensor pad.

The Atmel touch sensor IC is self calibrating, so when it’s powered on it will adjust itself so that it is not triggered. When the sensor was first installed and the adhesive was very wet it was probably unable to calibrate itself which resulted in the permanently triggered state. As the adhesive dried out it was able to calibrate itself to a non-triggered state, but then due to the connection of the ground wire to the pad through the tile adhesive, touching the tile wasn’t making enough of a difference to the overall capacitance to be detectable.

Not wanting to have to remove the tile twice, I countered this problem in three different ways for the second installation:

  1. I constructed a plastic enclosure over the back of the sensor to enforce an air gap between it and its surroundings. This was constructed by cutting up a plastic enclosure and glueing it to the tile with silicone sealant.
  2. I wrapped the ground wire in bubble wrap and then wrapped that with a layer of electrical tape, so that the ground wire is effectively sitting in the middle of a column of air.
  3. I only applied tile adhesive around the sides of the hole, this made it much harder to hold the tile in place while the adhesive set, but means there is very little adhesive around the back of the sensor and the ground wire.

This may be overkill, but with the sensor enclosed I was able to test it immediately while the adhesive was still fresh and removable, and the end result is a working sensor.

It is however not as sensitive as it was when testing on the bench, when it’s in the wall, a single finger tip generally isn’t enough to trigger it, instead it requires two fingers or a single finger with the rest of the hand close by to reliably trigger. In practise this is fine as people tend to press it with their whole hand rather than the tip of a single finger, but it is surprising.

I was also never able to recreate the permanently on state on the bench, even when going as far as pressing the entire unprotected sensor, component side down, into a grounded wet sponge. So there’s still something about being in the wall that is different in a way I don’t quite understand.


Sensor Hardware

Browse: github
Schematic: png
Gerbers: zip

Controller Hardware

Browse: github
Schematic: png
Gerbers: zip

Controller Firmware

Browse: github

Leave a Reply

Your email address will not be published. Required fields are marked *

Post Navigation