<?php

declare(strict_types=1);

/*
 * Chill is a software for social workers
 *
 * For the full copyright and license information, please view
 * the LICENSE file that was distributed with this source code.
 */

namespace Chill\MainBundle\Templating\Listing;

use Symfony\Component\Form\FormFactoryInterface;
use Symfony\Component\HttpFoundation\RequestStack;

class FilterOrderHelperBuilder
{
    private array $checkboxes = [];

    private array $dateRanges = [];

    private ?array $searchBoxFields = null;

    /**
     * @var array<string, array{label: string}>
     */
    private array $singleCheckboxes = [];

    /**
     * @var array<string, array{label: string, class: class-string, choices: array, options: array}>
     */
    private array $entityChoices = [];

    /**
     * @var array<string, array{label: string, options: array}>
     */
    private array $userPickers = [];

    public function __construct(private readonly FormFactoryInterface $formFactory, private readonly RequestStack $requestStack) {}

    public function addSingleCheckbox(string $name, string $label): self
    {
        $this->singleCheckboxes[$name] = ['label' => $label];

        return $this;
    }

    public function addCheckbox(string $name, array $choices, ?array $default = [], ?array $trans = []): self
    {
        $this->checkboxes[$name] = ['choices' => $choices, 'default' => $default, 'trans' => $trans];

        return $this;
    }

    /**
     * @param class-string $class
     */
    public function addEntityChoice(string $name, string $label, string $class, array $choices, ?array $options = []): self
    {
        $this->entityChoices[$name] = ['label' => $label, 'class' => $class, 'choices' => $choices, 'options' => $options];

        return $this;
    }

    public function addDateRange(string $name, ?string $label = null, ?\DateTimeImmutable $from = null, ?\DateTimeImmutable $to = null): self
    {
        $this->dateRanges[$name] = ['from' => $from, 'to' => $to, 'label' => $label];

        return $this;
    }

    public function addSearchBox(?array $fields = [], ?array $options = []): self
    {
        $this->searchBoxFields = $fields;

        return $this;
    }

    public function addUserPicker(string $name, ?string $label = null, ?array $options = []): self
    {
        $this->userPickers[$name] = ['label' => $label, 'options' => $options];

        return $this;
    }

    public function build(): FilterOrderHelper
    {
        $helper = new FilterOrderHelper(
            $this->formFactory,
            $this->requestStack,
        );

        $helper->setSearchBox($this->searchBoxFields);

        foreach (
            $this->checkboxes as $name => [
                'choices' => $choices,
                'default' => $default,
                'trans' => $trans,
            ]
        ) {
            $helper->addCheckbox($name, $choices, $default, $trans);
        }

        foreach (
            $this->singleCheckboxes as $name => ['label' => $label]
        ) {
            $helper->addSingleCheckbox($name, $label);
        }

        foreach (
            $this->entityChoices as $name => ['label' => $label, 'class' => $class, 'choices' => $choices, 'options' => $options]
        ) {
            $helper->addEntityChoice($name, $class, $label, $choices, $options);
        }

        foreach (
            $this->dateRanges as $name => [
                'from' => $from,
                'to' => $to,
                'label' => $label,
            ]
        ) {
            $helper->addDateRange($name, $label, $from, $to);
        }

        foreach (
            $this->userPickers as $name => [
                'label' => $label,
                'options' => $options,
            ]
        ) {
            $helper->addUserPicker($name, $label, $options);
        }

        return $helper;
    }
}
