Procházet zdrojové kódy

Maxwell3D: Reorganize and address feedback

Fernando Sahmkow před 7 roky
rodič
revize
7a35178ee2

+ 4 - 0
src/video_core/engines/maxwell_3d.cpp

@@ -70,6 +70,10 @@ void Maxwell3D::InitializeRegisterDefaults() {
     regs.stencil_back_func_mask = 0xFFFFFFFF;
     regs.stencil_back_mask = 0xFFFFFFFF;
 
+    regs.depth_test_func = Regs::ComparisonOp::Always;
+    regs.cull.front_face = Regs::Cull::FrontFace::CounterClockWise;
+    regs.cull.cull_face = Regs::Cull::CullFace::Back;
+
     // TODO(Rodrigo): Most games do not set a point size. I think this is a case of a
     // register carrying a default value. Assume it's OpenGL's default (1).
     regs.point_size = 1.0f;

+ 2 - 2
src/video_core/engines/maxwell_3d.h

@@ -1246,8 +1246,6 @@ private:
     /// Interpreter for the macro codes uploaded to the GPU.
     MacroInterpreter macro_interpreter;
 
-    Upload::State upload_state;
-
     static constexpr u32 null_cb_data = 0xFFFFFFFF;
     struct {
         std::array<std::array<u32, 0x4000>, 16> buffer;
@@ -1257,6 +1255,8 @@ private:
         u32 counter{};
     } cb_data_state;
 
+    Upload::State upload_state;
+
     /// Retrieves information about a specific TIC entry from the TIC buffer.
     Texture::TICEntry GetTICEntry(u32 tic_index) const;
 

+ 27 - 18
src/video_core/renderer_opengl/gl_rasterizer.cpp

@@ -993,37 +993,42 @@ void RasterizerOpenGL::SyncCullMode() {
     const auto& regs = maxwell3d.regs;
 
     state.cull.enabled = regs.cull.enabled != 0;
-    state.cull.front_face = MaxwellToGL::FrontFace(regs.cull.front_face);
-    state.cull.mode = MaxwellToGL::CullFace(regs.cull.cull_face);
-
-    const bool flip_triangles{regs.screen_y_control.triangle_rast_flip == 0 ||
-                              regs.viewport_transform[0].scale_y < 0.0f};
-
-    // If the GPU is configured to flip the rasterized triangles, then we need to flip the
-    // notion of front and back. Note: We flip the triangles when the value of the register is 0
-    // because OpenGL already does it for us.
-    if (flip_triangles) {
-        if (state.cull.front_face == GL_CCW)
-            state.cull.front_face = GL_CW;
-        else if (state.cull.front_face == GL_CW)
-            state.cull.front_face = GL_CCW;
+    if (state.cull.enabled) {
+        state.cull.front_face = MaxwellToGL::FrontFace(regs.cull.front_face);
+        state.cull.mode = MaxwellToGL::CullFace(regs.cull.cull_face);
+
+        const bool flip_triangles{regs.screen_y_control.triangle_rast_flip == 0 ||
+                                  regs.viewport_transform[0].scale_y < 0.0f};
+
+        // If the GPU is configured to flip the rasterized triangles, then we need to flip the
+        // notion of front and back. Note: We flip the triangles when the value of the register is 0
+        // because OpenGL already does it for us.
+        if (flip_triangles) {
+            if (state.cull.front_face == GL_CCW)
+                state.cull.front_face = GL_CW;
+            else if (state.cull.front_face == GL_CW)
+                state.cull.front_face = GL_CCW;
+        }
     }
 }
 
 void RasterizerOpenGL::SyncPrimitiveRestart() {
-    auto& maxwell3d = system.GPU().Maxwell3D();
-    const auto& regs = maxwell3d.regs;
+    const auto& regs = system.GPU().Maxwell3D().regs;
 
     state.primitive_restart.enabled = regs.primitive_restart.enabled;
     state.primitive_restart.index = regs.primitive_restart.index;
 }
 
 void RasterizerOpenGL::SyncDepthTestState() {
-    auto& maxwell3d = system.GPU().Maxwell3D();
-    const auto& regs = maxwell3d.regs;
+    const auto& regs = system.GPU().Maxwell3D().regs;
 
     state.depth.test_enabled = regs.depth_test_enable != 0;
     state.depth.write_mask = regs.depth_write_enabled ? GL_TRUE : GL_FALSE;
+
+    if (!state.depth.test_enabled) {
+        return;
+    }
+
     state.depth.test_func = MaxwellToGL::ComparisonOp(regs.depth_test_func);
 }
 
@@ -1035,6 +1040,10 @@ void RasterizerOpenGL::SyncStencilTestState() {
     const auto& regs = maxwell3d.regs;
 
     state.stencil.test_enabled = regs.stencil_enable != 0;
+    if (!regs.stencil_enable) {
+        return;
+    }
+
     state.stencil.front.test_func = MaxwellToGL::ComparisonOp(regs.stencil_front_func_func);
     state.stencil.front.test_ref = regs.stencil_front_func_ref;
     state.stencil.front.test_mask = regs.stencil_front_func_mask;