Raycast is bugged returning to nil unexpectedly

I’ll try my best to keep this simple and short, but I am planning on making something called SCP-173, which is an entity that can’t move within a direct line of sight. It will try to get close to humans close enough to snap their neck.

So, I found a 2013 weeping angel model, edited it up a bit to not use deprecated stuff. I used raycast.
I got it working. I coded it to turn green when it’s being looked at, but turn red when it’s not being looked out.
Link to the 2013 model if you’re curious

So the next day, I tried to improve it more to create SCP-173, but for some reason, the base model I created didn’t do as intended. Looking at it didn’t turn it green for some reason.
When I walk very close to it, it turns green, otherwise it turns red. I’m not sure what happened since I didn’t modify any code. I coded in print() and warn() into it to find out why it wasn’t working. the warn() said that the raycast was nil.

MODIFIEDBASE CODE:

local Character = script.Parent
local Humanoid = Character:FindFirstChildOfClass("Humanoid")

function canSee(subject, viewer)
	if (not subject) or (not viewer) then
		return
	end
	--SUBJECT IS THE SCRIPT.PARENT
	--THE CHAR IS THE PLAYER!!!!

	local subjectchar = subject:FindFirstChild("CharacterAreaBox")
	local plrhead = viewer:FindFirstChild("Head")

	if (not subjectchar) or (not plrhead) then
		return
	end
	
	if not subjectchar:IsA("BasePart") or not plrhead:IsA("BasePart") then
		return
	end

	local Distance = subjectchar.Position - plrhead.Position
	--local isInViewerFOV = (Distance:Dot(plrhead.CFrame.LookVector) > 0)
	local isInViewerFOV = (Distance:Dot(plrhead.CFrame.LookVector))
	warn("DOT: ".. Distance:Dot(plrhead.CFrame.LookVector))
	warn("DOT STATEMENT: "..tostring(isInViewerFOV))
	--This variable will check if they're facing each other.
	
	if isInViewerFOV > 0 then
		local GLASSLIST = {}
		for i, v in pairs(workspace:GetDescendants()) do
			--makes sure raycast goes through parts or something that have a transparency above 0
			if not v or not v.Parent then
				continue
			end
			local vparent = v.Parent
			if v:IsA("BasePart") then
				if v.Transparency > 0.02 or v.Material == Enum.Material.ForceField then
					if not plrhead or not subjectchar then
						table.insert(GLASSLIST, v)
					end
				end
			end
			if vparent:IsA("Accessory") or vparent:IsA("Tool") or vparent:IsA("Hat") then
				if not plrhead or not subjectchar then
					table.insert(GLASSLIST, v)
				end
			end
		end
		
		local PARAMS = RaycastParams.new()
		PARAMS.FilterType = Enum.RaycastFilterType.Exclude
		PARAMS.FilterDescendantsInstances = GLASSLIST
		if plrhead then
			local raycast = workspace:Raycast(subjectchar.Position, plrhead.Position, PARAMS)
			if not raycast then
				warn("OK SO THE raycast VARIABLE IS NIL!")
				return
			end
			warn("RAYCAST INSTANCE HIT: " ..tostring(raycast.Instance))
			return (raycast.Instance)
		else
			print("PLRHEAD IS NIL!!!!")
		end
	else
		return
		--return
	end
end

while true do
	for i, v in pairs(workspace:GetChildren()) do
		local char
		local player
		local humanoid
		local head
		if v:IsA("Model") then
			if v:FindFirstChildOfClass("Humanoid") then
				char = v
				player = game:GetService("Players"):GetPlayerFromCharacter(char)
				humanoid = char:FindFirstChildOfClass("Humanoid")
				head = char:FindFirstChild("Head")
			end
		end
		
		if humanoid then
			local WALKING_L = canSee(Character, char)
			print("CanSee Function Result: ".. tostring(WALKING_L))
			if WALKING_L then
				--Player is looking at SCP-173.
				script.Parent.BrickColor = BrickColor.new("Lime green")
			else
				--Player is not looking at SCP-173.
				script.Parent.BrickColor = BrickColor.new("Really red")
			end
		end
	end
	
	task.wait()
end

I’m starting to think the raycast returning nil is because Roblox raycast bugged out.

I found a work-around, however, I felt like it will eventually bug out soon.
Secondly I don’t think it’s an ethical way.
What I did was change the else function inside of the canSee() function to return “doesnt work” which resulted in it turning red when it’s observed, but green if not observed. I do not think it’s an ethical way because if raycast ever randomly fixes, it will probably bug out.

Also, yes, I have searched a bit of the dev forum for bug fixes, but so far I couldn’t find solutions.

NOTE: Before it broke, my avatar had accessories and it worked perfectly fine, so I don’t think avatar accessories hinder it. I never changed my avatar while I was developing.

I’m thinking that this is just a roblox raycast problem since it suddenly broke without modifications. Help is appreciated!

For raycasting, you don’t use destination. You typically use direction, which might be the reason why it is nil. To calculate direction, use this simple equation (from the Roblox Documentary): Destination - Origin = Direction.

Yes using destination.position - origin.position is how you can get the direction but also keep in mind that sometimes you can get ray = nil when the ray doesn’t hit anything so make sure you use if ray so you don’t get errors if the ray doesn’t hit anything

Thanks! BTW I forgot to mention in the post that I’m new to RayCasting. I modified the code and it finally works!

1 Like

This topic was automatically closed 14 days after the last reply. New replies are no longer allowed.