@ -81,7 +81,7 @@ class DisplayMono {
mDispWidth = mDisplay - > getDisplayWidth ( ) ;
mDispHeight = mDisplay - > getDisplayHeight ( ) ;
mDispSwitchTime . stopTimeMonitor ( ) ;
if ( mCfg - > graph_ratio = = 100 ) // if graph ratio is 100% start in graph mode
if ( 100 = = mCfg - > graph_ratio ) // if graph ratio is 100% start in graph mode
mDispSwitchState = DispSwitchState : : GRAPH ;
else if ( mCfg - > graph_ratio ! = 0 )
mDispSwitchTime . startTimeMonitor ( 150 * ( 100 - mCfg - > graph_ratio ) ) ; // start display mode change only if ratio is neither 0 nor 100
@ -90,39 +90,70 @@ class DisplayMono {
// pixelshift screensaver with wipe effect
void calcPixelShift ( int range ) {
int8_t mod = ( millis ( ) / 10000 ) % ( ( range > > 1 ) < < 2 ) ;
mPixelshift = mCfg - > screenSaver = = 1 ? ( ( mod < range ) ? mod - ( range > > 1 ) : - ( mod - range - ( range > > 1 ) + 1 ) ) : 0 ;
mPixelshift = ( 1 = = mCfg - > screenSaver ) ? ( ( mod < range ) ? mod - ( range > > 1 ) : - ( mod - range - ( range > > 1 ) + 1 ) ) : 0 ;
}
protected :
enum class PowerGraphState {
NO_TIME_SYNC ,
IN_PERIOD ,
WAIT_4_NEW_PERIOD ,
WAIT_4_RESTART
} ;
// initialize power graph and allocate data buffer based on pixel width
void initPowerGraph ( uint8_t width , uint8_t height ) {
DBGPRINTLN ( F ( " ---- Init Power Graph ---- " ) ) ;
mPgWidth = width ;
mPgHeight = height ;
mPgData = new float [ mPgWidth ] ;
mPgState = PowerGraphState : : NO_TIME_SYNC ;
resetPowerGraph ( ) ;
/*
Inverter < > * iv ;
mPgMaxAvailPower = 0 ;
uint8_t nInv = mSys - > getNumInverters ( ) ;
for ( uint8_t i = 0 ; i < nInv ; i + + ) {
iv = mSys - > getInverterByPos ( i ) ;
if ( iv = = NULL )
continue ;
for ( uint8_t ch = 0 ; ch < 6 ; ch + + ) {
mPgMaxAvailPower + = iv - > config - > chMaxPwr [ ch ] ;
}
}
DBGPRINTLN ( " max. Power = " + String ( mPgMaxAvailPower ) ) ; */
}
// add new value to power graph and maintain state engine for period times
void addPowerGraphEntry ( float val ) {
if ( ( nullptr ! = mPgData ) & & ( mDisplayData - > utcTs > 0 ) ) { // precondition: power graph initialized and utc time available
calcPowerGraphValues ( ) ;
//mPgData[mPgLastPos] = std::max(mPgData[mPgLastPos], (uint8_t) (val * 255.0 / mPgMaxAvailPower)); // normalizing of data to 0-255
mPgData [ mPgLastPos ] = std : : max ( mPgData [ mPgLastPos ] , val ) ;
mPgMaxPwr = std : : max ( mPgMaxPwr , val ) ; // max value of stored data for scaling of y-axis
if ( nullptr = = mPgData ) // power graph not initialized
return ;
bool store_entry = false ;
switch ( mPgState ) {
case PowerGraphState : : NO_TIME_SYNC :
if ( ( mDisplayData - > pGraphStartTime > 0 ) & & ( mDisplayData - > pGraphEndTime > 0 ) & & // wait until period data is available ...
( mDisplayData - > utcTs > = mDisplayData - > pGraphStartTime ) & & ( mDisplayData - > utcTs < mDisplayData - > pGraphEndTime ) ) { // and current time is in period
storeStartEndTimes ( ) ; // period was received -> store
store_entry = true ;
mPgState = PowerGraphState : : IN_PERIOD ;
}
break ;
case PowerGraphState : : IN_PERIOD :
if ( mDisplayData - > utcTs > mPgEndTime ) // check if end of day is reached ...
mPgState = PowerGraphState : : WAIT_4_NEW_PERIOD ; // then wait for new period setting
else
store_entry = true ;
break ;
case PowerGraphState : : WAIT_4_NEW_PERIOD :
if ( ( mPgStartTime ! = mDisplayData - > pGraphStartTime ) | | ( mPgEndTime ! = mDisplayData - > pGraphEndTime ) ) { // wait until new time period was received ...
storeStartEndTimes ( ) ; // and store it for next period
mPgState = PowerGraphState : : WAIT_4_RESTART ;
}
break ;
case PowerGraphState : : WAIT_4_RESTART :
if ( ( mDisplayData - > utcTs > = mPgStartTime ) & & ( mDisplayData - > utcTs < mPgEndTime ) ) { // wait until current time is in period again ...
resetPowerGraph ( ) ; // then reset power graph data
store_entry = true ;
mPgState = PowerGraphState : : IN_PERIOD ;
}
break ;
}
if ( store_entry ) {
mPgLastPos = std : : min ( ( uint8_t ) sss2PgPos ( mDisplayData - > utcTs - mPgStartTime ) , ( uint8_t ) ( mPgWidth - 1 ) ) ; // current datapoint based on seconds since start
mPgData [ mPgLastPos ] = std : : max ( mPgData [ mPgLastPos ] , val ) ; // update current datapoint to maximum of all seen values
mPgMaxPwr = std : : max ( mPgMaxPwr , val ) ; // update max value of stored data for scaling of y-axis
}
}
// plot power graph to given display offset
void plotPowerGraph ( uint8_t xoff , uint8_t yoff ) {
if ( nullptr = = mPgData ) // power graph not initialized
return ;
@ -146,7 +177,7 @@ class DisplayMono {
tm . Minute = 0 ;
tm . Second = 0 ;
for ( ; tm . Hour < = endHour ; tm . Hour + + ) {
uint8_t x_pos_screen = getPowerGraphXpos ( sss2pgp os ( ( uint32_t ) makeTime ( tm ) - mDisplayData - > pGraphStartTime ) ) ; // scale horizontal axis
uint8_t x_pos_screen = getPowerGraphXpos ( sss2PgP os ( ( uint32_t ) makeTime ( tm ) - mDisplayData - > pGraphStartTime ) ) ; // scale horizontal axis
mDisplay - > drawPixel ( xoff + x_pos_screen , yoff - 1 ) ;
}
@ -163,8 +194,8 @@ class DisplayMono {
// draw curve
for ( uint8_t i = 1 ; i < = mPgLastPos ; i + + ) {
mDisplay - > drawLine ( xoff + getPowerGraphXpos ( i - 1 ) , yoff - getPowerGraphYpos ( i - 1 ) ,
xoff + getPowerGraphXpos ( i ) , yoff - getPowerGraphYpos ( i ) ) ;
mDisplay - > drawLine ( xoff + getPowerGraphXpos ( i - 1 ) , yoff - getPowerGraphValue Ypos ( i - 1 ) ,
xoff + getPowerGraphXpos ( i ) , yoff - getPowerGraphValue Ypos ( i ) ) ;
}
// print max power value
@ -195,6 +226,7 @@ class DisplayMono {
return change ;
}
// reset power graph
void resetPowerGraph ( ) {
if ( mPgData ! = nullptr ) {
mPgMaxPwr = 0.0 ;
@ -205,34 +237,35 @@ class DisplayMono {
}
}
uint8_t sss2pgpos ( uint seconds_since_start ) {
uint32_t diff = ( mDisplayData - > pGraphEndTime - mDisplayData - > pGraphStartTime ) ;
if ( diff )
return ( seconds_since_start * ( mPgWidth - 1 ) / diff ) ;
return 0 ;
// store start and end times of current time period and calculate period length
void storeStartEndTimes ( ) {
mPgStartTime = mDisplayData - > pGraphStartTime ;
mPgEndTime = mDisplayData - > pGraphEndTime ;
mPgPeriod = mDisplayData - > pGraphEndTime - mDisplayData - > pGraphStartTime ; // time period of power graph in sec for scaling of x-axis
}
void calcPowerGraphValues ( ) {
mPgPeriod = mDisplayData - > pGraphEndTime - mDisplayData - > pGraphStartTime ; // length of power graph for scaling of x-axis
uint32_t oldTimeOfDay = mPgTimeOfDay ;
mPgTimeOfDay = ( mDisplayData - > utcTs > mDisplayData - > pGraphStartTime ) ? mDisplayData - > utcTs - mDisplayData - > pGraphStartTime : 0 ; // current time of day with respect to current sunrise time
if ( oldTimeOfDay > mPgTimeOfDay ) // new day -> reset old data
resetPowerGraph ( ) ;
if ( 0 = = mPgPeriod )
mPgPeriod = 1 ;
mPgLastPos = std : : min ( ( uint8_t ) ( mPgTimeOfDay * ( mPgWidth - 1 ) / mPgPeriod ) , ( uint8_t ) ( mPgWidth - 1 ) ) ; // current datapoint based on currenct time of day
// get power graph datapoint index, scaled to current time period, by seconds since start
uint8_t sss2PgPos ( uint seconds_since_start ) {
if ( mPgPeriod )
return ( seconds_since_start * ( mPgWidth - 1 ) / mPgPeriod ) ;
else
return 0 ;
}
uint8_t getPowerGraphXpos ( uint8_t p ) {
// get X-position of power graph, scaled to lastpos, by according data point index
uint8_t getPowerGraphXpos ( uint8_t p ) {
if ( ( p < = mPgLastPos ) & & ( mPgLastPos > 0 ) )
return ( ( p * ( mPgWidth - 1 ) ) / mPgLastPos ) ; // scaling of x-axis
return 0 ;
else
return 0 ;
}
uint8_t getPowerGraphYpos ( uint8_t p ) {
// get Y-position of power graph, scaled to maximum value, by according datapoint index
uint8_t getPowerGraphValueYpos ( uint8_t p ) {
if ( ( p < mPgWidth ) & & ( mPgMaxPwr > 0 ) )
return ( ( mPgData [ p ] * ( uint32_t ) mPgHeight / mPgMaxPwr ) ) ; // scaling of data to graph height
return 0 ;
else
return 0 ;
}
protected :
@ -254,9 +287,11 @@ class DisplayMono {
float * mPgData = nullptr ;
uint8_t mPgHeight = 0 ;
float mPgMaxPwr = 0.0 ;
uint32_t mPgPeriod = 0 ; // seconds
uint32_t mPgTimeOfDay = 0 ;
uint32_t mPgStartTime = 0 ;
uint32_t mPgEndTime = 0 ;
uint32_t mPgPeriod = 0 ; // seconds
uint8_t mPgLastPos = 0 ;
PowerGraphState mPgState = PowerGraphState : : NO_TIME_SYNC ;
uint16_t mDispHeight ;
uint8_t mLuminance ;