<?xml version="1.0" encoding="utf-8" ?><rss version="2.0"><channel><title><![CDATA[legendmohe的技术积累]]></title><description><![CDATA[技术积累]]></description><link>https://blog.youkuaiyun.com/legendmohe</link><language>zh-cn</language><generator>https://blog.youkuaiyun.com/</generator><copyright><![CDATA[Copyright &copy; legendmohe]]></copyright><item><title><![CDATA[[Android] Preloader 预加载框架]]></title><link>https://blog.youkuaiyun.com/legendmohe/article/details/79805642</link><guid>https://blog.youkuaiyun.com/legendmohe/article/details/79805642</guid><author>legendmohe</author><pubDate>Tue, 03 Apr 2018 16:44:39 +0800</pubDate><description><![CDATA[简介

Preloader是一个用于异步加载数据的工具。它提供同步或者异步的获取结果回调。
适当地使用可让业务层获取数据的时间点提前。

使用例子

以简单activity跳转的例子为例，从MainActivity跳转到SubActivity。其中SubActivity的完整
显示需要发起一次请求，获取到结果后显示在中央的textView。

利用Preloader，我们可以在MainActivi]]></description><category></category></item><item><title><![CDATA[[Android] 列表预加载工具类DataPreloader]]></title><link>https://blog.youkuaiyun.com/legendmohe/article/details/79747081</link><guid>https://blog.youkuaiyun.com/legendmohe/article/details/79747081</guid><author>legendmohe</author><pubDate>Thu, 29 Mar 2018 18:28:21 +0800</pubDate><description><![CDATA[DataPreloader用于实现列表数据预加载需求。注意这里的预加载是指预加载数据项的详细信息（例如预拉取视频列表里面某些视频的播放地址等），不是指预先拉取更多的列表项。

概念说明


加载窗口preload window:即需要发起预加载的项目的index区间
焦点:即当前外围逻辑所关心的中心点的index，决定了区间的中心


该工具类引入加载窗口的概念（由upperPosition和Lo]]></description><category></category></item><item><title><![CDATA[[Android] 如何计算View的Size]]></title><link>https://blog.youkuaiyun.com/legendmohe/article/details/79215713</link><guid>https://blog.youkuaiyun.com/legendmohe/article/details/79215713</guid><author>legendmohe</author><pubDate>Wed, 31 Jan 2018 12:27:11 +0800</pubDate><description><![CDATA[** 注：本文参考链接How Android caculates view size

本文例子如下所示:

<LinearLayout
    android:orientation="vertical"
    android:layout_width="match_parent"
    android:layout_height="wrap_content" >

    <TextVie]]></description><category></category></item><item><title><![CDATA[[Android] 一种优化view inflate耗时的方法]]></title><link>https://blog.youkuaiyun.com/legendmohe/article/details/78814971</link><guid>https://blog.youkuaiyun.com/legendmohe/article/details/78814971</guid><author>legendmohe</author><pubDate>Fri, 15 Dec 2017 17:06:10 +0800</pubDate><description><![CDATA[做项目的过程中，发现一种一种优化view inflate耗时的方法，思路是预先将view inflate出来备用，用的时候直接取出来，同时再生成下一个（要考虑屏幕方向）。代码如下所示：



用法大概如下所述：
1. 在适当的地方调用push方法。
2. 在使用view的时候，使用类似如下的代码：

    View view = ViewCache.getInstance().popAndAqu]]></description><category></category></item><item><title><![CDATA[[Android] 解决因键盘和表情panel显示/隐藏引起的闪屏]]></title><link>https://blog.youkuaiyun.com/legendmohe/article/details/78750932</link><guid>https://blog.youkuaiyun.com/legendmohe/article/details/78750932</guid><author>legendmohe</author><pubDate>Fri, 08 Dec 2017 13:59:50 +0800</pubDate><description><![CDATA[在实现一些IM页面，例如对话框，评论框时，常常会遇到键盘和表情panel显示/隐藏引起的闪屏问题。问题的根本原因是当键盘收起或弹出时，layout会发生变化，此时panel的高度的计算如果时机不对，那么会导致闪屏。

解决的办法有很多，这里提供一种重写onMeasure方法的实现：

使用方法：

    mEditText = (EditText) findViewById(R.id.editT]]></description><category></category></item><item><title><![CDATA[[Java] 异步case单元测试工具]]></title><link>https://blog.youkuaiyun.com/legendmohe/article/details/77091791</link><guid>https://blog.youkuaiyun.com/legendmohe/article/details/77091791</guid><author>legendmohe</author><pubDate>Fri, 11 Aug 2017 10:37:10 +0800</pubDate><description><![CDATA[有时候，需要对一些异步方法进行单元测试（尽管不推荐这样做），传统的assert只能在调用线程抛出AssertException，而测试框架往往只能监测主线程上的AssertException（JUnit），所以需要在主线程上等待异步调用结束，再去assert结果。

利用Java8的CompletableFuture，我们可以很方便地做到这一点，代码如下所示：

