I want to try BottomSheetDialog introduced in Android Support Library 23.2 but it doesn't seem to work correctly. Here is what the doc says:
While BottomSheetBehavior captures the persistent bottom sheet case, this release also provides a BottomSheetDialog and BottomSheetDialogFragment to fill the modal bottom sheets use case. Simply replace AppCompatDialog or AppCompatDialogFragment with their bottom sheet equivalents to have your dialog styled as a bottom sheet."
So I changed my AppCompatDialog
to BottomSheetDialog
:
package my.package.ui.dialog; import android.app.Activity; import android.content.Context; import android.os.Bundle; import android.support.design.widget.BottomSheetDialog; import my.package.R; public class AccountActionsDialog extends BottomSheetDialog { public AccountActionsDialog(Context context) { super(context); if (context instanceof Activity) { setOwnerActivity((Activity) context); } } @Override protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); setContentView(getLayoutInflater().inflate(R.layout.dialog_account_actions, null)); } }
Here is my layout file:
<?xml version="1.0" encoding="utf-8"?> <LinearLayout xmlns:android="http://schemas.android.com/apk/res/android" android:layout_width="match_parent" android:layout_height="wrap_content" android:orientation="vertical"> <TextView android:layout_width="match_parent" android:layout_height="wrap_content" android:background="#ff0000" android:padding="16dp" android:text="Delete account" android:textColor="#ffffff" /> </LinearLayout>
Then I use the following code in my Activity:
new AccountActionsDialog(this).show();
My screen becomes dimmed but the content of my dialog is not visible. Any thoughts on what might be missing? It works fine when I use AppCompatDialog instead.
Modal BottomSheet This kind of BottomSheet has an appearance similar to an alert-dialog or dialog fragment. The name has been given because of its behavior and appearance that are similar to Modals. Unlike Persistent BottomSheet, it appears from the bottom of the screen when a user requests certain actions.
Instead of having a separate class, you can simply create an instance for BottomSheetDialog in your Activity/Fragment like following and you can use it. It is very easier and simpler I think.
val dialog = BottomSheetDialog(this) val bottomSheet = layoutInflater.inflate(R.layout.bottom_sheet, null) bottomSheet.buttonSubmit.setOnClickListener { dialog.dismiss() } dialog.setContentView(bottomSheet) dialog.show()
This is the layout file of BottomSheetDialog.
<android.support.design.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" android:soundEffectsEnabled="false"> <FrameLayout android:id="@+id/design_bottom_sheet" android:layout_width="match_parent" android:layout_height="wrap_content" android:layout_gravity="center_horizontal" app:layout_behavior="@string/bottom_sheet_behavior" style="?attr/bottomSheetStyle"/> </android.support.design.widget.CoordinatorLayout>
Your content view is inside the view design_bottom_sheet
, it will be positioned center vertically by CoordinatorLayout
, and BottomSheetBehavior
will offset it.
mParentHeight = parent.getHeight(); mMinOffset = Math.max(0, mParentHeight - child.getHeight()); mMaxOffset = mParentHeight - mPeekHeight; if (mState == STATE_EXPANDED) { ViewCompat.offsetTopAndBottom(child, mMinOffset); } else if (mHideable && mState == STATE_HIDDEN) { ViewCompat.offsetTopAndBottom(child, mParentHeight); } else if (mState == STATE_COLLAPSED) { ViewCompat.offsetTopAndBottom(child, mMaxOffset); }
It intented to positon design_bottom_sheet
at mMaxOffset
, but actually the initial getTop of the child view is not 0, but (mParentHeight - childHeight) / 2
, so you view if offset more than the desired offset.
Find the view design_bottom_sheet
and set its gravity to Gravity.TOP | Gravity.CENTER_HORIZONTAL
will fix it. But, if the childHeight is less than mPeekHeight, there will be blank area below you content view.
However, if peekHeight > childHeight
, the mMaxOffset
will less than mMinOffset
, which will cause weird behavior.
Maybe the code should be changed to
mMaxOffset = Math.max((mParentHeight - mPeekHeight), mMinOffset);
insted of
mMaxOffset = mParentHeight - child.getHeight();
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With