Kotlin基础 — 扩展函数

一、概述

扩展函数: 指在一个类上增加一种新的行为,甚至我们没有这个类代码的访问权限。Java中,类似很多带有static方法的工具类。

优势: 不需要在调用方法的时候把整个对象当作参数传入。而是像是属于扩展类的一样,可以使用this关键字和调用所有public方法。


二、应用场景

参考anko-common 依赖包中ContextUtils、Dialogs 等文件的写法

// 属性扩展
// 注意:anko-common包中没有扩展V4包中的Fragment,需要自己扩展,否则无法获取到ctx属性
val Fragment.ctx: Context
    get() = activity

// 属性扩展
val Context.ctx: Context
    get() = this

// 函数扩展
inline fun <reified T : View> Activity.find(id: Int): T = findViewById(id) as T
inline fun <reified T : View> Fragment.find(id: Int): T = view?.findViewById(id) as T

// 函数扩展
fun Context.toast(textResource: Int) = Toast.makeText(this, textResource, Toast.LENGTH_SHORT).show()
fun Context.toast(text: CharSequence) = Toast.makeText(this, text, Toast.LENGTH_SHORT).show()
inline fun AnkoContext<*>.longToast(textResource: Int) = ctx.longToast(textResource)
// ...略...
1. 属性的扩展
val Fragment.ctx: Context
    get() = activity

public var TextView.text: CharSequence
    get() = getText()
    set(v) = setText(v)
2. 函数的扩展
fun Context.toast(message: CharSequence, duration: Int = Toast.LENGTH_SHORT) {
    Toast.makeText(this, message, duration).show()
}


三、应用

扩展EditText的TextWatcher监听

fun EditText.beforeTextChanged(action: (s: CharSequence?, start: Int, count: Int, after: Int)->Unit) = textWatch(before = action)

fun EditText.onTextChanged(action: (s: CharSequence?, start: Int, count: Int, after: Int)->Unit) = textWatch(change = action)

fun EditText.afterTextChanged(action: (s: Editable?)->Unit) = textWatch(after = action)


fun EditText.textWatch(
        before: ((s: CharSequence?, start: Int, count: Int, after: Int)->Unit)? = null,
        change: ((s: CharSequence?, start: Int, before: Int, count: Int)->Unit)? = null,
        after:  ((s: Editable?) -> Unit)? = null
) : EditText {

    return apply { // 这里返回EditText
        val listener = object : TextWatcher{
            override fun afterTextChanged(s: Editable?) {
                after?.invoke(s)
            }

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

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

        }
        addTextChangedListener(listener)
    }
}

使用

class JokeListFragment : Fragment() {

    override fun onCreateView(inflater: LayoutInflater?, container: ViewGroup?, savedInstanceState: Bundle?): View? {
        val view = inflater?.inflate(R.layout.joke_fragment_joke_list, null)
        return view
    }

    override fun onActivityCreated(savedInstanceState: Bundle?) {
        super.onActivityCreated(savedInstanceState)
       
        // 实现链式调用
        editText.beforeTextChanged {
            s, start, count, after -> Log.d("Joke", "before =$s")

        }.onTextChanged {
            s, start, count, after -> Log.d("Joke", "change =$s")

        }.afterTextChanged {
            s -> 
            Log.d("Joke", "after =${s.toString()}")
            toast(s.toString())
        }
    }
}

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值