Aller au contenu


Photo
- - - - -

arrosage pour bonsai


  • Veuillez vous connecter pour répondre
95 réponses à ce sujet

#41 Sandro

Sandro

    Pilier du forum

  • Modérateur
  • PipPipPipPipPip
  • 1 262 messages
  • Gender:Male

Posté 28 mars 2020 - 02:02

Bonjour,

 

je suis perdu comment je pouvais savoir que je devais utiliser .

void setWater(uint8_t mlValue)  {

 

}

La fonction setWater est sensé faire tourner la pompe, mais n'a pas d'info à renvoyer. Du coup, le type de retour est void.

Ensuite, on demande de passer en argument la quantitié d'eau, du coup, il faut un argument, qu'on vas appeller mlValue (tu aurais pu choisir un autre nom, voir même un nom qui correspond à une une autre unité (par exemple ces centilitres)).

On a donc quelque chose de la forme

void setWater(TYPE mlValue)  {

}

Reste à choisir le type. Là il n'y a pas une unique bonne solution, plusieurs conviennent, le tout est de savoir pourquoi on en choisi une en particulier :

- si tu penses avoir besoin d'être plus précis que le ml, alors une option peut d'être utiliser "float". Ici, on n'est pas au ml près, encore moins à une fraction de ml (surtout que je pense pas que ton capteur est aussi précis). Du coup, ici je ne conseillerais pas cette option

- dans le cas contraire, tu pars sur une variable de type entier (int8_t, uint8_t, int16_t, uint16_t, int32_t, uint32_t, ...)

 

Le volume d'eau ne peux pas être négatif, du coup ça ne sert à rien de prendre un type signé (ie les intX_t). Du coup, le choix logique est un uintX_t.

Reste à savoir quel est le volume maximum que tu veux pouvoir traiter : un uintX_t peut contenir des entiers de 0 à 2^X-1.

Du coup, un uint8_t peut contenir des valeurs de 0 à 255 (ml); un uint16_t de 0 à 65535 (ml), soit jusqu'à 65 litre; un uint32_t correspond à plus de 4000 m³ d'eau.

 

Et là, c'est à toi de choisir, selon une application. Plus que 65 litres me parait complètement inutile (le but est d'arroser un Bonsai, pas tout une rizière), du coup uint32_t (et supérieurs) sont à exclure.

 

Du coup, il ne restes que deux choix raisonnables : uint8_t et uint16_t. Là, je dirais que les deux sont valables, à toi de voir si tu envisage de mettre plus que 255 ml ou pas.

 

 

Du coup, en tant que "prof", je t'aurais mis tout les points si tu avais utilisé doit uint8_t, soit uint16_t.

 

 

 

 

 

 

Pour l'utilisation de water_read, l'idée est de toujours réutiliser les fonctions existantes plutôt que de re-écrire un code équivalent : pourquoi re-écrire le calcul du volume d'eau quand tu as une fonction qui le fait déjà?

 


Aidez-nous à vous aider : partagez toutes les informations pertinentes : description précise du problème, contexte, schéma de câblage, liens vers la documentation des composants, votre code (ou encore mieux un code minimal reproduisant le bug), ...

Vous recevrez ainsi plus de réponses, et elles seront plus pertinentes.


#42 michel

michel

    Habitué

  • Membres
  • PipPip
  • 179 messages
  • Gender:Male
  • Location:nice

Posté 28 mars 2020 - 06:27

bonsoir Sandro et Mike118,

voila le code qui fonctionne.

bonne soirée.

void setWater( uint8_t mlValue){
    static bool etatPompe = false;
    static uint32_t lastAffiche = millis ();
    static uint32_t totalMilliLitres =0 ;
    static uint32_t oldTime = millis();
    float flowRate = ((1000.0 / (millis() - oldTime)) * pulseCount) / calibrationFactor;
    float flowMilliLitres = (flowRate / 60) * 1000;
    totalMilliLitres += flowMilliLitres;
     mlValue =100;
    
  if ( etatPompe == false && millis() - lastAffiche >tempsEntreDeuxAffichages  )
      
  {
      setWaterPump(true);
      lastAffiche = millis();
  }
  if
                   
   ( etatPompe = true && water_read()>= mlValue){
 
      setWaterPump(false);
       Serial.println("dosage eau ok");
     
   }  
    
}
    


#43 Sandro

Sandro

    Pilier du forum

  • Modérateur
  • PipPipPipPipPip
  • 1 262 messages
  • Gender:Male

Posté 28 mars 2020 - 06:42

Bonsoir,

plusieurs questions :

- pourquoi est-ce que tu calcule toujours le volume dans la fonction, tu n'en a plus besoin maintenant que tu utilises water_read. Du coup, essaye de faire le ménage et de ne garder que le code utile

- qu'est ce que le temps entre 2 affichages vient faire dans la fonction?


Aidez-nous à vous aider : partagez toutes les informations pertinentes : description précise du problème, contexte, schéma de câblage, liens vers la documentation des composants, votre code (ou encore mieux un code minimal reproduisant le bug), ...

Vous recevrez ainsi plus de réponses, et elles seront plus pertinentes.


#44 Mike118

Mike118

    Staff Robot Maker

  • Administrateur
  • PipPipPipPipPip
  • 9 969 messages
  • Gender:Male
  • Location:Anglet

Posté 28 mars 2020 - 07:47

Michel je te montre une correction possible pour que tu puisse te rendre compte que ce n'est pas " si compliqué " ... 
 

