//! Create new scene page component.

use leptos::prelude::*;
use leptos_router::hooks::use_params_map;
#[cfg(feature = "hydrate")]
use leptos::task::spawn_local;

use crate::components::{Card, PageHeader};
#[cfg(feature = "hydrate")]
use crate::utils::fetch_image_dimensions_client;

/// Scene new page component.
#[component]
pub fn SceneNewPage() -> impl IntoView {
    let params = use_params_map();
    let realm_slug = move || params.get().get("slug").unwrap_or_default();

    // Form state
    let (name, set_name) = signal(String::new());
    let (slug, set_slug) = signal(String::new());
    let (description, set_description) = signal(String::new());
    let (background_color, set_background_color) = signal("#1a1a2e".to_string());
    let (background_image_url, set_background_image_url) = signal(String::new());
    let (infer_dimensions, set_infer_dimensions) = signal(false);
    let (width, set_width) = signal(800i32);
    let (height, set_height) = signal(600i32);
    let (dimension_mode, set_dimension_mode) = signal("fixed".to_string());
    let (sort_order, set_sort_order) = signal(0i32);
    let (is_entry_point, set_is_entry_point) = signal(false);
    let (is_hidden, set_is_hidden) = signal(false);

    // UI state
    let (message, set_message) = signal(Option::<(String, bool)>::None);
    let (pending, set_pending) = signal(false);
    let (created_id, _set_created_id) = signal(Option::<String>::None);
    #[cfg(feature = "hydrate")]
    let set_created_id = _set_created_id;
    let (slug_auto, set_slug_auto) = signal(true);
    let (fetching_dimensions, set_fetching_dimensions) = signal(false);
    let (dimension_message, set_dimension_message) = signal(Option::<(String, bool)>::None);

    let update_name = move |ev: leptos::ev::Event| {
        let new_name = event_target_value(&ev);
        set_name.set(new_name.clone());
        if slug_auto.get() {
            let new_slug = new_name
                .to_lowercase()
                .chars()
                .map(|c| if c.is_alphanumeric() { c } else { '-' })
                .collect::<String>()
                .trim_matches('-')
                .to_string();
            set_slug.set(new_slug);
        }
    };

    let fetch_dimensions = move |_: leptos::ev::MouseEvent| {
        let url = background_image_url.get();
        if url.is_empty() {
            set_dimension_message.set(Some(("Please enter an image URL first".to_string(), false)));
            return;
        }

        set_fetching_dimensions.set(true);
        set_dimension_message.set(None);

        #[cfg(feature = "hydrate")]
        {
            fetch_image_dimensions_client(
                url,
                move |w, h| {
                    set_width.set(w as i32);
                    set_height.set(h as i32);
                    set_dimension_message.set(Some((
                        format!("Dimensions: {}x{}", w, h),
                        true,
                    )));
                },
                move |err| {
                    set_dimension_message.set(Some((err, false)));
                },
                set_fetching_dimensions,
            );
        }
    };

    let on_submit = move |ev: leptos::ev::SubmitEvent| {
        ev.prevent_default();
        set_pending.set(true);
        set_message.set(None);

        #[cfg(feature = "hydrate")]
        let realm_slug_val = realm_slug();

        #[cfg(feature = "hydrate")]
        {
            use gloo_net::http::Request;

            // Build bounds WKT from width/height
            let w = width.get();
            let h = height.get();
            let bounds_wkt = format!("POLYGON((0 0, {} 0, {} {}, 0 {}, 0 0))", w, w, h, h);

            let data = serde_json::json!({
                "name": name.get(),
                "slug": slug.get(),
                "description": if description.get().is_empty() { None::<String> } else { Some(description.get()) },
                "background_color": if background_color.get().is_empty() { None::<String> } else { Some(background_color.get()) },
                "background_image_url": if background_image_url.get().is_empty() { None::<String> } else { Some(background_image_url.get()) },
                "infer_dimensions_from_image": infer_dimensions.get(),
                "bounds_wkt": bounds_wkt,
                "dimension_mode": dimension_mode.get(),
                "sort_order": sort_order.get(),
                "is_entry_point": is_entry_point.get(),
                "is_hidden": is_hidden.get()
            });

            spawn_local(async move {
                let url = format!("/api/admin/realms/{}/scenes", realm_slug_val);
                let response = Request::post(&url)
                    .json(&data)
                    .unwrap()
                    .send()
                    .await;

                set_pending.set(false);

                match response {
                    Ok(resp) if resp.ok() => {
                        #[derive(serde::Deserialize)]
                        #[allow(dead_code)]
                        struct CreateResponse {
                            id: String,
                            slug: String,
                        }
                        if let Ok(result) = resp.json::<CreateResponse>().await {
                            set_created_id.set(Some(result.id));
                            set_message.set(Some(("Scene created successfully!".to_string(), true)));
                        }
                    }
                    Ok(resp) => {
                        #[derive(serde::Deserialize)]
                        struct ErrorResp {
                            error: String,
                        }
                        if let Ok(err) = resp.json::<ErrorResp>().await {
                            set_message.set(Some((err.error, false)));
                        } else {
                            set_message.set(Some(("Failed to create scene".to_string(), false)));
                        }
                    }
                    Err(_) => {
                        set_message.set(Some(("Network error".to_string(), false)));
                    }
                }
            });
        }
    };

    let slug_for_header = realm_slug();

    view! {
        <PageHeader title="Create New Scene" subtitle="Create a new scene in this realm">
            <a href=format!("/admin/realms/{}/scenes", slug_for_header) class="btn btn-secondary">"Back to Scenes"</a>
        </PageHeader>

        <Card>
            <form on:submit=on_submit>
                <h3 class="section-title">"Scene Details"</h3>

                <div class="form-row">
                    <div class="form-group">
                        <label for="name" class="form-label">
                            "Scene Name" <span class="required">"*"</span>
                        </label>
                        <input
                            type="text"
                            id="name"
                            required=true
                            class="form-input"
                            placeholder="Main Lobby"
                            prop:value=move || name.get()
                            on:input=update_name
                        />
                    </div>
                    <div class="form-group">
                        <label for="slug" class="form-label">
                            "Slug (URL)" <span class="required">"*"</span>
                        </label>
                        <input
                            type="text"
                            id="slug"
                            required=true
                            pattern="[a-z0-9][a-z0-9\\-]*[a-z0-9]|[a-z0-9]"
                            class="form-input"
                            placeholder="main-lobby"
                            prop:value=move || slug.get()
                            on:input=move |ev| {
                                set_slug_auto.set(false);
                                set_slug.set(event_target_value(&ev));
                            }
                        />
                        <small class="form-help">"Lowercase letters, numbers, hyphens only"</small>
                    </div>
                </div>

                <div class="form-group">
                    <label for="description" class="form-label">"Description"</label>
                    <textarea
                        id="description"
                        class="form-textarea"
                        placeholder="Description of this scene"
                        prop:value=move || description.get()
                        on:input=move |ev| set_description.set(event_target_value(&ev))
                    ></textarea>
                </div>

                <h3 class="section-title">"Background"</h3>

                <div class="form-row">
                    <div class="form-group">
                        <label for="background_color" class="form-label">"Background Color"</label>
                        <input
                            type="color"
                            id="background_color"
                            class="form-color"
                            prop:value=move || background_color.get()
                            on:input=move |ev| set_background_color.set(event_target_value(&ev))
                        />
                    </div>
                    <div class="form-group" style="flex: 2">
                        <label for="background_image_url" class="form-label">"Background Image URL"</label>
                        <div style="display: flex; gap: 0.5rem">
                            <input
                                type="url"
                                id="background_image_url"
                                class="form-input"
                                style="flex: 1"
                                placeholder="https://example.com/image.png"
                                prop:value=move || background_image_url.get()
                                on:input=move |ev| set_background_image_url.set(event_target_value(&ev))
                            />
                            <button
                                type="button"
                                class="btn btn-secondary"
                                disabled=move || fetching_dimensions.get()
                                on:click=fetch_dimensions
                            >
                                {move || if fetching_dimensions.get() { "Fetching..." } else { "Get Size" }}
                            </button>
                        </div>
                        <small class="form-help">"Enter a public image URL and click 'Get Size' to auto-fill dimensions"</small>
                    </div>
                </div>

                // Image preview
                <Show when=move || !background_image_url.get().is_empty()>
                    <div class="form-group">
                        <label class="form-label">"Image Preview"</label>
                        <div style="max-width: 300px; border: 1px solid var(--color-border); border-radius: var(--radius-md); overflow: hidden; background: var(--color-bg-tertiary)">
                            <img
                                src=move || background_image_url.get()
                                alt="Background preview"
                                style="max-width: 100%; height: auto; display: block"
                            />
                        </div>
                    </div>
                </Show>

                // Dimension fetch message
                <Show when=move || dimension_message.get().is_some()>
                    {move || {
                        let (msg, is_success) = dimension_message.get().unwrap_or_default();
                        let class = if is_success { "alert alert-success" } else { "alert alert-error" };
                        view! {
                            <div class=class role="alert" style="margin-bottom: 1rem">
                                <p>{msg}</p>
                            </div>
                        }
                    }}
                </Show>

                <div class="checkbox-group">
                    <label class="checkbox-label">
                        <input
                            type="checkbox"
                            class="form-checkbox"
                            prop:checked=move || infer_dimensions.get()
                            on:change=move |ev| set_infer_dimensions.set(event_target_checked(&ev))
                        />
                        "Infer dimensions from image"
                    </label>
                    <small class="form-help">"If enabled, server will extract dimensions from the image when creating the scene"</small>
                </div>

                <h3 class="section-title">"Dimensions"</h3>

                <div class="form-row">
                    <div class="form-group">
                        <label for="width" class="form-label">"Width"</label>
                        <input
                            type="number"
                            id="width"
                            min=100
                            max=10000
                            class="form-input"
                            prop:value=move || width.get()
                            on:input=move |ev| {
                                if let Ok(v) = event_target_value(&ev).parse() {
                                    set_width.set(v);
                                }
                            }
                        />
                    </div>
                    <div class="form-group">
                        <label for="height" class="form-label">"Height"</label>
                        <input
                            type="number"
                            id="height"
                            min=100
                            max=10000
                            class="form-input"
                            prop:value=move || height.get()
                            on:input=move |ev| {
                                if let Ok(v) = event_target_value(&ev).parse() {
                                    set_height.set(v);
                                }
                            }
                        />
                    </div>
                    <div class="form-group">
                        <label for="dimension_mode" class="form-label">"Dimension Mode"</label>
                        <select
                            id="dimension_mode"
                            class="form-select"
                            on:change=move |ev| set_dimension_mode.set(event_target_value(&ev))
                        >
                            <option value="fixed" selected=move || dimension_mode.get() == "fixed">"Fixed"</option>
                            <option value="viewport" selected=move || dimension_mode.get() == "viewport">"Viewport"</option>
                        </select>
                    </div>
                </div>

                <h3 class="section-title">"Options"</h3>

                <div class="form-group">
                    <label for="sort_order" class="form-label">"Sort Order"</label>
                    <input
                        type="number"
                        id="sort_order"
                        class="form-input"
                        prop:value=move || sort_order.get()
                        on:input=move |ev| {
                            if let Ok(v) = event_target_value(&ev).parse() {
                                set_sort_order.set(v);
                            }
                        }
                    />
                    <small class="form-help">"Lower numbers appear first in scene lists"</small>
                </div>

                <div class="form-row">
                    <div class="checkbox-group">
                        <label class="checkbox-label">
                            <input
                                type="checkbox"
                                class="form-checkbox"
                                prop:checked=move || is_entry_point.get()
                                on:change=move |ev| set_is_entry_point.set(event_target_checked(&ev))
                            />
                            "Entry Point"
                        </label>
                        <small class="form-help">"Users spawn here when entering the realm"</small>
                    </div>
                    <div class="checkbox-group">
                        <label class="checkbox-label">
                            <input
                                type="checkbox"
                                class="form-checkbox"
                                prop:checked=move || is_hidden.get()
                                on:change=move |ev| set_is_hidden.set(event_target_checked(&ev))
                            />
                            "Hidden"
                        </label>
                        <small class="form-help">"Scene won't appear in public listings"</small>
                    </div>
                </div>

                <Show when=move || message.get().is_some()>
                    {move || {
                        let (msg, is_success) = message.get().unwrap_or_default();
                        let class = if is_success { "alert alert-success" } else { "alert alert-error" };
                        view! {
                            <div class=class role="alert">
                                <p>{msg}</p>
                            </div>
                        }
                    }}
                </Show>

                <Show when=move || created_id.get().is_some()>
                    {move || {
                        let id = created_id.get().unwrap_or_default();
                        let slug = realm_slug();
                        view! {
                            <div class="alert alert-info">
                                <p>
                                    <a href=format!("/admin/realms/{}/scenes/{}", slug, id)>
                                        "View scene"
                                    </a>
                                </p>
                            </div>
                        }
                    }}
                </Show>

                <div class="form-actions">
                    <button
                        type="submit"
                        class="btn btn-primary"
                        disabled=move || pending.get()
                    >
                        {move || if pending.get() { "Creating..." } else { "Create Scene" }}
                    </button>
                </div>
            </form>
        </Card>
    }
}
