zoukankan      html  css  js  c++  java
  • Android高仿IOS和QQ的弹出对话框

            我们知道Android中其实并不提供圆形的东西,像Button,TextView,EditView等等都是没有弧形元素在里面(看看这些控件的属性就知道了)。而很多时候我们的程序中又需要用到这样有弧形元素的控件,当然我们着先肯定会想到用图片去遮盖,例如我们要一个圆形的图片,我们可以在原有图片的基础上加上一个中间为空的图片。这样就可以获得圆形图片的效果。不过,这样方法一看就可以水平比较低的。因为要用这样的一张图片,势必消耗资源。不过,如果我们是要去实现一个非常不规则的图形时,这里,我们可以去采用图片覆盖的方法。言归正传,其实要获得圆形图片的方法我们可以去画,在以后我更新博客来讲解这个问题。

    我们来看一下这个仿IOS或是QQ的自定义的Dialog究竟长什么样子。如下:


    再来看看Android原生的Dialog长什么样子,如下:


    这里我只截取了屏幕的一部分来展示,自定义的Dialog显而易见。

    我们可以这样来思考,要实现这样一个效果,那它应该是一个Dialog。因为我们是要让它弹出来(说实话,如果你非要把整个搞一个Activity或是Fragment,然后设置背景透明,这样可以!不过不建议)。

    于是我们知道,我们的CustomDialog要去继承Android原生的Dialog,而同时又必须去重写里面的方法。像setPositiveButton(...),setNegativeButton(...),create()等。不过,show()方法不用重写,这里我感觉应该是和Toast中的show()的原理一样,只是将我们的Dialog加入到系统的Dialog队列中(当然也可能不是)。重写其方法的关键代码如下:

    public Builder setContentView(View v) {
    			this.contentView = v;
    			return this;
    		}
    
    		public Builder setPositiveButton(int confirm_btnText,
    				DialogInterface.OnClickListener listener) {
    			this.confirm_btnText = (String) context
    					.getText(confirm_btnText);
    			this.confirm_btnClickListener = listener;
    			return this;
    		}
    
    		public Builder setPositiveButton(String confirm_btnText,
    				DialogInterface.OnClickListener listener) {
    			this.confirm_btnText = confirm_btnText;
    			this.confirm_btnClickListener = listener;
    			return this;
    		}
    
    		public Builder setNegativeButton(int cancel_btnText,
    				DialogInterface.OnClickListener listener) {
    			this.cancel_btnText = (String) context
    					.getText(cancel_btnText);
    			this.cancel_btnClickListener = listener;
    			return this;
    		}
    
    		public Builder setNegativeButton(String cancel_btnText,
    				DialogInterface.OnClickListener listener) {
    			this.cancel_btnText = cancel_btnText;
    			this.cancel_btnClickListener = listener;
    			return this;
    		}
    
    		public CustomDialog create() {
    			LayoutInflater inflater = (LayoutInflater) context
    					.getSystemService(Context.LAYOUT_INFLATER_SERVICE);
    			// instantiate the dialog with the custom Theme
    			final CustomDialog dialog = new CustomDialog(context, R.style.mystyle);
    			View layout = inflater.inflate(R.layout.customdialog, null);
    			dialog.addContentView(layout, new LayoutParams(LayoutParams.MATCH_PARENT, LayoutParams.WRAP_CONTENT));
    			// set the dialog title
    			((TextView) layout.findViewById(R.id.title)).setText(title);
    			((TextView) layout.findViewById(R.id.title)).getPaint().setFakeBoldText(true);;
    			// set the confirm button
    			if (confirm_btnText != null) {
    				((Button) layout.findViewById(R.id.confirm_btn))
    						.setText(confirm_btnText);
    				if (confirm_btnClickListener != null) {
    					((Button) layout.findViewById(R.id.confirm_btn))
    							.setOnClickListener(new View.OnClickListener() {
    								public void onClick(View v) {
    									confirm_btnClickListener.onClick(dialog,
    											DialogInterface.BUTTON_POSITIVE);
    								}
    							});
    				}
    			} else {
    				// if no confirm button just set the visibility to GONE
    				layout.findViewById(R.id.confirm_btn).setVisibility(
    						View.GONE);
    			}
    			// set the cancel button
    			if (cancel_btnText != null) {
    				((Button) layout.findViewById(R.id.cancel_btn))
    						.setText(cancel_btnText);
    				if (cancel_btnClickListener != null) {
    					((Button) layout.findViewById(R.id.cancel_btn))
    							.setOnClickListener(new View.OnClickListener() {
    								public void onClick(View v) {
    									cancel_btnClickListener.onClick(dialog,
    											DialogInterface.BUTTON_NEGATIVE);
    								}
    							});
    				}
    			} else {
    				// if no confirm button just set the visibility to GONE
    				layout.findViewById(R.id.cancel_btn).setVisibility(
    						View.GONE);
    			}
    			// set the content message
    			if (message != null) {
    				((TextView) layout.findViewById(R.id.message)).setText(message);
    			} else if (contentView != null) {
    				((LinearLayout) layout.findViewById(R.id.message))
    						.removeAllViews();
    				((LinearLayout) layout.findViewById(R.id.message)).addView(
    						contentView, new LayoutParams(
    								LayoutParams.WRAP_CONTENT,
    								LayoutParams.WRAP_CONTENT));
    			}
    			dialog.setContentView(layout);
    			return dialog;
    		}
    使用的方法其实和我们使用AlertDialog的方法差不多,如下:

    CustomDialog.Builder builder = new Builder(MainActivity.this);
    builder.setTitle(R.string.prompt);
    builder.setMessage(R.string.exit_app);
    builder.setPositiveButton(R.string.confirm, dialogButtonClickListener);
    builder.setNegativeButton(R.string.cancel, dialogButtonClickListener);
    builder.create().show();
    同原生Dialog一样,这里的自定义Dialog不仅可以显示提示信息,其实它可以显示任何你想要显示的信息。关键是这里的builder.setMessage(R.string.exit_app);,这里的setMessage(...)的参数只是字符串,我们可以给它传一个对象,任何你想要传给它的对象。例如下图所示:


    图中用红色标出的地方,是一个Layout,我们可以创建一个Model,类似Java中bean,这个Model里有各种我们需要显示的信息,以作为这个Model的成员。

    如下是程序MainActivity的全部代码,在此贴出代码的原因是这里的MainActivity和我的工程中的MainActivity的代码有不一样的地方,主要是有关于确定和取消按钮的点击监听事件。

    public class MainActivity extends Activity implements OnClickListener{
    	private Button ios_dialog_btn,android_dialog_btn;
    	private Toast mToast;
    	
    	@Override
    	protected void onCreate(Bundle savedInstanceState) {
    		super.onCreate(savedInstanceState);
    		setContentView(R.layout.activity_main);
    		
    		ios_dialog_btn = (Button) findViewById(R.id.ios_dialog_btn);
    		android_dialog_btn = (Button) findViewById(R.id.android_dialog_btn);
    		
    		ios_dialog_btn.setOnClickListener(this);
    		android_dialog_btn.setOnClickListener(this);
    		
    	}
    
    	@Override
    	public void onClick(View v) {
    		switch (v.getId()) {
    		case R.id.ios_dialog_btn:
    			CustomDialog.Builder builder = new Builder(MainActivity.this);
    			builder.setTitle(R.string.prompt);
    			builder.setMessage(R.string.exit_app);
    			builder.setPositiveButton(R.string.confirm, dialogButtonClickListener);
    			builder.setNegativeButton(R.string.cancel, dialogButtonClickListener);
    			builder.create().show();
    			break;
    		case R.id.android_dialog_btn:
    			AlertDialog.Builder mbuilder = new AlertDialog.Builder(MainActivity.this);
    			mbuilder.setTitle(R.string.prompt);
    			mbuilder.setMessage(R.string.exit_app);
    			mbuilder.setPositiveButton(R.string.confirm, dialogButtonClickListener);
    			mbuilder.setNegativeButton(R.string.cancel, dialogButtonClickListener);
    			mbuilder.create().show();
    			break;
    
    		default:
    			break;
    		}
    	}
    	
    	private void showToast(CharSequence message) {
    		if (null == mToast) {
    			mToast = Toast.makeText(this, message, Toast.LENGTH_SHORT);
    			mToast.setGravity(Gravity.CENTER, 0, 0);
    		} else {
    			mToast.setText(message);
    		}
    
    		mToast.show();
    	}
    	
    	private DialogInterface.OnClickListener dialogButtonClickListener = new DialogInterface.OnClickListener() {
    		
    		@Override
    		public void onClick(DialogInterface dialog, int which) {
    			switch (which) {
    			case DialogInterface.BUTTON_POSITIVE:
    				dialog.dismiss();
    				showToast("你点击了确定按钮.");
    				break;
    			case DialogInterface.BUTTON_NEGATIVE:
    				dialog.dismiss();
    				showToast("你点击了取消按钮.");
    				break;
    
    			default:
    				break;
    			}
    		}
    	};
    
    }


    工程代码下载:http://download.csdn.net/detail/u013761665/8030735


  • 相关阅读:
    leetcode-easy-string-28 Implement strStr()
    leetcode-easy-string-242. Valid Anagram
    leetcode-easy-string-387 First Unique Character in a String
    指派问题(匈牙利算法)
    Neural Network Basics
    Softmax && Cross-entropy Error
    Our Future
    SVD
    Lecture2
    RF 和 GBDT联系和区别
  • 原文地址:https://www.cnblogs.com/fengju/p/6336138.html
Copyright © 2011-2022 走看看