当使用
Swift
协议作为函数参数构建 iOS 绑定库项目,或将其公开为公共字段时,会抛出 The type or namespace name 'xxx' could not be found (are you missing a using directive or an assembly reference?)
,即使 xxx
是在 ApiDefinition.cs
中定义的(使用以下命令生成的语法) sharpie
)
示例:
斯威夫特:
@objc(ScanOperation)
public protocol ScanOperation {
@obj(onItemAdded:)
func onItemAdded(itemObj: ItemData)
}
@objc(ScanAgent)
public class ScanAgent : NSObject {
@objc(Initialize:)
public func Initialize(scanOperation: ScanOperation) { }
}
在
sharpie
中生成 ApiDefinitions
语法:
[Protocol]
interface ScanOperation
{
// @required -(void)onItemAdded:(ItemData * _Nonnull)itemObj;
[Abstract]
[Export("onItemAdded:")]
void OnItemAdded(ItemData itemObj);
}
// @interface ScanAgent : NSObject
[BaseType(typeof(NSObject))]
interface ScanAgent
{
// -(void)Initialize:(id<ScanOperation> _Nonnull)scanOperation;
[Export("Initialize:")]
void Initialize(ScanOperation scanOperation);
}
这样不会编译,会出现上面的错误。
发生这种情况是因为生成的代码创建了一个带有
I
前缀的接口。
/obj/(Debug/Release)/iOS/<proj>/ScanOperation.g.cs
包含以下内容:
public partial interface IScanOperation : INativeObject, IDisposable
所以生成的代码中不存在
ScanOperation
。
需要做的是在
ApiDefinition.cs
中添加一个空接口并替换函数/字段的签名。
在上面的例子中:
interface IScanOperation { }
// @interface ScanAgent : NSObject
[BaseType(typeof(NSObject))]
interface ScanAgent
{
// -(void)Initialize:(id<ScanOperation> _Nonnull)scanOperation;
[Export("Initialize:")]
void Initialize(IScanOperation scanOperation);
}
更多信息可以在这里在
Binding protocols
部分找到。