首页
学习
活动
专区
圈层
工具
发布
首页
学习
活动
专区
圈层
工具
MCP广场
社区首页 >问答首页 >在Swift中将约束与可变和固定高度结合在UIView上

在Swift中将约束与可变和固定高度结合在UIView上
EN

Stack Overflow用户
提问于 2021-07-26 13:00:32
回答 3查看 161关注 0票数 0

更新:

感谢大家的独特做法。感谢你的见解。

背景:

我在下面的Xcode Swift 5中编写了一些代码,它创建了四个大小相等的矩形,根据设备大小和方向调整大小。

然而,所需的结果是具有不同高度的矩形,其中顶部矩形是可变高度,取决于设备大小和方向,而底部矩形的高度不变为200 of。

问题:

要实现顶部的可变高度和底部的固定高度,需要对代码进行哪些更改?

代码:

代码语言:javascript
运行
复制
import UIKit

class ViewController: UIViewController {

    override func viewDidLoad() {
        super.viewDidLoad()
        
        let frameTopLeft = UIView()
        frameTopLeft.backgroundColor = .systemRed
        view.addSubview(frameTopLeft)
        frameTopLeft.translatesAutoresizingMaskIntoConstraints = false
        NSLayoutConstraint.activate([
            frameTopLeft.topAnchor.constraint(equalTo: view.topAnchor),
            frameTopLeft.heightAnchor.constraint(equalTo: view.heightAnchor, multiplier: 0.5),
            frameTopLeft.leftAnchor.constraint(equalTo: view.leftAnchor),
            frameTopLeft.widthAnchor.constraint(equalTo: view.widthAnchor, multiplier: 0.5)
        ])

        let frameTopRight = UIView()
        frameTopRight.backgroundColor = .systemBlue
        view.addSubview(frameTopRight)
        frameTopRight.translatesAutoresizingMaskIntoConstraints = false
        NSLayoutConstraint.activate([
            frameTopRight.topAnchor.constraint(equalTo: view.topAnchor),
            frameTopRight.heightAnchor.constraint(equalTo: view.heightAnchor, multiplier: 0.5),
            frameTopRight.rightAnchor.constraint(equalTo: view.rightAnchor),
            frameTopRight.widthAnchor.constraint(equalTo: view.widthAnchor, multiplier: 0.5)
        ])

        let frameBottomLeft = UIView()
        frameBottomLeft.backgroundColor = .systemGreen
        view.addSubview(frameBottomLeft)
        frameBottomLeft.translatesAutoresizingMaskIntoConstraints = false
        NSLayoutConstraint.activate([
            frameBottomLeft.bottomAnchor.constraint(equalTo: view.bottomAnchor),
            frameBottomLeft.heightAnchor.constraint(equalTo: view.heightAnchor, multiplier: 0.5),
            frameBottomLeft.leftAnchor.constraint(equalTo: view.leftAnchor),
            frameBottomLeft.widthAnchor.constraint(equalTo: view.widthAnchor, multiplier: 0.5)
        ])

        let frameBottomRight = UIView()
        frameBottomRight.backgroundColor = .systemYellow
        view.addSubview(frameBottomRight)
        frameBottomRight.translatesAutoresizingMaskIntoConstraints = false
        NSLayoutConstraint.activate([
            frameBottomRight.bottomAnchor.constraint(equalTo: view.bottomAnchor),
            frameBottomRight.heightAnchor.constraint(equalTo: view.heightAnchor, multiplier: 0.5),
            frameBottomRight.rightAnchor.constraint(equalTo: view.rightAnchor),
            frameBottomRight.widthAnchor.constraint(equalTo: view.widthAnchor, multiplier: 0.5)
        ])

    }

}

图像:

模拟器输出

期望输出

EN

回答 3

Stack Overflow用户

发布于 2021-07-26 13:14:26

使用StackView来获得更好的代码和理解。

代码语言:javascript
运行
复制
class ViewController: UIViewController {
    
    override func viewDidLoad() {
        super.viewDidLoad()
        
        let topStack = UIStackView()
        topStack.axis = .horizontal
        topStack.distribution = .fillEqually
        
        let frameTopLeft = UIView()
        frameTopLeft.backgroundColor = .systemRed
        topStack.addArrangedSubview(frameTopLeft)
        
        
        let frameTopRight = UIView()
        frameTopRight.backgroundColor = .systemBlue
        topStack.addArrangedSubview(frameTopRight)
        
        
        let bottomStack = UIStackView()
        bottomStack.axis = .horizontal
        bottomStack.distribution = .fillEqually
        
        let frameBottomLeft = UIView()
        frameBottomLeft.backgroundColor = .systemGreen
        bottomStack.addArrangedSubview(frameBottomLeft)
        
        
        let frameBottomRight = UIView()
        frameBottomRight.backgroundColor = .systemYellow
        bottomStack.addArrangedSubview(frameBottomRight)
        
        frameBottomRight.translatesAutoresizingMaskIntoConstraints = false
        frameBottomRight.heightAnchor.constraint(equalToConstant: 200).isActive = true
        
        let mainStack = UIStackView()
        mainStack.axis = .vertical
        mainStack.addArrangedSubview(topStack)
        mainStack.addArrangedSubview(bottomStack)
        
        self.view.addSubview(mainStack)
        
        mainStack.translatesAutoresizingMaskIntoConstraints = false
        NSLayoutConstraint.activate([
            mainStack.topAnchor.constraint(equalTo: view.topAnchor),
            mainStack.heightAnchor.constraint(equalTo: view.heightAnchor),
            mainStack.leftAnchor.constraint(equalTo: view.leftAnchor),
            mainStack.widthAnchor.constraint(equalTo: view.widthAnchor)
        ])
    }
    
}

