подавление дребезга без делай и милис

vosara
vosara аватар
Offline
Зарегистрирован: 08.02.2014
Вот в интернете увидел интересное, на мой взгляд, подавление дребезга без делай и милис. Интересно что скажут по этому поводу специалисты да и просто пользователи. Сравнил два способа и вот что у меня получилось по размеру.
Без милис:
#define button1 3
byte drebezg1;
bool kn1;

void setup()
{
  pinMode(button1, INPUT_PULLUP);
}

void loop()
{
  if (!kn1 && !digitalRead(button1))drebezg1++;
  if (drebezg1 && digitalRead(button1)) {
    drebezg1 = 0;
    kn1 = 0;
  }
  if (drebezg1 >= 40)kn1 = 1;
}

 

Скетч использует 804 байт (2%) памяти устройства. 
Глобальные переменные используют 11 байт (0%) динамической памяти, оставляя 2 037 байт
 
А это с милис:
#define button1 3
bool kn1;
bool f_kn1;
unsigned long currentTime1;

void setup()
{
    pinMode(button1, INPUT_PULLUP);
}

void loop()
{
    if (!digitalRead(button1) && !f_kn1)
    {
        currentTime1 = millis();
        f_kn1 = 1;
    }
    if( digitalRead(button1))
    {
        kn1 = 0;
        f_kn1=0;
    }
    if(f_kn1 && millis() - currentTime1 >= 100)
    {
        kn1 = 1;
    }
}

Скетч использует 884 байт (2%) памяти устройства.

Глобальные переменные используют 15 байт (0%) динамической памяти, оставляя 2 033 байт
 

 

qwone
qwone аватар
Offline
Зарегистрирован: 03.07.2016

vosara, вы пытаетесь придумать "вечный двигатель" в противоречии физики. (Физика это вера сектантов , которые обычными людьми зовутся учеными. И законы Физики проходят в школе вместо Закона божьего или подобного.Прим автора). Что какое дребезг механических кнопок- это дребезжание контакта при замыкании. И время у него есть. И это время существенно для ЦП. Так вот перед ЦП стоят 3 последовательные задачи: 1 уловить начало изменений , 2 сделать паузу большую чем длительность дребезга, 3 зафиксировать уровень на входе.

ПС: Вот мой код деБонса

/*
#1
кнопка1 -> 2 (btn1_pin) 0 нажата /1 нет
*/
// #1
const int btn1_pin = 2; // вывод кнопки
bool btn1;// значение на кнопке без дребезга
bool bounce_btn1 = 0; // антидребезговый флаг

void setup() {
  // #1
  pinMode(btn1_pin, INPUT_PULLUP);
  btn1 = digitalRead(btn1_pin);

}

void loop() {
  // #1
  static uint32_t past_1 = 0 ;
  if (! bounce_btn1 && btn1 != digitalRead(btn1_pin)) { // если прошел фронт изм на выводн
    bounce_btn1 = 1;                                 // выставить флаг
    past_1 = millis();                          // сделать временую засветку
  }
  else if ( bounce_btn1 && millis() - past_1 >= 40 ) { // если прошло антидребезговое время
    bounce_btn1 = 0;                            // то снять флаг
    btn1 = digitalRead(btn1_pin) ;           // прочитать реальное значение на выводе
  }
}

Ну и аналоговый деБонс

/* AnalogBounce.ino
#1
кнопка1 -> A0 (Analog_pin) 0 нажата /1 нет
*/
// #1
const int Analog_pin = 0; // вывод кнопки
int Analog_new,Analog;// значение на кнопке без дребезга (новое и старое)
const int delta = 5;
bool bounce = 0; // антидребезговый флаг

void setup() {
  Serial.begin(9600);
  // #1
  Analog_new = analogRead(Analog_pin);
}

