Skip to content

Instantly share code, notes, and snippets.

@jonahwilliams
Created October 23, 2017 05:59
Show Gist options
  • Save jonahwilliams/71d22c88b84f35b247584f6308efbc00 to your computer and use it in GitHub Desktop.
Save jonahwilliams/71d22c88b84f35b247584f6308efbc00 to your computer and use it in GitHub Desktop.
incrmental-dom-example
// import {
// elementOpen,
// elementClose,
// elementVoid,
// text,
// patch,
// } from 'incremental-dom';
'use strict';
const EMPTY_ARRAY = [];
const EMPTY_OBJECT = {};
class Node {
constructor(key) {
this.key = key;
}
}
class StatelessWidget extends Node {
constructor(key) {
super(key);
}
inflate(tree) {
return WidgetRenderNode(tree);
}
}
class ElementWidget extends Node {
constructor(key, tag, children = EMPTY_ARRAY) {
super(key);
this.tag = tag;
this.children = children;
}
inflate(tree) {
return new ElementRenderNode(tree);
}
}
class Text extends Node {
constructor(value) {
super(null);
this.value = value;
}
inflate() {
return new RenderTextNode();
}
}
class StatefulWidget {
}
class State {
}
class RenderNode {
constructor(tree) {
this.tree = tree;
this.config = null;
this.element = null;
}
update(nextConfig) {
this.config = nextConfig;
}
}
class WidgetRenderNode extends RenderNode {
constructor(tree) {
super(tree);
this.child = null;
}
update(nextConfig) {
if (this.config == null) {
var childConfig = nextConfig.build();
this.child = childConfig.inflate(this.tree);
this.child.update(childConfig);
} else if (this.config != nextConfig) {
this.child.update(nextConfig.build());
}
super.update(nextConfig);
}
}
class ElementRenderNode extends RenderNode {
constructor(tree) {
super(tree);
this.element = null;
}
update(nextConfig) {
const { tag, children, key } = nextConfig;
this.element = IncrementalDOM.elementOpen(tag, key);
for (let i = 0; i < children.length; i++) {
var childConfig = children[i];
childConfig.inflate(this.tree).update(childConfig);
}
IncrementalDOM.elementClose(tag);
super.update(nextConfig);
}
}
class RenderTextNode extends RenderNode {
constructor(tree) {
super(tree);
}
update(nextConfig) {
IncrementalDOM.text(nextConfig.value);
super.update(nextConfig);
}
}
class Tree { }
class App {
constructor(root, widget) {
this.root = root;
this.widget = widget;
}
init() {
var renderNode = this.widget.inflate(new Tree());
IncrementalDOM.patch(this.root, () => renderNode.update(this.widget));
}
}
@jonahwilliams
Copy link
Author

When combined with

const root = document.getElementById('app');
const app = new App(root, new ElementWidget('1', 'div', [
  new ElementWidget('2', 'span', [
    new Text('Test'),
    new Text('Foo'),
  ]),
]));
app.init();

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment