详解Android中Dialog的使用

在Android中经常要使用Dialog来实现一些提示以及一些特殊的效果,而且样式也不一样,每次都得查一大堆资料,还不一定能解决,这里总结一些常用的Dialog的实践。

普通的Dialog

//普通的AlertDialog对话框
findViewById(R.id.btn_common).setOnClickListener(new View.OnClickListener() {
 @Override
 public void onClick(View v) {
 AlertDialog.Builder builder = new AlertDialog.Builder(MainActivity.this);
 builder.setTitle("普通的对话框的标题");
 builder.setMessage("这是一个普通的对话框的内容");
 builder.setNegativeButton("取消", new DialogInterface.OnClickListener() {
  @Override
  public void onClick(DialogInterface dialog, int which) {
  toast("取消");
  }
 });
 builder.setPositiveButton("确定", new DialogInterface.OnClickListener() {
  @Override
  public void onClick(DialogInterface dialog, int which) {
  toast("确定");
  }
 });
 AlertDialog dialog = builder.create();
 dialog.show();
 }
});

这里使用AlertDialog来显示一个系统的提示对话框,效果如下:

修改普通对话框的位置、大小、透明度

主要是在普通的dialog.show() 下面加上如下代码

//放在show()之后,不然有些属性是没有效果的,比如height和width
Window dialogWindow = dialog.getWindow();
WindowManager m = getWindowManager();
Display d = m.getDefaultDisplay(); // 获取屏幕宽、高用
WindowManager.LayoutParams p = dialogWindow.getAttributes(); // 获取对话框当前的参数值
//设置高度和宽度
p.height = (int) (d.getHeight() * 0.4); // 高度设置为屏幕的0.6
p.width = (int) (d.getWidth() * 0.6); // 宽度设置为屏幕的0.65
//设置位置
p.gravity = Gravity.BOTTOM;
//设置透明度
p.alpha = 0.5f;
dialogWindow.setAttributes(p);

在这里,设置dialog的高为屏幕的高度的4/10,宽为屏幕宽带的6/10,同事位置为底部,透明度为半透明。当然还有很多其他属性,这里暂不介绍,你们可以自己试一试。效果如下:

使用普通的dialog来添加自定义布局

我们需自定义一个布局,如下:

<?xml version="1.0" encoding="utf-8"?>
<LinearLayout
 xmlns:android="http://schemas.android.com/apk/res/android"
 android:layout_width="100dp"
 android:layout_height="100dp"
 android:background="#00ff00">

 <TextView
 android:layout_width="match_parent"
 android:layout_height="match_parent"
 android:gravity="center"
 android:textColor="#ff0000"
 android:text="你好"/>
</LinearLayout>

我们这里新建了一个布局设置高度和宽度为100dp,线性布局里面包裹了一个TextView,布局很简单,当然也可以自定义一个复杂的布局,这里就不介绍了。来看看Java代码的实现。

// 使用普通的dialog来添加自定义布局
findViewById(R.id.btn_custom2).setOnClickListener(new View.OnClickListener() {
 @Override
 public void onClick(View v) {
 AlertDialog.Builder builder = new AlertDialog.Builder(MainActivity.this);
 builder.setView(R.layout.dialog_custom1);
 AlertDialog dialog = builder.create();
 dialog.show();
 }
});

我们直接把我们的布局通过builder设置进去,看看效果:

这里的Dialog非常丑,这是与AlertDialog的默认主题有关,下面我们通过自定义主题来改变对话框的样式来使对话框变得漂亮。
在values/styles.xml自定义样式继承Android:Theme.Dialog来实现自己的样式

<style name="MyCommonDialog" parent="android:Theme.Dialog">
 <!-- 背景颜色及透明程度 -->
 <item name="android:windowBackground">@android:color/transparent</item>
 <!-- 是否半透明 -->
 <item name="android:windowIsTranslucent">false</item>
 <!-- 是否没有标题 -->
 <item name="android:windowNoTitle">true</item>
 <!-- 是否浮现在activity之上 -->
 <item name="android:windowIsFloating">true</item>
 <!-- 是否背景模糊 -->
 <item name="android:backgroundDimEnabled">false</item>
 <!-- 设置背景模糊的透明度-->
 <item name="android:backgroundDimAmount">0.5</item>
