Микроконтролери и електроника
http://mcu-bg.com/mcu_site/

Притреперване на контактите на бутон
http://mcu-bg.com/mcu_site/viewtopic.php?f=3&t=14842
Страница 1 от 2

Автор:  pldimitroff [ Сря Окт 19, 2016 3:09 pm ]
Заглавие:  Притреперване на контактите на бутон

Здравейте,
Начинаещ съм и за първи път програмирам микроконтролер, по-точно PIC16F84A. Да, програмата не тръгна от първия път, но както казваше един мой преподавател, ако едно нещо тръгне от първия път, то има груба грешка.
И така за проблема ми:
На вход RB0/INT съм поставил бутон свързан към 0V, OPTION_REG=0х00, тоест съм включил изтеглящите резистори (дано така се наричат), входът RB0/INT води до прекъсване по заден фронт 1/0 (при натискане на бутона), другите битове не са от значение (TMR0 не го ползвам).
При натискане и отпускане на бутона, микроконтролерът го приема като двойно натискане и отпускане.
Сложих кондензатор 220 nF паралелно на бутона (от входа към 0V). В подпрограмата за обработка на прекъсването поставих забавяне от 40-70 mS. Но и двете неща не помогнаха.
Предполагам, че проблема е от притреперване на контактите на бутона. Интересното е, че някога и при отпускане на бутона се получава проблема.
Предполагам, че напредналите, са срещали този проблем. По какъв начин да го отстраня?

Надявам се да съм улучил форума, защото мисля, че програмно може да се отстрани проблема.
Благодаря Ви предварително!

Автор:  radolin [ Сря Окт 19, 2016 3:18 pm ]
Заглавие:  Re: Притреперване на контактите на бутон

Този проблем най-лесно може да се отстрани като филтрираш нежеланите прищраквания в софтуера.

Попитай google за 'debounce'. Може и с прекъсване, но аз лично ползвам просто един таймер който през Nms чете състоянието на входовете където е бутона. Само ако последните 4-5 състояния за стабилни и едни и същи се приема, че е натиснат/отпуснат бутона.

Автор:  pldimitroff [ Сря Окт 19, 2016 4:16 pm ]
Заглавие:  Re: Притреперване на контактите на бутон

Благодаря Ви!
Този таймер, с който проверявате за стабилното състояние, сте написали Nms, от какъв порядък трябва да бъде?
Аз в прекъсването му задавах 40-70 mS, това малко ли е?

Автор:  gicho [ Сря Окт 19, 2016 4:26 pm ]
Заглавие:  Re: Притреперване на контактите на бутон

+1
Друг начин е да ползваш прекъсването, но да добавиш и таймера като single-shot.
- чакаш прекъсване - като дойде го забраняваш и пускаш таймер с дефинираното от теб debounce време - типично е няколко десетки мс, зависи от типа на контактите, може и да е 1-2мс, може и да е на 100мс при големи контакти (дето като щракнат мигаш с очи в съседната стая)
- като изтече времето за таймера проверяваш състоянието - четеш порта и гледаш - ако е отпуснат бутона значи е нещо кратко и го броиш за смущение (светкавица), ако е още натиснат продължаваш - тук идва логиката за кратко натискане, дълго натискане, двоен клик и тем подобни; разрешаваш порт прекъсването също тук
Разликата с реализацията на Radolin е броя прекъсвания и използването на таймера. Ако имаш нужда от тик в системата и вече имаш таймер (например 1мс) лесно можеш да си закачиш изцяло polling решение (без порт прекъсване).
Ако се опитваш да постигнеш tick-less реализация то ползваш таймера като single shot и той ти дава времевата база за таймера.
Комбинация е да ползваш прекъсването но споменатия от мен "таймер" да стане "софтуерен" - алгоритъм който се държи като single shot но реално е реализиран като код дето работи в tick-а.

Автор:  Gogo [ Сря Окт 19, 2016 4:34 pm ]
Заглавие:  Re: Притреперване на контактите на бутон

Махни кондензатора и сложи външен pull-up (изтеглящ) резистор, например 4.7к
Пробвай така: в прекъсването от RB0/INT с първата инструкция го забраняваш (самото прекъсване). Правиш си там каквото е нужно и пускаш таймера. 40-70 mS е много според мен, 10 би трябвало да стигнат. Когато пускаш таимера, му разреши прекъсването. Когато таймера свърши, спираш го и разрешаваш пак прекъсването на RB0/INT.

Автор:  michev [ Сря Окт 19, 2016 4:44 pm ]
Заглавие:  Re: Притреперване на контактите на бутон

Много добра (и изпитана) идея за debounce - http://www.cc.gatech.edu/~hadi/teaching ... bounce.pdf
И още нещо - смени тоя контролер с някой по-нов, че този скоро ще го има само в антикварните магазини :)

Автор:  slav4o.com [ Сря Окт 19, 2016 6:01 pm ]
Заглавие:  Re: Притреперване на контактите на бутон

Точно така и аз мисля за прекъсването, то по принцип се забранява когато се ползва някакво прекъсване.