void setWater( uint8_t mlValue) {

    uint16_t mlReference = water_read();  // on note la quantité en ml qui était déjà arrosée avant de commencer
    setWaterPump(true);                   // on allume la pompe
    Serial.println("Arrosage en cours");
    while(water_read() < mlReference + mlValue ) { 
      // On ne fait rien en attendant que le dosage d'eau soit ok 
    }
    Serial.println("dosage eau ok");
    setWaterPump(false);  // on éteind la pompe quand le dosage est ok
    
}

Teste cette fonction, confirme moi que tu as bien compris comment elle marche =)

 

Ce qui est dure c'est uniquement de bien se représenter la chose et de bien découper le problème, et c'est pour cela que je te fais faire ces exercices ... Il faut s'entraîner sur des petits codes pour ensuite pouvoir faire un code plus complexe, et même un code complexe, on ne le fait pas " d'un coup" il faut le découper en plusieurs fonctions simple ...

Dès que tu fais une fonction tu dois regarder si tu peux l'utiliser dans le travail qui suit ... 

 

Il faut essayer d'être " positivement feignant " 
=> On cherche à éviter de taper du code qu'on a déjà tapé. 
=> On évite de créer 50 000 mille variables 

=> On essaye d'avoir un code court

 

Bon du coup pour me montrer que tu as bien compris cette fonction que je viens de te montrer ci dessus tu vas me faire une fonction qui permet d'attendre un certain nombre de temps en seconde , qui prend en paramètre le temps en seconde qu'on veut attendre, et qui utilise la fonction " millis()   "  ( rappel: on fait ça car tu n'as pas le droit d'utiliser la fonction delay() ;)  et que dans la prochaine chose que tu devras faire et que j'ai déjà indiqué ici tu as besoin d'attendre un temps fixe )


Si mon commentaire vous a plus laissez nous un avis  !  :thank_you:

Nouveau sur Robot Maker ? 

Jetez un oeil aux blogs, aux tutoriels, aux ouvrages, au robotscope  aux articles,  à la boutique  et aux différents services disponible !
En attendant qu'une bibliothèque de fichiers 3D soit mise en place n'hésitez pas à demander si vous avez besoin du fichier 3D d'un des produits de la boutique... On l'a peut être ! 
Si vous souhaitez un robot pilotable par internet n'hésitez pas à visiter www.vigibot.com et à lire le sous forum dédié à vigibot!

 

Les réalisations de Mike118  

 

 

 


#45 michel

michel

    Habitué

  • Membres
  • PipPip
  • 179 messages
  • Gender:Male
  • Location:nice

Posté 29 mars 2020 - 05:50

bonsoir Mike118,

j'ai testé ton code ça fonctionne bien après avoir comptabilisé la quantité d'eau, le relais se décolle et se recolle .

je suis entrain d'essayer de voir pour la tempo mais ce n'est pas gagné, j'y suis depuis le début d’après midi et cela ne fonctionne tjs pas .

bonne soirée,



#46 Mike118

Mike118

    Staff Robot Maker

  • Administrateur
  • PipPipPipPipPip
  • 9 969 messages
  • Gender:Male
  • Location:Anglet

Posté 29 mars 2020 - 08:33

Tu veux dire que le relais se colle, puis quand la quantité d'eau souhaité est mesurée le relais se décolle ? 

 

 

Sinon pour la temporisation : 

 

la réponse est cachée dans la fonction setWater =) 

 

il te faut une référence de temps avant de commencer à attendre que tu vas prendre avec millis() 

 

puis tant que tu n'auras pas dépassé le temps à attendre + la référence eh bien tu attends ... 
et le temps à attendre doit être passé en paramètre de ta fonction comme l'était mlValue pour setWater ... 

Là je ne peux plus t'aider plus sans te donner directement la réponse ...


Si mon commentaire vous a plus laissez nous un avis  !  :thank_you:

Nouveau sur Robot Maker ? 

Jetez un oeil aux blogs, aux tutoriels, aux ouvrages, au robotscope  aux articles,  à la boutique  et aux différents services disponible !
En attendant qu'une bibliothèque de fichiers 3D soit mise en place n'hésitez pas à demander si vous avez besoin du fichier 3D d'un des produits de la boutique... On l'a peut être ! 
Si vous souhaitez un robot pilotable par internet n'hésitez pas à visiter www.vigibot.com et à lire le sous forum dédié à vigibot!

 

Les réalisations de Mike118  

 

 

 


#47 michel

michel

    Habitué

  • Membres
  • PipPip
  • 179 messages
  • Gender:Male
  • Location:nice

Posté 30 mars 2020 - 02:34

bonjour Mike118,

j'ai fait ce code :

void setWater( uint8_t mlValue, uint16_t attente) {
   mlValue=100;
   attente = 180000;//temp absortion de l'eau 3mn
   uint16_t mlReference = water_read();// on note la quantité en ml qui était déjà arrosée avant de commencer
   static uint32_t lastAffiche = millis ();
   if (millis()-lastAffiche >= attente){
   setWaterPump(true); // on allume la pompe
   Serial.println("Arrosage en cours");
   while(water_read() < mlReference + mlValue ) {
      // On ne fait rien en attendant que le dosage d'eau soit ok
    }
    lastAffiche = millis ();
    Serial.println("dosage eau ok");
    setWaterPump(false);// on éteind la pompe quand le dosage est ok
   }
    
 }
 
 

