Skip to content

Commit

Permalink
Merge pull request #43 from maciejhirsz/generic-anchor
Browse files Browse the repository at this point in the history
Generic Anchor
  • Loading branch information
maciejhirsz authored Mar 28, 2023
2 parents 7b712cc + 8e4072e commit bd39ad5
Show file tree
Hide file tree
Showing 13 changed files with 323 additions and 185 deletions.
26 changes: 26 additions & 0 deletions crates/kobold/js/util.js
Original file line number Diff line number Diff line change
Expand Up @@ -31,7 +31,33 @@ export function __kobold_fragment_replace(f,n)
f.appendChild(e);
f.insertBefore(b, f.firstChild);
}
export function __kobold_dyn_unmount(f)
{
let decorators = fragmentDecorators.get(f);
if (decorators == null) {
f.remove();
return;
}

let [b, e] = decorators;
while (b.nextSibling !== e) f.appendChild(b.nextSibling);
f.appendChild(e);
f.insertBefore(b, f.firstChild);
}
export function __kobold_dyn_replace(f,n)
{
let decorators = fragmentDecorators.get(f);
if (decorators == null) {
f.replaceWith(n);
return;
};

let [b, e] = decorators;
while (b.nextSibling !== e) f.appendChild(b.nextSibling);
b.replaceWith(n);
f.appendChild(e);
f.insertBefore(b, f.firstChild);
}
export function __kobold_set_text(n,t) { n.textContent = t; }
export function __kobold_set_attr(n,a,v) { n.setAttribute(a, v); }

Expand Down
36 changes: 28 additions & 8 deletions crates/kobold/src/branching.rs
Original file line number Diff line number Diff line change
Expand Up @@ -90,9 +90,11 @@
//! }
//! ```
use wasm_bindgen::JsValue;
use web_sys::Node;

use crate::{Element, Mountable, View};
use crate::dom::{self, Anchor, DynAnchor};
use crate::{Mountable, View};

macro_rules! branch {
($name:ident < $($var:ident),* >) => {
Expand Down Expand Up @@ -127,7 +129,7 @@ macro_rules! branch {
(html, old) => {
let new = html.build();

old.el().replace_with(new.js());
old.anchor().replace_with(new.js());

*old = new;
}
Expand All @@ -142,11 +144,28 @@ macro_rules! branch {
)*
{
type Js = Node;
type Anchor = DynAnchor;

fn el(&self) -> &Element {
fn anchor(&self) -> &DynAnchor {
match self {
$(
$name::$var(p) => p.el(),
$name::$var(p) => p.anchor().as_dyn(),
)*
}
}

fn replace_with(&self, new: &JsValue) {
match self {
$(
$name::$var(p) => p.replace_with(new),
)*
}
}

fn unmount(&self) {
match self {
$(
$name::$var(p) => p.unmount(),
)*
}
}
Expand All @@ -164,14 +183,15 @@ branch!(Branch7<A, B, C, D, E, F, G>);
branch!(Branch8<A, B, C, D, E, F, G, H>);
branch!(Branch9<A, B, C, D, E, F, G, H, I>);

pub struct EmptyNode(Element);
pub struct EmptyNode(Node);

pub struct Empty;

impl Mountable for EmptyNode {
type Js = Node;
type Anchor = Node;

fn el(&self) -> &Element {
fn anchor(&self) -> &Node {
&self.0
}
}
Expand All @@ -180,7 +200,7 @@ impl View for Empty {
type Product = EmptyNode;

fn build(self) -> Self::Product {
EmptyNode(Element::new_empty())
EmptyNode(dom::empty_node())
}

fn update(self, _: &mut Self::Product) {}
Expand All @@ -204,7 +224,7 @@ impl<T: View> View for Option<T> {
(html, old) => {
let new = html.build();

old.el().replace_with(new.js());
old.replace_with(new.js());

*old = new;
}
Expand Down
33 changes: 21 additions & 12 deletions crates/kobold/src/diff.rs
Original file line number Diff line number Diff line change
Expand Up @@ -9,8 +9,8 @@ use std::ops::Deref;
use web_sys::Node;

use crate::attribute::AttributeView;
use crate::dom::Element;
use crate::value::IntoText;
use crate::dom::TextContent;
use crate::value::{IntoText, Value};
use crate::{Mountable, View};

/// This is a wrapper around a `view` that will prevent updates to it, unless
Expand Down Expand Up @@ -90,9 +90,10 @@ where
P: Mountable,
{
type Js = P::Js;
type Anchor = P::Anchor;

fn el(&self) -> &Element {
self.inner.el()
fn anchor(&self) -> &Self::Anchor {
self.inner.anchor()
}
}

Expand Down Expand Up @@ -238,30 +239,38 @@ macro_rules! impl_no_diff {

impl<T> View for $name<T>
where
T: IntoText + Copy,
T: Value<TextContent> + IntoText + Copy,
{
type Product = Element;
type Product = Node;

fn build(self) -> Self::Product {
Element::new(self.into_text())
fn build(self) -> Node {
self.into_text()
}

fn update(self, _: &mut Self::Product) {}
fn update(self, node: &mut Node) {
if $update {
self.0.set_prop(TextContent, node);
}
}
}

impl<T, P> AttributeView<P> for $name<T>
where
T: AttributeView<P>,
T: Value<P>,
{
type Product = ();

fn build(self) {}

fn build_in(self, prop: P, node: &Node) {
self.0.build_in(prop, node);
self.0.set_prop(prop, node);
}

fn update_in(self, _: P, _: &Node, _: &mut ()) {}
fn update_in(self, prop: P, node: &Node, _: &mut ()) {
if $update {
self.0.set_prop(prop, node);
}
}
}

impl<T> Diff for $name<T>
Expand Down
Loading

0 comments on commit bd39ad5

Please sign in to comment.