This commit is contained in:
Mikhail Kilin
2026-01-30 17:26:21 +03:00
parent a4cf6bac72
commit 433233d766
11 changed files with 603 additions and 315 deletions

View File

@@ -114,16 +114,16 @@ pub async fn handle(app: &mut App, key: KeyEvent) {
app.select_previous_profile_action();
}
KeyCode::Down => {
if let Some(profile) = &app.profile_info {
if let Some(profile) = app.get_profile_info() {
let max_actions = get_available_actions_count(profile);
app.select_next_profile_action(max_actions);
}
}
KeyCode::Enter => {
// Выполнить выбранное действие
if let Some(profile) = &app.profile_info {
if let Some(profile) = app.get_profile_info() {
let actions = get_available_actions_count(profile);
let action_index = app.selected_profile_action;
let action_index = app.get_selected_profile_action().unwrap_or(0);
if action_index < actions {
// Определяем какое действие выбрано
@@ -201,36 +201,42 @@ pub async fn handle(app: &mut App, key: KeyEvent) {
}
}
KeyCode::Backspace => {
app.message_search_query.pop();
// Выполняем поиск при изменении запроса
if let Some(chat_id) = app.get_selected_chat_id() {
if !app.message_search_query.is_empty() {
// Удаляем символ из запроса
if let Some(mut query) = app.get_search_query().map(|s| s.to_string()) {
query.pop();
app.update_search_query(query.clone());
// Выполняем поиск при изменении запроса
if let Some(chat_id) = app.get_selected_chat_id() {
if !query.is_empty() {
if let Ok(Ok(results)) = timeout(
Duration::from_secs(3),
app.td_client.search_messages(chat_id, &query),
)
.await
{
app.set_search_results(results);
}
} else {
app.set_search_results(Vec::new());
}
}
}
}
KeyCode::Char(c) => {
// Добавляем символ к запросу
if let Some(mut query) = app.get_search_query().map(|s| s.to_string()) {
query.push(c);
app.update_search_query(query.clone());
// Выполняем поиск при изменении запроса
if let Some(chat_id) = app.get_selected_chat_id() {
if let Ok(Ok(results)) = timeout(
Duration::from_secs(3),
app.td_client
.search_messages(chat_id, &app.message_search_query),
app.td_client.search_messages(chat_id, &query),
)
.await
{
app.set_search_results(results);
}
} else {
app.set_search_results(Vec::new());
}
}
}
KeyCode::Char(c) => {
app.message_search_query.push(c);
// Выполняем поиск при изменении запроса
if let Some(chat_id) = app.get_selected_chat_id() {
if let Ok(Ok(results)) = timeout(
Duration::from_secs(3),
app.td_client
.search_messages(chat_id, &app.message_search_query),
)
.await
{
app.set_search_results(results);
}
}
}
@@ -287,17 +293,30 @@ pub async fn handle(app: &mut App, key: KeyEvent) {
}
KeyCode::Up => {
// Переход на ряд выше (8 эмодзи в ряду)
if app.selected_reaction_index >= 8 {
app.selected_reaction_index = app.selected_reaction_index.saturating_sub(8);
app.needs_redraw = true;
if let crate::app::ChatState::ReactionPicker {
selected_index,
..
} = &mut app.chat_state
{
if *selected_index >= 8 {
*selected_index = selected_index.saturating_sub(8);
app.needs_redraw = true;
}
}
}
KeyCode::Down => {
// Переход на ряд ниже (8 эмодзи в ряду)
let new_index = app.selected_reaction_index + 8;
if new_index < app.available_reactions.len() {
app.selected_reaction_index = new_index;
app.needs_redraw = true;
if let crate::app::ChatState::ReactionPicker {
selected_index,
available_reactions,
..
} = &mut app.chat_state
{
let new_index = *selected_index + 8;
if new_index < available_reactions.len() {
*selected_index = new_index;
app.needs_redraw = true;
}
}
}
KeyCode::Enter => {
@@ -351,7 +370,7 @@ pub async fn handle(app: &mut App, key: KeyEvent) {
match key.code {
KeyCode::Char('y') | KeyCode::Char('н') | KeyCode::Enter => {
// Подтверждение удаления
if let Some(msg_id) = app.confirm_delete_message_id {
if let Some(msg_id) = app.chat_state.selected_message_id() {
if let Some(chat_id) = app.get_selected_chat_id() {
// Находим сообщение для проверки can_be_deleted_for_all_users
let can_delete_for_all = app
@@ -377,7 +396,8 @@ pub async fn handle(app: &mut App, key: KeyEvent) {
app.td_client
.current_chat_messages
.retain(|m| m.id != msg_id);
app.selected_message_index = None;
// Сбрасываем состояние
app.chat_state = crate::app::ChatState::Normal;
}
Ok(Err(e)) => {
app.error_message = Some(e);
@@ -388,11 +408,12 @@ pub async fn handle(app: &mut App, key: KeyEvent) {
}
}
}
app.confirm_delete_message_id = None;
// Закрываем модалку
app.chat_state = crate::app::ChatState::Normal;
}
KeyCode::Char('n') | KeyCode::Char('т') | KeyCode::Esc => {
// Отмена удаления
app.confirm_delete_message_id = None;
app.chat_state = crate::app::ChatState::Normal;
}
_ => {}
}
@@ -411,7 +432,7 @@ pub async fn handle(app: &mut App, key: KeyEvent) {
if let Some(i) = app.chat_list_state.selected() {
if let Some(chat) = filtered.get(i) {
let to_chat_id = chat.id;
if let Some(msg_id) = app.forwarding_message_id {
if let Some(msg_id) = app.chat_state.selected_message_id() {
if let Some(from_chat_id) = app.get_selected_chat_id() {
match timeout(
Duration::from_secs(5),
@@ -528,7 +549,7 @@ pub async fn handle(app: &mut App, key: KeyEvent) {
// Редактирование начато
} else {
// Нельзя редактировать это сообщение
app.selected_message_index = None;
app.chat_state = crate::app::ChatState::Normal;
}
return;
}
@@ -538,11 +559,12 @@ pub async fn handle(app: &mut App, key: KeyEvent) {
if let Some(chat_id) = app.get_selected_chat_id() {
let text = app.message_input.clone();
if let Some(msg_id) = app.editing_message_id {
// Режим редактирования
app.message_input.clear();
app.cursor_position = 0;
app.editing_message_id = None;
if let Some(msg_id) = app.chat_state.selected_message_id() {
if app.is_editing() {
// Режим редактирования
app.message_input.clear();
app.cursor_position = 0;
app.chat_state = crate::app::ChatState::Normal;
match timeout(
Duration::from_secs(5),
@@ -570,9 +592,14 @@ pub async fn handle(app: &mut App, key: KeyEvent) {
app.error_message = Some("Таймаут редактирования".to_string());
}
}
}
} else {
// Обычная отправка (или reply)
let reply_to_id = app.replying_to_message_id;
let reply_to_id = if app.is_replying() {
app.chat_state.selected_message_id()
} else {
None
};
// Создаём ReplyInfo ДО отправки, пока сообщение точно доступно
let reply_info = app.get_replying_to_message().map(|m| {
crate::tdlib::client::ReplyInfo {
@@ -583,7 +610,10 @@ pub async fn handle(app: &mut App, key: KeyEvent) {
});
app.message_input.clear();
app.cursor_position = 0;
app.replying_to_message_id = None;
// Сбрасываем режим reply если он был активен
if app.is_replying() {
app.chat_state = crate::app::ChatState::Normal;
}
app.last_typing_sent = None;
// Отменяем typing status
@@ -665,7 +695,7 @@ pub async fn handle(app: &mut App, key: KeyEvent) {
if key.code == KeyCode::Esc {
if app.is_selecting_message() {
// Отменить выбор сообщения
app.selected_message_index = None;
app.chat_state = crate::app::ChatState::Normal;
} else if app.is_editing() {
// Отменить редактирование
app.cancel_editing();
@@ -709,7 +739,9 @@ pub async fn handle(app: &mut App, key: KeyEvent) {
let can_delete =
msg.can_be_deleted_only_for_self || msg.can_be_deleted_for_all_users;
if can_delete {
app.confirm_delete_message_id = Some(msg.id);
app.chat_state = crate::app::ChatState::DeleteConfirmation {
message_id: msg.id,
};
}
}
}
@@ -789,8 +821,7 @@ pub async fn handle(app: &mut App, key: KeyEvent) {
match timeout(Duration::from_secs(5), app.td_client.get_profile_info(chat_id)).await
{
Ok(Ok(profile)) => {
app.profile_info = Some(profile);
app.enter_profile_mode();
app.enter_profile_mode(profile);
app.status_message = None;
}
Ok(Err(e)) => {