diff options
Diffstat (limited to 'vcl')
-rw-r--r-- | vcl/inc/opengl/x11/gdiimpl.hxx | 11 | ||||
-rw-r--r-- | vcl/inc/unx/salgdi.h | 6 | ||||
-rw-r--r-- | vcl/inc/unx/x11/x11gdiimpl.h | 6 | ||||
-rw-r--r-- | vcl/opengl/x11/gdiimpl.cxx | 84 | ||||
-rw-r--r-- | vcl/unx/generic/gdi/gdiimpl.cxx | 11 | ||||
-rw-r--r-- | vcl/unx/generic/gdi/gdiimpl.hxx | 5 | ||||
-rw-r--r-- | vcl/unx/generic/gdi/salgdi2.cxx | 15 | ||||
-rw-r--r-- | vcl/unx/gtk/gdi/salnativewidgets-gtk.cxx | 23 |
8 files changed, 140 insertions, 21 deletions
diff --git a/vcl/inc/opengl/x11/gdiimpl.hxx b/vcl/inc/opengl/x11/gdiimpl.hxx index feb3961a5e71..9e2ece3448c0 100644 --- a/vcl/inc/opengl/x11/gdiimpl.hxx +++ b/vcl/inc/opengl/x11/gdiimpl.hxx @@ -16,6 +16,8 @@ #include "unx/x11/x11gdiimpl.h" #include "openglgdiimpl.hxx" +class TextureCombo; + class VCL_PLUGIN_PUBLIC X11OpenGLSalGraphicsImpl : public OpenGLSalGraphicsImpl, public X11GraphicsImpl { private: @@ -29,6 +31,8 @@ protected: virtual OpenGLContext* CreateWinContext() SAL_OVERRIDE; virtual bool UseContext( OpenGLContext* pContext ) SAL_OVERRIDE; + bool RenderPixmap(X11Pixmap* pPixmap, X11Pixmap* pMask, int nX, int nY, TextureCombo& rCombo); + public: // implementation of X11GraphicsImpl @@ -37,7 +41,12 @@ public: virtual void Init() SAL_OVERRIDE; bool FillPixmapFromScreen( X11Pixmap* pPixmap, int nX, int nY ) SAL_OVERRIDE; - bool RenderPixmapToScreen( X11Pixmap* pPixmap, X11Pixmap* pMask, int nX, int nY ) SAL_OVERRIDE; + bool RenderPixmapToScreen(X11Pixmap* pPixmap, X11Pixmap* pMask, int nX, int nY) SAL_OVERRIDE; + + bool RenderAndCacheNativeControl(X11Pixmap* pPixmap, X11Pixmap* pMask, int nX, int nY, + ControlCacheKey& aControlCacheKey) SAL_OVERRIDE; + bool TryRenderCachedNativeControl(ControlCacheKey& rControlCacheKey, + int nX, int nY) SAL_OVERRIDE; }; #endif // INCLUDED_VCL_INC_OPENGL_X11_GDIIMPL_HXX diff --git a/vcl/inc/unx/salgdi.h b/vcl/inc/unx/salgdi.h index 99fe40d87279..3e80153640ba 100644 --- a/vcl/inc/unx/salgdi.h +++ b/vcl/inc/unx/salgdi.h @@ -267,6 +267,12 @@ public: virtual void BeginPaint() SAL_OVERRIDE; virtual void EndPaint() SAL_OVERRIDE; + bool TryRenderCachedNativeControl(ControlCacheKey& aControlCacheKey, + int nX, int nY); + + bool RenderAndCacheNativeControl(X11Pixmap* pPixmap, X11Pixmap* pMask, int nX, int nY, + ControlCacheKey& aControlCacheKey); + // fill a pixmap from a screen region bool FillPixmapFromScreen( X11Pixmap* pPixmap, int nX, int nY ); diff --git a/vcl/inc/unx/x11/x11gdiimpl.h b/vcl/inc/unx/x11/x11gdiimpl.h index 22859c315b6d..c5043646e422 100644 --- a/vcl/inc/unx/x11/x11gdiimpl.h +++ b/vcl/inc/unx/x11/x11gdiimpl.h @@ -12,6 +12,8 @@ #include "unx/pixmap.hxx" +class ControlCacheKey; + class X11GraphicsImpl { public: @@ -19,6 +21,10 @@ public: virtual bool FillPixmapFromScreen( X11Pixmap* pPixmap, int nX, int nY ) = 0; virtual bool RenderPixmapToScreen( X11Pixmap* pPixmap, X11Pixmap* pMask, int nX, int nY ) = 0; + + virtual bool TryRenderCachedNativeControl(ControlCacheKey& rControlCacheKey, int nX, int nY) = 0; + virtual bool RenderAndCacheNativeControl(X11Pixmap* pPixmap, X11Pixmap* pMask, int nX, int nY, + ControlCacheKey& aControlCacheKey) = 0; }; #endif // INCLUDED_VCL_INC_UNX_X11_X11GDIIMPL_HXX diff --git a/vcl/opengl/x11/gdiimpl.cxx b/vcl/opengl/x11/gdiimpl.cxx index 1d453dabf007..3890b6443de3 100644 --- a/vcl/opengl/x11/gdiimpl.cxx +++ b/vcl/opengl/x11/gdiimpl.cxx @@ -111,18 +111,28 @@ bool X11OpenGLSalGraphicsImpl::FillPixmapFromScreen( X11Pixmap* pPixmap, int nX, return true; } -bool X11OpenGLSalGraphicsImpl::RenderPixmapToScreen( X11Pixmap* pPixmap, X11Pixmap* pMask, int nX, int nY ) +struct TextureCombo +{ + std::unique_ptr<OpenGLTexture> mpTexture; + std::unique_ptr<OpenGLTexture> mpMask; +}; + +typedef std::unordered_map<ControlCacheKey, std::unique_ptr<TextureCombo>, ControlCacheHashFunction> ControlCacheType; + +ControlCacheType gTextureCache; + +bool X11OpenGLSalGraphicsImpl::RenderPixmap(X11Pixmap* pPixmap, X11Pixmap* pMask, int nX, int nY, TextureCombo& rCombo) { - const int aAttribs[] = { + const int aAttribs[] = + { GLX_TEXTURE_TARGET_EXT, GLX_TEXTURE_2D_EXT, GLX_TEXTURE_FORMAT_EXT, GLX_TEXTURE_FORMAT_RGBA_EXT, None }; + Display* pDisplay = mrParent.GetXDisplay(); bool bInverted; - SAL_INFO( "vcl.opengl", "RenderPixmapToScreen (" << nX << " " << nY << ")" ); - const long nWidth = pPixmap->GetWidth(); const long nHeight = pPixmap->GetHeight(); SalTwoRect aPosAry(0, 0, nWidth, nHeight, nX, nY, nWidth, nHeight); @@ -145,27 +155,28 @@ bool X11OpenGLSalGraphicsImpl::RenderPixmapToScreen( X11Pixmap* pPixmap, X11Pixm //TODO: lfrb: glXGetProc to get the functions - OpenGLTexture aTexture( pPixmap->GetWidth(), pPixmap->GetHeight(), false ); + rCombo.mpTexture.reset(new OpenGLTexture(pPixmap->GetWidth(), pPixmap->GetHeight(), false)); + glActiveTexture( GL_TEXTURE0 ); - aTexture.Bind(); + rCombo.mpTexture->Bind(); glXBindTexImageEXT( pDisplay, pGlxPixmap, GLX_FRONT_LEFT_EXT, NULL ); - aTexture.Unbind(); + rCombo.mpTexture->Unbind(); if( pMask != NULL && pGlxMask ) { - OpenGLTexture aMaskTexture( pMask->GetWidth(), pMask->GetHeight(), false ); - aMaskTexture.Bind(); + rCombo.mpMask.reset(new OpenGLTexture(pPixmap->GetWidth(), pPixmap->GetHeight(), false)); + rCombo.mpMask->Bind(); glXBindTexImageEXT( pDisplay, pGlxMask, GLX_FRONT_LEFT_EXT, NULL ); - aMaskTexture.Unbind(); + rCombo.mpMask->Unbind(); - DrawTextureDiff( aTexture, aMaskTexture, aPosAry, bInverted ); + DrawTextureDiff(*rCombo.mpTexture, *rCombo.mpMask, aPosAry, bInverted); glXReleaseTexImageEXT( pDisplay, pGlxMask, GLX_FRONT_LEFT_EXT ); glXDestroyPixmap( pDisplay, pGlxMask ); } else { - DrawTexture( aTexture, aPosAry, bInverted ); + DrawTexture(*rCombo.mpTexture, aPosAry, bInverted); } CHECK_GL_ERROR(); @@ -176,7 +187,56 @@ bool X11OpenGLSalGraphicsImpl::RenderPixmapToScreen( X11Pixmap* pPixmap, X11Pixm PostDraw(); CHECK_GL_ERROR(); + return true; } +bool X11OpenGLSalGraphicsImpl::RenderPixmapToScreen( X11Pixmap* pPixmap, X11Pixmap* pMask, int nX, int nY ) +{ + SAL_INFO( "vcl.opengl", "RenderPixmapToScreen (" << nX << " " << nY << ")" ); + + TextureCombo aCombo; + return RenderPixmap(pPixmap, pMask, nX, nY, aCombo); +} + +bool X11OpenGLSalGraphicsImpl::TryRenderCachedNativeControl(ControlCacheKey& rControlCacheKey, int nX, int nY) +{ + static bool gbCacheEnabled = !getenv("SAL_WITHOUT_WIDGET_CACHE"); + + if (!gbCacheEnabled) + return false; + + ControlCacheType::const_iterator iterator = gTextureCache.find(rControlCacheKey); + + if (iterator == gTextureCache.end()) + return false; + + const std::unique_ptr<TextureCombo>& pCombo = iterator->second; + + PreDraw(); + + OpenGLTexture& rTexture = *pCombo->mpTexture; + + SalTwoRect aPosAry(0, 0, rTexture.GetWidth(), rTexture.GetHeight(), + nX, nY, rTexture.GetWidth(), rTexture.GetHeight()); + + if (pCombo->mpMask) + DrawTextureDiff(rTexture, *pCombo->mpMask, aPosAry, true); + else + DrawTexture(rTexture, aPosAry, true); + + PostDraw(); + + return true; +} + +bool X11OpenGLSalGraphicsImpl::RenderAndCacheNativeControl(X11Pixmap* pPixmap, X11Pixmap* pMask, int nX, int nY, + ControlCacheKey& aControlCacheKey) +{ + std::unique_ptr<TextureCombo> pCombo(new TextureCombo); + bool bResult = RenderPixmap(pPixmap, pMask, nX, nY, *pCombo); + gTextureCache[aControlCacheKey] = std::move(pCombo); + return bResult; +} + /* vim:set shiftwidth=4 softtabstop=4 expandtab: */ diff --git a/vcl/unx/generic/gdi/gdiimpl.cxx b/vcl/unx/generic/gdi/gdiimpl.cxx index 7a2beb14b9be..d350d019f961 100644 --- a/vcl/unx/generic/gdi/gdiimpl.cxx +++ b/vcl/unx/generic/gdi/gdiimpl.cxx @@ -212,6 +212,17 @@ bool X11SalGraphicsImpl::RenderPixmapToScreen( X11Pixmap* pPixmap, X11Pixmap* /* return true; } +bool X11SalGraphicsImpl::TryRenderCachedNativeControl(ControlCacheKey& /*rControlCacheKey*/, int /*nX*/, int /*nY*/) +{ + return false; +} + +bool X11SalGraphicsImpl::RenderAndCacheNativeControl(X11Pixmap* pPixmap, X11Pixmap* pMask, int nX, int nY, + ControlCacheKey& /*rControlCacheKey*/) +{ + return RenderPixmapToScreen(pPixmap, pMask, nX, nY); +} + XID X11SalGraphicsImpl::GetXRenderPicture() { XRenderPeer& rRenderPeer = XRenderPeer::GetInstance(); diff --git a/vcl/unx/generic/gdi/gdiimpl.hxx b/vcl/unx/generic/gdi/gdiimpl.hxx index f5df99caa853..3059dc4a790a 100644 --- a/vcl/unx/generic/gdi/gdiimpl.hxx +++ b/vcl/unx/generic/gdi/gdiimpl.hxx @@ -279,6 +279,11 @@ public: void Init() SAL_OVERRIDE; bool FillPixmapFromScreen( X11Pixmap* pPixmap, int nX, int nY ) SAL_OVERRIDE; bool RenderPixmapToScreen( X11Pixmap* pPixmap, X11Pixmap* pMask, int nX, int nY ) SAL_OVERRIDE; + + virtual bool TryRenderCachedNativeControl(ControlCacheKey& rControlCacheKey, + int nX, int nY) SAL_OVERRIDE; + virtual bool RenderAndCacheNativeControl(X11Pixmap* pPixmap, X11Pixmap* pMask, int nX, int nY, + ControlCacheKey& aControlCacheKey) SAL_OVERRIDE; }; #endif diff --git a/vcl/unx/generic/gdi/salgdi2.cxx b/vcl/unx/generic/gdi/salgdi2.cxx index b98d9b69cf66..629cf880a8cf 100644 --- a/vcl/unx/generic/gdi/salgdi2.cxx +++ b/vcl/unx/generic/gdi/salgdi2.cxx @@ -89,6 +89,21 @@ bool X11SalGraphics::RenderPixmapToScreen( X11Pixmap* pPixmap, X11Pixmap* pMask, return rImpl.RenderPixmapToScreen( pPixmap, pMask, nX, nY ); } +bool X11SalGraphics::TryRenderCachedNativeControl(ControlCacheKey& rControlCacheKey, int nX, int nY) +{ + SAL_INFO( "vcl", "TryRenderCachedNativeControl" ); + X11GraphicsImpl& rImpl = dynamic_cast<X11GraphicsImpl&>(*mxImpl.get()); + return rImpl.TryRenderCachedNativeControl(rControlCacheKey, nX, nY); +} + +bool X11SalGraphics::RenderAndCacheNativeControl(X11Pixmap* pPixmap, X11Pixmap* pMask, int nX, int nY, + ControlCacheKey& rControlCacheKey) +{ + SAL_INFO( "vcl", "RenderAndCachePixmap" ); + X11GraphicsImpl& rImpl = dynamic_cast<X11GraphicsImpl&>(*mxImpl.get()); + return rImpl.RenderAndCacheNativeControl(pPixmap, pMask, nX, nY, rControlCacheKey); +} + extern "C" { static Bool GraphicsExposePredicate( Display*, XEvent* pEvent, XPointer pFrameWindow ) diff --git a/vcl/unx/gtk/gdi/salnativewidgets-gtk.cxx b/vcl/unx/gtk/gdi/salnativewidgets-gtk.cxx index 9da1bfa67ffa..6a0768388693 100644 --- a/vcl/unx/gtk/gdi/salnativewidgets-gtk.cxx +++ b/vcl/unx/gtk/gdi/salnativewidgets-gtk.cxx @@ -896,12 +896,23 @@ bool GtkSalGraphics::drawNativeControl(ControlType nType, ControlPart nPart, if( aClipRegion.IsNull() ) aClipRegion = aCtrlRect; + Rectangle aPixmapRect; + + // make pixmap a little larger since some themes draw decoration + // outside the rectangle, see e.g. checkbox + aPixmapRect = Rectangle(Point( aCtrlRect.Left()-1, aCtrlRect.Top()-1 ), + Size( aCtrlRect.GetWidth()+2, aCtrlRect.GetHeight()+2) ); + + ControlCacheKey aControlCacheKey(nType, nPart, nState, aPixmapRect.GetSize()); + if (TryRenderCachedNativeControl(aControlCacheKey, aPixmapRect.Left(), aPixmapRect.Top())) + return true; + clipList aClip; int nPasses = 0; GdkDrawable* gdkDrawable[2]; std::unique_ptr<GdkX11Pixmap> xPixmap; std::unique_ptr<GdkX11Pixmap> xMask; - Rectangle aPixmapRect; + if ((bNeedPixmapPaint || (nState & ControlState::DOUBLEBUFFERING)) && nType != CTRL_SCROLLBAR && nType != CTRL_SPINBOX @@ -911,11 +922,6 @@ bool GtkSalGraphics::drawNativeControl(ControlType nType, ControlPart nPart, && ! (nType == CTRL_TOOLBAR && (nPart == PART_THUMB_HORZ || nPart == PART_THUMB_VERT) ) ) { - // make pixmap a little larger since some themes draw decoration - // outside the rectangle, see e.g. checkbox - aPixmapRect = Rectangle( Point( aCtrlRect.Left()-1, aCtrlRect.Top()-1 ), - Size( aCtrlRect.GetWidth()+2, aCtrlRect.GetHeight()+2) ); - if( bNeedTwoPasses ) { xPixmap.reset( NWGetPixmapFromScreen( aPixmapRect, BG_WHITE ) ); @@ -969,7 +975,9 @@ bool GtkSalGraphics::drawNativeControl(ControlType nType, ControlPart nPart, } if( xPixmap ) - returnVal = NWRenderPixmapToScreen( xPixmap.get(), xMask.get(), aPixmapRect) && returnVal; + returnVal = returnVal && RenderAndCacheNativeControl(xPixmap.get(), xMask.get(), + aPixmapRect.Left(), aPixmapRect.Top(), + aControlCacheKey); return returnVal; } @@ -4250,7 +4258,6 @@ GdkX11Pixmap* GtkSalGraphics::NWGetPixmapFromScreen( Rectangle srcRect, int nBgC { GdkX11Pixmap* pPixmap; int nDepth = vcl_sal::getSalDisplay(GetGenericData())->GetVisual( m_nXScreen ).GetDepth(); -; pPixmap = new GdkX11Pixmap( srcRect.GetWidth(), srcRect.GetHeight(), nDepth ); |