android - locationManager stops proving updates - java

I am making a tracking app, which has a service getting location updates and storing them into a database. And activity gets notified and retrieves location data from the DB.
The problem is that all works fine what the activity is running, yet when the activity is not in the foreground, service gets a few more locations and stops updating.
Once I open the activity, the updates continue.
I have checked, the service itself is running, I could add a countdown timer adding random numbers to the DB and it continues working. What do you think might be causing the location to stop updating?...
public class ServiceClass extends Service implements NavigationView.OnNavigationItemSelectedListener{
IBinder binder; // interface for clients that bind
boolean allowRebind; // indicates whether onRebind should be used
Notification notification;
MediaPlayer mp;
SharedPreferences sharedPreferences;
SharedPreferences.Editor spEdit;
LocationManager locationManager;
Context mContext;
ArrayList<CameraClass> camList = new ArrayList<CameraClass>();
Double carSpeed = 0.0;
int distance_to_nearest_radar = 999999;
boolean alarm = false;
int speedLimit = 100;
float bearing = 0;
Box<CoordinatePoint> cpBox;
Location loc;
Location locTemp;
#Override
public void onCreate() {
mContext = this;
mp = MediaPlayer.create(this, R.raw.beep01);
mp.setLooping(true);
BoxStore bs = ObjectBoxSingleton.get();
cpBox = bs.boxFor(CoordinatePoint.class);
Toast.makeText(this,"Service STARTED",Toast.LENGTH_SHORT).show();
loadCSV ( getResources().openRawResource(R.raw.radar_map));
}
/////////////////////////////////////////////////////////////////////////////////////////
#SuppressLint("MissingPermission")
#Override
public int onStartCommand(Intent intent, int flags, int startId) {
locationManager = (LocationManager) mContext.getSystemService(Context.LOCATION_SERVICE);
locationManager.requestLocationUpdates(LocationManager.GPS_PROVIDER, 500, 1, locationListenerGPS);
Intent intent_recallActivity = new Intent(getApplicationContext(), MapsActivity.class);
intent_recallActivity.setFlags(Intent.FLAG_ACTIVITY_CLEAR_TOP);
PendingIntent pendingIntent = PendingIntent.getActivity(ServiceClass.this, 0, intent_recallActivity, 0);
notification = new NotificationCompat.Builder(this, "nc01")
.setContentTitle("RADAR AHEAD!")
.setContentText("Waiting for GPS signal...")
.setSmallIcon(R.drawable.ic_nogps_notification)
.build();
startForeground(1, notification);
return START_STICKY;
}
/////////////////////////////////////////////////////////////////////////////////////////
LocationListener locationListenerGPS = new LocationListener() {
#Override
public void onLocationChanged(android.location.Location location) {
Log.e("GPS","NEW POINT!");
Toast.makeText(mContext,"NEW POINT",Toast.LENGTH_SHORT).show();
CoordinatePoint cp = new CoordinatePoint();
cp.latPoint = location.getLatitude();
cp.lonPoint = location.getLongitude();
cpBox.put(cp);
carSpeed = roundUp(Double.parseDouble(String.valueOf(location.getSpeed()))*3.6 , 1 );
checkForRadars();
updateNotification();
}
};
/////////////////////////////////////////////////////////////////////////////////////////
private void updateNotification() {
Intent intent_recallActivity = new Intent(getApplicationContext(), MapsActivity.class);
intent_recallActivity.setFlags(Intent.FLAG_ACTIVITY_CLEAR_TOP);
PendingIntent pendingIntent = PendingIntent.getActivity(ServiceClass.this, 0, intent_recallActivity, 0);
String a = "ACTIVITY ON PAUSE";
if ( isActivityRunningInForeground() )
{
a ="ACTIVITY RUNNING";
sendMessageToActivity();
}
notification = new NotificationCompat.Builder(this, "nc01")
.setContentTitle(a + ", objBox: " + String.valueOf( cpBox.count() ) )
.setContentText( "Speed: " + String.valueOf(carSpeed) + " km/h | Radar in: "
+ String.valueOf( roundUp( (double)distance_to_nearest_radar/1000, 2) )+" km " )
.setSmallIcon(R.drawable.ic_radar_notification)
.build();
startForeground(1, notification);
}
/////////////////////////////////////////////////////////////////////////////////////////
private void sendMessageToActivity() {
Intent intent = new Intent("GPSLocationUpdates");
intent.putExtra("carSpeed", Double.valueOf(carSpeed) );
intent.putExtra("distance_to_nearest_radar", distance_to_nearest_radar);
intent.putExtra("speedLimit", speedLimit);
LocalBroadcastManager.getInstance(this).sendBroadcast(intent);
};

Related

How to stop a service at 8 pm if its running?

I have a service which captures the location of a user and updates database using retrofit. I want to stop the service automatically at 8 pm everyday if its running and also update the database that the user has punched out at 8 pm.
I want the service to start the manually but want the service to stop automatically if it is not stopped manually.
Here is my service class
public class LiveLocationService extends Service {
private static final String TAG = LiveLocationService.class.getSimpleName();
Retrofit retrofitClient;
CompositeDisposable compositeDisposable = new CompositeDisposable();
MyService myService;
String empCode, year, month, date;
FusedLocationProviderClient client;
LocationCallback locationCallback;
#Override
public int onStartCommand(Intent intent, int flags, int startId) {
retrofitClient = RetrofitClient.getInstance();
myService = retrofitClient.create(MyService.class);
empCode = intent.getStringExtra("empCode");
year = intent.getStringExtra("year");
month = intent.getStringExtra("month");
date = intent.getStringExtra("date");
return super.onStartCommand(intent, flags, startId);
}
#Override
public IBinder onBind(Intent intent) {
return null;
}
#RequiresApi(api = Build.VERSION_CODES.O)
#Override
public void onCreate() {
super.onCreate();
if (isOnline()) {
buildNotification();
requestLocationUpdates();
} else {
Log.e("MSER", "Please connect to the internet.");
}
}
private void buildNotification() {
if (android.os.Build.VERSION.SDK_INT >= android.os.Build.VERSION_CODES.O) {
String NOTIFICATION_CHANNEL_ID = "com.deepankmehta.managementservices";
String channelName = "My Background Service";
NotificationChannel chan = null;
chan = new NotificationChannel(NOTIFICATION_CHANNEL_ID, channelName, NotificationManager.IMPORTANCE_HIGH);
chan.setLightColor(Color.BLUE);
chan.setLockscreenVisibility(Notification.VISIBILITY_PRIVATE);
NotificationManager manager = (NotificationManager) getSystemService(Context.NOTIFICATION_SERVICE);
assert manager != null;
manager.createNotificationChannel(chan);
PendingIntent intent = PendingIntent.getActivity(this, 0, new Intent(this, MainActivity.class), PendingIntent.FLAG_UPDATE_CURRENT);
NotificationCompat.Builder notificationBuilder = new NotificationCompat.Builder(this, NOTIFICATION_CHANNEL_ID);
Notification notification = notificationBuilder.setOngoing(true)
.setSmallIcon(R.drawable.mser)
.setContentTitle("xxxx")
.setContentText("xxxx is tracking your location.")
.setPriority(NotificationManager.IMPORTANCE_HIGH)
.setCategory(Notification.CATEGORY_SERVICE)
.setContentIntent(intent)
.build();
startForeground(2, notification);
} else {
PendingIntent broadcastIntent = PendingIntent.getActivity(
this, 0, new Intent(this, MainActivity.class), PendingIntent.FLAG_UPDATE_CURRENT);
// Create the persistent notification
NotificationCompat.Builder builder = new NotificationCompat.Builder(this)
.setContentTitle(getString(R.string.app_name))
.setContentText("xxxx is tracking your location.")
.setOngoing(true)
.setContentIntent(broadcastIntent)
.setSmallIcon(R.drawable.mser);
startForeground(1, builder.build());
}
}
private void requestLocationUpdates() {
if (isOnline()) {
LocationRequest request = new LocationRequest();
request.setInterval(10000);
request.setFastestInterval(5000);
request.setPriority(LocationRequest.PRIORITY_HIGH_ACCURACY);
client = LocationServices.getFusedLocationProviderClient(this);
int permission = ContextCompat.checkSelfPermission(this,
Manifest.permission.ACCESS_FINE_LOCATION);
if (permission == PackageManager.PERMISSION_GRANTED) {
locationCallback = new LocationCallback() {
#Override
public void onLocationResult(LocationResult locationResult) {
Location location = locationResult.getLastLocation();
if (location != null) {
Log.d(TAG, "location update " + location);
double lat = location.getLatitude();
double lon = location.getLongitude();
final String time = new SimpleDateFormat("HH:mm", Locale.getDefault()).format(new Date());
compositeDisposable.add(myService.userLocation(empCode, year, month, date, time, lat, lon)
.subscribeOn(Schedulers.io())
.observeOn(AndroidSchedulers.mainThread())
.subscribe(new Consumer< String >() {
#Override
public void accept(String s) throws Exception {
Log.e("data", s);
if (s.equals("\"done\"")) {
Log.e("status", "location punched");
}
}
}));
} else {
Log.d("MSER", "location update, no location found. ");
}
}
};
client.requestLocationUpdates(request, locationCallback, null);
} else {
Log.e("MSER", "Please enable location.");
}
} else {
Log.e("MSER", "Please connect to the internet.");
}
}
#Override
public void onDestroy() {
super.onDestroy();
client.removeLocationUpdates(locationCallback);
stopForeground(true);
stopSelf();
}
protected boolean isOnline() {
ConnectivityManager cm = (ConnectivityManager)getSystemService(Context.CONNECTIVITY_SERVICE);
NetworkInfo netInfo = cm.getActiveNetworkInfo();
if (netInfo != null && netInfo.isConnectedOrConnecting()) {
return true;
} else {
return false;
}
}
}
Here is home activity class start service and stop service methods. These methods are called when the user clicks on punch in and punch out buttons respectively.
private void startTrackerService() {
final String date = new SimpleDateFormat("yyyy-MM-dd", Locale.getDefault()).format(new Date());
final String year = date.substring(0, 4);
final String month = date.substring(5, 7);
final String dateToday = date.substring(8, 10);
Intent intent = new Intent(this, LiveLocationService.class);
intent.putExtra("empCode", empCode);
intent.putExtra("year", year);
intent.putExtra("month", month);
intent.putExtra("date", dateToday);
startService(intent);
}
private void stopTrackerService() {
stopService(new Intent(this, LiveLocationService.class));
}
You can use AlarmManager to schedule this kind of the task,
Register AlaramManger at specific time and check whether service is running, if it is running then stop service.
Here is the example of registering AlaramManager at specific time
AlarmManager alarmManager = (AlarmManager) getActivityContext()
.getSystemService(Context.ALARM_SERVICE);
Intent intent = new Intent(getActivityContext(), AutoStopReceiver.class);
PendingIntent pendingIntent = PendingIntent.getBroadcast(getActivityContext(),
0, intent, PendingIntent.FLAG_UPDATE_CURRENT);
alarmManager.setExactAndAllowWhileIdle(AlarmManager.RTC_WAKEUP,
stopServieTime, pendingIntent);
Here is the Receiver Class,
public class AutoStopReceiver extends BroadcastReceiver {
#Override
public void onReceive(Context context, Intent intent) {
//TODO Stop service from here
}
Register receiver in AndroidMenifest.xml
<receiver android:name=".AutoStopReceiver" />

Running an Alarm Service once a day on Oreo

I've created a service which consult notes if they are in recicle bin, it have to run once a day but with handler I think it will drain too much battery, So I need you help How can I do a task once a day without drain battery or other thing that's not a handler ?
When the app is launched the NotesApplication is created and start the NotesService class, it should be executing all day but it will drain battery, so I need to execute once a day
NotesApplication
public class NotesApplication extends Application {
String TAG = "NotesApplication";
Intent intent;
#Override
public void onCreate() {
// TODO: Implement this method
super.onCreate();
Log.d(TAG, "Application created");
intent = new Intent(getApplicationContext(), NotesService.class);
if(Build.VERSION.SDK_INT >= Build.VERSION_CODES.O){
Log.d(TAG, "Foreground service started");
getApplicationContext().startForegroundService(intent);
}else if(Build.VERSION.SDK_INT < Build.VERSION_CODES.O){
Log.d(TAG, "Service started");
getApplicationContext().startService(intent);
}
}
Notes Service
public class NotesService extends Service {
ArrayList<Notes> listNotas;
String TAG = "NotesService";
SQLiteHelperConnection conn;
#Override
public void onCreate()
{
// TODO: Implement this method
super.onCreate();
Log.d(TAG, "Notes service created");
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.O){
final NotificationManager mNotific= (NotificationManager)getSystemService(Context.NOTIFICATION_SERVICE);
CharSequence name = "Axco";
String description = "Service";
int importance = NotificationManager.IMPORTANCE_MIN;
final String ChannelID="Service Channel";
NotificationChannel mChannel = new NotificationChannel(ChannelID, name, importance);
mChannel.setDescription(description);
mChannel.setLightColor(ThemeClass.getColor());
mChannel.canShowBadge();
mChannel.setShowBadge(true);
mNotific.createNotificationChannel(mChannel);
final int code = 101;
String body= "Service Running";
Notification notification = new Notification.Builder(this, ChannelID)
.setContentTitle(getPackageName())
.setContentText(body)
.setBadgeIconType(R.drawable.ic_launcher)
.setNumber(1)
.setSmallIcon(R.drawable.ic_launcher)
.setAutoCancel(true)
.build();
startForeground(code, notification);
}
conn = new SQLiteHelperConnection(this, "db_notas.db", null, 1);
listNotas = new ArrayList<Notes>();
}
#Override
public int onStartCommand(Intent intent, int flags, int startId)
{
// TODO: Implement this method
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.O){
final NotificationManager mNotific= (NotificationManager)getSystemService(Context.NOTIFICATION_SERVICE);
CharSequence name = "Axco";
String description = "Service";
int importance = NotificationManager.IMPORTANCE_MIN;
final String ChannelID="Service Channel";
NotificationChannel mChannel = new NotificationChannel(ChannelID, name, importance);
mChannel.setDescription(description);
mChannel.setLightColor(ThemeClass.getColor());
mChannel.canShowBadge();
mChannel.setShowBadge(true);
mNotific.createNotificationChannel(mChannel);
final int code = 101;
String body= "Service Running";
Notification notification = new Notification.Builder(this, ChannelID)
.setContentTitle(getPackageName())
.setContentText(body)
.setBadgeIconType(R.drawable.ic_launcher)
.setNumber(1)
.setSmallIcon(R.drawable.ic_launcher)
.setAutoCancel(true)
.build();
startForeground(code, notification);
}
final Handler handler = new Handler();
Runnable runnable = new Runnable(){
#Override
public void run()
{
// TODO: Implement this method
Log.d(TAG, "Service running");
listNotas.clear();
consult();
check();
handler.postDelayed(this, 15000);
}
};
handler.post(runnable);
return Service.START_STICKY;
}
private void consult(){
Log.d(TAG, "Consulting...");
SQLiteDatabase db = conn.getReadableDatabase();
Notes notas = null;
Cursor cursor = db.rawQuery("SELECT * FROM "+Utilities.TABLA_NOTA, null);
while (cursor.moveToNext()) {
notas = new Notes();
notas.setId(cursor.getString(0));
notas.setLastModified(cursor.getString(5));
notas.setLastModifiedDate(cursor.getString(7));
boolean a = Boolean.valueOf(cursor.getString(4));
if(a){
listNotas.add(notas);
}
}
}
private void check(){
//Do something
}
private void deleteNote(int position){
SQLiteDatabase db = conn.getWritableDatabase();
String[] parametros = {listNotas.get(position).getId()};
db.delete(Utilities.TABLA_NOTA, Utilities.ID+"=?", parametros);
listNotas.remove(position);
}
#Override
public IBinder onBind(Intent p1){
// TODO: Implement this method
return null;
}
Using Alarm Manager is efficient.
See implementation
AlarmManager am=(AlarmManager)context.getSystemService(Context.ALARM_SERVICE);
Intent i= new Intent(context, AlarmManagerBroadcastReceiver.class);
//intent.putExtra(something you want to put);
PendingIntent pi = PendingIntent.getBroadcast(context, 0, i, 0);
Calendar calendar = Calendar.getInstance();
calendar.setTimeInMillis(System.currentTimeMillis());
// check if it is more than 11 am. if so set alarm for next day
if (Calendar.getInstance().get(Calendar.HOUR_OF_DAY)) {
calendar.add(Calendar.DAY_OF_YEAR, 1);
}
// everyday at 11 am
calendar.set(Calendar.HOUR_OF_DAY, 9);
calendar.set(Calendar.MINUTE, 0);
calendar.set(Calendar.SECOND, 0);
am.setRepeating(AlarmManager.RTC_WAKEUP, calendar.getTimeInMillis(),
AlarmManager.INTERVAL_DAY, pi);
// alarm set
Finally create a broadcast receiver to do the work you want.

CountDownTimer Service crashing when it is opened

I am trying to make a countdown timer screen that will keep counting down if I back out of the app or change screens or something. For some reason it keeps crashing saying that timeLeft is null. I can't figure out why it would be because I know the time variable in my Countdown class is there. Thanks for any help!
Countdown Activity
public class Countdown extends Activity {
public static String time;
public static String address;
#Override
protected void onCreate(Bundle savedInstanceState){
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_countdown);
Intent confIntent = getIntent();
time = confIntent.getStringExtra("time");
address = confIntent.getStringExtra("address");
LocalBroadcastManager.getInstance(this).registerReceiver(
new BroadcastReceiver() {
#Override
public void onReceive(Context context, Intent intent) {
TextView textView= findViewById(R.id.t1);
String timeLeftString = intent.getStringExtra("timeSent");
int timeLeft = Integer.parseInt(timeLeftString);
if(timeLeft>0) {
textView.setText("You have " + timeLeft + " minutes left");
}
else{
textView.setText("Y'all outta time, see ya again soon!");
killIt();
}
}
}, new IntentFilter(CountdownService.ACTION_LOCATION_BROADCAST)
);
Intent toService = new Intent(this, CountdownService.class);
startService(toService);
}
#Override
protected void onResume() {
super.onResume();
TextView textView= findViewById(R.id.t1);
textView.setText("You have " + CountdownService.toSend + " minutes left");
}
#Override
protected void onPause() {
super.onPause();
}
public void killIt(){
stopService(new Intent(this, CountdownService.class));
}
}
Countdown Service
public class CountdownService extends Service{
public static int toSend=0;
public int time;
public static final String
ACTION_LOCATION_BROADCAST = CountdownService.class.getName() +
"LocationBroadcast";
public final String timeFromCD = Countdown.time;
public final String address = Countdown.address;
#Override
public void onCreate() {
super.onCreate();
time = Integer.parseInt(timeFromCD);
time = time*60000;
new CountDownTimer(time, 5000) {
public void onTick(long millisUntilFinished) {
int timeLeftInt = (int) Math.ceil((double) millisUntilFinished / 60000); //Whole number of minutes left, ceiling
sendBroadcastMessage(timeLeftInt);
toSend = timeLeftInt;
if(timeLeftInt == 5){
Notify("Not Done");
}
}
public void onFinish() {
sendBroadcastMessage(0);
Notify("done");
Response.Listener<String> response = new Response.Listener<String>() {
#Override
public void onResponse(String response) {
try {
//creating a jsonResponse that will receive the php json
JSONObject jsonResponse = new JSONObject(response);
boolean success = jsonResponse.getBoolean("success");
if (success) {
} else {
AlertDialog.Builder builder = new AlertDialog.Builder(CountdownService.this);
builder.setMessage("Login Failed")
.setNegativeButton("Retry", null)
.create()
.show();
}
} catch (JSONException e) {
e.printStackTrace();
}
}
};
SpotAmountRequest spotAmountRequest = new SpotAmountRequest(address, "0", response);
RequestQueue queue = Volley.newRequestQueue(CountdownService.this);
queue.add(spotAmountRequest);
}
}.start();
}
private void sendBroadcastMessage(int timeSent) {
Intent intent = new Intent(ACTION_LOCATION_BROADCAST);
intent.putExtra("timeSent", timeSent);
LocalBroadcastManager.getInstance(this).sendBroadcast(intent);
}
#Override
public IBinder onBind(Intent intent) {
return null;
}
private void Notify(String doneness){
NotificationManager notificationManager = (NotificationManager)
getSystemService(NOTIFICATION_SERVICE);
Intent intent = new Intent(this, Map.class);
PendingIntent pIntent = PendingIntent.getActivity(this, (int) System.currentTimeMillis(), intent, 0);
if(doneness.equals("done")) {
Notification n = new Notification.Builder(this)
.setContentTitle("Time to leave!")
.setContentText("Your PrePark spot has expired, time to go home!")
.setSmallIcon(R.mipmap.ic_launcher)
.setContentIntent(pIntent)
.setAutoCancel(true)
.build();
notificationManager.notify(0, n);
Vibrator v = (Vibrator) getSystemService(Context.VIBRATOR_SERVICE);
// Vibrate for 500 milliseconds
v.vibrate(1000);
}
else{
Notification n = new Notification.Builder(this)
.setContentTitle("Ya got 5 minutes left in your PrePark spot!")
.setContentText("Better get going soon here")
.setSmallIcon(R.mipmap.ic_launcher)
.setContentIntent(pIntent)
.setAutoCancel(true)
.build();
notificationManager.notify(0, n);
}
}
}
You're storing an int value in the intent that you're broadcasting from the service, but you're then trying to get it out as a String where you receive the broadcast. Either change the receiver to use getIntExtra instead of getStringExtra, or convert the int to a String in the service before storing it in the intent.

Trying to get the user's location loaded onto a map, using a singleton, service and an alarm

So far I have an alarm set to wake up every so often and then take the latitude and longitude of the user. This is stored in the singleton class Position which will be loaded in a different activity and placed as a marker on a map, based on the last recorded position.
Objective
I want the app to track the user's location even when it is closed, as to why i've used an AlarmManager to wake the device after a certain amount of seconds and take the coordinates, until they request to stop it.
Problem
Even though the class returns the previously-recorded Position values i.e. the coordinates, the activity which calls this to place the position on the map returns the coordinates (0.0, 0.0) i.e. null, assuming that it is initialising the object as if it doesn't already exist.
What could be the problem?
Position - the Singleton
public class Position {
private double latitude;
private double longitude;
private String coordinate;
private String service;
private static Position instance;
private Position() {
}
public String getCoordinate() {
return coordinate;
}
public void setCoordinate(String coordinate) {
this.coordinate = coordinate;
}
public double getLongitude() {
return longitude;
}
public void setLongitude(double longitude) {
this.longitude = longitude;
}
public double getLatitude() {
return latitude;
}
public void setLatitude(double latitude) {
this.latitude = latitude;
}
public String getService() {
return service;
}
public void setService(String service) {
this.service = service;
}
public static Position getInstance() {
if (instance == null) {
instance = new Position();
}
return instance;
}
}
The Alarm - where the location is tracked
public class Alarm extends BroadcastReceiver {
#Override
public void onReceive(final Context context, Intent intent) {
PowerManager pm = (PowerManager) context.getSystemService(Context.POWER_SERVICE);
PowerManager.WakeLock wl = pm.newWakeLock(PowerManager.PARTIAL_WAKE_LOCK, "");
wl.acquire();
// get the service code
String serviceCode = intent.getStringExtra("serviceCode");
// get the last known location
LocationManager locationManager = (LocationManager)context.getSystemService(Context.LOCATION_SERVICE);
Criteria criteria = new Criteria();
String provider = locationManager.getBestProvider(criteria, true);
Location location = locationManager.getLastKnownLocation(provider);
//store the latitude and longitude locally
double latitude = location.getLatitude();
double longitude = location.getLongitude();
String coordinate = latitude + ", " + longitude;
Position pos = Position.getInstance();
Log.d("", "Previous position: " + pos.getCoordinate());
pos.setLatitude(latitude);
pos.setLongitude(longitude);
pos.setCoordinate(coordinate);The
pos.setService(serviceCode);
Log.d("", "Found new position: " + pos.getCoordinate());
wl.release();
}
public void SetAlarm(Context context) {
AlarmManager am=(AlarmManager)context.getSystemService(Context.ALARM_SERVICE);
Intent i = new Intent(context, Alarm.class);
PendingIntent pi = PendingIntent.getBroadcast(context, 0, i, 0);
am.setRepeating(AlarmManager.RTC_WAKEUP, System.currentTimeMillis(), 10000, pi); // Millisec * Second * Minute
}
public void CancelAlarm(Context context) {
Intent intent = new Intent(context, Alarm.class);
PendingIntent sender = PendingIntent.getBroadcast(context, 0, intent, 0);
AlarmManager alarmManager = (AlarmManager) context.getSystemService(Context.ALARM_SERVICE);
alarmManager.cancel(sender);
}
}
Location Service - what initialises the alarm
public class LocationService extends android.app.Service {
Alarm alarm = new Alarm();
private NotificationManager nm;
#Override
public void onCreate() {
super.onCreate();
showNotification();
}
#Override
public int onStartCommand(Intent intent, int flags, int startId) {
alarm.SetAlarm(LocationService.this);
return START_STICKY;
}
private void showNotification() {
// set up notification label to notify user that the app is still tracking the location
nm = (NotificationManager)getSystemService(NOTIFICATION_SERVICE);
CharSequence text = "Press to stop tracking";
// don't let user close it, for the purpose of always letting them know the location tracker is still running
Notification notification = new Notification(R.drawable.fav_buses, text, System.currentTimeMillis());
notification.flags = Notification.FLAG_NO_CLEAR;
// for older APIs
PendingIntent contentIntent = PendingIntent.getActivity(this, 0, new Intent(this, PushLocationActivity.class), 0);
notification.setLatestEventInfo(this, "Tracking Your Location", text, contentIntent);
nm.notify(R.string.notification_id, notification);
}
#Override
public void onDestroy() {
super.onDestroy();
alarm.CancelAlarm(LocationService.this);
nm.cancel(R.string.notification_id);
Log.d("", "DESTROYED");
}
#Override
public IBinder onBind(Intent intent) {
return null;
}
}
StopsFragment - where the NullPointerException occurs
#Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
stops = new HashMap<>();
stopList = StopList.getInstance(getActivity()).getStops();
request = getArguments().getString("request");
position = Position.getInstance();
Log.d("", position.getCoordinate());
}
You should not follow that approach, this will drain the device battery. Android have specific API to receive significant location changes for a user, you should use them. Follow this links:
https://developer.android.com/training/location/receive-location-updates.html
Just adapt the code, instead of an activity, the code should be executed from a service, and the service should be called to execute on boot.

