• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 //
2 // Copyright 2022 The ANGLE Project Authors. All rights reserved.
3 // Use of this source code is governed by a BSD-style license that can be
4 // found in the LICENSE file.
5 //
6 // FragDepthTest:
7 //   Tests the correctness of gl_FragDepth usage.
8 //
9 
10 #include "test_utils/ANGLETest.h"
11 #include "test_utils/gl_raii.h"
12 
13 using namespace angle;
14 
15 class FragDepthTest : public ANGLETest
16 {
17   protected:
18     struct FragDepthTestResources
19     {
20         GLuint program;
21         GLint depthLocation;
22         GLTexture colorTexture;
23         GLTexture depthTexture;
24         GLFramebuffer framebuffer;
25     };
26 
setupResources(FragDepthTestResources & resources)27     void setupResources(FragDepthTestResources &resources)
28     {
29 
30         // Writes a fixed depth value and green.
31         constexpr char kFS[] =
32             R"(#version 300 es
33             precision highp float;
34             layout(location = 0) out vec4 fragColor;
35             uniform float u_depth;
36             void main(){
37                 gl_FragDepth = u_depth;
38                 fragColor = vec4(0.0, 1.0, 0.0, 1.0);
39             })";
40 
41         resources.program       = CompileProgram(essl3_shaders::vs::Simple(), kFS);
42         resources.depthLocation = glGetUniformLocation(resources.program, "u_depth");
43 
44         glBindTexture(GL_TEXTURE_2D, resources.colorTexture);
45         glTexStorage2D(GL_TEXTURE_2D, 1, GL_RGBA8, 1, 1);
46         glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR);
47         glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR);
48 
49         glBindTexture(GL_TEXTURE_2D, resources.depthTexture);
50         glTexStorage2D(GL_TEXTURE_2D, 1, GL_DEPTH_COMPONENT32F, 1, 1);
51         glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_NEAREST);
52         glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST);
53 
54         glBindFramebuffer(GL_FRAMEBUFFER, resources.framebuffer);
55         glFramebufferTexture2D(GL_FRAMEBUFFER, GL_COLOR_ATTACHMENT0, GL_TEXTURE_2D,
56                                resources.colorTexture, 0);
57     }
58 
cleanupResources(FragDepthTestResources & resources)59     void cleanupResources(FragDepthTestResources &resources) { glDeleteProgram(resources.program); }
60 
checkDepthWritten(float expectedDepth,float fsDepth,bool bindDepthBuffer)61     void checkDepthWritten(float expectedDepth, float fsDepth, bool bindDepthBuffer)
62     {
63         FragDepthTestResources resources;
64         setupResources(resources);
65         ASSERT_NE(0u, resources.program);
66         ASSERT_NE(-1, resources.depthLocation);
67         ASSERT_GL_FRAMEBUFFER_COMPLETE(GL_FRAMEBUFFER);
68         ASSERT_GL_NO_ERROR();
69 
70         glBindFramebuffer(GL_FRAMEBUFFER, resources.framebuffer);
71         if (bindDepthBuffer)
72         {
73             glFramebufferTexture2D(GL_FRAMEBUFFER, GL_DEPTH_ATTACHMENT, GL_TEXTURE_2D,
74                                    resources.depthTexture, 0);
75             EXPECT_GL_FRAMEBUFFER_COMPLETE(GL_FRAMEBUFFER);
76 
77             // Clear to the expected depth so it will be compared to the FS depth with
78             // DepthFunc(GL_EQUAL)
79             glClearDepthf(expectedDepth);
80             glDepthFunc(GL_EQUAL);
81             glEnable(GL_DEPTH_TEST);
82         }
83         else
84         {
85             glFramebufferTexture2D(GL_FRAMEBUFFER, GL_DEPTH_ATTACHMENT, GL_TEXTURE_2D, 0, 0);
86             EXPECT_GL_FRAMEBUFFER_COMPLETE(GL_FRAMEBUFFER);
87             glDisable(GL_DEPTH_TEST);
88         }
89         glUseProgram(resources.program);
90 
91         // Clear to red, the FS will write green on success
92         glClearColor(1.0f, 0.0f, 0.0f, 0.0f);
93         // Clear to the expected depth so it will be compared to the FS depth with
94         // DepthFunc(GL_EQUAL)
95 
96         glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
97         glUniform1f(resources.depthLocation, fsDepth);
98 
99         drawQuad(resources.program, "a_position", 0.0f);
100         EXPECT_GL_NO_ERROR();
101 
102         EXPECT_PIXEL_COLOR_EQ(0, 0, GLColor::green);
103         cleanupResources(resources);
104     }
105 };
106 
107 // Test that writing to gl_FragDepth works
TEST_P(FragDepthTest,DepthBufferBound)108 TEST_P(FragDepthTest, DepthBufferBound)
109 {
110     checkDepthWritten(0.5f, 0.5f, true);
111 }
112 
113 // Test that writing to gl_FragDepth with no depth buffer works.
TEST_P(FragDepthTest,DepthBufferUnbound)114 TEST_P(FragDepthTest, DepthBufferUnbound)
115 {
116     // Depth test is disabled, so the expected depth should not matter.
117     checkDepthWritten(0.f, 0.5f, false);
118 }
119 
120 GTEST_ALLOW_UNINSTANTIATED_PARAMETERIZED_TEST(FragDepthTest);
121 ANGLE_INSTANTIATE_TEST_ES3(FragDepthTest);
122