3D Math for Games

Every frame of a 3D game is a long chain of math: objects are placed in the world with transforms, viewed through a camera, projected onto the screen, lit using normals, moved with velocities, rotated with quaternions, and tested for hits with rays. Engines hide much of it behind components and editors, but the moment you write a camera controller, an aiming system, a shader, or a physics query, you are working directly with vectors, matrices, and coordinate spaces.

Most 3D math bugs are not hard math — they are convention bugs: multiplying transforms in the wrong order, mixing local and world space, assuming the wrong handedness or up axis, interpolating rotations as Euler angles, or forgetting to scale by frame time. This page covers the core tools and the conventions that trip people up.

TL;DR

Quick Example

Building a model matrix, projecting a point, measuring an angle, and rotating with a quaternion (NumPy, right-handed, column vectors):

Core Concepts

Vectors, Dot, and Cross

The sign of a dot product tells you whether something is in front of or behind you; the sign of a cross product's component tells you left or right.

Coordinate Spaces

Physics, gameplay, and AI usually work in world space; shaders move vertices through all of them. Name variables by space (posWorld, dirLocal) to avoid mixing them.

Handedness and Engine Conventions

Importers convert between tools, but hand-written math, shaders, and data from other tools must use the right convention. Check also whether matrices act on column vectors (M·v, composed right to left) or row vectors (v·M, composed left to right).

Transforms and Order

A transform matrix combines translation, rotation, and scale (TRS). With column vectors, T · R · S · v scales first, rotates second, translates last; reversing the order rotates the object around the world origin instead of its own. Parent–child hierarchies multiply transforms down the tree: world = parentWorld · childLocal.

Rotations: Euler Angles and Quaternions

Euler angles (pitch, yaw, roll) are intuitive for editors and player input but suffer from gimbal lock and blend poorly. Quaternions represent orientation without gimbal lock, compose by multiplication, and interpolate smoothly with slerp. Keep orientation as quaternions internally; accumulate player yaw and pitch as angles (clamping pitch) and convert to a quaternion each frame. See Robot Kinematics and Dynamics for the same mathematics applied to robots.

Projection and Depth

A perspective projection makes distant objects smaller and is defined by field of view, aspect ratio, and near and far planes; an orthographic projection keeps sizes constant (2D games, strategy views, UI). Depth buffer precision is distributed non-linearly — most precision sits near the near plane — so a tiny near plane causes z-fighting in the distance. Push the near plane out, or use reversed-Z with a floating-point depth buffer, which many engines now do. See OpenGL.

Normals

Surface normals must be transformed by the inverse transpose of the model matrix's upper 3×3, not the model matrix itself, or non-uniform scaling skews lighting. Renormalize after transforming and after interpolation in shaders. See Shader Programming.

Interpolation and Easing

Linear interpolation is mechanical; easing curves (smoothstep, cubic, spring damping) make motion feel natural. For framerate-independent smoothing toward a target, use exponential decay: value = lerp(target, value, exp(-rate * dt)), not a fixed fraction per frame.

Rays and Intersections

Raycasts — a point plus a direction — power shooting, mouse picking, line of sight, and ground detection. Core tests include ray–plane, ray–sphere, ray–box (axis-aligned bounding boxes with the slab method), and ray–triangle. Engines provide optimized physics queries; understanding the math helps with custom gameplay checks and debugging. See Game Physics.

Time and Precision

Multiply velocities by delta time so movement does not depend on frame rate, and use fixed timesteps for physics. Single-precision floats lose precision far from the origin — jittering cameras and physics in open worlds — so large worlds use origin rebasing or double-precision world coordinates, as in Unreal Engine 5's Large World Coordinates.

Best Practices

Name Spaces and Conventions Explicitly

Label positions and directions by space and document handedness, up axis, and matrix convention.

Prefer Quaternions for Orientation

Store and interpolate rotations as quaternions; convert to and from Euler angles only at the edges.

Visualize Vectors While Debugging

Draw debug lines for normals, directions, and rays; most math bugs are obvious when visible.

Make Motion Frame-Rate Independent

Scale motion and smoothing by delta time and run physics at a fixed step.

Common Mistakes

Wrong Multiplication Order

Per-Frame Smoothing Without Delta Time

Transforming Normals Like Positions

FAQ

What math do I need for 3D game development?

Vectors and their operations, matrices for transforms and projection, quaternions for rotation, basic trigonometry, and interpolation. Collision and physics add geometry and some calculus.

What is the dot product used for in games?

Measuring how aligned two directions are: facing and view-cone checks, projecting movement onto surfaces, and lighting calculations.

Why use quaternions instead of Euler angles?

Quaternions avoid gimbal lock, combine cleanly, and interpolate smoothly between orientations. Euler angles are easier for humans to read and edit.

What is the difference between left-handed and right-handed coordinates?

The direction of the third axis relative to the other two. Engines and tools choose different conventions, so data and math must be converted when moving between them.

What causes z-fighting?

Two surfaces with nearly the same depth competing for the same pixels, made worse by limited depth-buffer precision — especially with a very small near plane. Increasing the near plane distance or using reversed-Z depth helps.

Related Topics

References