У меня есть DialogFragment
, чтобы показать View
как всплывающее окно. Окно появляется всегда посередине экрана. Есть ли способ установить положение окна DialogFragment
? Я просмотрел source code, но ничего не смог найти.Позиция DialogFragment в Android
ответ
попробовать что-то вроде этого:
@Override
public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState)
{
getDialog().getWindow().setGravity(Gravity.CENTER_HORIZONTAL | Gravity.TOP);
WindowManager.LayoutParams p = getDialog().getWindow().getAttributes();
p.width = ViewGroup.LayoutParams.MATCH_PARENT;
p.softInputMode = WindowManager.LayoutParams.SOFT_INPUT_STATE_ALWAYS_VISIBLE;
p.x = 200;
...
getDialog().getWindow().setAttributes(p);
...
или другие методы getDialog().getWindow()
.
Обязательно установите позицию после вызова заданного содержимого.
Я использую класс PopupWindow для этой цели, потому что вы можете указать местоположение и размер представления.
PopupWindow - это не фрагмент, так что это довольно большая головная боль. –
getDialog().getWindow()
не будет работать для DialogFragment
, так как getWindow()
вернет null, если хостинг-активность не отображается, а это не значит, что вы пишете приложение на основе фрагментов. Вы получите NullPointerException
при попытке getAttributes()
.
Я рекомендую ответ Mobistry. Если у вас уже есть класс DialogFragment, переключиться не стоит. Просто замените метод onCreateDialog тем, который создает и возвращает PopupWindow. Затем вы сможете повторно использовать View, который вы подаете, в AlertDialog.builder.setView()
и позвонить по номеру (PopupWindow object).showAtLocation()
.
Правильно, я ударил головой о стену в течение часа или двух с этим, прежде чем, наконец, получив DialogFragment
, как я хотел.
Я строию на Steelight's answer здесь. Это самый простой и надежный подход, который я нашел.
@Override
public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle b) {
Window window = getDialog().getWindow();
// set "origin" to top left corner, so to speak
window.setGravity(Gravity.TOP|Gravity.LEFT);
// after that, setting values for x and y works "naturally"
WindowManager.LayoutParams params = window.getAttributes();
params.x = 300;
params.y = 100;
window.setAttributes(params);
Log.d(TAG, String.format("Positioning DialogFragment to: x %d; y %d", params.x, params.y));
}
Обратите внимание, что params.width
и params.softInputMode
(используется в ответ Steelight в) не имеют значения для этого.
Ниже приведен более полный пример. То, что мне действительно нужно, - выровнять флажок «подтвердить» диалогового окна «Диалоговое окно» рядом с «исходным» или «родительским» представлением, в моем случае - ImageButton.
Я решил использовать DialogFragment вместо любого пользовательского фрагмента, потому что он дает вам «диалоговые» функции бесплатно (закрытие диалогового окна, когда пользователь щелкает за его пределами и т. Д.).
Пример ConfirmBox выше его «источник» ImageButton (мусорка)
/**
* A custom DialogFragment that is positioned above given "source" component.
*
* @author Jonik, https://stackoverflow.com/a/20419231/56285
*/
public class ConfirmBox extends DialogFragment {
private View source;
public ConfirmBox() {
}
public ConfirmBox(View source) {
this.source = source;
}
public static ConfirmBox newInstance(View source) {
return new ConfirmBox(source);
}
@Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setStyle(STYLE_NO_FRAME, R.style.Dialog);
}
@Override
public void onStart() {
super.onStart();
// Less dimmed background; see https://stackoverflow.com/q/13822842/56285
Window window = getDialog().getWindow();
WindowManager.LayoutParams params = window.getAttributes();
params.dimAmount = 0.2f; // dim only a little bit
window.setAttributes(params);
// Transparent background; see https://stackoverflow.com/q/15007272/56285
// (Needed to make dialog's alpha shadow look good)
window.setBackgroundDrawableResource(android.R.color.transparent);
}
@Override
public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) {
// Put your dialog layout in R.layout.view_confirm_box
View view = inflater.inflate(R.layout.view_confirm_box, container, false);
// Initialise what you need; set e.g. button texts and listeners, etc.
// ...
setDialogPosition();
return view;
}
/**
* Try to position this dialog next to "source" view
*/
private void setDialogPosition() {
if (source == null) {
return; // Leave the dialog in default position
}
// Find out location of source component on screen
// see https://stackoverflow.com/a/6798093/56285
int[] location = new int[2];
source.getLocationOnScreen(location);
int sourceX = location[0];
int sourceY = location[1];
Window window = getDialog().getWindow();
// set "origin" to top left corner
window.setGravity(Gravity.TOP|Gravity.LEFT);
WindowManager.LayoutParams params = window.getAttributes();
// Just an example; edit to suit your needs.
params.x = sourceX - dpToPx(110); // about half of confirm button size left of source view
params.y = sourceY - dpToPx(80); // above source view
window.setAttributes(params);
}
public int dpToPx(float valueInDp) {
DisplayMetrics metrics = getActivity().getResources().getDisplayMetrics();
return (int) TypedValue.applyDimension(TypedValue.COMPLEX_UNIT_DIP, valueInDp, metrics);
}
}
Это довольно легко сделать выше более общего пользования, добавляя параметры конструктора или сеттеры по мере необходимости. (Мой окончательный ConfirmBox
имеет стилизованную кнопку (внутри некоторые границ и т.д.), чьи текст и View.OnClickListener
может быть настроена в коде.)
Удивительный лучший ответ, который я нашел. –
Ребята, качайте - спасибо - мне любопытно, почему я не могу просто установить это в XML-фрагменте? ** Что я не понимаю как хромого iOS-разработчика? спасибо людям! :) – Fattie
Grt ответ !! У меня возникла какая-либо проблема: в моей сценарии кнопка «источник» (ниже которой должен отображаться фрагмент диалога) изменения позиции при изменении ориентации экрана, поэтому при изменении ориентации фрагмент диалога не обновляет позицию в соответствии с положением ' source'. Не могли бы вы дать мне некоторый намек на то, как это сделать. – Dory
Вы должны переопределить onResume() метод в вашем DialogFragment как следующее:
@Override
public void onResume() {
final Window dialogWindow = getDialog().getWindow();
WindowManager.LayoutParams lp = dialogWindow.getAttributes();
lp.x = 100; // set your X position here
lp.y = 200; // set your Y position here
dialogWindow.setAttributes(lp);
super.onResume();
}
- 1. Позиция DialogFragment в Android
- 2. Android DialogFragment
- 3. Android findViewById в DialogFragment
- 4. ClassCastException в DialogFragment в Android
- 5. Android - CountDownTimer на DialogFragment
- 6. Android - DialogFragment во фрагменте
- 7. Android transparent DialogFragment
- 8. Сброс Android DialogFragment
- 9. Android setLayoutDirection on DialogFragment
- 10. Android DialogFragment Dismissal
- 11. Android DialogFragment onResume Event
- 12. Android DialogFragment не отклоняется
- 13. Создание android DialogFragment в eclipse
- 14. Android DialogFragment пуст
- 15. Настройка android DialogFragment
- 16. Android Multiple Nested DialogFragment
- 17. Android: IllegalStateException вызова DialogFragment
- 18. Android - DialogFragment не отображается
- 19. Android Пользовательского Dialog (DialogFragment)
- 20. Позиция подвиды в Android
- 21. Позиция кнопки в android
- 22. Android: DialogFragment и универсальный xml
- 23. Datepicker DialogFragment mono для android
- 24. Timepicker with DialogFragment xamarin android
- 25. Android DialogFragment onViewCreated не называется
- 26. Android - Определить ProgressDialog внутри DialogFragment
- 27. Android DialogFragment newInstance необязательные параметры
- 28. Скрыть кнопки в DialogFragment в Android
- 29. ListView в DialogFragment отключен в Android 4.0
- 30. Фрагмент внутри DialogFragment C# android
спасибо Сальтайт я поддержал ваш ответ. Однако, у меня есть вопрос.Почему вы меняете WindowManager.LayoutParam p? setGravity(), похоже, делает трюк для установки окна наверху. По-видимому, никаких негативных последствий для LayoutParams не наблюдается, когда я тестировал его или когда читал документацию о setGravity. – flobacca
Вопрос был «как установить позицию», я не предполагал, что он имел в виду «верх», поэтому я привел пример установки нескольких атрибутов для получения желаемого эффекта. – Steelight
+1 потому что это показало мне правильное направление. Что в конечном итоге сработало для меня: http://stackoverflow.com/a/20419231/56285 – Jonik