swiftuigesturerecognizerviewcontrollerskscene

How to handle sideways swipes


I am creating a game, where you control using swipes and I wanted to know if it is possible to handle sideways swipes using UIGestureRecodnizer?

If so how do I do it.

In other word:

Instead of having 4 directions, how do I get 8:

From up,down,right,left to upleft,upright,downright,downleft,up,down,right,left ?

Also how do can I properly differ between a double swipe and a two single swipes, does UIGestureRecognizer have an inbuilt timeout?


Solution

  • This could use some cleaning up but it works:

    // a uiview that tracks touches in 8 directions when swiped
    class TouchRecognizer: UIView{
        
     // used for calculating degree between touches
        var startTouch: CGPoint = CGPoint(x: 0, y: 0)
        var endTouch: CGPoint = CGPoint(x: 0, y: 0)
        
        // gets initial touch
        override func touchesBegan(_ touches: Set<UITouch>, with event: UIEvent?) {
            let touch = touches.first!
            let location = touch.location(in: self)
        
            startTouch = location
        }
        
        // gets end touch, then checks angle
        override func touchesEnded(_ touches: Set<UITouch>, with event: UIEvent?) {
            let touch = touches.first!
            let location = touch.location(in: self)
            endTouch = location
           
            HandleSwipe()
       
        }
        
        // Gets The Degree between the two touches
        func HandleSwipe(){
            let p1 = startTouch
            let p2 = endTouch
            
            let center = CGPoint(x: (p1.x), y: (p1.y + 1))
            let v1 = CGVector(dx: p1.x - center.x, dy: p1.y - center.y)
            let v2 = CGVector(dx: p2.x - center.x, dy: p2.y - center.y)
            let angle = atan2(v2.dy, v2.dx) - atan2(v1.dy, v1.dx)
            let deg = angle * CGFloat(180.0 / .pi)
            
            PrintDirection(degree: deg)
        }
        
        
        // uses the degree between touches to figure out the direction user swiped
        func PrintDirection(degree: CGFloat){
            
            // if needed, adjust degree angles for optimized swiping
            if(degree < 30 && degree > -10){
                print("Up")
            }
            else if(degree > 30 && degree < 60){
                print("UpRight")
            }
            else if(degree > 75 && degree < 120){
                print("Right")
            }
            else if(degree > 120 && degree < 150){
                print("downRight")
            }
            else if(degree > 150 && degree < 210){
                print("Down")
            }
            else if(degree > 210 && degree < 240){
                print("downleft")
            }
            else if(degree > 240 && degree < 300){
                print("Left")
            }
            else if(degree > 300 && degree < 360){
                print("upLeft")
            }
            else if(degree < -30 && degree > -60){
                print("upLeft")
            }
            else if(degree < -60){
                      print("left")
                  }
        }
        
    }