RC522 et Ruban LED qui bloque allumé après passage du TAG

Salut à tous!
Voila je débute en programation arduino mais je me debrouille pour réussir ce que je veux en général mais la je sèche... :grin:
Le concept de mon projet est le suivant :grin:
J'ai un capteur RFID RC522 sur un arduino NANO.
Lorsque je pose le bon tag sur le capteur l'arduino allume via un système transistor un petit Ruban led (ça c'est ok pour moi), lorsque je retire le tag le ruban led s'éteind. Lorsque je met un mauvais tag il ne se passe rien.

Mon problème est le suivant lorsque je met le bon tag le ruban s'allume mais lorsque je le retire le ruban ne s'éteind pas... j'ai essayer plusieurs choses mais rien n'y fait... le mieux que j'ai obtenue c'est que le ruban s'éteind bien quand on retire le tag mais lorsque qu'il est allumé il clignotte.

Voici le code (un peu bordélique) ce code allume le ruban mais ne l'éteind pas.

Il y aurait t'il une solution pour que le ruban led reste allumé tant que le tag est présent devant le scanner et qu'il s'éteingne lorsque l'on retire le tag comme par exemple :
-Lecture RFID : TAG ok
-Allumage LED
-Mémorisation TAG ok
-Nouvelle lecture RFID
-Si TAG ok ne rien faire
-Si TAG absent ou différent
-LED OFF

J'epère etre assez clair dans mon explication :slight_smile:
Merci d'avance :slight_smile:

/*******************************************************************************
   RFID LEDs

   Exemple d'utilisation de la bibliothèque MFRC522 par Miguel Balboa

   Lorsque le tag RFID est accepté, une LED verte s'allume pendant 3 secondes
   Lorsque le tag RFID est refusé, une LED rougeo s'allume pendant 3 secondes

   Pour plus de détails:
   
   https://electroniqueamateur.blogspot.com/2017/04/module-rfid-rc522-et-arduino.html
   
***********************************************************************************/


#include <SPI.h>
#include <MFRC522.h>

// copier ici le résultat du sketch "lectureUID.ino":
const byte bonUID[4] = {196, 179, 128, 20};

const int pinLEDStrip = 7; // LED verte

const int pinRST = 9;  // pin RST du module RC522
const int pinSDA = 10; // pin SDA du module RC522
bool (tag) = false;

MFRC522 rfid(pinSDA, pinRST);

void setup()
{
  SPI.begin();
  rfid.PCD_Init();
  pinMode(pinLEDStrip, OUTPUT);


}

void loop()
{
  int refus = 0; // quand cette variable n'est pas nulle, c'est que le code est refusé

 if
  (rfid.PICC_IsNewCardPresent())  // on a dédecté un tag
  {  
    tag = true;}
    else{
      tag = false;
    }
   
    if (rfid.PICC_ReadCardSerial())  // on a lu avec succès son contenu
    {

      for (byte i = 0; i < rfid.uid.size; i++) // comparaison avec le bon UID
      {
        if (rfid.uid.uidByte[i] != bonUID[i]) {
          refus++;
        }
      }

      if (refus == 0) // UID accepté
      {
       if (tag) 
       {
// on allume la LED verte pendant trois secondes
        digitalWrite(pinLEDStrip, HIGH);
      }
     
      
    }
  
  }
}

     
    
      
  

Bonjour bixie

Tu n'as rien mis pour l'éteindre!

J'ai regardé comment mieux tourner ton programme, car tel quel c'était difficile.
J'ai déplacé le test de l'UID dans une fonction boolean cardCheck(byte bonUID[]) qui fait le nécessaire pour dire si l'UID est OK ou pas.
Ainsi, dès que l'UID est OK, la LED s'allume au moins 3 secondes, ensuite le programme attend que la carte soit retirée pour éteindre le LED.

/*******************************************************************************
   RFID LEDs

   Exemple d'utilisation de la bibliothèque MFRC522 par Miguel Balboa

   Lorsque le tag RFID est accepté, une LED verte s'allume pendant 3 secondes
   Lorsque le tag RFID est refusé, une LED rougeo s'allume pendant 3 secondes

   Pour plus de détails:
   
   https://electroniqueamateur.blogspot.com/2017/04/module-rfid-rc522-et-arduino.html
   
***********************************************************************************/


#include <SPI.h>
#include <MFRC522.h>

// copier ici le résultat du sketch "lectureUID.ino":
const byte bonUID[4] = {196, 179, 128, 20};

const int pinLEDStrip = 7; // LED verte

const int pinRST = 9;  // pin RST du module RC522
const int pinSDA = 10; // pin SDA du module RC522
bool (tag) = false;

MFRC522 rfid(pinSDA, pinRST);

void setup()
{
  Serial.begin(115200);
  SPI.begin();
  rfid.PCD_Init();
  pinMode(pinLEDStrip, OUTPUT);


}

void loop()
{
	if (cardCheck(bonUID))
	{
		Serial.println("Card OK");
			
		digitalWrite(pinLEDStrip, HIGH);     // on allume la LED verte pendant trois secondes
		delay(3000);

		while(cardCheck(bonUID)) {}     // tant que cette carte n'est pas retirée
		digitalWrite(pinLEDStrip, LOW);    // on éteind la LED une fois que la carteest retirée
	}
}

