KotlinAndroid技术知识Android开发

带有生命周期全新的Android开发框架,Kotlin语言

2018-04-24  本文已影响60人  谢长意

框架详细介绍GitHub地址

KotlinMvcLib2

升级版的mvc模式,controller和activity生命周期绑定,利用livedata(与接收者的生命周期相关)来传输数据
网络访问封装了retrofit基本访问,并没有结合rxjava,如果需要可以自己来设置

第一步 导入库

1.在根builde.gradle的allprojects下面添加jitpack仓库

 repositories {
        google()
        jcenter()
        maven { url 'https://jitpack.io' }
    }

2.设置依赖基本设置,在根builde.gradle的buildscript下面添加统一设置

    ext.kotlin_version = '1.2.40'//你的kotlin版本
    ext.sdk_version = '27.1.1'//你的sdk版本 eg:implementation "com.android.support:recyclerview-v7:$sdk_version"
    ext.archLifecycleVersion = '1.1.1' //生命周期版本
    ext.minSdkVersion = 19//最小版本
    ext.targetSdkVersion = 28//最大支持
    ext.compileSdkVersion = 27//编译版本

3.导入依赖库

 api 'com.github.kotle:KotlinMvcLib2:1.0.4'

第二步 开始使用

建议自己写三个基类(model,controller,activty)来继承仓库的三个基类
因为这样你可以在自己基类里面处理一些通用的操作

1.你的网络层应该继承KtBaseModel,提供一些数据来源

class DemoModel : KtBaseModel() {
}

2.你的控制层应该继承KtBaseController,做一些与ui无关的逻辑操作

//如果需要model,传入model的泛型
class DemoController(application: Application):KtBaseController<DemoModel>(application) {
    override fun createNet(): DemoModel? = DemoModel()
    //对象销毁的时候调用,有activty通过自己的生命周期调用,在onDestroy()之前
    override fun onCleared() {
        super.onCleared()
    }
}
//如果功能简单 不需要model类,泛型处传入KtBaseModel,并且createNet()方法返回null
class DemoController(application: Application):KtBaseController<KtBaseModel>(application) {
    override fun createNet(): DemoModel? = null
    //对象销毁的时候调用,有activty通过自己的生命周期调用,在onDestroy()之前
    override fun onCleared() {
        super.onCleared()
    }
}

3.你的activity应该继承KtBaseActivity,并传入控制层的泛型

//注意:这里并不是通过new的方式来创建controller类,而是另外一种,在基类已经处理
class DemoActivity : KtBaseActivity<DemoController>() {
    //获取和activity关联的xml
    override fun getLayoutRes(): Int =R.layout.activity_demo
    //返回值为标题,如果不需要返回null
    override fun initTitle(toolbar: Toolbar): String? {
       return "我是标题,不需要返回null"
    }
    //这里可以做一些初始化操作,比如设置liveData的监听
    override fun onObserve(controller: DemoController) {
       
    }
    //在Activity的onCreate最后执行,防止重写activity发出一些警告(由于java和kotlin的一些不兼容)
    override fun initCreate(savedInstanceState: Bundle?) {
        
    }
}
//一些简单的activity,如果不需要Controller类,泛型传入KtBaseController<*>或者KtBaseController<KtBaseModel>
class DemoActivity : KtBaseActivity<KtBaseController<*>>() {
    //不需要controller,一点要重写此方法,返回false,否则会抛出异常
    override fun isNeedController(): Boolean {
        return false
    }
    //获取和activity关联的xml
    override fun getLayoutRes(): Int =R.layout.activity_demo
    //返回值为标题,如果不需要返回null
    override fun initTitle(toolbar: Toolbar): String? {
       return "我是标题,不需要返回null"
    }
    //这里可以做一些初始化操作,比如设置liveData的监听
    override fun onObserve(controller: KtBaseController<*>) {

    }
    //在Activity的onCreate最后执行,防止重写activity发出一些警告(由于java和kotlin的一些不兼容)
    override fun initCreate(savedInstanceState: Bundle?) {

    }
}

3.你的fragment应该继承KtBaseFragment,并传入控制层的泛型

class DemoFragment : KtBaseFragment<DemoController>() {
    override fun getLayoutRes(): Int = R.layout.fragment_demo
    //在onCreateView()的时候调用
    override fun onCreateRootView(inflater: LayoutInflater, container: ViewGroup?, savedInstanceState: Bundle?) {
    }

    override fun onObserve(controller: DemoController) {

    }