Автор:  pldimitroff [ Сря Окт 19, 2016 6:37 pm ]
Заглавие:  Re: Притреперване на контактите на бутон

Благодаря Ви много на всички!
Да, зная, че PIC16F84A е вече стар, но четох преди време от къде да се започне и дадоха съвет за него. А и аз съм зле с английския и намерих на руски, където се справям. Освен, че съм начинаещ с микроконтролерите, съм начинаещ и в програмирането. Има доста термини (debounce, single-shot и др.), които не са ми ясни, но ще ги потърся в нета. Надявам се да се справя.
Ако срещна проблем, пак ще попитам.
Отново БЛАГОДАРЯ!

Автор:  slav4o.com [ Сря Окт 19, 2016 7:02 pm ]
Заглавие:  Re: Притреперване на контактите на бутон

Аз бих ти препоръчал PIC16F627/628/648 той е почти същия, като има някои допълнитени нещица - повече рам, по-вече програмна памет, повече EEPROM . USART модул. Може да работи без кварц. А цената е по-ниска. Идеален е за начинаещи, като почти всичко писано за 84 става и за него.

Автор:  bongo_x2 [ Чет Окт 20, 2016 1:09 pm ]
Заглавие:  Как бае бай Бонго:

Ся, само с кондензатор не става, иска и токоограничаващ резистор за да не се *** бутонът рано или късно. Освен това хистерезисът е задължителен.

Най-доброто софтуерно решение е имитация на най-доброто хардуерно.
Пример: променливата Х1 може да е от 0 до 9, а Х2 е 0 или 1. Периодично, да речем през 10мс, четеш порта и ако е "1" увеличаваш Х1, ако е "0" намаляваш Х1 с по единица - това е интегратор. После проверяваш Х1 дали е над 6 или под 3 - два компаратора. В първия случай установяваш Х2=1, а във втория Х2=0, това е тригерът.
Ба маа му таймер 555! :)
Разбира се, ако не си индиец може да си оптимизираш горния алгоритъм.

Автор:  sparkybg [ Чет Окт 20, 2016 2:54 pm ]
Заглавие:  Re: Притреперване на контактите на бутон

Аз често когато позволява приложението на нещото, чета порта през прекъсване на таймер, а не през прекъсване на порт. Примерно 100 пъти в секунда. И проблема практичеки до няма.

Автор:  ToHu [ Чет Окт 20, 2016 4:16 pm ]
Заглавие:  Re: Притреперване на контактите на бутон

Това става ако е бутон, ако трябва да реагираш по време това не върши работа. Примерно отически енкодер, имах такъв случай и се налага да знам кога точно е фронта на сигнала, в същото време обаче трябва да съм сигурен и че не е смущение, в този случай тайм стамп по фронта а след това си правя филтрирането, и ако не е смущение се обрбаотва нататък.

Автор:  sparkybg [ Чет Окт 20, 2016 4:41 pm ]
Заглавие:  Re: Притреперване на контактите на бутон

ToHu написа:
Това става ако е бутон


Тъй де. Темата е за бутон, затова съм и добавил уговорката след това. А то и не за всеки бутон става де, но в 99% от случаите работи екстра и практически на иска нищо като код.

С енкодер съм го правил общо взето по твоя начин - input capture например, и изхвърляне на "боклука" по критерий, зависещ от конкретното приложение.

Автор:  pldimitroff [ Чет Окт 20, 2016 10:13 pm ]
Заглавие:  Re: Как бае бай Бонго:

bongo_x2 написа:
Пример: променливата Х1 може да е от 0 до 9, а Х2 е 0 или 1. Периодично, да речем през 10мс, четеш порта и ако е "1" увеличаваш Х1, ако е "0" намаляваш Х1 с по единица - това е интегратор. После проверяваш Х1 дали е над 6 или под 3 - два компаратора. В първия случай установяваш Х2=1, а във втория Х2=0, това е тригерът.


По тази логика, възможно ли е променливата Х1 да е от 0 до 3, а Х2 си остава същата 0 или 1. Периодично, но примерно през 30мс (3 пъти по-голямо време) да се чете порта и по същата логика да се увеличава или намалява Х1 според състоянието на порта. И когато Х1=0, то Х2=0 и когато Х1 =3, то Х2=1.

Автор:  gicho [ Пет Окт 21, 2016 10:32 am ]
Заглавие:  Re: Притреперване на контактите на бутон

Цитат:
практически на иска нищо като код

Не е точно нищо, а има един известен цитат:
[url]the fastest code is the code that never runs[/url]
Което би ни върнало в темата за алтернативния подход и event-driven, но няма значение.
Периодичното следене (polling) има недостатъка че яде ток - изисква tick, който е анти-патерн за пестене на ток и ресурс на CPU.
Което автоматично го праща на заден план ако искаме да правим преизползваем код, който да леко универсален.
Но не отричам че е лесно да се направи така.

Страница 1 от 2 Часовете са според зоната UTC + 2 часа [ DST ]
Powered by phpBB © 2000, 2002, 2005, 2007 phpBB Group
http://www.phpbb.com/