void loop() {
  // #1
  static uint32_t past_1 = 0 ;
  Analog_new = analogRead(Analog_pin);
  if (!bounce &&  (Analog+delta < Analog_new  ||  Analog-delta > Analog_new)) { // если прошел фронт изм на выводн
    bounce = 1;                                 // выставить флаг
    past_1 = millis();                          // сделать временую засветку
  }
  else if ( bounce &&( millis() - past_1) >= 40 ) { // если прошло антидребезговое время
    bounce = 0;                            // то снять фл
    Analog = Analog_new;           // прочитать реальное значение на выводе
    Serial.println(Analog);// сюда можно воткнуть обработчик события
  }
}

 

andriano
andriano аватар
Offline
Зарегистрирован: 20.06.2015

vosara, а какой смысл сначала ловить нажатие на кнопку, избавляться от дребезга, а потом нигда это не использовать (и даже не проверять - работает ли)?

qwone
qwone аватар
Offline
Зарегистрирован: 03.07.2016

andriano пишет:

vosara, а какой смысл сначала ловить нажатие на кнопку, избавляться от дребезга, а потом нигда это не использовать (и даже не проверять - работает ли)?

Вообще-то есть ряд программ где надо ловить момент нажатия и отжатия кнопки. Те же таймеры, счетчики оборотов. При этом сенсорами служат механические кнопки. Но теория без практики мертва, практика без теории слепа. Я это тому , без теории как в программе бороться с дребезгом , делать это бессмыслено. И в этом надо или delay() или millic(),в крайнем случае аналог этого.

andriano
andriano аватар
Offline
Зарегистрирован: 20.06.2015

Да, qwone, программы такие есть. Не так много, но есть. И, кстати, наиболее эффективный метод борьбы с дребезгом - аппаратный, а не программный.

Но речь не о том.

ТС приводит код, в котором задержка (без которой, как Вы правильно заметили, не обойтись) формируется 40 проходами цикла loop(). При этом в теле loop() нет никакой реакции на нажатие, поэтому в таком виде программа бессмысленна. Если же в loop() добавить реакцию на нажатие, изменится длительность цикла loop() и, как следствие, формируемая задержка.

И так будет происходить практически при любом внесении изменений в программу.

Но это еще не все.

Конечно, delay() - это совсем не то, что следует широко использовать в программе, но если, к примеру, либо в сам loop(), либо в любую вызываемую им функцию вставить, скажем, delay(1000), то реакцию на нажатие нам придется ждать не менее 40 секунд.

vosara
vosara аватар
Offline
Зарегистрирован: 08.02.2014
Может я чегото не понимаю! 
При использовании милис мы засекаем время и потом сверяемся.
Здесь же используется время прохождения цыкла.
Если кнопка нажата переменную плюсуем если нет сбрасываем в ноль
при каждом проходе если есть дребезг - переменная = 0 и только если дребезг закончился и мы насчитали стабильное соединение при 10-40 проходах - фиксируем НАЖАТИЕ 
andriano
andriano аватар
Offline
Зарегистрирован: 20.06.2015

vosara пишет:

Может я чегото не понимаю! 

Может.

Но, скорее всего, Вы просто не успели прочитать сообщение выше.

vosara
vosara аватар
Offline
Зарегистрирован: 08.02.2014
andriano
Код сделан для проверки и сравнения размера а как его использовать это другое дело
по поводу увеличения времени ДА Вы правы но можно ставить 40 или 5
А если человек использует делай то здесь и милис не поможет
Logik
Offline
Зарегистрирован: 05.08.2014

Проблема в том что время прохождения лупа принципиально нестабильно. И соответственно при коротких циклах надо 40, а при длинных годится 5. А как узнатьв сколько конкретно сейчас цикл занял - ХЗ. Потому уход от явного определения времени через милис к неявному через кол-во прохода циклов - ересь привеликая.

qwone
qwone аватар
Offline
Зарегистрирован: 03.07.2016

