ReactiveCocoa,RACCommand在完成

时间:2015-05-18 21:48:37

标签: ios objective-c mvvm reactive-cocoa

我正在使用RACCommand进行UI按钮点击事件。我正在使用MVVM架构。在我的ViewModel中,我有这个:

@property (strong, nonatomic) RACCommand *executeRegistration;

在“init”里面我有这个:

self.executeRegistration = [[RACCommand alloc] initWithSignalBlock:^RACSignal *(id input)
{
    return  [self executeSearchSignal];
}];

执行搜索信号是这样的:

- (RACSignal *)executeSearchSignal {
return [[[self.services insertUserRegistration]
         registerUserName:self.userName]
         logAll];
}

我的“[self.services insertUserRegistration]              registerUserName:self.userName“是这个:

 @weakify(self);
return [RACSignal createSignal:^RACDisposable *(id<RACSubscriber> subscriber)
{
    @strongify(self);

    Manager *manager = [Manager sharedManager];
    manager._delegate = self;

    RACSignal *successSignal =
    [self rac_signalForSelector:@selector(manager:didSuccesWithoutError:)
                   fromProtocol:@protocol(ManagerDelegate)];

    RACSignal *failSignal =
    [self rac_signalForSelector:@selector(manager:didFailWithError:)
                   fromProtocol:@protocol(ManagerDelegate)];

    [[successSignal map:^id(RACTuple *tuple)
    {
        return tuple.second;
    }] subscribeNext:^(id x) {
        [subscriber sendNext:x];
        [subscriber sendCompleted];
    }];

    [[failSignal map:^id(RACTuple *tuple)
      {
          return tuple.second;
      }] subscribeNext:^(id x) {
          [subscriber sendError:x];
      }];

    [manager insertUserRegistration:name];
    return nil;
}];

我的ViewController在BindViewModel方法中有这个:

[self.finishRegistrationButton.rac_command.executionSignals subscribeNext:^(RACSignal *loginSignal) {
    // Log a message whenever we log in successfully.
    [loginSignal subscribeCompleted:^{
        NSLog(@"I'm here.");
    }];
}];

self.finishRegistrationButton.rac_command = self.viewModel.executeRegistration;

使用我的“logAll”属性,我可以看到一切正在执行,问题是在一切正常后它永远不会进入subsrcibeCompleted。我想在出现错误时显示错误消息,或者如果一切正常则执行segue。我究竟做错了什么?你能解释一下这个怎么样吗?我现在已经待了很长时间了。

2 个答案:

答案 0 :(得分:2)

我做到了。 RACCommand&#39;没有subscribeError&#39;。发送的信号不包含错误事件。有特殊财产的错误&#39;。在该属性中,发送错误发送的每个信号都是&#39; next&#39;。所以,解决方案是使用这个:

[self.executeRegistration.executionSignals subscribeNext:^(RACSignal *signal){
[signal subscribeCompleted:^{
     NSLog(@"Registered");
  }];
}];

[self.executeRegistration.errors subscribeNext:^(id x) {
    NSLog(@"Error");
}];

这没关系。如果您不想要每个新值,则无需订阅。这实际上是非常酷的东西,但是我已经读到它太混乱,为什么它不像经典实现那样发送错误(这对我来说:))。如果我没有弄错的话,那将包含在3.0中。

答案 1 :(得分:0)

self.finishRegistrationButton.rac_command.executionSignals会返回信号信号,因此您需要使用switchToLatest,如下所示:

self.finishRegistrationButton.rac_command.executionSignals.switchToLatest

此功能截取信号并切换到最新接收,发送下一个错误,并从该信号而不是操作的信号完成。对于随时间发送信号的操作非常方便。

此代码仅适用于保存单个信号的executionSignals,如果您需要多个目标,则需要更复杂的内容。如果您需要更改代码以便以这种方式工作,您可能需要查看flattenMap: