New domain and blog

New domain and blog
Please head over to my new domain to view my blog and current projects

Monday, 29 October 2012

Raspberry PI: Bottlepy and Twitter Bootstrap

I have been using my Raspberry Pi for the last few months quite a lot. I am currently working on a temperature/environment monitor that logs temperature, using a DS18B20, and light conditions using an optical sensor. I also have two LED's and two buttons to test basic input and output.

I am developing the application in python using the BottlePy framework. I chose the BottlePy framework as it is a single file that you add, it is very small and it works with Python 3. To control my GPIO's, I am using the Quick2Wire library. To display the temperature data, I am using Google Charts.


This is a picture of the main temperature logging page so far.

However, the purpose of this post is to show how to integrate BottlePy and Bootstrap by Twitter. According to their website, Bootstrap is a "Sleek, intuitive, and powerful front-end framework for faster and easier web development."

To display this, I am going to use my GPIO code which reads buttons and turns on LED's through a webpage. 


To start off we need python file that will run as the server. Below is a snippet of code. The @route shows that this particular function will be run when /gpio us entered into the browser. The webpage is broken up into four sections. The first controls LED 1, the second controls LED 2, the third gets the state of both buttons and light sensor and then the fourth runs a .c file to flash the LED's.

@route('/gpio', method="GET")
def gpio():
import os
from quick2wire.gpio import Pin, exported
colour1 = 'white'
colour2 = 'white'
colour3 = 'white'
#GET for when the LEDs are toggled or flashed
if request.GET.get('Led1On','').strip():
#turn on LED 1
from quick2wire.gpio import Pin, exported
with exported(Pin(12, Pin.Out)) as out1:
out1.value = 1
elif request.GET.get('Led1Off','').strip():
#turn off LED 1
from quick2wire.gpio import Pin, exported
with exported(Pin(12, Pin.Out)) as out1:
out1.value = 0
elif request.GET.get('Led2On','').strip():
#turn on LED 2
from quick2wire.gpio import Pin, exported
with exported(Pin(13, Pin.Out)) as out2:
out2.value = 1
elif request.GET.get('Led2Off','').strip():
#turn off LED 2
from quick2wire.gpio import Pin, exported
with exported(Pin(13, Pin.Out)) as out2:
out2.value = 0
elif request.GET.get('cFlash','').strip():
#flash LED 1 and LED 2 with c routinr
os.system('sudo ./cFlash')
elif request.GET.get('getButtonState','').strip():
#script to get the states of the button.
with exported(Pin(18, Pin.In)) as in_pin1, exported(Pin(11, Pin.In)) as in_pin2, exported(Pin(15, Pin.In)) as in_pin3:
if(in_pin1.value == 1):
colour1 = '#80FF00'
if(in_pin1.value == 0):
colour1 = '#FF0000'
if(in_pin2.value == 1):
colour2 = '#80FF00'
if(in_pin2.value == 0):
colour2 = '#FF0000'
if(in_pin3.value == 1):
colour3 = '#81DAF5'
if(in_pin3.value == 0):
colour3 = '#A4A4A4'
return template('templates/gpio.tpl', colour1=colour1, colour2=colour2, colour3=colour3)
view raw GPIO.py hosted with ❤ by GitHub

Now we need to have a look at the html code that creates the webpage. By default, Bootstrap works with the user downloading the .css and .js file. These are then statically linked to the html code. When using the BottlePy framework, I haven't found a way to return a webpage template, AND a static file. Therefore I have found a link where the .css and .js files have been hosted. By using these links, you only have access to the default settings, but they are enough for what I am wanting to do.

