wip: get diff compiling

Currently working through the normalization process. Occasionally, we want to iterate through all the nodes that we know have a real image in the dom. However, fragments and components don't directly have a mirror in the dom. This commit is exploring the concept of a custom iterator that explores every node in an array of nodes, returning only valid nodes which may be mounted to the dom. A big issue we're working through is heavily nested rootless nodes - something not terribly common but important nonetheless.

Inferno, React, and Preact all perform a mutative-form of normalization which alter the children list before comparing to the previous. Mostly, we're concerned about fragments in lists and heavily nested components that do not render real elements.
This commit is contained in:
Jonathan Kelley committed 2021-06-21 00:52:37 -04:00
1 parent 79127ea6cd
commit cff0547f1a
6 files changed
+644 -482

No files matched your search

+43 -2
View File
@@ -1,13 +1,15 @@
//! Helpers for building virtual DOM VNodes.
use std::{any::Any, borrow::BorrowMut, fmt::Arguments, intrinsics::transmute, u128};
use std::{
any::Any, borrow::BorrowMut, cell::RefCell, fmt::Arguments, intrinsics::transmute, u128,
};
use crate::{
events::VirtualEvent,
innerlude::{Properties, VComponent, FC},
nodes::{Attribute, Listener, NodeKey, VNode},
prelude::{VElement, VFragment},
virtual_dom::NodeCtx,
virtual_dom::Scope,
};
/// A virtual DOM element builder.
@@ -715,3 +717,42 @@ impl<'a, 'b> ChildrenList<'a, 'b> {
self.children.into_bump_slice()
}
}
// NodeCtx is used to build VNodes in the component's memory space.
// This struct adds metadata to the final VNode about listeners, attributes, and children
#[derive(Clone)]
pub struct NodeCtx<'a> {
pub scope_ref: &'a Scope,
pub listener_id: RefCell<usize>,
}
impl<'a> NodeCtx<'a> {
#[inline]
pub fn bump(&self) -> &'a bumpalo::Bump {
&self.scope_ref.cur_frame().bump
}
fn text(&self, args: Arguments) -> VNode<'a> {
text3(self.bump(), args)
}
fn element<'b, Listeners, Attributes, Children>(
&'b self,
tag_name: &'static str,
) -> ElementBuilder<
'a,
'b,
bumpalo::collections::Vec<'a, Listener<'a>>,
bumpalo::collections::Vec<'a, Attribute<'a>>,
bumpalo::collections::Vec<'a, VNode<'a>>,
> {
ElementBuilder::new(self, tag_name)
}
}
use std::fmt::Debug;
impl Debug for NodeCtx<'_> {
fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
Ok(())
}
}