</style>

这里样式的属性都有注释,没种样式不是必须的,你可以自己试着改变一些值来查看效果以便达到自己的最佳效果。
在创建dialog的时候将样式传过去

AlertDialog.Builder builder = new AlertDialog.Builder(MainActivity.this,R.style.MyCommonDialog);

现在的效果如下:

可以看的我们的布局的高度和宽带还是没效果,我们知道子空间的布局一般由布局来测量的于是我想到给这个布局的最外层套一个布局,看能不能达到我们的效果。

修改dialog_custom1.xml布局如下:

<?xml version="1.0" encoding="utf-8"?>
<RelativeLayout
 xmlns:android="http://schemas.android.com/apk/res/android"
 android:layout_width="match_parent"
 android:layout_height="match_parent">

 <LinearLayout
 android:layout_width="100dp"
 android:layout_height="100dp"
 android:layout_centerInParent="true"
 android:background="#00ff00">

 <TextView
  android:layout_width="match_parent"
  android:layout_height="match_parent"
  android:gravity="center"
  android:text="你好"
  android:textColor="#ff0000"/>
 </LinearLayout>
</RelativeLayout>

再次运行如下:

达到我们想要的效果了,这样你就可以引入样式和自定义布局实现各种对话框的效果了。

继承Dialog来实现Dialog

通过继承Dialog来实现自定义的Dialog,这样我们就可以在任何地方直接new我们的Dialog就可以实现特定的对话框了。

1.在values/styles.xml新建一个样式MyDialog

<style name="MyDialog" parent="android:Theme.Dialog">
 <!-- 背景颜色及透明程度 -->
 <item name="android:windowBackground">@android:color/transparent</item>
 <!-- 是否半透明 -->
 <item name="android:windowIsTranslucent">false</item>
 <!-- 是否没有标题 -->
 <item name="android:windowNoTitle">true</item>
 <!-- 是否浮现在activity之上 -->
 <item name="android:windowIsFloating">true</item>
 <!-- 是否背景模糊 -->
 <item name="android:backgroundDimEnabled">false</item>
 <!-- 设置背景模糊的透明度-->
 <item name="android:backgroundDimAmount">0.5</item>
</style>

2.新建一个MyDialog继承Dialog

public class MyDialog extends Dialog {
 //在构造方法里预加载我们的样式,这样就不用每次创建都指定样式了
 public MyDialog(Context context) {
 this(context, R.style.MyDialog);
 }

 public MyDialog(Context context, int themeResId) {
 super(context, themeResId);
 }

 @Override
 protected void onCreate(Bundle savedInstanceState) {
 super.onCreate(savedInstanceState);
 // 预先设置Dialog的一些属性
 Window dialogWindow = getWindow();
 WindowManager.LayoutParams p = dialogWindow.getAttributes();
 p.x = 0;
 p.y = 100;
 p.gravity = Gravity.LEFT | Gravity.TOP;
 dialogWindow.setAttributes(p);
 }
}

/*
* lp.x与lp.y表示相对于原始位置的偏移.
* 当参数值包含Gravity.LEFT时,对话框出现在左边,所以lp.x就表示相对左边的偏移,负值忽略.
* 当参数值包含Gravity.RIGHT时,对话框出现在右边,所以lp.x就表示相对右边的偏移,负值忽略.
* 当参数值包含Gravity.TOP时,对话框出现在上边,所以lp.y就表示相对上边的偏移,负值忽略.
* 当参数值包含Gravity.BOTTOM时,对话框出现在下边,所以lp.y就表示相对下边的偏移,负值忽略.
* 当参数值包含Gravity.CENTER_HORIZONTAL时,对话框水平居中,所以lp.x就表示在水平居中的位置移动
* lp.x像素,正值向右移动,负值向左移动.
* 当参数值包含Gravity.CENTER_VERTICAL时,对话框垂直居中,所以lp.y就表示在垂直居中的位置移动lp.y像
* 素,正值向右移动,负值向左移动.
* gravity的默认值为Gravity.CENTER,即Gravity.CENTER_HORIZONTAL | Gravity.CENTER_VERTICAL
*/

