From 61fc04ed8639b2f94ea67fb039beac90d9371072 Mon Sep 17 00:00:00 2001 From: stefanbode Date: Sun, 13 Mar 2022 11:30:05 +0100 Subject: [PATCH] Added comments and code description --- tasmota/xsns_01_counter.ino | 16 ++++++++++------ 1 file changed, 10 insertions(+), 6 deletions(-) diff --git a/tasmota/xsns_01_counter.ino b/tasmota/xsns_01_counter.ino index 6bd580612..20c0ecc81 100644 --- a/tasmota/xsns_01_counter.ino +++ b/tasmota/xsns_01_counter.ino @@ -52,15 +52,15 @@ struct COUNTER { struct AC_ZERO_CROSS_DIMMER { bool startReSync = false; // set to TRUE if zero-cross event occurs bool startMeasurePhase[MAX_COUNTERS] ; // set to TRUE if channel is ON and zero-cross occurs to initiate phase measure on channel - bool pwm_defined[MAX_COUNTERS]; + bool pwm_defined[MAX_COUNTERS]; // check if all GPIO are set and zerocross enabled. Then ADD dimmer. bool PWM_ON[MAX_COUNTERS] ; // internal ON/OFF of the channel uint32_t current_cycle_ClockCycles = 0; // amount of clock cycles between two zero-cross events. uint32_t currentPWMCycleCount[MAX_COUNTERS] ; // clock cycle time of PWM channel, required to measure actual phase. [3] is phase of zero-cross int16_t currentShiftClockCycle[MAX_COUNTERS]; // dynamic phase correction per channel in clock cycles uint32_t tobe_cycle_timeClockCycles = 0; // clock cycles between zero-cross events. Depend on main frequency and CPU speed - uint32_t lastCycleCount = 0; - uint32_t currentSteps = 100; - uint32_t high; + uint32_t lastCycleCount = 0; // Last value of GetCycleCount during zero-cross sychronisation + uint32_t currentSteps = 100; // dynamic value of zero-crosses between two sychronisation intervalls (default=20 == 200ms at 100Hz) + uint32_t high; // cycle counts for PWM high vaule. needs long enough (4µs) to secure fire TRIAC } ac_zero_cross_dimmer; #endif //USE_AC_ZERO_CROSS_DIMMER @@ -98,10 +98,10 @@ void IRAM_ATTR CounterIsrArg(void *arg) { ac_zero_cross_dimmer.currentPWMCycleCount[index] = ESP.getCycleCount(); ac_zero_cross_dimmer.startMeasurePhase[index] = false; } - // if zero-cross event occurs (200ms window, 5-times a second) and device is online for 10sec + // if zero-cross event occurs (200ms window, 5-times a second) and device is online for >10sec if (index == 3 && RtcSettings.pulse_counter[index]%(Settings->pwm_frequency / 5) == 0 && ac_zero_cross_dimmer.pwm_defined[index] && millis() > 10000) { ac_zero_cross_dimmer.currentPWMCycleCount[index] = ESP.getCycleCount(); - // 1000µs to ensure not to fire on the next sinus wave + if (ac_zero_cross_dimmer.lastCycleCount > 0) { // start phase measure on PWM channels and initiate phase sync with zero-cross. ac_zero_cross_dimmer.startReSync = true; @@ -169,6 +169,8 @@ void CounterInit(void) ac_zero_cross_dimmer.current_cycle_ClockCycles = ac_zero_cross_dimmer.tobe_cycle_timeClockCycles = microsecondsToClockCycles(1000000 / Settings->pwm_frequency); // short fire on PWM to ensure not to hit next sinus curve but trigger the TRIAC. 0.78% of duty cycle (10ms) ~4µs ac_zero_cross_dimmer.high = ac_zero_cross_dimmer.current_cycle_ClockCycles / 256; + + // Support for dimmer 1-3. Counter4 reseverd for zero-cross signal if ((i < MAX_COUNTERS-1 && PinUsed(GPIO_PWM1, i)) || ( i == MAX_COUNTERS-1) ) { ac_zero_cross_dimmer.pwm_defined[i] = true; if (i == 3) { @@ -303,6 +305,7 @@ void SyncACDimmer(void) ac_zero_cross_dimmer.PWM_ON[i]=true; pinMode(Pin(GPIO_PWM1, i), OUTPUT); } else { + // currentShiftClockCycle is an I-Controller (not PID) to realign the phase. grace time are 5 clock cycles ac_zero_cross_dimmer.currentShiftClockCycle[i] += phaseShift_ClockCycles > 5 ? 1 : (phaseShift_ClockCycles < -5 ? -1 : 0); ac_zero_cross_dimmer.current_cycle_ClockCycles += ac_zero_cross_dimmer.currentShiftClockCycle[i]+phaseShift_ClockCycles; } @@ -311,6 +314,7 @@ void SyncACDimmer(void) startWaveformClockCycles(Pin(GPIO_PWM1, i), ac_zero_cross_dimmer.high, ac_zero_cross_dimmer.current_cycle_ClockCycles - ac_zero_cross_dimmer.high, 0, -1, 0, true); #endif // ESP8266 #ifdef ESP32 + // Under investigation. Still not working double esp32freq = 1000000.0 / clockCyclesToMicroseconds(ac_zero_cross_dimmer.current_cycle_ClockCycles); ledcSetup(i, esp32freq, 10); ledcAttachPin(Pin(GPIO_PWM1, i), i);