Search code examples
androidgoogle-mapsmarkerclickablemarkerclusterer

How to add title, snippet and icon to ClusterItem?


I had this activity:

public class MapViewer extends Activity {

    private GoogleMap map;
    private Database db = new Database(this);

    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.mapviewer);

        try {
            map = ((MapFragment) getFragmentManager().findFragmentById(R.id.map)).getMap();
            if (map != null) {
                map.setMyLocationEnabled(true);
                map.setMapType(GoogleMap.MAP_TYPE_NORMAL);
                map.getUiSettings().setRotateGesturesEnabled(false);

                this.addMerchantMarkers(new MarkerOptions());
            }
        } catch (NullPointerException e) {
            e.printStackTrace();
        }
    }

    public void addMerchantMarkers(MarkerOptions mo) {
        SQLiteDatabase dbRead = db.getReadableDatabase();
        Cursor result = dbRead.rawQuery("SELECT title, addr, lat, lon FROM users", null);

        while(result.moveToNext()) {            
            map.addMarker(mo.position(new LatLng(result.getFloat(2), result.getFloat(3)))
                    .title(result.getString(0))
                    .snippet(result.getString(1))
                    );;
        }
    }
}

that i changed in the following way to use markers clustering:

public class MapViewer extends Activity {

    private GoogleMap map;
    private Database db = new Database(this);
    private ClusterManager<MyItem> mClusterManager;

    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.mapviewer);

        try {
            map = ((MapFragment) getFragmentManager().findFragmentById(R.id.map)).getMap();
            if (map != null) {
                map.setMyLocationEnabled(true);
                map.setMapType(GoogleMap.MAP_TYPE_NORMAL);
                map.getUiSettings().setRotateGesturesEnabled(false);

                setUpClusterer();
            }
        } catch (NullPointerException e) {
            e.printStackTrace();
        }
    }

    private void setUpClusterer() {
        mClusterManager = new ClusterManager<MyItem>(this, map);

        map.setOnCameraChangeListener(mClusterManager);
        map.setOnMarkerClickListener(mClusterManager);

        addItems();
    }

    private void addItems() {
        SQLiteDatabase dbRead = db.getReadableDatabase();
        Cursor result = dbRead.rawQuery("SELECT lat, lon, title, addr FROM users", null);

        while(result.moveToNext()) {
            MyItem offsetItem = new MyItem(result.getFloat(0), result.getFloat(1));
            mClusterManager.addItem(offsetItem);
        }
    }
}

Now i don't know how to add title, snippet and icon to every marker like previous code. Now if i click on single marker nothing happens... How to get that?


Solution

  • Here you should work with ClusterManager itself. For example, setting on cluster item click:

            mClusterManager.setOnClusterItemClickListener(new ClusterManager.OnClusterItemClickListener<MyItem>() {
                @Override
                public boolean onClusterItemClick(MyItem item) {
                    //put your code here
                    return false;
                }
            });
    

    And there are other different methods in ClusterManager class. You'll need a less obvious code to assign info window to marker or cluster - you should use this code:

    mClusterManager.getMarkerCollection().setOnInfoWindowAdapter(new MarkerInfoWindowAdapter());
    mClusterManager.getClusterMarkerCollection().setOnInfoWindowAdapter(new ClusterInfoWindow());
    

    There MarkerInfoWindowAdapter and ClusterWindowAdapter is your classes, which implements GoogleMap.InfoWindowAdapter.

    With icons it's a little harder, because clustering changes icons to default. You should use method:

    public void setRenderer(com.google.maps.android.clustering.view.ClusterRenderer<T> view)
    

    You could your own renderer class and override some methods. For example, to set custom icons use such a class:

    class OwnIconRendered extends DefaultClusterRenderer<MyItem> {
    
        public OwnIconRendered(Context context, GoogleMap map,
                               ClusterManager<MyItem> clusterManager) {
            super(context, map, clusterManager);
        }
    
        @Override
        protected void onBeforeClusterItemRendered(MyItem item, MarkerOptions markerOptions) {
            markerOptions.icon(item.getIcon());
            markerOptions.snippet(item.getSnippet());
            markerOptions.title(item.getTitle());
            super.onBeforeClusterItemRendered(item, markerOptions);
        }
    }
    

    And use it in such way:

    mClusterManager.setRenderer(new OwnIconRendered(activity.getApplicationContext(), getMap(), mClusterManager));