Hello, I am working on a group project in electrical engineering, and I made a program as part of my group project
I am using an Arduino AtMega2560 board which is connected with a 16x2 I2C LCD display and an LCD Keypad Shield (with 6 RIGHT, LEFT, UP, DOWN, SELECT and RESET buttons, and also a TCS3200 Programmable
Color Light-to-Frequency Converter.
My goal is to make a program that detects 3 colors in a certain order and moves on to the next when the detected color is true. Indeed, 1 corresponds to the color BLACK, 2 to the RED, 3 to the GREEN and 4 to the BLUE.
// LCD Keypad Shield
#include <LiquidCrystal.h> //Cette bibliothèque permet à une carte Arduino de contrôler les écrans LiquidCrystal (LCD)
// Création de l'objet lcd (avec les différents ports numériques qu'il utilise)
LiquidCrystal lcd(8, 9, 4, 5, 6, 7);
// Variables
int lcd_key = 0;
int adc_key_in = 0;
// Constantes
#define btnRIGHT 0
#define btnUP 1
#define btnDOWN 2
#define btnLEFT 3
#define btnSELECT 4
#define btnNONE 5
//Capteur couleur
#define S0 19
#define S1 18
#define S2 17
#define S3 16
#define sensorOut 15
int frequency = 0; //valeur de fréquence des couleurs
int ValeurR = 0; //valeur de la longueur d'onde de la couleur ROUGE
int ValeurG = 0; //valeur de la longueur d'onde de la couleur VERT
int ValeurB = 0; //valeur de la longueur d'onde de la couleur BLEU
char* message[] = {"T1:", "V ", "F ", "T2:", "V ", "F ", "T3:", "V ", "F ", "-"}; //Affiche les différents charactères
char Etat_cle = 0; //la clé est dans l'état REPOS
char tour = 0; // numéro de l'étape de détection des couleurs
char couleur_detectee = 0; //valeur de la couleur détectée
char place1 = 2; //assigne la première couleur à détecter
char place2 = 4; //assigne la deuxième couleur à détecter
char place3 = 3; //assigne la troisième couleur à détecter
void setup() {
pinMode(S0, OUTPUT); //Relie les broches des entrées du capteur couleur aux pins de la carte Arduino
pinMode(S1, OUTPUT);
pinMode(S2, OUTPUT);
pinMode(S3, OUTPUT);
pinMode(sensorOut, INPUT);
// Réglage de la mise à l'échelle de fréquence à 20%
digitalWrite(S0, HIGH);
digitalWrite(S1, LOW);
Serial.begin(9600); //Fixe le débit de communication en nombre de caractères par seconde (l'unité est le baud) pour la communication série
lcd.begin(16, 2); // Démarrage de l'écran
lcd.setCursor(0, 0); // Positionnement du curseur au début
lcd.print("Placer les tubes"); // Message
}
void loop() {
// Réglage des photodiodes rouges filtrées à lire
digitalWrite(S2, LOW);
digitalWrite(S3, LOW);
// Lecture de la fréquence de sortie
frequency = pulseIn(sensorOut, LOW);
//Remappage de la valeur de la fréquence au modèle RVB de 0 à 255
ValeurR = map(frequency, 25, 72, 255, 0);
// Impression de la valeur sur le moniteur série
Serial.print("R= ");//nom d'impression
Serial.print(ValeurR);//impression de la fréquence de couleur ROUGE
Serial.print(" "); //ajout d'un espace
delay(100); //delai en millisecondes
// Réglage des photodiodes vertes filtrées à lire
digitalWrite(S2, HIGH);
digitalWrite(S3, HIGH);
// Lecture de la fréquence de sortie
frequency = pulseIn(sensorOut, LOW);
//Remappage de la valeur de la fréquence au modèle RVB de 0 à 255
ValeurG = map(frequency, 30, 90, 255, 0);
// Impression de la valeur sur le moniteur série
Serial.print("G= ");//nom d'impression
Serial.print(ValeurG);//impression de la fréquence de couleur VERT
Serial.print(" "); //ajout d'un espace
delay(100); //delai en millisecondes
// Réglage des photodiodes bleues filtrées à lire
digitalWrite(S2, LOW);
digitalWrite(S3, HIGH);
// Lecture de la fréquence de sortie
frequency = pulseIn(sensorOut, LOW);
//Remappage de la valeur de la fréquence au modèle RVB de 0 à 255
ValeurB = map(frequency, 25, 70, 255, 0);
// Impression de la valeur sur le moniteur série
Serial.print("B= ");//nom d'impression
Serial.print(ValeurB);//impression de la fréquence de couleur BLEU
delay(100); //delai en millisecondes
//on ajoute pas d'espace afin de revenir à la ligne une fois la valeur B détectée
if (ValeurR <= 0 && ValeurG <= 0 && ValeurB <= 0)
{
Serial.print("NOIR ");//affiche NOIR sur le moniteur série
couleur_detectee = 1;//assigne la couleur NOIR au numéro 1
delay(100); //delai en millisecondes
}
else if (ValeurR > ValeurG && ValeurR > ValeurB)
{
Serial.print("ROUGE ");//affiche ROUGE sur le moniteur série
couleur_detectee = 2;//assigne la couleur ROUGE au numéro 2
delay(100); //delai en millisecondes
}
else if (ValeurG > ValeurR && ValeurG > ValeurB)
{
Serial.print("VERT ");//affiche VERT sur le moniteur série
couleur_detectee = 3;//assigne la couleur VERT au numéro 3
delay(100); //delai en millisecondes
}
else if (ValeurB > ValeurR && ValeurB > ValeurG)
{
Serial.print("BLEU ");//affiche BLEU sur le moniteur série
couleur_detectee = 4;//assigne la couleur BLEU au numéro 4
delay(100); //delai en millisecondes
}
bool wait = false; //variable boléenne pour attendre la pression d'un bouton
lcd.setCursor(0, 1); // Positionnement du curseur début de ligne 1
lcd_key = read_LCD_buttons(); // Lecture des touches
switch ( lcd_key ) { //action en cas de bouton appuyé
case btnRIGHT: //pression du bouton gauche
if ( tour == 0 ) //durant le tour 0 initial
{
Etat_cle++; //la clé passe dans l'état AMORCE
lcd.print(message[0]); //affiche "T1: "
tour++;//passe au prochain tour
}
else if (tour == 1 ) //durant le tour 1
{
lcd.setCursor(3, 1); //déplace le curseur
if (couleur_detectee == place1)
{
lcd.print(message[1]); //affiche "V"
delay (1000); //Délai d'une seconde
tour++; //passe au prochain tour
lcd.setCursor(5, 1); //déplace le curseur
lcd.print(message[3]); //affiche "T2: "
}
else
{
lcd.print(message[2]); //affiche "F"
delay (1000); //Délai d'une seconde
}
}
else if (tour == 2 ) //durant le tour 2
{
lcd.setCursor(8, 1); //déplace le curseur
if (couleur_detectee == place2)
{
lcd.print(message[4]); //affiche "V"
delay (1000); //Délai d'une seconde
tour++; //passe au prochain tour
lcd.setCursor(10, 1); //déplace le curseur
lcd.print(message[6]); //affiche "T3: "
}
else
{
lcd.print(message[5]); //affiche "F"
delay (1000); //Délai d'une seconde
}
}
else if (tour == 3 ) //durant le tour 3
{
lcd.setCursor(13, 1); //déplace le curseur
if (couleur_detectee == place3)
{
lcd.print(message[7]); //affiche "V"
delay (1000); //Délai d'une seconde
Etat_cle++; //La clé passe dans l'état DESAMORCE
}
else
{
lcd.print(message[8]); //affiche "F"
delay (1000); //Délai d'une seconde
}
}
wait = true;// on attend que le bouton soit appuyé
break;
}
if ( wait == true ) {
while ( read_LCD_buttons() != btnNONE )
{ //tant qu'un bouton est appuyé
delay(10); //delai en millisecondes
}
}
}
// Fonction de lecture des touches
int read_LCD_buttons()
{
adc_key_in = analogRead(0); // Lecture du port analogique
// Les valeurs qui suivent doivent être adaptées au shield
if (adc_key_in > 1000) return btnNONE; // En principe 1023 quand aucune touche n'est pressée
if (adc_key_in < 50) return btnRIGHT; // 0
if (adc_key_in < 195) return btnUP; // 99
if (adc_key_in < 380) return btnDOWN; // 255
if (adc_key_in < 555) return btnLEFT; // 409
if (adc_key_in < 790) return btnSELECT; // 640
return btnNONE;
}
It is then sufficient to press the RIGHT button to confirm the detected color, and you can rewrite the program to choose the colors to be detected.
The program works, but the problem is that the RIGHT button has difficulty performing the ordered action and I often have to press it several times.
Could someone help me to fix this button problem?
thank you in advance