summaryrefslogtreecommitdiff
path: root/core/property_list.hpp
diff options
context:
space:
mode:
authorJan Huwald <jh@sotun.de>2012-05-07 20:01:51 (GMT)
committerJan Huwald <jh@sotun.de>2012-05-07 20:01:51 (GMT)
commit420d2ef464d4a741028e132e662d5626806a41f5 (patch)
tree1aca6eb512e4ed0fb5f3c10c528cb998b6ffd695 /core/property_list.hpp
Initial commitHEADmaster
Diffstat (limited to 'core/property_list.hpp')
-rw-r--r--core/property_list.hpp94
1 files changed, 94 insertions, 0 deletions
diff --git a/core/property_list.hpp b/core/property_list.hpp
new file mode 100644
index 0000000..3fd5ee9
--- /dev/null
+++ b/core/property_list.hpp
@@ -0,0 +1,94 @@
+#ifndef RAA4DT8yVWXBMqy1rxYiM12MKFA
+#define RAA4DT8yVWXBMqy1rxYiM12MKFA
+
+#include <boost/mpl/assert.hpp>
+#include <boost/mpl/empty.hpp>
+#include <boost/mpl/front.hpp>
+#include <boost/mpl/list.hpp>
+#include <boost/mpl/logical.hpp>
+#include <boost/mpl/not.hpp>
+#include <boost/mpl/pop_front.hpp>
+#include <boost/static_assert.hpp>
+#include <boost/type_traits/is_same.hpp>
+
+#include "property_instance.hpp"
+#include "template_helpers.hpp"
+
+namespace PLImpl {
+
+ using namespace boost::mpl;
+
+ // forward decls
+ template <typename Haystack, typename Needle> struct PL_Contains;
+
+
+ /// PL - Property List
+
+ // template <typename Head, bool doWriteResults, typename Tail>
+ template <typename List>
+ struct PL {
+ // compile time data structure (types)
+ typedef typename front<List>::type head_t;
+ typedef typename pop_front<List>::type tail_t;
+
+ typedef typename head_t::first prop_t;
+ typedef typename head_t::second doWriteResult_t;
+ typedef typename if_<empty<tail_t>,
+ PL<Void>,
+ PL<tail_t>
+ >::type next_t;
+
+ typedef PropertyInstance<prop_t, doWriteResult_t::value > data_t;
+
+ // access methods
+ // template params:
+ // - PropComp: the list of all properties
+ // - Action: the action class to call
+ template<typename PropComp, typename Action>
+ inline typename Action::result_t call(PropComp &pc, Action &action) {
+ typename Action::template local_state_t<prop_t, doWriteResult_t::value> state;
+ action.pre(pc, data, state);
+ tail.call<PropComp, Action>(pc, action);
+ action.post(pc, data, state);
+ return action.result;
+ }
+
+ // data members
+ data_t data;
+ next_t tail;
+
+ // integrity checks:
+ // 1. each property may be used only once
+ BOOST_MPL_ASSERT(( not_< PL_Contains< next_t, prop_t > > ));
+ // TODO (beauty): dependencies (once they are implemented anywhere)
+ };
+
+ // the empty tail
+ template<>
+ struct PL<Void> {
+ typedef Void prop_t;
+ typedef PL<Void> tail_t;
+ typedef Void data_t;
+
+ template<typename PropComp, typename Action>
+ inline typename Action::result_t call(PropComp &pc, Action &action) {
+ return typename Action::result_t();
+ }
+ };
+
+ /// PL Template Helpers
+ template <typename Haystack, typename Needle>
+ struct PL_Contains : boost::mpl::or_<
+ boost::is_same<typename Haystack::prop_t, Needle>,
+ PL_Contains<typename Haystack::next_t, Needle>
+ > { };
+
+ template <typename Needle>
+ struct PL_Contains<PL<Void>, Needle> : boost::mpl::false_ { };
+
+};
+
+using PLImpl::PL;
+using PLImpl::PL_Contains;
+
+#endif // RAA4DT8yVWXBMqy1rxYiM12MKFA
contact: Jan Huwald // Impressum