Skip to content

Commit da8a0cc

Browse files
committed
🆕 [example] State names visitor
Problem: - There is no example showig how to print state names using a visitor. - There is no easy support to print sub State Machines state names. Solution: - Add example to print state names using a custom visitor and a composite State Machine.
1 parent 9fc46f5 commit da8a0cc

File tree

6 files changed

+94
-9
lines changed

6 files changed

+94
-9
lines changed

example/CMakeLists.txt

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -84,4 +84,6 @@ if (IS_COMPILER_GCC_LIKE)
8484
add_example(testing example_testing testing.cpp)
8585

8686
add_example(transitions example_transitions transitions.cpp)
87+
88+
add_example(visitor example_visitor visitor.cpp)
8789
endif()

example/visitor.cpp

Lines changed: 84 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,84 @@
1+
//
2+
// Copyright (c) 2016-2020 Kris Jusiak (kris at jusiak dot net)
3+
//
4+
// Distributed under the Boost Software License, Version 1.0.
5+
// (See accompanying file LICENSE_1_0.txt or copy at
6+
// http://www.boost.org/LICENSE_1_0.txt)
7+
//
8+
#include <boost/sml.hpp>
9+
#include <cassert>
10+
#include <iostream>
11+
12+
namespace sml = boost::sml;
13+
14+
struct e1 {};
15+
struct e2 {};
16+
struct e3 {};
17+
struct e4 {};
18+
struct e5 {};
19+
20+
struct sub {
21+
auto operator()() const {
22+
using namespace sml;
23+
// clang-format off
24+
return make_transition_table(
25+
*"idle"_s + event<e3> = "sub1"_s
26+
, "sub1"_s + event<e4> = X
27+
);
28+
// clang-format on
29+
}
30+
};
31+
32+
struct composite {
33+
auto operator()() const {
34+
using namespace sml;
35+
// clang-format off
36+
return make_transition_table(
37+
*"idle"_s + event<e1> = "s1"_s
38+
, "s1"_s + event<e2> = state<sub>
39+
, state<sub> + event<e5> = X
40+
);
41+
// clang-format on
42+
}
43+
};
44+
45+
template <class TSM>
46+
class state_name_visitor {
47+
public:
48+
explicit state_name_visitor(const TSM& sm) : sm_{sm} {}
49+
50+
template <class TSub>
51+
void operator()(boost::sml::aux::string<boost::sml::sm<TSub>>) const {
52+
std::cout << boost::sml::aux::get_type_name<TSub>() << ':';
53+
sm_.template visit_current_states<boost::sml::aux::identity<TSub>>(*this);
54+
}
55+
56+
template <class TState>
57+
void operator()(TState state) const {
58+
std::cout << state.c_str() << '\n';
59+
}
60+
61+
private:
62+
const TSM& sm_;
63+
};
64+
65+
int main() {
66+
sml::sm<composite> sm{};
67+
68+
const auto state_name = state_name_visitor<decltype(sm)>{sm};
69+
70+
sm.process_event(e1{});
71+
sm.visit_current_states(state_name); // s1
72+
73+
sm.process_event(e2{});
74+
sm.visit_current_states(state_name); // sub:idle
75+
76+
sm.process_event(e3{});
77+
sm.visit_current_states(state_name); // sub:sub1
78+
79+
sm.process_event(e4{});
80+
sm.visit_current_states(state_name); // sub:terminate
81+
82+
sm.process_event(e5{});
83+
sm.visit_current_states(state_name); // terminate
84+
}

include/boost/sml.hpp

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -338,7 +338,7 @@ struct missing_ctor_parameter {
338338
operator U() {
339339
return {};
340340
}
341-
#if !defined(_MSC_VER) && !defined(__clang__)
341+
#if !(defined(_MSC_VER) && !defined(__clang__))
342342
template <class TMissing, __BOOST_SML_REQUIRES(!aux::is_base_of<pool_type_base, TMissing>::value)>
343343
operator TMissing &() const {
344344
static_assert(missing_ctor_parameter<TMissing>::value,
@@ -2589,7 +2589,7 @@ struct transition<state<internal>, state<S2>, front::event<E>, always, none> {
25892589
};
25902590
}
25912591
using _ = back::_;
2592-
#if !defined(_MSC_VER) && !defined(__clang__)
2592+
#if !(defined(_MSC_VER) && !defined(__clang__))
25932593
template <class TEvent>
25942594
constexpr front::event<TEvent> event{};
25952595
#else
@@ -2606,15 +2606,15 @@ template <class T>
26062606
front::event<back::exception<T>> exception __BOOST_SML_VT_INIT;
26072607
using anonymous = back::anonymous;
26082608
using initial = back::initial;
2609-
#if !defined(_MSC_VER) && !defined(__clang__)
2609+
#if !(defined(_MSC_VER) && !defined(__clang__))
26102610
template <class T>
26112611
constexpr typename front::state_sm<T>::type state{};
26122612
#else
26132613
template <class T>
26142614
typename front::state_sm<T>::type state __BOOST_SML_VT_INIT;
26152615
#endif
26162616
inline namespace literals {
2617-
#if !defined(_MSC_VER) && !defined(__clang__)
2617+
#if !(defined(_MSC_VER) && !defined(__clang__))
26182618
template <class T, T... Chrs>
26192619
constexpr auto operator""_s() {
26202620
return front::state<aux::string<T, Chrs...>>{};

include/boost/sml/aux_/utility.hpp

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -160,7 +160,7 @@ struct missing_ctor_parameter {
160160
return {};
161161
}
162162

163-
#if !defined(_MSC_VER) && !defined(__clang__) // __pph__
163+
#if !(defined(_MSC_VER) && !defined(__clang__)) // __pph__
164164
template <class TMissing, __BOOST_SML_REQUIRES(!aux::is_base_of<pool_type_base, TMissing>::value)>
165165
operator TMissing &() const {
166166
static_assert(missing_ctor_parameter<TMissing>::value,

include/boost/sml/back/policies/testing.hpp

Lines changed: 0 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -13,7 +13,6 @@ namespace back {
1313
namespace policies {
1414

1515
struct testing_policy__ {};
16-
1716
struct testing : aux::pair<testing_policy__, testing> {};
1817

1918
} // namespace policies

include/boost/sml/transition_table.hpp

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -21,7 +21,7 @@ using _ = back::_;
2121

2222
/// events
2323

24-
#if !defined(_MSC_VER) && !defined(__clang__) // __pph__
24+
#if !(defined(_MSC_VER) && !defined(__clang__)) // __pph__
2525
template <class TEvent>
2626
constexpr front::event<TEvent> event{};
2727
#else // __pph__
@@ -46,7 +46,7 @@ using initial = back::initial;
4646

4747
/// states
4848

49-
#if !defined(_MSC_VER) && !defined(__clang__) // __pph__
49+
#if !(defined(_MSC_VER) && !defined(__clang__)) // __pph__
5050
template <class T>
5151
constexpr typename front::state_sm<T>::type state{};
5252
#else // __pph__
@@ -55,7 +55,7 @@ typename front::state_sm<T>::type state __BOOST_SML_VT_INIT;
5555
#endif // __pph__
5656

5757
inline namespace literals {
58-
#if !defined(_MSC_VER) && !defined(__clang__) // __pph__
58+
#if !(defined(_MSC_VER) && !defined(__clang__)) // __pph__
5959
template <class T, T... Chrs>
6060
constexpr auto operator""_s() {
6161
return front::state<aux::string<T, Chrs...>>{};

0 commit comments

Comments
 (0)