【问题标题】:Android - how to set dialog's outer marginAndroid - 如何设置对话框的外边距
【发布时间】:2016-09-21 13:50:04
【问题描述】:

我知道这个问题已经被问过几次了,但是我遇到的解决方案都没有为我工作,因此这个话题。正如标题所述 - 我想设置对话框的外边距:

PurchaseDetailsDialogFragment

public class PurchaseDetailsDialogFragment extends DialogFragment {

    private static final String MAX_AMOUNT = "maxAmount";

    private static final String UNIT_PRICE = "unitPrice";

    private static final String PICKUP_TIME_FROM = "pickupTimeFrom";

    private static final String PICKUP_TIME_TO = "pickupTimeTo";

    public PurchaseDetailsDialogFragment() { }

    public static PurchaseDetailsDialogFragment newInstance(int maxAmount, float unitPrice, String pickupTimeFrom, String pickupTimeTo) {
        PurchaseDetailsDialogFragment fragment = new PurchaseDetailsDialogFragment();
        Bundle args = new Bundle();

        args.putInt(MAX_AMOUNT, maxAmount);
        args.putFloat(UNIT_PRICE, unitPrice);
        args.putString(PICKUP_TIME_FROM, pickupTimeFrom);
        args.putString(PICKUP_TIME_TO, pickupTimeTo);
        fragment.setArguments(args);

        return fragment;
    }

    @Override
    public void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);

        if (getArguments() != null) {
            int maxAmount = getArguments().getInt(MAX_AMOUNT);
            float unitPrice = getArguments().getFloat(UNIT_PRICE);
            String pickupFrom = getArguments().getString(PICKUP_TIME_FROM);
            String pickupTo = getArguments().getString(PICKUP_TIME_TO);
        }
    }

    @Override
    public Dialog onCreateDialog(Bundle savedInstanceState) {
        Context context = getContext();
        FragmentPurchaseDetailsDialogBinding binding = DataBindingUtil.inflate(
                LayoutInflater.from(context),
                R.layout.fragment_purchase_details_dialog,
                null,
                false);

        binding.setDataContext(new PurchaseDetailsViewModel(context));

        AlertDialog dialog = new AlertDialog.Builder(getActivity(), R.style.DialogTheme)
                                            .setView(binding.getRoot())
                                            .create();

        dialog.getWindow().setBackgroundDrawable(new ColorDrawable(android.graphics.Color.TRANSPARENT));

        return dialog;
    }

}

fragment_purchase_details_dialog

<layout
    xmlns:android="http://schemas.android.com/apk/res/android"
    android:background="@drawable/dialog">

    <data>
        <variable
            name="dataContext"
            type="com.myapp.viewModels.PurchaseDetailsViewModel" />
    </data>

    <RelativeLayout
        android:layout_width="wrap_content"
        android:layout_height="wrap_content">

        <FrameLayout
            android:layout_width="wrap_content"
            android:layout_height="80dp"
            android:paddingTop="20dp"
            android:layout_centerHorizontal="true"
            android:background="@color/white">

            <TextView
                android:layout_width="wrap_content"
                android:layout_height="wrap_content"
                android:text="@string/choose_amount"
                style="@style/Widget.App.PurchaseTextViewTitle" />

        </FrameLayout>

        <LinearLayout
            android:id="@+id/dialogCentralContent"
            android:layout_width="match_parent"
            android:layout_height="200dp"
            android:orientation="vertical"
            android:layout_marginTop="80dp"
            android:background="@color/dirtyWhite">

            <TextView
                android:layout_width="wrap_content"
                android:layout_height="wrap_content"
                android:text="74" />

        </LinearLayout>

        <LinearLayout
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:orientation="horizontal"
            android:layout_marginTop="46dp"
            android:layout_centerHorizontal="true">

            <Button
                android:layout_width="44dp"
                android:layout_height="44dp"
                android:layout_marginTop="6dp"
                android:background="@drawable/button_filled"
                android:text="-"
                style="@style/Widget.App.PurchaseIncDecButton" />

            <FrameLayout
                android:layout_width="60dp"
                android:layout_height="60dp"
                android:layout_marginLeft="8dp"
                android:layout_marginRight="8dp"
                android:background="@drawable/edittext_white_rounded">

                <EditText
                    android:layout_width="30dp"
                    android:layout_height="match_parent"
                    android:layout_marginLeft="15dp"
                    android:gravity="center_horizontal"
                    android:maxLines="1"
                    style="@style/Widget.App.PurchaseAmountEditText" />

            </FrameLayout>

            <Button
                android:layout_width="44dp"
                android:layout_height="44dp"
                android:layout_marginTop="6dp"
                android:background="@drawable/button_filled"
                android:text="+"
                style="@style/Widget.App.PurchaseIncDecButton" />

        </LinearLayout>

        <Button
            android:layout_width="match_parent"
            android:layout_height="50dp"
            android:layout_below="@+id/dialogCentralContent"
            android:text="@string/buttonBuyText"
            android:background="@drawable/button_submit"
            style="@style/Widget.App.SubmitButton" />

    </RelativeLayout>

