ACTIVITE ARDUINO : Suiveur solaire à deux axes avec Arduino

Objectif

L’objectif de ce projet est de réaliser un suiveur solaire à deux axes à l’aide d’une carte Arduino, de quatre photorésistances et de deux servomoteurs.

Le dispositif fonctionne sur le principe d’un « tournesol robotisé » : il cherche en permanence la direction de la source lumineuse et oriente automatiquement son support vers celle-ci.

Un tel système peut notamment être utilisé pour orienter de façon optimale un panneau photovoltaïque vers le Soleil au cours de la journée.

Matériel nécessaire

1. Une carte Arduino

Une carte Arduino disposant d’au moins deux entrées analogiques est nécessaire.

Dans ce projet :

  • A0 est utilisée pour la mesure Est-Ouest (EO) ;
  • A1 est utilisée pour la mesure Nord-Sud (NS).

2. Quatre photorésistances

Quatre photorésistances permettent de déterminer la direction de la source lumineuse.

Elles sont disposées selon les quatre directions :

  • N : Nord ;
  • S : Sud ;
  • E : Est ;
  • O : Ouest.

Les quatre photorésistances sont installées dans un petit support carré imprimé en 3D comportant quatre trous.

La disposition des capteurs permet de comparer l’éclairement reçu dans les différentes directions.

3. Deux servomoteurs

Deux servomoteurs permettent d’orienter le support suivant deux axes :

  • un axe Est-Ouest ;
  • un axe Nord-Sud.
Ils sont montés sur un support Pan-Tilt à deux axes, par exemple le modèle DG2B proposé par Gotronic

Principe

Déterminer la direction de la lumière

Le système utilise quatre photorésistances pour déterminer si la source lumineuse est davantage située vers l’Est ou l’Ouest, et vers le Nord ou le Sud.

Les capteurs sont associés deux par deux afin d’obtenir deux informations :

  • une information Est-Ouest (EO) ;
  • une information Nord-Sud (NS).

Les photorésistances sont alimentées selon ce montage en pont pour obtenir les deux tensions de mesure EO et NS.

Ces deux informations sont mesurées par les entrées analogiques de l’Arduino :

MesureEntrée Arduino
Est-Ouest (EO)A0
Nord-Sud (NS)A1

Lorsque les photorésistances associées à un axe reçoivent une quantité de lumière comparable, le montage est proche de l’équilibre.

La valeur mesurée par l’Arduino est alors proche de 512, correspondant approximativement à 2,5 V pour une référence de 5 V et une conversion analogique sur 10 bits.

Si la lumière éclaire davantage l’un des deux côtés, le montage se déséquilibre et la valeur mesurée s’éloigne de 512.

L’Arduino peut alors commander le servomoteur correspondant pour corriger l’orientation.

Le support des quatre capteurs

Support imprimé en 3D permettant de positionner les quatre photorésistances.

Le petit support imprimé en 3D constitue la partie sensible du dispositif.

Les quatre photorésistances sont positionnées dans les quatre trous du support, suivant les directions N, S, E et O.

La géométrie du support permet de créer des différences d’éclairement entre les capteurs lorsque le dispositif n’est pas correctement orienté vers la source lumineuse.

Lorsque la source lumineuse se trouve dans l’axe du dispositif, les quatre capteurs reçoivent des éclairements plus proches les uns des autres.

Lorsque le dispositif est désorienté, une partie des capteurs est davantage éclairée que les autres. Cette différence permet au programme de déterminer dans quelle direction il doit déplacer le support.

Montage du Pan-Tilt

Le support Pan-Tilt permet d’obtenir les deux degrés de liberté nécessaires au suivi de la source lumineuse.

Un servomoteur commande l’orientation autour d’un premier axe et le second servomoteur commande l’inclinaison autour du deuxième axe.

Avant de fixer définitivement les éléments mécaniques, il est important de positionner les deux servomoteurs à 90°.

Cette étape permet de définir une position centrale de référence.

Mise au neutre des servomoteurs

Avant de monter mécaniquement les servomoteurs, connecter ceux-ci à l’Arduino et téléverser le programme suivant :

