读取 NSTimer 子类的 public var valid 失败并显示 'isValid only defined for abstract class'
reading public var valid of subclass of NSTimer fails with 'isValid only defined for abstract class'
我创建了一个 NSTimer 的子class,它添加(我希望)暂停和恢复功能到 scheduledTimerWithTimeInterval 函数。
class HCTimer: NSTimer {
var hcTimerInterval :NSTimeInterval!
var hcTarget :AnyObject!
var hcSelector :Selector!
var hcUserInfo :AnyObject!
var hcRepeats :Bool!
var hcTimer :HCTimer!
class func pausableScheduledTimerWithTimeInterval(ti: NSTimeInterval, target aTarget: AnyObject, selector aSelector: Selector, userInfo: AnyObject?, repeats yesOrNo: Bool) -> HCTimer {
let hcInstanceTimer = super.scheduledTimerWithTimeInterval(ti,target: aTarget, selector: aSelector, userInfo: userInfo, repeats: yesOrNo) as! HCTimer
hcInstanceTimer.hcTimerInterval = ti
hcInstanceTimer.hcTarget = aTarget
hcInstanceTimer.hcSelector = aSelector
hcInstanceTimer.hcUserInfo = userInfo!
hcInstanceTimer.hcRepeats = yesOrNo
hcInstanceTimer.hcTimer = hcInstanceTimer
return hcInstanceTimer
}
func pause() {
self.invalidate()
}
func resume() {
self.hcTimer = HCTimer.pausableScheduledTimerWithTimeInterval(hcTimerInterval, target: hcTarget, selector: hcSelector, userInfo: hcUserInfo, repeats: hcRepeats)
}
}
为了在现有 viewController 中使用新的 class,我将 NSTimer 类型的现有属性替换为 HCTimer。按下按钮时启动定时器,定时器无效。
class ViewController: UIViewController {
var severityButtonTimer = HCTimer()
@IBAction func sortOnSeverityButtonTouchInside(sender: UIButton) {
// Start animation if none running
if (!severityButtonTimer.valid) {
// Change sort order
代码编译成功,但是当函数读取 HCTimer 实例的值 'valid' 时,它失败并出现以下异常。
2016-04-08 12:03:25.234 homecaremonitor[45750:17518480] *** Terminating app due to uncaught exception 'NSInvalidArgumentException', reason: '*** -isValid only defined for abstract class. Define -[homecaremonitor.HCTimer isValid]!'
*** First throw call stack:
(
0 CoreFoundation 0x000000010f4c5d85 __exceptionPreprocess + 165
1 libobjc.A.dylib 0x0000000111269deb objc_exception_throw + 48
2 CoreFoundation 0x000000010f4c5cbd +[NSException raise:format:] + 205
3 Foundation 0x000000010f9477b9 NSRequestConcreteImplementation + 229
4 Foundation 0x000000010f95aa19 -[NSTimer(NSTimer) isValid] + 39
5 homecaremonitor 0x000000010ef43f78
仍在尝试解决此问题,感谢您的帮助!
干杯,
彼得
根据 Wain
的建议,将子 class HCTimer
替换为 HCTimerWrapper
class HCTimerWrapper {
var hcTimerInterval :NSTimeInterval!
var hcTarget :AnyObject!
var hcSelector :Selector!
var hcUserInfo :AnyObject!
var hcRepeats :Bool!
var hcTimer :NSTimer!
var valid : Bool {
get {
if hcTimer != nil {
return hcTimer.valid
} else {
return false
}
}
}
func pausableScheduledTimerWithTimeInterval(ti: NSTimeInterval, target aTarget: AnyObject, selector aSelector: Selector, userInfo: AnyObject?, repeats yesOrNo: Bool) {
let hcInstanceTimer = NSTimer.scheduledTimerWithTimeInterval(ti,target: aTarget, selector: aSelector, userInfo: userInfo, repeats: yesOrNo)
self.hcTimerInterval = ti
self.hcTarget = aTarget
self.hcSelector = aSelector
self.hcUserInfo = userInfo!
self.hcRepeats = yesOrNo
self.hcTimer = hcInstanceTimer
}
func pause() {
self.hcTimer.invalidate()
}
func resume() {
self.hcTimer = NSTimer.scheduledTimerWithTimeInterval(self.hcTimerInterval, target: self.hcTarget, selector: self.hcSelector, userInfo: self.hcUserInfo, repeats: self.hcRepeats)
}
}
不要创建 NSTimer
的子类,创建一个包装器来公开您需要的功能。您的代码中已经对 hcTimer
以及它的用途和用途有些困惑(我希望这还没有变得明显),您的包装器也可以避免这种情况。
因此,您的包装器将有选择地包含一个 NSTimer
实例。永远不要调用 NSTimer()
- 这实际上是您的代码当前正在做的事情。您应该没有计时器,或者您应该有一个完全创建和计划的计时器实例。
我创建了一个 NSTimer 的子class,它添加(我希望)暂停和恢复功能到 scheduledTimerWithTimeInterval 函数。
class HCTimer: NSTimer {
var hcTimerInterval :NSTimeInterval!
var hcTarget :AnyObject!
var hcSelector :Selector!
var hcUserInfo :AnyObject!
var hcRepeats :Bool!
var hcTimer :HCTimer!
class func pausableScheduledTimerWithTimeInterval(ti: NSTimeInterval, target aTarget: AnyObject, selector aSelector: Selector, userInfo: AnyObject?, repeats yesOrNo: Bool) -> HCTimer {
let hcInstanceTimer = super.scheduledTimerWithTimeInterval(ti,target: aTarget, selector: aSelector, userInfo: userInfo, repeats: yesOrNo) as! HCTimer
hcInstanceTimer.hcTimerInterval = ti
hcInstanceTimer.hcTarget = aTarget
hcInstanceTimer.hcSelector = aSelector
hcInstanceTimer.hcUserInfo = userInfo!
hcInstanceTimer.hcRepeats = yesOrNo
hcInstanceTimer.hcTimer = hcInstanceTimer
return hcInstanceTimer
}
func pause() {
self.invalidate()
}
func resume() {
self.hcTimer = HCTimer.pausableScheduledTimerWithTimeInterval(hcTimerInterval, target: hcTarget, selector: hcSelector, userInfo: hcUserInfo, repeats: hcRepeats)
}
}
为了在现有 viewController 中使用新的 class,我将 NSTimer 类型的现有属性替换为 HCTimer。按下按钮时启动定时器,定时器无效。
class ViewController: UIViewController {
var severityButtonTimer = HCTimer()
@IBAction func sortOnSeverityButtonTouchInside(sender: UIButton) {
// Start animation if none running
if (!severityButtonTimer.valid) {
// Change sort order
代码编译成功,但是当函数读取 HCTimer 实例的值 'valid' 时,它失败并出现以下异常。
2016-04-08 12:03:25.234 homecaremonitor[45750:17518480] *** Terminating app due to uncaught exception 'NSInvalidArgumentException', reason: '*** -isValid only defined for abstract class. Define -[homecaremonitor.HCTimer isValid]!'
*** First throw call stack:
(
0 CoreFoundation 0x000000010f4c5d85 __exceptionPreprocess + 165
1 libobjc.A.dylib 0x0000000111269deb objc_exception_throw + 48
2 CoreFoundation 0x000000010f4c5cbd +[NSException raise:format:] + 205
3 Foundation 0x000000010f9477b9 NSRequestConcreteImplementation + 229
4 Foundation 0x000000010f95aa19 -[NSTimer(NSTimer) isValid] + 39
5 homecaremonitor 0x000000010ef43f78
仍在尝试解决此问题,感谢您的帮助! 干杯, 彼得
根据 Wain
的建议,将子 classHCTimer
替换为 HCTimerWrapper
class HCTimerWrapper {
var hcTimerInterval :NSTimeInterval!
var hcTarget :AnyObject!
var hcSelector :Selector!
var hcUserInfo :AnyObject!
var hcRepeats :Bool!
var hcTimer :NSTimer!
var valid : Bool {
get {
if hcTimer != nil {
return hcTimer.valid
} else {
return false
}
}
}
func pausableScheduledTimerWithTimeInterval(ti: NSTimeInterval, target aTarget: AnyObject, selector aSelector: Selector, userInfo: AnyObject?, repeats yesOrNo: Bool) {
let hcInstanceTimer = NSTimer.scheduledTimerWithTimeInterval(ti,target: aTarget, selector: aSelector, userInfo: userInfo, repeats: yesOrNo)
self.hcTimerInterval = ti
self.hcTarget = aTarget
self.hcSelector = aSelector
self.hcUserInfo = userInfo!
self.hcRepeats = yesOrNo
self.hcTimer = hcInstanceTimer
}
func pause() {
self.hcTimer.invalidate()
}
func resume() {
self.hcTimer = NSTimer.scheduledTimerWithTimeInterval(self.hcTimerInterval, target: self.hcTarget, selector: self.hcSelector, userInfo: self.hcUserInfo, repeats: self.hcRepeats)
}
}
不要创建 NSTimer
的子类,创建一个包装器来公开您需要的功能。您的代码中已经对 hcTimer
以及它的用途和用途有些困惑(我希望这还没有变得明显),您的包装器也可以避免这种情况。
因此,您的包装器将有选择地包含一个 NSTimer
实例。永远不要调用 NSTimer()
- 这实际上是您的代码当前正在做的事情。您应该没有计时器,或者您应该有一个完全创建和计划的计时器实例。