Beiträge von Knisterbein

    Hallo Franz


    Du könntest den Rx doch wieder in Stand setzen und dann damit wieder mal reinhören? Wer weiss, vielleicht packt Dich dann das Fieber. Selber habe ich die Prüfung nur absolviert, weil ich wissen wollte, ob ich den Prüfungsstress aushalten würde und nebenbei war es ein gutes Gefühl ohne schlechtes Gewissen mit HF zu basteln.
    Natürlich ist das Gerät viel zu schade um in der Entsorgung zu landen und da es einige Sammer gibt, nehme ichmal an, dass Du das Gerät auch los wirst.

    herzliche Grüsse

    Pius

    Hallo Franz

    kenne mich damit auch nicht weiter aus. Es ist ein Gerät des Sommercamp Labels, die Daten findest Du sicher.

    der FR-100b ist der Empfänger und der Sender hat die Bezeichnung FL200B

    Ein Rat, schalte das Gerät nicht ein, resp. steck es nicht in die Steckdose um es auszuprobieren. Nach solanger Zeit sind die Elkos ausgetrocknet und sollten vor der Inbetriebname geprüft werden. Wird das Gerät eingeschaltet kann es passieren, dass ein Elko Schluss macht und damit weitere Bauteile zerstört.

    Wenn man dann die verdächtigen Kandidaten ersetzt hat, dann schaltet man das Gerät "langsam" ein (mit Regeltrafo) um den Kondensatoren die Möglichkeit zu geben, sich zu erholen. Gute Quellen für die Restaurierung alter Geräte findest Du hier beim Radiomuseum.

    Gruss

    Pius

    #Teckelfreund

    Die Uhr ist super geworden, vorallem für einen, der sich mit 3D Druck und Co nicht auskennt.
    Mein Respekt und nun eine DCF77 Synchronisierung?
    Muss ja nicht sein, die staunenden Blicke auf die Uhr reichen aus.

    Pius

    Super Kai


    beeindruckend, echt da wird C++ auch benutzt.

    Kleiner Hinweis, ich weiss nicht ob die Arduino C++ Compiler dies auch unterstützen (denke schon).

    Code
    1. class Timer {
    2. public:
    3. void start() { timeStamp = millis(); }
    4. bool operator()(const unsigned long duration) { return (millis() - timeStamp >= duration) ? true : false; }
    5. private:
    6. unsigned long timeStamp {0};
    7. };

    In obiger Klasse fragt man mit dem Operator ab, ob die Zeit erreicht ist. Soweit ich feststelle verändert der Operator den Inhalt der Klasse Timer nicht.

    In solchen Fällen, kann man den Compiler dies mitteilen mit "const" am Ende


    Code
    1. bool operator()(const unsigned long duration)const {
    2. return (millis() - timeStamp >= duration) ? true : false;
    3. }

    In allen Fällen, wo man mit der Klasse Timer dann weiterarbeiten möchte und diese selbst als const deklariert haben möchte, weil vielleicht nicht alle "Benutzer" der Klasse eine Veränderung im Inhalt der Klasse erlaubt sein soll. Im obigen Fall denke ich, ist es nicht notwendig.

    Aber ich habe mir angewöhnt alle Memberfunktionen einer Klasse, die den Inhalt der Klasse selbst nicht verändern mit dem const zu deklarieren.


    Code
    1. constexpr byte seq[NUM_SEQUENCES][NUM_PORTS] {
    2. {LOW, HIGH, HIGH, LOW },
    3. {LOW, LOW, HIGH, LOW },
    4. {LOW, LOW, HIGH, HIGH},
    5. {LOW, LOW, LOW, HIGH},
    6. {HIGH, LOW, LOW, HIGH},
    7. {HIGH, LOW, LOW, LOW },
    8. {HIGH, HIGH, LOW, LOW },
    9. {LOW, HIGH, LOW, LOW }
    10. };

    Bei dieser Tabelle könnte man nochviel Platz einsparen, da ich annehme dass der Compiler für LOW/HIGH jeweils ein Byte benutzt. Aber solange man nicht knapp mit Flash da steht, ist Deine Lösung schöner zu lesen.
    Ich stehe im Augenblick in einem meiner Projekte ganz hart an der Grenze des verfügbaren Flash Speichers und verbringe Tage damit um vielleicht 100 Byte einzusparen. So bin ich soweit, dass ich

    einen f(float n) Aufruf als f(float *pn) realisiere. Ein float belegt 4 Byte, ein Zeiger auf ein float belegt bei meiner 8-Bit CPU nur 2 Byte ...

    Es ist anstrengend ja, aber wenn Du dubuggen willst und der Compiler meldet dass ich 4 Bytes zu viel Code produziere, dann muss ich im Debug Mode Texte verkleinern und eben auch *pfloat anstelle einer Kopie auf dem Stack benutzen. Eine weitere Erkentnis war, dass ich öffters mal das Schlüsselwort "register" für lokale Daten in Funktionen benutze, was oft zu kleinerem Code führt.

    Code
    1. switch (btn.tick()) {
    2. case Btn::ButtonState::longPressed:
    3. rotate(STEPS_PER_MINUTE);
    4. timer.start();
    5. break;
    6. default: checkForNextMinute(timer); break;
    7. }

    würde man das switch mit einem if() else ersetzen:

    Code
    1. if (btn.tick() == Btn::ButtonState::longPressed) {
    2. rotate(STEPS_PER_MINUTE);
    3. timer.start();
    4. }
    5. else {
    6. checkForNextMinute(timer);
    7. }

    spart man etwas Platz ein. Was aber nur Sinn ergibt, wenn das switch case wenige Überprüfungen hat.

    Es macht Spass Code von Dir zu lesen!;)

    schönen Abend

    Pius

    Code
    1. Nach Drücken des Arduino Uno Resett-Buttons funktionierte die Schaltung wieder io.
    2. Also liegt es nicht im Bereich des externen PMW-Boards für die Servo.


    wie kommst Du auf diese Annahme? Für mich heisst dies (Reset am Arduino funktioniert) lediglich, dass es mit hoher Wahrscheinlichkeit kein latchup Effekt die Ursache ist. In Deiner Handzeichnung erkennt man schwarz die Masseverbindung (en) zwischen den Boards, aber nicht die Verdrahtung der Servos. Ich nehme an, dass die jeweils drei Leitungen 5V, Gnd und das PWM Signal darstellen. Ist sichergestellt dass das Masspotential möglichst an einem zentralen Punkt erfolgt, oder nicht? Dünne Leitungen mit längerem Weg weisen schnell mal Potentialdifferenzen aus, die dann bei schon relativ kleinen Störungen (von aussen) unschöne Auswirkungen haben können.

    Aber zuvor würde ich versuchen die SW mit einer per Software blinkenden Led zu erweitern, direkt beim Arduino. Stellt sich der Fehler wieder ein und die Led blinkt nach wie vor, kann man daraus schliessen, dass die SW nach wie vor ihren Dienst erledigt.

    Wenn ich in der Zeichnung (ein Schema wäre viel aufschlussreicher) mögliche Verdächtige suche, dann würde ich als erstes beim 220V Relais (ist die ein Schütz?) suchen, weil eine AC versorgte Spule, und dies mit hoher Spannung (230V) doch sehr viel magnetische Felder erzeugt.


    Ok, wenn Du schreibst, die Servo Leitungen sind nicht verdrillt, dann frage ich mich wer mit wem verdrillt sein soll. Die Masse dient als Rückleiter für die Versorgung der Servos und gleichzeitig auch für das PWM Signal. Ist die Leitung lange (vielleicht sind 3m bei einem dünnen Querschnitt bereits lange) dann addiert sich der Versorgungsstrom des Servos mit dem Rückstrom des PWM Signals wobei der Strom des PWM Signals vermutlich um Faktoren kleiner ist.

    Hier wäre es ein Versuch wert, jedes Servo-Kabel am Board jeweils 2-3 mal um einen Ferritkern zu wickeln.

    Mehr fällt mir im Moment leider auch nicht ein. Aber es führt kein Weg drum herum, viele einzelne Schritte nacheinander auszuprobieren. Wichtig, nur immer ein Schritt aufs mal, weil man andernfalls nicht sicher sein kann ob die Kombination zweier Dinge sich nicht wieder aufheben oder verstärken.

    schönen Abend

    Pius

    Hans, mir geht es so, dass je älter ich werde umso weniger wage ich mich etwas auszuprobieren. Bevor ich es tue, wird überlegt, studiert, gesucht und wenn ich mich dann aufgerafft habe etwas zu probieren, ärgere ich mich, dass ich es nicht viel früher wagte. Und obwohl ich meinen Mechanismus kenne, scheint es sich zu wiederholen.

    Für das aktuelle Projekt mit der Einarbeitung eines ATTinys tat ich mich sehr schwer, wagte es dann und war erstaunt, dass sich viele meiner Fragen zuvor in Luft aufgelöst haben und andere, nicht angedachte Probleme, löste ichdann eben in kleinen Schritten.

    Mein Fazit, ich befehle mir nun öffters: Probier es aus!

    Hallo Hans


    Code
    1. Was ich überhaupt nicht verstehe, dass am Ausgang eine positive Spannung anliegt.
    2. Frage: Sollte die Spannung nicht Negativ sein?

    Das Eingangssignale Deiner Beschaltung wird dem OP am - Eingang zugeführt. Damit ist der OP im Invertierenden Betrieb, wie Du bereits richtig festgestellt hast.

    ABER, Dein Foto zeigt zur Versorgung eine 9V Batterie was mich vermuten lässt, dass Du am OP lediglich eine positive Versorgung hast, womit die Ausgangsspannung am OP natürlich nie negativen Werte erreichen kann.

    Übrigens, das Messen von Spannungen am OP Eingang erscheint mir nicht zielführend, da es sich um sehr kleine Eingangsströme handelt, die in den - oder + Anschluss fliessen.

    Aber zuerst nimm eine zweite 9V Batterie in Serie geschaltet. Der gemeinsam verbundene Punkt der Batterien ist der Nullbezug (Masse). +9V führst Du auf den OP V+ und den -9V auf das V- des OP.

    Gruss
    Pius

    vielleicht hilft dier Link weiter: Grundlagen


    sorry, den Link hast Du ja schon

    nun Kai es geht natürlich in beide Richtungen, schliesslich kann ein Schrittmotor in zwei Richtungen positioniert werden. Meist sind die Schrittweiten (ich habe keine Ahnung von Schrittmotoren) 1.8 Grad under der Kreis hat ... passt doch.

    Sicher eine machbare und interessante Aufgabe.

    Hallo Franz


    ich kann leider auch nicht aus Erfahrung sprechen, betrachte ich jedoch meine Funkuhr an der Wand (Zeiger) und erinnere mich, wie sie sich manchmal nach dem Batteriewechsel richtet, dann könnte dies zumindest ein Lösungsansatz sein.
    Soll sich die Uhr richten, dann bewegt sie die Zeiger als erstes auf high noon (12h). Die Position(en) sind vermutlich mit Kontakten oder Schaltern definiert. Dann, wenn die Uhr eine Zeit korrekt empfangen konnte, bewegt sie die Zeiger vorwärts, was mit Schrittmotoren wohl einfach zu realisieren ist. Kurz, die Uhr benötigt eine mechanische Position, die bekannt sein muss. Damit steht aber auch sicher, dass sich die Uhr lediglich ab und an nach der empfangenen Zeit ausrichten kann. Mit mehr Aufwand sollte aber auch dies machbar sein, wenn die interne Uhrzeit (Positionen der Anzahl Schritte der Zeiger) mit der externen Zeit verglichen wird und dann eben gewartet oder die Zeiger vorwärts bewegt werden.


    Gruss

    Pius

    @Franz


    das Bild das Felix geschickt hat, zeigt einen Servo für den Antrieb der Klappe. Demnach gehe ich davon aus, dass man die Klappe mit dem Servo bestimmt und anschliessend, solange keine Veränderung gewünscht ist, so ruhen lassen kann. Im Code selbst wird aber, sofern ich das richtig interpretiert habe, der Servo, resp. Alle, bei jedem Loop Durchgang neu gesetzt. Da es sich um eine Lüftung handelt, kann ich mir nicht vorstellen, dass die Servos häufig betätigt werden müssen und dass man die Servos (vermutlich) nicht alle abwechelnd bewegen muss.

    Gruss

    Pius

    Hallo Felix


    ich habe nur mal schnell in den Code reingeschaut und erschrak an den sich repetierenden Code Teilen.


    Für jeden Knopf machst Du sowas:

    Code
    1. int nextButtonCount(int ButtCnt)
    2. { uint8_t PwmVal; if (digitalRead(0)== 0) { ButtCnt++ ; if (ButtCnt > 300) ButtCnt = 299; // ELSE Wert beschreibt den Winkel Klappe zu } else { // digitalRead(0) != 0 ButtCnt--; if (ButtCnt<1) ButtCnt=1; } }

    wobei ich in diesem Besipiel die Range Prüfung zumindest da hingestellt habe, wo sie auch plausibel werden. Damit meine ich, dass ich keine Prüfung von <1 machen muss, wenn ButtCnt zuvor inkrementiert wurde. Auf jeden Fall wird bei jedem Loop Durchgang entweder incrementiert oder dekrementiert.

    Was ist mit mit dem Button Wert von 0?



    Nach der Range Prüfung machst Du dann:

    Code
    1. if (Button1_Counter>100)     pwm.setPWM(1, 0, 110); else     pwm.setPWM(1, 0, 290); // Servoarm #1 90 Grad drehen
    2. //diesen Block könnte man auch so schreiben: pwm.setPWM(1, 0, (Button1_Counter>100) ?110 : 290 );
    3. // oder gleich mit einer Var
    4. int PwmVal = (Button1_Counter>100) ? 110 : 290;
    5. // und dann an einer Stelle die Funktion aufrufen:
    6. pwm.setPWM(1, 0, PwmVal); // Servoarm #1 90 Grad drehen

    was dann vermutlich bei jedem Button identisch gemacht wird -> Redundanz


    Ich verstehe nichts von Arduino und den Lib's, könnte mir aber vorstellen dass das sehr schnelle und wiederholte Beschicken der pwm.setPwm() Funktion ein Grund für heisse Servos sein könnte. Zusätzlich könnte es sein, da IMMER inkrementiert oder dekrementiert wird, dass alle Servos laufend etwas hin und her bewegt werden, auch wenn die Position schon längst erreicht ist. Dies produziert daurende Stromänderungen, die sich als Transienten auf den Leitungen äussern können (hang up, latchup).

    Gruss

    Pius

    Hallo Mitlesende


    Danke Franz. Ich rechnen mich zur «Die Unwissenden schämen sich und haben Angst, was falsches zu schreiben» Gruppe und gleichzeitig konnte ich die Frage für mich nicht einordnen.

    Die Stichworte «Multitasking», «sozusagen gleichzeitig» und «Echtzeit» irritierten mich und die Frage, die ich mir bereits vor 40 Jahren schon ab und zu stellte, wenn der Begriff «Echtzeit» benutzt wurde, ob damit echt Echt gemeint ist, was dann mit einem MC als auszuführende Einheit, die notabene jeden Befehl nach dem anderen auszuführen hat, nicht irreführend ist.


    Bereits in der Ausbildung löcherte ich meinen Lehrer mit einer (TTL) Beschaltung, in der Annahme, dass Zeit, auch wenn sie sehr kurz ist, für die Schaltung vielleicht nicht existieren würde.


    Was Bahnelektroniker vermutlich meint ist, dass irgendwelche Bedingungen geprüft und daraus Handlungen möglichst schnell und «zeitnah» ausgeführt werden. Was oft nicht erwähnt wird, ist der Umstand, dass es oft wichtiger ist, etwas nicht zu vergessen, wenn andere Ereignisse sich zeitlich überschneiden.


    Bei einer Lösung mit Schieberegistern (vermutlich als Porterweiterung) wird einem schnell klar, dass Zeit verstreichen wird, bis alle Register richtig beschrieben sind, und dass ich mit dem Latch Befehl die Ausgangs Pins «gleichzeitig» übernehmen kann.


    Es wird auch nicht zur Echtzeit, wenn ich einen schnelleren Prozessor benutze, lediglich die Reaktionszeit wird kürzer.


    Aber Franz liegt doch sicher richtig, wenn er konstruktiv darauf hinweist, dass man gerne wissen möchte, was mit den Schieberegistern erledigt werden soll (Signale stellen, Weichen positionieren, Zugposition erfassen, etc.), weil sich damit die Vorstellungen der Leser konkretisieren.


    Und Kai stellt auch fest, dass er bisher mit millis() für nicht blockierende Aktionen bisher immer eine Lösung gefunden hat. Die Eisenbahn bewegt sich nie in Echtzeit. Es wird geprüft, entschieden und gehandelt. Die Komplexität liegt in der Anzahl der Abläufe, die einem Menschen erschwert die Übersicht über all diese Prozesse zu behalten. Ich würde mal behaupten, dass man da um eine Priorisierung derselben nicht herumkommt. Wer sich schon mal mit der Priorisierung von Interrupt beschäftigt hat, der weiss vermutlich was ich meine. Fakt ist, dass der erfolgreiche Versuch der Arduino Macher, die Komplexität dem Benutzer abzunehmen, dann und wann seine Nachteile hat. Dies ist ein Grund, dass ich mich lieber gleich mit den Internas eines uC beschäftige. Übrigens, im Augenblick ist es der Tiny1626, der mich mehr und mehr fasziniert, aber viel Zeit (ich lerne sehr langsam) abverlangt. Kleines Beispiel: 1 Tag um heraus zu finden, weshalb eine Lösung einer Funktion langsam ist, trotz dem vorhandenen Multiplizierer im Tiny.


    Zu Kai und seinen unermüdlichen Antworten, die er bevorzugt gleich mit einem funktionierenden Beispiel abliefernd beweist, kann ich nur meinen Respekt zollen. Verständlich, dass er sein Tun hinterfragen muss, um nicht selbst unter die Räder zu kommen.


    Zu oft könnte man sich die Video’s von René anschauen, um sich selbst die Antwort auf die gestellte Frage geben zu können. Dies bedingt aber, dass man bereit ist etwas Zeit zu investieren, was man versucht mit der schnellen Frage ab zu kürzen, in der Hoffnung das Denken, Forschen und Suchen wird einem so abgenommen.


    Wir werden es nicht ändern können.


    Deshalb, ja ich zögere jeweils lange bevor ich eine Antwort auf eine Frage liefere und da die meisten Fragen sich um Arduino spezifische Lösungen handelt, halte ich mich auch zurück, da Kai da längst die viel besseren Kenntnisse vorweisen kann, als ich.

    schönen Abend

    Pius

    Hallo Hans


    Deine Überlegung geht in die richtige Richtung. Aber wie Kai schon sagte, ist es unmöglich einigermassen eine "sichere" Aussage zum Problem zu machen. Eine problematische Struktur hat man immer, wenn schnelle Leistungsschaltungen extern angeschlossen sind. Leitungen agieren als Antennen und können Transienten aussenden und empfangen. Mit ein Grund, dass man versucht solche Signale von der CPU mittels Optokoppler fern zu halten.


    Ein Controller der sich aufhängt kann mehrere Ursachen haben.

    • Die SW läuft in den Tod
    • Die Betriebsspannung wird zu tief oder die CPU läuft an, bevor die Betriebsspannung stabil anliegt.
    • Ausgangspin können einen Latchup Effekt einnehmen.

    Die meisten Controller können mit speziellen Funktionen toleranter gegenüber äusseren Bedingungen gemacht werden.

    • Startup Time des Oszillators erhöhen
    • Takt nur so schnell wie notwendig konfigurieren
    • Watchdog in der Software aktivieren
    • Brown-out detection richtig aktivieren


    Hardware


    Blockkondensatoren an allen Chips, auch an den Spannungsreglern.

    Externe Verbindungen so kurz wie möglich ausführen, wenn nicht möglich galvanisch trennen


    Filter auf alle externen Verbindungen vorsehen.

    Leitungen mit «schnellen» Signalen differenziell ausführen und geschirmte Leitungen benutzen.

    Eingänge mit Schutzmechanismen versehen die transiente Spitzen limitieren. Sind die Eingänge «langsam» können Tiefpassfilter die Zuverlässigkeit erhöhen.

    Für solide Masseverbindungen sorgen. Bei abgesetzten Einheiten ist dies leider kaum zu schaffen, dann bleibt nur die galvanische Trennung.

    Grundsätzlich muss man vorab einschätzen können, welche Einheiten Störungen verursachen können. Dann erfolgt die Minimierung der Störung zuerst beim Verursacher bevor man Störungen versucht fern zu halten.


    Aber im konkreten Beispiel wissen wir nichts über den Aufbau, die verwendeten Komponenten, die geschalteten Ströme (und Leistungen). Das Einzige das wir wissen ist, dass ein Reset die Schaltung wieder neu starten lässt. Dies wäre würde schon mal einen Latchup Effekt eher ausschliessen lassen, sofern wirklich nur ein Reset und kein Power Off/On das Gerät wieder ing Gang bringt. Unter dem Begriff Arduino gibt es leider ganz viele unterschiedliche Boards und Controller. Dann sind Begriffe wie "extern" so schwammig, dass die Distanzen im cm oder im Meter Bereich liegen können.


    Gruss

    Pius

    Vielen Dank Kai


    Das von Dir gelieferte Beispiel mit den Erläuterungen ist sehr hilfreich und hat auch mir, der auf einem Wissensstand von C++ seit 2010 sich kaum mehr weiter gebildet hat und im Mikrocontroller Umfeld immer eher auf C setzte, als auf C++. Zu dieser Zeit war constexpr noch nicht geboren.


    Auch das Statement:

    for (auto &nocke : nocken) {}


    scheint auch mit C++ 11 eingeführt worden zu sein und ist mir demnach (noch) nicht geläufig, nehme aber an, dass das «auto» an dieser Stelle eine Vereinfachung eines for() Schleife mitteilt und zum einen die Allokation eines Schleifenzählers, das Abbruchkriterium und auch die Anzahl der Durchläufe aus der Grösse der Tabelle nocke ermittelt wird.

    &nocke:nocken der Zeiger auf die Tabelle und dem anschliessenden Typen der Struktur

    nocke ist der Bezeichner des Schlaufenzählers, nocken der Inhalt des angegebenen Arrays, in diesem Beispiel zwei Strukturen nocken.

    Natürlich, ich muss dies selber nachlesen *g* Aber liege ich so in etwa richtig?

    Wenn dem so ist, dann erspart es einem die Schreibarbeit und beim Anlegen der Tabelle muss man sich jeweils nicht Gedanken darüber machen, den Compiler damit zu beauftragen, die Anzahl Einträge in der Tabelle bestimmen zu müssen. Damit werden einige Punkte, die gerne zu Fehlern führen, in einem Zug verhindert.


    Zu Deinem Kommentar in Post 23

    «Es ist mir ein Rätsel, warum auch in den Beispielen sehr häufig int verwendet wird. Ich habe noch keinen Controller mit mehr als 256 Pins gesehen. Schon gar keinen mit negativen Pin-Werten. Das soll aber erst mal nebensächlich sein, (int) stört die Funktion des Programmes nicht.»


    Per Definition ist ein int in der Grösse undefiniert und wird vom Compiler, abhängig von der Registergrösse der Ziel CPU, bestimmt.
    Nun passt dies aber bei einem Arduino mit einer 8-Bit CPU schon mal nicht zusammen, weil da nimmt der Compiler für int (wie Du korrekt geschrieben hast), 16 Bits. Ich weiss es nicht, vermute aber, dass man damit neuen Problemen ausweichen wollte, die man sich damit geschaffen hätte und definierte die 16Bit’s. Ich arbeitete mit C erst ab den 16 bit CPU’s (int war 16bit), dann mit den 32bit (int = 32bit) und heute sind es eben meist 64bit’s.


    Ich habe mir den Vortrag von Herb Sutter noch nicht ganz angehört, werde dies aber noch tun und vermutlich reicht einmal Anhören auch nicht.


    ich hoffe Du bleibst dem Forum noch lange treu, VIELEN DANK

    Pius

    Sorry, aber den Code durchschaue ich nicht.


    ein paar Hinweise:

    lösche Zeilen 25, 29, 33, 37 die sind alle doppelt gemoppelt


    Zeile 61 ist sicher falsch

    if (digitalRead(Nocke1) == HIGH, value <= 239 && value >= 284)

    ich vermute Du meinst

    if (digitalRead(Nocke1) == HIGH && value <= 239 && value >= 284)

    damit kommst Du aber kaum in den Block Zeile 66 weil value < 239 ist ja auch in der Zeile 61 bereits abgehandelt ausser Nocke1 ist FALSE


    Wenn Nocke1 FALSE ist passiert gar nichts. Dies kann zwar richtig sein, aber wenn zuvor Nocke1 HIGH war, dann wird nichst ausgeschaltet oder eingeschaltet.


    Ein Rat, folge der Logik im Kopf und schreibe diese in C so auf.

    Beispiel:


    // Wenn der Poti Wert 20% erreicht +-2% und der Schalter 2 EIN ist

    if (value <= 239 && value >= 284 && digitalRead(Nocke1) == HIGH ) {


    }

    Wenn nur Nocke1 FALSE ist wird kein Code mehr ausgeführt

    Vieleicht geht es leichter wenn Du die Logik am Anfang nicht verschachtelst:


    if(digitalRead(Nocke1) {


    if(value <= 239 && value >= 284 ) {

    ...

    }

    else {

    ...

    }


    }

    else {

    if(value <= 239 && value >= 284 ) {

    ...


    }

    else {

    ...


    }

    }


    Gruss

    Pius

    Ich habe zwar keine Ahnung vom Arduino, aber ein Rechteck Signal mit einer definierten On/Off Zeit lässt sich, sieht man von einem leichten Jitter mal ab, leicht realisieren.

    Ein Timer, der sagen wir mal mit einer Clock-Rate von 0.5mS zählt, löst immer dann einen Interrupt aus, wenn der Zähler den Wert (oder wenn man runter zählt 0) erreicht. In der Interrupt Routine wird dann die neue Zeit gesetzt und man wartet erneut, bis der Zähler das Ende erreicht hat.

    Bei jedem erreichen der Ziel - Zeit wird gleichzeitig das Ausgangspin aktiviert oder deaktiviert.

    Gruss

    Pius