Scripting HelpersARCHIVE
A little piece of Roblox history. Preserved for everyone, one question at a time.Read about the archive →
COMMUNITY QUESTION

How can I make the camera always look at one face of a block?

I know how to make the camera scriptable and such but I don't know how to rotate it properly, only move it. help? this is what I currently got:

local target = workspace.Kek
local camera = workspace.CurrentCamera
camera.CameraType = Enum.CameraType.Scriptable
camera.CameraSubject = target


 camera.CoordinateFrame = CFrame.new(target.Position)
							* CFrame.Angles(-.5,-.1,-.5) 
                                   

I dont know how to insert the CFrame.Angles without multiplying. Is there a variable for it? Thanks in advance.

3 comments

0

What exactly are you trying to do? Do you want to have the camera near the part looking at a particular face of it?

0

@LightningRoMan I want to make a main menu for a game with the camera facing at a structure

0

the lookVector property of a CFrame might help. Try with camera.CFrame = CFrame.new(somePos, structurePart.CFrame.lookVector)

1 answer

Warning: Overkill answer below. Look at the code at the bottom for a generalized solution. Read the answer below if you want to learn :)

Camera.CoordinateFrame is the defacto way to move the camera when the CameraType is "Scriptable".

CFrame.new() has a couple of different ways it can build a CFrame (which is just a representation of position and rotation) depending on what you put in the parenthesis.

One of these is CFrame.new(position, lookAt), where position is a Vector3 representing the camera's position, and lookAt is also a Vector3 representing the position to look towards.

I'm sure you see where we're going with this.

You can simple set position to, say, 5 studs in front of the part (i.e. Part.Position + Vector3.new(0, 0, -5)) and lookAt to Part.Position, and it will look at the part's front face. So you have:

local target = workspace.Kek
local camera = workspace.CurrentCamera
camera.CameraType = Enum.CameraType.Scriptable

local position = target.Position + Vector3.new(0, 0, -5)
local lookAt = target.Position

camera.CoordinateFrame = CFrame.new(position, lookAt)

But wait! What if target is rotated? Simply adding that offset won't work, since it's in world space, which means "not relative to anything but the sky". One way is to take advantage of CFrames being applied in object space by default:

local position = target.CFrame * CFrame.new(0, 0, -5) -- get the target's position and rotation information, add -5 in the local z axis.
position = position.p + part.Position -- convert it to a Vector3 and add it

But perhaps a more intuitive-looking way is to use a method of CFrame to get the world-space representation of an object-space vector:

local position = part.Position + part.CFrame:vectorToWorldSpace(Vector3.new(0, 0, -5))

That should work for your purposes.

For completeness and because I'm bored, I packaged everything in a function that allows you to simply specify a part, a face (Enum.NormalId or just "Right", "Up", "Back", etc.), and a distance from the center of the part:

local function LookAtFace(part, face, distance)
	face = face or Enum.NormalId.Front -- Make default face Front
	distance = distance or 10 -- Make default distance 10 studs
	
	if (type(face) == "string") then
		face = Enum.NormalId[face] -- Get face in enum form, if it isn't already
	end
	
	local position = part.Position
	local offset = part.CFrame:vectorToWorldSpace(Vector3.FromNormalId(face)) -- Gets the Vector3 from the face you put in and rotate it to world space
	
	workspace.CurrentCamera.CoordinateFrame = CFrame.new(position + distance*offset, position)
end

-- Example usage:

workspace.CurrentCamera.CameraType = Enum.CameraType.Scriptable

LookAtFace(workspace.Kek, "Front", 20) -- 20 studs away looking at front face
LookAtFace(workspace.Kek, Enum.NormalId.Right, 20) -- 20 studs away looking at right face

This discussion is preserved as it was. New answers, comments, and votes are closed.