<?php

declare(strict_types=1);

namespace PHPNative\Tailwind;

use PHPNative\Tailwind\Model\Size;
use PHPNative\Tailwind\Model\StyleCollection;
use PHPNative\Tailwind\Style\Style;

class StyleParser
{
    private static array $cache = [];

    public static function parse($style): StyleCollection
    {
        $computed = new StyleCollection();
        if($style === null) {
            return $computed;
        }
        $normalized = trim(preg_replace('/\s+/', ' ', $style));
        if ($normalized === '') {
            return $computed;
        }

        if (isset(self::$cache[$normalized])) {
            return clone self::$cache[$normalized];
        }

        $styles = explode(" ", $normalized);

        foreach($styles as $styleStr) {
            $styleStr = trim($styleStr);

            $style = self::parseSimpleStyle($styleStr);

            // Skip if style is not recognized
            if($style === null) {
                continue;
            }

            $s = new \PHPNative\Tailwind\Model\Style($style);
            $mq = \PHPNative\Tailwind\Parser\MediaQuery::parse($styleStr);
            if($mq) {
                $s->mediaQuery = $mq;
            }
            $state = \PHPNative\Tailwind\Parser\State::parse($styleStr);
            if($state) {
                $s->state = $state;
            }
            $computed->add($s);
        }

        self::$cache[$normalized] = clone $computed;

        return $computed;
    }

    public static function clearCache(): void
    {
        self::$cache = [];
    }

    private static function parseSimpleStyle(string $style): ?Style
    {
        // Shadow must be parsed before Width to avoid "shadow-*" being matched as "w-*"
        if($s = \PHPNative\Tailwind\Parser\Shadow::parse($style)) {
            return $s;
        }
        if($pd = \PHPNative\Tailwind\Parser\Padding::parse($style)) {
            return $pd;
        }
        if($m = \PHPNative\Tailwind\Parser\Margin::parse($style)) {
            return $m;
        }
        if($g = \PHPNative\Tailwind\Parser\Gap::parse($style)) {
            return $g;
        }
        if($o = \PHPNative\Tailwind\Parser\Overflow::parse($style)) {
            return $o;
        }
        if($w = \PHPNative\Tailwind\Parser\Width::parse($style)) {
            return $w;
        }
        if($h = \PHPNative\Tailwind\Parser\Height::parse($style)) {
            return $h;
        }
        if($b = \PHPNative\Tailwind\Parser\Basis::parse($style)) {
            return $b;
        }
        if($f = \PHPNative\Tailwind\Parser\Flex::parse($style)) {
            return $f;
        }
        if($bg = \PHPNative\Tailwind\Parser\Background::parse($style)) {
            return $bg;
        }
        if($t = \PHPNative\Tailwind\Parser\Text::parse($style)) {
            return $t;
        }
        if($b = \PHPNative\Tailwind\Parser\Border::parse($style)) {
            return $b;
        }

        return null;
    }
}
