leaflet【十一】地图瓦片路径可视化

发布于:2025-07-06 ⋅ 阅读:(12) ⋅ 点赞:(0)

前言

在开发调试过程当中,如果引入的是公司内部的Gis地图信息或者一些第三方定制来的Gis地图数据,当某一些地图块数据缺失的时候,要打开F12去一个个找那些链接(去找对应的xy与layer)失效、那么你可能需要使用以下插件帮你实现瓦片路径、层级可视化

leaflet-map-block

github 地址

npm 地址

该插件封装了一个 Leaflet 的网格图层 LeafletMapBlockLayer,用于在地图上渲染带有网格和文字标记的瓦片。支持自定义网格线样式和网格文字显示。安装和使用都非常简单,代码如下:

npm i leaflet-map-block

使用:

import {LeafletMapBlockLayer} from 'leaflet-map-block/dist/LeafletMapBlock';

map.addLayer(new LeafletMapBlockLayer({lineDash: [2, 2]}));

其中LeafletMapBlockLayer是一个类,他的构造函数可以传递一个对象,这个对象就是对这个插件进行的一个配置

值类型 默认值 说明
strokeStyle string ‘red’ 线颜色
lineWidth number 2 线宽
lineDash number[] [5,5] 线的虚线样式:[0,0] 为实线
showGridText boolean true 是否显示网格文字
gridTextColor string ‘black’ 网格文字颜色
gridFont string ‘12px Arial’ gridFont

比方说我们使用的是天地图的瓦片,那么我们的地图URL就是:http://t1.tianditu.gov.cn/DataServer?T=ter_w&x={x}&y={y}&l={z}&tk=tk
,那么当那一块缺了的时候没有渲染出来就可以拿地图上的xyz放到这个链接的xyz值中就可以快速定位到了

在这里插入图片描述

或者说我们有自己的地图的话,那也是一样的替换URL当中的xyz验证一下是不是真的图片缺失,是的话就去对应的文件系统找这个图片就好了

在这里插入图片描述

源码解析

授人以鱼不如授人以渔,这也是在一次机缘巧合之下发生的问题,使用内部地图但是缺失了一些块不好定位的时候,正好再看leaflet官方文档找的。

也就是这个GridLayer图层,我们知道地图渲染是按照瓦片一块块贴到canvas上面,然后渲染一个canvas实现的

一个冷姿势:在leaflet这个官网里面是英文的,如果想看中文版的,把.com改成.cn就可以了

那么正好:来开始封装吧:

  • 定义一个类,继承L.GridLayer
  • 实现构造,用来传递options配置
  • createTile方法会在map.addLayer()将该图层添加到地图的时候调用,返回一个canvas元素【也就是单个的地图瓦片】
  • 既然可以拿到每一次渲染的地图瓦片,那么我们就可以给它添加一些内容了
  • 创建一个canvas元素,这个canvas元素是和地图瓦片一样的大小
  • 给这个canvas元素添加内容【边框和文字】其中层级和定位信息在coords当中可以取到
  • 最后返回这个canvas对象tile就完成了
import L from 'leaflet';

interface CanvasLayerOptions extends L.GridLayerOptions {
  // 线颜色
  strokeStyle?: string;
  // 线宽
  lineWidth?: number;
  // 线的虚线样式:[0,0]为实线
  lineDash?: number[];
  // 是否显示网格文字
  showGridText?: boolean;
  // 网格文字颜色
  gridTextColor?: string;
  // 网格文字大小、字体等配置
  gridFont?: string;
}

let options: CanvasLayerOptions = {};

export class LeafletMapBlockLayer extends L.GridLayer {

  constructor(data?: CanvasLayerOptions) {
    super(data);
    options = {
      strokeStyle: 'red',
      lineWidth: 2,
      lineDash: [5, 5],
      showGridText: true,
      gridTextColor: 'black',
      gridFont: '12px Arial',
      ...data
    };
  }


  createTile(coords: any): HTMLCanvasElement {
    const tile = L.DomUtil.create('canvas', 'my-leaflet-tile') as HTMLCanvasElement;

    const size = this.getTileSize();
    tile.width = size.x;
    tile.height = size.y;

    const ctx = tile.getContext('2d');

    const {
      strokeStyle = '',
      lineWidth = 0,
      lineDash = [0, 0],
      showGridText = true,
      gridTextColor = 'black',
      gridFont = '12px Arial'
    } = options;

    if (ctx) {
      ctx.strokeStyle = strokeStyle;
      ctx.lineWidth = lineWidth;
      ctx?.setLineDash(lineDash);
      ctx?.strokeRect(0, 0, tile.width, tile.height);

      if (showGridText) {
        ctx.fillStyle = gridTextColor;
        ctx.font = gridFont;
        ctx.fillText(`x:${coords.x}, y:${coords.y}, z:${coords.z}`, 5, 15);
      }
    }
    return tile;
  }
}

npm publish

既然封装好了,那么也打包发布到npm上吧

  • 修改package.json文件,需要指定
    • name:项目名
    • version:版本号
    • description:项目描述
    • main:入口文件
    • module:es6模块入口文件
    • types:ts类型声明文件
    • keywords:关键字
    • author:作者
    • license:协议
    • scripts:打包脚本
  • 执行打包命令:npm run build-lib,打包完成之后会生成dist目录
  • 登录npm:npm login
  • 发布到npm:npm publish

就这样也就发布到了npm上。