Version 5.4.3.2, tag libreoffice-5.4.3.2
[LibreOffice.git] / vcl / source / gdi / lineinfo.cxx
blobbb27afed837d4cf8179ef8733ba21b51a422a6d9
1 /* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
2 /*
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 .
20 #include <tools/stream.hxx>
21 #include <tools/vcompat.hxx>
22 #include <vcl/lineinfo.hxx>
23 #include <basegfx/polygon/b2dpolypolygon.hxx>
24 #include <basegfx/polygon/b2dpolygontools.hxx>
25 #include <basegfx/polygon/b2dlinegeometry.hxx>
26 #include <numeric>
29 ImplLineInfo::ImplLineInfo() :
30 meStyle ( LineStyle::Solid ),
31 mnWidth ( 0 ),
32 mnDashCount ( 0 ),
33 mnDashLen ( 0 ),
34 mnDotCount ( 0 ),
35 mnDotLen ( 0 ),
36 mnDistance ( 0 ),
37 meLineJoin ( basegfx::B2DLineJoin::Round ),
38 meLineCap ( css::drawing::LineCap_BUTT )
42 ImplLineInfo::ImplLineInfo( const ImplLineInfo& rImplLineInfo ) :
43 meStyle ( rImplLineInfo.meStyle ),
44 mnWidth ( rImplLineInfo.mnWidth ),
45 mnDashCount ( rImplLineInfo.mnDashCount ),
46 mnDashLen ( rImplLineInfo.mnDashLen ),
47 mnDotCount ( rImplLineInfo.mnDotCount ),
48 mnDotLen ( rImplLineInfo.mnDotLen ),
49 mnDistance ( rImplLineInfo.mnDistance ),
50 meLineJoin ( rImplLineInfo.meLineJoin ),
51 meLineCap ( rImplLineInfo.meLineCap )
55 inline bool ImplLineInfo::operator==( const ImplLineInfo& rB ) const
57 return(meStyle == rB.meStyle
58 && mnWidth == rB.mnWidth
59 && mnDashCount == rB.mnDashCount
60 && mnDashLen == rB.mnDashLen
61 && mnDotCount == rB.mnDotCount
62 && mnDotLen == rB.mnDotLen
63 && mnDistance == rB.mnDistance
64 && meLineJoin == rB.meLineJoin
65 && meLineCap == rB.meLineCap);
69 LineInfo::LineInfo( LineStyle eStyle, long nWidth ) : mpImplLineInfo()
71 mpImplLineInfo->meStyle = eStyle;
72 mpImplLineInfo->mnWidth = nWidth;
75 LineInfo::LineInfo( const LineInfo& rLineInfo ) : mpImplLineInfo(rLineInfo.mpImplLineInfo)
79 LineInfo::LineInfo( LineInfo&& rLineInfo ) : mpImplLineInfo(std::move(rLineInfo.mpImplLineInfo))
83 LineInfo::~LineInfo()
87 LineInfo& LineInfo::operator=( const LineInfo& rLineInfo )
89 mpImplLineInfo = rLineInfo.mpImplLineInfo;
90 return *this;
93 LineInfo& LineInfo::operator=( LineInfo&& rLineInfo )
95 mpImplLineInfo = std::move(rLineInfo.mpImplLineInfo);
96 return *this;
99 bool LineInfo::operator==( const LineInfo& rLineInfo ) const
101 return mpImplLineInfo == rLineInfo.mpImplLineInfo;
104 void LineInfo::SetStyle( LineStyle eStyle )
106 mpImplLineInfo->meStyle = eStyle;
109 void LineInfo::SetWidth( long nWidth )
111 mpImplLineInfo->mnWidth = nWidth;
114 void LineInfo::SetDashCount( sal_uInt16 nDashCount )
116 mpImplLineInfo->mnDashCount = nDashCount;
119 void LineInfo::SetDashLen( long nDashLen )
121 mpImplLineInfo->mnDashLen = nDashLen;
124 void LineInfo::SetDotCount( sal_uInt16 nDotCount )
126 mpImplLineInfo->mnDotCount = nDotCount;
129 void LineInfo::SetDotLen( long nDotLen )
131 mpImplLineInfo->mnDotLen = nDotLen;
134 void LineInfo::SetDistance( long nDistance )
136 mpImplLineInfo->mnDistance = nDistance;
139 void LineInfo::SetLineJoin(basegfx::B2DLineJoin eLineJoin)
142 if(eLineJoin != mpImplLineInfo->meLineJoin)
144 mpImplLineInfo->meLineJoin = eLineJoin;
148 void LineInfo::SetLineCap(css::drawing::LineCap eLineCap)
150 if(eLineCap != mpImplLineInfo->meLineCap)
152 mpImplLineInfo->meLineCap = eLineCap;
156 bool LineInfo::IsDefault() const
158 return( !mpImplLineInfo->mnWidth
159 && ( LineStyle::Solid == mpImplLineInfo->meStyle )
160 && ( css::drawing::LineCap_BUTT == mpImplLineInfo->meLineCap));
163 SvStream& ReadLineInfo( SvStream& rIStm, LineInfo& rLineInfo )
165 VersionCompat aCompat( rIStm, StreamMode::READ );
166 sal_uInt16 nTmp16(0);
167 sal_Int32 nTmp32(0);
169 rIStm.ReadUInt16( nTmp16 ); rLineInfo.mpImplLineInfo->meStyle = (LineStyle) nTmp16;
170 rIStm.ReadInt32( nTmp32 );
171 rLineInfo.mpImplLineInfo->mnWidth = nTmp32;
173 if( aCompat.GetVersion() >= 2 )
175 // version 2
176 rIStm.ReadUInt16( rLineInfo.mpImplLineInfo->mnDashCount ).ReadInt32( nTmp32 );
177 rLineInfo.mpImplLineInfo->mnDashLen = nTmp32;
178 rIStm.ReadUInt16( rLineInfo.mpImplLineInfo->mnDotCount ).ReadInt32( nTmp32 );
179 rLineInfo.mpImplLineInfo->mnDotLen = nTmp32;
180 rIStm.ReadInt32( nTmp32 );
181 rLineInfo.mpImplLineInfo->mnDistance = nTmp32;
184 if( aCompat.GetVersion() >= 3 )
186 // version 3
187 rIStm.ReadUInt16( nTmp16 ); rLineInfo.mpImplLineInfo->meLineJoin = (basegfx::B2DLineJoin) nTmp16;
190 if( aCompat.GetVersion() >= 4 )
192 // version 4
193 rIStm.ReadUInt16( nTmp16 ); rLineInfo.mpImplLineInfo->meLineCap = (css::drawing::LineCap) nTmp16;
196 return rIStm;
199 SvStream& WriteLineInfo( SvStream& rOStm, const LineInfo& rLineInfo )
201 VersionCompat aCompat( rOStm, StreamMode::WRITE, 4 );
203 // version 1
204 rOStm.WriteUInt16( (sal_uInt16)rLineInfo.mpImplLineInfo->meStyle )
205 .WriteInt32( rLineInfo.mpImplLineInfo->mnWidth );
207 // since version2
208 rOStm.WriteUInt16( rLineInfo.mpImplLineInfo->mnDashCount )
209 .WriteInt32( rLineInfo.mpImplLineInfo->mnDashLen );
210 rOStm.WriteUInt16( rLineInfo.mpImplLineInfo->mnDotCount )
211 .WriteInt32( rLineInfo.mpImplLineInfo->mnDotLen );
212 rOStm.WriteInt32( rLineInfo.mpImplLineInfo->mnDistance );
214 // since version3
215 rOStm.WriteUInt16( static_cast<sal_uInt16>(rLineInfo.mpImplLineInfo->meLineJoin) );
217 // since version4
218 rOStm.WriteUInt16( (sal_uInt16)rLineInfo.mpImplLineInfo->meLineCap );
220 return rOStm;
223 void LineInfo::applyToB2DPolyPolygon(
224 basegfx::B2DPolyPolygon& io_rLinePolyPolygon,
225 basegfx::B2DPolyPolygon& o_rFillPolyPolygon) const
227 o_rFillPolyPolygon.clear();
229 if(io_rLinePolyPolygon.count())
231 if(LineStyle::Dash == GetStyle())
233 ::std::vector< double > fDotDashArray;
234 const double fDashLen(GetDashLen());
235 const double fDotLen(GetDotLen());
236 const double fDistance(GetDistance());
238 for(sal_uInt16 a(0); a < GetDashCount(); a++)
240 fDotDashArray.push_back(fDashLen);
241 fDotDashArray.push_back(fDistance);
244 for(sal_uInt16 b(0); b < GetDotCount(); b++)
246 fDotDashArray.push_back(fDotLen);
247 fDotDashArray.push_back(fDistance);
250 const double fAccumulated(::std::accumulate(fDotDashArray.begin(), fDotDashArray.end(), 0.0));
252 if(fAccumulated > 0.0)
254 basegfx::B2DPolyPolygon aResult;
256 for(sal_uInt32 c(0); c < io_rLinePolyPolygon.count(); c++)
258 basegfx::B2DPolyPolygon aLineTraget;
259 basegfx::tools::applyLineDashing(
260 io_rLinePolyPolygon.getB2DPolygon(c),
261 fDotDashArray,
262 &aLineTraget);
263 aResult.append(aLineTraget);
266 io_rLinePolyPolygon = aResult;
270 if(GetWidth() > 1 && io_rLinePolyPolygon.count())
272 const double fHalfLineWidth((GetWidth() * 0.5) + 0.5);
274 for(sal_uInt32 a(0); a < io_rLinePolyPolygon.count(); a++)
276 o_rFillPolyPolygon.append(basegfx::tools::createAreaGeometry(
277 io_rLinePolyPolygon.getB2DPolygon(a),
278 fHalfLineWidth,
279 GetLineJoin(),
280 GetLineCap()));
283 io_rLinePolyPolygon.clear();
288 /* vim:set shiftwidth=4 softtabstop=4 expandtab: */