Gil A Gil A - 2 months ago 34
Android Question

Android Firebase remove Google Maps markers

Trying to make a small Android app that shows the locations of people as Google Maps markers.

when the user presses a button to appear on the map, the app retrieves the users data from the Firebase JSON and shows the users on the map in real time. if a user moves, the marker moves with him (removed and recreated when his location changes).

everything works great, except that when the user presses to leave the map, his marker remains in all the other phones even though it's deleted from the Firebase JSON.

can anyone explain how to fix this problem ?

my code for retrieving the users and create markers in the map:

ValueEventListener UsersActiveListener = new ValueEventListener() {

@Override
public void onDataChange(DataSnapshot dataSnapshot) {
for (DataSnapshot userSnapshot : dataSnapshot.getChildren()) {

UsersActive uA = userSnapshot.getValue(UsersActive.class);

if (uA.getUserIDcode() != firebaseauth.getCurrentUser().getUid()) {

Double uAlatindouble = Double.valueOf(uA.getUserlat());
Double uAlonindouble = Double.valueOf(uA.getUserlon());

LatLng uALTLG;

if (uAmarker != null) {
uAmarker.remove();
}

uALTLG = new LatLng(uAlatindouble, uAlonindouble);
MarkerOptions markerOptions = new MarkerOptions();
markerOptions.position(uALTLG);
markerOptions.title(uA.getUsername());
markerOptions.icon(BitmapDescriptorFactory.fromResource(R.drawable.usermarker));
uAmarker = mMap.addMarker(markerOptions);

}
}
}


my code for entering or leaving the map (by pressing two FABs: goActive, goNotActive):

public void goActiveFAB (View view){

isActive = true;
FABgoActive.setVisibility(GONE);
FABDontgoActive.setVisibility(View.VISIBLE);

// user in map class

UsersActive CurrentUserActive = new UsersActive();

CurrentUserActive.setUserIDcode(firebaseauth.getCurrentUser().getUid());
CurrentUserActive.setUserlat(String.valueOf(mLastLocation.getLatitude()));
CurrentUserActive.setUserlon(String.valueOf(mLastLocation.getLongitude()));
CurrentUserActive.setUsername(currentUser.getNickname());

groupPosShareRef.child(firebaseauth.getCurrentUser().getUid()).setValue(CurrentUserActive);

}

public void goNotActiveFAB (View view){

isActive = false;
FABgoActive.setVisibility(View.VISIBLE);
FABDontgoActive.setVisibility(View.GONE);

groupPosShareRef.child(firebaseauth.getCurrentUser().getUid()).removeValue();


}


thanks!
Gil.

Answer

Use ChildEventListener instead, then map each marker to each user's id.

Map<String, Marker> markers = new HashMap();

ref.addChildEventListener(new ChildEventListener() {
    @Override
    public void onChildAdded(DataSnapshot dataSnapshot, String s) {
        UsersActive uA = dataSnapshot.getValue(UsersActive.class);

        // ...

        Marker uAmarker = mMap.addMarker(markerOptions);
        markers.put(dataSnapshot.getKey(), uAmarker);
    }

    @Override
    public void onChildChanged(DataSnapshot dataSnapshot, String s) {
        UsersActive uA = dataSnapshot.getValue(UsersActive.class);

        // ...

        if (markers.contains(dataSnapshot.getKey())) {
            Marker marker = markers.get(dataSnapshot.getKey());

            marker.remove();
            // or
            // marker.setPosition(newPosition);
        }

        Marker uAmarker = mMap.addMarker(markerOptions);
        markers.put(dataSnapshot.getKey(), uAmarker);
    }

    @Override
    public void onChildRemoved(DataSnapshot dataSnapshot) {
        if (markers.contains(dataSnapshot.getKey())) {
            Marker marker = markers.get(dataSnapshot.getKey());
            marker.remove();
        }
    }

    @Override
    public void onChildMoved(DataSnapshot dataSnapshot, String s) {

    }

    @Override
    public void onCancelled(DatabaseError databaseError) {

    }
});