I found old post:
Used it as a reference, then just plain used bits of it to get a 1D CA running on my norns, no sound, outputs first four rows to crow (maybe all to ansible, but have not tested).
Summary
-- 1D Cellular automata
-- v2? imminent gloom
--
--
-- adapted from elcos.lua
-- by zebra
g = grid.connect()
elca = require 'elca'
ca = elca.new()
local g_br = 4
local g_br_strong = 10
local rule_delay = 0
local name = 'rule'
local t_name = name
params:add_separator('1D CA')
params:add_control('rule', 'rule', controlspec.new(1, 256, 'lin', 1, 34, '', 1/256, true))
params:set_action('rule', function(x) ca.rule = x end)
params:add_control('offset', 'offset', controlspec.new(0, 119, 'lin', 1, 0, '', 1/120, false))
params:set_action('offset', function(x) ca.offset = x end)
-- creates and zeros 16x128 slot memory
function no_history()
col = {}
history = {}
for y = 1, 128 do col[y] = 0 end
for x = 1, 16 do history[x] = col end
end
-- clock function
function forever()
while true do
clock.sync (1/4)
col = ca:window(128)
table.insert(history, col)
table.remove(history, 1)
ca:update()
-- Eurorack output modes:
--crow_output_gate()
crow_output_pulse()
--crow_ansible_output()
redraw_all()
end
end
function init()
c = clock.run(forever)
no_history()
ca.state[9] = 1
end
function g.key(x, y, z)
y = params:get('offset') + y
if z == 1 then
if x == 16 then
if ca.state[y] == 1 then ca.state[y] = 0 else ca.state[y] = 1 end
elseif x > 4 then
-- earlier rows - change the rule such that it would have produced a different value
-- (and change the state too)
local col = history[x-1]
local l, r
if y == 1 then l = col[128] else l = col[y-1] end
if y == 128 then r = col[1] else r = col[y+1] end
local c = col[y]
local val
if history[x][y] == 1 then val = 0 else val = 1 end
history[x][y] = val
ca.state[y] = c
ca:set_rule_by_state(history[x][y], l, c, r)
params:set('rule', ca.rule)
end
redraw_all()
end
end
function key(n, z)
if z == 1 then
if n == 3 then
ca:clear()
no_history()
redraw_all()
end
end
end
function enc(n, d)
if n == 1 then
params:delta('clock_tempo', d)
t_name = 'clock_tempo'
name = 'bpm'
end
if n == 2 then
params:delta('rule', d)
t_name = 'rule'
name = 'rule'
end
if n == 3 then
params:delta('offset', d)
t_name = 'offset'
name = 'shift'
end
redraw_all()
end
function redraw()
screen.clear()
screen.font_face(10)
screen.font_size(32)
screen.move(1,56)
screen.text(name .. ': ' .. params:get(t_name))
if name ~= 'rule' then
rule_delay = rule_delay + 1
end
if rule_delay == 10 then
name = 'rule'
t_name = name
rule_delay = 0
end
screen.update()
end
function redraw_grid()
local val
for x = 1, 16 do
if x == 16 then val = g_br_strong else val = g_br end
local col = history[x]
local z
for y = 1, 8 do
if col[y] == 1 then z = val else z = 0 end
g:led(x, y, z)
end
end
g:refresh()
end
function redraw_all()
redraw()
redraw_grid()
end
function crow_output_gate()
for y = 1, 4 do
local col = history[16]
local z
if col[y] == 1 then z = 10 else z = 0 end
crow.output[y].volts = z
end
end
function crow_output_pulse()
for y = 1, 4 do
local col = history[16]
local z
if col[y] == 1 then
crow.output[y].action = "pulse(0.005)"
crow.output[y]()
end
end
end
function ansible_crow_output()
local col = history[16]
local z
for y = 1, 4 do
if col[y] == 1 then z = 1 else z = 0 end
crow.ii.ansible.trigger(y, z)
end
for y = 5, 4 do
if col[y] == 1 then z = 10 else z = 0 end
crow.ii.ansible.cv(y, z)
end
end
function cleanup()
end
Hope it’s ok to resurrect.