diff --git a/app/src/main/AndroidManifest.xml b/app/src/main/AndroidManifest.xml index 05c72e8b2..a43986fee 100644 --- a/app/src/main/AndroidManifest.xml +++ b/app/src/main/AndroidManifest.xml @@ -57,6 +57,7 @@ android:theme="@style/Hydra.Material" android:localeConfig="@xml/locales_config" android:networkSecurityConfig="@xml/network_security_config" + android:enableOnBackInvokedCallback="true" tools:ignore="AllowBackup,GoogleAppIndexingWarning,UnusedAttribute" tools:replace="android:supportsRtl"> diff --git a/app/src/main/java/be/ugent/zeus/hydra/MainActivity.java b/app/src/main/java/be/ugent/zeus/hydra/MainActivity.java index 706c996df..9093885d5 100644 --- a/app/src/main/java/be/ugent/zeus/hydra/MainActivity.java +++ b/app/src/main/java/be/ugent/zeus/hydra/MainActivity.java @@ -31,6 +31,7 @@ import android.util.Log; import android.view.MenuItem; import android.view.View; +import androidx.activity.OnBackPressedCallback; import androidx.annotation.*; import androidx.appcompat.app.ActionBarDrawerToggle; import androidx.core.view.GravityCompat; @@ -58,14 +59,15 @@ import be.ugent.zeus.hydra.resto.menu.RestoFragment; import be.ugent.zeus.hydra.schamper.SchamperFragment; import be.ugent.zeus.hydra.urgent.UrgentFragment; +import be.ugent.zeus.hydra.wpi.EnableManager; +import be.ugent.zeus.hydra.wpi.WpiActivity; import com.google.android.material.bottomnavigation.BottomNavigationView; import com.google.android.material.navigation.NavigationView; import com.google.android.material.shape.MaterialShapeDrawable; import com.google.android.material.tabs.TabLayout; -import be.ugent.zeus.hydra.wpi.EnableManager; -import be.ugent.zeus.hydra.wpi.WpiActivity; import dev.chrisbanes.insetter.Insetter; import jonathanfinerty.once.Once; +import org.jetbrains.annotations.NotNull; import static be.ugent.zeus.hydra.common.utils.FragmentUtils.requireArguments; @@ -260,6 +262,37 @@ private void initialize(@Nullable Bundle savedInstanceState) { // Register the listener for navigation events from the drawer. binding.navigationView.setNavigationItemSelectedListener(this); + OnBackPressedCallback drawerCloser = new OnBackPressedCallback(false) { + + @Override + public void handleOnBackPressed() { + binding.drawerLayout.closeDrawer(GravityCompat.START); + } + }; + getOnBackPressedDispatcher().addCallback(this, drawerCloser); + + binding.drawerLayout.addDrawerListener(new DrawerLayout.DrawerListener() { + @Override + public void onDrawerSlide(@NonNull @NotNull View drawerView, float slideOffset) { + // Do nothing. + } + + @Override + public void onDrawerOpened(@NonNull @NotNull View drawerView) { + drawerCloser.setEnabled(true); + } + + @Override + public void onDrawerClosed(@NonNull @NotNull View drawerView) { + drawerCloser.setEnabled(false); + } + + @Override + public void onDrawerStateChanged(int newState) { + // Do nothing. + } + }); + toggle = new ActionBarDrawerToggle(this, binding.drawerLayout, binding.toolbar, R.string.action_drawer_open, R.string.action_drawer_close) { @Override public void onDrawerSlide(View drawerView, float slideOffset) { @@ -498,44 +531,6 @@ private void setFragment(Fragment fragment, MenuItem menuItem, @NavigationSource binding.progressBar.progressBar.setVisibility(View.GONE); } - /** - * Implements the correct back-button behaviour for the drawer. If the drawer does not consume the back press, - * the parent method is called. - */ - @Override - public void onBackPressed() { - // If the drawer is open, close it. - if (binding.drawerLayout.isDrawerOpen(GravityCompat.START)) { - binding.drawerLayout.closeDrawer(GravityCompat.START); - return; - } - - // The super method handles both the fragment back stack and finishing the activity. To know what was executed, - // we need to add a listener. - FragmentManager.OnBackStackChangedListener listener = () -> { - Fragment current = getSupportFragmentManager().findFragmentById(R.id.content); - Log.w(TAG, "onBackPressed: current fragment is somehow null? Ignoring update for now."); - if (current == null) { - return; - } - MenuItem item = binding.navigationView.getMenu().findItem(getFragmentMenuId(current)); - updateDrawer(current, item); - }; - - // Allow the current fragment to intercept the back press. - Fragment current = getSupportFragmentManager().findFragmentById(R.id.content); - if (current instanceof OnBackPressed && (((OnBackPressed) current).onBackPressed())) { - // The fragment has handled it. - return; - } - - // We need to listen to the back stack to update the drawer. - getSupportFragmentManager().addOnBackStackChangedListener(listener); - super.onBackPressed(); - // The drawer has been updated, so we abandon the listener. - getSupportFragmentManager().removeOnBackStackChangedListener(listener); - } - /** * Set the menu ID as argument for a fragment. * @@ -665,21 +660,6 @@ public interface ScheduledRemovalListener { void onRemovalScheduled(); } - /** - * Allows fragments to listen to and intercept back button presses. - */ - @FunctionalInterface - public interface OnBackPressed { - - /** - * Called when the back button is pressed. This function provides the fragment - * with an opportunity to intercept the back press. - * - * @return True if consumed, false otherwise. Consumed events are not propagated. - */ - boolean onBackPressed(); - } - private static final class TutorialEndEvent implements Event { @Nullable @Override diff --git a/app/src/main/java/be/ugent/zeus/hydra/association/list/EventFragment.java b/app/src/main/java/be/ugent/zeus/hydra/association/list/EventFragment.java index 2604a004f..6e288dae3 100644 --- a/app/src/main/java/be/ugent/zeus/hydra/association/list/EventFragment.java +++ b/app/src/main/java/be/ugent/zeus/hydra/association/list/EventFragment.java @@ -28,6 +28,7 @@ import android.widget.Button; import android.widget.FrameLayout; import android.widget.LinearLayout; +import androidx.activity.OnBackPressedCallback; import androidx.annotation.NonNull; import androidx.annotation.Nullable; import androidx.appcompat.widget.Toolbar; @@ -68,7 +69,7 @@ * @author ellen * @author Niko Strijbol */ -public class EventFragment extends Fragment implements MainActivity.ScheduledRemovalListener, MainActivity.OnBackPressed { +public class EventFragment extends Fragment implements MainActivity.ScheduledRemovalListener { private static final String TAG = "EventFragment"; @@ -194,6 +195,30 @@ protected void onSuccess(@NonNull AssociationRequest.EventItemsAndAssociations d .setOnClickListener(v -> viewModel.onRefresh()); view.