Merge pull request #1265 from Demonthos/dioxus-web-features

Create default enabled features for large web events
This commit is contained in:
Jonathan Kelley 2023-07-31 17:14:07 -07:00 committed by GitHub
commit 8cf59fe52e
No known key found for this signature in database
GPG key ID: 4AEE18F83AFDEB23
6 changed files with 107 additions and 107 deletions

View file

@ -29,31 +29,26 @@ serde_json = { version = "1", optional = true }
optional = true
version = "0.3.56"
features = [
"TouchEvent",
"MouseEvent",
"InputEvent",
"ClipboardEvent",
"KeyboardEvent",
"TouchEvent",
"WheelEvent",
"AnimationEvent",
"TransitionEvent",
"PointerEvent",
"FocusEvent",
"CompositionEvent",
"ClipboardEvent",
"Element",
"DomRect",
"ScrollIntoViewOptions",
"ScrollLogicalPosition",
"ScrollBehavior",
"TouchEvent",
"MouseEvent",
"InputEvent",
"ClipboardEvent",
"KeyboardEvent",
"TouchEvent",
"WheelEvent",
"AnimationEvent",
"TransitionEvent",
"PointerEvent",
"FocusEvent",
"CompositionEvent",
"ClipboardEvent",
]
[dev-dependencies]
serde_json = "1"
[features]
default = ["serialize"]
default = ["serialize", "mounted"]
serialize = [
"serde",
"serde_repr",
@ -62,6 +57,14 @@ serialize = [
"keyboard-types/serde",
"dioxus-core/serialize",
]
mounted = [
"web-sys/Element",
"web-sys/DomRect",
"web-sys/ScrollIntoViewOptions",
"web-sys/ScrollLogicalPosition",
"web-sys/ScrollBehavior",
"web-sys/HtmlElement",
]
wasm-bind = ["web-sys", "wasm-bindgen"]
native-bind = ["tokio"]
hot-reload-context = ["dioxus-rsx"]

View file

@ -4,18 +4,14 @@ use crate::events::{
};
use crate::geometry::{ClientPoint, Coordinates, ElementPoint, PagePoint, ScreenPoint};
use crate::input_data::{decode_key_location, decode_mouse_button_set, MouseButton};
use crate::{
DragData, MountedData, MountedError, MountedResult, RenderedElementBacking, ScrollBehavior,
};
use crate::{DragData, MountedData};
use keyboard_types::{Code, Key, Modifiers};
use std::convert::TryInto;
use std::future::Future;
use std::pin::Pin;
use std::str::FromStr;
use wasm_bindgen::{JsCast, JsValue};
use web_sys::{
AnimationEvent, CompositionEvent, Event, KeyboardEvent, MouseEvent, PointerEvent,
ScrollIntoViewOptions, TouchEvent, TransitionEvent, WheelEvent,
AnimationEvent, CompositionEvent, Event, KeyboardEvent, MouseEvent, PointerEvent, TouchEvent,
TransitionEvent, WheelEvent,
};
macro_rules! uncheck_convert {
@ -198,16 +194,20 @@ impl From<&TransitionEvent> for TransitionData {
}
}
#[cfg(feature = "mounted")]
impl From<&web_sys::Element> for MountedData {
fn from(e: &web_sys::Element) -> Self {
MountedData::new(e.clone())
}
}
impl RenderedElementBacking for web_sys::Element {
#[cfg(feature = "mounted")]
impl crate::RenderedElementBacking for web_sys::Element {
fn get_client_rect(
&self,
) -> Pin<Box<dyn Future<Output = MountedResult<euclid::Rect<f64, f64>>>>> {
) -> std::pin::Pin<
Box<dyn std::future::Future<Output = crate::MountedResult<euclid::Rect<f64, f64>>>>,
> {
let rect = self.get_bounding_client_rect();
let result = Ok(euclid::Rect::new(
euclid::Point2D::new(rect.left(), rect.top()),
@ -216,33 +216,36 @@ impl RenderedElementBacking for web_sys::Element {
Box::pin(async { result })
}
fn get_raw_element(&self) -> MountedResult<&dyn std::any::Any> {
fn get_raw_element(&self) -> crate::MountedResult<&dyn std::any::Any> {
Ok(self)
}
fn scroll_to(
&self,
behavior: ScrollBehavior,
) -> Pin<Box<dyn Future<Output = MountedResult<()>>>> {
behavior: crate::ScrollBehavior,
) -> std::pin::Pin<Box<dyn std::future::Future<Output = crate::MountedResult<()>>>> {
match behavior {
ScrollBehavior::Instant => self.scroll_into_view_with_scroll_into_view_options(
ScrollIntoViewOptions::new().behavior(web_sys::ScrollBehavior::Instant),
crate::ScrollBehavior::Instant => self.scroll_into_view_with_scroll_into_view_options(
web_sys::ScrollIntoViewOptions::new().behavior(web_sys::ScrollBehavior::Instant),
),
ScrollBehavior::Smooth => self.scroll_into_view_with_scroll_into_view_options(
ScrollIntoViewOptions::new().behavior(web_sys::ScrollBehavior::Smooth),
crate::ScrollBehavior::Smooth => self.scroll_into_view_with_scroll_into_view_options(
web_sys::ScrollIntoViewOptions::new().behavior(web_sys::ScrollBehavior::Smooth),
),
}
Box::pin(async { Ok(()) })
}
fn set_focus(&self, focus: bool) -> Pin<Box<dyn Future<Output = MountedResult<()>>>> {
fn set_focus(
&self,
focus: bool,
) -> std::pin::Pin<Box<dyn std::future::Future<Output = crate::MountedResult<()>>>> {
let result = self
.dyn_ref::<web_sys::HtmlElement>()
.ok_or_else(|| MountedError::OperationFailed(Box::new(FocusError(self.into()))))
.ok_or_else(|| crate::MountedError::OperationFailed(Box::new(FocusError(self.into()))))
.and_then(|e| {
(if focus { e.focus() } else { e.blur() })
.map_err(|err| MountedError::OperationFailed(Box::new(FocusError(err))))
.map_err(|err| crate::MountedError::OperationFailed(Box::new(FocusError(err))))
});
Box::pin(async { result })
}

View file

@ -11,7 +11,7 @@ keywords = ["dom", "ui", "gui", "react", "wasm"]
[dependencies]
dioxus-core = { workspace = true, features = ["serialize"] }
dioxus-html = { workspace = true, features = ["wasm-bind"] }
dioxus-html = { workspace = true, features = ["wasm-bind"], default-features = false }
dioxus-interpreter-js = { workspace = true, features = [
"sledgehammer",
"minimal_bindings",
@ -23,11 +23,7 @@ wasm-bindgen-futures = "0.4.29"
log = { workspace = true }
rustc-hash = { workspace = true }
console_error_panic_hook = { version = "0.1.7", optional = true }
once_cell = "1.9.0"
anyhow = "1.0.53"
gloo-timers = { version = "0.2.3", features = ["futures"] }
futures-util = { workspace = true, features = ["std", "async-await", "async-await-macro"] }
smallstr = "0.2.0"
futures-channel = { workspace = true }
serde_json = { version = "1.0" }
serde = { version = "1.0" }
@ -38,55 +34,38 @@ async-channel = "1.8.0"
[dependencies.web-sys]
version = "0.3.56"
features = [
"Comment",
"Attr",
"Document",
"Element",
"CssStyleDeclaration",
"HtmlElement",
"HtmlInputElement",
"HtmlSelectElement",
"HtmlTextAreaElement",
"HtmlFormElement",
"EventTarget",
"HtmlCollection",
"Node",
"NodeList",
"Text",
"Window",
"Event",
"MouseEvent",
"InputEvent",
"ClipboardEvent",
"NamedNodeMap",
"KeyboardEvent",
"TouchEvent",
"WheelEvent",
"AnimationEvent",
"TransitionEvent",
"PointerEvent",
"FocusEvent",
"CompositionEvent",
"ClipboardEvent",
"DocumentType",
"CharacterData",
"SvgElement",
"SvgAnimatedString",
"HtmlOptionElement",
"IdleDeadline",
"WebSocket",
"Location",
"MessageEvent",
"console",
"FileList",
"File",
"FileReader"
]
[features]
default = ["panic_hook"]
default = ["panic_hook", "mounted", "file_engine", "hot_reload", "eval"]
panic_hook = ["console_error_panic_hook"]
hydrate = []
hydrate = [
"web-sys/Comment",
"web-sys/console",
]
mounted = [
"web-sys/Element",
"dioxus-html/mounted"
]
file_engine = [
"web-sys/File",
"web-sys/FileList",
"web-sys/FileReader",
]
hot_reload = [
"web-sys/MessageEvent",
"web-sys/WebSocket",
"web-sys/Location",
]
eval = []
[dev-dependencies]
dioxus = { workspace = true }

View file

@ -10,16 +10,16 @@
use dioxus_core::{
BorrowedAttributeValue, ElementId, Mutation, Template, TemplateAttribute, TemplateNode,
};
use dioxus_html::{event_bubbles, CompositionData, FileEngine, FormData, MountedData};
use dioxus_html::{event_bubbles, CompositionData, FormData, MountedData};
use dioxus_interpreter_js::{get_node, minimal_bindings, save_template, Channel};
use futures_channel::mpsc;
use js_sys::Array;
use rustc_hash::FxHashMap;
use std::{any::Any, rc::Rc, sync::Arc};
use std::{any::Any, rc::Rc};
use wasm_bindgen::{closure::Closure, prelude::wasm_bindgen, JsCast, JsValue};
use web_sys::{Document, Element, Event};
use crate::{file_engine::WebFileEngine, Config};
use crate::Config;
pub struct WebsysDom {
document: Document,
@ -385,11 +385,15 @@ fn read_input_to_data(target: Element) -> Rc<FormData> {
}
}
#[cfg(not(feature = "file_engine"))]
let files = None;
#[cfg(feature = "file_engine")]
let files = target
.dyn_ref()
.and_then(|input: &web_sys::HtmlInputElement| {
input.files().and_then(|files| {
WebFileEngine::new(files).map(|f| Arc::new(f) as Arc<dyn FileEngine>)
crate::file_engine::WebFileEngine::new(files)
.map(|f| std::sync::Arc::new(f) as std::sync::Arc<dyn dioxus_html::FileEngine>)
})
});

View file

@ -3,22 +3,12 @@
use futures_channel::mpsc::UnboundedReceiver;
use dioxus_core::Template;
use wasm_bindgen::closure::Closure;
use wasm_bindgen::JsCast;
use web_sys::{MessageEvent, WebSocket};
#[cfg(not(debug_assertions))]
pub(crate) fn init() -> UnboundedReceiver<Template<'static>> {
let (tx, rx) = futures_channel::mpsc::unbounded();
std::mem::forget(tx);
rx
}
#[cfg(debug_assertions)]
pub(crate) fn init() -> UnboundedReceiver<Template<'static>> {
use std::convert::TryInto;
use wasm_bindgen::closure::Closure;
use wasm_bindgen::JsCast;
use web_sys::{MessageEvent, WebSocket};
use serde::Deserialize;

View file

@ -55,13 +55,19 @@
pub use crate::cfg::Config;
use dioxus_core::{Element, Scope, VirtualDom};
use futures_util::{pin_mut, FutureExt, StreamExt};
use futures_util::{
future::{select, Either},
pin_mut, FutureExt, StreamExt,
};
mod cache;
mod cfg;
mod dom;
#[cfg(feature = "eval")]
mod eval;
#[cfg(feature = "file_engine")]
mod file_engine;
#[cfg(all(feature = "hot_reload", debug_assertions))]
mod hot_reload;
#[cfg(feature = "hydrate")]
mod rehydrate;
@ -167,15 +173,19 @@ pub async fn run_with_props<T: 'static>(root: fn(Scope<T>) -> Element, root_prop
let mut dom = VirtualDom::new_with_props(root, root_props);
// Eval
let cx = dom.base_scope();
eval::init_eval(cx);
#[cfg(feature = "eval")]
{
// Eval
let cx = dom.base_scope();
eval::init_eval(cx);
}
#[cfg(feature = "panic_hook")]
if cfg.default_panic_hook {
console_error_panic_hook::set_once();
}
#[cfg(all(feature = "hot_reload", debug_assertions))]
let mut hotreload_rx = hot_reload::init();
for s in crate::cache::BUILTIN_INTERNED_STRINGS {
@ -237,12 +247,23 @@ pub async fn run_with_props<T: 'static>(root: fn(Scope<T>) -> Element, root_prop
let work = dom.wait_for_work().fuse();
pin_mut!(work);
futures_util::select! {
_ = work => (None, None),
new_template = hotreload_rx.next() => {
(None, new_template)
}
evt = rx.next() => (evt, None)
#[cfg(all(feature = "hot_reload", debug_assertions))]
// futures_util::select! {
// _ = work => (None, None),
// new_template = hotreload_rx.next() => {
// (None, new_template)
// }
// evt = rx.next() =>
// }
match select(work, select(hotreload_rx.next(), rx.next())).await {
Either::Left((_, _)) => (None, None),
Either::Right((Either::Left((new_template, _)), _)) => (None, new_template),
Either::Right((Either::Right((evt, _)), _)) => (evt, None),
}
#[cfg(not(all(feature = "hot_reload", debug_assertions)))]
match select(work, rx.next()).await {
Either::Left((_, _)) => (None, None),
Either::Right((evt, _)) => (evt, None),
}
};