如何让 UI_USER_INTERFACE_IDIOM() 与 iPhone OS SDK 一起使用? 3.2

发布于 2024-08-27 20:27:04 字数 768 浏览 8 评论 0原文

Apple 建议使用以下代码来检测是否在 iPad 或 iPhone/iPod Touch 上运行:

if (UI_USER_INTERFACE_IDIOM() == UIUserInterfaceIdiomPad) {
  // The device is an iPad running iPhone 3.2 or later.
  // [for example, load appropriate iPad nib file]
}
else {
  // The device is an iPhone or iPod touch.
  // [for example, load appropriate iPhone nib file]
}

问题是 UI_USER_INTERFACE_IDIOM() 和 UIUserInterfaceIdiomPad 未在 3.2 之前的 SDK 中定义。这似乎完全违背了这样一个功能的目的。它们只能在 iPhone OS 3.2 上编译和运行(iPhone OS 3.2 只能在 iPad 上运行)。因此,如果您可以使用 UI_USER_INTERFACE_IDIOM(),结果将始终指示 iPad。

如果您包含此代码并使用目标操作系统 3.1.3(最新的 iPhone/iPod Touch 操作系统)来测试 iPhone 绑定的通用应用程序代码,您将收到编译器错误,因为这些符号未在 3.1.3 或更早版本中定义,针对 iPhone 模拟器 3.1.3 进行编译时。

如果这是 Apple 推荐的运行时设备检测方法,那么我做错了什么?有人成功使用这种方法进行设备检测吗?

Apple advises using the following code to detect whether running on an iPad or iPhone/iPod Touch:

if (UI_USER_INTERFACE_IDIOM() == UIUserInterfaceIdiomPad) {
  // The device is an iPad running iPhone 3.2 or later.
  // [for example, load appropriate iPad nib file]
}
else {
  // The device is an iPhone or iPod touch.
  // [for example, load appropriate iPhone nib file]
}

The problem is that UI_USER_INTERFACE_IDIOM() and UIUserInterfaceIdiomPad are NOT defined in the SDKs prior to 3.2. This seems to completely defeat the purpose of such a function. They can only be compiled and run on iPhone OS 3.2 (iPhone OS 3.2 can only be run on iPad). So if you can use UI_USER_INTERFACE_IDIOM(), the result will always be to indicate an iPad.

If you include this code and target OS 3.1.3 (the most recent iPhone/iPod Touch OS) in order to test your iPhone-bound universal app code, you will get compiler errors since the symbols are not defined in 3.1.3 or earlier, when compiling for iPhone simulator 3.1.3.

