java - Android-RxJava:使用 observable 从后台线程更新 UI
问题描述
我刚开始构建一个简单的 Android 应用程序,我想在后台线程中发出网络请求,然后使用服务器响应更新主线程(UI 线程)。到目前为止,我使用过AsyncTasks
,但未来的实现我想使用反应式 Java ( RxJava
)。我以前从未做过响应式调用,所以我想要一个简单但完整的示例(可观察和观察者的创建和订阅),可以在此基础上进一步构建。
我设法将 RxJava 依赖项包含到基本的 Android 项目中,并使用 AsyncTasks 为网络请求编写了一个非常简单的主要活动。现在我尝试用响应式实现来替换 AsyncTask 实现,但是却陷入了有关 Observable 和 Observer 的所有信息中。我只是不确定最小但完全有效的示例到底需要什么。
我真的很想在将主要部分转换为反应式实现方面提供一些帮助,因为我不知道如何处理从响应字符串生成 Observable 并订阅 Observer。
谢谢。
package com.example.reactiveTest;
import androidx.appcompat.app.AppCompatActivity;
import android.os.AsyncTask;
import android.os.Bundle;
import android.view.View;
import android.widget.Button;
import android.widget.TextView;
public class MainActivity extends AppCompatActivity {
private Button btnSend = null;
private TextView result = null;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
this.btnSend = findViewById(R.id.button_send);
this.result = findViewById(R.id.result);
}
public void onClickBtnSend(View view) {
new SomeTask().execute("Just some String");
}
class SomeTask extends AsyncTask<String, Void, String> {
@Override
protected String doInBackground(String... strings) {
// server request returning response String
return response;
}
@Override
protected void onPostExecute(String string) {
// update UI with response String
result.setText(string);
}
}
}
解决方案
使用 AsyncTask,您基本上是在工作线程上执行异步操作,然后在主线程上使用其结果。在 Rx 中,您将使用如下内容:
Observable.fromCallable(asyncOperation)
.subscribeOn(backgroundThread)
.observeOn(mainThread)
.subscribe(result -> { /* update UI for instance */ })
看来您也对onNext
和onError
感兴趣onComplete
。
onNext
每次可观察对象发出一个项目时都会调用它。每次调用它都会收到一个项目,然后可以处理它。onError
当可观察对象由于某种原因遇到错误时调用。当它被调用时,它会收到一个 Throwable,它表示错误的原因。调用后,不会调用 onNext 和 onComplete。onComplete
在使用最后一项调用 onNext 之后调用。它不接收任何输入,例如,您可以在其中进行一些清理。
使用上述方法如下所示:
Observable.fromCallable(asyncOperation)
.subscribeOn(backgroundThread)
.observeOn(mainThread)
.subscribe(onNext, onError, onComplete)
[编辑]
如果您想使用 创建 Observable Observable.create()
,您绝对可以这样做,它可以让您更好地控制通过 Observable 发出的内容和时间。例如,如果您想处理一些可能由网络请求导致的特定错误,并Throwable
根据错误发出不同的 s,您可以这样做。
ObservableOnSubscribe asyncOperation = new Observable.OnSubscribe<Integer>() {
@Override
public void call(Subscriber<? super Integer> emitter) {
try {
// network request
// Once result is ready, call emitter.onNext().
// When done, complete this Observable by calling emitter.onComplete()
} catch (Exception e) {
// handle error, and emit it using emitter.onError()
}
}
}
推荐阅读
- r - 提取向量中的所有值
- jquery - 焦点输入 Safari Mobile 以框阴影聚焦,但在输入字段内没有光标
- json - 有条件地合并 JSON 模式属性
- c++ - 如何编写一个返回标题内数组的函数?
- string - 使用索引python访问列表值
- python - 无法从频道中清除消息,discord.py
- python - 如何旋转 timeindex 的值
- swift - 从 Swift 中的 func 返回 void func
- c# - C# AutoMapper - 如果源中不存在,则在 dest 属性中设置默认值
- jquery - 如何使用 ChartJS 呈现具有多个相关数据点的折线图