We came across this Seance Table at the How to Haunt Your House website and we decided we had to build our very own Seance Table for Halloween. Instead of printing out the pattern onto multiple sheets and transferring it that way, we opted to project the image onto the wood and trace the pattern. We followed that up with detail work using (multiple) Sharpie markers. The outside border was painted with black acrylic paint because it would have been way too time and Sharpie-consuming with markers. A quick coat of wood stain and the table top looks fabulous. The table skirt and fringe really complete the look. The table top was then mounted to an existing folding card table we had.

We wanted to take the table design one step further and make it interactive for our guests. The idea was to have a crystal ball in the middle and have people ask questions and have the “spirits” answer them. To make this happen, multi-color LED lights were placed within a ceiling light fixture and controlled with hidden buttons under the table. The light fixture was painted and jeweled and Adafruit NeoPixels were used for the LEDs. A Trinket microcontroller controlled the light colors and patterns from button inputs. The whole thing was easily wired up on a breadboard and powered with a Lithium Polymer battery. One button puts the crystal ball into “standby” – pulsing white, another sets the “calculating” state – rapid rainbow colors, and the other two control “yes” – green and “no” – red.

What really made this build special for us is that we all collaborated on it – from the pattern transfer to the inking to the finishing and fabric work and to the concept and execution of the “crystal ball.” We think it turned out great and wanted to thank How to Haunt Your House for the plans and designs. Happy Halloween!

Finishing Up The Inking

Finishing Up The Inking

NeoPixels controlled by Trinket microcontroller.

NeoPixels controlled by Trinket microcontroller.

LEDs Placed in Light Fixture

LEDs Placed in Light Fixture

The Answer Is Yes

Stained and with skirt and fringe

Stained and with skirt and fringe

I’ve been using the Teensy 3.0 for an RGB LED bike wheel POV project and I am really impressed with the capabilities of this little board. For the POV to work properly, you need to know when to update the LED columns as they rotate around at different speeds. I’m using a simple hall effect sensor to accomplish that, similar to how the Adafruit SpokePOV works. As the wheel turns, the hall effect sensor detects the south pole of a magnet attached to the bike frame and generates an output pulse. The duration between these pulses are counted in the microcontroller to determine the wheel speed and thus the timing for updating the LEDs, which is important for images and patterns to remain in the same place as the wheel speed changes.

Most modern microcontrollers, including the Freescale K20 ARM Cortex-M4 on the Teensy 3.0, have hardware timers that can be used for a variety of purposes. They can trigger periodic events, keep track of elapsed times, generate precise delays, and create PWM outputs, as some examples. For this project one particularly useful feature is the Input Capture function. Basically the timer counts at a programmed clock rate up to a certain number, typically something like 65,535 for a 16-bit counter. When using input capture, the timer value is stored when an event occurs on an input, such as a falling edge (logic state high -> low). By looking at the captured timer value, you can determine the elapsed time between input conditions. In my case, the hall effect sensor output is normally at a logic high state unless it is in the presence of a magnetic south pole at which time it transitions to a logic low state. That falling edge triggers the input capture function on the Teensy and some simple math is used to calculate the time for one wheel rotation.

There is a more brute-force way of accomplishing more-or-less the same thing. I could continuously poll the state of the hall output and when it goes low note the time (the Arduino and Teensyduino environments have a function called millis() that keeps track of elapsed time in milliseconds since the program started). Then when the next pulse occurs, I note the time again and subtract the difference from the previous time.  Simple, right? So why bother with the Timer Input Capture? The reason is that all this polling and keeping track of system time takes up CPU time that could be better spent updating LEDs or doing some other function. The hardware timer can keep track of the time between pulses independently from the CPU and typically with greater precision.

For the 8-bit Atmel-based Arduino and Teensy boards, libraries exist for Teensyduino to accomplish such frequency measurement. However, since the timer hardware is so different on the Teensy 3.0, these functions had not (yet) been ported. Also, there existed very few examples (one here) of using the Input Capture function on the Teensy 3.0. So what’s a guy to do? Well, the >1,200 page (!) user manual does include a chapter on this function (Chapter 35) but unfortunately doesn’t provide any code examples. Between the manual and the example I found on GitHub, I managed to figure out how to use the FlexTimer Input Capture on the Teensy 3.0 (code examples below).

