Showing ghosts when near a torch

Someone told me that for some Luigi game, ghosts are hidden until Luigi shines a light onto the ghosts.
I want to do the same thing for my game.
I have this local script that works, but it’s my first time using RenderStepped or Heartbeat. I always avoided them thinking it’s too many iterations of the same code and it could slow things down. I don’t want to run things too much because I always want my code to be as efficient as possible.

local RunService = game:GetService("RunService")

local torch = game.Workspace:WaitForChild("Torch")
local ghosts = game.Workspace:WaitForChild("Ghosts")

local MIN_VISIBLE_DISTANCE = 30
local DISTANCE_WHEN_IT_IS_BRIGHTEST = 15
local k = MIN_VISIBLE_DISTANCE - DISTANCE_WHEN_IT_IS_BRIGHTEST

local function updateGhostVisibility()
	for _, ghost in pairs(ghosts:GetChildren()) do
		local distance = (torch.Position - ghost.Position).Magnitude
		local currentTransparency = ghost.Transparency

		if distance > MIN_VISIBLE_DISTANCE and currentTransparency < 1 then
			ghost.Transparency = 1
			return
		end

		distance -= DISTANCE_WHEN_IT_IS_BRIGHTEST

		if distance < 0 then
			ghost.Transparency = 0
		else
			ghost.Transparency = distance / k
		end
	end
end

RunService.RenderStepped:Connect(updateGhostVisibility)

This is the first script I wrote for this, eventually what will happen is this will only really be run when the player holds his torch. I’m assuming its okay and its not and issue, but I still wanted to check if anyone has anything to say. The Ghosts folder should only realistically have up to about 15 ghosts at a time (likely even less)

Is RenderStepped something I should be careful of?

Here’s a useful topic which explains Heartbeat / RenderStepped better than I could, I recommend reading it.

This might lag as it’s checking distances very frequently. Try some benchmarking tests to really make your decision though - try with as many ghosts as you can until it lags, and ask a friend with different hardware specifications to try it too.
You could also try detecting if a ghost is inside of an invisible part determining the range of the torch, which may be less laggy.

1 Like

Great, thanks
To be honest I had read that post previously, but I still don’t know “how much is too much” when putting functionality in a Heartbeat/RenderStepped

Thanks for the tips though.
I’m not sure how I’d do benchmarking tests, but I do like the idea of the invisible part determining the range of the torch. I’ll give that a try. Thanks!

P.S. After rereading it, I can see that I should have used Heartbeat instead of RunService because Heartbeat doesn’t mind as much if its a slow function

1 Like

No problem! :slight_smile:

With benchmarking tests, I imagine you’d want to determine how many ghosts is too many before lag starts, so you could make a small script that increments the amount of ghosts that are being detected by the distance-finder at once, every few seconds. Once it starts to lag, note the amount of ghosts, and that’s probably your best value for max ghosts.
It’s not entirely necessary if you aren’t planning to go higher than a certain number of ghosts at once though, as you can probably easily test that.
If you can, you should ask a friend to join and test that script too if they have significantly different hardware to you.

Best of luck! :+1:

1 Like

just use the PostSim, PreSim and PreRender instead it makes more sense

1 Like

Oh thanks
I honestly didnt know that was a thing

And judging by this comment

RunService.PreRender is the new RenderStepped
RunService.PreSimulation is the new Stepped
RunService.PostSimulation is the new Heartbeat

I guess I should then use PostSimulation if I were to not use the Invisible Part Solution provided by @cuberoot5

1 Like