Загрузка данных
local Players = game:GetService("Players")
local RunService = game:GetService("RunService")
local UserInputService = game:GetService("UserInputService")
local Settings = {
FallSpeedToRagdoll = 90, -- скорость падения для рагдола (примерно 20 стадов высоты)
FallRagdollTime = 2.5, -- сколько секунд лежишь после падения
TestKey = Enum.KeyCode.X, -- тест рагдола
TestRagdollTime = 3,
}
local player = Players.LocalPlayer
local character, humanoid, root
local ragdolled = false
local created = {}
local collideBackup = {}
local fallSpeed = 0
local token = 0
local function limitsFor(name)
if name:find("Neck") then return 40, 30 end
if name:find("Knee") or name:find("Elbow") then return 15, 5 end
if name:find("Ankle") or name:find("Wrist") then return 25, 10 end
return 65, 40
end
local function startRagdoll(duration)
if ragdolled or not humanoid or not character then return end
ragdolled = true
token += 1
local myToken = token
character:SetAttribute("Ragdoll", true)
humanoid.AutoRotate = false
humanoid:ChangeState(Enum.HumanoidStateType.Physics)
for _, d in ipairs(character:GetDescendants()) do
if d:IsA("BasePart") and d ~= root and not d:FindFirstAncestorOfClass("Accessory") then
collideBackup[d] = d.CanCollide
d.CanCollide = true
end
if d:IsA("Motor6D") and d.Part0 and d.Part1 and d.Part0 ~= root then
local a0 = Instance.new("Attachment")
a0.CFrame = d.C0
a0.Parent = d.Part0
local a1 = Instance.new("Attachment")
a1.CFrame = d.C1
a1.Parent = d.Part1
local ball = Instance.new("BallSocketConstraint")
ball.Attachment0 = a0
ball.Attachment1 = a1
ball.LimitsEnabled = true
ball.TwistLimitsEnabled = true
local up, tw = limitsFor(d.Name)
ball.UpperAngle = up
ball.TwistLowerAngle = -tw
ball.TwistUpperAngle = tw
ball.Parent = d.Part0
local nc = Instance.new("NoCollisionConstraint")
nc.Part0 = d.Part0
nc.Part1 = d.Part1
nc.Parent = d.Part0
d.Enabled = false
table.insert(created, { d, a0, a1, ball, nc })
end
end
if duration then
task.delay(duration, function()
if token ~= myToken or not ragdolled then return end
if humanoid.Health <= 0 then return end
for _, set in ipairs(created) do
set[1].Enabled = true
for i = 2, 5 do set[i]:Destroy() end
end
created = {}
for part, value in pairs(collideBackup) do
if part.Parent then part.CanCollide = value end
end
collideBackup = {}
local pos = root.Position + Vector3.new(0, 3, 0)
local look = root.CFrame.LookVector
character:PivotTo(CFrame.new(pos, pos + Vector3.new(look.X, 0, look.Z)))
humanoid.AutoRotate = true
humanoid:ChangeState(Enum.HumanoidStateType.GettingUp)
ragdolled = false
character:SetAttribute("Ragdoll", false)
end)
end
end
local function setup(char)
character = char
humanoid = char:WaitForChild("Humanoid")
root = char:WaitForChild("HumanoidRootPart")
ragdolled = false
created = {}
collideBackup = {}
fallSpeed = 0
humanoid.Died:Connect(function()
startRagdoll()
end)
humanoid.StateChanged:Connect(function(_, new)
if new == Enum.HumanoidStateType.Landed then
if fallSpeed >= Settings.FallSpeedToRagdoll then
startRagdoll(Settings.FallRagdollTime)
end
fallSpeed = 0
elseif new == Enum.HumanoidStateType.Running then
fallSpeed = 0
end
end)
end
RunService.Heartbeat:Connect(function()
if not root or ragdolled then return end
local vy = root.AssemblyLinearVelocity.Y
if vy < 0 then fallSpeed = math.max(fallSpeed, -vy) end
end)
UserInputService.InputBegan:Connect(function(input, processed)
if processed then return end
if input.KeyCode == Settings.TestKey then
startRagdoll(Settings.TestRagdollTime)
end
end)
player.CharacterAdded:Connect(setup)
if player.Character then setup(player.Character) end