<?php
namespace PHPFUI;
class HTML5Element extends \PHPFUI\Base
{
private array $attributes = [];
private array $classes = [];
private string $element = '';
private ?string $id = null;
private static array $masterId = [];
private bool $noEndTag = false;
private static array $noEndTags = [
'area' => true,
'base' => true,
'br' => true,
'col' => true,
'command' => true,
'embed' => true,
'hr' => true,
'img' => true,
'input' => true,
'keygen' => true,
'link' => true,
'meta' => true,
'param' => true,
'source' => true,
'track' => true,
'wbr' => true,
];
private string | \PHPFUI\ToolTip | null $tooltip = null;
public function __construct(string $element)
{
parent::__construct();
$this->element = \strtolower($element);
$this->noEndTag = isset(self::$noEndTags[$this->element]);
}
public function __clone()
{
if ($this->hasId())
{
$this->newId();
}
parent::__clone();
}
public function addAttribute(string $attribute, string $value = '') : static
{
if (! isset($this->attributes[$attribute]))
{
$this->attributes[$attribute] = (string)$value;
}
else
{
$this->attributes[$attribute] .= " {$value}";
}
return $this;
}
public function addClass(string $class) : static
{
foreach (\explode(' ', $class) as $oneClass)
{
if ($oneClass)
{
$this->classes[$oneClass] = true;
}
}
return $this;
}
public function addPHPClassName() : static
{
$parts = \explode('\\', static::class);
$this->classes[\array_pop($parts)] = true;
return $this;
}
public function deleteAttribute(string $attribute) : static
{
unset($this->attributes[$attribute]);
return $this;
}
public function deleteAttributes() : static
{
$this->attributes = [];
return $this;
}
public function deleteClass(string $classToDelete) : static
{
unset($this->classes[$classToDelete]);
return $this;
}
public function disabled() : static
{
$this->addClass('disabled');
return $this;
}
public function getAttribute(string $attribute) : ?string
{
return $this->attributes[$attribute] ?? null;
}
public function getAttributes() : string
{
$output = '';
foreach ($this->attributes as $type => $value)
{
if (! \strlen(\trim($value)))
{
$output .= ' ' . $type;
}
else
{
$output .= " {$type}='{$value}'";
}
}
return $output;
}
public function getClass() : string
{
if (\count($this->classes))
{
return " class='" . \implode(' ', \array_keys($this->classes)) . "'";
}
return '';
}
public function getClasses() : array
{
return \array_keys($this->classes);
}
public function getElement() : string
{
return $this->element;
}
public function getId() : string
{
if (null === $this->id)
{
$this->newId();
}
return $this->id;
}
public function getIdAttribute() : string
{
if (! $this->hasId())
{
return '';
}
return " id='{$this->id}'";
}
public function getToolTip(string $label) : string | \PHPFUI\ToolTip
{
$toolTip = $label;
if ($this->tooltip)
{
if ('string' == \gettype($this->tooltip))
{
$toolTip = new \PHPFUI\ToolTip($label, $this->tooltip);
}
else
{
$toolTip = $this->tooltip;
$toolTip->add($label);
}
}
return $toolTip;
}
public function hasClass(string $class) : bool
{
return isset($this->classes[$class]);
}
public function hasId() : bool
{
return null !== $this->id;
}
public function hasToolTip() : bool
{
return null !== $this->tooltip;
}
public function newId() : static
{
$parts = \explode('\\', static::class);
$class = \array_pop($parts);
self::$masterId[$class] ??= 0;
$this->id = $class . ++self::$masterId[$class];
return $this;
}
public function setAttribute(string $attribute, string $value = '') : static
{
$this->attributes[$attribute] = (string)$value;
return $this;
}
public function setConfirm($text) : static
{
$this->addAttribute('onclick', "return window.confirm(\"{$text}\");");
return $this;
}
public function setElement($element) : static
{
$this->element = $element;
$this->noEndTag = isset(self::$noEndTags[\strtolower($element)]);
return $this;
}
public function setId($id) : static
{
$this->id = $id;
return $this;
}
public function setToolTip(string | \PHPFUI\ToolTip $tip) : static
{
$this->tooltip = $tip;
return $this;
}
public function toggleAnimate(\PHPFUI\HTML5Element $element, string $animation) : static
{
$this->addAttribute('data-toggle', $element->getId());
$this->addAttribute('aria-controls', $element->getId());
$this->setAttribute('aria-expanded', 'true');
$element->addAttribute('data-toggler');
$element->addAttribute('data-animate', $animation);
return $this;
}
public function toggleClass(\PHPFUI\HTML5Element $element, string $class) : static
{
$this->addAttribute('data-toggle', $element->getId());
$this->addAttribute('aria-controls', $element->getId());
$this->setAttribute('aria-expanded', 'true');
$element->addAttribute('data-toggler', $class);
return $this;
}
public function transferAttributes(\PHPFUI\HTML5Element $from) : static
{
$this->attributes = \array_merge($this->attributes, $from->attributes);
$from->attributes = [];
return $this;
}
public function transferClasses(\PHPFUI\HTML5Element $from) : static
{
$this->classes = \array_merge($this->classes, $from->classes);
$from->classes = [];
return $this;
}
protected function getBody() : string
{
return '';
}
protected function getEnd() : string
{
return (! $this->element || $this->noEndTag) ? '' : "</{$this->element}>";
}
protected function getStart() : string
{
if (! $this->element)
{
return '';
}
$output = "<{$this->element}";
$output .= $this->getIdAttribute();
$output .= $this->getClass();
$output .= $this->getAttributes();
return $output . '>';
}
protected function upCastCopy(\PHPFUI\HTML5Element $to, HTML5Element $from) : object
{
$returnValue = clone $to;
foreach ($to as $key => $value)
{
$returnValue->{$key} = $from->{$key};
}
return $returnValue;
}
}