add opendcm constraint solver
This commit is contained in:
committed by
Stefan Tröger
parent
d50f7f1787
commit
02bc130c42
36
src/Mod/Assembly/App/opendcm/moduleState/defines.hpp
Normal file
36
src/Mod/Assembly/App/opendcm/moduleState/defines.hpp
Normal file
@@ -0,0 +1,36 @@
|
||||
/*
|
||||
openDCM, dimensional constraint manager
|
||||
Copyright (C) 2013 Stefan Troeger <stefantroeger@gmx.net>
|
||||
|
||||
This library is free software; you can redistribute it and/or modify
|
||||
it under the terms of the GNU Lesser General Public License as published by
|
||||
the Free Software Foundation; either version 2.1 of the License, or
|
||||
(at your option) any later version.
|
||||
|
||||
This library is distributed in the hope that it will be useful,
|
||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
GNU Lesser General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU Lesser General Public License along
|
||||
with this library; if not, write to the Free Software Foundation, Inc.,
|
||||
51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
*/
|
||||
|
||||
#ifndef DCM_DEFINES_STATE_H
|
||||
#define DCM_DEFINES_STATE_H
|
||||
|
||||
#include "opendcm/core/property.hpp"
|
||||
#include "opendcm/core/clustergraph.hpp"
|
||||
|
||||
namespace dcm {
|
||||
namespace details {
|
||||
|
||||
struct cluster_vertex_prop {
|
||||
typedef GlobalVertex type;
|
||||
typedef cluster_property kind;
|
||||
};
|
||||
}
|
||||
}
|
||||
|
||||
#endif
|
||||
@@ -0,0 +1,72 @@
|
||||
/*
|
||||
openDCM, dimensional constraint manager
|
||||
Copyright (C) 2013 Stefan Troeger <stefantroeger@gmx.net>
|
||||
|
||||
This library is free software; you can redistribute it and/or modify
|
||||
it under the terms of the GNU Lesser General Public License as published by
|
||||
the Free Software Foundation; either version 2.1 of the License, or
|
||||
(at your option) any later version.
|
||||
|
||||
This library is distributed in the hope that it will be useful,
|
||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
GNU Lesser General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU Lesser General Public License along
|
||||
with this library; if not, write to the Free Software Foundation, Inc.,
|
||||
51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
*/
|
||||
|
||||
#ifndef DCM_EDGE_GENERATOR_H
|
||||
#define DCM_EDGE_GENERATOR_H
|
||||
|
||||
#include "property_generator.hpp"
|
||||
#include "object_generator.hpp"
|
||||
#include "extractor.hpp"
|
||||
|
||||
#include <boost/spirit/include/karma.hpp>
|
||||
#include <boost/spirit/include/phoenix.hpp>
|
||||
#include <boost/fusion/support/is_sequence.hpp>
|
||||
|
||||
#include <boost/fusion/include/is_sequence.hpp>
|
||||
|
||||
namespace karma = boost::spirit::karma;
|
||||
namespace phx = boost::phoenix;
|
||||
|
||||
namespace dcm {
|
||||
namespace details {
|
||||
|
||||
template<typename Sys>
|
||||
struct edge_generator : karma::grammar<Iterator, std::vector<fusion::vector3<typename Sys::Cluster::edge_bundle, GlobalVertex, GlobalVertex> >()> {
|
||||
|
||||
edge_generator();
|
||||
|
||||
karma::rule<Iterator, std::vector<fusion::vector3<typename Sys::Cluster::edge_bundle, GlobalVertex, GlobalVertex> >()> edge_range;
|
||||
karma::rule<Iterator, fusion::vector3<typename Sys::Cluster::edge_bundle, GlobalVertex, GlobalVertex>()> edge;
|
||||
karma::rule<Iterator, std::vector<typename Sys::Cluster::edge_bundle_single>&()> globaledge_range;
|
||||
karma::rule<Iterator, typename Sys::Cluster::edge_bundle_single()> globaledge;
|
||||
details::edge_prop_gen<Sys> edge_prop;
|
||||
details::obj_gen<Sys> objects;
|
||||
Extractor<Sys> ex;
|
||||
};
|
||||
|
||||
template<typename Sys>
|
||||
struct vertex_generator : karma::grammar<Iterator, std::vector<typename Sys::Cluster::vertex_bundle>()> {
|
||||
|
||||
vertex_generator();
|
||||
|
||||
karma::rule<Iterator, std::vector<typename Sys::Cluster::vertex_bundle>()> vertex_range;
|
||||
karma::rule<Iterator, typename Sys::Cluster::vertex_bundle()> vertex;
|
||||
details::vertex_prop_gen<Sys> vertex_prop;
|
||||
details::obj_gen<Sys> objects;
|
||||
Extractor<Sys> ex;
|
||||
};
|
||||
|
||||
}//details
|
||||
}//dcm
|
||||
|
||||
#ifndef USE_EXTERNAL
|
||||
#include "edge_vertex_generator_imp.hpp"
|
||||
#endif
|
||||
|
||||
#endif
|
||||
@@ -0,0 +1,57 @@
|
||||
/*
|
||||
openDCM, dimensional constraint manager
|
||||
Copyright (C) 2013 Stefan Troeger <stefantroeger@gmx.net>
|
||||
|
||||
This library is free software; you can redistribute it and/or modify
|
||||
it under the terms of the GNU Lesser General Public License as published by
|
||||
the Free Software Foundation; either version 2.1 of the License, or
|
||||
(at your option) any later version.
|
||||
|
||||
This library is distributed in the hope that it will be useful,
|
||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
GNU Lesser General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU Lesser General Public License along
|
||||
with this library; if not, write to the Free Software Foundation, Inc.,
|
||||
51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
*/
|
||||
|
||||
#ifndef DCM_EDGE_GENERATOR_IMP_H
|
||||
#define DCM_EDGE_GENERATOR_IMP_H
|
||||
|
||||
#include "edge_vertex_generator.hpp"
|
||||
|
||||
namespace dcm {
|
||||
namespace details {
|
||||
|
||||
template<typename Sys>
|
||||
edge_generator<Sys>::edge_generator() : edge_generator<Sys>::base_type(edge_range) {
|
||||
|
||||
globaledge = karma::int_[phx::bind(&Extractor<Sys>::getGlobalEdgeID, ex, karma::_val, karma::_1)]
|
||||
<< " source=" << karma::int_[phx::bind(&Extractor<Sys>::getGlobalEdgeSource, ex, karma::_val, karma::_1)]
|
||||
<< " target=" << karma::int_[phx::bind(&Extractor<Sys>::getGlobalEdgeTarget, ex, karma::_val, karma::_1)] << '>'
|
||||
<< "+" << objects[karma::_1 = phx::at_c<0>(karma::_val)] << "-\n" ;
|
||||
|
||||
|
||||
globaledge_range = *(karma::lit("<GlobalEdge id=")<<globaledge<<karma::lit("</GlobalEdge>"));
|
||||
|
||||
edge = karma::lit("source=")<<karma::int_[karma::_1 = phx::at_c<1>(karma::_val)] << " target="<<karma::int_[karma::_1 = phx::at_c<2>(karma::_val)] << ">+"
|
||||
<< edge_prop[karma::_1 = phx::at_c<0>(phx::at_c<0>(karma::_val))]
|
||||
<< karma::eol << globaledge_range[karma::_1 = phx::at_c<1>(phx::at_c<0>(karma::_val))] << '-' << karma::eol;
|
||||
|
||||
edge_range = (karma::lit("<Edge ") << edge << karma::lit("</Edge>")) % karma::eol;
|
||||
};
|
||||
|
||||
template<typename Sys>
|
||||
vertex_generator<Sys>::vertex_generator() : vertex_generator<Sys>::base_type(vertex_range) {
|
||||
|
||||
vertex = karma::int_ << ">+" << vertex_prop << objects << "-\n";
|
||||
|
||||
vertex_range = '\n' << (karma::lit("<Vertex id=") << vertex << karma::lit("</Vertex>")) % karma::eol;
|
||||
};
|
||||
|
||||
}//details
|
||||
}//dcm
|
||||
|
||||
#endif
|
||||
@@ -0,0 +1,71 @@
|
||||
/*
|
||||
openDCM, dimensional constraint manager
|
||||
Copyright (C) 2013 Stefan Troeger <stefantroeger@gmx.net>
|
||||
|
||||
This library is free software; you can redistribute it and/or modify
|
||||
it under the terms of the GNU Lesser General Public License as published by
|
||||
the Free Software Foundation; either version 2.1 of the License, or
|
||||
(at your option) any later version.
|
||||
|
||||
This library is distributed in the hope that it will be useful,
|
||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
GNU Lesser General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU Lesser General Public License along
|
||||
with this library; if not, write to the Free Software Foundation, Inc.,
|
||||
51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
*/
|
||||
|
||||
#ifndef DCM_EDGE_VERTEX_PARSER_H
|
||||
#define DCM_EDGE_VERTEX_PARSER_H
|
||||
|
||||
#include <boost/spirit/include/qi.hpp>
|
||||
#include "opendcm/core/clustergraph.hpp"
|
||||
#include "extractor.hpp"
|
||||
|
||||
namespace qi = boost::spirit::qi;
|
||||
namespace fusion = boost::fusion;
|
||||
|
||||
namespace dcm {
|
||||
|
||||
typedef boost::spirit::istream_iterator IIterator;
|
||||
|
||||
namespace details {
|
||||
|
||||
template<typename Sys>
|
||||
struct edge_parser : qi::grammar< IIterator, fusion::vector<LocalEdge, GlobalEdge, bool, bool>(typename Sys::Cluster*, Sys*),
|
||||
qi::space_type > {
|
||||
|
||||
edge_parser();
|
||||
details::obj_par<Sys> objects;
|
||||
Injector<Sys> in;
|
||||
|
||||
qi::rule<IIterator, fusion::vector<LocalEdge, GlobalEdge, bool, bool>(typename Sys::Cluster*, Sys*), qi::space_type> edge;
|
||||
qi::rule<IIterator, typename Sys::Cluster::edge_bundle_single(Sys*), qi::space_type> global_edge;
|
||||
details::edge_prop_par<Sys> edge_prop;
|
||||
|
||||
};
|
||||
|
||||
template<typename Sys>
|
||||
struct vertex_parser : qi::grammar< IIterator, fusion::vector<LocalVertex, GlobalVertex>(typename Sys::Cluster*, Sys*),
|
||||
qi::space_type> {
|
||||
|
||||
vertex_parser();
|
||||
|
||||
details::obj_par<Sys> objects;
|
||||
Injector<Sys> in;
|
||||
|
||||
qi::rule<IIterator, fusion::vector<LocalVertex, GlobalVertex>(typename Sys::Cluster*, Sys*), qi::space_type> vertex;
|
||||
details::vertex_prop_par<Sys> prop;
|
||||
|
||||
};
|
||||
|
||||
}
|
||||
}
|
||||
|
||||
//#ifndef USE_EXTERNAL
|
||||
//#include "edge_vertex_parser_imp.hpp"
|
||||
//#endif
|
||||
|
||||
#endif
|
||||
@@ -0,0 +1,55 @@
|
||||
/*
|
||||
openDCM, dimensional constraint manager
|
||||
Copyright (C) 2013 Stefan Troeger <stefantroeger@gmx.net>
|
||||
|
||||
This library is free software; you can redistribute it and/or modify
|
||||
it under the terms of the GNU Lesser General Public License as published by
|
||||
the Free Software Foundation; either version 2.1 of the License, or
|
||||
(at your option) any later version.
|
||||
|
||||
This library is distributed in the hope that it will be useful,
|
||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
GNU Lesser General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU Lesser General Public License along
|
||||
with this library; if not, write to the Free Software Foundation, Inc.,
|
||||
51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
*/
|
||||
|
||||
#ifndef DCM_EDGE_PARSER_IMP_H
|
||||
#define DCM_EDGE_PARSER_IMP_H
|
||||
|
||||
#include "edge_vertex_parser.hpp"
|
||||
|
||||
namespace dcm {
|
||||
namespace details {
|
||||
|
||||
template<typename Sys>
|
||||
edge_parser<Sys>::edge_parser() : edge_parser<Sys>::base_type(edge) {
|
||||
|
||||
global_edge = qi::lit("<GlobalEdge") >> qi::lit("id=") >> qi::int_[phx::bind(&GlobalEdge::ID, phx::at_c<1>(qi::_val)) = qi::_1]
|
||||
>> qi::lit("source=") >> qi::int_[phx::bind(&GlobalEdge::source, phx::at_c<1>(qi::_val)) = qi::_1]
|
||||
>> qi::lit("target=") >> qi::int_[phx::bind(&GlobalEdge::target, phx::at_c<1>(qi::_val)) = qi::_1] >> '>'
|
||||
>> objects(qi::_r1)[phx::at_c<0>(qi::_val) = qi::_1] >> "</GlobalEdge>";
|
||||
|
||||
edge = (qi::lit("<Edge") >> "source=" >> qi::int_ >> "target=" >> qi::int_ >> '>')[qi::_val = phx::bind((&Sys::Cluster::addEdgeGlobal), qi::_r1, qi::_1, qi::_2)]
|
||||
>> edge_prop[phx::bind(&Injector<Sys>::setEdgeProperties, in, qi::_r1, phx::at_c<0>(qi::_val), qi::_1)]
|
||||
>> *global_edge(qi::_r2)
|
||||
>> ("</Edge>");
|
||||
};
|
||||
|
||||
template<typename Sys>
|
||||
vertex_parser<Sys>::vertex_parser() : vertex_parser<Sys>::base_type(vertex) {
|
||||
|
||||
vertex = qi::lit("<Vertex")[phx::bind(&Injector<Sys>::addVertex, in, qi::_r1, qi::_val)] >> qi::lit("id=")
|
||||
>> qi::int_[phx::at_c<1>(qi::_val) = phx::bind(&Sys::Cluster::setGlobalVertex, qi::_r1, phx::at_c<0>(qi::_val), qi::_1)]
|
||||
>> '>' >> prop[phx::bind(&Injector<Sys>::setVertexProperties, in, qi::_r1, phx::at_c<0>(qi::_val), qi::_1)]
|
||||
>> objects(qi::_r2)[phx::bind(&Injector<Sys>::setVertexObjects, in, qi::_r1, phx::at_c<0>(qi::_val), qi::_1)]
|
||||
>> ("</Vertex>");
|
||||
};
|
||||
|
||||
}//details
|
||||
}//dcm
|
||||
|
||||
#endif
|
||||
119
src/Mod/Assembly/App/opendcm/moduleState/extractor.hpp
Normal file
119
src/Mod/Assembly/App/opendcm/moduleState/extractor.hpp
Normal file
@@ -0,0 +1,119 @@
|
||||
/*
|
||||
openDCM, dimensional constraint manager
|
||||
Copyright (C) 2013 Stefan Troeger <stefantroeger@gmx.net>
|
||||
|
||||
This library is free software; you can redistribute it and/or modify
|
||||
it under the terms of the GNU Lesser General Public License as published by
|
||||
the Free Software Foundation; either version 2.1 of the License, or
|
||||
(at your option) any later version.
|
||||
|
||||
This library is distributed in the hope that it will be useful,
|
||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
GNU Lesser General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU Lesser General Public License along
|
||||
with this library; if not, write to the Free Software Foundation, Inc.,
|
||||
51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
*/
|
||||
|
||||
#ifndef DCM_EXTRACTOR_H
|
||||
#define DCM_EXTRACTOR_H
|
||||
|
||||
#include "defines.hpp"
|
||||
#include <opendcm/core/clustergraph.hpp>
|
||||
#include <boost/fusion/include/at_c.hpp>
|
||||
|
||||
namespace fusion = boost::fusion;
|
||||
|
||||
namespace dcm {
|
||||
|
||||
typedef std::ostream_iterator<char> Iterator;
|
||||
|
||||
template<typename Sys>
|
||||
struct Extractor {
|
||||
|
||||
typedef typename boost::graph_traits<typename Sys::Cluster>::vertex_iterator viter;
|
||||
typedef typename boost::graph_traits<typename Sys::Cluster>::edge_iterator eiter;
|
||||
|
||||
void getVertexRange(typename Sys::Cluster& cluster, std::vector<typename Sys::Cluster::vertex_bundle>& range) {
|
||||
std::pair<viter, viter> res = boost::vertices(cluster);
|
||||
for(; res.first != res.second; res.first++)
|
||||
range.push_back(cluster[*res.first]);
|
||||
};
|
||||
void getEdgeRange(typename Sys::Cluster& cluster,
|
||||
std::vector<fusion::vector3<typename Sys::Cluster::edge_bundle, GlobalVertex, GlobalVertex> >& range) {
|
||||
|
||||
std::pair<eiter, eiter> res = boost::edges(cluster);
|
||||
for(; res.first != res.second; res.first++)
|
||||
range.push_back(fusion::make_vector(cluster[*res.first],
|
||||
cluster.getGlobalVertex(boost::source(*res.first, cluster)),
|
||||
cluster.getGlobalVertex(boost::target(*res.first, cluster))));
|
||||
|
||||
};
|
||||
void getGlobalEdgeSource(typename Sys::Cluster::edge_bundle_single b, int& source) {
|
||||
source = fusion::at_c<1>(b).source;
|
||||
};
|
||||
void getGlobalEdgeTarget(typename Sys::Cluster::edge_bundle_single b, int& target) {
|
||||
target = fusion::at_c<1>(b).target;
|
||||
};
|
||||
void getGlobalEdgeID(typename Sys::Cluster::edge_bundle_single b, int& id) {
|
||||
id = fusion::at_c<1>(b).ID;
|
||||
};
|
||||
void setVertexID(typename Sys::Cluster* cluster, LocalVertex v, long& l) {
|
||||
if(v)
|
||||
l = cluster->getGlobalVertex(v);
|
||||
else
|
||||
l = 0;
|
||||
};
|
||||
void getClusterRange(typename Sys::Cluster& cluster, std::vector<std::pair<GlobalVertex, typename Sys::Cluster*> >& range) {
|
||||
|
||||
typedef typename Sys::Cluster::const_cluster_iterator iter;
|
||||
|
||||
for(iter it = cluster.m_clusters.begin(); it != cluster.m_clusters.end(); it++) {
|
||||
range.push_back( std::make_pair( cluster.getGlobalVertex((*it).first), (*it).second.get() ));
|
||||
};
|
||||
};
|
||||
};
|
||||
|
||||
template<typename Sys>
|
||||
struct Injector {
|
||||
|
||||
void setClusterProperties(typename Sys::Cluster* cluster,
|
||||
typename details::pts<typename Sys::Cluster::cluster_properties>::type& prop) {
|
||||
cluster->m_cluster_bundle = prop;
|
||||
};
|
||||
void setVertexProperties(typename Sys::Cluster* cluster, LocalVertex v,
|
||||
typename details::pts<typename Sys::vertex_properties>::type& prop) {
|
||||
fusion::at_c<1>(cluster->operator[](v)) = prop;
|
||||
};
|
||||
void setVertexObjects(typename Sys::Cluster* cluster, LocalVertex v,
|
||||
typename details::sps<typename Sys::objects>::type& obj) {
|
||||
fusion::at_c<2>(cluster->operator[](v)) = obj;
|
||||
};
|
||||
|
||||
void setEdgeProperties(typename Sys::Cluster* cluster, LocalEdge e,
|
||||
typename details::pts<typename Sys::edge_properties>::type& prop) {
|
||||
fusion::at_c<0>(cluster->operator[](e)) = prop;
|
||||
};
|
||||
void setVertexProperty(typename Sys::Cluster* cluster, int value) {
|
||||
cluster->template setClusterProperty<details::cluster_vertex_prop>(value);
|
||||
};
|
||||
void addCluster(typename Sys::Cluster* cluster, typename Sys::Cluster* addcl) {
|
||||
LocalVertex v = cluster->getLocalVertex(addcl->template getClusterProperty<details::cluster_vertex_prop>()).first;
|
||||
cluster->m_clusters[v] = boost::shared_ptr<typename Sys::Cluster>(addcl);
|
||||
};
|
||||
void addVertex(typename Sys::Cluster* cluster, fusion::vector<LocalVertex, GlobalVertex>& vec) {
|
||||
vec = cluster->addVertex();
|
||||
};
|
||||
};
|
||||
|
||||
|
||||
|
||||
}//namespace dcm
|
||||
|
||||
#endif //DCM_GENERATOR_H
|
||||
|
||||
|
||||
|
||||
|
||||
82
src/Mod/Assembly/App/opendcm/moduleState/generator.hpp
Normal file
82
src/Mod/Assembly/App/opendcm/moduleState/generator.hpp
Normal file
@@ -0,0 +1,82 @@
|
||||
/*
|
||||
openDCM, dimensional constraint manager
|
||||
Copyright (C) 2013 Stefan Troeger <stefantroeger@gmx.net>
|
||||
|
||||
This library is free software; you can redistribute it and/or modify
|
||||
it under the terms of the GNU Lesser General Public License as published by
|
||||
the Free Software Foundation; either version 2.1 of the License, or
|
||||
(at your option) any later version.
|
||||
|
||||
This library is distributed in the hope that it will be useful,
|
||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
GNU Lesser General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU Lesser General Public License along
|
||||
with this library; if not, write to the Free Software Foundation, Inc.,
|
||||
51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
*/
|
||||
|
||||
#ifndef DCM_GENERATOR_H
|
||||
#define DCM_GENERATOR_H
|
||||
|
||||
#include "property_generator.hpp"
|
||||
#include "edge_vertex_generator.hpp"
|
||||
#include "extractor.hpp"
|
||||
|
||||
#include <opendcm/core/clustergraph.hpp>
|
||||
|
||||
#include "traits.hpp"
|
||||
#include "traits_impl.hpp"
|
||||
#include "indent.hpp"
|
||||
|
||||
#include <boost/mpl/int.hpp>
|
||||
#include <boost/mpl/for_each.hpp>
|
||||
#include <boost/fusion/container/vector/convert.hpp>
|
||||
#include <boost/fusion/include/as_vector.hpp>
|
||||
#include <boost/fusion/include/at.hpp>
|
||||
#include <boost/fusion/include/at_c.hpp>
|
||||
|
||||
#include <boost/spirit/include/karma.hpp>
|
||||
#include <boost/spirit/include/phoenix.hpp>
|
||||
|
||||
namespace karma = boost::spirit::karma;
|
||||
namespace phx = boost::phoenix;
|
||||
namespace fusion = boost::fusion;
|
||||
|
||||
namespace dcm {
|
||||
|
||||
typedef std::ostream_iterator<char> Iterator;
|
||||
|
||||
template<typename Sys>
|
||||
struct generator : karma::grammar<Iterator, typename Sys::Cluster& ()> {
|
||||
|
||||
typedef typename Sys::Cluster graph;
|
||||
typedef typename graph::cluster_bundle graph_bundle;
|
||||
typedef typename boost::graph_traits<graph>::vertex_iterator viter;
|
||||
typedef typename boost::graph_traits<graph>::edge_iterator eiter;
|
||||
|
||||
generator();
|
||||
|
||||
karma::rule<Iterator, graph& ()> start;
|
||||
|
||||
karma::rule<Iterator, std::pair<GlobalVertex, graph*>()> cluster_pair;
|
||||
karma::rule<Iterator, graph&()> cluster;
|
||||
details::cluster_prop_gen<Sys> cluster_prop;
|
||||
|
||||
details::vertex_generator<Sys> vertex_range;
|
||||
details::edge_generator<Sys> edge_range;
|
||||
|
||||
Extractor<Sys> ex;
|
||||
};
|
||||
|
||||
}//namespace dcm
|
||||
|
||||
#ifndef USE_EXTERNAL
|
||||
#include "generator_imp.hpp"
|
||||
#endif
|
||||
|
||||
#endif //DCM_GENERATOR_H
|
||||
|
||||
|
||||
|
||||
72
src/Mod/Assembly/App/opendcm/moduleState/generator_imp.hpp
Normal file
72
src/Mod/Assembly/App/opendcm/moduleState/generator_imp.hpp
Normal file
@@ -0,0 +1,72 @@
|
||||
/*
|
||||
openDCM, dimensional constraint manager
|
||||
Copyright (C) 2013 Stefan Troeger <stefantroeger@gmx.net>
|
||||
|
||||
This library is free software; you can redistribute it and/or modify
|
||||
it under the terms of the GNU Lesser General Public License as published by
|
||||
the Free Software Foundation; either version 2.1 of the License, or
|
||||
(at your option) any later version.
|
||||
|
||||
This library is distributed in the hope that it will be useful,
|
||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
GNU Lesser General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU Lesser General Public License along
|
||||
with this library; if not, write to the Free Software Foundation, Inc.,
|
||||
51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
*/
|
||||
|
||||
#ifndef DCM_GENERATOR_IMP_H
|
||||
#define DCM_GENERATOR_IMP_H
|
||||
|
||||
#include "generator.hpp"
|
||||
#include "opendcm/core/clustergraph.hpp"
|
||||
//#include "karma_trans.hpp"
|
||||
|
||||
#include <boost/fusion/include/std_pair.hpp>
|
||||
#include <boost/fusion/adapted/struct/adapt_struct.hpp>
|
||||
#include <boost/fusion/include/adapt_struct.hpp>
|
||||
|
||||
|
||||
BOOST_FUSION_ADAPT_TPL_STRUCT(
|
||||
(T1)(T2)(T3)(T4),
|
||||
(dcm::ClusterGraph) (T1)(T2)(T3)(T4),
|
||||
(int, test)
|
||||
(typename dcm::details::pts<T3>::type, m_cluster_bundle))
|
||||
|
||||
|
||||
namespace boost { namespace spirit { namespace traits
|
||||
{
|
||||
template <typename T1, typename T2, typename T3, typename T4>
|
||||
struct transform_attribute<dcm::ClusterGraph<T1,T2,T3,T4>* const, dcm::ClusterGraph<T1,T2,T3,T4>&, karma::domain>
|
||||
{
|
||||
typedef dcm::ClusterGraph<T1,T2,T3,T4>& type;
|
||||
static type pre(dcm::ClusterGraph<T1,T2,T3,T4>* const& val) {
|
||||
return *val;
|
||||
}
|
||||
};
|
||||
}}}
|
||||
|
||||
namespace dcm {
|
||||
|
||||
template<typename Sys>
|
||||
generator<Sys>::generator() : generator<Sys>::base_type(start) {
|
||||
|
||||
cluster %= karma::omit[karma::int_] << cluster_prop << -vertex_range[phx::bind(&Extractor<Sys>::getVertexRange, ex, karma::_val, karma::_1)]
|
||||
<< -karma::buffer["\n" << edge_range[phx::bind(&Extractor<Sys>::getEdgeRange, ex, karma::_val, karma::_1)]]
|
||||
<< -karma::buffer["\n" << (cluster_pair % karma::eol)[phx::bind(&Extractor<Sys>::getClusterRange, ex, karma::_val, karma::_1)]] << "-\n"
|
||||
<< "</Cluster>";
|
||||
|
||||
cluster_pair %= karma::lit("<Cluster id=") << karma::int_ << ">+"
|
||||
<< karma::attr_cast<graph*,graph&>(cluster);
|
||||
|
||||
start %= karma::lit("<Cluster id=0>+") << cluster;
|
||||
};
|
||||
|
||||
}//namespace dcm
|
||||
|
||||
#endif //DCM_GENERATOR_H
|
||||
|
||||
|
||||
|
||||
63
src/Mod/Assembly/App/opendcm/moduleState/indent.hpp
Normal file
63
src/Mod/Assembly/App/opendcm/moduleState/indent.hpp
Normal file
@@ -0,0 +1,63 @@
|
||||
/*
|
||||
openDCM, dimensional constraint manager
|
||||
Copyright (C) 2013 Stefan Troeger <stefantroeger@gmx.net>
|
||||
|
||||
This library is free software; you can redistribute it and/or modify
|
||||
it under the terms of the GNU Lesser General Public License as published by
|
||||
the Free Software Foundation; either version 2.1 of the License, or
|
||||
(at your option) any later version.
|
||||
|
||||
This library is distributed in the hope that it will be useful,
|
||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
GNU Lesser General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU Lesser General Public License along
|
||||
with this library; if not, write to the Free Software Foundation, Inc.,
|
||||
51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
*/
|
||||
|
||||
#ifndef DCM_INDENT_H
|
||||
#define DCM_INDENT_H
|
||||
|
||||
#include <boost/iostreams/concepts.hpp>
|
||||
#include <boost/iostreams/operations.hpp>
|
||||
#include <boost/iostreams/filtering_stream.hpp>
|
||||
|
||||
class indent_filter : public boost::iostreams::output_filter {
|
||||
public:
|
||||
explicit indent_filter() : indent(0) {};
|
||||
|
||||
template<typename Sink>
|
||||
bool put(Sink& dest, int c) {
|
||||
|
||||
if(c == '+') {
|
||||
indent++;
|
||||
return true;
|
||||
} else if(c == '-') {
|
||||
indent--;
|
||||
return true;
|
||||
} else if(c == '\n') {
|
||||
bool ret = boost::iostreams::put(dest, c);
|
||||
for(int i=0; (i<indent) && ret; i++) {
|
||||
ret = boost::iostreams::put(dest, ' ');
|
||||
ret = boost::iostreams::put(dest, ' ');
|
||||
}
|
||||
|
||||
return ret;
|
||||
};
|
||||
|
||||
indent = (indent < 0) ? 0 : indent;
|
||||
|
||||
return boost::iostreams::put(dest, c);
|
||||
}
|
||||
|
||||
template<typename Source>
|
||||
void close(Source&) {
|
||||
indent = 0;
|
||||
}
|
||||
private:
|
||||
int indent;
|
||||
};
|
||||
|
||||
#endif //DCM_INDENT_H
|
||||
155
src/Mod/Assembly/App/opendcm/moduleState/karma_trans.hpp
Normal file
155
src/Mod/Assembly/App/opendcm/moduleState/karma_trans.hpp
Normal file
@@ -0,0 +1,155 @@
|
||||
/*//////////////////////////////////////////////////////////////////////////////
|
||||
Copyright (c) 2011 Jamboree
|
||||
|
||||
Distributed under the Boost Software License, Version 1.0. (See accompanying
|
||||
file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
|
||||
//////////////////////////////////////////////////////////////////////////////*/
|
||||
#ifndef BOOST_SPIRIT_REPOSITORY_KARMA_TRANS
|
||||
#define BOOST_SPIRIT_REPOSITORY_KARMA_TRANS
|
||||
|
||||
|
||||
#if defined(_MSC_VER)
|
||||
#pragma once
|
||||
#endif
|
||||
|
||||
#include <boost/spirit/home/karma/meta_compiler.hpp>
|
||||
#include <boost/spirit/home/karma/generator.hpp>
|
||||
#include <boost/spirit/home/karma/domain.hpp>
|
||||
#include <boost/spirit/home/support/unused.hpp>
|
||||
#include <boost/spirit/home/support/info.hpp>
|
||||
#include <boost/spirit/home/support/has_semantic_action.hpp>
|
||||
#include <boost/spirit/home/support/handles_container.hpp>
|
||||
#include <boost/spirit/home/karma/detail/attributes.hpp>
|
||||
|
||||
#include <boost/mpl/eval_if.hpp>
|
||||
#include <boost/mpl/identity.hpp>
|
||||
#include <boost/type_traits/is_same.hpp>
|
||||
|
||||
|
||||
namespace boost { namespace spirit { namespace repository
|
||||
{
|
||||
namespace tag
|
||||
{
|
||||
struct trans {};
|
||||
}
|
||||
|
||||
namespace karma
|
||||
{
|
||||
// enables trans<T>(f)[...]
|
||||
template <typename T, typename F>
|
||||
inline
|
||||
spirit::stateful_tag_type<F, tag::trans, T> trans(F f)
|
||||
{
|
||||
return spirit::stateful_tag_type<F, tag::trans, T>(f);
|
||||
}
|
||||
|
||||
// enables trans(f)[...]
|
||||
template <typename F>
|
||||
inline
|
||||
spirit::stateful_tag_type<F, tag::trans> trans(F f)
|
||||
{
|
||||
return spirit::stateful_tag_type<F, tag::trans>(f);
|
||||
}
|
||||
}
|
||||
}}}
|
||||
|
||||
|
||||
namespace boost { namespace spirit
|
||||
{
|
||||
///////////////////////////////////////////////////////////////////////////
|
||||
// Enablers
|
||||
///////////////////////////////////////////////////////////////////////////
|
||||
// enables trans<T>(f)[...]
|
||||
template <typename F, typename T>
|
||||
struct use_directive<karma::domain, tag::stateful_tag<F, repository::tag::trans, T> >
|
||||
: mpl::true_ {};
|
||||
}} // namespace boost::spirit
|
||||
|
||||
|
||||
namespace boost { namespace spirit { namespace repository {namespace karma
|
||||
{
|
||||
template <typename Subject, typename T, typename F>
|
||||
struct trans_directive
|
||||
: spirit::karma::unary_generator<trans_directive<Subject, T, F> >
|
||||
{
|
||||
typedef Subject subject_type;
|
||||
|
||||
template <typename Context, typename Iterator>
|
||||
struct attribute
|
||||
: mpl::eval_if
|
||||
<
|
||||
is_same<T, unused_type>
|
||||
, traits::attribute_of<subject_type, Context, Iterator>
|
||||
, mpl::identity<T>
|
||||
>
|
||||
{};
|
||||
|
||||
trans_directive(Subject const& subject, F f)
|
||||
: subject(subject), f(f)
|
||||
{}
|
||||
|
||||
template
|
||||
<
|
||||
typename OutputIterator, typename Context
|
||||
, typename Delimiter, typename Attribute
|
||||
>
|
||||
bool generate
|
||||
(
|
||||
OutputIterator& sink, Context& ctx, Delimiter const& d
|
||||
, Attribute const& attr) const
|
||||
{
|
||||
return subject.generate(sink, ctx, d, f(attr));
|
||||
}
|
||||
|
||||
template <typename Context>
|
||||
info what(Context& context) const
|
||||
{
|
||||
return info("trans", subject.what(context));
|
||||
}
|
||||
|
||||
Subject subject;
|
||||
F f;
|
||||
};
|
||||
}}}} // namespace boost::spirit::repository::karma
|
||||
|
||||
|
||||
namespace boost { namespace spirit { namespace karma
|
||||
{
|
||||
///////////////////////////////////////////////////////////////////////////
|
||||
// Generator generators: make_xxx function (objects)
|
||||
///////////////////////////////////////////////////////////////////////////
|
||||
template <typename F, typename T, typename Subject, typename Modifiers>
|
||||
struct make_directive<tag::stateful_tag<F, repository::tag::trans, T>, Subject, Modifiers>
|
||||
{
|
||||
typedef repository::karma::trans_directive<Subject, T, F> result_type;
|
||||
|
||||
template <typename StatefulTag>
|
||||
result_type operator()(
|
||||
StatefulTag const& tag, Subject const& subject, unused_type) const
|
||||
{
|
||||
return result_type(subject, tag.data_);
|
||||
}
|
||||
};
|
||||
}}} // namespace boost::spirit::karma
|
||||
|
||||
|
||||
namespace boost { namespace spirit { namespace traits
|
||||
{
|
||||
///////////////////////////////////////////////////////////////////////////
|
||||
template <typename Subject, typename T, typename F>
|
||||
struct has_semantic_action<repository::karma::trans_directive<Subject, T, F> >
|
||||
: unary_has_semantic_action<Subject> {};
|
||||
|
||||
///////////////////////////////////////////////////////////////////////////
|
||||
template <typename Subject, typename T, typename F
|
||||
, typename Attribute, typename Context, typename Iterator>
|
||||
struct handles_container
|
||||
<
|
||||
repository::karma::trans_directive<Subject, T, F>
|
||||
, Attribute, Context, Iterator
|
||||
>
|
||||
: mpl::false_ {}; // FIXME
|
||||
}}} // namespace boost::spirit::traits
|
||||
|
||||
|
||||
#endif
|
||||
98
src/Mod/Assembly/App/opendcm/moduleState/module.hpp
Normal file
98
src/Mod/Assembly/App/opendcm/moduleState/module.hpp
Normal file
@@ -0,0 +1,98 @@
|
||||
/*
|
||||
openDCM, dimensional constraint manager
|
||||
Copyright (C) 2013 Stefan Troeger <stefantroeger@gmx.net>
|
||||
|
||||
This library is free software; you can redistribute it and/or modify
|
||||
it under the terms of the GNU Lesser General Public License as published by
|
||||
the Free Software Foundation; either version 2.1 of the License, or
|
||||
(at your option) any later version.
|
||||
|
||||
This library is distributed in the hope that it will be useful,
|
||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
GNU Lesser General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU Lesser General Public License along
|
||||
with this library; if not, write to the Free Software Foundation, Inc.,
|
||||
51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
*/
|
||||
|
||||
#ifndef DCM_MODULE_STATE_H
|
||||
#define DCM_MODULE_STATE_H
|
||||
|
||||
#include <iosfwd>
|
||||
|
||||
#include "indent.hpp"
|
||||
#include "generator.hpp"
|
||||
#include "parser.hpp"
|
||||
#include "defines.hpp"
|
||||
|
||||
#include <boost/spirit/include/qi.hpp>
|
||||
#include <boost/spirit/include/support_istream_iterator.hpp>
|
||||
|
||||
namespace qi = boost::spirit::qi;
|
||||
|
||||
namespace dcm {
|
||||
|
||||
struct ModuleState {
|
||||
|
||||
template<typename Sys>
|
||||
struct type {
|
||||
|
||||
typedef Unspecified_Identifier Identifier;
|
||||
|
||||
struct inheriter {
|
||||
|
||||
inheriter() {
|
||||
m_this = (Sys*) this;
|
||||
};
|
||||
|
||||
Sys* m_this;
|
||||
|
||||
void saveState(std::ostream& stream) {
|
||||
|
||||
boost::iostreams::filtering_ostream indent_stream;
|
||||
indent_stream.push(indent_filter());
|
||||
indent_stream.push(stream);
|
||||
|
||||
std::ostream_iterator<char> out(indent_stream);
|
||||
generator<Sys> gen;
|
||||
|
||||
karma::generate(out, gen, *m_this->m_cluster);
|
||||
};
|
||||
|
||||
void loadState(std::istream& stream) {
|
||||
|
||||
//disable skipping of whitespace
|
||||
stream.unsetf(std::ios::skipws);
|
||||
|
||||
// wrap istream into iterator
|
||||
boost::spirit::istream_iterator begin(stream);
|
||||
boost::spirit::istream_iterator end;
|
||||
|
||||
// use iterator to parse file data
|
||||
parser<Sys> par;
|
||||
m_this->clear();
|
||||
typename Sys::Cluster* cl_ptr = m_this->m_cluster.get();
|
||||
qi::phrase_parse(begin, end, par(m_this), qi::space, cl_ptr);
|
||||
};
|
||||
};
|
||||
|
||||
|
||||
//add only a property to the cluster as we need it to store the clusers global vertex
|
||||
typedef mpl::vector1<details::cluster_vertex_prop> properties;
|
||||
typedef mpl::vector0<> objects;
|
||||
|
||||
//nothing to do on startup
|
||||
static void system_init(Sys& sys) {};
|
||||
};
|
||||
};
|
||||
|
||||
}
|
||||
|
||||
#endif //DCM_MODULE_STATE_H
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
@@ -0,0 +1,72 @@
|
||||
#ifndef DCM_OBJECT_GENERATOR_H
|
||||
#define DCM_OBJECT_GENERATOR_H
|
||||
|
||||
#include "property_generator.hpp"
|
||||
|
||||
namespace fusion = boost::fusion;
|
||||
|
||||
namespace dcm {
|
||||
|
||||
typedef std::ostream_iterator<char> Iterator;
|
||||
|
||||
|
||||
namespace details {
|
||||
|
||||
//grammar for a single object
|
||||
template<typename Sys, typename Object, typename Gen>
|
||||
struct obj_grammar : public karma::grammar<Iterator, boost::shared_ptr<Object>()> {
|
||||
typename Gen::generator subrule;
|
||||
karma::rule<Iterator, boost::shared_ptr<Object>()> start;
|
||||
details::prop_gen<Sys, typename Object::Sequence > prop;
|
||||
|
||||
obj_grammar();
|
||||
static void getProperties(boost::shared_ptr<Object> ptr, typename details::pts<typename Object::Sequence>::type& seq);
|
||||
};
|
||||
|
||||
//when objects should not be generated we need to get a empy rule, as obj_rule_init
|
||||
//trys always to access the rules attribute and when the parser_generator trait is not
|
||||
//specialitzed it's impossible to have the attribute type right in the unspecialized trait
|
||||
template<typename Sys, typename seq, typename state>
|
||||
struct obj_generator_fold : mpl::fold< seq, state,
|
||||
mpl::if_< parser_generate<mpl::_2, Sys>,
|
||||
mpl::push_back<mpl::_1,
|
||||
obj_grammar<Sys, mpl::_2, dcm::parser_generator<mpl::_2, Sys, Iterator> > >,
|
||||
mpl::push_back<mpl::_1, details::empty_grammar > > > {};
|
||||
|
||||
//currently max. 10 objects are supported
|
||||
template<typename Sys>
|
||||
struct obj_gen : public karma::grammar<Iterator, typename details::sps<typename Sys::objects>::type()> {
|
||||
|
||||
typedef typename Sys::objects ObjectList;
|
||||
|
||||
//create a vector with the appropriate rules for all objects. Do this with the rule init struct, as it gives
|
||||
//automatic initialisation of the rules when the objects are created
|
||||
typedef typename obj_generator_fold<Sys, ObjectList,mpl::vector<> >::type init_rules_vector;
|
||||
//push back a empty rule so that we know where to go when nothing is to do
|
||||
typedef typename mpl::push_back<init_rules_vector, empty_grammar >::type rules_vector;
|
||||
|
||||
//create the fusion sequence of our rules
|
||||
typedef typename fusion::result_of::as_vector<rules_vector>::type rules_sequnce;
|
||||
|
||||
//this struct returns the right accessvalue for the sequences. If we access a value bigger than the property vector size
|
||||
//we use the last rule, as we made sure this is an empty one
|
||||
template<int I>
|
||||
struct index : public mpl::if_< mpl::less<mpl::int_<I>, mpl::size<ObjectList> >,
|
||||
mpl::int_<I>, typename mpl::size<ObjectList>::prior >::type {};
|
||||
//this struct tells us if we should execute the generator
|
||||
template<int I>
|
||||
struct valid : public mpl::less< mpl::int_<I>, mpl::size<ObjectList> > {};
|
||||
|
||||
rules_sequnce rules;
|
||||
karma::rule<Iterator, typename details::sps<ObjectList>::type()> obj;
|
||||
|
||||
obj_gen();
|
||||
};
|
||||
} //namespace details
|
||||
}//dcm
|
||||
|
||||
#ifndef USE_EXTERNAL
|
||||
#include "object_generator_imp.hpp"
|
||||
#endif
|
||||
|
||||
#endif //DCM_OBJECT_GENERATOR_H
|
||||
@@ -0,0 +1,57 @@
|
||||
#ifndef DCM_OBJECT_GENERATOR_IMP_H
|
||||
#define DCM_OBJECT_GENERATOR_IMP_H
|
||||
|
||||
|
||||
#include "traits_impl.hpp"
|
||||
#include "object_generator.hpp"
|
||||
#include "property_generator_imp.hpp"
|
||||
|
||||
using namespace boost::spirit::karma;
|
||||
namespace karma = boost::spirit::karma;
|
||||
namespace phx = boost::phoenix;
|
||||
namespace fusion = boost::fusion;
|
||||
|
||||
namespace dcm {
|
||||
|
||||
typedef std::ostream_iterator<char> Iterator;
|
||||
|
||||
|
||||
namespace details {
|
||||
|
||||
template<typename Sys, typename Object, typename Gen>
|
||||
obj_grammar<Sys, Object,Gen>::obj_grammar() : obj_grammar<Sys, Object,Gen>::base_type(start) {
|
||||
Gen::init(subrule);
|
||||
start = lit("\n<Object>") << '+' << eol << subrule
|
||||
<< prop[phx::bind(&obj_grammar::getProperties, _val, karma::_1)]
|
||||
<< '-' << eol << lit("</Object>");
|
||||
};
|
||||
|
||||
template<typename Sys, typename Object, typename Gen>
|
||||
void obj_grammar<Sys, Object,Gen>::getProperties(boost::shared_ptr<Object> ptr, typename details::pts<typename Object::Sequence>::type& seq) {
|
||||
|
||||
if(ptr) seq = ptr->m_properties;
|
||||
else {
|
||||
//TODO: throw
|
||||
};
|
||||
};
|
||||
|
||||
template<typename Sys>
|
||||
obj_gen<Sys>::obj_gen() : obj_gen<Sys>::base_type(obj) {
|
||||
|
||||
obj = -(eps(valid<0>::value) << eps(phx::at_c<index<0>::value>(_val)) << fusion::at<index<0> >(rules)[karma::_1 = phx::at_c<index<0>::value>(_val)])
|
||||
<< -(eps(valid<1>::value) << eps(phx::at_c<index<1>::value>(_val)) << fusion::at<index<1> >(rules)[karma::_1 = phx::at_c<index<1>::value>(_val)])
|
||||
<< -(eps(valid<2>::value) << eps(phx::at_c<index<2>::value>(_val)) << fusion::at<index<2> >(rules)[karma::_1 = phx::at_c<index<2>::value>(_val)])
|
||||
<< -(eps(valid<3>::value) << eps(phx::at_c<index<3>::value>(_val)) << fusion::at<index<3> >(rules)[karma::_1 = phx::at_c<index<3>::value>(_val)])
|
||||
<< -(eps(valid<4>::value) << eps(phx::at_c<index<4>::value>(_val)) << fusion::at<index<4> >(rules)[karma::_1 = phx::at_c<index<4>::value>(_val)])
|
||||
<< -(eps(valid<5>::value) << eps(phx::at_c<index<5>::value>(_val)) << fusion::at<index<5> >(rules)[karma::_1 = phx::at_c<index<5>::value>(_val)])
|
||||
<< -(eps(valid<6>::value) << eps(phx::at_c<index<6>::value>(_val)) << fusion::at<index<6> >(rules)[karma::_1 = phx::at_c<index<6>::value>(_val)])
|
||||
<< -(eps(valid<7>::value) << eps(phx::at_c<index<7>::value>(_val)) << fusion::at<index<7> >(rules)[karma::_1 = phx::at_c<index<7>::value>(_val)])
|
||||
<< -(eps(valid<8>::value) << eps(phx::at_c<index<8>::value>(_val)) << fusion::at<index<8> >(rules)[karma::_1 = phx::at_c<index<8>::value>(_val)])
|
||||
<< -(eps(valid<9>::value) << eps(phx::at_c<index<9>::value>(_val)) << fusion::at<index<9> >(rules)[karma::_1 = phx::at_c<index<9>::value>(_val)]);
|
||||
|
||||
};
|
||||
|
||||
} //namespace details
|
||||
}//dcm
|
||||
|
||||
#endif //DCM_OBJECT_GENERATOR_H
|
||||
98
src/Mod/Assembly/App/opendcm/moduleState/object_parser.hpp
Normal file
98
src/Mod/Assembly/App/opendcm/moduleState/object_parser.hpp
Normal file
@@ -0,0 +1,98 @@
|
||||
/*
|
||||
openDCM, dimensional constraint manager
|
||||
Copyright (C) 2013 Stefan Troeger <stefantroeger@gmx.net>
|
||||
|
||||
This library is free software; you can redistribute it and/or modify
|
||||
it under the terms of the GNU Lesser General Public License as published by
|
||||
the Free Software Foundation; either version 2.1 of the License, or
|
||||
(at your option) any later version.
|
||||
|
||||
This library is distributed in the hope that it will be useful,
|
||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
GNU Lesser General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU Lesser General Public License along
|
||||
with this library; if not, write to the Free Software Foundation, Inc.,
|
||||
51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
*/
|
||||
|
||||
#ifndef DCM_OBJECT_PARSER_H
|
||||
#define DCM_OBJECT_PARSER_H
|
||||
|
||||
#include "property_parser.hpp"
|
||||
|
||||
namespace dcm {
|
||||
namespace details {
|
||||
|
||||
template<typename Obj, typename Sys>
|
||||
struct empty_obj_parser : public qi::grammar<IIterator, boost::shared_ptr<Obj>(Sys*), qi::space_type> {
|
||||
qi::rule<IIterator, boost::shared_ptr<Obj>(Sys*), qi::space_type> start;
|
||||
empty_obj_parser(): empty_obj_parser::base_type(start) {
|
||||
//start = qi::eps(false);
|
||||
};
|
||||
};
|
||||
|
||||
//grammar for a single object
|
||||
template<typename Sys, typename Object, typename Par>
|
||||
struct obj_parser : public qi::grammar<IIterator, boost::shared_ptr<Object>(Sys*), qi::space_type> {
|
||||
typename Par::parser subrule;
|
||||
qi::rule<IIterator, boost::shared_ptr<Object>(Sys*), qi::space_type> start;
|
||||
prop_par<Sys, typename Object::Sequence > prop;
|
||||
|
||||
obj_parser();
|
||||
|
||||
static void setProperties(boost::shared_ptr<Object> ptr, typename details::pts<typename Object::Sequence>::type& seq);
|
||||
};
|
||||
|
||||
//when objects should not be generated we need to get a empy rule, as obj_rule_init
|
||||
//trys always to access the rules attribute and when the parser_generator trait is not
|
||||
//specialitzed it's impossible to have the attribute type right in the unspecialized trait
|
||||
template<typename Sys, typename seq, typename state>
|
||||
struct obj_parser_fold : mpl::fold< seq, state,
|
||||
mpl::if_< parser_parse<mpl::_2, Sys>,
|
||||
mpl::push_back<mpl::_1,
|
||||
obj_parser<Sys, mpl::_2, dcm::parser_parser<mpl::_2, Sys, IIterator> > >,
|
||||
mpl::push_back<mpl::_1, empty_obj_parser<mpl::_2, Sys> > > > {};
|
||||
|
||||
//currently max. 10 objects are supported
|
||||
template<typename Sys>
|
||||
struct obj_par : public qi::grammar<IIterator,
|
||||
typename details::sps<typename Sys::objects>::type(Sys*),
|
||||
qi::space_type> {
|
||||
|
||||
typedef typename Sys::objects ObjectList;
|
||||
|
||||
//create a vector with the appropriate rules for all objects. Do this with the rule init struct, as it gives
|
||||
//automatic initialisation of the rules when the objects are created
|
||||
typedef typename obj_parser_fold<Sys, ObjectList, mpl::vector<> >::type init_rules_vector;
|
||||
//push back a empty rule so that we know where to go when nothing is to do
|
||||
typedef typename mpl::push_back<init_rules_vector,
|
||||
empty_obj_parser<typename mpl::back<ObjectList>::type, Sys> >::type rules_vector;
|
||||
|
||||
//create the fusion sequence of our rules
|
||||
typedef typename fusion::result_of::as_vector<rules_vector>::type rules_sequnce;
|
||||
|
||||
//this struct returns the right accessvalue for the sequences. If we access a value bigger than the property vector size
|
||||
//we use the last rule, as we made sure this is an empty one
|
||||
template<int I>
|
||||
struct index : public mpl::if_< mpl::less<mpl::int_<I>, mpl::size<ObjectList> >,
|
||||
mpl::int_<I>, typename mpl::size<ObjectList>::prior >::type {};
|
||||
//this struct tells us if we should execute the generator
|
||||
template<int I>
|
||||
struct valid : public mpl::less< mpl::int_<I>, mpl::size<ObjectList> > {};
|
||||
|
||||
rules_sequnce rules;
|
||||
qi::rule<IIterator, typename details::sps<ObjectList>::type(Sys*), qi::space_type> obj;
|
||||
|
||||
obj_par();
|
||||
};
|
||||
|
||||
}//details
|
||||
}//DCM
|
||||
|
||||
#ifndef USE_EXTERNAL
|
||||
#include "property_parser_imp.hpp"
|
||||
#endif
|
||||
|
||||
#endif
|
||||
@@ -0,0 +1,63 @@
|
||||
/*
|
||||
openDCM, dimensional constraint manager
|
||||
Copyright (C) 2013 Stefan Troeger <stefantroeger@gmx.net>
|
||||
|
||||
This library is free software; you can redistribute it and/or modify
|
||||
it under the terms of the GNU Lesser General Public License as published by
|
||||
the Free Software Foundation; either version 2.1 of the License, or
|
||||
(at your option) any later version.
|
||||
|
||||
This library is distributed in the hope that it will be useful,
|
||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
GNU Lesser General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU Lesser General Public License along
|
||||
with this library; if not, write to the Free Software Foundation, Inc.,
|
||||
51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
*/
|
||||
|
||||
#ifndef DCM_OBJECT_PARSER_IMP_H
|
||||
#define DCM_OBJECT_PARSER_IMP_H
|
||||
|
||||
#include "object_parser.hpp"
|
||||
#include "property_parser_imp.hpp"
|
||||
|
||||
namespace dcm {
|
||||
namespace details {
|
||||
|
||||
template<typename Sys, typename Object, typename Par>
|
||||
obj_parser<Sys, Object, Par>::obj_parser(): obj_parser::base_type(start) {
|
||||
Par::init(subrule);
|
||||
start = qi::lit("<Object>") >> subrule(qi::_r1)[qi::_val = qi::_1]
|
||||
>> qi::eps(qi::_val)[ phx::bind(&Sys::template push_back<Object>, qi::_r1, qi::_val)]
|
||||
>> prop[phx::bind(&obj_parser::setProperties, qi::_val, qi::_1)]
|
||||
>> qi::lit("</Object>");
|
||||
};
|
||||
|
||||
template<typename Sys, typename Object, typename Par>
|
||||
void obj_parser<Sys, Object, Par>::setProperties(boost::shared_ptr<Object> ptr, typename details::pts<typename Object::Sequence>::type& seq) {
|
||||
if(ptr) ptr->m_properties = seq;
|
||||
};
|
||||
|
||||
template<typename Sys>
|
||||
obj_par<Sys>::obj_par(): obj_par<Sys>::base_type(obj) {
|
||||
|
||||
obj = -(qi::eps(valid<0>::value) >> fusion::at<index<0> >(rules)(qi::_r1)[phx::at_c<index<0>::value>(qi::_val) = qi::_1])
|
||||
>> -(qi::eps(valid<1>::value) >> fusion::at<index<1> >(rules)(qi::_r1)[phx::at_c<index<1>::value>(qi::_val) = qi::_1])
|
||||
>> -(qi::eps(valid<2>::value) >> fusion::at<index<2> >(rules)(qi::_r1)[phx::at_c<index<2>::value>(qi::_val) = qi::_1])
|
||||
>> -(qi::eps(valid<3>::value) >> fusion::at<index<3> >(rules)(qi::_r1)[phx::at_c<index<3>::value>(qi::_val) = qi::_1])
|
||||
>> -(qi::eps(valid<4>::value) >> fusion::at<index<4> >(rules)(qi::_r1)[phx::at_c<index<4>::value>(qi::_val) = qi::_1])
|
||||
>> -(qi::eps(valid<5>::value) >> fusion::at<index<5> >(rules)(qi::_r1)[phx::at_c<index<5>::value>(qi::_val) = qi::_1])
|
||||
>> -(qi::eps(valid<6>::value) >> fusion::at<index<6> >(rules)(qi::_r1)[phx::at_c<index<6>::value>(qi::_val) = qi::_1])
|
||||
>> -(qi::eps(valid<7>::value) >> fusion::at<index<7> >(rules)(qi::_r1)[phx::at_c<index<7>::value>(qi::_val) = qi::_1])
|
||||
>> -(qi::eps(valid<8>::value) >> fusion::at<index<8> >(rules)(qi::_r1)[phx::at_c<index<8>::value>(qi::_val) = qi::_1])
|
||||
>> -(qi::eps(valid<9>::value) >> fusion::at<index<9> >(rules)(qi::_r1)[phx::at_c<index<9>::value>(qi::_val) = qi::_1]);
|
||||
|
||||
};
|
||||
|
||||
}//details
|
||||
}//DCM
|
||||
|
||||
|
||||
#endif
|
||||
82
src/Mod/Assembly/App/opendcm/moduleState/parser.hpp
Normal file
82
src/Mod/Assembly/App/opendcm/moduleState/parser.hpp
Normal file
@@ -0,0 +1,82 @@
|
||||
/*
|
||||
openDCM, dimensional constraint manager
|
||||
Copyright (C) 2013 Stefan Troeger <stefantroeger@gmx.net>
|
||||
|
||||
This library is free software; you can redistribute it and/or modify
|
||||
it under the terms of the GNU Lesser General Public License as published by
|
||||
the Free Software Foundation; either version 2.1 of the License, or
|
||||
(at your option) any later version.
|
||||
|
||||
This library is distributed in the hope that it will be useful,
|
||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
GNU Lesser General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU Lesser General Public License along
|
||||
with this library; if not, write to the Free Software Foundation, Inc.,
|
||||
51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
*/
|
||||
|
||||
#ifndef DCM_PARSER_H
|
||||
#define DCM_PARSER_H
|
||||
|
||||
#include <iosfwd>
|
||||
|
||||
#include <boost/spirit/include/qi.hpp>
|
||||
#include <boost/spirit/include/support_istream_iterator.hpp>
|
||||
#include <boost/spirit/include/qi_string.hpp>
|
||||
#include <boost/spirit/include/phoenix.hpp>
|
||||
|
||||
#include "opendcm/core/clustergraph.hpp"
|
||||
|
||||
#include "property_parser.hpp"
|
||||
#include "object_parser.hpp"
|
||||
#include "edge_vertex_parser.hpp"
|
||||
#include "extractor.hpp"
|
||||
|
||||
namespace qi = boost::spirit::qi;
|
||||
namespace ascii = boost::spirit::ascii;
|
||||
namespace phx = boost::phoenix;
|
||||
|
||||
namespace dcm {
|
||||
|
||||
typedef boost::spirit::istream_iterator IIterator;
|
||||
|
||||
struct sp : qi::grammar<IIterator, std::string()> {
|
||||
|
||||
qi::rule<IIterator, std::string()> start;
|
||||
sp() : sp::base_type(start) {
|
||||
start %= +qi::char_;
|
||||
};
|
||||
static void print(std::string s) {
|
||||
std::cout<<"parsed string:"<<std::endl<<s<<std::endl<<"done print string"<<std::endl;
|
||||
};
|
||||
|
||||
};
|
||||
|
||||
template<typename Sys>
|
||||
struct parser : qi::grammar<IIterator, typename Sys::Cluster*(Sys*), qi::locals<int>, qi::space_type> {
|
||||
|
||||
typedef typename Sys::Cluster graph;
|
||||
|
||||
parser();
|
||||
|
||||
qi::rule<IIterator, graph*(Sys*), qi::locals<int>, qi::space_type> cluster;
|
||||
details::cluster_prop_par<Sys> cluster_prop;
|
||||
|
||||
details::obj_par<Sys> objects;
|
||||
|
||||
details::vertex_parser<Sys> vertex;
|
||||
details::edge_parser<Sys> edge;
|
||||
|
||||
sp str;
|
||||
Injector<Sys> in;
|
||||
};
|
||||
|
||||
}
|
||||
|
||||
#ifndef USE_EXTERNAL
|
||||
#include "parser_imp.hpp"
|
||||
#endif
|
||||
|
||||
#endif //DCM_PARSER_H
|
||||
71
src/Mod/Assembly/App/opendcm/moduleState/parser_imp.hpp
Normal file
71
src/Mod/Assembly/App/opendcm/moduleState/parser_imp.hpp
Normal file
@@ -0,0 +1,71 @@
|
||||
/*
|
||||
openDCM, dimensional constraint manager
|
||||
Copyright (C) 2013 Stefan Troeger <stefantroeger@gmx.net>
|
||||
|
||||
This library is free software; you can redistribute it and/or modify
|
||||
it under the terms of the GNU Lesser General Public License as published by
|
||||
the Free Software Foundation; either version 2.1 of the License, or
|
||||
(at your option) any later version.
|
||||
|
||||
This library is distributed in the hope that it will be useful,
|
||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
GNU Lesser General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU Lesser General Public License along
|
||||
with this library; if not, write to the Free Software Foundation, Inc.,
|
||||
51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
*/
|
||||
|
||||
#ifndef DCM_PARSER_IMP_H
|
||||
#define DCM_PARSER_IMP_H
|
||||
|
||||
#include <boost/spirit/include/qi_attr_cast.hpp>
|
||||
|
||||
#include "opendcm/core/system.hpp"
|
||||
|
||||
#include <boost/fusion/include/std_pair.hpp>
|
||||
#include <boost/fusion/adapted/struct/adapt_struct.hpp>
|
||||
#include <boost/fusion/include/adapt_struct.hpp>
|
||||
|
||||
BOOST_FUSION_ADAPT_TPL_STRUCT(
|
||||
(T1)(T2)(T3)(T4),
|
||||
(dcm::ClusterGraph) (T1)(T2)(T3)(T4),
|
||||
(typename dcm::details::pts<T3>::type, m_cluster_bundle))
|
||||
|
||||
#include "parser.hpp"
|
||||
|
||||
|
||||
namespace boost { namespace spirit { namespace traits
|
||||
{
|
||||
template <typename T1, typename T2, typename T3, typename T4>
|
||||
struct transform_attribute<dcm::ClusterGraph<T1,T2,T3,T4>*, dcm::ClusterGraph<T1,T2,T3,T4>, qi::domain>
|
||||
{
|
||||
typedef dcm::ClusterGraph<T1,T2,T3,T4>& type;
|
||||
static type pre(dcm::ClusterGraph<T1,T2,T3,T4>* const& val) {
|
||||
return *val;
|
||||
}
|
||||
static void post(dcm::ClusterGraph<T1,T2,T3,T4>* const& val, dcm::ClusterGraph<T1,T2,T3,T4> const& attr) {}
|
||||
static void fail(dcm::ClusterGraph<T1,T2,T3,T4>* const&) {}
|
||||
};
|
||||
}}}
|
||||
|
||||
namespace dcm {
|
||||
|
||||
typedef boost::spirit::istream_iterator IIterator;
|
||||
|
||||
template<typename Sys>
|
||||
parser<Sys>::parser() : parser<Sys>::base_type(cluster) {
|
||||
|
||||
cluster %= qi::lit("<Cluster id=") >> qi::omit[qi::int_[qi::_a = qi::_1]] >> ">"
|
||||
>> -(qi::eps( qi::_a > 0 )[qi::_val = phx::new_<typename Sys::Cluster>()])
|
||||
>> qi::eps[phx::bind(&Injector<Sys>::setVertexProperty, in, qi::_val, qi::_a)]
|
||||
>> qi::attr_cast<graph*, graph>(cluster_prop >> qi::eps)
|
||||
>> qi::omit[*vertex(qi::_val, qi::_r1)]
|
||||
>> qi::omit[*edge(qi::_val, qi::_r1)]
|
||||
>> qi::omit[*(cluster(qi::_r1)[phx::bind(&Injector<Sys>::addCluster, in, qi::_val, qi::_1)])]
|
||||
>> "</Cluster>";// >> str[&sp::print];
|
||||
};
|
||||
|
||||
}
|
||||
#endif //DCM_PARSER_H
|
||||
102
src/Mod/Assembly/App/opendcm/moduleState/property_generator.hpp
Normal file
102
src/Mod/Assembly/App/opendcm/moduleState/property_generator.hpp
Normal file
@@ -0,0 +1,102 @@
|
||||
#ifndef DCM_PROPERTY_GENERATOR_H
|
||||
#define DCM_PROPERTY_GENERATOR_H
|
||||
|
||||
#include <boost/fusion/include/as_vector.hpp>
|
||||
#include <boost/spirit/include/karma.hpp>
|
||||
|
||||
#include <boost/mpl/range_c.hpp>
|
||||
#include <boost/mpl/fold.hpp>
|
||||
#include <boost/mpl/minus.hpp>
|
||||
#include <boost/mpl/less_equal.hpp>
|
||||
|
||||
#include "traits.hpp"
|
||||
|
||||
namespace karma = boost::spirit::karma;
|
||||
namespace fusion = boost::fusion;
|
||||
namespace mpl = boost::mpl;
|
||||
|
||||
namespace dcm {
|
||||
|
||||
typedef std::ostream_iterator<char> Iterator;
|
||||
|
||||
namespace details {
|
||||
|
||||
//a grammar that does nothing exept failing
|
||||
struct empty_grammar : public karma::grammar<Iterator> {
|
||||
karma::rule<Iterator> start;
|
||||
empty_grammar(): empty_grammar::base_type(start) {
|
||||
start = karma::eps(true);
|
||||
};
|
||||
empty_grammar(const empty_grammar& other) : empty_grammar::base_type(start) {};
|
||||
};
|
||||
|
||||
template<typename Prop>
|
||||
struct skip_grammar : public karma::grammar<Iterator, typename Prop::type&()> {
|
||||
karma::rule<Iterator, typename Prop::type&()> start;
|
||||
skip_grammar() : skip_grammar<Prop>::base_type(start) {
|
||||
start = karma::eps(true);
|
||||
};
|
||||
skip_grammar(const skip_grammar& other) : skip_grammar::base_type(start) {};
|
||||
};
|
||||
|
||||
//grammar for a single property
|
||||
template<typename Prop, typename Gen>
|
||||
struct prop_grammar : public karma::grammar<Iterator, typename Prop::type&()> {
|
||||
typename Gen::generator subrule;
|
||||
karma::rule<Iterator, typename Prop::type&()> start;
|
||||
prop_grammar();
|
||||
prop_grammar(const prop_grammar& other) : prop_grammar::base_type(start) {};
|
||||
};
|
||||
|
||||
template<typename Sys, typename seq, typename state>
|
||||
struct prop_generator_fold : mpl::fold< seq, state,
|
||||
mpl::if_< parser_generate<mpl::_2, Sys>,
|
||||
mpl::push_back<mpl::_1,
|
||||
prop_grammar<mpl::_2, dcm::parser_generator<mpl::_2, Sys, Iterator> > >,
|
||||
mpl::push_back<mpl::_1, skip_grammar<mpl::_2> > > > {};
|
||||
|
||||
//grammar for a fusion sequence of properties. currently max. 10 properties are supported
|
||||
template<typename Sys, typename PropertyList>
|
||||
struct prop_gen : karma::grammar<Iterator, typename details::pts<PropertyList>::type&()> {
|
||||
|
||||
//create a vector with the appropriate rules for all properties.
|
||||
typedef typename prop_generator_fold<Sys, PropertyList, mpl::vector<> >::type init_rules_sequence;
|
||||
//allow max 10 types as the following code expect this
|
||||
BOOST_MPL_ASSERT((mpl::less_equal< mpl::size<init_rules_sequence>, mpl::int_<10> >));
|
||||
//we want to process 10 elements, so create a vector with (10-prop.size()) empty rules
|
||||
//and append it to our rules vector
|
||||
typedef mpl::range_c<int,0, mpl::minus< mpl::int_<10>, mpl::size<init_rules_sequence> >::value > range;
|
||||
typedef typename mpl::fold< range,
|
||||
init_rules_sequence,
|
||||
mpl::push_back<mpl::_1, empty_grammar> >::type rules_sequence;
|
||||
|
||||
typename fusion::result_of::as_vector<rules_sequence>::type rules;
|
||||
karma::rule<Iterator, typename details::pts<PropertyList>::type&()> prop;
|
||||
|
||||
prop_gen();
|
||||
};
|
||||
|
||||
//special prop classes for better externalisaton, therefore the outside constructor to avoid auto inline
|
||||
template<typename Sys>
|
||||
struct cluster_prop_gen : public prop_gen<Sys, typename Sys::Cluster::cluster_properties> {
|
||||
cluster_prop_gen();
|
||||
};
|
||||
|
||||
template<typename Sys>
|
||||
struct vertex_prop_gen : public prop_gen<Sys, typename Sys::Cluster::vertex_properties> {
|
||||
vertex_prop_gen();
|
||||
};
|
||||
|
||||
template<typename Sys>
|
||||
struct edge_prop_gen : public prop_gen<Sys, typename Sys::Cluster::edge_properties> {
|
||||
edge_prop_gen();
|
||||
};
|
||||
|
||||
}//details
|
||||
}//dcm
|
||||
|
||||
#ifndef USE_EXTERNAL
|
||||
#include "property_generator_imp.hpp"
|
||||
#endif
|
||||
|
||||
#endif //DCM_PROPERTY_GENERATOR_H
|
||||
@@ -0,0 +1,43 @@
|
||||
#ifndef DCM_PROPERTY_GENERATOR_IMP_H
|
||||
#define DCM_PROPERTY_GENERATOR_IMP_H
|
||||
|
||||
#include "property_generator.hpp"
|
||||
#include "traits_impl.hpp"
|
||||
|
||||
namespace dcm {
|
||||
|
||||
typedef std::ostream_iterator<char> Iterator;
|
||||
|
||||
namespace details {
|
||||
|
||||
//grammar for a single property
|
||||
template<typename Prop, typename Gen>
|
||||
prop_grammar<Prop, Gen>::prop_grammar() : prop_grammar<Prop, Gen>::base_type(start) {
|
||||
|
||||
Gen::init(subrule);
|
||||
start = karma::lit("\n<Property>") << '+' << karma::eol << subrule
|
||||
<< '-' << karma::eol << karma::lit("</Property>");
|
||||
};
|
||||
|
||||
template<typename Sys, typename PropertyList>
|
||||
prop_gen<Sys, PropertyList>::prop_gen() : prop_gen<Sys, PropertyList>::base_type(prop) {
|
||||
|
||||
prop = fusion::at_c<0>(rules) << fusion::at_c<1>(rules) << fusion::at_c<2>(rules)
|
||||
<< fusion::at_c<3>(rules) << fusion::at_c<4>(rules) << fusion::at_c<5>(rules)
|
||||
<< fusion::at_c<6>(rules) << fusion::at_c<7>(rules) << fusion::at_c<8>(rules)
|
||||
<< fusion::at_c<9>(rules);
|
||||
};
|
||||
|
||||
template<typename Sys>
|
||||
cluster_prop_gen<Sys>::cluster_prop_gen() : prop_gen<Sys, typename Sys::Cluster::cluster_properties>() {};
|
||||
|
||||
template<typename Sys>
|
||||
vertex_prop_gen<Sys>::vertex_prop_gen() : prop_gen<Sys, typename Sys::Cluster::vertex_properties>() {};
|
||||
|
||||
template<typename Sys>
|
||||
edge_prop_gen<Sys>::edge_prop_gen() : prop_gen<Sys, typename Sys::Cluster::edge_properties>() {};
|
||||
|
||||
}//details
|
||||
}//dcm
|
||||
|
||||
#endif //DCM_PROPERTY_GENERATOR_H
|
||||
120
src/Mod/Assembly/App/opendcm/moduleState/property_parser.hpp
Normal file
120
src/Mod/Assembly/App/opendcm/moduleState/property_parser.hpp
Normal file
@@ -0,0 +1,120 @@
|
||||
/*
|
||||
openDCM, dimensional constraint manager
|
||||
Copyright (C) 2013 Stefan Troeger <stefantroeger@gmx.net>
|
||||
|
||||
This library is free software; you can redistribute it and/or modify
|
||||
it under the terms of the GNU Lesser General Public License as published by
|
||||
the Free Software Foundation; either version 2.1 of the License, or
|
||||
(at your option) any later version.
|
||||
|
||||
This library is distributed in the hope that it will be useful,
|
||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
GNU Lesser General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU Lesser General Public License along
|
||||
with this library; if not, write to the Free Software Foundation, Inc.,
|
||||
51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
*/
|
||||
|
||||
#ifndef DCM_PROPERTY_PARSER_H
|
||||
#define DCM_PROPERTY_PARSER_H
|
||||
|
||||
#include <boost/spirit/include/qi.hpp>
|
||||
#include <boost/spirit/include/support_istream_iterator.hpp>
|
||||
#include <boost/spirit/include/qi_string.hpp>
|
||||
#include <boost/spirit/include/phoenix.hpp>
|
||||
|
||||
#include <boost/mpl/less.hpp>
|
||||
#include <boost/mpl/int.hpp>
|
||||
|
||||
namespace fusion = boost::fusion;
|
||||
namespace qi = boost::spirit::qi;
|
||||
namespace ascii = boost::spirit::ascii;
|
||||
namespace phx = boost::phoenix;
|
||||
namespace mpl = boost::mpl;
|
||||
|
||||
namespace dcm {
|
||||
|
||||
typedef boost::spirit::istream_iterator IIterator;
|
||||
|
||||
namespace details {
|
||||
|
||||
struct empty_parser : public qi::grammar<IIterator> {
|
||||
qi::rule<IIterator> start;
|
||||
empty_parser(): empty_parser::base_type(start) {
|
||||
start = qi::eps(true);
|
||||
};
|
||||
empty_parser(const empty_parser& other) : empty_parser::base_type(start) {};
|
||||
};
|
||||
|
||||
template<typename Prop>
|
||||
struct skip_parser : public qi::grammar<IIterator, typename Prop::type()> {
|
||||
qi::rule<IIterator, typename Prop::type()> start;
|
||||
skip_parser() : skip_parser<Prop>::base_type(start) {
|
||||
start = qi::eps(true);
|
||||
};
|
||||
skip_parser(const skip_parser& other) : skip_parser::base_type(start) {};
|
||||
};
|
||||
|
||||
template<typename Prop, typename Par>
|
||||
struct prop_parser : qi::grammar<IIterator, typename Prop::type(), qi::space_type> {
|
||||
|
||||
typename Par::parser subrule;
|
||||
qi::rule<IIterator, typename Prop::type(), qi::space_type> start;
|
||||
prop_parser();
|
||||
prop_parser(const prop_parser& other) : prop_parser::base_type(start) {};
|
||||
};
|
||||
|
||||
template<typename Sys, typename seq, typename state>
|
||||
struct prop_parser_fold : mpl::fold< seq, state,
|
||||
mpl::if_< dcm::parser_parse<mpl::_2, Sys>,
|
||||
mpl::push_back<mpl::_1,
|
||||
prop_parser<mpl::_2, dcm::parser_parser<mpl::_2, Sys, IIterator> > >,
|
||||
mpl::push_back<mpl::_1, skip_parser<mpl::_2> > > > {};
|
||||
|
||||
//grammar for a fusion sequence of properties. currently max. 10 properties are supported
|
||||
template<typename Sys, typename PropertyList>
|
||||
struct prop_par : qi::grammar<IIterator, typename details::pts<PropertyList>::type(), qi::space_type> {
|
||||
|
||||
//create a vector with the appropriate rules for all properties.
|
||||
typedef typename prop_parser_fold<Sys, PropertyList, mpl::vector<> >::type init_rules_sequence;
|
||||
//allow max 10 types as the following code expect this
|
||||
BOOST_MPL_ASSERT((mpl::less_equal< mpl::size<init_rules_sequence>, mpl::int_<10> >));
|
||||
//we want to process 10 elements, so create a vector with (10-prop.size()) empty rules
|
||||
//and append it to our rules vector
|
||||
typedef mpl::range_c<int,0, mpl::minus< mpl::int_<10>, mpl::size<init_rules_sequence> >::value > range;
|
||||
typedef typename mpl::fold< range,
|
||||
init_rules_sequence,
|
||||
mpl::push_back<mpl::_1, empty_parser> >::type rules_sequence;
|
||||
|
||||
typename fusion::result_of::as_vector<rules_sequence>::type rules;
|
||||
qi::rule<IIterator, typename details::pts<PropertyList>::type(), qi::space_type> prop;
|
||||
|
||||
prop_par();
|
||||
};
|
||||
|
||||
//special prop classes for better externalisaton, therefore the outside constructor to avoid auto inline
|
||||
template<typename Sys>
|
||||
struct cluster_prop_par : public prop_par<Sys, typename Sys::Cluster::cluster_properties> {
|
||||
cluster_prop_par();
|
||||
};
|
||||
|
||||
template<typename Sys>
|
||||
struct vertex_prop_par : public prop_par<Sys, typename Sys::Cluster::vertex_properties> {
|
||||
vertex_prop_par();
|
||||
};
|
||||
|
||||
template<typename Sys>
|
||||
struct edge_prop_par : public prop_par<Sys, typename Sys::Cluster::edge_properties> {
|
||||
edge_prop_par();
|
||||
};
|
||||
|
||||
} //DCM
|
||||
} //details
|
||||
|
||||
#ifndef USE_EXTERNAL
|
||||
#include "property_parser_imp.hpp"
|
||||
#endif
|
||||
|
||||
#endif
|
||||
@@ -0,0 +1,60 @@
|
||||
/*
|
||||
openDCM, dimensional constraint manager
|
||||
Copyright (C) 2013 Stefan Troeger <stefantroeger@gmx.net>
|
||||
|
||||
This library is free software; you can redistribute it and/or modify
|
||||
it under the terms of the GNU Lesser General Public License as published by
|
||||
the Free Software Foundation; either version 2.1 of the License, or
|
||||
(at your option) any later version.
|
||||
|
||||
This library is distributed in the hope that it will be useful,
|
||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
GNU Lesser General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU Lesser General Public License along
|
||||
with this library; if not, write to the Free Software Foundation, Inc.,
|
||||
51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
*/
|
||||
|
||||
#ifndef DCM_PROPERTY_PARSER_IMP_H
|
||||
#define DCM_PROPERTY_PARSER_IMP_H
|
||||
|
||||
#include "property_parser.hpp"
|
||||
|
||||
|
||||
namespace dcm {
|
||||
|
||||
typedef boost::spirit::istream_iterator IIterator;
|
||||
|
||||
namespace details {
|
||||
|
||||
template<typename Prop, typename Par>
|
||||
prop_parser<Prop, Par>::prop_parser() : prop_parser<Prop, Par>::base_type(start) {
|
||||
Par::init(subrule);
|
||||
start %= qi::lit("<Property>") >> subrule >> qi::lit("</Property>");
|
||||
};
|
||||
|
||||
|
||||
template<typename Sys, typename PropertyList>
|
||||
prop_par<Sys, PropertyList>::prop_par() : prop_par<Sys, PropertyList>::base_type(prop) {
|
||||
|
||||
prop %= fusion::at_c<0>(rules) >> fusion::at_c<1>(rules) >> fusion::at_c<2>(rules)
|
||||
>> fusion::at_c<3>(rules) >> fusion::at_c<4>(rules) >> fusion::at_c<5>(rules)
|
||||
>> fusion::at_c<6>(rules) >> fusion::at_c<7>(rules) >> fusion::at_c<8>(rules)
|
||||
>> fusion::at_c<9>(rules);
|
||||
};
|
||||
|
||||
template<typename Sys>
|
||||
cluster_prop_par<Sys>::cluster_prop_par() : prop_par<Sys, typename Sys::Cluster::cluster_properties>() {};
|
||||
|
||||
template<typename Sys>
|
||||
vertex_prop_par<Sys>::vertex_prop_par() : prop_par<Sys, typename Sys::Cluster::vertex_properties>() {};
|
||||
|
||||
template<typename Sys>
|
||||
edge_prop_par<Sys>::edge_prop_par() : prop_par<Sys, typename Sys::Cluster::edge_properties>() {};
|
||||
|
||||
} //DCM
|
||||
} //details
|
||||
|
||||
#endif
|
||||
53
src/Mod/Assembly/App/opendcm/moduleState/traits.hpp
Normal file
53
src/Mod/Assembly/App/opendcm/moduleState/traits.hpp
Normal file
@@ -0,0 +1,53 @@
|
||||
/*
|
||||
openDCM, dimensional constraint manager
|
||||
Copyright (C) 2013 Stefan Troeger <stefantroeger@gmx.net>
|
||||
|
||||
This library is free software; you can redistribute it and/or modify
|
||||
it under the terms of the GNU Lesser General Public License as published by
|
||||
the Free Software Foundation; either version 2.1 of the License, or
|
||||
(at your option) any later version.
|
||||
|
||||
This library is distributed in the hope that it will be useful,
|
||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
GNU Lesser General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU Lesser General Public License along
|
||||
with this library; if not, write to the Free Software Foundation, Inc.,
|
||||
51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
*/
|
||||
|
||||
#ifndef DCM_PARSER_TRAITS_H
|
||||
#define DCM_PARSER_TRAITS_H
|
||||
|
||||
#include <boost/mpl/bool.hpp>
|
||||
#include <assert.h>
|
||||
|
||||
namespace dcm {
|
||||
|
||||
template<typename type, typename System>
|
||||
struct parser_generate : public boost::mpl::false_ {};
|
||||
|
||||
template<typename type, typename System, typename iterator>
|
||||
struct parser_generator {
|
||||
typedef int generator;
|
||||
|
||||
static void init(generator& r) {
|
||||
assert(false);
|
||||
};
|
||||
};
|
||||
|
||||
template<typename type, typename System>
|
||||
struct parser_parse : public boost::mpl::false_ {};
|
||||
|
||||
template<typename type, typename System, typename iterator>
|
||||
struct parser_parser {
|
||||
typedef int parser;
|
||||
|
||||
static void init(parser& r) {
|
||||
assert(false);
|
||||
};
|
||||
};
|
||||
|
||||
}
|
||||
#endif //DCM_PARSER_TRAITS_H
|
||||
160
src/Mod/Assembly/App/opendcm/moduleState/traits_impl.hpp
Normal file
160
src/Mod/Assembly/App/opendcm/moduleState/traits_impl.hpp
Normal file
@@ -0,0 +1,160 @@
|
||||
/*
|
||||
openDCM, dimensional constraint manager
|
||||
Copyright (C) 2013 Stefan Troeger <stefantroeger@gmx.net>
|
||||
|
||||
This library is free software; you can redistribute it and/or modify
|
||||
it under the terms of the GNU Lesser General Public License as published by
|
||||
the Free Software Foundation; either version 2.1 of the License, or
|
||||
(at your option) any later version.
|
||||
|
||||
This library is distributed in the hope that it will be useful,
|
||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
GNU Lesser General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU Lesser General Public License along
|
||||
with this library; if not, write to the Free Software Foundation, Inc.,
|
||||
51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
*/
|
||||
|
||||
//move the traits specializations outside of the traits definition to avoid the spirit header parsing every
|
||||
//time this module is included and just parse it in externalisation mode when the generator is build
|
||||
|
||||
#ifndef DCM_PARSER_TRAITS_IMPL_H
|
||||
#define DCM_PARSER_TRAITS_IMPL_H
|
||||
|
||||
#include "traits.hpp"
|
||||
#include "defines.hpp"
|
||||
|
||||
#include <boost/mpl/bool.hpp>
|
||||
|
||||
#include <boost/spirit/include/qi.hpp>
|
||||
#include <boost/spirit/include/karma.hpp>
|
||||
#include <boost/spirit/include/karma_string.hpp>
|
||||
#include <boost/spirit/include/karma_int.hpp>
|
||||
#include <boost/spirit/include/karma_bool.hpp>
|
||||
#include <boost/spirit/include/karma_rule.hpp>
|
||||
#include <boost/spirit/include/karma_auto.hpp>
|
||||
|
||||
namespace karma = boost::spirit::karma;
|
||||
namespace qi = boost::spirit::qi;
|
||||
|
||||
namespace boost {
|
||||
namespace spirit {
|
||||
namespace traits {
|
||||
template <>
|
||||
struct create_generator<dcm::No_Identifier> {
|
||||
|
||||
typedef BOOST_TYPEOF(karma::eps(false)) type;
|
||||
static type call() {
|
||||
return karma::eps(false);
|
||||
}
|
||||
};
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
namespace dcm {
|
||||
|
||||
template<typename System>
|
||||
struct parser_generate<type_prop, System> : public mpl::true_ {};
|
||||
|
||||
template<typename System, typename iterator>
|
||||
struct parser_generator<type_prop, System, iterator> {
|
||||
typedef karma::rule<iterator, int&()> generator;
|
||||
|
||||
static void init(generator& r) {
|
||||
r = karma::lit("<type>clustertype</type>\n<value>") << karma::int_ <<"</value>";
|
||||
};
|
||||
};
|
||||
|
||||
template<typename System>
|
||||
struct parser_generate<changed_prop, System> : public mpl::true_ {};
|
||||
|
||||
template<typename System, typename iterator>
|
||||
struct parser_generator<changed_prop, System, iterator> {
|
||||
typedef karma::rule<iterator, bool&()> generator;
|
||||
|
||||
static void init(generator& r) {
|
||||
r = karma::lit("<type>clusterchanged</type>\n<value>") << karma::bool_ <<"</value>";
|
||||
};
|
||||
};
|
||||
|
||||
template<typename System>
|
||||
struct parser_generate<id_prop<typename System::Identifier>, System>
|
||||
: public mpl::not_<boost::is_same<typename System::Identifier, No_Identifier> > {};
|
||||
|
||||
template<typename System, typename iterator>
|
||||
struct parser_generator<id_prop<typename System::Identifier>, System, iterator> {
|
||||
typedef karma::rule<iterator, typename System::Identifier()> generator;
|
||||
|
||||
static void init(generator& r) {
|
||||
r = karma::lit("<type>id</type>\n<value>") << karma::auto_ <<"</value>";
|
||||
};
|
||||
};
|
||||
|
||||
template<typename System>
|
||||
struct parser_parse<type_prop, System> : public mpl::true_ {};
|
||||
|
||||
template<typename System, typename iterator>
|
||||
struct parser_parser<type_prop, System, iterator> {
|
||||
typedef qi::rule<iterator, int(), qi::space_type> parser;
|
||||
|
||||
static void init(parser& r) {
|
||||
r = qi::lit("<type>clustertype</type>") >> ("<value>") >> qi::int_ >>"</value>";
|
||||
};
|
||||
};
|
||||
|
||||
template<typename System>
|
||||
struct parser_parse<changed_prop, System> : public mpl::true_ {};
|
||||
|
||||
template<typename System, typename iterator>
|
||||
struct parser_parser<changed_prop, System, iterator> {
|
||||
typedef qi::rule<iterator, bool(), qi::space_type> parser;
|
||||
|
||||
static void init(parser& r) {
|
||||
r = qi::lit("<type>clusterchanged</type>") >> ("<value>") >> qi::bool_ >>"</value>";
|
||||
};
|
||||
};
|
||||
|
||||
template<typename System>
|
||||
struct parser_parse<id_prop<typename System::Identifier>, System>
|
||||
: public mpl::not_<boost::is_same<typename System::Identifier, No_Identifier> > {};
|
||||
|
||||
template<typename System, typename iterator>
|
||||
struct parser_parser<id_prop<typename System::Identifier>, System, iterator> {
|
||||
typedef qi::rule<iterator, typename System::Identifier(), qi::space_type> parser;
|
||||
|
||||
static void init(parser& r) {
|
||||
r = qi::lit("<type>id</type>") >> ("<value>") >> qi::auto_ >>"</value>";
|
||||
};
|
||||
};
|
||||
/*
|
||||
template<typename System>
|
||||
struct parser_generate<details::cluster_vertex_prop, System>
|
||||
: public mpl::true_ {};
|
||||
|
||||
template<typename System, typename iterator>
|
||||
struct parser_generator<details::cluster_vertex_prop, System, iterator> {
|
||||
typedef karma::rule<iterator, int()> generator;
|
||||
|
||||
static void init(generator& r) {
|
||||
r = karma::lit("<type>id</type>\n<value>") << karma::int_ <<"</value>";
|
||||
};
|
||||
};
|
||||
|
||||
template<typename System>
|
||||
struct parser_parse<details::cluster_vertex_prop, System> : public mpl::true_ {};
|
||||
|
||||
template<typename System, typename iterator>
|
||||
struct parser_parser<details::cluster_vertex_prop, System, iterator> {
|
||||
typedef qi::rule<iterator, int(), qi::space_type> parser;
|
||||
|
||||
static void init(parser& r) {
|
||||
r = qi::lit("<type>id</type>") >> ("<value>") >> qi::int_ >>"</value>";
|
||||
};
|
||||
};*/
|
||||
|
||||
} //namespace dcm
|
||||
|
||||
#endif //DCM_PARSER_TRAITS_IMPL_H
|
||||
Reference in New Issue
Block a user