Реклама на сайте English version  DatasheetsDatasheets

KAZUS.RU - Электронный портал. Принципиальные схемы, Datasheets, Форум по электронике

Новости электроники Новости Литература, электронные книги Литература Документация, даташиты Документация Поиск даташитов (datasheets)Поиск PDF
  От производителей
Новости поставщиков
В мире электроники

  Сборник статей
Электронные книги
FAQ по электронике

  Datasheets
Поиск SMD
Он-лайн справочник

Принципиальные схемы Схемы Каталоги программ, сайтов Каталоги Общение, форум Общение Ваш аккаунтАккаунт
  Каталог схем
Избранные схемы
FAQ по электронике
  Программы
Каталог сайтов
Производители электроники
  Форумы по электронике
Помощь проекту


 
Опции темы
Непрочитано 23.08.2016, 23:20  
supercelt
Прописка
 
Регистрация: 29.03.2007
Сообщений: 185
Сказал спасибо: 11
Сказали Спасибо 1 раз в 1 сообщении
supercelt на пути к лучшему
По умолчанию Оцените алгоритм опроса матричной клавы

привет народ. Я написал опросник матричной клавы 4х4 для STM32F100RET6B. Проверял в железе всё работает прекрасно. Я выставляю сюда код с пояснением алгоритма. Извините за много букав, но если вы посмотрите, ответьте пож на вопросы.
Итак, сам код
Нажмите, чтобы открыть спойлер

Код:
#include "keyboard.h"

unsigned char decoded_key;
unsigned char find_key;
unsigned char key;
unsigned char old_key;
unsigned char valid_key;
unsigned char keyss[][2] = {
{0x11, '1'},
{0x12, '2'},
{0x14, '3'},
{0x21, '4'},
{0x22, '5'},
{0x24, '6'},
{0x41, '7'},
{0x42, '8'},
{0x44, '9'},
{0x82, '0'},
{0x81, '*'},
{0x84, '#'},
{0x18, 'A'},
{0x28, 'B'},
{0x48, 'C'},
{0x88, 'D'}};
										 												 
void TIM2_IRQHandler(void){
		if(((TIM2-›SR & TIM_SR_UIF) != 0) & ((TIM2-›DIER & TIM_DIER_UIE) != 0)){  
				TIM2-›SR &= ~TIM_SR_UIF;
			  KEYBOARD_SCAN();
		}
}											 
													 
void EXTI15_10_IRQHandler(void){
		EXTI-›PR |= EXTI_PR_PR11 | EXTI_PR_PR12 | EXTI_PR_PR13 | EXTI_PR_PR14; 
		NVIC_DisableIRQ(EXTI15_10_IRQn);
		GPIOB-›BRR |= 0x1E0;
		TIM2-›CR1 |= TIM_CR1_CEN;	
		//TIM3-›CR1 |= TIM_CR1_CEN;
}

