2 initStreams { arg priorityQ;
3 list.do({ arg pattern, i;
4 priorityQ.put(0.0, pattern.asStream);
7 asStream { | cleanup| ^Routine({ arg inval; this.embedInStream(inval, cleanup) }) }
9 embedInStream { arg inval, cleanup;
11 var priorityQ = PriorityQueue.new;
12 cleanup ?? { cleanup = EventStreamCleanup.new };
14 repeats.value(inval).do({ arg j;
15 var outval, stream, nexttime, now = 0.0;
17 this.initStreams(priorityQ);
19 // if first event not at time zero
20 if (priorityQ.notEmpty and: { (nexttime = priorityQ.topPriority) > 0.0 }, {
21 inval = Event.silent(nexttime, inval).yield;
28 stream = priorityQ.pop;
29 outval = stream.next(inval);
34 cleanup.update(outval);
36 priorityQ.put(now + outval.delta, stream);
37 nexttime = priorityQ.topPriority;
38 outval.put(\delta, nexttime - now);
41 // inval ?? { this.purgeQueue(priorityQ); ^nil.yield };
52 var <>makeFunction, <>pattern, <>cleanupFunc;
54 *new { | makeFunction, pattern, cleanupFunc|
55 ^super.newCopyArgs( makeFunction, pattern, cleanupFunc)
57 storeArgs { ^[makeFunction,pattern,cleanupFunc] }
58 embedInStream { | event |
59 var stream, ev, evType;
60 var cleanup, cleanupList, eventCleanupFunc;
61 var proto; // temporary proto event used in allocation
62 var makeRoutine; // routine wrapper for function that makes protoEvent
63 var protoEvent; // protoEvent created by function
65 // Step 1: generate resources from function
67 delta: 0, // events occur simultaneously
68 finish: { ev = currentEnvironment} // get copy of event object actually played
71 makeRoutine = Routine({ protoEvent.make (makeFunction) });
74 (ev = makeRoutine.next(ev)).notNil;
76 event = ev.proto_(proto).yield;
78 cleanupList = cleanupList.add(ev)
81 cleanup = EventStreamCleanup.new;
82 eventCleanupFunc = { | flag |
83 cleanupList.do { | ev |
84 EventTypesWithCleanup.cleanup(ev, flag)
87 cleanupFunc = eventCleanupFunc ?? { { | flag | eventCleanupFunc.value(proto, flag) } };
88 cleanup.addFunction(event, cleanupFunc);
90 stream = Pfpar(pattern.asArray).asStream(cleanup);
92 ev = event.copy.putAll(protoEvent);
93 ev = stream.next(ev) ?? { ^cleanup.exit(event) };