Kai*_*rdt 6 xcode ios swift swift-extensions swift-protocols
我正在编写媒体播放器应用程序,并创建了自己的框架来管理所有播放器功能.在这个框架中,我有一个名为的公共协议PlayerControllerType和一个内部协议_PlayerControllerType.在PlayerControllerType我已经声明了所有方法和属性,这些方法和属性应该可以从框架外部访问.在_PlayerControllerType我已经定义了几个属性,这些属性由PlayerControllerType框架内部实现的具体类型使用.其中一种类型是PlayerController.其声明如下:
public class PlayerController<Item: Equatable>: NSObject, PlayerControllerType,
_PlayerControllerType, QueueDelegate
Run Code Online (Sandbox Code Playgroud)
现在我想为我的框架中的类提供一些默认实现,它们符合PlayerControllerType和内部_PlayerControllerType,例如:
import Foundation
import MediaPlayer
public extension PlayerControllerType where Self: _PlayerControllerType, Item == MPMediaItem, Self.QueueT == Queue<Item>, Self: QueueDelegate {
public func setQueue(query query: MPMediaQuery) {
queue.items = query.items ?? []
}
}
Run Code Online (Sandbox Code Playgroud)
这在Xcode 7 Beta 4中按预期工作.昨天我更新到Beta 6并得到了这个错误:"Extensions不能公开,因为它的泛型要求使用内部类型"(也见截图).

我发现这个错误很刺激.当然,这延长了我的框架的好处以外没有任何类型,因为它不能访问内部协议_PlayerControllerType,但它是我的框架内的类型的同时实现是非常有用的PlayerControllerType和_PlayerControllerType.
这只是Swift编译器中的一个错误,还是预期的行为?非常不幸的是,这不再适用了,因为现在我必须将这些方法放入一个新创建的基类中,用于所有的PlayerControllers.
任何帮助或反馈将非常感谢.
凯
编辑:以下是协议及其扩展的缩写示例:
public protocol PlayerControllerType {
typealias Item
var nowPlayingItem: Item {get}
func play()
}
protocol _PlayerControllerType {
var nowPlayingItem: Item {get set}
}
public extension PlayerControllerType where Self: _PlayerControllerType {
/*
I want to provide a default implementation of play() for
all my PlayerControllers in my framework (there is more than one).
This method needs to be declared public, because it implements a
requirement of the public protocol PlayerControllerType.
But it cannot be implemented here, because this extension
has the requirement _PlayerControllerType. It needs this requirement,
because otherwise it cannot set the nowPlayingItem. I don't want to
expose the setter of nowPlayingItem.
I could make a base class for all PlayerControllers, but then I'm
restricted to this base class because Swift does not support
multiple inheritance.
*/
public func play() {
if nowPlayingItem == nil {
nowPlayingItem = queue.first
}
// Other stuff
}
}
Run Code Online (Sandbox Code Playgroud)
您需要将_PlayerControllerType协议的访问级别声明为“ public ”。
public protocol _PlayerControllerType {
// some code
}
Run Code Online (Sandbox Code Playgroud)
根据(《Swift 编程语言 - 访问控制》),
公共成员不能定义为具有内部或私有类型,因为该类型可能无法在使用公共变量的所有地方都可用。默认情况下,类被声明为内部类,因此您必须添加 public 关键字以使其成为公共类。
成员(类/协议/函数/变量)不能具有比其参数类型和返回类型更高的访问级别,因为该函数可以在其组成类型不可用于周围代码的情况下使用。
| 归档时间: |
|
| 查看次数: |
3172 次 |
| 最近记录: |