Как вызвать код Objective-C из Swift

На новом языке Swift от Apple, как вы вызываете Objective-C код?

Apple упомянула, что они могут сосуществовать в одном приложении, но означает ли это, что можно технически повторно использовать старые классы, сделанные в Objective-C, при создании новых классов в Swift?

Рассуждение

Objective-C - независимый от платформы язык, тогда как Swift зависит от платформы. Таким образом, писать не-платформенно-зависимый код (библиотеки бизнес-логики) в Swift не было бы разумным. Однако писать код, зависящий от платформы, в нем (например, связанный с интерфейсом) было бы прекрасно. Не сказать, что это будет хорошая идея, однако это определенно интерес.

855
задан David Mulder 02 июня '14 в 23:05
источник поделиться
16 ответов

Использование Objective-C Классы в Swift

** Если у вас есть существующий класс, который вы хотите использовать, выполните Шаг 2, а затем перейдите к Шаг 5. (В некоторых случаях я должен был добавить явный #import <Foundation/Foundation.h в старый Objective-C файл.) **

Шаг 1: Добавить Objective-C Реализация -.m

Добавьте файл .m в свой класс и назовите его CustomObject.m.

Шаг 2: Добавить заголовок заголовка

При добавлении файла .m вы, скорее всего, получите приглашение, которое выглядит так:

Enter image description here

Нажмите YES!

Если вы не увидели приглашение или случайно удалили заголовок моста, добавьте в проект новый файл .h и назовите его <#YourProjectName#>-Bridging-Header.h.

В некоторых ситуациях, особенно при работе с фреймами Objective-C, вы не добавляете класс Objective-C явно, и Xcode не может найти компоновщик. В этом случае создайте файл .h, названный так, как указано выше, затем убедитесь, что вы связали его путь в настройках целевого проекта следующим образом:

Enter image description here

Примечание

Лучше всего связать ваш проект с помощью макроса $(SRCROOT), чтобы при перемещении вашего проекта или работе с ним с другими пользователями с помощью удаленного репозитория он все равно будет работать. $(SRCROOT) можно рассматривать как каталог, содержащий ваш файл .xcodeproj. Это может выглядеть так:

$(SRCROOT)/Folder/Folder/<#YourProjectName#>-Bridging-Header.h

Шаг 3: Добавить Objective-C Заголовок -.h

Добавьте еще один .h файл и назовите его CustomObject.h.

Шаг 4: Создайте класс Objective-C

В 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

Шаг 5: добавьте класс в заголовок-заголовок

В YourProject-Bridging-Header.h:

#import "CustomObject.h"

Шаг 6: Используйте свой объект

В SomeSwiftFile.swift:

var instanceOfCustomObject: CustomObject = CustomObject()
instanceOfCustomObject.someProperty = "Hello World"
println(instanceOfCustomObject.someProperty)
instanceOfCustomObject.someMethod()

Нет необходимости явно импортировать; это то, для чего нужен мостовой заголовок.

Использование классов Swift в Objective-C

Шаг 1: Создать новый класс Swift

Добавьте в проект файл .swift и назовите его MySwiftObject.swift.

В MySwiftObject.swift:

import Foundation

class MySwiftObject : NSObject {

    var someProperty: AnyObject = "Some Initializer Val"

    init() {}

    func someFunction(someArg:AnyObject) -> String {
        var returnVal = "You sent me \(someArg)"
        return returnVal
    }   
}

Шаг 2. Импорт файлов Swift в класс ObjC

В SomeRandomClass.m:

#import "<#YourProjectName#>-Swift.h"

Файл: <#YourProjectName#>-Swift.h должен быть создан автоматически в вашем проекте, даже если вы его не видите.

Шаг 3: Используйте свой класс

MySwiftObject * myOb = [MySwiftObject new];
NSLog(@"MyOb.someProperty: %@", myOb.someProperty);
myOb.someProperty = @"Hello World";
NSLog(@"MyOb.someProperty: %@", myOb.someProperty);
NSString * retString = [myOb someFunction:@"Arg"];
NSLog(@"RetString: %@", retString);

Примечание:

1. CodeCompletion не вел себя так точно, как хотелось бы. В моей системе быстрый запуск с помощью "cmd + r", похоже, помог Swift найти код Objective-C и наоборот.

2. Если вы добавите файл .swift в более старый проект и получите ошибку: dyld: Library not loaded: @rpath/libswift_stdlib_core.dylib, попробуйте полностью перезапустить Xcode..

3. В то время как изначально возможно использовать чистые классы Swift в Objective-C с помощью префикса @objc, после Swift 2.0 это невозможно. См. Историю изменений для оригинального объяснения. Если эта функциональность будет повторно включена в будущих версиях Swift, ответ будет соответствующим образом обновлен.

1256
ответ дан Logan 03 июня '14 в 3:12
источник поделиться

См. руководство Apple в Использование Swift с Cocoa и Objective-C. В этом руководстве описывается использование Objective-C и кода C из Swift и наоборот, а также рекомендации по преобразованию проекта или его смешению и соответствия Objective-C/C и деталям Swift в существующем проекте.

Компилятор автоматически генерирует синтаксис Swift для вызова функций C и методов Objective-C. Как видно из документации, этот Objective-C:

UITableView *myTableView = [[UITableView alloc] initWithFrame:CGRectZero style:UITableViewStyleGrouped];

превращается в этот код Swift:

let myTableView: UITableView = UITableView(frame: CGRectZero, style: .Grouped)

Xcode также выполняет этот перевод "на лету" - вы можете использовать "Открыть быстро" при редактировании файла Swift и ввести имя класса Objective-C, и оно перенесет вас в версию заголовка класса Swift. (Вы также можете получить это, нажав cmd на символ API в файле Swift.) И вся справочная документация API в iOS 8 и OS X v10.10 (Yosemite) библиотеки разработчиков видны как в формах Objective-C, так и в Swift (например, UIView).

106
ответ дан rickster 02 июня '14 в 23:43
источник поделиться

Ниже приведены пошаговые инструкции по использованию кода Objective-C (в данном случае, рамки, предоставленной сторонней стороной) в проекте Swift:

В простых шагах:

  • Появится приглашение, а затем нажмите OK... Если он не появится, мы создадим его вручную, как в следующем... Создайте один заголовочный файл из источника iOS и укажите имя ProjectName-Bridging -Header (пример: Test-Bridging-Header), а затем перейдите к настройке сборки в коде компилятора Swift → Objective-C bridge add Objective-C имя моста.. (Test/Test-Bridging-Header.h). Да, это завершено.

  • Необязательно удалите добавленный Objective-C файл (названный "ничего" в изображении GIF выше). Вам это больше не нужно.

  • Откройте файл заголовка моста. Имя файла имеет вид [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
}

Что это!

Примечание. Если вы удаляете заголовочный файл моста из вашего проекта, обязательно зайдите в "Настройки сборки" и удалите значение для " Objective-C" Мостовой заголовок "в" Быстрый компилятор - генерация кода".

53
ответ дан derrrick 12 февр. '15 в 22:34
источник поделиться

Вы можете прочитать хороший пост 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)
  })

