Automatische Arduino Powered Pet Feeder

5 Schritt:Benötigte Materialien: Schritt 1 Schritt 2: Die Grundlagen - Making the Auger (Lebensmittelzuführungsmechanismus) Schritt 3: Erstellen der Box Schritt 4: Arduino - Die Hardware Schritt 5: Arduino - The Code

Automatische Arduino Powered Pet Feeder

Automatische Arduino Powered Pet Feeder


Das ist meine automatische Futterautomat. Präsentiert von Arduino, mit einem 3D-gedruckten Schnecke und programmierbar mit zwei Fütterungszeiten mit einem Benutzer eingestellt Quantität der Nahrung, mit einer Batterie gesicherten internen Uhr.
Meine Katzen fahren mich Nüsse in der Früh um Futter betteln also beschloss ich, es war Zeit, Fütterung Robotize
Ich habe frustriert mit pet Feeder erhältlich in Großbritannien. Sie sind entweder die Art, die sich drehen und enthüllen eine Mahlzeit, bis nur vier Mal, oder die einzige halbwegs ordentliche Maschine mit einem Trichter ist entsetzlich zu programmieren, vergisst alles, wenn Sie die Batterien zu entfernen, und häufig fehlschlägt, auch liefern zu essen! I-Programm hier und da, und die letzte Maschine, die ich verwendet, machte mich so wütend, nur versuchen, die Fütterungszeiten I fast warf sie aus dem Fenster.
Amerika hat einige gute Maschinen, sondern sie bei € 300 USD starten und Versand wäre schmerzhaft in das Vereinigte Königreich, also beschloss ich, zu machen!

Benötigte Materialien: Schritt 1


  1. Elektronik:
    1 x normalen RC Servo - regelmäßige Größe
    1 x Dauer RC Servo - von der Stange oder gehackt.
    1 x 3D gedruckt Auger Teilen (siehe Förderschnecke Schritt) (Pfennige, wenn Sie einen 3D-Drucker haben)
    1 x 1 1/2 "PVC T-Stück Rohr (ebay 2,89 £) http: //www.ebay.co.uk/itm/121534086943 _trksid = p20 ...
    1 x Arduino (Ich habe eine Uno, aber jede Art tun wird)
    OR ... für PCB (1 x ATMEGA328P, Kristall, 2 Kappen, 5V Spannung reg) - google "arduino Steckbrett"
    1 x KY-040 Drehgeber an Bord (ebay 3,85 £) http: //www.ebay.co.uk/itm/181595206550 _trksid = p20 ...
    1 x 16x2 LCD HD44780 kompatibel (ebay 2,53 £) http: //www.ebay.co.uk/itm/281211020326 _trksid = p20 ...
    1 x kleine Druckschalter (nicht selbsthaltend)
    1 x Futterraufe - Ich habe eine für die Lagerung von Lebensmitteln mit einem fest verschließbaren Deckel - zu stoppen, katzenartig kriminellen Aktivitäten.
    1 x Montagedose - I aus MDF gebaut ein
    1 x 12V-Netzteil - rund 500Ma + sicher zu sein - Ansteuerung der Servos. Möglicherweise müssen Sie mehr.

