Mapnik简要介绍

Mapnik

一、 Mapnik 介绍

Mapnik 是一个开源的 Python/C++ 地图渲染引擎,他的功能是把数据形式的地图,包含一些地理对象,如地图、层、数据源、特征和地理几何等,通过 一个样式表的定义,渲染成位图格式,用来提供 WMS 服务。其核心是一个 C++ 的共享库提供空间数据访问和可视化的算法和模式。该共享库支持多种操作系统,可以在多线程环境下很好的运行,主要面向一些提供 GIS 服务的 Web 应用开发。图一为使用 mapnik 渲染出来的街区图:

图一

二、 地图数据组织

Mapnik 数据组织包括地图、图层、风格、规则、符号等,其具体以渲染地图文件的方式或者是编程实现的方式予以提供,其地图文件的组织结构如下图二:

图二

备注:地图中可以包含多个风格( Style )、多个图层( Layer ),图层包含对应一个数据源及多个风格,风格包含多个规则,一个规则可以包含多种符号,不同的符号包含不同的属性设置,以 LineSymbolizer 为例,包含 stroke (颜色)、 stroke-width (宽度)、透明度( stroke-opacity )、线相交处模式( stroke-linejoin )、线头模式( stroke-linecap )、线段绘制迭代间隔( stroke-dasharray )。不同的符号之间也有一些相同的属性如 line_pattern_symbolizer polygon_pattern_symbolizerpoint_symbolizer 都需要一个file 属性来作为填充图片!

以下是一个仅有路(Road )表述信息的Mapnik 配置文件,可以对map 文件有初步的了解:

        

   

        

   

    

          

        road-border

        road-fill

        highway-border

        highway-fill

                   highway-label

       

            GB2312

            F:/BeijingM/Pathline1-6

            shape

       

   

三、 Mapnik 主要架构类关系图

图三

图三右边 feature_type_style 部分,为一系列的参数描述,主要是承载地图渲染所需要的相关绘制参数信息; Map 为组织图层数据及绘制风格的载体; feature_style_processor 为地图渲染的抽象基类, agg_renderer cairo_renderer 就是具体负责渲染绘制的类,在绘制时,需要一个用来绘制的设备,如 agg_renderer 需要一个 image_32 的内存图像缓冲区,来承载最终绘制的图片,然后可以使用 save_to_file() 函数将内存图片保存成最终文件格式!

四、 Mapnik 使用示例

Mapnik 开发主要流程:

l  定义 Map 对象,设置绘制使用的设备大小,及投影信息

l  加载 Map 的配置信息

l  设置 Map 绘制的地理范围

l  定义绘制使用的设备( agg_renderer 为内存图片缓冲区)

l  使用 agg_renderer 或者 cairo_renderer 渲染

l  保存到文件(可选,对于 cairo_renderer 渲染到 pdf svg 等矢量文件时不需要)

具体示例代码如下:

#include

#include

#include

#include

#include

#include

#include

 

#include

#include

#include "mapnik/load_map.hpp"

 

  int main ( int argc , char** argv)

  {

     using namespace mapnik;// 使用 mapnik 命名空间

     try {

         std::cout << " running demo ... /n";

                     // 注册数据源插件

         datasource_cache::instance()->register_datasources("F:/work/mapnik/trunk/builds/win32/Bin");

                     // 注册字体

                   freetype_engine::register_font("F:/work/fonts/simkai.ttf");

                   freetype_engine::register_font("F:/work/fonts/msyh.ttf");

         std::vector names = freetype_engine::face_names();

         std::cout << "face names size:" << names.size() << "/n";

         for (unsigned i = 0; i < names.size(); ++i){

             std::cout << names[i] << "/n";

         }

                     // 声明 Map 对象,包括绘制使用的设备大小,及投影信息

         Map m(1024,1024,"+proj=merc +a=6378137 +b=6378137 +lat_ts=0.0 +lon_0=0.0 +x_0=0.0 +y_0=0 +k=1.0 +units=m +nadgrids=@null +no_defs");

         //m.set_background(color_factory::from_string("white"));

                     // 加载 Map 配置文件

                     load_map(m,"mapconfig.xml");

                   // 设置地图绘制地理范围

         m.zoomToBox(box2d(12934400,4862620,12944200,4872400));

                   // 定义具体绘制的内存图片缓冲区

         image_32 buf(m.getWidth(),m.getHeight());

                     // 使用 agg_renderer 渲染绘制

         agg_renderer ren(m,buf);

          ren.apply();

                   //save_map(m,"mapconfig.xml");

         //save_to_file(buf.data(),"demo.jpg","jpeg");

         //save_to_file(buf.data(),"demo.png","png");

                     // 保存到文件

         save_to_file(buf.data(),"demo256.png","png256");

                   //save_map(m,"map.xml",false);

         std::cout << "One maps have been rendered using AGG in the current directory:/n"

            "Have a look!/n";

     }

     catch ( const mapnik::config_error & ex )

     {

         std::cerr << "### Configuration error: " << ex.what() << std::endl;

         return EXIT_FAILURE;

     }

     catch ( const std::exception & ex )

     {

         std::cerr << "### std::exception: " << ex.what() << std::endl;

         return EXIT_FAILURE;

     }

     catch ( ... )

     {

         std::cerr << "### Unknown exception." << std::endl;

         return EXIT_FAILURE;

     }

     return EXIT_SUCCESS;   

  }

五、 总结

Mapnik 作为一个开源的地图渲染引擎,拥有良好的技术架构,并使用了很多成熟的开源技术如 proj4 freetype libxml2 GDAL Boost ltdl 等,并使用 AGG Cairo-Graphics 来具体渲染绘制,具有良好的反锯齿效果!大量使用了 Boost 库特有的 C++ 技术,如 variant tuple ,并利用 C++ STL (仿函数等)、泛型编程技术及相关设计模式(单件模式、访问者模式等),使用插件式的数据源开发方式,使 Mapnik 可以灵活扩展出针对自己的数据格式插件!

然而对于开发人员, mapnik 采用的属性与具体渲染操作分开的模式,屏蔽了内部复杂的实现细节,而对外提供的接口确是简单易用!

 

你可能感兴趣的:(Mapnik简要介绍)