Ich habe es versucht
var timer = NSTimer()
timer(timeInterval: 0.01, target: self, selector: update, userInfo: nil, repeats: false)
Aber ich habe eine Fehlermeldung bekommen
'(timeInterval: $T1, target: ViewController, selector: () -> (), userInfo: NilType, repeats: Bool) -> $T6' is not identical to 'NSTimer'
Das wird funktionieren:
override func viewDidLoad() {
super.viewDidLoad()
// Swift block syntax (iOS 10+)
let timer = Timer(timeInterval: 0.4, repeats: true) { _ in print("Done!") }
// Swift >=3 selector syntax
let timer = Timer.scheduledTimer(timeInterval: 0.4, target: self, selector: #selector(self.update), userInfo: nil, repeats: true)
// Swift 2.2 selector syntax
let timer = NSTimer.scheduledTimerWithTimeInterval(0.4, target: self, selector: #selector(MyClass.update), userInfo: nil, repeats: true)
// Swift <2.2 selector syntax
let timer = NSTimer.scheduledTimerWithTimeInterval(0.4, target: self, selector: "update", userInfo: nil, repeats: true)
}
// must be internal or public.
@objc func update() {
// Something cool
}
Für Swift 4 muss die Methode, von der Sie den Selektor erhalten möchten, Objective-C ausgesetzt werden. Daher muss das @objc
-Attribut zur Methodendeklaration hinzugefügt werden.
Sie können einen Timer verwenden, um eine Aktion mehrmals auszuführen, wie im folgenden Beispiel gezeigt. Der Timer ruft eine Methode zum Aktualisieren eines Etiketts jede halbe Sekunde auf.
Hier ist der Code dafür:
import UIKit
class ViewController: UIViewController {
var counter = 0
var timer = Timer()
@IBOutlet weak var label: UILabel!
// start timer
@IBAction func startTimerButtonTapped(sender: UIButton) {
timer.invalidate() // just in case this button is tapped multiple times
// start the timer
timer = Timer.scheduledTimer(timeInterval: 0.5, target: self, selector: #selector(timerAction), userInfo: nil, repeats: true)
}
// stop timer
@IBAction func cancelTimerButtonTapped(sender: UIButton) {
timer.invalidate()
}
// called every time interval from the timer
func timerAction() {
counter += 1
label.text = "\(counter)"
}
}
Sie können auch einen Timer verwenden, um ein einmaliges Ereignis für eine bestimmte Zeit in der Zukunft zu planen. Der Hauptunterschied zum obigen Beispiel besteht darin, dass Sie repeats: false
anstelle von true
verwenden.
timer = Timer.scheduledTimer(timeInterval: 2.0, target: self, selector: #selector(delayedAction), userInfo: nil, repeats: false)
Das obige Beispiel ruft eine Methode namens delayedAction
zwei Sekunden nach dem Einstellen des Timers auf. Es wird nicht wiederholt, aber Sie können immer noch timer.invalidate()
aufrufen, wenn Sie das Ereignis abbrechen müssen, bevor es jemals passiert.
Auf Swift 4 aktualisiert, unter Nutzung von userInfo:
class TimerSample {
var timer: Timer?
func startTimer() {
timer = Timer.scheduledTimer(timeInterval: 5.0,
target: self,
selector: #selector(eventWith(timer:)),
userInfo: [ "foo" : "bar" ],
repeats: true)
}
// Timer expects @objc selector
@objc func eventWith(timer: Timer!) {
let info = timer.userInfo as Any
print(info)
}
}
Ab iOS 10 gibt es auch eine neue blockbasierte Timer-Factory-Methode, die sauberer ist als die Verwendung des Selektors:
_ = Timer.scheduledTimer(withTimeInterval: 5, repeats: false) { timer in
label.isHidden = true
}
Swift 3, vor iOS 10
func schedule() {
DispatchQueue.main.async {
self.timer = Timer.scheduledTimer(timeInterval: 20, target: self,
selector: #selector(self.timerDidFire(timer:)), userInfo: nil, repeats: false)
}
}
@objc private func timerDidFire(timer: Timer) {
print(timer)
}
Swift 3, iOS 10+
DispatchQueue.main.async {
self.timer = Timer.scheduledTimer(withTimeInterval: 20, repeats: false) { timer in
print(timer)
}
}
Anmerkungen
@objc
seinErkundigen Sie sich bei:
Swift 2
var timer = NSTimer.scheduledTimerWithTimeInterval(0.01, target: self, selector: Selector("update"), userInfo: nil, repeats: true)
Swift 3, 4, 5
var timer = Timer.scheduledTimer(timeInterval: 0.01, target: self, selector: #selector(self.update), userInfo: nil, repeats: true)
Sie müssen Timer anstelle von NSTimer in Swift 3 verwenden.
Hier ist ein Beispiel:
Timer.scheduledTimer(timeInterval: 1,
target: self,
selector: #selector(YourController.update),
userInfo: nil,
repeats: true)
// @objc selector expected for Timer
@objc func update() {
// do what should happen when timer triggers an event
}
für Swift 3 und Xcode 8.2 (Schön, Blöcke zu haben, aber wenn Sie für iOS9 kompilieren UND userInfo möchten):
...
self.timer = Timer(fireAt: fire,
interval: deltaT,
target: self,
selector: #selector(timerCallBack(timer:)),
userInfo: ["custom":"data"],
repeats: true)
RunLoop.main.add(self.timer!, forMode: RunLoopMode.commonModes)
self.timer!.fire()
}
func timerCallBack(timer: Timer!){
let info = timer.userInfo
print(info)
}
Dies ist eine einfache Timer-Klasse in Swift, mit der Sie:
SimpleTimer(interval: 3,repeats: true){print("tick")}.start()//Ticks every 3 secs
class SimpleTimer {/*<--was named Timer, but since Swift 3, NSTimer is now Timer*/
typealias Tick = ()->Void
var timer:Timer?
var interval:TimeInterval /*in seconds*/
var repeats:Bool
var tick:Tick
init( interval:TimeInterval, repeats:Bool = false, onTick:@escaping Tick){
self.interval = interval
self.repeats = repeats
self.tick = onTick
}
func start(){
timer = Timer.scheduledTimer(timeInterval: interval, target: self, selector: #selector(update), userInfo: nil, repeats: true)//Swift 3 upgrade
}
func stop(){
if(timer != nil){timer!.invalidate()}
}
/**
* This method must be in the public or scope
*/
@objc func update() {
tick()
}
}
In Swift so etwas mit @objc:
func startTimerForResendingCode() {
let timerIntervalForResendingCode = TimeInterval(60)
Timer.scheduledTimer(timeInterval: timerIntervalForResendingCode,
target: self,
selector: #selector(timerEndedUp),
userInfo: nil,
repeats: false)
}
@objc func timerEndedUp() {
output?.timerHasFinishedAndCodeMayBeResended()
}
timer = Timer.scheduledTimer(timeInterval: 1, target: self, selector: #selector(createEnemy), userInfo: nil, repeats: true)
Und erstellen Sie Spaß mit dem Namen createEnemy
fund createEnemy ()
{
do anything ////
}
Wenn Sie die Timer-Methode starten
let timer = Timer(timeInterval: 3, target: self, selector: #selector(update(_:)), userInfo: [key : value], repeats: false)
func update(_ timer : Timer) {
}
fügen Sie es dann mit einer anderen Methode zur Schleife hinzu. Der Selektor wird nicht aufgerufen
RunLoop.main.add(timer!, forMode: .defaultRunLoopMode)
HINWEIS: Wenn Sie möchten, dass dies wiederholt wird, machen Sie Wiederholungen wahr und behalten Sie die Referenz des Timers bei, da sonst die Aktualisierungsmethode nicht aufgerufen wird.
Wenn Sie diese Methode verwenden.
Timer.scheduledTimer(timeInterval: seconds, target: self, selector: #selector(update(_:)), userInfo: nil, repeats: true)
bewahren Sie eine Referenz für eine spätere Verwendung auf, wenn Wiederholungen zutreffen.