diff --git a/AndroidManifest.xml b/AndroidManifest.xml index 6a3cd05962..819179fb66 100644 --- a/AndroidManifest.xml +++ b/AndroidManifest.xml @@ -494,7 +494,7 @@ android:label="@string/AndroidManifest_remove_photo" android:theme="@style/Theme.AppCompat.Dialog.Alert"> - + @@ -529,32 +529,6 @@ - - - - - - - - - - - - - - - - - - - @@ -563,48 +537,12 @@ - - - - - - - - - - - - - - - - - - - - - - - - - - - + - + - + - + @@ -674,7 +612,7 @@ - + @@ -709,12 +647,12 @@ - + - + @@ -724,7 +662,7 @@ - + - diff --git a/src/org/thoughtcrime/securesms/ExperienceUpgradeActivity.java b/src/org/thoughtcrime/securesms/ExperienceUpgradeActivity.java index 47f9b6b44f..d0de27204c 100644 --- a/src/org/thoughtcrime/securesms/ExperienceUpgradeActivity.java +++ b/src/org/thoughtcrime/securesms/ExperienceUpgradeActivity.java @@ -33,7 +33,7 @@ import network.loki.messenger.R; public class ExperienceUpgradeActivity extends BaseActionBarActivity implements TypingIndicatorIntroFragment.Controller, LinkPreviewsIntroFragment.Controller { private static final String TAG = ExperienceUpgradeActivity.class.getSimpleName(); - private static final String DISMISS_ACTION = "org.thoughtcrime.securesms.ExperienceUpgradeActivity.DISMISS_ACTION"; + private static final String DISMISS_ACTION = "network.loki.securesms.ExperienceUpgradeActivity.DISMISS_ACTION"; private static final int NOTIFICATION_ID = 1339; private enum ExperienceUpgrade { diff --git a/src/org/thoughtcrime/securesms/avatar/AvatarSelection.java b/src/org/thoughtcrime/securesms/avatar/AvatarSelection.java index 6886b27c8d..328cd20c8b 100644 --- a/src/org/thoughtcrime/securesms/avatar/AvatarSelection.java +++ b/src/org/thoughtcrime/securesms/avatar/AvatarSelection.java @@ -102,7 +102,7 @@ public final class AvatarSelection { } if (includeClear) { - extraIntents.add(new Intent("org.thoughtcrime.securesms.action.CLEAR_PROFILE_PHOTO")); + extraIntents.add(new Intent("network.loki.securesms.action.CLEAR_PROFILE_PHOTO")); } Intent chooserIntent = Intent.createChooser(galleryIntent, context.getString(R.string.CreateProfileActivity_profile_photo)); diff --git a/src/org/thoughtcrime/securesms/notifications/AndroidAutoHeardReceiver.java b/src/org/thoughtcrime/securesms/notifications/AndroidAutoHeardReceiver.java index ba1032f634..dfa974a1f8 100644 --- a/src/org/thoughtcrime/securesms/notifications/AndroidAutoHeardReceiver.java +++ b/src/org/thoughtcrime/securesms/notifications/AndroidAutoHeardReceiver.java @@ -37,7 +37,7 @@ import java.util.List; public class AndroidAutoHeardReceiver extends BroadcastReceiver { public static final String TAG = AndroidAutoHeardReceiver.class.getSimpleName(); - public static final String HEARD_ACTION = "org.thoughtcrime.securesms.notifications.ANDROID_AUTO_HEARD"; + public static final String HEARD_ACTION = "network.loki.securesms.notifications.ANDROID_AUTO_HEARD"; public static final String THREAD_IDS_EXTRA = "car_heard_thread_ids"; public static final String NOTIFICATION_ID_EXTRA = "car_notification_id"; diff --git a/src/org/thoughtcrime/securesms/notifications/AndroidAutoReplyReceiver.java b/src/org/thoughtcrime/securesms/notifications/AndroidAutoReplyReceiver.java index c6c91ab02f..d196fe432e 100644 --- a/src/org/thoughtcrime/securesms/notifications/AndroidAutoReplyReceiver.java +++ b/src/org/thoughtcrime/securesms/notifications/AndroidAutoReplyReceiver.java @@ -44,7 +44,7 @@ import java.util.List; public class AndroidAutoReplyReceiver extends BroadcastReceiver { public static final String TAG = AndroidAutoReplyReceiver.class.getSimpleName(); - public static final String REPLY_ACTION = "org.thoughtcrime.securesms.notifications.ANDROID_AUTO_REPLY"; + public static final String REPLY_ACTION = "network.loki.securesms.notifications.ANDROID_AUTO_REPLY"; public static final String ADDRESS_EXTRA = "car_address"; public static final String VOICE_REPLY_KEY = "car_voice_reply_key"; public static final String THREAD_ID_EXTRA = "car_reply_thread_id"; diff --git a/src/org/thoughtcrime/securesms/notifications/DeleteNotificationReceiver.java b/src/org/thoughtcrime/securesms/notifications/DeleteNotificationReceiver.java index be541f2add..ea065fd18a 100644 --- a/src/org/thoughtcrime/securesms/notifications/DeleteNotificationReceiver.java +++ b/src/org/thoughtcrime/securesms/notifications/DeleteNotificationReceiver.java @@ -10,7 +10,7 @@ import org.thoughtcrime.securesms.database.DatabaseFactory; public class DeleteNotificationReceiver extends BroadcastReceiver { - public static String DELETE_NOTIFICATION_ACTION = "org.thoughtcrime.securesms.DELETE_NOTIFICATION"; + public static String DELETE_NOTIFICATION_ACTION = "network.loki.securesms.DELETE_NOTIFICATION"; public static String EXTRA_IDS = "message_ids"; public static String EXTRA_MMS = "is_mms"; diff --git a/src/org/thoughtcrime/securesms/notifications/MarkReadReceiver.java b/src/org/thoughtcrime/securesms/notifications/MarkReadReceiver.java index ed82b436a0..c6e7f1b784 100644 --- a/src/org/thoughtcrime/securesms/notifications/MarkReadReceiver.java +++ b/src/org/thoughtcrime/securesms/notifications/MarkReadReceiver.java @@ -35,7 +35,7 @@ import kotlin.contracts.Returns; public class MarkReadReceiver extends BroadcastReceiver { private static final String TAG = MarkReadReceiver.class.getSimpleName(); - public static final String CLEAR_ACTION = "org.thoughtcrime.securesms.notifications.CLEAR"; + public static final String CLEAR_ACTION = "network.loki.securesms.notifications.CLEAR"; public static final String THREAD_IDS_EXTRA = "thread_ids"; public static final String NOTIFICATION_ID_EXTRA = "notification_id"; diff --git a/src/org/thoughtcrime/securesms/notifications/MessageNotifier.java b/src/org/thoughtcrime/securesms/notifications/MessageNotifier.java index 3a3ca331f9..9fb501ba7e 100644 --- a/src/org/thoughtcrime/securesms/notifications/MessageNotifier.java +++ b/src/org/thoughtcrime/securesms/notifications/MessageNotifier.java @@ -49,6 +49,7 @@ import org.thoughtcrime.securesms.database.model.MediaMmsMessageRecord; import org.thoughtcrime.securesms.database.model.MessageRecord; import org.thoughtcrime.securesms.database.model.MmsMessageRecord; import org.thoughtcrime.securesms.logging.Log; +import org.thoughtcrime.securesms.loki.MultiDeviceUtilities; import org.thoughtcrime.securesms.mms.SlideDeck; import org.thoughtcrime.securesms.recipients.Recipient; import org.thoughtcrime.securesms.service.IncomingMessageObserver; @@ -58,6 +59,8 @@ import org.thoughtcrime.securesms.util.SpanUtil; import org.thoughtcrime.securesms.util.TextSecurePreferences; import org.thoughtcrime.securesms.webrtc.CallNotificationBuilder; import org.whispersystems.signalservice.internal.util.Util; +import org.whispersystems.signalservice.loki.messaging.LokiThreadFriendRequestStatus; +import org.whispersystems.signalservice.loki.utilities.PromiseUtil; import java.util.HashSet; import java.util.List; @@ -70,6 +73,7 @@ import java.util.concurrent.atomic.AtomicBoolean; import me.leolin.shortcutbadger.ShortcutBadger; import network.loki.messenger.R; +import nl.komponents.kovenant.Promise; /** @@ -316,15 +320,39 @@ public class MessageNotifier { long timestamp = notifications.get(0).getTimestamp(); if (timestamp != 0) builder.setWhen(timestamp); + long threadId = notifications.get(0).getThreadId(); + ReplyMethod replyMethod = ReplyMethod.forRecipient(context, recipient); + + // We can only reply if we are friends with the user or we're messaging a group + boolean isGroup = recipient.isGroupRecipient(); + boolean isRSSFeed = isGroup && recipient.getAddress().isRSSFeed(); + boolean isFriend = false; + if (!isGroup) { + isFriend = DatabaseFactory.getLokiThreadDatabase(context).getFriendRequestStatus(threadId) == LokiThreadFriendRequestStatus.FRIENDS; + // If we're not friends then we need to check if we're friends with any of the linked devices + if (!isFriend) { + Promise promise = PromiseUtil.timeout(MultiDeviceUtilities.isFriendsWithAnyLinkedDevice(context, recipient), 5000); + isFriend = PromiseUtil.get(promise, false); + } + } + + boolean canReply = (isGroup && !isRSSFeed) || isFriend; + + PendingIntent quickReplyIntent = canReply ? notificationState.getQuickReplyIntent(context, recipient) : null; + PendingIntent remoteReplyIntent = canReply ? notificationState.getRemoteReplyIntent(context, recipient, replyMethod) : null; + builder.addActions(notificationState.getMarkAsReadIntent(context, notificationId), - /*notificationState.getQuickReplyIntent(context, notifications.get(0).getRecipient()),*/ - notificationState.getRemoteReplyIntent(context, notifications.get(0).getRecipient(), replyMethod), + quickReplyIntent, + remoteReplyIntent, replyMethod); - builder.addAndroidAutoAction(notificationState.getAndroidAutoReplyIntent(context, notifications.get(0).getRecipient()), - notificationState.getAndroidAutoHeardIntent(context, notificationId), notifications.get(0).getTimestamp()); + if (canReply) { + builder.addAndroidAutoAction(notificationState.getAndroidAutoReplyIntent(context, recipient), + notificationState.getAndroidAutoHeardIntent(context, notificationId), + notifications.get(0).getTimestamp()); + } ListIterator iterator = notifications.listIterator(notifications.size()); @@ -514,7 +542,7 @@ public class MessageNotifier { public static class ReminderReceiver extends BroadcastReceiver { - public static final String REMINDER_ACTION = "org.thoughtcrime.securesms.MessageNotifier.REMINDER_ACTION"; + public static final String REMINDER_ACTION = "network.loki.securesms.MessageNotifier.REMINDER_ACTION"; @SuppressLint("StaticFieldLeak") @Override diff --git a/src/org/thoughtcrime/securesms/notifications/RemoteReplyReceiver.java b/src/org/thoughtcrime/securesms/notifications/RemoteReplyReceiver.java index 1f36a125f9..7b42d10aca 100644 --- a/src/org/thoughtcrime/securesms/notifications/RemoteReplyReceiver.java +++ b/src/org/thoughtcrime/securesms/notifications/RemoteReplyReceiver.java @@ -44,7 +44,7 @@ import java.util.List; public class RemoteReplyReceiver extends BroadcastReceiver { public static final String TAG = RemoteReplyReceiver.class.getSimpleName(); - public static final String REPLY_ACTION = "org.thoughtcrime.securesms.notifications.WEAR_REPLY"; + public static final String REPLY_ACTION = "network.loki.securesms.notifications.WEAR_REPLY"; public static final String ADDRESS_EXTRA = "address"; public static final String REPLY_METHOD = "reply_method"; @@ -85,11 +85,6 @@ public class RemoteReplyReceiver extends BroadcastReceiver { threadId = MessageSender.send(context, reply, -1, false, null); break; } - case UnsecuredSmsMessage: { - OutgoingTextMessage reply = new OutgoingTextMessage(recipient, responseText.toString(), expiresIn, subscriptionId); - threadId = MessageSender.send(context, reply, -1, true, null); - break; - } default: throw new AssertionError("Unknown Reply method"); } diff --git a/src/org/thoughtcrime/securesms/notifications/ReplyMethod.java b/src/org/thoughtcrime/securesms/notifications/ReplyMethod.java index fe660f1ec8..e744b5f58b 100644 --- a/src/org/thoughtcrime/securesms/notifications/ReplyMethod.java +++ b/src/org/thoughtcrime/securesms/notifications/ReplyMethod.java @@ -10,16 +10,12 @@ import org.thoughtcrime.securesms.util.TextSecurePreferences; public enum ReplyMethod { GroupMessage, - SecureMessage, - UnsecuredSmsMessage; + SecureMessage; public static @NonNull ReplyMethod forRecipient(Context context, Recipient recipient) { if (recipient.isGroupRecipient()) { return ReplyMethod.GroupMessage; - } else if (TextSecurePreferences.isPushRegistered(context) && recipient.getRegistered() == RecipientDatabase.RegisteredState.REGISTERED && !recipient.isForceSmsSelection()) { - return ReplyMethod.SecureMessage; - } else { - return ReplyMethod.UnsecuredSmsMessage; } + return ReplyMethod.SecureMessage; } } diff --git a/src/org/thoughtcrime/securesms/notifications/SingleRecipientNotificationBuilder.java b/src/org/thoughtcrime/securesms/notifications/SingleRecipientNotificationBuilder.java index 0da777e700..a9472ebbf3 100644 --- a/src/org/thoughtcrime/securesms/notifications/SingleRecipientNotificationBuilder.java +++ b/src/org/thoughtcrime/securesms/notifications/SingleRecipientNotificationBuilder.java @@ -28,7 +28,6 @@ import org.thoughtcrime.securesms.contacts.avatars.ContactColors; import org.thoughtcrime.securesms.contacts.avatars.ContactPhoto; import org.thoughtcrime.securesms.contacts.avatars.FallbackContactPhoto; import org.thoughtcrime.securesms.contacts.avatars.GeneratedContactPhoto; -import org.thoughtcrime.securesms.database.DatabaseFactory; import org.thoughtcrime.securesms.logging.Log; import org.thoughtcrime.securesms.mms.DecryptableStreamUriLoader; import org.thoughtcrime.securesms.mms.GlideApp; @@ -39,7 +38,6 @@ import org.thoughtcrime.securesms.recipients.Recipient; import org.thoughtcrime.securesms.util.BitmapUtil; import org.thoughtcrime.securesms.util.TextSecurePreferences; import org.thoughtcrime.securesms.util.Util; -import org.whispersystems.signalservice.loki.api.LokiPublicChat; import java.util.LinkedList; import java.util.List; @@ -156,59 +154,53 @@ public class SingleRecipientNotificationBuilder extends AbstractNotificationBuil } public void addActions(@NonNull PendingIntent markReadIntent, - @NonNull PendingIntent wearableReplyIntent, + @Nullable PendingIntent quickReplyIntent, + @Nullable PendingIntent wearableReplyIntent, @NonNull ReplyMethod replyMethod) { Action markAsReadAction = new Action(R.drawable.check, context.getString(R.string.MessageNotifier_mark_read), markReadIntent); - String actionName = context.getString(R.string.MessageNotifier_reply); - String label = context.getString(replyMethodLongDescription(replyMethod)); + addAction(markAsReadAction); - /* - Action replyAction = new Action(R.drawable.ic_reply_white_36dp, - actionName, - quickReplyIntent); - */ + NotificationCompat.WearableExtender wearableExtender = new NotificationCompat.WearableExtender().addAction(markAsReadAction); - if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.N) { - /* - replyAction = new Action.Builder(R.drawable.ic_reply_white_36dp, - actionName, - wearableReplyIntent) - .addRemoteInput(new RemoteInput.Builder(MessageNotifier.EXTRA_REMOTE_REPLY) - .setLabel(label).build()) - .build(); - */ + if (quickReplyIntent != null) { + String actionName = context.getString(R.string.MessageNotifier_reply); + String label = context.getString(replyMethodLongDescription(replyMethod)); + + Action replyAction = new Action(R.drawable.ic_reply_white_36dp, + actionName, + quickReplyIntent); + + if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.N) { + replyAction = new Action.Builder(R.drawable.ic_reply_white_36dp, + actionName, + wearableReplyIntent) + .addRemoteInput(new RemoteInput.Builder(MessageNotifier.EXTRA_REMOTE_REPLY) + .setLabel(label).build()) + .build(); + } + + Action wearableReplyAction = new Action.Builder(R.drawable.ic_reply, + actionName, + wearableReplyIntent) + .addRemoteInput(new RemoteInput.Builder(MessageNotifier.EXTRA_REMOTE_REPLY) + .setLabel(label).build()) + .build(); + + + addAction(replyAction); + wearableExtender.addAction(wearableReplyAction); } - Action wearableReplyAction = new Action.Builder(R.drawable.ic_reply, - actionName, - wearableReplyIntent) - .addRemoteInput(new RemoteInput.Builder(MessageNotifier.EXTRA_REMOTE_REPLY) - .setLabel(label).build()) - .build(); - - addAction(markAsReadAction); - // addAction(replyAction); - - extend(new NotificationCompat.WearableExtender().addAction(markAsReadAction) - .addAction(wearableReplyAction)); + extend(wearableExtender); } @StringRes private static int replyMethodLongDescription(@NonNull ReplyMethod replyMethod) { - switch (replyMethod) { - case GroupMessage: - return R.string.MessageNotifier_reply; - case SecureMessage: - return R.string.MessageNotifier_signal_message; - case UnsecuredSmsMessage: - return R.string.MessageNotifier_unsecured_sms; - default: - return R.string.MessageNotifier_reply; - } + return R.string.MessageNotifier_reply; } public void addMessageBody(@NonNull Recipient threadRecipient, diff --git a/src/org/thoughtcrime/securesms/service/AccountAuthenticatorService.java b/src/org/thoughtcrime/securesms/service/AccountAuthenticatorService.java deleted file mode 100644 index 0106818277..0000000000 --- a/src/org/thoughtcrime/securesms/service/AccountAuthenticatorService.java +++ /dev/null @@ -1,80 +0,0 @@ -package org.thoughtcrime.securesms.service; - -import android.accounts.AbstractAccountAuthenticator; -import android.accounts.Account; -import android.accounts.AccountAuthenticatorResponse; -import android.accounts.NetworkErrorException; -import android.app.Service; -import android.content.Context; -import android.content.Intent; -import android.os.Bundle; -import android.os.IBinder; - -public class AccountAuthenticatorService extends Service { - - private static AccountAuthenticatorImpl accountAuthenticator = null; - - @Override - public IBinder onBind(Intent intent) { - if (intent.getAction().equals(android.accounts.AccountManager.ACTION_AUTHENTICATOR_INTENT)) { - return getAuthenticator().getIBinder(); - } else { - return null; - } - } - - private synchronized AccountAuthenticatorImpl getAuthenticator() { - if (accountAuthenticator == null) { - accountAuthenticator = new AccountAuthenticatorImpl(this); - } - - return accountAuthenticator; - } - - private static class AccountAuthenticatorImpl extends AbstractAccountAuthenticator { - - public AccountAuthenticatorImpl(Context context) { - super(context); - } - - @Override - public Bundle addAccount(AccountAuthenticatorResponse response, String accountType, String authTokenType, - String[] requiredFeatures, Bundle options) - throws NetworkErrorException - { - return null; - } - - public Bundle confirmCredentials(AccountAuthenticatorResponse response, Account account, Bundle options) { - return null; - } - - @Override - public Bundle editProperties(AccountAuthenticatorResponse response, String accountType) { - return null; - } - - @Override - public Bundle getAuthToken(AccountAuthenticatorResponse response, Account account, String authTokenType, - Bundle options) throws NetworkErrorException { - return null; - } - - @Override - public String getAuthTokenLabel(String authTokenType) { - return null; - } - - @Override - public Bundle hasFeatures(AccountAuthenticatorResponse response, Account account, String[] features) - throws NetworkErrorException { - return null; - } - - @Override - public Bundle updateCredentials(AccountAuthenticatorResponse response, Account account, String authTokenType, - Bundle options) { - return null; - } - } -}