How can I rotate a player's character depending on the angle of a rope constraint or beam?

So I have a Spider-man web swinging system. It works by finding a nearby part and attaching a rope constraint from the character’s hand to that nearest part using attachments. Then applying a body force to that player to move them forward. I want the player 's character to rotate on the angle of the rope. So if the rope is rotated 45 degress, the player with rotate 45 with it.

Here is a picture of what I’m trying to achieve.

I am also using beams for this too if that helps at all. It makes the rope not visible, and then applies a beam from those same 2 attachment points with a web like texture.

4 Likes

You’d need to get the dot product between the player’s LookVector (so we get a nice 90 degree up-straight rotation when idle) and the player-to-rope’s end direction and then just apply a rotation on the player’s RootJoint (since the RootJoint’s C0 and stuff is only purely visual, and doesn’t affect the player’s collisions and the sort)

local RootJoint = HumanoidRootPart:WaitForChild("RootJoint")
RunService:BindToRenderStep("MakePlayerRotateBasedOnRopeAngle", 301, function()
	local Direction = (a1.WorldPosition - a0.WorldPosition).Unit
	-- The dot product isn't really the "angle", but it doesn't really matter as using
	-- the angle from the dot product just forces us to add some offset values for the same thing anyway
	local Angle = Direction:Dot(HumanoidRootPart.CFrame.LookVector) --
		
	-- This weird combination is the RootJoint's C0 default CFrame
	local A = CFrame.new(0, 0, 0, -1, 0, 0, 0, 0, 1, 0, 1, -0) * CFrame.Angles(Angle, 0, 0)
	RootJoint.C0 = A
end)

EDIT: Oops, forgot that you might also want the roll angle.
It’s the same thing but you have to use the RightVector

local Pitch = Direction:Dot(HumanoidRootPart.CFrame.LookVector)
local Roll = Direction:Dot(HumanoidRootPart.CFrame.RightVector)
local A = CFrame.new(0, 0, 0, -1, 0, 0, 0, 0, 1, 0, 1, -0) * CFrame.Angles(Pitch, -Roll, 0)
2 Likes

you could do CFrame.lookat(Attatchment1.WorldPosition, Attatchment2.WorldPosition) * CFrame.Angles(math.rad(90),math.rad(90),0) You’ll probably need to edit the CFrame.Angles values. I just wrote some stuff there

1 Like

Alright so I did what you did

humanoidRootPart.CFrame = CFrame.lookAt(humanoidRootPart.Position, currentRope.Attachment1.WorldPosition) * CFrame.Angles(math.rad(-90), math.rad(0), math.rad(0))

That rotates the player in the correct way, but since you are using CFrame.lookat, the player is gonna constantly be looking at that attachment point. So once they swing and the connection point is behind them, they are gonna rotate towards that part. So basically halfway through the swing, they are gonna rotate behind them. How can I keep this rotation, but make sure the player is ALWAYS staying forward?

1 Like

you could set the CFrame.Angles value once and not update it until they let go or swing again, it might need a bit of fiddling around to do this

did you ever get this working?

1 Like