Change Class After Notification Is Clicked Android

I am trying to change my class to to go to Login.java I have tried numerous solutions but can't seem to get it. I have a PromximityAlert set-up to check location and after that location is confirmed it will display the notification and when that notification is clicked, it will initiate the Login class.
Here is my code:
public class ProxAlertActivity extends Activity {
private static final long MINIMUM_DISTANCECHANGE_FOR_UPDATE = 1; // in Meters
private static final long MINIMUM_TIME_BETWEEN_UPDATE = 1000; // in Milliseconds
private static final long POINT_RADIUS = 1000; // in Meters
private static final long PROX_ALERT_EXPIRATION = -1;
private static final String POINT_LATITUDE_KEY = "POINT_LATITUDE_KEY";
private static final String POINT_LONGITUDE_KEY = "POINT_LONGITUDE_KEY";
private static final String PROX_ALERT_INTENT = "com.example.mysqltest.ProximityAlert";
private static final NumberFormat nf = new DecimalFormat("##.########");
private LocationManager locationManager;
private EditText latitudeEditText;
private EditText longitudeEditText;
private Button findCoordinatesButton;
private Button savePointButton;
#Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.main);
locationManager = (LocationManager) getSystemService(Context.LOCATION_SERVICE);
locationManager.requestLocationUpdates(
LocationManager.GPS_PROVIDER,
MINIMUM_TIME_BETWEEN_UPDATE,
MINIMUM_DISTANCECHANGE_FOR_UPDATE,
new MyLocationListener()
);
latitudeEditText = (EditText) findViewById(R.id.point_latitude);
longitudeEditText = (EditText) findViewById(R.id.point_longitude);
findCoordinatesButton = (Button) findViewById(R.id.find_coordinates_button);
savePointButton = (Button) findViewById(R.id.save_point_button);
findCoordinatesButton.setOnClickListener(new OnClickListener() {
#Override
public void onClick(View v) {
populateCoordinatesFromLastKnownLocation();
}
});
savePointButton.setOnClickListener(new OnClickListener() {
#Override
public void onClick(View v) {
saveProximityAlertPoint();
}
});
}
private void saveProximityAlertPoint() {
Location location = locationManager.getLastKnownLocation(LocationManager.GPS_PROVIDER);
if (location==null) {
Toast.makeText(this, "No last known location. Aborting...", Toast.LENGTH_LONG).show();
return;
}
saveCoordinatesInPreferences((float)location.getLatitude(), (float)location.getLongitude());
addProximityAlert(location.getLatitude(), location.getLongitude());
}
private void addProximityAlert(double latitude, double longitude) {
Intent intent = new Intent(PROX_ALERT_INTENT);
PendingIntent proximityIntent = PendingIntent.getBroadcast(this, 0, intent, 0);
locationManager.addProximityAlert(
41.69519672, // the latitude of the central point of the alert region
-87.80026184, // the longitude of the central point of the alert region
POINT_RADIUS, // the radius of the central point of the alert region, in meters
PROX_ALERT_EXPIRATION, // time for this proximity alert, in milliseconds, or -1 to indicate no expiration
proximityIntent // will be used to generate an Intent to fire when entry to or exit from the alert region is detected
);
IntentFilter filter = new IntentFilter(PROX_ALERT_INTENT);
registerReceiver(new ProximityIntentReceiver(), filter);
}
private void populateCoordinatesFromLastKnownLocation() {
Location location = locationManager.getLastKnownLocation(LocationManager.GPS_PROVIDER);
if (location!=null) {
latitudeEditText.setText(nf.format(location.getLatitude()));
longitudeEditText.setText(nf.format(location.getLongitude()));
}
}
private void saveCoordinatesInPreferences(float latitude, float longitude) {
SharedPreferences prefs = this.getSharedPreferences(getClass().getSimpleName(), Context.MODE_PRIVATE);
SharedPreferences.Editor prefsEditor = prefs.edit();
prefsEditor.putFloat(POINT_LATITUDE_KEY, latitude);
prefsEditor.putFloat(POINT_LONGITUDE_KEY, longitude);
prefsEditor.commit();
}
private Location retrievelocationFromPreferences() {
SharedPreferences prefs = this.getSharedPreferences(getClass().getSimpleName(), Context.MODE_PRIVATE);
Location location = new Location("POINT_LOCATION");
location.setLatitude(prefs.getFloat(POINT_LATITUDE_KEY, 0));
location.setLongitude(prefs.getFloat(POINT_LONGITUDE_KEY, 0));
return location;
}
public class MyLocationListener implements LocationListener {
public void onLocationChanged(Location location) {
Location pointLocation = retrievelocationFromPreferences();
float distance = location.distanceTo(pointLocation);
Toast.makeText(ProxAlertActivity.this,
"Distance from Point:"+distance, Toast.LENGTH_LONG).show();
}
public void onStatusChanged(String s, int i, Bundle b) {
}
public void onProviderDisabled(String s) {
}
public void onProviderEnabled(String s) {
}
}
}
public class ProximityIntentReceiver extends BroadcastReceiver {
private static final int NOTIFICATION_ID = 1000;
#Override
public void onReceive(Context context, Intent intent) {
String key = LocationManager.KEY_PROXIMITY_ENTERING;
Boolean entering = intent.getBooleanExtra(key, false);
if (entering) {
Log.d(getClass().getSimpleName(), "entering");
}
else {
Log.d(getClass().getSimpleName(), "exiting");
}
NotificationManager notificationManager =
(NotificationManager) context.getSystemService(Context.NOTIFICATION_SERVICE);
PendingIntent pendingIntent = PendingIntent.getActivity(context, 0, intent, 0);
Notification notification = createNotification();
notification.setLatestEventInfo(context, "Proximity Alert!", "You are near your point of interest.", pendingIntent);
notificationManager.notify(NOTIFICATION_ID, notification);
}
private Notification createNotification() {
Notification notification = new Notification();
notification.icon = R.drawable.ic_menu_notifications;
notification.when = System.currentTimeMillis();
notification.flags |= Notification.FLAG_AUTO_CANCEL;
notification.flags |= Notification.FLAG_SHOW_LIGHTS;
notification.defaults |= Notification.DEFAULT_VIBRATE;
notification.defaults |= Notification.DEFAULT_LIGHTS;
notification.ledARGB = Color.WHITE;
notification.ledOnMS = 1500;
notification.ledOffMS = 1500;
return notification;
}
}
Add this , I think its missing
Intent intent = new Intent(this, NotificationReceiver.class);
PendingIntent pendingIntent = PendingIntent.getActivity(this, 0, intent, 0);
notification.setContentIntent(pendingIntent );

Categories

Resources