diff --git a/app/src/main/java/eu/faircode/email/EntityRule.java b/app/src/main/java/eu/faircode/email/EntityRule.java index bb03925887..3722304656 100644 --- a/app/src/main/java/eu/faircode/email/EntityRule.java +++ b/app/src/main/java/eu/faircode/email/EntityRule.java @@ -1428,6 +1428,7 @@ public class EntityRule { private boolean onActionSound(Context context, EntityMessage message, JSONObject jargs) throws JSONException { Uri uri = (jargs.has("uri") ? Uri.parse(jargs.getString("uri")) : null); + boolean loop = jargs.getBoolean("loop"); boolean alarm = jargs.getBoolean("alarm"); int duration = jargs.optInt("duration", MediaPlayerHelper.DEFAULT_ALARM_DURATION); Log.i("Sound uri=" + uri + " alarm=" + alarm + " duration=" + duration); @@ -1438,7 +1439,7 @@ public class EntityRule { db.message().setMessageUiSilent(message.id, message.ui_silent); if (uri != null) - MediaPlayerHelper.queue(context, uri, alarm, duration); + MediaPlayerHelper.queue(context, uri, loop, alarm, duration); return true; } diff --git a/app/src/main/java/eu/faircode/email/FragmentRule.java b/app/src/main/java/eu/faircode/email/FragmentRule.java index 4b45038b36..c9771686bd 100644 --- a/app/src/main/java/eu/faircode/email/FragmentRule.java +++ b/app/src/main/java/eu/faircode/email/FragmentRule.java @@ -173,6 +173,7 @@ public class FragmentRule extends FragmentBase { private Button btnTtsData; private Button btnSound; + private CheckBox cbLoop; private CheckBox cbAlarm; private EditText etAlarmDuration; @@ -380,6 +381,7 @@ public class FragmentRule extends FragmentBase { btnTtsData = view.findViewById(R.id.btnTtsData); btnSound = view.findViewById(R.id.btnSound); + cbLoop = view.findViewById(R.id.cbLoop); cbAlarm = view.findViewById(R.id.cbAlarm); etAlarmDuration = view.findViewById(R.id.etAlarmDuration); @@ -1455,8 +1457,10 @@ public class FragmentRule extends FragmentBase { case EntityRule.TYPE_SOUND: if (jaction.has("uri")) FragmentRule.this.sound = Uri.parse(jaction.getString("uri")); + boolean loop = jaction.optBoolean("loop"); boolean alarm = jaction.optBoolean("alarm"); int duration = jaction.optInt("duration", 0); + cbLoop.setChecked(loop); cbAlarm.setChecked(alarm); etAlarmDuration.setEnabled(alarm); etAlarmDuration.setText(duration == 0 ? null : Integer.toString(duration)); @@ -1884,9 +1888,11 @@ public class FragmentRule extends FragmentBase { break; case EntityRule.TYPE_SOUND: + boolean loop = cbLoop.isChecked(); boolean alarm = cbAlarm.isChecked(); String duration = etAlarmDuration.getText().toString(); jaction.put("uri", sound); + jaction.put("loop", loop); jaction.put("alarm", alarm); if (alarm && !TextUtils.isEmpty(duration)) try { diff --git a/app/src/main/java/eu/faircode/email/MediaPlayerHelper.java b/app/src/main/java/eu/faircode/email/MediaPlayerHelper.java index 8f23317b24..9a13e58784 100644 --- a/app/src/main/java/eu/faircode/email/MediaPlayerHelper.java +++ b/app/src/main/java/eu/faircode/email/MediaPlayerHelper.java @@ -63,13 +63,13 @@ public class MediaPlayerHelper { static void queue(Context context, String uri) { try { - queue(context, Uri.parse(uri), false, DEFAULT_SOUND_DURATION); + queue(context, Uri.parse(uri), false, false, DEFAULT_SOUND_DURATION); } catch (Throwable ex) { Log.e(ex); } } - static void queue(Context context, Uri uri, boolean alarm, int duration) { + static void queue(Context context, Uri uri, boolean loop, boolean alarm, int duration) { Log.i("Queuing sound=" + uri); Helper.getMediaTaskExecutor().submit(new Runnable() { @@ -78,7 +78,7 @@ public class MediaPlayerHelper { try { if (!alarm && (isInCall(context) || isDnd(context))) return; - play(context, uri, alarm, duration); + play(context, uri, loop, alarm, duration); } catch (Throwable ex) { Log.e(ex); } @@ -86,12 +86,12 @@ public class MediaPlayerHelper { }); } - private static void play(Context context, Uri uri, boolean alarm, int duration) throws IOException { + private static void play(Context context, Uri uri, boolean loop, boolean alarm, int duration) throws IOException { synchronized (lock) { sem = new Semaphore(0); } - Log.i("Playing sound=" + uri); + Log.i("Playing alarm=" + alarm + " loop=" + loop + " sound=" + uri); AudioAttributes attrs = new AudioAttributes.Builder() .setContentType(AudioAttributes.CONTENT_TYPE_SONIFICATION) @@ -102,7 +102,7 @@ public class MediaPlayerHelper { try { mediaPlayer.setAudioAttributes(attrs); mediaPlayer.setDataSource(context.getApplicationContext(), uri); - mediaPlayer.setLooping(false); + mediaPlayer.setLooping(loop); mediaPlayer.setOnPreparedListener(new MediaPlayer.OnPreparedListener() { @Override public void onPrepared(MediaPlayer mp) { diff --git a/app/src/main/res/layout/fragment_rule.xml b/app/src/main/res/layout/fragment_rule.xml index 51bc147a74..edf66f32d2 100644 --- a/app/src/main/res/layout/fragment_rule.xml +++ b/app/src/main/res/layout/fragment_rule.xml @@ -1293,6 +1293,15 @@ app:layout_constraintStart_toStartOf="parent" app:layout_constraintTop_toBottomOf="@id/btnTtsData" /> + + + app:layout_constraintTop_toBottomOf="@id/cbLoop" /> Select sound Ringtone Audio file + Loop sound Use as alarm This will ignore "do not disturb" rules Maximum alarm duration (seconds)