aprés avoir comptabiliser la quantité d'eau la pompe = setWaterPump(false)  on attend temp absortion de l'eau ensuite la pompe= setWaterPump(true);

ainsi de suite .

Bonne journée .



#48 Mike118

Mike118

    Staff Robot Maker

  • Administrateur
  • PipPipPipPipPip
  • 9 969 messages
  • Gender:Male
  • Location:Anglet

Posté 30 mars 2020 - 03:20

alors il y a du bon et du moins bon. 

=> Il faut faire des fonctions pour les utiliser. 
=> Quand tu mets des paramètres dans une fonction il faut "utiliser le paramètre pas l'écraser par une valeur que tu mets à l'intérieur. 

 

J'ai demandé de faire deux fonctions distinctes donc on fait deux fonctions ! :P

 

Voici les fonctions corrigées : 
 

void setWater( uint8_t mlValue) {
   uint16_t mlReference = water_read();// on note la quantité en ml qui était déjà arrosée avant de commencer
   setWaterPump(true); // on allume la pompe
   Serial.println("Arrosage en cours");
   while(water_read() < mlReference + mlValue ) {
      // On ne fait rien en attendant que le dosage d'eau soit ok
   }
   Serial.println("dosage eau ok");
   setWaterPump(false);// on éteind la pompe quand le dosage est ok    
}
 
void attendre(uint16_t attente) {    // temps d'attente en secondes 
   uint16_t timeReference = millis();// temps avant de commencer
   Serial.println("on attend");
   while (millis() - timeReference <= attente * 1000) {
      // On ne fait rien en attendant 
   }
   Serial.println("Fin d'attente");
}
 



Constate bien que je n'écris pas les valeurs    mlValue=100;

   ni                                                                   attente = 180000;/

 

 

Car les valeurs sont passées en paramètre de la fonction. 

Quand tu vas utiliser tes fonctions tu le feras ainsi : 
setWater(100);

attendre(180);
 

Maintenant tu vas faire une nouvelle fonction, qui va utiliser ces deux fonctions ainsi que la fonction de lecture de l'humidité =) 

 

pour faire ce qu'on a dit plus tôt : 

 

humidité = lire humidité.

 

Si humidité < seuil  

  alors arroser (X ml )  puis Attendre (3min )

 

humidité  = lire humidité

 

Si humidité > seuil 
  alors Afficher "Arrosage terminé avec succès"
Sinon 

  afficher "Echec d'arrosage" 

 

 

 


Si mon commentaire vous a plus laissez nous un avis  !  :thank_you:

Nouveau sur Robot Maker ? 

Jetez un oeil aux blogs, aux tutoriels, aux ouvrages, au robotscope  aux articles,  à la boutique  et aux différents services disponible !
En attendant qu'une bibliothèque de fichiers 3D soit mise en place n'hésitez pas à demander si vous avez besoin du fichier 3D d'un des produits de la boutique... On l'a peut être ! 
Si vous souhaitez un robot pilotable par internet n'hésitez pas à visiter www.vigibot.com et à lire le sous forum dédié à vigibot!

 

Les réalisations de Mike118  

 

 

 


#49 michel

michel

    Habitué

  • Membres
  • PipPip
  • 179 messages
  • Gender:Male
  • Location:nice

Posté 01 avril 2020 - 02:44

bonjour Mike118,

je reviens vers toi car je n'ai pas réussi à faire le programme cela fait deux jours que je cherche .je te mets quand même ce que j'ai fait .au démarrage de la carte arduino .

soil_moisture immerger dans l'eau .

je le retire de l'eau , le relais" On" quand la quantité d'eau est passer ,relais" Off" (Serial message attente)

passer le délai (30 ) 1mn j'ai diminuer le temps pour aller plus vite ainsi que la quantité d'eau (10)ml.

le relais" On" quantité d'eau repasse mais ça ne s'arrête plus ??? 

par contre au premier arrosage pendant le temps d'attente si je replace le soil-moisture dans l'eau comme ci le premier arrosage aurais suffi (Arrosage terminé avec succès)

voila je te joint le code .

encore merci de ton aide ainsi que sandro.

bon courage prenez soin de vous ainsi que tous les membres du forum .

 void setWater( uint8_t mlValue) {
   uint16_t mlReference = water_read();// on note la quantité en ml qui était déjà arrosée avant de commencer
   bool etatPompe = false; // Pompe Off par défaut
   //setWaterPump(true); // on allume la pompe
   Serial.println("Arrosage en cours");
   while(water_read() < mlReference + mlValue  ) {
      // On ne fait rien en attendant que le dosage d'eau soit ok
   }
   Serial.println("dosage eau ok");
   
   //setWaterPump(false);// on éteind la pompe quand le dosage est ok    
}
 
void attendre(uint16_t attente) {    // temps d'attente en secondes
   uint16_t timeReference = millis();// temps avant de commencer
   Serial.println("on attend");
   while (millis() - timeReference <= attente * 1000) {
      // On ne fait rien en attendant
   }
   Serial.println("Fin d'attente");
}
    
 void Arrosage(){
 uint16_t mlReference = water_read();
 uint16_t rawHumidity = getRawHumidity();
 uint16_t timeReference = millis();// temps avant de commencer
 uint8_t percentHumidity = getPercentHumidity(rawHumidity);
 bool etatPompe = false; // Pompe Off par défaut
 
  if ( percentHumidity <30 ) {
      setWaterPump(true); // on allume la pompe
      setWater(10);//(x ml)
      setWaterPump(false);// on éteind la pompe quand le dosage est ok    
      attendre(30);//attendre  
         
  }
    else if( percentHumidity > 60 ){
        setWaterPump(false);
       
       Serial.println("Arrosage terminé avec succès");
  }
   else {
       Serial.println("Echec d'arrosage");
  }
}


