Change position of Google Maps API's "My location" button

JavaAndroidGoogle Maps-Android-Api-2Android Maps-V2

Java Problem Overview


I am using the Google Maps Android API v2, and I need a way to chance the position of the "My Location" button.

I get the "My Location" button like this:

GooglePlayServicesUtil.isGooglePlayServicesAvailable(getApplicationContext());
final GoogleMap map = ((SupportMapFragment) getSupportFragmentManager()
		.findFragmentById(R.id.map)).getMap();

// This gets the button
map.setMyLocationEnabled(true);

Java Solutions


Solution 1 - Java

You can get the "My Location" button and move it, like :

public class MapFragment extends SupportMapFragment {
@Override
public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) {
    View mapView = super.onCreateView(inflater, container, savedInstanceState);   

    // Get the button view 
    View locationButton = ((View) mapView.findViewById(1).getParent()).findViewById(2);

    // and next place it, for exemple, on bottom right (as Google Maps app)
    RelativeLayout.LayoutParams rlp = (RelativeLayout.LayoutParams) locationButton.getLayoutParams();
    // position on right bottom
    rlp.addRule(RelativeLayout.ALIGN_PARENT_TOP, 0);
    rlp.addRule(RelativeLayout.ALIGN_PARENT_BOTTOM, RelativeLayout.TRUE);
    rlp.setMargins(0, 0, 30, 30);
    }
}

Solution 2 - Java

Just use GoogleMap.setPadding(left, top, right, bottom), which allows you to indicate parts of the map that may be obscured by other views. Setting padding re-positions the standard map controls, and camera updates will use the padded region.

https://developers.google.com/maps/documentation/android/map#map_padding

Solution 3 - Java

This may not be the best solution, but you could place your own button over the map and handle it yourself. It would take the following:-

  1. Put the map in a frameLayout and add your button on top. E.g.

     <fragment
         xmlns:map="http://schemas.android.com/apk/res-auto"
         android:id="@+id/mapFragment"
         android:layout_width="fill_parent"
         android:layout_height="fill_parent"
         class="com.google.android.gms.maps.MapFragment"
         map:mapType="normal"
         map:uiCompass="true" />
     
     <ImageButton
         android:id="@+id/myMapLocationButton"
         android:layout_width="36dp"
         android:layout_height="36dp"
         android:layout_gravity="bottom|right"
         android:background="@drawable/myMapLocationDrawable"
         android:contentDescription="My Location" />
    

  2. Edit the maps UI settings so the button doesn't appear when you call setMyLocationEnabled(true). You can do this via map.getUiSettings(). setMyLocationButtonEnabled(false);

  3. Handle the click of your new button to emulate what the supplied button does. E.g. call mMap.setMyLocationEnabled(...); and pan the map to the current location.

Hope that helps, or hope someone comes a long with a simpler solution for you ;-)

Solution 4 - Java

It's already been explained above.Just a small addition to fabLouis's answer. You may also get your map view from the SupportMapFragment.

        /**
         * Move the button
         */
        SupportMapFragment mapFragment = (SupportMapFragment) getSupportFragmentManager().
                findFragmentById(R.id.map);
        View mapView = mapFragment.getView();
        if (mapView != null &&
                mapView.findViewById(1) != null) {
            // Get the button view
            View locationButton = ((View) mapView.findViewById(1).getParent()).findViewById(2);
            // and next place it, on bottom right (as Google Maps app)
            RelativeLayout.LayoutParams layoutParams = (RelativeLayout.LayoutParams)
                    locationButton.getLayoutParams();
            // position on right bottom
            layoutParams.addRule(RelativeLayout.ALIGN_PARENT_TOP, 0);
            layoutParams.addRule(RelativeLayout.ALIGN_PARENT_BOTTOM, RelativeLayout.TRUE);
            layoutParams.setMargins(0, 0, 30, 30);
        }

Solution 5 - Java

I don't fancy seeing these magic view IDs others are using, I suggest using tags to find MapViews children.

Here is my solution for placing the My Location button above the Zoom controls.

// Get map views
View location_button =_mapView.findViewWithTag("GoogleMapMyLocationButton");
View zoom_in_button = _mapView.findViewWithTag("GoogleMapZoomInButton");
View zoom_layout = (View) zoom_in_button.getParent();

// adjust location button layout params above the zoom layout
RelativeLayout.LayoutParams location_layout = (RelativeLayout.LayoutParams) location_button.getLayoutParams();
location_layout.addRule(RelativeLayout.ALIGN_PARENT_TOP, 0);
location_layout.addRule(RelativeLayout.ABOVE, zoom_layout.getId());

