Skip to content

Commit

Permalink
Fix Gen: matrix and rings241 rotation, added Star and Curtain
Browse files Browse the repository at this point in the history
LedLeds.h: Trigo: rename index to cache012

LedModFixtureGen:
- matrix: add rotation: add pan, tilt, roll, use Trigo
- matrix: advance with 10 as first is in mm
- cloud: first in mm
- geodesicDome: first in mm
- add Star
- add Curtain
- Helix: changed default values
- Rings241: add rotation: add pan, tilt, roll, use Trigo
- Wall: use mm instead of cm
- Human: use mm
  • Loading branch information
ewoudwijma committed Apr 25, 2024
1 parent 88a132a commit be4c9d6
Show file tree
Hide file tree
Showing 2 changed files with 128 additions and 46 deletions.
12 changes: 6 additions & 6 deletions src/App/LedLeds.h
Original file line number Diff line number Diff line change
Expand Up @@ -59,13 +59,13 @@ struct Trigo {
float cosValue[3]; uint16_t cosAngle[3] = {UINT16_MAX,UINT16_MAX,UINT16_MAX}; //caching of cosValue=cos(cosAngle) for pan, tilt and roll
virtual float sinBase(uint16_t angle) {return sinf(M_TWOPI * angle / period);}
virtual float cosBase(uint16_t angle) {return cosf(M_TWOPI * angle / period);}
int16_t sin(int16_t factor, uint16_t angle, uint8_t index = 0) {
if (sinAngle[index] != angle) {sinAngle[index] = angle; sinValue[index] = sinBase(angle);trigoUnCached++;} else trigoCached++;
return factor * sinValue[index];
int16_t sin(int16_t factor, uint16_t angle, uint8_t cache012 = 0) {
if (sinAngle[cache012] != angle) {sinAngle[cache012] = angle; sinValue[cache012] = sinBase(angle);trigoUnCached++;} else trigoCached++;
return factor * sinValue[cache012];
};
int16_t cos(int16_t factor, uint16_t angle, uint8_t index = 0) {
if (cosAngle[index] != angle) {cosAngle[index] = angle; cosValue[index] = cosBase(angle);trigoUnCached++;} else trigoCached++;
return factor * cosValue[index];
int16_t cos(int16_t factor, uint16_t angle, uint8_t cache012 = 0) {
if (cosAngle[cache012] != angle) {cosAngle[cache012] = angle; cosValue[cache012] = cosBase(angle);trigoUnCached++;} else trigoCached++;
return factor * cosValue[cache012];
};
// https://msl.cs.uiuc.edu/planning/node102.html
Coord3D pan(Coord3D in, Coord3D middle, uint16_t angle) {
Expand Down
162 changes: 122 additions & 40 deletions src/App/LedModFixtureGen.h
Original file line number Diff line number Diff line change
Expand Up @@ -129,11 +129,11 @@ class GenFix {

//utility
unsigned u_abs(int x) {
if (x <0) return -x;
if (x < 0) return -x;
else return x;
}

void matrix(Coord3D first, Coord3D rowEnd, Coord3D colEnd, unsigned8 ip, unsigned8 pin) {
void matrix(Coord3D first, Coord3D rowEnd, Coord3D colEnd, unsigned8 ip, unsigned8 pin, uint16_t pan = 0, uint16_t tilt = 0, uint16_t roll = 0) {

openPin(pin);

Expand All @@ -148,13 +148,22 @@ class GenFix {

// Coord3D pixel = first;

//middle is (max(rowEnd, colEnd) + first) / 2
Coord3D middle = rowEnd;
if (colEnd.x > middle.x) middle.x = colEnd.x;
if (colEnd.y > middle.y) middle.y = colEnd.y;
if (colEnd.z > middle.z) middle.z = colEnd.z;
middle = (middle + first) / 2;

ppf("middle %d,%d,%d", middle.x, middle.y, middle.z);

stackUnsigned8 rowDimension; //in what dimension the row will advance (x=0, y=1, z=2), now only one should differ
if (first.x != rowEnd.x) rowDimension = 0;
if (first.y != rowEnd.y) rowDimension = 1; //
if (first.y != rowEnd.y) rowDimension = 1;
if (first.z != rowEnd.z) rowDimension = 2;

stackUnsigned8 colDimension; //in what dimension the col will advance, not the rowDimension
if (first.x != colEnd.x && rowDimension != 0) colDimension = 0; //
if (first.x != colEnd.x && rowDimension != 0) colDimension = 0;
if (first.y != colEnd.y && rowDimension != 1) colDimension = 1;
if (first.z != colEnd.z && rowDimension != 2) colDimension = 2;

Expand All @@ -172,6 +181,8 @@ class GenFix {
colEnd.z = rowEnd.z;
}

Trigo trigo;

Coord3D colPixel = Coord3D{(rowDimension==0)?colEnd.x:first.x, (rowDimension==1)?colEnd.y:first.y, (rowDimension==2)?colEnd.z:first.z};
stackUnsigned8 colNr = 0;
while (true) {
Expand All @@ -189,16 +200,18 @@ class GenFix {
Coord3D rowPixel = cRowStart;
while (true) {
ppf(" %d,%d,%d", rowPixel.x, rowPixel.y, rowPixel.z);
write3D(rowPixel.x*10, rowPixel.y*10, rowPixel.z*10);
// write3D(rowPixel.x*10, rowPixel.y*10, rowPixel.z*10);
write3D(trigo.rotate(rowPixel, middle, pan, tilt, roll, 360));


if (rowPixel == cRowEnd) break; //end condition row
rowPixel.advance(cRowEnd);
rowPixel.advance(cRowEnd, 10);
}

ppf("\n");

if (colPixel == colEnd) break; //end condition columns
colPixel.advance(colEnd);
colPixel.advance(colEnd, 10);
colNr++;
}

Expand Down Expand Up @@ -367,31 +380,31 @@ class GenFix {

//first pin (red)
openPin(pin);
y = 150; for (int x = 530; x >= 0; x-=10) write3D(x+first.x*10, y+first.y*10, first.z*10);
y = 110; for (int x = 90; x <= 510; x+=10) write3D(x+first.x*10, y+first.y*10, first.z*10);
y = 70; for (int x = 400; x >= 110; x-=10) write3D(x+first.x*10, y+first.y*10, first.z*10);
y = 150; for (int x = 530; x >= 0; x-=10) write3D(x+first.x, y+first.y, first.z);
y = 110; for (int x = 90; x <= 510; x+=10) write3D(x+first.x, y+first.y, first.z);
y = 70; for (int x = 400; x >= 110; x-=10) write3D(x+first.x, y+first.y, first.z);
closePin();
//second pin (green)
openPin(pin);
y = 140; for (int x = 530; x >= 0; x-=10) write3D(x+first.x*10, y+first.y*10, first.z*10);
y = 100; for (int x = 90; x <= 510; x+=10) write3D(x+first.x*10, y+first.y*10, first.z*10);
y = 60; for (int x = 390; x >= 120; x-=10) write3D(x+first.x*10, y+first.y*10, first.z*10);
y = 140; for (int x = 530; x >= 0; x-=10) write3D(x+first.x, y+first.y, first.z);
y = 100; for (int x = 90; x <= 510; x+=10) write3D(x+first.x, y+first.y, first.z);
y = 60; for (int x = 390; x >= 120; x-=10) write3D(x+first.x, y+first.y, first.z);
closePin();
//third pin (blue)
openPin(pin);
y = 130; for (int x = 520; x >= 10; x-=10) write3D(x+first.x*10, y+first.y*10, first.z*10);
y = 90; for (int x = 100; x <= 500; x+=10) write3D(x+first.x*10, y+first.y*10, first.z*10);
y = 50; for (int x = 390; x >= 140; x-=10) write3D(x+first.x*10, y+first.y*10, first.z*10);
y = 130; for (int x = 520; x >= 10; x-=10) write3D(x+first.x, y+first.y, first.z);
y = 90; for (int x = 100; x <= 500; x+=10) write3D(x+first.x, y+first.y, first.z);
y = 50; for (int x = 390; x >= 140; x-=10) write3D(x+first.x, y+first.y, first.z);
closePin();
//fourth pin (yellow)
openPin(pin);
y = 120; for (int x = 520; x >= 30; x-=10) write3D(x+first.x*10, y+first.y*10, first.z*10);
y = 80; for (int x = 100; x <= 480; x+=10) write3D(x+first.x*10, y+first.y*10, first.z*10);
y = 40; for (int x = 380; x >= 240; x-=10) write3D(x+first.x*10, y+first.y*10, first.z*10);
y = 30; for (int x = 250; x <= 370; x+=10) write3D(x+first.x*10, y+first.y*10, first.z*10);
y = 20; for (int x = 360; x >= 260; x-=10) write3D(x+first.x*10, y+first.y*10, first.z*10);
y = 10; for (int x = 270; x <= 350; x+=10) write3D(x+first.x*10, y+first.y*10, first.z*10);
y = 00; for (int x = 330; x >= 290; x-=10) write3D(x+first.x*10, y+first.y*10, first.z*10);
y = 120; for (int x = 520; x >= 30; x-=10) write3D(x+first.x, y+first.y, first.z);
y = 80; for (int x = 100; x <= 480; x+=10) write3D(x+first.x, y+first.y, first.z);
y = 40; for (int x = 380; x >= 240; x-=10) write3D(x+first.x, y+first.y, first.z);
y = 30; for (int x = 250; x <= 370; x+=10) write3D(x+first.x, y+first.y, first.z);
y = 20; for (int x = 360; x >= 260; x-=10) write3D(x+first.x, y+first.y, first.z);
y = 10; for (int x = 270; x <= 350; x+=10) write3D(x+first.x, y+first.y, first.z);
y = 00; for (int x = 330; x >= 290; x-=10) write3D(x+first.x, y+first.y, first.z);
closePin();
}

Expand All @@ -416,13 +429,15 @@ class GenFix {
// https://stackoverflow.com/questions/17705621/algorithm-for-a-geodesic-sphere
//https://opengl.org.ru/docs/pg/0208.html
void geodesicDome(Coord3D first, unsigned16 radius, unsigned8 ip, unsigned8 pin) {

//radius unused (tbd)

stackUnsigned8 tindices[20][3] = { {0,4,1}, {0,9,4}, {9,5,4}, {4,5,8}, {4,8,1}, {8,10,1}, {8,3,10}, {5,3,8}, {5,2,3}, {2,7,3}, {7,10,3}, {7,6,10}, {7,11,6}, {11,0,6}, {0,1,6}, {6,1,10}, {9,0,11}, {9,11,2}, {9,2,5}, {7,2,11} };
stackUnsigned8 tindices[20][3] = { {0,40,10}, {0,90,40}, {90,50,40}, {40,50,80}, {40,80,10}, {80,100,10}, {80,30,100}, {50,30,80}, {50,20,30}, {20,70,30}, {70,100,30}, {70,60,100}, {70,110,60}, {110,0,60}, {0,10,60}, {60,10,100}, {90,0,110}, {90,110,20}, {90,20,50}, {70,20,110} };

openPin(pin);

for (int i=0; i<20; i++) {
write3D(tindices[i][0]*10 + first.x*10, tindices[i][1]*10 + first.y*10, tindices[i][2]*10 + first.z*10);
write3D(tindices[i][0] + first.x, tindices[i][1] + first.y, tindices[i][2] + first.z);
}

closePin();
Expand All @@ -442,11 +457,13 @@ enum Fixtures
f_Cone,
f_Cloud,
f_Wall,
f_Star,
f_6Rings,
f_SpaceStation,
f_Human,
f_Globe,
f_GeodesicDome,
f_Curtain,
fixtureCount
};

Expand Down Expand Up @@ -477,11 +494,13 @@ class LedModFixtureGen:public SysModule {
options.add("Cone");
options.add("Cloud");
options.add("Wall");
options.add("Star");
options.add("6Rings");
options.add("SpaceStation");
options.add("Human");
options.add("Globe");
options.add("GeodesicDome WIP");
options.add("Curtain");
return true;
}
case f_ChangeFun:
Expand Down Expand Up @@ -731,15 +750,15 @@ class LedModFixtureGen:public SysModule {
ui->initNumber(parentVar, "radius", 100, 1, 1000);
}
else if (fgValue == f_Helix) {
ui->initNumber(parentVar, "fixLeds", 64, 1, NUM_LEDS_Max, false, [](JsonObject var, unsigned8 rowNr, unsigned8 funType) { switch (funType) { //varFun
ui->initNumber(parentVar, "fixLeds", 100, 1, NUM_LEDS_Max, false, [](JsonObject var, unsigned8 rowNr, unsigned8 funType) { switch (funType) { //varFun
case f_UIFun:
ui->setLabel(var, "Leds");
return true;
default: return false;
}});
ui->initNumber(parentVar, "radius", 60, 1, 600);
ui->initNumber(parentVar, "pitch", 10, 1, 100);
ui->initNumber(parentVar, "deltaLed", 10, 1, 100);
ui->initNumber(parentVar, "pitch", 30, 1, 100);
ui->initNumber(parentVar, "deltaLed", 30, 1, 100);
}
else if (fgValue == f_Wheel) {
ui->initNumber(parentVar, "nrOfSpokes", 36, 1, 360);
Expand Down Expand Up @@ -804,8 +823,25 @@ class LedModFixtureGen:public SysModule {
else if (fgValue == f_Globe) {
ui->initNumber(parentVar, "width", 24, 1, 48);
}
else if (fgValue == f_GeodesicDome) {
ui->initNumber(parentVar, "radius", 100, 1, 1000);
}
else if (fgValue == f_Curtain) {
ui->initNumber(parentVar, "width", 20, 1, 100);
ui->initNumber(parentVar, "height", 20, 1, 100);
}

//general variables

if (fgValue == f_Matrix || fgValue == f_Rings241) { //tbd: the rest
ui->initCoord3D(parentVar, "fixRotate", {0,0,0}, 0, 359, false, [](JsonObject var, unsigned8 rowNr, unsigned8 funType) { switch (funType) { //varFun
case f_UIFun:
ui->setLabel(var, "Rotate");
ui->setComment(var, "Pan, Tilt, Roll");
return true;
default: return false;
}});
}

ui->initNumber(parentVar, "fixIP", WiFi.localIP()[3], 1, 256, false, [](JsonObject var, unsigned8 rowNr, unsigned8 funType) { switch (funType) { //varFun
case f_UIFun:
Expand Down Expand Up @@ -900,7 +936,10 @@ class LedModFixtureGen:public SysModule {
print->fFormat(fileName, 31, "F_Matrix%d%d%d", size.x, size.y, size.z);

getPanels(fileName, [](GenFix * genFix, unsigned8 rowNr, Coord3D pnlFirst, unsigned8 fixIP, unsigned8 fixPin) {
genFix->matrix(pnlFirst, mdl->getValue("mrxRowEnd", rowNr), mdl->getValue("mrxColEnd", rowNr), fixIP, fixPin);
Coord3D fixRotate = mdl->getValue("fixRotate", rowNr);
Coord3D mrxRowEnd = mdl->getValue("mrxRowEnd", rowNr);
Coord3D mrxColEnd = mdl->getValue("mrxColEnd", rowNr);
genFix->matrix(pnlFirst * 10, mrxRowEnd * 10, mrxColEnd * 10, fixIP, fixPin, fixRotate.x, fixRotate.y, fixRotate.z);
});

} else if (fgValue == f_Ring) {
Expand All @@ -924,12 +963,13 @@ class LedModFixtureGen:public SysModule {

getPanels(fileName, [](GenFix * genFix, unsigned8 rowNr, Coord3D pnlFirst, unsigned8 fixIP, unsigned8 fixPin) {
uint16_t nrOfLeds = mdl->getValue("fixLeds", rowNr);
Coord3D fixRotate = mdl->getValue("fixRotate", rowNr);
//first to middle (in mm)
Coord3D middle = pnlFirst;
uint8_t radius = 10 * 60 / M_TWOPI; //in mm
middle.x = middle.x*10 + radius;
middle.y = middle.y*10 + radius;
genFix->rings241(middle, mdl->getValue("nrOfRings", rowNr), mdl->getValue("in2out", rowNr), fixIP, fixPin);
genFix->rings241(middle, mdl->getValue("nrOfRings", rowNr), mdl->getValue("in2out", rowNr), fixIP, fixPin, fixRotate.x, fixRotate.y, fixRotate.z);
});

} else if (fgValue == f_Spiral) {
Expand Down Expand Up @@ -1014,7 +1054,7 @@ class LedModFixtureGen:public SysModule {

strcpy(fileName, "F_Cloud5416");
getPanels(fileName, [](GenFix * genFix, unsigned8 rowNr, Coord3D pnlFirst, unsigned8 fixIP, unsigned8 fixPin) {
genFix->cloud(pnlFirst, fixIP, fixPin);
genFix->cloud(pnlFirst*10, fixIP, fixPin);
});

} else if (fgValue == f_Wall) {
Expand All @@ -1023,14 +1063,36 @@ class LedModFixtureGen:public SysModule {
getPanels(fileName, [](GenFix * genFix, unsigned8 rowNr, Coord3D pnlFirst, unsigned8 fixIP, unsigned8 fixPin) {
genFix->rings241(Coord3D{110,110,0}, 9, true, fixIP, fixPin);

genFix->matrix(Coord3D{19,0,0}, Coord3D{19,8,0}, Coord3D{27,0,0}, fixIP, fixPin);
genFix->matrix(Coord3D{0,19,0}, Coord3D{0,25,0}, Coord3D{50,19,0}, fixIP, fixPin);
genFix->matrix(Coord3D{190,0,0}, Coord3D{190,80,0}, Coord3D{270,0,0}, fixIP, fixPin);
genFix->matrix(Coord3D{0,190,0}, Coord3D{0,250,0}, Coord3D{500,190,0}, fixIP, fixPin);

genFix->ring(Coord3D{190+80,80+80,0}, 48, fixIP, fixPin);

// genFix.spiral(240, 0, 0, 48);
});

} else if (fgValue == f_Star) {

strcpy(fileName, "F_Star");
getPanels(fileName, [](GenFix * genFix, unsigned8 rowNr, Coord3D pnlFirst, unsigned8 fixIP, unsigned8 fixPin) {

uint8_t ringsCentre = 170;
uint8_t sateliteRadius = 130;

genFix->rings241(Coord3D{ringsCentre,ringsCentre,0}, 9, true, fixIP, fixPin); //middle in mm

Trigo trigo;

for (int degrees = 0; degrees < 360; degrees+=45) {
Coord3D middle;
middle.x = ringsCentre + trigo.sin(sateliteRadius, degrees);
middle.y = ringsCentre + trigo.cos(sateliteRadius, degrees);
middle.z = 0;
genFix->matrix(middle + Coord3D{-35,-35,0}, middle + Coord3D{-35,35,0}, middle + Coord3D{+35,-35,0}, fixIP, fixPin, 0, 0, degrees);
}

});

} else if (fgValue == f_6Rings) {

strcpy(fileName, "F_6Rings");
Expand Down Expand Up @@ -1063,20 +1125,20 @@ class LedModFixtureGen:public SysModule {

//total dimensions width: 10 + 18 + 10
// height 18 + 5 +
Coord3D headSize = {18, 18, 1};
Coord3D armSize = {12, 5, 1};
Coord3D legSize = {5, 20, 1};
Coord3D headSize = {180, 180, 10};
Coord3D armSize = {120, 50, 10};
Coord3D legSize = {50, 200, 10};

// head
genFix->rings241({190,110,0}, 9, true, fixIP, fixPin);

//arms
genFix->matrix(Coord3D{0,headSize.y + 2,0}, Coord3D{0,headSize.y + 2 + armSize.y,0}, Coord3D{armSize.x,headSize.y + 2,0}, fixIP, fixPin);
genFix->matrix(Coord3D{armSize.x + 14,headSize.y + 2,0}, Coord3D{armSize.x + 14,headSize.y + 2 + armSize.y,0}, Coord3D{38,headSize.y + 2,0}, fixIP, fixPin);
genFix->matrix(Coord3D{0,headSize.y + 20,0}, Coord3D{0,headSize.y + 20 + armSize.y,0}, Coord3D{armSize.x,headSize.y + 20,0}, fixIP, fixPin);
genFix->matrix(Coord3D{armSize.x + 140,headSize.y + 20,0}, Coord3D{armSize.x + 140,headSize.y + 20 + armSize.y,0}, Coord3D{380,headSize.y + 20,0}, fixIP, fixPin);

//legs
genFix->matrix(Coord3D{10, 28, 0}, Coord3D{10, 50, 0}, Coord3D{15,28,0}, fixIP, fixPin);
genFix->matrix(Coord3D{23, 28, 0}, Coord3D{23, 50, 0}, Coord3D{28,28,0}, fixIP, fixPin);
genFix->matrix(Coord3D{100, 280, 0}, Coord3D{100, 500, 0}, Coord3D{150,280,0}, fixIP, fixPin);
genFix->matrix(Coord3D{230, 280, 0}, Coord3D{230, 500, 0}, Coord3D{280,280,0}, fixIP, fixPin);


});
Expand Down Expand Up @@ -1104,6 +1166,26 @@ class LedModFixtureGen:public SysModule {
genFix->geodesicDome(pnlFirst, mdl->getValue("radius", rowNr), fixIP, fixPin);
});

} else if (fgValue == f_Curtain) {

uint16_t width = mdl->getValue("width");
uint16_t height = mdl->getValue("height");
print->fFormat(fileName, 31, "F_Curtain%dx%d", width, height);

getPanels(fileName, [width, height](GenFix * genFix, unsigned8 rowNr, Coord3D pnlFirst, unsigned8 fixIP, unsigned8 fixPin) {
genFix->openPin(fixPin);

uint8_t offX;
for (int y=0; y<width; y++) {
for (int x=0; x<height; x++) {
offX = (y%2 == 1)?5:0;
genFix->write3D(x*10 + offX + pnlFirst.x, y*10 + pnlFirst.y, pnlFirst.z);
}
}

genFix->closePin();
});

}

files->filesChanged = true;
Expand Down

0 comments on commit be4c9d6

Please sign in to comment.