Подключение pir датчика d203s к ардуино.
- Войдите на сайт для отправки комментариев
Здравствуйте. Можно ли подключить инфракрасный датчик движения d203s напрямую к ардуино, и сложно ли будет писать под это дело код?
Мне нужно сделать автоматическую включалку света на этом датчике. Зачем ардуино? Дело в том, что я хочу приделать сюда и фоторезистор, и, соответственно должно получается так: если за окном темно инфракрасный датчик работает и фиксирует движения, если светло, то работать он не должен. Так же для того, чтобы прописать все необходимые задержки, чтобы, например, при случайном коротковременном затенении фоторезистора сразу он не срабатывал. Ардуинку планируют использовать маленькую, на attiny85.
P.S. Готовая платка из Китая с этим датчиком меня по ряду причин не устроила, поэтому прошу её, как решение проблемы, не предлагать.
Можно.
Почему именно на этом датчике? есть более подходящие для ARduino
На attiny 85 сами перепишите (с АЦП для определения освещенности придется помучаться, возьмите лучше ProMini), уберите датчик DHT и BT модуль обмена:
#include <EEPROM.h> #include "DHT.h" #include <SoftwareSerial.h> #define LBLUE 10 #define LGREEN 11 #define LRED 12 #define FRES1 A0 #define FRES2 A2 #define CYCLE_GET_TEMP 307 #define RELAY1 8 //lamp #define RELAY2 9 #define RCWL 7 #define RIP 6 #define DHTPIN 5 #define BTRXD 4 #define BTTXD 3 #define BTKEY 2 #define BTSTATUS A4 SoftwareSerial BT(BTTXD, BTRXD); DHT dht(DHTPIN, DHT22); unsigned long timerSec = 0; unsigned int timerGetTemp = 300; unsigned int timerNightON = 0; unsigned int timerDayON = 0; unsigned int timerLightON = 0; String strCommand = ""; boolean flagPowerON = false; float currentHum, currentTemp; boolean flagTempOK = false; unsigned int valNight1, valNight2; boolean flagRIP = true, flagRCWL = true; // test value boolean flagStreetLightON = false; boolean flagNightON = false; byte swNightValue = 127; byte swNightDelay = 10; //sec - delay ON/off Night mode byte valMaxStreetLightON = 127; void setup() { // put your setup code here, to run once: Serial.begin(9600); pinMode(LED_BUILTIN, OUTPUT); pinMode(LBLUE, OUTPUT); pinMode(LGREEN, OUTPUT); pinMode(LRED, OUTPUT); pinMode(RELAY1, OUTPUT); pinMode(RELAY2, OUTPUT); pinMode(RCWL, INPUT); pinMode(RIP, INPUT); //off all led and relay digitalWrite(LED_BUILTIN, LOW); digitalWrite(LBLUE, HIGH); digitalWrite(LGREEN, HIGH); digitalWrite(LRED, HIGH); digitalWrite(RELAY1, LOW); digitalWrite(RELAY2, LOW); //BT sets pinMode(BTKEY, OUTPUT); digitalWrite(BTKEY, LOW); BT.begin(9600); // get settings from eeprom // address = 0 = Power ON = 1 OFF = 0 byte item = EEPROM.read(0); if (item == 255) { EEPROM.write(0, 0); } if ((item == 0) || (item == 255)) { flagPowerON = false; printConsoleText("Power is OFF"); } else { flagPowerON = true; printConsoleText("Power is ON"); } // address = 1 = swNightValue swNightValue = EEPROM.read(1); // address = 2 = swNightDelay swNightDelay = EEPROM.read(2); // address = 3 = valMaxStreetLightON valMaxStreetLightON = EEPROM.read(3); } void loop() { // put your main code here, to run repeatedly: // read console command if (Serial.available()) { while (Serial.available()) { strCommand += char(Serial.read()); delay(50); } } // read BT console if (BT.available()) { while (BT.available()) { strCommand += char(BT.read()); delay(50); } } // exec command strCommand.trim(); if (strCommand.length() > 3) { executeCommand(); strCommand = ""; } // - /*unsigned int bs = analogRead(BTSTATUS); if (bs != btst) { btst = bs; Serial.println(bs); }*/ // count timers unsigned long ctmr = (long(millis() / 1000)); if ((timerSec > 4294900) && (ctmr < 100)) { timerSec = 0; } if (ctmr > timerSec) { timerSec = ctmr; //digitalWrite(LED_BUILTIN, !digitalRead(LED_BUILTIN)); //test // run every sec // read sensors // analize sensor and show led and log int ar1 = analogRead(FRES1); byte brl = map(ar1, 0, 1023, 0, 255); int rrl = brl - valNight1; if ((rrl > 5) || (rrl < (-5))) { valNight1 = brl; String st = "FRES1 changed "; st += String(brl); printConsoleText(st); } ar1 = analogRead(FRES2); brl = map(ar1, 0, 1023, 0, 255); rrl = brl - valNight2; if ((rrl > 5) || (rrl < (-5))) { valNight2 = brl; String st = "FRES2 changed "; st += String(brl); printConsoleText(st); } if (!flagStreetLightON) { if ((valNight1 < swNightValue) && (valNight2 < swNightValue)) { ++timerNightON; } else { ++timerDayON; } if (timerNightON >= swNightDelay) { timerNightON = 0; timerDayON = 0; if (!flagNightON) { flagNightON = true; digitalWrite(LED_BUILTIN, HIGH); printConsoleText("Night is ON"); } } if (timerDayON >= swNightDelay) { timerNightON = 0; timerDayON = 0; if (flagNightON) { flagNightON = false; digitalWrite(LED_BUILTIN, LOW); printConsoleText("Day is ON"); } } } else { // calculate time Light ++timerLightON; if (timerLightON >= valMaxStreetLightON) { timerLightON = 0; timerNightON = 0; timerDayON = 0; flagStreetLightON = false; printConsoleText("Lamp OFF"); // off ligth relay digitalWrite(RELAY1, LOW); } } // analize sensor and execute action byte flm = digitalRead(RCWL); if (flm == 1) { if (flm != flagRCWL) { printConsoleText("RCWL is ON"); } flagRCWL = true; digitalWrite(LGREEN, LOW); } else { if (flm != flagRCWL) { printConsoleText("RCWL is OFF"); } flagRCWL = false; digitalWrite(LGREEN, HIGH); } // get RIPs sensors flm = digitalRead(RIP); if (flm == 1) { if (flm != flagRIP) { printConsoleText("RIP is ON"); } flagRIP = true; digitalWrite(LBLUE, LOW); } else { if (flm != flagRIP) { printConsoleText("RIP is OFF"); } flagRIP = false; digitalWrite(LBLUE, HIGH); } //-- if (flagPowerON) { // power is on if ((!flagStreetLightON) && (flagNightON)) { // analize RIPs sensors and switch ligth on if ((flagRIP) && (flagRCWL)) { flagRIP = false; flagRCWL = false; flagStreetLightON = true; printConsoleText("Lamp ON"); timerLightON = 0; // lamp relay on digitalWrite(RELAY1, HIGH); } } } else { // off relay flagStreetLightON = false; digitalWrite(RELAY1, LOW); digitalWrite(RELAY2, LOW); } // load temp and hum ++timerGetTemp; if (timerGetTemp >= CYCLE_GET_TEMP) { timerGetTemp = 0; //get current temp and hum currentHum = dht.readHumidity(); currentTemp = dht.readTemperature(); if (isnan(currentHum) || isnan(currentTemp)) { flagTempOK = false; } else { flagTempOK = true; } } // end run every sec } } void executeCommand() { strCommand.toLowerCase(); if ((strCommand.indexOf("poweroff") > -1)) { flagPowerON = false; EEPROM.write(0, 0); printConsoleText("Power is OFF"); } if ((strCommand.indexOf("setbtlsch") > -1)) { digitalWrite(BTKEY, HIGH); //- begin cmd String cmd = "AT"; Serial.println(cmd); BT.println(cmd); delay(500); String val = ""; if (BT.available()) { while (BT.available()) { val += char(BT.read()); delay(50); } Serial.println(val); } //- begin cmd cmd = "AT+ORGL"; Serial.println(cmd); BT.println(cmd); delay(500); val = ""; if (BT.available()) { while (BT.available()) { val += char(BT.read()); delay(50); } Serial.println(val); } //- begin cmd cmd = "AT+ROLE=0"; Serial.println(cmd); BT.println(cmd); delay(500); val = ""; if (BT.available()) { while (BT.available()) { val += char(BT.read()); delay(50); } Serial.println(val); } //- begin cmd cmd = "AT+UART=9600,0,0"; Serial.println(cmd); BT.println(cmd); delay(500); val = ""; if (BT.available()) { while (BT.available()) { val += char(BT.read()); delay(50); } Serial.println(val); } //- begin cmd cmd = "AT+PSWD=5812"; Serial.println(cmd); BT.println(cmd); delay(500); val = ""; if (BT.available()) { while (BT.available()) { val += char(BT.read()); delay(50); } Serial.println(val); } //- begin cmd cmd = "AT+NAME=LSCHBT"; Serial.println(cmd); BT.println(cmd); delay(500); val = ""; if (BT.available()) { while (BT.available()) { val += char(BT.read()); delay(50); } Serial.println(val); } // - end cmd digitalWrite(BTKEY, LOW); } if ((strCommand.indexOf("uptime") > -1)) { String ss = "Uptime: " + String(int(timerSec / 3600)) + " hours"; printConsoleText(ss); ss = "Current valNight1 = " + String(valNight1); printConsoleText(ss); ss = "Current valNight2 = " + String(valNight2); printConsoleText(ss); ss = "Current flagRIP = " + String(flagRIP); printConsoleText(ss); ss = "Current flagRCWL = " + String(flagRCWL); printConsoleText(ss); ss = "Current flagStreetLightON = " + String(flagStreetLightON); printConsoleText(ss); ss = "Current swNightValue = " + String(swNightValue); printConsoleText(ss); ss = "Current swNightDelay = " + String(swNightDelay); printConsoleText(ss); ss = "Current valMaxStreetLightON = " + String(valMaxStreetLightON); printConsoleText(ss); } if ((strCommand.indexOf("poweron") > -1)) { flagPowerON = true; EEPROM.write(0, 1); printConsoleText("Power is ON"); } if ((strCommand.indexOf("gettemp") > -1)) { if (flagTempOK) { String ct = "Temperature: "; ct += currentTemp; ct += " °C Humidity: "; ct += currentHum; ct += " %"; printConsoleText(ct); } else { printConsoleText("No Temperature and Humidity"); } } if ((strCommand.indexOf("setnightvalue") > -1)) { byte sv = GetStrValCommand("setnightvalue", strCommand.indexOf("setnightvalue")); if (sv > 0 ) { swNightValue = sv; EEPROM.write(1, sv); printConsoleText("OK"); } } if ((strCommand.indexOf("setnightdelay") > -1)) { byte sv = GetStrValCommand("setnightdelay", strCommand.indexOf("setnightdelay")); if (sv > 0 ) { swNightDelay = sv; EEPROM.write(2, sv); printConsoleText("OK"); } } if ((strCommand.indexOf("setmaxstreetlighton") > -1)) { byte sv = GetStrValCommand("setmaxstreetlighton", strCommand.indexOf("setmaxstreetlighton")); if (sv > 0 ) { valMaxStreetLightON = sv; EEPROM.write(3, sv); printConsoleText("OK"); } } } byte GetStrValCommand(String CS, int indexStr) { int lc = CS.length(); int ls = strCommand.length(); if ((indexStr + lc) >= ls) { return 0; } int rv = 0; String rs = ""; for (int i = 0; i <= 2 ; ++i) { if ((indexStr + lc + i) > ls) { break; } int ti = int(strCommand[indexStr + lc + i]); if ((ti >= 48) && (ti <= 57)) { rs = rs + strCommand[indexStr + lc + i]; } } int lrs = rs.length(); if (lrs < 1) { return 0; } if (lrs == 1) { rv = (int(rs[0]) - 48); } if (lrs == 2) { int is = int(rs[0]) - 48; rv += 10 * is; rv += (int(rs[1]) - 48); } if (lrs == 3) { int is = int(rs[0]) - 48; rv += 100 * is; is = int(rs[1]) - 48; rv += 10 * is; rv += (int(rs[2]) - 48); } if (rv > 255) { rv = 255; } return rv; } void printConsoleText(String inText) { Serial.println(inText); // print BT console if (analogRead(BTSTATUS) > 500) { BT.println(inText); } }На attiny 85 ... с АЦП для определения освещенности придется помучаться
А что там за проблемы с АЦП? Вроде такой же analogRead, как везде? Что там не так?
Вроде такой же analogRead, как везде
Не знал, спасибо. Тогда ТС еще проще.
А я -то испугался, что я что-то пропустил. Это моя любимая микросхема, но я чаще её пользую ручками в атмел-студии. Но в IDE, если в менеджере плат её установить, то analogRead точно есть. Вот я и подумал, может там с ним не так что-нибудь, т.к. сам-то я его толком не использовал.
http://sc-tech.cn/en/D203Se.pdf
Большое спасибо! А какой датчик, более подходят для ардуино? Мне не принципиально какой использовать, выбор пал на этот, так как он стоял в палатке, которая мне пришла из Китая, и которая меня не устраивает.
Какой молоток лучше подходит для орехов? Сможете ответить с первого раза и в точку?
Требования сначала к системе и датчику опишите
Требования к такому датчику стандартные: необходимо, чтобы он фиксировал человека в небольшой комнате и система включала свет. Положение датчика не принципиально, установить могу где угодно, габариты тоже не важны. Если я Вас правильно понял, то вот все требования.
sr-hc501
Так это я о нем и говорил, когда имел ввиду "палатку из Китая"). Если бы в нем все было хорошо, тогда и ардуина была бы не нужна, так как там есть место под фоторезистор. Меня в нем не устраивают задержки. К примеру, зафиксировал этот контроллер движение, выдал лог.1, далее идёт задержка этой лог.1 (почему-то можно выставить минимум 5 мин, что уже не очень). Далее, если движений больше нет, то по истечении задержки, лог.1 пропадает и если сразу после этого снова пройтись под датчиком, то лог.1 он не выдаст, так как у него есть ещё какая-то задержка прим. 10с между выключением и последующим включением. Есть ещё пара моментов, которые меня не устраивают, которые уже касаются работы фоторезистора.
так для этого МК и придумали чтоб программировать исполнительные устройства под нужную логику :)
скетч выше я дал, или исправляйте или пишите сами.
Так это понятно, но тут то дело в том, что есть ненужные задержки. К примеру, если мне нужно чтобы задержка была не 5 мин (а как я уже говорил ниже не ставится), а 1 мин. Тут контроллером её уже не убрать). Так, конечно, удобней бы было подключать готовый блок.
И ещё маленький вопрос, сложно ли будет написать такую программу, которая бы всем этим заправляла? С программированием дело имел, основы знаю.
нифига не понял, как так задержку минуту не убрать?
501 датчик можно сделать минимальный несколько секунд - все остальное программируется
а программу вам кинул выше - там все это есть - и датчик освещения и регулировки значений времени включения и выключения, и удаленная настройка через BT.
код древний, кривенький, но уже больше года исправно в деревне трудится