void KEYBOARD_INI(void){
		RCC-›APB2ENR |= RCC_APB2ENR_IOPBEN | RCC_APB2ENR_AFIOEN;             //CMD PORT B. cmd alt func
		GPIOB-›CRH &= ~(GPIO_CRH_CNF11_0 | GPIO_CRH_CNF12_0 | GPIO_CRH_CNF13_0 | GPIO_CRH_CNF14_0);        //Scan Pins: PB11, PB12, PB13, PB14.
		GPIOB-›CRH |= GPIO_CRH_CNF11_1 | GPIO_CRH_CNF12_1 | GPIO_CRH_CNF13_1 | GPIO_CRH_CNF14_1;         //Input Push-down.
	  GPIOB-›CRL &= ~(GPIO_CRL_CNF5_0 | GPIO_CRL_CNF6_0 | GPIO_CRL_CNF7_0);       //Generate Pins: PB5, PB6, PB7, PB8.
		GPIOB-›CRH &= ~GPIO_CRH_CNF8_0;
		GPIOB-›CRL |= GPIO_CRL_MODE5_1 | GPIO_CRL_MODE6_1 | GPIO_CRL_MODE7_1;        //Output Push-pull.
    GPIOB-›CRH |= GPIO_CRH_MODE8_1;	
		GPIOB-›BSRR |= 0x1E0;
	
		//--------Setup TIMER 2---------------------------
		RCC-›APB1ENR |= RCC_APB1ENR_TIM2EN;                    //Enable TIMER 2
		TIM2-›PSC = 0x5DBF;                     //Prescaler 24000 - 1/ Clock timer 1 kHz
		TIM2-›CR1 &= ~(TIM_CR1_DIR | TIM_CR1_CMS | TIM_CR1_CKD);	                   //Count up, clock division, mode selection
		TIM2-›ARR = 0x28;                      //Count up to 1000/		
		NVIC_EnableIRQ(TIM2_IRQn);	             //Enable interrupt for timer2
		TIM2-›DIER |= TIM_DIER_UIE;                      //Interrupt update counter/ perepolnenie
		//TIM2-›CR1 |= TIM_CR1_CEN;                        //Timer counter2 Enable!
		//------------------------------------------------
		
		//-------Setup Timer 3------------------------------
		//RCC-›APB1ENR |= RCC_APB1ENR_TIM3EN;
		//TIM3-›PSC = 0x5DBF;
		//TIM3-›CR1 &= ~(TIM_CR1_DIR | TIM_CR1_CMS | TIM_CR1_CKD);
		//TIM3-›ARR = 0x28;
		//TIM3-›CR1 |= TIM_CR1_CEN;
		//--------------------------------------------------
	
		//-------Setup EXTI-------------------------------
		AFIO-›EXTICR[2] = AFIO_EXTICR3_EXTI11_PB;
		AFIO-›EXTICR[3] = AFIO_EXTICR4_EXTI12_PB | AFIO_EXTICR4_EXTI13_PB | AFIO_EXTICR4_EXTI14_PB;
		EXTI-›RTSR |= EXTI_RTSR_TR11 | EXTI_RTSR_TR12 | EXTI_RTSR_TR13 | EXTI_RTSR_TR14;
		EXTI-›IMR |= EXTI_IMR_MR11 | EXTI_IMR_MR12 | EXTI_IMR_MR13 | EXTI_IMR_MR14;
		NVIC_EnableIRQ(EXTI15_10_IRQn);
		//------------------------------------------------
}

void KEYBOARD_SCAN(void){
		unsigned char i, j;
				for(i = 0; i ‹ 4; i++){
						GPIOB-›ODR = 1 ‹‹ (i + 5);
						for(j = 0; j ‹ 4; j++){
								if(GPIOB-›IDR & 1 ‹‹ (j + 11)){
										key = (1 ‹‹ i);
										key |= (1 ‹‹ j) ‹‹ 4;
								}
						}
				}	
				if(old_key == 0){
						old_key = key;
				} else {
								GPIOD-›BSRR |= 0x4;
								if(!(key ^ old_key)){
										valid_key++;
								} else {
										valid_key = 0;
								}
								if(valid_key == 5){
										TIM2-›CR1 &= ~TIM_CR1_CEN;	
										find_key = key;
										valid_key = 0;
										old_key = 0;
										key = 0;
										NVIC_EnableIRQ(EXTI15_10_IRQn);
									  GPIOB-›BSRR |= 0x1E0;
								}	
				}
}

char READ_KEY(char key_press){
		unsigned char ind;
		unsigned char key_value;
		for (ind = 0; ind ‹ 16; ind++) {
				if(keyss[ind][0] == key_press){
						key_value = keyss[ind][1];
						GPIOD-›BRR |= 0x4;
						return key_value;
				}
		}
		return 0;
}


А вот тут объяснение алгоритма