In my application, I wanted to be able to measure elapsed time between hall effect sensor pulses up to about a second. This is because a 24″ bike wheel rotates at about 1 revolution per second at about 5mph. For the POV to work well, the wheel needs to be rotating quickly and the faster the better. I’m using two LED strips 180 degrees apart on the wheel so the ideal speed is >10mph but it will still look cool at slower speeds. To measure 1 second on a 16-bit timer without overflow (meaning the counter counts up the max and then starts over at zero, effectively preventing you from determining the elapsed time), the clock to the timer must be slower than 65.535kHz.

On the Teensy 3.0, the FlexTimer module can be connected to the system clock which runs at 48MHz, an external clock source, or what’s called the Fixed Frequency Clock. The Teensy 3.0 is setup such that the FLL input is the 16MHz crystal oscillator on the board divided by 512. This FLL input branches off and is also called the Fixed Frequency Clock (MCGFFCLK).  See Chapter 24 of the manual for more info on the Multipurpose Clock Generator or page 142 for a nice block diagram. Since it runs at 31.250kHz (16M/512), using that as the clock source for the timer means that the timer would not roll over until after 2 seconds. Otherwise, with the 48MHz input, the timer would provide finer time measurement but would roll over after only 1.3ms.  A pre-scaler (up to 128) can be used to reduce the system clock input down to 375kHz, but that’s still too fast for what I need. Therefore, in my example below, I have the FlexTimer module configured to use the MCGFFCLK.

Another advantage to using the hardware timer that I have not mentioned yet is its interrupt capability. You can either poll the captured value register periodically to get your elapsed time or just let it run and have it generate an interrupt when the capture event occurs.  Depending on your application, this interrupt may or may not be useful but when implemented, keeping track of time is truly happening in the background.

Now for some code examples.  I’ve commented the lines of code to show what is being set and why but please refer to the manual for additional information about the registers and their functions. The following was implemented using Teensyduino.

const int ledPin = 13;
const int hallPin = 22;
uint16_t FTM0Count = 0;
int timerOverflow = 0;

// Setup function for FlexTimer0
void setupFTM0() {
  // Input filter to help prevent glitches from triggering the capture
  // 4+4×val clock cycles, 48MHz = 4+4*7 = 32 clock cycles = 0.75us
  FTM0_FILTER = 0x07;

  // Must set the Write-protect disable (WPDIS) bit to allow modifying other registers
  // The enable (FTMEN) bit is also set to enable the FlexTimer0 module
  // FAULTIE=0, FAULTM=00, CAPTEST=0, PWMSYNC=0, WPDIS=1, INIT=0, FTMEN=1
  FTM0_MODE = 0x05;

  // FLEXTimer0 configuration
  // Clock source is Fixed Frequency Clock running at 31.25kHz (FLL Clock input = MCGFFCLK)
  // Dividing that by 2 would have the counter roll over about every 4 seconds
  FTM0_SC = 0x00; // Set this to zero before changing the modulus
  FTM0_CNT = 0x0000; // Reset the count to zero
  FTM0_MOD = 0xFFFF; // max modulus = 65535
  FTM0_SC = 0x11; // TOF=0 TOIE=0 CPWMS=0 CLKS=10 (FF clock) PS=001 (divide by 2)
  FTM0_C0SC = 0x48; // CHF=0 CHIE=1 (enable interrupt) MSB=0 MSA=0 ELSB=1 (input capture) ELSA=0 DMA=0

  // Enable FTM0 interrupt inside NVIC
  NVIC_ENABLE_IRQ(IRQ_FTM0);

  /* Pins that can be used for Input Capture:
     Teensy Port  Name  CPU Pin  Signal
     9            PTC3  46       FTM0_CH2
     10           PTC4  49       FTM0_CH3
     22           PTC1  44       FTM0_CH0
     23           PTC2  45       FTM0_CH1
  */

  // PIN configuration, alternative function 4 on Pin 44 (Teensy 22) (FTM0_CH0)
  PORTC_PCR1 |= 0x400;
}

