Welcome to OStack Knowledge Sharing Community for programmer and developer-Open, Learning and Share
Welcome To Ask or Share your Answers For Others

Categories

0 votes
306 views
in Technique[技术] by (71.8m points)

ios - How to call Swift from an Objective C project App Delegate?

This code is from a Swift project App delegate. It is used to help configure Stripe with a publishable key.

//Appdelegate.swift
func application(_ application: UIApplication, didFinishLaunchingWithOptions launchOptions: 
[UIApplicationLaunchOptionsKey: Any]?) -> Bool 
{
//The code helps configure Stripe with a publishable key.
STPPaymentConfiguration.shared().publishableKey = Constants.publishableKey
...
}

Two errors are displayed when building the app after adding the Swift line to the Objective C App Delegate

//AppDelegate.h
- (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary*)launchOptions
{
STPPaymentConfiguration.shared().publishableKey = Constants.publishableKey

Property 'shared' not found on object of type 'STPPaymentConfiguration'
Use of undeclared identifier 'Constants'

This was a similar error in compiling before @objc was added to the demo Swift function, MockApiClient. Should it be added elsewhere? I've tried adding @objc to the enum as mentioned in the answer here to no avail yet.

//Constants.swift 
//This is the file the original Swift app delegate accesses
import Foundation

  enum Constants {
  static let publishableKey = "pk_live_..."
  static let baseURLString = "http://54.33.123.227:1234"
  static let defaultCurrency = "usd"
  static let defaultDescription = "Receipt" //change to describe actual app & charge
  }

Steps taken:

  1. Opened the Objective C project and created a bridging header

  2. Created a demo class in Swift while still in the Obj C project to make sure it can be used, in this case to print from an Objective C file when the view is loaded. Specifically derived from an NSObject. Adding the override to the initializer and using the @objc prefix.

    //  MockApiClient.swift
    import Foundation
    class MockApiClient: NSObject
    {
    override init()
    {
    print("Initializer called in Mock API client")
    }
    @objc func executeRequest()
    {
    print("The execute request has been called in the Mock API Client")
    }
    }
    
    //ViewController.h
    //Prints the Swift request written in the MockApiClient the the view loads
    
    @implementation ViewController
    - (void)viewDidLoad
    {
    [super viewDidLoad];
    // Do any additional setup after loading the view, typically from a nib.
    MockApiClient *client = [MockApiClient new];
    [client executeRequest];
    }
    
  3. Copied the #import "ViewController.h" import to the automatically generated project-Bridging-Header.h file to expose the Objective C in it to swift

  4. Added the necessary Swift files to the Objective C project so that the Constants.publishablekey data from Constants.swift can be found

How can this Swift App delegate code be added to the App delegate of an Objective C project?

Edit: error when adding @objc to the enum declaration in Constants.swift

enter image description here

question from:https://stackoverflow.com/questions/65854409/how-to-call-swift-from-an-objective-c-project-app-delegate

与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…
Welcome To Ask or Share your Answers For Others

1 Answer

0 votes
by (71.8m points)

Edit: error when adding @objc to the enum declaration in Constants.swift

Swift enums used as namespace cannot be exposed to Objective-C. You may need to use class to make it work both for Swift and Objective-C:

@objcMembers
class Constants: NSObject {
    static let publishableKey = "pk_live_..."
    static let baseURLString = "http://54.33.123.227:1234"
    static let defaultCurrency = "usd"
    static let defaultDescription = "Receipt" //change to describe actual app & charge
    
    private override init() {}
}

与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…
Welcome to OStack Knowledge Sharing Community for programmer and developer-Open, Learning and Share
Click Here to Ask a Question

...