In order to make this device possible, we need a micrcontroller to control the Gesture Sensor and Bluetooth Module. The Gesture Sensor uses I2C protocol with an extra pin needed as in Interrupt Pin. The Bluetooth Module uses UART to send and receive data which takes two pins, but we only ever need to send data to the phone so only one pin is needed (TX). Overall that is 5 pins that are needed. Both of these devices run off 3.3V so a microcontroller that can supply 3.3V is needed. The device would also be on for long periods of time so the device would need to run off of a battery.
Our requirements for our micrcontroller look something like this:
- 3.3V Operation
- At least 5 pins
- Supports I2C and UART
- Small form factor
The first microcontroller that fit all of those requirements was the Teensy 3.1
The Teensy 3.1's statistics can be found on the PJRC webpage for the Teensy 3.1 : https://www.pjrc.com/teensy/teensy31.html
The Teensy 3.1 fits all of the requirements of this project so I decided to use the Teensy 3.1 as my microcontroller of choice.
Since the Bluetooth Module uses UART I was able to use the "Serial" Library provided in the Arduino Library. For the Gesture Sensor, I used Sparkfun's APDS-9960 LIbrary: https://github.com/sparkfun/SparkFun_APDS-9960_Sensor_Arduino_Library/tree/V_1.4.1
I used the "Gesture Test" Example and the code worked like a charm! I was able to receive the different gestures to my phone via Bluetooth! However, the Teensy 3.1's cost lead me to search for other microcontrollers. Although I was able to prove that my project is able to operate how I expected it to.
With the Teensy 3.1 costing too much, I decided to look for microcontroller's with minimal requirements. The Teensy 3.1 boasts 256kB of Flash and 64kB of RAM, however my device didn't need that much Flash or RAM, so essentially the cost for the extra Flash and RAM is waisted. Because of this I stumbled upon the ATTiny85V
The ATTiny85V is an 8 pin IC and costs a lot less than the Teensy 3.1. However that cost also means lower specifications
While the specs on the ATTiny85V on much lower than that of the Teensy3.1, we don't need a very powerful microcontroller for this device so the ATTiny85V should do the job.
In order to program the ATTiny85V we can use an Arduino Uno to act as a programmer so that we can upload code to the ATTiny85V. I set up the two microcontrollers like this:
However, a couple of problems arose when using the ATTiny85V as the microcontroller of choice.
The first problem was that the ATTiny85V actually didn't have a hardware I2C or UART. Instead, the ATTiny85V uses USI (Universial Serial Interface) to emulate I2C or UART. This means we can't use the default library for I2C and UART. For UART I used Arduino's "SoftwareSerial" Library which left the USI open for use as an I2C bus. For I2C I used Adafruit's "TinyWireM" Library: https://github.com/adafruit/TinyWireM
The second problem was that the APDS-9960 Library was only meant to be used with the Wire Library, however the ATTiny85V does not support the Wire Library. To solve this, I rewrote the APDS-9960 Library using the TinyWireM Library. The only parts that really needed to be changed with the Init, and Wire member functions. Once I did this, the library compiled.
The third problem was that the TinyWireM + APDS-9960 + SoftwareSerial Libraries required more than the ATTiny85V's 8kB of Flash. In order to solve this, I deleted all of the RX parts of the SoftwareSerial Library since I am only using the TX pin. This was fortunately enough and the size of all of these libraries together was around 7kB.
The final problem was that the microcontroller would restart in the middle of trying to guess a gesture. I first started to solve this problem by modifying the APDS-9960 Library to use the Modified SoftwareSerial Library in order to debug the program. From there I saw that the FIFO would start to fill up, but then eventually restart the entire program from the beginning. I then used the AvailableMemory Library: http://playground.arduino.cc/Code/AvailableMemory to determine how much RAM I had left at the point the program resets. However, I got varying results with the most common values being 32 Bytes left and -27 Bytes left. I determind the problem for this could have been due to the ATTiny85V running out of RAM and then restarting the program. I then tried reducing the size of the FIFO in the program, but the program would hang a lot and when the gesture would be picked, it would always pick "NONE". I unfortunately couldn't find a solution to this so I looked into another micocontroller.
With the ATTiny85V lacking a true hardware I2C and UART module, I looked to a device with around the same specifications and cost, but with on board I2C and UART. What I ended up with is the MSP430G2553.
The MSP430G2553 boasts 16kB of Flash and 512 Bytes of RAM as well as an onboard hardware I2C and UART interface. As a bonus it also has a lot of low power options which make it great to run off of battery. All of these specifications make it perfect for my device.
Setting up the UART interface was easy enough, however I ran into trouble trying to find examples using the I2C interface. Most examples online were for the MSP430G2542 which had half the amount of ram available and did not have a hardware UART. The examples from Texas Instruments only showed how to use I2C in one way only. Either Receiving or Sending, never both in the same program. To alleviate this I looked into the Energia Platform and was able to get the code up and running from there. I had originally thought of just using their Wire Library for I2C use alongside my already existing UART code, but I decided to just migrate over to Energia. Since Energia is based off of the Arduino Platform I was able to use Sparkfun's APDS-9960 Library without having to modify anything.
Due to this I deemed the MSP430G2553 my microcontroller of choice for this project!