Hifi, allumage décalé filtres/égaliseurs et amplis

Bonsoir, après avoir étudié ,en fonction de mes compétences, deux autres méthodes purement électronique en vain j'ai récupéré le kit que j'avais offert à mon fils il y a un an et voici ce que j'ai réussis à faire en quelques jours.

Mon installation hifi est composée d'un filtre actif, compresseur, équaliseur et de plusieurs amplis et comme source un PC musique. J'en avais assez d'allumer le PC musique, ensuite les filtres & co et les amplis. Je voulais n'avoir que le PC musique à allumer et que le reste se fasse tout seul.
J'utilise une sortie USB pour alimenter l'Arduino et le +5 de l'USB pour savoir si le PC est allumé ou pas.
Une fois démarré un relais alimente l'alim 9V de l'Arduino et à l'extinction ce même relais coupe tout.

Voici une photo du schéma


Elles n'apparaissent pas sur le schéma mais j'ai rajouté une résistance de rappel à la masse de 10k sur chaque pin.

Voici le code

int RelAlim=2;
int RelAmp=4;
int RelEq=6;
int PCusb=8;

void setup(){
  pinMode(RelAlim, OUTPUT);
  pinMode(RelAmp, OUTPUT);
  pinMode(RelEq, OUTPUT);
  pinMode(PCusb, INPUT);
  digitalWrite(RelAlim, HIGH);        //Alimentation du circuit via le transfo
}

void loop(){
 if (digitalRead(PCusb)==HIGH){       //PC Musique Allumé
    digitalWrite(RelAlim, HIGH);      //Maintient relais Alim ON
    delay(500);                       //Tempo pour ne pas surcharger l'alim
    digitalWrite(RelEq, HIGH);        //Allumage relais Eq
    delay(5000);                      //Tempo avant d'allumer les amplis
    digitalWrite(RelAmp, HIGH);       //Allumage relais Ampli
 }
  
 if (digitalRead(PCusb)==LOW){        //PC Musique éteind
    digitalWrite(RelAmp, LOW);        //Coupure relais Ampli
    delay(5000);                      //Tempo attente que l'ampli soit éteind
    digitalWrite(RelEq, LOW);         //Coupure relais Eq
    delay(500);                       //Tempo pour ne pas surcharger l'alim
    digitalWrite(RelAlim, LOW);       //Coupure relais Alim. On coupe le circuit
 }
}

C'est mon premier code alors dites moi ce que vous en pensez et ce que je peux apporter comme amélioration.

Bonne soirée ^^

Bonsoir mimikrakra
Pour ce faire, j'ai une multiprise "automatique" avec une prise maître où est connecté le PC, quand le PC consomme, ça allume les autres prises.
Je crois que ça s'appelle une smart power strip.

Cordialement
jpbbricole

Salut, je connais juste de nom ce genre de prises. Je n'ai pas cherché de ce coté car je voulais un système avec zéro conso au repo et surtout avec la possibilité de différer l'allumage des éléments.
En plus ça me donne l'occasion de mettre un pied dans la programmation.

Est-ce que je peux récupérer logiciellement l'information du +5 de l'USB ?

Bonjour, en relisant mon programme je me suis rendu compte que la boucle passait son temps à allumer les relais et à chaque passage il y a la tempo "delay" donc je l'ai réécris en prenant en compte l'état des sorties.
J'ai une version avec "if" et une autre avec "while". Les deux sont supposées fonctionner mais "while" dans l'esprit irait mieux, je pense.
Pendant que le micropoc traite ma boucle "while" est-ce qu'il peut traiter autre chose ou est-ce qu'il est bloqué dans la boucle tant qu'elle est active? je ferai le test ce soir ou ce weekend.
Voici les deux versions, dites moi ce que vous en pensez.

Merci ^^

int RelAlim=2;
int RelAmp=4;
int RelEq=6;
int PCusb=8;

void setup(){
  pinMode(RelAlim, OUTPUT);
  pinMode(RelAmp, OUTPUT);
  pinMode(RelEq, OUTPUT);
  pinMode(PCusb, INPUT);
  digitalWrite(RelAlim, HIGH);        //Alimentation du circuit via le transfo
  delay(500);
  digitalWrite(RelAmp, LOW);          //Relais ampli OFF
  digitalWrite(RelEq, LOW);           //Relais Eq OFF
}