boolean cardCheck(byte bonUID[])
{
	boolean check = false;
	rfid.PCD_Init();

	if(rfid.PICC_IsNewCardPresent())
	{		
		if (rfid.PICC_ReadCardSerial())  // on a lu avec succès son contenu
		{
			check = true;
			for (byte i = 0; i < rfid.uid.size; i++) // comparaison avec le bon UID
			{
				if (rfid.uid.uidByte[i] != bonUID[i]) 
				{
					check = false;
				}
			}
		}
	}
	return check;
}

Cordialement
jpbbricole

vous avez testé?

il me semble que rfid.PICC_IsNewCardPresent() n'est vrai que si c'est une nouvelle carte comme son nom l'indique

Bonsoir J-M-L

Oui!
Tu devrais savoir, que je teste toujours les programmes que je mets en ligne, si ce n'est pas le cas, je le signale.
En lisant ce programme tu verra un rfid.PCD_Init();.

Cordialement
jpbbricole

certes ! :wink: (mais la question était sans sous entendu)

j'avais raté le rfid.PCD_Init(); qui remet tout à zéro effectivement

PS:

pour chipoter si on retire la carte 2 secondes et qu'on la remet le programme ne s'en rend pas compte alors (pas votre faute, c'est la spécification qui n'est pas précise :wink: )

on pourrait régler cela avec votre code en ne faisant aucun délai ou ça revient à faire une loop toute simple qui allume la LED tant que la carte est détectée

void loop() {
    digitalWrite(pinLEDStrip, cardCheck(bonUID) ? HIGH : LOW);
}

et pour chipoter un peu plus, si je présente une carte qui a un UID de 10 octets, on accède au tableau bonUID au delà de ses bornes.
On pourrait corriger comme cela:

boolean cardCheck(byte bonUID[]) {
  rfid.PCD_Init();
  if (rfid.PICC_IsNewCardPresent() && rfid.PICC_ReadCardSerial())  // on a lu avec succès son contenu
      return (memcmp(rfid.uid.uidByte, bonUID, 4) == 0);
  return false;
}

PS2/ j'ai pas testé :slight_smile:

Bonjour J-M-L

C'était indiqué

Pour moi, c'est utile à "l'ergonomie" du programme

Oui et non, j'aime beaucoup cette possibilité de test, je la trouve élégante et je l'utilise assez souvent, mais je doute de sa pertinence, dans ce cas.
En effet, un programme de lecteur de cartes RFID ne se cantonne que rarement voire pas du tout au simple allumage d'une LED. Or cette fonction avec ? ne permet qu'une action, alors allumer une LED + une temporisation + attendre le retrait de la carte + éventuellement faire tirer un relais oblige à avoir un if() traditionnel.
Tes "chipotages" démontrent qu'il y a autant de façon de programmer qu'il y a de programmeurs :wink:

Cordialement
jpbbricole

Tout à fait ! Et que le cahier des charges est important - soit on colle au sujet, soit on prévoit des extensions futures probables ou on traite les cas non attendus (carte avec plus de 4 octets pour l’ID - et encore ici il faudrait faire plus et vérifier que la longueur de lID est 4 pas uniquement que les 4 premiers sont identiques)

De même une attente active n’est pas toujours souhaitable - une approche par état pourrait être nécessaire si le programme doit faire différentes tâches tant que la carte est posée

L’important reste de donner des idées de code à ceux qui viennent poser des questions, et toutes les idées pertinentes sont bonnes à prendre !

Bonjour à tous!!!

Désolé pour la réponse tardive je n'avais pas accès à mon ordinateur jusqu’à aujourd’hui :slight_smile:
Déjà merci pour vos réponses je vais regarder et tester tout ça ! (je reviens vers vous pour vous dire si cela fonctionne chez moi et si j'ai tout compris ou pas :slight_smile:
Pour le moment le programme ne doit effectivement faire que ça et n’évolueras pas sur ce projet mais peu être que dans un futur plus ou moins proche cela arriveras pour un autre projet je vais regarder tout ça! :slight_smile:

pas de souci

donc la version du sketch proposée par @jpbbricole doit être tout à fait fonctionnelle ou la version un peu plus "compacte" (que je n'ai absolument pas testée au contraire de jpbricole)

const byte pinLEDStrip = 7;                   // pin LED verte
const byte pinRST = 9;                        // pin RST du module RC522
const byte pinSDA = 10;                       // pin SDA du module RC522
const byte bonUID[] = {196, 179, 128, 20};    // copier ici le résultat du sketch "lectureUID.ino":

#include <MFRC522.h>
MFRC522 rfid(pinSDA, pinRST);

void setup() {
  SPI.begin();
  rfid.PCD_Init();
  pinMode(pinLEDStrip, OUTPUT);
}

void loop() {
  digitalWrite(pinLEDStrip, cardCheck() ? HIGH : LOW);
  delay(100);  // on vérifie ~10 fois par seconde 
}

boolean cardCheck() {
  rfid.PCD_Init();
  if (rfid.PICC_IsNewCardPresent() && rfid.PICC_ReadCardSerial())  // on a lu avec succès son contenu
      return (memcmp(rfid.uid.uidByte, bonUID, sizeof bonUID) == 0);
  return false;
}