Browse Source

got dimming working, dimming from ldr, can be testet via webbrowser; dynamic dimmer_t used for both dimmers, can be selected via dimmer_type_t (DIM_STUFEN, DIM_LDR)

tags/v1.0.0
Simon Schmidt 2 years ago
parent
commit
7643961ed2
2 changed files with 114 additions and 155 deletions
  1. 94
    132
      lib/treppe/treppe.cpp
  2. 20
    23
      lib/treppe/treppe.h

+ 94
- 132
lib/treppe/treppe.cpp View File

// #define DEBUG_TIMING // #define DEBUG_TIMING


/* /*
- dimmt stufe (0 - 15, PCA9685 outputs) mit linearen ticks
von idle bis active pwm
- return false solange gedimmt wird
- return true bei nächster stufe
- dimmer_tick: increment pwm jeden tick, bis anim beendet
- return: fsm_pend.anim_beendet
*/ */
bool Treppe::dimm_stufe(uint8_t stufe)
bool Treppe::dimmer_tick(dimmer_t* dimmer, bool dim_type)
{ {
if (fsm_outputs.dimmrichtung == DR_AUFDIMMEN)
dimmer_stufe.pwm += dimmer_stufe.delta_pwm;
else
dimmer_stufe.pwm -= dimmer_stufe.delta_pwm;
Serial.printf("%3.0f", dimmer_stufe.pwm);
pwmController.setChannelPWM(stufe, static_cast<uint16_t>(dimmer_stufe.pwm));
dimmer->pwm += dimmer->delta_pwm;
Serial.printf("%.0f", dimmer->pwm);

if(dim_type == DIM_STUFEN) {
pwmController.setChannelPWM(dimmer->stufe, static_cast<uint16_t>(dimmer->pwm));
} else { // DIM_LDR
pwmController.setAllChannelsPWM(static_cast<uint16_t>(dimmer->pwm));
}


dimmer_stufe.tick++;
if (dimmer_stufe.tick >= dimmer_stufe.ticks)
dimmer->tick++;
if (dimmer->tick < dimmer->ticks)
{ {
Serial.println("");
Serial.print("-");
return false; return false;
} }
Serial.print(" - ");
return true;
}


/*
- dimmt treppe (all PCA9685 outputs) mit linearen ticks
von idle bis active brightness
- return false solange gedimmt wird
- return true bei ende
*/
bool Treppe::dimm_treppe()
{
// needs to be in state machine
return true;
}


/*
- nach dem dimmen einer stufe wird die stufe weitergezählt
- abbruch am ende => anim_beendet = true;
*/
void Treppe::anim_tick()
{
if (!dimm_stufe(dimmer_stufe.stufe))
Serial.println("");
if(dim_type == DIM_LDR) {
Serial.printf("DIM_LDR: start: %d, ziel: %d\n",
dimmer->start_pwm, dimmer->ziel_pwm);
return true;
}
else // DIM_STUFEN
{ {
// Serial.printf("anim_tick(): stufe: %d, start: %d, ziel: %d, current %f\n",
// stufe, start_pwm, ziel_pwm, current_pwm);
Serial.printf("DIM_STUFEN: stufe: %d, start: %d, ziel: %d\n",
dimmer->stufe, dimmer->start_pwm, dimmer->ziel_pwm);

if (fsm_outputs.laufrichtung == LR_HOCH) if (fsm_outputs.laufrichtung == LR_HOCH)
{ {
if (dimmer_stufe.stufe >= stufen - 1)
{
anim_beendet = true;
return;
}
dimmer_stufe.stufe++;
if (dimmer->stufe >= stufen - 1)
return true;
dimmer->stufe++;
} }
else
else // LR_RUNTER
{ {
if (dimmer_stufe.stufe <= 0)
{
anim_beendet = true;
return;
}
dimmer_stufe.stufe--;
if (dimmer->stufe <= 0)
return true;
dimmer->stufe--;
} }
dimmer_stufe.tick = 0;
dimmer_stufe.pwm = dimmer_stufe.start_pwm;
dimmer->tick = 0;
dimmer->pwm = dimmer->start_pwm;
} }
return false;
} }


