<?php
namespace PHPFUI;
class Menu extends \PHPFUI\HTML5Element
{
protected array $menuItems = [];
protected array $menuLabels = [];
protected bool $sorted = false;
private bool $started = false;
private string $type = '';
public function __construct()
{
parent::__construct('ul');
$this->addClass('menu');
}
public function addMenuItem(\PHPFUI\MenuItem $item) : static
{
$name = $item->getName() . ':' . \count($this->menuItems);
$this->menuItems[$name] = $item;
$this->menuLabels[$name] = $item->getName();
return $this;
}
public function addSubMenu(\PHPFUI\MenuItem $item, \PHPFUI\Menu $subMenu) : static
{
$subMenu->addClass('nested');
$name = $item->getName() . ':' . \count($this->menuItems);
$this->menuItems[$name] = $subMenu;
$this->menuLabels[$name] = $item->getName();
return $this;
}
public function count() : int
{
return \count($this->menuItems);
}
public function getActive() : bool
{
foreach ($this->menuItems as $menuItem)
{
if ($menuItem->getActive())
{
return true;
}
}
return false;
}
public function getMenuItems() : array
{
return $this->menuItems;
}
public function getName() : string
{
return 'Menu';
}
public function setActiveLink(string $link) : bool
{
foreach ($this->menuItems as &$menuItem)
{
if ($menuItem instanceof \PHPFUI\MenuItem)
{
if ($menuItem->getLink() == $link)
{
$menuItem->setActive();
return true;
}
}
elseif ($menuItem->setActiveLink($link))
{
return true;
}
}
return false;
}
public function setActiveName(string $name) : bool
{
foreach ($this->menuItems as &$menuItem)
{
if ($menuItem->getName() == $name)
{
$menuItem->setActive();
return true;
}
}
return false;
}
public function setIconAlignment(string $type) : static
{
$types = ['top',
'right',
'bottom',
'left', ];
if (! \in_array($type, $types))
{
throw new \Exception(__METHOD__ . ' Error: Icon type {$type} should be one of ' . \implode('', $types));
}
$this->addClass('icons');
$this->addClass('icon-' . $type);
$this->type = $type;
return $this;
}
public function sort() : static
{
$this->sorted = true;
\ksort($this->menuItems);
return $this;
}
public function walk(string $method, mixed $argument = null) : static
{
foreach ($this->menuItems as $item)
{
if (\method_exists($item, $method))
{
if (null !== $argument)
{
\call_user_func([$item, $method], $argument);
}
else
{
\call_user_func([$item, $method]);
}
}
if ($item instanceof \PHPFUI\Menu)
{
$item->walk($method, $argument);
}
}
return $this;
}
protected function getStart() : string
{
if (! $this->started)
{
$this->started = true;
$somethingActive = 0;
if ($this->sorted)
{
\ksort($this->menuItems);
}
foreach ($this->menuItems as $label => $item)
{
if ($item instanceof \PHPFUI\MenuItem)
{
$somethingActive |= (int)$item->getActive();
if ($this->type)
{
$item->setAlignment($this->type);
}
$this->add($item);
}
else
{
$menuItem = new \PHPFUI\MenuItem($this->menuLabels[$label], '#');
$somethingActive |= (int)$item->getActive();
$menuItem->setActive($item->getActive());
$menuItem->add($item);
$this->add($menuItem);
}
}
if ($somethingActive)
{
$this->addClass('is-active');
}
}
return parent::getStart();
}
}