Say I had a function, any function, that I wanted to run for only three seconds and then never run again. How would I do this? Would I use NSTimer? Thank you for your help.
Here you go,
NSTimer.scheduledTimerWithTimeInterval(3, target: self, selector: Selector("updateProgress:"), userInfo: nil, repeats: false)
func updateProgress(timer: NSTimer){
}
Related
This question already has answers here:
How can I use Timer (formerly NSTimer) in Swift?
(16 answers)
Closed 4 years ago.
I am quite new to Swift and would love to know how to create a loop that runs some code every 30 seconds? I feel as though it is a basic question but I can't really find what I'm looking for.
You can make Use of Timer
Timer.scheduledTimerWithTimeInterval(0.30, target: self, selector: #selector(timerFired), userInfo: userInfo, repeats: true)
timerFired: is the method that gets called after interval
#objc func timerFired() {
print("Timer Called with interval 30seconds")
}
You need to use scheduled timer. In viewDidLoad()
Timer.scheduledTimer(timeInterval: 30, target: self, selector: #selector(YourFuncName), userInfo: nil, repeats: true)
and func for selector
#objc func YourFuncName() {
print("every 30seconds")
}
func startTimer() {
timer = Timer.scheduledTimer(timeInterval: 30, target: self, selector: #selector(UpdateTimer), userInfo: nil, repeats: true)
}
#objc func UpdateTimer() {
counter += 1
}
to start
startTimer();
and to stop
timer.invalidate()
I have scheduled timers that add sprite nodes to the screen as obstacles
func timers(){
personTimer = Timer.scheduledTimer(timeInterval: 1, target: self, selector: #selector(spawnPerson), userInfo: nil, repeats: true)
bikeTimer = Timer.scheduledTimer(timeInterval: 2, target: self, selector: #selector(spawnBike), userInfo: nil, repeats: true)
motorcycleTimer = Timer.scheduledTimer(timeInterval: 2.5, target: self, selector: #selector(spawnMotorcycle), userInfo: nil, repeats: true)
}
I added a function to invalidate those timers. so that a bonus "level" can be ran.
func invalidateTimers(){
// Obstacles
personTimer.invalidate()
bikeTimer.invalidate()
motorcycleTimer.invalidate()
}
When the bonus is called
func bonus() {
invalidateTimers()
bonusTimer = Timer.scheduledTimer(timeInterval: 1, target: self, selector: #selector(spawnDiamonds), userInfo: nil, repeats: true)
}
The problem that I'm having is that when the bonus is done running I invalidate the bonusTimer and recall timers(). But when I do all the timers in the function seem to be firing twice. Whats an easy workaround for that since they can't just be paused.
Instead of using timers, consider using SKActions, as they work well with SpriteKit. To start the timer, run:
let wait1 = SKAction.wait(forDuration: 1)
let personTimer = SKAction.repeatForever(SKAction.sequence([wait1, SKAction.run {
spawnPerson() // spawnBike() etc. for each different timer
}]))
self.run(personTimer, withKey: "spawnPerson")
with modified wait values and function calls for each different timer. Then to stop the timer, run:
self.removeAction(forKey: "spawnPerson")
for each action using a different key.
Instead of using timers, you can use update: method of your SKScene subclass. It calls once per frame and has currentTime parameter. So you can easily calculate time intervals you need and trigger corresponding methods.
This question already has answers here:
NSTimer not firing
(3 answers)
Closed 7 years ago.
I've been trying to get variations of this code to run, but countItems() never prints out the NSLog. Can someone tell me what is wrong?
func someFunction() {
var fireDate = NSDate(timeIntervalSinceNow: 5)
someTimer = NSTimer(fireDate: fireDate, interval: 120, target: self, selector: "countItems", userInfo: nil, repeats: true)
}
func countItems() {
NSLog("countItems")
//Perform some code here...
}
Try reading the docs! It's all right there. You have created the timer but you have never scheduled it on a run loop. So it does nothing. The docs clearly say:
You must add the new timer to a run loop, using addTimer:forMode:.
Well, you don't.
You might be happier like this:
NSTimer.scheduledTimerWithTimeInterval(
120, target: self, selector: "countItems", userInfo:nil, repeats:true)
Add fire():
func someFunction() {
var fireDate = NSDate(timeIntervalSinceNow: 5)
someTimer = NSTimer(fireDate: fireDate, interval: 120, target: self, selector: "countItems", userInfo: nil, repeats: true)
someTimer.fire()
}
Or it wont start: Documentation
class ViewController: UIViewController {
func ChangePage()
{
NSLog("Hej")
}
var timers = NSTimer(NSTimeInterval(0.5), target:self, selector: "ChangePage", userInfo: nil, repeats: true)
}
I get the following error from Xcode 6:
Extra Argument 'selector' in call
I've tried several configurations, does it have something to do with where in the code it's placed?
You might want to use:
var timer = NSTimer.scheduledTimerWithTimeInterval(0.5, target: self, selector: "changePage", userInfo: nil, repeats: true)
This returns a timer that is already added to the run loop and fires automatically.
To stop the timer to fire, you must invalidate it like this
timer.invalidate()
You should add timeInterval in the constructor like:
NSTimer(timeInterval: NSTimeInterval(0.5), target:self, selector: "ChangePage", userInfo: nil, repeats: true)
And yes, it does matter where you put. The problem is, that timers is a property, and it is created before the initialization. So when it is created, self is not existing, but you refer to it, and that causes the problem.
I'm trying to use an NSTimer in my app, and was wondering if it's possible to call two methods when the timer fires.
Here's the code:
gameTimer = NSTimer.scheduledTimerWithTimeInterval(0.01, target: self, selector:
Selector("gameMovement" && "fireBullet"), userInfo: nil, repeats: true)
I'm getting an error saying there are two arguments in the Selector.
Nope. You would call just one method that delegates to all the things you want.
func someFunc() {
gameTimer = NSTimer.scheduledTimerWithTimeInterval(
0.01,
target: self,
selector: Selector("timerFired"),
userInfo: nil,
repeats: true
)
}
func timerFired() {
gameMovement()
fireBullet()
}
This is a more maintainable pattern anyway, as it's easier to see how your code flows.