Go Down

Topic: Re: Capteur pour plantes vertes - WIP - Les codes et pb d'alim (Read 7720 times) previous topic - next topic

pixelgarden

Ensuite le serveur arduino :

Code: [Select]


//***********************************************************************************************************/
// Programme du Serveur BambooProbe Humidité du sol, humidité de l'air, température de l'air et Luminosité
//
// Code inspiré de http://geeklaboratories.com/408-comment-monitorer-le-climat-de-son-domicile-avec-arduino
//
// Shield Ethernet, nRF24L01+, led Temoin d'alerte secheresse
//
// David M - plantesvertes.net
//***********************************************************************************************************/

//La bibliothèque gérant les connexions SPI
#include <SPI.h>

//La bibliothèque gérant les nrf24L01+
#include <Mirf.h>
#include <nRF24L01.h>
#include <MirfHardwareSpiDriver.h>

//La bibliothèque gérant le serveur sur Ethernet
#include <Ethernet.h>

//L'adresse MAC du shield Ethernet
byte mac[] = { ici votre adresse mac du shield ethernet };

//L'objet contenant le serveur écoutant sur le port 80
EthernetServer server(80);

//L'adresse FIXE sur laquelle le serveur écoute
IPAddress ip(ici l ip du shield ethernet);

//Les dernières valeurs des capteurs
int lastTemp = 0;
int lastHumi = 0;
int lastSol = 0;
int lastSolGood = 0;
int lastLight = 0;
int lastSecheresse = 0;
int Secheresse =0;
int PinLed=6;    //LED témoin de seuil de  sécheresse

//Les valeurs des capteurs ont-elles changé depuis le dernier envoi de données via Ethernet ?
boolean valuesHaveChanged = false;

void setup()
{
  //On initie la connexion Série (via USB)
  Serial.begin(9600);
  Serial.println("Démarrage du capteur.");

  /*
   * On initialise le nrf24L01
   */
  Mirf.spi = &MirfHardwareSpi;
  Mirf.init();
  Mirf.setRADDR((byte *)"serv0");//Le nom du serveur dans le réseau d'émetteurs-recepteurs.
  Mirf.payload = 12;//La longueur d'un paquet exprimée en octets
  Mirf.config();

  Serial.println( "nRF24L01+ initialise!" );
   
  //On démarre le serveur en lui fournissant une adresse MAC et une IP
  Ethernet.begin(mac, ip);
  server.begin();
   
  //On affiche l'ip du serveur de manière à voir si tout va bien
  Serial.print("Adresse du serveur obtenue sans DHCP: ");
  Serial.println(Ethernet.localIP());
}


