Gestion volet roulant filaire

Bonjour,
débutant en prog arduino ,

Je suis entrain de réaliser une petite carte arduino pour gère mes 11 volets électriques de la maison.
Je me suis inspiré de plusieurs post du forum pour le réalisé.

mon programme est encore en ébauche .
J’ai déjà testé le prog sur 1 volet et cela fonctionnent

Donc ma question est au niveau de la répétabilité .Je veux gère 10 volet indépendamment + une commande centralisé avec fermeture en cascade .

Il y a-t-il une solution pas trop compliqué pour faire cela autre que faire copier collé 10X en changeant les variables.

const byte M1_PIN = 2;  // pin de contrôle du relais montée volet 1
const byte D1_PIN = 3;  // pin de contrôle du relais descente volet 1
const byte BP_M1_PIN = 6;     // pin de contrôle du bouton montée volet 1
const byte BP_D1_PIN = 7;     // pin de contrôle du bouton descente volet 1

#include <Wire.h>
#include "Adafruit_MCP23017.h"
#include <simpleBouton.h> // http://forum.arduino.cc/index.php?topic=375232.0
simpleBouton BP_M1(BP_M1_PIN);   //Cablage : pin---BP---GND
simpleBouton BP_D1(BP_D1_PIN);   //Cablage : pin---BP---GND
simpleBouton BP_M2(BP_M2_PIN);   //Cablage : pin---BP---GND
simpleBouton BP_D2(BP_D2_PIN);   //Cablage : pin---BP---GND
simpleBouton BP_D3(BP_D3_PIN);   //Cablage : pin---BP---GND
simpleBouton BP_M3(BP_M3_PIN);   //Cablage : pin---BP---GND
simpleBouton BP_D4(BP_D4_PIN);   //Cablage : pin---BP---GND
simpleBouton BP_M4(BP_M4_PIN);   //Cablage : pin---BP---GND
simpleBouton BP_D5(BP_D5_PIN);   //Cablage : pin---BP---GND
simpleBouton BP_M5(BP_M5_PIN);   //Cablage : pin---BP---GND
simpleBouton BP_D6(BP_D6_PIN);   //Cablage : pin---BP---GND
simpleBouton BP_M6(BP_M6_PIN);   //Cablage : pin---BP---GND
simpleBouton BP_D7(BP_D7_PIN);   //Cablage : pin---BP---GND
simpleBouton BP_M7(BP_M7_PIN);   //Cablage : pin---BP---GND
simpleBouton BP_D8(BP_D8_PIN);   //Cablage : pin---BP---GND
simpleBouton BP_M8(BP_M8_PIN);   //Cablage : pin---BP---GND
simpleBouton BP_D9(BP_D9_PIN);   //Cablage : pin---BP---GND
simpleBouton BP_M9(BP_M9_PIN);   //Cablage : pin---BP---GND
simpleBouton BP_D10(BP_D10_PIN);   //Cablage : pin---BP---GND
simpleBouton BP_M10(BP_M10_PIN);   //Cablage : pin---BP---GND
simpleBouton BP_D11(BP_D11_PIN);   //Cablage : pin---BP---GND
simpleBouton BP_M11(BP_M11_PIN);   //Cablage : pin---BP---GND


unsigned long chronoVolet1;
unsigned long chronoVolet2;
unsigned long chronoVolet3;
unsigned long chronoVolet4;
unsigned long chronoVolet5;
unsigned long chronoVolet6;
unsigned long chronoVolet7;
unsigned long chronoVolet8;
unsigned long chronoVolet9;
unsigned long chronoVolet10;
unsigned long chronoVolet11;
const unsigned long trenteSecondes = 30000UL;

enum : byte {REPOS, MONTE, DESCEND} etatVolet1;
enum : byte {REPOS, MONTE, DESCEND} etatVolet2;
enum : byte {REPOS, MONTE, DESCEND} etatVolet3;
enum : byte {REPOS, MONTE, DESCEND} etatVolet4;
enum : byte {REPOS, MONTE, DESCEND} etatVolet5;
enum : byte {REPOS, MONTE, DESCEND} etatVolet6;
enum : byte {REPOS, MONTE, DESCEND} etatVolet7;
enum : byte {REPOS, MONTE, DESCEND} etatVolet8;
enum : byte {REPOS, MONTE, DESCEND} etatVolet9;
enum : byte {REPOS, MONTE, DESCEND} etatVolet10;

void setup()
{
  Serial.begin(9600);
  pinMode(M1_PIN, OUTPUT);
  pinMode(D1_PIN, OUTPUT);
  reposVolet1();
  actualiserBoutons();

  mcp1.begin(0); // Utilise l'adresse 0x20 + 0 pour IC1
  mcp2.begin(5); // Utilise l'adresse 0x20 + 5 pour IC2


  // Définir la sortie #0 (GPA 0, broche 21) sur IC1 comme sortie
  mcp1.pinMode(0, OUTPUT);
  // Définir la sortie #1 (GPA 1, broche 22) sur IC2 comme sortie
  mcp2.pinMode(1, INTPUT);

}