Schritt 2: Die Grundlagen - Making the Auger (Lebensmittelzuführungsmechanismus)

  1. Automatische Arduino Powered Pet Feeder

    Automatische Arduino Powered Pet Feeder

    Automatische Arduino Powered Pet Feeder

    Die erste Hürde ist es, eine Förderschnecke (Schraubenzuführung) zu machen. Bisher war dies zu viel von einem Hindernis für mich, aber jetzt mit 3D-Druck, ich habe gerade heruntergeladen ein Motiv aus Thingiverse und gedruckte it! Wenn Sie gerne basteln, bauen Sie ein 3D-Drucker! - Es macht Spaß zu machen und erstaunlich nützlich, besitzen. Ich baute eine Prusa i3 für rund 350 £.
    (Http://www.thingiverse.com/thing:27854) - Credit für seinen ersten Entwurf, der meine Maschine ist stark auf der Grundlage Kitlaan.
    Seine physische Design ist gut, aber der Code ist zu einfach für meine Bedürfnisse, gibt es keine Anzeige, keine Mehrfach Fütterungen, und es werden keine Benutzer variable Portionsgrößen. Hier setzt die Arduino kommt und speichert das Tag. Ich habe Erfahrung mit Arduino, aber noch nie einen LCD oder einen Drehgeber verwendet - aber es ist kein Problem - die Arduino-Tutorials und Beispiele sind erstaunlich gut geschrieben. Ich habe Erfahrung mit batteriegepufferte Echtzeituhren (RTC), so das Hinzufügen einer war ein Kinderspiel.
    Die Schnecke Druck kommt in ein paar Dateien - eine für die Schnecke, eine für die Servohalterung / Rohrhalterung und eine Servoabstandshalter, die ich nicht brauchen. Ich druckte die Schnecke in einem Durchgang (der Autor bietet eine Split-Version zu, so dass Sie kleinere Gegenstände können drucken und kleben sie zusammen) - Ich habe einen Prusa i3, die keine Probleme mit diesem haben. Die Schnecke ist 10 cm hoch, die i3 druckt bis zu 20cm groß. Ich druckte ohne Trägermaterial und es kam in Ordnung. Ich musste die Basis mit einem Messer schneiden ein wenig, wo die Aussparung für das Servohorn ist, da es einen Bruchteil aufgrund des Mangels an Trägermaterial zusammengebrochen. Sie können sagen, slic3r Trägermaterial nur für die erste "x" Zeilen zu drucken, aber ich glaube nicht, das zu tun.
    Ich habe eine digitale Servo Futaba Ich hatte zu Hand, jeder Servo tun wird, es muss nicht digital sein. Sie benötigen es, um kontinuierlich (keine Endanschläge) sein - diese können von den Plätzen wie Sparkfun gekauft werden, aber ich öffnete die Servo, entfernt die Plastik Beule auf eines der Zahnräder, die es nicht mehr dreht unendlich, und entfernt das Potentiometer. Voila! - Eine kontinuierliche Servo. Suchen Sie einfach im Web - es gibt jede Menge wie-zu in Bezug auf wechselnde regelmäßigen Servos kontinuierliche Servos.
    Ich schraubte den Servo zu dem Schneckenbasis, um sicherzustellen, es war Ebene gedreht und ohne Wackeln und dann Test-Einbau es in einem Stück von 1 1/2 Zoll Kunststoff T-Stück Schlauch (gewöhnlich für Whirlpool Sanitär verwendet) - Kosten £ 2.90 off ebay (PVC Lösungsmittel Schweißrohr - Teiche / Whirlpools etc.). Einmal war ich glücklich wäre es ohne Bindung I fixiert ihn mit Heißkleber, wo es in die Rohreinsätze drehen.
    Jetzt habe ich eine Schnecke! (Hohoho) :-)

