The onMapReady function is never called. It needs to be triggered for proper initializating of my GoogleMap.
public class MainActivity extends AppCompatActivity {
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.main_activity);
}
}
Should I inherit MapFragment instead of Fragment? Because I get another Error when I do: it returns a NullPointerException in MainActivity
import android.os.Bundle;
import android.support.v4.app.Fragment;
import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;
import com.google.android.gms.maps.GoogleMap;
import com.google.android.gms.maps.OnMapReadyCallback;
public class MapsFragment extends Fragment implements OnMapReadyCallback {
private GoogleMap mMap;
#Override
public View onCreateView(LayoutInflater inflater, ViewGroup container,
Bundle savedInstanceState) {
return inflater.inflate(R.layout.activity_maps, container, false);
}
#Override
public void onMapReady(GoogleMap googleMap) {
mMap = googleMap;
}
}
main_activity.xml
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:orientation="vertical" android:layout_width="match_parent"
android:layout_height="match_parent">
<fragment android:name=".fragment.MapsFragment"
android:id="#+id/maps_fragment"
android:layout_width="match_parent"
android:layout_height="match_parent">
</fragment>
</LinearLayout>
activity_maps.xml
<fragment xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools"
android:id="#+id/map"
android:name="com.google.android.gms.maps.SupportMapFragment"
android:layout_width="match_parent"
android:layout_height="match_parent"
tools:context=".fragment.MapsFragment" />
Many thanks guys!
Update 1:
Added this to MapsActivity, but now MainActivity returns android.view.InflateException: Binary XML file line #6: Error inflating class fragment
#Override
public void onViewCreated(View view, #Nullable Bundle savedInstanceState) {
super.onViewCreated(view, savedInstanceState);
SupportMapFragment supportMapFragment = (SupportMapFragment) getChildFragmentManager().findFragmentById(R.id.map);
supportMapFragment.getMapAsync(this);
}
Try This
public class MapsFragment extends Fragment implements OnMapReadyCallback {
private GoogleMap mMap;
#Override
public View onCreateView(LayoutInflater inflater, ViewGroup container,
Bundle savedInstanceState) {
View mView = inflater.inflate(R.layout.activity_maps, container, false);
SupportMapFragment mapFragment = ((SupportMapFragment) getChildFragmentManager().findFragmentById(R.id.map));
mapFragment.getMapAsync(this);
return mView ;
}
#Override
public void onMapReady(GoogleMap googleMap) {
mMap = googleMap;
}
}
Your MapsFragment should request getMapAsync to load map then only onMapReady will be called.
public class MapsFragment extends Fragment implements OnMapReadyCallback
{
private View fragmentView;
private GoogleMap mMap;
#Nullable
#Override
public View onCreateView(LayoutInflater inflater, #Nullable ViewGroup container, #Nullable Bundle savedInstanceState)
{
fragmentView = inflater.inflate(R.layout.activity_maps, container, false);
return fragmentView;
}
#Override
public void onActivityCreated(#Nullable Bundle savedInstanceState)
{
super.onActivityCreated(savedInstanceState);
SupportMapFragment mapFragment = (SupportMapFragment) getActivity().getSupportFragmentManager().findFragmentById(R.id.map);
mapFragment.getMapAsync(this);
}
#Override
public void onMapReady(GoogleMap googleMap)
{
mMap = googleMap;
}
}
here is the correct, workings solution:
MapsFragment
import com.google.android.gms.maps.GoogleMap;
import com.google.android.gms.maps.OnMapReadyCallback;
import com.google.android.gms.maps.SupportMapFragment;
public class MapsFragment extends SupportMapFragment {
private GoogleMap mapView;
private void initGoogleMap() {
getMapAsync(new OnMapReadyCallback() {
#Override
public void onMapReady(GoogleMap googleMap) {
mapView = googleMap;
}
});
}
#Override
public void onActivityCreated(Bundle savedInstanceState) {
super.onActivityCreated(savedInstanceState);
initGoogleMap();
}
}
MainActivity
public class MainActivity extends AppCompatActivity {
private MapsFragment mapsFragment;
private void initializeMapsFragment() {
FragmentTransaction mTransaction = getSupportFragmentManager().beginTransaction();
mapsFragment = new MapsFragment();
SupportMapFragment supportMapFragment = mapsFragment;
mTransaction.add(R.id.google_maps_frame, supportMapFragment);
mTransaction.commit();
}
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.main_activity);
initializeMapsFragment();
}
}
main_activity.xml, removed maps_activity.xml
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:orientation="vertical" android:layout_width="match_parent"
android:layout_height="match_parent">
<FrameLayout
android:id="#+id/google_maps_frame"
android:layout_width="fill_parent"
android:layout_height="fill_parent"
android:layout_marginBottom="-8dp"
android:layout_weight="0.2" >
</FrameLayout>
</LinearLayout>
Related
I have a problem integrating google map in fragment in android. I know how to do it in activity but fragment reference on this site are very old and not working in 2018. I don't have any error.below is fragment file. Any help will be highly appreciated. I have added API key and proper manifest file.
package com.example.narmail.truck30mint.Api.Fragments;
import android.Manifest;
import android.content.Context;
import android.content.DialogInterface;
import android.content.pm.PackageManager;
import android.net.Uri;
import android.os.Bundle;
import android.support.annotation.NonNull;
import android.support.v4.app.ActivityCompat;
import android.support.v4.app.Fragment;
import android.support.v4.content.ContextCompat;
import android.support.v7.app.AlertDialog;
import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;
import android.widget.TextView;
import com.example.narmail.truck30mint.R;
import com.google.android.gms.maps.CameraUpdateFactory;
import com.google.android.gms.maps.GoogleMap;
import com.google.android.gms.maps.MapView;
import com.google.android.gms.maps.MapsInitializer;
import com.google.android.gms.maps.OnMapReadyCallback;
import com.google.android.gms.maps.model.CameraPosition;
import com.google.android.gms.maps.model.LatLng;
import com.google.android.gms.maps.model.MarkerOptions;
import java.util.ArrayList;
public class ViewTrucksFragment extends Fragment {
TextView pageTitle;
MapView mMapView;
private GoogleMap googleMap;
public ViewTrucksFragment() {
// Required empty public constructor
}
#Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
}
#Override
public View onCreateView(LayoutInflater inflater, ViewGroup container,
Bundle savedInstanceState) {
// Inflate the layout for this fragment
View rootView = inflater.inflate(R.layout.fragment_view_trucks, container, false);
pageTitle = rootView.findViewById(R.id.view_trucks_title);
String load_id = getArguments().getString("load_id");
String load_from = getArguments().getString("load_from");
String load_to = getArguments().getString("load_to");
if (load_id != null && load_from != null && load_to != null) {
pageTitle.setText("Matching Trucks for "+load_from+" to "+load_to);
}
mMapView= rootView.findViewById(R.id.view_trucks_map);
mMapView.onCreate(savedInstanceState);
mMapView.onResume();
try {
MapsInitializer.initialize(getActivity().getApplicationContext());
} catch (Exception e) {
e.printStackTrace();
}
mMapView.getMapAsync(new OnMapReadyCallback() {
#Override
public void onMapReady(GoogleMap mMap) {
googleMap = mMap;
googleMap.getUiSettings().setCompassEnabled(true);
googleMap.getUiSettings().setMyLocationButtonEnabled(true);
googleMap.getUiSettings().setRotateGesturesEnabled(true);
// For dropping a marker at a point on the Map
LatLng sydney = new LatLng(30.374219,76.782055);
googleMap.addMarker(new MarkerOptions().position(sydney).
title("Title").snippet("TitleName"));
// For zooming automatically to the location of the marker
CameraPosition cameraPosition = new CameraPosition.Builder().target(sydney).zoom(12).build();
googleMap.animateCamera(CameraUpdateFactory.newCameraPosition
(cameraPosition ));
}
});
/*----------------*/
return rootView;
}
}
and below is my layout file
<?xml version="1.0" encoding="utf-8"?>
<FrameLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:background="#color/colorWhite"
tools:context=".Api.Fragments.ViewTrucksFragment">
<LinearLayout
android:orientation="vertical"
android:layout_width="match_parent"
android:layout_height="match_parent">
<TextView
android:id="#+id/view_trucks_title"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:textAlignment="center"
android:layout_marginRight="10dp"
android:layout_marginLeft="10dp"
android:padding="10dp"
android:textColor="#color/colorPrimary"
android:textSize="15sp"
android:text="#string/hello_blank_fragment" />
<com.google.android.gms.maps.MapView
android:id="#+id/view_trucks_map"
android:layout_width="match_parent"
android:layout_height="match_parent">
</com.google.android.gms.maps.MapView>
</LinearLayout>
</FrameLayout>
Please follow below step to finish your task. Just need to create 3 files
(1) Create XML layout for map inside your fragment layout fragment_map.xml
<?xml version="1.0" encoding="utf-8"?>
<fragment xmlns:android="http://schemas.android.com/apk/res/android"
android:id="#+id/map"
android:name="com.google.android.gms.maps.SupportMapFragment"
android:layout_width="match_parent"
android:layout_height="match_parent" />
(2) Create Fragment to load MAP MapFragment.Java
public class MapFragment extends Fragment implements OnMapReadyCallback {
private GoogleMap mMap;
public MapFragment() {
// Required empty public constructor
}
#Override
public View onCreateView(LayoutInflater inflater, ViewGroup container,
Bundle savedInstanceState) {
// Inflate the layout for this fragment
return inflater.inflate(R.layout.fragment_map, container, false);
}
#Override
public void onActivityCreated(#Nullable Bundle savedInstanceState) {
super.onActivityCreated(savedInstanceState);
// Obtain the SupportMapFragment and get notified when the map is ready to be used.
if(getActivity()!=null) {
SupportMapFragment mapFragment = (SupportMapFragment) getActivity().getSupportFragmentManager()
.findFragmentById(R.id.map);
if (mapFragment != null) {
mapFragment.getMapAsync(this);
}
}
}
#Override
public void onMapReady(GoogleMap googleMap) {
mMap = googleMap;
//Do your stuff here
}
}
(3) Create Activity to load MAP fragment MapsActivity.java
public class MapsActivity extends FragmentActivity {
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_maps);
FragmentManager fragmentManager = getSupportFragmentManager();
FragmentTransaction fragmentTransaction = fragmentManager.beginTransaction();
fragmentTransaction.add(R.id.content,new MapFragment());
fragmentTransaction.commit();
}
}
For MAP key you need to follow same step you have done in your project. Hope this step will help you.
Inside Gradle please use below gradle
implementation 'com.google.android.gms:play-services-maps:15.0.1'
AndroidManifest.xml define below things.
<uses-permission android:name="android.permission.INTERNET"/>
Inside Application Tag.
<meta-data
android:name="com.google.android.geo.API_KEY"
android:value="YOUR MAP KEY" />
This question already has an answer here:
How to get current location within a Google Maps Fragment in a ViewPager with TabLayout
(1 answer)
Closed 5 years ago.
Hi i am new here and hope to find help...
i found a message "warning 1st argument found type MapActivity required android.support.v4.app.Fragment" I want to MapActivity as a Fragment because i want to add Map in View Pager. I am using View Pager and also View Pager Adapter and in View Pager Adapter i am using two Array List for Fragments and TabTitles
Here is the code of ViewPagerAdapter
public class ViewPagerAdapter extends FragmentPagerAdapter {
ArrayList<Fragment> fragments = new ArrayList<>();
ArrayList<String> tabTitles = new ArrayList<>();
public void addFragments(Fragment fragments, String titles)
{
this.fragments.add(fragments);
this.tabTitles.add(titles);
}
public ViewPagerAdapter(FragmentManager fm)
{
super(fm);
}
#Override
public Fragment getItem(int position) {
return fragments.get(position);
}
#Override
public int getCount() {
return tabTitles.size();
}
#Override
public CharSequence getPageTitle(int position) {
return tabTitles.get(position);
}
}
and here is code of MainActivity.java
public class MainActivity extends AppCompatActivity {
Toolbar toolbar;
TabLayout tabLayout;
ViewPager viewPager;
ViewPagerAdapter viewPagerAdapter;
/**
* ATTENTION: This was auto-generated to implement the App Indexing API.
* See https://g.co/AppIndexing/AndroidStudio for more information.
*/
private GoogleApiClient client;
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
toolbar = (Toolbar) findViewById(R.id.toolBar);
setSupportActionBar(toolbar);
tabLayout = (TabLayout) findViewById(R.id.tabLayout);
viewPager = (ViewPager) findViewById(R.id.viewPager);
viewPagerAdapter = new ViewPagerAdapter(getSupportFragmentManager());
viewPagerAdapter.addFragments(new HomeFragment(), "Home");
viewPagerAdapter.addFragments(new SearchFragment(), "Search");
// viewPagerAdapter.addFragments(new MapFragment(),"Map");
viewPagerAdapter.addFragments(new MapsActivity(), "Map");
viewPager.setAdapter(viewPagerAdapter);
tabLayout.setupWithViewPager(viewPager);
client = new GoogleApiClient.Builder(this).addApi(AppIndex.API).build();
}
/**
* ATTENTION: This was auto-generated to implement the App Indexing API.
* See https://g.co/AppIndexing/AndroidStudio for more information.
*/
public Action getIndexApiAction() {
Thing object = new Thing.Builder()
.setName("Main Page") // TODO: Define a title for the content shown.
// TODO: Make sure this auto-generated URL is correct.
.setUrl(Uri.parse("http://[ENTER-YOUR-URL-HERE]"))
.build();
return new Action.Builder(Action.TYPE_VIEW)
.setObject(object)
.setActionStatus(Action.STATUS_TYPE_COMPLETED)
.build();
}
#Override
public void onStart() {
super.onStart();
client.connect();
AppIndex.AppIndexApi.start(client, getIndexApiAction());
}
#Override
public void onStop() {
super.onStop();
AppIndex.AppIndexApi.end(client, getIndexApiAction());
client.disconnect();
}
}
in activity_main.xml
<?xml version="1.0" encoding="utf-8"?>
<RelativeLayout
xmlns:app="http://schemas.android.com/apk/res-auto"
xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools"
android:id="#+id/activity_main"
android:layout_width="match_parent"
android:layout_height="match_parent"
tools:context="com.example.lilla.tabdemo.MainActivity">
<android.support.design.widget.AppBarLayout
android:layout_width="match_parent"
android:layout_height="wrap_content"
>
<include
android:layout_height="wrap_content"
android:layout_width="match_parent"
layout="#layout/toolbar_layout"
/>
<android.support.design.widget.TabLayout
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:id="#+id/tabLayout"
app:tabMode="fixed"
app:tabGravity="fill"
>
</android.support.design.widget.TabLayout>
</android.support.design.widget.AppBarLayout>
<android.support.v4.view.ViewPager
android:layout_width="match_parent"
android:layout_height="match_parent"
android:id="#+id/viewPager"
>
</android.support.v4.view.ViewPager>
</RelativeLayout>
Please help me Thanks....
MapsActivity.java
package com.example.lilla.tabdemo;
import android.support.v4.app.FragmentActivity;
import android.os.Bundle;
import com.google.android.gms.maps.CameraUpdateFactory;
import com.google.android.gms.maps.GoogleMap;
import com.google.android.gms.maps.OnMapReadyCallback;
import com.google.android.gms.maps.SupportMapFragment;
import com.google.android.gms.maps.model.LatLng;
import com.google.android.gms.maps.model.MarkerOptions;
public class MapsActivity extends FragmentActivity implements
OnMapReadyCallback {
private GoogleMap mMap;
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_maps);
SupportMapFragment mapFragment = (SupportMapFragment)
getSupportFragmentManager()
.findFragmentById(R.id.map);
mapFragment.getMapAsync(this);
}
#Override
public void onMapReady(GoogleMap googleMap) {
mMap = googleMap;
// Add a marker in Sydney and move the camera
LatLng sydney = new LatLng(-34, 151);
mMap.addMarker(new MarkerOptions().position(sydney).title("Marker"));
mMap.moveCamera(CameraUpdateFactory.newLatLng(sydney));
}
}
Your MapsActivity class must extend Fragment class and the Fragment class must be imported from the
android.support.v4.app.Fragment package.
Try this class:
public class MapsActivity extends Fragment implements
OnMapReadyCallback {
private GoogleMap mMap;
private MapView mMapView;
#Override
public View onCreateView(LayoutInflater inflater, ViewGroup container,
Bundle savedInstanceState) {
View v = inflater.inflate(R.layout.activity_maps, container, false);
getActivity().setTitle("Map");
mMapView = (MapView) v.findViewById(R.id.map);
mMapView.onCreate(savedInstanceState);
mMapView.getMapAsync(this); //this is important
return v;
}
#Override
public void onResume() {
super.onResume();
mMapView.onResume();
}
#Override
public void onPause() {
super.onPause();
mMapView.onPause();
}
#Override
public void onDestroy() {
super.onDestroy();
mMapView.onDestroy();
}
#Override
public void onSaveInstanceState(Bundle outState) {
super.onSaveInstanceState(outState);
mMapView.onSaveInstanceState(outState);
}
#Override
public void onLowMemory() {
super.onLowMemory();
mMapView.onLowMemory();
}
#Override
public void onMapReady(GoogleMap googleMap) {
mMap = googleMap;
// Add a marker in Sydney and move the camera
LatLng sydney = new LatLng(-34, 151);
mMap.addMarker(new MarkerOptions().position(sydney).title("Marker"));
mMap.moveCamera(CameraUpdateFactory.newLatLng(sydney));
}
}
I have a map offline mapBox, but the map does not load because it is null. I followed the directions of the site: https://www.mapbox.com/android-sdk/
In layout
<com.mapbox.mapboxsdk.views.MapView
android:id="#+id/mapView"
android:layout_width="fill_parent"
android:layout_height="400dp"
android:layout_marginTop="30dp"
android:layout_marginLeft="50dp"
android:layout_marginRight="50dp"
mapbox:access_token="#string/access_token"
/>
In Fragment:
import com.mapbox.mapboxsdk.MapFragment;
........
public class ConctactsFragment extends MapFragment {
.........
#Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setRetainInstance(true);
}
#Nullable
#Override
public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) {
getActivity();
mRootView = inflater.inflate(R.layout.fragment_map, container, false);
mMapView =(MapView)mRootView.findViewById(R.id.mapView);
XmlPullParser parser=getResources().getXml(R.xml.attrs);
AttributeSet attrs = Xml.asAttributeSet(parser);
mMapView = new MapView(mContext, attrs);
Log.d(TAG, "The mapView in onCreateView: " + this.getMap());
//The mapView in onCreateView: null
mMapView.setStyleUrl(Style.MAPBOX_STREETS);
mMapView.setCenterCoordinate(new LatLng(40.956645, 14.304816));
mMapView.setZoomLevel(11);
return mRootView;
}
#Override
public void onStart() {
Log.d(TAG, "The mapView in OnStart: " +this.getMap());
// The mapView in OnStart: null
super.onStart();
mMapView.onStart();
}
}
The error is:
java.lang.NullPointerException
at com.mapbox.mapboxsdk.MapFragment.onStart(MapFragment.java:70)
Why are you extending MapFragment and defining your own layout? Anyway this looks like there is no R.id.mapView in your R.layout.fragment_map. Can't really say more without the full layouts and fragment loading logic.
Here is some code that works (using mapbox SDK 2.2, Android SDK 23):
MainActivity class:
import android.app.Activity;
import android.os.Bundle;
public class MainActivity extends Activity {
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
}
#Override
protected void onStart() {
super.onStart();
// Load the fragment dynamically
getFragmentManager()
.beginTransaction()
.add(R.id.fragment_container_layout, MyMapFragment.create())
.commit();
}
}
Custom Fragment:
import android.app.Fragment;
import android.os.Bundle;
import android.support.annotation.Nullable;
import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;
import com.mapbox.mapboxsdk.constants.Style;
import com.mapbox.mapboxsdk.geometry.LatLng;
import com.mapbox.mapboxsdk.views.MapView;
public class MyMapFragment extends Fragment {
private MapView mMapView;
public static MyMapFragment create() {
return new MyMapFragment();
}
#Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
}
#Nullable
#Override
public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) {
View rootView = inflater.inflate(R.layout.my_map_fragment, container, false);
mMapView = (MapView) rootView.findViewById(R.id.mb_map_view);
mMapView.setStyleUrl(Style.MAPBOX_STREETS);
mMapView.setCenterCoordinate(new LatLng(40.956645, 14.304816));
mMapView.setZoomLevel(11);
mMapView.onCreate(savedInstanceState); // If this line is omitted there is a native crash in the MapBox library
return rootView;
}
#Override
public void onStart() {
super.onStart();
mMapView.onStart();
}
#Override
public void onResume() {
super.onResume();
mMapView.onResume();
}
#Override
public void onSaveInstanceState(Bundle outState) {
super.onSaveInstanceState(outState);
mMapView.onSaveInstanceState(outState);
}
#Override
public void onPause() {
super.onPause();
mMapView.onPause();
}
#Override
public void onStop() {
super.onStop();
mMapView.onStop();
}
#Override
public void onDestroy() {
super.onDestroy();
mMapView.onDestroy();
}
}
activity_main.xml (layout for main activity):
<?xml version="1.0" encoding="utf-8"?>
<FrameLayout
xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools"
android:layout_width="match_parent"
android:layout_height="match_parent"
tools:context=".MainActivity">
<FrameLayout
android:id="#+id/fragment_container_layout"
android:layout_width="match_parent"
android:layout_height="match_parent"/>
</FrameLayout>
my_map_fragment.xml (layout for custom map fragment):
<?xml version="1.0" encoding="utf-8"?>
<FrameLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:custom="http://schemas.android.com/apk/res-auto"
android:layout_width="match_parent"
android:layout_height="match_parent">
<com.mapbox.mapboxsdk.views.MapView
android:id="#+id/mb_map_view"
android:layout_width="match_parent"
android:layout_height="match_parent"
custom:access_token="#string/mb_token"/>
</FrameLayout>
I received a null pointer exception when getting android google maps in a fragment. The error is at the line findFragmentById.I tried using
if (mMap != null) and it indicates that the map is still null. What can I do to resolve this?
In MapActivity.java,
//Relevant imports
import com.google.android.gms.maps.MapFragment;
import com.google.android.gms.maps.CameraUpdateFactory;
import com.google.android.gms.maps.GoogleMap;
import com.google.android.gms.maps.SupportMapFragment;
import android.support.v4.app.Fragment;
import android.support.v4.app.FragmentManager;
import android.os.Bundle;
import android.support.v4.app.Fragment;
import android.view.LayoutInflater;
import android.view.MenuItem;
import android.view.View;
import android.view.ViewGroup;
enter code here
public class MapView extends Fragment {
GoogleMap mMap;
LatLng mLocation = new LatLng(1.379348, 103.849876);
#Override
public View onCreateView(LayoutInflater inflater, ViewGroup container,
Bundle savedInstanceState) {
View rootView = inflater.inflate(R.layout.map_view, container, false);
mMap = ((SupportMapFragment) getFragmentManager().findFragmentById(R.id.map)).getMap();
mMap.setMapType(GoogleMap.MAP_TYPE_HYBRID);
//Zoom
mMap.getUiSettings().setZoomControlsEnabled(true);
mMap.moveCamera(CameraUpdateFactory.newLatLngZoom(mLocation, 17));
Marker mMarker = mMap.addMarker(new MarkerOptions()
.position(mLocation)
.title("School")
.snippet("NTU")
.icon(BitmapDescriptorFactory.fromResource(R.drawable.ic_launcher)));
mMap.setOnMarkerClickListener(new OnMarkerClickListener()
{
public boolean onMarkerClick(Marker marker){
Toast.makeText(getActivity().getApplicationContext(), "Welcome to " + marker.getTitle(), Toast.LENGTH_LONG);
return false;
}
});
mMap.setOnInfoWindowClickListener(new OnInfoWindowClickListener(){
#Override
public void onInfoWindowClick(Marker arg0) {
// TODO Auto-generated method stub
}
});
return rootView;
}
}
In map_view.xml,
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools"
android:layout_width="fill_parent"
android:layout_height="fill_parent" >
<fragment
android:id="#+id/map"
android:name="com.google.android.gms.maps.MapFragment"
android:layout_width="fill_parent"
android:layout_height="fill_parent" />
</RelativeLayout>
In order to have a SupportMapFragment nested inside a Fragment, you need to use getChildFragmentManager() instead of getFragmentManager().
So, you would change this:
mMap = ((SupportMapFragment) getFragmentManager().findFragmentById(R.id.map)).getMap();
To this, and also move all of the code referencing mMap to onResume():
mMap = ((SupportMapFragment) getChildFragmentManager().findFragmentById(R.id.map)).getMap();
If you go this route you will also need to fix your layout xml to use a SupportMapFragment:
<fragment
android:id="#+id/map"
class="com.google.android.gms.maps.SupportMapFragment"
android:layout_width="match_parent"
android:layout_height="match_parent"/>
However, it would be best to not have nested Fragments if you don't need to, since it can lead to other problems.
A better approach is just to make the Fragment extend SupportMapFragment. Doing it this way, you don't even need a layout xml file.
Example:
public class MapView extends SupportMapFragment
implements OnMapReadyCallback {
private GoogleMap mMap;
private Marker marker;
public MapView() {
}
#Override
public void onResume() {
super.onResume();
setUpMapIfNeeded();
}
private void setUpMapIfNeeded() {
if (mMap == null) {
getMapAsync(this);
}
}
#Override
public void onMapReady(GoogleMap googleMap) {
mMap = googleMap;
setUpMap();
}
private void setUpMap() {
mMap.setMyLocationEnabled(true);
mMap.setMapType(GoogleMap.MAP_TYPE_HYBRID);
mMap.getUiSettings().setMapToolbarEnabled(false);
}
}
Can you please try this way ?
<com.google.android.gms.maps.MapView
android:id="#+id/mapView"
android:layout_width="match_parent"
android:layout_height="match_parent" />
Activity or Fragment:
private GoogleMap mMap;
private MapView mapView;
on onCreate():
#Override
public View onCreateView(LayoutInflater inflater, ViewGroup container,Bundle savedInstanceState) {
View rootView = inflater.inflate(R.layout.fragment_map,container, false)
initializaMap(rootView, savedInstanceState);
return rootView;
}
on onResume()
#Override
public void onResume() {
if(mapView!=null){
mapView.onResume();
}
super.onResume();
}
on onDestroy()
#Override
public void onDestroy() {
if(mapView!=null){
mapView.onDestroy();
}
super.onDestroy();
}
on onLowMemory()
#Override
public void onLowMemory() {
if(mapView!=null){
mapView.onLowMemory();
}
super.onLowMemory();
}
Add new method:
private void initializaMap(View rootView, Bundle savedInstanceState){
MapsInitializer.initialize(getActivity());
switch (GooglePlayServicesUtil.isGooglePlayServicesAvailable(getActivity())) {
case ConnectionResult.SUCCESS:
mapView = (MapView) rootView.findViewById(R.id.mapView);
mapView.onCreate(savedInstanceState);
if (mapView != null) {
mMap = mapView.getMap();
mMap.setMapType(GoogleMap.MAP_TYPE_NORMAL);
UiSettings mUiSettings = mMap.getUiSettings();
mMap.setMyLocationEnabled(true);
mMap.animateCamera(CameraUpdateFactory.zoomTo(zoomLevel));
mUiSettings.setCompassEnabled(true);
mUiSettings.setMyLocationButtonEnabled(false);
mMap.setOnMarkerClickListener(this);
}
break;
case ConnectionResult.SERVICE_MISSING:
break;
case ConnectionResult.SERVICE_VERSION_UPDATE_REQUIRED:
break;
default:
}
}
Hope this will help you.
Mapview.getmap going back empty under 19 version of Android ! MapView getMap() returns null on Lollipop. Version 22 also does not have a problem. Map opens and we can add markers. Why invoke the GetMap method returns null in the old version?
public class AnaActivity extends ActionBarActivity {
public static FragmentManager mFragmenManager;
protected void onCreate(Bundle savedInstanceState) {
setContentView(R.layout.activity_main);
..
mFragmenManager = getSupportFragmentManager();
}
...
}
activity_main.xml
<?xml version="1.0" encoding="utf-8"?>
<android.support.v4.view.ViewPager
xmlns:android="http://schemas.android.com/apk/res/android"
android:id="#+id/pager"
android:layout_width="match_parent"
android:layout_height="match_parent"
class="com.google.android.gms.maps.SupportMapFragment"
/>
HaritaFragment.java
public class HaritaFragment extends Fragment {
GoogleMap mMap;
MapView mMapView;
#Override
public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) {
View rootView = inflater.inflate(R.layout.map_activity, container, false);
mMapView = (MapView) rootView.findViewById(R.id.mapView);
mMapView.onCreate(savedInstanceState);
mMapView.onResume();
try {
MapsInitializer.initialize(getActivity().getApplicationContext());
} catch (Exception e) {
hataGoster(e.getMessage());
}
mMap = mMapView.getMap(); // **** return null on LOLLIPOPS Version
}
}
map_activity.xml
<?xml version="1.0" encoding="utf-8"?>
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:map="http://schemas.android.com/tools"
android:layout_width="fill_parent"
android:layout_height="fill_parent">
<com.google.android.gms.maps.MapView
android:id="#+id/mapView"
class="com.google.android.gms.maps.SupportMapFragment"
android:layout_width="fill_parent"
android:layout_height="fill_parent" />
</RelativeLayout>
Try this:
MapsActivity.java
import android.support.v4.app.FragmentActivity;
import android.os.Bundle;
import com.google.android.gms.maps.GoogleMap;
import com.google.android.gms.maps.MapFragment;
import com.google.android.gms.maps.OnMapReadyCallback;
import com.google.android.gms.maps.model.LatLng;
import com.google.android.gms.maps.model.MarkerOptions;
public class MapsActivity extends FragmentActivity {
private GoogleMap mMap; // Might be null if Google Play services APK is not available.
private MapFragment mapFragment;
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_maps);
setUpMapIfNeeded();
}
#Override
protected void onResume() {
super.onResume();
setUpMapIfNeeded();
}
private void setUpMapIfNeeded() {
mapFragment = ((MapFragment) getFragmentManager().findFragmentById(R.id.map));
mapFragment.getMapAsync(new OnMapReadyCallback() {
#Override
public void onMapReady(GoogleMap googleMap) {
mMap = googleMap;
setUpMap();
}
});
}
private void setUpMap() {
mMap.setMyLocationEnabled(true);
mMap.addMarker(new MarkerOptions().position(new LatLng(0, 0)).title("Marker"));
}
}
Layout:
<fragment xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools" android:layout_width="match_parent"
android:layout_height="match_parent" android:id="#+id/map" tools:context=".MapsActivity"
android:name="com.google.android.gms.maps.MapFragment" />