"Dynamic" Type of Depth of Field For Your Games

I’ve taken a bit of my time to create a “dynamic”-ish focus script for the community!
I haven’t gotten very into lighting so you can change the settings if you know a bit about scripting.

Anyways onto my script.
(LocalScript In StarterCharacterScripts)

local RunService = game:GetService("RunService")
local plr = game.Players.LocalPlayer
mouse = plr:GetMouse()

--distance cap and/or Max Diameter
cap = 100
--Creating the blur effect
local DOF = Instance.new("DepthOfFieldEffect", game.Lighting)
DOF.FarIntensity = 0.222

	local OriginMath = (mouse.Origin.p - mouse.Hit.p)	 --Main math so DOF is around players center and not 0,0,0
	print(OriginMath)	   -- Remove if needed	
	local m = OriginMath.Magnitude 	--Convert to single number for DOF
	DOF.InFocusRadius = m 	--Make sure DOF is relative to mouses position
	-- Find the cap and stuff for the DOF
	if DOF.InFocusRadius > cap then
		print("alert1") -- Remove print if you don't want to kill your console
		DOF.InFocusRadius = cap
	elseif DOF.InFocusRadius < 80 then -- Good Zone
		DOF.InFocusRadius = m

If you can’t get any idea of what this does here’s a quick demo.

Based on where your mouse is the DOF diameter with expand or close in.

I hope this helps with one of your games!

(I might update sometimes)


What made you choose StarterCharacterScripts rather than StarterPlayerScripts? It doesn’t look like it has anything to do with the Character. So wouldn’t it be better to just have it created once under the Player rather than cloned every time the Character respawns?

Edit: Siiick effect though. I saved the code for later use :wink:


You could always put it there, I just put it in StarterCharacterScripts because it was where I inserted my script. : p


Hey there, which variable do i change to increase the Amount of the Dynamic Depth Field?


The Diameter or Blur?
For the Diameter that’s the cap variable, currently set to 100. Roblox maxes it out at 500.
Blur is FarIntensity which is currently 0.222.


I love the idea of this system. However, there’s a few ways on which you can improve upon this code. Firstly, GetMouse really shouldn’t be used over UserInputService and some raycasting as it’s the more modern method and from what I gather, it’s encouraged that you don’t use GetMouse() anymore (I could be wrong about that though). Additionally, there’s a few variables that aren’t localized. Furthermore, the second property of Instance.new has known performance issues and shouldn’t be used. Another issue is that you are using RenderStepped to change the Depth of Field when you honestly should be using Heartbeat for it as it’s better for performance and for what you are doing. Finally, you can use math.min or even math.clamp to clamp the focus radius instead of using that if statement. The elseif isn’t even doing anything different, so you don’t actually need that part of the code either. The result of these changes would be more organized and more optimized code.


Thanks! Ill make sure to update the code when I have the time!

Wonderful tutorial. I hope you had a amazing day and a wish you good luck!

1 Like

Thank you for making this! I learned a lot from it.

1 Like

I’ve applied this to the weapons in a testing game from mine, and the outcome looks good. If you aim the weapon (in first person) the DoF will be applied, once you stop aiming or unequip the tool, the DoF will be disabled.

For third-person cameras, this doesn’t look that good. For first person cameras, this contributes to the game’s quality! :upside_down_face:

Good contribution, thank you! Although the script is so simple, I never came on this by myself :joy:

1 Like

Of course! Glad I could help you out! :slight_smile:

1 Like

I really like this effect, and I wanted to contribute a bit to it.
I ended up using Auxintic’s Mouse Module using UIS: Custom Mouse Module

And then also used parts of microstaff’s message, however deciding because its on the Client, to use Renderstepped. Micros Post

If I did something incorrect i’d like to know.
localscript in StarterPlayerScripts:

local RunService = game:GetService("RunService")
local Lighting = game:GetService("Lighting")
local Players = game:GetService("Players")
local ReplicatedStorage = game:GetService("ReplicatedStorage")

local Player = Players.LocalPlayer

local UtilitiesStorage = ReplicatedStorage:WaitForChild("UtilitiesStorage")
local MouseModule = require(UtilitiesStorage.Modules:WaitForChild("MouseModule"))

local Mouse = MouseModule.new()

local RadiusCap = 100

local DepthOfField = Instance.new("DepthOfFieldEffect")
DepthOfField.Parent = Lighting
DepthOfField.FarIntensity = 0.222

	local RaycastResult = Mouse:CastRay()
	if RaycastResult then
		local OriginMath = (Mouse:GetOrigin() - RaycastResult.Position)	
		local Magnitude = OriginMath.Magnitude 
		DepthOfField.InFocusRadius = Magnitude 
		if DepthOfField.InFocusRadius > RadiusCap then
			DepthOfField.InFocusRadius = RadiusCap


If you are viewing this post at a later date please redirect to these superior resources below:

//Better implementations of my own

//Focus on objects in the workspace

1 Like