Quantcast
Channel: CSDN博客移动开发推荐文章
Viewing all articles
Browse latest Browse all 5930

Android----Rxjava与Retrofit初体验

$
0
0

RxJava(响应式编程)

RxJava 在 GitHub 主页上的自我介绍是 “a library for composing asynchronous and event-based programs using observable sequences for the Java VM”(一个在 Java VM 上使用可观测的序列来组成异步的、基于事件的程序的库)。这就是 RxJava ,概括得非常精准。

Retrofit

Retrofit与okhttp共同出自于Square公司,retrofit就是对okhttp做了一层封装。把网络请求都交给给了Okhttp,我们只需要通过简单的配置就能使用retrofit来进行网络请求了,其主要作者是Android大神JakeWharton

下面是相关学习文档

RxJava:http://gank.io/post/560e15be2dca930e00da1083
Retrofit:https://square.github.io/retrofit/

1.在buil.gradle添加依赖

    compile 'io.reactivex:rxandroid:1.2.1'
    compile 'io.reactivex:rxjava:1.2.1'
    compile 'com.squareup.retrofit2:retrofit:2.1.0'
    compile 'com.squareup.retrofit2:converter-scalars:2.1.0'

2.需要添加网络权限

<uses-permission android:name="android.permission.INTERNET" />

 这里请求用到的网络:http://www.omghz.cn/FirstService/getString

3.先来说说RxJava(观察者模式):第一种形式

// 创建字符串
    private String sayRxAndroid() {
        return "你好啊!RxAndroid";
    }
    //第一种
    private void numberOne() {
        //这里定义的Observable(被观察者,事件源)  对象仅仅发出一个Hello World字符串,然后就结束了。
        Observable<String> observable = Observable.create(
                new Observable.OnSubscribe<String>() {
                    @Override
                    public void call(Subscriber<? super String> sub) {
                        sub.onNext(sayRxAndroid());
                        sub.onCompleted();
                    }
                }
        );
        //接着我们创建一个Subscriber(观察者)来处理Observable对象发出的字符串。
        //只要订阅了observable,那么当他发生改变时这里就可以接收到消息
        Subscriber<String> subscriber = new Subscriber<String>() {
            @Override
            public void onNext(String s) {
                textView1.setText(s);
            }

            @Override
            public void onCompleted() {
            }

            @Override
            public void onError(Throwable e) {
                //出错回调
            }
        };
        //通过subscribe函数就可以将我们定义的observable对象和subscriber对象关联起来,
        // 这样就完成了subscriber对observable的订阅。
        observable.subscribe(subscriber);//订阅
    }

4.第二种形式,也就是对第一种形式的简化

//第二种,简单形式。Observable.just()就是用来创建只发出一个事件就结束的Observable对象
    private void numberTwo() {
        Observable<String> observable = Observable.just(sayRxAndroid() + "简单形式");
        //我们其实并不关心OnComplete和OnError,
        //我们只需要在onNext的时候做一些处理,这时候就可以使用Action1类。
        Action1<String> action1 = new Action1<String>() {
            @Override
            public void call(String s) {
                textView2.setText(s);
            }
        };
        //订阅
        observable.subscribe(action1);
    }

5.第三种形式,对第二种形式的简化

//方式二的代码最终可以简化成这样
    private void numberThree() {
        Observable.just(sayRxAndroid() + "简单形式二")
                .subscribe(new Action1<String>() {
                    @Override
                    public void call(String s) {
                        textView3.setText(s);
                    }
                });
    }

6.这里我没有引入Lambda表达式,Lambda表达式可以让上面的代码更加的简化、直观有兴趣的小伙伴可以尝试一下,下面我们使用RxJava来加载网络数据。

