diff options
| author | 2017-07-26 15:07:13 +0300 | |
|---|---|---|
| committer | 2017-08-19 10:13:20 +0300 | |
| commit | 36981a5aa6ffcc10417e533ab00de3b6f9bad067 (patch) | |
| tree | a1a32917c5e51c55ac05fe5780d3bebf85211c4c | |
| parent | correct constness (diff) | |
| download | yuzu-36981a5aa6ffcc10417e533ab00de3b6f9bad067.tar.gz yuzu-36981a5aa6ffcc10417e533ab00de3b6f9bad067.tar.xz yuzu-36981a5aa6ffcc10417e533ab00de3b6f9bad067.zip | |
pica/primitive_assembly: Handle winding for GS primitive
hwtest shows that, although GS always emit a group of three vertices as one primitive, it still respects to the topology type, as if the three vertices are input into the primitive assembler independently and sequentially. It is also shown that the winding flag in SETEMIT only takes effect for Shader topology type, which is believed to be the actual difference between List and Shader (hence removed the TODO). However, only Shader topology type is observed in official games when GS is in use, so the other mode seems to be just unintended usage.
Diffstat (limited to '')
| -rw-r--r-- | src/video_core/primitive_assembly.cpp | 15 | ||||
| -rw-r--r-- | src/video_core/primitive_assembly.h | 7 |
2 files changed, 19 insertions, 3 deletions
diff --git a/src/video_core/primitive_assembly.cpp b/src/video_core/primitive_assembly.cpp index acd2ac5e2..9c3dd4cab 100644 --- a/src/video_core/primitive_assembly.cpp +++ b/src/video_core/primitive_assembly.cpp | |||
| @@ -17,15 +17,18 @@ template <typename VertexType> | |||
| 17 | void PrimitiveAssembler<VertexType>::SubmitVertex(const VertexType& vtx, | 17 | void PrimitiveAssembler<VertexType>::SubmitVertex(const VertexType& vtx, |
| 18 | TriangleHandler triangle_handler) { | 18 | TriangleHandler triangle_handler) { |
| 19 | switch (topology) { | 19 | switch (topology) { |
| 20 | // TODO: Figure out what's different with TriangleTopology::Shader. | ||
| 21 | case PipelineRegs::TriangleTopology::List: | 20 | case PipelineRegs::TriangleTopology::List: |
| 22 | case PipelineRegs::TriangleTopology::Shader: | 21 | case PipelineRegs::TriangleTopology::Shader: |
| 23 | if (buffer_index < 2) { | 22 | if (buffer_index < 2) { |
| 24 | buffer[buffer_index++] = vtx; | 23 | buffer[buffer_index++] = vtx; |
| 25 | } else { | 24 | } else { |
| 26 | buffer_index = 0; | 25 | buffer_index = 0; |
| 27 | 26 | if (topology == PipelineRegs::TriangleTopology::Shader && winding) { | |
| 28 | triangle_handler(buffer[0], buffer[1], vtx); | 27 | triangle_handler(buffer[1], buffer[0], vtx); |
| 28 | winding = false; | ||
| 29 | } else { | ||
| 30 | triangle_handler(buffer[0], buffer[1], vtx); | ||
| 31 | } | ||
| 29 | } | 32 | } |
| 30 | break; | 33 | break; |
| 31 | 34 | ||
| @@ -51,9 +54,15 @@ void PrimitiveAssembler<VertexType>::SubmitVertex(const VertexType& vtx, | |||
| 51 | } | 54 | } |
| 52 | 55 | ||
| 53 | template <typename VertexType> | 56 | template <typename VertexType> |
| 57 | void PrimitiveAssembler<VertexType>::SetWinding() { | ||
| 58 | winding = true; | ||
| 59 | } | ||
| 60 | |||
| 61 | template <typename VertexType> | ||
| 54 | void PrimitiveAssembler<VertexType>::Reset() { | 62 | void PrimitiveAssembler<VertexType>::Reset() { |
| 55 | buffer_index = 0; | 63 | buffer_index = 0; |
| 56 | strip_ready = false; | 64 | strip_ready = false; |
| 65 | winding = false; | ||
| 57 | } | 66 | } |
| 58 | 67 | ||
| 59 | template <typename VertexType> | 68 | template <typename VertexType> |
diff --git a/src/video_core/primitive_assembly.h b/src/video_core/primitive_assembly.h index e8eccdf27..12de8e3b9 100644 --- a/src/video_core/primitive_assembly.h +++ b/src/video_core/primitive_assembly.h | |||
| @@ -30,6 +30,12 @@ struct PrimitiveAssembler { | |||
| 30 | void SubmitVertex(const VertexType& vtx, TriangleHandler triangle_handler); | 30 | void SubmitVertex(const VertexType& vtx, TriangleHandler triangle_handler); |
| 31 | 31 | ||
| 32 | /** | 32 | /** |
| 33 | * Invert the vertex order of the next triangle. Called by geometry shader emitter. | ||
| 34 | * This only takes effect for TriangleTopology::Shader. | ||
| 35 | */ | ||
| 36 | void SetWinding(); | ||
| 37 | |||
| 38 | /** | ||
| 33 | * Resets the internal state of the PrimitiveAssembler. | 39 | * Resets the internal state of the PrimitiveAssembler. |
| 34 | */ | 40 | */ |
| 35 | void Reset(); | 41 | void Reset(); |
| @@ -45,6 +51,7 @@ private: | |||
| 45 | int buffer_index; | 51 | int buffer_index; |
| 46 | VertexType buffer[2]; | 52 | VertexType buffer[2]; |
| 47 | bool strip_ready = false; | 53 | bool strip_ready = false; |
| 54 | bool winding = false; | ||
| 48 | }; | 55 | }; |
| 49 | 56 | ||
| 50 | } // namespace | 57 | } // namespace |