#include <Servo.h>

Servo servoEO;
Servo servoNS;

void setup() {

  servoEO.attach(9);
  servoNS.attach(10);

  // Position centrale des deux servomoteurs
  servoEO.write(90);
  servoNS.write(90);
}

void loop() {
  // Les servomoteurs restent à 90°
}

Les deux servomoteurs se positionnent alors à 90°.

Attention : les servomoteurs peuvent effectuer un mouvement brusque lors de leur mise sous tension. Il est préférable de maintenir le mécanisme libre pendant cette étape.

Une fois les servomoteurs positionnés, installer les palonniers et fixer mécaniquement le support.

La position recherchée est une position centrale, dans laquelle le support peut ensuite se déplacer dans les deux directions.

Pan-Tilt en position neutre

Vérification des deux axes

Avant de connecter les capteurs et de lancer le programme de suivi solaire, il est intéressant de vérifier séparément le fonctionnement des deux servomoteurs.

On peut par exemple tester l’axe Est-Ouest avec :

servoEO.write(60);
servoNS.write(90);

puis :

servoEO.write(120);
servoNS.write(90);

Le support doit alors se déplacer autour de l’axe Est-Ouest.

On peut ensuite tester l’autre axe :

servoEO.write(90);
servoNS.write(60);

puis :

servoEO.write(90);
servoNS.write(120);

Le support doit alors s’incliner autour de l’axe Nord-Sud.

Selon le montage mécanique, le sens de rotation peut être inversé. Il suffit alors d’adapter le programme.

Câblage

Les quatre photorésistances sont utilisées pour obtenir les deux mesures d’orientation.

Les connexions principales sur la carte Arduino sont les suivantes :

FonctionBroche Arduino
Mesure Est-Ouest (EO)A0
Mesure Nord-Sud (NS)A1
Servomoteur axe EOD9
Servomoteur axe NSD10

Les servomoteurs sont alimentés en 5 V par la carte Arduino (la puissance est suffisante pour ces petits modèles de servomoteurs, il n’est pas nécessaire d’utiliser une autre alimentation extérieure)

Programmer le suiveur solaire

Une fois le montage mécanique réalisé et les deux servomoteurs mis au neutre, on peut programmer le suivi de la source lumineuse.

Le programme mesure successivement :

analogRead(A0)

pour l’axe Est-Ouest, puis :

analogRead(A1)

pour l’axe Nord-Sud.

La valeur d’équilibre est fixée à environ 512.

Le programme commande alors les servomoteurs afin de réduire l’écart par rapport à cette valeur.

Programme Arduino

#include <Servo.h>

// -------------------------
// Entrées des capteurs
// -------------------------
const int CAPTEUR_EO = A0;
const int CAPTEUR_NS = A1;

// -------------------------
// Servomoteurs
// -------------------------
const int SERVO_EO = 9;
const int SERVO_NS = 10;

Servo MonServo1;
Servo MonServo2;

// -------------------------
// Position des servomoteurs
// -------------------------
int angleEO = 90;
int angleNS = 90;

// Limites mécaniques
const int ANGLE_MIN = 10;
const int ANGLE_MAX = 170;

// -------------------------
// Réglages des capteurs
// -------------------------

// Valeur correspondant à l'équilibre
const int CENTRE = 512;

// Zone morte autour de la valeur d'équilibre
const int ZONE_MORTE = 15;

// -------------------------
// Moyenne des mesures
// -------------------------
const int N = 5;


void setup() {

  MonServo1.attach(SERVO_EO);
  MonServo2.attach(SERVO_NS);

  // Position initiale
  MonServo1.write(angleEO);
  MonServo2.write(angleNS);

  Serial.begin(9600);
}


