ACTIVITÉ ARDUINO : Quelques systèmes « autonomes » avec carte SD et alimentation externe

Objectif : Réussir à faire des acquisitions sans liaison avec un ordinateur. Cela peut être utile dans certaines expériences, par exemple dans une enceinte fermée pour mesure de pression, ou à l’extérieur pour des mesures d’accélération sur une raquette de tennis, ou pour des mesures de force sur une pédale de vélo …

1. Shield carte SD pour Arduino

Le shield carte SD est une carte d’interface compatible Arduino permettant d’écrire les données directement sur une carte SD.

Il suffit de connecter ce shield directement sur la carte Arduino.

Shield carte SD pour Arduino TRU COMPONENTS

2. Choix de l’alimentation

Il y a plusieurs possibilités d’alimenter l’ensemble Carte Arduino/Shield carte SD si on veut se passer de liaison avec l’ordinateur.

a. Bloc d’alimentation secteur

Si les conditions de l’expérience permettent de brancher le système sur le secteur, il est possible d’utiliser un adaptateur secteur 9 ou 12 V.

Cet adaptateur se connecte sur la prise femelle jack DC 2,1 mm de la carte Arduino.

Le connecteur du bloc doit être un jack 2,1×5,5 mm, avec polarité positive au centre :

L’alimentation doit être suffisamment puissante, il serait confortable de choisir un adaptateur avec un courant maximal de 1 A à 2 A.

Quelques exemples d’adaptateurs dans le commerce :

b. Pile 9V

Pour avoir un système complètement autonome. on peut utiliser une pile 9V.

Pour connecter cette pile au connecteur DC 9 2,1 mm de la carte Arduino, voici un exemple de support de pile :

Support de pile 9 V pour carte Arduino disponible sur Conrad

c. Batterie LiPo

Une autre option pour avoir un système complètement autonome est d’utiliser une batterie LiPo .

Batterie LiPo disponible sur Conrad

Il faut relier respectivement les fils rouge et noir à l’Arduino sur les broches VIN et GND :

Attention :

Bien vérifier le branchement à plusieurs reprises avant de mettre sous tension. Il faut relier le fil + à la borne VIN et le fil – à une des broches GND.
Une erreur de branchement est fatale (j’en suis à une bonne demi douzaine de cartes Arduino HS à cause de trop de précipitation !).
La solution idéale serait d’associer une diode au fil rouge (voir schéma ci-dessus)

3. Programme Arduino

Pour communiquer avec la carte SD, nous allons utiliser la bibliothèque SD. Pour plus d’informations, cliquer sur sur ce lien.

Procédure d’installation des bibliothèques :

Dans l’application Arduino, à partir du menu [Croquis][Inclure une bibliothèque][Gérer les bibliothèques], rechercher et installer la bibliothèque «SD »

Code type à téléverser:

Voici le code de base à téléverser pour une acquisition sur A0. Il peut être utile d’appuyer sur le bouton reset de la carte Arduino pour lancer l’acquisition. Des données devraient apparaître sur la carte SD.

Pour lancer une nouvelle acquisition, il faudrait effacer les données du fichier créé ou simplement supprimer le fichier de la carte SD (directement sur l’ordinateur à la lecture de la carte SD). Une fois l’acquisition relancée, le fichier apparaîtra à nouveau avec de nouvelles données.

// Programme d'Arduino avec carte SD

#include <SPI.h>
#include <SD.h>



//Définition des broches analogiques utilisées par le capteur.

#define _NUMER0_BROCHE_ANALOGIQUE A0          //Broche analogique utilisée pour mesure entrée analogique A0
long temps;

File fichierSD;

//============================================================================================
// Procédure d'initialisation des périphériques
//==================================================================================================
void setup() {

  // Initialisation de la communication série avec le terminal à 9600 baud.
//  Serial.begin(9600);
  SD.begin(10);
//  //  Initialisation de la carte SD
    if(!SD.begin(10)) {
    return;
    }
  
}



//==================================================================================================
// Boucle principale Arduino.
//==================================================================================================
void loop() {
  fichierSD = SD.open("fichier.txt", FILE_WRITE);
  temps= millis();


  // Lecture de la valeur du capteur sur l'entree analogique. 
  // La valeur mesurée par le Convertisseur Analogique Numérique prend pour valeur 0 pour une tension de 0V et 1023 pour une tension de 5V.
  int valeurNumerique = analogRead(_NUMER0_BROCHE_ANALOGIQUE);
 
  
  //Affichage des résultats
   
    if(fichierSD) {
    
   //Ecriture
      fichierSD.print(temps);
  
    fichierSD.print("\t");
    fichierSD.print(valeurNumerique );
    fichierSD.println(""); 

    fichierSD.close();
  }


   
 
  
  delay(1000);                      // Délai en ms d'1s pour faciliter la visualisation.
}

