Evade Movement
Key RequiredUniversal

Evade Movement

Universal ScriptProScriptsProScripts 3.4K views 1.3K executesUpdated May 10, 2026
5.0/ 5(1 votes)
10100% Positive
Lua Script•725 lines (23564 chars)
-- THIS SCRIPT WAS EDITED BY PRO SCRIPTS
-- THANK YOU LAZUMN FOR PROVIDING THIS SCRIPT IT'S REALLY APPERICIATED

-- Framework is a recreation of evade and is in beta at the moment
-- It took me 3 months to create this please respect me...
-- arms are bugged right now.. animation might be added soon

-- DEV LOG:
-- Arms broke
-- Camera got broken lol 
-- lolllllll
-- i cant keep commenting at the top!!!!

-- FOLLOW MY ROBLOX ACCOUNT NOWWWW!!!!! 

-- ever played evade before? this framework was created for that but i made it easier for trimping 
-- i might just decompile evade first person scripts remake them than have a decompiled evade first person
-- waht you guys think? 
-- i spent so much timme scripting

local Players = game:GetService("Players")
local RunService = game:GetService("RunService")
local UserInputService = game:GetService("UserInputService")
local Workspace = game:GetService("Workspace")
local TweenService = game:GetService("TweenService")

local player = Players.LocalPlayer
player:GetMouse().Icon = "rbxassetid://11783958279"
local character = player.Character or player.CharacterAdded:Wait()
local humanoid = character:WaitForChild("Humanoid")
local rootPart = character:WaitForChild("HumanoidRootPart")
local camera = Workspace.CurrentCamera
humanoid.WalkSpeed = 90
if _G.fopFrameworkRunning then
	error(player.Name.. "[Framework] is already running — cannot run twice.")
	return
end
_G.fopFrameworkRunning = true

player.CharacterRemoving:Connect(function()
	_G.fopFrameworkRunning = nil
end)

local viewmodel = Instance.new("Model")
viewmodel.Name = "Viewmodel"
viewmodel.Parent = camera

local vHumanoid = Instance.new("Humanoid")
vHumanoid.Parent = viewmodel
vHumanoid.DisplayDistanceType = Enum.HumanoidDisplayDistanceType.None

local function createArm(name)
	local arm = Instance.new("Part")
	arm.Name = name
	arm.Size = Vector3.new(0.6, 1.5, 0.6)
	arm.CanCollide = false
	arm.CastShadow = false
	arm.Massless = true
	arm.Parent = viewmodel
	return arm
end

local lArm = createArm("Left Arm")
local rArm = createArm("Right Arm")

local function syncAppearance()
	local shirt = character:FindFirstChildOfClass("Shirt")
	if shirt then
		local vShirt = viewmodel:FindFirstChildOfClass("Shirt") or Instance.new("Shirt", viewmodel)
		vShirt.ShirtTemplate = shirt.ShirtTemplate
	end
	local charLeft = character:FindFirstChild("Left Arm") or character:FindFirstChild("LeftUpperArm")
	local charRight = character:FindFirstChild("Right Arm") or character:FindFirstChild("RightUpperArm")
	if charLeft then lArm.Color = charLeft.Color end
	if charRight then rArm.Color = charRight.Color end
end

local screenGui = Instance.new("ScreenGui")
screenGui.Name = "SpeedGui"
screenGui.ResetOnSpawn = false
screenGui.Parent = player.PlayerGui

local frame = Instance.new("Frame")
frame.Size = UDim2.new(0, 90, 0, 40)
frame.Position = UDim2.new(0, 16, 1, -56)
frame.BackgroundColor3 = Color3.fromRGB(0, 0, 0)
frame.BackgroundTransparency = 0.25
frame.BorderSizePixel = 0
frame.Parent = screenGui

local corner = Instance.new("UICorner")
corner.CornerRadius = UDim.new(0, 6)
corner.Parent = frame

local label = Instance.new("TextLabel")
label.Size = UDim2.new(1, 0, 1, 0)
label.BackgroundTransparency = 1
label.TextColor3 = Color3.fromRGB(255, 255, 255)
label.TextSize = 20
label.Font = Enum.Font.GothamBold
label.Parent = frame

syncAppearance()
character.ChildAdded:Connect(syncAppearance)

Workspace.Gravity = 190
player.CameraMaxZoomDistance = 0.5
humanoid.JumpPower = 52

local Config = {
	BaseSpeed = 16,
	CrouchSpeed = 8,
	SprintSpeed = 28,
	JUMP_BOOST = 1.18,
	BaseFOV = 85,
	SprintFOV = 110,
	MaxFOV = 130,
	MouseTiltSens = 0.08,
	BobIntensity = 0.35,
	StrafeTilt = 5,
	JumpBuildMax = 200,
	JumpBuildRate = 6,
	JumpBuildDecay = 18,
	JumpBuildBoost = 1.22,
}

local armState = {
	lArmPos  = Vector3.new(-1.2, 0, 0),
	rArmPos  = Vector3.new( 1.2, 0, 0),
	lArmAngX = 90,
	rArmAngX = 90,
	lArmAngY = 0,
	rArmAngY = 0,
	lArmAngZ = 0,
	rArmAngZ = 0,
}

local State = {
	Crouching = false,
	Sprinting = false,
	IsTrimping = false,
	IsThirdPerson = false,
	CanSwitch = true,
	OnGround = true,
	WasOnGround = true,
}

local vmBobTime = 0
local bobTime = 0
local swayAmount = Vector2.new(0, 0)
local bobOffset = CFrame.identity
local currentTilt = 0
local currentFOV = Config.BaseFOV
local currentStrafeTilt = 0
local builtSpeed = 0
local rayParams = RaycastParams.new()
rayParams.FilterDescendantsInstances = {character}
local currentShiftLockAngle = 0

local function enterThirdPerson()
	if not State.CanSwitch then return end
	State.CanSwitch = false
	State.IsThirdPerson = true
	player.CameraMaxZoomDistance = 5
	player.CameraMinZoomDistance = 5
	task.wait(0.5)
	State.CanSwitch = true
end

local function enterFirstPerson()
	if not State.CanSwitch then return end
	State.CanSwitch = false
	State.IsThirdPerson = false
	task.spawn(function()
		local start = player.CameraMinZoomDistance
		local steps = 20
		for i = 1, steps do
			local alpha = i / steps
			local current = start * (1 - alpha)
			player.CameraMaxZoomDistance = math.max(current, 0.5)
			player.CameraMinZoomDistance = math.max(current, 0.5)
			task.wait(0.005)
		end
		player.CameraMaxZoomDistance = 0.5
		player.CameraMinZoomDistance = 0.5
		task.wait(0.5)
		State.CanSwitch = true
	end)
end

local function togglePerspective()
	if State.IsThirdPerson then
		enterFirstPerson()
	else
		enterThirdPerson()
	end
end

local function getMoveDir()
	local moveDir = Vector3.new(0, 0, 0)
	local camCF = camera.CFrame
	local forward = Vector3.new(camCF.LookVector.X, 0, camCF.LookVector.Z).Unit
	local right = Vector3.new(camCF.RightVector.X, 0, camCF.RightVector.Z).Unit

	if UserInputService:IsKeyDown(Enum.KeyCode.W) then moveDir += forward end
	if UserInputService:IsKeyDown(Enum.KeyCode.S) then moveDir -= forward end
	if UserInputService:IsKeyDown(Enum.KeyCode.A) then moveDir -= right end
	if UserInputService:IsKeyDown(Enum.KeyCode.D) then moveDir += right end

	local thumbstick = UserInputService:GetNavigationGamepads()
	if #thumbstick > 0 then
		local leftStick = UserInputService:GetGamepadState(thumbstick[1])
		for _, input in ipairs(leftStick) do
			if input.KeyCode == Enum.KeyCode.Thumbstick1 then
				local stickDir = Vector3.new(input.Position.X, 0, -input.Position.Y)
				if stickDir.Magnitude > 0.15 then
					local fullDir = (forward * -stickDir.Z + right * stickDir.X)
					if fullDir.Magnitude > 0 then
						moveDir += fullDir.Unit
					end
				end
			end
		end
	end

	if moveDir.Magnitude > 1 then moveDir = moveDir.Unit end
	return moveDir
end

RunService.Heartbeat:Connect(function(dt)
	if not rootPart or not humanoid then return end

	local currentVel = rootPart.AssemblyLinearVelocity
	local flatVel = Vector3.new(currentVel.X, 0, currentVel.Z)
	local verticalY = currentVel.Y
	local moveDir = getMoveDir()
	local onGround = humanoid.FloorMaterial ~= Enum.Material.Air

	State.OnGround = onGround

	local justLanded = onGround and not State.WasOnGround
	State.WasOnGround = onGround

	if onGround and not justLanded then
		builtSpeed = math.max(builtSpeed - Config.JumpBuildDecay * dt, 0)
	end

	local baseMax = State.Crouching and (Config.CrouchSpeed * 4.5)
		or State.Sprinting and (Config.SprintSpeed * 4.5)
		or (Config.BaseSpeed * 4.5)

	local maxS = math.min(baseMax + builtSpeed, Config.JumpBuildMax)

	local accelBase = State.Crouching and Config.CrouchSpeed
		or State.Sprinting and Config.SprintSpeed
		or Config.BaseSpeed
	local accel = accelBase * 5.0

	if moveDir.Magnitude > 0 then
		flatVel += moveDir * accel * dt * 80
	end

	local frictionMult = (not onGround) and 0.995
	or State.Sprinting and 0.985
	or 0.94

	flatVel *= frictionMult

	if flatVel.Magnitude > maxS then
		flatVel = flatVel.Unit * maxS
	end

	local function doTrimp(normal)
	if flatVel.Magnitude < 18 then return end
		if normal.Y < 0.92 and normal.Y > 0.08 then
			local launch = flatVel.Magnitude * (1 - normal.Y) * 2.2
			if verticalY < launch then
				verticalY = launch
				humanoid:ChangeState(Enum.HumanoidStateType.Freefall)
				State.IsTrimping = true
			end
		elseif math.abs(normal.Y) < 0.15 then
			local sideDir = Vector3.new(normal.X, 0, normal.Z)
			local dot = flatVel.Unit:Dot(-sideDir)
			if dot > 0.3 then
				local sideBoost = flatVel.Magnitude * dot * 1.6
				if verticalY < sideBoost then
					verticalY = sideBoost
					flatVel = flatVel + sideDir * flatVel.Magnitude * 0.4
					humanoid:ChangeState(Enum.HumanoidStateType.Freefall)
					State.IsTrimping = true
				end
			end
		end
	end

	local forwardRayDir = (flatVel.Magnitude > 5 and flatVel.Unit or rootPart.CFrame.LookVector) * 2.5 + Vector3.new(0, -4.5, 0)
	local forwardRay = Workspace:Raycast(rootPart.Position, forwardRayDir, rayParams)
	if forwardRay then doTrimp(forwardRay.Normal) end

	local sideOffsets = {
		Vector3.new( rootPart.CFrame.RightVector.X, 0,  rootPart.CFrame.RightVector.Z) * 2.2,
		Vector3.new(-rootPart.CFrame.RightVector.X, 0, -rootPart.CFrame.RightVector.Z) * 2.2,
	}
	for _, offset in ipairs(sideOffsets) do
		local sideRay = Workspace:Raycast(rootPart.Position, offset + Vector3.new(0, -1.5, 0), rayParams)
		if sideRay then doTrimp(sideRay.Normal) end
	end

	if State.IsTrimping and verticalY > 5 then
		Workspace.Gravity = 130
	else
		State.IsTrimping = false
		Workspace.Gravity = math.min(Workspace.Gravity + (190 - Workspace.Gravity) * 5 * dt, 190)
	end

	if flatVel.Magnitude > maxS then
		flatVel = flatVel.Unit * maxS
	end

	rootPart.AssemblyLinearVelocity = Vector3.new(flatVel.X, verticalY, flatVel.Z)
end)

