Chromium Code Reviews| Index: third_party/WebKit/Source/modules/shapedetection/FaceDetector.cpp |
| diff --git a/third_party/WebKit/Source/modules/shapedetection/FaceDetector.cpp b/third_party/WebKit/Source/modules/shapedetection/FaceDetector.cpp |
| index 7ad81a6bf0ec83d632043f08af84645e0bd0a8a9..1e9adb673b4f8e6f8258bdf8232995f7d4196191 100644 |
| --- a/third_party/WebKit/Source/modules/shapedetection/FaceDetector.cpp |
| +++ b/third_party/WebKit/Source/modules/shapedetection/FaceDetector.cpp |
| @@ -8,6 +8,7 @@ |
| #include "core/dom/DOMRect.h" |
| #include "core/dom/Document.h" |
| #include "core/fetch/ImageResource.h" |
| +#include "core/frame/ImageBitmap.h" |
| #include "core/frame/LocalDOMWindow.h" |
| #include "core/frame/LocalFrame.h" |
| #include "core/html/HTMLImageElement.h" |
| @@ -20,7 +21,7 @@ namespace blink { |
| namespace { |
| -mojo::ScopedSharedBufferHandle getSharedBufferHandle( |
| +mojo::ScopedSharedBufferHandle getSharedBufferHandleForImageElement( |
| const HTMLImageElement* img, |
| ScriptPromiseResolver* resolver) { |
| ImageResource* const imageResource = img->cachedImage(); |
| @@ -112,7 +113,7 @@ ScriptPromise FaceDetector::detect(ScriptState* scriptState, |
| } |
| mojo::ScopedSharedBufferHandle sharedBufferHandle = |
| - getSharedBufferHandle(img, resolver); |
| + getSharedBufferHandleForImageElement(img, resolver); |
| if (!sharedBufferHandle->is_valid()) |
| return promise; |
| @@ -133,6 +134,75 @@ ScriptPromise FaceDetector::detect(ScriptState* scriptState, |
| return promise; |
| } |
| +ScriptPromise FaceDetector::detect(ScriptState* scriptState, |
| + ImageBitmap* imageBitmap) { |
| + ScriptPromiseResolver* resolver = ScriptPromiseResolver::create(scriptState); |
| + ScriptPromise promise = resolver->promise(); |
| + |
| + if (!imageBitmap) { |
| + resolver->reject( |
| + DOMException::create(InvalidStateError, "Invalid ImageBitmap")); |
| + return promise; |
| + } |
| + DCHECK(imageBitmap->size().area()) << "ImageBitmap has invalid dimension(s)."; |
| + if (!imageBitmap->originClean()) { |
| + resolver->reject( |
| + DOMException::create(SecurityError, "ImageBitmap is not origin clean")); |
| + return promise; |
| + } |
| + |
| + SkPixmap pixmap; |
| + RefPtr<Uint8Array> pixelData; |
|
xianglu
2016/10/25 21:07:45
Consider moving this line above l.165.
mcasas
2016/10/25 21:47:38
Can't move it in there, or it will fall out of sco
|
| + uint8_t* pixelDataPtr = nullptr; |
| + int allocationSize = 0; |
| + // Use |skImage|'s pixels if it has direct access to them, otherwise retrieve |
| + // them from elsewhere via copyBitmapData(). |
| + sk_sp<SkImage> skImage = imageBitmap->bitmapImage()->imageForCurrentFrame(); |
| + if (skImage->peekPixels(&pixmap)) { |
| + pixelDataPtr = static_cast<uint8_t*>(pixmap.writable_addr()); |
| + allocationSize = pixmap.getSafeSize(); |
| + } else { |
| + pixelData = imageBitmap->copyBitmapData(imageBitmap->isPremultiplied() |
| + ? PremultiplyAlpha |
| + : DontPremultiplyAlpha, |
| + N32ColorType); |
| + pixelDataPtr = pixelData->data(); |
| + allocationSize = imageBitmap->size().area() * 4; // 4 bpp. |
| + } |
| + DCHECK(allocationSize); |
| + |
| + mojo::ScopedSharedBufferHandle sharedBufferHandle = |
| + mojo::SharedBufferHandle::Create(allocationSize); |
| + |
| + if (!pixelDataPtr || !sharedBufferHandle->is_valid()) { |
| + resolver->reject( |
| + DOMException::create(InvalidStateError, "Internal allocation error")); |
| + return promise; |
| + } |
| + |
| + if (!m_service) { |
| + resolver->reject(DOMException::create( |
| + NotFoundError, "Face detection service unavailable.")); |
| + return promise; |
| + } |
| + |
| + const mojo::ScopedSharedBufferMapping mappedBuffer = |
| + sharedBufferHandle->Map(allocationSize); |
| + DCHECK(mappedBuffer.get()); |
| + |
| + memcpy(mappedBuffer.get(), pixelDataPtr, allocationSize); |
| + |
| + m_serviceRequests.add(resolver); |
| + DCHECK(m_service.is_bound()); |
| + m_service->DetectFace(std::move(sharedBufferHandle), imageBitmap->width(), |
| + imageBitmap->height(), |
| + convertToBaseCallback(WTF::bind( |
| + &FaceDetector::onDetectFace, wrapPersistent(this), |
| + wrapPersistent(resolver)))); |
| + sharedBufferHandle.reset(); |
| + return promise; |
| +} |
| + |
| void FaceDetector::onDetectFace( |
| ScriptPromiseResolver* resolver, |
| mojom::blink::FaceDetectionResultPtr faceDetectionResult) { |