Schritt 3: Erstellen der Box

  1. Automatische Arduino Powered Pet Feeder

    Automatische Arduino Powered Pet Feeder

    Automatische Arduino Powered Pet Feeder

    Automatische Arduino Powered Pet Feeder

    Automatische Arduino Powered Pet Feeder

    Automatische Arduino Powered Pet Feeder

    Alle 8 Artikel anzeigen

    Die Box / base / Gehäuse ist eine einfache MDF-Box (9mm). Ich zum ersten Mal einen Kasten, dann schneiden Sie die Basis mit einer Stichsäge, die Löcher für die Schnecke mit einem Loch Kappsäge Sie Ihre Bohrer anbringen und die quadratischen Öffnungen für das Bedienfeld und Servo mit einer Stichsäge wieder.
    Ich wollte nicht die Mühe zu versuchen, ordentlich genug Löcher geschnitten, um die LCD-Halterung so istead I 3D gedruckte ein Haus entworfen facia (quadratische Löcher!) - Das ist der LCD, Taster (für manuelle Zufuhr) und dem Drehgeberknopf . Sie können dann schrauben Sie diese in die Holzkiste und es sieht nett und ordentlich!
    Das Essen Rührwerk wieder 3D gedruckt und Schrauben direkt an einen Servohorn. Der runde Tülle wird auch 3D gedruckt (Kredit wieder auf Thingiverse http://www.thingiverse.com/thing:28483 Kitlaan) Ich konnte das Schneckenrohr gemacht haben ragen die Vorderseite der Box mehr negiert die Notwendigkeit für den Auslauf, aber Ich wollte das obere Loch ein littel weiter zurück vom Rand so, wenn ich entscheiden, die aktuelle Lebensmittelbehälter mit einem größeren zu ersetzen, das Loch nicht direkt am Rand sein.
    Die Futterraufe Schrauben an der Box und ist leicht austauschbar / aktualisierbar.
    Die Zeit wird zeigen, ob meine Katzen lernen, die manuelle Zufuhr-Taste drücken!

Schritt 4: Arduino - Die Hardware

  1. Automatische Arduino Powered Pet Feeder

    Automatische Arduino Powered Pet Feeder

    Automatische Arduino Powered Pet Feeder

    Automatische Arduino Powered Pet Feeder

    Automatische Arduino Powered Pet Feeder

    Automatische Arduino Powered Pet Feeder

    Alle 7 Artikel anzeigen

    Das gesamte Projekt wird von einem Arduino angetrieben. Ich empfehle Ihnen einen Prototyp zu bauen mit einem regelmäßigen arduino und ein Steckbrett. Es ist der beste Weg, um zu verstehen, was alles tut und Fehler später zu speichern. Ich habe die Fritzing-Datei enthalten, damit Sie es laden und sehen Sie die Steckbrett-Layout im Detail (Kabel im Programm markiert, wo unbedingt erforderlich!). Fritzing Software ist kostenlos / donateware.
    Ich baute ein Steckbrett mit dem LCD auf, dann lernte die Grundlagen, wie sie zu kontrollieren. Dann habe ich einen Drehgeber und gelernt, wie man das verwenden, dann die beiden in Code kombiniert I. Schließlich fügte ich die Echtzeituhr, die Servos und begann die Programmierung der endgültige Code.
    Sie werden bemerken, ich sagte: "Servos". Der zweite Servo ist ein regelmäßiger Servo, verwendet werden, um das Tierfutter vor jeder Futter agitieren, zu stoppen, es Verklumpung (das Haustierfutter als kibbles auf die USofA bekannt Ich glaube :-))
    Nachdem ich mit dem Arduino UNO und Breadboard Test glücklich ich ersetzte den Arduino Uno mit reinen Komponenten - die ATMEGA328P Chip, ein paar Mützen, 5V-Regler (Stromversorgung) und einen Kristall - im Grunde - ein Arduino, ohne die Leiterplatte. Es ist einfach tot zu klopfen (google arduino Steckbrett) und ist eine gute Angewohnheit, in zu erhalten - sparen Sie ein Vermögen für Arduino UNO und bedeutet, dass Sie eine PCB, alles zu Haus-Design. Das Bild von den Montageplatten mit einem Rattennest von Verdrahtung ist die "reine Version".
    Diese Version getestet ok so habe ich dann zog die Schaltung in PCB-Assistenten (ein großes Paket, das Maplin verkauft für £ 40 ish) und konvertiert sie in eine PCB Zeichnung mit Hilfe der Auto-Routing feature.I've enthalten die Datei.
    Ich drucken und zu ätzen meine PCBs mit der Laser-Drucker-Verfahren. Ich habe eine Instructable auf sie gemacht - werfen Sie einen Blick unter meinem Namen - es funktioniert jedes Mal (die PCB, meinen Namen nicht). Ich habe die PDF-Dateien für den Druck befestigt.
    Schließlich habe ich alle Komponenten aufgelötet und hakte die LCD, Drehgeber und manuelle Vorschubtaste mit Flachbandkabel.
    Sie brauchen nicht so weit zu gehen - Sie können Ihre Feeder mit einem regelmäßigen Arduino und ein Steckbrett ausführen, oder Sie können diese Leiterplatte zu verwenden, wo Sie Links mit einem Messer geschnitten - die Wahl liegt bei Ihnen. Die Hardware ist Art von akademischen - es ist alles in den Code.

