From d26fc722d5c2f18f8da8b6640949c352fa414469 Mon Sep 17 00:00:00 2001 From: Artem Pavlenko Date: Fri, 7 Feb 2020 13:53:06 +0000 Subject: [PATCH] Add SVG renderer unit test - both inline and css styled octocat result in identical image (ref PR #4123) --- test/data | 2 +- test/unit/svg/svg_renderer_test.cpp | 109 ++++++++++++++++++++++++++++ 2 files changed, 110 insertions(+), 1 deletion(-) create mode 100644 test/unit/svg/svg_renderer_test.cpp diff --git a/test/data b/test/data index c3982b766..e83b7f7c6 160000 --- a/test/data +++ b/test/data @@ -1 +1 @@ -Subproject commit c3982b76602bcbfea6403793ac2f3fab44552270 +Subproject commit e83b7f7c6d2d646a638bba404a0d637609722a09 diff --git a/test/unit/svg/svg_renderer_test.cpp b/test/unit/svg/svg_renderer_test.cpp new file mode 100644 index 000000000..91988dd1d --- /dev/null +++ b/test/unit/svg/svg_renderer_test.cpp @@ -0,0 +1,109 @@ +/***************************************************************************** + * + * This file is part of Mapnik (c++ mapping toolkit) + * + * Copyright (C) 2020 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 + * + *****************************************************************************/ + +#include "catch.hpp" + +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include + +#pragma GCC diagnostic push +#include +#include "agg_rasterizer_scanline_aa.h" +#include "agg_basics.h" +#include "agg_rendering_buffer.h" +#include "agg_renderer_base.h" +#include "agg_pixfmt_rgba.h" +#include "agg_scanline_u.h" +#pragma GCC diagnostic pop + +namespace +{ + +mapnik::image_rgba8 render_svg(std::string const& filename, double scale_factor) +{ + using pixfmt = agg::pixfmt_rgba32_pre; + using renderer_base = agg::renderer_base; + using renderer_solid = agg::renderer_scanline_aa_solid; + + agg::rasterizer_scanline_aa<> ras_ptr; + agg::scanline_u8 sl; + std::shared_ptr marker = mapnik::marker_cache::instance().find(filename, false); + mapnik::marker_svg const& svg = mapnik::util::get(*marker); + double svg_width, svg_height ; + std::tie(svg_width, svg_height) = svg.dimensions(); + int image_width = static_cast(std::round(svg_width)); + int image_height = static_cast(std::round(svg_height)); + + mapnik::image_rgba8 im(image_width, image_height, true, true); + agg::rendering_buffer buf(im.bytes(), im.width(), im.height(), im.row_size()); + pixfmt pixf(buf); + renderer_base renb(pixf); + + agg::trans_affine mtx = agg::trans_affine_translation(-0.5 * svg_width, -0.5 * svg_height); + mtx.scale(scale_factor); + mtx.translate(0.5 * svg_width, 0.5 * svg_height); + + mapnik::svg::vertex_stl_adapter stl_storage(svg.get_data()->source()); + mapnik::svg::svg_path_adapter svg_path(stl_storage); + mapnik::svg::renderer_agg renderer(svg_path, + svg.get_data()->attributes()); + double opacity = 1.0; + renderer.render(ras_ptr, sl, renb, mtx, opacity, {0, 0, svg_width, svg_height}); + return im; +} + +bool equal(mapnik::image_rgba8 const& im1, mapnik::image_rgba8 const& im2) +{ + if (im1.width() != im2.width() || im1.height() != im2.height()) + return false; + + for(auto tup : boost::combine(im1, im2)) + { + if (boost::get<0>(tup) != boost::get<1>(tup)) return false; + } + return true; +} +} + +TEST_CASE("SVG renderer") { + + SECTION("SVG octocat inline/css") + { + double scale_factor = 1.0; + std::string octocat_inline("./test/data/svg/octocat.svg"); + std::string octocat_css("./test/data/svg/octocat-css.svg"); + auto image1 = render_svg(octocat_inline, 1.0); + auto image2 = render_svg(octocat_css, 1.0); + REQUIRE(equal(image1, image2)); + } +}