【问题标题】:Return value from other class delegate其他类委托的返回值
【发布时间】:2012-07-01 01:09:04
【问题描述】:

我创建了一个类(UIView),里面有一个 UIScrollview。通过委托“scrollViewDidEndDecelerating”,我可以获得 3 个结果(1、2、3)。 如何将此结果发送到主 ViewController?

ViewController 标头

#import "Picker.h"

ViewController 实现

picker = [[Picker alloc]initWithFrame:CGRectMake(10, 10, 300, 300)];
[self.view addSubview:picker];

选择器实现

(...)

-(void)scrollViewDidEndDecelerating:(UIScrollView *)scrollView {

    if (scrollView.contentOffset.x <= 100) {

        int result = 1;

    } else if (scrollView.contentOffset.x > 100 && scrollView.contentOffset.x <= 200) {

        int result = 2;

    } else {

        int result = 3;

    }
}

(...)

我不得不创建一个 UIView 类,因为它除了 Scrollview 之外还有其他东西。

谢谢!

【问题讨论】:

    标签: objective-c xcode uiscrollview


    【解决方案1】:

    您可以在 Picker 类中定义一个属性:

    @property (nonatomic, assign) MyViewController* controller;
    

    并像这样初始化 Picker 的实例:

    picker = [[Picker alloc]initWithFrame:CGRectMake(10, 10, 300, 300) andController:self];
    

    那么你可以这样做:

    -(void)scrollViewDidEndDecelerating:(UIScrollView *)scrollView {
    
        [self.controller myMethod]; 
        ...
    

    这被称为依赖注入,如果在两个类之间创建如此强的耦合是有意义的,那就可以了。您可以创建一个委托协议来为此类交互提供更完整的状态。

    另一个可以避免耦合的选项是通过NSNotificationCenter 使用通知。

    在这种情况下,一个对象(您的控制器)将注册以观察PickerScrollViewChanged 通知:

    [[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(myMethod:) name:kPickerScrollViewChanged object:nil];
    

    picker 将通过其scrollViewDidEndDecelerating 方法发送此类通知:

    [[NSNotificationCenter defaultCenter] postNotificationName:kPickerScrollViewChanged object:self];
    

    【讨论】:

    • 谢谢,但是这样这个类不能在多个类中使用。
    • 为什么不呢?你决定什么签名有你的方法,如果你需要传递对选择器的引用,欢迎你......确实,这就是我对通知示例所做的......
    【解决方案2】:

    我建议您创建一个PickerDelegate 协议,其中包含将所需值返回给主视图控制器的方法。

    @protocol PickerDelegate <NSObject>
    
    -(void)picker:(Picker *)picker didScrollToResult:(NSInteger)result;
    
    @end
    

    Picker 有一个属性:

    @property (nonatomic, assign) id<PickerDelegate> delegate;
    

    然后您可以使用picker.delegate = self; 将您的视图控制器设置为选择器委托

    在 Picker UIView 的滚动视图委托方法中,您可以使用以下方法将消息传递给视图控制器:

    -(void)scrollViewDidEndDecelerating:(UIScrollView *)scrollView {
        if (scrollView.contentOffset.x <= 100) {
            int result = 1;
        } else if (scrollView.contentOffset.x > 100 && scrollView.contentOffset.x <= 200) {
            int result = 2;
        } else {
            int result = 3;
        }
        [self.delegate picker:self didScrollToResult:result];
    }
    

    视图控制器需要实现picker委托方法:

    -(void)picker:(Picker *)picker didScrollToResult:(NSInteger)result {
        // View controller now has result variable to action upon.
    }
    

    【讨论】:

      【解决方案3】:

      在您的视图控制器类中,您应该将观察者(注册通知)添加到 viewDidLoad 方法中。 在scrollViewDidEndDecelerating 中,您应该发布通知。

      所以,在 viewDidLoad 中:

      [[NSNotificationCenter defaultCenter]
       addObserver:self
       selector:@selector(scrollViewZoomed:)
       name:@"scrollViewDidZoom"
       object:nil];
      

      在你的 scrollViewDidEndDecelerating,

      [[NSNotificationCenter defaultCenter]
       postNotificationName:@"scrollViewDidZoom"
       object:self];
      

      不要忘记在不需要时删除观察者。

      【讨论】:

        猜你喜欢
        • 1970-01-01
        • 2014-12-10
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 2014-01-10
        • 1970-01-01
        • 1970-01-01
        相关资源
        最近更新 更多