![](/img/trans.png)
[英]How do I programatically resize a UIButton that already has constraints?
[英]How do I observe a signal and immediately receive a `next` event if it has already occured?
我正在尝试包装网络请求后初始化对象的API调用。 我不希望每个新观察者都发生网络请求,因此据我了解,我不应该使用SignalProducer
。 但是,通过使用单个Signal
,只有它的第一次使用会收到next
事件,而任何新订阅者将永远不会收到当前值。 我应该怎么做? 我可能在做RAC根本上出错的事情。
extension SparkDevice {
static func createMainDeviceSignal() -> Signal<SparkDevice, NSError> {
return Signal {
sink in
SparkCloud.sharedInstance().getDevices { (sparkDevices: [AnyObject]!, error: NSError!) -> Void in
if let error = error {
sink.sendFailed(error)
}
else {
if let devices = sparkDevices as? [SparkDevice] {
if devices.count > 0 {
sink.sendNext(devices[0])
}
}
}
}
return nil
}
}
}
class DeviceAccess {
let deviceSignal: Signal<SparkDevice, NSError>
init() {
self.deviceSignal = SparkDevice.createMainDeviceSignal()
}
}
我考虑过使用MutableProperty
,但这似乎需要一个默认属性,这似乎没有任何意义。
我实际上应该如何处理?
您需要的是多播 。 但是, ReactiveCocoa
3/4并没有提供一种简单的方法(与Rx相对),因为它们通常会导致大量的复杂性。
有时确实很必要,如您的示例所示,并且可以使用PropertyType
轻松实现。
我将从创建发出请求的冷信号开始。 那必须是SignalProducer
:
private func createMainDeviceSignalProducer() -> SignalProducer<SparkDevice, NSError> {
return SignalProducer { observer, _ in
....
}
}
如果你要原样公开此,副作用会发生每到这个制片人是时候start
编辑。 要multicast
这些值,您可以将其包装在属性中,然后公开该property
的producer
:
public final class DeviceAccess {
public let deviceProducer: SignalProducer<SparkDevice, NoError>
private let deviceProperty: AnyProperty<SparkDevice?>
init() {
self.deviceProperty = AnyProperty(
initialValue: nil, // we can use `nil` to mean "value isn't ready yet"
producer: SparkDevice.createMainDeviceSignal()
.map(Optional.init) // we need to wrap values into `Optional` because that's the type of the property
.flatMapError { error in
fatalError("Error... \(error)") // you'd probably want better error handling
return .empty // ignoring errors, but you probably want something better.
}
)
self.deviceProducer = deviceProperty
.producer // get the property producer
.ignoreNil() // ignore the initial value
}
}
现在, DeviceAccess.deviceProducer
将重播底层生产者发出的值,而不是重复产生副作用。 但是请注意,这并不懒惰 :底层的SignalProducer
将立即启动。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.