Android项目总结(一)

写在前面的话

我发现我生命里所崇拜的都是那些热血的人们,虽然我不是一个冷血的人,但我的血液是温的,我总是喜欢看见那些热血的人们,我希望我成为他们中的一个。我总是发现,当我在发呆的时候,他们已经在思考了,当我在思考的时候,他们已经行动了,当我行动的时候,他们已经翘了,然后我又不敢行动了。翘了的他们就成为我生命里至高的仰望。我天生佩服他们,希望他们身上的血能够温热我的身体。 from 1988 (侵删)

“他做每一件小事儿的时候都像救命稻草一样的抓着,有一天我看他,他抱着的是已经让我仰望的参天大树了,信念这个玩意儿,不是说出来的,是做出来的” (要不是小目标的话 估计这周总结又懒得写了。 惭愧脸 ==|)

Android项目总结(一)_第1张图片

关于文字大小用sp 还是 dp

大家都知道Android里面textview 里面文字大小 google官方推荐的是sp,但是Android碎片化比较严重 这就涉及到屏幕适配问题.(目前关于屏幕适配 个人认为 理想化的解决方案是百分比布局 百度的大神鸿洋出了一个适配布局的依赖库 以及常见的 关于xhdpi xxhdpi等适配) 后来大家定的默契原则是 文字大小 大于15sp的 用dp表示。上周偶然看到一篇文章 关于微信 以及一些比较大的app 他们的textview 文字大小依旧用的是sp 表示。不过他们在Application强制这样处理的:

/**

  • 强制 sp 字体不随系统改变而改变
  • @param newConfig
    */
    @Override
    public void onConfigurationChanged(Configuration newConfig) {
    if(newConfig.fontScale !=1 ){
    getResources();
    }
    super.onConfigurationChanged(newConfig);
    }

@Override
public Resources getResources() {
Resources res = super.getResources();
if(res.getConfiguration().fontScale != 1){
Configuration newConfig = new Configuration();
newConfig.setToDefaults();
res.updateConfiguration(newConfig, res.getDisplayMetrics());//默认
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.JELLY_BEAN_MR1) {
createConfigurationContext(newConfig);
} else {
res.updateConfiguration(newConfig, res.getDisplayMetrics());
}
}
return res;
}

关于BuildConfig.DEBUG LogUtil

平时大家在懒debug的时候 打log是最直接最有效的查看代码的方式。而好习惯的code哥都会建一个LogUtil类在Application里面判断是否BuildConfig.DEBUG debug状态才显示。
这里介绍JakeWharton大神的一款debug工具hugo能够准确的打印生命周期。集成:

app build:

apply plugin: 'com.android.application'
apply plugin: 'com.jakewharton.hugo'


项目name build:

mavenCentral()
classpath 'com.jakewharton.hugo:hugo-plugin:1.2.1'

使用方法很简单:@DebugLog 到你想要看的类或者方法上面。见 ONE HomeActivity

Bugly已经支持热修复和热更新

最初是想集成Bugly是项目体积太大了(当然网上缩小apk体积的方法有很多。常见的无非是只保留xhdpi目录下的图片。能用xml布局代替的 用xml布局代替。但是项目中本来就只保留xhdpi的一套图片 这样就无图可删。所以从代码和依赖入手 但是项目是接手别人的 不太敢删除一些东西怕出现其他问题。所以想在引入其他冲突的情况下还能够缩小体积) 朋友说他集成了bugly体积缩小了好几M。(估计是好多无用代码) 后来看到Bugly支持了热更新和热修复。不管怎么样 大家都在用了解一下也是有必要的。这里不做太多说明 官网非常详细。 吐槽:bug catch非常好 甚至还提供了解决方式。厉害了== 关于热更新和热修复 ONE后面会使用到。

Retrofit缓存问题

网上有好多重复的类似文章 按照他们的方式 但是感觉好像都没有解决缓存的问题。场景 有网络的时候 从网络获取数据计时更新 断网状态从缓存读取数据。常见的解决方式有一下几种:

  1. RxCache缓存Db数据库的形式。这种感觉有点麻烦。
  2. 针对不同接口Okhttp 新建Cache类 Retrofit 添加header的形式。需要的地方每次都要写一遍 感觉好累啊
  3. 最后一种 Retrofit单例入口中 Okhttp 添加拦截器处理request和response。ONE中采用这种。详见 RetrofitApiAdapter.java

Retrofit retrofit = new Retrofit.Builder()
.client(new OkHttpClient().newBuilder().cache(new Cache(fileP, ConstantApi.maxStale))
.addInterceptor(new HttpLoggingInterceptor().setLevel(BuildConfig.DEBUG ? HEADERS:NONE))
.addInterceptor(chain -> {
Request request = chain.request();
if(!HttpUtil.isNetworkAvailable(App.getContext())){
request = request.newBuilder()
.cacheControl(CacheControl.FORCE_CACHE)
.build();
Log.d("RetrofitApiAdapter", "request: no network");
}else{
Log.d("RetrofitApiAdapter", "request: else");
request = request.newBuilder()
.cacheControl(CacheControl.FORCE_NETWORK)
.build();
}
Response response = chain.proceed(request);
if(HttpUtil.isNetworkAvailable(App.getContext())){
Log.d("RetrofitApiAdapter", "response: isNetworkAvailable");
int maxAge = 0 * 60;
response.newBuilder()
.header(CACHE_CONTROL,"public,max-age"+maxAge)
.removeHeader(PRAGMA)
.build();
}else{
Log.d("RetrofitApiAdapter", "response: else");
int maxStale = 60 * 60 * 24;//网络断开 缓存一天
response.newBuilder()
.header(CACHE_CONTROL,"public,only-if-cached,max-stale="+maxStale)
.removeHeader(PRAGMA)
.build();
}
return response;
})
.addNetworkInterceptor(chain -> {// 处理 缓存丢失 504问题
Response response = chain.proceed(chain.request());
String header = response.header(CACHE_CONTROL);
if (header == null || header.contains("no-store") || header.contains("no-cache") ||
header.contains("must-revalidate") || header.contains("max-age=0")) {
return response.newBuilder()
.removeHeader(PRAGMA)
.header(CACHE_CONTROL, "public, max-age=" + 5000)
.build();
} else {
return response;
}
})
.retryOnConnectionFailure(true)
.build())
.baseUrl(baseUrl)
.addConverterFactory(ScalarsConverterFactory.create())//字符串
.addConverterFactory(GsonConverterFactory.create(new Gson()))//gson
.addCallAdapterFactory(RxJavaCallAdapterFactory.create())//其他
//.addCallAdapterFactory(new ErrorHandlingExecutorCallAdapterFactory(new ErrorHandlingExecutorCallAdapterFactory.MainThreadExecutor()))
.build();

项目中使用了useragent的 注意.header()添加上即可。

关于MVP Dagger2+Retrofit+RxJava 详见ONE关于RxJava的详细使用学习总结 后面会做笔录提醒自己。

关于我 1831808374
QQ群 521039620
欢迎学习和交流。
[原文](https://yizuochengchi.github.io/2017/05/21/android%E9%A1%B9%E7%9B%AE%E6%80%BB%E7%BB%93(%E4%B8%80%EF%BC%89/#more)

你可能感兴趣的:(Android项目总结(一))