// startbedingunen für animation // startbedingunen für animation
void Treppe::start_animation()
void Treppe::start_animation( dimmer_t* dimmer, bool dim_type,
uint16_t on_pwm, uint16_t off_pwm)
{ {
anim_beendet = false;
fsm_pend.anim_beendet = false;


if (fsm_outputs.laufrichtung == LR_HOCH)
dimmer_stufe.stufe = 0;
else
dimmer_stufe.stufe = stufen - 1;
if(dim_type == DIM_STUFEN) {
if (fsm_outputs.laufrichtung == LR_HOCH)
dimmer->stufe = 0;
else
dimmer->stufe = stufen - 1;

dimmer->ticks = time_per_stair / INT_TIME; // [ms]
}
else { // DIM_LDR
dimmer->ticks = time_ldr / INT_TIME; // [ms]
}


if (fsm_outputs.dimmrichtung == DR_AUFDIMMEN) if (fsm_outputs.dimmrichtung == DR_AUFDIMMEN)
{ {
dimmer_stufe.start_pwm = idle_pwm_ist;
dimmer_stufe.ziel_pwm = active_pwm;
dimmer->start_pwm = off_pwm;
dimmer->ziel_pwm = on_pwm;
dimmer->delta_pwm = (float)(on_pwm - off_pwm)
/ (float)dimmer->ticks;
} }
else else
{ {
dimmer_stufe.start_pwm = active_pwm;
dimmer_stufe.ziel_pwm = idle_pwm_ist;
dimmer->start_pwm = on_pwm;
dimmer->ziel_pwm = off_pwm;
dimmer->delta_pwm = (float)(off_pwm - on_pwm)
/ (float)dimmer->ticks;
} }


dimmer_stufe.tick = 0;
dimmer_stufe.pwm = dimmer_stufe.start_pwm;
dimmer->tick = 0;
dimmer->pwm = dimmer->start_pwm;

Serial.printf("stufe %d, ticks %d, delta %f, start %d, ziel %d\n",
dimmer->stufe, dimmer->ticks, dimmer->delta_pwm, dimmer->start_pwm, dimmer->ziel_pwm);
} }


void Treppe::print_state_on_change() void Treppe::print_state_on_change()
float ldr = read_ldr(); float ldr = read_ldr();


if (ldr < ldr_schwelle) { if (ldr < ldr_schwelle) {
idle_pwm_soll = idle_pwm_max;
active = true;
active = 1;
} }
if (ldr > ldr_schwelle + LDR_HYS) { if (ldr > ldr_schwelle + LDR_HYS) {
idle_pwm_soll = 0;
active = false;
active = 0;
} }

if (idle_pwm_soll != idle_pwm_ist) {
}
activate_idle_pwm(active);
return active; return active;
} }




fsm_inputs.sensor_oben = read_sensor(SENSOR_OBEN); fsm_inputs.sensor_oben = read_sensor(SENSOR_OBEN);
fsm_inputs.sensor_unten = read_sensor(SENSOR_UNTEN); fsm_inputs.sensor_unten = read_sensor(SENSOR_UNTEN);
fsm_inputs.anim_beendet = anim_beendet;
fsm_inputs.anim_beendet = fsm_pend.anim_beendet;


#ifdef DEBUG_TIMING #ifdef DEBUG_TIMING
Serial.print("2:"); Serial.print("2:");
fsm_outputs.status == ST_AUFDIMMEN_RUNTER || fsm_outputs.status == ST_AUFDIMMEN_RUNTER ||
fsm_outputs.status == ST_ABDIMMEN_RUNTER ) fsm_outputs.status == ST_ABDIMMEN_RUNTER )
{ {
if(anim_beendet)
start_animation();
if(fsm_pend.anim_beendet)
start_animation(&dimmer_stufen, DIM_STUFEN, active_pwm, idle_pwm_ist);
else else
anim_tick();
fsm_pend.anim_beendet = dimmer_tick(&dimmer_stufen, DIM_STUFEN);
}
else if ( fsm_outputs.status == ST_AUFDIMMEN_LDR ||
fsm_outputs.status == ST_ABDIMMEN_LDR )
{
if(fsm_pend.anim_beendet)
start_animation(&dimmer_ldr, DIM_LDR, idle_pwm_ist, 0);
else
fsm_pend.anim_beendet = dimmer_tick(&dimmer_ldr, DIM_LDR);
}
else if ( fsm_outputs.status == ST_RUHEZUSTAND )
{
if ( fsm_pend.ldr_changed ) {
fsm_pend.ldr_changed = false;
fsm_outputs.dimmrichtung = DR_AUFDIMMEN;
start_animation(&dimmer_ldr, DIM_LDR, idle_pwm_soll, idle_pwm_ist);
idle_pwm_ist = idle_pwm_soll;
}
if(!fsm_pend.anim_beendet) {
fsm_pend.anim_beendet = dimmer_tick(&dimmer_ldr, DIM_LDR);
}
} }


