Автоматическое включение света

Тема в разделе "Arduino & Shields", создана пользователем Евгений_KRD, 14 ноя 2015.

  1. Здравствуйте! Тема давно избитая палками но тем не менее подробностей нигде нет, все как то вокруг да около плавают и по сути не найти, тем более что желаю я сделать довольно гибкую и сложную систему нужна помощь в реализации. Значит есть у меня собственно Arduino UNO, реле Songle SDR-05, два ультразвуковых датчика HC-SCR04, тактовая кнопка и светочувствительный модуль с возможностью регулировки чувствительности вручную.
    Теперь к делу
    Если освещенность в помещении недостаточна:
    1) когда идем из коридора в комнату UltraSonic (US) модули срабатывают в порядке US1+US2 и свет включается
    1.1) выходим US2+US1 выключается свет
    2) свет включается и выключается кнопкой (это на случай ошибок и не стандартных ситуаций вроде: животных ношений жен на руках в комнату, когда вы зашли как один объект а вышло два и т.д.)
    пока что все.
     

    Вложения:

  2. В данный момент я мучаюсь с датчиками звука, реле включать запросто (привел код), а вот как сложить и узнать последовательность сработки не могу придумать

    #define K1in 2
    #define US1trig 3
    #define US1echo 4
    #define SB1 6

    int someBodyInRoom = 0;

    void setup()
    {
    pinMode(K1in, OUTPUT);
    pinMode(US1trig, OUTPUT);
    pinMode(US1echo, INPUT);
    pinMode(SB1, INPUT);

    Serial.begin(9600);
    }

    unsigned int impulseTime1 = 0;
    unsigned int distance_sm1 = 0;

    void loop()
    {
    digitalWrite (US1trig, HIGH);
    delayMicroseconds (10);
    digitalWrite (US1trig, LOW);
    impulseTime1=pulseIn (US1echo, HIGH); // Замеряем длину импульса
    distance_sm1=impulseTime1/58; // Пересчитываем в сантиметры
    Serial.println(distance_sm1); // Выводим на порт
    if (distance_sm1<75 || digitalRead(SB1) == HIGH)
    {
    digitalWrite (K1in, LOW);
    }
    else
    {
    digitalWrite (K1in, HIGH);
    }
    delay(100);
    }
     
  3. Karabas

    Karabas Гик

    А о какой последовательности речь?
    Судя по коду, если что то есть - свет горит, нет- значит нет.
    Я бы добавил еще одно условие и цикл задержки с мониторингом кнопки (вкл\выкл), чтоб свет погрел еще, а не вырубался сразу. К тому же это исключит ложные срабатывания и мигания когда датчик глючит.
     
  4. вы не внимательно прочитали первый комментарий (В данный момент я мучаюсь с датчиками звука, реле включать запросто (привел код- для включения реле, тоесть то что есть сейчас), а вот как сложить и узнать последовательность сработки не могу придумать
    )
    Естественно, что там добавляется еще и US2 в код, но этот код я не привел так как я его не могу довести до ума, как определить какой из них первый сработал какой второй я не знаю пока что. Про кнопку вы меня удивили, я в начале написал что у меня есть и что нужно задействовать
     
    Последнее редактирование: 14 ноя 2015
  5. Tomasina

    Tomasina Сушитель лампочек Модератор

    А зачем детектировать последовательность? У тебя же источник света только один? Вот и включай его при срабатывании любого из US, либо при срабатывании кнопки. А выключай по таймауту.

    Если последовательность действительно нужна, то введи булеву переменную и при срабатывании любого из трёх источников меняй её состояние на противоположное.
     
    Последнее редактирование: 14 ноя 2015
  6. a_komolow

    a_komolow Нуб

    Попробуй счётчик числа вошедших и вышедших человек
    US1 добавляет, US2 отнимает
     
  7. Tomasina

    Tomasina Сушитель лампочек Модератор

    да, со счетчиком код будет чуть проще.
    Код (C++):
    #define K1in    2
    #define US1trig 3
    #define US1echo 4
    #define US2trig 7
    #define US2echo 8
    #define SB1     6
    #define LDO     A1         // пин для фоторезистора
    #define LUMI_VALUE     280 // порог срабатывания для освещенности
    #define DISTANCE_VALUE 75  // порог срабатывания для УЗ-датчиков

    byte peopleCounter = 0;    // счетчик человеков и кошек
    unsigned int lumi;         // освещенность
    unsigned int distanceUS1;  // расстояние c первого US
    unsigned int distanceUS2;  // расстояние cо второго US

    void setup()
    {
      pinMode(K1in, OUTPUT);
      pinMode(US1trig, OUTPUT);
      pinMode(US1echo, INPUT);
      pinMode(US2trig, OUTPUT);
      pinMode(US2echo, INPUT);
      pinMode(SB1, INPUT);
      pinMode(LDO, INPUT);
      Serial.begin(9600);
    }

    void loop()
    {
      lumi = analogRead(LDO);   // получаем освещенность от фоторезистора
      distanceUS1 = readUS(US1trig, US1echo); // получаем расстояние от первого US
      distanceUS2 = readUS(US2trig, US2echo); // получаем расстояние от второго US

      Serial.print("Lumi: ");   // Выводим показания фоторезистора
      Serial.print(lumi);
      Serial.print("\tUS1: ");   // Выводим расстояние от первого US
      Serial.print(distanceUS1);
      Serial.print("\tUS2: ");   // Выводим расстояние от первого US
      Serial.print(distanceUS2);
      Serial.print("\tCounter: ");   // Выводим счетчик
      Serial.println(peopleCounter);

      if(distanceUS1 > DISTANCE_VALUE && distanceUS2 < DISTANCE_VALUE) // кто-то вошел
      {
        peopleCounter++;
        Serial.print("\tCounter: ");
        Serial.println(peopleCounter);
      }

      if(distanceUS1 < DISTANCE_VALUE && distanceUS2 > DISTANCE_VALUE) // кто-то вышел
      {
        if (peopleCounter > 0) peopleCounter--; // защита от призраков
        Serial.print("\tCounter: ");
        Serial.println(peopleCounter);
      }

      if (digitalRead(SB1) == HIGH) // нажатие кнопки
      {
        Serial.println("Button pressed!");
        if (peopleCounter > 0) peopleCounter = 0;
        else peopleCounter = 1;
        Serial.print("\tCounter: ");
        Serial.println(peopleCounter);
      }

      if (lumi < LUMI_VALUE && peopleCounter > 0) // включаем свет, если темно и кто-то есть в помещении
      {
        digitalWrite (K1in, LOW);
      }

      if (peopleCounter == 0) // выключаем свет, если никого нет в помещении
      {
        digitalWrite (K1in, HIGH);
      }

      delay(100);
    }


    unsigned int readUS(byte trigPin, byte echoPin)
    {
      digitalWrite (trigPin, HIGH);
      delayMicroseconds (10);
      digitalWrite (trigPin, LOW);
      unsigned int distance = pulseIn (echoPin, HIGH) / 58; // Замеряем длину импульса и пересчитываем в сантиметры
      return distance;
    }
     
  8. Karabas

    Karabas Гик

    Все понял, просто ультрозвуковые датчики сбили с толку, я думал они в лоб смотрят.
    Вот вам еще вариант,с определением направления прохождения, с отсеиванием ситуаций, если кто то закрыл один датчик но не вошел\вышел.
    Плюс еще можно добавить в комнату pir-датчик, чтоб переставить счетчик если кто то вошел и мультиплицировался.

    Код (C++):

    #include <Ultrasonic.h>
    Ultrasonic ultrasonic_1 (8,9);
    Ultrasonic ultrasonic_2 (10,11);
    int US1;
    int US2;
    int people=0;
    void setup()
    {
      US1 = ultrasonic.Ranging(CM); // Устанавливется значение без людей перед датчиками
      US2 = ultrasonic.Ranging(CM);
    }

    void loop()
    {
      if (ultrasonic_1.Ranging(CM) < US1)
      {
        for (int i=0; i<100; i++)    // Ждем прохождения через второй датчик
        {
         if (ultrasonic_2.Ranging(CM) < US2)
          {
           // Включаем свет
           people++;
           break;
          }
         delay (10);    // Подобрать скорость прохождения между датчиками
      }
    }

    if (ultrasonic_2.Ranging(CM) < US2)
    {
      for (int i=0; i<100; i++)    // Ждем прохождения через второй датчик
      {
       if (ultrasonic_1.Ranging(CM) < US1)
         {
         people--;
       
    //    if (PIR active)   // Читаем покозания pir-датчика. Ситуация когда счетчик обнулился, но в комнате кто то ходит
    //         {
    //         people = 1;  // Минимум один человк
    //         }
         if (!people)
           {
           // Выключаем свет
           break;
           }
           delay (10);        // Подобрать скорость прохождения между датчиками
         }
      }
    }
    }
     
    Последнее редактирование: 15 ноя 2015
  9. необходимо считать людей в комнате 2 датчика для того что бы определить вышел или вошел
     
  10. мне это и нужно
     
  11. Спасибо вам за этот код приду домой посмотрю но на вид то что надо, так же пир датчик буду ставить для проверки остался ли кто в комнате
     
  12. да отсеивание сработки одного датчика нужная вещь, все то что вы перечислили я об этом давно думаю я где то пол года уже занимаюсь этим, просто нуб в электронике, автоматику делаю все что угодно и релейные защиты это новое для меня, я так понял если я составлю подробную спецификацию то здесь с вашей помощью смогу сварить нормальную кашу, так как на других форумах активности было 0 по этому вопросу
     
  13. спасибо огромное за код, подскажите а как изучить библиотеку? Референс? Вот Wiring я учу от сюда большей частью http://arduino.ru/Reference , а как узнать команды библиотеки?
     
  14. Karabas

    Karabas Гик

    Я без понятия, помоему там кроме измерения расстояния ничего и нет. Вот посмотрите что там и к чему
     

    Вложения:

    • Ultrasonic.zip
      Размер файла:
      1,7 КБ
      Просмотров:
      318
  15. Onkel

    Onkel Гуру

    HC-SCR04 не очень обязательная штука. Надежно сечет человека метров с двух, если расстояние больше то может засечь а может и нет. советую переходить на пассивные ик датчики с соответствующими линзами (стандарт, корридор, штора - много есть разных).
     
  16. Здравствуйте! Сейчас на практике пробую по вашему примеру и нашлись проблемы одна из самых важных то что по этому коду if(distanceUS1 > DISTANCE_VALUE && distanceUS2 < DISTANCE_VALUE) // кто-то вошел
    считается что человек вошел если сработал один датчик
     
  17. Спасибо за ответ! Это прекрасный код, но не могу понять в чем дело выдает ошибку
    Light.ino: In function 'void setup()':
    Light.ino:10:7: error: 'ultrasonic' was not declared in this scope
    Ошибка компиляции.
     
  18. Кажется понял буквы заглавные должны были быть
     
  19. Как у вас получается выводить данные в столбик в порту? У меня все в строку :(
     
  20. Karabas

    Karabas Гик

    Чтоб выводить в столбик нужно либо печатать "перенос строки" /n
    Либо печатать построчно командой Serial.println();

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

    Код (C++):
    #include <Ultrasonic.h>
    Ultrasonic ultrasonic(8,9);  // Тут прописуем ноги Trig & Echo

    void setup() {
      Serial.begin(9600);
    }
    void loop()
    {
      Serial.print(ultrasonic.Ranging(CM));
      Serial.println("cm");  
      delay(100);
    }
    Ну и да, там где большие буквы они о должны быть большими
    И подключите библиотеку, Sketch>Import Library>Add Library
     
    Последнее редактирование: 21 ноя 2015