【问题标题】:Unable to simultaneously satisfy constraints - No constraints in place无法同时满足约束 - 没有约束
【发布时间】:2012-12-28 22:14:07
【问题描述】:

我已经完成并删除了每个用户限制,但在旋转设备后我仍然收到以下错误ONLY。我完全不知道为什么。有人有什么想法吗?

2013-01-14 21:30:31.363 myApp[35869:c07] 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. (Note: If you're seeing NSAutoresizingMaskLayoutConstraints that you don't understand, refer to the documentation for the UIView property translatesAutoresizingMaskIntoConstraints) 
(
    "<NSAutoresizingMaskLayoutConstraint:0x84543d0 h=--& v=--& V:[UIView:0xa330270(768)]>",
    "<NSLayoutConstraint:0xa338350 V:[UIView:0xa331260]-(-1)-|   (Names: '|':UIView:0xa330270 )>",
    "<NSLayoutConstraint:0xa338390 V:|-(841)-[UIView:0xa331260]   (Names: '|':UIView:0xa330270 )>"
)

Will attempt to recover by breaking constraint 
<NSLayoutConstraint:0xa338350 V:[UIView:0xa331260]-(-1)-|   (Names: '|':UIView:0xa330270 )>

Break on objc_exception_throw to catch this in the debugger.
The methods in the UIConstraintBasedLayoutDebugging category on UIView listed in <UIKit/UIView.h> may also be helpful.

【问题讨论】:

标签: ios ipad autoresizingmask nslayoutconstraint


【解决方案1】:

这一行解决了我在 uitableviewCell 中的上述日志时遇到的问题

func tableView(_ tableView: UITableView, heightForRowAt indexPath: IndexPath) -> CGFloat {
    return UITableView.automaticDimension > CellHeight.rowHeight44 ? UITableView.automaticDimension : CellHeight.rowHeight44
}

