Compare commits

..

1 commit

Author SHA1 Message Date
Dane Springmeyer
a378f07569 test clang 4.0.1 on travis 2017-08-24 08:28:24 -07:00
2566 changed files with 74104 additions and 516978 deletions

View file

@ -1,94 +0,0 @@
Language: Cpp
AccessModifierOffset: -2
AlignAfterOpenBracket: Align
AlignArrayOfStructures: None
AlignConsecutiveAssignments: None
AlignConsecutiveDeclarations: None
AlignConsecutiveMacros: Consecutive
AlignEscapedNewlines: Right
AlignOperands: Align
AlignTrailingComments: true
AllowAllArgumentsOnNextLine: false
AllowAllParametersOfDeclarationOnNextLine: false
AllowShortBlocksOnASingleLine: Empty
AllowShortCaseLabelsOnASingleLine: false
AllowShortEnumsOnASingleLine: true
AllowShortFunctionsOnASingleLine: Inline
AllowShortIfStatementsOnASingleLine: Never
AllowShortLambdasOnASingleLine: Inline
# AlwaysBreakAfterReturnType:
AlwaysBreakBeforeMultilineStrings: false
AlwaysBreakTemplateDeclarations: Yes
BinPackArguments: false
BitFieldColonSpacing: After
BreakBeforeBraces: Custom
BraceWrapping:
AfterCaseLabel: false
AfterClass: true
AfterControlStatement: Always
AfterEnum: false # see AllowShortEnumsOnASingleLine
AfterFunction: true # see AllowShortFunctionsOnASingleLine
AfterNamespace: false
AfterStruct: true
AfterExternBlock: false
BeforeCatch: true
BeforeElse: true
BeforeLambdaBody: false
BeforeWhile: false
SplitEmptyFunction: false
SplitEmptyRecord: false
SplitEmptyNamespace: false
BreakBeforeBinaryOperators: None
BreakBeforeConceptDeclarations: false
BreakBeforeTernaryOperators: true
BreakConstructorInitializers: BeforeComma
BreakInheritanceList: AfterComma
BreakStringLiterals: true
ColumnLimit: 120
CompactNamespaces: false
ContinuationIndentWidth: 2
Cpp11BracedListStyle: true
DeriveLineEnding: true
EmptyLineAfterAccessModifier: Leave
EmptyLineBeforeAccessModifier: LogicalBlock
FixNamespaceComments: true
IncludeBlocks: Preserve
IndentCaseBlocks: false
IndentCaseLabels: true
IndentExternBlock: NoIndent
IndentPPDirectives: None
IndentRequires: true
IndentWidth: 4
IndentWrappedFunctionNames: true
KeepEmptyLinesAtTheStartOfBlocks: false
LambdaBodyIndentation: Signature
MaxEmptyLinesToKeep: 1
NamespaceIndentation: None
# PackConstructorInitializers: CurrentLine # only clang-format > 14
PointerAlignment: Left
#QualifierAlignment: Left # only clang-format > 14
ReferenceAlignment: Left
ReflowComments: true
SortIncludes: Never
SpaceAfterLogicalNot: false
SpaceAfterTemplateKeyword: false
SpaceBeforeInheritanceColon: true
Standard: c++14
BinPackParameters: false
BreakBeforeInheritanceComma: false
IncludeCategories:
# Headers in <> without extension.
- Regex: '<([A-Za-z0-9\Q/-_\E])+>'
Priority: 1
# Headers in <> from specific external libraries.
- Regex: '<(boost)\/'
Priority: 2
# Headers in <> from specific external libraries.
- Regex: '<(mapnik)\/'
Priority: 3
# Headers in <> with extension.
- Regex: '<([A-Za-z0-9.\Q/-_\E])+>'
Priority: 4
# Headers in "" with extension.
- Regex: '"([A-Za-z0-9.\Q/-_\E])+"'
Priority: 5

1
.gitattributes vendored
View file

