Светофор для школы на IR пульте

Тема в разделе "Arduino & Shields", создана пользователем Legionerio, 7 фев 2019.

  1. Legionerio

    Legionerio Нуб

    Вопрос от валянка, помогите разобраться с кодом.
    Подкинули скетч работы светофора, пытаюсь к нему прикрутить пульт управления, но так как ардуино вижу в глаза первый раз
    очень все проблематично с понимаем режимов работы
    Как включить я вроде бы разобрался, а вот как теперь его выключить вопрос
    Код (C++):
    #include "IRremote.h"
    IRrecv irrecv(7); // указываем вывод, к которому подключен приемник
    decode_results results;
    // Текущий режим работы светофора
    enum State : int {OFF, CAR, WALK, YELLOW};
    enum Light : uint8_t {WAIT, ON_RED, OFF_RED, ON_YELLOW, OFF_YELLOW, ON_GREEN, OFF_GREEN, RETURN};
    // Временные интервалы работы в режиме дорожный
    const PROGMEM long TIME_TABLE[]  = {             1,         1,      1000,   1000,     1,        1,    5000,  500,      500,      500,      500,      500,       1,    1500,    1,      5000   };
    const PROGMEM uint8_t ACTION_TABLE[]  = {OFF_GREEN, OFF_YELLOW, ON_RED,ON_YELLOW,ON_GREEN,OFF_RED,OFF_YELLOW,WAIT,OFF_GREEN,ON_GREEN,OFF_GREEN,ON_GREEN,OFF_GREEN,ON_YELLOW,ON_RED, OFF_YELLOW, RETURN};
    State traffic;
    Light lights;
    const int RedLed = 9;             // Порт 9, красный светодиод
    const int YelLed = 10;             // Порт 10, желтый светодиод
    const int GrnLed = 3;             // Порт 3, зеленый светодиод
    long TimeDelay = 0;
    long CurrentDelay = 0;
    uint8_t CurrentStep = 0;
    void setup()
    {
        pinMode(RedLed, OUTPUT);  
        pinMode(YelLed, OUTPUT);
        pinMode(GrnLed, OUTPUT);
        pinMode(7, INPUT);
     
       Serial.begin(9600); // выставляем скорость COM порта
      irrecv.enableIRIn(); // запускаем прием
        CurrentStep = 0;
        CurrentDelay = pgm_read_word_near(TIME_TABLE+CurrentStep);
        lights = pgm_read_word_near(ACTION_TABLE+CurrentStep);
        TimeDelay = millis();
    }
    void ChangeLight(){
    switch (lights) {
      case WAIT:
        if (WaitTime(CurrentDelay)) {
         CurrentStep++;
         lights = pgm_read_word_near(ACTION_TABLE+CurrentStep);
         Serial.print("LIGHT - ");
         Serial.println(lights);
         return;
        }
       else {
        return;
       }
      break;
      case ON_RED:
        digitalWrite(RedLed, HIGH);
      break;
      case OFF_RED:
        digitalWrite(RedLed, LOW);
      break;
      case ON_YELLOW:
        digitalWrite(YelLed, HIGH);
      break;
      case OFF_YELLOW:
        digitalWrite(YelLed, LOW);
      break;
      case ON_GREEN:
         digitalWrite(GrnLed, HIGH);
      break;
      case OFF_GREEN:
         digitalWrite(GrnLed, LOW);
    break;
      case RETURN:
          CurrentStep = 0;
      break;
       }
       lights = WAIT;
       CurrentDelay = pgm_read_word_near(TIME_TABLE+CurrentStep);
       TimeDelay = millis();
    }
    int WaitTime(int timeDelay) {
    if((millis() - TimeDelay) < timeDelay) {
        return 0;
    } else {
        return 1;
    }
    }
    void loop(){
    if ( irrecv.decode( &results )) { // если данные пришли

     
    if (results.value == 0x202B04F); { // Код с пульта
       traffic = CAR;
    switch (traffic) {
      case OFF:
      break;
      case CAR:
        ChangeLight();
      break;
      return;
    }
    }
    irrecv.resume(); // принимаем следующую команду
    }    
    }
     
  2. Asper Daffy

    Asper Daffy Иксперд

    "Подкинули" - это вот здесь - http://arduino.ru/forum/pesochnitsa-razdel-dlya-novichkov/svetofor-dlya-shkoly ?

    Слушай родной, тебе там же "подкинули" правильную книгу, которую, как я понял читать ты не намерен. А если учиться не хочешь, то почему не заказать в платном разделе, чем неделями побираться по форумам? Неужели жаба настолько сильна?
     
  3. Legionerio

    Legionerio Нуб

    В платном разделе, мне дадут готовый код. А мне это не так важно. В данном случае я хоч понять как это работает.
    И к тому - же я уже нашел стенд на пульте со всеми видами светофоров 100$ Так что не в деньгах дело. Побираться??? А с каких пор спросить, что и как работает стало побираться?
    Обычный интерес.
    Если ты все знаешь - ну флаг тебе в руки, а я вот не знаю
    А если ты знаешь, то предложи вариант на коммерческой основе, только так чтобы я понял как это работает. Тупо код мне писать не надо и не интересно, потому как вся задумка которую я хотел сделать стоит в сборе 100$
     
  4. Asper Daffy

    Asper Daffy Иксперд

    В той теме, на которую я ссылался, тебе столько хороших идей подсказали, что мама не горюй. Но, книга не прочитана и ничего из того, что тебе сказали словами, а не кодом - не реализовано. Отсюда и вывод, что учиться тебе нахрен не надо - тебе код нужен. Ну, а ходить и клянчить код - это и есть "побираться".
     
    parovoZZ нравится это.
  5. Legionerio

    Legionerio Нуб

    Вот именно, что код как раз мне дали и он работает - но я них*ра там не понимаю. Потому как ардуино забрал на НП в пятницу посмотрел документацию, которая лежит на сайте ссылку на него ты выше бросил. и написал свой скетч как я это понимаю.
    Мне там ответили, что циклы for все равно прервать мне не удастся, и дали пример с конечными автоматами, но после того как я прикрутил пульт, опять же пользуясь примером из библиотеки IRremote.h у меня все путается и не хочет работать как этого надо мне, а это значит, что я недогнал куда, как, и что включать!!!!

    Мне не нужен код. Я написал на форуме в разделе для новичков, однозначно, что не один я столкнулся с данной проблемой.

    Рыл гуголь таких или подобных вопросов много именно связанных с пультами.

    А на счет кода, то не это есть конечная цель, я уже сделал маленький пример с использованием библиотеки
    SimpleTimer , то есть в принципе тот кусок кода который до LOOP мне вообще не интересен, потому как используя SimpleTimer мне хотя-бы понятно как работает сам светофор.

    Но и тут вопрос использования swich case используя пример из библиотеки IRremote.h


    Код (C++):
    #include "IRremote.h"

    IRrecv irrecv(2); // указываем вывод, к которому подключен приемник

    decode_results results;

    void setup() {
      irrecv.enableIRIn(); // запускаем прием
    }

    void loop() {
      if ( irrecv.decode( &results )) { // если данные пришли
        switch ( results.value ) {
        case 0xFFA857:
            digitalWrite( 13, HIGH );
            break;
        case 0xFFE01F:
            digitalWrite( 13, LOW );
            break;
        }  
        irrecv.resume(); // принимаем следующую команду
      }
    }
    Опять возникает вопрос, как это все скомпоновать.

    Ну если ты считаешь, что я побираюсь - это только твое мнение
     
  6. KindMan

    KindMan Гуру

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

    Legionerio Нуб

    traffic = CAR;
     
  8. Legionerio

    Legionerio Нуб

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

    Код (C++):
    void loop(){
    if ( irrecv.decode( &results )) { // если данные пришли

    if (results.value == 0x202B04F); { // Код с пульта
       traffic = CAR;
    switch (traffic) {
      case OFF:
      break;
      case CAR:
        ChangeLight();
      break;
    }
    }
    irrecv.resume(); // принимаем следующую команду
    }  
    }
    Она начинает работать в циклическом виде после того, как я ставлю return; после
    ChangeLight();
    break;
    А если не ставить, то счетчик в вашем примере
    Serial.print("LIGHT - "); печатает с каждым нажатием кнопки LIGHT - 4, LIGHT - 1, и тд. и чтобы прокрутить цикл, кнопку приходится все время нажимать - а это как я понял, после каждого нажатия включается CurrentStep+1;

    А если подключаю 2 кнопку пульта и включаю чтобы функция крутилась return;, то 2-я кнопка тупо не срабатывает, как я понял из-за использования того самого return;

    И у меня реально зло берет, что я никак не могу догнать почему так.
     
    Последнее редактирование: 7 фев 2019
  9. KindMan

    KindMan Гуру

    Нет, вы принимаете сигнал, меняете статус переменной и всё, заканчиваете обработку ик приемника. А затем уже свитч, в котором, согласно статуса трффик делаете что то. Не надо пихать одно в другое
     
  10. Legionerio

    Legionerio Нуб

    Как-то так??????

    Код (C++):
    void loop(){
    if ( irrecv.decode( &results )) { // если данные пришли
    switch ( results.value ) {
      case 0x202B04F: // Код с пульта
          traffic = CAR;
          break;
    case 0x20240BF:
        ?????????????
        break;
    irrecv.resume(); // принимаем следующую команду
    }
    }
    switch (traffic) {
        case OFF:
      break;
      case CAR:
        ChangeLight();
      break;

    }
    }
     
    Последнее редактирование: 7 фев 2019
  11. DetSimen

    DetSimen Guest

  12. Legionerio

    Legionerio Нуб

    :D :confused::confused::confused::confused:
    я уже нифига не соображаю
     
  13. b707

    b707 Гуру

    блин, может уже книжку почитать?
    Ну сколько можно тыкать вслепую?

    Ну или уже смирится с тем. что это "не твое" и пойти купить готовый светофор за 100 баксов
     
    parovoZZ и Belkin нравится это.
  14. Legionerio

    Legionerio Нуб

    Светофор уже заказал.

    Кажется начинаю доганять.
    Надо было начать с массивов, а не с конечных автоматов и прочего,

    На данный момент у меня получилось все. Может где не правильно, но работает.!!!!

    Код (C++):
    void loop(){
     
    if ( irrecv.decode( &results )) { // если данные пришли
    switch ( results.value ) {
      case 0x202B04F: // Код с пульта
       traffic = CAR;
    TimeDelay = millis();
    CurrentStep =0;
          break;
    case 0x20240BF:
    traffic = OFF;
    TimeDelay = 0;
    CurrentStep = 4;
    digitalWrite(YelLed, LOW);
    digitalWrite(GrnLed, LOW);
    digitalWrite(RedLed, LOW);
        break;
    }
    irrecv.resume(); // принимаем следующую команду
    }

    switch (traffic) {
      case OFF:
      break;
      case CAR:
      ChangeLight();
      break;
    }
    }
    Всем спасибо!

    Отдельная благодарность
    KindMan
    РЕАЛЬНО ПОМОГ
     
  15. Asper Daffy

    Asper Daffy Иксперд

    Да, нет же! Надо было начать с изучения нормальной литературы.
     
    b707 и Belkin нравится это.
  16. Legionerio

    Legionerio Нуб

    С какой? Позвольте полюбопытствовать ?
    Я смотрю документацию по ардуино на русском сайте поддержки и на домене юа, она там одинаковая
     
  17. qwone

    qwone Гик

    Вы не волнуйтесь. Попозже ее заменят на мову и добавят брехни , что бы отличались. Но пока можно пользоваться. Тем более плата скорее всего китайская.
     
  18. b707

    b707 Гуру

    после этого неудивительно, что до вас так долго доходило...

    Это как изучать металлугрию по инструкции к кастрюле - потому что она металлическая.
    На ардуино-ру вам давали ссылки на нормальные книги по языку. начните с них
     
  19. Legionerio

    Legionerio Нуб

    При чем тут мова? Я на русском них*ра не понимаю )))), а еще на мові я бы и пробовать не стал, у меня в школе 3 была
     
  20. Legionerio

    Legionerio Нуб

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

    Не думаю что прям все, кто взял в руки ардуино, начинают с чтения книг по программированию