// Interrupt Service Routine for FlexTimer0 Module
extern "C" void ftm0_isr(void) {
  // Reset count value
  FTM0_CNT = 0x0000;

  // Save current captured count value
  FTM0Count = FTM0_C0V;

  // Keep track of overflow condition
  // Read the timer overflow flag (TOF) in the status and control register (FTM0_SC)
  if ((FTM0_SC&FTM_SC_TOF) != 0) {
    timerOverflow = 1;
    // Clear overflow flag 
    FTM0_SC &= ~FTM_SC_TOF;
  }
  else
    timerOverflow = 0;
}

void setup() {
  pinMode(ledPin, OUTPUT);
  Serial.begin(115200);
  setupFTM0();
}

void loop() {
  if ((FTM0_C0SC&0x80) != 0) { // Look for channel interrupt flag
    // Clear channel interrupt flag
    FTM0_C0SC &= ~0x80;
    digitalWrite(ledPin, HIGH);
    Serial.print("Count: ");
    Serial.print(FTM0Count/(31250.0/2)); // Captured time of wheel revolution
    Serial.print("s");
    Serial.print(" Overflow: ");
    Serial.println(timerOverflow); // Overflow happens after ~ 4.2s
    delay(100);
  }
  else {
    digitalWrite(ledPin, LOW);
  }
}

When the magnet passes by the hall effect sensor, the timer detects the falling edge of the pulse, the interrupt routine runs which saves the captured time between sensor pulses, and the overflow condition is checked which tells me if the wheel is turning too slowly.  All that happens outside the loop(). Within the loop I check to see if the interrupt occurred and then print out the computed time between pulses and the overflow condition.  Really, I don’t even need to check if the interrupt occurred – I could just directly use the stored captured count value at any time and it would be automatically updated each rotation thanks to the interrupt routine. The same goes for the overflow flag – I plan on using that to tell me if I should be updating the LEDs for the POV effect or go into a different mode if the wheel is stationary or turning slowly.

My AltStick rocket altimeter is designed around a digital absolute pressure sensor from Freescale – MPL3115A.  I chose this part because 1. it’s small 2. it’s low power and 3. it outputs readings in height (meters) or pressure.  The previous generation part, MPL115A, only provided pressure outputs.  They are both the same size and about the same power, but I really liked the fact that I didn’t have to do any additional calculations in my software to get a height reading.  It wouldn’t have been difficult but it just comes for free with the MPL3115A. The data sheet states that the accuracy could be as good as 0.3 meter or about 1 foot, so I wanted to see if that could be achieved.  Unfortunately, I was never able to get close to that – readings were all over the place most of the time – so I thought I was using it wrong.  Then a discovery was made today…

I was at the Sensors Expo and Freescale had a booth there.  They are featuring the MPL3115A on just about every development kit and eval board now.  I noticed that one of these boards had black fabric over the top.  I thought it might have had to do with this pressure sensor and I was right but for the wrong reason.  Absolute pressure sensors like the ones from Freescale and other suppliers typically have a small port or opening in the top of the device where the sensor element can sense the ambient air.  I had seen people use foam or other material over the top of such sensors to help prevent erroneous readings from turbulent air, say on a quadcopter, for example.  However, when I asked about the fabric I was told it was instead to keep the light out of the sensor. “What does light have to do with it?” I asked.  Well, apparently the sensor die is light sensitive as are those for other sensors like accelerometers, I was told.  The difference is that the pressure sensors have a hole to let air/light in while the accelerometers are completely encapsulated. Now, this would not normally be an issue since they expect the sensor to be embedded within an end-item, say a cell phone.  However, in my case, I have be experimenting and testing with the board out in the open, mainly so I can access the buttons easily. I was assured that this was a well-known characteristic of these types of sensors but I’ve read the MPL3115A datasheet back and forth many many times and I know I didn’t see any mentions about light.

After the show I dug out the datasheet and searched for the word “light” – nothing.  It does refer to an App Note which talks about handling and soldering their pressure sensors but it had really no relevance to this part and again had no mention about precautions with light exposure.  I then went to the other similar part – MPL115A – and searched through that datasheet.  Lo and behold it did mention the light precaution: The sensor die is sensitive to light exposure. Direct light exposure through the port hole can lead to varied accuracy of pressure measurement. Avoid such exposure to the port during normal operation. So it is true!  However, my complaint is that, had I never known about that other part or had the helpful people at the Freescale booth not informed me of this, how would I know about the light sensitivity? On top of that, for design engineers who are using Freescale’s Xtrinsic Freedom development platforms that feature the MPL3115A (totally exposed, by the way), they may not be aware of this.  If you are wondering, I have already mentioned this to the Freescale reps and they are going to see about updating the documentation.