Note :

Il peut arriver qu’aucune donnée n’apparaisse sur la carte SD quand la source d’alimentation manque de puissance.
Bien tester à l’avance l’efficacité de la pile/batterie en lançant une acquisition test.

3. Applications

Ci-dessous quelques exemples d’acquisition avec systèmes autonomes sans liaison série avec l’ordinateur

a. Mesure de force

Pour plus de précisions sur la mesure de force, vous pouvez consulter cet article

Code Arduino à téléverser:

#include "HX711.h"
#include <SPI.h>
#include <SD.h>
#include <Wire.h>
 HX711 capteur;
 int DAT = 3;
 int CLK = 2;
 long valeur;
 float valeur2;
 
long temps;
File fichierSD;

 void setup() {
//  pinMode(8,OUTPUT);
 //  digitalWrite(8,HIGH); // si on veut créer une alimentation 5V sur la broche 8 de la carte Arduino, pour la broche VDD de l'amplificateur
   capteur.begin(DAT, CLK);

   capteur.tare();
   delay(1000);
   //  Initialisation de la carte SD
    if(!SD.begin(10)) {

    return;
    }
    
 }
 void loop() {
   fichierSD = SD.open("force.txt", FILE_WRITE);
 
   temps = millis();
   valeur = capteur.get_value();
   valeur2 = 0.00234*valeur -0.328 ;


    if(fichierSD) {

   //Ecriture
      fichierSD.print(temps);
  
    fichierSD.print("\t");
    fichierSD.print(valeur2);
    fichierSD.println(""); 

    fichierSD.close();
  }
   delay(50);
 }

b. Mesure de pression

Pour plus de précisions sur la mesure de pression, vous pouvez consulter cet article

Code Arduino à téléverser:

// Programme d'utilisation du capteur de pression avec Arduino avec carte SD

#include <SPI.h>
#include <SD.h>



//Définition des broches analogiques utilisées par le capteur.

#define _NUMER0_BROCHE_ANALOGIQUE A0          //Broche analogique utilisée par le capteur pression.
long temps;

File fichierSD;
//==================================================================================================
// Convertit la valeur numérique en une valeur de tension.
// Le Convertisseur Analogique Numérique converti la tension sur 10bits.  
// Pour une tension de 0V la valeur numérique est 0.
// Pour une tension de 5V la valeur numérique est 1023.  
//==================================================================================================
float ConvertiValeurMesureAnalogiqueEnTension(int _valeurNumerique)
{
// La fonction de conversion valeur numérique/tension est de la forme tension = a * valeurNumerique. 
const int   _VALEUR_NUMERIQUE_MIN= 0;
const float _VALEUR_TENSION_MIN  = 0.0;
const int   _VALEUR_NUMERIQUE_MAX= 1023;   // convertisseur 10bits 
const float _VALEUR_TENSION_MAX  = 5.0;
  //calcul du coefficient directeur
  float a = (_VALEUR_TENSION_MAX-_VALEUR_TENSION_MIN)/(_VALEUR_NUMERIQUE_MAX-_VALEUR_NUMERIQUE_MIN);
  //calcul de la tension
  float tension_V= a * _valeurNumerique; 
  return(tension_V);
}





//==================================================================================================
// Procédure d'initialisation des périphériques
//==================================================================================================
void setup() {


  //  Initialisation de la carte SD
    if(!SD.begin(10)) {
    return;
    }
  
}



//==================================================================================================
// Convertit la valeur de tension en une valeur de pression.
// On mesure une tension de 0,2V pour une pression de  150hPa (un étalonnage du capteur montre que la tension de 0,2 V donnée par le constructeur pour 15 kPa peut varier légèrement ! On a choisi ici 0,27 )
// On mesure une tension de 4,7V pour une pression de 7000hPa.  
//==================================================================================================
float ConvertiTensionEnPression(float _tension)
{
// La fonction de conversion tension vers pression est de la forme pression = a * tension +b.  
const float _VALEUR_PRESSION_MIN= 150.0;
const float _VALEUR_TENSION_MIN = 0.27;
const float _VALEUR_PRESSION_MAX= 7000.0; //  
const float _VALEUR_TENSION_MAX = 4.7;
  // calcul du coefficient directeur
  float a = (_VALEUR_PRESSION_MAX-_VALEUR_PRESSION_MIN)/(_VALEUR_TENSION_MAX-_VALEUR_TENSION_MIN);
  // calcul du coefficient décalage à l'origine.
  float b = _VALEUR_PRESSION_MAX - a * _VALEUR_TENSION_MAX;
  //calcul de la pression
  float pression_Pa= (a * _tension) + b; // Pression en hecto Pascal.
  pression_Pa = pression_Pa * 100;       // Pression en Pascal
  return(pression_Pa);
}