#ifdef DEBUG_TIMING
Serial.print("5:");
Serial.println(micros()-m);
m=micros();
#endif


// else if (fsm_outputs.status == ST_DIMMEN_LDR) {
// if(anim_beendet) {
// berechne_dimmer();
// anim_beendet = false;
// }
// anim_beendet = dimm_treppe();
// }


#ifdef DEBUG_TIMING #ifdef DEBUG_TIMING
Serial.print("6:");
Serial.print("5:");
Serial.println(micros()-m); Serial.println(micros()-m);
#endif #endif
} }


void Treppe::berechne_dimmer()
{
dimmer_stufe.ticks = time_per_stair / INT_TIME; // [ms]
dimmer_stufe.delta_pwm = (float)(active_pwm - idle_pwm_ist)
/ (float)dimmer_stufe.ticks;

dimmer_ldr.ticks = time_ldr / INT_TIME; // [ms]
dimmer_ldr.delta_pwm = (float)(idle_pwm_soll - idle_pwm_ist)
/ (float)dimmer_ldr.ticks;
}

void Treppe::setup() void Treppe::setup()
{ {
pwmController.resetDevices(); pwmController.resetDevices();
pinMode(OE, OUTPUT); pinMode(OE, OUTPUT);
digitalWrite(OE, 0); digitalWrite(OE, 0);


Serial.printf("dimmer_stufe.delta_pwm %f\n", dimmer_stufe.delta_pwm);
Serial.printf("Treppe: initial parameters: stufen=%d\n", stufen);
Serial.printf("Treppe: stufen=%d\n", stufen);
} }


void Treppe::set_idle_prozent(const int prozent) void Treppe::set_idle_prozent(const int prozent)
void Treppe::set_idle_pwm_max(const uint16_t new_pwm) void Treppe::set_idle_pwm_max(const uint16_t new_pwm)
{ {
if(new_pwm > active_pwm) { if(new_pwm > active_pwm) {
idle_pwm_max = active_pwm;
idle_pwm_soll = active_pwm;
} else { } else {
idle_pwm_max = new_pwm;
idle_pwm_soll = new_pwm;
} }


Serial.printf("Treppe: idle_pwm_max=%d\n", idle_pwm_max);
berechne_dimmer();
activate_idle_pwm(true);
}

void Treppe::activate_idle_pwm(bool active)
{
static uint16_t last_pwm = 0;

if (fsm_outputs.status == ST_RUHEZUSTAND || fsm_outputs.status == ST_INAKTIV_LDR)
{
idle_pwm_ist = idle_pwm_max * active;
if (idle_pwm_ist != last_pwm)
{
// Dimming Function for all LEDS ?
berechne_dimmer();
pwmController.setAllChannelsPWM(idle_pwm_ist);
last_pwm = idle_pwm_ist;
}
}
Serial.printf("Treppe: idle_pwm_soll=%d\n", idle_pwm_soll);
fsm_pend.ldr_changed = true;
} }


void Treppe::set_active_pwm(uint16_t _active_pwm) void Treppe::set_active_pwm(uint16_t _active_pwm)
{ {
active_pwm = _active_pwm; active_pwm = _active_pwm;
berechne_dimmer();
Serial.printf("Treppe: active_pwm=%d\n", active_pwm); Serial.printf("Treppe: active_pwm=%d\n", active_pwm);
} }
void Treppe::set_time_per_stair(uint16_t _time_per_stair) void Treppe::set_time_per_stair(uint16_t _time_per_stair)
{ {
time_per_stair = _time_per_stair; time_per_stair = _time_per_stair;
berechne_dimmer();
Serial.printf("Treppe: time_per_stair=%d\n", time_per_stair); Serial.printf("Treppe: time_per_stair=%d\n", time_per_stair);
} }

