Foreground notification service not working in one plus devices
Asked Answered
L

2

6

Below is the code for starting the foreground service. It is working fine for many devices like Samsung, moto, Vivo, Oppo and also with Android version nougat and oreo, but not working on One plus devices. Can anyone let me know if any extra changes or permission is required to run in One plus device or if any emulator supports one plus phones.

public class ForegroundService extends Service {

private Context ctx;
private static final String PRIMARY_NOTIF_CHANNEL = "default";

@Override
public void onCreate() {
    super.onCreate();
    ctx = this;
    createNotificationService();
}

private void createNotificationService(){

    TelephonyManager mTelephonyManager = (TelephonyManager) ctx.getSystemService(TELEPHONY_SERVICE);
    if(mTelephonyManager != null)
        mTelephonyManager.listen(new CellTowerStateListener(ctx), PhoneStateListener.LISTEN_SIGNAL_STRENGTHS);

    Intent notificationIntent = new Intent(this, MainActivity.class);
    notificationIntent.setAction(Constants.ACTION.MAIN_ACTION);
    notificationIntent.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK
            | Intent.FLAG_ACTIVITY_CLEAR_TASK);
    //PendingIntent pendingIntent = PendingIntent.getActivity(this, 0, notificationIntent, 0);

    RemoteViews notificationView = new RemoteViews(this.getPackageName(), R.layout.notification);

    if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.O) {
        setupChannel();
    }

    Notification notification = new NotificationCompat.Builder(this, PRIMARY_NOTIF_CHANNEL)
            .setSmallIcon(R.mipmap.ic_launcher)
            .setColor(Color.parseColor("#00f6d8"))
            .setContent(notificationView)
            .setPriority(Notification.PRIORITY_MIN)
            .setOngoing(true).build();

    startForeground(Constants.NOTIFICATION_ID.FOREGROUND_SERVICE, notification);
}

@Override
public int onStartCommand(Intent intent, int flags, int startId)
{
    return START_REDELIVER_INTENT;
}

private void setupChannel(){
    NotificationManager notificationManager = (NotificationManager) getSystemService(Context.NOTIFICATION_SERVICE);
    NotificationChannel chan1;
    if (android.os.Build.VERSION.SDK_INT >= android.os.Build.VERSION_CODES.O) {
        chan1 = new NotificationChannel(
                PRIMARY_NOTIF_CHANNEL,
                PRIMARY_NOTIF_CHANNEL,
                NotificationManager.IMPORTANCE_NONE);

        chan1.setLightColor(Color.TRANSPARENT);
        chan1.setLockscreenVisibility(Notification.VISIBILITY_SECRET);

        if(notificationManager != null)
            notificationManager.createNotificationChannel(chan1);
    }
}


@Override
public IBinder onBind(Intent intent) {
    // Used only in case of bound services.
    return null;
}

}

Lalittah answered 4/12, 2018 at 11:48 Comment(6)
What you mean by foreground state is app open or close or terminated?Rademacher
check your console for errors if there is any.Mcgehee
which android version is running on one plus device?Mcgehee
@CGPA6.4 app gets closed, as my app is not having any UI. It behaves as a background service just shows the notification.Lalittah
@NoumanCh - android version is: OxygenOS Open Beta 17 | Android 8.1. I can't check the logs as no emulator is having one plus devices.Lalittah
Having exact same issue. @surbhiverma you found any solutions ? not work in one plus, work in other devices. if any one found solutions, please suggest.Humidifier
S
8

So I solved this question just one hour ago:

Manifest

<application
    android:name=".AppNotification"
    android:allowBackup="true"
    android:icon="@mipmap/pro_icon"
    android:label="@string/app_name"
    android:roundIcon="@mipmap/pro_icon"
    android:supportsRtl="true"
    android:theme="@style/AppTheme">
<service
        android:name=".services.TrackingBackgroundService"
        android:enabled="true"
        android:exported="true" />

Application - creating a notification channel

public class AppNotification extends Application {

public static final String CHANNEL_ID = "AppNotificationChannel";
private void CreateNotificationChannel() {
    if(Build.VERSION.SDK_INT >= Build.VERSION_CODES.O){
        NotificationChannel serviceChannel = new NotificationChannel(
                CHANNEL_ID,
                "App Notification",
                NotificationManager.IMPORTANCE_HIGH
        );
        NotificationManager manager = getSystemService(NotificationManager.class);
        manager.createNotificationChannel(serviceChannel);
    }
}

}