//==================================================================================================
// Boucle principale Arduino.
//==================================================================================================
void loop() {
  temps= millis();


  // Lecture de la valeur du capteur sur l'entree analogique. 
  // La valeur mesurée par le Convertisseur Analogique Numérique prend pour valeur 0 pour une tension de 0V et 1023 pour une tension de 5V.
  int valeurNumerique = analogRead(_NUMER0_BROCHE_ANALOGIQUE);

  float tension_P_V   = ConvertiValeurMesureAnalogiqueEnTension(valeurNumerique);

  float pression_Pa = ConvertiTensionEnPression(tension_P_V);
  
  //Affichage des résultats
   fichierSD = SD.open("pression.txt", FILE_WRITE);
    if(fichierSD) {
  
   //Ecriture
     fichierSD.print(temps);
  
    fichierSD.print("\t");
    fichierSD.print(pression_Pa);
    fichierSD.println(""); 

    fichierSD.close();
  }

   

   
 
  
  delay(1000);                      // Délai en ms d'1s pour faciliter la visualisation.
}

c. Mesure d’accélération

Pour plus de précisions sur la mesure d’accélération, vous pouvez consulter cet article

Code Arduino à téléverser:

#include <SPI.h>
#include <SD.h>
#include "Wire.h"  // Arduino Wire library
#include "I2Cdev.h"  //bibliothèque I2Cdev à installer
#include "MPU6050.h" //bibliothèque MPU6050 à installer
// AD0 low = 0x68 (default for InvenSense evaluation board)
// AD0 high = 0x69

MPU6050 accelgyro;
long temps;
int16_t ax, ay, az;  //mesures brutes
int16_t gx, gy, gz;
File fichierSD;

    
void setup() {
  Wire.begin();  // bus I2C



//  Initialisation de la carte SD
    if(!SD.begin(10)) {
    return;
    }
    
  accelgyro.initialize();  // initialize device
  temps = millis();

}
     
void loop() {
  temps = millis();
  accelgyro.getAcceleration(&ax, &ay, &az);


   fichierSD = SD.open("acc.txt", FILE_WRITE);
 

        //Test pour écriture
   if(fichierSD) {

   //Ecriture
   fichierSD.print(temps);
   fichierSD.print("\t");
   fichierSD.println(ax);
   fichierSD.close();
  }

  
  
}

Changer de gamme pour de plus grandes accélérations

En cas d’expériences avec des mouvements rapdes comme pour des chocs, il est nécessaire de mesurer des valeurs d’accélération plus élevées.

Pour travailler sur une gamme -16g/+16g (au lieu de -2g/+2g), il suffit de rajouter une ligne de code dans le setup du programme Arduino :

accelgyro.setFullScaleAccelRange(3); // pour la gamme -16g/+16g

Voici le code Arduino modifié à téléverser (avec mesure de ax seulement):

#include <SPI.h>
#include <SD.h>
#include "Wire.h"  // Arduino Wire library
#include "I2Cdev.h"  //bibliothèque I2Cdev à installer
#include "MPU6050.h" //bibliothèque MPU6050 à installer
// AD0 low = 0x68 (default for InvenSense evaluation board)
// AD0 high = 0x69

MPU6050 accelgyro;
long temps;
int16_t ax, ay, az;  //mesures brutes
int16_t gx, gy, gz;
File fichierSD;

    
void setup() {
  Wire.begin();  // bus I2C



//  Initialisation de la carte SD
    if(!SD.begin(10)) {
    return;
    }
    
  accelgyro.initialize();  // initialize device
 accelgyro.setFullScaleAccelRange(3); // pour la gamme -16g/+16g
  temps = millis();

}
     
