logo
Expand description

Configures how data from vertex buffers is read into vertex shader input locations.

The vertex input stage is the stage where data is read from a buffer and fed into the vertex shader. After each invocation of the vertex shader, the pipeline then proceeds to the input assembly stage.

Input locations and components

Input data is assigned per shader input location. Locations are set by adding the location layout qualifier to an input variable in GLSL. A single location contains four data elements, named “components”, which are each 32 bits in size. These correspond to the x, y, z and w (or equivalently r, g, b, a) components of a vec4 inside the shader. A component can contain at most one value, and data types that are smaller than 32 bits will still take up a whole component, so a single i8vec4 variable will still take up all four components in a location, even if not all bits are actually used.

A variable may take up fewer than four components. For example, a single float takes up only one component, a vec2 takes up two, and so on. Using the component layout qualifier in GLSL, it is possible to fit multiple variables into a single four-component location slot, as long as the components of each variable don’t overlap.

If the input variable is an array, then it takes up a series of consecutive locations. Each element of the array always starts at a new location, regardless of whether there is still room in the previous one. So, for example, an array of three vec2 takes three locations, since vec2 alone needs one location. An array can be decorated with the component qualifier as well; this is equivalent to applying the qualifier to every element of the array. If elements do not use all components in their locations, those free components can be filled with additional variables, just like for non-array types.

Matrices are laid out as if they were an array of column vectors. Thus, a mat4x3 is laid out as an array of four vec3s, mat2x4 as two vec4s. As with individual vectors, each column of the matrix uses up as many components of its location as there are rows in the matrix, and the remaining components are available for additional variables as described above. However, it is not possible to use the component qualifier on a matrix.

If a 64-bit value is to be passed to a shader, it will take up two adjacent components. Vectors of 64-bit values are correspondingly twice as large: dvec2 takes up all four components of a location, dvec4 takes two full locations, while dvec3 takes one full location and the first two components of the next. An array or matrix of a 64-bit type is made up of multiple adjacent 64-bit elements, just like for smaller types: each new element starts at a fresh location.

Input attributes

An input attribute is a mapping between data in a vertex buffer and the locations and components of the vertex shader.

Input attributes are assigned on a per-location basis; it is not possible to assign attributes to individual components. Instead, each attribute specifies up to four values to be read from the vertex buffer at once, which are then mapped to the four components of the given location. Like the texels in an image, each attribute’s data format in a vertex buffer is described by a Format. The input data doesn’t have to be an actual color, the format simply describes the type, size and layout of the data for the four input components. For example, Format::R32G32B32A32_SFLOAT will read four f32 values from the vertex buffer and assigns them to the four components of the attribute’s location.

It is possible to specify a Format that contains less than four components. In this case, the missing components are given default values: the first three components default to 0, while the fourth defaults to 1. This means that you can, for example, store only the x, y and z components of a vertex position in a vertex buffer, and have the vertex input state automatically set the w value to 1 for you. An exception to this are 64-bit values: these do not receive default values, meaning that components that are missing from the format are assigned no value and must not be used in the shader at all.

When matching attribute formats to shader input types, the following rules apply:

  • Signed integers in the shader must have an attribute format with a SINT type.
  • Unsigned integers in the shader must have an attribute format with a UINT type.
  • Floating point values in the shader must have an attribute format with a type other than SINT or UINT. This includes SFLOAT, UFLOAT and SRGB, but also SNORM, UNORM, SSCALED and USCALED.
  • 64-bit values in the shader must have a 64-bit attribute format.
  • 32-bit and smaller values in the shader must have a 32-bit or smaller attribute format, but the exact number of bits doesn’t matter. For example, Format::R8G8B8A8_UNORM can be used with a vec4 in the shader.

Input bindings

An input binding is a definition of a Vulkan buffer that contains the actual data from which each input attribute is to be read. The buffer itself is referred to as a “vertex buffer”, and is set during drawing with the bind_vertex_buffers command.

The data in a vertex buffer is typically arranged into an array, where each array element contains the data for a single vertex shader invocation. When deciding which element read from the vertex buffer for a given vertex and instance number, each binding has an “input rate”. If the input rate is Vertex, then the vertex input state advances to the next element of that buffer each time a new vertex number is processed. Likewise, if the input rate is Instance, it advances to the next element for each new instance number. Different bindings can have different input rates, and it’s also possible to have multiple bindings with the same input rate.

Structs

A vertex definition for any number of vertex and instance buffers.

Describes a single vertex buffer attribute mapping.

Describes a single vertex buffer binding.

The state in a graphics pipeline describing how the vertex input stage should behave.

Information about a member of a vertex struct.

Enums

Error that can happen when the vertex definition doesn’t match the input of the vertex shader.

How the vertex source should be unrolled.

Type of a member of a vertex struct.

Traits

Describes an individual Vertex. In other words a collection of attributes that can be read from a vertex shader.

A collection of vertex buffers.

Trait for types that can create a VertexInputState from a ShaderInterface.

Trait for data types that can be used as vertex members. Used by the impl_vertex! macro.