xref: /trunk/main/basegfx/source/matrix/b2dhommatrixtools.cxx (revision 45d1b581a3afed2711c07fe77472516d35fbd7b3)
109dbbe93SAndrew Rist /**************************************************************
2cdf0e10cSrcweir  *
309dbbe93SAndrew Rist  * Licensed to the Apache Software Foundation (ASF) under one
409dbbe93SAndrew Rist  * or more contributor license agreements.  See the NOTICE file
509dbbe93SAndrew Rist  * distributed with this work for additional information
609dbbe93SAndrew Rist  * regarding copyright ownership.  The ASF licenses this file
709dbbe93SAndrew Rist  * to you under the Apache License, Version 2.0 (the
809dbbe93SAndrew Rist  * "License"); you may not use this file except in compliance
909dbbe93SAndrew Rist  * with the License.  You may obtain a copy of the License at
10cdf0e10cSrcweir  *
1109dbbe93SAndrew Rist  *   http://www.apache.org/licenses/LICENSE-2.0
12cdf0e10cSrcweir  *
1309dbbe93SAndrew Rist  * Unless required by applicable law or agreed to in writing,
1409dbbe93SAndrew Rist  * software distributed under the License is distributed on an
1509dbbe93SAndrew Rist  * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
1609dbbe93SAndrew Rist  * KIND, either express or implied.  See the License for the
1709dbbe93SAndrew Rist  * specific language governing permissions and limitations
1809dbbe93SAndrew Rist  * under the License.
19cdf0e10cSrcweir  *
2009dbbe93SAndrew Rist  *************************************************************/
2109dbbe93SAndrew Rist 
22cdf0e10cSrcweir // MARKER(update_precomp.py): autogen include statement, do not remove
23cdf0e10cSrcweir #include "precompiled_basegfx.hxx"
24cdf0e10cSrcweir 
25cdf0e10cSrcweir #include <basegfx/matrix/b2dhommatrixtools.hxx>
26cdf0e10cSrcweir #include <rtl/ustring.hxx>
27cdf0e10cSrcweir #include <rtl/ustrbuf.hxx>
28cdf0e10cSrcweir 
29cdf0e10cSrcweir namespace basegfx
30cdf0e10cSrcweir {
exportToSvg(const B2DHomMatrix & rMatrix)31cdf0e10cSrcweir     ::rtl::OUString exportToSvg( const B2DHomMatrix& rMatrix )
32cdf0e10cSrcweir     {
33cdf0e10cSrcweir         rtl::OUStringBuffer aStrBuf;
34cdf0e10cSrcweir         aStrBuf.appendAscii("matrix(");
35cdf0e10cSrcweir 
36cdf0e10cSrcweir         aStrBuf.append(rMatrix.get(0,0));
37cdf0e10cSrcweir         aStrBuf.appendAscii(", ");
38cdf0e10cSrcweir 
39cdf0e10cSrcweir         aStrBuf.append(rMatrix.get(1,0));
40cdf0e10cSrcweir         aStrBuf.appendAscii(", ");
41cdf0e10cSrcweir 
42cdf0e10cSrcweir         aStrBuf.append(rMatrix.get(0,1));
43cdf0e10cSrcweir         aStrBuf.appendAscii(", ");
44cdf0e10cSrcweir 
45cdf0e10cSrcweir         aStrBuf.append(rMatrix.get(1,1));
46cdf0e10cSrcweir         aStrBuf.appendAscii(", ");
47cdf0e10cSrcweir 
48cdf0e10cSrcweir         aStrBuf.append(rMatrix.get(0,2));
49cdf0e10cSrcweir         aStrBuf.appendAscii(", ");
50cdf0e10cSrcweir 
51cdf0e10cSrcweir         aStrBuf.append(rMatrix.get(1,2));
52cdf0e10cSrcweir         aStrBuf.appendAscii(")");
53cdf0e10cSrcweir 
54cdf0e10cSrcweir         return aStrBuf.makeStringAndClear();
55cdf0e10cSrcweir     }
56cdf0e10cSrcweir 
57cdf0e10cSrcweir     namespace tools
58cdf0e10cSrcweir     {
createSinCosOrthogonal(double & o_rSin,double & o_rCos,double fRadiant)59cdf0e10cSrcweir         void createSinCosOrthogonal(double& o_rSin, double& o_rCos, double fRadiant)
60cdf0e10cSrcweir         {
61cdf0e10cSrcweir             if( fTools::equalZero( fmod( fRadiant, F_PI2 ) ) )
62cdf0e10cSrcweir             {
63cdf0e10cSrcweir                 // determine quadrant
64cdf0e10cSrcweir                 const sal_Int32 nQuad(
65cdf0e10cSrcweir                     (4 + fround( 4/F_2PI*fmod( fRadiant, F_2PI ) )) % 4 );
66cdf0e10cSrcweir                 switch( nQuad )
67cdf0e10cSrcweir                 {
68cdf0e10cSrcweir                     case 0: // -2pi,0,2pi
69cdf0e10cSrcweir                         o_rSin = 0.0;
70cdf0e10cSrcweir                         o_rCos = 1.0;
71cdf0e10cSrcweir                         break;
72cdf0e10cSrcweir 
73cdf0e10cSrcweir                     case 1: // -3/2pi,1/2pi
74cdf0e10cSrcweir                         o_rSin = 1.0;
75cdf0e10cSrcweir                         o_rCos = 0.0;
76cdf0e10cSrcweir                         break;
77cdf0e10cSrcweir 
78cdf0e10cSrcweir                     case 2: // -pi,pi
79cdf0e10cSrcweir                         o_rSin = 0.0;
80cdf0e10cSrcweir                         o_rCos = -1.0;
81cdf0e10cSrcweir                         break;
82cdf0e10cSrcweir 
83cdf0e10cSrcweir                     case 3: // -1/2pi,3/2pi
84cdf0e10cSrcweir                         o_rSin = -1.0;
85cdf0e10cSrcweir                         o_rCos = 0.0;
86cdf0e10cSrcweir                         break;
87cdf0e10cSrcweir 
88cdf0e10cSrcweir                     default:
89cdf0e10cSrcweir                         OSL_ENSURE( false, "createSinCos: Impossible case reached" );
90cdf0e10cSrcweir                 }
91cdf0e10cSrcweir             }
92cdf0e10cSrcweir             else
93cdf0e10cSrcweir             {
94cdf0e10cSrcweir                 // TODO(P1): Maybe use glibc's sincos here (though
95cdf0e10cSrcweir                 // that's kinda non-portable...)
96cdf0e10cSrcweir                 o_rSin = sin(fRadiant);
97cdf0e10cSrcweir                 o_rCos = cos(fRadiant);
98cdf0e10cSrcweir             }
99cdf0e10cSrcweir         }
100cdf0e10cSrcweir 
createScaleB2DHomMatrix(double fScaleX,double fScaleY)101cdf0e10cSrcweir         B2DHomMatrix createScaleB2DHomMatrix(double fScaleX, double fScaleY)
102cdf0e10cSrcweir         {
103cdf0e10cSrcweir             B2DHomMatrix aRetval;
104cdf0e10cSrcweir             const double fOne(1.0);
105cdf0e10cSrcweir 
106cdf0e10cSrcweir             if(!fTools::equal(fScaleX, fOne))
107cdf0e10cSrcweir             {
108cdf0e10cSrcweir                 aRetval.set(0, 0, fScaleX);
109cdf0e10cSrcweir             }
110cdf0e10cSrcweir 
111cdf0e10cSrcweir             if(!fTools::equal(fScaleY, fOne))
112cdf0e10cSrcweir             {
113cdf0e10cSrcweir                 aRetval.set(1, 1, fScaleY);
114cdf0e10cSrcweir             }
115cdf0e10cSrcweir 
116cdf0e10cSrcweir             return aRetval;
117cdf0e10cSrcweir         }
118cdf0e10cSrcweir 
createShearXB2DHomMatrix(double fShearX)119cdf0e10cSrcweir         B2DHomMatrix createShearXB2DHomMatrix(double fShearX)
120cdf0e10cSrcweir         {
121cdf0e10cSrcweir             B2DHomMatrix aRetval;
122cdf0e10cSrcweir 
123cdf0e10cSrcweir             if(!fTools::equalZero(fShearX))
124cdf0e10cSrcweir             {
125cdf0e10cSrcweir                 aRetval.set(0, 1, fShearX);
126cdf0e10cSrcweir             }
127cdf0e10cSrcweir 
128cdf0e10cSrcweir             return aRetval;
129cdf0e10cSrcweir         }
130cdf0e10cSrcweir 
createShearYB2DHomMatrix(double fShearY)131cdf0e10cSrcweir         B2DHomMatrix createShearYB2DHomMatrix(double fShearY)
132cdf0e10cSrcweir         {
133cdf0e10cSrcweir             B2DHomMatrix aRetval;
134cdf0e10cSrcweir 
135cdf0e10cSrcweir             if(!fTools::equalZero(fShearY))
136cdf0e10cSrcweir             {
137cdf0e10cSrcweir                 aRetval.set(1, 0, fShearY);
138cdf0e10cSrcweir             }
139cdf0e10cSrcweir 
140cdf0e10cSrcweir             return aRetval;
141cdf0e10cSrcweir         }
142cdf0e10cSrcweir 
createRotateB2DHomMatrix(double fRadiant)143cdf0e10cSrcweir         B2DHomMatrix createRotateB2DHomMatrix(double fRadiant)
144cdf0e10cSrcweir         {
145cdf0e10cSrcweir             B2DHomMatrix aRetval;
146cdf0e10cSrcweir 
147cdf0e10cSrcweir             if(!fTools::equalZero(fRadiant))
148cdf0e10cSrcweir             {
149cdf0e10cSrcweir                 double fSin(0.0);
150cdf0e10cSrcweir                 double fCos(1.0);
151cdf0e10cSrcweir 
152cdf0e10cSrcweir                 createSinCosOrthogonal(fSin, fCos, fRadiant);
153cdf0e10cSrcweir                 aRetval.set(0, 0, fCos);
154cdf0e10cSrcweir                 aRetval.set(1, 1, fCos);
155cdf0e10cSrcweir                 aRetval.set(1, 0, fSin);
156cdf0e10cSrcweir                 aRetval.set(0, 1, -fSin);
157cdf0e10cSrcweir             }
158cdf0e10cSrcweir 
159cdf0e10cSrcweir             return aRetval;
160cdf0e10cSrcweir         }
161cdf0e10cSrcweir 
createTranslateB2DHomMatrix(double fTranslateX,double fTranslateY)162cdf0e10cSrcweir         B2DHomMatrix createTranslateB2DHomMatrix(double fTranslateX, double fTranslateY)
163cdf0e10cSrcweir         {
164cdf0e10cSrcweir             B2DHomMatrix aRetval;
165cdf0e10cSrcweir 
166cdf0e10cSrcweir             if(!(fTools::equalZero(fTranslateX) && fTools::equalZero(fTranslateY)))
167cdf0e10cSrcweir             {
168cdf0e10cSrcweir                 aRetval.set(0, 2, fTranslateX);
169cdf0e10cSrcweir                 aRetval.set(1, 2, fTranslateY);
170cdf0e10cSrcweir             }
171cdf0e10cSrcweir 
172cdf0e10cSrcweir             return aRetval;
173cdf0e10cSrcweir         }
174cdf0e10cSrcweir 
createScaleShearXRotateTranslateB2DHomMatrix(double fScaleX,double fScaleY,double fShearX,double fRadiant,double fTranslateX,double fTranslateY)175cdf0e10cSrcweir         B2DHomMatrix createScaleShearXRotateTranslateB2DHomMatrix(
176cdf0e10cSrcweir             double fScaleX, double fScaleY,
177cdf0e10cSrcweir             double fShearX,
178cdf0e10cSrcweir             double fRadiant,
179cdf0e10cSrcweir             double fTranslateX, double fTranslateY)
180cdf0e10cSrcweir         {
181cdf0e10cSrcweir             const double fOne(1.0);
182cdf0e10cSrcweir 
183cdf0e10cSrcweir             if(fTools::equal(fScaleX, fOne) && fTools::equal(fScaleY, fOne))
184cdf0e10cSrcweir             {
185*45d1b581Smseidel                 // no scale, take shortcut
186cdf0e10cSrcweir                 return createShearXRotateTranslateB2DHomMatrix(fShearX, fRadiant, fTranslateX, fTranslateY);
187cdf0e10cSrcweir             }
188cdf0e10cSrcweir             else
189cdf0e10cSrcweir             {
190*45d1b581Smseidel                 // scale used
191cdf0e10cSrcweir                 if(fTools::equalZero(fShearX))
192cdf0e10cSrcweir                 {
193*45d1b581Smseidel                     // no shear
194cdf0e10cSrcweir                     if(fTools::equalZero(fRadiant))
195cdf0e10cSrcweir                     {
196*45d1b581Smseidel                         // no rotate, take shortcut
197cdf0e10cSrcweir                         return createScaleTranslateB2DHomMatrix(fScaleX, fScaleY, fTranslateX, fTranslateY);
198cdf0e10cSrcweir                     }
199cdf0e10cSrcweir                     else
200cdf0e10cSrcweir                     {
201*45d1b581Smseidel                         // rotate and scale used, no shear
202cdf0e10cSrcweir                         double fSin(0.0);
203cdf0e10cSrcweir                         double fCos(1.0);
204cdf0e10cSrcweir 
205cdf0e10cSrcweir                         createSinCosOrthogonal(fSin, fCos, fRadiant);
206cdf0e10cSrcweir 
207cdf0e10cSrcweir                         B2DHomMatrix aRetval(
208cdf0e10cSrcweir                             /* Row 0, Column 0 */ fCos * fScaleX,
209cdf0e10cSrcweir                             /* Row 0, Column 1 */ fScaleY * -fSin,
210cdf0e10cSrcweir                             /* Row 0, Column 2 */ fTranslateX,
211cdf0e10cSrcweir                             /* Row 1, Column 0 */ fSin * fScaleX,
212cdf0e10cSrcweir                             /* Row 1, Column 1 */ fScaleY * fCos,
213cdf0e10cSrcweir                             /* Row 1, Column 2 */ fTranslateY);
214cdf0e10cSrcweir 
215cdf0e10cSrcweir                         return aRetval;
216cdf0e10cSrcweir                     }
217cdf0e10cSrcweir                 }
218cdf0e10cSrcweir                 else
219cdf0e10cSrcweir                 {
220*45d1b581Smseidel                     // scale and shear used
221cdf0e10cSrcweir                     if(fTools::equalZero(fRadiant))
222cdf0e10cSrcweir                     {
223*45d1b581Smseidel                         // scale and shear, but no rotate
224cdf0e10cSrcweir                         B2DHomMatrix aRetval(
225cdf0e10cSrcweir                             /* Row 0, Column 0 */ fScaleX,
226cdf0e10cSrcweir                             /* Row 0, Column 1 */ fScaleY * fShearX,
227cdf0e10cSrcweir                             /* Row 0, Column 2 */ fTranslateX,
228cdf0e10cSrcweir                             /* Row 1, Column 0 */ 0.0,
229cdf0e10cSrcweir                             /* Row 1, Column 1 */ fScaleY,
230cdf0e10cSrcweir                             /* Row 1, Column 2 */ fTranslateY);
231cdf0e10cSrcweir 
232cdf0e10cSrcweir                         return aRetval;
233cdf0e10cSrcweir                     }
234cdf0e10cSrcweir                     else
235cdf0e10cSrcweir                     {
236*45d1b581Smseidel                         // scale, shear and rotate used
237cdf0e10cSrcweir                         double fSin(0.0);
238cdf0e10cSrcweir                         double fCos(1.0);
239cdf0e10cSrcweir 
240cdf0e10cSrcweir                         createSinCosOrthogonal(fSin, fCos, fRadiant);
241cdf0e10cSrcweir 
242cdf0e10cSrcweir                         B2DHomMatrix aRetval(
243cdf0e10cSrcweir                             /* Row 0, Column 0 */ fCos * fScaleX,
244cdf0e10cSrcweir                             /* Row 0, Column 1 */ fScaleY * ((fCos * fShearX) - fSin),
245cdf0e10cSrcweir                             /* Row 0, Column 2 */ fTranslateX,
246cdf0e10cSrcweir                             /* Row 1, Column 0 */ fSin * fScaleX,
247cdf0e10cSrcweir                             /* Row 1, Column 1 */ fScaleY * ((fSin * fShearX) + fCos),
248cdf0e10cSrcweir                             /* Row 1, Column 2 */ fTranslateY);
249cdf0e10cSrcweir 
250cdf0e10cSrcweir                         return aRetval;
251cdf0e10cSrcweir                     }
252cdf0e10cSrcweir                 }
253cdf0e10cSrcweir             }
254cdf0e10cSrcweir         }
255cdf0e10cSrcweir 
createShearXRotateTranslateB2DHomMatrix(double fShearX,double fRadiant,double fTranslateX,double fTranslateY)256cdf0e10cSrcweir         B2DHomMatrix createShearXRotateTranslateB2DHomMatrix(
257cdf0e10cSrcweir             double fShearX,
258cdf0e10cSrcweir             double fRadiant,
259cdf0e10cSrcweir             double fTranslateX, double fTranslateY)
260cdf0e10cSrcweir         {
261cdf0e10cSrcweir             if(fTools::equalZero(fShearX))
262cdf0e10cSrcweir             {
263*45d1b581Smseidel                 // no shear
264cdf0e10cSrcweir                 if(fTools::equalZero(fRadiant))
265cdf0e10cSrcweir                 {
266*45d1b581Smseidel                     // no shear, no rotate, take shortcut
267cdf0e10cSrcweir                     return createTranslateB2DHomMatrix(fTranslateX, fTranslateY);
268cdf0e10cSrcweir                 }
269cdf0e10cSrcweir                 else
270cdf0e10cSrcweir                 {
271*45d1b581Smseidel                     // no shear, but rotate used
272cdf0e10cSrcweir                     double fSin(0.0);
273cdf0e10cSrcweir                     double fCos(1.0);
274cdf0e10cSrcweir 
275cdf0e10cSrcweir                     createSinCosOrthogonal(fSin, fCos, fRadiant);
276cdf0e10cSrcweir 
277cdf0e10cSrcweir                     B2DHomMatrix aRetval(
278cdf0e10cSrcweir                         /* Row 0, Column 0 */ fCos,
279cdf0e10cSrcweir                         /* Row 0, Column 1 */ -fSin,
280cdf0e10cSrcweir                         /* Row 0, Column 2 */ fTranslateX,
281cdf0e10cSrcweir                         /* Row 1, Column 0 */ fSin,
282cdf0e10cSrcweir                         /* Row 1, Column 1 */ fCos,
283cdf0e10cSrcweir                         /* Row 1, Column 2 */ fTranslateY);
284cdf0e10cSrcweir 
285cdf0e10cSrcweir                     return aRetval;
286cdf0e10cSrcweir                 }
287cdf0e10cSrcweir             }
288cdf0e10cSrcweir             else
289cdf0e10cSrcweir             {
290*45d1b581Smseidel                 // shear used
291cdf0e10cSrcweir                 if(fTools::equalZero(fRadiant))
292cdf0e10cSrcweir                 {
293*45d1b581Smseidel                     // no rotate, but shear used
294cdf0e10cSrcweir                     B2DHomMatrix aRetval(
295cdf0e10cSrcweir                         /* Row 0, Column 0 */ 1.0,
296cdf0e10cSrcweir                         /* Row 0, Column 1 */ fShearX,
297cdf0e10cSrcweir                         /* Row 0, Column 2 */ fTranslateX,
298cdf0e10cSrcweir                         /* Row 1, Column 0 */ 0.0,
299cdf0e10cSrcweir                         /* Row 1, Column 1 */ 1.0,
300cdf0e10cSrcweir                         /* Row 1, Column 2 */ fTranslateY);
301cdf0e10cSrcweir 
302cdf0e10cSrcweir                     return aRetval;
303cdf0e10cSrcweir                 }
304cdf0e10cSrcweir                 else
305cdf0e10cSrcweir                 {
306*45d1b581Smseidel                     // shear and rotate used
307cdf0e10cSrcweir                     double fSin(0.0);
308cdf0e10cSrcweir                     double fCos(1.0);
309cdf0e10cSrcweir 
310cdf0e10cSrcweir                     createSinCosOrthogonal(fSin, fCos, fRadiant);
311cdf0e10cSrcweir 
312cdf0e10cSrcweir                     B2DHomMatrix aRetval(
313cdf0e10cSrcweir                         /* Row 0, Column 0 */ fCos,
314cdf0e10cSrcweir                         /* Row 0, Column 1 */ (fCos * fShearX) - fSin,
315cdf0e10cSrcweir                         /* Row 0, Column 2 */ fTranslateX,
316cdf0e10cSrcweir                         /* Row 1, Column 0 */ fSin,
317cdf0e10cSrcweir                         /* Row 1, Column 1 */ (fSin * fShearX) + fCos,
318cdf0e10cSrcweir                         /* Row 1, Column 2 */ fTranslateY);
319cdf0e10cSrcweir 
320cdf0e10cSrcweir                     return aRetval;
321cdf0e10cSrcweir                 }
322cdf0e10cSrcweir             }
323cdf0e10cSrcweir         }
324cdf0e10cSrcweir 
createScaleTranslateB2DHomMatrix(double fScaleX,double fScaleY,double fTranslateX,double fTranslateY)325cdf0e10cSrcweir         B2DHomMatrix createScaleTranslateB2DHomMatrix(
326cdf0e10cSrcweir             double fScaleX, double fScaleY,
327cdf0e10cSrcweir             double fTranslateX, double fTranslateY)
328cdf0e10cSrcweir         {
329cdf0e10cSrcweir             const double fOne(1.0);
330cdf0e10cSrcweir 
331cdf0e10cSrcweir             if(fTools::equal(fScaleX, fOne) && fTools::equal(fScaleY, fOne))
332cdf0e10cSrcweir             {
333*45d1b581Smseidel                 // no scale, take shortcut
334cdf0e10cSrcweir                 return createTranslateB2DHomMatrix(fTranslateX, fTranslateY);
335cdf0e10cSrcweir             }
336cdf0e10cSrcweir             else
337cdf0e10cSrcweir             {
338*45d1b581Smseidel                 // scale used
339cdf0e10cSrcweir                 if(fTools::equalZero(fTranslateX) && fTools::equalZero(fTranslateY))
340cdf0e10cSrcweir                 {
341*45d1b581Smseidel                     // no translate, but scale.
342cdf0e10cSrcweir                     B2DHomMatrix aRetval;
343cdf0e10cSrcweir 
344cdf0e10cSrcweir                     aRetval.set(0, 0, fScaleX);
345cdf0e10cSrcweir                     aRetval.set(1, 1, fScaleY);
346cdf0e10cSrcweir 
347cdf0e10cSrcweir                     return aRetval;
348cdf0e10cSrcweir                 }
349cdf0e10cSrcweir                 else
350cdf0e10cSrcweir                 {
351*45d1b581Smseidel                     // translate and scale
352cdf0e10cSrcweir                     B2DHomMatrix aRetval(
353cdf0e10cSrcweir                         /* Row 0, Column 0 */ fScaleX,
354cdf0e10cSrcweir                         /* Row 0, Column 1 */ 0.0,
355cdf0e10cSrcweir                         /* Row 0, Column 2 */ fTranslateX,
356cdf0e10cSrcweir                         /* Row 1, Column 0 */ 0.0,
357cdf0e10cSrcweir                         /* Row 1, Column 1 */ fScaleY,
358cdf0e10cSrcweir                         /* Row 1, Column 2 */ fTranslateY);
359cdf0e10cSrcweir 
360cdf0e10cSrcweir                     return aRetval;
361cdf0e10cSrcweir                 }
362cdf0e10cSrcweir             }
363cdf0e10cSrcweir         }
364cdf0e10cSrcweir 
createRotateAroundPoint(double fPointX,double fPointY,double fRadiant)365cdf0e10cSrcweir         B2DHomMatrix createRotateAroundPoint(
366cdf0e10cSrcweir             double fPointX, double fPointY,
367cdf0e10cSrcweir             double fRadiant)
368cdf0e10cSrcweir         {
369cdf0e10cSrcweir             B2DHomMatrix aRetval;
370cdf0e10cSrcweir 
371cdf0e10cSrcweir             if(!fTools::equalZero(fRadiant))
372cdf0e10cSrcweir             {
373cdf0e10cSrcweir                 double fSin(0.0);
374cdf0e10cSrcweir                 double fCos(1.0);
375cdf0e10cSrcweir 
376cdf0e10cSrcweir                 createSinCosOrthogonal(fSin, fCos, fRadiant);
377cdf0e10cSrcweir 
378cdf0e10cSrcweir                 aRetval.set3x2(
379cdf0e10cSrcweir                     /* Row 0, Column 0 */ fCos,
380cdf0e10cSrcweir                     /* Row 0, Column 1 */ -fSin,
381cdf0e10cSrcweir                     /* Row 0, Column 2 */ (fPointX * (1.0 - fCos)) + (fSin * fPointY),
382cdf0e10cSrcweir                     /* Row 1, Column 0 */ fSin,
383cdf0e10cSrcweir                     /* Row 1, Column 1 */ fCos,
384cdf0e10cSrcweir                     /* Row 1, Column 2 */ (fPointY * (1.0 - fCos)) - (fSin * fPointX));
385cdf0e10cSrcweir             }
386cdf0e10cSrcweir 
387cdf0e10cSrcweir             return aRetval;
388cdf0e10cSrcweir         }
389d8ed516eSArmin Le Grand 
390*45d1b581Smseidel         // special for the case to map from source range to target range
createSourceRangeTargetRangeTransform(const B2DRange & rSourceRange,const B2DRange & rTargetRange)391d8ed516eSArmin Le Grand         B2DHomMatrix createSourceRangeTargetRangeTransform(
392d8ed516eSArmin Le Grand             const B2DRange& rSourceRange,
393d8ed516eSArmin Le Grand             const B2DRange& rTargetRange)
394d8ed516eSArmin Le Grand         {
395d8ed516eSArmin Le Grand             B2DHomMatrix aRetval;
396d8ed516eSArmin Le Grand 
397d8ed516eSArmin Le Grand             if(&rSourceRange == &rTargetRange)
398d8ed516eSArmin Le Grand             {
399d8ed516eSArmin Le Grand                 return aRetval;
400d8ed516eSArmin Le Grand             }
401d8ed516eSArmin Le Grand 
402d8ed516eSArmin Le Grand             if(!fTools::equalZero(rSourceRange.getMinX()) || !fTools::equalZero(rSourceRange.getMinY()))
403d8ed516eSArmin Le Grand             {
404d8ed516eSArmin Le Grand                 aRetval.set(0, 2, -rSourceRange.getMinX());
405d8ed516eSArmin Le Grand                 aRetval.set(1, 2, -rSourceRange.getMinY());
406d8ed516eSArmin Le Grand             }
407d8ed516eSArmin Le Grand 
408d8ed516eSArmin Le Grand             const double fSourceW(rSourceRange.getWidth());
409d8ed516eSArmin Le Grand             const double fSourceH(rSourceRange.getHeight());
410d8ed516eSArmin Le Grand             const bool bDivX(!fTools::equalZero(fSourceW) && !fTools::equal(fSourceW, 1.0));
411d8ed516eSArmin Le Grand             const bool bDivY(!fTools::equalZero(fSourceH) && !fTools::equal(fSourceH, 1.0));
412d8ed516eSArmin Le Grand             const double fScaleX(bDivX ? rTargetRange.getWidth() / fSourceW : rTargetRange.getWidth());
413d8ed516eSArmin Le Grand             const double fScaleY(bDivY ? rTargetRange.getHeight() / fSourceH : rTargetRange.getHeight());
414d8ed516eSArmin Le Grand 
415d8ed516eSArmin Le Grand             if(!fTools::equalZero(fScaleX) || !fTools::equalZero(fScaleY))
416d8ed516eSArmin Le Grand             {
417d8ed516eSArmin Le Grand                 aRetval.scale(fScaleX, fScaleY);
418d8ed516eSArmin Le Grand             }
419d8ed516eSArmin Le Grand 
420d8ed516eSArmin Le Grand             if(!fTools::equalZero(rTargetRange.getMinX()) || !fTools::equalZero(rTargetRange.getMinY()))
421d8ed516eSArmin Le Grand             {
422d8ed516eSArmin Le Grand                 aRetval.translate(
423d8ed516eSArmin Le Grand                     rTargetRange.getMinX(),
424d8ed516eSArmin Le Grand                     rTargetRange.getMinY());
425d8ed516eSArmin Le Grand             }
426d8ed516eSArmin Le Grand 
427d8ed516eSArmin Le Grand             return aRetval;
428d8ed516eSArmin Le Grand         }
429d8ed516eSArmin Le Grand 
430cdf0e10cSrcweir     } // end of namespace tools
431cdf0e10cSrcweir } // end of namespace basegfx
432cdf0e10cSrcweir 
433*45d1b581Smseidel /* vim: set noet sw=4 ts=4: */
434