1616
1717package com .google .android .material .behavior ;
1818
19+ import static androidx .annotation .RestrictTo .Scope .LIBRARY_GROUP ;
20+
1921import android .animation .Animator ;
2022import android .animation .AnimatorListenerAdapter ;
2123import android .animation .TimeInterpolator ;
2527import android .view .ViewGroup ;
2628import android .view .ViewPropertyAnimator ;
2729import androidx .annotation .Dimension ;
30+ import androidx .annotation .IntDef ;
2831import androidx .annotation .NonNull ;
2932import androidx .annotation .Nullable ;
33+ import androidx .annotation .RestrictTo ;
3034import androidx .coordinatorlayout .widget .CoordinatorLayout ;
3135import androidx .coordinatorlayout .widget .CoordinatorLayout .Behavior ;
3236import androidx .core .view .ViewCompat ;
3337import com .google .android .material .animation .AnimationUtils ;
38+ import java .util .LinkedHashSet ;
3439
3540/**
3641 * The {@link Behavior} for a View within a {@link CoordinatorLayout} to hide the view off the
3742 * bottom of the screen when scrolling down, and show it when scrolling up.
3843 */
3944public class HideBottomViewOnScrollBehavior <V extends View > extends CoordinatorLayout .Behavior <V > {
4045
46+ /**
47+ * Interface definition for a listener to be notified when the bottom view scroll state
48+ * changes.
49+ */
50+ public interface OnScrollStateChangedListener {
51+
52+ /**
53+ * Called when the bottom view changes its scrolled state.
54+ *
55+ * @param bottomView The bottom view.
56+ * @param newState The new state. This will be one of {@link #STATE_SCROLLED_UP} or {@link
57+ * #STATE_SCROLLED_DOWN}.
58+ */
59+ void onStateChanged (@ NonNull View bottomView , @ ScrollState int newState );
60+ }
61+
62+ @ NonNull
63+ private final LinkedHashSet <OnScrollStateChangedListener > onScrollStateChangedListeners =
64+ new LinkedHashSet <>();
65+
4166 protected static final int ENTER_ANIMATION_DURATION = 225 ;
4267 protected static final int EXIT_ANIMATION_DURATION = 175 ;
4368
44- private static final int STATE_SCROLLED_DOWN = 1 ;
45- private static final int STATE_SCROLLED_UP = 2 ;
69+ /** State of the bottom view when it's scrolled down. */
70+ public static final int STATE_SCROLLED_DOWN = 1 ;
71+ /**
72+ * State of the bottom view when it's scrolled up.
73+ */
74+ public static final int STATE_SCROLLED_UP = 2 ;
4675
4776 private int height = 0 ;
48- private int currentState = STATE_SCROLLED_UP ;
77+
78+ /**
79+ * Positions the scroll state can be set to.
80+ *
81+ * @hide
82+ */
83+ @ RestrictTo (LIBRARY_GROUP )
84+ @ IntDef ({STATE_SCROLLED_DOWN , STATE_SCROLLED_UP })
85+ public @interface ScrollState {}
86+
87+ @ ScrollState private int currentState = STATE_SCROLLED_UP ;
4988 private int additionalHiddenOffsetY = 0 ;
5089 @ Nullable private ViewPropertyAnimator currentAnimator ;
5190
@@ -135,7 +174,7 @@ public void slideUp(@NonNull V child, boolean animate) {
135174 currentAnimator .cancel ();
136175 child .clearAnimation ();
137176 }
138- currentState = STATE_SCROLLED_UP ;
177+ updateCurrentState ( child , STATE_SCROLLED_UP ) ;
139178 int targetTranslationY = 0 ;
140179 if (animate ) {
141180 animateChildTo (
@@ -176,7 +215,7 @@ public void slideDown(@NonNull V child, boolean animate) {
176215 currentAnimator .cancel ();
177216 child .clearAnimation ();
178217 }
179- currentState = STATE_SCROLLED_DOWN ;
218+ updateCurrentState ( child , STATE_SCROLLED_DOWN ) ;
180219 int targetTranslationY = height + additionalHiddenOffsetY ;
181220 if (animate ) {
182221 animateChildTo (
@@ -189,6 +228,13 @@ public void slideDown(@NonNull V child, boolean animate) {
189228 }
190229 }
191230
231+ private void updateCurrentState (@ NonNull V child , @ ScrollState int state ) {
232+ currentState = state ;
233+ for (OnScrollStateChangedListener listener : onScrollStateChangedListeners ) {
234+ listener .onStateChanged (child , currentState );
235+ }
236+ }
237+
192238 private void animateChildTo (
193239 @ NonNull V child , int targetY , long duration , TimeInterpolator interpolator ) {
194240 currentAnimator =
@@ -205,4 +251,27 @@ public void onAnimationEnd(Animator animation) {
205251 }
206252 });
207253 }
254+
255+ /**
256+ * Adds a listener to be notified of bottom view scroll state changes.
257+ *
258+ * @param listener The listener to notify when bottom view scroll state changes.
259+ */
260+ public void addOnScrollStateChangedListener (@ NonNull OnScrollStateChangedListener listener ) {
261+ onScrollStateChangedListeners .add (listener );
262+ }
263+
264+ /**
265+ * Removes a previously added listener.
266+ *
267+ * @param listener The listener to remove.
268+ */
269+ public void removeOnScrollStateChangedListener (@ NonNull OnScrollStateChangedListener listener ) {
270+ onScrollStateChangedListeners .remove (listener );
271+ }
272+
273+ /** Remove all previously added {@link OnScrollStateChangedListener}s. */
274+ public void clearOnScrollStateChangedListeners () {
275+ onScrollStateChangedListeners .clear ();
276+ }
208277}
0 commit comments