dbarnes
dbarnes

Reputation: 539

Android using a Wake Lock with Foreground service?

I'm working on an audio app utilizing exoplayer in a foreground service to allow the audio to play with the screen off. This appears to work as intended, but somewhere I read something about adding Wake Locks.

Is that something that would be necessary with a foreground service? The Wake Lock is used to keep the CPU awake, but the foreground service seems to do that while the service is playing.

I decided to test it on the way to work and it played audio with the screen off for +20 minutes without problems. I assume ~20 mins would be long enough for the OS to shut something down without a wake lock.

Upvotes: 5

Views: 1955

Answers (1)

Dev4Life
Dev4Life

Reputation: 3317

Yes, Wake lock is used when you start the service again after the device has been rebooted or when the service is killed.

Use it like this:

  1. Create BroadcastReceiver for receiving the broadcast to start a service.

    public class AutoStart extends BroadcastReceiver {
      LocalReceiver localReceiver = new LocalReceiver();
         public void onReceive(Context context, Intent intent) {
             if (intent.getAction().equals(Intent.ACTION_BOOT_COMPLETED)) {
             Intent intent2 = new Intent(context, YourService.class);
             if (Build.VERSION.SDK_INT >= 26)
                 context.startForegroundService(intent2);
             else
                 context.startService(intent2);
            localReceiver.startMainService(context); //It will create a receiver to receive the broadcast & start your service in it's `onReceive()`.
          }
       }
    }
    
  2. Register that receiver in the Manifest with ACTION_BOOT_COMPLETED intent-filter.

    <receiver android:name="com.demo.service.service_manager.AutoStart">
        <intent-filter>
          <action android:name="android.intent.action.BOOT_COMPLETED"/>
        </intent-filter>
    </receiver>
    
  3. Now we have created the receiver which will receive a broadcast only one time when the device is rebooted. So we have to use wakelock manager to keep the register our service within a limited time.

  4. Now, create the broadcast receiver which will be used to receive the broadcast to start the service.

    public class LocalReceiver extends BroadcastReceiver {
        PowerManager.WakeLock wakeLock = ((PowerManager) context.getSystemService(Context.POWER_SERVICE)).wakeLock(PowerManager.PARTIAL_WAKE_LOCK, ":YourService");
        wakeLock.acquire(60 * 1L); //It will keep the device awake & register the service within 1 minute time duration.
        context.getPackageManager().setComponentEnabledSetting(new ComponentName(context, YourService.class), 1, 1);
    
        playMusic(); //Play your audio here.
    
        wakeLock.release(); //Don't forget to add this line when using the wakelock
    }
    

Now create a method in LocalReceiver to send the broadcast to start the service.

public void startMainService(Context context) {
    PendingIntent broadcast = PendingIntent.getBroadcast(context, REQUEST_CODE, new Intent(context, LocalReceiver.class), 0);
}

That's it! We've successfully implemented the wake lock. Now, whenever you want to play a sound. Just send the broadcast to the LocalReceiver & it will get your job done.

Also, don't forget to register this receiver in the Manifest as well as add android:enabled="true" and android:exported="true" where you register your service in Manifest.

<receiver android:name="com.demo.service.service_manager.LocalReceiver">

NOTE : We have used playMusic() inside the onReceive(). So it will also play the audio when the device is rebooted & the service will be registered. If you just want to bind the service on reboot, then you can simply add startService() method inside the onReceive() instead of the playMusic().

Upvotes: 1

Related Questions