1 /*************************************************************************
2  *
3  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
4  *
5  * Copyright 2000, 2010 Oracle and/or its affiliates.
6  *
7  * OpenOffice.org - a multi-platform office productivity suite
8  *
9  * This file is part of OpenOffice.org.
10  *
11  * OpenOffice.org is free software: you can redistribute it and/or modify
12  * it under the terms of the GNU Lesser General Public License version 3
13  * only, as published by the Free Software Foundation.
14  *
15  * OpenOffice.org is distributed in the hope that it will be useful,
16  * but WITHOUT ANY WARRANTY; without even the implied warranty of
17  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
18  * GNU Lesser General Public License version 3 for more details
19  * (a copy is included in the LICENSE file that accompanied this code).
20  *
21  * You should have received a copy of the GNU Lesser General Public License
22  * version 3 along with OpenOffice.org.  If not, see
23  * <http://www.openoffice.org/license.html>
24  * for a copy of the LGPLv3 License.
25  *
26  ************************************************************************/
27 
28 #include "precompiled_svx.hxx"
29 #include <svx/sdr/primitive2d/sdrellipseprimitive2d.hxx>
30 #include <basegfx/polygon/b2dpolygon.hxx>
31 #include <basegfx/polygon/b2dpolygontools.hxx>
32 #include <svx/sdr/primitive2d/sdrdecompositiontools.hxx>
33 #include <drawinglayer/primitive2d/groupprimitive2d.hxx>
34 #include <svx/sdr/primitive2d/svx_primitivetypes2d.hxx>
35 #include <basegfx/color/bcolor.hxx>
36 #include <basegfx/matrix/b2dhommatrixtools.hxx>
37 #include <drawinglayer/primitive2d/sdrdecompositiontools2d.hxx>
38 
39 //////////////////////////////////////////////////////////////////////////////
40 
41 using namespace com::sun::star;
42 
43 //////////////////////////////////////////////////////////////////////////////
44 
45 namespace drawinglayer
46 {
47 	namespace primitive2d
48 	{
49 		Primitive2DSequence SdrEllipsePrimitive2D::create2DDecomposition(const geometry::ViewInformation2D& /*aViewInformation*/) const
50 		{
51 			Primitive2DSequence aRetval;
52 
53 			// create unit outline polygon
54 			// Do use createPolygonFromUnitCircle, but let create from first quadrant to mimic old geometry creation.
55 			// This is needed to have the same look when stroke is used since the polygon start point defines the
56 			// stroke start, too.
57 			basegfx::B2DPolygon aUnitOutline(basegfx::tools::createPolygonFromUnitCircle(1));
58 
59 			// scale and move UnitEllipse to UnitObject (-1,-1 1,1) -> (0,0 1,1)
60 			const basegfx::B2DHomMatrix aUnitCorrectionMatrix(
61                 basegfx::tools::createScaleTranslateB2DHomMatrix(0.5, 0.5, 0.5, 0.5));
62 
63 			// apply to the geometry
64 			aUnitOutline.transform(aUnitCorrectionMatrix);
65 
66 			// add fill
67 			if(!getSdrLFSTAttribute().getFill().isDefault())
68 			{
69 				appendPrimitive2DReferenceToPrimitive2DSequence(aRetval,
70                     createPolyPolygonFillPrimitive(
71                         basegfx::B2DPolyPolygon(aUnitOutline),
72                         getTransform(),
73                         getSdrLFSTAttribute().getFill(),
74                         getSdrLFSTAttribute().getFillFloatTransGradient()));
75 			}
76 
77 			// add line
78 			if(getSdrLFSTAttribute().getLine().isDefault())
79 			{
80 				// create invisible line for HitTest/BoundRect
81 				appendPrimitive2DReferenceToPrimitive2DSequence(aRetval,
82 					createHiddenGeometryPrimitives2D(
83                         false,
84 						basegfx::B2DPolyPolygon(aUnitOutline),
85                         getTransform()));
86 			}
87 			else
88 			{
89 				appendPrimitive2DReferenceToPrimitive2DSequence(aRetval,
90                     createPolygonLinePrimitive(
91                         aUnitOutline,
92                         getTransform(),
93                         getSdrLFSTAttribute().getLine(),
94 						attribute::SdrLineStartEndAttribute()));
95 			}
96 
97 			// add text
98 			if(!getSdrLFSTAttribute().getText().isDefault())
99 			{
100 				appendPrimitive2DReferenceToPrimitive2DSequence(aRetval,
101                     createTextPrimitive(
102                         basegfx::B2DPolyPolygon(aUnitOutline),
103                         getTransform(),
104                         getSdrLFSTAttribute().getText(),
105                         getSdrLFSTAttribute().getLine(),
106                         false,
107                         false,
108                         false));
109 			}
110 
111 			// add shadow
112 			if(!getSdrLFSTAttribute().getShadow().isDefault())
113 			{
114                 aRetval = createEmbeddedShadowPrimitive(
115                     aRetval,
116                     getSdrLFSTAttribute().getShadow());
117 			}
118 
119 			return aRetval;
120 		}
121 
122 		SdrEllipsePrimitive2D::SdrEllipsePrimitive2D(
123 			const basegfx::B2DHomMatrix& rTransform,
124 			const attribute::SdrLineFillShadowTextAttribute& rSdrLFSTAttribute)
125 		:	BufferedDecompositionPrimitive2D(),
126 			maTransform(rTransform),
127 			maSdrLFSTAttribute(rSdrLFSTAttribute)
128 		{
129 		}
130 
131 		bool SdrEllipsePrimitive2D::operator==(const BasePrimitive2D& rPrimitive) const
132 		{
133 			if(BufferedDecompositionPrimitive2D::operator==(rPrimitive))
134 			{
135 				const SdrEllipsePrimitive2D& rCompare = (SdrEllipsePrimitive2D&)rPrimitive;
136 
137 				return (getTransform() == rCompare.getTransform()
138 					&& getSdrLFSTAttribute() == rCompare.getSdrLFSTAttribute());
139 			}
140 
141 			return false;
142 		}
143 
144 		// provide unique ID
145 		ImplPrimitrive2DIDBlock(SdrEllipsePrimitive2D, PRIMITIVE2D_ID_SDRELLIPSEPRIMITIVE2D)
146 
147 	} // end of namespace primitive2d
148 } // end of namespace drawinglayer
149 
150 //////////////////////////////////////////////////////////////////////////////
151 
152 namespace drawinglayer
153 {
154 	namespace primitive2d
155 	{
156 		Primitive2DSequence SdrEllipseSegmentPrimitive2D::create2DDecomposition(const geometry::ViewInformation2D& /*aViewInformation*/) const
157 		{
158 			Primitive2DSequence aRetval;
159 
160 			// create unit outline polygon
161 			basegfx::B2DPolygon aUnitOutline(basegfx::tools::createPolygonFromUnitEllipseSegment(mfStartAngle, mfEndAngle));
162 
163 			if(mbCloseSegment)
164 			{
165 				if(mbCloseUsingCenter)
166 				{
167 					// for compatibility, insert the center point at polygon start to get the same
168 					// line stroking pattern as the old painting mechanisms.
169 					aUnitOutline.insert(0L, basegfx::B2DPoint(0.0, 0.0));
170 				}
171 
172 				aUnitOutline.setClosed(true);
173 			}
174 
175 			// move and scale UnitEllipse to UnitObject (-1,-1 1,1) -> (0,0 1,1)
176 			const basegfx::B2DHomMatrix aUnitCorrectionMatrix(
177                 basegfx::tools::createScaleTranslateB2DHomMatrix(0.5, 0.5, 0.5, 0.5));
178 
179 			// apply to the geometry
180 			aUnitOutline.transform(aUnitCorrectionMatrix);
181 
182 			// add fill
183 			if(!getSdrLFSTAttribute().getFill().isDefault() && aUnitOutline.isClosed())
184 			{
185 				appendPrimitive2DReferenceToPrimitive2DSequence(aRetval,
186                     createPolyPolygonFillPrimitive(
187                         basegfx::B2DPolyPolygon(aUnitOutline),
188                         getTransform(),
189                         getSdrLFSTAttribute().getFill(),
190                         getSdrLFSTAttribute().getFillFloatTransGradient()));
191 			}
192 
193 			// add line
194 			if(getSdrLFSTAttribute().getLine().isDefault())
195 			{
196 				// create invisible line for HitTest/BoundRect
197 				appendPrimitive2DReferenceToPrimitive2DSequence(aRetval,
198 					createHiddenGeometryPrimitives2D(
199                         false,
200 						basegfx::B2DPolyPolygon(aUnitOutline),
201                         getTransform()));
202 			}
203 			else
204 			{
205 				appendPrimitive2DReferenceToPrimitive2DSequence(aRetval,
206                     createPolygonLinePrimitive(
207                         aUnitOutline,
208                         getTransform(),
209                         getSdrLFSTAttribute().getLine(),
210                         getSdrLFSTAttribute().getLineStartEnd()));
211 			}
212 
213 			// add text
214 			if(!getSdrLFSTAttribute().getText().isDefault())
215 			{
216 				appendPrimitive2DReferenceToPrimitive2DSequence(aRetval,
217                     createTextPrimitive(
218                         basegfx::B2DPolyPolygon(aUnitOutline),
219                         getTransform(),
220 						getSdrLFSTAttribute().getText(),
221                         getSdrLFSTAttribute().getLine(),
222                         false,
223                         false,
224                         false));
225 			}
226 
227 			// add shadow
228 			if(!getSdrLFSTAttribute().getShadow().isDefault())
229 			{
230                 aRetval = createEmbeddedShadowPrimitive(
231                     aRetval,
232                     getSdrLFSTAttribute().getShadow());
233 			}
234 
235 			return aRetval;
236 		}
237 
238 		SdrEllipseSegmentPrimitive2D::SdrEllipseSegmentPrimitive2D(
239 			const basegfx::B2DHomMatrix& rTransform,
240 			const attribute::SdrLineFillShadowTextAttribute& rSdrLFSTAttribute,
241 			double fStartAngle,
242 			double fEndAngle,
243 			bool bCloseSegment,
244 			bool bCloseUsingCenter)
245 		:	SdrEllipsePrimitive2D(rTransform, rSdrLFSTAttribute),
246 			mfStartAngle(fStartAngle),
247 			mfEndAngle(fEndAngle),
248 			mbCloseSegment(bCloseSegment),
249 			mbCloseUsingCenter(bCloseUsingCenter)
250 		{
251 		}
252 
253 		bool SdrEllipseSegmentPrimitive2D::operator==(const BasePrimitive2D& rPrimitive) const
254 		{
255 			if(SdrEllipsePrimitive2D::operator==(rPrimitive))
256 			{
257 				const SdrEllipseSegmentPrimitive2D& rCompare = (SdrEllipseSegmentPrimitive2D&)rPrimitive;
258 
259 				if(	mfStartAngle == rCompare.mfStartAngle
260 					&& mfEndAngle == rCompare.mfEndAngle
261 					&& mbCloseSegment == rCompare.mbCloseSegment
262 					&& mbCloseUsingCenter == rCompare.mbCloseUsingCenter)
263 				{
264 					return true;
265 				}
266 			}
267 
268 			return false;
269 		}
270 
271 		// provide unique ID
272 		ImplPrimitrive2DIDBlock(SdrEllipseSegmentPrimitive2D, PRIMITIVE2D_ID_SDRELLIPSESEGMENTPRIMITIVE2D)
273 
274 	} // end of namespace primitive2d
275 } // end of namespace drawinglayer
276 
277 //////////////////////////////////////////////////////////////////////////////
278 // eof
279