BottomSheetDialog
- довольно своеобразная Dialog
реализация.Он не добавляется и не опирается на *, CoordinatorLayout
в макете Activity
.Он устанавливает свой собственный CoordinatorLayout
внутри, а внутри него FrameLayout
с BottomSheetBehavior
, в который помещается ваш View
.BottomSheetDialog
сам заполняет весь экран и имеет прозрачный фон, так что он может обрабатывать взаимодействие нижнего листа и любые внешние прикосновения.
Если вам нужен доступ к этому нижнему листу и его BottomSheetBehavior
нам нужно получить его из иерархии Dialog
View
.Это так же просто, как вызов findViewById(R.id.design_bottom_sheet)
на Dialog
, но нам нужно подождать, пока не появится Dialog
, чтобы изменить BottomSheetBehavior
.Кроме того, поскольку BottomSheetDialog
устанавливает свой собственный BottomSheetCallback
, мы должны обеспечить его надлежащую замену.То есть мы должны позаботиться об отмене Dialog
, когда он достигнет закрытого состояния.Например:
final BottomSheetDialog bsd = new BottomSheetDialog(MainActivity.this);
bsd.setContentView(R.layout.your_dialog_layout);
bsd.show();
FrameLayout bottomSheet = (FrameLayout) bsd.findViewById(R.id.design_bottom_sheet);
BottomSheetBehavior behavior = BottomSheetBehavior.from(bottomSheet);
behavior.setBottomSheetCallback(new BottomSheetBehavior.BottomSheetCallback() {
@Override
public void onStateChanged(View bottomSheet, int newState) {
// This is the crucial bit.
if (newState == BottomSheetBehavior.STATE_HIDDEN) {
bsd.cancel();
}
}
@Override
public void onSlide(View bottomSheet, float slideOffset) {}
}
);
Если вы используете BottomSheetDialogFragment
, Dialog
отображается в DialogFragment
onStart()
, и мы можем переопределить этот метод для наших модификаций,после звонка super
.Например:
public class MyFragment extends BottomSheetDialogFragment {
public MyFragment() {}
@Override
public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) {
return inflater.inflate(R.layout.your_dialog_layout, container, false);
}
@Override
public void onStart() {
super.onStart();
FrameLayout bottomSheet = getDialog().findViewById(R.id.design_bottom_sheet);
BottomSheetBehavior behavior = BottomSheetBehavior.from(bottomSheet);
behavior.setBottomSheetCallback(new BottomSheetBehavior.BottomSheetCallback() {
@Override
public void onStateChanged(View bottomSheet, int newState) {
// This is the crucial bit.
if (newState == BottomSheetBehavior.STATE_HIDDEN) {
getDialog().cancel();
}
}
@Override
public void onSlide(View bottomSheet, float slideOffset) {}
}
);
}
}
В любом случае вы можете делать почти все, что хотите, в BottomSheetCallback
, если вы cancel()
Dialog
в onStateChanged()
при newState == BottomSheetBehavior.STATE_HIDDEN
.
* Кстати, это означает, что вам не нужно иметь CoordinatorLayout
в вашем Activity
'макете, чтобы использовать BottomSheetDialog
или BottomSheetDialogFragment
, хотя яне уверен, что это ясно указано в документации или других ресурсах разработчика.