vosara. Основная проблема не написать рабочий код, а убедиться в его работоспособности. Т.е. оттестировать его. И чем длинее код, тем дольше идет тестирование.  Иногда 2 скетча  вдвое короче легче и быстрее оттестировать, чем 1 но длиный. Есть даже темы: есть 2 рабочих скетча. Помогите их объединить.  И вот вы предлагаете рабочий кусок, который будет работать замечательно, сам по себе. И с приколами если куда-то его впихнуть.  Так что millis() таких приколов дает значительно меньше. Тем более его millis() можно использовать в разных независимых частях и ничего опасного в этом не будет. 

andriano
andriano аватар
Offline
Зарегистрирован: 20.06.2015

Понимаете, vosara, millis() - это подход к решению целого ряда проблем, включая подлавлекние дребезга контактов. Вы же вместо этого подхода не предлагаете вообще ничего.

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

vosara
vosara аватар
Offline
Зарегистрирован: 08.02.2014
Это решение, как я писал выше, я нашол в ИТЕРНЕТЕ оно мне показалось интересным. Спросил совета и Вы меня, да думаю и других кто найдет такое, УБЕДИЛИ.
 
qwone
qwone аватар
Offline
Зарегистрирован: 03.07.2016

vosara пишет:
Это решение, как я писал выше, я нашол в ИТЕРНЕТЕ оно мне показалось интересным. Спросил совета и Вы меня, да думаю и других кто найдет такое, УБЕДИЛИ.

 Почему я такой "умный" по этому вопросу, потому что неделю назад был "счастливым дураком". Но начал разбираться как FLProg борется с дребезгом. Ужасный код . Но когда разобрался с алгоритмом , то пришлось писать более менее человеческий свой. Тем более его я и оптимизировал. Так что я стал "богат"  на еще один подход. 
Клапауций 234
Offline
Зарегистрирован: 24.10.2016

vosara пишет:

Без милис:
#define button1 3
byte drebezg1;
bool kn1;

void setup()
{
  pinMode(button1, INPUT_PULLUP);
}

void loop()
{
  if (!kn1 && !digitalRead(button1))drebezg1++;
  if (drebezg1 && digitalRead(button1)) {
    drebezg1 = 0;
    kn1 = 0;
  }
  if (drebezg1 >= 40)kn1 = 1;
}

т.е. нужно держать кнопку нажатой 40 циклов программы и ни в коем случае не отпускать раньше, иначе это будет считаться дребезгом.

и, ты считаешь это разумным алгоритмом.

*ну, ок.

inspiritus
Offline
Зарегистрирован: 17.12.2012

Хм. А я ставлю емкостюшку и не парюсь.

Logik
Offline
Зарегистрирован: 05.08.2014

qwone пишет:

 Но начал разбираться как FLProg борется с дребезгом.

Не страдайте фигней, пищите код проекта, который должен будет работать по нажатию кнопки. Его исполнение займет время, за это время дребезг скорей всего закончится. Вы о нем даже не узнаете, а если узнаете, то еще и кроме дребезга будет проблема повторной отработки нажатия, тогда и порешите обе сразу с помощю паузы на милис. 

ПС. Найденое Клапауций 234 мне больше нравится.

Клапауций 234
Offline
Зарегистрирован: 24.10.2016

inspiritus пишет:

Хм. А я ставлю емкостюшку и не парюсь.

схему подключения покажи.

inspiritus
Offline
Зарегистрирован: 17.12.2012

В ардуино васик коннектионс есть пример

Клапауций 234
Offline
Зарегистрирован: 24.10.2016

inspiritus пишет:

В ардуино васик коннектионс есть пример

дай ссылку на схему

потому как здесь https://www.arduino.cc/en/Tutorial/Button конденсатор отсутсвует

inspiritus
Offline
Зарегистрирован: 17.12.2012

Возьми книгу и посмотри на первой странице сам. Или поищщи в инете. Чай не маленький. Версия уже 234 :)

Ворота
Ворота аватар
Offline
Зарегистрирован: 10.01.2016

