How to rotate sprites around a joint

I need the arms and hands to rotate around the center of the hook, as shown in the image below, without separating or changing their shape (no changes in the angles between the arms and hands, just rotating by A), as in the image below:

enter image description here

I tried to rotate the weapon, but it made them split and change shape. You can check my code below:

let hookCategoryName = "hook" let leftArmCategoryName = "leftArm" let rightArmCategoryName = "rightArm" let leftHandCategoryName = "leftHand" let rightHandCategoryName = "rightHand" let hookCategory : UInt32 = 0x1 << 0 let leftArmCategory : UInt32 = 0x1 << 1 let rightArmCategory : UInt32 = 0x1 << 2 let leftHandCategory : UInt32 = 0x1 << 3 let rightHandCategory : UInt32 = 0x1 << 4 extension Int { var degreesToRadians: Double { return Double(self) * .pi / 180 } } extension FloatingPoint { var degreesToRadians: Self { return self * .pi / 180 } var radiansToDegrees: Self { return self * 180 / .pi } } class GameScene: SKScene, SKPhysicsContactDelegate { var hook = SKSpriteNode(imageNamed: "hook") var leftArm = SKSpriteNode(imageNamed: "arm") var rightArm = SKSpriteNode(imageNamed: "arm") var leftHand = SKSpriteNode(imageNamed: "leftHand") var rightHand = SKSpriteNode(imageNamed: "rightHand") override func didMove(to view: SKView) { self.physicsWorld.gravity = CGVector(dx: 0, dy: 0) self.physicsWorld.contactDelegate = self var yellowBg = SKSpriteNode(imageNamed: "yellowBg") yellowBg.position = CGPoint(x: frame.midX, y: frame.midY) yellowBg.zPosition = 2 addChild(yellowBg) hook.position = CGPoint(x: frame.midX, y: frame.midY + frame.midY/2) hook.zPosition = 5 hook.name = hookCategoryName hook.physicsBody = SKPhysicsBody(rectangleOf: hook.frame.size) hook.physicsBody?.categoryBitMask = hookCategory hook.physicsBody?.isDynamic = false addChild(hook) rightArm.anchorPoint = CGPoint(x: 0.5, y: 1) rightArm.position = hook.position rightArm.zPosition = 5 rightArm.name = rightArmCategoryName rightArm.physicsBody = SKPhysicsBody(rectangleOf: rightArm.frame.size) rightArm.physicsBody?.categoryBitMask = rightArmCategory rightArm.physicsBody!.isDynamic = true addChild(rightArm) leftArm.anchorPoint = CGPoint(x: 0.5, y: 1) leftArm.position = hook.position leftArm.zPosition = 5 leftArm.name = leftArmCategoryName leftArm.physicsBody = SKPhysicsBody(rectangleOf: leftArm.frame.size) leftArm.physicsBody?.categoryBitMask = leftArmCategory leftArm.physicsBody!.isDynamic = true addChild(leftArm) // leftHand leftHand.anchorPoint = CGPoint(x: 0.5, y: 0.5) leftHand.position = CGPoint(x: leftArm.frame.minX - 22, y: leftArm.frame.minY + 7) //CGPoint(x: armLeft.position.x, y: armLeft.position.y) leftHand.zPosition = 5 leftHand.name = leftHandCategoryName leftHand.physicsBody = SKPhysicsBody(rectangleOf: leftHand.frame.size) leftHand.physicsBody?.categoryBitMask = leftHandCategory leftHand.zRotation = CGFloat(Double(-30).degreesToRadians)//CGFloat(-Double.pi/6) //armLeft.physicsBody?.categoryBitMask = armCategory leftHand.physicsBody!.isDynamic = true addChild(leftHand) // rightHand rightHand.anchorPoint = CGPoint(x: 0.5, y: 0.5) rightHand.position = CGPoint(x: rightArm.frame.minX + 30, y: rightArm.frame.minY + 7) //CGPoint(x: armLeft.position.x, y: armLeft.position.y) rightHand.zPosition = 5 rightHand.name = rightHandCategoryName rightHand.physicsBody = SKPhysicsBody(rectangleOf: rightHand.frame.size) rightHand.physicsBody?.categoryBitMask = rightHandCategory rightHand.zRotation = CGFloat(Double(30).degreesToRadians)//CGFloat(-Double.pi/6) //armLeft.physicsBody?.categoryBitMask = armCategory rightHand.physicsBody!.isDynamic = true addChild(rightHand) leftArm.zRotation = CGFloat(Double(-45).degreesToRadians) rightArm.zRotation = CGFloat(Double(45).degreesToRadians) rightHand.physicsBody?.contactTestBitMask = rightHandCategory leftHand.physicsBody?.contactTestBitMask = leftHandCategory rightHand.physicsBody?.collisionBitMask = rightHandCategory leftHand.physicsBody?.collisionBitMask = leftHandCategory let hookAndRightArmJoint = SKPhysicsJointPin.joint(withBodyA: hook.physicsBody!, bodyB: rightArm.physicsBody!, anchor: CGPoint(x: hook.position.x, y: self.rightArm.frame.maxY)) self.physicsWorld.add(hookAndRightArmJoint) let hookAndLeftArmJoint = SKPhysicsJointPin.joint(withBodyA: hook.physicsBody!, bodyB: leftArm.physicsBody!, anchor: CGPoint(x: hook.position.x, y: self.leftArm.frame.maxY)) self.physicsWorld.add(hookAndLeftArmJoint) let armsFixedJoint = SKPhysicsJointFixed.joint(withBodyA: leftArm.physicsBody!, bodyB: rightArm.physicsBody!, anchor: CGPoint.zero) self.physicsWorld.add(armsFixedJoint) //left arm and hand joint let leftArmAndHandJoint = SKPhysicsJointPin.joint(withBodyA: leftArm.physicsBody!, bodyB: leftHand.physicsBody!, anchor: CGPoint(x: self.leftArm.frame.minX, y: self.leftArm.frame.minY)/*CGPoint(x: armLeft.position.x, y: self.armLeft.frame.minY)*/) self.physicsWorld.add(leftArmAndHandJoint) //right arm and hand joint let rightArmAndHandJoint = SKPhysicsJointPin.joint(withBodyA: rightArm.physicsBody!, bodyB: rightHand.physicsBody!, anchor: CGPoint(x: self.rightArm.frame.maxX, y: self.rightArm.frame.minY)/*CGPoint(x: armLeft.position.x, y: self.armLeft.frame.minY)*/) self.physicsWorld.add(rightArmAndHandJoint) } override func touchesBegan(_ touches: Set<UITouch>, with event: UIEvent?) { hook.run(SKAction.rotate(byAngle: CGFloat(Double(60).degreesToRadians), duration: 0.5)) } } 

Also, the rotation of the hook does not affect the hands and arms, as shown in the figure below, when the above code is executed:

enter image description here

How can I get the rotation on the first image of the image?

+5
source share
1 answer

You can make arms and hands children of a common parent node. You can create an empty SKNode just for this purpose:

 let armsParent = SKNode() 

Then, instead of adding arms and hands as children to the scene directly, add them as children of arms. Guy like this:

 armsParent.addChild(leftArm) armsParent.addChild(rightArm) // same for hands... 

Then you can simply rotate armParent with SKAction to achieve what you want.

OR, to make it even easier, you can simply add arms and hands as children to the hook , as follows:

 hook.addChild(leftArm) // same for other arm and hands... 

Since arms and hands are children of a hook or armParent , now their positions will be determined relative to their parent. Thus, you may need to change your entire initialization code .position = to accept this.

0
source

Source: https://habr.com/ru/post/1268285/


All Articles