<?php

namespace apexl\Io\modules\display\pages;

use apexl\Io\includes\HookManager;
use apexl\Io\includes\System;
use apexl\Io\modules\admin\enums\permissions\Admin;
use apexl\Io\modules\display\ComponentFactory\FilterableMenusComponentFactory;
use apexl\Io\modules\display\ComponentFactory\MenuComponentFactory;
use apexl\Io\modules\display\components\AccountTile;
use apexl\Io\modules\display\components\DropdownMenu;
use apexl\Io\modules\display\components\HorizontalMenu;
use apexl\Io\modules\display\components\ImageTile;
use apexl\Io\modules\display\components\RowWrapper;
use apexl\Io\modules\display\components\TitleTile;
use apexl\Io\modules\display\includes\Page;
use apexl\Io\modules\display\regions\AdminMenuRegion;
use apexl\Io\modules\display\regions\ContentRegion;
use apexl\Io\modules\display\regions\LeftSideBarRegion;
use apexl\Io\modules\display\regions\PageContentRegion;
use apexl\Io\modules\display\regions\TopBarRegion;
use apexl\Io\services\VariableManager;
use app\module\newtonsTrailers\Enum\Menu;
use Exception;

class genericPageLeftMenu extends Page
{
    public const string HOOK__MENUS = 'genericPageLeftMenu.menus';
    public const string HOOK__MENUS_FILTERABLE = 'genericPageLeftMenu.menusFilterable';

    protected bool $hasImageTileInLeftSidebar = true;
    protected bool $hasAccountTileInLeftSidebar = true;
    protected bool $hasAdminMenuInTopBar = true;

    public function __construct(
        private readonly FilterableMenusComponentFactory $filterableMenusComponentFactory,
        private readonly MenuComponentFactory $menuComponentFactory,
        private readonly HookManager $hookManager,
        private readonly VariableManager $variableManager
    ) {
        parent::__construct();
    }

    /**
     * @param $component
     * @param null $weight
     */
    public function addToTopBar($component, $weight = null)
    {
        $this->addToRegion($component, "TopBarRegion", $weight);
    }

    /**
     * @param $component
     * @param null $weight
     */
    public function addToLeftSidebar($component, $weight = null)
    {
        $this->addToRegion($component, "LeftSideBarRegion", $weight);
    }

    /**
     * build the wrapper, specify some default "regions" that can be populated with components.
     *
     * Page structure by default looks like this:
     *  The page content
     *  |------------------------------------------------
     *  | The Top Menu bar
     *  | - Image region -- Menu region --
     *  |------------------------------------------------
     *  | - The Left Sidebar -- | Main content area
     *  |                       | Title Tile
     *  |                       | Main content
     *  | -----------------------------------------------
     *  | - The footer
     *  | -----------------------------------------------
     * @throws Exception
     */
    protected function buildRegions()
    {
        $this->registerTitleComponent(
            $this->componentFactory
                ->make(TitleTile::class, ['page' => $this])
                ->addBreadcrumbs($this->menuManager->getMenu())
        );

        //reset the regions, we have only content as a default.
        $this->globalRegion = new PageContentRegion()->addWrapperClass('page-left-menu row m-0');

        if ($this->currentUser->isAllowed(Admin::ADMINISTER) && (System::getVariable(
                'core_display_admin_menu'
            ) ?? true)) {

            if ($this->hasAdminMenuInTopBar) {
                $this->globalRegion->addWrapperClass('showing-admin-menu');
                $this->addAdminMenu();
            }
        }

        $this->addLeftSidebarRegion();
        $this->addContentRegion();

    }

    protected function addAdminMenu(): void
    {
        $this->globalRegion->addRegion(
            new AdminMenuRegion([
                $this->menuComponentFactory->make(
                    menuItems: $this->menuManager->getAllItemsAsMenu($this->currentUser, Menu::ADMINISTRATION),
                    menuClass: HorizontalMenu::class
                )
                    ->setId("TopBarAdminMenu")
                    ->addClass('col'),
            ])->addWrapperClass('administration-menu')
        );

    }

    protected function addLeftSidebarRegion(): void
    {
        $components = [];
        if ($this->hasImageTileInLeftSidebar) {
            $components[] = $this->componentFactory->make(ImageTile::class)
                ->src($this->variableManager->get('generic_page_logo_url') ?? '/assets/logos/logo.svg');
        }

        if ($this->hasAccountTileInLeftSidebar) {
            $components[] = $this->componentFactory->make(AccountTile::class)
                ->name($this->currentUser->getNiceName());
        }

        $this->globalRegion->addRegions([
            new LeftSideBarRegion([
                ...$components,
                $this->filterableMenusComponentFactory->make(
                    $this->leftSidebarRegionMenus(),
                    $this->hookManager->processHook(self::HOOK__MENUS_FILTERABLE, true)
                ),
            ])->clearWrapperClasses()->addWrapperClass('col col-3'),
        ]);
    }

    protected function leftSidebarRegionMenus(): array
    {
        return $this->hookManager->processHook(
            genericPageLeftMenu::HOOK__MENUS,
            [
                $this->menuComponentFactory->make(
                    $this->menuManager->getAllItemsAsMenu($this->currentUser),
                    'Navigation'
                )
            ],
            $this->menuManager
        );
    }

    protected function addContentRegion(): void
    {
        $this->globalRegion->addRegions([
            new ContentRegion([
                new TopBarRegion([
                    $this->componentFactory->make(RowWrapper::class)->addClass('col')
                        ->addComponent($this->titleTile->addClass('row')),
                    $this->menuComponentFactory->make(
                        title: $this->currentUser->getNiceName(),
                        menuClass: DropdownMenu::class
                    )
                        ->addMenuByName("Account Menu")
                        ->addIcon("user-circle")
                        ->addClass('col top-bar-user-menu'),
                ])->addWrapperClass('content-no-bg'),
            ])->clearWrapperClasses()->addWrapperClass('col'),
        ]);

    }
}
