1*035a2f44SArmin Le Grand /**************************************************************
2*035a2f44SArmin Le Grand  *
3*035a2f44SArmin Le Grand  * Licensed to the Apache Software Foundation (ASF) under one
4*035a2f44SArmin Le Grand  * or more contributor license agreements.  See the NOTICE file
5*035a2f44SArmin Le Grand  * distributed with this work for additional information
6*035a2f44SArmin Le Grand  * regarding copyright ownership.  The ASF licenses this file
7*035a2f44SArmin Le Grand  * to you under the Apache License, Version 2.0 (the
8*035a2f44SArmin Le Grand  * "License"); you may not use this file except in compliance
9*035a2f44SArmin Le Grand  * with the License.  You may obtain a copy of the License at
10*035a2f44SArmin Le Grand  *
11*035a2f44SArmin Le Grand  *   http://www.apache.org/licenses/LICENSE-2.0
12*035a2f44SArmin Le Grand  *
13*035a2f44SArmin Le Grand  * Unless required by applicable law or agreed to in writing,
14*035a2f44SArmin Le Grand  * software distributed under the License is distributed on an
15*035a2f44SArmin Le Grand  * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
16*035a2f44SArmin Le Grand  * KIND, either express or implied.  See the License for the
17*035a2f44SArmin Le Grand  * specific language governing permissions and limitations
18*035a2f44SArmin Le Grand  * under the License.
19*035a2f44SArmin Le Grand  *
20*035a2f44SArmin Le Grand  *************************************************************/
21*035a2f44SArmin Le Grand 
22*035a2f44SArmin Le Grand 
23*035a2f44SArmin Le Grand 
24*035a2f44SArmin Le Grand // MARKER(update_precomp.py): autogen include statement, do not remove
25*035a2f44SArmin Le Grand #include "precompiled_drawinglayer.hxx"
26*035a2f44SArmin Le Grand 
27*035a2f44SArmin Le Grand #include <drawinglayer/primitive2d/graphicprimitivehelper2d.hxx>
28*035a2f44SArmin Le Grand #include <drawinglayer/animation/animationtiming.hxx>
29*035a2f44SArmin Le Grand #include <drawinglayer/primitive2d/bitmapprimitive2d.hxx>
30*035a2f44SArmin Le Grand #include <drawinglayer/primitive2d/animatedprimitive2d.hxx>
31*035a2f44SArmin Le Grand #include <drawinglayer/primitive2d/metafileprimitive2d.hxx>
32*035a2f44SArmin Le Grand #include <drawinglayer/primitive2d/transformprimitive2d.hxx>
33*035a2f44SArmin Le Grand #include <drawinglayer/primitive2d/maskprimitive2d.hxx>
34*035a2f44SArmin Le Grand #include <basegfx/polygon/b2dpolygon.hxx>
35*035a2f44SArmin Le Grand #include <basegfx/polygon/b2dpolygontools.hxx>
36*035a2f44SArmin Le Grand 
37*035a2f44SArmin Le Grand //////////////////////////////////////////////////////////////////////////////
38*035a2f44SArmin Le Grand // helper class for animated graphics
39*035a2f44SArmin Le Grand 
40*035a2f44SArmin Le Grand #include <vcl/animate.hxx>
41*035a2f44SArmin Le Grand #include <vcl/graph.hxx>
42*035a2f44SArmin Le Grand #include <vcl/virdev.hxx>
43*035a2f44SArmin Le Grand #include <vcl/svapp.hxx>
44*035a2f44SArmin Le Grand #include <vcl/metaact.hxx>
45*035a2f44SArmin Le Grand 
46*035a2f44SArmin Le Grand //////////////////////////////////////////////////////////////////////////////
47*035a2f44SArmin Le Grand // includes for testing MetafilePrimitive2D::create2DDecomposition
48*035a2f44SArmin Le Grand 
49*035a2f44SArmin Le Grand // this switch defines if the test code is included or not
50*035a2f44SArmin Le Grand #undef USE_DEBUG_CODE_TO_TEST_METAFILE_DECOMPOSE
51*035a2f44SArmin Le Grand 
52*035a2f44SArmin Le Grand #ifdef USE_DEBUG_CODE_TO_TEST_METAFILE_DECOMPOSE
53*035a2f44SArmin Le Grand #include <vcl/gradient.hxx>
54*035a2f44SArmin Le Grand #include <vcl/pngread.hxx>
55*035a2f44SArmin Le Grand #include <vcl/lineinfo.hxx>
56*035a2f44SArmin Le Grand #endif // USE_DEBUG_CODE_TO_TEST_METAFILE_DECOMPOSE
57*035a2f44SArmin Le Grand 
58*035a2f44SArmin Le Grand //////////////////////////////////////////////////////////////////////////////
59*035a2f44SArmin Le Grand 
60*035a2f44SArmin Le Grand namespace
61*035a2f44SArmin Le Grand {
62*035a2f44SArmin Le Grand 	struct animationStep
63*035a2f44SArmin Le Grand 	{
64*035a2f44SArmin Le Grand 		BitmapEx								maBitmapEx;
65*035a2f44SArmin Le Grand 		sal_uInt32								mnTime;
66*035a2f44SArmin Le Grand 	};
67*035a2f44SArmin Le Grand 
68*035a2f44SArmin Le Grand 	class animatedBitmapExPreparator
69*035a2f44SArmin Le Grand 	{
70*035a2f44SArmin Le Grand 		::Animation								maAnimation;
71*035a2f44SArmin Le Grand 		::std::vector< animationStep >			maSteps;
72*035a2f44SArmin Le Grand 
73*035a2f44SArmin Le Grand 		sal_uInt32 generateStepTime(sal_uInt32 nIndex) const;
74*035a2f44SArmin Le Grand 
75*035a2f44SArmin Le Grand 	public:
76*035a2f44SArmin Le Grand 		animatedBitmapExPreparator(const Graphic& rGraphic);
77*035a2f44SArmin Le Grand 
78*035a2f44SArmin Le Grand 		sal_uInt32 count() const { return maSteps.size(); }
79*035a2f44SArmin Le Grand 		sal_uInt32 loopCount() const { return (sal_uInt32)maAnimation.GetLoopCount(); }
80*035a2f44SArmin Le Grand 		sal_uInt32 stepTime(sal_uInt32 a) const { return maSteps[a].mnTime; }
81*035a2f44SArmin Le Grand 		const BitmapEx& stepBitmapEx(sal_uInt32 a) const { return maSteps[a].maBitmapEx; }
82*035a2f44SArmin Le Grand 	};
83*035a2f44SArmin Le Grand 
84*035a2f44SArmin Le Grand 	sal_uInt32 animatedBitmapExPreparator::generateStepTime(sal_uInt32 nIndex) const
85*035a2f44SArmin Le Grand 	{
86*035a2f44SArmin Le Grand 		const AnimationBitmap& rAnimBitmap = maAnimation.Get(sal_uInt16(nIndex));
87*035a2f44SArmin Le Grand 		sal_uInt32 nWaitTime(rAnimBitmap.nWait * 10);
88*035a2f44SArmin Le Grand 
89*035a2f44SArmin Le Grand 		// #115934#
90*035a2f44SArmin Le Grand 		// Take care of special value for MultiPage TIFFs. ATM these shall just
91*035a2f44SArmin Le Grand 		// show their first page. Later we will offer some switching when object
92*035a2f44SArmin Le Grand 		// is selected.
93*035a2f44SArmin Le Grand 		if(ANIMATION_TIMEOUT_ON_CLICK == rAnimBitmap.nWait)
94*035a2f44SArmin Le Grand 		{
95*035a2f44SArmin Le Grand 			// ATM the huge value would block the timer, so
96*035a2f44SArmin Le Grand 			// use a long time to show first page (whole day)
97*035a2f44SArmin Le Grand 			nWaitTime = 100 * 60 * 60 * 24;
98*035a2f44SArmin Le Grand 		}
99*035a2f44SArmin Le Grand 
100*035a2f44SArmin Le Grand 		// Bad trap: There are animated gifs with no set WaitTime (!).
101*035a2f44SArmin Le Grand 		// In that case use a default value.
102*035a2f44SArmin Le Grand 		if(0L == nWaitTime)
103*035a2f44SArmin Le Grand 		{
104*035a2f44SArmin Le Grand 			nWaitTime = 100L;
105*035a2f44SArmin Le Grand 		}
106*035a2f44SArmin Le Grand 
107*035a2f44SArmin Le Grand 		return nWaitTime;
108*035a2f44SArmin Le Grand 	}
109*035a2f44SArmin Le Grand 
110*035a2f44SArmin Le Grand 	animatedBitmapExPreparator::animatedBitmapExPreparator(const Graphic& rGraphic)
111*035a2f44SArmin Le Grand 	:	maAnimation(rGraphic.GetAnimation())
112*035a2f44SArmin Le Grand 	{
113*035a2f44SArmin Le Grand 		OSL_ENSURE(GRAPHIC_BITMAP == rGraphic.GetType() && rGraphic.IsAnimated(), "animatedBitmapExPreparator: graphic is not animated (!)");
114*035a2f44SArmin Le Grand 
115*035a2f44SArmin Le Grand 		// #128539# secure access to Animation, looks like there exist animated GIFs out there
116*035a2f44SArmin Le Grand 		// with a step count of zero
117*035a2f44SArmin Le Grand 		if(maAnimation.Count())
118*035a2f44SArmin Le Grand 		{
119*035a2f44SArmin Le Grand 			VirtualDevice aVirtualDevice(*Application::GetDefaultDevice());
120*035a2f44SArmin Le Grand 			VirtualDevice aVirtualDeviceMask(*Application::GetDefaultDevice(), 1L);
121*035a2f44SArmin Le Grand 
122*035a2f44SArmin Le Grand 			// Prepare VirtualDevices and their states
123*035a2f44SArmin Le Grand 			aVirtualDevice.EnableMapMode(sal_False);
124*035a2f44SArmin Le Grand 			aVirtualDeviceMask.EnableMapMode(sal_False);
125*035a2f44SArmin Le Grand 			aVirtualDevice.SetOutputSizePixel(maAnimation.GetDisplaySizePixel());
126*035a2f44SArmin Le Grand 			aVirtualDeviceMask.SetOutputSizePixel(maAnimation.GetDisplaySizePixel());
127*035a2f44SArmin Le Grand 			aVirtualDevice.Erase();
128*035a2f44SArmin Le Grand 			aVirtualDeviceMask.Erase();
129*035a2f44SArmin Le Grand 
130*035a2f44SArmin Le Grand 			for(sal_uInt16 a(0L); a < maAnimation.Count(); a++)
131*035a2f44SArmin Le Grand 			{
132*035a2f44SArmin Le Grand 				animationStep aNextStep;
133*035a2f44SArmin Le Grand 				aNextStep.mnTime = generateStepTime(a);
134*035a2f44SArmin Le Grand 
135*035a2f44SArmin Le Grand 				// prepare step
136*035a2f44SArmin Le Grand 				const AnimationBitmap& rAnimBitmap = maAnimation.Get(sal_uInt16(a));
137*035a2f44SArmin Le Grand 
138*035a2f44SArmin Le Grand 				switch(rAnimBitmap.eDisposal)
139*035a2f44SArmin Le Grand 				{
140*035a2f44SArmin Le Grand 					case DISPOSE_NOT:
141*035a2f44SArmin Le Grand 					{
142*035a2f44SArmin Le Grand 						aVirtualDevice.DrawBitmapEx(rAnimBitmap.aPosPix, rAnimBitmap.aBmpEx);
143*035a2f44SArmin Le Grand 						Bitmap aMask = rAnimBitmap.aBmpEx.GetMask();
144*035a2f44SArmin Le Grand 
145*035a2f44SArmin Le Grand 						if(aMask.IsEmpty())
146*035a2f44SArmin Le Grand 						{
147*035a2f44SArmin Le Grand 							const Point aEmpty;
148*035a2f44SArmin Le Grand 							const Rectangle aRect(aEmpty, aVirtualDeviceMask.GetOutputSizePixel());
149*035a2f44SArmin Le Grand 							const Wallpaper aWallpaper(COL_BLACK);
150*035a2f44SArmin Le Grand 							aVirtualDeviceMask.DrawWallpaper(aRect, aWallpaper);
151*035a2f44SArmin Le Grand 						}
152*035a2f44SArmin Le Grand 						else
153*035a2f44SArmin Le Grand 						{
154*035a2f44SArmin Le Grand 							BitmapEx aExpandVisibilityMask = BitmapEx(aMask, aMask);
155*035a2f44SArmin Le Grand 							aVirtualDeviceMask.DrawBitmapEx(rAnimBitmap.aPosPix, aExpandVisibilityMask);
156*035a2f44SArmin Le Grand 						}
157*035a2f44SArmin Le Grand 
158*035a2f44SArmin Le Grand 						break;
159*035a2f44SArmin Le Grand 					}
160*035a2f44SArmin Le Grand 					case DISPOSE_BACK:
161*035a2f44SArmin Le Grand 					{
162*035a2f44SArmin Le Grand 						// #i70772# react on no mask, for primitives, too.
163*035a2f44SArmin Le Grand 						const Bitmap aMask(rAnimBitmap.aBmpEx.GetMask());
164*035a2f44SArmin Le Grand 						const Bitmap aContent(rAnimBitmap.aBmpEx.GetBitmap());
165*035a2f44SArmin Le Grand 
166*035a2f44SArmin Le Grand 						aVirtualDeviceMask.Erase();
167*035a2f44SArmin Le Grand 						aVirtualDevice.DrawBitmap(rAnimBitmap.aPosPix, aContent);
168*035a2f44SArmin Le Grand 
169*035a2f44SArmin Le Grand 						if(aMask.IsEmpty())
170*035a2f44SArmin Le Grand 						{
171*035a2f44SArmin Le Grand 							const Rectangle aRect(rAnimBitmap.aPosPix, aContent.GetSizePixel());
172*035a2f44SArmin Le Grand 							aVirtualDeviceMask.SetFillColor(COL_BLACK);
173*035a2f44SArmin Le Grand 							aVirtualDeviceMask.SetLineColor();
174*035a2f44SArmin Le Grand 							aVirtualDeviceMask.DrawRect(aRect);
175*035a2f44SArmin Le Grand 						}
176*035a2f44SArmin Le Grand 						else
177*035a2f44SArmin Le Grand 						{
178*035a2f44SArmin Le Grand 							aVirtualDeviceMask.DrawBitmap(rAnimBitmap.aPosPix, aMask);
179*035a2f44SArmin Le Grand 						}
180*035a2f44SArmin Le Grand 
181*035a2f44SArmin Le Grand 						break;
182*035a2f44SArmin Le Grand 					}
183*035a2f44SArmin Le Grand 					case DISPOSE_FULL:
184*035a2f44SArmin Le Grand 					{
185*035a2f44SArmin Le Grand 						aVirtualDevice.DrawBitmapEx(rAnimBitmap.aPosPix, rAnimBitmap.aBmpEx);
186*035a2f44SArmin Le Grand 						break;
187*035a2f44SArmin Le Grand 					}
188*035a2f44SArmin Le Grand 					case DISPOSE_PREVIOUS :
189*035a2f44SArmin Le Grand 					{
190*035a2f44SArmin Le Grand 						aVirtualDevice.DrawBitmapEx(rAnimBitmap.aPosPix, rAnimBitmap.aBmpEx);
191*035a2f44SArmin Le Grand 						aVirtualDeviceMask.DrawBitmap(rAnimBitmap.aPosPix, rAnimBitmap.aBmpEx.GetMask());
192*035a2f44SArmin Le Grand 						break;
193*035a2f44SArmin Le Grand 					}
194*035a2f44SArmin Le Grand 				}
195*035a2f44SArmin Le Grand 
196*035a2f44SArmin Le Grand 				// create BitmapEx
197*035a2f44SArmin Le Grand 				Bitmap aMainBitmap = aVirtualDevice.GetBitmap(Point(), aVirtualDevice.GetOutputSizePixel());
198*035a2f44SArmin Le Grand 				Bitmap aMaskBitmap = aVirtualDeviceMask.GetBitmap(Point(), aVirtualDeviceMask.GetOutputSizePixel());
199*035a2f44SArmin Le Grand 				aNextStep.maBitmapEx = BitmapEx(aMainBitmap, aMaskBitmap);
200*035a2f44SArmin Le Grand 
201*035a2f44SArmin Le Grand 				// add to vector
202*035a2f44SArmin Le Grand 				maSteps.push_back(aNextStep);
203*035a2f44SArmin Le Grand 			}
204*035a2f44SArmin Le Grand 		}
205*035a2f44SArmin Le Grand 	}
206*035a2f44SArmin Le Grand } // end of anonymous namespace
207*035a2f44SArmin Le Grand 
208*035a2f44SArmin Le Grand //////////////////////////////////////////////////////////////////////////////
209*035a2f44SArmin Le Grand 
210*035a2f44SArmin Le Grand namespace drawinglayer
211*035a2f44SArmin Le Grand {
212*035a2f44SArmin Le Grand 	namespace primitive2d
213*035a2f44SArmin Le Grand 	{
214*035a2f44SArmin Le Grand 		Primitive2DSequence create2DDecompositionOfGraphic(
215*035a2f44SArmin Le Grand             const Graphic& rGraphic,
216*035a2f44SArmin Le Grand             const basegfx::B2DHomMatrix& rTransform)
217*035a2f44SArmin Le Grand 		{
218*035a2f44SArmin Le Grand 			Primitive2DSequence aRetval;
219*035a2f44SArmin Le Grand 
220*035a2f44SArmin Le Grand             switch(rGraphic.GetType())
221*035a2f44SArmin Le Grand 			{
222*035a2f44SArmin Le Grand 				case GRAPHIC_BITMAP :
223*035a2f44SArmin Le Grand 				{
224*035a2f44SArmin Le Grand                     if(rGraphic.IsAnimated())
225*035a2f44SArmin Le Grand 					{
226*035a2f44SArmin Le Grand 						// prepare animation data
227*035a2f44SArmin Le Grand 						animatedBitmapExPreparator aData(rGraphic);
228*035a2f44SArmin Le Grand 
229*035a2f44SArmin Le Grand 						if(aData.count())
230*035a2f44SArmin Le Grand 						{
231*035a2f44SArmin Le Grand 							// create sub-primitives for animated bitmap and the needed animation loop
232*035a2f44SArmin Le Grand 							animation::AnimationEntryLoop aAnimationLoop(aData.loopCount() ? aData.loopCount() : 0xffff);
233*035a2f44SArmin Le Grand 							Primitive2DSequence aBitmapPrimitives(aData.count());
234*035a2f44SArmin Le Grand 
235*035a2f44SArmin Le Grand 							for(sal_uInt32 a(0); a < aData.count(); a++)
236*035a2f44SArmin Le Grand 							{
237*035a2f44SArmin Le Grand                                 animation::AnimationEntryFixed aTime((double)aData.stepTime(a), (double)a / (double)aData.count());
238*035a2f44SArmin Le Grand 								aAnimationLoop.append(aTime);
239*035a2f44SArmin Le Grand 								aBitmapPrimitives[a] = new BitmapPrimitive2D(
240*035a2f44SArmin Le Grand                                     aData.stepBitmapEx(a),
241*035a2f44SArmin Le Grand                                     rTransform);
242*035a2f44SArmin Le Grand 							}
243*035a2f44SArmin Le Grand 
244*035a2f44SArmin Le Grand 							// prepare animation list
245*035a2f44SArmin Le Grand 							animation::AnimationEntryList aAnimationList;
246*035a2f44SArmin Le Grand 							aAnimationList.append(aAnimationLoop);
247*035a2f44SArmin Le Grand 
248*035a2f44SArmin Le Grand 							// create and add animated switch primitive
249*035a2f44SArmin Le Grand                             aRetval.realloc(1);
250*035a2f44SArmin Le Grand 							aRetval[0] = new AnimatedSwitchPrimitive2D(
251*035a2f44SArmin Le Grand                                 aAnimationList,
252*035a2f44SArmin Le Grand                                 aBitmapPrimitives,
253*035a2f44SArmin Le Grand                                 false);
254*035a2f44SArmin Le Grand 						}
255*035a2f44SArmin Le Grand 					}
256*035a2f44SArmin Le Grand                     else if(rGraphic.getSvgData().get())
257*035a2f44SArmin Le Grand                     {
258*035a2f44SArmin Le Grand                         // embedded Svg fill, create embed transform
259*035a2f44SArmin Le Grand                         const basegfx::B2DRange& rSvgRange(rGraphic.getSvgData()->getRange());
260*035a2f44SArmin Le Grand 
261*035a2f44SArmin Le Grand                         if(basegfx::fTools::more(rSvgRange.getWidth(), 0.0) && basegfx::fTools::more(rSvgRange.getHeight(), 0.0))
262*035a2f44SArmin Le Grand                         {
263*035a2f44SArmin Le Grand                             // translate back to origin, scale to unit coordinates
264*035a2f44SArmin Le Grand                             basegfx::B2DHomMatrix aEmbedSvg(
265*035a2f44SArmin Le Grand                                 basegfx::tools::createTranslateB2DHomMatrix(
266*035a2f44SArmin Le Grand                                     -rSvgRange.getMinX(),
267*035a2f44SArmin Le Grand                                     -rSvgRange.getMinY()));
268*035a2f44SArmin Le Grand 
269*035a2f44SArmin Le Grand                             aEmbedSvg.scale(
270*035a2f44SArmin Le Grand                                 1.0 / rSvgRange.getWidth(),
271*035a2f44SArmin Le Grand                                 1.0 / rSvgRange.getHeight());
272*035a2f44SArmin Le Grand 
273*035a2f44SArmin Le Grand                             // apply created object transformation
274*035a2f44SArmin Le Grand                             aEmbedSvg = rTransform * aEmbedSvg;
275*035a2f44SArmin Le Grand 
276*035a2f44SArmin Le Grand                             // add Svg primitives embedded
277*035a2f44SArmin Le Grand                             aRetval.realloc(1);
278*035a2f44SArmin Le Grand                             aRetval[0] = new TransformPrimitive2D(
279*035a2f44SArmin Le Grand                                 aEmbedSvg,
280*035a2f44SArmin Le Grand                                 rGraphic.getSvgData()->getPrimitive2DSequence());
281*035a2f44SArmin Le Grand                         }
282*035a2f44SArmin Le Grand                     }
283*035a2f44SArmin Le Grand 					else
284*035a2f44SArmin Le Grand 					{
285*035a2f44SArmin Le Grand                         aRetval.realloc(1);
286*035a2f44SArmin Le Grand 						aRetval[0] = new BitmapPrimitive2D(
287*035a2f44SArmin Le Grand                             rGraphic.GetBitmapEx(),
288*035a2f44SArmin Le Grand                             rTransform);
289*035a2f44SArmin Le Grand 					}
290*035a2f44SArmin Le Grand 
291*035a2f44SArmin Le Grand 					break;
292*035a2f44SArmin Le Grand 				}
293*035a2f44SArmin Le Grand 
294*035a2f44SArmin Le Grand 				case GRAPHIC_GDIMETAFILE :
295*035a2f44SArmin Le Grand 				{
296*035a2f44SArmin Le Grand #ifdef USE_DEBUG_CODE_TO_TEST_METAFILE_DECOMPOSE
297*035a2f44SArmin Le Grand                     static bool bDoTest(false);
298*035a2f44SArmin Le Grand 
299*035a2f44SArmin Le Grand                     if(bDoTest)
300*035a2f44SArmin Le Grand                     {
301*035a2f44SArmin Le Grand 						// All this is/was test code for testing MetafilePrimitive2D::create2DDecomposition
302*035a2f44SArmin Le Grand 						// extensively. It may be needed again when diverse actions need debugging, so i leave
303*035a2f44SArmin Le Grand 						// it in here, but take it out using USE_DEBUG_CODE_TO_TEST_METAFILE_DECOMPOSE.
304*035a2f44SArmin Le Grand 						// Use it by compiling with the code, insert any DrawObject, convert to Metafile. The
305*035a2f44SArmin Le Grand 						// debugger will then stop here (when breakpoint set, of course). You may enter single
306*035a2f44SArmin Le Grand 						// parts of actions and/or change to true what You want to check.
307*035a2f44SArmin Le Grand                         GDIMetaFile aMtf;
308*035a2f44SArmin Le Grand 			            VirtualDevice aOut;
309*035a2f44SArmin Le Grand         		        const basegfx::B2DRange aRange(getB2DRange(rViewInformation));
310*035a2f44SArmin Le Grand                         const Rectangle aRectangle(
311*035a2f44SArmin Le Grand                             basegfx::fround(aRange.getMinX()), basegfx::fround(aRange.getMinY()),
312*035a2f44SArmin Le Grand                             basegfx::fround(aRange.getMaxX()), basegfx::fround(aRange.getMaxY()));
313*035a2f44SArmin Le Grand                         const Point aOrigin(aRectangle.TopLeft());
314*035a2f44SArmin Le Grand                         const Fraction aScaleX(aRectangle.getWidth());
315*035a2f44SArmin Le Grand                         const Fraction aScaleY(aRectangle.getHeight());
316*035a2f44SArmin Le Grand                         MapMode aMapMode(MAP_100TH_MM, aOrigin, aScaleX, aScaleY);
317*035a2f44SArmin Le Grand 
318*035a2f44SArmin Le Grand                         Size aDummySize(2, 2);
319*035a2f44SArmin Le Grand                         aOut.SetOutputSizePixel(aDummySize);
320*035a2f44SArmin Le Grand 			            aOut.EnableOutput(FALSE);
321*035a2f44SArmin Le Grand 			            aOut.SetMapMode(aMapMode);
322*035a2f44SArmin Le Grand 
323*035a2f44SArmin Le Grand                         aMtf.Clear();
324*035a2f44SArmin Le Grand 			            aMtf.Record(&aOut);
325*035a2f44SArmin Le Grand 
326*035a2f44SArmin Le Grand 			            const Fraction aNeutralFraction(1, 1);
327*035a2f44SArmin Le Grand 			            const MapMode aRelativeMapMode(
328*035a2f44SArmin Le Grand                             MAP_RELATIVE,
329*035a2f44SArmin Le Grand                             Point(-aRectangle.Left(), -aRectangle.Top()),
330*035a2f44SArmin Le Grand                             aNeutralFraction, aNeutralFraction);
331*035a2f44SArmin Le Grand 			            aOut.SetMapMode(aRelativeMapMode);
332*035a2f44SArmin Le Grand 
333*035a2f44SArmin Le Grand                         if(false)
334*035a2f44SArmin Le Grand                         {
335*035a2f44SArmin Le Grand                             const sal_Int32 nHor(aRectangle.getWidth() / 4);
336*035a2f44SArmin Le Grand                             const sal_Int32 nVer(aRectangle.getHeight() / 4);
337*035a2f44SArmin Le Grand                             const Rectangle aCenteredRectangle(
338*035a2f44SArmin Le Grand                                 aRectangle.Left() + nHor, aRectangle.Top() + nVer,
339*035a2f44SArmin Le Grand                                 aRectangle.Right() - nHor, aRectangle.Bottom() - nVer);
340*035a2f44SArmin Le Grand                             aOut.SetClipRegion(aCenteredRectangle);
341*035a2f44SArmin Le Grand                         }
342*035a2f44SArmin Le Grand 
343*035a2f44SArmin Le Grand                         if(false)
344*035a2f44SArmin Le Grand                         {
345*035a2f44SArmin Le Grand                             const Rectangle aRightRectangle(aRectangle.TopCenter(), aRectangle.BottomRight());
346*035a2f44SArmin Le Grand                             aOut.IntersectClipRegion(aRightRectangle);
347*035a2f44SArmin Le Grand                         }
348*035a2f44SArmin Le Grand 
349*035a2f44SArmin Le Grand                         if(false)
350*035a2f44SArmin Le Grand                         {
351*035a2f44SArmin Le Grand                             const Rectangle aRightRectangle(aRectangle.TopCenter(), aRectangle.BottomRight());
352*035a2f44SArmin Le Grand                             const Rectangle aBottomRectangle(aRectangle.LeftCenter(), aRectangle.BottomRight());
353*035a2f44SArmin Le Grand                             Region aRegion(aRightRectangle);
354*035a2f44SArmin Le Grand                             aRegion.Intersect(aBottomRectangle);
355*035a2f44SArmin Le Grand                             aOut.IntersectClipRegion(aRegion);
356*035a2f44SArmin Le Grand                         }
357*035a2f44SArmin Le Grand 
358*035a2f44SArmin Le Grand                         if(false)
359*035a2f44SArmin Le Grand                         {
360*035a2f44SArmin Le Grand                             const sal_Int32 nHor(aRectangle.getWidth() / 10);
361*035a2f44SArmin Le Grand                             const sal_Int32 nVer(aRectangle.getHeight() / 10);
362*035a2f44SArmin Le Grand                             aOut.MoveClipRegion(nHor, nVer);
363*035a2f44SArmin Le Grand                         }
364*035a2f44SArmin Le Grand 
365*035a2f44SArmin Le Grand                         if(false)
366*035a2f44SArmin Le Grand                         {
367*035a2f44SArmin Le Grand                             Wallpaper aWallpaper(Color(COL_BLACK));
368*035a2f44SArmin Le Grand                             aOut.DrawWallpaper(aRectangle, aWallpaper);
369*035a2f44SArmin Le Grand                         }
370*035a2f44SArmin Le Grand 
371*035a2f44SArmin Le Grand                         if(false)
372*035a2f44SArmin Le Grand                         {
373*035a2f44SArmin Le Grand                             Wallpaper aWallpaper(Gradient(GRADIENT_LINEAR, Color(COL_RED), Color(COL_GREEN)));
374*035a2f44SArmin Le Grand                             aOut.DrawWallpaper(aRectangle, aWallpaper);
375*035a2f44SArmin Le Grand                         }
376*035a2f44SArmin Le Grand 
377*035a2f44SArmin Le Grand                         if(false)
378*035a2f44SArmin Le Grand                         {
379*035a2f44SArmin Le Grand             				SvFileStream aRead((const String&)String(ByteString( "c:\\test.png" ), RTL_TEXTENCODING_UTF8), STREAM_READ);
380*035a2f44SArmin Le Grand                             vcl::PNGReader aPNGReader(aRead);
381*035a2f44SArmin Le Grand 		                    BitmapEx aBitmapEx(aPNGReader.Read());
382*035a2f44SArmin Le Grand                             Wallpaper aWallpaper(aBitmapEx);
383*035a2f44SArmin Le Grand                             aOut.DrawWallpaper(aRectangle, aWallpaper);
384*035a2f44SArmin Le Grand                         }
385*035a2f44SArmin Le Grand 
386*035a2f44SArmin Le Grand                         if(false)
387*035a2f44SArmin Le Grand                         {
388*035a2f44SArmin Le Grand                             const double fHor(aRectangle.getWidth());
389*035a2f44SArmin Le Grand                             const double fVer(aRectangle.getHeight());
390*035a2f44SArmin Le Grand 							Color aColor(basegfx::BColor(rand() / 32767.0, rand() / 32767.0, rand() / 32767.0));
391*035a2f44SArmin Le Grand 
392*035a2f44SArmin Le Grand 							for(sal_uInt32 a(0); a < 5000; a++)
393*035a2f44SArmin Le Grand 							{
394*035a2f44SArmin Le Grand 								const Point aPoint(
395*035a2f44SArmin Le Grand 									aRectangle.Left() + basegfx::fround(rand() * (fHor / 32767.0)),
396*035a2f44SArmin Le Grand 									aRectangle.Top() + basegfx::fround(rand() * (fVer / 32767.0)));
397*035a2f44SArmin Le Grand 
398*035a2f44SArmin Le Grand 								if(!(a % 3))
399*035a2f44SArmin Le Grand 								{
400*035a2f44SArmin Le Grand 									aColor = Color(basegfx::BColor(rand() / 32767.0, rand() / 32767.0, rand() / 32767.0));
401*035a2f44SArmin Le Grand 								}
402*035a2f44SArmin Le Grand 
403*035a2f44SArmin Le Grand 								aOut.DrawPixel(aPoint, aColor);
404*035a2f44SArmin Le Grand 							}
405*035a2f44SArmin Le Grand 						}
406*035a2f44SArmin Le Grand 
407*035a2f44SArmin Le Grand                         if(false)
408*035a2f44SArmin Le Grand                         {
409*035a2f44SArmin Le Grand                             const double fHor(aRectangle.getWidth());
410*035a2f44SArmin Le Grand                             const double fVer(aRectangle.getHeight());
411*035a2f44SArmin Le Grand 
412*035a2f44SArmin Le Grand 							aOut.SetLineColor(Color(basegfx::BColor(rand() / 32767.0, rand() / 32767.0, rand() / 32767.0)));
413*035a2f44SArmin Le Grand 							aOut.SetFillColor();
414*035a2f44SArmin Le Grand 
415*035a2f44SArmin Le Grand 							for(sal_uInt32 a(0); a < 5000; a++)
416*035a2f44SArmin Le Grand 							{
417*035a2f44SArmin Le Grand 								const Point aPoint(
418*035a2f44SArmin Le Grand 									aRectangle.Left() + basegfx::fround(rand() * (fHor / 32767.0)),
419*035a2f44SArmin Le Grand 									aRectangle.Top() + basegfx::fround(rand() * (fVer / 32767.0)));
420*035a2f44SArmin Le Grand 								aOut.DrawPixel(aPoint);
421*035a2f44SArmin Le Grand 							}
422*035a2f44SArmin Le Grand 						}
423*035a2f44SArmin Le Grand 
424*035a2f44SArmin Le Grand                         if(false)
425*035a2f44SArmin Le Grand                         {
426*035a2f44SArmin Le Grand                             const double fHor(aRectangle.getWidth());
427*035a2f44SArmin Le Grand                             const double fVer(aRectangle.getHeight());
428*035a2f44SArmin Le Grand 
429*035a2f44SArmin Le Grand 							aOut.SetLineColor(Color(basegfx::BColor(rand() / 32767.0, rand() / 32767.0, rand() / 32767.0)));
430*035a2f44SArmin Le Grand 							aOut.SetFillColor();
431*035a2f44SArmin Le Grand 
432*035a2f44SArmin Le Grand 							Point aStart(
433*035a2f44SArmin Le Grand 								aRectangle.Left() + basegfx::fround(rand() * (fHor / 32767.0)),
434*035a2f44SArmin Le Grand 								aRectangle.Top() + basegfx::fround(rand() * (fVer / 32767.0)));
435*035a2f44SArmin Le Grand 							Point aStop(
436*035a2f44SArmin Le Grand 								aRectangle.Left() + basegfx::fround(rand() * (fHor / 32767.0)),
437*035a2f44SArmin Le Grand 								aRectangle.Top() + basegfx::fround(rand() * (fVer / 32767.0)));
438*035a2f44SArmin Le Grand 
439*035a2f44SArmin Le Grand 							LineInfo aLineInfo(LINE_SOLID, basegfx::fround(fHor / 50.0));
440*035a2f44SArmin Le Grand 							bool bUseLineInfo(false);
441*035a2f44SArmin Le Grand 
442*035a2f44SArmin Le Grand 							for(sal_uInt32 a(0); a < 20; a++)
443*035a2f44SArmin Le Grand 							{
444*035a2f44SArmin Le Grand 								if(!(a%6))
445*035a2f44SArmin Le Grand 								{
446*035a2f44SArmin Le Grand 									bUseLineInfo = !bUseLineInfo;
447*035a2f44SArmin Le Grand 								}
448*035a2f44SArmin Le Grand 
449*035a2f44SArmin Le Grand 								if(!(a%4))
450*035a2f44SArmin Le Grand 								{
451*035a2f44SArmin Le Grand 									aOut.SetLineColor(Color(basegfx::BColor(rand() / 32767.0, rand() / 32767.0, rand() / 32767.0)));
452*035a2f44SArmin Le Grand 								}
453*035a2f44SArmin Le Grand 
454*035a2f44SArmin Le Grand 								if(a%3)
455*035a2f44SArmin Le Grand 								{
456*035a2f44SArmin Le Grand 									aStart = aStop;
457*035a2f44SArmin Le Grand 									aStop = Point(
458*035a2f44SArmin Le Grand 										aRectangle.Left() + basegfx::fround(rand() * (fHor / 32767.0)),
459*035a2f44SArmin Le Grand 										aRectangle.Top() + basegfx::fround(rand() * (fVer / 32767.0)));
460*035a2f44SArmin Le Grand 								}
461*035a2f44SArmin Le Grand 								else
462*035a2f44SArmin Le Grand 								{
463*035a2f44SArmin Le Grand 									aStart = Point(
464*035a2f44SArmin Le Grand 										aRectangle.Left() + basegfx::fround(rand() * (fHor / 32767.0)),
465*035a2f44SArmin Le Grand 										aRectangle.Top() + basegfx::fround(rand() * (fVer / 32767.0)));
466*035a2f44SArmin Le Grand 									aStop = Point(
467*035a2f44SArmin Le Grand 										aRectangle.Left() + basegfx::fround(rand() * (fHor / 32767.0)),
468*035a2f44SArmin Le Grand 										aRectangle.Top() + basegfx::fround(rand() * (fVer / 32767.0)));
469*035a2f44SArmin Le Grand 								}
470*035a2f44SArmin Le Grand 
471*035a2f44SArmin Le Grand 								if(bUseLineInfo)
472*035a2f44SArmin Le Grand 								{
473*035a2f44SArmin Le Grand 									aOut.DrawLine(aStart, aStop, aLineInfo);
474*035a2f44SArmin Le Grand 								}
475*035a2f44SArmin Le Grand 								else
476*035a2f44SArmin Le Grand 								{
477*035a2f44SArmin Le Grand 									aOut.DrawLine(aStart, aStop);
478*035a2f44SArmin Le Grand 								}
479*035a2f44SArmin Le Grand 							}
480*035a2f44SArmin Le Grand 						}
481*035a2f44SArmin Le Grand 
482*035a2f44SArmin Le Grand                         if(false)
483*035a2f44SArmin Le Grand                         {
484*035a2f44SArmin Le Grand 							aOut.SetLineColor(Color(basegfx::BColor(rand() / 32767.0, rand() / 32767.0, rand() / 32767.0)));
485*035a2f44SArmin Le Grand 							aOut.SetFillColor(Color(basegfx::BColor(rand() / 32767.0, rand() / 32767.0, rand() / 32767.0)));
486*035a2f44SArmin Le Grand 							aOut.DrawRect(aRectangle);
487*035a2f44SArmin Le Grand 						}
488*035a2f44SArmin Le Grand 
489*035a2f44SArmin Le Grand                         if(false)
490*035a2f44SArmin Le Grand                         {
491*035a2f44SArmin Le Grand 							aOut.SetLineColor(Color(basegfx::BColor(rand() / 32767.0, rand() / 32767.0, rand() / 32767.0)));
492*035a2f44SArmin Le Grand 							aOut.SetFillColor(Color(basegfx::BColor(rand() / 32767.0, rand() / 32767.0, rand() / 32767.0)));
493*035a2f44SArmin Le Grand                             const sal_uInt32 nHor(aRectangle.getWidth() / 10);
494*035a2f44SArmin Le Grand                             const sal_uInt32 nVer(aRectangle.getHeight() / 10);
495*035a2f44SArmin Le Grand 							aOut.DrawRect(aRectangle, nHor, nVer);
496*035a2f44SArmin Le Grand 						}
497*035a2f44SArmin Le Grand 
498*035a2f44SArmin Le Grand                         if(false)
499*035a2f44SArmin Le Grand                         {
500*035a2f44SArmin Le Grand 							aOut.SetLineColor(Color(basegfx::BColor(rand() / 32767.0, rand() / 32767.0, rand() / 32767.0)));
501*035a2f44SArmin Le Grand 							aOut.SetFillColor(Color(basegfx::BColor(rand() / 32767.0, rand() / 32767.0, rand() / 32767.0)));
502*035a2f44SArmin Le Grand 							aOut.DrawEllipse(aRectangle);
503*035a2f44SArmin Le Grand 						}
504*035a2f44SArmin Le Grand 
505*035a2f44SArmin Le Grand                         if(false)
506*035a2f44SArmin Le Grand                         {
507*035a2f44SArmin Le Grand 							aOut.SetLineColor(Color(basegfx::BColor(rand() / 32767.0, rand() / 32767.0, rand() / 32767.0)));
508*035a2f44SArmin Le Grand 							aOut.SetFillColor(Color(basegfx::BColor(rand() / 32767.0, rand() / 32767.0, rand() / 32767.0)));
509*035a2f44SArmin Le Grand 							aOut.DrawArc(aRectangle, aRectangle.TopLeft(), aRectangle.BottomCenter());
510*035a2f44SArmin Le Grand 						}
511*035a2f44SArmin Le Grand 
512*035a2f44SArmin Le Grand                         if(false)
513*035a2f44SArmin Le Grand                         {
514*035a2f44SArmin Le Grand 							aOut.SetLineColor(Color(basegfx::BColor(rand() / 32767.0, rand() / 32767.0, rand() / 32767.0)));
515*035a2f44SArmin Le Grand 							aOut.SetFillColor(Color(basegfx::BColor(rand() / 32767.0, rand() / 32767.0, rand() / 32767.0)));
516*035a2f44SArmin Le Grand 							aOut.DrawPie(aRectangle, aRectangle.TopLeft(), aRectangle.BottomCenter());
517*035a2f44SArmin Le Grand 						}
518*035a2f44SArmin Le Grand 
519*035a2f44SArmin Le Grand                         if(false)
520*035a2f44SArmin Le Grand                         {
521*035a2f44SArmin Le Grand 							aOut.SetLineColor(Color(basegfx::BColor(rand() / 32767.0, rand() / 32767.0, rand() / 32767.0)));
522*035a2f44SArmin Le Grand 							aOut.SetFillColor(Color(basegfx::BColor(rand() / 32767.0, rand() / 32767.0, rand() / 32767.0)));
523*035a2f44SArmin Le Grand 							aOut.DrawChord(aRectangle, aRectangle.TopLeft(), aRectangle.BottomCenter());
524*035a2f44SArmin Le Grand 						}
525*035a2f44SArmin Le Grand 
526*035a2f44SArmin Le Grand                         if(false)
527*035a2f44SArmin Le Grand                         {
528*035a2f44SArmin Le Grand                             const double fHor(aRectangle.getWidth());
529*035a2f44SArmin Le Grand                             const double fVer(aRectangle.getHeight());
530*035a2f44SArmin Le Grand 
531*035a2f44SArmin Le Grand 							for(sal_uInt32 b(0); b < 5; b++)
532*035a2f44SArmin Le Grand 							{
533*035a2f44SArmin Le Grand 								const sal_uInt32 nCount(basegfx::fround(rand() * (20 / 32767.0)));
534*035a2f44SArmin Le Grand 								const bool bClose(basegfx::fround(rand() / 32767.0));
535*035a2f44SArmin Le Grand 								Polygon aPolygon(nCount + (bClose ? 1 : 0));
536*035a2f44SArmin Le Grand 
537*035a2f44SArmin Le Grand 								for(sal_uInt32 a(0); a < nCount; a++)
538*035a2f44SArmin Le Grand 								{
539*035a2f44SArmin Le Grand 									const Point aPoint(
540*035a2f44SArmin Le Grand 										aRectangle.Left() + basegfx::fround(rand() * (fHor / 32767.0)),
541*035a2f44SArmin Le Grand 										aRectangle.Top() + basegfx::fround(rand() * (fVer / 32767.0)));
542*035a2f44SArmin Le Grand 									aPolygon[a] = aPoint;
543*035a2f44SArmin Le Grand 								}
544*035a2f44SArmin Le Grand 
545*035a2f44SArmin Le Grand 								if(bClose)
546*035a2f44SArmin Le Grand 								{
547*035a2f44SArmin Le Grand 									aPolygon[aPolygon.GetSize() - 1] = aPolygon[0];
548*035a2f44SArmin Le Grand 								}
549*035a2f44SArmin Le Grand 
550*035a2f44SArmin Le Grand 								aOut.SetLineColor(Color(basegfx::BColor(rand() / 32767.0, rand() / 32767.0, rand() / 32767.0)));
551*035a2f44SArmin Le Grand 								aOut.SetFillColor(Color(basegfx::BColor(rand() / 32767.0, rand() / 32767.0, rand() / 32767.0)));
552*035a2f44SArmin Le Grand 
553*035a2f44SArmin Le Grand 								if(!(b%2))
554*035a2f44SArmin Le Grand 								{
555*035a2f44SArmin Le Grand 									const LineInfo aLineInfo(LINE_SOLID, basegfx::fround(fHor / 50.0));
556*035a2f44SArmin Le Grand 									aOut.DrawPolyLine(aPolygon, aLineInfo);
557*035a2f44SArmin Le Grand 								}
558*035a2f44SArmin Le Grand 								else
559*035a2f44SArmin Le Grand 								{
560*035a2f44SArmin Le Grand 									aOut.DrawPolyLine(aPolygon);
561*035a2f44SArmin Le Grand 								}
562*035a2f44SArmin Le Grand 							}
563*035a2f44SArmin Le Grand 						}
564*035a2f44SArmin Le Grand 
565*035a2f44SArmin Le Grand                         if(false)
566*035a2f44SArmin Le Grand                         {
567*035a2f44SArmin Le Grand                             const double fHor(aRectangle.getWidth());
568*035a2f44SArmin Le Grand                             const double fVer(aRectangle.getHeight());
569*035a2f44SArmin Le Grand 
570*035a2f44SArmin Le Grand 							for(sal_uInt32 b(0); b < 5; b++)
571*035a2f44SArmin Le Grand 							{
572*035a2f44SArmin Le Grand 								const sal_uInt32 nCount(basegfx::fround(rand() * (20 / 32767.0)));
573*035a2f44SArmin Le Grand 								const bool bClose(basegfx::fround(rand() / 32767.0));
574*035a2f44SArmin Le Grand 								Polygon aPolygon(nCount + (bClose ? 1 : 0));
575*035a2f44SArmin Le Grand 
576*035a2f44SArmin Le Grand 								for(sal_uInt32 a(0); a < nCount; a++)
577*035a2f44SArmin Le Grand 								{
578*035a2f44SArmin Le Grand 									const Point aPoint(
579*035a2f44SArmin Le Grand 										aRectangle.Left() + basegfx::fround(rand() * (fHor / 32767.0)),
580*035a2f44SArmin Le Grand 										aRectangle.Top() + basegfx::fround(rand() * (fVer / 32767.0)));
581*035a2f44SArmin Le Grand 									aPolygon[a] = aPoint;
582*035a2f44SArmin Le Grand 								}
583*035a2f44SArmin Le Grand 
584*035a2f44SArmin Le Grand 								if(bClose)
585*035a2f44SArmin Le Grand 								{
586*035a2f44SArmin Le Grand 									aPolygon[aPolygon.GetSize() - 1] = aPolygon[0];
587*035a2f44SArmin Le Grand 								}
588*035a2f44SArmin Le Grand 
589*035a2f44SArmin Le Grand 								aOut.SetLineColor(Color(basegfx::BColor(rand() / 32767.0, rand() / 32767.0, rand() / 32767.0)));
590*035a2f44SArmin Le Grand 								aOut.SetFillColor(Color(basegfx::BColor(rand() / 32767.0, rand() / 32767.0, rand() / 32767.0)));
591*035a2f44SArmin Le Grand 								aOut.DrawPolygon(aPolygon);
592*035a2f44SArmin Le Grand 							}
593*035a2f44SArmin Le Grand 						}
594*035a2f44SArmin Le Grand 
595*035a2f44SArmin Le Grand                         if(false)
596*035a2f44SArmin Le Grand                         {
597*035a2f44SArmin Le Grand                             const double fHor(aRectangle.getWidth());
598*035a2f44SArmin Le Grand                             const double fVer(aRectangle.getHeight());
599*035a2f44SArmin Le Grand 							PolyPolygon aPolyPolygon;
600*035a2f44SArmin Le Grand 
601*035a2f44SArmin Le Grand 							for(sal_uInt32 b(0); b < 3; b++)
602*035a2f44SArmin Le Grand 							{
603*035a2f44SArmin Le Grand 								const sal_uInt32 nCount(basegfx::fround(rand() * (6 / 32767.0)));
604*035a2f44SArmin Le Grand 								const bool bClose(basegfx::fround(rand() / 32767.0));
605*035a2f44SArmin Le Grand 								Polygon aPolygon(nCount + (bClose ? 1 : 0));
606*035a2f44SArmin Le Grand 
607*035a2f44SArmin Le Grand 								for(sal_uInt32 a(0); a < nCount; a++)
608*035a2f44SArmin Le Grand 								{
609*035a2f44SArmin Le Grand 									const Point aPoint(
610*035a2f44SArmin Le Grand 										aRectangle.Left() + basegfx::fround(rand() * (fHor / 32767.0)),
611*035a2f44SArmin Le Grand 										aRectangle.Top() + basegfx::fround(rand() * (fVer / 32767.0)));
612*035a2f44SArmin Le Grand 									aPolygon[a] = aPoint;
613*035a2f44SArmin Le Grand 								}
614*035a2f44SArmin Le Grand 
615*035a2f44SArmin Le Grand 								if(bClose)
616*035a2f44SArmin Le Grand 								{
617*035a2f44SArmin Le Grand 									aPolygon[aPolygon.GetSize() - 1] = aPolygon[0];
618*035a2f44SArmin Le Grand 								}
619*035a2f44SArmin Le Grand 
620*035a2f44SArmin Le Grand 								aPolyPolygon.Insert(aPolygon);
621*035a2f44SArmin Le Grand 							}
622*035a2f44SArmin Le Grand 
623*035a2f44SArmin Le Grand 							aOut.SetLineColor(Color(basegfx::BColor(rand() / 32767.0, rand() / 32767.0, rand() / 32767.0)));
624*035a2f44SArmin Le Grand 							aOut.SetFillColor(Color(basegfx::BColor(rand() / 32767.0, rand() / 32767.0, rand() / 32767.0)));
625*035a2f44SArmin Le Grand 							aOut.DrawPolyPolygon(aPolyPolygon);
626*035a2f44SArmin Le Grand 						}
627*035a2f44SArmin Le Grand 
628*035a2f44SArmin Le Grand                         if(false)
629*035a2f44SArmin Le Grand                         {
630*035a2f44SArmin Le Grand             				SvFileStream aRead((const String&)String(ByteString( "c:\\test.png" ), RTL_TEXTENCODING_UTF8), STREAM_READ);
631*035a2f44SArmin Le Grand                             vcl::PNGReader aPNGReader(aRead);
632*035a2f44SArmin Le Grand 		                    BitmapEx aBitmapEx(aPNGReader.Read());
633*035a2f44SArmin Le Grand 							aOut.DrawBitmapEx(aRectangle.TopLeft(), aBitmapEx);
634*035a2f44SArmin Le Grand 						}
635*035a2f44SArmin Le Grand 
636*035a2f44SArmin Le Grand                         if(false)
637*035a2f44SArmin Le Grand                         {
638*035a2f44SArmin Le Grand             				SvFileStream aRead((const String&)String(ByteString( "c:\\test.png" ), RTL_TEXTENCODING_UTF8), STREAM_READ);
639*035a2f44SArmin Le Grand                             vcl::PNGReader aPNGReader(aRead);
640*035a2f44SArmin Le Grand 		                    BitmapEx aBitmapEx(aPNGReader.Read());
641*035a2f44SArmin Le Grand 							aOut.DrawBitmapEx(aRectangle.TopLeft(), aRectangle.GetSize(), aBitmapEx);
642*035a2f44SArmin Le Grand 						}
643*035a2f44SArmin Le Grand 
644*035a2f44SArmin Le Grand                         if(false)
645*035a2f44SArmin Le Grand                         {
646*035a2f44SArmin Le Grand             				SvFileStream aRead((const String&)String(ByteString( "c:\\test.png" ), RTL_TEXTENCODING_UTF8), STREAM_READ);
647*035a2f44SArmin Le Grand                             vcl::PNGReader aPNGReader(aRead);
648*035a2f44SArmin Le Grand 		                    BitmapEx aBitmapEx(aPNGReader.Read());
649*035a2f44SArmin Le Grand 							const Size aSizePixel(aBitmapEx.GetSizePixel());
650*035a2f44SArmin Le Grand 							aOut.DrawBitmapEx(
651*035a2f44SArmin Le Grand 								aRectangle.TopLeft(),
652*035a2f44SArmin Le Grand 								aRectangle.GetSize(),
653*035a2f44SArmin Le Grand 								Point(0, 0),
654*035a2f44SArmin Le Grand 								Size(aSizePixel.Width() /2, aSizePixel.Height() / 2),
655*035a2f44SArmin Le Grand 								aBitmapEx);
656*035a2f44SArmin Le Grand 						}
657*035a2f44SArmin Le Grand 
658*035a2f44SArmin Le Grand                         if(false)
659*035a2f44SArmin Le Grand                         {
660*035a2f44SArmin Le Grand                             const double fHor(aRectangle.getWidth());
661*035a2f44SArmin Le Grand                             const double fVer(aRectangle.getHeight());
662*035a2f44SArmin Le Grand 							const Point aPointA(
663*035a2f44SArmin Le Grand 								aRectangle.Left() + basegfx::fround(fHor * 0.2),
664*035a2f44SArmin Le Grand 								aRectangle.Top() + basegfx::fround(fVer * 0.3));
665*035a2f44SArmin Le Grand 							const Point aPointB(
666*035a2f44SArmin Le Grand 								aRectangle.Left() + basegfx::fround(fHor * 0.2),
667*035a2f44SArmin Le Grand 								aRectangle.Top() + basegfx::fround(fVer * 0.5));
668*035a2f44SArmin Le Grand 							const Point aPointC(
669*035a2f44SArmin Le Grand 								aRectangle.Left() + basegfx::fround(fHor * 0.2),
670*035a2f44SArmin Le Grand 								aRectangle.Top() + basegfx::fround(fVer * 0.7));
671*035a2f44SArmin Le Grand                             const String aText(ByteString("Hello, World!"), RTL_TEXTENCODING_UTF8);
672*035a2f44SArmin Le Grand 
673*035a2f44SArmin Le Grand                             const String aFontName(ByteString("Comic Sans MS"), RTL_TEXTENCODING_UTF8);
674*035a2f44SArmin Le Grand                             Font aFont(aFontName, Size(0, 1000));
675*035a2f44SArmin Le Grand                             aFont.SetAlign(ALIGN_BASELINE);
676*035a2f44SArmin Le Grand                             aFont.SetColor(COL_RED);
677*035a2f44SArmin Le Grand                             //sal_Int32* pDXArray = new sal_Int32[aText.Len()];
678*035a2f44SArmin Le Grand 
679*035a2f44SArmin Le Grand                             aFont.SetOutline(true);
680*035a2f44SArmin Le Grand                             aOut.SetFont(aFont);
681*035a2f44SArmin Le Grand                             aOut.DrawText(aPointA, aText, 0, aText.Len());
682*035a2f44SArmin Le Grand 
683*035a2f44SArmin Le Grand                             aFont.SetShadow(true);
684*035a2f44SArmin Le Grand                             aOut.SetFont(aFont);
685*035a2f44SArmin Le Grand                             aOut.DrawText(aPointB, aText, 0, aText.Len());
686*035a2f44SArmin Le Grand 
687*035a2f44SArmin Le Grand                             aFont.SetRelief(RELIEF_EMBOSSED);
688*035a2f44SArmin Le Grand                             aOut.SetFont(aFont);
689*035a2f44SArmin Le Grand                             aOut.DrawText(aPointC, aText, 0, aText.Len());
690*035a2f44SArmin Le Grand 
691*035a2f44SArmin Le Grand                             //delete pDXArray;
692*035a2f44SArmin Le Grand                         }
693*035a2f44SArmin Le Grand 
694*035a2f44SArmin Le Grand                         if(false)
695*035a2f44SArmin Le Grand                         {
696*035a2f44SArmin Le Grand                             const double fHor(aRectangle.getWidth());
697*035a2f44SArmin Le Grand                             const double fVer(aRectangle.getHeight());
698*035a2f44SArmin Le Grand 							const Point aPointA(
699*035a2f44SArmin Le Grand 								aRectangle.Left() + basegfx::fround(fHor * 0.2),
700*035a2f44SArmin Le Grand 								aRectangle.Top() + basegfx::fround(fVer * 0.3));
701*035a2f44SArmin Le Grand 							const Point aPointB(
702*035a2f44SArmin Le Grand 								aRectangle.Left() + basegfx::fround(fHor * 0.2),
703*035a2f44SArmin Le Grand 								aRectangle.Top() + basegfx::fround(fVer * 0.5));
704*035a2f44SArmin Le Grand 							const Point aPointC(
705*035a2f44SArmin Le Grand 								aRectangle.Left() + basegfx::fround(fHor * 0.2),
706*035a2f44SArmin Le Grand 								aRectangle.Top() + basegfx::fround(fVer * 0.7));
707*035a2f44SArmin Le Grand                             const String aText(ByteString("Hello, World!"), RTL_TEXTENCODING_UTF8);
708*035a2f44SArmin Le Grand 
709*035a2f44SArmin Le Grand                             const String aFontName(ByteString("Comic Sans MS"), RTL_TEXTENCODING_UTF8);
710*035a2f44SArmin Le Grand                             Font aFont(aFontName, Size(0, 1000));
711*035a2f44SArmin Le Grand                             aFont.SetAlign(ALIGN_BASELINE);
712*035a2f44SArmin Le Grand                             aFont.SetColor(COL_RED);
713*035a2f44SArmin Le Grand 
714*035a2f44SArmin Le Grand                             aOut.SetFont(aFont);
715*035a2f44SArmin Le Grand 							const sal_Int32 nWidth(aOut.GetTextWidth(aText, 0, aText.Len()));
716*035a2f44SArmin Le Grand                             aOut.DrawText(aPointA, aText, 0, aText.Len());
717*035a2f44SArmin Le Grand                             aOut.DrawTextLine(aPointA, nWidth, STRIKEOUT_SINGLE, UNDERLINE_SINGLE, UNDERLINE_SMALLWAVE);
718*035a2f44SArmin Le Grand                             aOut.DrawTextLine(aPointB, nWidth, STRIKEOUT_SINGLE, UNDERLINE_SINGLE, UNDERLINE_SMALLWAVE);
719*035a2f44SArmin Le Grand                             aOut.DrawTextLine(aPointC, nWidth, STRIKEOUT_SINGLE, UNDERLINE_SINGLE, UNDERLINE_SMALLWAVE);
720*035a2f44SArmin Le Grand                         }
721*035a2f44SArmin Le Grand 
722*035a2f44SArmin Le Grand                         aMtf.Stop();
723*035a2f44SArmin Le Grand 			            aMtf.WindStart();
724*035a2f44SArmin Le Grand 		                aMtf.SetPrefMapMode(MapMode(MAP_100TH_MM));
725*035a2f44SArmin Le Grand 			            aMtf.SetPrefSize(Size(aRectangle.getWidth(), aRectangle.getHeight()));
726*035a2f44SArmin Le Grand 
727*035a2f44SArmin Le Grand                         aRetval.realloc(1);
728*035a2f44SArmin Le Grand                         aRetval[0] = new MetafilePrimitive2D(
729*035a2f44SArmin Le Grand                             rTransform,
730*035a2f44SArmin Le Grand                             aMtf);
731*035a2f44SArmin Le Grand                     }
732*035a2f44SArmin Le Grand                     else
733*035a2f44SArmin Le Grand                     {
734*035a2f44SArmin Le Grand #endif // USE_DEBUG_CODE_TO_TEST_METAFILE_DECOMPOSE
735*035a2f44SArmin Le Grand                         // create MetafilePrimitive2D
736*035a2f44SArmin Le Grand                         const GDIMetaFile& rMetafile = rGraphic.GetGDIMetaFile();
737*035a2f44SArmin Le Grand 
738*035a2f44SArmin Le Grand                         aRetval.realloc(1);
739*035a2f44SArmin Le Grand                         aRetval[0] = new MetafilePrimitive2D(
740*035a2f44SArmin Le Grand                             rTransform,
741*035a2f44SArmin Le Grand                             rMetafile);
742*035a2f44SArmin Le Grand 
743*035a2f44SArmin Le Grand                         // #i100357# find out if clipping is needed for this primitive. Unfortunately,
744*035a2f44SArmin Le Grand                         // there exist Metafiles who's content is bigger than the proposed PrefSize set
745*035a2f44SArmin Le Grand                         // at them. This is an error, but we need to work around this
746*035a2f44SArmin Le Grand                         const Size aMetaFilePrefSize(rMetafile.GetPrefSize());
747*035a2f44SArmin Le Grand                         const Size aMetaFileRealSize(
748*035a2f44SArmin Le Grand                             const_cast< GDIMetaFile& >(rMetafile).GetBoundRect(
749*035a2f44SArmin Le Grand                                 *Application::GetDefaultDevice()).GetSize());
750*035a2f44SArmin Le Grand 
751*035a2f44SArmin Le Grand                         if(aMetaFileRealSize.getWidth() > aMetaFilePrefSize.getWidth()
752*035a2f44SArmin Le Grand                             || aMetaFileRealSize.getHeight() > aMetaFilePrefSize.getHeight())
753*035a2f44SArmin Le Grand                         {
754*035a2f44SArmin Le Grand                             // clipping needed. Embed to MaskPrimitive2D. Create childs and mask polygon
755*035a2f44SArmin Le Grand                             basegfx::B2DPolygon aMaskPolygon(basegfx::tools::createUnitPolygon());
756*035a2f44SArmin Le Grand                             aMaskPolygon.transform(rTransform);
757*035a2f44SArmin Le Grand 
758*035a2f44SArmin Le Grand                             aRetval[0] = new MaskPrimitive2D(
759*035a2f44SArmin Le Grand                                 basegfx::B2DPolyPolygon(aMaskPolygon),
760*035a2f44SArmin Le Grand                                 aRetval);
761*035a2f44SArmin Le Grand                         }
762*035a2f44SArmin Le Grand #ifdef USE_DEBUG_CODE_TO_TEST_METAFILE_DECOMPOSE
763*035a2f44SArmin Le Grand                     }
764*035a2f44SArmin Le Grand #endif // USE_DEBUG_CODE_TO_TEST_METAFILE_DECOMPOSE
765*035a2f44SArmin Le Grand 
766*035a2f44SArmin Le Grand 					break;
767*035a2f44SArmin Le Grand 				}
768*035a2f44SArmin Le Grand 
769*035a2f44SArmin Le Grand 				default:
770*035a2f44SArmin Le Grand 				{
771*035a2f44SArmin Le Grand 					// nothing to create
772*035a2f44SArmin Le Grand 					break;
773*035a2f44SArmin Le Grand 				}
774*035a2f44SArmin Le Grand 			}
775*035a2f44SArmin Le Grand 
776*035a2f44SArmin Le Grand 			return aRetval;
777*035a2f44SArmin Le Grand 		}
778*035a2f44SArmin Le Grand 	} // end of namespace primitive2d
779*035a2f44SArmin Le Grand } // end of namespace drawinglayer
780*035a2f44SArmin Le Grand 
781*035a2f44SArmin Le Grand //////////////////////////////////////////////////////////////////////////////
782*035a2f44SArmin Le Grand // eof
783