在安卓开发中,我们经常会遇到这种情况,就是可爱的UI们设计了一套属于我们自己风格的弹出框,为了彰显我们自己的风格,使用自动的dialog当然满足不了我们的需求,所以还是得这基础上写出我们自己的提示框,以后UI再变化,我们也只需要修改样式就好了。
1.首先我们先写好dialog的样式
custom_dialog.xml
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89
| <?xml version="1.0" encoding="utf-8"?> <LinearLayout xmlns:android="http://schemas.android.com/apk/res/android" android:id="@+id/content" android:layout_width="280dp" android:layout_height="wrap_content" android:paddingRight="24dp" android:paddingLeft="24dp" android:paddingTop="21dp" android:paddingBottom="21dp" android:orientation="vertical"> <TextView android:id="@+id/title" android:layout_width="wrap_content" android:layout_height="wrap_content" android:textSize="16sp" android:textColor="#deffffff" android:letterSpacing="0.03" android:lineSpacingExtra="8sp" android:text="提示" android:layout_marginTop="6dp" android:layout_marginBottom="15dp" android:visibility="gone"/> <TextView android:id="@+id/message" android:layout_width="256dp" android:layout_height="wrap_content" android:textSize="14sp" android:textColor="#99ffffff" android:letterSpacing="0.02" android:lineSpacingExtra="6sp" android:text="这是自定义弹出框" /> <RelativeLayout android:id="@+id/twoButtonLayout" android:layout_width="match_parent" android:layout_height="wrap_content" android:layout_marginTop="31dp"> <TextView android:id="@+id/negativeBtn" android:layout_width="wrap_content" android:layout_height="wrap_content" android:textSize="14sp" android:textColor="#138ef0" android:letterSpacing="0.09" android:lineSpacingExtra="2sp" android:text="取消" android:layout_alignParentRight="true" android:layout_marginRight="89dp" android:padding="10dp" android:focusableInTouchMode="false" /> <TextView android:id="@+id/positiveBtn" android:layout_width="wrap_content" android:layout_height="wrap_content" android:textSize="14sp" android:textColor="#138ef0" android:letterSpacing="0.09" android:lineSpacingExtra="2sp" android:text="满意" android:layout_alignParentRight="true" android:paddingBottom="10dp" android:paddingTop="10dp" android:paddingLeft="10dp" android:paddingRight="5dp" /> </RelativeLayout> <RelativeLayout android:id="@+id/singleButtonLayout" android:layout_width="match_parent" android:layout_height="wrap_content" android:layout_marginTop="41dp"> <TextView android:id="@+id/singleBtn" android:layout_width="wrap_content" android:layout_height="wrap_content" android:textSize="14sp" android:textColor="#138ef0" android:letterSpacing="0.09" android:lineSpacingExtra="2sp" android:text="确定" android:layout_alignParentRight="true" android:paddingBottom="10dp" android:paddingTop="10dp" android:paddingLeft="10dp" android:paddingRight="5dp" /> </RelativeLayout> </LinearLayout>
|
2.然后定义一个CustomDialog继承Dialog,在这里定义我们自己要调用的方法等。
CustomDialog.kt
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151
| package com.xindong.rocket
import android.app.Dialog import android.content.Context import android.view.LayoutInflater import android.view.View import android.view.ViewGroup import android.widget.LinearLayout import android.widget.TextView
class CustomDialog : Dialog {
constructor(context: Context) : super(context) {} constructor(context: Context, theme: Int) : super(context, theme) {}
class Builder(context: Context) { private var title: String? = null private var message: String? = null private var contentView: View? = null private var positiveButtonText: String? = null private var negativeButtonText: String? = null private var singleButtonText: String? = null private var positiveButtonClickListener: View.OnClickListener? = null private var negativeButtonClickListener: View.OnClickListener? = null private var singleButtonClickListener: View.OnClickListener? = null
private val layout: View private val dialog: CustomDialog = CustomDialog(context, R.style.CustomDialog)
init { val inflater = context.getSystemService(Context.LAYOUT_INFLATER_SERVICE) as LayoutInflater layout = inflater.inflate(R.layout.custom_dialog, null) dialog.addContentView(layout, ViewGroup.LayoutParams(ViewGroup.LayoutParams.MATCH_PARENT, ViewGroup.LayoutParams.WRAP_CONTENT)) }
fun setTitle(title: String): Builder{ this.title = title return this }
fun setMessage(message: String): Builder { this.message = message return this }
fun setContentView(v: View): Builder { this.contentView = v return this }
fun setPositiveButton(positiveButtonText: String, listener: View.OnClickListener): Builder { this.positiveButtonText = positiveButtonText this.positiveButtonClickListener = listener return this }
fun setNegativeButton(negativeButtonText: String, listener: View.OnClickListener): Builder { this.negativeButtonText = negativeButtonText this.negativeButtonClickListener = listener return this }
fun setSingleButton(singleButtonText: String, listener: View.OnClickListener): Builder { this.singleButtonText = singleButtonText this.singleButtonClickListener = listener return this }
fun createSingleButtonDialog(): CustomDialog { showSingleButton() layout.findViewById<View>(R.id.singleBtn).setOnClickListener(singleButtonClickListener) if (singleButtonText != null) { (layout.findViewById<View>(R.id.singleBtn) as TextView).text = singleButtonText } else { (layout.findViewById<View>(R.id.singleBtn) as TextView).text = "知道了" } create() return dialog }
fun createTwoButtonDialog(): CustomDialog { showTwoButton() layout.findViewById<View>(R.id.positiveBtn).setOnClickListener(positiveButtonClickListener) layout.findViewById<View>(R.id.negativeBtn).setOnClickListener(negativeButtonClickListener) if (positiveButtonText != null) { (layout.findViewById<View>(R.id.positiveBtn) as TextView).text = positiveButtonText } else { (layout.findViewById<View>(R.id.positiveBtn) as TextView).text = "确定" } if (negativeButtonText != null) { (layout.findViewById<View>(R.id.negativeBtn) as TextView).text = negativeButtonText } else { (layout.findViewById<View>(R.id.negativeBtn) as TextView).text = "取消" } create() return dialog }
private fun create() { if (message != null) { (layout.findViewById<View>(R.id.message) as TextView).text = message } else if (contentView != null) { (layout.findViewById<View>(R.id.content) as LinearLayout).removeAllViews() (layout.findViewById<View>(R.id.content) as LinearLayout) .addView(contentView, ViewGroup.LayoutParams(ViewGroup.LayoutParams.MATCH_PARENT, ViewGroup.LayoutParams.MATCH_PARENT)) } if(title!=null && title!!.isNotEmpty()){ (layout.findViewById<View>(R.id.title) as TextView).text = title showTitle() } dialog.setContentView(layout) dialog.setCancelable(true) dialog.setCanceledOnTouchOutside(false) }
private fun showTwoButton() { layout.findViewById<View>(R.id.singleButtonLayout).visibility = View.GONE layout.findViewById<View>(R.id.twoButtonLayout).visibility = View.VISIBLE }
private fun showSingleButton() { layout.findViewById<View>(R.id.singleButtonLayout).visibility = View.VISIBLE layout.findViewById<View>(R.id.twoButtonLayout).visibility = View.GONE }
private fun showTitle() { layout.findViewById<View>(R.id.title).visibility = View.VISIBLE }
} }
|
3.设置dialog的背景
drawable/comment_dialog_bg.xml
1 2 3 4 5
| <?xml version="1.0" encoding="utf-8"?> <shape xmlns:android="http://schemas.android.com/apk/res/android"> <corners android:radius="4dp"/> <solid android:color="#282a34"/> </shape>
|
4.将上面写好的dialog背景设置给一个style
style.xml
1 2 3
| <style name="CustomDialog" parent="android:Theme.Dialog"> <item name="android:windowBackground">@drawable/comment_dialog_bg</item> </style>
|
5.最后在activity里定义并调用自定义dialog的方法。
MainActivty.kt
1 2
| private var builderForCustom: CustomDialog.Builder? = null private var mDialog: CustomDialog? = null
|
然后在onCreate里
1
| builderForCustom = CustomDialog.Builder(this)
|
定义方法
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16
| private fun showSingleButtonDialog(title: String, alertText: String, btnText: String, onClickListener:View.OnClickListener) { mDialog = builderForCustom!!.setTitle(title) .setMessage(alertText) .setSingleButton(btnText, onClickListener) .createSingleButtonDialog() mDialog!!.show() }
private fun showTwoButtonDialog(title: String, alertText: String, confirmText: String, cancelText: String, conFirmListener: View.OnClickListener, cancelListener: View.OnClickListener) { mDialog = builderForCustom!!.setTitle(title) .setMessage(alertText) .setPositiveButton(confirmText, conFirmListener) .setNegativeButton(cancelText, cancelListener) .createTwoButtonDialog() mDialog!!.show() }
|
调用方法
1 2 3 4 5 6 7
| showTwoButtonDialog("", "这是自定义弹出框","确定", "取消", View.OnClickListener { mDialog!!.dismiss() },View.OnClickListener { mDialog!!.dismiss() })
|
调用单个按钮的方法也是同样的方式。
如果是在fragment调用activity里定义的弹出框方法,则可以单独定义一个关闭弹出框的方法,或者将mDialog设置为公共属性。
效果如下
