Étiquettes : ,
0
(0)

Dans ce tutoriel, nous allons voir comment gérer plusieurs capteurs avec un registre à décalage. Nous avons vu dans le dernier tutoriel sur le sujet, que le registre pouvait servir à piloter des LEDs. Nous allons voir ici, comment lire la valeur de 8 capteurs sur une seule entrée analogique. En électronique, le nombre d’entrées-sorties devient critique lorsqu’on utilise plusieurs capteurs. L’utilisation d’un registre à décalage est une bonne solution pour diminuer le nombre de broches utilisées.

Dans cet article, nous utilisons le registre à décalage 74HC595 mais il est possible d’uiliser un multiplexeur ou un 74HC165 (Parallèle vers série, plus adapter pour la lecture de capteur)

Matériel

  • Ordinateur
  • Arduino UNO
  • Câble USB A Mâle/B Mâle
  • Shift Register 74HC595

Principe de fonctionnement

Le registre à décalage (ou shift register) est un composant électronique contenant des bascules synchrones. Ce sont des circuits logiques qui gardent en mémoire un état haut ou bas (comme un bit) relié par une même horloge. Le principe de décalage vient du fait que l’on vient écrire ou lire dans chaque mémoire bit par bit.

Pour gérer des capteurs, nous allons utiliser la sortie du registre à décalage comme source de tension et toute les sorties capteurs seront reliées à une entrée analogique de l’Arduino. Les capteurs seront alimentés les uns après les autres ce qui nous permettra de récupérer, sur la broche analogique, la valeur du capteur alimenté.

Schéma

Le registre à décalage nécessite 3 broches de sortie d’un microcontrôleur. Il est possible de gérer plusieurs registres montés en série.

  • GND masse du circuit intégré
  • Vcc broche d’alimentation. Généralement connecté à 5V
  • SH_CP ou RCLK shift register clock input. Le signal d’horloge du registre qui détermine si on écrit dans la mémoire
  • ST_CP ou SRCLK storage register clock input. Le signal d’horloge de stockage qui définit dans quel mémoire on vient lire ou écrire.
  • DS ou SER serial data input. Signal contenant la données à enregistrer (HAUT ou BAS)
  • Q0-Q7 parallel data output. Broches de sorties du registre à décalage
  • OE Output enable, active LOW. Broche connectée à GND pour activer les sorties
  • MR Master reset, active LOW. Broche de remise à zéro. Connectée au 5V
  • Q7′ serial data output (broche utilisée seulement si plusieurs registres sont montés en série)

Une fois le registre à décalage branché correctement, nous allons connecter chacun des boutons. Pour pouvoir détecter l’état de plusieurs boutons, il faut rajouter une diode à chaque sortie afin que le courant ne passe pas d’une sortie à l’autre du registre à décalage.

Code

Pour communiquer avec le registre à décalage, nous allons jongler avec ses broches d’entrée. Il faut mettre la broche RCLK à bas pour écrire dans un registre. Pour écrire dans les bascules, il faut passer l’horloge de stockage à bas. A chaque impulsion d’horloge, on passe à la bascule suivante. Pour simplifier notre code, nous allons définir cette procédure dans la fonction writeRegister().
Pour gérer le groupe de capteur à travers le registre, nous allons envoyer des impulsions sur chaque bascule et lire la valeur du bouton lorsque la bascule est à l’état haut, c’est-à-dire, qu’un courant passe dans le bouton.

//Constants
#define number_of_74hc595s 1
#define numOfRegisterPins number_of_74hc595s * 8
#define SER_Pin 2
#define RCLK_Pin 3
#define SRCLK_Pin 4

//Parameters
const int grpBtnPin = A0;

//Variables
boolean registers[numOfRegisterPins] = {0, 0, 0, 0, 0, 0, 0, 0};
boolean grpBtnState[numOfRegisterPins] = {0, 0, 0, 0, 0, 0, 0, 0};
boolean oldGrpBtnState[numOfRegisterPins] = {0, 0, 0, 0, 0, 0, 0, 0};
int grpBtnVal[numOfRegisterPins] = {0, 0, 0, 0, 0, 0, 0, 0};

void setup() {
  //Init Serial USB
  Serial.begin(9600);
  Serial.println(F("Initialize System"));
  //Init register
  pinMode(SER_Pin, OUTPUT);
  pinMode(RCLK_Pin, OUTPUT);
  pinMode(SRCLK_Pin, OUTPUT);
  pinMode(grpBtnPin, INPUT);
}

void loop() {
  readGrpBtn();
}

void clearRegisters() { /* function clearRegisters */
  //// Clear registers variables
  for (int i = numOfRegisterPins - 1; i >=  0; i--) {
    registers[i] = LOW;
  }
}

void writeRegisters() { /* function writeRegisters */
  //// Write register after being set
  digitalWrite(RCLK_Pin, LOW);
  for (int i = numOfRegisterPins - 1; i >=  0; i--) {
    digitalWrite(SRCLK_Pin, LOW); int val = registers[i];
    digitalWrite(SER_Pin, val);
    digitalWrite(SRCLK_Pin, HIGH);
  }
  digitalWrite(RCLK_Pin, HIGH);
}

void setRegisterPin(int index, int value) { /* function setRegisterPin */
  ////Set register variable to HIGH or LOW
  registers[index] = value;
}

void readGrpBtn() { /* function readGrpBtn */
  //// Read each btn
  for (int i = numOfRegisterPins - 1; i >=  0; i--) {
    grpBtnState[i] = false;
    setRegisterPin(i, HIGH);
    writeRegisters();
    delay(20);
    grpBtnVal[i] = analogRead(grpBtnPin);
    setRegisterPin(i, LOW);
    writeRegisters();

    if (grpBtnVal[i] > 500) {
      grpBtnState[i] = true;
      if (oldGrpBtnState[i] != grpBtnState[i]) {
        Serial.print(F("Btn "));
        Serial.print(i);
        Serial.print(F(" detected -> State =  "));
        Serial.println(grpBtnVal[i]);
      }
    }
  }
}

Résultats

L’état du bouton est actualisé à chaque passage par la mémoire du registre correspondante et il nous est possible de lire 8 boutons à l’aide d’une seule entrée analogique.

Applications

  • Gérer jusqu’à 8 capteurs avec trois broches digitales et une broche analogique d’un microcontrôleur
  • Créer un périphérique HID avec plusieurs touches

Sources

Retrouvez nos tutoriels et d’autres exemples dans notre générateur automatique de code
La Programmerie

How useful was this post?

Click on a star to rate it!

Average rating 0 / 5. Vote count: 0

No votes so far! Be the first to rate this post.

As you found this post useful...

Follow us on social media!

We are sorry that this post was not useful for you!

Let us improve this post!

Tell us how we can improve this post?