Saturday, February 8, 2014

BeagleBone Black TTL serial camera home security system with private motion activated tweets

In 2013, I bought my first BeagleBone Black with the intention to jump head first into new robotics projects.  I had been reading a lot of books and blogs on robotics over the past few years, with my career starting taking precedence to my passion projects, but it was time to get back into it.  My last robot was a maze navigating and flame detecting & extinguishing mobile robot.  Embedded devices have evolved quite a bit since that HC12 project with the recent popularity of Arduino, Raspberry Pi, BeagleBone and similar products.  It's a perfect storm of embedded electronics fun.

To get started, I bought the BeagleBone Black starter kit from Adafruit (awesome company) and a series of parts and tools from Amazon and The Robot Shop (Canadian!) - more on this in another post.

I also needed a good introductory project to follow the classic embedded equivalent to Hello World: make a LED blink.  Since I was about to head out on a vacation out of the country for two weeks, I decided to build a home security system.

Here's my part list:
  • Weatherproof TTL Serial JPEG Camera with NTSC Video and IR LEDs
  • Adafruit Beagle Bone Black Starter Pack 
  • USB Wifi dongle
  • 2 port USB hub
  • 32Gig micro SD card
  • That's it!
I've always believed in code over hardware in design decisions.  Even with my electrical engineering background, I find it less costly, more flexible and more robust to code solutions rather than to rely on hardware.

Here's a Python code snippet of my project.

 enable_tty01 = 'sudo sh -c \'echo ttyO1_armhf.com > /sys/devices/bone_capemgr.9/slots\''   
 os.system(enable_tty01)   
 filepath = "/home/ubuntu/"  
 def initialize():   
   resp = ""  
   time.sleep(1)  
   while(serial.inWaiting() > 0):  
       data = serial.read()  
       resp += data  
       if "Init end\r\n" in resp:  
           print "Ready"  
           break  
   # Set image size to 640 x 480  
   serial.write(b'\x56\x00\x54\x01\x00')  
   resp = ""  
   time.sleep(1)  
   while (serial.inWaiting() > 0):  
     data = serial.read()  
     resp += data  
     if b'\x76\x00\x54\x00\x00' in resp:  
       print "Size set"  
       break  
 #Picture function  
 def takePic():  
   print "Take Picture"  
   # Take picture  
   cam.takephoto()  
   #Get JPG size  
   serial.write(b'\x56\x00\x34\x01\x00')  
   resp = ""  
   #time.sleep(1)  
   print "Get image size from serial device"  
   bytes = cam.getbufferlength()  
   # Write image to file  
   print "Read image from serial device"  
   return cam.readbuffer(bytes)  
 # Initialize serial connection.  
 serial = serial.Serial("/dev/ttyO1", baudrate=38400)  
 serial.write(b'\x56\x00\x26\x00')  
 cam = VCam(serial)  
 # Initialize the camera settings for the first picture.  
 initialize()  
 tweet = Tweet()  
 cam.enablemotion()  
 while 1:  
   # Continuously check for motion detection.  
   if (cam.motionDetected()):  
     # If motion is detected, take a pic.      
     cam.disablemotion()  
     frame1 = takePic()  
     string_frame = ''.join(frame1)  
     now = datetime.datetime.now()  
     filename = "%d.%02d.%02d.%02d.%02d.%02d.jpg" % \  
     (now.year,now.month,now.day,now.hour,now.minute,now.second)  
     try:  
       f = open(filepath + filename, 'w')  
       f.write(string_frame)  
     except:  
       print "Error writing the file to the system."  
     else:  
       f.close()  
     #Post the image to Twitter in a new thread to resume motion detection.  
     t = Thread(target = tweet.postimage, args = (filepath, filename))  
     t.start()  
     cam.reset()  
     initialize()  
     cam.enablemotion()  


I had a number of challenges in getting my program to work.  The main two include:


  1. The camera's baud rate is rather slow so I wasn't able to implement the motion detection on the computer and had to rely on the built in feature from the camera.  In the future, I will use a USB or IP camera instead.
  2. The wifi dongle was difficult to install but with enough googling, I was able to find working steps.  While I was working on this project, the BeagleBone Black was still relatively new compared to the Raspberry Pi so there were limited examples available online.  This is no longer the case.


And finally, the working prototype!



While I was away, I had pictures of the sun rise and sun set lighting change against the wall of my home office tweeted to me on a daily basis (they were detected as motion).  It was nice to see everything was good at home while being away.

Until next time!