高德地图实现 Canvas 截图并在左侧页面展示的方案

68 阅读2分钟

实现高德地图截图并且展示在左侧页面上效果

image.png

核心原理

利用高德地图(AMap)基于 Canvas 的渲染机制,直接提取地图容器内的 Canvas 渲染层,通过原生 Canvas API 转换为 Base64 格式的图片数据,最终将图片渲染到左侧页面指定区域。

实现步骤

  1. 获取地图 Canvas 渲染层

    • 通过地图实例 / ID 获取地图容器 DOM 引用;
    • 查找容器内所有 Canvas 元素(高德地图多图层渲染,核心渲染层通常为最后一个 Canvas);
    • 校验 Canvas 元素有效性,避免获取失败。
  2. Canvas 转 Base64 图片数据

    • 创建新 Canvas 并继承原地图 Canvas 宽高,保证截图尺寸一致;
    • 填充白色背景(避免透明底适配问题),将原 Canvas 内容绘制到新 Canvas;
    • 调用 toDataURL 转换为 PNG 格式的 Base64 数据。
  3. 左侧页面展示截图

    • 将 Base64 数据赋值给左侧页面图片标签的 src,或通过状态管理(如 React 的 setMapUrl)绑定到页面

4、 具体代码

```
   // 地图截图功能
    const handleScreenshot = async () => {
    if (!amapRef.current) {
      alert('地图尚未加载完成');
      return;
    }
    try {
      // 延迟一小段时间确保地图渲染完成
      setTimeout(() => {
        // 获取地图容器元素
        const mapContainer = amapRef.current.getContainer
          ? amapRef.current.getContainer()
          : document.getElementById('sandtable-map__map__dev');
        // 确保mapContainer是有效的DOM元素
        if (!mapContainer || typeof mapContainer.querySelectorAll !== 'function') {
          console.error('无法获取地图容器或容器不是有效的DOM元素');
          alert('地图截图失败,请重试');
          return;
        }

    // 查找地图容器中的canvas元素
    const canvasElements = mapContainer.querySelectorAll('canvas');

    if (canvasElements.length > 0) {
      // 通常最后一个canvas是地图渲染层
      const canvas = canvasElements[canvasElements.length - 1];

      // 确保canvas元素存在
      if (!canvas || typeof canvas.toDataURL !== 'function') {
        console.error('无法获取地图canvas元素');
        alert('地图截图失败,请重试');
        return;
      }

      // 创建一个新的canvas,设置宽高比
      const originalWidth = canvas.width;
      const originalHeight = canvas.height;

      // 计算宽高比的新尺寸
      const newWidth = originalWidth;
      // const newHeight = Math.round((newWidth * 10) / 20);
      const newHeight = originalHeight;

      // 创建新的canvas元素
      const newCanvas = document.createElement('canvas');
      newCanvas.width = newWidth;
      newCanvas.height = newHeight;

      // 获取绘图上下文
      const ctx = newCanvas.getContext('2d');
      if (!ctx) {
        console.error('无法获取canvas绘图上下文');
        alert('地图截图失败,请重试');
        return;
      }

      // 计算绘制位置,居中显示
      const x = 0;
      const y = (newHeight - originalHeight) / 2;

      // 绘制原始canvas内容到新canvas
      ctx.fillStyle = '#ffffff';
      ctx.fillRect(0, 0, newWidth, newHeight);
      ctx.drawImage(canvas, x, y, originalWidth, originalHeight);

      // 将新canvas转换为图片数据
      const dataUrl = newCanvas.toDataURL('image/png', 1.0);
      //存储图片
      setMapUrl(dataUrl);
    } else {
      // 如果找不到canvas元素,尝试使用高德地图的截图插件
      console.warn('未找到地图canvas元素,尝试使用高德地图截图插件');
    }
  }, 1000);
} catch (error) {
  console.error('截图失败:', error);
}