use std::collections::HashSet;

use seed::{prelude::*, *};

use crate::{
    api::urls,
    graphql::front_page_query::*,
    state::{Context, Model, Msg},
    view::{self, human_age, pretty_authors, search_toolbar, set_title, tags_chiclet, view_header},
};

pub(super) fn view(model: &Model) -> Node<Msg> {
    log::info!("tablet::view");
    let show_icon_text = false;
    let content = match &model.context {
        Context::None => div![h1!["Loading"]],
        Context::ThreadResult {
            thread,
            open_messages,
        } => view::thread(thread, open_messages, show_icon_text),
        Context::SearchResult {
            query,
            results,
            count,
            pager,
            selected_threads,
        } => search_results(
            &query,
            results.as_slice(),
            *count,
            pager,
            selected_threads,
            show_icon_text,
        ),
    };
    div![
        view_header(&model.query, &model.refreshing_state),
        content,
        view_header(&model.query, &model.refreshing_state),
    ]
}

fn search_results(
    query: &str,
    results: &[FrontPageQuerySearchNodes],
    count: usize,
    pager: &FrontPageQuerySearchPageInfo,
    selected_threads: &HashSet<String>,
    show_icon_text: bool,
) -> Node<Msg> {
    if query.is_empty() {
        set_title("all mail");
    } else {
        set_title(query);
    }
    let rows = results.iter().map(|r| {
        let tid = r.thread.clone();
        let check_tid = r.thread.clone();
        let datetime = human_age(r.timestamp as i64);
        let unread_idx = r.tags.iter().position(|e| e == &"unread");
        let mut tags = r.tags.clone();
        if let Some(idx) = unread_idx {
            tags.remove(idx);
        };
        div![
            C!["row"],
            label![
                C!["b-checkbox", "checkbox", "is-large"],
                input![attrs! {
                    At::Type=>"checkbox",
                    At::Checked=>selected_threads.contains(&tid).as_at_value(),
                }],
                span![C!["check"]],
                ev(Ev::Input, move |e| {
                    if let Some(input) = e
                        .target()
                        .as_ref()
                        .expect("failed to get reference to target")
                        .dyn_ref::<web_sys::HtmlInputElement>()
                    {
                        if input.checked() {
                            Msg::SelectionAddThread(check_tid)
                        } else {
                            Msg::SelectionRemoveThread(check_tid)
                        }
                    } else {
                        Msg::Noop
                    }
                }),
            ],
            a![
                C!["has-text-light", "summary"],
                IF!(unread_idx.is_some() => C!["unread"]),
                attrs! {
                    At::Href => urls::thread(&tid)
                },
                div![C!["subject"], &r.subject],
                span![C!["from", "is-size-7"], pretty_authors(&r.authors)],
                div![
                    span![C!["is-size-7"], tags_chiclet(&tags, true)],
                    span![C!["is-size-7", "float-right", "date"], datetime]
                ]
            ]
        ]
    });
    let show_bulk_edit = !selected_threads.is_empty();
    div![
        C!["search-results"],
        search_toolbar(count, pager, show_bulk_edit, show_icon_text),
        div![C!["index"], rows],
        search_toolbar(count, pager, show_bulk_edit, show_icon_text),
    ]
}
