Микроконтроллеры, АЦП, память и т.д Темы касающиеся микроконтроллеров разных производителей, памяти, АЦП/ЦАП, периферийных модулей... |
20.02.2009, 16:32
|
|
Частый гость
Регистрация: 06.10.2007
Сообщений: 11
Сказал спасибо: 1
Сказали Спасибо 1 раз в 1 сообщении
|
Не матричная клавиатура для МП
Не матричная клавиатура для МП
При построении микропроцессорных систем часто возникает проблема нехватки портов, поскольку клавиатура и дисплей занимают много выходных линий. Допустим, что мы хотим создать недорогую почти универсальную микропроцессорную систему, которая имеет развитую клавиатуру более 16-ти клавиш и в качестве дисплея использовать графический дисплей 128х64 точек, который также имеет небольшую стоимость и позволяет отобразить достаточно много информации. Например это может быть GLCD *WG12864 или аналогичный. Микропроцессор Pic 16F877A очень хорошо подходит для этой цели, как по цене так и по своим характеристикам. Оценив всю совокупность характеристик и считая, что найдено оптимальное решение приступаем к проектированию. Немедленно обнаруживается сложная проблема, микропроцессор Pic 16F877A и большинство ему подобных предоставляют только один порт для матричной клавиатуры на 16 клавиш. Даже если каждой клавише назначить несколько значений и потерять некоторое количество памяти за счет усложнения драйвера клавиатуры, то все равно остается дисплей под который необходимо выделить два порта. В результате теряется функциональность микропроцессора, поскольку порты устройств МП занимаются дисплеем.
Существуют решения, которые позволяют использовать линии клавиатуры для вывода данных на дисплей, но при этом усложняется программа, память расходуется для обслуживания алгоритма уплотнения дисплея и клавиатуры. На эту тему написано множество статей, однако в Интернете не удалось найти решения которое бы обладало следующими свойствами:
Клавиатура должна иметь более 16-ти клавиш, занимая при этом не более 3-х линий порта
Алгоритм обслуживания клавиатуры должен быть простой и потреблять небольшое количество памяти
Аппаратная реализация клавиатуры должна быть минимальна и допускать наращивание числа клавиш без существенного усложнения.
При выполнении этих условий удалось бы разместить большую клавиатуру и дисплей WG12864 заняв только два порта МП. Тогда МП система на основе Pic 16F877A и WG12864 приобретает большую гибкость и информативность. С учетом возможности перепрограммирования системы непосредственно через порт СОМ без программатора, появляется возможность создания универсального устройства, которое можно использовать для решения разнородных редких задач. Например есть система, которая используется повседневно как вольтметр, термометр и т.д. и память МП занята практически вся. Тогда для выполнения эпизодической задачи можно за несколько минут перепрограммируете МП и получить другой прибор, клавиатура и дисплей при этом обеспечивают необходимую гибкость и информативность системы.
Задачу создания такой клавиатуры удалось решить применив для обслуживания каждых 8-ми клавиш один 8-ми разрядный сдвигающий регистр и 8 развязывающих диодов. Если использовать сдвигающий регистр большей разрядности, схему можно существенно упростить(рис1).
Алгоритм обслуживания клавиатуры очень прост:
*В исходном состоянии регистр заполнен нулями.
*Нажатие любой клавиши вызывает прерывание порта P3.
*Подпрограмма прерывания заполняет регистр единицами. В нулевой разряд регистра записывается нуль. Нуль продвигается по регистру, при этом производится анализ порта P3 и подсчет импульсов сдвига, которые формирует P2. Если P3 равен нулю, значит нажата соответствующая клавиша. В этом случае определяется ее номер и производится запись в буфер клавиатуры. Регистр устанавливается в исходное состояние, производится выход из подпрограммы прерывания.
Анализ буфера клавиатуры и выполнение основной программы.
По данной схеме была реализована клавиатура на 24 клавиши. Драйвер написан на С и компилирован компилятором CCS. Размер занимаемой памяти зависит от числа клавиш(таблица перекодировки), для 24 клавиш составляет примерно 150 слов и два рабочих регистра. Схему и рисунки печатной платы можно посмотреть здесь http://www.dslev.narod.ru/key.htm.
-- Прилагается рисунок: --
|
|
|
|
21.02.2009, 12:15
|
|
Почётный гражданин KAZUS.RU
Регистрация: 19.01.2007
Сообщений: 1,747
Сказал спасибо: 2
Сказали Спасибо 46 раз(а) в 35 сообщении(ях)
|
Есть PCF8575, позволяют по квадратной шине сделать полноценное поле ввода-вывода до 128 бит(8*16)...
Удачт!
__________________
Я, думаю, нужно подумать...
|
|
|
|
21.02.2009, 16:53
|
|
Почётный гражданин KAZUS.RU
Регистрация: 13.12.2004
Сообщений: 3,172
Сказал спасибо: 11
Сказали Спасибо 692 раз(а) в 504 сообщении(ях)
|
Re: Не матричная клавиатура для МП
Сообщение от alexplev
|
Существуют решения, которые позволяют использовать линии клавиатуры для вывода данных на дисплей, но при этом усложняется программа, память расходуется для обслуживания алгоритма уплотнения дисплея и клавиатуры.
....
По данной схеме была реализована клавиатура на 24 клавиши. Драйвер написан на С и компилирован компилятором CCS. Размер занимаемой памяти зависит от числа клавиш(таблица перекодировки), для 24 клавиш составляет примерно 150 слов и два рабочих регистра. Схему и рисунки печатной платы можно посмотреть здесь http://www.dslev.narod.ru/key.htm.
|
Усложнение при совместном использовании линий дисплеем и клавиатурой выходит куда выгодней. У меня при точно такой ситуации, правда на АВР, примерные затраты 50 слов и ... ни одного аппаратного регистра. И диодов всего 8.
Причем и опрос получается намного быстрей. Ваше решение подойдет для мелких 8-ми ногих МК, но к ним обычно такие клавиатуры не подключают.
-- Прилагается рисунок: --
|
|
|
|
21.02.2009, 17:36
|
|
Почётный гражданин KAZUS.RU
Регистрация: 13.05.2006
Адрес: Москва
Сообщений: 3,559
Сказал спасибо: 76
Сказали Спасибо 326 раз(а) в 230 сообщении(ях)
|
Сообщение от kison
|
У меня при точно такой ситуации, правда на АВР, примерные затраты 50 слов и ... ни одного аппаратного регистра. И диодов всего 8.
Причем и опрос получается намного быстрей.
|
Надеюсь поделитесь с народом !
__________________
Обучалка AVR PIC ARM начинающим программирование курс самоучитель шаг за шагом с нуля, CVAVR, PROTEUS, MPLAB, WinAVR, IAR, KEIL электроника - http://proavr.narod.ru
|
|
|
|
21.02.2009, 18:57
|
|
Частый гость
Регистрация: 06.10.2007
Сообщений: 11
Сказал спасибо: 1
Сказали Спасибо 1 раз в 1 сообщении
|
Не сочтите за труд, покажите схему, где на двух портах подключен GLCD WG12864 и клавиатура на 24 клавиши без аппаратной реализации. Да и драйвер на 50 слов покажите, хотя бы алгоритм. Я просил об этом на форуме Микрочип, много было предложений, в основном как можно заменить, но про это не пишите, об этом я знаю, и про контроллер клавиатуры I2C тоже знаю. Мне нужно самое дешевое решение для Pic877A.
|
|
|
|
22.02.2009, 01:00
|
|
Почётный гражданин KAZUS.RU
Регистрация: 07.10.2007
Адрес: Луганск
Сообщений: 1,816
Сказал спасибо: 13
Сказали Спасибо 399 раз(а) в 214 сообщении(ях)
|
Сообщение от alexplev
|
Не сочтите за труд, покажите схему, где на двух портах подключен GLCD WG12864 и клавиатура на 24 клавиши без аппаратной реализации.
|
А чё там сложного...
ножки для ЖКИ
D/I=1
R/W=1
E=1
данные 8 бит
CS1=1
CS2=1
RES=1
для клавиатуры:
данные 8 бит
CSKEY1(общий для 1-8клавиш)=1
CSKEY2(общий для 9-16клавиш)=1
CSKEY3(общий для 17-24клавиш)=1
Шина данных общая ЖКИ + клавиши, подтягиваеш к + или к GND.
Итого 16 ног, то есть два порта, как и просили.
Опрос клавиш в паузе между выводами на ЖКИ.
Драйвер клавиш , пользую уже лет 7-8, иногда с небольшими изменениями, добавляю ускорение срабатывания если удерживать клавишу, или отпускание клавиши
сравниваеш текущее состояние и отжатые клавиши,
если равно то грузиш счётчик подавления дребезга
сравниваеш предыдущее состояние и текущее,
если повтор то уменьшение счётчик подавления дребезга,
если счётчик=0 то сработало, флаг нажати=1
если не равно, то предыдущее = текущее,
счётчик = время подавления дребезга.
три групы клавиш по 8,
3 флага нажатия
3 регистра текушеге нажатия
3 регистра предыдущего нажатия.
1 (можно 3) счётчика подавления дребезга...
|
|
|
|
22.02.2009, 02:23
|
|
Супер-модератор
Регистрация: 13.03.2004
Адрес: Minsk
Сообщений: 2,378
Сказал спасибо: 1,948
Сказали Спасибо 1,327 раз(а) в 578 сообщении(ях)
|
А не прорабатывался вариант подключения обычной компьютерной клавиатуры? Стоимость - копейки, принять данные с PS2 тоже не так уж и сложно. Зато кнопок - море
|
|
|
|
22.02.2009, 03:05
|
|
Почётный гражданин KAZUS.RU
Регистрация: 13.12.2004
Сообщений: 3,172
Сказал спасибо: 11
Сказали Спасибо 692 раз(а) в 504 сообщении(ях)
|
Сообщение от alexplev
|
Не сочтите за труд, покажите схему, где на двух портах подключен GLCD WG12864 и клавиатура на 24 клавиши без аппаратной реализации. Да и драйвер на 50 слов покажите, хотя бы алгоритм. Я просил об этом на форуме Микрочип, много было предложений, в основном как можно заменить, но про это не пишите, об этом я знаю, и про контроллер клавиатуры I2C тоже знаю. Мне нужно самое дешевое решение для Pic877A.
|
Если мне не изменяет память, то WG12864 нужно 6 линий управления. Тогда на два порта не влезть - 8 порт данных, 3 сканирования клавиатуры и 6 управления индикатором получается 17. Ну или ресет не подключать.
Я выше ошибся - диодов должно быть по числу кнопок. Старый свой проект не нашел, вот по быстрому накидал под АВР. Вышел сам драйвер 166 байт - 83 слова. Комментировал все что можно , алгоритм извлекается из исходника легко. Я думаю и на микрочиповский контроллер перевести нетрудно. Даже если учесть более раздутый код под 16/18 семейства, все равно слов в 100 уложитесь.
button.h
Код:
|
/*
button.h
Заголовочный файл для button.c
Реализует клавиатуру 3х8 БЕЗ определения совместного нажатия
Внимание! Если порт сканирования не поддерживает атомарные операции cbi и sbi то в макросы SCAN_XX_XX_ON и SCAN_XX_XX_OFF
нужно вводить критические секции!
При одновременном нажатии нескольких кнопок отработана будет кнопка с большим номером
При коротком нажатии код нажатой кнопки возвращается всего один раз. При длительном - после истечения интервала на каждый запрос возвращается код с признаком длительного нажатия
*/
#ifndef _BUTTON_H_
#define _BUTTON_H_
#include ‹inttypes.h›
//#define DEBUG
#define TIME_DR 0.05 // время подавления дребезга, в сек., MIN 0.01, MAX 2.5
#define TIME_LONG_PRESS 0.1 // время до "долгого" нажатия, в сек., MIN =TIME_DR+1, MAX 2.5
#define TIME_DR_COUNT ((uint8_t)(TIME_DR / 0.01))
#define TIME_MAX_COUNT ((uint8_t)(TIME_LONG_PRESS / 0.01))
#define BUTTONS_PORT PORTD
#define BUTTONS_PIN PIND
#define BUTTONS_DDR DDRD
#define BUT_SCAN_00_07 PC0 // линия сканирования кнопок 0-7
#define BUT_SCAN_08_15 PC1 // линия сканирования кнопок 8-15
#define BUT_SCAN_16_23 PC2 // линия сканирования кнопок 15-23
// инициализация сканирующих линий
#define BUT_SCAN_INIT() PORTC|=(1‹‹BUT_SCAN_00_07); DDRC|= (1‹‹BUT_SCAN_00_07);
PORTC|=(1‹‹BUT_SCAN_08_15); DDRC|= (1‹‹BUT_SCAN_08_15);
PORTC|=(1‹‹BUT_SCAN_16_23); DDRC|= (1‹‹BUT_SCAN_16_23)
// макросы управления линиями сканирования
#define SCAN_00_07_ON() PORTC &= ~(1‹‹BUT_SCAN_00_07)
#define SCAN_00_07_OFF() PORTC |= (1‹‹BUT_SCAN_00_07)
#define SCAN_08_15_ON() PORTC &= ~(1‹‹BUT_SCAN_08_15)
#define SCAN_08_15_OFF() PORTC |= (1‹‹BUT_SCAN_08_15)
#define SCAN_16_23_ON() PORTC &= ~(1‹‹BUT_SCAN_16_23)
#define SCAN_16_23_OFF() PORTC |= (1‹‹BUT_SCAN_16_23)
//----------------------------------------------------------------------------------
// опрос клавиатуры 3 х 8
// возвращает код нажатой кнопки (0-23) или 0xFF если нажатых кнопок нет
// также в MSB возвращается признак длительного нажатия
// функцию нужно вызывать каждые 10мс
//----------------------------------------------------------------------------------
uint8_t CheckButtonPress(void);
#endif |
button.c
Код:
|
#include "button.h"
#include ‹inttypes.h›
#include ‹avr/io.h›
static uint8_t ScanPressButton(uint8_t buttons)
{
uint8_t count = 8;
uint8_t btn = 0xFF;
while(count)
{
if((buttons & 0x01) == 0) btn = count;
count--;
buttons ››= 1;
}
if(btn == 0xFF) return btn;
return (8 - btn);
}
uint8_t CheckButtonPress(void)
{
static uint8_t KeySave = 0xFF; // храним номер кнопки из предыдущего опроса
static uint8_t CountPressTime = TIME_MAX_COUNT; // обратный отсчет времени нажатия
uint8_t key = 0xFF, tmp;
BUTTONS_PORT = 0xFF; // подтяжка внутренними резисторами
BUTTONS_DDR = 0x00; // перенастроим порт на ввод
// сканируем клавиатуру
// группа 0-7
SCAN_00_07_ON();
tmp = ScanPressButton(BUTTONS_PIN);
SCAN_00_07_OFF();
if(tmp != 0xFF) key = tmp;
// группа 8-15
SCAN_08_15_ON();
tmp = ScanPressButton(BUTTONS_PIN);
SCAN_08_15_OFF();
if(tmp != 0xFF) key = tmp + 8;
// группа 16-23
SCAN_16_23_ON();
tmp = ScanPressButton(BUTTONS_PIN);
SCAN_16_23_OFF();
if(tmp != 0xFF) key = tmp + 16;
BUTTONS_DDR = 0xFF; // восстановим направление порта данных на вывод
if((key == 0xFF) || (KeySave != key)) // если не было нажатых кнопок или кнопка отлична от предыдущего опроса
{
CountPressTime = TIME_MAX_COUNT;
KeySave = key; // сохраним номер кнопки
return 0xFF; // вернем - ничего не нажато
}
if(CountPressTime) // Проверим счетчик времени нажатия
{
CountPressTime--; // уменьшим его если это возможно
// если кнопка нажата в течении времени подавления дребезга - вернем код кнопки
if(CountPressTime == (TIME_MAX_COUNT - TIME_DR_COUNT)) return KeySave;
}
else
{
// кнопка нажата долго - вернем код кнопки и признак долгого нажатия
return (KeySave | 0x80);
}
return 0xFF;
} |
main.c
Код:
|
#include ‹avr/io.h›
#include "button.h"
unsigned char key; // просто для примера
int main(void)
{
// тут что то делаем
BUT_SCAN_INIT(); // инициализация клавиатуры
// инициализация индикатора и т.п.
while(1)
{
// тут что то делаем
key = CheckButtonPress(); // вызов каждые 10 миллисекунд
// смотрим что за кнопка и обрабатываем ее
}
} |
Драйвер использует 2 байта ОЗУ.
Подключение рисовать лень - 3 группы по 8 кнопок. Одна сторона объединена и идет на линию сканирования. От другой через диоды на шину данных индикатора. В условиях помех лучше подтянуть шину внешними резисторами к Vcc.
|
|
|
|
22.02.2009, 03:16
|
|
Почётный гражданин KAZUS.RU
Регистрация: 17.05.2005
Адрес: Украина
Сообщений: 1,958
Сказал спасибо: 292
Сказали Спасибо 494 раз(а) в 359 сообщении(ях)
|
Сообщение от nml
|
А не прорабатывался вариант подключения обычной компьютерной клавиатуры? Стоимость - копейки, принять данные с PS2 тоже не так уж и сложно. Зато кнопок - море
|
Для офиса (дома) - да, а если надо IP65? Дороговато получится...
|
|
|
|
Ваши права в разделе
|
Вы не можете создавать новые темы
Вы не можете отвечать в темах
Вы не можете прикреплять вложения
Вы не можете редактировать свои сообщения
HTML код Выкл.
|
|
|
Часовой пояс GMT +4, время: 17:09.
|
|