Solution 6 - Java

I solved this problem in my map fragment by re positioning my location button to the right bottom corner of view using code below, here is my Maps Activity.java :-

add this lines of code in onCreate() method,

 SupportMapFragment mapFragment = (SupportMapFragment) getSupportFragmentManager()
                .findFragmentById(R.id.map);
        mapView = mapFragment.getView();
        mapFragment.getMapAsync(this);

and here is onMapReady() code :-

@Override
        public void onMapReady(GoogleMap googleMap) {
            mMap = googleMap;
            mMap.setMyLocationEnabled(true);

            // Add a marker in Sydney and move the camera
            LatLng sydney = new LatLng(-34, 151);
            mMap.addMarker(new MarkerOptions().position(sydney).title("Marker in Sydney"));
            mMap.moveCamera(CameraUpdateFactory.newLatLng(sydney));

            if (mapView != null &&
                    mapView.findViewById(Integer.parseInt("1")) != null) {
                // Get the button view
                View locationButton = ((View) mapView.findViewById(Integer.parseInt("1")).getParent()).findViewById(Integer.parseInt("2"));
                // and next place it, on bottom right (as Google Maps app)
                RelativeLayout.LayoutParams layoutParams = (RelativeLayout.LayoutParams)
                        locationButton.getLayoutParams();
                // position on right bottom
                layoutParams.addRule(RelativeLayout.ALIGN_PARENT_TOP, 0);
                layoutParams.addRule(RelativeLayout.ALIGN_PARENT_BOTTOM, RelativeLayout.TRUE);
                layoutParams.setMargins(0, 0, 30, 30);
            }

        }

I hope, this will solve your problem. Thanks.

Solution 7 - Java

First, obtain Google Map View:

 View mapView = ((MapFragment) getFragmentManager().findFragmentById(R.id.map)).getView();

Then find MyLocation button (id's from Android Studio debugger):

 View btnMyLocation = ((View) mapView.findViewById(1).getParent()).findViewById(2);

Finally, just set new RelativeLayout params for MyLocation button (align parent right + center vertically in this case):

RelativeLayout.LayoutParams params = new RelativeLayout.LayoutParams(80,80); // size of button in dp
    params.addRule(RelativeLayout.ALIGN_PARENT_RIGHT, RelativeLayout.TRUE);
    params.addRule(RelativeLayout.CENTER_VERTICAL, RelativeLayout.TRUE);
    params.setMargins(0, 0, 20, 0);
    btnMyLocation.setLayoutParams(params);

Boom! Now you can move it as you want ;)

Solution 8 - Java

See the method below. It lives inside a class that extends SupportMapFragment. It gets the container view for the button and displays it at the bottom, centered horizontally.

/**
	 * Move my position button at the bottom of map
	 */
	private void resetMyPositionButton()
	{
		//deep paths for map controls
		ViewGroup v1 = (ViewGroup)this.getView();
		ViewGroup v2 = (ViewGroup)v1.getChildAt(0);
		ViewGroup v3 = (ViewGroup)v2.getChildAt(0);
		ViewGroup v4 = (ViewGroup)v3.getChildAt(1);
		
		//my position button
		View position =  (View)v4.getChildAt(0);
		
		int positionWidth = position.getLayoutParams().width;
		int positionHeight = position.getLayoutParams().height;
		
		//lay out position button
		RelativeLayout.LayoutParams positionParams = new RelativeLayout.LayoutParams(positionWidth,positionHeight);
		int margin = positionWidth/5;
		positionParams.setMargins(0, 0, 0, margin);
		positionParams.addRule(RelativeLayout.CENTER_HORIZONTAL, RelativeLayout.TRUE);
		positionParams.addRule(RelativeLayout.ALIGN_PARENT_BOTTOM, RelativeLayout.TRUE);
		position.setLayoutParams(positionParams);
	}

Solution 9 - Java

If you just want to have location indication enabled (the blue dot) but don't need default My Location button:

mGoogleMap.setMyLocationEnabled(true);
mGoogleMap.getUiSettings().setMyLocationButtonEnabled(false);

This way you can also draw your own button where you want without strange stuff like this mapView.findViewById(1).getParent()).

Solution 10 - Java

I had the same problem. I ended up using the Hierarchy Viewer to identify the view used to display the button and manipulated it. Very hacky, I know, but could not figure out a different way.

