Friday, May 22, 2009

X10 Wireless Temperature Transmitter

This is a battery operated Arduino project that uses the CM17A to wirelessly transmit the temperature to the power line. From there, it is picked up by the X10 Book, (see below) and displayed and logged. (It can also be used to trigger macros.)

The PSC05/TW523 will not receive X10 "extended" codes. Therefore I had to get tricky with how I sent the temperature and how I received it. This means that the technique requires you to have control over the receiving end as well.

The idea is simple. An entire House Code is dedicated to the temperature. Each digit is sent as a Unit Code representing that digit (i.e. Unit Code"3" is sent if the digit is 3). The Command is used to indicate the digit position. So for the least significant digit, I used "OFF" for the next digit I used "ON". BRIGHT and DIM can also be used for more positions or to represent + and -. So with 4 types of commands (and 4 separate transmissions) you can transmit variables up to "9999" or "+/-999".

[detail . . .]
Since Unit Codes really have a range of 1-16 you could use this to transmit even larger values - with 2 transmissions you could transmit and digit up to 255. However I choose not to do this because the CM17A is transmitting to the same (TM751) receiver that I use to receive form a motion sensor. The motion sensor uses Unit Codes 1 and 2. So in actuality I offset the digits by 5, leaving the first 5 Unit Codes. (Two for the motion sensor and 3 reserved.) I'm sure there are other methods you can use to transmit values, but this works fine for me.

So much for theory!
Since the CM17A is wireless, it's a nice idea to make the whole thing battery operated. There are techniques to use with the Arduino to conserve battery power. I used one that combines "sleep" mode with the "watchdog timer" There is a good example of this here. The idea is to have the Arduino in low power sleep mode, wake it up every now and then, and have it read and transmit the temperature before going back to sleep. The example cited has a maximum sleep time only 8 seconds, but on waking, a variable can simply be incremented and skip sending until say 10 wakeups have occurred. Mine sends the temperature about every 2 min. (The less often you send, the longer your battery lasts.)

I used the DS1621 temperature sensor. It's I2C and simple to connect. You will find examples of how to use it on the Arduino Forum.
I put everything in a waterproof box. A word about the picture. You can see the DS1621 temperature sensor on the "spring" ribbon cable. The green square on the right is the CM17A with it's jackets removed and covered with heat shrink tubing. The Arduino (ATmemg128) board is a custom board I made that includes a boost circuit so it only needs 2 AA batteries. You can use any Arduino and use 3 AA batteries instead.

On the temperature receiver side (the X10 Book in my case) I look for commands from the dedicated temperature House Code. When I get one, I determine which digit position it represents by the command code, convert the Unit Code into a digit, and store it in a global for that digit position. It's OK if a digit is somehow missed, it's likely to be picked up from the next transmission. When I want to log or display the temperature (periodically or using the TV Remote) I simply multiply the values in the various digit positions to get the current temperature.

Here's a short video . . .


  1. Very useful, a real contribution!
    Please keep posting.

  2. What kind of battery life do you get out of the temperature sensor?

  3. Right now I'm getting 27 days using 2xAA NiMH (eneloop) batteries. The temperature is sent every 6 min.

    I have some things I'd like to try to improve this like setting unused pins so they don't float.

  4. This is pretty slick! Do you recommend using resistors on the outputs going to the CM17A? Arduino recommends resistors on the outputs but I'm not sure if there's a need here.

  5. Thanks!
    To be honest, I never thought about using them! I've never measured how much current the CM17A uses, but I expect it's much less than the 40mA / pin max. After all, it was made to steal power from RS232. But my answer has to be - I don't know.
    I do know I have a couple of these running for several months now with no resistors and no problems. Hope this helps.

  6. So you're using X10 protocol to send data.
    I've wondered if that was possible, but never got around to trying it.
    Nice job.
    You could really send any kind of sensor data.

    What is the maximum bit rate? It's slow but that really doesn't matter.