1 // Copyright (c) 2012 The Chromium Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file.
5 #include "gpu/command_buffer/service/error_state_mock.h"
6 #include "gpu/command_buffer/service/framebuffer_manager.h"
7 #include "gpu/command_buffer/service/feature_info.h"
8 #include "gpu/command_buffer/service/gpu_service_test.h"
9 #include "gpu/command_buffer/service/renderbuffer_manager.h"
10 #include "gpu/command_buffer/service/test_helper.h"
11 #include "gpu/command_buffer/service/texture_manager.h"
12 #include "testing/gtest/include/gtest/gtest.h"
13 #include "ui/gl/gl_mock.h"
16 using ::testing::Return
;
22 const GLint kMaxTextureSize
= 64;
23 const GLint kMaxCubemapSize
= 64;
24 const GLint kMaxRectangleTextureSize
= 64;
25 const GLint kMax3DTextureSize
= 256;
26 const GLint kMaxRenderbufferSize
= 64;
27 const GLint kMaxSamples
= 4;
28 const uint32 kMaxDrawBuffers
= 16;
29 const uint32 kMaxColorAttachments
= 16;
30 const bool kUseDefaultTextures
= false;
34 class FramebufferManagerTest
: public GpuServiceTest
{
36 FramebufferManagerTest()
37 : manager_(1, 1, ContextGroup::CONTEXT_TYPE_UNDEFINED
),
38 feature_info_(new FeatureInfo()) {
39 texture_manager_
.reset(new TextureManager(NULL
,
43 kMaxRectangleTextureSize
,
45 kUseDefaultTextures
));
46 renderbuffer_manager_
.reset(new RenderbufferManager(NULL
,
49 feature_info_
.get()));
51 ~FramebufferManagerTest() override
{
52 manager_
.Destroy(false);
53 texture_manager_
->Destroy(false);
54 renderbuffer_manager_
->Destroy(false);
58 FramebufferManager manager_
;
59 scoped_refptr
<FeatureInfo
> feature_info_
;
60 scoped_ptr
<TextureManager
> texture_manager_
;
61 scoped_ptr
<RenderbufferManager
> renderbuffer_manager_
;
64 TEST_F(FramebufferManagerTest
, Basic
) {
65 const GLuint kClient1Id
= 1;
66 const GLuint kService1Id
= 11;
67 const GLuint kClient2Id
= 2;
68 // Check we can create framebuffer.
69 manager_
.CreateFramebuffer(kClient1Id
, kService1Id
);
70 // Check framebuffer got created.
71 Framebuffer
* framebuffer1
= manager_
.GetFramebuffer(kClient1Id
);
72 ASSERT_TRUE(framebuffer1
!= NULL
);
73 EXPECT_FALSE(framebuffer1
->IsDeleted());
74 EXPECT_EQ(kService1Id
, framebuffer1
->service_id());
76 EXPECT_TRUE(manager_
.GetClientId(framebuffer1
->service_id(), &client_id
));
77 EXPECT_EQ(kClient1Id
, client_id
);
78 // Check we get nothing for a non-existent framebuffer.
79 EXPECT_TRUE(manager_
.GetFramebuffer(kClient2Id
) == NULL
);
80 // Check trying to a remove non-existent framebuffers does not crash.
81 manager_
.RemoveFramebuffer(kClient2Id
);
82 // Check framebuffer gets deleted when last reference is released.
83 EXPECT_CALL(*gl_
, DeleteFramebuffersEXT(1, ::testing::Pointee(kService1Id
)))
85 .RetiresOnSaturation();
86 // Check we can't get the framebuffer after we remove it.
87 manager_
.RemoveFramebuffer(kClient1Id
);
88 EXPECT_TRUE(manager_
.GetFramebuffer(kClient1Id
) == NULL
);
91 TEST_F(FramebufferManagerTest
, Destroy
) {
92 const GLuint kClient1Id
= 1;
93 const GLuint kService1Id
= 11;
94 // Check we can create framebuffer.
95 manager_
.CreateFramebuffer(kClient1Id
, kService1Id
);
96 // Check framebuffer got created.
97 Framebuffer
* framebuffer1
= manager_
.GetFramebuffer(kClient1Id
);
98 ASSERT_TRUE(framebuffer1
!= NULL
);
99 EXPECT_CALL(*gl_
, DeleteFramebuffersEXT(1, ::testing::Pointee(kService1Id
)))
101 .RetiresOnSaturation();
102 manager_
.Destroy(true);
103 // Check the resources were released.
104 framebuffer1
= manager_
.GetFramebuffer(kClient1Id
);
105 ASSERT_TRUE(framebuffer1
== NULL
);
108 class FramebufferInfoTestBase
: public GpuServiceTest
{
110 static const GLuint kClient1Id
= 1;
111 static const GLuint kService1Id
= 11;
113 explicit FramebufferInfoTestBase(ContextGroup::ContextType context_type
)
114 : manager_(kMaxDrawBuffers
, kMaxColorAttachments
, context_type
),
115 feature_info_(new FeatureInfo()) {
116 texture_manager_
.reset(new TextureManager(NULL
,
120 kMaxRectangleTextureSize
,
122 kUseDefaultTextures
));
123 renderbuffer_manager_
.reset(new RenderbufferManager(NULL
,
124 kMaxRenderbufferSize
,
126 feature_info_
.get()));
128 ~FramebufferInfoTestBase() override
{
129 manager_
.Destroy(false);
130 texture_manager_
->Destroy(false);
131 renderbuffer_manager_
->Destroy(false);
135 void SetUp() override
{
136 InitializeContext("2.0", "GL_EXT_framebuffer_object");
139 void InitializeContext(const char* gl_version
, const char* extensions
) {
140 GpuServiceTest::SetUpWithGLVersion(gl_version
, extensions
);
141 TestHelper::SetupFeatureInfoInitExpectationsWithGLVersion(gl_
.get(),
142 extensions
, "", gl_version
);
143 feature_info_
->Initialize();
144 manager_
.CreateFramebuffer(kClient1Id
, kService1Id
);
145 error_state_
.reset(new ::testing::StrictMock
<gles2::MockErrorState
>());
146 framebuffer_
= manager_
.GetFramebuffer(kClient1Id
);
147 ASSERT_TRUE(framebuffer_
!= NULL
);
150 FramebufferManager manager_
;
151 Framebuffer
* framebuffer_
;
152 scoped_refptr
<FeatureInfo
> feature_info_
;
153 scoped_ptr
<TextureManager
> texture_manager_
;
154 scoped_ptr
<RenderbufferManager
> renderbuffer_manager_
;
155 scoped_ptr
<MockErrorState
> error_state_
;
158 class FramebufferInfoTest
: public FramebufferInfoTestBase
{
160 FramebufferInfoTest()
161 : FramebufferInfoTestBase(ContextGroup::CONTEXT_TYPE_UNDEFINED
) {
165 // GCC requires these declarations, but MSVC requires they not be present
166 #ifndef COMPILER_MSVC
167 const GLuint
FramebufferInfoTestBase::kClient1Id
;
168 const GLuint
FramebufferInfoTestBase::kService1Id
;
171 TEST_F(FramebufferInfoTest
, Basic
) {
172 EXPECT_EQ(kService1Id
, framebuffer_
->service_id());
173 EXPECT_FALSE(framebuffer_
->IsDeleted());
174 EXPECT_TRUE(NULL
== framebuffer_
->GetAttachment(GL_COLOR_ATTACHMENT0
));
175 EXPECT_TRUE(NULL
== framebuffer_
->GetAttachment(GL_DEPTH_ATTACHMENT
));
176 EXPECT_TRUE(NULL
== framebuffer_
->GetAttachment(GL_STENCIL_ATTACHMENT
));
178 NULL
== framebuffer_
->GetAttachment(GL_DEPTH_STENCIL_ATTACHMENT
));
179 EXPECT_FALSE(framebuffer_
->HasDepthAttachment());
180 EXPECT_FALSE(framebuffer_
->HasStencilAttachment());
181 EXPECT_EQ(static_cast<GLenum
>(GL_FRAMEBUFFER_INCOMPLETE_MISSING_ATTACHMENT
),
182 framebuffer_
->IsPossiblyComplete());
183 EXPECT_TRUE(framebuffer_
->IsCleared());
184 EXPECT_EQ(static_cast<GLenum
>(0), framebuffer_
->GetColorAttachmentFormat());
185 EXPECT_FALSE(manager_
.IsComplete(framebuffer_
));
188 TEST_F(FramebufferInfoTest
, AttachRenderbuffer
) {
189 const GLuint kRenderbufferClient1Id
= 33;
190 const GLuint kRenderbufferService1Id
= 333;
191 const GLuint kRenderbufferClient2Id
= 34;
192 const GLuint kRenderbufferService2Id
= 334;
193 const GLuint kRenderbufferClient3Id
= 35;
194 const GLuint kRenderbufferService3Id
= 335;
195 const GLuint kRenderbufferClient4Id
= 36;
196 const GLuint kRenderbufferService4Id
= 336;
197 const GLsizei kWidth1
= 16;
198 const GLsizei kHeight1
= 32;
199 const GLenum kFormat1
= GL_RGBA4
;
200 const GLenum kBadFormat1
= GL_DEPTH_COMPONENT16
;
201 const GLsizei kSamples1
= 0;
202 const GLsizei kWidth2
= 16;
203 const GLsizei kHeight2
= 32;
204 const GLenum kFormat2
= GL_DEPTH_COMPONENT16
;
205 const GLsizei kSamples2
= 0;
206 const GLsizei kWidth3
= 16;
207 const GLsizei kHeight3
= 32;
208 const GLenum kFormat3
= GL_STENCIL_INDEX8
;
209 const GLsizei kSamples3
= 0;
210 const GLsizei kWidth4
= 16;
211 const GLsizei kHeight4
= 32;
212 const GLenum kFormat4
= GL_STENCIL_INDEX8
;
213 const GLsizei kSamples4
= 0;
215 EXPECT_FALSE(framebuffer_
->HasUnclearedAttachment(GL_COLOR_ATTACHMENT0
));
216 EXPECT_FALSE(framebuffer_
->HasUnclearedAttachment(GL_DEPTH_ATTACHMENT
));
217 EXPECT_FALSE(framebuffer_
->HasUnclearedAttachment(GL_STENCIL_ATTACHMENT
));
219 framebuffer_
->HasUnclearedAttachment(GL_DEPTH_STENCIL_ATTACHMENT
));
221 renderbuffer_manager_
->CreateRenderbuffer(
222 kRenderbufferClient1Id
, kRenderbufferService1Id
);
223 Renderbuffer
* renderbuffer1
=
224 renderbuffer_manager_
->GetRenderbuffer(kRenderbufferClient1Id
);
225 ASSERT_TRUE(renderbuffer1
!= NULL
);
227 // check adding one attachment
228 framebuffer_
->AttachRenderbuffer(GL_COLOR_ATTACHMENT0
, renderbuffer1
);
229 EXPECT_FALSE(framebuffer_
->HasUnclearedAttachment(GL_COLOR_ATTACHMENT0
));
230 EXPECT_FALSE(framebuffer_
->HasUnclearedAttachment(GL_DEPTH_ATTACHMENT
));
231 EXPECT_EQ(static_cast<GLenum
>(GL_RGBA4
),
232 framebuffer_
->GetColorAttachmentFormat());
233 EXPECT_FALSE(framebuffer_
->HasDepthAttachment());
234 EXPECT_FALSE(framebuffer_
->HasStencilAttachment());
235 EXPECT_EQ(static_cast<GLenum
>(GL_FRAMEBUFFER_INCOMPLETE_ATTACHMENT
),
236 framebuffer_
->IsPossiblyComplete());
237 EXPECT_TRUE(framebuffer_
->IsCleared());
239 // Try a format that's not good for COLOR_ATTACHMENT0.
240 renderbuffer_manager_
->SetInfo(
241 renderbuffer1
, kSamples1
, kBadFormat1
, kWidth1
, kHeight1
);
242 EXPECT_EQ(static_cast<GLenum
>(GL_FRAMEBUFFER_INCOMPLETE_ATTACHMENT
),
243 framebuffer_
->IsPossiblyComplete());
245 // Try a good format.
246 renderbuffer_manager_
->SetInfo(
247 renderbuffer1
, kSamples1
, kFormat1
, kWidth1
, kHeight1
);
248 EXPECT_EQ(static_cast<GLenum
>(kFormat1
),
249 framebuffer_
->GetColorAttachmentFormat());
250 EXPECT_FALSE(framebuffer_
->HasDepthAttachment());
251 EXPECT_FALSE(framebuffer_
->HasStencilAttachment());
252 EXPECT_EQ(static_cast<GLenum
>(GL_FRAMEBUFFER_COMPLETE
),
253 framebuffer_
->IsPossiblyComplete());
254 EXPECT_FALSE(framebuffer_
->IsCleared());
256 // check adding another
257 renderbuffer_manager_
->CreateRenderbuffer(
258 kRenderbufferClient2Id
, kRenderbufferService2Id
);
259 Renderbuffer
* renderbuffer2
=
260 renderbuffer_manager_
->GetRenderbuffer(kRenderbufferClient2Id
);
261 ASSERT_TRUE(renderbuffer2
!= NULL
);
262 framebuffer_
->AttachRenderbuffer(GL_DEPTH_ATTACHMENT
, renderbuffer2
);
263 EXPECT_TRUE(framebuffer_
->HasUnclearedAttachment(GL_COLOR_ATTACHMENT0
));
264 EXPECT_FALSE(framebuffer_
->HasUnclearedAttachment(GL_DEPTH_ATTACHMENT
));
265 EXPECT_EQ(static_cast<GLenum
>(kFormat1
),
266 framebuffer_
->GetColorAttachmentFormat());
267 EXPECT_TRUE(framebuffer_
->HasDepthAttachment());
268 EXPECT_FALSE(framebuffer_
->HasStencilAttachment());
269 // The attachment has a size of 0,0 so depending on the order of the map
270 // of attachments it could either get INCOMPLETE_ATTACHMENT because it's 0,0
271 // or INCOMPLETE_DIMENSIONS because it's not the same size as the other
273 GLenum status
= framebuffer_
->IsPossiblyComplete();
275 status
== GL_FRAMEBUFFER_INCOMPLETE_ATTACHMENT
||
276 status
== GL_FRAMEBUFFER_INCOMPLETE_DIMENSIONS_EXT
);
277 EXPECT_FALSE(framebuffer_
->IsCleared());
279 renderbuffer_manager_
->SetInfo(
280 renderbuffer2
, kSamples2
, kFormat2
, kWidth2
, kHeight2
);
281 EXPECT_EQ(static_cast<GLenum
>(GL_FRAMEBUFFER_COMPLETE
),
282 framebuffer_
->IsPossiblyComplete());
283 EXPECT_FALSE(framebuffer_
->IsCleared());
284 EXPECT_TRUE(framebuffer_
->HasUnclearedAttachment(GL_DEPTH_ATTACHMENT
));
286 // check marking them as cleared.
287 manager_
.MarkAttachmentsAsCleared(
288 framebuffer_
, renderbuffer_manager_
.get(), texture_manager_
.get());
289 EXPECT_FALSE(framebuffer_
->HasUnclearedAttachment(GL_COLOR_ATTACHMENT0
));
290 EXPECT_FALSE(framebuffer_
->HasUnclearedAttachment(GL_DEPTH_ATTACHMENT
));
291 EXPECT_EQ(static_cast<GLenum
>(GL_FRAMEBUFFER_COMPLETE
),
292 framebuffer_
->IsPossiblyComplete());
293 EXPECT_TRUE(framebuffer_
->IsCleared());
295 // Check adding one that is already cleared.
296 renderbuffer_manager_
->CreateRenderbuffer(
297 kRenderbufferClient3Id
, kRenderbufferService3Id
);
298 Renderbuffer
* renderbuffer3
=
299 renderbuffer_manager_
->GetRenderbuffer(kRenderbufferClient3Id
);
300 ASSERT_TRUE(renderbuffer3
!= NULL
);
301 renderbuffer_manager_
->SetInfo(
302 renderbuffer3
, kSamples3
, kFormat3
, kWidth3
, kHeight3
);
303 renderbuffer_manager_
->SetCleared(renderbuffer3
, true);
305 framebuffer_
->AttachRenderbuffer(GL_STENCIL_ATTACHMENT
, renderbuffer3
);
306 EXPECT_FALSE(framebuffer_
->HasUnclearedAttachment(GL_STENCIL_ATTACHMENT
));
307 EXPECT_EQ(static_cast<GLenum
>(kFormat1
),
308 framebuffer_
->GetColorAttachmentFormat());
309 EXPECT_TRUE(framebuffer_
->HasDepthAttachment());
310 EXPECT_TRUE(framebuffer_
->HasStencilAttachment());
311 EXPECT_EQ(static_cast<GLenum
>(GL_FRAMEBUFFER_COMPLETE
),
312 framebuffer_
->IsPossiblyComplete());
313 EXPECT_TRUE(framebuffer_
->IsCleared());
315 // Check marking the renderbuffer as unclared.
316 renderbuffer_manager_
->SetInfo(
317 renderbuffer1
, kSamples1
, kFormat1
, kWidth1
, kHeight1
);
318 EXPECT_EQ(static_cast<GLenum
>(kFormat1
),
319 framebuffer_
->GetColorAttachmentFormat());
320 EXPECT_TRUE(framebuffer_
->HasDepthAttachment());
321 EXPECT_TRUE(framebuffer_
->HasStencilAttachment());
322 EXPECT_EQ(static_cast<GLenum
>(GL_FRAMEBUFFER_COMPLETE
),
323 framebuffer_
->IsPossiblyComplete());
324 EXPECT_FALSE(framebuffer_
->IsCleared());
326 const Framebuffer::Attachment
* attachment
=
327 framebuffer_
->GetAttachment(GL_COLOR_ATTACHMENT0
);
328 ASSERT_TRUE(attachment
!= NULL
);
329 EXPECT_EQ(kWidth1
, attachment
->width());
330 EXPECT_EQ(kHeight1
, attachment
->height());
331 EXPECT_EQ(kSamples1
, attachment
->samples());
332 EXPECT_EQ(kFormat1
, attachment
->internal_format());
333 EXPECT_FALSE(attachment
->cleared());
335 EXPECT_TRUE(framebuffer_
->HasUnclearedAttachment(GL_COLOR_ATTACHMENT0
));
338 manager_
.MarkAttachmentsAsCleared(
339 framebuffer_
, renderbuffer_manager_
.get(), texture_manager_
.get());
340 EXPECT_FALSE(framebuffer_
->HasUnclearedAttachment(GL_COLOR_ATTACHMENT0
));
341 EXPECT_TRUE(framebuffer_
->IsCleared());
343 // Check replacing an attachment
344 renderbuffer_manager_
->CreateRenderbuffer(
345 kRenderbufferClient4Id
, kRenderbufferService4Id
);
346 Renderbuffer
* renderbuffer4
=
347 renderbuffer_manager_
->GetRenderbuffer(kRenderbufferClient4Id
);
348 ASSERT_TRUE(renderbuffer4
!= NULL
);
349 renderbuffer_manager_
->SetInfo(
350 renderbuffer4
, kSamples4
, kFormat4
, kWidth4
, kHeight4
);
352 framebuffer_
->AttachRenderbuffer(GL_STENCIL_ATTACHMENT
, renderbuffer4
);
353 EXPECT_TRUE(framebuffer_
->HasUnclearedAttachment(GL_STENCIL_ATTACHMENT
));
354 EXPECT_FALSE(framebuffer_
->IsCleared());
356 attachment
= framebuffer_
->GetAttachment(GL_STENCIL_ATTACHMENT
);
357 ASSERT_TRUE(attachment
!= NULL
);
358 EXPECT_EQ(kWidth4
, attachment
->width());
359 EXPECT_EQ(kHeight4
, attachment
->height());
360 EXPECT_EQ(kSamples4
, attachment
->samples());
361 EXPECT_EQ(kFormat4
, attachment
->internal_format());
362 EXPECT_FALSE(attachment
->cleared());
363 EXPECT_EQ(static_cast<GLenum
>(GL_FRAMEBUFFER_COMPLETE
),
364 framebuffer_
->IsPossiblyComplete());
366 // Check changing an attachment.
367 renderbuffer_manager_
->SetInfo(
368 renderbuffer4
, kSamples4
, kFormat4
, kWidth4
+ 1, kHeight4
);
370 attachment
= framebuffer_
->GetAttachment(GL_STENCIL_ATTACHMENT
);
371 ASSERT_TRUE(attachment
!= NULL
);
372 EXPECT_EQ(kWidth4
+ 1, attachment
->width());
373 EXPECT_EQ(kHeight4
, attachment
->height());
374 EXPECT_EQ(kSamples4
, attachment
->samples());
375 EXPECT_EQ(kFormat4
, attachment
->internal_format());
376 EXPECT_FALSE(attachment
->cleared());
377 EXPECT_FALSE(framebuffer_
->IsCleared());
378 EXPECT_EQ(static_cast<GLenum
>(GL_FRAMEBUFFER_INCOMPLETE_DIMENSIONS_EXT
),
379 framebuffer_
->IsPossiblyComplete());
381 // Check removing it.
382 framebuffer_
->AttachRenderbuffer(GL_STENCIL_ATTACHMENT
, NULL
);
383 EXPECT_FALSE(framebuffer_
->HasUnclearedAttachment(GL_STENCIL_ATTACHMENT
));
384 EXPECT_EQ(static_cast<GLenum
>(kFormat1
),
385 framebuffer_
->GetColorAttachmentFormat());
386 EXPECT_TRUE(framebuffer_
->HasDepthAttachment());
387 EXPECT_FALSE(framebuffer_
->HasStencilAttachment());
389 EXPECT_TRUE(framebuffer_
->IsCleared());
390 EXPECT_EQ(static_cast<GLenum
>(GL_FRAMEBUFFER_COMPLETE
),
391 framebuffer_
->IsPossiblyComplete());
393 // Remove depth, Set color to 0 size.
394 framebuffer_
->AttachRenderbuffer(GL_DEPTH_ATTACHMENT
, NULL
);
395 renderbuffer_manager_
->SetInfo(renderbuffer1
, kSamples1
, kFormat1
, 0, 0);
396 EXPECT_EQ(static_cast<GLenum
>(GL_FRAMEBUFFER_INCOMPLETE_ATTACHMENT
),
397 framebuffer_
->IsPossiblyComplete());
400 framebuffer_
->AttachRenderbuffer(GL_COLOR_ATTACHMENT0
, NULL
);
401 EXPECT_EQ(static_cast<GLenum
>(GL_FRAMEBUFFER_INCOMPLETE_MISSING_ATTACHMENT
),
402 framebuffer_
->IsPossiblyComplete());
405 TEST_F(FramebufferInfoTest
, AttachTexture
) {
406 const GLuint kTextureClient1Id
= 33;
407 const GLuint kTextureService1Id
= 333;
408 const GLuint kTextureClient2Id
= 34;
409 const GLuint kTextureService2Id
= 334;
410 const GLint kDepth
= 1;
411 const GLint kBorder
= 0;
412 const GLenum kType
= GL_UNSIGNED_BYTE
;
413 const GLsizei kWidth1
= 16;
414 const GLsizei kHeight1
= 32;
415 const GLint kLevel1
= 0;
416 const GLenum kFormat1
= GL_RGBA
;
417 const GLenum kBadFormat1
= GL_DEPTH_COMPONENT16
;
418 const GLenum kTarget1
= GL_TEXTURE_2D
;
419 const GLsizei kSamples1
= 0;
420 const GLsizei kWidth2
= 16;
421 const GLsizei kHeight2
= 32;
422 const GLint kLevel2
= 0;
423 const GLenum kFormat2
= GL_RGB
;
424 const GLenum kTarget2
= GL_TEXTURE_2D
;
425 const GLsizei kSamples2
= 0;
426 const GLsizei kWidth3
= 75;
427 const GLsizei kHeight3
= 123;
428 const GLint kLevel3
= 0;
429 const GLenum kFormat3
= GL_RGB565
;
430 const GLsizei kSamples3
= 0;
431 EXPECT_FALSE(framebuffer_
->HasUnclearedAttachment(GL_COLOR_ATTACHMENT0
));
432 EXPECT_FALSE(framebuffer_
->HasUnclearedAttachment(GL_DEPTH_ATTACHMENT
));
433 EXPECT_FALSE(framebuffer_
->HasUnclearedAttachment(GL_STENCIL_ATTACHMENT
));
435 framebuffer_
->HasUnclearedAttachment(GL_DEPTH_STENCIL_ATTACHMENT
));
436 EXPECT_EQ(static_cast<GLenum
>(GL_FRAMEBUFFER_INCOMPLETE_MISSING_ATTACHMENT
),
437 framebuffer_
->IsPossiblyComplete());
439 texture_manager_
->CreateTexture(kTextureClient1Id
, kTextureService1Id
);
440 scoped_refptr
<TextureRef
> texture1(
441 texture_manager_
->GetTexture(kTextureClient1Id
));
442 ASSERT_TRUE(texture1
.get() != NULL
);
444 // check adding one attachment
445 framebuffer_
->AttachTexture(
446 GL_COLOR_ATTACHMENT0
, texture1
.get(), kTarget1
, kLevel1
, kSamples1
);
447 EXPECT_FALSE(framebuffer_
->HasUnclearedAttachment(GL_COLOR_ATTACHMENT0
));
448 EXPECT_EQ(static_cast<GLenum
>(GL_FRAMEBUFFER_INCOMPLETE_ATTACHMENT
),
449 framebuffer_
->IsPossiblyComplete());
450 EXPECT_TRUE(framebuffer_
->IsCleared());
451 EXPECT_EQ(static_cast<GLenum
>(0), framebuffer_
->GetColorAttachmentFormat());
453 // Try format that doesn't work with COLOR_ATTACHMENT0
454 texture_manager_
->SetTarget(texture1
.get(), GL_TEXTURE_2D
);
455 texture_manager_
->SetLevelInfo(
456 texture1
.get(), GL_TEXTURE_2D
, kLevel1
, kBadFormat1
, kWidth1
, kHeight1
,
457 kDepth
, kBorder
, kBadFormat1
, kType
, gfx::Rect(kWidth1
, kHeight1
));
458 EXPECT_EQ(static_cast<GLenum
>(GL_FRAMEBUFFER_INCOMPLETE_ATTACHMENT
),
459 framebuffer_
->IsPossiblyComplete());
461 // Try a good format.
462 texture_manager_
->SetLevelInfo(texture1
.get(), GL_TEXTURE_2D
, kLevel1
,
463 kFormat1
, kWidth1
, kHeight1
, kDepth
, kBorder
,
464 kFormat1
, kType
, gfx::Rect());
465 EXPECT_EQ(static_cast<GLenum
>(GL_FRAMEBUFFER_COMPLETE
),
466 framebuffer_
->IsPossiblyComplete());
467 EXPECT_FALSE(framebuffer_
->IsCleared());
468 texture_manager_
->SetLevelInfo(texture1
.get(), GL_TEXTURE_2D
, kLevel1
,
469 kFormat1
, kWidth1
, kHeight1
, kDepth
, kBorder
,
470 kFormat1
, kType
, gfx::Rect(kWidth1
, kHeight1
));
471 EXPECT_EQ(static_cast<GLenum
>(GL_FRAMEBUFFER_COMPLETE
),
472 framebuffer_
->IsPossiblyComplete());
473 EXPECT_TRUE(framebuffer_
->IsCleared());
474 EXPECT_EQ(static_cast<GLenum
>(kFormat1
),
475 framebuffer_
->GetColorAttachmentFormat());
477 const Framebuffer::Attachment
* attachment
=
478 framebuffer_
->GetAttachment(GL_COLOR_ATTACHMENT0
);
479 ASSERT_TRUE(attachment
!= NULL
);
480 EXPECT_EQ(kWidth1
, attachment
->width());
481 EXPECT_EQ(kHeight1
, attachment
->height());
482 EXPECT_EQ(kSamples1
, attachment
->samples());
483 EXPECT_EQ(kFormat1
, attachment
->internal_format());
484 EXPECT_TRUE(attachment
->cleared());
486 // Check replacing an attachment
487 texture_manager_
->CreateTexture(kTextureClient2Id
, kTextureService2Id
);
488 scoped_refptr
<TextureRef
> texture2(
489 texture_manager_
->GetTexture(kTextureClient2Id
));
490 ASSERT_TRUE(texture2
.get() != NULL
);
491 texture_manager_
->SetTarget(texture2
.get(), GL_TEXTURE_2D
);
492 texture_manager_
->SetLevelInfo(texture2
.get(), GL_TEXTURE_2D
, kLevel2
,
493 kFormat2
, kWidth2
, kHeight2
, kDepth
, kBorder
,
494 kFormat2
, kType
, gfx::Rect(kWidth2
, kHeight2
));
496 framebuffer_
->AttachTexture(
497 GL_COLOR_ATTACHMENT0
, texture2
.get(), kTarget2
, kLevel2
, kSamples2
);
498 EXPECT_EQ(static_cast<GLenum
>(kFormat2
),
499 framebuffer_
->GetColorAttachmentFormat());
500 EXPECT_EQ(static_cast<GLenum
>(GL_FRAMEBUFFER_COMPLETE
),
501 framebuffer_
->IsPossiblyComplete());
502 EXPECT_TRUE(framebuffer_
->IsCleared());
504 attachment
= framebuffer_
->GetAttachment(GL_COLOR_ATTACHMENT0
);
505 ASSERT_TRUE(attachment
!= NULL
);
506 EXPECT_EQ(kWidth2
, attachment
->width());
507 EXPECT_EQ(kHeight2
, attachment
->height());
508 EXPECT_EQ(kSamples2
, attachment
->samples());
509 EXPECT_EQ(kFormat2
, attachment
->internal_format());
510 EXPECT_TRUE(attachment
->cleared());
512 // Check changing attachment
513 texture_manager_
->SetLevelInfo(texture2
.get(), GL_TEXTURE_2D
, kLevel3
,
514 kFormat3
, kWidth3
, kHeight3
, kDepth
, kBorder
,
515 kFormat3
, kType
, gfx::Rect());
516 attachment
= framebuffer_
->GetAttachment(GL_COLOR_ATTACHMENT0
);
517 ASSERT_TRUE(attachment
!= NULL
);
518 EXPECT_EQ(kWidth3
, attachment
->width());
519 EXPECT_EQ(kHeight3
, attachment
->height());
520 EXPECT_EQ(kSamples3
, attachment
->samples());
521 EXPECT_EQ(kFormat3
, attachment
->internal_format());
522 EXPECT_FALSE(attachment
->cleared());
523 EXPECT_EQ(static_cast<GLenum
>(kFormat3
),
524 framebuffer_
->GetColorAttachmentFormat());
525 EXPECT_EQ(static_cast<GLenum
>(GL_FRAMEBUFFER_COMPLETE
),
526 framebuffer_
->IsPossiblyComplete());
527 EXPECT_FALSE(framebuffer_
->IsCleared());
530 texture_manager_
->SetLevelInfo(texture2
.get(), GL_TEXTURE_2D
, kLevel3
,
531 kFormat3
, 0, 0, kDepth
, kBorder
, kFormat3
,
533 EXPECT_EQ(static_cast<GLenum
>(GL_FRAMEBUFFER_INCOMPLETE_ATTACHMENT
),
534 framebuffer_
->IsPossiblyComplete());
536 // Check removing it.
537 framebuffer_
->AttachTexture(GL_COLOR_ATTACHMENT0
, NULL
, 0, 0, 0);
538 EXPECT_TRUE(framebuffer_
->GetAttachment(GL_COLOR_ATTACHMENT0
) == NULL
);
539 EXPECT_EQ(static_cast<GLenum
>(0), framebuffer_
->GetColorAttachmentFormat());
541 EXPECT_EQ(static_cast<GLenum
>(GL_FRAMEBUFFER_INCOMPLETE_MISSING_ATTACHMENT
),
542 framebuffer_
->IsPossiblyComplete());
543 EXPECT_TRUE(framebuffer_
->IsCleared());
546 TEST_F(FramebufferInfoTest
, DrawBuffers
) {
547 const GLuint kTextureClientId
[] = { 33, 34 };
548 const GLuint kTextureServiceId
[] = { 333, 334 };
550 for (GLenum i
= GL_COLOR_ATTACHMENT0
;
551 i
< GL_COLOR_ATTACHMENT0
+ kMaxColorAttachments
; ++i
) {
552 EXPECT_FALSE(framebuffer_
->HasUnclearedAttachment(i
));
554 EXPECT_FALSE(framebuffer_
->HasUnclearedColorAttachments());
556 EXPECT_EQ(static_cast<GLenum
>(GL_COLOR_ATTACHMENT0
),
557 framebuffer_
->GetDrawBuffer(GL_DRAW_BUFFER0_ARB
));
558 for (GLenum i
= GL_DRAW_BUFFER1_ARB
;
559 i
< GL_DRAW_BUFFER0_ARB
+ kMaxDrawBuffers
; ++i
) {
560 EXPECT_EQ(static_cast<GLenum
>(GL_NONE
),
561 framebuffer_
->GetDrawBuffer(i
));
564 for (size_t ii
= 0; ii
< arraysize(kTextureClientId
); ++ii
) {
565 texture_manager_
->CreateTexture(
566 kTextureClientId
[ii
], kTextureServiceId
[ii
]);
567 scoped_refptr
<TextureRef
> texture(
568 texture_manager_
->GetTexture(kTextureClientId
[ii
]));
569 ASSERT_TRUE(texture
.get() != NULL
);
571 framebuffer_
->AttachTexture(
572 GL_COLOR_ATTACHMENT0
+ ii
, texture
.get(), GL_TEXTURE_2D
, 0, 0);
574 framebuffer_
->HasUnclearedAttachment(GL_COLOR_ATTACHMENT0
+ ii
));
576 const Framebuffer::Attachment
* attachment
=
577 framebuffer_
->GetAttachment(GL_COLOR_ATTACHMENT0
+ ii
);
578 ASSERT_TRUE(attachment
!= NULL
);
579 EXPECT_TRUE(attachment
->cleared());
581 EXPECT_TRUE(framebuffer_
->IsCleared());
582 EXPECT_FALSE(framebuffer_
->HasUnclearedColorAttachments());
584 // Set a texture as uncleared.
585 scoped_refptr
<TextureRef
> texture1(
586 texture_manager_
->GetTexture(kTextureClientId
[1]));
587 texture_manager_
->SetTarget(texture1
.get(), GL_TEXTURE_2D
);
588 texture_manager_
->SetLevelInfo(texture1
.get(), GL_TEXTURE_2D
, 0, GL_RGBA
, 4,
589 4, 1, 0, GL_RGBA
, GL_UNSIGNED_BYTE
,
592 const Framebuffer::Attachment
* attachment1
=
593 framebuffer_
->GetAttachment(GL_COLOR_ATTACHMENT1
);
594 ASSERT_TRUE(attachment1
!= NULL
);
595 EXPECT_FALSE(attachment1
->cleared());
596 EXPECT_FALSE(framebuffer_
->IsCleared());
597 EXPECT_TRUE(framebuffer_
->HasUnclearedAttachment(GL_COLOR_ATTACHMENT1
));
598 EXPECT_TRUE(framebuffer_
->HasUnclearedColorAttachments());
600 GLenum buffers
[] = { GL_COLOR_ATTACHMENT0
, GL_COLOR_ATTACHMENT1
};
601 framebuffer_
->SetDrawBuffers(2, buffers
);
602 EXPECT_EQ(static_cast<GLenum
>(GL_COLOR_ATTACHMENT0
),
603 framebuffer_
->GetDrawBuffer(GL_DRAW_BUFFER0_ARB
));
604 EXPECT_EQ(static_cast<GLenum
>(GL_COLOR_ATTACHMENT1
),
605 framebuffer_
->GetDrawBuffer(GL_DRAW_BUFFER1_ARB
));
606 for (GLenum i
= GL_DRAW_BUFFER2_ARB
;
607 i
< GL_DRAW_BUFFER0_ARB
+ kMaxDrawBuffers
; ++i
) {
608 EXPECT_EQ(static_cast<GLenum
>(GL_NONE
),
609 framebuffer_
->GetDrawBuffer(i
));
613 framebuffer_
->PrepareDrawBuffersForClear();
614 framebuffer_
->RestoreDrawBuffersAfterClear();
616 // Now we disable a draw buffer 1.
617 buffers
[1] = GL_NONE
;
618 framebuffer_
->SetDrawBuffers(2, buffers
);
619 // We will enable the disabled draw buffer for clear(), and disable it
621 EXPECT_CALL(*gl_
, DrawBuffersARB(kMaxDrawBuffers
, _
))
623 .RetiresOnSaturation();
624 framebuffer_
->PrepareDrawBuffersForClear();
625 EXPECT_CALL(*gl_
, DrawBuffersARB(kMaxDrawBuffers
, _
))
627 .RetiresOnSaturation();
628 framebuffer_
->RestoreDrawBuffersAfterClear();
630 // Now remove draw buffer 1's attachment.
631 framebuffer_
->AttachTexture(GL_COLOR_ATTACHMENT1
, NULL
, 0, 0, 0);
632 EXPECT_TRUE(framebuffer_
->GetAttachment(GL_COLOR_ATTACHMENT1
) == NULL
);
635 framebuffer_
->PrepareDrawBuffersForClear();
636 framebuffer_
->RestoreDrawBuffersAfterClear();
639 class FramebufferInfoFloatTest
: public FramebufferInfoTest
{
641 FramebufferInfoFloatTest()
642 : FramebufferInfoTest() {
644 ~FramebufferInfoFloatTest() override
{}
647 void SetUp() override
{
648 InitializeContext("OpenGL ES 3.0",
649 "GL_OES_texture_float GL_EXT_color_buffer_float");
653 TEST_F(FramebufferInfoFloatTest
, AttachFloatTexture
) {
654 const GLuint kTextureClientId
= 33;
655 const GLuint kTextureServiceId
= 333;
656 const GLint kDepth
= 1;
657 const GLint kBorder
= 0;
658 const GLenum kType
= GL_FLOAT
;
659 const GLsizei kWidth
= 16;
660 const GLsizei kHeight
= 32;
661 const GLint kLevel
= 0;
662 const GLenum kFormat
= GL_RGBA
;
663 const GLenum kInternalFormat
= GL_RGBA32F
;
664 const GLenum kTarget
= GL_TEXTURE_2D
;
665 const GLsizei kSamples
= 0;
666 EXPECT_FALSE(framebuffer_
->HasUnclearedAttachment(GL_COLOR_ATTACHMENT0
));
667 EXPECT_FALSE(framebuffer_
->HasUnclearedAttachment(GL_DEPTH_ATTACHMENT
));
668 EXPECT_FALSE(framebuffer_
->HasUnclearedAttachment(GL_STENCIL_ATTACHMENT
));
670 texture_manager_
->CreateTexture(kTextureClientId
, kTextureServiceId
);
671 scoped_refptr
<TextureRef
> texture(
672 texture_manager_
->GetTexture(kTextureClientId
));
673 ASSERT_TRUE(texture
.get() != NULL
);
675 framebuffer_
->AttachTexture(
676 GL_COLOR_ATTACHMENT0
, texture
.get(), kTarget
, kLevel
, kSamples
);
677 EXPECT_EQ(static_cast<GLenum
>(0), framebuffer_
->GetColorAttachmentFormat());
679 texture_manager_
->SetTarget(texture
.get(), GL_TEXTURE_2D
);
680 texture_manager_
->SetLevelInfo(texture
.get(), GL_TEXTURE_2D
, kLevel
,
681 kInternalFormat
, kWidth
, kHeight
, kDepth
,
682 kBorder
, kFormat
, kType
, gfx::Rect());
683 // Texture with a sized float internalformat is allowed as an attachment
684 // since float color attachment extension is present.
685 EXPECT_EQ(static_cast<GLenum
>(GL_FRAMEBUFFER_COMPLETE
),
686 framebuffer_
->IsPossiblyComplete());
689 TEST_F(FramebufferInfoTest
, UnbindRenderbuffer
) {
690 const GLuint kRenderbufferClient1Id
= 33;
691 const GLuint kRenderbufferService1Id
= 333;
692 const GLuint kRenderbufferClient2Id
= 34;
693 const GLuint kRenderbufferService2Id
= 334;
695 renderbuffer_manager_
->CreateRenderbuffer(
696 kRenderbufferClient1Id
, kRenderbufferService1Id
);
697 Renderbuffer
* renderbuffer1
=
698 renderbuffer_manager_
->GetRenderbuffer(kRenderbufferClient1Id
);
699 ASSERT_TRUE(renderbuffer1
!= NULL
);
700 renderbuffer_manager_
->CreateRenderbuffer(
701 kRenderbufferClient2Id
, kRenderbufferService2Id
);
702 Renderbuffer
* renderbuffer2
=
703 renderbuffer_manager_
->GetRenderbuffer(kRenderbufferClient2Id
);
704 ASSERT_TRUE(renderbuffer2
!= NULL
);
706 // Attach to 2 attachment points.
707 framebuffer_
->AttachRenderbuffer(GL_COLOR_ATTACHMENT0
, renderbuffer1
);
708 framebuffer_
->AttachRenderbuffer(GL_DEPTH_ATTACHMENT
, renderbuffer1
);
709 // Check they were attached.
710 EXPECT_TRUE(framebuffer_
->GetAttachment(GL_COLOR_ATTACHMENT0
) != NULL
);
711 EXPECT_TRUE(framebuffer_
->GetAttachment(GL_DEPTH_ATTACHMENT
) != NULL
);
712 // Unbind unattached renderbuffer.
713 framebuffer_
->UnbindRenderbuffer(GL_RENDERBUFFER
, renderbuffer2
);
715 EXPECT_TRUE(framebuffer_
->GetAttachment(GL_COLOR_ATTACHMENT0
) != NULL
);
716 EXPECT_TRUE(framebuffer_
->GetAttachment(GL_DEPTH_ATTACHMENT
) != NULL
);
717 // Unbind renderbuffer.
718 framebuffer_
->UnbindRenderbuffer(GL_RENDERBUFFER
, renderbuffer1
);
719 // Check they were detached
720 EXPECT_TRUE(framebuffer_
->GetAttachment(GL_COLOR_ATTACHMENT0
) == NULL
);
721 EXPECT_TRUE(framebuffer_
->GetAttachment(GL_DEPTH_ATTACHMENT
) == NULL
);
724 TEST_F(FramebufferInfoTest
, UnbindTexture
) {
725 const GLuint kTextureClient1Id
= 33;
726 const GLuint kTextureService1Id
= 333;
727 const GLuint kTextureClient2Id
= 34;
728 const GLuint kTextureService2Id
= 334;
729 const GLenum kTarget1
= GL_TEXTURE_2D
;
730 const GLint kLevel1
= 0;
731 const GLint kSamples1
= 0;
733 texture_manager_
->CreateTexture(kTextureClient1Id
, kTextureService1Id
);
734 scoped_refptr
<TextureRef
> texture1(
735 texture_manager_
->GetTexture(kTextureClient1Id
));
736 ASSERT_TRUE(texture1
.get() != NULL
);
737 texture_manager_
->CreateTexture(kTextureClient2Id
, kTextureService2Id
);
738 scoped_refptr
<TextureRef
> texture2(
739 texture_manager_
->GetTexture(kTextureClient2Id
));
740 ASSERT_TRUE(texture2
.get() != NULL
);
742 // Attach to 2 attachment points.
743 framebuffer_
->AttachTexture(
744 GL_COLOR_ATTACHMENT0
, texture1
.get(), kTarget1
, kLevel1
, kSamples1
);
745 framebuffer_
->AttachTexture(
746 GL_DEPTH_ATTACHMENT
, texture1
.get(), kTarget1
, kLevel1
, kSamples1
);
747 // Check they were attached.
748 EXPECT_TRUE(framebuffer_
->GetAttachment(GL_COLOR_ATTACHMENT0
) != NULL
);
749 EXPECT_TRUE(framebuffer_
->GetAttachment(GL_DEPTH_ATTACHMENT
) != NULL
);
750 // Unbind unattached texture.
751 framebuffer_
->UnbindTexture(kTarget1
, texture2
.get());
753 EXPECT_TRUE(framebuffer_
->GetAttachment(GL_COLOR_ATTACHMENT0
) != NULL
);
754 EXPECT_TRUE(framebuffer_
->GetAttachment(GL_DEPTH_ATTACHMENT
) != NULL
);
756 framebuffer_
->UnbindTexture(kTarget1
, texture1
.get());
757 // Check they were detached
758 EXPECT_TRUE(framebuffer_
->GetAttachment(GL_COLOR_ATTACHMENT0
) == NULL
);
759 EXPECT_TRUE(framebuffer_
->GetAttachment(GL_DEPTH_ATTACHMENT
) == NULL
);
762 TEST_F(FramebufferInfoTest
, IsCompleteMarkAsComplete
) {
763 const GLuint kRenderbufferClient1Id
= 33;
764 const GLuint kRenderbufferService1Id
= 333;
765 const GLuint kTextureClient2Id
= 34;
766 const GLuint kTextureService2Id
= 334;
767 const GLenum kTarget1
= GL_TEXTURE_2D
;
768 const GLint kLevel1
= 0;
769 const GLint kSamples1
= 0;
771 renderbuffer_manager_
->CreateRenderbuffer(
772 kRenderbufferClient1Id
, kRenderbufferService1Id
);
773 Renderbuffer
* renderbuffer1
=
774 renderbuffer_manager_
->GetRenderbuffer(kRenderbufferClient1Id
);
775 ASSERT_TRUE(renderbuffer1
!= NULL
);
776 texture_manager_
->CreateTexture(kTextureClient2Id
, kTextureService2Id
);
777 scoped_refptr
<TextureRef
> texture2(
778 texture_manager_
->GetTexture(kTextureClient2Id
));
779 ASSERT_TRUE(texture2
.get() != NULL
);
781 // Check MarkAsComlete marks as complete.
782 manager_
.MarkAsComplete(framebuffer_
);
783 EXPECT_TRUE(manager_
.IsComplete(framebuffer_
));
785 // Check at attaching marks as not complete.
786 framebuffer_
->AttachTexture(
787 GL_COLOR_ATTACHMENT0
, texture2
.get(), kTarget1
, kLevel1
, kSamples1
);
788 EXPECT_FALSE(manager_
.IsComplete(framebuffer_
));
789 manager_
.MarkAsComplete(framebuffer_
);
790 EXPECT_TRUE(manager_
.IsComplete(framebuffer_
));
791 framebuffer_
->AttachRenderbuffer(GL_DEPTH_ATTACHMENT
, renderbuffer1
);
792 EXPECT_FALSE(manager_
.IsComplete(framebuffer_
));
794 // Check MarkAttachmentsAsCleared marks as complete.
795 manager_
.MarkAttachmentsAsCleared(
796 framebuffer_
, renderbuffer_manager_
.get(), texture_manager_
.get());
797 EXPECT_TRUE(manager_
.IsComplete(framebuffer_
));
799 // Check Unbind marks as not complete.
800 framebuffer_
->UnbindRenderbuffer(GL_RENDERBUFFER
, renderbuffer1
);
801 EXPECT_FALSE(manager_
.IsComplete(framebuffer_
));
802 manager_
.MarkAsComplete(framebuffer_
);
803 EXPECT_TRUE(manager_
.IsComplete(framebuffer_
));
804 framebuffer_
->UnbindTexture(kTarget1
, texture2
.get());
805 EXPECT_FALSE(manager_
.IsComplete(framebuffer_
));
808 TEST_F(FramebufferInfoTest
, GetStatus
) {
809 const GLuint kRenderbufferClient1Id
= 33;
810 const GLuint kRenderbufferService1Id
= 333;
811 const GLuint kTextureClient2Id
= 34;
812 const GLuint kTextureService2Id
= 334;
813 const GLenum kTarget1
= GL_TEXTURE_2D
;
814 const GLint kLevel1
= 0;
815 const GLint kSamples1
= 0;
817 renderbuffer_manager_
->CreateRenderbuffer(
818 kRenderbufferClient1Id
, kRenderbufferService1Id
);
819 Renderbuffer
* renderbuffer1
=
820 renderbuffer_manager_
->GetRenderbuffer(kRenderbufferClient1Id
);
821 ASSERT_TRUE(renderbuffer1
!= NULL
);
822 texture_manager_
->CreateTexture(kTextureClient2Id
, kTextureService2Id
);
823 scoped_refptr
<TextureRef
> texture2(
824 texture_manager_
->GetTexture(kTextureClient2Id
));
825 ASSERT_TRUE(texture2
.get() != NULL
);
826 texture_manager_
->SetTarget(texture2
.get(), GL_TEXTURE_2D
);
828 EXPECT_CALL(*gl_
, CheckFramebufferStatusEXT(GL_FRAMEBUFFER
))
829 .WillOnce(Return(GL_FRAMEBUFFER_COMPLETE
))
830 .RetiresOnSaturation();
831 framebuffer_
->GetStatus(texture_manager_
.get(), GL_FRAMEBUFFER
);
833 // Check a second call for the same type does not call anything
834 if (!framebuffer_
->AllowFramebufferComboCompleteMapForTesting()) {
835 EXPECT_CALL(*gl_
, CheckFramebufferStatusEXT(GL_FRAMEBUFFER
))
836 .WillOnce(Return(GL_FRAMEBUFFER_COMPLETE
))
837 .RetiresOnSaturation();
839 framebuffer_
->GetStatus(texture_manager_
.get(), GL_FRAMEBUFFER
);
841 // Check changing the attachments calls CheckFramebufferStatus.
842 framebuffer_
->AttachTexture(
843 GL_COLOR_ATTACHMENT0
, texture2
.get(), kTarget1
, kLevel1
, kSamples1
);
844 EXPECT_CALL(*gl_
, CheckFramebufferStatusEXT(GL_FRAMEBUFFER
))
845 .WillOnce(Return(GL_FRAMEBUFFER_COMPLETE
)).RetiresOnSaturation();
846 framebuffer_
->GetStatus(texture_manager_
.get(), GL_FRAMEBUFFER
);
848 // Check a second call for the same type does not call anything.
849 if (!framebuffer_
->AllowFramebufferComboCompleteMapForTesting()) {
850 EXPECT_CALL(*gl_
, CheckFramebufferStatusEXT(GL_FRAMEBUFFER
))
851 .WillOnce(Return(GL_FRAMEBUFFER_COMPLETE
))
852 .RetiresOnSaturation();
854 framebuffer_
->GetStatus(texture_manager_
.get(), GL_FRAMEBUFFER
);
856 // Check a second call with a different target calls CheckFramebufferStatus.
857 EXPECT_CALL(*gl_
, CheckFramebufferStatusEXT(GL_READ_FRAMEBUFFER
))
858 .WillOnce(Return(GL_FRAMEBUFFER_COMPLETE
))
859 .RetiresOnSaturation();
860 framebuffer_
->GetStatus(texture_manager_
.get(), GL_READ_FRAMEBUFFER
);
862 // Check a second call for the same type does not call anything.
863 if (!framebuffer_
->AllowFramebufferComboCompleteMapForTesting()) {
864 EXPECT_CALL(*gl_
, CheckFramebufferStatusEXT(GL_READ_FRAMEBUFFER
))
865 .WillOnce(Return(GL_FRAMEBUFFER_COMPLETE
))
866 .RetiresOnSaturation();
868 framebuffer_
->GetStatus(texture_manager_
.get(), GL_READ_FRAMEBUFFER
);
870 // Check adding another attachment calls CheckFramebufferStatus.
871 framebuffer_
->AttachRenderbuffer(GL_DEPTH_ATTACHMENT
, renderbuffer1
);
872 EXPECT_CALL(*gl_
, CheckFramebufferStatusEXT(GL_READ_FRAMEBUFFER
))
873 .WillOnce(Return(GL_FRAMEBUFFER_COMPLETE
))
874 .RetiresOnSaturation();
875 framebuffer_
->GetStatus(texture_manager_
.get(), GL_READ_FRAMEBUFFER
);
877 // Check a second call for the same type does not call anything.
878 if (!framebuffer_
->AllowFramebufferComboCompleteMapForTesting()) {
879 EXPECT_CALL(*gl_
, CheckFramebufferStatusEXT(GL_READ_FRAMEBUFFER
))
880 .WillOnce(Return(GL_FRAMEBUFFER_COMPLETE
))
881 .RetiresOnSaturation();
883 framebuffer_
->GetStatus(texture_manager_
.get(), GL_READ_FRAMEBUFFER
);
885 // Check changing the format calls CheckFramebuffferStatus.
886 TestHelper::SetTexParameteriWithExpectations(gl_
.get(),
888 texture_manager_
.get(),
894 EXPECT_CALL(*gl_
, CheckFramebufferStatusEXT(GL_READ_FRAMEBUFFER
))
895 .WillOnce(Return(GL_FRAMEBUFFER_INCOMPLETE_ATTACHMENT
))
896 .WillOnce(Return(GL_FRAMEBUFFER_COMPLETE
))
897 .RetiresOnSaturation();
898 framebuffer_
->GetStatus(texture_manager_
.get(), GL_READ_FRAMEBUFFER
);
900 // Check since it did not return FRAMEBUFFER_COMPLETE that it calls
901 // CheckFramebufferStatus
902 framebuffer_
->GetStatus(texture_manager_
.get(), GL_READ_FRAMEBUFFER
);
904 // Check putting it back does not call CheckFramebufferStatus.
905 if (!framebuffer_
->AllowFramebufferComboCompleteMapForTesting()) {
906 EXPECT_CALL(*gl_
, CheckFramebufferStatusEXT(GL_READ_FRAMEBUFFER
))
907 .WillOnce(Return(GL_FRAMEBUFFER_COMPLETE
))
908 .RetiresOnSaturation();
910 TestHelper::SetTexParameteriWithExpectations(gl_
.get(),
912 texture_manager_
.get(),
917 framebuffer_
->GetStatus(texture_manager_
.get(), GL_READ_FRAMEBUFFER
);
919 // Check Unbinding does not call CheckFramebufferStatus
920 framebuffer_
->UnbindRenderbuffer(GL_RENDERBUFFER
, renderbuffer1
);
921 if (!framebuffer_
->AllowFramebufferComboCompleteMapForTesting()) {
922 EXPECT_CALL(*gl_
, CheckFramebufferStatusEXT(GL_READ_FRAMEBUFFER
))
923 .WillOnce(Return(GL_FRAMEBUFFER_COMPLETE
))
924 .RetiresOnSaturation();
926 framebuffer_
->GetStatus(texture_manager_
.get(), GL_READ_FRAMEBUFFER
);
929 class FramebufferInfoES3Test
: public FramebufferInfoTestBase
{
931 FramebufferInfoES3Test()
932 : FramebufferInfoTestBase(ContextGroup::CONTEXT_TYPE_WEBGL2
) {
936 TEST_F(FramebufferInfoES3Test
, DifferentDimensions
) {
937 const GLuint kRenderbufferClient1Id
= 33;
938 const GLuint kRenderbufferService1Id
= 333;
939 const GLuint kRenderbufferClient2Id
= 34;
940 const GLuint kRenderbufferService2Id
= 334;
941 const GLsizei kWidth1
= 16;
942 const GLsizei kHeight1
= 32;
943 const GLenum kFormat1
= GL_RGBA4
;
944 const GLsizei kSamples1
= 0;
945 const GLsizei kWidth2
= 32; // Different from kWidth1
946 const GLsizei kHeight2
= 32;
947 const GLenum kFormat2
= GL_DEPTH_COMPONENT16
;
948 const GLsizei kSamples2
= 0;
950 EXPECT_FALSE(framebuffer_
->HasUnclearedAttachment(GL_COLOR_ATTACHMENT0
));
951 EXPECT_FALSE(framebuffer_
->HasUnclearedAttachment(GL_DEPTH_ATTACHMENT
));
952 EXPECT_FALSE(framebuffer_
->HasUnclearedAttachment(GL_STENCIL_ATTACHMENT
));
954 framebuffer_
->HasUnclearedAttachment(GL_DEPTH_STENCIL_ATTACHMENT
));
956 renderbuffer_manager_
->CreateRenderbuffer(
957 kRenderbufferClient1Id
, kRenderbufferService1Id
);
958 Renderbuffer
* renderbuffer1
=
959 renderbuffer_manager_
->GetRenderbuffer(kRenderbufferClient1Id
);
960 ASSERT_TRUE(renderbuffer1
!= NULL
);
961 renderbuffer_manager_
->SetInfo(
962 renderbuffer1
, kSamples1
, kFormat1
, kWidth1
, kHeight1
);
963 framebuffer_
->AttachRenderbuffer(GL_COLOR_ATTACHMENT0
, renderbuffer1
);
965 renderbuffer_manager_
->CreateRenderbuffer(
966 kRenderbufferClient2Id
, kRenderbufferService2Id
);
967 Renderbuffer
* renderbuffer2
=
968 renderbuffer_manager_
->GetRenderbuffer(kRenderbufferClient2Id
);
969 ASSERT_TRUE(renderbuffer2
!= NULL
);
970 renderbuffer_manager_
->SetInfo(
971 renderbuffer2
, kSamples2
, kFormat2
, kWidth2
, kHeight2
);
972 framebuffer_
->AttachRenderbuffer(GL_DEPTH_ATTACHMENT
, renderbuffer2
);
974 EXPECT_EQ(static_cast<GLenum
>(GL_FRAMEBUFFER_COMPLETE
),
975 framebuffer_
->IsPossiblyComplete());