【问题标题】:iOS | Layout constraint error when adding two views programaticallyiOS |以编程方式添加两个视图时出现布局约束错误
【发布时间】:2023-03-30 01:44:02
【问题描述】:

我有一段代码可以并排显示图像视图和 UILabel。它根据提供的约束按预期显示,但控制台中有很多警告

这是错误

[LayoutConstraints] Unable to simultaneously satisfy constraints.
    Probably at least one of the constraints in the following list is one you don't want. 
Try this: 
    (1) look at each constraint and try to figure out which you don't expect; 
    (2) find the code that added the unwanted constraint or constraints and fix it. 
(
    "<NSLayoutConstraint:0x6000003d0190 V:|-(0)-[UIImageView:0x7faa7401b940]   (active, names: '|':Movies_TODO.MovieViewCell:0x7faa7402caa0'custom' )>",
    "<NSLayoutConstraint:0x6000003d05a0 UIImageView:0x7faa7401b940.bottom == Movies_TODO.MovieViewCell:0x7faa7402caa0'custom'.bottom   (active)>",
    "<NSLayoutConstraint:0x6000003d0640 UIImageView:0x7faa7401b940.height == 100   (active)>",
    "<NSLayoutConstraint:0x6000003e7070 'UIView-Encapsulated-Layout-Height' Movies_TODO.MovieViewCell:0x7faa7402caa0'custom'.height == 100.5   (active)>"
)

将尝试通过打破约束来恢复

这是我的一段代码

self.addSubview(movieImageView)
self.addSubview(titleLabel)

movieImageView.topAnchor.constraint(equalTo: self.topAnchor).isActive = true
movieImageView.leadingAnchor.constraint(equalTo: self.leadingAnchor).isActive = true
movieImageView.bottomAnchor.constraint(equalTo: self.bottomAnchor).isActive = true
movieImageView.widthAnchor.constraint(equalToConstant: 100).isActive = true

movieImageView.heightAnchor.constraint(equalToConstant: 100).isActive = true

titleLabel.leadingAnchor.constraint(equalTo: movieImageView.trailingAnchor, constant: 20).isActive = true
titleLabel.topAnchor.constraint(equalTo: self.topAnchor).isActive = true
titleLabel.trailingAnchor.constraint(equalTo: self.trailingAnchor).isActive = true
titleLabel.bottomAnchor.constraint(equalTo: self.bottomAnchor).isActive = true

【问题讨论】:

    标签: ios swift iphone autolayout


    【解决方案1】:

    您的movieImageView 具有类似height equal to 100height equal to super view's height 的约束(这是因为您添加了顶部和底部锚约束)。


    1 - 如果你想从上到下设置movieImageView,只需删除movieImageView.heightAnchor.constraint(equalToConstant: 100).isActive = true


    2 - 如果您想将movieImageView 的高度始终设置为 100,只需删除您不想为 movieImageView 设置的行 ->

    // if you want to stick your imageView to bottom delete this
    movieImageView.topAnchor.constraint(equalTo: self.topAnchor).isActive = true
    
    // if you want to stick your imageView to top delete this
    movieImageView.bottomAnchor.constraint(equalTo: self.bottomAnchor).isActive = true
    

    UIStackView

    • 如果您想创建一个TableViewCell 具有左侧图像和右侧标签,您可以使用StackView,您可以不受任何限制地为所欲为。

    创建UIStackView

    let stackView = UIStackView()
    

    添加您的movieImageViewtitleLabel

    stackView.addArrangedSubviews(movieImageView, titleLabel)
    stackView.axis = .horizontal
    stackView.spacing = 20.0
    

    将您的stackView 添加到super.view

    self.addSubview(stackView)
    stackView.translatesAutoresizingMaskIntoConstraints = false
    
    stackView.topAnchor.constraint(equalTo: self.topAnchor).isActive = true
    stackView.bottomAnchor.constraint(equalTo: self.bottomAnchor).isActive = true
    
    stackView. trailingAnchor.constraint(equalTo: self. trailingAnchor).isActive = true
    stackView.leadingAnchor.constraint(equalTo: self.leadingAnchor).isActive = true
    

    如果你想设置movieImageView的图片宽度,你应该设置movieImageViewContent Hugging Priority

    movieImageView.setContentHuggingPriority(.defaultHigh, for: .horizontal)
    

    如果你想设置titleLabel的宽度从它的文本并且比imageView更耐,你应该设置titleLabelCompression Resistance Priority

    titleLabel.setContentCompressionResistancePriority(.defaultHigh, for: .horizontal)
    

    奖金

    Intrinsic Content Size

    UIStackView Guide

    UIStackView Example of Hackingwithswift

    【讨论】:

    • 如果我删除任何约束,视图就会扭曲。顺便说一句,这是一个表格视图单元格
    • 图像的大小很大,即使添加到堆栈视图中也会扭曲视图。如何将图像大小包含到特定的宽度和高度
    • 如果我添加高度约束并移除底部锚点到堆栈视图,视图仍然失真
    • 您的问题是关于约束错误的,请在对 (stackView) 或您的 UI 相关问题进行一些研究之后再问一个关于您的 UI 的问题。请考虑这个:stackoverflow.com/help/how-to-ask。
    【解决方案2】:

    你已经设置了你的movieImageView的底部锚点和顶部锚点,它们间接表示你的movieImageView的高度。

    设置高度后,您再次将高度更改为某个恒定值 100。

    为避免此警告删除

    movieImageView.bottomAnchor.constraint(equalTo: self.bottomAnchor).isActive = true
    

    此警告是由于对同一属性的冗余约束。

    你试试下面的约束

        movieImageView.topAnchor.constraint(equalTo: self.view.safeAreaLayoutGuide.topAnchor).isActive = true
        movieImageView.leadingAnchor.constraint(equalTo: self.view.leadingAnchor).isActive = true
        movieImageView.widthAnchor.constraint(equalToConstant: 100).isActive = true
        movieImageView.heightAnchor.constraint(equalToConstant: 100).isActive = true
    
        titleLabel.leadingAnchor.constraint(equalTo: movieImageView.trailingAnchor, constant: 20).isActive = true
        titleLabel.topAnchor.constraint(equalTo: self.view.safeAreaLayoutGuide.topAnchor).isActive = true
        titleLabel.trailingAnchor.constraint(equalTo: self.view.trailingAnchor).isActive = true
        titleLabel.bottomAnchor.constraint(equalTo: self.movieImageView.bottomAnchor).isActive = true
    

    这个约束的结果是

    【讨论】:

    • 如果我删除任何约束,视图就会扭曲。顺便说一句,这是一个表格视图单元格
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2016-10-10
    • 1970-01-01
    • 1970-01-01
    • 2014-04-22
    • 1970-01-01
    相关资源
    最近更新 更多