А, что поставить простой конденсатор и не париться уже не вариант? Ну. если нет конденсатора, так можно поставить МС14490 сразу на шесть каналов. Помниться Dimax пробовал - ему понравилось. А вообще, самое подробное обсуждение темы было у Джека Гансли - http://www.eng.utah.edu/~cs5780/debouncing.pdf

qwone
qwone аватар
Offline
Зарегистрирован: 03.07.2016

Кину сюда код на дебонсе энкодера.

/*encoder_bounce.ino
#1  Ардуино энкодер   CLK -> 2   CLK_pin   0 нажата 1 нет
                      DT  -> 3   DT_pin    0 нажата 1 нет
                      SW  -> 4   SW_pin    0 нажата 1 нет
                      GND -> GND
                      +5V -> +5V
*/
// #1
int count = 0; //счетчик
const int CLK_pin = 2; // вывод тактов
bool CLK;// значение такта без дребезга
bool CLK_old;// старое значение такта без дребезга
bool bounce_CLK = 0; // антидребезговый флаг
const int DT_pin = 3; // вывод направления
bool DT;// значение напраления
const int SW_pin = 4; // вывод кнопки
bool SW;// значение на кнопке без дребезга
bool SW_old;// старое значение на кнопке без дребезга
bool bounce_SW = 0; // антидребезговый флаг



void setup() {
  Serial.begin(9600);
  // #1
  pinMode(CLK_pin, INPUT_PULLUP);
  CLK = digitalRead(SW_pin);
  pinMode(DT_pin, INPUT_PULLUP);
  pinMode(SW_pin, INPUT_PULLUP);
  SW = digitalRead(SW_pin);
}

void loop() {
  // #1
  static uint32_t past_1 = 0 ;
  if (! bounce_CLK && CLK != digitalRead(CLK_pin)) { // если прошел фронт изм на выводн
    bounce_CLK = 1;                                 // выставить флаг
    past_1 = millis();                          // сделать временую засветку
  }
  else if ( bounce_CLK && millis() - past_1 >= 5 ) { // если прошло антидребезговое время
    bounce_CLK = 0;                            // то снять флаг
    CLK_old = CLK;
    CLK = digitalRead(CLK_pin) ;           // прочитать реальное значение на выводе
    DT = digitalRead(DT_pin) ;
    if ((CLK_old && ! CLK && DT) ) { // || (! CLK_old &&  CLK && ! DT)
      count++;
      Serial.println(count);
    }
    if ((CLK_old && ! CLK && ! DT) ) { // || (! CLK_old &&  CLK && DT)
      count--;
      Serial.println(count);
    }
  }

  static uint32_t past1_1 = 0 ;
  if (! bounce_SW && SW != digitalRead(SW_pin)) { // если прошел фронт изм на выводн
    bounce_SW = 1;                                 // выставить флаг
    past1_1 = millis();                          // сделать временую засветку
  }
  else if ( bounce_SW && millis() - past1_1 >= 40 ) { // если прошло антидребезговое время
    bounce_SW = 0;    // то снять флаг
    SW_old = SW ;
    SW = digitalRead(SW_pin) ;           // прочитать реальное значение на выводе
    if (SW_old && ! SW) Serial.println("SW up");
    if (!SW_old && SW) Serial.println("SW down");
  }
}

 

Doooh
Offline
Зарегистрирован: 10.08.2017

Ещё вариантик аналоговый.

const int button = 2;
const int led = 3;

void setup() {
  pinMode(button, INPUT);
  pinMode(led, OUTPUT);
}

void loop() {
  if (analogRead(button) > 1020) { //настраивается по max напряжению с кнопки
    //delay(50); зависит от желаемой скорости реакции кнопки
    digitalWrite(led, HIGH);
  }
  else {
    digitalWrite(led, LOW);
  }
}

 В общем-то тут уже философией попахивает. Если брать на "дребезг" какое-то время, дык может, у человека тремор и правильный delay(10000). А если ловить вершинку графика включения, кмк это ближе к цели. И задержек не нужно. Критикуйте. Мне всё уже увиденное по размеру не нравится. Это же всего лишь кнопка. В конце-концов именно в таком случае можно прилепить .01uF на вход и это уж точно решит все запросы.
 

b707
Онлайн
Зарегистрирован: 26.05.2017

Doooh. зачем вы апнули старую тему, да еще с таким бредовым кодом?

Я вижу. вы только что зарегистрировались... Подозреваю, что и программировать ардуину начали пару дней назад. Через полгода, если не бросите - вам будет стыдно за этот код.

По сути - в вашем коде нет никакого антидребезга. От слова "вообще".

Doooh
Offline
Зарегистрирован: 10.08.2017

b707 пишет:

Doooh. зачем вы апнули старую тему, да еще с таким бредовым кодом?

Смысл новую такую же создавать?

b707 пишет:
Я вижу... Подозреваю...
Так точно. Я электронщик и всегда это ёмкостью решал. Купил Уну с ребёнком изучать. Как видите, дошёл до кнопок.

Ну хорошо, неужели в сегодняшнем мире до сих пор считается нормальным обрабатывать всего лишь кнопку кодом микрософтовского размера? Да ещё временами и прогу затуплять задержками.

Что касаемо моей писанины, от какой строчки нужно краснеть особенно? Принято вроде через RS-монитор оценивать успех, так в этом плане результат достигнут.
Ещё вариант, если не трогать выход, пока ничего не происходит.

const int button = 2;
const int led = 3;
int state = 0;

void setup() {
  pinMode(button, INPUT);
  pinMode(led, OUTPUT);
}

void loop() {
  state = analogRead(button);
  switch (state) {
    case 1023:
      digitalWrite(led, HIGH);
      delay(100); //тупит программу только при нажатой кнопке
    case 0:
      digitalWrite(led, LOW);
  }
}

Просто перепечатывая код из пособий я вряд ли чему-то научусь и уж тем более не научу ребёнка.

Клапауций 112
Клапауций 112 аватар
Offline
Зарегистрирован: 01.03.2017

Doooh пишет:

Ну хорошо, неужели в сегодняшнем мире до сих пор считается нормальным обрабатывать всего лишь кнопку кодом микрософтовского размера? Да ещё временами и прогу затуплять задержками.

да - всё очень плохо. люди забыли, что у них есть конденсаторы, которыми можно считать время с точностью до микросекунды.

 

Doooh пишет:

delay(100); //тупит программу только при нажатой кнопке

а, должно было тупить и при отжатой? О_О

b707
Онлайн
Зарегистрирован: 26.05.2017

Doooh пишет:

Что касаемо моей писанины, от какой строчки нужно краснеть особенно?

Ну давайте

Строка 11 - почему analogread ? зачем вам значение напряжения на пине, вас же интересует только ON и OFF. Тем более что.... см ниже

Строка 13 - вы в строке 11 считали напряжение на пине и теперь сравниваете его с напряжением питания. И сравниваете очень жестко - только 1023 и ни на единицу ниже. Для 5в платы это означает, что 5.000в на кнопке - это ON, а 4.995в - это уже OFF. Вы же электроншик.... знаете, что точных значений не бывает.

Строка 15 - в чем смысл задержки? она имела бы смысл, если б вы, выждав, еще раз проверили кнопку на предмет дребезга. Но вы же этого не делаете. Вы все равно используете в программе первый же замер, так зачем ждать?

пока хватит

Doooh
Offline
Зарегистрирован: 10.08.2017

Считываю в аналоге исходя из идеи, что при дребезге напряжение с кнопки какое угодно, но не напряжение питания. Сравниваю жёстко, ибо при 10-битном АЦП точности внутреннего стабилизатора вполне хватает. 
Задержка вообще говоря не нужна. Воткнуть функцию в реальную программу и времени отработки основной программы вполне хватит, чтобы не считывать кнопку слишком часто. Вообще здесь должно быть прерывание, конечно, но это другой уровень.

