Hi, i have been making a script for a while now that allows a player to pick up a model using E and rotate it using W, A, S, D. im using a body gyro to rotate the model but for some reason the model will jolt back and forth every couple seconds. note this only happens when i rotate it in multiple axis at the same time. Here is a link to the GIF file. https://imgur.com/a/fke4psQ . i am using a bunch of variables to determine when the player is able to rotate the part and that is fine, i have a table which its indexes are set to nil and are set to a value when input is detected. im using runService.HeartBeat when input is detected and connecting a function with the arguments as the tables indexes. i have a feeling its because of the heart beat but im not sure. (Sorry that its a lot of code. the problem is most likely in the client side)
client:
-- Wait for game to load
repeat wait() until game.Loaded
-- Remote variables
local replicatedStorage = game:GetService("ReplicatedStorage")
local remoteEvents = replicatedStorage.RemoteEvents
local remoteFunctions = replicatedStorage.RemoteFunctions
local reqGrab = remoteFunctions.RequestGrab
local stpGrab = remoteEvents.StopGrab
-- Variables
local player = game:GetService("Players").LocalPlayer
local mouse = player:GetMouse()
local Uis = game:GetService("UserInputService")
local character = player.Character or player.CharacterAdded:Wait()
local root = character:FindFirstChild("HumanoidRootPart")
local head = character:FindFirstChild("Head")
local canRequestGrab = {["grabOrDrop"] = "canGrab"}
local playerGui = player:FindFirstChild("PlayerGui")
local runService = game:GetService("RunService")
local mouseHeartBeat
local canShift = false
local isShifting = false
local bodyGyro = nil
local rotateHeartBeat = nil
local rotateTable = {
["W"] = nil,
["A"] = nil,
["S"] = nil,
["D"] = nil
}
if playerGui then
textBox = playerGui:FindFirstChild("ScreenGui").TextBox
if textBox then
end
end
local part = nil
local canGrabDebounce = false
local canDropDebounce = true
-- Make model follow mouse
function followMouse(bp, bg, primaryPart)
if bp and bg then
if (primaryPart.Position - head.Position).magnitude > 10 then
toFarAway()
end
local ray = mouse.UnitRay
--local follow = Ray.new(head.Position, ray.Direction)
--local findRay = workspace:FindPartOnRayWithWhitelist(follow, {})
bp.Position = ray.Origin + ray.Direction * 6
end
end
-- Rotating model
function rotate(rotateKeys)
if bodyGyro ~= nil then
if rotateKeys["W"] == "W" then
bodyGyro.CFrame = bodyGyro.CFrame * CFrame.Angles(math.rad(-1),0,0)
print("W")
end
if rotateKeys["A"] == "A" then
bodyGyro.CFrame = bodyGyro.CFrame * CFrame.Angles(0,math.rad(1),0)
print("A")
end
if rotateKeys["S"] == "S" then
bodyGyro.CFrame = bodyGyro.CFrame * CFrame.Angles(math.rad(1),0,0)
print("S")
end
if rotateKeys["D"] == "D" then
bodyGyro.CFrame = bodyGyro.CFrame * CFrame.Angles(0,math.rad(-1),0)
print("D")
end
end
end
--Checking for rotation key input
Uis.InputBegan:Connect(function(inputObject)
if isShifting == true then
if inputObject.KeyCode == Enum.KeyCode.W then
rotateTable["W"] = "W"
end
if inputObject.KeyCode == Enum.KeyCode.A then
rotateTable["A"] = "A"
end
if inputObject.KeyCode == Enum.KeyCode.S then
rotateTable["S"] = "S"
end
if inputObject.KeyCode == Enum.KeyCode.D then
rotateTable["D"] = "D"
end
rotateHeartBeat = runService.Heartbeat:Connect(function()
rotate(rotateTable)
end)
end
end)
-- Checking for rotation key end of input
Uis.InputEnded:Connect(function(inputObject)
if inputObject.KeyCode == Enum.KeyCode.W then
rotateTable["W"] = nil
end
if inputObject.KeyCode == Enum.KeyCode.A then
rotateTable["A"] = nil
end
if inputObject.KeyCode == Enum.KeyCode.S then
rotateTable["S"] = nil
end
if inputObject.KeyCode == Enum.KeyCode.D then
rotateTable["D"] = nil
end
end)
-- Checking for rotation conditions
Uis.InputBegan:Connect(function(inputObject)
if inputObject.KeyCode == Enum.KeyCode.LeftShift then
if canShift == true then
isShifting = true
root.Anchored = true
print("We are shifting")
end
end
end)
-- Checking if shift is unpressed
Uis.InputEnded:Connect(function(inputObject)
if inputObject.KeyCode == Enum.KeyCode.LeftShift then
isShifting = false
root.Anchored = false
print("We are not shifting")
rotateHeartBeat:Disconnect()
for i, v in pairs(rotateTable) do
v = nil
end
end
end)
-- Requesting to grab grab
Uis.InputBegan:Connect(function(inputObject)
if canGrabDebounce == false then
if inputObject.KeyCode == Enum.KeyCode.E then
if mouse.Target ~= nil then
local model = mouse.Target:FindFirstAncestorWhichIsA("Model")
if model then
local primaryPart = model:FindFirstChild("PrimaryPart")
if primaryPart then
mouse.TargetFilter = primaryPart
if mouse.Target ~= nil and mouse.Target ~= mouse.TargetFilter then
part = mouse.Target
if (part.Position - root.Position).magnitude < 8 then
local grabSuccess, bp, bg = reqGrab:InvokeServer(part)
if grabSuccess == true then
canGrabDebounce = true
bodyGyro = bg
canShift = true
mouseHeartBeat = runService.Heartbeat:Connect(function()
followMouse(bp, bg, primaryPart)
end)
textBox.Text = "Grabbed"
wait(1)
canDropDebounce = false
end
end
end
end
end
end
end
end
end)
-- If Drop
function toFarAway()
if canDropDebounce == false then
canDropDebounce = true
stpGrab:FireServer(part)
canShift = false
isShifting = false
root.Anchored = false
bodyGyro = nil
if rotateHeartBeat ~= nil then
rotateHeartBeat:Disconnect()
end
for i, v in pairs(rotateTable) do
v = nil
end
print("We are not shifting")
mouseHeartBeat:Disconnect()
part = nil
textBox.Text = "Dropped"
wait(1)
canGrabDebounce = false -- 7 can grab
end
end
-- Dectecting if "E" is pressed to drop Model
Uis.InputBegan:Connect(function(inputObject)
if inputObject.KeyCode == Enum.KeyCode.E then
toFarAway()
end
end)
Server:
-- Wait for game to load
repeat wait() until game.Loaded
-- Remote variables
local replicatedStorage = game:GetService("ReplicatedStorage")
local remoteEvents = replicatedStorage.RemoteEvents
local remoteFunctions = replicatedStorage.RemoteFunctions
local reqGrab = remoteFunctions.RequestGrab
local stpGrab = remoteEvents.StopGrab
-- Variables
local playerParts = {}
local collectionService = game:GetService("CollectionService")
local tag = "PickUp"
-- Config
function applyConfig(primaryPart)
local bp = Instance.new("BodyPosition")
local bg = Instance.new("BodyGyro")
bp.Parent = primaryPart
bg.Parent = primaryPart
bp.MaxForce = Vector3.new(10000, 10000, 1000)
bp.P = 3000
bp.D = 400
bp.Position = primaryPart.Position
bg.MaxTorque = Vector3.new(math.huge, math.huge, math.huge)
bg.CFrame = primaryPart.CFrame
return bp, bg
end
-- Grabs part
function requestGrab(player, part)
if playerParts[part] ~= nil then return false end
local model = part:FindFirstAncestorWhichIsA("Model")
if model then
if collectionService:HasTag(model, tag) then
local primaryPart = model:FindFirstChild("PrimaryPart")
if primaryPart then
local walkSpeed = primaryPart:FindFirstChild("WalkSpeed")
local character = player.Character
if character then
local humanoid = character:FindFirstChild("Humanoid")
if humanoid and walkSpeed then
humanoid.WalkSpeed = walkSpeed.Value
for i, v in pairs(model:GetChildren()) do
v:SetNetworkOwner(player)
end
playerParts[part] = player
local bp, bg = applyConfig(primaryPart)
print("Model successfully claimed!")
return true, bp, bg
end
end
end
end
end
end
-- Stops grab
function stopGrab(player, part)
if playerParts[part] ~= player then return false end
local model = part:FindFirstAncestorWhichIsA("Model")
if model then
local primaryPart = model:FindFirstChild("PrimaryPart")
if primaryPart then
local walkSpeed = primaryPart:FindFirstChild("WalkSpeed")
local character = player.Character
if character then
local humanoid = character:FindFirstChild("Humanoid")
if humanoid and walkSpeed then
humanoid.WalkSpeed = 14
for i, v in pairs (primaryPart:GetChildren()) do
if v:IsA("BodyPosition") or v:IsA("BodyGyro") then
v:Destroy()
end
end
for i, v in pairs(model:GetChildren()) do
v:SetNetworkOwnershipAuto()
end
playerParts[part] = nil
print("Model successfully unclaimed!")
end
end
end
end
end
-- Requests a grab
reqGrab.OnServerInvoke = (function(player, part)
local returnGrab, bp, bg = requestGrab(player, part)
if returnGrab == true then
return true, bp, bg
end
end)
-- Requests to stop a grab
stpGrab.OnServerEvent:Connect(function(player, part)
stopGrab(player, part)
end)
