[Libreoffice-commits] core.git: Branch 'libreoffice-7-0' - vcl/inc vcl/skia

Luboš Luňák (via logerrit) logerrit at kemper.freedesktop.org
Wed Mar 3 08:07:31 UTC 2021


 vcl/inc/skia/gdiimpl.hxx |    4 ++--
 vcl/skia/gdiimpl.cxx     |   34 +++++++++++++++++++++-------------
 vcl/skia/win/gdiimpl.cxx |    1 +
 vcl/skia/x11/gdiimpl.cxx |    2 ++
 4 files changed, 26 insertions(+), 15 deletions(-)

New commits:
commit f0c3eec0f26d8b71ec92b32cfa0cf5747f0702eb
Author:     Luboš Luňák <l.lunak at centrum.cz>
AuthorDate: Thu Feb 25 11:37:54 2021 +0000
Commit:     Xisco Fauli <xiscofauli at libreoffice.org>
CommitDate: Wed Mar 3 09:06:54 2021 +0100

    generic Skia workaround for VCL sending empty size (tdf#140288)
    
    There have already been commits to handle this, but the case
    of getting the wrong size the first was still broken (or was
    fixed in the past and got broken again). Try to be generic
    by forcing these to be always considered to be offscreen
    and force non-zero size there.
    
    Change-Id: Ie366a296f7f6645333630fa31e9fe18d54c7fba8
    Reviewed-on: https://gerrit.libreoffice.org/c/core/+/111528
    Tested-by: Jenkins
    Reviewed-by: Luboš Luňák <l.lunak at collabora.com>
    (cherry picked from commit 9d8c04d2d5529626d649af3fcebb6d4b65193b28)
    Reviewed-on: https://gerrit.libreoffice.org/c/core/+/111711
    Reviewed-by: Caolán McNamara <caolanm at redhat.com>
    (cherry picked from commit 21305ff47a1bee1fa4787bf792fb3ecdb10d4863)
    Reviewed-on: https://gerrit.libreoffice.org/c/core/+/111782
    Reviewed-by: Xisco Fauli <xiscofauli at libreoffice.org>

diff --git a/vcl/inc/skia/gdiimpl.hxx b/vcl/inc/skia/gdiimpl.hxx
index ca227e4e809d..057adf4bfcbb 100644
--- a/vcl/inc/skia/gdiimpl.hxx
+++ b/vcl/inc/skia/gdiimpl.hxx
@@ -229,7 +229,7 @@ protected:
     void checkSurface();
     void destroySurface();
     // Reimplemented for X11.
-    virtual bool avoidRecreateByResize() const { return false; }
+    virtual bool avoidRecreateByResize() const;
     void createWindowSurface(bool forceRaster = false);
     virtual void createWindowContext(bool forceRaster = false) = 0;
     void createOffscreenSurface();
@@ -239,7 +239,7 @@ protected:
 
     void setProvider(SalGeometryProvider* provider) { mProvider = provider; }
 
-    bool isOffscreen() const { return mProvider == nullptr || mProvider->IsOffScreen(); }
+    bool isOffscreen() const;
     bool isGPU() const { return mIsGPU; }
 
     void invert(basegfx::B2DPolygon const& rPoly, SalInvert eFlags);
diff --git a/vcl/skia/gdiimpl.cxx b/vcl/skia/gdiimpl.cxx
index bd497d7f8f6e..946663c2d886 100644
--- a/vcl/skia/gdiimpl.cxx
+++ b/vcl/skia/gdiimpl.cxx
@@ -311,14 +311,24 @@ void SkiaSalGraphicsImpl::createWindowSurface(bool forceRaster)
 #endif
 }
 
+bool SkiaSalGraphicsImpl::isOffscreen() const
+{
+    if (mProvider == nullptr || mProvider->IsOffScreen())
+        return true;
+    // HACK: Sometimes (tdf#131939, tdf#138022, tdf#140288) VCL passes us a zero-sized window,
+    // and zero size is invalid for Skia, so force offscreen surface, where we handle this.
+    if (GetWidth() <= 0 || GetHeight() <= 0)
+        return true;
+    return false;
+}
+
 void SkiaSalGraphicsImpl::createOffscreenSurface()
 {
     SkiaZone zone;
     assert(isOffscreen());
     assert(!mSurface);
     assert(!mWindowContext);
-    // When created (especially on Windows), Init() gets called with size (0,0), which is invalid size
-    // for Skia. May happen also in rare cases such as shutting down (tdf#131939).
+    // HACK: See isOffscreen().
     int width = std::max(1, GetWidth());
     int height = std::max(1, GetHeight());
     switch (SkiaHelper::renderMethodToUse())
@@ -428,17 +438,7 @@ void SkiaSalGraphicsImpl::checkSurface()
     }
     else if (GetWidth() != mSurface->width() || GetHeight() != mSurface->height())
     {
-        if (avoidRecreateByResize())
-            return;
-
-        if (!GetWidth() || !GetHeight())
-        {
-            SAL_WARN("vcl.skia", "recreate(" << this << "): can't create empty surface "
-                                             << Size(GetWidth(), GetHeight())
-                                             << " => keeping old one!");
-            return;
-        }
-
+        if (!avoidRecreateByResize())
         {
             Size oldSize(mSurface->width(), mSurface->height());
             // Recreating a surface means that the old SkSurface contents will be lost.
@@ -471,6 +471,14 @@ void SkiaSalGraphicsImpl::checkSurface()
     }
 }
 
+bool SkiaSalGraphicsImpl::avoidRecreateByResize() const
+{
+    // Keep the old surface if VCL sends us a broken size (see isOffscreen()).
+    if (GetWidth() == 0 || GetHeight() == 0)
+        return true;
+    return false;
+}
+
 void SkiaSalGraphicsImpl::flushDrawing()
 {
     if (!mSurface)
diff --git a/vcl/skia/win/gdiimpl.cxx b/vcl/skia/win/gdiimpl.cxx
index a4cbe062f3a5..3b5249bf4077 100644
--- a/vcl/skia/win/gdiimpl.cxx
+++ b/vcl/skia/win/gdiimpl.cxx
@@ -39,6 +39,7 @@ void WinSkiaSalGraphicsImpl::createWindowContext(bool forceRaster)
 {
     SkiaZone zone;
     sk_app::DisplayParams displayParams;
+    assert(GetWidth() > 0 && GetHeight() > 0);
     switch (forceRaster ? SkiaHelper::RenderRaster : SkiaHelper::renderMethodToUse())
     {
         case SkiaHelper::RenderRaster:
diff --git a/vcl/skia/x11/gdiimpl.cxx b/vcl/skia/x11/gdiimpl.cxx
index 1602218c16ac..c3b0e81f7e81 100644
--- a/vcl/skia/x11/gdiimpl.cxx
+++ b/vcl/skia/x11/gdiimpl.cxx
@@ -97,6 +97,8 @@ X11SkiaSalGraphicsImpl::createWindowContext(Display* display, Drawable drawable,
 
 bool X11SkiaSalGraphicsImpl::avoidRecreateByResize() const
 {
+    if (SkiaSalGraphicsImpl::avoidRecreateByResize())
+        return true;
     if (!mSurface || isOffscreen())
         return false;
     // Skia's WindowContext uses actual dimensions of the X window, which due to X11 being


More information about the Libreoffice-commits mailing list