天天看點

Android自定義資料傳輸機制[仿照EventBus]

作者:XINHAO_HAN

大家有時候想在Android當中之間的Activity來回傳遞資料,是不是很費勁,Intent的傳遞确實勇氣來不錯,
           

但問題是隻能一層一層傳遞,

可能你在寫那個過程P(劈)X(叉)了,找起來真的那心疼的要死啊.....

第一種方式:單例模式

原理:單例模式,它可以在Android[APK]當中的任意一個Activity當中取出資料,因為它記憶體中就它一個對象,你是不是很爽啊 0.0
           

例子[單例模式]

package com.jiuhong.redcabinet.utils.eventbus;

/**
 * XINHAO_HAN
 */

public class DLdATA {

    private static DLdATA dLdATA;

    public static DLdATA getInstall() {

        if (dLdATA == null) {
            synchronized (DLdATA.class) {
                if (dLdATA == null) {
                    dLdATA = new DLdATA();
                    return dLdATA;
                } else {
                    return dLdATA;
                }
            }
        } else {
            return dLdATA;
        }

    }

    /**
     * 這塊寫你要傳遞的資料
     */
    
    public String test = "測試";
}

           

這樣你可以在任意一個Activity當中取到資料了

就這樣

/**
     * A Class
     */
    
    
    class A{
        public void test(){
            DLdATA.getInstall().test = "我是要傳遞的資料";
        }
    }
    /**
     * B Class
     */


    class B{
        public void test(){
          //這塊就列印出來了
            System.out.println(DLdATA.getInstall().test);
        }
    }
           

[圖檔上傳中...(無标題.png-e2aa1f-1512715726678-0)]

給大家普及一下單例模式

1.餓漢式

2.懶漢式 [線程安全/不安全/利用靜态代碼塊new]

3.枚舉

4.内部類模式

這些大家都可以上網查查

下面是重點了 //-------------------------------------------------------------------------------------------XHEventBus

仿照EventBus[超級簡單版,總體代碼不超過80行]

//大緻流程和EventBus相差不多

Android自定義資料傳輸機制[仿照EventBus]

無标題.png

//但EventBus有一個缺點,就是當你一個類未注冊,EventBus的Map集合中就沒有你要調用的那個類,是以必須是在你注冊之後發送消息,而不能再注冊之前發送

//這個類的機制,就像離線消息一樣,如果你目前類沒有被注冊,那麼這個消息就暫時儲存到一個緩存Map當中,相當于離線消息

Android自定義資料傳輸機制[仿照EventBus]

無标題.png

這個圖

Android自定義資料傳輸機制[仿照EventBus]

無标題.png

//唉,畫的圖,有點垃圾........

貼代碼:

/**
 * XINHAO_HAN自定義資料傳輸機制
 */

public class XHEventBus {


    //監聽機制 ---這個是正常注冊的存儲
    private static Map<String, InData> objectMap;
    //監聽機制 ---這個是離線消息機制
    private static Map<String, OffLine> offLineMap;

    static {
        objectMap = new HashMap<String, InData>();
        offLineMap = new HashMap<>();
    }


    /**
     * 設定監聽
     */

    public static void setListener(XHDatListener xhDatListener) {
        InData inData = new InData();
        inData.xhDatListener = xhDatListener;
        //多次注冊是無效的,HashMap集合,不能存儲相同[重複]數值
        objectMap.put(inData.xhDatListener.getClass().getName(), inData);
        getOffLineData(xhDatListener);
        LOGE.e("測試效果", "SIZE大小:" + objectMap.size());
    }

    /**
     * 開始取離線消息
     */
    public static void getOffLineData(XHDatListener xhDatListener) {

        if (offLineMap.size() == 0)
            return;


        OffLine offLine = offLineMap.get(xhDatListener.getClass().getName());
        if (offLine == null)
            return;
        xhDatListener.dataComplete(offLine.dataCompleteMessage);
        LOGE.e("測試效果", "離線消息" + offLine.dataCompleteMessage.getObject());
        /**
         * 處理完成,移除該消息
         */
        offLineMap.remove(offLine.aClass.getName());

        LOGE.e("測試效果", "離線消息已移除:" + offLineMap.size());


    }

    /**
     * 移除監聽
     */
    public static void romeListener(Object o) {
        objectMap.remove(o.getClass().getName());

    }


    /**
     * 發送資料,如果該類消息已被注冊,就直接發送該類的消息,如果該類沒有被注冊,那麼就存到離線消息庫,等有該類資訊被注冊的時候就開始調用
     */

    public static void sendData(DataCompleteMessage dataCompleteMessage, Class clazz) {

        for (String key : objectMap.keySet()) {


            if (TextUtils.equals(key, clazz.getName())) { //如果集合當中有,就表示該類已經被注冊過了,直接發送消息即可


                objectMap.get(key).xhDatListener.dataComplete(dataCompleteMessage);


            } else { //如果集合當中沒有,那麼就代表要發送的那個消息類沒有被注冊,是以該消息被儲存到離線消息庫中如果有就調用

                //這塊可能會多次添加,但由于HashMap的特點,不會添加重複數值
                saveOffLineMessage(dataCompleteMessage, clazz);
            }
        }

        //如果集合為0,上邊的for可能不會走
        if (objectMap.size() == 0) {
            saveOffLineMessage(dataCompleteMessage, clazz);
        }

    }

    /**
     * 開始[存]離線消息當中的資料
     */

    private static void saveOffLineMessage(DataCompleteMessage dataCompleteMessage, Class clazz) {


        OffLine offLine = new OffLine();
        offLine.dataCompleteMessage = dataCompleteMessage;
        offLine.inData = new InData();
        offLine.aClass = clazz;

        offLineMap.put(clazz.getName(), offLine);
        LOGE.e("測試效果", "SIZE[離線]大小:" + offLineMap.size());
    }

    private static class OffLine {
        public DataCompleteMessage dataCompleteMessage;
        public InData inData;
        public Class aClass;
    }
}


//可能有其他的類包含


public class DataCompleteMessage {

    private Object object;

    public Object getObject() {
        return object;
    }

    public void setObject(Object object) {
        this.object = object;
    }
}


public interface XHDatListener {

    void dataComplete(DataCompleteMessage dataCompleteMessage);
}

           

//這塊是根據接口自定義的,如果有興趣的老鐵,你可以用反射機制來做的更強大一點

---------------------------------------END--------------------------------------