#50 Sandro

Sandro

    Pilier du forum

  • Modérateur
  • PipPipPipPipPip
  • 1 262 messages
  • Gender:Male

Posté 01 avril 2020 - 02:50

Bonjour,

tout d'abord une question : pourquoi est-ce que tu as modifié la fonction "setWater"?

 

Et à quoi correspond ce seuil de 60? Tu vises de dépasser une humidité de 30 ou de 60?


Aidez-nous à vous aider : partagez toutes les informations pertinentes : description précise du problème, contexte, schéma de câblage, liens vers la documentation des composants, votre code (ou encore mieux un code minimal reproduisant le bug), ...

Vous recevrez ainsi plus de réponses, et elles seront plus pertinentes.


#51 michel

michel

    Habitué

  • Membres
  • PipPip
  • 179 messages
  • Gender:Male
  • Location:nice

Posté 01 avril 2020 - 05:14

SANDRO,

Je pensais que je devais la commander par une autre fonction étant donnè que c'était un exemple .

je l'ai remis dans le code mais tant que le soil_ moisture est dans l'eau, le relais oscille entre deux positions.

hors de l'eau il colle (On)

mais toujours dans l'impasse .....

void setWater( uint8_t mlValue) {
   uint16_t mlReference = water_read();// on note la quantité en ml qui était déjà arrosée avant de commencer
   bool etatPompe = false; // Pompe Off par défaut
   setWaterPump(true); // on allume la pompe
   Serial.println("Arrosage en cours");
   while(water_read() < mlReference + mlValue  ) {
      // On ne fait rien en attendant que le dosage d'eau soit ok
   }
   Serial.println("dosage eau ok");
   
   setWaterPump(false);// on éteind la pompe quand le dosage est ok    
}
 
void attendre(uint16_t attente) {    // temps d'attente en secondes
   uint16_t timeReference = millis();// temps avant de commencer
   Serial.println("on attend");
   while (millis() - timeReference <= attente * 1000) {
      // On ne fait rien en attendant
   }
   Serial.println("Fin d'attente");
}
    
 void Arrosage(uint8_t seuil){
 
 uint16_t mlReference = water_read();
 uint16_t rawHumidity = getRawHumidity();
 uint16_t timeReference = millis();// temps avant de commencer
 uint8_t percentHumidity = getPercentHumidity(rawHumidity);
 bool etatPompe = false; // Pompe Off par défaut
 
  if ( percentHumidity <seuil ) {
       setWaterPump(true);
       setWater(10);//(x ml)
       attendre(30);//attendre
         
   }
   
   else {( percentHumidity >seuil ) ;
        setWaterPump(false);
        
       
   }
     
  Serial.println("Arrosage terminé avec succès");
  }
 


#52 Mike118

Mike118

    Staff Robot Maker

  • Administrateur
  • PipPipPipPipPip
  • 9 969 messages
  • Gender:Male
  • Location:Anglet

Posté 01 avril 2020 - 05:52

alors tu as un bon début mais petites remarques comme ça : 

 

Déjà :

 

ça

 else {( percentHumidity >seuil ) ;
        setWaterPump(false);

je ne pense pas que ça soit équivalent à ça 

 else if(percentHumidity > seuil)
  setWaterPump(false);

Ensuite 

=> On évite d'avoir plein de variables qu'on utilise pas  

tu n'as pas besoin de mlReference, ni de timeReference ni de etatPompe dans ta fonction Arrosage. 
=> Pour une fonction plus c'est court en général mieux c'est ;) Donc à chaque fois que tu ajoutes une ligne demande toi si tu en as besoin ! :P

Ensuite un fois que tu as enlevé ces variables, si tu reprends ce que j'ai écris à savoir : 

 

humidité = lire humidité.

 

Si humidité < seuil   {

  alors arroser (X ml ) 
  Attendre (3min )

 

  humidité  = lire humidité

 

 Si humidité > seuil  
   alors Afficher "Arrosage terminé avec succès"
 Sinon 

  afficher "Echec d'arrosage"  

}

 

tu vois que moi j'ai bien précisé le fait que je faisais 2 fois la lecture de l'humidité. Une fois à l'entré de la fonction pour savoir si on continue ou pas et une fois après avoir versé l'eau pour vérifier si succès ou échec. 

 

J'ai rajouté des accolades sur le premier " si " pour que tu vois où il commence et fini ...

 

Je te laisse proposer des corrections de ta fonction Arrosage en fonction de ce que je viens d'écrire =)


Si mon commentaire vous a plus laissez nous un avis  !  :thank_you:

Nouveau sur Robot Maker ? 

Jetez un oeil aux blogs, aux tutoriels, aux ouvrages, au robotscope  aux articles,  à la boutique  et aux différents services disponible !
En attendant qu'une bibliothèque de fichiers 3D soit mise en place n'hésitez pas à demander si vous avez besoin du fichier 3D d'un des produits de la boutique... On l'a peut être ! 
Si vous souhaitez un robot pilotable par internet n'hésitez pas à visiter www.vigibot.com et à lire le sous forum dédié à vigibot!

 