Activity

first you need to ask to the user to disable battery optimizations :

Intent intent = new Intent();
    String packageName = this.getPackageName();
    PowerManager pm = (PowerManager) this.getSystemService(Context.POWER_SERVICE);
    if (pm.isIgnoringBatteryOptimizations(packageName))
        intent.setAction(Settings.ACTION_IGNORE_BATTERY_OPTIMIZATION_SETTINGS);
    else {
        intent.setAction(Settings.ACTION_REQUEST_IGNORE_BATTERY_OPTIMIZATIONS);
        intent.setData(Uri.parse("package:" + packageName));
        startActivity(intent);
    }

then you need to start the service like this to handle different versions:

public void startService() {
    Intent serviceIntent = new Intent(InitSkipperActivity.this, TrackingBackgroundService.class);
    if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.O) {
        startForegroundService(serviceIntent);
    } else {
        startService(serviceIntent);
    }
}

Service

public class TrackingBackgroundService extends Service {

@Nullable
@Override
public IBinder onBind(Intent intent) {
    return null;
}

@Override
public void onCreate() {
    super.onCreate();
}

@Override
public int onStartCommand(Intent intent, int flags, int startId) {
    Intent notificationIntent = new Intent(this, TrackingActivity.class);
    notificationIntent.setFlags(Intent.FLAG_ACTIVITY_SINGLE_TOP);
    PendingIntent pendingIntent = PendingIntent.getActivity(this, 0, notificationIntent, 0);

    Notification notification = new NotificationCompat.Builder(this, CHANNEL_ID)
            .setContentTitle("title")
            .setContentText("content")
            .setSmallIcon(R.mipmap.pro_icon)
            .setPriority(5)
            .setContentIntent(pendingIntent)
            .build();
    startForeground(1, notification);

    return START_STICKY;
}

}

After this you need to test your service with the android profiler:

My app was with an abnormal CPU usage and on Oppo, OnePlus and Xiaomi and Samsung when I was offline tracking was using 50 to 60% CPU. found it was some threads that I called interrupt but were still running

after learning to use, start recording pieces of your app and analized them, you have 2 good options to start:

  • Sample Java Methods

  • Trace Java Methods

The Android Logcat its good to see the BG detect of oneplus trying to delete your service and if needed your app.

P.S: BGDetect eliminates without fear. I need to put my tracking performance both online and offline to an average of 20% to 30% in app and 15% to 20% on sleep before OnePlus and Oppo stop killing me without giving me the chance of rebooting my service.

As you probably already noticed when these OS want to kill something they start from the app an not from the service, keep in mind: DO NOT BOUND an app to a SERVICE if you do this I do not know why but the OS is even more relentless.

BG-Detect is too much -> they should've given the android devs the warning when reimplemented the function

P.P.S It's too much, but I take my hat OnePlus BugHunters, its damm well implemented.

Hope I could help.

tested on OP3 Oreo 8.0.1

Editted

OnePlus on reboot sets your app to optimized again. Am testing to fix the ussue

Suburb answered 18/5, 2019 at 1:16 Comment(3)
Hi @rmindzstar, have you fixed it for one plus device. I am having the same issue with one plus which having an Android 10 OS.Eddy
Only with all this setups and with a less than 10% of cpu usage. And in android 9. Above 12% I was shutdown. Could not find the real "crux" tho.. On all other devices it runs fineSuburb
Now it gives a warning: "Use of REQUEST_IGNORE_BATTERY_OPTIMIZATIONS violates the Play Store Content Policy regarding acceptable use cases, as described in developer.android.com/training/monitoring-device-state/…". I also get a "Error getting package info: com." when trying it.Uropod
B
0

Use my method work in all devices

 private void checkOptimization() {
    if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.M) {
        String packageName = getApplicationContext().getPackageName();
        PowerManager pm = (PowerManager) getApplicationContext().getSystemService(Context.POWER_SERVICE);
        if (pm != null) {
            if (!pm.isIgnoringBatteryOptimizations(packageName)) {
                Intent intent = new Intent();
                intent.setAction(Settings.ACTION_REQUEST_IGNORE_BATTERY_OPTIMIZATIONS);
                intent.setData(Uri.parse("package:" + getPackageName()));
                startActivity(intent);
            }
        }
    }

}
Benzoyl answered 18/6, 2020 at 10:6 Comment(0)

© 2022 - 2024 — McMap. All rights reserved.