Garage Door Hacking

Warning! Mains Voltage! This article in no way implies any endorsement of the following methods. Safety and fitness is not guaranteed or even suggested. I do not claim or imply that these instructions are in conformance with electrical or building codes of any jurisdiction.

Between a neighbor of mine and Vivint soliciting with a demo service, I have officially contracted the home automation bug. And somehow I got it in my mind that a garage door opener and sensor was the most important first step.

Well, not quite, I first needed a “system”, or software services that do things with and to the smart things. I tried OpenHab and HomeAssistant, and decided to go with the latter. But in the meantime I had already begun plotting and scheming for the garage door. Starting with checking out the opener itself.

Before opening the case of the opener, I unplugged it. Again, we’re talking about mains voltages here. I identified several components that might be useful, power supplies, rectifiers, where the mains are, etc. But the most important piece was the endstops! I didn’t take a picture of mine, so here’s a stock photo. The two screws on either side are what you adjust from the outside of the opener, to set the travel limits. Note again that the inside of the case contains MAINS VOLTAGES. The case is not intended to be opened, and the mains circuitry and wires are not protected once inside the case. It is not recommended to add stuff like this!

I could not find a very obvious and accessible source of 5V power rail, so I set out on a circuit that would be powered entirely by the new interface. I probed and prodded, and determined that the center contact (black in this photo) was a direct ground connection (vss or common) and the red and blue each have a 10kOhm resistance to +5V, or a pullup. See Figure 1. What this means is that the blue or red wire is HIGH (+5V) unless the travel has reached that limit and the center contact is touching it and then it is driven LOW. I decided to use standard switch transistors to “read out” these levels for my own selfish purposes, at first NPN transistors as diagrammed in Figure 2. When I finally got my circuit connected up for testing, I quickly found that the gate current was sufficient to pull the blue and red wires LOW, which the garage opener machine definitely noticed. It refused to go anywhere. So a quick mod to the design and a few transistors later, I had instead PNP transistors as diagrammed in Figure 3. This of course inverts the logic which was actually better for the LEDs. This configuration now worked without side effects on the machine. Yes!

As you can see I planned to use some CAT5/5e/6 cable to run my signals, which I soon had connected up to my LittleWire. At the time I only had a single PNP transistor so I could only detect one endstop on the LittleWire, but that one was working! Alas, when I drove the command pin HIGH on the LittleWire, the garage opener would respond, but the LittleWire or the USB bus would then immediately reset, which was not super useful. My theory now is that the capacitance in the cable was drawing too much current from the LittleWire, which hit me when I was reading an excellent tl;dr on protecting Raspberry PI pins (“Don’t drive capacitive loads!” Do’h). And yes, I migrated to a Raspi for the final piece of the project.

This is getting long, and the above was, IMO, the more interesting aspects of the project. On the raspi I used pi-mqtt-gpio from github to bridge the signals into HomeAssistant, another breadboard for buffering the raspi gpio (including a current resistor to the cable for sending the close signal), and an awesome idea to zip tie the raspi to cardboard for mounting.  Here’s the rest of the pictures to wrap it up!

Breadboard Friendly Dual OneWire, Easy

I’ve decided to start blogging about the random, small, and probably insignificant ideas and timesavers I come up with.

So for this one, a while ago I had put some temp probes into an IDC connector. Seems simple enough, and I just plugged jumper wires into the IDC socket and then a breadboard.

I went to use them again this week and I thought,


well if I could just put a 2×3 header in here and straight into the breadboard… they would just need to be interleaved. I’d have probably made a 4x temp probe connector if I had any 2×6 IDC, but 2×5 is all I have right now.


So I undid the IDC and rearranged the leads (be very gentle undoing an IDC connector, or have a spare handy, or both really).

Gently press pins to center

Then you just need a standard piece of 2×3 breakaway header. Use some pliers to grip the long end of a pin and the header body. One by one, gently slide the pins so they’re centered on the header body.

