[Libreoffice-commits] core.git: 2 commits - include/vcl vcl/inc vcl/source vcl/win
Jan Holesovsky
kendy at collabora.com
Thu Nov 20 09:53:47 PST 2014
include/vcl/salgtype.hxx | 7 +++
vcl/inc/win/salgdi.h | 44 ++++++++++++++++++-
vcl/source/outdev/bitmap.cxx | 6 +-
vcl/win/source/gdi/salgdi.cxx | 55 +++++++++++++++++++++++
vcl/win/source/gdi/salnativewidgets-luna.cxx | 54 +++++++++++++++++++----
vcl/win/source/gdi/salvd.cxx | 6 +-
vcl/win/source/gdi/winlayout.cxx | 62 +++++++--------------------
7 files changed, 175 insertions(+), 59 deletions(-)
New commits:
commit 57d6b92b69a31260dea0d84fcd1fc5866ada7adb
Author: Jan Holesovsky <kendy at collabora.com>
Date: Thu Nov 20 18:49:03 2014 +0100
windows opengl: Implement the native theming with OpenGL.
Change-Id: If8eb5cef228f4eb28e16de3e3135742282403cdc
diff --git a/vcl/inc/win/salgdi.h b/vcl/inc/win/salgdi.h
index 831a703..8d88784 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<SalGraphicsImpl> 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 d011f31..678067d 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<sal_uInt8*>(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 8fcc16e..8c87710 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 <opengl/win/gdiimpl.hxx>
#include "vcl/svapp.hxx"
#include <vcl/settings.hxx>
@@ -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<WinOpenGLSalGraphicsImpl*>(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 2b00c03..c85133d 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 8457c55..3778db3 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<WinOpenGLSalGraphicsImpl*>(rWinGraphics.mpImpl.get());
+ if (pImpl)
+ {
+ OpenGLTexture *pTexture = aDC.getTexture();
+ if (pTexture)
+ {
+ pImpl->PreDraw();
+ pImpl->DrawMask(*pTexture, salColor, aDC.getTwoRect());
+ pImpl->PostDraw();
+ delete pTexture;
+ }
+ }
}
}
commit 3f94c9e9ddfd807b449f3bb9b232cf2041fa12d2
Author: Jan Holesovsky <kendy at collabora.com>
Date: Thu Nov 20 14:14:30 2014 +0100
windows opengl: Introduce OpenGLCompatibleDC.
This is to abstract the compatible DC creation and usage, to be reused in the
native theme rendering.
Change-Id: Id34bba4aeea7f46fc2aa42f292f0a525d753b8d7
diff --git a/include/vcl/salgtype.hxx b/include/vcl/salgtype.hxx
index dc21904..23b8977 100644
--- a/include/vcl/salgtype.hxx
+++ b/include/vcl/salgtype.hxx
@@ -46,6 +46,13 @@ struct SalTwoRect
long mnDestY;
long mnDestWidth;
long mnDestHeight;
+
+ SalTwoRect() {}
+
+ SalTwoRect(long nSrcX, long nSrcY, long nSrcWidth, long nSrcHeight, long nDestX, long nDestY, long nDestWidth, long nDestHeight)
+ : mnSrcX(nSrcX), mnSrcY(nSrcY), mnSrcWidth(nSrcWidth), mnSrcHeight(nSrcHeight), mnDestX(nDestX), mnDestY(nDestY), mnDestWidth(nDestWidth), mnDestHeight(nDestHeight)
+ {
+ }
};
typedef sal_uInt16 SalROPColor;
diff --git a/vcl/inc/win/salgdi.h b/vcl/inc/win/salgdi.h
index 74e8fe0..831a703 100644
--- a/vcl/inc/win/salgdi.h
+++ b/vcl/inc/win/salgdi.h
@@ -41,6 +41,7 @@ class ImplWinFontEntry;
class ImplFontAttrCache;
class PhysicalFontCollection;
class SalGraphicsImpl;
+class WinOpenGLSalGraphicsImpl;
#define RGB_TO_PALRGB(nRGB) ((nRGB)|0x02000000)
#define PALRGB_TO_RGB(nPalRGB) ((nPalRGB)&0x00ffffff)
@@ -139,11 +140,43 @@ public:
bool IsGSUBstituted( sal_UCS4 ) const;
};
+/** Class that creates (and destroys) a compatible Device Context.
+
+This is to be used for GDI drawing into a DIB that we later use as a texture for OpenGL drawing.
+*/
+class OpenGLCompatibleDC
+{
+private:
+ /// The compatible DC that we create for our purposes.
+ HDC mhCompatibleDC;
+
+ /// DIBSection that we use for the GDI drawing, and later obtain.
+ HBITMAP mhBitmap;
+
+ /// DIBSection data.
+ sal_uInt8 *mpData;
+
+ /// Mapping between the GDI position and OpenGL, to use for OpenGL drawing.
+ SalTwoRect maRects;
+
+ /// The OpenGL-based SalGraphicsImpl where we will draw. If null, we ignora the drawing, it means it happened directly to the DC..
+ WinOpenGLSalGraphicsImpl *mpImpl;
+
+public:
+ OpenGLCompatibleDC(SalGraphics &rGraphics, int x, int y, int width, int height);
+ ~OpenGLCompatibleDC();
+
+ HDC getCompatibleHDC() { return mhCompatibleDC; }
+
+ /// Call the WinOpenGLSalGraphicsImpl's DrawMask().
+ void DrawMask(SalColor color);
+};
+
class WinSalGraphics : public SalGraphics
{
friend class WinSalGraphicsImpl;
friend class ScopedFont;
- friend class WinLayout;
+ friend class OpenGLCompatibleDC;
private:
boost::scoped_ptr<SalGraphicsImpl> mpImpl;
diff --git a/vcl/source/outdev/bitmap.cxx b/vcl/source/outdev/bitmap.cxx
index 93c37c4..93a04b8 100644
--- a/vcl/source/outdev/bitmap.cxx
+++ b/vcl/source/outdev/bitmap.cxx
@@ -653,12 +653,12 @@ void OutputDevice::DrawDeviceAlphaBitmap( const Bitmap& rBmp, const AlphaMask& r
if(bTryDirectPaint)
{
Point aRelPt = aOutPt + Point( mnOutOffX, mnOutOffY );
- SalTwoRect aTR = {
+ SalTwoRect aTR(
rSrcPtPixel.X(), rSrcPtPixel.Y(),
rSrcSizePixel.Width(), rSrcSizePixel.Height(),
aRelPt.X(), aRelPt.Y(),
- aOutSz.Width(), aOutSz.Height()
- };
+ aOutSz.Width(), aOutSz.Height());
+
SalBitmap* pSalSrcBmp = rBmp.ImplGetImpBitmap()->ImplGetSalBitmap();
SalBitmap* pSalAlphaBmp = rAlpha.ImplGetImpBitmap()->ImplGetSalBitmap();
diff --git a/vcl/win/source/gdi/salgdi.cxx b/vcl/win/source/gdi/salgdi.cxx
index 1004fbb..d011f31 100644
--- a/vcl/win/source/gdi/salgdi.cxx
+++ b/vcl/win/source/gdi/salgdi.cxx
@@ -30,6 +30,7 @@
#include <win/saldata.hxx>
#include <win/salgdi.h>
#include <win/salframe.h>
+#include <win/salvd.h>
#include <basegfx/matrix/b2dhommatrixtools.hxx>
#include "salgdiimpl.hxx"
@@ -565,6 +566,55 @@ void ImplClearHDCCache( SalData* pData )
}
}
+OpenGLCompatibleDC::OpenGLCompatibleDC(SalGraphics &rGraphics, int x, int y, int width, int height)
+ : mhBitmap(0)
+ , mpData(NULL)
+ , maRects(0, 0, width, height, x, y, width, height)
+{
+ WinSalGraphics& rWinGraphics = static_cast<WinSalGraphics&>(rGraphics);
+ mpImpl = dynamic_cast<WinOpenGLSalGraphicsImpl*>(rWinGraphics.mpImpl.get());
+
+ if (!mpImpl)
+ {
+ // we avoid the OpenGL drawing, instead we draw directly to the DC
+ mhCompatibleDC = rWinGraphics.getHDC();
+ return;
+ }
+
+ mhCompatibleDC = CreateCompatibleDC(rWinGraphics.getHDC());
+
+ // move the origin so that we always paint at 0,0 - to keep the bitmap
+ // small
+ OffsetViewportOrgEx(mhCompatibleDC, -x, -y, NULL);
+
+ mhBitmap = WinSalVirtualDevice::ImplCreateVirDevBitmap(mhCompatibleDC, width, height, 32, reinterpret_cast<void **>(&mpData));
+
+ SelectObject(mhCompatibleDC, mhBitmap);
+}
+
+OpenGLCompatibleDC::~OpenGLCompatibleDC()
+{
+ if (mpImpl)
+ {
+ DeleteObject(mhBitmap);
+ DeleteDC(mhCompatibleDC);
+ }
+}
+
+void OpenGLCompatibleDC::DrawMask(SalColor color)
+{
+ if (!mpImpl)
+ 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();
+
+ mpImpl->PreDraw();
+ mpImpl->DrawMask(aTexture, color, maRects);
+ mpImpl->PostDraw();
+}
+
WinSalGraphics::WinSalGraphics(WinSalGraphics::Type eType, bool bScreen, HWND hWnd):
mhLocalDC(0),
mbPrinter(eType == WinSalGraphics::PRINTER),
diff --git a/vcl/win/source/gdi/winlayout.cxx b/vcl/win/source/gdi/winlayout.cxx
index 1d461e6..8457c55 100644
--- a/vcl/win/source/gdi/winlayout.cxx
+++ b/vcl/win/source/gdi/winlayout.cxx
@@ -27,7 +27,6 @@
#include <vcl/opengl/OpenGLHelper.hxx>
#include <win/salgdi.h>
#include <win/saldata.hxx>
-#include <win/salvd.h>
#include "sft.hxx"
#include "sallayout.hxx"
@@ -195,64 +194,28 @@ void WinLayout::DrawText(SalGraphics& rGraphics) const
Rectangle aRect;
GetBoundRect(rGraphics, aRect);
- const int origin_x = aRect.Left();
- const int origin_y = aRect.Top();
- const int width = aRect.GetWidth();
- const int height = aRect.GetHeight();
- const int bpp = 32;
+ OpenGLCompatibleDC aDC(rGraphics, aRect.Left(), aRect.Top(), aRect.GetWidth(), aRect.GetHeight());
- HDC compatibleDC = CreateCompatibleDC(hDC);
-
- // move the origin so that we always paint at 0,0 - to keep the bitmap
- // small
- OffsetViewportOrgEx(compatibleDC, -origin_x, -origin_y, NULL);
-
- sal_uInt8 *data;
- HBITMAP hBitmap = WinSalVirtualDevice::ImplCreateVirDevBitmap(compatibleDC, width, height, bpp, reinterpret_cast<void **>(&data));
+ // we are making changes to the DC, make sure we got a new one
+ assert(aDC.getCompatibleHDC() != hDC);
// setup the hidden DC with black color and white background, we will
// use the result of the text drawing later as a mask only
- HGDIOBJ hBitmapOld = SelectObject(compatibleDC, hBitmap);
- SelectFont(compatibleDC, mhFont);
+ SelectFont(aDC.getCompatibleHDC(), mhFont);
- SetTextColor(compatibleDC, RGB(0, 0, 0));
- SetBkColor(compatibleDC, RGB(255, 255, 255));
+ SetTextColor(aDC.getCompatibleHDC(), RGB(0, 0, 0));
+ SetBkColor(aDC.getCompatibleHDC(), RGB(255, 255, 255));
UINT nTextAlign = GetTextAlign(hDC);
- SetTextAlign(compatibleDC, nTextAlign);
+ SetTextAlign(aDC.getCompatibleHDC(), nTextAlign);
// the actual drawing
- DrawTextImpl(compatibleDC);
+ DrawTextImpl(aDC.getCompatibleHDC());
- SelectObject(compatibleDC, hBitmapOld);
+ COLORREF color = GetTextColor(hDC);
+ SalColor salColor = MAKE_SALCOLOR(GetRValue(color), GetGValue(color), GetBValue(color));
- // and turn it into a texture
- OpenGLTexture aTexture(width, height, GL_RGBA, GL_UNSIGNED_BYTE, data);
- CHECK_GL_ERROR();
-
- WinOpenGLSalGraphicsImpl *pImpl = dynamic_cast<WinOpenGLSalGraphicsImpl*>(rWinGraphics.mpImpl.get());
- if (pImpl)
- {
- SalTwoRect aRects;
- aRects.mnSrcX = 0;
- aRects.mnSrcY = 0;
- aRects.mnSrcWidth = width;
- aRects.mnSrcHeight = height;
- aRects.mnDestX = origin_x;
- aRects.mnDestY = origin_y;
- aRects.mnDestWidth = width;
- aRects.mnDestHeight = height;
-
- COLORREF color = GetTextColor(hDC);
- SalColor salColor = MAKE_SALCOLOR(GetRValue(color), GetGValue(color), GetBValue(color));
-
- pImpl->PreDraw();
- pImpl->DrawMask(aTexture, salColor, aRects);
- pImpl->PostDraw();
- }
-
- DeleteObject(hBitmap);
- DeleteDC(compatibleDC);
+ aDC.DrawMask(salColor);
}
}
More information about the Libreoffice-commits
mailing list