JavaScript:维护界限的最佳方式(谷歌地图)?

时间:2011-05-13 07:31:07

标签: javascript google-maps bounds

我正在使用Google Maps v3 API。我目前正在请求每次更改视口时(通过缩放或移动地图)获取新数据并丢弃我的旧数据。这很好用,但现在我想缓存数据,以便每次视口更改时都不需要获取数据。 Google Maps API通过其东北和西南坐标定义视口,该坐标由纬度和经度组成。它们存储在名为LatLngBounds的对象中。

我想出了两种可以做到这一点的方法:

  1. 存储用户访问的每个新视口的边界,并检查新视口是否位于旧视口中,并仅获取新视口中不在旧视口内的部分的新数据。基本上,
  2. 将每个新视口划分为我们拥有的数据的矩形部分和需要获取的数据。存储每个矩形部分的边界。
  3. 如果有人能想出更好的方法,可以随意提出新方法。

    我的问题是哪一个在性能/内存使用率和整体速度方面会更好?它们都是类似的算法,所以真的很重要吗?

    此外,现在两种算法都依赖于基于旧视口划分新视口。划分新视口的算法是什么样的? (假设我实现了我的第二个算法)

    var prevBounds = [ /* Array of previously seen bounds */ ];
    var newViewport = map.getBounds(); // New Viewport to divide up
    var sw = newViewport.getSouthWest();
    var swlat = sw.lat();
    var swlng = sw.lng();
    var ne = newViewport.getNorthEast();
    var nelat = ne.lat();
    var nelng = ne.lng();
    // newViewport.intersects(bounds) 
    // Returns true if this bounds shares any points with this bounds.
    

1 个答案:

答案 0 :(得分:1)

我可能会考虑采用谷歌提供地图图块的方式或多或少 - 而不是一次加载整个视口的数据,将整个地图划分为方形区域(尽管可能比Google的256x256图块更大),确定当前视口中的哪些区域,并加载这些区域的数据。当用户平移和缩放地图时,检查视口边界以查看是否有新区域进入框架,并根据需要加载它们。粗糙的伪代码:

var cache = {}

function onViewportChange() {
    // get new bounds
    var bounds = map.getBounds();
    // identify all the areas in the bounds
    var areas = getAreas(bounds);
    areas.forEach(function(area) {
        if (area.key in cache) {
            // do nothing, or load items from cache
        } else {
            // load new data, storing the key (and maybe the data) 
            // to the cache
        }
    })
}

function getAreas(bounds) {
    /* given a set of bounds, return an array of objects like:
    [
        {
           x: 1,
           y: 2,
           zoom: 4,
           key: "4-1,2",
           bounds: b // lat/lon bounds of this area
        },
        ...
    ]
    */
}

(请参阅Google explanation of map coordinatesthis example了解如何实施getAreas。)

这样做的吸引力在于您检索的区域要简单得多,并且检查您是否已经加载了给定区域的数据变得非常容易 - 每个区域都可以有一个简单的唯一键,可能是一个字符串由x / y /缩放坐标组成,并且在加载每个新区域时,您可以保存密钥(或者密钥和数据 - 这取决于您是从地图中删除旧数据还是仅将其保留在那里)到一些缓存对象。然后,当视口移动到新区域时,您需要做的就是检查缓存中是否存在该密钥。

缺点是您可能经常在当前视口之外加载数据,并且您可能向服务器发送的请求多于您建议的实现。如果您以不同的缩放级别提供不同的数据,则此方法可能效果最佳 - 否则您可能会因为尝试选择在不同缩放时效果良好的单一尺寸缓存区而陷入困境。