Disable interactions while user is unregistered or expired.
This commit is contained in:
parent
65d5f4c426
commit
c2c1537858
37 changed files with 527 additions and 44 deletions
|
@ -2,6 +2,8 @@ package org.thoughtcrime.securesms.components.reminder;
|
|||
|
||||
import android.content.Context;
|
||||
|
||||
import androidx.annotation.NonNull;
|
||||
|
||||
import org.thoughtcrime.securesms.R;
|
||||
import org.thoughtcrime.securesms.registration.RegistrationNavigationActivity;
|
||||
import org.thoughtcrime.securesms.util.TextSecurePreferences;
|
||||
|
@ -9,12 +11,14 @@ import org.thoughtcrime.securesms.util.TextSecurePreferences;
|
|||
public class UnauthorizedReminder extends Reminder {
|
||||
|
||||
public UnauthorizedReminder(final Context context) {
|
||||
super(context.getString(R.string.UnauthorizedReminder_device_no_longer_registered),
|
||||
super(null,
|
||||
context.getString(R.string.UnauthorizedReminder_this_is_likely_because_you_registered_your_phone_number_with_Signal_on_a_different_device));
|
||||
|
||||
setOkListener(v -> {
|
||||
context.startActivity(RegistrationNavigationActivity.newIntentForReRegistration(context));
|
||||
});
|
||||
|
||||
addAction(new Action(context.getString(R.string.UnauthorizedReminder_reregister_action), R.id.reminder_action_re_register));
|
||||
}
|
||||
|
||||
@Override
|
||||
|
@ -22,6 +26,11 @@ public class UnauthorizedReminder extends Reminder {
|
|||
return false;
|
||||
}
|
||||
|
||||
@Override
|
||||
public @NonNull Importance getImportance() {
|
||||
return Importance.ERROR;
|
||||
}
|
||||
|
||||
public static boolean isEligible(Context context) {
|
||||
return TextSecurePreferences.isUnauthorizedReceived(context);
|
||||
}
|
||||
|
|
|
@ -64,6 +64,7 @@ abstract class PreferenceViewHolder<T : PreferenceModel<T>>(itemView: View) : Ma
|
|||
val icon = model.icon?.resolve(context)
|
||||
iconView.setImageDrawable(icon)
|
||||
iconView.visible = icon != null
|
||||
iconView.alpha = if (model.isEnabled) 1f else 0.5f
|
||||
|
||||
val iconEnd = model.iconEnd?.resolve(context)
|
||||
iconEndView?.setImageDrawable(iconEnd)
|
||||
|
|
|
@ -1,13 +1,22 @@
|
|||
package org.thoughtcrime.securesms.components.settings.app
|
||||
|
||||
import android.os.Bundle
|
||||
import android.view.View
|
||||
import android.widget.TextView
|
||||
import android.widget.Toast
|
||||
import androidx.annotation.IdRes
|
||||
import androidx.fragment.app.viewModels
|
||||
import androidx.navigation.fragment.findNavController
|
||||
import org.greenrobot.eventbus.EventBus
|
||||
import org.greenrobot.eventbus.Subscribe
|
||||
import org.greenrobot.eventbus.ThreadMode
|
||||
import org.thoughtcrime.securesms.R
|
||||
import org.thoughtcrime.securesms.badges.BadgeImageView
|
||||
import org.thoughtcrime.securesms.components.AvatarImageView
|
||||
import org.thoughtcrime.securesms.components.reminder.ExpiredBuildReminder
|
||||
import org.thoughtcrime.securesms.components.reminder.Reminder
|
||||
import org.thoughtcrime.securesms.components.reminder.ReminderView
|
||||
import org.thoughtcrime.securesms.components.reminder.UnauthorizedReminder
|
||||
import org.thoughtcrime.securesms.components.settings.DSLConfiguration
|
||||
import org.thoughtcrime.securesms.components.settings.DSLSettingsFragment
|
||||
import org.thoughtcrime.securesms.components.settings.DSLSettingsIcon
|
||||
|
@ -15,20 +24,37 @@ import org.thoughtcrime.securesms.components.settings.DSLSettingsText
|
|||
import org.thoughtcrime.securesms.components.settings.PreferenceModel
|
||||
import org.thoughtcrime.securesms.components.settings.PreferenceViewHolder
|
||||
import org.thoughtcrime.securesms.components.settings.configure
|
||||
import org.thoughtcrime.securesms.events.ReminderUpdateEvent
|
||||
import org.thoughtcrime.securesms.keyvalue.SignalStore
|
||||
import org.thoughtcrime.securesms.phonenumbers.PhoneNumberFormatter
|
||||
import org.thoughtcrime.securesms.recipients.Recipient
|
||||
import org.thoughtcrime.securesms.registration.RegistrationNavigationActivity
|
||||
import org.thoughtcrime.securesms.util.FeatureFlags
|
||||
import org.thoughtcrime.securesms.util.PlayStoreUtil
|
||||
import org.thoughtcrime.securesms.util.Util
|
||||
import org.thoughtcrime.securesms.util.ViewUtil
|
||||
import org.thoughtcrime.securesms.util.adapter.mapping.LayoutFactory
|
||||
import org.thoughtcrime.securesms.util.adapter.mapping.MappingAdapter
|
||||
import org.thoughtcrime.securesms.util.adapter.mapping.MappingViewHolder
|
||||
import org.thoughtcrime.securesms.util.navigation.safeNavigate
|
||||
import org.thoughtcrime.securesms.util.views.Stub
|
||||
|
||||
class AppSettingsFragment : DSLSettingsFragment(R.string.text_secure_normal__menu_settings) {
|
||||
class AppSettingsFragment : DSLSettingsFragment(
|
||||
titleId = R.string.text_secure_normal__menu_settings,
|
||||
layoutId = R.layout.dsl_settings_fragment_with_reminder
|
||||
) {
|
||||
|
||||
private val viewModel: AppSettingsViewModel by viewModels()
|
||||
|
||||
private lateinit var reminderView: Stub<ReminderView>
|
||||
|
||||
override fun onViewCreated(view: View, savedInstanceState: Bundle?) {
|
||||
super.onViewCreated(view, savedInstanceState)
|
||||
reminderView = ViewUtil.findStubById(view, R.id.reminder_stub)
|
||||
|
||||
updateReminders()
|
||||
}
|
||||
|
||||
override fun bindAdapter(adapter: MappingAdapter) {
|
||||
adapter.registerFactory(BioPreference::class.java, LayoutFactory(::BioPreferenceViewHolder, R.layout.bio_preference_item))
|
||||
adapter.registerFactory(PaymentsPreference::class.java, LayoutFactory(::PaymentsPreferenceViewHolder, R.layout.dsl_payments_preference))
|
||||
|
@ -39,9 +65,60 @@ class AppSettingsFragment : DSLSettingsFragment(R.string.text_secure_normal__men
|
|||
}
|
||||
}
|
||||
|
||||
@Subscribe(threadMode = ThreadMode.MAIN)
|
||||
fun onEvent(event: ReminderUpdateEvent?) {
|
||||
updateReminders()
|
||||
}
|
||||
|
||||
private fun updateReminders() {
|
||||
if (ExpiredBuildReminder.isEligible()) {
|
||||
showReminder(ExpiredBuildReminder(context))
|
||||
} else if (UnauthorizedReminder.isEligible(context)) {
|
||||
showReminder(UnauthorizedReminder(context))
|
||||
} else {
|
||||
hideReminders()
|
||||
}
|
||||
viewModel.refreshDeprecatedOrUnregistered()
|
||||
}
|
||||
|
||||
private fun showReminder(reminder: Reminder) {
|
||||
if (!reminderView.resolved()) {
|
||||
reminderView.get().addOnLayoutChangeListener { _, _, top, _, bottom, _, _, _, _ ->
|
||||
recyclerView?.setPadding(0, bottom - top, 0, 0)
|
||||
}
|
||||
recyclerView?.clipToPadding = false
|
||||
}
|
||||
reminderView.get().showReminder(reminder)
|
||||
reminderView.get().setOnActionClickListener { reminderActionId: Int -> this.handleReminderAction(reminderActionId) }
|
||||
}
|
||||
|
||||
private fun hideReminders() {
|
||||
if (reminderView.resolved()) {
|
||||
reminderView.get().hide()
|
||||
recyclerView?.clipToPadding = true
|
||||
}
|
||||
}
|
||||
|
||||
private fun handleReminderAction(@IdRes reminderActionId: Int) {
|
||||
when (reminderActionId) {
|
||||
R.id.reminder_action_update_now -> {
|
||||
PlayStoreUtil.openPlayStoreOrOurApkDownloadPage(requireContext())
|
||||
}
|
||||
R.id.reminder_action_re_register -> {
|
||||
startActivity(RegistrationNavigationActivity.newIntentForReRegistration(requireContext()))
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
override fun onResume() {
|
||||
super.onResume()
|
||||
viewModel.refreshExpiredGiftBadge()
|
||||
EventBus.getDefault().register(this)
|
||||
}
|
||||
|
||||
override fun onPause() {
|
||||
super.onPause()
|
||||
EventBus.getDefault().unregister(this)
|
||||
}
|
||||
|
||||
private fun getConfiguration(state: AppSettingsState): DSLConfiguration {
|
||||
|
@ -75,7 +152,8 @@ class AppSettingsFragment : DSLSettingsFragment(R.string.text_secure_normal__men
|
|||
icon = DSLSettingsIcon.from(R.drawable.symbol_devices_24),
|
||||
onClick = {
|
||||
findNavController().safeNavigate(R.id.action_appSettingsFragment_to_deviceActivity)
|
||||
}
|
||||
},
|
||||
isEnabled = state.isDeprecatedOrUnregistered()
|
||||
)
|
||||
|
||||
if (state.allowUserToGoToDonationManagementScreen) {
|
||||
|
@ -111,7 +189,8 @@ class AppSettingsFragment : DSLSettingsFragment(R.string.text_secure_normal__men
|
|||
icon = DSLSettingsIcon.from(R.drawable.symbol_chat_24),
|
||||
onClick = {
|
||||
findNavController().safeNavigate(R.id.action_appSettingsFragment_to_chatsSettingsFragment)
|
||||
}
|
||||
},
|
||||
isEnabled = state.isDeprecatedOrUnregistered()
|
||||
)
|
||||
|
||||
clickPref(
|
||||
|
@ -119,7 +198,8 @@ class AppSettingsFragment : DSLSettingsFragment(R.string.text_secure_normal__men
|
|||
icon = DSLSettingsIcon.from(R.drawable.symbol_stories_24),
|
||||
onClick = {
|
||||
findNavController().safeNavigate(AppSettingsFragmentDirections.actionAppSettingsFragmentToStoryPrivacySettings(R.string.preferences__stories))
|
||||
}
|
||||
},
|
||||
isEnabled = state.isDeprecatedOrUnregistered()
|
||||
)
|
||||
|
||||
clickPref(
|
||||
|
@ -127,7 +207,8 @@ class AppSettingsFragment : DSLSettingsFragment(R.string.text_secure_normal__men
|
|||
icon = DSLSettingsIcon.from(R.drawable.symbol_bell_24),
|
||||
onClick = {
|
||||
findNavController().safeNavigate(R.id.action_appSettingsFragment_to_notificationsSettingsFragment)
|
||||
}
|
||||
},
|
||||
isEnabled = state.isDeprecatedOrUnregistered()
|
||||
)
|
||||
|
||||
clickPref(
|
||||
|
@ -135,7 +216,8 @@ class AppSettingsFragment : DSLSettingsFragment(R.string.text_secure_normal__men
|
|||
icon = DSLSettingsIcon.from(R.drawable.symbol_lock_24),
|
||||
onClick = {
|
||||
findNavController().safeNavigate(R.id.action_appSettingsFragment_to_privacySettingsFragment)
|
||||
}
|
||||
},
|
||||
isEnabled = state.isDeprecatedOrUnregistered()
|
||||
)
|
||||
|
||||
clickPref(
|
||||
|
|
|
@ -6,5 +6,11 @@ data class AppSettingsState(
|
|||
val self: Recipient,
|
||||
val unreadPaymentsCount: Int,
|
||||
val hasExpiredGiftBadge: Boolean,
|
||||
val allowUserToGoToDonationManagementScreen: Boolean
|
||||
)
|
||||
val allowUserToGoToDonationManagementScreen: Boolean,
|
||||
val userUnregistered: Boolean,
|
||||
val clientDeprecated: Boolean
|
||||
) {
|
||||
fun isDeprecatedOrUnregistered(): Boolean {
|
||||
return !(userUnregistered || clientDeprecated)
|
||||
}
|
||||
}
|
||||
|
|
|
@ -11,6 +11,7 @@ import org.thoughtcrime.securesms.conversationlist.model.UnreadPaymentsLiveData
|
|||
import org.thoughtcrime.securesms.dependencies.ApplicationDependencies
|
||||
import org.thoughtcrime.securesms.keyvalue.SignalStore
|
||||
import org.thoughtcrime.securesms.recipients.Recipient
|
||||
import org.thoughtcrime.securesms.util.TextSecurePreferences
|
||||
import org.thoughtcrime.securesms.util.livedata.Store
|
||||
|
||||
class AppSettingsViewModel(
|
||||
|
@ -22,7 +23,9 @@ class AppSettingsViewModel(
|
|||
Recipient.self(),
|
||||
0,
|
||||
SignalStore.donationsValues().getExpiredGiftBadge() != null,
|
||||
SignalStore.donationsValues().isLikelyASustainer() || InAppDonations.hasAtLeastOnePaymentMethodAvailable()
|
||||
SignalStore.donationsValues().isLikelyASustainer() || InAppDonations.hasAtLeastOnePaymentMethodAvailable(),
|
||||
TextSecurePreferences.isUnauthorizedReceived(ApplicationDependencies.getApplication()),
|
||||
SignalStore.misc().isClientDeprecated
|
||||
)
|
||||
)
|
||||
|
||||
|
@ -50,6 +53,10 @@ class AppSettingsViewModel(
|
|||
disposables.clear()
|
||||
}
|
||||
|
||||
fun refreshDeprecatedOrUnregistered() {
|
||||
store.update { it.copy(clientDeprecated = SignalStore.misc().isClientDeprecated, userUnregistered = TextSecurePreferences.isUnauthorizedReceived(ApplicationDependencies.getApplication())) }
|
||||
}
|
||||
|
||||
fun refreshExpiredGiftBadge() {
|
||||
store.update { it.copy(hasExpiredGiftBadge = SignalStore.donationsValues().getExpiredGiftBadge() != null) }
|
||||
}
|
||||
|
|
|
@ -1,6 +1,7 @@
|
|||
package org.thoughtcrime.securesms.components.settings.app.account
|
||||
|
||||
import android.content.Context
|
||||
import android.content.DialogInterface
|
||||
import android.content.Intent
|
||||
import android.graphics.Typeface
|
||||
import android.text.InputType
|
||||
|
@ -9,6 +10,7 @@ import android.view.ViewGroup
|
|||
import android.widget.Button
|
||||
import android.widget.EditText
|
||||
import android.widget.TextView
|
||||
import android.widget.Toast
|
||||
import androidx.appcompat.app.AlertDialog
|
||||
import androidx.autofill.HintConstants
|
||||
import androidx.core.app.DialogCompat
|
||||
|
@ -24,12 +26,16 @@ import org.thoughtcrime.securesms.components.settings.DSLSettingsFragment
|
|||
import org.thoughtcrime.securesms.components.settings.DSLSettingsText
|
||||
import org.thoughtcrime.securesms.components.settings.configure
|
||||
import org.thoughtcrime.securesms.contactshare.SimpleTextWatcher
|
||||
import org.thoughtcrime.securesms.dependencies.ApplicationDependencies
|
||||
import org.thoughtcrime.securesms.keyvalue.SignalStore
|
||||
import org.thoughtcrime.securesms.lock.PinHashing
|
||||
import org.thoughtcrime.securesms.lock.v2.CreateKbsPinActivity
|
||||
import org.thoughtcrime.securesms.lock.v2.KbsConstants
|
||||
import org.thoughtcrime.securesms.lock.v2.PinKeyboardType
|
||||
import org.thoughtcrime.securesms.pin.RegistrationLockV2Dialog
|
||||
import org.thoughtcrime.securesms.registration.RegistrationNavigationActivity
|
||||
import org.thoughtcrime.securesms.util.PlayStoreUtil
|
||||
import org.thoughtcrime.securesms.util.ServiceUtil
|
||||
import org.thoughtcrime.securesms.util.ViewUtil
|
||||
import org.thoughtcrime.securesms.util.adapter.mapping.MappingAdapter
|
||||
import org.thoughtcrime.securesms.util.navigation.safeNavigate
|
||||
|
@ -64,6 +70,7 @@ class AccountSettingsFragment : DSLSettingsFragment(R.string.AccountSettingsFrag
|
|||
@Suppress("DEPRECATION")
|
||||
clickPref(
|
||||
title = DSLSettingsText.from(if (state.hasPin) R.string.preferences_app_protection__change_your_pin else R.string.preferences_app_protection__create_a_pin),
|
||||
isEnabled = state.isDeprecatedOrUnregistered(),
|
||||
onClick = {
|
||||
if (state.hasPin) {
|
||||
startActivityForResult(CreateKbsPinActivity.getIntentForPinChangeFromSettings(requireContext()), CreateKbsPinActivity.REQUEST_NEW_PIN)
|
||||
|
@ -77,7 +84,7 @@ class AccountSettingsFragment : DSLSettingsFragment(R.string.AccountSettingsFrag
|
|||
title = DSLSettingsText.from(R.string.preferences_app_protection__pin_reminders),
|
||||
summary = DSLSettingsText.from(R.string.AccountSettingsFragment__youll_be_asked_less_frequently),
|
||||
isChecked = state.hasPin && state.pinRemindersEnabled,
|
||||
isEnabled = state.hasPin,
|
||||
isEnabled = state.hasPin && state.isDeprecatedOrUnregistered(),
|
||||
onClick = {
|
||||
setPinRemindersEnabled(!state.pinRemindersEnabled)
|
||||
}
|
||||
|
@ -87,7 +94,7 @@ class AccountSettingsFragment : DSLSettingsFragment(R.string.AccountSettingsFrag
|
|||
title = DSLSettingsText.from(R.string.preferences_app_protection__registration_lock),
|
||||
summary = DSLSettingsText.from(R.string.AccountSettingsFragment__require_your_signal_pin),
|
||||
isChecked = state.registrationLockEnabled,
|
||||
isEnabled = state.hasPin,
|
||||
isEnabled = state.hasPin && state.isDeprecatedOrUnregistered(),
|
||||
onClick = {
|
||||
setRegistrationLockEnabled(!state.registrationLockEnabled)
|
||||
}
|
||||
|
@ -95,6 +102,7 @@ class AccountSettingsFragment : DSLSettingsFragment(R.string.AccountSettingsFrag
|
|||
|
||||
clickPref(
|
||||
title = DSLSettingsText.from(R.string.preferences__advanced_pin_settings),
|
||||
isEnabled = state.isDeprecatedOrUnregistered(),
|
||||
onClick = {
|
||||
Navigation.findNavController(requireView()).safeNavigate(R.id.action_accountSettingsFragment_to_advancedPinSettingsActivity)
|
||||
}
|
||||
|
@ -107,6 +115,7 @@ class AccountSettingsFragment : DSLSettingsFragment(R.string.AccountSettingsFrag
|
|||
if (SignalStore.account().isRegistered) {
|
||||
clickPref(
|
||||
title = DSLSettingsText.from(R.string.AccountSettingsFragment__change_phone_number),
|
||||
isEnabled = state.isDeprecatedOrUnregistered(),
|
||||
onClick = {
|
||||
Navigation.findNavController(requireView()).safeNavigate(R.id.action_accountSettingsFragment_to_changePhoneNumberFragment)
|
||||
}
|
||||
|
@ -116,6 +125,7 @@ class AccountSettingsFragment : DSLSettingsFragment(R.string.AccountSettingsFrag
|
|||
clickPref(
|
||||
title = DSLSettingsText.from(R.string.preferences_chats__transfer_account),
|
||||
summary = DSLSettingsText.from(R.string.preferences_chats__transfer_account_to_a_new_android_device),
|
||||
isEnabled = state.isDeprecatedOrUnregistered(),
|
||||
onClick = {
|
||||
Navigation.findNavController(requireView()).safeNavigate(R.id.action_accountSettingsFragment_to_oldDeviceTransferActivity)
|
||||
}
|
||||
|
@ -123,13 +133,49 @@ class AccountSettingsFragment : DSLSettingsFragment(R.string.AccountSettingsFrag
|
|||
|
||||
clickPref(
|
||||
title = DSLSettingsText.from(R.string.AccountSettingsFragment__request_account_data),
|
||||
isEnabled = state.isDeprecatedOrUnregistered(),
|
||||
onClick = {
|
||||
Navigation.findNavController(requireView()).safeNavigate(R.id.action_accountSettingsFragment_to_exportAccountFragment)
|
||||
}
|
||||
)
|
||||
|
||||
if (!state.isDeprecatedOrUnregistered()) {
|
||||
if (state.clientDeprecated) {
|
||||
clickPref(
|
||||
title = DSLSettingsText.from(R.string.preferences_account_update_signal),
|
||||
onClick = {
|
||||
PlayStoreUtil.openPlayStoreOrOurApkDownloadPage(requireContext())
|
||||
}
|
||||
)
|
||||
} else if (state.userUnregistered) {
|
||||
clickPref(
|
||||
title = DSLSettingsText.from(R.string.preferences_account_reregister),
|
||||
onClick = {
|
||||
startActivity(RegistrationNavigationActivity.newIntentForReRegistration(requireContext()))
|
||||
}
|
||||
)
|
||||
}
|
||||
|
||||
clickPref(
|
||||
title = DSLSettingsText.from(R.string.preferences_account_delete_all_data, ContextCompat.getColor(requireContext(), R.color.signal_alert_primary)),
|
||||
onClick = {
|
||||
MaterialAlertDialogBuilder(requireContext())
|
||||
.setTitle(R.string.preferences_account_delete_all_data_confirmation_title)
|
||||
.setMessage(R.string.preferences_account_delete_all_data_confirmation_message)
|
||||
.setPositiveButton(R.string.preferences_account_delete_all_data_confirmation_proceed) { _: DialogInterface, _: Int ->
|
||||
if (!ServiceUtil.getActivityManager(ApplicationDependencies.getApplication()).clearApplicationUserData()) {
|
||||
Toast.makeText(requireContext(), R.string.preferences_account_delete_all_data_failed, Toast.LENGTH_LONG).show()
|
||||
}
|
||||
}
|
||||
.setNegativeButton(R.string.preferences_account_delete_all_data_confirmation_cancel, null)
|
||||
.show()
|
||||
}
|
||||
)
|
||||
}
|
||||
|
||||
clickPref(
|
||||
title = DSLSettingsText.from(R.string.preferences__delete_account, ContextCompat.getColor(requireContext(), R.color.signal_alert_primary)),
|
||||
title = DSLSettingsText.from(R.string.preferences__delete_account, ContextCompat.getColor(requireContext(), if (state.isDeprecatedOrUnregistered()) R.color.signal_alert_primary else R.color.signal_alert_primary_50)),
|
||||
isEnabled = state.isDeprecatedOrUnregistered(),
|
||||
onClick = {
|
||||
Navigation.findNavController(requireView()).safeNavigate(R.id.action_accountSettingsFragment_to_deleteAccountFragment)
|
||||
}
|
||||
|
|
|
@ -3,5 +3,11 @@ package org.thoughtcrime.securesms.components.settings.app.account
|
|||
data class AccountSettingsState(
|
||||
val hasPin: Boolean,
|
||||
val pinRemindersEnabled: Boolean,
|
||||
val registrationLockEnabled: Boolean
|
||||
)
|
||||
val registrationLockEnabled: Boolean,
|
||||
val userUnregistered: Boolean,
|
||||
val clientDeprecated: Boolean
|
||||
) {
|
||||
fun isDeprecatedOrUnregistered(): Boolean {
|
||||
return !(userUnregistered || clientDeprecated)
|
||||
}
|
||||
}
|
||||
|
|
|
@ -2,7 +2,9 @@ package org.thoughtcrime.securesms.components.settings.app.account
|
|||
|
||||
import androidx.lifecycle.LiveData
|
||||
import androidx.lifecycle.ViewModel
|
||||
import org.thoughtcrime.securesms.dependencies.ApplicationDependencies
|
||||
import org.thoughtcrime.securesms.keyvalue.SignalStore
|
||||
import org.thoughtcrime.securesms.util.TextSecurePreferences
|
||||
import org.thoughtcrime.securesms.util.livedata.Store
|
||||
|
||||
class AccountSettingsViewModel : ViewModel() {
|
||||
|
@ -18,7 +20,9 @@ class AccountSettingsViewModel : ViewModel() {
|
|||
return AccountSettingsState(
|
||||
hasPin = SignalStore.kbsValues().hasPin() && !SignalStore.kbsValues().hasOptedOut(),
|
||||
pinRemindersEnabled = SignalStore.pinValues().arePinRemindersEnabled(),
|
||||
registrationLockEnabled = SignalStore.kbsValues().isV2RegistrationLockEnabled
|
||||
registrationLockEnabled = SignalStore.kbsValues().isV2RegistrationLockEnabled,
|
||||
userUnregistered = TextSecurePreferences.isUnauthorizedReceived(ApplicationDependencies.getApplication()),
|
||||
clientDeprecated = SignalStore.misc().isClientDeprecated
|
||||
)
|
||||
}
|
||||
}
|
||||
|
|
|
@ -109,6 +109,7 @@ class ConversationSettingsFragment : DSLSettingsFragment(
|
|||
|
||||
private val args: ConversationSettingsFragmentArgs by navArgs()
|
||||
private val alertTint by lazy { ContextCompat.getColor(requireContext(), R.color.signal_alert_primary) }
|
||||
private val alertDisabledTint by lazy { ContextCompat.getColor(requireContext(), R.color.signal_alert_primary_50) }
|
||||
private val blockIcon by lazy {
|
||||
ContextUtil.requireDrawable(requireContext(), R.drawable.ic_block_tinted_24).apply {
|
||||
colorFilter = PorterDuffColorFilter(alertTint, PorterDuff.Mode.SRC_IN)
|
||||
|
@ -383,6 +384,7 @@ class ConversationSettingsFragment : DSLSettingsFragment(
|
|||
customPref(
|
||||
ButtonStripPreference.Model(
|
||||
state = state.buttonStripState,
|
||||
enabled = !state.isDeprecatedOrUnregistered,
|
||||
onMessageClick = {
|
||||
val intent = ConversationIntents
|
||||
.createBuilder(requireContext(), state.recipient.id, state.threadId)
|
||||
|
@ -470,7 +472,7 @@ class ConversationSettingsFragment : DSLSettingsFragment(
|
|||
title = DSLSettingsText.from(R.string.ConversationSettingsFragment__disappearing_messages),
|
||||
summary = summary,
|
||||
icon = DSLSettingsIcon.from(icon),
|
||||
isEnabled = enabled,
|
||||
isEnabled = enabled && !state.isDeprecatedOrUnregistered,
|
||||
onClick = {
|
||||
val action = ConversationSettingsFragmentDirections.actionConversationSettingsFragmentToAppSettingsExpireTimer()
|
||||
.setInitialValue(state.disappearingMessagesLifespan)
|
||||
|
@ -496,6 +498,7 @@ class ConversationSettingsFragment : DSLSettingsFragment(
|
|||
clickPref(
|
||||
title = DSLSettingsText.from(R.string.ConversationSettingsFragment__sounds_and_notifications),
|
||||
icon = DSLSettingsIcon.from(R.drawable.ic_speaker_24),
|
||||
isEnabled = !state.isDeprecatedOrUnregistered,
|
||||
onClick = {
|
||||
val action = ConversationSettingsFragmentDirections.actionConversationSettingsFragmentToSoundsAndNotificationsSettingsFragment(state.recipient.id)
|
||||
|
||||
|
@ -540,6 +543,7 @@ class ConversationSettingsFragment : DSLSettingsFragment(
|
|||
clickPref(
|
||||
title = DSLSettingsText.from(R.string.ConversationSettingsFragment__view_safety_number),
|
||||
icon = DSLSettingsIcon.from(R.drawable.ic_safety_number_24),
|
||||
isEnabled = !state.isDeprecatedOrUnregistered,
|
||||
onClick = {
|
||||
startActivity(VerifyIdentityActivity.newIntent(requireActivity(), recipientState.identityRecord))
|
||||
}
|
||||
|
@ -615,6 +619,7 @@ class ConversationSettingsFragment : DSLSettingsFragment(
|
|||
LargeIconClickPreference.Model(
|
||||
title = DSLSettingsText.from(R.string.ConversationSettingsFragment__add_to_a_group),
|
||||
icon = DSLSettingsIcon.from(R.drawable.add_to_a_group, NO_TINT),
|
||||
isEnabled = !state.isDeprecatedOrUnregistered,
|
||||
onClick = {
|
||||
viewModel.onAddToGroup()
|
||||
}
|
||||
|
@ -657,7 +662,7 @@ class ConversationSettingsFragment : DSLSettingsFragment(
|
|||
sectionHeaderPref(DSLSettingsText.from(resources.getQuantityString(R.plurals.ContactSelectionListFragment_d_members, memberCount, memberCount)))
|
||||
}
|
||||
|
||||
if (groupState.canAddToGroup) {
|
||||
if (groupState.canAddToGroup && !state.isDeprecatedOrUnregistered) {
|
||||
customPref(
|
||||
LargeIconClickPreference.Model(
|
||||
title = DSLSettingsText.from(R.string.ConversationSettingsFragment__add_members),
|
||||
|
@ -700,6 +705,7 @@ class ConversationSettingsFragment : DSLSettingsFragment(
|
|||
title = DSLSettingsText.from(R.string.ConversationSettingsFragment__group_link),
|
||||
summary = DSLSettingsText.from(if (groupState.groupLinkEnabled) R.string.preferences_on else R.string.preferences_off),
|
||||
icon = DSLSettingsIcon.from(R.drawable.ic_link_16),
|
||||
isEnabled = !state.isDeprecatedOrUnregistered,
|
||||
onClick = {
|
||||
navController.safeNavigate(ConversationSettingsFragmentDirections.actionConversationSettingsFragmentToShareableGroupLinkFragment(groupState.groupId.requireV2().toString()))
|
||||
}
|
||||
|
@ -708,6 +714,7 @@ class ConversationSettingsFragment : DSLSettingsFragment(
|
|||
clickPref(
|
||||
title = DSLSettingsText.from(R.string.ConversationSettingsFragment__requests_and_invites),
|
||||
icon = DSLSettingsIcon.from(R.drawable.ic_update_group_add_16),
|
||||
isEnabled = !state.isDeprecatedOrUnregistered,
|
||||
onClick = {
|
||||
startActivity(ManagePendingAndRequestingMembersActivity.newIntent(requireContext(), groupState.groupId.requireV2()))
|
||||
}
|
||||
|
@ -717,6 +724,7 @@ class ConversationSettingsFragment : DSLSettingsFragment(
|
|||
clickPref(
|
||||
title = DSLSettingsText.from(R.string.ConversationSettingsFragment__permissions),
|
||||
icon = DSLSettingsIcon.from(R.drawable.ic_lock_24),
|
||||
isEnabled = !state.isDeprecatedOrUnregistered,
|
||||
onClick = {
|
||||
val action = ConversationSettingsFragmentDirections.actionConversationSettingsFragmentToPermissionsSettingsFragment(ParcelableGroupId.from(groupState.groupId))
|
||||
navController.safeNavigate(action)
|
||||
|
@ -729,8 +737,9 @@ class ConversationSettingsFragment : DSLSettingsFragment(
|
|||
dividerPref()
|
||||
|
||||
clickPref(
|
||||
title = DSLSettingsText.from(R.string.conversation__menu_leave_group, alertTint),
|
||||
title = DSLSettingsText.from(R.string.conversation__menu_leave_group, if (state.isDeprecatedOrUnregistered) alertDisabledTint else alertTint),
|
||||
icon = DSLSettingsIcon.from(leaveIcon),
|
||||
isEnabled = !state.isDeprecatedOrUnregistered,
|
||||
onClick = {
|
||||
LeaveGroupDialog.handleLeavePushGroup(requireActivity(), groupState.groupId.requirePush(), null)
|
||||
}
|
||||
|
@ -759,12 +768,13 @@ class ConversationSettingsFragment : DSLSettingsFragment(
|
|||
else -> R.string.ConversationSettingsFragment__block
|
||||
}
|
||||
|
||||
val titleTint = if (isBlocked) null else alertTint
|
||||
val titleTint = if (isBlocked) null else if (state.isDeprecatedOrUnregistered) alertDisabledTint else alertTint
|
||||
val blockUnblockIcon = if (isBlocked) unblockIcon else blockIcon
|
||||
|
||||
clickPref(
|
||||
title = if (titleTint != null) DSLSettingsText.from(title, titleTint) else DSLSettingsText.from(title),
|
||||
icon = DSLSettingsIcon.from(blockUnblockIcon),
|
||||
isEnabled = !state.isDeprecatedOrUnregistered,
|
||||
onClick = {
|
||||
if (state.recipient.isBlocked) {
|
||||
BlockUnblockDialog.showUnblockFor(requireContext(), viewLifecycleOwner.lifecycle, state.recipient) {
|
||||
|
|
|
@ -14,6 +14,7 @@ data class ConversationSettingsState(
|
|||
val threadId: Long = -1,
|
||||
val storyViewState: StoryViewState = StoryViewState.NONE,
|
||||
val recipient: Recipient = Recipient.UNKNOWN,
|
||||
val isDeprecatedOrUnregistered: Boolean = false,
|
||||
val buttonStripState: ButtonStripPreference.State = ButtonStripPreference.State(),
|
||||
val disappearingMessagesLifespan: Int = 0,
|
||||
val canModifyBlockedState: Boolean = false,
|
||||
|
|
|
@ -21,6 +21,7 @@ import org.thoughtcrime.securesms.components.settings.conversation.preferences.L
|
|||
import org.thoughtcrime.securesms.database.AttachmentTable
|
||||
import org.thoughtcrime.securesms.database.RecipientTable
|
||||
import org.thoughtcrime.securesms.database.model.StoryViewState
|
||||
import org.thoughtcrime.securesms.dependencies.ApplicationDependencies
|
||||
import org.thoughtcrime.securesms.groups.GroupId
|
||||
import org.thoughtcrime.securesms.groups.LiveGroup
|
||||
import org.thoughtcrime.securesms.groups.v2.GroupAddMembersResult
|
||||
|
@ -29,6 +30,7 @@ import org.thoughtcrime.securesms.recipients.Recipient
|
|||
import org.thoughtcrime.securesms.recipients.RecipientId
|
||||
import org.thoughtcrime.securesms.recipients.RecipientUtil
|
||||
import org.thoughtcrime.securesms.util.FeatureFlags
|
||||
import org.thoughtcrime.securesms.util.TextSecurePreferences
|
||||
import org.thoughtcrime.securesms.util.livedata.LiveDataUtil
|
||||
import org.thoughtcrime.securesms.util.livedata.Store
|
||||
import java.util.Optional
|
||||
|
@ -46,7 +48,8 @@ sealed class ConversationSettingsViewModel(
|
|||
|
||||
protected val store = Store(
|
||||
ConversationSettingsState(
|
||||
specificSettingsState = specificSettingsState
|
||||
specificSettingsState = specificSettingsState,
|
||||
isDeprecatedOrUnregistered = SignalStore.misc().isClientDeprecated || TextSecurePreferences.isUnauthorizedReceived(ApplicationDependencies.getApplication())
|
||||
)
|
||||
)
|
||||
protected val internalEvents: Subject<ConversationSettingsEvent> = PublishSubject.create()
|
||||
|
|
|
@ -7,6 +7,7 @@ import androidx.appcompat.content.res.AppCompatResources
|
|||
import org.thoughtcrime.securesms.R
|
||||
import org.thoughtcrime.securesms.components.settings.DSLSettingsIcon
|
||||
import org.thoughtcrime.securesms.components.settings.PreferenceModel
|
||||
import org.thoughtcrime.securesms.util.ViewUtil
|
||||
import org.thoughtcrime.securesms.util.adapter.mapping.LayoutFactory
|
||||
import org.thoughtcrime.securesms.util.adapter.mapping.MappingAdapter
|
||||
import org.thoughtcrime.securesms.util.adapter.mapping.MappingViewHolder
|
||||
|
@ -24,6 +25,7 @@ object ButtonStripPreference {
|
|||
class Model(
|
||||
val state: State,
|
||||
val background: DSLSettingsIcon? = null,
|
||||
val enabled: Boolean = true,
|
||||
val onAddToStoryClick: () -> Unit = {},
|
||||
val onMessageClick: () -> Unit = {},
|
||||
val onVideoClick: () -> Unit = {},
|
||||
|
@ -87,6 +89,11 @@ object ButtonStripPreference {
|
|||
}
|
||||
}
|
||||
|
||||
listOf(messageContainer, videoContainer, audioContainer, muteContainer, addToStoryContainer, searchContainer).forEach {
|
||||
it.alpha = if (model.enabled) 1.0f else 0.5f
|
||||
ViewUtil.setEnabledRecursive(it, model.enabled)
|
||||
}
|
||||
|
||||
message.setOnClickListener { model.onMessageClick() }
|
||||
videoCall.setOnClickListener { model.onVideoClick() }
|
||||
audioCall.setOnClickListener { model.onAudioClick() }
|
||||
|
|
|
@ -22,6 +22,7 @@ object LargeIconClickPreference {
|
|||
override val title: DSLSettingsText?,
|
||||
override val icon: DSLSettingsIcon,
|
||||
override val summary: DSLSettingsText? = null,
|
||||
override val isEnabled: Boolean = true,
|
||||
val onClick: () -> Unit
|
||||
) : PreferenceModel<Model>()
|
||||
|
||||
|
|
|
@ -399,6 +399,7 @@ public class ConversationParentFragment extends Fragment
|
|||
private ConversationFragment fragment;
|
||||
private Button unblockButton;
|
||||
private Stub<View> smsExportStub;
|
||||
private Stub<View> loggedOutStub;
|
||||
private Button registerButton;
|
||||
private InputAwareLayout container;
|
||||
protected Stub<ReminderView> reminderView;
|
||||
|
@ -1728,11 +1729,12 @@ public class ConversationParentFragment extends Fragment
|
|||
Integer actionableRequestingMembers = groupViewModel.getActionableRequestingMembers().getValue();
|
||||
List<RecipientId> gv1MigrationSuggestions = groupViewModel.getGroupV1MigrationSuggestions().getValue();
|
||||
|
||||
if (UnauthorizedReminder.isEligible(context)) {
|
||||
reminderView.get().showReminder(new UnauthorizedReminder(context));
|
||||
} else if (ExpiredBuildReminder.isEligible()) {
|
||||
if (ExpiredBuildReminder.isEligible()) {
|
||||
reminderView.get().showReminder(new ExpiredBuildReminder(context));
|
||||
reminderView.get().setOnActionClickListener(this::handleReminderAction);
|
||||
} else if (UnauthorizedReminder.isEligible(context)) {
|
||||
reminderView.get().showReminder(new UnauthorizedReminder(context));
|
||||
reminderView.get().setOnActionClickListener(this::handleReminderAction);
|
||||
} else if (ServiceOutageReminder.isEligible(context)) {
|
||||
ApplicationDependencies.getJobManager().add(new ServiceOutageDetectionJob());
|
||||
reminderView.get().showReminder(new ServiceOutageReminder(context));
|
||||
|
@ -1788,6 +1790,8 @@ public class ConversationParentFragment extends Fragment
|
|||
InsightsLauncher.showInsightsDashboard(getChildFragmentManager());
|
||||
} else if (reminderActionId == R.id.reminder_action_update_now) {
|
||||
PlayStoreUtil.openPlayStoreOrOurApkDownloadPage(requireContext());
|
||||
} else if (reminderActionId == R.id.reminder_action_re_register) {
|
||||
startActivity(RegistrationNavigationActivity.newIntentForReRegistration(requireContext()));
|
||||
} else {
|
||||
throw new IllegalArgumentException("Unknown ID: " + reminderActionId);
|
||||
}
|
||||
|
@ -1872,6 +1876,7 @@ public class ConversationParentFragment extends Fragment
|
|||
attachmentKeyboardStub = ViewUtil.findStubById(view, R.id.attachment_keyboard_stub);
|
||||
unblockButton = view.findViewById(R.id.unblock_button);
|
||||
smsExportStub = ViewUtil.findStubById(view, R.id.sms_export_stub);
|
||||
loggedOutStub = ViewUtil.findStubById(view, R.id.logged_out_stub);
|
||||
registerButton = view.findViewById(R.id.register_button);
|
||||
container = view.findViewById(R.id.layout_container);
|
||||
reminderView = ViewUtil.findStubById(view, R.id.reminder_stub);
|
||||
|
@ -2608,16 +2613,46 @@ public class ConversationParentFragment extends Fragment
|
|||
return;
|
||||
}
|
||||
|
||||
if (!conversationSecurityInfo.isPushAvailable() && isPushGroupConversation()) {
|
||||
if (conversationSecurityInfo.isClientExpired() || conversationSecurityInfo.isUnauthorized()) {
|
||||
unblockButton.setVisibility(View.GONE);
|
||||
inputPanel.setHideForBlockedState(true);
|
||||
smsExportStub.setVisibility(View.GONE);
|
||||
registerButton.setVisibility(View.GONE);
|
||||
loggedOutStub.setVisibility(View.VISIBLE);
|
||||
messageRequestBottomView.setVisibility(View.GONE);
|
||||
|
||||
int color = ContextCompat.getColor(requireContext(), recipient.hasWallpaper() ? R.color.wallpaper_bubble_color : R.color.signal_colorBackground);
|
||||
loggedOutStub.get().setBackgroundColor(color);
|
||||
WindowUtil.setNavigationBarColor(requireActivity(), color);
|
||||
|
||||
TextView message = loggedOutStub.get().findViewById(R.id.logged_out_message);
|
||||
MaterialButton actionButton = loggedOutStub.get().findViewById(R.id.logged_out_button);
|
||||
|
||||
if (conversationSecurityInfo.isClientExpired()) {
|
||||
message.setText(R.string.ExpiredBuildReminder_this_version_of_signal_has_expired);
|
||||
actionButton.setText(R.string.ConversationFragment__update_build);
|
||||
actionButton.setOnClickListener(v -> {
|
||||
PlayStoreUtil.openPlayStoreOrOurApkDownloadPage(requireContext());
|
||||
});
|
||||
} else if (conversationSecurityInfo.isUnauthorized()) {
|
||||
message.setText(R.string.UnauthorizedReminder_this_is_likely_because_you_registered_your_phone_number_with_Signal_on_a_different_device);
|
||||
actionButton.setText(R.string.ConversationFragment__reregister_signal);
|
||||
actionButton.setOnClickListener(v -> {
|
||||
startActivity(RegistrationNavigationActivity.newIntentForReRegistration(requireContext()));
|
||||
});
|
||||
}
|
||||
} else if (!conversationSecurityInfo.isPushAvailable() && isPushGroupConversation()) {
|
||||
unblockButton.setVisibility(View.GONE);
|
||||
inputPanel.setHideForBlockedState(true);
|
||||
smsExportStub.setVisibility(View.GONE);
|
||||
loggedOutStub.setVisibility(View.GONE);
|
||||
registerButton.setVisibility(View.VISIBLE);
|
||||
} else if (!conversationSecurityInfo.isPushAvailable() && !(SignalStore.misc().getSmsExportPhase().isSmsSupported() && conversationSecurityInfo.isDefaultSmsApplication()) && (recipient.hasSmsAddress() || recipient.isMmsGroup())) {
|
||||
unblockButton.setVisibility(View.GONE);
|
||||
inputPanel.setHideForBlockedState(true);
|
||||
smsExportStub.setVisibility(View.VISIBLE);
|
||||
registerButton.setVisibility(View.GONE);
|
||||
loggedOutStub.setVisibility(View.GONE);
|
||||
|
||||
int color = ContextCompat.getColor(requireContext(), recipient.hasWallpaper() ? R.color.wallpaper_bubble_color : R.color.signal_colorBackground);
|
||||
smsExportStub.get().setBackgroundColor(color);
|
||||
|
|
|
@ -28,6 +28,7 @@ import org.thoughtcrime.securesms.recipients.RecipientUtil;
|
|||
import org.thoughtcrime.securesms.util.BubbleUtil;
|
||||
import org.thoughtcrime.securesms.util.ConversationUtil;
|
||||
import org.thoughtcrime.securesms.util.MessageRecordUtil;
|
||||
import org.thoughtcrime.securesms.util.TextSecurePreferences;
|
||||
import org.thoughtcrime.securesms.util.Util;
|
||||
|
||||
import java.io.IOException;
|
||||
|
@ -187,7 +188,9 @@ public class ConversationRepository {
|
|||
registeredState == RecipientTable.RegisteredState.REGISTERED && signalEnabled,
|
||||
Util.isDefaultSmsProvider(context),
|
||||
true,
|
||||
hasUnexportedInsecureMessages);
|
||||
hasUnexportedInsecureMessages,
|
||||
SignalStore.misc().isClientDeprecated(),
|
||||
TextSecurePreferences.isUnauthorizedReceived(context));
|
||||
}).subscribeOn(Schedulers.io());
|
||||
}
|
||||
|
||||
|
|
|
@ -7,5 +7,7 @@ data class ConversationSecurityInfo(
|
|||
val isPushAvailable: Boolean = false,
|
||||
val isDefaultSmsApplication: Boolean = false,
|
||||
val isInitialized: Boolean = false,
|
||||
val hasUnexportedInsecureMessages: Boolean = false
|
||||
val hasUnexportedInsecureMessages: Boolean = false,
|
||||
val isClientExpired: Boolean = false,
|
||||
val isUnauthorized: Boolean = false
|
||||
)
|
||||
|
|
|
@ -158,6 +158,7 @@ import org.thoughtcrime.securesms.profiles.manage.ManageProfileActivity;
|
|||
import org.thoughtcrime.securesms.ratelimit.RecaptchaProofBottomSheetFragment;
|
||||
import org.thoughtcrime.securesms.recipients.Recipient;
|
||||
import org.thoughtcrime.securesms.recipients.RecipientId;
|
||||
import org.thoughtcrime.securesms.registration.RegistrationNavigationActivity;
|
||||
import org.thoughtcrime.securesms.search.MessageResult;
|
||||
import org.thoughtcrime.securesms.service.KeyCachingService;
|
||||
import org.thoughtcrime.securesms.sms.MessageSender;
|
||||
|
@ -803,6 +804,8 @@ public class ConversationListFragment extends MainFragment implements ActionMode
|
|||
CdsPermanentErrorBottomSheet.show(getChildFragmentManager());
|
||||
} else if (reminderActionId == R.id.reminder_action_fix_username) {
|
||||
startActivity(ManageProfileActivity.getIntentForUsernameEdit(requireContext()));
|
||||
} else if (reminderActionId == R.id.reminder_action_re_register) {
|
||||
startActivity(RegistrationNavigationActivity.newIntentForReRegistration(requireContext()));
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -1042,10 +1045,10 @@ public class ConversationListFragment extends MainFragment implements ActionMode
|
|||
Context context = requireContext();
|
||||
|
||||
SimpleTask.run(getViewLifecycleOwner().getLifecycle(), () -> {
|
||||
if (UnauthorizedReminder.isEligible(context)) {
|
||||
return Optional.of(new UnauthorizedReminder(context));
|
||||
} else if (ExpiredBuildReminder.isEligible()) {
|
||||
if (ExpiredBuildReminder.isEligible()) {
|
||||
return Optional.of(new ExpiredBuildReminder(context));
|
||||
} else if (UnauthorizedReminder.isEligible(context)) {
|
||||
return Optional.of(new UnauthorizedReminder(context));
|
||||
} else if (ServiceOutageReminder.isEligible(context)) {
|
||||
ApplicationDependencies.getJobManager().add(new ServiceOutageDetectionJob());
|
||||
return Optional.of(new ServiceOutageReminder(context));
|
||||
|
|
|
@ -176,7 +176,7 @@ final class GroupManagerV1 {
|
|||
|
||||
OutgoingMessage outgoingMessage = OutgoingMessage.groupUpdateMessage(groupRecipient,
|
||||
new MessageGroupContext(groupContext),
|
||||
Collections.singletonList(avatarAttachment),
|
||||
avatarAttachment != null ? Collections.singletonList(avatarAttachment) : Collections.emptyList(),
|
||||
System.currentTimeMillis(),
|
||||
0,
|
||||
false,
|
||||
|
|
|
@ -38,6 +38,7 @@ import org.thoughtcrime.securesms.payments.backup.RecoveryPhraseStates;
|
|||
import org.thoughtcrime.securesms.payments.backup.confirm.PaymentsRecoveryPhraseConfirmFragment;
|
||||
import org.thoughtcrime.securesms.payments.preferences.model.InfoCard;
|
||||
import org.thoughtcrime.securesms.payments.preferences.model.PaymentItem;
|
||||
import org.thoughtcrime.securesms.registration.RegistrationNavigationActivity;
|
||||
import org.thoughtcrime.securesms.util.CommunicationActions;
|
||||
import org.thoughtcrime.securesms.util.PlayStoreUtil;
|
||||
import org.thoughtcrime.securesms.util.SpanUtil;
|
||||
|
@ -261,6 +262,8 @@ public class PaymentsHomeFragment extends LoggingFragment {
|
|||
reminderView.get().setOnActionClickListener(actionId -> {
|
||||
if (actionId == R.id.reminder_action_update_now) {
|
||||
PlayStoreUtil.openPlayStoreOrOurApkDownloadPage(requireContext());
|
||||
} else if (actionId == R.id.reminder_action_re_register) {
|
||||
startActivity(RegistrationNavigationActivity.newIntentForReRegistration(requireContext()));
|
||||
}
|
||||
});
|
||||
} else {
|
||||
|
|
|
@ -49,6 +49,8 @@ import org.thoughtcrime.securesms.util.ThemeUtil;
|
|||
import org.thoughtcrime.securesms.util.Util;
|
||||
import org.thoughtcrime.securesms.util.WindowUtil;
|
||||
|
||||
import java.util.Arrays;
|
||||
import java.util.List;
|
||||
import java.util.Objects;
|
||||
|
||||
import kotlin.Unit;
|
||||
|
@ -87,6 +89,8 @@ public final class RecipientBottomSheetDialogFragment extends BottomSheetDialogF
|
|||
private BadgeImageView badgeImageView;
|
||||
private Callback callback;
|
||||
|
||||
private ButtonStripPreference.ViewHolder buttonStripViewHolder;
|
||||
|
||||
public static BottomSheetDialogFragment create(@NonNull RecipientId recipientId,
|
||||
@Nullable GroupId groupId)
|
||||
{
|
||||
|
@ -135,6 +139,7 @@ public final class RecipientBottomSheetDialogFragment extends BottomSheetDialogF
|
|||
interactionsContainer = view.findViewById(R.id.interactions_container);
|
||||
badgeImageView = view.findViewById(R.id.rbs_badge);
|
||||
|
||||
buttonStripViewHolder = new ButtonStripPreference.ViewHolder(buttonStrip);
|
||||
return view;
|
||||
}
|
||||
|
||||
|
@ -245,6 +250,7 @@ public final class RecipientBottomSheetDialogFragment extends BottomSheetDialogF
|
|||
ButtonStripPreference.Model buttonStripModel = new ButtonStripPreference.Model(
|
||||
buttonStripState,
|
||||
DSLSettingsIcon.from(ContextUtil.requireDrawable(requireContext(), R.drawable.selectable_recipient_bottom_sheet_icon_button)),
|
||||
!viewModel.isDeprecatedOrUnregistered(),
|
||||
() -> Unit.INSTANCE,
|
||||
() -> {
|
||||
dismiss();
|
||||
|
@ -267,7 +273,7 @@ public final class RecipientBottomSheetDialogFragment extends BottomSheetDialogF
|
|||
() -> Unit.INSTANCE
|
||||
);
|
||||
|
||||
new ButtonStripPreference.ViewHolder(buttonStrip).bind(buttonStripModel);
|
||||
buttonStripViewHolder.bind(buttonStripModel);
|
||||
|
||||
if (recipient.isReleaseNotes()) {
|
||||
buttonStrip.setVisibility(View.GONE);
|
||||
|
@ -342,12 +348,21 @@ public final class RecipientBottomSheetDialogFragment extends BottomSheetDialogF
|
|||
viewModel.getAdminActionBusy().observe(getViewLifecycleOwner(), busy -> {
|
||||
adminActionBusy.setVisibility(busy ? View.VISIBLE : View.GONE);
|
||||
|
||||
makeGroupAdminButton.setEnabled(!busy);
|
||||
removeAdminButton.setEnabled(!busy);
|
||||
removeFromGroupButton.setEnabled(!busy);
|
||||
boolean userLoggedOut = viewModel.isDeprecatedOrUnregistered();
|
||||
makeGroupAdminButton.setEnabled(!busy && !userLoggedOut);
|
||||
removeAdminButton.setEnabled(!busy && !userLoggedOut);
|
||||
removeFromGroupButton.setEnabled(!busy && !userLoggedOut);
|
||||
});
|
||||
|
||||
callback = getParentFragment() != null && getParentFragment() instanceof Callback ? (Callback) getParentFragment() : null;
|
||||
|
||||
if (viewModel.isDeprecatedOrUnregistered()) {
|
||||
List<TextView> viewsToDisable = Arrays.asList(blockButton, unblockButton, removeFromGroupButton, makeGroupAdminButton, removeAdminButton, addToGroupButton, viewSafetyNumberButton);
|
||||
for (TextView view : viewsToDisable) {
|
||||
view.setEnabled(false);
|
||||
view.setAlpha(0.5f);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
|
|
|
@ -29,12 +29,14 @@ import org.thoughtcrime.securesms.groups.LiveGroup;
|
|||
import org.thoughtcrime.securesms.groups.ui.GroupChangeFailureReason;
|
||||
import org.thoughtcrime.securesms.groups.ui.GroupErrors;
|
||||
import org.thoughtcrime.securesms.groups.ui.addtogroup.AddToGroupsActivity;
|
||||
import org.thoughtcrime.securesms.keyvalue.SignalStore;
|
||||
import org.thoughtcrime.securesms.recipients.Recipient;
|
||||
import org.thoughtcrime.securesms.recipients.RecipientId;
|
||||
import org.thoughtcrime.securesms.recipients.RecipientUtil;
|
||||
import org.thoughtcrime.securesms.stories.StoryViewerArgs;
|
||||
import org.thoughtcrime.securesms.stories.viewer.StoryViewerActivity;
|
||||
import org.thoughtcrime.securesms.util.CommunicationActions;
|
||||
import org.thoughtcrime.securesms.util.TextSecurePreferences;
|
||||
import org.thoughtcrime.securesms.util.livedata.LiveDataUtil;
|
||||
import org.thoughtcrime.securesms.verify.VerifyIdentityActivity;
|
||||
|
||||
|
@ -54,16 +56,17 @@ final class RecipientDialogViewModel extends ViewModel {
|
|||
private final MutableLiveData<Boolean> adminActionBusy;
|
||||
private final MutableLiveData<StoryViewState> storyViewState;
|
||||
private final CompositeDisposable disposables;
|
||||
|
||||
private final boolean isDeprecatedOrUnregistered;
|
||||
private RecipientDialogViewModel(@NonNull Context context,
|
||||
@NonNull RecipientDialogRepository recipientDialogRepository)
|
||||
{
|
||||
this.context = context;
|
||||
this.recipientDialogRepository = recipientDialogRepository;
|
||||
this.identity = new MutableLiveData<>();
|
||||
this.adminActionBusy = new MutableLiveData<>(false);
|
||||
this.storyViewState = new MutableLiveData<>();
|
||||
this.disposables = new CompositeDisposable();
|
||||
this.context = context;
|
||||
this.recipientDialogRepository = recipientDialogRepository;
|
||||
this.identity = new MutableLiveData<>();
|
||||
this.adminActionBusy = new MutableLiveData<>(false);
|
||||
this.storyViewState = new MutableLiveData<>();
|
||||
this.disposables = new CompositeDisposable();
|
||||
this.isDeprecatedOrUnregistered = SignalStore.misc().isClientDeprecated() || TextSecurePreferences.isUnauthorizedReceived(context);
|
||||
|
||||
boolean recipientIsSelf = recipientDialogRepository.getRecipientId().equals(Recipient.self().getId());
|
||||
|
||||
|
@ -113,6 +116,10 @@ final class RecipientDialogViewModel extends ViewModel {
|
|||
disposables.clear();
|
||||
}
|
||||
|
||||
boolean isDeprecatedOrUnregistered() {
|
||||
return isDeprecatedOrUnregistered;
|
||||
}
|
||||
|
||||
LiveData<StoryViewState> getStoryViewState() {
|
||||
return storyViewState;
|
||||
}
|
||||
|
|
|
@ -10,6 +10,7 @@ import android.view.MenuItem
|
|||
import android.view.View
|
||||
import android.widget.Toast
|
||||
import androidx.activity.OnBackPressedCallback
|
||||
import androidx.annotation.IdRes
|
||||
import androidx.core.app.ActivityOptionsCompat
|
||||
import androidx.core.app.SharedElementCallback
|
||||
import androidx.core.view.ViewCompat
|
||||
|
@ -21,9 +22,16 @@ import com.google.android.material.snackbar.Snackbar
|
|||
import io.reactivex.rxjava3.android.schedulers.AndroidSchedulers
|
||||
import io.reactivex.rxjava3.core.Single
|
||||
import io.reactivex.rxjava3.kotlin.subscribeBy
|
||||
import org.greenrobot.eventbus.EventBus
|
||||
import org.greenrobot.eventbus.Subscribe
|
||||
import org.greenrobot.eventbus.ThreadMode
|
||||
import org.signal.core.util.concurrent.LifecycleDisposable
|
||||
import org.thoughtcrime.securesms.R
|
||||
import org.thoughtcrime.securesms.components.Material3SearchToolbar
|
||||
import org.thoughtcrime.securesms.components.reminder.ExpiredBuildReminder
|
||||
import org.thoughtcrime.securesms.components.reminder.Reminder
|
||||
import org.thoughtcrime.securesms.components.reminder.ReminderView
|
||||
import org.thoughtcrime.securesms.components.reminder.UnauthorizedReminder
|
||||
import org.thoughtcrime.securesms.components.settings.DSLConfiguration
|
||||
import org.thoughtcrime.securesms.components.settings.DSLSettingsFragment
|
||||
import org.thoughtcrime.securesms.components.settings.DSLSettingsText
|
||||
|
@ -35,10 +43,12 @@ import org.thoughtcrime.securesms.database.model.MediaMmsMessageRecord
|
|||
import org.thoughtcrime.securesms.database.model.MmsMessageRecord
|
||||
import org.thoughtcrime.securesms.database.model.StoryViewState
|
||||
import org.thoughtcrime.securesms.dependencies.ApplicationDependencies
|
||||
import org.thoughtcrime.securesms.events.ReminderUpdateEvent
|
||||
import org.thoughtcrime.securesms.main.Material3OnScrollHelperBinder
|
||||
import org.thoughtcrime.securesms.main.SearchBinder
|
||||
import org.thoughtcrime.securesms.mediasend.v2.MediaSelectionActivity
|
||||
import org.thoughtcrime.securesms.permissions.Permissions
|
||||
import org.thoughtcrime.securesms.registration.RegistrationNavigationActivity
|
||||
import org.thoughtcrime.securesms.safety.SafetyNumberBottomSheet
|
||||
import org.thoughtcrime.securesms.stories.StoryTextPostModel
|
||||
import org.thoughtcrime.securesms.stories.StoryViewerArgs
|
||||
|
@ -49,8 +59,11 @@ import org.thoughtcrime.securesms.stories.settings.StorySettingsActivity
|
|||
import org.thoughtcrime.securesms.stories.tabs.ConversationListTab
|
||||
import org.thoughtcrime.securesms.stories.tabs.ConversationListTabsViewModel
|
||||
import org.thoughtcrime.securesms.stories.viewer.StoryViewerActivity
|
||||
import org.thoughtcrime.securesms.util.PlayStoreUtil
|
||||
import org.thoughtcrime.securesms.util.ViewUtil
|
||||
import org.thoughtcrime.securesms.util.adapter.mapping.MappingAdapter
|
||||
import org.thoughtcrime.securesms.util.fragments.requireListener
|
||||
import org.thoughtcrime.securesms.util.views.Stub
|
||||
import org.thoughtcrime.securesms.util.visible
|
||||
import java.util.concurrent.TimeUnit
|
||||
|
||||
|
@ -66,6 +79,8 @@ class StoriesLandingFragment : DSLSettingsFragment(layoutId = R.layout.stories_l
|
|||
private lateinit var emptyNotice: View
|
||||
private lateinit var cameraFab: FloatingActionButton
|
||||
|
||||
private lateinit var reminderView: Stub<ReminderView>
|
||||
|
||||
private val lifecycleDisposable = LifecycleDisposable()
|
||||
|
||||
private val viewModel: StoriesLandingViewModel by viewModels(
|
||||
|
@ -95,11 +110,13 @@ class StoriesLandingFragment : DSLSettingsFragment(layoutId = R.layout.stories_l
|
|||
viewModel.markStoriesRead()
|
||||
|
||||
ApplicationDependencies.getExpireStoriesManager().scheduleIfNecessary()
|
||||
EventBus.getDefault().register(this)
|
||||
}
|
||||
|
||||
override fun onPause() {
|
||||
super.onPause()
|
||||
requireListener<SearchBinder>().getSearchAction().setOnClickListener(null)
|
||||
EventBus.getDefault().unregister(this)
|
||||
}
|
||||
|
||||
private fun initializeSearchAction() {
|
||||
|
@ -121,6 +138,57 @@ class StoriesLandingFragment : DSLSettingsFragment(layoutId = R.layout.stories_l
|
|||
}
|
||||
}
|
||||
|
||||
override fun onViewCreated(view: View, savedInstanceState: Bundle?) {
|
||||
super.onViewCreated(view, savedInstanceState)
|
||||
|
||||
reminderView = ViewUtil.findStubById(view, R.id.reminder)
|
||||
updateReminders()
|
||||
}
|
||||
|
||||
@Subscribe(threadMode = ThreadMode.MAIN)
|
||||
fun onEvent(event: ReminderUpdateEvent?) {
|
||||
updateReminders()
|
||||
}
|
||||
|
||||
private fun updateReminders() {
|
||||
if (ExpiredBuildReminder.isEligible()) {
|
||||
showReminder(ExpiredBuildReminder(context))
|
||||
} else if (UnauthorizedReminder.isEligible(context)) {
|
||||
showReminder(UnauthorizedReminder(context))
|
||||
} else {
|
||||
hideReminders()
|
||||
}
|
||||
}
|
||||
|
||||
private fun showReminder(reminder: Reminder) {
|
||||
if (!reminderView.resolved()) {
|
||||
reminderView.get().addOnLayoutChangeListener { _, _, top, _, bottom, _, _, _, _ ->
|
||||
recyclerView?.setPadding(0, bottom - top, 0, 0)
|
||||
}
|
||||
recyclerView?.clipToPadding = false
|
||||
}
|
||||
reminderView.get().showReminder(reminder)
|
||||
reminderView.get().setOnActionClickListener { reminderActionId: Int -> this.handleReminderAction(reminderActionId) }
|
||||
}
|
||||
|
||||
private fun hideReminders() {
|
||||
if (reminderView.resolved()) {
|
||||
reminderView.get().hide()
|
||||
recyclerView?.clipToPadding = true
|
||||
}
|
||||
}
|
||||
|
||||
private fun handleReminderAction(@IdRes reminderActionId: Int) {
|
||||
when (reminderActionId) {
|
||||
R.id.reminder_action_update_now -> {
|
||||
PlayStoreUtil.openPlayStoreOrOurApkDownloadPage(requireContext())
|
||||
}
|
||||
R.id.reminder_action_re_register -> {
|
||||
startActivity(RegistrationNavigationActivity.newIntentForReRegistration(requireContext()))
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
override fun bindAdapter(adapter: MappingAdapter) {
|
||||
this.adapter = adapter
|
||||
|
||||
|
|
|
@ -24,6 +24,7 @@ import com.google.android.material.dialog.MaterialAlertDialogBuilder;
|
|||
|
||||
import org.thoughtcrime.securesms.R;
|
||||
import org.thoughtcrime.securesms.keyvalue.SignalStore;
|
||||
import org.thoughtcrime.securesms.registration.RegistrationNavigationActivity;
|
||||
|
||||
public class Dialogs {
|
||||
public static void showAlertDialog(Context context, String title, String message) {
|
||||
|
@ -54,4 +55,26 @@ public class Dialogs {
|
|||
})
|
||||
.show();
|
||||
}
|
||||
|
||||
public static void showUpgradeSignalDialog(@NonNull Context context) {
|
||||
new MaterialAlertDialogBuilder(context)
|
||||
.setTitle(R.string.UpdateSignalExpiredDialog__title)
|
||||
.setMessage(R.string.UpdateSignalExpiredDialog__message)
|
||||
.setNegativeButton(R.string.UpdateSignalExpiredDialog__cancel_action, null)
|
||||
.setPositiveButton(R.string.UpdateSignalExpiredDialog__update_action, (d, w) -> {
|
||||
PlayStoreUtil.openPlayStoreOrOurApkDownloadPage(context);
|
||||
})
|
||||
.show();
|
||||
}
|
||||
|
||||
public static void showReregisterSignalDialog(@NonNull Context context) {
|
||||
new MaterialAlertDialogBuilder(context)
|
||||
.setTitle(R.string.ReregisterSignalDialog__title)
|
||||
.setMessage(R.string.ReregisterSignalDialog__message)
|
||||
.setNegativeButton(R.string.ReregisterSignalDialog__cancel_action, null)
|
||||
.setPositiveButton(R.string.ReregisterSignalDialog__reregister_action, (d, w) -> {
|
||||
context.startActivity(RegistrationNavigationActivity.newIntentForReRegistration(context));
|
||||
})
|
||||
.show();
|
||||
}
|
||||
}
|
||||
|
|
|
@ -0,0 +1,5 @@
|
|||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<selector xmlns:android="http://schemas.android.com/apk/res/android">
|
||||
<item android:color="@color/signal_colorOnSurface_50" android:state_enabled="false" />
|
||||
<item android:color="@color/signal_colorOnSurface" />
|
||||
</selector>
|
|
@ -148,6 +148,13 @@
|
|||
android:inflatedId="@+id/sms_export_view"
|
||||
android:layout="@layout/conversation_activity_sms_export_stub" />
|
||||
|
||||
<ViewStub
|
||||
android:id="@+id/logged_out_stub"
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="wrap_content"
|
||||
android:inflatedId="@+id/logged_out_view"
|
||||
android:layout="@layout/conversation_activity_logged_out_stub" />
|
||||
|
||||
<TextView
|
||||
android:id="@+id/space_left"
|
||||
android:layout_width="fill_parent"
|
||||
|
|
|
@ -0,0 +1,27 @@
|
|||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
|
||||
xmlns:tools="http://schemas.android.com/tools"
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="wrap_content"
|
||||
android:gravity="center_horizontal"
|
||||
android:orientation="vertical"
|
||||
android:padding="24dp">
|
||||
|
||||
<TextView
|
||||
android:id="@+id/logged_out_message"
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="wrap_content"
|
||||
android:gravity="center"
|
||||
android:textAppearance="@style/Signal.Text.BodyMedium"
|
||||
android:textColor="@color/signal_colorOnSurfaceVariant"
|
||||
tools:text="This device is no longer registered. Re-register to continue using Signal on this device." />
|
||||
|
||||
<com.google.android.material.button.MaterialButton
|
||||
android:id="@+id/logged_out_button"
|
||||
style="@style/Signal.Widget.Button.Large.Tonal"
|
||||
android:layout_width="wrap_content"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_marginTop="24dp"
|
||||
tools:text="Re-register" />
|
||||
|
||||
</LinearLayout>
|
|
@ -0,0 +1,30 @@
|
|||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<androidx.constraintlayout.widget.ConstraintLayout xmlns:android="http://schemas.android.com/apk/res/android"
|
||||
xmlns:tools="http://schemas.android.com/tools"
|
||||
tools:viewBindingIgnore="true"
|
||||
xmlns:app="http://schemas.android.com/apk/res-auto"
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="match_parent">
|
||||
|
||||
<include layout="@layout/dsl_settings_toolbar" />
|
||||
|
||||
<androidx.recyclerview.widget.RecyclerView
|
||||
android:id="@+id/recycler"
|
||||
android:layout_width="0dp"
|
||||
android:layout_height="0dp"
|
||||
android:orientation="vertical"
|
||||
app:layoutManager="androidx.recyclerview.widget.LinearLayoutManager"
|
||||
app:layout_constraintBottom_toBottomOf="parent"
|
||||
app:layout_constraintEnd_toEndOf="parent"
|
||||
app:layout_constraintStart_toStartOf="parent"
|
||||
app:layout_constraintTop_toBottomOf="@id/toolbar" />
|
||||
|
||||
<ViewStub
|
||||
android:id="@+id/reminder_stub"
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="wrap_content"
|
||||
android:inflatedId="@+id/reminder"
|
||||
android:layout="@layout/conversation_activity_reminderview_stub"
|
||||
app:layout_constraintTop_toTopOf="@id/recycler"/>
|
||||
|
||||
</androidx.constraintlayout.widget.ConstraintLayout>
|
|
@ -136,6 +136,7 @@
|
|||
android:textAppearance="@style/Signal.Text.BodyLarge"
|
||||
android:visibility="gone"
|
||||
app:drawableStartCompat="@drawable/ic_block_tinted_24"
|
||||
app:drawableTint="@color/icon_tint_color_primary_enabled_selector"
|
||||
tools:visibility="visible" />
|
||||
|
||||
<TextView
|
||||
|
@ -152,6 +153,7 @@
|
|||
android:textAppearance="@style/Signal.Text.BodyLarge"
|
||||
android:visibility="gone"
|
||||
app:drawableStartCompat="@drawable/ic_block_tinted_24"
|
||||
app:drawableTint="@color/icon_tint_color_primary_enabled_selector"
|
||||
tools:visibility="visible" />
|
||||
|
||||
<TextView
|
||||
|
@ -168,6 +170,7 @@
|
|||
android:textAppearance="@style/Signal.Text.BodyLarge"
|
||||
android:visibility="gone"
|
||||
app:drawableStartCompat="@drawable/ic_leave_tinted_24"
|
||||
app:drawableTint="@color/icon_tint_color_primary_enabled_selector"
|
||||
tools:visibility="visible" />
|
||||
|
||||
<TextView
|
||||
|
@ -184,6 +187,7 @@
|
|||
android:textAppearance="@style/Signal.Text.BodyLarge"
|
||||
android:visibility="gone"
|
||||
app:drawableStartCompat="@drawable/ic_group_24"
|
||||
app:drawableTint="@color/icon_tint_color_primary_enabled_selector"
|
||||
tools:visibility="visible" />
|
||||
|
||||
<TextView
|
||||
|
@ -200,6 +204,7 @@
|
|||
android:textAppearance="@style/Signal.Text.BodyLarge"
|
||||
android:visibility="gone"
|
||||
app:drawableStartCompat="@drawable/ic_group_24"
|
||||
app:drawableTint="@color/icon_tint_color_primary_enabled_selector"
|
||||
tools:visibility="visible" />
|
||||
|
||||
<TextView
|
||||
|
@ -215,6 +220,7 @@
|
|||
android:textAppearance="@style/Signal.Text.BodyLarge"
|
||||
android:visibility="gone"
|
||||
app:drawableStartCompat="@drawable/ic_group_24"
|
||||
app:drawableTint="@color/icon_tint_color_primary_enabled_selector"
|
||||
tools:text="@string/RecipientBottomSheet_add_to_a_group"
|
||||
tools:visibility="visible" />
|
||||
|
||||
|
@ -232,6 +238,7 @@
|
|||
android:textAppearance="@style/Signal.Text.BodyLarge"
|
||||
android:visibility="gone"
|
||||
app:drawableStartCompat="@drawable/ic_plus_24"
|
||||
app:drawableTint="@color/icon_tint_color_primary_enabled_selector"
|
||||
tools:visibility="visible" />
|
||||
|
||||
<TextView
|
||||
|
@ -248,6 +255,7 @@
|
|||
android:textAppearance="@style/Signal.Text.BodyLarge"
|
||||
android:visibility="gone"
|
||||
app:drawableStartCompat="@drawable/ic_profile_circle_24"
|
||||
app:drawableTint="@color/icon_tint_color_primary_enabled_selector"
|
||||
tools:visibility="visible" />
|
||||
|
||||
<TextView
|
||||
|
@ -264,7 +272,7 @@
|
|||
android:textAppearance="@style/Signal.Text.BodyLarge"
|
||||
android:visibility="gone"
|
||||
app:drawableStartCompat="@drawable/ic_safety_number_24"
|
||||
app:drawableTint="@color/signal_icon_tint_primary"
|
||||
app:drawableTint="@color/icon_tint_color_primary_enabled_selector"
|
||||
tools:visibility="visible" />
|
||||
|
||||
</LinearLayout>
|
||||
|
|
|
@ -100,5 +100,12 @@
|
|||
app:layout_constraintTop_toTopOf="parent"
|
||||
tools:visibility="visible" />
|
||||
|
||||
<ViewStub
|
||||
android:id="@+id/reminder"
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="wrap_content"
|
||||
android:inflatedId="@+id/reminder"
|
||||
android:layout="@layout/stories_landing_reminder_view"
|
||||
app:layout_constraintTop_toTopOf="parent" />
|
||||
|
||||
</androidx.constraintlayout.widget.ConstraintLayout>
|
|
@ -0,0 +1,8 @@
|
|||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<org.thoughtcrime.securesms.components.reminder.ReminderView
|
||||
xmlns:tools="http://schemas.android.com/tools"
|
||||
tools:viewBindingIgnore="true"
|
||||
xmlns:android="http://schemas.android.com/apk/res/android"
|
||||
android:id="@+id/reminder"
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="wrap_content" />
|
|
@ -51,6 +51,7 @@
|
|||
<color name="signal_divider_major">@color/core_grey_60</color>
|
||||
|
||||
<color name="signal_alert_primary">@color/core_red</color>
|
||||
<color name="signal_alert_primary_50">@color/core_red_50</color>
|
||||
|
||||
<color name="signal_transparent">@color/transparent_black</color>
|
||||
<color name="signal_transparent_40">@color/transparent_black_40</color>
|
||||
|
|
|
@ -53,6 +53,7 @@
|
|||
<color name="signal_colorSurfaceVariant_38">#61303133</color>
|
||||
<color name="signal_colorSurfaceVariant_64">#A3303133</color>
|
||||
<color name="signal_colorOnSurface_12">#1FE2E1E5</color>
|
||||
<color name="signal_colorOnSurface_50">#80E2E1E5</color>
|
||||
<color name="signal_colorOnSurfaceVariant_60">#99BEBFC5</color>
|
||||
<color name="signal_colorOnBackground_60">#99E2E1E5</color>
|
||||
<color name="signal_colorOutline_38">#615C5E65</color>
|
||||
|
|
|
@ -10,7 +10,9 @@
|
|||
<color name="core_green">#4caf50</color>
|
||||
<color name="core_yellow">#ffd624</color>
|
||||
<color name="core_red">#f44336</color>
|
||||
<color name="core_red_50">#80f44336</color>
|
||||
<color name="core_red_highlight">#ef5350</color>
|
||||
<color name="core_red_highlight_50">#80ef5350</color>
|
||||
<color name="core_red_shade">#e51d0e</color>
|
||||
|
||||
<color name="core_white">#ffffff</color>
|
||||
|
|
|
@ -7,6 +7,7 @@
|
|||
<item name="reminder_action_view_insights" type="id" />
|
||||
<item name="reminder_action_invite" type="id" />
|
||||
<item name="reminder_action_update_now" type="id" />
|
||||
<item name="reminder_action_re_register" type="id" />
|
||||
<item name="reminder_action_review_join_requests" type="id" />
|
||||
|
||||
<item name="reminder_action_gv1_suggestion_no_thanks" type="id" />
|
||||
|
|
|
@ -50,6 +50,7 @@
|
|||
<color name="signal_divider_major">@color/core_grey_25</color>
|
||||
|
||||
<color name="signal_alert_primary">@color/core_red_highlight</color>
|
||||
<color name="signal_alert_primary_50">@color/core_red_highlight_50</color>
|
||||
|
||||
<color name="signal_transparent">@color/transparent</color>
|
||||
<color name="signal_transparent_40">@color/transparent_white_40</color>
|
||||
|
|
|
@ -53,6 +53,7 @@
|
|||
<color name="signal_colorSurfaceVariant_38">#61E7EBF3</color>
|
||||
<color name="signal_colorSurfaceVariant_64">#A3E7EBF3</color>
|
||||
<color name="signal_colorOnSurface_12">#1F1B1B1D</color>
|
||||
<color name="signal_colorOnSurface_50">#801B1B1D</color>
|
||||
<color name="signal_colorOnSurfaceVariant_60">#99545863</color>
|
||||
<color name="signal_colorOnBackground_60">#991B1D1D</color>
|
||||
<color name="signal_colorOutline_38">#61808389</color>
|
||||
|
|
|
@ -482,6 +482,10 @@
|
|||
<string name="ConversationFragment__cancel">Cancel</string>
|
||||
<!-- Message shown after successfully blocking join requests for a user -->
|
||||
<string name="ConversationFragment__blocked">Blocked</string>
|
||||
<!-- Action shown to allow a user to update their application because it has expired -->
|
||||
<string name="ConversationFragment__update_build">Update Signal</string>
|
||||
<!-- Action shown to allow a user to re-register as they are no longer registered -->
|
||||
<string name="ConversationFragment__reregister_signal">Re-register Signal</string>
|
||||
<!-- Label for a button displayed in conversation list to clear the chat filter -->
|
||||
<string name="ConversationListFragment__clear_filter">Clear filter</string>
|
||||
<!-- Notice on chat list when no unread chats are available, centered on display -->
|
||||
|
@ -2251,7 +2255,10 @@
|
|||
|
||||
<!-- UnauthorizedReminder -->
|
||||
<string name="UnauthorizedReminder_device_no_longer_registered">Device no longer registered</string>
|
||||
<string name="UnauthorizedReminder_this_is_likely_because_you_registered_your_phone_number_with_Signal_on_a_different_device">This is likely because you registered your phone number with Signal on a different device. Tap to re-register.</string>
|
||||
<!-- Message shown in a reminder banner when the user's device is no longer registered -->
|
||||
<string name="UnauthorizedReminder_this_is_likely_because_you_registered_your_phone_number_with_Signal_on_a_different_device">This device is no longer registered. This is likely because you registered your phone number with Signal on a different device.</string>
|
||||
<!-- Action in reminder banner that will take user to re-register -->
|
||||
<string name="UnauthorizedReminder_reregister_action">Re-register device</string>
|
||||
|
||||
<!-- Push notification when the app is forcibly logged out by the server. -->
|
||||
<string name="LoggedOutNotification_you_have_been_logged_out">You have been logged out of Signal on this device.</string>
|
||||
|
@ -3580,6 +3587,23 @@
|
|||
<string name="prompt_passphrase_activity__tap_to_unlock">TAP TO UNLOCK</string>
|
||||
<string name="Recipient_unknown">Unknown</string>
|
||||
|
||||
<!-- Option in settings that will take use to re-register if they are no longer registered -->
|
||||
<string name="preferences_account_reregister">Re-register account</string>
|
||||
<!-- Option in settings that will take user to our website or playstore to update their expired build -->
|
||||
<string name="preferences_account_update_signal">Update Signal</string>
|
||||
<!-- Option in settings shown when user is no longer registered or expired client that will WIPE ALL THEIR DATA -->
|
||||
<string name="preferences_account_delete_all_data">Delete all data</string>
|
||||
<!-- Title for confirmation dialog confirming user wants to delete all their data -->
|
||||
<string name="preferences_account_delete_all_data_confirmation_title">Delete all data?</string>
|
||||
<!-- Message in confirmation dialog to delete all data explaining how it works, and that the app will be closed after deletion -->
|
||||
<string name="preferences_account_delete_all_data_confirmation_message">This will reset the app and delete all messages. The app will close after this process is complete.</string>
|
||||
<!-- Confirmation action to proceed with application data deletion -->
|
||||
<string name="preferences_account_delete_all_data_confirmation_proceed">Proceed</string>
|
||||
<!-- Confirmation action to cancel application data deletion -->
|
||||
<string name="preferences_account_delete_all_data_confirmation_cancel">Cancel</string>
|
||||
<!-- Error message shown when we fail to delete the data for some unknown reason -->
|
||||
<string name="preferences_account_delete_all_data_failed">Failed to delete data</string>
|
||||
|
||||
<!-- TransferOrRestoreFragment -->
|
||||
<string name="TransferOrRestoreFragment__transfer_or_restore_account">Transfer or restore account</string>
|
||||
<string name="TransferOrRestoreFragment__if_you_have_previously_registered_a_signal_account">If you have previously registered a Signal account, you can transfer or restore your account and messages</string>
|
||||
|
@ -4637,6 +4661,24 @@
|
|||
<string name="MySupportPreference__couldnt_add_badge_s">Couldn\'t add badge. %1$s</string>
|
||||
<string name="MySupportPreference__please_contact_support">Please contact support.</string>
|
||||
|
||||
<!-- Title of dialog telling user they need to update signal as it expired -->
|
||||
<string name="UpdateSignalExpiredDialog__title">Update Signal</string>
|
||||
<!-- Message of dialog telling user they need to update signal as it expired -->
|
||||
<string name="UpdateSignalExpiredDialog__message">This version of Signal has expired. Update now to continue using Signal.</string>
|
||||
<!-- Button text of expiration dialog, will take user to update the app -->
|
||||
<string name="UpdateSignalExpiredDialog__update_action">Update</string>
|
||||
<!-- Button text of expiration dialog to cancel the dialog. -->
|
||||
<string name="UpdateSignalExpiredDialog__cancel_action">Cancel</string>
|
||||
|
||||
<!-- Title of dialog telling user they need to re-register signal -->
|
||||
<string name="ReregisterSignalDialog__title">Device not registered</string>
|
||||
<!-- Message of dialog telling user they need to re-register signal as it is no longer registered -->
|
||||
<string name="ReregisterSignalDialog__message">This device is no longer registered. Re-register to continue using Signal on this device.</string>
|
||||
<!-- Button text of re-registration dialog to re-register the device. -->
|
||||
<string name="ReregisterSignalDialog__reregister_action">Re-register</string>
|
||||
<!-- Button text of re-registration dialog to cancel the dialog. -->
|
||||
<string name="ReregisterSignalDialog__cancel_action">Cancel</string>
|
||||
|
||||
<!-- Title of expiry sheet when boost badge falls off profile unexpectedly. -->
|
||||
<string name="ExpiredBadgeBottomSheetDialogFragment__boost_badge_expired">Boost Badge Expired</string>
|
||||
<!-- Displayed in the bottom sheet if a monthly donation badge unexpectedly falls off the user\'s profile -->
|
||||
|
|
Loading…
Add table
Reference in a new issue