void loop()
{
   
     
  //On récupère une connexion entrante sur le serveur web, si une se présente
  EthernetClient client = server.available();
   
  //Si des données sont disponibles via les ondes (nrf24L01+)
  if(Mirf.dataReady())
  {
    //On crée le tableau qui va contenir les données
    byte datas[6];
     
    //On récupère et place les données dans le tableau
    Mirf.getData(datas);
     
    //On les affiche via le port série pour débugger
    Serial.print("Temp:");
    Serial.println(datas[1]);
    Serial.print("Humi:");
    Serial.println(datas[2]);
    Serial.print("Sol:");
    Serial.println(datas[3]);
    Serial.print("Light:");
    Serial.println(datas[4]);
    Serial.print("Secheresse:");
    Serial.println(datas[5]);
   
    /* Si le serveur detecte un seuil de secheresse a 1 on allume la led d'alerte */
      int Secheresse = (datas[5]);
      Serial.print(Secheresse);
    if (Secheresse==1) // si le capteur est au sec (valeur 1 numerique)
        {
            digitalWrite(PinLed, HIGH);   // LED allumée
        }
          else {
        digitalWrite(PinLed, LOW);   // LED off car tout vas bien
           }
   
     
    //On les stocke afin de pouvoir les renvoyer
    lastTemp = datas[1];
    lastHumi = datas[2];
    lastSol = datas[3];
    lastSolGood = lastSol*4;
    lastLight = datas[4]; 
    lastSecheresse = datas[5];   
    //On indique au programme que les valeurs ont changés et qu'il y a donc des choses à renvoyer
    valuesHaveChanged = true;
  }
 
 
   
  //Si on recupéré un client sur le serv' web
  if (client)
  {
    Serial.println("Nouveau client");

    boolean currentLineIsBlank = true;
     
    //Tant que le client est connecté
    while (client.connected())
    {
      //Tant qu'on a pas fini de lire sa requête
      if (client.available())
      {
        //On lit un octet de la requete du client et on l'affiche sur le port série
        char c = client.read();
        Serial.write(c);
         
        //Si on est face à un saut de ligne et que la ligne actuelle est déjà vide
        if (c == '\n' && currentLineIsBlank)
        {
          //On répond à la requête avec nos données
          client.println("HTTP/1.1 200 OK");//Code 200 = Tout s'est bien déroulé
          client.println("Content-Type: application/xml");//On spécifie le MIME-TYPE des données qu'on envoit (XML)
          client.println("Connection: close");
          client.println();
         
          client.println("<?xml version=\"1.0\"?>");//Entête du document XML
           
          //L'element racine du document XML
          client.println("<sensors>");
           
          //On parcours tout nos capteurs
          for (int i = 0; i < 1; i++)
          {
            //On crée un élement correspondant à chaque capteur
            client.print("<sensor name=\"sns");
            client.print(i);//Id du capteur
            client.println("\">");
             
            //On crée un élément enfant contenant les valeurs de température
            client.print("<temperature>");
            //Si les valeurs de capteurs ont changé, on les envoit
            if(valuesHaveChanged)
              client.print(lastTemp);
            //Sinon on renvoit une chaine non-numérique
            else
              client.print("NaN");
            client.println("</temperature>");
             
            //On créé un élément enfant contenant les valeurs d'humidité
            client.print("<humidity>");
            //Si les données ont changé, on les envoit
            if(valuesHaveChanged)
              client.print(lastHumi);
            //Sinon on renvoit une chaine non-numérique
            else
              client.print("NaN");
            client.println("</humidity>");
           
            //******
           
            //On créé un élément enfant contenant les valeurs d'humidité du sol
            client.print("<Sol>");
            //Si les données ont changé, on les envoit
            if(valuesHaveChanged)
              client.print(lastSolGood);
            //Sinon on renvoit une chaine non-numérique
            else
              client.print("NaN");
            client.println("</Sol>");
           
              //On créé un élément enfant contenant les valeurs de lumiere
            client.print("<Light>");
            //Si les données ont changé, on les envoit
            if(valuesHaveChanged)
              client.print(lastLight);
            //Sinon on renvoit une chaine non-numérique
            else
              client.print("NaN");
            client.println("</Light>");
             
            client.println("</sensor>"); 
          }
           
          //On ferme l'élement racine
          client.println("</sensors>");
          break;
        }
         
        //Si on saute une ligne
        if (c == '\n')
        {
          //C'est qu'on démarre une nouvelle ligne
          currentLineIsBlank = true;
        }
        else if (c != '\r')
        {
          //On a un caractère sur la ligne courante, elle n'est pas vide
          currentLineIsBlank = false;
        }
      }
    }
    //On laisse au navigateur client le temps de récuperer les données
    delay(1);
     
    //On déconnecte le client
    client.stop();
    Serial.println("client deconnecte");
  }
 

}

pixelgarden

On continue avec le code php du cron qui doit etre lancé a intervalle régulier. Chez moi toute les heures.

Code: [Select]

<meta charset="utf-8">
<table>
    <tr>
        <th>Nom du capteur: </th>
        <th>Température: </th>
        <th>Hygrométrie: </th>
        <th>Hygrométrie sol: </th>
    </tr>
