Mvp框架的使用

MVP 使用文檔

導(dǎo)入

將MVP資源包導(dǎo)入
在settings.gradle設(shè)置如下目錄

rootProject.name='Test'
include ':app'
include ': mvplib '
include ' : mvplib:libMvpAnotation:compiler '

在 app build.gradle

 implementation project(path: ':mvplib')
 annotationProcessor project(path: ':mvplib:libMvpAnotation:compiler')

注釋: compileOptions {
        sourceCompatibility JavaVersion.VERSION_1_8
        targetCompatibility JavaVersion.VERSION_1_8
    }
必須使用java8依賴
必須導(dǎo)入version.gradlee

使用

注釋使用

@MvpEntity

使用該注解得到從服務(wù)器beam類(這里要特別注意code值)

@MvpEntity
public  class HttpResult<T> implements IMvpEntity<T> {

    /**
     * 'code': '1',
     * 'message': '成功提示',
     * 'data':
     */
    private int code;

    private String message;

    private  T data;

    public int getCode() {
        return code;
    }

    public void setCode(int code) {
        this.code = code;
    }

    @Override
    public boolean isOk() {
    
    //每個(gè)服務(wù)器返回的code值
    
        return code == 1 && data != null;
    }

    public String getMessage() {
        return message;
    }

    public void setMessage(String message) {
        this.message = message;
    }

    public T getData() {
        return data;
    }

    public void setData(T data) {
        this.data = data;
    }
}

@OkInterceptor(1)

添加自定義ok攔截器

@OkInterceptor(1)//括號(hào)里代表OK連接器的等級(jí)
public class Intercepter1 implements Interceptor {

    @Override
    public Response intercept(Chain chain) throws IOException {
        return chain.proceed(chain.request());
    }
}

@ApiService

自定義ApiService

@ApiService
public interface AppApiService {
    @POST()
    Observable<HttpResult<User>> getUser(@FieldMap HashMap<String, Object> map);
}

@BaseUrl

自定義BaseUrl

public interface Constrant {

    @BaseUrl
    String BASE_URL = "https://www.seetao.com";
    }

設(shè)置請(qǐng)求params

public class MvpApplication extends Application {
    @Override
    public void onCreate() {
        super.onCreate();
        MvpManager.setParamsGetter(ParamsUtils::getCommonParams);
    }
}

自定義解析GsonFactory

@GsonConverter
public class JDGsonConverterFactory extends MvpGsonConverterFactory {

    @Override
    public Converter<ResponseBody, ?> responseBodyConverter(Type type, Annotation[] annotations, Retrofit retrofit) {
        TypeAdapter<?> adapter = gson.getAdapter(TypeToken.get(type));
        return new JDGsonResponseBodyConverter<>(gson, adapter,type);
    }
}
/**
 * 繼承BaseSmartFragment1<>范型返回需要的解析的數(shù)據(jù)
 */
public class JDGsonResponseBodyConverter<T> extends MvpGsonResponseBodyConverter<T> {
    public JDGsonResponseBodyConverter(Gson gson, TypeAdapter<T> adapter, Type type) {
        super(gson, adapter, type);
    }

    @Override
    public String handJson(String json) {
        try {
            JSONObject jsonObject = new JSONObject(json);

            if(!jsonObject.isNull("code")){
                int code = jsonObject.getInt("code");
                if(code != 1){ // 失敗
                    if(!jsonObject.isNull("data")){
                        String data = jsonObject.getString("data");
                        if(TextUtils.isEmpty(data)){ // 如果 data 是一個(gè)空字符串
                            jsonObject.remove("data");
                            return jsonObject.toString();
                        }
                    }
                }
            }
        } catch (Exception e) {
            e.printStackTrace();
        }
        return json;
    }
}

使用

ONE 繼承BaseSmartFragment1

使用在Fragment頁(yè)面

public class VideoFragment extends BaseSmartFragment1<VideoBean> {
    /**
     * 
     * @return
     * 返回該類所在xml布局
     */
    @Override
    protected int getLayoutId() {
        return R.layout.fragment_video;
    }

    /**
     * 
     * @param data
     * 接受成功bean類
     */
    @Override
    public void onResult1(MvpResponse<VideoBean> data) {
        if (data.getCode() == 1) {

            Toast.makeText(getActivity(), data.getData().getList().get(1).getShare_link(), Toast.LENGTH_SHORT).show();

        } else {

            Toast.makeText(getActivity(), data.getMsg(), Toast.LENGTH_SHORT).show();


        }
    }

