mirror of
https://codeberg.org/Freeyourgadget/Gadgetbridge
synced 2024-11-28 12:56:49 +01:00
Add support for exclusive audio focus
This pauses temporarily other apps that are playing sound while our notifications get spoken.
This commit is contained in:
parent
9ba96231c3
commit
9c68acce2e
@ -460,6 +460,7 @@ public class DeviceSettingsPreferenceConst {
|
||||
public static final String PREF_AUTO_REPLY_INCOMING_CALL = "pref_auto_reply_phonecall";
|
||||
public static final String PREF_AUTO_REPLY_INCOMING_CALL_DELAY = "pref_auto_reply_phonecall_delay";
|
||||
public static final String PREF_SPEAK_NOTIFICATIONS_ALOUD = "pref_speak_notifications_aloud";
|
||||
public static final String PREF_SPEAK_NOTIFICATIONS_FOCUS_EXCLUSIVE = "pref_speak_notifications_focus_exclusive";
|
||||
|
||||
public static final String PREF_CYCLING_SENSOR_PERSISTENCE_INTERVAL = "pref_cycling_persistence_interval";
|
||||
public static final String PREF_CYCLING_SENSOR_WHEEL_DIAMETER = "pref_cycling_wheel_diameter";
|
||||
|
@ -646,6 +646,8 @@ public class DeviceSpecificSettingsFragment extends AbstractPreferenceFragment i
|
||||
addPreferenceHandlerFor(PREF_CYCLING_SENSOR_PERSISTENCE_INTERVAL);
|
||||
addPreferenceHandlerFor(PREF_CYCLING_SENSOR_WHEEL_DIAMETER);
|
||||
|
||||
addPreferenceHandlerFor(PREF_SPEAK_NOTIFICATIONS_FOCUS_EXCLUSIVE);
|
||||
|
||||
addPreferenceHandlerFor("lock");
|
||||
|
||||
String sleepTimeState = prefs.getString(PREF_SLEEP_TIME, PREF_DO_NOT_DISTURB_OFF);
|
||||
|
@ -17,6 +17,7 @@
|
||||
package nodomain.freeyourgadget.gadgetbridge.service;
|
||||
|
||||
import android.content.SharedPreferences;
|
||||
import android.media.AudioManager;
|
||||
import android.os.Handler;
|
||||
import android.os.Looper;
|
||||
|
||||
@ -31,6 +32,8 @@ import nodomain.freeyourgadget.gadgetbridge.model.NotificationSpec;
|
||||
import nodomain.freeyourgadget.gadgetbridge.service.serial.AbstractSerialDeviceSupport;
|
||||
import nodomain.freeyourgadget.gadgetbridge.util.GBTextToSpeech;
|
||||
|
||||
import static nodomain.freeyourgadget.gadgetbridge.activities.devicesettings.DeviceSettingsPreferenceConst.PREF_SPEAK_NOTIFICATIONS_FOCUS_EXCLUSIVE;
|
||||
|
||||
public abstract class AbstractHeadphoneDeviceSupport extends AbstractSerialDeviceSupport {
|
||||
private static final Logger LOG = LoggerFactory.getLogger(AbstractHeadphoneDeviceSupport.class);
|
||||
private GBTextToSpeech gbTextToSpeech;
|
||||
@ -94,10 +97,26 @@ public abstract class AbstractHeadphoneDeviceSupport extends AbstractSerialDevic
|
||||
@Override
|
||||
public boolean connect() {
|
||||
getDeviceIOThread().start();
|
||||
gbTextToSpeech = new GBTextToSpeech(getContext(), new UtteranceProgressListener());
|
||||
final SharedPreferences prefs = GBApplication.getDeviceSpecificSharedPrefs(getDevice().getAddress());
|
||||
gbTextToSpeech = new GBTextToSpeech(getContext(), new UtteranceProgressListener(),
|
||||
prefs.getBoolean(PREF_SPEAK_NOTIFICATIONS_FOCUS_EXCLUSIVE, false) ?
|
||||
AudioManager.AUDIOFOCUS_GAIN_TRANSIENT_EXCLUSIVE :
|
||||
AudioManager.AUDIOFOCUS_GAIN_TRANSIENT_MAY_DUCK
|
||||
);
|
||||
return true;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onSendConfiguration(String config) {
|
||||
LOG.warn("ONSENDCONFIGURATION");
|
||||
if (PREF_SPEAK_NOTIFICATIONS_FOCUS_EXCLUSIVE.equals(config)) {
|
||||
final SharedPreferences prefs = GBApplication.getDeviceSpecificSharedPrefs(getDevice().getAddress());
|
||||
gbTextToSpeech.setAudioFocus(prefs.getBoolean(PREF_SPEAK_NOTIFICATIONS_FOCUS_EXCLUSIVE, false) ?
|
||||
AudioManager.AUDIOFOCUS_GAIN_TRANSIENT_EXCLUSIVE :
|
||||
AudioManager.AUDIOFOCUS_GAIN_TRANSIENT_MAY_DUCK);
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public void dispose() {
|
||||
gbTextToSpeech.shutdown();
|
||||
@ -113,6 +132,8 @@ public abstract class AbstractHeadphoneDeviceSupport extends AbstractSerialDevic
|
||||
@Override
|
||||
public void onDone(String utteranceId) {
|
||||
// LOG.debug("UtteranceProgressListener onDone.");
|
||||
|
||||
gbTextToSpeech.abandonFocus();
|
||||
if (utteranceId.equals("call")) {
|
||||
SharedPreferences prefs = GBApplication.getDeviceSpecificSharedPrefs(getDevice().getAddress());
|
||||
final int delayMillis = Integer.parseInt(prefs.getString(DeviceSettingsPreferenceConst.PREF_AUTO_REPLY_INCOMING_CALL_DELAY, "15")) * 1000;
|
||||
|
@ -17,10 +17,18 @@ public class GBTextToSpeech {
|
||||
private final Context context;
|
||||
private TextToSpeech textToSpeech;
|
||||
private boolean isConnected = false;
|
||||
private final AudioManager audioManager;
|
||||
private int audioFocus;
|
||||
|
||||
public GBTextToSpeech(Context context, UtteranceProgressListener callback) {
|
||||
public GBTextToSpeech(Context context, UtteranceProgressListener callback, int audioFocus) {
|
||||
this.context = context;
|
||||
initializeTTS(callback);
|
||||
this.audioManager = (AudioManager) context.getSystemService(Context.AUDIO_SERVICE);
|
||||
this.audioFocus = audioFocus;
|
||||
}
|
||||
|
||||
public void setAudioFocus(int audioFocus) {
|
||||
this.audioFocus = audioFocus;
|
||||
}
|
||||
|
||||
public boolean isConnected() {
|
||||
@ -51,6 +59,9 @@ public class GBTextToSpeech {
|
||||
}
|
||||
|
||||
public void speakNotification(String text) {
|
||||
int result = audioManager.requestAudioFocus(null, AudioManager.STREAM_MUSIC, this.audioFocus);
|
||||
if (AudioManager.AUDIOFOCUS_REQUEST_GRANTED != result)
|
||||
LOG.warn("AudioManager did not grant us the requested focus");
|
||||
Bundle params = new Bundle();
|
||||
params.putInt(TextToSpeech.Engine.KEY_PARAM_STREAM, AudioManager.STREAM_MUSIC);
|
||||
textToSpeech.speak(text, TextToSpeech.QUEUE_FLUSH, params, "notification");
|
||||
@ -63,5 +74,7 @@ public class GBTextToSpeech {
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
public void abandonFocus() {
|
||||
audioManager.abandonAudioFocus(null);
|
||||
}
|
||||
}
|
||||
|
@ -2807,6 +2807,9 @@
|
||||
<string name="pref_auto_reply_calls_delay_title">Automatic Answer Delay</string>
|
||||
<string name="pref_speak_notifications_aloud_summary">Notifications will be read aloud through the headphones</string>
|
||||
<string name="pref_speak_notifications_aloud_title">Speak Notifications Aloud</string>
|
||||
<string name="pref_speak_notifications_focus_exclusive_title">Pause audio of other applications</string>
|
||||
<string name="pref_speak_notifications_focus_exclusive_summary_on">Playback from other applications will be paused while the notification is spoken</string>
|
||||
<string name="pref_speak_notifications_focus_exclusive_summary_off">Playback volume of other applications will be lowered while the notification is spoken</string>
|
||||
<string name="pref_header_calls_and_notifications">Calls and notifications</string>
|
||||
<string name="pref_title_bottom_navigation_bar">Bottom navigation bar</string>
|
||||
<string name="pref_summary_bottom_navigation_bar_on">Switch between main screens using the navigation bar or horizontal swiping</string>
|
||||
|
@ -22,4 +22,11 @@
|
||||
android:key="pref_speak_notifications_aloud"
|
||||
android:summary="@string/pref_speak_notifications_aloud_summary"
|
||||
android:title="@string/pref_speak_notifications_aloud_title" />
|
||||
<SwitchPreferenceCompat
|
||||
android:defaultValue="false"
|
||||
android:icon="@drawable/ic_voice"
|
||||
android:key="pref_speak_notifications_focus_exclusive"
|
||||
android:summaryOff="@string/pref_speak_notifications_focus_exclusive_summary_off"
|
||||
android:summaryOn="@string/pref_speak_notifications_focus_exclusive_summary_on"
|
||||
android:title="@string/pref_speak_notifications_focus_exclusive_title" />
|
||||
</androidx.preference.PreferenceScreen>
|
Loading…
Reference in New Issue
Block a user