将源文件类型更改为Objective-C++时,使用GameKit会导致链接器错误。

5

我在我的Objective-C应用中使用Xcode 6.1。

我的应用程序使用GameKit框架。

我试图从我的GameViewController(Objective-C源文件)调用外部C ++方法。

为了使GameViewController.mm编译,我不得不手动将类型设置为“Objective-C ++源”。

然而,即使现在该源代码可以编译,它也会在链接时失败,并显示以下错误:

    Undefined symbols for architecture x86_64:
 "_OBJC_CLASS_$_GLKViewController", referenced from:
      _OBJC_CLASS_$_GameViewController in GameViewController.o
  "_OBJC_METACLASS_$_GLKViewController", referenced from:
      _OBJC_METACLASS_$_GameViewController in GameViewController.o
ld: symbol(s) not found for architecture x86_64
clang: error: linker command failed with exit code 1 (use -v to see invocation)

只有将类型设置为"Objective-C Source"并删除对外部C++函数的调用,才能消除链接器错误。

如果我的源文件编译为"Objective-C++ Source"而不是"Objective-C Source"类型,为什么链接器会失败?

请注意,我在Build-phases正确地链接了GameKit。


".mm"文件不是自动编译为ObjC++代码吗?为什么需要手动设置?无论如何,您可能需要添加对GLKit的引用。 - Bryan Chen
请注意,任何导入/包含C++头文件的类(直接或间接地导入另一个导入C++头文件的头文件)都需要.mm扩展名。如果您将C++头文件放在前缀中,则所有源文件都需要是.mm格式的。 - CodeSmile
哇,这个有点奇怪 - 在从.m更改为.mm后,我不得不在Xcode 8.0中手动添加GLKit框架。 - Charlie Scott-Skinner
1个回答

4

好的。事实证明这是一个奇怪的问题,但是:

我正在链接GameKit,而不是GLKit。 解决方法:同时链接GLKit。

现在,奇怪的部分是如果视图控制器作为Objective-C源代码构建,则不链接GLKit不会导致任何问题。但如果作为Objective-C++源代码构建,则会出现问题。

奇怪,但是真的。


当将代码构建为ObjC代码时,clang会将#import翻译为@import,从而进行链接。我猜这个特性在ObjC++中没有启用。 - Bryan Chen
我曾经遇到过类似的问题,所以我发现这个非常有用。当我将源类型更改为Objective-C++时,我不得不指定链接到MediaPlayer框架(我猜在Objective-C模式下程序也会链接到它)。谢谢! - notadam

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接