[英]Why foreground Service not working after removing app from the background?
I have been trying to implement foreground service to get location after every 3 sec even when the app is in the background by showing a notification. 即使应用程序在后台显示通知,我也一直在尝试实施前台服务,以便每隔3秒获取一次位置。 But when I remove my app from the background notification also removes. 但是当我从后台删除我的应用时,通知也会删除。 However, this is only occurring when I am doing it in MI REDMI NOTE 5(API version 28) and MI REDMI NOTE 4(API version 24) but when I ran the same app in Samsung J5(API version 23), the notification is showing even when the app is removed from background until it is manually stopped from the activity. 但是,这只发生在MI REDMI NOTE 5(API版本28)和MI REDMI NOTE 4(API版本24)中,但是当我在Samsung J5(API版本23)中运行相同的应用程序时,通知是甚至在应用程序从后台删除,直到从活动中手动停止为止。 Is the varied result behavior is due to change in API or is it because of different phone model? 变化的结果行为是由于API的变化还是因为不同的手机型号?
Here's my Service Class 这是我的服务类
package com.example.locationrunandall;
import android.app.Notification;
import android.app.NotificationChannel;
import android.app.NotificationManager;
import android.app.Service;
import android.content.Intent;
import android.location.Location;
import android.os.Build;
import android.os.Handler;
import android.os.HandlerThread;
import android.os.IBinder;
import android.util.Log;
import androidx.annotation.NonNull;
import androidx.core.app.NotificationCompat;
import androidx.localbroadcastmanager.content.LocalBroadcastManager;
import com.google.android.gms.location.FusedLocationProviderClient;
import com.google.android.gms.location.LocationCallback;
import com.google.android.gms.location.LocationRequest;
import com.google.android.gms.location.LocationResult;
import com.google.android.gms.location.LocationServices;
import com.google.android.gms.tasks.OnCompleteListener;
import com.google.android.gms.tasks.Task;
public class ForeService extends Service {
private static final String PACKAGE_NAME =
"com.example.customizedforeground";
static final String ACTION_BROADCAST = PACKAGE_NAME + ".broadcast";
static final String EXTRA_LOCATION = PACKAGE_NAME + ".location";
private static final String EXTRA_STARTED_FROM_NOTIFICATION = PACKAGE_NAME +
".started_from_notification";
private Handler mServiceHandler;
private NotificationManager mNotificationManager;
// private Notification notification;
private LocationRequest mLocationRequest;
private FusedLocationProviderClient mFusedLocationClient;
private LocationCallback mLocationCallback;
private Location mLocation;
private static final String CHANNEL_ID = "CHANNEL_ONE";
private static final int NOTIFICATION_ID = 4567123;
private static final String TAG = "123";
String loc;
public ForeService(){}
@Override
public void onCreate() {
mFusedLocationClient = LocationServices.getFusedLocationProviderClient(this);
mLocationCallback = new LocationCallback(){
@Override
public void onLocationResult(LocationResult locationResult) {
super.onLocationResult(locationResult);
//Do Location Work You Want To Do
onNewLocation(locationResult.getLastLocation());
}
};
mLocationRequest = new LocationRequest();
mLocationRequest.setInterval(3*1000);
mLocationRequest.setFastestInterval(1000);
mLocationRequest.setPriority(LocationRequest.PRIORITY_HIGH_ACCURACY);
getLastLocation();
HandlerThread handlerThread = new HandlerThread("HANDLER");
handlerThread.start();
mServiceHandler = new Handler(handlerThread.getLooper());
mNotificationManager = (NotificationManager) getSystemService(NOTIFICATION_SERVICE);
CharSequence name = "Name Charseq";
if(Build.VERSION.SDK_INT>= Build.VERSION_CODES.O){
NotificationChannel notificationChannel = new
NotificationChannel(CHANNEL_ID,name, NotificationManager.IMPORTANCE_DEFAULT);
mNotificationManager.createNotificationChannel(notificationChannel);
}
startForeground(NOTIFICATION_ID,getNotification());
}
@Override
public int onStartCommand(Intent intent, int flags, int startId) {
// startForeground(NOTIFICATION_ID,getNotification());
return START_NOT_STICKY;
}
@Override
public void onDestroy() {
mServiceHandler.removeCallbacksAndMessages(null);
//stopForeground(true);
}
@androidx.annotation.Nullable
@Override
public IBinder onBind(Intent intent) {
return null;
}
private void getLastLocation() {
try {
mFusedLocationClient.getLastLocation()
.addOnCompleteListener(new OnCompleteListener<Location>() {
@Override
public void onComplete(@NonNull Task<Location> task) {
if (task.isSuccessful() && task.getResult() != null) {
mLocation = task.getResult();
} else {
Log.d(TAG, "Failed to get location.");
}
}
});
} catch (SecurityException unlikely) {
Log.d(TAG, "Lost location permission." + unlikely);
}
}
private void onNewLocation(Location location) {
mLocation = location;
if(mLocation==null)
Log.d("DSK_OPER","Lat: = "+"Not known");
else
Log.d("DSK_OPER"," : "+location.getLatitude());
//send intent to broadcast reciever
Intent intent = new Intent(ACTION_BROADCAST);
intent.putExtra(EXTRA_LOCATION, location);
LocalBroadcastManager.getInstance(getApplicationContext()).sendBroadcast(intent);
// todo - Write More code here
mNotificationManager.notify(NOTIFICATION_ID,getNotification());
}
private Notification getNotification() {
//Intent intent = new Intent(this,MainActivity.class);
if(mLocation==null)
loc = "unknown loc";
else
loc = String.valueOf(mLocation.getLatitude());
NotificationCompat.Builder builder = new NotificationCompat.Builder(this)
.setContentTitle("Latitude and longitude")
.setContentText(" = "+loc)
.setOngoing(true)
.setPriority(Notification.PRIORITY_HIGH)
.setSmallIcon(R.mipmap.ic_launcher)
.setWhen(System.currentTimeMillis());
// Set the Channel ID for Android O.
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.O) {
builder.setChannelId(CHANNEL_ID);
}
return builder.build();
}
}
I am using the foreground service for location update after some interval. 我在一段时间后使用前台服务进行位置更新。 Foreground service is useful when you wants to update the location if your app is in background but not killed. 如果您想要在应用程序处于后台但未被杀死的情况下更新位置,则前台服务非常有用。 But this is your responsibility to stop the foreground service when your app is killed. 但是,当您的应用程序被杀时,您有责任停止前台服务。 So you just implement the LifeCycleDelegate so that you can start the service when app is in background and stop the service when app is in foreground. 因此,您只需实现LifeCycleDelegate,以便在应用程序处于后台时启动服务,并在应用程序处于前台时停止服务。 and also kill the service when your main activity or HomeActivity is killed. 并在主要活动或HomeActivity被杀死时终止服务。 this is the code for AppLifecycleHandler. 这是AppLifecycleHandler的代码。
internal class AppLifecycleHandler(private val lifeCycleDelegate: LifeCycleDelegate) : Application.ActivityLifecycleCallbacks,
ComponentCallbacks2 {
private var appInForeground = false
override fun onActivityPaused(p0: Activity?) {}
/**
* app resumed
*/
override fun onActivityResumed(p0: Activity?) {
if (!appInForeground) {
appInForeground = true
lifeCycleDelegate.onAppForegrounded()
}
}
override fun onActivityStarted(p0: Activity?) {
}
override fun onActivityDestroyed(p0: Activity?) {
}
override fun onActivitySaveInstanceState(p0: Activity?, p1: Bundle?) {
}
override fun onActivityStopped(p0: Activity?) {
}
override fun onActivityCreated(p0: Activity?, p1: Bundle?) {
}
override fun onLowMemory() {}
override fun onConfigurationChanged(p0: Configuration?) {}
/**
* app sent to background
*/
override fun onTrimMemory(level: Int) {
if (level == ComponentCallbacks2.TRIM_MEMORY_UI_HIDDEN) {
appInForeground = false
lifeCycleDelegate.onAppBackgrounded()
}
}
Add this method to your application class private fun registerLifecycleHandler(lifeCycleHandler: AppLifecycleHandler) { registerActivityLifecycleCallbacks(lifeCycleHandler) registerComponentCallbacks(lifeCycleHandler) } 将此方法添加到您的应用程序类private fun registerLifecycleHandler(lifeCycleHandler:AppLifecycleHandler){registerActivityLifecycleCallbacks(lifeCycleHandler)registerComponentCallbacks(lifeCycleHandler)}
override fun getLifecycle(): Lifecycle {
return mLifecycleRegistry
}
implements LifeCycleDelegate in your application class and override the methods 在您的应用程序类中实现LifeCycleDelegate并覆盖这些方法
internal interface LifeCycleDelegate {
fun onAppBackgrounded()
fun onAppForegrounded()
} }
create app object in application class 在应用程序类中创建app对象
val lifeCycleHandler = AppLifecycleHandler(this)
registerLifecycleHandler(lifeCycleHandler)
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.