如何修复Mapbox GL中的画布大小?

时间:2017-02-10 02:12:03

标签: mapbox-gl mapbox-gl-js

我使用Mapbox GL来显示地图并从中心裁剪出固定大小的图像。它适用于我设计的特定分辨率(1920x1080),但当我开始使地图样式widthheight发生变化时页面响应时,画布大小也开始变化!

因此,当我裁剪图像时,尺寸应始终不同,因为900px画布上的300px与2000px画布上的300px不同。如果我在Chrome中将设备类型从桌面更改为移动设备,则画布大小甚至会发生巨大变化。

有没有办法在使用CSS属性缩放整个地图时固定画布DOM大小,因为它是在普通canvas上完成的?我尝试做trackResize: false并且画布DOM大小保持固定但是地图没有缩放以适应容器。

8 个答案:

答案 0 :(得分:2)

我最好的方法是在加载地图之前使地图大小无效,从而迫使其自行调整大小。

在Angular / Ionic中

import { AfterViewInit, Component, OnInit } from '@angular/core'
import * as  mapboxgl from 'mapbox-gl'

@Component({
  selector: 'app-map',
  templateUrl: 'map.page.html',
  styleUrls: ['map.page.scss']
})
export class MapPage implements AfterViewInit, OnInit {
  private map: mapboxgl.Map  

  constructor() {
    mapboxgl.accessToken = "<YOUR_TOKEN>"
  }

  ngOnInit() {
    setTimeout(() => this.buildMap(), 0);
  }

  ngAfterViewInit() {
    setTimeout(() => this.map.invalidateSize(), 0);
  }

  buildMap() {
    let conf = {
      container: 'map',
      style: '<YOUR_CUSTOM_STYLE>'
      zoom: 13,
      center: [lng, lat]
    }
    this.map = new mapboxgl.Map(conf)  
    // Add map controls
    this.map.addControl(new mapboxgl.NavigationControl())
  }
}

答案 1 :(得分:2)

map.on('idle',function(){
map.resize()
})

试试这个。它对我来说很好。(仅适用于 mapbox 用户)

答案 2 :(得分:1)

如果我理解正确,您希望地图始终显示地理区域,无论地图容器有多大或多小?这与大多数网络地图的标准行为相反,这使得规模保持不变,并扩大或缩小覆盖范围。

如果这是你想要的,你可以通过在你的窗口调整大小时调用map.fitBounds()来实现它。

答案 3 :(得分:1)

对于版本:“ mapbox-gl”:“ ^ 1.2.1”,设置画布地图容器类的高度:

.mapboxgl-canvas-container {

    height: 100vh;

}

然后在地图加载事件:

onMapLoaded(event) {

    event.map.resize();

}

答案 4 :(得分:0)

根据@davejoem答案,通过将setTimeout放在buildMap()函数外部,我能够显示完整的地图高度而无需拉伸。我不必使用invalidateSize(),因为它会引发此错误:

错误TS2339:类型“地图”上不存在属性'invalidateSize'。

我不得不将setTimeout的{​​{1}}放在buildMap()函数中,并将2000放在setTimeout的第二个参数上,因为有些时候很难刷新,因此映射不完整高度。

希望这可以帮助您彻底解决问题。

答案 5 :(得分:0)

我正在使用angular 9,这对我来说是这样的: ngAfterViewInit() { setTimeout(() => this.buildMap(), 2000); }

答案 6 :(得分:0)

我不知道这是否会对某人有所帮助,但出于某种原因,桌面窗口的设备像素比为 1,而在移动设备中则不同。

如果您尝试使地图具有响应性,而当您切换到移动设备时,情况就变了,这是因为您的设备像素比率因一个平台而异。

尝试使用以下方法获取您的设备像素比率:

window.devicePixelRatio

并使用它。

就我而言,我正在使用片段着色器尝试使用地图上的位置和缩放的组合来绘制圆圈。但是由于片段着色器在我切换到移动设备时使用 canvas.width(而不是 canvas.clientWidth)工作,因此代表 100 米的像素数量发生了变化,我使用了设备像素比率,然后使用设备像素将更大数量的像素转换为米比率...

如果有人在 MapboxGL-JS 片段着色器和像素到米转换方面遇到问题:

uniform float u_dpr; // the window.devicePixelRatio

//v_rad is radius in meters
//40075017.0 circunference of earth
//cos(-0.296) is based on my latitude
//etc.. 
//multiply the final value by the pixel ratio to get responsiveness working 

float maxDist = (v_rad / (40075017.0*cos(-0.296)/pow(2.0, (u_zoom+9.0)))*u_dpr);

答案 7 :(得分:-2)

解决方案

<div
    ref={el => this.mapContainer = el}
    style={{
            position: 'absolute',
            top: 0,
            bottom: 0,
            width: '100%',
            height: '100vh',
     }}
 />