Hi,
Finally, I can use my card with 74HC595 to use 8 relays. I found a beginning of code which I modified to use it with Home Assistant because the original does not save the starting values on the node. If it can be used for others …
#include <Arduino.h>
/* Fonctionnement de 8 relais à l'aide de montage et du 74HC595
Le status est conservé lors de la coupure de courant et peut faire
actionner des relais.
Réjean Maltais 2019
Ajout des valeurs enregistré dans l'eeprom.
Version originale du programme L. Lemarinel
*/
// Radio enable
#define MY_RADIO_RF24
#define MY_DEBUG
#include <SPI.h>
#include <MySensors.h>
#define SN "8-Relais"
#define SV "1.6"
#define RELAY_ON 1
#define RELAY_OFF 0
#define NB_OUTPUTS 8
// Utilise le composant 74HC595 pour minimiser le nombre sorties.
#define OUTPUT_SER 7 // Data
#define OUTPUT_RCLK 8 // Latch
#define OUTPUT_SRCLK 4 // Clock
#define OUTPUT_ENA 6 // Enable (Must be low with my board, othewise not need)
#define CHILD_ID 0
#define HEARTBEAT_DELAY 3600000
bool initialValueSent = false;
bool state;
byte outputStates;
unsigned long lastHeartBeat=0;
void changeOutputState(int i, boolean newState){
bitWrite(outputStates, i, newState);
// Lock latch
digitalWrite(OUTPUT_RCLK, LOW);
// Write bits
shiftOut(OUTPUT_SER, OUTPUT_SRCLK, MSBFIRST, outputStates);
// Unlock latch
digitalWrite(OUTPUT_RCLK, HIGH);
}
void updateStatus()
{
for (int sensor=0; sensor<NB_OUTPUTS; sensor++)
{
MyMessage initMsg(sensor, V_STATUS);
int lstate = loadState(sensor);
//changeOutputState(initMsg.sensor, lstate);
Serial.print("Valeur dans l'eprom: ");
Serial.println(lstate);
// Set relay to last known state (using eeprom storage)
send(initMsg.setSensor(sensor).set(lstate?RELAY_ON:RELAY_OFF));
changeOutputState(sensor, lstate);
}
}
void setup()
{
pinMode( OUTPUT_SER, OUTPUT);
pinMode( OUTPUT_RCLK, OUTPUT);
pinMode( OUTPUT_SRCLK, OUTPUT);
pinMode( OUTPUT_ENA, OUTPUT);
// Activé le 74HC595 en raison de la configuration de la plaquette.
digitalWrite(OUTPUT_ENA, LOW);
// Ici avec Home Assistant, on doit initialisé les relais pour qu'il soit reconnus
updateStatus();
}
void presentation() {
// Send the Sketch Version Information to the Gateway
sendSketchInfo(SN, SV);
// Présentation de tous les relais :
for (int i=0; i< NB_OUTPUTS; i++){
present(i, S_BINARY );
}
}
void loop(){
// Send a HeartBeat frequently so Domoticz see us as alive.
if (millis() > lastHeartBeat + HEARTBEAT_DELAY){
lastHeartBeat = millis();
sendHeartbeat();
}
}
void receive(const MyMessage &message){
boolean currentStatus;
switch(message.type){
case V_CUSTOM:
// Revert output status :
currentStatus=bitRead(outputStates, message.sensor);
changeOutputState(message.sensor, !currentStatus);
break;
case V_STATUS:
changeOutputState(message.sensor, message.getBool());
break;
}
// Send new state :
currentStatus=bitRead(outputStates, message.sensor);
MyMessage msg(message.sensor, V_STATUS);
msg.set(currentStatus);
send(msg);
saveState(message.getSensor(), message.getBool());
Serial.print("Incoming change for sensor:");
Serial.print(message.getSensor());
Serial.print(", New status: ");
Serial.println(message.getBool());
}
Regards,