Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(117)

Side by Side Diff: third_party/WebKit/Source/platform/graphics/AcceleratedStaticBitmapImage.cpp

Issue 2261623002: Make DrawingBuffer and Canvas2DLayerBridge be cc::TextureLayerClients. (Closed) Base URL: https://chromium.googlesource.com/chromium/src.git@master
Patch Set: webmailbox: fix-passrefptr Created 4 years, 4 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
OLDNEW
1 // Copyright 2016 The Chromium Authors. All rights reserved. 1 // Copyright 2016 The Chromium Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be 2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file. 3 // found in the LICENSE file.
4 4
5 #include "platform/graphics/AcceleratedStaticBitmapImage.h" 5 #include "platform/graphics/AcceleratedStaticBitmapImage.h"
6 6
7 #include "gpu/command_buffer/client/gles2_interface.h" 7 #include "gpu/command_buffer/client/gles2_interface.h"
8 #include "gpu/command_buffer/common/sync_token.h"
8 #include "platform/graphics/StaticBitmapImage.h" 9 #include "platform/graphics/StaticBitmapImage.h"
9 #include "platform/graphics/skia/SkiaUtils.h" 10 #include "platform/graphics/skia/SkiaUtils.h"
10 #include "public/platform/Platform.h" 11 #include "public/platform/Platform.h"
11 #include "public/platform/WebGraphicsContext3DProvider.h" 12 #include "public/platform/WebGraphicsContext3DProvider.h"
12 #include "skia/ext/texture_handle.h" 13 #include "skia/ext/texture_handle.h"
13 #include "third_party/skia/include/core/SkImage.h" 14 #include "third_party/skia/include/core/SkImage.h"
14 #include "third_party/skia/include/gpu/GrContext.h" 15 #include "third_party/skia/include/gpu/GrContext.h"
15 #include "wtf/PtrUtil.h" 16 #include "wtf/PtrUtil.h"
17
16 #include <memory> 18 #include <memory>
19 #include <utility>
17 20
18 namespace blink { 21 namespace blink {
19 22
20 PassRefPtr<AcceleratedStaticBitmapImage> AcceleratedStaticBitmapImage::create(We bExternalTextureMailbox& mailbox)
21 {
22 return adoptRef(new AcceleratedStaticBitmapImage(mailbox));
23 }
24
25 PassRefPtr<AcceleratedStaticBitmapImage> AcceleratedStaticBitmapImage::create(Pa ssRefPtr<SkImage> image) 23 PassRefPtr<AcceleratedStaticBitmapImage> AcceleratedStaticBitmapImage::create(Pa ssRefPtr<SkImage> image)
26 { 24 {
27 return adoptRef(new AcceleratedStaticBitmapImage(image)); 25 return adoptRef(new AcceleratedStaticBitmapImage(image));
28 } 26 }
29 27
30 AcceleratedStaticBitmapImage::AcceleratedStaticBitmapImage(WebExternalTextureMai lbox& mailbox) 28 PassRefPtr<AcceleratedStaticBitmapImage> AcceleratedStaticBitmapImage::create(Pa ssRefPtr<SkImage> image, sk_sp<GrContext> grContext, const gpu::Mailbox& mailbox , const gpu::SyncToken& syncToken)
31 : StaticBitmapImage() 29 {
32 , m_mailbox(mailbox) 30 return adoptRef(new AcceleratedStaticBitmapImage(image, std::move(grContext) , mailbox, syncToken));
31 }
32
33 AcceleratedStaticBitmapImage::AcceleratedStaticBitmapImage(PassRefPtr<SkImage> i mage)
34 : StaticBitmapImage(std::move(image))
35 , m_imageIsForSharedMainThreadContext(true)
33 { 36 {
34 } 37 }
35 38
36 AcceleratedStaticBitmapImage::AcceleratedStaticBitmapImage(PassRefPtr<SkImage> i mage) 39 AcceleratedStaticBitmapImage::AcceleratedStaticBitmapImage(PassRefPtr<SkImage> i mage, sk_sp<GrContext> grContext, const gpu::Mailbox& mailbox, const gpu::SyncTo ken& syncToken)
37 : StaticBitmapImage(image) 40 : StaticBitmapImage(std::move(image))
41 , m_imageIsForSharedMainThreadContext(false) // TODO(danakj): Could be true though, caller would know.
42 , m_grContext(std::move(grContext))
43 , m_hasMailbox(true)
44 , m_mailbox(mailbox)
45 , m_syncToken(syncToken)
38 { 46 {
47 DCHECK(m_grContext);
39 } 48 }
40 49
41 IntSize AcceleratedStaticBitmapImage::size() const 50 AcceleratedStaticBitmapImage::~AcceleratedStaticBitmapImage() = default;
51
52 void AcceleratedStaticBitmapImage::copyToTexture(WebGraphicsContext3DProvider* d estProvider, GLuint destTextureId, GLenum internalFormat, GLenum destType, bool flipY)
42 { 53 {
43 if (m_image) 54 // |destProvider| may not be the same context as the one used for |m_image| so we use a mailbox to
44 return IntSize(m_image->width(), m_image->height()); 55 // generate a texture id for |destProvider| to access.
45 return IntSize(m_mailbox.textureSize.width, m_mailbox.textureSize.height); 56 ensureMailbox();
46 }
47 57
48 void AcceleratedStaticBitmapImage::copyToTexture(WebGraphicsContext3DProvider* p rovider, GLuint destinationTexture, GLenum internalFormat, GLenum destType, bool flipY) 58 // Get a texture id that |destProvider| knows about and copy from it.
49 { 59 gpu::gles2::GLES2Interface* destGL = destProvider->contextGL();
50 GLuint textureId = switchStorageToSkImageForWebGL(provider); 60 destGL->WaitSyncTokenCHROMIUM(m_syncToken.GetData());
51 gpu::gles2::GLES2Interface* gl = provider->contextGL(); 61 GLuint sourceTextureId = destGL->CreateAndConsumeTextureCHROMIUM(GL_TEXTURE_ 2D, m_mailbox.name);
52 if (!gl) 62 destGL->CopyTextureCHROMIUM(sourceTextureId, destTextureId, internalFormat, destType, flipY, false, false);
53 return; 63 // This drops the |destGL| context's reference on our |m_mailbox|, but it's still held alive by our SkImage.
54 gl->CopyTextureCHROMIUM(textureId, destinationTexture, internalFormat, destT ype, flipY, false, false); 64 destGL->DeleteTextures(1, &sourceTextureId);
55 const GLuint64 fenceSync = gl->InsertFenceSyncCHROMIUM();
56 gl->Flush();
57 GLbyte syncToken[24];
58 gl->GenSyncTokenCHROMIUM(fenceSync, syncToken);
59 // Get a new mailbox because we cannot retain a texture in the WebGL context .
60 switchStorageToMailbox(provider);
61 }
62
63 bool AcceleratedStaticBitmapImage::switchStorageToMailbox(WebGraphicsContext3DPr ovider* provider)
64 {
65 m_mailbox.textureSize = WebSize(m_image->width(), m_image->height());
66 GrContext* grContext = provider->grContext();
67 if (!grContext)
68 return false;
69 grContext->flush();
70 m_mailbox.textureTarget = GL_TEXTURE_2D;
71 gpu::gles2::GLES2Interface* gl = provider->contextGL();
72 if (!gl)
73 return false;
74 GLuint textureID = skia::GrBackendObjectToGrGLTextureInfo(m_image->getTextur eHandle(true))->fID;
75 gl->BindTexture(GL_TEXTURE_2D, textureID);
76
77 gl->GenMailboxCHROMIUM(m_mailbox.name);
78 gl->ProduceTextureCHROMIUM(GL_TEXTURE_2D, m_mailbox.name);
79 const GLuint64 fenceSync = gl->InsertFenceSyncCHROMIUM();
80 gl->Flush();
81 gl->GenSyncTokenCHROMIUM(fenceSync, m_mailbox.syncToken);
82 m_mailbox.validSyncToken = true;
83 gl->BindTexture(GL_TEXTURE_2D, 0);
84 grContext->resetContext(kTextureBinding_GrGLBackendState);
85 m_image = nullptr;
86 return true;
87 }
88
89 // This function is called only in the case that m_image is texture backed.
90 GLuint AcceleratedStaticBitmapImage::switchStorageToSkImageForWebGL(WebGraphicsC ontext3DProvider* contextProvider)
91 {
92 DCHECK(!m_image || m_image->isTextureBacked());
93 GLuint textureId = 0;
94 if (m_image) {
95 // SkImage is texture-backed on the shared context
96 if (!hasMailbox()) {
97 std::unique_ptr<WebGraphicsContext3DProvider> sharedProvider = wrapU nique(Platform::current()->createSharedOffscreenGraphicsContext3DProvider());
98 if (!switchStorageToMailbox(sharedProvider.get()))
99 return 0;
100 textureId = switchStorageToSkImage(contextProvider);
101 return textureId;
102 }
103 }
104 DCHECK(hasMailbox());
105 textureId = switchStorageToSkImage(contextProvider);
106 return textureId;
107 }
108
109 GLuint AcceleratedStaticBitmapImage::switchStorageToSkImage(WebGraphicsContext3D Provider* provider)
110 {
111 if (!provider)
112 return 0;
113 GrContext* grContext = provider->grContext();
114 if (!grContext)
115 return 0;
116 gpu::gles2::GLES2Interface* gl = provider->contextGL();
117 if (!gl)
118 return 0;
119 gl->WaitSyncTokenCHROMIUM(m_mailbox.syncToken);
120 GLuint textureId = gl->CreateAndConsumeTextureCHROMIUM(GL_TEXTURE_2D, m_mail box.name);
121 GrGLTextureInfo textureInfo;
122 textureInfo.fTarget = GL_TEXTURE_2D;
123 textureInfo.fID = textureId;
124 GrBackendTextureDesc backendTexture;
125 backendTexture.fOrigin = kBottomLeft_GrSurfaceOrigin;
126 backendTexture.fWidth = m_mailbox.textureSize.width;
127 backendTexture.fHeight = m_mailbox.textureSize.height;
128 backendTexture.fConfig = kSkia8888_GrPixelConfig;
129 backendTexture.fTextureHandle = skia::GrGLTextureInfoToGrBackendObject(textu reInfo);
130 sk_sp<SkImage> skImage = SkImage::MakeFromAdoptedTexture(grContext, backendT exture);
131 m_image = fromSkSp(skImage);
132 return textureId;
133 } 65 }
134 66
135 PassRefPtr<SkImage> AcceleratedStaticBitmapImage::imageForCurrentFrame() 67 PassRefPtr<SkImage> AcceleratedStaticBitmapImage::imageForCurrentFrame()
136 { 68 {
137 if (m_image) 69 // This must return an SkImage that can be used with the shared main thread context. If |m_image| satisfies that, we are done.
70 if (m_imageIsForSharedMainThreadContext)
138 return m_image; 71 return m_image;
139 if (!hasMailbox()) 72
140 return nullptr; 73 // TODO(xidachen): make this work on a worker thread.
141 // Has mailbox, consume mailbox, prepare a new mailbox if contextProvider is not null (3D).
142 DCHECK(isMainThread()); 74 DCHECK(isMainThread());
143 // TODO(xidachen): make this work on a worker thread. 75
144 std::unique_ptr<WebGraphicsContext3DProvider> sharedProvider = wrapUnique(Pl atform::current()->createSharedOffscreenGraphicsContext3DProvider()); 76 // If the SkImage came from any other context than the shared main thread on e, we expect to be given a mailbox at construction. We
145 if (!switchStorageToSkImage(sharedProvider.get())) 77 // use the mailbox to generate a texture id for the shared main thread conte xt to use.
146 return nullptr; 78 DCHECK(m_hasMailbox);
79
80 auto sharedMainThreadContextProvider = wrapUnique(Platform::current()->creat eSharedOffscreenGraphicsContext3DProvider());
81 gpu::gles2::GLES2Interface* sharedGL = sharedMainThreadContextProvider->cont extGL();
82 GrContext* sharedGrContext = sharedMainThreadContextProvider->grContext();
83 if (!sharedGrContext)
84 return nullptr; // Can happen if the context is lost, the SkImage won't be any good now anyway.
85
86 sharedGL->WaitSyncTokenCHROMIUM(m_syncToken.GetData());
87 GLuint sharedContextTextureId = sharedGL->CreateAndConsumeTextureCHROMIUM(GL _TEXTURE_2D, m_mailbox.name);
88
89 GrGLTextureInfo textureInfo;
90 textureInfo.fTarget = GL_TEXTURE_2D;
91 textureInfo.fID = sharedContextTextureId;
92 GrBackendTextureDesc backendTexture;
93 backendTexture.fOrigin = kBottomLeft_GrSurfaceOrigin;
94 backendTexture.fWidth = size().width();
95 backendTexture.fHeight = size().height();
96 backendTexture.fConfig = kSkia8888_GrPixelConfig;
97 backendTexture.fTextureHandle = skia::GrGLTextureInfoToGrBackendObject(textu reInfo);
98
99 m_image = fromSkSp(SkImage::MakeFromAdoptedTexture(sharedGrContext, backendT exture));
100 m_imageIsForSharedMainThreadContext = true;
101 // Can drop the ref on the GrContext since m_image is now backed by a textur e from the shared main thread context.
102 m_grContext = nullptr;
147 return m_image; 103 return m_image;
148 } 104 }
149 105
106 void AcceleratedStaticBitmapImage::ensureMailbox()
107 {
108 if (m_hasMailbox)
109 return;
110
111 // If we weren't given a mailbox at creation, then we were given a SkImage t hat is assumed to be from the shared main thread context.
112 DCHECK(m_imageIsForSharedMainThreadContext);
113 auto sharedMainThreadContextProvider = wrapUnique(Platform::current()->creat eSharedOffscreenGraphicsContext3DProvider());
114
115 gpu::gles2::GLES2Interface* sharedGL = sharedMainThreadContextProvider->cont extGL();
116 GrContext* sharedGrContext = sharedMainThreadContextProvider->grContext();
117 if (!sharedGrContext)
118 return; // Can happen if the context is lost, the SkImage won't be any g ood now anyway.
119
120 GLuint imageTextureId = skia::GrBackendObjectToGrGLTextureInfo(m_image->getT extureHandle(true))->fID;
121 sharedGL->BindTexture(GL_TEXTURE_2D, imageTextureId);
122
123 sharedGL->GenMailboxCHROMIUM(m_mailbox.name);
124 sharedGL->ProduceTextureCHROMIUM(GL_TEXTURE_2D, m_mailbox.name);
125 const GLuint64 fenceSync = sharedGL->InsertFenceSyncCHROMIUM();
126 sharedGL->Flush();
127 sharedGL->GenSyncTokenCHROMIUM(fenceSync, m_syncToken.GetData());
128
129 sharedGL->BindTexture(GL_TEXTURE_2D, 0);
130 // We changed bound textures in this function, so reset the GrContext.
131 sharedGrContext->resetContext(kTextureBinding_GrGLBackendState);
132
133 m_hasMailbox = true;
134 }
135
150 } // namespace blink 136 } // namespace blink
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698