// src/functions/modes/navigation/add_logic_nav.rs
use crate::config::binds::config::{Config, EditorKeybindingMode};
use crate::state::{
    app::state::AppState,
    pages::add_logic::{AddLogicFocus, AddLogicState},
    app::buffer::AppView,
    app::buffer::BufferState,
};
use crossterm::event::{KeyEvent, KeyCode, KeyModifiers};
use crate::services::GrpcClient;
use tokio::sync::mpsc;
use anyhow::Result;
use crate::components::common::text_editor::TextEditor;
use crate::services::ui_service::UiService;
use tui_textarea::CursorMove; // Ensure this import is present

pub type SaveLogicResultSender = mpsc::Sender<Result<String>>;

pub fn handle_add_logic_navigation(
    key_event: KeyEvent,
    config: &Config,
    app_state: &mut AppState,
    add_logic_state: &mut AddLogicState,
    is_edit_mode: &mut bool,
    buffer_state: &mut BufferState,
    grpc_client: GrpcClient,
    _save_logic_sender: SaveLogicResultSender, // Marked as unused
    command_message: &mut String,
) -> bool {
    // === FULLSCREEN SCRIPT EDITING - COMPLETE ISOLATION ===
    if add_logic_state.current_focus == AddLogicFocus::InsideScriptContent {
        // === AUTOCOMPLETE HANDLING ===
        if add_logic_state.script_editor_autocomplete_active {
            match key_event.code {
                // ... (Char, Backspace, Tab, Down, Up cases remain the same) ...
                KeyCode::Char(c) if c.is_alphanumeric() || c == '_' => {
                    add_logic_state.script_editor_filter_text.push(c);
                    add_logic_state.update_script_editor_suggestions();
                    {
                        let mut editor_borrow = add_logic_state.script_content_editor.borrow_mut();
                        TextEditor::handle_input(
                            &mut editor_borrow,
                            key_event,
                            &add_logic_state.editor_keybinding_mode,
                            &mut add_logic_state.vim_state,
                        );
                    }
                    *command_message = format!("Filtering: @{}", add_logic_state.script_editor_filter_text);
                    return true;
                }
                KeyCode::Backspace => {
                    if !add_logic_state.script_editor_filter_text.is_empty() {
                        add_logic_state.script_editor_filter_text.pop();
                        add_logic_state.update_script_editor_suggestions();
                        {
                            let mut editor_borrow = add_logic_state.script_content_editor.borrow_mut();
                            TextEditor::handle_input(
                                &mut editor_borrow,
                                key_event,
                                &add_logic_state.editor_keybinding_mode,
                                &mut add_logic_state.vim_state,
                            );
                        }
                        *command_message = if add_logic_state.script_editor_filter_text.is_empty() {
                            "Autocomplete: @".to_string()
                        } else {
                            format!("Filtering: @{}", add_logic_state.script_editor_filter_text)
                        };
                    } else {
                        let should_deactivate = if let Some((trigger_line, trigger_col)) = add_logic_state.script_editor_trigger_position {
                            let current_cursor = {
                                let editor_borrow = add_logic_state.script_content_editor.borrow();
                                editor_borrow.cursor()
                            };
                            current_cursor.0 == trigger_line && current_cursor.1 == trigger_col + 1
                        } else {
                            false
                        };
                        if should_deactivate {
                            add_logic_state.deactivate_script_editor_autocomplete();
                            *command_message = "Autocomplete cancelled".to_string();
                        }
                        {
                            let mut editor_borrow = add_logic_state.script_content_editor.borrow_mut();
                            TextEditor::handle_input(
                                &mut editor_borrow,
                                key_event,
                                &add_logic_state.editor_keybinding_mode,
                                &mut add_logic_state.vim_state,
                            );
                        }
                    }
                    return true;
                }
                KeyCode::Tab | KeyCode::Down => {
                    if !add_logic_state.script_editor_suggestions.is_empty() {
                        let current = add_logic_state.script_editor_selected_suggestion_index.unwrap_or(0);
                        let next = (current + 1) % add_logic_state.script_editor_suggestions.len();
                        add_logic_state.script_editor_selected_suggestion_index = Some(next);
                        *command_message = format!("Selected: {}", add_logic_state.script_editor_suggestions[next]);
                    }
                    return true;
                }
                KeyCode::Up => {
                    if !add_logic_state.script_editor_suggestions.is_empty() {
                        let current = add_logic_state.script_editor_selected_suggestion_index.unwrap_or(0);
                        let prev = if current == 0 {
                            add_logic_state.script_editor_suggestions.len() - 1
                        } else {
                            current - 1
                        };
                        add_logic_state.script_editor_selected_suggestion_index = Some(prev);
                        *command_message = format!("Selected: {}", add_logic_state.script_editor_suggestions[prev]);
                    }
                    return true;
                }
                KeyCode::Enter => {
                    if let Some(selected_idx) = add_logic_state.script_editor_selected_suggestion_index {
                        if let Some(suggestion) = add_logic_state.script_editor_suggestions.get(selected_idx).cloned() {
                            let trigger_pos = add_logic_state.script_editor_trigger_position;
                            let filter_len = add_logic_state.script_editor_filter_text.len();

                            add_logic_state.deactivate_script_editor_autocomplete();
                            add_logic_state.has_unsaved_changes = true;

                            if let Some(pos) = trigger_pos {
                                let mut editor_borrow = add_logic_state.script_content_editor.borrow_mut();

                                if suggestion == "sql" {
                                    replace_autocomplete_text(&mut editor_borrow, pos, filter_len, "sql");
                                    editor_borrow.insert_str("('')");
                                    // Move cursor back twice to be between the single quotes
                                    editor_borrow.move_cursor(CursorMove::Back); // Before ')'
                                    editor_borrow.move_cursor(CursorMove::Back); // Before ''' (inside '')
                                    *command_message = "Inserted: @sql('')".to_string();
                                } else {
                                    let is_table_selection = add_logic_state.is_table_name_suggestion(&suggestion);
                                    replace_autocomplete_text(&mut editor_borrow, pos, filter_len, &suggestion);

                                    if is_table_selection {
                                        editor_borrow.insert_str(".");
                                        let new_cursor = editor_borrow.cursor();
                                        drop(editor_borrow); // Release borrow before calling add_logic_state methods

                                        add_logic_state.script_editor_trigger_position = Some(new_cursor);
                                        add_logic_state.script_editor_autocomplete_active = true;
                                        add_logic_state.script_editor_filter_text.clear();
                                        add_logic_state.trigger_column_autocomplete_for_table(suggestion.clone());

                                        let profile_name = add_logic_state.profile_name.clone();
                                        let table_name_for_fetch = suggestion.clone();
                                        let mut client_clone = grpc_client.clone();
                                        tokio::spawn(async move {
                                            match UiService::fetch_columns_for_table(&mut client_clone, &profile_name, &table_name_for_fetch).await {
                                                Ok(_columns) => {
                                                    // Result handled by main UI loop
                                                }
                                                Err(e) => {
                                                    tracing::error!("Failed to fetch columns for {}.{}: {}", profile_name, table_name_for_fetch, e);
                                                }
                                            }
                                        });
                                        *command_message = format!("Selected table '{}', fetching columns...", suggestion);
                                    } else {
                                        *command_message = format!("Inserted: {}", suggestion);
                                    }
                                }
                            }
                            return true;
                        }
                    }
                    add_logic_state.deactivate_script_editor_autocomplete();
                    {
                        let mut editor_borrow = add_logic_state.script_content_editor.borrow_mut();
                        TextEditor::handle_input(
                            &mut editor_borrow,
                            key_event,
                            &add_logic_state.editor_keybinding_mode,
                            &mut add_logic_state.vim_state,
                        );
                    }
                    return true;
                }
                KeyCode::Esc => {
                    add_logic_state.deactivate_script_editor_autocomplete();
                    *command_message = "Autocomplete cancelled".to_string();
                }
                _ => {
                    add_logic_state.deactivate_script_editor_autocomplete();
                    *command_message = "Autocomplete cancelled".to_string();
                    {
                        let mut editor_borrow = add_logic_state.script_content_editor.borrow_mut();
                        TextEditor::handle_input(
                            &mut editor_borrow,
                            key_event,
                            &add_logic_state.editor_keybinding_mode,
                            &mut add_logic_state.vim_state,
                        );
                    }
                    return true;
                }
            }
        }

        if key_event.code == KeyCode::Char('@') && key_event.modifiers == KeyModifiers::NONE {
            let should_trigger = match add_logic_state.editor_keybinding_mode {
                EditorKeybindingMode::Vim => *is_edit_mode,
                _ => true,
            };
            if should_trigger {
                let cursor_before = {
                    let editor_borrow = add_logic_state.script_content_editor.borrow();
                    editor_borrow.cursor()
                };
                {
                    let mut editor_borrow = add_logic_state.script_content_editor.borrow_mut();
                    TextEditor::handle_input(
                        &mut editor_borrow,
                        key_event,
                        &add_logic_state.editor_keybinding_mode,
                        &mut add_logic_state.vim_state,
                    );
                }
                add_logic_state.script_editor_trigger_position = Some(cursor_before);
                add_logic_state.script_editor_autocomplete_active = true;
                add_logic_state.script_editor_filter_text.clear();
                add_logic_state.update_script_editor_suggestions();
                add_logic_state.has_unsaved_changes = true;
                *command_message = "Autocomplete: @ (Tab/↑↓ to navigate, Enter to select, Esc to cancel)".to_string();
                return true;
            }
        }

        if key_event.code == KeyCode::Esc && key_event.modifiers == KeyModifiers::NONE {
            match add_logic_state.editor_keybinding_mode {
                EditorKeybindingMode::Vim => {
                    if *is_edit_mode {
                        {
                            let mut editor_borrow = add_logic_state.script_content_editor.borrow_mut();
                            TextEditor::handle_input(
                                &mut editor_borrow,
                                key_event,
                                &add_logic_state.editor_keybinding_mode,
                                &mut add_logic_state.vim_state,
                            );
                        }
                        if TextEditor::is_vim_normal_mode(&add_logic_state.vim_state) {
                            *is_edit_mode = false;
                            *command_message = "VIM: Normal Mode. Esc again to exit script.".to_string();
                        }
                    } else {
                        add_logic_state.current_focus = AddLogicFocus::ScriptContentPreview;
                        app_state.ui.focus_outside_canvas = true;
                        *is_edit_mode = false;
                        *command_message = "Exited script editing.".to_string();
                    }
                }
                _ => {
                    if *is_edit_mode {
                        *is_edit_mode = false;
                        *command_message = "Exited script edit. Esc again to exit script.".to_string();
                    } else {
                        add_logic_state.current_focus = AddLogicFocus::ScriptContentPreview;
                        app_state.ui.focus_outside_canvas = true;
                        *is_edit_mode = false;
                        *command_message = "Exited script editing.".to_string();
                    }
                }
            }
            return true;
        }

        let changed = {
            let mut editor_borrow = add_logic_state.script_content_editor.borrow_mut();
            TextEditor::handle_input(
                &mut editor_borrow,
                key_event,
                &add_logic_state.editor_keybinding_mode,
                &mut add_logic_state.vim_state,
            )
        };
        if changed {
            add_logic_state.has_unsaved_changes = true;
        }
        if add_logic_state.editor_keybinding_mode == EditorKeybindingMode::Vim {
            *is_edit_mode = !TextEditor::is_vim_normal_mode(&add_logic_state.vim_state);
        }
        return true;
    }

    let action = config.get_general_action(key_event.code, key_event.modifiers);
    let current_focus = add_logic_state.current_focus;
    let mut handled = true;
    let mut new_focus = current_focus;

    match action.as_deref() {
        Some("exit_table_scroll") => {
            handled = false;
        }
        Some("move_up") => {
            match current_focus {
                AddLogicFocus::InputLogicName => {}
                AddLogicFocus::InputTargetColumn => new_focus = AddLogicFocus::InputLogicName,
                AddLogicFocus::InputDescription => new_focus = AddLogicFocus::InputTargetColumn,
                AddLogicFocus::ScriptContentPreview => new_focus = AddLogicFocus::InputDescription,
                AddLogicFocus::SaveButton => new_focus = AddLogicFocus::ScriptContentPreview,
                AddLogicFocus::CancelButton => new_focus = AddLogicFocus::SaveButton,
                _ => handled = false,
            }
        }
        Some("move_down") => {
            match current_focus {
                AddLogicFocus::InputLogicName => new_focus = AddLogicFocus::InputTargetColumn,
                AddLogicFocus::InputTargetColumn => new_focus = AddLogicFocus::InputDescription,
                AddLogicFocus::InputDescription => {
                    add_logic_state.last_canvas_field = 2;
                    new_focus = AddLogicFocus::ScriptContentPreview;
                },
                AddLogicFocus::ScriptContentPreview => new_focus = AddLogicFocus::SaveButton,
                AddLogicFocus::SaveButton => new_focus = AddLogicFocus::CancelButton,
                AddLogicFocus::CancelButton => {}
                _ => handled = false,
            }
        }
        Some("next_option") => {
            match current_focus {
                AddLogicFocus::InputLogicName | AddLogicFocus::InputTargetColumn | AddLogicFocus::InputDescription =>
                    { new_focus = AddLogicFocus::ScriptContentPreview; }
                AddLogicFocus::ScriptContentPreview => new_focus = AddLogicFocus::SaveButton,
                AddLogicFocus::SaveButton => new_focus = AddLogicFocus::CancelButton,
                AddLogicFocus::CancelButton => { }
                _ => handled = false,
            }
        }
        Some("previous_option") => {
            match current_focus {
                AddLogicFocus::InputLogicName | AddLogicFocus::InputTargetColumn | AddLogicFocus::InputDescription =>
                    { }
                AddLogicFocus::ScriptContentPreview => new_focus = AddLogicFocus::InputDescription,
                AddLogicFocus::SaveButton => new_focus = AddLogicFocus::ScriptContentPreview,
                AddLogicFocus::CancelButton => new_focus = AddLogicFocus::SaveButton,
                _ => handled = false,
            }
        }
        Some("next_field") => {
            new_focus = match current_focus {
                AddLogicFocus::InputLogicName => AddLogicFocus::InputTargetColumn,
                AddLogicFocus::InputTargetColumn => AddLogicFocus::InputDescription,
                AddLogicFocus::InputDescription => AddLogicFocus::ScriptContentPreview,
                AddLogicFocus::ScriptContentPreview => AddLogicFocus::SaveButton,
                AddLogicFocus::SaveButton => AddLogicFocus::CancelButton,
                AddLogicFocus::CancelButton => AddLogicFocus::InputLogicName,
                _ => current_focus,
            };
        }
        Some("prev_field") => {
            new_focus = match current_focus {
                AddLogicFocus::InputLogicName => AddLogicFocus::CancelButton,
                AddLogicFocus::InputTargetColumn => AddLogicFocus::InputLogicName,
                AddLogicFocus::InputDescription => AddLogicFocus::InputTargetColumn,
                AddLogicFocus::ScriptContentPreview => AddLogicFocus::InputDescription,
                AddLogicFocus::SaveButton => AddLogicFocus::ScriptContentPreview,
                AddLogicFocus::CancelButton => AddLogicFocus::SaveButton,
                _ => current_focus,
            };
        }
        Some("select") => {
            match current_focus {
                AddLogicFocus::ScriptContentPreview => {
                    new_focus = AddLogicFocus::InsideScriptContent;
                    *is_edit_mode = false;
                    app_state.ui.focus_outside_canvas = false;
                    let mode_hint = match add_logic_state.editor_keybinding_mode {
                        EditorKeybindingMode::Vim => "VIM mode - 'i'/'a'/'o' to edit",
                        _ => "Enter/Ctrl+E to edit",
                    };
                    *command_message = format!("Fullscreen script editing. {} or Esc to exit.", mode_hint);
                }
                AddLogicFocus::SaveButton => {
                    *command_message = "Save logic action".to_string();
                }
                AddLogicFocus::CancelButton => {
                    buffer_state.update_history(AppView::Admin);
                    app_state.ui.show_add_logic = false;
                    *command_message = "Cancelled Add Logic".to_string();
                    *is_edit_mode = false;
                }
                AddLogicFocus::InputLogicName | AddLogicFocus::InputTargetColumn | AddLogicFocus::InputDescription => {
                    *is_edit_mode = !*is_edit_mode;
                    *command_message = format!("Field edit mode: {}", if *is_edit_mode { "ON" } else { "OFF" });
                }
                _ => handled = false,
            }
        }
        Some("toggle_edit_mode") => {
            match current_focus {
                AddLogicFocus::InputLogicName | AddLogicFocus::InputTargetColumn | AddLogicFocus::InputDescription => {
                    *is_edit_mode = !*is_edit_mode;
                    *command_message = format!("Canvas field edit mode: {}", if *is_edit_mode { "ON" } else { "OFF" });
                }
                _ => {
                    *command_message = "Cannot toggle edit mode here.".to_string();
                }
            }
        }
        _ => handled = false,
    }

    if handled && current_focus != new_focus {
        add_logic_state.current_focus = new_focus;
        let new_is_canvas_input_focus = matches!(new_focus,
            AddLogicFocus::InputLogicName | AddLogicFocus::InputTargetColumn | AddLogicFocus::InputDescription
        );
        if new_is_canvas_input_focus {
            *is_edit_mode = false;
            app_state.ui.focus_outside_canvas = false;
        } else {
            app_state.ui.focus_outside_canvas = true;
            if matches!(new_focus, AddLogicFocus::ScriptContentPreview) {
                *is_edit_mode = false;
            }
        }
    }
    handled
}

fn replace_autocomplete_text(
    editor: &mut tui_textarea::TextArea,
    trigger_pos: (usize, usize),
    filter_len: usize,
    replacement: &str,
) {
    // use tui_textarea::CursorMove; // Already imported at the top of the module
    let filter_start_pos = (trigger_pos.0, trigger_pos.1 + 1);
    editor.move_cursor(CursorMove::Jump(filter_start_pos.0 as u16, filter_start_pos.1 as u16));
    for _ in 0..filter_len {
        editor.delete_next_char();
    }
    editor.insert_str(replacement);
}