public class Asyn]]></description><category></category></item><item><title><![CDATA[[Gradle] 如何在android项目中对纯Java module使用release/debug build并启用proguard]]></title><link>https://blog.youkuaiyun.com/legendmohe/article/details/75604786</link><guid>https://blog.youkuaiyun.com/legendmohe/article/details/75604786</guid><author>legendmohe</author><pubDate>Fri, 21 Jul 2017 09:58:25 +0800</pubDate><description><![CDATA[如何在android项目中对纯Java module使用release/debug build并启用proguard？这里提供一种方法，
尽管不是很“好看”，但是可用。

假设app模块依赖lib模块，lib模块是一个纯Java模块（apply plugin: 'java'）。整个过程可以分成两步。

引入Proguard

在lib模块的build.gradle里添加以下代码

import p]]></description><category></category></item><item><title><![CDATA[[Java]Java Socket选项解析]]></title><link>https://blog.youkuaiyun.com/legendmohe/article/details/75127035</link><guid>https://blog.youkuaiyun.com/legendmohe/article/details/75127035</guid><author>legendmohe</author><pubDate>Fri, 14 Jul 2017 17:53:39 +0800</pubDate><description><![CDATA[Java里，Socket的Option由java.net.SocketOptions这个接口声明，如下所示：

@Native public final static int TCP_NODELAY = 0x0001;
@Native public final static int SO_BINDADDR = 0x000F;
@Native public final static int SO_R]]></description><category></category></item><item><title><![CDATA[[Java] 一个不依赖Android环境的Handler]]></title><link>https://blog.youkuaiyun.com/legendmohe/article/details/75008594</link><guid>https://blog.youkuaiyun.com/legendmohe/article/details/75008594</guid><author>legendmohe</author><pubDate>Wed, 12 Jul 2017 12:59:11 +0800</pubDate><description><![CDATA[最近项目中遇到将android project转成java project的需求，要把项目中android相关的部分去掉。其中最纠结的就是如何替换handler。
handler多用于指定线程（Looper）上执行回调，还可以当成一个消息队列使用。通过sendMessageDelayed可以做到事件的延时执行、条件执行和去抖（debouncing）。
于是，我利用Java里面的ScheduledE]]></description><category></category></item><item><title><![CDATA[[vscode] markdown_index----可以为你的markdown标题添加序号的插件]]></title><link>https://blog.youkuaiyun.com/legendmohe/article/details/74644576</link><guid>https://blog.youkuaiyun.com/legendmohe/article/details/74644576</guid><author>legendmohe</author><pubDate>Fri, 07 Jul 2017 11:55:12 +0800</pubDate><description><![CDATA[markdown_index

markdown_index是一个可以为你的markdown标题添加序号的插件。

假设原文如下所示：

# a
foolbar

## a-b
foolbar

## a-c
foolbar
foolbar

### a-c-d
foolbar

## a-e
foolbar

# f
foolbar


安装markdown_index，运行 > markdow]]></description><category></category></item><item><title><![CDATA[[Android] 如何在 Activity 或者 Fragment 的生命周期结束时停止订阅 Observable]]></title><link>https://blog.youkuaiyun.com/legendmohe/article/details/54694520</link><guid>https://blog.youkuaiyun.com/legendmohe/article/details/54694520</guid><author>legendmohe</author><pubDate>Mon, 23 Jan 2017 16:45:41 +0800</pubDate><description><![CDATA[NavUtil

利用 NavUtil，你可以在 Activity 或 Fragment 的生命周期发生变化时，停止订阅你的 Observable。

Usage

首先，需要初始化 NavUtil 单例

public class App extends Application {
    @Override
    public void onCreate() {
        super.]]></description><category></category></item><item><title><![CDATA[[Android] PermissionUtil]]></title><link>https://blog.youkuaiyun.com/legendmohe/article/details/53994639</link><guid>https://blog.youkuaiyun.com/legendmohe/article/details/53994639</guid><author>legendmohe</author><pubDate>Tue, 03 Jan 2017 15:07:47 +0800</pubDate><description><![CDATA[Usage

PermissionUtil.with(this) // Activity or Fragment
    .addPermission(Manifest.permission.CAMERA)
    .setCallback(new PermissionUtil.Callback() {
        @Override
        public void onPermiss]]></description><category></category></item><item><title><![CDATA[[Android] PacketParser 二进制协议转换工具]]></title><link>https://blog.youkuaiyun.com/legendmohe/article/details/52330664</link><guid>https://blog.youkuaiyun.com/legendmohe/article/details/52330664</guid><author>legendmohe</author><pubDate>Fri, 26 Aug 2016 17:58:45 +0800</pubDate><description><![CDATA[这个工具通过自动生成解析类，实现了字节数组和对象之间的转换。

使用@ParsePacket注解标注实体类:

