ios - 子类化 NSLayoutConstraint,常量的奇怪行为

标签 ios nslayoutconstraint

无论您目前从事什么项目,只需

  1. 在 UIView 中的任何屏幕上放置

  2. 只需添加一个宽度限制(666 或任何合适的),

  3. 将约束的自定义类更改为Constrainty

  4. 运行应用,

enter image description here

这怎么可能?

它实际上是否在“类初始化之前”或类似的情况下调用常量的值?

怎么会发生,怎么解决?

起初,我将这两个变量作为 @IBInspectable,令我惊讶的是它们根本不起作用。但后来我将它们更改为普通的 let 常量 - 但这是行不通的!

class Constrainty: NSLayoutConstraint {

    let percentageWidth: CGFloat = 77 // nothing up my sleeve
    let limitWidth: CGFloat = 350

    override var constant: CGFloat {

        get { return teste() }
        set { super.constant = newValue }
    }

    func teste()->CGFloat {

        print("\n\n HERE WE GO \(percentageWidth) \(limitWidth) \n\n")

        if let sw = (firstItem as? UIView)?.superview?.bounds.width {

            let w = sw * ( percentageWidth / 100.0 )
            let r = w > limitWidth ? limitWidth : w
            print("result is \(r) \n\n")
            return r
        }

        return 50
    }

}

最佳答案

我不认为继承 NSLayoutConstraint 是个好主意。我不认为它被设计为在 Apple 之外进行子类化。

不管怎样,问题是NSLayoutConstraint 符合NSCoding 协议(protocol),但是没有在header 中声明它符合NSCoding文件。正因为如此,Swift 不知道 NSLayoutConstraint 可以通过 -[NSLayoutConstraint initWithCoder:] 进行初始化,所以它不会生成 initWithCoder 的重写: 初始化您在子类中添加的实例变量。

这是修复它的方法。

首先,如果您的项目没有桥接头,请添加一个。添加一个最简单的方法是在您的项目中创建一个新的 Objective-C 类,接受 Xcode 提供的创建桥接 header 的提议,然后删除 .h.m它为类(class)创建的文件(但保留桥接头)。

然后,在桥接 header 中,声明NSLayoutConstraint 符合NSCoding:

//
//  Use this file to import your target's public headers that you would like to expose to Swift.
//

@import UIKit;

@interface NSLayoutConstraint (MyProject) <NSCoding>
@end

最后,在您的 Constrainty 类中,像这样覆盖 init(coder:):

required init(coder decoder: NSCoder) {
    super.init(coder: decoder)!
}

等等:

 HERE WE GO 77.0 350.0 


result is 246.4 

关于ios - 子类化 NSLayoutConstraint,常量的奇怪行为,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/48101160/

相关文章:

objective-c - 自动布局 : how does fittingSize work exactly?

objective-c - CCLabelTTF 没有出现

iphone - 使用 Core Graphics 绘制图形线

ios - Apple swift 2.1 中的数组升级

ios - 使用 Phonegap 安装 Cordova 插件 - no Cordova.plist

ios - NSLayoutConstraint 中断

iphone - 当UITabBarController加载而不是在ViewController上时添加角标(Badge)

ios - 以编程方式添加约束不尊重优先级

objective-c - iOS 在设备旋转时更改自动布局约束

swift - 更新通过 Swift 3 中的 NSLayout 设置的 UITextView 大小