void loop() {

  // -------------------------
  // Lecture moyenne des capteurs
  // -------------------------

  long sommeEO = 0;
  long sommeNS = 0;

  for (int i = 0; i < N; i++) {

    sommeEO += analogRead(CAPTEUR_EO);
    sommeNS += analogRead(CAPTEUR_NS);

    delay(2);
  }

  int ValEO = sommeEO / N;
  int ValNS = sommeNS / N;


  // -------------------------
  // Axe Est-Ouest
  // -------------------------

  if (ValEO > CENTRE + ZONE_MORTE) {

    if (angleEO < ANGLE_MAX) {
      angleEO++;
    }
  }

  else if (ValEO < CENTRE - ZONE_MORTE) {

    if (angleEO > ANGLE_MIN) {
      angleEO--;
    }
  }


  // -------------------------
  // Axe Nord-Sud
  // -------------------------

  if (ValNS < CENTRE - ZONE_MORTE) {

    if (angleNS < ANGLE_MAX) {
      angleNS++;
    }
  }

  else if (ValNS > CENTRE + ZONE_MORTE) {

    if (angleNS > ANGLE_MIN) {
      angleNS--;
    }
  }


  // -------------------------
  // Commande des servomoteurs
  // -------------------------

  MonServo1.write(angleEO);
  MonServo2.write(angleNS);


  // -------------------------
  // Affichage dans le moniteur série
  // -------------------------

  Serial.print("EO : ");
  Serial.print(ValEO);

  Serial.print("   NS : ");
  Serial.print(ValNS);

  Serial.print("   Angle EO : ");
  Serial.print(angleEO);

  Serial.print("   Angle NS : ");
  Serial.println(angleNS);


  delay(50);
}

Explication du programme

Lecture des capteurs

L’Arduino réalise plusieurs mesures successives :

sommeEO += analogRead(CAPTEUR_EO);
sommeNS += analogRead(CAPTEUR_NS);

Les cinq mesures sont ensuite moyennées.

Cette moyenne permet de réduire les petites fluctuations de la mesure et d’obtenir un mouvement plus régulier des servomoteurs.

Une zone morte autour de 512

Une mesure exactement égale à 512 est difficile à obtenir en permanence dans un montage réel.

Les mesures peuvent par exemple osciller entre 508, 514, 510, 516…

Si le programme réagissait à chaque variation, les servomoteurs pourraient effectuer de petits mouvements permanents.

On introduit donc une zone morte :

const int ZONE_MORTE = 15;

Le système considère ainsi que le capteur est suffisamment équilibré lorsque la mesure est comprise approximativement entre :

497 et 527.

Dans cette zone, le servomoteur ne bouge pas.

Limitation de la course des servomoteurs

Les angles sont limités à :

const int ANGLE_MIN = 10;
const int ANGLE_MAX = 170;

Cela permet d’éviter d’aller jusqu’aux extrémités de la course du servomoteur et de limiter les risques de blocage mécanique.

Contrairement au programme initial, le système ne revient pas brutalement à 90° lorsqu’une limite est atteinte.

Chaque axe est simplement maintenu dans sa plage autorisée.

Mise au point

Pour les premiers essais, il est préférable d’utiliser une lampe plutôt que directement le Soleil.

On peut déplacer progressivement la source lumineuse autour du capteur et observer :

  • les valeurs EO et NS dans le moniteur série ;
  • les variations des angles des servomoteurs ;
  • le déplacement du support ;
  • la recherche progressive de la position d’équilibre.

Le moniteur série affiche par exemple :

EO : 518   NS : 507   Angle EO : 94   Angle NS : 87
EO : 514   NS : 510   Angle EO : 95   Angle NS : 88
EO : 512   NS : 512   Angle EO : 95   Angle NS : 88

Lorsque les valeurs se rapprochent de la zone d’équilibre, les servomoteurs cessent progressivement de bouger.

Si le système tourne dans le mauvais sens

Selon la façon dont les photorésistances et les servomoteurs ont été montés, il est possible qu’un axe tourne dans le mauvais sens.

Par exemple, si le système s’éloigne de la source lumineuse au lieu de s’en rapprocher, il suffit d’inverser les deux commandes correspondantes.

Pour l’axe EO :

angleEO++;

et

angleEO--;

peuvent être interverties.

Même chose pour l’axe NS.

Tous les fichiers (code Arduino, fichiers 3D, …) sont ICI