diff options
author | Luboš Luňák <l.lunak@collabora.com> | 2021-08-13 07:35:00 +0200 |
---|---|---|
committer | Luboš Luňák <l.lunak@collabora.com> | 2021-08-23 14:59:42 +0200 |
commit | 830abb2437e3f150e1369816f491fb12a3db0c16 (patch) | |
tree | d4368de32a0d3e2cf0b7c6d6fd78ccd1601078d7 /vcl/skia/osx | |
parent | 09b16f9f44578182306c47cdabe92a31cc5d3b4c (diff) |
implement blitting to screen for skia on mac
Change-Id: I01fdb57815dc3dff6d2c5757b55445f16825ed20
Reviewed-on: https://gerrit.libreoffice.org/c/core/+/120807
Tested-by: Jenkins
Reviewed-by: Luboš Luňák <l.lunak@collabora.com>
Diffstat (limited to 'vcl/skia/osx')
-rw-r--r-- | vcl/skia/osx/gdiimpl.cxx | 47 |
1 files changed, 45 insertions, 2 deletions
diff --git a/vcl/skia/osx/gdiimpl.cxx b/vcl/skia/osx/gdiimpl.cxx index 399f8d024f0a..c815fc1ebe9d 100644 --- a/vcl/skia/osx/gdiimpl.cxx +++ b/vcl/skia/osx/gdiimpl.cxx @@ -56,7 +56,7 @@ void AquaSkiaSalGraphicsImpl::createWindowContext(bool forceRaster) switch (renderMethod) { case RenderRaster: - displayParams.fColorType = kBGRA_8888_SkColorType; // TODO + displayParams.fColorType = kRGBA_8888_SkColorType; // TODO mWindowContext.reset( new AquaSkiaWindowContextRaster(GetWidth(), GetHeight(), displayParams)); break; @@ -75,11 +75,54 @@ void AquaSkiaSalGraphicsImpl::performFlush() if (mWindowContext) { if (mDirtyRect.intersect(SkIRect::MakeWH(GetWidth(), GetHeight()))) - mWindowContext->swapBuffers(&mDirtyRect); // TODO + flushToScreen(mDirtyRect); mDirtyRect.setEmpty(); } } +void AquaSkiaSalGraphicsImpl::flushToScreen(const SkIRect& rect) +{ + // Based on AquaGraphicsBackend::drawBitmap(). + if (!mrShared.checkContext()) + return; + + assert(mSurface.get()); + // Do not use sub-rect, it creates copies of the data. + sk_sp<SkImage> image = makeCheckedImageSnapshot(mSurface); + SkPixmap pixmap; + if (!image->peekPixels(&pixmap)) + abort(); + // This creates the bitmap context from the cropped part, writable_addr32() will get + // the first pixel of rect.topLeft(), and using pixmap.rowBytes() ensures the following + // pixel lines will be read from correct positions. + CGContextRef context + = CGBitmapContextCreate(pixmap.writable_addr32(rect.left(), rect.top()), rect.width(), + rect.height(), 8, pixmap.rowBytes(), // TODO + GetSalData()->mxRGBSpace, kCGImageAlphaNoneSkipLast); // TODO + assert(context); // TODO + CGImageRef screenImage = CGBitmapContextCreateImage(context); + assert(screenImage); // TODO + if (mrShared.isFlipped()) + { + const CGRect screenRect = CGRectMake(rect.left(), GetHeight() - rect.top() - rect.height(), + rect.width(), rect.height()); + mrShared.maContextHolder.saveState(); + CGContextTranslateCTM(mrShared.maContextHolder.get(), 0, pixmap.height()); + CGContextScaleCTM(mrShared.maContextHolder.get(), 1, -1); + CGContextDrawImage(mrShared.maContextHolder.get(), screenRect, screenImage); + mrShared.maContextHolder.restoreState(); + } + else + { + const CGRect screenRect = CGRectMake(rect.left(), rect.top(), rect.width(), rect.height()); + CGContextDrawImage(mrShared.maContextHolder.get(), screenRect, screenImage); + } + + CGImageRelease(screenImage); + CGContextRelease(context); + mrShared.refreshRect(rect.left(), rect.top(), rect.width(), rect.height()); +} + std::unique_ptr<sk_app::WindowContext> createVulkanWindowContext(bool /*temporary*/) { return nullptr; |