【问题标题】:Using a Macro (Define) in an if/else statement ? Without redefined error在 if/else 语句中使用宏(定义)?没有重新定义的错误
【发布时间】:2021-12-06 14:10:38
【问题描述】:

我知道这不是一种好的编码方式,但是我正在制作从Obj-CSwift 的游戏,但我正在努力让它正确运行我的设备只是为了让我可以回去参考所有内容。

所以,这实际上是一种临时措施!我定义了几个宏,

#define BTNNUMBER_W         60
#define BTNNUMBER_H         60 

它们在代码中被引用,在一个我真的无法拆分 if/else 语句的区域,所以想有效地调试使用;

if(IS_IPHONE_OLD)
    {
    #define BTNNUMBER_W         60
    #define BTNNUMBER_H         60
    }
    else if (IS_IPHONE_5)
    {
    #define BTNNUMBER_W         60
    #define BTNNUMBER_H         60
    }
    else if (IS_IPHONE_6_6S_6P_6SP_7_8)
    {
    #define BTNNUMBER_W         30
    #define BTNNUMBER_H         30
        NSLog(@"iPhone 6 to 8");
    }
    else if (IS_IPHONE_7P_8P)
    {
    #define BTNNUMBER_W         60
    #define BTNNUMBER_H         60
        NSLog(@"iPhone 7P to 8P");
    }
    else if (IS_IPHONE_X)
    {
    #define BTNNUMBER_W         110
    #define BTNNUMBER_H         110
    }

正如已经说过的,实际上只是为了再次“让它工作”,而我重新做这一切,但任何指针都会非常有义务!

#define IS_IPHONE (UI_USER_INTERFACE_IDIOM() == UIUserInterfaceIdiomPhone)
#define IDIOM    UI_USER_INTERFACE_IDIOM()
#define IPAD     UIUserInterfaceIdiomPad


#define SCREEN_WIDTH ([[UIScreen mainScreen] bounds].size.width)
#define SCREEN_HEIGHT ([[UIScreen mainScreen] bounds].size.height)
#define SCREEN_MAX_LENGTH (MAX(SCREEN_WIDTH, SCREEN_HEIGHT))
#define SCREEN_MIN_LENGTH (MIN(SCREEN_WIDTH, SCREEN_HEIGHT))

#define IS_IPHONE_OLD (IS_IPHONE && SCREEN_MAX_LENGTH == 480.0)
#define IS_IPHONE_5 (IS_IPHONE && SCREEN_MAX_LENGTH == 568.0)
#define IS_IPHONE_6_6S_6P_6SP_7_8 (IS_IPHONE && SCREEN_MAX_LENGTH == 667.0)
#define IS_IPHONE_7P_8P (IS_IPHONE && SCREEN_MAX_LENGTH == 736.0)
#define IS_IPHONE_X (IS_IPHONE && SCREEN_MAX_LENGTH == 812.0)

【问题讨论】:

    标签: ios objective-c


    【解决方案1】:

    在 C 和 Objective-C 中,使用预处理器的 #if 而不是编程语言的 if

    #if IS_IPHONE_OLD || IS_IPHONE_5
    #define BTNNUMBER_W         60
    #define BTNNUMBER_H         60
    #elif IS_IPHONE_6_6S_6P_6SP_7_8
    #define BTNNUMBER_W         30
    #define BTNNUMBER_H         30
    // …
    #endif
    

    但是这不起作用,因为您的IS_IPHONE_OLD 等不是编译时常量(它们也不可能,因为同一个应用程序可以在多部手机上运行)。预处理器进行简单的文本替换,所有这些都发生在之前任何代码甚至被解析(因此预处理器)。

    无法在运行时影响预处理器宏,但您只能在运行时知道屏幕尺寸……

    相反,将您的宏切换为同名变量:

    CGFloat BTNNUMBER_W;
    CGFloat BTNNUMBER_H;
    

    然后在使用之前运行的某个函数中,为其赋值:

    if (IS_IPHONE_OLD || IS_IPHONE_5) {
       BTNNUMBER_W = 60;
       BTNNUMBER_H = 60;
    } // …
    

    或者,将变量命名为更好的名称,然后:

    #define BTNNUMBER_W ([[AppDelegate instance] buttonNumberWidth])
    

    在 Swift 中,使用计算属性:

    static var buttonNumberWidth: CGFloat {
        let screenWidth = UIScreen.main.bounds.size.width
        if screenWidth <= 480 {
            return 30
        } // …
    }
    static var buttonNumberHeight: CGFloat { buttonNumberWidth }
    

    【讨论】:

    • 所以如果我使用那个方法; #if IS_IPHONE_OLD || IS_IPHONE_5 #define BTNNUMBER_W 60 #define BTNNUMBER_H 60 #elif IS_IPHONE_6_6S_6P_6SP_7_8 #define BTNNUMBER_W 30 #define BTNNUMBER_H 30 #elif IS_IPHONE_7P_8P #define BTNNUMBER_W 30 #define BTNNUMBER_H 30 #endif 宏由于某种原因是看不见的,并且错误Use of undeclared identifier 'BTNNUMBER_W' 稍后出现在引用它的代码中,是否应该首先对上述内容进行空白定义?在使用预处理器之前?
    • TBH 不清楚您到底要做什么,因为 IS_IPHONE_OLD 不是编译时常量。您能否编辑问题以显示 IS_IPHONE_OLD 的定义究竟如何?我怀疑没有宏的原因是因为您在预处理器中没有任何IS_IPHONE_OLD#defined,并且在这种情况下您没有#else 子句来定义任何内容。
    • 我的错!事实上,我忘记了宏末尾的#else!谢谢,这完全符合我的需要!
    • @DannyRoy 如果它与#else 一起工作,那么结果总是只有#else 部分。所以你可以用#define BTNNUMBER_W 60 替换你的整个东西,而不用任何#ifs。
    猜你喜欢
    • 1970-01-01
    • 2022-07-16
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2018-03-25
    • 2016-07-15
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多