@ParsePacket(
        "header:1|cmd:2|len:2|seq:2|mac:6|data:this.len-6|check:1|tail:1"
)
public class TargetObject {
    public byte header;
  ]]></description><category></category></item><item><title><![CDATA[[Android] Dagger2 入门 2]]></title><link>https://blog.youkuaiyun.com/legendmohe/article/details/52274421</link><guid>https://blog.youkuaiyun.com/legendmohe/article/details/52274421</guid><author>legendmohe</author><pubDate>Mon, 22 Aug 2016 10:15:40 +0800</pubDate><description><![CDATA[上一篇文章介绍了Dagger2的基本用法，这篇文章主要说一下Dagger2中@Scope和@Subcomponent这两个注解的用法和原理。

@Singleton

上一篇文章中提到：


  如上面例子所示，如果要求D对象为单例，可以通过@Singleton注解来实现。首先我们需要在依赖图中声明对象是单例的：
  
      @Module
      public class DModul]]></description><category></category></item><item><title><![CDATA[[Android] Dagger2 入门 1]]></title><link>https://blog.youkuaiyun.com/legendmohe/article/details/52262441</link><guid>https://blog.youkuaiyun.com/legendmohe/article/details/52262441</guid><author>legendmohe</author><pubDate>Sat, 20 Aug 2016 17:16:48 +0800</pubDate><description><![CDATA[这篇文章主要谈一下本人在学习Dagger2的心得，如有错漏，敬请谅解。

什么是依赖注入

依赖注入就是把下面这样的代码：

class A {

    public A() {
    }

}

class B {

    A a;

    public B() {
        a = new A();
    }
}

class C {

    A a;
    B b;

 ]]></description><category></category></item><item><title><![CDATA[[Android] TopSheetBehavior]]></title><link>https://blog.youkuaiyun.com/legendmohe/article/details/51761307</link><guid>https://blog.youkuaiyun.com/legendmohe/article/details/51761307</guid><author>legendmohe</author><pubDate>Sun, 26 Jun 2016 08:02:37 +0800</pubDate><description><![CDATA[将BottomSheetBehavior修改成从上方拉出的TopSheetBehavior，使用方法和BottomSheetBehavior一模一样，代码如下：



未经严格测试，请谅解。查看原文：http://legendmohe.net/2016/06/26/android-topsheetbehavior/]]></description><category></category></item><item><title><![CDATA[[Android] RippleDrawable]]></title><link>https://blog.youkuaiyun.com/legendmohe/article/details/51647325</link><guid>https://blog.youkuaiyun.com/legendmohe/article/details/51647325</guid><author>legendmohe</author><pubDate>Sun, 12 Jun 2016 16:39:40 +0800</pubDate><description><![CDATA[Ripple Effect的例子Github很多，这里我自做轮子，也实现了一个，效果如下所示：

项目地址：
https://github.com/legendmohe/RippleDrawable
查看原文：http://legendmohe.net/2016/06/12/android-rippledrawable/]]></description><category></category></item><item><title><![CDATA[[Android] CircleView 仿小米空气净化器首页旋转UI]]></title><link>https://blog.youkuaiyun.com/legendmohe/article/details/51480857</link><guid>https://blog.youkuaiyun.com/legendmohe/article/details/51480857</guid><author>legendmohe</author><pubDate>Mon, 23 May 2016 13:02:53 +0800</pubDate><description><![CDATA[CircleViewDemo
效果图如下：

模仿并实现了小米空气净化器的主页旋转UI，动画效果比小米的流畅。
查看原文：http://legendmohe.net/2016/05/23/android-circleview-%e4%bb%bf%e5%b0%8f%e7%b1%b3%e7%a9%ba%e6%b0%94%e5%87%80%e5%8c%96%e5%99%a8%e9%a6%96%e9%a1]]></description><category></category></item><item><title><![CDATA[[Android] SlidingDrawableTabLayout]]></title><link>https://blog.youkuaiyun.com/legendmohe/article/details/51460131</link><guid>https://blog.youkuaiyun.com/legendmohe/article/details/51460131</guid><author>legendmohe</author><pubDate>Fri, 20 May 2016 11:07:47 +0800</pubDate><description><![CDATA[TabLayout with drawable indicator

Usage
gradle
compile 'com.legendmohe.maven:slidingdrawabletablayout:0.1'

code
Just use it as TabLayout:
// Create the adapter that will return a fragment for each o]]></description><category></category></item><item><title><![CDATA[[Android] IntentInjector]]></title><link>https://blog.youkuaiyun.com/legendmohe/article/details/51436310</link><guid>https://blog.youkuaiyun.com/legendmohe/article/details/51436310</guid><author>legendmohe</author><pubDate>Tue, 17 May 2016 15:15:25 +0800</pubDate><description><![CDATA[做app的时候，经常遇到这样的需求：将数据放置在Intent中，再通过startActivity方法传给下一个Activity。常用写法如下所示：
Intent intent = new Intent(this, StickyTabActivity.class);
intent.putExtra("string", "sdsd");
intent.putExtra("int", 101);
int]]></description><category></category></item></channel></rss>