MVVM with ReactiveCocoa: limit the text length of a UITextField in view model

限于喜欢 提交于 2019-12-10 12:16:12

问题


I'm adopting MVVM with ReactiveCocoa. Now I have a UITextField which I need to limit it's max text length to 100.

In my view:

- (void)bindViewModel
{
    RAC(self.viewModel, text) = self.textField.rac_textSignal;
    [RACObserve(self.viewModel, text) subscribeNext:(NSString *text) {
        self.textField.text = text;
    }];
}

In my view model

- (id)init
{
    [RACObserve(self, text) subscribeNext:^(NSString *x) {
        //block 1
        if (x.length > maxTextLength) {
            x = [x substringToIndex:maxTextLength];
        }
    }];
}

But this doesn't work, block 1 is never called.

By using MVVM, I believe that the text length control logic should be put in my view model, but what is the proper way to achieve this?


回答1:


As described in this answer: you can take rac_textSignal from the text field and use map to trim the string to the desired length. Then bind the mapped signal to the text field using RAC macro. As you noted, view model shouldn't have a reference to the view. But it can be passed a signal and return a mapped signal.

In a view:

RAC(self.textField, text) = [self.viewModel validatedTextWithSignal:self.deviceName.rac_textSignal];

in your view model:

- (RACSignal *)validatedTextWithSignal:(RACSignal *)signal {
    NSUInteger kMaxLength = 5;
    return [signal map:^id(NSString *text) {
        return text.length <= kMaxLength ? text : [text substringToIndex:kMaxLength];
    }];
}

This also makes the text control logic easy to test - in unit tests, you can pass something like -[RACSignal return:@"foo"] to the view model and check if the output is correct.



来源:https://stackoverflow.com/questions/31228116/mvvm-with-reactivecocoa-limit-the-text-length-of-a-uitextfield-in-view-model

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!