Les réalisations de Mike118  

 

 

 


#53 michel

michel

    Habitué

  • Membres
  • PipPip
  • 179 messages
  • Gender:Male
  • Location:nice

Posté 02 avril 2020 - 03:42

bonjour Mike118,

je te met le code complet pour que tu puisse regarder, par ce que j'ai toujours le relais qui oscille entre deux positions  quand le soil_moisture et dans l'eau .

quand je retire (soil_moisture) de  l'eau le relais (On) flow water (10) mlValue le relais ce décolle (Off) mais flow water ne comptabilise plus rien .

voila je suis tjs au même point .

j’espère que humidité = lire humidité c'est ceux que j'ai fait .

Bonne journée..

/*Soil Moisture*/
const uint8_t  sensor_MoisturePin =  A0;
const uint32_t tempsEntreDeuxAffichages = 1000;// Temps en ms
float flowRate;
/*Relay Pompe Arrosage*/
const uint8_t RelayPin = A2;

/* Capteur de débit d'eau*/
const uint8_t sensorInterrupt = 0;
const uint8_t sensorPin       = 2;
const float calibrationFactor = 98;//4.5

/* Variables volatiles utilisées dans l'interruption pour le débit d'eau = une des rares variables qu'on a le droit d'avoir en globale*/
  volatile uint8_t pulseCount = 0;

void setup() {
    Serial.begin(9600);
    /* Init SoilMoisture*/
    pinMode(sensor_MoisturePin,INPUT);
    /* Init Relay Pumpe  */
    pinMode(RelayPin, OUTPUT);
    /* initialisation du capteur de pompe*/
    water_setup ();
     
}

uint16_t getRawHumidity(){
/* Variables Arrosage*/
    uint16_t rawHumidity = analogRead(sensor_MoisturePin);
    return rawHumidity;
}

uint8_t getPercentHumidity(uint16_t rawHumidity){
    if(rawHumidity > 1023)
     rawHumidity = 1023;
    uint8_t percentHumidity = map(rawHumidity, 0, 1023, 0, 100);
    return percentHumidity;
}
void water_setup () {
  pinMode(sensorPin, INPUT);
  digitalWrite(sensorPin, HIGH);
  pulseCount = 0;
  attachInterrupt(sensorInterrupt, pulseCounter, FALLING);
}
/* fonction qui lit stock en interne et retourne le résultat */
uint32_t water_read () {
  /* Les variables statiques sont des variables qui ne sont pas écrasée, ça permet d'éviter d'utiliser des variables globales*/
  static uint32_t totalMilliLitres = 0;
  static uint32_t oldTime = millis();

  /* Variables temporaires juste pour les calculs => Pas besoin d'avoir des variables globales pour ça*/
  float flowRate = ((1000.0 / (millis() - oldTime)) * pulseCount) / calibrationFactor;
  float flowMilliLitres = (flowRate / 60) *1000;

  /* Mise à jour de notre variable de stockage ( variable statique ) */
  totalMilliLitres += flowMilliLitres;

  /* Remise à zero des outils de calculs ( variable statique + globale volatile)*/
  oldTime = millis();
  pulseCount = 0;

  /* Retour du résultat*/
  return totalMilliLitres;
}

void pulseCounter() {
  /* Incremente pulseCount*/
  pulseCount++;
}


void setWaterPump(bool etat) {
  if ( etat == false ) {
    digitalWrite(RelayPin,false);
    Serial.println("pompe Off");
 }
 else {
    digitalWrite(RelayPin,true);
    
    Serial.println("pompe On");
  }
}
void loop() {
 
    static uint32_t totalMilliLitres=0 ;
    static uint32_t lastAffiche = millis (); // Variable statique initialisée que la première fois ...
    static bool etatPompe = false;
    uint16_t rawHumidity = getRawHumidity();
    uint8_t percentHumidity = getPercentHumidity(rawHumidity);
    uint8_t lireHumidity = getPercentHumidity(rawHumidity);
    uint8_t mlValue;
    uint16_t attente ;
    uint8_t seuil=30;
    setWater(  mlValue) ;
    Arrosage(seuil,lireHumidity,percentHumidity);
  if( millis() - lastAffiche > tempsEntreDeuxAffichages ) {
    Serial.print("Raw Humidity value: ");
    Serial.print(rawHumidity);
    Serial.print("\t");
    Serial.print("Percentage: ");
    Serial.print(percentHumidity);
    Serial.println("%");
    Serial.print("Output Liquid Quantity: ");
    Serial.print(water_read ());
    Serial.println("mL");
    lastAffiche = millis ();
    
  }

}

 void setWater( uint8_t mlValue) {
   uint16_t mlReference = water_read();// on note la quantité en ml qui était déjà arrosée avant de commencer
   bool etatPompe = false; // Pompe Off par défaut
   setWaterPump(true); // on allume la pompe
   Serial.println("Arrosage en cours");
   while(water_read() < mlReference + mlValue  ) {
      // On ne fait rien en attendant que le dosage d'eau soit ok
   }
   Serial.println("dosage eau ok");
   
   setWaterPump(false);// on éteind la pompe quand le dosage est ok    
}
 
