diff --git a/SConstruct b/SConstruct index e2b492df7..5c38657e1 100644 --- a/SConstruct +++ b/SConstruct @@ -266,6 +266,7 @@ opts.AddVariables( ('CXX', 'The C++ compiler to use to compile mapnik (defaults to g++).', 'g++'), ('CC', 'The C compiler used for configure checks of C libs (defaults to gcc).', 'gcc'), ('CUSTOM_CXXFLAGS', 'Custom C++ flags, e.g. -I if you have headers in a nonstandard directory ', ''), + ('CUSTOM_CFLAGS', 'Custom C flags, e.g. -I if you have headers in a nonstandard directory (only used for configure checks)', ''), ('CUSTOM_LDFLAGS', 'Custom linker flags, e.g. -L if you have libraries in a nonstandard directory ', ''), EnumVariable('LINKING', "Set library format for libmapnik",'shared', ['shared','static']), EnumVariable('RUNTIME_LINK', "Set preference for linking dependencies",'shared', ['shared','static']), @@ -372,7 +373,7 @@ opts.AddVariables( pickle_store = [# Scons internal variables 'CC', # compiler user to check if c deps compile during configure 'CXX', # C++ compiler to compile mapnik - 'CCFLAGS', + 'CFLAGS', 'CPPDEFINES', 'CPPFLAGS', # c preprocessor flags 'CPPPATH', @@ -382,6 +383,7 @@ pickle_store = [# Scons internal variables 'LINKFLAGS', 'CUSTOM_LDFLAGS', # user submitted 'CUSTOM_CXXFLAGS', # user submitted + 'CUSTOM_CFLAGS', # user submitted 'MAPNIK_LIB_NAME', 'LINK', 'RUNTIME_LINK', @@ -1012,8 +1014,10 @@ if not preconfigured: env['CPPPATH'] = ['#include', '#'] env['LIBPATH'] = ['#src'] - # set any custom cxxflags to come first + # set any custom cxxflags and ldflags to come first env.Append(CXXFLAGS = env['CUSTOM_CXXFLAGS']) + env.Append(CFLAGS = env['CUSTOM_CFLAGS']) + env.Append(LINKFLAGS = env['CUSTOM_LDFLAGS']) ### platform specific bits diff --git a/include/mapnik/datasource_cache.hpp b/include/mapnik/datasource_cache.hpp index 845abd764..93ac6ea92 100644 --- a/include/mapnik/datasource_cache.hpp +++ b/include/mapnik/datasource_cache.hpp @@ -54,7 +54,8 @@ private: public: static std::vector plugin_names(); static std::string plugin_directories(); - static void register_datasources(const std::string& path); + static void register_datasources(std::string const& path); + static bool register_datasource(std::string const& path); static boost::shared_ptr create(parameters const& params, bool bind=true); }; } diff --git a/include/mapnik/json/feature_collection_grammar.hpp b/include/mapnik/json/feature_collection_grammar.hpp index 9117b14a7..54c749dd4 100644 --- a/include/mapnik/json/feature_collection_grammar.hpp +++ b/include/mapnik/json/feature_collection_grammar.hpp @@ -87,7 +87,7 @@ struct feature_collection_grammar : features = lit("\"features\"") > lit(":") > lit('[') - > feature(_val) % lit(',') + > -(feature(_val) % lit(',')) > lit(']') ; diff --git a/include/mapnik/json/feature_grammar.hpp b/include/mapnik/json/feature_grammar.hpp index 20b13f9b1..b756daead 100644 --- a/include/mapnik/json/feature_grammar.hpp +++ b/include/mapnik/json/feature_grammar.hpp @@ -162,7 +162,7 @@ struct feature_grammar : using qi::_pass; using qi::eps; using qi::raw; - + using phoenix::new_; using phoenix::push_back; using phoenix::construct; @@ -197,7 +197,7 @@ struct feature_grammar : unesc_char.add ("\\\"", '\"') // quotation mark ("\\\\", '\\') // reverse solidus - ("\\/", '/') // solidus + ("\\/", '/') // solidus ("\\b", '\b') // backspace ("\\f", '\f') // formfeed ("\\n", '\n') // newline @@ -207,7 +207,7 @@ struct feature_grammar : string_ %= lit('"') >> *(unesc_char | "\\u" >> hex4 | (char_ - lit('"'))) >> lit('"') ; - + // geojson types feature_type = lit("\"type\"") @@ -244,17 +244,17 @@ struct feature_grammar : // ; ////////////////////////////////////////////////////////////////// - geometry = (lit('{')[_a = 0 ] + geometry = (lit('{')[_a = 0 ] >> lit("\"type\"") >> lit(':') >> geometry_dispatch[_a = _1] // <---- should be Nabialek trick! - >> lit(',') + >> lit(',') >> (lit("\"coordinates\"") > lit(':') > coordinates(_r1,_a) - | - lit("\"geometries\"") > lit(':') + | + lit("\"geometries\"") > lit(':') >> lit('[') >> geometry_collection(_r1) >> lit(']')) >> lit('}')) | lit("null") ; - + geometry_dispatch.add ("\"Point\"",1) ("\"LineString\"",2) @@ -265,7 +265,7 @@ struct feature_grammar : ("\"GeometryCollection\"",7) // ; - + coordinates = (eps(_r2 == 1) > point_coordinates(extract_geometry_(_r1))) | (eps(_r2 == 2) > linestring_coordinates(extract_geometry_(_r1))) | (eps(_r2 == 3) > polygon_coordinates(extract_geometry_(_r1))) @@ -273,46 +273,45 @@ struct feature_grammar : | (eps(_r2 == 5) > multilinestring_coordinates(extract_geometry_(_r1))) | (eps(_r2 == 6) > multipolygon_coordinates(extract_geometry_(_r1))) ; - + point_coordinates = eps[ _a = new_(Point) ] > ( point(SEG_MOVETO,_a) [push_back(_r1,_a)] | eps[cleanup_(_a)][_pass = false] ) ; linestring_coordinates = eps[ _a = new_(LineString)] - > (points(_a) [push_back(_r1,_a)] + > -(points(_a) [push_back(_r1,_a)] | eps[cleanup_(_a)][_pass = false]) ; polygon_coordinates = eps[ _a = new_(Polygon) ] > ((lit('[') - > points(_a) % lit(',') + > -(points(_a) % lit(',')) > lit(']')) [push_back(_r1,_a)] | eps[cleanup_(_a)][_pass = false]) ; - - multipoint_coordinates = lit('[') - > (point_coordinates(_r1) % lit(',')) + + multipoint_coordinates = lit('[') + > -(point_coordinates(_r1) % lit(',')) > lit(']') ; - - multilinestring_coordinates = lit('[') - > (linestring_coordinates(_r1) % lit(',')) + + multilinestring_coordinates = lit('[') + > -(linestring_coordinates(_r1) % lit(',')) > lit(']') ; - - multipolygon_coordinates = lit('[') - > (polygon_coordinates(_r1) % lit(',')) + + multipolygon_coordinates = lit('[') + > -(polygon_coordinates(_r1) % lit(',')) > lit(']') ; geometry_collection = *geometry(_r1) >> *(lit(',') >> geometry(_r1)) ; - - // point - point = (lit('[') > double_ > lit(',') > double_ > lit(']')) [push_vertex_(_r1,_r2,_1,_2)]; - // points - points = lit('[')[_a = SEG_MOVETO] > point (_a,_r1) % lit(',') [_a = SEG_LINETO] > lit(']'); + // point + point = lit('[') > -((double_ > lit(',') > double_)[push_vertex_(_r1,_r2,_1,_2)]) > lit(']'); + // points + points = lit('[')[_a = SEG_MOVETO] > -(point (_a,_r1) % lit(',')[_a = SEG_LINETO]) > lit(']'); on_error ( feature @@ -362,7 +361,7 @@ struct feature_grammar : qi::rule, void(boost::ptr_vector& ),space_type> linestring_coordinates; qi::rule, - void(boost::ptr_vector& ),space_type> polygon_coordinates; + void(boost::ptr_vector& ),space_type> polygon_coordinates; qi::rule& ),space_type> multipoint_coordinates; qi::rule& ),space_type> multilinestring_coordinates; diff --git a/plugins/input/geojson/geojson_datasource.cpp b/plugins/input/geojson/geojson_datasource.cpp index 7c1fc978f..068bf4c1f 100644 --- a/plugins/input/geojson/geojson_datasource.cpp +++ b/plugins/input/geojson/geojson_datasource.cpp @@ -25,7 +25,6 @@ #include #include - // boost #include #include @@ -129,11 +128,9 @@ std::map geojson_datasource::get_statistics() c return statistics_; } -// FIXME: implement mapnik::box2d geojson_datasource::envelope() const { if (!is_bound_) bind(); - return extent_; } @@ -149,9 +146,12 @@ mapnik::featureset_ptr geojson_datasource::features(mapnik::query const& q) cons if (!is_bound_) bind(); // if the query box intersects our world extent then query for features - if (extent_.intersects(q.get_bbox())) + mapnik::box2d const& b = q.get_bbox(); + if (extent_.intersects(b)) { - return boost::make_shared(features_,tree_); + box_type box(point_type(b.minx(),b.miny()),point_type(b.maxx(),b.maxy())); + index_array_ = tree_.find(box); + return boost::make_shared(features_, index_array_.begin(), index_array_.end()); } // otherwise return an empty featureset pointer return mapnik::featureset_ptr(); diff --git a/plugins/input/geojson/geojson_datasource.hpp b/plugins/input/geojson/geojson_datasource.hpp index 829a30f5f..079cb7e3c 100644 --- a/plugins/input/geojson/geojson_datasource.hpp +++ b/plugins/input/geojson/geojson_datasource.hpp @@ -62,6 +62,7 @@ private: boost::shared_ptr tr_; mutable std::vector features_; mutable spatial_index_type tree_; + mutable std::deque index_array_; }; diff --git a/plugins/input/geojson/geojson_featureset.cpp b/plugins/input/geojson/geojson_featureset.cpp index bf5cb7878..f6d45a9d1 100644 --- a/plugins/input/geojson/geojson_featureset.cpp +++ b/plugins/input/geojson/geojson_featureset.cpp @@ -29,23 +29,24 @@ #include "geojson_featureset.hpp" -geojson_featureset::geojson_featureset(std::vector const& features, - geojson_datasource::spatial_index_type const& tree) - : feature_id_(1), - features_(features), - tree_(tree) {} +geojson_featureset::geojson_featureset(std::vector const& features, + std::deque::const_iterator index_itr, + std::deque::const_iterator index_end) + : features_(features), + index_itr_(index_itr), + index_end_(index_end) {} geojson_featureset::~geojson_featureset() {} mapnik::feature_ptr geojson_featureset::next() { - feature_id_++; - if (feature_id_ <= features_.size()) + if (index_itr_ != index_end_) { - return features_.at(feature_id_ - 1); - } - else - { - return mapnik::feature_ptr(); - } + std::size_t index = *index_itr_++; + if ( index < features_.size()) + { + return features_.at(index); + } + } + return mapnik::feature_ptr(); } diff --git a/plugins/input/geojson/geojson_featureset.hpp b/plugins/input/geojson/geojson_featureset.hpp index 6a463f66e..d10919ef8 100644 --- a/plugins/input/geojson/geojson_featureset.hpp +++ b/plugins/input/geojson/geojson_featureset.hpp @@ -2,22 +2,26 @@ #define GEOJSON_FEATURESET_HPP #include -#include #include "geojson_datasource.hpp" +#include +#include + + class geojson_featureset : public mapnik::Featureset { public: geojson_featureset(std::vector const& features, - geojson_datasource::spatial_index_type const& tree); + std::deque::const_iterator index_itr, + std::deque::const_iterator index_end); virtual ~geojson_featureset(); mapnik::feature_ptr next(); private: mapnik::box2d box_; - unsigned int feature_id_; std::vector const& features_; - geojson_datasource::spatial_index_type const& tree_; + std::deque::const_iterator index_itr_; + std::deque::const_iterator index_end_; }; #endif // GEOJSON_FEATURESET_HPP diff --git a/src/datasource_cache.cpp b/src/datasource_cache.cpp index 4c78d6cf2..1d8bbc1f3 100644 --- a/src/datasource_cache.cpp +++ b/src/datasource_cache.cpp @@ -118,7 +118,7 @@ datasource_ptr datasource_cache::create(const parameters& params, bool bind) return ds; } -bool datasource_cache::insert(const std::string& type,const lt_dlhandle module) +bool datasource_cache::insert(std::string const& type,const lt_dlhandle module) { return plugins_.insert(make_pair(type,boost::make_shared (type,module))).second; @@ -140,7 +140,7 @@ std::vector datasource_cache::plugin_names () return names; } -void datasource_cache::register_datasources(const std::string& str) +void datasource_cache::register_datasources(std::string const& str) { #ifdef MAPNIK_THREADSAFE mutex::scoped_lock lock(mapnik::singletonpath().leaf())) #endif { - try +#if (BOOST_FILESYSTEM_VERSION == 3) + if (register_datasource(itr->path().string().c_str())) +#else // v2 + if (register_datasource(itr->string().c_str())) +#endif { -#if (BOOST_FILESYSTEM_VERSION == 3) - lt_dlhandle module = lt_dlopen(itr->path().string().c_str()); -#else // v2 - lt_dlhandle module = lt_dlopen(itr->string().c_str()); -#endif - if (module) - { - // http://www.mr-edd.co.uk/blog/supressing_gcc_warnings -#ifdef __GNUC__ - __extension__ -#endif - datasource_name* ds_name = - reinterpret_cast(lt_dlsym(module, "datasource_name")); - if (ds_name && insert(ds_name(),module)) - { - MAPNIK_LOG_DEBUG(datasource_cache) << "datasource_cache: Registered=" << ds_name(); - - registered_=true; - } - else if (!ds_name) - { - MAPNIK_LOG_ERROR(datasource_cache) - << "Problem loading plugin library '" - << itr->path().string() << "' (plugin is lacking compatible interface)"; - } - } - else - { -#if (BOOST_FILESYSTEM_VERSION == 3) - MAPNIK_LOG_ERROR(datasource_cache) - << "Problem loading plugin library: " << itr->path().string() - << " (dlopen failed - plugin likely has an unsatisfied dependency or incompatible ABI)"; -#else // v2 - MAPNIK_LOG_ERROR(datasource_cache) - << "Problem loading plugin library: " << itr->string() - << " (dlopen failed - plugin likely has an unsatisfied dependency or incompatible ABI)"; -#endif - } + registered_ = true; } - catch (...) {} } } } } +bool datasource_cache::register_datasource(std::string const& str) +{ + bool success = false; + try + { + lt_dlhandle module = lt_dlopen(str.c_str()); + if (module) + { + // http://www.mr-edd.co.uk/blog/supressing_gcc_warnings +#ifdef __GNUC__ + __extension__ +#endif + datasource_name* ds_name = + reinterpret_cast(lt_dlsym(module, "datasource_name")); + if (ds_name && insert(ds_name(),module)) + { + MAPNIK_LOG_DEBUG(datasource_cache) << "datasource_cache: Registered=" << ds_name(); + + success = true; + } + else if (!ds_name) + { + MAPNIK_LOG_ERROR(datasource_cache) + << "Problem loading plugin library '" + << str << "' (plugin is lacking compatible interface)"; + } + } + else + { + MAPNIK_LOG_ERROR(datasource_cache) + << "Problem loading plugin library: " << str + << " (dlopen failed - plugin likely has an unsatisfied dependency or incompatible ABI)"; + } + } + catch (...) { + MAPNIK_LOG_ERROR(datasource_cache) + << "Exception caught while loading plugin library: " << str; + } + return success; +} + }