Ajout stockage CV en mémoire non volatile

This commit is contained in:
Serge NOEL
2026-08-10 16:58:53 +02:00
parent 12bfe5ed20
commit f7ef209bdf
+52 -21
View File
@@ -1,6 +1,7 @@
#include <Arduino.h> #include <Arduino.h>
#include <Servo.h> #include <Servo.h>
#include <NmraDcc.h> #include <NmraDcc.h>
#include <EEPROM.h>
#define DCC_SIGNAL_PIN 2 #define DCC_SIGNAL_PIN 2
#define LED_PIN 3 #define LED_PIN 3
@@ -15,6 +16,9 @@
#define DEFAULT_MAX_UP 180 #define DEFAULT_MAX_UP 180
#define DEFAULT_MAX_DOWN 0 #define DEFAULT_MAX_DOWN 0
#define EEPROM_SIG_ADDR 0
#define EEPROM_SIG_VALUE 0xA5
NmraDcc Dcc; NmraDcc Dcc;
Servo servoMotor; Servo servoMotor;
uint8_t PalesSpeed = DEFAULT_PALES_SPEED; uint8_t PalesSpeed = DEFAULT_PALES_SPEED;
@@ -23,31 +27,60 @@ uint8_t ServoMaxDown = DEFAULT_MAX_DOWN;
int STROBE_ON = 0; int STROBE_ON = 0;
int HelicoUP = 0; int HelicoUP = 0;
struct CVPair
{
uint16_t CV;
uint8_t Value;
};
CVPair FactoryDefaultCVs[] = {
{CV_PALES_SPEED, DEFAULT_PALES_SPEED},
{CV_MAX_UP, DEFAULT_MAX_UP},
{CV_MAX_DOWN, DEFAULT_MAX_DOWN},
};
uint8_t FactoryDefaultCVIndex = 0;
void notifyCVAck(void) void notifyCVAck(void)
{ {
// Si le contrôleur demande un ACK de programmation CV, on peut utiliser une LED ou un signal dédié.
digitalWrite(LED_PIN, HIGH); digitalWrite(LED_PIN, HIGH);
delay(6); delay(6);
digitalWrite(LED_PIN, LOW); digitalWrite(LED_PIN, LOW);
} }
void notifyCVChange(uint16_t CV, uint8_t Value)
{
if (CV == CV_PALES_SPEED) {
PalesSpeed = Value;
} else if (CV == CV_MAX_UP) {
ServoMaxUp = Value;
} else if (CV == CV_MAX_DOWN) {
ServoMaxDown = Value;
}
}
void notifyCVResetFactoryDefault() void notifyCVResetFactoryDefault()
{ {
FactoryDefaultCVIndex = sizeof(FactoryDefaultCVs) / sizeof(CVPair); Dcc.setCV(CV_PALES_SPEED, DEFAULT_PALES_SPEED);
Dcc.setCV(CV_MAX_UP, DEFAULT_MAX_UP);
Dcc.setCV(CV_MAX_DOWN, DEFAULT_MAX_DOWN);
EEPROM.update(EEPROM_SIG_ADDR, EEPROM_SIG_VALUE);
}
void loadCvDefaultsIfNeeded()
{
if (EEPROM.read(EEPROM_SIG_ADDR) != EEPROM_SIG_VALUE) {
if (Dcc.isSetCVReady()) {
Dcc.setCV(CV_PALES_SPEED, DEFAULT_PALES_SPEED);
Dcc.setCV(CV_MAX_UP, DEFAULT_MAX_UP);
Dcc.setCV(CV_MAX_DOWN, DEFAULT_MAX_DOWN);
EEPROM.update(EEPROM_SIG_ADDR, EEPROM_SIG_VALUE);
}
}
}
void loadCvFromDcc()
{
PalesSpeed = Dcc.getCV(CV_PALES_SPEED);
if (PalesSpeed == 0) {
PalesSpeed = DEFAULT_PALES_SPEED;
}
ServoMaxUp = Dcc.getCV(CV_MAX_UP);
if (ServoMaxUp == 0) {
ServoMaxUp = DEFAULT_MAX_UP;
}
ServoMaxDown = Dcc.getCV(CV_MAX_DOWN);
if (ServoMaxDown == 0) {
ServoMaxDown = DEFAULT_MAX_DOWN;
}
} }
void notifyDccAccTurnoutOutput(uint16_t Addr, uint8_t Direction, uint8_t OutputPower) void notifyDccAccTurnoutOutput(uint16_t Addr, uint8_t Direction, uint8_t OutputPower)
@@ -58,6 +91,7 @@ void notifyDccAccTurnoutOutput(uint16_t Addr, uint8_t Direction, uint8_t OutputP
analogWrite(PWM_PIN, Direction ? PalesSpeed : 0); analogWrite(PWM_PIN, Direction ? PalesSpeed : 0);
} else if (Addr == 3) { } else if (Addr == 3) {
HelicoUP = Direction; HelicoUP = Direction;
servoMotor.write(Direction ? ServoMaxUp : ServoMaxDown);
} }
} }
@@ -80,17 +114,14 @@ void setup()
#endif #endif
Dcc.init(MAN_ID_DIY, 10, CV29_ACCESSORY_DECODER | CV29_OUTPUT_ADDRESS_MODE, 0); Dcc.init(MAN_ID_DIY, 10, CV29_ACCESSORY_DECODER | CV29_OUTPUT_ADDRESS_MODE, 0);
loadCvDefaultsIfNeeded();
loadCvFromDcc();
} }
void loop() void loop()
{ {
Dcc.process(); Dcc.process();
if (FactoryDefaultCVIndex && Dcc.isSetCVReady()) {
FactoryDefaultCVIndex--;
Dcc.setCV(FactoryDefaultCVs[FactoryDefaultCVIndex].CV, FactoryDefaultCVs[FactoryDefaultCVIndex].Value);
}
if (STROBE_ON) { if (STROBE_ON) {
digitalWrite(LED_PIN, HIGH); digitalWrite(LED_PIN, HIGH);
delay(100); delay(100);