Merge branch 'master' into pr/atty303/1349
This commit is contained in:
commit
355cd9b19e
20 files changed
+125
-85
No files matched your search
+1
-1
@@ -90,7 +90,7 @@ slab = "0.4.2"
|
|||||||
futures-channel = "0.3.21"
|
futures-channel = "0.3.21"
|
||||||
futures-util = { version = "0.3", default-features = false }
|
futures-util = { version = "0.3", default-features = false }
|
||||||
rustc-hash = "1.1.0"
|
rustc-hash = "1.1.0"
|
||||||
wasm-bindgen = "0.2.87"
|
wasm-bindgen = "0.2.88"
|
||||||
html_parser = "0.7.0"
|
html_parser = "0.7.0"
|
||||||
thiserror = "1.0.40"
|
thiserror = "1.0.40"
|
||||||
prettyplease = { package = "prettier-please", version = "0.2", features = [
|
prettyplease = { package = "prettier-please", version = "0.2", features = [
|
||||||
|
|||||||
@@ -62,6 +62,7 @@ fn app(cx: Scope) -> Element {
|
|||||||
div { id: "wrapper",
|
div { id: "wrapper",
|
||||||
div { class: "app",
|
div { class: "app",
|
||||||
div { class: "calculator",
|
div { class: "calculator",
|
||||||
|
tabindex: "0",
|
||||||
onkeydown: handle_key_down_event,
|
onkeydown: handle_key_down_event,
|
||||||
div { class: "calculator-display", val.to_string() }
|
div { class: "calculator-display", val.to_string() }
|
||||||
div { class: "calculator-keypad",
|
div { class: "calculator-keypad",
|
||||||
|
|||||||
@@ -11,7 +11,7 @@ It handles building, bundling, development and publishing to simplify developmen
|
|||||||
### Install the stable version (recommended)
|
### Install the stable version (recommended)
|
||||||
|
|
||||||
```
|
```
|
||||||
cargo install dioxus-cli --locked
|
cargo install dioxus-cli
|
||||||
```
|
```
|
||||||
|
|
||||||
### Install the latest development build through git
|
### Install the latest development build through git
|
||||||
|
|||||||
@@ -469,7 +469,7 @@ pub fn gen_page(config: &DioxusConfig, serve: bool) -> String {
|
|||||||
.unwrap_or_default()
|
.unwrap_or_default()
|
||||||
.contains_key("tailwindcss")
|
.contains_key("tailwindcss")
|
||||||
{
|
{
|
||||||
style_str.push_str("<link rel=\"stylesheet\" href=\"tailwind.css\">\n");
|
style_str.push_str("<link rel=\"stylesheet\" href=\"/{base_path}/tailwind.css\">\n");
|
||||||
}
|
}
|
||||||
|
|
||||||
replace_or_insert_before("{style_include}", &style_str, "</head", &mut html);
|
replace_or_insert_before("{style_include}", &style_str, "</head", &mut html);
|
||||||
|
|||||||
@@ -29,6 +29,9 @@ pub enum Error {
|
|||||||
#[error("Cargo Error: {0}")]
|
#[error("Cargo Error: {0}")]
|
||||||
CargoError(String),
|
CargoError(String),
|
||||||
|
|
||||||
|
#[error("Couldn't retrieve cargo metadata")]
|
||||||
|
CargoMetadata(#[source] cargo_metadata::Error),
|
||||||
|
|
||||||
#[error("{0}")]
|
#[error("{0}")]
|
||||||
CustomError(String),
|
CustomError(String),
|
||||||
|
|
||||||
|
|||||||
+28
-39
@@ -9,42 +9,31 @@ use dioxus_cli::plugin::PluginManager;
|
|||||||
|
|
||||||
use Commands::*;
|
use Commands::*;
|
||||||
|
|
||||||
fn get_bin(bin: Option<String>) -> Result<Option<PathBuf>> {
|
fn get_bin(bin: Option<String>) -> Result<PathBuf> {
|
||||||
const ERR_MESSAGE: &str = "The `--bin` flag has to be ran in a Cargo workspace.";
|
let metadata = cargo_metadata::MetadataCommand::new()
|
||||||
|
.exec()
|
||||||
|
.map_err(Error::CargoMetadata)?;
|
||||||
|
let package = if let Some(bin) = bin {
|
||||||
|
metadata
|
||||||
|
.workspace_packages()
|
||||||
|
.into_iter()
|
||||||
|
.find(|p| p.name == bin)
|
||||||
|
.ok_or(format!("no such package: {}", bin))
|
||||||
|
.map_err(Error::CargoError)?
|
||||||
|
} else {
|
||||||
|
metadata
|
||||||
|
.root_package()
|
||||||
|
.ok_or("no root package?".into())
|
||||||
|
.map_err(Error::CargoError)?
|
||||||
|
};
|
||||||
|
|
||||||
if let Some(ref bin) = bin {
|
let crate_dir = package
|
||||||
let manifest = cargo_toml::Manifest::from_path("./Cargo.toml")
|
.manifest_path
|
||||||
.map_err(|_| Error::CargoError(ERR_MESSAGE.to_string()))?;
|
.parent()
|
||||||
|
.ok_or("couldn't take parent dir".into())
|
||||||
|
.map_err(Error::CargoError)?;
|
||||||
|
|
||||||
if let Some(workspace) = manifest.workspace {
|
Ok(crate_dir.into())
|
||||||
for item in workspace.members.iter() {
|
|
||||||
let path = PathBuf::from(item);
|
|
||||||
|
|
||||||
if !path.exists() {
|
|
||||||
continue;
|
|
||||||
}
|
|
||||||
|
|
||||||
if !path.is_dir() {
|
|
||||||
continue;
|
|
||||||
}
|
|
||||||
|
|
||||||
if path.ends_with(bin.clone()) {
|
|
||||||
return Ok(Some(path));
|
|
||||||
}
|
|
||||||
}
|
|
||||||
} else {
|
|
||||||
return Err(Error::CargoError(ERR_MESSAGE.to_string()));
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
// If the bin exists but we couldn't find it
|
|
||||||
if bin.is_some() {
|
|
||||||
return Err(Error::CargoError(
|
|
||||||
"The specified bin does not exist.".to_string(),
|
|
||||||
));
|
|
||||||
}
|
|
||||||
|
|
||||||
Ok(None)
|
|
||||||
}
|
}
|
||||||
|
|
||||||
#[tokio::main]
|
#[tokio::main]
|
||||||
@@ -55,7 +44,7 @@ async fn main() -> anyhow::Result<()> {
|
|||||||
|
|
||||||
let bin = get_bin(args.bin)?;
|
let bin = get_bin(args.bin)?;
|
||||||
|
|
||||||
let _dioxus_config = DioxusConfig::load(bin.clone())
|
let _dioxus_config = DioxusConfig::load(Some(bin.clone()))
|
||||||
.map_err(|e| anyhow!("Failed to load Dioxus config because: {e}"))?
|
.map_err(|e| anyhow!("Failed to load Dioxus config because: {e}"))?
|
||||||
.unwrap_or_else(|| {
|
.unwrap_or_else(|| {
|
||||||
log::warn!("You appear to be creating a Dioxus project from scratch; we will use the default config");
|
log::warn!("You appear to be creating a Dioxus project from scratch; we will use the default config");
|
||||||
@@ -72,15 +61,15 @@ async fn main() -> anyhow::Result<()> {
|
|||||||
.map_err(|e| anyhow!("🚫 Translation of HTML into RSX failed: {}", e)),
|
.map_err(|e| anyhow!("🚫 Translation of HTML into RSX failed: {}", e)),
|
||||||
|
|
||||||
Build(opts) => opts
|
Build(opts) => opts
|
||||||
.build(bin.clone())
|
.build(Some(bin.clone()))
|
||||||
.map_err(|e| anyhow!("🚫 Building project failed: {}", e)),
|
.map_err(|e| anyhow!("🚫 Building project failed: {}", e)),
|
||||||
|
|
||||||
Clean(opts) => opts
|
Clean(opts) => opts
|
||||||
.clean(bin.clone())
|
.clean(Some(bin.clone()))
|
||||||
.map_err(|e| anyhow!("🚫 Cleaning project failed: {}", e)),
|
.map_err(|e| anyhow!("🚫 Cleaning project failed: {}", e)),
|
||||||
|
|
||||||
Serve(opts) => opts
|
Serve(opts) => opts
|
||||||
.serve(bin.clone())
|
.serve(Some(bin.clone()))
|
||||||
.await
|
.await
|
||||||
.map_err(|e| anyhow!("🚫 Serving project failed: {}", e)),
|
.map_err(|e| anyhow!("🚫 Serving project failed: {}", e)),
|
||||||
|
|
||||||
@@ -93,7 +82,7 @@ async fn main() -> anyhow::Result<()> {
|
|||||||
.map_err(|e| anyhow!("🚫 Configuring new project failed: {}", e)),
|
.map_err(|e| anyhow!("🚫 Configuring new project failed: {}", e)),
|
||||||
|
|
||||||
Bundle(opts) => opts
|
Bundle(opts) => opts
|
||||||
.bundle(bin.clone())
|
.bundle(Some(bin.clone()))
|
||||||
.map_err(|e| anyhow!("🚫 Bundling project failed: {}", e)),
|
.map_err(|e| anyhow!("🚫 Bundling project failed: {}", e)),
|
||||||
|
|
||||||
#[cfg(feature = "plugin")]
|
#[cfg(feature = "plugin")]
|
||||||
|
|||||||
@@ -31,6 +31,7 @@ fn get_out_comp_fn(orig_comp_fn: &ItemFn, cx_pat: &Pat) -> ItemFn {
|
|||||||
block: parse_quote! {
|
block: parse_quote! {
|
||||||
{
|
{
|
||||||
#[warn(non_snake_case)]
|
#[warn(non_snake_case)]
|
||||||
|
#[allow(clippy::inline_always)]
|
||||||
#[inline(always)]
|
#[inline(always)]
|
||||||
#inner_comp_fn
|
#inner_comp_fn
|
||||||
#inner_comp_ident (#cx_pat)
|
#inner_comp_ident (#cx_pat)
|
||||||
|
|||||||
@@ -632,18 +632,16 @@ mod struct_info {
|
|||||||
let generics_with_empty = modify_types_generics_hack(&b_initial_generics, |args| {
|
let generics_with_empty = modify_types_generics_hack(&b_initial_generics, |args| {
|
||||||
args.insert(0, syn::GenericArgument::Type(empties_tuple.clone().into()));
|
args.insert(0, syn::GenericArgument::Type(empties_tuple.clone().into()));
|
||||||
});
|
});
|
||||||
let phantom_generics = self.generics.params.iter().map(|param| match param {
|
let phantom_generics = self.generics.params.iter().filter_map(|param| match param {
|
||||||
syn::GenericParam::Lifetime(lifetime) => {
|
syn::GenericParam::Lifetime(lifetime) => {
|
||||||
let lifetime = &lifetime.lifetime;
|
let lifetime = &lifetime.lifetime;
|
||||||
quote!(::core::marker::PhantomData<&#lifetime ()>)
|
Some(quote!(::core::marker::PhantomData<&#lifetime ()>))
|
||||||
}
|
}
|
||||||
syn::GenericParam::Type(ty) => {
|
syn::GenericParam::Type(ty) => {
|
||||||
let ty = &ty.ident;
|
let ty = &ty.ident;
|
||||||
quote!(::core::marker::PhantomData<#ty>)
|
Some(quote!(::core::marker::PhantomData<#ty>))
|
||||||
}
|
|
||||||
syn::GenericParam::Const(_cnst) => {
|
|
||||||
quote!()
|
|
||||||
}
|
}
|
||||||
|
syn::GenericParam::Const(_cnst) => None,
|
||||||
});
|
});
|
||||||
let builder_method_doc = match self.builder_attr.builder_method_doc {
|
let builder_method_doc = match self.builder_attr.builder_method_doc {
|
||||||
Some(ref doc) => quote!(#doc),
|
Some(ref doc) => quote!(#doc),
|
||||||
@@ -738,7 +736,7 @@ Finally, call `.build()` to create the instance of `{name}`.
|
|||||||
Ok(quote! {
|
Ok(quote! {
|
||||||
impl #impl_generics #name #ty_generics #where_clause {
|
impl #impl_generics #name #ty_generics #where_clause {
|
||||||
#[doc = #builder_method_doc]
|
#[doc = #builder_method_doc]
|
||||||
#[allow(dead_code)]
|
#[allow(dead_code, clippy::type_complexity)]
|
||||||
#vis fn builder(_cx: & #extend_lifetime ::dioxus::prelude::ScopeState) -> #builder_name #generics_with_empty {
|
#vis fn builder(_cx: & #extend_lifetime ::dioxus::prelude::ScopeState) -> #builder_name #generics_with_empty {
|
||||||
#builder_name {
|
#builder_name {
|
||||||
#(#extend_fields_value,)*
|
#(#extend_fields_value,)*
|
||||||
@@ -1073,6 +1071,7 @@ Finally, call `.build()` to create the instance of `{name}`.
|
|||||||
#[allow(dead_code, non_camel_case_types, missing_docs)]
|
#[allow(dead_code, non_camel_case_types, missing_docs)]
|
||||||
impl #impl_generics #builder_name < #( #ty_generics ),* > #where_clause {
|
impl #impl_generics #builder_name < #( #ty_generics ),* > #where_clause {
|
||||||
#doc
|
#doc
|
||||||
|
#[allow(clippy::type_complexity)]
|
||||||
pub fn #field_name (self, #field_name: #arg_type) -> #builder_name < #( #target_generics ),* > {
|
pub fn #field_name (self, #field_name: #arg_type) -> #builder_name < #( #target_generics ),* > {
|
||||||
let #field_name = (#arg_expr,);
|
let #field_name = (#arg_expr,);
|
||||||
let ( #(#descructuring,)* ) = self.fields;
|
let ( #(#descructuring,)* ) = self.fields;
|
||||||
@@ -1093,6 +1092,7 @@ Finally, call `.build()` to create the instance of `{name}`.
|
|||||||
#[deprecated(
|
#[deprecated(
|
||||||
note = #repeated_fields_error_message
|
note = #repeated_fields_error_message
|
||||||
)]
|
)]
|
||||||
|
#[allow(clippy::type_complexity)]
|
||||||
pub fn #field_name (self, _: #repeated_fields_error_type_name) -> #builder_name < #( #target_generics ),* > {
|
pub fn #field_name (self, _: #repeated_fields_error_type_name) -> #builder_name < #( #target_generics ),* > {
|
||||||
self
|
self
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -164,17 +164,11 @@ impl VirtualDom {
|
|||||||
});
|
});
|
||||||
|
|
||||||
// Now that all the references are gone, we can safely drop our own references in our listeners.
|
// Now that all the references are gone, we can safely drop our own references in our listeners.
|
||||||
let mut listeners = scope.attributes_to_drop.borrow_mut();
|
let mut listeners = scope.attributes_to_drop_before_render.borrow_mut();
|
||||||
listeners.drain(..).for_each(|listener| {
|
listeners.drain(..).for_each(|listener| {
|
||||||
let listener = unsafe { &*listener };
|
let listener = unsafe { &*listener };
|
||||||
match &listener.value {
|
if let AttributeValue::Listener(l) = &listener.value {
|
||||||
AttributeValue::Listener(l) => {
|
_ = l.take();
|
||||||
_ = l.take();
|
|
||||||
}
|
|
||||||
AttributeValue::Any(a) => {
|
|
||||||
_ = a.take();
|
|
||||||
}
|
|
||||||
_ => (),
|
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -1,10 +1,13 @@
|
|||||||
use crate::nodes::RenderReturn;
|
use crate::nodes::RenderReturn;
|
||||||
|
use crate::{Attribute, AttributeValue};
|
||||||
use bumpalo::Bump;
|
use bumpalo::Bump;
|
||||||
|
use std::cell::RefCell;
|
||||||
use std::cell::{Cell, UnsafeCell};
|
use std::cell::{Cell, UnsafeCell};
|
||||||
|
|
||||||
pub(crate) struct BumpFrame {
|
pub(crate) struct BumpFrame {
|
||||||
pub bump: UnsafeCell<Bump>,
|
pub bump: UnsafeCell<Bump>,
|
||||||
pub node: Cell<*const RenderReturn<'static>>,
|
pub node: Cell<*const RenderReturn<'static>>,
|
||||||
|
pub(crate) attributes_to_drop_before_reset: RefCell<Vec<*const Attribute<'static>>>,
|
||||||
}
|
}
|
||||||
|
|
||||||
impl BumpFrame {
|
impl BumpFrame {
|
||||||
@@ -13,6 +16,7 @@ impl BumpFrame {
|
|||||||
Self {
|
Self {
|
||||||
bump: UnsafeCell::new(bump),
|
bump: UnsafeCell::new(bump),
|
||||||
node: Cell::new(std::ptr::null()),
|
node: Cell::new(std::ptr::null()),
|
||||||
|
attributes_to_drop_before_reset: Default::default(),
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -31,8 +35,23 @@ impl BumpFrame {
|
|||||||
unsafe { &*self.bump.get() }
|
unsafe { &*self.bump.get() }
|
||||||
}
|
}
|
||||||
|
|
||||||
#[allow(clippy::mut_from_ref)]
|
pub(crate) fn add_attribute_to_drop(&self, attribute: *const Attribute<'static>) {
|
||||||
pub(crate) unsafe fn bump_mut(&self) -> &mut Bump {
|
self.attributes_to_drop_before_reset
|
||||||
unsafe { &mut *self.bump.get() }
|
.borrow_mut()
|
||||||
|
.push(attribute);
|
||||||
|
}
|
||||||
|
|
||||||
|
pub(crate) unsafe fn reset(&self) {
|
||||||
|
let mut attributes = self.attributes_to_drop_before_reset.borrow_mut();
|
||||||
|
attributes.drain(..).for_each(|attribute| {
|
||||||
|
let attribute = unsafe { &*attribute };
|
||||||
|
if let AttributeValue::Any(l) = &attribute.value {
|
||||||
|
_ = l.take();
|
||||||
|
}
|
||||||
|
});
|
||||||
|
unsafe {
|
||||||
|
let bump = &mut *self.bump.get();
|
||||||
|
bump.reset();
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -23,8 +23,37 @@ use crate::{innerlude::VNode, ScopeState};
|
|||||||
///
|
///
|
||||||
///
|
///
|
||||||
/// ```rust, ignore
|
/// ```rust, ignore
|
||||||
/// LazyNodes::new(|f| f.element("div", [], [], [] None))
|
/// LazyNodes::new(|f| {
|
||||||
|
/// static TEMPLATE: dioxus::core::Template = dioxus::core::Template {
|
||||||
|
/// name: "main.rs:5:5:20", // Source location of the template for hot reloading
|
||||||
|
/// roots: &[
|
||||||
|
/// dioxus::core::TemplateNode::Element {
|
||||||
|
/// tag: dioxus_elements::div::TAG_NAME,
|
||||||
|
/// namespace: dioxus_elements::div::NAME_SPACE,
|
||||||
|
/// attrs: &[],
|
||||||
|
/// children: &[],
|
||||||
|
/// },
|
||||||
|
/// ],
|
||||||
|
/// node_paths: &[],
|
||||||
|
/// attr_paths: &[],
|
||||||
|
/// };
|
||||||
|
/// dioxus::core::VNode {
|
||||||
|
/// parent: None,
|
||||||
|
/// key: None,
|
||||||
|
/// template: std::cell::Cell::new(TEMPLATE),
|
||||||
|
/// root_ids: dioxus::core::exports::bumpalo::collections::Vec::with_capacity_in(
|
||||||
|
/// 1usize,
|
||||||
|
/// f.bump(),
|
||||||
|
/// )
|
||||||
|
/// .into(),
|
||||||
|
/// dynamic_nodes: f.bump().alloc([]),
|
||||||
|
/// dynamic_attrs: f.bump().alloc([]),
|
||||||
|
/// })
|
||||||
|
/// }
|
||||||
/// ```
|
/// ```
|
||||||
|
///
|
||||||
|
/// Find more information about how to construct [`VNode`] at <https://dioxuslabs.com/learn/0.4/contributing/walkthrough_readme#the-rsx-macro>
|
||||||
|
|
||||||
pub struct LazyNodes<'a, 'b> {
|
pub struct LazyNodes<'a, 'b> {
|
||||||
#[cfg(not(miri))]
|
#[cfg(not(miri))]
|
||||||
inner: SmallBox<dyn FnMut(&'a ScopeState) -> VNode<'a> + 'b, S16>,
|
inner: SmallBox<dyn FnMut(&'a ScopeState) -> VNode<'a> + 'b, S16>,
|
||||||
@@ -61,7 +90,7 @@ impl<'a, 'b> LazyNodes<'a, 'b> {
|
|||||||
/// Call the closure with the given factory to produce real [`VNode`].
|
/// Call the closure with the given factory to produce real [`VNode`].
|
||||||
///
|
///
|
||||||
/// ```rust, ignore
|
/// ```rust, ignore
|
||||||
/// let f = LazyNodes::new(move |f| f.element("div", [], [], [] None));
|
/// let f = LazyNodes::new(/* Closure for creating VNodes */);
|
||||||
///
|
///
|
||||||
/// let node = f.call(cac);
|
/// let node = f.call(cac);
|
||||||
/// ```
|
/// ```
|
||||||
|
|||||||
@@ -35,7 +35,7 @@ impl VirtualDom {
|
|||||||
hook_idx: Default::default(),
|
hook_idx: Default::default(),
|
||||||
|
|
||||||
borrowed_props: Default::default(),
|
borrowed_props: Default::default(),
|
||||||
attributes_to_drop: Default::default(),
|
attributes_to_drop_before_render: Default::default(),
|
||||||
}));
|
}));
|
||||||
|
|
||||||
let context =
|
let context =
|
||||||
@@ -54,7 +54,7 @@ impl VirtualDom {
|
|||||||
|
|
||||||
let new_nodes = unsafe {
|
let new_nodes = unsafe {
|
||||||
let scope = &self.scopes[scope_id.0];
|
let scope = &self.scopes[scope_id.0];
|
||||||
scope.previous_frame().bump_mut().reset();
|
scope.previous_frame().reset();
|
||||||
|
|
||||||
scope.context().suspended.set(false);
|
scope.context().suspended.set(false);
|
||||||
|
|
||||||
|
|||||||
@@ -95,7 +95,7 @@ pub struct ScopeState {
|
|||||||
pub(crate) hook_idx: Cell<usize>,
|
pub(crate) hook_idx: Cell<usize>,
|
||||||
|
|
||||||
pub(crate) borrowed_props: RefCell<Vec<*const VComponent<'static>>>,
|
pub(crate) borrowed_props: RefCell<Vec<*const VComponent<'static>>>,
|
||||||
pub(crate) attributes_to_drop: RefCell<Vec<*const Attribute<'static>>>,
|
pub(crate) attributes_to_drop_before_render: RefCell<Vec<*const Attribute<'static>>>,
|
||||||
|
|
||||||
pub(crate) props: Option<Box<dyn AnyProps<'static>>>,
|
pub(crate) props: Option<Box<dyn AnyProps<'static>>>,
|
||||||
}
|
}
|
||||||
@@ -349,12 +349,22 @@ impl<'src> ScopeState {
|
|||||||
pub fn render(&'src self, rsx: LazyNodes<'src, '_>) -> Element<'src> {
|
pub fn render(&'src self, rsx: LazyNodes<'src, '_>) -> Element<'src> {
|
||||||
let element = rsx.call(self);
|
let element = rsx.call(self);
|
||||||
|
|
||||||
let mut listeners = self.attributes_to_drop.borrow_mut();
|
let mut listeners = self.attributes_to_drop_before_render.borrow_mut();
|
||||||
for attr in element.dynamic_attrs {
|
for attr in element.dynamic_attrs {
|
||||||
attr.ty.for_each(|attr| {
|
match attr.value {
|
||||||
let unbounded = unsafe { std::mem::transmute(attr as *const Attribute) };
|
// We need to drop listeners before the next render because they may borrow data from the borrowed props which will be dropped
|
||||||
listeners.push(unbounded);
|
AttributeValue::Listener(_) => {
|
||||||
})
|
let unbounded = unsafe { std::mem::transmute(attr as *const Attribute) };
|
||||||
|
listeners.push(unbounded);
|
||||||
|
}
|
||||||
|
// We need to drop any values manually to make sure that their drop implementation is called before the next render
|
||||||
|
AttributeValue::Any(_) => {
|
||||||
|
let unbounded = unsafe { std::mem::transmute(attr as *const Attribute) };
|
||||||
|
self.previous_frame().add_attribute_to_drop(unbounded);
|
||||||
|
}
|
||||||
|
|
||||||
|
_ => (),
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
let mut props = self.borrowed_props.borrow_mut();
|
let mut props = self.borrowed_props.borrow_mut();
|
||||||
|
|||||||
@@ -7,6 +7,6 @@ use dioxus_core::ScopeState;
|
|||||||
pub fn use_atom_root(cx: &ScopeState) -> &Rc<AtomRoot> {
|
pub fn use_atom_root(cx: &ScopeState) -> &Rc<AtomRoot> {
|
||||||
cx.use_hook(|| match cx.consume_context::<Rc<AtomRoot>>() {
|
cx.use_hook(|| match cx.consume_context::<Rc<AtomRoot>>() {
|
||||||
Some(root) => root,
|
Some(root) => root,
|
||||||
None => panic!("No atom root found in context. Did you forget place an AtomRoot component at the top of your app?"),
|
None => panic!("No atom root found in context. Did you forget to call use_init_atom_root at the top of your app?"),
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
@@ -86,7 +86,9 @@ impl<T: 'static> AtomState<T> {
|
|||||||
/// ```
|
/// ```
|
||||||
#[must_use]
|
#[must_use]
|
||||||
pub fn current(&self) -> Rc<T> {
|
pub fn current(&self) -> Rc<T> {
|
||||||
self.value.as_ref().unwrap().clone()
|
let atoms = self.root.atoms.borrow();
|
||||||
|
let slot = atoms.get(&self.id).unwrap();
|
||||||
|
slot.value.clone().downcast().unwrap()
|
||||||
}
|
}
|
||||||
|
|
||||||
/// Get the `setter` function directly without the `AtomState` wrapper.
|
/// Get the `setter` function directly without the `AtomState` wrapper.
|
||||||
|
|||||||
@@ -11,7 +11,7 @@ keywords = ["ui", "gui", "react", "ssr", "fullstack"]
|
|||||||
|
|
||||||
[dependencies]
|
[dependencies]
|
||||||
# server functions
|
# server functions
|
||||||
server_fn = { version = "0.4.6", default-features = false }
|
server_fn = { version = "0.5.2", default-features = false }
|
||||||
dioxus_server_macro = { workspace = true }
|
dioxus_server_macro = { workspace = true }
|
||||||
|
|
||||||
# warp
|
# warp
|
||||||
|
|||||||
@@ -53,7 +53,7 @@ fn default_external_navigation_handler() -> fn(Scope) -> Element {
|
|||||||
dioxus_router::prelude::FailureExternalNavigation
|
dioxus_router::prelude::FailureExternalNavigation
|
||||||
}
|
}
|
||||||
|
|
||||||
/// The configeration for the router
|
/// The configuration for the router
|
||||||
#[derive(Props, serde::Serialize, serde::Deserialize)]
|
#[derive(Props, serde::Serialize, serde::Deserialize)]
|
||||||
pub struct FullstackRouterConfig<R>
|
pub struct FullstackRouterConfig<R>
|
||||||
where
|
where
|
||||||
|
|||||||
@@ -125,14 +125,6 @@ impl server_fn::ServerFunctionRegistry<()> for DioxusServerFnRegistry {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
fn register(
|
|
||||||
url: &'static str,
|
|
||||||
server_function: ServerFunction,
|
|
||||||
encoding: server_fn::Encoding,
|
|
||||||
) -> Result<(), Self::Error> {
|
|
||||||
Self::register_explicit("", url, server_function, encoding)
|
|
||||||
}
|
|
||||||
|
|
||||||
/// Returns the server function registered at the given URL, or `None` if no function is registered at that URL.
|
/// Returns the server function registered at the given URL, or `None` if no function is registered at that URL.
|
||||||
fn get(url: &str) -> Option<server_fn::ServerFnTraitObj<()>> {
|
fn get(url: &str) -> Option<server_fn::ServerFnTraitObj<()>> {
|
||||||
REGISTERED_SERVER_FUNCTIONS
|
REGISTERED_SERVER_FUNCTIONS
|
||||||
|
|||||||
@@ -17,7 +17,7 @@ proc-macro2 = "^1.0.63"
|
|||||||
quote = "^1.0.26"
|
quote = "^1.0.26"
|
||||||
syn = { version = "2", features = ["full"] }
|
syn = { version = "2", features = ["full"] }
|
||||||
convert_case = "^0.6.0"
|
convert_case = "^0.6.0"
|
||||||
server_fn_macro = "^0.4.6"
|
server_fn_macro = "^0.5.2"
|
||||||
|
|
||||||
[lib]
|
[lib]
|
||||||
proc-macro = true
|
proc-macro = true
|
||||||
|
|||||||
@@ -294,7 +294,7 @@ pub fn virtual_event_from_websys_event(event: web_sys::Event, target: Element) -
|
|||||||
"select" => Rc::new(SelectionData {}),
|
"select" => Rc::new(SelectionData {}),
|
||||||
"touchcancel" | "touchend" | "touchmove" | "touchstart" => Rc::new(TouchData::from(event)),
|
"touchcancel" | "touchend" | "touchmove" | "touchstart" => Rc::new(TouchData::from(event)),
|
||||||
|
|
||||||
"scroll" => Rc::new(()),
|
"scroll" => Rc::new(ScrollData {}),
|
||||||
"wheel" => Rc::new(WheelData::from(event)),
|
"wheel" => Rc::new(WheelData::from(event)),
|
||||||
"animationstart" | "animationend" | "animationiteration" => {
|
"animationstart" | "animationend" | "animationiteration" => {
|
||||||
Rc::new(AnimationData::from(event))
|
Rc::new(AnimationData::from(event))
|
||||||
|
|||||||
Reference in new issue
Block a user