用于iPhone测试的通用iPhone / iPad应用程序调试编译错误

时间:2010-04-11 22:07:40

标签: iphone ios ipad ios-universal-app

我已经编写了一个iPhone和iPad通用应用程序,可以在Xcode上的iPad模拟器中正常运行,但我现在想测试iPhone的功能。我似乎无法使用此代码运行iPhone模拟器,因为它始终默认为iPad?

相反,我尝试在设备上运行,当它开始运行时,我收到以下错误:

dyld: Symbol not found: _OBJC_CLASS_$_UISplitViewController
  Referenced from: /var/mobile/Applications/9770ACFA-0B88-41D4-AF56-77B66B324640/Test.app/Test
  Expected in: /System/Library/Frameworks/UIKit.framework/UIKit in /var/mobile/Applications/9770ACFA-0B88-41D4-AF56-77B66B324640/Test.app/TEST

由于App是以编程方式而不是使用XIB构建的,因此我使用main.m方法中的以下行拆分了2个设备逻辑:

if (UI_USER_INTERFACE_IDIOM() == UIUserInterfaceIdiomPad)
{
    retVal = UIApplicationMain(argc, argv, nil, @"AppDelegate_Pad");
}
else
{
    retVal = UIApplicationMain(argc, argv, nil, @"AppDelegate_Phone");
}

从那时起,他们使用不同的AppDelegates,我检查了我的标题,以确保永远不会使用UISplitView,也不会通过Phone逻辑导入。

如何避免此错误,是否有更好的方法在这个以编程方式创建的应用程序中拆分通用逻辑路径?

3 个答案:

答案 0 :(得分:66)

由于您未对UIKit框架进行弱连接,因此触发了该错误。 iPhone OS 3.2中的UIKit框架添加了UISplitViewController,如果你正常链接它,你的应用程序将假设这些符号存在于3.0,而不是。

要弱化链接框架,请在Xcode中找到您的应用程序目标,检查它,然后转到“常规”选项卡。该选项卡的底部应该是框架列表,其中包含Type列。将UIKit的类型从Required更改为Weak并重建您的应用程序。这应该处理运行时错误。

您的条件逻辑是合理的,但我倾向于共享一个应用程序委托,并在接下来的行中进行特定于接口的布局。

(更新:12/21/2011)从iOS 4.2开始,您不再需要弱链接框架来防止这样的错误。如Marco Arment describes,如果您使用iOS 4.2或更高版本构建并定位到iPhone OS 3.1+,则各个类现在都是弱链接的,并且如果该类的话,它们的+class方法应返回nil在当前运行的操作系统版本中不存在。

答案 1 :(得分:4)

我有一个非常类似的错误,这让我疯了! :-)搜索几个小时,无法弄清楚......

就像你说的那样,在iPad模拟器中运行时一切都很好但是当试图用iPhone OS 3.1.2在iPhone上测试应用程序时,它甚至不会启动但是崩溃并出现以下错误消息:

  

mi_cmd_stack_list_frames堆栈中没有足够的帧

通过检查几乎所有代码行,我意识到分配3.2类如UIPopoverController或UISplitViewController(已经在分叉的iPad特定代码中)导致了这个问题。

所以而不是即:。

  

infoPopover = [[UIPopoverController alloc] initWithContentViewController:infoNavController];

我会写

  

infoPopover = [[NSClassFromString(@“UIPopoverController”)alloc] initWithContentViewController:infoNavController];

这解决了我的问题! (如果错误消息没有告诉你哪里可能找到bug,那么调试可能会很难......)

答案 2 :(得分:0)

Xcode 8.3,iPad 2(非视网膜),Swift 3代码

对我有帮助的是:

  • 重启Xcode
  • 做一个'产品 - >清理' Shift 命令 K
  • 重建项目