Com 2 sensores de toque (é o que tenho neste momento) e um motor ocorreu-me um elevador automático, capaz de desligar ou reverter o motor cada vez que a cabina atinja um dos extremos do percurso:
O elevador em si não é muito diferente do de elevador de Linda Hamilton e a ideia da sua utilização com um Raspberry Pi e um PiFace Digital também não é original (Reinoud de Lange recorreu a microswitches em vez de sensores LEGO).
O código (um loop infinito que desloca a cabina para cima e para baixo)
O sensor no fundo do «poço» do elevadorO mecanismo que puxa o elevadorO sensor no topo do «poço» do elevadorA cabina do elevador levando um assustado base jumper
Faltava ainda um tipo qualquer de sensor para ter um sistema verdadeiramente autónomo por isso liguei um sensor de toque LEGO Mindstorms (ainda estilo RCX) a uma das entradas digitais PiFace.
O PiFace tem 8 entradas digitais com pull-ups internos (li algures que se podem desligar, deixando as entradas «flutuantes»). Como o sensor de toque RCX é um mero interruptor basta ligar um dos cabos a uma das entradas e o outro à massa. Com o sensor em repouso (interruptor aberto) a entrada do PiFace vai ler um “1” e quando ocorrer contacto (interruptor fechado) a entrada vai ficar ligada à massa e é lido um “0”.
bricklink.com: Lego Touch Sensor (879)
É muito fácil acompanhar o estado do sensor, basta ler continuamente o estado da entrada. No script abixo usei a entrada #0 e acrescentei um atraso de 200 ms entre cada leitura para não inundar o terminal com mensagens “ON!” ou “OFF!”
Para a primeira aplicação prática montei o Roaring Lion do conjunto LEGO WeDo (as instruções de montagem deste e outros modelos simples estão disponiveis no site LEGO Education).
O leão é muito simples: fazendo rodar o motor num sentido ele levanta-se nas patas dianteiras, no outro sentido volta a deitar-se (como não há sensor de posição é necessário afinar os tempos à mão)
Numa primeira fase testei comandar o leão remotamente a partir de uma sessão SSH, criando para isso um script (lion.py) em python:
#!/usr/bin/python3
import sys
from time import sleep
import pifacedigitalio
DELAY_UP = 0.17 # o leão custa um pouco mais a subir
DELAY_DOWN = 0.14 # do que a descer
pifacedigital = pifacedigitalio.PiFaceDigital()
led7=pifacedigital.leds[7]
led6=pifacedigital.leds[6]
led7.turn_off()
led6.turn_off()
comando='.'
while(comando!="s"):
comando=input("Comando: ")
if (comando=="c"):
print("Para cima!")
led7.turn_on()
sleep(DELAY_UP)
led7.turn_off()
elif (comando=="b"):
print("Para baixo!")
led6.turn_on()
sleep(DELAY_DOWN)
led6.turn_off()
elif (comando=="s"):
print("Tchau!")
else:
print("?") # comando desconhecido
É necessário dar permissões de execução ao script:
sudo chmod u+x lion.py
Para correr, basta invocar directamente o script:
./lion.py
Os comandos são simples:
c – para cima
b – para baixo
s – para sair
Funciona bem mas seria bem melhor se o leão estivesse sempre à espera de um comando e pudessemos usar o rato em vez do teclado, por exemplo a partir de um browser.
Para isso precisamos de um servidor (daemon) http – poderia ter ido para o apache mas preferi ir à procura de um servidor http mais leve e encontrei o Monkey (no passado tive boas experiências com o lighttpd e existe também o nginx):
Começamos por adicionar o repositório para usar a versão directamente mais recente em vez da que vem do mundo Debian:
sudo nano /etc/apt/sources.list
e adicionar a linha
deb http://packages.monkey-project.com/primates_pi primates_pi main
(embora só seja, mesmo necessários o monkey e os módulos liana e cgi )
Para testar basta aceder por browser na porta 2001:
http://192.168.1.123:2001/
(o conteúdo desta página está ficamente em /usr/share/monkey/)
Para poder invocar scripts de python a partir de páginas html é necessário recorrer a CGI (penso que seria possível fastcgi mas esta não é de todo a minha especialidade).
Criei uma pasta só para armazenar os scripts que vão ser acedidos por browser:
sudo mkdir /usr/share/monkey/cgi-bin
É necessário configurar o monkey para carregar o módulo CGI:
sudo nano /etc/monkey/plugins.load
basta descomentar a linha (mentendo os espaços em branco):
Load /usr/lib/monkey/monkey-cgi.so
além disso é necessário mudar a conta com que o monkey corre para poder utilizar as libraries do PiFace:
sudo nano /etc/monkey/monkey.conf
(basta mudar de www-data para root)
E finalmente reiniciar o monkey:
sudo service monkey restart
Para testar, colocar na pasta /usr/share/monkey/cgi-bin o ficheiro hello.cgi:
#!/usr/bin/python3
print("Content-Type: text/html") # HTML is following
print() # blank line, end of headers
print("<TITLE>CGI script output</TITLE>")
print("<H1>This is my first CGI script</H1>")
print("Hello, world!")
(eventualmente dar-lhe permissões de execução – sudo chmod u+x)
E aceder por browser: http://192.168.1.123:2001/cgi-bin/hello.cgi
Confirmado o funcionamento, criar 2 scripts para controlo do leão:
É pena que o CGI obrigue a que cada vez que é dado um comando seja reinicializado o python e recarregados os módulos – cada comando demora por isso demora 2 ou 3 segundos. Os melhoramentos ficam para outra altura.
Objectivo: utilizar um Raspbery Pi sem teclado nem monitor nem cabo de rede em momento algum.
Nota: as instruções são para quem usa Ubuntu e deverão servir para a generalidade dos Linuxes mas não para Windows.
Download do Raspbian (neste momento a versão mais recente é a ‘2014-01-07-wheezy-raspbian.zip’) e extrair a imagem (‘2014-01-07-wheezy-raspbian.img’).
Inserir um SD card com pelo menos 4 GB e lançar a aplicação “Disks” (gnome-disks). Seleccionar o SD Card, no meu caso o SD Card é visto como “8 GB Block Device (/dev/mmcblk0)” e carregar em “More Options” (o botão no canto superior direito) e escolher “Restore Disk Image…”
Escolher o ficheiro com a imagem Raspbian (2014-01-07-wheezy-raspbian.img) e esperar alguns minutos que a operação termine. Ficam 2 partições no SD Card:
BOOT
2.9 GB Volume
A segunda partição será utilizada como “/” pelo Raspbian e tem uma estrutura semelhante à do Ubuntu (ambos são baseados em Debian).
Basta editar 3 ficheiros:
[…]/etc/hostname
[…]/etc/network/interfaces
[…]/etc/wpa_supplicant/wpa_supplicant.conf
$sudo nano [...]/etc/hostname
A ideia é ter um nome distinto e reconhecível para podermos depois encontrar o nosso dispositivo no router wireless. Substituí o ‘raspberrypi’ que vem de origem por ‘pitagoras’.
$sudo nano [...]/etc/network/interfaces
Aqui bastou acrescentar uma linha (post-up…) para desactivar a ligação por cabo quando a ligação wi-fi estiver funcional:
auto lo
iface lo inet loopback
allow-hotplug eth0
iface eth0 inet dhcp
allow-hotplug wlan0
iface wlan0 inet manual
wpa-roam /etc/wpa_supplicant/wpa_supplicant.conf
post-up ifdown eth0
iface default inet dhcp
Assume-se IP dinâmico tanto para ligação por cabo como wireless mas pode-se determinar um endereço IP estático (não o fiz ainda por pura preguiça).
Neste ficheiro apenas estavam presentes as duas primerias linhas, o resto foi acrescentado.
ctrl_interface=DIR=/var/run/wpa_supplicant GROUP=netdev
update_config=1
network={
ssid="ID da rede Wi-Fi"
psk="Preshared Key da rede Wi-Fi"
id_str="Descritivo opcional"
}
Com um Wi-Pi para a ligação wireless funcionou à primeira (não testei ainda outros dispositivos mas pelo menos o D-Link DWA-131 deverá funcionar, está a funcionar noutro projecto). Para saber o endereço IP bastou ir ao router ver os devices ligados:
00:0f:13:38:1e:38 192.168.1.123 0 dia 0 hora 01 minuto pitagoras
Para aceder remotamente por ssh:
ssh pi@192.168.1.123
E pronto (no Raspbian a password de origem de ‘pi’ é ‘raspberry’)
O LED #7 acende e apaga segundo a segundo, tudo OK podemos passar ao controlo do motor.
As saídas do PiFace são Open Collector pelo que é necessário um pull up (ligar aos +5 V através de um resistência) para obter algo compatível com as entradas da bridge.
A bridge é alimentada pela bateria Lego Power Functions (usei um cabo Power Functions cortado a meio, aproveitando apenas os 2 condutores exteriores – um para GND e o outro para PWR).
Utilizei um voltímetro para confirmar qual o positivo e qual o negativo – no caso do modelo 8878 da foto acima o selector de velocidade ficou rodado até ao extremo no sentido dos ponteiros do relógio; no modelo 8881 é necessário deslocar o selector no sentido da ficha.
O motor é ligado à H-bridge com a outra metade do cabo anterior, desta vez utilizando apenas os 2 condutores interiores.
O script blinky.py anterior serve para testar mas para controlo manual a partir da shell do python optei por usar estes comandos:
ligar os blocos maiores entre si (o conjunto bateria + Raspberry PI e o Mindstorms NXT) tendo o cuidado de não dificultar a troca de pilhas do NXT nem o acesso aos vários botões e fichas do conjunto:
depois ligar os dois motores e as três rodas (uma roda por motor e uma terceira roda livre que serve apenas para sustentar o Rover e facilitar as curvas à esquerda ou à direita):
e finalmente os cabos, o cartão SD e o adaptador WiFi USB:
Esta foi a primeira versão, serviu para o primeiro video de demonstração mas o comportamento deixava muito a desejar (sobretudo devido ao centro de gravidade muito alto e à roda livre instável. Mais à frente mostrarei versões melhoradas, inclusive com sensores (um Rover para poder ser um robot autónomo precisa de algum tipo de sensor para entender o mundo à sua volta).
1 bateria com ficha USB (PNY PowerPack 5200mAh, à venda na FNAC)
1 cabo USB-MicroUSB (vem com a bateria)
1 adaptador WiFi USB, preferencialmente mini (D-Link DWA-131 à venda na FNAC)
1 cabo USB A-B o mais curto possível (arranjei um cabo «prolongador» USB extremamente curto numa loja chinesa e juntei um adaptador A-B mas há cabos à venda no eBay)
Poderá ser conveniente, mas não indispensável:
1 hub USB 2.0* (à venda na Worten)
1 teclado USB (à venda em todo o lado, na Mediamarkt há uns muito pequenos)
1 rato USB (à venda em todo o lado)
1 monitor/TV com ligação HDMI ou DVI (neste caso é também necessário um adaptador HDMI-DVI)
1 caixa para Raspberry Pi
* infelizmente nem todos servem, há alguns como o Targus ACH114EV que não seguem devidamente as normas e apesar de funcionarem num PC normal não funcionam no Raspberry Pi. Os modelos KUNFT H-088 e Mitsai H-092 funcionam (este último tem inclusive uma ficha para alimentação externa que poderá dar jeito se quisermos ligar dispositivos USB que consumam mais corrente do que o Raspberry Pi consegue fornecer)
É necessário ligar as duas peças mais volumosas (o Raspberry Pi e a bateria) às restantes peças Lego de um modo prático mas sólido. Optei por colar duas vigas Technic a cada uma de modo a poder tratá-las como se fossem blocos Lego normais.
Raspberry Pi + Bateria USB antes de serem legoficados
Usei uma cola de contacto própria para plásticos ABS tendo apenas o cuidado adicional de espaçar as vigas a colar com outras peças lego de modo a assegurar que a distância entre as duas respeita os padrões Lego.
Disponibilizar uma plataforma para que crianças de todas as idades se divertam enquanto desenvolvem aptidões nas áreas da Ciência e Engenharia (sobretudo Robótica).
Os blocos Lego não são apenas um brinquedo, são excelentes ferramentas pedagógicas. E além dos blocos básicos, com os quais já se pode construir quase tudo que vier à imaginação, os conjuntos Technic, Power Functions e Mindstorms permitem-nos acrescentar movimento e autonomia às nossas criações.
Nos Estados Unidos (e não só) existem várias organizações que pretendem incutir nas crianças e adolescentes o gosto pelas ciências (STEM – science, technology, engineering and mathematics). Muitas delas fazem-no justamente com Lego:
LEGO Engineering Design Group Educators (The EDGE)
a linguagem de programação Snap! da University of California at Berkeley
A Raspberry Pi Foundation surgiu da preocupação de quatro docentes do Computer Laboratory na University of Cambridge com a falta de preparação dos candidatos a cursos de ciências da computação no Reino Unido. Decidiram por isso difundir entre o público juvenil a versão moderna dos micro-computadores baratos e fáceis de programar que abundaram nos anos 80/90 (a ideia parece-me pertinente já que eu tive um ZX Spectrum 128 aos 14 anos e vejam no que deu).
Tal como no Spectrum havia uma ligação muito directa à linguagem Basic, a Raspberry Pi Foundation decidiu apostar na linguagem Python (daí o Pi que surge no nome) e ainda na linguagem Scratch desenvolvida no Lifelong Kindergarten Group do Media Lab (MIT, Massachussets Institute of Technology) especificamente para estudantes dos 8 aos 16. Esta última é uma linguagem visual que permite desenvolver programas ou animações sem ser necessário escrever código, bastando apenas juntar blocos (como no Lego) e ajustá-los às nossas necessidades.
Como o Media Lab autoriza e até incentiva o desenvolvimento de extensões ao Scratch surgiram muitos outros projectos dele derivados, incluindo alguns que permitem interagir com blocos Lego Mindstorms como o Enchanting do Southern Alberta Robotics Enthusiasts e o Snap! (anteriormente chamado BYOB – Bring Your Own Blocks) da University of California em Berkeley.
Juntando tudo (Snap! + Raspberry Pi + algumas peças Lego Technic e Mindstorms) podemos criar pequenos robots relativamente fáceis de programar, sem o preço nem o peso de um computador portátil nem a complexidade de um microcontrolador dedicado (como um PIC ou um ARM, apesar de neste campo projectos como o Arduíno terem permitido diminuir significativamente a componente complexidade).
Depois é só dar asas à criativade e ao engenho dos engenheiros e cientistas de todas as idades que possam pegar nisto.
Nesta paróquia da Diocese de Leiria onde viemos passar o fim de semana a igreja tem 2 televisores LCD que na missa vespertina passam as letras dos cânticos em formato karaoke. Além disso os próprios cânticos são em playback e em vez do regente do coro há um segundo ambão com mesa de som.
Aos Domingos as leituras passam também nos ecrans.
Dizem-me que este software litúrgico está à venda, com algum sucesso. Imagino que daqui a uns anos saia um upgrade com um pregador a assegurar as homílias. Se houver a opção «10 minutos, sem devaneios nem fugas ao tema» e a opção de download de vários avatares 3D à escolha então sim, as vendas serão colossais!
Já que tive de desmontar a Engenhoca para melhorar alguns dos pontos identificados na versão anterior aproveito para documentar melhor o projecto.
Numa nora verdadeira, a água é levada por uns recipientes (alcatruzes) montados nas extremidades dos braços da nora. Apesar de existirem versões Lego muito engenhosas que mantêm a ideia dos alcatruzes, não tenho experiência nem variedade de peças à disposição para me aventurar por aí, preferi empurrar os berlindes ao longo de uma superfície.
O trajecto dos alcatruzes forma uma circunferência mas em Lego há poucas peças grandes e curvas que possam ser usadas (há umas secções de rampa de skate mas não tenho nenhuma) e não consegui aproximações suficientemente boas com as peças-rampa (telhas) tradicionais (o berlinde ou ficava encravado entre a rampa e o braço da nora ou escorregava por entre ambos).
Optei então por uma superficie ajustável, à custa de uma corrente:
Os berlindes deslizam ao longo desta corrente, disposta como um quarto de circunferência.
A corrente tem 33 unidades de comprimento, à custa de 11 «elos» cinzentos interligados com outros10 elos brancos, todos eles «vigas» (beams) de comprimento 3, do tipo 32523. A ideia é suspender a corrente de modo a formar um quarto de uma circunferência (não muito exacta mas se for flexível o suficiente acaba por autoajustar-se com o próprio deslizar do berlinde).
Os pontos de fixação dos extremos da corrente podem ser calculados sabendo o raio da circunferência:
Como a corrente tem o comprimento de apenas um quarto de circunferência, o perímetro total será 33×4=132 a que corresponde um raio de 21 unidades:
P=2πR
Na verdade a nora tem um raio ligeiramente menor, cerca de 20 unidades (é difícil obter-se exactamente o comprimento pretendido com a combinação de peças utilizada) mas como o percurso da corrente também não segue uma circunferência perfeita acaba tudo por se ajustar.
A nora utiliza uma roda com 8 braços com pequenos alcatruzes nas extermidades.
Finalmente um pormenor da corrente depois de montada:
Consegue-se ver os extremos dos braços a roçarem a corrente: após 1 ou 2 rotações completas da nora a corrente ficou ajustada.