New Part Collision Property: CanQuery - Now Available!

The server in general should never trust what the client does or says and game critical code (i.e anything that can affect other players) should never be run on the client if possible or at the very least be validated on the server.

3 Likes

This is a super cool update, but I’m not sure why CanQuery requires CanCollide to be off?
I know this is a rather unusual usecase, but a while back, I tried developing an isometric deathmatch game, but I ran into a problem where invisible walls (primarily used to keep players inside of indoor spaces without obscuring vision) would still be hit by raycasts from weapons, causing players to shoot towards the camera instead of towards their target. It would be very useful to be able to disable spatial query methods while still retaining player collision.

11 Likes

Have you tried creating an ignore list when raycasting?

https://developer.roblox.com/en-us/api-reference/function/WorldRoot/Raycast

3 Likes

Pretty cool update. Very useful for raycast.

1 Like

I believe it saves on loading times, since all the collision data the client needs to download for that mesh is a simple box

1 Like

I agree with this reply.

Currently I have a Coin Generator that covers a map, currently it’s too hard to determine which Part is a floor, and which is a roof. It would be very beneficial for me and builders to disable CanQuery without disabling CanCollide because obviously I don’t want players jumping out of / falling into buildings through the roof.

I also want / need RayCast to ignore my invisible map barricades.

Limiting our ability to use this new property by tying it to a different one is bad design, CanQuery is less usable in it’s current state.

Have you tried it before because It’s a pain to use and I wouldn’t recommend it to anyone.

Especially for @fighterbuilder’s use case. They have to constantly add new BaseParts into workspace which the IgnoreList you suggested doesn’t update (Immutable) and will cause problems and complications. By simply allowing us to use CanQuery without any restrictions would be a lot easier and starter friendly.


Here’s the hacky code I have to use to get achieve what I want for my game

local WorldRootIgnoreLists = {}

local function getIgnoredPartsForWorldRoot(worldroot: WorldRoot)
	if not WorldRootIgnoreLists[worldroot] then
		local IgnoredParts = {}
		for _, descendant: Instance in ipairs(worldroot:GetDescendants()) do
			if descendant:IsA("BasePart") then
				local BasePart: BasePart = descendant
				if not BasePart.CanCollide or BasePart.Transparency == 1 then
					if not CollectionService:HasTag(BasePart, "Raycast_WHITELIST") then
						table.insert(IgnoredParts, BasePart)
					end
				end
			end
		end
		WorldRootIgnoreLists[worldroot] = IgnoredParts
	end
	return WorldRootIgnoreLists[worldroot]
end
local function handleIgnoredPartsForWorldRoot(worldroot: WorldRoot)
	if not WorldRootIgnoreLists[worldroot] then
		local IgnoredParts = {}

		for _, descendant: Instance in ipairs(worldroot:GetDescendants()) do
			if descendant:IsA("BasePart") then
				local BasePart: BasePart = descendant
				if not BasePart.CanCollide or BasePart.Transparency == 1 then
					if not CollectionService:HasTag(BasePart, "Raycast_WHITELIST") then
						table.insert(IgnoredParts, BasePart)
					end
				end
			end
		end

		worldroot.DescendantAdded:Connect(function(AddedDescendant: Instance)
			if AddedDescendant:IsA("BasePart") then
				local BasePart: BasePart = AddedDescendant
				if not BasePart.CanCollide or BasePart.Transparency == 1 then
					if not CollectionService:HasTag(BasePart, "Raycast_WHITELIST") then
						table.insert(IgnoredParts, BasePart)
					end
				end
			end
		end)

		worldroot.DescendantRemoving:Connect(function(RemovedDescendant: Instance)
			if RemovedDescendant:IsA("BasePart") then
				local BasePart: BasePart = RemovedDescendant
				table.remove(IgnoredParts, table.find(IgnoredParts, BasePart))
			end
		end)

		WorldRootIgnoreLists[worldroot] = IgnoredParts
	end