Schritt 5: Arduino - The Code

  1. Automatische Arduino Powered Pet Feeder

    Der Code ist nicht so einschüchternd, wie es zunächst aussieht, und ich habe versucht, es so weit wie möglich zu kommentieren.
    Zusammenfassend:
    Liest die Zeit aus dem RTC-Chip
    Zeigt die Zeit, und die Standardzulaufzeiten und Menge
    Überprüft, ob der Drehgeber gedrückt wurde, wenn es: es geht dann in den Programmierroutine, Radfahren, um durch Uhr, Portionsgröße, Zulaufzeit 1, Zulaufzeit 2. Wenn Sie fertig sind, geht es weiter unten ... .
    Überprüft, ob es eingezogen Zeit 1 oder 2 - wenn ja, sie ernährt.
    Überprüft, ob Sie die manuelle Zufuhr-Taste gedrückt haben, wenn es so Feeds. Und dann geht es wieder von vorn.
    Dies ist das erste Mal, dass ich einen Interrupt-Service-Routine verwendet - für den Drehgeber. Das bedeutet, wenn Sie ihn, was das Programm ist damit beschäftigt, die Aktion registriert sie. So ist es immer hören für den Encoder.
    Ich dachte, die Routine für die Einstellung der Uhr / Zulaufzeiten & Anzahl wäre entmutigend, aber ich brach es gerade nach unten in einfachen Schritten. 1. Ich habe gelernt, wie man den Cursor blinken auf dem Bildschirm, einfach genug zu machen. Dann positioniert ich den Cursor auf die Stundenanzeige der Uhr, und gesagt, dass es, um die Stunden zu erhöhen, wie der Geber eingeschaltet wurde (oder Abnahme), dann, wenn der Drehgeber gedrückt wurde, schreiben die neuen "Stunde", um die Echtzeit-Uhr, und dann bewegen Sie den Cursor auf die Minute, und starten Sie das Ändern, und so weiter. War überraschend einfach.
    Die Fütterung Routinen sind einfach "if" Routinen - also ", wenn" die Zeiten übereinstimmen, dann die Fütterung Routine. So einfach ist das. Ich musste ein wenig hinzufügen, damit es die Sekunden überprüft oder er-Feeds für eine ganze Minute, als die Programmschleifen und überprüft die Zeit noch einmal - und es ist noch Fütterungszeit! so dass es wiederholt ... Hinzufügen einer Überprüfung auf die Sekunden stoppt diese, da sie zumindest eine zweite für die Zuführung Zyklus dauert.
    Das Programm ist nicht perfekt - manchmal Drehen des Encoders nicht immer die Anzahl zu erhöhen auf dem Bildschirm. Ich denke, das ist bis zu meiner Unerfahrenheit. Es ist jedoch nicht den Betrieb der Maschine behindern!
    Ich habe einen Screen Grab meiner Arduino IDE für keinen wirklichen Grund anders als ich wollte nicht diesen Abschnitt, um ohne Bild ist inbegriffen :-)
    Offensichtlich ist das Video auf der 1. Seite zeigt mir Drücken des manuellen Einzugstaste, aber natürlich, es auto-Feeds an den beiden eingestellten Zeiten (man konnte beide Male die gleiche gesetzt und es wäre nur einmal füttern).
      / *
    
     Automatische Auger Audiono Futterautomat Urheberrecht Roger Donoghue 28/03/2015 alle Rechte vorbehalten.  Für den persönlichen Gebrauch.
     Nicht zur kommerziellen Verwendung oder Weiterverkauf.
     Ermöglicht es Ihnen, 2 Fütterungszeiten und die Quantität als Vielfaches der Standard-Fördermenge einstellen.
     Verwendet ein DS1307 Echtzeituhr, um die Zeit zu halten, mit einer wiederaufladbaren Batterie eingebaut.
     (Sie können die Arduino RTC Beispiel-Code in der IDE verwenden, um die Uhr zu stellen, oder verwenden Sie den Drehgeber, wie beabsichtigt)
    
     * /
     // Gehören die Bibliothekscode:
     #include <LiquidCrystal.h>
     #include <Wire.h> // für den RTC libraty erforderlich
     #include <Time.h>
     #include <DS1307RTC.h> // Real Time Clock-Bibliothek
     #include <Servo.h>
    
     // Initialisierung der Bibliothek mit den Nummern der Anschlußstifte dor LCD
     Liquid LCD (12, 11, 5, 8, 7, 6);
    
     #define PIN_SERVO 9
    
     Servo feedServo;
     Servo stirServo;
     int pos = 0;
     volatile boolean TurnDetected;
     volatile boolean up;
     const int PinCLK = 2;  // Wird für die Erzeugung von Interrupts mit CLK-Signal
     const int Pindt = 3;  // Wird für das Lesen DT-Signal
     const int PinSW = 4;  // Wird für die Druckknopfschalter des Drehgebers
     const int buttonPin = A3;  // Die Anzahl der Drucktaste Pin für manuelle Zufuhr 13
     int Buttonstate = 0;  // Variable zum Lesen des manuellen Papierdrucktaste Status
     int feed1hour = 07;  // Variablen für Fütterungszeiten und Menge
     int feed1minute = 00;
     int feed2hour = 17;
     int feed2minute = 30;
     int feedQty = 4;
     int Vorschub = 800;  // Ein PWM-Rate die Auslöser nach vorne auf der Servo 75
     int feedReversal = 80;  // Ein PWM-Rate, die Trigger rückgängig am Servo
                            // Spielen mit diesen Zahlen für die Servo.  Mir ist ein Futaba Digital Servo
                            // Dass ich entfernt den Topf aus und die Kunststofflasche, es kontinuierlich zu machen.
    
     Leere isr () {// Interrupt-Service-Routine wird ausgeführt, wenn ein HIGH nach LOW Übergang auf CLK erkannt
      if (digitalRead (PinCLK)) // dies hält ein Auge für den Drehgeber ist unabhängig davon, wo das Programm eingeschaltet
        up = digitalRead (Pindt);  // Zeit exectuting - in anderen Worten, während der Hauptschleife dieses ISR wird immer aktiv
      sonst
        up = digitalRead (Pindt!);
      TurnDetected = true;
     }
    
    
     Leere setup () {
        // Bis die LCD-Reihe von Spalten und Zeilen ein: 
       lcd.begin (16, 2);
       // Setup den Drehschalter,
      pinMode (PinCLK, INPUT);
      pinMode (Pindt, INPUT);  
      pinMode (PinSW, INPUT);
      pinMode (buttonPin, INPUT);
      attachInterrupt (0, isr, Fallen);  // Interrupt 0 wird immer auf Arduino UNO Pin 2 verbunden
         lcd.setCursor (17,0);            
         lcd.print ("Roger Donoghue ist");  // Ein bisschen Spaß :-)
         lcd.setCursor (17,1);
         lcd.print ("Cat-O-Matic");
          for (int positionCounter = 0; positionCounter <17; positionCounter ++) {
          // Bildlauf um eine Position nach links:
          lcd.scrollDisplayLeft (); 
          // Warten Sie ein wenig:
          Verzögerung (150);
               }
           Verzögerung (3000);
           for (int positionCounter = 0; positionCounter <17; positionCounter ++) {
          // Bildlauf um eine Position nach links:
          lcd.scrollDisplayRight (); 
          // Warten Sie ein wenig:
          Verzögerung (150);
         
                  } // End of fun
          lcd.setCursor (17,0);
          lcd.print ("");
          lcd.setCursor (17,1);
          lcd.print ("");  
             }
      
     Leere Schleife () {// Hauptprogrammschleife - die meisten Dinge in here!
         statische lang virtualPosition = 0;  // Ohne STATIC es nicht richtig zählen !!!
         tmElements_t tm;  // Diese sectionm liest die Zeit aus der RTC, setzt es in tmElements tm (schön, mit zu arbeiten), zeigt es dann.
         RTC.read (tm); 
         lcd.setCursor (0, 0);
         printDigits (tm.Hour);  // Aufruf zu stellige Funktion drucken, die führenden Nullen, die fehlen können addiert
         lcd.print (":");
         printDigits (tm.Minute);
         lcd.print (":");
         printDigits (tm.Second);
         lcd.print ("");
         lcd.print ("Anzahl");
         lcd.print (feedQty);
         lcd.print ("");
         lcd.setCursor (0,1);
         lcd.print ("1)");
         printDigits (feed1hour);
         lcd.print (":");
         printDigits (feed1minute);
         lcd.print ("2)");
         printDigits (feed2hour);
         lcd.print (":");
         printDigits (feed2minute);
        
        
     // MAIN BREAKOUT "IF" secion unter dem der Druckknopf MONITORE und tritt PROGRAMMIER wenn es PUSHED 
    
      if (! (digitalRead (PinSW))) {// überprüfen, ob Taste gedrückt
                                        // Wenn JA geben Sie dann die Programmierunterprogramm
         lcd.blink ();  // Auf den blinkenden Cursor drehen:
         lcd.setCursor (5,0);
         lcd.print ("SET");
         virtualPosition = tm.Hour;  // Benötigt oder die Stunde Null jedesmal, wenn Sie die Uhr zu ändern.
            machen {
                 lcd.setCursor (0,0);  // Cursor auf Uhrzeit Stunde setzen  
                 Verzögerung (500);  // Verzögerung benötigt oder dieselbe Taste drücken wird beendet do-while als während prüft für eine andere Tastendruck!
                 if (TurnDetected) {// tun dies nur, wenn eine Drehung festgestellt wurde
                 if (up)
                   virtualPosition--;
                 sonst
                 virtualPosition ++;
                 TurnDetected = false;  // Nicht wiederholen IF Schleife, bis neue Rotation erkannt
                                    }
                 // Hier ich die Stunde Zeit -
                 tm.Hour = virtualPosition;
                 RTC.write (tm);
                 lcd.setCursor (0, 0);
                 printDigits (tm.Hour);  // Dann erneut zu drucken die Stunde auf dem LCD-
              } While ((digitalRead (PinSW)));  // Tun dies, "do" loop während die PinSW Taste nicht gedrückt wird
              lcd.noBlink ();
              Verzögerung (1000);
           
            // DIE SET MINS
            
             lcd.blink ();  // Auf den blinkenden Cursor drehen:
            virtualPosition = tm.Minute;  // Benötigt oder die Minute Null jedesmal, wenn Sie die Uhr zu ändern.
            machen {
            lcd.setCursor (3,0);  // Cursor auf Zeit Mins setzen
            Verzögerung (500);  // Verzögerung benötigt oder dieselbe Taste drücken wird beendet do-while als während prüft für eine andere Tastendruck!
                if (TurnDetected) {// tun dies nur, wenn eine Drehung festgestellt wurde
                 if (up)
                   virtualPosition--;
                 sonst
                 virtualPosition ++;
                 TurnDetected = false;  // Nicht wiederholen IF Schleife, bis neue Rotation erkannt
                                    }
                 // Hier ich die min der Zeit -
                 tm.Minute = virtualPosition;
                 RTC.write (tm);
                 lcd.setCursor (3, 0);
                 printDigits (tm.Minute);  // Dann erneut drucken min auf dem LCD-
              } While ((digitalRead (PinSW)));
              lcd.noBlink ();
              Verzögerung (1000);
        
            // Das QTY - Aufgabemenge
            
            lcd.blink ();  // Auf den blinkenden Cursor drehen:
            virtualPosition = feedQty;  // Benötigt wird oder die Menge Null.
            machen {
            lcd.setCursor (14,0);  // Cursor an QTY setzen
            Verzögerung (500);  // Verzögerung benötigt oder dieselbe Taste drücken wird beendet do-while als während prüft für eine andere Tastendruck!
                if (TurnDetected) {// tun dies nur, wenn eine Drehung festgestellt wurde
                 if (up)
                   virtualPosition--;
                 sonst
                 virtualPosition ++;
                 TurnDetected = false;  // Nicht wiederholen IF Schleife, bis neue Rotation erkannt
                                    }
                 // Hier habe ich den Feed Menge ändern
                 feedQty = virtualPosition;
                 lcd.setCursor (14, 0);
                 lcd.print (feedQty);
                } While ((digitalRead (PinSW)));
              lcd.noBlink ();
              Verzögerung (1000);
             
          // Den Feed1 Hour
            
            lcd.blink ();  // Auf den blinkenden Cursor drehen:
            virtualPosition = feed1hour;  // Benötigt wird oder null, um zu starten.
            machen {
            lcd.setCursor (2,1);  // Cursor an feed1hour setzen
            Verzögerung (500);  // Verzögerung benötigt oder dieselbe Taste drücken wird beendet do-while als während prüft für eine andere Tastendruck!
                if (TurnDetected) {// tun dies nur, wenn eine Drehung festgestellt wurde
                 if (up)
                   virtualPosition--;
                 sonst
                 virtualPosition ++;
                 TurnDetected = false;  // Nicht wiederholen IF Schleife, bis neue Rotation erkannt
                                    }
                 // Hier habe ich die feed1 Stunden ändern
                 feed1hour = virtualPosition;
                 lcd.setCursor (2,1);
                 printDigits (feed1hour);
                } While ((digitalRead (PinSW)));
              lcd.noBlink ();
              Verzögerung (1000);  
      
           // Den Feed1 Mins
            
            lcd.blink ();  // Auf den blinkenden Cursor drehen:
            virtualPosition = feed1minute;  // Benötigt wird oder null, um zu starten.
            machen {
            lcd.setCursor (5,1);  // Cursor an feed1minute setzen
            Verzögerung (500);  // Verzögerung benötigt oder dieselbe Taste drücken wird beendet do-while als während prüft für eine andere Tastendruck!
                if (TurnDetected) {// tun dies nur, wenn eine Drehung festgestellt wurde
                 if (up)
                   virtualPosition--;
                 sonst
                 virtualPosition ++;
                 TurnDetected = false;  // Nicht wiederholen IF Schleife, bis neue Rotation erkannt
                                    }
                 // Hier ich die feed1 Minute
                 feed1minute = virtualPosition;
                 lcd.setCursor (5,1);
                 printDigits (feed1minute);
                } While ((digitalRead (PinSW)));
              lcd.noBlink ();
              Verzögerung (1000);   
    
        // Den FEED2 Hour
            
            lcd.blink ();  // Auf den blinkenden Cursor drehen:
            virtualPosition = feed2hour;  // Benötigt wird oder null, um zu starten.
            machen {
            lcd.setCursor (10,1);  // Cursor an feed1hour setzen
            Verzögerung (500);  // Verzögerung benötigt oder dieselbe Taste drücken wird beendet do-while als während prüft für eine andere Tastendruck!
                if (TurnDetected) {// tun dies nur, wenn eine Drehung festgestellt wurde
                 if (up)
                   virtualPosition--;
                 sonst
                 virtualPosition ++;
                 TurnDetected = false;  // Nicht wiederholen IF Schleife, bis neue Rotation erkannt
                                    }
                 // Hier habe ich die feed1 Stunden ändern
                 feed2hour = virtualPosition;
                 lcd.setCursor (10,1);
                 printDigits (feed2hour);
                } While ((digitalRead (PinSW)));
              lcd.noBlink ();
              Verzögerung (1000);  
      
           // Den FEED2 Mins
            
            lcd.blink ();  // Auf den blinkenden Cursor drehen:
            virtualPosition = feed2minute;  // Benötigt wird oder null, um zu starten.
            machen {
            lcd.setCursor (13,1);  // Cursor an feed1minute setzen
            Verzögerung (500);  // Verzögerung benötigt oder dieselbe Taste drücken wird beendet do-while als während prüft für eine andere Tastendruck!
                if (TurnDetected) {// tun dies nur, wenn eine Drehung festgestellt wurde
                 if (up)
                   virtualPosition--;
                 sonst
                 virtualPosition ++;
                 TurnDetected = false;  // Nicht wiederholen IF Schleife, bis neue Rotation erkannt
                                    }
                 // Hier ich die feed1 Minute
                 feed2minute = virtualPosition;
                 lcd.setCursor (13,1);
                 printDigits (feed2minute);
                } While ((digitalRead (PinSW)));
              lcd.noBlink ();
              Verzögerung (1000);                         
          
       } // Ende der Haupt IF Drehgeber Taster checker
     
        // Check für Handvorschub BUTTON
       Button = digitalRead (buttonPin);
       if (Button == HIGH) {
         Futtermittel ();
       }
       // Check FEEDING TIME AND FEED IF MATCHED
      
       if (tm.Hour == feed1hour && tm.Minute == feed1minute && tm.Second == 0) {// wenn ich nicht 'überprüfen Sekunden Null
         Futtermittel ();  // Dann wird es kontinuierlich für 1 Minute zu füttern!
           }
       if (tm.Hour == feed2hour && tm.Minute == feed2minute && tm.Second == 0) {
         Futtermittel ();
           }  
      
     } // Ende der Hauptschleife
    
     Leere printDigits (int digits) {// Nutzenfunktion für digitale Zeitanzeige: prints führende 0
        if (Ziffern <10)
         lcd.print ('0');
        lcd.print (Ziffern);
      }
     
      Leere Feed () {
       
        lcd.setCursor (17,0);
        lcd.print ("Meowwwww!");
         for (int positionCounter = 0; positionCounter <16; positionCounter ++) {
          // Bildlauf um eine Position nach links:
          lcd.scrollDisplayLeft (); 
          // Warten Sie ein wenig:
          Verzögerung (150);
              }
      
        // Stir Servoabschnitt Wenn Sie nicht brauchen, für Aufsehen Servo einfach kommentieren Sie alle fo dies, bis der Bohrer drehen Abschnitt  
        stirServo.attach (10);  // Ich weiß nicht, ob ich eine solche entweder, aber ich bin jetzt das Hinzufügen es, wie es am einfachsten ist, bevor ich sie zu bauen!
         für (pos = 0; pos <= 180; pos + = 1) {                                  
         stirServo.write (POS);              
         Verzögerung (5);  } 
        für (pos = 180; pos> = 0; mög- = 1) {                                
         stirServo.write (POS);          
         Verzögerung (10);  } 
         Verzögerung (200);
        für (pos = 0; pos <= 180; pos + = 1) {                                  
         stirServo.write (POS);              
         Verzögerung (10);  } 
        für (pos = 180; pos> = 0; mög- = 1) {                                
         stirServo.write (POS);          
         Verzögerung (5);  }  
        stirServo.detach ();  
       
        // Drehen Sie das Auger   
        feedServo.attach (PIN_SERVO);
         for (int cnt = 0; cnt <feedQty cnt ++)
         {
           feedServo.write (Vorschub);  // Die Vorschubgeschwindigkeit ist wirklich der Vorschubrichtung und Geschwindigkeit.
           Verzögerung (600);  // Diese Verzögerung setzt, wie lange der Servo bleibt vom vorherigen Befehl läuft
           feedServo.write (feedReversal);  //...until Dieser Befehl setzt die Servo eine neue Aufgabe!
           Verzögerung (200);
           feedServo.write (Vorschub);  
           Verzögerung (600);   
           feedServo.write (feedReversal);  //, Wenn Sie die Gesamtvorschubgeschwindigkeit zu erhöhen, die zukunfts Verzögerungen (1000 im Moment) wollen
           Verzögerung (200);  // Oder noch besser einfach kopieren und an der nach vorn & hinten Code unterhalb wiederholen
               } // Diese Weise das kleine umgekehrte wackeln ist immer da, um Papierstaus zu vermeiden
          feedServo.detach ();
          for (int positionCounter = 0; positionCounter <16; positionCounter ++) {
          // Bildlauf um eine Position nach links:
          lcd.scrollDisplayRight (); 
          // Warten Sie ein wenig:
          Verzögerung (150);
              }
                  }