void loop(){
 if (digitalRead(PCusb)==HIGH){       //PC Musique Allumé
   if (digitalRead(RelAlim)==LOW){    //Si relais Alim OFF
      digitalWrite(RelAlim, HIGH);    //Allumage relais Alim
      delay(500);                     //Tempo pour ne pas surcharger l'alim
   }
   if (digitalRead(RelEq)==LOW){      //Si relais Eq OFF
      digitalWrite(RelEq, HIGH);      //Allumage relais Eq
      delay(5000);                    //Tempo avant d'allumer les amplis
   }
    if (digitalRead(RelAmp)==LOW){    //Si relais Ampli OFF
       digitalWrite(RelAmp, HIGH);    //Allumage relais Ampli
   }
 }
 if (digitalRead(PCusb)==LOW){        //PC Musique éteind
    if (digitalRead(RelAmp)==HIGH) {
       digitalWrite(RelAmp, LOW);        //Coupure relais Ampli
       delay(5000);                      //Tempo attente que l'ampli soit éteind
    }
    if (digitalRead(RelEq)==HIGH){
       digitalWrite(RelEq, LOW);         //Coupure relais Eq
//       delay(500);                       //Tempo pour ne pas surcharger l'alim
    }
    if (digitalRead(RelAlim)==HIGH) {
       digitalWrite(RelAlim, LOW);       //Coupure relais Alim. On coupe le circuit
    }
 }
}
int RelAlim=2;
int RelAmp=4;
int RelEq=6;
int PCusb=8;

void setup(){
  pinMode(RelAlim, OUTPUT);
  pinMode(RelAmp, OUTPUT);
  pinMode(RelEq, OUTPUT);
  pinMode(PCusb, INPUT);
  digitalWrite(RelAlim, HIGH);         //Alimentation du circuit via le transfo
  delay(500);                          //Attente 500ms
  digitalWrite(RelAmp, LOW);           //Relais ampli OFF
  digitalWrite(RelEq, LOW);            //Relais Eq OFF
}

void loop(){
  while (digitalRead(PCusb)==HIGH) {   //Tant que le PC est allume alors...
    if (digitalRead(RelAlim)==LOW){    //Si relais Alim OFF
       digitalWrite(RelAlim, HIGH);    //Allumage relais Alim
       delay(500);                     //Tempo pour ne pas surcharger l'alim
     }
    if (digitalRead(RelEq)==LOW){      //Si relais Eq OFF
       digitalWrite(RelEq, HIGH);      //Allumage relais Eq
       delay(5000);                    //Tempo avant d'allumer les amplis
    }
    if (digitalRead(RelAmp)==LOW){     //Si relais Ampli OFF
       digitalWrite(RelAmp, HIGH);     //Allumage relais Ampli
    }
  }
  while (digitalRead(PCusb)==LOW) {    //Tant que le PC est éteint
    if (digitalRead(RelAmp)==HIGH) {   //Si relais ampli ON
       digitalWrite(RelAmp, LOW);      //Coupure relais Ampli
       delay(5000);                    //Tempo attente que l'ampli soit éteind
    }
    if (digitalRead(RelEq)==HIGH){     //Si relais Eq ON
       digitalWrite(RelEq, LOW);       //Coupure relais Eq
    }
    if (digitalRead(RelAlim)==HIGH) {  //Si realais Alim ON
       digitalWrite(RelAlim, LOW);     //Coupure relais Alim. On coupe le circuit
    }
  }
}

Les relais sont alimentés en 5V par une sortie de l'Arduino. Les relais consomment-ils vraiment moins de 20mA? En général, on ne peut pas alimenter un relais directement par Arduino.

Ahhhh je ne m'étais pas posé la question.
Ce sont des relais Finder 40.52-05 que j'avais acheté au début du projet avant de passer à l'Arduino.
Sur la doc la bobine est donnée pour 130mA donc c'est loin des 20mA. En tout ca ça fonctionnait bien lors de mes essais :wink: ...mais pour combien de temps ?

Je regarde sur amazon les cartes 8 relais qui sont prévues pour être pilotées directement par les sorties de l'Arduino et quand c'est indiqué certaines demandent 70mA par canal. Ce n'est pas parce que c'est en vente qu'il faut l'acheter, je sais ^^.
Il me faut des relais capables de supporter 250V/10A car j'ai des amplis derrière.

Bonjour mimikrakra

Si tu veux garder tes relais, il y a la solution ULN2803.

Cordialement
jpbbricole

