使用 ClusterManager 时如何更新 Map 上的标记

Posted

技术标签:

【中文标题】使用 ClusterManager 时如何更新 Map 上的标记【英文标题】:How update markers on Map when using ClusterManager 【发布时间】:2015-12-20 01:20:18 【问题描述】:

我正在尝试使用来自服务器的较新数据更新我的地图,但我不知道如何从中删除旧项目(标记和集群 - 使用 ClusterManager) map ( - 在我看来,我只能在 ClusterManager 中添加。

我有 BroadcastReceiver,它会在有新数据时获得意图。我正在尝试这样的事情:(但它给了我 UnsupportedOperationException 在线 "...getMarkers().clear();"

private BroadcastReceiver myRefrestMapBroadcastReceiver = new BroadcastReceiver() 
    @Override
    public void onReceive(Context context, Intent intent) 
        Log.d(TAG, "onReceive");
        mClusterManager.clearItems();
        mClusterManager.getMarkerCollection().getMarkers().clear();
        mClusterManager.getClusterMarkerCollection().getMarkers().clear();
        mClusterManager.addItems(LocationGetter.getReports());
    
;

添加了数据来映射只有这个功能。

java.util.Collection<Marker> userCollection = mClusterManager.getMarkerCollection().getMarkers();
            ArrayList<Marker> userList = new ArrayList<Marker>(userCollection);
            // now is userList empty
            for(Marker marker: userList)
                marker.remove();
            

            java.util.Collection<Marker> userCollection2 = mClusterManager.getClusterMarkerCollection().getMarkers();
            ArrayList<Marker> userList2 = new ArrayList<Marker>(userCollection2);
            // now is userList2 empty
            for(Marker marker: userList2)
                marker.remove();
            

            mClusterManager.addItems(LocationGetter.getReports());

【问题讨论】:

我用了这里的方法如果你得到了空的ArrayList,确保你有正确的ClusterManagerMarkerCollection() 【参考方案1】:

我一直专注于 ClusterManager,所以我忘记了 GoogleMap,特别是方法 clear()。我能够用这段代码解决问题:

mGoogleMap.clear();
mClusterManager.clearItems();  // calling just in case (may not be needed)
mClusterManager.addItems(LocationGetter.getReports());

【讨论】:

对我来说这还不够。我正在删除和添加很多项目。操作完成后调用它解决了我缺少刷新的问题:mClusterManager.cluster(); - 也许它可以帮助某人。 正如@plexus 所说,需要调用 cluster() 来确保更新集群。并且要小心 .clear() 因为很多时候您需要放大/缩小地图才能正确更新。【参考方案2】:

根据ClusterManagerdocumentation,我们可以使用mClusterManager.cluster();

此方法强制重新集群。您可能想在添加后调用它 新项目。

【讨论】:

使用多个项目时如何删除特定项目?你能看看这个帖子***.com/questions/53405893/…吗??【参考方案3】:

没有任何 API 来通知集群项目已更新。 但是您可以使用clusterManager.removeItem() + clusterManager.addItem() 来强制更新项目。

但您必须小心,因为您通常要更新项目,因为它更改了一些影响渲染的属性,您需要使用支持此功能并覆盖 onClusterItemRendered() 和/或 onClusterRendered() 的自定义 ClusterRenderer。使用 onBefore 变体将不起作用,因为它们只在标记创建时被调用一次。

你可以看看这个 GitHub 问题GitHub issue

【讨论】:

你可以看看这个帖子***.com/questions/53405893/…【参考方案4】:

由于我的应用需要在创建地图后多次更新集群,我发现此工作流是删除和添加新集群的最佳解决方案:

mGoogleMap.clear();
mClusterManager.clear(); 
//Do work to add items to cluster
mClusterManager.addItems(yourItemsList);
//Finally 
mClusterManager.cluster(); 

这应该会在修改内容后强制集群重新渲染。

【讨论】:

【参考方案5】:

我想知道我怎么会遇到这个问题 - 我以前从未遇到过这样的地图节点问题。

但是,这在我的示例应用程序的设置或更新映射逻辑中:

        mClusterManager = new ClusterManager<>(getContext(), googleMap);
        mClusterManager.setAnimation(false);
        mClusterManager.clearItems();

我从数据库中添加节点,然后从请求中添加一些节点,在我为构造函数添加空检查之前有明显的影响

也就是说,这就是我应该拥有的:

    if (mClusterManager == null)
            mClusterManager = new ClusterManager<>(getContext(), googleMap);
        mClusterManager.setAnimation(false);
        mClusterManager.clearItems();

我一定是复制粘贴了这个,在那个上面浪费了半个小时......小心!

【讨论】:

【参考方案6】:

对我有用的不是clear()the map,因为我还有一些其他标记未附加到集群管理器。

对我有用的是:

this.clustermanger.clearItems()
this.clustermanager.clusterMakerCollection.clear()
//and I had to force a "cluster" again, force the clustermanager to take down all markers
this.clustermanager.cluster()

【讨论】:

【参考方案7】:

你应该可以做到:

val didUpdate = clusterManager?.updateItem(MyClusterItem(data))
clusterManager?.cluster()

确保 clusterManager 确实更新项目的关键是在扩展 ClusterItem 的类中覆盖 equals 和 hashcode,例如:

fun getId(): String 
    return data.id

override fun equals(other: Any?): Boolean 
    return other is MyClusterItem && other.getId() == getId()

override fun hashCode(): Int 
    return getId().hashCode()

【讨论】:

以上是关于使用 ClusterManager 时如何更新 Map 上的标记的主要内容,如果未能解决你的问题,请参考以下文章

如何在 android 中获得 ClusterManager 点击和 ClusterManager 项目点击

ClusterManager setOnCameraIdleListener

从 ClusterManager 获取标记

来自 android:android-maps-utils 的 ClusterManager 已更改且不兼容

Android:Google Maps Clustermanager 行为异常。群集图标有时在全放大时不会消失。为啥?

ClusterManager onMarkerClickListener 用于非聚集标记