Solution 11 - Java

It was a bit of a struggle to get this working. But I got it done, and in the process also started to move the zoom buttons around. Here my complete code:

package com.squirrel.hkairpollution;

import android.os.Bundle;
import android.util.Log;
import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;
import android.widget.RelativeLayout;

import com.google.android.gms.maps.CameraUpdateFactory;
import com.google.android.gms.maps.SupportMapFragment;
import com.google.android.gms.maps.UiSettings;
import com.google.android.gms.maps.model.LatLng;

public class MySupportMapFragment extends SupportMapFragment {

private static final String TAG = HKAirPollution.TAG;

public MySupportMapFragment() {
	return;
}

@Override
public View onCreateView(LayoutInflater arg0, ViewGroup arg1, Bundle arg2) {
	Log.v(TAG, "In overridden onCreateView.");
    View v = super.onCreateView(arg0, arg1, arg2);
    Log.v(TAG, "Initialising map.");
    initMap();
    return v;
}

@Override
 public void onViewCreated (View view, Bundle savedInstanceState) {
	super.onViewCreated(view, savedInstanceState);
	resetButtons();
}

private void initMap(){
    UiSettings settings = getMap().getUiSettings();
    settings.setAllGesturesEnabled(true);
    settings.setMyLocationButtonEnabled(true);
    LatLng latLong = new LatLng(22.320542, 114.185715);
    getMap().moveCamera(CameraUpdateFactory.newLatLngZoom(latLong,11));
}


/**
 * Move my position button at the bottom of map
 */
private void resetButtons()
{
	// Get a reference to the zoom buttons and the position button.
    ViewGroup v1 = (ViewGroup)this.getView();
    ViewGroup v2 = (ViewGroup)v1.getChildAt(0);
    ViewGroup v3 = (ViewGroup)v2.getChildAt(0);
    ViewGroup v4 = (ViewGroup)v3.getChildAt(1);

    // The My Position button
    View position =  (View)v4.getChildAt(0);
    int positionWidth = position.getLayoutParams().width;
    int positionHeight = position.getLayoutParams().height;

    // Lay out the My Position button.
    RelativeLayout.LayoutParams positionParams = new RelativeLayout.LayoutParams(positionWidth,positionHeight);
    int margin = positionWidth/5;
    positionParams.setMargins(0, 0, 0, margin);
    positionParams.addRule(RelativeLayout.CENTER_HORIZONTAL, RelativeLayout.TRUE);
    positionParams.addRule(RelativeLayout.ALIGN_PARENT_TOP, RelativeLayout.TRUE);
    position.setLayoutParams(positionParams);

    // The Zoom buttons
    View zoom = (View)v4.getChildAt(2);
    int zoomWidth = zoom.getLayoutParams().width;
    int zoomHeight = zoom.getLayoutParams().height;

    // Lay out the Zoom buttons.
    RelativeLayout.LayoutParams zoomParams = new RelativeLayout.LayoutParams(zoomWidth, zoomHeight);
    zoomParams.setMargins(0, 0, 0, margin);
    zoomParams.addRule(RelativeLayout.ALIGN_PARENT_RIGHT, RelativeLayout.TRUE);
    zoomParams.addRule(RelativeLayout.ALIGN_PARENT_TOP, RelativeLayout.TRUE);
    zoom.setLayoutParams(zoomParams);
} 
}

Solution 12 - Java

One way to deal with this problem. Delete default button and create your own. In OnCreate statement add the next:

GoogleMap mMap = ((MapView) inflatedView.findViewById(R.id.mapview)).getMap();
LocationManager locationManager =    
(LocationManager)getActivity().getSystemService(Context.LOCATION_SERVICE);
Criteria criteria = new Criteria();
String provider = locationManager.getBestProvider(criteria, false);
Location location = locationManager.getLastKnownLocation(provider);
locationManager.requestLocationUpdates(provider, 2000, 1,  this);
    
mMap.setMyLocationEnabled(true);
mMap.getUiSettings().setMyLocationButtonEnabled(false); // delete default button
    
Imagebutton imgbtn = (ImageButton) view.findViewById(R.id.imgbutton); //your button
imgbtn.setOnClickListener(new View.OnClickListener() {
        @Override
        public void onClick(View view) {
            mMap.animateCamera(CameraUpdateFactory.newLatLngZoom(new    
LatLng(location.getLatitude(),     
location.getLongitude()), 15));
        }
    });

Solution 13 - Java

try this code

