Joh*_*esy 3 uiscrollview ios programmatically-created swift swift-playground
在将视图添加到我的应用程序之前,我已经创建了一个小型演示游乐场来使其工作。
我有一个滚动视图,它将包含许多水平滚动的按钮。我知道这些按钮需要进入滚动视图中的容器视图,并且也创建了它。我最初使用自动布局约束来创建所有这些,但现在尝试使用常量来确保内容视图大于滚动视图。但是,按钮仍然不会滚动......我错过了什么吗?滚动视图不适用于自动布局吗?
我也在我的 iPad 上以编程方式执行所有这些操作,因此不幸的是,使用界面构建器的解决方案不是一种选择...
这是完整的代码:
import UIKit
import PlaygroundSupport
class FilterViewController: UIViewController {
var filterView: UIView!
var scrollView: UIScrollView!
var containerView: UIView!
override func loadView() {
filterView = UIView()
view = filterView
view.backgroundColor = #colorLiteral(red: 0.909803926944733, green: 0.47843137383461, blue: 0.643137276172638, alpha: 1.0)
scrollView = UIScrollView()
scrollView.backgroundColor = #colorLiteral(red: 0.474509805440903, green: 0.839215695858002, blue: 0.976470589637756, alpha: 1.0)
view.addSubview(scrollView)
scrollView.translatesAutoresizingMaskIntoConstraints = false
scrollView.topAnchor.constraint(equalTo:view.topAnchor, constant:40).isActive = true
scrollView.leadingAnchor.constraint(equalTo:view.leadingAnchor).isActive = true
scrollView.widthAnchor.constraint(equalTo:view.widthAnchor).isActive = true
scrollView.heightAnchor.constraint(equalToConstant: 200).isActive = true
scrollView.isScrollEnabled = true
containerView = UIView()
containerView.backgroundColor = #colorLiteral(red: 0.176470592617989, green: 0.498039215803146, blue: 0.756862759590149, alpha: 1.0)
scrollView.addSubview(containerView)
containerView.frame = CGRect(x: 0, y: 0, width: 1080, height: 200)
}
class Buttons{
let button = UIButton()
init (titleText : String){
button.backgroundColor = #colorLiteral(red: 0.976470589637756, green: 0.850980401039124, blue: 0.549019634723663, alpha: 1.0)
button.setTitle(titleText, for: .normal)
button.frame = CGRect(x: 0, y: 0, width: 200, height: 200)
}
}
override func viewDidLoad() {
super.viewDidLoad()
let b1 = Buttons(titleText: "one")
let b2 = Buttons(titleText: "two")
let b3 = Buttons(titleText: "three")
let b4 = Buttons(titleText: "four")
let b5 = Buttons(titleText: "five")
let buttonArray = [b1,b2,b3,b4,b5]
var startPoint : CGFloat = 0.0
for btn in buttonArray {
let theBtn = btn.button
containerView.addSubview(theBtn)
theBtn.frame = CGRect(x: startPoint, y: 0, width: 200, height: 200)
startPoint += 220
}
}
}
let filterViewController = FilterViewController()
PlaygroundPage.current.liveView = filterViewController
Run Code Online (Sandbox Code Playgroud)
谢谢瓦卡瓦玛!这是具有所有自动布局约束的完整(现在工作)迷你项目:
import UIKit
import PlaygroundSupport
class FilterViewController: UIViewController {
var filterView: UIView!
var scrollView: UIScrollView!
var containerView: UIView!
override func loadView() {
filterView = UIView()
view = filterView
view.backgroundColor = #colorLiteral(red: 0.909803926944733, green: 0.47843137383461, blue: 0.643137276172638, alpha: 1.0)
scrollView = UIScrollView()
scrollView.backgroundColor = #colorLiteral(red: 0.474509805440903, green: 0.839215695858002, blue: 0.976470589637756, alpha: 1.0)
view.addSubview(scrollView)
scrollView.translatesAutoresizingMaskIntoConstraints = false
scrollView.topAnchor.constraint(equalTo:view.topAnchor, constant:40).isActive = true
scrollView.leadingAnchor.constraint(equalTo:view.leadingAnchor).isActive = true
scrollView.widthAnchor.constraint(equalTo:view.widthAnchor).isActive = true
scrollView.heightAnchor.constraint(equalTo: view.heightAnchor, multiplier: 0.25).isActive = true
scrollView.isScrollEnabled = true
containerView = UIView()
containerView.backgroundColor = #colorLiteral(red: 0.176470592617989, green: 0.498039215803146, blue: 0.756862759590149, alpha: 1.0)
scrollView.addSubview(containerView)
containerView.translatesAutoresizingMaskIntoConstraints = false
containerView.topAnchor.constraint(equalTo:scrollView.topAnchor).isActive = true
containerView.leadingAnchor.constraint(equalTo:scrollView.leadingAnchor).isActive = true
containerView.trailingAnchor.constraint(equalTo:scrollView.trailingAnchor).isActive = true
containerView.bottomAnchor.constraint(equalTo:scrollView.bottomAnchor).isActive = true
containerView.heightAnchor.constraint(equalTo: scrollView.heightAnchor).isActive = true
}
class Buttons{
let button = UIButton()
init (titleText : String){
button.backgroundColor = #colorLiteral(red: 0.976470589637756, green: 0.850980401039124, blue: 0.549019634723663, alpha: 1.0)
button.setTitle(titleText, for: .normal)
//button.frame = CGRect(x: 0, y: 0, width: 200, height: 200)
}
}
override func viewDidLoad() {
super.viewDidLoad()
let b1 = Buttons(titleText: "one")
let b2 = Buttons(titleText: "two")
let b3 = Buttons(titleText: "three")
let b4 = Buttons(titleText: "four")
let b5 = Buttons(titleText: "five")
let buttonArray = [b1,b2,b3,b4,b5]
var startPoint = containerView.leadingAnchor
for btn in buttonArray {
let theBtn = btn.button
containerView.addSubview(theBtn)
theBtn.translatesAutoresizingMaskIntoConstraints = false
theBtn.leadingAnchor.constraint(equalTo:startPoint, constant:20).isActive = true
theBtn.topAnchor.constraint(equalTo:containerView.topAnchor).isActive = true
theBtn.bottomAnchor.constraint(equalTo:containerView.bottomAnchor).isActive = true
theBtn.widthAnchor.constraint(equalTo: theBtn.heightAnchor).isActive = true
startPoint = theBtn.trailingAnchor
containerView.widthAnchor.constraint(equalTo: theBtn.widthAnchor, multiplier:CGFloat(buttonArray.count), constant: CGFloat(buttonArray.count * 20)).isActive = true
}
}
}
let filterViewController = FilterViewController()
PlaygroundPage.current.liveView = filterViewController
Run Code Online (Sandbox Code Playgroud)
您可以使用Auto Layout做到这一点。该秘密是的边缘约束containerView
到的边缘scrollView
。它不直观,但约束 的边缘containerView
并没有设置大小,它只是确保内容的大小scrollView
随着增长而containerView
增长。通过将 宽度的约束设置为containerView
大于宽度的常数,scrollView
内容将水平滚动。
注:在配置scrollView
这种方式,你不设置contentSize
的scrollView
。在contentSize
将计算为你自动布局,这将是相等的大小containerView
。确保containerView
完全由约束指定的大小很重要。
这是我为使其工作所做的更改:
containerView = UIView()
containerView.backgroundColor = #colorLiteral(red: 0.176470592617989, green: 0.498039215803146, blue: 0.756862759590149, alpha: 1.0)
scrollView.addSubview(containerView)
//containerView.frame = CGRect(x: 0, y: 0, width: 1080, height: 200)
containerView.translatesAutoresizingMaskIntoConstraints = false
containerView.topAnchor.constraint(equalTo:scrollView.topAnchor).isActive = true
containerView.leadingAnchor.constraint(equalTo:scrollView.leadingAnchor).isActive = true
containerView.trailingAnchor.constraint(equalTo:scrollView.trailingAnchor).isActive = true
containerView.bottomAnchor.constraint(equalTo:scrollView.bottomAnchor).isActive = true
containerView.heightAnchor.constraint(equalToConstant: 200).isActive = true
containerView.widthAnchor.constraint(equalToConstant: 1080).isActive = true
Run Code Online (Sandbox Code Playgroud)
为什么我的内容不滚动?
要使其滚动,containerView
必须大于scrollView
。您的错误是您设置了约束,使得 的containerView
宽度和高度与 相同scrollView
,这就是您的内容不滚动的原因。
如果您希望它水平滚动,则 的宽度containerView
必须大于scrollView
的宽度。您可以通过以下两种方式之一执行此操作:
containerView
为大于 的宽度的 指定显式恒定scrollView
宽度。
或者
将 的子视图containerView
从左到右链接起来,最左边的被包含在containerView
. 完全指定子视图的宽度,并在子视图之间放置距离约束。最右边的子视图必须与containerView
. 通过这样做,自动布局可以计算的宽度containerView
和设置contentSize
的scrollView
。
小项目:更新
这是您的迷你项目的一个版本,它使用一系列受约束的视图来定义containerView
的宽度。关键是for
循环之后的最后一个约束,viewDidLoad()
其中将最后一个按钮的 trailingAnchor(又名startPoint
)连接到containerView
's trailingAnchor。这完成了将 的前缘containerView
与 的后缘连接起来的约束和按钮链containerView
。有了这个,自动布局能够计算的宽度containerView
和建立contentSize
的scrollView
。
import UIKit
import PlaygroundSupport
class FilterViewController: UIViewController {
var filterView: UIView!
var scrollView: UIScrollView!
var containerView: UIView!
override func loadView() {
filterView = UIView()
view = filterView
view.backgroundColor = #colorLiteral(red: 0.909803926944733, green: 0.47843137383461, blue: 0.643137276172638, alpha: 1.0)
scrollView = UIScrollView()
scrollView.backgroundColor = #colorLiteral(red: 0.474509805440903, green: 0.839215695858002, blue: 0.976470589637756, alpha: 1.0)
view.addSubview(scrollView)
scrollView.translatesAutoresizingMaskIntoConstraints = false
scrollView.topAnchor.constraint(equalTo: view.topAnchor, constant: 40).isActive = true
scrollView.leadingAnchor.constraint(equalTo: view.leadingAnchor).isActive = true
scrollView.widthAnchor.constraint(equalTo: view.widthAnchor).isActive = true
scrollView.heightAnchor.constraint(equalTo: view.heightAnchor, multiplier: 0.25).isActive = true
scrollView.isScrollEnabled = true
containerView = UIView()
containerView.backgroundColor = #colorLiteral(red: 0.176470592617989, green: 0.498039215803146, blue: 0.756862759590149, alpha: 1.0)
scrollView.addSubview(containerView)
containerView.translatesAutoresizingMaskIntoConstraints = false
// This is key: connect all four edges of the containerView to
// to the edges of the scrollView
containerView.topAnchor.constraint(equalTo: scrollView.topAnchor).isActive = true
containerView.leadingAnchor.constraint(equalTo: scrollView.leadingAnchor).isActive = true
containerView.trailingAnchor.constraint(equalTo: scrollView.trailingAnchor).isActive = true
containerView.bottomAnchor.constraint(equalTo: scrollView.bottomAnchor).isActive = true
// Making containerView and scrollView the same height means the
// content will not scroll vertically
containerView.heightAnchor.constraint(equalTo: scrollView.heightAnchor).isActive = true
}
class Buttons {
let button = UIButton()
init(titleText: String) {
button.backgroundColor = #colorLiteral(red: 0.976470589637756, green: 0.850980401039124, blue: 0.549019634723663, alpha: 1.0)
button.setTitle(titleText, for: .normal)
}
}
override func viewDidLoad() {
super.viewDidLoad()
let b1 = Buttons(titleText: "one")
let b2 = Buttons(titleText: "two")
let b3 = Buttons(titleText: "three")
let b4 = Buttons(titleText: "four")
let b5 = Buttons(titleText: "five")
let buttonArray = [b1, b2, b3, b4, b5]
var startPoint = containerView.leadingAnchor
for btn in buttonArray {
let theBtn = btn.button
containerView.addSubview(theBtn)
theBtn.translatesAutoresizingMaskIntoConstraints = false
theBtn.leadingAnchor.constraint(equalTo: startPoint, constant: 20).isActive = true
theBtn.topAnchor.constraint(equalTo: containerView.topAnchor).isActive = true
theBtn.bottomAnchor.constraint(equalTo: containerView.bottomAnchor).isActive = true
theBtn.widthAnchor.constraint(equalTo: theBtn.heightAnchor).isActive = true
startPoint = theBtn.trailingAnchor
}
// Complete the chain of constraints
containerView.trailingAnchor.constraint(equalTo: startPoint, constant: 20).isActive = true
}
}
let filterViewController = FilterViewController()
PlaygroundPage.current.liveView = filterViewController
Run Code Online (Sandbox Code Playgroud)
归档时间: |
|
查看次数: |
8574 次 |
最近记录: |