FloatingActionButton скрывает список прокрутки
Im, используя FloatingActionButton
из пакета android.support.design.widget
:
<android.support.design.widget.FloatingActionButton
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_alignParentBottom="true"
android:layout_alignParentEnd="true"
android:layout_marginBottom="20dp"
android:layout_marginEnd="16dp"
android:clickable="true"
android:backgroundTint="@color/primaryColor"
android:src="@drawable/ic_search_white_24dp"
app:borderWidth="0dp"
app:elevation="6dp"
app:backgroundTint="@color/primaryColorDark"
app:rippleColor="@color/accentColor" />
Можно ли настроить эту кнопку, чтобы скрыть анимацию, когда прокрутка списка вниз и показать ее снова, когда listview прокручивается вверх?
Ответы
Ответ 1
Смотрите это. Здесь он рассказывает, как делать то, что вы пытаетесь достичь. Вы должны использовать его так: CoordinatorLayout
и ListView
:
<android.support.design.widget.CoordinatorLayout
android:id="@+id/main_content"
xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:app="http://schemas.android.com/apk/res-auto"
android:layout_width="match_parent"
android:layout_height="match_parent">
<ListView
android:id="@+id/lvToDoList"
android:layout_width="match_parent"
android:layout_height="match_parent"></ListView>
<android.support.design.widget.FloatingActionButton
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_gravity="bottom|right"
android:layout_margin="16dp"
android:src="@drawable/ic_done"
app:layout_anchor="@id/lvToDoList"
app:layout_anchorGravity="bottom|right|end" />
</android.support.design.widget.CoordinatorLayout>
Ответ 2
Те, кто хочет сделать это с переработчиком, могут сделать это:
recyclerView.addOnScrollListener(new RecyclerView.OnScrollListener() {
@Override
public void onScrolled(RecyclerView recyclerView, int dx, int dy) {
if (dy > 0 || dy < 0 && fab.isShown())
fab.hide();
}
@Override
public void onScrollStateChanged(RecyclerView recyclerView, int newState) {
if (newState == RecyclerView.SCROLL_STATE_IDLE)
fab.show();
super.onScrollStateChanged(recyclerView, newState);
}
});
Ответ 3
Небольшое улучшение кода из Irfan Raza:
recyclerView.addOnScrollListener(new RecyclerView.OnScrollListener(){
@Override
public void onScrolled(RecyclerView recyclerView, int dx, int dy){
if (dy<0 && !fab.isShown())
fab.show();
else if(dy>0 && fab.isShown())
fab.hide();
}
@Override
public void onScrollStateChanged(RecyclerView recyclerView, int newState) {
super.onScrollStateChanged(recyclerView, newState);
}
});
Кнопка плавающего действия скрывается при прокрутке вниз и отображается при прокрутке вверх.
Ответ 4
используя этот класс, вы можете легко анимировать FAB, здесь я реализовал метод onStopNestedScroll(), чтобы показать ваш Fab всякий раз, когда останавливается прокрутка.
Я установил 1000 miliSeconds в качестве задержки с помощью Handler();
public class FabBehaviour extends CoordinatorLayout.Behavior<FloatingActionButton> {
private static final String TAG = "ScrollingFABBehavior";
Handler mHandler;
public FabBehaviour(Context context, AttributeSet attrs) {
super();
}
public FabBehaviour() {
super();
}
@Override
public void onStopNestedScroll(@NonNull CoordinatorLayout coordinatorLayout, @NonNull final FloatingActionButton child, @NonNull View target, int type) {
super.onStopNestedScroll(coordinatorLayout, child, target, type);
if (mHandler == null)
mHandler = new Handler();
mHandler.postDelayed(new Runnable() {
@Override
public void run() {
child.animate().translationY(0).setInterpolator(new LinearInterpolator()).start();
Log.d("FabAnim", "startHandler()");
}
}, 1000);
}
@Override
public void onNestedScroll(@NonNull CoordinatorLayout coordinatorLayout, @NonNull FloatingActionButton child, @NonNull View target, int dxConsumed, int dyConsumed, int dxUnconsumed, int dyUnconsumed, int type) {
super.onNestedScroll(coordinatorLayout, child, target, dxConsumed, dyConsumed, dxUnconsumed, dyUnconsumed, type);
if (dyConsumed > 0) {
Log.d("Scrolling", "Up");
CoordinatorLayout.LayoutParams layoutParams = (CoordinatorLayout.LayoutParams) child.getLayoutParams();
int fab_bottomMargin = layoutParams.bottomMargin;
child.animate().translationY(child.getHeight() + fab_bottomMargin).setInterpolator(new LinearInterpolator()).start();
} else if (dyConsumed < 0) {
Log.d("Scrolling", "down");
child.animate().translationY(0).setInterpolator(new LinearInterpolator()).start();
}
}
@Override
public boolean onStartNestedScroll(@NonNull CoordinatorLayout coordinatorLayout, @NonNull FloatingActionButton child, @NonNull View directTargetChild, @NonNull View target, int axes, int type) {
if (mHandler != null) {
mHandler.removeMessages(0);
Log.d("Scrolling", "stopHandler()");
}
return axes == ViewCompat.SCROLL_AXIS_VERTICAL;
}
}
your_layout.xml
<android.support.design.widget.FloatingActionButton
android:id="@+id/imageViewYes"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_gravity="bottom|end|right"
android:layout_margin="@dimen/fab_margin"
android:src="@drawable/ic_yes"
app:backgroundTint="@color/white"
android:scaleType="center"
app:elevation="6dp"
app:fabSize="normal"
app:layout_behavior="com.your.package.FabBehaviour"
app:pressedTranslationZ="12dp"
app:rippleColor="@color/gray" />
Ответ 5
Есть мой код в котлине.
class ScrollAwareFABBehavior (val recyclerView: RecyclerView, val floatingActionButton: FloatingActionButton) {
fun start() {
recyclerView.addOnScrollListener(object : RecyclerView.OnScrollListener() {
override fun onScrolled(recyclerView: RecyclerView, dx: Int, dy: Int) {
super.onScrolled(recyclerView, dx, dy)
if (dy > 0) {
if (floatingActionButton!!.isShown) {
floatingActionButton?.hide()
}
} else if (dy < 0) {
if (!floatingActionButton!!.isShown) {
floatingActionButton?.show()
}
}
}
})
}
}
Теперь вам просто нужно вызвать ScrollAwareFABBehavior с recyclerView и потрясающим конструктором, а затем вызвать метод start().
ScrollAwareFABBehavior(recyclerView = recyclerViewPlaceFormContainer, floatingActionButton = floatingActionButton).start()
Ответ 6
Привет, вам нужно взять recyclerview для автоматического скрытия кнопки плавающего действия при прокрутке вниз для этой цели, мы можем использовать стандартный список по умолчанию с плавающей кнопкой действия обычным способом, только вносить изменения в listview.onscroll listener, тогда мы можем почувствовать как рециркуляция
listview.setOnScrollListener(new AbsListView.OnScrollListener() {
@Override
public void onScrollStateChanged(AbsListView view, int scrollState) {
}
@Override
public void onScroll(AbsListView view, int firstVisibleItem, int visibleItemCount, int totalItemCount) {
int lastItem = firstVisibleItem + visibleItemCount;
if (lastItem == totalItemCount) {
fab.setVisibility(View.INVISIBLE);
}else {
fab.setVisibility(View.VISIBLE);
}
}
});
Ответ 7
По моему мнению, лучший способ реализовать это будет следующим:
public class ScrollingFABBehavior extends FloatingActionButton.Behavior {
private static final String TAG = "ScrollingFABBehavior";
public ScrollingFABBehavior(Context context, AttributeSet attrs) {
super();
// Log.e(TAG, "ScrollAwareFABBehavior");
}
public boolean onStartNestedScroll(CoordinatorLayout parent, FloatingActionButton child, View directTargetChild, View target, int nestedScrollAxes) {
return true;
}
@Override
public boolean layoutDependsOn(CoordinatorLayout parent, FloatingActionButton child, View dependency) {
if (dependency instanceof RecyclerView)
return true;
return false;
}
@Override
public void onNestedScroll(CoordinatorLayout coordinatorLayout,
FloatingActionButton child, View target, int dxConsumed,
int dyConsumed, int dxUnconsumed, int dyUnconsumed) {
// TODO Auto-generated method stub
super.onNestedScroll(coordinatorLayout, child, target, dxConsumed, dyConsumed,
dxUnconsumed, dyUnconsumed);
//Log.e(TAG, "onNestedScroll called");
if (dyConsumed > 0 && child.getVisibility() == View.VISIBLE) {
// Log.e(TAG, "child.hide()");
child.hide();
} else if (dyConsumed < 0 && child.getVisibility() != View.VISIBLE) {
// Log.e(TAG, "child.show()");
child.show();
}
}}
Для подробного ответа проверьте это. Скрыть FloatingActionButton в прокрутке RecyclerView
Ответ 8
mRecyclerView.addOnScrollListener(new RecyclerView.OnScrollListener() {
@Override
public void onScrolled(RecyclerView recyclerView, int dx, int dy) {
super.onScrolled(recyclerView, dx, dy);
if (dy > 0 && mFloatingActionButton.getVisibility() == View.VISIBLE) {
mFloatingActionButton.hide();
} else if (dy < 0 && mFloatingActionButton.getVisibility() != View.VISIBLE) {
mFloatingActionButton.show();
}
}});
Ответ 9
Здесь я добавляю дополнительное дополнение для последнего элемента обзора, чтобы избежать перекрытия элемента списка с помощью кнопки с плавающим действием
Я использовал это в методе RecyclerView.Adapter onBindViewHolder, чтобы установить нижнее поле последнего элемента в списке на 72dp, чтобы оно прокручивалось над кнопкой плавающего действия.
Это не требует фиктивной записи в списке.
@Override
public void onBindViewHolder(ViewHolder holder, int position) {
// other binding code goes here.
if (position + 1 == getItemCount()) {
// set bottom margin to 72dp.
setBottomMargin(holder.itemView, (int) (72 * Resources.getSystem().getDisplayMetrics().density));
} else {
// reset bottom margin back to zero. (your value may be different)
setBottomMargin(holder.itemView, 0);
}
}
public static void setBottomMargin(View view, int bottomMargin) {
if (view.getLayoutParams() instanceof ViewGroup.MarginLayoutParams) {
ViewGroup.MarginLayoutParams params = (ViewGroup.MarginLayoutParams) view.getLayoutParams();
params.setMargins(params.leftMargin, params.topMargin, params.rightMargin, bottomMargin);
view.requestLayout();
}
}
Ответ 10
Kotlin + адаптер привязки данных
@BindingAdapter("bindAdapter:attachFloatingButton")
fun bindRecyclerViewWithFB(recyclerView: RecyclerView, fb: FloatingActionButton) {
recyclerView.addOnScrollListener(object : RecyclerView.OnScrollListener() {
override fun onScrolled(recyclerView: RecyclerView, dx: Int, dy: Int) {
super.onScrolled(recyclerView, dx, dy)
if (dy > 0 && fb.isShown) {
fb.hide()
} else if (dy < 0 && !fb.isShown) {
fb.show()
}
}
})
}
и XML
<androidx.recyclerview.widget.RecyclerView
android:id="@+id/main_recyclerview"
android:layout_width="match_parent"
app:layoutManager="androidx.recyclerview.widget.LinearLayoutManager"
android:layout_height="wrap_content"
android:clipToPadding="false"
android:paddingBottom="8dp" app:layout_constraintEnd_toEndOf="parent" android:layout_marginEnd="8dp"
app:layout_constraintStart_toStartOf="parent" android:layout_marginStart="8dp"
android:layout_marginTop="8dp" app:layout_constraintTop_toBottomOf="@+id/main_chips"
android:layout_marginBottom="8dp"
**bindAdapter:attachFloatingButton="@{mainFb}"**
app:layout_constraintBottom_toBottomOf="parent"
app:layout_constraintVertical_bias="0.0"/>
<com.google.android.material.floatingactionbutton.ExtendedFloatingActionButton
android:id="@+id/main_fb"
android:layout_width="wrap_content"
app:layout_constraintBottom_toBottomOf="parent"
style="@style/Widget.Design.FloatingActionButton"
app:layout_constraintEnd_toEndOf="parent"
android:layout_height="wrap_content"
android:layout_margin="18dp"
android:background="@color/colorPrimaryDark"
app:icon="@drawable/ic_add_black_24dp"/>