void attendre(uint16_t attente) {    // temps d'attente en secondes
   uint16_t timeReference = millis();// temps avant de commencer
   Serial.println("on attend");
   while (millis() - timeReference <= attente * 1000) {
      // On ne fait rien en attendant
   }
   Serial.println("Fin d'attente");
}
    
 void Arrosage(uint8_t seuil,uint8_t lireHumidity,uint8_t percentHumidity){
       percentHumidity = lireHumidity ;
   if ( percentHumidity < seuil ) {
         setWater(10);//(x ml)
         attendre(30);//attendre
         percentHumidity = lireHumidity ;
  }
    
   if ( percentHumidity > seuil ){
          
      Serial.println("Arrosage terminé avec succès");    
  }
   else {
    
       Serial.println("Echec d'arrosage");
  }
}     
 
   
      
 
 
 


#54 Mike118

Mike118

    Staff Robot Maker

  • Administrateur
  • PipPipPipPipPip
  • 9 969 messages
  • Gender:Male
  • Location:Anglet

Posté 02 avril 2020 - 05:46

alors non en effet c'était peut être pas très clair mais " lire Humidité " c'est faire appel aux fonctions que tu as faites et qui te retournent un nouveau pourcentage d'humidité. Il ne s'agit pas d'un paramètre à mettre dans ta fonction. 
 

tu peux faire ça de cette façon : 


    uint8_t percentHumidity = getPercentHumidity(getRawHumidity());

Ensuite je vois encore plein de choses inutiles dans ton programme... Donc essaye d'en éliminer ! :P Plus il va y avoir de choses dans ton programme plus tu vas avoir du mal à avoir une vue d'ensemble...  Je pense qu'il y a  trop de choses dans ton loop ... à la limite on pourrait faire une fonction d'affichage des informations ... Pourquoi mets tu un setWater dans ton loop ?  qui en plus se fait sur un mlValue qui n'est pas défini ? 

Bref en plus de corriger la fonction arrosage il faut que tu épures ton loop =) 

 


 


Si mon commentaire vous a plus laissez nous un avis  !  :thank_you:

Nouveau sur Robot Maker ? 

Jetez un oeil aux blogs, aux tutoriels, aux ouvrages, au robotscope  aux articles,  à la boutique  et aux différents services disponible !
En attendant qu'une bibliothèque de fichiers 3D soit mise en place n'hésitez pas à demander si vous avez besoin du fichier 3D d'un des produits de la boutique... On l'a peut être ! 
Si vous souhaitez un robot pilotable par internet n'hésitez pas à visiter www.vigibot.com et à lire le sous forum dédié à vigibot!

 

Les réalisations de Mike118  

 

 

 


#55 michel

michel

    Habitué

  • Membres
  • PipPip
  • 179 messages
  • Gender:Male
  • Location:nice

Posté 03 avril 2020 - 02:19

bonjour Mike118,

j'ai fait les rectificatif au code .

il n'y a plus le battement du relais , tout ce passe bien sauf si le soil_moisture est < au seuil pour le second arrosage le relais ne se décolle pas .

sinon tout est ok .

j'ai fait une fonction affichage Serial .

Je te remet le code en entier.

 

 
/*Soil Moisture*/
const uint8_t  sensor_MoisturePin =  A0;
const uint32_t tempsEntreDeuxAffichages = 1000;// Temps en ms
float flowRate;
/*Relay Pompe Arrosage*/
const uint8_t RelayPin = A2;

/* Capteur de débit d'eau*/
const uint8_t sensorInterrupt = 0;
const uint8_t sensorPin       = 2;
const float calibrationFactor = 98;//4.5

/* Variables volatiles utilisées dans l'interruption pour le débit d'eau = une des rares variables qu'on a le droit d'avoir en globale*/
  volatile uint8_t pulseCount = 0;

void setup() {
    Serial.begin(9600);
    /* Init SoilMoisture*/
    pinMode(sensor_MoisturePin,INPUT);
    /* Init Relay Pumpe  */
    pinMode(RelayPin, OUTPUT);
    /* initialisation du capteur de pompe*/
    water_setup ();
    
}

uint16_t getRawHumidity(){
/* Variables Arrosage*/
    uint16_t rawHumidity = analogRead(sensor_MoisturePin);
    return rawHumidity;
}

uint8_t getPercentHumidity(uint16_t rawHumidity){
    if(rawHumidity > 1023)
     rawHumidity = 1023;
    uint8_t percentHumidity = map(rawHumidity, 0, 1023, 0, 100);
    return percentHumidity;
}
void water_setup () {
  pinMode(sensorPin, INPUT);
  digitalWrite(sensorPin, HIGH);
  pulseCount = 0;
  attachInterrupt(sensorInterrupt, pulseCounter, FALLING);
}
/* fonction qui lit stock en interne et retourne le résultat */
  uint32_t water_read () {
  /* Les variables statiques sont des variables qui ne sont pas écrasée, ça permet d'éviter d'utiliser des variables globales*/
  static uint32_t totalMilliLitres = 0;
  static uint32_t oldTime = millis();

  /* Variables temporaires juste pour les calculs => Pas besoin d'avoir des variables globales pour ça*/
  float flowRate = ((1000.0 / (millis() - oldTime)) * pulseCount) / calibrationFactor;
  float flowMilliLitres = (flowRate / 60) *1000;

  /* Mise à jour de notre variable de stockage ( variable statique ) */
  totalMilliLitres += flowMilliLitres;

  /* Remise à zero des outils de calculs ( variable statique + globale volatile)*/
  oldTime = millis();
  pulseCount = 0;

  /* Retour du résultat*/
  return totalMilliLitres;
}

