Skip to content

Commit

Permalink
Merge branch 'projection-classes'
Browse files Browse the repository at this point in the history
  • Loading branch information
ewoudwijma committed Jun 22, 2024
2 parents 1b66834 + 4322c3e commit bdfc44f
Show file tree
Hide file tree
Showing 9 changed files with 349 additions and 182 deletions.
2 changes: 1 addition & 1 deletion platformio.ini
Original file line number Diff line number Diff line change
Expand Up @@ -52,7 +52,7 @@ lib_deps =
build_flags =
; -D APP=StarBase
-D PIOENV=$PIOENV
-D VERSION=24062111 ; Date and time (GMT!), update at every commit!!
-D VERSION=24062218 ; Date and time (GMT!), update at every commit!!
-D CONFIG_ASYNC_TCP_USE_WDT=0
-D LFS_THREADSAFE ; enables use of semaphores in LittleFS driver
-D STARBASE_DEVMODE
Expand Down
18 changes: 9 additions & 9 deletions src/App/LedEffects.h
Original file line number Diff line number Diff line change
Expand Up @@ -1265,7 +1265,7 @@ class ScrollingText: public Effect {
// tbd: this should be removed and fx.changeFUn (setEffect) must make sure this cannot happen!!
if (text && strlen(text)>0) {
leds.fadeToBlackBy();
leds.drawText(text, 0, 0, font, CRGB::Red, - (sys->now/25*speed/256));
leds.drawText(text, 0, 0, font, CRGB::Red, - (sys->now/25*speed/256)); //instead of call
}

}
Expand Down Expand Up @@ -1375,13 +1375,13 @@ class GameOfLife: public Effect {
for (int i = 0; i < 5; i++) {
int nx = x + pattern[i][0];
int ny = y + pattern[i][1];
if (getBitValue(futureCells, leds.XYZNoSpin({nx, ny, z}))) {canPlace = false; break;}
if (getBitValue(futureCells, leds.XYZUnprojected({nx, ny, z}))) {canPlace = false; break;}
}
if (canPlace || attempts == 99) {
for (int i = 0; i < 5; i++) {
int nx = x + pattern[i][0];
int ny = y + pattern[i][1];
setBitValue(futureCells, leds.XYZNoSpin({nx, ny, z}), true);
setBitValue(futureCells, leds.XYZUnprojected({nx, ny, z}), true);
leds.setPixelColor({nx, ny, z}, colorByAge ? CRGB::Green : color, 0);
}
return;
Expand Down Expand Up @@ -1432,9 +1432,9 @@ class GameOfLife: public Effect {
// Setup Grid
memset(cells, 0, dataSize);
for (int x = 0; x < leds.size.x; x++) for (int y = 0; y < leds.size.y; y++) for (int z = 0; z < leds.size.z; z++){
if (leds.projectionDimension == _3D && !leds.isMapped(leds.XYZNoSpin({x,y,z}))) continue;
if (leds.projectionDimension == _3D && !leds.isMapped(leds.XYZUnprojected({x,y,z}))) continue;
if (random8(100) < lifeChance) {
setBitValue(cells, leds.XYZNoSpin({x,y,z}), true);
setBitValue(cells, leds.XYZUnprojected({x,y,z}), true);
leds.setPixelColor({x,y,z}, colorByAge ? CRGB::Green : ColorFromPalette(leds.palette, random8()), 0);
}
else leds.setPixelColor({x,y,z}, bgColor, 0);
Expand Down Expand Up @@ -1465,8 +1465,8 @@ class GameOfLife: public Effect {
if (paletteChanged) *prevPalette = ColorFromPalette(leds.palette, 0);
// Redraw Loop
for (int x = 0; x < leds.size.x; x++) for (int y = 0; y < leds.size.y; y++) for (int z = 0; z < leds.size.z; z++){
if (!leds.isMapped(leds.XYZNoSpin({x,y,z}))) continue;
bool alive = getBitValue(cells, leds.XYZNoSpin({x,y,z}));
if (!leds.isMapped(leds.XYZUnprojected({x,y,z}))) continue;
bool alive = getBitValue(cells, leds.XYZUnprojected({x,y,z}));
if (alive) aliveCount++; else deadCount++;
// Redraw alive if palette changed or overlay1
if (alive && paletteChanged) leds.setPixelColor({x,y,z}, ColorFromPalette(leds.palette, random8()), 0); // Random color if palette changed
Expand Down Expand Up @@ -1511,7 +1511,7 @@ class GameOfLife: public Effect {
//Loop through all cells. Count neighbors, apply rules, setPixel
for (int x = 0; x < leds.size.x; x++) for (int y = 0; y < leds.size.y; y++) for (int z = 0; z < leds.size.z; z++){
Coord3D cPos = {x, y, z}; //current cells position
uint16_t cIndex = leds.XYZNoSpin(cPos);
uint16_t cIndex = leds.XYZUnprojected(cPos);
if (leds.projectionDimension == _3D && !leds.isMapped(leds.XYZ(x,y,z))) continue; //skip if not physical led
byte neighbors = 0;
byte colorCount = 0; //track number of valid colors
Expand All @@ -1526,7 +1526,7 @@ class GameOfLife: public Effect {
if (k != 0) continue; //no z axis (wrap around only for x and y
nPos = (nPos + leds.size) % leds.size;
}
uint16_t nIndex = leds.XYZNoSpin(nPos);
uint16_t nIndex = leds.XYZUnprojected(nPos);
// count neighbors and store up to 9 neighbor colors
if (getBitValue(cells, nIndex)) { //if alive
neighbors++;
Expand Down
59 changes: 18 additions & 41 deletions src/App/LedFixture.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -102,27 +102,12 @@ void Fixture::projectAndMap() {
if (sizeAdjusted.y > 1) leds->projectionDimension++;
if (sizeAdjusted.z > 1) leds->projectionDimension++;

Coord3D proCenter;
if (leds->projectionNr == p_DistanceFromPoint || leds->projectionNr == p_Preset1) {
proCenter = mdl->getValue("proCenter", rowNr);
}
else
proCenter = Coord3D{0,0,0};

Coord3D mirrors = Coord3D{0,0,0}; // no mirrors
if (leds->projectionNr == p_Multiply || leds->projectionNr == p_Preset1) {
Coord3D proMulti;
proMulti = mdl->getValue("proMulti", rowNr);
//promultu can be 0,0,0 but /= protects from /div0
sizeAdjusted /= proMulti; sizeAdjusted = sizeAdjusted.maximum(Coord3D{1,1,1}); //size min 1,1,1
proCenter /= proMulti;
mirrors = pixelAdjusted / sizeAdjusted; //place the pixel in the right quadrant
pixelAdjusted = pixelAdjusted%sizeAdjusted; // pixel % size
// ppf("Multiply %d,%d,%d\n", leds->size.x, leds->size.y, leds->size.z);
}
bool mirror = mdl->getValue("mirror", rowNr);
Projection *projection = projections[leds->projectionNr];
mdl->getValueRowNr = rowNr; //run projection functions in the right rowNr context

Coord3D proCenter = mdl->getValue("proCenter", rowNr);

// ppf("projectionNr p:%d f:%d s:%d, %d-%d-%d %d-%d-%d %d-%d-%d\n", leds->projectionNr, leds->effectDimension, leds->projectionDimension, x, y, z, uint16CollectList[0], uint16CollectList[1], uint16CollectList[2], size.x, size.y, size.z);
projection->adjustSizeAndPixel(sizeAdjusted, pixelAdjusted, proCenter);

if (leds->size == Coord3D{0,0,0}) { // first
ppf("projectAndMap first leds[%d] size:%d,%d,%d s:%d,%d,%d e:%d,%d,%d\n", rowNr, sizeAdjusted.x, sizeAdjusted.y, sizeAdjusted.z, startPosAdjusted.x, startPosAdjusted.y, startPosAdjusted.z, endPosAdjusted.x, endPosAdjusted.y, endPosAdjusted.z);
Expand All @@ -142,18 +127,13 @@ void Fixture::projectAndMap() {

mapped = pixelAdjusted;

// if mirrored find the indexV of the mirrored pixel
if (mirror) {
if (mirrors.x %2 != 0) mapped.x = sizeAdjusted.x - 1 - mapped.x;
if (mirrors.y %2 != 0) mapped.y = sizeAdjusted.y - 1 - mapped.y;
if (mirrors.z %2 != 0) mapped.z = sizeAdjusted.z - 1 - mapped.z;
}
projection->adjustMapped(mapped, sizeAdjusted, (pixel - startPosAdjusted)/10);

mapped.x = mapped.distance(proCenter);
mapped.y = 0;
mapped.z = 0;

indexV = leds->XYZNoSpin(mapped);
indexV = leds->XYZUnprojected(mapped);
break;
case _2D: //effectDimension
switch(leds->projectionDimension) {
Expand Down Expand Up @@ -205,12 +185,9 @@ void Fixture::projectAndMap() {
break;
}

if (mirror) {
if (mirrors.x %2 != 0) mapped.x = sizeAdjusted.x - 1 - mapped.x;
if (mirrors.y %2 != 0) mapped.y = sizeAdjusted.y - 1 - mapped.y;
if (mirrors.z %2 != 0) mapped.z = sizeAdjusted.z - 1 - mapped.z;
}
indexV = leds->XYZNoSpin(mapped);
projection->adjustMapped(mapped, sizeAdjusted, (pixel - startPosAdjusted)/10);

indexV = leds->XYZUnprojected(mapped);
break;
case _3D: //effectDimension
mapped = pixelAdjusted;
Expand Down Expand Up @@ -238,12 +215,10 @@ void Fixture::projectAndMap() {
}
break;
}
if (mirror) {
if (mirrors.x %2 != 0) mapped.x = sizeAdjusted.x - 1 - mapped.x;
if (mirrors.y %2 != 0) mapped.y = sizeAdjusted.y - 1 - mapped.y;
if (mirrors.z %2 != 0) mapped.z = sizeAdjusted.z - 1 - mapped.z;
}
indexV = leds->XYZNoSpin(mapped);

projection->adjustMapped(mapped, sizeAdjusted, (pixel - startPosAdjusted)/10);

indexV = leds->XYZUnprojected(mapped);

break; //effectDimension _3D
} //effectDimension
Expand Down Expand Up @@ -329,10 +304,12 @@ void Fixture::projectAndMap() {
} //indexV not too high
} //indexV

mdl->getValueRowNr = UINT8_MAX; // end of run projection functions in the right rowNr context

} //if x,y,z between start and endpos
} //leds->doMap
} //if leds->doMap
rowNr++;
} //listOfLeds
} //for listOfLeds
indexP++; //also increase if no buffer created
} //if 1D-3D pixel

Expand Down
18 changes: 18 additions & 0 deletions src/App/LedFixture.h
Original file line number Diff line number Diff line change
Expand Up @@ -24,6 +24,22 @@

class Leds; //forward

class Projection {
public:
virtual const char * name() {return "noname";}
virtual const char * tags() {return "";}
virtual uint8_t dim() {return _1D;};

virtual void adjustSizeAndPixel(Coord3D &sizeAdjusted, Coord3D &pixelAdjusted, Coord3D &proCenter) {}

virtual void adjustMapped(Coord3D &mapped, Coord3D sizeAdjusted, Coord3D pixelAdjusted) {}

virtual void adjustXYZ(Leds &leds, Coord3D &pixel) {}

virtual void controls(Leds &leds, JsonObject parentVar) {}

};

class Fixture {

public:
Expand All @@ -39,6 +55,8 @@ class Fixture {
// leds = (CRGB*)malloc(nrOfLeds * sizeof(CRGB));
// leds = (CRGB*)reallocarray

std::vector<Projection *> projections;

unsigned16 nrOfLeds = 64; //amount of physical leds
unsigned8 fixtureNr = -1;
Coord3D fixSize = {8,8,1};
Expand Down
35 changes: 9 additions & 26 deletions src/App/LedLeds.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -10,7 +10,7 @@
*/

#include "LedLeds.h"
#include "../Sys/SysModSystem.h"
#include "../Sys/SysModSystem.h" //for sys->now
#ifdef STARBASE_USERMOD_MPU6050
#include "../User/UserModMPU6050.h"
#endif
Expand All @@ -26,32 +26,15 @@ void fastled_fill_rainbow(struct CRGB * targetArray, int numToFill, unsigned8 in
fill_rainbow(targetArray, numToFill, initialhue, deltahue);
}

unsigned16 Leds::XYZ(unsigned16 x, unsigned16 y, unsigned16 z) {
if (projectionNr == p_TiltPanRoll || projectionNr == p_Preset1) {
Coord3D result = Coord3D{x, y, z};
unsigned16 Leds::XYZ(Coord3D pixel) {

#ifdef STARBASE_USERMOD_MPU6050
if (proGyro) {
result = trigoTiltPanRoll.tilt(result, size/2, mpu6050->gyro.x);
result = trigoTiltPanRoll.pan(result, size/2, mpu6050->gyro.y);
result = trigoTiltPanRoll.roll(result, size/2, mpu6050->gyro.z);
}
else
#endif
{
if (proTiltSpeed) result = trigoTiltPanRoll.tilt(result, size/2, sys->now * 5 / (255 - proTiltSpeed));
if (proPanSpeed) result = trigoTiltPanRoll.pan(result, size/2, sys->now * 5 / (255 - proPanSpeed));
if (proRollSpeed) result = trigoTiltPanRoll.roll(result, size/2, sys->now * 5 / (255 - proRollSpeed));
}
//as this is a call to a virtual function it reduces the theoretical (no show) speed by half, even if XYZ is not implemented
// the real speed is hardly affected, but room for improvement!
// so as a workaround we list them here explicetly
if (projectionNr == p_TiltPanRoll || projectionNr == p_Preset1)
fixture->projections[projectionNr]->adjustXYZ(*this, pixel);

if (fixture->fixSize.z == 1) result.z = 0; // 3d effects will be flattened on 2D fixtures
if (result >= 0 && result < size)
return result.x + result.y * size.x + result.z * size.x * size.y;
else
return UINT16_MAX;
}
else
return x + y * size.x + z * size.x * size.y;
return XYZUnprojected(pixel);
}

// maps the virtual led to the physical led(s) and assign a color to it
Expand All @@ -70,7 +53,7 @@ void Leds::setPixelColor(unsigned16 indexV, CRGB color, unsigned8 blendAmount) {
}
}
else if (indexV < NUM_LEDS_Max) //no projection
fixture->ledsP[projectionNr==p_Random?random(fixture->nrOfLeds):indexV] = color;
fixture->ledsP[(projectionNr == p_Random)?random(fixture->nrOfLeds):indexV] = color;
else if (indexV != UINT16_MAX) //assuming UINT16_MAX is set explicitly (e.g. in XYZ)
ppf(" dev sPC V:%d >= %d", indexV, NUM_LEDS_Max);
}
Expand Down
20 changes: 11 additions & 9 deletions src/App/LedLeds.h
Original file line number Diff line number Diff line change
Expand Up @@ -32,12 +32,12 @@

enum ProjectionsE
{
p_None,
p_Default,
p_Multiply,
p_TiltPanRoll,
p_DistanceFromPoint,
p_Preset1,
p_None,
p_Random,
p_Reverse,
p_Mirror,
Expand Down Expand Up @@ -140,6 +140,7 @@ class SharedData {
index = 0;
}

//sets the sharedData pointer back to 0 so loop effect can go through it
void loop() {
index = 0;
}
Expand Down Expand Up @@ -239,11 +240,9 @@ struct PhysMap {
//dev new indexes 894 type:88,122,254,63 p:0x3ffe7a58
if (!isMultipleIndexes()) //check if pointer is not setting the type[3] value
ppf("dev new PhysMap type:%d t3:%d b:%d p:%p\n", type, type[3], type[3] & 0x80, indexes);

if (isMultipleIndexes()) {
else {
indexes->push_back(oldIndex); //add the old to the indexes vector
}

}

if (isMultipleIndexes()) {
Expand Down Expand Up @@ -290,15 +289,18 @@ class Leds {
return XYZ(x, y, 0);
}

unsigned16 XYZNoSpin(Coord3D coord) {
return coord.x + coord.y * size.x + coord.z * size.x * size.y;
unsigned16 XYZUnprojected(Coord3D pixel) {
if (pixel >= 0 && pixel < size)
return pixel.x + pixel.y * size.x + pixel.z * size.x * size.y;
else
return UINT16_MAX;
}

unsigned16 XYZ(Coord3D coord) {
return XYZ(coord.x, coord.y, coord.z);
unsigned16 XYZ(unsigned16 x, unsigned16 y, unsigned16 z) {
return XYZ({x, y, z});
}

unsigned16 XYZ(unsigned16 x, unsigned16 y, unsigned16 z);
unsigned16 XYZ(Coord3D pixel);

Leds(Fixture &fixture) {
ppf("Leds constructor (PhysMap:%d)\n", sizeof(PhysMap));
Expand Down
Loading

0 comments on commit bdfc44f

Please sign in to comment.