humanoid.Jumping:Connect(function()
	local vel = rootPart.AssemblyLinearVelocity
	local flatSpeed = Vector3.new(vel.X, 0, vel.Z).Magnitude

	builtSpeed = math.min(builtSpeed + Config.JumpBuildRate, Config.JumpBuildMax)

	task.wait()
	local boost = Config.JUMP_BOOST + (builtSpeed / Config.JumpBuildMax) * (Config.JumpBuildBoost - Config.JUMP_BOOST)
	rootPart.AssemblyLinearVelocity = Vector3.new(vel.X * boost, rootPart.AssemblyLinearVelocity.Y, vel.Z * boost)
end)

local function ensureArms()
	if not lArm or not lArm.Parent then lArm = createArm("Left Arm") end
	if not rArm or not rArm.Parent then rArm = createArm("Right Arm") end
end

RunService.RenderStepped:Connect(function(dt)
	if not rootPart or not humanoid then return end

	local velocity = rootPart.AssemblyLinearVelocity
	local velY = velocity.Y
	local speed = Vector3.new(velocity.X, 0, velocity.Z).Magnitude
	local isMoving = speed > 2
	local isFalling = humanoid.FloorMaterial == Enum.Material.Air

	local mouseDelta = UserInputService:GetMouseDelta()
	swayAmount = swayAmount:Lerp(mouseDelta, 0.1)
	local swayCF = CFrame.Angles(
		math.rad(swayAmount.Y * 0.07),
		math.rad(swayAmount.X * 0.07),
		math.rad(swayAmount.X * 0.04)
	)

	label.Text = math.floor(speed) .. "%"

	local strafeInput = 0
	if UserInputService:IsKeyDown(Enum.KeyCode.A) then strafeInput -= 1 end
	if UserInputService:IsKeyDown(Enum.KeyCode.D) then strafeInput += 1 end

	local thumbstick = UserInputService:GetNavigationGamepads()
	if #thumbstick > 0 then
		local leftStick = UserInputService:GetGamepadState(thumbstick[1])
		for _, input in ipairs(leftStick) do
			if input.KeyCode == Enum.KeyCode.Thumbstick1 then
				if math.abs(input.Position.X) > 0.15 then
					strafeInput = input.Position.X
				end
			end
		end
	end

	local targetStrafeTilt = math.rad(strafeInput * Config.StrafeTilt * (isMoving and 1 or 0.4))
	currentStrafeTilt = currentStrafeTilt + (targetStrafeTilt - currentStrafeTilt) * 8 * dt

	local speedRatio = math.clamp(speed / Config.JumpBuildMax, 0, 1)
	local targetFOV
	if State.Sprinting and isMoving then
		targetFOV = Config.SprintFOV + (Config.MaxFOV - Config.SprintFOV) * speedRatio
	elseif State.Crouching then
		targetFOV = Config.BaseFOV - 5
	else
		targetFOV = Config.BaseFOV + (Config.SprintFOV - Config.BaseFOV) * speedRatio
	end
	currentFOV = currentFOV + (targetFOV - currentFOV) * 6 * dt

	vmBobTime += dt * (isMoving and (speed * 0.21) or 0.38)
	local pump = isMoving and math.sin(vmBobTime) * 0.28 or 0
	local verticalBob = isMoving and (math.sin(vmBobTime) * 0.1) or (math.sin(vmBobTime * 0.5) * 0.03)
	local horizontalSway = isMoving and 0 or (math.cos(vmBobTime * 0.5) * 0.02)

	lArm.Transparency = State.IsThirdPerson and 1 or 0
	rArm.Transparency = State.IsThirdPerson and 1 or 0

	if State.IsThirdPerson then
		local targetAngle = math.atan2(velocity.X, velocity.Z)
		if speed > 1 then
			currentShiftLockAngle = currentShiftLockAngle + (targetAngle - currentShiftLockAngle) * 10 * dt
		end
		local camCF = camera.CFrame
		local flatLook = Vector3.new(camCF.LookVector.X, 0, camCF.LookVector.Z).Unit
		rootPart.CFrame = rootPart.CFrame:Lerp(CFrame.new(rootPart.Position) * CFrame.Angles(0, math.atan2(-flatLook.X, -flatLook.Z), 0), 12 * dt)
	end

	if not State.IsThirdPerson then
		camera.FieldOfView = currentFOV

		local vmRoot = camera.CFrame * swayCF * CFrame.new(horizontalSway, -1.6 + verticalBob, -1.1)

		local function getArmTargets()
			local isOnGround = humanoid.FloorMaterial ~= Enum.Material.Air

			if velY > 4 and not isOnGround then
				local jumpBlend = math.clamp((velY - 4) / 12, 0, 1)
				return {
					lArmPos  = Vector3.new(-1.35, 0.15 * jumpBlend, -0.3 * jumpBlend),
					rArmPos  = Vector3.new( 1.35, 0.15 * jumpBlend, -0.3 * jumpBlend),
					lArmAngX = 90 - 30 * jumpBlend, rArmAngX = 90 - 30 * jumpBlend,
					lArmAngY = 0, rArmAngY = 0,
					lArmAngZ = 18 * jumpBlend, rArmAngZ = -18 * jumpBlend,
				}
			elseif velY < -4 and not isOnGround then
				local fallBlend = math.clamp((-velY - 4) / 14, 0, 1)
				return {
					lArmPos  = Vector3.new(-1.3, 0.2 * fallBlend, 0.25 * fallBlend),
					rArmPos  = Vector3.new( 1.3, 0.2 * fallBlend, 0.25 * fallBlend),
					lArmAngX = 90 + 25 * fallBlend, rArmAngX = 90 + 25 * fallBlend,
					lArmAngY = 0, rArmAngY = 0,
					lArmAngZ = 22 * fallBlend, rArmAngZ = -22 * fallBlend,
				}
			elseif isMoving then
				local runBlend = math.clamp((speed - 2) / 6, 0, 1)
				local swing = math.sin(vmBobTime) * 40 * runBlend
				return {
					lArmPos  = Vector3.new(-1.2, verticalBob, pump * 1.6 * runBlend),
					rArmPos  = Vector3.new( 1.2, verticalBob, -pump * 1.6 * runBlend),
					lArmAngX = 90, rArmAngX = 90,
					lArmAngY = swing, rArmAngY = -swing,
					lArmAngZ = 6 * runBlend, rArmAngZ = -6 * runBlend,
				}
			else
				local breatheZ = math.sin(vmBobTime * 0.4) * 0.015
				local breatheY = math.sin(vmBobTime * 0.5) * 0.03
				return {
					lArmPos  = Vector3.new(-1.18 + horizontalSway, breatheY, 0),
					rArmPos  = Vector3.new( 1.18 - horizontalSway, breatheY, 0),
					lArmAngX = 90, rArmAngX = 90,
					lArmAngY = 0, rArmAngY = 0,
					lArmAngZ = breatheZ + 3, rArmAngZ = -breatheZ - 3,
				}
			end
		end

		local targets = getArmTargets()
		local lerpSpeed = 8 * dt

		armState.lArmPos  = armState.lArmPos:Lerp(targets.lArmPos, lerpSpeed)
		armState.rArmPos  = armState.rArmPos:Lerp(targets.rArmPos, lerpSpeed)
		armState.lArmAngX = armState.lArmAngX + (targets.lArmAngX - armState.lArmAngX) * lerpSpeed
		armState.rArmAngX = armState.rArmAngX + (targets.rArmAngX - armState.rArmAngX) * lerpSpeed
		armState.lArmAngY = armState.lArmAngY + (targets.lArmAngY - armState.lArmAngY) * lerpSpeed
		armState.rArmAngY = armState.rArmAngY + (targets.rArmAngY - armState.rArmAngY) * lerpSpeed
		armState.lArmAngZ = armState.lArmAngZ + (targets.lArmAngZ - armState.lArmAngZ) * lerpSpeed
		armState.rArmAngZ = armState.rArmAngZ + (targets.rArmAngZ - armState.rArmAngZ) * lerpSpeed

		lArm.CFrame = vmRoot
			* CFrame.new(armState.lArmPos)
			* CFrame.Angles(math.rad(armState.lArmAngX), math.rad(armState.lArmAngY), math.rad(armState.lArmAngZ))

		rArm.CFrame = vmRoot
			* CFrame.new(armState.rArmPos)
			* CFrame.Angles(math.rad(armState.rArmAngX), math.rad(armState.rArmAngY), math.rad(armState.rArmAngZ))
	end

	local targetTilt = math.clamp(-mouseDelta.X * Config.MouseTiltSens, -12, 12)
	currentTilt = currentTilt + (math.rad(targetTilt) - currentTilt) * 6 * dt

	local bTime = tick() * 2.0
	local breathing = Vector3.new(math.sin(bTime * 0.5) * 0.04, math.sin(bTime) * 0.12, 0)

	if isMoving and not isFalling then
		bobTime += dt * (speed * 0.4)
		bobOffset = CFrame.new(math.cos(bobTime / 2) * 0.15, math.sin(bobTime) * 0.35, 0)
	else
		bobOffset = bobOffset:Lerp(CFrame.identity, 0.1)
	end

	if not State.IsThirdPerson then
		camera.CFrame = camera.CFrame * CFrame.new(breathing) * bobOffset * CFrame.Angles(0, 0, currentTilt + currentStrafeTilt)
	else
		camera.CFrame = camera.CFrame * CFrame.Angles(0, 0, currentTilt + currentStrafeTilt)
	end

	local crouchGoal = State.Crouching and -1.8 or 0
	humanoid.CameraOffset = humanoid.CameraOffset:Lerp(Vector3.new(0, crouchGoal, 0), 10 * dt)
end)

