Estou tentando fazer a leitura de um encoder no arduino DUE, mas a passagem de LOW para HIGH esta gerando ruido e o meu programa esta lendo a mesma passagem ate 7 vezes. Tentei colocar um delay na função de interrupcao, mas nao pode. Alguém tem alguma ideia?

Exibições: 1660

Responder esta

Respostas a este tópico

será que não vale a pena vc verificar sobre debounce?

http://arduino.cc/en/Tutorial/Debounce

Mas no meu programa eu não leio a saída, eu uso interrupção. Como eu usaria debouce? 

//CALCULO DA VELOCIDADE

volatile int CanalA = 0;
volatile int CanalB = 0;

void setup()
{
Serial.begin(9600);
attachInterrupt(53,cont_interrupcaoA, RISING); //Quando o pino 53 passa de 0 para 1 o programa chama a funcao
attachInterrupt(51,cont_interrupcaoB, RISING); //Quando o pino 51 passa de 0 para 1 o programa chama a funcao

}
void loop()
{

Serial.println(CanalA);
}

void cont_interrupcaoA() //Aqui eu posso contar quantas interrupcoes eu tenho
{
CanalA += 1;
}
void cont_interrupcaoB() //Aqui eu posso contar quantas interrupcoes eu tenho
{
CanalB += 1;
}

Marcelo,

Já tive enormes problemas na leitura de encoders (no meu caso com detecção por IR) e depois de muita discussão aqui neste fórum, partí para a sugestão de desmontar todo o meu robô e ir remontando item a item para detectar onde ocorria o problema. Quando achei me lembrei de uma coisa que havia lido em vários artigos e não me dei conta. "As interrupções dos ATmega (no meu caso) são EXTREMAMENTE sensíveis". Grifo o extremamente porque no meu caso, um contato em um pino de saída que passava por uma protoboard era o problema!. Como pino de saída não estava relacionado à leitura do encoder certo, mas foi o problema.

Portanto recomendação é se preocupar muito com mal contatos e sinais passando em protoboards!.

Espero que te ajude!

Wilmar

Realmente o meu circuito esta montado na protoboard. Eu ate coloquei um LED para ver se o encoder estava funcionando certinho e realmente está. Acredito que o problema seja mal contato. Você tem alguma ideia de como eu posso tratar isso no código, eu tentei colocar um delay na função de interrupção, mas não funcionou.

É difícil tratar isso no código porque no limite você pode acabar perdendo pulsos.

No meu caso o encoder serviria para controle da rotação das rodas do robô por PID, assim, idealmente não poderia perder nenhum pulso porque isso afetaria o funcionamento do controle.

Eu resolví o problema do meu substituindo a protoboard por conexões soldadas e conectores do tipo Modu.

No mínimo tente substituir os cabos (jumpers) com ponta redonda (normalmente chineses de péssima qualidade em se tratando de contato) por quadrados - pode fabricá-los comprando conectores retos fáceis de encontrar e soldá-los em cabinhos comuns.

Outra coisa (alem de tudo ja dito):

Normalmente os encoders tem 2 sinais.

Um é chamado pulso e o outro direção, que é a função primordial deles.

Mas existe uma função secundária, que é a eliminação de pulsos fantasma.

Imagine que o encoder esteja no limiar de um pulso, parado, mas com vibração. Ele ficaria indicando um avanço (ruido da vibração).

Para aproveitar que são 2 sinais e filtrar isso usa-se um flip flop (seja eletronico ou em software). Quando pulsa o "pulso" seta e quando pulsa o "dir" reseta. Assim somente ciclos completos são computados.

Veja se cabe colocar o segundo sinal. Se sim será o fim dos seus problemas. Basta gerar 2 interrupções e uma flag (veriável) que diga que a outra já pulsou. Anulando o incremento caso negativo.

Otima ideia, vou tentar implementar isso aqui. Muito obtigado

Pelo que parece você já tem as duas interrupções, certo? O que o Eduardo falou realmente vai eliminar seus problemas. Você pode até, tendo os dois sinais, criar uma função com contador up/down e verificar o sentido de giro do encoder, se necessário.

Este eh meu primeiro contato com Arduino, como eu faco para verificar o sentido no codigo?

Encoders padrões, com canal A e B, possuem uma defasagem entre os canais, conforme o primeiro exemplo da imagem abaixo. Sempre que ocorrer uma transição positiva do canal A com o canal B em nível alto tem-se um sentido de giro; caso canal B esteja em nivel baixo, o sentido é o oposto. Desta forma, é só verificar o estado do canal B na transição do canal A.

Vou testar aqui. obrigado

RSS

© 2024   Criado por Marcelo Rodrigues.   Ativado por

Badges  |  Relatar um incidente  |  Termos de serviço