diff options
Diffstat (limited to 'src/components/roster_list/contact_request_manager.rs')
-rw-r--r-- | src/components/roster_list/contact_request_manager.rs | 221 |
1 files changed, 141 insertions, 80 deletions
diff --git a/src/components/roster_list/contact_request_manager.rs b/src/components/roster_list/contact_request_manager.rs index 174e677..cfb5f28 100644 --- a/src/components/roster_list/contact_request_manager.rs +++ b/src/components/roster_list/contact_request_manager.rs @@ -1,12 +1,18 @@ use std::{collections::HashSet, str::FromStr}; -use filamento::{error::{CommandError, SubscribeError}, roster::ContactStoreFields}; +use filamento::{ + error::{CommandError, SubscribeError}, + roster::ContactStoreFields, +}; use jid::{BareJID, JID}; use leptos::{html::Input, prelude::*}; use reactive_stores::Store; use thiserror::Error; -use crate::{client::Client, roster::{Roster, RosterStoreFields}}; +use crate::{ + client::Client, + roster::{Roster, RosterStoreFields}, +}; #[derive(Clone, Debug, Error)] pub enum AddContactError { @@ -21,9 +27,11 @@ pub enum AddContactError { #[component] // TODO: rename pub fn AddContact() -> impl IntoView { - let requests: ReadSignal<HashSet<BareJID>> = use_context().expect("no pending subscriptions in context"); - let set_requests: WriteSignal<HashSet<BareJID>> = use_context().expect("no pending subscriptions write signal in context"); - let roster: Store<Roster> = use_context().expect("no roster in context"); + let requests: ReadSignal<HashSet<BareJID>> = + use_context().expect("no pending subscriptions in context"); + let set_requests: WriteSignal<HashSet<BareJID>> = + use_context().expect("no pending subscriptions write signal in context"); + let roster: Store<Roster> = use_context().expect("no roster in context"); let jid = RwSignal::new("".to_string()); // TODO: compartmentalise into error component, form component... @@ -44,7 +52,7 @@ pub fn AddContact() -> impl IntoView { let client3 = client.clone(); let client4 = client.clone(); - let add_contact= Action::new_local(move |_| { + let add_contact = Action::new_local(move |_| { let client = client.clone(); async move { set_add_contact_pending.set(true); @@ -71,8 +79,8 @@ pub fn AddContact() -> impl IntoView { Err(e) => { set_error.set(Some(e.into())); set_add_contact_pending.set(false); - return; - }, + return; + } }; set_add_contact_pending.set(false); @@ -90,19 +98,26 @@ pub fn AddContact() -> impl IntoView { } }); - let outgoing = move || roster.contacts().get().into_iter().filter(|(jid, contact)| { - match *contact.contact.subscription().read() { - filamento::roster::Subscription::None => false, - filamento::roster::Subscription::PendingOut => true, - filamento::roster::Subscription::PendingIn => false, - filamento::roster::Subscription::PendingInPendingOut => true, - filamento::roster::Subscription::OnlyOut => false, - filamento::roster::Subscription::OnlyIn => false, - filamento::roster::Subscription::OutPendingIn => false, - filamento::roster::Subscription::InPendingOut => true, - filamento::roster::Subscription::Buddy => false, - } - }).collect::<Vec<_>>(); + let outgoing = move || { + roster + .contacts() + .get() + .into_iter() + .filter( + |(jid, contact)| match *contact.contact.subscription().read() { + filamento::roster::Subscription::None => false, + filamento::roster::Subscription::PendingOut => true, + filamento::roster::Subscription::PendingIn => false, + filamento::roster::Subscription::PendingInPendingOut => true, + filamento::roster::Subscription::OnlyOut => false, + filamento::roster::Subscription::OnlyIn => false, + filamento::roster::Subscription::OutPendingIn => false, + filamento::roster::Subscription::InPendingOut => true, + filamento::roster::Subscription::Buddy => false, + }, + ) + .collect::<Vec<_>>() + }; let accept_friend_request = Action::new_local(move |jid: &BareJID| { let client = client2.clone(); @@ -129,70 +144,116 @@ pub fn AddContact() -> impl IntoView { async move { // TODO: error client.unsubscribe_from_contact(jid).await; - } }); view! { <div class="add-contact-menu"> - <div> - {error_message} - <form on:submit=move |ev| { - ev.prevent_default(); - add_contact.dispatch(()); - }> - <input - disabled=add_contact_pending - placeholder="JID" - type="text" - node_ref=jid_input - bind:value=jid - name="jid" - id="jid" - autofocus="true" - /> - <input disabled=add_contact_pending class="button" type="submit" value="Send Friend Request" /> - </form> - </div> - {move || if !requests.read().is_empty() { - view! { - <div> - <h3>Incoming Subscription Requests</h3> - <For each=move || requests.get() key=|request| request.clone() let(request)> - { - let request2 = request.clone(); - let request3 = request.clone(); - let jid_string = move || request.to_string(); - view! { - <div class="jid-with-button"><div class="jid">{jid_string}</div> - <div><div class="button" on:click=move |_| { accept_friend_request.dispatch(request2.clone()); } >Accept</div><div class="button" on:click=move |_| { reject_friend_request.dispatch(request3.clone()); } >Reject</div></div></div> - } - } - </For> - </div> - }.into_any() - } else { - view! {}.into_any() - }} - {move || if !outgoing().is_empty() { - view! { - <div> - <h3>Pending Outgoing Subscription Requests</h3> - <For each=move || outgoing() key=|(jid, _contact)| jid.clone() let((jid, contact))> - { - let jid2 = jid.clone(); - let jid_string = move || jid.to_string(); - view! { - <div class="jid-with-button"><div class="jid">{jid_string}</div><div class="button" on:click=move |_| { cancel_subscription_request.dispatch(jid2.clone()); } >Cancel</div></div> - } - } - </For> - </div> - }.into_any() - } else { - view! {}.into_any() - }} + <div> + {error_message} + <form on:submit=move |ev| { + ev.prevent_default(); + add_contact.dispatch(()); + }> + <input + disabled=add_contact_pending + placeholder="JID" + type="text" + node_ref=jid_input + bind:value=jid + name="jid" + id="jid" + autofocus="true" + /> + <input + disabled=add_contact_pending + class="button" + type="submit" + value="Send Friend Request" + /> + </form> + </div> + {move || { + if !requests.read().is_empty() { + view! { + <div> + <h3>Incoming Subscription Requests</h3> + <For + each=move || requests.get() + key=|request| request.clone() + let(request) + > + { + let request2 = request.clone(); + let request3 = request.clone(); + let jid_string = move || request.to_string(); + view! { + <div class="jid-with-button"> + <div class="jid">{jid_string}</div> + <div> + <div + class="button" + on:click=move |_| { + accept_friend_request.dispatch(request2.clone()); + } + > + Accept + </div> + <div + class="button" + on:click=move |_| { + reject_friend_request.dispatch(request3.clone()); + } + > + Reject + </div> + </div> + </div> + } + } + </For> + </div> + } + .into_any() + } else { + view! {}.into_any() + } + }} + {move || { + if !outgoing().is_empty() { + view! { + <div> + <h3>Pending Outgoing Subscription Requests</h3> + <For + each=move || outgoing() + key=|(jid, _contact)| jid.clone() + let((jid, contact)) + > + { + let jid2 = jid.clone(); + let jid_string = move || jid.to_string(); + view! { + <div class="jid-with-button"> + <div class="jid">{jid_string}</div> + <div + class="button" + on:click=move |_| { + cancel_subscription_request.dispatch(jid2.clone()); + } + > + Cancel + </div> + </div> + } + } + </For> + </div> + } + .into_any() + } else { + view! {}.into_any() + } + }} </div> } } - |