+ 20
- 23
lib/treppe/treppe.h View File

class Treppe { class Treppe {
private: private:
const uint8_t stufen; const uint8_t stufen;
const uint16_t time_ldr = 300;
const uint16_t time_ldr = 500;
uint16_t time_per_stair = 300; // dimmtime per stair [ms] uint16_t time_per_stair = 300; // dimmtime per stair [ms]
uint16_t idle_pwm_max = 100; uint16_t idle_pwm_max = 100;
uint16_t idle_pwm_ist = 0;
uint16_t idle_pwm_ist = idle_pwm_max;
uint16_t idle_pwm_soll = 0; uint16_t idle_pwm_soll = 0;
uint16_t active_pwm = 700; uint16_t active_pwm = 700;


uint16_t ldr_schwelle = 2; // activation value for FSM [lx] uint16_t ldr_schwelle = 2; // activation value for FSM [lx]
struct fsm_pending_inputs_t {
bool anim_beendet = true;
bool sensor_unten = false;
bool sensor_oben = false;
bool ldr_changed = false;
};
fsm_pending_inputs_t fsm_pend;


bool anim_beendet = true;

struct dimmer_stufe_t {
struct dimmer_t {
uint8_t stufe = 0; uint8_t stufe = 0;
uint16_t ticks = 0; uint16_t ticks = 0;
uint16_t tick = 0; uint16_t tick = 0;
uint16_t start_pwm = 0; uint16_t start_pwm = 0;
uint16_t ziel_pwm = 0; uint16_t ziel_pwm = 0;
}; };
dimmer_stufe_t dimmer_stufe;

struct dimmer_ldr_t {
uint16_t ticks = 0;
uint16_t tick = 0;

float delta_pwm = 0.0;
float pwm = 0.0;
uint16_t start_pwm = 0;
uint16_t ziel_pwm = 0;
enum dimmer_type_t {
DIM_STUFEN=0,
DIM_LDR=1
}; };
dimmer_ldr_t dimmer_ldr;
dimmer_t dimmer_stufen;
dimmer_t dimmer_ldr;
// initialize with i2c-Address 0, use Wire Library // initialize with i2c-Address 0, use Wire Library
PCA9685 pwmController; PCA9685 pwmController;
}; };


/* DIMM */ /* DIMM */
bool dimm_stufe(uint8_t stufe);
bool dimm_treppe();
void anim_tick();
void start_animation();
void berechne_dimmer();
// bool dimmer(dimmer_t* dimmer, bool dim_type);
bool dimmer_tick(dimmer_t* dimmer, bool dim_type);
void start_animation(dimmer_t* dimmer, bool dim_type,
uint16_t on_pwm, uint16_t off_pwm);
// void berechne_dimmer(dimmer_t* dimmer, bool dim_type);
void print_state_on_change(); void print_state_on_change();


/* LDR */ /* LDR */
public: public:
Treppe(uint8_t _stufen) : stufen(_stufen){ Treppe(uint8_t _stufen) : stufen(_stufen){
FSMTreppe_Obj.initialize(); FSMTreppe_Obj.initialize();
berechne_dimmer();
} }
~Treppe() { ~Treppe() {
FSMTreppe_Obj.terminate(); FSMTreppe_Obj.terminate();
// Parameter section // Parameter section
void set_idle_prozent(int prozent); void set_idle_prozent(int prozent);
void set_idle_pwm_max(const uint16_t new_pwm); void set_idle_pwm_max(const uint16_t new_pwm);
void activate_idle_pwm(bool active);
void set_active_pwm(uint16_t _active_pwm); void set_active_pwm(uint16_t _active_pwm);
void set_time_per_stair(uint16_t _time_per_stair); void set_time_per_stair(uint16_t _time_per_stair);
}; };

Loading…
Cancel
Save