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 .
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/BitmapAccessMode.hxx>
35 #include <vcl/BitmapBuffer.hxx>
36 #include <vcl/BitmapPalette.hxx>
37 #include <vcl/Scanline.hxx>
38 #include <vcl/bitmapaccess.hxx>
39 #include <outdata.hxx>
40 #include <salgdiimpl.hxx>
41 #include <opengl/win/gdiimpl.hxx>
43 #include <config_features.h>
45 #include <skia/win/gdiimpl.hxx>
46 #include <skia/salbmp.hxx>
50 bool WinSalGraphics::supportsOperation( OutDevSupportType eType
) const
52 return mpImpl
->supportsOperation(eType
);
55 void WinSalGraphics::copyBits( const SalTwoRect
& rPosAry
, SalGraphics
* pSrcGraphics
)
57 mpImpl
->copyBits( rPosAry
, pSrcGraphics
);
60 void WinSalGraphics::copyArea( tools::Long nDestX
, tools::Long nDestY
,
61 tools::Long nSrcX
, tools::Long nSrcY
,
62 tools::Long nSrcWidth
, tools::Long nSrcHeight
,
63 bool bWindowInvalidate
)
65 mpImpl
->copyArea( nDestX
, nDestY
, nSrcX
, nSrcY
,
66 nSrcWidth
, nSrcHeight
, bWindowInvalidate
);
72 class ColorScanlineConverter
75 ScanlineFormat meSourceFormat
;
78 int mnComponentExchangeIndex
;
80 tools::Long mnScanlineSize
;
82 ColorScanlineConverter(ScanlineFormat eSourceFormat
, int nComponentSize
, tools::Long nScanlineSize
)
83 : meSourceFormat(eSourceFormat
)
84 , mnComponentSize(nComponentSize
)
85 , mnComponentExchangeIndex(0)
86 , mnScanlineSize(nScanlineSize
)
88 if (meSourceFormat
== ScanlineFormat::N32BitTcAbgr
||
89 meSourceFormat
== ScanlineFormat::N32BitTcArgb
)
91 mnComponentExchangeIndex
= 1;
95 void convertScanline(sal_uInt8
* pSource
, sal_uInt8
* pDestination
)
97 for (tools::Long x
= 0; x
< mnScanlineSize
; x
+= mnComponentSize
)
99 for (int i
= 0; i
< mnComponentSize
; ++i
)
101 pDestination
[x
+ i
] = pSource
[x
+ i
];
103 pDestination
[x
+ mnComponentExchangeIndex
+ 0] = pSource
[x
+ mnComponentExchangeIndex
+ 2];
104 pDestination
[x
+ mnComponentExchangeIndex
+ 2] = pSource
[x
+ mnComponentExchangeIndex
+ 0];
109 void convertToWinSalBitmap(SalBitmap
& rSalBitmap
, WinSalBitmap
& rWinSalBitmap
)
111 BitmapPalette aBitmapPalette
;
112 OpenGLSalBitmap
* pGLSalBitmap
= dynamic_cast<OpenGLSalBitmap
*>(&rSalBitmap
);
113 if (pGLSalBitmap
!= nullptr)
115 aBitmapPalette
= pGLSalBitmap
->GetBitmapPalette();
117 #if HAVE_FEATURE_SKIA
118 if(SkiaSalBitmap
* pSkiaSalBitmap
= dynamic_cast<SkiaSalBitmap
*>(&rSalBitmap
))
119 aBitmapPalette
= pSkiaSalBitmap
->Palette();
122 BitmapBuffer
* pRead
= rSalBitmap
.AcquireBuffer(BitmapAccessMode::Read
);
124 rWinSalBitmap
.Create(rSalBitmap
.GetSize(), rSalBitmap
.GetBitCount(), aBitmapPalette
);
125 BitmapBuffer
* pWrite
= rWinSalBitmap
.AcquireBuffer(BitmapAccessMode::Write
);
127 sal_uInt8
* pSource(pRead
->mpBits
);
128 sal_uInt8
* pDestination(pWrite
->mpBits
);
129 tools::Long readRowChange
= pRead
->mnScanlineSize
;
130 if(pRead
->mnFormat
& ScanlineFormat::TopDown
)
132 pSource
+= pRead
->mnScanlineSize
* (pRead
->mnHeight
- 1);
133 readRowChange
= -readRowChange
;
136 std::unique_ptr
<ColorScanlineConverter
> pConverter
;
138 if (RemoveScanline(pRead
->mnFormat
) == ScanlineFormat::N24BitTcRgb
)
139 pConverter
.reset(new ColorScanlineConverter(ScanlineFormat::N24BitTcRgb
,
140 3, pRead
->mnScanlineSize
));
141 else if (RemoveScanline(pRead
->mnFormat
) == ScanlineFormat::N32BitTcRgba
)
142 pConverter
.reset(new ColorScanlineConverter(ScanlineFormat::N32BitTcRgba
,
143 4, pRead
->mnScanlineSize
));
146 for (tools::Long y
= 0; y
< pRead
->mnHeight
; y
++)
148 pConverter
->convertScanline(pSource
, pDestination
);
149 pSource
+= readRowChange
;
150 pDestination
+= pWrite
->mnScanlineSize
;
155 for (tools::Long y
= 0; y
< pRead
->mnHeight
; y
++)
157 memcpy(pDestination
, pSource
, pRead
->mnScanlineSize
);
158 pSource
+= readRowChange
;
159 pDestination
+= pWrite
->mnScanlineSize
;
162 rWinSalBitmap
.ReleaseBuffer(pWrite
, BitmapAccessMode::Write
);
164 rSalBitmap
.ReleaseBuffer(pRead
, BitmapAccessMode::Read
);
167 } // end anonymous namespace
169 void WinSalGraphics::drawBitmap(const SalTwoRect
& rPosAry
, const SalBitmap
& rSalBitmap
)
171 if (dynamic_cast<WinOpenGLSalGraphicsImpl
*>(mpImpl
.get()) == nullptr &&
172 #if HAVE_FEATURE_SKIA
173 dynamic_cast<WinSkiaSalGraphicsImpl
*>(mpImpl
.get()) == nullptr &&
175 dynamic_cast<const WinSalBitmap
*>(&rSalBitmap
) == nullptr)
177 std::unique_ptr
<WinSalBitmap
> pWinSalBitmap(new WinSalBitmap());
178 SalBitmap
& rConstBitmap
= const_cast<SalBitmap
&>(rSalBitmap
);
179 convertToWinSalBitmap(rConstBitmap
, *pWinSalBitmap
);
180 mpImpl
->drawBitmap(rPosAry
, *pWinSalBitmap
);
184 mpImpl
->drawBitmap(rPosAry
, rSalBitmap
);
188 void WinSalGraphics::drawBitmap( const SalTwoRect
& rPosAry
,
189 const SalBitmap
& rSSalBitmap
,
190 const SalBitmap
& rSTransparentBitmap
)
192 if (dynamic_cast<WinOpenGLSalGraphicsImpl
*>(mpImpl
.get()) == nullptr &&
193 #if HAVE_FEATURE_SKIA
194 dynamic_cast<WinSkiaSalGraphicsImpl
*>(mpImpl
.get()) == nullptr &&
196 dynamic_cast<const WinSalBitmap
*>(&rSSalBitmap
) == nullptr)
198 std::unique_ptr
<WinSalBitmap
> pWinSalBitmap(new WinSalBitmap());
199 SalBitmap
& rConstBitmap
= const_cast<SalBitmap
&>(rSSalBitmap
);
200 convertToWinSalBitmap(rConstBitmap
, *pWinSalBitmap
);
203 std::unique_ptr
<WinSalBitmap
> pWinTransparentSalBitmap(new WinSalBitmap());
204 SalBitmap
& rConstTransparentBitmap
= const_cast<SalBitmap
&>(rSTransparentBitmap
);
205 convertToWinSalBitmap(rConstTransparentBitmap
, *pWinTransparentSalBitmap
);
207 mpImpl
->drawBitmap(rPosAry
, *pWinSalBitmap
, *pWinTransparentSalBitmap
);
211 mpImpl
->drawBitmap(rPosAry
, rSSalBitmap
, rSTransparentBitmap
);
215 bool WinSalGraphics::drawAlphaRect( tools::Long nX
, tools::Long nY
, tools::Long nWidth
,
216 tools::Long nHeight
, sal_uInt8 nTransparency
)
218 return mpImpl
->drawAlphaRect( nX
, nY
, nWidth
, nHeight
, nTransparency
);
221 void WinSalGraphics::drawMask( const SalTwoRect
& rPosAry
,
222 const SalBitmap
& rSSalBitmap
,
225 mpImpl
->drawMask( rPosAry
, rSSalBitmap
, nMaskColor
);
228 std::shared_ptr
<SalBitmap
> WinSalGraphics::getBitmap( tools::Long nX
, tools::Long nY
, tools::Long nDX
, tools::Long nDY
)
230 return mpImpl
->getBitmap( nX
, nY
, nDX
, nDY
);
233 Color
WinSalGraphics::getPixel( tools::Long nX
, tools::Long nY
)
235 return mpImpl
->getPixel( nX
, nY
);
238 void WinSalGraphics::invert( tools::Long nX
, tools::Long nY
, tools::Long nWidth
, tools::Long nHeight
, SalInvert nFlags
)
240 mpImpl
->invert( nX
, nY
, nWidth
, nHeight
, nFlags
);
243 void WinSalGraphics::invert( sal_uInt32 nPoints
, const Point
* pPtAry
, SalInvert nSalFlags
)
245 mpImpl
->invert( nPoints
, pPtAry
, nSalFlags
);
248 /* vim:set shiftwidth=4 softtabstop=4 expandtab: */