Prepare for upstream merge: seperate declarations from definitions

In rotary and 4ld
This commit is contained in:
Ewoud
2023-06-27 22:21:20 +02:00
parent d53de3d82b
commit 17147f3b50
2 changed files with 2098 additions and 1788 deletions

View File

@@ -120,23 +120,6 @@ class FourLineDisplayUsermod : public Usermod {
// HW interface & configuration // HW interface & configuration
U8X8 *u8x8 = nullptr; // pointer to U8X8 display object U8X8 *u8x8 = nullptr; // pointer to U8X8 display object
#if defined(ARDUINO_ARCH_ESP32) && defined(FLD_ESP32_USE_THREADS)
// semaphores - needed on ESP32 only, as we use a separate task to update the display
SemaphoreHandle_t drawMux = xSemaphoreCreateBinary(); // for drawstring and drawglyph functions (to prevent concurrent access to HW)
SemaphoreHandle_t drawMuxBig = xSemaphoreCreateBinary(); // for draw2x2GlyphIcons() and showCurrentEffectOrPalette() - more complex and not thread-safe
const TickType_t maxWait = 300 * portTICK_PERIOD_MS; // wait max. 300ms (drawstring semaphore)
const TickType_t maxWaitLong = 800 * portTICK_PERIOD_MS; // wait max. 800ms (big drawing semaphore)
#define FLD_SemaphoreTake(x,t) xSemaphoreTake((x),(t))
#define FLD_SemaphoreGive(x) xSemaphoreGive(x)
#else
// 8266 or no tasks - no semaphores
#define FLD_SemaphoreTake(x,t) pdTRUE
#define FLD_SemaphoreGive(x)
#if !defined(ARDUINO_ARCH_ESP32) && !defined(pdTRUE)
#define pdTRUE true
#endif
#endif
#ifndef FLD_SPI_DEFAULT #ifndef FLD_SPI_DEFAULT
int8_t ioPin[5] = {FLD_PIN_SCL, FLD_PIN_SDA, -1, -1, -1}; // I2C pins: SCL, SDA int8_t ioPin[5] = {FLD_PIN_SCL, FLD_PIN_SDA, -1, -1, -1}; // I2C pins: SCL, SDA
uint32_t ioFrequency = 400000; // in Hz (minimum is 100000, baseline is 400000 and maximum should be 3400000) uint32_t ioFrequency = 400000; // in Hz (minimum is 100000, baseline is 400000 and maximum should be 3400000)
@@ -214,7 +197,7 @@ class FourLineDisplayUsermod : public Usermod {
// or check the gallery: // or check the gallery:
// https://github.com/olikraus/u8g2/wiki/gallery // https://github.com/olikraus/u8g2/wiki/gallery
// is this display using SPI? // WLEDMM is this display using SPI?
bool displayIsSPI(DisplayType disp) { bool displayIsSPI(DisplayType disp) {
switch(disp) { switch(disp) {
case SSD1306_SPI: // falls thru case SSD1306_SPI: // falls thru
@@ -229,7 +212,231 @@ class FourLineDisplayUsermod : public Usermod {
} }
// some displays need this to properly apply contrast // some displays need this to properly apply contrast
void setVcomh(bool highContrast) { void setVcomh(bool highContrast);
/**
* Wrappers for screen drawing
*/
void setFlipMode(uint8_t mode);
void setContrast(uint8_t contrast);
void drawString(uint8_t col, uint8_t row, const char *string, bool ignoreLH=false);
void draw2x2String(uint8_t col, uint8_t row, const char *string);
void drawGlyph(uint8_t col, uint8_t row, char glyph, const uint8_t *font, bool ignoreLH=false);
void draw2x2Glyph(uint8_t col, uint8_t row, char glyph, const uint8_t *font);
uint8_t getCols();
void clear();
void setPowerSave(uint8_t save);
void center(String &line, uint8_t width);
void draw2x2GlyphIcons();
/**
* Display the current date and time in large characters
* on the middle rows. Based 24 or 12 hour depending on
* the useAMPM configuration.
*/
void showTime();
public:
// gets called once at boot. Do all initialization that doesn't depend on
// network here
void setup();
// gets called every time WiFi is (re-)connected. Initialize own network
// interfaces here
void connected();
/**
* Da loop.
*/
void loop();
//function to update lastredraw
inline void updateRedrawTime() {lastRedraw = millis(); }
//function to to check if a redraw or overlay draw is active. Needed for UM Rotary, to avoid random/concurrent drawing
bool canDraw(void);
/**
* Redraw the screen (but only if things have changed
* or if forceRedraw).
*/
void redraw(bool forceRedraw);
void redraw_core(bool forceRedraw);
void updateBrightness();
void updateSpeed();
void updateIntensity();
void drawStatusIcons();
/**
* marks the position of the arrow showing
* the current setting being changed
* pass line and colum info
*/
void setMarkLine(byte newMarkLineNum, byte newMarkColNum);
//Draw the arrow for the current setting being changed
void drawArrow();
//Display the current effect or palette (desiredEntry)
// on the appropriate line (row).
void showCurrentEffectOrPalette(int inputEffPal, const char *qstring, uint8_t row);
/**
* If there screen is off or in clock is displayed,
* this will return true. This allows us to throw away
* the first input from the rotary encoder but
* to wake up the screen.
*/
bool wakeDisplay();
/**
* Allows you to show one line and a glyph as overlay for a period of time.
* Clears the screen and prints.
* Used in Rotary Encoder usermod.
*/
void overlay(const char* line1, long showHowLong, byte glyphType);
/**
* Allows you to show Akemi WLED logo overlay for a period of time.
* Clears the screen and prints.
*/
void overlayLogo(long showHowLong);
/**
* Allows you to show two lines as overlay for a period of time.
* Clears the screen and prints.
* Used in Auto Save usermod
*/
void overlay(const char* line1, const char* line2, long showHowLong);
void networkOverlay(const char* line1, long showHowLong);
/**
* Enable sleep (turn the display off) or clock mode.
*/
void sleepOrClock(bool sleepEnable);
/**
* handleButton() can be used to override default button behaviour. Returning true
* will prevent button working in a default way.
* Replicating button.cpp
*/
bool handleButton(uint8_t b);
void onUpdateBegin(bool init);
/*
* addToJsonInfo() can be used to add custom entries to the /json/info part of the JSON API.
* Creating an "u" object allows you to add custom key/value pairs to the Info section of the WLED web UI.
* Below it is shown how this could be used for e.g. a light sensor
*/
//void addToJsonInfo(JsonObject& root) {
//JsonObject user = root["u"];
//if (user.isNull()) user = root.createNestedObject("u");
//JsonArray data = user.createNestedArray(F("4LineDisplay"));
//data.add(F("Loaded."));
//}
/*
* addToJsonState() can be used to add custom entries to the /json/state part of the JSON API (state object).
* Values in the state object may be modified by connected clients
*/
//void addToJsonState(JsonObject& root) {
//}
/*
* readFromJsonState() can be used to receive data clients send to the /json/state part of the JSON API (state object).
* Values in the state object may be modified by connected clients
*/
//void readFromJsonState(JsonObject& root) {
// if (!initDone) return; // prevent crash on boot applyPreset()
//}
void appendConfigData();
/*
* addToConfig() can be used to add custom persistent settings to the cfg.json file in the "um" (usermod) object.
* It will be called by WLED when settings are actually saved (for example, LED settings are saved)
* If you want to force saving the current state, use serializeConfig() in your loop().
*
* CAUTION: serializeConfig() will initiate a filesystem write operation.
* It might cause the LEDs to stutter and will cause flash wear if called too often.
* Use it sparingly and always in the loop, never in network callbacks!
*
* addToConfig() will also not yet add your setting to one of the settings pages automatically.
* To make that work you still have to add the setting to the HTML, xml.cpp and set.cpp manually.
*
* I highly recommend checking out the basics of ArduinoJson serialization and deserialization in order to use custom settings!
*/
void addToConfig(JsonObject& root);
/*
* readFromConfig() can be used to read back the custom settings you added with addToConfig().
* This is called by WLED when settings are loaded (currently this only happens once immediately after boot)
*
* readFromConfig() is called BEFORE setup(). This means you can use your persistent values in setup() (e.g. pin assignments, buffer sizes),
* but also that if you want to write persistent values to a dynamic buffer, you'd need to allocate it here instead of in setup.
* If you don't know what that is, don't fret. It most likely doesn't affect your use case :)
*/
bool readFromConfig(JsonObject& root);
/*
* getId() allows you to optionally give your V2 usermod an unique ID (please define it in const.h!).
* This could be used in the future for the system to determine whether your usermod is installed.
*/
uint16_t getId() {
return USERMOD_ID_FOUR_LINE_DISP;
}
};
// strings to reduce flash memory usage (used more than twice)
const char FourLineDisplayUsermod::_name[] PROGMEM = "4LineDisplay";
const char FourLineDisplayUsermod::_enabled[] PROGMEM = "enabled";
const char FourLineDisplayUsermod::_contrast[] PROGMEM = "contrast";
const char FourLineDisplayUsermod::_refreshRate[] PROGMEM = "refreshRate-ms";
const char FourLineDisplayUsermod::_screenTimeOut[] PROGMEM = "screenTimeOutSec";
const char FourLineDisplayUsermod::_flip[] PROGMEM = "flip";
const char FourLineDisplayUsermod::_sleepMode[] PROGMEM = "sleepMode";
const char FourLineDisplayUsermod::_clockMode[] PROGMEM = "clockMode";
const char FourLineDisplayUsermod::_showSeconds[] PROGMEM = "showSeconds";
const char FourLineDisplayUsermod::_busClkFrequency[] PROGMEM = "i2c-freq-kHz";
const char FourLineDisplayUsermod::_contrastFix[] PROGMEM = "contrastFix";
#ifdef ARDUINO_ARCH_ESP32
FourLineDisplayUsermod *FourLineDisplayUsermod::instance = nullptr;
#endif
//WLEDMM
#if defined(ARDUINO_ARCH_ESP32) && defined(FLD_ESP32_USE_THREADS)
// semaphores - needed on ESP32 only, as we use a separate task to update the display
SemaphoreHandle_t drawMux = xSemaphoreCreateBinary(); // for drawstring and drawglyph functions (to prevent concurrent access to HW)
SemaphoreHandle_t drawMuxBig = xSemaphoreCreateBinary(); // for draw2x2GlyphIcons() and showCurrentEffectOrPalette() - more complex and not thread-safe
const TickType_t maxWait = 300 * portTICK_PERIOD_MS; // wait max. 300ms (drawstring semaphore)
const TickType_t maxWaitLong = 800 * portTICK_PERIOD_MS; // wait max. 800ms (big drawing semaphore)
#define FLD_SemaphoreTake(x,t) xSemaphoreTake((x),(t))
#define FLD_SemaphoreGive(x) xSemaphoreGive(x)
#else
// 8266 or no tasks - no semaphores
#define FLD_SemaphoreTake(x,t) pdTRUE
#define FLD_SemaphoreGive(x)
#if !defined(ARDUINO_ARCH_ESP32) && !defined(pdTRUE)
#define pdTRUE true
#endif
#endif
// some displays need this to properly apply contrast
void FourLineDisplayUsermod::setVcomh(bool highContrast) {
if (!typeOK || !enabled) return; // WLEDMM make sure the display is initialized before we try to draw on it if (!typeOK || !enabled) return; // WLEDMM make sure the display is initialized before we try to draw on it
if (u8x8 == nullptr) return; if (u8x8 == nullptr) return;
@@ -243,17 +450,17 @@ class FourLineDisplayUsermod : public Usermod {
/** /**
* Wrappers for screen drawing * Wrappers for screen drawing
*/ */
void setFlipMode(uint8_t mode) { void FourLineDisplayUsermod::setFlipMode(uint8_t mode) {
if (!typeOK || !enabled) return; // WLEDMM make sure the display is initialized before we try to draw on it if (!typeOK || !enabled) return; // WLEDMM make sure the display is initialized before we try to draw on it
if (u8x8 == nullptr) return; if (u8x8 == nullptr) return;
u8x8->setFlipMode(mode); u8x8->setFlipMode(mode);
} }
void setContrast(uint8_t contrast) { void FourLineDisplayUsermod::setContrast(uint8_t contrast) {
if (!typeOK || !enabled) return; // WLEDMM make sure the display is initialized before we try to draw on it if (!typeOK || !enabled) return; // WLEDMM make sure the display is initialized before we try to draw on it
if (u8x8 == nullptr) return; if (u8x8 == nullptr) return;
u8x8->setContrast(contrast); u8x8->setContrast(contrast);
} }
void drawString(uint8_t col, uint8_t row, const char *string, bool ignoreLH=false) { void FourLineDisplayUsermod::drawString(uint8_t col, uint8_t row, const char *string, bool ignoreLH) {
if (!typeOK || !enabled) return; // WLEDMM make sure the display is initialized before we try to draw on it if (!typeOK || !enabled) return; // WLEDMM make sure the display is initialized before we try to draw on it
if (u8x8 == nullptr) return; if (u8x8 == nullptr) return;
if (FLD_SemaphoreTake(drawMux, maxWait) != pdTRUE) return; // WLEDMM acquire draw mutex if (FLD_SemaphoreTake(drawMux, maxWait) != pdTRUE) return; // WLEDMM acquire draw mutex
@@ -277,7 +484,7 @@ class FourLineDisplayUsermod : public Usermod {
#endif #endif
FLD_SemaphoreGive(drawMux); // WLEDMM release draw mutex FLD_SemaphoreGive(drawMux); // WLEDMM release draw mutex
} }
void draw2x2String(uint8_t col, uint8_t row, const char *string) { void FourLineDisplayUsermod::draw2x2String(uint8_t col, uint8_t row, const char *string) {
if (!typeOK || !enabled) return; if (!typeOK || !enabled) return;
if (u8x8 == nullptr) return; if (u8x8 == nullptr) return;
if (FLD_SemaphoreTake(drawMux, maxWait) != pdTRUE) return; // WLEDMM acquire draw mutex if (FLD_SemaphoreTake(drawMux, maxWait) != pdTRUE) return; // WLEDMM acquire draw mutex
@@ -302,7 +509,7 @@ class FourLineDisplayUsermod : public Usermod {
#endif #endif
FLD_SemaphoreGive(drawMux); // WLEDMM release draw mutex FLD_SemaphoreGive(drawMux); // WLEDMM release draw mutex
} }
void drawGlyph(uint8_t col, uint8_t row, char glyph, const uint8_t *font, bool ignoreLH=false) { void FourLineDisplayUsermod::drawGlyph(uint8_t col, uint8_t row, char glyph, const uint8_t *font, bool ignoreLH) {
if (!typeOK || !enabled) return; if (!typeOK || !enabled) return;
if (FLD_SemaphoreTake(drawMux, maxWait) != pdTRUE) return; // WLEDMM acquire draw mutex if (FLD_SemaphoreTake(drawMux, maxWait) != pdTRUE) return; // WLEDMM acquire draw mutex
u8x8->setFont(font); u8x8->setFont(font);
@@ -310,37 +517,37 @@ class FourLineDisplayUsermod : public Usermod {
else u8x8->drawGlyph(col, row, glyph); else u8x8->drawGlyph(col, row, glyph);
FLD_SemaphoreGive(drawMux); // WLEDMM release draw mutex FLD_SemaphoreGive(drawMux); // WLEDMM release draw mutex
} }
void draw2x2Glyph(uint8_t col, uint8_t row, char glyph, const uint8_t *font) { void FourLineDisplayUsermod::draw2x2Glyph(uint8_t col, uint8_t row, char glyph, const uint8_t *font) {
if (!typeOK || !enabled) return; if (!typeOK || !enabled) return;
if (FLD_SemaphoreTake(drawMux, maxWait) != pdTRUE) return; // WLEDMM acquire draw mutex if (FLD_SemaphoreTake(drawMux, maxWait) != pdTRUE) return; // WLEDMM acquire draw mutex
u8x8->setFont(font); u8x8->setFont(font);
u8x8->draw2x2Glyph(col, row, glyph); u8x8->draw2x2Glyph(col, row, glyph);
FLD_SemaphoreGive(drawMux); // WLEDMM release draw mutex FLD_SemaphoreGive(drawMux); // WLEDMM release draw mutex
} }
uint8_t getCols() { uint8_t FourLineDisplayUsermod::getCols() {
if (!typeOK || !enabled) return 0; if (!typeOK || !enabled) return 0;
return u8x8->getCols(); return u8x8->getCols();
} }
void clear() { void FourLineDisplayUsermod::clear() {
if (!typeOK || !enabled) return; if (!typeOK || !enabled) return;
if (nullptr == u8x8) return; // prevents some crashes if (nullptr == u8x8) return; // prevents some crashes
if (FLD_SemaphoreTake(drawMux, maxWaitLong ) != pdTRUE) return; // WLEDMM acquire draw mutex - clear() can take very long in software I2C mode if (FLD_SemaphoreTake(drawMux, maxWaitLong ) != pdTRUE) return; // WLEDMM acquire draw mutex - clear() can take very long in software I2C mode
u8x8->clear(); // crashes randomly on ESP32 u8x8->clear(); // crashes randomly on ESP32
FLD_SemaphoreGive(drawMux); // WLEDMM release draw mutex FLD_SemaphoreGive(drawMux); // WLEDMM release draw mutex
} }
void setPowerSave(uint8_t save) { void FourLineDisplayUsermod::setPowerSave(uint8_t save) {
if (!typeOK || !enabled) return; // WLEDMM make sure the display is initialized before we try to draw on it if (!typeOK || !enabled) return; // WLEDMM make sure the display is initialized before we try to draw on it
if (u8x8 == nullptr) return; if (u8x8 == nullptr) return;
u8x8->setPowerSave(save); u8x8->setPowerSave(save);
} }
void center(String &line, uint8_t width) { void FourLineDisplayUsermod::center(String &line, uint8_t width) {
int len = line.length(); int len = line.length();
if (len<width) for (byte i=(width-len)/2; i>0; i--) line = ' ' + line; if (len<width) for (byte i=(width-len)/2; i>0; i--) line = ' ' + line;
for (byte i=line.length(); i<width; i++) line += ' '; for (byte i=line.length(); i<width; i++) line += ' ';
} }
void draw2x2GlyphIcons() { void FourLineDisplayUsermod::draw2x2GlyphIcons() {
if (!typeOK || !enabled) return; // WLEDMM make sure the display is initialized before we try to draw on it if (!typeOK || !enabled) return; // WLEDMM make sure the display is initialized before we try to draw on it
if (FLD_SemaphoreTake(drawMuxBig, maxWaitLong) != pdTRUE) return; // WLEDMM acquire BIG draw mutex if (FLD_SemaphoreTake(drawMuxBig, maxWaitLong) != pdTRUE) return; // WLEDMM acquire BIG draw mutex
if (lineHeight > 1) { if (lineHeight > 1) {
@@ -364,7 +571,7 @@ class FourLineDisplayUsermod : public Usermod {
* on the middle rows. Based 24 or 12 hour depending on * on the middle rows. Based 24 or 12 hour depending on
* the useAMPM configuration. * the useAMPM configuration.
*/ */
void showTime() { void FourLineDisplayUsermod::showTime() {
if (!typeOK || !enabled || !displayTurnedOff) return; if (!typeOK || !enabled || !displayTurnedOff) return;
unsigned long now = millis(); unsigned long now = millis();
@@ -426,11 +633,11 @@ class FourLineDisplayUsermod : public Usermod {
drawing = false; drawing = false;
} }
public: // public:
// gets called once at boot. Do all initialization that doesn't depend on // gets called once at boot. Do all initialization that doesn't depend on
// network here // network here
void setup() { void FourLineDisplayUsermod::setup() {
if (!enabled) return; // typeOK = true will be set after successful setup if (!enabled) return; // typeOK = true will be set after successful setup
bool isHW = false; bool isHW = false;
@@ -623,7 +830,7 @@ class FourLineDisplayUsermod : public Usermod {
// gets called every time WiFi is (re-)connected. Initialize own network // gets called every time WiFi is (re-)connected. Initialize own network
// interfaces here // interfaces here
void connected() { void FourLineDisplayUsermod::connected() {
knownSsid = WiFi.SSID(); //apActive ? apSSID : WiFi.SSID(); //apActive ? WiFi.softAPSSID() : knownSsid = WiFi.SSID(); //apActive ? apSSID : WiFi.SSID(); //apActive ? WiFi.softAPSSID() :
knownIp = Network.localIP(); //apActive ? IPAddress(4, 3, 2, 1) : Network.localIP(); knownIp = Network.localIP(); //apActive ? IPAddress(4, 3, 2, 1) : Network.localIP();
networkOverlay(PSTR("NETWORK INFO"),7000); networkOverlay(PSTR("NETWORK INFO"),7000);
@@ -632,7 +839,7 @@ class FourLineDisplayUsermod : public Usermod {
/** /**
* Da loop. * Da loop.
*/ */
void loop() { void FourLineDisplayUsermod::loop() {
#if !defined(ARDUINO_ARCH_ESP32) || !defined(FLD_ESP32_USE_THREADS) #if !defined(ARDUINO_ARCH_ESP32) || !defined(FLD_ESP32_USE_THREADS)
static unsigned long lastRunTime = 0; static unsigned long lastRunTime = 0;
unsigned long now = millis(); unsigned long now = millis();
@@ -647,13 +854,8 @@ class FourLineDisplayUsermod : public Usermod {
#endif #endif
} }
//function to update lastredraw
void updateRedrawTime() {
lastRedraw = millis();
}
//function to to check if a redraw or overlay draw is active. Needed for UM Rotary, to avoid random/concurrent drawing //function to to check if a redraw or overlay draw is active. Needed for UM Rotary, to avoid random/concurrent drawing
bool canDraw(void) { bool FourLineDisplayUsermod::canDraw(void) {
if (!typeOK || !enabled || !initDone) return(false); // WLEDMM make sure the display is initialized before we try to draw on it if (!typeOK || !enabled || !initDone) return(false); // WLEDMM make sure the display is initialized before we try to draw on it
#if defined(ARDUINO_ARCH_ESP32) && defined(FLD_ESP32_USE_THREADS) // only necessary on ESP32 #if defined(ARDUINO_ARCH_ESP32) && defined(FLD_ESP32_USE_THREADS) // only necessary on ESP32
if (drawing) return(false); // overlay draws someting if (drawing) return(false); // overlay draws someting
@@ -666,7 +868,7 @@ class FourLineDisplayUsermod : public Usermod {
* Redraw the screen (but only if things have changed * Redraw the screen (but only if things have changed
* or if forceRedraw). * or if forceRedraw).
*/ */
void redraw(bool forceRedraw) { void FourLineDisplayUsermod::redraw(bool forceRedraw) {
#if defined(ARDUINO_ARCH_ESP32) && defined(FLD_ESP32_USE_THREADS) #if defined(ARDUINO_ARCH_ESP32) && defined(FLD_ESP32_USE_THREADS)
// use a wrapper onESP32, to ensure the functions is not running several times in parallel ! // use a wrapper onESP32, to ensure the functions is not running several times in parallel !
static bool doForceRedraw = false; // for delaying "force redraw" static bool doForceRedraw = false; // for delaying "force redraw"
@@ -686,7 +888,7 @@ class FourLineDisplayUsermod : public Usermod {
reDrawing = false; // reset activity flag, as redraw has too many early returns that don't take care of this reDrawing = false; // reset activity flag, as redraw has too many early returns that don't take care of this
} }
void redraw_core(bool forceRedraw) { void FourLineDisplayUsermod::redraw_core(bool forceRedraw) {
#endif #endif
bool needRedraw = false; bool needRedraw = false;
unsigned long now = millis(); unsigned long now = millis();
@@ -802,7 +1004,7 @@ class FourLineDisplayUsermod : public Usermod {
showCurrentEffectOrPalette(knownMode, JSON_mode_names, 3); //Effect Mode info showCurrentEffectOrPalette(knownMode, JSON_mode_names, 3); //Effect Mode info
} }
void updateBrightness() { void FourLineDisplayUsermod::updateBrightness() {
knownBrightness = bri; knownBrightness = bri;
if (overlayUntil == 0) { if (overlayUntil == 0) {
brightness100 = ((uint16_t)bri*100)/255; brightness100 = ((uint16_t)bri*100)/255;
@@ -813,7 +1015,7 @@ class FourLineDisplayUsermod : public Usermod {
} }
} }
void updateSpeed() { void FourLineDisplayUsermod::updateSpeed() {
knownEffectSpeed = effectSpeed; knownEffectSpeed = effectSpeed;
if (overlayUntil == 0) { if (overlayUntil == 0) {
fxspeed100 = ((uint16_t)effectSpeed*100)/255; fxspeed100 = ((uint16_t)effectSpeed*100)/255;
@@ -824,7 +1026,7 @@ class FourLineDisplayUsermod : public Usermod {
} }
} }
void updateIntensity() { void FourLineDisplayUsermod::updateIntensity() {
knownEffectIntensity = effectIntensity; knownEffectIntensity = effectIntensity;
if (overlayUntil == 0) { if (overlayUntil == 0) {
fxintensity100 = ((uint16_t)effectIntensity*100)/255; fxintensity100 = ((uint16_t)effectIntensity*100)/255;
@@ -835,7 +1037,7 @@ class FourLineDisplayUsermod : public Usermod {
} }
} }
void drawStatusIcons() { void FourLineDisplayUsermod::drawStatusIcons() {
uint8_t col = 15; uint8_t col = 15;
uint8_t row = 0; uint8_t row = 0;
drawGlyph(col, row, (wificonnected ? 20 : 0), u8x8_4LineDisplay_WLED_icons_1x1, true); // wifi icon drawGlyph(col, row, (wificonnected ? 20 : 0), u8x8_4LineDisplay_WLED_icons_1x1, true); // wifi icon
@@ -850,19 +1052,19 @@ class FourLineDisplayUsermod : public Usermod {
* the current setting being changed * the current setting being changed
* pass line and colum info * pass line and colum info
*/ */
void setMarkLine(byte newMarkLineNum, byte newMarkColNum) { void FourLineDisplayUsermod::setMarkLine(byte newMarkLineNum, byte newMarkColNum) {
markLineNum = newMarkLineNum; markLineNum = newMarkLineNum;
markColNum = newMarkColNum; markColNum = newMarkColNum;
} }
//Draw the arrow for the current setting being changed //Draw the arrow for the current setting being changed
void drawArrow() { void FourLineDisplayUsermod::drawArrow() {
if (markColNum != 255 && markLineNum !=255) drawGlyph(markColNum, markLineNum*lineHeight, 21, u8x8_4LineDisplay_WLED_icons_1x1); if (markColNum != 255 && markLineNum !=255) drawGlyph(markColNum, markLineNum*lineHeight, 21, u8x8_4LineDisplay_WLED_icons_1x1);
} }
//Display the current effect or palette (desiredEntry) //Display the current effect or palette (desiredEntry)
// on the appropriate line (row). // on the appropriate line (row).
void showCurrentEffectOrPalette(int inputEffPal, const char *qstring, uint8_t row) { void FourLineDisplayUsermod::showCurrentEffectOrPalette(int inputEffPal, const char *qstring, uint8_t row) {
char lineBuffer[MAX_JSON_CHARS] = { '\0' }; char lineBuffer[MAX_JSON_CHARS] = { '\0' };
if (!typeOK || !enabled) return; // WLEDMM make sure the display is initialized before we try to draw on it if (!typeOK || !enabled) return; // WLEDMM make sure the display is initialized before we try to draw on it
if (FLD_SemaphoreTake(drawMuxBig, maxWaitLong) != pdTRUE) return; // WLEDMM acquire BIG draw mutex if (FLD_SemaphoreTake(drawMuxBig, maxWaitLong) != pdTRUE) return; // WLEDMM acquire BIG draw mutex
@@ -934,7 +1136,7 @@ class FourLineDisplayUsermod : public Usermod {
* the first input from the rotary encoder but * the first input from the rotary encoder but
* to wake up the screen. * to wake up the screen.
*/ */
bool wakeDisplay() { bool FourLineDisplayUsermod::wakeDisplay() {
if (!typeOK || !enabled) return false; if (!typeOK || !enabled) return false;
if (!initDone) return false; if (!initDone) return false;
if (displayTurnedOff) { if (displayTurnedOff) {
@@ -956,7 +1158,7 @@ class FourLineDisplayUsermod : public Usermod {
* Clears the screen and prints. * Clears the screen and prints.
* Used in Rotary Encoder usermod. * Used in Rotary Encoder usermod.
*/ */
void overlay(const char* line1, long showHowLong, byte glyphType) { void FourLineDisplayUsermod::overlay(const char* line1, long showHowLong, byte glyphType) {
if (!typeOK || !enabled) return; // WLEDMM make sure the display is initialized before we try to draw on it if (!typeOK || !enabled) return; // WLEDMM make sure the display is initialized before we try to draw on it
if (!initDone) return; // WLEDMM bugfix if (!initDone) return; // WLEDMM bugfix
unsigned long now = millis(); unsigned long now = millis();
@@ -983,7 +1185,7 @@ class FourLineDisplayUsermod : public Usermod {
* Allows you to show Akemi WLED logo overlay for a period of time. * Allows you to show Akemi WLED logo overlay for a period of time.
* Clears the screen and prints. * Clears the screen and prints.
*/ */
void overlayLogo(long showHowLong) { void FourLineDisplayUsermod::overlayLogo(long showHowLong) {
if (!typeOK || !enabled) return; // WLEDMM make sure the display is initialized before we try to draw on it if (!typeOK || !enabled) return; // WLEDMM make sure the display is initialized before we try to draw on it
unsigned long now = millis(); unsigned long now = millis();
while (drawing && millis()-now < 250) delay(1); // wait if someone else is drawing while (drawing && millis()-now < 250) delay(1); // wait if someone else is drawing
@@ -1045,7 +1247,7 @@ class FourLineDisplayUsermod : public Usermod {
* Clears the screen and prints. * Clears the screen and prints.
* Used in Auto Save usermod * Used in Auto Save usermod
*/ */
void overlay(const char* line1, const char* line2, long showHowLong) { void FourLineDisplayUsermod::overlay(const char* line1, const char* line2, long showHowLong) {
if (!typeOK || !enabled) return; // WLEDMM make sure the display is initialized before we try to draw on it if (!typeOK || !enabled) return; // WLEDMM make sure the display is initialized before we try to draw on it
if (!initDone) return; // WLEDMM bugfix if (!initDone) return; // WLEDMM bugfix
unsigned long now = millis(); unsigned long now = millis();
@@ -1069,7 +1271,7 @@ class FourLineDisplayUsermod : public Usermod {
drawing = false; drawing = false;
} }
void networkOverlay(const char* line1, long showHowLong) { void FourLineDisplayUsermod::networkOverlay(const char* line1, long showHowLong) {
if (!typeOK || !enabled) return; // WLEDMM make sure the display is initialized before we try to draw on it if (!typeOK || !enabled) return; // WLEDMM make sure the display is initialized before we try to draw on it
if (!initDone) return; // WLEDMM bugfix if (!initDone) return; // WLEDMM bugfix
unsigned long now = millis(); unsigned long now = millis();
@@ -1113,7 +1315,7 @@ class FourLineDisplayUsermod : public Usermod {
/** /**
* Enable sleep (turn the display off) or clock mode. * Enable sleep (turn the display off) or clock mode.
*/ */
void sleepOrClock(bool sleepEnable) { void FourLineDisplayUsermod::sleepOrClock(bool sleepEnable) {
if (sleepEnable) { if (sleepEnable) {
displayTurnedOff = true; displayTurnedOff = true;
//setContrast(contrastFix? 2+ contrast/4 : 0); // un-comment to dim display in "clock mode" //setContrast(contrastFix? 2+ contrast/4 : 0); // un-comment to dim display in "clock mode"
@@ -1134,7 +1336,7 @@ class FourLineDisplayUsermod : public Usermod {
* will prevent button working in a default way. * will prevent button working in a default way.
* Replicating button.cpp * Replicating button.cpp
*/ */
bool handleButton(uint8_t b) { bool FourLineDisplayUsermod::handleButton(uint8_t b) {
yield(); yield();
if (!enabled if (!enabled
|| b // butto 0 only || b // butto 0 only
@@ -1210,7 +1412,7 @@ class FourLineDisplayUsermod : public Usermod {
#define ARDUINO_RUNNING_CORE 1 #define ARDUINO_RUNNING_CORE 1
#endif #endif
#endif #endif
void onUpdateBegin(bool init) { void FourLineDisplayUsermod::onUpdateBegin(bool init) {
#if defined(ARDUINO_ARCH_ESP32) && defined(FLD_ESP32_USE_THREADS) #if defined(ARDUINO_ARCH_ESP32) && defined(FLD_ESP32_USE_THREADS)
if (init && Display_Task) { if (init && Display_Task) {
vTaskSuspend(Display_Task); // update is about to begin, disable task to prevent crash vTaskSuspend(Display_Task); // update is about to begin, disable task to prevent crash
@@ -1271,7 +1473,7 @@ class FourLineDisplayUsermod : public Usermod {
// if (!initDone) return; // prevent crash on boot applyPreset() // if (!initDone) return; // prevent crash on boot applyPreset()
//} //}
void appendConfigData() { void FourLineDisplayUsermod::appendConfigData() {
oappend(SET_F("addHB('4LineDisplay');")); oappend(SET_F("addHB('4LineDisplay');"));
oappend(SET_F("dd=addDropdown('4LineDisplay','type');")); oappend(SET_F("dd=addDropdown('4LineDisplay','type');"));
@@ -1346,7 +1548,7 @@ class FourLineDisplayUsermod : public Usermod {
* *
* I highly recommend checking out the basics of ArduinoJson serialization and deserialization in order to use custom settings! * I highly recommend checking out the basics of ArduinoJson serialization and deserialization in order to use custom settings!
*/ */
void addToConfig(JsonObject& root) { void FourLineDisplayUsermod::addToConfig(JsonObject& root) {
// determine if we are using global HW pins (data & clock) // determine if we are using global HW pins (data & clock)
int8_t hw_dta, hw_clk; int8_t hw_dta, hw_clk;
if (displayIsSPI(type)) { if (displayIsSPI(type)) {
@@ -1389,7 +1591,7 @@ class FourLineDisplayUsermod : public Usermod {
* but also that if you want to write persistent values to a dynamic buffer, you'd need to allocate it here instead of in setup. * but also that if you want to write persistent values to a dynamic buffer, you'd need to allocate it here instead of in setup.
* If you don't know what that is, don't fret. It most likely doesn't affect your use case :) * If you don't know what that is, don't fret. It most likely doesn't affect your use case :)
*/ */
bool readFromConfig(JsonObject& root) { bool FourLineDisplayUsermod::readFromConfig(JsonObject& root) {
bool needsRedraw = false; bool needsRedraw = false;
DisplayType newType = type; DisplayType newType = type;
int8_t oldPin[5]; for (byte i=0; i<5; i++) oldPin[i] = ioPin[i]; int8_t oldPin[5]; for (byte i=0; i<5; i++) oldPin[i] = ioPin[i];
@@ -1477,33 +1679,6 @@ class FourLineDisplayUsermod : public Usermod {
return !top[FPSTR(_contrastFix)].isNull(); return !top[FPSTR(_contrastFix)].isNull();
} }
/*
* getId() allows you to optionally give your V2 usermod an unique ID (please define it in const.h!).
* This could be used in the future for the system to determine whether your usermod is installed.
*/
uint16_t getId() {
return USERMOD_ID_FOUR_LINE_DISP;
}
};
// strings to reduce flash memory usage (used more than twice)
const char FourLineDisplayUsermod::_name[] PROGMEM = "4LineDisplay";
const char FourLineDisplayUsermod::_enabled[] PROGMEM = "enabled";
const char FourLineDisplayUsermod::_contrast[] PROGMEM = "contrast";
const char FourLineDisplayUsermod::_refreshRate[] PROGMEM = "refreshRate-ms";
const char FourLineDisplayUsermod::_screenTimeOut[] PROGMEM = "screenTimeOutSec";
const char FourLineDisplayUsermod::_flip[] PROGMEM = "flip";
const char FourLineDisplayUsermod::_sleepMode[] PROGMEM = "sleepMode";
const char FourLineDisplayUsermod::_clockMode[] PROGMEM = "clockMode";
const char FourLineDisplayUsermod::_showSeconds[] PROGMEM = "showSeconds";
const char FourLineDisplayUsermod::_busClkFrequency[] PROGMEM = "i2c-freq-kHz";
const char FourLineDisplayUsermod::_contrastFix[] PROGMEM = "contrastFix";
#ifdef ARDUINO_ARCH_ESP32
FourLineDisplayUsermod *FourLineDisplayUsermod::instance = nullptr;
#endif
// WLEDMM clean up some macros, so they don't cause problems in other usermods // WLEDMM clean up some macros, so they don't cause problems in other usermods
#undef FLD_SemaphoreTake #undef FLD_SemaphoreTake
#undef FLD_SemaphoreGive #undef FLD_SemaphoreGive

View File

@@ -184,7 +184,162 @@ private:
* Sort the modes and palettes to the index arrays * Sort the modes and palettes to the index arrays
* modes_alpha_indexes and palettes_alpha_indexes. * modes_alpha_indexes and palettes_alpha_indexes.
*/ */
void sortModesAndPalettes() { void sortModesAndPalettes();
byte *re_initIndexArray(int numModes);
/**
* Return an array of mode or palette names from the JSON string.
* They don't end in '\0', they end in '"'.
*/
const char **re_findModeStrings(const char json[], int numModes);
/**
* Sort either the modes or the palettes using quicksort.
*/
void re_sortModes(const char **modeNames, byte *indexes, int count, int numSkip);
public:
/*
* setup() is called once at boot. WiFi is not yet connected at this point.
* You can use it to initialize variables, sensors or similar.
*/
void setup();
/*
* connected() is called every time the WiFi is (re)connected
* Use it to initialize network interfaces
*/
void connected();
/*
* loop() is called continuously. Here you can check for events, read sensors, etc.
*
* Tips:
* 1. You can use "if (WLED_CONNECTED)" to check for a successful network connection.
* Additionally, "if (WLED_MQTT_CONNECTED)" is available to check for a connection to an MQTT broker.
*
* 2. Try to avoid using the delay() function. NEVER use delays longer than 10 milliseconds.
* Instead, use a timer check as shown here.
*/
void loop();
void displayNetworkInfo();
void findCurrentEffectAndPalette();
boolean changeState(const char *stateName, byte markedLine, byte markedCol, byte glyph);
void lampUdated();
void changeBrightness(bool increase);
void changeEffect(bool increase);
void changeEffectSpeed(bool increase);
void changeEffectIntensity(bool increase);
void changeCustom(uint8_t par, bool increase);
void changePalette(bool increase);
void changeHue(bool increase);
void changeSat(bool increase);
void changePreset(bool increase) ;
void changeCCT(bool increase);
/*
* addToJsonInfo() can be used to add custom entries to the /json/info part of the JSON API.
* Creating an "u" object allows you to add custom key/value pairs to the Info section of the WLED web UI.
* Below it is shown how this could be used for e.g. a light sensor
*/
/*
void addToJsonInfo(JsonObject& root)
{
int reading = 20;
//this code adds "u":{"Light":[20," lux"]} to the info object
JsonObject user = root["u"];
if (user.isNull()) user = root.createNestedObject("u");
JsonArray lightArr = user.createNestedArray("Light"); //name
lightArr.add(reading); //value
lightArr.add(" lux"); //unit
}
*/
/*
* addToJsonState() can be used to add custom entries to the /json/state part of the JSON API (state object).
* Values in the state object may be modified by connected clients
*/
/*
void addToJsonState(JsonObject &root)
{
//root["user0"] = userVar0;
}
*/
/*
* readFromJsonState() can be used to receive data clients send to the /json/state part of the JSON API (state object).
* Values in the state object may be modified by connected clients
*/
/*
void readFromJsonState(JsonObject &root)
{
//userVar0 = root["user0"] | userVar0; //if "user0" key exists in JSON, update, else keep old value
//if (root["bri"] == 255) Serial.println(F("Don't burn down your garage!"));
}
*/
/**
* addToConfig() (called from set.cpp) stores persistent properties to cfg.json
*/
void addToConfig(JsonObject &root);
//WLEDMM: add appendConfigData
void appendConfigData();
/**
* readFromConfig() is called before setup() to populate properties from values stored in cfg.json
*
* The function should return true if configuration was successfully loaded or false if there was no configuration.
*/
bool readFromConfig(JsonObject &root);
/*
* getId() allows you to optionally give your V2 usermod an unique ID (please define it in const.h!).
* This could be used in the future for the system to determine whether your usermod is installed.
*/
uint16_t getId()
{
return USERMOD_ID_ROTARY_ENC_UI;
}
};
// strings to reduce flash memory usage (used more than twice)
const char RotaryEncoderUIUsermod::_name[] PROGMEM = "Rotary-Encoder";
const char RotaryEncoderUIUsermod::_enabled[] PROGMEM = "enabled";
const char RotaryEncoderUIUsermod::_DT_pin[] PROGMEM = "DT-pin";
const char RotaryEncoderUIUsermod::_CLK_pin[] PROGMEM = "CLK-pin";
const char RotaryEncoderUIUsermod::_SW_pin[] PROGMEM = "SW-pin";
const char RotaryEncoderUIUsermod::_presetHigh[] PROGMEM = "preset-high";
const char RotaryEncoderUIUsermod::_presetLow[] PROGMEM = "preset-low";
const char RotaryEncoderUIUsermod::_applyToAll[] PROGMEM = "apply-2-all-seg";
/**
* Sort the modes and palettes to the index arrays
* modes_alpha_indexes and palettes_alpha_indexes.
*/
void RotaryEncoderUIUsermod::sortModesAndPalettes() {
//modes_qstrings = re_findModeStrings(JSON_mode_names, strip.getModeCount()); //modes_qstrings = re_findModeStrings(JSON_mode_names, strip.getModeCount());
modes_qstrings = strip.getModeDataSrc(); modes_qstrings = strip.getModeDataSrc();
modes_alpha_indexes = re_initIndexArray(strip.getModeCount()); modes_alpha_indexes = re_initIndexArray(strip.getModeCount());
@@ -200,7 +355,7 @@ private:
re_sortModes(palettes_qstrings, palettes_alpha_indexes, strip.getPaletteCount(), skipPaletteCount); re_sortModes(palettes_qstrings, palettes_alpha_indexes, strip.getPaletteCount(), skipPaletteCount);
} }
byte *re_initIndexArray(int numModes) { byte *RotaryEncoderUIUsermod::re_initIndexArray(int numModes) {
byte *indexes = (byte *)malloc(sizeof(byte) * numModes); byte *indexes = (byte *)malloc(sizeof(byte) * numModes);
for (byte i = 0; i < numModes; i++) { for (byte i = 0; i < numModes; i++) {
indexes[i] = i; indexes[i] = i;
@@ -212,7 +367,7 @@ private:
* Return an array of mode or palette names from the JSON string. * Return an array of mode or palette names from the JSON string.
* They don't end in '\0', they end in '"'. * They don't end in '\0', they end in '"'.
*/ */
const char **re_findModeStrings(const char json[], int numModes) { const char **RotaryEncoderUIUsermod::re_findModeStrings(const char json[], int numModes) {
const char **modeStrings = (const char **)malloc(sizeof(const char *) * numModes); const char **modeStrings = (const char **)malloc(sizeof(const char *) * numModes);
uint8_t modeIndex = 0; uint8_t modeIndex = 0;
bool insideQuotes = false; bool insideQuotes = false;
@@ -250,7 +405,7 @@ private:
/** /**
* Sort either the modes or the palettes using quicksort. * Sort either the modes or the palettes using quicksort.
*/ */
void re_sortModes(const char **modeNames, byte *indexes, int count, int numSkip) { void RotaryEncoderUIUsermod::re_sortModes(const char **modeNames, byte *indexes, int count, int numSkip) {
if (!modeNames) return; if (!modeNames) return;
listBeingSorted = modeNames; listBeingSorted = modeNames;
qsort(indexes + numSkip, count - numSkip, sizeof(byte), re_qstringCmp); qsort(indexes + numSkip, count - numSkip, sizeof(byte), re_qstringCmp);
@@ -258,12 +413,12 @@ private:
} }
public: // public:
/* /*
* setup() is called once at boot. WiFi is not yet connected at this point. * setup() is called once at boot. WiFi is not yet connected at this point.
* You can use it to initialize variables, sensors or similar. * You can use it to initialize variables, sensors or similar.
*/ */
void setup() void RotaryEncoderUIUsermod::setup()
{ {
DEBUG_PRINTLN(F("Usermod Rotary Encoder init.")); DEBUG_PRINTLN(F("Usermod Rotary Encoder init."));
PinManagerPinType pins[3] = { { pinA, false }, { pinB, false }, { pinC, false } }; PinManagerPinType pins[3] = { { pinA, false }, { pinB, false }, { pinC, false } };
@@ -318,7 +473,7 @@ public:
* connected() is called every time the WiFi is (re)connected * connected() is called every time the WiFi is (re)connected
* Use it to initialize network interfaces * Use it to initialize network interfaces
*/ */
void connected() void RotaryEncoderUIUsermod::connected()
{ {
//Serial.println("Connected to WiFi!"); //Serial.println("Connected to WiFi!");
} }
@@ -333,7 +488,7 @@ public:
* 2. Try to avoid using the delay() function. NEVER use delays longer than 10 milliseconds. * 2. Try to avoid using the delay() function. NEVER use delays longer than 10 milliseconds.
* Instead, use a timer check as shown here. * Instead, use a timer check as shown here.
*/ */
void loop() void RotaryEncoderUIUsermod::loop()
{ {
if (!enabled) return; if (!enabled) return;
unsigned long currentTime = millis(); // get the current elapsed time unsigned long currentTime = millis(); // get the current elapsed time
@@ -469,14 +624,14 @@ public:
} }
} }
void displayNetworkInfo() { void RotaryEncoderUIUsermod::displayNetworkInfo() {
#ifdef USERMOD_FOUR_LINE_DISPLAY #ifdef USERMOD_FOUR_LINE_DISPLAY
if (display != nullptr) if (display != nullptr)
display->networkOverlay(PSTR("NETWORK INFO"), 10000); display->networkOverlay(PSTR("NETWORK INFO"), 10000);
#endif #endif
} }
void findCurrentEffectAndPalette() { void RotaryEncoderUIUsermod::findCurrentEffectAndPalette() {
if (modes_alpha_indexes == nullptr) return; // WLEDMM bugfix if (modes_alpha_indexes == nullptr) return; // WLEDMM bugfix
currentEffectAndPaletteInitialized = true; currentEffectAndPaletteInitialized = true;
for (uint8_t i = 0; i < strip.getModeCount(); i++) { for (uint8_t i = 0; i < strip.getModeCount(); i++) {
@@ -494,7 +649,7 @@ public:
} }
} }
boolean changeState(const char *stateName, byte markedLine, byte markedCol, byte glyph) { boolean RotaryEncoderUIUsermod::changeState(const char *stateName, byte markedLine, byte markedCol, byte glyph) {
#ifdef USERMOD_FOUR_LINE_DISPLAY #ifdef USERMOD_FOUR_LINE_DISPLAY
if (display != nullptr) { if (display != nullptr) {
if (display->wakeDisplay()) { if (display->wakeDisplay()) {
@@ -509,7 +664,7 @@ public:
return true; return true;
} }
void lampUdated() { void RotaryEncoderUIUsermod::lampUdated() {
//call for notifier -> 0: init 1: direct change 2: button 3: notification 4: nightlight 5: other (No notification) //call for notifier -> 0: init 1: direct change 2: button 3: notification 4: nightlight 5: other (No notification)
// 6: fx changed 7: hue 8: preset cycle 9: blynk 10: alexa // 6: fx changed 7: hue 8: preset cycle 9: blynk 10: alexa
//setValuesFromFirstSelectedSeg(); //to make transition work on main segment (should no longer be required) //setValuesFromFirstSelectedSeg(); //to make transition work on main segment (should no longer be required)
@@ -518,7 +673,7 @@ public:
updateInterfaces(CALL_MODE_BUTTON); updateInterfaces(CALL_MODE_BUTTON);
} }
void changeBrightness(bool increase) { void RotaryEncoderUIUsermod::changeBrightness(bool increase) {
#ifdef USERMOD_FOUR_LINE_DISPLAY #ifdef USERMOD_FOUR_LINE_DISPLAY
if (display && display->wakeDisplay()) { if (display && display->wakeDisplay()) {
display->redraw(true); display->redraw(true);
@@ -539,7 +694,7 @@ public:
} }
void changeEffect(bool increase) { void RotaryEncoderUIUsermod::changeEffect(bool increase) {
#ifdef USERMOD_FOUR_LINE_DISPLAY #ifdef USERMOD_FOUR_LINE_DISPLAY
if (display && display->wakeDisplay()) { if (display && display->wakeDisplay()) {
display->redraw(true); display->redraw(true);
@@ -569,7 +724,7 @@ public:
} }
void changeEffectSpeed(bool increase) { void RotaryEncoderUIUsermod::changeEffectSpeed(bool increase) {
#ifdef USERMOD_FOUR_LINE_DISPLAY #ifdef USERMOD_FOUR_LINE_DISPLAY
if (display && display->wakeDisplay()) { if (display && display->wakeDisplay()) {
display->redraw(true); display->redraw(true);
@@ -598,7 +753,7 @@ public:
} }
void changeEffectIntensity(bool increase) { void RotaryEncoderUIUsermod::changeEffectIntensity(bool increase) {
#ifdef USERMOD_FOUR_LINE_DISPLAY #ifdef USERMOD_FOUR_LINE_DISPLAY
if (display && display->wakeDisplay()) { if (display && display->wakeDisplay()) {
display->redraw(true); display->redraw(true);
@@ -627,7 +782,7 @@ public:
} }
void changeCustom(uint8_t par, bool increase) { void RotaryEncoderUIUsermod::changeCustom(uint8_t par, bool increase) {
#ifdef USERMOD_FOUR_LINE_DISPLAY #ifdef USERMOD_FOUR_LINE_DISPLAY
uint8_t val = 0; uint8_t val = 0;
if (display && display->wakeDisplay()) { if (display && display->wakeDisplay()) {
@@ -676,7 +831,7 @@ public:
} }
void changePalette(bool increase) { void RotaryEncoderUIUsermod::changePalette(bool increase) {
#ifdef USERMOD_FOUR_LINE_DISPLAY #ifdef USERMOD_FOUR_LINE_DISPLAY
if (display && display->wakeDisplay()) { if (display && display->wakeDisplay()) {
display->redraw(true); display->redraw(true);
@@ -706,7 +861,7 @@ public:
} }
void changeHue(bool increase){ void RotaryEncoderUIUsermod::changeHue(bool increase){
#ifdef USERMOD_FOUR_LINE_DISPLAY #ifdef USERMOD_FOUR_LINE_DISPLAY
if (display && display->wakeDisplay()) { if (display && display->wakeDisplay()) {
display->redraw(true); display->redraw(true);
@@ -736,7 +891,7 @@ public:
#endif #endif
} }
void changeSat(bool increase){ void RotaryEncoderUIUsermod::changeSat(bool increase){
#ifdef USERMOD_FOUR_LINE_DISPLAY #ifdef USERMOD_FOUR_LINE_DISPLAY
if (display && display->wakeDisplay()) { if (display && display->wakeDisplay()) {
display->redraw(true); display->redraw(true);
@@ -765,7 +920,7 @@ public:
#endif #endif
} }
void changePreset(bool increase) { void RotaryEncoderUIUsermod::changePreset(bool increase) {
#ifdef USERMOD_FOUR_LINE_DISPLAY #ifdef USERMOD_FOUR_LINE_DISPLAY
if (display && display->wakeDisplay()) { if (display && display->wakeDisplay()) {
display->redraw(true); display->redraw(true);
@@ -797,7 +952,7 @@ public:
} }
} }
void changeCCT(bool increase){ void RotaryEncoderUIUsermod::changeCCT(bool increase){
#ifdef USERMOD_FOUR_LINE_DISPLAY #ifdef USERMOD_FOUR_LINE_DISPLAY
if (display && display->wakeDisplay()) { if (display && display->wakeDisplay()) {
display->redraw(true); display->redraw(true);
@@ -869,7 +1024,7 @@ public:
/** /**
* addToConfig() (called from set.cpp) stores persistent properties to cfg.json * addToConfig() (called from set.cpp) stores persistent properties to cfg.json
*/ */
void addToConfig(JsonObject &root) { void RotaryEncoderUIUsermod::addToConfig(JsonObject &root) {
// we add JSON object: {"Rotary-Encoder":{"DT-pin":12,"CLK-pin":14,"SW-pin":13}} // we add JSON object: {"Rotary-Encoder":{"DT-pin":12,"CLK-pin":14,"SW-pin":13}}
JsonObject top = root.createNestedObject(FPSTR(_name)); // usermodname JsonObject top = root.createNestedObject(FPSTR(_name)); // usermodname
top[FPSTR(_enabled)] = enabled; top[FPSTR(_enabled)] = enabled;
@@ -883,7 +1038,7 @@ public:
} }
//WLEDMM: add appendConfigData //WLEDMM: add appendConfigData
void appendConfigData() void RotaryEncoderUIUsermod::appendConfigData()
{ {
oappend(SET_F("addHB('Rotary-Encoder');")); oappend(SET_F("addHB('Rotary-Encoder');"));
@@ -903,7 +1058,7 @@ public:
* *
* The function should return true if configuration was successfully loaded or false if there was no configuration. * The function should return true if configuration was successfully loaded or false if there was no configuration.
*/ */
bool readFromConfig(JsonObject &root) { bool RotaryEncoderUIUsermod::readFromConfig(JsonObject &root) {
// we look for JSON object: {"Rotary-Encoder":{"DT-pin":12,"CLK-pin":14,"SW-pin":13}} // we look for JSON object: {"Rotary-Encoder":{"DT-pin":12,"CLK-pin":14,"SW-pin":13}}
JsonObject top = root[FPSTR(_name)]; JsonObject top = root[FPSTR(_name)];
if (top.isNull()) { if (top.isNull()) {
@@ -950,23 +1105,3 @@ public:
// use "return !top["newestParameter"].isNull();" when updating Usermod with new features // use "return !top["newestParameter"].isNull();" when updating Usermod with new features
return !top[FPSTR(_applyToAll)].isNull(); return !top[FPSTR(_applyToAll)].isNull();
} }
/*
* getId() allows you to optionally give your V2 usermod an unique ID (please define it in const.h!).
* This could be used in the future for the system to determine whether your usermod is installed.
*/
uint16_t getId()
{
return USERMOD_ID_ROTARY_ENC_UI;
}
};
// strings to reduce flash memory usage (used more than twice)
const char RotaryEncoderUIUsermod::_name[] PROGMEM = "Rotary-Encoder";
const char RotaryEncoderUIUsermod::_enabled[] PROGMEM = "enabled";
const char RotaryEncoderUIUsermod::_DT_pin[] PROGMEM = "DT-pin";
const char RotaryEncoderUIUsermod::_CLK_pin[] PROGMEM = "CLK-pin";
const char RotaryEncoderUIUsermod::_SW_pin[] PROGMEM = "SW-pin";
const char RotaryEncoderUIUsermod::_presetHigh[] PROGMEM = "preset-high";
const char RotaryEncoderUIUsermod::_presetLow[] PROGMEM = "preset-low";
const char RotaryEncoderUIUsermod::_applyToAll[] PROGMEM = "apply-2-all-seg";