Home > Android Location using Fused Provider

Android Location using Fused Provider

This Android learning tutorial to explain how to get current location in a android application using a fused location provider. No need GPS or Network location Provider, "Fused Location Provider" automatically chooses the underlying technology and gives the best location as per the need.

In this tutorial we explain how to get current location using fused provider.

Creating Android Project

1. Create a new project in Android Studio from File ? New Project and fill the project details.


2. Open build.gradle add Google Play Services 'com.google.android.gms:play-services:9.4.0' after adding click on Sync Now

									
apply plugin: 'com.android.application' android { compileSdkVersion 25 buildToolsVersion "25.0.2" defaultConfig { applicationId "com.androidlearningtutorials.locationdemo" minSdkVersion 15 targetSdkVersion 25 versionCode 1 versionName "1.0" multiDexEnabled true } android { packagingOptions { exclude 'META-INF/DEPENDENCIES' exclude 'META-INF/NOTICE' exclude 'META-INF/LICENSE' } } buildTypes { release { minifyEnabled false proguardFiles getDefaultProguardFile('proguard-android.txt'), 'proguard-rules.pro' } } } dependencies { compile fileTree(dir: 'libs', include: ['*.jar']) testCompile 'junit:junit:4.12' compile 'com.android.support:appcompat-v7:25.2.0' compile 'com.google.android.gms:play-services:9.4.0' }

3. Add the below permissions to AndroidManifest.xml file.

									
<?xml version="1.0" encoding="utf-8"?> <manifest xmlns:android="http://schemas.android.com/apk/res/android" package="com.androidlearningtutorials.locationdemo"> <!-- location permission --> <uses-permission android:name="android.permission.ACCESS_COARSE_LOCATION" /> <uses-permission android:name="android.permission.ACCESS_FINE_LOCATION" /> <application android:allowBackup="true" android:icon="@mipmap/ic_launcher" android:label="@string/app_name" android:supportsRtl="true" android:theme="@style/AppTheme"> <activity android:name=".MainActivity"> <intent-filter> <action android:name="android.intent.action.MAIN" /> <category android:name="android.intent.category.LAUNCHER" /> </intent-filter> </activity> <meta-data android:name="com.google.android.gms.version" android:value="@integer/google_play_services_version" /> </application> </manifest>

4. Now open activity_main.xml add a textview for showing location like as below.

									
<?xml version="1.0" encoding="utf-8"?> <RelativeLayout 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:padding="20dip"> <TextView android:id="@+id/myLocation" android:layout_width="wrap_content" android:layout_height="wrap_content" android:text="My Location" /> </RelativeLayout>

5. Now open MainActivity.java and add the below code.If you used compileSdkVersion, buildToolsVersion & targetSdkVersion from 23 then implemented runtime permission checking permission.

