@@ -40,7 +40,7 @@ use ui::dock_area::{ClosePanel, DockArea, DockItem};
|
|||||||
use ui::modal::ModalButtonProps;
|
use ui::modal::ModalButtonProps;
|
||||||
use ui::notification::Notification;
|
use ui::notification::Notification;
|
||||||
use ui::popup_menu::PopupMenuExt;
|
use ui::popup_menu::PopupMenuExt;
|
||||||
use ui::{h_flex, v_flex, ContextModal, IconName, Root, Sizable, StyledExt};
|
use ui::{h_flex, v_flex, ContextModal, Disableable, IconName, Root, Sizable, StyledExt};
|
||||||
|
|
||||||
use crate::actions::{DarkMode, Logout, Settings};
|
use crate::actions::{DarkMode, Logout, Settings};
|
||||||
use crate::views::compose::compose_button;
|
use crate::views::compose::compose_button;
|
||||||
@@ -64,10 +64,17 @@ pub fn new_account(window: &mut Window, cx: &mut App) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
pub struct ChatSpace {
|
pub struct ChatSpace {
|
||||||
|
// Workspace
|
||||||
title_bar: Entity<TitleBar>,
|
title_bar: Entity<TitleBar>,
|
||||||
dock: Entity<DockArea>,
|
dock: Entity<DockArea>,
|
||||||
auth_requests: Vec<(String, RelayUrl)>,
|
|
||||||
|
// Temporarily store all authentication requests
|
||||||
|
auth_requests: HashMap<AuthRequest, bool>,
|
||||||
|
|
||||||
|
// Local state to determine if the user has set up NIP-17 relays
|
||||||
has_nip17_relays: bool,
|
has_nip17_relays: bool,
|
||||||
|
|
||||||
|
// System
|
||||||
_subscriptions: SmallVec<[Subscription; 3]>,
|
_subscriptions: SmallVec<[Subscription; 3]>,
|
||||||
_tasks: SmallVec<[Task<()>; 5]>,
|
_tasks: SmallVec<[Task<()>; 5]>,
|
||||||
}
|
}
|
||||||
@@ -174,7 +181,7 @@ impl ChatSpace {
|
|||||||
Self {
|
Self {
|
||||||
dock,
|
dock,
|
||||||
title_bar,
|
title_bar,
|
||||||
auth_requests: vec![],
|
auth_requests: HashMap::new(),
|
||||||
has_nip17_relays: true,
|
has_nip17_relays: true,
|
||||||
_subscriptions: subscriptions,
|
_subscriptions: subscriptions,
|
||||||
_tasks: tasks,
|
_tasks: tasks,
|
||||||
@@ -279,9 +286,10 @@ impl ChatSpace {
|
|||||||
|
|
||||||
loop {
|
loop {
|
||||||
if client.has_signer().await {
|
if client.has_signer().await {
|
||||||
|
total_loops += 1;
|
||||||
|
|
||||||
if css.gift_wrap_processing.load(Ordering::Acquire) {
|
if css.gift_wrap_processing.load(Ordering::Acquire) {
|
||||||
is_start_processing = true;
|
is_start_processing = true;
|
||||||
total_loops += 1;
|
|
||||||
|
|
||||||
// Reset gift wrap processing flag
|
// Reset gift wrap processing flag
|
||||||
let _ = css.gift_wrap_processing.compare_exchange(
|
let _ = css.gift_wrap_processing.compare_exchange(
|
||||||
@@ -295,8 +303,8 @@ impl ChatSpace {
|
|||||||
ingester.send(signal).await;
|
ingester.send(signal).await;
|
||||||
} else {
|
} else {
|
||||||
// Only run further if we are already processing
|
// Only run further if we are already processing
|
||||||
// Wait until after 3 loops to prevent exiting early while events are still being processed
|
// Wait until after 2 loops to prevent exiting early while events are still being processed
|
||||||
if is_start_processing && total_loops >= 3 {
|
if is_start_processing && total_loops >= 2 {
|
||||||
let signal = Signal::GiftWrapProcess(UnwrappingStatus::Complete);
|
let signal = Signal::GiftWrapProcess(UnwrappingStatus::Complete);
|
||||||
ingester.send(signal).await;
|
ingester.send(signal).await;
|
||||||
|
|
||||||
@@ -522,21 +530,19 @@ impl ChatSpace {
|
|||||||
});
|
});
|
||||||
}
|
}
|
||||||
Signal::Auth(req) => {
|
Signal::Auth(req) => {
|
||||||
let relay_url = &req.url;
|
let url = &req.url;
|
||||||
let challenge = &req.challenge;
|
|
||||||
let auto_auth = AppSettings::get_auto_auth(cx);
|
let auto_auth = AppSettings::get_auto_auth(cx);
|
||||||
let is_authenticated_relays =
|
let is_authenticated = AppSettings::read_global(cx).is_authenticated(url);
|
||||||
AppSettings::read_global(cx).is_authenticated_relays(relay_url);
|
|
||||||
|
|
||||||
view.update(cx, |this, cx| {
|
view.update(cx, |this, cx| {
|
||||||
this.push_auth_request(challenge, relay_url, cx);
|
this.push_auth_request(&req, cx);
|
||||||
|
|
||||||
if auto_auth && is_authenticated_relays {
|
if auto_auth && is_authenticated {
|
||||||
// Automatically authenticate if the relay is authenticated before
|
// Automatically authenticate if the relay is authenticated before
|
||||||
this.auth(challenge, relay_url, window, cx);
|
this.auth(req, window, cx);
|
||||||
} else {
|
} else {
|
||||||
// Otherwise open the auth request popup
|
// Otherwise open the auth request popup
|
||||||
this.open_auth_request(challenge, relay_url, window, cx);
|
this.open_auth_request(req, window, cx);
|
||||||
}
|
}
|
||||||
})
|
})
|
||||||
.ok();
|
.ok();
|
||||||
@@ -780,19 +786,18 @@ impl ChatSpace {
|
|||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
fn auth(
|
fn auth(&mut self, req: AuthRequest, window: &mut Window, cx: &mut Context<Self>) {
|
||||||
&mut self,
|
|
||||||
challenge: &str,
|
|
||||||
url: &RelayUrl,
|
|
||||||
window: &mut Window,
|
|
||||||
cx: &mut Context<Self>,
|
|
||||||
) {
|
|
||||||
let settings = AppSettings::global(cx);
|
let settings = AppSettings::global(cx);
|
||||||
let challenge = challenge.to_string();
|
|
||||||
let url = url.to_owned();
|
let challenge = req.challenge.to_owned();
|
||||||
|
let url = req.url.to_owned();
|
||||||
|
|
||||||
let challenge_clone = challenge.clone();
|
let challenge_clone = challenge.clone();
|
||||||
let url_clone = url.clone();
|
let url_clone = url.clone();
|
||||||
|
|
||||||
|
// Set Coop is sending auth for this request
|
||||||
|
self.sending_auth_request(&challenge, cx);
|
||||||
|
|
||||||
let task: Task<Result<(), Error>> = cx.background_spawn(async move {
|
let task: Task<Result<(), Error>> = cx.background_spawn(async move {
|
||||||
let client = nostr_client();
|
let client = nostr_client();
|
||||||
let css = css();
|
let css = css();
|
||||||
@@ -885,7 +890,7 @@ impl ChatSpace {
|
|||||||
.ok();
|
.ok();
|
||||||
}
|
}
|
||||||
Err(e) => {
|
Err(e) => {
|
||||||
cx.update(|window, cx| {
|
this.update_in(cx, |_, window, cx| {
|
||||||
window.push_notification(Notification::error(e.to_string()), cx);
|
window.push_notification(Notification::error(e.to_string()), cx);
|
||||||
})
|
})
|
||||||
.ok();
|
.ok();
|
||||||
@@ -895,16 +900,10 @@ impl ChatSpace {
|
|||||||
.detach();
|
.detach();
|
||||||
}
|
}
|
||||||
|
|
||||||
fn open_auth_request(
|
fn open_auth_request(&mut self, req: AuthRequest, window: &mut Window, cx: &mut Context<Self>) {
|
||||||
&mut self,
|
|
||||||
challenge: &str,
|
|
||||||
relay_url: &RelayUrl,
|
|
||||||
window: &mut Window,
|
|
||||||
cx: &mut Context<Self>,
|
|
||||||
) {
|
|
||||||
let weak_view = cx.entity().downgrade();
|
let weak_view = cx.entity().downgrade();
|
||||||
let challenge = challenge.to_string();
|
let challenge = req.challenge.to_owned();
|
||||||
let relay_url = relay_url.to_owned();
|
let relay_url = req.url.to_owned();
|
||||||
let url_as_string = SharedString::from(relay_url.to_string());
|
let url_as_string = SharedString::from(relay_url.to_string());
|
||||||
|
|
||||||
let note = Notification::new()
|
let note = Notification::new()
|
||||||
@@ -929,19 +928,25 @@ impl ChatSpace {
|
|||||||
)
|
)
|
||||||
.into_any_element()
|
.into_any_element()
|
||||||
})
|
})
|
||||||
.action(move |_window, _cx| {
|
.action(move |_window, cx| {
|
||||||
let weak_view = weak_view.clone();
|
let weak_view = weak_view.clone();
|
||||||
let challenge = challenge.clone();
|
let req = req.clone();
|
||||||
let relay_url = relay_url.clone();
|
let loading = weak_view
|
||||||
|
.read_with(cx, |this, cx| {
|
||||||
|
this.is_sending_auth_request(&req.challenge, cx)
|
||||||
|
})
|
||||||
|
.unwrap_or_default();
|
||||||
|
|
||||||
Button::new("approve")
|
Button::new("approve")
|
||||||
.label(t!("common.approve"))
|
.label(t!("common.approve"))
|
||||||
.small()
|
.small()
|
||||||
.primary()
|
.primary()
|
||||||
|
.loading(loading)
|
||||||
|
.disabled(loading)
|
||||||
.on_click(move |_e, window, cx| {
|
.on_click(move |_e, window, cx| {
|
||||||
weak_view
|
weak_view
|
||||||
.update(cx, |this, cx| {
|
.update(cx, |this, cx| {
|
||||||
this.auth(&challenge, &relay_url, window, cx);
|
this.auth(req.clone(), window, cx);
|
||||||
})
|
})
|
||||||
.ok();
|
.ok();
|
||||||
})
|
})
|
||||||
@@ -951,23 +956,42 @@ impl ChatSpace {
|
|||||||
}
|
}
|
||||||
|
|
||||||
fn reopen_auth_request(&mut self, window: &mut Window, cx: &mut Context<Self>) {
|
fn reopen_auth_request(&mut self, window: &mut Window, cx: &mut Context<Self>) {
|
||||||
for (challenge, relay_url) in self.auth_requests.clone().iter() {
|
for req in self.auth_requests.clone().into_iter() {
|
||||||
self.open_auth_request(challenge, relay_url, window, cx);
|
self.open_auth_request(req.0, window, cx);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
fn push_auth_request(&mut self, challenge: &str, url: &RelayUrl, cx: &mut Context<Self>) {
|
fn push_auth_request(&mut self, req: &AuthRequest, cx: &mut Context<Self>) {
|
||||||
self.auth_requests.push((challenge.into(), url.to_owned()));
|
self.auth_requests.insert(req.to_owned(), false);
|
||||||
cx.notify();
|
cx.notify();
|
||||||
}
|
}
|
||||||
|
|
||||||
fn remove_auth_request(&mut self, challenge: &str, cx: &mut Context<Self>) {
|
fn sending_auth_request(&mut self, challenge: &str, cx: &mut Context<Self>) {
|
||||||
if let Some(ix) = self.auth_requests.iter().position(|(c, _)| c == challenge) {
|
for (req, status) in self.auth_requests.iter_mut() {
|
||||||
self.auth_requests.remove(ix);
|
if req.challenge == challenge {
|
||||||
cx.notify();
|
*status = true;
|
||||||
|
cx.notify();
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
fn is_sending_auth_request(&self, challenge: &str, _cx: &App) -> bool {
|
||||||
|
if let Some(req) = self
|
||||||
|
.auth_requests
|
||||||
|
.iter()
|
||||||
|
.find(|(req, _)| req.challenge == challenge)
|
||||||
|
{
|
||||||
|
req.1.to_owned()
|
||||||
|
} else {
|
||||||
|
false
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
fn remove_auth_request(&mut self, challenge: &str, cx: &mut Context<Self>) {
|
||||||
|
self.auth_requests.retain(|r, _| r.challenge != challenge);
|
||||||
|
cx.notify();
|
||||||
|
}
|
||||||
|
|
||||||
fn set_onboarding_layout(&mut self, window: &mut Window, cx: &mut Context<Self>) {
|
fn set_onboarding_layout(&mut self, window: &mut Window, cx: &mut Context<Self>) {
|
||||||
let panel = Arc::new(onboarding::init(window, cx));
|
let panel = Arc::new(onboarding::init(window, cx));
|
||||||
let center = DockItem::panel(panel);
|
let center = DockItem::panel(panel);
|
||||||
@@ -1016,6 +1040,11 @@ impl ChatSpace {
|
|||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
|
fn set_no_nip17_relays(&mut self, cx: &mut Context<Self>) {
|
||||||
|
self.has_nip17_relays = false;
|
||||||
|
cx.notify();
|
||||||
|
}
|
||||||
|
|
||||||
fn load_local_account(&mut self, window: &mut Window, cx: &mut Context<Self>) {
|
fn load_local_account(&mut self, window: &mut Window, cx: &mut Context<Self>) {
|
||||||
let task = cx.background_spawn(async move {
|
let task = cx.background_spawn(async move {
|
||||||
let client = nostr_client();
|
let client = nostr_client();
|
||||||
@@ -1059,11 +1088,6 @@ impl ChatSpace {
|
|||||||
.detach();
|
.detach();
|
||||||
}
|
}
|
||||||
|
|
||||||
fn set_no_nip17_relays(&mut self, cx: &mut Context<Self>) {
|
|
||||||
self.has_nip17_relays = false;
|
|
||||||
cx.notify();
|
|
||||||
}
|
|
||||||
|
|
||||||
fn on_settings(&mut self, _ev: &Settings, window: &mut Window, cx: &mut Context<Self>) {
|
fn on_settings(&mut self, _ev: &Settings, window: &mut Window, cx: &mut Context<Self>) {
|
||||||
let view = preferences::init(window, cx);
|
let view = preferences::init(window, cx);
|
||||||
|
|
||||||
|
|||||||
@@ -15,6 +15,7 @@ use gpui::{
|
|||||||
use i18n::{shared_t, t};
|
use i18n::{shared_t, t};
|
||||||
use nostr_connect::prelude::*;
|
use nostr_connect::prelude::*;
|
||||||
use nostr_sdk::prelude::*;
|
use nostr_sdk::prelude::*;
|
||||||
|
use smallvec::{smallvec, SmallVec};
|
||||||
use theme::ActiveTheme;
|
use theme::ActiveTheme;
|
||||||
use ui::avatar::Avatar;
|
use ui::avatar::Avatar;
|
||||||
use ui::button::{Button, ButtonVariants};
|
use ui::button::{Button, ButtonVariants};
|
||||||
@@ -44,6 +45,7 @@ pub struct Account {
|
|||||||
// Panel
|
// Panel
|
||||||
name: SharedString,
|
name: SharedString,
|
||||||
focus_handle: FocusHandle,
|
focus_handle: FocusHandle,
|
||||||
|
_tasks: SmallVec<[Task<()>; 1]>,
|
||||||
}
|
}
|
||||||
|
|
||||||
impl Account {
|
impl Account {
|
||||||
@@ -59,6 +61,7 @@ impl Account {
|
|||||||
loading: false,
|
loading: false,
|
||||||
name: "Account".into(),
|
name: "Account".into(),
|
||||||
focus_handle: cx.focus_handle(),
|
focus_handle: cx.focus_handle(),
|
||||||
|
_tasks: smallvec![],
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -89,24 +92,25 @@ impl Account {
|
|||||||
// Handle auth url with the default browser
|
// Handle auth url with the default browser
|
||||||
signer.auth_url_handler(CoopAuthUrlHandler);
|
signer.auth_url_handler(CoopAuthUrlHandler);
|
||||||
|
|
||||||
// Handle connection
|
self._tasks.push(
|
||||||
cx.spawn_in(window, async move |_this, cx| {
|
// Handle connection
|
||||||
let client = nostr_client();
|
cx.spawn_in(window, async move |_this, cx| {
|
||||||
|
let client = nostr_client();
|
||||||
|
|
||||||
match signer.bunker_uri().await {
|
match signer.bunker_uri().await {
|
||||||
Ok(_) => {
|
Ok(_) => {
|
||||||
// Set the client's signer with the current nostr connect instance
|
// Set the client's signer with the current nostr connect instance
|
||||||
client.set_signer(signer).await;
|
client.set_signer(signer).await;
|
||||||
|
}
|
||||||
|
Err(e) => {
|
||||||
|
cx.update(|window, cx| {
|
||||||
|
window.push_notification(e.to_string(), cx);
|
||||||
|
})
|
||||||
|
.ok();
|
||||||
|
}
|
||||||
}
|
}
|
||||||
Err(e) => {
|
}),
|
||||||
cx.update(|window, cx| {
|
);
|
||||||
window.push_notification(e.to_string(), cx);
|
|
||||||
})
|
|
||||||
.ok();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
})
|
|
||||||
.detach();
|
|
||||||
}
|
}
|
||||||
|
|
||||||
fn set_proxy(&mut self, window: &mut Window, cx: &mut Context<Self>) {
|
fn set_proxy(&mut self, window: &mut Window, cx: &mut Context<Self>) {
|
||||||
@@ -240,24 +244,26 @@ impl Account {
|
|||||||
}
|
}
|
||||||
|
|
||||||
fn logout(&mut self, _window: &mut Window, cx: &mut Context<Self>) {
|
fn logout(&mut self, _window: &mut Window, cx: &mut Context<Self>) {
|
||||||
cx.background_spawn(async move {
|
self._tasks.push(
|
||||||
let client = nostr_client();
|
// Reset the nostr client in the background
|
||||||
let ingester = ingester();
|
cx.background_spawn(async move {
|
||||||
|
let client = nostr_client();
|
||||||
|
let ingester = ingester();
|
||||||
|
|
||||||
let filter = Filter::new()
|
let filter = Filter::new()
|
||||||
.kind(Kind::ApplicationSpecificData)
|
.kind(Kind::ApplicationSpecificData)
|
||||||
.identifier(ACCOUNT_IDENTIFIER);
|
.identifier(ACCOUNT_IDENTIFIER);
|
||||||
|
|
||||||
// Delete account
|
// Delete account
|
||||||
client.database().delete(filter).await.ok();
|
client.database().delete(filter).await.ok();
|
||||||
|
|
||||||
// Unset the client's signer
|
// Unset the client's signer
|
||||||
client.unset_signer().await;
|
client.unset_signer().await;
|
||||||
|
|
||||||
// Notify the channel about the signer being unset
|
// Notify the channel about the signer being unset
|
||||||
ingester.send(Signal::SignerUnset).await;
|
ingester.send(Signal::SignerUnset).await;
|
||||||
})
|
}),
|
||||||
.detach();
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
fn set_loading(&mut self, status: bool, cx: &mut Context<Self>) {
|
fn set_loading(&mut self, status: bool, cx: &mut Context<Self>) {
|
||||||
|
|||||||
@@ -168,26 +168,28 @@ impl Chat {
|
|||||||
}
|
}
|
||||||
|
|
||||||
/// Load all messages belonging to this room
|
/// Load all messages belonging to this room
|
||||||
fn load_messages(&self, window: &mut Window, cx: &mut Context<Self>) {
|
fn load_messages(&mut self, window: &mut Window, cx: &mut Context<Self>) {
|
||||||
let load_messages = self.room.read(cx).load_messages(cx);
|
let load_messages = self.room.read(cx).load_messages(cx);
|
||||||
|
|
||||||
cx.spawn_in(window, async move |this, cx| {
|
self._tasks.push(
|
||||||
match load_messages.await {
|
// Run the task in the background
|
||||||
Ok(events) => {
|
cx.spawn_in(window, async move |this, cx| {
|
||||||
this.update(cx, |this, cx| {
|
match load_messages.await {
|
||||||
this.insert_messages(events, cx);
|
Ok(events) => {
|
||||||
})
|
this.update(cx, |this, cx| {
|
||||||
.ok();
|
this.insert_messages(events, cx);
|
||||||
}
|
})
|
||||||
Err(e) => {
|
.ok();
|
||||||
cx.update(|window, cx| {
|
}
|
||||||
window.push_notification(e.to_string(), cx);
|
Err(e) => {
|
||||||
})
|
cx.update(|window, cx| {
|
||||||
.ok();
|
window.push_notification(e.to_string(), cx);
|
||||||
}
|
})
|
||||||
};
|
.ok();
|
||||||
})
|
}
|
||||||
.detach();
|
};
|
||||||
|
}),
|
||||||
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
#[allow(dead_code)]
|
#[allow(dead_code)]
|
||||||
|
|||||||
@@ -9,7 +9,7 @@ use gpui::prelude::FluentBuilder;
|
|||||||
use gpui::{
|
use gpui::{
|
||||||
div, img, px, relative, svg, AnyElement, App, AppContext, ClipboardItem, Context, Entity,
|
div, img, px, relative, svg, AnyElement, App, AppContext, ClipboardItem, Context, Entity,
|
||||||
EventEmitter, FocusHandle, Focusable, Image, InteractiveElement, IntoElement, ParentElement,
|
EventEmitter, FocusHandle, Focusable, Image, InteractiveElement, IntoElement, ParentElement,
|
||||||
Render, SharedString, StatefulInteractiveElement, Styled, Subscription, Window,
|
Render, SharedString, StatefulInteractiveElement, Styled, Subscription, Task, Window,
|
||||||
};
|
};
|
||||||
use i18n::{shared_t, t};
|
use i18n::{shared_t, t};
|
||||||
use nostr_connect::prelude::*;
|
use nostr_connect::prelude::*;
|
||||||
@@ -66,8 +66,8 @@ pub struct Onboarding {
|
|||||||
// Panel
|
// Panel
|
||||||
name: SharedString,
|
name: SharedString,
|
||||||
focus_handle: FocusHandle,
|
focus_handle: FocusHandle,
|
||||||
#[allow(dead_code)]
|
_subscriptions: SmallVec<[Subscription; 2]>,
|
||||||
subscriptions: SmallVec<[Subscription; 2]>,
|
_tasks: SmallVec<[Task<()>; 1]>,
|
||||||
}
|
}
|
||||||
|
|
||||||
impl Onboarding {
|
impl Onboarding {
|
||||||
@@ -104,10 +104,11 @@ impl Onboarding {
|
|||||||
nostr_connect,
|
nostr_connect,
|
||||||
nostr_connect_uri,
|
nostr_connect_uri,
|
||||||
qr_code,
|
qr_code,
|
||||||
subscriptions,
|
|
||||||
connecting: false,
|
connecting: false,
|
||||||
name: "Onboarding".into(),
|
name: "Onboarding".into(),
|
||||||
focus_handle: cx.focus_handle(),
|
focus_handle: cx.focus_handle(),
|
||||||
|
_subscriptions: subscriptions,
|
||||||
|
_tasks: smallvec![],
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -131,36 +132,37 @@ impl Onboarding {
|
|||||||
cx.notify();
|
cx.notify();
|
||||||
});
|
});
|
||||||
|
|
||||||
cx.spawn_in(window, async move |this, cx| {
|
self._tasks.push(
|
||||||
let client = nostr_client();
|
// Wait for Nostr Connect approval
|
||||||
let connect = this.read_with(cx, |this, cx| this.nostr_connect.read(cx).clone());
|
cx.spawn_in(window, async move |this, cx| {
|
||||||
|
let client = nostr_client();
|
||||||
|
let connect = this.read_with(cx, |this, cx| this.nostr_connect.read(cx).clone());
|
||||||
|
|
||||||
if let Ok(Some(signer)) = connect {
|
if let Ok(Some(signer)) = connect {
|
||||||
match signer.bunker_uri().await {
|
match signer.bunker_uri().await {
|
||||||
Ok(uri) => {
|
Ok(uri) => {
|
||||||
this.update(cx, |this, cx| {
|
this.update(cx, |this, cx| {
|
||||||
this.set_connecting(cx);
|
this.set_connecting(cx);
|
||||||
this.write_uri_to_disk(&uri, cx);
|
this.write_uri_to_disk(&uri, cx);
|
||||||
})
|
})
|
||||||
.ok();
|
.ok();
|
||||||
|
|
||||||
// Set the client's signer with the current nostr connect instance
|
// Set the client's signer with the current nostr connect instance
|
||||||
client.set_signer(signer).await;
|
client.set_signer(signer).await;
|
||||||
}
|
}
|
||||||
Err(e) => {
|
Err(e) => {
|
||||||
log::warn!("Nostr Connect instance (QR Code) is timeout. TODO: fix this");
|
this.update_in(cx, |_, window, cx| {
|
||||||
this.update_in(cx, |_, window, cx| {
|
window.push_notification(
|
||||||
window.push_notification(
|
Notification::error(e.to_string()).title("Nostr Connect"),
|
||||||
Notification::error(e.to_string()).title("Nostr Connect"),
|
cx,
|
||||||
cx,
|
);
|
||||||
);
|
})
|
||||||
})
|
.ok();
|
||||||
.ok();
|
}
|
||||||
}
|
};
|
||||||
};
|
}
|
||||||
}
|
}),
|
||||||
})
|
)
|
||||||
.detach();
|
|
||||||
}
|
}
|
||||||
|
|
||||||
fn set_proxy(&mut self, window: &mut Window, cx: &mut Context<Self>) {
|
fn set_proxy(&mut self, window: &mut Window, cx: &mut Context<Self>) {
|
||||||
|
|||||||
@@ -11,9 +11,7 @@ use registry::room::RoomKind;
|
|||||||
use registry::Registry;
|
use registry::Registry;
|
||||||
use settings::AppSettings;
|
use settings::AppSettings;
|
||||||
use theme::ActiveTheme;
|
use theme::ActiveTheme;
|
||||||
use ui::actions::OpenProfile;
|
|
||||||
use ui::avatar::Avatar;
|
use ui::avatar::Avatar;
|
||||||
use ui::context_menu::ContextMenuExt;
|
|
||||||
use ui::modal::ModalButtonProps;
|
use ui::modal::ModalButtonProps;
|
||||||
use ui::skeleton::Skeleton;
|
use ui::skeleton::Skeleton;
|
||||||
use ui::{h_flex, ContextModal, StyledExt};
|
use ui::{h_flex, ContextModal, StyledExt};
|
||||||
@@ -167,10 +165,6 @@ impl RenderOnce for RoomListItem {
|
|||||||
.child(created_at),
|
.child(created_at),
|
||||||
),
|
),
|
||||||
)
|
)
|
||||||
.context_menu(move |this, _window, _cx| {
|
|
||||||
// TODO: add share chat room
|
|
||||||
this.menu(t!("profile.view"), Box::new(OpenProfile(public_key)))
|
|
||||||
})
|
|
||||||
.hover(|this| this.bg(cx.theme().elevated_surface_background))
|
.hover(|this| this.bg(cx.theme().elevated_surface_background))
|
||||||
.on_click(move |event, window, cx| {
|
.on_click(move |event, window, cx| {
|
||||||
handler(event, window, cx);
|
handler(event, window, cx);
|
||||||
|
|||||||
@@ -176,12 +176,12 @@ impl AppSettings {
|
|||||||
!self.setting_values.authenticated_relays.is_empty() && self.setting_values.auto_auth
|
!self.setting_values.authenticated_relays.is_empty() && self.setting_values.auto_auth
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn is_authenticated_relays(&self, url: &RelayUrl) -> bool {
|
pub fn is_authenticated(&self, url: &RelayUrl) -> bool {
|
||||||
self.setting_values.authenticated_relays.contains(url)
|
self.setting_values.authenticated_relays.contains(url)
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn push_relay(&mut self, relay_url: &RelayUrl, cx: &mut Context<Self>) {
|
pub fn push_relay(&mut self, relay_url: &RelayUrl, cx: &mut Context<Self>) {
|
||||||
if !self.is_authenticated_relays(relay_url) {
|
if !self.is_authenticated(relay_url) {
|
||||||
self.setting_values
|
self.setting_values
|
||||||
.authenticated_relays
|
.authenticated_relays
|
||||||
.push(relay_url.to_owned());
|
.push(relay_url.to_owned());
|
||||||
|
|||||||
Reference in New Issue
Block a user