program GoodOldPlasma;
@use "system/screen"
var
	time : byte;
	// Sqrt table	
	
	const width : byte = 40;
	const height : byte = 25;
	
	// some plasma variables
	val,c2x, c2y,ax, ay,c : byte;
	x,y : byte;
	colorP: ^byte; // same as "pointer" or "pointer of byte";	

	sin : array[256] of byte = buildsinetable(127);
	cols : array[31] of byte = buildsinetable(15);

// charset will be placed at $2000 in bank 1	
	const charsetLocation: address = $2000;
 // look in the character set
 	const baseCharacter:byte = $68;
 	
	// Custom c64 charset
	@export "charsets/charset.flf" "charsets/charset.bin" 256
	// Include it
	charset : incbin("charsets/charset.bin");
	

	// mini sine table
    siny : array[height] of byte; 
	sinx : array[width] of byte; 

	// Lookup table for division by 16
	lookupDiv16 : array[256] of byte = buildtable("i/16");

	ptr : ^byte;


	const yStart:byte = 0;
	const yEnd:byte = 25;
	const xStart:byte = 0;
	const xEnd:byte = 40;



// Plasma procedure

procedure Plasma();
begin
	c2x:=ax;
	c2y:=ay;
	
	// Set up y-sine table
	for x:=0 to height unroll do begin 
		siny[x]:=  sin[c2x] + sin[c2y];
		c2x:=c2x+4;
		c2y:=c2y+9;
	end;

	ax:=ax+3;
	ay:=ay-5;

	// Set up x-sine table
	for x:=0 to width unroll do begin 
		sinx[x] := sin[c2x] + sin[c2y];
		c2x:=c2x+3;
		c2y:=c2y+7;

	end;
	
	
		Screen::out(Screen::cursor_home);
	
	for y:=yStart to yEnd offpage do 
	begin
		val:=siny[y];
		for x:=xStart to xEnd offpage do 
		begin
		
			// here, we take (sin[x]+val) and divide by 16. However, since this is a slow procedure,
			// we have created a lookup table instead!
			c:=lookupDiv16[ (sinx[x] +val) ];
			// Set the screen memory
			Screen::SetTextCol(cols[c]);
			Screen::out(c+128);
			// Set color memory
		end;
		// Increase screen memory pointer by 40 (next row)
		ptr+=width;
		// Increase color pointer by 40 (next row)
	end;

end;

	
begin
		
	Screen::SetMode(Screen::mode_320_200_64);
	Screen::DisableCursor();	

	Screen::LoadCharset(#charset + 8*64, 16, 128);
	


	ax:=1;
	ay:=5;

	// Clear screen and color memory
	// Main loop
	while (true) do begin
		Plasma();
	end;


end.