@IBDesignable UIView 不在情节提要中调用 init
Posted
技术标签:
【中文标题】@IBDesignable UIView 不在情节提要中调用 init【英文标题】:@IBDesignable UIView not calling init within storyboard 【发布时间】:2018-07-24 11:27:22 【问题描述】:我有一个UIView
,即@IBDesignable
@IBDesignable
class MyView: UIView
override init(frame: CGRect)
super.init(frame: frame)
sharedInit()
required init?(coder aDecoder: NSCoder)
super.init(coder: aDecoder)
sharedInit()
private func sharedInit()
translatesAutoresizingMaskIntoConstraints = false
backgroundColor = .blue
当我将 UIView
放在情节提要中,并在 身份检查器 中将其类分配给 MyView
时,UIView
仍然具有默认背景颜色。为什么它的背景颜色不是故事板中的UIColor.blue
?还有,请问我怎样才能做到这一点?
感谢您的帮助。
【问题讨论】:
init
用于 runtime - 而 Interface Builder 是 design-time。虽然这可能不起作用,但请考虑使用 prepareForInterfaceBuilder()
来查看 sharedInit
。
【参考方案1】:
从情节提要初始化此视图的初始化程序将在运行时调用,为了在编译时更新情节提要中的视图,您应该尝试包含prepareForInterfaceBuilder
,它会在编译时更新情节提要 xib 文件。
我建议你在创建@IBDesignable 类时做多件事:
-
用
@IBDesignable
标签标记班级
用@IBInspectable
标记UIView
属性,然后您将能够使用StoryBoard 更改此属性的值
在该属性的willSet
中设置配置代码,该配置代码在属性获取值之前观察更改,或者在属性接收到值之后设置didSet
。
在prepareForInterfaceBuilder()
中进行额外设置,它覆盖了它的超类UIView
简单易行!
您的代码应如下所示:
斯威夫特 5:
import UIKit
@IBDesignable
class myView: UIView
@IBInspectable var storyBoardColor : UIColor = .red
willSet(myVariableNameToCatch)
self.backgroundColor = myVariableNameToCatch
fileprivate func sharedInit()
translatesAutoresizingMaskIntoConstraints = false
backgroundColor = storyBoardColor
override func prepareForInterfaceBuilder()
super.prepareForInterfaceBuilder()
sharedInit()
myView 的 storyBoardColor 初始值为 red,您可以从 storyBoard 更改它;)
【讨论】:
@thibautnoah 嗨,我在第 (3) 节中提醒了他,并告诉他如何实现 structre base。答案可以在第 (3) 节中找到,对于我想让每个人都知道它是如何工作的功能......但谢谢,也许我应该少解释一下。 @mohamadrezakoohkan 视图首先不是初始化的。因此我说你没有回答这个问题。我同意可检查部分,但您更改了类本身的结构。【参考方案2】:一旦您使用标签@IBDesignable 制作您的视图。接下来是使用@IBInspectable 设置您的属性。
@IBDesignable
class MyView: UIView
@IBInspectable var myBackgroundColour: UIColor? = nil
willSet(v)
self.backgroundColor = v
// YOUR EXISTING CODE HERE
现在,当您在 Identity Inspector 中将 MyView 设置为类名时。您将能够在 Attributes Inspector 中看到您的可检查属性。在那里您可以设置颜色,它会立即反映到您的自定义视图中。
我认为使用自定义属性设置背景颜色没有任何用处,因为 UIView 具有设置背景颜色的默认属性。
希望对你有帮助。
【讨论】:
【参考方案3】:Swift 4.2 经过测试并且可以正常工作。这是最干净的解决方案。
在 Xcode 中确保选中 Editor -> Automatically refresh views
。
import UIKit
@IBDesignable
class BoxView: UIView
override func prepareForInterfaceBuilder()
super.prepareForInterfaceBuilder()
layer.borderColor = borderColor?.cgColor
layer.borderWidth = borderWidth
layer.cornerRadius = cornerRadius
@IBInspectable var borderColor: UIColor?
didSet
layer.borderColor = borderColor?.cgColor
setNeedsLayout()
@IBInspectable var borderWidth: CGFloat = 0.0
didSet
layer.borderWidth = borderWidth
setNeedsLayout()
@IBInspectable var cornerRadius: CGFloat = 0.0
didSet
layer.cornerRadius = cornerRadius
setNeedsLayout()
-
在上面创建 BoxView.swift 文件。
在 InterfaceBuilder 中选择一个 UIView。
在
Identity Inspector
中选择Custom Class -> Class to "BoxView"
。
在Attributes Inspector
中设置borderColor
、borderWidth
和borderRadius
。
【讨论】:
以上是关于@IBDesignable UIView 不在情节提要中调用 init的主要内容,如果未能解决你的问题,请参考以下文章
无法将自定义 IBDesignable 类链接到情节提要上的 UIButton
iOS - 无法让 @IBDesignable .xib 文件显示在情节提要或模拟器上
层的 UIView 的子层在 Storyboard 中显示为 @IBDesignable,但在模拟器中却没有
如何使用创建的自定义 IBDesignable 类从情节提要中更改按钮的角半径