Pet Movement Remote Spamming

(If I don’t respond, probably sleeping so please add in you message if its okay for me to reply in the morning)

I have asked countless Discord servers similar questions but got no proper response. My issue currently is I’m trying to make a pet system and have pets circle the player, while the player is standing still the pets will be facing the player, when the player starts to move the pets will face in the direction the player is moving. I here have a local script that is meant to be attaching the movement of a pet to a remote which will be fired from the server to the client. You may be wondering why I’m doing it on the client and not the server, that’s because I’m trying to keep the tween as smooth as possible, and using a server/regular script causes it to be buggy.

Here is the local script: (located in playergui)

--local player = game.Players.LocalPlayer


local replicatedStorage = game.ReplicatedStorage
local modules = replicatedStorage:WaitForChild("Modules")

local petData = require(modules.PetStats)


local tweenService = game:GetService("TweenService")

local tweenInfo = TweenInfo.new(
	.2,
	Enum.EasingStyle.Linear,
	Enum.EasingDirection.InOut,
	0,
	false,
	0
)

local fullCircle = 2 * math.pi
local radius = 8

local function getXAndZPositions(angle)
	local x = math.cos(angle) * radius
	local z = math.sin(angle) * radius
	return x, z
end


local remote = game.ReplicatedStorage.PetRemotes.IfYouRunThisYouSped
local rmt = game.ReplicatedStorage.PetRemotes.PetMovement
local currentAnimation