Now that I am aware of the light-sensitive nature, I did find another (brief) mention of it in a presentation about this sensor (a really good read, by the way, if you are interested in this device, along with the Pressure Altimetry App Note).  I also went ahead and covered my sensor on the AltStick with a small piece of foam as you can see in the picture below.  It sufficiently blocks out light without preventing the sensor from measuring the ambient pressure.  Again, this really wouldn’t be an issue when the board is enclosed or contained within a rocket. I had planned on using heat shrink or some other material before using it in a rocket anyway to protect it against hot ejection gasses and landing impact.  The great news is that, after over a dozen ground-based tests, I am now reliably getting +/- 1 foot accuracy – achievement unlocked! Thank you Freescale for making such a great part! I think it is finally time for me to do some test launches to learn more about how this board holds up and what sort of measurements I can get from a much more dynamic environment.

Foam placed on pressure sensor to keep out light

Foam placed on pressure sensor to keep out light

Homebrew (hardware and beer) Kegerator Thermostat

Homebrew (hardware and beer) Kegerator Thermostat

Here’s a picture of a project I recently completed: a thermostat for controlling the temperature in a homebrew kegerator. I am using a small chest freezer which can hold two cornelius kegs and associated CO2 tank. I could have spent the $ to just buy a nice digital one (from my favorite homebrew supply shop, Chicago Brew Werks), but I had some parts on hand and picked up a few parts from Adafruit and pieced it all together for much less. The main switch is a 25A solid state relay which is controlled by a spare ColorNode board I had laying around (eventually I’ll use the transceiver to let me monitor/control the temperature wirelessly). The design uses the Maxim 1-Wire DS18B20 for temperature measurement (accurate to ~0.5°F with ~0.1° resolution), white I2C seven-segment display, round tactile buttons for adjusting temperature settings (high/low turn on/off points) and enabling the temperature control, and cable glands to hold the input/output power cords securely in place (not necessarily for water proofing).  The electronics are powered from the AC line input using a miniature AC/DC converter which supplies 5V @ 1W. The temperature sensor is attached via some speaker wire and encapsulated in Sugru on one end and the other end terminates at a 1/8″ stereo plug. The enclosure is a Radio Shack plastic project box into which I cut holes for the display, buttons, ON LED, power cables, and temperature probe jack. The display and buttons (and a bunch of wires) are soldered to a protoboard and mounted via standoffs to the box lid. The height of the buttons and the display almost matched up perfectly to each other when mounted on the board. I made sure to isolate the AC line wiring from the DC control wiring to make sure it would be safe to use. Overall it turned out really well and I’m looking forward to having cold homebrew on tap! For a summary and more info on the design, see the parts list and specs below. The firmware can be found on GitHub.

Item Manufacturer Part Number Price
SSR Opto 22 120D25 $30.00
PCB DigitalMisery ColorNode V1.1 $4.00
Components See CN BOM See CN BOM $6.00
AC/DC Recom Power RAC01-05SC $12.50
Temp Sensor Maxim DS18B20 $4.00
Display Adafruit 1002 $11.00
Buttons Adafruit 1009 $6.00
Hardware Ace Hardware Nuts, screws $2.00
Cable Glands Adafruit 761 $4.00
Cords CNC Tech 800-0.75-44L-BL-00200 $9.00
1/8″ Plug Radio Shack 274-284 $4.50
1/8″ Jack Radio Shack 274-249 $3.50
Wire Radio Shack Speaker wire $1.00
Box Radio Shack 270-1803 $5.50
Proto Board Sparkfun PRT-08815 $4.50
 Parts Total $107.50
Specifications
Temperature Accuracy ~ 0.5°F
Temperature Resolution 0.1°F
Temperature Range -67°F to +257°F
Temperature Regulation High/Low Temp Points
Temperature Update Rate Once per second
Solid-State Relay Rating 25A
SSR Motor Rating 1/3 HP (248W)
My Kegerator (small Jewel freezer, fits 2 kegs)
Volume 5.3 ft^3
Compressor Current 1.5A
Compressor Power 180W / 1/4 HP