Нажмите, чтобы открыть спойлер

Алгоритм для матричной клавы

Настроить входы и выходы

Подать на все 4 пина входа клавы лог 1. Что бы при нажатии ЛЮБОЙ кнопки зафиксировать нажатие

Настроить таймер, и прерывание, что бы входил в прер каждые 20 милисек. При настройке не запускать таймер!

Настроить внешнее прерывание (что бы сработало при лог 1 на любом из сканирующих пинов клавы, 4 шт.)

!!! Прогон кнопки - это каждые 20 мс проверять нажата ли одна и таже кнопка. Если она нажата в течении опред кол-ва прогонов, то считаем, что нажатие кнопки состоялось!!!!!!

Ход событий:

Нажами кнопу, сработало внешнее прерывание, ввалились в вектор
сбрасываем флаги прерываний на всякий случай со всех 4 линий. Потому что нам важно что прер сработало при нажатии любой клавиши.
вырубаем внешнее прерывание, убираем все лог 1 с четырёх пинов клавы. Врубаем таймер, чтоб начал тикать. При прохождении 20 мс, прерывание таймера, - вваливаемся в вектор при переполнении.
Проверяем что прер прилетело именно от этого таймера, сбрасываем флаг прерывания, вызываем ф-ию скана клавы. Ф-ия выполнит скан и выход из прер таймера. Далее таймер опять тикает до 20 мс и всё повторяется. (Когда клавиша опознана таймер вырубается).

ФункциЯ скана:

два цикла. Один в другом. Внешний цикл скан по столбам, внутр цикл скан по строкам

Во внешнем цикле просто гоняем лог 1 по 4 портам (сдвигаем). Подали лог 1 на 1 пин, и внутр цикл сканит все 4 строки, далее внеш цикл перебрасывает лог 1 на след пин, и опять внутр цикл сканить все 4 строки. И так пока не пройдёт все 4 столба.

Итак. Во внеш цикле подаём(сдвигаем) лог 1 на 1 столб. Внутр цикл перебирает все 4 пина строк - проверяем есть ли на пинах лог 1. Если обнаруживем лог 1. записываем в переменную key комбинацию битов на столбах и строках. В биты 0-3 выставляем бит из пеерменной внешнего цикла. А в биты 4-7 пишем бит из внутреннего цикла и сдвигаем его на 4 влево. пишем бит это который в
for(i=0; i‹.....). Прошли все циклы, в переменной key записан код кнопки.
Далее проверяем. Если(1) предыдушего нажатия кнопки не было, то есть это первый прогон кнопки (используем переменную old_key). То old_key = код нажатой кнопки (key)
Иначе(1)(значит это 2 и более прогон кнопки)
(опция) ставим на пин порта лог 1, который выходит на звуковой буззер.
Сравниваем код текущего прогона с кодом в прошлом прогоне. Если(2) совпадает, то увелич счётчик прогонов (переменная valid_key).
иначе(2)
обнуляем счётчик прогонов.
Далее после сравнивания прошлого прогона и текущего
проверяем Если(3) кол-во прогонов == 5 (то есть мы дошли до 5 прогонов при этом все коды прогонов совпадали), то Вызывем ф-ию чтения кода кнопки (выводит сам символ по коду). Эту ф-ию можно сразу подставить в ф-ию вывода на дисплей.
раз вывели на дисплей, значит нажатие удалось. Сразу после вывода обнуляем valid_key, old_key, key и врубаем снова разрешение на внешние прерывания.

ЗА проверкой на первый прогон снова подаём на все 4 пина клавы лог 1.

ф-ия чтения кода кнопки:

в цикле 16 итераций, потому что 16 кнопок. Перебираем массив из 16 кодов и 16 символов кнопок

пример массива:

unsigned char keyss[][2] = {{0x11, '1'},
{0x12, '2'},
{0x14, '3'},
{0x21, '4'},
{0x22, '5'},
{0x24, '6'},
{0x41, '7'},
{0x42, '8'},
{0x44, '9'},
{0x82, '0'},
{0x81, '*'},
{0x84, '#'},
{0x18, 'A'},
{0x28, 'B'},
{0x48, 'C'},
{0x88, 'D'}};

В цикле: Если текущий элемент массива, нулевого элемента, то есть часть с кодом, равна коду подтверждённой кнопки, то записываем в перем key_value символ кнопки key_value = keyss[ind][1];
(опция) вырубаем буззер
возвращаем key_value (return key_value
после цикла for поставить что возвращаем по умолчанию return 0;



А теперь что я хочу спросить. Во всех примерах опрос клавы происходит постоянно. И я подумал, что наверное некомильфо всё время сканить клаву в холостую, ведь можно использовать время с пользой для другого. И я написал (расписал в алгоритме) так, что при нажатии на любую клавишу, мы вваливаемся во внешнее прерывание, а уже от него запускаем таймер, который с интервалом в 20 мс сканит клаву. И как только кнопа опознана, вырубается таймер и снова ждём внешнее прерывание.
Вопрос насколько это целесообразно? Что будет работать шустрее, постоянный скан или вот как я сделал
? Стоит ли вообще так делать, если делаешь для коммерческого девайса?
И последний вопрос. Если имеет место быть мой вариант, то как сделать так что бы когда постоянно жмёшь на кнопу, срабатывало только одно нажатие, а не как у меня сейчас - я жму постоянно и на дисплее цифры друг за другом с интервалом в 0.5 сек. В этом есть конечно плюс, что не надо каждый раз нажимать, если надо напечатать много одинаковых символов. Но мне надо одно нажатие - один символ. Я так помыслил, надо считать время между внешними прерываниями. Но не заводить же для этого ещё таймер.

Спасибо что прочёл всё! )
Реклама:

Последний раз редактировалось supercelt; 23.08.2016 в 23:24. Причина: забыл указать МК
supercelt вне форума  
Непрочитано 24.08.2016, 12:45  
NewWriter
Заблокирован
 
Регистрация: 07.09.2014
Адрес: В Кремле!
Сообщений: 4,486
Сказал спасибо: 396
Сказали Спасибо 2,220 раз(а) в 1,319 сообщении(ях)
NewWriter на пути к лучшему
По умолчанию Re: Оцените алгоритм опроса матричной клавы

С ходу вот такие есть замечания:
Поменять настройку выводов наоборот. То есть. На столбцы - режим входа с подтяжкой к VCC, pull-up. Строки - выходы в режиме выхода Open drain. Фиксировать прерывание по спаду на входах. Сканирование производится методом перевода в 0 каждой строки с выходом Open drain, остальные строки деактивируются простой записью 1 в выходной регистр и неактивен выходы не мешают.
Детекция нажатия происходит теперь уже по присутствию нуля на входах столбцов.
Что это даёт. Это уберегает от токов короткого замыкания выходов с разными уровнями, когда нажимается одновременно две и более кнопок. Такая ситуация очень может произойти, особенно в коммерческом готовом изделии. Иначе придётся ставить диоды или резисторы между клавиатурой и выходами МК.
А благодаря выходам Open drain и входам pullup, никаких запредельных токов и без дополнительных элементов, клавиатура подключается непосредственно на порты МК.
Что касается повторных срабатывания, то тут нужно отслеживать отпускание кнопок, чтобы отделить однократное нажатие от удержания кнопки
NewWriter вне форума  
Непрочитано 24.08.2016, 16:25  
supercelt
Прописка
 
Регистрация: 29.03.2007
Сообщений: 185
Сказал спасибо: 11
Сказали Спасибо 1 раз в 1 сообщении
supercelt на пути к лучшему
По умолчанию Re: Оцените алгоритм опроса матричной клавы

