<?php

namespace Planaday\Html\NodeTags\Course\ListTag;

use Planaday\Config\Course\General\GeneralSettings;
use Planaday\Entities\Course\CourseUtility;
use Planaday\Entities\Course\DTO\Course;
use Planaday\Html\Nodes\NodeData;
use Planaday\Html\NodeTags\Course\ListItem\CourseListItemSettings;
use Planaday\Html\NodeTags\Course\ListShortcode\CourseListShortcodeSettings;
use Planaday\Html\NodeTags\Course\ListTag\TemplateSettings\CalendarTemplateSettings;
use Planaday\Html\NodeTags\Tag;
use Planaday\Html\NodeTags\TemplateOnlyTag;
use Planaday\Html\Parsers\NodeParsers\TagMarkers\RefreshUniqueId;
use Planaday\Html\Parsers\NodeParsers\TagMarkers\TestDataTag;
use Planaday\Utility\DependencyInjection\Attributes\Transient;
use Traversable;

#[Transient]
class ListTag implements Tag, RefreshUniqueId, TestDataTag {
	use TemplateOnlyTag;

	public function __construct(
		protected CourseUtility $courseUtility,
		protected GeneralSettings $generalSettings,
		protected CalendarTemplateSettings $calendarSettings,
		protected CourseListShortcodeSettings $courseListSettings,
		protected CourseListItemSettings $courseListItemSettings
	) {
		$this->config = [
			"showDayPartsCount" => $this->courseListItemSettings->isShowDayPartCount(...),
			"showPrice"         => $this->courseListItemSettings->isShowPrice(...),
			"showDetailButton"  => $this->courseListItemSettings->isShowCourseButton(...),
			"showLocation"      => $this->courseListItemSettings->isShowFirstLocation(...),
			"showMouseoverText" => $this->calendarSettings->isShowMouseoverText(...),
			"showAllDayParts"   => $this->calendarSettings->isShowAllDayParts(...),
			"limit"             => $this->courseListSettings->getLimit(...),
		];
	}

	protected function prepareData( $nodeData ): void {
		$nodeData->data["calendarData"] ??= function () use ($nodeData) {
			return $this->buildCalendarData($nodeData);
		};
	}

	public function getTagDir(): string {
		return __DIR__;
	}

	protected function buildCalendarData(NodeData $nodeData):string {
		$courses = $nodeData->data["courses"] ?? [];
		$showAllDayParts = $this->calendarSettings->isShowAllDayParts();
		$eLearningCountAsStart = $this->generalSettings->isELearningCountsAsStart();

		if ( ! $courses instanceof Traversable && !is_array( $courses )) {
			$this->logError("Courses is not an array or Traversable");
			return '{}';
		}

		$dataArray = [];
		/** @var Course $course */
		foreach ( $courses as $course ) {
			if ($showAllDayParts){
				$dayParts = $course->getDayParts();
			} else {
				$dayParts = [$course->getEarliestDayPart($eLearningCountAsStart)];
			}

			foreach ($dayParts as $dayPart) {
				$location = $dayPart->getLocations()[0] ?? null;

				$start = $dayPart->getStartTime()->format("H:i:s");
				$end   = $dayPart->getEndTime()->format("H:i:s");

				$calenderDate = $dayPart->getStartTime()->format('Y-m-d');
				$date         = $dayPart->getStartTime()->format('d-m-Y');
				$description  = "<b> " . $course->getName() . ": " . $dayPart->getName() . "</b><br>" . "Begint op " . $date . " (" . $start . " - " . $end . ")<br />Locatie: " . ( $location?->getCity() ?? '-' );

				$dataArray[]  = [
					"title"       => $course->getName() . ": " . $dayPart->getName() . " in " . ( $location?->getCity() ?? '-' ),
					"description" => $description,
					"allDay"      => false,
					"start"       => $calenderDate . "T" . $start,
					"end"         => $calenderDate . "T" . $end,
					"editable"    => false,
					"url"         => $this->courseUtility->getDetailLink($course)
				];
			}
		}

		return json_encode($dataArray);
	}

	public function injectTestData(): void {
		$this->nodeData->data["calendarData"] = function () {
			$this->nodeData->data["courses"] = [];
			return $this->buildCalendarData($this->nodeData);
		};
	}
}