用Kotlin实现极简回调

栏目: IOS · Android · 发布时间: 7年前

内容简介:在各种开发场景中,回调都有着广泛的应用,命名往往是各种不过写多了也有点烦恼,我只想打印一条日志,却写了这么多代码。不过好在这个接口里面只包含一个方法,但换做一些包含方法数量比较多的回调就显得比较臃肿了:如果你想优化你的代码,让它们看起来更简洁优雅,可以试试Kotlin的中的一些方法。

在各种开发场景中,回调都有着广泛的应用,命名往往是各种 CallbackListener ,其中在Android中接触最早也最常用的可能就是 View.OnClickListener 了。

mBtn.setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View v) {
                Log.d("MM","Click");
            }
        });
复制代码

不过写多了也有点烦恼,我只想打印一条日志,却写了这么多代码。不过好在这个接口里面只包含一个方法,但换做一些包含方法数量比较多的回调就显得比较臃肿了:

mEdit.addTextChangedListener(new TextWatcher() {
            @Override
            public void beforeTextChanged(CharSequence s, int start, int count, int after) {
                
            }

            @Override
            public void onTextChanged(CharSequence s, int start, int before, int count) {

            }

            @Override
            public void afterTextChanged(Editable s) {

            }
        });
复制代码

如果你想优化你的代码,让它们看起来更简洁优雅,可以试试Kotlin的中的一些方法。

简化

先来看下Kotlin中的回调:

mBtn.setOnClickListener(object :View.OnClickListener{
            override fun onClick(v: View?) {
                println("Click")
            }
        })
复制代码

好像一点也没简化嘛,不过因为在 Kotlin 里函数也是参数的一种,在 Java 中只包含一个方法的接口,在 Kotlin 中都可以使用 Lambda 表达式来达成一样的效果。

mBtnCallback.setOnClickListener { println("Click") }
复制代码

是不是简单很多了,但上面的用法仅适用于接口中只有一个方法的情况,如果存在多个方法的话,当然也可以简化了:

mEdit.addTextChangedListener {
            beforeTextChanged { text, start, count, after -> println("beforeTextChanged") }
            onTextChanged { text, start, before, count -> println("onTextChanged") }
            afterTextChanged { text -> println("afterTextChanged") }
        }
复制代码

也可以按需调用其中任意个方法:

mEdit.addTextChangedListener {
            onTextChanged { text, start, before, count -> println("onTextChanged") }
        }
复制代码

不过此处的 addTextChangedListener 是一个扩展函数,需要我们来自己实现:

inline fun TextView.addTextChangedListener(init: TextWatcherBridge.() -> Unit) = addTextChangedListener(TextWatcherBridge().apply(init))

class TextWatcherBridge : TextWatcher {

    private var beforeTextChanged: ((CharSequence?, Int, Int, Int) -> Unit)? = null
    private var onTextChanged: ((CharSequence?, Int, Int, Int) -> Unit)? = null
    private var afterTextChanged: ((Editable?) -> Unit)? = null

    override fun beforeTextChanged(s: CharSequence?, start: Int, count: Int, after: Int) {
        beforeTextChanged?.invoke(s, start, count, after)
    }

    override fun onTextChanged(s: CharSequence?, start: Int, before: Int, count: Int) {
        onTextChanged?.invoke(s, start, before, count)
    }

    override fun afterTextChanged(s: Editable?) {
        afterTextChanged?.invoke(s)
    }

    fun beforeTextChanged(listener: (CharSequence?, Int, Int, Int) -> Unit) {
        beforeTextChanged = listener
    }

    fun onTextChanged(listener: (CharSequence?, Int, Int, Int) -> Unit) {
        onTextChanged = listener
    }

    fun afterTextChanged(listener: (Editable?) -> Unit) {
       afterTextChanged = listener
    }

}
复制代码

原理就是实现一个扩展函数,把我们自己实现的 TextWatcherBridge 加入到回调中,因为Kotlin支持函数式编程,里面都是高阶函数。为了减少性能损耗,扩展函数声明为内联函数。


以上就是本文的全部内容,希望本文的内容对大家的学习或者工作能带来一定的帮助,也希望大家多多支持 码农网

查看所有标签

猜你喜欢:

本站部分资源来源于网络,本站转载出于传递更多信息之目的,版权归原作者或者来源机构所有,如转载稿涉及版权问题,请联系我们

Web Design Handbook

Web Design Handbook

Baeck, Philippe de 编 / 2009-12 / $ 22.54

This non-technical book brings together contemporary web design's latest and most original creative examples in the areas of services, media, blogs, contacts, links and jobs. It also traces the latest......一起来看看 《Web Design Handbook》 这本书的介绍吧!

JSON 在线解析
JSON 在线解析

在线 JSON 格式化工具

Base64 编码/解码
Base64 编码/解码

Base64 编码/解码

XML、JSON 在线转换
XML、JSON 在线转换

在线XML、JSON转换工具