Спасибо за ответ. У меня кстати диоды стоят. Так что кз не будет. А что вы думаете по поводу моего основного вопроса. Скан через внешние прерывания лучше чем постоянный опрос?
supercelt вне форума  
Непрочитано 24.08.2016, 16:48  
akegor
Гуру портала
 
Аватар для akegor
 
Регистрация: 06.05.2005
Адрес: Краснодар, возле укротворного моря.
Сообщений: 19,058
Сказал спасибо: 2,563
Сказали Спасибо 11,890 раз(а) в 5,964 сообщении(ях)
akegor на пути к лучшему
По умолчанию Re: Оцените алгоритм опроса матричной клавы

Однозначно лучше.
__________________
Не бейте больно, ежели чо, ну не удержался... А вааще,
"Мы за все хорошее, против всей х..., По лугам некошеным чтобы шли ступни,
Чтобы миром правила правда, а не ложь, Мы за все хорошее, нас не на...!
..." (Ленинград)
Я не несу ответственности за свои действия в Вашей голове.
akegor вне форума  
Непрочитано 24.08.2016, 16:53  
supercelt
Прописка
 
Регистрация: 29.03.2007
Сообщений: 185
Сказал спасибо: 11
Сказали Спасибо 1 раз в 1 сообщении
supercelt на пути к лучшему
По умолчанию Re: Оцените алгоритм опроса матричной клавы

Upd. Нарисовал ща схематично кнопки и представил как вы написали. Я правильно понял, что на строках (выходах open drain) постоянно лог 1. И по таймеру мы гоняем ноль как бегущую строку? То есть в определенный момент времени на строках может быть вот так к примеру: 1101. Так еслм оно так, то если нажать две кнопки в одном столбе, то будет кз. Не так?
supercelt вне форума  
Непрочитано 24.08.2016, 17:43  
NewWriter
Заблокирован
 
Регистрация: 07.09.2014
Адрес: В Кремле!
Сообщений: 4,486
Сказал спасибо: 396
Сказали Спасибо 2,220 раз(а) в 1,319 сообщении(ях)
NewWriter на пути к лучшему
По умолчанию Re: Оцените алгоритм опроса матричной клавы

В принципе, я же уже, насколько помню, где-то тут выкладывал работающий код для матричной клавиатуры, с определением одинарных нажатий и блокировкой повторного действия при удержании.
Open drain тем и хорош, что он не выдает лог.1 на выход, он просто переводит выход в высокоомное состояние. Ну а если 0, то он, грубо говоря, подает 0 на выход.
А вот входы - в режиме подтяжки pullup, через внутренний резистор 50 кОм с ножки выходит лог.1, и без проблем может быть притянута к GND, ток будет микроамперным.
Поэтому, никаких кз ни при каких обстоятельствах.
А вот как раз в вашем случае - вот именно там, как вы и описали, если на сканирующих выходах столбцов 1011, и окажутся нажатыми одновременно две соседние кнопки в одной строке - вот там и получится кз в выходах столбцов. Я тоже раньше ставил диоды в линии, когда на мелких ПИКах делал. Или когда линии клавиатуры мультиплексорованы с еще какими-нибудь линиями, например, с ЖК-дисплеем.. Но когда есть возможность сделать без лишнего обвеса, почему бы и не сделать?

Ну и далее...
Записывая некоторое значение в регистр ODR, вы сразу переписываете ведь 16-выводный порт, в то время, как под клавиатуру отведено лишь 8 выводов. У F100 доступ к порту идет во всю ширину 16 бит, поэтому оставшиеся 8 ножек будут потеряны для работы в качестве выходов.
(строка GPIOB-›ODR = 1 ‹‹ (i + 5);)