end
function raycastUtil.Raycast(worldroot: WorldRoot, Origin: Vector3, Direction: Vector3): RaycastResult?
	raycastParams.FilterDescendantsInstances = getIgnoredPartsForWorldRoot(worldroot)
	return worldroot:Raycast(Origin, Direction, raycastParams)
end
5 Likes

Hey @kleptonaut, I am unsure on whether this is a recent issue, but I have noticed raycasts being inacurate for my game; they intersect with objects they should otherwise be unable to.
I am unsure on whether you are apart of the Bug-Support group, but I have sent a PM to them elaborating on the issue: https://devforum.roblox.com/t/raycasts-are-inaccurate-intersecting-objects-they-should-be-unable-to/1453850

1 Like

@fighterbuilder @RuizuKun_Dev
I think collision groups would be a better solution for your use cases.

The problem is player collisions use raycasts to detect the floor, so you wouldn’t be able to do this even if you could toggle them independently. Simply relying on collision groups instead feels like the better option.

3 Likes

This is overall a great update, but can we please stop messing with the order of properties? It was messed up for a couple months and then it was finally restored to it’s previous state. If this is a permanent change, I feel it’s necessary to have the legacy order as an option.

I also don’t agree with CanQuery not being enabled on parts that have collision turned on. It kinda nullifies the property becuase as @kleptonaut said, you can use a CollisionGroup for that usecase.

I feel like the Humanoid raycast should be revamped to account for parts that have CanQuery enabled, such that it overrides it, and instead only checks for CanCollide and Collision groups instead. It seems strange that a property designed for raycasts also applies to humanoids because they use raycast under the hood (which is unexpected behavior to a new developer!)

2 Likes

Looks like this this bug still exists, and the only way to get around it is to have TC disabled on your place at the moment, not sure if @kleptonaut has seen this bug report. When I first discovered this bug I disabled CanQuery on over 100+ parts (allowing guns to shoot though doors without adding to the raycast blacklist)., then came back the next day and found it enabled again, I reproduced this several times and found that the CanQuery option doesn’t save in TC

As a beta feature, you can only use CanQuery in a solo studio session. Once out of beta, it should work fine in TC and in your published games.

4 Likes

Now that you guys are adding CanQuery, do you guys have any plans with studio to add a shortcut or use the Alt key for the selector that will allow you to ignore a part and select the part behind it? Just like how you can select parts inside a model while ignoring the model.

For example; If I created a bounding box around a model that was invisible and I wanted to select the parts behind that bounding box without having to set the bounding box CanCollide false and CanQuery false and reenable it again.

It would be easier than having to constantly set those properties for every object I quickly want to select parts behind other parts in studio

1 Like

Yea, I recommend posting this as a feature request, as well as other selection/dragger ideas.

To be clear, the selector doesn’t need CanQuery to add this behavior. And CanQuery isn’t really intended to add functionality for studio editing, rather to be used in game as an additional collision filtering option. I agree you shouldn’t need to be toggling it on and off for parts while editing.

Oh ok, I did not know beta features only works in solo studio sessions, thank you for the information.

Oooooo, Thats pretty nice guys. Kepp up this good work Roblox staff team ;D

I’m noticing that every time I re-open studio, all my parts where I set CanQuery to false reset back to true. Is this a known bug? I haven’t seen it reported here.

2 Likes

Have you tried opening any of the new Studio builds recently? This happened to me when I was switching back and forth from the regular Studio build and into the new materials build.

THANK GOD!! AND THE DEVS OFCOURSEEE!!!

Ive hated seeing my poor gun bullets stop to Hitboxes and Such, and this will finally allow me to improve shooting from cars and such, maybe even shooting through walls, VERY GOOD

Nope, strictly in the regular studio build.

Quick question, if I have CanQuery and CanCollide enabled, is there any benefit by disabling CanTouch? Or does it not matter?