Fantastic! To the arduino to measure a temperature differential between a heated chamber and ambient.

And here’s all the pics.

Kicad and Wings

You couldn’t pair up a more esoteric set. The only thing that beats wings3d’s user interface is wxwidgets.

My understanding is that wings3d vmrl (or wrl) files are used in kicad because that is just about the only open format that also supports textured faces, but then kicad goes and only supports an old obsolete vmrl format. Some programs, like FreeCAD, can export wrl files. You might get excited by that. You might then get very, very disappointed. It is not compatible.

I’ve found a pretty good groove though for creating pretty 3d models for kicad. First I generate the model using either FreeCADftsh-mt or OpenSCAD. I find FreeCAD more amenable to creating things like pin arrays, like the ones in this 0.05 pitch header I modeled, and OpenSCAD a better fit for making oddball shapes. That probably seems backwards to other people. Meh, it’s my experience. OpenSCAD is also good for making parameterized models where you can generate a slew of different sized headers or SMD DIP packages. I’ve BOMeddip-smd some MOC3031 and opto-transistors in what can only be described as a standard DIP through hole package, but with the legs bent and flattened out for SMD. This here is the footprint preview in kicad. Having this modeled in OpenSCAD, and properly parameterized, would make adding a 10 pin version quick and easy. This one was, however, modeled with FreeCAD as well.

Once I’ve got a model I’m happy with, I export it into a format that wings3d understands. I have not,
for all my trying and googling, found any format that wings3d will import with color. Nothing. Nada. If anyone knows of one, please… So my export is usually STL or obj. Now here’s the trick! Create a separate export for each color. Everything that’s black, export in one file. Everything that’s silver in another, and so on.

Now start up wings3d. You might think you could give it a file on the command line, and have it open that file! You’re wrong. At least, if the file type you’re opening is actually an importable file type and not the native .wings filetype. But actually I do open a wings file, one I’ve populated with various “materials” that wings3d uses to apply colors to the final wrl export. Spend some time playing with the materials, maybe find some existing .wings files online for examples? It’s not hard, but it’s very much not intuitive. This post has a great rundown of how to access materials, create new ones, and apply them to surfaces.

Here’s the trouble. At least, I haven’t found a way to get materials from different files and combine them into a single file! The mind boggles. So whenever I want a new color, I open up that particular file that shall forever hold all my different materials, and add the new material there, not while I’m playing with my shiny new model. I know, it’s so tempting!

So, now I’ve opened my colors file that already has the colors I want. Then I delete the ‘test objects’ from geometry graph (there’s a few windows you’ll want open from the windows menu item while you work in wings3d). With a blank workspace, Go to File -> Import -> STL (or .obj). Import each separate model file for each color. This is the trick from before. As Happy Robot Labs mentions in the linked post above, selecting the faces to color is not exactly all that easy. Dragging a selection box is effective, but you’ve got to orient things. And any concave selections… forget about it. However, each separate import becomes a group. And with the solid red box icon selected, you just click on any part of that group and the whole thing is selected. Apply the material, bam.

Finally, export the material in .wrl format. Add it to the footprint in kicad (I usually have to scale it by 1/2.54), play with the rotations, and enjoy amazing 3d board previews!

RC Networks, They Matter!

After a long hiatus, I’m finally dusting off some projects and getting back into them, well, one in particular, the sous vide controller. I knew there were board errors from the prints I ordered early last year, I had even started to fix some of them. I got the boards and components and eagerly assembled one. Once I powered it on, there was one immediate problem. The LCD contrast with a diode that I wrote about previously, well, it’s not giving so constant a contrast on this board. Maybe it’s a poor diode, maybe I’ll build a bench power supply to vary the voltage across different diodes and see how they respond.

After putting some code on the chip, I found another problem. The push button on the encoder would not work. I got nothing at all from it. From probing the board and the resistors, I discovered that the button was active high, but my idle resistors were also pull-up. Tsk tsk. Ah well, that’s an “easy” fix, just scratch out some traces, re-route (in this case a power rail) around them, no problem, and connect the common side of those resistors to GND instead.

