На Mega128 использую 3 кнопки по прерыванию INT5-INT7.
Ноги подтянуты килоомными резисторами на плюс, кнопки коротят на землю. Ноги настроены на вход с подтягивающими резисторами.
Стоит задача отследить длинное и короткое нажатие кнопки.
Прерывание отрабатывает без вопросов, но не могу зарегистрировать отпускание кнопки.
Код такой (сокращенно):
Код: Выделить всё
#include <avr/io.h>
#include <avr/interrupt.h>
#include <util/delay.h>
#define LED1 PORTE0 // светодиоды управляются 0
#define LED2 PORTE1
#define LED3 PORTE2
#define LED4 PORTE3
#define LED5 PORTE4
#define BUTNR PINE5 // кнопка R
...
// Глобальные переменные
volatile unsigned int butR;
volatile unsigned int butScnt;
volatile unsigned int butSflag;
volatile unsigned int butShort;
volatile unsigned int butLong;
// External Interrupt 5 R
ISR(INT5_vect)
{
butR=1; // сработала кнопка R
}
// Timer0 64Hz
ISR(TIMER0_COMP_vect)
{
if(butSflag==1) // флаг старта счетчика
{
butScnt++; // счетчик
if(!(PORTE & (1<<BUTNR))) // нажата кнопка R
{
if(butScnt>128)
butLong=1; // 2 секунды задержка - длинное нажатие
}
else
butShort=1; // короткое нажатие
}
}
int main(void)
{
_delay_ms(1000);
funcInit();
butR = 0; // Кнопка R
butScnt=0; // счетчик длины нажатия
butSflag=0; // флаг кнопки
butShort=0; // короткое нажатие
butLong=0; // длинное нажатие
sei();
while(1)
{
if(butR==1) // сработала кнопка R
{
butSflag=1; // разрешаем счетчик в прерывании 64Hz
}
if(butShort==1) // короткая кнопка
{
butR=0;
butSflag=0;
PORTE &= (~(1<<LED4)); // зажигаем 4 диод
}
else if(butLong==1) // длинная кнопка
{
butR=0;
butSflag=0;
PORTE &= (~(1<<LED5)); // зажигаем 5 диод
}
}
}
void funcInit(void)
{
...
// Port E initialization
// Function: Bit7=In Bit6=In Bit5=In Bit4=Out Bit3=Out Bit2=Out Bit1=Out Bit0=Out
DDRE=(0<<DDE7) | (0<<DDE6) | (0<<DDE5) | (1<<DDE4) | (1<<DDE3) | (1<<DDE2) | (1<<DDE1) | (1<<DDE0);
// State: Bit7=T Bit6=T Bit5=T Bit4=1 Bit3=1 Bit2=1 Bit1=1 Bit0=1
PORTE=(0<<PORTE7) | (0<<PORTE6) | (0<<PORTE5) | (1<<PORTE4) | (1<<PORTE3) | (1<<PORTE2) | (1<<PORTE1) | (1<<PORTE0);
...
/ Interrupts
TIMSK = (0<<OCIE2) | (0<<TOIE2) | (0<<TICIE1) | (1<<OCIE1A) | (0<<OCIE1B) | (0<<TOIE1) | (1<<OCIE0) | (0<<TOIE0);
ETIMSK=(0<<TICIE3) | (1<<OCIE3A) | (0<<OCIE3B) | (0<<TOIE3) | (0<<OCIE3C) | (0<<OCIE1C);
EICRA=(0<<ISC31) | (0<<ISC30) | (0<<ISC21) | (0<<ISC20) | (0<<ISC11) | (0<<ISC10) | (0<<ISC01) | (0<<ISC00);
EICRB=(1<<ISC71) | (0<<ISC70) | (1<<ISC61) | (0<<ISC60) | (1<<ISC51) | (0<<ISC50) | (0<<ISC41) | (0<<ISC40);
EIMSK=(1<<INT7) | (1<<INT6) | (1<<INT5) | (0<<INT4) | (0<<INT3) | (0<<INT2) | (0<<INT1) | (0<<INT0);
EIFR=(1<<INTF7) | (1<<INTF6) | (1<<INTF5) | (0<<INTF4) | (0<<INTF3) | (0<<INTF2) | (0<<INTF1) | (0<<INTF0);
}
Всегда срабатывает 5 диод длинного нажатия. Такое впечатление что кнопка буферизируется
Всем заранее спасибо за помощь
Proteus 7.8


