Android应用程序中的RxJava和MVP

时间:2016-10-27 01:17:53

标签: android rx-java mvp rx-android rx-binding

我正在尝试使用MVP架构在Android应用中实现一个屏幕,并在View端使用RxJava和RxBinding。

基本上我有2个Spinners,1个TextEdit和一个默认禁用的按钮。我想在Spinners选择了项目且文本字段不为空时启用该按钮。这是代码:

Observable.combineLatest(
        RxAdapterView.itemSelections(mFirstSpinner),
        RxAdapterView.itemSelections(mSecondSpinner),
        RxTextView.textChanges(mEditText),
        new Func3<Integer, Integer, CharSequence, Boolean>() {
            @Override
            public Boolean call(Integer first, Integer second, CharSequence value) {
                return !TextUtils.isEmpty(value);
            }
        }).subscribe(new Action1<Boolean>() {
        @Override
        public void call(Boolean enable) {
            mButton.setEnabled(enable);
        }
    });

现在的问题是如何将其整合到MVP模式中。理想情况下,&#34;业务逻辑&#34;启用按钮应该在演示者中。实现这一目标的最佳方法是什么?我正在考虑将原始观察者以某种方式传递给演示者(侧面问题是如何?),演示者将组合这些观察者,并且它将具有启用按钮的逻辑。最后,它只会调用View来修改按钮状态。

还有更好的选择吗?在View端有没有RxJava MVP的好例子?

2 个答案:

答案 0 :(得分:5)

我的主张:

你走在正确的轨道上。但是RxBinding逻辑应该仍然在视图中。我将移动逻辑连接,决定是否启用按钮进入演示者。

从您要检查的所有字段定义模型保留值:

private class ViewValuesModel {
    public Integer adapter1Value;
    public Integer adapter2Value;
    public CharSequence textValue;

    public ViewValuesModel(Integer adapter1Value, Integer adapter2Value, CharSequence textValue) {
        this.adapter1Value = adapter1Value;
        this.adapter2Value = adapter2Value;
        this.textValue = textValue;
    }
}

视图内部会创建Observable

Observable observable = Observable.combineLatest(
        RxAdapterView.itemSelections(mFirstSpinner),
        RxAdapterView.itemSelections(mSecondSpinner),
        RxTextView.textChanges(mEditText),
        new Func3<Integer, Integer, CharSequence, ViewValuesModel>() {
            @Override
            public ViewValuesModel call(Integer first, Integer second, CharSequence value) {
                return new ViewValuesModel(first, second, value);
            }
        }
)

然后将此Observable传递给演示者:

mPresenter.observeChoosableFieldChanges(observable).

内部演示者完成剩下的工作:

observable
    .map(new Func1<ViewValuesModel, Boolean>() {
        @Override
        public Booleancall(ViewValuesModel viewStates) {
            return !TextUtils.isEmpty(viewStates.textValue);
        }
    })
    .subscribe(new Action1<Boolean>() {
        @Override
        public void call(Boolean enable) {
            if (enable) {
                view.enableButton();
            } 
        }
    });

答案 1 :(得分:0)

您可以枚举您的源并将Pair值事件传递给Subject / Processor,您可以在其中执行逻辑,无论是否启用按钮并发布布尔事件。从演示者更新按钮的人将订阅此主题/处理器。

像这样,您可以灵活地更改源和逻辑,而无需更改Presenter-View合同。

基本上,Presenter中可以有2个绝对分离的组件:

1)侦听传入视图事件并生成动作流以启用或禁用按钮的组件 2)一个组件,它分别监听启用/禁用操作并更新视图(这也可以通过Google的绑定库实现)

通过这种方式,您可以启用多个解耦的交互链,并且易于维护由于组件的简单性和流连接的清晰度。

你也可以像RHub library一样使用smth。您可以找到组件示例here