I found that the wiki says creating a CFrame in this way is now deprecated:
Is this true? I couldn’t find any other source than this misspelled wiki entry, and I don’t see any reason why this feature would be deprecated.
I found that the wiki says creating a CFrame in this way is now deprecated:
Is this true? I couldn’t find any other source than this misspelled wiki entry, and I don’t see any reason why this feature would be deprecated.
My guess is that passing two Vector3s in the CFrame.new constructor is confusing in terms of its intentions and so it was deprecated in favour of a constructor that actually spells out the intention in the function name.
While the functionality won’t be removed or will be supported for a long time, just be wary that deprecated items are subject to removal at any given time so be sure to use updated methods as recommended in the message.
As far as I know it is, but one of the issues with using the example on the wiki as a replacement is that it does not handle edge cases well at all.
For example if you plug in:
function lookAt(target, eye)
local forwardVector = (eye - target).Unit
local upVector = Vector3.new(0, 1, 0)
-- You have to remember the right hand rule or google search to get this right
local rightVector = forwardVector:Cross(upVector)
local upVector2 = rightVector:Cross(forwardVector)
return CFrame.fromMatrix(eye, rightVector, upVector2)
end
print(lookAt(Vector3.new(), Vector3.new(0, 1, 0)))
-- 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0
You’ll get a invalid CFrame which is somewhat problematic for users that don’t know how to fix this as they may resort to the depreciated constructor. As such I think it would be in Roblox’s favour to add a replacement constructor that (as Colbert says) spells out the intention.
For now I recommend using a function that takes those edge cases into consideration such as this:
local UNIT_X = Vector3.new(1, 0, 0)
local UNIT_Y = Vector3.new(0, 1, 0)
local UNIT_Z = Vector3.new(0, 0, 1)
local IDENTITYCF = CFrame.new()
local function lookAt(eye, target, normalId)
local cf = IDENTITYCF
local forward = target - eye
-- technically returns 0, 1, 0, NAN, NAN, NAN, NAN, NAN, NAN, NAN, NAN, NAN
if (forward:Dot(forward) == 0) then
return IDENTITYCF + eye
end
-- calculate needed rotation for adjusting face
if (normalId and normalId ~= Enum.NormalId.Front) then
local face = Vector3.FromNormalId(normalId)
local axis = math.abs(face.z) >= 1 and UNIT_Y or UNIT_Z:Cross(face)
local theta = math.acos(-face.z)
cf = CFrame.fromAxisAngle(axis, theta)
end
-- return the CFrame
forward = forward.Unit
if (math.abs(forward.y) >= 0.9999) then
return CFrame.fromMatrix(eye, -math.sign(forward.y) * UNIT_Z, UNIT_X) * cf
else
local right = forward:Cross(UNIT_Y).Unit
local up = right:Cross(forward).Unit
return CFrame.fromMatrix(eye, right, up) * cf
end
end
I think the claim that it’s deprecated is dubious. I vaguely remember some years ago how the lookAt constructor (lookAt
) was disfavored because it didn’t let you specify the longitudinal axis (or “roll”). That is, the resulting CFrame is always oriented upright. With the addition of fromMatrix
, it became possible to specify other axes more easily. I think that whoever wrote the documentation interpreted this as lookAt
becoming obsolete, and therefore “deprecated”. However, as the given example suggests, using fromMatrix
to reproduce the behavior provided by lookAt
is involved and complicated. fromMatrix
is no replacement, and lookAt
is not made obsolete by it.
If I were to reword it, I would indicate that the resulting CFrame is always oriented upright, and then refer to fromMatrix
for when the user needs to be more specific about the orientation.
It’s deprecated? That’s funny, I was looking through the Roblox camera scripts today and the constructor is used frequently.
How are you supposed to know if things are deprecated without searching it up? I honestly had no idea.
I could understand CFrame.p being deprecated, but this is just weird