Android 中的接口回调

本文详细介绍了Android中回调机制的应用,特别是UI事件处理,通过一个简单的按钮点击事件示例,展示了如何实现回调接口。此外,文章还提供了一个Dialog对话框的封装类,简化了Dialog的使用过程。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

http://blog.youkuaiyun.com/wangjinyu501/article/details/22052187

在Android中到处可见接口回调机制,尤其是UI事件处理方面。举一个最常见的例子button点击事件,button有一个点击方法onClick(),我们知道onclick()是一个回调方法,当用户点击button就执行这个方法。在源码中是这样定义的:
[html] view plain copy 在CODE上查看代码片 派生到我的代码片
  1. //这个是View的一个回调接口
  2. /**
  3. *Interfacedefinitionforacallbacktobeinvokedwhenaviewisclicked.
  4. */
  5. publicinterfaceOnClickListener{
  6. /**
  7. *Calledwhenaviewhasbeenclicked.
  8. *
  9. *@paramvTheviewthatwasclicked.
  10. */
  11. voidonClick(Viewv);
  12. }
下面看一个简单的例子:
[html] view plain copy 在CODE上查看代码片 派生到我的代码片
  1. importandroid.app.Activity;
  2. importandroid.os.Bundle;
  3. importandroid.view.View;
  4. importandroid.view.View.OnClickListener;
  5. importandroid.widget.Button;
  6. importandroid.widget.Toast;
  7. publicclassMainActivityextendsActivityimplementsOnClickListener{
  8. privateButtonbutton;
  9. @Override
  10. publicvoidonCreate(BundlesavedInstanceState){
  11. super.onCreate(savedInstanceState);
  12. setContentView(R.layout.activity_main);
  13. button=(Button)findViewById(R.id.button1);
  14. button.setOnClickListener(this);
  15. }
  16. @Override
  17. publicvoidonClick(Viewv){
  18. Toast.makeText(getApplication(),"OnClick",Toast.LENGTH_LONG).show();
  19. }
  20. }
  21. 这就是一个很典型的例子,当然也可以这样写:
  22. importandroid.app.Activity;
  23. importandroid.os.Bundle;
  24. importandroid.view.View;
  25. importandroid.view.View.OnClickListener;
  26. importandroid.widget.Button;
  27. publicclassSSSSextendsActivity{
  28. privateButtonbutton;
  29. privateOnClickListenerclickListener=newOnClickListener(){
  30. @Override
  31. publicvoidonClick(Viewv){
  32. //TODOAuto-generatedmethodstub
  33. }
  34. };
  35. @Override
  36. protectedvoidonCreate(BundlesavedInstanceState){
  37. //TODOAuto-generatedmethodstub
  38. super.onCreate(savedInstanceState);
  39. button=(Button)findViewById(R.id.button1);
  40. button.setOnClickListener(clickListener);
  41. }
  42. }
下面是View类的setOnClickListener方法,把和回调相关代码贴出来。什么贴它呢,因为Button继承于TextView,而TextView继承于View,在View里面处理的回调:
[html] view plain copy 在CODE上查看代码片 派生到我的代码片
  1. /**
  2. *
  3. */
  4. publicclassViewimplementsDrawable.Callback,KeyEvent.Callback,AccessibilityEventSource{
  5. /**
  6. *Listenerusedtodispatchclickevents.
  7. *Thisfieldshouldbemadeprivate,soitishiddenfromtheSDK.
  8. *{@hide}
  9. */
  10. protectedOnClickListenermOnClickListener;
  11. /**
  12. *
  13. *Registeracallbacktobeinvokedwhenthisviewisclicked.Ifthisviewisnot
  14. *clickable,itbecomesclickable.
  15. *
  16. *@paramlThecallbackthatwillrun
  17. *
  18. *@see#setClickable(boolean)
  19. */
  20. publicvoidsetOnClickListener(OnClickListenerl){
  21. if(!isClickable()){
  22. setClickable(true);
  23. }
  24. mOnClickListener=l;
  25. }
  26. /**
  27. *Callthisview'sOnClickListener,ifitisdefined.
  28. *
  29. *@returnTruetherewasanassignedOnClickListenerthatwascalled,false
  30. *otherwiseisreturned.
  31. */
  32. publicbooleanperformClick(){
  33. sendAccessibilityEvent(AccessibilityEvent.TYPE_VIEW_CLICKED);
  34. if(mOnClickListener!=null){
  35. playSoundEffect(SoundEffectConstants.CLICK);
  36. mOnClickListener.onClick(this);
  37. returntrue;
  38. }
  39. returnfalse;
  40. }
  41. }
