local function V()return Player and Player.Character end local function q()local V=findPlayerHumanoid(Player)return V and V.Torso end local function d(V)return V and(V.Parent and V.Parent:FindFirstChild("\072\117\109\097\110\111\105\100")~=nil)end local function g()local g=V()if g==nil then return end local P=findPlayerHumanoid(Player)if P==nil then return end local M=1.5 local b=7.0 local l=q()if l==nil then return end local t=l.CFrame local N=t.lookVector local k=t.p local Z=Ray.new(k+Vector3.new(0,-l.Size.Y/2,0),N*M)local E=Ray.new(k+Vector3.new(0,b-l.Size.Y,0),N*M)local u,C=RayCastIgnoreList(workspace,Z,{g},false)local G,Y=RayCastIgnoreList(workspace,E,{g},false)if u and(G==nil and u.CanCollide==true)then if not d(u)then P.Jump=true end end end local P={[Enum.HumanoidStateType.FallingDown]=false;[Enum.HumanoidStateType.Flying]=false,[Enum.HumanoidStateType.Freefall]=false,[Enum.HumanoidStateType.GettingUp]=false;[Enum.HumanoidStateType.Ragdoll]=false,[Enum.HumanoidStateType.Running]=false,[Enum.HumanoidStateType.Seated]=false,[Enum.HumanoidStateType.Swimming]=false;[Enum.HumanoidStateType.Climbing]=false}local function M()local V=findPlayerHumanoid(Player)local q=V and V:GetState()if q then return P[q]==nil end return false end local function b()return true end local function l(V)return V.magnitude<.05 end


local function GetCharacter()
	return Player and Player.Character
end

local function GetTorso()
	local humanoid = findPlayerHumanoid(Player)
	return humanoid and humanoid.Torso
end

local function IsPartAHumanoid(part)
	return part and part.Parent and (part.Parent:FindFirstChild('Humanoid') ~= nil)
end

local function doAutoJump()
	local character = GetCharacter()
	if (character == nil) then
		return;
	end

	local humanoid = findPlayerHumanoid(Player)
	if (humanoid == nil) then
		return;
	end

	local rayLength = 1.5;
	-- This is how high a ROBLOXian jumps from the mid point of his torso
	local jumpHeight = 7.0;

	local torso = GetTorso()
	if (torso == nil) then
		return;
	end

	local torsoCFrame = torso.CFrame;
	local torsoLookVector = torsoCFrame.lookVector;
	local torsoPos = torsoCFrame.p;

	local torsoRay = Ray.new(torsoPos + Vector3.new(0, -torso.Size.Y/2, 0), torsoLookVector * rayLength);
	local jumpRay = Ray.new(torsoPos + Vector3.new(0, jumpHeight - torso.Size.Y, 0), torsoLookVector * rayLength);

	local hitPart, _ = RayCastIgnoreList(workspace, torsoRay, {character}, false)
	local jumpHitPart, _ = RayCastIgnoreList(workspace, jumpRay, {character}, false)

	if (hitPart and jumpHitPart == nil and hitPart.CanCollide == true) then
		 -- NOTE: this follow line is not in the C++ impl, but an improvement  in Click to Move
		if not IsPartAHumanoid(hitPart) then
			humanoid.Jump = true;
		end
	end
end

local NO_JUMP_STATES =
{
	[Enum.HumanoidStateType.FallingDown] = false;
	[Enum.HumanoidStateType.Flying] = false;
	[Enum.HumanoidStateType.Freefall] = false;
	[Enum.HumanoidStateType.GettingUp] = false;
	[Enum.HumanoidStateType.Ragdoll] = false;
	[Enum.HumanoidStateType.Running] = false;
	[Enum.HumanoidStateType.Seated] = false;
	[Enum.HumanoidStateType.Swimming] = false;

	-- Special case to detect if we are on a ladder
	[Enum.HumanoidStateType.Climbing] = false;
}

local function enableAutoJump()
	local humanoid = findPlayerHumanoid(Player)
	local currentState = humanoid and humanoid:GetState()
	if currentState then
		return NO_JUMP_STATES[currentState] == nil
	end
	return false
end

local function getAutoJump()
	return true
end

local function vec3IsZero(vec3)
	return vec3.magnitude < 0.05
end
