studio sheets sheet modal example bottomsheetdialogfragment bottom android android-support-library

android - sheets - bottomsheetdialogfragment example



¿Cómo usar BottomSheetDialog? (5)

Comenzó a funcionar cuando configuré la altura fija para mi TextView (200dp), aunque para algunos valores de altura todavía se comporta de manera incorrecta. Obviamente es un problema de soporte lib. Ya hay pocos informes relacionados con BottomSheetDialog en el rastreador de errores:

https://code.google.com/p/android/issues/detail?id=201793&sort=-opened&colspec=ID%20Status%20Priority%20Owner%20Summary%20Stars%20Reporter%20Opened

https://code.google.com/p/android/issues/detail?id=201826

Quiero probar BottomSheetDialog introducido en la biblioteca de soporte de Android 23.2 pero no parece funcionar correctamente. Esto es lo que dice el doc:

Si bien BottomSheetBehavior captura el caso de la hoja inferior persistente, esta versión también proporciona BottomSheetDialog y BottomSheetDialogFragment para llenar el caso de uso de las hojas finales modales. Simplemente reemplace AppCompatDialog o AppCompatDialogFragment con sus equivalentes en la parte inferior de la hoja para que su cuadro de diálogo se convierta en una hoja inferior. "

Así que cambié mi AppCompatDialog a 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)); } }

Aquí está mi archivo de diseño:

<?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>

Luego uso el siguiente código en mi actividad:

new AccountActionsDialog(this).show();

Mi pantalla se atenúa pero el contenido de mi diálogo no es visible. ¿Alguna idea sobre lo que podría faltar? Funciona bien cuando uso AppCompatDialog en su lugar.


En lugar de tener una clase separada, puede simplemente crear una instancia para BottomSheetDialog en su Actividad / Fragmento como la siguiente y puede usarla. Es mucho más fácil y más simple, creo.

val dialog = BottomSheetDialog(this) val bottomSheet = layoutInflater.inflate(R.layout.bottom_sheet, null) bottomSheet.buttonSubmit.setOnClickListener { dialog.dismiss() } dialog.setContentView(bottomSheet) dialog.show()

Para un breve tutorial puedes consultar here


Estaba experimentando el mismo problema, el fondo atenuado y el contenido no visible. Aquí es cómo me las arreglé para solucionarlo configurando la vista de contenido en el método oculto setupDialog() .

public class CustomBottomSheetDialogFragment extends BottomSheetDialogFragment { private TextView mOffsetText; private TextView mStateText; private BottomSheetBehavior.BottomSheetCallback mBottomSheetBehaviorCallback = new BottomSheetBehavior.BottomSheetCallback() { @Override public void onStateChanged(@NonNull View bottomSheet, int newState) { setStateText(newState); if (newState == BottomSheetBehavior.STATE_HIDDEN) { dismiss(); } } @Override public void onSlide(@NonNull View bottomSheet, float slideOffset) { setOffsetText(slideOffset); } }; private LinearLayoutManager mLinearLayoutManager; private ApplicationAdapter mAdapter; @Override public Dialog onCreateDialog(Bundle savedInstanceState) { return super.onCreateDialog(savedInstanceState); } @Override public void onViewCreated(View contentView, @Nullable Bundle savedInstanceState) { super.onViewCreated(contentView, savedInstanceState); } @Override public void setupDialog(Dialog dialog, int style) { super.setupDialog(dialog, style); View contentView = View.inflate(getContext(), R.layout.bottom_sheet_dialog_content_view, null); dialog.setContentView(contentView); mBottomSheetBehavior = BottomSheetBehavior.from(((View) contentView.getParent())); if (mBottomSheetBehavior != null) { mBottomSheetBehavior.setBottomSheetCallback(mBottomSheetBehaviorCallback); } mOffsetText = (TextView) contentView.findViewById(R.id.offsetText); mStateText = (TextView) contentView.findViewById(R.id.stateText); } }

Y el diseño:

<?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="match_parent" android:orientation="vertical"> <TextView android:id="@+id/offsetText" android:layout_width="wrap_content" android:layout_height="wrap_content" android:textColor="@android:color/black" /> <TextView android:id="@+id/stateText" android:layout_width="wrap_content" android:layout_height="wrap_content" android:textColor="@android:color/black" /> <TextView android:layout_width="match_parent" android:layout_height="wrap_content" /> </LinearLayout>


Este es el archivo de diseño de 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>

Su vista de contenido está dentro de la vista design_bottom_sheet , se ubicará en el centro verticalmente por CoordinatorLayout , y BottomSheetBehavior lo compensará.

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); }

design_bottom_sheet mMaxOffset design_bottom_sheet en mMaxOffset , pero en realidad el getTop inicial de la vista secundaria no es 0, sino (mParentHeight - childHeight) / 2 , por lo que (mParentHeight - childHeight) / 2 si el desplazamiento es mayor que el desplazamiento deseado.

Encuentre la vista design_bottom_sheet y establezca su gravedad en Gravity.TOP | Gravity.CENTER_HORIZONTAL Gravity.TOP | Gravity.CENTER_HORIZONTAL lo arreglará. Pero, si childHeight es menor que mPeekHeight, habrá un área en blanco debajo de la vista de contenido.

Sin embargo, si peekHeight > childHeight , mMaxOffset será menor que mMinOffset , lo que causará un comportamiento extraño.

Tal vez el código debería ser cambiado a

mMaxOffset = Math.max((mParentHeight - mPeekHeight), mMinOffset);

insted de

mMaxOffset = mParentHeight - child.getHeight();


Este es el problema en code.google.com https://code.google.com/p/android/issues/detail?id=201793

Un problema que algunos usuarios ven se reduce al FrameLayout que envuelve nuestra vista de contenido centrada verticalmente. BottomSheetBehavior solo funciona si esta vista está alineada en la parte superior. No he descubierto qué hace que el FrameLayout se centre verticalmente todavía, pero aquí hay una posible solución:

View contentView = ... // You may have to measure your content view first. dialog.setContentView(contentView); // Change this to a percentage or a constant, whatever you want to do. // The default is 1024 - any views smaller than this will be pulled off // the bottom of the screen. float peekHeight = contentView.getMeasuredHeight(); View parent = (View)contentView.getParent(); BottomSheetBehavior behavior = BottomSheetBehavior.from(parent); behavior.setPeekHeight(peekHeight); CoordinatorLayout.LayoutParams layoutParams = (CoordinatorLayout.LayoutParams)parent.getLayoutParams(); layoutParams.gravity = Gravity.TOP | Gravity.CENTER_HORIZONTAL;