OLD | NEW |
---|---|
1 /* | 1 /* |
2 * Copyright (c) 2010, Google Inc. All rights reserved. | 2 * Copyright (c) 2010, Google Inc. All rights reserved. |
3 * | 3 * |
4 * Redistribution and use in source and binary forms, with or without | 4 * Redistribution and use in source and binary forms, with or without |
5 * modification, are permitted provided that the following conditions are | 5 * modification, are permitted provided that the following conditions are |
6 * met: | 6 * met: |
7 * | 7 * |
8 * * Redistributions of source code must retain the above copyright | 8 * * Redistributions of source code must retain the above copyright |
9 * notice, this list of conditions and the following disclaimer. | 9 * notice, this list of conditions and the following disclaimer. |
10 * * Redistributions in binary form must reproduce the above | 10 * * Redistributions in binary form must reproduce the above |
(...skipping 28 matching lines...) Expand all Loading... | |
39 #include "public/platform/Platform.h" | 39 #include "public/platform/Platform.h" |
40 #include "public/platform/WebCompositorSupport.h" | 40 #include "public/platform/WebCompositorSupport.h" |
41 #include "public/platform/WebExternalBitmap.h" | 41 #include "public/platform/WebExternalBitmap.h" |
42 #include "public/platform/WebExternalTextureLayer.h" | 42 #include "public/platform/WebExternalTextureLayer.h" |
43 #include "public/platform/WebGraphicsContext3D.h" | 43 #include "public/platform/WebGraphicsContext3D.h" |
44 #include "public/platform/WebGraphicsContext3DProvider.h" | 44 #include "public/platform/WebGraphicsContext3DProvider.h" |
45 #ifndef NDEBUG | 45 #ifndef NDEBUG |
46 #include "wtf/RefCountedLeakCounter.h" | 46 #include "wtf/RefCountedLeakCounter.h" |
47 #endif | 47 #endif |
48 | 48 |
49 #define ENABLE_WEBGL_IMAGE_CHROMIUM | |
50 | |
49 using namespace std; | 51 using namespace std; |
50 | 52 |
51 namespace WebCore { | 53 namespace WebCore { |
52 | 54 |
53 namespace { | 55 namespace { |
54 // Global resource ceiling (expressed in terms of pixels) for DrawingBuffer crea tion and resize. | 56 // Global resource ceiling (expressed in terms of pixels) for DrawingBuffer crea tion and resize. |
55 // When this limit is set, DrawingBuffer::create() and DrawingBuffer::reset() ca lls that would | 57 // When this limit is set, DrawingBuffer::create() and DrawingBuffer::reset() ca lls that would |
56 // exceed the global cap will instead clear the buffer. | 58 // exceed the global cap will instead clear the buffer. |
57 const int s_maximumResourceUsePixels = 16 * 1024 * 1024; | 59 const int s_maximumResourceUsePixels = 16 * 1024 * 1024; |
58 int s_currentResourceUsePixels = 0; | 60 int s_currentResourceUsePixels = 0; |
(...skipping 162 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
221 | 223 |
222 // We must restore the texture binding since creating new textures, | 224 // We must restore the texture binding since creating new textures, |
223 // consuming and producing mailboxes changes it. | 225 // consuming and producing mailboxes changes it. |
224 ScopedTextureUnit0BindingRestorer restorer(m_context.get(), m_activeTextureU nit, m_texture2DBinding); | 226 ScopedTextureUnit0BindingRestorer restorer(m_context.get(), m_activeTextureU nit, m_texture2DBinding); |
225 | 227 |
226 // First try to recycle an old buffer. | 228 // First try to recycle an old buffer. |
227 RefPtr<MailboxInfo> frontColorBufferMailbox = recycledMailbox(); | 229 RefPtr<MailboxInfo> frontColorBufferMailbox = recycledMailbox(); |
228 | 230 |
229 // No buffer available to recycle, create a new one. | 231 // No buffer available to recycle, create a new one. |
230 if (!frontColorBufferMailbox) { | 232 if (!frontColorBufferMailbox) { |
231 unsigned newColorBuffer = createColorTexture(m_size); | 233 unsigned newColorBuffer = createColorTexture(); |
234 allocateTextureMemory(newColorBuffer, m_size); | |
232 // Bad things happened, abandon ship. | 235 // Bad things happened, abandon ship. |
233 if (!newColorBuffer) | 236 if (!newColorBuffer) |
234 return false; | 237 return false; |
235 | 238 |
236 frontColorBufferMailbox = createNewMailbox(newColorBuffer); | 239 frontColorBufferMailbox = createNewMailbox(newColorBuffer); |
237 } | 240 } |
238 | 241 |
239 if (m_preserveDrawingBuffer == Discard) { | 242 if (m_preserveDrawingBuffer == Discard) { |
240 swap(frontColorBufferMailbox->textureId, m_colorBuffer); | 243 swap(frontColorBufferMailbox->textureId, m_colorBuffer); |
241 // It appears safe to overwrite the context's framebuffer binding in the Discard case since there will always be a | 244 // It appears safe to overwrite the context's framebuffer binding in the Discard case since there will always be a |
(...skipping 74 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
316 } | 319 } |
317 ASSERT(mailboxInfo); | 320 ASSERT(mailboxInfo); |
318 | 321 |
319 if (mailboxInfo->mailbox.syncPoint) { | 322 if (mailboxInfo->mailbox.syncPoint) { |
320 m_context->waitSyncPoint(mailboxInfo->mailbox.syncPoint); | 323 m_context->waitSyncPoint(mailboxInfo->mailbox.syncPoint); |
321 mailboxInfo->mailbox.syncPoint = 0; | 324 mailboxInfo->mailbox.syncPoint = 0; |
322 } | 325 } |
323 | 326 |
324 if (mailboxInfo->size != m_size) { | 327 if (mailboxInfo->size != m_size) { |
325 m_context->bindTexture(GL_TEXTURE_2D, mailboxInfo->textureId); | 328 m_context->bindTexture(GL_TEXTURE_2D, mailboxInfo->textureId); |
326 texImage2DResourceSafe(GL_TEXTURE_2D, 0, m_internalColorFormat, m_size.w idth(), m_size.height(), 0, m_colorFormat, GL_UNSIGNED_BYTE); | 329 allocateTextureMemory(mailboxInfo->textureId, m_size); |
327 mailboxInfo->size = m_size; | 330 mailboxInfo->size = m_size; |
328 } | 331 } |
329 | 332 |
330 return mailboxInfo.release(); | 333 return mailboxInfo.release(); |
331 } | 334 } |
332 | 335 |
333 PassRefPtr<DrawingBuffer::MailboxInfo> DrawingBuffer::createNewMailbox(unsigned textureId) | 336 PassRefPtr<DrawingBuffer::MailboxInfo> DrawingBuffer::createNewMailbox(unsigned textureId) |
334 { | 337 { |
335 RefPtr<MailboxInfo> returnMailbox = adoptRef(new MailboxInfo()); | 338 RefPtr<MailboxInfo> returnMailbox = adoptRef(new MailboxInfo()); |
336 m_context->genMailboxCHROMIUM(returnMailbox->mailbox.name); | 339 m_context->genMailboxCHROMIUM(returnMailbox->mailbox.name); |
337 returnMailbox->textureId = textureId; | 340 returnMailbox->textureId = textureId; |
338 returnMailbox->size = m_size; | 341 returnMailbox->size = m_size; |
339 m_textureMailboxes.append(returnMailbox); | 342 m_textureMailboxes.append(returnMailbox); |
340 return returnMailbox.release(); | 343 return returnMailbox.release(); |
341 } | 344 } |
342 | 345 |
343 void DrawingBuffer::deleteMailbox(const blink::WebExternalTextureMailbox& mailbo x) | 346 void DrawingBuffer::deleteMailbox(const blink::WebExternalTextureMailbox& mailbo x) |
344 { | 347 { |
345 for (size_t i = 0; i < m_textureMailboxes.size(); i++) { | 348 for (size_t i = 0; i < m_textureMailboxes.size(); i++) { |
346 if (nameEquals(m_textureMailboxes[i]->mailbox, mailbox)) { | 349 if (nameEquals(m_textureMailboxes[i]->mailbox, mailbox)) { |
347 if (mailbox.syncPoint) | 350 if (mailbox.syncPoint) |
348 m_context->waitSyncPoint(mailbox.syncPoint); | 351 m_context->waitSyncPoint(mailbox.syncPoint); |
352 #if defined(ENABLE_WEBGL_IMAGE_CHROMIUM) | |
353 deleteChromiumImageForTexture(m_textureMailboxes[i]->textureId); | |
354 #endif | |
349 m_context->deleteTexture(m_textureMailboxes[i]->textureId); | 355 m_context->deleteTexture(m_textureMailboxes[i]->textureId); |
350 m_textureMailboxes.remove(i); | 356 m_textureMailboxes.remove(i); |
351 return; | 357 return; |
352 } | 358 } |
353 } | 359 } |
354 ASSERT_NOT_REACHED(); | 360 ASSERT_NOT_REACHED(); |
355 } | 361 } |
356 | 362 |
357 bool DrawingBuffer::initialize(const IntSize& size) | 363 bool DrawingBuffer::initialize(const IntSize& size) |
358 { | 364 { |
(...skipping 164 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
523 context->deleteTexture(sourceTexture); | 529 context->deleteTexture(sourceTexture); |
524 context->flush(); | 530 context->flush(); |
525 m_context->waitSyncPoint(context->insertSyncPoint()); | 531 m_context->waitSyncPoint(context->insertSyncPoint()); |
526 return; | 532 return; |
527 } | 533 } |
528 | 534 |
529 // Since the m_frontColorBuffer was produced and sent to the compositor, it cannot be bound to an fbo. | 535 // Since the m_frontColorBuffer was produced and sent to the compositor, it cannot be bound to an fbo. |
530 // We have to make a copy of it here and bind that copy instead. | 536 // We have to make a copy of it here and bind that copy instead. |
531 // FIXME: That's not true any more, provided we don't change texture | 537 // FIXME: That's not true any more, provided we don't change texture |
532 // parameters. | 538 // parameters. |
533 unsigned sourceTexture = createColorTexture(m_size); | 539 unsigned sourceTexture = createColorTexture(); |
540 texImage2DResourceSafe(GL_TEXTURE_2D, 0, m_internalColorFormat, m_size.width (), m_size.height(), 0, m_colorFormat, GL_UNSIGNED_BYTE); | |
534 m_context->copyTextureCHROMIUM(GL_TEXTURE_2D, m_frontColorBuffer, sourceText ure, 0, GL_RGBA, GL_UNSIGNED_BYTE); | 541 m_context->copyTextureCHROMIUM(GL_TEXTURE_2D, m_frontColorBuffer, sourceText ure, 0, GL_RGBA, GL_UNSIGNED_BYTE); |
535 | 542 |
536 // Since we're using the same context as WebGL, we have to restore any state we change (in this case, just the framebuffer binding). | 543 // Since we're using the same context as WebGL, we have to restore any state we change (in this case, just the framebuffer binding). |
537 // FIXME: The WebGLRenderingContext tracks the current framebuffer binding, it would be slightly more efficient to use this value | 544 // FIXME: The WebGLRenderingContext tracks the current framebuffer binding, it would be slightly more efficient to use this value |
538 // rather than querying it off of the context. | 545 // rather than querying it off of the context. |
539 GLint previousFramebuffer = 0; | 546 GLint previousFramebuffer = 0; |
540 m_context->getIntegerv(GL_FRAMEBUFFER_BINDING, &previousFramebuffer); | 547 m_context->getIntegerv(GL_FRAMEBUFFER_BINDING, &previousFramebuffer); |
541 | 548 |
542 Platform3DObject framebuffer = m_context->createFramebuffer(); | 549 Platform3DObject framebuffer = m_context->createFramebuffer(); |
543 m_context->bindFramebuffer(GL_FRAMEBUFFER, framebuffer); | 550 m_context->bindFramebuffer(GL_FRAMEBUFFER, framebuffer); |
(...skipping 37 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
581 | 588 |
582 if (m_depthStencilBuffer) | 589 if (m_depthStencilBuffer) |
583 m_context->deleteRenderbuffer(m_depthStencilBuffer); | 590 m_context->deleteRenderbuffer(m_depthStencilBuffer); |
584 | 591 |
585 if (m_depthBuffer) | 592 if (m_depthBuffer) |
586 m_context->deleteRenderbuffer(m_depthBuffer); | 593 m_context->deleteRenderbuffer(m_depthBuffer); |
587 | 594 |
588 if (m_stencilBuffer) | 595 if (m_stencilBuffer) |
589 m_context->deleteRenderbuffer(m_stencilBuffer); | 596 m_context->deleteRenderbuffer(m_stencilBuffer); |
590 | 597 |
591 if (m_colorBuffer) | 598 if (m_colorBuffer) { |
599 #if defined(ENABLE_WEBGL_IMAGE_CHROMIUM) | |
600 deleteChromiumImageForTexture(m_colorBuffer); | |
601 #endif | |
592 m_context->deleteTexture(m_colorBuffer); | 602 m_context->deleteTexture(m_colorBuffer); |
603 } | |
593 | 604 |
594 setSize(IntSize()); | 605 setSize(IntSize()); |
595 | 606 |
596 m_colorBuffer = 0; | 607 m_colorBuffer = 0; |
597 m_frontColorBuffer = 0; | 608 m_frontColorBuffer = 0; |
598 m_multisampleColorBuffer = 0; | 609 m_multisampleColorBuffer = 0; |
599 m_depthStencilBuffer = 0; | 610 m_depthStencilBuffer = 0; |
600 m_depthBuffer = 0; | 611 m_depthBuffer = 0; |
601 m_stencilBuffer = 0; | 612 m_stencilBuffer = 0; |
602 m_multisampleFBO = 0; | 613 m_multisampleFBO = 0; |
603 m_fbo = 0; | 614 m_fbo = 0; |
604 m_contextEvictionManager.clear(); | 615 m_contextEvictionManager.clear(); |
605 | 616 |
606 if (m_layer) | 617 if (m_layer) |
607 GraphicsLayer::unregisterContentsLayer(m_layer->layer()); | 618 GraphicsLayer::unregisterContentsLayer(m_layer->layer()); |
608 } | 619 } |
609 | 620 |
610 unsigned DrawingBuffer::createColorTexture(const IntSize& size) | 621 unsigned DrawingBuffer::createColorTexture() |
611 { | 622 { |
612 unsigned offscreenColorTexture = m_context->createTexture(); | 623 unsigned offscreenColorTexture = m_context->createTexture(); |
613 if (!offscreenColorTexture) | 624 if (!offscreenColorTexture) |
614 return 0; | 625 return 0; |
615 | 626 |
616 m_context->bindTexture(GL_TEXTURE_2D, offscreenColorTexture); | 627 m_context->bindTexture(GL_TEXTURE_2D, offscreenColorTexture); |
617 m_context->texParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR); | 628 m_context->texParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR); |
618 m_context->texParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR); | 629 m_context->texParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR); |
619 m_context->texParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_CLAMP_TO_EDGE) ; | 630 m_context->texParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_CLAMP_TO_EDGE) ; |
620 m_context->texParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_CLAMP_TO_EDGE) ; | 631 m_context->texParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_CLAMP_TO_EDGE) ; |
621 if (!size.isEmpty()) | |
622 texImage2DResourceSafe(GL_TEXTURE_2D, 0, m_internalColorFormat, size.wid th(), size.height(), 0, m_colorFormat, GL_UNSIGNED_BYTE); | |
623 | 632 |
624 return offscreenColorTexture; | 633 return offscreenColorTexture; |
625 } | 634 } |
626 | 635 |
627 void DrawingBuffer::createSecondaryBuffers() | 636 void DrawingBuffer::createSecondaryBuffers() |
628 { | 637 { |
629 // create a multisample FBO | 638 // create a multisample FBO |
630 if (m_multisampleMode == ExplicitResolve) { | 639 if (m_multisampleMode == ExplicitResolve) { |
631 m_multisampleFBO = m_context->createFramebuffer(); | 640 m_multisampleFBO = m_context->createFramebuffer(); |
632 m_context->bindFramebuffer(GL_FRAMEBUFFER, m_multisampleFBO); | 641 m_context->bindFramebuffer(GL_FRAMEBUFFER, m_multisampleFBO); |
633 m_multisampleColorBuffer = m_context->createRenderbuffer(); | 642 m_multisampleColorBuffer = m_context->createRenderbuffer(); |
634 } | 643 } |
635 } | 644 } |
636 | 645 |
637 bool DrawingBuffer::resizeFramebuffer(const IntSize& size) | 646 bool DrawingBuffer::resizeFramebuffer(const IntSize& size) |
638 { | 647 { |
639 // resize regular FBO | 648 // resize regular FBO |
640 m_context->bindFramebuffer(GL_FRAMEBUFFER, m_fbo); | 649 m_context->bindFramebuffer(GL_FRAMEBUFFER, m_fbo); |
641 | 650 |
642 m_context->bindTexture(GL_TEXTURE_2D, m_colorBuffer); | 651 m_context->bindTexture(GL_TEXTURE_2D, m_colorBuffer); |
643 | 652 |
644 texImage2DResourceSafe(GL_TEXTURE_2D, 0, m_internalColorFormat, size.width() , size.height(), 0, m_colorFormat, GL_UNSIGNED_BYTE); | 653 allocateTextureMemory(m_colorBuffer, m_size); |
645 | 654 |
646 if (m_multisampleMode == ImplicitResolve) | 655 if (m_multisampleMode == ImplicitResolve) |
647 m_context->framebufferTexture2DMultisampleEXT(GL_FRAMEBUFFER, GL_COLOR_A TTACHMENT0, GL_TEXTURE_2D, m_colorBuffer, 0, m_sampleCount); | 656 m_context->framebufferTexture2DMultisampleEXT(GL_FRAMEBUFFER, GL_COLOR_A TTACHMENT0, GL_TEXTURE_2D, m_colorBuffer, 0, m_sampleCount); |
648 else | 657 else |
649 m_context->framebufferTexture2D(GL_FRAMEBUFFER, GL_COLOR_ATTACHMENT0, GL _TEXTURE_2D, m_colorBuffer, 0); | 658 m_context->framebufferTexture2D(GL_FRAMEBUFFER, GL_COLOR_ATTACHMENT0, GL _TEXTURE_2D, m_colorBuffer, 0); |
650 | 659 |
651 m_context->bindTexture(GL_TEXTURE_2D, 0); | 660 m_context->bindTexture(GL_TEXTURE_2D, 0); |
652 | 661 |
653 if (m_multisampleMode != ExplicitResolve) | 662 if (m_multisampleMode != ExplicitResolve) |
654 resizeDepthStencil(size); | 663 resizeDepthStencil(size); |
(...skipping 358 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
1013 memcpy(rowA, scanline, rowBytes); | 1022 memcpy(rowA, scanline, rowBytes); |
1014 } | 1023 } |
1015 } | 1024 } |
1016 | 1025 |
1017 void DrawingBuffer::texImage2DResourceSafe(GLenum target, GLint level, GLenum in ternalformat, GLsizei width, GLsizei height, GLint border, GLenum format, GLenum type, GLint unpackAlignment) | 1026 void DrawingBuffer::texImage2DResourceSafe(GLenum target, GLint level, GLenum in ternalformat, GLsizei width, GLsizei height, GLint border, GLenum format, GLenum type, GLint unpackAlignment) |
1018 { | 1027 { |
1019 ASSERT(unpackAlignment == 1 || unpackAlignment == 2 || unpackAlignment == 4 || unpackAlignment == 8); | 1028 ASSERT(unpackAlignment == 1 || unpackAlignment == 2 || unpackAlignment == 4 || unpackAlignment == 8); |
1020 m_context->texImage2D(target, level, internalformat, width, height, border, format, type, 0); | 1029 m_context->texImage2D(target, level, internalformat, width, height, border, format, type, 0); |
1021 } | 1030 } |
1022 | 1031 |
1032 void DrawingBuffer::allocateTextureMemory(Platform3DObject textureId, const IntS ize& size) | |
1033 { | |
1034 #if defined(ENABLE_WEBGL_IMAGE_CHROMIUM) | |
1035 deleteChromiumImageForTexture(textureId); | |
1036 | |
1037 blink::WGC3Duint newImage = m_context->createImageCHROMIUM(size.width(), siz e.height(), GL_RGBA8_OES); | |
alexst (slow to review)
2014/05/08 18:00:50
This will have a scanout usage once deps roll.
| |
1038 if (newImage) { | |
1039 m_context->bindTexImage2DCHROMIUM(GL_TEXTURE_2D, newImage); | |
1040 m_textureToImageChromiumMap.add(textureId, newImage); | |
1041 return; | |
1042 } | |
1043 #endif | |
1044 | |
1045 texImage2DResourceSafe(GL_TEXTURE_2D, 0, m_internalColorFormat, size.width() , size.height(), 0, m_colorFormat, GL_UNSIGNED_BYTE); | |
1046 } | |
1047 | |
1048 void DrawingBuffer::deleteChromiumImageForTexture(Platform3DObject textureId) | |
1049 { | |
1050 HashMap<Platform3DObject, blink::WGC3Duint>::iterator imageIter = m_textureT oImageChromiumMap.find(textureId); | |
1051 // Release the old buffer if we have any. | |
1052 if (imageIter != m_textureToImageChromiumMap.end()) { | |
1053 m_context->releaseTexImage2DCHROMIUM(GL_TEXTURE_2D, imageIter->value); | |
1054 m_context->destroyImageCHROMIUM(imageIter->value); | |
1055 m_textureToImageChromiumMap.remove(imageIter); | |
1056 } | |
1057 } | |
1058 | |
1023 } // namespace WebCore | 1059 } // namespace WebCore |
OLD | NEW |