使用 ib 操作删除尾随约束 - Swift
Remove trailing constraint with ib action- Swift
我创建了一个顶部有分段控制器的视图控制器。当您点击分段控制器时,它只是作为一个按钮,并通过调用将其更改为相应尺寸的函数来更改控制器内部的 imageView 是纵向模式还是横向模式。
我的问题是我改变它的方式是我只是向 imageView 添加了约束,但是当切换到横向模式时,尾随约束没有被删除。
并且,这是将 imageView 更改为纵向的代码(imageView 已经具有顶部和底部约束):
func portraitContraints() {
NSLayoutConstraint.activate ([
// the trailing contraint
imageView.trailingAnchor.constraint(equalTo: viewContainer.safeAreaLayoutGuide.trailingAnchor, constant: -75), // this is the contraints that doesn't get removed
// the leading contraints
imageView.leadingAnchor.constraint(equalTo: viewContainer.safeAreaLayoutGuide.leadingAnchor, constant: 75
])
// the aspect ratio contraints
imageView.addConstraint(NSLayoutConstraint(item: self.imageView as Any,attribute: .height,relatedBy: .equal,toItem: self.imageView,attribute: .width,multiplier: (4.0 / 3.0),constant: 0))
}
这是将 imageView 更改为横向的代码:
func landscapeContraints() {
NSLayoutConstraint.activate([
// the trailing contraints
imageView.trailingAnchor.constraint(equalTo: viewContainer.safeAreaLayoutGuide.trailingAnchor, constant: 0),
// the leading contraint
imageView.leadingAnchor.constraint(equalTo: viewContainer.safeAreaLayoutGuide.leadingAnchor, constant: 0)
])
// the aspect ratio contraint
imageView.addConstraint(NSLayoutConstraint(item: self.imageView as Any,attribute: .height,relatedBy: .equal,toItem: self.imageView,attribute: .width,multiplier: (9.0 / 16.0),constant: 0))
}
这段代码就像一个魅力,除了唯一的问题是纵向模式的尾随约束将保留在视图上(-75 常量约束)。
横向看起来像这样(注意右边的常量是-75):
肖像看起来像这样:
尝试在添加新约束之前删除旧约束。这是有关如何执行此操作的 Apple 文档:https://developer.apple.com/documentation/uikit/uiview/1622593-removeconstraints
您可以通过添加具有不同优先级的both比率约束来实现。更改优先级以使所需比率“有效”。
并且,创建前导和尾随约束变量,以便您可以更改它们的常量。
这是一个简单的例子:
class ToggleConstraintsViewController: UIViewController {
let imageView = UIImageView()
var isPortrait: Bool = true
var portraitConstraint: NSLayoutConstraint!
var landscapeConstraint: NSLayoutConstraint!
var leadingConstraint: NSLayoutConstraint!
var trailingConstraint: NSLayoutConstraint!
override func viewDidLoad() {
super.viewDidLoad()
imageView.backgroundColor = .blue
imageView.translatesAutoresizingMaskIntoConstraints = false
view.addSubview(imageView)
let g = view.safeAreaLayoutGuide
portraitConstraint = imageView.heightAnchor.constraint(equalTo: imageView.widthAnchor, multiplier: 4.0/3.0)
portraitConstraint.priority = .defaultHigh
landscapeConstraint = imageView.heightAnchor.constraint(equalTo: imageView.widthAnchor, multiplier: 9.0/16.0)
landscapeConstraint.priority = .defaultLow
leadingConstraint = imageView.leadingAnchor.constraint(equalTo: g.leadingAnchor, constant: 75.0)
trailingConstraint = imageView.trailingAnchor.constraint(equalTo: g.trailingAnchor, constant: -75.0)
NSLayoutConstraint.activate([
// y-position constraint does not change
imageView.centerYAnchor.constraint(equalTo: g.centerYAnchor),
// these will have their priorities changed when desired
portraitConstraint,
landscapeConstraint,
// these will have their constants changed when desired
leadingConstraint,
trailingConstraint,
])
let t = UITapGestureRecognizer(target: self, action: #selector(self.toggleOrientation(_:)))
view.addGestureRecognizer(t)
}
@objc func toggleOrientation(_ g: UITapGestureRecognizer) -> Void {
isPortrait.toggle()
portraitConstraint.priority = isPortrait ? .defaultHigh : .defaultLow
landscapeConstraint.priority = isPortrait ? .defaultLow : .defaultHigh
leadingConstraint.constant = isPortrait ? 75.0 : 0.0
trailingConstraint.constant = isPortrait ? -75.0 : 0.0
}
}
每次点击view,imageView的width:height比例都会改变,leading/trailing约束常量也会改变。
我创建了一个顶部有分段控制器的视图控制器。当您点击分段控制器时,它只是作为一个按钮,并通过调用将其更改为相应尺寸的函数来更改控制器内部的 imageView 是纵向模式还是横向模式。
我的问题是我改变它的方式是我只是向 imageView 添加了约束,但是当切换到横向模式时,尾随约束没有被删除。
并且,这是将 imageView 更改为纵向的代码(imageView 已经具有顶部和底部约束):
func portraitContraints() {
NSLayoutConstraint.activate ([
// the trailing contraint
imageView.trailingAnchor.constraint(equalTo: viewContainer.safeAreaLayoutGuide.trailingAnchor, constant: -75), // this is the contraints that doesn't get removed
// the leading contraints
imageView.leadingAnchor.constraint(equalTo: viewContainer.safeAreaLayoutGuide.leadingAnchor, constant: 75
])
// the aspect ratio contraints
imageView.addConstraint(NSLayoutConstraint(item: self.imageView as Any,attribute: .height,relatedBy: .equal,toItem: self.imageView,attribute: .width,multiplier: (4.0 / 3.0),constant: 0))
}
这是将 imageView 更改为横向的代码:
func landscapeContraints() {
NSLayoutConstraint.activate([
// the trailing contraints
imageView.trailingAnchor.constraint(equalTo: viewContainer.safeAreaLayoutGuide.trailingAnchor, constant: 0),
// the leading contraint
imageView.leadingAnchor.constraint(equalTo: viewContainer.safeAreaLayoutGuide.leadingAnchor, constant: 0)
])
// the aspect ratio contraint
imageView.addConstraint(NSLayoutConstraint(item: self.imageView as Any,attribute: .height,relatedBy: .equal,toItem: self.imageView,attribute: .width,multiplier: (9.0 / 16.0),constant: 0))
}
这段代码就像一个魅力,除了唯一的问题是纵向模式的尾随约束将保留在视图上(-75 常量约束)。
横向看起来像这样(注意右边的常量是-75):
肖像看起来像这样:
尝试在添加新约束之前删除旧约束。这是有关如何执行此操作的 Apple 文档:https://developer.apple.com/documentation/uikit/uiview/1622593-removeconstraints
您可以通过添加具有不同优先级的both比率约束来实现。更改优先级以使所需比率“有效”。
并且,创建前导和尾随约束变量,以便您可以更改它们的常量。
这是一个简单的例子:
class ToggleConstraintsViewController: UIViewController {
let imageView = UIImageView()
var isPortrait: Bool = true
var portraitConstraint: NSLayoutConstraint!
var landscapeConstraint: NSLayoutConstraint!
var leadingConstraint: NSLayoutConstraint!
var trailingConstraint: NSLayoutConstraint!
override func viewDidLoad() {
super.viewDidLoad()
imageView.backgroundColor = .blue
imageView.translatesAutoresizingMaskIntoConstraints = false
view.addSubview(imageView)
let g = view.safeAreaLayoutGuide
portraitConstraint = imageView.heightAnchor.constraint(equalTo: imageView.widthAnchor, multiplier: 4.0/3.0)
portraitConstraint.priority = .defaultHigh
landscapeConstraint = imageView.heightAnchor.constraint(equalTo: imageView.widthAnchor, multiplier: 9.0/16.0)
landscapeConstraint.priority = .defaultLow
leadingConstraint = imageView.leadingAnchor.constraint(equalTo: g.leadingAnchor, constant: 75.0)
trailingConstraint = imageView.trailingAnchor.constraint(equalTo: g.trailingAnchor, constant: -75.0)
NSLayoutConstraint.activate([
// y-position constraint does not change
imageView.centerYAnchor.constraint(equalTo: g.centerYAnchor),
// these will have their priorities changed when desired
portraitConstraint,
landscapeConstraint,
// these will have their constants changed when desired
leadingConstraint,
trailingConstraint,
])
let t = UITapGestureRecognizer(target: self, action: #selector(self.toggleOrientation(_:)))
view.addGestureRecognizer(t)
}
@objc func toggleOrientation(_ g: UITapGestureRecognizer) -> Void {
isPortrait.toggle()
portraitConstraint.priority = isPortrait ? .defaultHigh : .defaultLow
landscapeConstraint.priority = isPortrait ? .defaultLow : .defaultHigh
leadingConstraint.constant = isPortrait ? 75.0 : 0.0
trailingConstraint.constant = isPortrait ? -75.0 : 0.0
}
}
每次点击view,imageView的width:height比例都会改变,leading/trailing约束常量也会改变。