mirror of
https://github.com/adoyle0/leptos-use.git
synced 2025-01-23 09:09:21 -05:00
Merge branch 'main' into leptos-0.7
# Conflicts: # Cargo.toml # examples/use_broadcast_channel/Cargo.toml # examples/use_cookie/Cargo.toml # examples/use_websocket/Cargo.toml # src/use_websocket.rs
This commit is contained in:
commit
b6a5d36df1
13 changed files with 105 additions and 57 deletions
|
@ -9,6 +9,14 @@ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0
|
||||||
|
|
||||||
- `use_prefers_reduced_motion`
|
- `use_prefers_reduced_motion`
|
||||||
|
|
||||||
|
### Breaking Change 🛠
|
||||||
|
|
||||||
|
- `use_websocket` now supports different types for sending and receiving messages
|
||||||
|
|
||||||
|
### Change 🔥
|
||||||
|
|
||||||
|
- There is now a feature for almost every function to get better compile and rust-analyzer times.
|
||||||
|
|
||||||
## [0.12.0] - 2024-08-14
|
## [0.12.0] - 2024-08-14
|
||||||
|
|
||||||
> Make sure you also update `cargo-leptos` to the latest version if you use that.
|
> Make sure you also update `cargo-leptos` to the latest version if you use that.
|
||||||
|
|
|
@ -16,7 +16,7 @@ homepage = "https://leptos-use.rs"
|
||||||
actix-web = { version = "4", optional = true, default-features = false }
|
actix-web = { version = "4", optional = true, default-features = false }
|
||||||
async-trait = { version = "0.1", optional = true }
|
async-trait = { version = "0.1", optional = true }
|
||||||
cfg-if = "1"
|
cfg-if = "1"
|
||||||
codee = { version = "0.1", optional = true }
|
codee = { version = "0.2", optional = true }
|
||||||
cookie = { version = "0.18", features = ["percent-encode"], optional = true }
|
cookie = { version = "0.18", features = ["percent-encode"], optional = true }
|
||||||
default-struct-builder = "0.5"
|
default-struct-builder = "0.5"
|
||||||
futures-util = { version = "0.3", optional = true }
|
futures-util = { version = "0.3", optional = true }
|
||||||
|
@ -40,7 +40,7 @@ wasm-bindgen-futures = "0.4"
|
||||||
web-sys = { version = "=0.3.70", optional = true }
|
web-sys = { version = "=0.3.70", optional = true }
|
||||||
|
|
||||||
[dev-dependencies]
|
[dev-dependencies]
|
||||||
codee = { version = "0.1", features = [
|
codee = { version = "0.2", features = [
|
||||||
"json_serde",
|
"json_serde",
|
||||||
"msgpack_serde",
|
"msgpack_serde",
|
||||||
"base64",
|
"base64",
|
||||||
|
|
|
@ -94,5 +94,8 @@ panic = "abort"
|
||||||
|
|
||||||
[lib]
|
[lib]
|
||||||
|
|
||||||
|
[workspace.dependencies]
|
||||||
|
codee = { version = "0.2" }
|
||||||
|
|
||||||
[package.metadata.leptos]
|
[package.metadata.leptos]
|
||||||
lib-profile-release = "wasm-release"
|
lib-profile-release = "wasm-release"
|
||||||
|
|
|
@ -8,7 +8,7 @@ crate-type = ["cdylib", "rlib"]
|
||||||
|
|
||||||
[dependencies]
|
[dependencies]
|
||||||
axum = { version = "0.7", optional = true }
|
axum = { version = "0.7", optional = true }
|
||||||
codee = "0.1"
|
codee.workspace = true
|
||||||
console_error_panic_hook = "0.1"
|
console_error_panic_hook = "0.1"
|
||||||
console_log = "1"
|
console_log = "1"
|
||||||
cfg-if = "1"
|
cfg-if = "1"
|
||||||
|
|
|
@ -8,7 +8,7 @@ leptos = { git = "https://github.com/leptos-rs/leptos", features = [
|
||||||
"nightly",
|
"nightly",
|
||||||
"csr",
|
"csr",
|
||||||
] }
|
] }
|
||||||
codee = "0.1"
|
codee.workspace = true
|
||||||
console_error_panic_hook = "0.1"
|
console_error_panic_hook = "0.1"
|
||||||
console_log = "1"
|
console_log = "1"
|
||||||
log = "0.4"
|
log = "0.4"
|
||||||
|
|
|
@ -8,7 +8,7 @@ leptos = { git = "https://github.com/leptos-rs/leptos", features = [
|
||||||
"nightly",
|
"nightly",
|
||||||
"csr",
|
"csr",
|
||||||
] }
|
] }
|
||||||
codee = "0.1"
|
codee.workspace = true
|
||||||
console_error_panic_hook = "0.1"
|
console_error_panic_hook = "0.1"
|
||||||
console_log = "1"
|
console_log = "1"
|
||||||
log = "0.4"
|
log = "0.4"
|
||||||
|
|
|
@ -4,7 +4,7 @@ version = "0.1.0"
|
||||||
edition = "2021"
|
edition = "2021"
|
||||||
|
|
||||||
[dependencies]
|
[dependencies]
|
||||||
codee = { version = "0.1", features = ["json_serde"] }
|
codee = { workspace = true, features = ["json_serde"] }
|
||||||
console_error_panic_hook = "0.1"
|
console_error_panic_hook = "0.1"
|
||||||
console_log = "1"
|
console_log = "1"
|
||||||
leptos = { git = "https://github.com/leptos-rs/leptos", features = [
|
leptos = { git = "https://github.com/leptos-rs/leptos", features = [
|
||||||
|
|
|
@ -8,7 +8,7 @@ leptos = { git = "https://github.com/leptos-rs/leptos", features = [
|
||||||
"nightly",
|
"nightly",
|
||||||
"csr",
|
"csr",
|
||||||
] }
|
] }
|
||||||
codee = { version = "0.1", features = ["msgpack_serde"] }
|
codee = { workspace = true, features = ["msgpack_serde"] }
|
||||||
console_error_panic_hook = "0.1"
|
console_error_panic_hook = "0.1"
|
||||||
console_log = "1"
|
console_log = "1"
|
||||||
log = "0.4"
|
log = "0.4"
|
||||||
|
|
|
@ -33,7 +33,7 @@ fn Demo() -> impl IntoView {
|
||||||
open,
|
open,
|
||||||
close,
|
close,
|
||||||
..
|
..
|
||||||
} = use_websocket::<Apple, MsgpackSerdeCodec>("wss://echo.websocket.events/");
|
} = use_websocket::<Apple, Apple, MsgpackSerdeCodec>("wss://echo.websocket.events/");
|
||||||
|
|
||||||
let send_message = move |_| {
|
let send_message = move |_| {
|
||||||
let m = Apple {
|
let m = Apple {
|
||||||
|
@ -101,7 +101,7 @@ fn Demo() -> impl IntoView {
|
||||||
close: close2,
|
close: close2,
|
||||||
message: message2,
|
message: message2,
|
||||||
..
|
..
|
||||||
} = use_websocket_with_options::<String, FromToStringCodec>(
|
} = use_websocket_with_options::<String, String, FromToStringCodec>(
|
||||||
"wss://echo.websocket.events/",
|
"wss://echo.websocket.events/",
|
||||||
UseWebSocketOptions::default()
|
UseWebSocketOptions::default()
|
||||||
.immediate(false)
|
.immediate(false)
|
||||||
|
|
|
@ -3,6 +3,7 @@ use cfg_if::cfg_if;
|
||||||
use default_struct_builder::DefaultBuilder;
|
use default_struct_builder::DefaultBuilder;
|
||||||
use leptos::prelude::{wrappers::read::Signal, *};
|
use leptos::prelude::{wrappers::read::Signal, *};
|
||||||
use std::rc::Rc;
|
use std::rc::Rc;
|
||||||
|
use wasm_bindgen::JsValue;
|
||||||
|
|
||||||
/// Reactive [Notification API](https://developer.mozilla.org/en-US/docs/Web/API/Notification).
|
/// Reactive [Notification API](https://developer.mozilla.org/en-US/docs/Web/API/Notification).
|
||||||
///
|
///
|
||||||
|
@ -219,7 +220,6 @@ impl From<NotificationDirection> for web_sys::NotificationDirection {
|
||||||
/// See [MDN Docs](https://developer.mozilla.org/en-US/docs/Web/API/notification) for more info.
|
/// See [MDN Docs](https://developer.mozilla.org/en-US/docs/Web/API/notification) for more info.
|
||||||
///
|
///
|
||||||
/// The following implementations are missing:
|
/// The following implementations are missing:
|
||||||
/// - `vibrate`
|
|
||||||
#[derive(DefaultBuilder, Clone)]
|
#[derive(DefaultBuilder, Clone)]
|
||||||
#[cfg_attr(feature = "ssr", allow(dead_code))]
|
#[cfg_attr(feature = "ssr", allow(dead_code))]
|
||||||
pub struct UseWebNotificationOptions {
|
pub struct UseWebNotificationOptions {
|
||||||
|
@ -268,10 +268,15 @@ pub struct UseWebNotificationOptions {
|
||||||
renotify: bool,
|
renotify: bool,
|
||||||
|
|
||||||
/// A boolean value specifying whether the notification should be silent, regardless of the device settings.
|
/// A boolean value specifying whether the notification should be silent, regardless of the device settings.
|
||||||
/// The default is `false`, which means the notification is not silent. If `true`, then the notification will be silent.
|
/// The default is `null`, which means the notification is not silent. If `true`, then the notification will be silent.
|
||||||
#[builder(into)]
|
#[builder(into)]
|
||||||
silent: Option<bool>,
|
silent: Option<bool>,
|
||||||
|
|
||||||
|
/// A `Vec<u16>` specifying the vibration pattern in milliseconds for vibrating and not vibrating.
|
||||||
|
/// The last entry can be a vibration since it stops automatically after each period.
|
||||||
|
#[builder(into)]
|
||||||
|
vibrate: Option<Vec<u16>>,
|
||||||
|
|
||||||
/// Called when the user clicks on displayed `Notification`.
|
/// Called when the user clicks on displayed `Notification`.
|
||||||
on_click: Rc<dyn Fn(web_sys::Event)>,
|
on_click: Rc<dyn Fn(web_sys::Event)>,
|
||||||
|
|
||||||
|
@ -299,6 +304,7 @@ impl Default for UseWebNotificationOptions {
|
||||||
require_interaction: false,
|
require_interaction: false,
|
||||||
renotify: false,
|
renotify: false,
|
||||||
silent: None,
|
silent: None,
|
||||||
|
vibrate: None,
|
||||||
on_click: Rc::new(|_| {}),
|
on_click: Rc::new(|_| {}),
|
||||||
on_close: Rc::new(|_| {}),
|
on_close: Rc::new(|_| {}),
|
||||||
on_error: Rc::new(|_| {}),
|
on_error: Rc::new(|_| {}),
|
||||||
|
@ -336,6 +342,9 @@ impl From<&UseWebNotificationOptions> for web_sys::NotificationOptions {
|
||||||
web_sys_options.set_tag(tag);
|
web_sys_options.set_tag(tag);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if let Some(vibrate) = &options.vibrate {
|
||||||
|
web_sys_options.set_vibrate(&vibration_pattern_to_jsvalue(vibrate));
|
||||||
|
}
|
||||||
web_sys_options
|
web_sys_options
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -345,7 +354,6 @@ impl From<&UseWebNotificationOptions> for web_sys::NotificationOptions {
|
||||||
/// See [MDN Docs](https://developer.mozilla.org/en-US/docs/Web/API/notification) for more info.
|
/// See [MDN Docs](https://developer.mozilla.org/en-US/docs/Web/API/notification) for more info.
|
||||||
///
|
///
|
||||||
/// The following implementations are missing:
|
/// The following implementations are missing:
|
||||||
/// - `vibrate`
|
|
||||||
#[derive(DefaultBuilder, Default)]
|
#[derive(DefaultBuilder, Default)]
|
||||||
#[cfg_attr(feature = "ssr", allow(dead_code))]
|
#[cfg_attr(feature = "ssr", allow(dead_code))]
|
||||||
pub struct ShowOptions {
|
pub struct ShowOptions {
|
||||||
|
@ -396,9 +404,14 @@ pub struct ShowOptions {
|
||||||
renotify: Option<bool>,
|
renotify: Option<bool>,
|
||||||
|
|
||||||
/// A boolean value specifying whether the notification should be silent, regardless of the device settings.
|
/// A boolean value specifying whether the notification should be silent, regardless of the device settings.
|
||||||
/// The default is `false`, which means the notification is not silent. If `true`, then the notification will be silent.
|
/// The default is `null`, which means the notification is not silent. If `true`, then the notification will be silent.
|
||||||
#[builder(into)]
|
#[builder(into)]
|
||||||
silent: Option<bool>,
|
silent: Option<bool>,
|
||||||
|
|
||||||
|
/// A `Vec<u16>` specifying the vibration pattern in milliseconds for vibrating and not vibrating.
|
||||||
|
/// The last entry can be a vibration since it stops automatically after each period.
|
||||||
|
#[builder(into)]
|
||||||
|
vibrate: Option<Vec<u16>>,
|
||||||
}
|
}
|
||||||
|
|
||||||
#[cfg(not(feature = "ssr"))]
|
#[cfg(not(feature = "ssr"))]
|
||||||
|
@ -439,6 +452,10 @@ impl ShowOptions {
|
||||||
if let Some(silent) = self.silent {
|
if let Some(silent) = self.silent {
|
||||||
options.set_silent(Some(silent));
|
options.set_silent(Some(silent));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if let Some(vibrate) = &self.vibrate {
|
||||||
|
options.set_vibrate(&vibration_pattern_to_jsvalue(vibrate));
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -453,6 +470,15 @@ fn browser_supports_notifications() -> bool {
|
||||||
false
|
false
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// Helper function to convert a slice of `u16` into a `JsValue` array that represents a vibration pattern
|
||||||
|
fn vibration_pattern_to_jsvalue(pattern: &[u16]) -> JsValue {
|
||||||
|
let array = js_sys::Array::new();
|
||||||
|
for &value in pattern.iter() {
|
||||||
|
array.push(&JsValue::from(value));
|
||||||
|
}
|
||||||
|
array.into()
|
||||||
|
}
|
||||||
|
|
||||||
#[derive(Copy, Clone, PartialEq, Eq, Debug, Default)]
|
#[derive(Copy, Clone, PartialEq, Eq, Debug, Default)]
|
||||||
/// The permission to send notifications
|
/// The permission to send notifications
|
||||||
pub enum NotificationPermission {
|
pub enum NotificationPermission {
|
||||||
|
|
|
@ -1,17 +1,15 @@
|
||||||
#![cfg_attr(feature = "ssr", allow(unused_variables, unused_imports, dead_code))]
|
#![cfg_attr(feature = "ssr", allow(unused_variables, unused_imports, dead_code))]
|
||||||
|
|
||||||
|
use crate::{core::ConnectionReadyState, ReconnectLimit};
|
||||||
use cfg_if::cfg_if;
|
use cfg_if::cfg_if;
|
||||||
|
use codee::{CodecError, Decoder, Encoder, HybridCoderError, HybridDecoder, HybridEncoder};
|
||||||
|
use default_struct_builder::DefaultBuilder;
|
||||||
|
use js_sys::Array;
|
||||||
use leptos::{leptos_dom::helpers::TimeoutHandle, prelude::*};
|
use leptos::{leptos_dom::helpers::TimeoutHandle, prelude::*};
|
||||||
|
use std::marker::PhantomData;
|
||||||
use std::sync::{atomic::AtomicBool, Arc};
|
use std::sync::{atomic::AtomicBool, Arc};
|
||||||
use std::time::Duration;
|
use std::time::Duration;
|
||||||
use thiserror::Error;
|
use thiserror::Error;
|
||||||
|
|
||||||
use crate::{core::ConnectionReadyState, ReconnectLimit};
|
|
||||||
use codee::{
|
|
||||||
CodecError, Decoder, Encoder, HybridCoderError, HybridDecoder, HybridEncoder, IsBinary,
|
|
||||||
};
|
|
||||||
use default_struct_builder::DefaultBuilder;
|
|
||||||
use js_sys::Array;
|
|
||||||
use wasm_bindgen::prelude::*;
|
use wasm_bindgen::prelude::*;
|
||||||
use web_sys::{BinaryType, CloseEvent, Event, MessageEvent, WebSocket};
|
use web_sys::{BinaryType, CloseEvent, Event, MessageEvent, WebSocket};
|
||||||
|
|
||||||
|
@ -44,7 +42,7 @@ use web_sys::{BinaryType, CloseEvent, Event, MessageEvent, WebSocket};
|
||||||
/// open,
|
/// open,
|
||||||
/// close,
|
/// close,
|
||||||
/// ..
|
/// ..
|
||||||
/// } = use_websocket::<String, FromToStringCodec>("wss://echo.websocket.events/");
|
/// } = use_websocket::<String, String, FromToStringCodec>("wss://echo.websocket.events/");
|
||||||
///
|
///
|
||||||
/// let send_message = move |_| {
|
/// let send_message = move |_| {
|
||||||
/// send(&"Hello, world!".to_string());
|
/// send(&"Hello, world!".to_string());
|
||||||
|
@ -97,7 +95,7 @@ use web_sys::{BinaryType, CloseEvent, Event, MessageEvent, WebSocket};
|
||||||
/// message,
|
/// message,
|
||||||
/// send,
|
/// send,
|
||||||
/// ..
|
/// ..
|
||||||
/// } = use_websocket::<SomeData, MsgpackSerdeCodec>("wss://some.websocket.server/");
|
/// } = use_websocket::<SomeData, SomeData, MsgpackSerdeCodec>("wss://some.websocket.server/");
|
||||||
///
|
///
|
||||||
/// let send_data = move || {
|
/// let send_data = move || {
|
||||||
/// send(&SomeData {
|
/// send(&SomeData {
|
||||||
|
@ -188,7 +186,7 @@ use web_sys::{BinaryType, CloseEvent, Event, MessageEvent, WebSocket};
|
||||||
/// message,
|
/// message,
|
||||||
/// send,
|
/// send,
|
||||||
/// ..
|
/// ..
|
||||||
/// } = use_websocket::<String, FromToStringCodec>("ws:://some.websocket.io");
|
/// } = use_websocket::<String, String, FromToStringCodec>("ws:://some.websocket.io");
|
||||||
///
|
///
|
||||||
/// provide_context(WebsocketContext::new(message, Arc::new(send.clone())));
|
/// provide_context(WebsocketContext::new(message, Arc::new(send.clone())));
|
||||||
/// #
|
/// #
|
||||||
|
@ -228,45 +226,47 @@ use web_sys::{BinaryType, CloseEvent, Event, MessageEvent, WebSocket};
|
||||||
/// ## Server-Side Rendering
|
/// ## Server-Side Rendering
|
||||||
///
|
///
|
||||||
/// On the server the returned functions amount to no-ops.
|
/// On the server the returned functions amount to no-ops.
|
||||||
pub fn use_websocket<T, C>(
|
pub fn use_websocket<Tx, Rx, C>(
|
||||||
url: &str,
|
url: &str,
|
||||||
) -> UseWebSocketReturn<
|
) -> UseWebSocketReturn<
|
||||||
T,
|
Tx,
|
||||||
|
Rx,
|
||||||
impl Fn() + Clone + 'static,
|
impl Fn() + Clone + 'static,
|
||||||
impl Fn() + Clone + 'static,
|
impl Fn() + Clone + 'static,
|
||||||
impl Fn(&T) + Clone + 'static,
|
impl Fn(&Tx) + Clone + 'static,
|
||||||
>
|
>
|
||||||
where
|
where
|
||||||
T: Send + Sync + 'static,
|
Tx: Send + Sync + 'static,
|
||||||
C: Encoder<T> + Decoder<T>,
|
Rx: Send + Sync + 'static,
|
||||||
C: IsBinary<T, <C as Decoder<T>>::Encoded>,
|
C: Encoder<Tx> + Decoder<Rx>,
|
||||||
C: HybridDecoder<T, <C as Decoder<T>>::Encoded, Error = <C as Decoder<T>>::Error>,
|
C: HybridEncoder<Tx, <C as Encoder<Tx>>::Encoded, Error = <C as Encoder<Tx>>::Error>,
|
||||||
C: HybridEncoder<T, <C as Encoder<T>>::Encoded, Error = <C as Encoder<T>>::Error>,
|
C: HybridDecoder<Rx, <C as Decoder<Rx>>::Encoded, Error = <C as Decoder<Rx>>::Error>,
|
||||||
{
|
{
|
||||||
use_websocket_with_options::<T, C>(url, UseWebSocketOptions::default())
|
use_websocket_with_options::<Tx, Rx, C>(url, UseWebSocketOptions::default())
|
||||||
}
|
}
|
||||||
|
|
||||||
/// Version of [`use_websocket`] that takes `UseWebSocketOptions`. See [`use_websocket`] for how to use.
|
/// Version of [`use_websocket`] that takes `UseWebSocketOptions`. See [`use_websocket`] for how to use.
|
||||||
#[allow(clippy::type_complexity)]
|
#[allow(clippy::type_complexity)]
|
||||||
pub fn use_websocket_with_options<T, C>(
|
pub fn use_websocket_with_options<Tx, Rx, C>(
|
||||||
url: &str,
|
url: &str,
|
||||||
options: UseWebSocketOptions<
|
options: UseWebSocketOptions<
|
||||||
T,
|
Rx,
|
||||||
HybridCoderError<<C as Encoder<T>>::Error>,
|
HybridCoderError<<C as Encoder<Tx>>::Error>,
|
||||||
HybridCoderError<<C as Decoder<T>>::Error>,
|
HybridCoderError<<C as Decoder<Rx>>::Error>,
|
||||||
>,
|
>,
|
||||||
) -> UseWebSocketReturn<
|
) -> UseWebSocketReturn<
|
||||||
T,
|
Tx,
|
||||||
|
Rx,
|
||||||
impl Fn() + Clone + 'static,
|
impl Fn() + Clone + 'static,
|
||||||
impl Fn() + Clone + 'static,
|
impl Fn() + Clone + 'static,
|
||||||
impl Fn(&T) + Clone + 'static,
|
impl Fn(&Tx) + Clone + 'static,
|
||||||
>
|
>
|
||||||
where
|
where
|
||||||
T: Send + Sync + 'static,
|
Tx: Send + Sync + 'static,
|
||||||
C: Encoder<T> + Decoder<T>,
|
Rx: Send + Sync + 'static,
|
||||||
C: IsBinary<T, <C as Decoder<T>>::Encoded>,
|
C: Encoder<Tx> + Decoder<Rx>,
|
||||||
C: HybridDecoder<T, <C as Decoder<T>>::Encoded, Error = <C as Decoder<T>>::Error>,
|
C: HybridEncoder<Tx, <C as Encoder<Tx>>::Encoded, Error = <C as Encoder<Tx>>::Error>,
|
||||||
C: HybridEncoder<T, <C as Encoder<T>>::Encoded, Error = <C as Encoder<T>>::Error>,
|
C: HybridDecoder<Rx, <C as Decoder<Rx>>::Encoded, Error = <C as Decoder<Rx>>::Error>,
|
||||||
{
|
{
|
||||||
let url = normalize_url(url);
|
let url = normalize_url(url);
|
||||||
|
|
||||||
|
@ -301,7 +301,11 @@ where
|
||||||
let reconnect_ref: StoredValue<Option<Arc<dyn Fn() + Send + Sync>>> =
|
let reconnect_ref: StoredValue<Option<Arc<dyn Fn() + Send + Sync>>> =
|
||||||
StoredValue::new(None);
|
StoredValue::new(None);
|
||||||
reconnect_ref.set_value({
|
reconnect_ref.set_value({
|
||||||
|
let unmounted = Arc::clone(&unmounted);
|
||||||
|
|
||||||
Some(Arc::new(move || {
|
Some(Arc::new(move || {
|
||||||
|
let unmounted = Arc::clone(&unmounted);
|
||||||
|
|
||||||
if !manually_closed_ref.get_value()
|
if !manually_closed_ref.get_value()
|
||||||
&& !reconnect_limit.is_exceeded_by(reconnect_times_ref.get_value())
|
&& !reconnect_limit.is_exceeded_by(reconnect_times_ref.get_value())
|
||||||
&& ws_ref
|
&& ws_ref
|
||||||
|
@ -311,6 +315,9 @@ where
|
||||||
reconnect_timer_ref.set_value(
|
reconnect_timer_ref.set_value(
|
||||||
set_timeout_with_handle(
|
set_timeout_with_handle(
|
||||||
move || {
|
move || {
|
||||||
|
if unmounted.get() {
|
||||||
|
return;
|
||||||
|
}
|
||||||
if let Some(connect) = connect_ref.get_value() {
|
if let Some(connect) = connect_ref.get_value() {
|
||||||
connect();
|
connect();
|
||||||
reconnect_times_ref.update_value(|current| *current += 1);
|
reconnect_times_ref.update_value(|current| *current += 1);
|
||||||
|
@ -552,8 +559,8 @@ where
|
||||||
let send = {
|
let send = {
|
||||||
let on_error = Arc::clone(&on_error);
|
let on_error = Arc::clone(&on_error);
|
||||||
|
|
||||||
move |value: &T| {
|
move |value: &Tx| {
|
||||||
if C::is_binary() {
|
if C::is_binary_encoder() {
|
||||||
match C::encode_bin(value) {
|
match C::encode_bin(value) {
|
||||||
Ok(val) => send_bytes(&val),
|
Ok(val) => send_bytes(&val),
|
||||||
Err(err) => on_error(CodecError::Encode(err).into()),
|
Err(err) => on_error(CodecError::Encode(err).into()),
|
||||||
|
@ -607,6 +614,7 @@ where
|
||||||
open,
|
open,
|
||||||
close,
|
close,
|
||||||
send,
|
send,
|
||||||
|
_marker: PhantomData,
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -614,15 +622,15 @@ type ArcFnBytes = Arc<dyn Fn(&[u8]) + Send + Sync>;
|
||||||
|
|
||||||
/// Options for [`use_websocket_with_options`].
|
/// Options for [`use_websocket_with_options`].
|
||||||
#[derive(DefaultBuilder)]
|
#[derive(DefaultBuilder)]
|
||||||
pub struct UseWebSocketOptions<T, E, D>
|
pub struct UseWebSocketOptions<Rx, E, D>
|
||||||
where
|
where
|
||||||
T: ?Sized,
|
Rx: ?Sized,
|
||||||
{
|
{
|
||||||
/// `WebSocket` connect callback.
|
/// `WebSocket` connect callback.
|
||||||
on_open: Arc<dyn Fn(Event) + Send + Sync>,
|
on_open: Arc<dyn Fn(Event) + Send + Sync>,
|
||||||
/// `WebSocket` message callback for typed message decoded by codec.
|
/// `WebSocket` message callback for typed message decoded by codec.
|
||||||
#[builder(skip)]
|
#[builder(skip)]
|
||||||
on_message: Arc<dyn Fn(&T) + Send + Sync>,
|
on_message: Arc<dyn Fn(&Rx) + Send + Sync>,
|
||||||
/// `WebSocket` message callback for text.
|
/// `WebSocket` message callback for text.
|
||||||
on_message_raw: Arc<dyn Fn(&str) + Send + Sync>,
|
on_message_raw: Arc<dyn Fn(&str) + Send + Sync>,
|
||||||
/// `WebSocket` message callback for binary.
|
/// `WebSocket` message callback for binary.
|
||||||
|
@ -645,7 +653,7 @@ where
|
||||||
protocols: Option<Vec<String>>,
|
protocols: Option<Vec<String>>,
|
||||||
}
|
}
|
||||||
|
|
||||||
impl<T: ?Sized, E, D> UseWebSocketOptions<T, E, D> {
|
impl<Rx: ?Sized, E, D> UseWebSocketOptions<Rx, E, D> {
|
||||||
/// `WebSocket` error callback.
|
/// `WebSocket` error callback.
|
||||||
pub fn on_error<F>(self, handler: F) -> Self
|
pub fn on_error<F>(self, handler: F) -> Self
|
||||||
where
|
where
|
||||||
|
@ -660,7 +668,7 @@ impl<T: ?Sized, E, D> UseWebSocketOptions<T, E, D> {
|
||||||
/// `WebSocket` message callback for typed message decoded by codec.
|
/// `WebSocket` message callback for typed message decoded by codec.
|
||||||
pub fn on_message<F>(self, handler: F) -> Self
|
pub fn on_message<F>(self, handler: F) -> Self
|
||||||
where
|
where
|
||||||
F: Fn(&T) + Send + Sync + 'static,
|
F: Fn(&Rx) + Send + Sync + 'static,
|
||||||
{
|
{
|
||||||
Self {
|
Self {
|
||||||
on_message: Arc::new(handler),
|
on_message: Arc::new(handler),
|
||||||
|
@ -669,7 +677,7 @@ impl<T: ?Sized, E, D> UseWebSocketOptions<T, E, D> {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
impl<T: ?Sized, E, D> Default for UseWebSocketOptions<T, E, D> {
|
impl<Rx: ?Sized, E, D> Default for UseWebSocketOptions<Rx, E, D> {
|
||||||
fn default() -> Self {
|
fn default() -> Self {
|
||||||
Self {
|
Self {
|
||||||
on_open: Arc::new(|_| {}),
|
on_open: Arc::new(|_| {}),
|
||||||
|
@ -688,17 +696,18 @@ impl<T: ?Sized, E, D> Default for UseWebSocketOptions<T, E, D> {
|
||||||
|
|
||||||
/// Return type of [`use_websocket`].
|
/// Return type of [`use_websocket`].
|
||||||
#[derive(Clone)]
|
#[derive(Clone)]
|
||||||
pub struct UseWebSocketReturn<T, OpenFn, CloseFn, SendFn>
|
pub struct UseWebSocketReturn<Tx, Rx, OpenFn, CloseFn, SendFn>
|
||||||
where
|
where
|
||||||
T: Send + Sync + 'static,
|
Tx: Send + Sync + 'static,
|
||||||
|
Rx: Send + Sync + 'static,
|
||||||
OpenFn: Fn() + Clone + 'static,
|
OpenFn: Fn() + Clone + 'static,
|
||||||
CloseFn: Fn() + Clone + 'static,
|
CloseFn: Fn() + Clone + 'static,
|
||||||
SendFn: Fn(&T) + Clone + 'static,
|
SendFn: Fn(&Tx) + Clone + 'static,
|
||||||
{
|
{
|
||||||
/// The current state of the `WebSocket` connection.
|
/// The current state of the `WebSocket` connection.
|
||||||
pub ready_state: Signal<ConnectionReadyState>,
|
pub ready_state: Signal<ConnectionReadyState>,
|
||||||
/// Latest message received from `WebSocket`.
|
/// Latest message received from `WebSocket`.
|
||||||
pub message: Signal<Option<T>>,
|
pub message: Signal<Option<Rx>>,
|
||||||
/// The `WebSocket` instance.
|
/// The `WebSocket` instance.
|
||||||
pub ws: Option<WebSocket>,
|
pub ws: Option<WebSocket>,
|
||||||
/// Opens the `WebSocket` connection
|
/// Opens the `WebSocket` connection
|
||||||
|
@ -707,6 +716,8 @@ where
|
||||||
pub close: CloseFn,
|
pub close: CloseFn,
|
||||||
/// Sends data through the socket
|
/// Sends data through the socket
|
||||||
pub send: SendFn,
|
pub send: SendFn,
|
||||||
|
|
||||||
|
_marker: PhantomData<Tx>,
|
||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Error, Debug)]
|
#[derive(Error, Debug)]
|
||||||
|
|
|
@ -1,4 +1,4 @@
|
||||||
use crate::{watch_with_options, utils::DebounceOptions, WatchOptions};
|
use crate::{utils::DebounceOptions, watch_with_options, WatchOptions};
|
||||||
use default_struct_builder::DefaultBuilder;
|
use default_struct_builder::DefaultBuilder;
|
||||||
use leptos::prelude::*;
|
use leptos::prelude::*;
|
||||||
|
|
||||||
|
|
|
@ -1,4 +1,4 @@
|
||||||
use crate::{watch_with_options, utils::ThrottleOptions, WatchOptions};
|
use crate::{utils::ThrottleOptions, watch_with_options, WatchOptions};
|
||||||
use default_struct_builder::DefaultBuilder;
|
use default_struct_builder::DefaultBuilder;
|
||||||
|
|
||||||
/// A throttled version of `leptos::watch`.
|
/// A throttled version of `leptos::watch`.
|
||||||
|
|
Loading…
Add table
Reference in a new issue