这里对window的一些参数进行了解释,我把对话框设置的离左上角离顶部100px的位置。

3.使用MyDialog

自定义布局dialog_custom2.xml

<?xml version="1.0" encoding="utf-8"?>
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
  android:layout_width="match_parent"
  android:layout_height="match_parent"
  android:orientation="vertical">

 <LinearLayout
 android:layout_width="match_parent"
 android:layout_height="match_parent"
 android:layout_centerInParent="true"
 android:background="#ffffff"
 android:orientation="vertical"
 android:padding="10dp">

 <TextView
  android:layout_width="match_parent"
  android:layout_height="wrap_content"
  android:layout_margin="2dp"
  android:background="#00ff00"
  android:gravity="center"
  android:padding="10dp"
  android:text="你好"
  android:textColor="#000000"/>

 <TextView
  android:layout_width="match_parent"
  android:layout_height="wrap_content"
  android:layout_margin="2dp"
  android:background="#00ff00"
  android:gravity="center"
  android:padding="10dp"
  android:text="你好"
  android:textColor="#000000"/>

 <TextView
  android:layout_width="match_parent"
  android:layout_height="wrap_content"
  android:layout_margin="2dp"
  android:background="#00ff00"
  android:gravity="center"
  android:padding="10dp"
  android:text="你好"
  android:textColor="#000000"/>
 </LinearLayout>
</RelativeLayout>

Java代码

//继承Dialog来实现Dialog
findViewById(R.id.btn_custom3).setOnClickListener(new View.OnClickListener() {
 @Override
 public void onClick(View v) {
 MyDialog dialog = new MyDialog(MainActivity.this);
 dialog.setContentView(R.layout.dialog_custom2);
 dialog.show();
 }
});

4.查看效果:

给Dialog设置动画

1.新建动画文件

进入动画dialog_enter.xml

<?xml version="1.0" encoding="utf-8"?>
<set xmlns:android="http://schemas.android.com/apk/res/android">
<translate
 android:duration="200"
 android:fillAfter="true"
 android:fromYDelta="100%p"
 android:toYDelta="0%"/>
</set>

退出动画dialog_exit.xml

<?xml version="1.0" encoding="utf-8"?>
<set xmlns:android="http://schemas.android.com/apk/res/android">
 <translate
 android:duration="200"
 android:fillAfter="true"
 android:fromYDelta="0%"
 android:toYDelta="100%p"/>
</set>

2.在values/styles.xml中新建样式

<style name="MyAnimDialog" parent="android:Theme.Dialog">
 <!-- 背景颜色及透明程度 -->
 <item name="android:windowBackground">@android:color/transparent</item>
 <!-- 是否半透明 -->
 <item name="android:windowIsTranslucent">false</item>
 <!-- 是否没有标题 -->
 <item name="android:windowNoTitle">true</item>
 <!-- 是否浮现在activity之上 -->
 <item name="android:windowIsFloating">true</item>
 <!-- 是否背景模糊 -->
 <item name="android:backgroundDimEnabled">true</item>
 <!-- 设置背景模糊的透明度-->
 <item name="android:backgroundDimAmount">0.5</item>
 <!-- 动画 -->
 <item name="android:windowAnimationStyle">@style/dialog_animation</item>
</style>

<!-- 对话框显示和退出动画 -->
<style name="dialog_animation">
 <item name="android:windowEnterAnimation">@anim/dialog_enter</item>
 <item name="android:windowExitAnimation">@anim/dialog_exit</item>
