Swift-OC混编

294 阅读2分钟

「这是我参与2022首次更文挑战的第27天,活动详情查看:2022首次更文挑战」。

一、swift怎么用oc定义的宏?

1、在swift中,能直接使用定义为常量的宏,不能使用带有方法调用的宏,也不能使用静态常量。

下面这种定义为常量的宏可以使用
#define APP_LANGUAGE_EN @"en" 
#define kNavigationBarHeight 44.0
 
下面带有方法调用的宏不可以使用
#define kScreenHeight [[UIScreen mainScreen] bounds].size.height
#define kScreenWidth [[UIScreen mainScreen] bounds].size.width

下面带有静态常量swift不能使用,可以改成宏
static NSString *const StopTabRefreshNotifyNameHtml = @"TabRefreshNotifyNameHtml";

2、如何解决?
在公共*.swift文件里面重新定义带有方法调用的宏。

image.png

二、如何加载字符串、图片资源?\

之前我们开发oc组件时候一般会使用宏定义来加载资源,由于在swift不能使用带有方法调用的宏,所以可以专门写一个类,使用静态方法来加载资源

image.png

三、swift组件如何暴露接口给业务方调用?\

由于我们组件化架构是使用BeeHive来暴露接口的,所以swift组件还是得遵循这个规范,仍然可以service和delegate的方式来跟业务方交互

1、暴露接口给业务方使用

image.png 2、获取delegte

image.png

3、怎么判断一个协议是否实现了某个方法?

1)用respondsToSelector判断,判断的方法可以定义为@required或者@optional

if let delegate = ((BHConfig.get(BPChowder.delegateName)) as? BPChowderDelegate) {
            if delegate.responds(to: #selector(BPChowderDelegate.getURLH5(_:))){
                let url = delegate.getURLH5("/faq/privacy")
                BPCommonJumpModel .jump(withRouterUrl: url, fromVC: self, shouldPresent: false)
            }
        }

2)用可选链调用。判断的方法必须定义为@optional,否则编译报错

let delegate = ((BHConfig.get(BPChowder.delegateName)) as? BPChowderDelegate)

        if let url = delegate?.getURLH5?("/faq/privacy"){

            BPCommonJumpModel .jump(withRouterUrl: url, fromVC: self, shouldPresent: false)
        }

4、在Swift组件中会需要创建BeeHive的Service,如BPChowderService,它不能改成swift版,只能使用OC版

原因:BeeHive使用NSClassFromString创建BPChowderService类,若BPChowderService是swift类会创建失败
 
- (Class)serviceImplClass:(Protocol *)service
{
    NSString *serviceImpl = [[self servicesDict] objectForKey:NSStringFromProtocol(service)];
    if (serviceImpl.length > 0) {
        return NSClassFromString(serviceImpl);
    }
    return nil;
}

四、如何使用懒加载属性\

在oc中写业务,经常使用懒加载,swift中懒加载属性写法如下

Swift中懒加载只会执行一次,将属性置为nil,不会再触发懒加载

image.png