UserInputService.InputBegan:Connect(function(i, gp)
	if gp then return end

	if i.KeyCode == Enum.KeyCode.C or i.KeyCode == Enum.KeyCode.ButtonB then
		State.Crouching = true
		State.Sprinting = false
	elseif i.KeyCode == Enum.KeyCode.LeftShift or i.KeyCode == Enum.KeyCode.ButtonL3 then
		if not State.Crouching then
			State.Sprinting = true
		end
	elseif i.KeyCode == Enum.KeyCode.Z or i.KeyCode == Enum.KeyCode.ButtonR3 then
		togglePerspective()
	end
end)

UserInputService.InputEnded:Connect(function(i, gp)
	if gp then return end

	if i.KeyCode == Enum.KeyCode.C or i.KeyCode == Enum.KeyCode.ButtonB then
		State.Crouching = false
	elseif i.KeyCode == Enum.KeyCode.LeftShift or i.KeyCode == Enum.KeyCode.ButtonL3 then
		State.Sprinting = false
	end
end)

local isMobile = UserInputService.TouchEnabled and not UserInputService.KeyboardEnabled

if isMobile then
	local sprintGui = Instance.new("ScreenGui")
	sprintGui.Name = "SprintGui"
	sprintGui.ResetOnSpawn = false
	sprintGui.IgnoreGuiInset = true
	sprintGui.Parent = player.PlayerGui

	local sprintBtn = Instance.new("TextButton")
	sprintBtn.Size = UDim2.new(0.18, 0, 0.12, 0)
	sprintBtn.Position = UDim2.new(0.78, 0, 0.78, 0)
	sprintBtn.AnchorPoint = Vector2.new(0.5, 0.5)
	sprintBtn.BackgroundColor3 = Color3.fromRGB(255, 255, 255)
	sprintBtn.BackgroundTransparency = 0.3
	sprintBtn.BorderSizePixel = 0
	sprintBtn.Text = "SPRINT"
	sprintBtn.TextColor3 = Color3.fromRGB(255, 255, 255)
	sprintBtn.TextScaled = true
	sprintBtn.Font = Enum.Font.GothamBold
	sprintBtn.Parent = sprintGui

	local btnCorner = Instance.new("UICorner")
	btnCorner.CornerRadius = UDim.new(0.25, 0)
	btnCorner.Parent = sprintBtn

	local btnStroke = Instance.new("UIStroke")
	btnStroke.Color = Color3.fromRGB(255, 255, 255)
	btnStroke.Thickness = 2
	btnStroke.Transparency = 0.6
	btnStroke.Parent = sprintBtn

	local function setSprinting(val)
		if State.Crouching then return end
		State.Sprinting = val
		sprintBtn.BackgroundTransparency = val and 0.1 or 0.3
		sprintBtn.TextColor3 = val
			and Color3.fromRGB(255, 220, 80)
			or Color3.fromRGB(255, 255, 255)
	end

	sprintBtn.InputBegan:Connect(function(input)
		if input.UserInputType == Enum.UserInputType.Touch then
			setSprinting(true)
		end
	end)

	sprintBtn.InputEnded:Connect(function(input)
		if input.UserInputType == Enum.UserInputType.Touch then
			setSprinting(false)
		end
	end)
