kemosabe Inserito: 11 febbraio 2020 Segnala Inserito: 11 febbraio 2020 Signori, buongiorno. Come da vostro consiglio, sto cercando di imparare il C con il libro da voi consigliato, e nel frattempo cercando di fare esercizi con il c, che so che non è solo c, di Arduino. Sto cercando di modificare un programma carino, che ho trovato in rete, per l'apertura di una porta con codice numerico e con RFID. Per il momento, visto che le mie modifiche non funzionano, sto cercando di capire la parte vecchia del programma. Solo che anche studiando sul libro, non riesco a capire come si comporta il " return" nelle varie situazioni in cui viene messo dopo una funzione. 1: non capisco quando dopo una funzione esempio if cosa succede se c'è un return senza valori. 2: in alcuni casi trovo il return con con () parentesi tonde senza nessun valore 3: return (1) oppure return(0) in pratica vorrei capire che cosa fa il return. Per esempio come si comporta all'interno di uno switch case messo prima del break. Vi chiedo se avete voglia di chiarirmi un po questo return......grazie!
Livio Orsini Inserita: 11 febbraio 2020 Segnala Inserita: 11 febbraio 2020 L'istruzione return, ritorna uno o più valori, secondo quanto dichiarato nella funzione. Se la funzione è dichiarata void non ritorna alcun valore. 1 ora fa, kemosabe ha scritto: return (1) oppure return(0) In questo caso avrai una variabile dichiarata boolean e la funzione ritorna vero (1) o falso(0). Comunque metti i codici di funzioni correispondeti a 3 casi, così ragionaimo su qualche cosa di reale.
kemosabe Inserita: 11 febbraio 2020 Autore Segnala Inserita: 11 febbraio 2020 mfrc522.PCD_Init(); if ( mfrc522.PICC_IsNewCardPresent() && mfrc522.PICC_ReadCardSerial() ) { citireNFC(); if(validareNFC()) { stare=1; id_valido(); return; } else { id_error(); // 399 return; break; } } char c=myKeypad.getKey(); if(c != NO_KEY) { String codcurent=iaCOD(c); int A=comparareCOD(codcurent); if(A==0) { id_error(); // 401 return; } if(A==1) { id_valido(); // 360 stare = 1; return; } if(A==2); { stare = 2; lcd.clear(); lcd.setCursor(0,0); lcd.print("Pairing..."); Serial.println("Pairing..."); delay(2000); return; } } break; } Ciao,come in questi casi, per esempio, vorrei capire cosa e dove ritorna il return. Come vedi in alcuni casi c'è solo il return in altri c'è il return e il break...... grazie
del_user_97632 Inserita: 11 febbraio 2020 Segnala Inserita: 11 febbraio 2020 (modificato) 5 ore fa, kemosabe ha scritto: 1: non capisco quando dopo una funzione esempio if cosa succede se c'è un return senza valori. 2: in alcuni casi trovo il return con con () parentesi tonde senza nessun valore 3: return (1) oppure return(0) in pratica vorrei capire che cosa fa il return. Per esempio come si comporta all'interno di uno switch case messo prima del break. Livio ti ha gia dato alcune spiegaizoni, ma forse aggiungo due parole 1. return senza valori si usa per uscire da una funzione void funzione() prima della fine dello scope. 2. return non e' una funzione, quindi return() e' un errore. main.c:5:10: error: expected expression before ‘)’ token 5 | return (); 3. le parentesi su return (1); etc non servono, e molti correttori di sintassi segnalano di rimuoverle, ma e' lecito lasciarle. Poi, molte funzioni int funzione() { ... } ritornano tipicamente 0 se non ci sono errori o un valore diverso da zero in caso di errore. Si usa generalmente int, perche' in molti casi gli errori sono negativi, ma sono convenzioni. Modificato: 11 febbraio 2020 da _angelo_
del_user_97632 Inserita: 11 febbraio 2020 Segnala Inserita: 11 febbraio 2020 (modificato) del tuo codice sopra, manca la dichiarazione delal funzuone, che sara' immagino void funzione() le funzioni hanno uno spazio di vita detto "scope", tra le due graffe. void funzione() { } il return esce dallo scope, termina la funziojne, e ritorni li dove la funzione era stata chiamata Nota: il tuo codice e' forse incasinato con tabulazioni e graffe, dunque devi aver perso il filo per quello. Riordinalo. Modificato: 11 febbraio 2020 da _angelo_
kemosabe Inserita: 12 febbraio 2020 Autore Segnala Inserita: 12 febbraio 2020 il pezzo di codice che vi ho allegato prima, in effetti è inserito in uno switch case. ancora non capisco per esempio, quando è scritto senza variabile, ritorna al chiamante uno 0 o un 1 in caso di errore. prendiamo questo pezzo e vediamo di capirci qualcosa. char c=myKeypad.getKey(); if(c != NO_KEY) { String codcurent=iaCOD(c); int A=comparareCOD(codcurent); if(A==0) { id_error(); // 401 return; quale tipo di errore puo succedere in questo pezzo. int comparareCOD(String a) { if(a.equals(codacces)) return 1; else if(a.equals(codpairing)) return 2; else return 0; } vi allego anche questo come esempio. mi fate capire quale errore puo essere scatenato, e i vari return 1, 2 , 0, cosa restituiscono, a chi, e per quale scopo grazie
Livio Orsini Inserita: 12 febbraio 2020 Segnala Inserita: 12 febbraio 2020 int comparareCOD(String a) { int iret; if(a.equals(codacces)) iret = 1; else if(a.equals(codpairing)) iret = 2; else iret = 0; return (iret); } Per far ritornare un valore devi scriverla così
del_user_97632 Inserita: 12 febbraio 2020 Segnala Inserita: 12 febbraio 2020 beh intanto il codice qui sopra sembra compilato C++, lo si deduce da oggetti-porcheria "String" di VisualC se non ricordo male, comunque per il resto e' codice C 2 ore fa, kemosabe ha scritto: quale tipo di errore puo succedere in questo pezzo. a naso: e' stato premuto un tasto, o meglio un codice di alcuni tasti, se poi il codice non coincide compareCOD restituisce 0 (errore in questo caso).
kemosabe Inserita: 12 febbraio 2020 Autore Segnala Inserita: 12 febbraio 2020 il problema è che quei pezzi di codice sono quelli del programma originale, e funzionano. il fatto è che non capisco il funzionamento dei vari return, return 1 ...... a chi restituisce 1???? return 2 ....... idem return da solo....... dove ritorna il ciclo? scusate se insisto ma non capisco: char c=myKeypad.getKey(); if(c != NO_KEY) { String codcurent=iaCOD(c); int A=comparareCOD(codcurent); if(A==0) { id_error(); // 401 return; } if(A==1) { id_valido(); // 360 stare = 1; return; } if(A==2); { stare = 2; lcd.clear(); lcd.setCursor(0,0); lcd.print("Pairing..."); Serial.println("Pairing..."); delay(2000); return; } } break; quello che capisco di questo pezzo è che se inserisco un codice e se il codice non corrisponde a : iaCOD(c), A diventa 0, quindi va alla funzione ...id_error(); poi ritorna, ma dove? se io non mettessi il return, uscito dalla funzione id_error(), non ritornerebbe lo stesso a " char c=myKeypad.getKey();" ???? per capire come funziona il return devo avere dei riscontri reali, altrimenti non ci arrivo........ grazie
del_user_97632 Inserita: 12 febbraio 2020 Segnala Inserita: 12 febbraio 2020 (modificato) Continui a postare codice incompleto e tutto stabulato. Manca parte della funzione, e il nome. Prova a postare almeno l'intera funzione. id_error() cosa faccia lo sai solo tu, manca il codice Nei programmi, e qui non c'entra il C, c'e' un chiamante e un chiamato. Il return ritorna dal chiamante. Modificato: 12 febbraio 2020 da _angelo_
Livio Orsini Inserita: 12 febbraio 2020 Segnala Inserita: 12 febbraio 2020 2 ore fa, kemosabe ha scritto: String codcurent=iaCOD(c); int A=comparareCOD(codcurent); if(A==0) Qui chiami la funzione comparareCOD(codcurent); Da qualche parte èm dichiarato int A Ritorna dove c'è la riga del 1° if e rende un valore intero in A Nella funzione che ho messo io ho dichiarato come locale int iret; il valore di iret almomentodel ritorno viene asseganto ad A. Lo studio di un linguaggio va fatto con metodo! Se ti basi su di un testo come il Ritchie, ma anche con altri testi, devi partire a studuare dalla prima pagina, provare i vari esercizi che incontri e non proseguire sino a quando non hai capito bene quello che hai fatto sino a quel punto. Questo vale per qualsiasi cosa si studi. Saltabeccare da un punto all'altro o, peggio, saltare certe parti che i considerano noiose o insignificanti è deleterio. Solo quando domini bene il linguaggio puoi usare il testo come un manuale e consultarlo per verificare o rinfrescare certi argomenti specifici. Inoltre bisognerebbe, prima ancora di studiare un linguaggio, farsi una cultura generale sulle tecniche di programmazione. Io ho iniziato a programmare oltre 55 anni fa con stile "pene di molosso", poi pochi anni dopo ho dovuto dare un'esame universitario di programamzione e fortunatamente ho dovuto acquisire le basi teoriche sulle "macchine calcolatrici". Questo è stato, per me, il punto di svolta; da quel momento in poi ho imparato come si studia la programmazione e conme si affronta l'analisi di un problema software.
kemosabe Inserita: 12 febbraio 2020 Autore Segnala Inserita: 12 febbraio 2020 Livio, tu hai ragione, perchè tutto quello che hai studiato ( università......), lo hai fatto per poi applicarlo al tuo lavoro. Io, lo faccio per pura passione e con tanta voglia, ma, mai e poi mai potrei nemmeno avvicinarmi a quello che sai tu. Cerco in tutti i modi, senza basi logicamente, ad apprendere, e penso che tu capisca che non è facile. Da quando avevo 10 anni, la mia passione era quella dell'elettricità, che poi mi ha portato per 40 anni a fare l'elettricista, ma ti assicuro che la mia seconda passione sono i computer, e da un po di tempo sto cercando di addentrarmi in questo mondo, che in un certo senso lega le mie due passioni. Ti e Vi chiedo scusa se in base alle mie domande vi sembra che sia stupido, ma se secondo voi con le poche basi che ho, mi dite che dovrei lasciar perdere, lo faccio e cercherò di dedicarmi ad altro. grazie per la comprensione
Livio Orsini Inserita: 12 febbraio 2020 Segnala Inserita: 12 febbraio 2020 1 ora fa, kemosabe ha scritto: Ti e Vi chiedo scusa se in base alle mie domande vi sembra che sia stupido, ma se secondo voi con le poche basi che ho, mi dite che dovrei lasciar perdere, lo faccio e cercherò di dedicarmi ad altro. Ma no, il forum esiste proprio per questo. Sto solo cercando di spiegarti come studiare. Anche se studi per hobby è sempre necessario farlo con metodo. Altrimenti si rischia da avere tanta confusione in testa. Io vado per i 76,quello che faccio ora lo faccio solo per hobby, ovvero son tornato alle origini quando l'elettronica per me era solo passione. Però anche se lavoro per hobby, quando mi metto a studiare qualche cosa di nuovo lo faccio con metodo. A volte mi lascio prendere dall'entusiasmo e vado a tentativi, ma quasi mai i risultati sono buoni; quasi sempre è solo una perdita di tempo. Quando mi accorgo che sto facendo confusione, faccio un bel reset e riparto con metodo dall'inizio. Comunque spero tu abbia capito come lavora la funzione return(). Se hai dei dubbi chiedi; al massimo ti arriva qualche .... saluto.
dott.cicala Inserita: 12 febbraio 2020 Segnala Inserita: 12 febbraio 2020 (modificato) Partire dal C puro per imparare a programmare Arduino è molto faticoso, specialmente se si parte da zero e con un testo così "pesante" e teorico. Arduino è nato proprio per facilitare l'apprendimento per mezzo della pratica e sarebbe meglio fare riferimento a uno dei tanti testi ad esso dedicati come ad esempio questo oppure questo ma ce ne sono molti altri che affrontano anche la programmazione avanzata. Acquisite le basi ti sarà più facile affrontare lo studio del C anche se non è necessario conoscerlo nella sua completezza per programmare Arduino. Tieni presente che nel mondo dell'automazione industriale ci sono tantissimi programmatori professionisti che non conoscono nulla del C, del testo strutturato in genere e nemmeno linguaggi di tipo IL...eppure lavorano, se bene o male è tutt'altro di scorso, ma hanno il loro mercato e riescono a soddisfare le richieste dei loro clienti, quindi non ti devi sentire incapace. Hai solo scelto la strada più difficile. Modificato: 12 febbraio 2020 da dott.cicala
kemosabe Inserita: 13 febbraio 2020 Autore Segnala Inserita: 13 febbraio 2020 Sono andato a vermi i manuali da te suggeriti,Stefano, e a parte due righe dove dice che return da solo ritorna al chiamante interrompendo l'esecuzione, o che ritorna un valore ad una variabile, non c'è molto altro. Il fatto è che non capisco in che modo mi possa essere utile all'interno di un programma. Posso partire da un esempio semplice? switch (stare) { case 0: { mfrc522.PCD_Init(); if ( mfrc522.PICC_IsNewCardPresent() && mfrc522.PICC_ReadCardSerial() ) { citireNFC(); // chiama funzione di richiamo da eeprom if (validareNFC()) // se il codice è presente ed è corretto { id_valido(); //chiama funzione stare = 0; // poi ricomincia return; } else { id_error(); // se codice errato chiama questa funzione return; break; } } // ecc. ecc // _-_---_---_----_--__--_-__----_--_----_--_-_----- switch (stare) { case 0: { mfrc522.PCD_Init(); if ( mfrc522.PICC_IsNewCardPresent() && mfrc522.PICC_ReadCardSerial() ) { citireNFC(); // chiama funzione di richiamo da eeprom if (validareNFC()) // se il codice è presente ed è corretto { id_valido(); //chiama funzione stare = 0; // poi ricomincia } else { id_error(); // se codice errato chiama questa funzione break; } } // ecc. ecc come vedete ho inserito lo stesso codice due volte uno con e uno senza i return da quel poco che so io quello che succede nel primo codice, succederebbe anche nel secondo. Se cosi non fosse allora vorrei capirne le differenze. Scusate ma sono un praticone, e mi piace vedere per capire. Grazie
Livio Orsini Inserita: 13 febbraio 2020 Segnala Inserita: 13 febbraio 2020 (modificato) 1 ora fa, kemosabe ha scritto: e a parte due righe dove dice che return da solo ritorna al chiamante interrompendo l'esecuzione, o che ritorna un valore ad una variabile, non c'è molto altro. Corretto perchè non c'è altro da dire. Per capirne l'utilità devi arrivare a capire l'utilità di delegare funzioni ripetitive a pezzi di codice specializzati nellafunzione Ho dato una letta veloce alle due versioni; a mio avviso, come prima impressione, il return non sevono, per interrompere chi sono già le istruzioni di break. Nel linguaggio "C", ed in quelli assimilati, la funzione "return" serve quando si vuole ritornare un valore. Ti faccio un esempio semplicissimo. ...... int A, B, C; ..... A = 3; B = 5; C = mul(A, B); ..... int c mul(int a, int b) { c = a * b; return c; } In questo caso chiami la funzione mul che esegue la moltiplicazione di 2 interi e rende un intero. E' una cosa banale che non meriterebbe una funzione dedicata, però immagina di dover effetture un'operazione più complessaper esempio una conversione da esadecimale a BCD di un numero doppio intero. Torno a ripeterti che partire a costruire un edificio da l secondo piano si spreca tempo e materiale. Partire dalle fondazioni e poi costruire con i tempi giusti non è spreco di tempo, ma è risparmio di tempo Modificato: 13 febbraio 2020 da Livio Orsini
kemosabe Inserita: 13 febbraio 2020 Autore Segnala Inserita: 13 febbraio 2020 solo a titolo di divertimento, vi allego il file con le modifiche da me apportate, alcune delle quali ancora non funzionano, vedi funzione open_door() grazie ancora.......continuo lo studio del libro #include <EEPROM.h> #include <SPI.h> #include <MFRC522.h> #include <Wire.h> #include <LiquidCrystal_I2C.h> //FASTLED #include <FastLED.h> #define DATA_PIN 3 #define NUM_LEDS 6 #define CLOCK_PIN 13 CRGB leds[NUM_LEDS]; //KEYPAD #include <Keypad.h> #include <Keypad_I2C.h> #define I2CADDR 0x20 //il pezzo di codice che vi char customKey = 0; //BLINK unsigned long previousMillis = 0; //DOOR int fc_door = 4; bool bool_door = false; int last_door_state = LOW; int door_state = LOW; int val_fc_door = LOW; bool fc_state = false; bool door_time; bool time_door; //BUZZER int Buzz = A5; int stare = 0; byte COD[10]; byte AUX[10]; int k = 0; String codacces = "1234#"; String codpairing = "987A#"; //nfc #define RST_PIN 9 // Configurable, see typical pin layout above #define SS_PIN 10 // Configurable, see typical pin layout above MFRC522 mfrc522(SS_PIN, RST_PIN); // Create MFRC522 instance #define NEW_UID {0xDE, 0xAD, 0xBE, 0xEF} MFRC522::MIFARE_Key key; //lcd LiquidCrystal_I2C lcd(0x27, 16, 2); //TASTIERA const byte numRows = 4; //number of rows on the keypad const byte numCols = 4; //number of columns on the keypad //keymap defines the key pressed according to the row and columns just as appears on the keypad char keymap[numRows][numCols] = { {'1', '2', '3', 'A'}, {'4', '5', '6', 'B'}, {'7', '8', '9', 'C'}, {'*', '0', '#', 'D'} }; //Code that shows the the keypad connections to the arduino terminals byte rowPins[numRows] = {0, 1, 2, 3}; //Rows 0 to 3 byte colPins[numCols] = {4, 5, 6, 7}; //Columns 0 to 3 //initializes an instance of the Keypad class //Keypad myKeypad= Keypad(makeKeymap(keymap), rowPins, colPins, numRows, numCols); Keypad_I2C myKeypad( makeKeymap(keymap), rowPins, colPins, numRows, numCols, I2CADDR); void setup() { myKeypad.begin( ); FastLED.addLeds<NEOPIXEL, DATA_PIN>(leds, NUM_LEDS); FastLED.setBrightness(50); FastLED.clear (); FastLED.show(); pinMode(fc_door, INPUT_PULLUP); pinMode(Buzz, OUTPUT); //nfc Serial.begin(9600); // Initialize serial communications with the PC //Serial.println("Come apro?:"); while (!Serial); // Do nothing if no serial port is opened (added for Arduinos based on ATMEGA32U4) SPI.begin(); // Init SPI bus mfrc522.PCD_Init(); // Init MFRC522 card for (byte i = 0; i < 6; i++) { key.keyByte[i] = 0xFF; } start(); // 347 } void citireNFC() { for (byte i = 0; i < (mfrc522.uid.size); i++) { COD[i] = mfrc522.uid.uidByte[i]; } /*Serial.println(""); Serial.print("COD : "); Serial.print(COD[0]); Serial.print(COD[1]); Serial.print(COD[2]); Serial.print(COD[3]);*/ } void pairNFC() { Serial.println(""); Serial.print("COD in pair : "); Serial.print(COD[0]); Serial.print(COD[1]); Serial.print(COD[2]); Serial.print(COD[3]); long r = 0; int c = 0; for (int i = 1; i <= EEPROM.read(0); i++) { switch (i % 4) { case 1 : { AUX[0] = EEPROM.read(i); break; } case 2 : { AUX[1] = EEPROM.read(i); break; } case 3 : { AUX[2] = EEPROM.read(i); break; } case 0 : { AUX[3] = EEPROM.read(i); break; } } if ((i) % 4 == 0) { Serial.println(r); if ( AUX[0] == COD[0] && AUX[1] == COD[1] && AUX[2] == COD[2] && AUX[3] == COD[3] ) { //lcd.clear(); //lcd.setCursor(0,0); //lcd.print("ID PRESENTE"); Serial.println("ID PRESENTE"); leds[2].setRGB(0, 0, 255); //blue on FastLED.show(); delay(2000); //lcd.setCursor(0,1); //lcd.print("SYSTEM"); Serial.println("SYSTEM"); leds[2].setRGB(0, 0, 0); //blue off FastLED.show(); //digitalWrite(b_led,LOW); delay(2000); c = 1; break; } } } if (c == 0) { int ttt = EEPROM.read(0); //lcd.print("ID AGGIUNTO"); Serial.println("ID AGGIUNTO"); leds[4].setRGB(255, 255, 255); //white on leds[2].setRGB(0, 0, 255); //blue on FastLED.show(); Serial.print(COD[0]); Serial.print(COD[1]); Serial.print(COD[2]); Serial.print(COD[3]); EEPROM.write(ttt + 1, COD[0]); EEPROM.write(ttt + 2, COD[1]); EEPROM.write(ttt + 3, COD[2]); EEPROM.write(ttt + 4, COD[3]); ttt = ttt + 4; //Serial.println("ttt"); //Serial.println(ttt); EEPROM.write(0, 0); EEPROM.write(0, ttt); //lcd.clear(); //lcd.setCursor(0,0); leds[4].setRGB(0, 0, 0); //white off leds[2].setRGB(0, 0, 0); //blue off FastLED.show(); delay(2000); start(); } } boolean validareNFC() { boolean c = false; for (int i = 1; i <= EEPROM.read(0); i++) { switch (i % 4) { case 1 : { AUX[0] = EEPROM.read(i); break; } case 2 : { AUX[1] = EEPROM.read(i); break; } case 3 : { AUX[2] = EEPROM.read(i); break; } case 0 : { AUX[3] = EEPROM.read(i); break; } } if ((i) % 4 == 0) { if ( AUX[0] == COD[0] && AUX[1] == COD[1] && AUX[2] == COD[2] && AUX[3] == COD[3]) c = true; } } return c; } int comparareCOD(String a) { if (a.equals(codacces)) return 1; else if (a.equals(codpairing)) return 2; else return 0; } String iaCOD(char x) { char vec[8]; vec[0] = x; lcd.setCursor(0, 0); lcd.clear(); lcd.print('X'); Serial.println('X'); for (int i = 1; i < 5; i++) { vec[i] = myKeypad.waitForKey(); lcd.print('X'); Serial.println('X'); } vec[5] = NULL; String str(vec); return str; } void loop() { switch (stare) { case 0: { mfrc522.PCD_Init(); if ( mfrc522.PICC_IsNewCardPresent() && mfrc522.PICC_ReadCardSerial() ) { citireNFC(); if (validareNFC()) { id_valido(); stare = 0; return; } else { id_error(); // 399 return; break; } } char c = myKeypad.getKey(); if (c != NO_KEY) { String codcurent = iaCOD(c); int A = comparareCOD(codcurent); if (A == 0) { id_error(); // 401 return; } if (A == 1) { id_valido(); // 360 stare = 1; return; } if (A == 2); { stare = 2; lcd.clear(); lcd.setCursor(0, 0); lcd.print("Pairing..."); Serial.println("Pairing..."); delay(2000); return; } } break; } case 1: { stare = 0; return; } case 2: { mfrc522.PCD_Init(); if ( mfrc522.PICC_IsNewCardPresent() && mfrc522.PICC_ReadCardSerial() ) { citireNFC(); pairNFC(); stare = 0; delay(2000); // start(); } break; } } } void blinkled() // 263 { unsigned long previousMillis = millis(); while (millis() - previousMillis < 3000UL) { leds[4].setRGB(0, 0, 0); //white leds[3].setRGB(255, 64, 0); //orange FastLED.show(); delay(50); leds[4].setRGB(255, 255, 255); //white leds[3].setRGB(0, 0, 0); //red FastLED.show(); delay(50); leds[4].setRGB(0, 0, 0); //white FastLED.show(); } } void start() { lcd.init(); lcd.backlight(); lcd.setCursor(0, 0); lcd.clear(); lcd.print("COME APRO?"); lcd.print("PORTA CHIUSA"); Serial.println("Come apro?:"); Serial.println("PORTA CHIUSA"); door_time = true; } void id_valido() { lcd.clear(); lcd.setCursor(0, 0); lcd.print("ID VALIDO"); Serial.println("ID VALIDO"); delay(1000); open_door(); start(); } void id_error() { lcd.clear(); lcd.setCursor(0, 0); lcd.print("ID NON VALIDO"); Serial.println("ID NON VALIDO"); blinkled(); lcd.setCursor(0, 1); lcd.clear(); lcd.print("CHIUSA"); Serial.println("CHIUSA"); delay(1000); start(); } void open_door() { door_state= digitalRead(fc_door); if ( door_state) { leds[0]=CRGB(0,0,0); //led porta rosso off aperta leds[1]=CRGB(0,255,0); //led porta verde on aperta FastLED.show(); //door_state = HIGH; } else { leds[0]=CRGB(255,0,0); // led porta rosso on chiusa leds[1]=CRGB(0,0,0); // led porta verde off chiusa FastLED.show(); // door_state = LOW; } unsigned long currentMillis = millis(); // if (door_state == LOW || door_time==true) // { if (door_time && (millis() - previousMillis )>= 10000UL ) { door_time=false; time_door==false; } time_door==true; previousMillis = millis(); // } if (door_state == LOW && time_door == true) { leds[5]=CRGB(255,255,0); // serratura on leds[3]=CRGB(7,150,44); // buzzer medio FastLED.show(); Serial.println ("door close time serratura on 2 sec suono medio"); Serial.println (" "); } else if (door_state == LOW && time_door==false) { leds[5]=CRGB(152,52,221); // serratura off leds[3]=CRGB(0,0,0); // buzzer stop FastLED.show(); Serial.println ("door close no time no serratura suono stop"); Serial.println (" "); delay(100); } else if (time_door==false && door_state == HIGH) { leds[5]=CRGB(152,52,221); // serratura off leds[3]=CRGB(11,49,3); // buzzer alto FastLED.show(); Serial.println ("door open & time stop stop serratura suono alto"); Serial.println (" "); } }
Livio Orsini Inserita: 13 febbraio 2020 Segnala Inserita: 13 febbraio 2020 Che libreria stai usando per <LiquidCrystal_I2C.h>? perchè alcune hanno problemi
del_user_97632 Inserita: 13 febbraio 2020 Segnala Inserita: 13 febbraio 2020 (modificato) Codice un po' mal organizzato. Si fa fatica a leggerlo in quanto mal tabulato e mal scritto. E' per chi legge che ti aiuta e anche per te, come principiante, perche piu' e' ben chiaro e leggibile, piu capisci al volo il funzionamento del codice. Ti consiglio di seguire uno stile di scrittura preciso. Se non sai quale usare leggiti https://www.kernel.org/doc/html/v4.10/process/coding-style.html Altro consiglio, ok un buon libro, poi, una buona palestra di C e' l'opensource, da li puoi imparare molto, il codice e' li ovunque in progetti gitlab etc, in genere scritto da esperti, visibile a tutti. Un esempio il kernel linux. https://elixir.bootlin.com/linux/v5.6-rc1/source Poi, infine, verifica in open_door() time_door==false; } time_door==true; Modificato: 13 febbraio 2020 da _angelo_
del_user_97632 Inserita: 13 febbraio 2020 Segnala Inserita: 13 febbraio 2020 (modificato) Qui c'e' qualcosa che non va void blinkled() // 263 { unsigned long previousMillis = millis(); while (millis() - previousMillis < 3000UL) { previousMillis e' anche globale, ma se la ridefinisci dentro una funzione, viene usata la variabile locale. Credo che la condizione sopra sia sempre vera. lo "shadowing" di variabili e' da evitare. https://en.wikipedia.org/wiki/Variable_shadowing Modificato: 13 febbraio 2020 da _angelo_
kemosabe Inserita: 14 febbraio 2020 Autore Segnala Inserita: 14 febbraio 2020 per quanto riguarda la libreria <LiquidCrystal_I2C.h> sto usando la master. molto interessante l'articolo sulla formattazione. si ho notato l'errore di previus millis, mi sono dimenticato di eliminarlo,grazie. a parte queste cose, resta di fatto che la funzione open_door, se la uso da sola in un programma a parte funzione, se la inserisco nel programma che vi ho allegato prima no. è per questo che vi chiedo delucidazioni su quei return, perchè non vorrei che fossero quelli che fanno fare alla funzione open_door strane cose grazie
Livio Orsini Inserita: 14 febbraio 2020 Segnala Inserita: 14 febbraio 2020 29 minuti fa, kemosabe ha scritto: se la uso da sola in un programma a parte funzione, se la inserisco nel programma che vi ho allegato prima no. Che difetto riscontri? Visto che l'ambiente arduino non ha la possibilità di inserire blocchi, fare delle traccie di percorso e altro di quanto servedevi arrangiarti con il monitor della seriale. Nel programma metti dei Serial.println (" xxxx") con cui visualizzi dei messaggi (esempio 1, 2, ... n) così puoi seguire il percorso del tuo software e vedere se passa da determinati punti e che valore assumono le variabili facendole stampare, ad esempio se fai uno switch puoi far stampare immediatamente prima il valore della variabile dello switch. 35 minuti fa, kemosabe ha scritto: per quanto riguarda la libreria <LiquidCrystal_I2C.h> sto usando la master. Io uso una libreria scaricata dal forum ufficiale di Arduino (Testato è il nome della libreria).
kemosabe Inserita: 14 febbraio 2020 Autore Segnala Inserita: 14 febbraio 2020 si Livio ho gia fatto le varie prove inserendo i serial.print, lo faccio sempre in fase di test. In pratica il Millis di pausa della funzione open_door è in una funzione in un'altro sketch funziona, quando la funzione la metto nel programma completo no. Questo è uno dei dilemmi che non capisco di arduino
del_user_97632 Inserita: 14 febbraio 2020 Segnala Inserita: 14 febbraio 2020 19 minuti fa, kemosabe ha scritto: n pratica il Millis di pausa della funzione open_door è in una funzione in un'altro sketch funziona, Ah, ho capito tardi che lavoravi su arduino, ok. Cosa vuoi fare di preciso ? questo codice in open_door non ha molto senso a mio avviso // if (door_state == LOW || door_time==true) // { if (door_time && (millis() - previousMillis )>= 10000UL ) { door_time=false; time_door==false; } time_door==true; previousMillis = millis(); Se vuoi richiudere la serratura dopo 10 sedondi, da qualche parte nel main loop, dovresti effettuare il controllo del tempo e chiuderla (se aperta). Perche open_door la chiami una volta sola su id_valido
kemosabe Inserita: 15 febbraio 2020 Autore Segnala Inserita: 15 febbraio 2020 (modificato) scusa ma non capisco perchè, se creo un un nuovo skech e faccio la chiamata alla funzione dal loop: ovvero questo: //FASTLED #include <FastLED.h> #define DATA_PIN 3 #define NUM_LEDS 6 #define CLOCK_PIN 13 CRGB leds[NUM_LEDS]; //CONSTANTS const int fc_door = 4; // Button //const int serr = 6; // serratura giallo //const int buzzer_low = 5; // green buzzer basso //const int buzzer_high = 7; // red buzzer alto //VARIABLES int buttonPushCounter = 0; // counter for the number of button presses bool bool_door = 0; // current state of the button int lastButtonState = 0; // previous state of the button bool time_door = false; bool door_time=false; //MILLIS unsigned long previousMillis = 0; const unsigned long interval = 5000; const unsigned long redLedInterval = 2000; void setup(){ FastLED.addLeds<NEOPIXEL, DATA_PIN>(leds, NUM_LEDS); FastLED.setBrightness(50); FastLED.clear (); FastLED.show(); Serial.begin ( 9600 ); pinMode ( fc_door, INPUT ); // pinMode ( buzzer_low, OUTPUT ); // pinMode( buzzer_high, OUTPUT ); // pinMode ( serr, OUTPUT ); } void loop(){ open_door(); } void open_door() { // read the pushbutton input pin: bool_door = digitalRead(fc_door); unsigned long currentMillis = millis(); // if button is pressed, turn relay on (if it wasn't already on), and reset the timer // no need to check for previous state, in this specific case if( !door_time ) { time_door = true; if (currentMillis - previousMillis >= 6000) { previousMillis = currentMillis; leds[5].setRGB ( 0, 0, 0 ); // serratura giallo leds[1].setRGB ( 0, 0, 0 ); // buzzer basso verde leds[0].setRGB ( 0, 0, 0 ); //buzzer alto rosso FastLED.show (); time_door = false ; door_time = true ; } } // if relay is currently on... if( time_door==true && bool_door==LOW ) { leds[5].setRGB ( 255, 255, 0 ); // serratura giallo leds[1].setRGB ( 0, 255, 0); // buzzer verde FastLED.show (); } else if ( time_door==true && bool_door==HIGH) { leds[1].setRGB ( 0, 0, 0 ); // buzzer verde leds[0].setRGB ( 255, 0, 0 ); FastLED.show (); } else if ( time_door==false && bool_door==HIGH) { leds[0].setRGB ( 255, 0, 0 ); FastLED.show (); } else if ( time_door==false && bool_door==LOW) { leds[0].setRGB ( 0, 0, 0 ); FastLED.show (); } } tutto funziona, magari c'è un modo migliore per farlo??? se lo inserisco nel programma con tastiera e rfid no è qui che non capisco, perchè da una parte va e dall'altra no ho apportato delle modifiche nel frattempo. grazie Modificato: 15 febbraio 2020 da kemosabe
Messaggi consigliati
Crea un account o accedi per commentare
Devi essere un utente per poter lasciare un commento
Crea un account
Registrati per un nuovo account nella nostra comunità. è facile!
Registra un nuovo accountAccedi
Hai già un account? Accedi qui.
Accedi ora