2
votes

I'm setting the NotificationCompat.Builder with:

.setSound(getNotificationSound(), AudioManager.STREAM_ALARM)
.setCategory(NotificationCompat.CATEGORY_ALARM)
.setPriority(NotificationCompat.PRIORITY_MAX)

among the other mandatory properties.

For the NotificationChannel that I'm using, I added:

.setBypassDnd(true)

For Oreo, the problem is that:

  • the fired notification doesn't have any sound when the phone is muted or on vibrate so it's not acting like an alarm

What's the point of Do not disturb custom exception toggle button from a notification category/channel? Can it help to achieve my goal because I didn't see any differences?

For versions older than Oreo, where I'm not using the NotificationChannel I have a behavior which I prefer:

  • notification sound works when the phone is muted but no vibration
  • notification sound AND vibration works when the phone is on vibration or with sound enabled

Any ideas how to solve this inconsistency?

1

1 Answers

0
votes

In the end I gave up using the notification channels for sound and vibration to get consistent results across Android versions.

channel.setSound(null, null);

and used the MediaPlayer and Vibrator instead with a helper class like this:

public class RingtoneAndVibrationPlayer extends ContextWrapper{

private MediaPlayer mMediaPlayer;
private Vibrator mVibrator;

public RingtoneAndVibrationPlayer(Context context) {
    super(context);
}

public void play() {
    try {
        mMediaPlayer = new MediaPlayer();
        mVibrator = (Vibrator) this.getSystemService(VIBRATOR_SERVICE);

        final Uri uri = Uri.parse(PreferenceHelper.getNotificationSound();

        mMediaPlayer.setDataSource(this, uri);
        if (PreferenceHelper.isRingtoneEnabled()) {
            mMediaPlayer.setAudioStreamType(AudioManager.STREAM_ALARM);
            mMediaPlayer.setLooping(PreferenceHelper.isRingtoneInsistent());
            mMediaPlayer.prepareAsync();
        }

        mMediaPlayer.setOnPreparedListener(new MediaPlayer.OnPreparedListener() {
            @Override
            public void onPrepared(MediaPlayer mp) {
                mMediaPlayer.start();
            }
        });

        if (PreferenceHelper.isVibrationEnabled()) {
            mVibrator.vibrate(new long[] {0, 500, 500, 500},
                    PreferenceHelper.isRingtoneInsistent() ? 2 : -1);
        }
    } catch (SecurityException | IOException e) {
        stop();
    }
}

public void stop() {
    if (mMediaPlayer != null && mVibrator != null) {
        mMediaPlayer.reset();
        mMediaPlayer.release();
        mMediaPlayer = null;
    }
    if (mVibrator != null) {
        mVibrator.cancel();
    }
}
}

The only dissadvantage that I see is that a user could manually change the sound and vibration settings of a notification channel which will play along with the ones above. In my case, this is discouraged by having explicit preferences for sound and vibration in the app's settings.