    /**
     * 1.創(chuàng)建請(qǐng)求對(duì)象如果是
     * 范型中添加得到bean類
     * Get請(qǐng)求創(chuàng)建GetRequest
     * Post請(qǐng)求創(chuàng)建PostRequest
     * 2.如果有參數(shù)調(diào)用
     * request.setParams();設(shè)置參數(shù)
     *3.調(diào)用請(qǐng)求方法
     * doRequest(request);
     */
    @Override
    protected void initView() {
        super.initView();
        GetRequest<VideoBean> request = new GetRequest<>("/app/v_1_6/article/videolist");
        
        doRequest(request);
    }

    /**
     * 
     * @param view
     * 綁定View
     */
    @Override
    protected void bindView(View view) {
        super.bindView(view);
    }

TWO(在p層處理邏輯)

重寫p層
創(chuàng)建契約類
創(chuàng)建Presenter繼承IBasePresenter
創(chuàng)建View繼承IBaseView

public interface ConstrantVideo {
//    創(chuàng)建P層繼承IBasePresenter
    interface IVideoPresenter extends IBasePresenter<IVideoView> {
    //p傳遞數(shù)據(jù)方法
        void getVideoData();
    }
    
// 創(chuàng)建View契約類
    interface IVideoView extends IBaseView<ConstrantVideo.IVideoPresenter> {
        void onSucces(Video video);

        void onFail(String error);

        void onNetError();

        void showLoadLing();

        void closeLoadLing();
    }
}

創(chuàng)建P層
BaseRepository創(chuàng)建model成員變量在P層構(gòu)造方法通過new BaseRepository()得到model實(shí)例
在P層方法中根據(jù)請(qǐng)求Url 創(chuàng)建GetRequest或者PostRequest對(duì)象
如果有參數(shù)設(shè)置請(qǐng)求參數(shù)
通過model對(duì)象調(diào)用mModel.doRequest(request,new IBaseCallBack<T>{})獲得數(shù)據(jù)

public class VideoPresenter extends BasePresenter<ConstrantVideo.IVideoView> implements ConstrantVideo.IVideoPresenter {
    private BaseRepository mModel;
    private CompositeDisposable mCompositeDisposable = new CompositeDisposable();

    public VideoPresenter() {
        mModel = new BaseRepository();
    }
    @Override
    public void getVideoData() {
//    給請(qǐng)求對(duì)象添加參數(shù)
        GetRequest request = new GetRequest("/app/v_1_6/article/videolist");
// 設(shè)置請(qǐng)求參數(shù)
    request.setParams(ParamsUtils.getCommonParams());
        request.setType(Video.class);
//   加載動(dòng)畫
        mView.showLoadLing();

        mModel.doRequest(request, new IBaseCallBack<Video>() {
            //            切斷cut方法
            @Override
            public void onCut(Disposable disposable) {
                mCompositeDisposable.add(disposable);
            }

            //   獲取結(jié)果
            @Override
            public void onResult(MvpResponse<Video> data) {
                if (data.getCode() == 1) {
                    mView.onSucces(data.getData());
                    mView.closeLoadLing();
                } else {
                    mView.onFail(data.getMsg());
                }
   }
        });
    }

    @Override
    public boolean cancelRequest() {
         return true;
    }
}

Fragmenrt
繼承BaseMvpFragment<T extend IBasePresenter>implements具體的View
在成功失敗方法得到數(shù)據(jù)

public class VideoFragmenrt extends BaseMvpFragment<ConstrantVideo.IVideoPresenter> implements ConstrantVideo.IVideoView {
    @Override
    protected int getLayoutView() {

        return R.layout.fragment_video_fragmenrt;
    }

    @Override
    public void onSucces(Video video) {
        toast(video.getList().get(2).getShare_link());
    }

    @Override
    public void onFail(String error) {
        toast(error);
    }

    @Override
    public void onNetError() {
        toast("網(wǎng)絡(luò)錯(cuò)誤");
    }

    @Override
    public void showLoadLing() {
        showPopLoading();
    }

    @Override
    public void closeLoadLing() {
        closeLoading();
    }
 @Override
    public ConstrantVideo.IVideoPresenter creatPresenter() {
        return new VideoPresenter();
    }

