GCC Code Coverage Report


Directory: ./
File: overlays/WLEDEffects.cpp
Date: 2026-10-29 08:11:58
Exec Total Coverage
Lines: 407 458 88.9%
Functions: 33 35 94.3%
Branches: 417 801 52.1%

Line Branch Exec Source
1 /*
2 * Pixel Overlay Effects for Falcon Player (FPP) ported from WLED
3 *
4 * This file is part of the Falcon Player (FPP) and is Copyright (C)
5 * 2013-2022 by the Falcon Player Developers.
6 *
7 * The Falcon Player (FPP) is free software, and is covered under
8 * multiple Open Source licenses. Please see the included 'LICENSES'
9 * file for descriptions of what files are covered by each license.
10 *
11 * This source file is covered under the LGPL v2.1 as described in the
12 * included LICENSE.LGPL file.
13 */
14
15 #include "fpp-pch.h"
16
17 #include "fpp-json.h"
18
19 #include "PixelOverlay.h"
20 #include "PixelOverlayModel.h"
21 #include "WLEDEffects.h"
22 #include "PolarBufferMap.h"
23
24 #include "wled/wled.h"
25
26 #include <string_view>
27
28 499698 WLEDEffect::WLEDEffect(const std::string& name) :
29 499698 PixelOverlayEffect(name) {
30 499698 }
31 195108 WLEDEffect::~WLEDEffect() {
32 195108 }
33
34 class WLEDRunningEffect : public RunningEffect {
35 public:
36 1197 WLEDRunningEffect(PixelOverlayModel* m, const std::string& n, const std::string& ad) :
37 RunningEffect(m),
38 1197 effectName(n),
39
1/2
✓ Branch 0 taken 1197 times.
✗ Branch 1 not taken.
1197 autoDisable(false) {
40
1/2
✓ Branch 0 taken 1197 times.
✗ Branch 1 not taken.
1197 PixelOverlayState st(ad);
41
2/2
✓ Branch 0 taken 1196 times.
✓ Branch 1 taken 1 times.
1197 if (st.getState() != PixelOverlayState::PixelState::Disabled) {
42 1196 autoDisable = true;
43
1/2
✓ Branch 0 taken 1196 times.
✗ Branch 1 not taken.
1196 model->setState(st);
44 }
45 1197 }
46 23 const std::string& name() const override {
47 23 return effectName;
48 }
49 ✗ virtual void toJson(Json::Value& v) const override {
50 ✗ v["name"] = name();
51 ✗ };
52 virtual int32_t doIteration() = 0;
53
54 8552 virtual int32_t update() override {
55
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 8552 times.
8552 if (stopped) {
56 ✗ if (autoDisable) {
57 ✗ model->setState(PixelOverlayState(PixelOverlayState::PixelState::Disabled));
58 }
59 ✗ return EFFECT_DONE;
60 }
61 8552 int r = doIteration();
62
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 8552 times.
8552 if (r <= 0) {
63 ✗ stopped = true;
64 ✗ return EFFECT_AFTER_NEXT_OUTPUT;
65 }
66 8552 return r;
67 }
68 bool stopped = false;
69 std::string effectName;
70 bool autoDisable;
71
72 4280 static int parseInt(const std::string& setting) {
73 4280 return std::atoi(setting.c_str());
74 }
75 1035 static int parseBool(const std::string& setting) {
76
3/4
✓ Branch 0 taken 1035 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 245 times.
✓ Branch 3 taken 790 times.
1035 return setting == "true" || setting == "1";
77 }
78 2740 static uint32_t parseColor(const std::string& setting) {
79 2740 return PixelOverlayManager::mapColor(setting);
80 }
81 2 static uint32_t adjustColor(uint32_t color, int brightness) {
82 2 int r = (color >> 16) & 0xFF;
83 2 int g = (color >> 8) & 0xFF;
84 2 int b = color & 0xFF;
85 2 int w = (color >> 24) & 0xFF; // RGBW high byte; 0 for plain #RRGGBB inputs
86
87 2 r = (r * brightness / 100) & 0xFF;
88 2 g = (g * brightness / 100) & 0xFF;
89 2 b = (b * brightness / 100) & 0xFF;
90 2 w = (w * brightness / 100) & 0xFF;
91
92 2 return ((uint32_t)w << 24) | (r << 16) | (g << 8) | b;
93 }
94
95 1 void fill(uint32_t color) {
96 1 model->fillOverlayBuffer((color & 0xFF0000) >> 16, (color & 0xFF00) >> 8, color & 0xFF);
97 1 }
98 1 void flush() {
99 1 model->flushOverlayBuffer();
100 1 }
101 };
102
103 class BlinkEffect : public WLEDEffect {
104 public:
105 2346 BlinkEffect() :
106
2/4
✓ Branch 0 taken 2346 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 2346 times.
✗ Branch 3 not taken.
4692 WLEDEffect("Blink") {
107
6/12
✓ Branch 0 taken 2346 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 2346 times.
✗ Branch 3 not taken.
✓ Branch 4 taken 2346 times.
✗ Branch 5 not taken.
✓ Branch 6 taken 2346 times.
✗ Branch 7 not taken.
✓ Branch 8 taken 2346 times.
✗ Branch 9 not taken.
✓ Branch 10 taken 2346 times.
✗ Branch 11 not taken.
14076 args.push_back(CommandArg("Brightness", "range", "Brightness").setRange(0, 100).setDefaultValue("100"));
108
6/12
✓ Branch 0 taken 2346 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 2346 times.
✗ Branch 3 not taken.
✓ Branch 4 taken 2346 times.
✗ Branch 5 not taken.
✓ Branch 6 taken 2346 times.
✗ Branch 7 not taken.
✓ Branch 8 taken 2346 times.
✗ Branch 9 not taken.
✓ Branch 10 taken 2346 times.
✗ Branch 11 not taken.
14076 args.push_back(CommandArg("Speed", "range", "Speed").setRange(1, 5000).setDefaultValue("1000"));
109
6/12
✓ Branch 0 taken 2346 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 2346 times.
✗ Branch 3 not taken.
✓ Branch 4 taken 2346 times.
✗ Branch 5 not taken.
✓ Branch 6 taken 2346 times.
✗ Branch 7 not taken.
✓ Branch 8 taken 2346 times.
✗ Branch 9 not taken.
✓ Branch 10 taken 2346 times.
✗ Branch 11 not taken.
14076 args.push_back(CommandArg("Intensity", "range", "Intensity").setRange(0, 100).setDefaultValue("50"));
110
6/12
✓ Branch 0 taken 2346 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 2346 times.
✗ Branch 3 not taken.
✓ Branch 4 taken 2346 times.
✗ Branch 5 not taken.
✓ Branch 6 taken 2346 times.
✗ Branch 7 not taken.
✓ Branch 8 taken 2346 times.
✗ Branch 9 not taken.
✓ Branch 10 taken 2346 times.
✗ Branch 11 not taken.
14076 args.push_back(CommandArg("Color1", "color", "Color1").setDefaultValue("#FF0000"));
111
6/12
✓ Branch 0 taken 2346 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 2346 times.
✗ Branch 3 not taken.
✓ Branch 4 taken 2346 times.
✗ Branch 5 not taken.
✓ Branch 6 taken 2346 times.
✗ Branch 7 not taken.
✓ Branch 8 taken 2346 times.
✗ Branch 9 not taken.
✓ Branch 10 taken 2346 times.
✗ Branch 11 not taken.
14076 args.push_back(CommandArg("Color2", "color", "Color2").setDefaultValue("#000000"));
112 2346 }
113
114 1 virtual bool apply(PixelOverlayModel* model, const std::string& autoEnable, const std::vector<std::string>& args) override {
115
4/10
✓ Branch 0 taken 1 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 1 times.
✗ Branch 3 not taken.
✓ Branch 4 taken 1 times.
✗ Branch 5 not taken.
✗ Branch 6 not taken.
✓ Branch 7 taken 1 times.
✗ Branch 8 not taken.
✗ Branch 9 not taken.
3 model->setRunningEffect(new BlinkEffectInternal(model, "Blink", autoEnable, args), 25);
116 1 return true;
117 }
118
119 class BlinkEffectInternal : public WLEDRunningEffect {
120 public:
121 1 BlinkEffectInternal(PixelOverlayModel* m, const std::string& n, const std::string& ad, const std::vector<std::string>& args) :
122 1 WLEDRunningEffect(m, n, ad) {
123 1 brightness = parseInt(args[0]);
124 1 speed = parseInt(args[1]);
125 1 intensity = parseInt(args[2]);
126
1/2
✓ Branch 0 taken 1 times.
✗ Branch 1 not taken.
1 color1 = adjustColor(parseColor(args[3]), brightness);
127
1/2
✓ Branch 0 taken 1 times.
✗ Branch 1 not taken.
1 color2 = adjustColor(parseColor(args[4]), brightness);
128 1 }
129
130 ✗ virtual void toJson(Json::Value& v) const override {
131 ✗ v["name"] = name();
132 ✗ v["brightness"] = brightness;
133 ✗ v["speed"] = speed;
134 ✗ v["intensity"] = intensity;
135 ✗ v["color1"] = color1;
136 ✗ v["color2"] = color2;
137 ✗ }
138 1 virtual int32_t doIteration() override {
139
1/2
✓ Branch 0 taken 1 times.
✗ Branch 1 not taken.
1 if (isColor2) {
140 1 fill(color1);
141 1 isColor2 = false;
142 1 flush();
143 1 return speed * intensity / 100;
144 }
145 ✗ fill(color2);
146 ✗ flush();
147 ✗ isColor2 = true;
148 ✗ return speed - (speed * intensity / 100);
149 }
150
151 int brightness;
152 int speed;
153 int intensity;
154 uint32_t color1;
155 uint32_t color2;
156 bool isColor2 = true;
157 };
158 };
159
160 // APPEND ONLY, NEVER REORDER. The index of a value here is what reaches
161 // Bus::setPixelColor, and the NAMES are persisted in sequences, cue files and
162 // plugin configs. Reordering would silently repaint every saved show.
163 //
164 // The four Radial/Angular entries lay the buffer out in POLAR order (radius and
165 // angle) using the model's geometry from config/virtualdisplaymap; see
166 // PolarBufferMap.h. A player with no xLights layout cannot build one, and
167 // then the strip behaves as Horizontal. A name not in this list (empty, a
168 // typo, or from a newer build) is Horizontal too: it is read as index 0.
169 static std::array<std::string_view, 8> BUFFERMAPS{
170 "Horizontal", "Vertical", "Horizontal Flipped", "Vertical Flipped",
171 "Radial Out", "Radial In", "Angular CW", "Angular CCW"
172 };
173
174 2346 static std::vector<std::string_view> fillPalettes() {
175 // TODO: It would be better to have a span of string_views directly in program memory
176 // rather than parsing it from JSON
177 2346 std::vector<std::string_view> palettes;
178
179 2346 auto sv = std::string_view(JSON_palette_names);
180 // Count the number of quotes
181 2346 unsigned quotes = 0;
182
2/2
✓ Branch 0 taken 337824 times.
✓ Branch 1 taken 1508478 times.
1848648 std::for_each(sv.begin(), sv.end(), [&quotes](char c) { if (c == '"') ++quotes; });
183
1/2
✓ Branch 0 taken 2346 times.
✗ Branch 1 not taken.
2346 palettes.reserve(quotes / 2);
184
185 // Walk the list doing a simple parse of strings in quotes
186 2346 auto index = sv.find('"');
187 2346 sv.remove_prefix(index + 1);
188
1/2
✓ Branch 0 taken 168912 times.
✗ Branch 1 not taken.
168912 while (!sv.empty()) {
189 168912 index = sv.find('"');
190
2/4
✓ Branch 0 taken 168912 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 168912 times.
✗ Branch 3 not taken.
168912 palettes.push_back(sv.substr(0, index));
191 168912 index = sv.find('"', index + 1);
192
2/2
✓ Branch 0 taken 2346 times.
✓ Branch 1 taken 166566 times.
168912 if (index == sv.npos)
193 2346 break;
194 166566 sv.remove_prefix(index + 1);
195 }
196 2346 return palettes;
197 ✗ }
198
199 927866 static const std::vector<std::string_view>& PALETTES() {
200
4/8
✓ Branch 0 taken 2346 times.
✓ Branch 1 taken 925520 times.
✓ Branch 2 taken 2346 times.
✗ Branch 3 not taken.
✓ Branch 4 taken 2346 times.
✗ Branch 5 not taken.
✗ Branch 6 not taken.
✗ Branch 7 not taken.
927866 static std::vector<std::string_view> palettes = fillPalettes();
201 927866 return palettes;
202 }
203
204 extern float GetChannelOutputRefreshRate();
205
206 // Re-use the public WLEDArgRole enum for our internal slot-mapping;
207 // keeps the WLEDAPIResponder's view of slot semantics in lockstep with
208 // the per-effect arg layout RawWLEDEffect builds at construction time.
209 using ArgMapping = WLEDArgRole;
210
211 2029290 const char* defaultSliderName(int idx, ArgMapping& m) {
212
8/9
✓ Branch 0 taken 492660 times.
✓ Branch 1 taken 441048 times.
✓ Branch 2 taken 234600 times.
✓ Branch 3 taken 225216 times.
✓ Branch 4 taken 211140 times.
✓ Branch 5 taken 194718 times.
✓ Branch 6 taken 145452 times.
✓ Branch 7 taken 84456 times.
✗ Branch 8 not taken.
2029290 switch (idx) {
213 492660 case 0:
214 492660 m = ArgMapping::Speed;
215 492660 return "Speed";
216 441048 case 1:
217 441048 m = ArgMapping::Intensity;
218 441048 return "Intensity";
219 234600 case 2:
220 234600 m = ArgMapping::Custom1;
221 234600 return "Custom 1";
222 225216 case 3:
223 225216 m = ArgMapping::Custom2;
224 225216 return "Custom 2";
225 211140 case 4:
226 211140 m = ArgMapping::Custom3;
227 211140 return "Custom 3";
228 194718 case 5:
229 194718 m = ArgMapping::Check1;
230 194718 return "Check 1";
231 145452 case 6:
232 145452 m = ArgMapping::Check2;
233 145452 return "Check 2";
234 84456 case 7:
235 84456 m = ArgMapping::Check3;
236 84456 return "Check 3";
237 }
238 ✗ m = ArgMapping::Custom1;
239 ✗ return "Custom";
240 }
241 663918 const char* defaultColorName(int idx, ArgMapping& m, std::string& defVal) {
242
2/2
✓ Branch 0 taken 323748 times.
✓ Branch 1 taken 340170 times.
663918 if (idx == 0) {
243 323748 m = ArgMapping::Color1;
244 323748 defVal = "#FF0000";
245 323748 return "Color 1";
246 }
247
2/2
✓ Branch 0 taken 279174 times.
✓ Branch 1 taken 60996 times.
340170 if (idx == 1) {
248 279174 m = ArgMapping::Color2;
249 279174 defVal = "#0000FF";
250 279174 return "Color 2";
251 }
252 60996 m = ArgMapping::Color3;
253 60996 defVal = "#000000";
254 60996 return "Color 3";
255 }
256
257 class RawWLEDEffect : public WLEDEffect {
258 public:
259 497352 RawWLEDEffect(const std::string& name, const std::string& config, int m) :
260 WLEDEffect(name),
261 497352 mode(m) {
262
6/12
✓ Branch 0 taken 497352 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 497352 times.
✗ Branch 3 not taken.
✓ Branch 4 taken 497352 times.
✗ Branch 5 not taken.
✓ Branch 6 taken 497352 times.
✗ Branch 7 not taken.
✓ Branch 8 taken 497352 times.
✗ Branch 9 not taken.
✓ Branch 10 taken 497352 times.
✗ Branch 11 not taken.
2984112 args.push_back(CommandArg("BufferMapping", "string", "Buffer Mapping").setContentListRange(BUFFERMAPS));
263
1/2
✓ Branch 0 taken 497352 times.
✗ Branch 1 not taken.
497352 argMap.push_back(ArgMapping::Mapping); // always have mapping
264
6/12
✓ Branch 0 taken 497352 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 497352 times.
✗ Branch 3 not taken.
✓ Branch 4 taken 497352 times.
✗ Branch 5 not taken.
✓ Branch 6 taken 497352 times.
✗ Branch 7 not taken.
✓ Branch 8 taken 497352 times.
✗ Branch 9 not taken.
✓ Branch 10 taken 497352 times.
✗ Branch 11 not taken.
2984112 args.push_back(CommandArg("brightness", "range", "Brightness").setRange(0, 255).setDefaultValue("128"));
265
1/2
✓ Branch 0 taken 497352 times.
✗ Branch 1 not taken.
497352 argMap.push_back(ArgMapping::Brightness); // always have brightness
266
267
1/2
✓ Branch 0 taken 497352 times.
✗ Branch 1 not taken.
497352 std::string c = config;
268 497352 size_t t = c.find("@");
269
2/2
✓ Branch 0 taken 495006 times.
✓ Branch 1 taken 2346 times.
497352 if (t != std::string::npos) {
270
1/2
✓ Branch 0 taken 495006 times.
✗ Branch 1 not taken.
495006 c = c.substr(t + 1);
271
1/2
✓ Branch 0 taken 495006 times.
✗ Branch 1 not taken.
495006 std::string sliders = c;
272 495006 t = c.find(";");
273
1/2
✓ Branch 0 taken 495006 times.
✗ Branch 1 not taken.
495006 if (t != std::string::npos) {
274
1/2
✓ Branch 0 taken 495006 times.
✗ Branch 1 not taken.
495006 c = c.substr(t + 1);
275
1/2
✓ Branch 0 taken 495006 times.
✗ Branch 1 not taken.
495006 sliders = sliders.substr(0, t);
276 }
277
1/2
✓ Branch 0 taken 495006 times.
✗ Branch 1 not taken.
495006 std::string pallete = c;
278 495006 t = c.find(";");
279
1/2
✓ Branch 0 taken 495006 times.
✗ Branch 1 not taken.
495006 if (t != std::string::npos) {
280
1/2
✓ Branch 0 taken 495006 times.
✗ Branch 1 not taken.
495006 c = c.substr(t + 1);
281
1/2
✓ Branch 0 taken 495006 times.
✗ Branch 1 not taken.
495006 pallete = pallete.substr(0, t);
282 }
283
1/2
✓ Branch 0 taken 495006 times.
✗ Branch 1 not taken.
495006 std::string palEnable = c;
284 495006 t = c.find(";");
285
2/2
✓ Branch 0 taken 358938 times.
✓ Branch 1 taken 136068 times.
495006 if (t != std::string::npos) {
286
1/2
✓ Branch 0 taken 358938 times.
✗ Branch 1 not taken.
358938 c = c.substr(t + 1);
287
1/2
✓ Branch 0 taken 358938 times.
✗ Branch 1 not taken.
358938 palEnable = palEnable.substr(0, t);
288 }
289
290 495006 int idx = 0;
291 // printf("%s -%s- -%s-\n", name.c_str(), pallete.c_str(), p2.c_str());
292
2/2
✓ Branch 0 taken 2029290 times.
✓ Branch 1 taken 495006 times.
2524296 while (!sliders.empty()) {
293 ArgMapping m;
294
2/4
✓ Branch 0 taken 2029290 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 2029290 times.
✗ Branch 3 not taken.
2198830 std::string sname = defaultSliderName(idx, m);
295
2/2
✓ Branch 0 taken 382398 times.
✓ Branch 1 taken 1646892 times.
2029290 if (sliders[0] == '!') {
296
1/2
✓ Branch 0 taken 382398 times.
✗ Branch 1 not taken.
382398 sliders = sliders.substr(1);
297
5/6
✓ Branch 0 taken 290904 times.
✓ Branch 1 taken 91494 times.
✓ Branch 2 taken 290904 times.
✗ Branch 3 not taken.
✓ Branch 4 taken 290904 times.
✓ Branch 5 taken 91494 times.
382398 if (!sliders.empty() && sliders[0] == ',') {
298
1/2
✓ Branch 0 taken 290904 times.
✗ Branch 1 not taken.
290904 sliders = sliders.substr(1);
299 }
300 } else {
301 1646892 size_t comma = sliders.find(',');
302
2/2
✓ Branch 0 taken 1248072 times.
✓ Branch 1 taken 398820 times.
1646892 if (comma != std::string::npos) {
303
1/2
✓ Branch 0 taken 1248072 times.
✗ Branch 1 not taken.
1248072 sname = sliders.substr(0, comma);
304
1/2
✓ Branch 0 taken 1248072 times.
✗ Branch 1 not taken.
1248072 sliders = sliders.substr(comma + 1);
305 } else {
306
1/2
✓ Branch 0 taken 398820 times.
✗ Branch 1 not taken.
398820 sname = sliders;
307
1/2
✓ Branch 0 taken 398820 times.
✗ Branch 1 not taken.
398820 sliders = "";
308 }
309 }
310 // printf(" s%d: %s\n", idx, sname.c_str());
311
3/4
✓ Branch 0 taken 2029290 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 1628124 times.
✓ Branch 3 taken 401166 times.
2029290 if (sname != "") {
312
2/2
✓ Branch 0 taken 107916 times.
✓ Branch 1 taken 1520208 times.
1628124 if (m == ArgMapping::Custom3) {
313 // custom3 is
314
1/2
✓ Branch 0 taken 107916 times.
✗ Branch 1 not taken.
107916 int i = extractModeDefaults(mode, "c3");
315
2/2
✓ Branch 0 taken 39882 times.
✓ Branch 1 taken 68034 times.
107916 if (i < 0) {
316 39882 i = DEFAULT_C3;
317 }
318
4/8
✓ Branch 0 taken 107916 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 107916 times.
✗ Branch 3 not taken.
✓ Branch 4 taken 107916 times.
✗ Branch 5 not taken.
✓ Branch 6 taken 107916 times.
✗ Branch 7 not taken.
323748 args.push_back(CommandArg(sname, "range", sname).setRange(0, 31).setDefaultValue(std::to_string(i)));
319
3/4
✓ Branch 0 taken 356592 times.
✓ Branch 1 taken 1163616 times.
✓ Branch 2 taken 356592 times.
✗ Branch 3 not taken.
1520208 } else if (m >= ArgMapping::Check1 && m <= ArgMapping::Check3) {
320
1/2
✓ Branch 0 taken 356592 times.
✗ Branch 1 not taken.
356592 std::string dn = "o1";
321
2/2
✓ Branch 0 taken 133722 times.
✓ Branch 1 taken 222870 times.
356592 if (m == ArgMapping::Check2) {
322
1/2
✓ Branch 0 taken 133722 times.
✗ Branch 1 not taken.
133722 dn = "o2";
323
2/2
✓ Branch 0 taken 84456 times.
✓ Branch 1 taken 138414 times.
222870 } else if (m == ArgMapping::Check3) {
324
1/2
✓ Branch 0 taken 84456 times.
✗ Branch 1 not taken.
84456 dn = "o3";
325 }
326
1/2
✓ Branch 0 taken 356592 times.
✗ Branch 1 not taken.
356592 int i = extractModeDefaults(mode, dn.c_str());
327
6/10
✓ Branch 0 taken 356592 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 356592 times.
✗ Branch 3 not taken.
✓ Branch 4 taken 46920 times.
✓ Branch 5 taken 309672 times.
✓ Branch 6 taken 356592 times.
✗ Branch 7 not taken.
✓ Branch 8 taken 356592 times.
✗ Branch 9 not taken.
713184 args.push_back(CommandArg(sname, "bool", sname).setDefaultValue(i > 0 ? "1" : "0"));
328 356592 } else {
329 // speed, intensity, custom1, custom2 are full range
330 1163616 int defValue = 128;
331
2/2
✓ Branch 0 taken 478584 times.
✓ Branch 1 taken 685032 times.
1163616 if (m == ArgMapping::Speed) {
332
1/2
✓ Branch 0 taken 478584 times.
✗ Branch 1 not taken.
478584 defValue = extractModeDefaults(mode, "sx");
333
2/2
✓ Branch 0 taken 429318 times.
✓ Branch 1 taken 255714 times.
685032 } else if (m == ArgMapping::Intensity) {
334
1/2
✓ Branch 0 taken 429318 times.
✗ Branch 1 not taken.
429318 defValue = extractModeDefaults(mode, "ix");
335
2/2
✓ Branch 0 taken 143106 times.
✓ Branch 1 taken 112608 times.
255714 } else if (m == ArgMapping::Custom1) {
336
1/2
✓ Branch 0 taken 143106 times.
✗ Branch 1 not taken.
143106 defValue = extractModeDefaults(mode, "c1");
337
1/2
✓ Branch 0 taken 112608 times.
✗ Branch 1 not taken.
112608 } else if (m == ArgMapping::Custom2) {
338
1/2
✓ Branch 0 taken 112608 times.
✗ Branch 1 not taken.
112608 defValue = extractModeDefaults(mode, "c2");
339 }
340
2/2
✓ Branch 0 taken 797640 times.
✓ Branch 1 taken 365976 times.
1163616 if (defValue < 0) {
341 797640 defValue = 128;
342 }
343
4/8
✓ Branch 0 taken 1163616 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 1163616 times.
✗ Branch 3 not taken.
✓ Branch 4 taken 1163616 times.
✗ Branch 5 not taken.
✓ Branch 6 taken 1163616 times.
✗ Branch 7 not taken.
3490848 args.push_back(CommandArg(sname, "range", sname).setRange(0, 255).setDefaultValue(std::to_string(defValue)));
344 }
345
1/2
✓ Branch 0 taken 1628124 times.
✗ Branch 1 not taken.
1628124 argMap.push_back(m);
346 }
347 2029290 idx++;
348 2029290 }
349
350
3/4
✓ Branch 0 taken 495006 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 462162 times.
✓ Branch 3 taken 32844 times.
495006 if (palEnable == "!") {
351
1/2
✓ Branch 0 taken 462162 times.
✗ Branch 1 not taken.
462162 int i = extractModeDefaults(mode, "pal");
352
2/2
✓ Branch 0 taken 333132 times.
✓ Branch 1 taken 129030 times.
462162 if (i < 0) {
353 333132 i = 0;
354 }
355
10/20
✓ Branch 0 taken 462162 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 462162 times.
✗ Branch 3 not taken.
✓ Branch 4 taken 462162 times.
✗ Branch 5 not taken.
✓ Branch 6 taken 462162 times.
✗ Branch 7 not taken.
✓ Branch 8 taken 462162 times.
✗ Branch 9 not taken.
✓ Branch 10 taken 462162 times.
✗ Branch 11 not taken.
✓ Branch 12 taken 462162 times.
✗ Branch 13 not taken.
✓ Branch 14 taken 462162 times.
✗ Branch 15 not taken.
✓ Branch 16 taken 462162 times.
✗ Branch 17 not taken.
✓ Branch 18 taken 462162 times.
✗ Branch 19 not taken.
2772972 args.push_back(CommandArg("palette", "string", "Palette").setContentListRange(PALETTES()).setDefaultValue(PALETTES().at(i)));
356
1/2
✓ Branch 0 taken 462162 times.
✗ Branch 1 not taken.
462162 argMap.push_back(ArgMapping::Palette); // Palette
357 }
358
2/2
✓ Branch 0 taken 323748 times.
✓ Branch 1 taken 171258 times.
495006 if (!pallete.empty()) {
359 323748 idx = 0;
360
2/2
✓ Branch 0 taken 663918 times.
✓ Branch 1 taken 323748 times.
987666 while (!pallete.empty()) {
361 ArgMapping m;
362 663918 std::string val;
363
2/4
✓ Branch 0 taken 663918 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 663918 times.
✗ Branch 3 not taken.
719386 std::string cname = defaultColorName(idx, m, val);
364
2/2
✓ Branch 0 taken 480930 times.
✓ Branch 1 taken 182988 times.
663918 if (pallete[0] == '!') {
365
1/2
✓ Branch 0 taken 480930 times.
✗ Branch 1 not taken.
480930 pallete = pallete.substr(1);
366
5/6
✓ Branch 0 taken 213486 times.
✓ Branch 1 taken 267444 times.
✓ Branch 2 taken 213486 times.
✗ Branch 3 not taken.
✓ Branch 4 taken 213486 times.
✓ Branch 5 taken 267444 times.
480930 if (!pallete.empty() && pallete[0] == ',') {
367
1/2
✓ Branch 0 taken 213486 times.
✗ Branch 1 not taken.
213486 pallete = pallete.substr(1);
368 }
369 } else {
370 182988 size_t comma = pallete.find(',');
371
2/2
✓ Branch 0 taken 129030 times.
✓ Branch 1 taken 53958 times.
182988 if (comma != std::string::npos) {
372
1/2
✓ Branch 0 taken 129030 times.
✗ Branch 1 not taken.
129030 cname = pallete.substr(0, comma);
373
1/2
✓ Branch 0 taken 129030 times.
✗ Branch 1 not taken.
129030 pallete = pallete.substr(comma + 1);
374 } else {
375
1/2
✓ Branch 0 taken 53958 times.
✗ Branch 1 not taken.
53958 cname = pallete;
376
1/2
✓ Branch 0 taken 53958 times.
✗ Branch 1 not taken.
53958 pallete = "";
377 }
378 }
379 // printf(" p%d: %s %s\n", idx, cname.c_str(), val.c_str());
380
3/4
✓ Branch 0 taken 663918 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 595884 times.
✓ Branch 3 taken 68034 times.
663918 if (cname != "") {
381
5/10
✓ Branch 0 taken 595884 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 595884 times.
✗ Branch 3 not taken.
✓ Branch 4 taken 595884 times.
✗ Branch 5 not taken.
✓ Branch 6 taken 595884 times.
✗ Branch 7 not taken.
✓ Branch 8 taken 595884 times.
✗ Branch 9 not taken.
1241552 args.push_back(CommandArg("color" + std::to_string(idx + 1), "color", cname).setDefaultValue(val));
382
1/2
✓ Branch 0 taken 595884 times.
✗ Branch 1 not taken.
595884 argMap.push_back(m);
383 }
384 663918 idx++;
385 663918 }
386 } else {
387
6/12
✓ Branch 0 taken 171258 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 171258 times.
✗ Branch 3 not taken.
✓ Branch 4 taken 171258 times.
✗ Branch 5 not taken.
✓ Branch 6 taken 171258 times.
✗ Branch 7 not taken.
✓ Branch 8 taken 171258 times.
✗ Branch 9 not taken.
✓ Branch 10 taken 171258 times.
✗ Branch 11 not taken.
1027548 args.push_back(CommandArg("color1", "color", "Color 1").setDefaultValue("#FF0000"));
388
6/12
✓ Branch 0 taken 171258 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 171258 times.
✗ Branch 3 not taken.
✓ Branch 4 taken 171258 times.
✗ Branch 5 not taken.
✓ Branch 6 taken 171258 times.
✗ Branch 7 not taken.
✓ Branch 8 taken 171258 times.
✗ Branch 9 not taken.
✓ Branch 10 taken 171258 times.
✗ Branch 11 not taken.
1027548 args.push_back(CommandArg("color2", "color", "Color 2").setDefaultValue("#0000FF"));
389
6/12
✓ Branch 0 taken 171258 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 171258 times.
✗ Branch 3 not taken.
✓ Branch 4 taken 171258 times.
✗ Branch 5 not taken.
✓ Branch 6 taken 171258 times.
✗ Branch 7 not taken.
✓ Branch 8 taken 171258 times.
✗ Branch 9 not taken.
✓ Branch 10 taken 171258 times.
✗ Branch 11 not taken.
1027548 args.push_back(CommandArg("color3", "color", "Color 3").setDefaultValue("#000000"));
390
1/2
✓ Branch 0 taken 171258 times.
✗ Branch 1 not taken.
171258 argMap.push_back(ArgMapping::Color1); // c1
391
1/2
✓ Branch 0 taken 171258 times.
✗ Branch 1 not taken.
171258 argMap.push_back(ArgMapping::Color2); // c2
392
1/2
✓ Branch 0 taken 171258 times.
✗ Branch 1 not taken.
171258 argMap.push_back(ArgMapping::Color3); // c3
393 }
394 495006 } else {
395
6/12
✓ Branch 0 taken 2346 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 2346 times.
✗ Branch 3 not taken.
✓ Branch 4 taken 2346 times.
✗ Branch 5 not taken.
✓ Branch 6 taken 2346 times.
✗ Branch 7 not taken.
✓ Branch 8 taken 2346 times.
✗ Branch 9 not taken.
✓ Branch 10 taken 2346 times.
✗ Branch 11 not taken.
14076 args.push_back(CommandArg("Speed", "range", "Speed").setRange(0, 255).setDefaultValue("128"));
396
6/12
✓ Branch 0 taken 2346 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 2346 times.
✗ Branch 3 not taken.
✓ Branch 4 taken 2346 times.
✗ Branch 5 not taken.
✓ Branch 6 taken 2346 times.
✗ Branch 7 not taken.
✓ Branch 8 taken 2346 times.
✗ Branch 9 not taken.
✓ Branch 10 taken 2346 times.
✗ Branch 11 not taken.
14076 args.push_back(CommandArg("Intensity", "range", "Intensity").setRange(0, 255).setDefaultValue("128"));
397
1/2
✓ Branch 0 taken 2346 times.
✗ Branch 1 not taken.
2346 argMap.push_back(ArgMapping::Speed); // speed
398
1/2
✓ Branch 0 taken 2346 times.
✗ Branch 1 not taken.
2346 argMap.push_back(ArgMapping::Intensity); // intensity
399
400
8/16
✓ Branch 0 taken 2346 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 2346 times.
✗ Branch 3 not taken.
✓ Branch 4 taken 2346 times.
✗ Branch 5 not taken.
✓ Branch 6 taken 2346 times.
✗ Branch 7 not taken.
✓ Branch 8 taken 2346 times.
✗ Branch 9 not taken.
✓ Branch 10 taken 2346 times.
✗ Branch 11 not taken.
✓ Branch 12 taken 2346 times.
✗ Branch 13 not taken.
✓ Branch 14 taken 2346 times.
✗ Branch 15 not taken.
14076 args.push_back(CommandArg("palette", "string", "Palette").setContentListRange(PALETTES()).setDefaultValue("Default"));
401
6/12
✓ Branch 0 taken 2346 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 2346 times.
✗ Branch 3 not taken.
✓ Branch 4 taken 2346 times.
✗ Branch 5 not taken.
✓ Branch 6 taken 2346 times.
✗ Branch 7 not taken.
✓ Branch 8 taken 2346 times.
✗ Branch 9 not taken.
✓ Branch 10 taken 2346 times.
✗ Branch 11 not taken.
14076 args.push_back(CommandArg("color1", "color", "Color1").setDefaultValue("#FF0000"));
402
6/12
✓ Branch 0 taken 2346 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 2346 times.
✗ Branch 3 not taken.
✓ Branch 4 taken 2346 times.
✗ Branch 5 not taken.
✓ Branch 6 taken 2346 times.
✗ Branch 7 not taken.
✓ Branch 8 taken 2346 times.
✗ Branch 9 not taken.
✓ Branch 10 taken 2346 times.
✗ Branch 11 not taken.
14076 args.push_back(CommandArg("color2", "color", "Color2").setDefaultValue("#0000FF"));
403
6/12
✓ Branch 0 taken 2346 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 2346 times.
✗ Branch 3 not taken.
✓ Branch 4 taken 2346 times.
✗ Branch 5 not taken.
✓ Branch 6 taken 2346 times.
✗ Branch 7 not taken.
✓ Branch 8 taken 2346 times.
✗ Branch 9 not taken.
✓ Branch 10 taken 2346 times.
✗ Branch 11 not taken.
14076 args.push_back(CommandArg("color3", "color", "Color3").setDefaultValue("#000000"));
404
1/2
✓ Branch 0 taken 2346 times.
✗ Branch 1 not taken.
2346 argMap.push_back(ArgMapping::Palette); // Palette
405
1/2
✓ Branch 0 taken 2346 times.
✗ Branch 1 not taken.
2346 argMap.push_back(ArgMapping::Color1); // c1
406
1/2
✓ Branch 0 taken 2346 times.
✗ Branch 1 not taken.
2346 argMap.push_back(ArgMapping::Color2); // c2
407
1/2
✓ Branch 0 taken 2346 times.
✗ Branch 1 not taken.
2346 argMap.push_back(ArgMapping::Color3); // c3
408 }
409
2/2
✓ Branch 0 taken 2346 times.
✓ Branch 1 taken 495006 times.
497352 if (name.find("Text") != std::string::npos) {
410
5/10
✓ Branch 0 taken 2346 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 2346 times.
✗ Branch 3 not taken.
✓ Branch 4 taken 2346 times.
✗ Branch 5 not taken.
✓ Branch 6 taken 2346 times.
✗ Branch 7 not taken.
✓ Branch 8 taken 2346 times.
✗ Branch 9 not taken.
14076 args.push_back(CommandArg("Text", "string", "Text"));
411
1/2
✓ Branch 0 taken 2346 times.
✗ Branch 1 not taken.
2346 argMap.push_back(ArgMapping::Text);
412 }
413 497352 }
414
415 1196 virtual bool apply(PixelOverlayModel* model, const std::string& autoEnable, const std::vector<std::string>& args) override {
416
4/10
✓ Branch 0 taken 1196 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 1196 times.
✗ Branch 3 not taken.
✓ Branch 4 taken 1196 times.
✗ Branch 5 not taken.
✗ Branch 6 not taken.
✓ Branch 7 taken 1196 times.
✗ Branch 8 not taken.
✗ Branch 9 not taken.
1196 model->setRunningEffect(new RawWLEDEffectInternal(model, name, autoEnable, args, mode, argMap), 25);
417 1196 return true;
418 }
419
420 class RawWLEDEffectInternal : public WLEDRunningEffect {
421 public:
422 1196 RawWLEDEffectInternal(PixelOverlayModel* m, const std::string& n, const std::string& ad, const std::vector<std::string>& args, int mode, const std::vector<ArgMapping> am) :
423
2/4
✓ Branch 0 taken 1196 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 1196 times.
✗ Branch 3 not taken.
3588 WLEDRunningEffect(m, n, ad), argMap(am) {
424 1196 int mapping = 0;
425 1196 bool hasC3 = false;
426 1196 int count = args.size();
427
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 1196 times.
1196 if (count > argMap.size()) {
428 ✗ count = argMap.size();
429 }
430
2/2
✓ Branch 0 taken 10375 times.
✓ Branch 1 taken 1196 times.
11571 for (int x = 0; x < count; x++) {
431
15/16
✓ Branch 0 taken 1196 times.
✓ Branch 1 taken 1196 times.
✓ Branch 2 taken 1132 times.
✓ Branch 3 taken 1054 times.
✓ Branch 4 taken 396 times.
✓ Branch 5 taken 253 times.
✓ Branch 6 taken 246 times.
✓ Branch 7 taken 409 times.
✓ Branch 8 taken 365 times.
✓ Branch 9 taken 261 times.
✓ Branch 10 taken 1122 times.
✓ Branch 11 taken 1073 times.
✓ Branch 12 taken 1068 times.
✓ Branch 13 taken 597 times.
✓ Branch 14 taken 7 times.
✗ Branch 15 not taken.
10375 switch (argMap[x]) {
432 1196 case ArgMapping::Mapping:
433
1/2
✓ Branch 0 taken 1196 times.
✗ Branch 1 not taken.
1196 mapping = std::find(BUFFERMAPS.begin(), BUFFERMAPS.end(), std::string_view(args[x])) - BUFFERMAPS.begin();
434
2/2
✓ Branch 0 taken 1160 times.
✓ Branch 1 taken 36 times.
1196 if (mapping >= (int)BUFFERMAPS.size()) {
435 1160 mapping = 0;
436 }
437
1/2
✓ Branch 0 taken 1196 times.
✗ Branch 1 not taken.
1196 mappingName = args[x];
438 1196 break;
439 1196 case ArgMapping::Brightness:
440 1196 brightness = parseInt(args[x]);
441 1196 break;
442 1132 case ArgMapping::Speed:
443 1132 speed = parseInt(args[x]);
444 1132 break;
445 1054 case ArgMapping::Intensity:
446 1054 intensity = parseInt(args[x]);
447 1054 break;
448 396 case ArgMapping::Custom1:
449 396 custom1 = parseInt(args[x]);
450 396 break;
451 253 case ArgMapping::Custom2:
452 253 custom2 = parseInt(args[x]);
453 253 break;
454 246 case ArgMapping::Custom3:
455 246 custom3 = parseInt(args[x]);
456 246 break;
457 409 case ArgMapping::Check1:
458
1/2
✓ Branch 0 taken 409 times.
✗ Branch 1 not taken.
409 check1 = parseBool(args[x]);
459 409 break;
460 365 case ArgMapping::Check2:
461
1/2
✓ Branch 0 taken 365 times.
✗ Branch 1 not taken.
365 check2 = parseBool(args[x]);
462 365 break;
463 261 case ArgMapping::Check3:
464
1/2
✓ Branch 0 taken 261 times.
✗ Branch 1 not taken.
261 check3 = parseBool(args[x]);
465 261 break;
466 1122 case ArgMapping::Palette:
467
1/2
✓ Branch 0 taken 1122 times.
✗ Branch 1 not taken.
1122 palette = args[x];
468 1122 break;
469 1073 case ArgMapping::Color1:
470
1/2
✓ Branch 0 taken 1073 times.
✗ Branch 1 not taken.
1073 color1 = parseColor(args[x]);
471 1073 break;
472 1068 case ArgMapping::Color2:
473
1/2
✓ Branch 0 taken 1068 times.
✗ Branch 1 not taken.
1068 color2 = parseColor(args[x]);
474 1068 break;
475 597 case ArgMapping::Color3:
476 597 hasC3 = true;
477
1/2
✓ Branch 0 taken 597 times.
✗ Branch 1 not taken.
597 color3 = parseColor(args[x]);
478 597 break;
479 7 case ArgMapping::Text:
480
1/2
✓ Branch 0 taken 7 times.
✗ Branch 1 not taken.
7 text = args[x];
481 7 break;
482 ✗ default:
483 ✗ printf("Don't know what to do with %d\n", argMap[x]);
484 ✗ break;
485 }
486 }
487
488 1196 int p = 0;
489
1/2
✓ Branch 0 taken 1196 times.
✗ Branch 1 not taken.
1196 auto& palettes = PALETTES();
490
2/4
✓ Branch 0 taken 1196 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 1196 times.
✗ Branch 3 not taken.
1196 if (auto it = std::find(palettes.begin(), palettes.end(), (std::string_view)palette); it != palettes.end())
491 1196 p = (int)(it - palettes.begin());
492
493
2/2
✓ Branch 0 taken 599 times.
✓ Branch 1 taken 597 times.
1196 if (!hasC3) {
494 599 color3 = color1;
495 }
496 // The constructor pushes and pops itself.
497
2/4
✓ Branch 0 taken 1196 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 1196 times.
✗ Branch 3 not taken.
2392 std::lock_guard<std::recursive_mutex> l(WS2812FXExt::lock());
498
1/4
✗ Branch 0 not taken.
✓ Branch 1 taken 1196 times.
✗ Branch 2 not taken.
✗ Branch 3 not taken.
1196 wled = new WS2812FXExt(m, mapping, brightness,
499 1196 mode, speed, intensity, p,
500 color1, color2, color3,
501 1196 custom1, custom2, custom3,
502 1196 check1, check2, check3, text,
503
3/6
✓ Branch 0 taken 1196 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 1196 times.
✗ Branch 3 not taken.
✓ Branch 4 taken 1196 times.
✗ Branch 5 not taken.
1196 PolarModeFromName(mappingName));
504 1196 }
505 7020 virtual ~RawWLEDEffectInternal() {
506 2340 std::lock_guard<std::recursive_mutex> l(WS2812FXExt::lock());
507
1/2
✓ Branch 0 taken 1170 times.
✗ Branch 1 not taken.
2340 delete wled;
508 4680 }
509
510 4 virtual void toJson(Json::Value& v) const override {
511
3/6
✓ Branch 0 taken 4 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 4 times.
✗ Branch 3 not taken.
✓ Branch 4 taken 4 times.
✗ Branch 5 not taken.
4 v["name"] = name();
512
513
2/2
✓ Branch 0 taken 32 times.
✓ Branch 1 taken 4 times.
36 for (int x = 0; x < argMap.size(); x++) {
514
8/16
✓ Branch 0 taken 4 times.
✓ Branch 1 taken 4 times.
✓ Branch 2 taken 4 times.
✓ Branch 3 taken 4 times.
✗ Branch 4 not taken.
✗ Branch 5 not taken.
✗ Branch 6 not taken.
✗ Branch 7 not taken.
✗ Branch 8 not taken.
✗ Branch 9 not taken.
✓ Branch 10 taken 4 times.
✓ Branch 11 taken 4 times.
✓ Branch 12 taken 4 times.
✓ Branch 13 taken 4 times.
✗ Branch 14 not taken.
✗ Branch 15 not taken.
32 switch (argMap[x]) {
515 4 case ArgMapping::Mapping:
516 4 break;
517 4 case ArgMapping::Brightness:
518
2/4
✓ Branch 0 taken 4 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 4 times.
✗ Branch 3 not taken.
4 v["brightness"] = brightness;
519 4 break;
520 4 case ArgMapping::Speed:
521
2/4
✓ Branch 0 taken 4 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 4 times.
✗ Branch 3 not taken.
4 v["speed"] = speed;
522 4 break;
523 4 case ArgMapping::Intensity:
524
2/4
✓ Branch 0 taken 4 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 4 times.
✗ Branch 3 not taken.
4 v["intensity"] = intensity;
525 4 break;
526 ✗ case ArgMapping::Custom1:
527 ✗ v["custom1"] = custom1;
528 ✗ break;
529 ✗ case ArgMapping::Custom2:
530 ✗ v["custom2"] = custom2;
531 ✗ break;
532 ✗ case ArgMapping::Custom3:
533 ✗ v["custom3"] = custom3;
534 ✗ break;
535 ✗ case ArgMapping::Check1:
536 ✗ v["check1"] = check1;
537 ✗ break;
538 ✗ case ArgMapping::Check2:
539 ✗ v["check2"] = check2;
540 ✗ break;
541 ✗ case ArgMapping::Check3:
542 ✗ v["check3"] = check3;
543 ✗ break;
544 4 case ArgMapping::Palette:
545
2/4
✓ Branch 0 taken 4 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 4 times.
✗ Branch 3 not taken.
4 v["palette"] = palette;
546 4 break;
547 4 case ArgMapping::Color1:
548
2/4
✓ Branch 0 taken 4 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 4 times.
✗ Branch 3 not taken.
4 v["color1"] = color1;
549 4 break;
550 4 case ArgMapping::Color2:
551
2/4
✓ Branch 0 taken 4 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 4 times.
✗ Branch 3 not taken.
4 v["color2"] = color2;
552 4 break;
553 4 case ArgMapping::Color3:
554
2/4
✓ Branch 0 taken 4 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 4 times.
✗ Branch 3 not taken.
4 v["color3"] = color3;
555 4 break;
556 ✗ case ArgMapping::Text:
557 ✗ v["text"] = text;
558 ✗ break;
559 }
560 }
561 4 }
562 8551 virtual int32_t doIteration() override {
563 {
564
2/4
✓ Branch 0 taken 8551 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 8551 times.
✗ Branch 3 not taken.
8551 std::lock_guard<std::recursive_mutex> l(WS2812FXExt::lock());
565
1/2
✓ Branch 0 taken 8551 times.
✗ Branch 1 not taken.
8551 WS2812FXExt::pushCurrent(wled);
566
1/2
✓ Branch 0 taken 8551 times.
✗ Branch 1 not taken.
8551 wled->service();
567
1/2
✓ Branch 0 taken 8551 times.
✗ Branch 1 not taken.
8551 WS2812FXExt::popCurrent();
568 8551 }
569
570 8551 wled->model->flushOverlayBuffer();
571 // no sense updating faster than the output
572 8551 float f = 1000.0f / GetChannelOutputRefreshRate();
573 8551 int i = f;
574 8551 return i;
575 }
576
577 int brightness = 128;
578 int speed = 128;
579 int intensity = 128;
580 uint32_t color1 = 0xFF0000;
581 uint32_t color2 = 0x0000FF;
582 uint32_t color3 = 0x000000;
583 std::string palette = "Default";
584 int custom1 = 128;
585 int custom2 = 128;
586 int custom3 = 128;
587 int check1 = 0;
588 int check2 = 0;
589 int check3 = 0;
590 std::string text;
591 std::string mappingName;
592
593 WS2812FXExt* wled;
594 const std::vector<ArgMapping> argMap;
595 };
596
597 int mode;
598 std::vector<ArgMapping> argMap;
599
600 public:
601 8 std::vector<WLEDArgRole> getArgRoles() const override { return argMap; }
602 };
603
604 // Copy Segment mirrors another segment of the same strip, and FPP gives each
605 // model's effect exactly one segment: whatever its source id, there is
606 // nothing to copy and it can only fade to black. The port keeps the mode
607 // (upstream syncs stay simple); FPP doesn't offer it, so a preset still naming
608 // it is refused as an unknown effect.
609 1022856 static bool isRetiredWLEDMode(int mode) {
610 1022856 return mode == FX_MODE_COPY;
611 }
612
613 4692 static WS2812FX* wledInstance() {
614 4692 WS2812FX* inst = WS2812FXExt::getInstance();
615
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 4692 times.
4692 if (inst == nullptr) {
616 ✗ inst = new WS2812FXExt();
617 }
618 4692 return inst;
619 }
620
621 // FPP's name for WLED mode `x` (its mode data in `ename`), or "" for a
622 // reserved slot.
623 511428 static std::string wledEffectName(WS2812FX* inst, int x, std::string& ename) {
624
1/2
✓ Branch 0 taken 511428 times.
✗ Branch 1 not taken.
511428 std::string name = "WLED - ";
625
1/2
✓ Branch 0 taken 511428 times.
✗ Branch 1 not taken.
511428 ename = inst->getModeData(x);
626
2/2
✓ Branch 0 taken 65688 times.
✓ Branch 1 taken 445740 times.
511428 if (ename.find("si=0") != std::string::npos) {
627 // audio reactive effects, add a note so people know these are special
628
1/2
✓ Branch 0 taken 65688 times.
✗ Branch 1 not taken.
65688 name = "WLED♪ - ";
629 }
630
3/4
✓ Branch 0 taken 511428 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 11730 times.
✓ Branch 3 taken 499698 times.
511428 if (ename == "RSVD") {
631
1/2
✓ Branch 0 taken 11730 times.
✗ Branch 1 not taken.
23460 return "";
632 }
633
2/2
✓ Branch 0 taken 7038 times.
✓ Branch 1 taken 499698 times.
506736 while (ename.find('+') != std::string::npos) {
634 7038 int idx = ename.find('+');
635
4/8
✓ Branch 0 taken 7038 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 7038 times.
✗ Branch 3 not taken.
✓ Branch 4 taken 7038 times.
✗ Branch 5 not taken.
✓ Branch 6 taken 7038 times.
✗ Branch 7 not taken.
7038 ename = ename.substr(0, idx) + "-Plus" + ename.substr(idx + 1);
636 }
637
2/2
✓ Branch 0 taken 497352 times.
✓ Branch 1 taken 2346 times.
499698 if (ename.find('@') != std::string::npos) {
638
2/4
✓ Branch 0 taken 497352 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 497352 times.
✗ Branch 3 not taken.
497352 name += ename.substr(0, ename.find('@'));
639 } else {
640
1/2
✓ Branch 0 taken 2346 times.
✗ Branch 1 not taken.
2346 name += ename;
641 }
642 499698 return name;
643 511428 }
644
645 2346 std::list<PixelOverlayEffect*> WLEDEffect::getWLEDEffects() {
646 2346 std::list<PixelOverlayEffect*> v;
647
4/10
✓ Branch 0 taken 2346 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 2346 times.
✗ Branch 3 not taken.
✓ Branch 4 taken 2346 times.
✗ Branch 5 not taken.
✗ Branch 6 not taken.
✓ Branch 7 taken 2346 times.
✗ Branch 8 not taken.
✗ Branch 9 not taken.
2346 v.push_back(new BlinkEffect());
648
649
1/2
✓ Branch 0 taken 2346 times.
✗ Branch 1 not taken.
2346 WS2812FX* inst = wledInstance();
650 2346 int i = inst->getModeCount();
651
2/2
✓ Branch 0 taken 511428 times.
✓ Branch 1 taken 2346 times.
513774 for (int x = 2; x < i; x++) {
652
2/2
✓ Branch 0 taken 2346 times.
✓ Branch 1 taken 509082 times.
511428 if (isRetiredWLEDMode(x)) {
653 2346 continue;
654 }
655 509082 std::string ename;
656
1/2
✓ Branch 0 taken 509082 times.
✗ Branch 1 not taken.
509082 std::string name = wledEffectName(inst, x, ename);
657
3/4
✓ Branch 0 taken 509082 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 497352 times.
✓ Branch 3 taken 11730 times.
509082 if (name != "") {
658
4/10
✓ Branch 0 taken 497352 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 497352 times.
✗ Branch 3 not taken.
✓ Branch 4 taken 497352 times.
✗ Branch 5 not taken.
✗ Branch 6 not taken.
✓ Branch 7 taken 497352 times.
✗ Branch 8 not taken.
✗ Branch 9 not taken.
497352 v.push_back(new RawWLEDEffect(name, ename, x));
659 }
660 509082 }
661 2346 return v;
662 ✗ }
663
664 2346 std::list<std::string> WLEDEffect::getRetiredWLEDEffectNames() {
665 2346 std::list<std::string> v;
666
1/2
✓ Branch 0 taken 2346 times.
✗ Branch 1 not taken.
2346 WS2812FX* inst = wledInstance();
667 2346 int i = inst->getModeCount();
668
2/2
✓ Branch 0 taken 511428 times.
✓ Branch 1 taken 2346 times.
513774 for (int x = 2; x < i; x++) {
669
2/2
✓ Branch 0 taken 2346 times.
✓ Branch 1 taken 509082 times.
511428 if (isRetiredWLEDMode(x)) {
670 2346 std::string ename;
671
1/2
✓ Branch 0 taken 2346 times.
✗ Branch 1 not taken.
2346 std::string name = wledEffectName(inst, x, ename);
672
2/4
✓ Branch 0 taken 2346 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 2346 times.
✗ Branch 3 not taken.
2346 if (name != "") {
673
1/2
✓ Branch 0 taken 2346 times.
✗ Branch 1 not taken.
2346 v.push_back(name);
674 }
675 2346 }
676 }
677 2346 return v;
678 ✗ }
679 458 void WLEDEffect::cleanupWLEDEffects() {
680 458 WS2812FXExt::clearInstance();
681 458 }
682