Skip to content

Commit

Permalink
Lock pixels before calling SkBitmap::getPixels and copy bitmap row-…
Browse files Browse the repository at this point in the history
…wise in case (stride != width)
  • Loading branch information
alespergl authored and alexeykuzmin committed Jul 28, 2017
1 parent 6c5d537 commit e149418
Showing 1 changed file with 19 additions and 17 deletions.
36 changes: 19 additions & 17 deletions atom/browser/api/frame_subscriber.cc
Expand Up @@ -14,18 +14,6 @@

namespace atom {

namespace {

void CopyPixelsToBuffer(const SkBitmap& bitmap,
const v8::Local<v8::Object>& buffer) {
size_t rgb_arr_size = bitmap.width() * bitmap.height() *
bitmap.bytesPerPixel();

memcpy(node::Buffer::Data(buffer), bitmap.getPixels(), rgb_arr_size);
}

} // namespace

namespace api {

FrameSubscriber::FrameSubscriber(v8::Isolate* isolate,
Expand Down Expand Up @@ -90,18 +78,32 @@ void FrameSubscriber::OnFrameDelivered(const FrameCaptureCallback& callback,
v8::Locker locker(isolate_);
v8::HandleScope handle_scope(isolate_);

size_t rgb_arr_size = bitmap.width() * bitmap.height() *
bitmap.bytesPerPixel();
v8::MaybeLocal<v8::Object> buffer = node::Buffer::New(isolate_, rgb_arr_size);
size_t rgb_row_size = bitmap.width() * bitmap.bytesPerPixel();

v8::MaybeLocal<v8::Object> buffer =
node::Buffer::New(isolate_, rgb_row_size * bitmap.height());

if (buffer.IsEmpty())
return;

CopyPixelsToBuffer(bitmap, buffer.ToLocalChecked());
auto local_buffer = buffer.ToLocalChecked();

{
SkAutoLockPixels lock(bitmap);
auto source = static_cast<const unsigned char*>(bitmap.getPixels());
auto target = node::Buffer::Data(local_buffer);

for (int y = 0; y < bitmap.height(); ++y) {
memcpy(target, source, rgb_row_size);
source += bitmap.rowBytes();
target += rgb_row_size;
}
}

v8::Local<v8::Value> damage =
mate::Converter<gfx::Rect>::ToV8(isolate_, damage_rect);

callback_.Run(buffer.ToLocalChecked(), damage);
callback_.Run(local_buffer, damage);
}

} // namespace api
Expand Down

0 comments on commit e149418

Please sign in to comment.