Ces relais consomment 70mA par canal, ce qui est différent. 70mA est le courant de bobine.
Ils demandent en général quelques mA sur la commande, pas plus.

Merci à tous pour vos réponses ^^
Les relais, oui et non. Tant que je peux piloter mon install c'est le principal.

J'étais en train de regarder les Mini Relais optocoupleur 8 canaux et ça m'a l'air pas mal et livré demain ^^

Merci pour l'ULN2803, je garde l'info pour plus tard.
Je crois qu'il va falloir que j'ouvre un compte sur aliexpress ^^

Il y a moins de 8 relais, un ULN2003 fonctionne aussi.

Au début mon projet était prévu avec des montages RC pour gérer la tempo des relais. En théorie ça fonctionne très bien mais en pratique, non. Sur un forum d'électronique on m'a parlé de super condensateur etc. donc j'ai lâché l'affaire. J'avais déjà commandé les relais avec leur support pour faire mes essais.
Maintenant avec l'Arduino je peux faire un montage propre et avec le module 8 relais l'ensemble est plus compacte. Ce sont des relais 1RT et je veux couper le neutre et la phase donc 6 relais.

Vous avez un avis sur mes deux versions de codes histoire de savoir si je suis sur la bonne voir ^^ ?
Ca fait 4 jours que je programme

Je note que ces lignes sont équivalentes à

    digitalWrite(RelAmp, HIGH);     //Si relais Ampli OFF, Allumage relais Ampli

car si (digitalRead(RelAmp)==LOW), on fait l'action et sinon mettre une sortie à HIGH si elle y était déjà ne change rien

Regarde quand même du côté de la machine à états

Les deux codes sont quasi équivalents dans la mesure ou tu ne fais rien 'autre. On peut faire des tas de test ou rester bloqué, cela n'a pas une grande importance.

L'avantage de la machine à états qui va bloquer les différentes étapes est que l'on ne va pas passer de l'allumage à l'extinction rapidement si il y a un faux contact sur la prise USB. Voir ce que cela donne avec tes deux versions.
Une tension fugitive sur l'USB va provoquer l'allumage de RelAlim, de RelEq pendant 5s.
Une perte de tension très brève sur l'USB (on bouge le câble) Va tout éteindre et rallumer.
C'est un fonctionnement possible, mais est-ce bien cela que tu désires?

Merci pour tes remarques.
C'est vrai que d'activer une sortie qui est déjà active ne sert pas à grand chose. Mon but était de rajouter ensuite le delay.
Le delay est bien mais il met tout le programme en pause donc j'ai un peu cherché et travailler avec millis() c'est beaucoup mieux.

Voici encore une version du programme. Je fais peut être trop contrôles et de tests de variables ?

int RelAlim=2;
int RelAmp=4;
int RelEq=6;
int PCusb=8;
long Temps;
long TempsPC;
int ChgtPCusb;

void setup(){
  pinMode(RelAlim, OUTPUT);
  pinMode(RelAmp, OUTPUT);
  pinMode(RelEq, OUTPUT);
  pinMode(PCusb, INPUT);
  digitalWrite(RelAlim, HIGH);                       //Alimentation du circuit via le transfo
  digitalWrite(RelAmp, LOW);                         //Relais ampli OFF
  digitalWrite(RelEq, LOW);                          //Relais Eq OFF
  Temps=millis();                                    //enregistre l'heure - Début du chrono
  TempsPC=millis();
  ChgtPCusb=digitalRead(PCusb);                      //Initialisation de la variable de changement d'état de l'USB
}

