【问题标题】:Google Map Marker Cluster error when using custom icons使用自定义图标时出现 Google Map Marker Cluster 错误
【发布时间】:2020-04-01 04:52:59
【问题描述】:

目前正在开发具有 500 多个标记的 android 移动应用程序。我正在使用标记群集功能以便清晰地查看谷歌地图。我已经实现了 ClusterItemDefaultClusterRenderer 类。

ClusterItem 类提供标记集群功能,DefaultClusterRenderer 提供除默认红气球以外的自定义图标。

一旦我实现了 DefaultClusterRenderer 类并只更改了图标,它就会给我以下错误。一开始可以正常登录,但是一旦我尝试缩放地图,就会发生错误。

Logcat 指向类的默认实现 Logcat输出如下

java.lang.NullPointerException: Attempt to invoke virtual method 'boolean java.lang.String.equals(java.lang.Object)' on a null object reference
        at com.google.maps.android.clustering.view.DefaultClusterRenderer.onClusterItemUpdated(DefaultClusterRenderer.java:789)
        at com.google.maps.android.clustering.view.DefaultClusterRenderer$CreateMarkerTask.perform(DefaultClusterRenderer.java:973)
        at com.google.maps.android.clustering.view.DefaultClusterRenderer$CreateMarkerTask.access$2000(DefaultClusterRenderer.java:934)
        at com.google.maps.android.clustering.view.DefaultClusterRenderer$MarkerModifier.performNextTask(DefaultClusterRenderer.java:650)
        at com.google.maps.android.clustering.view.DefaultClusterRenderer$MarkerModifier.handleMessage(DefaultClusterRenderer.java:621)
        at android.os.Handler.dispatchMessage(Handler.java:106)
        at android.os.Looper.loop(Looper.java:164)
        at android.app.ActivityThread.main(ActivityThread.java:6501)
        at java.lang.reflect.Method.invoke(Native Method)

它指向默认实现,知道如何解决这个问题吗?

【问题讨论】:

标签: android google-maps markerclusterer markers


【解决方案1】:

显然这是 Google Maps Utils 库中的一个错误,您可以从 here 看到相关线程

在他们发布新版本之前,我找到了解决方法。正如您提到的,您实现了 DefaultClusterRenderer 类。如果您没有像我一样重写 onClusterUpdatedItem 方法,请使用库中正确版本的代码重写此方法。

如果你使用的是 java

protected void onClusterItemUpdated(T item, Marker marker) {
        boolean changed = false;
        // Update marker text if the item text changed - same logic as adding marker in CreateMarkerTask.perform()
        if (item.getTitle() != null && item.getSnippet() != null) {
            if (!item.getTitle().equals(marker.getTitle())) {
                marker.setTitle(item.getTitle());
                changed = true;
            }
            if (!item.getSnippet().equals(marker.getSnippet())) {
                marker.setSnippet(item.getSnippet());
                changed = true;
            }
        } else if (item.getSnippet() != null && !item.getSnippet().equals(marker.getTitle())) {
            marker.setTitle(item.getSnippet());
            changed = true;
        } else if (item.getTitle() != null && !item.getTitle().equals(marker.getTitle())) {
            marker.setTitle(item.getTitle());
            changed = true;
        }
        // Update marker position if the item changed position
        if (!marker.getPosition().equals(item.getPosition())) {
            marker.setPosition(item.getPosition());
            changed = true;
        }
        if (changed && marker.isInfoWindowShown()) {
            // Force a refresh of marker info window contents
            marker.showInfoWindow();
        }
    }

或者如果你正在使用 Kotlin

override fun onClusterItemUpdated(item: YOUR_MARKER_ITEM_CLASS?, marker: Marker?) {
        var changed = false
        // Update marker text if the item text changed - same logic as adding marker in CreateMarkerTask.perform()
        // Update marker text if the item text changed - same logic as adding marker in CreateMarkerTask.perform()
        if (item!!.title != null && item!!.snippet != null) {
            if (!item!!.title.equals(marker!!.title)) {
                marker!!.title = item!!.title
                changed = true
            }
            if (!item!!.snippet.equals(marker!!.snippet)) {
                marker!!.snippet = item!!.snippet
                changed = true
            }
        } else if (item!!.snippet != null && !item!!.snippet.equals(marker!!.title)) {
            marker!!.title = item!!.snippet
            changed = true
        } else if (item!!.title != null && !item!!.title.equals(marker!!.title)) {
            marker!!.title = item!!.title
            changed = true
        }
        // Update marker position if the item changed position
        // Update marker position if the item changed position
        if (!marker!!.position.equals(item!!.position)) {
            marker!!.position = item!!.position
            changed = true
        }
        if (changed && marker!!.isInfoWindowShown) {
            // Force a refresh of marker info window contents
            marker!!.showInfoWindow()
        }
    }

至少在他们发布下一个版本之前,这个小解决方法解决了问题。

编辑: 我还建议您离开 Google Maps Utils 库并使用 this 库进行聚类。它更适合和快速。

【讨论】:

    【解决方案2】:

    我也有同样的问题,我找到了 1 个解决方案。每次重新创建 ClusterManager。我知道它不能解决问题,但你不会有错误。

    【讨论】:

      【解决方案3】:

      使用 Kotlin,在 DefaultClusterRenderer 中重写 onClusterUpdated 方法,如下所示:

      override fun onClusterUpdated(cluster: Cluster<MyModel>, marker: Marker) {}
      

      它对我有用!

      【讨论】:

        猜你喜欢
        • 2020-11-02
        • 1970-01-01
        • 2021-01-31
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 2017-01-31
        • 1970-01-01
        • 2016-02-05
        相关资源
        最近更新 更多