    @Override
    protected void initView() {
        mPresenter.getVideoData();
    }
}

Three(在model層做數(shù)據(jù)緩存)

重寫model層

在Fragment
//重寫createPresenter 返回自定義的model 層
 @Override
    public BaseSmartPresenter1<RecommendData, ?> createPresenter() {
        return new BaseSmartPresenter1<>(RecommondRepository.getInstance());
    }

重寫model


public class RecommondRepository extends BaseRepository {
    private static final String CACHE_FILE_NAME_PREFIX = "version_code";
    private static RecommondRepository mInstance;
    private HashMap<String, RecommendData> mMemoryData = new HashMap<>();

    /**
     *
     * @return
     * 單例是的只有一個(gè)model對(duì)象
     */
    public static RecommondRepository getInstance() {
//        判斷對(duì)象是否創(chuàng)建
        if (mInstance == null) {
//            在此處創(chuàng)建線程索讓其他線程減少等待時(shí)間
            synchronized (RecommondRepository.class) {
//                如果線程1拿到鎖對(duì)象未創(chuàng)建完成,線程2拿到鎖創(chuàng)建完對(duì)象線程1繼續(xù)創(chuàng)建此時(shí)對(duì)象已經(jīng)通過線程2實(shí)例化所以進(jìn)行二次判空
                if (mInstance == null) {
//                    創(chuàng)建對(duì)象
                    mInstance = new RecommondRepository();

                }
            }
        }

        return mInstance;
    }

    @Override
    public <T> void doRequest(LifecycleProvider lifecycleProvider, MvpRequest<T> request, IBaseCallBack<T> callBack) {
        /*取數(shù)據(jù)*/
//        不調(diào)用父類的方法,重寫子類
//        super.doRequest(lifecycleProvider, request, callBack);
//        得到欄目ID
        String columnId = request.getParams().get(Constract.RequestKey.KEY_COLUMN_ID).toString();

        switch (request.getRequestType()) {

//            case加入括號(hào){}可以重復(fù)創(chuàng)建變量局部變量只能在方法里有效
/**
 * 默認(rèn)都是第一次請(qǐng)求
 * 刷新和加載更多都不需要讀取緩存數(shù)據(jù)
 */
            case FIRST: {
//                step1.先從內(nèi)從存查找直接傳入P層
                MvpResponse response = getFromMemory(columnId);
                if (response != null) {
                    callBack.onResult(response);
                    return;

                }
//             step2.如果內(nèi)存沒有直接從sdcard讀取


                /*
                 *Observable 內(nèi)置線程池節(jié)省系統(tǒng)開銷
                 * scared都為耗時(shí)操作為 */
                Observable.create(new ObservableOnSubscribe<MvpResponse>() {
                    @Override
                    public void subscribe(@NonNull ObservableEmitter<MvpResponse> emitter) throws Throwable {
                        MvpResponse fromSdCard = getFromSdCard(columnId);
                        if (fromSdCard != null) {
                            emitter.onNext(fromSdCard);
                            emitter.onComplete();
                        } else {
                            emitter.onError(new NullPointerException("sdcard no data"));
                        }
                    }
                })
                        .subscribeOn(Schedulers.io())
                        .observeOn(AndroidSchedulers.mainThread())
                        .subscribe(new Consumer<MvpResponse>() {
                            @Override
                            public void accept(MvpResponse mvpResponse) throws Throwable {
                                callBack.onResult(mvpResponse);
                            }
                        }, new Consumer<Throwable>() {
                            @Override
                            public void accept(Throwable throwable) throws Throwable {
                                doRequest(lifecycleProvider, request, callBack, new CacheTask<>(request));
                            }
                        });

                break;
            }
            default:{
//                從服務(wù)請(qǐng)求

                doRequest(lifecycleProvider,request,callBack,new CacheTask<>(request));
            }
        }

    }
//  讀取內(nèi)存數(shù)據(jù)
    private MvpResponse getFromMemory(String key) {
//        看內(nèi)存是否有該數(shù)據(jù)
        RecommendData data = mMemoryData.get(key);
        if (data != null) {
//            設(shè)置數(shù)據(jù)
            MvpResponse<RecommendData> response = new MvpResponse<>();
            return response.setData(data).setCode(1).setRequestType(RequestType.FIRST).setType(ResponseType.MEMORY);
        }
        return null;
    }