<?php
//On désactive l'affichage des erreurs, car les erreurs PDO renvoit le nom d'utilisateur et le mot de passe
error_reporting(0);
 
//On crée l'objet gérant la base de données
$usr "ici votre login BDD";
$pass "et la votre pasword BDD";

$bdd = new PDO('mysql:dbname=ici le nom de la BDD;host=localhost'$usr$pass);
 
//Le temps du serveur formatté en javascript (nombre de millisecondes depuis le 1er Janvier 1970)
$temps time()*1000 3600*1000;
 
//On récupère le document XML généré par l'Arduino
$doc simplexml_load_file('http://ici l ip sur serveur arduino:et son port souvent 80');//Doit correspondre à l'adresse de l'Ethernet Shield
 
//On boucle sur tous les éléments du document XML
foreach($doc as $elem)
{
    
//On récupére les attributs de l'élement notamment le nom du capteur
    
$attributes $elem->attributes();
    
$name $attributes["name"];
     
    
//On récupère les valeurs des capteurs (température/humidité)
    
$enfants $elem->children();
    
$temp $enfants[0];
    
$hygro $enfants[1];
$hSol $enfants[2];
     
    
//On prépare la requete avec les bons paramètres
    
$requete $bdd->prepare("INSERT INTO graph_tbl(`id`, `nomCapteur`, `temperature`, `humidity`, `sol`, `date`) VALUES (NULL, :nom, :temp, :humi, :lesol, :time);");
     
    
//On execute la requête en lui passant les données qui vont bien
    
$etat $requete->execute(array("nom" => $name,
                                    
"temp" => $temp,
                                    
"humi" => $hygro,
"lesol" => $hSol,
                                    
"time" => $temps));
     
    
//Si la requête s'est bien déroulée
    
if($etat)
        echo 
"OK";
    else
        echo 
"Fail";
     
    
//On affiche l'état des capteurs (pour debug)
    
echo "<tr><td>".$name."</td><td>".$temp."</td><td>".$hygro."</td><td>".$hSol."</td></tr>";
}
?>

</table>

pixelgarden

Et on termine par le code d'affichage :

Code: [Select]

<?php
//Connexion a la base de données
// Remplacez localhost, highcharts, username, password, par vos informations de connexion.
$hostname "localhost";
$database "ici le nom de la BDD";
$username "ici le login bdd";
$password "ici le pasword BDD";


$Conn mysql_pconnect($hostname$username$password);  
?>

<html>
<head>
<title>Falaf.net - Highstock Exemple 2</title>
<!-- Chargement des librairies: Jquery & highcharts -->
<script type="text/javascript" src="http://ajax.googleapis.com/ajax/libs/jquery/1.8.2/jquery.min.js"></script>
<script type="text/javascript" src="js/highstock.js" ></script>
<script type="text/javascript" src="js/themes/gray.js" ></script>
<script type="text/javascript" src="js/modules/exporting.js" ></script>
<!-- Chargement des traductions -->
<script type="text/javascript" src="js/options.js"></script>
<!-- Chargement des variables, et paramètres de Highcharts -->
    <script type="text/javascript">
