Bladeren bron

wip: clean it up a bit

Jonathan Kelley 3 jaren geleden
bovenliggende
commit
fa106be1f5

+ 39 - 0
packages/core/README.md

@@ -4,6 +4,45 @@ This is the core crate for the Dioxus Virtual DOM. This README will focus on the
 
 To build new apps with Dioxus or to extend the ecosystem with new hooks or components, use the higher-level `dioxus` crate with the appropriate feature flags.
 
+
+```rust
+fn app(cx: Scope<()>) -> Element {
+    cx.render(rsx!(
+        div { "hello world" }
+    ))
+}
+
+
+fn main() {
+    let mut renderer = SomeRenderer::new();
+
+
+    // Creating a new virtualdom from a component
+    let mut dom = VirtualDom::new(app);
+
+    // Patching the renderer with the changes to draw the screen
+    let edits = dom.rebuild();
+    renderer.apply(edits);
+
+    // Injecting events
+    dom.handle_message(SchedulerMsg::UserEvent());
+
+}
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+```
 ## Internals
 
 Dioxus-core builds off the many frameworks that came before it. Notably, Dioxus borrows these concepts:

+ 0 - 2
packages/core/src/diff.rs

@@ -1295,8 +1295,6 @@ impl<'bump> DiffState<'bump> {
                     let scope_id = c.scope.get().unwrap();
                     let root = self.scopes.root_node(scope_id);
                     self.remove_nodes(Some(root), gen_muts);
-
-                    log::debug!("Destroying scope {:?}", scope_id);
                     self.scopes.try_remove(scope_id).unwrap();
                 }
             }

+ 8 - 15
packages/core/src/scopes.rs

