Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

How to create an android Bottom sheet that fits the size of the sheet with view always aligned to bottom?

I had a bit of trouble figuring out how to word this one when researching so I've made a quick mockup of what I'm trying to achieve below. my app has a persistent bottom sheet and I would like the contents of the sheet to be resized based on whether the sheet is expanded or half expanded.

My sheet consists of a recycler view and a view at the bottom with some buttons. Currently, the contents of the sheet are always sized as though the sheet is full expanded. This means that the buttons are not displayed unless the sheet is fully expanded and much of the recycler view is also hidden behind the cropped-off sheet. What I want to happen is for the buttons to always be displayed at the bottom of the sheet, even when said sheet is half expanded, and for the recyclerview to fill whatever space is left. Is this possible in a persistent bottom sheet and if now, what means should I use to achieve this? And help would be greatly appreciated.

Mockup

like image 681
BooleanCheese Avatar asked Oct 23 '25 16:10

BooleanCheese


1 Answers

You can make the buttons layout to always be displayed at the bottom of the sheet by setting its y coordinate by tracking the bottom sheet sliding using addBottomSheetCallback callbacks:

val bottomSheet = findViewById<ConstraintLayout>(R.id.bottom_sheet)
val bottomLayout = findViewById<LinearLayout>(R.id.button_layout)

// initial setting the y coordinates of the bottom layout
bottomSheet.post {
    val bottomSheetVisibleHeight = bottomSheet.height - bottomSheet.top
    bottomLayout.y =
        (bottomSheetVisibleHeight - bottomLayout.height).toFloat()
}

BottomSheetBehavior.from(bottomSheet).apply {

    addBottomSheetCallback(object : BottomSheetBehavior.BottomSheetCallback() {
        override fun onSlide(bottomSheet: View, slideOffset: Float) {
        
            // set the y coordinates of the bottom layout on bottom sheet slide
            val bottomSheetVisibleHeight = bottomSheet.height - bottomSheet.top
            bottomLayout.y =
                (bottomSheetVisibleHeight - bottomLayout.height).toFloat()
        }

        override fun onStateChanged(bottomSheet: View, newState: Int) {
        }
    })
}

Layout:

<?xml version="1.0" encoding="utf-8"?>
<androidx.coordinatorlayout.widget.CoordinatorLayout 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">

    <!--    Main Layout -->
    <androidx.constraintlayout.widget.ConstraintLayout
        android:layout_width="match_parent"
        android:layout_height="match_parent">

    </androidx.constraintlayout.widget.ConstraintLayout>

    <androidx.coordinatorlayout.widget.CoordinatorLayout
        android:layout_width="match_parent"
        android:layout_height="match_parent">

        <androidx.constraintlayout.widget.ConstraintLayout
            android:id="@+id/bottom_sheet"
            android:layout_width="match_parent"
            android:layout_height="match_parent"
            android:orientation="vertical"
            app:behavior_hideable="false"
            app:layout_behavior="@string/bottom_sheet_behavior">

            <androidx.recyclerview.widget.RecyclerView
                android:id="@+id/recyclerview"
                android:layout_width="0dp"
                android:layout_height="0dp"
                android:background="#CFE2F3"
                app:layout_constraintBottom_toTopOf="@+id/button_layout"
                app:layout_constraintEnd_toEndOf="parent"
                app:layout_constraintStart_toStartOf="parent"
                app:layout_constraintTop_toTopOf="parent" />

            <LinearLayout
                android:id="@+id/button_layout"
                android:layout_width="match_parent"
                android:layout_height="60dp"
                android:background="#FF03DAC5"
                android:orientation="horizontal"
                app:layout_constraintBottom_toBottomOf="parent">

                <Button
                    android:layout_width="0dp"
                    android:layout_height="match_parent"
                    android:layout_marginStart="8dp"
                    android:layout_marginEnd="40dp"
                    android:layout_weight="1"
                    android:text="cancel" />

                <Button
                    android:layout_width="0dp"
                    android:layout_height="match_parent"
                    android:layout_marginEnd="8dp"
                    android:layout_weight="1"
                    android:text="ok" />

            </LinearLayout>

        </androidx.constraintlayout.widget.ConstraintLayout>

    </androidx.coordinatorlayout.widget.CoordinatorLayout>

</androidx.coordinatorlayout.widget.CoordinatorLayout>

like image 125
Zain Avatar answered Oct 26 '25 06:10

Zain



Donate For Us

If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!