1pub use chargrid_input;
2pub use chargrid_input::Input;
3pub use chargrid_render;
4pub use chargrid_render::{ColModify, Frame, View, ViewContext};
5use std::marker::PhantomData;
6use std::time::Duration;
7
8mod app;
9pub mod common_event;
10pub use app::*;
11
12pub enum Handled<R, C> {
13 Return(R),
14 Continue(C),
15}
16
17impl<R, C> Handled<R, C> {
18 pub fn map_continue<D, F>(self, f: F) -> Handled<R, D>
19 where
20 F: FnOnce(C) -> D,
21 {
22 match self {
23 Handled::Return(r) => Handled::Return(r),
24 Handled::Continue(c) => Handled::Continue(f(c)),
25 }
26 }
27 pub fn map_return<S, F>(self, f: F) -> Handled<S, C>
28 where
29 F: FnOnce(R) -> S,
30 {
31 match self {
32 Handled::Return(r) => Handled::Return(f(r)),
33 Handled::Continue(c) => Handled::Continue(c),
34 }
35 }
36}
37
38pub trait EventOrPeek: Sized + private::Sealed {
39 type Event;
40 fn with<A, X, F, G>(self, arg: A, f: F, g: G) -> X
41 where
42 F: FnOnce(A, Self::Event) -> X,
43 G: FnOnce(A) -> X;
44}
45
46pub fn event_or_peek_with_handled<EP, A, X, F>(event_or_peek: EP, arg: A, f: F) -> Handled<X, A>
47where
48 EP: EventOrPeek,
49 F: FnOnce(A, EP::Event) -> Handled<X, A>,
50{
51 event_or_peek.with(arg, f, Handled::Continue)
52}
53
54pub struct Event<E>(E);
55pub struct Peek<E>(PhantomData<E>);
56
57impl<E> Event<E> {
58 pub fn new(e: E) -> Self {
59 Self(e)
60 }
61}
62
63impl<E> Peek<E> {
64 pub fn new() -> Self {
65 Self(PhantomData)
66 }
67}
68
69impl<E> Default for Peek<E> {
70 fn default() -> Self {
71 Self::new()
72 }
73}
74
75impl<E> EventOrPeek for Event<E> {
76 type Event = E;
77 fn with<A, X, F, G>(self, arg: A, f: F, _g: G) -> X
78 where
79 F: FnOnce(A, Self::Event) -> X,
80 G: FnOnce(A) -> X,
81 {
82 f(arg, self.0)
83 }
84}
85
86impl<E> EventOrPeek for Peek<E> {
87 type Event = E;
88 fn with<A, X, F, G>(self, arg: A, _f: F, g: G) -> X
89 where
90 F: FnOnce(A, Self::Event) -> X,
91 G: FnOnce(A) -> X,
92 {
93 g(arg)
94 }
95}
96
97mod private {
98 pub trait Sealed {}
99 impl<E> Sealed for super::Event<E> {}
100 impl<E> Sealed for super::Peek<E> {}
101}
102
103pub trait EventRoutine: Sized {
104 type Return;
105 type Data;
106 type View;
107 type Event;
108
109 fn handle<EP>(
110 self,
111 data: &mut Self::Data,
112 view: &Self::View,
113 event_or_peek: EP,
114 ) -> Handled<Self::Return, Self>
115 where
116 EP: EventOrPeek<Event = Self::Event>;
117
118 fn view<F, C>(
119 &self,
120 data: &Self::Data,
121 view: &mut Self::View,
122 context: ViewContext<C>,
123 frame: &mut F,
124 ) where
125 F: Frame,
126 C: ColModify;
127
128 fn repeat<U, F>(self, f: F) -> Repeat<Self, F>
129 where
130 F: FnMut(Self::Return) -> Handled<U, Self>,
131 {
132 Repeat { t: self, f }
133 }
134
135 fn select<S>(self, selector: S) -> Select<Self, S>
136 where
137 S: Selector<DataOutput = Self::Data, ViewOutput = Self::View>,
138 {
139 Select { t: self, selector }
140 }
141
142 fn then<U, F>(self, f: F) -> Then<Self, U, F>
143 where
144 U: EventRoutine<Data = Self::Data, View = Self::View>,
145 F: FnOnce() -> U,
146 {
147 Then(AndThenPrivate::First { t: self, f })
148 }
149
150 fn and_then<U, F>(self, f: F) -> AndThen<Self, U, F>
151 where
152 U: EventRoutine<Data = Self::Data, View = Self::View>,
153 F: FnOnce(Self::Return) -> U,
154 {
155 AndThen(AndThenPrivate::First { t: self, f })
156 }
157
158 fn map<F, U>(self, f: F) -> Map<Self, F>
159 where
160 F: FnOnce(Self::Return) -> U,
161 {
162 Map { t: self, f }
163 }
164
165 fn convert_input_to_common_event(self) -> common_event::ConvertInputToCommonEvent<Self> {
166 common_event::ConvertInputToCommonEvent(self)
167 }
168
169 fn app_one_shot_ignore_return(
170 self,
171 data: Self::Data,
172 view: Self::View,
173 ) -> EventRoutineAppOneShotIgnoreReturn<Self> {
174 EventRoutineAppOneShotIgnoreReturn::new(self, data, view)
175 }
176
177 fn return_on_exit<F>(self, f: F) -> common_event::ReturnOnExit<Self, F>
178 where
179 F: FnOnce(&mut Self::Data) -> Self::Return,
180 {
181 common_event::ReturnOnExit { t: self, f }
182 }
183
184 fn decorated<D>(self, d: D) -> Decorated<Self, D>
185 where
186 D: Decorate<View = Self::View, Data = Self::Data>,
187 {
188 Decorated { t: self, d }
189 }
190
191 fn on_event<F>(self, f: F) -> OnEvent<Self, F>
192 where
193 F: FnMut(&mut &mut Self::Data, &Self::Event),
194 {
195 OnEvent { t: self, f }
196 }
197}
198
199struct OneShot<T, D, V, E> {
200 field: T,
201 data: PhantomData<D>,
202 view: PhantomData<V>,
203 event: PhantomData<E>,
204}
205
206impl<T, D, V, E> OneShot<T, D, V, E> {
207 pub fn new(field: T) -> Self {
208 Self {
209 field,
210 data: PhantomData,
211 view: PhantomData,
212 event: PhantomData,
213 }
214 }
215}
216
217pub struct Value<T, D, V, E>(OneShot<T, D, V, E>);
218
219impl<T, D, V, E> Value<T, D, V, E> {
220 pub fn new(value: T) -> Self {
221 Self(OneShot::new(value))
222 }
223}
224
225impl<T, D, V, E> EventRoutine for Value<T, D, V, E> {
226 type Return = T;
227 type Data = D;
228 type View = V;
229 type Event = E;
230
231 fn handle<EP>(
232 self,
233 _data: &mut Self::Data,
234 _view: &Self::View,
235 _event_or_peek: EP,
236 ) -> Handled<Self::Return, Self>
237 where
238 EP: EventOrPeek<Event = Self::Event>,
239 {
240 Handled::Return(self.0.field)
241 }
242
243 fn view<F, C>(
244 &self,
245 _data: &Self::Data,
246 _view: &mut Self::View,
247 _context: ViewContext<C>,
248 _frame: &mut F,
249 ) where
250 F: Frame,
251 C: ColModify,
252 {
253 }
254}
255
256pub struct SideEffect<F, D, V, E>(OneShot<F, D, V, E>);
257
258impl<F, D, V, E> SideEffect<F, D, V, E> {
259 pub fn new_with_view(f: F) -> Self {
260 Self(OneShot::new(f))
261 }
262}
263
264pub fn side_effect_with_view<F, D, V, E, T>(
265 f: F,
266) -> impl EventRoutine<Return = T, Data = D, View = V, Event = E>
267where
268 F: FnOnce(&mut D, &V) -> T,
269{
270 SideEffect::new_with_view(f)
271}
272
273pub fn side_effect<F, D, V, E, T>(
274 f: F,
275) -> impl EventRoutine<Return = T, Data = D, View = V, Event = E>
276where
277 F: FnOnce(&mut D) -> T,
278{
279 side_effect_with_view(|data: &mut D, _view: &V| f(data))
280}
281
282impl<F, D, V, E, T> EventRoutine for SideEffect<F, D, V, E>
283where
284 F: FnOnce(&mut D, &V) -> T,
285{
286 type Return = T;
287 type Data = D;
288 type View = V;
289 type Event = E;
290
291 fn handle<EP>(
292 self,
293 data: &mut Self::Data,
294 view: &Self::View,
295 _event_or_peek: EP,
296 ) -> Handled<Self::Return, Self>
297 where
298 EP: EventOrPeek<Event = Self::Event>,
299 {
300 Handled::Return((self.0.field)(data, view))
301 }
302
303 fn view<G, C>(
304 &self,
305 _data: &Self::Data,
306 _view: &mut Self::View,
307 _context: ViewContext<C>,
308 _frame: &mut G,
309 ) where
310 G: Frame,
311 C: ColModify,
312 {
313 }
314}
315
316enum SideEffectThenPrivate<F, D, V, E, U> {
317 First(OneShot<F, D, V, E>),
318 Second(U),
319}
320pub struct SideEffectThen<F, D, V, E, U>(SideEffectThenPrivate<F, D, V, E, U>);
321
322impl<F, D, V, E, U> SideEffectThen<F, D, V, E, U>
323where
324 U: EventRoutine<Data = D, View = V, Event = E>,
325 F: FnOnce(&mut D, &V) -> U,
326{
327 pub fn new_with_view(f: F) -> Self {
328 Self(SideEffectThenPrivate::First(OneShot::new(f)))
329 }
330}
331
332pub fn side_effect_then_with_view<F, D, V, U>(
333 f: F,
334) -> impl EventRoutine<Return = U::Return, Data = U::Data, View = U::View, Event = U::Event>
335where
336 U: EventRoutine<Data = D, View = V>,
337 F: FnOnce(&mut D, &V) -> U,
338{
339 SideEffectThen::new_with_view(f)
340}
341
342pub fn side_effect_then<F, D, V, U>(
343 f: F,
344) -> impl EventRoutine<Return = U::Return, Data = U::Data, View = U::View, Event = U::Event>
345where
346 U: EventRoutine<Data = D, View = V>,
347 F: FnOnce(&mut D) -> U,
348{
349 side_effect_then_with_view(|data: &mut D, _view: &V| f(data))
350}
351
352impl<F, D, V, E, U> EventRoutine for SideEffectThen<F, D, V, E, U>
353where
354 U: EventRoutine<Data = D, View = V, Event = E>,
355 F: FnOnce(&mut D, &V) -> U,
356{
357 type Return = U::Return;
358 type Data = D;
359 type View = V;
360 type Event = E;
361
362 fn handle<EP>(
363 self,
364 data: &mut Self::Data,
365 view: &Self::View,
366 event_or_peek: EP,
367 ) -> Handled<Self::Return, Self>
368 where
369 EP: EventOrPeek<Event = Self::Event>,
370 {
371 match self.0 {
372 SideEffectThenPrivate::First(one_shot) => (one_shot.field)(data, view)
373 .handle(data, view, Peek::new())
374 .map_continue(|u| SideEffectThen(SideEffectThenPrivate::Second(u))),
375 SideEffectThenPrivate::Second(u) => u
376 .handle(data, view, event_or_peek)
377 .map_continue(|u| SideEffectThen(SideEffectThenPrivate::Second(u))),
378 }
379 }
380
381 fn view<G, C>(
382 &self,
383 data: &Self::Data,
384 view: &mut Self::View,
385 context: ViewContext<C>,
386 frame: &mut G,
387 ) where
388 G: Frame,
389 C: ColModify,
390 {
391 match self.0 {
392 SideEffectThenPrivate::First(_) => (),
393 SideEffectThenPrivate::Second(ref u) => u.view(data, view, context, frame),
394 }
395 }
396}
397
398pub struct Map<T, F> {
399 t: T,
400 f: F,
401}
402
403impl<T, U, F> EventRoutine for Map<T, F>
404where
405 T: EventRoutine,
406 F: FnOnce(T::Return) -> U,
407{
408 type Return = U;
409 type Data = T::Data;
410 type View = T::View;
411 type Event = T::Event;
412
413 fn handle<EP>(
414 self,
415 data: &mut Self::Data,
416 view: &Self::View,
417 event_or_peek: EP,
418 ) -> Handled<Self::Return, Self>
419 where
420 EP: EventOrPeek<Event = Self::Event>,
421 {
422 let Self { t, f } = self;
423 match t.handle(data, view, event_or_peek) {
424 Handled::Continue(t) => Handled::Continue(Self { t, f }),
425 Handled::Return(r) => Handled::Return(f(r)),
426 }
427 }
428
429 fn view<G, C>(
430 &self,
431 data: &Self::Data,
432 view: &mut Self::View,
433 context: ViewContext<C>,
434 frame: &mut G,
435 ) where
436 G: Frame,
437 C: ColModify,
438 {
439 self.t.view(data, view, context, frame)
440 }
441}
442
443enum AndThenPrivate<T, U, F> {
444 First { t: T, f: F },
445 Second(U),
446}
447
448pub struct Then<T, U, F>(AndThenPrivate<T, U, F>);
449
450impl<T, U, F> EventRoutine for Then<T, U, F>
451where
452 T: EventRoutine,
453 U: EventRoutine<Data = T::Data, View = T::View, Event = T::Event>,
454 F: FnOnce() -> U,
455{
456 type Return = U::Return;
457 type Data = T::Data;
458 type View = T::View;
459 type Event = T::Event;
460
461 fn handle<EP>(
462 self,
463 data: &mut Self::Data,
464 view: &Self::View,
465 event_or_peek: EP,
466 ) -> Handled<Self::Return, Self>
467 where
468 EP: EventOrPeek<Event = Self::Event>,
469 {
470 match self.0 {
471 AndThenPrivate::First { t, f } => match t.handle(data, view, event_or_peek) {
472 Handled::Continue(t) => Handled::Continue(Self(AndThenPrivate::First { t, f })),
473 Handled::Return(_) => f()
474 .handle(data, view, Peek::new())
475 .map_continue(|u| Self(AndThenPrivate::Second(u))),
476 },
477 AndThenPrivate::Second(u) => u
478 .handle(data, view, event_or_peek)
479 .map_continue(|u| Self(AndThenPrivate::Second(u))),
480 }
481 }
482
483 fn view<G, C>(
484 &self,
485 data: &Self::Data,
486 view: &mut Self::View,
487 context: ViewContext<C>,
488 frame: &mut G,
489 ) where
490 G: Frame,
491 C: ColModify,
492 {
493 match self.0 {
494 AndThenPrivate::First { ref t, .. } => t.view(data, view, context, frame),
495 AndThenPrivate::Second(ref u) => u.view(data, view, context, frame),
496 }
497 }
498}
499
500pub struct AndThen<T, U, F>(AndThenPrivate<T, U, F>);
501
502impl<T, U, F> EventRoutine for AndThen<T, U, F>
503where
504 T: EventRoutine,
505 U: EventRoutine<Data = T::Data, View = T::View, Event = T::Event>,
506 F: FnOnce(T::Return) -> U,
507{
508 type Return = U::Return;
509 type Data = T::Data;
510 type View = T::View;
511 type Event = T::Event;
512
513 fn handle<EP>(
514 self,
515 data: &mut Self::Data,
516 view: &Self::View,
517 event_or_peek: EP,
518 ) -> Handled<Self::Return, Self>
519 where
520 EP: EventOrPeek<Event = Self::Event>,
521 {
522 match self.0 {
523 AndThenPrivate::First { t, f } => match t.handle(data, view, event_or_peek) {
524 Handled::Continue(t) => Handled::Continue(Self(AndThenPrivate::First { t, f })),
525 Handled::Return(r) => f(r)
526 .handle(data, view, Peek::new())
527 .map_continue(|u| Self(AndThenPrivate::Second(u))),
528 },
529 AndThenPrivate::Second(u) => u
530 .handle(data, view, event_or_peek)
531 .map_continue(|u| Self(AndThenPrivate::Second(u))),
532 }
533 }
534
535 fn view<G, C>(
536 &self,
537 data: &Self::Data,
538 view: &mut Self::View,
539 context: ViewContext<C>,
540 frame: &mut G,
541 ) where
542 G: Frame,
543 C: ColModify,
544 {
545 match self.0 {
546 AndThenPrivate::First { ref t, .. } => t.view(data, view, context, frame),
547 AndThenPrivate::Second(ref u) => u.view(data, view, context, frame),
548 }
549 }
550}
551
552pub trait DataSelector {
553 type DataInput;
554 type DataOutput;
555 fn data<'a>(&self, input: &'a Self::DataInput) -> &'a Self::DataOutput;
556 fn data_mut<'a>(&self, input: &'a mut Self::DataInput) -> &'a mut Self::DataOutput;
557}
558
559pub trait ViewSelector {
560 type ViewInput;
561 type ViewOutput;
562 fn view<'a>(&self, input: &'a Self::ViewInput) -> &'a Self::ViewOutput;
563 fn view_mut<'a>(&self, input: &'a mut Self::ViewInput) -> &'a mut Self::ViewOutput;
564}
565
566pub trait Selector: DataSelector + ViewSelector {}
567
568#[derive(Clone, Copy)]
569pub struct Select<T, S> {
570 t: T,
571 selector: S,
572}
573
574impl<T, S> EventRoutine for Select<T, S>
575where
576 T: EventRoutine,
577 S: Selector<DataOutput = T::Data, ViewOutput = T::View>,
578{
579 type Return = T::Return;
580 type Data = S::DataInput;
581 type View = S::ViewInput;
582 type Event = T::Event;
583
584 fn handle<EP>(
585 self,
586 data: &mut Self::Data,
587 view: &Self::View,
588 event_or_peek: EP,
589 ) -> Handled<Self::Return, Self>
590 where
591 EP: EventOrPeek<Event = Self::Event>,
592 {
593 let Self { t, selector } = self;
594 t.handle(selector.data_mut(data), selector.view(view), event_or_peek)
595 .map_continue(|t| Self { t, selector })
596 }
597
598 fn view<F, C>(
599 &self,
600 data: &Self::Data,
601 view: &mut Self::View,
602 context: ViewContext<C>,
603 frame: &mut F,
604 ) where
605 F: Frame,
606 C: ColModify,
607 {
608 self.t.view(
609 self.selector.data(data),
610 self.selector.view_mut(view),
611 context,
612 frame,
613 )
614 }
615}
616
617pub struct Repeat<T, F> {
618 t: T,
619 f: F,
620}
621impl<T, U, F> EventRoutine for Repeat<T, F>
622where
623 T: EventRoutine,
624 F: FnMut(T::Return) -> Handled<U, T>,
625{
626 type Return = U;
627 type Data = T::Data;
628 type View = T::View;
629 type Event = T::Event;
630
631 fn handle<EP>(
632 self,
633 data: &mut Self::Data,
634 view: &Self::View,
635 event_or_peek: EP,
636 ) -> Handled<Self::Return, Self>
637 where
638 EP: EventOrPeek<Event = Self::Event>,
639 {
640 let Self { t, mut f } = self;
641 match t.handle(data, view, event_or_peek) {
642 Handled::Continue(t) => Handled::Continue(Self { t, f }),
643 Handled::Return(r) => match f(r) {
644 Handled::Continue(t) => Handled::Continue(Self { t, f }),
645 Handled::Return(r) => Handled::Return(r),
646 },
647 }
648 }
649
650 fn view<G, C>(
651 &self,
652 data: &Self::Data,
653 view: &mut Self::View,
654 context: ViewContext<C>,
655 frame: &mut G,
656 ) where
657 G: Frame,
658 C: ColModify,
659 {
660 self.t.view(data, view, context, frame)
661 }
662}
663
664pub struct EventRoutineView<'e, 'v, E: EventRoutine> {
665 pub event_routine: &'e E,
666 pub view: &'v mut E::View,
667}
668
669impl<'e, 'v, 'd, E> View<&'d E::Data> for EventRoutineView<'e, 'v, E>
670where
671 E: EventRoutine,
672{
673 fn view<F: Frame, C: ColModify>(
674 &mut self,
675 data: &'d E::Data,
676 context: ViewContext<C>,
677 frame: &mut F,
678 ) {
679 self.event_routine.view(data, self.view, context, frame)
680 }
681}
682
683pub trait Decorate {
684 type View;
685 type Data;
686
687 fn view<E, F, C>(
688 &self,
689 data: &Self::Data,
690 event_routine_view: EventRoutineView<E>,
691 context: ViewContext<C>,
692 frame: &mut F,
693 ) where
694 E: EventRoutine<Data = Self::Data, View = Self::View>,
695 F: Frame,
696 C: ColModify;
697}
698
699pub struct Decorated<T, D> {
700 t: T,
701 d: D,
702}
703
704impl<T, D> EventRoutine for Decorated<T, D>
705where
706 T: EventRoutine,
707 D: Decorate<View = T::View, Data = T::Data>,
708{
709 type Return = T::Return;
710 type Data = T::Data;
711 type View = T::View;
712 type Event = T::Event;
713
714 fn handle<EP>(
715 self,
716 data: &mut Self::Data,
717 view: &Self::View,
718 event_or_peek: EP,
719 ) -> Handled<Self::Return, Self>
720 where
721 EP: EventOrPeek<Event = Self::Event>,
722 {
723 let Self { t, d } = self;
724 t.handle(data, view, event_or_peek)
725 .map_continue(|t| Self { t, d })
726 }
727
728 fn view<F, C>(
729 &self,
730 data: &Self::Data,
731 view: &mut Self::View,
732 context: ViewContext<C>,
733 frame: &mut F,
734 ) where
735 F: Frame,
736 C: ColModify,
737 {
738 let event_routine_view = EventRoutineView {
739 event_routine: &self.t,
740 view,
741 };
742 self.d.view(data, event_routine_view, context, frame)
743 }
744}
745
746pub struct OnEvent<T, F> {
747 t: T,
748 f: F,
749}
750
751impl<T, F> EventRoutine for OnEvent<T, F>
752where
753 T: EventRoutine,
754 F: FnMut(&mut &mut T::Data, &T::Event),
755{
756 type Return = T::Return;
757 type Data = T::Data;
758 type View = T::View;
759 type Event = T::Event;
760
761 fn handle<EP>(
762 self,
763 data: &mut Self::Data,
764 view: &Self::View,
765 event_or_peek: EP,
766 ) -> Handled<Self::Return, Self>
767 where
768 EP: EventOrPeek<Event = Self::Event>,
769 {
770 let on_peek = |(s, data)| {
771 let Self { t, f } = s;
772 t.handle(data, view, Peek::new())
773 .map_continue(|t| Self { t, f })
774 };
775 let on_event = |(s, mut data), event| {
776 let Self { t, mut f } = s;
777 (f)(&mut data, &event);
778 t.handle(data, view, Event::new(event))
779 .map_continue(|t| Self { t, f })
780 };
781 event_or_peek.with((self, data), on_event, on_peek)
782 }
783
784 fn view<G, C>(
785 &self,
786 data: &Self::Data,
787 view: &mut Self::View,
788 context: ViewContext<C>,
789 frame: &mut G,
790 ) where
791 G: Frame,
792 C: ColModify,
793 {
794 self.t.view(data, view, context, frame);
795 }
796}
797
798pub struct Unfold<T, U, F, R> {
799 t: PhantomData<T>,
800 u: PhantomData<U>,
801 f: F,
802 routine: R,
803}
804
805impl<T, U, F, R> Unfold<T, U, F, R>
806where
807 F: FnMut(T) -> R,
808 R: EventRoutine<Return = Handled<U, T>>,
809{
810 pub fn new(acc: T, mut f: F) -> Self {
811 let routine = f(acc);
812 Self {
813 f,
814 routine,
815 t: PhantomData,
816 u: PhantomData,
817 }
818 }
819}
820
821impl<T, U, F, R> EventRoutine for Unfold<T, U, F, R>
822where
823 F: FnMut(T) -> R,
824 R: EventRoutine<Return = Handled<U, T>>,
825{
826 type Return = U;
827 type Data = R::Data;
828 type View = R::View;
829 type Event = R::Event;
830
831 fn handle<EP>(
832 self,
833 data: &mut Self::Data,
834 view: &Self::View,
835 event_or_peek: EP,
836 ) -> Handled<Self::Return, Self>
837 where
838 EP: EventOrPeek<Event = Self::Event>,
839 {
840 let Self {
841 t,
842 u,
843 mut f,
844 routine,
845 } = self;
846 match routine.handle(data, view, event_or_peek) {
847 Handled::Continue(routine) => Handled::Continue(Self { t, u, f, routine }),
848 Handled::Return(handled) => match handled {
849 Handled::Continue(acc) => Handled::Continue(Self {
850 t,
851 u,
852 routine: f(acc),
853 f,
854 }),
855 Handled::Return(ret) => Handled::Return(ret),
856 },
857 }
858 }
859
860 fn view<G, C>(
861 &self,
862 data: &Self::Data,
863 view: &mut Self::View,
864 context: ViewContext<C>,
865 frame: &mut G,
866 ) where
867 G: Frame,
868 C: ColModify,
869 {
870 self.routine.view(data, view, context, frame)
871 }
872}
873
874pub struct Loop<T, F, R> {
875 t: PhantomData<T>,
876 f: F,
877 routine: R,
878}
879impl<T, F, R> Loop<T, F, R>
880where
881 F: FnMut() -> R,
882 R: EventRoutine<Return = Option<T>>,
883{
884 pub fn new(mut f: F) -> Self {
885 let routine = f();
886 Self {
887 t: PhantomData,
888 f,
889 routine,
890 }
891 }
892}
893
894impl<T, F, R> EventRoutine for Loop<T, F, R>
895where
896 F: FnMut() -> R,
897 R: EventRoutine<Return = Option<T>>,
898{
899 type Return = T;
900 type Data = R::Data;
901 type View = R::View;
902 type Event = R::Event;
903
904 fn handle<EP>(
905 self,
906 data: &mut Self::Data,
907 view: &Self::View,
908 event_or_peek: EP,
909 ) -> Handled<Self::Return, Self>
910 where
911 EP: EventOrPeek<Event = Self::Event>,
912 {
913 let Self { t, mut f, routine } = self;
914 match routine.handle(data, view, event_or_peek) {
915 Handled::Continue(routine) => Handled::Continue(Self { t, f, routine }),
916 Handled::Return(maybe_ret) => match maybe_ret {
917 None => Handled::Continue(Self { t, routine: f(), f }),
918 Some(ret) => Handled::Return(ret),
919 },
920 }
921 }
922
923 fn view<G, C>(
924 &self,
925 data: &Self::Data,
926 view: &mut Self::View,
927 context: ViewContext<C>,
928 frame: &mut G,
929 ) where
930 G: Frame,
931 C: ColModify,
932 {
933 self.routine.view(data, view, context, frame)
934 }
935}
936
937#[macro_export]
938macro_rules! make_either {
939 ($type:ident = $first:ident | $($rest:ident)|*) => {
940 pub enum $type<$first, $($rest),*> {
941 $first($first),
942 $($rest($rest)),*
943 }
944 impl<$first, $($rest),*> EventRoutine for $type<$first, $($rest),*>
945 where
946 $first: EventRoutine,
947 $($rest: EventRoutine<Data = $first::Data, View = $first::View, Return = $first::Return, Event = $first::Event>),*
948 {
949 type Return = $first::Return;
950 type Data = $first::Data;
951 type View = $first::View;
952 type Event = $first::Event;
953
954 fn handle<EP>(self, data: &mut Self::Data, view: &Self::View, event_or_peek: EP) -> Handled<Self::Return, Self>
955 where
956 EP: EventOrPeek<Event = Self::Event>,
957 {
958 match self {
959 $type::$first(x) => x.handle(data, view, event_or_peek).map_continue($type::$first),
960 $($type::$rest(x) => x.handle(data, view, event_or_peek).map_continue($type::$rest)),*
961 }
962 }
963 fn view<FR, CM>(&self, data: &Self::Data, view: &mut Self::View, context: ViewContext<CM>, frame: &mut FR)
964 where
965 FR: Frame,
966 CM: ColModify,
967 {
968 match self {
969 $type::$first(x) => x.view(data, view, context, frame),
970 $($type::$rest(x) => x.view(data, view, context, frame)),*
971 }
972 }
973 }
974 };
975}