smart attribute comparisons
This commit is contained in:
parent
ec4a413a7b
commit
6c152ed516
2 changed files with 19 additions and 3 deletions
|
|
@ -210,9 +210,8 @@ proc eq(a, b: VNode): EqResult =
|
||||||
let x = VComponent(b)
|
let x = VComponent(b)
|
||||||
assert x.changedImpl != nil
|
assert x.changedImpl != nil
|
||||||
return if x.changedImpl(x, VComponent(a)): changed else: identical
|
return if x.changedImpl(x, VComponent(a)): changed else: identical
|
||||||
if not sameAttrs(a, b): return different
|
|
||||||
if a.class != b.class: return different
|
if a.class != b.class: return different
|
||||||
if not eq(a.style, b.style): return similar
|
if not eq(a.style, b.style) or not sameAttrs(a, b): return similar
|
||||||
# Do not test event listeners here!
|
# Do not test event listeners here!
|
||||||
return result
|
return result
|
||||||
|
|
||||||
|
|
@ -223,6 +222,16 @@ proc updateStyles(newNode, oldNode: VNode) =
|
||||||
else: oldNode.dom.style = Style()
|
else: oldNode.dom.style = Style()
|
||||||
oldNode.style = newNode.style
|
oldNode.style = newNode.style
|
||||||
|
|
||||||
|
proc updateAttributes(newNode, oldNode: VNode) =
|
||||||
|
# we keep the oldNode, but take over the attributes from the new node:
|
||||||
|
if oldNode.dom != nil:
|
||||||
|
for k, _ in attrs(oldNode):
|
||||||
|
oldNode.dom.removeAttribute(k)
|
||||||
|
for k, v in attrs(newNode):
|
||||||
|
if v != nil:
|
||||||
|
oldNode.dom.setAttr(k, v)
|
||||||
|
takeOverAttr(newNode, oldNode)
|
||||||
|
|
||||||
proc mergeEvents(newNode, oldNode: VNode; kxi: KaraxInstance) =
|
proc mergeEvents(newNode, oldNode: VNode; kxi: KaraxInstance) =
|
||||||
let d = oldNode.dom
|
let d = oldNode.dom
|
||||||
for i in 0..<oldNode.events.len:
|
for i in 0..<oldNode.events.len:
|
||||||
|
|
@ -301,6 +310,8 @@ proc apply(kxi: KaraxInstance) =
|
||||||
assert p.newChild.dom != nil
|
assert p.newChild.dom != nil
|
||||||
kxi.patchLenV = 0
|
kxi.patchLenV = 0
|
||||||
|
|
||||||
|
var outputted = false
|
||||||
|
|
||||||
proc diff(newNode, oldNode: VNode; parent, current: Node; kxi: KaraxInstance): EqResult =
|
proc diff(newNode, oldNode: VNode; parent, current: Node; kxi: KaraxInstance): EqResult =
|
||||||
when defined(stats):
|
when defined(stats):
|
||||||
if kxi.recursion > 100:
|
if kxi.recursion > 100:
|
||||||
|
|
@ -314,7 +325,9 @@ proc diff(newNode, oldNode: VNode; parent, current: Node; kxi: KaraxInstance): E
|
||||||
case result
|
case result
|
||||||
of identical, similar:
|
of identical, similar:
|
||||||
newNode.dom = oldNode.dom
|
newNode.dom = oldNode.dom
|
||||||
if result == similar: updateStyles(newNode, oldNode)
|
if result == similar:
|
||||||
|
updateStyles(newNode, oldNode)
|
||||||
|
updateAttributes(newNode, oldNode)
|
||||||
if newNode.events.len != 0 or oldNode.events.len != 0:
|
if newNode.events.len != 0 or oldNode.events.len != 0:
|
||||||
mergeEvents(newNode, oldNode, kxi)
|
mergeEvents(newNode, oldNode, kxi)
|
||||||
if oldNode.kind == VNodeKind.input or oldNode.kind == VNodeKind.textarea:
|
if oldNode.kind == VNodeKind.input or oldNode.kind == VNodeKind.textarea:
|
||||||
|
|
|
||||||
|
|
@ -199,6 +199,9 @@ proc getAttr*(n: VNode; key: cstring): cstring =
|
||||||
for i in countup(0, n.attrs.len-2, 2):
|
for i in countup(0, n.attrs.len-2, 2):
|
||||||
if n.attrs[i] == key: return n.attrs[i+1]
|
if n.attrs[i] == key: return n.attrs[i+1]
|
||||||
|
|
||||||
|
proc takeOverAttr*(newNode, oldNode: VNode) =
|
||||||
|
oldNode.attrs = newNode.attrs
|
||||||
|
|
||||||
proc len*(x: VNode): int = x.kids.len
|
proc len*(x: VNode): int = x.kids.len
|
||||||
proc `[]`*(x: VNode; idx: int): VNode = x.kids[idx]
|
proc `[]`*(x: VNode; idx: int): VNode = x.kids[idx]
|
||||||
proc `[]=`*(x: VNode; idx: int; y: VNode) = x.kids[idx] = y
|
proc `[]=`*(x: VNode; idx: int; y: VNode) = x.kids[idx] = y
|
||||||
|
|
|
||||||
Loading…
Add table
Add a link
Reference in a new issue