More tuning

- replaced POD new/delete with malloc/free
- some more SEGLEN <= 1
- some gnu::pure
- more const attributes
- some static attributes
This commit is contained in:
Blaž Kristan 2025-01-09 13:29:06 +01:00 committed by Damian Schneider
parent 872465df40
commit 01c463c8e8
12 changed files with 109 additions and 108 deletions

View File

@ -197,7 +197,7 @@ static const char _data_FX_MODE_STROBE_RAINBOW[] PROGMEM = "Strobe Rainbow@!;,!;
* if (bool rev == true) then LEDs are turned off in reverse order
*/
uint16_t color_wipe(bool rev, bool useRandomColors) {
if (SEGLEN == 1) return mode_static();
if (SEGLEN <= 1) return mode_static();
uint32_t cycleTime = 750 + (255 - SEGMENT.speed)*150;
uint32_t perc = strip.now % cycleTime;
unsigned prog = (perc * 65535) / cycleTime;
@ -410,7 +410,7 @@ static const char _data_FX_MODE_FADE[] PROGMEM = "Fade@!;!,!;!;01";
* Scan mode parent function
*/
uint16_t scan(bool dual) {
if (SEGLEN == 1) return mode_static();
if (SEGLEN <= 1) return mode_static();
uint32_t cycleTime = 750 + (255 - SEGMENT.speed)*150;
uint32_t perc = strip.now % cycleTime;
int prog = (perc * 65535) / cycleTime;
@ -1017,7 +1017,7 @@ static const char _data_FX_MODE_COLORFUL[] PROGMEM = "Colorful@!,Saturation;1,2,
* Emulates a traffic light.
*/
uint16_t mode_traffic_light(void) {
if (SEGLEN == 1) return mode_static();
if (SEGLEN <= 1) return mode_static();
for (unsigned i=0; i < SEGLEN; i++)
SEGMENT.setPixelColor(i, SEGMENT.color_from_palette(i, true, PALETTE_SOLID_WRAP, 1));
uint32_t mdelay = 500;
@ -1050,7 +1050,7 @@ static const char _data_FX_MODE_TRAFFIC_LIGHT[] PROGMEM = "Traffic Light@!,US st
*/
#define FLASH_COUNT 4
uint16_t mode_chase_flash(void) {
if (SEGLEN == 1) return mode_static();
if (SEGLEN <= 1) return mode_static();
unsigned flash_step = SEGENV.call % ((FLASH_COUNT * 2) + 1);
for (unsigned i = 0; i < SEGLEN; i++) {
@ -1080,7 +1080,7 @@ static const char _data_FX_MODE_CHASE_FLASH[] PROGMEM = "Chase Flash@!;Bg,Fx;!";
* Prim flashes running, followed by random color.
*/
uint16_t mode_chase_flash_random(void) {
if (SEGLEN == 1) return mode_static();
if (SEGLEN <= 1) return mode_static();
unsigned flash_step = SEGENV.call % ((FLASH_COUNT * 2) + 1);
for (int i = 0; i < SEGENV.aux1; i++) {
@ -1162,7 +1162,7 @@ static const char _data_FX_MODE_RUNNING_RANDOM[] PROGMEM = "Stream@!,Zone size;;
* K.I.T.T.
*/
uint16_t mode_larson_scanner(void) {
if (SEGLEN == 1) return mode_static();
if (SEGLEN <= 1) return mode_static();
const unsigned speed = FRAMETIME * map(SEGMENT.speed, 0, 255, 96, 2); // map into useful range
const unsigned pixels = SEGLEN / speed; // how many pixels to advance per frame
@ -1220,7 +1220,7 @@ static const char _data_FX_MODE_DUAL_LARSON_SCANNER[] PROGMEM = "Scanner Dual@!,
* Firing comets from one end. "Lighthouse"
*/
uint16_t mode_comet(void) {
if (SEGLEN == 1) return mode_static();
if (SEGLEN <= 1) return mode_static();
unsigned counter = (strip.now * ((SEGMENT.speed >>2) +1)) & 0xFFFF;
unsigned index = (counter * SEGLEN) >> 16;
if (SEGENV.call == 0) SEGENV.aux0 = index;
@ -1248,7 +1248,7 @@ static const char _data_FX_MODE_COMET[] PROGMEM = "Lighthouse@!,Fade rate;!,!;!"
* Fireworks function.
*/
uint16_t mode_fireworks() {
if (SEGLEN == 1) return mode_static();
if (SEGLEN <= 1) return mode_static();
const uint16_t width = SEGMENT.is2D() ? SEG_W : SEGLEN;
const uint16_t height = SEG_H;
@ -1290,7 +1290,7 @@ static const char _data_FX_MODE_FIREWORKS[] PROGMEM = "Fireworks@,Frequency;!,!;
//Twinkling LEDs running. Inspired by https://github.com/kitesurfer1404/WS2812FX/blob/master/src/custom/Rain.h
uint16_t mode_rain() {
if (SEGLEN == 1) return mode_static();
if (SEGLEN <= 1) return mode_static();
const unsigned width = SEG_W;
const unsigned height = SEG_H;
SEGENV.step += FRAMETIME;
@ -1356,7 +1356,7 @@ static const char _data_FX_MODE_FIRE_FLICKER[] PROGMEM = "Fire Flicker@!,!;!;!;0
* Gradient run base function
*/
uint16_t gradient_base(bool loading) {
if (SEGLEN == 1) return mode_static();
if (SEGLEN <= 1) return mode_static();
uint16_t counter = strip.now * ((SEGMENT.speed >> 2) + 1);
uint16_t pp = (counter * SEGLEN) >> 16;
if (SEGENV.call == 0) pp = 0;
@ -1401,7 +1401,7 @@ static const char _data_FX_MODE_LOADING[] PROGMEM = "Loading@!,Fade;!,!;!;;ix=16
* Two dots running
*/
uint16_t mode_two_dots() {
if (SEGLEN == 1) return mode_static();
if (SEGLEN <= 1) return mode_static();
unsigned delay = 1 + (FRAMETIME<<3) / SEGLEN; // longer segments should change faster
uint32_t it = strip.now / map(SEGMENT.speed, 0, 255, delay<<4, delay);
unsigned offset = it % SEGLEN;
@ -1852,7 +1852,7 @@ static const char _data_FX_MODE_OSCILLATE[] PROGMEM = "Oscillate";
//TODO
uint16_t mode_lightning(void) {
if (SEGLEN == 1) return mode_static();
if (SEGLEN <= 1) return mode_static();
unsigned ledstart = hw_random16(SEGLEN); // Determine starting location of flash
unsigned ledlen = 1 + hw_random16(SEGLEN -ledstart); // Determine length of flash (not to go beyond NUM_LEDS-1)
uint8_t bri = 255/hw_random8(1, 3);
@ -1938,7 +1938,7 @@ static const char _data_FX_MODE_PRIDE_2015[] PROGMEM = "Pride 2015@!;;";
//eight colored dots, weaving in and out of sync with each other
uint16_t mode_juggle(void) {
if (SEGLEN == 1) return mode_static();
if (SEGLEN <= 1) return mode_static();
SEGMENT.fadeToBlackBy(192 - (3*SEGMENT.intensity/4));
CRGB fastled_col;
@ -2083,7 +2083,7 @@ static const char _data_FX_MODE_PALETTE[] PROGMEM = "Palette@Shift,Size,Rotation
// feel of your fire: COOLING (used in step 1 above) (Speed = COOLING), and SPARKING (used
// in step 3 above) (Effect Intensity = Sparking).
uint16_t mode_fire_2012() {
if (SEGLEN == 1) return mode_static();
if (SEGLEN <= 1) return mode_static();
const unsigned strips = SEGMENT.nrOfVStrips();
if (!SEGENV.allocateData(strips * SEGLEN)) return mode_static(); //allocation failed
byte* heat = SEGENV.data;
@ -2430,7 +2430,7 @@ static const char _data_FX_MODE_METEOR[] PROGMEM = "Meteor@!,Trail,,,,Gradient,,
//Railway Crossing / Christmas Fairy lights
uint16_t mode_railway() {
if (SEGLEN == 1) return mode_static();
if (SEGLEN <= 1) return mode_static();
unsigned dur = (256 - SEGMENT.speed) * 40;
uint16_t rampdur = (dur * SEGMENT.intensity) >> 8;
if (SEGENV.step > dur)
@ -2721,7 +2721,7 @@ uint16_t mode_halloween_eyes()
uint32_t blinkEndTime;
};
if (SEGLEN == 1) return mode_static();
if (SEGLEN <= 1) return mode_static();
const unsigned maxWidth = strip.isMatrix ? SEG_W : SEGLEN;
const unsigned HALLOWEEN_EYE_SPACE = MAX(2, strip.isMatrix ? SEG_W>>4: SEGLEN>>5);
const unsigned HALLOWEEN_EYE_WIDTH = HALLOWEEN_EYE_SPACE/2;
@ -2906,7 +2906,7 @@ static const char _data_FX_MODE_TRI_STATIC_PATTERN[] PROGMEM = "Solid Pattern Tr
static uint16_t spots_base(uint16_t threshold)
{
if (SEGLEN == 1) return mode_static();
if (SEGLEN <= 1) return mode_static();
if (!SEGMENT.check2) SEGMENT.fill(SEGCOLOR(1));
unsigned maxZones = SEGLEN >> 2;
@ -2962,7 +2962,7 @@ typedef struct Ball {
* Bouncing Balls Effect
*/
uint16_t mode_bouncing_balls(void) {
if (SEGLEN == 1) return mode_static();
if (SEGLEN <= 1) return mode_static();
//allocate segment data
const unsigned strips = SEGMENT.nrOfVStrips(); // adapt for 2D
const size_t maxNumBalls = 16;
@ -3140,7 +3140,7 @@ static const char _data_FX_MODE_ROLLINGBALLS[] PROGMEM = "Rolling Balls@!,# of b
* Sinelon stolen from FASTLED examples
*/
static uint16_t sinelon_base(bool dual, bool rainbow=false) {
if (SEGLEN == 1) return mode_static();
if (SEGLEN <= 1) return mode_static();
SEGMENT.fade_out(SEGMENT.intensity);
unsigned pos = beatsin16_t(SEGMENT.speed/10,0,SEGLEN-1);
if (SEGENV.call == 0) SEGENV.aux0 = pos;
@ -3245,7 +3245,7 @@ typedef struct Spark {
* modified from https://github.com/kitesurfer1404/WS2812FX/blob/master/src/custom/Popcorn.h
*/
uint16_t mode_popcorn(void) {
if (SEGLEN == 1) return mode_static();
if (SEGLEN <= 1) return mode_static();
//allocate segment data
unsigned strips = SEGMENT.nrOfVStrips();
unsigned usablePopcorns = maxNumPopcorn;
@ -3420,7 +3420,7 @@ typedef struct particle {
} star;
uint16_t mode_starburst(void) {
if (SEGLEN == 1) return mode_static();
if (SEGLEN <= 1) return mode_static();
unsigned maxData = FAIR_DATA_PER_SEG; //ESP8266: 256 ESP32: 640
unsigned segs = strip.getActiveSegmentsNum();
if (segs <= (strip.getMaxSegments() /2)) maxData *= 2; //ESP8266: 512 if <= 8 segs ESP32: 1280 if <= 16 segs
@ -3539,7 +3539,7 @@ static const char _data_FX_MODE_STARBURST[] PROGMEM = "Fireworks Starburst@Chanc
*/
uint16_t mode_exploding_fireworks(void)
{
if (SEGLEN == 1) return mode_static();
if (SEGLEN <= 1) return mode_static();
const int cols = SEGMENT.is2D() ? SEG_W : 1;
const int rows = SEGMENT.is2D() ? SEG_H : SEGLEN;
@ -3677,7 +3677,7 @@ static const char _data_FX_MODE_EXPLODING_FIREWORKS[] PROGMEM = "Fireworks 1D@Gr
*/
uint16_t mode_drip(void)
{
if (SEGLEN == 1) return mode_static();
if (SEGLEN <= 1) return mode_static();
//allocate segment data
unsigned strips = SEGMENT.nrOfVStrips();
const int maxNumDrops = 4;
@ -3773,7 +3773,7 @@ typedef struct Tetris {
} tetris;
uint16_t mode_tetrix(void) {
if (SEGLEN == 1) return mode_static();
if (SEGLEN <= 1) return mode_static();
unsigned strips = SEGMENT.nrOfVStrips(); // allow running on virtual strips (columns in 2D segment)
unsigned dataSize = sizeof(tetris);
if (!SEGENV.allocateData(dataSize * strips)) return mode_static(); //allocation failed
@ -4080,7 +4080,7 @@ static const char _data_FX_MODE_PACIFICA[] PROGMEM = "Pacifica@!,Angle;;!;;pal=5
* Mode simulates a gradual sunrise
*/
uint16_t mode_sunrise() {
if (SEGLEN == 1) return mode_static();
if (SEGLEN <= 1) return mode_static();
//speed 0 - static sun
//speed 1 - 60: sunrise time in minutes
//speed 60 - 120 : sunset time in minutes - 60;
@ -4287,7 +4287,7 @@ static const char _data_FX_MODE_FLOW[] PROGMEM = "Flow@!,Zones;;!;;m12=1"; //ver
*/
uint16_t mode_chunchun(void)
{
if (SEGLEN == 1) return mode_static();
if (SEGLEN <= 1) return mode_static();
SEGMENT.fade_out(254); // add a bit of trail
unsigned counter = strip.now * (6 + (SEGMENT.speed >> 4));
unsigned numBirds = 2 + (SEGLEN >> 3); // 2 + 1/8 of a segment
@ -4338,7 +4338,7 @@ typedef struct Spotlight {
*/
uint16_t mode_dancing_shadows(void)
{
if (SEGLEN == 1) return mode_static();
if (SEGLEN <= 1) return mode_static();
unsigned numSpotlights = map(SEGMENT.intensity, 0, 255, 2, SPOT_MAX_COUNT); // 49 on 32 segment ESP32, 17 on 16 segment ESP8266
bool initialize = SEGENV.aux0 != numSpotlights;
SEGENV.aux0 = numSpotlights;
@ -4800,7 +4800,7 @@ static const char _data_FX_MODE_AURORA[] PROGMEM = "Aurora@!,!;1,2,3;!;;sx=24,pa
// 16 bit perlinmove. Use Perlin Noise instead of sinewaves for movement. By Andrew Tuline.
// Controls are speed, # of pixels, faderate.
uint16_t mode_perlinmove(void) {
if (SEGLEN == 1) return mode_static();
if (SEGLEN <= 1) return mode_static();
SEGMENT.fade_out(255-SEGMENT.custom1);
for (int i = 0; i < SEGMENT.intensity/16 + 1; i++) {
unsigned locn = inoise16(strip.now*128/(260-SEGMENT.speed)+i*15000, strip.now*128/(260-SEGMENT.speed)); // Get a new pixel location from moving noise.
@ -4836,7 +4836,7 @@ static const char _data_FX_MODE_WAVESINS[] PROGMEM = "Wavesins@!,Brightness vari
//////////////////////////////
// By: ldirko https://editor.soulmatelights.com/gallery/392-flow-led-stripe , modifed by: Andrew Tuline
uint16_t mode_FlowStripe(void) {
if (SEGLEN == 1) return mode_static();
if (SEGLEN <= 1) return mode_static();
const int hl = SEGLEN * 10 / 13;
uint8_t hue = strip.now / (SEGMENT.speed+1);
uint32_t t = strip.now / (SEGMENT.intensity/8+1);
@ -6598,7 +6598,7 @@ static const char _data_FX_MODE_MATRIPIX[] PROGMEM = "Matripix@!,Brightness;!,!;
// * MIDNOISE //
//////////////////////
uint16_t mode_midnoise(void) { // Midnoise. By Andrew Tuline.
if (SEGLEN == 1) return mode_static();
if (SEGLEN <= 1) return mode_static();
// Changing xdist to SEGENV.aux0 and ydist to SEGENV.aux1.
um_data_t *um_data = getAudioData();
@ -6689,7 +6689,7 @@ static const char _data_FX_MODE_NOISEMETER[] PROGMEM = "Noisemeter@Fade rate,Wid
// * PIXELWAVE //
//////////////////////
uint16_t mode_pixelwave(void) { // Pixelwave. By Andrew Tuline.
if (SEGLEN == 1) return mode_static();
if (SEGLEN <= 1) return mode_static();
// even with 1D effect we have to take logic for 2D segments for allocation as fill_solid() fills whole segment
if (SEGENV.call == 0) {
@ -6757,7 +6757,7 @@ static const char _data_FX_MODE_PLASMOID[] PROGMEM = "Plasmoid@Phase,# of pixels
//////////////////////
// Puddles/Puddlepeak By Andrew Tuline. Merged by @dedehai
uint16_t mode_puddles_base(bool peakdetect) {
if (SEGLEN == 1) return mode_static();
if (SEGLEN <= 1) return mode_static();
unsigned size = 0;
uint8_t fadeVal = map(SEGMENT.speed, 0, 255, 224, 254);
unsigned pos = hw_random16(SEGLEN); // Set a random starting position.
@ -6807,7 +6807,7 @@ static const char _data_FX_MODE_PUDDLES[] PROGMEM = "Puddles@Fade rate,Puddle si
// * PIXELS //
//////////////////////
uint16_t mode_pixels(void) { // Pixels. By Andrew Tuline.
if (SEGLEN == 1) return mode_static();
if (SEGLEN <= 1) return mode_static();
if (!SEGENV.allocateData(32*sizeof(uint8_t))) return mode_static(); //allocation failed
uint8_t *myVals = reinterpret_cast<uint8_t*>(SEGENV.data); // Used to store a pile of samples because WLED frame rate and WLED sample rate are not synchronized. Frame rate is too low.
@ -6835,7 +6835,7 @@ static const char _data_FX_MODE_PIXELS[] PROGMEM = "Pixels@Fade rate,# of pixels
// ** Blurz //
//////////////////////
uint16_t mode_blurz(void) { // Blurz. By Andrew Tuline.
if (SEGLEN == 1) return mode_static();
if (SEGLEN <= 1) return mode_static();
// even with 1D effect we have to take logic for 2D segments for allocation as fill_solid() fills whole segment
um_data_t *um_data = getAudioData();
@ -6899,7 +6899,7 @@ static const char _data_FX_MODE_DJLIGHT[] PROGMEM = "DJ Light@Speed;;;01f;m12=2,
// ** Freqmap //
////////////////////
uint16_t mode_freqmap(void) { // Map FFT_MajorPeak to SEGLEN. Would be better if a higher framerate.
if (SEGLEN == 1) return mode_static();
if (SEGLEN <= 1) return mode_static();
// Start frequency = 60 Hz and log10(60) = 1.78
// End frequency = MAX_FREQUENCY in Hz and lo10(MAX_FREQUENCY) = MAX_FREQ_LOG10

View File

@ -79,7 +79,7 @@ extern byte realtimeMode; // used in getMappedPixelIndex()
#define MAX_NUM_SEGMENTS 32
#endif
#if defined(ARDUINO_ARCH_ESP32S2)
#define MAX_SEGMENT_DATA (MAX_NUM_SEGMENTS*768) // 24k by default (S2 is short on free RAM)
#define MAX_SEGMENT_DATA (MAX_NUM_SEGMENTS*768) // 24k by default (S2 is short on free RAM)
#else
#define MAX_SEGMENT_DATA (MAX_NUM_SEGMENTS*1280) // 40k by default
#endif
@ -518,7 +518,7 @@ typedef struct Segment {
//if (data) Serial.printf(" %d->(%p)", (int)_dataLen, data);
//Serial.println();
#endif
if (name) { delete[] name; name = nullptr; }
if (name) { free(name); name = nullptr; }
stopTransition();
deallocateData();
}
@ -534,7 +534,6 @@ typedef struct Segment {
inline bool isSelected() const { return selected; }
inline bool isInTransition() const { return _t != nullptr; }
inline bool isActive() const { return stop > start; }
inline bool is2D() const { return (width()>1 && height()>1); }
inline bool hasRGB() const { return _isRGB; }
inline bool hasWhite() const { return _hasW; }
inline bool isCCT() const { return _isCCT; }
@ -599,14 +598,14 @@ typedef struct Segment {
// 1D strip
[[gnu::hot]] uint16_t virtualLength() const;
[[gnu::hot]] void setPixelColor(int n, uint32_t c); // set relative pixel within segment with color
inline void setPixelColor(unsigned n, uint32_t c) { setPixelColor(int(n), c); }
inline void setPixelColor(int n, byte r, byte g, byte b, byte w = 0) { setPixelColor(n, RGBW32(r,g,b,w)); }
inline void setPixelColor(int n, CRGB c) { setPixelColor(n, RGBW32(c.r,c.g,c.b,0)); }
[[gnu::hot]] void setPixelColor(int n, uint32_t c) const; // set relative pixel within segment with color
inline void setPixelColor(unsigned n, uint32_t c) const { setPixelColor(int(n), c); }
inline void setPixelColor(int n, byte r, byte g, byte b, byte w = 0) const { setPixelColor(n, RGBW32(r,g,b,w)); }
inline void setPixelColor(int n, CRGB c) const { setPixelColor(n, RGBW32(c.r,c.g,c.b,0)); }
#ifdef WLED_USE_AA_PIXELS
void setPixelColor(float i, uint32_t c, bool aa = true);
inline void setPixelColor(float i, uint8_t r, uint8_t g, uint8_t b, uint8_t w = 0, bool aa = true) { setPixelColor(i, RGBW32(r,g,b,w), aa); }
inline void setPixelColor(float i, CRGB c, bool aa = true) { setPixelColor(i, RGBW32(c.r,c.g,c.b,0), aa); }
void setPixelColor(float i, uint32_t c, bool aa = true) const;
inline void setPixelColor(float i, uint8_t r, uint8_t g, uint8_t b, uint8_t w = 0, bool aa = true) const { setPixelColor(i, RGBW32(r,g,b,w), aa); }
inline void setPixelColor(float i, CRGB c, bool aa = true) const { setPixelColor(i, RGBW32(c.r,c.g,c.b,0), aa); }
#endif
[[gnu::hot]] uint32_t getPixelColor(int i) const;
// 1D support functions (some implement 2D as well)
@ -642,16 +641,17 @@ typedef struct Segment {
#endif
}
#ifndef WLED_DISABLE_2D
[[gnu::hot]] uint16_t XY(int x, int y) const; // support function to get relative index within segment
inline bool is2D() const { return (width()>1 && height()>1); }
[[gnu::hot]] int XY(int x, int y) const; // support function to get relative index within segment
[[gnu::hot]] void setPixelColorXY(int x, int y, uint32_t c) const; // set relative pixel within segment with color
inline void setPixelColorXY(unsigned x, unsigned y, uint32_t c) const { setPixelColorXY(int(x), int(y), c); }
inline void setPixelColorXY(int x, int y, byte r, byte g, byte b, byte w = 0) const { setPixelColorXY(x, y, RGBW32(r,g,b,w)); }
inline void setPixelColorXY(int x, int y, CRGB c) const { setPixelColorXY(x, y, RGBW32(c.r,c.g,c.b,0)); }
inline void setPixelColorXY(unsigned x, unsigned y, CRGB c) const { setPixelColorXY(int(x), int(y), RGBW32(c.r,c.g,c.b,0)); }
#ifdef WLED_USE_AA_PIXELS
void setPixelColorXY(float x, float y, uint32_t c, bool aa = true);
inline void setPixelColorXY(float x, float y, byte r, byte g, byte b, byte w = 0, bool aa = true) { setPixelColorXY(x, y, RGBW32(r,g,b,w), aa); }
inline void setPixelColorXY(float x, float y, CRGB c, bool aa = true) { setPixelColorXY(x, y, RGBW32(c.r,c.g,c.b,0), aa); }
void setPixelColorXY(float x, float y, uint32_t c, bool aa = true) const;
inline void setPixelColorXY(float x, float y, byte r, byte g, byte b, byte w = 0, bool aa = true) const { setPixelColorXY(x, y, RGBW32(r,g,b,w), aa); }
inline void setPixelColorXY(float x, float y, CRGB c, bool aa = true) const { setPixelColorXY(x, y, RGBW32(c.r,c.g,c.b,0), aa); }
#endif
[[gnu::hot]] uint32_t getPixelColorXY(int x, int y) const;
// 2D support functions
@ -678,7 +678,8 @@ typedef struct Segment {
void wu_pixel(uint32_t x, uint32_t y, CRGB c);
inline void fill_solid(CRGB c) { fill(RGBW32(c.r,c.g,c.b,0)); }
#else
inline uint16_t XY(int x, int y) { return x; }
inline constexpr bool is2D() const { return false; }
inline int XY(int x, int y) const { return x; }
inline void setPixelColorXY(int x, int y, uint32_t c) { setPixelColor(x, c); }
inline void setPixelColorXY(unsigned x, unsigned y, uint32_t c) { setPixelColor(int(x), c); }
inline void setPixelColorXY(int x, int y, byte r, byte g, byte b, byte w = 0) { setPixelColor(x, RGBW32(r,g,b,w)); }
@ -778,7 +779,7 @@ class WS2812FX { // 96 bytes
}
~WS2812FX() {
if (customMappingTable) delete[] customMappingTable;
if (customMappingTable) free(customMappingTable);
_mode.clear();
_modeData.clear();
_segments.clear();
@ -804,7 +805,7 @@ class WS2812FX { // 96 bytes
resetSegments(), // marks all segments for reset
makeAutoSegments(bool forceReset = false), // will create segments based on configured outputs
fixInvalidSegments(), // fixes incorrect segment configuration
setPixelColor(unsigned n, uint32_t c), // paints absolute strip pixel with index n and color c
setPixelColor(unsigned n, uint32_t c) const, // paints absolute strip pixel with index n and color c
show(), // initiates LED output
setTargetFps(unsigned fps),
setupEffectData(); // add default effects to the list; defined in FX.cpp
@ -812,9 +813,9 @@ class WS2812FX { // 96 bytes
inline void resetTimebase() { timebase = 0UL - millis(); }
inline void restartRuntime() { for (Segment &seg : _segments) { seg.markForReset().resetIfRequired(); } }
inline void setTransitionMode(bool t) { for (Segment &seg : _segments) seg.startTransition(t ? _transitionDur : 0); }
inline void setPixelColor(unsigned n, uint8_t r, uint8_t g, uint8_t b, uint8_t w = 0) { setPixelColor(n, RGBW32(r,g,b,w)); }
inline void setPixelColor(unsigned n, CRGB c) { setPixelColor(n, c.red, c.green, c.blue); }
inline void fill(uint32_t c) { for (unsigned i = 0; i < getLengthTotal(); i++) setPixelColor(i, c); } // fill whole strip with color (inline)
inline void setPixelColor(unsigned n, uint8_t r, uint8_t g, uint8_t b, uint8_t w = 0) const { setPixelColor(n, RGBW32(r,g,b,w)); }
inline void setPixelColor(unsigned n, CRGB c) const { setPixelColor(n, c.red, c.green, c.blue); }
inline void fill(uint32_t c) const { for (unsigned i = 0; i < getLengthTotal(); i++) setPixelColor(i, c); } // fill whole strip with color (inline)
inline void trigger() { _triggered = true; } // Forces the next frame to be computed on all active segments.
inline void setShowCallback(show_callback cb) { _callback = cb; }
inline void setTransition(uint16_t t) { _transitionDur = t; } // sets transition time (in ms)
@ -824,7 +825,7 @@ class WS2812FX { // 96 bytes
bool
paletteFade,
checkSegmentAlignment(),
checkSegmentAlignment() const,
hasRGBWBus() const,
hasCCTBus() const,
deserializeMap(unsigned n = 0);
@ -918,11 +919,11 @@ class WS2812FX { // 96 bytes
void setUpMatrix(); // sets up automatic matrix ledmap from panel configuration
// outsmart the compiler :) by correctly overloading
inline void setPixelColorXY(int x, int y, uint32_t c) { setPixelColor((unsigned)(y * Segment::maxWidth + x), c); }
inline void setPixelColorXY(int x, int y, byte r, byte g, byte b, byte w = 0) { setPixelColorXY(x, y, RGBW32(r,g,b,w)); }
inline void setPixelColorXY(int x, int y, CRGB c) { setPixelColorXY(x, y, RGBW32(c.r,c.g,c.b,0)); }
inline void setPixelColorXY(int x, int y, uint32_t c) const { setPixelColor((unsigned)(y * Segment::maxWidth + x), c); }
inline void setPixelColorXY(int x, int y, byte r, byte g, byte b, byte w = 0) const { setPixelColorXY(x, y, RGBW32(r,g,b,w)); }
inline void setPixelColorXY(int x, int y, CRGB c) const { setPixelColorXY(x, y, RGBW32(c.r,c.g,c.b,0)); }
inline uint32_t getPixelColorXY(int x, int y) const { return getPixelColor(isMatrix ? y * Segment::maxWidth + x : x); }
inline uint32_t getPixelColorXY(int x, int y) const { return getPixelColor(isMatrix ? y * Segment::maxWidth + x : x); }
// end 2D support

View File

@ -50,8 +50,8 @@ void WS2812FX::setUpMatrix() {
customMappingSize = 0; // prevent use of mapping if anything goes wrong
if (customMappingTable) delete[] customMappingTable;
customMappingTable = new(std::nothrow) uint16_t[getLengthTotal()];
if (customMappingTable) free(customMappingTable);
customMappingTable = static_cast<uint16_t*>(malloc(sizeof(uint16_t)*getLengthTotal()));
if (customMappingTable) {
customMappingSize = getLengthTotal();
@ -68,7 +68,7 @@ void WS2812FX::setUpMatrix() {
// content of the file is just raw JSON array in the form of [val1,val2,val3,...]
// there are no other "key":"value" pairs in it
// allowed values are: -1 (missing pixel/no LED attached), 0 (inactive/unused pixel), 1 (active/used pixel)
char fileName[32]; strcpy_P(fileName, PSTR("/2d-gaps.json")); // reduce flash footprint
char fileName[32]; strcpy_P(fileName, PSTR("/2d-gaps.json"));
bool isFile = WLED_FS.exists(fileName);
size_t gapSize = 0;
int8_t *gapTable = nullptr;
@ -85,7 +85,7 @@ void WS2812FX::setUpMatrix() {
JsonArray map = pDoc->as<JsonArray>();
gapSize = map.size();
if (!map.isNull() && gapSize >= matrixSize) { // not an empty map
gapTable = new(std::nothrow) int8_t[gapSize];
gapTable = static_cast<int8_t*>(malloc(gapSize));
if (gapTable) for (size_t i = 0; i < gapSize; i++) {
gapTable[i] = constrain(map[i], -1, 1);
}
@ -113,7 +113,7 @@ void WS2812FX::setUpMatrix() {
}
// delete gap array as we no longer need it
if (gapTable) delete[] gapTable;
if (gapTable) free(gapTable);
#ifdef WLED_DEBUG
DEBUG_PRINT(F("Matrix ledmap:"));
@ -146,7 +146,7 @@ void WS2812FX::setUpMatrix() {
#ifndef WLED_DISABLE_2D
// XY(x,y) - gets pixel index within current segment (often used to reference leds[] array element)
uint16_t IRAM_ATTR_YN Segment::XY(int x, int y) const
int IRAM_ATTR_YN Segment::XY(int x, int y) const
{
const int vW = vWidth(); // segment width in logical pixels (can be 0 if segment is inactive)
const int vH = vHeight(); // segment height in logical pixels (is always >= 1)
@ -215,7 +215,7 @@ void IRAM_ATTR_YN Segment::setPixelColorXY(int x, int y, uint32_t col) const
#ifdef WLED_USE_AA_PIXELS
// anti-aliased version of setPixelColorXY()
void Segment::setPixelColorXY(float x, float y, uint32_t col, bool aa)
void Segment::setPixelColorXY(float x, float y, uint32_t col, bool aa) const
{
if (!isActive()) return; // not active
if (x<0.0f || x>1.0f || y<0.0f || y>1.0f) return; // not normalized

View File

@ -94,7 +94,7 @@ Segment::Segment(const Segment &orig) {
name = nullptr;
data = nullptr;
_dataLen = 0;
if (orig.name) { name = new(std::nothrow) char[strlen(orig.name)+1]; if (name) strcpy(name, orig.name); }
if (orig.name) { name = static_cast<char*>(malloc(strlen(orig.name)+1)); if (name) strcpy(name, orig.name); }
if (orig.data) { if (allocateData(orig._dataLen)) memcpy(data, orig.data, orig._dataLen); }
}
@ -113,7 +113,7 @@ Segment& Segment::operator= (const Segment &orig) {
//DEBUG_PRINTF_P(PSTR("-- Copying segment: %p -> %p\n"), &orig, this);
if (this != &orig) {
// clean destination
if (name) { delete[] name; name = nullptr; }
if (name) { free(name); name = nullptr; }
stopTransition();
deallocateData();
// copy source
@ -122,7 +122,7 @@ Segment& Segment::operator= (const Segment &orig) {
data = nullptr;
_dataLen = 0;
// copy source data
if (orig.name) { name = new(std::nothrow) char[strlen(orig.name)+1]; if (name) strcpy(name, orig.name); }
if (orig.name) { name = static_cast<char*>(malloc(strlen(orig.name)+1)); if (name) strcpy(name, orig.name); }
if (orig.data) { if (allocateData(orig._dataLen)) memcpy(data, orig.data, orig._dataLen); }
}
return *this;
@ -132,7 +132,7 @@ Segment& Segment::operator= (const Segment &orig) {
Segment& Segment::operator= (Segment &&orig) noexcept {
//DEBUG_PRINTF_P(PSTR("-- Moving segment: %p -> %p\n"), &orig, this);
if (this != &orig) {
if (name) { delete[] name; name = nullptr; } // free old name
if (name) { free(name); name = nullptr; } // free old name
stopTransition();
deallocateData(); // free old runtime data
memcpy((void*)this, (void*)&orig, sizeof(Segment));
@ -869,7 +869,7 @@ void IRAM_ATTR_YN Segment::setPixelColor(int i, uint32_t col)
#ifdef WLED_USE_AA_PIXELS
// anti-aliased normalized version of setPixelColor()
void Segment::setPixelColor(float i, uint32_t col, bool aa)
void Segment::setPixelColor(float i, uint32_t col, bool aa) const
{
if (!isActive()) return; // not active
int vStrip = int(i/10.0f); // hack to allow running on virtual strips (2D segment columns/rows)
@ -1413,7 +1413,7 @@ void WS2812FX::service() {
#endif
}
void IRAM_ATTR WS2812FX::setPixelColor(unsigned i, uint32_t col) {
void IRAM_ATTR WS2812FX::setPixelColor(unsigned i, uint32_t col) const {
i = getMappedPixelIndex(i);
if (i >= _length) return;
BusManager::setPixelColor(i, col);
@ -1694,9 +1694,9 @@ void WS2812FX::fixInvalidSegments() {
//true if all segments align with a bus, or if a segment covers the total length
//irrelevant in 2D set-up
bool WS2812FX::checkSegmentAlignment() {
bool WS2812FX::checkSegmentAlignment() const {
bool aligned = false;
for (segment &seg : _segments) {
for (const segment &seg : _segments) {
for (unsigned b = 0; b<BusManager::getNumBusses(); b++) {
Bus *bus = BusManager::getBus(b);
if (seg.start == bus->getStart() && seg.stop == bus->getStart() + bus->getLength()) aligned = true;
@ -1808,8 +1808,8 @@ bool WS2812FX::deserializeMap(unsigned n) {
Segment::maxHeight = min(max(root[F("height")].as<int>(), 1), 128);
}
if (customMappingTable) delete[] customMappingTable;
customMappingTable = new(std::nothrow) uint16_t[getLengthTotal()];
if (customMappingTable) free(customMappingTable);
customMappingTable = static_cast<uint16_t*>(malloc(sizeof(uint16_t)*getLengthTotal()));
if (customMappingTable) {
DEBUG_PRINT(F("Reading LED map from ")); DEBUG_PRINTLN(fileName);

View File

@ -161,11 +161,11 @@ class NeoGammaWLEDMethod {
};
#define gamma32(c) NeoGammaWLEDMethod::Correct32(c)
#define gamma8(c) NeoGammaWLEDMethod::rawGamma8(c)
[[gnu::hot]] uint32_t color_blend(uint32_t c1, uint32_t c2 , uint8_t blend);
[[gnu::hot, gnu::pure]] uint32_t color_blend(uint32_t c1, uint32_t c2 , uint8_t blend);
inline uint32_t color_blend16(uint32_t c1, uint32_t c2, uint16_t b) { return color_blend(c1, c2, b >> 8); };
[[gnu::hot]] uint32_t color_add(uint32_t, uint32_t, bool preserveCR = false);
[[gnu::hot]] uint32_t color_fade(uint32_t c1, uint8_t amount, bool video=false);
[[gnu::hot]] uint32_t ColorFromPaletteWLED(const CRGBPalette16 &pal, unsigned index, uint8_t brightness = (uint8_t)255U, TBlendType blendType = LINEARBLEND);
[[gnu::hot, gnu::pure]] uint32_t color_add(uint32_t, uint32_t, bool preserveCR = false);
[[gnu::hot, gnu::pure]] uint32_t color_fade(uint32_t c1, uint8_t amount, bool video=false);
[[gnu::hot, gnu::pure]] uint32_t ColorFromPaletteWLED(const CRGBPalette16 &pal, unsigned index, uint8_t brightness = (uint8_t)255U, TBlendType blendType = LINEARBLEND);
CRGBPalette16 generateHarmonicRandomPalette(const CRGBPalette16 &basepalette);
CRGBPalette16 generateRandomPalette();
inline uint32_t colorFromRgbw(byte* rgbw) { return uint32_t((byte(rgbw[3]) << 24) | (byte(rgbw[0]) << 16) | (byte(rgbw[1]) << 8) | (byte(rgbw[2]))); }
@ -176,7 +176,7 @@ inline CHSV rgb2hsv(const CRGB c) { CHSV32 hsv; rgb2hsv((uint32_t((byte(c.r) <<
void colorKtoRGB(uint16_t kelvin, byte* rgb);
void colorCTtoRGB(uint16_t mired, byte* rgb); //white spectrum to rgb
void colorXYtoRGB(float x, float y, byte* rgb); // only defined if huesync disabled TODO
void colorRGBtoXY(byte* rgb, float* xy); // only defined if huesync disabled TODO
void colorRGBtoXY(const byte* rgb, float* xy); // only defined if huesync disabled TODO
void colorFromDecOrHexString(byte* rgb, const char* in);
bool colorFromHexString(byte* rgb, const char* in);
uint32_t colorBalanceFromKelvin(uint16_t kelvin, uint32_t rgb);
@ -467,10 +467,10 @@ void userLoop();
#include "soc/wdev_reg.h"
#define HW_RND_REGISTER REG_READ(WDEV_RND_REG)
#endif
int getNumVal(const String* req, uint16_t pos);
[[gnu::pure]] int getNumVal(const String* req, uint16_t pos);
void parseNumber(const char* str, byte* val, byte minv=0, byte maxv=255);
bool getVal(JsonVariant elem, byte* val, byte minv=0, byte maxv=255); // getVal supports inc/decrementing and random ("X~Y(r|~[w][-][Z])" form)
bool getBoolVal(JsonVariant elem, bool dflt);
bool getVal(JsonVariant elem, byte* val, byte minv=0, byte maxv=255); // getVal supports inc/decrementing and random ("X~Y(r|[w]~[-][Z])" form)
[[gnu::pure]] bool getBoolVal(const JsonVariant &elem, bool dflt);
bool updateVal(const char* req, const char* key, byte* val, byte minv=0, byte maxv=255);
size_t printSetFormCheckbox(Print& settingsScript, const char* key, int val);
size_t printSetFormValue(Print& settingsScript, const char* key, int val);
@ -478,7 +478,7 @@ size_t printSetFormValue(Print& settingsScript, const char* key, const char* val
size_t printSetFormIndex(Print& settingsScript, const char* key, int index);
size_t printSetClassElementHTML(Print& settingsScript, const char* key, const int index, const char* val);
void prepareHostname(char* hostname);
bool isAsterisksOnly(const char* str, byte maxLen);
[[gnu::pure]] bool isAsterisksOnly(const char* str, byte maxLen);
bool requestJSONBufferLock(uint8_t moduleID=255);
void releaseJSONBufferLock();
uint8_t extractModeName(uint8_t mode, const char *src, char *dest, uint8_t maxLen);
@ -491,8 +491,8 @@ uint16_t beatsin16_t(accum88 beats_per_minute, uint16_t lowest = 0, uint16_t hig
uint8_t beatsin8_t(accum88 beats_per_minute, uint8_t lowest = 0, uint8_t highest = 255, uint32_t timebase = 0, uint8_t phase_offset = 0);
um_data_t* simulateSound(uint8_t simulationId);
void enumerateLedmaps();
uint8_t get_random_wheel_index(uint8_t pos);
float mapf(float x, float in_min, float in_max, float out_min, float out_max);
[[gnu::hot]] uint8_t get_random_wheel_index(uint8_t pos);
[[gnu::hot, gnu::pure]] float mapf(float x, float in_min, float in_max, float out_min, float out_max);
// fast (true) random numbers using hardware RNG, all functions return values in the range lowerlimit to upperlimit-1
// note: for true random numbers with high entropy, do not call faster than every 200ns (5MHz)

View File

@ -176,7 +176,7 @@ static void writeSpace(size_t l)
if (knownLargestSpace < l) knownLargestSpace = l;
}
bool appendObjectToFile(const char* key, const JsonDocument* content, uint32_t s, uint32_t contentLen = 0)
static bool appendObjectToFile(const char* key, const JsonDocument* content, uint32_t s, uint32_t contentLen = 0)
{
#ifdef WLED_DEBUG_FS
DEBUGFS_PRINTLN(F("Append"));

View File

@ -68,7 +68,7 @@ bool deserializeSegment(JsonObject elem, byte it, byte presetId)
if (elem["n"]) {
// name field exists
if (seg.name) { //clear old name
delete[] seg.name;
free(seg.name);
seg.name = nullptr;
}
@ -77,7 +77,7 @@ bool deserializeSegment(JsonObject elem, byte it, byte presetId)
if (name != nullptr) len = strlen(name);
if (len > 0) {
if (len > WLED_MAX_SEGNAME_LEN) len = WLED_MAX_SEGNAME_LEN;
seg.name = new(std::nothrow) char[len+1];
seg.name = static_cast<char*>(malloc(len+1));
if (seg.name) strlcpy(seg.name, name, WLED_MAX_SEGNAME_LEN+1);
} else {
// but is empty (already deleted above)
@ -86,7 +86,7 @@ bool deserializeSegment(JsonObject elem, byte it, byte presetId)
} else if (start != seg.start || stop != seg.stop) {
// clearing or setting segment without name field
if (seg.name) {
delete[] seg.name;
free(seg.name);
seg.name = nullptr;
}
}

View File

@ -68,8 +68,8 @@ static void onMqttMessage(char* topic, char* payload, AsyncMqttClientMessageProp
}
if (index == 0) { // start (1st partial packet or the only packet)
if (payloadStr) delete[] payloadStr; // fail-safe: release buffer
payloadStr = new char[total+1]; // allocate new buffer
if (payloadStr) free(payloadStr); // fail-safe: release buffer
payloadStr = static_cast<char*>(malloc(total+1)); // allocate new buffer
}
if (payloadStr == nullptr) return; // buffer not allocated
@ -94,7 +94,7 @@ static void onMqttMessage(char* topic, char* payload, AsyncMqttClientMessageProp
} else {
// Non-Wled Topic used here. Probably a usermod subscribed to this topic.
UsermodManager::onMqttMessage(topic, payloadStr);
delete[] payloadStr;
free(payloadStr);
payloadStr = nullptr;
return;
}
@ -124,7 +124,7 @@ static void onMqttMessage(char* topic, char* payload, AsyncMqttClientMessageProp
// topmost topic (just wled/MAC)
parseMQTTBriPayload(payloadStr);
}
delete[] payloadStr;
free(payloadStr);
payloadStr = nullptr;
}

View File

@ -76,8 +76,8 @@ static void doSaveState() {
// clean up
saveLedmap = -1;
presetToSave = 0;
delete[] saveName;
delete[] quickLoad;
free(saveName);
free(quickLoad);
saveName = nullptr;
quickLoad = nullptr;
playlistSave = false;
@ -216,8 +216,8 @@ void handlePresets()
//called from handleSet(PS=) [network callback (sObj is empty), IR (irrational), deserializeState, UDP] and deserializeState() [network callback (filedoc!=nullptr)]
void savePreset(byte index, const char* pname, JsonObject sObj)
{
if (!saveName) saveName = new(std::nothrow) char[33];
if (!quickLoad) quickLoad = new(std::nothrow) char[9];
if (!saveName) saveName = static_cast<char*>(malloc(33));
if (!quickLoad) quickLoad = static_cast<char*>(malloc(9));
if (!saveName || !quickLoad) return;
if (index == 0 || (index > 250 && index < 255)) return;
@ -263,8 +263,8 @@ void savePreset(byte index, const char* pname, JsonObject sObj)
presetsModifiedTime = toki.second(); //unix time
updateFSInfo();
}
delete[] saveName;
delete[] quickLoad;
free(saveName);
free(quickLoad);
saveName = nullptr;
quickLoad = nullptr;
} else {

View File

@ -209,7 +209,7 @@ void handleSettingsSet(AsyncWebServerRequest *request, byte subPage)
// actual finalization is done in WLED::loop() (removing old busses and adding new)
// this may happen even before this loop is finished so we do "doInitBusses" after the loop
if (busConfigs[s] != nullptr) delete busConfigs[s];
busConfigs[s] = new BusConfig(type, pins, start, length, colorOrder | (channelSwap<<4), request->hasArg(cv), skip, awmode, freq, useGlobalLedBuffer, maPerLed, maMax);
busConfigs[s] = new(std::nothrow) BusConfig(type, pins, start, length, colorOrder | (channelSwap<<4), request->hasArg(cv), skip, awmode, freq, useGlobalLedBuffer, maPerLed, maMax);
busesChanged = true;
}
//doInitBusses = busesChanged; // we will do that below to ensure all input data is processed

View File

@ -206,7 +206,7 @@ void notify(byte callMode, bool followUp)
notificationCount = followUp ? notificationCount + 1 : 0;
}
void parseNotifyPacket(const uint8_t *udpIn) {
static void parseNotifyPacket(const uint8_t *udpIn) {
//ignore notification if received within a second after sending a notification ourselves
if (millis() - notificationSentTime < 1000) return;
if (udpIn[1] > 199) return; //do not receive custom versions

View File

@ -73,7 +73,7 @@ bool getVal(JsonVariant elem, byte* val, byte vmin, byte vmax) {
}
bool getBoolVal(JsonVariant elem, bool dflt) {
bool getBoolVal(const JsonVariant &elem, bool dflt) {
if (elem.is<const char*>() && elem.as<const char*>()[0] == 't') {
return !dflt;
} else {
@ -538,7 +538,7 @@ void enumerateLedmaps() {
#ifndef ESP8266
if (ledmapNames[i-1]) { //clear old name
delete[] ledmapNames[i-1];
free(ledmapNames[i-1]);
ledmapNames[i-1] = nullptr;
}
#endif
@ -556,7 +556,7 @@ void enumerateLedmaps() {
const char *name = root["n"].as<const char*>();
if (name != nullptr) len = strlen(name);
if (len > 0 && len < 33) {
ledmapNames[i-1] = new char[len+1];
ledmapNames[i-1] = static_cast<char*>(malloc(len+1));
if (ledmapNames[i-1]) strlcpy(ledmapNames[i-1], name, 33);
}
}
@ -564,7 +564,7 @@ void enumerateLedmaps() {
char tmp[33];
snprintf_P(tmp, 32, s_ledmap_tmpl, i);
len = strlen(tmp);
ledmapNames[i-1] = new char[len+1];
ledmapNames[i-1] = static_cast<char*>(malloc(len+1));
if (ledmapNames[i-1]) strlcpy(ledmapNames[i-1], tmp, 33);
}
}