14

Xcode is giving me this error for my Swift code:

'myColor' cannot be constructed because it has no accessible initializers

import Foundation

protocol Prototype {
    func Clone<T>() -> T
}

class myColor: Prototype {
    var red: Int?
    var green: Int?
    var blue: Int?
    
    init () {}
    
    func Clone<myColor>() -> myColor {
        let newColor = myColor()
        newColor.red = self.red
        newColor.green = self.green
        newColor.blue = self.blue
        
        return newColor
    }
}

The error is on line:

let newColor = myColor()

Type 'myColor' has no member 'init'

pkamb
  • 33,281
  • 23
  • 160
  • 191
RKD
  • 426
  • 1
  • 5
  • 12

4 Answers4

21

Even if you set your framework to public, you still need to declare all classes you want to make accessible as 'public'. Same goes for your init method.

public init() {
}

Did the trick for me.

  • 5
    This solved this error message for me - the base class (in which I have overridden the default init) needed to be written as override public init() – leafcutter Jul 29 '15 at 14:26
9

First, classes have leading caps. Methods have leading lowercase. You mean MyColor and clone().

You're confusing the compiler at this point:

func Clone<myColor>() -> myColor {

It thinks you mean that myColor is a type variable that is shadowing the class name. So when you get to myColor(), it's basically the same thing as T(), which has no trivial constructor.

If you fix this stuff up, you'll find that the correct error is

Type 'MyColor' does not conform to protocol 'Prototype'

That error is a completely different problem. See Protocol func returning Self for an explanation of how to implement a copy protocol. You also may be interested in the followup: Swift protocol and return types on global functions.

Community
  • 1
  • 1
Rob Napier
  • 286,113
  • 34
  • 456
  • 610
1

You will hit this error if you attempt to add a new property to a subclass without adding new initializers.

'SomeSubclass' cannot be constructed because it has no accessible initializers

Suddenly none of the existing superclass's initializers will be valid, as the new variable needs to be set within an init() method on the subclass (which doesn't yet exist).

class SomeSubclass: UIViewController { // Class 'SomeSubclass' has no initializers

    var date: Date
    
    class func `for`(_ date: Date) -> SomeSubclass {
        let someSubclass = SomeSubclass() // 'SomeSubclass' cannot be constructed because it has no accessible initializers
        someSubclass.date = date
        return someSubclass
    }
        
}

A fix for most UIViewController situations, as is commonly used for IBOutlets, is to declare the subclass's properties as optionals or implicitly unwrapped optionals, which will be valid and initialized to nil when using the existing superclass init methods. Then set the value immediately after initialization.

var date: Date?
// - or - //
var date: Date!
pkamb
  • 33,281
  • 23
  • 160
  • 191
0

Seems generic generates extend of class, and need for use.

override init() {...

Note that any class in Swift must have initializer. And in your case nevertheless generic, class must have init()

dimpiax
  • 12,093
  • 5
  • 62
  • 45