I am trying to make a mouse based placement system, and everything seems to be all good and well, except that due to how the location of a part is techinically the midpoint of a part, the part would clip into whatever the mouse is pointing at. Now, I managed to solve this by offsetting the part by the difference between the lowest and highest point (or furthest and closest if X or Z axis), however, everything breaks once the mouse.Target is also rotated.
When mouse.Target has the regular rotation:
Perfeclty well, right?
when mouse.Target is rotated:
yep, the block wont go there, why? because the if statement doesn’t think thats the X side, as techinically, it isn’t, its the Z side of the block, but its facing the X direction…
(The 2 parts in the 2 previous photos look almost identical, except one has been rotated and rescaled.)
Now, I have tried to solve this problem by finding the furthest/closest point on the target part, but that introduces a problem that I cant think of a way to solve: what if the part wasn’t rotated at a 90 degrees angle? if not, the if statement would assume you arn’t on the correct location since the mouse isn’t pointing at the closest/furthest location of the part.
Part of the code responsible for finding the location of the part
place = run.RenderStepped:Connect(function()
if mouse.Target then
if mouse.Hit.Y >= mouse.Target.Position.Y + mouse.Target.Size.Y/2 then
dum.CFrame = CFrame.new(mouse.Hit.Position.X, mouse.Target.Position.Y + mouse.Target.Size.Y/2 + dum.Position.Y - computePoint(dum, "Y").Y, mouse.Hit.Position.Z) * CFrame.Angles(math.rad(rot["r"]), math.rad(rot["t"]), math.rad(rot["y"]))
elseif mouse.Hit.Y <= mouse.Target.Position.Y - mouse.Target.Size.Y/2 then
dum.CFrame = CFrame.new(mouse.Hit.Position.X, mouse.Target.Position.Y - mouse.Target.Size.Y/2 - dum.Position.Y + computePoint(dum, "Y").Y, mouse.Hit.Position.Z) * CFrame.Angles(math.rad(rot["r"]), math.rad(rot["t"]), math.rad(rot["y"]))
elseif mouse.Hit.X >= mouse.Target.Position.X + mouse.Target.Size.X/2 then
dum.CFrame = CFrame.new(mouse.Target.Position.X + mouse.Target.Size.X/2 + dum.Position.X - computePoint(dum, "X").X, mouse.Hit.Position.Y, mouse.Hit.Position.Z) * CFrame.Angles(math.rad(rot["r"]), math.rad(rot["t"]), math.rad(rot["y"]))
end
end
end)
here is computePoint (yoinked from some other post)
local function getDir(v, s)
if s == "X" then
return (
((v.X == 0) and Vector3.new()) or -- flat
((v.X > 0) and -v) or -- flip
v -- perfect
)
elseif s == "Y" then
return (
((v.Y == 0) and Vector3.new()) or -- flat
((v.Y > 0) and -v) or -- flip
v -- perfect
)
else
return (
((v.Z == 0) and Vector3.new()) or -- flat
((v.Z > 0) and -v) or -- flip
v -- perfect
)
end
end
local function computePoint(part, s)
local cf = part.CFrame
local dist = part.Size/2
local xVec = getDir(cf.RightVector, s) * dist.X
local yVec = getDir(cf.UpVector, s) * dist.Y
local zVec = getDir(cf.LookVector, s) * dist.Z
return (cf + xVec + yVec + zVec).p
end
To simplify the question: How to find where the location of a part should be if it shouldn’t be intersecting with the mouse.Target but still based there, while not relying on what side of the part it is on?
If any other information (such as the code used in an attempt to calculate the side of the mouse.Target correctly) is needed, just tell me
Maybe for easier visualization, here are some pictures of a succesful implementation of this: (from BABFT)
What I have (or atleast theoretically can do)
What I cant think of a way to do (literally absolutely no idea at all)
(The wall doesnt have a rotation of 90, 180, 270, or 360 degrees)