Так долго ждать для получения факта нажатия кнопки совсем не обязательно. Там в коде 16 раз через 20 мс проверяется, и лишь потом кнопка считается нажатой. 0,3 с удержания - это долго. Клавиатура получится очень тормознутой, будут пропуски из-за раннего отпускания кнопок, особенно для массовых применений.
Ну ладно бы еще какая-нить одинарная кнопка, у которой специально задумано чуть более долгое нажатие, например, для кнопки включения/выключения питания, чтобы отбросить случайные короткие нажатия.
Но клавиатура на 16 кнопок с цифрами для ввода каких-то данных - и вдруг такие медленные нажатия. Вот сейчас, когда я печатаю на клавиатуре, я за секунду ввожу 3 - 5 символов, то есть, длительность удержания нажатой одной кнопки намного меньше 0,3 с.
Дребезг контактов затухает гораздо быстрее.

Ну а что до самого принципа через внешние прерывания - ой, ну как сказать... сканирование клавиатуры занимает десятки микросекунд, а интервалы превываний - десятки миллисекунд, в тысячу раз больше. Так что не сказать чтобы слишком уж че-то дам даст. Менее 1% прироста, а то и еще меньше.
Да и все равно МК будет какую-то часть времени простаивать в циклах ожидания. Некоторый фон прерываний - нормальное дело. Например, когда работает системный таймер, он дает постоянный фон. прерываний. И ничо, нормальдос.

Единственно, когда МК переводится в слип, то тогда, чтобы разбудить МК с матричной клавиатуры, вот тут будут весьма кстати внешние прерывания.

Последний раз редактировалось NewWriter; 24.08.2016 в 18:23.
NewWriter вне форума  
Непрочитано 24.08.2016, 22:26  
supercelt
Прописка
 
Регистрация: 29.03.2007
Сообщений: 185
Сказал спасибо: 11
Сказали Спасибо 1 раз в 1 сообщении
supercelt на пути к лучшему
По умолчанию Re: Оцените алгоритм опроса матричной клавы

Значит GPIOB-›ODR = 1 ‹‹ (i + 5); - это плохой вариант. А как тогда сделать, что бы остальные 8 пинов не затрагивать?
У меня скан пинов происходит 5 раз через 20 мс. Я так сделал, потому что где-то прочитал, что дребезг может длиться до 100мс.
Сейчас попробовал, я могу на клаве тоже за секунду нажать 3 кнопки без проблем.
И ещё, сканирование клавы - десятки мкс - это вы имеете ввиду, если просто сканить циклом без всяких задержек?, то есть 5 раз подряд прогнал, сравнил итерации, и если одинаково выдал кнопку. Или это при каждом прерывании по таймеру?
supercelt вне форума  
Непрочитано 25.08.2016, 09:38  
NewWriter
Заблокирован
 
Регистрация: 07.09.2014
Адрес: В Кремле!
Сообщений: 4,486
Сказал спасибо: 396
Сказали Спасибо 2,220 раз(а) в 1,319 сообщении(ях)
NewWriter на пути к лучшему
По умолчанию Re: Оцените алгоритм опроса матричной клавы

Сообщение от supercelt Посмотреть сообщение
А как тогда сделать, что бы остальные 8 пинов не затрагивать?
Ну так вы же уже это делали GPIOB-›BSRR = 0xFF‹‹16 | 1‹‹(i+5) производит такое же действие, как и ODR. Запись лог.1 в старшие 16 бит BSRR сбросит выходные биты, а запись лог.1 в младшие 16 бит - установит выходные биты. Запись лог.0 в BSRR ничего не меняет. При одновременной установке и сбросе одного и того же выходного бита установка бита имеет приоритет над сбросом бита.
А регистр ODR имеет доступ только по полуслову - изменятся все 16 бит, все ножки.
Можете все это сами проверить.

