use nalgebra_glm::{Vec2, Vec4};
use std::collections::HashMap;

use crate::ecs::text::components::{TextMesh, TextProperties};
use crate::render::wgpu::passes::geometry::UiLayer;

use super::super::layout::LayoutStack;
use super::super::theme::ThemeState;
use super::super::types::{Rect, UiId, UiStyle, WidgetState};

#[derive(Clone, Debug)]
pub struct UiWidget {
    pub text: String,
    pub position: Vec2,
    pub properties: TextProperties,
    pub clip_rect: Option<Rect>,
    pub layer: UiLayer,
    pub z_index: i32,
}

#[derive(Clone)]
pub struct ImmediateTextInstance {
    pub mesh: TextMesh,
    pub position: Vec2,
    pub color: Vec4,
    pub outline_color: Vec4,
    pub outline_width: f32,
    pub font_index: usize,
    pub clip_rect: Option<Rect>,
    pub layer: UiLayer,
    pub z_index: i32,
}

#[derive(Clone, Copy, Debug, Default)]
pub struct ReservedAreas {
    pub top: f32,
    pub bottom: f32,
    pub left: f32,
    pub right: f32,
}

#[derive(Clone, Copy, Debug)]
pub struct KeyInput {
    pub key: winit::keyboard::KeyCode,
    pub pressed: bool,
}

pub struct ImmediateUi {
    pub frame_widgets: Vec<UiWidget>,
    pub frame_rects: Vec<crate::render::wgpu::passes::geometry::UiRect>,
    pub frame_text_meshes: Vec<ImmediateTextInstance>,
    pub widget_states: HashMap<UiId, WidgetState>,
    pub style: UiStyle,
    pub theme_state: ThemeState,
    pub screen_size: Vec2,
    pub mouse_pos: Vec2,
    pub mouse_down: bool,
    pub mouse_just_pressed: bool,
    pub mouse_just_released: bool,
    pub scroll_delta: Vec2,
    pub active_widget: Option<UiId>,
    pub focused_widget: Option<UiId>,
    pub hot_widget: Option<UiId>,
    pub background_color: Option<Vec4>,
    pub enabled: bool,
    pub(super) layout_stack: LayoutStack,
    pub(super) id_stack: Vec<UiId>,
    pub(super) clip_stack: Vec<Rect>,
    pub(super) char_input: Vec<char>,
    pub(super) key_input: Vec<KeyInput>,
    pub(super) deferred_rects: Vec<crate::render::wgpu::passes::geometry::UiRect>,
    pub(super) deferred_widgets: Vec<UiWidget>,
    pub(super) reserved_areas: ReservedAreas,
    pub(super) current_layer: UiLayer,
    pub(super) scroll_area_stack: Vec<(UiId, Rect)>,
    pub(super) next_z_index: i32,
    pub(super) next_focus_order: i32,
    pub(super) current_panel_z_base: i32,
    pub(super) current_tab_bar_id: Option<UiId>,
    pub(super) current_tab_index: usize,
    pub(super) tab_bar_y: f32,
    pub(super) tab_bar_start_x: f32,
    pub(super) selected_tab_rect: Option<Rect>,
}

impl Default for ImmediateUi {
    fn default() -> Self {
        Self {
            frame_widgets: Vec::new(),
            frame_rects: Vec::new(),
            frame_text_meshes: Vec::new(),
            widget_states: HashMap::new(),
            style: UiStyle::default(),
            theme_state: ThemeState::default(),
            screen_size: Vec2::new(0.0, 0.0),
            mouse_pos: Vec2::new(0.0, 0.0),
            mouse_down: false,
            mouse_just_pressed: false,
            mouse_just_released: false,
            scroll_delta: Vec2::new(0.0, 0.0),
            active_widget: None,
            focused_widget: None,
            hot_widget: None,
            background_color: None,
            enabled: true,
            layout_stack: LayoutStack::new(),
            id_stack: Vec::new(),
            clip_stack: Vec::new(),
            char_input: Vec::new(),
            key_input: Vec::new(),
            deferred_rects: Vec::new(),
            deferred_widgets: Vec::new(),
            reserved_areas: ReservedAreas::default(),
            current_layer: UiLayer::Background,
            scroll_area_stack: Vec::new(),
            next_z_index: 0,
            next_focus_order: 1,
            current_panel_z_base: 0,
            current_tab_bar_id: None,
            current_tab_index: 0,
            tab_bar_y: 0.0,
            tab_bar_start_x: 0.0,
            selected_tab_rect: None,
        }
    }
}
