Lucas Almeida
Lucas Almeida

Reputation: 255

Dispatch and Delay between calls

I'm making a clone for that old game Simon (a.k.a. Genius, in Brazil), the one with the for coloured buttons which the player needs to press following a sequence of colors.

For testing, interface has 4 coloured buttons I created an array for the button outlets, for easy access:

var buttonArray:[UIButton] = [self.greenButton, self.yellowButton, self.redButton, self.blueButton]

Also, created another array to store the sequence of colors

var colors:[Int] = []

When a game starts it calls a function which adds a random number from 0 to 3 (index on buttonArray), and add this number to the colors array After adding a new color the color sequence, the app needs to show the sequence for the user, so he can repeat it

For that, it calls the playMoves function, which uses a for loop the run through the colors array and change the alpha from the button, simulating a 'blink'

func playMoves(){

    let delay = 0.5 * Double(NSEC_PER_SEC)
    let time = dispatch_time(DISPATCH_TIME_NOW, Int64(delay))

        for i in self.colors{

            self.buttonArray[i].alpha = 0.2

            dispatch_after(time, dispatch_get_main_queue(), {
                self.buttonArray[i].alpha = 1
            })                
        }    
}

It changes the alpha from the button to 0.2 and then, after half a second it returns the alpha to 1. I was using dispatch_after, passing the 0.5 seconds and on the code block it returns the alpha, as you guys can see on the code above.

On the first run, it appears to do it correctly, but when the colors array has 2 or more items, when it runs the loop, although it has a 0.5 sec delay, it blinks all the buttons on the same time.

It's probably some dumb mistake I'm making, but I'm clueless on the moment.

I would appreciate very much all the help!

Thanks!

Upvotes: 4

Views: 311

Answers (1)

Rob
Rob

Reputation: 437552

All of these dispatch_after calls are scheduled at nearly the same time, making them appear to blink at the same time. There are a couple of approaches that would solve this:

You could, for example, adjust the when parameter (the dispatch_time_t parameter) for each button to be offset from the original time (such that delay was, effectively i * 0.5 * Double(NSEC_PER_SEC)).

You could also use key-frame animation, but I'd suggest you first try fixing the delay in your dispatch_after approach first.

Upvotes: 2

Related Questions