Browse Source

Fix #210

Signed-off-by: Mario Danic <mario@lovelyhq.com>
Mario Danic 6 years ago
parent
commit
77f8652177

+ 1 - 0
app/src/main/AndroidManifest.xml

@@ -26,6 +26,7 @@
     <uses-permission android:name="android.permission.ACCESS_WIFI_STATE"/>
     <uses-permission android:name="android.permission.ACCESS_WIFI_STATE"/>
     <uses-permission android:name="android.permission.CHANGE_NETWORK_STATE"/>
     <uses-permission android:name="android.permission.CHANGE_NETWORK_STATE"/>
     <uses-permission android:name="android.permission.MODIFY_AUDIO_SETTINGS"/>
     <uses-permission android:name="android.permission.MODIFY_AUDIO_SETTINGS"/>
+    <uses-permission android:name="android.permission.VIBRATE"/>
 
 
     <uses-permission
     <uses-permission
         android:name="android.permission.USE_CREDENTIALS"
         android:name="android.permission.USE_CREDENTIALS"

+ 45 - 2
app/src/main/java/com/nextcloud/talk/controllers/CallNotificationController.java

@@ -21,11 +21,17 @@
 package com.nextcloud.talk.controllers;
 package com.nextcloud.talk.controllers;
 
 
 import android.annotation.SuppressLint;
 import android.annotation.SuppressLint;
+import android.content.Context;
 import android.graphics.Bitmap;
 import android.graphics.Bitmap;
 import android.graphics.drawable.BitmapDrawable;
 import android.graphics.drawable.BitmapDrawable;
+import android.media.AudioManager;
 import android.media.MediaPlayer;
 import android.media.MediaPlayer;
 import android.net.Uri;
 import android.net.Uri;
+import android.os.Build;
 import android.os.Bundle;
 import android.os.Bundle;
+import android.os.Handler;
+import android.os.VibrationEffect;
+import android.os.Vibrator;
 import android.renderscript.Allocation;
 import android.renderscript.Allocation;
 import android.renderscript.Element;
 import android.renderscript.Element;
 import android.renderscript.RenderScript;
 import android.renderscript.RenderScript;
@@ -136,6 +142,8 @@ public class CallNotificationController extends BaseController {
     private MediaPlayer mediaPlayer;
     private MediaPlayer mediaPlayer;
     private boolean leavingScreen = false;
     private boolean leavingScreen = false;
     private RenderScript renderScript;
     private RenderScript renderScript;
+    private Vibrator vibrator;
+    private Handler handler;
 
 
     public CallNotificationController(Bundle args) {
     public CallNotificationController(Bundle args) {
         super(args);
         super(args);
@@ -325,9 +333,38 @@ public class CallNotificationController extends BaseController {
             if (ringtoneUri != null) {
             if (ringtoneUri != null) {
                 mediaPlayer = MediaPlayer.create(getApplicationContext(), ringtoneUri);
                 mediaPlayer = MediaPlayer.create(getApplicationContext(), ringtoneUri);
                 mediaPlayer.setLooping(true);
                 mediaPlayer.setLooping(true);
+                mediaPlayer.setAudioStreamType(AudioManager.STREAM_RING);
                 mediaPlayer.start();
                 mediaPlayer.start();
             }
             }
         }
         }
+
+        if (DoNotDisturbUtils.shouldVibrate(appPreferences.getShouldVibrateSetting())) {
+            vibrator = (Vibrator) getApplicationContext().getSystemService(Context.VIBRATOR_SERVICE);
+
+            if (vibrator != null) {
+                long[] vibratePattern = new long[]{0, 400, 800, 600, 800, 800, 800, 1000};
+                int[] amplitudes = new int[]{0, 255, 0, 255, 0, 255, 0, 255};
+
+                VibrationEffect vibrationEffect;
+                if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.O) {
+                    if (vibrator.hasAmplitudeControl()) {
+                        vibrationEffect = VibrationEffect.createWaveform(vibratePattern, amplitudes, 0);
+                        vibrator.vibrate(vibrationEffect);
+                    } else {
+                        vibrationEffect = VibrationEffect.createWaveform(vibratePattern, 0);
+                        vibrator.vibrate(vibrationEffect);
+                    }
+                } else {
+                    vibrator.vibrate(vibratePattern, 0);
+                }
+            }
+
+            handler.postDelayed(() -> {
+                if (vibrator != null) {
+                    vibrator.cancel();
+                }
+            }, 10000);
+        }
     }
     }
 
 
 
 
