mirror of
https://github.com/mapnik/mapnik.git
synced 2025-12-08 20:13:09 +00:00
initial image_data_any implentation (work-in-progress)
This commit is contained in:
parent
33c1d21b7f
commit
bf9c99e3d3
@ -41,7 +41,14 @@ struct buffer
|
||||
data_(static_cast<unsigned char*>(size_ != 0 ? ::operator new(size_) : nullptr))
|
||||
{}
|
||||
|
||||
buffer(buffer && rhs) noexcept = default;
|
||||
buffer(buffer && rhs) noexcept
|
||||
: size_(std::move(rhs.size_)),
|
||||
data_(std::move(rhs.data_))
|
||||
{
|
||||
rhs.size_ = 0;
|
||||
rhs.data_ = nullptr;
|
||||
}
|
||||
|
||||
buffer(buffer const& rhs)
|
||||
: size_(rhs.size_),
|
||||
data_(rhs.data_)
|
||||
@ -184,6 +191,7 @@ private:
|
||||
|
||||
using image_data_32 = image_data<std::uint32_t>;
|
||||
using image_data_8 = image_data<byte> ;
|
||||
using image_data_float32 = image_data<float>;
|
||||
}
|
||||
|
||||
#endif // MAPNIK_IMAGE_DATA_HPP
|
||||
|
||||
@ -27,26 +27,99 @@
|
||||
#include <mapnik/box2d.hpp>
|
||||
#include <mapnik/image_data.hpp>
|
||||
#include <mapnik/noncopyable.hpp>
|
||||
|
||||
#include <mapnik/util/variant.hpp>
|
||||
// boost
|
||||
#include <boost/optional.hpp>
|
||||
|
||||
namespace mapnik {
|
||||
|
||||
using image_data_base = util::variant<image_data_32, image_data_8, image_data_float32>;
|
||||
|
||||
namespace detail {
|
||||
|
||||
struct get_bytes_visitor : util::static_visitor<unsigned char*>
|
||||
{
|
||||
template <typename T>
|
||||
unsigned char* operator()(T & data)
|
||||
{
|
||||
return data.getBytes();
|
||||
}
|
||||
};
|
||||
|
||||
struct get_bytes_visitor_const : util::static_visitor<unsigned char const*>
|
||||
{
|
||||
template <typename T>
|
||||
unsigned char const* operator()(T const& data) const
|
||||
{
|
||||
return data.getBytes();
|
||||
}
|
||||
};
|
||||
|
||||
struct get_width_visitor : util::static_visitor<std::size_t>
|
||||
{
|
||||
template <typename T>
|
||||
std::size_t operator()(T const& data) const
|
||||
{
|
||||
return data.width();
|
||||
}
|
||||
};
|
||||
|
||||
struct get_height_visitor : util::static_visitor<std::size_t>
|
||||
{
|
||||
template <typename T>
|
||||
std::size_t operator()(T const& data) const
|
||||
{
|
||||
return data.height();
|
||||
}
|
||||
};
|
||||
|
||||
|
||||
} // namespace detail
|
||||
|
||||
struct image_data_any : image_data_base
|
||||
{
|
||||
template <typename T>
|
||||
image_data_any(T && data) noexcept
|
||||
: image_data_base(std::move(data)) {}
|
||||
|
||||
unsigned char const* getBytes() const
|
||||
{
|
||||
return util::apply_visitor(detail::get_bytes_visitor_const(),*this);
|
||||
}
|
||||
|
||||
unsigned char* getBytes()
|
||||
{
|
||||
return util::apply_visitor(detail::get_bytes_visitor(),*this);
|
||||
}
|
||||
|
||||
std::size_t width() const
|
||||
{
|
||||
return util::apply_visitor(detail::get_width_visitor(),*this);
|
||||
}
|
||||
|
||||
std::size_t height() const
|
||||
{
|
||||
return util::apply_visitor(detail::get_height_visitor(),*this);
|
||||
}
|
||||
};
|
||||
|
||||
|
||||
class raster : private mapnik::noncopyable
|
||||
{
|
||||
public:
|
||||
box2d<double> ext_;
|
||||
image_data_32 data_;
|
||||
image_data_any data_;
|
||||
double filter_factor_;
|
||||
bool premultiplied_alpha_;
|
||||
boost::optional<double> nodata_;
|
||||
|
||||
template <typename ImageData>
|
||||
raster(box2d<double> const& ext,
|
||||
unsigned width,
|
||||
unsigned height,
|
||||
ImageData && data,
|
||||
double filter_factor,
|
||||
bool premultiplied_alpha = false)
|
||||
: ext_(ext),
|
||||
data_(width,height),
|
||||
data_(std::move(data)),
|
||||
filter_factor_(filter_factor),
|
||||
premultiplied_alpha_(premultiplied_alpha) {}
|
||||
|
||||
|
||||
@ -86,7 +86,8 @@ void render_raster_symbolizer(raster_symbolizer const &sym,
|
||||
{
|
||||
double offset_x = ext.minx() - start_x;
|
||||
double offset_y = ext.miny() - start_y;
|
||||
raster target(target_ext, raster_width, raster_height, source->get_filter_factor());
|
||||
image_data_32 data(raster_width, raster_height);
|
||||
raster target(target_ext, data, source->get_filter_factor());
|
||||
unsigned mesh_size = static_cast<unsigned>(get<value_integer>(sym,keys::mesh_size,feature, common.vars_, 16));
|
||||
reproject_and_scale_raster(target,
|
||||
*source,
|
||||
@ -95,7 +96,10 @@ void render_raster_symbolizer(raster_symbolizer const &sym,
|
||||
offset_y,
|
||||
mesh_size,
|
||||
scaling_method);
|
||||
composite(target.data_, comp_op, opacity, start_x, start_y);
|
||||
if (target.data_.is<image_data_32>())
|
||||
{
|
||||
composite(util::get<image_data_32>(target.data_), comp_op, opacity, start_x, start_y);
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
@ -107,20 +111,27 @@ void render_raster_symbolizer(raster_symbolizer const &sym,
|
||||
(std::abs(start_x) <= eps) &&
|
||||
(std::abs(start_y) <= eps) )
|
||||
{
|
||||
composite(source->data_, comp_op, opacity, start_x, start_y);
|
||||
if (source->data_.is<image_data_32>())
|
||||
{
|
||||
composite(util::get<image_data_32>(source->data_), comp_op, opacity, start_x, start_y);
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
raster target(target_ext, raster_width, raster_height, source->get_filter_factor());
|
||||
scale_image_agg<image_data_32>(target.data_,
|
||||
source->data_,
|
||||
scaling_method,
|
||||
image_ratio_x,
|
||||
image_ratio_y,
|
||||
0.0,
|
||||
0.0,
|
||||
source->get_filter_factor());
|
||||
composite(target.data_, comp_op, opacity, start_x, start_y);
|
||||
if (source->data_.is<image_data_32>())
|
||||
{
|
||||
image_data_32 data(raster_width, raster_height);
|
||||
raster target(target_ext, data, source->get_filter_factor());
|
||||
scale_image_agg<image_data_32>(util::get<image_data_32>(target.data_),
|
||||
util::get<image_data_32>(source->data_),
|
||||
scaling_method,
|
||||
image_ratio_x,
|
||||
image_ratio_y,
|
||||
0.0,
|
||||
0.0,
|
||||
source->get_filter_factor());
|
||||
composite(util::get<image_data_32>(target.data_), comp_op, opacity, start_x, start_y);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@ -199,9 +199,10 @@ feature_ptr gdal_featureset::get_feature(mapnik::query const& q)
|
||||
|
||||
if (im_width > 0 && im_height > 0)
|
||||
{
|
||||
mapnik::raster_ptr raster = std::make_shared<mapnik::raster>(intersect, im_width, im_height, filter_factor);
|
||||
mapnik::image_data_32 data(im_width, im_height);
|
||||
mapnik::raster_ptr raster = std::make_shared<mapnik::raster>(intersect, data, filter_factor);
|
||||
feature->set_raster(raster);
|
||||
mapnik::image_data_32 & image = raster->data_;
|
||||
mapnik::image_data_32 & image = mapnik::util::get<mapnik::image_data_32>(raster->data_);
|
||||
image.set(0xffffffff);
|
||||
|
||||
MAPNIK_LOG_DEBUG(gdal) << "gdal_featureset: Image Size=(" << im_width << "," << im_height << ")";
|
||||
|
||||
@ -28,6 +28,7 @@
|
||||
#include <mapnik/image_reader.hpp>
|
||||
#include <mapnik/image_util.hpp>
|
||||
#include <mapnik/feature_factory.hpp>
|
||||
#include <mapnik/util/variant.hpp>
|
||||
|
||||
// boost
|
||||
#pragma GCC diagnostic push
|
||||
@ -113,9 +114,9 @@ feature_ptr raster_featureset<LookupPolicy>::next()
|
||||
rem.maxx() + x_off + width,
|
||||
rem.maxy() + y_off + height);
|
||||
intersect = t.backward(feature_raster_extent);
|
||||
|
||||
mapnik::raster_ptr raster = std::make_shared<mapnik::raster>(intersect, width, height, 1.0);
|
||||
reader->read(x_off, y_off, raster->data_);
|
||||
image_data_32 data(width,height);
|
||||
reader->read(x_off, y_off, data);
|
||||
mapnik::raster_ptr raster = std::make_shared<mapnik::raster>(intersect, data, 1.0);
|
||||
raster->premultiplied_alpha_ = reader->premultiplied_alpha();
|
||||
feature->set_raster(raster);
|
||||
}
|
||||
|
||||
@ -124,14 +124,14 @@ bool raster_colorizer::add_stop(colorizer_stop const& stop)
|
||||
|
||||
void raster_colorizer::colorize(raster_ptr const& raster, feature_impl const& f) const
|
||||
{
|
||||
unsigned *imageData = raster->data_.getData();
|
||||
unsigned* imageData = reinterpret_cast<unsigned*>(raster->data_.getBytes());
|
||||
|
||||
int len = raster->data_.width() * raster->data_.height();
|
||||
boost::optional<double> const& nodata = raster->nodata();
|
||||
for (int i=0; i<len; ++i)
|
||||
{
|
||||
// the GDAL plugin reads single bands as floats
|
||||
float value = *reinterpret_cast<float *> (&imageData[i]);
|
||||
float value = *reinterpret_cast<float*> (&imageData[i]);
|
||||
if (nodata && (std::fabs(value - *nodata) < epsilon_))
|
||||
{
|
||||
imageData[i] = 0;
|
||||
|
||||
@ -83,7 +83,7 @@ void reproject_and_scale_raster(raster & target, raster const& source,
|
||||
|
||||
agg::rasterizer_scanline_aa<> rasterizer;
|
||||
agg::scanline_bin scanline;
|
||||
agg::rendering_buffer buf((unsigned char*)target.data_.getData(),
|
||||
agg::rendering_buffer buf(target.data_.getBytes(),
|
||||
target.data_.width(),
|
||||
target.data_.height(),
|
||||
target.data_.width()*4);
|
||||
@ -91,7 +91,7 @@ void reproject_and_scale_raster(raster & target, raster const& source,
|
||||
renderer_base rb(pixf);
|
||||
rasterizer.clip_box(0, 0, target.data_.width(), target.data_.height());
|
||||
agg::rendering_buffer buf_tile(
|
||||
(unsigned char*)source.data_.getData(),
|
||||
const_cast<unsigned char*>(source.data_.getBytes()),
|
||||
source.data_.width(),
|
||||
source.data_.height(),
|
||||
source.data_.width() * 4);
|
||||
|
||||
Loading…
x
Reference in New Issue
Block a user