--game.ReplicatedStorage:WaitForChild("PetRemotes"):WaitForChild("PetMovement").OnClientEvent:Connect(function()
--game:GetService("RunService").Heartbeat:Connect(function(step)
local playersWhoWait = {}

rmt.OnClientEvent:Connect(function()
	print("PETMOVEMENT HAS FIRED")
	
	for _, player in pairs(game.Players:GetPlayers()) do
		if not table.find(playersWhoWait, player.Name) then
			table.insert(playersWhoWait, player.Name)
		
		task.spawn(function()
		local move
		local position
		--	local animation
		local character = player.Character
		if character then
			
		else
			return
		end
		local hrp = character:WaitForChild("HumanoidRootPart")
		local pets = character.Pets:GetChildren()
		
		local pets = character.Pets:GetChildren()
		local numberOfParts = #pets

		for i, part in pairs(pets) do
			local angle = i * (fullCircle / #pets)
			local x, z = getXAndZPositions(angle)

			local ray = Ray.new(part.PrimaryPart.Position, Vector3.new(0, -2, 0))
			local obj, position = workspace:FindPartOnRay(ray, nil, false, true)

			local lookAt

			if petData[part.Name].Flying == true then
				position = (hrp.CFrame * CFrame.new(x, 2, z)).p
				lookAt = hrp.Position
				--animation = part.Humanoid:LoadAnimation(script.PetFly)
				--	animation.Looped = true
				--animation:Play()
			else

				--animation = part.Humanoid:LoadAnimation(script.PetWalk)
				position = (hrp.CFrame * CFrame.new(x, -1.65, z)).p
				lookAt = Vector3.new(hrp.Position.X, hrp.Position.Y - 1.65, hrp.Position.Z)
			end




			if player.Character then

			else
				return
			end

			local X, Y, Z = player.Character.HumanoidRootPart.CFrame:ToOrientation()

			--part.PrimaryPart.CFrame = part.PrimaryPart.CFrame:Lerp(part.PrimaryPart.CFrame * CFrame.new(0, 0.66 * math.sin(tick()), 0), step) 

			if player.Character:WaitForChild("Humanoid").MoveDirection:FuzzyEq(Vector3.zero,.01) then
				move = tweenService:Create(part.PrimaryPart, tweenInfo, {CFrame = CFrame.new(position, lookAt)})
				remote:FireServer(part.Walking, false)
				
			else
				move = tweenService:Create(part.PrimaryPart, tweenInfo, {CFrame = CFrame.new(position) * CFrame.Angles(X, Y, Z)--[[, Orientation = player.Character.LowerTorso.CFrame.lookVector]]})
				remote:FireServer(part.Walking, true)
			end
				
			task.wait(0.1)

			if move then
				move:Play()
				move.Completed:Wait()
			end
				end
				
				task.wait(0.1)
				table.remove(playersWhoWait, table.find(playersWhoWait, player.Name))
			end)
			
			
		end
	end
end)

then I have a server script that is meant to make this pet movement function and such, I will paste some variables and a snippet of the entire script which is using that remote set by a local script. If you think you need to see the entire script I can send it, though it is quite long.

Server/Regular script in serverscriptservice:

local character = player.Character
	local rmt = game.ReplicatedStorage.PetRemotes.PetMovement
	game:GetService("RunService").Heartbeat:Connect(function()
		rmt:FireClient(player)
		task.wait(0.075)
	end)

and here is one more script which is what the “IfYouRunThisYouSped” remote in the previous local script I sent has attached to it:

local remotes = game.ReplicatedStorage:WaitForChild("PetRemotes")

local tab = {}
local cooldown = 1.25

remotes.IfYouRunThisYouSped.OnServerEvent:Connect(function(player, obj, val)
	print("RUNSPED HAS BEEN FIRED")
	if not tab[player.UserId] then
		tab[player.UserId] = true
	if obj.Name ~= "Walking" then
		player:Kick("why you ran this bro u sped and banned lolll")
	else
		obj.Value = val
		end
		task.wait(cooldown)
		tab[player.UserId] = nil
	end
end)

which is also a server script in serverscriptservice.

My goal and issue (summary): The PetMovement script (/remote) Is firing over 1000 times a second and is causing the game to lag terribly, how can I prevent this without ruining how the pet tweens would act? If I would need to change my movement script to a server script, how would I keep the tweening movement smooth and not buggy?

Sorry if something isn’t explained well, it was a lot and I lost track lol

You could just completely change movement to the client instead of firing a remote.

I do recall trying that, looping through all the players and tweening them all accordingly for each player’s client (not sure if that’s the best way to do it) but for some reason, I remember it not working. I’ll have to try this again tomorrow just in case, if it works ill mark that as the solution - if not ill reply to this message. Thank you

I have tried this, though I get tons of warnings in output about an animation load limit and I’m not sure how I can play an animation already loaded into a humanoid:

--local player = game.Players.LocalPlayer


local replicatedStorage = game.ReplicatedStorage
local modules = replicatedStorage:WaitForChild("Modules")

local petData = require(modules.PetStats)


local tweenService = game:GetService("TweenService")

local tweenInfo = TweenInfo.new(
	.2,
	Enum.EasingStyle.Linear,
	Enum.EasingDirection.InOut,
	0,
	false,
	0
)

local fullCircle = 2 * math.pi
local radius = 8

local function getXAndZPositions(angle)
	local x = math.cos(angle) * radius
	local z = math.sin(angle) * radius
	return x, z
end


local remote = game.ReplicatedStorage.PetRemotes.IfYouRunThisYouSped
local rmt = game.ReplicatedStorage.PetRemotes.PetMovement
local currentAnimation

--game.ReplicatedStorage:WaitForChild("PetRemotes"):WaitForChild("PetMovement").OnClientEvent:Connect(function()
--game:GetService("RunService").Heartbeat:Connect(function(step)
local playersWhoWait = {}

local petfly = script.PetFly
local petwalk = script.PetWalk

local loadedPets = {}

while task.wait(0.05) do
	print("PETMOVEMENT HAS FIRED")
	
	for _, player in pairs(game.Players:GetPlayers()) do
		
		
		task.spawn(function()
		local move
		local position
		--	local animation
		local character = player.Character
		if character then
			
		else
			return
		end
		local hrp = character:WaitForChild("HumanoidRootPart")
		local pets = character.Pets:GetChildren()
		
		local pets = character.Pets:GetChildren()
		local numberOfParts = #pets

			for i, part in pairs(pets) do
				local loadedAnim
			local angle = i * (fullCircle / #pets)
			local x, z = getXAndZPositions(angle)

			local ray = Ray.new(part.PrimaryPart.Position, Vector3.new(0, -2, 0))
			local obj, position = workspace:FindPartOnRay(ray, nil, false, true)

				local lookAt
				
				
				if not table.find(loadedPets, part) then
					if petData[part.Name].Flying == false then
						loadedAnim = part:WaitForChild("Humanoid"):LoadAnimation(petwalk)
						----print("loaded false")
					else
						loadedAnim = part:WaitForChild("Humanoid"):LoadAnimation(petfly)
						loadedAnim:Play()
						--print("loaded true")
					end
				end
				
				table.insert(loadedPets,  part)

			if petData[part.Name].Flying == true then
				position = (hrp.CFrame * CFrame.new(x, 2, z)).p
				lookAt = hrp.Position
				--animation = part.Humanoid:LoadAnimation(script.PetFly)
				--	animation.Looped = true
				--animation:Play()
			else

				--animation = part.Humanoid:LoadAnimation(script.PetWalk)
				position = (hrp.CFrame * CFrame.new(x, -1.65, z)).p
				lookAt = Vector3.new(hrp.Position.X, hrp.Position.Y - 1.65, hrp.Position.Z)
			end




			if player.Character then

			else
				return
			end

			local X, Y, Z = player.Character.HumanoidRootPart.CFrame:ToOrientation()

			--part.PrimaryPart.CFrame = part.PrimaryPart.CFrame:Lerp(part.PrimaryPart.CFrame * CFrame.new(0, 0.66 * math.sin(tick()), 0), step) 

			if player.Character:WaitForChild("Humanoid").MoveDirection:FuzzyEq(Vector3.zero,.01) then
					move = tweenService:Create(part.PrimaryPart, tweenInfo, {CFrame = CFrame.new(position, lookAt)})
					
					if petData[part.Name].Flying == false then
						loadedAnim:Stop()
					else
						loadedAnim:Play()
					end
				
			else
				move = tweenService:Create(part.PrimaryPart, tweenInfo, {CFrame = CFrame.new(position) * CFrame.Angles(X, Y, Z)--[[, Orientation = player.Character.LowerTorso.CFrame.lookVector]]})
					loadedAnim:Play()
			end
				
			task.wait(0.1)

			if move then
				move:Play()
			--	move.Completed:Wait()
			end
				end
				
			
			end)
	end
end

this is what my local script has turned into, no more of any other script.

this is my exact error:

AnimationTrack limit of 256 tracks for one Animator exceeded, new animations will not be played. (x24)

Only load the animations one time per pet, save in in an array. And play it through the array.

local Animations = {}

local Humanoid = part:WaitForChild("Humanoid")
Animations[Humanoid] = Humanoid:WaitForChild("Animator"):LoadAnimation(petfly)

Then play it with this command

Animations[Humanoid]:Play()

The animations are working better now thank you, bit fast but I can fix that myself. I now see through that client memory usage is at 1.7K+ and any events that were made locally aren’t working, I disabled the pet movement and such and it doesn’t reduce it by really anything just goes down to 1.68K. I see the main use is scripts, is it just loops in specific that really make memory go up or is there something else I should be checking for? Might just hire someone to fix this if it gets worse though