Блок с датойБлок с временемБлок с возрастом сайта
Mr.ALB

    Анатолий Беляев (aka Mr.ALB). Персональный сайт

    Да пребудут с вами Силы СВЕТА!

     

    Ардуино (Arduino). #3

    Управляем гирляндами

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

    В скетче, который рассмотрим на этой странице, будет использование аппаратного прерывания для считывания кнопки, а так же используем ШИМ (PWM), как в предыдущем примере, для управления яркостью некоторых гирлянд.

    Так как хочу использовать кнопку для выбора светового эффекта, то потребуется устранить дребезг контактов этой кнопки. В данном случае, раз мы её будем использовать через прерывания, то для уменьшения кода имеет смысл сделать схему аппаратного устранения дребезга. Для этих целей использовал операционный усилитель LM358P. Эта микросхема не дорогая, доступная, имеет корпус DIP8 и обладает пониженным энергопотреблением. Её удобно использовать, и в одном корпусе имеется два операционных усилителя, что удобно, если использовать две кнопки (для возможного расширения функций в будущем).

    Для устранения дребезга кнопки подходит схема триггера Шмитта. Это такое построение схемы, при котором имеется гистерезис выходного сигнала. Изменяющееся входное напряжение при достижении определённого уровня вызывает скачкообразное изменение на выходе, то есть позволяет на выходе получить импульсный сигнал из аналогового на входе. Этим выходным сигналом мы будем управлять выбором световых эффектов.

    Чтобы устранить множественность импульсов, которые даёт кнопка при её нажатии и отпускании, использую интегрирующий конденсатор, который установим параллельно кнопке. Сигнал с этого конденсатора подадим на инвертирующий вход ОУ (контакт 2).

    Принцип работы триггера Шмитта поясняется на картинке Pic 1. Когда нажимается кнопка SB, то напряжение на конденсаторе C быстро разряжается через контакты кнопки. При достижении на нём уровня TL, выходное напряжение на триггере переходит в высокое состояние. При отпускании кнопки, конденсатор C начинает относительно медленно заряжаться через резистор R до уровня напряжения питания. Когда напряжение на нём достигнет уровня TH, то на выходе триггера напряжение скачком перейдёт в низкое значение. Дребезг контактов кнопки в виде пачки импульсов на включении и выключении сглаживается за счёт инерции заряда конденсатора, что не даёт напряжению на входе инвертора достигнуть порога TH и тем самым переключить выход триггера в другое состояние.

    Принцип работы триггера Шмитта
    Pic 1. Принцип работы триггера Шмитта

    Для реализации схемы триггера Шмитта на ОУ потребуется:

    1. Резистор 10k...24k (подтягивающий к +5V)
    2. Резистор 12k
    3. Резистор 24k
    4. Конденсатор 0.1uF...1uF на напряжение больше 5V
    5. Микросхема LM358P

    Ниже на рисунке два типа включения LM358. На типе a) ближе к монтажной схеме, где операционный усилитель представлен DIP корпусом, а на типе b) — уже электрическая принципиальная схема.

    Подавитель дребезга кнопки
    Pic 2. Подавитель дребезга кнопки

    Используя схему триггера Шмитта в качестве подавителя дребезга кнопки, разрабатываем нашу схему, см. рис.3.

    В этом примере, в качестве гирлянд, использую одиночные светодиоды, которые можно подключить к выходам 3,4,5,6,7 через резисторы 330...1000 Ом. Конечно, для подключения реальной светодиодной гирлянды потребуется сделать силовую часть схемы, на которую будут поступать сигналы с Arduino. Думаю, что к следующим новогодним праздникам и новогодней ёлке сделаю такую силовую плату и добавлю в этот проект, а пока чисто программа управления гирляндами и имитация их с помощью светодиодов.

    Схема для скетча #3
    Pic 3. Схема для скетча #3

    Всё монтируем на макетной панельке. Делаем надлежащие подключения к плате Arduino и переходим к самому скетчу (программе).

    Реализация скетча #3
    Pic 4. Реализация скетча #3

    Используем наработки предыдущих скетчей и добавляем кое-что новое. Этим новым будет использование прерываний. У Arduino есть два аппаратных прерывания int0 и int1, которые подключены к контактам pin2 и pin3 соответственно. В моём случае буду использовать прерывание int0 (контакт pin2). На этот контакт подключим выход схемы устранения дребезга.

    Что такое прерывание? Это значит, что выполнение программы аппаратно прерывается и опрашивается определённый вход, в нашем случае – pin2. Если на заданном входе ничего не происходит, то выполняется очередной шаг программы дальше.

    Само прерывание программно подключается с помощью функции attachInterrupt. Аргументы у этой функции следующие:

    • numberInt – Номер прерывания (у нас = 0);
    • fn_ISR – Имя функции обработки прерывания (любая ваша функция);
    • RISING – На что реагировать, условие при котором срабатывает функция обработки прерывания (в данном примере на фронт, то есть на изменение сигнала с низкого уровня на высокий).

      Кроме этой возможности, существуют ещё и другие, для отслеживания события на контакте прерывания:
      • LOW — прерывание будет срабатывать всякий раз, когда на выводе присутствует низкий уровень сигнала;
      • CHANGE — прерывание будет срабатывать всякий раз, когда меняется состояние вывода;
      • FALLING — прерывание сработает, когда состояние вывода изменится с высокого уровня на низкий.

    Для того, чтобы передавать значение выбранного эффекта из функции обработки прерывания fn_ISR() в функцию loop(), используем для переменной effect тип volatile byte.

    Ниже полный скетч, который можно скопировать и вставить в свой Arduino IDE:

    /**********************************************************************
     * 2018-03-19 Mr.ALB Тренировка в программировании Ардуино
     * Управление 5-ю светодиодными гирляндами (можно больше)
     * 7-мь световых эффектов (можно больше)
     * Дребезг кнопки SB1 устраняется аппаратно с помощью LM358P
    **********************************************************************/
    /* Задержки в мс */
    #define delay_1 100
    #define delay_2 200
    #define delay_3 300
    #define delay_5 500
    #define delay_10 1000
    
    byte mode = 0;       // Режим работы гирлянды
    byte ledLevel = 0;
    byte deltaLevel = 10;// Шаг изменения яркости
    byte repeat=3;       // Повтор в 3-м эффекте 3 раза
    
    /* Переменные для кнопки */
    byte switchPin = 2;// Подключаем выход LM358P (кнопка SB1) на 2-й pin
    
    /* Перывание */
    volatile byte effect = 0;// Визуальный эффект через прерывание
    byte numberInt = 0;      // Номер прерывания
    
    /**********************************************************************
     * Настроечная функция, выполняется один раз вначале
    **********************************************************************/
    void setup()
    {
    /* Конфигурируем цифровые выводы под номерами 3,4,5,6,7 на выход */
     for(byte i = 3; i < 8; i++)
     {
       pinMode(i, INPUT);
     }
     pinMode(switchPin, INPUT);   // SB1 - Выбор эффектов
     pinMode(LED_BUILTIN,OUTPUT);// Используем светодиод для сигнализации
    
     /* Потушим светодиод на pin13 (LED_BUILTIN) */
     digitalWrite(LED_BUILTIN, LOW);
    
     /* Прикрепим прерывание int0 (pin2) к функции fn_ISR */
     attachInterrupt(numberInt, fn_ISR, RISING);
    }
    
    /**********************************************************************
     * Функция включения гирлянды
     *
     * Состояние flag:
     *  Если 0, то выключить
     *  Если 1, то включить
     *  Если 2, то включить и выключить
     * По умолчанию flag = 2 – включить-выключить
    **********************************************************************/
    void fn_blinkLed(byte pin, word msec, byte flag = 2)
    {
      /* Включение */
      if(flag == 1 || flag== 2)
      {
        digitalWrite(pin, HIGH);
        delay(msec);
      }
    
      /* Выключение */
      if(flag == 0 || flag== 2)
      {
        digitalWrite(pin, LOW);
        delay(msec);
      }
    }
    
    /**********************************************************************
     * Функция loop() выполняется постоянно
     *
     * Переключение пяти гирлянд. 7 световых эффектов
     * effect = 0 - все эффекты последовательно
     *          1 - первый эффект
     *          2 - второй эффект
     *          ...
    **********************************************************************/
    void loop()
    {
     /* Первый эффект. Поочерёдно включаем и выключаем гирлянды */
     if(effect==1 || effect== 0)
     {
       for(byte i = 3; i < 8; i++)
       {
         fn_blinkLed(i, delay_5);
       }
     }
    
     /* Второй эффект. Последовательно включаем все гирлянды... */
     if(effect== 2 || effect== 0)
     {
       for(byte i = 3; i < 8; i++)
       {
         fn_blinkLed(i, delay_3, 1);
       }
       /* ...потом в обратном порядке их выключаем */
       for(byte i=7; i > 2; i--)
       {
         fn_blinkLed(i, delay_3, 0);
       }
     }
    
    /* Третий эффект. Все включить - Все выключить. С задержкой 1 с */
     if(effect== 3 || effect== 0)
     {
       for(byte k= 0; k < repeat; k++)
       {
        for(byte j = 0; j < 2; j++)
        {
         if(j == 0) mode=1;// Режим включения
         else mode= 0;    // Режим выключения
         for(byte i = 3; i < 7; i++)
         {
           fn_blinkLed(i, 1, mode);// Задержка 1 мс
         }
         delay(delay_10);// Задержка 1 с
        }
       }
     }
    
     /* Четвертый эффект. Быстрая последовательная пробежка по гирляндам */
     if(effect== 4 || effect== 0)
     {
       // В прямом порядке...
       for(byte i = 3; i < 8; i++)
       {
         fn_blinkLed(i, delay_1);
       }
       // ...в обратном порядке
       for(byte i=6; i > 2; i--)
       {
         fn_blinkLed(i, delay_1);
       }
     }
    
     /* Пятый эффект. Включаем с крайних к центральной */
     if(effect==5 || effect== 0)
     {
       // Включаем с крайних до центральной
       byte n=7;
       for(byte i = 3; i < 6; i++)
       {
         fn_blinkLed(i, 1, 1); // Задержка 1 мс
         fn_blinkLed(n--, 1, 1);
         delay(delay_5);// Задержка 500 мс
       }
    
       // Выключаем-выключаем центральную
       fn_blinkLed(5, delay_5);// Задержка 500 мс
       // Выключаем от центральной к крайним
       n=6;
       for(byte i=4; i > 2; i--)
       {
         fn_blinkLed(i, 1, 0);
         fn_blinkLed(n++, 1, 0);
         delay(delay_5);// Задержка 500 мс
       }
     }
    
     /* Шестой эффект. Включаем ШИМ на 3,5,6 */
     if(effect==6 || effect== 0)
     {
       for(byte i = 3; i < 7; i++)
       {
        if(i != 4)
         {
           fn_stepBrightness(i, delay_1, deltaLevel, 1);// Зажигается
           fn_stepBrightness(i, delay_1, deltaLevel, -1);// Тухнет
         }
       }
     }
    
     /* Седьмой эффект. Быстрое моргание - мерцание */
     if(effect== 7 || effect== 0)
     {
       byte repeat=63;// Повтор 63 раза
       for(byte k= 0; k < repeat; k++)
       {
         for(byte j = 0; j < 2; j++)
         {
           if(j == 0) mode=1;// Режим включения
           else mode= 0;    // Режим выключения
           for(byte i = 3; i < 7; i++)
           {
             fn_blinkLed(i, 1, mode);// Задержка 1 мс
           }
           delay(21);// Задержка 21 мс
         }
       }
     }
    
     /* Выключаем все гирлянды */
     for(byte i = 3; i < 8; i++)
     {
       fn_blinkLed(i, 1,0);
     }
     delay(delay_5);
     fn_blinkLed(LED_BUILTIN, delay_2);// Сигнализируем об окончании цикла
    
    }// Конец loop()
    
    
    /**********************************************************************
     * Функции
    **********************************************************************/
    
    /* Функция обработки прерывания */
    void fn_ISR()
    {
     /* При нажатии на кнопку SB1, происходит выбор эффекта по кругу */
      ++effect;// Переходим на следующий эффект
     if(effect > 7) effect= 0;// Установим все эффекты сразу
    }
    
    /**********************************************************************
     * Функция изменения яркости гирлянды через ШИМ (PWM)
    **********************************************************************/
    void fn_stepBrightness(byte ledPin,
           word step_delay,
           byte deltaLevel,
           int sign)
    {
     for(byte i = 0; i < (int(256 / deltaLevel) + 1); i++)
     {
      ledLevel = ledLevel + deltaLevel * sign;
      ledLevel = constrain(ledLevel, 0, 255);// Ограничиваем диапазон
      analogWrite(ledPin, ledLevel);
      delay(step_delay);
     }
    }
    
    

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

    Код подробно закоментирован, надеюсь трудностей в его понимании не будет.

    P.S. Изменил типы переменных с int на byte, что позволило уменьшить код.

    2018-03-28

    Скетч можно скачать тут: sketch__3.zip

    2018-07-23

     



    Подошло время новогодней ёлки, соответственно потребовалась уже реальная гирлянда из светодиодов. Сделал небольшую гирлянду из 25 светодиодов. Пять секций по пять светодиодов. Можно сделать любую, какую хотите, всё упирается в напряжение, которое подаётся на светодиоды. У меня был использован блок питания Импульсный блок питания на 9 В, только выходное напряжение не 9 В, а перенастроил его на 12 В.

    Дополнительно сделал фильтр. Добавил модуль ключей на транзисторах 2N2222, которые управляют секциями гирлянды. На входы ключей идут управляющие сигналы с Ардуино через резисторы 1.2 кОм. Для их управления задействовал порты только с ШИМ, чтобы можно было плавно менять яркость всех секций. Номера контактов: D3, D5, D6, D9, D10. Кнопку выбора эффекта и кнопку сброса вывел на небольшую плату, на ней же вначале установил линейный стабилизатор на КРЕН5В, дающий 5В для питания Ардуино от импульсного блока питания. Потом для этого стабилизатора сделал отдельный модуль. Размеры его платы 27.5х20 мм.

    Окончательный скетч смотрите ниже:

    /***********************************************************
     * 2018-03-19 Mr.ALB Тренировка в программировании Ардуино
     *
     * Управление 5-ю светодиодными гирляндами
     * 11-ть эффектов работы
     * Дребезг книпки SB1 устраняется аппаратно с помощью LM358P
     *
     * 2018-12-08 9-ть  эффектов работы
     * 2018-12-11 11-ть эффектов работы
    ***********************************************************/
    
    /* Задержки в мс */
    #define DELAY_1     100
    #define DELAY_2     200
    #define DELAY_3     300
    #define DELAY_5     500
    #define DELAY_10    1000
    #define MAX_EFFECT  11
    
    byte mode = 0;            //Режим работы гирлянды
    byte ledLevel = 0;
    byte deltaLevel = 10;     // Шаг изменения яркости
    
    /* Переменные для кнопки */
    byte switchPin = 2;       // Подключаем кнопку SB1 на 2-й pin
    
    /* Перывание */
    volatile byte effect = 0; //Визуальный эффект через прерывание
    byte numberInt = 0;       //Номер прерывания
    
    int repeat;
    
    /***************************************
     * Функция - Включение гирлянды (секции)
     * 
     * Состояние flag:
     *  Если 0, то выключить
     *  Если 1, то включить
     *  Если 2, то включить и выключить
     **************************************/
    void fn_blinkLed(byte pin, word  msec, byte flag = 2)
    {
      if(flag == 1 || flag == 2)
      {
        digitalWrite(pin, HIGH);//Включение
        delay(msec);
      }
      if(flag == 0 || flag == 2)
      {
        digitalWrite(pin, LOW);//Выключение
        delay(msec);
      }
    }
    
    void setup()
    {
      /* Конфигурируем цифровые выводы под номерами 3,5,6,9,10 на выход */
      for(byte i = 3; i < 11; i++)
      {
        if(i != 4 && i != 7 && i != 8)
          pinMode(i, OUTPUT);
      }
      pinMode(switchPin, INPUT);      // SB1 - Выбор эффектов
      pinMode(LED_BUILTIN, OUTPUT);   // Светодиод на pin13 для сигнализации
      digitalWrite(LED_BUILTIN, LOW); // Потушим светодиод на pin13
    
      /* Прикрепим прерывание int0 (pin2) к функции fn_ISR */
      attachInterrupt(numberInt, fn_ISR, RISING);
    }
    
    /*******************************************
     * Переключение пяти гирлянд. 11 эффектов
     * effect = 0 - все эффекты последовательно
     *          1 - первый эффект
     *          2 - второй эффект
     *          ...
    ********************************************/
    void loop()
    {
      if(effect == 1  || effect == 0) fn_Effect1();
      if(effect == 2  || effect == 0) fn_Effect2();
      if(effect == 3  || effect == 0) fn_Effect3();
      if(effect == 4  || effect == 0) fn_Effect4();
      if(effect == 5  || effect == 0) fn_Effect5();
      if(effect == 6  || effect == 0) fn_Effect6();
      if(effect == 7  || effect == 0) fn_Effect7();
      if(effect == 8  || effect == 0) fn_Effect8();
      if(effect == 9  || effect == 0) fn_Effect9();
      if(effect == 10 || effect == 0) fn_Effect10();
      if(effect == 11 || effect == 0) fn_Effect11();
    
      /* Выключаем все гирлянды */
      for(byte i = 3; i<11; i++)
      {
        if(i != 4 && i != 7 && i != 8)
          fn_blinkLed(i, 1, 0);   //Выключаем
      }
      delay(DELAY_10);
      //Сигнализируем об окончании цикла
      fn_blinkLed(LED_BUILTIN, DELAY_2);
    }
    
    /***********************
     * Функции
     ***********************/
    
    /* Функция - Обработка прерывания */
    void fn_ISR()
    {
      /* При нажатии на кнопку SB1, происходит выбор эффекта */
      ++effect; //Переходим на другой эффект
      if(effect > MAX_EFFECT) effect = 0;// Установим все эффекты сразу
    }
    
    /* Функция - Изменение яркости светодиода */
    void fn_stepBrightness(byte ledPin, word step_delay, byte deltaLevel, int sign)
    {
      if(sign == 1) ledLevel = 0;
      else ledLevel = 255;
    
      for(byte i = 0; i  <  25; i++)
      {
       analogWrite(ledPin, ledLevel);
       ledLevel = ledLevel + deltaLevel * sign;
       if(ledLevel < deltaLevel) ledLevel = 0;
       delay(step_delay);
      }
    }
    
    /*******************************
     * Первый эффект.
     *  Поочерёдно включаем и выключаем гирлянды
     */
    void fn_Effect1()
    {
      for(int i = 3; i < 11; i++)
      {
        if(i != 4 && i != 7 && i != 8)
          fn_blinkLed(i, DELAY_5);
      }
    }
    
    /*******************************
     * Второй эффект.
     *  Последовательно включаем все гирлянды...
     */
    void fn_Effect2()
    {
      for(byte i = 3; i < 11; i++)
      {
        if(i != 4 && i != 7 && i != 8)
          fn_blinkLed(i, DELAY_5, 1);
      }
      /* ...потом в обратном порядке их выключаем */
      for(byte i = 10; i > 2; i--)
      {
        if(i != 4 && i != 7 && i != 8)
          fn_blinkLed(i, DELAY_5, 0);
      }
    }
    
    /*******************************
     * Третий эффект.
     *  Все включить,  задержка 1 с
     *  Все выключить, задержка 1 с
     */
    void fn_Effect3()
    {
      repeat = 5;//Повтор 5 раз
      for(int k = 0; k < repeat; k++)
      {
        for(byte j = 0; j < 2; j++)
        {
          if(j == 0) mode = 1;      //Режим включения
          else mode = 0;            //Режим выключения
          for(byte i = 3; i < 11; i++)
          {
            if(i != 4 && i != 7 && i != 8)
              fn_blinkLed(i, 1, mode);//Задержка 1 мс
          }
          delay(DELAY_10);//Задержка 1 с
        }
      }
    }
    
    /*******************************
     * Четвертый эффект.
     *  Быстрая последовательная пробежка по гирляндам
     */
    void fn_Effect4()
    {
     if(effect == 4 || effect == 0)
      {
        repeat = 5;                  //Повтор 5 раз
        for(byte k = 0;k < repeat;k++)
        {
         // В прямом порядке...
         for(byte i = 3; i < 11; i++)
         {
           if(i== 3)
            fn_blinkLed(i, DELAY_2, 0);
           if(i== 5||i== 6||i== 9)
            fn_blinkLed(i, DELAY_2);
           if(i== 10)
            fn_blinkLed(i, DELAY_2, 1);
         }
         // ...в обратном порядке
         for(byte i = 10; i > 2; i--)
         {
           if(i== 10)
            fn_blinkLed(i, DELAY_2, 0);
           if(i== 5||i== 6||i== 9)
            fn_blinkLed(i, DELAY_2);
           if(i== 3)
            fn_blinkLed(i, DELAY_2, 1);
         }
       }
     }
    }
    
    /*******************************
     * Пятый эффект.
     *  Включаем с крайних к центральной
     */
    void fn_Effect5()
    {
      // Включаем с крайних до центральной
      fn_blinkLed(3, 1, 1);
      fn_blinkLed(10, 1, 1);    //Задержка 1 мс
      delay(DELAY_5);           //Задержка 500 мс
      fn_blinkLed(5, 1, 1);
      fn_blinkLed(9, 1, 1);
      delay(DELAY_5);
      fn_blinkLed(6, 1, 1);
      delay(DELAY_10);
    
      // Выключаем центральную
      fn_blinkLed(6, 1, 0);     //Задержка 1 мс
      delay(DELAY_5);           //Задержка 500 мс
      fn_blinkLed(5, 1, 0);
      fn_blinkLed(9, 1, 0);
      delay(DELAY_5);
      fn_blinkLed(3, 1, 0);
      fn_blinkLed(10, 1, 0);
      delay(DELAY_10);
    }
    
    /*******************************
     * Шестой эффект.
     *  Включаем ШИМ на 3,5,6,9,10
     */
    void fn_Effect6()
    {
       for(byte i = 3; i  <  11; i++)
       {
        if(i != 4 && i != 7 && i != 8)
         {
           fn_stepBrightness(i, DELAY_1, deltaLevel, 1);   // Зажигается
           fn_stepBrightness(i, DELAY_1, deltaLevel, - 1); // Тухнет
         }
       }
      delay(DELAY_5);
    }
    
    /*******************************
     * Седьмой эффект.
     * Быстрое моргание - мерцание
     */
    void fn_Effect7()
    {
      repeat = 108;//Повтор 108 раз
      for(byte k = 0;k < repeat;k++)
      {
        for(byte j = 0; j < 2; j++)
        {
          if(j == 0) mode = 1;          //Режим включения
          else mode = 0;                //Режим выключения
          for(byte i = 3; i < 11; i++)
          {
            if(i != 4 && i != 7 && i != 8)
              fn_blinkLed(i, 1, mode);//Задержка 1 мс
          }
          delay(21);
        }
      }
    }
    
    /*******************************
     * Восьмой эффект.
     *   включение 3-6-10 далее 5-9 → повтор
     */
    void fn_Effect8()
    {
      repeat=16;                //Повтор 16 раз
      for(byte k = 0;k < repeat;k++)
      {
        fn_blinkLed(5, 1, 0);   //Режим выключения
        fn_blinkLed(9, 1, 0);
        fn_blinkLed(3, 1, 1);   //Режим включения
        fn_blinkLed(6, 1, 1);
        fn_blinkLed(10, 1, 1);
        delay(DELAY_5);
        fn_blinkLed(5, 1, 1);   //Режим включения
        fn_blinkLed(9, 1, 1);
        fn_blinkLed(3, 1, 0);   //Режим выключения
        fn_blinkLed(6, 1, 0);
        fn_blinkLed(10, 1, 0);
        delay(DELAY_5);
      }
    }
    
    /************************
     * Девятый эффект.
     * включение x-5-6-9-10
     *     далее 3-x-6-9-10
     *     далее 3-5-x-9-10
     *     далее 3-5-6-x-10
     *     далее 3-5-6-9-x
     */
    void fn_Effect9()
    {
      repeat = 5;                         //Повтор 5 раз
      for(byte k = 0;k < repeat;k++)
      {
        for(byte i=5; i < 11; i++)
        { // Включаем 5-6-9-10
          if(i != 7 && i != 8)
            fn_blinkLed(i, 1, 1);       //Задержка 1 мс
          if(i== 3)
            fn_blinkLed(3, DELAY_5, 0); // Гасим
        }
    
        fn_blinkLed(3, 1, 1);       // Включаем
        fn_blinkLed(5, DELAY_5, 0); // Гасим
    
        fn_blinkLed(5, 1, 1);       // Включаем
        fn_blinkLed(6, DELAY_5, 0); // Гасим
    
        fn_blinkLed(6, 1, 1);       // Включаем
        fn_blinkLed(9, DELAY_5, 0); // Гасим
    
        fn_blinkLed(9, 1, 1);       // Включаем
        fn_blinkLed(10, DELAY_5, 0);// Гасим
      }
    }
    
    /*******************************
     * Десятый эффект.
     * Быстрое разное моргание - мерцание
     */
    void fn_Effect10()
    {
      repeat = 108;//Повтор 108 раз
      for(byte k = 0;k < repeat;k++)
      {
        for(byte j = 0; j < 2; j++)
        {
          if(j == 0) mode = 1;          //Режим включения
          else mode = 0;                //Режим выключения
          for(byte i = 3; i < 11; i++)
          {
            if(i== 3)
              fn_blinkLed(i, 1, mode);//Задержка 1 мс
            if(i== 5)
              fn_blinkLed(i, 2, mode);//Задержка 2 мс
            if(i== 6)
              fn_blinkLed(i, 3, mode);//Задержка 3 мс
            if(i== 9)
              fn_blinkLed(i, 4, mode);//Задержка 4 мс
            if(i== 10)
              fn_blinkLed(i, 5, mode);//Задержка 5 мс
          }  
          delay(21);
        }
      }
    }
    
    /*******************************
     * Одиннадцатый эффект.
     * Просто включены
     */
    void fn_Effect11()
    {
      mode = 1;            //Режим включения
      for(byte i = 3; i < 11; i++)
      {
        if(i != 4 && i != 7 && i != 8)
          fn_blinkLed(i, 1, mode);//Задержка 1 мс
      }
      delay(DELAY_10);
      mode = 0;                   //Режим выключения
      for(byte i = 3; i < 11; i++)
      {
        if(i != 4 && i != 7 && i != 8)
          fn_blinkLed(i, 1, mode);//Задержка 1 мс
      }
    }
    
    

    Новый скетч можно скачать тут: my_led_elka.zip

    Триггер Шмитта (подавитель дребезга кнопки) сделал в виде отдельного модуля, если вдруг понадобится не в новогоднее время, то можно быстро снять и использовать в каком-нибудь другом проекте улыбка. Модуль имеет размеры 25х20 мм.

    Модуль подавителя дребезга на LM358P
    Pic 5. Модуль подавителя дребезга на LM358P
    Модуль подавителя дребезга на LM358P<br>Вид со стороны соединений
    Pic 6. Модуль подавителя дребезга на LM358P
    Вид со стороны соединений

    Ниже на фото реализация устройства, остаётся лишь всё поместить в удобную коробку или какой-нибудь корпусок.

    Реализация устройства
    Pic 7. Реализация устройства

    На фото выше слева-направо видны отдельные модули:

    • Блок питания 12 В;
    • Фильтр питания;
    • Модуль подавителя дребезга кнопки;
    • Планка с кнопками;
    • Модуль стабилизатора на 5 В;
    • Arduino UNO;
    • Модуль ключей.

    Промежуточный вариант. Процесс настройки
    Pic 8. Промежуточный вариант. Процесс настройки

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

    2018-12-11

    Вот и дошло дело до коробка. Решил сделать его из ДВП, по-быстрому. Ниже на фото рабочий процесс изготовления.

    Процесс изотовления коробки
    Pic 9. Процесс изотовления коробки

    А далее всё уже установлено в коробок. На боковой стенке есть отверстие под кнопки управления и ещё отверстие под USB, для загрузки обновлений программы. В принципе, это устройство нужно до 19 января, а там можно его части, по необходимости, снять и использовать в других проектах, особенно саму плату Ардуино.

    Тестирование работоспособности уже собранного устройства
    Pic 10. Тестирование работоспособности уже собранного устройства
    2018-12-23
    . Mr.ALB
    Предыдущая страница Страница 4 Далее