Также посмотрите документ Apple С помощью Swift с Cocoa и Objective-C.

33
ответ дан Jake Lin 04 июня '14 в 5:11
источник поделиться

Я написал простой проект Xcode 6, который показывает, как смешивать С++, Objective-C и код Swift:

https://github.com/romitagl/shared/tree/master/C-ObjC-Swift/Performance_Console

В частности, пример вызывает функцию Objective-C и С++ из Swift.

Ключом является создание общего заголовка Project-Bridging-Header.h и размещение заголовков Objective-C.

Пожалуйста, загрузите проект в качестве полного примера.

21
ответ дан Gian Luigi Romita 13 июня '14 в 13:10
источник поделиться

Цитата из documentation:

Любая инфраструктура Objective-C (или библиотека C), доступная как модуль могут быть импортированы непосредственно в Swift. Сюда входят все Objective-C системные рамки, такие как Foundation, UIKit и SpriteKit, а также общие библиотеки C, поставляемые с системой. Для Например, чтобы импортировать Foundation, просто добавьте этот оператор импорта в вверху файла Swift, в котором вы работаете:

import Foundation

Этот импорт делает все базовые API-интерфейсы, включая NSDate, NSURL, NSMutableData и все их методы, свойства и категорий, доступных непосредственно в Swift.

19
ответ дан Gergo Erdosi 02 июня '14 в 23:43
источник поделиться

Еще одна вещь, которую я хотел бы добавить здесь:

Я очень благодарен за ответ @Logan. Он очень помогает создавать файл моста и настройки.

Но после выполнения всех этих шагов я все еще не получаю класс Objective-C в Swift.

Я использовал библиотеку cocoapods и интегрировал ее в свой проект. Что такое pod "pop".

Поэтому, если вы используете объекты Objective-C в Swift, тогда может возникнуть вероятность того, что вы не сможете получить или import классы в Swift.

Простая вещь, которую вы должны сделать, это:

  1. Перейдите в <YOUR-PROJECT>-Bridging-Header file и
  2. Заменить оператор #import <ObjC_Framework> на @import ObjC_Framework

Например: (поп-библиотека)

замещать

#import <pop/POP.h>

с

@import pop;

Использовать clang import когда #import не работает.

17
ответ дан Kampai 16 сент. '15 в 10:00
источник поделиться

Просто обратите внимание на тех, кто пытается добавить библиотеку Objective-C в Swift: вы должны добавить -ObjC в настройках сборки → Связывание → Другие флаги компоновщика.

9
ответ дан david72 20 марта '16 в 20:53
источник поделиться

После того, как вы создали заголовок Bridging, перейдите в "Настройка сборки" = > "Искать" Objective-C "Мостовой заголовок".