Сообщение от supercelt Посмотреть сообщение
дребезг может длиться до 100мс.
Ну это у очень плохих кнопок. Для таких кнопок параллельно надо небольшой конденсатор ставить.
Сообщение от supercelt Посмотреть сообщение
сканирование клавы - десятки мкс
Да. На стандартной частоте МК 8 МГц один проход занимает 40 мкс. А период между сканированиями, то есть, период прерываний - 10-20 мс. Один проход занимает менее полупроцента времени. Если частоту МК поднять, то и того меньше выйдет.

Сообщение от supercelt Посмотреть сообщение
сравнил итерации, и если одинаково выдал кнопку
Немного не так надо бы. Иначе слишком долго будет.
В каждой итерации, если кнопка определяется как нажатая, то счетчик инкрементируется, если кнопка определяется как отпущенная, счетчик декрементируется. Если по истечении некоторого периода в счетчике число больше 0, значит, кнопка нажата.

Последний раз редактировалось NewWriter; 25.08.2016 в 10:06.
NewWriter вне форума  
Непрочитано 25.08.2016, 10:35  
supercelt
Прописка
 
Регистрация: 29.03.2007
Сообщений: 185
Сказал спасибо: 11
Сказали Спасибо 1 раз в 1 сообщении
supercelt на пути к лучшему
По умолчанию Re: Оцените алгоритм опроса матричной клавы

А если взять в расчет идеальные условия. И предположить что во время сканирования вдруг нажали другую кнопку. Это конечно не возможно на таких частоиах но все же. То есть получается мы не сравниваем именно коды кнопки при каждой итерации. А просто фиксим нажатие?
supercelt вне форума  
Непрочитано 27.08.2016, 19:20  
NewWriter
Заблокирован
 
Регистрация: 07.09.2014
Адрес: В Кремле!
Сообщений: 4,486
Сказал спасибо: 396
Сказали Спасибо 2,220 раз(а) в 1,319 сообщении(ях)
NewWriter на пути к лучшему
По умолчанию Re: Оцените алгоритм опроса матричной клавы

Тогда будет определено нажатие другой кнопки...
Вообще, для себя я определил, что клавиатура на микрокнопках или контактных резинках вполне хорошо, без ложных срабатываний и не тормознуто, без пропусков работает при простом однопроходном опросе каждые 20-50 мс. Лично на мой взгляд, такой диапазон периода опроса получается оптимальным по скорости реакции и точности срабатывания. Увеличение времени срабатывания более чем 100 мс уже отражается тормознутостью и пропусками при быстрых нажатиях.
Проверял на нескольких клавиатурах. Правда, клавиатуры новые, с нераздолбанными кнопками.
Но в любом случае - нажатия кнопок должны определятся не более чем за 100 мс, иначе могут быть пропуски нажатий.

Урезанный вариант (выкинул лишнее) драйвера - во вложении.
Функцию сканирования клавиатуры можно вызывать любым удобным способом - по аппаратному таймеру, либо по счетчику, работающему от системного таймера (SysTick).
Как и писал ранее, один проход сканирования занимает около 40 мкс при 8МГц, а период между сканированиями - 50 мс. То есть, не более 0,1% времени.
Результат выполнения функции - в виде байта кода нажатой кнопки и байта с флагами состояния. Чтобы не было повторных выполнений действий, пока кнопка удерживается некоторое время, нужно отслеживать флаг отпускания кнопки.
Вложения:
Тип файла: zip Driver_Keyboard_Matrix_4x4.zip (3.9 Кб, 0 просмотров)
NewWriter вне форума  
 

Закладки
Опции темы

Ваши права в разделе
Вы не можете создавать новые темы
Вы не можете отвечать в темах
Вы не можете прикреплять вложения
Вы не можете редактировать свои сообщения

BB коды Вкл.
Смайлы Вкл.
[IMG] код Вкл.
HTML код Выкл.

Быстрый переход


Часовой пояс GMT +4, время: 17:02.


Powered by vBulletin® Version 3.8.4
Copyright ©2000 - 2024, Jelsoft Enterprises Ltd. Перевод: zCarot