@ -1,2 +1 @@
*.svg text eol=lf *.svg text eol=lf
scons/** linguist-vendored

View file

@ -1,85 +0,0 @@
name: Run tests with coverage
description: Runs all mapnik tests with coverage
inputs:
cmake-preset:
description: The used CMake preset
required: true
runs:
using: composite
steps:
- name: Set PROJ_LIB
shell: bash
run: |
cmake --preset ${{ inputs.cmake-preset }} -N -L | grep -o "PROJ_LIB=.*" >> ${GITHUB_ENV}
- name: Set TEST_WRAPPER (Windows)
if: runner.os == 'Windows'
shell: bash
run: |-
echo "TEST_WRAPPER=OpenCppCoverage \
--cover_children \
--export_type binary \
--modules '*.input' \
--modules '*libmapnik*' \
--modules 'mapnik*.exe' \
--quiet \
--sources '${{ github.workspace }}' \
--" >> ${GITHUB_ENV}
- name: Test
shell: bash
env:
UPDATE: 1
run: |
${TEST_WRAPPER:-} ctest --preset ${{ inputs.cmake-preset }}
- name: Test visuals
continue-on-error: true
working-directory: build/out
shell: bash
run: |
${TEST_WRAPPER:-} ./mapnik-test-visual -j ${CTEST_PARALLEL_LEVEL} --output-dir visual-test-result
- name: Pack visual test results
working-directory: build/out
shell: bash
run: |
tar -vzcf visual-test-results.tar.gz visual-test-result
- name: Upload visual test results
uses: actions/upload-artifact@v4
with:
name: ${{ inputs.cmake-preset }}-visual-tests-${{ github.sha }}
path: build/out/visual-test-results.tar.gz
- name: Run Benchmarks (Linux & macOS)
working-directory: build/out
if: runner.os != 'Windows'
shell: bash
run: |
./run_benchmarks
- name: Collect coverage (Linux & macOS)
working-directory: build
if: runner.os != 'Windows'
shell: bash
run: |
if [ "${RUNNER_OS}" == "macOS" ]; then
LCOV_EXTRA_OPTIONS="--ignore-errors count,gcov,inconsistent,range,unused --keep-going"
fi
lcov ${LCOV_EXTRA_OPTIONS:-} --directory . --capture --output-file coverage.info
lcov ${LCOV_EXTRA_OPTIONS:-} --remove coverage.info '/usr/*' '*/vcpkg_installed/*' '/.cache/*' '*/test/*' --output-file coverage.info
lcov ${LCOV_EXTRA_OPTIONS:-} --list coverage.info
- name: Upload coverage to Codecov (Linux & macOS)
if: runner.os != 'Windows'
uses: codecov/codecov-action@v4
with:
files: build/coverage.info
- name: Upload coverage to Codecov (Windows)
if: runner.os == 'Windows'
uses: codecov/codecov-action@v4
with:
files: ctest.cov,build/out/mapnik-test-visual.cov

View file

@ -1,136 +0,0 @@
name: Build and Test
on:
push:
branches:
- "*"
pull_request:
branches-ignore:
- "no-ci-*"
env:
VCPKG_BINARY_SOURCES: clear;x-gha,readwrite
VCPKG_RELEASE: 2024.06.15
jobs:
checkSource:
name: Check Source Code
runs-on: ubuntu-22.04
steps:
- uses: actions/checkout@v4
- uses: actions/setup-python@v5
with:
python-version: "3.10"
- uses: pre-commit/action@v3.0.1
buildAndTest:
name: >-
Build & Test
(${{ matrix.os }})
(C++ ${{ matrix.cxx-standard }})
${{ startsWith(matrix.os, 'macos-') && (matrix.os == 'macos-14' && '(ARM64)' || '(AMD64)') || '' }}
needs: checkSource
runs-on: ${{ matrix.os }}
strategy:
fail-fast: false
matrix:
os:
- macos-14
- ubuntu-22.04
- windows-2022
cxx-standard:
- 17
steps:
- name: Checkout Mapnik
uses: actions/checkout@v4
with:
submodules: recursive
- name: Checkout vcpkg
uses: actions/checkout@v4
with:
path: vcpkg
ref: ${{ env.VCPKG_RELEASE }}
repository: microsoft/vcpkg
- name: Export GitHub Actions cache environment variables
uses: actions/github-script@v7
with:
script: |
core.exportVariable('ACTIONS_CACHE_URL', process.env.ACTIONS_CACHE_URL || '');
core.exportVariable('ACTIONS_RUNTIME_TOKEN', process.env.ACTIONS_RUNTIME_TOKEN || '');
- name: Install required system packages
shell: bash
run: |
if [ "${RUNNER_OS}" == "Linux" ]; then
sudo apt-get update
sudo apt-get -y install \
autoconf \
autoconf-archive \
automake \
gperf \
lcov \
libxxf86vm-dev \
ninja-build \
postgresql-client
elif [ "${RUNNER_OS}" == "macOS" ]; then
brew install \
autoconf \
autoconf-archive \
automake \
lcov \
libtool \
ninja \
vcpkg
elif [ "${RUNNER_OS}" == "Windows" ]; then
choco install \
ninja \
OpenCppCoverage
echo "C:\Program Files\OpenCppCoverage" >> ${GITHUB_PATH}
fi
- name: Enable Developer Command Prompt (Windows)
uses: ilammy/msvc-dev-cmd@v1
if: runner.os == 'Windows'
- name: Set CMAKE_BUILD_PARALLEL_LEVEL, CTEST_PARALLEL_LEVEL & PRESET
shell: bash
run: |
PRESET=$(echo "${RUNNER_OS}" | perl -ne "print lc")-ci
if [ "${RUNNER_OS}" == "Linux" ]; then
echo "CMAKE_BUILD_PARALLEL_LEVEL=$(nproc)" >> ${GITHUB_ENV}
echo "CTEST_PARALLEL_LEVEL=$(nproc)" >> ${GITHUB_ENV}
elif [ "${RUNNER_OS}" == "macOS" ]; then
echo "CMAKE_BUILD_PARALLEL_LEVEL=$(sysctl -n hw.logicalcpu)" >> ${GITHUB_ENV}
echo "CTEST_PARALLEL_LEVEL=$(sysctl -n hw.logicalcpu)" >> ${GITHUB_ENV}
PRESET=${PRESET}-${{ matrix.os == 'macos-14' && 'arm64' || 'x64' }}
elif [ "${RUNNER_OS}" == "Windows" ]; then
echo "CMAKE_BUILD_PARALLEL_LEVEL=$(pwsh -Command '(Get-CimInstance -ClassName Win32_ComputerSystem).NumberOfLogicalProcessors')" >> ${GITHUB_ENV}
echo "CTEST_PARALLEL_LEVEL=$(pwsh -Command '(Get-CimInstance -ClassName Win32_ComputerSystem).NumberOfLogicalProcessors')" >> ${GITHUB_ENV}
fi
echo "PRESET=${PRESET}" >> ${GITHUB_ENV}
- name: Configure CMake
shell: bash
run: |
cmake \
-DBUILD_SHARED_LIBS:BOOL=ON \
-DCMAKE_CXX_STANDARD:STRING=${{ matrix.cxx-standard }} \
-DUSE_MEMORY_MAPPED_FILE:BOOL=ON \
-LA \
--preset ${PRESET}
- name: Build
shell: bash
run: |
cmake \
--build \
--preset ${PRESET}
- name: Run Tests
uses: ./.github/actions/run_tests
with:
cmake-preset: ${{ env.PRESET }}

View file

@ -1,55 +0,0 @@
name: Release Linux
on:
push:
branches:
- "*"
pull_request:
branches-ignore:
- "no-ci-*"
env:
PRESET: linux-ci-release
jobs:
build:
runs-on: "ubuntu-22.04"
steps:
- name: checkout mapnik
uses: actions/checkout@v4
with:
submodules: "recursive"
- name: "Install required system packages"
shell: bash
run: |
sudo apt update
sudo apt install -y ninja-build\
libicu-dev \
libfreetype6-dev \
libharfbuzz-dev \
libxml2-dev \
libjpeg-dev \
libtiff-dev \
libwebp-dev \
libcairo2-dev \
libproj-dev \
libgdal-dev \
libboost-filesystem-dev \
libboost-program-options-dev \
libboost-regex-dev
- name: Configure CMake
run: cmake -LA --preset ${{ env.PRESET }}
- name: Build
run: cmake --build --preset ${{ env.PRESET }}
- name: Package
run: cmake --build --preset ${{ env.PRESET }} --target package
- name: Upload mapnik debian package
uses: actions/upload-artifact@v4
with:
name: ${{ env.PRESET }}-deb
path: build/mapnik-*.deb

7
.gitignore vendored
View file

@ -1,6 +1,4 @@
.DS_Store .DS_Store
.vscode
.cache
*.gcov *.gcov
*.gcda *.gcda
*.gcno *.gcno
@ -58,8 +56,3 @@ demo/viewer/ui_layer_info.h
test/standalone/*-bin test/standalone/*-bin
test/unit/run test/unit/run
test/visual/run test/visual/run
# cmake
build
.vs
CMakeUserPresets.json

3
.gitmodules vendored
View file

@ -18,6 +18,3 @@
path = deps/mapbox/protozero path = deps/mapbox/protozero
url = https://github.com/mapbox/protozero.git url = https://github.com/mapbox/protozero.git
branch = master branch = master
[submodule "deps/mapbox/polylabel"]
path = deps/mapbox/polylabel
url = https://github.com/mapbox/polylabel.git

View file

@ -1,16 +0,0 @@
# See https://pre-commit.com for more information
# See https://pre-commit.com/hooks.html for more hooks
repos:
- repo: https://github.com/pre-commit/pre-commit-hooks
rev: v4.6.0
hooks:
- id: trailing-whitespace
files: ^.*\.cmake|CMakeLists\.txt$
- id: end-of-file-fixer
files: ^.*\.cmake|CMakeLists\.txt$
- repo: https://github.com/pre-commit/mirrors-clang-format
rev: v18.1.3
hooks:
- id: clang-format
types_or: [c++, c]

115
.travis.yml Normal file
View file

@ -0,0 +1,115 @@
language: generic
git:
depth: 10
submodules: false
env:
global:
- CCACHE_TEMPDIR=/tmp/.ccache-temp
- CCACHE_COMPRESS=1
- HEAVY_JOBS="2"
- PREFIX=/tmp/mapnik
- secure: "F6ivqDNMBQQnrDGA9+7IX+GDswuIqQQd7YPJdQqa2Ked9jddAQDeJClb05ig3JlwfOlYLGZOd43ZX0pKuMtI2Gbkwz211agGP9S3YunwlRg8iWtJlO5kYFUdKCmJNhjg4icfkGELCgwXn+zuEWFSLpkPcjqAFKFlQrIJeAJJgKM="
addons:
postgresql: "9.4"
cache:
directories:
- $HOME/.ccache
matrix:
include:
- os: linux
sudo: false
compiler: ": clang"
env: JOBS=4 CXX="ccache g++-6" CC="gcc-6"
addons:
apt:
sources: [ 'ubuntu-toolchain-r-test']
packages: [ 'libstdc++-6-dev', 'g++-6', 'xutils-dev']
- os: linux
sudo: false
compiler: ": clang"
env: JOBS=8 CXX="ccache clang++-4.0 -Qunused-arguments" CC="clang-4.0" TRIGGER=true
addons:
apt:
sources: [ 'ubuntu-toolchain-r-test']
packages: [ 'libstdc++-4.9-dev', 'xutils-dev']
- os: linux
sudo: false
compiler: ": clang-coverage"
env: JOBS=8 COVERAGE=true CXX="ccache clang++-4.0 -Qunused-arguments" CC="clang-4.0"
addons:
apt:
sources: [ 'ubuntu-toolchain-r-test']
packages: ['libstdc++-4.9-dev', 'xutils-dev' ]
- os: osx
compiler: ": clang-osx"
# https://docs.travis-ci.com/user/languages/objective-c/#Supported-OS-X-iOS-SDK-versions
osx_image: xcode7.3 # upgrades clang from 6 -> 7
env: JOBS=4 CXX="ccache clang++ -Qunused-arguments"
before_install:
# workaround travis rvm bug
# http://superuser.com/questions/1044130/why-am-i-having-how-can-i-fix-this-error-shell-session-update-command-not-f
- |
if [[ "${TRAVIS_OS_NAME}" == "osx" ]]; then
rvm get head || true
fi
- source scripts/travis-common.sh
- export PATH=${PREFIX}/bin:$(pwd)/mason_packages/.link/bin:${PATH}
- export COVERAGE=${COVERAGE:-false}
- export MASON_PUBLISH=${MASON_PUBLISH:-false}
- export BENCH=${BENCH:-false}
- if [[ ${TRAVIS_BRANCH} != 'master' ]]; then export MASON_PUBLISH=false; fi
- if [[ ${TRAVIS_PULL_REQUEST} != 'false' ]]; then export MASON_PUBLISH=false; fi
- git_submodule_update --init --depth=10
install:
- on 'osx' export DATA_PATH=$(brew --prefix)/var/postgres
- on 'osx' rm -rf ${DATA_PATH}
- on 'osx' initdb ${DATA_PATH} -E utf8
- on 'osx' pg_ctl -w start -l postgres.log --pgdata ${DATA_PATH};
- on 'osx' cat postgres.log;
- on 'osx' createuser -s postgres
- psql -c 'create database template_postgis;' -U postgres
- psql -c 'create extension postgis;' -d template_postgis -U postgres
- enabled ${COVERAGE} curl -S -f https://codecov.io/bash -o codecov
- enabled ${COVERAGE} chmod +x codecov
before_script:
- source bootstrap.sh
- |
if [[ $(uname -s) == 'Linux' ]]; then
mason install clang++ 4.0.1
export PATH=$(mason prefix clang++ 4.0.1)/bin:${PATH}
mason install llvm-cov 4.0.1
export PATH=$(mason prefix llvm-cov 4.0.1)/bin:${PATH}
which llvm-cov
export LLVM_COV="$(mason prefix llvm-cov 4.0.1)/bin/llvm-cov"
fi
- ccache --version
- ccache -p || true
- ccache --show-stats || true
- commit_message_parse
script:
- export SCONSFLAGS='--debug=time'
- configure BENCHMARK=${BENCH}
- cat config.log
# we limit the `make` to 40 min
# to ensure that slow builds still upload their
# ccache results and therefore should be faster
# (and might work) for the next build
- DURATION=2400
- scripts/travis-command-wrapper.py -s "date" -i 120 --deadline=$(( $(date +%s) + ${DURATION} )) make
- RESULT=0
- make test || RESULT=$?
# we allow visual failures with g++ for now: https://github.com/mapnik/mapnik/issues/3567
- if [[ ${RESULT} != 0 ]] && [[ ${CXX} =~ 'clang++' ]]; then false; fi;
- enabled ${COVERAGE} coverage
- enabled ${BENCH} make bench
after_success:
- enabled ${TRIGGER} trigger_downstream

File diff suppressed because it is too large Load diff

View file

@ -1,34 +0,0 @@
# This CITATION.cff file was generated with cffinit.
# Visit https://bit.ly/cffinit to generate yours today!
cff-version: 1.2.0
title: mapnik
message: >-
If you use this software, please cite it using the
metadata from this file.
type: software
authors:
- given-names: Artem
family-names: Pavlenko
identifiers:
- type: url
value: 'https://github.com/mapnik/mapnik'
description: GitHub Repository
- type: swh
value: >-
swh:1:dir:3f5758e17e9d54016ca694268da68cf6856fab58
description: Software Archive
repository-code: 'https://github.com/mapnik/mapnik'
url: 'https://mapnik.org/'
abstract: >-
Mapnik is an open source toolkit for developing
mapping applications. At the core is a C++ shared
library providing algorithms and patterns for
spatial data access and visualization.
keywords:
- mapping
- gis
- cartography
- beautiful-maps
- rendering
license: LGPL-2.1

View file

@ -1,472 +0,0 @@
cmake_minimum_required(VERSION 3.15)
# 3.15 is required since the Boost::XXXX targets was first added. https://cmake.org/cmake/help/latest/module/FindBoost.html#imported-targets
# 3.14 is required since SQLite3 Module was first added. https://cmake.org/cmake/help/latest/module/FindSQLite3.html#findsqlite3
include(cmake/GetVersion.cmake)
get_mapnik_version()
project(mapnik
VERSION ${MAPNIK_MAJOR_VERSION}.${MAPNIK_MINOR_VERSION}.${MAPNIK_PATCH_VERSION}
HOMEPAGE_URL "https://mapnik.org/"
DESCRIPTION "Mapnik is an open source toolkit for developing mapping applications"
LANGUAGES CXX
)
message(STATUS "mapnik version: ${PROJECT_VERSION}")
# https://cliutils.gitlab.io/modern-cmake/chapters/features/ides.html
set_property(GLOBAL PROPERTY USE_FOLDERS ON)
set(CMAKE_FIND_PACKAGE_TARGETS_GLOBAL ON) # with newer cmake versions put all find_package in global scope
set(CMAKE_MODULE_PATH ${CMAKE_MODULE_PATH} "${CMAKE_CURRENT_SOURCE_DIR}/cmake")
include(FeatureSummary)
include(MapnikOption)
include(MapnikMinimumVersions)
include(MapnikFindPackage)
include(MapnikInstall)
include(CTest)
add_feature_info(BUILD_TESTING BUILD_TESTING "Adds tests")
mapnik_option(INSTALL_DEPENDENCIES "if ON, all dependencies (eg. required dlls) will be copied into CMAKE_INSTALL_PREFIX/MAPNIK_BIN_DIR." ON)
mapnik_option(BUILD_SHARED_LIBS "build mapnik dynamic(ON) or static(OFF)" ON)
mapnik_option(BUILD_SHARED_PLUGINS "build dynamic plugins" ${BUILD_SHARED_LIBS}) # use BUILD_SHARED_LIBS as default option
mapnik_option(BUILD_SHARED_CRT "(only windows with msvc) use msvc shared crt" ON)
if(WIN32 AND BUILD_SHARED_PLUGINS AND NOT BUILD_SHARED_LIBS)
message(FATAL_ERROR "static libmapnik and dynamic plugins won't work correctly")
endif()
mapnik_option(USE_EXTERNAL_MAPBOX_GEOMETRY "Use a external mapnik/geometry.hpp. If off, use the submodule" OFF)
mapnik_option(USE_EXTERNAL_MAPBOX_POLYLABEL "Use a external mapnik/polylabel. If off, use the submodule" OFF)
mapnik_option(USE_EXTERNAL_MAPBOX_PROTOZERO "Use a external mapnik/protozero. If off, use the submodule" OFF)
mapnik_option(USE_EXTERNAL_MAPBOX_VARIANT "Use a external mapnik/variant. If off, use the submodule" OFF)
mapnik_option(USE_JPEG "adds jpeg support" ON)
mapnik_option(USE_PNG "adds png support" ON)
mapnik_option(USE_TIFF "adds tiff support" ON)
mapnik_option(USE_WEBP "adds webp support" ON)
mapnik_option(USE_LIBXML2 "adds libxml2 support" ON)
mapnik_option(USE_CAIRO "adds the cairo renderer" ON)
mapnik_option(USE_PROJ "adds proj support" ON)
mapnik_option(USE_GRID_RENDERER "adds grid renderer" ON)
mapnik_option(USE_SVG_RENDERER "adds svg renderer" ON)
mapnik_option(USE_BIGINT "uses 64 bit instead of 32" ON)
mapnik_option(USE_BOOST_FILESYSTEM "use boost::filesytem even if `std::filesystem` is available (since c++17)" OFF)
mapnik_option(USE_MEMORY_MAPPED_FILE "uses file cache" ON)
mapnik_option(USE_MULTITHREADED "enables the multithreaded features (threadsafe)" ON)
mapnik_option(USE_NO_ATEXIT "disable atexit" OFF)
mapnik_option(USE_NO_DLCLOSE "disable dlclose" OFF)
mapnik_option(USE_DEBUG_OUTPUT "enables some debug messages for development" OFF)
mapnik_option(USE_LOG "enables logging output. See log severity level." OFF)
# 0 = debug
# 1 = warn
# 2 = error
# 3 = none
set(USE_LOG_SEVERITY "1" CACHE STRING "sets the logging severity (only applies when USE_LOG is ON")
mapnik_option(USE_STATS "Enable statistics reporting" OFF)
mapnik_option(DISABLE_MAPNIK_AUTOSETUP "disables the autosetup. Need to call mapnik::setup() then" OFF)
mapnik_option(USE_PLUGIN_INPUT_CSV "adds plugin input csv" ON)
mapnik_option(USE_PLUGIN_INPUT_GDAL "adds plugin input gdal" ON)
mapnik_option(USE_PLUGIN_INPUT_GEOBUF "adds plugin input geobuf" ON)
mapnik_option(USE_PLUGIN_INPUT_GEOJSON "adds plugin input geojson" ON)
mapnik_option(USE_PLUGIN_INPUT_OGR "adds plugin input ogr" ON)
mapnik_option(USE_PLUGIN_INPUT_PGRASTER "adds plugin input pgraster" ON)
mapnik_option(USE_PLUGIN_INPUT_POSTGIS "adds plugin input postgis" ON)
mapnik_option(USE_PLUGIN_INPUT_RASTER "adds plugin input raster" ON)
mapnik_option(USE_PLUGIN_INPUT_SHAPE "adds plugin input shape" ON)
mapnik_option(USE_PLUGIN_INPUT_SQLITE "adds plugin input sqlite" ON)
mapnik_option(USE_PLUGIN_INPUT_TOPOJSON "adds plugin input topojson" ON)
mapnik_option(BUILD_DEMO_VIEWER "builds the demo viewer" ON)
mapnik_option(BUILD_DEMO_CPP "builds the demo c++ application" ON)
mapnik_option(BUILD_BENCHMARK "builds benchmark project" ON)
mapnik_option(BUILD_UTILITY_GEOMETRY_TO_WKB "builds the utility program geometry_to_wkb" ON)
mapnik_option(BUILD_UTILITY_MAPNIK_INDEX "builds the utility program mapnik_index" ON)
mapnik_option(BUILD_UTILITY_MAPNIK_RENDER "builds the utility program mapnik_render" ON)
mapnik_option(BUILD_UTILITY_OGRINDEX "builds the utility program ogrindex" OFF)
mapnik_option(BUILD_UTILITY_PGSQL2SQLITE "builds the utility program pgsql2sqlite" ON)
mapnik_option(BUILD_UTILITY_SHAPEINDEX "builds the utility program shapeindex" ON)
mapnik_option(BUILD_UTILITY_SVG2PNG "builds the utility program svg2png" ON)
mapnik_option(USE_BOOST_REGEX_ICU_WORKAROUND "if you don't use your system libraries and get double linked icu libraries set this to ON" OFF)
mapnik_option(USE_GLIBC_WORKAROUND "see https://github.com/mapnik/mapnik/pull/3792 if you building with libstdc++-4.9" OFF)
feature_summary(WHAT ENABLED_FEATURES DISABLED_FEATURES)
feature_summary(FILENAME "${CMAKE_CURRENT_BINARY_DIR}/features.log" WHAT ENABLED_FEATURES DISABLED_FEATURES)
include(GNUInstallDirs)
# See for more details: https://cmake.org/cmake/help/latest/manual/cmake-buildsystem.7.html
set(MAPNIK_BIN_DIR ${CMAKE_INSTALL_BINDIR} CACHE STRING "Install directory for binaries")
set(MAPNIK_LIB_DIR ${CMAKE_INSTALL_LIBDIR} CACHE STRING "Install directory for libraries")
set(MAPNIK_ARCHIVE_DIR ${CMAKE_INSTALL_LIBDIR} CACHE STRING "Install directory for archives")
set(MAPNIK_INCLUDE_DIR ${CMAKE_INSTALL_INCLUDEDIR} CACHE STRING "Install directory for the headers")
set(MAPNIK_CMAKE_DIR ${MAPNIK_LIB_DIR}/cmake/mapnik CACHE STRING "Install directory of the cmake targets")
set(MAPNIK_PKGCONF_DIR ${MAPNIK_LIB_DIR}/pkgconfig CACHE STRING "Install directory for the .pc files for pkg-config")
set(MAPNIK_OUTPUT_DIR "${CMAKE_BINARY_DIR}/out")
if(WIN32)
set(DEFAULT_PLUGINS_INSTALL_DIR ${MAPNIK_BIN_DIR}/mapnik/input)
else()
set(DEFAULT_PLUGINS_INSTALL_DIR ${MAPNIK_LIB_DIR}/mapnik/input)
endif()
set(PLUGINS_INSTALL_DIR ${DEFAULT_PLUGINS_INSTALL_DIR} CACHE STRING "installs the plugins in the specified directory")
message(STATUS "Installing plugins to ${PLUGINS_INSTALL_DIR}")
set(FONTS_INSTALL_DIR ${MAPNIK_LIB_DIR}/mapnik/fonts CACHE STRING "installs the fonts in the specified directory")
message(STATUS "Installing fonts to ${FONTS_INSTALL_DIR}")
set(MAPNIK_COMPILE_DEFS "")
set(MAPNIK_OPTIONAL_LIBS "")
set(MAPNIK_OPTIONAL_LIBS_INCLUDE "")
#############################
#############################
# Begin project configuration
#############################
#############################
set(CMAKE_CXX_STANDARD 17 CACHE STRING "Sets the c++ standard. c++17 is minimum.")
set(CMAKE_CXX_STANDARD_REQUIRED ON) # require the specified CMAKE_CXX_STANDARD
set(CMAKE_CXX_EXTENSIONS OFF CACHE STRING "Enables the compiler specific extensions.") # Fallsback to -std=c++<ver> if off
message(STATUS "Using c++${CMAKE_CXX_STANDARD}")
message(STATUS "Using c++ extensions: ${CXX_EXTENSIONS}")
# add debug postfix to the libraries
set(CMAKE_DEBUG_POSTFIX "d" CACHE STRING "sets the debug library postfix on mapnik, wkt and json")
message(STATUS "postfix for debug libraries: ${CMAKE_DEBUG_POSTFIX}")
set(CMAKE_MSVC_RUNTIME_LIBRARY "MultiThreaded$<$<CONFIG:Debug>:Debug>$<$<BOOL:${BUILD_SHARED_CRT}>:DLL>")
set(CMAKE_RUNTIME_OUTPUT_DIRECTORY "${MAPNIK_OUTPUT_DIR}")
set(CMAKE_LIBRARY_OUTPUT_DIRECTORY "${MAPNIK_OUTPUT_DIR}")
set(CMAKE_ARCHIVE_OUTPUT_DIRECTORY "${MAPNIK_OUTPUT_DIR}/lib")
# needs to be before the first call of find_boost.
if(CMAKE_CXX_STANDARD VERSION_LESS 17)
list(APPEND MAPNIK_COMPILE_DEFS BOOST_SPIRIT_X3_HIDE_CXX17_WARNING)
endif()
if(USE_MULTITHREADED)
set(Boost_USE_MULTITHREADED ON)
list(APPEND MAPNIK_COMPILE_DEFS MAPNIK_THREADSAFE)
else()
set(Boost_USE_MULTITHREADED OFF)
endif()
mapnik_find_package(PkgConfig REQUIRED)
mapnik_find_threads()
mapnik_find_package(ICU REQUIRED COMPONENTS uc i18n data)
mapnik_find_package(Boost ${BOOST_MIN_VERSION} REQUIRED COMPONENTS regex)
if(CMAKE_CXX_STANDARD VERSION_LESS 17)
set(USE_BOOST_FILESYSTEM ON CACHE BOOL "Use boost::filesystem" FORCE)
endif()
if(USE_BOOST_FILESYSTEM)
mapnik_find_package(Boost ${BOOST_MIN_VERSION} REQUIRED COMPONENTS filesystem system)
endif()
list(APPEND MAPNIK_COMPILE_DEFS BOOST_REGEX_HAS_ICU)
if(USE_BOOST_REGEX_ICU_WORKAROUND)
message(STATUS "using boost regex workaround")
set_property(TARGET Boost::regex PROPERTY INTERFACE_LINK_LIBRARIES)
endif()
include(CheckBoostRegexIcu)
check_boost_regex()
if(BOOST_REGEX_HAS_ICU)
message(STATUS "boost regex has icu support")
list(APPEND MAPNIK_COMPILE_DEFS BOOST_REGEX_HAS_ICU)
endif()
mapnik_find_package(Freetype REQUIRED)
# try to find harfbuzz with the native configuration and fallback to our "own" FindHarfBuzz
mapnik_find_package(harfbuzz CONFIG QUIET)
if(harfbuzz_FOUND)
message(STATUS "Found harfbuzz native cmake")
list(APPEND MAPNIK_OPTIONAL_LIBS harfbuzz::harfbuzz)
else()
# Use pkg-config when harfbuzz is not found.
# It might be possible that in future version harfbuzz could only be found via pkg-config.
# harfbuzz related discussion: https://github.com/harfbuzz/harfbuzz/issues/2653
message(STATUS "harfbuzz not found via cmake. Searching via pkg-config...")
mapnik_pkg_check_modules(harfbuzz REQUIRED IMPORTED_TARGET harfbuzz>=${HARFBUZZ_MIN_VERSION})
list(APPEND MAPNIK_OPTIONAL_LIBS PkgConfig::harfbuzz)
endif()
if(USE_EXTERNAL_MAPBOX_GEOMETRY)
# this is used to provide a way to specify include dirs with CACHE VARIABLES
if(NOT MAPBOX_GEOMETRY_INCLUDE_DIRS)
message(STATUS "Searching for the include dir of mapbox/geometry.hpp")
find_path(MAPBOX_GEOMETRY_INCLUDE_DIRS "mapbox/geometry.hpp" REQUIRED)
endif()
else()
set(MAPBOX_GEOMETRY_INCLUDE_DIRS
$<BUILD_INTERFACE:${CMAKE_CURRENT_SOURCE_DIR}/deps/mapbox/geometry/include>
$<INSTALL_INTERFACE:include>
)
endif()
if(NOT MAPBOX_GEOMETRY_INCLUDE_DIRS)
message(FATAL_ERROR "Set -DMAPBOX_GEOMETRY_INCLUDE_DIRS to the mapbox/geometry.hpp include dir")
endif()
if(USE_EXTERNAL_MAPBOX_POLYLABEL)
if(NOT MAPBOX_POLYLABEL_INCLUDE_DIRS)
message(STATUS "Searching for the include dir of mapbox/polylabel")
find_path(MAPBOX_POLYLABEL_INCLUDE_DIRS "mapbox/polylabel.hpp")
endif()
else()
set(MAPBOX_POLYLABEL_INCLUDE_DIRS
$<BUILD_INTERFACE:${CMAKE_CURRENT_SOURCE_DIR}/deps/mapbox/polylabel/include>
$<INSTALL_INTERFACE:include>
)
endif()
if(NOT MAPBOX_POLYLABEL_INCLUDE_DIRS)
message(FATAL_ERROR "Set MAPBOX_POLYLABEL_INCLUDE_DIRS to the mapbox/geometry include dir")
endif()
if(USE_EXTERNAL_MAPBOX_PROTOZERO)
if(NOT MAPBOX_PROTOZERO_INCLUDE_DIRS)
message(STATUS "Searching for the include dir of mapbox/protozero")
find_path(MAPBOX_PROTOZERO_INCLUDE_DIRS "protozero/pbf_message.hpp")
endif()
else()
set(MAPBOX_PROTOZERO_INCLUDE_DIRS
$<BUILD_INTERFACE:${CMAKE_CURRENT_SOURCE_DIR}/deps/mapbox/protozero/include>
$<INSTALL_INTERFACE:include>
)
endif()
if(NOT MAPBOX_PROTOZERO_INCLUDE_DIRS)
message(FATAL_ERROR "Set MAPBOX_PROTOZERO_INCLUDE_DIRS to the mapbox/protozero include dir")
endif()
if(USE_EXTERNAL_MAPBOX_VARIANT)
if(NOT MAPBOX_VARIANT_INCLUDE_DIRS)
message(STATUS "Searching for the include dir of mapbox/variant")
find_path(MAPBOX_VARIANT_INCLUDE_DIRS "mapbox/variant.hpp")
endif()
else()
set(MAPBOX_VARIANT_INCLUDE_DIRS
$<BUILD_INTERFACE:${CMAKE_CURRENT_SOURCE_DIR}/deps/mapbox/variant/include>
$<INSTALL_INTERFACE:include>
)
endif()
if(NOT MAPBOX_VARIANT_INCLUDE_DIRS)
message(FATAL_ERROR "Set MAPBOX_VARIANT_INCLUDE_DIRS to the mapbox/variant include dir")
endif()
# (used by MapnikInstall.cmake. properties are needed since "set(...)" will be out of scope
set_property(GLOBAL PROPERTY TARGETS "")
set_property(GLOBAL PROPERTY PLUGINS "")
set_property(GLOBAL PROPERTY MAPNIK_UTILITIES "")
if(USE_GLIBC_WORKAROUND)
list(APPEND MAPNIK_COMPILE_DEFS MAPNIK_ENABLE_GLIBC_WORKAROUND)
endif()
if(USE_BIGINT)
list(APPEND MAPNIK_COMPILE_DEFS BIGINT)
endif()
if(USE_BOOST_FILESYSTEM)
list(APPEND MAPNIK_COMPILE_DEFS USE_BOOST_FILESYSTEM)
list(APPEND MAPNIK_OPTIONAL_LIBS Boost::filesystem)
endif()
if(USE_MEMORY_MAPPED_FILE)
list(APPEND MAPNIK_COMPILE_DEFS MAPNIK_MEMORY_MAPPED_FILE)
endif()
if(USE_NO_ATEXIT)
list(APPEND MAPNIK_COMPILE_DEFS MAPNIK_NO_ATEXIT)
endif()
if(USE_NO_DLCLOSE)
list(APPEND MAPNIK_COMPILE_DEFS MAPNIK_NO_DLCLOSE)
endif()
if(USE_DEBUG_OUTPUT)
list(APPEND MAPNIK_COMPILE_DEFS MAPNIK_DEBUG)
endif()
if(USE_LOG)
list(APPEND MAPNIK_COMPILE_DEFS MAPNIK_LOG MAPNIK_DEFAULT_LOG_SEVERITY=${USE_LOG_SEVERITY})
endif()
if(USE_STATS)
list(APPEND MAPNIK_COMPILE_DEFS MAPNIK_STATS)
endif()
if(USE_LIBXML2)
mapnik_find_package(LibXml2 REQUIRED)
list(APPEND MAPNIK_COMPILE_DEFS HAVE_LIBXML2)
list(APPEND MAPNIK_OPTIONAL_LIBS LibXml2::LibXml2)
endif()
if(USE_PNG)
mapnik_find_package(PNG REQUIRED)
list(APPEND MAPNIK_COMPILE_DEFS HAVE_PNG)
list(APPEND MAPNIK_OPTIONAL_LIBS PNG::PNG)
endif()
if(USE_JPEG)
mapnik_find_package(JPEG REQUIRED)
list(APPEND MAPNIK_COMPILE_DEFS HAVE_JPEG)
list(APPEND MAPNIK_OPTIONAL_LIBS JPEG::JPEG)
endif()
if(USE_TIFF)
mapnik_find_package(TIFF REQUIRED)
list(APPEND MAPNIK_COMPILE_DEFS HAVE_TIFF)
list(APPEND MAPNIK_OPTIONAL_LIBS TIFF::TIFF)
endif()
if(USE_WEBP)
mapnik_pkg_check_modules(WebP REQUIRED IMPORTED_TARGET libwebp)
list(APPEND MAPNIK_COMPILE_DEFS HAVE_WEBP)
list(APPEND MAPNIK_OPTIONAL_LIBS PkgConfig::WebP)
endif()
if(USE_CAIRO)
mapnik_pkg_check_modules(Cairo REQUIRED IMPORTED_TARGET cairo)
list(APPEND MAPNIK_COMPILE_DEFS HAVE_CAIRO)
list(APPEND MAPNIK_OPTIONAL_LIBS PkgConfig::Cairo)
endif()
if(USE_PROJ)
#https://proj.org/development/cmake.html
mapnik_find_package(PROJ QUIET)
# currently the cmake files are not installed, when installing proj via apt-get. So search via pkg-config
if(NOT PROJ_FOUND)
message(STATUS "PROJ not found via FindPROJ. Searching via pkg-config...")
mapnik_pkg_check_modules(PROJ REQUIRED IMPORTED_TARGET proj>=${PROJ_MIN_VERSION})
string(REGEX MATCH "([0-9]+)\.([0-9]+)\.([0-9]+)" _dummy "${PROJ_VERSION}")
set(PROJ_VERSION_MAJOR "${CMAKE_MATCH_1}")
set(PROJ_VERSION_MINOR "${CMAKE_MATCH_2}")
set(PROJ_VERSION_PATCH "${CMAKE_MATCH_3}")
list(APPEND MAPNIK_OPTIONAL_LIBS PkgConfig::PROJ)
else()
if(PROJ_VERSION VERSION_LESS PROJ_MIN_VERSION)
message(FATAL_ERROR "Proj needs to be at least version ${PROJ_MIN_VERSION}")
endif()
list(APPEND MAPNIK_OPTIONAL_LIBS ${PROJ_LIBRARIES})
list(APPEND MAPNIK_OPTIONAL_LIBS_INCLUDE $<BUILD_INTERFACE:${PROJ_INCLUDE_DIRS}>)
endif()
math(EXPR MAPNIK_PROJ_VERSION "${PROJ_VERSION_MAJOR}*10000 + ${PROJ_VERSION_MINOR}*100 + ${PROJ_VERSION_PATCH}" OUTPUT_FORMAT DECIMAL)
message(STATUS "Using mapnik PROJ version: ${MAPNIK_PROJ_VERSION}")
list(APPEND MAPNIK_COMPILE_DEFS MAPNIK_USE_PROJ MAPNIK_PROJ_VERSION=${MAPNIK_PROJ_VERSION})
endif()
if(USE_GRID_RENDERER)
list(APPEND MAPNIK_COMPILE_DEFS GRID_RENDERER)
endif()
if(USE_SVG_RENDERER)
list(APPEND MAPNIK_COMPILE_DEFS SVG_RENDERER)
endif()
if(NOT WIN32)
message(STATUS "Compiling with -DMAPNIK_HAS_DLCFN")
list(APPEND MAPNIK_COMPILE_DEFS MAPNIK_HAS_DLCFN)
list(APPEND MAPNIK_OPTIONAL_LIBS ${CMAKE_DL_LIBS})
endif()
if(NOT BUILD_SHARED_PLUGINS)
list(APPEND MAPNIK_COMPILE_DEFS MAPNIK_STATIC_PLUGINS)
endif()
# when building static, this have to be public so that all depending libs know about
if(NOT BUILD_SHARED_LIBS)
list(APPEND MAPNIK_COMPILE_DEFS MAPNIK_STATIC_DEFINE)
endif()
if(DISABLE_MAPNIK_AUTOSETUP)
list(APPEND MAPNIK_COMPILE_DEFS MAPNIK_DISABLE_AUTOSETUP)
endif()
# force utf-8 source code processing
# see https://docs.microsoft.com/de-de/cpp/build/reference/utf-8-set-source-and-executable-character-sets-to-utf-8?view=msvc-170
add_compile_options(
"$<$<CXX_COMPILER_ID:MSVC>:/utf-8>"
"$<$<CXX_COMPILER_ID:MSVC>:/EHsc>"
)
add_library(core INTERFACE)
add_library(mapnik::core ALIAS core)
target_include_directories(core INTERFACE
$<BUILD_INTERFACE:${CMAKE_CURRENT_SOURCE_DIR}/include>
$<BUILD_INTERFACE:${MAPBOX_GEOMETRY_INCLUDE_DIRS}>
$<BUILD_INTERFACE:${MAPBOX_POLYLABEL_INCLUDE_DIRS}>
$<BUILD_INTERFACE:${MAPBOX_VARIANT_INCLUDE_DIRS}>
$<BUILD_INTERFACE:${MAPBOX_PROTOZERO_INCLUDE_DIRS}>
$<BUILD_INTERFACE:${CMAKE_CURRENT_SOURCE_DIR}/deps>
$<INSTALL_INTERFACE:include>
${MAPNIK_OPTIONAL_LIBS_INCLUDE}
)
target_link_libraries(core INTERFACE
Threads::Threads
ICU::uc
ICU::data
ICU::i18n
Boost::headers
Boost::regex
Freetype::Freetype
${MAPNIK_OPTIONAL_LIBS}
)
target_compile_definitions(core INTERFACE ${MAPNIK_COMPILE_DEFS})
mapnik_install(core)
###
# forward declaring libraries to consume them when building static plugins (circle deps between mapnik <-> plugin_target)
add_library(mapnik "")
add_library(mapnik::mapnik ALIAS mapnik)
add_library(wkt STATIC "")
add_library(mapnik::wkt ALIAS wkt)
add_library(json STATIC "")
add_library(mapnik::json ALIAS json)
# end forward declaration
###
add_subdirectory(deps)
add_subdirectory(plugins)
add_subdirectory(src)
add_subdirectory(utils)
add_subdirectory(demo)
if(BUILD_BENCHMARK)
add_subdirectory(benchmark)
endif()
if(BUILD_TESTING)
add_subdirectory(test)
endif()
file(COPY fonts DESTINATION "${MAPNIK_OUTPUT_DIR}")
feature_summary(FILENAME "${CMAKE_CURRENT_BINARY_DIR}/packages.log" WHAT PACKAGES_FOUND PACKAGES_NOT_FOUND INCLUDE_QUIET_PACKAGES)
# start package mapnik
include(MapnikExport)
include(MapnikExportPkgConfig)
install(DIRECTORY include/mapnik/ DESTINATION "${MAPNIK_INCLUDE_DIR}/mapnik")
install(DIRECTORY deps/agg/include/ DESTINATION "${MAPNIK_INCLUDE_DIR}/mapnik/agg")
install(DIRECTORY deps/mapnik DESTINATION "${MAPNIK_INCLUDE_DIR}")
file(GLOB TTF_FONT_FILES "fonts/*/*/*.ttf")
install(FILES ${TTF_FONT_FILES} DESTINATION "${FONTS_INSTALL_DIR}")
if(NOT USE_EXTERNAL_MAPBOX_GEOMETRY)
install(DIRECTORY "${CMAKE_CURRENT_SOURCE_DIR}/deps/mapbox/geometry/include/" DESTINATION "${MAPNIK_INCLUDE_DIR}")
endif()
if(NOT USE_EXTERNAL_MAPBOX_POLYLABEL)
install(DIRECTORY "${CMAKE_CURRENT_SOURCE_DIR}/deps/mapbox/polylabel/include/" DESTINATION "${MAPNIK_INCLUDE_DIR}")
endif()
if(NOT USE_EXTERNAL_MAPBOX_PROTOZERO)
install(DIRECTORY "${CMAKE_CURRENT_SOURCE_DIR}/deps/mapbox/protozero/include/" DESTINATION "${MAPNIK_INCLUDE_DIR}")
endif()
if(NOT USE_EXTERNAL_MAPBOX_VARIANT)
install(DIRECTORY "${CMAKE_CURRENT_SOURCE_DIR}/deps/mapbox/variant/include/" DESTINATION "${MAPNIK_INCLUDE_DIR}")
endif()
mapnik_install_targets()
include(pack)

View file

@ -1,350 +0,0 @@
{
"version": 6,
"cmakeMinimumRequired": {
"major": 3,
"minor": 25,
"patch": 0
},
"configurePresets": [
{
"name": "use-ninja",
"hidden": true,
"generator": "Ninja",
"cacheVariables": {
"CMAKE_EXPORT_COMPILE_COMMANDS": "ON"
}
},
{
"name": "default-build-dir",
"hidden": true,
"binaryDir": "${sourceDir}/build"
},
{
"name": "debug-build",
"hidden": true,
"cacheVariables": {
"CMAKE_BUILD_TYPE": "Debug",
"USE_DEBUG_OUTPUT": "ON",
"USE_LOG": "ON",
"USE_LOG_SEVERITY": "0"
}
},
{
"name": "release-with-debug-build",
"hidden": true,
"cacheVariables": {
"CMAKE_BUILD_TYPE": "RelWithDebInfo",
"USE_DEBUG_OUTPUT": "OFF",
"USE_LOG": "OFF"
}
},
{
"name": "release-build",
"hidden": true,
"cacheVariables": {
"CMAKE_BUILD_TYPE": "Release",
"USE_DEBUG_OUTPUT": "OFF",
"USE_LOG": "OFF"
}
},
{
"name": "use-clang",
"hidden": true,
"inherits": [
"default-build-dir",
"use-ninja"
],
"cacheVariables": {
"CMAKE_C_COMPILER": "clang",
"CMAKE_CXX_COMPILER": "clang++",
"CMAKE_CXX_FLAGS": "-stdlib=libc++",
"CMAKE_EXE_LINKER_FLAGS": "-stdlib=libc++",
"CMAKE_SHARED_LINKER_FLAGS": "-stdlib=libc++"
}
},
{
"name": "use-gcc",
"hidden": true,
"inherits": [
"default-build-dir",
"use-ninja"
],
"cacheVariables": {
"CMAKE_C_COMPILER": "gcc",
"CMAKE_CXX_COMPILER": "g++"
}
},
{
"name": "use-msvc-cl",
"hidden": true,
"inherits": [
"default-build-dir",
"use-ninja"
],
"cacheVariables": {
"CMAKE_C_COMPILER": "cl",
"CMAKE_CXX_COMPILER": "cl"
}
},
{
"name": "use-msvc-clang-cl",
"hidden": true,
"inherits": [
"default-build-dir",
"use-ninja"
],
"cacheVariables": {
"CMAKE_C_COMPILER": "clang-cl",
"CMAKE_CXX_COMPILER": "clang-cl"
}
},
{
"name": "linux-clang-debug",
"displayName": "Linux clang debug",
"inherits": [
"use-clang",
"debug-build"
]
},
{
"name": "linux-clang-release",
"displayName": "Linux clang release",
"inherits": [
"use-clang",
"release-build"
]
},
{
"name": "linux-gcc-debug",
"displayName": "Linux gcc debug",
"inherits": [
"use-gcc",
"debug-build"
]
},
{
"name": "linux-gcc-release",
"displayName": "Linux gcc release",
"inherits": [
"use-gcc",
"release-build"
]
},
{
"name": "windows-arch-x64",
"hidden": true,
"architecture": {
"value": "x64",
"strategy": "external"
},
"toolset": {
"value": "host=x64",
"strategy": "external"
}
},
{
"name": "windows-default",
"displayName": "Windows x64 Debug",
"hidden": true,
"inherits": [
"use-msvc-cl",
"windows-arch-x64"
],
"vendor": {
"microsoft.com/VisualStudioSettings/CMake/1.0": {
"hostOS": [
"Windows"
]
}
}
},
{
"name": "windows-debug",
"displayName": "Windows x64 Debug",
"inherits": [
"windows-default",
"debug-build"
]
},
{
"name": "windows-release",
"displayName": "Windows x64 Release",
"inherits": [
"windows-default",
"release-build"
]
},
{
"name": "ci-options",
"hidden": true,
"cacheVariables": {
"BUILD_TESTING": "ON",
"BUILD_DEMO_VIEWER": "OFF",
"DISABLE_MAPNIK_AUTOSETUP": "ON"
},
"toolchainFile": "vcpkg/scripts/buildsystems/vcpkg.cmake"
},
{
"name": "windows-ci",
"description": "used by the ci pipeline",
"inherits": [
"windows-release",
"ci-options"
],
"cacheVariables": {
"INSTALL_DEPENDENCIES": "ON",
"ADDITIONAL_LIBARIES_PATHS": "${sourceDir}/build/vcpkg_installed/x64-windows/bin"
},
"environment": {
"PROJ_LIB": "${sourceDir}/build/vcpkg_installed/x64-windows/share/proj"
}
},
{
"name": "linux-ci",
"description": "used by the ci pipeline",
"inherits": [
"release-with-debug-build",
"use-gcc",
"ci-options"
],
"cacheVariables": {
"CMAKE_CXX_FLAGS": "--coverage"
},
"environment": {
"PROJ_LIB": "${sourceDir}/build/vcpkg_installed/x64-linux/share/proj"
}
},
{
"name": "linux-ci-release",
"description": "used by the ci pipeline for releasing",
"inherits": [
"release-build",
"linux-gcc-release"
],
"cacheVariables": {
"BUILD_TESTING": "OFF",
"BUILD_DEMO_VIEWER": "OFF",
"USE_MEMORY_MAPPED_FILE": "ON"
}
},
{
"name": "macos-ci-arm64",
"description": "used by the ci pipeline",
"inherits": [
"use-ninja",
"release-with-debug-build",
"default-build-dir",
"ci-options"
],
"cacheVariables": {
"CMAKE_CXX_FLAGS": "-fprofile-arcs -ftest-coverage"
},
"environment": {
"PROJ_LIB": "${sourceDir}/build/vcpkg_installed/arm64-osx/share/proj"
}
},
{
"name": "macos-ci-x64",
"description": "used by the ci pipeline",
"inherits": [
"use-ninja",
"release-with-debug-build",
"default-build-dir",
"ci-options"
],
"cacheVariables": {
"CMAKE_CXX_FLAGS": "-fprofile-arcs -ftest-coverage"
},
"environment": {
"PROJ_LIB": "${sourceDir}/build/vcpkg_installed/x64-osx/share/proj"
}
}
],
"buildPresets": [
{
"name": "windows-debug",
"configurePreset": "windows-debug"
},
{
"name": "windows-release",
"configurePreset": "windows-release"
},
{
"name": "linux-clang-debug",
"configurePreset": "linux-clang-debug"
},
{
"name": "linux-clang-release",
"configurePreset": "linux-clang-release"
},
{
"name": "linux-gcc-debug",
"configurePreset": "linux-gcc-debug"
},
{
"name": "linux-gcc-release",
"configurePreset": "linux-gcc-release"
},
{
"name": "windows-ci",
"configurePreset": "windows-ci"
},
{
"name": "linux-ci",
"configurePreset": "linux-ci"
},
{
"name": "linux-ci-release",
"configurePreset": "linux-ci-release"
},
{
"name": "macos-ci-arm64",
"configurePreset": "macos-ci-arm64"
},
{
"name": "macos-ci-x64",
"configurePreset": "macos-ci-x64"
}
],
"testPresets": [
{
"name": "test-default",
"hidden": true,
"output": {
"outputOnFailure": true
},
"execution": {
"noTestsAction": "error",
"stopOnFailure": false
}
},
{
"name": "windows-ci",
"configurePreset": "windows-ci",
"inherits": [
"test-default"
]
},
{
"name": "linux-ci",
"configurePreset": "linux-ci",
"inherits": [
"test-default"
]
},
{
"name": "macos-ci-arm64",
"configurePreset": "macos-ci-arm64",
"inherits": [
"test-default"
]
},
{
"name": "macos-ci-x64",
"configurePreset": "macos-ci-x64",
"inherits": [
"test-default"
]
}
]
}

View file

@ -2,18 +2,10 @@
Mapnik runs on Linux, OS X, Windows, and BSD systems. Mapnik runs on Linux, OS X, Windows, and BSD systems.
## Package managers
### vcpkg
To install mapnik with vcpkg type `vcpkg install mapnik`. It will install a minimal version of mapnik and all the needed dependencies.
To install more features, type `vcpkg search mapnik` to see all available features.
## Source build
First clone mapnik from github and initialize submodules First clone mapnik from github and initialize submodules
```bash ```bash
git clone https://github.com/mapnik/mapnik.git git clone https://github.com/mapnik/mapnik.git
cd mapnik
git submodule update --init git submodule update --init
``` ```
@ -42,8 +34,8 @@ To use a Python interpreter that is not named `python` for your build, do
something like the following instead: something like the following instead:
```bash ```bash
$ PYTHON=python3 ./configure $ PYTHON=python2 ./configure
$ make PYTHON=python3 $ make PYTHON=python2
``` ```
NOTE: the above will not work on windows, rather see https://github.com/mapnik/mapnik/wiki/WindowsInstallation NOTE: the above will not work on windows, rather see https://github.com/mapnik/mapnik/wiki/WindowsInstallation
@ -71,15 +63,15 @@ For troubleshooting help see https://github.com/mapnik/mapnik/wiki/InstallationT
Build system dependencies are: Build system dependencies are:
* C++ compiler supporting `-std=c++17` (like >= g++ 9 or >= clang++ 5) * C++ compiler supporting `-std=c++11` (like >= g++ 4.8 or >= clang++ 3.4)
* \>= 2 GB RAM (> 5 GB for g++) * >= 2 GB RAM (> 5 GB for g++)
* Python 3 * Python 2.4-2.7
* Scons (a copy is bundled) or CMake >= 3.15 see [docs/cmake-usage.md](./docs/cmake-usage.md) * Scons (a copy is bundled)
Mapnik Core depends on: Mapnik Core depends on:
* Boost * Boost
- \>= 1.73 is required - >= 1.47 is required and >= 1.56 recommended
- These libraries are used: - These libraries are used:
- filesystem - filesystem
- system - system
@ -97,7 +89,7 @@ Mapnik Core optionally depends on:
* libjpeg - JPEG graphics (Default enabled, if found) * libjpeg - JPEG graphics (Default enabled, if found)
* libtiff - TIFF graphics (Default enabled, if found) * libtiff - TIFF graphics (Default enabled, if found)
* libwebp - WEBP graphics (Default enabled, if found) * libwebp - WEBP graphics (Default enabled, if found)
* libproj >= 7.2.0 - PROJ projection library (Default enabled, if found) * libproj - PROJ.4 projection library (Default enabled, if found)
Additional optional dependencies: Additional optional dependencies:
@ -191,7 +183,7 @@ If you need help or want to participate starting points include:
### Cartographers ### Cartographers
TileMill, which uses Mapnik internally, offers great step by step tutorials for TileMill, which uses Mapnik internally, offers great step by step tutorials for
learning advanced map styling: https://tilemill-project.github.io/tilemill/docs/crashcourse/introduction/ learning advanced map styling: http://mapbox.com/tilemill/docs/crashcourse/introduction/
### Programmers ### Programmers
@ -199,6 +191,6 @@ Mapnik is great for building your own mapping applications. Visit
https://github.com/mapnik/mapnik/wiki/LearningMapnik for basic https://github.com/mapnik/mapnik/wiki/LearningMapnik for basic
tutorials on how to programmatically use Mapnik. tutorials on how to programmatically use Mapnik.
### Contributors ### Contributers
Read [docs/contributing.md](docs/contributing.md) for resources for getting involved with Mapnik development. Read docs/contributing.md for resources for getting involved with Mapnik development.

View file

@ -28,8 +28,7 @@ src/json/libmapnik-json.a:
src/renderer_common/render_thunk_extractor.os \ src/renderer_common/render_thunk_extractor.os \
src/json/libmapnik-json.a \ src/json/libmapnik-json.a \
src/wkt/libmapnik-wkt.a \ src/wkt/libmapnik-wkt.a \
src/css/css_grammar_x3.os \ src/css_color_grammar_x3.os \
src/css/css_color_grammar_x3.os \
src/expression_grammar_x3.os \ src/expression_grammar_x3.os \
src/transform_expression_grammar_x3.os \ src/transform_expression_grammar_x3.os \
src/image_filter_grammar_x3.os \ src/image_filter_grammar_x3.os \

View file

@ -8,7 +8,8 @@ _/ _/ _/_/_/ _/_/_/ _/ _/ _/ _/ _/
_/ _/
``` ```
[![TravisCI](https://api.travis-ci.com/mapnik/mapnik.svg?branch=master)](http://travis-ci.com/mapnik/mapnik) [![Build Status Linux](https://api.travis-ci.org/mapnik/mapnik.svg?branch=master)](http://travis-ci.org/mapnik/mapnik)
[![Build Status Windows](https://ci.appveyor.com/api/projects/status/hc9l7okdjtucfqqn?branch=master&svg=true)](https://ci.appveyor.com/project/Mapbox/mapnik)
[![codecov](https://codecov.io/gh/mapnik/mapnik/branch/master/graph/badge.svg)](https://codecov.io/gh/mapnik/mapnik) [![codecov](https://codecov.io/gh/mapnik/mapnik/branch/master/graph/badge.svg)](https://codecov.io/gh/mapnik/mapnik)
Mapnik is an open source toolkit for developing mapping applications. At the core is a C++ shared library providing algorithms and patterns for spatial data access and visualization. Mapnik is an open source toolkit for developing mapping applications. At the core is a C++ shared library providing algorithms and patterns for spatial data access and visualization.
@ -27,4 +28,4 @@ Please note that this project is released with a [Contributor Code of Conduct](h
# License # License
Mapnik software is free and is released under the LGPL v2.1 ([GNU Lesser General Public License, version 2.1](https://www.gnu.org/licenses/old-licenses/lgpl-2.1.html)). Please see [COPYING](https://github.com/mapnik/mapnik/blob/master/COPYING) for more information. Mapnik software is free and is released under the LGPL ([GNU Lesser General Public License](http://www.gnu.org/licenses/lgpl.html)). Please see [COPYING](https://github.com/mapnik/mapnik/blob/master/COPYING) for more information.

File diff suppressed because it is too large Load diff

39
appveyor.yml Normal file
View file

@ -0,0 +1,39 @@
environment:
msvs_toolset: 14
FASTBUILD: 1
matrix:
- platform: x64
configuration: Release
os: Visual Studio 2015
#shallow_clone: true
# limit clone to latest 5 commits
clone_depth: 5
services:
- postgresql94 #if changing this, also change PATH below
install:
- SET PGUSER=postgres
- SET PGPASSWORD=Password12!
- SET PATH=C:\Program Files\PostgreSQL\9.4\bin\;%PATH%
build_script:
- scripts\build-appveyor.bat
after_build:
- 7z a visual-test-results.zip C:\tmp\mapnik-visual-images\visual-test-results
artifacts:
- path: mapnik-gyp\msbuild-summary.txt
name: msbuild-summary.txt
- path: mapnik-gyp\msbuild-errors.txt
name: msbuild-errors.txt
- path: mapnik-gyp\msbuild-warnings.txt
name: msbuild-warnings.txt
- path: visual-test-results.zip
name: visual-test-results.zip
test: off
deploy: off

View file

@ -1,52 +0,0 @@
project(mapnik-benchmark)
set(BENCHMARK_SRCS
src/normalize_angle.cpp
src/test_array_allocation.cpp
src/test_expression_parse.cpp
src/test_face_ptr_creation.cpp
src/test_font_registration.cpp
src/test_getline.cpp
src/test_marker_cache.cpp
src/test_noop_rendering.cpp
src/test_numeric_cast_vs_static_cast.cpp
src/test_offset_converter.cpp
src/test_png_encoding1.cpp
src/test_png_encoding2.cpp
src/test_polygon_clipping_rendering.cpp
src/test_polygon_clipping.cpp
src/test_proj_transform1.cpp
src/test_quad_tree.cpp
src/test_rendering_shared_map.cpp
src/test_rendering.cpp
src/test_to_bool.cpp
src/test_to_double.cpp
src/test_to_int.cpp
src/test_to_string1.cpp
src/test_to_string2.cpp
src/test_utf_encoding.cpp
)
function(mapnik_create_benchmark)
get_filename_component(BENCHNAME ${ARGV0} NAME_WE)
set(TARGET_NAME "mapnik-benchmark-${BENCHNAME}")
add_executable(${TARGET_NAME} ${ARGV0})
target_include_directories(${TARGET_NAME} PRIVATE include)
target_link_libraries(${TARGET_NAME} PRIVATE
mapnik::agg
mapnik::mapnik
ICU::data ICU::i18n ICU::uc # needed for the static build (TODO: why isn't this correctly propagated from mapnik::mapnik?)
)
set_target_properties(${TARGET_NAME} PROPERTIES
OUTPUT_NAME "${BENCHNAME}"
)
endfunction()
foreach(benchmark ${BENCHMARK_SRCS})
mapnik_create_benchmark(${benchmark})
endforeach()
file(COPY data DESTINATION "${MAPNIK_OUTPUT_DIR}/benchmark")
file(COPY run_benchmarks
DESTINATION "${MAPNIK_OUTPUT_DIR}"
FILE_PERMISSIONS OWNER_READ OWNER_EXECUTE OWNER_WRITE GROUP_WRITE GROUP_READ GROUP_EXECUTE WORLD_READ
)

View file

@ -2,7 +2,6 @@
#define MAPNIK_BENCH_FRAMEWORK_HPP #define MAPNIK_BENCH_FRAMEWORK_HPP
// mapnik // mapnik
#include <mapnik/mapnik.hpp>
#include <mapnik/debug.hpp> #include <mapnik/debug.hpp>
#include <mapnik/params.hpp> #include <mapnik/params.hpp>
#include <mapnik/value/types.hpp> #include <mapnik/value/types.hpp>
@ -13,10 +12,10 @@
#include <chrono> #include <chrono>
#include <cmath> // log10, round #include <cmath> // log10, round
#include <cstdio> // snprintf #include <cstdio> // snprintf
#include <iomanip>
#include <iostream> #include <iostream>
#include <set>
#include <sstream>
#include <thread> #include <thread>
#include <mutex>
#include <vector> #include <vector>
namespace benchmark { namespace benchmark {
@ -33,16 +32,24 @@ class test_case
mapnik::parameters params_; mapnik::parameters params_;
std::size_t threads_; std::size_t threads_;
std::size_t iterations_; std::size_t iterations_;
public: public:
test_case(mapnik::parameters const& params) test_case(mapnik::parameters const& params)
: params_(params) : params_(params),
, threads_(mapnik::safe_cast<std::size_t>(*params.get<mapnik::value_integer>("threads", 0))) threads_(mapnik::safe_cast<std::size_t>(*params.get<mapnik::value_integer>("threads",0))),
, iterations_(mapnik::safe_cast<std::size_t>(*params.get<mapnik::value_integer>("iterations", 0))) iterations_(mapnik::safe_cast<std::size_t>(*params.get<mapnik::value_integer>("iterations",0)))
{} {}
std::size_t threads() const { return threads_; } std::size_t threads() const
std::size_t iterations() const { return iterations_; } {
mapnik::parameters const& params() const { return params_; } return threads_;
}
std::size_t iterations() const
{
return iterations_;
}
mapnik::parameters const& params() const
{
return params_;
}
virtual bool validate() const = 0; virtual bool validate() const = 0;
virtual bool operator()() const = 0; virtual bool operator()() const = 0;
}; };
@ -52,23 +59,19 @@ class test_case
// or negated index of an ill-formed option argument // or negated index of an ill-formed option argument
inline int parse_args(int argc, char** argv, mapnik::parameters & params) inline int parse_args(int argc, char** argv, mapnik::parameters & params)
{ {
for (int i = 1; i < argc; ++i) for (int i = 1; i < argc; ++i) {
{
const char* opt = argv[i]; const char* opt = argv[i];
if (opt[0] != '-') if (opt[0] != '-') {
{
// non-option argument, return its index // non-option argument, return its index
return i; return i;
} }
if (opt[1] != '-') if (opt[1] != '-') {
{
// we only accept --long-options, but instead of throwing, // we only accept --long-options, but instead of throwing,
// just issue a warning and let the caller decide what to do // just issue a warning and let the caller decide what to do
std::clog << argv[0] << ": invalid option '" << opt << "'\n"; std::clog << argv[0] << ": invalid option '" << opt << "'\n";
return -i; // negative means ill-formed option #i return -i; // negative means ill-formed option #i
} }
if (opt[2] == '\0') if (opt[2] == '\0') {
{
// option-list terminator '--' // option-list terminator '--'
return i + 1; return i + 1;
} }
@ -76,18 +79,15 @@ inline int parse_args(int argc, char** argv, mapnik::parameters& params)
// take option name without the leading '--' // take option name without the leading '--'
std::string key(opt + 2); std::string key(opt + 2);
size_t eq = key.find('='); size_t eq = key.find('=');
if (eq != std::string::npos) if (eq != std::string::npos) {
{
// one-argument form '--foo=bar' // one-argument form '--foo=bar'
params[key.substr(0, eq)] = key.substr(eq + 1); params[key.substr(0, eq)] = key.substr(eq + 1);
} }
else if (i + 1 < argc) else if (i + 1 < argc) {
{
// two-argument form '--foo' 'bar' // two-argument form '--foo' 'bar'
params[key] = std::string(argv[++i]); params[key] = std::string(argv[++i]);
} }
else else {
{
// missing second argument // missing second argument
std::clog << argv[0] << ": missing option '" << opt << "' value\n"; std::clog << argv[0] << ": missing option '" << opt << "' value\n";
return -i; // negative means ill-formed option #i return -i; // negative means ill-formed option #i
@ -98,8 +98,7 @@ inline int parse_args(int argc, char** argv, mapnik::parameters& params)
inline void handle_common_args(mapnik::parameters const& params) inline void handle_common_args(mapnik::parameters const& params)
{ {
if (auto severity = params.get<std::string>("log")) if (auto severity = params.get<std::string>("log")) {
{
if (*severity == "debug") if (*severity == "debug")
mapnik::logger::set_severity(mapnik::logger::debug); mapnik::logger::set_severity(mapnik::logger::debug);
else if (*severity == "warn") else if (*severity == "warn")
@ -109,7 +108,8 @@ inline void handle_common_args(mapnik::parameters const& params)
else if (*severity == "none") else if (*severity == "none")
mapnik::logger::set_severity(mapnik::logger::none); mapnik::logger::set_severity(mapnik::logger::none);
else else
std::clog << "ignoring option --log='" << *severity << "' (allowed values are: debug, warn, error, none)\n"; std::clog << "ignoring option --log='" << *severity
<< "' (allowed values are: debug, warn, error, none)\n";
} }
} }
@ -123,7 +123,6 @@ inline int handle_args(int argc, char** argv, mapnik::parameters& params)
#define BENCHMARK(test_class,name) \ #define BENCHMARK(test_class,name) \
int main(int argc, char** argv) \ int main(int argc, char** argv) \
{ \ { \
mapnik::setup(); \
try \ try \
{ \ { \
mapnik::parameters params; \ mapnik::parameters params; \
@ -139,7 +138,7 @@ inline int handle_args(int argc, char** argv, mapnik::parameters& params)
testing::run_cleanup(); \ testing::run_cleanup(); \
return -1; \ return -1; \
} \ } \
} } \
struct big_number_fmt struct big_number_fmt
{ {
@ -148,9 +147,7 @@ struct big_number_fmt
const char* u; const char* u;
big_number_fmt(int width, double value, int base = 1000) big_number_fmt(int width, double value, int base = 1000)
: w(width) : w(width), v(value), u("")
, v(value)
, u("")
{ {
static const char* suffixes = "\0\0k\0M\0G\0T\0P\0E\0Z\0Y\0\0"; static const char* suffixes = "\0\0k\0M\0G\0T\0P\0E\0Z\0Y\0\0";
u = suffixes; u = suffixes;
@ -197,7 +194,8 @@ int run(T const& test_runner, std::string const& name)
std::mutex mtx_ready; std::mutex mtx_ready;
std::unique_lock<std::mutex> lock_ready(mtx_ready); std::unique_lock<std::mutex> lock_ready(mtx_ready);
auto stub = [&](T const& test_copy) { auto stub = [&](T const& test_copy)
{
// workers will wait on this mutex until the main thread // workers will wait on this mutex until the main thread
// constructs all of them and starts measuring time // constructs all of them and starts measuring time
std::unique_lock<std::mutex> my_lock(mtx_ready); std::unique_lock<std::mutex> my_lock(mtx_ready);
@ -228,8 +226,7 @@ int run(T const& test_runner, std::string const& name)
else else
{ {
start = std::chrono::high_resolution_clock::now(); start = std::chrono::high_resolution_clock::now();
do do {
{
test_runner(); test_runner();
elapsed = std::chrono::high_resolution_clock::now() - start; elapsed = std::chrono::high_resolution_clock::now() - start;
total_iters += num_iters; total_iters += num_iters;
@ -242,26 +239,14 @@ int run(T const& test_runner, std::string const& name)
big_number_fmt itersf(4, total_iters); big_number_fmt itersf(4, total_iters);
big_number_fmt ips(5, total_iters / seconds<double>(elapsed_nonzero).count()); big_number_fmt ips(5, total_iters / seconds<double>(elapsed_nonzero).count());
std::clog << std::left << std::setw(43) << name; std::snprintf(msg, sizeof(msg),
std::clog << std::resetiosflags(std::ios::adjustfield); "%-43s %3zu threads %*.0f%s iters %6.0f milliseconds %*.0f%s i/s\n",
if (num_threads > 0) name.c_str(),
{ num_threads,
std::clog << ' ' << std::setw(3) << num_threads << " worker" << (num_threads > 1 ? "s" : " "); itersf.w, itersf.v, itersf.u,
}
else
{
std::clog << " main thread";
}
std::snprintf(msg,
sizeof(msg),
" %*.0f%s iters %6.0f milliseconds %*.0f%s i/t/s\n",
itersf.w,
itersf.v,
itersf.u,
dur_total, dur_total,
ips.w, ips.w, ips.v, ips.u
ips.v, );
ips.u);
std::clog << msg; std::clog << msg;
return 0; return 0;
} }
@ -280,7 +265,10 @@ struct sequencer
benchmark::handle_args(argc, argv, params_); benchmark::handle_args(argc, argv, params_);
} }
int done() const { return exit_code_; } int done() const
{
return exit_code_;
}
template <typename Test, typename... Args> template <typename Test, typename... Args>
sequencer & run(std::string const& name, Args && ...args) sequencer & run(std::string const& name, Args && ...args)
@ -297,6 +285,6 @@ struct sequencer
int exit_code_; int exit_code_;
}; };
} // namespace benchmark }
#endif // MAPNIK_BENCH_FRAMEWORK_HPP #endif // MAPNIK_BENCH_FRAMEWORK_HPP

View file

@ -9,7 +9,6 @@ test_env = env.Clone()
test_env['LIBS'] = [env['MAPNIK_NAME']] test_env['LIBS'] = [env['MAPNIK_NAME']]
test_env.AppendUnique(LIBS=copy(env['LIBMAPNIK_LIBS'])) test_env.AppendUnique(LIBS=copy(env['LIBMAPNIK_LIBS']))
test_env.AppendUnique(LIBS='mapnik-wkt') test_env.AppendUnique(LIBS='mapnik-wkt')
test_env.AppendUnique(LIBS='sqlite3')
if env['PLATFORM'] == 'Linux': if env['PLATFORM'] == 'Linux':
test_env.AppendUnique(LIBS='dl') test_env.AppendUnique(LIBS='dl')
test_env.AppendUnique(LIBS='rt') test_env.AppendUnique(LIBS='rt')
@ -19,19 +18,40 @@ test_env.Append(CPPDEFINES = env['LIBMAPNIK_DEFINES'])
if test_env['HAS_CAIRO']: if test_env['HAS_CAIRO']:
test_env.PrependUnique(CPPPATH=test_env['CAIRO_CPPPATHS']) test_env.PrependUnique(CPPPATH=test_env['CAIRO_CPPPATHS'])
test_env.Append(CPPDEFINES = '-DHAVE_CAIRO') test_env.Append(CPPDEFINES = '-DHAVE_CAIRO')
test_env.PrependUnique(CPPPATH='include', delete_existing=True)
test_env['LINKFLAGS'] = copy(test_env['LIBMAPNIK_LINKFLAGS']) test_env['LINKFLAGS'] = copy(test_env['LIBMAPNIK_LINKFLAGS'])
if env['PLATFORM'] == 'Darwin': if env['PLATFORM'] == 'Darwin':
test_env.Append(LINKFLAGS='-F/ -framework CoreFoundation') test_env.Append(LINKFLAGS='-F/ -framework CoreFoundation')
test_env_local = test_env.Clone() test_env_local = test_env.Clone()
benchmarks = glob.glob("src/*.cpp") #benchmarks = glob.glob('test*cpp')
benchmarks = [
for src in benchmarks: #"test_array_allocation.cpp",
name, ext = os.path.splitext(os.path.basename(src)) #"test_png_encoding1.cpp",
out = os.path.join("out", name) #"test_png_encoding2.cpp",
test_program = test_env_local.Program(out, source=[src]) #"test_to_string1.cpp",
#"test_to_string2.cpp",
#"test_to_bool.cpp",
#"test_to_double.cpp",
#"test_to_int.cpp",
#"test_utf_encoding.cpp"
"test_polygon_clipping.cpp",
#"test_polygon_clipping_rendering.cpp",
"test_proj_transform1.cpp",
"test_expression_parse.cpp",
"test_face_ptr_creation.cpp",
"test_font_registration.cpp",
"test_rendering.cpp",
"test_rendering_shared_map.cpp",
"test_offset_converter.cpp",
"test_marker_cache.cpp",
"test_quad_tree.cpp",
"test_noop_rendering.cpp",
"test_getline.cpp",
# "test_numeric_cast_vs_static_cast.cpp",
]
for cpp_test in benchmarks:
test_program = test_env_local.Program('out/'+cpp_test.replace('.cpp',''), source=[cpp_test])
if 'install' in COMMAND_LINE_TARGETS: if 'install' in COMMAND_LINE_TARGETS:
env.Alias('install',test_program) env.Alias('install',test_program)
#Depends(test_program, env.subst('../src/%s' % env['MAPNIK_LIB_NAME'])) #Depends(test_program, env.subst('../src/%s' % env['MAPNIK_LIB_NAME']))

View file

@ -0,0 +1,36 @@
#ifndef MAPNIK_COMPARE_IMAGES_HPP
#define MAPNIK_COMPARE_IMAGES_HPP
#include <mapnik/image.hpp>
#include <mapnik/image_util.hpp>
#include <mapnik/image_reader.hpp>
namespace benchmark {
bool compare_images(std::string const& src_fn,std::string const& dest_fn)
{
std::unique_ptr<mapnik::image_reader> reader1(mapnik::get_image_reader(dest_fn,"png"));
if (!reader1.get())
{
throw mapnik::image_reader_exception("Failed to load: " + dest_fn);
}
std::unique_ptr<mapnik::image_reader> reader2(mapnik::get_image_reader(src_fn,"png"));
if (!reader2.get())
{
throw mapnik::image_reader_exception("Failed to load: " + src_fn);
}
const mapnik::image_any desc_any = reader1->read(0,0,reader1->width(), reader1->height());
const mapnik::image_any src_any = reader2->read(0,0,reader2->width(), reader2->height());
mapnik::image_rgba8 const& dest = mapnik::util::get<mapnik::image_rgba8>(desc_any);
mapnik::image_rgba8 const& src = mapnik::util::get<mapnik::image_rgba8>(src_any);
return compare(dest, src, 0, true) == 0;
}
}
#endif // MAPNIK_COMPARE_IMAGES_HPP

View file

@ -1,7 +1,7 @@
<?xml version="1.0" encoding="utf-8"?> <?xml version="1.0" encoding="utf-8"?>
<!DOCTYPE Map[]> <!DOCTYPE Map[]>
<Map <Map
srs="epsg:4326" srs="+init=epsg:4326"
background-color="#dfd8c9"> background-color="#dfd8c9">
<Style name="style"> <Style name="style">
@ -10,7 +10,7 @@
</Rule> </Rule>
</Style> </Style>
<Layer name="layer" <Layer name="layer"
srs="epsg:4326"> srs="+init=epsg:4326">
<StyleName>style</StyleName> <StyleName>style</StyleName>
<Datasource> <Datasource>
<Parameter name="file">./valid.geotiff.tif</Parameter> <Parameter name="file">./valid.geotiff.tif</Parameter>

View file

@ -1,7 +1,7 @@
<?xml version="1.0" encoding="utf-8"?> <?xml version="1.0" encoding="utf-8"?>
<!DOCTYPE Map[]> <!DOCTYPE Map[]>
<Map <Map
srs="epsg:4326" srs="+init=epsg:4326"
background-color="#dfd8c9"> background-color="#dfd8c9">
<Style name="style"> <Style name="style">
@ -10,7 +10,7 @@
</Rule> </Rule>
</Style> </Style>
<Layer name="layer" <Layer name="layer"
srs="epsg:4326"> srs="+init=epsg:4326">
<StyleName>style</StyleName> <StyleName>style</StyleName>
<Datasource> <Datasource>
<Parameter name="file">./valid.geotiff.tif</Parameter> <Parameter name="file">./valid.geotiff.tif</Parameter>

View file

@ -1,35 +0,0 @@
#ifndef MAPNIK_COMPARE_IMAGES_HPP
#define MAPNIK_COMPARE_IMAGES_HPP
#include <mapnik/image.hpp>
#include <mapnik/image_util.hpp>
#include <mapnik/image_reader.hpp>
namespace benchmark {
bool compare_images(std::string const& src_fn, std::string const& dest_fn)
{
std::unique_ptr<mapnik::image_reader> reader1(mapnik::get_image_reader(dest_fn, "png"));
if (!reader1.get())
{
throw mapnik::image_reader_exception("Failed to load: " + dest_fn);
}
std::unique_ptr<mapnik::image_reader> reader2(mapnik::get_image_reader(src_fn, "png"));
if (!reader2.get())
{
throw mapnik::image_reader_exception("Failed to load: " + src_fn);
}
const mapnik::image_any desc_any = reader1->read(0, 0, reader1->width(), reader1->height());
const mapnik::image_any src_any = reader2->read(0, 0, reader2->width(), reader2->height());
mapnik::image_rgba8 const& dest = mapnik::util::get<mapnik::image_rgba8>(desc_any);
mapnik::image_rgba8 const& src = mapnik::util::get<mapnik::image_rgba8>(src_any);
return compare(dest, src, 0, true) == 0;
}
} // namespace benchmark
#endif // MAPNIK_COMPARE_IMAGES_HPP

View file

@ -28,7 +28,6 @@ run test_expression_parse 10 10000
run test_face_ptr_creation 10 1000 run test_face_ptr_creation 10 1000
run test_font_registration 10 100 run test_font_registration 10 100
run test_offset_converter 10 1000 run test_offset_converter 10 1000
#run normalize_angle 0 1000000 --min-duration=0.2
# commented since this is really slow on travis # commented since this is really slow on travis
: ' : '

View file

@ -1,65 +0,0 @@
#!/bin/bash
BASE=.
function run {
local runner="$BASE/$1 --log=none"
local threads="$2"
local iters="$3"
shift 3
$runner --threads 0 --iterations $iters "$@"
if test $threads -gt 0; then
$runner --threads $threads --iterations $((iters/threads)) "$@"
fi
}
run test_getline 30 10000000
#run test_array_allocation 20 100000
#run test_png_encoding1 10 1000
#run test_png_encoding2 10 50
#run test_to_string1 10 100000
#run test_to_string2 10 100000
#run test_polygon_clipping 10 1000
#run test_polygon_clipping_rendering 10 100
run test_proj_transform1 10 100
run test_expression_parse 10 10000
run test_face_ptr_creation 10 1000
run test_font_registration 10 100
run test_offset_converter 10 1000
#run normalize_angle 0 1000000 --min-duration=0.2
# commented since this is really slow on travis
: '
$BASE/test_rendering \
--name "text rendering" \
--map benchmark/data/roads.xml \
--extent 1477001.12245,6890242.37746,1480004.49012,6892244.62256 \
--width 600 \
--height 600 \
--iterations 20 \
--threads 10
'
$BASE/test_rendering \
--name "gdal tiff rendering" \
--map benchmark/data/gdal-wgs.xml \
--extent -180.0,-120.0,180.0,120.0 \
--width 600 \
--height 600 \
--iterations 20 \
--threads 10
$BASE/test_rendering \
--name "raster tiff rendering" \
--map benchmark/data/raster-wgs.xml \
--extent -180.0,-120.0,180.0,120.0 \
--width 600 \
--height 600 \
--iterations 20 \
--threads 10
$BASE/test_quad_tree \
--iterations 10000 \
--threads 1
$BASE/test_quad_tree \
--iterations 1000 \
--threads 10

View file

@ -1,72 +0,0 @@
#include "bench_framework.hpp"
#include <mapnik/util/math.hpp>
template<typename T>
struct bench_func : benchmark::test_case
{
T (*const func_)(T);
T const value_;
bench_func(mapnik::parameters const& params, T (*func)(T), T value)
: test_case(params)
, func_(func)
, value_(value)
{}
bool validate() const { return true; }
bool operator()() const
{
for (auto i = this->iterations_; i-- > 0;)
{
func_(value_);
}
return true;
}
};
#define BENCH_FUNC1(func, value) run<bench_func<double>>(#func "(" #value ")", func, value)
int main(int argc, char** argv)
{
mapnik::setup();
return benchmark::sequencer(argc, argv)
.BENCH_FUNC1(mapnik::util::normalize_angle, +3)
.BENCH_FUNC1(mapnik::util::normalize_angle, +6)
.BENCH_FUNC1(mapnik::util::normalize_angle, +9)
.BENCH_FUNC1(mapnik::util::normalize_angle, +12)
.BENCH_FUNC1(mapnik::util::normalize_angle, +15)
.BENCH_FUNC1(mapnik::util::normalize_angle, +20)
.BENCH_FUNC1(mapnik::util::normalize_angle, +30)
.BENCH_FUNC1(mapnik::util::normalize_angle, +40)
.BENCH_FUNC1(mapnik::util::normalize_angle, +50)
.BENCH_FUNC1(mapnik::util::normalize_angle, +70)
.BENCH_FUNC1(mapnik::util::normalize_angle, +90)
.BENCH_FUNC1(mapnik::util::normalize_angle, +110)
.BENCH_FUNC1(mapnik::util::normalize_angle, +130)
.BENCH_FUNC1(mapnik::util::normalize_angle, +157)
.BENCH_FUNC1(mapnik::util::normalize_angle, +209)
.BENCH_FUNC1(mapnik::util::normalize_angle, +314)
.BENCH_FUNC1(mapnik::util::normalize_angle, +628)
.BENCH_FUNC1(mapnik::util::normalize_angle, +942)
.BENCH_FUNC1(mapnik::util::normalize_angle, -3)
.BENCH_FUNC1(mapnik::util::normalize_angle, -6)
.BENCH_FUNC1(mapnik::util::normalize_angle, -9)
.BENCH_FUNC1(mapnik::util::normalize_angle, -12)
.BENCH_FUNC1(mapnik::util::normalize_angle, -15)
.BENCH_FUNC1(mapnik::util::normalize_angle, -20)
.BENCH_FUNC1(mapnik::util::normalize_angle, -30)
.BENCH_FUNC1(mapnik::util::normalize_angle, -40)
.BENCH_FUNC1(mapnik::util::normalize_angle, -50)
.BENCH_FUNC1(mapnik::util::normalize_angle, -70)
.BENCH_FUNC1(mapnik::util::normalize_angle, -90)
.BENCH_FUNC1(mapnik::util::normalize_angle, -110)
.BENCH_FUNC1(mapnik::util::normalize_angle, -130)
.BENCH_FUNC1(mapnik::util::normalize_angle, -157)
.BENCH_FUNC1(mapnik::util::normalize_angle, -209)
.BENCH_FUNC1(mapnik::util::normalize_angle, -314)
.BENCH_FUNC1(mapnik::util::normalize_angle, -628)
.BENCH_FUNC1(mapnik::util::normalize_angle, -942)
.done();
}

View file

@ -1,370 +0,0 @@
#include "bench_framework.hpp"
#include <cstring>
#include <cstdlib>
#include <deque>
#include <stdexcept>
#include <array>
#include <valarray>
#include <boost/version.hpp>
#if BOOST_VERSION >= 105400
#include <boost/container/static_vector.hpp>
#endif
// http://stackoverflow.com/questions/17347254/why-is-allocation-and-deallocation-of-stdvector-slower-than-dynamic-array-on-m
#define FULL_ZERO_CHECK
inline void ensure_zero(uint8_t* data, uint32_t size)
{
#ifdef FULL_ZERO_CHECK
for (std::size_t i = 0; i < size; ++i)
{
if (data[i] != 0)
{
throw std::runtime_error("found non zero value");
}
}
#else
if (data[0] != 0)
{
throw std::runtime_error("found non zero value");
}
#endif
}
class test1 : public benchmark::test_case
{
public:
uint32_t size_;
std::vector<uint8_t> array_;
test1(mapnik::parameters const& params)
: test_case(params)
, size_(*params.get<mapnik::value_integer>("size", 256 * 256))
, array_(size_, 0)
{}
bool validate() const { return true; }
bool operator()() const
{
for (std::size_t i = 0; i < iterations_; ++i)
{
// NOTE: sizeof(uint8_t) == 1
uint8_t* data = (uint8_t*)malloc(sizeof(uint8_t) * size_);
memcpy(data, &array_[0], size_);
ensure_zero(data, size_);
free(data);
}
return true;
}
};
class test1b : public benchmark::test_case
{
public:
uint32_t size_;
std::vector<uint8_t> array_;
test1b(mapnik::parameters const& params)
: test_case(params)
, size_(*params.get<mapnik::value_integer>("size", 256 * 256))
, array_(size_, 0)
{}
bool validate() const { return true; }
bool operator()() const
{
for (std::size_t i = 0; i < iterations_; ++i)
{
// NOTE: sizeof(uint8_t) == 1
uint8_t* data = (uint8_t*)malloc(sizeof(uint8_t) * size_);
memset(data, 0, sizeof(uint8_t) * size_);
ensure_zero(data, size_);
free(data);
}
return true;
}
};
class test1c : public benchmark::test_case
{
public:
uint32_t size_;
std::vector<uint8_t> array_;
test1c(mapnik::parameters const& params)
: test_case(params)
, size_(*params.get<mapnik::value_integer>("size", 256 * 256))
, array_(size_, 0)
{}
bool validate() const { return true; }
bool operator()() const
{
for (std::size_t i = 0; i < iterations_; ++i)
{
uint8_t* data = static_cast<uint8_t*>(::operator new(sizeof(uint8_t) * size_));
std::fill(data, data + size_, 0);
ensure_zero(data, size_);
::operator delete(data);
}
return true;
}
};
class test2 : public benchmark::test_case
{
public:
uint32_t size_;
std::vector<uint8_t> array_;
test2(mapnik::parameters const& params)
: test_case(params)
, size_(*params.get<mapnik::value_integer>("size", 256 * 256))
, array_(size_, 0)
{}
bool validate() const { return true; }
bool operator()() const
{
for (std::size_t i = 0; i < iterations_; ++i)
{
uint8_t* data = static_cast<uint8_t*>(::operator new(sizeof(uint8_t) * size_));
memcpy(data, &array_[0], size_);
ensure_zero(data, size_);
::operator delete(data), data = 0;
}
return true;
}
};
class test3 : public benchmark::test_case
{
public:
uint32_t size_;
std::vector<uint8_t> array_;
test3(mapnik::parameters const& params)
: test_case(params)
, size_(*params.get<mapnik::value_integer>("size", 256 * 256))
, array_(size_, 0)
{}
bool validate() const { return true; }
bool operator()() const
{
for (std::size_t i = 0; i < iterations_; ++i)
{
std::vector<uint8_t> data(size_);
ensure_zero(&data[0], data.size());
}
return true;
}
};
class test3b : public benchmark::test_case
{
public:
uint32_t size_;
std::vector<uint8_t> array_;
test3b(mapnik::parameters const& params)
: test_case(params)
, size_(*params.get<mapnik::value_integer>("size", 256 * 256))
, array_(size_, 0)
{}
bool validate() const { return true; }
bool operator()() const
{
for (std::size_t i = 0; i < iterations_; ++i)
{
std::vector<uint8_t> data(0);
data.resize(size_, 0);
ensure_zero(&data[0], data.size());
}
return true;
}
};
class test3c : public benchmark::test_case
{
public:
uint32_t size_;
std::vector<uint8_t> array_;
test3c(mapnik::parameters const& params)
: test_case(params)
, size_(*params.get<mapnik::value_integer>("size", 256 * 256))
, array_(size_, 0)
{}
bool validate() const { return true; }
bool operator()() const
{
for (std::size_t i = 0; i < iterations_; ++i)
{
std::vector<uint8_t> data(0);
data.assign(size_, 0);
ensure_zero(&data[0], data.size());
}
return true;
}
};
class test3d : public benchmark::test_case
{
public:
uint32_t size_;
std::vector<uint8_t> array_;
test3d(mapnik::parameters const& params)
: test_case(params)
, size_(*params.get<mapnik::value_integer>("size", 256 * 256))
, array_(size_, 0)
{}
bool validate() const { return true; }
bool operator()() const
{
for (std::size_t i = 0; i < iterations_; ++i)
{
std::deque<uint8_t> data(size_);
for (std::size_t i = 0; i < size_; ++i)
{
if (data[i] != 0)
{
throw std::runtime_error("found non zero value");
}
}
}
return true;
}
};
class test4 : public benchmark::test_case
{
public:
uint32_t size_;
std::vector<uint8_t> array_;
test4(mapnik::parameters const& params)
: test_case(params)
, size_(*params.get<mapnik::value_integer>("size", 256 * 256))
, array_(size_, 0)
{}
bool validate() const { return true; }
bool operator()() const
{
for (std::size_t i = 0; i < iterations_; ++i)
{
uint8_t* data = (uint8_t*)calloc(size_, sizeof(uint8_t));
ensure_zero(data, size_);
free(data);
}
return true;
}
};
class test5 : public benchmark::test_case
{
public:
uint32_t size_;
std::vector<uint8_t> array_;
test5(mapnik::parameters const& params)
: test_case(params)
, size_(*params.get<mapnik::value_integer>("size", 256 * 256))
, array_(size_, 0)
{}
bool validate() const { return true; }
bool operator()() const
{
for (std::size_t i = 0; i < iterations_; ++i)
{
std::string data(array_.begin(), array_.end());
ensure_zero((uint8_t*)&data[0], size_);
}
return true;
}
};
class test5b : public benchmark::test_case
{
public:
uint32_t size_;
std::vector<char> array_;
test5b(mapnik::parameters const& params)
: test_case(params)
, size_(*params.get<mapnik::value_integer>("size", 256 * 256))
, array_(size_, 0)
{}
bool validate() const { return true; }
bool operator()() const
{
for (std::size_t i = 0; i < iterations_; ++i)
{
std::string data(&array_[0], array_.size());
ensure_zero((uint8_t*)&data[0], size_);
}
return true;
}
};
// C++14 dynarray<T>
// http://isocpp.org/blog/2013/04/trip-report-iso-c-spring-2013-meeting
// http://lists.cs.uiuc.edu/pipermail/cfe-commits/Week-of-Mon-20130909/088700.html
// http://stackoverflow.com/questions/17303902/any-alternative-to-stddynarray-presently-available
class test6 : public benchmark::test_case
{
public:
uint32_t size_;
std::vector<uint8_t> array_;
test6(mapnik::parameters const& params)
: test_case(params)
, size_(*params.get<mapnik::value_integer>("size", 256 * 256))
, array_(size_, 0)
{}
bool validate() const { return true; }
bool operator()() const
{
for (std::size_t i = 0; i < iterations_; ++i)
{
std::valarray<uint8_t> data(static_cast<uint8_t>(0), static_cast<size_t>(size_));
ensure_zero(&data[0], size_);
}
return true;
}
};
#if BOOST_VERSION >= 105400
// http://i42.co.uk/stuff/vecarray.htm
// http://www.boost.org/doc/libs/1_54_0/doc/html/boost/container/static_vector.html
class test7 : public benchmark::test_case
{
public:
uint32_t size_;
std::vector<uint8_t> array_;
test7(mapnik::parameters const& params)
: test_case(params)
, size_(*params.get<mapnik::value_integer>("size", 256 * 256))
, array_(size_, 0)
{}
bool validate() const { return true; }
bool operator()() const
{
for (std::size_t i = 0; i < iterations_; ++i)
{
boost::container::static_vector<uint8_t, 256 * 256> data(size_, 0);
ensure_zero(&data[0], size_);
}
return true;
}
};
#endif
int main(int argc, char** argv)
{
mapnik::setup();
return benchmark::sequencer(argc, argv)
.run<test4>("calloc")
.run<test1>("malloc/memcpy")
.run<test1b>("malloc/memset")
.run<test1c>("operator new/std::fill")
.run<test2>("operator new/memcpy")
.run<test3>("vector(N)")
.run<test3b>("vector/resize")
.run<test3c>("vector/assign")
.run<test3d>("deque(N)")
.run<test5>("std::string range")
.run<test5b>("std::string &[0]")
.run<test6>("valarray")
#if BOOST_VERSION >= 105400
.run<test7>("static_vector")
#endif
.done();
}

View file

@ -1,40 +0,0 @@
#include "bench_framework.hpp"
#include <mapnik/marker_cache.hpp>
class test : public benchmark::test_case
{
std::vector<std::string> images_;
public:
test(mapnik::parameters const& params)
: test_case(params)
, images_{"./test/data/images/dummy.jpg",
"./test/data/images/dummy.jpeg",
"./test/data/images/dummy.png",
"./test/data/images/dummy.tif",
"./test/data/images/dummy.tiff",
//"./test/data/images/landusepattern.jpeg", // will fail since it is a png
//"./test/data/images/xcode-CgBI.png", // will fail since its an invalid png
"./test/data/svg/octocat.svg",
"./test/data/svg/place-of-worship-24.svg",
"./test/data/svg/point_sm.svg",
"./test/data/svg/point.svg",
"./test/data/svg/airfield-12.svg"}
{}
bool validate() const { return true; }
bool operator()() const
{
unsigned count = 0;
for (std::size_t i = 0; i < iterations_; ++i)
{
for (auto filename : images_)
{
auto marker = mapnik::marker_cache::instance().find(filename, true);
}
++count;
}
return (count == iterations_);
}
};
BENCHMARK(test, "marker cache")

View file

@ -1,59 +0,0 @@
#include "bench_framework.hpp"
#include <mapnik/map.hpp>
#include <mapnik/load_map.hpp>
#include <mapnik/agg_renderer.hpp>
#include <mapnik/datasource_cache.hpp>
class test : public benchmark::test_case
{
std::string xml_;
mapnik::box2d<double> extent_;
public:
test(mapnik::parameters const& params, std::string const& xml, mapnik::box2d<double> const& extent)
: test_case(params)
, xml_(xml)
, extent_(extent)
{}
bool validate() const
{
mapnik::Map m(256, 256);
mapnik::load_map(m, xml_);
m.zoom_to_box(extent_);
mapnik::image_rgba8 im(m.width(), m.height());
mapnik::agg_renderer<mapnik::image_rgba8> ren(m, im);
ren.apply();
// mapnik::save_to_file(im.data(),"test.png");
return true;
}
bool operator()() const
{
mapnik::Map m(256, 256);
mapnik::load_map(m, xml_);
m.zoom_to_box(extent_);
for (unsigned i = 0; i < iterations_; ++i)
{
mapnik::image_rgba8 im(m.width(), m.height());
mapnik::agg_renderer<mapnik::image_rgba8> ren(m, im);
ren.apply();
}
return true;
}
};
int main(int argc, char** argv)
{
mapnik::setup();
mapnik::parameters params;
benchmark::handle_args(argc, argv, params);
mapnik::datasource_cache::instance().register_datasources("./plugins/input/");
mapnik::box2d<double> z1(-20037508.3428, -8317435.0606, 20037508.3428, 18399242.7298);
// bbox for 16/10491/22911.png
mapnik::box2d<double> z16(-13622912.929097254, 6026906.8062295765, -13621689.93664469, 6028129.79868214);
return benchmark::sequencer(argc, argv)
.run<test>("polygon clip render z1", "benchmark/data/polygon_rendering_clip.xml", z1)
.run<test>("polygon noclip render z1", "benchmark/data/polygon_rendering_no_clip.xml", z1)
.run<test>("polygon clip render z16", "benchmark/data/polygon_rendering_clip.xml", z16)
.run<test>("polygon noclip render z16", "benchmark/data/polygon_rendering_no_clip.xml", z16)
.done();
}

View file

@ -1,77 +0,0 @@
#include "bench_framework.hpp"
#include <mapnik/geometry/box2d.hpp>
#include <mapnik/projection.hpp>
#include <mapnik/proj_transform.hpp>
class test : public benchmark::test_case
{
std::string src_;
std::string dest_;
mapnik::box2d<double> from_;
mapnik::box2d<double> to_;
bool defer_proj_init_;
public:
test(mapnik::parameters const& params,
std::string const& src,
std::string const& dest,
mapnik::box2d<double> const& from,
mapnik::box2d<double> const& to,
bool defer_proj)
: test_case(params)
, src_(src)
, dest_(dest)
, from_(from)
, to_(to)
, defer_proj_init_(defer_proj)
{}
bool validate() const
{
mapnik::projection src(src_, defer_proj_init_);
mapnik::projection dest(dest_, defer_proj_init_);
mapnik::proj_transform tr(src, dest);
mapnik::box2d<double> bbox = from_;
if (!tr.forward(bbox))
return false;
return ((std::fabs(bbox.minx() - to_.minx()) < .5) && (std::fabs(bbox.maxx() - to_.maxx()) < .5) &&
(std::fabs(bbox.miny() - to_.miny()) < .5) && (std::fabs(bbox.maxy() - to_.maxy()) < .5));
}
bool operator()() const
{
mapnik::projection src(src_, defer_proj_init_);
mapnik::projection dest(dest_, defer_proj_init_);
mapnik::proj_transform tr(src, dest);
for (std::size_t i = 0; i < iterations_; ++i)
{
for (int j = -180; j < 180; j = j + 5)
{
for (int k = -85; k < 85; k = k + 5)
{
mapnik::box2d<double> box(j, k, j, k);
if (!tr.forward(box))
throw std::runtime_error("could not transform coords");
}
}
}
return true;
}
};
// echo -180 -60 | cs2cs -f "%.10f" epsg:4326 +to epsg:3857
int main(int argc, char** argv)
{
mapnik::setup();
mapnik::box2d<double> from(-180, -80, 180, 80);
mapnik::box2d<double> to(-20037508.3427892476, -15538711.0963092316, 20037508.3427892476, 15538711.0963092316);
std::string from_str("epsg:4326");
std::string to_str("epsg:3857");
std::string from_str2("+proj=longlat +ellps=WGS84 +datum=WGS84 +no_defs");
std::string to_str2("+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");
return benchmark::sequencer(argc, argv)
.run<test>("lonlat->merc epsg (internal)", from_str, to_str, from, to, true)
.run<test>("lonlat->merc literal (libproj)", from_str2, to_str2, from, to, true)
.run<test>("merc->lonlat epsg (internal)", to_str, from_str, to, from, true)
.run<test>("merc->lonlat literal (libproj)", to_str2, from_str2, to, from, true)
.done();
}

View file

@ -1,34 +0,0 @@
#include "bench_framework.hpp"
#include <mapnik/util/conversions.hpp>
class test : public benchmark::test_case
{
std::string value_;
public:
test(mapnik::parameters const& params)
: test_case(params)
, value_("true")
{}
bool validate() const
{
bool result = false;
mapnik::util::string2bool(value_.data(), value_.data() + value_.size(), result);
if (!result)
return result;
mapnik::util::string2bool(value_, result);
return (result == true);
}
bool operator()() const
{
for (std::size_t i = 0; i < iterations_; ++i)
{
bool result = false;
mapnik::util::string2bool(value_, result);
mapnik::util::string2bool(value_.data(), value_.data() + value_.size(), result);
}
return true;
}
};
BENCHMARK(test, "string->bool")

View file

@ -1,39 +0,0 @@
#include "bench_framework.hpp"
#include <mapnik/util/conversions.hpp>
class test : public benchmark::test_case
{
std::string value_;
public:
test(mapnik::parameters const& params)
: test_case(params)
, value_("1.23456789")
{}
bool validate() const
{
double result = 0;
if (!mapnik::util::string2double(value_.data(), value_.data() + value_.size(), result))
return false;
if (result != 1.23456789)
return false;
result = 0;
if (!mapnik::util::string2double(value_, result))
return false;
if (result != 1.23456789)
return false;
return true;
}
bool operator()() const
{
for (std::size_t i = 0; i < iterations_; ++i)
{
double result = 0;
mapnik::util::string2double(value_, result);
mapnik::util::string2double(value_.data(), value_.data() + value_.size(), result);
}
return true;
}
};
BENCHMARK(test, "string->double")

View file

@ -1,39 +0,0 @@
#include "bench_framework.hpp"
#include <mapnik/util/conversions.hpp>
class test : public benchmark::test_case
{
std::string value_;
public:
test(mapnik::parameters const& params)
: test_case(params)
, value_("123456789")
{}
bool validate() const
{
mapnik::value_integer result = 0;
if (!mapnik::util::string2int(value_.data(), value_.data() + value_.size(), result))
return false;
if (result != 123456789)
return false;
result = 0;
if (!mapnik::util::string2int(value_, result))
return false;
if (result != 123456789)
return false;
return true;
}
bool operator()() const
{
for (std::size_t i = 0; i < iterations_; ++i)
{
mapnik::value_integer result = 0;
mapnik::util::string2int(value_, result);
mapnik::util::string2int(value_.data(), value_.data() + value_.size(), result);
}
return true;
}
};
BENCHMARK(test, "string->int")

View file

@ -4,10 +4,14 @@ class test : public benchmark::test_case
{ {
public: public:
test(mapnik::parameters const& params) test(mapnik::parameters const& params)
: test_case(params) : test_case(params) {}
{} bool validate() const
bool validate() const { return true; } {
void operator()() const {} return true;
}
void operator()() const
{
}
}; };
BENCHMARK(test,"test name") BENCHMARK(test,"test name")

View file

@ -0,0 +1,379 @@
#include "bench_framework.hpp"
#include <cstring>
#include <cstdlib>
#include <deque>
#include <stdexcept>
#include <array>
#include <valarray>
#include <boost/version.hpp>
#if BOOST_VERSION >= 105400
#include <boost/container/static_vector.hpp>
#endif
// http://stackoverflow.com/questions/17347254/why-is-allocation-and-deallocation-of-stdvector-slower-than-dynamic-array-on-m
#define FULL_ZERO_CHECK
inline void ensure_zero(uint8_t * data, uint32_t size) {
#ifdef FULL_ZERO_CHECK
for (std::size_t i=0;i<size;++i) {
if (data[i] != 0) {
throw std::runtime_error("found non zero value");
}
}
#else
if (data[0] != 0) {
throw std::runtime_error("found non zero value");
}
#endif
}
class test1 : public benchmark::test_case
{
public:
uint32_t size_;
std::vector<uint8_t> array_;
test1(mapnik::parameters const& params)
: test_case(params),
size_(*params.get<mapnik::value_integer>("size",256*256)),
array_(size_,0) { }
bool validate() const
{
return true;
}
bool operator()() const
{
for (std::size_t i=0;i<iterations_;++i) {
// NOTE: sizeof(uint8_t) == 1
uint8_t *data = (uint8_t *)malloc(sizeof(uint8_t)*size_);
memcpy(data, &array_[0], size_);
ensure_zero(data,size_);
free(data);
}
return true;
}
};
class test1b : public benchmark::test_case
{
public:
uint32_t size_;
std::vector<uint8_t> array_;
test1b(mapnik::parameters const& params)
: test_case(params),
size_(*params.get<mapnik::value_integer>("size",256*256)),
array_(size_,0) { }
bool validate() const
{
return true;
}
bool operator()() const
{
for (std::size_t i=0;i<iterations_;++i) {
// NOTE: sizeof(uint8_t) == 1
uint8_t *data = (uint8_t *)malloc(sizeof(uint8_t)*size_);
memset(data, 0, sizeof(uint8_t)*size_);
ensure_zero(data,size_);
free(data);
}
return true;
}
};
class test1c : public benchmark::test_case
{
public:
uint32_t size_;
std::vector<uint8_t> array_;
test1c(mapnik::parameters const& params)
: test_case(params),
size_(*params.get<mapnik::value_integer>("size",256*256)),
array_(size_,0) { }
bool validate() const
{
return true;
}
bool operator()() const
{
for (std::size_t i=0;i<iterations_;++i) {
uint8_t *data = static_cast<uint8_t *>(::operator new(sizeof(uint8_t) * size_));
std::fill(data,data + size_,0);
ensure_zero(data,size_);
::operator delete(data);
}
return true;
}
};
class test2 : public benchmark::test_case
{
public:
uint32_t size_;
std::vector<uint8_t> array_;
test2(mapnik::parameters const& params)
: test_case(params),
size_(*params.get<mapnik::value_integer>("size",256*256)),
array_(size_,0) { }
bool validate() const
{
return true;
}
bool operator()() const
{
for (std::size_t i=0;i<iterations_;++i) {
uint8_t * data = static_cast<uint8_t*>(::operator new(sizeof(uint8_t)*size_));
memcpy(data, &array_[0], size_);
ensure_zero(data,size_);
::operator delete(data),data=0;
}
return true;
}
};
class test3 : public benchmark::test_case
{
public:
uint32_t size_;
std::vector<uint8_t> array_;
test3(mapnik::parameters const& params)
: test_case(params),
size_(*params.get<mapnik::value_integer>("size",256*256)),
array_(size_,0) { }
bool validate() const
{
return true;
}
bool operator()() const
{
for (std::size_t i=0;i<iterations_;++i) {
std::vector<uint8_t> data(size_);
ensure_zero(&data[0],data.size());
}
return true;
}
};
class test3b : public benchmark::test_case
{
public:
uint32_t size_;
std::vector<uint8_t> array_;
test3b(mapnik::parameters const& params)
: test_case(params),
size_(*params.get<mapnik::value_integer>("size",256*256)),
array_(size_,0) { }
bool validate() const
{
return true;
}
bool operator()() const
{
for (std::size_t i=0;i<iterations_;++i) {
std::vector<uint8_t> data(0);
data.resize(size_,0);
ensure_zero(&data[0],data.size());
}
return true;
}
};
class test3c : public benchmark::test_case
{
public:
uint32_t size_;
std::vector<uint8_t> array_;
test3c(mapnik::parameters const& params)
: test_case(params),
size_(*params.get<mapnik::value_integer>("size",256*256)),
array_(size_,0) { }
bool validate() const
{
return true;
}
bool operator()() const
{
for (std::size_t i=0;i<iterations_;++i) {
std::vector<uint8_t> data(0);
data.assign(size_,0);
ensure_zero(&data[0],data.size());
}
return true;
}
};
class test3d : public benchmark::test_case
{
public:
uint32_t size_;
std::vector<uint8_t> array_;
test3d(mapnik::parameters const& params)
: test_case(params),
size_(*params.get<mapnik::value_integer>("size",256*256)),
array_(size_,0) { }
bool validate() const
{
return true;
}
bool operator()() const
{
for (std::size_t i=0;i<iterations_;++i) {
std::deque<uint8_t> data(size_);
for (std::size_t i=0;i<size_;++i) {
if (data[i] != 0) {
throw std::runtime_error("found non zero value");
}
}
}
return true;
}
};
class test4 : public benchmark::test_case
{
public:
uint32_t size_;
std::vector<uint8_t> array_;
test4(mapnik::parameters const& params)
: test_case(params),
size_(*params.get<mapnik::value_integer>("size",256*256)),
array_(size_,0) { }
bool validate() const
{
return true;
}
bool operator()() const
{
for (std::size_t i=0;i<iterations_;++i) {
uint8_t *data = (uint8_t *)calloc(size_,sizeof(uint8_t));
ensure_zero(data,size_);
free(data);
}
return true;
}
};
class test5 : public benchmark::test_case
{
public:
uint32_t size_;
std::vector<uint8_t> array_;
test5(mapnik::parameters const& params)
: test_case(params),
size_(*params.get<mapnik::value_integer>("size",256*256)),
array_(size_,0) { }
bool validate() const
{
return true;
}
bool operator()() const
{
for (std::size_t i=0;i<iterations_;++i) {
std::string data(array_.begin(),array_.end());
ensure_zero((uint8_t *)&data[0],size_);
}
return true;
}
};
class test5b : public benchmark::test_case
{
public:
uint32_t size_;
std::vector<char> array_;
test5b(mapnik::parameters const& params)
: test_case(params),
size_(*params.get<mapnik::value_integer>("size",256*256)),
array_(size_,0) { }
bool validate() const
{
return true;
}
bool operator()() const
{
for (std::size_t i=0;i<iterations_;++i) {
std::string data(&array_[0],array_.size());
ensure_zero((uint8_t *)&data[0],size_);
}
return true;
}
};
// C++14 dynarray<T>
// http://isocpp.org/blog/2013/04/trip-report-iso-c-spring-2013-meeting
// http://lists.cs.uiuc.edu/pipermail/cfe-commits/Week-of-Mon-20130909/088700.html
// http://stackoverflow.com/questions/17303902/any-alternative-to-stddynarray-presently-available
class test6 : public benchmark::test_case
{
public:
uint32_t size_;
std::vector<uint8_t> array_;
test6(mapnik::parameters const& params)
: test_case(params),
size_(*params.get<mapnik::value_integer>("size",256*256)),
array_(size_,0) { }
bool validate() const
{
return true;
}
bool operator()() const
{
for (std::size_t i=0;i<iterations_;++i) {
std::valarray<uint8_t> data(static_cast<uint8_t>(0),static_cast<size_t>(size_));
ensure_zero(&data[0],size_);
}
return true;
}
};
#if BOOST_VERSION >= 105400
// http://i42.co.uk/stuff/vecarray.htm
// http://www.boost.org/doc/libs/1_54_0/doc/html/boost/container/static_vector.html
class test7 : public benchmark::test_case
{
public:
uint32_t size_;
std::vector<uint8_t> array_;
test7(mapnik::parameters const& params)
: test_case(params),
size_(*params.get<mapnik::value_integer>("size",256*256)),
array_(size_,0) { }
bool validate() const
{
return true;
}
bool operator()() const
{
for (std::size_t i=0;i<iterations_;++i) {
boost::container::static_vector<uint8_t,256*256> data(size_,0);
ensure_zero(&data[0],size_);
}
return true;
}
};
#endif
int main(int argc, char** argv)
{
return benchmark::sequencer(argc, argv)
.run<test4>("calloc")
.run<test1>("malloc/memcpy")
.run<test1b>("malloc/memset")
.run<test1c>("operator new/std::fill")
.run<test2>("operator new/memcpy")
.run<test3>("vector(N)")
.run<test3b>("vector/resize")
.run<test3c>("vector/assign")
.run<test3d>("deque(N)")
.run<test5>("std::string range")
.run<test5b>("std::string &[0]")
.run<test6>("valarray")
#if BOOST_VERSION >= 105400
.run<test7>("static_vector")
#endif
.done();
}

View file

@ -7,12 +7,10 @@
class test : public benchmark::test_case class test : public benchmark::test_case
{ {
std::string expr_; std::string expr_;
public: public:
test(mapnik::parameters const& params) test(mapnik::parameters const& params)
: test_case(params) : test_case(params),
, expr_("((([mapnik::geometry_type]=2) and ([oneway]=1)) and ([class]='path'))") expr_("((([mapnik::geometry_type]=2) and ([oneway]=1)) and ([class]='path'))") {}
{}
bool validate() const bool validate() const
{ {
mapnik::expression_ptr expr = mapnik::parse_expression(expr_); mapnik::expression_ptr expr = mapnik::parse_expression(expr_);
@ -26,17 +24,16 @@ class test : public benchmark::test_case
} }
bool operator()() const bool operator()() const
{ {
for (std::size_t i = 0; i < iterations_; ++i) for (std::size_t i=0;i<iterations_;++i) {
{
mapnik::expression_ptr expr = mapnik::parse_expression(expr_); mapnik::expression_ptr expr = mapnik::parse_expression(expr_);
} }
return true; return true;
} }
}; };
int main(int argc, char** argv) int main(int argc, char** argv)
{ {
mapnik::setup();
mapnik::parameters params; mapnik::parameters params;
benchmark::handle_args(argc,argv,params); benchmark::handle_args(argc,argv,params);
test test_runner(params); test test_runner(params);

View file

@ -6,8 +6,7 @@ class test : public benchmark::test_case
{ {
public: public:
test(mapnik::parameters const& params) test(mapnik::parameters const& params)
: test_case(params) : test_case(params) {}
{}
bool validate() const bool validate() const
{ {
std::size_t count = 0; std::size_t count = 0;
@ -23,8 +22,7 @@ class test : public benchmark::test_case
font_cache, font_cache,
mapnik::freetype_engine::get_mapping(), mapnik::freetype_engine::get_mapping(),
mapnik::freetype_engine::get_cache()); mapnik::freetype_engine::get_cache());
if (f) if (f) ++count;
++count;
} }
return count == expected_count; return count == expected_count;
} }
@ -45,11 +43,9 @@ class test : public benchmark::test_case
font_cache, font_cache,
mapnik::freetype_engine::get_mapping(), mapnik::freetype_engine::get_mapping(),
mapnik::freetype_engine::get_cache()); mapnik::freetype_engine::get_cache());
if (f) if (f) ++count;
++count;
} }
if (count != expected_count) if (count != expected_count) {
{
std::clog << "warning: face creation not working as expected\n"; std::clog << "warning: face creation not working as expected\n";
} }
} }
@ -59,12 +55,10 @@ class test : public benchmark::test_case
int main(int argc, char** argv) int main(int argc, char** argv)
{ {
mapnik::setup();
mapnik::parameters params; mapnik::parameters params;
benchmark::handle_args(argc,argv,params); benchmark::handle_args(argc,argv,params);
bool success = mapnik::freetype_engine::register_fonts("./fonts", true); bool success = mapnik::freetype_engine::register_fonts("./fonts", true);
if (!success) if (!success) {
{
std::clog << "warning, did not register any new fonts!\n"; std::clog << "warning, did not register any new fonts!\n";
return -1; return -1;
} }
@ -72,3 +66,4 @@ int main(int argc, char** argv)
test test_runner(params); test test_runner(params);
return run(test_runner,(boost::format("font_engine: creating %ld faces") % (face_count)).str()); return run(test_runner,(boost::format("font_engine: creating %ld faces") % (face_count)).str());
} }

View file

@ -1,14 +1,17 @@
#include "bench_framework.hpp" #include "bench_framework.hpp"
#include <mapnik/font_engine_freetype.hpp> #include <mapnik/font_engine_freetype.hpp>
#include <boost/format.hpp> #include <boost/format.hpp>
#include <boost/foreach.hpp>
class test : public benchmark::test_case class test : public benchmark::test_case
{ {
public: public:
test(mapnik::parameters const& params) test(mapnik::parameters const& params)
: test_case(params) : test_case(params) {}
{} bool validate() const
bool validate() const { return mapnik::freetype_engine::register_fonts("./fonts", true); } {
return mapnik::freetype_engine::register_fonts("./fonts", true);
}
bool operator()() const bool operator()() const
{ {
unsigned long count = 0; unsigned long count = 0;

View file

@ -1,15 +1,17 @@
#include "bench_framework.hpp" #include "bench_framework.hpp"
#include "../plugins/input/csv/csv_getline.hpp" #include "../plugins/input/csv/csv_getline.hpp"
class test : public benchmark::test_case class test : public benchmark::test_case
{ {
public: public:
std::string line_data_; std::string line_data_;
test(mapnik::parameters const& params) test(mapnik::parameters const& params)
: test_case(params) : test_case(params),
, line_data_("this is one line\nand this is a second line\nand a third line") line_data_("this is one line\nand this is a second line\nand a third line")
{ {
auto line_data = params.get<std::string>("line"); boost::optional<std::string> line_data = params.get<std::string>("line");
if (line_data) if (line_data)
{ {
line_data_ = *line_data; line_data_ = *line_data;
@ -30,8 +32,7 @@ class test : public benchmark::test_case
} }
else else
{ {
std::clog << "Error: the parsed line (" << csv_line << ") should be a subset of the original line (" std::clog << "Error: the parsed line (" << csv_line << ") should be a subset of the original line (" << line_data_ << ") (ensure you pass a line with a \\n)\n";
<< line_data_ << ") (ensure you pass a line with a \\n)\n";
} }
return true; return true;
} }
@ -49,15 +50,16 @@ class test : public benchmark::test_case
} }
}; };
class test2 : public benchmark::test_case class test2 : public benchmark::test_case
{ {
public: public:
std::string line_data_; std::string line_data_;
test2(mapnik::parameters const& params) test2(mapnik::parameters const& params)
: test_case(params) : test_case(params),
, line_data_("this is one line\nand this is a second line\nand a third line") line_data_("this is one line\nand this is a second line\nand a third line")
{ {
auto line_data = params.get<std::string>("line"); boost::optional<std::string> line_data = params.get<std::string>("line");
if (line_data) if (line_data)
{ {
line_data_ = *line_data; line_data_ = *line_data;
@ -79,8 +81,7 @@ class test2 : public benchmark::test_case
} }
else else
{ {
std::clog << "Error: the parsed line (" << csv_line << ") should be a subset of the original line (" std::clog << "Error: the parsed line (" << csv_line << ") should be a subset of the original line (" << line_data_ << ") (ensure you pass a line with a \\n)\n";
<< line_data_ << ") (ensure you pass a line with a \\n)\n";
} }
return true; return true;
} }
@ -101,7 +102,6 @@ class test2 : public benchmark::test_case
int main(int argc, char** argv) int main(int argc, char** argv)
{ {
mapnik::setup();
int return_value = 0; int return_value = 0;
try try
{ {

View file

@ -0,0 +1,42 @@
#include "bench_framework.hpp"
#include <mapnik/marker_cache.hpp>
class test : public benchmark::test_case
{
std::vector<std::string> images_;
public:
test(mapnik::parameters const& params)
: test_case(params),
images_{
"./test/data/images/dummy.jpg",
"./test/data/images/dummy.jpeg",
"./test/data/images/dummy.png",
"./test/data/images/dummy.tif",
"./test/data/images/dummy.tiff",
//"./test/data/images/landusepattern.jpeg", // will fail since it is a png
//"./test/data/images/xcode-CgBI.png", // will fail since its an invalid png
"./test/data/svg/octocat.svg",
"./test/data/svg/place-of-worship-24.svg",
"./test/data/svg/point_sm.svg",
"./test/data/svg/point.svg",
"./test/data/svg/airfield-12.svg"
} {}
bool validate() const
{
return true;
}
bool operator()() const
{
unsigned count = 0;
for (std::size_t i=0;i<iterations_;++i) {
for (auto filename : images_)
{
auto marker = mapnik::marker_cache::instance().find(filename,true);
}
++count;
}
return (count == iterations_);
}
};
BENCHMARK(test,"marker cache")

View file

@ -16,13 +16,15 @@ class test : public benchmark::test_case
{ {
public: public:
test(mapnik::parameters const& params) test(mapnik::parameters const& params)
: test_case(params) : test_case(params) {}
{}
bool validate() const { return true; } bool validate() const
{
return true;
}
bool operator()() const bool operator()() const
{ {
mapnik::Map m(256, 256, "epsg:3857"); mapnik::Map m(256,256,"+init=epsg:3857");
mapnik::parameters params; mapnik::parameters params;
params["type"]="memory"; params["type"]="memory";

View file

@ -9,25 +9,23 @@ class test_static : public benchmark::test_case
{ {
double step_; double step_;
std::uint8_t start_; std::uint8_t start_;
public: public:
test_static(mapnik::parameters const& params) test_static(mapnik::parameters const& params)
: test_case(params) : test_case(params),
, step_(STEP_NUM) step_(STEP_NUM),
, start_(START_NUM) start_(START_NUM) {}
{} bool validate() const
bool validate() const { return true; } {
return true;
}
bool operator()() const bool operator()() const
{ {
double value_ = 0.0; double value_ = 0.0;
std::uint8_t x; std::uint8_t x;
for (std::size_t i = 0; i < iterations_; ++i) for (std::size_t i=0;i<iterations_;++i) {
{
double c = static_cast<double>(start_) * value_; double c = static_cast<double>(start_) * value_;
if (c >= 256.0) if (c >= 256.0) c = 255.0;
c = 255.0; if (c < 0.0) c = 0.0;
if (c < 0.0)
c = 0.0;
x = static_cast<std::uint8_t>(c); x = static_cast<std::uint8_t>(c);
value_ += step_; value_ += step_;
} }
@ -35,29 +33,28 @@ class test_static : public benchmark::test_case
} }
}; };
using boost::numeric::negative_overflow;
using boost::numeric::positive_overflow; using boost::numeric::positive_overflow;
using boost::numeric::negative_overflow;
class test_numeric : public benchmark::test_case class test_numeric : public benchmark::test_case
{ {
double step_; double step_;
std::uint8_t start_; std::uint8_t start_;
public: public:
test_numeric(mapnik::parameters const& params) test_numeric(mapnik::parameters const& params)
: test_case(params) : test_case(params),
, step_(STEP_NUM) step_(STEP_NUM),
, start_(START_NUM) start_(START_NUM) {}
{} bool validate() const
bool validate() const { return true; } {
return true;
}
bool operator()() const bool operator()() const
{ {
double value_ = 0.0; double value_ = 0.0;
std::uint8_t x; std::uint8_t x;
for (std::size_t i = 0; i < iterations_; ++i) for (std::size_t i=0;i<iterations_;++i) {
{ try {
try
{
x = boost::numeric_cast<std::uint8_t>(start_ * value_); x = boost::numeric_cast<std::uint8_t>(start_ * value_);
} }
catch(negative_overflow&) catch(negative_overflow&)
@ -76,6 +73,8 @@ class test_numeric : public benchmark::test_case
int main(int argc, char** argv) int main(int argc, char** argv)
{ {
mapnik::setup(); return benchmark::sequencer(argc, argv)
return benchmark::sequencer(argc, argv).run<test_static>("static_cast").run<test_numeric>("numeric_cast").done(); .run<test_static>("static_cast")
.run<test_numeric>("numeric_cast")
.done();
} }

View file

@ -14,36 +14,31 @@ struct fake_path
cont_type::iterator itr_; cont_type::iterator itr_;
fake_path(std::initializer_list<double> l) fake_path(std::initializer_list<double> l)
: fake_path(l.begin(), l.size()) : fake_path(l.begin(), l.size()) {
{} }
fake_path(std::vector<double> const &v) fake_path(std::vector<double> const &v)
: fake_path(v.begin(), v.size()) : fake_path(v.begin(), v.size()) {
{} }
template <typename Itr> template <typename Itr>
fake_path(Itr itr, size_t sz) fake_path(Itr itr, size_t sz) {
{
size_t num_coords = sz >> 1; size_t num_coords = sz >> 1;
vertices_.reserve(num_coords); vertices_.reserve(num_coords);
for (size_t i = 0; i < num_coords; ++i) for (size_t i = 0; i < num_coords; ++i) {
{
double x = *itr++; double x = *itr++;
double y = *itr++; double y = *itr++;
unsigned cmd = (i == 0) ? mapnik::SEG_MOVETO : mapnik::SEG_LINETO; unsigned cmd = (i == 0) ? mapnik::SEG_MOVETO : mapnik::SEG_LINETO;
vertices_.push_back(std::make_tuple(x, y, cmd)); vertices_.push_back(std::make_tuple(x, y, cmd));
if (i == num_coords - 1) if (i == num_coords - 1) cmd = mapnik::SEG_END;
cmd = mapnik::SEG_END;
vertices_.push_back(std::make_tuple(x, y, cmd)); vertices_.push_back(std::make_tuple(x, y, cmd));
} }
itr_ = vertices_.begin(); itr_ = vertices_.begin();
} }
unsigned vertex(double* x, double* y) unsigned vertex(double *x, double *y) {
{ if (itr_ == vertices_.end()) {
if (itr_ == vertices_.end())
{
return mapnik::SEG_END; return mapnik::SEG_END;
} }
*x = std::get<0>(*itr_); *x = std::get<0>(*itr_);
@ -53,16 +48,20 @@ struct fake_path
return cmd; return cmd;
} }
void rewind(unsigned) { itr_ = vertices_.begin(); } void rewind(unsigned) {
itr_ = vertices_.begin();
}
}; };
class test_offset : public benchmark::test_case class test_offset : public benchmark::test_case
{ {
public: public:
test_offset(mapnik::parameters const& params) test_offset(mapnik::parameters const& params)
: test_case(params) : test_case(params) {}
{} bool validate() const
bool validate() const { return true; } {
return true;
}
bool operator()() const bool operator()() const
{ {
std::vector<double> path; std::vector<double> path;
@ -75,8 +74,7 @@ class test_offset : public benchmark::test_case
path.push_back( 0 ); path.push_back( 0 );
} }
fake_path fpath(path); fake_path fpath(path);
for (std::size_t i = 0; i < iterations_; ++i) for (std::size_t i=0;i<iterations_;++i) {
{
mapnik::offset_converter<fake_path> off_path(fpath); mapnik::offset_converter<fake_path> off_path(fpath);
off_path.set_offset(10); off_path.set_offset(10);
unsigned cmd; unsigned cmd;
@ -90,9 +88,9 @@ class test_offset : public benchmark::test_case
} }
}; };
int main(int argc, char** argv) int main(int argc, char** argv)
{ {
mapnik::setup();
mapnik::parameters params; mapnik::parameters params;
benchmark::handle_args(argc,argv,params); benchmark::handle_args(argc,argv,params);
int return_value = 0; int return_value = 0;

View file

@ -4,18 +4,18 @@
class test : public benchmark::test_case class test : public benchmark::test_case
{ {
mapnik::image_rgba8 im_; mapnik::image_rgba8 im_;
public: public:
test(mapnik::parameters const& params) test(mapnik::parameters const& params)
: test_case(params) : test_case(params),
, im_(256, 256) im_(256,256) {}
{} bool validate() const
bool validate() const { return true; } {
return true;
}
bool operator()() const bool operator()() const
{ {
std::string out; std::string out;
for (std::size_t i = 0; i < iterations_; ++i) for (std::size_t i=0;i<iterations_;++i) {
{
out.clear(); out.clear();
out = mapnik::save_to_string(im_,"png8:m=h:z=1"); out = mapnik::save_to_string(im_,"png8:m=h:z=1");
} }

View file

@ -1,15 +1,12 @@
#include "bench_framework.hpp" #include "bench_framework.hpp"
#include "compare_images.hpp" #include "compare_images.hpp"
#include <memory>
class test : public benchmark::test_case class test : public benchmark::test_case
{ {
std::shared_ptr<mapnik::image_rgba8> im_; std::shared_ptr<mapnik::image_rgba8> im_;
public: public:
test(mapnik::parameters const& params) test(mapnik::parameters const& params)
: test_case(params) : test_case(params) {
{
std::string filename("./benchmark/data/multicolor.png"); std::string filename("./benchmark/data/multicolor.png");
std::unique_ptr<mapnik::image_reader> reader(mapnik::get_image_reader(filename,"png")); std::unique_ptr<mapnik::image_reader> reader(mapnik::get_image_reader(filename,"png"));
if (!reader.get()) if (!reader.get())
@ -29,8 +26,7 @@ class test : public benchmark::test_case
bool operator()() const bool operator()() const
{ {
std::string out; std::string out;
for (std::size_t i = 0; i < iterations_; ++i) for (std::size_t i=0;i<iterations_;++i) {
{
out.clear(); out.clear();
out = mapnik::save_to_string(*im_,"png8:m=h:z=1"); out = mapnik::save_to_string(*im_,"png8:m=h:z=1");
} }

View file

@ -39,8 +39,7 @@ void render(mapnik::geometry::multi_polygon<double> const& geom,
mapnik::box2d<double> const& extent, mapnik::box2d<double> const& extent,
std::string const& name) std::string const& name)
{ {
using path_type = using path_type = mapnik::transform_path_adapter<mapnik::view_transform,mapnik::geometry::polygon_vertex_adapter<double>>;
mapnik::transform_path_adapter<mapnik::view_transform, mapnik::geometry::polygon_vertex_adapter<double>>;
using ren_base = agg::renderer_base<agg::pixfmt_rgba32_plain>; using ren_base = agg::renderer_base<agg::pixfmt_rgba32_plain>;
using renderer = agg::renderer_scanline_aa_solid<ren_base>; using renderer = agg::renderer_scanline_aa_solid<ren_base>;
mapnik::image_rgba8 im(256,256); mapnik::image_rgba8 im(256,256);
@ -52,7 +51,7 @@ void render(mapnik::geometry::multi_polygon<double> const& geom,
agg::pixfmt_rgba32_plain pixf(buf); agg::pixfmt_rgba32_plain pixf(buf);
ren_base renb(pixf); ren_base renb(pixf);
renderer ren(renb); renderer ren(renb);
mapnik::proj_transform prj_trans(mapnik::projection("epsg:4326"), mapnik::projection("epsg:4326")); mapnik::proj_transform prj_trans(mapnik::projection("+init=epsg:4326"),mapnik::projection("+init=epsg:4326"));
ren.color(agg::rgba8(127,127,127,255)); ren.color(agg::rgba8(127,127,127,255));
agg::rasterizer_scanline_aa<> ras; agg::rasterizer_scanline_aa<> ras;
for (auto const& poly : geom) for (auto const& poly : geom)
@ -71,15 +70,15 @@ class test1 : public benchmark::test_case
std::string wkt_in_; std::string wkt_in_;
mapnik::box2d<double> extent_; mapnik::box2d<double> extent_;
std::string expected_; std::string expected_;
public: public:
using conv_clip = agg::conv_clip_polygon<mapnik::geometry::polygon_vertex_adapter<double>>; using conv_clip = agg::conv_clip_polygon<mapnik::geometry::polygon_vertex_adapter<double>>;
test1(mapnik::parameters const& params, std::string const& wkt_in, mapnik::box2d<double> const& extent) test1(mapnik::parameters const& params,
: test_case(params) std::string const& wkt_in,
, wkt_in_(wkt_in) mapnik::box2d<double> const& extent)
, extent_(extent) : test_case(params),
, expected_("./benchmark/data/polygon_clipping_agg") wkt_in_(wkt_in),
{} extent_(extent),
expected_("./benchmark/data/polygon_clipping_agg") {}
bool validate() const bool validate() const
{ {
mapnik::geometry::geometry<double> geom; mapnik::geometry::geometry<double> geom;
@ -100,8 +99,14 @@ class test1 : public benchmark::test_case
mapnik::geometry::polygon<double> const& poly = mapnik::util::get<mapnik::geometry::polygon<double>>(geom); mapnik::geometry::polygon<double> const& poly = mapnik::util::get<mapnik::geometry::polygon<double>>(geom);
mapnik::geometry::polygon_vertex_adapter<double> va(poly); mapnik::geometry::polygon_vertex_adapter<double> va(poly);
conv_clip clipped(va); conv_clip clipped(va);
clipped.clip_box(extent_.minx(), extent_.miny(), extent_.maxx(), extent_.maxy()); clipped.clip_box(
extent_.minx(),
extent_.miny(),
extent_.maxx(),
extent_.maxy());
clipped.rewind(0); clipped.rewind(0);
mapnik::geometry::polygon<double> poly2; mapnik::geometry::polygon<double> poly2;
@ -113,8 +118,7 @@ class test1 : public benchmark::test_case
{ {
if (cmd == mapnik::SEG_MOVETO) if (cmd == mapnik::SEG_MOVETO)
{ {
x0 = x; x0 = x; y0 = y;
y0 = y;
} }
if (cmd == mapnik::SEG_CLOSE) if (cmd == mapnik::SEG_CLOSE)
@ -131,8 +135,7 @@ class test1 : public benchmark::test_case
{ {
if (cmd == mapnik::SEG_MOVETO) if (cmd == mapnik::SEG_MOVETO)
{ {
x0 = x; x0 = x; y0 = y;
y0 = y;
} }
else if (cmd == mapnik::SEG_CLOSE) else if (cmd == mapnik::SEG_CLOSE)
{ {
@ -181,22 +184,23 @@ class test1 : public benchmark::test_case
mapnik::geometry::polygon<double> const& poly = mapnik::util::get<mapnik::geometry::polygon<double>>(geom); mapnik::geometry::polygon<double> const& poly = mapnik::util::get<mapnik::geometry::polygon<double>>(geom);
mapnik::geometry::polygon_vertex_adapter<double> va(poly); mapnik::geometry::polygon_vertex_adapter<double> va(poly);
conv_clip clipped(va); conv_clip clipped(va);
clipped.clip_box(extent_.minx(), extent_.miny(), extent_.maxx(), extent_.maxy()); clipped.clip_box(
extent_.minx(),
extent_.miny(),
extent_.maxx(),
extent_.maxy());
unsigned cmd; unsigned cmd;
double x,y; double x,y;
// NOTE: this rewind is critical otherwise // NOTE: this rewind is critical otherwise
// agg_conv_adapter_vpgen will give garbage // agg_conv_adapter_vpgen will give garbage
// values for the first vertex // values for the first vertex
clipped.rewind(0); clipped.rewind(0);
while ((cmd = clipped.vertex(&x, &y)) != mapnik::SEG_END) while ((cmd = clipped.vertex(&x, &y)) != mapnik::SEG_END) {
{
count++; count++;
} }
unsigned expected_count = 30; unsigned expected_count = 30;
if (count != expected_count) if (count != expected_count) {
{ std::clog << "test1: clipping failed: processed " << count << " verticies but expected " << expected_count << "\n";
std::clog << "test1: clipping failed: processed " << count << " verticies but expected "
<< expected_count << "\n";
valid = false; valid = false;
} }
} }
@ -204,19 +208,20 @@ class test1 : public benchmark::test_case
} }
}; };
class test3 : public benchmark::test_case class test3 : public benchmark::test_case
{ {
std::string wkt_in_; std::string wkt_in_;
mapnik::box2d<double> extent_; mapnik::box2d<double> extent_;
std::string expected_; std::string expected_;
public: public:
test3(mapnik::parameters const& params, std::string const& wkt_in, mapnik::box2d<double> const& extent) test3(mapnik::parameters const& params,
: test_case(params) std::string const& wkt_in,
, wkt_in_(wkt_in) mapnik::box2d<double> const& extent)
, extent_(extent) : test_case(params),
, expected_("./benchmark/data/polygon_clipping_boost") wkt_in_(wkt_in),
{} extent_(extent),
expected_("./benchmark/data/polygon_clipping_boost") {}
bool validate() const bool validate() const
{ {
mapnik::geometry::geometry<double> geom; mapnik::geometry::geometry<double> geom;
@ -303,15 +308,12 @@ class test3 : public benchmark::test_case
mapnik::geometry::polygon_vertex_adapter<double> va(_geom); mapnik::geometry::polygon_vertex_adapter<double> va(_geom);
unsigned cmd; unsigned cmd;
double x,y; double x,y;
while ((cmd = va.vertex(&x, &y)) != mapnik::SEG_END) while ((cmd = va.vertex(&x, &y)) != mapnik::SEG_END) {
{
++count; ++count;
} }
unsigned expected_count = 29; unsigned expected_count = 29;
if (count != expected_count) if (count != expected_count) {
{ std::clog << "test3: clipping failed: processed " << count << " verticies but expected " << expected_count << "\n";
std::clog << "test3: clipping failed: processed " << count << " verticies but expected "
<< expected_count << "\n";
valid = false; valid = false;
} }
} }
@ -498,8 +500,8 @@ public:
} }
unsigned expected_count = 29; unsigned expected_count = 29;
if (count != expected_count) { if (count != expected_count) {
std::clog << "test3: clipping failed: processed " << count << " verticies but expected " << std::clog << "test3: clipping failed: processed " << count << " verticies but expected " << expected_count << "\n";
expected_count << "\n"; valid = false; valid = false;
} }
} }
} }
@ -510,18 +512,14 @@ expected_count << "\n"; valid = false;
int main(int argc, char** argv) int main(int argc, char** argv)
{ {
mapnik::setup();
mapnik::parameters params; mapnik::parameters params;
benchmark::handle_args(argc,argv,params); benchmark::handle_args(argc,argv,params);
// polygon/rect clipping // polygon/rect clipping
// IN : POLYGON ((155 203, 233 454, 315 340, 421 446, 463 324, 559 466, 665 253, 528 178, 394 229, 329 138, 212 134, // IN : POLYGON ((155 203, 233 454, 315 340, 421 446, 463 324, 559 466, 665 253, 528 178, 394 229, 329 138, 212 134, 183 228, 200 264, 155 203),(313 190, 440 256, 470 248, 510 305, 533 237, 613 263, 553 397, 455 262, 405 378, 343 287, 249 334, 229 191, 313 190))
// 183 228, 200 264, 155 203),(313 190, 440 256, 470 248, 510 305, 533 237, 613 263, 553 397, 455 262, 405 378, 343 // RECT : POLYGON ((181 106, 181 470, 631 470, 631 106, 181 106))
// 287, 249 334, 229 191, 313 190)) RECT : POLYGON ((181 106, 181 470, 631 470, 631 106, 181 106)) OUT (expected) // OUT (expected)
// POLYGON ((181 286.6666666666667, 233 454, 315 340, 421 446, 463 324, 559 466, 631 321.3207547169811, 631 // POLYGON ((181 286.6666666666667, 233 454, 315 340, 421 446, 463 324, 559 466, 631 321.3207547169811, 631 234.38686131386862, 528 178, 394 229, 329 138, 212 134, 183 228, 200 264, 181 238.24444444444444, 181 286.6666666666667),(313 190, 440 256, 470 248, 510 305, 533 237, 613 263, 553 397, 455 262, 405 378, 343 287, 249 334, 229 191, 313 190))
// 234.38686131386862, 528 178, 394 229, 329 138, 212 134, 183 228, 200 264, 181 238.24444444444444, 181
// 286.6666666666667),(313 190, 440 256, 470 248, 510 305, 533 237, 613 263, 553 397, 455 262, 405 378, 343 287, 249
// 334, 229 191, 313 190))
#if 0 #if 0
mapnik::box2d<double> clipping_box(181,106,631,470); mapnik::box2d<double> clipping_box(181,106,631,470);
std::string filename_("./benchmark/data/polygon.wkt"); std::string filename_("./benchmark/data/polygon.wkt");

View file

@ -0,0 +1,60 @@
#include "bench_framework.hpp"
#include <mapnik/map.hpp>
#include <mapnik/load_map.hpp>
#include <mapnik/agg_renderer.hpp>
#include <mapnik/datasource_cache.hpp>
class test : public benchmark::test_case
{
std::string xml_;
mapnik::box2d<double> extent_;
public:
test(mapnik::parameters const& params,
std::string const& xml,
mapnik::box2d<double> const& extent)
: test_case(params),
xml_(xml),
extent_(extent)
{}
bool validate() const
{
mapnik::Map m(256,256);
mapnik::load_map(m,xml_);
m.zoom_to_box(extent_);
mapnik::image_rgba8 im(m.width(),m.height());
mapnik::agg_renderer<mapnik::image_rgba8> ren(m,im);
ren.apply();
//mapnik::save_to_file(im.data(),"test.png");
return true;
}
bool operator()() const
{
mapnik::Map m(256,256);
mapnik::load_map(m,xml_);
m.zoom_to_box(extent_);
for (unsigned i=0;i<iterations_;++i)
{
mapnik::image_rgba8 im(m.width(),m.height());
mapnik::agg_renderer<mapnik::image_rgba8> ren(m,im);
ren.apply();
}
return true;
}
};
int main(int argc, char** argv)
{
mapnik::parameters params;
benchmark::handle_args(argc,argv,params);
mapnik::datasource_cache::instance().register_datasources("./plugins/input/");
mapnik::box2d<double> z1(-20037508.3428,-8317435.0606,20037508.3428,18399242.7298);
// bbox for 16/10491/22911.png
mapnik::box2d<double> z16(-13622912.929097254,6026906.8062295765,-13621689.93664469,6028129.79868214);
return benchmark::sequencer(argc, argv)
.run<test>("polygon clip render z1", "benchmark/data/polygon_rendering_clip.xml", z1)
.run<test>("polygon noclip render z1", "benchmark/data/polygon_rendering_no_clip.xml", z1)
.run<test>("polygon clip render z16", "benchmark/data/polygon_rendering_clip.xml", z16)
.run<test>("polygon noclip render z16", "benchmark/data/polygon_rendering_no_clip.xml", z16)
.done();
}

View file

@ -0,0 +1,74 @@
#include "bench_framework.hpp"
#include <mapnik/geometry/box2d.hpp>
#include <mapnik/projection.hpp>
#include <mapnik/proj_transform.hpp>
class test : public benchmark::test_case
{
std::string src_;
std::string dest_;
mapnik::box2d<double> from_;
mapnik::box2d<double> to_;
bool defer_proj4_init_;
public:
test(mapnik::parameters const& params,
std::string const& src,
std::string const& dest,
mapnik::box2d<double> const& from,
mapnik::box2d<double> const& to,
bool defer_proj)
: test_case(params),
src_(src),
dest_(dest),
from_(from),
to_(to),
defer_proj4_init_(defer_proj) {}
bool validate() const
{
mapnik::projection src(src_,defer_proj4_init_);
mapnik::projection dest(dest_,defer_proj4_init_);
mapnik::proj_transform tr(src,dest);
mapnik::box2d<double> bbox = from_;
if (!tr.forward(bbox)) return false;
return ((std::fabs(bbox.minx() - to_.minx()) < .5) &&
(std::fabs(bbox.maxx() - to_.maxx()) < .5) &&
(std::fabs(bbox.miny() - to_.miny()) < .5) &&
(std::fabs(bbox.maxy() - to_.maxy()) < .5)
);
}
bool operator()() const
{
for (std::size_t i=0;i<iterations_;++i)
{
for (int j=-180;j<180;j=j+5)
{
for (int k=-85;k<85;k=k+5)
{
mapnik::projection src(src_,defer_proj4_init_);
mapnik::projection dest(dest_,defer_proj4_init_);
mapnik::proj_transform tr(src,dest);
mapnik::box2d<double> box(j,k,j,k);
if (!tr.forward(box)) throw std::runtime_error("could not transform coords");
}
}
}
return true;
}
};
// echo -180 -60 | cs2cs -f "%.10f" +init=epsg:4326 +to +init=epsg:3857
int main(int argc, char** argv)
{
mapnik::box2d<double> from(-180,-80,180,80);
mapnik::box2d<double> to(-20037508.3427892476,-15538711.0963092316,20037508.3427892476,15538711.0963092316);
std::string from_str("+init=epsg:4326");
std::string to_str("+init=epsg:3857");
std::string from_str2("+proj=longlat +ellps=WGS84 +datum=WGS84 +no_defs");
std::string to_str2("+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");
return benchmark::sequencer(argc, argv)
.run<test>("lonlat->merc epsg", from_str, to_str, from, to, true)
.run<test>("lonlat->merc literal", from_str2, to_str2, from, to, true)
.run<test>("merc->lonlat epsg", to_str, from_str, to, from, true)
.run<test>("merc->lonlat literal", to_str2, from_str2, to, from, true)
.done();
}

View file

@ -8,10 +8,12 @@ class test : public benchmark::test_case
{ {
public: public:
test(mapnik::parameters const& params) test(mapnik::parameters const& params)
: test_case(params) : test_case(params) {}
{}
bool validate() const { return true; } bool validate() const
{
return true;
}
bool operator()() const bool operator()() const
{ {

View file

@ -15,25 +15,24 @@ class test : public benchmark::test_case
mapnik::value_integer height_; mapnik::value_integer height_;
double scale_factor_; double scale_factor_;
std::string preview_; std::string preview_;
public: public:
test(mapnik::parameters const& params) test(mapnik::parameters const& params)
: test_case(params) : test_case(params),
, xml_() xml_(),
, extent_() extent_(),
, width_(*params.get<mapnik::value_integer>("width", 256)) width_(*params.get<mapnik::value_integer>("width",256)),
, height_(*params.get<mapnik::value_integer>("height", 256)) height_(*params.get<mapnik::value_integer>("height",256)),
, scale_factor_(*params.get<mapnik::value_double>("scale_factor", 1.0)) scale_factor_(*params.get<mapnik::value_double>("scale_factor",1.0)),
, preview_(*params.get<std::string>("preview", "")) preview_(*params.get<std::string>("preview",""))
{ {
const auto map = params.get<std::string>("map"); boost::optional<std::string> map = params.get<std::string>("map");
if (!map) if (!map)
{ {
throw std::runtime_error("please provide a --map <path to xml> arg"); throw std::runtime_error("please provide a --map <path to xml> arg");
} }
xml_ = *map; xml_ = *map;
const auto ext = params.get<std::string>("extent"); boost::optional<std::string> ext = params.get<std::string>("extent");
if (ext && !ext->empty()) if (ext && !ext->empty())
{ {
if (!extent_.from_string(*ext)) if (!extent_.from_string(*ext))
@ -44,24 +43,21 @@ class test : public benchmark::test_case
{ {
throw std::runtime_error("please provide a --extent=<minx,miny,maxx,maxy> arg"); throw std::runtime_error("please provide a --extent=<minx,miny,maxx,maxy> arg");
}*/ }*/
} }
bool validate() const bool validate() const
{ {
mapnik::Map m(width_,height_); mapnik::Map m(width_,height_);
mapnik::load_map(m,xml_,true); mapnik::load_map(m,xml_,true);
if (extent_.valid()) if (extent_.valid()) {
{
m.zoom_to_box(extent_); m.zoom_to_box(extent_);
} } else {
else
{
m.zoom_all(); m.zoom_all();
} }
mapnik::image_rgba8 im(m.width(),m.height()); mapnik::image_rgba8 im(m.width(),m.height());
mapnik::agg_renderer<mapnik::image_rgba8> ren(m,im,scale_factor_); mapnik::agg_renderer<mapnik::image_rgba8> ren(m,im,scale_factor_);
ren.apply(); ren.apply();
if (!preview_.empty()) if (!preview_.empty()) {
{
std::clog << "preview available at " << preview_ << "\n"; std::clog << "preview available at " << preview_ << "\n";
mapnik::save_to_file(im,preview_); mapnik::save_to_file(im,preview_);
} }
@ -69,18 +65,14 @@ class test : public benchmark::test_case
} }
bool operator()() const bool operator()() const
{ {
if (!preview_.empty()) if (!preview_.empty()) {
{
return false; return false;
} }
mapnik::Map m(width_,height_); mapnik::Map m(width_,height_);
mapnik::load_map(m,xml_); mapnik::load_map(m,xml_);
if (extent_.valid()) if (extent_.valid()) {
{
m.zoom_to_box(extent_); m.zoom_to_box(extent_);
} } else {
else
{
m.zoom_all(); m.zoom_all();
} }
for (unsigned i=0;i<iterations_;++i) for (unsigned i=0;i<iterations_;++i)
@ -93,15 +85,15 @@ class test : public benchmark::test_case
} }
}; };
int main(int argc, char** argv) int main(int argc, char** argv)
{ {
mapnik::setup();
int return_value = 0; int return_value = 0;
try try
{ {
mapnik::parameters params; mapnik::parameters params;
benchmark::handle_args(argc,argv,params); benchmark::handle_args(argc,argv,params);
const auto name = params.get<std::string>("name"); boost::optional<std::string> name = params.get<std::string>("name");
if (!name) if (!name)
{ {
std::clog << "please provide a name for this test\n"; std::clog << "please provide a name for this test\n";

View file

@ -12,8 +12,7 @@
#include <mapnik/datasource_cache.hpp> #include <mapnik/datasource_cache.hpp>
#include <stdexcept> #include <stdexcept>
template<typename Renderer> template <typename Renderer> void process_layers(Renderer & ren,
void process_layers(Renderer& ren,
mapnik::request const& m_req, mapnik::request const& m_req,
mapnik::projection const& map_proj, mapnik::projection const& map_proj,
std::vector<mapnik::layer> const& layers, std::vector<mapnik::layer> const& layers,
@ -51,27 +50,26 @@ class test : public benchmark::test_case
double scale_factor_; double scale_factor_;
std::string preview_; std::string preview_;
mutable mapnik::image_rgba8 im_; mutable mapnik::image_rgba8 im_;
public: public:
test(mapnik::parameters const& params) test(mapnik::parameters const& params)
: test_case(params) : test_case(params),
, xml_() xml_(),
, extent_() extent_(),
, width_(*params.get<mapnik::value_integer>("width", 256)) width_(*params.get<mapnik::value_integer>("width",256)),
, height_(*params.get<mapnik::value_integer>("height", 256)) height_(*params.get<mapnik::value_integer>("height",256)),
, m_(new mapnik::Map(width_, height_)) m_(new mapnik::Map(width_,height_)),
, scale_factor_(*params.get<mapnik::value_double>("scale_factor", 2.0)) scale_factor_(*params.get<mapnik::value_double>("scale_factor",2.0)),
, preview_(*params.get<std::string>("preview", "")) preview_(*params.get<std::string>("preview","")),
, im_(m_->width(), m_->height()) im_(m_->width(),m_->height())
{ {
const auto map = params.get<std::string>("map"); boost::optional<std::string> map = params.get<std::string>("map");
if (!map) if (!map)
{ {
throw std::runtime_error("please provide a --map=<path to xml> arg"); throw std::runtime_error("please provide a --map=<path to xml> arg");
} }
xml_ = *map; xml_ = *map;
auto ext = params.get<std::string>("extent"); boost::optional<std::string> ext = params.get<std::string>("extent");
mapnik::load_map(*m_,xml_,true); mapnik::load_map(*m_,xml_,true);
if (ext && !ext->empty()) if (ext && !ext->empty())
{ {
@ -100,8 +98,7 @@ class test : public benchmark::test_case
std::vector<mapnik::layer> const& layers = m_->layers(); std::vector<mapnik::layer> const& layers = m_->layers();
process_layers(ren,m_req,map_proj,layers,scale_denom); process_layers(ren,m_req,map_proj,layers,scale_denom);
ren.end_map_processing(*m_); ren.end_map_processing(*m_);
if (!preview_.empty()) if (!preview_.empty()) {
{
std::clog << "preview available at " << preview_ << "\n"; std::clog << "preview available at " << preview_ << "\n";
mapnik::save_to_file(im_,preview_); mapnik::save_to_file(im_,preview_);
} }
@ -110,8 +107,7 @@ class test : public benchmark::test_case
bool operator()() const bool operator()() const
{ {
if (!preview_.empty()) if (!preview_.empty()) {
{
return false; return false;
} }
for (unsigned i=0;i<iterations_;++i) for (unsigned i=0;i<iterations_;++i)
@ -137,26 +133,24 @@ class test : public benchmark::test_case
const unsigned int* row_to = dest.get_row(y); const unsigned int* row_to = dest.get_row(y);
for (unsigned int x = 0; x < width_; ++x) for (unsigned int x = 0; x < width_; ++x)
{ {
if (row_from[x] != row_to[x]) if (row_from[x] != row_to[x]) diff = true;
diff = true;
} }
} }
if (diff) if (diff) throw std::runtime_error("images differ");
throw std::runtime_error("images differ");
} }
return true; return true;
} }
}; };
int main(int argc, char** argv) int main(int argc, char** argv)
{ {
mapnik::setup();
int return_value = 0; int return_value = 0;
try try
{ {
mapnik::parameters params; mapnik::parameters params;
benchmark::handle_args(argc,argv,params); benchmark::handle_args(argc,argv,params);
const auto name = params.get<std::string>("name"); boost::optional<std::string> name = params.get<std::string>("name");
if (!name) if (!name)
{ {
std::clog << "please provide a name for this test\n"; std::clog << "please provide a name for this test\n";

View file

@ -0,0 +1,30 @@
#include "bench_framework.hpp"
#include <mapnik/util/conversions.hpp>
class test : public benchmark::test_case
{
std::string value_;
public:
test(mapnik::parameters const& params)
: test_case(params),
value_("true") {}
bool validate() const
{
bool result = false;
mapnik::util::string2bool(value_.data(),value_.data()+value_.size(),result);
if (!result) return result;
mapnik::util::string2bool(value_,result);
return (result == true);
}
bool operator()() const
{
for (std::size_t i=0;i<iterations_;++i) {
bool result = false;
mapnik::util::string2bool(value_,result);
mapnik::util::string2bool(value_.data(),value_.data()+value_.size(),result);
}
return true;
}
};
BENCHMARK(test,"string->bool")

View file

@ -0,0 +1,32 @@
#include "bench_framework.hpp"
#include <mapnik/util/conversions.hpp>
class test : public benchmark::test_case
{
std::string value_;
public:
test(mapnik::parameters const& params)
: test_case(params),
value_("1.23456789") {}
bool validate() const
{
double result = 0;
if (!mapnik::util::string2double(value_.data(),value_.data()+value_.size(),result)) return false;
if (result != 1.23456789) return false;
result = 0;
if (!mapnik::util::string2double(value_,result)) return false;
if (result != 1.23456789) return false;
return true;
}
bool operator()() const
{
for (std::size_t i=0;i<iterations_;++i) {
double result = 0;
mapnik::util::string2double(value_,result);
mapnik::util::string2double(value_.data(),value_.data()+value_.size(),result);
}
return true;
}
};
BENCHMARK(test,"string->double")

32
benchmark/test_to_int.cpp Normal file
View file

@ -0,0 +1,32 @@
#include "bench_framework.hpp"
#include <mapnik/util/conversions.hpp>
class test : public benchmark::test_case
{
std::string value_;
public:
test(mapnik::parameters const& params)
: test_case(params),
value_("123456789") {}
bool validate() const
{
mapnik::value_integer result = 0;
if (!mapnik::util::string2int(value_.data(),value_.data()+value_.size(),result)) return false;
if (result != 123456789) return false;
result = 0;
if (!mapnik::util::string2int(value_,result)) return false;
if (result != 123456789) return false;
return true;
}
bool operator()() const
{
for (std::size_t i=0;i<iterations_;++i) {
mapnik::value_integer result = 0;
mapnik::util::string2int(value_,result);
mapnik::util::string2int(value_.data(),value_.data()+value_.size(),result);
}
return true;
}
};
BENCHMARK(test,"string->int")

View file

@ -4,12 +4,10 @@
class test : public benchmark::test_case class test : public benchmark::test_case
{ {
double value_; double value_;
public: public:
test(mapnik::parameters const& params) test(mapnik::parameters const& params)
: test_case(params) : test_case(params),
, value_(-0.1234) value_(-0.1234) {}
{}
bool validate() const bool validate() const
{ {
std::string s; std::string s;
@ -19,8 +17,7 @@ class test : public benchmark::test_case
bool operator()() const bool operator()() const
{ {
std::string out; std::string out;
for (std::size_t i = 0; i < iterations_; ++i) for (std::size_t i=0;i<iterations_;++i) {
{
out.clear(); out.clear();
mapnik::util::to_string(out,value_); mapnik::util::to_string(out,value_);
} }

View file

@ -4,12 +4,10 @@
class test : public benchmark::test_case class test : public benchmark::test_case
{ {
double value_; double value_;
public: public:
test(mapnik::parameters const& params) test(mapnik::parameters const& params)
: test_case(params) : test_case(params),
, value_(-0.1234) value_(-0.1234) {}
{}
bool validate() const bool validate() const
{ {
std::ostringstream s; std::ostringstream s;
@ -19,8 +17,7 @@ class test : public benchmark::test_case
bool operator()() const bool operator()() const
{ {
std::string out; std::string out;
for (std::size_t i = 0; i < iterations_; ++i) for (std::size_t i=0;i<iterations_;++i) {
{
std::ostringstream s; std::ostringstream s;
s << value_; s << value_;
out = s.str(); out = s.str();

View file

@ -1,40 +1,33 @@
#include "bench_framework.hpp" #include "bench_framework.hpp"
#include <mapnik/unicode.hpp> #include <mapnik/unicode.hpp>
#include <mapnik/util/from_u8string.hpp>
#include <mapnik/value.hpp> #include <mapnik/value.hpp>
#include <boost/locale.hpp> #include <boost/locale.hpp>
#ifndef __linux__ #ifndef __linux__
#include <codecvt> #include <codecvt>
#endif
using mapnik::util::from_u8string;
#ifndef __linux__
class test : public benchmark::test_case class test : public benchmark::test_case
{ {
std::string utf8_; std::string utf8_;
public: public:
test(mapnik::parameters const& params) test(mapnik::parameters const& params)
: test_case(params) : test_case(params),
, utf8_(from_u8string(u8"שלום")) utf8_(u8"שלום") {}
{}
bool validate() const bool validate() const
{ {
std::wstring_convert<std::codecvt_utf8<char32_t>, char32_t> utf32conv; std::wstring_convert<std::codecvt_utf8<char32_t>, char32_t> utf32conv;
std::u32string utf32 = utf32conv.from_bytes(utf8_); std::u32string utf32 = utf32conv.from_bytes(utf8_);
if (utf32.size() != 4) if (utf32.size() != 4) return false;
return false; if (utf32[0] != 0x5e9 &&
if (utf32[0] != 0x5e9 && utf32[1] != 0x5dc && utf32[2] != 0x5d5 && utf32[3] != 0x5dd) utf32[1] != 0x5dc &&
return false; utf32[2] != 0x5d5 &&
utf32[3] != 0x5dd) return false;
return true; return true;
} }
bool operator()() const bool operator()() const
{ {
std::u32string utf32; std::u32string utf32;
std::wstring_convert<std::codecvt_utf8<char32_t>, char32_t> utf32conv; std::wstring_convert<std::codecvt_utf8<char32_t>, char32_t> utf32conv;
for (std::size_t i = 0; i < iterations_; ++i) for (std::size_t i=0;i<iterations_;++i) {
{
utf32 = utf32conv.from_bytes(utf8_); utf32 = utf32conv.from_bytes(utf8_);
} }
return true; return true;
@ -46,26 +39,24 @@ class test : public benchmark::test_case
class test2 : public benchmark::test_case class test2 : public benchmark::test_case
{ {
std::string utf8_; std::string utf8_;
public: public:
test2(mapnik::parameters const& params) test2(mapnik::parameters const& params)
: test_case(params) : test_case(params),
, utf8_(from_u8string(u8"שלום")) utf8_(u8"שלום") {}
{}
bool validate() const bool validate() const
{ {
std::u32string utf32 = boost::locale::conv::utf_to_utf<char32_t>(utf8_); std::u32string utf32 = boost::locale::conv::utf_to_utf<char32_t>(utf8_);
if (utf32.size() != 4) if (utf32.size() != 4) return false;
return false; if (utf32[0] != 0x5e9 &&
if (utf32[0] != 0x5e9 && utf32[1] != 0x5dc && utf32[2] != 0x5d5 && utf32[3] != 0x5dd) utf32[1] != 0x5dc &&
return false; utf32[2] != 0x5d5 &&
utf32[3] != 0x5dd) return false;
return true; return true;
} }
bool operator()() const bool operator()() const
{ {
std::u32string utf32; std::u32string utf32;
for (std::size_t i = 0; i < iterations_; ++i) for (std::size_t i=0;i<iterations_;++i) {
{
utf32 = boost::locale::conv::utf_to_utf<char32_t>(utf8_); utf32 = boost::locale::conv::utf_to_utf<char32_t>(utf8_);
} }
return true; return true;
@ -75,29 +66,27 @@ class test2 : public benchmark::test_case
class test3 : public benchmark::test_case class test3 : public benchmark::test_case
{ {
std::string utf8_; std::string utf8_;
public: public:
test3(mapnik::parameters const& params) test3(mapnik::parameters const& params)
: test_case(params) : test_case(params),
, utf8_(from_u8string(u8"שלום")) utf8_(u8"שלום") {}
{}
bool validate() const bool validate() const
{ {
mapnik::transcoder tr_("utf-8"); mapnik::transcoder tr_("utf-8");
mapnik::value_unicode_string utf32 = tr_.transcode(utf8_.data(),utf8_.size()); mapnik::value_unicode_string utf32 = tr_.transcode(utf8_.data(),utf8_.size());
//std::u32string utf32 = boost::locale::conv::utf_to_utf<char32_t>(utf8_); //std::u32string utf32 = boost::locale::conv::utf_to_utf<char32_t>(utf8_);
if (utf32.length() != 4) if (utf32.length() != 4) return false;
return false; if (utf32[0] != 0x5e9 &&
if (utf32[0] != 0x5e9 && utf32[1] != 0x5dc && utf32[2] != 0x5d5 && utf32[3] != 0x5dd) utf32[1] != 0x5dc &&
return false; utf32[2] != 0x5d5 &&
utf32[3] != 0x5dd) return false;
return true; return true;
} }
bool operator()() const bool operator()() const
{ {
mapnik::transcoder tr_("utf-8"); mapnik::transcoder tr_("utf-8");
mapnik::value_unicode_string utf32; mapnik::value_unicode_string utf32;
for (std::size_t i = 0; i < iterations_; ++i) for (std::size_t i=0;i<iterations_;++i) {
{
utf32 = tr_.transcode(utf8_.data(),utf8_.size()); utf32 = tr_.transcode(utf8_.data(),utf8_.size());
} }
return true; return true;
@ -106,7 +95,6 @@ class test3 : public benchmark::test_case
int main(int argc, char** argv) int main(int argc, char** argv)
{ {
mapnik::setup();
mapnik::parameters params; mapnik::parameters params;
benchmark::handle_args(argc,argv,params); benchmark::handle_args(argc,argv,params);
int return_value = 0; int return_value = 0;

View file

@ -3,8 +3,8 @@ import random
im = mapnik.Image(256,256) im = mapnik.Image(256,256)
for x in range(im.width()): for x in xrange(0,im.width()):
for y in range(im.height()): for y in xrange(0,im.height()):
r = int(random.random() * 255) r = int(random.random() * 255)
g = random.random() * 255 g = random.random() * 255
b = random.random() * 255 b = random.random() * 255

153
bootstrap.sh Executable file
View file

@ -0,0 +1,153 @@
#!/usr/bin/env bash
set -eu
set -o pipefail
: '
todo
- docs for base setup: sudo apt-get -y install zlib1g-dev make git
- shrink icu data
'
MASON_VERSION="v0.14.2"
function setup_mason() {
if [[ ! -d ./.mason ]]; then
git clone https://github.com/mapbox/mason.git ./.mason
(cd ./.mason && git checkout ${MASON_VERSION})
else
echo "Updating to latest mason"
(cd ./.mason && git fetch && git checkout ${MASON_VERSION} && git pull origin ${MASON_VERSION})
fi
export PATH=$(pwd)/.mason:$PATH
export CXX=${CXX:-clang++}
export CC=${CC:-clang}
}
function install() {
MASON_PLATFORM_ID=$(mason env MASON_PLATFORM_ID)
if [[ ! -d ./mason_packages/${MASON_PLATFORM_ID}/${1}/${2} ]]; then
mason install $1 $2
if [[ ${3:-false} != false ]]; then
LA_FILE=$(mason prefix $1 $2)/lib/$3.la
if [[ -f ${LA_FILE} ]]; then
perl -i -p -e 's:\Q$ENV{HOME}/build/mapbox/mason\E:$ENV{PWD}:g' ${LA_FILE}
else
echo "$LA_FILE not found"
fi
fi
fi
# the rm here is to workaround https://github.com/mapbox/mason/issues/230
rm -f ./mason_packages/.link/mason.ini
mason link $1 $2
}
ICU_VERSION="57.1"
function install_mason_deps() {
install ccache 3.3.1
install zlib 1.2.8
install jpeg_turbo 1.5.1 libjpeg
install libpng 1.6.28 libpng
install libtiff 4.0.7 libtiff
install libpq 9.6.2
install sqlite 3.17.0 libsqlite3
install expat 2.2.0 libexpat
install icu ${ICU_VERSION}
install proj 4.9.3 libproj
install pixman 0.34.0 libpixman-1
install cairo 1.14.8 libcairo
install protobuf 3.2.0
# technically protobuf is not a mapnik core dep, but installing
# here by default helps make mapnik-vector-tile builds easier
install webp 0.6.0 libwebp
install libgdal 2.1.3 libgdal
install boost 1.63.0
install boost_libsystem 1.63.0
install boost_libfilesystem 1.63.0
install boost_libprogram_options 1.63.0
install boost_libregex_icu57 1.63.0
# technically boost thread and python are not a core dep, but installing
# here by default helps make python-mapnik builds easier
install boost_libthread 1.63.0
install boost_libpython 1.63.0
install freetype 2.7.1 libfreetype
install harfbuzz 1.4.4-ft libharfbuzz
}
MASON_LINKED_ABS=$(pwd)/mason_packages/.link
MASON_LINKED_REL=./mason_packages/.link
export C_INCLUDE_PATH="${MASON_LINKED_ABS}/include"
export CPLUS_INCLUDE_PATH="${MASON_LINKED_ABS}/include"
export LIBRARY_PATH="${MASON_LINKED_ABS}/lib"
function make_config() {
echo "
CXX = '$CXX'
CC = '$CC'
CUSTOM_CXXFLAGS = '-D_GLIBCXX_USE_CXX11_ABI=0'
RUNTIME_LINK = 'static'
INPUT_PLUGINS = 'all'
PATH = '${MASON_LINKED_REL}/bin'
PKG_CONFIG_PATH = '${MASON_LINKED_REL}/lib/pkgconfig'
PATH_REMOVE = '/usr:/usr/local'
PATH_REPLACE = '$HOME/build/mapbox/mason/mason_packages:./mason_packages'
BOOST_INCLUDES = '${MASON_LINKED_REL}/include'
BOOST_LIBS = '${MASON_LINKED_REL}/lib'
ICU_INCLUDES = '${MASON_LINKED_REL}/include'
ICU_LIBS = '${MASON_LINKED_REL}/lib'
HB_INCLUDES = '${MASON_LINKED_REL}/include'
HB_LIBS = '${MASON_LINKED_REL}/lib'
PNG_INCLUDES = '${MASON_LINKED_REL}/include/libpng16'
PNG_LIBS = '${MASON_LINKED_REL}/lib'
JPEG_INCLUDES = '${MASON_LINKED_REL}/include'
JPEG_LIBS = '${MASON_LINKED_REL}/lib'
TIFF_INCLUDES = '${MASON_LINKED_REL}/include'
TIFF_LIBS = '${MASON_LINKED_REL}/lib'
WEBP_INCLUDES = '${MASON_LINKED_REL}/include'
WEBP_LIBS = '${MASON_LINKED_REL}/lib'
PROJ_INCLUDES = '${MASON_LINKED_REL}/include'
PROJ_LIBS = '${MASON_LINKED_REL}/lib'
PG_INCLUDES = '${MASON_LINKED_REL}/include'
PG_LIBS = '${MASON_LINKED_REL}/lib'
FREETYPE_INCLUDES = '${MASON_LINKED_REL}/include/freetype2'
FREETYPE_LIBS = '${MASON_LINKED_REL}/lib'
SVG_RENDERER = True
CAIRO_INCLUDES = '${MASON_LINKED_REL}/include'
CAIRO_LIBS = '${MASON_LINKED_REL}/lib'
SQLITE_INCLUDES = '${MASON_LINKED_REL}/include'
SQLITE_LIBS = '${MASON_LINKED_REL}/lib'
BENCHMARK = True
CPP_TESTS = True
PGSQL2SQLITE = True
XMLPARSER = 'ptree'
SVG2PNG = True
"
}
# NOTE: the `mapnik-settings.env` is used by test/run (which is run by `make test`)
function setup_runtime_settings() {
echo "export PROJ_LIB=${MASON_LINKED_ABS}/share/proj" > mapnik-settings.env
echo "export ICU_DATA=${MASON_LINKED_ABS}/share/icu/${ICU_VERSION}" >> mapnik-settings.env
echo "export GDAL_DATA=${MASON_LINKED_ABS}/share/gdal" >> mapnik-settings.env
source mapnik-settings.env
}
function main() {
setup_mason
install_mason_deps
make_config > ./config.py
setup_runtime_settings
echo "Ready, now run:"
echo ""
echo " ./configure && make"
}
main
# allow sourcing of script without
# causing the terminal to bail on error
set +eu
set +o pipefail

41
circle.yml Normal file
View file

@ -0,0 +1,41 @@
machine:
xcode:
version: 7.3
environment:
XCODE_SCHEME: "no"
XCODE_WORKSPACE: "no"
JOBS: 8
CCACHE_TEMPDIR: /tmp/.ccache-temp
CCACHE_COMPRESS: 1
LLVM_VERSION: 3.9.1
checkout:
post:
- git submodule update --init
dependencies:
cache_directories:
- "~/.ccache"
- "~/.apt-cache"
pre:
# https://discuss.circleci.com/t/add-ability-to-cache-apt-get-programs/598/3
- sudo rm -rf /var/cache/apt/archives && sudo ln -s ~/.apt-cache /var/cache/apt/archives && mkdir -p ~/.apt-cache/partial
- sudo add-apt-repository -y ppa:ubuntu-toolchain-r/test
override:
- sudo apt-get update -y
- sudo apt-get install -y libstdc++-5-dev xutils-dev
database:
pre:
- ./bootstrap.sh
- ./.mason/mason install clang++ ${LLVM_VERSION}
- ./.mason/mason link clang++ ${LLVM_VERSION}
- ./configure CC="$(pwd)/mason_packages/.link/bin/clang" CXX="$(pwd)/mason_packages/.link/bin/ccache $(pwd)/mason_packages/.link/bin/clang++ -Qunused-arguments"
- make
override:
- psql -c 'create database template_postgis;'
- psql -c 'create extension postgis;' -d template_postgis
test:
override:
- make test

View file

@ -1,23 +0,0 @@
include(CheckCXXSourceRuns)
function(check_boost_regex)
set(CMAKE_REQUIRED_LIBRARIES ICU::uc ICU::data ICU::i18n Boost::headers Boost::regex)
check_cxx_source_runs([[
#include <boost/regex/icu.hpp>
#include <unicode/unistr.h>
int main()
{
U_NAMESPACE_QUALIFIER UnicodeString ustr;
try {
boost::u32regex pattern = boost::make_u32regex(ustr);
}
// an exception is fine, still indicates support is
// likely compiled into regex
catch (...) {
return 0;
}
return 0;
}
]] BOOST_REGEX_HAS_ICU)
set(BOOST_REGEX_HAS_ICU ${BOOST_REGEX_HAS_ICU} PARENT_SCOPE)
endfunction(check_boost_regex)

View file

@ -1,14 +0,0 @@
macro(get_mapnik_version)
file(READ ${CMAKE_CURRENT_SOURCE_DIR}/include/mapnik/version.hpp VERSION_FILE)
string(REGEX MATCH "MAPNIK_MAJOR_VERSION ([0-9]*)" _ ${VERSION_FILE})
set(MAPNIK_MAJOR_VERSION ${CMAKE_MATCH_1})
string(REGEX MATCH "MAPNIK_MINOR_VERSION ([0-9]*)" _ ${VERSION_FILE})
set(MAPNIK_MINOR_VERSION ${CMAKE_MATCH_1})
string(REGEX MATCH "MAPNIK_PATCH_VERSION ([0-9]*)" _ ${VERSION_FILE})
set(MAPNIK_PATCH_VERSION ${CMAKE_MATCH_1})
set(MAPNIK_VERSION ${MAPNIK_MAJOR_VERSION}.${MAPNIK_MINOR_VERSION}.${MAPNIK_PATCH_VERSION})
endmacro()

View file

@ -1,68 +0,0 @@
include(CMakePackageConfigHelpers)
### exports mapnik cmake config files (mapnikConfigVersion and mapnikConfig)
function(mapnik_export_cmake_config)
# export mapnik configuration
write_basic_package_version_file(
"${CMAKE_CURRENT_BINARY_DIR}/mapnikConfigVersion.cmake"
VERSION ${MAPNIK_VERSION}
COMPATIBILITY ExactVersion
)
get_property(MAPNIK_UTILITIES GLOBAL PROPERTY MAPNIK_UTILITIES)
# generate all find_dependency and pkg_config calls
set(mapnik_find_deps)
foreach(dep IN LISTS mapnik_deps)
set(ver_comment "# ${dep} used with version ${mapnik_${dep}_version}")
set(mapnik_find_deps "${mapnik_find_deps}\n${ver_comment}\n")
if(mapnik_${dep}_find_args)
list(REMOVE_DUPLICATES mapnik_${dep}_find_args)
list(JOIN mapnik_${dep}_find_args " " m_args_joined)
set(mapnik_find_deps "${mapnik_find_deps}find_dependency(${dep} ${m_args_joined})")
else()
list(JOIN mapnik_${dep}_pkg_args " " m_args_joined)
set(mapnik_find_deps "${mapnik_find_deps}pkg_check_modules(${dep} ${m_args_joined})")
endif()
endforeach()
configure_package_config_file("${CMAKE_CURRENT_SOURCE_DIR}/cmake/mapnikConfig.cmake.in"
"${CMAKE_CURRENT_BINARY_DIR}/mapnikConfig.cmake"
INSTALL_DESTINATION ${MAPNIK_CMAKE_DIR}
PATH_VARS MAPNIK_INCLUDE_DIR PLUGINS_INSTALL_DIR FONTS_INSTALL_DIR mapnik_find_deps MAPNIK_UTILITIES
NO_CHECK_REQUIRED_COMPONENTS_MACRO
)
install(
FILES
"${CMAKE_CURRENT_BINARY_DIR}/mapnikConfig.cmake"
"${CMAKE_CURRENT_BINARY_DIR}/mapnikConfigVersion.cmake"
DESTINATION ${MAPNIK_CMAKE_DIR}
)
endfunction()
mapnik_export_cmake_config()
install(EXPORT MapnikTargets
DESTINATION ${MAPNIK_CMAKE_DIR}
FILE mapnikTargets.cmake
NAMESPACE mapnik::
)
### install plugin cmake config files ###
# Create configuration dependend files for the plugin install dirs.
# some package managers are using different paths per configuration.
string(TOLOWER "${CMAKE_BUILD_TYPE}" _build_type)
string(TOUPPER "${CMAKE_BUILD_TYPE}" _build_type_l)
set(m_mapnik_plugin_file_name mapnikPlugins-${_build_type})
file(WRITE "${CMAKE_CURRENT_BINARY_DIR}/${m_mapnik_plugin_file_name}.cmake.in" "set(MAPNIK_PLUGINS_DIR_${_build_type_l} \"@PACKAGE_PLUGINS_INSTALL_DIR@\" CACHE STRING \"\")\n")
include(CMakePackageConfigHelpers)
configure_package_config_file(
"${CMAKE_CURRENT_BINARY_DIR}/${m_mapnik_plugin_file_name}.cmake.in"
"${CMAKE_CURRENT_BINARY_DIR}/${m_mapnik_plugin_file_name}.cmake"
PATH_VARS PLUGINS_INSTALL_DIR
INSTALL_DESTINATION ${MAPNIK_CMAKE_DIR}
)
install(
FILES "${CMAKE_CURRENT_BINARY_DIR}/${m_mapnik_plugin_file_name}.cmake"
DESTINATION ${MAPNIK_CMAKE_DIR}
)

View file

@ -1,92 +0,0 @@
function(create_pkg_config_file _target _lib_name _description)
string(CONFIGURE [[
prefix=@CMAKE_INSTALL_PREFIX@
exec_prefix=${prefix}
includedir=${prefix}/include
libdir=${exec_prefix}/@MAPNIK_LIB_DIR@
Name: @_lib_name@
Description: @_description@
Version: @MAPNIK_VERSION@
Libs: -L"${libdir}" -l$<TARGET_FILE_BASE_NAME:@_target@>$<TARGET_PROPERTY:@_target@,$<CONFIG>_POSTFIX>
Cflags: -I"${includedir}" -I"${includedir}/mapnik" ]]
_contents @ONLY)
file(GENERATE
OUTPUT ${CMAKE_CURRENT_BINARY_DIR}/${_lib_name}-$<CONFIG>.pc
CONTENT "${_contents}"
)
install(
FILES ${CMAKE_CURRENT_BINARY_DIR}/${_lib_name}-$<CONFIG>.pc
DESTINATION ${MAPNIK_PKGCONF_DIR}
RENAME ${_lib_name}.pc
)
endfunction()
function(create_pkg_config_file_mapnik _lib_name _description)
get_target_property(m_compile_defs core INTERFACE_COMPILE_DEFINITIONS)
string(JOIN " -D" m_str_compile_defs ${m_compile_defs})
if(m_str_compile_defs)
set(m_str_compile_defs "-D${m_str_compile_defs}")
endif()
set(m_requires
libmapnikwkt
libmapnikjson
icu-uc
icu-i18n
harfbuzz
freetype2
)
if(USE_LIBXML2)
list(APPEND m_requires libxml-2.0)
endif()
if(USE_PNG)
list(APPEND m_requires libpng)
endif()
if(USE_JPEG)
list(APPEND m_requires libjpeg)
endif()
if(USE_TIFF)
list(APPEND m_requires libtiff-4)
endif()
if(USE_WEBP)
list(APPEND m_requires libwebp)
endif()
if(USE_CAIRO)
list(APPEND m_requires cairo)
endif()
if(USE_PROJ)
list(APPEND m_requires "proj >= ${PROJ_MIN_VERSION}")
endif()
string(JOIN " " m_requires ${m_requires})
string(CONFIGURE [[
prefix=@CMAKE_INSTALL_PREFIX@
exec_prefix=${prefix}
includedir=${prefix}/include
libdir=${exec_prefix}/@MAPNIK_LIB_DIR@
fonts_dir=${prefix}/@FONTS_INSTALL_DIR@
plugins_dir=${prefix}/@PLUGINS_INSTALL_DIR@
Name: @_lib_name@
Description: @_description@
Version: @MAPNIK_VERSION@
Requires: @m_requires@
Libs: -L"${libdir}" -l$<TARGET_FILE_BASE_NAME:mapnik>$<TARGET_PROPERTY:mapnik,$<CONFIG>_POSTFIX>
Cflags: -I"${includedir}" -I"${includedir}/mapnik" -I"${includedir}/mapnik/agg" @m_str_compile_defs@]]
_contents @ONLY)
file(GENERATE
OUTPUT ${CMAKE_CURRENT_BINARY_DIR}/${_lib_name}-$<CONFIG>.pc
CONTENT "${_contents}"
)
install(
FILES ${CMAKE_CURRENT_BINARY_DIR}/${_lib_name}-$<CONFIG>.pc
DESTINATION ${MAPNIK_PKGCONF_DIR}
RENAME ${_lib_name}.pc
)
endfunction()
create_pkg_config_file(wkt libmapnikwkt "wkt library")
create_pkg_config_file(json libmapnikjson "json library")
create_pkg_config_file_mapnik("libmapnik" "mapnik library")

View file

@ -1,64 +0,0 @@
function(mapnik_set_dep_version dep var)
string(TOUPPER ${dep} m_package_name_upc)
set(m_package_name ${dep})
if(${m_package_name}_VERSION_STRING)
set(${var} ${${m_package_name}_VERSION_STRING} PARENT_SCOPE)
elseif(${m_package_name}_VERSION)
set(${var} ${${m_package_name}_VERSION} PARENT_SCOPE)
elseif(${m_package_name_upc}_VERSION_STRING)
set(${var} ${${m_package_name_upc}_VERSION_STRING} PARENT_SCOPE)
elseif(${m_package_name_upc}_VERSION)
set(${var} ${${m_package_name_upc}_VERSION} PARENT_SCOPE)
endif()
endfunction()
function(mapnik_print_package_info dep)
message(STATUS "Using ${dep} version: ${mapnik_${dep}_version}")
endfunction()
macro(mapnik_find_package dep)
find_package(${dep} ${ARGN})
if(${dep}_FOUND)
list(APPEND mapnik_deps ${dep})
if(mapnik_${dep}_find_args)
list(APPEND mapnik_${dep}_find_args ${ARGN})
else()
set(mapnik_${dep}_find_args ${ARGN})
endif()
mapnik_set_dep_version(${dep} mapnik_${dep}_version)
mapnik_print_package_info(${dep})
else()
message(STATUS "not found: ${dep}")
endif()
endmacro()
macro(mapnik_pkg_check_modules dep)
pkg_check_modules(${dep} ${ARGN})
if(${dep}_FOUND)
list(APPEND mapnik_deps ${dep})
set(mapnik_${dep}_pkg_args ${ARGN})
mapnik_set_dep_version(${dep} mapnik_${dep}_version)
mapnik_print_package_info(${dep})
else()
message(STATUS "not found: ${dep}")
endif()
endmacro()
macro(mapnik_find_threads)
find_package(Threads REQUIRED)
if(CMAKE_THREAD_LIBS_INIT)
message(STATUS "Using Threads (system libraries)")
elseif(CMAKE_USE_WIN32_THREADS_INIT)
message(STATUS "Using Threads (win32 threads)")
elseif(CMAKE_USE_PTHREADS_INIT)
message(STATUS "Using Threads (pthread)")
elseif(CMAKE_HP_PTHREADS_INIT)
message(STATUS "Using Threads (HP thread)")
else()
message(STATUS "Using Threads (unknown backend)")
endif()
endmacro()

View file

@ -1,98 +0,0 @@
#
# Install library targets that consuming users need.
#
function(mapnik_install _target)
install(TARGETS ${_target}
EXPORT MapnikTargets
INCLUDES DESTINATION ${MAPNIK_INCLUDE_DIR}
RUNTIME DESTINATION ${MAPNIK_BIN_DIR}
COMPONENT MapnikRuntime
LIBRARY DESTINATION ${MAPNIK_LIB_DIR}
COMPONENT MapnikRuntime
NAMELINK_COMPONENT MapnikDevelopment
ARCHIVE DESTINATION ${MAPNIK_ARCHIVE_DIR}
COMPONENT MapnikDevelopment
)
get_target_property(TARGET_TYPE "${_target}" TYPE)
if (TARGET_TYPE STREQUAL "SHARED_LIBRARY")
set_property(GLOBAL APPEND PROPERTY TARGETS ${_target})
endif()
endfunction()
#
# Install plugins
#
function(mapnik_install_plugin _target)
if(NOT BUILD_SHARED_PLUGINS)
return()
endif()
install(TARGETS ${_target}
RUNTIME DESTINATION ${PLUGINS_INSTALL_DIR}
COMPONENT MapnikPluginRuntime
LIBRARY DESTINATION ${PLUGINS_INSTALL_DIR}
COMPONENT MapnikPluginRuntime
NAMELINK_COMPONENT MapnikPluginDevelopment
ARCHIVE DESTINATION ${PLUGINS_INSTALL_DIR}
COMPONENT MapnikPluginDevelopment
)
set_property(GLOBAL APPEND PROPERTY PLUGINS ${_target})
endfunction()
#
# Install executables. These are available via COMPONENTS in find_package
#
function(mapnik_install_utility _target)
set(_target_name "mapnikUtilityTargets_${_target}")
install(TARGETS ${_target}
EXPORT ${_target_name}
INCLUDES DESTINATION ${MAPNIK_INCLUDE_DIR}
RUNTIME DESTINATION ${MAPNIK_BIN_DIR}
COMPONENT MapnikRuntime
LIBRARY DESTINATION ${MAPNIK_LIB_DIR}
COMPONENT MapnikRuntime
NAMELINK_COMPONENT MapnikDevelopment
ARCHIVE DESTINATION ${MAPNIK_ARCHIVE_DIR}
COMPONENT MapnikDevelopment
)
install(EXPORT ${_target_name}
FILE ${_target_name}.cmake
NAMESPACE mapnik::
DESTINATION ${MAPNIK_CMAKE_DIR}
)
set_property(GLOBAL APPEND PROPERTY MAPNIK_UTILITIES ${_target})
endfunction()
function(mapnik_install_targets)
if(INSTALL_DEPENDENCIES AND WIN32)
# https://cmake.org/cmake/help/latest/policy/CMP0087.html
cmake_policy(SET CMP0087 NEW)
get_property(_installed_utilities GLOBAL PROPERTY MAPNIK_UTILITIES)
get_property(_installed_targets GLOBAL PROPERTY TARGETS)
get_property(_installed_plugins GLOBAL PROPERTY PLUGINS)
set(_internal_executables "")
set(_internal_libraries "")
foreach(_target IN LISTS _installed_utilities)
list(APPEND _internal_executables "\${CMAKE_INSTALL_PREFIX}/${MAPNIK_BIN_DIR}/$<TARGET_FILE_NAME:${_target}>")
endforeach()
foreach(_target IN LISTS _installed_targets)
list(APPEND _internal_libraries "\${CMAKE_INSTALL_PREFIX}/${MAPNIK_BIN_DIR}/$<TARGET_FILE_NAME:${_target}>")
endforeach()
foreach(_target IN LISTS _installed_plugins)
list(APPEND _internal_libraries "\${CMAKE_INSTALL_PREFIX}/${PLUGINS_INSTALL_DIR}/$<TARGET_FILE_NAME:${_target}>")
endforeach()
# all other executables get auto detected and fixed.
if(_internal_executables)
list(GET _internal_executables 0 _internal_executables)
endif()
INSTALL(CODE "
message(STATUS \"internal_executables: ${_internal_executables}\")
message(STATUS \"internal_libraries: ${_internal_libraries}\")
message(STATUS \"ADDITIONAL_LIBARIES_PATHS: ${ADDITIONAL_LIBARIES_PATHS}\")
include(BundleUtilities)
fixup_bundle(\"${_internal_executables}\" \"${_internal_libraries}\" \"${ADDITIONAL_LIBARIES_PATHS}\")
" COMPONENT MapnikRuntime)
endif()
endfunction()

View file

@ -1,3 +0,0 @@
set(BOOST_MIN_VERSION 1.73)
set(HARFBUZZ_MIN_VERSION 0.9.34)
set(PROJ_MIN_VERSION 7.2.0)

View file

@ -1,4 +0,0 @@
macro(mapnik_option option_name option_description option_default_value)
option(${option_name} "${option_description}" ${option_default_value})
add_feature_info(${option_name} ${option_name} "${option_description}")
endmacro()

View file

@ -1,16 +0,0 @@
function(format_dir dir)
file(GLOB_RECURSE sources
"${dir}/*.cpp"
"${dir}/*.hpp"
)
execute_process(COMMAND clang-format -style=file -i ${sources})
endfunction()
format_dir(benchmark)
format_dir(demo)
format_dir(include)
format_dir(plugins)
format_dir(src)
format_dir(test)
format_dir(utils)

View file

@ -1,52 +0,0 @@
@PACKAGE_INIT@
set_and_check(MAPNIK_INCLUDE_DIR "@PACKAGE_MAPNIK_INCLUDE_DIR@" CACHE STRING "")
set_and_check(MAPNIK_FONTS_DIR "@PACKAGE_FONTS_INSTALL_DIR@" CACHE STRING "")
set(CMAKE_MODULE_PATH ${CMAKE_MODULE_PATH} "${CMAKE_CURRENT_LIST_DIR}/Modules/")
include(CMakeFindDependencyMacro)
find_dependency(Threads REQUIRED)
@mapnik_find_deps@
include("${CMAKE_CURRENT_LIST_DIR}/mapnikTargets.cmake")
set(_supported_components @MAPNIK_UTILITIES@)
foreach(_comp ${mapnik_FIND_COMPONENTS})
if (NOT _comp IN_LIST _supported_components)
set(mapnik_FOUND False)
set(mapnik_NOT_FOUND_MESSAGE "Unsupported component: ${_comp}")
endif()
include("${CMAKE_CURRENT_LIST_DIR}/mapnikUtilityTargets_${_comp}.cmake")
endforeach()
get_filename_component(_plugin_dir "${CMAKE_CURRENT_LIST_FILE}" PATH)
file(GLOB CONFIG_FILES "${_plugin_dir}/mapnikPlugins-*.cmake")
foreach(f ${CONFIG_FILES})
include(${f})
endforeach()
function(mapnik_find_plugin_dir PLUGIN_DIR)
string(TOUPPER "${CMAKE_BUILD_TYPE}" _build_type_l)
set(_plugin_dir "${MAPNIK_PLUGINS_DIR_${_build_type_l}}")
# only release has more then one configuration
if(NOT _plugin_dir)
set(_all_rel_cfgs RELEASE RELWITHDEBINFO MINSIZEREL)
list(FIND _all_rel_cfgs ${_build_type_l} _is_rel_cfg)
# check if the current configuration is a known release configuration
if(${_is_rel_cfg} GREATER_EQUAL 0)
foreach(_rel_cfg IN LISTS _all_rel_cfgs)
set(_plugin_dir "${MAPNIK_PLUGINS_DIR_${_rel_cfg}}")
if(_plugin_dir)
break()
endif()
endforeach()
endif()
endif()
if(NOT _plugin_dir)
message(WARNING "Could not find a plugin install dir for configuration ${_build_type_l}")
endif()
set(${PLUGIN_DIR} ${_plugin_dir} PARENT_SCOPE)
endfunction()

View file

@ -1,18 +0,0 @@
include(InstallRequiredSystemLibraries)
set(CPACK_PACKAGE_NAME "mapnik")
set(CPACK_PACKAGE_CONTACT "ubuntu-mathis@outlook.com")
set(CPACK_PACKAGE_HOMEPAGE_URL "https://mapnik.org")
set(CPACK_RESOURCE_FILE_LICENSE "${PROJECT_SOURCE_DIR}/COPYING")
set(CPACK_SOURCE_GENERATOR "TGZ")
set(CPACK_GENERATOR "DEB;TGZ")
set(CPACK_SOURCE_IGNORE_FILES
\\.git/
build/
".*~$"
out/
\\.vs/
\\.vscode/
)
set(CPACK_VERBATIM_VARIABLES YES)
include(CPack)

31
configure vendored
View file

@ -1,32 +1,5 @@
#! /usr/bin/env bash #!/bin/sh
set -eu PYTHON=${PYTHON:-python}
: ${PYTHON:=python}
# Only some shells (Bash and Z shell) support arrays. Therefore,
# the following code provides an alternative for users calling the script
# with shells other than Bash or Z shell (e.g. Debian users using Dash).
THE_SHELL=$(basename $SHELL)
if [ "$THE_SHELL" != "bash" ] && [ "$THE_SHELL" != "zsh" ]; then
if [ -f mapnik-settings.env ]; then
echo "WARNING: Reading from mapnik-settings.env is supported with Bash or Z shell only."
fi
$PYTHON scons/scons.py --implicit-deps-changed configure "$@" $PYTHON scons/scons.py --implicit-deps-changed configure "$@"
exit 0
fi
# mapnik-settings.env is an optional file to store
# environment variables that should be used before
# running tests like PROJ_LIB, GDAL_DATA, and ICU_DATA
# These do not normally need to be set except when
# building against binary versions of dependencies like
# done via bootstrap.sh
if [ -f mapnik-settings.env ]; then
echo "Inheriting from mapnik-settings.env"
. ./mapnik-settings.env
VARS=( $(cat mapnik-settings.env) )
fi
$PYTHON scons/scons.py --implicit-deps-changed configure ${VARS[*]:-} "$@"

View file

@ -1,7 +0,0 @@
if(BUILD_DEMO_VIEWER)
add_subdirectory(viewer)
endif()
if(BUILD_DEMO_CPP)
add_subdirectory(c++)
endif()

View file

@ -1,6 +0,0 @@
add_executable(mapnik-demo rundemo.cpp)
target_link_libraries(mapnik-demo PRIVATE
mapnik::agg
mapnik::mapnik
ICU::data ICU::i18n ICU::uc # needed for the static build (TODO: why isn't this correctly propagated from mapnik::mapnik?)
)

View file

@ -41,7 +41,7 @@ if env['HAS_CAIRO']:
demo_env.Append(CPPDEFINES = '-DHAVE_CAIRO') demo_env.Append(CPPDEFINES = '-DHAVE_CAIRO')
libraries = [env['MAPNIK_NAME']] libraries = [env['MAPNIK_NAME']]
libraries.extend([copy(env['LIBMAPNIK_LIBS']), 'sqlite3', 'pthread']) libraries.extend(copy(env['LIBMAPNIK_LIBS']))
rundemo = demo_env.Program('rundemo', source, LIBS=libraries) rundemo = demo_env.Program('rundemo', source, LIBS=libraries)
Depends(rundemo, env.subst('../../src/%s' % env['MAPNIK_LIB_NAME'])) Depends(rundemo, env.subst('../../src/%s' % env['MAPNIK_LIB_NAME']))

View file

@ -2,7 +2,7 @@
* *
* This file is part of Mapnik (c++ mapping toolkit) * This file is part of Mapnik (c++ mapping toolkit)
* *
* Copyright (C) 2024 Artem Pavlenko * Copyright (C) 2017 Artem Pavlenko
* *
* This library is free software; you can redistribute it and/or * This library is free software; you can redistribute it and/or
* modify it under the terms of the GNU Lesser General Public * modify it under the terms of the GNU Lesser General Public
@ -20,7 +20,6 @@
* *
*****************************************************************************/ *****************************************************************************/
#include <mapnik/mapnik.hpp>
#include <mapnik/map.hpp> #include <mapnik/map.hpp>
#include <mapnik/layer.hpp> #include <mapnik/layer.hpp>
#include <mapnik/rule.hpp> #include <mapnik/rule.hpp>
@ -46,16 +45,14 @@
#include <iostream> #include <iostream>
int main ( int, char** ) int main ( int, char** )
{ {
using namespace mapnik; using namespace mapnik;
const std::string srs_lcc = const std::string srs_lcc="+proj=lcc +ellps=GRS80 +lat_0=49 +lon_0=-95 +lat+1=49 +lat_2=77 +datum=NAD83 +units=m +no_defs";
"+proj=lcc +ellps=GRS80 +lat_0=49 +lon_0=-95 +lat+1=49 +lat_2=77 +datum=NAD83 +units=m +no_defs"; const std::string srs_merc="+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";
const std::string srs_merc = "+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"; try {
mapnik::setup();
try
{
std::cout << " running demo ... \n"; std::cout << " running demo ... \n";
datasource_cache::instance().register_datasources("plugins/input/"); datasource_cache::instance().register_datasources("plugins/input/");
freetype_engine::register_font("fonts/dejavu-fonts-ttf-2.37/ttf/DejaVuSans.ttf"); freetype_engine::register_font("fonts/dejavu-fonts-ttf-2.37/ttf/DejaVuSans.ttf");
@ -132,8 +129,8 @@ int main(int, char**)
line_symbolizer line_sym; line_symbolizer line_sym;
put(line_sym,keys::stroke,color(171,158,137)); put(line_sym,keys::stroke,color(171,158,137));
put(line_sym,keys::stroke_width,2.0); put(line_sym,keys::stroke_width,2.0);
put(line_sym, keys::stroke_linecap, line_cap_enum::ROUND_CAP); put(line_sym,keys::stroke_linecap,ROUND_CAP);
put(line_sym, keys::stroke_linejoin, line_join_enum::ROUND_JOIN); put(line_sym,keys::stroke_linejoin,ROUND_JOIN);
r.append(std::move(line_sym)); r.append(std::move(line_sym));
} }
roads34_style.add_rule(std::move(r)); roads34_style.add_rule(std::move(r));
@ -149,8 +146,8 @@ int main(int, char**)
line_symbolizer line_sym; line_symbolizer line_sym;
put(line_sym,keys::stroke,color(171,158,137)); put(line_sym,keys::stroke,color(171,158,137));
put(line_sym,keys::stroke_width,4.0); put(line_sym,keys::stroke_width,4.0);
put(line_sym, keys::stroke_linecap, line_cap_enum::ROUND_CAP); put(line_sym,keys::stroke_linecap,ROUND_CAP);
put(line_sym, keys::stroke_linejoin, line_join_enum::ROUND_JOIN); put(line_sym,keys::stroke_linejoin,ROUND_JOIN);
r.append(std::move(line_sym)); r.append(std::move(line_sym));
} }
roads2_style_1.add_rule(std::move(r)); roads2_style_1.add_rule(std::move(r));
@ -165,8 +162,8 @@ int main(int, char**)
line_symbolizer line_sym; line_symbolizer line_sym;
put(line_sym,keys::stroke,color(255,250,115)); put(line_sym,keys::stroke,color(255,250,115));
put(line_sym,keys::stroke_width,2.0); put(line_sym,keys::stroke_width,2.0);
put(line_sym, keys::stroke_linecap, line_cap_enum::ROUND_CAP); put(line_sym,keys::stroke_linecap,ROUND_CAP);
put(line_sym, keys::stroke_linejoin, line_join_enum::ROUND_JOIN); put(line_sym,keys::stroke_linejoin,ROUND_JOIN);
r.append(std::move(line_sym)); r.append(std::move(line_sym));
} }
roads2_style_2.add_rule(std::move(r)); roads2_style_2.add_rule(std::move(r));
@ -182,8 +179,8 @@ int main(int, char**)
line_symbolizer line_sym; line_symbolizer line_sym;
put(line_sym,keys::stroke,color(188,149,28)); put(line_sym,keys::stroke,color(188,149,28));
put(line_sym,keys::stroke_width,7.0); put(line_sym,keys::stroke_width,7.0);
put(line_sym, keys::stroke_linecap, line_cap_enum::ROUND_CAP); put(line_sym,keys::stroke_linecap,ROUND_CAP);
put(line_sym, keys::stroke_linejoin, line_join_enum::ROUND_JOIN); put(line_sym,keys::stroke_linejoin,ROUND_JOIN);
r.append(std::move(line_sym)); r.append(std::move(line_sym));
} }
roads1_style_1.add_rule(std::move(r)); roads1_style_1.add_rule(std::move(r));
@ -198,8 +195,8 @@ int main(int, char**)
line_symbolizer line_sym; line_symbolizer line_sym;
put(line_sym,keys::stroke,color(242,191,36)); put(line_sym,keys::stroke,color(242,191,36));
put(line_sym,keys::stroke_width,5.0); put(line_sym,keys::stroke_width,5.0);
put(line_sym, keys::stroke_linecap, line_cap_enum::ROUND_CAP); put(line_sym,keys::stroke_linecap,ROUND_CAP);
put(line_sym, keys::stroke_linejoin, line_join_enum::ROUND_JOIN); put(line_sym,keys::stroke_linejoin,ROUND_JOIN);
r.append(std::move(line_sym)); r.append(std::move(line_sym));
} }
roads1_style_2.add_rule(std::move(r)); roads1_style_2.add_rule(std::move(r));
@ -218,8 +215,7 @@ int main(int, char**)
placement_finder->defaults.format_defaults.fill = color(0,0,0); placement_finder->defaults.format_defaults.fill = color(0,0,0);
placement_finder->defaults.format_defaults.halo_fill = color(255,255,200); placement_finder->defaults.format_defaults.halo_fill = color(255,255,200);
placement_finder->defaults.format_defaults.halo_radius = 1.0; placement_finder->defaults.format_defaults.halo_radius = 1.0;
placement_finder->defaults.set_format_tree( placement_finder->defaults.set_format_tree(std::make_shared<mapnik::formatting::text_node>(parse_expression("[GEONAME]")));
std::make_shared<mapnik::formatting::text_node>(parse_expression("[GEONAME]")));
put<text_placements_ptr>(text_sym, keys::text_placements_, placement_finder); put<text_placements_ptr>(text_sym, keys::text_placements_, placement_finder);
r.append(std::move(text_sym)); r.append(std::move(text_sym));
} }
@ -346,7 +342,8 @@ int main(int, char**)
but instead let's build up a surface for more flexibility but instead let's build up a surface for more flexibility
*/ */
cairo_surface_ptr image_surface(cairo_image_surface_create(CAIRO_FORMAT_ARGB32, m.width(), m.height()), cairo_surface_ptr image_surface(
cairo_image_surface_create(CAIRO_FORMAT_ARGB32,m.width(),m.height()),
cairo_surface_closer()); cairo_surface_closer());
double scale_factor = 1.0; double scale_factor = 1.0;
cairo_ptr image_context(create_context(image_surface)); cairo_ptr image_context(create_context(image_surface));
@ -356,8 +353,7 @@ int main(int, char**)
cairo_surface_write_to_png(&*image_surface, "cairo-demo.png"); cairo_surface_write_to_png(&*image_surface, "cairo-demo.png");
// but we can also benefit from quantization by converting // but we can also benefit from quantization by converting
// to a mapnik image object and then saving that // to a mapnik image object and then saving that
mapnik::image_rgba8 im_data(cairo_image_surface_get_width(&*image_surface), mapnik::image_rgba8 im_data(cairo_image_surface_get_width(&*image_surface), cairo_image_surface_get_height(&*image_surface));
cairo_image_surface_get_height(&*image_surface));
cairo_image_to_rgba8(im_data, image_surface); cairo_image_to_rgba8(im_data, image_surface);
save_to_file(im_data, "cairo-demo256.png","png8"); save_to_file(im_data, "cairo-demo256.png","png8");
cairo_surface_finish(&*image_surface); cairo_surface_finish(&*image_surface);

View file

@ -1,64 +0,0 @@
find_package(QT NAMES Qt6 Qt5 COMPONENTS Widgets REQUIRED)
find_package(Qt${QT_VERSION_MAJOR} COMPONENTS Widgets REQUIRED)
set(PROJECT_SOURCES
about_dialog.cpp
info_dialog.cpp
layerdelegate.cpp
layerlistmodel.cpp
layerwidget.cpp
layer_info_dialog.cpp
main.cpp
mainwindow.cpp
mapwidget.cpp
styles_model.cpp
forms/about.ui
forms/info.ui
forms/layer_info.ui
mapnik_viewer.qrc
)
if(${QT_VERSION_MAJOR} GREATER_EQUAL 6)
qt_add_executable(mapnik-viewer
MANUAL_FINALIZATION
${PROJECT_SOURCES}
)
else()
if(ANDROID)
add_library(mapnik-viewer SHARED
${PROJECT_SOURCES}
)
else()
add_executable(mapnik-viewer
${PROJECT_SOURCES}
)
endif()
endif()
set_target_properties(mapnik-viewer PROPERTIES
AUTOUIC_SEARCH_PATHS forms
AUTORCC ON
AUTOUIC ON
AUTOMOC ON
)
target_link_libraries(mapnik-viewer PRIVATE
Qt${QT_VERSION_MAJOR}::Widgets
mapnik::agg
mapnik::mapnik
ICU::data ICU::i18n ICU::uc # needed for the static build (TODO: why isn't this correctly propagated from mapnik::mapnik?)
)
file(WRITE ${CMAKE_CURRENT_BINARY_DIR}/viewer.ini
"[mapnik]
plugins_dir=${PLUGINS_INSTALL_DIR}
fonts/1/dir=${FONTS_INSTALL_DIR}
fonts/size=1"
)
if(QT_VERSION_MAJOR EQUAL 6)
qt_finalize_executable(mapnik-viewer)
endif()
install(FILES ${CMAKE_CURRENT_BINARY_DIR}/viewer.ini DESTINATION bin)
mapnik_install_utility(mapnik-viewer)

View file

@ -1,6 +1,6 @@
/* This file is part of Mapnik (c++ mapping toolkit) /* This file is part of Mapnik (c++ mapping toolkit)
* *
* Copyright (C) 2024 Artem Pavlenko * Copyright (C) 2017 Artem Pavlenko
* *
* Mapnik is free software; you can redistribute it and/or * Mapnik is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License * modify it under the terms of the GNU General Public License
@ -17,8 +17,10 @@
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
*/ */
#include "about_dialog.hpp" #include "about_dialog.hpp"
about_dialog::about_dialog(QWidget *parent) about_dialog::about_dialog(QWidget *parent)
: QDialog(parent) : QDialog(parent)
{ {

View file

@ -1,6 +1,6 @@
/* This file is part of Mapnik (c++ mapping toolkit) /* This file is part of Mapnik (c++ mapping toolkit)
* *
* Copyright (C) 2024 Artem Pavlenko * Copyright (C) 2017 Artem Pavlenko
* *
* Mapnik is free software; you can redistribute it and/or * Mapnik is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License * modify it under the terms of the GNU General Public License
@ -17,6 +17,8 @@
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
*/ */
#if !defined ABOUT_DIALOG_HPP #if !defined ABOUT_DIALOG_HPP
#define ABOUT_DIALOG_HPP #define ABOUT_DIALOG_HPP
@ -28,9 +30,9 @@ class about_dialog : public QDialog
Q_OBJECT Q_OBJECT
public: public:
about_dialog(QWidget * parent = 0); about_dialog(QWidget * parent = 0);
private: private:
Ui::Dialog ui; Ui::Dialog ui;
}; };
#endif //ABOUT_DIALOG_HPP #endif //ABOUT_DIALOG_HPP

View file

@ -43,5 +43,5 @@ ini = ini_template % locals()
open('viewer.ini','w').write(ini) open('viewer.ini','w').write(ini)
try: try:
os.chmod('viewer.ini',0o666) os.chmod('viewer.ini',0666)
except: pass except: pass

View file

@ -1,6 +1,6 @@
/* This file is part of Mapnik (c++ mapping toolkit) /* This file is part of Mapnik (c++ mapping toolkit)
* *
* Copyright (C) 2024 Artem Pavlenko * Copyright (C) 2017 Artem Pavlenko
* *
* Mapnik is free software; you can redistribute it and/or * Mapnik is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License * modify it under the terms of the GNU General Public License
@ -17,8 +17,10 @@
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
*/ */
#include "info_dialog.hpp" #include "info_dialog.hpp"
info_dialog::info_dialog(QVector<QPair<QString,QString> > const& info, QWidget *parent) info_dialog::info_dialog(QVector<QPair<QString,QString> > const& info, QWidget *parent)
: QDialog(parent) : QDialog(parent)
{ {

View file

@ -1,6 +1,6 @@
/* This file is part of Mapnik (c++ mapping toolkit) /* This file is part of Mapnik (c++ mapping toolkit)
* *
* Copyright (C) 2024 Artem Pavlenko * Copyright (C) 2017 Artem Pavlenko
* *
* Mapnik is free software; you can redistribute it and/or * Mapnik is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License * modify it under the terms of the GNU General Public License
@ -17,6 +17,8 @@
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
*/ */
#ifndef INFO_DIALOG_HPP #ifndef INFO_DIALOG_HPP
#define INFO_DIALOG_HPP #define INFO_DIALOG_HPP
@ -28,9 +30,9 @@ class info_dialog : public QDialog
Q_OBJECT Q_OBJECT
public: public:
info_dialog(QVector<QPair<QString,QString> > const& info,QWidget * parent = 0); info_dialog(QVector<QPair<QString,QString> > const& info,QWidget * parent = 0);
private: private:
Ui::InfoDialog ui; Ui::InfoDialog ui;
}; };
#endif //INFO_DIALOG_HPP #endif //INFO_DIALOG_HPP

View file

@ -1,6 +1,6 @@
/* This file is part of Mapnik (c++ mapping toolkit) /* This file is part of Mapnik (c++ mapping toolkit)
* *
* Copyright (C) 2024 Artem Pavlenko * Copyright (C) 2017 Artem Pavlenko
* *
* Mapnik is free software; you can redistribute it and/or * Mapnik is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License * modify it under the terms of the GNU General Public License
@ -17,6 +17,7 @@
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
*/ */
#include "layer_info_dialog.hpp" #include "layer_info_dialog.hpp"
// mapnik // mapnik
@ -25,6 +26,7 @@
#include <mapnik/params_impl.hpp> #include <mapnik/params_impl.hpp>
#include <mapnik/layer.hpp> #include <mapnik/layer.hpp>
layer_info_dialog::layer_info_dialog(mapnik::layer& lay, QWidget *parent) layer_info_dialog::layer_info_dialog(mapnik::layer& lay, QWidget *parent)
: QDialog(parent) : QDialog(parent)
{ {
@ -51,7 +53,7 @@ layer_info_dialog::layer_info_dialog(mapnik::layer& lay, QWidget* parent)
int index=0; int index=0;
for (pos = ps.begin();pos != ps.end();++pos) for (pos = ps.begin();pos != ps.end();++pos)
{ {
std::optional<std::string> result; boost::optional<std::string> result;
mapnik::util::apply_visitor(mapnik::value_extractor_visitor<std::string>(result),pos->second); mapnik::util::apply_visitor(mapnik::value_extractor_visitor<std::string>(result),pos->second);
if (result) if (result)
{ {

View file

@ -1,6 +1,6 @@
/* This file is part of Mapnik (c++ mapping toolkit) /* This file is part of Mapnik (c++ mapping toolkit)
* *
* Copyright (C) 2024 Artem Pavlenko * Copyright (C) 2017 Artem Pavlenko
* *
* Mapnik is free software; you can redistribute it and/or * Mapnik is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License * modify it under the terms of the GNU General Public License
@ -17,13 +17,16 @@
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
*/ */
#ifndef LAYER_INFO_DIALOG_HPP #ifndef LAYER_INFO_DIALOG_HPP
#define LAYER_INFO_DIALOG_HPP #define LAYER_INFO_DIALOG_HPP
#include "ui_layer_info.h" #include "ui_layer_info.h"
#include <QDialog> #include <QDialog>
namespace mapnik { namespace mapnik
{
class layer; class layer;
} }
@ -33,9 +36,9 @@ class layer_info_dialog : public QDialog
public: public:
layer_info_dialog(mapnik::layer& l, QWidget * parent = 0); layer_info_dialog(mapnik::layer& l, QWidget * parent = 0);
Ui::LayerInfoDialog& getUI(); Ui::LayerInfoDialog& getUI();
private: private:
Ui::LayerInfoDialog ui; Ui::LayerInfoDialog ui;
}; };
#endif //LAYER_INFO_DIALOG_HPP #endif //LAYER_INFO_DIALOG_HPP

View file

@ -1,6 +1,6 @@
/* This file is part of Mapnik (c++ mapping toolkit) /* This file is part of Mapnik (c++ mapping toolkit)
* *
* Copyright (C) 2024 Artem Pavlenko * Copyright (C) 2017 Artem Pavlenko
* *
* Mapnik is free software; you can redistribute it and/or * Mapnik is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License * modify it under the terms of the GNU General Public License
@ -17,14 +17,17 @@
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
*/ */
#include <QtGui> #include <QtGui>
#include "layerdelegate.hpp" #include "layerdelegate.hpp"
LayerDelegate::LayerDelegate(QObject *parent) LayerDelegate::LayerDelegate(QObject *parent)
: QAbstractItemDelegate(parent) : QAbstractItemDelegate(parent)
{} {
}
void LayerDelegate::paint(QPainter* painter, const QStyleOptionViewItem& option, const QModelIndex& index) const void LayerDelegate::paint(QPainter *painter, const QStyleOptionViewItem &option,
const QModelIndex &index) const
{ {
painter->setRenderHint(QPainter::Antialiasing); painter->setRenderHint(QPainter::Antialiasing);
painter->setPen(QPen(QColor(255,0,0),1)); painter->setPen(QPen(QColor(255,0,0),1));
@ -34,15 +37,18 @@ void LayerDelegate::paint(QPainter* painter, const QStyleOptionViewItem& option,
else else
painter->setBrush(QBrush(QColor(255, 0, 0, 64))); painter->setBrush(QBrush(QColor(255, 0, 0, 64)));
painter->drawRoundedRect(option.rect, 4, 4);
painter->drawRoundRect(option.rect,4,4);
if (option.state & QStyle::State_Selected) if (option.state & QStyle::State_Selected)
painter->setBrush(option.palette.highlightedText()); painter->setBrush(option.palette.highlightedText());
else else
painter->setBrush(QBrush(QColor(255, 120, 0, 127))); painter->setBrush(QBrush(QColor(255, 120, 0, 127)));
} }
QSize LayerDelegate::sizeHint(const QStyleOptionViewItem& /* option */, const QModelIndex& /* index */) const QSize LayerDelegate::sizeHint(const QStyleOptionViewItem & /* option */,
const QModelIndex & /* index */) const
{ {
return QSize(120,24); return QSize(120,24);
} }

View file

@ -1,6 +1,6 @@
/* This file is part of Mapnik (c++ mapping toolkit) /* This file is part of Mapnik (c++ mapping toolkit)
* *
* Copyright (C) 2024 Artem Pavlenko * Copyright (C) 2017 Artem Pavlenko
* *
* Mapnik is free software; you can redistribute it and/or * Mapnik is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License * modify it under the terms of the GNU General Public License
@ -35,8 +35,10 @@ class LayerDelegate : public QAbstractItemDelegate
public: public:
LayerDelegate(QObject *parent = 0); LayerDelegate(QObject *parent = 0);
void paint(QPainter* painter, const QStyleOptionViewItem& option, const QModelIndex& index) const; void paint(QPainter *painter, const QStyleOptionViewItem &option,
QSize sizeHint(const QStyleOptionViewItem& option, const QModelIndex& index) const; const QModelIndex &index) const;
QSize sizeHint(const QStyleOptionViewItem &option,
const QModelIndex &index ) const;
}; };
#endif //LAYER_DELEGATE_HPP #endif //LAYER_DELEGATE_HPP

View file

@ -1,6 +1,6 @@
/* This file is part of Mapnik (c++ mapping toolkit) /* This file is part of Mapnik (c++ mapping toolkit)
* *
* Copyright (C) 2024 Artem Pavlenko * Copyright (C) 2017 Artem Pavlenko
* *
* Mapnik is free software; you can redistribute it and/or * Mapnik is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License * modify it under the terms of the GNU General Public License
@ -17,22 +17,23 @@
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
*/ */
#include "layerlistmodel.hpp" #include "layerlistmodel.hpp"
#include <QIcon> #include <QIcon>
#include <QBrush>
#include <iostream>
#include <mapnik/layer.hpp> #include <mapnik/layer.hpp>
using mapnik::Map; using mapnik::Map;
LayerListModel::LayerListModel(std::shared_ptr<Map> map,QObject *parent) LayerListModel::LayerListModel(std::shared_ptr<Map> map,QObject *parent)
: QAbstractListModel(parent) : QAbstractListModel(parent),
, map_(map) map_(map) {}
{}
int LayerListModel::rowCount(QModelIndex const&) const int LayerListModel::rowCount(QModelIndex const&) const
{ {
if (map_) if (map_) return map_->layers().size();
return map_->layers().size();
return 0; return 0;
} }
@ -63,20 +64,14 @@ QVariant LayerListModel::data(QModelIndex const& index, int role) const
else else
return QVariant(Qt::Unchecked); return QVariant(Qt::Unchecked);
} }
else if (role == Qt::ForegroundRole)
{
if (map_->layers().at(index.row()).active())
return QBrush(QColor("black"));
else
return QBrush(QColor("lightgrey"));
}
else else
{ {
return QVariant(); return QVariant();
} }
} }
QVariant LayerListModel::headerData(int section, Qt::Orientation orientation, int role) const QVariant LayerListModel::headerData(int section, Qt::Orientation orientation,
int role) const
{ {
if (role != Qt::DisplayRole) if (role != Qt::DisplayRole)
return QVariant(); return QVariant();
@ -87,10 +82,10 @@ QVariant LayerListModel::headerData(int section, Qt::Orientation orientation, in
return QString("TODO Row %1").arg(section); return QString("TODO Row %1").arg(section);
} }
bool LayerListModel::setData(const QModelIndex& index, const QVariant& value, int role) bool LayerListModel::setData(const QModelIndex &index,
const QVariant &value, int role)
{ {
if (!map_) if (!map_) return false;
return false;
if (index.isValid() && role == Qt::CheckStateRole) if (index.isValid() && role == Qt::CheckStateRole)
{ {
@ -106,6 +101,7 @@ bool LayerListModel::setData(const QModelIndex& index, const QVariant& value, in
Qt::ItemFlags LayerListModel::flags(QModelIndex const& index) const Qt::ItemFlags LayerListModel::flags(QModelIndex const& index) const
{ {
Qt::ItemFlags flags = QAbstractItemModel::flags(index); Qt::ItemFlags flags = QAbstractItemModel::flags(index);
if (index.isValid()) if (index.isValid())
flags |= Qt::ItemIsUserCheckable; flags |= Qt::ItemIsUserCheckable;
return flags; return flags;

View file

@ -1,6 +1,6 @@
/* This file is part of Mapnik (c++ mapping toolkit) /* This file is part of Mapnik (c++ mapping toolkit)
* *
* Copyright (C) 2024 Artem Pavlenko * Copyright (C) 2017 Artem Pavlenko
* *
* Mapnik is free software; you can redistribute it and/or * Mapnik is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License * modify it under the terms of the GNU General Public License
@ -17,6 +17,8 @@
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
*/ */
#ifndef LAYER_LIST_MODEL_HPP #ifndef LAYER_LIST_MODEL_HPP
#define LAYER_LIST_MODEL_HPP #define LAYER_LIST_MODEL_HPP
@ -35,8 +37,10 @@ class LayerListModel : public QAbstractListModel
LayerListModel(std::shared_ptr<mapnik::Map> map, QObject * parent = 0); LayerListModel(std::shared_ptr<mapnik::Map> map, QObject * parent = 0);
int rowCount(const QModelIndex &parent = QModelIndex()) const; int rowCount(const QModelIndex &parent = QModelIndex()) const;
QVariant data(const QModelIndex &index, int role) const; QVariant data(const QModelIndex &index, int role) const;
QVariant headerData(int section, Qt::Orientation orientation, int role = Qt::DisplayRole) const; QVariant headerData(int section, Qt::Orientation orientation,
bool setData(const QModelIndex& index, const QVariant& value, int role = Qt::EditRole); int role = Qt::DisplayRole) const;
bool setData(const QModelIndex &index, const QVariant &value,
int role = Qt::EditRole);
Qt::ItemFlags flags(QModelIndex const& index) const; Qt::ItemFlags flags(QModelIndex const& index) const;
boost::optional<mapnik::layer&> map_layer(int i); boost::optional<mapnik::layer&> map_layer(int i);

View file

@ -1,6 +1,6 @@
/* This file is part of Mapnik (c++ mapping toolkit) /* This file is part of Mapnik (c++ mapping toolkit)
* *
* Copyright (C) 2024 Artem Pavlenko * Copyright (C) 2017 Artem Pavlenko
* *
* Mapnik is free software; you can redistribute it and/or * Mapnik is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License * modify it under the terms of the GNU General Public License
@ -17,6 +17,7 @@
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
*/ */
#include "layerwidget.hpp" #include "layerwidget.hpp"
#include <qabstractitemdelegate.h> #include <qabstractitemdelegate.h>
#include <qapplication.h> #include <qapplication.h>
@ -28,22 +29,27 @@
#include <qscrollbar.h> #include <qscrollbar.h>
#include <qrubberband.h> #include <qrubberband.h>
#include <qdebug.h> #include <qdebug.h>
#include <iostream>
#include "layerlistmodel.hpp" #include "layerlistmodel.hpp"
#include "layer_info_dialog.hpp" #include "layer_info_dialog.hpp"
using namespace std;
LayerTab::LayerTab(QWidget* parent) LayerTab::LayerTab(QWidget* parent)
: QListView(parent) : QListView(parent) {}
{}
void LayerTab::paintEvent(QPaintEvent *e) void LayerTab::paintEvent(QPaintEvent *e)
{ {
QListView::paintEvent(e); QListView::paintEvent(e);
} }
void LayerTab::dataChanged(const QModelIndex& topLeft, const QModelIndex& bottomRight, const QVector<int>& roles) void LayerTab::dataChanged(const QModelIndex &topLeft,
const QModelIndex &bottomRight)
{ {
QListView::dataChanged(topLeft, bottomRight);
qDebug("FIXME : update map view!");
emit update_mapwidget(); emit update_mapwidget();
QListView::dataChanged(topLeft, bottomRight, roles);
} }
void LayerTab::selectionChanged(const QItemSelection & selected, const QItemSelection &) void LayerTab::selectionChanged(const QItemSelection & selected, const QItemSelection &)
@ -51,7 +57,7 @@ void LayerTab::selectionChanged(const QItemSelection& selected, const QItemSelec
QModelIndexList list = selected.indexes(); QModelIndexList list = selected.indexes();
if (list.size() != 0) if (list.size() != 0)
{ {
qDebug("SELECTED LAYER -> %d", list[0].row()); std::cout << "SELECTED LAYER ->" << list[0].row() << "\n";
emit layerSelected(list[0].row()); emit layerSelected(list[0].row());
} }
} }
@ -63,6 +69,7 @@ void LayerTab::layerInfo()
if (indexes.size() > 0) if (indexes.size() > 0)
{ {
qDebug("id = %d",indexes[0].row()); qDebug("id = %d",indexes[0].row());
} }
} }
@ -82,7 +89,10 @@ void LayerTab::layerInfo2(QModelIndex const& index)
} }
} }
StyleTab::StyleTab(QWidget*) {} StyleTab::StyleTab(QWidget*)
{
}
void StyleTab::contextMenuEvent(QContextMenuEvent * event ) void StyleTab::contextMenuEvent(QContextMenuEvent * event )
{ {

View file

@ -1,6 +1,6 @@
/* This file is part of Mapnik (c++ mapping toolkit) /* This file is part of Mapnik (c++ mapping toolkit)
* *
* Copyright (C) 2024 Artem Pavlenko * Copyright (C) 2017 Artem Pavlenko
* *
* Mapnik is free software; you can redistribute it and/or * Mapnik is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License * modify it under the terms of the GNU General Public License
@ -17,6 +17,7 @@
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
*/ */
#ifndef LAYERWIDGET_HPP #ifndef LAYERWIDGET_HPP
#define LAYERWIDGET_HPP #define LAYERWIDGET_HPP
@ -37,7 +38,7 @@ class LayerTab : public QListView
void layerInfo(); void layerInfo();
void layerInfo2(QModelIndex const&); void layerInfo2(QModelIndex const&);
protected slots: protected slots:
void dataChanged(const QModelIndex& topLeft, const QModelIndex& bottomRight, const QVector<int>& roles); void dataChanged(const QModelIndex &topLeft, const QModelIndex &bottomRight);
void selectionChanged(const QItemSelection & selected, const QItemSelection &); void selectionChanged(const QItemSelection & selected, const QItemSelection &);
}; };
@ -46,7 +47,6 @@ class StyleTab : public QTreeView
Q_OBJECT Q_OBJECT
public: public:
StyleTab(QWidget* parent=0); StyleTab(QWidget* parent=0);
protected: protected:
void contextMenuEvent(QContextMenuEvent * event ); void contextMenuEvent(QContextMenuEvent * event );
}; };

View file

@ -1,6 +1,6 @@
/* This file is part of Mapnik (c++ mapping toolkit) /* This file is part of Mapnik (c++ mapping toolkit)
* *
* Copyright (C) 2024 Artem Pavlenko * Copyright (C) 2017 Artem Pavlenko
* *
* Mapnik is free software; you can redistribute it and/or * Mapnik is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License * modify it under the terms of the GNU General Public License
@ -17,32 +17,30 @@
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
*/ */
// qt // qt
#include <QApplication> #include <QApplication>
#include <QStringList> #include <QStringList>
#include <QSettings> #include <QSettings>
#include <mapnik/datasource_cache.hpp> #include <mapnik/datasource_cache.hpp>
#include <mapnik/font_engine_freetype.hpp> #include <mapnik/font_engine_freetype.hpp>
#include <mapnik/mapnik.hpp>
#include "mainwindow.hpp" #include "mainwindow.hpp"
int main( int argc, char **argv ) int main( int argc, char **argv )
{ {
using mapnik::datasource_cache; using mapnik::datasource_cache;
using mapnik::freetype_engine; using mapnik::freetype_engine;
mapnik::setup();
try try
{ {
#if QT_VERSION >= QT_VERSION_CHECK(5, 6, 0)
QApplication::setAttribute(Qt::AA_EnableHighDpiScaling);
#endif
QCoreApplication::setOrganizationName("Mapnik"); QCoreApplication::setOrganizationName("Mapnik");
QCoreApplication::setOrganizationDomain("mapnik.org"); QCoreApplication::setOrganizationDomain("mapnik.org");
QCoreApplication::setApplicationName("Viewer"); QCoreApplication::setApplicationName("Viewer");
QSettings settings("viewer.ini",QSettings::IniFormat); QSettings settings("viewer.ini",QSettings::IniFormat);
// register input plug-ins // register input plug-ins
QString plugins_dir = settings.value("mapnik/plugins_dir", QVariant("/usr/local/lib/mapnik/input/")).toString(); QString plugins_dir = settings.value("mapnik/plugins_dir",
QVariant("/usr/local/lib/mapnik/input/")).toString();
datasource_cache::instance().register_datasources(plugins_dir.toStdString()); datasource_cache::instance().register_datasources(plugins_dir.toStdString());
// register fonts // register fonts
int count = settings.beginReadArray("mapnik/fonts"); int count = settings.beginReadArray("mapnik/fonts");
@ -57,8 +55,7 @@ int main(int argc, char** argv)
QApplication app( argc, argv ); QApplication app( argc, argv );
MainWindow window; MainWindow window;
window.show(); window.show();
if (argc > 1) if (argc > 1) window.open(argv[1]);
window.open(argv[1]);
if (argc >= 3) if (argc >= 3)
{ {
QStringList list = QString(argv[2]).split(","); QStringList list = QString(argv[2]).split(",");
@ -69,22 +66,19 @@ int main(int argc, char** argv)
double y0 = list[1].toDouble(&ok); double y0 = list[1].toDouble(&ok);
double x1 = list[2].toDouble(&ok); double x1 = list[2].toDouble(&ok);
double y1 = list[3].toDouble(&ok); double y1 = list[3].toDouble(&ok);
if (ok) if (ok) window.set_default_extent(x0,y0,x1,y1);
window.set_default_extent(x0, y0, x1, y1);
} }
} }
else else
{ {
std::shared_ptr<mapnik::Map> map = window.get_map(); std::shared_ptr<mapnik::Map> map = window.get_map();
if (map) if (map) map->zoom_all();
map->zoom_all();
} }
if (argc == 4) if (argc == 4)
{ {
bool ok; bool ok;
double scaling_factor = QString(argv[3]).toDouble(&ok); double scaling_factor = QString(argv[3]).toDouble(&ok);
if (ok) if (ok) window.set_scaling_factor(scaling_factor);
window.set_scaling_factor(scaling_factor);
} }
return app.exec(); return app.exec();
} }

View file

@ -1,6 +1,6 @@
/* This file is part of Mapnik (c++ mapping toolkit) /* This file is part of Mapnik (c++ mapping toolkit)
* *
* Copyright (C) 2024 Artem Pavlenko * Copyright (C) 2017 Artem Pavlenko
* *
* Mapnik is free software; you can redistribute it and/or * Mapnik is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License * modify it under the terms of the GNU General Public License
@ -17,6 +17,7 @@
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
*/ */
// stl // stl
#include <iostream> #include <iostream>
@ -57,8 +58,8 @@
#include <boost/algorithm/string.hpp> #include <boost/algorithm/string.hpp>
MainWindow::MainWindow() MainWindow::MainWindow()
: filename_() : filename_(),
, default_extent_(-20037508.3428, -20037508.3428, 20037508.3428, 20037508.3428) default_extent_(-20037508.3428,-20037508.3428,20037508.3428,20037508.3428)
{ {
mapWidget_ = new MapWidget(this); mapWidget_ = new MapWidget(this);
QSplitter *splitter = new QSplitter(this); QSplitter *splitter = new QSplitter(this);
@ -106,15 +107,19 @@ MainWindow::MainWindow()
// slider // slider
connect(slider_,SIGNAL(valueChanged(int)),mapWidget_,SLOT(zoomToLevel(int))); connect(slider_,SIGNAL(valueChanged(int)),mapWidget_,SLOT(zoomToLevel(int)));
// renderer selector // renderer selector
connect(renderer_selector_, SIGNAL(currentIndexChanged(int)), mapWidget_, SLOT(updateRenderer(int))); connect(renderer_selector_,SIGNAL(currentIndexChanged(QString const&)),
mapWidget_, SLOT(updateRenderer(QString const&)));
// scale factor // scale factor
connect(scale_factor_, SIGNAL(valueChanged(double)), mapWidget_, SLOT(updateScaleFactor(double))); connect(scale_factor_,SIGNAL(valueChanged(double)),
mapWidget_, SLOT(updateScaleFactor(double)));
// //
connect(layerTab_,SIGNAL(update_mapwidget()),mapWidget_,SLOT(updateMap())); connect(layerTab_,SIGNAL(update_mapwidget()),mapWidget_,SLOT(updateMap()));
connect(layerTab_, SIGNAL(layerSelected(int)), mapWidget_, SLOT(layerSelected(int))); connect(layerTab_,SIGNAL(layerSelected(int)),
mapWidget_,SLOT(layerSelected(int)));
} }
MainWindow::~MainWindow() MainWindow::~MainWindow()
{ {
delete mapWidget_; delete mapWidget_;
@ -136,7 +141,8 @@ void MainWindow::open(QString const& path)
{ {
if (path.isNull()) if (path.isNull())
{ {
filename_ = QFileDialog::getOpenFileName(this, tr("Open Mapnik file"), currentPath, "*.xml"); filename_ = QFileDialog::getOpenFileName(this,tr("Open Mapnik file"),
currentPath,"*.xml");
} }
else else
{ {
@ -145,15 +151,18 @@ void MainWindow::open(QString const& path)
if (!filename_.isEmpty()) if (!filename_.isEmpty())
{ {
load_map_file(filename_); load_map_file(filename_);
setWindowTitle(tr("%1 - Mapnik Viewer").arg(filename_)); setWindowTitle(tr("%1 - Mapnik Viewer").arg(filename_));
} }
} }
void MainWindow::reload() void MainWindow::reload()
{ {
if (!filename_.isEmpty()) if (!filename_.isEmpty())
{ {
mapnik::box2d<double> bbox = mapWidget_->getMap()->get_current_extent(); mapnik::box2d<double> bbox = mapWidget_->getMap()->get_current_extent();
load_map_file(filename_); load_map_file(filename_);
mapWidget_->zoomToBox(bbox); mapWidget_->zoomToBox(bbox);
@ -164,10 +173,10 @@ void MainWindow::reload()
void MainWindow::save() void MainWindow::save()
{ {
QString initialPath = QDir::currentPath() + "/untitled.xml"; QString initialPath = QDir::currentPath() + "/untitled.xml";
QString filename = QFileDialog::getSaveFileName(this, QString filename = QFileDialog::getSaveFileName(this, tr("Save"),
tr("Save"),
initialPath, initialPath,
tr("%1 Files (*.xml)").arg(QString("Mapnik definition"))); tr("%1 Files (*.xml)")
.arg(QString("Mapnik definition")));
if (!filename.isEmpty()) if (!filename.isEmpty())
{ {
std::cout<<"saving "<< filename.toStdString() << std::endl; std::cout<<"saving "<< filename.toStdString() << std::endl;
@ -247,11 +256,11 @@ void MainWindow::export_as()
QByteArray fileFormat = action->data().toByteArray(); QByteArray fileFormat = action->data().toByteArray();
QString initialPath = QDir::currentPath() + "/map." + fileFormat; QString initialPath = QDir::currentPath() + "/map." + fileFormat;
QString fileName = QFileDialog::getSaveFileName( QString fileName = QFileDialog::getSaveFileName(this, tr("Export As"),
this,
tr("Export As"),
initialPath, initialPath,
tr("%1 Files (*.%2);;All Files (*)").arg(QString(fileFormat.toUpper())).arg(QString(fileFormat))); tr("%1 Files (*.%2);;All Files (*)")
.arg(QString(fileFormat.toUpper()))
.arg(QString(fileFormat)));
if (!fileName.isEmpty()) if (!fileName.isEmpty())
{ {
QPixmap const& pix = mapWidget_->pixmap(); QPixmap const& pix = mapWidget_->pixmap();
@ -261,6 +270,7 @@ void MainWindow::export_as()
void MainWindow::print() void MainWindow::print()
{ {
//Q_ASSERT(mapWidget_->pixmap()); //Q_ASSERT(mapWidget_->pixmap());
//QPrintDialog dialog(&printer, this); //QPrintDialog dialog(&printer, this);
//if (dialog.exec()) { //if (dialog.exec()) {
@ -387,7 +397,7 @@ void MainWindow::createToolBars()
scale_factor_ = new QDoubleSpinBox(fileToolBar); scale_factor_ = new QDoubleSpinBox(fileToolBar);
scale_factor_->setMinimum(0.1); scale_factor_->setMinimum(0.1);
scale_factor_->setMaximum(10.0); scale_factor_->setMaximum(5.0);
scale_factor_->setSingleStep(0.1); scale_factor_->setSingleStep(0.1);
scale_factor_->setValue(1.0); scale_factor_->setValue(1.0);
@ -401,6 +411,8 @@ void MainWindow::createToolBars()
fileToolBar->addAction(aboutAct); fileToolBar->addAction(aboutAct);
} }
void MainWindow::set_default_extent(double x0,double y0, double x1, double y1) void MainWindow::set_default_extent(double x0,double y0, double x1, double y1)
{ {
try try
@ -413,11 +425,10 @@ void MainWindow::set_default_extent(double x0, double y0, double x1, double y1)
prj.forward(x1,y1); prj.forward(x1,y1);
default_extent_=mapnik::box2d<double>(x0,y0,x1,y1); default_extent_=mapnik::box2d<double>(x0,y0,x1,y1);
mapWidget_->zoomToBox(default_extent_); mapWidget_->zoomToBox(default_extent_);
std::cout << "SET DEFAULT EXT:" << default_extent_ << std::endl; std::cout << "SET DEFAULT EXT\n";
} }
} }
catch (...) catch (...) {}
{}
} }
void MainWindow::set_scaling_factor(double scaling_factor) void MainWindow::set_scaling_factor(double scaling_factor)

View file

@ -1,6 +1,6 @@
/* This file is part of Mapnik (c++ mapping toolkit) /* This file is part of Mapnik (c++ mapping toolkit)
* *
* Copyright (C) 2024 Artem Pavlenko * Copyright (C) 2017 Artem Pavlenko
* *
* Mapnik is free software; you can redistribute it and/or * Mapnik is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License * modify it under the terms of the GNU General Public License
@ -17,6 +17,7 @@
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
*/ */
#ifndef MAINWINDOW_HPP #ifndef MAINWINDOW_HPP
#define MAINWINDOW_HPP #define MAINWINDOW_HPP
@ -45,10 +46,8 @@ class MainWindow : public QMainWindow
virtual ~MainWindow(); virtual ~MainWindow();
void set_default_extent(double x0,double y0,double x1, double y1); void set_default_extent(double x0,double y0,double x1, double y1);
void set_scaling_factor(double scaling_factor); void set_scaling_factor(double scaling_factor);
public : public :
std::shared_ptr<mapnik::Map> get_map(); std::shared_ptr<mapnik::Map> get_map();
protected: protected:
void closeEvent(QCloseEvent* event); void closeEvent(QCloseEvent* event);
public slots: public slots:
@ -66,7 +65,6 @@ class MainWindow : public QMainWindow
void pan_right(); void pan_right();
void pan_up(); void pan_up();
void pan_down(); void pan_down();
private: private:
void createActions(); void createActions();
void createMenus(); void createMenus();
@ -114,4 +112,5 @@ class MainWindow : public QMainWindow
mapnik::box2d<double> default_extent_; mapnik::box2d<double> default_extent_;
}; };
#endif //MAINWINDOW_HPP #endif //MAINWINDOW_HPP

View file

@ -1,6 +1,6 @@
/* This file is part of Mapnik (c++ mapping toolkit) /* This file is part of Mapnik (c++ mapping toolkit)
* *
* Copyright (C) 2024 Artem Pavlenko * Copyright (C) 2017 Artem Pavlenko
* *
* Mapnik is free software; you can redistribute it and/or * Mapnik is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License * modify it under the terms of the GNU General Public License
@ -17,12 +17,13 @@
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
*/ */
#include <QtGui> #include <QtGui>
#include <boost/bind.hpp> #include <boost/bind.hpp>
#include <mapnik/agg_renderer.hpp> #include <mapnik/agg_renderer.hpp>
#include <mapnik/layer.hpp> #include <mapnik/layer.hpp>
#include <mapnik/proj_transform.hpp> #include <mapnik/projection.hpp>
#include <mapnik/scale_denominator.hpp> #include <mapnik/scale_denominator.hpp>
#include <mapnik/view_transform.hpp> #include <mapnik/view_transform.hpp>
#include <mapnik/transform_path_adapter.hpp> #include <mapnik/transform_path_adapter.hpp>
@ -40,38 +41,54 @@
#include "mapwidget.hpp" #include "mapwidget.hpp"
#include "info_dialog.hpp" #include "info_dialog.hpp"
using mapnik::image_rgba8;
using mapnik::Map;
using mapnik::layer;
using mapnik::box2d; using mapnik::box2d;
using mapnik::coord2d; using mapnik::coord2d;
using mapnik::feature_kv_iterator;
using mapnik::feature_ptr; using mapnik::feature_ptr;
using mapnik::image_rgba8; using mapnik::view_transform;
using mapnik::layer;
using mapnik::Map;
using mapnik::projection; using mapnik::projection;
using mapnik::scale_denominator; using mapnik::scale_denominator;
using mapnik::view_transform; using mapnik::feature_kv_iterator;
double scales[] = {279541132.014, 139770566.007, 69885283.0036, 34942641.5018, 17471320.7509, double scales [] = {279541132.014,
8735660.37545, 4367830.18772, 2183915.09386, 1091957.54693, 545978.773466, 139770566.007,
272989.386733, 136494.693366, 68247.3466832, 34123.6733416, 17061.8366708, 69885283.0036,
8530.9183354, 4265.4591677, 2132.72958385, 1066.36479192, 533.182395962}; 34942641.5018,
17471320.7509,
8735660.37545,
4367830.18772,
2183915.09386,
1091957.54693,
545978.773466,
272989.386733,
136494.693366,
68247.3466832,
34123.6733416,
17061.8366708,
8530.9183354,
4265.4591677,
2132.72958385,
1066.36479192,
533.182395962};
MapWidget::MapWidget(QWidget *parent) MapWidget::MapWidget(QWidget *parent)
: QWidget(parent) : QWidget(parent),
, map_() map_(),
, selected_(1) selected_(1),
, extent_() extent_(),
, cur_tool_(ZoomToBox) cur_tool_(ZoomToBox),
, start_x_(0) start_x_(0),
, start_y_(0) start_y_(0),
, end_x_(0) end_x_(0),
, end_y_(0) end_y_(0),
, drag_(false) drag_(false),
, first_(true) first_(true),
, pen_(QColor(0, 0, 255, 96)) pen_(QColor(0,0,255,96)),
, selectedLayer_(-1) selectedLayer_(-1),
, scaling_factor_(1.0) scaling_factor_(1.0),
, cur_renderer_(AGG) cur_renderer_(AGG)
{ {
pen_.setWidth(3); pen_.setWidth(3);
pen_.setCapStyle(Qt::RoundCap); pen_.setCapStyle(Qt::RoundCap);
@ -139,23 +156,21 @@ void MapWidget::mousePressEvent(QMouseEvent* e)
{ {
QVector<QPair<QString,QString> > info; QVector<QPair<QString,QString> > info;
projection map_proj(map_->srs(), true); // map projection projection map_proj(map_->srs()); // map projection
double scale_denom = scale_denominator(map_->scale(),map_proj.is_geographic()); double scale_denom = scale_denominator(map_->scale(),map_proj.is_geographic());
view_transform t(map_->width(),map_->height(),map_->get_current_extent()); view_transform t(map_->width(),map_->height(),map_->get_current_extent());
for (unsigned index = 0; index < map_->layer_count();++index) for (unsigned index = 0; index < map_->layer_count();++index)
{ {
if (int(index) != selectedLayer_) if (int(index) != selectedLayer_) continue;
continue;
layer & layer = map_->layers()[index]; layer & layer = map_->layers()[index];
if (!layer.visible(scale_denom)) if (!layer.visible(scale_denom)) continue;
continue;
std::string name = layer.name(); std::string name = layer.name();
double x = e->x(); double x = e->x();
double y = e->y(); double y = e->y();
std::cout << "query at " << x << "," << y << "\n"; std::cout << "query at " << x << "," << y << "\n";
projection layer_proj(layer.srs(), true); projection layer_proj(layer.srs());
mapnik::proj_transform prj_trans(map_proj,layer_proj); mapnik::proj_transform prj_trans(map_proj,layer_proj);
//std::auto_ptr<mapnik::memory_datasource> data(new mapnik::memory_datasource); //std::auto_ptr<mapnik::memory_datasource> data(new mapnik::memory_datasource);
mapnik::featureset_ptr fs = map_->query_map_point(index,x,y); mapnik::featureset_ptr fs = map_->query_map_point(index,x,y);
@ -216,9 +231,10 @@ void MapWidget::mousePressEvent(QMouseEvent* e)
} }
// remove annotation layer // remove annotation layer
map_->layers().erase( map_->layers().erase(remove_if(map_->layers().begin(),
remove_if(map_->layers().begin(), map_->layers().end(), bind(&layer::name, _1) == "*annotations*"), map_->layers().end(),
map_->layers().end()); bind(&layer::name,_1) == "*annotations*")
, map_->layers().end());
} }
} }
} }
@ -277,23 +293,7 @@ void MapWidget::wheelEvent(QWheelEvent* e)
{ {
return; return;
} }
#if QT_VERSION >= QT_VERSION_CHECK(5, 14, 0)
QPointF corner(map_->width(), map_->height());
QPointF zoomCoords;
double zoom;
if (e->angleDelta().y() > 0)
{
zoom = 0.5;
QPointF center = corner / 2;
QPointF delta = e->position() - center;
zoomCoords = zoom * delta + center;
}
else
{
zoom = 2.0;
zoomCoords = corner - e->position();
}
#else
QPoint corner(map_->width(), map_->height()); QPoint corner(map_->width(), map_->height());
QPoint zoomCoords; QPoint zoomCoords;
double zoom; double zoom;
@ -309,7 +309,6 @@ void MapWidget::wheelEvent(QWheelEvent* e)
zoom = 2.0; zoom = 2.0;
zoomCoords = corner - e->pos(); zoomCoords = corner - e->pos();
} }
#endif
map_->pan_and_zoom(zoomCoords.x(), zoomCoords.y(), zoom); map_->pan_and_zoom(zoomCoords.x(), zoomCoords.y(), zoom);
updateMap(); updateMap();
@ -318,8 +317,7 @@ void MapWidget::wheelEvent(QWheelEvent* e)
void MapWidget::keyPressEvent(QKeyEvent *e) void MapWidget::keyPressEvent(QKeyEvent *e)
{ {
std::cout << "key pressed:"<< e->key()<<"\n"; std::cout << "key pressed:"<< e->key()<<"\n";
switch (e->key()) switch (e->key()) {
{
case Qt::Key_Minus: case Qt::Key_Minus:
zoomOut(); zoomOut();
break; break;
@ -372,6 +370,8 @@ void MapWidget::keyPressEvent(QKeyEvent* e)
default: default:
QWidget::keyPressEvent(e); QWidget::keyPressEvent(e);
} }
} }
void MapWidget::zoomToBox(mapnik::box2d<double> const& bbox) void MapWidget::zoomToBox(mapnik::box2d<double> const& bbox)
@ -455,6 +455,7 @@ void MapWidget::panRight()
} }
} }
void MapWidget::zoomToLevel(int level) void MapWidget::zoomToLevel(int level)
{ {
if ( map_ && level >= 0 && level < 19 ) if ( map_ && level >= 0 && level < 19 )
@ -520,11 +521,13 @@ void render_agg(mapnik::Map const& map, double scaling_factor, QPixmap& pix)
} }
} }
void render_grid(mapnik::Map const& map, double scaling_factor, QPixmap & pix) void render_grid(mapnik::Map const& map, double scaling_factor, QPixmap & pix)
{ {
std::cerr << "Not supported" << std::endl; std::cerr << "Not supported" << std::endl;
} }
void render_cairo(mapnik::Map const& map, double scaling_factor, QPixmap & pix) void render_cairo(mapnik::Map const& map, double scaling_factor, QPixmap & pix)
{ {
// FIXME // FIXME
@ -545,15 +548,12 @@ void render_cairo(mapnik::Map const& map, double scaling_factor, QPixmap& pix)
#endif #endif
} }
void MapWidget::updateRenderer(int index) void MapWidget::updateRenderer(QString const& txt)
{ {
std::cerr << "updateRenderer:" << index << std::endl; if (txt == "AGG") cur_renderer_ = AGG;
if (index == 0) else if (txt == "Cairo") cur_renderer_ = Cairo;
cur_renderer_ = AGG; else if (txt == "Grid") cur_renderer_ = Grid;
else if (index == 1) std::cerr << "Update renderer called" << std::endl;
cur_renderer_ = Cairo;
else if (index == 2)
cur_renderer_ = Grid;
updateMap(); updateMap();
} }
@ -586,19 +586,14 @@ void MapWidget::updateMap()
try try
{ {
projection prj(map_->srs(), true); // map projection projection prj(map_->srs()); // map projection
box2d<double> ext = map_->get_current_extent(); box2d<double> ext = map_->get_current_extent();
double x0 = ext.minx(); double x0 = ext.minx();
double y0 = ext.miny(); double y0 = ext.miny();
double x1 = ext.maxx(); double x1 = ext.maxx();
double y1 = ext.maxy(); double y1 = ext.maxy();
double z = 0; prj.inverse(x0,y0);
std::string dest_srs = {"epsg:4326"}; prj.inverse(x1,y1);
mapnik::proj_transform proj_tr(map_->srs(), dest_srs);
proj_tr.forward(x0, y0, z);
proj_tr.forward(x1, y1, z);
std::cout << "MAP SIZE:" << map_->width() << "," << map_->height() << std::endl;
std::cout << "BBOX (WGS84): " << x0 << "," << y0 << "," << x1 << "," << y1 << "\n"; std::cout << "BBOX (WGS84): " << x0 << "," << y0 << "," << x1 << "," << y1 << "\n";
update(); update();
// emit signal to interested widgets // emit signal to interested widgets
@ -621,6 +616,7 @@ void MapWidget::setMap(std::shared_ptr<Map> map)
map_ = map; map_ = map;
} }
void MapWidget::layerSelected(int index) void MapWidget::layerSelected(int index)
{ {
selectedLayer_ = index; selectedLayer_ = index;

View file

@ -1,6 +1,6 @@
/* This file is part of Mapnik (c++ mapping toolkit) /* This file is part of Mapnik (c++ mapping toolkit)
* *
* Copyright (C) 2024 Artem Pavlenko * Copyright (C) 2017 Artem Pavlenko
* *
* Mapnik is free software; you can redistribute it and/or * Mapnik is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License * modify it under the terms of the GNU General Public License
@ -17,6 +17,7 @@
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
*/ */
#ifndef MAP_WIDGET_HPP #ifndef MAP_WIDGET_HPP
#define MAP_WIDGET_HPP #define MAP_WIDGET_HPP
@ -29,6 +30,7 @@
#include <string> #include <string>
#include <memory> #include <memory>
#ifndef Q_MOC_RUN #ifndef Q_MOC_RUN
#include <mapnik/map.hpp> #include <mapnik/map.hpp>
#endif #endif
@ -38,13 +40,19 @@ class MapWidget : public QWidget
Q_OBJECT Q_OBJECT
public: public:
enum eTool { enum eTool
{
ZoomToBox = 1, ZoomToBox = 1,
Pan, Pan,
Info, Info,
}; };
enum eRenderer { AGG, Cairo, Grid }; enum eRenderer
{
AGG,
Cairo,
Grid
};
private: private:
std::shared_ptr<mapnik::Map> map_; std::shared_ptr<mapnik::Map> map_;
@ -62,7 +70,6 @@ class MapWidget : public QWidget
int selectedLayer_; int selectedLayer_;
double scaling_factor_; double scaling_factor_;
eRenderer cur_renderer_; eRenderer cur_renderer_;
public: public:
MapWidget(QWidget *parent=0); MapWidget(QWidget *parent=0);
void setTool(eTool tool); void setTool(eTool tool);
@ -82,11 +89,10 @@ class MapWidget : public QWidget
void zoomToLevel(int level); void zoomToLevel(int level);
void updateMap(); void updateMap();
void layerSelected(int); void layerSelected(int);
void updateRenderer(int); void updateRenderer(QString const& txt);
void updateScaleFactor(double scale_factor); void updateScaleFactor(double scale_factor);
signals: signals:
void mapViewChanged(); void mapViewChanged();
protected: protected:
void paintEvent(QPaintEvent* ev); void paintEvent(QPaintEvent* ev);
void resizeEvent(QResizeEvent* ev); void resizeEvent(QResizeEvent* ev);
@ -95,7 +101,10 @@ class MapWidget : public QWidget
void mouseReleaseEvent(QMouseEvent* e); void mouseReleaseEvent(QMouseEvent* e);
void wheelEvent(QWheelEvent* e); void wheelEvent(QWheelEvent* e);
void keyPressEvent(QKeyEvent *e); void keyPressEvent(QKeyEvent *e);
void export_to_file(unsigned width, unsigned height, std::string const& filename, std::string const& type); void export_to_file(unsigned width,
unsigned height,
std::string const& filename,
std::string const& type);
}; };
#endif // MAP_WIDGET_HPP #endif // MAP_WIDGET_HPP

View file

@ -1,6 +1,6 @@
/* This file is part of Mapnik (c++ mapping toolkit) /* This file is part of Mapnik (c++ mapping toolkit)
* *
* Copyright (C) 2024 Artem Pavlenko * Copyright (C) 2017 Artem Pavlenko
* *
* Mapnik is free software; you can redistribute it and/or * Mapnik is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License * modify it under the terms of the GNU General Public License
@ -17,6 +17,7 @@
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
*/ */
#include "styles_model.hpp" #include "styles_model.hpp"
#include <mapnik/config.hpp> #include <mapnik/config.hpp>
#include <mapnik/util/variant.hpp> #include <mapnik/util/variant.hpp>
@ -47,14 +48,19 @@ class node : private mapnik::util::noncopyable
struct wrap : public node_base struct wrap : public node_base
{ {
wrap(T const& obj) wrap(T const& obj)
: obj_(obj) : obj_(obj) {}
{}
~wrap() {} ~wrap() {}
QString name() const { return obj_.name(); } QString name () const
{
return obj_.name();
}
QIcon icon() const { return obj_.icon(); } QIcon icon() const
{
return obj_.icon();
}
T obj_; T obj_;
}; };
@ -62,19 +68,34 @@ class node : private mapnik::util::noncopyable
public: public:
template <typename T> template <typename T>
node ( T const& obj, node * parent=0) node ( T const& obj, node * parent=0)
: impl_(new wrap<T>(obj)) : impl_(new wrap<T>(obj)),
, parent_(parent) parent_(parent)
{} {}
QString name() const { return impl_->name(); } QString name() const
{
return impl_->name();
}
QIcon icon() const { return impl_->icon(); } QIcon icon() const
{
return impl_->icon();
}
unsigned num_children() const { return children_.count(); } unsigned num_children() const
{
return children_.count();
}
node* child(unsigned row) const { return children_.value(row); } node * child(unsigned row) const
{
return children_.value(row);
}
node* parent() const { return parent_; } node * parent() const
{
return parent_;
}
node * add_child(node * child) node * add_child(node * child)
{ {
@ -89,7 +110,10 @@ class node : private mapnik::util::noncopyable
return 0; return 0;
} }
~node() { qDeleteAll(children_); } ~node()
{
qDeleteAll(children_);
}
private: private:
const std::unique_ptr<node_base> impl_; const std::unique_ptr<node_base> impl_;
@ -97,6 +121,7 @@ class node : private mapnik::util::noncopyable
node * parent_; node * parent_;
}; };
struct symbolizer_info struct symbolizer_info
{ {
QString operator() (mapnik::point_symbolizer const& sym) const QString operator() (mapnik::point_symbolizer const& sym) const
@ -214,8 +239,7 @@ class symbolizer_node
{ {
public: public:
symbolizer_node(mapnik::symbolizer const & sym) symbolizer_node(mapnik::symbolizer const & sym)
: sym_(sym) : sym_(sym) {}
{}
~symbolizer_node(){} ~symbolizer_node(){}
QString name() const QString name() const
@ -235,9 +259,8 @@ class rule_node
{ {
public: public:
rule_node(QString name,mapnik::rule const & r) rule_node(QString name,mapnik::rule const & r)
: name_(name) : name_(name),
, rule_(r) rule_(r) {}
{}
~rule_node() {} ~rule_node() {}
QString name() const QString name() const
{ {
@ -245,7 +268,10 @@ class rule_node
return QString(mapnik::to_expression_string(*filter).c_str()); return QString(mapnik::to_expression_string(*filter).c_str());
} }
QIcon icon() const { return QIcon(":/images/filter.png"); } QIcon icon() const
{
return QIcon(":/images/filter.png");
}
private: private:
QString name_; QString name_;
@ -256,15 +282,20 @@ class style_node
{ {
public: public:
style_node(QString name, mapnik::feature_type_style const& style) style_node(QString name, mapnik::feature_type_style const& style)
: name_(name) : name_(name),
, style_(style) style_(style) {}
{}
~style_node() {} ~style_node() {}
QString name() const { return name_; } QString name() const
{
return name_;
}
QIcon icon() const { return QIcon(":/images/style.png"); } QIcon icon() const
{
return QIcon(":/images/style.png");
}
private: private:
QString name_; QString name_;
@ -275,21 +306,26 @@ class map_node
{ {
public: public:
explicit map_node(std::shared_ptr<mapnik::Map> map) explicit map_node(std::shared_ptr<mapnik::Map> map)
: map_(map) : map_(map) {}
{}
~map_node() {} ~map_node() {}
QString name() const { return QString("Map"); } QString name() const
{
return QString("Map");
}
QIcon icon() const { return QIcon(":/images/map.png"); } QIcon icon() const
{
return QIcon(":/images/map.png");
}
private: private:
std::shared_ptr<mapnik::Map> map_; std::shared_ptr<mapnik::Map> map_;
}; };
StyleModel::StyleModel(std::shared_ptr<mapnik::Map> map, QObject * parent) StyleModel::StyleModel(std::shared_ptr<mapnik::Map> map, QObject * parent)
: QAbstractItemModel(parent) : QAbstractItemModel(parent),
, root_(new node(map_node(map))) root_(new node(map_node(map)))
{ {
using style_type = std::map<std::string,mapnik::feature_type_style>; using style_type = std::map<std::string,mapnik::feature_type_style>;
style_type const & styles = map->styles(); style_type const & styles = map->styles();
@ -346,8 +382,7 @@ int StyleModel::rowCount(QModelIndex const& parent) const
{ {
//qDebug("rowCount"); //qDebug("rowCount");
node * parent_node; node * parent_node;
if (parent.column() > 0) if (parent.column() > 0) return 0;
return 0;
if (!parent.isValid()) if (!parent.isValid())
parent_node = root_.get(); parent_node = root_.get();
else else
@ -370,6 +405,7 @@ QVariant StyleModel::data(const QModelIndex& index, int role) const
{ {
if (role == Qt::DisplayRole) if (role == Qt::DisplayRole)
{ {
return QVariant(cur_node->name()); return QVariant(cur_node->name());
} }
else if ( role == Qt::DecorationRole) else if ( role == Qt::DecorationRole)

View file

@ -1,6 +1,6 @@
/* This file is part of Mapnik (c++ mapping toolkit) /* This file is part of Mapnik (c++ mapping toolkit)
* *
* Copyright (C) 2024 Artem Pavlenko * Copyright (C) 2017 Artem Pavlenko
* *
* Mapnik is free software; you can redistribute it and/or * Mapnik is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License * modify it under the terms of the GNU General Public License
@ -17,6 +17,7 @@
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
*/ */
#ifndef STYLE_MODEL_HPP #ifndef STYLE_MODEL_HPP
#define STYLE_MODEL_HPP #define STYLE_MODEL_HPP
@ -26,6 +27,8 @@
#include <mapnik/map.hpp> #include <mapnik/map.hpp>
#endif #endif
class node; class node;
class StyleModel : public QAbstractItemModel class StyleModel : public QAbstractItemModel
{ {
@ -39,7 +42,6 @@ class StyleModel : public QAbstractItemModel
int rowCount( QModelIndex const& parent = QModelIndex()) const; int rowCount( QModelIndex const& parent = QModelIndex()) const;
int columnCount( QModelIndex const& parent = QModelIndex()) const; int columnCount( QModelIndex const& parent = QModelIndex()) const;
QVariant data(const QModelIndex & index, int role = Qt::DisplayRole) const; QVariant data(const QModelIndex & index, int role = Qt::DisplayRole) const;
private: private:
//std::shared_ptr<mapnik::Map> map_; //std::shared_ptr<mapnik::Map> map_;
const std::unique_ptr<node> root_; const std::unique_ptr<node> root_;

View file

@ -3,12 +3,12 @@
###################################################################### ######################################################################
TEMPLATE = app TEMPLATE = app
QT += core gui widgets QT += core gui widgets
LIBS += $$system(mapnik-config --libs --dep-libs)
QMAKE_CXX = $$system(mapnik-config --cxx) QMAKE_CXX = $$system(mapnik-config --cxx)
QMAKE_LINK = $$system(mapnik-config --cxx) QMAKE_LINK = $$system(mapnik-config --cxx)
QMAKE_CXXFLAGS += $$system(mapnik-config --cxxflags) QMAKE_CXXFLAGS += $$system(mapnik-config --cxxflags)
QMAKE_CXXFLAGS += $$system(mapnik-config --includes --dep-includes --defines) QMAKE_CXXFLAGS += $$system(mapnik-config --includes --dep-includes --defines)
QMAKE_LFLAGS += $$system(mapnik-config --ldflags) QMAKE_LFLAGS += $$system(mapnik-config --libs)
QMAKE_LFLAGS += $$system(mapnik-config --ldflags --dep-libs)
# Input # Input
CONFIG += qt debug_and_release CONFIG += qt debug_and_release

Some files were not shown because too many files have changed in this diff Show more