Несколько вещей здесь:
1) ваш случайный случай основан на квадрате, а не на круге, поэтому вы увидите, что ваши враги появляются на углах больше, чем в центре каждой стороны экрана. Я бы порекомендовал сделать случайный угол между 0 и 2 пи, случайный радиус, который я предполагаю между 0 и 2000, а затем установить свою позицию с помощью CGPoint(x:cos(angle) * radius, y:sin(angle) * radius)
2) Ваша более низкая скорость будет отрицательной через 25 секунд, это может стать проблемой. Я бы использовал процент вместо:
lowerRate = lowerRateStart * percentage
percentage *= 0.90
Это уменьшит ваши спрайты на 10 процентов от их текущего местоположения, поэтому 90 81 73 64 58 52 47 42 38 34 31 28 25 22 20 18 16 14 13 12 11 10 9 8 7 6 5 4 ..... затем быть между 4 и 0 на некоторое время. Это в основном гарантирует, что ваше число приближается к нулю, но никогда не станет 0.
3) Ваш случайный старт и ограничение по расстоянию коррелируют неправильно, и это может вызвать проблемы. Я бы порекомендовал установить положение где-то внутри радиуса ограничения расстояния, поэтому ваши ставки должны быть:
let radius = CGFloat(arc4random_uniform(UInt32(upperRate - lowerRate)))
newEnemy.position = CGPoint(x:cos(angle) * radius + lowerRate + targetSprite.x, y:sin(angle) * radius + lowerRate + targetSprite.y)