android开发笔记之从Button点击说起

android开发笔记之从Button点击说起_第1张图片

Button使用

平时,我们开发,Button控件一般就是如下使用:

先在布局文件中定义Button控件:

    <Button
        android:id="@+id/button"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:text="TestButton" />

再在java文件中使用此Button控件:

//定义Button
private Button button = null;
//定义接口OnClickListener
private View.OnClickListener onClickListener = new View.OnClickListener() {
        @Override
        public void onClick(View v) {
            Log.i(TAG,"View.OnClickListener--onClick");
        }
};
//获取button对象
button = (Button)findViewById(R.id.button);
//设置button点击事件监听接口
button.setOnClickListener(onClickListener);

执行程序,当button点击时,执行接口OnClickListener中的onClick方法,打印Log:

View.OnClickListener--onClick

android是怎么样设计此功能的

我们查看源码—View.java

OnClickListener 接口定义:

因此,响应点击Button后的操作,各个控件,各个场景都不一样,是一个可变的动作,所以android定义了一个接口OnClickListener来应对这个可变的因素:

    public interface OnClickListener {
        /** * Called when a view has been clicked. * * @param v The view that was clicked. */
        void onClick(View v);
    }

定义内部的OnClickListener变量mOnClickListener:

/** * Listener used to dispatch click events. * This field should be made private, so it is hidden from the SDK. * {@hide} */
public OnClickListener mOnClickListener;

setOnClickListener方法:

public void setOnClickListener(OnClickListener l) {
        if (!isClickable()) {
            setClickable(true);
        }
        //给mOnClickListener变量赋值
        getListenerInfo().mOnClickListener = l;
}

执行click的方法performClick:

    /** * Call this view's OnClickListener, if it is defined. Performs all normal * actions associated with clicking: reporting accessibility event, playing * a sound, etc. * * @return True there was an assigned OnClickListener that was called, false * otherwise is returned. */
    public boolean performClick() {
        final boolean result;
        final ListenerInfo li = mListenerInfo;
        if (li != null && li.mOnClickListener != null) {
            //播放点击声音
            playSoundEffect(SoundEffectConstants.CLICK);
            //执行点击的回调方法onClick
            li.mOnClickListener.onClick(this);
            result = true;
        } else {
            result = false;
        }

        sendAccessibilityEvent(AccessibilityEvent.TYPE_VIEW_CLICKED);
        return result;
    }

执行click的方法callOnClick:

/** * Directly call any attached OnClickListener. Unlike {@link #performClick()}, * this only calls the listener, and does not do any associated clicking * actions like reporting an accessibility event. * * @return True there was an assigned OnClickListener that was called, false * otherwise is returned. */
public boolean callOnClick() {
        ListenerInfo li = mListenerInfo;
        if (li != null && li.mOnClickListener != null) {
            //执行点击的回调方法onClick
            li.mOnClickListener.onClick(this);
            return true;
        }
        return false;
}

点击button是在什么时候点击监听回调接口:

boolean performAccessibilityActionInternal(int action, Bundle arguments) {
        switch (action) {
            //ACTION_CLICK 点击Button
            case AccessibilityNodeInfo.ACTION_CLICK: {
                if (isClickable()) {
                    //执行点击button监听接口
                    performClick();
                    return true;
                }
            } break;
......
......
public boolean onTouchEvent(MotionEvent event) {
......
        //可以点击
        if (((viewFlags & CLICKABLE) == CLICKABLE ||
                (viewFlags & LONG_CLICKABLE) == LONG_CLICKABLE)) {
            switch (event.getAction()) {
                //button ACTION_UP
                case MotionEvent.ACTION_UP:
                   ......
                   if (mPerformClick == null) {
                       mPerformClick = new PerformClick();
                    }
                    if (!post(mPerformClick)) {
                       //执行点击button监听接口
                       performClick();
                    }
......

再修改Button使用方法:

我们为了让大家真正看明白android为什么如此设计Button是这样响应点击事件,我们再定义一个MyButtonOnClickListener类:

//类MyButtonOnClickListener实现接口View.OnClickListener,实现方法onClick:

public class MyButtonOnClickListener implements View.OnClickListener {
    public static final String TAG = "MyButtonOnClickListener";

    @Override
    public void onClick(View v) {
        Log.i(TAG,"MyButtonOnClickListener--onClick");
    }
}

然后,我们再实现点击Button代码:

//定义Button
private Button button = null;
//定义MyButtonOnClickListener
private MyButtonOnClickListener myButtonOnClickListener = new MyButtonOnClickListener();
//获取button对象
button = (Button)findViewById(R.id.button);
//设置button点击事件监听接口myButtonOnClickListener
button.setOnClickListener(myButtonOnClickListener);

现在,我们列出uml类图:

大家看类图,应该是不是觉得有一点眼熟呢?是不是和策略模式的类图相似呢?
对,这就是一个最简单的策略模式。

接口在android开发中的样例

android开发笔记之监听者模式—http://blog.csdn.net/hfreeman2008/article/details/37568615

这是我以前写的一篇文章,非常好的应用了接口。

接口在java开发中的样例

定义接口:

接口IListener:

public interface IListener {
    public void run();
}

定义一个Body类:

public class Body {
    //定义一个IListener类型的变量listener
    private IListener listener = null;
    //设置Listener
    public void setListener(IListener listener){
        this.listener = listener;
    }
    //执行方法
    public void dosomething(){
        System.out.println("Body--dosomething()--before");
        if(listener != null){
            //这才是接口方法的调用的地方,也是用于后面的地方实现的地方
            listener.run();
        }
        System.out.println("Body--dosomething()--after");
    }

}

我们再定义一个接口实现类ListenerTest01:

public class ListenerTest01 implements IListener {

    //ListenerTest01实现接口IListener中run方法
    @Override
    public void run() {
        // TODO Auto-generated method stub
        System.out.println("ListenerTest01---run()");
    }
}

我们在Client中使用:


public class Client {

    public static void main(String[] args) {
        // TODO Auto-generated method stub
        //定义一个对象listener,大家常用这一种方式,实现接口IListener中run方法
        IListener listener = new IListener() {

            @Override
            public void run() {
                // TODO Auto-generated method stub
                System.out.println("listener---run()");
            }
        };
        //定义一个对象listenerTest01 
        IListener listenerTest01 = new ListenerTest01();

        //我们没有设置Listener
        System.out.println("---------------------");
        Body body = new Body();
        body.dosomething();

        //我们设置Listener为listener
        System.out.println("---------------------");
        body.setListener(listener);
        body.dosomething();

        //我们设置Listener为listenerTest01
        System.out.println("---------------------");        
        body.setListener(listenerTest01);
        body.dosomething(); 
    }

}

输出结果:

--------------------- Body--dosomething()--before Body--dosomething()--after ---------------------
Body--dosomething()--before
listener---run()
Body--dosomething()--after ---------------------
Body--dosomething()--before
ListenerTest01---run()
Body--dosomething()--after

从输出结果,我们可以看到:
如果不设置Listener,就直接执行对象的dosomething方法,而不执行listener.run()方法。
如果我们设置Listener为listener,则执行listener—run()方法。
如果我们设置Listener为ListenerTest01,则执行ListenerTest01—run()方法。

接口是将一个行为操作的实现放到后面具体类,具体位置来实现,并且此行为操作还可以改变。

你可能感兴趣的:(android,接口,button,interface)