</layout>

现在只有上面的代码,我的对话框占据了整个屏幕的宽度。但是,如果我这样做,在片段 java 代码中:

AlertDialog dialog = new AlertDialog.Builder(getActivity(), R.style.DialogTheme) /// the rest of the code

并添加一个主题:

<resources>

    <style name="DialogTheme" parent="@android:style/Theme.Material.Dialog.Alert">
        <item name="android:windowMinWidthMajor">380dp</item>
        <item name="android:windowMinWidthMinor">380dp</item>
    </style>

</resources>

然后发生了一些时髦的事情。在 API23 上一切看起来都很好,而在 API19 及以下(未检查 19 到 23 之间的 api)上,对话框是 100% 宽并与屏幕顶部对齐。如何让它按照我想要的方式工作?

【问题讨论】:

  • 你可以尝试为19以下的api级别创建一个资源文件来改变对话框的宽度
  • 我意识到这一点,但也许有一些通用的解决方案可以在任何地方都可以使用?另外 - 为什么它在 API19 上的行为如此
  • 我不是 100% 确定,但我相信材料设计是在 api 级别 21 上添加的,因此它可能无法将 Theme.Material.Dialog.Alert 定位为父级并使用通用的东西?或者什么都没有
  • 我刚才已经检查过了,你是对的。但是我仍然不知道使用哪个主题来让对话框在所有 api 版本中看起来都一样 - 我的意思是 apis

标签: android android-dialogfragment


【解决方案1】:

有一个非常简单的解决方案。只需将您的布局放入其中,例如 FrameLayout 并在外部布局元素上设置适当的填充。然后所有 api 的一切看起来都一样:

<FrameLayout
    android:layout_width="wrap_content"
    android:layout_height="wrap_content"
    android:paddingLeft="@dimen/defaultMargin"
    android:paddingRight="@dimen/defaultMargin">

    <RelativeLayout
        android:layout_width="wrap_content"
        android:layout_height="wrap_content">
    </RelativeLayout>
</FrameLayout>

【讨论】:

    【解决方案2】:

    你试过了吗?

    How to Build AppCompatDialog From AlertDialog.Builder or Equivalent?

    建议您使用android.support.v7.app.AlertDialog 而不是android.app.AlertDialog

    所以对于有多个选择的对话框,试试AppCompactDialog

    AlertDialog.Builder builder = new AlertDialog.Builder(getActivity(), R.style.DialogTheme)
                                            .setView(binding.getRoot())
                                            .create();
    dialog.getWindow().setBackgroundDrawable(new ColorDrawable(android.graphics.Color.TRANSPARENT));
    AppCompatDialog alert = builder.create();
    alert.show();
    

    我没有试过这个。让我知道这是否有效。

    【讨论】:

    • 是的,我试过了。我没有在我的代码中发布该导入,但我已经在使用android.support.v7.app.AlertDialog
    【解决方案3】:
    <item name="android:windowMinWidthMinor">380dp</item>
    

    这将使对话框宽度保持在 380dp 的最小值,但如果设备宽度

    如果你用宽度较小的设备进行测试(很可能是设备的api较低,例如Galaxy Nexus的宽度为360dp),当然它会占据整个宽度。

    最好将 minWidth 指定为百分比

    对于您的特定情况,要实现预定义的边距(无需以编程方式修改窗口的布局属性),我们可以将最小宽度设置为 100%

    <item name="android:windowMinWidthMinor">100%</item>
    

    并使用 inset drawble 作为 windowBackground,如果您使用的是 AppCompat,则已经是这种情况

    <item name="android:windowBackground">@drawable/abc_dialog_material_background</item>
    

    abc_dialog_material_background:

    <inset xmlns:android="http://schemas.android.com/apk/res/android"
        android:insetLeft="16dp"
        android:insetTop="16dp"
        android:insetRight="16dp"
        android:insetBottom="16dp">
        <shape android:shape="rectangle">
            <corners android:radius="@dimen/abc_dialog_corner_radius_material" />
            <solid android:color="@android:color/white" />
        </shape>
    </inset>
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2023-03-23
      • 1970-01-01
      • 2011-09-03
      • 2016-08-11
      • 2015-09-22
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多