    override fun isNeedController(): Boolean {
        //如果不需要controller 返回false
        mController//拿到controller对象
        mRootView//拿到fragment对应的xml
        return super.isNeedController()
    }
}

第三步 通过KtLiveData来把controller的数据给activity

1.设置一个KtLiveData的变量

val test=KtLiveData<String>()
//然后推送数据
 test.set("在主线程用这个方法")
 test.post("在子线程用这个方法")

2.在Activity注册监听

 //这里可以做一些初始化操作,比如设置liveData的监听
    override fun onObserve(controller: DemoController) {
         controller.test.call(this, Observer { 
             //这里接收set或者post的值,在onStart()之后接收,在onStop()不在接收
         })
    }

其他

在KtBaseActivity有一个mController的变量,直接拿到congtroller对象
在KtBaseController,getViewModel()获取model对象,getApplication<>()拿到全局的application

关于网络框架的使用

1.新建一个Api接口,然后获取searvice

interface Api {
    @GET("open/xiaohua.json")
    fun getJokListRes():Call<ResponseBody>
}
//创建retrofit对象
val BASE_URL = "http://api.laifudao.com/"
val service by lazy { KtNet.ktCreateService(BASE_URL, Api::class.java) }
//然后发送请求
  KtNet.ktSendRequest(service.getJokListRes(), {
            //成功
       }, {
          //失败
        })

2.KtNet是封装的一个网络请求,完整代码如下

object KtNet {
    private var retrofit: Retrofit? = null
    private lateinit var api: Any
    /**
     * 默认的创建网络的请求,数据会转为Bean
     */
    fun <T> ktCreateService(baseUrl: String, t: Class<T>, client: OkHttpClient? = null): T {
        if (retrofit != null && retrofit?.baseUrl().toString() == baseUrl) {
            return (api as? T)!!
        }
        retrofit = Retrofit.Builder()
                .baseUrl(baseUrl)
                .client(client ?: OkHttpClient())
                .addConverterFactory(GsonConverterFactory.create())
                .build()
        api = retrofit!!.create<T>(t)!!
        return (api as? T)!!
    }

    /**
     * 有基本的使用功能,需要自定义转换器
     */
    fun <T> ktCreateBaseNet(baseUrl: String, apiClass: Class<T>, builder: ((Retrofit.Builder) -> Unit)? = null): T {
        val retrofitBuilder = Retrofit.Builder();
        retrofitBuilder.baseUrl(baseUrl)
        builder?.invoke(retrofitBuilder)
        return retrofitBuilder.build().create<T>(apiClass)
    }

    /**
     * 通过service发送请求,并回调
     */
    fun <T> ktSendRequest(request: retrofit2.Call<T>, success: (T) -> Unit, fail: ((Throwable?) -> Unit)? = null) {
        request.enqueue(object : Callback<T> {
            override fun onFailure(call: retrofit2.Call<T>?, t: Throwable?) {
                fail?.invoke(t)
                t?.printStackTrace()
            }

            override fun onResponse(call: retrofit2.Call<T>?, response: Response<T>?) {
                if (response?.body() == null) {
                    fail?.invoke(Throwable("response.body is null"))
                } else {
                    success.invoke(response.body()!!)
                }
            }
        })
    }
}

关于KtPermission

object KtPermission {
    private var noPermissionList = ArrayList<String>()
    //需要的权限添加到这个集合中
    private var needPermissions = ArrayList<String>()

    fun addNeedPermission(vararg permissions: String) {
        for (c in permissions) {
            if (!needPermissions.contains(c)) {
                needPermissions.add(c)
            }
        }
    }

    fun addNeedPermission(permissions: List<String>) {
        for (c in permissions) {
            if (!needPermissions.contains(c)) {
                needPermissions.add(c)
            }
        }
    }

    /**
     * ture 获取所有权限
     * false 没有获取所有权限
     */
    fun checkedPermission(context: Activity): Boolean {
        var isGetAllPermission = true
        noPermissionList.clear()
        needPermissions?.filter { ContextCompat.checkSelfPermission(context, it) == PackageManager.PERMISSION_DENIED }
                ?.forEach {
                    isGetAllPermission = false
                    noPermissionList.add(it)
                }
        if (!isGetAllPermission) {
            val p = Array(noPermissionList.size, { noPermissionList[it] })
            ActivityCompat.requestPermissions(context, p, 1)
        }
        return isGetAllPermission
    }
}
上一篇 下一篇

猜你喜欢

热点阅读