alexthescott.lofi 3d 1

-- lofi 3d 1
-- alexthescott
-- 10/20/21 8:12am

-- based on 3d demo
-- by @noahrosamilia

-- new seed every day of the year 
srand(31*stat(81)+stat(82)) 

p1={7,6,135,10,138,11,139,3,131,12,140,1,129,130,128,0}
p2={7,135,10,9,15,143,142,137,14,136,8,2,130,133,128,0}
p3={7,15,143,142,14,8,136,137,9,10,135,138,11,139,12,140}

p={p1,p2,p3}
c=rnd(p)

pal(c,1)

function draw_shape(s,c)
	for l in all(s[2]) do
		draw_line(s[1][l[1]],s[1][l[2]],c)
	end
end

function draw_line(p1,p2,c)
	x0,y0=project(p1)
	x1,y1=project(p2)
	line(x0,y0,x1,y1,c)
end

function draw_point(p,c)
	x,y=project(p)
	pset(x,y,c)
end

function project(p)
	-- calculate x,y and center it
	x=(p[1]-cam[1])*mult/(p[3]-cam[3])+127/2
	y=-(p[2]-cam[2])*mult/(p[3]-cam[3])+127/2
	return x,y
end

function translate_shape(s,t)
	-- copy shape, 0 out points,
	-- keep og lines
	ns={{},s[2]}
	-- add displacement to point
	for p in all(s[1])do
		add(ns[1],{p[1]+t[1],p[2]+t[2],p[3]+t[3]})
	end
	return ns
end

function rotate_shape(s,a,r)
	-- copy shape, 0 out points
	-- keep og lines
	ns={{},s[2]}
	for p in all(s[1])do
		add(ns[1],rotate_point(p,a,r))
	end
	return ns
end

function rotate_point(p,a,r)
	-- figure axis we're rotating
	if a==1 then
		x,y,z=3,2,1
	elseif a==2 then
		x,y,z=1,3,2
	elseif a==3 then
		x,y,z=1,2,3
	end
	
	_x=cos(r)*p[x]-sin(r)*p[y]
	_y=sin(r)*p[x]+cos(r)*p[y]
	np={}
	np[x]=_x
	np[y]=_y
	np[z]=p[z]
	return np
end

function limit_int(v,l)
	if v>0 then
		return min(v,l)
	else
		return max(v,-l)
	end
end

function burn()
	for p=0,384 do
		x=rnd(128)\1
		y=rnd(128)\1
		pc=pget(x,y)
		if pc!=0 then
			pset(x,y,pc-1)
		else
			pset(x,y,0)
		end
	end
end

function fuzz(big)
	if big then
		sz=10
		cnt=512
	else
		sz=3
		cnt=384
	end

	for p=0,cnt do
		x=rnd(128)\1
		y=rnd(128)\1
		pc=pget(x,y)
		if pc!=0 then
			for l=1,rnd(sz)\1 do
			pset(x-l,y,pc)
			pset(x+l,y,pc)
			end
		end		
	end
end