$(function() {
        // Ici commence le code pour le premier graphique
// Ce graphique à pour nom: container_chart_un
        $('#container_chart_un').highcharts('StockChart', {

            rangeSelector : {
            buttons: [
                                {type: 'day',count: 1,text: '1j'},
                                {type: 'day',count: 3,text: '3j'},
                                {type: 'day',count: 7,text: '7j'},
                                {type: 'month',count: 1,text: '1m'},
                                {type: 'year',count: 1,text: '1a'},
                                {type: 'all',text: 'Tout'}],
                selected : 5
            },
            legend:
            {
                verticalAlign: 'top',
                floating : false,
                y: 25,
                enabled: true
            },
            yAxis: {
                title: {
                    text: 'temperature (°)'
                }
            },
            tooltip: {
                shared: true,
                //Ajout d'une unité de mesure lors du survole d'un point du graphique
                valueSuffix: ' °'
            },   
            title : {
                text : 'Temperature'
            },

series: [
<?php
mysql_select_db
($database$Conn);
 
// Dans la ligne ci-dessous, modifiez sonde_1, par le nom de votre première sonde
 
$query_info "SELECT ftimestamp, temperature FROM `graph_tbl` WHERE  `nomCapteur` LIKE  'sns0' ORDER BY ftimestamp ASC";
$info mysql_query($query_info$Conn);
$row_info mysql_fetch_assoc($info);
$totalRows_info mysql_num_rows($info);
?>

{

// Dans la ligne ci-dessous, modifiez name, par le nom de votre courbe. (Exemple: Température, pression, etc.)
                name: 'Température',
                data: [<?php do { ?>
[Date.UTC(<?php echo date("Y"strtotime("".$row_info['ftimestamp'])).", ".(date("m"strtotime("".$row_info['ftimestamp'])) - 1).", ".date("d, H, i"strtotime("".$row_info['ftimestamp'])); ?>), <?php echo $row_info['temperature']; ?>],
<?php } while ($row_info mysql_fetch_assoc($info)); ?>],
            },
            ]
        });
//Ici se termine le code pour le premier graphique

// Ici commence le code pour le second graphique
// Ce second graphique à pour nom: container_chart_deux
        $('#container_chart_deux').highcharts('StockChart', {

            rangeSelector : {
            buttons: [
                                {type: 'day',count: 1,text: '1j'},
                                {type: 'day',count: 3,text: '3j'},
                                {type: 'day',count: 7,text: '7j'},
                                {type: 'month',count: 1,text: '1m'},
                                {type: 'year',count: 1,text: '1a'},
                                {type: 'all',text: 'Tout'}],
                selected : 5
            },
            legend:
            {
                verticalAlign: 'top',
                floating : false,
                y: 25,
                enabled: true
            },
            yAxis: {
                title: {
                    text: 'humidité (%)'
                }
            },
            tooltip: {
                shared: true,
                //Ajout d'une unité de mesure lors du survole d'un point du graphique
                valueSuffix: ' %'
            },   
            title : {
                text : 'humiditée air'
            },

series: [
<?php
mysql_select_db
($database$Conn);
 
// Dans la ligne ci-dessous, modifiez sonde_2, par le nom de votre deuxième sonde
 
$query_info "SELECT ftimestamp, humidity FROM `graph_tbl` WHERE  `nomCapteur` LIKE  'sns0' ORDER BY ftimestamp ASC";
$info mysql_query($query_info$Conn);
$row_info mysql_fetch_assoc($info);
$totalRows_info mysql_num_rows($info);
?>

{

// Dans la ligne ci-dessous, modifiez name, par le nom de votre courbe. (Exemple: Température, pression, etc.)
                name: 'Humidité Air',
                data: [<?php do { ?>
[Date.UTC(<?php echo date("Y"strtotime("".$row_info['ftimestamp'])).", ".(date("m"strtotime("".$row_info['ftimestamp'])) - 1).", ".date("d, H, i"strtotime("".$row_info['ftimestamp'])); ?>), <?php echo $row_info['humidity']; ?>],
<?php } while ($row_info mysql_fetch_assoc($info)); ?>],
            },]
        });
//Ici se termine le code pour le second graphique



//Ajoutez ici le code pour les nouveaux graphiques
// Ici commence le code pour le second graphique
// Ce second graphique à pour nom: container_chart_trois
        $('#container_chart_trois').highcharts('StockChart', {

            rangeSelector : {
            buttons: [
                                {type: 'day',count: 1,text: '1j'},
                                {type: 'day',count: 3,text: '3j'},
                                {type: 'day',count: 7,text: '7j'},
                                {type: 'month',count: 1,text: '1m'},
                                {type: 'year',count: 1,text: '1a'},
                                {type: 'all',text: 'Tout'}],
                selected : 5
            },
            legend:
            {
                verticalAlign: 'top',
                floating : false,
                y: 25,
                enabled: true
            },
            yAxis: {
                title: {
                    text: 'sol '
                }
            },
            tooltip: {
                shared: true,
                //Ajout d'une unité de mesure lors du survole d'un point du graphique
                valueSuffix: ' /1024'
            },   
            title : {
                text : 'humiditée du sol'
            },

series: [
<?php
mysql_select_db
($database$Conn);
 
// Dans la ligne ci-dessous, modifiez sonde_2, par le nom de votre deuxième sonde
 
$query_info "SELECT ftimestamp, sol FROM `graph_tbl` WHERE  `nomCapteur` LIKE  'sns0' ORDER BY ftimestamp ASC";
$info mysql_query($query_info$Conn);
$row_info mysql_fetch_assoc($info);
$totalRows_info mysql_num_rows($info);
?>

{

// Dans la ligne ci-dessous, modifiez name, par le nom de votre courbe. (Exemple: Température, pression, etc.)
                name: 'Humidité du sol',
                data: [<?php do { ?>
[Date.UTC(<?php echo date("Y"strtotime("".$row_info['ftimestamp'])).", ".(date("m"strtotime("".$row_info['ftimestamp'])) - 1).", ".date("d, H, i"strtotime("".$row_info['ftimestamp'])); ?>), <?php echo $row_info['sol']; ?>],
<?php } while ($row_info mysql_fetch_assoc($info)); ?>],
            },]
        });
//Ici se termine le code pour le second graphique

// Fin du code pour Highstock
});

        </script>
