• android开发学习 ------- Retrofit+Rxjava+MVP网络请求的实例


    http://www.jianshu.com/p/7b839b7c5884   推荐 ,照着这个敲完 , 测试成功 , 推荐大家都去看一下 。 

    下面贴一下我照着这个敲完的代码:

    Book实体类 - 用于封装网络请求返回的数据; 这个借助GsonFormat 插件,注意若实体类有实体,一定要手动实现toString();

    public interface RetrofitService {
        /**
         //拼接一个URL然后进行网络请求
         //这里我们拼接的URL就是 完整URL:https://api.douban.com/v2/book/search?q=xxx&tag=&start=0&count=1;
         //每个URL前面都是以http://www.jianshu.com/开头,我们把这个不变的部分,也叫做baseUrl提出来,放到另一个地方,在下面我们会提到
         */
    
        //将返回值call改为observable
        @GET("book/search")
        Observable<Book> getSearchBook(@Query("q") String name,
                                       @Query("tag") String tag,
                                       @Query("start") int start,
                                       @Query("count") int count
                                 );
    
    /**
     * 在每个入参前还多了一个注解。比如第一个入参@Query("q") String name,Query表示把你传入的字段拼接起来
     * 这个url需要几个入参你就在这个方法中定义几个入参,每个入参前都要加上Query注解
     *
     * @GET("book/search")
       Call<Book> getSearchBook(@Query("q") String name);//name由调用者传入
       @GET("book/search?q=name")
       Call<Book> getSearchBook();
      **********************************************************
       如果入参比较多,就可以把它们都放在Map中
       @GET("book/search")
       Call<Book> getSearchBook(@QueryMap Map<String, String> options);
       ***********************************************************
       用于替换url中某个字段
     @GET("group/{id}/users")
     Call<Book> groupList(@Path("id") int groupId);
     *******************************************************
     指定一个对象作为HTTP请求体
     @POST("users/new")
     Call<User> createUser(@Body User user);
     它会把我们传入的User实体类转换为用于传输的HTTP请求体,进行网络请求
     **********************************************************
     传送表单数据
     @FormUrlEncoded
     @POST("user/edit")
     Call<User> updateUser(@Field("first_name") String first, @Field("last_name") String last);
     */
    }
    /**
     * Created by lemon on 2017/11/20.
     * 主要用于Retrofit的初始化:
     */
    
    public class RetrofitHelper {
        private Context mCntext;
        OkHttpClient client = new OkHttpClient();
        GsonConverterFactory factory = GsonConverterFactory.create(new GsonBuilder().create());
        private static RetrofitHelper instance = null;
        private Retrofit mRetrofit = null;
    
        //静态方法getInstance用于获取自身RetrofitHelper的实例化,并且只会实例化一次。
        public static RetrofitHelper getInstance(Context context){
            if (instance == null){
                instance = new RetrofitHelper(context);
            }
            return instance;
        }
        private RetrofitHelper(Context mContext){
            mCntext = mContext;
            init();
        }
    
        private void init() {
            resetApp();
        }
    
        private void resetApp() {
            mRetrofit = new Retrofit.Builder()
                    .baseUrl("https://api.douban.com/v2/")
                    .client(client)
                    // 因为接口返回的数据不是我们需要的实体类,我们需要调用addConverterFactory方法进行转换。
                    // 由于返回的数据为json类型,所以在这个方法中传入Gson转换工厂
                    .addConverterFactory(factory)
                    //支持RXJava
                    .addCallAdapterFactory(RxJavaCallAdapterFactory.create())
                    .build();
        }
    
        //创建RetrofitService的实体类
        //getServer方法就是为了获取RetrofitService接口类的实例化。
        public RetrofitService getServer(){
            return mRetrofit.create(RetrofitService.class);
        }
    
    }
    /**
     * Created by lemon on 2017/11/20.
     * 这个是和其他层直接调用的接口
     * 让你更方便的调用RetrofitService 中定义的方法:
     */
    
    public class DataManager {
    
        private RetrofitService mRetrofitService;
    
        // 在它的构造方法中,我们得到了RetrofitService 的实例化
        // 这样,把RetrofitService 中定义的方法都封装到DataManager 中,
        // 以后无论在哪个要调用方法时直接在DataManager 中调用就可以了,
        // 而不是重复建立RetrofitService 的实例化,再调用其中的方法。
        public DataManager(Context context){
            this.mRetrofitService = RetrofitHelper.getInstance(context).getServer();
        }
    
        public Observable<Book> getSearchBooks(String name, String tag, int start, int count){
            return mRetrofitService.getSearchBook(name,tag,start,count);
        }
    }
    /**
     * Created by lemon on 2017/11/20.
     * presenter主要用于网络的请求以及数据的获取,view就是将presenter获取到的数据进行展示。
     */
    
    public interface Presenter {
        void onCreate();
    
        void onStart();//暂时没用到
    
        void onStop();
    
        void pause();//暂时没用到
    
        /*
        用于绑定我们定义的View.也就是,你想把请求下来的数据实体类给哪个View就传入哪个View
         */
        void attachView(BookView view);
    
        void attachIncomingIntent(Intent intent);//暂时没用到
    
    
    }
    public class BookPresenter implements Presenter {
    
        private DataManager manager;
        private CompositeSubscription mCompositeSubscription;
        private Context mContext;
        private BookView mBookView;
        private Book mBook;
    
    
        public BookPresenter (Context mContext){
            this.mContext = mContext;
        }
    
        @Override
        public void onCreate() {
            manager = new DataManager(mContext);
            /**
             * CompositeSubscription是用来存放RxJava中的订阅关系的。
             * 注意请求完数据要及时清掉这个订阅关系,不然会发生内存泄漏。
             * 可在onStop中通过调用CompositeSubscription的unsubscribe方法来取消这个订阅关系,
             * 不过一旦调用这个方法,那么这个CompositeSubscription也就无法再用了,要想再用只能重新new一个。
             */
            mCompositeSubscription = new CompositeSubscription();
        }
    
        @Override
        public void onStart() {
    
        }
    
        @Override
        public void onStop() {
            if (mCompositeSubscription.hasSubscriptions()){
                mCompositeSubscription.unsubscribe();
            }
        }
    
        @Override
        public void pause() {
    
        }
    
        //想把请求下来的数据实体类给哪个View就传入哪个View
        //在attachView中,我们把BookView传进去。也就是说我们要把请求下来的实体类交给BookView来处理。
        @Override
        public void attachView(BookView view) {
            mBookView = view;
        }
    
        @Override
        public void attachIncomingIntent(Intent intent) {
    
        }
    
        /**
         * 名字和入参都和请求接口RetrofitService中的方法相同。这个方法也就是请求的具体实现过程。
         */
        public void getSearchBook(String name,String tag,int start,int count){
            mCompositeSubscription.add(manager.getSearchBooks(name, tag, start, count)
                    .subscribeOn(Schedulers.io())  //请求数据的事件发生在IO线程
                    .observeOn(AndroidSchedulers.mainThread())  //请求完成后在主线程更新UI
                    .subscribe(new Observer<Book>() {
                        @Override
                        public void onCompleted() {
                            //所有的事件都完成,可做这些操作
                            if(mBook != null){
                                mBookView.onSuccess(mBook);
                            }
                        }
    
                        @Override
                        public void onError(Throwable throwable) {
                            //请求过程中发生错误
                            throwable.printStackTrace();
                            mBookView.onError("请求失败!!");
                        }
    
                        @Override
                        public void onNext(Book book) {
                            //这里的BOOK就是我们请求接口返回的实体类
                            mBook = book;
                        }
                    })
            );
        }
    }
    /**
     * Created by lemon on 2017/11/20.
     * View是空的,主要用于和Android中的View区别开来
     */
    
    public interface View {
    }
    public interface BookView extends View {
        /**
         * 如果presenter请求成功,将向该方法传入请求下来的实体类,
         * 也就是Book,view拿到这个数据实体类后,就可以进行关于这个数据的展示或其他的一些操作
         * @param mBook
         */
        void onSuccess(Book mBook);
    
        /**
         * 如果请求失败,就会向这个view传入失败信息,你可以弹个Toast来提示请求失败
         * @param result
         */
        void onError(String result);
    }
    public class BookActivity extends AppCompatActivity {
    
        private TextView text ;
        private Button btn ;
        private BookPresenter mBookPresenter = new BookPresenter(this);
    
        @Override
        protected void onCreate(@Nullable Bundle savedInstanceState) {
            super.onCreate(savedInstanceState);
            setContentView(R.layout.activity_message);
            text = (TextView) findViewById(R.id.text);
            btn = (Button) findViewById(R.id.button);
            btn.setOnClickListener(new View.OnClickListener() {
                @Override
                public void onClick(View view) {
                    mBookPresenter.getSearchBook("xxx",null,0,1);
                }
            });
            mBookPresenter.onCreate();
            mBookPresenter.attachView(mBookView);
        }
    
    
        private BookView mBookView = new BookView() {
            @Override
            public void onSuccess(Book mBook) {
                Log.e("log","mbook"+mBook.toString());
                text.setText(mBook.toString());
            }
    
            @Override
            public void onError(String result) {
                Toast.makeText(BookActivity.this,result, Toast.LENGTH_SHORT).show();
            }
        };
    
    
        @Override
        protected void onDestroy() {
            super.onDestroy();
            mBookPresenter.onStop();
        }
    }
  • 相关阅读:
    软工网络15团队作业4——Alpha阶段敏捷冲刺之Scrum 冲刺博客(Day4)
    软工网络15团队作业4——Alpha阶段敏捷冲刺之Scrum 冲刺博客(Day3)
    201521123066 《Java程序设计》第十二周实验总结
    201521123066 《Java程序设计》第十一周学习总结
    201521123066 《Java程序设计》第十周学习总结
    201521123066 《Java程序设计》第九周学习总结
    201521123066《Java程序设计》第八周学习总结
    201521123066《Java程序设计》第七周学习总结
    201521123066 《Java程序设计》 第六周学习总结
    201521123066《Java程序设计》第五周学习总结
  • 原文地址:https://www.cnblogs.com/mengxiao/p/8027817.html
Copyright © 2020-2023  润新知