mirror of
https://github.com/status-im/Vulkan-Docs.git
synced 2025-02-20 01:58:06 +00:00
* Bump API patch number and header version number to 40 for this update. * There is a major build change in this release. We are now using the Ruby-based ``asciidoctor'' implementation, rather than the Python-based ``asciidoc'' implementation, to process the specification. While the actual specification markup changes were minimal, this requires a new set of build tools and a very different installation process, especially because we now use an experimental direct-to-PDF backend for Asciidoctor instead of Docbook->dblatex->PDF. It is no longer possible to build the Specification using asciidoc. See doc/specs/vulkan/README.adoc for some guidance on installing the new toolchain components. * There are some minor rendering issues in the PDF output due to teething problems with the asciidoctor toolchain, especially with mathematical equations. We are aware of these and working on them. Github Issues: * Updated sample code for the <<sparsememory-examples-basic,sparse resource binding example>> (public issue 97). * Modify line and point clipping behavior in the <<vertexpostproc-clipping, Primitive Clipping>> section to allow for pop-free behavior. The ability to check for which behavior is implemented may be added a future feature or extension (public issue 113). * Unify the discussions of implicit ordering throughout the spec, in particular in the new sections <<drawing-primitive-order, Primitive Order>>, <<primrast-order, Rasterization Order>>, and <<synchronization-implicit, Implicit Synchronization Guarantees>>; the discussion of <<synchronization-submission-order, submission order>>; and references elsewhere to these sections (public issue 133). * Clarify \<\<descriptorsets-compatibility,Pipeline Layout Compatibility>> language and introduce the term ``identically defined'' (public issue 164). * Add a dependency to the +VK_EXT_debug_marker+ extension that's needed to reuse the object type enum from +VK_EXT_debug_report+, and moves the definition of that enum into +VK_EXT_debug_report+ where it should be (public issue 409). * Remove redundant valid usage statement from slink:VkImageBlit (public issue 421). * Update GL_KHR_vulkan_glsl to allow the ternary operator to result in a specialization constant (public issue 424). * Fix valid usage for flink:VkPipelineShaderStageCreateInfo (public issue 426). * Correct typo in New Objects list for <<VK_EXT_debug_report>> (public issue 447). Internal Issues: * Moved to asciidoctor for spec builds (internal issue 121). * Update style guide to describe where to put new extensions-specific asciidoc files, and what to name them (internal issue 626). * Add src/spec/indexExt.py to autogenerate registry index entries linking into the 1.0-extensions specification, instead of maintaining the index manually. (internal issue 642). * Autogenerate extension dependencies and lists of all extensions and all KHR extensions from the "supported" attributes in +vk.xml+. Execute +make config/extDependency.sh+ from +doc/specs/vulkan+ when a supported extension is added to vk.xml, to regenerate the dependency script. The consequence is that specifying a single extension to the +makeExt+ script will automatically enable all extensions it depends on as well, and that the +makeAllExts+ and +makeKHR+ scripts do not need to be updated when a new extension is supported (internal issue 648). * Put extension appendices all at the same asciidoc section level, so KHR WSI extensions show up in the HTML index (internal issue 648). Other Issues: * Imbed images in the generated HTML specs instead of loading them from the images/ directory. * Fix missing EXT in extension name (ename:VK_EXT_SWAPCHAIN_COLOR_SPACE_EXTENSION_NAME). * Add new +VK_EXT_SMPTE_2086_metadata+ extension. * In the <<platformCreateSurface_xlib,Xlib Surface>> section of the +VK_KHR_xlib_surface+ specification, add language warning users that they always need to call code:XinitThreads. * Use the term "presentable image" (rather than "swapchain image") consistently in +VK_KHR_swapchain+ and related extensions, and add a glossary term defining it. * Relocate the valid usage for samples of flink:vkGetPhysicalDeviceSparseImageFormatProperties2KHR::pname:pFormatInfo to be below the flink:VkPhysicalDeviceSparseImageFormatInfo2KHR structure.
491 lines
24 KiB
Plaintext
491 lines
24 KiB
Plaintext
// Copyright (c) 2015-2017 The Khronos Group Inc.
|
|
// Copyright notice at https://www.khronos.org/registry/speccopyright.html
|
|
|
|
[[tessellation]]
|
|
= Tessellation
|
|
|
|
Tessellation involves three pipeline stages.
|
|
First, a <<shaders-tessellation-control,tessellation control shader>>
|
|
transforms control points of a patch and can: produce per-patch data.
|
|
Second, a fixed-function tessellator generates multiple primitives
|
|
corresponding to a tessellation of the patch in (u,v) or (u,v,w) parameter
|
|
space.
|
|
Third, a <<shaders-tessellation-evaluation,tessellation evaluation shader>>
|
|
transforms the vertices of the tessellated patch, for example to compute
|
|
their positions and attributes as part of the tessellated surface.
|
|
The tessellator is enabled when the pipeline contains both a tessellation
|
|
control shader and a tessellation evaluation shader.
|
|
|
|
|
|
== Tessellator
|
|
|
|
If a pipeline includes both tessellation shaders (control and evaluation),
|
|
the tessellator consumes each input patch (after vertex shading) and
|
|
produces a new set of independent primitives (points, lines, or triangles).
|
|
These primitives are logically produced by subdividing a geometric primitive
|
|
(rectangle or triangle) according to the per-patch outer and inner
|
|
tessellation levels written by the tessellation control shader.
|
|
These levels are specified using the <<interfaces-builtin-variables,built-in
|
|
variables>> code:TessLevelOuter and code:TessLevelInner, respectively.
|
|
This subdivision is performed in an implementation-dependent manner.
|
|
If no tessellation shaders are present in the pipeline, the tessellator is
|
|
disabled and incoming primitives are passed through without modification.
|
|
|
|
The type of subdivision performed by the tessellator is specified by an
|
|
code:OpExecutionMode instruction in the tessellation evaluation or
|
|
tessellation control shader using one of execution modes code:Triangles,
|
|
code:Quads, and code:IsoLines.
|
|
Other tessellation-related execution modes can: also be specified in either
|
|
the tessellation control or tessellation evaluation shaders, and if they are
|
|
specified in both then the modes must: be the same.
|
|
|
|
Tessellation execution modes include:
|
|
|
|
* code:Triangles, code:Quads, and code:IsoLines.
|
|
These control the type of subdivision and topology of the output
|
|
primitives.
|
|
One mode must: be set in at least one of the tessellation shader stages.
|
|
* code:VertexOrderCw and code:VertexOrderCcw.
|
|
These control the orientation of triangles generated by the tessellator.
|
|
One mode must: be set in at least one of the tessellation shader stages.
|
|
* code:PointMode.
|
|
Controls generation of points rather than triangles or lines.
|
|
This functionality defaults to disabled, and is enabled if either shader
|
|
stage includes the execution mode.
|
|
* code:SpacingEqual, code:SpacingFractionalEven, and
|
|
code:SpacingFractionalOdd.
|
|
Controls the spacing of segments on the edges of tessellated primitives.
|
|
One mode must: be set in at least one of the tessellation shader stages.
|
|
* code:OutputVertices.
|
|
Controls the size of the output patch of the tessellation control
|
|
shader.
|
|
One value must: be set in at least one of the tessellation shader
|
|
stages.
|
|
|
|
For triangles, the tessellator subdivides a triangle primitive into smaller
|
|
triangles.
|
|
For quads, the tessellator subdivides a rectangle primitive into smaller
|
|
triangles.
|
|
For isolines, the tessellator subdivides a rectangle primitive into a
|
|
collection of line segments arranged in strips stretching across the
|
|
rectangle in the [eq]#u# dimension (i.e. the coordinates in code:TessCoord
|
|
are of the form (0,x) through (1,x) for all tessellation evaluation shader
|
|
invocations that share a line).
|
|
|
|
Each vertex produced by the tessellator has an associated (u,v,w) or (u,v)
|
|
position in a normalized parameter space, with parameter values in the range
|
|
[eq]#[0,1]#, as illustrated in figure <<img-tessellation-topology>>.
|
|
|
|
[[img-tessellation-topology]]
|
|
image::images/tessparam.svg[align="center",title="Domain parameterization for tessellation primitive modes",{fullimagewidth}]
|
|
|
|
.Caption
|
|
****
|
|
In the <<img-tessellation-topology,Domain parameterization>> diagram, the
|
|
coordinates illustrate the value of code:TessCoord at the corners of the
|
|
domain.
|
|
The labels on the edges indicate the inner (IL0 and IL1) and outer (OL0
|
|
through OL3) tessellation level values used to control the number of
|
|
subdivisions along each edge of the domain.
|
|
****
|
|
|
|
For triangles, the vertex's position is a barycentric coordinate (u,v,w),
|
|
where u + v + w = 1.0, and indicates the relative influence of the three
|
|
vertices of the triangle on the position of the vertex.
|
|
For quads and isolines, the position is a (u,v) coordinate indicating the
|
|
relative horizontal and vertical position of the vertex relative to the
|
|
subdivided rectangle.
|
|
The subdivision process is explained in more detail in subsequent sections.
|
|
|
|
|
|
== Tessellator Patch Discard
|
|
|
|
A patch is discarded by the tessellator if any relevant outer tessellation
|
|
level is less than or equal to zero.
|
|
|
|
Patches will also be discarded if any relevant outer tessellation level
|
|
corresponds to a floating-point [eq]#NaN# (not a number) in implementations
|
|
supporting [eq]#NaN#.
|
|
|
|
No new primitives are generated and the tessellation evaluation shader is
|
|
not executed for patches that are discarded.
|
|
For code:Quads, all four outer levels are relevant.
|
|
For code:Triangles and code:IsoLines, only the first three or two outer
|
|
levels, respectively, are relevant.
|
|
Negative inner levels will not cause a patch to be discarded; they will be
|
|
clamped as described below.
|
|
|
|
|
|
[[tessellation-tessellator-spacing]]
|
|
== Tessellator Spacing
|
|
|
|
Each of the tessellation levels is used to determine the number and spacing
|
|
of segments used to subdivide a corresponding edge.
|
|
The method used to derive the number and spacing of segments is specified by
|
|
an code:OpExecutionMode in the tessellation control or tessellation
|
|
evaluation shader using one of the identifiers code:SpacingEqual,
|
|
code:SpacingFractionalEven, or code:SpacingFractionalOdd.
|
|
|
|
If code:SpacingEqual is used, the floating-point tessellation level is first
|
|
clamped to [eq]#[1, pname:maxLevel]#, where [eq]#pname:maxLevel# is the
|
|
implementation-dependent maximum tessellation level
|
|
(sname:VkPhysicalDeviceLimits::pname:maxTessellationGenerationLevel).
|
|
The result is rounded up to the nearest integer [eq]#n#, and the
|
|
corresponding edge is divided into [eq]#n# segments of equal length in (u,v)
|
|
space.
|
|
|
|
If code:SpacingFractionalEven is used, the tessellation level is first
|
|
clamped to [eq]#[2, pname:maxLevel]# and then rounded up to the nearest even
|
|
integer [eq]#n#.
|
|
If code:SpacingFractionalOdd is used, the tessellation level is clamped to
|
|
[eq]#[1, pname:maxLevel - 1]# and then rounded up to the nearest odd integer
|
|
[eq]#n#.
|
|
If [eq]#n# is one, the edge will not be subdivided.
|
|
Otherwise, the corresponding edge will be divided into [eq]#n - 2# segments
|
|
of equal length, and two additional segments of equal length that are
|
|
typically shorter than the other segments.
|
|
The length of the two additional segments relative to the others will
|
|
decrease monotonically with [eq]#n - f#, where [eq]#f# is the clamped
|
|
floating-point tessellation level.
|
|
When [eq]#n - f# is zero, the additional segments will have equal length to
|
|
the other segments.
|
|
As [eq]#n - f# approaches 2.0, the relative length of the additional
|
|
segments approaches zero.
|
|
The two additional segments must: be placed symmetrically on opposite sides
|
|
of the subdivided edge.
|
|
The relative location of these two segments is implementation-dependent, but
|
|
must: be identical for any pair of subdivided edges with identical values of
|
|
[eq]#f#.
|
|
|
|
When the tessellator produces triangles (in the code:Triangles or code:Quads
|
|
modes), the orientation of all triangles is specified with an
|
|
code:OpExecutionMode of code:VertexOrderCw or code:VertexOrderCcw in the
|
|
tessellation control or tessellation evaluation shaders.
|
|
If the order is code:VertexOrderCw, the vertices of all generated triangles
|
|
will have clockwise ordering in (u,v) or (u,v,w) space.
|
|
If the order is code:VertexOrderCcw, the vertices will have
|
|
counter-clockwise ordering.
|
|
|
|
The vertices of a triangle have counter-clockwise ordering if
|
|
|
|
:: [eq]#a = u~0~ v~1~ - u~1~ v~0~ + u~1~ v~2~ - u~2~ v~1~ + u~2~ v~0~ -
|
|
u~0~ v~2~#
|
|
|
|
is positive, and clockwise ordering if [eq]#a# is negative.
|
|
[eq]#u~i~# and [eq]#v~i~# are the [eq]#u# and [eq]#v# coordinates in
|
|
normalized parameter space of the [eq]##i##th vertex of the triangle.
|
|
|
|
[NOTE]
|
|
.Note
|
|
====
|
|
The value [eq]#a# is proportional (with a positive factor) to the signed
|
|
area of the triangle.
|
|
|
|
In code:Triangles mode, even though the vertex coordinates have a [eq]#w#
|
|
value, it does not participate directly in the computation of [eq]#a#, being
|
|
an affine combination of [eq]#u# and [eq]#v#.
|
|
====
|
|
|
|
For all primitive modes, the tessellator is capable of generating points
|
|
instead of lines or triangles.
|
|
If the tessellation control or tessellation evaluation shader specifies the
|
|
code:OpExecutionMode code:PointMode, the primitive generator will generate
|
|
one point for each distinct vertex produced by tessellation.
|
|
Otherwise, the tessellator will produce a collection of line segments or
|
|
triangles according to the primitive mode.
|
|
When tessellating triangles or quads in point mode with fractional odd
|
|
spacing, the tessellator may: produce _interior vertices_ that are
|
|
positioned on the edge of the patch if an inner tessellation level is less
|
|
than or equal to one.
|
|
Such vertices are considered distinct from vertices produced by subdividing
|
|
the outer edge of the patch, even if there are pairs of vertices with
|
|
identical coordinates.
|
|
|
|
|
|
[[tessellation-primitive-order]]
|
|
== Tessellation Primitive Ordering
|
|
|
|
Few guarantees are provided for the relative ordering of primitives produced
|
|
by tessellation, as they pertain to <<drawing-primitive-order, primitive
|
|
order>>.
|
|
|
|
* The output primitives generated from each input primitive are passed to
|
|
subsequent pipeline stages in an implementation-dependent order.
|
|
* All output primitives generated from a given input primitive are passed
|
|
to subsequent pipeline stages before any output primitives generated
|
|
from subsequent input primitives.
|
|
|
|
|
|
[[tessellation-triangle-tessellation]]
|
|
== Triangle Tessellation
|
|
|
|
If the tessellation primitive mode is code:Triangles, an equilateral
|
|
triangle is subdivided into a collection of triangles covering the area of
|
|
the original triangle.
|
|
First, the original triangle is subdivided into a collection of concentric
|
|
equilateral triangles.
|
|
The edges of each of these triangles are subdivided, and the area between
|
|
each triangle pair is filled by triangles produced by joining the vertices
|
|
on the subdivided edges.
|
|
The number of concentric triangles and the number of subdivisions along each
|
|
triangle except the outermost is derived from the first inner tessellation
|
|
level.
|
|
The edges of the outermost triangle are subdivided independently, using the
|
|
first, second, and third outer tessellation levels to control the number of
|
|
subdivisions of the [eq]#u = 0# (left), [eq]#v = 0# (bottom), and [eq]#w =
|
|
0# (right) edges, respectively.
|
|
The second inner tessellation level and the fourth outer tessellation level
|
|
have no effect in this mode.
|
|
|
|
If the first inner tessellation level and all three outer tessellation
|
|
levels are exactly one after clamping and rounding, only a single triangle
|
|
with [eq]#(u,v,w)# coordinates of [eq]#(0,0,1)#, [eq]#(1,0,0)#, and
|
|
[eq]#(0,1,0)# is generated.
|
|
If the inner tessellation level is one and any of the outer tessellation
|
|
levels is greater than one, the inner tessellation level is treated as
|
|
though it were originally specified as [eq]#1 + {epsilon}# and will result
|
|
in a two- or three-segment subdivision depending on the tessellation
|
|
spacing.
|
|
When used with fractional odd spacing, the three-segment subdivision may:
|
|
produce _inner vertices_ positioned on the edge of the triangle.
|
|
|
|
If any tessellation level is greater than one, tessellation begins by
|
|
producing a set of concentric inner triangles and subdividing their edges.
|
|
First, the three outer edges are temporarily subdivided using the clamped
|
|
and rounded first inner tessellation level and the specified tessellation
|
|
spacing, generating [eq]#n# segments.
|
|
For the outermost inner triangle, the inner triangle is degenerate -- a
|
|
single point at the center of the triangle -- if [eq]#n# is two.
|
|
Otherwise, for each corner of the outer triangle, an inner triangle corner
|
|
is produced at the intersection of two lines extended perpendicular to the
|
|
corner's two adjacent edges running through the vertex of the subdivided
|
|
outer edge nearest that corner.
|
|
If [eq]#n# is three, the edges of the inner triangle are not subdivided and
|
|
is the final triangle in the set of concentric triangles.
|
|
Otherwise, each edge of the inner triangle is divided into [eq]#n - 2#
|
|
segments, with the [eq]#n - 1# vertices of this subdivision produced by
|
|
intersecting the inner edge with lines perpendicular to the edge running
|
|
through the [eq]#n - 1# innermost vertices of the subdivision of the outer
|
|
edge.
|
|
Once the outermost inner triangle is subdivided, the previous subdivision
|
|
process repeats itself, using the generated triangle as an outer triangle.
|
|
This subdivision process is illustrated in <<img-innertri,Inner Triangle
|
|
Tessellation>>.
|
|
|
|
[[img-innertri]]
|
|
image::images/innertri.svg[align="center",title="Inner Triangle Tessellation",{fullimagewidth}]
|
|
|
|
.Caption
|
|
****
|
|
In the <<img-innertri,Inner Triangle Tessellation>> diagram, inner
|
|
tessellation levels of (a) five and (b) four are shown (not to scale).
|
|
Solid black circles depict vertices along the edges of the concentric
|
|
triangles.
|
|
The edges of inner triangles are subdivided by intersecting the edge with
|
|
segments perpendicular to the edge passing through each inner vertex of the
|
|
subdivided outer edge.
|
|
Dotted lines depict edges connecting corresponding vertices on the inner and
|
|
outer triangle edges.
|
|
****
|
|
|
|
Once all the concentric triangles are produced and their edges are
|
|
subdivided, the area between each pair of adjacent inner triangles is filled
|
|
completely with a set of non-overlapping triangles.
|
|
In this subdivision, two of the three vertices of each triangle are taken
|
|
from adjacent vertices on a subdivided edge of one triangle; the third is
|
|
one of the vertices on the corresponding edge of the other triangle.
|
|
If the innermost triangle is degenerate (i.e., a point), the triangle
|
|
containing it is subdivided into six triangles by connecting each of the six
|
|
vertices on that triangle with the center point.
|
|
If the innermost triangle is not degenerate, that triangle is added to the
|
|
set of generated triangles as-is.
|
|
|
|
After the area corresponding to any inner triangles is filled, the
|
|
tessellator generates triangles to cover the area between the outermost
|
|
triangle and the outermost inner triangle.
|
|
To do this, the temporary subdivision of the outer triangle edge above is
|
|
discarded.
|
|
Instead, the [eq]#u = 0#, [eq]#v = 0#, and [eq]#w = 0# edges are subdivided
|
|
according to the first, second, and third outer tessellation levels,
|
|
respectively, and the tessellation spacing.
|
|
The original subdivision of the first inner triangle is retained.
|
|
The area between the outer and first inner triangles is completely filled by
|
|
non-overlapping triangles as described above.
|
|
If the first (and only) inner triangle is degenerate, a set of triangles is
|
|
produced by connecting each vertex on the outer triangle edges with the
|
|
center point.
|
|
|
|
After all triangles are generated, each vertex in the subdivided triangle is
|
|
assigned a barycentric (u,v,w) coordinate based on its location relative to
|
|
the three vertices of the outer triangle.
|
|
|
|
The algorithm used to subdivide the triangular domain in (u,v,w) space into
|
|
individual triangles is implementation-dependent.
|
|
However, the set of triangles produced will completely cover the domain, and
|
|
no portion of the domain will be covered by multiple triangles.
|
|
|
|
The order in which the vertices for a given output triangle is generated is
|
|
implementation-dependent.
|
|
However, when depicted in a manner similar to <<img-innertri,Inner Triangle
|
|
Tessellation>>, the order of the vertices in each generated triangle will be
|
|
either all clockwise or all counter-clockwise, according to the vertex order
|
|
layout declaration.
|
|
|
|
|
|
[[tessellation-quad-tessellation]]
|
|
== Quad Tessellation
|
|
|
|
If the tessellation primitive mode is code:Quads, a rectangle is subdivided
|
|
into a collection of triangles covering the area of the original rectangle.
|
|
First, the original rectangle is subdivided into a regular mesh of
|
|
rectangles, where the number of rectangles along the [eq]#u = 0# and [eq]#u
|
|
= 1# (vertical) and [eq]#v = 0# and [eq]#v = 1# (horizontal) edges are
|
|
derived from the first and second inner tessellation levels, respectively.
|
|
All rectangles, except those adjacent to one of the outer rectangle edges,
|
|
are decomposed into triangle pairs.
|
|
The outermost rectangle edges are subdivided independently, using the first,
|
|
second, third, and fourth outer tessellation levels to control the number of
|
|
subdivisions of the [eq]#u = 0# (left), [eq]#v = 0# (bottom), [eq]#u = 1#
|
|
(right), and [eq]#v = 1# (top) edges, respectively.
|
|
The area between the inner rectangles of the mesh and the outer rectangle
|
|
edges are filled by triangles produced by joining the vertices on the
|
|
subdivided outer edges to the vertices on the edge of the inner rectangle
|
|
mesh.
|
|
|
|
If both clamped inner tessellation levels and all four clamped outer
|
|
tessellation levels are exactly one, only a single triangle pair covering
|
|
the outer rectangle is generated.
|
|
Otherwise, if either clamped inner tessellation level is one, that
|
|
tessellation level is treated as though it were originally specified as
|
|
[eq]#1 + {epsilon}# and will result in a two- or three-segment subdivision
|
|
depending on the tessellation spacing.
|
|
When used with fractional odd spacing, the three-segment subdivision may:
|
|
produce _inner vertices_ positioned on the edge of the rectangle.
|
|
|
|
If any tessellation level is greater than one, tessellation begins by
|
|
subdividing the [eq]#u = 0# and [eq]#u = 1# edges of the outer rectangle
|
|
into [eq]#m# segments using the clamped and rounded first inner tessellation
|
|
level and the tessellation spacing.
|
|
The [eq]#v = 0# and [eq]#v = 1# edges are subdivided into [eq]#n# segments
|
|
using the second inner tessellation level.
|
|
Each vertex on the [eq]#u = 0# and [eq]#v = 0# edges are joined with the
|
|
corresponding vertex on the [eq]#u = 1# and [eq]#v = 1# edges to produce a
|
|
set of vertical and horizontal lines that divide the rectangle into a grid
|
|
of smaller rectangles.
|
|
The primitive generator emits a pair of non-overlapping triangles covering
|
|
each such rectangle not adjacent to an edge of the outer rectangle.
|
|
The boundary of the region covered by these triangles forms an inner
|
|
rectangle, the edges of which are subdivided by the grid vertices that lie
|
|
on the edge.
|
|
If either [eq]#m# or [eq]#n# is two, the inner rectangle is degenerate, and
|
|
one or both of the rectangle's _edges_ consist of a single point.
|
|
This subdivision is illustrated in Figure <<img-innerquad,Inner Quad
|
|
Tessellation>>.
|
|
|
|
[[img-innerquad]]
|
|
image::images/innerquad.svg[align="center",title="Inner Quad Tessellation",{fullimagewidth}]
|
|
|
|
.Caption
|
|
****
|
|
In the <<img-innerquad,Inner Quad Tessellation>> diagram, inner quad
|
|
tessellation levels of (a) [eq]#(4,2)# and (b) [eq]#(7,4)# are shown.
|
|
Gray regions in figure (b) depict the 10 inner rectangles, each of which
|
|
will be subdivided into two triangles.
|
|
Solid black circles depict vertices on the boundary of the outer and inner
|
|
rectangles, where the inner rectangle on the top figure is degenerate (a
|
|
single line segment).
|
|
Dotted lines depict the horizontal and vertical edges connecting
|
|
corresponding vertices on the inner and outer rectangle edges.
|
|
****
|
|
|
|
After the area corresponding to the inner rectangle is filled, the
|
|
tessellator must: produce triangles to cover the area between the inner and
|
|
outer rectangles.
|
|
To do this, the subdivision of the outer rectangle edge above is discarded.
|
|
Instead, the [eq]#u = 0#, [eq]#v = 0#, [eq]#u = 1#, and [eq]#v = 1# edges
|
|
are subdivided according to the first, second, third, and fourth outer
|
|
tessellation levels, respectively, and the tessellation spacing.
|
|
The original subdivision of the inner rectangle is retained.
|
|
The area between the outer and inner rectangles is completely filled by
|
|
non-overlapping triangles.
|
|
Two of the three vertices of each triangle are adjacent vertices on a
|
|
subdivided edge of one rectangle; the third is one of the vertices on the
|
|
corresponding edge of the other triangle.
|
|
If either edge of the innermost rectangle is degenerate, the area near the
|
|
corresponding outer edges is filled by connecting each vertex on the outer
|
|
edge with the single vertex making up the _inner edge_.
|
|
|
|
The algorithm used to subdivide the rectangular domain in (u,v) space into
|
|
individual triangles is implementation-dependent.
|
|
However, the set of triangles produced will completely cover the domain, and
|
|
no portion of the domain will be covered by multiple triangles.
|
|
|
|
The order in which the vertices for a given output triangle is generated is
|
|
implementation-dependent.
|
|
However, when depicted in a manner similar to <<img-innerquad,Inner Quad
|
|
Tessellation>>, the order of the vertices in each generated triangle will be
|
|
either all clockwise or all counter-clockwise, according to the vertex order
|
|
layout declaration.
|
|
|
|
|
|
[[tessellation-isoline-tessellation]]
|
|
== Isoline Tessellation
|
|
|
|
If the tessellation primitive mode is code:IsoLines, a set of independent
|
|
horizontal line segments is drawn.
|
|
The segments are arranged into connected strips called _isolines_, where the
|
|
vertices of each isoline have a constant v coordinate and u coordinates
|
|
covering the full range [eq]#[0,1]#.
|
|
The number of isolines generated is derived from the first outer
|
|
tessellation level; the number of segments in each isoline is derived from
|
|
the second outer tessellation level.
|
|
Both inner tessellation levels and the third and fourth outer tessellation
|
|
levels have no effect in this mode.
|
|
|
|
As with quad tessellation above, isoline tessellation begins with a
|
|
rectangle.
|
|
The [eq]#u = 0# and [eq]#u = 1# edges of the rectangle are subdivided
|
|
according to the first outer tessellation level.
|
|
For the purposes of this subdivision, the tessellation spacing mode is
|
|
ignored and treated as equal_spacing.
|
|
An isoline is drawn connecting each vertex on the [eq]#u = 0# rectangle edge
|
|
to the corresponding vertex on the [eq]#u = 1# rectangle edge, except that
|
|
no line is drawn between (0,1) and (1,1).
|
|
If the number of isolines on the subdivided [eq]#u = 0# and [eq]#u = 1#
|
|
edges is [eq]#n#, this process will result in [eq]#n# equally spaced lines
|
|
with constant v coordinates of 0, latexmath:[\frac{1}{n}, \frac{2}{n},
|
|
\ldots, \frac{n-1}{n}].
|
|
|
|
Each of the [eq]#n# isolines is then subdivided according to the second
|
|
outer tessellation level and the tessellation spacing, resulting in [eq]#m#
|
|
line segments.
|
|
Each segment of each line is emitted by the tessellator.
|
|
|
|
The order in which the vertices for a given output line is generated is
|
|
implementation-dependent.
|
|
|
|
|
|
== Tessellation Pipeline State
|
|
|
|
The pname:pTessellationState member of slink:VkGraphicsPipelineCreateInfo
|
|
points to a structure of type sname:VkPipelineTessellationStateCreateInfo.
|
|
|
|
// refBegin VkPipelineTessellationStateCreateInfo Structure specifying parameters of a newly created pipeline tessellation state
|
|
|
|
The sname:VkPipelineTessellationStateCreateInfo structure is defined as:
|
|
|
|
include::../api/structs/VkPipelineTessellationStateCreateInfo.txt[]
|
|
|
|
* pname:sType is the type of this structure.
|
|
* pname:pNext is `NULL` or a pointer to an extension-specific structure.
|
|
* pname:flags is reserved for future use.
|
|
* pname:patchControlPoints number of control points per patch.
|
|
|
|
.Valid Usage
|
|
****
|
|
* pname:patchControlPoints must: be greater than zero and less than or
|
|
equal to sname:VkPhysicalDeviceLimits::pname:maxTessellationPatchSize
|
|
****
|
|
|
|
include::../validity/structs/VkPipelineTessellationStateCreateInfo.txt[]
|