1 /* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
3 * This file is part of the LibreOffice project.
5 * This Source Code Form is subject to the terms of the Mozilla Public
6 * License, v. 2.0. If a copy of the MPL was not distributed with this
7 * file, You can obtain one at http://mozilla.org/MPL/2.0/.
9 * This file incorporates work covered by the following license notice:
11 * Licensed to the Apache Software Foundation (ASF) under one or more
12 * contributor license agreements. See the NOTICE file distributed
13 * with this work for additional information regarding copyright
14 * ownership. The ASF licenses this file to you under the Apache
15 * License, Version 2.0 (the "License"); you may not use this file
16 * except in compliance with the License. You may obtain a copy of
17 * the License at http://www.apache.org/licenses/LICENSE-2.0 .
24 #include <tools/debug.hxx>
26 #include <win/wincomp.hxx>
27 #include <win/salbmp.h>
28 #include <win/saldata.hxx>
29 #include <win/salids.hrc>
30 #include <win/salgdi.h>
31 #include <win/salframe.h>
32 #include <opengl/salbmp.hxx>
34 #include <vcl/salbtype.hxx>
35 #include <vcl/bitmapaccess.hxx>
36 #include "outdata.hxx"
37 #include "salgdiimpl.hxx"
38 #include "opengl/win/gdiimpl.hxx"
41 bool WinSalGraphics::supportsOperation( OutDevSupportType eType
) const
43 static bool bAllowForTest(true);
48 case OutDevSupportType::TransparentRect
:
49 bRet
= mbVirDev
|| mbWindow
;
51 case OutDevSupportType::B2DDraw
:
59 void WinSalGraphics::copyBits( const SalTwoRect
& rPosAry
, SalGraphics
* pSrcGraphics
)
61 mpImpl
->copyBits( rPosAry
, pSrcGraphics
);
64 void WinSalGraphics::copyArea( long nDestX
, long nDestY
,
65 long nSrcX
, long nSrcY
,
66 long nSrcWidth
, long nSrcHeight
,
67 bool bWindowInvalidate
)
69 mpImpl
->copyArea( nDestX
, nDestY
, nSrcX
, nSrcY
,
70 nSrcWidth
, nSrcHeight
, bWindowInvalidate
);
76 class ColorScanlineConverter
79 ScanlineFormat meSourceFormat
;
80 ScanlineFormat meDestinationFormat
;
83 int mnComponentExchangeIndex
;
87 ColorScanlineConverter(ScanlineFormat eSourceFormat
, ScanlineFormat eDestinationFormat
, int nComponentSize
, long nScanlineSize
)
88 : meSourceFormat(eSourceFormat
)
89 , meDestinationFormat(eDestinationFormat
)
90 , mnComponentSize(nComponentSize
)
91 , mnComponentExchangeIndex(0)
92 , mnScanlineSize(nScanlineSize
)
94 if (meSourceFormat
== ScanlineFormat::N32BitTcAbgr
||
95 meSourceFormat
== ScanlineFormat::N32BitTcArgb
)
97 mnComponentExchangeIndex
= 1;
101 void convertScanline(sal_uInt8
* pSource
, sal_uInt8
* pDestination
)
103 for (int x
= 0; x
< mnScanlineSize
; x
+= mnComponentSize
)
105 for (int i
= 0; i
< mnComponentSize
; ++i
)
107 pDestination
[x
+ i
] = pSource
[x
+ i
];
109 pDestination
[x
+ mnComponentExchangeIndex
+ 0] = pSource
[x
+ mnComponentExchangeIndex
+ 2];
110 pDestination
[x
+ mnComponentExchangeIndex
+ 2] = pSource
[x
+ mnComponentExchangeIndex
+ 0];
115 void convertToWinSalBitmap(SalBitmap
& rSalBitmap
, WinSalBitmap
& rWinSalBitmap
)
117 BitmapPalette aBitmapPalette
;
118 OpenGLSalBitmap
* pGLSalBitmap
= dynamic_cast<OpenGLSalBitmap
*>(&rSalBitmap
);
119 if (pGLSalBitmap
!= nullptr)
121 aBitmapPalette
= pGLSalBitmap
->GetBitmapPalette();
124 BitmapBuffer
* pRead
= rSalBitmap
.AcquireBuffer(BitmapAccessMode::Read
);
126 rWinSalBitmap
.Create(rSalBitmap
.GetSize(), rSalBitmap
.GetBitCount(), aBitmapPalette
);
127 BitmapBuffer
* pWrite
= rWinSalBitmap
.AcquireBuffer(BitmapAccessMode::Write
);
129 sal_uInt8
* pSource(pRead
->mpBits
);
130 sal_uInt8
* pDestination(pWrite
->mpBits
);
132 std::unique_ptr
<ColorScanlineConverter
> pConverter
;
134 if (pRead
->mnFormat
== ScanlineFormat::N24BitTcRgb
)
135 pConverter
.reset(new ColorScanlineConverter(ScanlineFormat::N24BitTcRgb
, ScanlineFormat::N24BitTcBgr
,
136 3, pRead
->mnScanlineSize
));
137 else if (pRead
->mnFormat
== ScanlineFormat::N32BitTcRgba
)
138 pConverter
.reset(new ColorScanlineConverter(ScanlineFormat::N32BitTcRgba
, ScanlineFormat::N32BitTcBgra
,
139 4, pRead
->mnScanlineSize
));
142 for (long y
= 0; y
< pRead
->mnHeight
; y
++)
144 pConverter
->convertScanline(pSource
, pDestination
);
145 pSource
+= pRead
->mnScanlineSize
;
146 pDestination
+= pWrite
->mnScanlineSize
;
151 for (long y
= 0; y
< pRead
->mnHeight
; y
++)
153 memcpy(pDestination
, pSource
, pRead
->mnScanlineSize
);
154 pSource
+= pRead
->mnScanlineSize
;
155 pDestination
+= pWrite
->mnScanlineSize
;
158 rWinSalBitmap
.ReleaseBuffer(pWrite
, BitmapAccessMode::Write
);
160 rSalBitmap
.ReleaseBuffer(pRead
, BitmapAccessMode::Read
);
163 } // end anonymous namespace
165 void WinSalGraphics::drawBitmap(const SalTwoRect
& rPosAry
, const SalBitmap
& rSalBitmap
)
167 if (dynamic_cast<WinOpenGLSalGraphicsImpl
*>(mpImpl
.get()) == nullptr &&
168 dynamic_cast<const WinSalBitmap
*>(&rSalBitmap
) == nullptr)
170 std::unique_ptr
<WinSalBitmap
> pWinSalBitmap(new WinSalBitmap());
171 SalBitmap
& rConstBitmap
= const_cast<SalBitmap
&>(rSalBitmap
);
172 convertToWinSalBitmap(rConstBitmap
, *pWinSalBitmap
.get());
173 mpImpl
->drawBitmap(rPosAry
, *pWinSalBitmap
.get());
177 mpImpl
->drawBitmap(rPosAry
, rSalBitmap
);
181 void WinSalGraphics::drawBitmap( const SalTwoRect
& rPosAry
,
182 const SalBitmap
& rSSalBitmap
,
183 const SalBitmap
& rSTransparentBitmap
)
185 if (dynamic_cast<WinOpenGLSalGraphicsImpl
*>(mpImpl
.get()) == nullptr &&
186 dynamic_cast<const WinSalBitmap
*>(&rSSalBitmap
) == nullptr)
188 std::unique_ptr
<WinSalBitmap
> pWinSalBitmap(new WinSalBitmap());
189 SalBitmap
& rConstBitmap
= const_cast<SalBitmap
&>(rSSalBitmap
);
190 convertToWinSalBitmap(rConstBitmap
, *pWinSalBitmap
.get());
193 std::unique_ptr
<WinSalBitmap
> pWinTransparentSalBitmap(new WinSalBitmap());
194 SalBitmap
& rConstTransparentBitmap
= const_cast<SalBitmap
&>(rSTransparentBitmap
);
195 convertToWinSalBitmap(rConstTransparentBitmap
, *pWinTransparentSalBitmap
.get());
197 mpImpl
->drawBitmap(rPosAry
, *pWinSalBitmap
.get(), *pWinTransparentSalBitmap
.get());
201 mpImpl
->drawBitmap(rPosAry
, rSSalBitmap
, rSTransparentBitmap
);
205 bool WinSalGraphics::drawAlphaRect( long nX
, long nY
, long nWidth
,
206 long nHeight
, sal_uInt8 nTransparency
)
208 return mpImpl
->drawAlphaRect( nX
, nY
, nWidth
, nHeight
, nTransparency
);
211 void WinSalGraphics::drawMask( const SalTwoRect
& rPosAry
,
212 const SalBitmap
& rSSalBitmap
,
213 SalColor nMaskColor
)
215 mpImpl
->drawMask( rPosAry
, rSSalBitmap
, nMaskColor
);
218 SalBitmap
* WinSalGraphics::getBitmap( long nX
, long nY
, long nDX
, long nDY
)
220 return mpImpl
->getBitmap( nX
, nY
, nDX
, nDY
);
223 SalColor
WinSalGraphics::getPixel( long nX
, long nY
)
225 return mpImpl
->getPixel( nX
, nY
);
228 void WinSalGraphics::invert( long nX
, long nY
, long nWidth
, long nHeight
, SalInvert nFlags
)
230 mpImpl
->invert( nX
, nY
, nWidth
, nHeight
, nFlags
);
233 void WinSalGraphics::invert( sal_uInt32 nPoints
, const SalPoint
* pPtAry
, SalInvert nSalFlags
)
235 mpImpl
->invert( nPoints
, pPtAry
, nSalFlags
);
238 /* vim:set shiftwidth=4 softtabstop=4 expandtab: */