Schedulers(调度器)->线程控制
subscribeOn(Schedulers.io())—>指定 observable 发生在 IO 线程
observeOn(AndroidSchedulers.mainThread())—>指定 subscribe 的回调发生在主线程

    //请求网络数据,获取数据
    private void numberFour() {
        final Observable<String> observable = Observable.create(new Observable.OnSubscribe<String>() {
            @Override
            public void call(Subscriber<? super String> subscriber) {
                subscriber.onNext(getInternet());
                subscriber.onCompleted();
            }
        })
                .subscribeOn(Schedulers.io())
                .observeOn(AndroidSchedulers.mainThread());
        button.setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(final View v) {
                observable.subscribe(new Subscriber<String>() {
                    @Override
                    public void onCompleted() {

                    }

                    @Override
                    public void onError(Throwable e) {

                    }

                    @Override
                    public void onNext(String s) {
                        textView4.setText(s);
                    }
                });
            }
        });
    }

getInternet()从网络获取数据

 private String getInternet() {
        StringBuilder sb = new StringBuilder();
        String line;
        BufferedReader reader;
        try {
            URL url = new URL("http://www.omghz.cn/FirstService/getString?username=a_zhon&password=9584");
            HttpURLConnection urlConnection = (HttpURLConnection) url.openConnection();
            urlConnection.setRequestMethod("GET");
            urlConnection.setConnectTimeout(3000);
            urlConnection.setReadTimeout(3000);
            if (urlConnection.getResponseCode() == 200) {
                reader = new BufferedReader(new InputStreamReader(urlConnection.getInputStream(), "UTF-8"));
                while ((line = reader.readLine()) != null) {
                    sb.append(line);
                }
                return sb.toString();
            }
        } catch (Exception e) {
            e.printStackTrace();
        }
        return null;
    }

7.我们还可以来获取网络图片

 //从网络上获取一张图片
    private void numberFive() {
        Observable.just("http://sc.jb51.net/uploads/allimg/141119/10-1411192130010-L.jpg") // 输入类型 String
                .map(new Func1<String, Bitmap>() {
                    @Override
                    public Bitmap call(String url) { // 参数类型 String
                        return getBitmap(url); // 返回类型 Bitmap
                    }
                })
                .subscribeOn(Schedulers.io())
                .observeOn(AndroidSchedulers.mainThread())
                .subscribe(new Action1<Bitmap>() {
                    @Override
                    public void call(Bitmap bitmap) {
                        showBitmap(bitmap);
                    }

                    //显示获取的图片
                    private void showBitmap(Bitmap bitmap) {
                        ImageView iv = (ImageView) findViewById(R.id.iv);
                        iv.setImageBitmap(bitmap);
                    }
                });
    }

从网络获取一张图片

//从网络获取图片
    private Bitmap getBitmap(String path) {
        try {
            URL url = new URL(path);
            HttpURLConnection urlConnection = (HttpURLConnection) url.openConnection();
            urlConnection.setRequestMethod("GET");
            urlConnection.setConnectTimeout(3000);
            urlConnection.setReadTimeout(3000);
            if (urlConnection.getResponseCode() == 200) {
                InputStream inputStream = urlConnection.getInputStream();
                return BitmapFactory.decodeStream(inputStream);
            }
        } catch (IOException e) {
            e.printStackTrace();
        }
        return null;
    }

8.说了那么多RxJava,现在来看下RxJava与Retrofit结合请求网络,先来说说Retrofit的使用

Retrofit需要定义一个接口,用来返回我们的Call对象。
这里请求所使用的接口:http://www.omghz.cn/FirstService/getString

RequestServes.class

interface RequestServes {
    /**
     * 使用retrofit与Get方式获取网络数据
     * @GET("getString")--->定义请求方式和请求接口==== Call<String>--->定义返回结果类型
     */
    @GET("getString")
    Call<String> getJson(@Query("username") String username, @Query("password") String password);
    //@Query("username") String username, @Query("password") String password
    //请求参数,括号内为键值名,参数为传递的值


    //使用retrofit与Post方式获取网络数据
    @POST("getString")
    Call<String> getStringRetrofit(@Query("username") String username, @Query("password") String password);


    //使用retrofit与RxJava与Post方式获取网络数据
    @POST("getString")
    Observable<String> getStringRxJava(@Query("username") String username, @Query("password") String password);
}

