Scripting HelpersARCHIVE
A little piece of Roblox history. Preserved for everyone, one question at a time.Read about the archive →
COMMUNITY QUESTION

Alternative methods for achieving collision detection? [SOLVED!!!! by myself :P]

Basically there are a few methods of getting collisions, the current ones I know of are .Touched, :GetTouchingParts(), raycasting....

Now suppose I were to make a fighting game which includes loads of magic and I had a part flying to a player, I would have to loop the raycasting to detect if it was in the players range or I would have to loop :GetTouchingParts, for this reason I would use .Touched, that's assuming I use body movers and the player's character isn't a custom character that is fully anchored.

However, in this scenario, if the character was just a block and not really a character with certain inputs, .Touched wouldn't work because the part is anchored and the part that was suppose to touch the player would return whatever isn't anchored

Now in the scenario above I could use GetTouchingParts or raycasting but that would cause excessive lag from being looped for low end devices.

Thus, is there any alternative to getting collision detection?

I also use this: Trick for GetTouchingParts to work with non-cancollide parts.

Currently the only way I could help reduce lag for low end devices is by using GetPropertyChangedSignal for positions but even then, that might not do much good since the positions will change pretty fast.

Tl;dr: Basically what I want is for there to be a .Touched that returns all the parts it touches regardless of its properties for efficiency. Is there a method for such a thing / a hacky trick that could be used just like in the link I posted above

Thanks for any help.

Example of .Touched not working when 2 anchored parts collide:

workspace.P1.Touched:Connect(function(h)
	print(h,' touched me.')
end)

if P1 is anchored and P2 is also anchored then I won't be able to use .Touched because touched runs only when an anchored and an unanchored part runs / 2 unanchored parts.

Example of GetTouchingParts causing lag:

while true do wait()
	for _, v in pairs(workspace.P1:GetTouchingParts()) do -- when the bullet / object goes through a wall there will be a bit of lag..
		print(v.Name)
	end
end

There has to be a much more efficient way of doing this. Regardless of the properties.

6 comments

1

Uh Region3?

0

I never really learned that but I believe I would have to loop through region3 too. Unless you can provide me with a method that doesn't require looping.

0

Connect touched event on client. You will get immediate feedback regardless of lag. I it will however require robust server sided anti hack script and even then, due to lag possibility, it will be impossible to detect some hacks while avoiding false positives. That is an unfortunate trade off.

0

I use touched and it works even with anchored parts. I'm not sure I understand in which scenario it doesn't work for you. Can you show us an example and show your script. I'd love to help.

0

I'll edit the description.

0

They work but on low end devices having 20 different anchored projectiles at once is pretty hard to handle

1 answer

So I uh, kinda solved this on my own. This might not be as efficient but it does the job and I made it pretty good.

local GetTouched = {}
local function GetTouchingParts(part,func)
	print('checked')
	local connection = part.Touched:Connect(function() end)
	local results = part:GetTouchingParts()
	connection:Disconnect()
	return results
end
local TouchedList = {}
TouchedList.__index = TouchedList
function GetTouched.new(part,func)
	print('set')
	local returned = setmetatable(GetTouched,TouchedList)
	part:GetPropertyChangedSignal("Position"):Connect(function()
		if #GetTouchingParts(part) == 0 then else
			returned = GetTouchingParts(part)
			TouchedList[part] = returned
		end
	end)
	part:GetPropertyChangedSignal("Size"):Connect(function()
		if #GetTouchingParts(part) == 0 then else
			returned = GetTouchingParts(part)
			TouchedList[part] = returned
		end
	end)
	local meta = setmetatable(TouchedList,{
		__index = GetTouched,
		__newindex = function(a,b,c)
			func()
		end
	})
end

GetTouched.new(script.Parent, function()
	print('hello')
end)

Basically, once the function runs, it checks for anything that touches script.Parent and when found, it runs the function in the __newindex method. (Rather than looping which shows how efficient this is)

This discussion is preserved as it was. New answers, comments, and votes are closed.