ВходНаше всё Теги codebook 无线电组件 Поиск Опросы Закон Среда
27 ноября
95676 Топик полностью
Dany (28.07.2007 10:46, просмотров: 1) ответил Dany на Спасибо за терпение rezident. Устранение дребезга вставлю, а иначе зачем спрашивать совета, а потом его игнорироавть:)
Выкладываю конечный код, дабы начинающие такие как я не задавали глупые вопросы :). Считаю данный код прост для понимания, и удовлетворит начальный интерес к работе с кнопками. <c> /*=========================================== определения для линий матричной клавиатуры ===========================================*/ // определения портов клавиатуры // порты строк #define KB_PORT_ROW PORTD #define KB_PIN_ROW PIND #define KB_DDR_ROW DDRD // порты столбцов #define KB_PORT_COL PORTD #define KB_PIN_COL PIND #define KB_DDR_COL DDRD // линии строк #define KB_ROW_WIRES ((1 << PD1) | (1 << PD2)) #define KB_ROW_SHIFT 1 // количество сдвигов вправо кода строк при формировании кода кнопки // линии столбцов #define KB_COL_WIRES ((1 << PD5) | (1 << PD6) | (1 << PD7)) char scan; // Код нажатой клавиши, формируется KB_Read_2x3 /****************************************************************************** Опрос клавиатуры. Возвращает код нажатой кнопки в переменную scan. В старшей тетраде – состояние линий строк, в младшей тетраде – состояние линий столбцов Если в одной из тетрад кода кнопки более одного нуля, код не действительный ******************************************************************************/ // Прерывание TIMER 0 для опроса клавиатуры каждые 32 ms interrupt [TIM0_OVF] void KB_Read_2x3(void) { char code1, code2; static char press; KB_DDR_ROW &= ~KB_ROW_WIRES; // порт строк на ввод KB_PORT_ROW |= KB_ROW_WIRES; // к выводам порта строк подключаем pull-up резисторы KB_DDR_COL |= KB_COL_WIRES; // порт столбцов на вывод KB_PORT_COL &= ~KB_COL_WIRES; // на всех выводах порта столбцов лог "0" #asm("nop") // задержка на один такт, для установления сигналов на выводах порта code1 = (KB_PIN_ROW >> KB_ROW_SHIFT) & 0x3; // считываем состояние линий строк и преобразуем в код KB_DDR_COL &= ~KB_COL_WIRES; // порт столбцов на ввод KB_PORT_COL |= KB_COL_WIRES; // к выводам порта столбцов подключаем pull-up резисторы KB_DDR_ROW |= KB_ROW_WIRES; // устанавливаем направление порта строк на вывод KB_PORT_ROW &= ~KB_ROW_WIRES; // на всех линиях порта строк лог "0" #asm("nop") // задержка на один такт, для установления сигналов на выводах порта code2 = (KB_PIN_COL & 0xE0); // считываем состояние линий столбцов и преобразуем в код /* Устранение дребезга. Алгоритм устранения сводится к сравнению двух сканов, если они равны, значит состояние устойчивое, сохраняем код. Иначе код равен нулю.*/ code2|=code1|0x1C; // Формируем код кнопки и сохраняем в code2 scan=(~(press^code2))&press; // возвращаем полученные коды состояний столбцов и строк если совпали два соседних скана press=code2; // Сохраняем предыдущий скан } /****************************************************************************** Функция проверки новых нажатий, возвращает код нажатой кнопки. Активный ноль. ******************************************************************************/ char inkey(void) { static char pressOld; // Переменная для хранения предыдущего состояния клавиатуры char code; // Код нажатой кнопки - активный ноль if(!(scan^pressOld)) // Если нет нажатых кнопок {code=0; // Код равен нулю pressOld=scan; // Сохраняем текущий скан return code; // Возвращаем код=0 } code=scan; // Если есть новое нажатие pressOld=scan; // Сохраняем текущий скан return code; // Возвращаем код нажатой кнопки } // Функция инициализации таймера // Вызывает прерывание каждые 32 мс. timer_init(void) { // Timer/Counter 0 initialization // Clock source: System Clock // Clock value: 7,813 kHz TCCR0=0x05; TCNT0=0x00; // Timer(s)/Counter(s) Interrupt(s) initialization TIMSK=0x01; #asm("sei") } </c>