Well after `one_clone = one.clone()`, position `three` becomes invalid,
because `one.clone()` inserts cloned node above the node `three`. If you
add:
three._childIndex += 1
after `one_clone = one.clone()`, there will be no error after executing
script.
If I were you I would make all tree changes using v-nodes, and for making
things undoable I would create my own undoHelper and redoHelper. Here is
for example one of your scripts that we have discussed before:
import time
import leo.core.leoNodes as leoNodes
def findFtlistAncestor(p):
p = p.copy()
while p and not p.h.startswith('@ftlist'):
p = p.parent()
return p
def moveToTopAndCloneToAtDay(c, p):
"""
Move the node identified by position p to the first child of
an ancestor @ftlist node and also clone it to a sibling @day
node with date matching today's date
"""
ftlist = findFtlistAncestor(p)
if not ftlist:
g.es("Not in ftlist tree")
return {}
vft = ftlist.v
before = make_snapshot(vft)
v = p.v
if vft in v.parents:
i = vft.children.index(v)
del vft.children[i]
vft.children.insert(0, v)
else:
vft.children.insert(0, v)
v.parents.append(vft)
today = "@day " + time.strftime("%Y-%m-%d", time.gmtime())
for i, ch in enumerate(vft.children):
if ch.h == today:
break
else:
i = len(vft.children)
ch = leoNodes.vnode(c)
ch.h = today
vft.children.append(ch)
ch.parents.append(vft)
if ch in v.parents:
i = ch.children.index(v)
del ch.children[i]
ch.children.insert(0, v)
else:
ch.children.insert(0, v)
v.parents.append(ch)
return ftlist, before, make_snapshot(vft)
def from_snapshot(data):
for v, children, parents in data:
v.children[:] = children
v.parents[:] = parents
def make_snapshot(v0):
def it(v):
yield v, tuple(v.children), tuple(v.parents)
# if you need to keep track of headlines and boides too
# yield v, tuple(v.children), tuple(v.parents), v.h, v.b
for ch in v.children:
yield from it(ch)
return tuple(it(v0))
def do_change():
undo_data = c.undoer.createCommonBunch(p)
undo_data.kind = 'my-special-operation'
undo_data.undoType = 'my-special-operation'
ftlist, before, after = moveToTopAndCloneToAtDay(c, p)
undo_data.before = before
undo_data.after = after
undo_data.ftlist = ftlist
undo_data.undoHelper = lambda:from_snapshot(undo_data.before) or c.
redraw(undo_data.p)
undo_data.redoHelper = lambda:from_snapshot(undo_data.after) or c.redraw
(undo_data.ftlist.firstChild())
c.undoer.pushBead(undo_data)
c.redraw(ftlist.firstChild())
do_change()
If you make a script button of this code, you can try your action and its
undo/redo functionality on some of the descendants of your @ftlist tree.
HTH Vitalije
--
You received this message because you are subscribed to the Google Groups
"leo-editor" group.
To unsubscribe from this group and stop receiving emails from it, send an email
to [email protected].
To view this discussion on the web visit
https://groups.google.com/d/msgid/leo-editor/20942315-145c-4dff-83ea-d0b6a1a39afe%40googlegroups.com.