AutoLayout - 多控件自适应布局

intrinsicContentSize详解

对于UILabel, UIimageView,UIButton等控件都有intrinsicContentSize的属性

  • intrinsic Content Size: 固有内部大小 ,拥有此属性的控件在设置约束时,如果没有设置控件的大小,就会根据此属性来设置控件的大小
    • 比如UILabel设置约束时,只需要指定位置,就能根据文本内容和字体大小计算出label的大小

在水平/垂直并行布局中,两个控件的intrinsicSize(固有大小)比父控件的宽/高的数值大,父控件就没有办法完全展示完成,就只能通过压缩其中一个控件来实现。如果我们想要想要指定某个控件来进行自适应,压缩另外一个控件,就需要修改控件的约束优先级,以下两个方法修改优先级

  • setContentCompressionResistancePriority(抗压缩)
    • 数值越低,在宽/高度不够下,就会被压缩
    • 常见默认值:UILayoutPriority.defaultHigh = 750
swift 复制代码
    open func setContentCompressionResistancePriority(_ priority: UILayoutPriority, for axis: NSLayoutConstraint.Axis)
  • setContentHuggingPriority (抗拉伸)
    • 数组越低。在宽/高度多余的情况下就会被拉伸
    • 常见默认值:UILayoutPriority.defaultLow = 250
swift 复制代码
    open func setContentHuggingPriority(_ priority: UILayoutPriority, for axis: NSLayoutConstraint.Axis)

使用场景:

  • contentCompressionResistancePriority (抗压缩)

    swift 复制代码
        lazy var label1: UILabel = {
            let label = UILabel()
            label.text = "可能会显示省略号的label1"
            return label
        }()
      
        lazy var label2: UILabel = {
            let label = UILabel()
            label.text = "优先自适应的宽度的label2"
            return label
        }()
        
        view.addSubview(label1)
        view.addSubview(label2)
     
        label1.snp.makeConstraints { make in
            make.left.top.bottom.equalTo(0)
        }
          
        label2.snp.makeConstraints { make in
            make.right.top.bottom.equalTo(0)
            make.left.equalTo(self.label1.snp.right).offset(5)
        }
    • 按照上面的代码显示会label1正常显示,label2被压缩,如果需求是保证label2正常显示,需要调用setContentCompressionResistancePriority 设置约束优先级
    less 复制代码
        label1.setContentCompressionResistancePriority(.defaultLow, for: .horizontal)
        label2.setContentCompressionResistancePriority(.defaultHigh, for: .horizontal)
  • contentHuggingPriority(抗拉伸)

    swift 复制代码
        lazy var label1: UILabel = {
            let label = UILabel()
            label.text = "label1"
            return label
         }()
      
        lazy var label2: UILabel = {
            let label = UILabel()
            label.text = "被拉伸的label2"
            return label
          }()
      
        view.addSubview(label1)
        view.addSubview(label2)
     
        label1.snp.makeConstraints { make in
            make.left.top.bottom.equalTo(0)
        }
          
        label2.snp.makeConstraints { make in
            make.right.top.bottom.equalTo(0)
            make.left.equalTo(self.label1.snp.right).offset(5)
        }
        
    • 按照上面的代码显示会label1会被拉伸,label2正常显示,如果需求是label1正常显示,拉伸label2,需要调用setContentHuggingPriority 设置约束优先级
    less 复制代码
        label1.setContentHuggingPriority(.defaultHigh, for: .horizontal)
        label2.setContentHuggingPriority(.defaultLow, for: .horizontal)
相关推荐
传奇开心果编程2 小时前
【Compose Multiplatform 跨端开发学与练】第7课 平台适配与互操作
android·windows·学习·ui·ios·kotlin·composer
传奇开心果编程7 小时前
【Compose Multiplatform 跨端开发学与练】第5课 网络与数据层
android·网络·学习·ui·ios·kotlin·composer
茶底世界之下8 小时前
视频预览切换为何会闪回旧帧:用 generation + mode identity 管住异步回调
ios·swift
老李IT笔记10 小时前
从备份恢复会把管理状态带回来吗:iOS 27 之后答案变了|MDM.Plus
ios·智能手机
谢亮_vipxieliang10 小时前
Go 接口设计原则核心知识点
开发语言·ios·golang
Hello_Pyhx14 小时前
iPhoneMirror:把 iPhone 接入 Windows,先分清投屏与反控
windows·ios·iphone
茶底世界之下20 小时前
类型擦除之后,Metal 滤镜组合为什么不能只执行一个 Filter?
ios·swift
传奇开心果编程1 天前
【SwiftUI提高练中学】第8课 网络层架构:拦截器、重试、缓存与离线优先
学习·macos·ui·ios·swiftui
传奇开心果编程1 天前
【Compose Multiplatform 跨端开发学与练】第3课 布局与组件
android·windows·学习·ui·ios·kotlin·composer
tink1 天前
告别 Xcode IDE:用 VS Code + SweetPad + XcodeGen 开发 iOS 应用的完整指南
ios·swiftui·xcode