Mercurial > MadButterfly
changeset 1151:71c72e8d6755
Refactory cod eof TweenObject.updateTweenContent and MBScene.setCurrentScene().
- updateTweenContent() use frameline.get_frame_blocks(), instead of
frameline._keys, to get information of tweens and key frames.
- MBScene.setCurrentScene() use 'ns0:duplicate-src' attribute to map
nodes from a start scene to a stop scene.
author | Thinker K.F. Li <thinker@codemud.net> |
---|---|
date | Sun, 26 Dec 2010 23:40:09 +0800 |
parents | 6586cd10c92f |
children | d333baa702a9 |
files | pyink/MBScene.py pyink/tween.py |
diffstat | 2 files changed, 121 insertions(+), 104 deletions(-) [+] |
line wrap: on
line diff
--- a/pyink/MBScene.py Sun Dec 26 19:17:12 2010 +0800 +++ b/pyink/MBScene.py Sun Dec 26 23:40:09 2010 +0800 @@ -141,10 +141,26 @@ self.ui.updateUI() pass +def _travel_DOM(node): + nodes = [node] + while nodes: + node = nodes.pop(0) + child = node.firstChild() + while child: + nodes.append(child) + child = child.next() + pass + yield node + pass + pass + class MBScene(): - _tween_types = (frameline.TWEEN_TYPE_NONE, - frameline.TWEEN_TYPE_MOVE, - frameline.TWEEN_TYPE_SHAPE) + _frameline_tween_types = (frameline.TWEEN_TYPE_NONE, + frameline.TWEEN_TYPE_MOVE, + frameline.TWEEN_TYPE_SHAPE) + _tween_obj_tween_types = (TweenObject.TWEEN_TYPE_NORMAL, + TweenObject.TWEEN_TYPE_RELOCATE, + TweenObject.TWEEN_TYPE_SCALE) _tween_type_names = ('normal', 'relocate', 'scale') def __init__(self, desktop, win, root=None): @@ -550,6 +566,7 @@ """ self.current = nth self.tween.updateMapping() + idx = nth - 1 for layer in self._framelines: i=0 @@ -565,37 +582,38 @@ layer.layer.node.appendChild(layer.duplicateGroup) pass # Create a new group -#layer.duplicateGroup = None - while i < len(layer._keys): - s = layer._keys[i] - print s.ref.getAttribute("id"),s.idx,s.left_tween,s.right_tween - if s.right_tween is False: - if nth == s.idx+1: - s.ref.setAttribute("style","") + for start_idx, stop_idx, tween_type in layer.get_frame_blocks(): + if start_idx == stop_idx: + scene_group = layer.get_frame_data(start_idx) + if idx == start_idx: + scene_group.setAttribute('style', '') else: - s.ref.setAttribute("style","display:none") - i = i + 1 - continue - - if nth == s.idx + 1: - s.ref.setAttribute("style","") + scene_group.setAttribute('style', 'display: none') + pass + elif start_idx <= idx and stop_idx >= idx: + scene_group = layer.get_frame_data(start_idx) + scene_group.setAttribute("style","display:none") + layer.duplicateGroup.setAttribute("style","") + tween_type_idx = \ + self._frameline_tween_types.index(tween_type) + tween_obj_tween_type = \ + self._tween_obj_tween_types[tween_type_idx] + + next_idx, next_stop_idx, next_tween_type = \ + layer.get_frame_block(stop_idx + 1) + next_scene_group = layer.get_frame_data(next_idx) + + nframes = next_idx - start_idx + 1 + percent = float(idx - start_idx) / nframes + self.tween.updateTweenContent(layer.duplicateGroup, + tween_obj_tween_type, + scene_group, + next_scene_group, + percent) else: - if nth > (s.idx+1) and nth <= (layer._keys[i+1].idx+1): - if i+2 < len(layer._keys): - s.ref.setAttribute("style","display:none") - layer.duplicateGroup.setAttribute("style","") - d = layer._keys[i + 2] - self.tween.\ - updateTweenContent(layer.duplicateGroup, - layer.get_tween_type(s.idx), - s, d, nth) - else: - layer.duplicateGroup.setAttribute("style","") - s.ref.setAttribute("style","display:none") - pass - else: - s.ref.setAttribute("style","display:none") - i = i + 2 + scene_group = layer.get_frame_data(start_idx) + scene_group.setAttribute("style","display:none") + pass pass pass pass @@ -635,7 +653,7 @@ pass def setTweenType(self, tween_type): - sel_type = MBScene._tween_types.index(tween_type) + sel_type = MBScene._frameline_tween_types.index(tween_type) self._disable_tween_type_selector = True self.tweenTypeSelector.set_active(sel_type) self._disable_tween_type_selector = False @@ -729,7 +747,7 @@ if scene.start != scene.end: frameline.add_keyframe(scene.end-1,scene.node) tween_type_idx = self._tween_type_names.index(scene.type) - tween_type = self._tween_types[tween_type_idx] + tween_type = self._frameline_tween_types[tween_type_idx] frameline.tween(scene.start-1, tween_type) pass pass @@ -787,6 +805,15 @@ if orig == None: return None ns = orig.duplicate(rdoc) + + old_nodes = _travel_DOM(orig) + new_nodes = _travel_DOM(ns) + for old_node in old_nodes: + old_node_id = old_node.getAttribute('id') + new_node = new_nodes.next() + new_node.setAttribute('ns0:duplicate-src', old_node_id) + pass + gid = self.last_line.node.getAttribute("inkscape:label")+self.newID() self.ID[gid]=1 ns.setAttribute("id",gid) @@ -893,7 +920,7 @@ for start_idx, stop_idx, tween_type in frameline.get_frame_blocks(): if start_idx < stop_idx: n = self.tweenTypeSelector.get_active() - new_tween_type = MBScene._tween_types[n] + new_tween_type = MBScene._frameline_tween_types[n] self.last_line.set_tween_type(start_idx, new_tween_type) self.update() break @@ -929,7 +956,7 @@ doc = self.document for start_idx, stop_idx, tween_type in frameline.get_frame_blocks(): ref = frameline.get_frame_data(start_idx) - tween_type_idx = self._tween_types.index(tween_type) + tween_type_idx = self._frameline_tween_types.index(tween_type) tween_type_name = self._tween_type_names[tween_type_idx] scene_node = doc.createElement("ns0:scene")
--- a/pyink/tween.py Sun Dec 26 19:17:12 2010 +0800 +++ b/pyink/tween.py Sun Dec 26 23:40:09 2010 +0800 @@ -2,7 +2,12 @@ # vim: sw=4:ts=8:sts=4 import traceback import math + class TweenObject: + TWEEN_TYPE_NORMAL = 0 + TWEEN_TYPE_RELOCATE = 1 + TWEEN_TYPE_SCALE = 2 + def __init__(self,doc,dom): self.document = doc self.dom = dom @@ -24,81 +29,66 @@ self.nodeToItem[c.getAttribute("id")] = c except: pass - def updateTweenContent(self,obj, typ, source,dest,cur): + def updateTweenContent(self, duplicate_group, tween_type, + start_scene_group, stop_scene_group, percent): """ - Update the content of the duplicate scene group. We will - use the (start,end) and cur to calculate the percentage of - the tween motion effect and then use it to update the - transform matrix of the duplicated scene group. + Update the content of the duplicate scene group. We will + use precent, start_scene_group, stop_scene_group to + compute transform matrix and update duplicate scene group + specified. """ - - start = source.idx - end = dest.idx - print cur,start,end - percent = (cur-start)*1.0/(end-start) - i = 0 - s = source.ref.firstChild() - d = dest.ref.firstChild() - sources={} - dests={} # Collect ref from the obj - o = obj.firstChild() - maps={} - while o: - print "--->",o + node = duplicate_group.firstChild() + dup_nodes = {} + while node: try: - ref = o.getAttribute("ref") + ref = node.getAttribute("ref") + dup_nodes[ref] = node except: - print o ref = None + pass + node = node.next() + pass - if ref: - maps[ref] = o - o = o.next() - # Collect all objects - while d: + # Collect all nodes in stop scene + stop_nodes = {} + node = stop_scene_group.firstChild() + while node: try: - label = d.getAttribute("inkscape:label") - except: - d = d.next() - continue - dests[label] = d - d = d.next() - # Check if the object in the source exists in the destination - s = source.ref.firstChild() - d = dest.ref.firstChild() - while s: - print s,d - sid = s.getAttribute("id") - if maps.has_key(sid): - o = maps[sid] - else: - o = None - try: - label = s.getAttribute("inkscape:label") - # Use i8nkscape:label to identidy the equipvalent objects - if label: - if dests.has_key(label): - self.updateTweenObject(obj, typ, s, - dests[label], percent, o) - s = s.next() - continue + node_label = node.getAttribute("ns0:duplicate-src") + stop_nodes[node_label] = node except: pass - # Search obejcts in the destination - while d: - try: - d.getAttribute("inkscape:label") - d = d.next() - continue - except: - pass - if s.name() == d.name(): - self.updateTweenObject(obj,typ,s,d,percent,o) - d = d.next() - break - d = d.next() - s = s.next() + node = node.next() + pass + + # + # Node ID of a node of start scene must be mapped to + # 'ns0:duplicate-src' attribute of a node of stop scene. The + # nodes which can not be mapped to a node of stop scene are + # not manipulated by the tween. + # + # When a scene is duplicated, 'ns0:duplicate-src' attribute of + # nodes, in the new scene, must be setted to ID of respective + # one in the duplicated scene. + # + start_node = start_scene_group.firstChild() + while start_node: + start_node_id = start_node.getAttribute('id') + try: + stop_node = stop_nodes[start_node_id] + except KeyError: + start_node = start_node.next() + continue + + dup_node = dup_nodes.setdefault(start_node_id, None) + + self.updateTweenObject(duplicate_group, tween_type, + start_node, stop_node, + percent, dup_node) + start_node = start_node.next() + pass + pass def parseTransform(self,obj): """ @@ -171,7 +161,7 @@ Generate tweened object in the @obj by using s and d in the @p percent http://lists.w3.org/Archives/Public/www-style/2010Jun/0602.html """ - if typ == 1: + if typ == self.TWEEN_TYPE_RELOCATE: if s.name() == 'svg:g': if not newobj: newobj = s.duplicate(self.document) @@ -207,10 +197,10 @@ traceback.print_exc() pass pass - elif typ == 2: + elif typ == self.TWEEN_TYPE_SCALE: self.updateTweenObjectScale(obj,s,d,p,newobj) pass - elif typ == 0: + elif typ == self.TWEEN_TYPE_NORMAL: newobj = s.duplicate(self.document) newobj.setAttribute("ref", s.getAttribute("id")) top = self.document.createElement("svg:g")