ich benötige einmal eure Hilfe.
Mein plan ist es ein Gerät zu bauen welches ein kleines Magnetventil, eine LEDVorformatierter Text sowie einen Taster und einen Schwimmerschalter besitzt. Dieses Gerät soll unseren Wasserhahn in der Gerage intervallmäßig "durchspülen". Die Beschaffung der Komponenten und das zusammenbauen ist kein Problem. Beim Code für den Arduino struggle ich aber noch ein bisschen.
Ziel ist es, dass alle 24h (muss nicht auf die Sekunde genau passieren) nach einschalten des Geräts das Ventil für 60s angesteuert ,also einfach ein high-Pegel an einem Ausgang erzeugt werden soll. Zusätzlich soll die LED alle 10s kurz blinken, um zu sehen dass das Gerät noch an ist. Mit dem Taster soll man das Ventil händisch betätigen/testen können, ohne den 24h Rhythmus zu beeinflussen oder neu zu starten. Der Schwimmerschalter unterbricht lediglich den Kontakt zum Ventil wenn das Becken überlaufen sollte.
Hier meine Ansätze:
const byte LED=1;
void setup()
{
pinMode(LED,OUTPUT);
}
void loop()
{
digitalWrite(LED,millis()%10000<200);
}
````Vorformatierter Text`
mit dieser Zeile: digitalWrite(LED,millis()%10000<200); lasse ich die InfoLED alle 10s für 200ms blinken.
Könnte ich mit so einer Zeile mit angepassten Zahlen auch meinen 24h Timer bauen?
Ich habe ebenso versucht für den Funktionstest mit dem Taster Folgendes einzufügen:
const byte LED=1;
const byte Ventil=2;
int taster=3;
int tasterstatus=0;
Dies funktioniert soweit nur benötige ich noch einen Rat für den 24h Timer.
Eventuell kann mir ja jemand helfen.
Besten Dank schonmal im Voraus! :slight_smile:
Im englischen Teil des Forum müssen die Beiträge und Diskussionen in englischer Sprache verfasst werden. Deswegen wurde diese Diskussion in den deutschen Teil des Forums verschoben.
Rein vorsorglich: Dein Code hat keinen Schwimmerschalter.
Handelt es sich dabei um eine Sicherheitseinrichtung, gehört die dahin, wo sie wirksam ist und Du wertest nur deren tatsächlichen Zustand aus, so das notwendig ist.
Na denn...
gibt es von mir auch einen Vorschlag.
Du schreibst nicht, was Du verwendest.
Auf einem Arduino ist 1 als PIN ggfls. nicht die beste Idee. auf 0 und 1 ist die USB-Schnittstelle mit drauf, Du sperrst Dich ggfls. aus.
const byte LED = 1;
const byte Ventil = 2;
const byte taster = 3;
const unsigned long tag = 86400 * 1000UL; // Jeder Tag hat 86400 sekunden
const unsigned long ventilzeit = 60 * 1000UL; // zeit in ms
unsigned long laststart = 0;
void setup()
{
pinMode(LED, OUTPUT);
pinMode(Ventil, OUTPUT);
pinMode(taster, INPUT);
}
void loop()
{
if (!manual()) automatic(); // manuell nicht ausgelöst? Dann Automatik
heartbeat(); // blinkblink
}
bool manual()
{
if (digitalRead(taster)) // ausgelöst?
{
digitalWrite(Ventil, HIGH); // ventil setzen
return true; // Schluss
}
return false;
}
void automatic()
{
if (millis() - laststart >= tag) // ein ganzer Tag ist abgelaufen
{
digitalWrite(Ventil, HIGH); // Ventil setzen
laststart = millis(); // Startzeit merken
}
if (millis() - laststart >= ventilzeit) // Laufzeit - Startzeit erfüllt?
{
digitalWrite(Ventil, LOW); // Aus
}
}
void heartbeat()
{
static unsigned long lastmillis = 0;
if (millis() - lastmillis >= 500)
{
digitalWrite(LED, !digitalRead(LED));
lastmillis = millis();
}
}
@my_xy_projekt dein Sketch funktioniert soweit super. Nur wenn ich den Taster innerhalb der ersten 60s nach dem einschalten betätige, bleibt das Ventil für 60s offen. Danach öffnet es nur beim drücken des Tasters und schließt auch wieder beim los lassen(wie es eigentlich von Anfang an sein sollte).
An sich keine schlimme Sache nur wundert es mich woran das liegen könnte?
Ja.. ich weiss.
Ich war mir gestern nicht sicher, ob das wirklich richtig gedacht war.
Ersetze den manual.
Was der Code machen soll:
Ich benötige eine zusätzliche Variable um mir den letzten Zustand der Taste zu merken, die ist default nicht gesetzt.
Wenn die Taste gedrückt wird, wird der PIN gesetzt und die Variable.
-Bis hierhin wie vorher auch.
Was jetzt zusätzlich dazu kommt:
Wenn ich die Taste wieder loslasse UND die merker-Variable vorher gesetzt war, NUR dann setze ich das Ventil wieder LOW.
Die Rückgabe des Zustandes erfolgt über den Inhalt der Variablen.
Der lokale Merker muss static sein, weil beim verlassen der Funktion der Inhalt nicht verloren gehen darf.
bool manual()
{
static bool isManual = false;
if (digitalRead(taster)) // ausgelöst?
{
digitalWrite(Ventil, HIGH); // ventil setzen
isManual = true; // merken
}
else if (isManual) // taste war vorher und jetzt nicht mehr ausgelöst
{
digitalWrite(Ventil, LOW); // ventil setzen
isManual = false; // wieder merken (Buchstabensalat korrigiert)
}
return isManual; // Rückgabe des Merkers
}
Da war ich mir schon recht sicher.
Die Geschichte hat nur einen Haken...
Das Timing kommt durcheinander, wenn manual() startet und dann zeitlich in die automatik()-Phase läuft.
Nach aktuellem Codestand würde automatic erst nach loslassen von manual() wieder starten und den Versatz nicht mehr aufholen.
Wenn Dich das nicht stört, ist es egal.
Wenn doch, weil du automatik() immer zur selben Zeit ausführen willst, ist das nur eine kleine Änderung...
laststart nicht mit millis füllen sondern mit tag.
Willst Du selbst probieren und rausfinden warum? Dann Zettel und Stift nehmen und die zeitlichen Abläufe aufschreiben.
Ich habe dafür auch etwas länger gebraucht. Einmal aufschreiben.. und seitdem erinner mich immer mal wieder daran