That got the button working, but not the encoder. Long story short, I played with the hard-to-see LCD for a while and then set it down for many moons. Oh that’s right, I also had to cut the common freewheel diode leg from the transistor array because apparently that’s not supposed to connect to “common”. Oops.

Fast forward, and now I dust it off, scratch my head, and try writing some simple encoder and button tests onto it. When they failed, I turned to my schematics, and scratched my head again. What I noticed actually pretty quickly is that the encoder legs were active LOW, but the push button active HIGH! *sigh* “I see why I did that,” in a way at least. I had to tie the push button active high because it shared with the common anode on the encoder LEDs. And it would seem I found that out after I made the quadrature active low.

So, I fixed all of that. I’m determined now to get this board to work. Of course I’ll make another run with corrections, but only after I find all the corrections. A few more trace cuts, more jumpers, and I got all the inputs working. Well, kinda… The rotary worked, a little bit. But not nearly fast enough. First I sped up the polling and that helped, only a little. Then I went full on PCINT driven, and no more improvement was to be found. At this point  I was beginning to suspect the RC network was too slow.


I plugged those values into units (not that that would be particularly needed in this case, but just the same, I highly recommend units!) and looky there. Fall time of 15ms! Yikes.

So I replaced the capacitors with some 15pF I found at Ra-Elco, and now it works flawlessly.

Moral is, don’t make board mistakes.
Moral is, you’re probably going to make board mistakes.
Moral is, don’t just pick component values because … whatever? Ya, don’t do that.

LCD Contrast With a Diode

Some very long time ago I read something about using a diode forward voltage to feed v0 for LCD contrast. I tried it forthwith, and indeed it worked for me, too! Now it may well be that not all LCD look great at 0.65V on v0. YMMV

I believe I have found where I read that, if memory serves, at good ol’ Ray’s Hobby. Also known (by me at least) for the AASaver.

Speaking of AASaver, I fried mine. 🙁 Time to get a new one, and perhaps a part or two to fix the other one.

Cylon Pumpkin

In a fun diversion, I decided the day before a pumpkin carving contest to make a cylon pumpkin. Things got real when I realized I could use the polymorph I had to hold the LEDs in a curve. Here’s an example pic of polymorph in action from an instructable.

Polymorph A.K.A Shapelock

And here’s the LED fixture held together with the stuff. I got mine at SparkFun (I also got the heat gun there).

Shapelock, heat gun and finished eye
Shapelock, heat gun and finished eye

Closeup of "eye"
Closeup of “eye”

I shopped around for a bit looking for something to use for the “lens”. I ended up at an art supply store ordering a strip of translucent grey acrylic. Their computerized saw was down so they couldn’t get it right away, so I was going to go back the next morning.

When I got home I soon had the idea to use a CD jewel case, which is what you see above. It adhered very nicely to the warm polymorph.

The LEDs used are some bar indicators I picked up at Ra-Elco for 20¢ each. There’s actually 2 LEDs in each bar, 4 total in each unit. I only lit one LED per bar, because I got tired of soldering wires. :p

Next I wired it all up and wrote the code (arduino) to control the shift registers. The main loop consists of 2 smaller loops. The first shifts a single 1 down the registers after the single 1 is shifted in. The second loop shifts all 12 bits in with the single 1 bit positioned back one each iteration.

int ndigits = 12;

#define OFF LOW
#define ON HIGH

#define SCLK 2
#define SLATCH 3
#define SOUT 4

// 1 second for full cycle
#define DELAY 1000 / 24

