1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
|
/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
/*
* This file is part of the LibreOffice project.
*
* This Source Code Form is subject to the terms of the Mozilla Public
* License, v. 2.0. If a copy of the MPL was not distributed with this
* file, You can obtain one at http://mozilla.org/MPL/2.0/.
*
* This file incorporates work covered by the following license notice:
*
* Licensed to the Apache Software Foundation (ASF) under one or more
* contributor license agreements. See the NOTICE file distributed
* with this work for additional information regarding copyright
* ownership. The ASF licenses this file to you under the Apache
* License, Version 2.0 (the "License"); you may not use this file
* except in compliance with the License. You may obtain a copy of
* the License at http://www.apache.org/licenses/LICENSE-2.0 .
*/
#pragma once
#include <sal/config.h>
#include <config_features.h>
#include <cairo.h>
#include <vcl/dllapi.h>
#include <vcl/region.hxx>
#include <vcl/salgtype.hxx>
#include <vcl/vclenum.hxx>
#include <vcl/BitmapBuffer.hxx>
#include <com/sun/star/drawing/LineCap.hpp>
#include <basegfx/utils/systemdependentdata.hxx>
#include <basegfx/range/b2drange.hxx>
#include <basegfx/range/b2irange.hxx>
#include <basegfx/matrix/b2dhommatrix.hxx>
#include <basegfx/polygon/b2dpolypolygon.hxx>
#include <basegfx/polygon/b2dpolygon.hxx>
#include <optional>
#include <unordered_map>
typedef struct _cairo cairo_t;
typedef struct _cairo_surface cairo_surface_t;
typedef struct _cairo_user_data_key cairo_user_data_key_t;
class Gradient;
struct SalGradient;
VCL_DLLPUBLIC void dl_cairo_surface_set_device_scale(cairo_surface_t* surface, double x_scale,
double y_scale);
VCL_DLLPUBLIC void dl_cairo_surface_get_device_scale(cairo_surface_t* surface, double* x_scale,
double* y_scale);
VCL_DLLPUBLIC basegfx::B2DRange getFillDamage(cairo_t* cr);
VCL_DLLPUBLIC basegfx::B2DRange getClipBox(cairo_t* cr);
VCL_DLLPUBLIC basegfx::B2DRange getClippedFillDamage(cairo_t* cr);
VCL_DLLPUBLIC basegfx::B2DRange getClippedStrokeDamage(cairo_t* cr);
VCL_DLLPUBLIC basegfx::B2DRange getStrokeDamage(cairo_t* cr);
class SystemDependentData_CairoPath : public basegfx::SystemDependentData
{
private:
// the path data itself
cairo_path_t* mpCairoPath;
// all other values the path data is based on and
// need to be compared with to check for data validity
bool mbNoJoin;
bool mbAntiAlias;
std::vector<double> maStroke;
public:
SystemDependentData_CairoPath(size_t nSizeMeasure, cairo_t* cr, bool bNoJoin, bool bAntiAlias,
const std::vector<double>* pStroke); // MM01
virtual ~SystemDependentData_CairoPath() override;
// read access
cairo_path_t* getCairoPath() { return mpCairoPath; }
bool getNoJoin() const { return mbNoJoin; }
bool getAntiAlias() const { return mbAntiAlias; }
const std::vector<double>& getStroke() const { return maStroke; }
virtual sal_Int64 estimateUsageInBytes() const override;
};
VCL_DLLPUBLIC size_t AddPolygonToPath(cairo_t* cr, const basegfx::B2DPolygon& rPolygon,
const basegfx::B2DHomMatrix& rObjectToDevice, bool bPixelSnap,
bool bPixelSnapHairline);
VCL_DLLPUBLIC basegfx::B2DPoint impPixelSnap(const basegfx::B2DPolygon& rPolygon,
const basegfx::B2DHomMatrix& rObjectToDevice,
basegfx::B2DHomMatrix& rObjectToDeviceInv,
sal_uInt32 nIndex);
VCL_DLLPUBLIC void add_polygon_path(cairo_t* cr, const basegfx::B2DPolyPolygon& rPolyPolygon,
const basegfx::B2DHomMatrix& rObjectToDevice, bool bPixelSnap);
VCL_DLLPUBLIC cairo_format_t getCairoFormat(const BitmapBuffer& rBuffer);
VCL_DLLPUBLIC std::unique_ptr<BitmapBuffer>
FastConvert24BitRgbTo32BitCairo(const BitmapBuffer* pSrc);
VCL_DLLPUBLIC void Toggle1BitTransparency(const BitmapBuffer& rBuf);
enum class PaintMode
{
Over,
Xor
};
typedef void (*damageHandler)(void* handle, sal_Int32 nExtentsX, sal_Int32 nExtentsY,
sal_Int32 nExtentsWidth, sal_Int32 nExtentsHeight);
struct VCL_DLLPUBLIC DamageHandler
{
void* handle;
damageHandler damaged;
};
struct VCL_DLLPUBLIC CairoCommon
{
cairo_surface_t* m_pSurface;
basegfx::B2IVector m_aFrameSize;
vcl::Region m_aClipRegion;
std::optional<Color> m_oLineColor;
std::optional<Color> m_oFillColor;
PaintMode m_ePaintMode;
double m_fScale;
CairoCommon()
: m_pSurface(nullptr)
, m_oLineColor(Color(0x00, 0x00, 0x00))
, m_oFillColor(Color(0xFF, 0xFF, 0XFF))
, m_ePaintMode(PaintMode::Over)
, m_fScale(1.0)
{
}
static cairo_user_data_key_t* getDamageKey();
cairo_surface_t* getSurface() const { return m_pSurface; }
cairo_t* getCairoContext(bool bXorModeAllowed, bool bAntiAlias) const;
void releaseCairoContext(cairo_t* cr, bool bXorModeAllowed,
const basegfx::B2DRange& rExtents) const;
cairo_t* createTmpCompatibleCairoContext() const;
static void applyColor(cairo_t* cr, Color rColor, double fTransparency = 0.0);
void clipRegion(cairo_t* cr);
static void clipRegion(cairo_t* cr, const vcl::Region& rClipRegion);
static void drawPixel(cairo_t* cr, basegfx::B2DRange* pExtents,
const std::optional<Color>& rLineColor, tools::Long nX, tools::Long nY);
static Color getPixel(cairo_surface_t* pSurface, tools::Long nX, tools::Long nY);
static void drawLine(cairo_t* cr, basegfx::B2DRange* pExtents, const Color& rLineColor,
bool bAntiAlias, tools::Long nX1, tools::Long nY1, tools::Long nX2,
tools::Long nY2);
static void drawRect(cairo_t* cr, basegfx::B2DRange* pExtents,
const std::optional<Color>& rLineColor,
const std::optional<Color>& rFillColor, bool bAntiAlias, double nX,
double nY, double nWidth, double nHeight);
static void drawPolygon(cairo_t* cr, basegfx::B2DRange* pExtents,
const std::optional<Color>& rLineColor,
const std::optional<Color>& rFillColor, bool bAntiAlias,
sal_uInt32 nPoints, const Point* pPtAry);
static void drawPolyPolygon(cairo_t* cr, basegfx::B2DRange* pExtents,
const std::optional<Color>& rLineColor,
const std::optional<Color>& rFillColor, bool bAntiAlias,
sal_uInt32 nPoly, const sal_uInt32* pPoints, const Point** pPtAry);
static bool drawPolyPolygon(cairo_t* cr, basegfx::B2DRange* pExtents,
const std::optional<Color>& rLineColor,
const std::optional<Color>& rFillColor, bool bAntiAlias,
const basegfx::B2DHomMatrix& rObjectToDevice,
const basegfx::B2DPolyPolygon&, double fTransparency);
static void drawPolyLine(cairo_t* cr, basegfx::B2DRange* pExtents, const Color& rLineColor,
bool bAntiAlias, sal_uInt32 nPoints, const Point* pPtAry);
static bool drawPolyLine(cairo_t* cr, basegfx::B2DRange* pExtents, const Color& rLineColor,
bool bAntiAlias, const basegfx::B2DHomMatrix& rObjectToDevice,
const basegfx::B2DPolygon& rPolyLine, double fTransparency,
double fLineWidth, const std::vector<double>* pStroke,
basegfx::B2DLineJoin eLineJoin, css::drawing::LineCap eLineCap,
double fMiterMinimumAngle, bool bPixelSnapHairline);
static bool drawAlphaRect(cairo_t* cr, basegfx::B2DRange* pExtents,
const std::optional<Color>& rLineColor,
const std::optional<Color>& rFillColor, tools::Long nX,
tools::Long nY, tools::Long nWidth, tools::Long nHeight,
sal_uInt8 nTransparency);
static bool drawGradient(cairo_t* cr, basegfx::B2DRange* pExtents, bool bAntiAlias,
const tools::PolyPolygon& rPolyPolygon, const Gradient& rGradient);
static bool implDrawGradient(cairo_t* cr, basegfx::B2DRange* pExtents, bool bAntiAlias,
basegfx::B2DPolyPolygon const& rPolyPolygon,
SalGradient const& rGradient);
void copyWithOperator(const SalTwoRect& rTR, cairo_surface_t* source, cairo_operator_t eOp,
bool bAntiAlias);
void copySource(const SalTwoRect& rTR, cairo_surface_t* source, bool bAntiAlias);
static basegfx::B2DRange renderSource(cairo_t* cr, const SalTwoRect& rTR,
cairo_surface_t* source);
void copyBitsCairo(const SalTwoRect& rTR, cairo_surface_t* pSourceSurface, bool bAntiAlias);
void invert(const basegfx::B2DPolygon& rPoly, SalInvert nFlags, bool bAntiAlias);
static cairo_surface_t* createCairoSurface(const BitmapBuffer* pBuffer);
static bool supportsOperation(OutDevSupportType eType);
static bool hasFastDrawTransformedBitmap();
private:
void doXorOnRelease(sal_Int32 nExtentsLeft, sal_Int32 nExtentsTop, sal_Int32 nExtentsRight,
sal_Int32 nExtentsBottom, cairo_surface_t* const surface,
sal_Int32 nWidth) const;
};
class SurfaceHelper
{
private:
cairo_surface_t* pSurface;
std::unordered_map<sal_uInt64, cairo_surface_t*> maDownscaled;
SurfaceHelper(const SurfaceHelper&) = delete;
SurfaceHelper& operator=(const SurfaceHelper&) = delete;
cairo_surface_t* implCreateOrReuseDownscale(unsigned long nTargetWidth,
unsigned long nTargetHeight);
protected:
cairo_surface_t* implGetSurface() const { return pSurface; }
void implSetSurface(cairo_surface_t* pNew) { pSurface = pNew; }
bool isTrivial() const;
public:
explicit SurfaceHelper();
~SurfaceHelper();
cairo_surface_t* getSurface(unsigned long nTargetWidth = 0,
unsigned long nTargetHeight = 0) const;
};
/* vim:set shiftwidth=4 softtabstop=4 expandtab: */
|