Клапауций 112 пишет:

а, должно было тупить и при отжатой? О_О


Это я согласился с ущербностью первого варианта.

b707
Онлайн
Зарегистрирован: 26.05.2017

Doooh пишет:

Считываю в аналоге исходя из идеи, что при дребезге напряжение с кнопки какое угодно, но не напряжение питания. Сравниваю жёстко, ибо при 10-битном АЦП точности внутреннего стабилизатора вполне хватает. 
Задержка вообще говоря не нужна. Воткнуть функцию в реальную программу и времени отработки основной программы вполне хватит, чтобы не считывать кнопку слишком часто.

то есть весь этот странный код не от новичковыго тупизма, а с задумкой? - тогда я пожалуй в сторонку отойду, подожду что старшие скажут.

Всякие "фронты" и конденсаторы - не мое, я не электронщик

Penumbra
Offline
Зарегистрирован: 06.08.2017

b707 пишет:

Всякие "фронты" и конденсаторы 

да просто 50% ардуинщикам использовать "фронты" и конденсаторы и прерывания религия не позволяет... :)) вот и чудят))

b707
Онлайн
Зарегистрирован: 26.05.2017

Penumbra пишет:

да просто 50% ардуинщикам использовать "фронты" и конденсаторы и прерывания религия не позволяет... :)) вот и чудят))

а вторая половина использует конденсаторы, потому что им проще за паяльник взяться. чем код поправить  :) так и живем

Penumbra
Offline
Зарегистрирован: 06.08.2017

b707 пишет:

а вторая половина использует конденсаторы, потому что им проще за паяльник взяться. чем код поправить  :) так и живем

зачем же сразу за паяльник ?   конденсатор можно аккуратненько в разьемчик ардуино впихнуть  ( если ножки подогнуть))))

b707
Онлайн
Зарегистрирован: 26.05.2017

Penumbra пишет:

зачем же сразу за паяльник ?   конденсатор можно аккуратненько в разьемчик ардуино впихнуть  ( если ножки подогнуть))))

ну здрасте... еще перед каждым кондером ножки подгибать? :)

240265
240265 аватар
Offline
Зарегистрирован: 12.08.2015

b707 пишет:

а вторая половина использует конденсаторы, потому что им проще за паяльник взяться. чем код поправить  :) так и живем

Все правильно , каждый делает как проще, вот сдесь http://arduino.ru/forum/proekty/generator-s-reguliruemoei-chastotoi-na-arduino#comment-299179  пост36 , я поставил RC цепь потому что ни делай ни миллис нет возможности использовать т.к. СИСТИК отключен. А ломать голову и Авторскую программу не хотелось.

Doooh
Offline
Зарегистрирован: 10.08.2017

240265 пишет:
я поставил RC цепь потому что ни делай ни миллис нет возможности использовать т.к. СИСТИК отключен.

Там интересные цепочки, да :)

+ 10к кнопка 2к -||- GND
Действительно, если уж 1 раз 10к ток ограничили, ещё раз незачем. Хотя я всё же не инженер.

А ещё заметил тему для начинающих про кнопки и мне идея со счётчиком очень понравилась. Программа себе вертится, а ты выхватываешь и реагируешь только на ту длительность нажатия, что тебе по душе. Я про это 

digitalRead(switch_pin);
val++;
if(long val > 100000) //для секундного нажатия
 {digitalWrite(pin_led, digitalRead(switch_pin))}
else 
 {digitalWrite(pin_led, LOW)};
 val = 0;

Причём далее можно навтыкать реакций на любое время нажатия вплоть до гирлянды.
Поясните, насколько это ужасно и по каким причинам не стоит использовать. Ясно, что при увеличении кода val будет увеличиваться медленнее. Или миллис тут красивше будет? Да не, такой вариант начинает отсчёт заново даже если палец дрогнул, что по мне хорошо.

 

ЕвгенийП
ЕвгенийП аватар
Offline
Зарегистрирован: 25.05.2015