@@ -429,7 +466,7 @@ public class CallNotificationController extends BaseController {
         }
         }
     }
     }
 
 
-    private void endMediaPlayer() {
+    private void endMediaAndVibratorNotifications() {
         if (mediaPlayer != null) {
         if (mediaPlayer != null) {
             if (mediaPlayer.isPlaying()) {
             if (mediaPlayer.isPlaying()) {
                 mediaPlayer.stop();
                 mediaPlayer.stop();
@@ -438,14 +475,20 @@ public class CallNotificationController extends BaseController {
             mediaPlayer.release();
             mediaPlayer.release();
             mediaPlayer = null;
             mediaPlayer = null;
         }
         }
+
+        if (vibrator != null) {
+            vibrator.cancel();
+        }
     }
     }
 
 
     @Override
     @Override
     public void onDestroy() {
     public void onDestroy() {
         AvatarStatusCodeHolder.getInstance().setStatusCode(0);
         AvatarStatusCodeHolder.getInstance().setStatusCode(0);
         leavingScreen = true;
         leavingScreen = true;
+        handler.removeCallbacksAndMessages(null);
+        handler = null;
         dispose();
         dispose();
-        endMediaPlayer();
+        endMediaAndVibratorNotifications();
         super.onDestroy();
         super.onDestroy();
     }
     }
 
 

+ 10 - 1
app/src/main/java/com/nextcloud/talk/controllers/SettingsController.java

@@ -54,17 +54,19 @@ import com.nextcloud.talk.jobs.AccountRemovalJob;
 import com.nextcloud.talk.models.RingtoneSettings;
 import com.nextcloud.talk.models.RingtoneSettings;
 import com.nextcloud.talk.models.database.UserEntity;
 import com.nextcloud.talk.models.database.UserEntity;
 import com.nextcloud.talk.utils.ApiUtils;
 import com.nextcloud.talk.utils.ApiUtils;
-import com.nextcloud.talk.utils.singletons.ApplicationWideMessageHolder;
+import com.nextcloud.talk.utils.DoNotDisturbUtils;
 import com.nextcloud.talk.utils.bundle.BundleKeys;
 import com.nextcloud.talk.utils.bundle.BundleKeys;
 import com.nextcloud.talk.utils.database.user.UserUtils;
 import com.nextcloud.talk.utils.database.user.UserUtils;
 import com.nextcloud.talk.utils.glide.GlideApp;
 import com.nextcloud.talk.utils.glide.GlideApp;
 import com.nextcloud.talk.utils.preferences.AppPreferences;
 import com.nextcloud.talk.utils.preferences.AppPreferences;
 import com.nextcloud.talk.utils.preferences.MagicUserInputModule;
 import com.nextcloud.talk.utils.preferences.MagicUserInputModule;
+import com.nextcloud.talk.utils.singletons.ApplicationWideMessageHolder;
 import com.yarolegovich.mp.MaterialChoicePreference;
 import com.yarolegovich.mp.MaterialChoicePreference;
 import com.yarolegovich.mp.MaterialEditTextPreference;
 import com.yarolegovich.mp.MaterialEditTextPreference;
 import com.yarolegovich.mp.MaterialPreferenceCategory;
 import com.yarolegovich.mp.MaterialPreferenceCategory;
 import com.yarolegovich.mp.MaterialPreferenceScreen;
 import com.yarolegovich.mp.MaterialPreferenceScreen;
 import com.yarolegovich.mp.MaterialStandardPreference;
 import com.yarolegovich.mp.MaterialStandardPreference;
+import com.yarolegovich.mp.MaterialSwitchPreference;
 
 
 import net.orange_box.storebox.listeners.OnPreferenceValueChangedListener;
 import net.orange_box.storebox.listeners.OnPreferenceValueChangedListener;
 
 
@@ -146,6 +148,9 @@ public class SettingsController extends BaseController {
     @BindView(R.id.settings_client_cert)
     @BindView(R.id.settings_client_cert)
     MaterialStandardPreference certificateSetup;
     MaterialStandardPreference certificateSetup;
 
 
+    @BindView(R.id.settings_always_vibrate)
+    MaterialSwitchPreference shouldVibrateSwitchPreference;
+
     @BindView(R.id.message_text)
     @BindView(R.id.message_text)
     TextView messageText;
     TextView messageText;
 
 
@@ -207,6 +212,10 @@ public class SettingsController extends BaseController {
             licenceButton.setVisibility(View.GONE);
             licenceButton.setVisibility(View.GONE);
         }
         }
 
 
+        if (!DoNotDisturbUtils.hasVibrator()) {
+            shouldVibrateSwitchPreference.setVisibility(View.GONE);
+        }
+
         if (!TextUtils.isEmpty(getResources().getString(R.string.nc_privacy_url))) {
         if (!TextUtils.isEmpty(getResources().getString(R.string.nc_privacy_url))) {
             privacyButton.addPreferenceClickListener(view12 -> {
             privacyButton.addPreferenceClickListener(view12 -> {
                 Intent browserIntent = new Intent(Intent.ACTION_VIEW, Uri.parse(getResources().
                 Intent browserIntent = new Intent(Intent.ACTION_VIEW, Uri.parse(getResources().

+ 16 - 0
app/src/main/java/com/nextcloud/talk/jobs/NotificationJob.java

@@ -27,10 +27,13 @@ import android.content.Context;
 import android.content.Intent;
 import android.content.Intent;
 import android.graphics.Bitmap;
 import android.graphics.Bitmap;
 import android.graphics.BitmapFactory;
 import android.graphics.BitmapFactory;
+import android.media.AudioManager;
 import android.media.MediaPlayer;
 import android.media.MediaPlayer;
 import android.net.Uri;
 import android.net.Uri;
 import android.os.Build;
 import android.os.Build;
 import android.os.Bundle;
 import android.os.Bundle;
+import android.os.VibrationEffect;
+import android.os.Vibrator;
 import android.support.annotation.NonNull;
 import android.support.annotation.NonNull;
 import android.text.TextUtils;
 import android.text.TextUtils;
 import android.util.Base64;
 import android.util.Base64;
@@ -349,9 +352,22 @@ public class NotificationJob extends Job {
             if (soundUri != null & !ApplicationWideCurrentRoomHolder.getInstance().isInCall() &&
             if (soundUri != null & !ApplicationWideCurrentRoomHolder.getInstance().isInCall() &&
                     DoNotDisturbUtils.shouldPlaySound()) {
                     DoNotDisturbUtils.shouldPlaySound()) {
                 MediaPlayer mediaPlayer = MediaPlayer.create(context, soundUri);
                 MediaPlayer mediaPlayer = MediaPlayer.create(context, soundUri);
+                mediaPlayer.setAudioStreamType(AudioManager.STREAM_NOTIFICATION);
                 mediaPlayer.start();
                 mediaPlayer.start();
                 mediaPlayer.setOnCompletionListener(MediaPlayer::release);
                 mediaPlayer.setOnCompletionListener(MediaPlayer::release);
+            }
+
+
+            if (DoNotDisturbUtils.shouldVibrate(appPreferences.getShouldVibrateSetting())) {
+                Vibrator vibrator = (Vibrator) context.getSystemService(Context.VIBRATOR_SERVICE);
 
 
+                if (vibrator != null) {
+                    if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.O) {
+                        vibrator.vibrate(VibrationEffect.createOneShot(500, VibrationEffect.DEFAULT_AMPLITUDE));
+                    } else {
+                        vibrator.vibrate(500);
+                    }
+                }
             }
             }
         }
         }
     }
     }

+ 26 - 0
app/src/main/java/com/nextcloud/talk/utils/DoNotDisturbUtils.java

@@ -24,6 +24,7 @@ import android.app.NotificationManager;
 import android.content.Context;
 import android.content.Context;
 import android.media.AudioManager;
 import android.media.AudioManager;
 import android.os.Build;
 import android.os.Build;
+import android.os.Vibrator;
 
 
 import com.nextcloud.talk.application.NextcloudTalkApplication;
 import com.nextcloud.talk.application.NextcloudTalkApplication;
 
 
@@ -49,6 +50,31 @@ public class DoNotDisturbUtils {
                 shouldPlaySound = false;
                 shouldPlaySound = false;
             }
             }
         }
         }
+
         return shouldPlaySound;
         return shouldPlaySound;
     }
     }
+
+    public static boolean hasVibrator() {
+        Context context = NextcloudTalkApplication.getSharedApplication().getApplicationContext();
+        Vibrator vibrator = (Vibrator) context.getSystemService(Context.VIBRATOR_SERVICE);
+        return (vibrator != null && vibrator.hasVibrator());
+    }
+
+    public static boolean shouldVibrate(boolean vibrate) {
+
+        if (hasVibrator()) {
+            Context context = NextcloudTalkApplication.getSharedApplication().getApplicationContext();
+            AudioManager audioManager = (AudioManager) context.getSystemService(Context.AUDIO_SERVICE);
+
+            if (audioManager != null) {
+                if (vibrate) {
+                    return (audioManager.getRingerMode() != AudioManager.RINGER_MODE_SILENT);
+                } else {
+                    return (audioManager.getRingerMode() == AudioManager.RINGER_MODE_VIBRATE);
+                }
+            }
+        }
+
+        return false;
+    }
 }
 }

+ 12 - 0
app/src/main/java/com/nextcloud/talk/utils/preferences/AppPreferences.java

@@ -21,6 +21,7 @@
 package com.nextcloud.talk.utils.preferences;
 package com.nextcloud.talk.utils.preferences;
 
 
 import net.orange_box.storebox.annotations.method.ClearMethod;
 import net.orange_box.storebox.annotations.method.ClearMethod;
+import net.orange_box.storebox.annotations.method.DefaultValue;
 import net.orange_box.storebox.annotations.method.KeyByString;
 import net.orange_box.storebox.annotations.method.KeyByString;
 import net.orange_box.storebox.annotations.method.RegisterChangeListenerMethod;
 import net.orange_box.storebox.annotations.method.RegisterChangeListenerMethod;
 import net.orange_box.storebox.annotations.method.RemoveMethod;
 import net.orange_box.storebox.annotations.method.RemoveMethod;
@@ -178,6 +179,17 @@ public interface AppPreferences {
     @RemoveMethod
     @RemoveMethod
     void removeMessagesNotificationChannelUpgradeToV3();
     void removeMessagesNotificationChannelUpgradeToV3();
 
 
+    @KeyByString("notifications_vibrate")
+    @DefaultValue(1)
+    boolean getShouldVibrateSetting();
+
+    @KeyByString("notifications_vibrate")
+    void setVibrateSetting(boolean value);
+
+    @KeyByString("notifications_vibrate")
+    @RemoveMethod
+    void removeVibrateSetting();
+
     @ClearMethod
     @ClearMethod
     void clear();
     void clear();
 }
 }

+ 9 - 0
app/src/main/res/layout/controller_settings.xml

@@ -132,6 +132,15 @@
             apc:mp_key="@string/nc_settings_message_ringtone_key"
             apc:mp_key="@string/nc_settings_message_ringtone_key"
             apc:mp_title="@string/nc_settings_other_notifications_ringtone"/>
             apc:mp_title="@string/nc_settings_other_notifications_ringtone"/>
 
 
+        <com.yarolegovich.mp.MaterialSwitchPreference
+            android:id="@+id/settings_always_vibrate"
+            android:layout_width="match_parent"
+            android:layout_height="wrap_content"
+            apc:mp_key="@string/nc_settings_vibrate_key"
+            apc:mp_title="@string/nc_settings_vibrate"
+            apc:mp_summary="@string/nc_settings_vibrate_desc"
+            apc:mp_default_value="true"/>
+
     </com.yarolegovich.mp.MaterialPreferenceCategory>
     </com.yarolegovich.mp.MaterialPreferenceCategory>
 
 
 
 

+ 4 - 0
app/src/main/res/values/strings.xml

@@ -67,6 +67,10 @@
     <string name="nc_settings_message_ringtone_key" translatable="false">message_ringtone</string>
     <string name="nc_settings_message_ringtone_key" translatable="false">message_ringtone</string>
     <string name="nc_settings_default_ringtone" translatable="false">Librem by feandesign</string>
     <string name="nc_settings_default_ringtone" translatable="false">Librem by feandesign</string>
     <string name="nc_settings_no_ringtone">No sound</string>
     <string name="nc_settings_no_ringtone">No sound</string>
+    <string name="nc_settings_vibrate">Vibrate</string>
+    <string name="nc_settings_vibrate_desc">When enabled, phone will vibrate unless it\'s silenced</string>
+    <string name="nc_settings_vibrate_key" translatable="false">notifications_vibrate</string>
+
 
 
     <string name="nc_no_proxy">No proxy</string>
     <string name="nc_no_proxy">No proxy</string>
     <string name="nc_username">Username</string>
     <string name="nc_username">Username</string>