1.2.22. fejezet, Eventually: az esemény vezérelt programozás egyszerűen
Hasznos linkek
Hasonló projektek
Minta alkalmazás
Ez egy WC lámpa kapcsoló algoritmusa. Mikor kinyílik az ajtó, felkapcsolódik a világítás. Mikor becsulódik, ellenőrzi az ülőkétől mért a távolságot egy ultrahangos távolságmérő. A távolságmérés azért jobb a mozgásérzékelésnél, mert mozgás hiányában lekapcsolhat a lámpa. A program az Eventually könyvtárat használja.
Az Eventually könyvtár EvtPinListener csak a gombnyomás tényéről értesítene. Ezért implementálni kell a EvtPinChangeListener-t a pinevent.h-ban.
class EvtPinChangeListener : public EvtListener { protected: int pin; int lastRead; public: EvtPinChangeListener(int pin, EvtAction t); void setupListener(); bool isEventTriggered(); }; EvtPinChangeListener::EvtPinChangeListener(int pin, EvtAction t) { this->lastRead = -1; this->pin = pin; this->triggerAction = t; } void EvtPinChangeListener::setupListener() { } bool EvtPinChangeListener::isEventTriggered() { int readed = digitalRead(pin); bool result; if (lastRead == -1) { this->lastRead = readed; result = false; } else { result = this->lastRead != readed; this->lastRead = readed; } return result; }
A következő kód végzi a vezérlést.
#include <Eventually.h> #include "pinevent.h" EvtManager mgr; const char buttonPin = 5; const char TRIGGERPIN=6; const char ECHOPIN=7; const int ledPin = 13; int buttonState = 0; int lastOffTimer = 0; void setup() { pinMode(ledPin, OUTPUT); digitalWrite(ledPin, LOW); pinMode(buttonPin, INPUT); pinMode(TRIGGERPIN,OUTPUT); pinMode(ECHOPIN,INPUT); Serial.begin(9600); Serial.println("Setup..."); mgr.addListener(new EvtPinChangeListener(buttonPin, (EvtAction)checkDoor)); Serial.println("Listeners started."); } bool checkDoor() { Serial.println("Door swith changed."); buttonState = digitalRead(buttonPin); mgr.resetContext(); if (buttonState == HIGH) { Serial.println("Switch Led on."); digitalWrite(ledPin, LOW); mgr.addListener(new EvtPinChangeListener(buttonPin, (EvtAction)checkDoor)); } else { Serial.println("Check distance."); mgr.addListener(new EvtTimeListener(500, true, (EvtAction)checkDistance)); mgr.addListener(new EvtPinChangeListener(buttonPin, (EvtAction)checkDoor)); } } bool checkDistance() { long duration, distance; digitalWrite(TRIGGERPIN,LOW); delayMicroseconds(3); digitalWrite(TRIGGERPIN,HIGH); delayMicroseconds(12); digitalWrite(TRIGGERPIN,LOW); duration = pulseIn(ECHOPIN,HIGH); distance = 10 * duration / 58.2; Serial.print("distance:"); Serial.print(distance); Serial.println(" mm"); if (distance < 500) { lastOffTimer = 0; } else { lastOffTimer += 1; if (lastOffTimer > 10){ lastOffTimer = 0; digitalWrite(ledPin, HIGH); mgr.resetContext(); mgr.addListener(new EvtPinChangeListener(buttonPin, (EvtAction)checkDoor)); } } return true; } USE_EVENTUALLY_LOOP(mgr)
A példában jól látható hogyan lehet új eseménykezelőt definiálni. Egy, a soros portról érkező eseményeket például az alábbi serialevent.h-ban definiált EvtSerialListener osztály végezheti:
class EvtSerialListener : public EvtListener { protected: Stream * _serial; public: EvtSerialListener(Stream *serial, EvtAction t); void setupListener(); bool isEventTriggered(); }; EvtSerialListener::EvtSerialListener(Stream *serial, EvtAction t) { this->_serial = serial; this->triggerAction = t; } void EvtSerialListener::setupListener() { } bool EvtSerialListener::isEventTriggered() { return _serial->available(); }
Ez a kód - ügyelve a Serial globális változó inicializálására, pedig a soros port echo funkcióját végzi:
#include <Eventually.h> #include "serialevent.h" EvtManager mgr; char inChar; bool serialAction() { while(Serial.available() > 0) { inChar = Serial.read(); Serial.print(inChar); } return true; } void setup() { Serial.begin(9600); while(!Serial); mgr.addListener(new EvtSerialListener(&Serial, (EvtAction) serialAction)); Serial.println("Listeners started."); } USE_EVENTUALLY_LOOP(mgr)
- A hozzászóláshoz be kell jelentkezni