As interrupções são um recurso poderoso dos microcontroladores que permitem lidar com eventos de forma assíncrona. Diferentemente da pesquisa, que continuamente verifica os eventos, as interrupções respondem imediatamente quando um evento específico ocorre, como uma pressão de botão ou um excesso de timer. Este tutorial o guiará através da compreensão e do uso de interrupções com o Arduino.
O que você precisará
- Arduino Uno (ou uma placa compatível)
- Botão
- Resistor de 10k-ohm (para configuração de puxar)
- Resistor LED e 220-OHM (opcional)
- Fios de pão e jumper
- Arduino IDE instalado no seu computador
Etapa 1: O que são interrupções?
Uma interrupção interrompe temporariamente a execução do programa principal para lidar com um evento específico. Depois que o evento é processado, o programa é retomado de onde parou. As interrupções são gerenciadas usando funções especiais chamadas Rotinas de serviço de interrupção (ISRs).
Tipos de interrupções no Arduino
- Interrupções externas: Acionado por eventos em pinos específicos (por exemplo, pino 2 ou 3 no Arduino Uno).
- Alteração do pino interrupções: Acionado por uma alteração em qualquer pino digital.
- Interrupções do timer: Acionado por timer transborce ou compare correspondências.
Etapa 2: Usando interrupções externas
O Arduino UNO suporta interrupções externas nos pinos 2 e 3. Você pode configurar essas interrupções para acionar:
- ASCENDENTE: O sinal vai de baixo para alto.
- CAINDO: O sinal vai de alto para baixo.
- MUDAR: Alterações de sinal Estado (baixo a alto ou alto a baixo).
- BAIXO: O sinal permanece baixo.
Exemplo Código: Detectar um botão Pressione
Este exemplo alterna um LED quando um botão conectado ao pino 2 é pressionado.
#define buttonPin 2 // Interrupt pin
#define ledPin 13 // Built-in LED
volatile bool ledState = false; // Shared variable between ISR and main code
void handleInterrupt() {
ledState = !ledState; // Toggle LED state
digitalWrite(ledPin, ledState);
}
void setup() {
pinMode(buttonPin, INPUT_PULLUP); // Enable internal pull-up resistor
pinMode(ledPin, OUTPUT);
attachInterrupt(digitalPinToInterrupt(buttonPin), handleInterrupt, FALLING); // Trigger on button press
}
void loop() {
// Main loop does nothing; interrupt handles the LED
}
Explicação
-
attachInterrupt(digitalPinToInterrupt(pin), ISR, mode)
: Configura a interrupção.-
pin
: O pino de interrupção (por exemplo, pino 2 ou 3 no Arduino Uno). -
ISR
: A rotina de serviço de interrupção para executar. -
mode
: A condição de disparo (RISING
,FALLING
,CHANGE
, ouLOW
).
-
-
digitalPinToInterrupt(pin)
: Converte um número de pinos em seu número de interrupção.
Etapa 3: Usando interrupções de mudança de pino
As interrupções de mudança de pino permitem detectar alterações em qualquer pino digital. Isso requer bibliotecas adicionais, como Ativar interrupção.
Exemplo Código: Alteração do PIN interrompida
#include <EnableInterrupt.h>
#define pin 4 // Pin to monitor
void handlePinChange() {
Serial.println("Pin state changed!");
}
void setup() {
Serial.begin(9600);
enableInterrupt(pin, handlePinChange, CHANGE); // Trigger on any state change
}
void loop() {
// Main loop does nothing; interrupt handles the event
}
Instalação da biblioteca
Para usar interrupções de mudança de pino, instale o Ativar interrupção Biblioteca através do gerente da biblioteca Arduino.
Etapa 4: interrupções do timer
As interrupções do timer são úteis para agendar tarefas em intervalos precisos. Consulte o Tutorial do Timer Arduino Para detalhes sobre a configuração de interrupções do timer.
Exemplo: piscar um LED com interrupção do timer1
#define ledPin 13
void setup() {
pinMode(ledPin, OUTPUT);
// Configure Timer1
noInterrupts(); // Disable interrupts during setup
TCCR1A = 0;
TCCR1B = 0;
TCNT1 = 0;
OCR1A = 15624; // Compare match value for 1Hz (1-second interval)
TCCR1B |= (1 << WGM12); // CTC mode
TCCR1B |= (1 << CS12) | (1 << CS10); // 1024 prescaler
TIMSK1 |= (1 << OCIE1A); // Enable Timer1 compare interrupt
interrupts(); // Enable interrupts
}
ISR(TIMER1_COMPA_vect) {
digitalWrite(ledPin, !digitalRead(ledPin)); // Toggle LED
}
void loop() {
// Main loop does nothing; Timer1 handles the LED
}
Etapa 5: práticas recomendadas para usar interrupções
- Mantenha o ISRS curto: Evite atrasos ou cálculos complexos no ISRS para garantir uma resposta rápida.
- Evite a comunicação em série no ISRS: As funções em série podem não funcionar de maneira confiável dentro de um ISR.
-
Usar
volatile
Para variáveis compartilhadas: Variáveis de marca compartilhadas entre ISRs e o programa principal comovolatile
Para evitar problemas de otimização do compilador. - Entradas de debounce: Lidar com a lógica Debounce em software ou hardware para sinais barulhentos, como pressões de botão.
-
Desativar interrupções durante seções críticas: Usar
noInterrupts()
einterrupts()
Para proteger seções críticas de código.
Aplicações de interrupções
- O botão de manuseio pressiona sem voar
- Lendo codificadores rotativos
- Timing Eventos críticos (por exemplo, controle preciso do motor)
- Agendar tarefas periódicas
- Reagindo a sinais externos (por exemplo, sensores, eventos de comunicação)
Solução de problemas
- Interromper não desencadear: Verifique se o pino e o modo corretos estão configurados.
- Comportamento instável: Debounce Sinais ruidosos e evite ISRs longos.
- Conflitos com bibliotecas: Algumas bibliotecas usam interrupções internamente (por exemplo, servo, PWM). Não garanta conflito com seu código.
Conclusão
As interrupções permitem manuseio responsivo e eficiente de eventos em projetos Arduino. Ao aprender a usar interrupções externas, alterações de pino e timer, você pode criar aplicativos robustos e precisos. Experimente diferentes tipos de interrupções para aprimorar seus projetos e otimizar o desempenho!