Call a Swift Singleton from Objective-C
Swift 5 and above
final class Singleton: NSObject {
@objc static let shared = Singleton()
@objc var string: String = "Hello World"
private override init() {}
}
use in Objective-C
NSLog("Singleton String = %@", [Singleton shared].string]);
For now I have the following solution. Maybe I am overlooking something that would enable me to access "swiftSharedInstance" directly?
@objc class SingletonTest: NSObject {
// swiftSharedInstance is not accessible from ObjC
class var swiftSharedInstance: SingletonTest {
struct Singleton {
static let instance = SingletonTest()
}
return Singleton.instance
}
// the sharedInstance class method can be reached from ObjC
class func sharedInstance() -> SingletonTest {
return SingletonTest.swiftSharedInstance
}
// Some testing
func testTheSingleton() -> String {
return "Hello World"
}
}
Then in ObjC I can get the sharedInstance class method (after importing the xcode generated swift header bindings)
SingletonTest *aTest = [SingletonTest sharedInstance];
NSLog(@"Singleton says: %@", [aTest testTheSingleton]);
Nicky Goethlis's answer is correct but I just want to add another way of Singleton creation termed as One line Singleton" in Swift which I came across recently and it does not use Struct
:
Singleton.swift
@objc class Singleton: NSObject {
static let _singletonInstance = Singleton()
private override init() {
//This prevents others from using the default '()' initializer for this class.
}
// the sharedInstance class method can be reached from ObjC. (From OP's answer.)
class func sharedInstance() -> Singleton {
return Singleton._singletonInstance
}
// Some testing
func testTheSingleton() -> String {
return "Hello World"
}
}
SomeObjCFile.m
Singleton *singleton = [Singleton sharedInstance];
NSString *testing = [singleton testTheSingleton];
NSLog(@"Testing---> %@",testing);