</style>

主要是给android:windowAnimationStyle指定我们新建的动画即可,引用和前面一样,这里就给出了,

3.查看效果

继承Dialog来实现底部弹出Dialog

自定义MyBottomDialog

public class MyBottomDialog extends Dialog {
 public MyBottomDialog(Context context) {
 this(context, R.style.MyAnimDialog);
 }

 public MyBottomDialog(Context context, int themeResId) {
 super(context, themeResId);
 //加载布局并给布局的控件设置点击事件
 View contentView = getLayoutInflater().inflate(R.layout.dialog_custom3, null);
 contentView.findViewById(R.id.tv_1).setOnClickListener(new View.OnClickListener() {
  @Override
  public void onClick(View v) {
  Toast.makeText(getContext(), "你好", Toast.LENGTH_SHORT).show();
  }
 });
 super.setContentView(contentView);
 }

 @Override
 protected void onCreate(Bundle savedInstanceState) {
 super.onCreate(savedInstanceState);
 // 预先设置Dialog的一些属性
 Window dialogWindow = getWindow();
 WindowManager.LayoutParams p = dialogWindow.getAttributes();
 WindowManager m = getWindow().getWindowManager();
 Display d = m.getDefaultDisplay();
 getWindow().setAttributes(p);
 p.height = (int) (d.getHeight() * 0.6);
 p.width = d.getWidth();
 p.gravity = Gravity.LEFT | Gravity.BOTTOM;
 dialogWindow.setAttributes(p);
 }
}

在onCreate方法里指定的Dialog的高度和宽度

布局dialog_custom3.xml

<?xml version="1.0" encoding="utf-8"?>
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
  android:layout_width="match_parent"
  android:layout_height="match_parent"
  android:orientation="vertical">

 <LinearLayout
 android:layout_width="match_parent"
 android:layout_height="match_parent"
 android:layout_centerInParent="true"
 android:background="#ffffff"
 android:orientation="vertical"
 android:padding="10dp">

 <TextView
  android:id="@+id/tv_1"
  android:layout_width="match_parent"
  android:layout_height="wrap_content"
  android:layout_margin="2dp"
  android:background="#00ff00"
  android:gravity="center"
  android:padding="10dp"
  android:text="你好"
  android:textColor="#000000"/>

 <TextView
  android:layout_width="match_parent"
  android:layout_height="wrap_content"
  android:layout_margin="2dp"
  android:background="#00ff00"
  android:gravity="center"
  android:padding="10dp"
  android:text="你好"
  android:textColor="#000000"/>

 <TextView
  android:layout_width="match_parent"
  android:layout_height="wrap_content"
  android:layout_margin="2dp"
  android:background="#00ff00"
  android:gravity="center"
  android:padding="10dp"
  android:text="你好"
  android:textColor="#000000"/>
 </LinearLayout>
</RelativeLayout>

使用是方法是一样的

//继承Dialog来实现底部弹出Dialog
findViewById(R.id.btn_custom5).setOnClickListener(new View.OnClickListener() {
 @Override
 public void onClick(View v) {
 MyBottomDialog dialog = new MyBottomDialog(MainActivity.this);
 dialog.show();
 }
});

这里就不用设置布局了,因为我们在MyBottomDialog的构造方法里已经预加载了布局并设置了点击事件

查看效果:

自定义仿Meun的弹出Dialog

MyMenuDialog的代码

public class MyMenuDialog extends Dialog {
 public MyMenuDialog(Context context) {
 this(context, R.style.MyDialog);
 }

 public MyMenuDialog(Context context, int themeResId) {
 super(context, themeResId);
 }

