# What can I do with the 4th component of gl_Position?

When I set gl_Position I usually assign it such as gl_Position = vec4(in_position, 1.0) where in_position as a vector of three components representing a vertex of my model.

But looking up tutorials and such I cannot find anything explaining what the 4th component of the gl_Position vec4 is doing aside from making the vector big enough so matrix transformations can be applied to it.

Q: What can I do with the 4th component of gl_Position / what does it influence in the rendering process?

• Just a comment since I'm not entirely sure. But if I remember correctly a vector can either be a position or a direction. When the 4th parameter is 1 it is treated as position and when it's 0 as direction. But of course it depends on context how it's used. This is more a convention. Jan 11, 2018 at 13:52
• gl_Position = vec4(in_position, 1.0) Do you actually do it in the shader? No matrix transformations? Do you really mean gl_Position = u_matrix * vec4(in_position, 1.0);? Jan 11, 2018 at 14:23
• @HolyBlackCat naturally there are some matrix multiplications for view and projection transformations, but I did not see any point in bloating the example with them. Jan 11, 2018 at 14:24
• @dot_Sp0T If you have used a perspective projection matrix, after that multiplication gl_Position.w will no longer be equal to 1, and the perspective division will happen. Not sure if it helps or you ask about a completely different thing. Jan 11, 2018 at 14:30
• @HolyBlackCat that is a good point. The idea behind the question is probably best described as 'finding out what that value does in the end' - I will amend the question Jan 11, 2018 at 14:34

## 2 Answers

gl_Position is a Homogeneous coordinates. Homogeneous coordinates are needed for perspective projection.

Note, if a vector vec4(x, y, z, 1.0) is multiplied by a perspective projection matrix, this results in a Homogeneous coordinates.

The projection matrix describes the mapping from 3D points of a scene, to 2D points of the viewport. The projection matrix transforms from view space to the clip space. The coordinates in the clip space are transformed to the normalized device coordinates (NDC) in the range (-1, -1, -1) to (1, 1, 1) by dividing with the w component of the clip coordinates.
At Perspective Projection the projection matrix describes the mapping from 3D points in the world as they are seen from of a pinhole camera, to 2D points of the viewport.
The eye space coordinates in the camera frustum (a truncated pyramid) are mapped to a cube (the normalized device coordinates).

This means the position in normalized device space is calculated like this:

vec3 ndc = gl_Position.xyz / gl_Position.w;


If you manually set the w component of gl_Position, this causes a reciprocal scaling of the position in normalized device space.

• so, what would modifying the w component do if anything at all? Jan 13, 2018 at 10:42
• @dot_Sp0T A reciprocal scaling of the normalized device coordinates. See the answer. Jan 13, 2018 at 10:51
• sweet, now I only need to find out what 'reciprocal' means. +1 Jan 13, 2018 at 10:53
• @dot_Sp0T In math reciprocal means * 1.0/x in compare to * x. The reciprocal of x is 1.0/x. Jan 13, 2018 at 10:55
• @dot_Sp0T A reciprocal is just 1 / whatever. In practice, a reciprocal is generally the inverse or opposite of something (max vs min, front vs back, the multiplicand needed to reach the opposite extreme, determining if a phone is rotated depending on current resolution, etc). Incidentally, the consequence of this is that taking the reciprocal of a reciprocal gets you back to the original number. Jul 16, 2023 at 6:20

It's not particularly useful for you but you should definitely leave it at 1. It's used when applying transformations to the model.

Matrix multiplication can only multiply numbers, it can't add. That makes moving objects impossible unless the 4th component exists. Let's look at an example: If we want to move the vector

$$\vec v = \begin{bmatrix}a \\ b\\c\end{bmatrix}$$

by

$$\vec d = \begin{bmatrix}x\\y\\z\end{bmatrix}$$

Then we use the

$$T = \begin{bmatrix} 1 & 0 & 0 & x\\ 0 & 1 & 0 & y\\ 0 & 0 & 1 & z\\ 0 & 0 & 0 & 1 \end{bmatrix}$$

matrix and give $\vec v$ a fourth component. When we multiply them together, then the result is going to be

$$\vec r = T\space \cdot\space\vec v = \begin{bmatrix} 1 \cdot a + 0 \cdot b + 0 \cdot c + x \cdot 1\\ 0 \cdot a + 1 \cdot b + 0 \cdot c + y \cdot 1\\ 0 \cdot a + 0 \cdot b + 1 \cdot c + z \cdot 1\\ 0 \cdot a + 0 \cdot b + 0 \cdot c + 1 \cdot 1\\ \end{bmatrix} = \begin{bmatrix} a + x\\ b + y\\ c + z\\ 1 \end{bmatrix}$$

The second use for the 4th component is perspective division. A projection matrix basically normalizes and copies the z component to the w. OpenGL then automatically divides the x, y and z components by it.

• A (simplified) real-world example of use of this knowledge can be seen in my answer here, where I convert clip coordinates down to screen coordinates, round them and convert back. Jan 1, 2020 at 14:46