<?php

/*
 * ▓▒░
 * »«º×■·
 * ╔ ╚ ╝ ╗ ║ ═
 */

use Automata\NC;
use Automata\ToolData;

require_once __DIR__ . '/../vendor/autoload.php';

const W = 128;
const H = 96;

$nc = new NC();
$nc->TM->write(new ToolData(1, 5500, 2));
$nc->TM->write(new ToolData(2, 3000, 61379));
(new ProgramLoader)->loadPrograms($nc);

$nc->loadProgram(9002);

$xBuffer = [];
$zBuffer = [];
while ($nc->PPMC->ready()) {
	$startingPosition = new Vector2D($nc->DR->X, $nc->DR->Z);
	$centre = new Vector2D($nc->DR->I, $nc->DR->K);
	$nc->step();
	$endingPosition = new Vector2D($nc->DR->X, $nc->DR->Z);
	switch ($nc->DR->G_TRAVERSE) {
		case 2:
		case 3:
			// Circular
			$arc = new Arc2D($startingPosition, $endingPosition, $centre);
			dump($arc);
			readline();
		default:

	}

	$diff = $endingPosition->diff($startingPosition);

	readline();
	p($endingPosition);
	usleep(100000);
}

function p(Vector2D $v): void
{
	system('clear');
	$x = map($v->x, -1000 * W, 1000 * W, 0, W);
	$z = map($v->y, -1000 * H, 1000 * H, 0, H);
	print('╔' . str_repeat('═', W) . '╗' . PHP_EOL);    // Top
	print(str_repeat("║" . str_repeat(' ', W) . "║\n", $z - 1));
	print('║' . str_repeat(' ', $x - 1) . 'X' . str_repeat(' ', W - $x) . "║\n");
	print(str_repeat("║" . str_repeat(' ', W) . "║\n", H - $z));
	print('╚' . str_repeat('═', W) . '╝' . PHP_EOL); // Bottom
}

function map(int $x, int $in_min, int $in_max, int $out_min, int $out_max): int
{
	return ($x - $in_min) * ($out_max - $out_min) / ($in_max - $in_min) + $out_min;
}

class Vector2D
{
	public float $x;
	public float $y;


	public function __construct(float $x, float $y)
	{
		$this->x = $x;
		$this->y = $y;
	}


	public function length(): float
	{
		return sqrt($this->x ** 2 + $this->y ** 2);
	}


	public function diff(self $other): self
	{
		return new self(
			sqrt(($this->x - $other->x) ** 2),
			sqrt(($this->y - $other->y) ** 2)
		);
	}
}

class Arc2D
{
	public Vector2D $start;
	public Vector2D $end;
	public Vector2D $centre;


	public function __construct(Vector2D $start, Vector2D $end, Vector2D $centre)
	{
		$this->start = $start;
		$this->end = $end;
		$this->centre = $centre;
	}


	public function radius(): float
	{
		return $this->start->diff($this->centre)->length();
	}
}