void loop(){
 if (ChgtPCusb != digitalRead(PCusb)) {          //Si l'état de l'USB et différent
    TempsPC=millis();                            //Enregistre l'heure - Début du chrono
    ChgtPCusb=PCusb;                             //Initialisation de la variable de changement d'état de l'USB
 }
 if ((digitalRead(PCusb)==HIGH) & ((millis()-TempsPC) > 1000)) {                                  //Si PC Musique Allumé et tempo > à 1000ms
    if ((digitalRead(RelAlim)==LOW) & digitalRead(RelEq)==LOW & digitalRead(RelAmp)==LOW) {       //Si relais alim OFF et relais EQ OFF et Relais ampli OFF
       digitalWrite(RelAlim, HIGH);                                                               //Allumage relais alim
    }
    if (digitalRead(RelAlim)==HIGH & digitalRead(RelEq)==LOW & digitalRead(RelAmp)==LOW) {     //Si relais alim ON et relais EQ OFF et relais ampli OFF
       digitalWrite(RelEq, HIGH);                                                              //Allumage relais Eq
       Temps=millis();                                                                         //Enregistre l'heure
    }
    if (digitalRead(RelAlim)==HIGH & digitalRead(RelEq)==HIGH & digitalRead(RelAmp)==LOW & ((millis()-Temps)>5000)) {   //Si relais alim ON et relais EQ ON et relais ampli OFF
       digitalWrite(RelAmp, HIGH);                                                                                      //Allumage relais ampli
       Temps=millis();                                                                                                  //Enregistre l'heure
    }
 }
 if ((digitalRead(PCusb)==LOW) & ((millis()-TempsPC) > 1000)) {                                    //Si PC Musique éteind et tempo > à 1000ms
    if (digitalRead(RelAmp)==HIGH & (digitalRead(RelEq)==HIGH) & (digitalRead(RelAlim)==HIGH)) {   //Si relais ampli ON et relais EQ ON et relais alim ON
       digitalWrite(RelAmp, LOW);                                                                   //Coupure relais ampli
       Temps=millis();                                                                              //Enregistre l'heure
    }
    if (digitalRead(RelAmp)==LOW & (digitalRead(RelEq)==HIGH) & (digitalRead(RelAlim)==HIGH) & ((millis-Temps) > 5000)) {  //Si relais ampli OFF et relais EQ ON et relais alim ON
       digitalWrite(RelEq, LOW);                                                                                           //Coupure relais Eq
    }
    if (digitalRead(RelAmp)==LOW & (digitalRead(RelEq)==LOW) & (digitalRead(RelAlim)==HIGH)) {     //Si relais ampli OFF et relais EQ OFF et relais alim ON
       digitalWrite(RelAlim, LOW);                                                                 //Coupure relais Alim. On coupe le circuit
    }
  }
}

Apres quelques erreurs d'écritures de certaines variables ça fonctionne ^^

Votre avis sur le code...

int RelAlima=2;
int RelAlimb=4;
int RelAmpa=6;
int RelAmpb=8;
int RelEqa=10;
int RelEqb=12;
int PCusb=13;
long Temps;
long TempsPC;
int ChgtPCusb;

void setup(){
  pinMode(RelAlima, OUTPUT);
  pinMode(RelAlimb, OUTPUT);
  pinMode(RelAmpa, OUTPUT);
  pinMode(RelAmpb, OUTPUT);
  pinMode(RelEqa, OUTPUT);
  pinMode(RelEqb, OUTPUT);
  pinMode(PCusb, INPUT_PULLUP);
  digitalWrite(RelAlima, HIGH);                       //Alimentation du circuit via le transfo
  digitalWrite(RelAlimb, HIGH);                       //Alimentation du circuit via le transfo
  digitalWrite(RelAmpa, LOW);                         //Relais ampli OFF
  digitalWrite(RelAmpb, LOW);                         //Relais ampli OFF
  digitalWrite(RelEqa, LOW);                          //Relais Eq OFF
  digitalWrite(RelEqb, LOW);                          //Relais Eq OFF
  Temps=millis();                                     //enregistre l'heure - Début du chrono
  TempsPC=millis();                                   //enregistre l'heure - Début du chrono
  ChgtPCusb=digitalRead(PCusb);                       //Initialisation de la variable de changement d'état de l'USB
}

