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