或者,您可以给每个底部视图提供相对约束。

代码语言:javascript
运行
复制
class ViewController: UIViewController {
    
    override func viewDidLoad() {
        super.viewDidLoad()
        let frameTopLeft = UIView()
        frameTopLeft.backgroundColor = .systemRed
        view.addSubview(frameTopLeft)
        frameTopLeft.translatesAutoresizingMaskIntoConstraints = false
        NSLayoutConstraint.activate([
            frameTopLeft.topAnchor.constraint(equalTo: view.topAnchor),
            //            frameTopLeft.heightAnchor.constraint(equalTo: view.heightAnchor, multiplier: 0.5), << Here
            frameTopLeft.leftAnchor.constraint(equalTo: view.leftAnchor),
            frameTopLeft.widthAnchor.constraint(equalTo: view.widthAnchor, multiplier: 0.5)
        ])
        
        let frameTopRight = UIView()
        frameTopRight.backgroundColor = .systemBlue
        view.addSubview(frameTopRight)
        frameTopRight.translatesAutoresizingMaskIntoConstraints = false
        NSLayoutConstraint.activate([
            frameTopRight.topAnchor.constraint(equalTo: view.topAnchor),
            //            frameTopRight.heightAnchor.constraint(equalTo: view.heightAnchor, multiplier: 0.5), << Here
            frameTopRight.rightAnchor.constraint(equalTo: view.rightAnchor),
            frameTopRight.widthAnchor.constraint(equalTo: view.widthAnchor, multiplier: 0.5)
        ])
        
        let frameBottomLeft = UIView()
        frameBottomLeft.backgroundColor = .systemGreen
        view.addSubview(frameBottomLeft)
        frameBottomLeft.translatesAutoresizingMaskIntoConstraints = false
        NSLayoutConstraint.activate([
            frameBottomLeft.topAnchor.constraint(equalTo: frameTopLeft.bottomAnchor), // << Here
            frameBottomLeft.bottomAnchor.constraint(equalTo: view.bottomAnchor),
            frameBottomLeft.heightAnchor.constraint(equalToConstant: 200), // << Here
            frameBottomLeft.leftAnchor.constraint(equalTo: view.leftAnchor),
            frameBottomLeft.widthAnchor.constraint(equalTo: view.widthAnchor, multiplier: 0.5)
        ])
        
        let frameBottomRight = UIView()
        frameBottomRight.backgroundColor = .systemYellow
        view.addSubview(frameBottomRight)
        frameBottomRight.translatesAutoresizingMaskIntoConstraints = false
        NSLayoutConstraint.activate([
            frameBottomRight.topAnchor.constraint(equalTo: frameTopRight.bottomAnchor), // << Here
            frameBottomRight.bottomAnchor.constraint(equalTo: view.bottomAnchor),
            frameBottomRight.heightAnchor.constraint(equalToConstant: 200), // << Here
            frameBottomRight.rightAnchor.constraint(equalTo: view.rightAnchor),
            frameBottomRight.widthAnchor.constraint(equalTo: view.widthAnchor, multiplier: 0.5)
        ])
    }
}
票数 1
EN

Stack Overflow用户

发布于 2021-07-26 13:35:31

您希望将底部视图的恒定高度约束设为200,然后将顶部视图的底座约束为底部视图的顶点。

您可能会发现将相关代码分组在一起很有帮助,并在执行过程中添加注释(为了使更清楚地了解您认为代码应该做什么)。

所以,试着这样做:

代码语言:javascript
运行
复制
override func viewDidLoad() {
    super.viewDidLoad()

    // create 4 views
    let frameTopLeft = UIView()
    let frameTopRight = UIView()
    let frameBottomLeft = UIView()
    let frameBottomRight = UIView()

    // set background colors
    frameTopLeft.backgroundColor = .systemRed
    frameTopRight.backgroundColor = .systemBlue
    frameBottomLeft.backgroundColor = .systemGreen
    frameBottomRight.backgroundColor = .systemYellow

    // set Autoresizing and add to view
    [frameTopLeft, frameTopRight, frameBottomLeft, frameBottomRight].forEach { v in
        v.translatesAutoresizingMaskIntoConstraints = false
        view.addSubview(v)
    }

    NSLayoutConstraint.activate([
        
        // top-left view constrained Top / Left / 50% Width
        frameTopLeft.topAnchor.constraint(equalTo: view.topAnchor),
        frameTopLeft.leftAnchor.constraint(equalTo: view.leftAnchor),
        frameTopLeft.widthAnchor.constraint(equalTo: view.widthAnchor, multiplier: 0.5),

        // top-right view constrained Top / Right / 50% Width
        frameTopRight.topAnchor.constraint(equalTo: view.topAnchor),
        frameTopRight.rightAnchor.constraint(equalTo: view.rightAnchor),
        frameTopRight.widthAnchor.constraint(equalTo: view.widthAnchor, multiplier: 0.5),

        // bottom-left view constrained Bottom / Left / 50% Width
        frameBottomLeft.bottomAnchor.constraint(equalTo: view.bottomAnchor),
        frameBottomLeft.leftAnchor.constraint(equalTo: view.leftAnchor),
        frameBottomLeft.widthAnchor.constraint(equalTo: view.widthAnchor, multiplier: 0.5),

        // bottom-right view constrained Bottom / Right / 50% Width
        frameBottomRight.bottomAnchor.constraint(equalTo: view.bottomAnchor),
        frameBottomRight.rightAnchor.constraint(equalTo: view.rightAnchor),
        frameBottomRight.widthAnchor.constraint(equalTo: view.widthAnchor, multiplier: 0.5),

        // bottom views, constant Height of 200-pts
        frameBottomLeft.heightAnchor.constraint(equalToConstant: 200.0),
        frameBottomRight.heightAnchor.constraint(equalToConstant: 200.0),
        
        // constrain bottoms of top views to tops of bottom views
        frameTopLeft.bottomAnchor.constraint(equalTo: frameBottomLeft.topAnchor),
        frameTopRight.bottomAnchor.constraint(equalTo: frameBottomRight.topAnchor),
        
    ])

}
票数 1
EN

Stack Overflow用户

发布于 2021-07-26 13:49:40

我会这样做:

代码语言:javascript
运行
复制
let frameTopLeft = UIView()
frameTopLeft.backgroundColor = .systemRed
view.addSubview(frameTopLeft)
frameTopLeft.translatesAutoresizingMaskIntoConstraints = false
NSLayoutConstraint.activate([
    frameTopLeft.topAnchor.constraint(equalTo: view.topAnchor),
    frameTopLeft.leftAnchor.constraint(equalTo: view.leftAnchor),
])

let frameTopRight = UIView()
frameTopRight.backgroundColor = .systemBlue
view.addSubview(frameTopRight)
frameTopRight.translatesAutoresizingMaskIntoConstraints = false
NSLayoutConstraint.activate([
    frameTopRight.topAnchor.constraint(equalTo: view.topAnchor),
    frameTopRight.rightAnchor.constraint(equalTo: view.rightAnchor),
    frameTopRight.leftAnchor.constraint(equalTo: frameTopLeft.rightAnchor),
    frameTopRight.widthAnchor.constraint(equalTo: frameTopLeft.widthAnchor)
])

let frameBottomLeft = UIView()
frameBottomLeft.backgroundColor = .systemGreen
view.addSubview(frameBottomLeft)
frameBottomLeft.translatesAutoresizingMaskIntoConstraints = false
NSLayoutConstraint.activate([
    frameBottomLeft.topAnchor.constraint(equalTo: frameTopLeft.bottomAnchor),
    frameBottomLeft.bottomAnchor.constraint(equalTo: view.bottomAnchor),
    frameBottomLeft.leftAnchor.constraint(equalTo: view.leftAnchor),
    frameBottomLeft.heightAnchor.constraint(equalToConstant: 200),
])

let frameBottomRight = UIView()
frameBottomRight.backgroundColor = .systemYellow
view.addSubview(frameBottomRight)
frameBottomRight.translatesAutoresizingMaskIntoConstraints = false
NSLayoutConstraint.activate([
    frameBottomRight.topAnchor.constraint(equalTo: frameTopRight.bottomAnchor),
    frameBottomRight.bottomAnchor.constraint(equalTo: view.bottomAnchor),
    frameBottomRight.rightAnchor.constraint(equalTo: view.rightAnchor),
    frameBottomRight.leftAnchor.constraint(equalTo: frameBottomLeft.rightAnchor),
    frameBottomRight.heightAnchor.constraint(equalTo: frameBottomLeft.heightAnchor),
    frameBottomRight.widthAnchor.constraint(equalTo: frameBottomLeft.widthAnchor),
])

与其他人的主要区别是尽可能地去掉常量。

  1. 你的底层视图应该是200吗?添加单个200约束,并使第二个视图的高度等于第一个约束。
  2. ,而不是使宽度等于父级的50%,您可以使左宽等于右一

它使您的代码易于维护,减少了需要编辑的位置。

票数 1
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/68530352

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档