Xcode9/iOS11中UIScrollView上层Next/Prev按钮不显示问题求助
UIScrollView上层按钮消失+约束警告问题解决(Xcode 9/iOS 11)
嘿,这个问题我之前帮团队里的新人踩过坑,其实核心是UIScrollView的布局逻辑和层级关系没搞对,咱们一步步拆解:
问题根源
- UIScrollView的内容区域特性:UIScrollView需要明确的
contentSize才能知道可滚动的范围。当你把按钮直接放在它内部作为子视图时,如果你只给按钮加了相对于scrollView的位置约束,Interface Builder会混淆按钮的约束是用来确定scrollView的frame还是contentSize,导致contentSize计算错误——按钮其实没消失,是被“藏”在scrollView的可视区域外面了。 - 约束警告的由来:提示“Drag scrollview Constraints”是因为scrollView缺少能明确
contentSize的约束。当按钮在scrollView下方时,它是兄弟视图,不会干扰scrollView的内容布局,IB能正常推断scrollView的尺寸;但按钮作为子视图时,IB无法确定scrollView的内容边界,所以抛出警告。
两种解决方案(按需选择)
方案一:按钮不随滚动移动(最省心)
如果按钮是固定在屏幕某个位置(比如底部导航),不需要跟着scrollView滚动,那直接调整层级:
- 在IB的Document Outline里,把Next/Prev按钮从scrollView的子视图列表里拖出来,放到和scrollView同级的位置;
- 调整按钮的z轴层级(把按钮拖到scrollView的上方),这样按钮就会显示在scrollView视觉上层,同时完全不影响scrollView的布局,约束警告也会自动消失。
方案二:按钮需要随滚动移动
如果按钮是scrollView内容的一部分,要跟着滚动,那得用正确的约束方式(Xcode 9开始的新布局指南很有用):
- 先给scrollView设置到父视图的约束:比如
top、leading、trailing、bottom都和父视图对齐,确定scrollView的可视frame; - 在scrollView内部添加一个
UIView(命名为contentView),作为所有子视图的容器; - 给contentView添加约束:
top、leading、trailing、bottom四个方向都和scrollView的Content Layout Guide对齐;- 如果是垂直滚动,给contentView加一个
width等于scrollView的Frame Layout Guide的width约束(水平滚动则加height约束);
- 最后把Next/Prev按钮放到contentView上,设置相对于contentView的位置约束——这样IB能正确计算scrollView的contentSize,按钮正常显示,约束警告也会消失。
小提示
Xcode 9/iOS 11引入的Content Layout Guide和Frame Layout Guide,就是专门用来区分scrollView的内容区域和自身帧区域的,之前很多开发者容易把这两个搞混,用它们来设置约束就能避开大部分布局坑。
内容的提问来源于stack exchange,提问作者Dragos
相关产品推荐
相关产品推荐