void pulseCounter() {
  /* Incremente pulseCount*/
    pulseCount++;
}


void setWaterPump(bool etat) {
  if ( etat == false ) {
    digitalWrite(RelayPin,false);
    Serial.println("pompe Off");
 }
 else {
    digitalWrite(RelayPin,true);
    Serial.println("pompe On");
  }
}
void loop() {
    uint8_t seuil=30;
    uint16_t rawHumidity = getRawHumidity();
    uint8_t percentHumidity = getPercentHumidity(rawHumidity);
    affichage();//affichage Serial
    Arrosage(seuil,percentHumidity);
    
       
    
}
void affichage() {
   static uint32_t lastAffiche = millis (); // Variable statique initialisée que la première fois ...   
   if( millis() - lastAffiche > tempsEntreDeuxAffichages ) {
    uint16_t rawHumidity = getRawHumidity();
    uint8_t percentHumidity = getPercentHumidity(rawHumidity);
    Serial.print("Raw Humidity value: ");
    Serial.print(rawHumidity);
    Serial.print("\t");
    Serial.print("Percentage: ");
    Serial.print(percentHumidity);
    Serial.println("%");
    Serial.print("Output Liquid Quantity: ");
    Serial.print(water_read ());
    Serial.println("mL");
    lastAffiche = millis ();
    
  }

}
  void setWater( uint8_t mlValue) {
   uint16_t mlReference = water_read();// on note la quantité en ml qui était déjà arrosée avant de commencer
   bool etatPompe = false; // Pompe Off par défaut
   setWaterPump(true); // on allume la pompe
   Serial.println("Arrosage en cours");
   while(water_read() < mlReference + mlValue  ) {
      // On ne fait rien en attendant que le dosage d'eau soit ok
   }
   Serial.println("dosage eau ok");
   
   setWaterPump(false);// on éteind la pompe quand le dosage est ok    
}
 
void attendre(uint16_t attente) {    // temps d'attente en secondes
   uint16_t timeReference = millis();// temps avant de commencer
   Serial.println("on attend");
   while (millis() - timeReference <= attente * 1000) {
      // On ne fait rien en attendant
   }
   Serial.println("Fin d'attente");
}
    
 void Arrosage(uint8_t seuil,uint8_t percentHumidity){
       percentHumidity = getPercentHumidity(getRawHumidity());
   if ( percentHumidity < seuil ) {
         setWater(10);//(x ml)
         attendre(30);//attendre
       percentHumidity = getPercentHumidity(getRawHumidity());
         
   }
   if ( percentHumidity > seuil ){
        Serial.println("Arrosage terminé avec succès");    
  }
   else {
         Serial.println("Echec d'arrosage");
  }
}     
 
   
      
 
   

 
 
 
 
      
 
   

 

#56 Sandro

Sandro

    Pilier du forum

  • Modérateur
  • PipPipPipPipPip
  • 1 262 messages
  • Gender:Male

Posté 03 avril 2020 - 03:43

Bonjour,

tout d'abord, ça ne fait aucun sens de passer percentHumidity en argument à Arrosage pour le recalculer dessuite après dans la fonction : soit tu le passe en argument, soit tu le calculs au début, mais pas les deux.

 

 

Pour ton erreur si aux premier arrosage il n'y a pas eut assez d'eau, avec les informations que tu me donnes, je n'arrive pas à deviner ce qui se passe. Mais c'est pas grave, il est temps que tu essaye de trouver tes erreurs toi même dans la mesure du possible. Du coup, je vais te donner quelques tests à faire, et tu pourra essayer de voir si avec ça tu trouve l'erreur (et au pire, tu nous donnera ces infos, ce qui pourra nous aider) :

- regarde attentivement la sortie du serial monitor : tu as quoi? Deux fois "Echec d'arrosage" (une fois pour le premier arrosage, et une fois pour le second?)

- ajoute en début de fonction (si tu enlève la ligne "percentHumidity = getPercentHumidity(getRawHumidity());") ou juste après celle-ci (si tu enlèves percetHumidity comme argument) : ajoute un Serial.print pour indiquer la valeur de l'humidité, ça permettra de savoir si elle est effectivement sous le seuil ou pas).

- regarde en particulier si tu ne serais pas sur le cas particulier où l'humidité=seuil, ou tu n'arroses pas mais que tu écris quand même que c'est un échec (nb : tu devrais mettre un <= ou un >= pour l'un de tes if)


Aidez-nous à vous aider : partagez toutes les informations pertinentes : description précise du problème, contexte, schéma de câblage, liens vers la documentation des composants, votre code (ou encore mieux un code minimal reproduisant le bug), ...

Vous recevrez ainsi plus de réponses, et elles seront plus pertinentes.


#57 michel

michel

    Habitué

  • Membres
  • PipPip
  • 179 messages
  • Gender:Male
  • Location:nice

Posté 03 avril 2020 - 05:01

bonjour Sandro,

merci pour ton aide voila les résultats .

au démarrage de la carte soil_moisture dans l'eau .

Serial port = arrosage avec succés

soil_moisture hors de l'eau .

Serial port = Pompe On ,arrosage en cours .

flow water tourne avec l'eau = dosage eau ok , Pompe Off, on attend , fin d'attente échec d'arrosage ,raw humidity 0 percentage 0%

Pompe On arrosage en cours

