1

I am making a simple Pong game using SpriteKit + Swift. I am trying to move the two paddles even if a finger is already touching the display. I got a suggestion to split the screen into two View Controller. Would this help? If so, how would this be done? Link to previous question.

override func touchesBegan(touches: Set<UITouch>, withEvent event: UIEvent?) {
    let touch = touches.first as UITouch?
    let touchLocation = touch?.locationInNode(self)
    let body: SKPhysicsBody? = self.physicsWorld.bodyAtPoint(touchLocation!)

    if body?.node!.name == PaddleCategoryName {
        print("Paddle Touched!")
        fingerIsOnPaddle = true
    }

    if body?.node!.name == PaddleCategoryName2 {
        print("Paddle2 Touched!")
        fingerIsOnPaddle2 = true
    }


}

override func touchesMoved(touches: Set<UITouch>, withEvent event: UIEvent?) {
    if fingerIsOnPaddle {
        let touch = touches.first as UITouch?
        let touchLocation = touch?.locationInNode(self)
        let previousTouchLocation = touch?.previousLocationInNode(self)

        let paddle = self.childNodeWithName(PaddleCategoryName) as! SKSpriteNode

        var newYPosition = paddle.position.y + (touchLocation!.y - previousTouchLocation!.y)

        newYPosition = max(paddle.size.height / 2, newYPosition)
        newYPosition = min(self.size.height - paddle.size.height / 2, newYPosition)

        paddle.position = CGPointMake(paddle.position.x, newYPosition)

    }

    if fingerIsOnPaddle2 {
        let touch = touches.first as UITouch?
        let touchLocation = touch?.locationInNode(self)
        let previousTouchLocation = touch?.previousLocationInNode(self)

        let paddle2 = self.childNodeWithName(PaddleCategoryName2) as! SKSpriteNode

        var newYPosition = paddle2.position.y + (touchLocation!.y - previousTouchLocation!.y)

        newYPosition = max(paddle2.size.height / 2, newYPosition)
        newYPosition = min(self.size.height - paddle2.size.height / 2, newYPosition)

        paddle2.position = CGPointMake(paddle2.position.x, newYPosition)
    }
}

override func touchesEnded(touches: Set<UITouch>, withEvent event: UIEvent?) {
    fingerIsOnPaddle = false
    fingerIsOnPaddle2 = false
}
Community
  • 1
  • 1
  • 1
    I'm not sure that is really what you want to do. You might be better getting the location of the touch, so you can just use that location to see if it on one side of the iDevice or the other. Same would go for `touchesMoved`, just see where the location of the touch is, and move the paddle on that side. – Gliderman Oct 18 '15 at 13:37
  • I did try that, but it still did not work. – Shawn Patel Oct 18 '15 at 16:26
  • What errors did you run into? Would you be able to show some of that code? – Gliderman Oct 18 '15 at 16:46
  • Basically, I made two nodes that were tilted LeftSide and RightSide. If LeftSide was pressed then, it would find if I pressed on Paddle1 which is on the left side and vice versa. When I ran the changes, I was still running into the same problem. – Shawn Patel Oct 18 '15 at 17:00
  • I added the code in the question. – Shawn Patel Oct 18 '15 at 17:12
  • You are only using the first touch (by `touches.first`). That may be why you don't get the touches all the time. Also, would it just be better not to detect a touch _on_ the paddle, but set the position of the paddle to where the touch is? I would do something like (saying that this game is horizontal): `if touchLocation.x > self.view.frame.size.width { set paddle1 position.y to touchLocation.y } else { set paddle2 position.y to touchLocation.y }` rather than detecting if it on one side of the screen, and then detecting if you are touching the paddle. Are you using `touchesMoved` for moving? – Gliderman Oct 19 '15 at 22:38
  • I am using touchesMoved for moving. – Shawn Patel Oct 20 '15 at 02:55
  • I added the code I have for touchesBegan, touchesMoved, and touchesEnded for you to look at. – Shawn Patel Oct 20 '15 at 04:02
  • Thank you, that explains a lot. I'll write up an answer later today. – Gliderman Oct 20 '15 at 18:15

1 Answers1

0

The primary problem with the code you have provided is that you are only using the first touch, which is not good when you have two people moving the paddles around. I would in fact not use touchesBegan or touchesEnded. I'm going to assume that the game field will have x along the horizontal, so 512 (the default scene width divided by 2) will be the middle line, with the paddles positioned at x = 0 and x = 1024.

The code below is in touchesMoved, and handles each touch that moved. If the touch location is on one side of the screen, it gets the paddle for that side and moves it. You may wish to put this code in the touchesBegan method as well, so that the user can touch where they want the paddle to go. You could go back to your paddle detection method (I didn't see anything wrong with it aside from not using every touch), but I would recommend using paddle.containsPoint to test if the touch is inside.

override func touchesMoved(touches: Set<UITouch>, withEvent event: UIEvent?) {
    for touch: UITouch in touches {
        let location = touch.locationInNode(self)
        if location.x < 512 {
            let paddle = self.childNodeWithName(PaddleCategoryName) as! SKSpriteNode
            paddle.position.y = location.y
        } else {
            let paddle2 = self.childNodeWithName(PaddleCategoryName2) as! SKSpriteNode
            paddle2.position.y = location.y
        }
    }
}

I am currently downloading Xcode 7 to get Swift 2, and I will edit this with proper syntax. But for now, with a few changes (like to the method call), it should work.

Gliderman
  • 1,195
  • 9
  • 18