связывание категорий target-c в статической библиотеке - PullRequest
37 голосов
/ 25 июля 2011

Я разрабатываю плагин для приложения для iOS.Я собираю его в файл .a, который затем используется основным проектом xcode.

До сих пор я создал категорию класса UIDevice в этой библиотеке.Когда я запускаю основной проект с использованием этой библиотеки, он падает из-за нераспознанного селектора

- [платформа UIDevice]: нераспознанный селектор, отправленный на платформу экземпляра

, является одним из функций, которые я добавил через категорию.

Поэтому я подумал, что эти функции вообще не связаны, и добавил функцию ac в тот же файл, что и категория UIDevice, а затем вызвал ее из моего кода.

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

Мои вопросы: почему xcode игнорирует определение категории, если я не вызываю функцию, объявленную в том же файле?

Есть ли xcodeнастройку я могу изменить, чтобы включить в нее эти методы из категории UIDevice независимо от того, вызываю ли я функцию из этого файла или нет?

cheers

Ответы [ 3 ]

72 голосов
/ 25 июля 2011

Извлечение Создание статических библиотек Objective-C с категориями :

Objective-C не определяет символы компоновщика для каждой функции (или метод в Objective-C) - вместо этого генерируются только символы компоновщика для каждого класса. Если вы расширяете уже существующий класс с категориями, компоновщик не знает, чтобы связать объектный код ядра реализация класса и реализация категории. Это мешает объекты, созданные в результирующем приложении от ответа на селектор, определенный в категории.

Чтобы решить эту проблему, целевое связывание со статической библиотекой должен передать опцию -ObjC компоновщику. Этот флаг вызывает компоновщик загрузить каждый объектный файл в библиотеке, которая определяет Objective-C класс или категория. Хотя эта опция, как правило, приведет к большему исполняемый (из-за дополнительного объектного кода, загруженного в приложение), это позволит успешно создавать эффективные Статические библиотеки Objective-C, которые содержат категории существующих классы.


Важно : для 64-битных приложений и приложений для iPhone OS существует ошибка компоновщика, которая не позволяет -ObjC загружать файлы объектов из статики библиотеки, которые содержат только категории и не содержат классов. Обходной путь использовать флаги -all_load или -force_load.

Источник: @albertamg ( связывание категорий target-c в статической библиотеке )

8 голосов
/ 05 октября 2011

У меня была такая же проблема. Метод, определенный в категории, определенной в подпроекте, привел к нераспознанному исключению селектора. (Фактически это проявлялось в невозможности указать подкласс UILabel в Интерфейсном Разработчике; XIB содержал класс, показанный в IB (UILabel или UIView, в зависимости от того, что я там перетащил), а не класс, который я набрал, и что выглядело как странная ошибка XCode.)

Решение, которое сработало для меня, заключалось в использовании -force_load:

На левой панели выберите ваш основной проект (корневой элемент). Справа вы увидите PROJECT и TARGETS. Выберите TARGETS. Перейдите в «Настройки сборки» (в верхней панели) - «Связывание» - «Другие флаги компоновщика» и, предположив, что ваш подпроект называется XXXXX, добавьте -force_load ${BUILT_PRODUCTS_DIR}/libXXXXX.a там (у элемента есть два подэлемента, Debug и Release, но вы нажимаете на этот составной элемент, чтобы он влиял как на Debug, так и на Release).

Обратите внимание, что -force_load работает для отдельной библиотеки, и вам может потребоваться указать отдельную -force_load для каждой библиотеки подпроекта.

0 голосов
/ 13 июля 2016

У меня была эта проблема, и я потратил около 1 часа на ее решение. Слава Богу! это было сделано. Методы, которые определены, должны быть статического типа!

...