• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 #ifndef BOOST_STATECHART_REACTION_DISPATCHER_HPP_INCLUDED
2 #define BOOST_STATECHART_REACTION_DISPATCHER_HPP_INCLUDED
3 //////////////////////////////////////////////////////////////////////////////
4 // Copyright 2008 Andreas Huber Doenni
5 // Distributed under the Boost Software License, Version 1.0. (See accompany-
6 // ing file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
7 //////////////////////////////////////////////////////////////////////////////
8 
9 
10 
11 #include <boost/statechart/result.hpp>
12 
13 #include <boost/mpl/if.hpp>
14 
15 #include <boost/polymorphic_cast.hpp> // boost::polymorphic_downcast
16 #include <boost/type_traits/is_same.hpp>
17 
18 
19 
20 namespace boost
21 {
22 namespace statechart
23 {
24 namespace detail
25 {
26 
27 
28 
29 //////////////////////////////////////////////////////////////////////////////
30 template< class Event >
31 struct no_context
32 {
33   void no_function( const Event & );
34 };
35 
36 //////////////////////////////////////////////////////////////////////////////
37 template<
38   class Reactions, class State, class EventBase, class Event,
39   class ActionContext, class IdType >
40 class reaction_dispatcher
41 {
42   private:
43     struct without_action
44     {
reactboost::statechart::detail::reaction_dispatcher::without_action45       static result react( State & stt, const EventBase & )
46       {
47         return Reactions::react_without_action( stt );
48       }
49     };
50 
51     struct base_with_action
52     {
reactboost::statechart::detail::reaction_dispatcher::base_with_action53       static result react( State & stt, const EventBase & evt )
54       {
55         return Reactions::react_with_action( stt, evt );
56       }
57     };
58 
59     struct base
60     {
reactboost::statechart::detail::reaction_dispatcher::base61       static result react(
62         State & stt, const EventBase & evt, const IdType & )
63       {
64         typedef typename mpl::if_<
65           is_same< ActionContext, detail::no_context< Event > >,
66           without_action, base_with_action
67         >::type reaction;
68         return reaction::react( stt, evt );
69       }
70     };
71 
72     struct derived_with_action
73     {
reactboost::statechart::detail::reaction_dispatcher::derived_with_action74       static result react( State & stt, const EventBase & evt )
75       {
76         return Reactions::react_with_action(
77           stt, *polymorphic_downcast< const Event * >( &evt ) );
78       }
79     };
80 
81     struct derived
82     {
reactboost::statechart::detail::reaction_dispatcher::derived83       static result react(
84         State & stt, const EventBase & evt, const IdType & eventType )
85       {
86         if ( eventType == Event::static_type() )
87         {
88           typedef typename mpl::if_<
89             is_same< ActionContext, detail::no_context< Event > >,
90             without_action, derived_with_action
91           >::type reaction;
92           return reaction::react( stt, evt );
93         }
94         else
95         {
96           return detail::result_utility::make_result( detail::no_reaction );
97         }
98       }
99     };
100 
101   public:
react(State & stt,const EventBase & evt,const IdType & eventType)102     static reaction_result react(
103       State & stt, const EventBase & evt, const IdType & eventType )
104     {
105       typedef typename mpl::if_<
106         is_same< Event, EventBase >, base, derived
107       >::type reaction;
108       return result_utility::get_result(
109         reaction::react( stt, evt, eventType ) );
110     }
111 };
112 
113 
114 
115 } // namespace detail
116 } // namespace statechart
117 } // namespace boost
118 
119 
120 
121 #endif
122