From 57d6b92b69a31260dea0d84fcd1fc5866ada7adb Mon Sep 17 00:00:00 2001 From: Jan Holesovsky Date: Thu, 20 Nov 2014 18:49:03 +0100 Subject: windows opengl: Implement the native theming with OpenGL. Change-Id: If8eb5cef228f4eb28e16de3e3135742282403cdc --- vcl/inc/win/salgdi.h | 17 ++++++--- vcl/win/source/gdi/salgdi.cxx | 21 ++++++----- vcl/win/source/gdi/salnativewidgets-luna.cxx | 54 +++++++++++++++++++++++----- vcl/win/source/gdi/salvd.cxx | 6 ++-- vcl/win/source/gdi/winlayout.cxx | 13 ++++++- 5 files changed, 87 insertions(+), 24 deletions(-) diff --git a/vcl/inc/win/salgdi.h b/vcl/inc/win/salgdi.h index 831a7032fa8e..8d88784c805f 100644 --- a/vcl/inc/win/salgdi.h +++ b/vcl/inc/win/salgdi.h @@ -39,6 +39,7 @@ class FontSelectPattern; class ImplWinFontEntry; class ImplFontAttrCache; +class OpenGLTexture; class PhysicalFontCollection; class SalGraphicsImpl; class WinOpenGLSalGraphicsImpl; @@ -154,7 +155,7 @@ private: HBITMAP mhBitmap; /// DIBSection data. - sal_uInt8 *mpData; + sal_uInt32 *mpData; /// Mapping between the GDI position and OpenGL, to use for OpenGL drawing. SalTwoRect maRects; @@ -168,8 +169,13 @@ public: HDC getCompatibleHDC() { return mhCompatibleDC; } - /// Call the WinOpenGLSalGraphicsImpl's DrawMask(). - void DrawMask(SalColor color); + SalTwoRect getTwoRect() { return maRects; } + + /// Reset the DC with the defined color. + void fill(sal_uInt32 color); + + /// Obtain the texture; the caller must delete it after use. + OpenGLTexture* getTexture(); }; class WinSalGraphics : public SalGraphics @@ -177,9 +183,12 @@ class WinSalGraphics : public SalGraphics friend class WinSalGraphicsImpl; friend class ScopedFont; friend class OpenGLCompatibleDC; -private: + friend class WinLayout; + +protected: boost::scoped_ptr mpImpl; +private: HDC mhLocalDC; // HDC bool mbPrinter : 1; // is Printer bool mbVirDev : 1; // is VirDev diff --git a/vcl/win/source/gdi/salgdi.cxx b/vcl/win/source/gdi/salgdi.cxx index d011f3168282..678067d1add3 100644 --- a/vcl/win/source/gdi/salgdi.cxx +++ b/vcl/win/source/gdi/salgdi.cxx @@ -601,18 +601,23 @@ OpenGLCompatibleDC::~OpenGLCompatibleDC() } } -void OpenGLCompatibleDC::DrawMask(SalColor color) +void OpenGLCompatibleDC::fill(sal_uInt32 color) { - if (!mpImpl) + if (!mpData) return; - // turn what's in the mpData into a texture - OpenGLTexture aTexture(maRects.mnSrcWidth, maRects.mnSrcHeight, GL_RGBA, GL_UNSIGNED_BYTE, mpData); - CHECK_GL_ERROR(); + sal_uInt32 *p = mpData; + for (int i = maRects.mnSrcWidth * maRects.mnSrcHeight; i > 0; --i) + *p++ = color; +} - mpImpl->PreDraw(); - mpImpl->DrawMask(aTexture, color, maRects); - mpImpl->PostDraw(); +OpenGLTexture* OpenGLCompatibleDC::getTexture() +{ + if (!mpImpl) + return NULL; + + // turn what's in the mpData into a texture + return new OpenGLTexture(maRects.mnSrcWidth, maRects.mnSrcHeight, GL_RGBA, GL_UNSIGNED_BYTE, reinterpret_cast(mpData)); } WinSalGraphics::WinSalGraphics(WinSalGraphics::Type eType, bool bScreen, HWND hWnd): diff --git a/vcl/win/source/gdi/salnativewidgets-luna.cxx b/vcl/win/source/gdi/salnativewidgets-luna.cxx index 8fcc16ef2540..8c8771029145 100644 --- a/vcl/win/source/gdi/salnativewidgets-luna.cxx +++ b/vcl/win/source/gdi/salnativewidgets-luna.cxx @@ -35,6 +35,7 @@ #include "osl/module.h" +#include #include "vcl/svapp.hxx" #include @@ -1260,18 +1261,53 @@ bool WinSalGraphics::drawNativeControl( ControlType nType, rc.top = buttonRect.Top(); rc.bottom = buttonRect.Bottom()+1; - // set default text alignment - int ta = SetTextAlign( getHDC(), TA_LEFT|TA_TOP|TA_NOUPDATECP ); + OUString aCaptionStr(aCaption.replace('~', '&')); // translate mnemonics - OUString aCaptionStr( aCaption.replace('~', '&') ); // translate mnemonics - bOk = ImplDrawNativeControl(getHDC(), hTheme, rc, - nType, nPart, nState, aValue, - aCaptionStr ); + WinOpenGLSalGraphicsImpl *pImpl = dynamic_cast(mpImpl.get()); + if (pImpl == NULL) + { + // set default text alignment + int ta = SetTextAlign(getHDC(), TA_LEFT|TA_TOP|TA_NOUPDATECP); + + bOk = ImplDrawNativeControl(getHDC(), hTheme, rc, nType, nPart, nState, aValue, aCaptionStr); + + // restore alignment + SetTextAlign(getHDC(), ta); + } + else + { + // We can do OpenGL + OpenGLCompatibleDC aBlackDC(*this, buttonRect.Left(), buttonRect.Top(), buttonRect.GetWidth(), buttonRect.GetHeight()); + SetTextAlign(aBlackDC.getCompatibleHDC(), TA_LEFT|TA_TOP|TA_NOUPDATECP); + aBlackDC.fill(MAKE_SALCOLOR(0, 0, 0)); + + OpenGLCompatibleDC aWhiteDC(*this, buttonRect.Left(), buttonRect.Top(), buttonRect.GetWidth(), buttonRect.GetHeight()); + SetTextAlign(aWhiteDC.getCompatibleHDC(), TA_LEFT|TA_TOP|TA_NOUPDATECP); + aWhiteDC.fill(MAKE_SALCOLOR(0xff, 0xff, 0xff)); - // restore alignment - SetTextAlign( getHDC(), ta ); + if (ImplDrawNativeControl(aBlackDC.getCompatibleHDC(), hTheme, rc, nType, nPart, nState, aValue, aCaptionStr) && + ImplDrawNativeControl(aWhiteDC.getCompatibleHDC(), hTheme, rc, nType, nPart, nState, aValue, aCaptionStr)) + { + OpenGLTexture *pBlackTexture = aBlackDC.getTexture(); + if (!pBlackTexture) + return false; + + OpenGLTexture *pWhiteTexture = aWhiteDC.getTexture(); + if (!pWhiteTexture) + { + delete pBlackTexture; + return false; + } - //GdiFlush(); + pImpl->PreDraw(); + pImpl->DrawTexture(*pBlackTexture, aBlackDC.getTwoRect()); // FIXME combine the textures - DrawTextureSynthesizedAlpha() + pImpl->PostDraw(); + + delete pBlackTexture; + delete pWhiteTexture; + bOk = true; + } + } return bOk; } diff --git a/vcl/win/source/gdi/salvd.cxx b/vcl/win/source/gdi/salvd.cxx index 2b00c0377be3..c85133d6584c 100644 --- a/vcl/win/source/gdi/salvd.cxx +++ b/vcl/win/source/gdi/salvd.cxx @@ -38,6 +38,9 @@ HBITMAP WinSalVirtualDevice::ImplCreateVirDevBitmap(HDC hDC, long nDX, long nDY, } else { + if (nBitCount == 0) + nBitCount = (WORD)GetDeviceCaps(hDC, BITSPIXEL); + // #146839# Don't use CreateCompatibleBitmap() - there seem to // be build-in limits for those HBITMAPs, at least this fails // rather often on large displays/multi-monitor setups. @@ -46,8 +49,7 @@ HBITMAP WinSalVirtualDevice::ImplCreateVirDevBitmap(HDC hDC, long nDX, long nDY, aBitmapInfo.bmiHeader.biWidth = nDX; aBitmapInfo.bmiHeader.biHeight = nDY; aBitmapInfo.bmiHeader.biPlanes = 1; - aBitmapInfo.bmiHeader.biBitCount = (WORD)GetDeviceCaps( hDC, - BITSPIXEL ); + aBitmapInfo.bmiHeader.biBitCount = nBitCount; aBitmapInfo.bmiHeader.biCompression = BI_RGB; aBitmapInfo.bmiHeader.biSizeImage = 0; aBitmapInfo.bmiHeader.biXPelsPerMeter = 0; diff --git a/vcl/win/source/gdi/winlayout.cxx b/vcl/win/source/gdi/winlayout.cxx index 8457c559da4a..3778db308536 100644 --- a/vcl/win/source/gdi/winlayout.cxx +++ b/vcl/win/source/gdi/winlayout.cxx @@ -215,7 +215,18 @@ void WinLayout::DrawText(SalGraphics& rGraphics) const COLORREF color = GetTextColor(hDC); SalColor salColor = MAKE_SALCOLOR(GetRValue(color), GetGValue(color), GetBValue(color)); - aDC.DrawMask(salColor); + WinOpenGLSalGraphicsImpl *pImpl = dynamic_cast(rWinGraphics.mpImpl.get()); + if (pImpl) + { + OpenGLTexture *pTexture = aDC.getTexture(); + if (pTexture) + { + pImpl->PreDraw(); + pImpl->DrawMask(*pTexture, salColor, aDC.getTwoRect()); + pImpl->PostDraw(); + delete pTexture; + } + } } } -- cgit