<!--
You are free to copy and use this sample in accordance with the terms of the
Apache license (http://www.apache.org/licenses/LICENSE-2.0.html)
-->
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Strict//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-strict.dtd">
<html xmlns="http://www.w3.org/1999/xhtml">
<head>
<title>Raspberry Pi GPIO control</title>
<link href="//netdna.bootstrapcdn.com/twitter-bootstrap/2.1.1/css/bootstrap-combined.min.css" rel="stylesheet">
</head>
<body>
<script src="//netdna.bootstrapcdn.com/twitter-bootstrap/2.1.1/js/bootstrap.min.js"></script>
<div class="navbar">
<div class="navbar-inner">
<ul class="nav">
<li><a href="/index">Go to the index</a></li>
<li><a href="/gpio">Control GPIO</a></li>
<li><a href="/climate?from=&to=&selectDate=Update+graph+to+selected+Dates">Environment graph</a></li>
</ul>
</div>
</div>
<div class="container">
<form action="/gpio" method="get">
<div class="row-fluid">
<div class="span3">
<input type="submit" class="btn" name="Led1On" value="Led1On">
<input type="submit" class="btn" name="Led1Off" value="Led1Off">
</div>
</div>
<br/>
<div class="row-fluid">
<div class="span3">
<input type="submit" class="btn" name="Led2On" value="Led2On">
<input type="submit" class="btn" name="Led2Off" value="Led2Off">
</div>
</div>
<br/>
<div class="row-fluid">
<div class="span3">
<input type="submit" class="btn" name="getButtonState" value="Get state of buttons">
</div>
</div>
<br/>
<table class="table table-bordered" style="width:170px">
<tr style="border:1px solid grey">
<td bgcolor="{{colour1}}" style="border:1px solid grey"><strong>Button 1</strong></td>
</tr>
<tr style="border:1px solid grey">
<td bgcolor="{{colour2}}" style="border:1px solid grey"><strong>Button 2</strong></td>
</tr>
<tr style="border:1px solid grey">
<td bgcolor="{{colour3}}" style="border:1px solid grey"><strong>Light level</strong></td>
</tr>
</table>
<div class="fluid>
<div class="span3">
<input type="submit" class="btn" name="cFlash" value="Flash LED">
</div>
</div>
<br/>
</form>
</div>
</body>
<footer>
<div class="navbar" style="position: fixed; bottom:0; left:0; right:0">
<div class="navbar-inner">
<ul class="nav">
GPIO controls external sensors from the Raspberry Pi
</ul>
</div>
</div>
</footer>
</html>
view raw GPIO.html hosted with ❤ by GitHub

You have to link to the .js and .css file and then by using certain classes that have been defined and explained on the Bootstrap website, you can get nice looking buttons, navigation bars, and tables. They have many options to use but these are the three that I used here for my site. 

When a button on the website is pressed, it sends the value back to the python function and the python code will perform the task. With the Flash LED button, the python code calls a .c file that has been compiled and runs when called. 

When requesting the button state, I return hex formatted colours to show the state of the buttons. These the colour in the table. 


The red shows that Button 1 has been pressed, the Green shows that Button 2 is not pressed and the Blue shows that the light level is currently light.

There are many different elements that can be added by using the Bootstrap framework. The documentation is really clear and easy to follow with many examples. 

If you get stuck or need some more explanations give me a shout.

Greg

Embedding Gist code into Blogger

I have been playing with my Raspberry Pi and Linux for a few weeks now. Most of the example code has been published on GitHub so I thought I'd give it a go and see what it's all about.

At first I tried to add a repository and then the code snippets. That didn't seem to work as I liked so had a quick look around and saw that you can add a Gist and embed that a lot better. You are also able to link to a raw piece of code. This will hopefully come in handy as I have an idea on how to use this. If it works I will cover it in another post.

All you need to do is create a GitHub account and add a new Gist. Save the Gist get the embedded link.

When you are writing your post, switch to HTML view and paste the script where you want it to appear in your post. You can then switch back to normal view to finish writing the post.

@route('/flash')
def flash():
# import flash
# flash.flashLed()
return template('templates/flash.tpl')
@route('/c_flash')
def c_flash():
return template('templates/c_flash.tpl')
@route('/toggle', method='GET')
def toggle():
if request.GET.get('Led1On','').strip():
#turn on LED 1
from quick2wire.gpio import Pin, exported
with exported(Pin(12, Pin.Out)) as out1:
out1.value = 1
return template('templates/toggle.tpl')
elif request.GET.get('Led1Off','').strip():
#turn off LED 1
from quick2wire.gpio import Pin, exported
with exported(Pin(12, Pin.Out)) as out1:
out1.value = 0
return template('templates/toggle.tpl')
elif request.GET.get('Led2On','').strip():
#turn on LED 2
from quick2wire.gpio import Pin, exported
with exported(Pin(13, Pin.Out)) as out2:
out2.value = 1
return template('templates/toggle.tpl')
elif request.GET.get('Led2Off','').strip():
#turn off LED 2
from quick2wire.gpio import Pin, exported
with exported(Pin(13, Pin.Out)) as out2:
out2.value = 0
return template('templates/toggle.tpl')
else:
return template('templates/toggle.tpl')
view raw test.py hosted with ❤ by GitHub
That's about it really. Pretty simple and quick to add code. This is much easier than some of the other methods that I have seen where you have to edit the HTML code of the template with custom java script code.

Greg