How would I make my pet follow system have a smooth transition from "Bobbling" to standing still when a player is moving / not moving?

I am trying to figure out how to make the pets have a smooth transition to being still to bobbling when a player moves.

RenderStepped:Connect(function(deltaTime)
		for player : Player, Pets : {Model} in pairs(PetHandler.Loaded_Pets) do
			local Character = player.Character
			if not Character then continue end
			
			local HumanoidRootPart = Character.PrimaryPart :: BasePart
			local Humanoid = Character:FindFirstChild('Humanoid') :: Humanoid

			for index, Pet : Model in pairs(Pets) do
				local PrimaryPart = Pet.PrimaryPart :: BasePart

				local angle = math.rad((index - 1) * (360 / #Pets))
				local offset = Vector3.new(math.cos(angle), 0, math.sin(angle)) * Radius

				local start_position = HumanoidRootPart.Position + offset + Vector3.new(0, HoverHeight, 0)
				local hover_offset = math.sin(os.clock() * HoverSpeed + index) * HoverAmplitude
				local target_position = if Humanoid.MoveDirection == Vector3.zero then HumanoidRootPart.Position + offset + Vector3.new(0, HoverHeight, 0) else HumanoidRootPart.Position + offset + Vector3.new(0, HoverHeight + hover_offset, 0)
				local target_cframe = CFrame.new(target_position, HumanoidRootPart.Position)
				
				PrimaryPart.CFrame = target_cframe
			end
		end
	end)

Video of the not smooth transitions:

1 Like

An idea would be to use TweenService to smoothly move the pets into the new positions when you first start/stop moving.

That’s my problem, I don’t want to use TweenService and spam a bunch of tweens. I wanna have be done with math.

But if I’d have to I’d rather just use a spring module as springs look 100x better than tweening imo

I believe that since you’re using math, can’t you just multiply it by a variable, and then tween it between 0 and 1? Either with TweenService or with equations (like var *= 0.9)

Well you can either use lerping or a spring module

1 Like

i have a pet follow system done on the client that uses math and raycasts. you can lerp the pets cframe by calculating the targetcframe using the humanoidrootparts X, Z * the rotation * x - x offset y, z + the distance from the player, where x in my case is petindexinrow - 1 * spcing, z is row index * spacing and y is HRP Y - 1.5. Then lerp that to that calculated targetcframe, 0.1, dt, * 60 per heartbeat

heres a video of the finished look

1 Like