Why did my model float if it get ragdoll while jumping?

First time making my own ragdoll module following a tutorial on youtube. it working fine on normal scenario but when a model get ragdoll while airbone the PlatformStand boolean will not get toggle like normal, why is that?

The Modulescript

local ragdoll = {}

local RagdollData = require(script.OffsetData)

local players = game:GetService("Players")
local RagdollEvent = game:GetService("ReplicatedStorage").RemoteEvents.Ragdoll

function ragdoll:BuildCollisionPart(char : Model)
	for i,part in pairs(char:GetChildren()) do
		if part:IsA("BasePart") and part.Name ~= "HumanoidRootPart" then
			local new = part:Clone()
			new.Parent = part
			new.CanCollide = false
			new.Massless = true
			new.Size = Vector3.one
			new.Name = "Collider"
			new.Transparency = 1
			new:ClearAllChildren()
			new.Shape = Enum.PartType.Block
			
			local weld = Instance.new("Weld",new)
			weld.Part0 = part
			weld.Part1 = new
			weld.C0 = CFrame.new(0,0,0)*CFrame.Angles(0,0,math.rad(90))
		end
	end
end

function ragdoll:SetupHumanoid(hum : Humanoid)
	hum.BreakJointsOnDeath = false
	hum.RequiresNeck = false
end

function ragdoll:Init()	
	players.PlayerAdded:Connect(function(plr)
		plr.CharacterAdded:Connect(function(char)
			local hum = char:WaitForChild("Humanoid")
			ragdoll:SetupHumanoid(hum)
			ragdoll:BuildCollisionPart(char)
		end)
	end)
	
	local npcFolder = workspace.NPC
	if npcFolder then
		for i,npc in pairs(npcFolder:GetChildren()) do
			if npc then
				if npc:IsA("Model") then
					local hum = npc:WaitForChild("Humanoid")
					ragdoll:SetupHumanoid(hum)
					ragdoll:BuildCollisionPart(npc)
				end
			end
		end
	end
	
	workspace.NPC.ChildAdded:Connect(function(child)
		if child:IsA("Model") then
			local hum = child:WaitForChild("Humanoid")
			ragdoll:SetupHumanoid(hum)
			ragdoll:BuildCollisionPart(child)
		end
	end)
end

function ragdoll:EnableM6D(char : Model, Toggle : boolean)
	for _,v in pairs(char:GetDescendants()) do
		if v.Name == "Handle" or v.Name == "RootJoint" or v.Name == "Neck" or v.Name == "SyringM6D" then continue end
		if v:IsA("Motor6D") then v.Enabled = Toggle end
	end
end

function ragdoll:BuildBallsocketJoint(char : Model)
	local root = char:WaitForChild("HumanoidRootPart")
	
	for _,v in pairs(char:GetDescendants()) do
		if not v:IsA("BasePart") or v:FindFirstAncestorOfClass("Accessory") or v.Name == "Torso" or v == root then continue end
		
		if not RagdollData[v.Name] then continue end
		
		local att0, att1 = Instance.new("Attachment",v), Instance.new("Attachment",root)
		local joint = Instance.new("BallSocketConstraint",v)
		
		att0.Name,att1.Name = "Ragdoll_Att","Ragdoll_Att"
		att0.CFrame,att1.CFrame = RagdollData[v.Name].CFrame[2],RagdollData[v.Name].CFrame[1]
		
		joint.Name = "Ragdoll_Constraint"
		joint.Attachment0,joint.Attachment1 = att0,att1
		
		v.Massless = true
	end
end

function ragdoll:DestroyBallsocketJoint(char : Model)
	for _,v in pairs(char:GetDescendants()) do
		if v.Name == "Ragdoll_Att" or v.Name == "Ragdoll_Constraint" then v:Destroy() end
		
		if not v:IsA("BasePart") or v:FindFirstAncestorOfClass("Accessory") or v.Name == "Torso" or v.Name == "Head" then continue end
	end

end
function ragdoll:EnableCollision(char : Model, Toggle : boolean)
	for _,v in pairs(char:GetChildren()) do
		if v:IsA("BasePart") and v.Name ~= "HumanoidRootPart" then
			v.CanCollide = not Toggle
			v.Collider.CanCollide = Toggle
		end
	end
end

function ragdoll:UnRagdollCharacter(char : Model)
	local plr = players:GetPlayerFromCharacter(char)
	local hum = char:WaitForChild("Humanoid")
	local root = char:WaitForChild("HumanoidRootPart")
	
	if plr then
		RagdollEvent:FireClient(plr, false)
	else
		root:SetNetworkOwner(nil)
		if hum:GetState() == Enum.HumanoidStateType.Dead then return end
		hum.PlatformStand = false
		hum:SetStateEnabled(Enum.HumanoidStateType.FallingDown, false)
		hum:ChangeState(Enum.HumanoidStateType.GettingUp)
	end
	
	ragdoll:DestroyBallsocketJoint(char)
	ragdoll:EnableM6D(char, true)
	ragdoll:EnableCollision(char, false)
	
	hum.AutoRotate = true
end

function ragdoll:RagdollCharacter(char : Model, Duration : number)
	local plr = players:GetPlayerFromCharacter(char)
	local hum = char:WaitForChild("Humanoid")
	local root = char:WaitForChild("HumanoidRootPart")
	if not root then return end
	
	ragdoll:EnableM6D(char, false)
	ragdoll:BuildBallsocketJoint(char)
	ragdoll:EnableCollision(char, true)
	
	if plr then
		RagdollEvent:FireClient(plr, true)
	else
		root:SetNetworkOwner(nil)
		hum.PlatformStand = true
		hum.AutoRotate = false
	end
	
	if not Duration then return end
	task.delay(Duration, function()
		ragdoll:UnRagdollCharacter(char)
	end)
end

return ragdoll

The Video

2 Likes

First of all: don’t use methods when you never use self.

Set EvaluateStateMachine to false and disconnect character from player when it is ragdolled, this way removing all controll you have over dead character.

basically:

function ragdoll:RagdollCharacter(char : Model, Duration : number)
	local plr = players:GetPlayerFromCharacter(char)::Player
	plr.Character=nil
	local hum = char:WaitForChild("Humanoid")::Humanoid
	local root = char:WaitForChild("HumanoidRootPart")::BasePart
	if not root then return end

	ragdoll:EnableM6D(char, false)
	ragdoll:BuildBallsocketJoint(char)
	ragdoll:EnableCollision(char, true)

	if plr then
		RagdollEvent:FireClient(plr, true)
	else
		root:SetNetworkOwner(nil)
		hum.PlatformStand = true
		hum.AutoRotate = false
	end

	if not Duration then return end
	task.delay(Duration, ragdoll.UnRagdollCharacter,ragdoll,char)
end
2 Likes
  1. Is there a downside to using Method instead of dot to make a function
  2. the player character is not dead. their health has been set to 0.01 and set into “Down” state
    from my testing I find setting humanoid’s jumpheight to 0 to be a solution of my original problem but I don’t want to modify the number directly and SetStateEnable doesn’t prevent it since it happen only if player still holding jump button. Is there another alternate solution I haven’t mentioned? if not then it is fine I’ll mark the reply as solution if you only answer my first question

Yes

It generates proto (function) that expects the 1st argument as “self” and calling function through : forces bytecode to make namecall setup.

You are also better off just caching a reference to a function like

local module = require(...path stuff)
local ragdoll = module.ragdoll

Well, the best you can do is to make the player unable to interact with the character’s humanoid by disconnecting it from the player.

1 Like

This topic was automatically closed 14 days after the last reply. New replies are no longer allowed.