【问题标题】:How to invoke a Selector in Swift with more than 2 arguments如何在 Swift 中使用超过 2 个参数调用选择器
【发布时间】:2019-08-23 05:47:03
【问题描述】:

我在 Swift 中覆盖了 NSDocumentControllers reviewUnsavedDocuments(withAlertTitle:cancellable:delegate:didReviewAllSelector:contextInfo:)。文档说 didReviewAllSelector 有这个签名,注意它有 3 个参数:

- (void)documentController:(NSDocumentController *)docController  didReviewAll: (BOOL)didReviewAll contextInfo:(void *)contextInfo

所以我需要使用三个参数在delegate 上调用selector。我面临的问题是我似乎无法找到一种快速做到这一点的巧妙方法。

我能找到的最接近的匹配是 NSObject 有 perform(aSelector:with:with:) 带 2 个参数。有这样的东西有 3 个参数吗?

示例代码

func reviewUnsavedDocuments(withAlertTitle title: String?, cancellable: Bool, delegate: Any?, didReviewAllSelector: Selector?, contextInfo: UnsafeMutableRawPointer?) {

  if let object = delegate as? NSObject {
    object.perform(didReviewAllSelector, with: self, with: true ... and
              now I need to add contextInfo as a third paramenter here?
  }
}

我已经使用 NSInvocation 在 obj-c 中成功完成了这项工作。但这不是 swift 提供的 :(

【问题讨论】:

  • 我无法控制delegateselector。它是从框架传递给我的。这是我在 NSDocumentController 上覆盖的系统方法。
  • 我最终编写了一个使用 NSInvocation 的 obj-c 类。

标签: swift nsdocument


【解决方案1】:

使用 @convention(c) 从 Swift 3 开始提供

let methodIMP: IMP! = object.method(for: didReviewAllSelector)
unsafeBitCast(methodIMP,to:(@convention(c)(Any?,Selector,Any?,Bool, OpaquePointer)->Void).self)(object,didReviewAllSelector,self,true,OpaquePointer(contextInfo)) 

我的回答here中涵盖了更多信息和示例。

我相信OpaquePointer 应该适用于您的第三个参数,但如果您遇到任何问题,请告诉我。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2012-03-31
    • 2018-05-27
    • 2013-02-18
    • 2016-10-25
    • 1970-01-01
    相关资源
    最近更新 更多