So! I had the same issue and didn't find the answer so I've come up with mine
Easy one
I might think that Paul have in mind some kind of punishment for user, like
- Instant GameOver, but this will make game almost unplayable.
- Getting back user to the original coordinates (set in didMove method), but this will change nothing and will break gameplay a little. It's like we answering to users cheating with cheat from our side.
My variant
My idea is to use finger location as desired location of player and move player object there on every with calculated velocity. If user will lift his fingers - then desired location is nil and object will loose it's velocity.
We will need to create a custom class for that, and I learned what is convenience initializer while doing that :)
//
// Player.swift
// Project17
//
// Created by Andrei Chenchik on 2/6/21.
//
import SpriteKit
class Player: SKSpriteNode {
var direction: CGPoint?
var possibleSpeed: CGFloat = 800.0
init(imageNamed name: String) {
let texture = SKTexture(imageNamed: name)
let size = texture.size()
super.init(texture: texture, color: .clear, size: size)
}
required init?(coder aDecoder: NSCoder) {
fatalError("init(coder:) has not been implemented")
}
}
Use new class like that
var player: Player!
And additionally I've updated methods for touches and update.
Have no idea how to calculate velocity right so used my school baggage.
override func update(_ currentTime: TimeInterval) {
for node in children {
if node.position.x < -300 {
node.removeFromParent()
}
}
if !isGameOver {
score += 1
}
if let direction = player.direction {
let position = player.position
let distance = sqrt(pow((direction.x - position.x), 2) + pow((direction.y - position.y), 2))
let multiplier = distance / player.possibleSpeed
if multiplier > 1/60 {
let dx = (direction.x - position.x) / multiplier
let dy = (direction.y - position.y) / multiplier
player.physicsBody?.velocity = CGVector(dx: dx, dy: dy)
} else {
player.physicsBody?.velocity = .zero
player.position = direction
}
} else {
player.physicsBody?.velocity = .zero
}
}
override func touchesEnded(_ touches: Set<UITouch>, with event: UIEvent?) {
player.direction = nil
}
override func touchesMoved(_ touches: Set<UITouch>, with event: UIEvent?) {
guard let touch = touches.first else { return }
var location = touch.location(in: self)
if location.y < 100 {
location.y = 100
} else if location.y > 668 {
location.y = 668
}
//player.position = location
player.direction = location
}