Lots of changes, too long ago to remember

This commit is contained in:
Thomas Kolb 2018-06-19 20:13:22 +00:00
parent 6a11b7a16c
commit 57b2fa6cbc
15 changed files with 856 additions and 76 deletions

View file

@ -20,7 +20,7 @@
#define PORT 2703 #define PORT 2703
// FFT transformation parameters // FFT transformation parameters
#define FFT_EXPONENT 10 // ATTENTION: when you change this, run gen_lut.py with this value as argument #define FFT_EXPONENT 8 // ATTENTION: when you change this, run gen_lut.py with this value as argument
#define BLOCK_LEN (1 << FFT_EXPONENT) // 2^FFT_EXPONENT #define BLOCK_LEN (1 << FFT_EXPONENT) // 2^FFT_EXPONENT
#define SAMPLE_RATE 44100 #define SAMPLE_RATE 44100
#define DATALEN (BLOCK_LEN / 2) #define DATALEN (BLOCK_LEN / 2)
@ -29,7 +29,7 @@
#define BUFFER_PARTS 2 #define BUFFER_PARTS 2
// update rate for the led strip (in seconds) // update rate for the led strip (in seconds)
#define LED_INTERVAL 0.03 #define LED_INTERVAL 0.01
// frequency ranges for the base colors // frequency ranges for the base colors
#define RED_MIN_FREQ 0 #define RED_MIN_FREQ 0

View file

@ -1,7 +1,7 @@
WS2801_HOST = "192.168.23.222" WS2801_HOST = "192.168.2.136"
WS2801_PORT = 2703 WS2801_PORT = 2703
NUM_MODULES = 20 NUM_MODULES = 128
CENTER_MODULE = 10 CENTER_MODULE = 64
GAMMA = 2.0 GAMMA = 2.0

174
flame.lua Normal file
View file

@ -0,0 +1,174 @@
COOLDOWN_FACTOR = 0.9995
OVERDRIVE = 1.70
EXPONENT = 1.5
M = 1.7 -- mass
D = 1 -- spring strength
DAMPING = {} -- filled in init()
num_modules = 128
center_module = 64
num_masses = math.floor(num_modules/2)
excitement_pos = 1
-- maximum energy values for each band
maxRedEnergy = 1
maxGreenEnergy = 1
maxBlueEnergy = 1
-- spring-mass-grid values
pos_r = {}
pos_g = {}
pos_b = {}
vel_r = {}
vel_g = {}
vel_b = {}
acc_r = {}
acc_g = {}
acc_b = {}
-- output color buffers
red = {}
green = {}
blue = {}
r_tmp = {}
g_tmp = {}
b_tmp = {}
function limit(val)
if val > 1 then
return 1
elseif val < 0 then
return 0
else
return val
end
end
function periodic()
local redEnergy = get_energy_in_band(0, 400);
local greenEnergy = get_energy_in_band(400, 4000);
local blueEnergy = get_energy_in_band(4000, 22000);
local centerIndex = 2 * center_module + 1;
maxRedEnergy = maxRedEnergy * COOLDOWN_FACTOR
if redEnergy > maxRedEnergy then
maxRedEnergy = redEnergy
end
maxGreenEnergy = maxGreenEnergy * COOLDOWN_FACTOR
if greenEnergy > maxGreenEnergy then
maxGreenEnergy = greenEnergy
end
maxBlueEnergy = maxBlueEnergy * COOLDOWN_FACTOR
if blueEnergy > maxBlueEnergy then
maxBlueEnergy = blueEnergy
end
-- update the spring-mass string
-- the outside masses are special, as they are auto-returned to 0 position
-- { spring-mass pendulum } { friction }
--acc_r[1] = (-pos_r[1] + (pos_r[2] - pos_r[1])) * D / M
--acc_g[1] = (-pos_g[1] + (pos_g[2] - pos_g[1])) * D / M
--acc_b[1] = (-pos_b[1] + (pos_b[2] - pos_b[1])) * D / M
acc_r[num_masses] = (-pos_r[num_masses] + (pos_r[num_masses-1] - pos_r[num_masses])) * D / M
acc_g[num_masses] = (-pos_g[num_masses] + (pos_g[num_masses-1] - pos_g[num_masses])) * D / M
acc_b[num_masses] = (-pos_b[num_masses] + (pos_b[num_masses-1] - pos_b[num_masses])) * D / M
-- inside masses are only influenced by their neighbors
for i = 2,num_masses-1 do
acc_r[i] = (pos_r[i-1] + pos_r[i+1] - 2 * pos_r[i]) * D / M
acc_g[i] = (pos_g[i-1] + pos_g[i+1] - 2 * pos_g[i]) * D / M
acc_b[i] = (pos_b[i-1] + pos_b[i+1] - 2 * pos_b[i]) * D / M
end
-- update velocity and position
for i = 1,num_masses do
vel_r[i] = DAMPING[i] * (vel_r[i] + acc_r[i])
vel_g[i] = DAMPING[i] * (vel_g[i] + acc_g[i])
vel_b[i] = DAMPING[i] * (vel_b[i] + acc_b[i])
pos_r[i] = pos_r[i] + vel_r[i]
pos_g[i] = pos_g[i] + vel_g[i]
pos_b[i] = pos_b[i] + vel_b[i]
end
-- set the new position for the center module
newRed = redEnergy / maxRedEnergy
pos_r[excitement_pos] = newRed
vel_r[excitement_pos] = 0
acc_r[excitement_pos] = 0
newGreen = greenEnergy / maxGreenEnergy
pos_g[excitement_pos] = newGreen
vel_b[excitement_pos] = 0
acc_b[excitement_pos] = 0
newBlue = blueEnergy / maxBlueEnergy
pos_b[excitement_pos] = newBlue
vel_b[excitement_pos] = 0
acc_b[excitement_pos] = 0
-- map to LED modules
for i = 1,num_masses do
r_tmp[i] = pos_r[i]
g_tmp[i] = pos_g[i]
b_tmp[i] = pos_b[i]
r_tmp[num_modules-i+1] = pos_r[i]
g_tmp[num_modules-i+1] = pos_g[i]
b_tmp[num_modules-i+1] = pos_b[i]
--print(i, pos_r[i])
end
-- make colors more exciting
for i = 1,num_modules do
red[i] = limit(OVERDRIVE * math.pow(r_tmp[i], EXPONENT))
green[i] = limit(OVERDRIVE * math.pow(g_tmp[i], EXPONENT))
blue[i] = limit(OVERDRIVE * math.pow(b_tmp[i], EXPONENT))
end
-- return the 3 color arrays
return red, green, blue
end
function init(nmod, cmod)
num_modules = nmod
center_module = cmod
num_masses = math.floor(nmod/2)
excitement_pos = 1
for i = 1,nmod do
red[i] = 0
green[i] = 0
blue[i] = 0
end
for i = 1,num_masses do
pos_r[i] = 0
pos_g[i] = 0
pos_b[i] = 0
vel_r[i] = 0
vel_g[i] = 0
vel_b[i] = 0
acc_r[i] = 0
acc_g[i] = 0
acc_b[i] = 0
DAMPING[i] = 1 - 0.08 * math.pow(math.abs((i - excitement_pos) / num_masses), 2)
end
-- don't use fading
return 0
end