void actualiserBoutons()
{
  BP_M1.actualiser();
  BP_D1.actualiser();
}

void reposVolet1()
{
  digitalWrite(M1_PIN, LOW); //on éteint le relay_M1
  digitalWrite(D1_PIN, LOW); //on éteint le relay_D1
  etatVolet1 = REPOS;
}

void monteVolet1()
{
  digitalWrite(D1_PIN, LOW);
  delay(500); // pour s'assurer que les 2 relais ne sont pas actifs en même temps
  digitalWrite(M1_PIN, HIGH);
  chronoVolet1 = millis();
  etatVolet1 = MONTE;
}

void descendVolet1()
{
  digitalWrite(M1_PIN, LOW);
  delay(500); // pour s'assurer que les 2 relais ne sont pas actifs en même temps
  digitalWrite(D1_PIN, HIGH);
  chronoVolet1 = millis();
  etatVolet1 = DESCEND;
}

void actualiserVolet1()
{
  switch (etatVolet1) {
    case REPOS: // 2 évènements possibles bouton Monter ou Descendre
      if (BP_M1.vientDEtreEnfonce()) monteVolet1();
      else if (BP_D1.vientDEtreEnfonce()) descendVolet1();
      break;

    case MONTE:// 3 évènements possibles bouton Monter ou Descendre ou timeOut
      if (millis() - chronoVolet1 >= trenteSecondes) reposVolet1();
      else if (BP_M1.vientDEtreEnfonce()) reposVolet1();
      else if (BP_D1.vientDEtreEnfonce()) descendVolet1();
      break;

    case DESCEND:// 3 évènements possibles bouton Monter ou Descendre ou timeOut
      if (millis() - chronoVolet1 >= trenteSecondes) reposVolet1();
      else if (BP_M1.vientDEtreEnfonce()) monteVolet1();
      else if (BP_D1.vientDEtreEnfonce()) reposVolet1();
      break;
  }
}



void loop()
{
  actualiserBoutons();
  actualiserVolet1();
}


ça s'appelle un tableau et des boucles sans doute (plus une structure pour regrouper le tout)

faudrait aussi donner un nom au type énuméré plutôt que d'en créer 10

enum : byte {REPOS, MONTE, DESCEND} etatVolet1;
enum : byte {REPOS, MONTE, DESCEND} etatVolet2;
enum : byte {REPOS, MONTE, DESCEND} etatVolet3;
enum : byte {REPOS, MONTE, DESCEND} etatVolet4;
enum : byte {REPOS, MONTE, DESCEND} etatVolet5;
enum : byte {REPOS, MONTE, DESCEND} etatVolet6;
enum : byte {REPOS, MONTE, DESCEND} etatVolet7;
enum : byte {REPOS, MONTE, DESCEND} etatVolet8;
enum : byte {REPOS, MONTE, DESCEND} etatVolet9;
enum : byte {REPOS, MONTE, DESCEND} etatVolet10;

devient

enum t_etat: byte {REPOS, MONTE, DESCEND} ;
const byte nombreDeVolets = 10;
t_etat etatVolets[nombreDeVolets];

avec une structure pour tout regrouper ça pourrait avoir cette tête:

#include <simpleBouton.h> // http://forum.arduino.cc/index.php?topic=375232.0

enum t_etat : byte {REPOS, MONTE, DESCEND} ;

struct t_volet {
  t_etat etatVolet;
  const byte pinRelaisMonter;
  const byte pinRelaisDescendre;
  simpleBouton boutonMonter;
  simpleBouton boutonDescendre;
  unsigned long chronoVolet;
};


t_volet volets[] {
  {REPOS, 2, 3, 6, 7, 0},   // Volet #1
  {REPOS, 4, 5, 8, 9, 0},   // Volet #2
  // ...
};

const byte nombreDeVolets = sizeof volets / sizeof volets[0];

void setup() {
  for (byte v = 0; v < nombreDeVolets; v++) {
    pinMode(volets[v].pinRelaisMonter,    OUTPUT);
    pinMode(volets[v].pinRelaisDescendre, OUTPUT);
  }
}

void loop() {}

il faut bien sûr adapter le reste du code pour que les fonctions travaillent sur un volet particulier, par exemple en passant un indice à la fonction

void reposVolet(const byte indiceVolet) { // éventuellement tester que indiceVolet est < nombreDeVolets
  digitalWrite(volets[indiceVolet].pinRelaisMonter, LOW);    // on éteint le relai de montée
  digitalWrite(volets[indiceVolet].pinRelaisDescendre, LOW); // on éteint le relai de descente
  volets[indiceVolet].etatVolet = REPOS;
}