Swift文档说可以在扩展中添加初始化程序,文档中的示例是关于向 struct 添加初始化程序。 Xcode在我的便利初始化程序中无法识别UIColor
指定的初始化程序:
extension UIColor {
convenience init(rawValue red: CGFloat, green g: CGFloat, blue b: CGFloat, alpha a: CGFloat) {
// Can not find out the designated initializer here
self.init()
}
}
任何解决方案?
答案 0 :(得分:31)
你不能这样做,你必须选择不同的参数名来创建你自己的初始化器,如下所示:
extension UIColor {
convenience init(r: UInt8, g: UInt8 , b: UInt8 , a: UInt8) {
self.init(red: CGFloat(r)/255, green: CGFloat(g)/255, blue: CGFloat(b)/255, alpha: CGFloat(a)/255)
}
convenience init(r: Double, g: Double , b: Double , alpha: Double) {
self.init(red: CGFloat(r), green: CGFloat(g), blue: CGFloat(b), alpha: CGFloat(alpha))
}
}
let myGreenColor1 = UIColor(r: 0, g: 255, b: 0, a: 255)
let myGreenColor2 = UIColor(r: 0, g: 1, b: 0, alpha: 1)
答案 1 :(得分:2)
好吧,如果你真的,真的,真的想要覆盖初始化者,那就有办法了。
在您进一步阅读之前:永远不要这样做更改 UIKit
行为。为什么?它可能会让那些能够弄清楚UIColor
初始化者没有做正常事情的人的混淆。只做它来修复UIKit
错误或添加功能等。
我使用以下内容修补了几个iOS错误。
extension UIColor {
private static var needsToOverrideInit = true
override open class func initialize() {
// Only run once - otherwise subclasses will call this too. Not obvious.
if needsToOverrideInit {
let defaultInit = class_getInstanceMethod(UIColor.self, #selector(UIColor.init(red:green:blue:alpha:)))
let ourInit = class_getInstanceMethod(UIViewController.self, #selector(UIColor.init(_red:_green:_blue:_alpha:)))
method_exchangeImplementations(defaultInit, ourInit)
needsToOverrideInit = false
}
}
convenience init(_red: CGFloat, _green: CGFloat, _blue: CGFloat, _alpha: CGFloat) {
// This is trippy. We swapped implementations... won't recurse.
self.init(red: _red, green: _green, blue: _blue, alpha: _alpha)
///////////////////////////
// Add custom logic here //
///////////////////////////
}
}
这是使用从Swift调用的Objective-C的动态特性来在运行时交换方法定义指针。如果您不知道这意味着什么,或者它的含义,在您使用此代码之前阅读该主题可能是一个好主意。
答案 2 :(得分:1)
更改参数类型也可以。
extension UIColor {
convenience init(red: Int, green: Int, blue: Int, alpha: CGFloat) {
let normalizedRed = CGFloat(red) / 255
let normalizedGreen = CGFloat(green) / 255
let normalizedBlue = CGFloat(blue) / 255
self.init(red: normalizedRed, green: normalizedGreen, blue: normalizedBlue, alpha: alpha)
}
}
<强>用法强>:
let newColor: UIColor = UIColor.init(red: 74, green: 74, blue: 74, alpha: 1)
我通常会忘记将组件值除以255的冗余工作。所以我使用这种方法来方便我。