子ViewController视图无法添加至父ViewController自定义View问题咨询
为什么子控制器视图无法添加到自定义UIView中?
这个问题我之前也碰到过,其实核心是iOS对视图控制器容器关系的严格要求,再加上自定义视图的布局问题,一起来拆解下:
问题根源
1. 未正确建立父子控制器的容器关联
iOS中,视图控制器(VC)的视图不能随便直接添加到另一个视图上——你必须通过官方的容器API来建立父子VC的关系。如果只调用self.customView.addSubview(childViewController.view),系统不会把这个子VC纳入父VC的管理体系:
- 子VC的生命周期方法(比如
viewDidAppear、viewWillDisappear)不会被正确触发 - 系统可能无法正确维护子VC视图的布局状态,甚至在某些场景下会释放子VC的视图
- 当父VC的视图层级发生变化时,子VC的视图会被忽略
而直接添加到self.view时,虽然严格来说也不符合规范,但因为self.view是当前VC的根视图,系统可能会隐式做一些兼容处理,让视图暂时显示出来,但这其实是不推荐的写法。
2. 自定义UIView的布局未正确设置
你的customView可能存在尺寸为0的情况:
- 如果用frame布局,没给
customView设置非零的frame,导致它的bounds是CGRectZero,即使添加了子VC的视图,也因为父视图没有尺寸而无法显示 - 如果用Auto Layout,没给
customView添加足够的约束(比如没有和父视图绑定位置/尺寸,也没设置固定宽高),Auto Layout无法计算出它的有效尺寸
解决方案
要让子VC的视图正确显示在自定义UIView中,需要按以下步骤操作:
第一步:正确建立父子控制器关系
在添加子视图前,必须调用容器API完成关联(以Swift为例):
// 1. 将子VC添加为当前VC的子控制器 self.addChild(childViewController) // 2. 将子VC的视图添加到自定义View中 self.customView.addSubview(childViewController.view) // 3. 通知子VC已完成容器添加 childViewController.didMove(toParent: self)
如果是Objective-C,代码如下:
[self addChildViewController:childViewController]; [self.customView addSubview:childViewController.view]; [childViewController didMoveToParentViewController:self];
第二步:确保自定义UIView有有效尺寸
- Frame布局:给
customView设置明确的frame,比如:self.customView.frame = CGRect(x: 20, y: 100, width: self.view.bounds.width - 40, height: 300) - Auto Layout:给
customView添加完整的约束,比如让它水平居中、距离顶部100pt、宽度占满屏幕减40pt、高度300pt:self.customView.translatesAutoresizingMaskIntoConstraints = false NSLayoutConstraint.activate([ self.customView.topAnchor.constraint(equalTo: self.view.topAnchor, constant: 100), self.customView.leadingAnchor.constraint(equalTo: self.view.leadingAnchor, constant: 20), self.customView.trailingAnchor.constraint(equalTo: self.view.trailingAnchor, constant: -20), self.customView.heightAnchor.constraint(equalToConstant: 300) ])
第三步:给子VC的视图设置布局约束
将子VC的视图添加到customView后,要让它占满customView的空间,避免显示不全:
childViewController.view.translatesAutoresizingMaskIntoConstraints = false NSLayoutConstraint.activate([ childViewController.view.topAnchor.constraint(equalTo: self.customView.topAnchor), childViewController.view.leadingAnchor.constraint(equalTo: self.customView.leadingAnchor), childViewController.view.trailingAnchor.constraint(equalTo: self.customView.trailingAnchor), childViewController.view.bottomAnchor.constraint(equalTo: self.customView.bottomAnchor) ])
按照这三步操作,子VC的视图就能正常显示在自定义UIView中了。
内容的提问来源于stack exchange,提问作者dre_84w934
相关产品推荐
相关产品推荐