void loop(){
 if (digitalRead(ChgtPCusb) != digitalRead(PCusb)) {          //Si l'état de l'USB et différent
    TempsPC=millis();                                         //Enregistre l'heure - Début du chrono
    ChgtPCusb=PCusb;                                          //Initialisation de la variable de changement d'état de l'USB
 }
 if ((digitalRead(PCusb)==HIGH) & ((millis()-TempsPC) > 1000)) {                                  //Si PC Musique Allumé et tempo > à 1000ms
    if ((digitalRead(RelAlima)==LOW) & digitalRead(RelEqa)==LOW & digitalRead(RelAmpa)==LOW) {    //Si relais alim OFF et relais EQ OFF et Relais ampli OFF
       digitalWrite(RelAlima, HIGH);                                                              //Allumage relais alim
       digitalWrite(RelAlimb, HIGH);                                                              //Allumage relais alim
    }
    if (digitalRead(RelAlima)==HIGH & digitalRead(RelEqa)==LOW & digitalRead(RelAmpa)==LOW) {   //Si relais alim ON et relais EQ OFF et relais ampli OFF
       digitalWrite(RelEqa, HIGH);                                                              //Allumage relais Eq
       digitalWrite(RelEqb, HIGH);                                                              //Allumage relais Eq
       Temps=millis();                                                                          //Enregistre l'heure
    }
    if (digitalRead(RelAlima)==HIGH & digitalRead(RelEqa)==HIGH & digitalRead(RelAmpa)==LOW & ((millis()-Temps)>5000)) {   //Si relais alim ON et relais EQ ON et relais ampli OFF
       digitalWrite(RelAmpa, HIGH);                                                                                        //Allumage relais ampli
       digitalWrite(RelAmpb, HIGH);                                                                                        //Allumage relais ampli
       Temps=millis();                                                                                                     //Enregistre l'heure
    }
 }
 if ((digitalRead(PCusb)==LOW) & ((millis()-TempsPC) > 1000)) {                                       //Si PC Musique éteind et tempo > à 1000ms
    if (digitalRead(RelAmpa)==HIGH & (digitalRead(RelEqa)==HIGH) & (digitalRead(RelAlima)==HIGH)) {   //Si relais ampli ON et relais EQ ON et relais alim ON
       digitalWrite(RelAmpa, LOW);                                                                    //Coupure relais ampli
       digitalWrite(RelAmpb, LOW);                                                                    //Coupure relais ampli
       Temps=millis();                                                                                //Enregistre l'heure
    }
    if (digitalRead(RelAmpa)==LOW & (digitalRead(RelEqa)==HIGH) & (digitalRead(RelAlima)==HIGH) & ((millis()-Temps) > 5000)) {  //Si relais ampli OFF et relais EQ ON et relais alim ON
       digitalWrite(RelEqa, LOW);                                                                                               //Coupure relais Eq
       digitalWrite(RelEqb, LOW);                                                                                               //Coupure relais Eq
    }
    if (digitalRead(RelAmpa)==LOW & (digitalRead(RelEqa)==LOW) & (digitalRead(RelAlima)==HIGH)) {   //Si relais ampli OFF et relais EQ OFF et relais alim ON
       digitalWrite(RelAlima, LOW);                                                                 //Coupure relais Alim. On coupe le circuit
       digitalWrite(RelAlimb, LOW);                                                                 //Coupure relais Alim. On coupe le circuit
    }
  }
}

Bonne soirée...

Cela représente quoi ChgtPCusb et PCusb? Le numéro des entrées, un état? Il y a un mélange! Que doivent elle contenir?
La première ligne dit que PCusb est un numéro de pin (constante), et que ChgtPCusb vaut HIGH ou LOW. Mais dans ce cas, on ne peut pas faire digitalRead(ChgtPCusb).

Sinon quelques remarques de moindre imoprtance, qui ne nuisent en rien au fonctionnement.

Je suis assez allergique à ce genre de déclarations que l'on voit 99% du temps. Ce nombre est utilisé dans le digitalReadWrite qui demandent un uint8_t. Pourquoi demander un int (2 octets) plutôt qu'un uint8_t (1 octet). De plus c'est une constante, autant la définir comme telle. Cela fait:
const uint8_t RelAlima=2;
D'accord, de toutes façon le résultat est exactement le même, le compilateur corrige.

Usuellement la convention des nom en C++ serait de mettre les constantes en majuscules (LOW, HIGH, mais pourquoi pas aussi PC_USB, REL_ALIMA...), les variables en minuscules, avec un majuscule pour séparer les mots (chgtPCusb, temps...) C'est surtout pour celui qui lit le code sans l'avoir écrit.

C'est bien par contre de mettre des commentaires. C'est une bonne habitude à prendre.

ChgtPCusb contient la valeur précédente de PCusb qui est l'état du signal USB.
Au démarrage c'est le PC Musique qui alimente la carte Arduino via l'USB et je repique le +5 sur la pin 13 (PCusb) pour savoir si le PC est allumé ou pas. C'est pour ça qu'il y l'alim 9V (RelAlim) pour maintenir l'Arduino en vie à la coupure de l'USB.
Avec ChgtPCusb je peux calculer depuis combien de temps PCusb est actif (une remarque qui m'a été faite pour éviter le bagotement)

Pourquoi on ne peut pas faire ça? Ca fonctionne bien

Merci pour les remarques de moindre importance mais importantes tout de même. Je vais faire attention à tout ça.

J'ai modifié en pinMode(PCusb, INPUT)
PULLUP c'était juste pour mes essais.