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

Side by Side Diff: third_party/WebKit/Source/modules/offscreencanvas/OffscreenCanvasModules.cpp

Issue 2420203002: Implement convertToBlob() in OffscreenCanvas (Closed)
Patch Set: webgl layout test Created 4 years, 2 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 "modules/offscreencanvas/OffscreenCanvasModules.h" 5 #include "modules/offscreencanvas/OffscreenCanvasModules.h"
6 6
7 #include "core/fileapi/Blob.h"
8 #include "core/html/ImageData.h"
9 #include "core/html/canvas/CanvasAsyncBlobCreator.h"
7 #include "core/html/canvas/CanvasContextCreationAttributes.h" 10 #include "core/html/canvas/CanvasContextCreationAttributes.h"
8 #include "core/offscreencanvas/OffscreenCanvas.h" 11 #include "core/offscreencanvas/OffscreenCanvas.h"
9 #include "modules/offscreencanvas2d/OffscreenCanvasRenderingContext2D.h" 12 #include "modules/offscreencanvas2d/OffscreenCanvasRenderingContext2D.h"
13 #include "modules/webgl/WebGLRenderingContextBase.h"
14 #include "platform/graphics/StaticBitmapImage.h"
15 #include "platform/image-encoders/ImageEncoderUtils.h"
10 16
11 namespace blink { 17 namespace blink {
12 18
13 void OffscreenCanvasModules::getContext( 19 void OffscreenCanvasModules::getContext(
14 ScriptState* scriptState, 20 ScriptState* scriptState,
15 OffscreenCanvas& offscreenCanvas, 21 OffscreenCanvas& offscreenCanvas,
16 const String& id, 22 const String& id,
17 const CanvasContextCreationAttributes& attributes, 23 const CanvasContextCreationAttributes& attributes,
18 ExceptionState& exceptionState, 24 ExceptionState& exceptionState,
19 OffscreenRenderingContext& result) { 25 OffscreenRenderingContext& result) {
20 if (offscreenCanvas.isNeutered()) { 26 if (offscreenCanvas.isNeutered()) {
21 exceptionState.throwDOMException(InvalidStateError, 27 exceptionState.throwDOMException(InvalidStateError,
22 "OffscreenCanvas object is detached"); 28 "OffscreenCanvas object is detached");
23 return; 29 return;
24 } 30 }
25 31
26 CanvasRenderingContext* context = 32 CanvasRenderingContext* context =
27 offscreenCanvas.getCanvasRenderingContext(scriptState, id, attributes); 33 offscreenCanvas.getCanvasRenderingContext(scriptState, id, attributes);
28 if (context) 34 if (context)
29 context->setOffscreenCanvasGetContextResult(result); 35 context->setOffscreenCanvasGetContextResult(result);
30 } 36 }
31 37
38 ImageData* OffscreenCanvasModules::toImageData(OffscreenCanvas& offscreenCanvas,
xlai (Olivia) 2016/10/19 18:51:06 This function requires a higher-level view of Offs
39 SourceDrawingBuffer sourceBuffer,
40 SnapshotReason reason) {
41 ImageData* imageData = nullptr;
42 if (!offscreenCanvas.renderingContext())
43 return imageData;
44 if (offscreenCanvas.renderingContext()->is3d()) {
45 // TODO: Furnish toImageData in webgl renderingcontext for jpeg and webp
46 // images. See crbug.com/657531.
xlai (Olivia) 2016/10/19 18:51:06 I might be missing something here in converting we
47 WebGLRenderingContextBase* webglContext =
48 toWebGLRenderingContextBase(offscreenCanvas.renderingContext());
49 imageData = ImageData::create(offscreenCanvas.size());
50 if (webglContext->drawingBuffer()) {
51 sk_sp<SkImage> snapshot = webglContext->drawingBuffer()
52 ->transferToStaticBitmapImage()
53 ->imageForCurrentFrame();
54 if (snapshot) {
55 SkImageInfo imageInfo =
56 SkImageInfo::Make(offscreenCanvas.width(), offscreenCanvas.height(),
57 kRGBA_8888_SkColorType, kUnpremul_SkAlphaType);
58 snapshot->readPixels(imageInfo, imageData->data()->data(),
59 imageInfo.minRowBytes(), 0, 0);
60 }
61 }
62 return imageData;
63 }
64
65 if (offscreenCanvas.renderingContext()->is2d()) {
66 OffscreenCanvasRenderingContext2D* context2d =
67 toOffscreenCanvasRenderingContext2D(offscreenCanvas.renderingContext());
68 imageData = ImageData::create(offscreenCanvas.size());
69 if (context2d->imageBuffer()) {
70 sk_sp<SkImage> snapshot = context2d->imageBuffer()->newSkImageSnapshot(
71 PreferNoAcceleration, reason);
72 if (snapshot) {
73 SkImageInfo imageInfo =
74 SkImageInfo::Make(offscreenCanvas.width(), offscreenCanvas.height(),
75 kRGBA_8888_SkColorType, kUnpremul_SkAlphaType);
76 snapshot->readPixels(imageInfo, imageData->data()->data(),
77 imageInfo.minRowBytes(), 0, 0);
78 }
79 }
80 return imageData;
81 }
82
83 return nullptr;
84 }
85
86 ScriptPromise OffscreenCanvasModules::convertToBlob(
87 ScriptState* scriptState,
88 OffscreenCanvas& offscreenCanvas,
89 const ImageEncodeOptions& options,
90 ExceptionState& exceptionState) {
91 if (offscreenCanvas.isNeutered()) {
92 exceptionState.throwDOMException(InvalidStateError,
93 "OffscreenCanvas object is detached.");
94 return exceptionState.reject(scriptState);
95 }
96
97 if (!offscreenCanvas.originClean()) {
98 exceptionState.throwSecurityError(
99 "Tainted OffscreenCanvas may not be exported.");
100 return exceptionState.reject(scriptState);
101 }
102
103 if (!offscreenCanvas.isPaintable()) {
104 return ScriptPromise();
105 }
106
107 double startTime = WTF::monotonicallyIncreasingTime();
108 String encodingMimeType = ImageEncoderUtils::toEncodingMimeType(
109 options.type(), ImageEncoderUtils::EncodeReasonConvertToBlobPromise);
110
111 ImageData* imageData =
112 toImageData(offscreenCanvas, BackBuffer, SnapshotReasonUnknown);
113 ScriptPromiseResolver* resolver = ScriptPromiseResolver::create(scriptState);
114
115 Document* document =
116 scriptState->getExecutionContext()->isDocument()
117 ? static_cast<Document*>(scriptState->getExecutionContext())
118 : nullptr;
119
120 CanvasAsyncBlobCreator* asyncCreator = CanvasAsyncBlobCreator::create(
121 imageData->data(), encodingMimeType, imageData->size(), nullptr,
122 startTime, document, resolver);
123
124 asyncCreator->scheduleAsyncBlobCreation(options.quality());
125
126 return resolver->promise();
127 }
128
32 } // namespace blink 129 } // namespace blink
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698