Merge commit '00517a507f68237874630dae1821c8a2c844bc3d' into harfbuzz
Conflicts: tests/visual_tests/test.py
|
@ -53,6 +53,7 @@ struct MAPNIK_DECL image_reader
|
|||
{
|
||||
virtual unsigned width() const=0;
|
||||
virtual unsigned height() const=0;
|
||||
virtual bool premultiplied_alpha() const=0;
|
||||
virtual void read(unsigned x,unsigned y,image_data_32& image)=0;
|
||||
virtual ~image_reader() {}
|
||||
};
|
||||
|
|
|
@ -26,7 +26,7 @@
|
|||
// mapnik
|
||||
#include <mapnik/global.hpp>
|
||||
#include <mapnik/geometry.hpp>
|
||||
#include <mapnik/util/vertex_iterator.hpp>
|
||||
#include <mapnik/util/path_iterator.hpp>
|
||||
#include <mapnik/util/container_adapter.hpp>
|
||||
|
||||
// boost
|
||||
|
|
|
@ -32,11 +32,13 @@ struct raster
|
|||
{
|
||||
box2d<double> ext_;
|
||||
image_data_32 data_;
|
||||
raster(box2d<double> const& ext,image_data_32 const& data)
|
||||
bool premultiplied_alpha_;
|
||||
raster(box2d<double> const& ext,image_data_32 const& data, bool premultiplied_alpha = false)
|
||||
: ext_(ext),
|
||||
data_(data) {}
|
||||
data_(data),
|
||||
premultiplied_alpha_(premultiplied_alpha)
|
||||
{}
|
||||
};
|
||||
}
|
||||
|
||||
#endif // MAPNIK_RASTER_HPP
|
||||
|
||||
|
|
|
@ -17,7 +17,8 @@
|
|||
namespace mapnik
|
||||
{
|
||||
|
||||
struct weighted_vertex : private boost::noncopyable {
|
||||
struct weighted_vertex : private boost::noncopyable
|
||||
{
|
||||
vertex2d coord;
|
||||
double weight;
|
||||
weighted_vertex *prev;
|
||||
|
@ -27,20 +28,23 @@ struct weighted_vertex : private boost::noncopyable {
|
|||
coord(coord_),
|
||||
weight(std::numeric_limits<double>::infinity()),
|
||||
prev(NULL),
|
||||
next(NULL) { }
|
||||
next(NULL) {}
|
||||
|
||||
double nominalWeight() {
|
||||
double nominalWeight()
|
||||
{
|
||||
if (prev == NULL || next == NULL || coord.cmd != SEG_LINETO) {
|
||||
return std::numeric_limits<double>::infinity();
|
||||
}
|
||||
vertex2d& A = prev->coord;
|
||||
vertex2d& B = next->coord;
|
||||
vertex2d& C = coord;
|
||||
vertex2d const& A = prev->coord;
|
||||
vertex2d const& B = next->coord;
|
||||
vertex2d const& C = coord;
|
||||
return std::abs((double)((A.x - C.x) * (B.y - A.y) - (A.x - B.x) * (C.y - A.y))) / 2.0;
|
||||
}
|
||||
|
||||
struct ascending_sort {
|
||||
bool operator() (const weighted_vertex *a, const weighted_vertex *b) {
|
||||
struct ascending_sort
|
||||
{
|
||||
bool operator() (const weighted_vertex *a, const weighted_vertex *b)
|
||||
{
|
||||
return b->weight > a->weight;
|
||||
}
|
||||
};
|
||||
|
@ -97,10 +101,11 @@ struct MAPNIK_DECL simplify_converter
|
|||
{
|
||||
public:
|
||||
simplify_converter(Geometry& geom)
|
||||
: geom_(geom)
|
||||
, tolerance_(0.0)
|
||||
, status_(initial)
|
||||
, algorithm_(radial_distance)
|
||||
: geom_(geom),
|
||||
tolerance_(0.0),
|
||||
status_(initial),
|
||||
algorithm_(radial_distance),
|
||||
pos_(0)
|
||||
{}
|
||||
|
||||
enum status
|
||||
|
@ -117,8 +122,10 @@ public:
|
|||
return algorithm_;
|
||||
}
|
||||
|
||||
void set_simplify_algorithm(simplify_algorithm_e value) {
|
||||
if (algorithm_ != value) {
|
||||
void set_simplify_algorithm(simplify_algorithm_e value)
|
||||
{
|
||||
if (algorithm_ != value)
|
||||
{
|
||||
algorithm_ = value;
|
||||
reset();
|
||||
}
|
||||
|
@ -145,7 +152,7 @@ public:
|
|||
pos_ = 0;
|
||||
}
|
||||
|
||||
void rewind(unsigned int)
|
||||
void rewind(unsigned int) const
|
||||
{
|
||||
pos_ = 0;
|
||||
}
|
||||
|
@ -360,7 +367,8 @@ private:
|
|||
}
|
||||
}
|
||||
|
||||
status init_vertices_visvalingam_whyatt() {
|
||||
status init_vertices_visvalingam_whyatt()
|
||||
{
|
||||
typedef std::set<weighted_vertex *, weighted_vertex::ascending_sort> VertexSet;
|
||||
typedef std::vector<weighted_vertex *> VertexList;
|
||||
|
||||
|
@ -371,13 +379,13 @@ private:
|
|||
v_list.push_back(new weighted_vertex(vtx));
|
||||
}
|
||||
|
||||
if (!v_list.size()) {
|
||||
if (v_list.empty()) {
|
||||
return status_ = process;
|
||||
}
|
||||
|
||||
// Connect the vertices in a linked list and insert them into the set.
|
||||
VertexSet v;
|
||||
for (VertexList::iterator i = v_list.begin(); i != v_list.end(); i++)
|
||||
for (VertexList::iterator i = v_list.begin(); i != v_list.end(); ++i)
|
||||
{
|
||||
(*i)->prev = i == v_list.begin() ? NULL : *(i - 1);
|
||||
(*i)->next = i + 1 == v_list.end() ? NULL : *(i + 1);
|
||||
|
@ -415,9 +423,10 @@ private:
|
|||
v.clear();
|
||||
|
||||
// Traverse the remaining list and insert them into the vertex cache.
|
||||
for (VertexList::iterator i = v_list.begin(); i != v_list.end(); i++)
|
||||
for (VertexList::iterator i = v_list.begin(); i != v_list.end(); ++i)
|
||||
{
|
||||
if ((*i)->weight >= tolerance_) {
|
||||
if ((*i)->weight >= tolerance_)
|
||||
{
|
||||
vertices_.push_back((*i)->coord);
|
||||
}
|
||||
delete *i;
|
||||
|
@ -431,10 +440,10 @@ private:
|
|||
double tolerance_;
|
||||
status status_;
|
||||
simplify_algorithm_e algorithm_;
|
||||
size_t pos_;
|
||||
std::deque<vertex2d> vertices_;
|
||||
std::deque<vertex2d> sleeve_cont_;
|
||||
vertex2d previous_vertex_;
|
||||
mutable size_t pos_;
|
||||
};
|
||||
|
||||
|
||||
|
|
|
@ -26,7 +26,7 @@
|
|||
// mapnik
|
||||
#include <mapnik/global.hpp>
|
||||
#include <mapnik/geometry.hpp>
|
||||
#include <mapnik/util/vertex_iterator.hpp>
|
||||
#include <mapnik/util/path_iterator.hpp>
|
||||
|
||||
// boost
|
||||
#include <boost/tuple/tuple.hpp>
|
||||
|
@ -40,26 +40,26 @@ struct is_container<mapnik::geometry_type const> : mpl::true_ {} ;
|
|||
template <>
|
||||
struct container_iterator<mapnik::geometry_type const>
|
||||
{
|
||||
typedef mapnik::util::vertex_iterator<double> type;
|
||||
typedef mapnik::util::path_iterator<mapnik::geometry_type> type;
|
||||
};
|
||||
|
||||
template <>
|
||||
struct begin_container<mapnik::geometry_type const>
|
||||
{
|
||||
static mapnik::util::vertex_iterator<double>
|
||||
static mapnik::util::path_iterator<mapnik::geometry_type>
|
||||
call (mapnik::geometry_type const& g)
|
||||
{
|
||||
return mapnik::util::vertex_iterator<double>(g.data());
|
||||
return mapnik::util::path_iterator<mapnik::geometry_type>(g);
|
||||
}
|
||||
};
|
||||
|
||||
template <>
|
||||
struct end_container<mapnik::geometry_type const>
|
||||
{
|
||||
static mapnik::util::vertex_iterator<double>
|
||||
static mapnik::util::path_iterator<mapnik::geometry_type>
|
||||
call (mapnik::geometry_type const& g)
|
||||
{
|
||||
return mapnik::util::vertex_iterator<double>();
|
||||
return mapnik::util::path_iterator<mapnik::geometry_type>();
|
||||
}
|
||||
};
|
||||
|
||||
|
|
|
@ -26,7 +26,7 @@
|
|||
// mapnik
|
||||
#include <mapnik/global.hpp>
|
||||
#include <mapnik/geometry.hpp>
|
||||
#include <mapnik/util/vertex_iterator.hpp>
|
||||
#include <mapnik/util/path_iterator.hpp>
|
||||
#include <mapnik/util/container_adapter.hpp>
|
||||
|
||||
// boost
|
||||
|
|
|
@ -26,7 +26,6 @@
|
|||
// mapnik
|
||||
#include <mapnik/global.hpp>
|
||||
#include <mapnik/geometry.hpp>
|
||||
#include <mapnik/util/vertex_iterator.hpp>
|
||||
#include <mapnik/util/geometry_svg_generator.hpp>
|
||||
|
||||
// boost
|
||||
|
|
|
@ -126,8 +126,8 @@ namespace mapnik { namespace util {
|
|||
ss.write(reinterpret_cast<char*>(&byte_order),1);
|
||||
int type = static_cast<int>(mapnik::Point);
|
||||
write(ss,type,4,byte_order);
|
||||
double x(0);
|
||||
double y(0);
|
||||
double x = 0;
|
||||
double y = 0;
|
||||
g.vertex(0,&x,&y);
|
||||
write(ss,x,8,byte_order);
|
||||
write(ss,y,8,byte_order);
|
||||
|
@ -146,8 +146,8 @@ namespace mapnik { namespace util {
|
|||
int type = static_cast<int>(mapnik::LineString);
|
||||
write(ss,type,4,byte_order);
|
||||
write(ss,num_points,4,byte_order);
|
||||
double x(0);
|
||||
double y(0);
|
||||
double x = 0;
|
||||
double y = 0;
|
||||
for (unsigned i=0; i< num_points; ++i)
|
||||
{
|
||||
g.vertex(i,&x,&y);
|
||||
|
@ -167,8 +167,8 @@ namespace mapnik { namespace util {
|
|||
typedef std::vector<point_type> linear_ring;
|
||||
boost::ptr_vector<linear_ring> rings;
|
||||
|
||||
double x(0);
|
||||
double y(0);
|
||||
double x = 0;
|
||||
double y = 0;
|
||||
std::size_t size = 1 + 4 + 4 ; // byteOrder + wkbType + numRings
|
||||
for (unsigned i=0; i< num_points; ++i)
|
||||
{
|
||||
|
|
|
@ -26,7 +26,6 @@
|
|||
// mapnik
|
||||
#include <mapnik/global.hpp>
|
||||
#include <mapnik/geometry.hpp>
|
||||
#include <mapnik/util/vertex_iterator.hpp>
|
||||
#include <mapnik/util/geometry_wkt_generator.hpp>
|
||||
|
||||
// boost
|
||||
|
@ -40,7 +39,7 @@ bool to_wkt(std::string & wkt, mapnik::geometry_type const& geom)
|
|||
{
|
||||
typedef std::back_insert_iterator<std::string> sink_type;
|
||||
sink_type sink(wkt);
|
||||
wkt_generator<sink_type> generator(true);
|
||||
wkt_generator<sink_type, mapnik::geometry_type> generator(true);
|
||||
bool result = karma::generate(sink, generator, geom);
|
||||
return result;
|
||||
}
|
||||
|
@ -49,7 +48,7 @@ bool to_wkt(std::string & wkt, mapnik::geometry_container const& geom)
|
|||
{
|
||||
typedef std::back_insert_iterator<std::string> sink_type;
|
||||
sink_type sink(wkt);
|
||||
wkt_multi_generator<sink_type> generator;
|
||||
wkt_multi_generator<sink_type, mapnik::geometry_container> generator;
|
||||
bool result = karma::generate(sink, generator, geom);
|
||||
return result;
|
||||
}
|
||||
|
|
|
@ -25,7 +25,6 @@
|
|||
|
||||
// mapnik
|
||||
#include <mapnik/global.hpp>
|
||||
#include <mapnik/geometry.hpp>
|
||||
|
||||
// boost
|
||||
#include <boost/tuple/tuple.hpp>
|
||||
|
@ -36,7 +35,7 @@
|
|||
#include <boost/spirit/include/phoenix_function.hpp>
|
||||
#include <boost/spirit/home/phoenix/statement/if.hpp>
|
||||
#include <boost/fusion/include/boost_tuple.hpp>
|
||||
|
||||
#include <boost/type_traits/remove_pointer.hpp>
|
||||
|
||||
//#define BOOST_SPIRIT_USE_PHOENIX_V3 1
|
||||
|
||||
|
@ -50,7 +49,6 @@ struct is_container<mapnik::geometry_container>
|
|||
|
||||
}}}
|
||||
|
||||
|
||||
namespace mapnik { namespace util {
|
||||
|
||||
namespace karma = boost::spirit::karma;
|
||||
|
@ -58,34 +56,41 @@ namespace phoenix = boost::phoenix;
|
|||
|
||||
namespace detail {
|
||||
|
||||
template <typename Geometry>
|
||||
struct get_type
|
||||
{
|
||||
template <typename T>
|
||||
struct result { typedef int type; };
|
||||
|
||||
int operator() (geometry_type const& geom) const
|
||||
int operator() (Geometry const& geom) const
|
||||
{
|
||||
return static_cast<int>(geom.type());
|
||||
}
|
||||
};
|
||||
|
||||
template <typename T>
|
||||
struct get_first
|
||||
{
|
||||
template <typename T>
|
||||
struct result { typedef geometry_type::value_type const type; };
|
||||
typedef T geometry_type;
|
||||
|
||||
geometry_type::value_type const operator() (geometry_type const& geom) const
|
||||
template <typename U>
|
||||
struct result { typedef typename geometry_type::value_type const type; };
|
||||
|
||||
typename geometry_type::value_type const operator() (geometry_type const& geom) const
|
||||
{
|
||||
geometry_type::value_type coord;
|
||||
boost::get<0>(coord) = geom.vertex(0,&boost::get<1>(coord),&boost::get<2>(coord));
|
||||
typename geometry_type::value_type coord;
|
||||
geom.rewind(0);
|
||||
boost::get<0>(coord) = geom.vertex(&boost::get<1>(coord),&boost::get<2>(coord));
|
||||
return coord;
|
||||
}
|
||||
};
|
||||
|
||||
|
||||
template <typename T>
|
||||
struct multi_geometry_
|
||||
{
|
||||
template <typename T>
|
||||
typedef T geometry_container;
|
||||
|
||||
template <typename U>
|
||||
struct result { typedef bool type; };
|
||||
|
||||
bool operator() (geometry_container const& geom) const
|
||||
|
@ -94,9 +99,12 @@ struct multi_geometry_
|
|||
}
|
||||
};
|
||||
|
||||
template <typename T>
|
||||
struct multi_geometry_type
|
||||
{
|
||||
template <typename T>
|
||||
typedef T geometry_container;
|
||||
|
||||
template <typename U>
|
||||
struct result { typedef boost::tuple<unsigned,bool> type; };
|
||||
|
||||
boost::tuple<unsigned,bool> operator() (geometry_container const& geom) const;
|
||||
|
@ -113,10 +121,13 @@ struct wkt_coordinate_policy : karma::real_policies<T>
|
|||
|
||||
}
|
||||
|
||||
template <typename OutputIterator>
|
||||
template <typename OutputIterator, typename Geometry>
|
||||
struct wkt_generator :
|
||||
karma::grammar<OutputIterator, geometry_type const& ()>
|
||||
karma::grammar<OutputIterator, Geometry const& ()>
|
||||
{
|
||||
typedef Geometry geometry_type;
|
||||
typedef typename boost::remove_pointer<typename geometry_type::value_type>::type coord_type;
|
||||
|
||||
wkt_generator(bool single = false);
|
||||
// rules
|
||||
karma::rule<OutputIterator, geometry_type const& ()> wkt;
|
||||
|
@ -126,33 +137,35 @@ struct wkt_generator :
|
|||
|
||||
karma::rule<OutputIterator, geometry_type const& ()> coords;
|
||||
karma::rule<OutputIterator, karma::locals<unsigned>, geometry_type const& ()> coords2;
|
||||
karma::rule<OutputIterator, geometry_type::value_type ()> point_coord;
|
||||
karma::rule<OutputIterator, geometry_type::value_type (unsigned& )> polygon_coord;
|
||||
karma::rule<OutputIterator, coord_type ()> point_coord;
|
||||
karma::rule<OutputIterator, coord_type (unsigned& )> polygon_coord;
|
||||
|
||||
// phoenix functions
|
||||
phoenix::function<detail::get_type > _type;
|
||||
phoenix::function<detail::get_first> _first;
|
||||
phoenix::function<detail::get_type<geometry_type> > _type;
|
||||
phoenix::function<detail::get_first<geometry_type> > _first;
|
||||
//
|
||||
karma::real_generator<double, detail::wkt_coordinate_policy<double> > coord_type;
|
||||
karma::real_generator<double, detail::wkt_coordinate_policy<double> > coordinate;
|
||||
};
|
||||
|
||||
|
||||
template <typename OutputIterator>
|
||||
template <typename OutputIterator, typename GeometryContainer>
|
||||
struct wkt_multi_generator :
|
||||
karma::grammar<OutputIterator, karma::locals< boost::tuple<unsigned,bool> >, geometry_container const& ()>
|
||||
karma::grammar<OutputIterator, karma::locals< boost::tuple<unsigned,bool> >, GeometryContainer const& ()>
|
||||
{
|
||||
typedef GeometryContainer geometry_contaner;
|
||||
typedef boost::remove_pointer<typename geometry_container::value_type>::type geometry_type;
|
||||
|
||||
wkt_multi_generator();
|
||||
// rules
|
||||
karma::rule<OutputIterator, karma::locals<boost::tuple<unsigned,bool> >, geometry_container const& ()> wkt;
|
||||
karma::rule<OutputIterator, geometry_container const& ()> geometry;
|
||||
karma::rule<OutputIterator, karma::locals<boost::tuple<unsigned,bool> >, GeometryContainer const& ()> wkt;
|
||||
karma::rule<OutputIterator, GeometryContainer const& ()> geometry;
|
||||
karma::rule<OutputIterator, geometry_type const& ()> single_geometry;
|
||||
karma::rule<OutputIterator, geometry_container const& ()> multi_geometry;
|
||||
wkt_generator<OutputIterator> path;
|
||||
karma::rule<OutputIterator, GeometryContainer const& ()> multi_geometry;
|
||||
wkt_generator<OutputIterator, geometry_type > path;
|
||||
// phoenix
|
||||
phoenix::function<detail::multi_geometry_> is_multi;
|
||||
phoenix::function<detail::multi_geometry_type> _multi_type;
|
||||
phoenix::function<detail::get_type > _type;
|
||||
phoenix::function<detail::multi_geometry_<GeometryContainer> > is_multi;
|
||||
phoenix::function<detail::multi_geometry_type<GeometryContainer> > _multi_type;
|
||||
phoenix::function<detail::get_type<geometry_type> > _type;
|
||||
//
|
||||
karma::symbols<unsigned, char const*> geometry_types;
|
||||
};
|
||||
|
|
85
include/mapnik/util/path_iterator.hpp
Normal file
|
@ -0,0 +1,85 @@
|
|||
/*****************************************************************************
|
||||
*
|
||||
* This file is part of Mapnik (c++ mapping toolkit)
|
||||
*
|
||||
* Copyright (C) 2011 Artem Pavlenko
|
||||
*
|
||||
* 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 St, Fifth Floor, Boston, MA 02110-1301 USA
|
||||
*
|
||||
*****************************************************************************/
|
||||
|
||||
#ifndef MAPNIK_VERTEX_ITERATOR_HPP
|
||||
#define MAPNIK_VERTEX_ITERATOR_HPP
|
||||
|
||||
// mapnik
|
||||
#include <mapnik/global.hpp>
|
||||
|
||||
// boost
|
||||
#include <boost/tuple/tuple.hpp>
|
||||
#include <boost/iterator/iterator_facade.hpp>
|
||||
|
||||
namespace mapnik { namespace util {
|
||||
|
||||
template <typename T>
|
||||
class path_iterator
|
||||
: public boost::iterator_facade< path_iterator<T>,
|
||||
boost::tuple<unsigned,double,double> const,
|
||||
boost::forward_traversal_tag
|
||||
>
|
||||
{
|
||||
|
||||
public:
|
||||
typedef T path_type;
|
||||
typedef typename boost::tuple<unsigned, double, double> value_type;
|
||||
|
||||
path_iterator()
|
||||
: v_(mapnik::SEG_END,0,0),
|
||||
vertices_()
|
||||
{}
|
||||
|
||||
explicit path_iterator(path_type const& vertices)
|
||||
: vertices_(&vertices)
|
||||
{
|
||||
vertices_->rewind(0);
|
||||
increment();
|
||||
}
|
||||
|
||||
private:
|
||||
friend class boost::iterator_core_access;
|
||||
|
||||
void increment()
|
||||
{
|
||||
boost::get<0>(v_) = vertices_->vertex( &boost::get<1>(v_), &boost::get<2>(v_));
|
||||
}
|
||||
|
||||
bool equal( path_iterator const& other) const
|
||||
{
|
||||
return boost::get<0>(v_) == boost::get<0>(other.v_);
|
||||
}
|
||||
|
||||
value_type const& dereference() const
|
||||
{
|
||||
return v_;
|
||||
}
|
||||
|
||||
value_type v_;
|
||||
const path_type *vertices_;
|
||||
unsigned pos_;
|
||||
};
|
||||
|
||||
}}
|
||||
|
||||
|
||||
#endif // MAPNIK_VERTEX_ITERATOR_HPP
|
|
@ -1,87 +0,0 @@
|
|||
/*****************************************************************************
|
||||
*
|
||||
* This file is part of Mapnik (c++ mapping toolkit)
|
||||
*
|
||||
* Copyright (C) 2011 Artem Pavlenko
|
||||
*
|
||||
* 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 St, Fifth Floor, Boston, MA 02110-1301 USA
|
||||
*
|
||||
*****************************************************************************/
|
||||
|
||||
#ifndef MAPNIK_VERTEX_ITERATOR_HPP
|
||||
#define MAPNIK_VERTEX_ITERATOR_HPP
|
||||
|
||||
// mapnik
|
||||
#include <mapnik/global.hpp>
|
||||
#include <mapnik/vertex_vector.hpp>
|
||||
|
||||
// boost
|
||||
#include <boost/tuple/tuple.hpp>
|
||||
#include <boost/iterator/iterator_facade.hpp>
|
||||
|
||||
namespace mapnik { namespace util {
|
||||
|
||||
template <typename T>
|
||||
class vertex_iterator
|
||||
: public boost::iterator_facade< vertex_iterator<T>,
|
||||
typename boost::tuple<unsigned,T,T> const,
|
||||
boost::forward_traversal_tag
|
||||
>
|
||||
{
|
||||
|
||||
public:
|
||||
typedef typename boost::tuple<unsigned, T, T> value_type;
|
||||
typedef vertex_vector<T> container_type;
|
||||
|
||||
vertex_iterator()
|
||||
: v_(SEG_END,0,0),
|
||||
vertices_(),
|
||||
pos_(0)
|
||||
{}
|
||||
|
||||
explicit vertex_iterator(container_type const& vertices)
|
||||
: vertices_(&vertices),
|
||||
pos_(0)
|
||||
{
|
||||
increment();
|
||||
}
|
||||
|
||||
private:
|
||||
friend class boost::iterator_core_access;
|
||||
|
||||
void increment()
|
||||
{
|
||||
boost::get<0>(v_) = vertices_->get_vertex(pos_++, &boost::get<1>(v_), &boost::get<2>(v_));
|
||||
}
|
||||
|
||||
bool equal( vertex_iterator const& other) const
|
||||
{
|
||||
return boost::get<0>(v_) == boost::get<0>(other.v_);
|
||||
}
|
||||
|
||||
value_type const& dereference() const
|
||||
{
|
||||
return v_;
|
||||
}
|
||||
|
||||
value_type v_;
|
||||
container_type const *vertices_;
|
||||
unsigned pos_;
|
||||
};
|
||||
|
||||
}}
|
||||
|
||||
|
||||
#endif // MAPNIK_VERTEX_ITERATOR_HPP
|
|
@ -113,7 +113,7 @@ feature_ptr raster_featureset<LookupPolicy>::next()
|
|||
|
||||
image_data_32 image(width,height);
|
||||
reader->read(x_off, y_off, image);
|
||||
feature->set_raster(boost::make_shared<raster>(intersect, image));
|
||||
feature->set_raster(boost::make_shared<raster>(intersect, image,reader->premultiplied_alpha()));
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
@ -524,7 +524,7 @@ boost::optional<mapnik::datasource::geometry_t> sqlite_datasource::get_geometry_
|
|||
if (data)
|
||||
{
|
||||
boost::ptr_vector<mapnik::geometry_type> paths;
|
||||
if (mapnik::geometry_utils::from_wkb(paths, data, size, mapnik::wkbAuto))
|
||||
if (mapnik::geometry_utils::from_wkb(paths, data, size, format_))
|
||||
{
|
||||
mapnik::util::to_ds_type(paths,result);
|
||||
if (result)
|
||||
|
|
|
@ -96,7 +96,9 @@ void agg_renderer<T>::process(raster_symbolizer const& sym,
|
|||
filter_radius);
|
||||
}
|
||||
}
|
||||
composite(current_buffer_->data(), target.data_, sym.comp_op(), sym.get_opacity(), start_x, start_y, true);
|
||||
composite(current_buffer_->data(), target.data_,
|
||||
sym.comp_op(), sym.get_opacity(),
|
||||
start_x, start_y, !source->premultiplied_alpha_);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
@ -50,6 +50,7 @@ public:
|
|||
~JpegReader();
|
||||
unsigned width() const;
|
||||
unsigned height() const;
|
||||
inline bool premultiplied_alpha() const { return true ;}
|
||||
void read(unsigned x,unsigned y,image_data_32& image);
|
||||
private:
|
||||
void init();
|
||||
|
|
|
@ -46,6 +46,7 @@ public:
|
|||
~png_reader();
|
||||
unsigned width() const;
|
||||
unsigned height() const;
|
||||
bool premultiplied_alpha() const { return false; } //http://www.libpng.org/pub/png/spec/1.1/PNG-Rationale.html
|
||||
void read(unsigned x,unsigned y,image_data_32& image);
|
||||
private:
|
||||
void init();
|
||||
|
|
|
@ -64,7 +64,7 @@ private:
|
|||
int tile_width_;
|
||||
int tile_height_;
|
||||
tiff_ptr tif_;
|
||||
|
||||
bool premultiplied_alpha_;
|
||||
public:
|
||||
enum TiffType {
|
||||
generic=1,
|
||||
|
@ -75,6 +75,7 @@ public:
|
|||
virtual ~tiff_reader();
|
||||
unsigned width() const;
|
||||
unsigned height() const;
|
||||
bool premultiplied_alpha() const;
|
||||
void read(unsigned x,unsigned y,image_data_32& image);
|
||||
private:
|
||||
tiff_reader(const tiff_reader&);
|
||||
|
@ -103,7 +104,8 @@ tiff_reader::tiff_reader(std::string const& file_name)
|
|||
height_(0),
|
||||
rows_per_strip_(0),
|
||||
tile_width_(0),
|
||||
tile_height_(0)
|
||||
tile_height_(0),
|
||||
premultiplied_alpha_(false)
|
||||
{
|
||||
init();
|
||||
}
|
||||
|
@ -132,6 +134,16 @@ void tiff_reader::init()
|
|||
{
|
||||
read_method_=stripped;
|
||||
}
|
||||
//TIFFTAG_EXTRASAMPLES
|
||||
uint16 extrasamples;
|
||||
uint16* sampleinfo;
|
||||
TIFFGetFieldDefaulted(tif, TIFFTAG_EXTRASAMPLES,
|
||||
&extrasamples, &sampleinfo);
|
||||
if (extrasamples == 1 &&
|
||||
sampleinfo[0] == EXTRASAMPLE_ASSOCALPHA)
|
||||
{
|
||||
premultiplied_alpha_ = true;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
|
@ -156,6 +168,10 @@ unsigned tiff_reader::height() const
|
|||
return height_;
|
||||
}
|
||||
|
||||
bool tiff_reader::premultiplied_alpha() const
|
||||
{
|
||||
return premultiplied_alpha_;
|
||||
}
|
||||
|
||||
void tiff_reader::read(unsigned x,unsigned y,image_data_32& image)
|
||||
{
|
||||
|
|
|
@ -24,19 +24,22 @@
|
|||
|
||||
#if BOOST_VERSION >= 104700
|
||||
|
||||
#include <mapnik/geometry.hpp>
|
||||
#include <mapnik/util/geometry_wkt_generator.hpp>
|
||||
#include <mapnik/util/vertex_iterator.hpp>
|
||||
#include <mapnik/util/path_iterator.hpp>
|
||||
#include <mapnik/util/container_adapter.hpp>
|
||||
|
||||
namespace mapnik { namespace util {
|
||||
|
||||
boost::tuple<unsigned,bool> detail::multi_geometry_type::operator() (geometry_container const& geom) const
|
||||
template <typename T>
|
||||
boost::tuple<unsigned,bool> detail::multi_geometry_type<T>::operator() (T const& geom) const
|
||||
{
|
||||
typedef T geometry_container;
|
||||
unsigned type = 0u;
|
||||
bool collection = false;
|
||||
|
||||
geometry_container::const_iterator itr = geom.begin();
|
||||
geometry_container::const_iterator end = geom.end();
|
||||
typename geometry_container::const_iterator itr = geom.begin();
|
||||
typename geometry_container::const_iterator end = geom.end();
|
||||
|
||||
for ( ; itr != end; ++itr)
|
||||
{
|
||||
|
@ -50,8 +53,8 @@ boost::tuple<unsigned,bool> detail::multi_geometry_type::operator() (geometry_co
|
|||
return boost::tuple<unsigned,bool>(type, collection);
|
||||
}
|
||||
|
||||
template <typename OutputIterator>
|
||||
wkt_generator<OutputIterator>::wkt_generator(bool single)
|
||||
template <typename OutputIterator, typename Geometry>
|
||||
wkt_generator<OutputIterator, Geometry>::wkt_generator(bool single)
|
||||
: wkt_generator::base_type(wkt)
|
||||
{
|
||||
using boost::spirit::karma::uint_;
|
||||
|
@ -86,15 +89,15 @@ wkt_generator<OutputIterator>::wkt_generator(bool single)
|
|||
<< lit("))")
|
||||
;
|
||||
|
||||
point_coord = &uint_ << coord_type << lit(' ') << coord_type
|
||||
point_coord = &uint_ << coordinate << lit(' ') << coordinate
|
||||
;
|
||||
|
||||
polygon_coord %= ( &uint_(mapnik::SEG_MOVETO) << eps[_r1 += 1]
|
||||
<< string[ if_ (_r1 > 1) [_1 = "),("]
|
||||
.else_[_1 = "("] ] | &uint_ << ",")
|
||||
<< coord_type
|
||||
<< coordinate
|
||||
<< lit(' ')
|
||||
<< coord_type
|
||||
<< coordinate
|
||||
;
|
||||
|
||||
coords2 %= *polygon_coord(_a)
|
||||
|
@ -104,8 +107,8 @@ wkt_generator<OutputIterator>::wkt_generator(bool single)
|
|||
;
|
||||
}
|
||||
|
||||
template <typename OutputIterator>
|
||||
wkt_multi_generator<OutputIterator>::wkt_multi_generator()
|
||||
template <typename OutputIterator, typename GeometryContainer>
|
||||
wkt_multi_generator<OutputIterator, GeometryContainer>::wkt_multi_generator()
|
||||
: wkt_multi_generator::base_type(wkt)
|
||||
{
|
||||
using boost::spirit::karma::lit;
|
||||
|
@ -138,8 +141,8 @@ wkt_multi_generator<OutputIterator>::wkt_multi_generator()
|
|||
|
||||
}
|
||||
|
||||
template struct mapnik::util::wkt_generator<std::back_insert_iterator<std::string> >;
|
||||
template struct mapnik::util::wkt_multi_generator<std::back_insert_iterator<std::string> >;
|
||||
template struct mapnik::util::wkt_generator<std::back_insert_iterator<std::string>, mapnik::geometry_type>;
|
||||
template struct mapnik::util::wkt_multi_generator<std::back_insert_iterator<std::string>, mapnik::geometry_container >;
|
||||
|
||||
|
||||
}}
|
||||
|
|
BIN
tests/data/raster/river.tiff
Normal file
BIN
tests/data/raster/river_merc.tiff
Normal file
BIN
tests/data/raster/river_wgs.tiff
Normal file
BIN
tests/data/raster/white-alpha-assoc-alpha-correct.tiff
Normal file
|
@ -1,7 +1,7 @@
|
|||
#!/usr/bin/env python
|
||||
|
||||
from nose.tools import *
|
||||
from utilities import execution_path, save_data, contains_word
|
||||
from utilities import execution_path, contains_word
|
||||
|
||||
import os, mapnik
|
||||
|
||||
|
@ -40,8 +40,6 @@ def test_multi_tile_policy():
|
|||
im = mapnik.Image(_map.width, _map.height)
|
||||
mapnik.render(_map, im)
|
||||
|
||||
save_data('test_multi_tile_policy.png', im.tostring('png'))
|
||||
|
||||
# test green chunk
|
||||
eq_(im.view(0,64,1,1).tostring(), '\x00\xff\x00\xff')
|
||||
eq_(im.view(127,64,1,1).tostring(), '\x00\xff\x00\xff')
|
||||
|
|
|
@ -1,7 +1,7 @@
|
|||
#!/usr/bin/env python
|
||||
|
||||
from nose.tools import *
|
||||
from utilities import execution_path, save_data, contains_word
|
||||
from utilities import execution_path, contains_word
|
||||
|
||||
import os, mapnik
|
||||
|
||||
|
@ -51,8 +51,6 @@ def test_dataraster_coloring():
|
|||
|
||||
im = mapnik.Image(_map.width,_map.height)
|
||||
mapnik.render(_map, im)
|
||||
# save a png somewhere so we can see it
|
||||
save_data('test_dataraster_coloring.png', im.tostring('png'))
|
||||
imdata = im.tostring()
|
||||
# we have some values in the [20,30) interval so check that they're colored
|
||||
assert contains_word('\xff\xff\x00\xff', imdata)
|
||||
|
@ -135,8 +133,6 @@ def test_raster_with_alpha_blends_correctly_with_background():
|
|||
mim = mapnik.Image(WIDTH, HEIGHT)
|
||||
|
||||
mapnik.render(map, mim)
|
||||
save_data('test_raster_with_alpha_blends_correctly_with_background.png',
|
||||
mim.tostring('png'))
|
||||
imdata = mim.tostring()
|
||||
# All white is expected
|
||||
assert contains_word('\xff\xff\xff\xff', imdata)
|
||||
|
@ -166,8 +162,6 @@ def test_raster_warping():
|
|||
|
||||
im = mapnik.Image(_map.width,_map.height)
|
||||
mapnik.render(_map, im)
|
||||
# save a png somewhere so we can see it
|
||||
save_data('test_raster_warping.png', im.tostring('png'))
|
||||
imdata = im.tostring()
|
||||
assert contains_word('\xff\xff\x00\xff', imdata)
|
||||
|
||||
|
@ -195,9 +189,6 @@ def test_raster_warping_does_not_overclip_source():
|
|||
|
||||
im = mapnik.Image(_map.width,_map.height)
|
||||
mapnik.render(_map, im)
|
||||
# save a png somewhere so we can see it
|
||||
save_data('test_raster_warping_does_not_overclip_source.png',
|
||||
im.tostring('png'))
|
||||
assert im.view(0,200,1,1).tostring()=='\xff\xff\x00\xff'
|
||||
|
||||
if __name__ == "__main__":
|
||||
|
|
|
@ -15,20 +15,6 @@ class TodoPlugin(ErrorClassPlugin):
|
|||
|
||||
todo = ErrorClass(Todo, label='TODO', isfailure=False)
|
||||
|
||||
def save_data(filename, data, key='MAPNIK_TEST_DATA_DIR'):
|
||||
"""Saves bytestring 'data' into os.environ[key]/filename if
|
||||
key in os.environ"""
|
||||
if key in os.environ:
|
||||
dir = os.environ[key]
|
||||
if not os.path.exists(dir):
|
||||
os.makedirs(dir)
|
||||
fname = os.path.join(dir, filename)
|
||||
f = open(fname, 'w')
|
||||
try:
|
||||
f.write(data)
|
||||
finally:
|
||||
f.close()
|
||||
|
||||
def contains_word(word, bytestring_):
|
||||
"""
|
||||
Checks that a bytestring contains a given word. len(bytestring) should be
|
||||
|
|
|
@ -24,6 +24,10 @@ def compare_pixels(pixel1, pixel2):
|
|||
else:
|
||||
return False
|
||||
|
||||
def fail(actual,expected,message):
|
||||
global errors
|
||||
errors.append((message, actual, expected))
|
||||
|
||||
# compare two images and return number of different pixels
|
||||
def compare(actual, expected):
|
||||
global errors
|
||||
|
@ -52,11 +56,14 @@ def compare(actual, expected):
|
|||
def summary(generate=False):
|
||||
global errors
|
||||
global passed
|
||||
print "-"*80
|
||||
print "Visual text rendering summary:",
|
||||
|
||||
if len(errors) != 0:
|
||||
for error in errors:
|
||||
if (error[0] is None):
|
||||
msg = "Visual text rendering: %s failures" % len(errors)
|
||||
print "-"*len(msg)
|
||||
print msg
|
||||
print "-"*len(msg)
|
||||
for idx,error in enumerate(errors):
|
||||
if error[0] is None:
|
||||
if generate:
|
||||
actual = open(error[1],'r').read()
|
||||
open(error[2],'wb').write(actual)
|
||||
|
@ -64,9 +71,14 @@ def summary(generate=False):
|
|||
continue
|
||||
else:
|
||||
print "Could not verify %s: No reference image found!" % error[1]
|
||||
else:
|
||||
print "Failed: %d different pixels:\n\t%s (actual)\n\t%s (expected)" % error
|
||||
elif isinstance(error[0],int):
|
||||
print str(idx+1) + ") \x1b[34m%s different pixels\x1b[0m:\n\t%s (\x1b[31mactual\x1b[0m)\n\t%s (\x1b[32mexpected\x1b[0m)" % error
|
||||
elif isinstance(error[0],str):
|
||||
print str(idx+1) + ") \x1b[31mfailure to run test:\x1b[0m %s" % error[0]
|
||||
sys.exit(1)
|
||||
else:
|
||||
print 'All %s tests passed: \x1b[1;32m✓ \x1b[0m' % passed
|
||||
msg = 'All %s visual tests passed: \x1b[1;32m✓ \x1b[0m' % passed
|
||||
print "-"*len(msg)
|
||||
print msg
|
||||
print "-"*len(msg)
|
||||
sys.exit(0)
|
||||
|
|
After Width: | Height: | Size: 4.3 KiB |
After Width: | Height: | Size: 4.3 KiB |
Before Width: | Height: | Size: 4.3 KiB After Width: | Height: | Size: 4.3 KiB |
Before Width: | Height: | Size: 4.3 KiB After Width: | Height: | Size: 4.3 KiB |
After Width: | Height: | Size: 10 KiB |
After Width: | Height: | Size: 10 KiB |
|
@ -0,0 +1,21 @@
|
|||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<!DOCTYPE Map[]>
|
||||
<Map srs="+proj=merc +a=6378137 +b=6378137 +lat_ts=0.0 +lon_0=0.0 +x_0=0.0 +y_0=0.0 +k=1.0 +units=m +nadgrids=@null +wktext +no_defs +over" background-color="red">
|
||||
|
||||
<Style name="white">
|
||||
<Rule>
|
||||
<RasterSymbolizer opacity="1" scaling="bilinear" comp-op="src-over"/>
|
||||
</Rule>
|
||||
</Style>
|
||||
<Layer name="white"
|
||||
srs="+proj=merc +a=6378137 +b=6378137 +lat_ts=0.0 +lon_0=0.0 +x_0=0.0 +y_0=0.0 +k=1.0 +units=m +nadgrids=@null +wktext +no_defs +over">
|
||||
<StyleName>white</StyleName>
|
||||
<Datasource>
|
||||
<!-- tiffinfo data/raster/white-alpha-assoc-alpha-wrong.tiff reports 'Extra Samples: 1<assoc-alpha>' which is incorrect -->
|
||||
<!-- https://github.com/mapnik/mapnik/issues/1511 -->
|
||||
<Parameter name="file">../../data/raster/white-alpha-assoc-alpha-wrong.tiff</Parameter>
|
||||
<Parameter name="type">gdal</Parameter>
|
||||
</Datasource>
|
||||
</Layer>
|
||||
|
||||
</Map>
|
|
@ -0,0 +1,22 @@
|
|||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<!DOCTYPE Map[]>
|
||||
<Map srs="+proj=merc +a=6378137 +b=6378137 +lat_ts=0.0 +lon_0=0.0 +x_0=0.0 +y_0=0.0 +k=1.0 +units=m +nadgrids=@null +wktext +no_defs +over" background-color="red">
|
||||
|
||||
<Style name="white">
|
||||
<Rule>
|
||||
<RasterSymbolizer opacity="1" scaling="bilinear" comp-op="src-over"/>
|
||||
</Rule>
|
||||
</Style>
|
||||
<Layer name="white"
|
||||
srs="+proj=merc +a=6378137 +b=6378137 +lat_ts=0.0 +lon_0=0.0 +x_0=0.0 +y_0=0.0 +k=1.0 +units=m +nadgrids=@null +wktext +no_defs +over">
|
||||
<StyleName>white</StyleName>
|
||||
<Datasource>
|
||||
<!-- tiffinfo data/raster/white-alpha-assoc-alpha-wrong.tiff reports 'Extra Samples: 1<assoc-alpha>' which is incorrect -->
|
||||
<!-- https://github.com/mapnik/mapnik/issues/1511 -->
|
||||
<Parameter name="file">../../data/raster/white-alpha-assoc-alpha-wrong.tiff</Parameter>
|
||||
<Parameter name="type">raster</Parameter>
|
||||
<Parameter name="extent">1001859.9561,5922814.94334,1021141.75555,5942096.74279</Parameter>
|
||||
</Datasource>
|
||||
</Layer>
|
||||
|
||||
</Map>
|
|
@ -11,7 +11,7 @@
|
|||
srs="+proj=merc +a=6378137 +b=6378137 +lat_ts=0.0 +lon_0=0.0 +x_0=0.0 +y_0=0.0 +k=1.0 +units=m +nadgrids=@null +wktext +no_defs +over">
|
||||
<StyleName>white</StyleName>
|
||||
<Datasource>
|
||||
<Parameter name="file">../../data/raster/white-alpha.tiff</Parameter>
|
||||
<Parameter name="file">../../data/raster/white-alpha-assoc-alpha-correct.tiff</Parameter>
|
||||
<Parameter name="type">gdal</Parameter>
|
||||
</Datasource>
|
||||
</Layer>
|
||||
|
|
|
@ -11,7 +11,7 @@
|
|||
srs="+proj=merc +a=6378137 +b=6378137 +lat_ts=0.0 +lon_0=0.0 +x_0=0.0 +y_0=0.0 +k=1.0 +units=m +nadgrids=@null +wktext +no_defs +over">
|
||||
<StyleName>white</StyleName>
|
||||
<Datasource>
|
||||
<Parameter name="file">../../data/raster/white-alpha.tiff</Parameter>
|
||||
<Parameter name="file">../../data/raster/white-alpha-assoc-alpha-correct.tiff</Parameter>
|
||||
<Parameter name="type">raster</Parameter>
|
||||
<Parameter name="extent">1001859.9561,5922814.94334,1021141.75555,5942096.74279</Parameter>
|
||||
</Datasource>
|
||||
|
|
17
tests/visual_tests/styles/tiff-opaque-edge-gdal.xml
Normal file
|
@ -0,0 +1,17 @@
|
|||
<Map srs="+init=EPSG:4326" background-color="white">
|
||||
|
||||
<Style name="test">
|
||||
<Rule>
|
||||
<RasterSymbolizer scaling="bilinear" />
|
||||
</Rule>
|
||||
</Style>
|
||||
|
||||
<Layer name="test" srs="+init=EPSG:4326">
|
||||
<StyleName>test</StyleName>
|
||||
<Datasource>
|
||||
<Parameter name="file">../../data/raster/river.tiff</Parameter>
|
||||
<Parameter name="type">gdal</Parameter>
|
||||
</Datasource>
|
||||
</Layer>
|
||||
|
||||
</Map>
|
18
tests/visual_tests/styles/tiff-opaque-edge-raster.xml
Normal file
|
@ -0,0 +1,18 @@
|
|||
<Map srs="+init=EPSG:4326" background-color="white">
|
||||
|
||||
<Style name="test">
|
||||
<Rule>
|
||||
<RasterSymbolizer scaling="bilinear" />
|
||||
</Rule>
|
||||
</Style>
|
||||
|
||||
<Layer name="test" srs="+init=EPSG:4326">
|
||||
<StyleName>test</StyleName>
|
||||
<Datasource>
|
||||
<Parameter name="file">../../data/raster/river.tiff</Parameter>
|
||||
<Parameter name="type">raster</Parameter>
|
||||
<Parameter name="extent">0,0,256,210</Parameter>
|
||||
</Datasource>
|
||||
</Layer>
|
||||
|
||||
</Map>
|
|
@ -2,9 +2,11 @@
|
|||
# -*- coding: utf-8 -*-
|
||||
|
||||
import mapnik
|
||||
mapnik.logger.set_severity(mapnik.severity_type.None)
|
||||
|
||||
import sys
|
||||
import os.path
|
||||
from compare import compare, summary
|
||||
from compare import compare, summary, fail
|
||||
|
||||
defaults = {
|
||||
'sizes': [(500, 100)]
|
||||
|
@ -51,9 +53,13 @@ files = [
|
|||
{'name': "line-offset", 'sizes':[(900, 250)],'bbox': mapnik.Box2d(-5.192, 50.189, -5.174, 50.195)},
|
||||
{'name': "tiff-alpha-gdal", 'sizes':[(600,400)]},
|
||||
{'name': "tiff-alpha-raster", 'sizes':[(600,400)]},
|
||||
{'name': "tiff-alpha-broken-assoc-alpha-gdal", 'sizes':[(600,400)]},
|
||||
{'name': "tiff-alpha-broken-assoc-alpha-raster", 'sizes':[(600,400)]},
|
||||
{'name': "tiff-alpha-gradient-gdal", 'sizes':[(600,400)]},
|
||||
{'name': "tiff-nodata-edge-gdal", 'sizes':[(600,400)]},
|
||||
{'name': "tiff-nodata-edge-raster", 'sizes':[(600,400)]},
|
||||
{'name': "tiff-opaque-edge-gdal", 'sizes':[(256,256)]},
|
||||
{'name': "tiff-opaque-edge-raster", 'sizes':[(256,256)]},
|
||||
{'name': "shieldsymbolizer-2"},
|
||||
{'name': "shieldsymbolizer-3"},
|
||||
{'name': "shieldsymbolizer-4"},
|
||||
|
@ -65,25 +71,28 @@ files = [
|
|||
|
||||
def render(filename, width, height, bbox, quiet=False):
|
||||
if not quiet:
|
||||
print "Rendering style \"%s\" with size %dx%d ... \x1b[1;32m✓ \x1b[0m" % (filename, width, height)
|
||||
print "-"*80
|
||||
print "\"%s\" with size %dx%d ..." % (filename, width, height),
|
||||
m = mapnik.Map(width, height)
|
||||
mapnik.load_map(m, os.path.join(dirname, "styles", "%s.xml" % filename), False)
|
||||
if bbox is not None:
|
||||
m.zoom_to_box(bbox)
|
||||
else:
|
||||
m.zoom_all()
|
||||
expected = os.path.join(dirname, "images", '%s-%d-reference.png' % (filename, width))
|
||||
if not os.path.exists('/tmp/mapnik-visual-images'):
|
||||
os.makedirs('/tmp/mapnik-visual-images')
|
||||
actual = os.path.join("/tmp/mapnik-visual-images", '%s-%d-agg.png' % (filename, width))
|
||||
mapnik.render_to_file(m, actual)
|
||||
diff = compare(actual, expected)
|
||||
if diff > 0:
|
||||
print "-"*80
|
||||
print '\x1b[33mError:\x1b[0m %u different pixels' % diff
|
||||
print "-"*80
|
||||
|
||||
try:
|
||||
mapnik.load_map(m, os.path.join(dirname, "styles", "%s.xml" % filename), False)
|
||||
if bbox is not None:
|
||||
m.zoom_to_box(bbox)
|
||||
else:
|
||||
m.zoom_all()
|
||||
if not os.path.exists('/tmp/mapnik-visual-images'):
|
||||
os.makedirs('/tmp/mapnik-visual-images')
|
||||
mapnik.render_to_file(m, actual)
|
||||
diff = compare(actual, expected)
|
||||
if not quiet:
|
||||
if diff > 0:
|
||||
print '\x1b[31m✘\x1b[0m (\x1b[34m%u different pixels\x1b[0m)' % diff
|
||||
else:
|
||||
print '\x1b[32m✓\x1b[0m'
|
||||
except Exception, e:
|
||||
sys.stderr.write(e.message + '\n')
|
||||
fail(actual,expected,str(e.message))
|
||||
return m
|
||||
|
||||
if __name__ == "__main__":
|
||||
|
|