void shift(bool b) {
  digitalWrite(SOUT, b);
  digitalWrite(13, b);
  digitalWrite(SOUT, OFF);
  digitalWrite(13, OFF);

void pulse() {
  digitalWrite(SCLK, HIGH);
  digitalWrite(SCLK, LOW);

void latch() {
  digitalWrite(SLATCH, HIGH);
  digitalWrite(SLATCH, LOW);

void setup() {
  pinMode(SCLK, OUTPUT);
  pinMode(SLATCH, OUTPUT);
  pinMode(SOUT, OUTPUT);

  digitalWrite(SOUT, OFF);
  digitalWrite(SCLK, LOW);
  digitalWrite(SLATCH, LOW);



  for (int i = 0; i < ndigits; i++) {

void loop() {
  int i = 0, j=0;

  // assume already lighted
  // shift lighted position to end
  for (i = 0; i < ndigits-1; i++) {
  // Shift backwards
  for (i = ndigits-1; i >= 0; i--) {
    for (j = i; j < ndigits; j++) {
    for (j = 0; j < i; j++) {

And here it is all wired up! I had to tear apart my sous vide to use my redboard. 🙁 Hopefully I’ll have my sous vide PCBs by the time I want to have a controller again. 😕

Everything wired up!
Everything wired up!

That nice silvery finish? I superglued a strip of static bag to the front. I only had to glue the ends.

Once I had the pumpkin all carved it was time to shove the eye into the hole. I tried only briefly to fit the whole board inside the pumpkin, the bundle of wires was very stiff and I didn’t want to risk pulling out of the breadboard or breaking the solder joints on the lens side. So I gave up and just left it hanging out the back.

Ready to cut
Ready to cut

Carved and assembled
Carved and assembled

The whole build took approximately 8 or 9 hours. A good chunk of that late into the night with a little dozing. 1 hour looking for the soldering iron. Another hour debugging the code when in fact the problem was my arduino had a fried output pin. CURSES! Soldering 24 wires to DIP leads was of course a time consuming and frustrating portion. The polymorph was easy to work with and I had the eye assembly done in only about 1 hour.

Broken, Now Fixed

Seems this blog was broken, not sure for how long. Tracked the issue to a missing AllowOverides directive for apache.

Hey googlers. If you have a wordpress site and you get 404 on every page but the main page, and you’ve checked everything else everyone tells you to do (check the .htaccess file, check mod_rewrite is on, save the permalink style again and again) and still no dice? Check apache’s AllowOverrides for the directory. 😀


Arduino LiquidCrystal library

RGB backlight, negative display LCD

As I’ve been progressing on the sous vide controller, I’ve been playing with the LCD 16×2 character display screen that I’m going to put on it. It’s a negative display, RGB backlighted steal of a deal from Amazon.

In this process I got interested in ways to drive the LCD, things like using shift registers and even this amazing Shift1 system to control a whole LCD through a shift register with 1. single. pin. Rather than download various hacked libraries from different sources, I wanted a “standard” library that yet supported all these methods. I wanted support for latching shift registers, registers without latches, and of course shift1, all in the “standard” lib.

So, I did some minor refactoring of the arduino core LiquidCrystal library and extended it with a few more constructor options. You can pass it 3 pins to use a latching shift register where everything goes through the register using just shiftdata, shiftclock, and shiftlatch. You can also pass it a separate enable pin, for 4 pins total, which should speed things up marginally as it doesn’t have to shift the whole register for each LCD enable clock edge up and down. And of course you need that enable pin to use a non-latching register (or a latching register with latch tied to clock), and you can pass 255 as the shiftlatch pin and the library won’t try to use another pin for it.

Then there’s my favorite, the callback function method. You simply define a function that takes three uint8_t types, value, mode, and nbits. The value parameter is the bits the library wants to pound into the LCD, the mode is what it wants the RS pin set to, and nbits is just somewhat of a sanity check, but you can safely ignore it if your function assumes the same nbits that you passed to the constructor. You could write a single function that can do either 4 bit or 8 bit mode, and checks nbits to do either one.

Here’s an example of just how easy it is to use the callback, as well as a link to the github project. If you just use the shift1 library, your custom callback can easily call into the shift1 library to drive your LCD, no need for hacking shift1 directly into the LCD library!