Esse artigo é uma sequência do artigo “Integrando processing e Arduino com a biblioteca Firmata”. Anteriormente entendemos o que é o Processing e como programar o Arduíno escrevendo somente no Processing via a biblioteca firmata. Hoje, vamos aprender sobre as suas funções principais. Para isso, vamos montar um circuito com Arduino, LDR, Chave Táctil, Buzzer e LED e criar uma interface no Processing para ser controlado pelo computador.
Materiais Necessários
- 1x Arduino Uno
- 1x LED
- 1x LDR
- 1x Buzzer
- 1x Chave Táctil
- 1x Protoboard
- Jumpers
- 1x Resistor 220 Ohms
- 1x Resistor 10K Ohms
- 1x Resistor 47K Ohms
Circuito Fritizing
Programando o Arduino para criar a interface no Processing
Como foi mostrado no artigo anterior “Integrando processing e Arduino com a biblioteca Firmata” primeiro precisamos programar o Arduino com o sketch firmata. Na Arduino IDE vá em:
Arquivos > Exemplos > Firmata > StandardFirmata
Posteriormente vamos preparar o circuito no Arduino, basta seguir as ligações como na imagem do circuito feita no Fritizing.
Como criar a interface no Processing?
Vamos simular o interior de um carro no Processing. A chave táctil fará o papel do botão de ignição ligando o carro, o LDR irá controlar o dia e a noite no exterior do carro, o LED responderá ao botão de alerta e o Buzzer a buzina. O interior do carro será como as imagens abaixo (você pode salvá-las no seu computador porque você vai precisar delas adiante).
Colocando a mão na massa
Agora precisamos instalar as bibliotecas. A biblioteca firmata já foi instalada no artigo anterior, mas a biblioteca minim precisa ser instalada agora. Para isso, basta seguir os passos:
Sketch > Import Library… > Add library > {escrever “sound” na pesquisa} > {selecionar e instalar a biblioteca minim}
Voltando ao programa, vamos iniciar chamando as bibliotecas e inicializando os objetos no código. Fica assim:
import ddf.minim.*; import processing.serial.*; import cc.arduino.*; Arduino arduino; SoundFile file;
Como o Arduino, o Processing usa duas funções principais que devem estar presentes em todos os projetos, elas são a void setup( ) e a void draw( ). A função draw funciona como a void loop do Arduino e nela vamos construir o programa. A setup funciona exatamente com o mesmo propósito da função no Arduino, no Processing vamos usá-la para criar o Canvas, a tela onde construiremos a nossa interface.
Como usaremos um botão virtual, ou seja, vamos clicar em um botão na tela do Processing e assim tomar uma ação no Arduino, devemos chamar uma função própria do Processing chamada void mousePressed() que será chamada toda vez que houver um click no mouse.
Colocando as imagens no projeto
Antes da função setup precisamos criar o objeto e fazemos isso dessa forma:
PImage img;
Precisamos fazer isso com cada imagem que queremos usar dentro do projeto. É como declarar uma variável, PImage é o tipo da variável e img é o nome da sua variável. Logo, não podemos repetir esse nome, se queremos outra imagem no projeto precisamos dar outro nome. Como usaremos duas imagens, o resultado será o seguinte:
PImage img1; PImage img2;
Agora precisamos colocar realmente as imagens no projeto, para fazer isso basta arrastar as imagens e soltar na janela do Processing, assim:
O Processing irá criar automaticamente uma pasta chamada “data” dentro da pasta do seu projeto. Nela ficará contidos os arquivos que vamos usar daqui em diante. Guarde essa informação.
Precisamos trabalhar a imagem dentro da função setup. Fazemos isso chamando o construtor dessa forma:
img = loadImage ("exemplo.jpg");
Essa função cria o link entre a sua “variável” e o arquivo que você enviou para o Processing. Lembre-se de colocar nomes fáceis na sua imagem para não ter problemas aqui. No nosso caso, fica assim:
img1 = loadImage ("carroclaro.jpg"); img2 = loadImage ("carroescuro.jpg");
No setup também inicializamos o Canvas. Fazemos isso usando a função size(), ela determina o tamanho da janela. No nosso caso vamos usar as dimensões originais da imagem que queremos usar.
E por último, quando desejarmos mostrar uma das imagens precisamos chamar a função dessa forma:
image (img, 0, 0);
Onde “img” é a variável onde sua imagem está “guardada” e os algarismos seguintes são a posição onde a ponta esquerda superior da imagem será posicionada. Até agora o nosso programa está assim:
import ddf.minim.*; import processing.serial.*; import cc.arduino.*; Arduino arduino; SoundFile file; PImage img1; PImage img2; void setup() { size(640,537); img1 = loadImage ("carroclaro.jpg"); img2 = loadImage ("carroescuro.jpg"); } void draw() { image (img1, 0, 0); } void mousePressed() { }
Colocando o som no projeto
O arquivo utilizado pode ser baixado no seguinte link.
Precisamos antes do setup fazer as seguintes declarações:
Minim minim; AudioPlayer player;
E no setup precisamos declarar:
minim = new Minim(this);
Para que a biblioteca possa acessar a pasta Data, onde ficam guardados os arquivos do projeto.
No setup, precisamos declarar também:
player = minim.loadFile("ignit.mp3");
Que vai ligar o arquivo de som a uma variável. Para “tocar” o som chamamos a função:
player.play();
Até agora o nosso programa está da seguinte forma:
import ddf.minim.*; import processing.serial.*; import cc.arduino.*; Arduino arduino; Minim minim; AudioPlayer player; PImage img1; PImage img2; void setup() { size(640,537); minim = new Minim(this); player = minim.loadFile("ignit.mp3"); img1 = loadImage ("carroclaro.jpg"); img2 = loadImage ("carroescuro.jpg"); player.play(); image (img1, 0, 0); } void draw() { } void mousePressed() { }
Colocando o Arduino na jogada
Primeiro precisamos declarar no setup as entradas e saídas do nosso projeto.
Definimos assim:
LDR > Entrada (pino A0)
Botão > Entrada (pino 8)
LED > Saída (pino 9)
Buzzer > Saída (pino 10)
No Processing, escrevemos dessa forma:
//Declaração dos pinos nos quais os elementos estão conectados arduino.pinMode(10, Arduino.OUTPUT);// Buzzer arduino.pinMode(9, Arduino.OUTPUT); // LED arduino.pinMode(8, Arduino.INPUT); // Chave arduino.pinMode(A0, Arduino.INPUT); // LDR
Adicionalmente precisamos inicializar o Arduino em si. Fazemos isso no setup chamando a função:
arduino = new Arduino(this, Arduino.list()[1], 57600);
Se for preciso, retorne ao artigo anterior para entender como declarar o índice da porta a qual o seu Arduino está conectado.
Na função void Draw do Processing, vamos escrever a lógica da nossa aplicação, vamos lembrar como usamos as funções próprias do Arduino pela biblioteca firmata:
Escrita digital (Output): arduino.digitalWrite(pino, Arduino.HIGH) Leitura digial (Input): arduino.digitalRead(pino) == Arduino.HIGH Leitura Analógica (Input): arduino.analogRead(pino)
Lógica
Abaixo segue o código do nosso projeto, ele está todo comentado.
//Adicionamos as bibliotecas necessárias ao nosso projeto: //Reprodutor de sons, Firmata e Arduino import ddf.minim.*; import processing.serial.*; import cc.arduino.*; Arduino arduino; Minim minim; AudioPlayer player; //Adicionamos as 3 imagens que iremos usar no projeto. //Todas as imagens devem estar na pasta DATA que está //na pasta do projeto PImage img1; PImage img2; PImage img3; //Declaramos as variáveis que iremos utilizar no projeto int tempopassado = 0, //Usada para memorizar o tempo do acionamento do botao tempopassado2 = 0;//Usada para memorizar o tempo do blink LED boolean botao = false, //Usada para guardar o estado do botão aux = false, //Variável auxiliar para marcar as mudança de estados alerta = false,//Usada para guardar o estado do Alerta estado = false, //Usada para guardar o estado buzzer = false; //Usada para guardar o estado do Buzzer void setup() { size(640,445);//Determina o tamanho da janela do programa arduino = new Arduino(this, Arduino.list()[1], 57600); //Inicia o Arduino minim = new Minim(this); //Inicia o player de sons player = minim.loadFile("ignit.mp3"); //Traz ao programa o arquivo de som que está na pasta DATA img1 = loadImage ("carroclaro.jpg"); // Traz ao programa os arquivos de imagem que estão na pasta DATA img2 = loadImage ("carroescuro.jpg"); img3 = loadImage ("carrodesligado.jpg"); //Declaração dos pinos nos quais os elementos estão conectados arduino.pinMode(10, Arduino.OUTPUT);// Buzzer arduino.pinMode(9, Arduino.OUTPUT); // LED arduino.pinMode(8, Arduino.INPUT); // Chave //arduino.pinMode(A0, Arduino.INPUT); //LDR: A entrada analógica não precisa ser declarada } void draw() { //Loop infinito do processing int tempoatual = millis();//Guarda o tempo atual int valorLDR = arduino.analogRead(0); //Inicio do código que detectará se o botão foi pressionado ou não if (arduino.digitalRead(8) == Arduino.HIGH){ //checa a porta if (tempoatual - tempopassado > 1000){ //checa se foi passado 1 segundo if(botao==false){ //Se o estado do botão é desligado, então botao=true; // liga o botão aux=true; //e salva a mudança de estado } else if(botao==true){ botao=false; aux=false; } tempopassado = tempoatual; //Guarda o tempo que este código foi ativado } } //Final da checagem do botão //Inicio do código quando o botão for pressionado (ligando o carro) if(botao==true){ //Checa se o botão está no estado ligado if(aux==true){ //Essas linhas detectam a mudança de estado, assim player.play(); //O som tocará somente uma vez aux=false; //a alteração do estado dessa variável assegura isso. } //Checa o pino do LDR if(valorLDR < 850){ //Se está escuro image (img2, 0, 0); //mostra a imagem do carro com o exterior escuro } else if(valorLDR >= 850) { //Se está claro image (img1, 0, 0);//mostra a imagem do carro com o exterior claro }//Fim do código que trata do LDR if(alerta==true){//Se o mouse clicou no botão virtual do alerta if (tempoatual - tempopassado2 > 1000){ //checa caso tenha se passado 1 seg if(estado==false){ //Se o estado do LED está desligado arduino.digitalWrite(9, Arduino.LOW); //mantém o LED desligado estado = true; //e altera o estado } else{ //Assim na proxima checagem, se o estado é ligado arduino.digitalWrite(9, Arduino.HIGH); //Liga o LED estado = false; //e altera o estado } tempopassado2 = tempoatual; //guarda o tempo para proxima checagem } }//Fim do Alerta if(buzzer==true){//Se o botão da buzina for pressionado arduino.digitalWrite(10, Arduino.HIGH); //Liga o Buzzer }//fim }//Fim do Carro ligado //Inicio do código quando o botão não foi pressionado (desligando o carro) if(botao==false){ if(aux==false){ //a variável auxiliar permite image(img3,0,0); //que a imagem seja renderizada uma vez aux=true; } }//Fim Teste do botão desligado } void mousePressed() { //Buzina e alerta if (mouseX >= 130 && mouseX <= 205 && //checa se o mouse está entre as posições mouseY >= 175 && mouseY <= 250) { //determinadas pelo perimetro de um quadrado if(buzzer==false)buzzer=true; //Checa o estado da variável alerta e else if(buzzer==true){ buzzer=false;//muda o seu estado conforme o botão é pressionado arduino.digitalWrite(10, Arduino.LOW); //Garante o Buzzer desligado } } if (mouseX >= 300 && mouseX <= 340 && mouseY >= 220 && mouseY <= 260) { if(alerta==false)alerta=true; //Checa o estado da variável alerta e else if(alerta==true){ alerta=false;//muda o seu estado conforme o botão é pressionado arduino.digitalWrite(9, Arduino.LOW); //Garante o LED desligado } } }
Resultado da Interface no Processing para o Arduino
Agora veja na prática como ficou nosso projeto:
Obrigado por ler o artigo até aqui! No próximo artigo vamos conhecer mais uma forma de comunicar o Arduino com o Processing, dessa vez sem o uso da biblioteca firmata. Vamos criar um jogo no Processing e fazer um controle simples usando Arduino!
Se você deseja ler mais conteúdos que vão te ajudar a melhorar as suas habilidades com Arduino, visite o blog da MakerHero. Siga nas redes sociais e não deixe de conferir as novidades!