function forward()
	v=c[1]
	del(c,v)
	c[#c+1]=v
	pal(c,1)
end

function backward()
	v=c[#c]
	del(c,v)
	for i=#c+1,1,-1 do
		if i!=1 then
			c[i]=c[i-1]
		else
			c[i]=v
		end
	end
	pal(c,1)
end

for i=1,rnd()*16 do
	forward()
end

cube={
	--points
	{{-1,-1,-1},
	{-1,-1,1},
	{1,-1,1},
	{1,-1,-1},
	{-1,1,-1},
	{-1,1,1},
	{1,1,1},
	{1,1,-1}},
	--lines
	{{1,2},{2,3},
	{3,4},{4,1},
	{5,6},{6,7},
	{7,8},{8,5},
	{1,5},{2,6},
	{3,7},{4,8}}
}
sz2=2/3
cube2={
	--points
	{{-sz2,-sz2,-sz2},
	{-sz2,-sz2,sz2},
	{sz2,-sz2,sz2},
	{sz2,-sz2,-sz2},
	{-sz2,sz2,-sz2},
	{-sz2,sz2,sz2},
	{sz2,sz2,sz2},
	{sz2,sz2,-sz2}},
	--lines
	{{1,2},{2,3},
	{3,4},{4,1},
	{5,6},{6,7},
	{7,8},{8,5},
	{1,5},{2,6},
	{3,7},{4,8}}}
	
sz3=1/3
cube3={
	--points
	{{-sz3,-sz3,-sz3},
	{-sz3,-sz3,sz3},
	{sz3,-sz3,sz3},
	{sz3,-sz3,-sz3},
	{-sz3,sz3,-sz3},
	{-sz3,sz3,sz3},
	{sz3,sz3,sz3},
	{sz3,sz3,-sz3}},
	--lines
	{{1,2},{2,3},
	{3,4},{4,1},
	{5,6},{6,7},
	{7,8},{8,5},
	{1,5},{2,6},
	{3,7},{4,8}}
	}

cam={0,0,-2.5}
mult=64
a1_1=1+rnd(3)\1
a2_1=1+rnd(3)\1
a1_2,a1_3=a1_1,a1_1
a2_2,a2_3=a2_1,a2_1
while a1_1==a2_1 do
	a2_1=1+rnd(3)\1
	a2_2,a2_3=a2_1,a2_1
end
t1=50+rnd(50)\1
t2=t1+20
t3=t2+40

t_gap=5+(5*rnd())\1

burn_count=3+(40*rnd())\1
burn_var=5+(15*rnd())\1

show_center_circ=rnd()>0.5
show_outside_circ=rnd()>0.5

month=stat(81)
day=stat(82)

cls()
_set_fps(60)
::♥::
if t()<2 then
	print("lofi 3d 1",46,59,1)
	print(month.."/"..day,55,65)
else

	if btn(❎) and btn(🅾️) or 
		time()%burn_var==0 then
			burn_count=3+(40*rnd())\1
			burn_var=5+(15*rnd())\1
			burn()
	elseif burn_count>0 then
		burn()
		burn_count-=1
	else
		cls()
	end
	
	if btn(⬅️) then cam[1] -= 0.1 end
	if btn(➡️) then cam[1] += 0.1 end
	if btn(⬆️) then cam[2] += 0.1 end
	if btn(⬇️) then cam[2] -= 0.1 end
	if btn(❎) then cam[3] -= 0.1 end
	if btn(🅾️) then cam[3] += 0.1 end
	
	if btn(⬆️) and btn(⬇️) or
		btn(➡️) and btn(⬅️) then
			print("cam.x="..cam[1],0,0,2)
			print("cam.y="..cam[2],0,6,2)
			print("cam.z="..cam[3],0,12,2)
			
			print("t1="..t1,0,110,t1/t_gap)
			print("t2="..t2,0,116,t2/t_gap)
			print("t3="..t3,0,122,t3/t_gap)
	end
	
	t1-=1
	t2-=1
	t3-=1
	
	if t1<0 then
		a1_1=1+rnd(3)\1
		a2_1=1+rnd(3)\1
		while a1_1==a2_1 do
			a2_1=1+rnd(3)\1
		end
		t1=50+rnd(50)\1
	end
	
	if t2<0 then
		t2=t1+20
		a1_2,a2_2=a1_1,a2_1
	end
	
	if t3<0 then
		t3=t1+40
		a1_3,a2_3=a1_1,a2_1
	end
	
	cube=rotate_shape(cube,a1_1,0.004)
	cube=rotate_shape(cube,a2_1,0.004)
	cube2=rotate_shape(cube2,a1_2,0.004)
	cube2=rotate_shape(cube2,a2_2,0.004)
	cube3=rotate_shape(cube3,a1_3,0.004)
	cube3=rotate_shape(cube3,a2_3,0.004)
	
	if show_center_circ then
		fillp(0b1111110111111111)
		circfill(64,64,20,1)
		fillp(0b111110111111111)
		circfill(64,64,15,1)
		fillp()
		circfill(64,64,10,0)
	end
	
	draw_shape(cube,t1/t_gap)
	draw_shape(cube2,t2/t_gap)
	draw_shape(cube3,t3/t_gap)
	
	if(show_outside_circ) circ(64,64,62,1)
	
	if btn(🅾️) or btn(❎) then
		fuzz(true)
	else
		fuzz(false)
	end	
end
flip()
goto ♥