Directional Movements [Help]

I wanted to make a Directional Movement System. With different playing animation per direction, and a little Tweaning for each direction.

But the problem is I’m incredibly stupid with scripting, but I want to learn. So like what’s the basics with Tweaning Service and Directional Movement things?

Now here are some things that I know:

  1. Directional Movement Animation with Tweaning requires the Torso in the Animation to not be moved. As for it would ruin the Twean Effect thing.

  2. Different Animation per Direction means it needs different speed according where he is and where he is looking at.
    Example:


    The Directions Should change accordingly to the player’s prespective, and movement.

Some Things I’ve Learned is that when trying to detect Strafing it usually uses 2 variables such as when moving directions: forward = W, Left/Right = A/D, now when you press A/D with W at the same time it will go to a 45 degree angle which is strafing. Now I want them to Tween to the direction they’re moving to, unfortunately my brain capacity isn’t that high to comprehend such divine power of scripting :3

The animation is ready and all but idk how to script and I just need some guidance.

4 Likes

What do you need to tween? Also you can use UserInputService to detect where the player is moving (or more like the movement keys they’re pressing).

1 Like

Hi!

Have you checked out useStrafingAnimation that ROBLOX themselves provide?

Head to `Players.useStrafingAnimation’ and play, and you’ll strafe.
Here’s the post to the annoucement.

If you don’t want to use these specifically, you could load the animations and see how they do make them as well as seeing what they do from an engineering perspective in the Animation script.

Happy developing :slight_smile:

1 Like

when you walk, you sort of tilt to that direction but i want it to be smooth, not from animations. i want the animation and tilting to be separate

1 Like

The easiest way to find the direction is by using the Humanoid.MoveDirection.

1 Like

With tilting i’m going to guess you mean the character actually tilting its whole body towards the direction you’re moving at?

1 Like

yes the body, the torso tilting its body towards the direction. Tying to make it for shift lock and such

1 Like

In that case, to find the strafing direction you need to find the rootpart’s relative velocity. I believe you can use VectorToObjectSpace and pass the rootpart’s cframe and its velocity as arguments to retrieve it

1 Like

i have no idea, can you use an exmaple script?

1 Like
local root = player.Character.HumanoidRootPart;
game:GetService("RunService").PreRender:Connect(function(dt)
   local cf = root.CFrame;
   local velocity = root.AssemblyLinearVelocity;
   local relativeVelocity = cf:VectorToObjectSpace(velocity);
   if relativeVelocity.X > 0.5 then
      -- moving right
   elseif relativeVelocity.X < -0.5 then
      -- moving left
   end;
end);

This gets the direction the player is moving in every frame. Since it uses velocity it’s universal so works for every platform.

1 Like

so that tilts the Player, right?

The Script I used is the script below which was made by my friend’s friend, it makes the body rotates and tilt. It’s in StarterCharacterScript, but I want it to tilt more when Sprinting. And I want it to play Different Animation in directions. This one works but I just need more understanding to it so I don’t have to ask someone for it.

.

.

local RunService = game:GetService(“RunService”)
local Players = game:GetService(“Players”)

local LocalPlayer = Players.LocalPlayer

local Character = LocalPlayer.Character or LocalPlayer.CharacterAdded:Wait()

local Humanoid = Character:WaitForChild(“Humanoid”)
local HumanoidRootPart = Character:WaitForChild(“HumanoidRootPart”)
local Torso = Character:WaitForChild(“Torso”)

local RootJoint = HumanoidRootPart:WaitForChild(“RootJoint”)
local RightShoulder = Torso:WaitForChild(“Right Shoulder”)
local LeftShoulder = Torso:WaitForChild(“Left Shoulder”)
local RightHip = Torso:WaitForChild(“Right Hip”)
local LeftHip = Torso:WaitForChild(“Left Hip”)

local RootJointC0 = RootJoint.C0
local RightShoulderC0 = RightShoulder.C0
local LeftShoulderC0 = LeftShoulder.C0
local RightHipC0 = RightHip.C0
local LeftHipC0 = LeftHip.C0

local RootJointTilt = CFrame.new()
local RightShoulderTilt = CFrame.new()
local LeftShoulderTilt = CFrame.new()
local RightHipTilt = CFrame.new()
local LeftHipTilt = CFrame.new()

local DefaultLerpAlpha = 0.145 – Lerping Speed
local dotThreshold = 0.9 – dotThreshold (Do not edit)
local lastTime = 0 – Last Time (Do not edit)
local tickRate = 1 / 60 – 60 fps limit

local function UpdateDirectionalMovement(DeltaTime)
local Now = workspace:GetServerTimeNow() – os.clock Instead? Idrk

if Now - lastTime >= tickRate then
	lastTime = Now

	local MoveDirection = HumanoidRootPart.CFrame:VectorToObjectSpace(Humanoid.MoveDirection)

	if MoveDirection:Dot(Vector3.new(1,0,-1).Unit) > dotThreshold then
		-- print("Forwards-Right")

		RootJointTilt = RootJointTilt:Lerp(CFrame.Angles(math.rad(-MoveDirection.Z) * 5, 0, math.rad(-MoveDirection.X) * 25), DefaultLerpAlpha)
		RootJoint.C0 = RootJointC0 * RootJointTilt

		RightShoulderTilt = RightShoulderTilt:Lerp(CFrame.Angles(0, math.rad(-MoveDirection.X) * 10, 0), DefaultLerpAlpha)
		RightShoulder.C0 = RightShoulderC0 * RightShoulderTilt

		LeftShoulderTilt = LeftShoulderTilt:Lerp(CFrame.Angles(0, math.rad(-MoveDirection.X) * 10, 0), DefaultLerpAlpha)
		LeftShoulder.C0 = LeftShoulderC0 * LeftShoulderTilt

		RightHipTilt = RightHipTilt:Lerp(CFrame.Angles(0, math.rad(-MoveDirection.X) * 10, 0), DefaultLerpAlpha)
		RightHip.C0 = RightHipC0 * RightHipTilt

		LeftHipTilt = LeftHipTilt:Lerp(CFrame.Angles(0, math.rad(-MoveDirection.X) * 10, 0), DefaultLerpAlpha)
		LeftHip.C0 = LeftHipC0 * LeftHipTilt
	elseif MoveDirection:Dot(Vector3.new(1,0,1).Unit) > dotThreshold then
		-- print("Backwards-Right")

		RootJointTilt = RootJointTilt:Lerp(CFrame.Angles(math.rad(-MoveDirection.Z) * 5, 0, math.rad(MoveDirection.X) * 25), DefaultLerpAlpha)
		RootJoint.C0 = RootJointC0 * RootJointTilt

		RightShoulderTilt = RightShoulderTilt:Lerp(CFrame.Angles(0, math.rad(MoveDirection.X) * 10, 0), DefaultLerpAlpha)
		RightShoulder.C0 = RightShoulderC0 * RightShoulderTilt

		LeftShoulderTilt = LeftShoulderTilt:Lerp(CFrame.Angles(0, math.rad(MoveDirection.X) * 10, 0), DefaultLerpAlpha)
		LeftShoulder.C0 = LeftShoulderC0 * LeftShoulderTilt

		RightHipTilt = RightHipTilt:Lerp(CFrame.Angles(0, math.rad(MoveDirection.X) * 10, 0), DefaultLerpAlpha)
		RightHip.C0 = RightHipC0 * RightHipTilt

		LeftHipTilt = LeftHipTilt:Lerp(CFrame.Angles(0, math.rad(MoveDirection.X) * 10, 0), DefaultLerpAlpha)
		LeftHip.C0 = LeftHipC0 * LeftHipTilt
	elseif MoveDirection:Dot(Vector3.new(-1,0,1).Unit) > dotThreshold then
		-- print("Backwards-Left")

		RootJointTilt = RootJointTilt:Lerp(CFrame.Angles(math.rad(-MoveDirection.Z) * 5, 0, math.rad(MoveDirection.X) * 25), DefaultLerpAlpha)
		RootJoint.C0 = RootJointC0 * RootJointTilt

		RightShoulderTilt = RightShoulderTilt:Lerp(CFrame.Angles(0, math.rad(MoveDirection.X) * 10, 0), DefaultLerpAlpha)
		RightShoulder.C0 = RightShoulderC0 * RightShoulderTilt

		LeftShoulderTilt = LeftShoulderTilt:Lerp(CFrame.Angles(0, math.rad(MoveDirection.X) * 10, 0), DefaultLerpAlpha)
		LeftShoulder.C0 = LeftShoulderC0 * LeftShoulderTilt

		RightHipTilt = RightHipTilt:Lerp(CFrame.Angles(0, math.rad(MoveDirection.X) * 10, 0), DefaultLerpAlpha)
		RightHip.C0 = RightHipC0 * RightHipTilt

		LeftHipTilt = LeftHipTilt:Lerp(CFrame.Angles(0, math.rad(MoveDirection.X) * 10, 0), DefaultLerpAlpha)
		LeftHip.C0 = LeftHipC0 * LeftHipTilt
	elseif MoveDirection:Dot(Vector3.new(-1,0,-1).Unit) > dotThreshold then
		-- print("Forwards-Left")

		RootJointTilt = RootJointTilt:Lerp(CFrame.Angles(math.rad(-MoveDirection.Z) * 5, 0, math.rad(-MoveDirection.X) * 25), DefaultLerpAlpha)
		RootJoint.C0 = RootJointC0 * RootJointTilt

		RightShoulderTilt = RightShoulderTilt:Lerp(CFrame.Angles(0, math.rad(-MoveDirection.X) * 10, 0), DefaultLerpAlpha)
		RightShoulder.C0 = RightShoulderC0 * RightShoulderTilt

		LeftShoulderTilt = LeftShoulderTilt:Lerp(CFrame.Angles(0, math.rad(-MoveDirection.X) * 10, 0), DefaultLerpAlpha)
		LeftShoulder.C0 = LeftShoulderC0 * LeftShoulderTilt

		RightHipTilt = RightHipTilt:Lerp(CFrame.Angles(0, math.rad(-MoveDirection.X) * 10, 0), DefaultLerpAlpha)
		RightHip.C0 = RightHipC0 * RightHipTilt

		LeftHipTilt = LeftHipTilt:Lerp(CFrame.Angles(0, math.rad(-MoveDirection.X) * 10, 0), DefaultLerpAlpha)
		LeftHip.C0 = LeftHipC0 * LeftHipTilt
	elseif MoveDirection:Dot(Vector3.new(0,0,-1).Unit) > dotThreshold then
		-- print("Forwards")

		RootJointTilt = RootJointTilt:Lerp(CFrame.Angles(math.rad(-MoveDirection.Z) * 10, 0, 0), DefaultLerpAlpha)
		RootJoint.C0 = RootJointC0 * RootJointTilt

		RightShoulderTilt = RightShoulderTilt:Lerp(CFrame.Angles(0, 0, 0), DefaultLerpAlpha)
		RightShoulder.C0 = RightShoulderC0 * RightShoulderTilt

		LeftShoulderTilt = LeftShoulderTilt:Lerp(CFrame.Angles(0, 0, 0), DefaultLerpAlpha)
		LeftShoulder.C0 = LeftShoulderC0 * LeftShoulderTilt

		RightHipTilt = RightHipTilt:Lerp(CFrame.Angles(0, 0, 0), DefaultLerpAlpha)
		RightHip.C0 = RightHipC0 * RightHipTilt

		LeftHipTilt = LeftHipTilt:Lerp(CFrame.Angles(0, 0, 0), DefaultLerpAlpha)
		LeftHip.C0 = LeftHipC0 * LeftHipTilt
	elseif MoveDirection:Dot(Vector3.new(1,0,0).Unit) > dotThreshold then
		-- print("Right")

		RootJointTilt = RootJointTilt:Lerp(CFrame.Angles(0, 0, math.rad(-MoveDirection.X) * 35), DefaultLerpAlpha)
		RootJoint.C0 = RootJointC0 * RootJointTilt

		RightShoulderTilt = RightShoulderTilt:Lerp(CFrame.Angles(0, math.rad(-MoveDirection.X) * 15, 0), DefaultLerpAlpha)
		RightShoulder.C0 = RightShoulderC0 * RightShoulderTilt

		LeftShoulderTilt = LeftShoulderTilt:Lerp(CFrame.Angles(0, math.rad(-MoveDirection.X) * 15, 0), DefaultLerpAlpha)
		LeftShoulder.C0 = LeftShoulderC0 * LeftShoulderTilt

		RightHipTilt = RightHipTilt:Lerp(CFrame.Angles(0, math.rad(-MoveDirection.X) * 15, 0), DefaultLerpAlpha)
		RightHip.C0 = RightHipC0 * RightHipTilt

		LeftHipTilt = LeftHipTilt:Lerp(CFrame.Angles(0, math.rad(-MoveDirection.X) * 15, 0), DefaultLerpAlpha)
		LeftHip.C0 = LeftHipC0 * LeftHipTilt
	elseif MoveDirection:Dot(Vector3.new(0,0,1).Unit) > dotThreshold then
		-- print("Backwards")

		RootJointTilt = RootJointTilt:Lerp(CFrame.Angles(math.rad(-MoveDirection.Z) * 10, 0, 0), DefaultLerpAlpha)
		RootJoint.C0 = RootJointC0 * RootJointTilt

		RightShoulderTilt = RightShoulderTilt:Lerp(CFrame.Angles(0, 0, 0), DefaultLerpAlpha)
		RightShoulder.C0 = RightShoulderC0 * RightShoulderTilt

		LeftShoulderTilt = LeftShoulderTilt:Lerp(CFrame.Angles(0, 0, 0), DefaultLerpAlpha)
		LeftShoulder.C0 = LeftShoulderC0 * LeftShoulderTilt

		RightHipTilt = RightHipTilt:Lerp(CFrame.Angles(0, 0, 0), DefaultLerpAlpha)
		RightHip.C0 = RightHipC0 * RightHipTilt

		LeftHipTilt = LeftHipTilt:Lerp(CFrame.Angles(0, 0, 0), DefaultLerpAlpha)
		LeftHip.C0 = LeftHipC0 * LeftHipTilt
	elseif MoveDirection:Dot(Vector3.new(-1,0,0).Unit) > dotThreshold then
		-- print("Left")

		RootJointTilt = RootJointTilt:Lerp(CFrame.Angles(0, 0, math.rad(-MoveDirection.X) * 35), DefaultLerpAlpha)
		RootJoint.C0 = RootJointC0 * RootJointTilt

		RightShoulderTilt = RightShoulderTilt:Lerp(CFrame.Angles(0, math.rad(-MoveDirection.X) * 15, 0), DefaultLerpAlpha)
		RightShoulder.C0 = RightShoulderC0 * RightShoulderTilt

		LeftShoulderTilt = LeftShoulderTilt:Lerp(CFrame.Angles(0, math.rad(-MoveDirection.X) * 15, 0), DefaultLerpAlpha)
		LeftShoulder.C0 = LeftShoulderC0 * LeftShoulderTilt

		RightHipTilt = RightHipTilt:Lerp(CFrame.Angles(0, math.rad(-MoveDirection.X) * 15, 0), DefaultLerpAlpha)
		RightHip.C0 = RightHipC0 * RightHipTilt

		LeftHipTilt = LeftHipTilt:Lerp(CFrame.Angles(0, math.rad(-MoveDirection.X) * 15, 0), DefaultLerpAlpha)
		LeftHip.C0 = LeftHipC0 * LeftHipTilt
	elseif MoveDirection == Vector3.new(0, 0, 0) or script:GetAttribute("Toggle") == false then
		RootJointTilt = RootJointTilt:Lerp(CFrame.Angles(0, 0, 0), DefaultLerpAlpha)
		RootJoint.C0 = RootJointC0 * RootJointTilt

		RightShoulderTilt = RightShoulderTilt:Lerp(CFrame.Angles(0, 0, 0), DefaultLerpAlpha)
		RightShoulder.C0 = RightShoulderC0 * RightShoulderTilt

		LeftShoulderTilt = LeftShoulderTilt:Lerp(CFrame.Angles(0, 0, 0), DefaultLerpAlpha)
		LeftShoulder.C0 = LeftShoulderC0 * LeftShoulderTilt

		RightHipTilt = RightHipTilt:Lerp(CFrame.Angles(0, 0, 0), DefaultLerpAlpha)
		RightHip.C0 = RightHipC0 * RightHipTilt

		LeftHipTilt = LeftHipTilt:Lerp(CFrame.Angles(0, 0, 0), DefaultLerpAlpha)
		LeftHip.C0 = LeftHipC0 * LeftHipTilt
	end
end

end

RunService.Heartbeat:Connect(UpdateDirectionalMovement)

I just need more understanding into the code, explain it to me somehow :frowning:

.

.

Now I’ve also made the custom animation but I can’t even make the normal running work, even without directional movement its already weird.

local UIS = game:GetService("UserInputService")
local Plr = game.Players.LocalPlayer
local Char = Plr.Character or Plr.CharacterAdded:Wait()
local Hum = Char:WaitForChild("Humanoid")

local anim = script:WaitForChild("RunAnim")
local loadAnim = Hum:LoadAnimation(anim)

local isMoving = false

-- PC and Controller Player
UIS.InputBegan:Connect(function(input, gameProcessed)
	if input.KeyCode == Enum.KeyCode.LeftControl or (input.UserInputType == Enum.UserInputType.Gamepad1 and input.KeyCode == Enum.KeyCode.Thumbstick1) then
		Hum.WalkSpeed = 26
		isMoving = true
		loadAnim:Play()
	end
end)

UIS.InputEnded:Connect(function(input, gameProcessed)
	if input.KeyCode == Enum.KeyCode.LeftControl or (input.UserInputType == Enum.UserInputType.Gamepad1 and input.KeyCode == Enum.KeyCode.Thumbstick1) then
		Hum.WalkSpeed = 10
		isMoving = false
		loadAnim:Stop()
	end
end)

-- Check player movement every frame
game:GetService("RunService").Heartbeat:Connect(function()
	if isMoving and Hum.MoveDirection.magnitude < 20 then
		-- Player has stopped moving, stop the animation
		isMoving = false
		loadAnim:Stop()
	end
end)	

I made this and I don’t see how can i fix it, the animation plays whenever i press ctrl and move, that’s what i wanted but, it also plays when you sit down or jump or swim.
What animation priorities should I use?

1 Like