[][src]Struct async_hsm::Composite

pub struct Composite<Data> {
    pub data: Data,
}

The structure may be used to share data between states within the same Composite

Fields

data: Data

Implementations

impl<Data> Composite<Data>[src]

Implementing Composite methods

pub fn new(data: Data) -> Self[src]

Create a new Composite instance, sharing the data between all states within the Composite

pub async fn init<'s, Factory, FactoryArg, Out, Err, Fut>(
    &'s mut self,
    f: Factory,
    arg: FactoryArg
) -> Result<Out, Err> where
    Factory: FnOnce(&'s mut Self, FactoryArg) -> Fut,
    Fut: Future<Output = Result<Transit<'s, Self, Out, Err>, Err>>,
    Out: Sized + Copy
[src]

Composition of states, only one sub-state at a time. The function f is initializing the first sub state.

#Examples

    use async_std::prelude::*;
    use async_std::stream;
    use async_std::task;
    use async_hsm::{Composite, Transit, Builder, BuilderPair};
    use std::rc::Rc;
    use std::cell::RefCell;

    type Score = u32;
    type EnterStateScore = u32;
    type AppComposite = Composite<AppData>;
    type AppTransit<'s> = Transit<'s, AppComposite, Score, AppError>;
    type AppBuilder = Builder<AppComposite, EnterStateScore, Score, AppError>;
    type AppBuilderPair = BuilderPair<AppComposite, EnterStateScore, Score, AppError>;

    #[derive(Debug, Clone, PartialEq)]
    enum AppError { Failure }

    #[derive(Debug, Clone, PartialEq)]
    enum IoEvent { Ping, Pong, Terminate, Menu, Play }

    #[derive(Debug, Clone)]
    struct AppData { event: Rc<RefCell<stream::FromIter<std::vec::IntoIter<IoEvent>>>> }

    async fn ping<'s>(comp: &'s mut AppComposite, score: Score) -> Result<AppTransit<'s>, AppError> {
        let mut score = score + 1;
        let event = comp.data.event.clone();
        while let Some(event) = (*event).borrow_mut().next().await {
            match event {
                IoEvent::Pong => return Ok(Transit::To(Box::pin(pong(comp, score)))),
                _ => score += 1,
            }
        }
        Ok(Transit::Lift(score))
    }

    async fn pong<'s>(comp: &'s mut AppComposite, score: Score) -> Result<AppTransit<'s>, AppError> {
        let mut score = score + 1;
        let event = comp.data.event.clone();
        while let Some(event) = (*event).borrow_mut().next().await {
            match event {
                IoEvent::Ping => return Ok(Transit::To(Box::pin(ping(comp, score)))),
                _ => score += 1,
            }
        }
        Ok(Transit::Lift(score))
    }

    #[test]
    fn test_game() {
        let sequence = vec![ IoEvent::Ping, IoEvent::Pong, IoEvent::Ping, IoEvent::Pong];
        let event = Rc::new(RefCell::new(stream::from_iter(sequence)));
        let start_score = 0;
        let mut app = AppComposite::new(AppData { event: event });
        let result: Result<Score, AppError> = task::block_on(app.init(ping, start_score));
        assert_eq!(Ok(5), result);
    }

Auto Trait Implementations

impl<Data> RefUnwindSafe for Composite<Data> where
    Data: RefUnwindSafe

impl<Data> Send for Composite<Data> where
    Data: Send

impl<Data> Sync for Composite<Data> where
    Data: Sync

impl<Data> Unpin for Composite<Data> where
    Data: Unpin

impl<Data> UnwindSafe for Composite<Data> where
    Data: UnwindSafe

Blanket Implementations

impl<T> Any for T where
    T: 'static + ?Sized
[src]

impl<T> Borrow<T> for T where
    T: ?Sized
[src]

impl<T> BorrowMut<T> for T where
    T: ?Sized
[src]

impl<T> From<T> for T[src]

impl<T, U> Into<U> for T where
    U: From<T>, 
[src]

impl<T, U> TryFrom<U> for T where
    U: Into<T>, 
[src]

type Error = Infallible

The type returned in the event of a conversion error.

impl<T, U> TryInto<U> for T where
    U: TryFrom<T>, 
[src]

type Error = <U as TryFrom<T>>::Error

The type returned in the event of a conversion error.