    /**
     * @param key
     * @return 從sd卡讀取文件
     */
    private MvpResponse getFromSdCard(String key) {
//        從內(nèi)存卡讀取數(shù)據(jù)
        RecommendData data = MvpDataFileCacheUtils.getencryptedDataFromFile(getCacheDataSdcardFile(key), RecommendData.class);
        if (data != null) {
            MvpResponse<RecommendData> response = new MvpResponse<>();
            return response.setCode(1).setData(data).setType(ResponseType.SDCARD);
        }
        return null;
    }

    /**
     * @param columnId
     * @return 創(chuàng)建手機(jī)文件
     */
//    找到文件
    private File getCacheDataSdcardFile(String columnId) {
        return new File(MvpManager.getExternalCacheDir(), CACHE_FILE_NAME_PREFIX + columnId);
    }

//  緩存數(shù)據(jù)
    private class CacheTask<T> implements Consumer<MvpResponse<T>> {//實(shí)現(xiàn)做緩存接口

        private MvpRequest request;

        CacheTask(MvpRequest request) {
            this.request = request;
        }

        @SuppressWarnings("ALL")
        @Override
        public void accept(MvpResponse<T> mvpResponse) throws Throwable {
//            得到保存的Key值
            String key = request.getParams().get(Constract.RequestKey.KEY_COLUMN_ID).toString();
            saveToMemory((MvpResponse<RecommendData>) mvpResponse, request.getRequestType(), key);
            saveToSdcard((MvpResponse<RecommendData>) mvpResponse, key);
        }
//         保存到card
        private void saveToSdcard(MvpResponse<RecommendData> mvpResponse, String key) {

        }
//      保存到內(nèi)存
        private void saveToMemory(MvpResponse<RecommendData> mvpResponse, RequestType requestType, String key) {
            if (requestType != RequestType.LOAD_MORE){//不是加載更多
                mMemoryData.clear();//將內(nèi)存設(shè)置空
                RecommendData recommendData = new RecommendData();//創(chuàng)建空對(duì)象開辟內(nèi)存
                RecommendData serverData = mvpResponse.getData();//從網(wǎng)絡(luò)獲取data
//                設(shè)置數(shù)據(jù)
                recommendData.setAlbumId(serverData.getAlbumId());
                recommendData.setAlbumNews(serverData.getAlbumNews());
                recommendData.setAlbumTitle(serverData.getAlbumTitle());
                recommendData.setBannerList(serverData.getBannerList());
                recommendData.setFlashId(serverData.getFlashId());
                recommendData.setFlashNews(serverData.getFlashNews());
                recommendData.setMore(serverData.getMore());
                recommendData.setPointTime(serverData.getPointTime());
                recommendData.setStart(serverData.getStart());
                recommendData.setNews(new ArrayList<>(serverData.getNews()));
//                緩存到集合
                mMemoryData.put(key,recommendData);
            }else {
                RecommendData cacheData = mMemoryData.get(key);//獲取緩存加入數(shù)據(jù)

                RecommendData serverData = mvpResponse.getData();//獲取網(wǎng)絡(luò)數(shù)據(jù)
//                如果網(wǎng)絡(luò)數(shù)據(jù)和緩存數(shù)據(jù)都不為空
                if(cacheData != null && serverData != null){
//                    所有數(shù)據(jù)只有新聞數(shù)據(jù)需要實(shí)施gen新
                    cacheData.setStart(serverData.getStart());
                    cacheData.setNumber(serverData.getNumber());
                    cacheData.setPointTime(serverData.getPointTime());
                    cacheData.setMore(serverData.getMore());
                    cacheData.getNews().addAll(serverData.getNews());
                }
            }
        }
    }
}
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請(qǐng)聯(lián)系作者
【社區(qū)內(nèi)容提示】社區(qū)部分內(nèi)容疑似由AI輔助生成,瀏覽時(shí)請(qǐng)結(jié)合常識(shí)與多方信息審慎甄別。
平臺(tái)聲明:文章內(nèi)容(如有圖片或視頻亦包括在內(nèi))由作者上傳并發(fā)布,文章內(nèi)容僅代表作者本人觀點(diǎn),簡(jiǎn)書系信息發(fā)布平臺(tái),僅提供信息存儲(chǔ)服務(wù)。

友情鏈接更多精彩內(nèi)容