174
flame_diffspeed.lua Normal file
View file

@ -0,0 +1,174 @@
COOLDOWN_FACTOR = 0.9995
OVERDRIVE = 1.70
EXPONENT = 1.5
M = {2.3, 1.3, 1.0} -- mass
D = {1, 1, 1} -- spring strength
DAMPING = {} -- filled in init()
num_modules = 128
center_module = 64
num_masses = math.floor(num_modules/2)
excitement_pos = 1
-- maximum energy values for each band
maxRedEnergy = 1
maxGreenEnergy = 1
maxBlueEnergy = 1
-- spring-mass-grid values
pos_r = {}
pos_g = {}
pos_b = {}
vel_r = {}
vel_g = {}
vel_b = {}
acc_r = {}
acc_g = {}
acc_b = {}
-- output color buffers
red = {}
green = {}
blue = {}
r_tmp = {}
g_tmp = {}
b_tmp = {}
function limit(val)
if val > 1 then
return 1
elseif val < 0 then
return 0
else
return val
end
end
function periodic()
local redEnergy = get_energy_in_band(0, 400);
local greenEnergy = get_energy_in_band(400, 4000);
local blueEnergy = get_energy_in_band(4000, 22000);
local centerIndex = 2 * center_module + 1;
maxRedEnergy = maxRedEnergy * COOLDOWN_FACTOR
if redEnergy > maxRedEnergy then
maxRedEnergy = redEnergy
end
maxGreenEnergy = maxGreenEnergy * COOLDOWN_FACTOR
if greenEnergy > maxGreenEnergy then
maxGreenEnergy = greenEnergy
end
maxBlueEnergy = maxBlueEnergy * COOLDOWN_FACTOR
if blueEnergy > maxBlueEnergy then
maxBlueEnergy = blueEnergy
end
-- update the spring-mass string
-- the outside masses are special, as they are auto-returned to 0 position
-- { spring-mass pendulum } { friction }
--acc_r[1] = (-pos_r[1] + (pos_r[2] - pos_r[1])) * D / M
--acc_g[1] = (-pos_g[1] + (pos_g[2] - pos_g[1])) * D / M
--acc_b[1] = (-pos_b[1] + (pos_b[2] - pos_b[1])) * D / M
acc_r[num_masses] = (-pos_r[num_masses] + (pos_r[num_masses-1] - pos_r[num_masses])) * D[1] / M[1]
acc_g[num_masses] = (-pos_g[num_masses] + (pos_g[num_masses-1] - pos_g[num_masses])) * D[2] / M[2]
acc_b[num_masses] = (-pos_b[num_masses] + (pos_b[num_masses-1] - pos_b[num_masses])) * D[3] / M[3]
-- inside masses are only influenced by their neighbors
for i = 2,num_masses-1 do
acc_r[i] = (pos_r[i-1] + pos_r[i+1] - 2 * pos_r[i]) * D[1] / M[1]
acc_g[i] = (pos_g[i-1] + pos_g[i+1] - 2 * pos_g[i]) * D[2] / M[2]
acc_b[i] = (pos_b[i-1] + pos_b[i+1] - 2 * pos_b[i]) * D[3] / M[3]
end
-- update velocity and position
for i = 1,num_masses do
vel_r[i] = DAMPING[i] * (vel_r[i] + acc_r[i])
vel_g[i] = DAMPING[i] * (vel_g[i] + acc_g[i])
vel_b[i] = DAMPING[i] * (vel_b[i] + acc_b[i])
pos_r[i] = pos_r[i] + vel_r[i]
pos_g[i] = pos_g[i] + vel_g[i]
pos_b[i] = pos_b[i] + vel_b[i]
end
-- set the new position for the center module
newRed = redEnergy / maxRedEnergy
pos_r[excitement_pos] = newRed
vel_r[excitement_pos] = 0
acc_r[excitement_pos] = 0
newGreen = greenEnergy / maxGreenEnergy
pos_g[excitement_pos] = newGreen
vel_b[excitement_pos] = 0
acc_b[excitement_pos] = 0
newBlue = blueEnergy / maxBlueEnergy
pos_b[excitement_pos] = newBlue
vel_b[excitement_pos] = 0
acc_b[excitement_pos] = 0
-- map to LED modules
for i = 1,num_masses do
r_tmp[i] = pos_r[i]
g_tmp[i] = pos_g[i]
b_tmp[i] = pos_b[i]
r_tmp[num_modules-i+1] = pos_r[i]
g_tmp[num_modules-i+1] = pos_g[i]
b_tmp[num_modules-i+1] = pos_b[i]
--print(i, pos_r[i])
end
-- make colors more exciting
for i = 1,num_modules do
red[i] = limit(OVERDRIVE * math.pow(r_tmp[i], EXPONENT))
green[i] = limit(OVERDRIVE * math.pow(g_tmp[i], EXPONENT))
blue[i] = limit(OVERDRIVE * math.pow(b_tmp[i], EXPONENT))
end
-- return the 3 color arrays
return red, green, blue
end
function init(nmod, cmod)
num_modules = nmod
center_module = cmod
num_masses = math.floor(nmod/2)
excitement_pos = 1
for i = 1,nmod do
red[i] = 0
green[i] = 0
blue[i] = 0
end
for i = 1,num_masses do
pos_r[i] = 0
pos_g[i] = 0
pos_b[i] = 0
vel_r[i] = 0
vel_g[i] = 0
vel_b[i] = 0
acc_r[i] = 0
acc_g[i] = 0
acc_b[i] = 0
DAMPING[i] = 1 - 0.08 * math.pow(math.abs((i - excitement_pos) / num_masses), 2)
end
-- don't use fading
return 0
end