Read ours tutorial for Marshmallow Runtime Permissions.

								
package com.androidlearningtutorials.locationdemo; import android.*; import android.Manifest; import android.app.Activity; import android.content.DialogInterface; import android.content.Intent; import android.content.IntentSender; import android.content.SharedPreferences; import android.content.pm.PackageManager; import android.location.Location; import android.net.Uri; import android.os.Build; import android.provider.Settings; import android.support.annotation.NonNull; import android.support.v4.app.ActivityCompat; import android.support.v7.app.AlertDialog; import android.support.v7.app.AppCompatActivity; import android.os.Bundle; import android.util.Log; import android.widget.TextView; import android.widget.Toast; import com.google.android.gms.common.ConnectionResult; import com.google.android.gms.common.GooglePlayServicesUtil; import com.google.android.gms.common.api.GoogleApiClient; import com.google.android.gms.common.api.PendingResult; import com.google.android.gms.common.api.ResultCallback; import com.google.android.gms.common.api.Status; import com.google.android.gms.location.LocationListener; import com.google.android.gms.location.LocationRequest; import com.google.android.gms.location.LocationServices; import com.google.android.gms.location.LocationSettingsRequest; import com.google.android.gms.location.LocationSettingsResult; import com.google.android.gms.location.LocationSettingsStatusCodes; import java.text.DateFormat; import java.text.SimpleDateFormat; import java.util.Calendar; public class MainActivity extends AppCompatActivity implements LocationListener, GoogleApiClient.ConnectionCallbacks, GoogleApiClient.OnConnectionFailedListener{ // location LocationRequest mLocationRequest; GoogleApiClient mGoogleApiClient; Location mCurrentLocation; private static final int REQUEST_LOCATION = 10001; private static final String TAG = "LocationDemo"; private static final long INTERVAL = 1000 * 10; private static final long FASTEST_INTERVAL = 1000 * 5; private static int DISPLACEMENT = 10; // marshmallow permission private static final int PERMISSION_CALLBACK_CONSTANT = 100; private static final int REQUEST_PERMISSION_SETTING = 101; String[] permissionsRequired = new String[]{android.Manifest.permission.ACCESS_FINE_LOCATION, Manifest.permission.ACCESS_COARSE_LOCATION}; private SharedPreferences permissionStatus; private boolean sentToSettings = false; //display location variable TextView myLocation; @Override protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); setContentView(R.layout.activity_main); permissionStatus = getSharedPreferences("permissionStatus",MODE_PRIVATE); myLocation = (TextView)findViewById(R.id.myLocation); if(Build.VERSION.SDK_INT >= 23) { if (ActivityCompat.checkSelfPermission(MainActivity.this, permissionsRequired[0]) != PackageManager.PERMISSION_GRANTED || ActivityCompat.checkSelfPermission(MainActivity.this, permissionsRequired[1]) != PackageManager.PERMISSION_GRANTED) { if (ActivityCompat.shouldShowRequestPermissionRationale(MainActivity.this, permissionsRequired[0]) || ActivityCompat.shouldShowRequestPermissionRationale(MainActivity.this, permissionsRequired[1])) { //Show Information about why you need the permission AlertDialog.Builder builder = new AlertDialog.Builder(MainActivity.this); builder.setTitle("Need Location Permissions"); builder.setMessage("This app needs Location permissions."); builder.setPositiveButton("Grant", new DialogInterface.OnClickListener() { @Override public void onClick(DialogInterface dialog, int which) { dialog.cancel(); ActivityCompat.requestPermissions(MainActivity.this, permissionsRequired, PERMISSION_CALLBACK_CONSTANT); } }); builder.setNegativeButton("Cancel", new DialogInterface.OnClickListener() { @Override public void onClick(DialogInterface dialog, int which) { dialog.cancel(); } }); builder.show(); } else if (permissionStatus.getBoolean(permissionsRequired[0], false)) { //Previously Permission Request was cancelled with 'Dont Ask Again', // Redirect to Settings after showing Information about why you need the permission AlertDialog.Builder builder = new AlertDialog.Builder(MainActivity.this); builder.setTitle("Need Location Permissions"); builder.setMessage("This app needs Location permissions"); builder.setPositiveButton("Grant", new DialogInterface.OnClickListener() { @Override public void onClick(DialogInterface dialog, int which) { dialog.cancel(); sentToSettings = true; Intent intent = new Intent(Settings.ACTION_APPLICATION_DETAILS_SETTINGS); Uri uri = Uri.fromParts("package", getPackageName(), null); intent.setData(uri); startActivityForResult(intent, REQUEST_PERMISSION_SETTING); Toast.makeText(getBaseContext(), "Go to Permissions to Grant Location", Toast.LENGTH_LONG).show(); } }); builder.setNegativeButton("Cancel", new DialogInterface.OnClickListener() { @Override public void onClick(DialogInterface dialog, int which) { dialog.cancel(); } }); builder.show(); } else { //just request the permission ActivityCompat.requestPermissions(MainActivity.this, permissionsRequired, PERMISSION_CALLBACK_CONSTANT); } SharedPreferences.Editor editor = permissionStatus.edit(); editor.putBoolean(permissionsRequired[0], true); editor.commit(); } else { //You already have the permission, just go ahead. startLocationFinder(); } }else{ startLocationFinder(); } } private void startLocationFinder(){ // checking google play service if (isGooglePlayServicesAvailable()) { // checking location enable or not enableLoc(); }else{ Toast.makeText(MainActivity.this, "Check google service. Your phone not support latest play store.",Toast.LENGTH_LONG).show(); } } @Override public void onRequestPermissionsResult(int requestCode, @NonNull String[] permissions, @NonNull int[] grantResults) { super.onRequestPermissionsResult(requestCode, permissions, grantResults); if(requestCode == PERMISSION_CALLBACK_CONSTANT){ //check if all permissions are granted boolean allgranted = false; for(int i=0;i<grantResults.length;i++){ if(grantResults[i]==PackageManager.PERMISSION_GRANTED){ allgranted = true; } else { allgranted = false; break; } } if(allgranted){ startLocationFinder(); } else if(ActivityCompat.shouldShowRequestPermissionRationale(MainActivity.this,permissionsRequired[0]) || ActivityCompat.shouldShowRequestPermissionRationale(MainActivity.this,permissionsRequired[1])){ AlertDialog.Builder builder = new AlertDialog.Builder(MainActivity.this); builder.setTitle("Need Location Permissions"); builder.setMessage("This app needs Location permissions."); builder.setPositiveButton("Grant", new DialogInterface.OnClickListener() { @Override public void onClick(DialogInterface dialog, int which) { dialog.cancel(); ActivityCompat.requestPermissions(MainActivity.this,permissionsRequired,PERMISSION_CALLBACK_CONSTANT); } }); builder.setNegativeButton("Cancel", new DialogInterface.OnClickListener() { @Override public void onClick(DialogInterface dialog, int which) { dialog.cancel(); } }); builder.show(); } else { Toast.makeText(getBaseContext(),"Unable to get Permission",Toast.LENGTH_LONG).show(); } } } @Override public void onStart() { super.onStart(); if(mGoogleApiClient != null) { mGoogleApiClient.connect(); } } @Override public void onStop() { super.onStop(); if(mGoogleApiClient != null) { mGoogleApiClient.disconnect(); } } @Override protected void onPostResume() { super.onPostResume(); if (sentToSettings) { if (ActivityCompat.checkSelfPermission(MainActivity.this, permissionsRequired[0]) == PackageManager.PERMISSION_GRANTED) { //Got Permission startLocationFinder(); } } } private boolean isGooglePlayServicesAvailable() { int status = GooglePlayServicesUtil.isGooglePlayServicesAvailable(this); if (ConnectionResult.SUCCESS == status) { return true; } else { GooglePlayServicesUtil.getErrorDialog(status, this, 0).show(); return false; } } @Override public void onConnected(Bundle bundle) { if(mGoogleApiClient.isConnected()){ startLocationUpdates(); } } protected void startLocationUpdates() { if (ActivityCompat.checkSelfPermission(this, android.Manifest.permission.ACCESS_FINE_LOCATION) != PackageManager.PERMISSION_GRANTED && ActivityCompat.checkSelfPermission(this, android.Manifest.permission.ACCESS_COARSE_LOCATION) != PackageManager.PERMISSION_GRANTED) { // TODO: Consider calling return; } try{ PendingResult<Status> pendingResult = LocationServices.FusedLocationApi.requestLocationUpdates(mGoogleApiClient, mLocationRequest, this); }catch (Exception ev){ System.out.print(ev.getMessage()); } } @Override public void onConnectionSuspended(int i) { } @Override public void onConnectionFailed(ConnectionResult connectionResult) { Log.d(TAG, "Connection failed: " + connectionResult.toString()); } @Override public void onLocationChanged(Location location) { Log.d(TAG, "Firing onLocationChanged.............................................."); mCurrentLocation = location; String mlocation = "Latitude: " + mCurrentLocation.getLatitude() + "\n" + "Longitude: " + mCurrentLocation.getLongitude() + "\n" + "Timestamp: " + getDate(mCurrentLocation.getTime(),"dd:MM:yy HH:mm:ss") ; myLocation.setText(mlocation); } private String getDate(long milliSeconds, String dateFormat) { // Create a DateFormatter object for displaying date in specified format. DateFormat formatter = new SimpleDateFormat(dateFormat); // Create a calendar object that will convert the date and time value in milliseconds to date. Calendar calendar = Calendar.getInstance(); calendar.setTimeInMillis(milliSeconds); return formatter.format(calendar.getTime()); } private void enableLoc() { mGoogleApiClient = new GoogleApiClient.Builder(MainActivity.this) .addApi(LocationServices.API) .addConnectionCallbacks(MainActivity.this) .addOnConnectionFailedListener(new GoogleApiClient.OnConnectionFailedListener() { @Override public void onConnectionFailed(ConnectionResult connectionResult) { Log.d(TAG, "Location error: " + connectionResult.getErrorCode()); } }).build(); mGoogleApiClient.connect(); mLocationRequest = new LocationRequest(); mLocationRequest.setInterval(INTERVAL); mLocationRequest.setFastestInterval(FASTEST_INTERVAL); mLocationRequest.setPriority(LocationRequest.PRIORITY_HIGH_ACCURACY); mLocationRequest.setSmallestDisplacement(DISPLACEMENT); LocationSettingsRequest.Builder builder = new LocationSettingsRequest.Builder() .addLocationRequest(mLocationRequest); builder.setAlwaysShow(true); PendingResult<LocationSettingsResult> result = LocationServices.SettingsApi.checkLocationSettings(mGoogleApiClient, builder.build()); result.setResultCallback(new ResultCallback() { @Override public void onResult(LocationSettingsResult result) { final Status status = result.getStatus(); switch (status.getStatusCode()) { case LocationSettingsStatusCodes.RESOLUTION_REQUIRED: try { // Show the dialog by calling startResolutionForResult(), // and check the result in onActivityResult(). status.startResolutionForResult(MainActivity.this, REQUEST_LOCATION); } catch (IntentSender.SendIntentException e) { // Ignore the error. } break; } } }); } @Override public void onActivityResult(int requestCode, int resultCode, Intent data) { super.onActivityResult(requestCode, resultCode, data); //check location permission granted or not if (requestCode == REQUEST_PERMISSION_SETTING) { if (ActivityCompat.checkSelfPermission(MainActivity.this, permissionsRequired[0]) == PackageManager.PERMISSION_GRANTED) { //Got Permission startLocationFinder(); } } // check location enable granted or not status if (requestCode == REQUEST_LOCATION) { switch (resultCode) { case Activity.RESULT_OK: Toast.makeText(getApplicationContext(),"Accept",Toast.LENGTH_LONG).show(); break; case Activity.RESULT_CANCELED: Toast.makeText(getApplicationContext(),"Cancel", Toast.LENGTH_LONG).show(); finish(); break; } } } }

5. Output as below.

  • Location Permission
  • Location enable
  • Current location

Dheerendra Singh

Dheerendra Singh is a Mobile Developer(Android) & Web Developer(PHP) of Amisun IT Solutions, Master degree in Computer Science.


About Us

Amisun IT Solutions is an expert Software Development Company giving complete IT arrangements and going about as a seaward improvement community for abroad advancement firms.

We are an imaginative organization, situated in India that gives a progression of Web-based programming applications that have helped clients make fruitful online activities.

Our group of forward masterminds and reforming individuals tries to furnish you with the best of arrangements with flawlessness second to none. Our key concentration is dependably to furnish you with solid arrangements which are precisely planned and planned with stringent quality principles. ...   

Read more

Address

Shoppers Square Mall Shop No. 17 & 18, First Floor,
Shoppers Square Mall, Budhh Prakash Garg Marg, Block 14, Sector 10,
Raj Nagar, Ghaziabad, Uttar Pradesh 201002
P: (+91) 9899776200, (+91) 9899773200