Manual
do
Maker
.
com
Os últimos posts mostram recursos que serão aplicados ao projeto do cofrinho eletrônico, mas precisamente nesse post ainda há algo importante a tratar - A abertura e o fechamento da plataforma por onde desliza a moeda. Nesse post vou apenas descrever a ideia, a percepção da abertura e fechamento e um exemplo de código. Todo o resto descrito aqui será implementado já no próximo post.
Se estivéssemos utilizando um servo motor ou um motor de passo, Não seria necessário esse trabalho, mas o custo se elevaria, afinal - "qualidade infinita, custo infinito". E mais, só dá trabalho da primeira vez, depois é só replicar (exceto as calibragens, tanto do motor quanto do LDR do sensor de moedas)!
Então deixando a preguiça de lado, vejamos o cenário; as portas B foram reservadas para as moedas, ainda há espaço no RB2 e RB3, mas invés de utilizar IOC, vamos utilizar a leitura digital nas portas RA0 e RA7. Talvez você se pergunte o porque utilizar duas portas nesse momento. Até poderia utilizar apenas uma, mas os pinos estão aí para serem utilizados e isso facilitará no tratamento lógico.
Esses dois pinos ajudarão na localização do posicionamento da porta, de uma forma a escolher. Se estiver em cima, estará fechado, então uma variável OPEN_CLOSE é marcada como 0. O loop principal verifica se o estado da porta é aberto (1), então verifica o nível lógico de RA7. Se a porta estiver realmente aberta, então faz um delay de 1 segundo, passa OPEN_CLOSE para 0 e lê o pino RA0 até que a porta esteja fechada. O estado da porta é mudado na interrupção. Isto quer dizer que a porta pode estar fechada, mas recebeu um pedido para abrir, então o estado da porta é validado e sua abertura é efetuada. Após 1 segundo, ela é fechada.
A abertura e fechamento pode ser feita através de uma função chamada pela interrupção. Então não precisará estar em um loop. Nesse caso pode ser mais simples:
As portas RA serão utilizadas para verificar o nível lógico. Assim economiza-se processamento (por não haver polling) e também economiza memória, como a qual seria utilizada para a variável OPEN_CLOSE. Vou pela segunda opção.
Essa foi a lógica no nível macro, agora entrando em mais detalhes, os passos seriam:
O restante do tratamento é feito pela função interrupts, sendo que esssa parte já está pronta, então simplesmente adicionamos código para uma funcionalidade específica.
Esse tipo de tratamento exemplificado nesse post não é uma interrupção propriamente dito. As interrupções do hardware são tratados via flags do próprio hardware, enquanto fazer a leitura de sinal de um pino necessita ainda outros tratamentos.
Se você leu os posts sobre interrupções e os posts sobre IOC, pode lhe ser um pouco complicado de imediato, mas é mais simples tratar as interrupções do hardware do que fazer polling. Mas ainda assim não é polling também porque a verificação do nível de sinal só será executada quando solicitada pela interrupção, então o trabalho no código pode-se dizer que é intermediário.
Para uma leitura digital, o trabalho não é tão grande e vou criar aqui um código pequeno apenas para exemplificar.
sbit CLOSED_TRIS at TRISA0_bit;
sbit CLOSED at RA0_bit;
sbit OPENED_TRIS at TRISA7_bit;
sbit OPENED at RA7_bit;
sbit LED_VERDE_TRIS at TRISA1_bit;
sbit LED_VERDE at RA1_bit;
void main(){
ANSELA = 0;
C1ON_bit = 0; //desativar comparadores
C2ON_bit = 0;
//configura as portas
OPENED_TRIS = 0;
CLOSED_TRIS = 0;
LED_VERDE_TRIS = 0;
LED_VERDE = 0;
//Desativar conversor AD
ADCON0 = 0;
ADCON1 = 0;
//Desativar pull-ups (default, mas estou enfatizando, depois explico)
WPUB = 0x00;
WPUA = 0x00;
while (1){
if (OPENED){
LED_VERDE = ~LED_VERDE;
Delay_ms(1000);
OPENED = 0;
Delay_ms(1000);
}
}
}
Com um LED (não necessariamente verde) na porta RA1, você poderá visualizar essa mudança de estado graças a esse loop criado para teste.
Repare que a leitura aqui é digital, então não precisamos ler valores para uma variável, apenas ver se o estado foi para HIGH. Depois disso deve-se baixar o pino novamente e pronto.
Quando necessita-se de um nível de sinal estável, deve-se utilizar resistores de pull-up ou no caso desse modelo de PIC, seu próprio recurso interno de pull-up.
No código sobre IOC eu levantei todos os WPUB, mas isso foi um erro. Isso eu descobri lendo sobre os pull-ups no datasheet, e nele está descrito que os WPUx são desabilitados automaticamente quando os pinos são colocados em output. Não sei para quantos modelos isso vale, mas para esse é assim.
Além disso, se for usar pull-ups em algum outro caso onde seja válido, é necessário habilitá-lo com WPUEN = 1.
Como foi visto em outro post, a plataforma provisória foi revestida com papel alumínio de um bombom. Para fazer a interrupção da porta aberta, será necessário revestir a parte de baixo da base também, logo, comerei outro bombom.
A base é mantida com 5v não aterrado, enquanto os pinos do sensor de moedas são conectados aos pinos da MCU. Como a base já tem o sinal, o único trabalho será posicionar contatos para as mudanças de estado de RA0 e RA7.
Não tenho certeza de que seja necessário, mas se quiser limitar a 20mA, use um resistor de 15ohms ou menos para não conectar diretamente os 5v à MCU. Particularmente, não utilizarei na base assim como não utilizarei também nas interrupções das moedas.
Outra coisa muito importante que não falei é que essa MCU tem sensor capacitivo responsivo a variação de frequência ao contato - e estão aí habilitados no IOC. Se você segurar um fio jumper na mão em uma das pontas e tocar a outra no pino com IOC devidamente configurado, você obterá a mesma resposta que enviando um sinal de 5v. Então, pode não ser uma má ideia colocar resistores nesses pinos, mas fica a seu critério.
Enfim, esse é o código de exemplo para a leitura digital. A função será implementada no próximo post onde já veremos a abertura e fechamento automático na interrupção das moedas.
Se gostou, não deixe de compartilhar; dê seu like no video e inscreva-se no nosso canal Manual do Maker Brasil no YouTube.
Próximo post a caminho!
Autor do blog "Do bit Ao Byte / Manual do Maker".
Viciado em embarcados desde 2006.
LinuxUser 158.760, desde 1997.