使用 RxAndroid 进行改造
Using RxAndroid with retrofit
我一直在寻找我的问题,但找不到问题的解决方案,因为 RxAndroid
对我来说很难理解。
如何从 Internet 获取数据并将其显示在我的屏幕上?
public class MainActivity extends AppCompatActivity implements View.OnClickListener {
Button btnLoad;
ListView listView;
public static final String BASE_URL = "http://api.icndb.com/";
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
btnLoad = findViewById(R.id.btnSet);
btnLoad.setOnClickListener(this);
listView = findViewById(R.id.listView);
}
@Override
public void onClick(View v) {
useRxJava();
}
private void setAdapter(ArrayList<String> jokes) {
ArrayAdapter<String> adapter = new ArrayAdapter<String>(this, android.R.layout.simple_list_item_1, jokes);
listView.setAdapter(adapter);
}
private ArrayList<String> sentRequest() {
ArrayList<String> jokes = new ArrayList<>();
Retrofit.Builder builder = new Retrofit.Builder()
.baseUrl(BASE_URL)
.addConverterFactory(GsonConverterFactory.create());
Retrofit retrofit = builder.build();
JokeRetrofitInterface client = retrofit.create(JokeRetrofitInterface.class);
Call<RootObject> call = client.getJokes();
RootObject rootObject = null;
try {
rootObject = call.execute().body();
} catch (IOException e) {
e.printStackTrace();
}
Value[] values = rootObject.getValue();
for (Value value : values) {
String joke = value.getJoke();
jokes.add(joke);
}
return jokes;
}
private void useRxJava() {
Observable observable = Observable.create(new ObservableOnSubscribe<ArrayList<String>>() {
@Override
public void subscribe(ObservableEmitter<ArrayList<String>> emitter) throws Exception {
ArrayList<String> myJokes = new ArrayList<>();
myJokes = sentRequest();
emitter.onNext(myJokes);
}
});
observable.subscribe(new Consumer<ArrayList<String>>() {
@Override
public void accept(ArrayList<String> jokes) throws Exception {
setAdapter(jokes);
}
});
}
}
更新你的方法。使用 RxJava()
private void useRxJava() {
Observable observable = Observable.fromCallable(new
Callable<ArrayList<String>>() {
@Override
public ArrayList<String> call() throws Exception {
return sentRequest()
}
});
observable.subscribeOn(Schedulers.io) // This makes sure that network operation happens in io thread
.observeOn(AndroidSchedulers.mainThread()) // This makes sure that you get response back in main thread
.subscribe(new Consumer<ArrayList<String>>() {
@Override
public void accept(ArrayList<String> jokes) throws Exception {
setAdapter(jokes);
}
});
}
其他一些建议和意见:
- 使用 rxjava2 而不是 RxJava 1
- 将 JokeRetrofitInterface 设为单例
- Retrofit 本身可以 return 一个 Observable,所以你的 JokeRetrofitInterface.getJokes 本身可以 return 一个 Observable(或 RxJava 2 中的 Single),它会减少一些代码量。
- 我在你的代码中没有发现 RxAndroid 的使用,它只是普通的 RxJava
- 不要停止学习:)。一开始会很难,但你最终会赢得它。
我一直在寻找我的问题,但找不到问题的解决方案,因为 RxAndroid
对我来说很难理解。
如何从 Internet 获取数据并将其显示在我的屏幕上?
public class MainActivity extends AppCompatActivity implements View.OnClickListener {
Button btnLoad;
ListView listView;
public static final String BASE_URL = "http://api.icndb.com/";
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
btnLoad = findViewById(R.id.btnSet);
btnLoad.setOnClickListener(this);
listView = findViewById(R.id.listView);
}
@Override
public void onClick(View v) {
useRxJava();
}
private void setAdapter(ArrayList<String> jokes) {
ArrayAdapter<String> adapter = new ArrayAdapter<String>(this, android.R.layout.simple_list_item_1, jokes);
listView.setAdapter(adapter);
}
private ArrayList<String> sentRequest() {
ArrayList<String> jokes = new ArrayList<>();
Retrofit.Builder builder = new Retrofit.Builder()
.baseUrl(BASE_URL)
.addConverterFactory(GsonConverterFactory.create());
Retrofit retrofit = builder.build();
JokeRetrofitInterface client = retrofit.create(JokeRetrofitInterface.class);
Call<RootObject> call = client.getJokes();
RootObject rootObject = null;
try {
rootObject = call.execute().body();
} catch (IOException e) {
e.printStackTrace();
}
Value[] values = rootObject.getValue();
for (Value value : values) {
String joke = value.getJoke();
jokes.add(joke);
}
return jokes;
}
private void useRxJava() {
Observable observable = Observable.create(new ObservableOnSubscribe<ArrayList<String>>() {
@Override
public void subscribe(ObservableEmitter<ArrayList<String>> emitter) throws Exception {
ArrayList<String> myJokes = new ArrayList<>();
myJokes = sentRequest();
emitter.onNext(myJokes);
}
});
observable.subscribe(new Consumer<ArrayList<String>>() {
@Override
public void accept(ArrayList<String> jokes) throws Exception {
setAdapter(jokes);
}
});
}
}
更新你的方法。使用 RxJava()
private void useRxJava() {
Observable observable = Observable.fromCallable(new
Callable<ArrayList<String>>() {
@Override
public ArrayList<String> call() throws Exception {
return sentRequest()
}
});
observable.subscribeOn(Schedulers.io) // This makes sure that network operation happens in io thread
.observeOn(AndroidSchedulers.mainThread()) // This makes sure that you get response back in main thread
.subscribe(new Consumer<ArrayList<String>>() {
@Override
public void accept(ArrayList<String> jokes) throws Exception {
setAdapter(jokes);
}
});
}
其他一些建议和意见:
- 使用 rxjava2 而不是 RxJava 1
- 将 JokeRetrofitInterface 设为单例
- Retrofit 本身可以 return 一个 Observable,所以你的 JokeRetrofitInterface.getJokes 本身可以 return 一个 Observable(或 RxJava 2 中的 Single),它会减少一些代码量。
- 我在你的代码中没有发现 RxAndroid 的使用,它只是普通的 RxJava
- 不要停止学习:)。一开始会很难,但你最终会赢得它。