Moving Part Position while having collisions

What do you want to achieve? When moving or modifying a Part’s Position property, move the Part back up like it has collisions.

image
image

RunService.RenderStepped:Connect(function()
	local rayParams = RaycastParams.new()
	rayParams.FilterDescendantsInstances = blacklist
	rayParams.FilterType = Enum.RaycastFilterType.Blacklist
	local res = game.Workspace:Raycast(camera.CFrame.Position, camera.CFrame.LookVector * 1000, rayParams)
	
	if res then
		ball.Position = res.Position
	end
end)

:MoveTo has this functionality, but is only use-able on models. Model | Roblox Creator Documentation

:MoveTo() does not work with my example, I already used it before and it will still clip into the ground.

Like @Ocipa said, MoveTo works.

For a simple solution, add half the Y size of the moved part to the position.

For more fine-grained control you basically have to move it around until you find a position that fits.

This thread has some discussion between myself and a roblox dev about how the built-in studio draggers do it along the axis you’re moving (e.g. they’ll stop your object when they hit a wall). Not exactly what you’re looking for but could give inspiration:

2 Likes

Although this does not account for walls. Would there be a good way to detect parts of a Part?
image
Not sure how else to really word it.

Basically, what that thread I linked discussed: move it upwards until it doesn’t touch anything, then fine-tune the position with a binary search:

local TINY = 0.000199999995 -- apparently the default threshold for ArePartsTouchingOthers

local function IsTouchingAnything(part)
  return workspace:ArePartsTouchingOthers({part}, TINY)
end

local function MoveUpUntilNoCollisions(part, stepSize)
  while IsTouchingAnything(part) do
    part.Position = part.Position + Vector3.new(0, stepSize, 0)
  end
end

local function BinarySearchDown(part, stepSize)
  local top = part.Position
  while stepSize > TINY do
    stepSize = stepSize / 2
    local mid = top - Vector3.new(0, stepSize, 0)
    part.Position = mid
    if not IsTouchingAnything(part) then
      -- at the halfway point, we're not touching anything - check the bottom half next time
      top = mid
    end
  emd
end

local function PlacePartWithCollisions(part, desiredPos)
  part.Position = desiredPos
  local stepSize = part.Size.Y / 2 -- seems fine IDK maybe could be smaller
  MoveUpUntilNoCollisions(part, stepSize)
  BinarySearchDown(part, stepSize)
end

So that last function should place your part correctly. It’s not the fastest algorithm in the world but it should work fine. Unfortunately I can’t test right now because the most recent studio update broke itself.

I’m taking a guess that this is only the Y axis?

Sure, but it could be easily extended to others.

I’ll try and fiddle with it then, I may make a custom collision group to solve the MoveTo issue