I am trying to create an open circle from a UIBezierPath and turn that into an SKShapeNode which will later be turned into a SKSpriteNode.
I had an problem where I could not figure out how to shrink a Sprite while its line width did not scale down. You can see the solution here: Resize sprite without shrinking contents
I ended up fixing some things and creating a new class to implement a custom SKShapeNode with this functionality:
class ShrinkableShape: SKShapeNode {
let level: Int
let bezierPath: UIBezierPath
let scale: CGFloat
let finalLineWidth: CGFloat
let from: SKSpriteNode
let initialLineWidth = CGFloat(20)
let duration = 0.3
// level would be from 1 to 5 (it is in a for loop)
init(level: Int, from: SKSpriteNode) {
self.level = level
self.from = from
// create the open circle which is (43 * level) + 140
bezierPath = UIBezierPath(arcCenter: CGPoint(x: 0, y: 0), radius: CGFloat(((43 * level) + 140)), startAngle: CGFloat(GLKMathDegreesToRadians(-50)), endAngle: CGFloat(M_PI * 2), clockwise: false)
// calls static function in this class so it is more readable
scale = ShrinkableShape.scaleFrom(level: level) / ShrinkableShape.scaleFrom(level: level + 1)
finalLineWidth = (initialLineWidth / scale)
// inits shape and then sets it up to specific values
super.init()
setup()
}
required init?(coder aDecoder: NSCoder) {
fatalError("init(coder:) has not been implemented")
}
func setup() {
// set sprite to path, set color, set line width and rotate it
self.path = bezierPath.cgPath
self.strokeColor = UIColor(red:0.98, green:0.99, blue:0.99, alpha:1.00)
self.lineWidth = 20
self.position = from.position
// FOR DEBUG: you will see what this makes in the screenshot
let color = SKShapeNode(rect: self.frame)
color.fillColor = UIColor.red
color.alpha = 0.2
color.position = self.position
self.addChild(color)
}
// Makes the radius from the value given (only 1...5) 183, 226, 269, etc
static func scaleFrom(level: Int) -> CGFloat {
return (CGFloat((level * 43) + 140) * 2.0)
}
}
If you look at the screenshot you can notice the white circle is a little off compared to where it should be aligned (the gray bar and white circle path should be on each other). This only happens when I call the scale function shown in the solution (linked above).
I think it is because of the frame being all messed up. If you see, the frame is very off (and that same issue was the reason for past issues when converting to a texture because the frame was not exact as it should be)
Why does this happen? How do I fix it? Is there a way for me to manually set the correct frame for the SKShapeNode? Any other ideas on how I can do this?
--Edit-- I forgot to mention. The red part in the picture is a debug to see the frame of the SKShapeNode. You can see how it is created in the setup() func. But I included that to show how far off the frame was.
(level * 43 + 140) / ((level + 1) * 43) + 140
so for example, the first circle is 183x183 and the second circle is 226x226. The scale is 183/226. When you plug in sprite.scale(183/226) it will go to the exact length and width I want. But the problem is, it isnt. My thought on why it isnt is because the frame is not the right size.It is bigger than 226x226 for example – Ancestress