FastLED 3.9.15
Loading...
Searching...
No Matches

◆ loop()

void loop ( )

Definition at line 214 of file Chromancer.ino.

214 {
215 unsigned long benchmark = millis();
216 net_loop();
217
218
219
220 // Fade all dots to create trails
221 for (int strip = 0; strip < 40; strip++) {
222 for (int led = 0; led < 14; led++) {
223 for (int i = 0; i < 3; i++) {
224 ledColors[strip][led][i] *= sliderDecay.value();
225 }
226 }
227 }
228
229 for (int i = 0; i < numberOfRipples; i++) {
230 ripples[i].advance(ledColors);
231 }
232
233 for (int segment = 0; segment < 40; segment++) {
234 for (int fromBottom = 0; fromBottom < 14; fromBottom++) {
235 int strip = ledAssignments[segment][0];
236 int led = round(fmap(fromBottom, 0, 13, ledAssignments[segment][2],
237 ledAssignments[segment][1]));
238 leds[strip][led] = CRGB(ledColors[segment][fromBottom][0],
239 ledColors[segment][fromBottom][1],
240 ledColors[segment][fromBottom][2]);
241 }
242 }
243
244 if (allWhite) {
245 // for all strips
246 for (int i = 0; i < 4; i++) {
247 for (int j = 0; j < lengths[i]; j++) {
248 leds[i][j] = CRGB::White;
249 }
250 }
251 }
252
253 FastLED.show();
254
255
256 // Check if buttons were clicked
262
263 if (wasSpiralClicked) {
264 // Trigger spiral wave effect from center
265 unsigned int baseColor = random(0xFFFF);
266 byte centerNode = 15; // Center node
267
268 // Create 6 ripples in a spiral pattern
269 for (int i = 0; i < 6; i++) {
270 if (nodeConnections[centerNode][i] >= 0) {
271 for (int j = 0; j < numberOfRipples; j++) {
272 if (ripples[j].state == dead) {
273 ripples[j].start(
274 centerNode, i,
276 baseColor + (0xFFFF / 6) * i, 255, 255),
277 0.3 + (i * 0.1), // Varying speeds creates spiral effect
278 2000,
279 i % 2 ? alwaysTurnsLeft : alwaysTurnsRight); // Alternating turn directions
280 break;
281 }
282 }
283 }
284 }
285 lastHeartbeat = millis();
286 }
287
289 // Trigger immediate border wave effect
290 unsigned int baseColor = random(0xFFFF);
291
292 // Start ripples from each border node in sequence
293 for (int i = 0; i < numberOfBorderNodes; i++) {
294 byte node = borderNodes[i];
295 // Find an inward direction
296 for (int dir = 0; dir < 6; dir++) {
297 if (nodeConnections[node][dir] >= 0 &&
298 !isNodeOnBorder(nodeConnections[node][dir])) {
299 for (int j = 0; j < numberOfRipples; j++) {
300 if (ripples[j].state == dead) {
301 ripples[j].start(
302 node, dir,
304 baseColor + (0xFFFF / numberOfBorderNodes) * i,
305 255, 255),
306 .4, 2000, 0);
307 break;
308 }
309 }
310 break;
311 }
312 }
313 }
314 lastHeartbeat = millis();
315 }
316
318 // Trigger immediate rainbow cube effect
319 int node = cubeNodes[random(numberOfCubeNodes)];
320 unsigned int baseColor = random(0xFFFF);
321 byte behavior = random(2) ? alwaysTurnsLeft : alwaysTurnsRight;
322
323 for (int i = 0; i < 6; i++) {
324 if (nodeConnections[node][i] >= 0) {
325 for (int j = 0; j < numberOfRipples; j++) {
326 if (ripples[j].state == dead) {
327 ripples[j].start(
328 node, i,
330 baseColor + (0xFFFF / 6) * i, 255, 255),
331 .5, 2000, behavior);
332 break;
333 }
334 }
335 }
336 }
337 lastHeartbeat = millis();
338 }
339
341 // Trigger immediate starburst effect
342 unsigned int baseColor = random(0xFFFF);
343 byte behavior = random(2) ? alwaysTurnsLeft : alwaysTurnsRight;
344
345 for (int i = 0; i < 6; i++) {
346 for (int j = 0; j < numberOfRipples; j++) {
347 if (ripples[j].state == dead) {
348 ripples[j].start(
349 starburstNode, i,
351 baseColor + (0xFFFF / 6) * i, 255, 255),
352 .65, 1500, behavior);
353 break;
354 }
355 }
356 }
357 lastHeartbeat = millis();
358 }
359
361 // Trigger immediate heartbeat effect
362 for (int i = 0; i < 6; i++) {
363 for (int j = 0; j < numberOfRipples; j++) {
364 if (ripples[j].state == dead) {
365 ripples[j].start(15, i, 0xEE1111,
366 float(random(100)) / 100.0 * .1 + .4, 1000, 0);
367 break;
368 }
369 }
370 }
371 lastHeartbeat = millis();
372 }
373
374 if (millis() - lastHeartbeat >= autoPulseTimeout) {
375 // When biometric data is unavailable, visualize at random
377 millis() - lastRandomPulse >= randomPulseTime) {
378 unsigned int baseColor = random(0xFFFF);
379
380 if (currentAutoPulseType == 255 ||
383 byte possiblePulse = 255;
384 while (true) {
385 possiblePulse = random(3);
386
387 if (possiblePulse == currentAutoPulseType)
388 continue;
389
390 switch (possiblePulse) {
391 case 0:
393 continue;
394 break;
395
396 case 1:
398 continue;
399 break;
400
401 case 2:
403 continue;
404 break;
405
406 default:
407 continue;
408 }
409
410 currentAutoPulseType = possiblePulse;
411 lastAutoPulseChange = millis();
412 break;
413 }
414 }
415
416 switch (currentAutoPulseType) {
417 case 0: {
418 int node = 0;
419 bool foundStartingNode = false;
420 while (!foundStartingNode) {
421 node = random(25);
422 foundStartingNode = true;
423 for (int i = 0; i < numberOfBorderNodes; i++) {
424 // Don't fire a pulse on one of the outer nodes - it
425 // looks boring
426 if (node == borderNodes[i])
427 foundStartingNode = false;
428 }
429
430 if (node == lastAutoPulseNode)
431 foundStartingNode = false;
432 }
433
434 lastAutoPulseNode = node;
435
436 for (int i = 0; i < 6; i++) {
437 if (nodeConnections[node][i] >= 0) {
438 for (int j = 0; j < numberOfRipples; j++) {
439 if (ripples[j].state == dead) {
440 ripples[j].start(
441 node, i,
442 // strip0.ColorHSV(baseColor
443 // + (0xFFFF / 6) * i,
444 // 255, 255),
445 Adafruit_DotStar_ColorHSV(baseColor, 255,
446 255),
447 float(random(100)) / 100.0 * .2 + .5, 3000,
448 1);
449
450 break;
451 }
452 }
453 }
454 }
455 break;
456 }
457
458 case 1: {
459 int node = cubeNodes[random(numberOfCubeNodes)];
460
461 while (node == lastAutoPulseNode)
462 node = cubeNodes[random(numberOfCubeNodes)];
463
464 lastAutoPulseNode = node;
465
466 byte behavior = random(2) ? alwaysTurnsLeft : alwaysTurnsRight;
467
468 for (int i = 0; i < 6; i++) {
469 if (nodeConnections[node][i] >= 0) {
470 for (int j = 0; j < numberOfRipples; j++) {
471 if (ripples[j].state == dead) {
472 ripples[j].start(
473 node, i,
474 // strip0.ColorHSV(baseColor
475 // + (0xFFFF / 6) * i,
476 // 255, 255),
477 Adafruit_DotStar_ColorHSV(baseColor, 255,
478 255),
479 .5, 2000, behavior);
480
481 break;
482 }
483 }
484 }
485 }
486 break;
487 }
488
489 case 2: {
490 byte behavior = random(2) ? alwaysTurnsLeft : alwaysTurnsRight;
491
493
494 for (int i = 0; i < 6; i++) {
495 for (int j = 0; j < numberOfRipples; j++) {
496 if (ripples[j].state == dead) {
497 ripples[j].start(
498 starburstNode, i,
500 baseColor + (0xFFFF / 6) * i, 255, 255),
501 .65, 1500, behavior);
502
503 break;
504 }
505 }
506 }
507 break;
508 }
509
510 default:
511 break;
512 }
513 lastRandomPulse = millis();
514 }
515
517 // Simulated heartbeat
518 if (millis() >= nextSimulatedHeartbeat) {
519 for (int i = 0; i < 6; i++) {
520 for (int j = 0; j < numberOfRipples; j++) {
521 if (ripples[j].state == dead) {
522 ripples[j].start(
523 15, i, 0xEE1111,
524 float(random(100)) / 100.0 * .1 + .4, 1000, 0);
525
526 break;
527 }
528 }
529 }
530
533 }
534
535 // Simulated EDA ripples
536 if (millis() >= nextSimulatedEda) {
537 for (int i = 0; i < 10; i++) {
538 for (int j = 0; j < numberOfRipples; j++) {
539 if (ripples[j].state == dead) {
540 byte targetNode =
542 byte direction = 255;
543
544 while (direction == 255) {
545 direction = random(6);
546 if (nodeConnections[targetNode][direction] < 0)
547 direction = 255;
548 }
549
550 ripples[j].start(
551 targetNode, direction, 0x1111EE,
552 float(random(100)) / 100.0 * .5 + 2, 300, 2);
553
554 break;
555 }
556 }
557 }
558
560 random(simulatedEdaVariance);
561 }
562 }
563 }
564
565 // Serial.print("Benchmark: ");
566 // Serial.println(millis() - benchmark);
567}
CRGB leds[NUM_LEDS]
Definition Apa102.ino:11
byte currentAutoPulseType
#define simulatedHeartbeatBaseTime
bool isNodeOnBorder(byte node)
UICheckbox allWhite("All White", false)
bool wasStarburstClicked
UISlider sliderDecay("decay",.97f,.8, 1.0,.01)
bool wasRainbowCubeClicked
byte lastAutoPulseNode
unsigned long nextSimulatedHeartbeat
byte ledColors[40][14][3]
unsigned long lastAutoPulseChange
UICheckbox simulatedBiometricsEnabled("Simulated Biometrics", true)
unsigned long lastRandomPulse
#define simulatedEdaBaseTime
UIButton triggerBorderWave("Border Wave")
#define simulatedEdaVariance
bool wasSpiralClicked
#define randomPulsesEnabled
UIButton triggerSpiral("Spiral Wave")
constexpr int lengths[]
unsigned long lastHeartbeat
#define autoPulseTimeout
UICheckbox starburstPulsesEnabled("Starburst Pulses", true)
bool wasHeartbeatClicked
UIButton simulatedHeartbeat("Simulated Heartbeat")
UIButton triggerStarburst("Trigger Starburst")
#define simulatedHeartbeatVariance
#define randomPulseTime
bool wasBorderWaveClicked
UIButton triggerRainbowCube("Rainbow Cube")
#define numberOfRipples
#define autoPulseChangeTime
unsigned long nextSimulatedEda
byte numberOfAutoPulseTypes
Ripple ripples[numberOfRipples]
#define cubePulsesEnabled
CFastLED FastLED
Global LED strip management instance.
Definition FastLED.cpp:58
uint32_t Adafruit_DotStar_ColorHSV(uint16_t hue, uint8_t sat, uint8_t val)
Definition detail.h:6
int starburstNode
Definition mapping.h:156
int numberOfCubeNodes
Definition mapping.h:152
int nodeConnections[25][6]
Definition mapping.h:15
int ledAssignments[40][3]
Definition mapping.h:95
int numberOfBorderNodes
Definition mapping.h:147
int borderNodes[]
Definition mapping.h:148
int cubeNodes[]
Definition mapping.h:153
void net_loop()
Definition net.h:159
@ dead
Definition ripple.h:17
@ alwaysTurnsRight
Definition ripple.h:27
@ alwaysTurnsLeft
Definition ripple.h:28
float fmap(float x, float in_min, float in_max, float out_min, float out_max)
Definition ripple.h:31
@ White
<div style='background:#FFFFFF;width:4em;height:4em;'></div>
Definition crgb.h:635
Representation of an RGB pixel (Red, Green, Blue)
Definition crgb.h:54
#define round(x)
Definition util.h:10

References Adafruit_DotStar_ColorHSV(), allWhite, alwaysTurnsLeft, alwaysTurnsRight, autoPulseChangeTime, autoPulseTimeout, borderNodes, cubeNodes, cubePulsesEnabled, currentAutoPulseType, dead, FastLED, fmap(), isNodeOnBorder(), lastAutoPulseChange, lastAutoPulseNode, lastHeartbeat, lastRandomPulse, ledAssignments, ledColors, leds, lengths, net_loop(), nextSimulatedEda, nextSimulatedHeartbeat, nodeConnections, numberOfAutoPulseTypes, numberOfBorderNodes, numberOfCubeNodes, numberOfRipples, randomPulsesEnabled, randomPulseTime, ripples, round, simulatedBiometricsEnabled, simulatedEdaBaseTime, simulatedEdaVariance, simulatedHeartbeat, simulatedHeartbeatBaseTime, simulatedHeartbeatVariance, sliderDecay, starburstNode, starburstPulsesEnabled, triggerBorderWave, triggerRainbowCube, triggerSpiral, triggerStarburst, wasBorderWaveClicked, wasHeartbeatClicked, wasRainbowCubeClicked, wasSpiralClicked, wasStarburstClicked, and CRGB::White.

+ Here is the call graph for this function: