从超级视图中删除视图时会调用什么?
想象一下,我有一个名为 blueView
的视图控制器和另一个名为 greenView
的视图控制器。然后,我添加 greenView.view
作为 blueView.view
的子视图。现在假设在一些用户交互之后,我想使用以下方法从 blueView.view
中删除 greenView.view
:
[self.view removeFromSuperview]
这里实际发生了什么? blueView.view
是否被重绘过?我认为可能会调用 viewDidLoad 方法,但是在将 NSLog 消息放入 viewDidLoad 后,删除子视图后从未调用该方法。任何有关从其超级视图中删除子视图时实际发生的情况的澄清将不胜感激。
Imagine I have a view controller called blueView
and another called greenView
. I then add greenView.view
as a subview of blueView.view
. Now suppose that after some user interaction, I'd like to remove greenView.view
from blueView.view
using:
[self.view removeFromSuperview]
What is actually happening here? Is blueView.view
ever redrawn? I thought the viewDidLoad
method might be called, however after putting an NSLog
messge in viewDidLoad
, it was never called after removing the subview. Any clarification as to what is actually happening when you remove a subview from its superview would be much appreciated.
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(1)
首先,视图控制器旨在一次管理整个视图层次结构;你不应该有两个视图控制器(除了像 UINavigationController 这样的容器控制器)同时处于活动状态。请参阅这个问题和我的答案以更好地理解这一重要点。所以,你所描述的特殊情况不应该出现。 (旁白:人们经常混淆视图和视图控制器,因此为视图控制器提供以“-view”结尾的名称是没有帮助的,例如“blueView”。将其称为“blueViewController”以帮助避免混淆。)
其次,正如 @InsertWittyName 指出的out,
-viewDidLoad
是一个 UIViewController 方法,而不是 UIView 方法。更进一步,视图控制器和 -viewDidLoad 都没有在视图中添加或删除子视图方面发挥任何作用。-viewDidLoad
在视图控制器的视图首次创建时被调用。它基本上只是将视图控制器初始化的与视图相关的部分推迟到创建视图层次结构之后的一种方法,因此没有理由仅仅因为从层次结构中删除了子视图就再次调用它。最后,视图如何从其超级视图中删除自身实际上是一个实现细节——它可能会调用超级视图上的私有 UIView 方法,或者可能会直接修改超级视图的子视图列表,或者其他什么。我在文档中没有看到任何内容明确说明超级视图将在子视图被删除后重新绘制自身,但根据我的经验,超级视图确实会重新绘制自身。您可以通过在超级视图的 -drawRect 方法上放置断点来检查这一点。
First, a view controller is meant to manage an entire view hierarchy at once; you shouldn't have two view controllers (other than container controllers like UINavigationController) active at the same time. See this SO question and my answer to get a better understanding on this important point. So, the particular situation you describe shouldn't come up. (Aside: people often confuse views and view controllers, so it's not helpful to give your view controllers names ending in "-view", like "blueView." Call it "blueViewController" to help avoid confusion.)
Second, as @InsertWittyName points out,
-viewDidLoad
is a UIViewController method, not a UIView method. Taking that a step further, neither view controllers nor-viewDidLoad
has any role in adding or removing subviews from a view.-viewDidLoad
is called when the view controller's view is first created. It's basically just a way of deferring the view-related part of view controller initialization until after the view hierarchy has been created, so there's no reason that it'd be called again just because a subview was removed from the hierarchy.Finally, exactly how a view removes itself from its superview is really an implementation detail -- it might call a private UIView method on the superview, or it might modify the superview's list of subviews directly, or something else. I don't see anything in the documentation that explicitly says that the superview will redraw itself after a subview has been removed, but in my experience the superview does indeed redraw itself. You can check this by putting a breakpoint on the
-drawRect
method of the superview.