ICode9

精准搜索请尝试: 精确搜索
首页 > 其他分享> 文章详细

Retrofit完美适配LiveData,使用Kotlin和Android JetPack开发一款App

2019-03-08 16:55:33  阅读:355  来源: 互联网

标签:responseType val 适配 App LiveData fun JetPack override class


项目简介

电影资讯App是一个纯练手项目,使用了系统API28,全部是基于Androidx包下的。使用Kotlin语言开发,使用了Android JetPack中的LiveData、ViewModel以及Room。为了学习Kotlin和巩固自定义View和ViewGroup,这个项目是尽量少应用依赖第三方库。Api来自豆瓣电影,豆瓣电影Api目前是不公开的,小编是在简书上看到有人公开了访问豆瓣电影的Api的API_KEY,如果有侵犯,请联系删除!

项目截图

截图1 截图2 截图 3 截图 4 截图5
在这里插入图片描述 在这里插入图片描述 在这里插入图片描述 在这里插入图片描述

app主要设计到知识点:

  • Material Design UI设计风格;
  • 使用Kotlin开发,大家想学习和巩固Kotlin,可以参考这个App;
  • Retrofit适配LiveData手写一个LiveDataCallAdapter适配器;
  • RecyclerView支持上拉刷新和下拉加载,并且可以添加不同类型头部和底部的View以及动画;
  • 支持视频播放

看几段代码,访问网络的核心代码,设计到了蛮多的知识点,这是初始化Retrofit

class RetrofitClient {
    companion object {
        val serviceApi: ServiceApi by lazy {
            val retrofitClient = Retrofit.Builder()
                    .baseUrl(BASE_URL)
                    .client(OkHttpClient.Builder()
                            .addInterceptor(HttpLoggingInterceptor(HttpLoggingInterceptor.Logger { message ->
                                Log.i(TAG, message)
                            }).setLevel(HttpLoggingInterceptor.Level.BODY)
                            ).build())
                    .addConverterFactory(GsonConverterFactory.create())
                    .addCallAdapterFactory(LiveDataCallAdapterFactory())
                    .build()
            retrofitClient.create(ServiceApi::class.java)
        }
    }
}

注意这段代码,通过工厂模式添加一个LiveData数据源适配器

  .addCallAdapterFactory(LiveDataCallAdapterFactory())

通过方法工厂返回LiveDataCallAdapter的实例,并且获取泛型的参数类型

class LiveDataCallAdapterFactory : Factory() {
    override fun get(returnType: Type, annotations: Array<Annotation>, retrofit: Retrofit): CallAdapter<*, *>? {
        val responseType: Type

        if (Factory.getRawType(returnType) != LiveData::class.java) {
            throw IllegalStateException("return type must be parameterized")
        }
        val observableType = Factory.getParameterUpperBound(0, returnType as ParameterizedType)
        val rawObservableType = Factory.getRawType(observableType)
        responseType = if (rawObservableType == Response::class.java) {
            if (observableType !is ParameterizedType) {
                throw IllegalArgumentException("Response must be parameterized")
            }
            Factory.getParameterUpperBound(0, observableType)
        } else {
            observableType
        }
        return LiveDataCallAdapter<Any>(responseType)
    }
}

注意adapt()方法中的代码,通过适配器模式将Call转为LiveData

class LiveDataCallAdapter<R>(private val responseType: Type) :
        CallAdapter<R, LiveData<R>> {
​
    override fun responseType() = responseType
​
    override fun adapt(call: Call<R>): LiveData<R> {
        return object : LiveData<R>() {
            private var started = AtomicBoolean(false)
            override fun onActive() {
                super.onActive()
                if (started.compareAndSet(false, true)) {
                    call.enqueue(object : Callback<R> {
                        override fun onResponse(call: Call<R>, response: Response<R>) {
                            postValue(response.body())
                        }
​
                        override fun onFailure(call: Call<R>, throwable: Throwable) {
                            postValue(null)
                        }
                    })
                }
            }
        }
    }
}

大家可能看这些代码会比较懵,我是看了RxJava2中的RxJava2CallAdapterFactory中的代码,以前只是会写,但是点击去看源码,在分析就不一样了。Observable在这相当于LiveData(被观察者)。通过调用retrofitClient.create(ServiceApi::class.java),最终会调用到adapt()方法中。

公众号后台回复:“源码” 关键字获取项目地址。

标签:responseType,val,适配,App,LiveData,fun,JetPack,override,class
来源: https://blog.csdn.net/zhiwenyan/article/details/88353558

本站声明: 1. iCode9 技术分享网(下文简称本站)提供的所有内容,仅供技术学习、探讨和分享;
2. 关于本站的所有留言、评论、转载及引用,纯属内容发起人的个人观点,与本站观点和立场无关;
3. 关于本站的所有言论和文字,纯属内容发起人的个人观点,与本站观点和立场无关;
4. 本站文章均是网友提供,不完全保证技术分享内容的完整性、准确性、时效性、风险性和版权归属;如您发现该文章侵犯了您的权益,可联系我们第一时间进行删除;
5. 本站为非盈利性的个人网站,所有内容不会用来进行牟利,也不会利用任何形式的广告来间接获益,纯粹是为了广大技术爱好者提供技术内容和技术思想的分享性交流网站。

专注分享技术,共同学习,共同进步。侵权联系[81616952@qq.com]

Copyright (C)ICode9.com, All Rights Reserved.

ICode9版权所有