Unrecognized selector calling category method in static iOS library
Asked Answered
D

2

14

I am using some third party software to aid in writing an iPad application using Xcode 4.3.2. The software is open source and is usually set up so its code will be compiled along with whatever code the developer writes for the application. Because I was using the software in numerous places, I decided to build it as a static library for the iOS simulator.

I was able to build the library, and convert one application to link to that library instead of compiling the original source code. However, when I go to run the application on the simulator, I get an error that says, unrecognized selector sent to instance.

I have verified that the program is successfully using portions of the static library. However, there is one piece of code that tries to call a method on an object, and that where the failure occurs. The method being called is not actually defined in the interface of that object. Rather it is provided in an additional module that defines a category for that object's class. The header file for that module is properly included and the compiler should have been able to find the category method and apply it to the object, yet at run time, the error mentioned above occurs.

I used the 'nm' command to verify that the category method exists in the static library. Here is an example of the output:

nm libStaticLibrary.a | grep categoryMethod
00000130 t -[SomeClass(Category) categoryMethod:]
0000354c s -[SomeClass(Category) categoryMethod:].eh

What ideas do people have about how this library can be made to work correctly with the desired application?

Discountenance answered 4/5, 2012 at 4:16 Comment(3)
Add -ObjC linker flag as explained here: #2567998Admittance
possible duplicate of linking objective-c categories in a static libraryAdmittance
It doesn't work in my project. I have imported the category header but didn't include the corresponding .m in the target compile sources. Build succeeds but crashes at runtime.Taciturn
C
27

Your 3rd party framework is probable using a category on a existing (apple) class. But to load/find the category you need to add the -ObjC flag in the build settings under Other Linker Flags

buildsettings

Christly answered 4/5, 2012 at 5:51 Comment(4)
This must be set in the linker settings for the target using the library, not in the library itself.Bioastronautics
Remember it is -ObjC and not -ObjcCaul
You saved me lot.Sinistrorse
It doesn't work in my project. I have imported the category header but didn't include the corresponding .m in the target compile sources. Build succeeds but crashes at runtime.Taciturn
D
3

Pfitz answer is great, but this will cause the compiler to load a bunch of unused binaries to your project which is not what you want. Please refer to this answer to know why https://mcmap.net/q/16786/-objective-c-categories-in-static-library

Here is the best solution:

1) select your project target from the left panel (the folders navigator)
2) select "Build Phases" tap
3) expand "Compile Sources" cell
4) hit the plus button at the bottom and then add your category's .m file

Done!

Note: you have to search for the file by navigating through the folder by your self, don't type the file's name in the search field

Decastro answered 8/1, 2015 at 11:58 Comment(2)
Doesn't this just effectively copy the .m file to the project, defeating the point of encapsulating the code in a static libary in the first place?Chang
I already had the -ObjC flag, and the -load_all didn't solve it the problem either. This did. Thanks.Pyrenees

© 2022 - 2024 — McMap. All rights reserved.