Официальный сайт компании Arduino по адресу arduino.cc
проблеммы с прерываниями...
- Войдите или зарегистрируйтесь, чтобы получить возможность отправлять комментарии
Вс, 04/12/2016 - 19:29
Первый раз столкнулся ... вроде все понятно ... однако не работает...
Подключен 4 разрядный семисегментный индикатор. Он точно работает ... цифры выводил любые ...
Диод моргает исправно ... но на вывод идет 0000... тоесть не растет переменная oborots. Не идет в обработчик прерывания.
Подключение
код
#include <TM1637.h> #define CLK 10 //определим константы как номера пинов на которые будут соединены с одноименными пинами на модуле #define DIO 9 //это нужно будет позже int flash = 11; //порт выхода генератора int taho=2;//вход тахометра volatile int time1 = 0; volatile int time2 = 0; volatile int oborots = 0; TM1637 tm1637(CLK, DIO); //создаем экземпляр объекта типа «TM1637», с которым будем далее работать и задаем пины. // можно было и не определять константы, а написать проще — вместо трёх предыдущих строк одну: // TM1637 tm1637(3,2);, но так как мы сделали наглядней int n1, n2, n3, n4, n; unsigned long int time; void setup() { tm1637.init();// инициализация библиотеки «TM1637.h» tm1637.set(BRIGHT_TYPICAL);//установка яркости указанная константа равна 2, значение по умолчанию pinMode (flash, OUTPUT); pinMode (taho, INPUT); attachInterrupt(2, merilka, RISING); } void loop() { razbivka(); printdisplay(); miganie(); } void printdisplay() { tm1637.display(0, n1); //1 цифра дисплея tm1637.display(1, n2); //2 tm1637.display(2, n3); //3 tm1637.display(3, n4); //4 } void razbivka () { n4 = oborots % 10; oborots = oborots - n4; n3 = ((oborots % 100) / 10); oborots = oborots - n3 * 10; n2 = ((oborots % 1000) / 100); oborots = oborots - n2 * 100; n1 = ((oborots % 10000) / 1000); Serial.println(n1); } void miganie() { time = millis(); if ((time % 1000) < 10) { digitalWrite (11, HIGH); delay(100); } digitalWrite (11, LOW); } void merilka () { oborots = oborots + 1; }
возможно сигнал надо снимать до резистора? просто плату не хочу спалить ....
Для начала нужно посмотреть что за сигнал на ножке 2. Или подключить кнопку ко второму выходу и к + питания, вход нагрузить резистором на землю. Понажимать и посмотреть что будет. Если ничего не будет. Вот тогда разбираться. И не плохо было бы в разбивке не oborots обрабатывать, а окружив noInterrupts(); Interrupts(); присвоить значение другой переменной и уже эту переменную обрабатывать. На схеме не показан датчик. Или снимать с резистора.
за окружение спасибо ...
по первому совету.... нет у мну осцилографа ... даж мультиметра под рукой нет )
но диод моргает ... знач импульс на порту должен быть
тоесть кнока идет между плюсом и 2 входом... и между ними резисор на землю? в электроннике не силен )
как вы поняли наверно будет тахометр ... оборотс пока стоит тока для примера работы.. там будет боле крупная процедура...
частота мигания диода около 1 секунды... так что проблемма не в окружении отключением прерывания.... у мну ощущение что обработчик прерывания не стартует ...
А как он может работать, если вы не обеспечили сигнал на входе? Резистор от входа на землю.
тоесть кнока идет между плюсом и 2 входом... и между ними резисор на землю? в электроннике не силен )
Возможно два варианта: кнопку к плюсу или к минусу. Также нужно правильно настроить фронт срабатывания прерывания: по возрастающему (rising) или по ниспадающему (falling).
А как он может работать, если вы не обеспечили сигнал на входе? Резистор от входа на землю.
О, а я уж подумал, что мне одному показалось что вход намертво заземлён :) Мало того, скечт всё равно никогда не заработает -аттач интеррапт аттачится непонятно к чему.
переключил второй порт между резистором и светодиодом... диод моргает ... от входа резистор на землю... 10кОм... эфекта нет ... пробовал даж до светодиода ... не хотит ... блин вторую ардуинку брать для генерации синала чтоли ..
тоесть кнока идет между плюсом и 2 входом... и между ними резисор на землю? в электроннике не силен )
Возможно два варианта: кнопку к плюсу или к минусу. Также нужно правильно настроить фронт срабатывания прерывания: по возрастающему (rising) или по ниспадающему (falling).
щас получается 1 режим... тока вместо кнопки светодиод
А как он может работать, если вы не обеспечили сигнал на входе? Резистор от входа на землю.
О, а я уж подумал, что мне одному показалось что вход намертво заземлён :) Мало того, скечт всё равно никогда не заработает -аттач интеррапт аттачится непонятно к чему.
подробнее? вроде к мерилке атачится нет ?
аттачинтеррапт ( 2.... ) и вход 2 - это не одно и тоже.
подробнее? вроде к мерилке атачится нет ?
Прочтите внимательно - AttachInterrupt. Там нужно указывать номер прерывания, а не номер пина.
Первый режим не очень получается. Не понятно какой у вас светодиод и сколько на нём падает вольт. Просто подключите вход 2 к любой свободной ноге и дергайте её вместе с диодом - параллельно. 100% гарантия что сработает.
аттачинтеррапт ( 2.... ) и вход 2 - это не одно и тоже.
перечитал еще раз Статьи ... там 0 должен стоять да ? ) ...
поправил ... таймер бежит непрерывно ... при мигании диода раз в секунду... оборотс набирает +10-15 единиц... но все равно спасибо ...
Да. Эх, слона то я и не приметил....
----
Т.е считает больше чем импульсов?
угу в во много раз... как будто прерывание обрабатывается постоянно .... не зависимо от того пришел импульс или нет ... почти такая же была скорость когда я оборотс в цикле перебирал
диод не горит ... а счетчик бежит )
Поставте параллельно резистору конденсатор на 1000 пикофарад. А ещё лучше подключить не прямо к резистору, а через другой резистор около 1кОм и между ножкой 2 и землёй поставить 10 нанофарад. Фильтр от звона поставить. Должно помочь. Если программа не очень занята, можно в прерывании организовать задержку с помощью пустого цикла for со счетом где то до 1000.
спасибо ... огромное спасибо ... кондеры щас по рою... ардуина пока ваще свободная... она будет тока считать частоту и передавать другой.... ну и вывод на экран возможно ... ну это уже завтра ... поздно у меня ...
Спасибо все зароаботало
код:
Но есть проблемма ... чем выше обороты тем больше погрешность измерений. Такак меряю функцией millis(). Почитал для функции Micros() описание .... хватает ее на 70 минут ... можно ли ее программно сбросить на 0 не перезагружая ардуино ? Чтобы повысить точнось.
При Millis() на 6000 оборотах в секунду 1 милисекунда меняет сразу на 600 оборотов... при 3000 обортах на 143 оборота
Что как бы многовато.
Ну и приму советы как усреднить значения проще ) я придумал пока только так ) .
Почитал для функции Micros() описание .... хватает ее на 70 минут ... можно ли ее программно сбросить на 0 не перезагружая ардуино ?
обязательно.
иначе, разогнавшийся счётчик сорвёт механические аварийные ограничители и провалится во вневремя, откуда его придётся доставать облачившись в хроноскафандр - существует риск вернуться из вневремени в настоящее на микросекунду раньше, породив временную петлю в настоящем и копию себя каждую микросекунду...
Шутки шутками ... но я вижу использование только так... сбрасывать в 0 на каждом измерении... иначе на стыке сброса будет ошибка... или делать конструкцию на If что не больно быстро
Шутки шутками ... но я вижу использование только так... сбрасывать в 0 на каждом измерении... иначе на стыке сброса будет ошибка...
покажи, в каком месте кода у тебя случится ошибка?
тут
57
time2 = millis();
58
time = ((time2 - time1));
тут
57
time2 = millis();
58
time = ((time2 - time1));
ты проверял?
щас проверяю.... эта конструкция дает задержку 480 микросекунд.... хотя моргание стоит раз в 66 милисикунд .... пока хз откуда цифра... просто заменил мллис на микрос
щас проверяю.... эта конструкция дает задержку 480 микросекунд.... хотя моргание стоит раз в 66 милисикунд .... пока хз откуда цифра... просто заменил мллис на микрос
я тебе пример привёл, который показывает, что твоя формула успешно переползает из до переполнения в переполнение
разобрался ... тип переменной тайм просто инт был ... тоесть вычитание работает норм при сбросе таймера ... спасибо
Всем спасибо за помошь .. работает с точностью до 10 оборотов в минуту .... устроит такая точность ... осталось мелочи... оптопару прикрутить ... есть несколько вариантов оптопар ... и модуль опторазвязки 4 канальный... буду читать как подключать )