end

local function resetArms()
	armState.lArmPos  = Vector3.new(-1.2, 0, 0)
	armState.rArmPos  = Vector3.new( 1.2, 0, 0)
	armState.lArmAngX = 90
	armState.rArmAngX = 90
	armState.lArmAngY = 0
	armState.rArmAngY = 0
	armState.lArmAngZ = 0
	armState.rArmAngZ = 0

	if lArm and lArm.Parent then lArm:Destroy() end
	if rArm and rArm.Parent then rArm:Destroy() end

	lArm = createArm("Left Arm")
	rArm = createArm("Right Arm")
	syncAppearance()
end

UserInputService.InputBegan:Connect(function(i, gp)
	if gp then return end
	if i.KeyCode == Enum.KeyCode.Minus then
		resetArms()
	end
end)

if isMobile then

	local perspectiveGui = Instance.new("ScreenGui")
	perspectiveGui.Name = "PerspectiveGui"
	perspectiveGui.ResetOnSpawn = false
	perspectiveGui.IgnoreGuiInset = true
	perspectiveGui.Parent = player.PlayerGui

	local perspectiveBtn = Instance.new("TextButton")
	perspectiveBtn.Size = UDim2.new(0.22, 0, 0.07, 0)
	perspectiveBtn.Position = UDim2.new(0.5, 0, 0.03, 0)
	perspectiveBtn.AnchorPoint = Vector2.new(0.5, 0)
	perspectiveBtn.BackgroundColor3 = Color3.fromRGB(0, 0, 0)
	perspectiveBtn.BackgroundTransparency = 0.35
	perspectiveBtn.BorderSizePixel = 0
	perspectiveBtn.Text = "FIRST PERSON"
	perspectiveBtn.TextColor3 = Color3.fromRGB(255, 255, 255)
	perspectiveBtn.TextScaled = true
	perspectiveBtn.Font = Enum.Font.GothamBold
	perspectiveBtn.Parent = perspectiveGui

	local perspCorner = Instance.new("UICorner")
	perspCorner.CornerRadius = UDim.new(0, 8)
	perspCorner.Parent = perspectiveBtn

	local perspStroke = Instance.new("UIStroke")
	perspStroke.Color = Color3.fromRGB(180, 180, 180)
	perspStroke.Thickness = 1.5
	perspStroke.Transparency = 0.5
	perspStroke.Parent = perspectiveBtn

	perspectiveBtn.MouseButton1Click:Connect(function()
		togglePerspective()
		task.wait(0.1)
		perspectiveBtn.Text = State.IsThirdPerson and "THIRD PERSON" or "FIRST PERSON"
	end)

	local resetGui = Instance.new("ScreenGui")
	resetGui.Name = "ResetArmsGui"
	resetGui.ResetOnSpawn = false
	resetGui.IgnoreGuiInset = true
	resetGui.Parent = player.PlayerGui

	local resetBtn = Instance.new("TextButton")
	resetBtn.Size = UDim2.new(0.18, 0, 0.08, 0)
	resetBtn.Position = UDim2.new(0.78, 0, 0.65, 0)
	resetBtn.AnchorPoint = Vector2.new(0.5, 0.5)
	resetBtn.BackgroundColor3 = Color3.fromRGB(255, 255, 255)
	resetBtn.BackgroundTransparency = 0.3
	resetBtn.BorderSizePixel = 0
	resetBtn.Text = "RESET ARMS"
	resetBtn.TextColor3 = Color3.fromRGB(255, 255, 255)
	resetBtn.TextScaled = true
	resetBtn.Font = Enum.Font.GothamBold
	resetBtn.Parent = resetGui

	local resetCorner = Instance.new("UICorner")
	resetCorner.CornerRadius = UDim.new(0.25, 0)
	resetCorner.Parent = resetBtn

	local resetStroke = Instance.new("UIStroke")
	resetStroke.Color = Color3.fromRGB(255, 255, 255)
	resetStroke.Thickness = 2
	resetStroke.Transparency = 0.6
	resetStroke.Parent = resetBtn

	local dragging = false
	local dragStartPos = Vector2.new()
	local btnStartPos = Vector2.new()
	local wasDrag = false
	local DRAG_THRESHOLD = 10

	resetBtn.InputBegan:Connect(function(input)
		if input.UserInputType == Enum.UserInputType.Touch then
			dragging = true
			wasDrag = false
			dragStartPos = Vector2.new(input.Position.X, input.Position.Y)
			local absPos = resetBtn.AbsolutePosition
			local absSize = resetBtn.AbsoluteSize
			btnStartPos = Vector2.new(
				absPos.X + absSize.X * 0.5,
				absPos.Y + absSize.Y * 0.5
			)
		end
	end)

	UserInputService.TouchMoved:Connect(function(input)
		if not dragging then return end
		local delta = Vector2.new(input.Position.X, input.Position.Y) - dragStartPos
		if delta.Magnitude > DRAG_THRESHOLD then
			wasDrag = true
		end
		if wasDrag then
			local vp = camera.ViewportSize
			local newX = (btnStartPos.X + delta.X) / vp.X
			local newY = (btnStartPos.Y + delta.Y) / vp.Y
			newX = math.clamp(newX, 0.05, 0.95)
			newY = math.clamp(newY, 0.05, 0.95)
			resetBtn.Position = UDim2.new(newX, 0, newY, 0)
		end
	end)

	UserInputService.TouchEnded:Connect(function(input)
		if not dragging then return end
		dragging = false
		if not wasDrag then
			resetBtn.BackgroundTransparency = 0.1
			resetArms()
			task.wait(0.12)
			resetBtn.BackgroundTransparency = 0.3
		end
	end)
