# Copyright (C) 2022 Thomas Hoppe (h0bB1T). All rights reserved.
#
# Unauthorized copying of this file via any medium is strictly prohibited.
# Proprietary and confidential.

import os

from typing import List

from .common import is_image
from .gray_directory import GrayDirectory
from .gray_entry import GrayEntry
from .abstract_scanner import AbstractScanner


class GrayLinearScanner:
    """
    Scans gray images (including 4 channel packed)
    recursively from directory.
    """
    @staticmethod
    def scan(path: str) -> List[GrayDirectory]:
        t = GrayDirectory('<ROOT>', path)
        GrayLinearScanner._scan_path(t)

        # Flatten to list.
        r = [] # type: List[GrayDirectory]
        AbstractScanner.flatten(t, r, [], True)
        r = sorted(r, key=lambda d: d.name)

        return r
        

    @staticmethod
    def _scan_path(dir: GrayDirectory):
        """
        Recursively scan all paths for gray textures.
        """
        # Loop over all content entries.
        for _f in os.listdir(dir.path):
            # Full path.
            f = os.path.join(dir.path, _f)

            # Whether it's a file or dir, either store file
            # or scan recursively.
            if os.path.isfile(f):
                # Filter, so just gray images (no previews) are in the list.
                n, ex = os.path.splitext(_f)

                # Image file?
                if is_image(ex.lower()): 
                    # Is no preview image?
                    if not ('@' in n or n.lower().endswith('_preview')):
                        # Yes, seems to be a valid entry.
                        # Check if this is a special 4-channel packed entry.
                        # Either those from material wizard or SNW grunge pack
                        # naming convention.
                        g4file = f + '.4g'
                        if os.path.exists(g4file) or os.path.splitext(f)[0].endswith('-4g'):
                            for i in range(4):
                                dir.entries.append(GrayEntry(
                                    f'{n}@{i + 1}',
                                    os.path.join(dir.path, f'{n}@{i + 1}.jpg'),
                                    f,
                                    i
                                ))
                        else:
                            dir.entries.append(GrayEntry(
                                n,
                                os.path.join(dir.path, f'{n}_preview.jpg'),
                                f
                            ))

            elif os.path.isdir(f):
                d = GrayDirectory(_f, f)
                GrayLinearScanner._scan_path(d)
                # Add only if contains at least on element.
                if not d.empty():
                    dir.subdirs.append(d)

        # Finally sort items.
        dir.entries = sorted(dir.entries, key=lambda d: d.name)
