diff options
author | Jason A. Donenfeld <Jason@zx2c4.com> | 2023-03-23 15:45:01 +0100 |
---|---|---|
committer | Jason A. Donenfeld <Jason@zx2c4.com> | 2023-03-24 14:12:21 +0100 |
commit | cf943b7119dcd09f70ea0557cec8401c38a04a35 (patch) | |
tree | ad15ba5f1fac94c3f463c0acd11a95a4c021ef6e | |
parent | b7295cd56f9ea94297d28f36bcba9a2cabc1c0a7 (diff) |
ui: migrate to OnBackPressedDispatcher
This is compatible with Android 13's prediction-based back gesture
animation.
Signed-off-by: Jason A. Donenfeld <Jason@zx2c4.com>
-rw-r--r-- | ui/src/main/AndroidManifest.xml | 1 | ||||
-rw-r--r-- | ui/src/main/java/com/wireguard/android/activity/MainActivity.kt | 21 | ||||
-rw-r--r-- | ui/src/main/java/com/wireguard/android/activity/TvMainActivity.kt | 16 |
3 files changed, 28 insertions, 10 deletions
diff --git a/ui/src/main/AndroidManifest.xml b/ui/src/main/AndroidManifest.xml index f1daac30..a7538a6e 100644 --- a/ui/src/main/AndroidManifest.xml +++ b/ui/src/main/AndroidManifest.xml @@ -35,6 +35,7 @@ android:name=".Application" android:allowBackup="false" android:banner="@mipmap/banner" + android:enableOnBackInvokedCallback="true" android:icon="@mipmap/ic_launcher" android:label="@string/app_name" android:roundIcon="@mipmap/ic_launcher_round" diff --git a/ui/src/main/java/com/wireguard/android/activity/MainActivity.kt b/ui/src/main/java/com/wireguard/android/activity/MainActivity.kt index 2276e873..1566c129 100644 --- a/ui/src/main/java/com/wireguard/android/activity/MainActivity.kt +++ b/ui/src/main/java/com/wireguard/android/activity/MainActivity.kt @@ -9,6 +9,8 @@ import android.os.Bundle import android.view.Menu import android.view.MenuItem import android.view.View +import androidx.activity.OnBackPressedCallback +import androidx.activity.addCallback import androidx.appcompat.app.ActionBar import androidx.fragment.app.FragmentManager import androidx.fragment.app.FragmentTransaction @@ -26,27 +28,29 @@ import com.wireguard.android.model.ObservableTunnel class MainActivity : BaseActivity(), FragmentManager.OnBackStackChangedListener { private var actionBar: ActionBar? = null private var isTwoPaneLayout = false + private var backPressedCallback: OnBackPressedCallback? = null - override fun onBackPressed() { + private fun handleBackPressed() { val backStackEntries = supportFragmentManager.backStackEntryCount // If the two-pane layout does not have an editor open, going back should exit the app. if (isTwoPaneLayout && backStackEntries <= 1) { finish() return } - // Deselect the current tunnel on navigating back from the detail pane to the one-pane list. - if (!isTwoPaneLayout && backStackEntries == 1) { + + if (backStackEntries >= 1) supportFragmentManager.popBackStack() + + // Deselect the current tunnel on navigating back from the detail pane to the one-pane list. + if (backStackEntries == 1) selectedTunnel = null - return - } - super.onBackPressed() } override fun onBackStackChanged() { + val backStackEntries = supportFragmentManager.backStackEntryCount + backPressedCallback?.isEnabled = backStackEntries >= 1 if (actionBar == null) return // Do not show the home menu when the two-pane layout is at the detail view (see above). - val backStackEntries = supportFragmentManager.backStackEntryCount val minBackStackEntries = if (isTwoPaneLayout) 2 else 1 actionBar!!.setDisplayHomeAsUpEnabled(backStackEntries >= minBackStackEntries) } @@ -57,6 +61,7 @@ class MainActivity : BaseActivity(), FragmentManager.OnBackStackChangedListener actionBar = supportActionBar isTwoPaneLayout = findViewById<View?>(R.id.master_detail_wrapper) != null supportFragmentManager.addOnBackStackChangedListener(this) + backPressedCallback = onBackPressedDispatcher.addCallback(this) { handleBackPressed() } onBackStackChanged() } @@ -69,7 +74,7 @@ class MainActivity : BaseActivity(), FragmentManager.OnBackStackChangedListener return when (item.itemId) { android.R.id.home -> { // The back arrow in the action bar should act the same as the back button. - onBackPressed() + onBackPressedDispatcher.onBackPressed() true } R.id.menu_action_edit -> { diff --git a/ui/src/main/java/com/wireguard/android/activity/TvMainActivity.kt b/ui/src/main/java/com/wireguard/android/activity/TvMainActivity.kt index a0903793..ae98f442 100644 --- a/ui/src/main/java/com/wireguard/android/activity/TvMainActivity.kt +++ b/ui/src/main/java/com/wireguard/android/activity/TvMainActivity.kt @@ -16,12 +16,14 @@ import android.os.storage.StorageVolume import android.util.Log import android.view.View import android.widget.Toast +import androidx.activity.addCallback import androidx.activity.result.contract.ActivityResultContracts import androidx.appcompat.app.AppCompatActivity import androidx.core.content.ContextCompat import androidx.core.content.getSystemService import androidx.core.view.forEach import androidx.databinding.DataBindingUtil +import androidx.databinding.Observable import androidx.databinding.ObservableBoolean import androidx.databinding.ObservableField import androidx.lifecycle.lifecycleScope @@ -185,6 +187,17 @@ class TvMainActivity : AppCompatActivity() { binding.tunnelList.requestFocus() } } + + val backPressedCallback = onBackPressedDispatcher.addCallback(this) { handleBackPressed() } + val updateBackPressedCallback = object : Observable.OnPropertyChangedCallback() { + override fun onPropertyChanged(sender: Observable?, propertyId: Int) { + backPressedCallback.isEnabled = isDeleting.get() || filesRoot.get()?.isNotEmpty() == true + } + } + isDeleting.addOnPropertyChangedCallback(updateBackPressedCallback) + filesRoot.addOnPropertyChangedCallback(updateBackPressedCallback) + backPressedCallback.isEnabled = false + binding.executePendingBindings() setContentView(binding.root) @@ -298,7 +311,7 @@ class TvMainActivity : AppCompatActivity() { } } - override fun onBackPressed() { + private fun handleBackPressed() { when { isDeleting.get() -> { isDeleting.set(false) @@ -313,7 +326,6 @@ class TvMainActivity : AppCompatActivity() { binding.tunnelList.requestFocus() } } - else -> super.onBackPressed() } } |