11import std::io;
22import std::math;
3+ import std::collections::list;
34import raylib5::rl;
45import future;
56
@@ -36,7 +37,7 @@ fn any! Lerp.poll(&self, any env) @dynamic {
3637}
3738
3839fn Future lerp (float * place , float a , float b , float duration ) {
39- return @tclone (Lerp {
40+ return @clone (Lerp {
4041 .place = place ,
4142 .a = a ,
4243 .b = b ,
@@ -60,7 +61,7 @@ fn any! Parallel.poll(&urmom, any env) @dynamic {
6061}
6162
6263fn Future parallel (Future [] futures ) {
63- return @tclone (Parallel {
64+ return @clone (Parallel {
6465 .futures = futures ,
6566 });
6667}
@@ -82,33 +83,90 @@ fn any! Seq.poll(&urmom, any env) @dynamic {
8283}
8384
8485fn Future seq (Future [] futures ) {
85- return @tclone (Seq {
86+ return @clone (Seq {
8687 .futures = futures ,
8788 });
8889}
8990
91+ struct Patcher {
92+ List (<Future * >) lerp ;
93+ List (<Future * >) par ;
94+ List (<Future * >) seq ;
95+ }
96+
97+ fn void Patcher .add (& urmom , Future * f ) {
98+ switch (f .type ) {
99+ case Lerp .typeid :
100+ urmom .lerp .push (f );
101+ case Parallel .typeid :
102+ urmom .par .push (f );
103+ case Seq .typeid :
104+ urmom .seq .push (f );
105+ default :
106+ unreachable (" unexpected type " );
107+ }
108+ }
109+
110+ macro @list_patch (list , $Type ) {
111+ for (usz i = 0 ; i < list .len (); i ++ ) {
112+ * list [i ] = (Future ) any_make (list [i ].ptr , $Type .typeid );
113+ $Type * ft = anycast (* list [i ], $Type )!! ; // Some dirty trickery
114+ (void )ft ;
115+ }
116+ }
117+
118+ fn void Patcher .patch (& urmom ) {
119+ io::printfn (" Patching futures " );
120+ @list_patch (urmom .lerp , Lerp );
121+ @list_patch (urmom .par , Parallel );
122+ @list_patch (urmom .seq , Seq );
123+ }
124+
125+ fn void Patcher .clear (& urmom ) {
126+ urmom .lerp .clear ();
127+ urmom .par .clear ();
128+ urmom .seq .clear ();
129+ }
130+
90131struct State {
91132 float t1 , t2 ;
92133 bool finished ;
93134 Future anim ;
135+ Patcher patcher ;
94136}
95137
96138State * state = null ;
97139
98140fn void reset_anim ()
99141{
100- // TODO: clean up allocator::temp() here
101- state .anim = parallel (@tclone (Future [* ] {
102- // TODO: Tuck the whole @tclone(Future[*]{ ... }) under the future constructors
142+ // TODO: clean up allocator::heap() here
143+ // Leaky-leaky
144+ state .anim = parallel (@clone (Future [* ] {
145+ // TODO: Tuck the whole @clone(Future[*]{ ... }) under the future constructors
103146 // See if variadic args can be applied here
104- seq (@tclone (Future [* ] {
147+ seq (@clone (Future [* ] {
105148 lerp (& state .t1 , 0 , 1 , CYCLE_DURATION ),
106149 lerp (& state .t1 , 1 , 0 , CYCLE_DURATION / 4 ),
107150 })),
108- seq (@tclone (Future [* ] {
151+ seq (@clone (Future [* ] {
109152 lerp (& state .t2 , 0 , 1 , CYCLE_DURATION + CYCLE_DURATION / 4 ),
110153 }))
111154 }));
155+
156+ state .patcher .clear ();
157+
158+ // TODO: reflection to do this automatically or something
159+ // Maybe Future.traverse(fn void FutureTraverseFn(void *env, Future *f))?
160+
161+ state .patcher .add (& state .anim );
162+ Parallel * p = anycast (state .anim , Parallel )!! ;
163+ foreach (& s : p .futures ) {
164+ state .patcher .add (s );
165+ Seq * s1 = anycast (* s , Seq )!! ;
166+ foreach (& l : s1 .futures ) {
167+ state .patcher .add (l );
168+ }
169+ }
112170}
113171
114172fn void plug_init () @export (" plug_init " )
@@ -125,6 +183,8 @@ fn void* plug_pre_reload() @export("plug_pre_reload")
125183fn void plug_post_reload (void * old_state ) @export (" plug_post_reload " )
126184{
127185 state = old_state ;
186+
187+ state .patcher .patch ();
128188}
129189
130190fn void orbit_circle (Env env , float t , float radius , float orbit , Color color )
0 commit comments