Ниже вы найдете файл с именем "Objective-C сгенерированный интерфейс заголовка".

Импортируйте этот файл в свой контроллер.

Пример: В моем случае: "Dauble-Swift.h"

eEter image description here

5
ответ дан Avijit Nagare 25 нояб. '15 в 11:29
источник поделиться

Нажмите меню "Новый файл" и выберите язык выбора файла Цель. В это время он автоматически генерирует файл Objective-C Bridging Header ", который используется для определения некоторого имени класса.

"Objective-C Мостовой заголовок" в разделе "Быстрый компилятор - генерация кода".

4
ответ дан Yogesh shelke 10 сент. '15 в 15:16
источник поделиться
  • Создайте файл .h из файла NewFile → Source → header
  • Затем сохраните имя файла Your_Target_Name-Bridging-Header.h. Люди здесь часто ошибаются, беря имя своего проекта, но это должно быть имя проекта, если в обоих случаях разные, как правило, они одинаковы.
  • Затем в настройках сборки найдите Objective-C флаг заголовка Bridging Header и поместите адрес вашего вновь созданного файла моста, вы можете сделать его правой кнопкой мыши по файлу → показать в finder → перетащить файл в текстовую область, затем адрес будет заполнен.
  • Использование #import Your_Objective-C_file.h
  • В быстром файле вы можете получить доступ к файлу ObjC, но только по быстрому языку.
3
ответ дан Nish 29 июня '17 в 9:38
источник поделиться

enter image description here Я добавил проект на github, который включает небольшой образец для вызова объектного кода c из swift.

Вызов класса ObjectiveC из swift

2
ответ дан CrazyPro007 19 мая '18 в 19:27
источник поделиться

Любая инфраструктура Objective-C (или библиотека C), доступная как модуль, может быть импортирована непосредственно в Swift. Сюда входят все системные рамки Objective-C, такие как Foundation, UIKit и SpriteKit, а также общие библиотеки C, поставляемые с системой. Например, чтобы импортировать Foundation, просто добавьте этот оператор импорта в начало файла Swift, в котором вы работаете:

import Foundation

Этот импорт включает все базовые API-интерфейсы, включая NSDate, NSURL, NSMutableData и все их методы, свойства и категории, непосредственно доступные в Swift.

Я взял это из документации Apple.

2
ответ дан user4601102 28 сент. '16 в 10:12
источник поделиться

В проекте Swift 4.2.1 в Xcode 10.1 вы можете легко добавить файл Objective-C. Выполните следующие шаги, чтобы сфокусировать файл Objective-C в проекте Swift.

Step_01: Создайте новый проект Xcode с использованием языка Swift:

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?

enter image description here

Step_04: Выберите параметр:

Create Bridging Header.

Step_05: Будет создан соответствующий файл с именем:

Objc-Bridging-Header.h.

enter image description here

Шаг_06: Теперь вам нужно установить путь к файлу Bridge в заголовке моста. В Project Navigator нажмите проект с именем objc а затем выберите:

Build Settings > Objective-C Bridging Header > Objc-Bridging-Header.h.

Step_07: Перетащите свой Objc-Bridging-Header.h в это поле, чтобы создать путь к файлу.

enter image description here

Step_08: Откройте файл Objc-Bridging-Header.h и импортируйте файл Objective-C, который вы хотите использовать в вашем файле Swift.

#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)
}

enter image description here enter image description here

1
ответ дан ARGeo 13 июня '18 в 0:43
источник поделиться

Двусторонний подход к объективному объекту-c

1

1. Create bridge-header.h file in Xcode Project
2. import .h file in bridge-Header file
3. Set path of bridge-Header in Build settings. 
3. Clean the Project 

2

  1. Create objective-c files in project(it automatically set path in Build Settings for you )
  2. import .h file in bridge-Header file

Теперь хорошо идти Спасибо

1
ответ дан Sanjay Mali 13 апр. '18 в 12:39
источник поделиться

Первый шаг: -

Если вы добавляете объективный файл c, где ваш проект был создан на языке быстрой передачи, вы получаете такой вариант, как ниже

введите описание изображения здесь

создать мостовой файл заголовка отсюда или добавить новое имя файла заголовка моста как

Имя_проекта (название проекта) -Bridging-Header.h

импортировать Objective C ".h" файл в заголовке, например,

#ifndef Test_Bridging_Header_h
#define Test_Bridging_Header_h

#import "TestViewController.h" /*Objective C file*/

#endif /* Test_Bridging_Header_h */

Второй шаг: -

Связывание заголовка моста с вашей целью

Цель проекта → Настройка сборки. Обновите эти свойства.

"Определяет модуль": ДА.

"Всегда вставлять быстрые стандартные библиотеки": ДА.

"Установить Objective-C Заголовок совместимости": ДА.

введите описание изображения здесь

0
ответ дан Darshan Panchal 05 дек. '17 в 6:30
поделиться

Другие вопросы по меткам или Задайте вопрос