flow water tourne avec l'eau = la ça ne comptabilise plus

comme tu peux le voir j'ai mis seuil >= mais ça ne change rien .

pour ne pas avoir l'echec arrosage il faut mettre .

else if  ( percentHumidity >= seuil ){
    
        Serial.println("Arrosage terminé avec succès");    
  }
   else {
         Serial.println("Echec d'arrosage");
  }
}    

mais ça change rien au deuxiéme arrosage avec soil_moisture hors de l'eau il n'y a plus de comptage .

j’espère avoir étais utile .

merci bonne soirée .

void Arrosage(uint8_t seuil){
       uint8_t percentHumidity = getPercentHumidity(getRawHumidity());
       
   if ( percentHumidity < seuil ) {
         setWater(10);//(x ml)
         attendre(30);//attendre
       percentHumidity = getPercentHumidity(getRawHumidity());
         
   }
      
    if ( percentHumidity >= seuil ){
    
        Serial.println("Arrosage terminé avec succès");    
  }
   else {
         Serial.println("Echec d'arrosage");
  }
}     
 


#58 Sandro

Sandro

    Pilier du forum

  • Modérateur
  • PipPipPipPipPip
  • 1 262 messages
  • Gender:Male

Posté 03 avril 2020 - 06:35

Bonsoir,

je crois que tu as raté deux points dans mon message précédent :

1) Je te demandais de mettre un Serial.print juste après "uint8_t percentHumidity = getPercentHumidity(getRawHumidity());" pour savoir quel est l'humidité mesurée (d'ailleurs, en mettre un en plus juste avant "if ( percentHumidity >= seuil ){" serait pas mal, à condition de rajouter un petit texte pour le distinguer de l'autre)

2) Je te demandais, une fois que tu as les résultats, de d'abord essayer de comprendre par toi même

 

 

Une dernière question : qu'entends tu par "comptage"?


Aidez-nous à vous aider : partagez toutes les informations pertinentes : description précise du problème, contexte, schéma de câblage, liens vers la documentation des composants, votre code (ou encore mieux un code minimal reproduisant le bug), ...

Vous recevrez ainsi plus de réponses, et elles seront plus pertinentes.


#59 Mike118

Mike118

    Staff Robot Maker

  • Administrateur
  • PipPipPipPipPip
  • 9 969 messages
  • Gender:Male
  • Location:Anglet

Posté 04 avril 2020 - 02:01

déjà je te propose cette modification : 

 

void Arrosage(uint8_t seuil){
   uint8_t percentHumidity = getPercentHumidity(getRawHumidity());
       
   if ( percentHumidity < seuil ) {
         setWater(10);//(x ml)
         attendre(30);//attendre

         percentHumidity = getPercentHumidity(getRawHumidity());
         if ( percentHumidity >= seuil ) {
           Serial.println("Arrosage terminé avec succès");   
         } else {
           Serial.println("Echec d'arrosage");
         }
   } else {
         Serial.println("Pas besoin d'arroser");
   }
}  

et enlève le " float flowRate; "  qui sert à rien tout en haut de ton code

N'hésite pas à coller ce qui est affiché dans ton moniteur série ... 

 

Autre remarque petite alternative, mais là c'est une question de préférence ... tu aurais pu faire une fonction affiche qui ne fait que afficher et pas " attendre " ... 
et du coup le loop serait aussi un peu différent : 

 

void affichage() {
    uint16_t rawHumidity = getRawHumidity();
    uint8_t percentHumidity = getPercentHumidity(rawHumidity);
    Serial.print("Raw Humidity value: ");
    Serial.print(rawHumidity);
    Serial.print("\t");
    Serial.print("Percentage: ");
    Serial.print(percentHumidity);
    Serial.println("%");
    Serial.print("Output Liquid Quantity: ");
    Serial.print(water_read ());
    Serial.println("mL");
}

void loop() {
    affichage();      //affichage des constantes sur le serial
    Arrosage(30);     // arroser si humidité <30%
    attendre(1);   // attendre 1s   
}

Pour le reste je n'ai pas bien compris le problème rencontré ... Il est important que tu arrives à identifier quelle est la fonction qui ne marche pas comme prévu. 
Maintenant que le code est clairement découpé en fonction chasser un problème et plus facile =) 


Si mon commentaire vous a plus laissez nous un avis  !  :thank_you:

Nouveau sur Robot Maker ? 

Jetez un oeil aux blogs, aux tutoriels, aux ouvrages, au robotscope  aux articles,  à la boutique  et aux différents services disponible !
En attendant qu'une bibliothèque de fichiers 3D soit mise en place n'hésitez pas à demander si vous avez besoin du fichier 3D d'un des produits de la boutique... On l'a peut être ! 
Si vous souhaitez un robot pilotable par internet n'hésitez pas à visiter www.vigibot.com et à lire le sous forum dédié à vigibot!

 

Les réalisations de Mike118  

 

 

 


#60 michel

michel

    Habitué

  • Membres
  • PipPip
  • 179 messages
  • Gender:Male
  • Location:nice

Posté 04 avril 2020 - 02:39

bonjour Mike118,

le problème c'est le deuxième arrosage si le premier n'es pas suffisant .

le flow water ne coupe plus le relais .

je te joint le Serial.print .

[attachment=11455:IMG_1708.JPG]

MERCI de ton aide .






0 utilisateur(s) li(sen)t ce sujet

0 members, 0 guests, 0 anonymous users