Hi. I’m trying to replicate a feature from the plugin BuildV4, where a part rotates from an edge on another part to create smooth terrain:
I found this post
which helped me write this code, this is in an ArcHandle drag event, and edgePosition is the position of the edge to rotate around:
local normalEdges = getNormalEdges(hitPart, normal)
local originalCFrame = newPart.CFrame
local currentAngle = nil
local releaseAngle = 0
local dragConnection = handle.MouseDrag:Connect(function(axis, angle, radius)
local angle = math.deg(angle) - (math.deg(angle) % rotationIncrement)
angle = releaseAngle + angle
if (angle > 360) then angle -= 360 elseif (angle < -360) then angle += 360 end
local radAngle = math.rad(angle)
-- Determine edge to rotate around
local edgePosition
if (axis == Enum.Axis.Top or axis == Enum.Axis.Bottom) then
if ((0 < angle and angle < 180) or (-360 < angle and angle < -180)) then
edgePosition = normalEdges.RightEdge
else
edgePosition = normalEdges.LeftEdge
end
else
if ((0 < angle and angle < 180) or (-360 < angle and angle < -180)) then
edgePosition = normalEdges.DownEdge
else
edgePosition = normalEdges.UpEdge
end
end
-- Rotate part around edge.
local hingeOffset = CFrame.new(edgePosition - originalCFrame.Position)
local inverseHingeOffset = hingeOffset:Inverse()
local baseCFrame = originalCFrame * hingeOffset
local axis = Vector3.FromAxis(axis)
local newCFrame = baseCFrame * CFrame.Angles(axis.X * radAngle, axis.Y * radAngle, axis.Z * radAngle) * inverseHingeOffset
newPart.CFrame = newCFrame
currentAngle = angle
end)
local releaseConnection = handle.MouseButton1Up:Connect(function(axis)
releaseAngle = currentAngle
end)
This results in this behaviour.
The green points are where the edges are. As you can see, this works fine on non-rotated parts, but as soon as the original CFrame is rotated, this breaks.
Edit: After slowing down the CFrame calculations, it seems that when the original CFrame is rotated, doing originalCFrame * hingeOffset just results in a weird, offset position.
No ideas where to start on this, any help would be appreciated.