 @Override
 protected void onCreate(Bundle savedInstanceState) {
 super.onCreate(savedInstanceState);
 // 预先设置Dialog的一些属性
 Window dialogWindow = getWindow();
 WindowManager.LayoutParams p = dialogWindow.getAttributes(); // 获取对话框当前的参数值
 //获取屏幕的高度和宽带
 WindowManager m = getWindow().getWindowManager();
 Display d = m.getDefaultDisplay();
 DisplayMetrics outMetrics = new DisplayMetrics();
 d.getMetrics(outMetrics);
 //设置WindowManager.LayoutParams
// p.height = (int) (outMetrics.heightPixels * 0.6);
// p.width = (int) (outMetrics.widthPixels * 0.4);
 //根据s随意来的高度来设置x轴偏移量
 p.x = (int) (15 * outMetrics.density);
 //根据Title的高度来设置y轴偏移量
 p.y = (int) (45 * outMetrics.density);
 p.gravity = Gravity.RIGHT | Gravity.TOP;
 dialogWindow.setAttributes(p);
 }
}

使用就不介绍了,这里主要是利用WindowManager.LayoutParams的x、y、gravity来实现的,当然可以自定义Dialog的弹出动画就可以实现一个菜单对话框了。

效果如下:

基本上Dialog的实现了这些效果应该能满足大部分项目的需求,至于以下复杂的,想带有ListView、GridView的Dialog等等都可以通过自定义Dialog来继承Dialog来实现,都是依葫芦画瓢就可以了,以后遇到什么再来补充。

(0)