private void resetMyPositionButton()
{
    Fragment fragment = ( (SupportMapFragment) getSupportFragmentManager().findFragmentById( R.id.map ) );
    ViewGroup v1 = (ViewGroup) fragment.getView();
    ViewGroup v2 = (ViewGroup)v1.getChildAt(0);
    ViewGroup v3 = (ViewGroup)v2.getChildAt(2);
    View position =  (View)v3.getChildAt(0);
    int positionWidth = position.getLayoutParams().width;
    int positionHeight = position.getLayoutParams().height;

    //lay out position button
    RelativeLayout.LayoutParams positionParams = new RelativeLayout.LayoutParams(positionWidth,positionHeight);
    int margin = positionWidth/5;
    positionParams.setMargins(margin, 0, 0, margin);
    positionParams.addRule(RelativeLayout.CENTER_VERTICAL, RelativeLayout.TRUE);
    positionParams.addRule(RelativeLayout.ALIGN_PARENT_LEFT, RelativeLayout.TRUE);
    position.setLayoutParams(positionParams);
}

Solution 14 - Java

This button was moved on to the left side of mapBefore, you could remove old rule of button:

@Override
public void onMapReady(final GoogleMap googleMap) {
    this.map = googleMap;
    // Show location button
    View locationButton = ((View) mapView.findViewById(Integer.parseInt("1")).getParent()).findViewById(Integer.parseInt("2"));
    RelativeLayout.LayoutParams rlp = (RelativeLayout.LayoutParams) locationButton.getLayoutParams();
    // position on right bottom
    Log.l(Arrays.toString(rlp.getRules()), L.getLogInfo());
    int[] ruleList = rlp.getRules();
    for (int i = 0; i < ruleList.length; i ++) {
        rlp.removeRule(i);
    }
    Log.l(Arrays.toString(rlp.getRules()), L.getLogInfo());
    //Do what you want to move this location button:
    rlp.addRule(RelativeLayout.CENTER_IN_PARENT, RelativeLayout.TRUE);
    rlp.addRule(RelativeLayout.ALIGN_PARENT_LEFT, RelativeLayout.TRUE);
}

Solution 15 - Java

You can use following approach:

    View myLocationParent = ((View) getView().findViewById(1).getParent());
	View myLocationParentParent = ((View) myLocationParent.getParent());

	// my position button

	int positionWidth = myLocationParent.getLayoutParams().width;
	int positionHeight = myLocationParent.getLayoutParams().height;

	// lay out position button
	FrameLayout.LayoutParams positionParams = new FrameLayout.LayoutParams(
			positionWidth, positionHeight);
	positionParams.setMargins(0, 100, 0, 0);

	myLocationParent.setLayoutParams(positionParams);

Solution 16 - Java

I added a line to my fragment android:layout_marginTop="?attr/actionBarSize" It helped me

Solution 17 - Java

use this one for bottom-right location

map.setMyLocationEnabled(true); 
map.setPadding(0,1600,0,0);

Attributions

All content for this solution is sourced from the original question on Stackoverflow.

The content on this page is licensed under the Attribution-ShareAlike 4.0 International (CC BY-SA 4.0) license.

Content TypeOriginal AuthorOriginal Content on Stackoverflow
QuestionJakobView Question on Stackoverflow
Solution 1 - JavafabLouisView Answer on Stackoverflow
Solution 2 - JavaAscot HarrisView Answer on Stackoverflow
Solution 3 - JavaRyanView Answer on Stackoverflow
Solution 4 - JavaSahil JainView Answer on Stackoverflow
Solution 5 - JavaCord RehnView Answer on Stackoverflow
Solution 6 - JavaPriya JagtapView Answer on Stackoverflow
Solution 7 - JavaRomanView Answer on Stackoverflow
Solution 8 - JavaoviroaView Answer on Stackoverflow
Solution 9 - JavafraggjkeeView Answer on Stackoverflow
Solution 10 - JavaoviroaView Answer on Stackoverflow
Solution 11 - JavaWouterView Answer on Stackoverflow
Solution 12 - JavaDarynView Answer on Stackoverflow
Solution 13 - JavaMetro PolinetView Answer on Stackoverflow
Solution 14 - Javanobjta_9x_tqView Answer on Stackoverflow
Solution 15 - JavaNayanesh GupteView Answer on Stackoverflow
Solution 16 - JavaOlegView Answer on Stackoverflow
Solution 17 - JavaMuazziss NajmiView Answer on Stackoverflow