<?php

declare(strict_types=1);

namespace Atdt\Screens;

use Atdt\Ansi;
use Atdt\Ctx;
use Atdt\In;
use Atdt\Screen;

/**
 * The HELP menu action (1.5.0): a two-page caller guide to the pipe
 * color codes and the MCI variables, with every color shown in itself.
 * SysOps place it anywhere with a HELP-action menu item.
 */
final class HelpScreen implements Screen
{
    public function describe(): string
    {
        return 'Reading the codes guide';
    }

    public function enter(Ctx $c): array
    {
        $c->set('page', 1);
        return $this->page($c);
    }

    public function input(Ctx $c, In $in): array
    {
        if ($in->kind !== 'key') {
            return [$c->bell()];
        }
        $key = strtoupper((string)$in->key);
        if ($key === 'Q' || $key === 'ESC') {
            return $c->pop();
        }
        if ((int)$c->get('page', 1) === 1) {
            $c->set('page', 2);
            return $this->page($c);
        }
        return $c->pop();
    }

    private function page(Ctx $c): array
    {
        $o = $c->out()->cls();
        $o->at(1, 1)->txt($c->center($c->tstr('help.title')));
        $o->at(2, 1)->fg(8)->txt($c->center(str_repeat('─', 60)))->reset();
        if ((int)$c->get('page', 1) === 1) {
            $this->pipePage($c, $o);
            $o->at(24, 1)->txt($c->center($c->tstr('help.more')));
        } else {
            $this->mciPage($c, $o);
            $o->at(24, 1)->txt($c->center($c->tstr('help.done')));
        }
        return [$c->ansi($o->reset()->str()), $c->hotkey()];
    }

    /** Every color code, shown in its own color (page one). */
    private function pipePage(Ctx $c, Ansi $o): void
    {
        $o->at(3, 3)->txt(\Atdt\Pipe::render(
            '|07Pipe codes color text: type |15||NN|07 in front of what you write.'
        ));
        $fg = [
            '00 Black', '01 Blue', '02 Green', '03 Cyan',
            '04 Red', '05 Magenta', '06 Brown', '07 Gray',
            '08 Dark gray', '09 Brt blue', '10 Brt green', '11 Brt cyan',
            '12 Brt red', '13 Brt magenta', '14 Yellow', '15 White',
        ];
        $row = 5;
        $o->at($row, 3)->txt(\Atdt\Pipe::render('|15Foreground |08(||00 to ||15)'));
        $row++;
        foreach (array_chunk($fg, 4) as $chunk) {
            $line = '';
            foreach ($chunk as $entry) {
                $code = substr($entry, 0, 2);
                $name = substr($entry, 3);
                // The sample paints itself; black gets a gray bed to be seen.
                $swatch = $code === '00' ? '|17|00' : '|' . $code;
                $line .= '|08||' . $code . ' ' . $swatch . str_pad($name, 12) . '|16|07  ';
            }
            $o->at($row++, 3)->txt(\Atdt\Pipe::render(rtrim($line)));
        }
        $row++;
        $o->at($row++, 3)->txt(\Atdt\Pipe::render('|15Background |08(||16 to ||23)'));
        $bg = ['16 Black', '17 Blue', '18 Green', '19 Cyan', '20 Red', '21 Magenta', '22 Brown', '23 Gray'];
        foreach (array_chunk($bg, 4) as $chunk) {
            $line = '';
            foreach ($chunk as $entry) {
                $code = substr($entry, 0, 2);
                $name = substr($entry, 3);
                $line .= '|08||' . $code . ' |' . $code . '|15 ' . str_pad($name, 10) . ' |16|07  ';
            }
            $o->at($row++, 3)->txt(\Atdt\Pipe::render(rtrim($line)));
        }
        $row++;
        $o->at($row++, 3)->txt(\Atdt\Pipe::render('|07Type |15||||07 for a plain | character. Example: |15||12hello|07 makes |12hello|07.'));
        $allowed = $c->settings()->bool('allow_user_color', false);
        $o->at($row + 1, 3)->txt(\Atdt\Pipe::render($allowed
            ? '|10On this board your own colors work|07 in messages, mail, chat, oneliners,'
            : '|08On this board caller colors are switched off: codes will show as typed.'));
        if ($allowed) {
            $o->at($row + 2, 3)->txt(\Atdt\Pipe::render('|07rumors, and the auto-message. Board screens are always colored.'));
        }
    }

    /** The MCI variables (page two). */
    private function mciPage(Ctx $c, Ansi $o): void
    {
        $o->at(3, 3)->txt(\Atdt\Pipe::render(
            '|07MCI codes are live substitutions: write |15%HN|07 and every reader sees'
        ));
        $o->at(4, 3)->txt(\Atdt\Pipe::render('|07their own values filled in, wherever text or art is shown.'));
        $mci = [
            ['%HN', 'your handle'],
            ['%LV', 'your level'],
            ['%ND', 'your node number'],
            ['%BN', 'the board name'],
            ['%PH', 'the board phone number'],
            ['%VN', 'the BBS software version'],
            ['%DT', 'the date (board clock)'],
            ['%TM', 'the time (board clock)'],
            ['%CT', 'calls today'],
            ['%CA', 'calls ever'],
            ['%LC', 'the last caller'],
            ['%UT', 'total user accounts'],
            ['%AN', 'the current message area'],
            ['%AD', "that area's description"],
            ['%MC', 'messages in that area'],
            ['%BD', 'your connection speed (FAST when unthrottled)'],
        ];
        $row = 6;
        foreach (array_chunk($mci, 2) as $pair) {
            $line = '';
            foreach ($pair as [$code, $desc]) {
                $line .= '|14' . $code . ' |07' . str_pad($desc, 30) . ' ';
            }
            $o->at($row++, 5)->txt(\Atdt\Pipe::render(rtrim($line)));
        }
        $row++;
        $o->at($row++, 3)->txt(\Atdt\Pipe::render('|07They work in messages, chat, the wall texts, and even inside ANSI'));
        $o->at($row++, 3)->txt(\Atdt\Pipe::render('|07art. An unknown %-pair is left exactly as you typed it.'));
        $o->at($row + 1, 3)->txt(\Atdt\Pipe::render('|08Try one in a message: write "hi %HN" and watch it greet each reader.'));
    }
}
