<?php

namespace Planaday\Html\Tags\Admin\Form\OptionGroupArea;

use Planaday\Config\OptionGroups\OptionGroup;
use Planaday\Html\Tags\Admin\Form\AdminOptionInput\AdminOptionInput;
use Planaday\Html\Tags\Form\SelectableDataInputFieldTag;
use Planaday\Html\Tags\Tag;
use Planaday\Utility\DependencyInjection\ComponentRegistry;
use Planaday\Utility\DependencyInjection\InjectionImpossibleException;

class OptionGroupArea extends SelectableDataInputFieldTag {
	const TAG = 'admin-form-option-group-area';
	const DEFAULT_TEMPLATE = 'optionGroup';
	const OPTION_GROUP_ARRAY_CONTEXT = 'optionGroup';
	const OPTION_GROUP_INDEX_ATTRIBUTE = self::ATTRIBUTE_PREFIX . 'option-group-index';

	/**
	 * @param ComponentRegistry $registry
	 *
	 * @throws InjectionImpossibleException
	 */
	public function __construct(ComponentRegistry $registry) {
		parent::__construct(__DIR__, self::DEFAULT_TEMPLATE, $registry);
	}

	public function buildTag(): string {
		$optionGroupArray = $this->context[self::OPTION_GROUP_ARRAY_CONTEXT] ?? null;
		$index = $this->attributes[self::OPTION_GROUP_INDEX_ATTRIBUTE] ?? null;

		if (!is_array($optionGroupArray)){
			$this->logError(self::TAG . ' was called without array in optionGroupArray context');
			return '';
		}
		if ($index === null){
			$this->logError(self::TAG . ' was called without a valid index');
			return '';
		}
		if (!isset($optionGroupArray[$index])){
			$this->logError(self::TAG . ' was called without the anything at index ' . $index);
			return '';
		}
		if (!$optionGroupArray[$index] instanceof OptionGroup){
			$this->logError(self::TAG . ' was called with the wrong type at index ' . $index);
			return '';
		}

		$optionGroup = $optionGroupArray[$index];

		$this->attributes[self::FIELD_NAME_ATTRIBUTE] = $optionGroup->getIndex() ?? '';

		$this->logInfo(self::TAG . ' was called for ' . $optionGroup->getIndex());

		$parser = $this->getNewParser();

		if (in_array('submit', $this->postEntities->getActions())){
			$parser->setCondition('success-block', true);
			$parser->setData('successMessage', 'Instellingen succesvol opgeslagen');
		}

		$parser->addContext(self::OPTION_GROUP_ARRAY_CONTEXT, $optionGroup->getLayout());
		$parser->setUnsafeData('option-group-area', $this->getTags($optionGroup));
		$parser->setUnsafeData('option-group-tabs', $this->getHeaders($optionGroup));
		$parser->setData('title', $optionGroup->getName());
		$parser->setUnsafeData('description', $optionGroup->getDescription());

		$errors = $this->getErrorMessage(0);
		if ($optionGroup->getIndex() === null) {
			$errors = null;
			$parser->setData('error-class', '');
		}
		if (($this->attributes[self::TEMPLATE_ATTRIBUTE] ?? null) === 'optionGroupPage' && $errors !== null) {
			$errors .= "<style>.pad-option-group-tab-{$optionGroup->getIndex()} a{color:red;}</style>";
		}
		$parser->setUnsafeData('error-message', $errors ?? null);

		$parser->addStylesheet($this->getStylePath());

		return $parser->parse($this->getTemplate());
	}

	private function getTags(OptionGroup $optionGroup): string {
		$tags = '';

		foreach ($optionGroup->getLayout() as $key => $option){
			$attr = [
				OptionGroupArea::OPTION_GROUP_INDEX_ATTRIBUTE => $key
			];

			if ($option instanceof OptionGroup){
				$tag = OptionGroupArea::TAG;
				if (($this->attributes[self::TEMPLATE_ATTRIBUTE] ?? null) === 'optionGroupTabs') {
					$attr[self::TEMPLATE_ATTRIBUTE] = 'optionGroupPage';
				}
			} else {
				$tag = AdminOptionInput::TAG;
			}

			if (($this->attributes[self::TEMPLATE_ATTRIBUTE] ?? null) === 'optionGroupTabs') {
				$tags .= "<div id='pad-option-group-tab-$key-{{pad-uniqueId}}'>" . Tag::getParsableTag($tag, $attr) . "</div>";
			} else {
				$tags .= Tag::getParsableTag($tag, $attr);
			}
		}

		return $tags;
	}

	private function getHeaders(OptionGroup $optionGroup):string {
		$tags = '';

		foreach ($optionGroup->getLayout() as $key => $option){
			if ($option instanceof OptionGroup){
				$tags .= "<li class='pad-option-group-tab-{$option->getIndex()}'><a href='#pad-option-group-tab-$key-{{pad-uniqueId}}'>" . $option->getName() . "</a></li>";
			}
		}

		return $tags;
	}
}