那现在一起来总结一下基本的回调是如何实现的,首先创建一个接口,这个接口用于你在某个情景下执行相应的操作。接着创建一个功能类,比如这个类可以显示一个对话框、可以滑动菜单、可以下载数据等等。然后,在这个类里面声明回调接口的对象,之后在这个类里面创建在某个情景下需要执行的方法,而且在这个方法里面为声明的接口对象赋值。最后在其他的类中使用这个功能类就可以了。所以说,最少也是需要三个类共同来完成这个回调机制。
这下大家应该就比较明白了,那我们就自己按照这个方式和流程完成一个这样的例子。以Dialog为例,一般我们在开发时候,经常会用到Dialog。比如一个弹出框,里面有确认和取消。通常情况下,我们可能会这样写:
[html] view plain copy 在CODE上查看代码片 派生到我的代码片
  1. finalDialogdialog=newDialog(this,R.style.MyDialogStyle);
  2. dialog.setContentView(R.layout.dialog_exit_train);
  3. dialog.show();
  4. ImageButtonib_affirm=(ImageButton)dialog
  5. .findViewById(R.id.dialog_exit_ib_affirm);
  6. ImageButtonib_cancel=(ImageButton)dialog
  7. .findViewById(R.id.dialog_exit_ib_cancel);
  8. ib_affirm.setOnClickListener(newView.OnClickListener(){
  9. @Override
  10. publicvoidonClick(Viewv){
  11. saveUserData();
  12. dialog.dismiss();
  13. TestActivity.this.finish();
  14. }
  15. });
  16. ib_cancel.setOnClickListener(newView.OnClickListener(){
  17. @Override
  18. publicvoidonClick(Viewv){
  19. dialog.dismiss();
  20. }
  21. });
也就是得到点击对象之后再去调用 onClick(),这样有一个缺点就是你每次都要写,不利于重复使用。那我们就可以对此进行一个封装,看代码:
[html] view plain copy 在CODE上查看代码片 派生到我的代码片
  1. importandroid.app.Dialog;
  2. importandroid.content.Context;
  3. importandroid.os.Bundle;
  4. importandroid.text.TextPaint;
  5. importandroid.view.View;
  6. importandroid.view.Window;
  7. importandroid.view.WindowManager;
  8. importandroid.widget.Button;
  9. importandroid.widget.TextView;
  10. importcom.fanfou.app.opensource.R;
  11. /**
  12. *
  13. *
  14. */
  15. publicclassAlertInfoDialogextendsDialogimplementsView.OnClickListener{
  16. //创建接口
  17. publicstaticinterfaceOnOKClickListener{
  18. publicvoidonOKClick();
  19. }
  20. privatefinalContextmContext;
  21. privateTextViewmTitleView;
  22. privateTextViewmTextView;
  23. privateButtonmButtonOk;
  24. privateCharSequencemTitle;
  25. privateCharSequencemText;
  26. //生命接口对象
  27. privateOnOKClickListenermClickListener;
  28. publicAlertInfoDialog(finalContextcontext,finalStringtitle,
  29. finalStringtext){
  30. super(context,R.style.Dialog);
  31. this.mContext=context;
  32. this.mTitle=title;
  33. this.mText=text;
  34. }
  35. privatevoidinit(){
  36. setContentView(R.layout.dialog_alert);
  37. this.mTitleView=(TextView)findViewById(R.id.title);
  38. finalTextPainttp=this.mTitleView.getPaint();
  39. tp.setFakeBoldText(true);
  40. this.mTitleView.setText(this.mTitle);
  41. this.mTextView=(TextView)findViewById(R.id.text);
  42. this.mTextView.setText(this.mText);
  43. this.mButtonOk=(Button)findViewById(R.id.button_ok);
  44. this.mButtonOk.setOnClickListener(this);
  45. }
  46. @Override
  47. publicvoidonClick(finalViewv){
  48. finalintid=v.getId();
  49. switch(id){
  50. caseR.id.button_ok:
  51. cancel();//调用
  52. if(this.mClickListener!=null){
  53. this.mClickListener.onOKClick();
  54. }
  55. break;
  56. default:
  57. break;
  58. }
  59. }
  60. @Override
  61. protectedvoidonCreate(finalBundlesavedInstanceState){
  62. super.onCreate(savedInstanceState);
  63. setBlurEffect();
  64. init();
  65. }
  66. protectedvoidsetBlurEffect(){
  67. finalWindowwindow=getWindow();
  68. finalWindowManager.LayoutParamslp=window.getAttributes();
  69. //lp.alpha=0.8f;
  70. lp.dimAmount=0.6f;
  71. window.setAttributes(lp);
  72. window.addFlags(WindowManager.LayoutParams.FLAG_DIM_BEHIND);
  73. //window.addFlags(WindowManager.LayoutParams.FLAG_BLUR_BEHIND);
  74. }
  75. publicvoidsetMessage(finalCharSequencemessage){
  76. this.mText=message;
  77. this.mTextView.setText(this.mText);
  78. }
  79. publicvoidsetMessage(finalintresId){
  80. this.mText=this.mContext.getResources().getText(resId);
  81. this.mTextView.setText(this.mText);
  82. }
  83. //设置监听器也就是实例化接口
  84. publicvoidsetOnClickListener(finalOnOKClickListenerclickListener){
  85. this.mClickListener=clickListener;
  86. }
  87. @Override
  88. publicvoidsetTitle(finalCharSequencetitle){
  89. this.mTitle=title;
  90. this.mTitleView.setText(this.mTitle);
  91. }
  92. @Override
  93. publicvoidsetTitle(finalintresId){
  94. this.mTitle=this.mContext.getResources().getText(resId);
  95. this.mTitleView.setText(this.mTitle);
  96. }
  97. }
方式和上面介绍的一样,感兴趣的朋友可以自己去实现其他效果的。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值