void loop() {
  temps = millis();
  accelgyro.getAcceleration(&ax, &ay, &az);


   fichierSD = SD.open("acc.txt", FILE_WRITE);
 

        //Test pour écriture
   if(fichierSD) {

   //Ecriture
   fichierSD.print(temps);
   fichierSD.print("\t");
   fichierSD.println(ax);
   fichierSD.close();
  }

  
  
}
     
    void loop() {
      temps = millis();
      accelgyro.getMotion6(&ax, &ay, &az, &gx, &gy, &gz);

      Serial.print(temps); 
      Serial.print("\t");
      Serial.println(ax);  
    }

d. Mesure avec deux accéléromètres

Accéléromètre 1 :

  • GND > GND
  • 5V > 5V
  • SDA > A4
  • SCL > A5

Accéléromètre 2 :

  • GND > GND
  • AD0 > 5V
  • SDA > A4
  • SCL > A5

Code Arduino à téléverser:

#include <SPI.h>
#include <SD.h>

#include <Wire.h>


const int MPU2 = 0x69, MPU1=0x68;

long accelX, accelY, accelZ,accel;



long temps;



File fichierSD;

    
void setup() {
   Wire.begin();
  Wire.beginTransmission(MPU1);
  Wire.write(0x6B);
  Wire.write(0b00000000);
  Wire.endTransmission();  
  Wire.beginTransmission(MPU1);
  Wire.write(0x1B);
  Wire.write(0x00000000);
  Wire.endTransmission(); 
  Wire.beginTransmission(MPU1);
  Wire.write(0x1C);
  Wire.write(0b00000000);
  Wire.endTransmission(); 
  
  Wire.begin();
  Wire.beginTransmission(MPU2);
  Wire.write(0x6B);
  Wire.write(0b00000000); 
  Wire.endTransmission();  
  Wire.beginTransmission(MPU2); 
  Wire.write(0x1B);
  Wire.write(0x00000000);
  Wire.endTransmission(); 
  Wire.beginTransmission(MPU2);
  Wire.write(0x1C);
  Wire.write(0b00000000);
  Wire.endTransmission(); 


//  Initialisation de la carte SD
    if(!SD.begin(10)) {

    return;
    }
    

 
  
 
  
}
     
void loop() {
  temps = millis();


   fichierSD = SD.open("acc.txt", FILE_WRITE);
 

   
   if(fichierSD) {

   //Ecriture
 fichierSD.print(temps);
  
  fichierSD.print("\t");
//  fichierSD.print("Acc1\t");
  fichierSD.print(GetMpuValue(MPU1));
//  fichierSD.print("\t ||| Acc2\t");
fichierSD.print("\t");
  fichierSD.print(GetMpuValue(MPU2));
  fichierSD.println(""); 

fichierSD.close();
  }
}
  
  
int GetMpuValue(const int MPU){
  
  Wire.beginTransmission(MPU); 
  Wire.write(0x3B);
  Wire.endTransmission();
  Wire.requestFrom(MPU,6);
  while(Wire.available() < 6);
  accelX = Wire.read()<<8|Wire.read(); 
  accelY = Wire.read()<<8|Wire.read(); 
  accelZ = Wire.read()<<8|Wire.read();
  accel = sqrt(accelX*accelX+accelY*accelY+accelZ*accelZ);
 
  
 return(accel);

}

4. Récupération des données avec Python

Un petit script Python ci dessous pour récupérer les données et tracer le graphe :




import matplotlib.pyplot as plt # pour les graphiques
import numpy as np # numpy pour l'importation des donnees en format txt
# importation des donnees txt obtenues apres pointage en supprimant la premiere ligne dans le fichier texte
lines = open('C:/fichier.txt').readlines() #on lit les lignes du fichier texte, spécifier le chemin C:/fichier.txt par exemple
open('data_new.txt', 'w').writelines(lines) #création d'un nouveau fichier texte
data = np.loadtxt('data_new.txt')# importation du nouveau fichier texte pour récupérer les valeurs de t, et des autres colonnes de donnees dans un tableau

t = data[:,0] # selection de la premiere colonne
donnee = data[:,1] # selection de la deuxieme colonne

# afficher points avec croix rouges. Inserer texte (titre, nom des axes,…)
plt.figure(1)
plt.scatter(t, donnee, c = 'red', marker = '+')
plt.xlabel("t en s")
plt.ylabel("donnée récupérée")

plt.show()











Lien Github des scripts Python et Arduino :

https://github.com/jonasforlot/python-arduino/tree/main/Syst%C3%A8mes%20ARDUINO%20autonomes%20SD

Laisser un commentaire

Votre adresse e-mail ne sera pas publiée. Les champs obligatoires sont indiqués avec *