Saturday, November 16, 2019

ios - How to combine tap and long hold gesture recognizers?


I have a game in which the player moves around a sprite by tapping on various sections of the screen (left, right, up, down). So far, each tap moves the sprite one tile (I use a tile system for movement, among other things), so to move the sprite a long distance the player has to tap in the direction they want for a while. Is there a way to combine a tap gesture recognizer and a long hold gesture recognizer so that if the player taps once, the sprite moves one tile in the direction tapped and if the player holds, the player moves in that direction until the player stops holding?



Here's my code for a single direction just as an example of what I have:


-(void)handleRightTap {

self.player.direction = RIGHT;
float currentSpriteX = self.playerSprite.center.x;
float currentSpriteY = self.playerSprite.center.y;

//If the animation is not already happening and the destination is accessible...
if(!self.isAnimating && self.toTile.isWalkable) {
self.isAnimating = YES;


//If the player has reached the edge of the screen...
if([self checkIfPlayerHasReachedEndForPoint:toPoint]) {
self.isAnimating = NO;
return;
}
CABasicAnimation *moveAnimation = [CABasicAnimation animation];
moveAnimation.toValue = [NSValue valueWithCGPoint:CGPointMake(currentSpriteX + TILE_WIDTH, currentSpriteY)];
[moveAnimation setDelegate:self];
[moveAnimation setFillMode:kCAFillModeForwards];

[moveAnimation setRemovedOnCompletion:NO];
[moveAnimation setDuration:MOVE_ANIMATION_DURATION];
[self.playerSprite.layer addAnimation:moveAnimation forKey:@"position"];
}
}

Answer



The way to deal with this is to set a timer once the person taps the phone. The most user friendly scenario that you'd implement would look something like this:



  1. When you detect a tap, set a timer (t = timeToRepeat)

  2. On each frame, decrease the timer by dt


  3. If the timer reaches zero, move the sprite a tile and reset the timer

  4. If the user releases their finger before the first cycle of the timer, move the sprite one tile


Obviously the amount of time that you set your timer to will determine how fast your sprite moves. There are a few variations on this theme depending on the kind of behavior you want as well. For example, you can move the sprite once immediately upon detecting a tap and ignore step #4.


No comments:

Post a Comment

Simple past, Present perfect Past perfect

Can you tell me which form of the following sentences is the correct one please? Imagine two friends discussing the gym... I was in a good s...