Add buttons for removing statuses/locations in sharing tab #122
@ -53,12 +53,17 @@
|
|||||||
android:name=".activity.SettingsActivity"
|
android:name=".activity.SettingsActivity"
|
||||||
android:screenOrientation="portrait"
|
android:screenOrientation="portrait"
|
||||||
android:configChanges="keyboardHidden|orientation|screenSize"/>
|
android:configChanges="keyboardHidden|orientation|screenSize"/>
|
||||||
|
|
||||||
<service
|
<service
|
||||||
android:name=".service.BackgroundLocalizationService"
|
android:name=".service.BackgroundLocalizationService"
|
||||||
android:enabled="true"
|
android:enabled="true"
|
||||||
android:exported="false"
|
android:exported="false"
|
||||||
android:launchMode="singleTop" />
|
android:launchMode="singleTop" />
|
||||||
|
<!--
|
||||||
|
<service
|
||||||
|
android:name=".service.BackgroundService"
|
||||||
|
android:enabled="true"
|
||||||
|
android:exported="false"
|
||||||
|
android:launchMode="singleTop" />-->
|
||||||
|
|
||||||
<activity
|
<activity
|
||||||
android:name=".activity.TutorTab"
|
android:name=".activity.TutorTab"
|
||||||
|
@ -0,0 +1,46 @@
|
|||||||
|
package com.uam.wmi.findmytutor.activity;
|
||||||
|
|
||||||
|
//import android.app.Fragment;
|
||||||
|
import android.support.v4.app.Fragment;
|
||||||
|
import android.os.Bundle;
|
||||||
|
import android.support.v4.app.FragmentTabHost;
|
||||||
|
import android.view.LayoutInflater;
|
||||||
|
import android.view.View;
|
||||||
|
import android.view.ViewGroup;
|
||||||
|
|
||||||
|
import com.uam.wmi.findmytutor.R;
|
||||||
|
|
||||||
|
public class TutorsListTab extends Fragment {
|
||||||
|
private FragmentTabHost mTabHost;
|
||||||
|
|
||||||
|
public TutorsListTab() {
|
||||||
|
}
|
||||||
|
|
||||||
|
public static TutorsListTab newInstance() {
|
||||||
|
return new TutorsListTab();
|
||||||
|
}
|
||||||
|
|
||||||
|
public void onCreate(Bundle savedInstanceState) {
|
||||||
|
super.onCreate(savedInstanceState);
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
public View onCreateView(LayoutInflater inflater, ViewGroup container,
|
||||||
|
Bundle savedInstanceState) {
|
||||||
|
|
||||||
|
View rootView = inflater.inflate(R.layout.tutors_list_tabs, container, false);
|
||||||
|
|
||||||
|
mTabHost = rootView.findViewById(android.R.id.tabhost);
|
||||||
|
mTabHost.setup(getActivity(), getFragmentManager(), R.id.realtabcontent);
|
||||||
|
|
||||||
|
mTabHost.addTab(mTabHost.newTabSpec("fragmentb").setIndicator("Fragment B"),
|
||||||
|
UsersListFragment.class, null);
|
||||||
|
mTabHost.addTab(mTabHost.newTabSpec("fragmentc").setIndicator("Fragment C"),
|
||||||
|
UsersListFragment.class, null);
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
return rootView;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
@ -129,9 +129,7 @@ public class BackgroundLocalizationService extends Service {
|
|||||||
mStatusChecker = () -> {
|
mStatusChecker = () -> {
|
||||||
try {
|
try {
|
||||||
mFusedLocationClient = LocationServices.getFusedLocationProviderClient(this);
|
mFusedLocationClient = LocationServices.getFusedLocationProviderClient(this);
|
||||||
initializeLocationManager();
|
|
||||||
getLocalizationFromListeners();
|
getLocalizationFromListeners();
|
||||||
changeBackgroundMode();
|
|
||||||
} finally {
|
} finally {
|
||||||
mFusedLocationClient = null;
|
mFusedLocationClient = null;
|
||||||
destroyLocationListeners();
|
destroyLocationListeners();
|
||||||
@ -192,10 +190,6 @@ public class BackgroundLocalizationService extends Service {
|
|||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
List<String> providers1 = mLocationManager.getProviders(true);
|
|
||||||
Location bestLocation = null;
|
|
||||||
AtomicReference<Boolean> triggerAnotherLocationListener = new AtomicReference<>(false);
|
|
||||||
|
|
||||||
mFusedLocationClient.getLastLocation().addOnSuccessListener(
|
mFusedLocationClient.getLastLocation().addOnSuccessListener(
|
||||||
location -> {
|
location -> {
|
||||||
if (location != null) {
|
if (location != null) {
|
||||||
@ -204,24 +198,8 @@ public class BackgroundLocalizationService extends Service {
|
|||||||
sendCoordinateToBackend(location);
|
sendCoordinateToBackend(location);
|
||||||
}
|
}
|
||||||
|
|
||||||
triggerAnotherLocationListener.set(true);
|
|
||||||
});
|
});
|
||||||
|
|
||||||
if (triggerAnotherLocationListener.get()) {
|
|
||||||
for (String provider : providers1) {
|
|
||||||
Location location = mLocationManager.getLastKnownLocation(provider);
|
|
||||||
|
|
||||||
if (location == null) {
|
|
||||||
continue;
|
|
||||||
}
|
|
||||||
if (bestLocation == null || location.getAccuracy() < bestLocation.getAccuracy()) {
|
|
||||||
bestLocation = location;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
coordinatesHistory.add(bestLocation);
|
|
||||||
}
|
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
private void sendCoordinateToBackend(Location location) {
|
private void sendCoordinateToBackend(Location location) {
|
||||||
@ -238,48 +216,10 @@ public class BackgroundLocalizationService extends Service {
|
|||||||
}
|
}
|
||||||
|
|
||||||
private void destroyLocationListeners(){
|
private void destroyLocationListeners(){
|
||||||
if (mLocationManager != null) {
|
|
||||||
for (LocationListener listener : mLocationListeners) {
|
|
||||||
try {
|
|
||||||
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) {
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
mLocationManager.removeUpdates(listener);
|
|
||||||
|
|
||||||
} catch (Exception ex) {
|
|
||||||
Log.i(TAG, "fail to remove location listener, ignore", ex);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
private void initializeLocationManager() {
|
|
||||||
Log.e(TAG, "initializeLocationManager - LOCATION_INTERVAL: " + notify_interval + " LOCATION_DISTANCE: " + LOCATION_DISTANCE);
|
|
||||||
|
|
||||||
if (mLocationManager == null) {
|
|
||||||
mLocationManager = (LocationManager) getApplicationContext().getSystemService(Context.LOCATION_SERVICE);
|
|
||||||
}
|
|
||||||
|
|
||||||
Integer providerIndex = 0;
|
|
||||||
|
|
||||||
for (LocationListener listener : mLocationListeners) {
|
|
||||||
try {
|
|
||||||
mLocationManager.requestLocationUpdates(
|
|
||||||
providers.get(providerIndex),
|
|
||||||
notify_interval,
|
|
||||||
LOCATION_DISTANCE,
|
|
||||||
listener
|
|
||||||
);
|
|
||||||
|
|
||||||
} catch (java.lang.SecurityException ex) {
|
|
||||||
Log.i(TAG, "fail to request location update, ignore", ex);
|
|
||||||
} catch (IllegalArgumentException ex) {
|
|
||||||
Log.d(TAG, "network provider does not exist, " + ex.getMessage());
|
|
||||||
}
|
|
||||||
|
|
||||||
providerIndex++;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
private class LocationListener implements android.location.LocationListener {
|
private class LocationListener implements android.location.LocationListener {
|
||||||
|
|
||||||
|
@ -0,0 +1,264 @@
|
|||||||
|
package com.uam.wmi.findmytutor.service;
|
||||||
|
|
||||||
|
import android.Manifest;
|
||||||
|
import android.annotation.SuppressLint;
|
||||||
|
import android.app.Service;
|
||||||
|
import android.content.Context;
|
||||||
|
import android.content.Intent;
|
||||||
|
import android.content.pm.PackageManager;
|
||||||
|
import android.location.Location;
|
||||||
|
import android.location.LocationListener;
|
||||||
|
import android.os.Binder;
|
||||||
|
import android.os.Bundle;
|
||||||
|
import android.os.IBinder;
|
||||||
|
import android.os.PowerManager;
|
||||||
|
import android.provider.SyncStateContract;
|
||||||
|
import android.support.v4.app.ActivityCompat;
|
||||||
|
import android.util.Log;
|
||||||
|
|
||||||
|
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.location.LocationRequest;
|
||||||
|
import com.google.android.gms.location.LocationServices;
|
||||||
|
|
||||||
|
import java.text.DateFormat;
|
||||||
|
import java.util.Date;
|
||||||
|
|
||||||
|
import static com.uam.wmi.findmytutor.utils.Const.onlineBackgroundLocationInterval;
|
||||||
|
|
||||||
|
|
||||||
|
public class BackgroundService extends Service implements
|
||||||
|
GoogleApiClient.ConnectionCallbacks,
|
||||||
|
GoogleApiClient.OnConnectionFailedListener,
|
||||||
|
LocationListener {
|
||||||
|
|
||||||
|
IBinder mBinder = new LocalBinder();
|
||||||
|
private static final String TAG = "MyLocationService";
|
||||||
|
|
||||||
|
private GoogleApiClient mGoogleApiClient;
|
||||||
|
private PowerManager.WakeLock mWakeLock;
|
||||||
|
private LocationRequest mLocationRequest;
|
||||||
|
// Flag that indicates if a request is underway.
|
||||||
|
private boolean mInProgress;
|
||||||
|
private static long notify_interval = onlineBackgroundLocationInterval;
|
||||||
|
|
||||||
|
private Boolean servicesAvailable = false;
|
||||||
|
|
||||||
|
public class LocalBinder extends Binder {
|
||||||
|
public BackgroundService getServerInstance() {
|
||||||
|
return BackgroundService.this;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void onCreate() {
|
||||||
|
super.onCreate();
|
||||||
|
|
||||||
|
|
||||||
|
mInProgress = false;
|
||||||
|
// Create the LocationRequest object
|
||||||
|
mLocationRequest = LocationRequest.create();
|
||||||
|
// Use high accuracy
|
||||||
|
mLocationRequest.setPriority(LocationRequest.PRIORITY_BALANCED_POWER_ACCURACY);
|
||||||
|
// Set the update interval to 5 seconds
|
||||||
|
mLocationRequest.setInterval(notify_interval);
|
||||||
|
// Set the fastest update interval to 1 second
|
||||||
|
mLocationRequest.setFastestInterval(notify_interval);
|
||||||
|
|
||||||
|
servicesAvailable = servicesConnected();
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Create a new location client, using the enclosing class to
|
||||||
|
* handle callbacks.
|
||||||
|
*/
|
||||||
|
setUpLocationClientIfNeeded();
|
||||||
|
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Create a new location client, using the enclosing class to
|
||||||
|
* handle callbacks.
|
||||||
|
*/
|
||||||
|
protected synchronized void buildGoogleApiClient() {
|
||||||
|
this.mGoogleApiClient = new GoogleApiClient.Builder(this)
|
||||||
|
.addConnectionCallbacks(this)
|
||||||
|
.addOnConnectionFailedListener(this)
|
||||||
|
.addApi(LocationServices.API)
|
||||||
|
.build();
|
||||||
|
}
|
||||||
|
|
||||||
|
private boolean servicesConnected() {
|
||||||
|
|
||||||
|
// Check that Google Play services is available
|
||||||
|
int resultCode = GooglePlayServicesUtil.isGooglePlayServicesAvailable(this);
|
||||||
|
|
||||||
|
// If Google Play services is available
|
||||||
|
if (ConnectionResult.SUCCESS == resultCode) {
|
||||||
|
|
||||||
|
return true;
|
||||||
|
} else {
|
||||||
|
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
@SuppressLint("InvalidWakeLockTag")
|
||||||
|
public int onStartCommand(Intent intent, int flags, int startId) {
|
||||||
|
super.onStartCommand(intent, flags, startId);
|
||||||
|
|
||||||
|
PowerManager mgr = (PowerManager) getSystemService(Context.POWER_SERVICE);
|
||||||
|
|
||||||
|
/*
|
||||||
|
WakeLock is reference counted so we don't want to create multiple WakeLocks. So do a check before initializing and acquiring.
|
||||||
|
|
||||||
|
This will fix the "java.lang.Exception: WakeLock finalized while still held: MyWakeLock" error that you may find.
|
||||||
|
*/
|
||||||
|
/* if (this.mWakeLock == null) { //**Added this
|
||||||
|
this.mWakeLock = mgr.newWakeLock(PowerManager.PARTIAL_WAKE_LOCK, "MyWakeLock");
|
||||||
|
}
|
||||||
|
|
||||||
|
if (!this.mWakeLock.isHeld()) { //**Added this
|
||||||
|
this.mWakeLock.acquire(10*60*1000L *//*10 minutes*//*);
|
||||||
|
}*/
|
||||||
|
|
||||||
|
if (!servicesAvailable || mGoogleApiClient.isConnected() || mInProgress)
|
||||||
|
return START_STICKY;
|
||||||
|
|
||||||
|
setUpLocationClientIfNeeded();
|
||||||
|
if (!mGoogleApiClient.isConnected() || !mGoogleApiClient.isConnecting() && !mInProgress) {
|
||||||
|
mInProgress = true;
|
||||||
|
mGoogleApiClient.connect();
|
||||||
|
}
|
||||||
|
|
||||||
|
return START_STICKY;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
private void setUpLocationClientIfNeeded() {
|
||||||
|
if (mGoogleApiClient == null)
|
||||||
|
buildGoogleApiClient();
|
||||||
|
}
|
||||||
|
|
||||||
|
// Define the callback method that receives location updates
|
||||||
|
@Override
|
||||||
|
public void onLocationChanged(Location location) {
|
||||||
|
// Report to the UI that the location was updated
|
||||||
|
String msg = Double.toString(location.getLatitude()) + "," +
|
||||||
|
Double.toString(location.getLongitude());
|
||||||
|
Log.d("debug", msg);
|
||||||
|
Log.e(TAG, "onLocationChanged: " + location);
|
||||||
|
|
||||||
|
// Toast.makeText(this, msg, Toast.LENGTH_SHORT).show();
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void onStatusChanged(String s, int i, Bundle bundle) {
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void onProviderEnabled(String s) {
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void onProviderDisabled(String s) {
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public IBinder onBind(Intent intent) {
|
||||||
|
return mBinder;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void onDestroy() {
|
||||||
|
// Turn off the request flag
|
||||||
|
this.mInProgress = false;
|
||||||
|
|
||||||
|
if (this.servicesAvailable && this.mGoogleApiClient != null) {
|
||||||
|
this.mGoogleApiClient.unregisterConnectionCallbacks(this);
|
||||||
|
this.mGoogleApiClient.unregisterConnectionFailedListener(this);
|
||||||
|
this.mGoogleApiClient.disconnect();
|
||||||
|
// Destroy the current location client
|
||||||
|
this.mGoogleApiClient = null;
|
||||||
|
}
|
||||||
|
// Display the connection status
|
||||||
|
// Toast.makeText(this, DateFormat.getDateTimeInstance().format(new Date()) + ":
|
||||||
|
// Disconnected. Please re-connect.", Toast.LENGTH_SHORT).show();
|
||||||
|
|
||||||
|
if (this.mWakeLock != null) {
|
||||||
|
this.mWakeLock.release();
|
||||||
|
this.mWakeLock = null;
|
||||||
|
}
|
||||||
|
|
||||||
|
super.onDestroy();
|
||||||
|
}
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Called by Location Services when the request to connect the
|
||||||
|
* client finishes successfully. At this point, you can
|
||||||
|
* request the current location or start periodic updates
|
||||||
|
*/
|
||||||
|
@Override
|
||||||
|
public void onConnected(Bundle bundle) {
|
||||||
|
|
||||||
|
// Request location updates using static settings
|
||||||
|
//Intent intent = new Intent(this, LocationReceiver.class);
|
||||||
|
if (ActivityCompat.checkSelfPermission(this, Manifest.permission.ACCESS_FINE_LOCATION) != PackageManager.PERMISSION_GRANTED && ActivityCompat.checkSelfPermission(this, Manifest.permission.ACCESS_COARSE_LOCATION) != PackageManager.PERMISSION_GRANTED) {
|
||||||
|
// TODO: Consider calling
|
||||||
|
// ActivityCompat#requestPermissions
|
||||||
|
// here to request the missing permissions, and then overriding
|
||||||
|
// public void onRequestPermissionsResult(int requestCode, String[] permissions,
|
||||||
|
// int[] grantResults)
|
||||||
|
// to handle the case where the user grants the permission. See the documentation
|
||||||
|
// for ActivityCompat#requestPermissions for more details.
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
LocationServices.getFusedLocationProviderClient(this);
|
||||||
|
LocationServices.FusedLocationApi.requestLocationUpdates(mGoogleApiClient, mLocationRequest, (com.google.android.gms.location.LocationListener) this);
|
||||||
|
|
||||||
|
/* .requestLocationUpdates(this.mGoogleApiClient,
|
||||||
|
mLocationRequest, (com.google.android.gms.location.LocationListener) this); // This is the changed line.*/
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Called by Location Services if the connection to the
|
||||||
|
* location client drops because of an error.
|
||||||
|
*/
|
||||||
|
@Override
|
||||||
|
public void onConnectionSuspended(int i) {
|
||||||
|
// Turn off the request flag
|
||||||
|
mInProgress = false;
|
||||||
|
// Destroy the current location client
|
||||||
|
mGoogleApiClient = null;
|
||||||
|
// Display the connection status
|
||||||
|
// Toast.makeText(this, DateFormat.getDateTimeInstance().format(new Date()) + ": Disconnected. Please re-connect.", Toast.LENGTH_SHORT).show();
|
||||||
|
}
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Called by Location Services if the attempt to
|
||||||
|
* Location Services fails.
|
||||||
|
*/
|
||||||
|
@Override
|
||||||
|
public void onConnectionFailed(ConnectionResult connectionResult) {
|
||||||
|
mInProgress = false;
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Google Play services can resolve some errors it detects.
|
||||||
|
* If the error has a resolution, try sending an Intent to
|
||||||
|
* start a Google Play services activity that can resolve
|
||||||
|
* error.
|
||||||
|
*/
|
||||||
|
if (connectionResult.hasResolution()) {
|
||||||
|
|
||||||
|
// If no resolution is available, display an error dialog
|
||||||
|
} else {
|
||||||
|
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
56
app/src/main/res/layout/tutors_list_tabs.xml
Normal file
56
app/src/main/res/layout/tutors_list_tabs.xml
Normal file
@ -0,0 +1,56 @@
|
|||||||
|
<?xml version="1.0" encoding="utf-8"?>
|
||||||
|
<RelativeLayout
|
||||||
|
xmlns:android="http://schemas.android.com/apk/res/android"
|
||||||
|
android:layout_width="wrap_content"
|
||||||
|
android:layout_height="wrap_content">
|
||||||
|
|
||||||
|
<android.support.v4.app.FragmentTabHost
|
||||||
|
android:id="@+id/tabHost"
|
||||||
|
android:layout_width="match_parent"
|
||||||
|
android:layout_height="match_parent"
|
||||||
|
android:layout_alignParentTop="true"
|
||||||
|
android:layout_centerHorizontal="true">
|
||||||
|
|
||||||
|
<LinearLayout
|
||||||
|
android:layout_width="match_parent"
|
||||||
|
android:layout_height="match_parent"
|
||||||
|
android:orientation="vertical">
|
||||||
|
|
||||||
|
<TabWidget
|
||||||
|
android:id="@android:id/tabs"
|
||||||
|
android:layout_width="match_parent"
|
||||||
|
android:layout_height="30dp"/>
|
||||||
|
|
||||||
|
<FrameLayout
|
||||||
|
android:id="@android:id/tabcontent"
|
||||||
|
android:layout_width="match_parent"
|
||||||
|
android:layout_height="match_parent">
|
||||||
|
|
||||||
|
<LinearLayout
|
||||||
|
android:id="@+id/tab1"
|
||||||
|
android:layout_width="match_parent"
|
||||||
|
android:layout_height="match_parent"
|
||||||
|
android:orientation="vertical">
|
||||||
|
|
||||||
|
</LinearLayout>
|
||||||
|
|
||||||
|
<LinearLayout
|
||||||
|
android:id="@+id/tab2"
|
||||||
|
android:layout_width="match_parent"
|
||||||
|
android:layout_height="match_parent"
|
||||||
|
android:orientation="vertical">
|
||||||
|
|
||||||
|
</LinearLayout>
|
||||||
|
|
||||||
|
</FrameLayout>
|
||||||
|
|
||||||
|
</LinearLayout>
|
||||||
|
|
||||||
|
<FrameLayout
|
||||||
|
android:id="@+id/realtabcontent"
|
||||||
|
android:layout_width="match_parent"
|
||||||
|
android:layout_height="50dp"
|
||||||
|
android:layout_below="@+id/tabLinear"/>
|
||||||
|
|
||||||
|
</android.support.v4.app.FragmentTabHost>
|
||||||
|
</RelativeLayout>
|
Loading…
Reference in New Issue
Block a user