【问题标题】:Is it OK for a view to know about its controller?视图可以了解其控制器吗?
【发布时间】:2012-02-27 04:33:34
【问题描述】:

我希望我的控制器订阅来自视图的通知。但是,在此之前,我想确认视图是否可以知道其控制器的实例?

让我举一个更具体的例子来说明我的想法。

我的控制器创建视图并通知它它是它的控制器

self.gameView = [[GameView alloc] initWithController:self];

完成后,它会从该视图订阅通知

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

虽然视图会做它的事情,但当合适的时间到来时,它会发布通知

[[NSNotificationCenter defaultCenter] postNotificationName:
                                        @"SaySomethingClever" object:gvc];

为了做到这一点,视图需要知道通知的接收者(gvc)。

我想借此机会和你一样,以下是否可以:

initWithController被调用时,视图

-(id) initWithController: (GameViewController* )g {
    gvc = g;
    return [self initWithFrame:CGRectMake(0, 0, 480, 300)];
}

initWithFrame:CGRectMake 是处理特定视图内容的私有方法。

一切正常,但是,我想知道这种方法在道德上是否可以接受

【问题讨论】:

    标签: objective-c model-view-controller nsnotificationcenter


    【解决方案1】:

    如果视图有对其控制器的引用,这不是严格的问题,但看起来你真正的问题是对通知发布方法的误解。

    object 参数不是接收者。事实上,如果是——如果通知的发布者必须知道将要获得通知的对象——那将破坏通知的整个目的。你可以调用适当的方法!通知的重点是发布者不需要知道正在监听的其他对象。

    object 参数实际上被接收者用来区分它应该关心哪些通知。最常见的争论是海报本身:

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

    但它实际上可以是任何对象。

    注册通知时,您可以指定您感兴趣的通知的特定实例。这是addObserver:...object 参数,然后通知中心将只传递名称为和 对象匹配指定的内容。

    即使您将object 传递给addObserver:... 中的nil,您也可以检查收到的通知的对象,并且仅当发布者是您感兴趣的内容时才采取行动。

    例如,您的应用程序中可能有多个窗口,您可能想知道何时调整其中一个窗口的大小,但您并不关心其余窗口会发生什么。您只需将该窗口实例作为object 传递给addObserver:...

    总而言之,在这种情况下,您的视图不需要对其控制器的引用,以便控制器接收视图发布的通知。

    另请参阅:"Posting Notifications"

    【讨论】:

    • 优秀的答案乔希!谢谢
    • 很高兴它有帮助!写的时候感觉有点乱。
    【解决方案2】:

    虽然这个概念没问题,但在您的情况下不需要:

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

    NSNotification 引用的对象通常是发布通知的对象。整个通知的想法是张贴者不需要了解观察者。

    【讨论】:

      【解决方案3】:

      我会专注于调用其他控制器(或理想的模型方法)的控制器。
      允许每个视图使用它的主要资源,并允许该视图的控制器进行额外的调用。

      【讨论】:

        猜你喜欢
        • 1970-01-01
        • 2011-07-11
        • 2016-04-11
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 2017-10-29
        相关资源
        最近更新 更多