我试图在Swift中创建一个NSTimer,但我遇到了一些麻烦。
NSTimer(timeInterval: 1, target: self, selector: test(), userInfo: nil, repeats: true)
Test()是同一个类中的一个函数。
我在编辑器中得到一个错误:
无法找到一个超载的'init'接受提供的
参数
当我把selector: test()改为selector: nil时,错误就消失了。
我试过了:
选择器:测试()
选择器:测试
选择器:选择器(测试())
但是什么都没用,我在参考文献中找不到解决方案。
objective - c选择器
Selector标识一个方法。
//Compile time
SEL selector = @selector(foo);
//Runtime
SEL selector = NSSelectorFromString(@"foo");
例如
[object sayHello:@"Hello World"];
//sayHello: is a selector
selector是一个来自Objective-C世界的词,你可以从Swift中使用它,有可能从Swift中调用Objective-C,它允许你在运行时执行一些代码
在Swift 2.2之前,语法是:
Selector("foo:")
因为函数名是作为字符串参数("foo")传入Selector的,所以在编译时不可能检查名称。结果你会得到一个运行时错误:
unrecognized selector sent to instance
在Swift 2.2+之后,语法是:
#selector(foo(_:))
Xcode的自动完成功能帮助你调用正确的方法
如果你想从NSTimer中传递一个参数给函数,那么这里是你的解决方案:
var somethingToPass = "It worked"
let timer = NSTimer.scheduledTimerWithTimeInterval(0.01, target: self, selector: "tester:", userInfo: somethingToPass, repeats: false)
func tester(timer: NSTimer)
{
let theStringToPrint = timer.userInfo as String
println(theStringToPrint)
}
在选择器文本(tester:)中包含冒号,参数则放在userInfo中。
你的函数应该以NSTimer作为参数。然后提取userInfo以获得传递的参数。
Swift 2.2+和Swift 3更新
使用新的#selector表达式,它消除了使用字符串文字的需要,使使用更不容易出错。供参考:
Selector("keyboardDidHide:")
就变成了
#selector(keyboardDidHide(_:))
参见:快速进化提案
注意(Swift 4.0):
如果使用# selector,你需要将函数标记为@objc
例子:
@objc func something(_ sender: UIButton)