Skip to content
This repository has been archived by the owner on Aug 24, 2024. It is now read-only.

Commit

Permalink
feat: add command helper (#67)
Browse files Browse the repository at this point in the history
  • Loading branch information
b-avb authored Mar 27, 2024
1 parent b061e15 commit cd56089
Show file tree
Hide file tree
Showing 4 changed files with 190 additions and 51 deletions.
19 changes: 10 additions & 9 deletions src/components/atoms/helper.rs
Original file line number Diff line number Diff line change
Expand Up @@ -3,36 +3,37 @@ use dioxus::prelude::*;
pub struct HelperData {
pub title: String,
pub description: String,
pub subtitle: String,
pub example: String,
}

#[derive(Props)]
pub struct HelperProps<'a> {
helper: HelperData,
_on_click: EventHandler<'a, MouseEvent>,
on_click: EventHandler<'a, MouseEvent>,
}

pub fn Helper<'a>(cx: Scope<'a, HelperProps<'a>>) -> Element<'a> {
cx.render(rsx!(
render!(rsx!(
section {
class: "helper",
span {
class: "helper",
onclick: move |event| cx.props.on_click.call(event),
h3 {
class: "helper__title",
"{cx.props.helper.title}"
},
p {
class: "helper__description",
"{cx.props.helper.description}"
},
h4 {
class: "helper__title",
"Ejemplo"
class: "helper__subtitle",
"{cx.props.helper.subtitle}"
},
p {
class: "helper__description",
class: "helper__example",
"{cx.props.helper.example}"
}
}
}
}
))
}
26 changes: 16 additions & 10 deletions src/components/organisms/chat/utils/handle_command.rs
Original file line number Diff line number Diff line change
@@ -1,7 +1,5 @@
use matrix_sdk::{ruma::RoomId, Client};
use ruma::OwnedRoomId;

use crate::{pages::chat::chat::MessageItem, services::matrix::matrix::join_room};
use matrix_sdk::{ruma::RoomId, Client};

pub enum CommandError {
RoomIdNotFound,
Expand All @@ -10,10 +8,15 @@ pub enum CommandError {
RequestFailed,
}

pub enum Command {
Join(String),
PublicRooms,
}

pub async fn handle_command(
message_item: &MessageItem,
client: &Client,
) -> Result<OwnedRoomId, CommandError> {
) -> Result<Command, CommandError> {
let query: Vec<String> = message_item
.msg
.trim()
Expand All @@ -22,14 +25,17 @@ pub async fn handle_command(
.collect();

let action = query.get(0).ok_or(CommandError::ActionNotFound)?.as_str();
let rid = query.get(1).ok_or(CommandError::InvalidRoomId)?;

let room_id = RoomId::parse(rid).map_err(|_| CommandError::InvalidRoomId)?;

match action {
"!join" => join_room(client, &room_id)
.await
.map_err(|_| CommandError::RequestFailed),
"!join" => {
let rid = query.get(1).ok_or(CommandError::InvalidRoomId)?;
let room_id = RoomId::parse(rid).map_err(|_| CommandError::InvalidRoomId)?;
join_room(client, &room_id)
.await
.map(|id| Command::Join(id.to_string()))
.map_err(|_| CommandError::RequestFailed)
}
"!rooms" => Ok(Command::PublicRooms),
_ => Err(CommandError::ActionNotFound),
}
}
47 changes: 26 additions & 21 deletions src/hooks/use_send_message.rs
Original file line number Diff line number Diff line change
Expand Up @@ -11,8 +11,8 @@ use std::time::{Duration, UNIX_EPOCH};
use uuid::Uuid;

use crate::{
components::organisms::chat::utils::handle_command,
hooks::factory::message_factory::MessageFactory,
components::organisms::chat::utils::handle_command::{self, Command},
hooks::{factory::message_factory::MessageFactory, use_public::PublicState},
pages::chat::chat::MessageItem,
services::matrix::matrix::{send_message, TimelineMessageType, TimelineRelation},
};
Expand All @@ -23,6 +23,7 @@ use super::{
use_init_app::MessageDispatchId,
use_messages::use_messages,
use_notification::use_notification,
use_public::use_public,
use_reply::use_reply,
use_session::use_session,
use_thread::{use_thread, UseThreadState},
Expand Down Expand Up @@ -51,6 +52,7 @@ pub fn use_send_message(cx: &ScopeState) -> &UseSendMessageState {
let messages = use_messages(cx);
let session = use_session(cx);
let replying_to = use_reply(cx);
let public = use_public(cx);
let threading_to = use_thread(cx);
let message_factory = use_message_factory(cx);

Expand Down Expand Up @@ -85,32 +87,35 @@ pub fn use_send_message(cx: &ScopeState) -> &UseSendMessageState {
messages,
session,
message_dispatch_id,
message_factory
message_factory,
public
];

async move {
while let Some(message_item) = rx.next().await {
if message_item.msg.starts_with('!') {
let Err(error) = handle_command(&message_item, &client.get()).await else {
return;
};
match handle_command::handle_command(&message_item, &client.get()).await {
Ok(Command::Join(_)) => {}
Ok(Command::PublicRooms) => public.set(PublicState { show: true }),
Err(error) => {
let message = match error {
handle_command::CommandError::RoomIdNotFound => {
&key_commands_join_errors_room_not_found
}
handle_command::CommandError::ActionNotFound => {
&key_commands_join_errors_action_not_found
}
handle_command::CommandError::InvalidRoomId => {
&key_commands_join_errors_invalid_room
}
handle_command::CommandError::RequestFailed => {
&key_commands_join_errors_request_failed
}
};

let message = match error {
handle_command::CommandError::RoomIdNotFound => {
&key_commands_join_errors_room_not_found
}
handle_command::CommandError::ActionNotFound => {
&key_commands_join_errors_action_not_found
notification.handle_error(message);
}
handle_command::CommandError::InvalidRoomId => {
&key_commands_join_errors_invalid_room
}
handle_command::CommandError::RequestFailed => {
&key_commands_join_errors_request_failed
}
};

notification.handle_error(message)
}
} else {
let mut back_messages = messages.get();
let uuid = Uuid::new_v4().to_string();
Expand Down
149 changes: 138 additions & 11 deletions src/pages/chat/chat_list.rs
Original file line number Diff line number Diff line change
Expand Up @@ -6,16 +6,35 @@ use dioxus_std::{i18n::use_i18, translate};
use crate::{
components::{
atoms::{
input::InputType, message::Messages, room::RoomItem, MessageInput, Space, SpaceSkeleton,
helper::HelperData, input::InputType, message::Messages, room::RoomItem, Helper,
MessageInput, Space, SpaceSkeleton,
},
molecules::{
rooms::{CurrentRoom, FormRoomEvent},
RoomsList,
},
organisms::{chat::ActiveRoom, main::TitleHeaderMain},
organisms::{
chat::{
utils::handle_command::{self, Command},
ActiveRoom, PreviewRoom, PublicRooms,
},
main::TitleHeaderMain,
},
},
hooks::{
use_client::use_client, use_lifecycle::use_lifecycle, use_messages::use_messages, use_notification::use_notification, use_room::use_room, use_session::use_session
use_client::use_client,
use_lifecycle::use_lifecycle,
use_messages::use_messages,
use_notification::use_notification,
use_public::{use_public, PublicState},
use_room::use_room,
use_room_preview::{use_room_preview, PreviewRoom},
use_rooms::{use_rooms, RoomsList},
use_session::use_session,
},
pages::chat::chat::MessageItem,
services::matrix::matrix::{
invited_rooms, list_rooms_and_spaces, public_rooms_and_spaces, Conversations,
},
services::matrix::matrix::{list_rooms_and_spaces, Conversations},
};
Expand Down Expand Up @@ -45,7 +64,7 @@ pub fn ChatList(cx: Scope) -> Element {
let title_header =
use_shared_state::<TitleHeaderMain>(cx).expect("Unable to read title header");
let is_loading = use_state(cx, || false);

let r = room.clone();
use_lifecycle(
&cx,
Expand Down Expand Up @@ -114,6 +133,66 @@ pub fn ChatList(cx: Scope) -> Element {
}
});

enum ScrollToPosition {
Top,
Bottom,
Right,
Left,
Custom(f64, f64),
}

let on_scroll_chat_list_wrapper = move |position: ScrollToPosition| {
if let Some(e) = chat_list_wrapper_ref.read().as_ref() {
let (x, y) = match position {
ScrollToPosition::Top | ScrollToPosition::Left => (0.0, 0.0),
ScrollToPosition::Bottom => (0.0, e.get_bounding_client_rect().height()),
ScrollToPosition::Right => (e.get_bounding_client_rect().width(), 0.0),
ScrollToPosition::Custom(x, y) => (x, y),
};
e.scroll_to_with_x_and_y(x, y);
}
};

let on_click_invitation = move |evt: FormRoomEvent| {
preview.set(PreviewRoom::Invited(evt.room.clone()));
room.default();
};

let on_click_room = move |evt: FormRoomEvent| {
room.set(evt.room.clone());
room_tabs.with_mut(|tabs| tabs.insert(evt.room, vec![]));
messages.reset();
preview.default();

on_scroll_chat_list_wrapper(ScrollToPosition::Right);
};

let on_click_helper = move |_| {
on_scroll_chat_list_wrapper(ScrollToPosition::Right);
cx.spawn({
to_owned![client, notification, public];
async move {
let message_item = MessageItem {
room_id: String::new(),
msg: String::from("!rooms"),
reply_to: None,
send_to_thread: false,
};
match handle_command::handle_command(&message_item, &client).await {
Ok(Command::Join(_)) => {}
Ok(Command::PublicRooms) => public.set(PublicState { show: true }),
Err(error) => {
let message = match error {
_ => "Error",
};

notification.handle_error(message);
}
}
}
})
};

render! {
section {
class: "chat-list options",
Expand Down Expand Up @@ -217,13 +296,61 @@ pub fn ChatList(cx: Scope) -> Element {
}
)

if !room.get().name.is_empty() {
rsx!(
section {
class: "chat-list__active-room",
ActiveRoom {}
}
)

div {
class: "chat-list__content",
onclick: move |_| {
on_scroll_chat_list_wrapper(ScrollToPosition::Right)
},
if public.get().show {
rsx!(
section {
class: "chat-list__active-room",
PublicRooms {
on_back: move |_| {
on_scroll_chat_list_wrapper(ScrollToPosition::Left)
}
}
}
)
} else if !preview.get().is_none() {
rsx!(
section {
class: "chat-list__active-room",
PreviewRoom {
on_back: move |_| {
on_scroll_chat_list_wrapper(ScrollToPosition::Left)
}
}
}
)
} else if !room.get().name.is_empty(){
rsx!(
section {
class: "chat-list__active-room",
ActiveRoom {
on_back: move |_| {
on_scroll_chat_list_wrapper(ScrollToPosition::Left)
}
}
}
)
} else {
rsx!(
section {
class: "chat-list__static",
Helper {
helper: HelperData {
title: key_chat_helper_rooms_title,
description: key_chat_helper_rooms_description,
subtitle: key_chat_helper_rooms_subtitle,
example: String::from("!rooms")
},
on_click: on_click_helper
}
}
)
}
}
}
}
Expand Down

0 comments on commit cd56089

Please sign in to comment.