import os
from omni import ui
from .icons import Icons
from .filebrowser import FileBrowserSelectionType, FileBrowserMode
from .file_picker import FilePicker


class CollectMainWindow:
    def __init__(self, collect_button_fn=None, cancel_button_fn=None):
        self._collect_button_fn = collect_button_fn
        self._cancel_button_fn = cancel_button_fn
        self._file_picker = None
        self._collection_path_field = None
        self._build_content_ui()

    def destroy(self):
        self._collect_button_fn = None
        self._cancel_button_fn = None
        self._collection_path_field = None
        if self._file_picker:
            self._file_picker.destroy()
            self._file_picker = None
        if self._cancel_button:
            self._cancel_button.set_clicked_fn(None)
            self._cancel_button = None
        if self._collect_button:
            self._collect_button.set_clicked_fn(None)
            self._collect_button = None
        if self._folder_button:
            self._folder_button.set_clicked_fn(None)
            self._folder_button = None
        self._window = None

    def set_collect_fn(self, collect_fn):
        self._collect_button_fn = collect_fn

    def set_cancel_fn(self, cancel_fn):
        self._cancel_button_fn = cancel_fn

    def _build_content_ui(self):
        self._window = ui.Window(
            "Collection Options", visible=False, height=0, dockPreference=ui.DockPreference.DISABLED
        )
        self._window.flags = (
            ui.WINDOW_FLAGS_NO_COLLAPSE
            | ui.WINDOW_FLAGS_NO_RESIZE
            | ui.WINDOW_FLAGS_NO_SCROLLBAR
            | ui.WINDOW_FLAGS_NO_RESIZE
            | ui.WINDOW_FLAGS_NO_MOVE
        )

        self._window.flags = self._window.flags | ui.WINDOW_FLAGS_MODAL

        def _build_option_checkbox(text, default_value, identifier, tooltip=None):
            stack = ui.HStack(height=0, width=0)
            with stack:
                checkbox = ui.CheckBox(width=20, identifier=identifier, style={"font_size": 16})
                checkbox.model.set_value(default_value)
                ui.Label(text, alignment=ui.Alignment.LEFT)
                if tooltip:
                    stack.set_tooltip(tooltip)

            return checkbox

        style = {
            "Rectangle::hovering": {"background_color": 0x0, "border_radius": 2, "margin": 0, "padding": 0},
            "Rectangle::hovering:hovered": {"background_color": 0xFF9E9E9E},
            "Button.Image::folder": {"image_url": Icons().get("folder")},
            "Button.Image::folder:checked": {"image_url": Icons().get("folder")},
            "Button::folder": {"background_color": 0x0, "margin": 0},
            "Button::folder:checked": {"background_color": 0x0, "margin": 0},
            "Button::folder:pressed": {"background_color": 0x0, "margin": 0},
            "Button::folder:hovered": {"background_color": 0x0, "margin": 0},
        }

        self._window.width = 600
        with self._window.frame:
            with ui.HStack(height=0, style=style):
                ui.Spacer(width=40)
                with ui.VStack(spacing=10):
                    ui.Spacer(height=10)
                    # build collection path widgets
                    with ui.HStack(height=0):
                        ui.Label("Collection Path:  ", width=0)
                        with ui.VStack(height=0):
                            ui.Spacer(height=4)
                            self._collection_path_field = ui.StringField(
                                height=20, identifier="collect_path", width=ui.Fraction(1)
                            )
                            ui.Spacer(height=4)
                        ui.Spacer(width=5)
                        with ui.VStack(width=0):
                            ui.Spacer()
                            with ui.ZStack(width=20, height=20):
                                ui.Rectangle(name="hovering")
                                self._folder_button = ui.Button(
                                    name="folder", identifier="folder_button", width=24, height=24
                                )
                            self._folder_button.set_tooltip("Choose folder")
                            ui.Spacer()
                        ui.Spacer(width=2)
                        self._folder_button.set_clicked_fn(lambda: self._show_file_picker())

                    # build collection options
                    with ui.HStack(height=0, spacing=10):
                        self._usd_only_checkbox = _build_option_checkbox(
                            "USD Only",
                            False,
                            "usd_only_checkbox",
                            "Only USD files will be collected. Any materials bindings will be removed.",
                        )
                        self._material_only_checkbox = _build_option_checkbox(
                            "Material Only",
                            False,
                            "material_only_checkbox",
                            "Only MDL files and their depdendent textures will be collected.",
                        )
                        self._flat_collection_checkbox = _build_option_checkbox(
                            "Flat Collection",
                            False,
                            "flat_collection_checkbox",
                            "By default, it will keep the folder structure after collection. "
                            "After this option is enabled, assets will be collected into specified folders.",
                        )
                        # add value changed callback to enable flat collection settings combo
                        self._flat_collection_checkbox.model.add_value_changed_fn(self._on_flat_collection_toggled)

                    # build flat collection texture options (visibility toggled by flat collection checkbox)
                    with ui.HStack(spacing=10):
                        tooltip = "Options for grouping for textures.\nTextures can be grouped under parent folders by MDL or USD, or flat in the same hierarchy."
                        self._flat_options_widgets = [
                            ui.Label("Flat Collection Texture Option: ", name="label", width=0, tooltip=tooltip),
                            ui.ComboBox(
                                0,
                                "Group By MDL",
                                "Group By USD",
                                "Flat",
                                height=10,
                                name="choices",
                                identifier="texture_option_combo",
                            ),
                        ]
                        for widget in self._flat_options_widgets:
                            widget.visible = False
                    ui.Spacer(height=0)

                    # build action buttons
                    with ui.HStack(height=0):
                        ui.Spacer()
                        self._collect_button = ui.Button("Start", width=120, height=0)
                        self._collect_button.set_clicked_fn(self._on_collect_button_clicked)
                        self._cancel_button = ui.Button("Cancel", width=120, height=0)
                        self._cancel_button.set_clicked_fn(self._on_cancel_button_clicked)
                        ui.Spacer()
                    ui.Spacer(height=20)
                ui.Spacer(width=40)

    def _on_collect_button_clicked(self):
        if self._collect_button_fn:
            collect_dir = self._collection_path_field.model.get_value_as_string()
            usd_only = self._usd_only_checkbox.model.get_value_as_bool()
            material_only = self._material_only_checkbox.model.get_value_as_bool()
            flat_collection = self._flat_collection_checkbox.model.get_value_as_bool()
            texture_option = self._flat_options_widgets[1].model.get_item_value_model().as_int
            self._collect_button_fn(collect_dir, usd_only, flat_collection, material_only, texture_option)

        self._window.visible = False

    def _on_cancel_button_clicked(self):
        if self._cancel_button_fn:
            self._cancel_button_fn()

        self._window.visible = False

    def _select_picked_folder_callback(self, path):
        self._collection_path_field.model.set_value(path)
        self._window.visible = True

    def _cancel_picked_folder_callback(self):
        self._window.visible = True

    def _show_file_picker(self):
        self._window.visible = False
        if not self._file_picker:
            mode = FileBrowserMode.SAVE
            file_type = FileBrowserSelectionType.DIRECTORY_ONLY
            filters = [(".*", "All Files (*.*)")]
            self._file_picker = FilePicker(
                "Select Collect Destination", mode=mode, file_type=file_type, filter_options=filters
            )
            self._file_picker.set_filebar_label_name("Folder name")
            self._file_picker.set_file_selected_fn(self._select_picked_folder_callback)
            self._file_picker.set_cancel_fn(self._cancel_picked_folder_callback)

        path = self._collection_path_field.model.get_value_as_string().rstrip("/")

        dir_name = os.path.dirname(path)
        folder_name = os.path.basename(path)
        self._file_picker.show(dir_name, folder_name)

    def _on_flat_collection_toggled(self, model):
        for widget in self._flat_options_widgets:
            widget.visible = model.as_bool

    def show(self, export_folder=None):
        if export_folder:
            self._collection_path_field.model.set_value(export_folder)
        self._window.visible = True

    def hide(self):
        self._window.visible = False
