Humanoid dies on spawn when using Humanoid:Move and refuses to respawn

You can write your topic however you want, but you need to answer these questions:

  1. What do you want to achieve? Quake movement

  2. What is the issue? Character instantly dies and wont respawn

  3. What solutions have you tried so far? Trying to dig into the code to find what would cause it

Attempted port of https://github.com/WiggleWizard/quake3-movement-unity3d/blob/master/CPMPlayer.cs

    --Movement stuff
	local friction = 6;
	local gravity = 20
	local moveSpeed = 7.0;                -- Ground move speed
	local runAcceleration = 14.0;         -- Ground accel
	local runDeacceleration = 10.0;       -- Deacceleration that occurs when running on the ground
	local airAcceleration = 2.0;          -- Air accel
	local airDecceleration = 2.0;         -- Deacceleration experienced when ooposite strafing
	local airControl = 0.3;               -- How precise air control is
	local sideStrafeAcceleration = 50.0;  -- How fast acceleration occurs to get up to sideStrafeSpeed when
	local sideStrafeSpeed = 1.0;          -- What the max speed to generate when side strafing
	local jumpSpeed = 8.0;                -- The speed at which the character's up axis gains when hitting jump
	local holdJumpToBhop = false; 
	local grounded = true
	
	local playerVelocity = Vector3.zero;
	local playerFriction = 0
	local moveDirectionNorm =  Vector3.zero;
	
	local wishJump = false;
	
	local _cmd = {
		forwardMove = 0,
		rightMove = 0,
		upMove = 0
	}
	local dt = 0
	local function getAxisVert()
		local move = 0
		move = move + (userInputService:IsKeyDown(Enum.KeyCode.W) and 1 or 0)
		move = move - (userInputService:IsKeyDown(Enum.KeyCode.S) and 1 or 0)
		return move
	end
	local function getAxisHoriz()
		local move = 0
		move = move - (userInputService:IsKeyDown(Enum.KeyCode.A) and 1 or 0)
		move = move + (userInputService:IsKeyDown(Enum.KeyCode.D) and 1 or 0)
		return move
	end
	
	local function SetMovementDir()
		_cmd.forwardMove = getAxisVert()
		_cmd.rightMove = getAxisHoriz()
	end
	
	local function QueueJump()
		if (userInputService:IsKeyDown(Enum.KeyCode.Space) and not wishJump) then
			wishJump = true
		end
		if not (userInputService:IsKeyDown(Enum.KeyCode.Space)) then
			wishJump = false
		end
	end
	
	local function Accelerate(wishdir , wishspeed , accel )
		local addspeed = 0;
		local accelspeed = 0;
		local currentspeed = 0;

		currentspeed = fix(playerVelocity:Dot(wishdir))
		addspeed = fix(wishspeed - currentspeed)
		if(addspeed <= 0) then
			return;
		end
		accelspeed =  fix(accel * dt * wishspeed);
		if(accelspeed > addspeed) then
			accelspeed =  fix(addspeed);
		end
		playerVelocity = Vector3.new(playerVelocity.X + accelspeed * wishdir.X, 0 ,playerVelocity.Z + accelspeed * wishdir.Z)
	end
	
	local function AirControl(wishdir , wishspeed )
		local zspeed;
		local speed;
		local dot;
		local k;

		-- Can't control movement if not moving forward or backward
		if(math.abs(_cmd.forwardMove) < 0.001 and math.abs(wishspeed) < 0.001) then
			return;
		end
		zspeed = playerVelocity.Y;
		playerVelocity *= Vector3.new(1,0,1)
		-- Next two lines are equivalent to idTech's VectorNormalize() */
		speed = playerVelocity.magnitude;
		playerVelocity = playerVelocity.Unit;

		dot = playerVelocity:Dot(wishdir);
		k = 32;
		k *= airControl * dot * dot * dt;

		-- Change direction while slowing down
		if (dot > 0) then
			playerVelocity = Vector3.new(playerVelocity.X * speed + wishdir.X * k, playerVelocity.Y * speed + wishdir.Y * k, playerVelocity.Z * speed + wishdir.Z * k)
			playerVelocity = playerVelocity.Unit;
			moveDirectionNorm = playerVelocity;
		end

		playerVelocity = Vector3.new(playerVelocity.X * speed, zspeed, playerVelocity.Z * speed)
	end
	
	local function AirMove()
		local wishdir  = Vector3.zero
		local accel = 0
		
		SetMovementDir()
			
		wishdir = Vector3.new(_cmd.rightMove,0, _cmd.forwardMove)
		local wishspeed = wishdir.Magnitude;
		
		wishspeed *= moveSpeed
		
		wishdir = wishdir.Unit
		
		moveDirectionNorm = wishdir
		
		local wishspeed2 = wishspeed;
		if playerVelocity:Dot(wishdir) < 0 then
			accel = airDecceleration;
		else
			accel = airAcceleration;
		end
		
		if(_cmd.forwardMove == 0 and _cmd.rightMove ~= 0) then
			if(wishspeed > sideStrafeSpeed) then
				wishspeed = sideStrafeSpeed;
			end
			accel = sideStrafeAcceleration;
		end
		Accelerate(wishdir, wishspeed, accel)
		if(airControl > 0) then
			AirControl(wishdir, wishspeed2);
		end
		
		playerVelocity += Vector3.new(0, gravity * dt, 0)
	end
	
	local function ApplyFriction(t)
		local vec = playerVelocity; -- Equivalent to: VectorCopy();
		local speed;
		local newspeed;
		local control;
		local drop;
		
		vec *= Vector3.new(1,0,1)
		speed = vec.magnitude;
		drop = 0.0;

		-- Only if the player is on the ground then apply friction */
		if(grounded) then
			control = speed < runDeacceleration and runDeacceleration or speed
			drop = control * friction * dt * t;
		end

		newspeed = speed - drop;
		playerFriction = newspeed;
		if(newspeed < 0) then
			newspeed = 0;
		end
		if(speed > 0) then
			newspeed /= speed;
		end
		playerVelocity = Vector3.new(playerVelocity.X * newspeed, playerVelocity.Y,playerVelocity.Z * newspeed)
	end
	
	local function GroundMove()
		local wishdir  = Vector3.zero

		-- Do not apply friction if the player is queueing up the next jump
		if (not wishJump) then
			ApplyFriction(1.0);
		else
			ApplyFriction(0);
		end

		SetMovementDir();
		wishdir = Vector3.new (_cmd.rightMove, 0, _cmd.forwardMove);
		--wishdir = transform.TransformDirection(wishdir);
		wishdir = wishdir.Unit;
		moveDirectionNorm = wishdir;

		local wishspeed = wishdir.Magnitude;
		wishspeed *= moveSpeed;

		Accelerate(wishdir, wishspeed, runAcceleration);
		-- Reset the gravity velocity
		playerVelocity = Vector3.new(playerVelocity.X, -gravity * dt, playerVelocity.Z)

		if (wishJump) then
			playerVelocity = Vector3.new(playerVelocity.X, jumpSpeed, playerVelocity.Z)
			wishJump = false;
		end
	end
	
	local endTime = os.clock()
	local startTime = os.clock()
	function update()
		dt = math.abs(endTime-startTime)
		QueueJump()
		if (grounded) then
			GroundMove()
		elseif (not grounded) then
			AirMove()
		end
		
		p.Character.Humanoid:Move(playerVelocity)
	end
	
	runservice.Stepped:Connect(function()
		startTime = os.clock()
		if p.Character and p.Character:FindFirstChild("Humanoid") then
			grounded = not (p.Character.Humanoid.FloorMaterial == Enum.Material.Air)
			update()
		end
		endTime = os.clock()
	end)

Adding on to this, when relativeToCamera is set to true it doesnt die and it just gets stuck at the negative 32bit integer limit

1 Like