【讨论】:

    【解决方案2】:

    在调试控制台中生成消息“无法同时满足约束”的问题,在 XCode 9.4 中也遇到过。
    在我在 iPad 模拟器上的特定实例中,该消息将生成:
    1) 仅当将焦点放在特定 UITextField 上时。
    2) 即使删除了所有视图约束。
    2) 即使所有视图约束都“重置为建议的约束”。

    但是,当打开软件键盘进行显示时,不会生成该消息。 因此,我应该在这个问题上花费多少时间,在我的实例中,只有在关闭软件键盘时才会生成。

    【讨论】:

      【解决方案3】:

      我遇到了这个问题,花了我 2 天的时间找出问题的根源......

      如果您在代码中以编程方式打开情节提要,请确保您这样做:

      UIStoryboard *story = [UIStoryboard storyboardWithName:@"MovieMaker" bundle:nil];
          UIViewController *vc = [story instantiateInitialViewController];
          //this causes layout to break [self presentViewController:vc animated:YES completion:nil];
          [self showViewController:vc sender:nil];
      

      我正在使用注释行(使用 presentViewController),并且发生了方向错误,引发了不是我的约束的约束冲突......更改为 showViewController 所有约束冲突都消失了,方向工作......(我真的不知道为什么它适用于表演而不是在场......仍然认为它是......外星人......)

      【讨论】:

        【解决方案4】:

        对我来说,这个错误是在我给tableView.estimatedRowHeight = UITableViewAutomaticDimension时吐出的

        这应该是tableView.estimatedRowHeight = "Some hardcoded value"

        【讨论】:

          【解决方案5】:

          值得了解基础知识,并了解 Apple/Xcode 试图通过日志告诉您的内容

          H = Horizontal constraint(for leading and Trailing)
          V = Vertical constraint(top and bottom edge)
          h = height
          w = width
          
          TopEdge    -> V:|-(points)-[VIEW:memoryAddress] 
          BottomEdge -> V:[VIEW:memoryAddress]-(points)-|
          Leading    -> H:|-(points)-[VIEW:memoryAddress] 
          Trailing   -> H:[VIEW:memoryAddress] -(points)-|
          height     -> h= --& v=--& V:[VIEW:memoryAddress((points)] 
          width      -> VIEW:memoryAddress.width == points 
          between    -> H:[VIEW 1]-(51)-[VIEW 2] 
          

          一旦你理解了这一点,阅读你的具体错误就很容易了

          【讨论】:

            【解决方案6】:

            YourConstraintView.translatesAutoresizingMaskIntoConstraints = NO;

            为我做的。

            【讨论】:

              【解决方案7】:

              一个音符。如果您使用个人热点连接进行测试,您会在日志中收到此错误,并且热点状态栏位于顶部。它摆脱了约束。

              希望这对某人有所帮助..让我发疯了。

              【讨论】:

              • 嘿 mtb,这个警告应该被处理还是预期的?我的应用程序看起来恰到好处,我不知道是否应该修复或忽略它?
              【解决方案8】:

              感谢http://useYourLoaf.com 提供完整的解决方案:

              http://useyourloaf.com/blog/using-identifiers-to-debug-autolayout.html

              我在 WWDC 2015 会议中发现的关于自动布局的快速提示,有助于调试约束问题

              如果您使用过 Auto Layout,您将熟悉 Xcode 在出错时吐出的日志。为了创建一个示例,我修改了my Stack View sample code,并为每个图像添加了一个约束,为它们提供了 240 的固定宽度(我们将看到这不是一个好主意)。

              这适用于 iPad 等常规宽度视图,但对于紧凑宽度视图(如 iPhone 纵向视图)来说太宽了。运行时的控制台日志读起来并不有趣。跳过样板文本,您将获得有问题的约束列表:

              "<NSLayoutConstraint:0x7fc1ab520360 H:[UIImageView:0x7fc1ab532650(240)]>",
              "<NSLayoutConstraint:0x7fc1ab536ef0 H:[UIImageView:0x7fc1ab537380(240)]>",
              "<NSLayoutConstraint:0x7fc1ab545cc0 UIView:0x7fc1ab53d870.trailingMargin == UIStackView:0x7fc1ab53dae0.trailing>",
              "<NSLayoutConstraint:0x7fc1ab545d10 UIStackView:0x7fc1ab53dae0.leading == UIView:0x7fc1ab53d870.leadingMargin>",
              "<NSLayoutConstraint:0x7fc1ab54e240 'UISV-alignment' UIStackView:0x7fc1ab53dc70.centerX == UIStackView:0x7fc1ab531a10.centerX>",
              "<NSLayoutConstraint:0x7fc1ab5167c0 'UISV-canvas-connection' UIStackView:0x7fc1ab531a10.leading == UIImageView:0x7fc1ab532650.leading>",
              "<NSLayoutConstraint:0x7fc1ab54ad80 'UISV-canvas-connection' H:[UIImageView:0x7fc1ab537380]-(0)-|   (Names: '|':UIStackView:0x7fc1ab531a10 )>",
              "<NSLayoutConstraint:0x7fc1ab5397d0 'UISV-canvas-connection' UIStackView:0x7fc1ab53dae0.leading == _UILayoutSpacer:0x7fc1ab54c3c0'UISV-alignment-spanner'.leading>",
              "<NSLayoutConstraint:0x7fc1ab54a4a0 'UISV-canvas-connection' UIStackView:0x7fc1ab53dae0.centerX == UIStackView:0x7fc1ab53dc70.centerX>",
              "<NSLayoutConstraint:0x7fc1ab54b110 'UISV-spacing' H:[UIImageView:0x7fc1ab532650]-(16)-[UIImageView:0x7fc1ab537380]>",
              "<NSLayoutConstraint:0x7fc1ab548210 'UISV-spanning-boundary' _UILayoutSpacer:0x7fc1ab54c3c0'UISV-alignment-spanner'.leading <= UIStackView:0x7fc1ab531a10.leading>",
              "<NSLayoutConstraint:0x7fc1ab551690 'UIView-Encapsulated-Layout-Width' H:[UIView:0x7fc1ab53d870(375)]>"
              

              然后,日志会告诉您它已决定打破上述哪些限制:

              Will attempt to recover by breaking constraint 
              <NSLayoutConstraint:0x7fc1ab536ef0 H:[UIImageView:0x7fc1ab537380(240)]>
              

              日志输出使用自动布局可视化格式语言,但很难从系统创建的约束中挑选出我的约束。对于堆栈视图尤其如此,堆栈视图的设计旨在为您创建大部分约束。在这个简单的例子中,我知道我刚刚添加的固定宽度约束破坏了一些东西,但从日志中很难看出这一点,而且视图越复杂,就越难。

              向约束添加标识符

              如果您为每个约束添加一个标识符,日志会更容易理解(NSLayoutConstraint 从 iOS 7 开始就有一个标识符属性)。在 Interface Builder 中找到约束并在属性检查器中添加标识符(我使用 $ 作为前缀/后缀以使它们在日志中脱颖而出):

              2015 年 8 月 18 日更新:正如 cmets 中所指出的,标识符只能在从 Xcode 7 开始的 Interface Builder 中编辑。它在 Xcode 6.4 中不可见。

              如果在代码中添加约束:

              constraint.identifier = "$HeartImageFixedWidth$"
              

              如果您使用的是使用约束数组的可视化格式语言,那就更棘手了。例如,考虑为心脏图像视图创建固定宽度约束的 Swift 代码片段:

              let heartWidth = NSLayoutConstraint.constraintsWithVisualFormat("[heart(240)]", 
                               options:[], metrics:nil, views:viewsDictionary)
              

              由于 heartWidth 是 [NSLayoutConstraint] 类型的数组,因此设置标识符需要做更多工作:

              for constraint in heartWidth {
                constraint.identifier = "$HeartImageFixedWidth$"
              }
              heartImage.addConstraints(heartWidth)
              

              为我的约束设置了标识,现在可以更容易地在日志文件中找到它们(参见前四行):

              "<NSLayoutConstraint:0x7f92a305aeb0 '$ContainerStackViewLeading$' UIStackView:0x7f92a3053220.leading == UIView:0x7f92a3052fb0.leadingMargin + 32>",
              "<NSLayoutConstraint:0x7f92a305b340 '$ContainerStackViewTrailing$' UIView:0x7f92a3052fb0.trailingMargin == UIStackView:0x7f92a3053220.trailing + 32>",
              "<NSLayoutConstraint:0x7f92a301cf20 '$HeartImageFixedWidth$' H:[UIImageView:0x7f92a3047ef0(240)]>",
              "<NSLayoutConstraint:0x7f92a3009be0 '$StarImageFixedWidth$' H:[UIImageView:0x7f92a304d190(240)]>",
              "<NSLayoutConstraint:0x7f92a3060cc0 'UISV-alignment' UIStackView:0x7f92a30533b0.centerX == UIStackView:0x7f92a30472b0.centerX>",
              "<NSLayoutConstraint:0x7f92a301c590 'UISV-canvas-connection' UIStackView:0x7f92a30472b0.leading == UIImageView:0x7f92a3047ef0.leading>",
              "<NSLayoutConstraint:0x7f92a305f680 'UISV-canvas-connection' H:[UIImageView:0x7f92a304d190]-(0)-|   (Names: '|':UIStackView:0x7f92a30472b0 )>",
              "<NSLayoutConstraint:0x7f92a3064190 'UISV-canvas-connection' UIStackView:0x7f92a3053220.leading == _UILayoutSpacer:0x7f92a30608a0'UISV-alignment-spanner'.leading>",
              "<NSLayoutConstraint:0x7f92a30415d0 'UISV-canvas-connection' UIStackView:0x7f92a3053220.centerX == UIStackView:0x7f92a30533b0.centerX>",
              "<NSLayoutConstraint:0x7f92a305fa10 'UISV-spacing' H:[UIImageView:0x7f92a3047ef0]-(16)-[UIImageView:0x7f92a304d190]>",
              "<NSLayoutConstraint:0x7f92a30508c0 'UISV-spanning-boundary' _UILayoutSpacer:0x7f92a30608a0'UISV-alignment-spanner'.leading <= UIStackView:0x7f92a30472b0.leading>",
              "<NSLayoutConstraint:0x7f92a3063240 'UIView-Encapsulated-Layout-Width' H:[UIView:0x7f92a3052fb0(375)]>"
              

              系统选择打破哪些约束也更加清晰:

              Will attempt to recover by breaking constraint 
              <NSLayoutConstraint:0x7f92a3009be0 '$StarImageFixedWidth$' H:[UIImageView:0x7f92a304d190(240)]>
              

              向约束中添加标识符并非不费吹灰之力,但下次您必须对复杂布局的调试日志进行排序时,它可以得到回报。

              进一步阅读

              【讨论】:

                【解决方案9】:

                我已经解决了这个问题,即从 xib 文件中删除所有 translatesAutoresizingMaskIntoConstraints 属性(将 xib 作为源代码打开)。

                【讨论】:

                • 也可以在代码中设置 self.dimmingView.translatesAutoresizingMaskIntoConstraints = NO
                • 这就是为我解决的问题!就我而言,以编程方式将translatesAutoresizingMaskIntoConstraints 设置为YES 似乎可行,但我进入了控制台Unable to simultaneously satisfy constraints(尽管它实际上看起来不错)。我以 XML 格式打开,看到很多 translatesAutoresizingMaskIntoConstraints="NO"(我怀疑是在故事板之间复制的结果,其中只有一个启用了 AutoLayout)。从 XML 中删除之后 - 不再有警告! (实际上我什至不需要以编程方式做任何事情,YES 是默认值)。谢谢!
                【解决方案10】:

                我想这不是一个常见的错误,但我以一种外行的方式解决了它。我收到了像上面这样的神秘信息。为了理解它,我创建了虚拟视图类并将其附加到我的故事板中的视图中。例如,如果我有一个 UIView,我创建了一个名为 AddressView 的类并将其附加到故事板中的这个视图。它有点耗时,但它对我有用。在那之后,我得到了类名,而不是对象 ID,这帮助我将很容易导致问题的视图归零。我的错误信息现在已阅读,

                2013-07-02 04:16:20.434 Myproject [2908:c07] 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. (Note: If you're seeing NSAutoresizingMaskLayoutConstraints that you don't understand, refer to the documentation for the UIView property translatesAutoresizingMaskIntoConstraints) 
                (
                    "<NSLayoutConstraint:0x9edeae0 V:|-(0)-[AddressView:0x143ee020]   (Names: '|':MainView:0x129eb6a0 )>",
                    "<NSAutoresizingMaskLayoutConstraint:0x11e998c0 h=--& v=--& V:[MainView:0x129eb6a0(704)]>",
                    "<NSLayoutConstraint:0x156720b0 V:[AddressView:0x143ee020]-(896)-|   (Names: '|':MainView:0x129eb6a0 )>"
                )
                

                在这里您可以看到,我的视图 MainView 和 Address 视图的名称导致了问题。

                为了解决这个问题,我只是移动了我的子视图(在本例中为地址视图)并将其重新定位。我认为问题开始于我在 Xcode 4.5 中混合使用新的 Automatic Layour 和旧技能或手动定位视图。

                无论如何,不​​确定是不是运气比勤奋更重要,但这可能是一种不同的调试方式。也许这对某人有帮助!

                【讨论】:

                  【解决方案11】:

                  让我们一一来看看。

                  "&lt;NSAutoresizingMaskLayoutConstraint:0x84543d0 h=--&amp; v=--&amp; V:[UIView:0xa330270(768)]&gt;"

                  这是说视图 0xa330270 (A) 必须是 768 点高。

                  "&lt;NSLayoutConstraint:0xa338350 V:[UIView:0xa331260]-(-1)-| (Names: '|':UIView:0xa330270 )&gt;"

                  这就是说view 0xa331260 (B)的底边距离A的底边必须有-1的间隙,这是它的superview。

                  "&lt;NSLayoutConstraint:0xa338390 V:|-(841)-[UIView:0xa331260] (Names: '|':UIView:0xa330270 )&gt;"

                  这就是说 B 的上边缘必须与其父视图 A 的顶部相距 841 点。

                  这三件事不可能都是真的 - A 不能是 768 点高,并且包含一个子视图,其顶部边缘从顶部插入 841 点,从顶部插入 -1 点底部。您在哪里定义了这些约束?

                  您还没有说出您要实现的布局,但看起来您可能在超级视图上有一个自动调整大小的蒙版,当您旋转设备时,它会阻止它的高度变化。据我所知,仅当您以编程方式添加视图时才会出现自动调整大小约束,因为情节提要或 xib 要么是全自动布局,要么不是。除非您正在执行诸如将自动布局视图(从笔尖加载?)添加到非自动布局笔尖的另一个视图之类的操作?

                  【讨论】:

                  • 原来高度约束被设置以及一个约束告诉它伸展到超级视图。为了解决这个问题,我刚刚摆脱了高度限制。谢谢!
                  • 我们如何摆脱高度限制?我也面临同样的问题。
                  • 有什么方法可以判断 0xa331260 实际指的是什么视图?
                  • @thumbtackthief 你可以po它或者使用Chisel(Facebook调试工具,非常好)让它在UI中闪烁,或者打开视图调试器并比较地址。
                  • @jrturton - 您能否提供一个示例 Chisel 命令,根据上述信息(即 UIView 的内存地址)在 UI 中制作视图闪烁?
                  猜你喜欢
                  • 1970-01-01
                  • 1970-01-01
                  • 2016-02-09
                  • 2020-11-15
                  • 1970-01-01
                  • 2014-10-27
                  • 2014-06-19
                  • 1970-01-01
                  • 1970-01-01
                  相关资源
                  最近更新 更多