If this is the recommended-by-Apple approach to runtime device-detection, what am I doing wrong? Has anyone succeeded using this approach to device-detection?

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(8

远昼 2024-09-03 20:27:04

我这样做是为了在 3.1.3 和 3.2 中编译代码:

BOOL iPad = NO;
#ifdef UI_USER_INTERFACE_IDIOM
iPad = (UI_USER_INTERFACE_IDIOM() == UIUserInterfaceIdiomPad);
#endif
if (iPad) {
// iPad specific code here
} else {
// iPhone/iPod specific code here
}

我还在这里写了一篇关于它的快速博客文章:
http://www. programbles.com/2010/04/03/compiling-conditional-code-in-universal-iphone-ipad-applications/

I do this to get the code to compile in both 3.1.3 and 3.2:

BOOL iPad = NO;
#ifdef UI_USER_INTERFACE_IDIOM
iPad = (UI_USER_INTERFACE_IDIOM() == UIUserInterfaceIdiomPad);
#endif
if (iPad) {
// iPad specific code here
} else {
// iPhone/iPod specific code here
}

I also wrote a quick blog post about it here:
http://www.programbles.com/2010/04/03/compiling-conditional-code-in-universal-iphone-ipad-applications/

够钟 2024-09-03 20:27:04

这就是我使用的:

- (BOOL) amIAnIPad {
    #if (__IPHONE_OS_VERSION_MAX_ALLOWED >= 30200)
        if ([[UIDevice currentDevice] respondsToSelector: @selector(userInterfaceIdiom)])
            return ([UIDevice currentDevice].userInterfaceIdiom == UIUserInterfaceIdiomPad);
    #endif
    return NO;
}

这有条件编译,因此您仍然可以构建 3.0 sim。然后它检查 UIDevice 类是否响应选择器。如果其中任何一个失败,那么它就不是 iPad。

This is what I use:

- (BOOL) amIAnIPad {
    #if (__IPHONE_OS_VERSION_MAX_ALLOWED >= 30200)
        if ([[UIDevice currentDevice] respondsToSelector: @selector(userInterfaceIdiom)])
            return ([UIDevice currentDevice].userInterfaceIdiom == UIUserInterfaceIdiomPad);
    #endif
    return NO;
}

This conditionally compiles, so you can still build for the 3.0 sim. It then checks to see if the UIDevice class responds to the selector. If either of these fail, it's not an iPad.

旧人哭 2024-09-03 20:27:04

如果这是 Apple 推荐的运行时方法
设备检测,我做错了什么?有没有人成功使用过
这种设备检测方法?

这是运行时检测的解决方案:

#define isIPhone (![[UIDevice currentDevice] respondsToSelector:@selector(userInterfaceIdiom)] || [[UIDevice currentDevice] userInterfaceIdiom] == UIUserInterfaceIdiomPhone)

之后您可以轻松地在代码中的任何位置对其进行测试:

if (isIPhone) { ... }

这与使用 #if / #ifdef 之间的区别在于,这是运行时测试,而 #if 是编译测试 -时间测试。

我认为运行时测试更好,因为在这种情况下,您可以对任何操作系统版本使用一个精确的测试。如果您使用编译时检查,则需要为不同的操作系统版本生成不同的可执行文件。

如果您的问题是编译时错误,您只需针对最新版本的 SDK 进行编译(另请参阅 如何访问iOS中的弱链接框架?)。

If this is the recommended-by-Apple approach to runtime
device-detection, what am I doing wrong? Has anyone succeeded using
this approach to device-detection?

This is solution for runtime detection:

#define isIPhone (![[UIDevice currentDevice] respondsToSelector:@selector(userInterfaceIdiom)] || [[UIDevice currentDevice] userInterfaceIdiom] == UIUserInterfaceIdiomPhone)

After that you can easily test it anywhere in your code:

if (isIPhone) { ... }

The difference between this and using #if / #ifdef is that this is runtime testing, while #if is compile-time testing.

I think the runtime testing is better, because you can use one exactable for any OS version in this case. If you use compile-time check, you'll need to produce different executables for different OS versions.

If your problem is compile-time errors, you just should compile against last version of SDK (see also How to access weak linked framework in iOS?).

负佳期 2024-09-03 20:27:04

我相信答案就是不要尝试在 iPhone 模拟器 3.1.3 或更早版本上运行代码。始终使用 3.2 SDK 进行编译。 iPhone 模拟器 3.2 将为您提供 iPad 模拟器,或者为 iPhone 设备 3.2 进行编译并将应用程序放在手机上进行测试。

无法针对 3.2 SDK 进行编译并使用 3.1.3 或更早版本的模拟器。

I believe the answer is simply do not attempt to run the code on iPhone simulator 3.1.3 or earlier. Always compile with a 3.2 SDK. The iPhone simulator 3.2 will get you the iPad simulator, or compile for iPhone Device 3.2 and put the app on a phone to test it.

There is no way to compile against 3.2 SDK and use a 3.1.3 or earlier simulator.

没︽人懂的悲伤 2024-09-03 20:27:04

我使用的不是任何基于编译器的东西:

- (BOOL)deviceIsAnIPad {
if ([[UIDevice currentDevice] respondsToSelector:@selector(userInterfaceIdiom)])
    //We can test if it's an iPad. Running iOS3.2+
    if ([[UIDevice currentDevice] userInterfaceIdiom] == UIUserInterfaceIdiomPad)
        return YES; //is an iPad
    else 
        return NO; //is an iPhone
else 
    return NO; //does not respond to selector, therefore must be < iOS3.2, therefore is an iPhone
}

Instead of any compiler based stuff I use:

- (BOOL)deviceIsAnIPad {
if ([[UIDevice currentDevice] respondsToSelector:@selector(userInterfaceIdiom)])
    //We can test if it's an iPad. Running iOS3.2+
    if ([[UIDevice currentDevice] userInterfaceIdiom] == UIUserInterfaceIdiomPad)
        return YES; //is an iPad
    else 
        return NO; //is an iPhone
else 
    return NO; //does not respond to selector, therefore must be < iOS3.2, therefore is an iPhone
}
德意的啸 2024-09-03 20:27:04

声明使用它

#ifdef UI_USER_INTERFACE_IDIOM
#define IS_IPAD (UI_USER_INTERFACE_IDIOM() == UIUserInterfaceIdiomPad)
#else
#define IS_IPAD false
#endif

,然后使用检查,如下所示

#define DetailLabel_PosX (IS_IPAD ? 200 : 160)

还有一些用于检查 iphone 5 的定义

#define IS_IPHONE5 (([[UIScreen mainScreen] bounds].size.height-568)?NO:YES)
#define IOS_OLDER_THAN_6 ([[[UIDevice currentDevice] systemVersion] floatValue] < 6.0 )
#define IOS_NEWER_OR_EQUAL_TO_6 ([[[UIDevice currentDevice] systemVersion] floatValue] >= 6.0 )

Declare using this

#ifdef UI_USER_INTERFACE_IDIOM
#define IS_IPAD (UI_USER_INTERFACE_IDIOM() == UIUserInterfaceIdiomPad)
#else
#define IS_IPAD false
#endif

then use check as below

#define DetailLabel_PosX (IS_IPAD ? 200 : 160)

There are also some define for checking iphone 5

#define IS_IPHONE5 (([[UIScreen mainScreen] bounds].size.height-568)?NO:YES)
#define IOS_OLDER_THAN_6 ([[[UIDevice currentDevice] systemVersion] floatValue] < 6.0 )
#define IOS_NEWER_OR_EQUAL_TO_6 ([[[UIDevice currentDevice] systemVersion] floatValue] >= 6.0 )
豆芽 2024-09-03 20:27:04

这似乎完全违背了这样一个函数的目的。他们
只能在iPhone上编译运行
OS 3.2(iPhone OS 3.2只能运行
在 iPad 上)。所以如果你可以使用
UI_USER_INTERFACE_IDIOM(),结果
始终表示 iPad。

这是完全错误的。它可以在 3.2 的 Base SDK 上编译,但如果您正确设置部署目标,则可以在任何操作系统上运行。

This seems to completely defeat the purpose of such a function. They
can only be compiled and run on iPhone
OS 3.2 (iPhone OS 3.2 can only be run
on iPad). So if you can use
UI_USER_INTERFACE_IDIOM(), the result
will always be to indicate an iPad.

This is completely incorrect. It can be compiled on Base SDK of 3.2, but it can be run on any OS, if you set the deployment target appropriately.

呆头 2024-09-03 20:27:04

UI_USER_INTERFACE_IDIOM() 和 UIUserInterfaceIdiomPad 可以在 iOS3.2 及更高版本上使用,重要的部分是“向上”。当然。 iOS3.2仅适用于iPad,但iOS4.0及更高版本可在iPhone和iPad上运行,因此检查并不像您想象的那样毫无意义。

UI_USER_INTERFACE_IDIOM() and UIUserInterfaceIdiomPad can be used on iOS3.2 and upwards, the important part being the 'upwards'. Sure. iOS3.2 is only for iPad, but iOS4.0 and beyond run on both iPhones and iPads, so the check isn't as pointless as you think.

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文