Swift에서 Objective-C 코드를 어떻게 호출합니까?
애플은 하나의 애플리케이션에 공존 할 수 있다고 언급했지만, 이는 스위프트에서 새로운 클래스를 구축하면서 Objective-C로 만든 오래된 클래스를 기술적으로 재사용 할 수 있다는 것을 의미합니까?
Swift에서 Objective-C 코드를 어떻게 호출합니까?
애플은 하나의 애플리케이션에 공존 할 수 있다고 언급했지만, 이는 스위프트에서 새로운 클래스를 구축하면서 Objective-C로 만든 오래된 클래스를 기술적으로 재사용 할 수 있다는 것을 의미합니까?
답변:
사용하려는 기존 클래스가있는 경우 2 단계를 수행 한 다음 5 단계 로 건너 뜁니다 . (어떤 경우
#import <Foundation/Foundation.h
에는 이전 Objective-C 파일에 명시 를 추가해야했습니다 .)
.m
클래스에 파일을 추가 하고 이름을 지정하십시오 CustomObject.m
.
.m
파일을 추가 할 때 다음과 같은 프롬프트가 표시 될 수 있습니다.
예를 클릭하십시오 !
프롬프트가 표시되지 않거나 실수로 브리징 헤더를 삭제 한 경우 .h
프로젝트에 새 파일을 추가 하고 이름을 지정하십시오 <#YourProjectName#>-Bridging-Header.h
.
경우에 따라, 특히 Objective-C 프레임 워크로 작업 할 때 Objective-C 클래스를 명시 적으로 추가하지 않고 Xcode가 링커를 찾을 수 없습니다. 이 경우 .h
위에서 언급 한대로 이름이 지정된 파일을 만든 다음 대상의 프로젝트 설정에서 다음과 같이 경로를 연결해야합니다.
노트 :
$(SRCROOT)
매크로를 사용하여 프로젝트를 연결하는 것이 가장 좋습니다. 프로젝트를 이동하거나 원격 저장소를 사용하여 다른 사람들과 함께 작업해도 여전히 작동합니다. $(SRCROOT)
.xcodeproj 파일이 들어있는 디렉토리로 생각할 수 있습니다. 다음과 같이 보일 수 있습니다 :
$(SRCROOT)/Folder/Folder/<#YourProjectName#>-Bridging-Header.h
다른 .h
파일을 추가 하고 이름을 지정하십시오 CustomObject.h
.
에 CustomObject.h
#import <Foundation/Foundation.h>
@interface CustomObject : NSObject
@property (strong, nonatomic) id someProperty;
- (void) someMethod;
@end
에 CustomObject.m
#import "CustomObject.h"
@implementation CustomObject
- (void) someMethod {
NSLog(@"SomeMethod Ran");
}
@end
에서 YourProject-Bridging-Header.h
:
#import "CustomObject.h"
에서 SomeSwiftFile.swift
:
var instanceOfCustomObject = CustomObject()
instanceOfCustomObject.someProperty = "Hello World"
print(instanceOfCustomObject.someProperty)
instanceOfCustomObject.someMethod()
명시 적으로 가져올 필요는 없습니다. 이것이 브리징 헤더의 목적입니다.
.swift
프로젝트에 파일을 추가 하고 이름을 지정하십시오 MySwiftObject.swift
.
에서 MySwiftObject.swift
:
import Foundation
@objc(MySwiftObject)
class MySwiftObject : NSObject {
@objc
var someProperty: AnyObject = "Some Initializer Val" as NSString
init() {}
@objc
func someFunction(someArg: Any) -> NSString {
return "You sent me \(someArg)"
}
}
에서 SomeRandomClass.m
:
#import "<#YourProjectName#>-Swift.h"
파일 : 파일 <#YourProjectName#>-Swift.h
이 보이지 않더라도 프로젝트에서 이미 자동으로 생성되어야합니다.
MySwiftObject * myOb = [MySwiftObject new];
NSLog(@"MyOb.someProperty: %@", myOb.someProperty);
myOb.someProperty = @"Hello World";
NSLog(@"MyOb.someProperty: %@", myOb.someProperty);
NSString * retString = [myOb someFunctionWithSomeArg:@"Arg"];
NSLog(@"RetString: %@", retString);
코드 완성이 예상대로 작동하지 않으면 빠른 빌드를 실행하여 ⌘⇧RXcode가 Swift 컨텍스트에서 Objective-C 코드 중 일부를 찾거나 그 반대로 할 수 있도록하십시오.
.swift
이전 프로젝트에 파일을 추가 하고 오류가 발생 dyld: Library not loaded: @rpath/libswift_stdlib_core.dylib
하면 Xcode를 완전히 다시 시작하십시오 .
접두사 NSObject
를 사용하여 Objective-C에 표시되는 순수한 Swift 클래스 (의 자손 아님 )를 원래 사용할 수 있었지만 @objc
더 이상 가능하지 않습니다. 이제 Objective-C에서 볼 수 있도록 Swift 객체는 NSObjectProtocol
(이를 수행하는 가장 쉬운 방법은)을 준수하는 클래스 NSObject
이거나 와 같은 정수 유형의 원시 값으로 enum
표시되어 있어야합니다 . 이러한 제한없이 Swift 1.x 코드의 예에 대한 편집 기록을 볼 수 있습니다 .@objc
Int
@objc
Cocoa 및 Objective-C와 함께 Swift 사용에 관한 Apple의 안내서를 참조하십시오 . 이 안내서는 Swift에서 Objective-C 및 C 코드를 사용하는 방법과 그 반대로 사용하는 방법을 설명하고 기존 프로젝트에서 프로젝트를 변환하거나 Objective-C / C 및 Swift 부품을 혼합하고 일치시키는 방법에 대한 권장 사항을 제공합니다.
컴파일러는 C 함수 및 Objective-C 메소드 호출을위한 Swift 구문을 자동으로 생성합니다. 설명서에서 볼 수 있듯이이 Objective-C는 다음과 같습니다.
UITableView *myTableView = [[UITableView alloc] initWithFrame:CGRectZero style:UITableViewStyleGrouped];
이 스위프트 코드로 바뀝니다.
let myTableView: UITableView = UITableView(frame: CGRectZero, style: .Grouped)
Xcode는 또한이 변환을 즉석에서 수행합니다. Swift 파일을 편집하는 동안 빨리 열기를 사용하고 Objective-C 클래스 이름을 입력하면 Swift 버전의 클래스 헤더로 이동합니다. (Swift 파일에서 API 기호를 cmd- 클릭하여 얻을 수도 있습니다.) 그리고 iOS 8 및 OS X v10.10 (Yosemite) 개발자 라이브러리의 모든 API 참조 문서는 Objective-C 및 Swift에 모두 표시됩니다. 양식 (예 :) UIView
.
다음은 Swift 프로젝트에서 Objective-C 코드 (이 경우 타사에서 제공 한 프레임 워크)를 사용하기위한 단계별 지침입니다.
간단한 단계로 :
프롬프트가 나타난 다음 확인을 클릭하십시오. 표시되지 않으면 다음과 같이 수동으로 작성하십시오. iOS 소스에서 하나의 헤더 파일을 작성하고 이름을 ProjectName-Bridging-Header로 지정하십시오 (예 : 테스트). -Bridging-Header)를 클릭 한 다음 Swift 컴파일러 코드-> Objective-C 브리지에서 Objective-C 브리지 이름 .. (Test / Test-Bridging-Header.h)에서 빌드 설정으로 이동하십시오. 예, 완료되었습니다.
선택적으로 추가 한 Objective-C 파일 (위의 GIF 이미지에서 "anything")을 삭제하십시오. 더 이상 필요하지 않습니다.
브리징 헤더 파일을 엽니 다. 파일 이름은 [YourProject] -Bridging-Header.h 형식 입니다. Xcode 제공 주석이 포함되어 있습니다. 타사 프레임 워크와 같이 포함하려는 Objective-C 파일에 대한 코드 줄을 추가하십시오 . 예를 들어, 프로젝트에 Mixpanel을 추가하려면 브리징 헤더 파일에 다음 코드 줄을 추가해야합니다.
#import "Mixpanel.h"
이제 모든 Swift 파일에서 기존 Objective-C 코드를 Swift 구문으로 사용할 수 있습니다 (이 예제의 경우 Mixpanel SDK 메서드 등을 호출 할 수 있음). Xcode가 Objective-C를 Swift로 변환하는 방법을 숙지해야합니다. Apple 가이드 는 빠른 읽기입니다. 불완전한 요약은이 답변을 참조하십시오.
Mixpanel의 예 :
func application(application: UIApplication, didFinishLaunchingWithOptions launchOptions: [NSObject: AnyObject]?) -> Bool {
Mixpanel.sharedInstanceWithToken("your-token")
return true
}
그게 다야!
참고 : 프로젝트에서 브리징 헤더 파일을 제거하는 경우 빌드 설정으로 이동하여 "Swift Compiler-Code Generation" 에서 " Objective-C Bridging Header " 값을 제거하십시오 .
좋은 게시물 Swift & Cocoapods를 읽을 수 있습니다 . 기본적으로 브리징 헤더 파일을 생성하고 모든 Objective-C 헤더를 거기에 배치해야합니다. 그런 다음 빌드 설정에서 참조해야합니다. 그런 다음 Objective-C 코드를 사용할 수 있습니다.
let manager = AFHTTPRequestOperationManager()
manager.GET(
"http://example.com/resources.json",
parameters: nil,
success: { (operation: AFHTTPRequestOperation!,
responseObject: AnyObject!) in
println("JSON: " + responseObject.description)
},
failure: { (operation: AFHTTPRequestOperation!,
error: NSError!) in
println("Error: " + error.localizedDescription)
})
또한 Cocoa 및 Objective-C와 함께 Apple의 문서 Using Swift를 살펴보십시오 .
C ++, Objective-C 및 Swift 코드를 혼합하는 방법을 보여주는 간단한 Xcode 6 프로젝트를 작성했습니다.
https://github.com/romitagl/shared/tree/master/C-ObjC-Swift/Performance_Console
특히,이 예제 는 Swift에서 Objective-C 및 C ++ 함수를 호출합니다 .
핵심은 공유 헤더 인 Project-Bridging-Header.h를 생성하고 Objective-C 헤더를 배치하는 것입니다.
완전한 예제로 프로젝트를 다운로드하십시오.
@Logan의 답변에 매우 감사드립니다. 브리지 파일과 설정을 만드는 데 많은 도움이됩니다.
그러나이 모든 단계를 수행 한 후에도 여전히 Swift에서 Objective-C 클래스를 얻지 못했습니다.
cocoapods
라이브러리를 사용하여 프로젝트에 통합했습니다. 어느 것입니다 pod "pop"
.
따라서 Swift에서 Objective-C 포드를 사용하는 import
경우 클래스를 Swift로 가져올 수 없거나 기회가 없을 수 있습니다 .
당신이해야 할 간단한 일은 :
<YOUR-PROJECT>-Bridging-Header
파일로 이동하여#import <ObjC_Framework>
을@import ObjC_Framework
예 : (팝 라이브러리)
바꾸다
#import <pop/POP.h>
와
@import pop;
작동하지 않을 clang import
때 사용하십시오 #import
.
문서 에서 인용 :
모듈로 액세스 할 수있는 Objective-C 프레임 워크 (또는 C 라이브러리)는 Swift로 직접 가져올 수 있습니다. 여기에는 Foundation, UIKit 및 SpriteKit과 같은 모든 Objective-C 시스템 프레임 워크와 시스템과 함께 제공되는 공통 C 라이브러리가 포함됩니다. 예를 들어 Foundation을 가져 오려면이 import 문을 작업중인 Swift 파일 맨 위에 추가하면됩니다.
import Foundation
이 가져 오기를 통해 NSDate, NSURL, NSMutableData 및 모든 메소드, 속성 및 범주를 포함한 모든 Foundation API를 Swift에서 직접 사용할 수 있습니다.
Objective-C 라이브러리를 Swift에 추가하려는 사람을위한 참고 사항 : 빌드 설정 -> 링크 -> 기타 링커 플래그 에서 -ObjC 를 추가해야합니다 .
Xcode 10.1의 Swift 4.2.1 프로젝트에서 Objective-C 파일을 쉽게 추가 할 수 있습니다. Objective-C 파일을 Swift 프로젝트에 브릿지하려면 아래 단계를 따르십시오.
Step_01 : Swift 언어를 사용하여 새 Xcode 프로젝트를 작성하십시오.
File
> New
> Project
> objc
.
Step_02 : Swift 프로젝트에서 새로운 Objective-C 파일을 추가하십시오 :
File
> New
> File...
> macOS
> Objective-C File
.
Step_03 : 새로운 Objective-C 파일을 Swift 프로젝트에 처음 추가하면 Xcode가 다음을 묻습니다.
Would you like to configure an Objective-C bridging header
?
Step_04 : 옵션을 선택하십시오 :
Create Bridging Header
.
Step_05 : 해당 파일이 이름으로 생성됩니다 :
Objc-Bridging-Header.h
.
Step_06 : 이제 브리지 헤더에 브리지 파일 경로를 설정해야합니다. Project Navigator에서 이름이있는 프로젝트를 클릭 objc
한 후 다음을 선택하십시오.
Build Settings
> Objective-C Bridging Header
> Objc-Bridging-Header.h
.
Step_07 : Objc-Bridging-Header.h
파일 상자를 드래그 앤 드롭하여 파일 경로를 생성하십시오.
Step_08 : Objc-Bridging-Header.h
파일을 열고 Swift 파일에서 사용하려는 Objective-C 파일을 가져옵니다.
#import "SpecialObjcFile.m"
내용은 다음과 같습니다 SpecialObjcFile.m
.
#import <Foundation/Foundation.h>
@interface Person: NSObject {
@public
bool busy;
}
@property
bool busy;
@end
Step_09 : 이제 Swift 파일에서 Objective-C 클래스를 사용할 수 있습니다.
override func viewDidLoad() {
super.viewDidLoad()
let myObjcContent = Person()
print(myObjcContent.busy)
}
Logans 응답 은 최신 Swift 5
오류를 제외하고는 정상적으로 작동합니다 . 컴파일러 오류가 있습니다. 다음은 Swift 5를 사용하는 사람들을위한 수정 사항입니다.
import Foundation
class MySwiftObject : NSObject {
var someProperty: AnyObject = "Some Initializer Val" as AnyObject
override init() {}
func someFunction(someArg:AnyObject) -> String {
let returnVal = "You sent me \(someArg)"
return returnVal
}
}
헤더 .h
및 구현 .m
파일 추가 -Cocoa 클래스 파일 (Objective-C)
예를 들어MyFileName
클릭
할 때 브리징 헤더 구성 Would you like to configure an Objective-C bridging header
- 예
<target_name>-Bridging-Header.h
자동으로 생성됩니다브리징 - 헤더에 클래스 추가
에 <target_name>-Bridging-Header.h
줄을 추가#import "<MyFileName>.h"
추신 기존 Objective-C 파일을 Swift 프로젝트에 추가해야하는 경우 Bridging-Header.h
미리 추가하십시오.
추가 <MyFileName>.swift
및 확장NSObject
Swift 파일을 ObjC 클래스로 가져 오기 Objective-C 파일에
추가#import "<#YourProjectName#>-Swift.h"
공개 스위프트 코드 표시 [@objc 및 @objcMembers]
애플은이 문서에 공식 가이드를 제공하고 있습니다 방법 - 투 - 콜 목표 - C-코드에서-빠른
관련 부분은 다음과 같습니다.
동일한 앱 대상 내에서 Objective-C 파일 세트를 Swift 코드로 가져 오려면 Objective-C 브리징 헤더 파일을 사용하여 해당 파일을 Swift에 노출시킵니다 . Xcode는 기존 Objective-C 앱에 Swift 파일을 추가하거나 기존 Swift 앱에 Objective-C 파일을 추가 할 때이 헤더를 생성합니다.
수락하면 Xcode는 만들고있는 파일과 함께 브리징 헤더 파일을 만들고 제품 모듈 이름과 "-Bridging-Header.h"를 사용하여 이름을 지정합니다. 또는 파일> 새로 만들기> 파일> [운영 체제]> 소스> 헤더 파일을 선택하여 브리징 헤더를 직접 작성할 수 있습니다.
브리징 헤더를 편집하여 Objective-C 코드를 Swift 코드에 노출하십시오.
브리징 헤더에 나열된 모든 공개 Objective-C 헤더는 Swift에 표시됩니다.