diff --git a/lib/java/com/google/android/material/motion/MaterialBackAnimationHelper.java b/lib/java/com/google/android/material/motion/MaterialBackAnimationHelper.java index f5cc1f884e5..4767a9180bc 100644 --- a/lib/java/com/google/android/material/motion/MaterialBackAnimationHelper.java +++ b/lib/java/com/google/android/material/motion/MaterialBackAnimationHelper.java @@ -71,7 +71,7 @@ public MaterialBackAnimationHelper(@NonNull V view) { context, R.attr.motionDurationShort2, CANCEL_DURATION_DEFAULT); } - protected float interpolateProgress(float progress) { + public float interpolateProgress(float progress) { return progressInterpolator.getInterpolation(progress); } diff --git a/lib/java/com/google/android/material/navigation/NavigationView.java b/lib/java/com/google/android/material/navigation/NavigationView.java index 4d7b709edc3..2a4bfa3024a 100644 --- a/lib/java/com/google/android/material/navigation/NavigationView.java +++ b/lib/java/com/google/android/material/navigation/NavigationView.java @@ -75,6 +75,7 @@ import androidx.drawerlayout.widget.DrawerLayout; import androidx.drawerlayout.widget.DrawerLayout.DrawerListener; import androidx.drawerlayout.widget.DrawerLayout.SimpleDrawerListener; +import com.google.android.material.animation.AnimationUtils; import com.google.android.material.drawable.DrawableUtils; import com.google.android.material.internal.ContextUtils; import com.google.android.material.internal.NavigationMenu; @@ -146,6 +147,8 @@ public class NavigationView extends ScrimInsetsFrameLayout implements MaterialBa private boolean bottomInsetScrimEnabled = true; @Px private int drawerLayoutCornerSize = 0; + private final boolean drawerLayoutCornerSizeBackAnimationEnabled; + @Px private final int drawerLayoutCornerSizeBackAnimationMax; private final ShapeableDelegate shapeableDelegate = ShapeableDelegate.create(this); private final MaterialSideContainerBackHelper sideContainerBackHelper = @@ -166,6 +169,7 @@ public void onDrawerOpened(@NonNull View drawerView) { public void onDrawerClosed(@NonNull View drawerView) { if (drawerView == NavigationView.this) { backOrchestrator.stopListeningForBackCallbacks(); + maybeClearCornerSizeAnimationForDrawerLayout(); } } }; @@ -199,6 +203,9 @@ public NavigationView(@NonNull Context context, @Nullable AttributeSet attrs, in // placed inside a drawer layout. drawerLayoutCornerSize = a.getDimensionPixelSize(R.styleable.NavigationView_drawerLayoutCornerSize, 0); + drawerLayoutCornerSizeBackAnimationEnabled = drawerLayoutCornerSize == 0; + drawerLayoutCornerSizeBackAnimationMax = + getResources().getDimensionPixelSize(R.dimen.m3_navigation_drawer_layout_corner_size); // Set the background to a MaterialShapeDrawable if it hasn't been set or if it can be converted // to a MaterialShapeDrawable. @@ -400,7 +407,7 @@ public void setForceCompatClippingEnabled(boolean enabled) { private void maybeUpdateCornerSizeForDrawerLayout(@Px int width, @Px int height) { if (getParent() instanceof DrawerLayout && getLayoutParams() instanceof DrawerLayout.LayoutParams - && drawerLayoutCornerSize > 0 + && (drawerLayoutCornerSize > 0 || drawerLayoutCornerSizeBackAnimationEnabled) && getBackground() instanceof MaterialShapeDrawable) { int layoutGravity = ((DrawerLayout.LayoutParams) getLayoutParams()).gravity; boolean isAbsGravityLeft = @@ -432,6 +439,13 @@ && getBackground() instanceof MaterialShapeDrawable) { } } + private void maybeClearCornerSizeAnimationForDrawerLayout() { + if (drawerLayoutCornerSizeBackAnimationEnabled && drawerLayoutCornerSize != 0) { + drawerLayoutCornerSize = 0; + maybeUpdateCornerSizeForDrawerLayout(getWidth(), getHeight()); + } + } + private boolean hasShapeAppearance(@NonNull TintTypedArray a) { return a.hasValue(R.styleable.NavigationView_itemShapeAppearance) || a.hasValue(R.styleable.NavigationView_itemShapeAppearanceOverlay); @@ -983,6 +997,13 @@ public void startBackProgress(@NonNull BackEventCompat backEvent) { public void updateBackProgress(@NonNull BackEventCompat backEvent) { Pair drawerLayoutPair = requireDrawerLayoutParent(); sideContainerBackHelper.updateBackProgress(backEvent, drawerLayoutPair.second.gravity); + + if (drawerLayoutCornerSizeBackAnimationEnabled) { + float progress = sideContainerBackHelper.interpolateProgress(backEvent.getProgress()); + drawerLayoutCornerSize = + AnimationUtils.lerp(0, drawerLayoutCornerSizeBackAnimationMax, progress); + maybeUpdateCornerSizeForDrawerLayout(getWidth(), getHeight()); + } } @Override @@ -1009,6 +1030,7 @@ public void handleBackInvoked() { public void cancelBackProgress() { requireDrawerLayoutParent(); sideContainerBackHelper.cancelBackProgress(); + maybeClearCornerSizeAnimationForDrawerLayout(); } @CanIgnoreReturnValue