Cuprins:
- Provizii
- Pasul 1: Părți imprimate 3D
- Pasul 2: Atașați capacul la servomotor
- Pasul 3: Construiți circuitul NodeMCU ESP8266
- Pasul 4: Încărcați codul Arduino și testați
- Pasul 5: Folosește-l
Video: Control acces acces la hrană pentru pisici (ESP8266 + servomotor + imprimare 3D): 5 pași (cu imagini)
2024 Autor: John Day | [email protected]. Modificat ultima dată: 2024-01-30 11:41
Acest proiect trece peste procesul pe care l-am folosit pentru a crea un bol automat de hrană pentru pisici, pentru pisica mea în vârstă, diabetică Chaz. Vezi, trebuie să mănânce micul dejun înainte de a-și putea lua insulina, dar uit de multe ori să-i iau mâncarea înainte de culcare, ceea ce îi strică pofta de mâncare și îi aruncă programul de insulină. Acest vas folosește un servomotor pentru a închide un capac peste mâncare între orele de miezul nopții și 7:30. Schița Arduino a microcontrolerului NodeMCU ESP8266 folosește Network Time Protocol (NTP) pentru a controla programul.
Este posibil ca acest proiect să nu fie potrivit pentru pisicile mai tinere și mai active. Chaz este atât de bătrân și fragil încât nu este înclinat să încerce să deschidă castronul, dar este posibil.
Dacă sunteți nou în Arduino sau ESP8266, vă puteți bucura de următoarele ghiduri preliminare:
- Instructables Clasa Arduino
- Clasa de instrumente Internet de obiecte
Provizii
- Imprimantă 3D (folosesc un Creality CR-10s Pro)
- Filament pentru imprimantă 3D (folosesc aur PLA)
- Microcontroler wifi NodeMCU ESP8266
- Cablu USB (de la A la microB)
- Adaptor de alimentare USB
- Micro servomotor
- Șurubelniță mică și șuruburi
- Sârmă de conectare
- Pinii antetului
- Placă Perma-proto
Pentru a ține pasul cu ceea ce lucrez, urmează-mă pe YouTube, Instagram, Twitter, Pinterest și abonează-te la newsletter-ul meu. În calitate de asociat Amazon câștig din achizițiile eligibile pe care le faceți folosind linkurile mele de afiliere.
Pasul 1: Părți imprimate 3D
Suportul pentru bol pentru hrană pentru pisici se bazează pe designul lui Ardy Lai de pe Thingiverse. Am făcut-o mai mare pentru a găzdui bolul pisicii mele și, de asemenea, am redus-o mai scurt, deoarece ridicarea ei a făcut-o prea înaltă. Am adăugat un suport pentru un micro servomotor și câteva găuri pentru ca cablurile să fie trase spre interior.
Am modelat un capac simplu folosind Tinkercad, conceput pentru a fi atașat la claxonul micro servo. Puteți să luați designul meu direct de la Tinkercad și / sau să descărcați STL-urile atașate acestui pas.
Am imprimat piesele de pe imprimanta mea Creality CR-10s Pro cu filament PLA auriu.
Dezvăluire: în momentul redactării acestui articol, sunt angajat al Autodesk, care face Tinkercad.
Pasul 2: Atașați capacul la servomotor
Am folosit un burghiu mic pentru a crește dimensiunea găurilor de pe claxonul servo, apoi am folosit șuruburi pentru a atașa servo-ul la capacul imprimat 3D.
Pasul 3: Construiți circuitul NodeMCU ESP8266
Circuitul este controlat de un microcontroler wifi NodeMCU ESP8266. Am folosit pini de antet pe o placă perma-proto pentru a face micro servo motorul ușor detașabil. Anteturile servo sunt conectate la NodeMCU după cum urmează:
Sârmă servo galbenă: NodeMCU D1
Sârmă servo roșie: putere NodeMCU (3V3 sau VIN)
Sârmă servo negru: masă NodeMCU (GND)
Pasul 4: Încărcați codul Arduino și testați
Instalați ansamblul motor / capac în decupajul în formă de motor de pe partea imprimată 3D a suportului bolului. Conectați antetul motorului la pinii antetului plăcii microcontrolerului și conectați circuitul la computer cu un cablu USB.
Schița Arduino folosește Network Time Protocol pentru a prelua ora curentă și apoi deschide sau închide capacul conform unui program hard-coded. Copiați următorul cod, actualizați datele de conectare wifi și decalajul orar UTC și încărcați-l pe placa dvs. NodeMCU folosind ID-ul Arduino.
#include
#include #include #include ESP8266WiFiMulti wifiMulti; // Creați o instanță a clasei ESP8266WiFiMulti, numită „wifiMulti” WiFiUDP UDP; // Creați o instanță a clasei WiFiUDP pentru a trimite și primi IPAddress timeServerIP; // time.nist.gov adresa serverului NTP const char * NTPServerName = "time.nist.gov"; const int NTP_PACKET_SIZE = 48; // Timpul NTP este în primii 48 de octeți ai octetului mesajului NTPBuffer [NTP_PACKET_SIZE]; // tampon pentru a păstra pachetele de intrare și de ieșire Servo myservo; // creați un obiect servo pentru a controla un servo // douăsprezece obiecte servo pot fi create pe majoritatea plăcilor int pos = 0; // variabilă pentru a stoca configurarea nulă a poziției servo () {myservo.attach (5); // atașează servo pe pinul 5 aka D1 la obiectul servo // deschideți capacul în mod implicit Serial.println („deschiderea capacului”); for (pos = 95; pos> = 0; pos - = 1) {// merge de la 95 grade la 0 grade myservo.write (pos); // spuneți servo-ului să meargă în poziție în variabila „pos” întârziere (15); // așteaptă 15ms pentru ca servo să ajungă la poziția} Serial.begin (115200); // Porniți comunicarea Serial pentru a trimite mesaje către întârzierea computerului (10); Serial.println ("\ r / n"); startWiFi (); // Încercați să vă conectați la unele puncte de acces date. Apoi, așteptați o conexiune startUDP (); if (! WiFi.hostByName (NTPServerName, timeServerIP)) {// Obțineți adresa IP a serverului NTP Serial.println ("Căutarea DNS a eșuat. Repornirea."); Serial.flush (); ESP.reset (); } Serial.print ("IP server de timp: / t"); Serial.println (timeServerIP); Serial.println ("\ r / nTrimiterea cererii NTP …"); sendNTPpacket (timeServerIP); } interval lung nesemnat NTP = 60000; // Solicitați timp NTP în fiecare minut nesemnat lung prevNTP = 0; unsigned long lastNTPResponse = millis (); uint32_t timeUNIX = 0; nesemnat lung prevActualTime = 0; bucla void () {unsigned long currentMillis = millis (); if (currentMillis - prevNTP> intervalNTP) {// Dacă a trecut un minut de la ultima solicitare NTP prevNTP = currentMillis; Serial.println ("\ r / nTrimiterea cererii NTP …"); sendNTPpacket (timeServerIP); // Trimiteți o cerere NTP} uint32_t time = getTime (); // Verificați dacă a sosit un răspuns NTP și obțineți ora (UNIX) dacă (ora) {// Dacă s-a primit o nouă marcă de timp ora UNIX = ora; Serial.print ("Răspuns NTP: / t"); Serial.println (timeUNIX); lastNTPResponse = currentMillis; } else if ((currentMillis - lastNTPResponse)> 3600000) {Serial.println ("Mai mult de 1 oră de la ultimul răspuns NTP. Repornire."); Serial.flush (); ESP.reset (); } uint32_t actualTime = timeUNIX + (currentMillis - lastNTPResponse) / 1000; uint32_t EasternTime = timeUNIX - 18000 + (currentMillis - lastNTPResponse) / 1000; if (actualTime! = prevActualTime && timeUNIX! = 0) {// Dacă a trecut o secundă de la ultima imprimare prevActualTime = actualTime; Serial.printf ("\ rUTC time: / t% d:% d:% d", getHours (actualTime), getMinutes (actualTime), getSeconds (actualTime)); Serial.printf ("\ rEST (-5): / t% d:% d:% d", getHours (EasternTime), getMinutes (EasternTime), getSeconds (EasternTime)); Serial.println (); } // 7:30 am if (getHours (EasternTime) == 7 && getMinutes (EasternTime) == 30 && getSeconds (EasternTime) == 0) {// deschideți capacul Serial.println („deschiderea capacului”); for (pos = 95; pos> = 0; pos - = 1) {// merge de la 95 grade la 0 grade myservo.write (pos); // spuneți servo-ului să meargă în poziție în variabila „pos” întârziere (15); // așteaptă 15 ms pentru ca servo-ul să ajungă la poziție}} // miezul nopții if (getHours (EasternTime) == 0 && getMinutes (EasternTime) == 0 && getSeconds (EasternTime) == 0) {// închideți capacul Serial. println („închiderea capacului”); for (pos = 0; pos <= 95; pos + = 1) {// merge de la 0 grade la 95 grade // în pași de 1 grad myservo.write (pos); // spuneți servo-ului să meargă în poziție în variabila „pos” întârziere (15); // așteaptă 15 ms pentru ca servo-ul să ajungă la poziția}} / * // testând dacă (getHours (EasternTime) == 12 && getMinutes (EasternTime) == 45 && getSeconds (EasternTime) == 0) {// închideți capacul Serial.println („închiderea capacului”); for (pos = 0; pos = 0; pos - = 1) {// merge de la 95 grade la 0 grade myservo.write (pos); // spuneți servo-ului să meargă în poziție în variabila „pos” întârziere (15); // așteaptă 15 ms pentru ca servo-ul să atingă poziția}} * /} void startWiFi () {// Încercați să vă conectați la unele puncte de acces date. Așteptați apoi o conexiune wifiMulti.addAP ("ssid_from_AP_1", "your_password_for_AP_1"); // adăugați rețele Wi-Fi la care doriți să vă conectați la //wifiMulti.addAP("ssid_from_AP_2 "," your_password_for_AP_2 "); //wifiMulti.addAP("ssid_from_AP_3 "," your_password_for_AP_3 "); Serial.println („Conectarea”); while (wifiMulti.run ()! = WL_CONNECTED) {// Așteptați ca Wi-Fi să se conecteze la întârziere (250); Serial.print ('.'); } Serial.println ("\ r / n"); Serial.print („Conectat la”); Serial.println (WiFi. SSID ()); // Spuneți-ne la ce rețea suntem conectați la Serial.print („Adresă IP: / t”); Serial.print (WiFi.localIP ()); // Trimiteți adresa IP a ESP8266 pe computerul Serial.println ("\ r / n"); } void startUDP () {Serial.println ("Pornirea UDP"); UDP.begin (123); // Începeți să ascultați mesajele UDP pe portul 123 Serial.print ("Port local: / t"); Serial.println (UDP.localPort ()); Serial.println (); } uint32_t getTime () {if (UDP.parsePacket () == 0) {// Dacă nu există niciun răspuns (încă) returnează 0; } UDP.read (NTPBuffer, NTP_PACKET_SIZE); // citiți pachetul în buffer // Combinați cei 4 octeți de timestamp într-un număr de 32 de biți uint32_t NTPTime = (NTPBuffer [40] << 24) | (NTPBuffer [41] << 16) | (NTPBuffer [42] << 8) | NTPBuffer [43]; // Conversia timpului NTP într-un timestamp UNIX: // Unix time începe pe 1 ianuarie 1970. Aceasta este 2208988800 secunde în timpul NTP: const uint32_t sevenyYears = 2208988800UL; // scade șaptezeci de ani: uint32_t UNIXTime = NTPTime - șaptezeci de ani; returnează UNIXTime; } void sendNTPpacket (IPAddress & address) {memset (NTPBuffer, 0, NTP_PACKET_SIZE); // setați toți octeții din buffer la 0 // Inițializați valorile necesare pentru a forma cererea NTP NTPBuffer [0] = 0b11100011; // LI, Versiune, Mod // trimite un pachet solicitând un timestamp: UDP.beginPacket (adresa, 123); // Solicitările NTP sunt către portul 123 UDP.write (NTPBuffer, NTP_PACKET_SIZE); UDP.endPacket (); } inline int getSeconds (uint32_t UNIXTime) {return UNIXTime% 60; } inline int getMinutes (uint32_t UNIXTime) {return UNIXTime / 60% 60; } inline int getHours (uint32_t UNIXTime) {return UNIXTime / 3600% 24; }
Pasul 5: Folosește-l
Treceți firele către interiorul suportului bolului și conectați alimentatorul pentru pisici la o priză utilizând un adaptor USB AC. Modul în care este scris codul simplu, este menit să fie pornit în starea „deschis” și își va schimba poziția capacului doar la pragurile de timp specificate în schița Arduino.
Vă mulțumim că ați urmat! Dacă îți faci propria versiune, mi-ar plăcea să o văd în secțiunea I Made It de mai jos!
Dacă îți place acest proiect, s-ar putea să te intereseze unii dintre ceilalți ai mei:
- Suport prismă pentru portrete Rainbow
- Perete de depozitare din placaj cu Cat Tower
- Lanterne LED Mason Jar (capac imprimat 3D)
- Imprimantă 3D Filament Cutie uscată
- Sursă de alimentare USB de urgență (tipărit 3D)
- Bomboane Gummy LED strălucitoare
- Mașină de plantat geometrică tipărită 3D cu drenaj
- Flori imprimate 3D strălucitoare
- Cum se instalează LED-uri sub un scuter (cu Bluetooth)
Pentru a ține pasul cu ceea ce lucrez, urmează-mă pe YouTube, Instagram, Twitter și Pinterest.
Recomandat:
Sourino - Cea mai bună jucărie pentru pisici și copii: 14 pași (cu imagini)
Sourino - Cea mai bună jucărie pentru pisici și copii: imaginați-vă petreceri lungi cu copii și pisici jucând Sourino. Această jucărie va uimi atât pisicile, cât și copiii. Vă veți bucura să jucați în modul controlat de la distanță și să vă înnebuniți pisica. În modul autonom, veți aprecia să lăsați Sourino să se miște în jurul pisicii dvs.
Repelent pentru pisici: 4 pași (cu imagini)
Cat Repellent: Pentru început, nu urăsc pisicile, dar iubesc păsările. În grădina mea avem niște cuști deschise unde păsările pot intra și ieși după bunul plac. Ei pot găsi mâncare și apă acolo. Din păcate, uneori o pisică din cartier intră în grădina mea și eu
Dispenser automat pentru hrana pentru pisici: 7 pași (cu imagini)
Dispenser automat pentru hrana pentru pisici: dacă nu controlați cantitatea de mâncare pe care o mănâncă pisica, acest lucru poate duce la supraalimentare și la probleme cu supraponderalitatea. Acest lucru este valabil mai ales dacă sunteți departe de casă și lăsați hrană suplimentară pentru ca pisica dvs. să o consume în propriul program. Alteori poți să
Alarmă pentru hrana pentru câini: 5 pași
Alarmă pentru hrana pentru câini: Bună ziua din nou! În gospodăria mea, responsabilitățile de a ne hrăni câinele, un doodle de aur numit Taos (după noul oraș mexican), ne revin adesea copiilor. Cu toate acestea, când vine timpul să-l hrănești, este greu de spus dacă a fost hrănit anterior sau
Dispozitiv de acoperire a bolului pentru hrană pentru pisici: 4 pași
Dispozitiv de acoperire a bolului pentru hrană pentru pisici: Acest material instructiv a fost creat pentru a îndeplini cerințele proiectului Makecourse de la Universitatea din Florida de Sud (www.makecourse.com). Acest dispozitiv era