Mercurial > code > home > repos > light9
comparison flax/Timeline.py @ 123:41c0ec6cd10a
bugfixes, tableau demo
author | dmcc |
---|---|
date | Fri, 13 Jun 2003 15:46:53 +0000 |
parents | 2ed9bfd1dd0e |
children | 8de8a2f467db |
comparison
equal
deleted
inserted
replaced
122:2ed9bfd1dd0e | 123:41c0ec6cd10a |
---|---|
39 def __repr__(self): | 39 def __repr__(self): |
40 return "<TimedEvent %s at %.2f, time=%.2f, next blender=%s>" % \ | 40 return "<TimedEvent %s at %.2f, time=%.2f, next blender=%s>" % \ |
41 (self.frame, self.level, self.time, self.next_blender) | 41 (self.frame, self.level, self.time, self.next_blender) |
42 def get_level(self): | 42 def get_level(self): |
43 return self.level | 43 return self.level |
44 def __hash__(self): | |
45 return id(self.time) ^ id(self.frame) ^ id(self.next_blender) | |
44 | 46 |
45 class Blender: | 47 class Blender: |
46 """Blenders are functions that merge the effects of two LevelFrames.""" | 48 """Blenders are functions that merge the effects of two LevelFrames.""" |
47 def __init__(self): | 49 def __init__(self): |
48 pass | 50 pass |
70 blends. blendtime is the percent/100 that the blend should | 72 blends. blendtime is the percent/100 that the blend should |
71 completed. In other words, 0.25 means it should be 0.75 * startframe + | 73 completed. In other words, 0.25 means it should be 0.75 * startframe + |
72 0.25 * endframe. This function is included since many blenders are | 74 0.25 * endframe. This function is included since many blenders are |
73 just functions on the percentage and still combine start and end frames | 75 just functions on the percentage and still combine start and end frames |
74 in this way.""" | 76 in this way.""" |
75 return {startframe : (1.0 - blendtime), endframe : blendtime} | 77 # print "linear_blend", startframe, endframe, blendtime |
78 if startframe.frame == endframe.frame: | |
79 # print "same frames" | |
80 startlevel = startframe.level * (1.0 - blendtime) | |
81 endlevel = endframe.level * blendtime | |
82 levels = {startframe.frame : max(startlevel, endlevel)} | |
83 else: | |
84 # print "diff frames" | |
85 levels = {startframe.frame : (1.0 - blendtime) * startframe.level, | |
86 endframe.frame : blendtime * endframe.level} | |
87 # print "return", levels | |
88 return levels | |
76 | 89 |
77 class InstantEnd(Blender): | 90 class InstantEnd(Blender): |
78 """Instant change from startframe to endframe at the end. In other words, | 91 """Instant change from startframe to endframe at the end. In other words, |
79 the value returned will be the startframe all the way until the very end | 92 the value returned will be the startframe all the way until the very end |
80 of the blend.""" | 93 of the blend.""" |
81 def __call__(self, startframe, endframe, blendtime): | 94 def __call__(self, startframe, endframe, blendtime): |
82 # "What!?" you say, "Why don't you care about blendtime?" | 95 # "What!?" you say, "Why don't you care about blendtime?" |
83 # This is because Blenders never be asked for blenders at the endpoints | 96 # This is because Blenders never be asked for blenders at the endpoints |
84 # (after all, they wouldn't be blenders if they were). Please see | 97 # (after all, they wouldn't be blenders if they were). Please see |
85 # 'Very important note' in Blender.__doc__ | 98 # 'Very important note' in Blender.__doc__ |
86 return {startframe : 1.0} | 99 return {startframe.frame : startframe.level} |
87 | 100 |
88 class InstantStart(Blender): | 101 class InstantStart(Blender): |
89 """Instant change from startframe to endframe at the beginning. In other | 102 """Instant change from startframe to endframe at the beginning. In other |
90 words, the value returned will be the startframe at the very beginning | 103 words, the value returned will be the startframe at the very beginning |
91 and then be endframe at all times afterwards.""" | 104 and then be endframe at all times afterwards.""" |
92 def __call__(self, startframe, endframe, blendtime): | 105 def __call__(self, startframe, endframe, blendtime): |
93 # "What!?" you say, "Why don't you care about blendtime?" | 106 # "What!?" you say, "Why don't you care about blendtime?" |
94 # This is because Blenders never be asked for blenders at the endpoints | 107 # This is because Blenders never be asked for blenders at the endpoints |
95 # (after all, they wouldn't be blenders if they were). Please see | 108 # (after all, they wouldn't be blenders if they were). Please see |
96 # 'Very important note' in Blender.__doc__ | 109 # 'Very important note' in Blender.__doc__ |
97 return {endframe : 1.0} | 110 return {endframe.frame : endframe.level} |
98 | 111 |
99 class LinearBlender(Blender): | 112 class LinearBlender(Blender): |
100 """Linear fade from one frame to another""" | 113 """Linear fade from one frame to another""" |
101 def __call__(self, startframe, endframe, blendtime): | 114 def __call__(self, startframe, endframe, blendtime): |
102 return self.linear_blend(startframe, endframe, blendtime) | 115 return self.linear_blend(startframe, endframe, blendtime) |
183 self.get(time, direction=FORWARD) | 196 self.get(time, direction=FORWARD) |
184 def get_levels_at_time(self, time): | 197 def get_levels_at_time(self, time): |
185 """Returns a LevelFrame with the levels of this track at that time.""" | 198 """Returns a LevelFrame with the levels of this track at that time.""" |
186 before, after = self.get_surrounding_frames(time) | 199 before, after = self.get_surrounding_frames(time) |
187 | 200 |
188 if before == after: | 201 if not after or before == after: |
189 return {before.frame : 1.0} | 202 return {before.frame : before.level} |
190 else: # we have a blended value | 203 else: # we have a blended value |
191 diff = after.time - before.time | 204 diff = after.time - before.time |
192 elapsed = time - before.time | 205 elapsed = time - before.time |
193 percent = elapsed / diff | 206 percent = elapsed / diff |
194 if not before.next_blender: | 207 if not before.next_blender: |
195 raise MissingBlender, before | 208 raise MissingBlender, before |
196 return before.next_blender(before.frame, after.frame, percent) | 209 return before.next_blender(before, after, percent) |
197 | 210 |
198 class Timeline: | 211 class Timeline: |
199 def __init__(self, tracks, rate=1, direction=FORWARD): | 212 def __init__(self, tracks, rate=1, direction=FORWARD): |
200 """ | 213 """ |
201 Most/all of this is old: | 214 Most/all of this is old: |
281 linear = LinearBlender() | 294 linear = LinearBlender() |
282 quad = ExponentialBlender(2) | 295 quad = ExponentialBlender(2) |
283 invquad = ExponentialBlender(0.5) | 296 invquad = ExponentialBlender(0.5) |
284 smoove = SmoothBlender() | 297 smoove = SmoothBlender() |
285 | 298 |
286 track1 = TimelineTrack('lights', | 299 track1 = TimelineTrack('red track', |
287 T(0, 'red', blender=linear), | 300 T(0, 'red', blender=linear, level=0), |
288 T(5, 'blue', blender=quad), | 301 T(4, 'red', blender=quad, level=0.5), |
289 T(10, 'red', blender=smoove), | 302 T(12, 'red', blender=smoove, level=0.7), |
290 T(15, 'blue')) # last TimedEvent doesn't need a blender | 303 T(15, 'red', level=0.0)) # last TimedEvent doesn't need a blender |
291 | 304 track2 = TimelineTrack('green track', |
292 tl = Timeline([track1]) | 305 T(0, 'green', blender=invquad, level=0.2), |
306 T(5, 'green', blender=smoove, level=1), | |
307 T(10, 'green', blender=linear, level=0.8), | |
308 T(15, 'green', blender=linear, level=0.6), | |
309 T(20, 'green', level=0.0)) # last TimedEvent doesn't need a blender | |
310 track3 = TimelineTrack('tableau demo', | |
311 T(0, 'blue', level=0.0, blender=linear), | |
312 T(2, 'blue', level=1.0, blender=InstantEnd()), | |
313 T(18, 'blue', level=1.0, blender=linear), | |
314 T(20, 'blue', level=0.0, blender=linear)) | |
315 | |
316 tl = Timeline([track1, track2, track3]) | |
293 | 317 |
294 tl.play() | 318 tl.play() |
295 | 319 |
296 import Tix | 320 import Tix |
297 root = Tix.Tk() | 321 root = Tix.Tk() |