</head>

<body style="background:#000;">
    <p></p>
    <p>
<!-- Affichage des graphiques -->
    <div id="container_chart_un" class="Tableau"></div>
    <div id="container_chart_deux" class="Tableau"></div>
<div id="container_chart_trois" class="Tableau"></div></p>
<div align="center">
    <p><a href="http://www.falaf.net">© Falaf.net</a></p>
    </div>

<style>

body {background:#000;}
.Tableau
{width:49%; height:400px; display:inline-block; margin-bottom:2%
}
</style>
</body>
</html>

pixelgarden

Ce qui donne au final :


Bon donc tout marche plutot bien... mais il y un mais !!

Gros gros probleme d'alimentation sur la partie capteur.
Pour le moment j'utilise un uno pour le proto (ensuite je passe sur mini pro) et j'alimente avec un pile 9V.
J'ai fait un test avec un envoi de donnée toute les 5 secondes pour voir la décharge de la pile... en 4 h c'etait terminé !!
Bon bien sur au final le delais sera plus long (45mn a priori).

En fait le plus gros probleme, je pense, est la sonde d'humidité du sol qui est en 5V et qui a une led allumé en permanence.
Du coups j'ai ajouté une librairy sleep mais je ne suis pas certain que cela marche vraiment... la led reste allumé deja, et qund je test je vois toujours 5v sur ma breadboad...

Il y a toujours la solus d'un lipo mais ce n'est pas vraiment economique.

peut etre voyez vous une solus ??

Merci d'avance.

Artouste


...
En fait le plus gros probleme, je pense, est la sonde d'humidité du sol qui est en 5V et qui a une led allumé en permanence.
Du coups j'ai ajouté une librairy sleep mais je ne suis pas certain que cela marche vraiment... la led reste allumé deja, et qund je test je vois toujours 5v sur ma breadboad...

Il y a toujours la solus d'un lipo mais ce n'est pas vraiment economique.

peut etre voyez vous une solus ??

Merci d'avance.

bonjour
ref de ta sonde ?
une peut etre solution , l'alimenter juste "un peu avant" la mesure et couper ensuite
un petit BS170 doit surement faire l'affaire

pixelgarden

la sonde est celle la :http://letmeknow.fr/shop/capteurs/16-capteur-hygrometrie.html basé sur un LM393.

comment alimenter et couper l alim ? comme pour un led ? Ca peut regler mon probleme !!

Merci


Artouste

#21
Aug 31, 2014, 12:52 pm Last Edit: Aug 31, 2014, 12:59 pm by Artouste Reason: 1

la sonde est celle la :http://letmeknow.fr/shop/capteurs/16-capteur-hygrometrie.html basé sur un LM393.

comment alimenter et couper l alim ? comme pour un led ? Ca peut regler mon probleme !!

Merci



tu peux t'inspirer de ça ( commande bobine, ton pcb capteur à la place de la bobine)


fdufnews

Un truc a essayer. Supprimer les 2 LED sur le capteur et alimenter celui-ci par une broche de l'arduino. Le LM393 ne consomme pas grand chose à lui tout seul. Ainsi tu pilotes quand tu veux l'alimenter.
Le capteur fonctionne avec une alimentation comprise entre 3,3 et 5V donc cela devrait faire l'affaire. S'assurer quand même que le système n'est pas trop sensible à la qualité de la tension délivrée par un I/O.

derder9161

#23
Sep 01, 2014, 09:49 am Last Edit: Sep 01, 2014, 09:55 am by derder9161 Reason: 1
Bonjour,

Dans un premier temps félicitation pour ce superbe projet. L'esthétique est très soignée.

Pour économiser ton accu, voila quelques conseils :

Un lien vers la librairie power, qui permet de désactiver des étages du microcontrôleur pour quelques mA de consso en moins.
http://www.nongnu.org/avr-libc/user-manual/group__avr__power.html

Un lien vers la lib sleep et WDT :

http://www.nongnu.org/avr-libc/user-manual/group__avr__watchdog.html
http://www.nongnu.org/avr-libc/user-manual/group__avr__sleep.html

Ce sont les lib du micro, tu peux en trouver d'autres sur internet toute faite et prête à l'emploi. Celle la agisse dans un niveau plus bas.

Ce que je te conseil ( et je l'ai testé en pratique), c'est d'éteindre tout ce qui ne te sert à rien le maximum de tps et de ne l'activer qu'en cas d'utilisation prolongé.
Ensuite, si j'ai bien compris, tu souhaites envoyé de la data à intervalle régulier.
Rien de bien compliqué. Tu peux donc utiliser un timer avec la fonction sleep qui va bien pour réveiller ton micro à intervalle régulier. En comptant le nbr de réveil en fonction des réglages du timer, tu pourras envoyé tes données toutes les 5s (ex).

ça devrait te faire gagner quelques heures.

Mais ce ne sera pas encore assez j'imagine.

Quand je vois mes capteurs koubachi qui sont à 98% de batterie aprés ... heu ... 1 ans et demie voir 2 ans d'utilisation.
A mon avis c'est pas un accu de 9V type commerce.

Mais il y a encore une autre solution. Utiliser une carte en 3V3.
Mettre un petit panneau solaire, voir utilisé l'acidité du sol .... enfin bref  :)

En espérant t'aider

Bon courage

Edit : d'aprés ce site, mettre les entrées en "INPUT" réduirait aussi la consso général ! (reste à voir si par défaut ce n'est pas déjà le cas)

pixelgarden

Merci pour vos reponses.

je vais me pencher sur le BS170 et effectivement changer de lib sleep.

Je pense aussi virer les leds energivores.

Un truc que j'ai pas testé... et c'est idiot de ma part, passer de 5V a 3V sur le capteur d'humidité du sol.

Menfin au final il y a des chances que je passe sur un capteur solaire.


Go Up