32
lut.c

File diff suppressed because one or more lines are too long

37
main.c
View file

@ -113,7 +113,7 @@ void* fft_thread(void *param) {
} }
nextFrame += 1.000/FPS; nextFrame += 1.000/FPS;
sleep_until(nextFrame); //sleep_until(nextFrame);
} }
return NULL; return NULL;
@ -130,6 +130,7 @@ int main(int argc, char **argv) {
pthread_t fftThread; pthread_t fftThread;
int active = 1; int active = 1;
int frame = 0;
double *red; double *red;
double *green; double *green;
@ -143,7 +144,7 @@ int main(int argc, char **argv) {
} }
// initialize lua // initialize lua
lua_State *L = lua_open(); lua_State *L = luaL_newstate();
// load the lua libraries // load the lua libraries
luaL_openlibs(L); luaL_openlibs(L);
@ -240,22 +241,24 @@ int main(int argc, char **argv) {
lua_readdoublearray(L, green, num_modules); lua_readdoublearray(L, green, num_modules);
lua_readdoublearray(L, red, num_modules); lua_readdoublearray(L, red, num_modules);
if(useFading) { if((++frame & 1) == 0) {
for(i = 0; i < num_modules; i++) { if(useFading) {
ws2801_fade_color(i, for(i = 0; i < num_modules; i++) {
255 * gamma_correct(red[i], gamma), ws2801_fade_color(i,
255 * gamma_correct(green[i], gamma), 255 * gamma_correct(red[i], gamma),
255 * gamma_correct(blue[i], gamma)); 255 * gamma_correct(green[i], gamma),
255 * gamma_correct(blue[i], gamma));
}
ws2801_commit();
} else {
for(i = 0; i < num_modules; i++) {
ws2801_set_color(i,
255 * gamma_correct(red[i], gamma),
255 * gamma_correct(green[i], gamma),
255 * gamma_correct(blue[i], gamma));
}
ws2801_commit();
} }
ws2801_commit();
} else {
for(i = 0; i < num_modules; i++) {
ws2801_set_color(i,
255 * gamma_correct(red[i], gamma),
255 * gamma_correct(green[i], gamma),
255 * gamma_correct(blue[i], gamma));
}
ws2801_commit();
} }
if(lastUpdateTime < nextFrame - 1) { if(lastUpdateTime < nextFrame - 1) {

174
pulsar.lua Normal file
View file

@ -0,0 +1,174 @@
COOLDOWN_FACTOR = 0.9995
OVERDRIVE = 1.50
EXPONENT = 1.5
M = 1.7 -- mass
D = 1 -- spring strength
DAMPING = {} -- filled in init()
num_modules = 128
center_module = 64
num_masses = math.floor(num_modules/2)
excitement_pos = math.floor(center_module/2)
-- maximum energy values for each band
maxRedEnergy = 1
maxGreenEnergy = 1
maxBlueEnergy = 1
-- spring-mass-grid values
pos_r = {}
pos_g = {}
pos_b = {}
vel_r = {}
vel_g = {}
vel_b = {}
acc_r = {}
acc_g = {}
acc_b = {}
-- output color buffers
red = {}
green = {}
blue = {}
r_tmp = {}
g_tmp = {}
b_tmp = {}
function limit(val)
if val > 1 then
return 1
elseif val < 0 then
return 0
else
return val
end
end
function periodic()
local redEnergy = get_energy_in_band(0, 400);
local greenEnergy = get_energy_in_band(400, 4000);
local blueEnergy = get_energy_in_band(4000, 22000);
local centerIndex = 2 * center_module + 1;
maxRedEnergy = maxRedEnergy * COOLDOWN_FACTOR
if redEnergy > maxRedEnergy then
maxRedEnergy = redEnergy
end
maxGreenEnergy = maxGreenEnergy * COOLDOWN_FACTOR
if greenEnergy > maxGreenEnergy then
maxGreenEnergy = greenEnergy
end
maxBlueEnergy = maxBlueEnergy * COOLDOWN_FACTOR
if blueEnergy > maxBlueEnergy then
maxBlueEnergy = blueEnergy
end
-- update the spring-mass string
-- the outside masses are special, as they are auto-returned to 0 position
-- { spring-mass pendulum } { friction }
acc_r[1] = (-pos_r[1] + (pos_r[2] - pos_r[1])) * D / M
acc_g[1] = (-pos_g[1] + (pos_g[2] - pos_g[1])) * D / M
acc_b[1] = (-pos_b[1] + (pos_b[2] - pos_b[1])) * D / M
acc_r[num_masses] = (-pos_r[num_masses] + (pos_r[num_masses-1] - pos_r[num_masses])) * D / M
acc_g[num_masses] = (-pos_g[num_masses] + (pos_g[num_masses-1] - pos_g[num_masses])) * D / M
acc_b[num_masses] = (-pos_b[num_masses] + (pos_b[num_masses-1] - pos_b[num_masses])) * D / M
-- inside masses are only influenced by their neighbors
for i = 2,num_masses-1 do
acc_r[i] = (pos_r[i-1] + pos_r[i+1] - 2 * pos_r[i]) * D / M
acc_g[i] = (pos_g[i-1] + pos_g[i+1] - 2 * pos_g[i]) * D / M
acc_b[i] = (pos_b[i-1] + pos_b[i+1] - 2 * pos_b[i]) * D / M
end
-- update velocity and position
for i = 1,num_masses do
vel_r[i] = DAMPING[i] * (vel_r[i] + acc_r[i])
vel_g[i] = DAMPING[i] * (vel_g[i] + acc_g[i])
vel_b[i] = DAMPING[i] * (vel_b[i] + acc_b[i])
pos_r[i] = pos_r[i] + vel_r[i]
pos_g[i] = pos_g[i] + vel_g[i]
pos_b[i] = pos_b[i] + vel_b[i]
end
-- set the new position for the center module
newRed = redEnergy / maxRedEnergy
pos_r[excitement_pos] = newRed
vel_r[excitement_pos] = 0
acc_r[excitement_pos] = 0
newGreen = greenEnergy / maxGreenEnergy
pos_g[excitement_pos] = newGreen
vel_b[excitement_pos] = 0
acc_b[excitement_pos] = 0
newBlue = blueEnergy / maxBlueEnergy
pos_b[excitement_pos] = newBlue
vel_b[excitement_pos] = 0
acc_b[excitement_pos] = 0
-- map to LED modules
for i = 1,num_masses do
r_tmp[i] = pos_r[i]
g_tmp[i] = pos_g[i]
b_tmp[i] = pos_b[i]
r_tmp[num_modules-i+1] = pos_r[i]
g_tmp[num_modules-i+1] = pos_g[i]
b_tmp[num_modules-i+1] = pos_b[i]
--print(i, pos_r[i])
end
-- make colors more exciting
for i = 1,num_modules do
red[i] = limit(OVERDRIVE * math.pow(r_tmp[i], EXPONENT))
green[i] = limit(OVERDRIVE * math.pow(g_tmp[i], EXPONENT))
blue[i] = limit(OVERDRIVE * math.pow(b_tmp[i], EXPONENT))
end
-- return the 3 color arrays
return red, green, blue
end
function init(nmod, cmod)
num_modules = nmod
center_module = cmod
num_masses = math.floor(nmod/2)
excitement_pos = math.floor(cmod/2)
for i = 1,nmod do
red[i] = 0
green[i] = 0
blue[i] = 0
end
for i = 1,num_masses do
pos_r[i] = 0
pos_g[i] = 0
pos_b[i] = 0
vel_r[i] = 0
vel_g[i] = 0
vel_b[i] = 0
acc_r[i] = 0
acc_g[i] = 0
acc_b[i] = 0
DAMPING[i] = 1 - 0.5 * math.pow(math.abs((i - excitement_pos) / num_masses), 2)
end
-- don't use fading
return 0
end

View file

@ -1,8 +1,10 @@
COOLDOWN_FACTOR = 0.9998 COOLDOWN_FACTOR = 0.9998
FADE_FACTOR = 0.985 FADE_FACTOR = 1
OVERDRIVE = 1.30
EXPONENT = 1.8
num_modules = 20 num_modules = 160
center_module = 10 center_module = 80
-- maximum energy values for each band -- maximum energy values for each band
maxRedEnergy = 1 maxRedEnergy = 1
@ -18,6 +20,14 @@ tmpRed = {}
tmpGreen = {} tmpGreen = {}
tmpBlue = {} tmpBlue = {}
function limit(val)
if val > 1 then
return 1
else
return val
end
end
function periodic() function periodic()
local redEnergy = get_energy_in_band(0, 400); local redEnergy = get_energy_in_band(0, 400);
local greenEnergy = get_energy_in_band(400, 4000); local greenEnergy = get_energy_in_band(400, 4000);
@ -48,30 +58,33 @@ function periodic()
-- set the new value for the center module -- set the new value for the center module
newRed = redEnergy / maxRedEnergy newRed = redEnergy / maxRedEnergy
if newRed > tmpRed[num_modules] then tmpRed[1] = newRed
tmpRed[1] = newRed --if newRed > tmpRed[num_modules] then
else -- tmpRed[1] = newRed
tmpRed[1] = tmpRed[num_modules] --else
end -- tmpRed[1] = tmpRed[num_modules]
--end
newGreen = greenEnergy / maxGreenEnergy newGreen = greenEnergy / maxGreenEnergy
if newGreen > tmpGreen[num_modules] then tmpGreen[1] = newGreen
tmpGreen[1] = newGreen --if newGreen > tmpGreen[num_modules] then
else -- tmpGreen[1] = newGreen
tmpGreen[1] = tmpGreen[num_modules] --else
end -- tmpGreen[1] = tmpGreen[num_modules]
--end
newBlue = blueEnergy / maxBlueEnergy newBlue = blueEnergy / maxBlueEnergy
if newBlue > tmpBlue[num_modules] then tmpBlue[1] = newBlue
tmpBlue[1] = newBlue --if newBlue > tmpBlue[num_modules] then
else -- tmpBlue[1] = newBlue
tmpBlue[1] = tmpBlue[num_modules] --else
end -- tmpBlue[1] = tmpBlue[num_modules]
--end
for i = 1,num_modules do for i = 1,num_modules do
red[i] = tmpRed[i] red[i] = limit(OVERDRIVE * math.pow(tmpRed[i], EXPONENT))
green[i] = tmpGreen[i] green[i] = limit(OVERDRIVE * math.pow(tmpGreen[i], EXPONENT))
blue[i] = tmpBlue[i] blue[i] = limit(OVERDRIVE * math.pow(tmpBlue[i], EXPONENT))
end end
-- return the 3 color arrays -- return the 3 color arrays

100
pulsecircle_ultrafast.lua Normal file
View file

@ -0,0 +1,100 @@
COOLDOWN_FACTOR = 0.9998
FADE_FACTOR = 1
OVERDRIVE = 1.30
EXPONENT = 1.8
SHIFT=2
num_modules = 20
center_module = 10
-- maximum energy values for each band
maxRedEnergy = 1
maxGreenEnergy = 1
maxBlueEnergy = 1
-- output color buffers
red = {}
green = {}
blue = {}
tmpRed = {}
tmpGreen = {}
tmpBlue = {}
function limit(val)
if val > 1 then
return 1
else
return val
end
end
function periodic()
local redEnergy = get_energy_in_band(0, 400);
local greenEnergy = get_energy_in_band(400, 4000);
local blueEnergy = get_energy_in_band(4000, 22000);
local centerIndex = 2 * center_module + 1;
maxRedEnergy = maxRedEnergy * COOLDOWN_FACTOR
if redEnergy > maxRedEnergy then
maxRedEnergy = redEnergy
end
maxGreenEnergy = maxGreenEnergy * COOLDOWN_FACTOR
if greenEnergy > maxGreenEnergy then
maxGreenEnergy = greenEnergy
end
maxBlueEnergy = maxBlueEnergy * COOLDOWN_FACTOR
if blueEnergy > maxBlueEnergy then
maxBlueEnergy = blueEnergy
end
-- move the color buffers on by one
for i = num_modules-SHIFT,1,-1 do
tmpRed[i+SHIFT] = FADE_FACTOR * tmpRed[i]
tmpGreen[i+SHIFT] = FADE_FACTOR * tmpGreen[i]
tmpBlue[i+SHIFT] = FADE_FACTOR * tmpBlue[i]
end
-- set the new value for the center module
newRed = redEnergy / maxRedEnergy
newGreen = greenEnergy / maxGreenEnergy
newBlue = blueEnergy / maxBlueEnergy
for i = 1,SHIFT do
tmpRed[i] = newRed
tmpGreen[i] = newGreen
tmpBlue[i] = newBlue
end
for i = 1,num_modules do
red[i] = limit(OVERDRIVE * math.pow(tmpRed[i], EXPONENT))
green[i] = limit(OVERDRIVE * math.pow(tmpGreen[i], EXPONENT))
blue[i] = limit(OVERDRIVE * math.pow(tmpBlue[i], EXPONENT))
end
-- return the 3 color arrays
return red, green, blue
end
function init(nmod, cmod)
num_modules = nmod
center_module = cmod
for i = 1,nmod do
red[i] = 0
green[i] = 0
blue[i] = 0
end
for i = 1,nmod do
tmpRed[i] = 0
tmpGreen[i] = 0
tmpBlue[i] = 0
end
-- don't use fading
return 0
end

View file

@ -1,7 +1,7 @@
COOLDOWN_FACTOR = 0.9998 COOLDOWN_FACTOR = 0.9998
num_modules = 20 num_modules = 160
center_module = 10 center_module = 80
-- maximum energy values for each band -- maximum energy values for each band
maxRedEnergy = 1 maxRedEnergy = 1

View file

@ -20,9 +20,9 @@ tmpGreen = {}
tmpBlue = {} tmpBlue = {}
function weighted_avg(array, centerIndex) function weighted_avg(array, centerIndex)
return 0.2 * array[centerIndex - 1] + return 0.20 * array[centerIndex - 1] +
0.6 * array[centerIndex] + 0.60 * array[centerIndex] +
0.2 * array[centerIndex + 1] 0.20 * array[centerIndex + 1]
end end
function periodic() function periodic()
@ -63,6 +63,9 @@ function periodic()
tmpBlue[centerIndex] = blueEnergy / maxEnergy tmpBlue[centerIndex] = blueEnergy / maxEnergy
for i = 1,num_modules do for i = 1,num_modules do
--red[i] = tmpRed[i+centerIndex-num_modules/2]
--green[i] = tmpGreen[i+centerIndex-num_modules/2]
--blue[i] = tmpBlue[i+centerIndex-num_modules/2]
red[i] = weighted_avg(tmpRed, 2*i) red[i] = weighted_avg(tmpRed, 2*i)
green[i] = weighted_avg(tmpGreen, 2*i) green[i] = weighted_avg(tmpGreen, 2*i)
blue[i] = weighted_avg(tmpBlue, 2*i) blue[i] = weighted_avg(tmpBlue, 2*i)

143
pulsetunnel_fast.lua Normal file
View file

@ -0,0 +1,143 @@
COOLDOWN_FACTOR = 0.9998
FADE_FACTOR = 1
OVERDRIVE = 1.30
EXPONENT = 1.8
INTERP_FACTOR = 2
INTERP_FILTER = {0.5, 1.0, 0.5}
num_modules = 128
center_module = 64
-- maximum energy values for each band
maxRedEnergy = 1
maxGreenEnergy = 1
maxBlueEnergy = 1
-- output color buffers
red = {}
green = {}
blue = {}
tmpRed = {}
tmpGreen = {}
tmpBlue = {}
tmpRed2 = {}
tmpGreen2 = {}
tmpBlue2 = {}
tmpRed3 = {}
tmpGreen3 = {}
tmpBlue3 = {}
function limit(val)
if val > 1 then
return 1
else
return val
end
end
function periodic()
local redEnergy = get_energy_in_band(0, 400);
local greenEnergy = get_energy_in_band(400, 4000);
local blueEnergy = get_energy_in_band(4000, 22000);
local centerIndex = 2 * center_module + 1;
maxRedEnergy = maxRedEnergy * COOLDOWN_FACTOR
if redEnergy > maxRedEnergy then
maxRedEnergy = redEnergy
end
maxGreenEnergy = maxGreenEnergy * COOLDOWN_FACTOR
if greenEnergy > maxGreenEnergy then
maxGreenEnergy = greenEnergy
end
maxBlueEnergy = maxBlueEnergy * COOLDOWN_FACTOR
if blueEnergy > maxBlueEnergy then
maxBlueEnergy = blueEnergy
end
-- move the color buffers on by one
for i = center_module/INTERP_FACTOR,1,-1 do
tmpRed[i+1] = FADE_FACTOR * tmpRed[i]
tmpGreen[i+1] = FADE_FACTOR * tmpGreen[i]
tmpBlue[i+1] = FADE_FACTOR * tmpBlue[i]
end
for i = center_module/INTERP_FACTOR+1,num_modules/INTERP_FACTOR,1 do
tmpRed[i-1] = FADE_FACTOR * tmpRed[i]
tmpGreen[i-1] = FADE_FACTOR * tmpGreen[i]
tmpBlue[i-1] = FADE_FACTOR * tmpBlue[i]
end
-- set the new value for the center module
newRed = redEnergy / maxRedEnergy
tmpRed[1] = newRed
tmpRed[num_modules/INTERP_FACTOR] = newRed
newGreen = greenEnergy / maxGreenEnergy
tmpGreen[1] = newGreen
tmpGreen[num_modules/INTERP_FACTOR] = newGreen
newBlue = blueEnergy / maxBlueEnergy
tmpBlue[1] = newBlue
tmpBlue[num_modules/INTERP_FACTOR] = newBlue
for i = INTERP_FACTOR,num_modules,INTERP_FACTOR do
tmpRed2[i] = tmpRed[math.floor(i/INTERP_FACTOR)]
tmpGreen2[i] = tmpGreen[math.floor(i/INTERP_FACTOR)]
tmpBlue2[i] = tmpBlue[math.floor(i/INTERP_FACTOR)]
end
for i = 1,num_modules do
tmpRed3[i] = 0
tmpGreen3[i] = 0
tmpBlue3[i] = 0
for j = 1,#INTERP_FILTER do
idx = math.floor(i+j-#INTERP_FILTER/2)
if idx >= 1 and idx <= num_modules then
tmpRed3[i] = tmpRed3[i] + tmpRed2[idx] * INTERP_FILTER[j]
tmpGreen3[i] = tmpGreen3[i] + tmpGreen2[idx] * INTERP_FILTER[j]
tmpBlue3[i] = tmpBlue3[i] + tmpBlue2[idx] * INTERP_FILTER[j]
end
end
end
for i = 1,num_modules do
red[i] = limit(OVERDRIVE * math.pow(tmpRed3[i], EXPONENT))
green[i] = limit(OVERDRIVE * math.pow(tmpGreen3[i], EXPONENT))
blue[i] = limit(OVERDRIVE * math.pow(tmpBlue3[i], EXPONENT))
end
-- return the 3 color arrays
return red, green, blue
end
function init(nmod, cmod)
num_modules = nmod
center_module = cmod
for i = 1,nmod do
red[i] = 0
green[i] = 0
blue[i] = 0
end
for i = 1,nmod do
tmpRed[i] = 0
tmpGreen[i] = 0
tmpBlue[i] = 0
tmpRed2[i] = 0
tmpGreen2[i] = 0
tmpBlue2[i] = 0
end
-- don't use fading
return 0
end

View file

@ -1,4 +1,4 @@
#!/bin/sh #!/bin/sh
#dd if=/tmp/mpd.fifo bs=1024 | ./musiclight2 #dd if=/tmp/mpd.fifo bs=1024 | ./musiclight2
./musiclight2 $* < /tmp/mpd.fifo ./musiclight2 $* < /tmp/musiclight.fifo

View file

@ -1,3 +1,3 @@
#!/bin/sh #!/bin/sh
nc -l -p 12345 | ./musiclight2 $* socat UDP4-RECV:12345 STDOUT | ./musiclight2 $*

View file

@ -24,12 +24,13 @@
#define SET_FADESTEP 3 #define SET_FADESTEP 3
struct WS2801Packet { struct WS2801Packet {
uint8_t metadata; uint8_t action;
uint8_t module;
uint8_t data[3]; uint8_t data[3];
}; };
int ws2801_socket = -1; int ws2801_socket = -1;
struct WS2801Packet packetQueue[50]; struct WS2801Packet packetQueue[1024];
int queueIndex = 0; int queueIndex = 0;
// creates the socket needed for steering the LED strip // creates the socket needed for steering the LED strip
@ -70,7 +71,8 @@ int ws2801_init(const char *host, unsigned short port) {
} }
void ws2801_set_color(uint8_t module, uint8_t r, uint8_t g, uint8_t b) { void ws2801_set_color(uint8_t module, uint8_t r, uint8_t g, uint8_t b) {
packetQueue[queueIndex].metadata = (SET_COLOR << 6) | (module & 0x3F); packetQueue[queueIndex].action = SET_COLOR;
packetQueue[queueIndex].module = module;
packetQueue[queueIndex].data[0] = r; packetQueue[queueIndex].data[0] = r;
packetQueue[queueIndex].data[1] = g; packetQueue[queueIndex].data[1] = g;
packetQueue[queueIndex].data[2] = b; packetQueue[queueIndex].data[2] = b;
@ -78,7 +80,8 @@ void ws2801_set_color(uint8_t module, uint8_t r, uint8_t g, uint8_t b) {
} }
void ws2801_fade_color(uint8_t module, uint8_t r, uint8_t g, uint8_t b) { void ws2801_fade_color(uint8_t module, uint8_t r, uint8_t g, uint8_t b) {
packetQueue[queueIndex].metadata = (FADE_COLOR << 6) | (module & 0x3F); packetQueue[queueIndex].action = FADE_COLOR;
packetQueue[queueIndex].module = module;
packetQueue[queueIndex].data[0] = r; packetQueue[queueIndex].data[0] = r;
packetQueue[queueIndex].data[1] = g; packetQueue[queueIndex].data[1] = g;
packetQueue[queueIndex].data[2] = b; packetQueue[queueIndex].data[2] = b;
@ -86,7 +89,8 @@ void ws2801_fade_color(uint8_t module, uint8_t r, uint8_t g, uint8_t b) {
} }
void ws2801_add_color(uint8_t module, uint8_t r, uint8_t g, uint8_t b) { void ws2801_add_color(uint8_t module, uint8_t r, uint8_t g, uint8_t b) {
packetQueue[queueIndex].metadata = (ADD_COLOR << 6) | (module & 0x3F); packetQueue[queueIndex].action = ADD_COLOR;
packetQueue[queueIndex].module = module;
packetQueue[queueIndex].data[0] = r; packetQueue[queueIndex].data[0] = r;
packetQueue[queueIndex].data[1] = g; packetQueue[queueIndex].data[1] = g;
packetQueue[queueIndex].data[2] = b; packetQueue[queueIndex].data[2] = b;
@ -94,7 +98,7 @@ void ws2801_add_color(uint8_t module, uint8_t r, uint8_t g, uint8_t b) {
} }
void ws2801_set_fadestep(uint8_t fadestep) { void ws2801_set_fadestep(uint8_t fadestep) {
packetQueue[queueIndex].metadata = (SET_FADESTEP << 6); packetQueue[queueIndex].action = SET_FADESTEP;
packetQueue[queueIndex].data[0] = fadestep; packetQueue[queueIndex].data[0] = fadestep;
queueIndex++; queueIndex++;
} }