Hallo zusammen,
Ich habe ein Problem in meinem Code und verstehe nicht wieso das passiert und wie ich es lösen soll. Ich hoffe hier kann mir jemand helfen!
Das Projekt:
Ich möchte mit einem Hygrometer und Photosensor einen Automatisch bewässerten Blumentopf machen (Ich weiß es gibt dieses Projekt schon, möchte aber mein eigenes machen) Es sollen verschiedene werte auf Display und mithilfe eines Knopfes die Bewässerung Schwelle eingestellt werden.
Den Bildschirm sowie die Sensoren funktionieren wie ich es mir vorgestellt habe. Den Rest mit der Steuerung habe ich noch nicht angegangen.
Zu meinem Problem:
Ich musste erfahren wie delay() nicht die richtige option war da es das ganze Programm pausiert. Ich habe mich daraufhin etwas mit millis() erkundet und habe versucht meine Idee umzusetzen. Ich möchte, dass das Relais das an pin 7 ist für 3 Sekunden geschlossen wird.
Ich habe versucht das mithilfe einer if-Bedingung zu bewältigen, indem ich versucht habe bis 3000 millis() den Pin auf High zu stellen und nach dieser Zeit mit else die Zeit wieder auf 0 zu stellen damit er erneut bis 3000 Zählen kann.
Leider bleibt er, egal ob mit else, if, else if, immer bei Zeit = 0 und möchte nicht von vorne anfangen zu Zälen.
P.S.: Ich bin noch relativ neu auf diesem Gebiet und bitte verzeiht mir, wenn ich (für euch) offensichtliche Sachen übersehen habe.
int Pumpe = 7;
unsigned long Zeit = 0;
void setup() {
Serial.begin(9600);
pinMode(Pumpe, OUTPUT);
}
void loop() {
Zeit = millis();
if (Zeit < 3000) {
digitalWrite(Pumpe, HIGH);
}
if (Zeit > 3000) {
digitalWrite(Pumpe, LOW);
Zeit = 0;
delay(1000);
}
Serial.println(Zeit);
delay(100);
}
2.) Schau dir das BlinkWithoutDelay Beispiel an. millis() gibt die Zeit seit dem Einschalten zurück. Du musst daher die Differenz der aktuellen Zeit zu einem vorherigen Ereignis bilden. Und wenn die Differenz größer 3000 ist sind 3 Sekunden vobeit
Das, was Du machen willst, entspricht ja in etwa dem Blinken einer LED. Also schaue Dir das Beispiel BlinkWithoutDelay in Deiner IDE an. Da hast Du den Ablauf, den Du brauchst.
Es gibt übrigens keine if-Schleife, nur eine if-Abfrage.
du willlst es ja verstehen also millis() läuft ab start des Arduino immer weiter.(fast) Also ist es nur für etwa 3s kleiner als 3000.
Mit Deiner Zeile: start=millis() hat start den gleiche Wert wie millis(). Soweit noch alles klar ?
die Abfrage if(zeit<3000) ist also nur für 3s nach start des systems erfüllt und dann nie mehr.
die Abfrage if(zeit> 3000) ist dann nach 3 s Laufzeit des Systems immer erfüllt.
aber Du bist ganz nah dran du musst Dir nur die Zeit merken wen du eingeschaltet hast zeit=millis() und dann mit der Differenz wieder ausschalten.
if( millis()-zeit >3000)
Wenn man nun noch 'sprechende variablen' dafür nimmt ...
// Funktionalität starten
startmillis=millis();
digitalWrite(kompressorPin,HIGH);
stateKompressor=true;
...
if (stateKompressor==true && millis-startmillis>=solllaufzeitkompressor){
//Laufzeit erreicht/überschritten
digitalWrite(kompressorPin,LOW);
stateKompressor=false;
...
Erstmal vielen Dank für eure Antworten.
Ich habe es nun versucht wie in dem Tutorial mit der LED zu machen. Leider ist das nicht ganz das, was ich brauche... Das Relais soll nicht alle 3000ms kurz aktiviert werden und dann wieder ausgeschaltet, es soll für 3000ms Sekunden GEHALTEN werden, wenn die Bedingungen von den Sensoren gegeben sind.
Leider fällt mir nun auch nicht mehr ein was ich ändern soll um das umzusetzen...
Das geht sehr ähnlich. Zeitpunkt abspeichern und dann ständig über die Differenz abfragen ob die Zeit schon abgelaufen ist. Eventuell eine zusätzliche Statusvariable einführen.
du must noch darüber nachdenken was passieren soll wenn wärend der 3s die Einschaltbedingung wieder weg geht. Soll dann auch das Relais wieder ausgehen oder trotzdem so lange anbleiben wie die Einschaltbedingung vorhanden ist. Was soll passieren wenn die Einschaltbedingung länger als 3s ansteht soll dann das Relais anbleiben oder trotzdem nach 3s ausgehen.
ich hab mal was gemacht ganz einfach zum verstehen. Einschaltbedingung ist ein Taster an pin4 der nach GND schaltet. Ausgang geht auf die interne LED des UNO pin 13. der Sketch arbeitet als Impulsverlängerung.
uint32_t startzeit;
const byte butonpin = 4;
const byte led = 13;
void setup() {
// put your setup code here, to run once:
// Serial.begin(9600);
pinMode(butonpin, INPUT_PULLUP);
pinMode (led, OUTPUT);
}
void loop() {
if (digitalRead(butonpin) == 0) {// Bedingung einschalten
startzeit = millis();// startzeit aug aktuelle Zeit setzen
}
if (millis() - startzeit < 3000) { // Differenz < 3000
digitalWrite(led, HIGH);
}
else {
digitalWrite(led, LOW);
}
}
So oder so solltest Du geteert, gefedert und zum Schluss mit Gewichten an den Füßen in den See geworfen werden, denn Du hast „If Schleife“ geschrieben. Aber naja ... bald ist wieder Wochenende, da wollen wir dem Raumpflegepersonal mal nicht zu viel Arbeit machen
Dir fehlt nach meinem Eindruck der letzte „Dreh“ beim Verstehen eines Zustandsautomates (=State Machine, Endlicher Automat).
Ein Zustandsautomat ist ein „Strickmuster“, das ungefähr so blöd zu verstehen ist wie Rekursion. Ein Beispiel und eine gute Erklärung können da viel helfen. Sieh Dir auf jeden Fall mal die Nachtwächter-Erklärung an! Vielleicht hilft auch das, was mir dazu einfiel.
Außerdem finde ich, dass es auch mal eine gute Einführung in die Idee von Objektorientierung und Klassen geben sollte. Was Du möchtest würde sich IMO ganz gut für ein Beispiel eignen.