如何在react-map-gl / deck.gl视口中获得H3六角形?

时间:2019-06-18 10:06:51

标签: deck.gl react-map-gl h3

我想基于在视口上可见的H3六边形查询数据(并在每次视口更改时查询新数据)。无论如何,有没有用react-map-gl和deck.gl实现这一目标?

1 个答案:

答案 0 :(得分:0)

要获取视口内部的六边形,需要获取当前视口的边界框。如果当前视口为{latitude, longitude, zoom, width, height}(如果使用react-map-gl,则可能处于组件状态),则可以使用viewport-mercator-project获取视口:

import WebMercatorViewport from 'viewport-mercator-project';

function bboxFromViewport(viewport) {
    const {width, height} = viewport;
    const projection = new WebMercatorViewport(viewport);
    const [west, north] = projection.unproject([0, 0]);
    const [east, south] = projection.unproject([width, height]);
    return {north, south, east, west};
}

然后,您可以将边界框与h3.polyfill一起使用,以给定的分辨率获取包含的六边形的列表:

const nw = [north, west];
const ne = [north, east];
const sw = [south, west];
const se = [south, east];
const hexes = h3.polyfill([nw, ne, se, sw], resolution);

根据您的用例,您可能需要在调用polyfill之前扩展边界框,以在即时视口之外获取其他数据。

您可能还想以某种方式在视口范围上将其绑定,否则最终可能会缩小以百万计的六边形。我为此使用的一种廉价技巧是对我们将得到的六边形数量进行非常粗略的估计,如果过高则避免调用polyfill

// Inexact, but it doesn't matter for our purposes
const KM_PER_DEGREE_LAT = 111.2;

function estimateHexagonsInBBox(bbox, width, height, res) {
    // This is an extremely rough estimate, but we're just trying
    // to get a reasonable order of magnitude
    const aspect = width / height;
    const latKm = (bbox.north - bbox.south) * KM_PER_DEGREE_LAT;
    const lonKm = latKm * aspect;
    return (latKm * lonKm) / h3.hexArea(res, h3.UNITS.km2);
}