从框架添加时视图不响应操作
Views not responding on action when added from framework
我为自定义视图创建了一个简单的框架。从我的角度来看,我希望可以跨多个应用程序重复使用。问题是,当我更改项目中的约束时,视图没有响应任何操作,例如点击按钮、在 textField 中输入文本。我猜问题出在 translatesAutoresizingMaskIntoConstraints
.
假设我有一个如下所示的框架:
public class CustomView: UIView {
public let customButton: UIButton = {
let button = UIButton()
button.translatesAutoresizingMaskIntoConstraints = false
button.setTitle("Save", for: .normal)
button.layer.cornerRadius = 10
button.layer.borderWidth = 1
button.layer.borderColor = UIColor.red.cgColor
button.setTitleColor(.red, for: .normal)
return button
}()
public var buttonWidth: CGFloat = 100
public override init(frame: CGRect) {
super.init(frame: frame)
initConstraints()
}
func initConstraints(){
addSubview(customButton)
NSLayoutConstraint.activate([
customButton.topAnchor.constraint(equalTo: safeAreaLayoutGuide.topAnchor, constant: 80),
customButton.centerXAnchor.constraint(equalTo: centerXAnchor),
customButton.widthAnchor.constraint(equalToConstant: buttonWidth)
])
}
public required init?(coder: NSCoder) {
fatalError("init(coder:) has not been implemented")
}}
当成功将框架添加到项目后,我需要更改视图的位置。从中心到更上层。我正在创建 class
class FrameworkView: UIView {
let customButton: CustomView = {
let cusomView = CustomView()
cusomView.translatesAutoresizingMaskIntoConstraints = false
return cusomView
}()
override init(frame: CGRect) {
super.init(frame: frame)
initConst()
}
func initConst() {
addSubview(customButton)
NSLayoutConstraint.activate([
customButton.topAnchor.constraint(equalTo: safeAreaLayoutGuide.topAnchor, constant: 100),
customButton.leadingAnchor.constraint(equalTo: leadingAnchor, constant: 25),
customButton.trailingAnchor.constraint(equalTo: trailingAnchor, constant: -25),
])
}
required init?(coder: NSCoder) {
fatalError("init(coder:) has not been implemented")
}}
当我将视图添加到 ViewController 时,一切看起来都正常。
override func viewDidLoad() {
super.viewDidLoad()
// Do any additional setup after loading the view.
let demo = FrameworkView(frame: view.frame)
view.addSubview(demo)
demo.customButton.customButton.addTarget(self, action: #selector(tap(_:)), for: .touchUpInside)
}
@objc func tap(_ sender: UIButton){
print("Test")
}
很遗憾,按钮没有响应操作。与其他视图(如 textFields、TextViews 等)相同。
我不知道如何解决这个错误。我猜想子视图和约束有问题。
感谢您提供任何帮助。
马特
CustomView
(FrameworkView
的子视图)的高度不明确。这导致它不显示。但是因为UIButton
的frame没有歧义,所以还是显示出来了。我认为这可能是点击事件没有传递到按钮的原因 - 按钮的超级视图的框架 CustomView
不明确。
之所以高度不明确是因为你好像忘记了一个底部约束:
// in FrameworkView
NSLayoutConstraint.activate([
customButton.topAnchor.constraint(equalTo: safeAreaLayoutGuide.topAnchor, constant: 100),
customButton.leadingAnchor.constraint(equalTo: leadingAnchor, constant: 25),
customButton.trailingAnchor.constraint(equalTo: trailingAnchor, constant: -25),
// your forgot this!
customButton.bottomAnchor.constraint(equalTo: bottomAnchor, constant: -100)
])
如果您添加底部约束,则该按钮将起作用。
而不是创建另一个包装 CustomView
的视图,您可以考虑修改 CustomView
以便它公开 topConstraint
属性(因为您似乎想要做的是将按钮向下移动一点):
public class CustomView: UIView {
public var topConstraint: NSLayoutConstraint!
...
private func initConstraints(){
addSubview(customButton)
topConstraint = customButton.topAnchor.constraint(equalTo: safeAreaLayoutGuide.topAnchor, constant: 80)
NSLayoutConstraint.activate([
topConstraint,
customButton.centerXAnchor.constraint(equalTo: centerXAnchor),
customButton.widthAnchor.constraint(equalToConstant: buttonWidth)
])
}
现在不需要FrameworkView
,可以设置topConstraint.constant
向下移动按钮。
我为自定义视图创建了一个简单的框架。从我的角度来看,我希望可以跨多个应用程序重复使用。问题是,当我更改项目中的约束时,视图没有响应任何操作,例如点击按钮、在 textField 中输入文本。我猜问题出在 translatesAutoresizingMaskIntoConstraints
.
假设我有一个如下所示的框架:
public class CustomView: UIView {
public let customButton: UIButton = {
let button = UIButton()
button.translatesAutoresizingMaskIntoConstraints = false
button.setTitle("Save", for: .normal)
button.layer.cornerRadius = 10
button.layer.borderWidth = 1
button.layer.borderColor = UIColor.red.cgColor
button.setTitleColor(.red, for: .normal)
return button
}()
public var buttonWidth: CGFloat = 100
public override init(frame: CGRect) {
super.init(frame: frame)
initConstraints()
}
func initConstraints(){
addSubview(customButton)
NSLayoutConstraint.activate([
customButton.topAnchor.constraint(equalTo: safeAreaLayoutGuide.topAnchor, constant: 80),
customButton.centerXAnchor.constraint(equalTo: centerXAnchor),
customButton.widthAnchor.constraint(equalToConstant: buttonWidth)
])
}
public required init?(coder: NSCoder) {
fatalError("init(coder:) has not been implemented")
}}
当成功将框架添加到项目后,我需要更改视图的位置。从中心到更上层。我正在创建 class
class FrameworkView: UIView {
let customButton: CustomView = {
let cusomView = CustomView()
cusomView.translatesAutoresizingMaskIntoConstraints = false
return cusomView
}()
override init(frame: CGRect) {
super.init(frame: frame)
initConst()
}
func initConst() {
addSubview(customButton)
NSLayoutConstraint.activate([
customButton.topAnchor.constraint(equalTo: safeAreaLayoutGuide.topAnchor, constant: 100),
customButton.leadingAnchor.constraint(equalTo: leadingAnchor, constant: 25),
customButton.trailingAnchor.constraint(equalTo: trailingAnchor, constant: -25),
])
}
required init?(coder: NSCoder) {
fatalError("init(coder:) has not been implemented")
}}
当我将视图添加到 ViewController 时,一切看起来都正常。
override func viewDidLoad() {
super.viewDidLoad()
// Do any additional setup after loading the view.
let demo = FrameworkView(frame: view.frame)
view.addSubview(demo)
demo.customButton.customButton.addTarget(self, action: #selector(tap(_:)), for: .touchUpInside)
}
@objc func tap(_ sender: UIButton){
print("Test")
}
很遗憾,按钮没有响应操作。与其他视图(如 textFields、TextViews 等)相同。 我不知道如何解决这个错误。我猜想子视图和约束有问题。 感谢您提供任何帮助。 马特
CustomView
(FrameworkView
的子视图)的高度不明确。这导致它不显示。但是因为UIButton
的frame没有歧义,所以还是显示出来了。我认为这可能是点击事件没有传递到按钮的原因 - 按钮的超级视图的框架 CustomView
不明确。
之所以高度不明确是因为你好像忘记了一个底部约束:
// in FrameworkView
NSLayoutConstraint.activate([
customButton.topAnchor.constraint(equalTo: safeAreaLayoutGuide.topAnchor, constant: 100),
customButton.leadingAnchor.constraint(equalTo: leadingAnchor, constant: 25),
customButton.trailingAnchor.constraint(equalTo: trailingAnchor, constant: -25),
// your forgot this!
customButton.bottomAnchor.constraint(equalTo: bottomAnchor, constant: -100)
])
如果您添加底部约束,则该按钮将起作用。
而不是创建另一个包装 CustomView
的视图,您可以考虑修改 CustomView
以便它公开 topConstraint
属性(因为您似乎想要做的是将按钮向下移动一点):
public class CustomView: UIView {
public var topConstraint: NSLayoutConstraint!
...
private func initConstraints(){
addSubview(customButton)
topConstraint = customButton.topAnchor.constraint(equalTo: safeAreaLayoutGuide.topAnchor, constant: 80)
NSLayoutConstraint.activate([
topConstraint,
customButton.centerXAnchor.constraint(equalTo: centerXAnchor),
customButton.widthAnchor.constraint(equalToConstant: buttonWidth)
])
}
现在不需要FrameworkView
,可以设置topConstraint.constant
向下移动按钮。