9.接口写完了,我们来创建一个Retrofit对象使用Get请求网络

    /**
     * 使用Retrofit与Get请求
     */
    private void getJson() {
        Retrofit retrofit = new Retrofit.Builder()
          //请求地址,会与@GET("getString")拼接成一个完整的地址
          //http://www.omghz.cn/FirstService/getString
           .baseUrl("http://www.omghz.cn/FirstService/")
          //增加返回值为String的支持  
                       .addConverterFactory(ScalarsConverterFactory.create())
                .build();
        RequestServes serves = retrofit.create(RequestServes.class);//这里采用的是Java的动态代理模式
        Call<String> call = serves.getJson("名字", "密码");//传入我们请求的键值对的值
        call.enqueue(new Callback<String>() {
            @Override
            public void onResponse(Call<String> call, Response<String> response) {
                textView4.setText("Retrofit:--Get" + response.body());
            }

            @Override
            public void onFailure(Call<String> call, Throwable t) {

            }
        });
    }

10.使用Retrofit与Post请求网络

    /**
     * 使用Retrofit与Post请求网络
     */
    private void getStringRetrofit() {
        Retrofit retrofit = new Retrofit.Builder()
                .baseUrl("http://www.omghz.cn/FirstService/")
                //增加返回值为String的支持
                .addConverterFactory(ScalarsConverterFactory.create())
                .build();
        RequestServes serves = retrofit.create(RequestServes.class);//这里采用的是Java的动态代理模式
        Call<String> call = serves.getStringRetrofit("阿钟", "1011");//传入我们请求的键值对的值
        call.enqueue(new Callback<String>() {
            @Override
            public void onResponse(Call<String> call, Response<String> response) {
                textView4.setText("Retrofit:--Post" + response.body());
            }

            @Override
            public void onFailure(Call<String> call, Throwable t) {

            }
        });

11.使用Retrofit+RxJava与Post请求网络

    /**
     * 使用Retrofit+RxJava与Post请求网络
     */
    private void getStringRetrofitRxJava() {
        Retrofit retrofit = new Retrofit.Builder()
                .baseUrl("http://www.omghz.cn/FirstService/")
                .addConverterFactory(ScalarsConverterFactory.create())
                .build();
        retrofit.create(RequestServes.class)//这里采用的是Java的动态代理模式
                .getStringRxJava("阿钟", "1011")//传入我们请求的键值对的值
                .subscribeOn(Schedulers.io())
                .observeOn(AndroidSchedulers.mainThread())
                .subscribe(new Subscriber<String>() {
                    @Override
                    public void onCompleted() {

                    }

                    @Override
                    public void onError(Throwable e) {

                    }

                    @Override
                    public void onNext(String s) {
                        textView4.setText("Retrofit+RxJava:--Post" + s);
                    }
                });
    }
}

12.当你安装到手机上你会看到使用Retrofit+RxJava与Post请求网络 直接报如下错误

这里写图片描述

解决方法:在build.gradle中添加 compile ‘com.squareup.retrofit2:adapter-rxjava:2.1.0’在创建Retrofit 时添加 .addCallAdapterFactory()函数

 Retrofit retrofit = new Retrofit.Builder()
                .baseUrl("http://www.omghz.cn/FirstService/")
                .addConverterFactory(ScalarsConverterFactory.create())

                //解决 Unable to create call adapter for rx.Observable<java.lang.String>
                .addCallAdapterFactory(RxJavaCallAdapterFactory.create())
                .build();

效果图

这里写图片描述

到这里我们的第一次体验就结束了,对于Retrofit请求网络感觉真是太好用了省去了很多繁琐的步骤。这里好多用法都在代码注释中,所以小伙伴们阅读要仔细耐心哦!

项目地址:https://github.com/azhong1011/Rxjava-Retrofit

作者:a_zhon 发表于2016/10/18 11:23:22 原文链接
阅读:42 评论:0 查看评论

Viewing all articles
Browse latest Browse all 5930

Trending Articles



<script src="https://jsc.adskeeper.com/r/s/rssing.com.1596347.js" async> </script>