I am using Google Maps and its clustering utility in my app. Clustering itself is working fine, but I have issue, when I try to deal with configuration changes.
This is my case:
fragment
.markers
.marker
, it is highlighted and BottomSheet
is expanded to display.If user rotates screen (i.e. configuration change happens), I save what marker was selected using onSaveInstanceState
(actually I do not save marker itself, but only a link to related List
entry like ID). Then, I want to restore that user selection that was before configuration change.
Clustering itself is executed like this:
clusterManager.clearItems();
clusterManager.addItems(eventManager.getEventList());
clusterManager.cluster();
This code is executed, when data is received from server. When clustering is executed, all markers
, obviously, are recreated as well. So in order to highlight previous user selection (previous marker
), I must know WHEN clustering utility finishes its operation. By that time I am sure that I can safely use such functions like:
clusterManager.getRenderer()).getMarker(<param>)
and
clusterManager.getRenderer()).getClusterItem(<param>)
otherwise, these will return null
sometimes, if clustering task is not completed yet.
However, I cannot find a reasonable way, how to get a response from clustering utility (i.e. ClusterManager
), when clustering is completed. I think I need to update this standard clustering code:
/**
* Runs the clustering algorithm in a background thread, then re-paints when results come back.
*/
private class ClusterTask extends AsyncTask<Float, Void, Set<? extends Cluster<T>>> {
@Override
protected Set<? extends Cluster<T>> doInBackground(Float... zoom) {
mAlgorithmLock.readLock().lock();
try {
return mAlgorithm.getClusters(zoom[0]);
} finally {
mAlgorithmLock.readLock().unlock();
}
}
@Override
protected void onPostExecute(Set<? extends Cluster<T>> clusters) {
mRenderer.onClustersChanged(clusters);
}
}
I think, that onPostExecute
should provide a response not to Renderer
only, but to a user of ClusterManager
(like my fragment
) that clustering is done. But I do not want to modify standard code.
Is there a better way how to handle this case?
You are going about this the wrong way.
You should implement:
class YourClusterItemRenderer extends DefaultClusterRenderer<YourClusterItem>
and set it to ClusterManager as renderer like this:
mClusterManager.setRenderer(new YourClusterItemRenderer(...));
Override YourClusterItemRenderer's methods onBeforeClusterItemRendered
and onBeforeClusterRendered
and there you can change what each marker looks like according to your logic as per parameters from your server.
So when ClusterManager finishes rendering all your markers already look like you want them according to user state etc.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With