# CFrame math gone wrong

I want to lerp a part with an attachment, so the attachment stays relative to its original position
But when shrinking the size of the part for long enough, the attachment behaves erratically, and eventually goes off to infinity.
Why is this?

To recreate this, just have a part with an attachment in it with a z position of anything else but 0 (this also works on the x axis, but then you need to change the code to affect the x axis). Finally, the part’s z size needs to be more than 9 (I have it at 10).

``````local Part=game.Workspace.Part
local Attachment=Part.Attachment
local OldAttachmentPos=CFrame.new()
local LastCF=Vector3.new(0,0,0)

for alpha=0,1,0.003 do
--GenerateNextPos
local nextpos=Vector3.new():Lerp(Vector3.new(0,0,-9),alpha)

--PartSize
Part.Size=nextpos+(Part.Size-LastCF)
LastCF=nextpos

--AttachmentPosition
local nextApos=CFrame.new((nextpos.X*Attachment.CFrame.Position.X)/Part.Size.X,
(nextpos.Y*Attachment.CFrame.Position.Y)/Part.Size.Y,
(nextpos.Z*Attachment.CFrame.Position.Z)/Part.Size.Z)

print(OldAttachmentPos.Position.Z," ! ",Attachment.CFrame.Position.Z," ! ",nextApos.Position.Z," ! ",OldAttachmentPos:Inverse().Position.Z)

Attachment.CFrame=nextApos*(Attachment.CFrame*OldAttachmentPos:Inverse())
OldAttachmentPos=nextApos

end

``````

This may be like a floating point rounding issue, but its so weird just seeing it arise from nothing.

The blue circled points are where the problems first begin, where it starts oscillating back and forth. Above it you can see the position moving down by roughly 0.01, but after it jumps around adding and subtracting (adding a negative) larger and larger numbers until it reaches infinity, then nan.
This is so weird. Especially since the size works normally.
I suspect it has something to do with :Inverse() but I don’t know. Any help appreciated!

Root of the problem still unknown, instead of doing this, I just made a script on every attachment to adjust its position.

``````local oldsize=script.Parent.Parent.Size
script.Parent.Parent:GetPropertyChangedSignal("Size"):Connect(function()
local Size=script.Parent.Parent.Size
local OldPos=script.Parent.CFrame
local NewPos=CFrame.new((Size.X*OldPos.Position.X)/oldsize.X,
(Size.Y*OldPos.Position.Y)/oldsize.Y,
(Size.Z*OldPos.Position.Z)/oldsize.Z
)
local finalCFrame=(OldPos-OldPos.Position)*NewPos
script.Parent.CFrame=finalCFrame
OldPos=NewPos
oldsize=Size
end)
``````

This topic was automatically closed 14 days after the last reply. New replies are no longer allowed.