@@ -123,13 +123,6 @@ impl ScopeArena {
             debug_assert!(any_item.is_none());
         } else {
             // else create a new scope
-            let (node_capacity, hook_capacity) = self
-                .heuristics
-                .borrow()
-                .get(&fc_ptr)
-                .map(|h| (h.node_arena_size, h.hook_arena_size))
-                .unwrap_or_default();
-
             self.scopes.borrow_mut().insert(
                 new_scope_id,
                 self.bump.alloc(ScopeState::new(
@@ -139,8 +132,11 @@ impl ScopeArena {
                     self.sender.clone(),
                     parent_scope,
                     vcomp,
-                    node_capacity,
-                    hook_capacity,
+                    self.heuristics
+                        .borrow()
+                        .get(&fc_ptr)
+                        .map(|h| (h.node_arena_size, h.hook_arena_size))
+                        .unwrap_or_default(),
                 )),
             );
         }
@@ -437,19 +433,16 @@ impl ScopeState {
         sender: UnboundedSender<SchedulerMsg>,
         parent_scope: Option<*mut ScopeState>,
         vcomp: Box<dyn AnyProps>,
-        node_capacity: usize,
-        hook_capacity: usize,
+        (node_capacity, hook_capacity): (usize, usize),
     ) -> Self {
-        let frames = [BumpFrame::new(node_capacity), BumpFrame::new(node_capacity)];
-
         ScopeState {
             sender,
             container,
             our_arena_idx,
             parent_scope,
-            props: RefCell::new(Some(vcomp)),
             height,
-            frames,
+            props: RefCell::new(Some(vcomp)),
+            frames: [BumpFrame::new(node_capacity), BumpFrame::new(node_capacity)],
 
             // todo: subtrees
             subtree: Cell::new(0),

+ 10 - 15
packages/core/src/virtual_dom.rs

@@ -345,11 +345,10 @@ impl VirtualDom {
 
     pub fn process_message(&mut self, msg: SchedulerMsg) {
         match msg {
-            // just keep looping, the task is now saved but we should actually poll it
             SchedulerMsg::NewTask(id) => {
                 self.scopes.pending_futures.borrow_mut().insert(id);
             }
-            SchedulerMsg::UiEvent(event) => {
+            SchedulerMsg::Event(event) => {
                 if let Some(element) = event.element {
                     self.scopes.call_listener_with_bubbling(event, element);
                 }
@@ -640,6 +639,7 @@ impl VirtualDom {
         (create.mutations, edit.mutations)
     }
 }
+
 /*
 Scopes and ScopeArenas are never dropped internally.
 An app will always occupy as much memory as its biggest form.
@@ -662,9 +662,6 @@ should we build a vcomponent for the root?
 
 - 1: Use remove_nodes to use the ensure_drop_safety pathway to safely drop the tree
 - 2: Drop the ScopeState itself
-
-
-
 */
 impl Drop for VirtualDom {
     fn drop(&mut self) {
@@ -684,27 +681,26 @@ impl Drop for VirtualDom {
 
         // make sure there are no "live" components
         for (_, scopeptr) in self.scopes.scopes.get_mut().drain() {
+            // safety: all scopes were made in the bump's allocator
+            // They are never dropped until now. The only way to drop is through Box.
             let scope = unsafe { bumpalo::boxed::Box::from_raw(scopeptr) };
             drop(scope);
         }
 
         for scopeptr in self.scopes.free_scopes.get_mut().drain(..) {
+            // safety: all scopes were made in the bump's allocator
+            // They are never dropped until now. The only way to drop is through Box.
             let mut scope = unsafe { bumpalo::boxed::Box::from_raw(scopeptr) };
             scope.reset();
             drop(scope);
         }
-
-        // Safety: all refereneces to this caller have been dropped
-        // the pointer is still valid since we haven't moved it since the virtualdom was created
-        // ensure the root component's caller is dropped
-        // drop(unsafe { Box::from_raw(self.caller) });
     }
 }
 
 #[derive(Debug)]
 pub enum SchedulerMsg {
     // events from the host
-    UiEvent(UserEvent),
+    Event(UserEvent),
 
     // setstate
     Immediate(ScopeId),
@@ -746,20 +742,19 @@ pub enum SchedulerMsg {
 /// ```
 #[derive(Debug)]
 pub struct UserEvent {
-    /// The originator of the event trigger
+    /// The originator of the event trigger if available
     pub scope_id: Option<ScopeId>,
 
+    /// The priority of the event to be scheduled around ongoing work
     pub priority: EventPriority,
 
     /// The optional real node associated with the trigger
     pub element: Option<ElementId>,
 
     /// The event type IE "onclick" or "onmouseover"
-    ///
-    /// The name that the renderer will use to mount the listener.
     pub name: &'static str,
 
-    /// Event Data
+    /// The event data to be passed onto the event handler
     pub data: Arc<dyn Any + Send + Sync>,
 }
 

+ 1 - 1
packages/desktop/src/lib.rs

@@ -210,7 +210,7 @@ impl DesktopController {
                     "user_event" => {
                         let event = events::trigger_from_serialized(req.params.unwrap());
                         log::debug!("User event: {:?}", event);
-                        sender.unbounded_send(SchedulerMsg::UiEvent(event)).unwrap();
+                        sender.unbounded_send(SchedulerMsg::Event(event)).unwrap();
                     }
                     "initialize" => {
                         is_ready.store(true, std::sync::atomic::Ordering::Relaxed);

+ 1 - 1
packages/web/src/dom.rs

@@ -300,7 +300,7 @@ impl WebsysDom {
                 // "Result" cannot be received from JS
                 // Instead, we just build and immediately execute a closure that returns result
                 match decode_trigger(event) {
-                    Ok(synthetic_event) => trigger.as_ref()(SchedulerMsg::UiEvent(synthetic_event)),
+                    Ok(synthetic_event) => trigger.as_ref()(SchedulerMsg::Event(synthetic_event)),
                     Err(e) => log::error!("Error decoding Dioxus event attribute. {:#?}", e),
                 };
             });