Doooh пишет:
 

digitalRead(switch_pin);
val++;
if(long val > 100000) //для секундного нажатия
 {digitalWrite(pin_led, digitalRead(switch_pin))}
else 
 {digitalWrite(pin_led, LOW)};
 val = 0;

Поясните, насколько это ужасно и по каким причинам не стоит использовать. 

Это не ужасно - это просто бред. Главная причина не использовать - не работает нихрена :)

давайте я это прокомментиирую:

digitalRead(switch_pin); // Читаем пин и никуда не сохраняем. Нахрена читали?
val++; 
if(long val > 100000) // Такого компилятор не перенесёт и обдристается сообщениями
 {digitalWrite(pin_led, digitalRead(switch_pin))} // такого тоже ";" Пушкин ставить будет
else 
 {digitalWrite(pin_led, LOW)}; // и этого компилятор не съест ";" Пушкин ставить будет
 val = 0;
}

 

Doooh
Offline
Зарегистрирован: 10.08.2017

Хотел указать лишь идею, но раз необходимо код целиком, ладно.
 


int knopka = 2;
int led_green = 3; //воткнули все светодиоды, что были
int led_red = 4;
int led_yellow = 5;
int led_blue = 6;
long val = 0;

void setup() {
  pinMode(knopka, INPUT);
  pinMode(led_green, OUTPUT);
  pinMode(led_red, OUTPUT);
  pinMode(led_yellow, OUTPUT);
  pinMode(led_blue, OUTPUT);
}

void loop() {
  if (digitalRead(knopka) == HIGH)
  { val++;   //unsigned int не хватило, объявил как long

    if (val > 100000 && val < 300000) { //удержание кнопки 1...3с
      digitalWrite(led_green, HIGH);    //включаем зелёный

    };

    if (val >= 300000 && val < 500000) { //удержание кнопки 3..5с

      digitalWrite(led_red, HIGH);     //включаем красный

      digitalWrite(led_green, LOW);   //гасим зелёный
    };

    if (val >= 500000 && val < 700000) {  //удержание кнопки 5..7с

      digitalWrite(led_yellow, HIGH);  //включаем жёлтый
      digitalWrite(led_red, LOW);     //гасим красный
    };

    if (val >= 700000 && val < 900000) {  //удержание кнопки 7..9с

      digitalWrite(led_blue, HIGH);   //включаем синий
      digitalWrite(led_yellow, LOW);  //гасим жёлтый
    };

    if (val >= 900000) {             //удержание кнопки дольше 9с

      digitalWrite(led_green, HIGH);  //включаем все
      digitalWrite(led_red, HIGH);
      digitalWrite(led_yellow, HIGH);
    };
  }
  else {
    digitalWrite(led_green, LOW);  //гасим все при малейшем намёке
    digitalWrite(led_red, LOW);    //на отпускание
    digitalWrite(led_yellow, LOW);
    digitalWrite(led_blue, LOW);
    val = 0;
  }
}

Работает по факту.

Клапауций 112
Клапауций 112 аватар
Offline
Зарегистрирован: 01.03.2017

я же запретил хрустальные шары под страхом отправки в Сирию

с какого пальца это насосано:

//удержание кнопки дольше 9с

Doooh
Offline
Зарегистрирован: 10.08.2017

Я ж говорю, по факту :) Я не знаю, почему 900 тыщ проходов примерно 9 секунд занимает :)
Наверняка это как-то можно высчитать, если почитать ассемблерный код на выходе.

Клапауций 112
Клапауций 112 аватар
Offline
Зарегистрирован: 01.03.2017

Doooh пишет:

Я ж говорю, по факту :) Я не знаю, почему 900 тыщ проходов примерно 9 секунд занимает :)

ну, ок. и зачем ты этим занимаешься?

почему нельзя делать тоже самое, но вместо val++;  делать val = millis(); и тогда точно будешь знать, откуда что берётся.

в чём профит?