end

if isMobile then
    task.wait(1)
    game:GetService("StarterGui"):SetCore("SendNotification", {
        Title = "HOW TO CHANGE SPEED EASILY",
        Text = "This bug may never get fixed but if your speed is stuck at 16 please go to Infinite Yield and set your speed",
        Duration = 8,
    })
end

Features & Information

This script involves trimping very easily when executing i allow you to copy the script and yes you can change the settings if you want. Trimping is very easy just run up a part thats like a ramp doesnt have to be one but like a upside down right angle rotate to the right a bit. Bhopping - Jumping to get faster No Delay When Moving - When Moving There Is No Delay Making it more easier Some Games May Work - Many Games have their own framework or character movement which wont allow this script to work. I spent the last 3 months working on this. As of right i know how scripting works. Thanks to Lazumn(burstoutmee) for giving us this script many things have been taken off. and rewritten by me. More better scripts comes in the future! Im not sure about sprinting like the sprint buttons and to hold shift to sprint.
#Evade#Movement#Physics#Frameowkr#Fun

Community Comments (3)

ProScriptsProScriptsMay 10, 2026

MOBILE IS CURRENTLY BEING TESTED AT THE MOMENT I WILL COME BACK IF IT GETS FIXED

ProScriptsProScriptsMay 10, 2026

* FOR MOBILE PLAYERS GO TO INFINITIE YIELD AND SET YOUR SPEED TO HOWEVER YOU LIKE THAN IT'LL WORK AT THIS TIME I AM NOT FIXING IT *

Luc14324Luc14324May 11, 2026

nice!

More Scripts for Universal Scripts