use crate::components::websocket::WebSocketContext;
use leptos::html::Input;
use leptos::*;
use leptos_use::core::ConnectionReadyState;
use lib::*;
use serde_json::to_string;
use std::collections::BTreeSet;

#[component]
pub fn Browser() -> impl IntoView {
    let websocket = expect_context::<WebSocketContext>();
    let connected = move || websocket.ready_state.get() == ConnectionReadyState::Open;

    let game_update_context = expect_context::<ReadSignal<Option<GamesUpdate>>>();
    let card_packs = expect_context::<ReadSignal<CardPacksMeta>>();
    let (active_games, set_active_games) = create_signal::<Vec<String>>(vec![]);

    let new_game_name_ref = create_node_ref::<Input>();
    let (selected_packs, set_selected_packs) = create_signal::<BTreeSet<u8>>(BTreeSet::new());
    create_effect(move |_| {
        logging::log!("{:#?}", selected_packs().iter().collect::<Vec<_>>());
    });

    // Game stuff
    let new_game = move |_| {
        if let Some(input) = new_game_name_ref.get() {
            if input.value() == String::from("") {
                logging::log!("New game name is empty!");
            } else if selected_packs().is_empty() {
                logging::log!("New game selected packs is empty!");
            } else {
                (websocket.send)(
                    &to_string(&NewGameRequest {
                        name: input.value(),
                        packs: selected_packs()
                            .into_iter()
                            .map(|n| n.clone()) // hax
                            .collect::<Vec<_>>(),
                    })
                    .unwrap(),
                );
                input.set_value("");
            }
        }
    };

    create_effect(move |_| {
        game_update_context.with(move |games| {
            if let Some(games) = games {
                set_active_games(games.games.clone());
            }
        })
    });

    // Clear games list on disconnect
    create_effect(move |_| {
        if !connected() {
            set_active_games(vec![]);
        }
    });
    let (show_packs, set_show_packs) = create_signal(false);

    let show_packs_button = move |_| set_show_packs(!show_packs());

    view! {
        <div class="p-1">
            <h2 class="text-2xl">Game Browser</h2>
            <ul>
                {move || active_games().into_iter().map(|n| view! { <li>{n}</li> }).collect_view()}
            </ul>

        </div>
        <hr/>
        <div class="flex p-1">
            <form onsubmit="return false" on:submit=new_game>
                <h2 class="text-2xl">Create Game</h2>
                <input
                    class="w-80 h-11 font-mono rounded-sm bg-neutral-900 text-neutral-200"
                    placeholder="Name"
                    disabled=move || !connected()
                    node_ref=new_game_name_ref
                />
                <h2 class="text-2xl">Packs</h2>
                <div class="p-2">
                    <button type="button" class="bg-neutral-600">
                        <input type="checkbox" id="all"/>
                        <label for="all">All</label>
                    </button>
                    <button type="button" class="bg-neutral-600">
                        <input type="checkbox" id="official" checked/>
                        <label for="official">Official</label>
                    </button>
                    <button type="button" class="bg-neutral-600" on:click=show_packs_button>
                        <label>Custom</label>
                    </button>
                    finish this
                </div>
                <Show when=move || show_packs()>
                    <span class="flex">
                        <div>
                            <h2 class="text-xl">Official</h2>
                            {move || {
                                card_packs()
                                    .official_meta
                                    .into_iter()
                                    .map(|n| {
                                        view! {
                                            <input
                                                type="checkbox"
                                                value=n.pack
                                                id=n.pack
                                                checked
                                                on:change=move |e| {
                                                    if event_target_checked(&e) {
                                                        logging::log!("insert");
                                                        set_selected_packs
                                                            .update(|packs| {
                                                                packs.insert(n.pack);
                                                            })
                                                    } else {
                                                        logging::log!("remove");
                                                        set_selected_packs
                                                            .update(|packs| {
                                                                packs.remove(&n.pack);
                                                            })
                                                    }
                                                }
                                            />

                                            <label for=n.pack>{n.name}</label>
                                            <br/>
                                            {set_selected_packs
                                                .update(|packs| {
                                                    packs.insert(n.pack);
                                                })}
                                        }
                                    })
                                    .collect_view()
                            }}

                        </div>
                        <div>
                            <h2 class="text-xl">Unofficial</h2>
                            {move || {
                                card_packs()
                                    .unofficial_meta
                                    .into_iter()
                                    .map(|n| {
                                        view! {
                                            <input
                                                type="checkbox"
                                                value=n.pack
                                                id=n.pack
                                                on:change=move |e| {
                                                    if event_target_checked(&e) {
                                                        logging::log!("insert");
                                                        set_selected_packs
                                                            .update(|packs| {
                                                                packs.insert(n.pack);
                                                            })
                                                    } else {
                                                        logging::log!("remove");
                                                        set_selected_packs
                                                            .update(|packs| {
                                                                packs.remove(&n.pack);
                                                            })
                                                    }
                                                }
                                            />

                                            <label for=n.pack>{n.name}</label>
                                            <br/>
                                        }
                                    })
                                    .collect_view()
                            }}

                        </div>
                    </span>
                </Show>

                <input
                    class="py-2 px-4 pl-4 font-bold text-white rounded border-b-4 bg-neutral-600 border-neutral-800 hover:bg-neutral-700 hover:border-neutral-500"
                    type="submit"
                    disabled=move || !connected()
                    value="New Game"
                />
            </form>
        </div>
    }
}