Doooh
Offline
Зарегистрирован: 10.08.2017

Ну как сбросить val в ноль я знаю, а millis - нет.
Что поделаешь, мышление у меня нестандартное. Но я обучаемый. При этом от функции debounce из книжки меня воротит.

Ещё я знаю, что миллис использует Timer0, который иногда может быть неплохо перенастроить. По верхам нахватался, чо :) В конце-концов почему-то существует тема с данным названием.

DetSimen
DetSimen аватар
Offline
Зарегистрирован: 25.01.2017

Doooh пишет:

Ещё я знаю, что миллис использует Timer0, который иногда может быть неплохо перенастроить. 

и полетять в дальние края, матерясь, все delay() и millis().  

b707
Онлайн
Зарегистрирован: 26.05.2017

Doooh пишет:

Ну как сбросить val в ноль я знаю, а millis - нет.

советую все же немного поучиться. нестандартный наш. Сбрасывать миллис в ноль почему-то требуется только новичкам...

ЕвгенийП
ЕвгенийП аватар
Offline
Зарегистрирован: 25.05.2015

Doooh пишет:

Ну как сбросить val в ноль я знаю, а millis - нет.

Практически также - как два пальца, только вот, нафига?

Клапауций 112
Клапауций 112 аватар
Offline
Зарегистрирован: 01.03.2017

Doooh пишет:

Ну как сбросить val в ноль я знаю, а millis - нет.
Что поделаешь, мышление у меня нестандартное. Но я обучаемый. При этом от функции debounce из книжки меня воротит.

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

и, сожги эту книжку с дебоунке.

Irinka
Irinka аватар
Offline
Зарегистрирован: 28.06.2017

По поводу аппаратной борьбы с дребезгом кнопок, встречаю в интернете два вида, какой из них более правильный?

Logik
Offline
Зарегистрирован: 05.08.2014

Б

Irinka
Irinka аватар
Offline
Зарегистрирован: 28.06.2017

Нашла пару вариантов, которые удобнее, меньше деталей.

На микросхеме MAX6818 - относительно дорого выходит

И на микросхеме MC14490, на два входа (выхода меньше), но в разы дешевле

Подскажите как рассчитывать емкость C1, не понимаю где в даташите про это написано.

Даташит:

https://drive.google.com/file/d/0Bzaa2zpsYEBnQ1JpWUQzN0d4VVU/view

 

qwone
qwone аватар
Offline
Зарегистрирован: 03.07.2016

Irinka, как тут не вспомнить одесский анекдот.

Урок математики в одесской школе.
Учитель:
— Сколько будет дважды два? 
Отличник с первой парты:
— А мы покупаем или продаём?

 А теперь по делу - открываем схему и смотрим  https://arduinoplus.ru/wp-content/uploads/2017/09/nano-principialnaya-shema.jpg

Вывод. Оба не верны. Избыточность и не нужность.

ЕвгенийП
ЕвгенийП аватар
Offline
Зарегистрирован: 25.05.2015

Самое толковое, что я видел про практические меры подавления дребезга - https://drive.google.com/open?id=0B9r7cRXQ4DU4TVJzQVhOMmtCc00

Irinka
Irinka аватар
Offline
Зарегистрирован: 28.06.2017

ЕвгенийП пишет:

Самое толковое, что я видел про практические меры подавления дребезга - https://drive.google.com/open?id=0B9r7cRXQ4DU4TVJzQVhOMmtCc00

74HC14 ещё дешевле,  70 рублей за 20 штук, так же, 6 входов-выходов, только добавлять резисторы и конденсатор, а в тех микросхемах всё встроено.

А для чего диод?

И ещё вопрос, я программно проверяю на дребезг через 50-100 мкс, т.е: (пример с паузой)

if (digitalRead(buttonPin)){
  delay(100);
  if (digitalRead(buttonPin)){
  нажата 
  }
}

Добавив аппаратное устранение мне в коде не придётся делать повторную проверку через промежуток времени?