相关推荐

  • 浅析Android中强大的Dialog

    Android中经常会使用到Dialog(弹出框效果),而且功能非常强大,可以模拟出N种弹出框效果.如图所示: 下面将通过一个小实例,来像大家展示Android中功能强大的Dialog.代码都写了详细的注释,读者不妨试着手动去敲. 当然,由于时间的关系,还有个别功能没有完成,先有的几个展示效果中也可能有bug,代码也有很多需要优化的地方.望大家热心指出. 下面是代码(有点长哦): 复制代码 代码如下: package com.chaoyang.activity; import java.util

  • Android Dialog 设置字体大小的具体方法

    先看下面图片: 这是我在做登录页面的时候,调用系统的ProgressDialog 进行等待,可是看起来很不协调,左边的等待图片过大,右边文字过小,看起来老别扭,虽然功能上不存在什么问题,但是我有强迫症,看不顺的就像弄掉.可是找了好久,没发现 ProgressDialog  有一个方法是可以设置字体的. 于是我又来CSDN查找解决方案,可是找了好久,翻了好几页都没看到想要的结果,心冷了,找到的都说ProgressDialog 可以自定义一个View,在layout定义一个布局,然后设置到Progr

  • Android修改源码解决Alertdialog触摸对话框边缘消失的问题

    研究其父类时候发现,可以设置这么一条属性,在AlertDialog.Builder.create()之后才能调用这两个方法 方法一: setCanceledOnTouchOutside(false);调用这个方法时,按对话框以外的地方不起作用.按返回键还起作用 方法二: setCanceleable(false);调用这个方法时,按对话框以外的地方不起作用.按返回键也不起作用 这两个方法都属于Dialog方法,可查阅源码 修改后的源码如下: 复制代码 代码如下: case 1:         

  • Android ProgressBar进度条和ProgressDialog进度框的展示DEMO

    在做手机开发时,经常碰到一些比较耗时的操作,这个时候进度条就开始派上用场了.这个demo展示了ProgressBar进度条和ProgressDialog进度框.一.ProgressDialog进度框,效果如图所示:代码如下: 复制代码 代码如下: //进度对话框按钮监听     class ProssButtonListener implements OnClickListener {         @Override         public void onClick(View v) {

  • 实例详解Android自定义ProgressDialog进度条对话框的实现

    Android SDK已经提供有进度条组件ProgressDialog组件,但用的时候我们会发现可能风格与我们应用的整体风格不太搭配,而且ProgressDialog的可定制行也不太强,这时就需要我们自定义实现一个ProgressDialog. 通过看源码我们发现,ProgressDialog继承自Alertdialog,有一个ProgressBar和两个TextView组成的,通过对ProgressDialog的源码进行改进就可以实现一个自定义的ProgressDialog. 1.效果: 首先

  • Android自定义ProgressDialog进度等待框

    Android本身已经提供了ProgressDialog进度等待框,使用该Dialog,我们可以为用户提供更好的体验:在网络请求时,弹出此框等待网络数据. 不过,既然是为了提高用户体验,我们肯定希望该Dialog能更加炫酷,让用户看着更舒服.那如何做呢,当然是我们自己定义一个ProgressDialog了. 可以先看下,接下来将实现的Dialog效果图: 步骤1:要定义布局文件,该布局文件即是Dialog的布局了 <?xml version="1.0" encoding=&quo

  • Android中自定义对话框(Dialog)的实例代码

    1.修改系统默认的Dialog样式(风格.主题) 2.自定义Dialog布局文件 3.可以自己封装一个类,继承自Dialog或者直接使用Dialog类来实现,为了方便以后重复使用,建议自己封装一个Dialog类 第一步: 我们知道Android定义个控件或View的样式都是通过定义其style来实现的,查看Android框架中的主题文件,在源码中的路径:/frameworks/base/core/res/res/values/themes.xml,我们可以看到,Android为Dialog定义了

  • Android开发笔记之:Dialog的使用详解

    Dialog是任何系统都必须有的一个控件,作为辅助窗口,用于显示一些消息,或请求用户采取一引起操作等.在Android中也不例外,基本使用可能参看文档.使用时的注意事项1. BACK键能取消掉对话框(dismiss),但是却不会触发其onOkey和onCancel回调接口,所以如果你的对话框会改某些状态,一定要注意还有第三种方式取消对话框.2. 尽量少用模态对话框(Model dialog),如果Dialog.setCancellable(false),就变成了一个模态对话框,除了程序内部把其D

  • Android中Dialog去黑边的方法

    本文实例展示了Android中Dialog去黑边的方法.并且分为保留阴影与不保留阴影两种实现方法.供大家参考借鉴.具体实现方法如下: 1.不保留阴影 代码如下: <?xml version="1.0" encoding="utf-8"?> <resources> <style name="dialog" parent="@android:style/Theme.Dialog"><!--

  • android控件封装 自己封装的dialog控件

    自定义dialog肯定是用的很多了但是感觉每次做都是很乱 单纯完成任务而已,现在封装了一下 以后用到直接copy 先上图: 主activity 复制代码 代码如下: package com.su.testcustomdialog; import com.su.testcustomdialog.MyDialog.Dialogcallback; import android.app.Activity; import android.os.Bundle; import android.view.Vie

  • Android 去掉自定义dialog的白色边框的简单方法

    在value目录下,创建styles.xml文件 复制代码 代码如下: <?xml version="1.0" encoding="UTF-8"?><resources xmlns:android="http://schemas.android.com/apk/res/android"> <style        name="dialog"        parent="@androi

  • android dialog自定义实例详解

    本人工作有一个月多了.对于android很多东西,都有了新的了解或者说真正的掌握.为了让更多的像我这样的小白少走弯路,所以我会坚持将我在工作中遇到的一些比较令我印象深刻的知识点整合出来给大家(顺序是按照我工作到现在的时间来制作的,其实也是想给自己一个记录吧.记录自己一路走来以及以后的路, 至少我想找到曾经的记录都有了). 第一个需求:简单的自定义dialog 需求:创建一个dialog,该dialog具备以下功能: 1.有一个窗口可以显示文章 2.根据需求显示 1)点击同意(不同意),触发对应的

  • Android入门之AlertDialog用法实例分析

    本文实例讲述的是AlertDialog,这种对话框会经常遇到.AlertDialog跟WIN32开发中的Dialog不一样,AlertDialog是非阻塞的,而阻塞的对话框用的是PopupWindow. 先贴出该程序运行的截图: main.xml的源码: <?xml version="1.0" encoding="utf-8"?> <LinearLayout xmlns:android="http://schemas.android.co

随机推荐