1 /************************************************************** 2 * 3 * Licensed to the Apache Software Foundation (ASF) under one 4 * or more contributor license agreements. See the NOTICE file 5 * distributed with this work for additional information 6 * regarding copyright ownership. The ASF licenses this file 7 * to you under the Apache License, Version 2.0 (the 8 * "License"); you may not use this file except in compliance 9 * with the License. You may obtain a copy of the License at 10 * 11 * http://www.apache.org/licenses/LICENSE-2.0 12 * 13 * Unless required by applicable law or agreed to in writing, 14 * software distributed under the License is distributed on an 15 * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY 16 * KIND, either express or implied. See the License for the 17 * specific language governing permissions and limitations 18 * under the License. 19 * 20 *************************************************************/ 21 22 23 24 // MARKER(update_precomp.py): autogen include statement, do not remove 25 #include "precompiled_xmloff.hxx" 26 #include "xexptran.hxx" 27 #include <tools/debug.hxx> 28 #include <rtl/ustrbuf.hxx> 29 #include <xmloff/xmluconv.hxx> 30 #include <tools/gen.hxx> 31 #include <basegfx/vector/b2dvector.hxx> 32 #include <basegfx/matrix/b2dhommatrix.hxx> 33 #include <basegfx/tuple/b3dtuple.hxx> 34 #include <basegfx/matrix/b3dhommatrix.hxx> 35 #include <tools/string.hxx> 36 37 using ::rtl::OUString; 38 using ::rtl::OUStringBuffer; 39 40 using namespace ::com::sun::star; 41 42 ////////////////////////////////////////////////////////////////////////////// 43 // Defines 44 45 #define BORDER_INTEGERS_ARE_EQUAL (4) 46 47 ////////////////////////////////////////////////////////////////////////////// 48 // Predeclarations 49 50 void Imp_SkipDouble(const OUString& rStr, sal_Int32& rPos, const sal_Int32 nLen); 51 void Imp_CalcVectorValues(::basegfx::B2DVector& aVec1, ::basegfx::B2DVector& aVec2, bool& bSameLength, bool& bSameDirection); 52 53 ////////////////////////////////////////////////////////////////////////////// 54 ////////////////////////////////////////////////////////////////////////////// 55 // parsing help functions for simple chars 56 void Imp_SkipSpaces(const OUString& rStr, sal_Int32& rPos, const sal_Int32 nLen) 57 { 58 while(rPos < nLen 59 && sal_Unicode(' ') == rStr[rPos]) 60 rPos++; 61 } 62 63 void Imp_SkipSpacesAndOpeningBraces(const OUString& rStr, sal_Int32& rPos, const sal_Int32 nLen) 64 { 65 while(rPos < nLen 66 && (sal_Unicode(' ') == rStr[rPos] || sal_Unicode('(') == rStr[rPos])) 67 rPos++; 68 } 69 70 void Imp_SkipSpacesAndCommas(const OUString& rStr, sal_Int32& rPos, const sal_Int32 nLen) 71 { 72 while(rPos < nLen 73 && (sal_Unicode(' ') == rStr[rPos] || sal_Unicode(',') == rStr[rPos])) 74 rPos++; 75 } 76 77 void Imp_SkipSpacesAndClosingBraces(const OUString& rStr, sal_Int32& rPos, const sal_Int32 nLen) 78 { 79 while(rPos < nLen 80 && (sal_Unicode(' ') == rStr[rPos] || sal_Unicode(')') == rStr[rPos])) 81 rPos++; 82 } 83 84 ////////////////////////////////////////////////////////////////////////////// 85 ////////////////////////////////////////////////////////////////////////////// 86 // parsing help functions for integer numbers 87 88 bool Imp_IsOnNumberChar(const OUString& rStr, const sal_Int32 nPos, bool bSignAllowed = true) 89 { 90 sal_Unicode aChar(rStr[nPos]); 91 92 if((sal_Unicode('0') <= aChar && sal_Unicode('9') >= aChar) 93 || (bSignAllowed && sal_Unicode('+') == aChar) 94 || (bSignAllowed && sal_Unicode('-') == aChar) 95 ) 96 return true; 97 return false; 98 } 99 100 bool Imp_IsOnUnitChar(const OUString& rStr, const sal_Int32 nPos) 101 { 102 sal_Unicode aChar(rStr[nPos]); 103 104 if((sal_Unicode('a') <= aChar && sal_Unicode('z') >= aChar) 105 || (sal_Unicode('A') <= aChar && sal_Unicode('Z') >= aChar) 106 || sal_Unicode('%') == aChar 107 ) 108 return true; 109 return false; 110 } 111 112 void Imp_SkipNumber(const OUString& rStr, sal_Int32& rPos, const sal_Int32 nLen) 113 { 114 bool bSignAllowed(true); 115 116 while(rPos < nLen && Imp_IsOnNumberChar(rStr, rPos, bSignAllowed)) 117 { 118 bSignAllowed = false; 119 rPos++; 120 } 121 } 122 123 void Imp_SkipNumberAndSpacesAndCommas(const OUString& rStr, sal_Int32& rPos, 124 const sal_Int32 nLen) 125 { 126 Imp_SkipNumber(rStr, rPos, nLen); 127 Imp_SkipSpacesAndCommas(rStr, rPos, nLen); 128 } 129 130 // #100617# Allow to skip doubles, too. 131 void Imp_SkipDoubleAndSpacesAndCommas(const OUString& rStr, sal_Int32& rPos, 132 const sal_Int32 nLen) 133 { 134 Imp_SkipDouble(rStr, rPos, nLen); 135 Imp_SkipSpacesAndCommas(rStr, rPos, nLen); 136 } 137 138 void Imp_PutNumberChar(OUString& rStr, sal_Int32 nValue) 139 { 140 OUStringBuffer sStringBuffer; 141 SvXMLUnitConverter::convertNumber(sStringBuffer, nValue); 142 rStr += OUString(sStringBuffer.makeStringAndClear()); 143 } 144 145 void Imp_PutNumberCharWithSpace(OUString& rStr, sal_Int32 nValue) 146 { 147 const sal_Int32 aLen(rStr.getLength()); 148 if(aLen) 149 if(Imp_IsOnNumberChar(rStr, aLen - 1, false) && nValue >= 0) 150 rStr += String(sal_Unicode(' ')); 151 Imp_PutNumberChar(rStr, nValue); 152 } 153 154 ////////////////////////////////////////////////////////////////////////////// 155 ////////////////////////////////////////////////////////////////////////////// 156 // parsing help functions for double numbers 157 158 void Imp_SkipDouble(const OUString& rStr, sal_Int32& rPos, const sal_Int32) 159 { 160 sal_Unicode aChar(rStr[rPos]); 161 162 if(sal_Unicode('+') == aChar || sal_Unicode('-') == aChar) 163 aChar = rStr[++rPos]; 164 165 while((sal_Unicode('0') <= aChar && sal_Unicode('9') >= aChar) 166 || sal_Unicode('.') == aChar) 167 { 168 aChar = rStr[++rPos]; 169 } 170 171 if(sal_Unicode('e') == aChar || sal_Unicode('E') == aChar) 172 { 173 aChar = rStr[++rPos]; 174 175 if(sal_Unicode('+') == aChar || sal_Unicode('-') == aChar) 176 aChar = rStr[++rPos]; 177 178 while(sal_Unicode('0') <= aChar && sal_Unicode('9') >= aChar) 179 { 180 aChar = rStr[++rPos]; 181 } 182 } 183 } 184 185 double Imp_GetDoubleChar(const OUString& rStr, sal_Int32& rPos, const sal_Int32 nLen, 186 const SvXMLUnitConverter& rConv, double fRetval, bool bLookForUnits = false) 187 { 188 sal_Unicode aChar(rStr[rPos]); 189 OUStringBuffer sNumberString; 190 191 if(sal_Unicode('+') == aChar || sal_Unicode('-') == aChar) 192 { 193 sNumberString.append(rStr[rPos]); 194 aChar = rStr[++rPos]; 195 } 196 197 while((sal_Unicode('0') <= aChar && sal_Unicode('9') >= aChar) 198 || sal_Unicode('.') == aChar) 199 { 200 sNumberString.append(rStr[rPos]); 201 aChar = rStr[++rPos]; 202 } 203 204 if(sal_Unicode('e') == aChar || sal_Unicode('E') == aChar) 205 { 206 sNumberString.append(rStr[rPos]); 207 aChar = rStr[++rPos]; 208 209 if(sal_Unicode('+') == aChar || sal_Unicode('-') == aChar) 210 { 211 sNumberString.append(rStr[rPos]); 212 aChar = rStr[++rPos]; 213 } 214 215 while(sal_Unicode('0') <= aChar && sal_Unicode('9') >= aChar) 216 { 217 sNumberString.append(rStr[rPos]); 218 aChar = rStr[++rPos]; 219 } 220 } 221 222 if(bLookForUnits) 223 { 224 Imp_SkipSpaces(rStr, rPos, nLen); 225 while(rPos < nLen && Imp_IsOnUnitChar(rStr, rPos)) 226 sNumberString.append(rStr[rPos++]); 227 } 228 229 if(sNumberString.getLength()) 230 { 231 if(bLookForUnits) 232 rConv.convertDouble(fRetval, sNumberString.makeStringAndClear(), true); 233 else 234 rConv.convertDouble(fRetval, sNumberString.makeStringAndClear()); 235 } 236 237 return fRetval; 238 } 239 240 void Imp_PutDoubleChar(OUString& rStr, double fValue) 241 { 242 OUStringBuffer sStringBuffer; 243 SvXMLUnitConverter::convertDouble(sStringBuffer, fValue); 244 rStr += OUString(sStringBuffer.makeStringAndClear()); 245 } 246 247 void Imp_PutDoubleChar(OUString& rStr, const SvXMLUnitConverter& rConv, double fValue, 248 bool bConvertUnits = false) 249 { 250 OUStringBuffer sStringBuffer; 251 252 if(bConvertUnits) 253 rConv.convertDouble(sStringBuffer, fValue, true); 254 else 255 rConv.convertDouble(sStringBuffer, fValue); 256 257 rStr += OUString(sStringBuffer.makeStringAndClear()); 258 } 259 260 ////////////////////////////////////////////////////////////////////////////// 261 ////////////////////////////////////////////////////////////////////////////// 262 // base class of all 2D transform objects 263 264 struct ImpSdXMLExpTransObj2DBase 265 { 266 sal_uInt16 mnType; 267 ImpSdXMLExpTransObj2DBase(sal_uInt16 nType) 268 : mnType(nType) {} 269 }; 270 271 ////////////////////////////////////////////////////////////////////////////// 272 // possible object types for 2D 273 274 #define IMP_SDXMLEXP_TRANSOBJ2D_ROTATE 0x0000 275 #define IMP_SDXMLEXP_TRANSOBJ2D_SCALE 0x0001 276 #define IMP_SDXMLEXP_TRANSOBJ2D_TRANSLATE 0x0002 277 #define IMP_SDXMLEXP_TRANSOBJ2D_SKEWX 0x0003 278 #define IMP_SDXMLEXP_TRANSOBJ2D_SKEWY 0x0004 279 #define IMP_SDXMLEXP_TRANSOBJ2D_MATRIX 0x0005 280 281 ////////////////////////////////////////////////////////////////////////////// 282 // classes of objects, different sizes 283 284 struct ImpSdXMLExpTransObj2DRotate : public ImpSdXMLExpTransObj2DBase 285 { 286 double mfRotate; 287 ImpSdXMLExpTransObj2DRotate(double fVal) 288 : ImpSdXMLExpTransObj2DBase(IMP_SDXMLEXP_TRANSOBJ2D_ROTATE), mfRotate(fVal) {} 289 }; 290 struct ImpSdXMLExpTransObj2DScale : public ImpSdXMLExpTransObj2DBase 291 { 292 ::basegfx::B2DTuple maScale; 293 ImpSdXMLExpTransObj2DScale(const ::basegfx::B2DTuple& rNew) 294 : ImpSdXMLExpTransObj2DBase(IMP_SDXMLEXP_TRANSOBJ2D_SCALE), maScale(rNew) {} 295 }; 296 struct ImpSdXMLExpTransObj2DTranslate : public ImpSdXMLExpTransObj2DBase 297 { 298 ::basegfx::B2DTuple maTranslate; 299 ImpSdXMLExpTransObj2DTranslate(const ::basegfx::B2DTuple& rNew) 300 : ImpSdXMLExpTransObj2DBase(IMP_SDXMLEXP_TRANSOBJ2D_TRANSLATE), maTranslate(rNew) {} 301 }; 302 struct ImpSdXMLExpTransObj2DSkewX : public ImpSdXMLExpTransObj2DBase 303 { 304 double mfSkewX; 305 ImpSdXMLExpTransObj2DSkewX(double fVal) 306 : ImpSdXMLExpTransObj2DBase(IMP_SDXMLEXP_TRANSOBJ2D_SKEWX), mfSkewX(fVal) {} 307 }; 308 struct ImpSdXMLExpTransObj2DSkewY : public ImpSdXMLExpTransObj2DBase 309 { 310 double mfSkewY; 311 ImpSdXMLExpTransObj2DSkewY(double fVal) 312 : ImpSdXMLExpTransObj2DBase(IMP_SDXMLEXP_TRANSOBJ2D_SKEWY), mfSkewY(fVal) {} 313 }; 314 struct ImpSdXMLExpTransObj2DMatrix : public ImpSdXMLExpTransObj2DBase 315 { 316 ::basegfx::B2DHomMatrix maMatrix; 317 ImpSdXMLExpTransObj2DMatrix(const ::basegfx::B2DHomMatrix& rNew) 318 : ImpSdXMLExpTransObj2DBase(IMP_SDXMLEXP_TRANSOBJ2D_MATRIX), maMatrix(rNew) {} 319 }; 320 321 ////////////////////////////////////////////////////////////////////////////// 322 ////////////////////////////////////////////////////////////////////////////// 323 // delete all entries in list 324 325 void SdXMLImExTransform2D::EmptyList() 326 { 327 const sal_uInt32 nCount = maList.size(); 328 for(sal_uInt32 a(0L); a < nCount; a++) 329 { 330 ImpSdXMLExpTransObj2DBase* pObj = maList[a]; 331 332 switch(pObj->mnType) 333 { 334 case IMP_SDXMLEXP_TRANSOBJ2D_ROTATE : 335 { 336 delete (ImpSdXMLExpTransObj2DRotate*)pObj; 337 break; 338 } 339 case IMP_SDXMLEXP_TRANSOBJ2D_SCALE : 340 { 341 delete (ImpSdXMLExpTransObj2DScale*)pObj; 342 break; 343 } 344 case IMP_SDXMLEXP_TRANSOBJ2D_TRANSLATE : 345 { 346 delete (ImpSdXMLExpTransObj2DTranslate*)pObj; 347 break; 348 } 349 case IMP_SDXMLEXP_TRANSOBJ2D_SKEWX : 350 { 351 delete (ImpSdXMLExpTransObj2DSkewX*)pObj; 352 break; 353 } 354 case IMP_SDXMLEXP_TRANSOBJ2D_SKEWY : 355 { 356 delete (ImpSdXMLExpTransObj2DSkewY*)pObj; 357 break; 358 } 359 case IMP_SDXMLEXP_TRANSOBJ2D_MATRIX : 360 { 361 delete (ImpSdXMLExpTransObj2DMatrix*)pObj; 362 break; 363 } 364 default : 365 { 366 DBG_ERROR("SdXMLImExTransform2D: impossible entry!"); 367 break; 368 } 369 } 370 } 371 372 maList.clear(); 373 } 374 375 ////////////////////////////////////////////////////////////////////////////// 376 // add members 377 378 void SdXMLImExTransform2D::AddRotate(double fNew) 379 { 380 if(fNew != 0.0) 381 maList.push_back(new ImpSdXMLExpTransObj2DRotate(fNew)); 382 } 383 384 void SdXMLImExTransform2D::AddScale(const ::basegfx::B2DTuple& rNew) 385 { 386 if(1.0 != rNew.getX() || 1.0 != rNew.getY()) 387 maList.push_back(new ImpSdXMLExpTransObj2DScale(rNew)); 388 } 389 390 void SdXMLImExTransform2D::AddTranslate(const ::basegfx::B2DTuple& rNew) 391 { 392 if(!rNew.equalZero()) 393 maList.push_back(new ImpSdXMLExpTransObj2DTranslate(rNew)); 394 } 395 396 void SdXMLImExTransform2D::AddSkewX(double fNew) 397 { 398 if(fNew != 0.0) 399 maList.push_back(new ImpSdXMLExpTransObj2DSkewX(fNew)); 400 } 401 402 void SdXMLImExTransform2D::AddSkewY(double fNew) 403 { 404 if(fNew != 0.0) 405 maList.push_back(new ImpSdXMLExpTransObj2DSkewY(fNew)); 406 } 407 408 void SdXMLImExTransform2D::AddMatrix(const ::basegfx::B2DHomMatrix& rNew) 409 { 410 if(!rNew.isIdentity()) 411 maList.push_back(new ImpSdXMLExpTransObj2DMatrix(rNew)); 412 } 413 414 ////////////////////////////////////////////////////////////////////////////// 415 // gen string for export 416 const OUString& SdXMLImExTransform2D::GetExportString(const SvXMLUnitConverter& rConv) 417 { 418 OUString aNewString; 419 OUString aClosingBrace(sal_Unicode(')')); 420 OUString aEmptySpace(sal_Unicode(' ')); 421 422 const sal_uInt32 nCount = maList.size(); 423 for(sal_uInt32 a(0L); a < nCount; a++) 424 { 425 ImpSdXMLExpTransObj2DBase* pObj = maList[a]; 426 switch(pObj->mnType) 427 { 428 case IMP_SDXMLEXP_TRANSOBJ2D_ROTATE : 429 { 430 aNewString += OUString::createFromAscii("rotate ("); 431 Imp_PutDoubleChar(aNewString, rConv, ((ImpSdXMLExpTransObj2DRotate*)pObj)->mfRotate); 432 aNewString += aClosingBrace; 433 break; 434 } 435 case IMP_SDXMLEXP_TRANSOBJ2D_SCALE : 436 { 437 aNewString += OUString::createFromAscii("scale ("); 438 Imp_PutDoubleChar(aNewString, rConv, ((ImpSdXMLExpTransObj2DScale*)pObj)->maScale.getX()); 439 aNewString += aEmptySpace; 440 Imp_PutDoubleChar(aNewString, rConv, ((ImpSdXMLExpTransObj2DScale*)pObj)->maScale.getY()); 441 aNewString += aClosingBrace; 442 break; 443 } 444 case IMP_SDXMLEXP_TRANSOBJ2D_TRANSLATE : 445 { 446 aNewString += OUString::createFromAscii("translate ("); 447 Imp_PutDoubleChar(aNewString, rConv, ((ImpSdXMLExpTransObj2DTranslate*)pObj)->maTranslate.getX(), true); 448 aNewString += aEmptySpace; 449 Imp_PutDoubleChar(aNewString, rConv, ((ImpSdXMLExpTransObj2DTranslate*)pObj)->maTranslate.getY(), true); 450 aNewString += aClosingBrace; 451 break; 452 } 453 case IMP_SDXMLEXP_TRANSOBJ2D_SKEWX : 454 { 455 aNewString += OUString::createFromAscii("skewX ("); 456 Imp_PutDoubleChar(aNewString, rConv, ((ImpSdXMLExpTransObj2DSkewX*)pObj)->mfSkewX); 457 aNewString += aClosingBrace; 458 break; 459 } 460 case IMP_SDXMLEXP_TRANSOBJ2D_SKEWY : 461 { 462 aNewString += OUString::createFromAscii("skewY ("); 463 Imp_PutDoubleChar(aNewString, rConv, ((ImpSdXMLExpTransObj2DSkewY*)pObj)->mfSkewY); 464 aNewString += aClosingBrace; 465 break; 466 } 467 case IMP_SDXMLEXP_TRANSOBJ2D_MATRIX : 468 { 469 aNewString += OUString::createFromAscii("matrix ("); 470 471 // a 472 Imp_PutDoubleChar(aNewString, rConv, ((ImpSdXMLExpTransObj2DMatrix*)pObj)->maMatrix.get(0, 0)); 473 aNewString += aEmptySpace; 474 475 // b 476 Imp_PutDoubleChar(aNewString, rConv, ((ImpSdXMLExpTransObj2DMatrix*)pObj)->maMatrix.get(1, 0)); 477 aNewString += aEmptySpace; 478 479 // c 480 Imp_PutDoubleChar(aNewString, rConv, ((ImpSdXMLExpTransObj2DMatrix*)pObj)->maMatrix.get(0, 1)); 481 aNewString += aEmptySpace; 482 483 // d 484 Imp_PutDoubleChar(aNewString, rConv, ((ImpSdXMLExpTransObj2DMatrix*)pObj)->maMatrix.get(1, 1)); 485 aNewString += aEmptySpace; 486 487 // e 488 Imp_PutDoubleChar(aNewString, rConv, ((ImpSdXMLExpTransObj2DMatrix*)pObj)->maMatrix.get(0, 2), true); 489 aNewString += aEmptySpace; 490 491 // f 492 Imp_PutDoubleChar(aNewString, rConv, ((ImpSdXMLExpTransObj2DMatrix*)pObj)->maMatrix.get(1, 2), true); 493 494 aNewString += aClosingBrace; 495 break; 496 } 497 default : 498 { 499 DBG_ERROR("SdXMLImExTransform2D: impossible entry!"); 500 break; 501 } 502 } 503 504 // if not the last entry, add one space to next tag 505 if(a + 1UL != maList.size()) 506 { 507 aNewString += aEmptySpace; 508 } 509 } 510 511 // fill string form OUString 512 msString = aNewString; 513 514 return msString; 515 } 516 517 ////////////////////////////////////////////////////////////////////////////// 518 // for Import: constructor with string, parses it and generates entries 519 SdXMLImExTransform2D::SdXMLImExTransform2D(const OUString& rNew, const SvXMLUnitConverter& rConv) 520 { 521 SetString(rNew, rConv); 522 } 523 524 ////////////////////////////////////////////////////////////////////////////// 525 // sets new string, parses it and generates entries 526 void SdXMLImExTransform2D::SetString(const OUString& rNew, const SvXMLUnitConverter& rConv) 527 { 528 msString = rNew; 529 EmptyList(); 530 531 if(msString.getLength()) 532 { 533 const OUString aStr(msString.getStr(), (sal_uInt16)msString.getLength()); 534 const sal_Int32 nLen(aStr.getLength()); 535 536 const OUString aString_rotate(OUString::createFromAscii("rotate")); 537 const OUString aString_scale(OUString::createFromAscii("scale")); 538 const OUString aString_translate(OUString::createFromAscii("translate")); 539 const OUString aString_skewX(OUString::createFromAscii("skewX")); 540 const OUString aString_skewY(OUString::createFromAscii("skewY")); 541 const OUString aString_matrix(OUString::createFromAscii("matrix")); 542 543 sal_Int32 nPos(0); 544 545 while(nPos < nLen) 546 { 547 // skip spaces 548 Imp_SkipSpaces(aStr, nPos, nLen); 549 550 // look for tag 551 if(nPos < nLen) 552 { 553 if(nPos == aStr.indexOf(aString_rotate, nPos)) 554 { 555 double fValue(0.0); 556 nPos += 6; 557 Imp_SkipSpacesAndOpeningBraces(aStr, nPos, nLen); 558 fValue = Imp_GetDoubleChar(aStr, nPos, nLen, rConv, fValue); 559 if(fValue != 0.0) 560 maList.push_back(new ImpSdXMLExpTransObj2DRotate(fValue)); 561 562 Imp_SkipSpacesAndClosingBraces(aStr, nPos, nLen); 563 } 564 else if(nPos == aStr.indexOf(aString_scale, nPos)) 565 { 566 ::basegfx::B2DTuple aValue(1.0, 1.0); 567 nPos += 5; 568 Imp_SkipSpacesAndOpeningBraces(aStr, nPos, nLen); 569 aValue.setX(Imp_GetDoubleChar(aStr, nPos, nLen, rConv, aValue.getX())); 570 Imp_SkipSpacesAndCommas(aStr, nPos, nLen); 571 aValue.setY(Imp_GetDoubleChar(aStr, nPos, nLen, rConv, aValue.getY())); 572 573 if(aValue.getX() != 1.0 || aValue.getY() != 1.0) 574 maList.push_back(new ImpSdXMLExpTransObj2DScale(aValue)); 575 576 Imp_SkipSpacesAndClosingBraces(aStr, nPos, nLen); 577 } 578 else if(nPos == aStr.indexOf(aString_translate, nPos)) 579 { 580 ::basegfx::B2DTuple aValue; 581 nPos += 9; 582 Imp_SkipSpacesAndOpeningBraces(aStr, nPos, nLen); 583 aValue.setX(Imp_GetDoubleChar(aStr, nPos, nLen, rConv, aValue.getX(), true)); 584 Imp_SkipSpacesAndCommas(aStr, nPos, nLen); 585 aValue.setY(Imp_GetDoubleChar(aStr, nPos, nLen, rConv, aValue.getY(), true)); 586 587 if(!aValue.equalZero()) 588 maList.push_back(new ImpSdXMLExpTransObj2DTranslate(aValue)); 589 590 Imp_SkipSpacesAndClosingBraces(aStr, nPos, nLen); 591 } 592 else if(nPos == aStr.indexOf(aString_skewX, nPos)) 593 { 594 double fValue(0.0); 595 nPos += 5; 596 Imp_SkipSpacesAndOpeningBraces(aStr, nPos, nLen); 597 fValue = Imp_GetDoubleChar(aStr, nPos, nLen, rConv, fValue); 598 if(fValue != 0.0) 599 maList.push_back(new ImpSdXMLExpTransObj2DSkewX(fValue)); 600 601 Imp_SkipSpacesAndClosingBraces(aStr, nPos, nLen); 602 } 603 else if(nPos == aStr.indexOf(aString_skewY, nPos)) 604 { 605 double fValue(0.0); 606 nPos += 5; 607 Imp_SkipSpacesAndOpeningBraces(aStr, nPos, nLen); 608 fValue = Imp_GetDoubleChar(aStr, nPos, nLen, rConv, fValue); 609 if(fValue != 0.0) 610 maList.push_back(new ImpSdXMLExpTransObj2DSkewY(fValue)); 611 612 Imp_SkipSpacesAndClosingBraces(aStr, nPos, nLen); 613 } 614 else if(nPos == aStr.indexOf(aString_matrix, nPos)) 615 { 616 ::basegfx::B2DHomMatrix aValue; 617 618 nPos += 6; 619 Imp_SkipSpacesAndOpeningBraces(aStr, nPos, nLen); 620 621 // a 622 aValue.set(0, 0, Imp_GetDoubleChar(aStr, nPos, nLen, rConv, aValue.get(0, 0))); 623 Imp_SkipSpacesAndCommas(aStr, nPos, nLen); 624 625 // b 626 aValue.set(1, 0, Imp_GetDoubleChar(aStr, nPos, nLen, rConv, aValue.get(1, 0))); 627 Imp_SkipSpacesAndCommas(aStr, nPos, nLen); 628 629 // c 630 aValue.set(0, 1, Imp_GetDoubleChar(aStr, nPos, nLen, rConv, aValue.get(0, 1))); 631 Imp_SkipSpacesAndCommas(aStr, nPos, nLen); 632 633 // d 634 aValue.set(1, 1, Imp_GetDoubleChar(aStr, nPos, nLen, rConv, aValue.get(1, 1))); 635 Imp_SkipSpacesAndCommas(aStr, nPos, nLen); 636 637 // e 638 aValue.set(0, 2, Imp_GetDoubleChar(aStr, nPos, nLen, rConv, aValue.get(0, 2), true)); 639 Imp_SkipSpacesAndCommas(aStr, nPos, nLen); 640 641 // f 642 aValue.set(1, 2, Imp_GetDoubleChar(aStr, nPos, nLen, rConv, aValue.get(1, 2), true)); 643 Imp_SkipSpacesAndCommas(aStr, nPos, nLen); 644 645 if(!aValue.isIdentity()) 646 maList.push_back(new ImpSdXMLExpTransObj2DMatrix(aValue)); 647 648 Imp_SkipSpacesAndClosingBraces(aStr, nPos, nLen); 649 } 650 else 651 { 652 nPos++; 653 } 654 } 655 } 656 } 657 } 658 659 void SdXMLImExTransform2D::GetFullTransform(::basegfx::B2DHomMatrix& rFullTrans) 660 { 661 rFullTrans.identity(); 662 663 const sal_uInt32 nCount = maList.size(); 664 for(sal_uInt32 a(0L); a < nCount; a++) 665 { 666 ImpSdXMLExpTransObj2DBase* pObj = maList[a]; 667 switch(pObj->mnType) 668 { 669 case IMP_SDXMLEXP_TRANSOBJ2D_ROTATE : 670 { 671 // #i78696# 672 // mfRotate is mathematically wrong oriented since we export/import the angle 673 // values mirrored. This error is fixed in the API, but not yet in the FileFormat. 674 // For the FileFormat there is a follow-up task (#i78698#) to fix this in the next 675 // ODF FileFormat version. For now - to emulate the old behaviour - it is necessary 676 // to mirror the value here 677 rFullTrans.rotate(((ImpSdXMLExpTransObj2DRotate*)pObj)->mfRotate * -1.0); 678 break; 679 } 680 case IMP_SDXMLEXP_TRANSOBJ2D_SCALE : 681 { 682 const ::basegfx::B2DTuple& rScale = ((ImpSdXMLExpTransObj2DScale*)pObj)->maScale; 683 rFullTrans.scale(rScale.getX(), rScale.getY()); 684 break; 685 } 686 case IMP_SDXMLEXP_TRANSOBJ2D_TRANSLATE : 687 { 688 const ::basegfx::B2DTuple& rTranslate = ((ImpSdXMLExpTransObj2DTranslate*)pObj)->maTranslate; 689 rFullTrans.translate(rTranslate.getX(), rTranslate.getY()); 690 break; 691 } 692 case IMP_SDXMLEXP_TRANSOBJ2D_SKEWX : 693 { 694 rFullTrans.shearX(tan(((ImpSdXMLExpTransObj2DSkewX*)pObj)->mfSkewX)); 695 break; 696 } 697 case IMP_SDXMLEXP_TRANSOBJ2D_SKEWY : 698 { 699 rFullTrans.shearY(tan(((ImpSdXMLExpTransObj2DSkewY*)pObj)->mfSkewY)); 700 break; 701 } 702 case IMP_SDXMLEXP_TRANSOBJ2D_MATRIX : 703 { 704 rFullTrans *= ((ImpSdXMLExpTransObj2DMatrix*)pObj)->maMatrix; 705 break; 706 } 707 default : 708 { 709 DBG_ERROR("SdXMLImExTransform2D: impossible entry!"); 710 break; 711 } 712 } 713 } 714 } 715 716 ////////////////////////////////////////////////////////////////////////////// 717 ////////////////////////////////////////////////////////////////////////////// 718 // base class of all 3D transform objects 719 720 struct ImpSdXMLExpTransObj3DBase 721 { 722 sal_uInt16 mnType; 723 ImpSdXMLExpTransObj3DBase(sal_uInt16 nType) 724 : mnType(nType) {} 725 }; 726 727 ////////////////////////////////////////////////////////////////////////////// 728 // possible object types for 3D 729 730 #define IMP_SDXMLEXP_TRANSOBJ3D_ROTATE_X 0x0000 731 #define IMP_SDXMLEXP_TRANSOBJ3D_ROTATE_Y 0x0001 732 #define IMP_SDXMLEXP_TRANSOBJ3D_ROTATE_Z 0x0002 733 #define IMP_SDXMLEXP_TRANSOBJ3D_SCALE 0x0003 734 #define IMP_SDXMLEXP_TRANSOBJ3D_TRANSLATE 0x0004 735 #define IMP_SDXMLEXP_TRANSOBJ3D_MATRIX 0x0005 736 737 ////////////////////////////////////////////////////////////////////////////// 738 // classes of objects, different sizes 739 740 struct ImpSdXMLExpTransObj3DRotateX : public ImpSdXMLExpTransObj3DBase 741 { 742 double mfRotateX; 743 ImpSdXMLExpTransObj3DRotateX(double fVal) 744 : ImpSdXMLExpTransObj3DBase(IMP_SDXMLEXP_TRANSOBJ3D_ROTATE_X), mfRotateX(fVal) {} 745 }; 746 struct ImpSdXMLExpTransObj3DRotateY : public ImpSdXMLExpTransObj3DBase 747 { 748 double mfRotateY; 749 ImpSdXMLExpTransObj3DRotateY(double fVal) 750 : ImpSdXMLExpTransObj3DBase(IMP_SDXMLEXP_TRANSOBJ3D_ROTATE_Y), mfRotateY(fVal) {} 751 }; 752 struct ImpSdXMLExpTransObj3DRotateZ : public ImpSdXMLExpTransObj3DBase 753 { 754 double mfRotateZ; 755 ImpSdXMLExpTransObj3DRotateZ(double fVal) 756 : ImpSdXMLExpTransObj3DBase(IMP_SDXMLEXP_TRANSOBJ3D_ROTATE_Z), mfRotateZ(fVal) {} 757 }; 758 struct ImpSdXMLExpTransObj3DScale : public ImpSdXMLExpTransObj3DBase 759 { 760 ::basegfx::B3DTuple maScale; 761 ImpSdXMLExpTransObj3DScale(const ::basegfx::B3DTuple& rNew) 762 : ImpSdXMLExpTransObj3DBase(IMP_SDXMLEXP_TRANSOBJ3D_SCALE), maScale(rNew) {} 763 }; 764 struct ImpSdXMLExpTransObj3DTranslate : public ImpSdXMLExpTransObj3DBase 765 { 766 ::basegfx::B3DTuple maTranslate; 767 ImpSdXMLExpTransObj3DTranslate(const ::basegfx::B3DTuple& rNew) 768 : ImpSdXMLExpTransObj3DBase(IMP_SDXMLEXP_TRANSOBJ3D_TRANSLATE), maTranslate(rNew) {} 769 }; 770 struct ImpSdXMLExpTransObj3DMatrix : public ImpSdXMLExpTransObj3DBase 771 { 772 ::basegfx::B3DHomMatrix maMatrix; 773 ImpSdXMLExpTransObj3DMatrix(const ::basegfx::B3DHomMatrix& rNew) 774 : ImpSdXMLExpTransObj3DBase(IMP_SDXMLEXP_TRANSOBJ3D_MATRIX), maMatrix(rNew) {} 775 }; 776 777 ////////////////////////////////////////////////////////////////////////////// 778 ////////////////////////////////////////////////////////////////////////////// 779 // delete all entries in list 780 781 void SdXMLImExTransform3D::EmptyList() 782 { 783 const sal_uInt32 nCount = maList.size(); 784 for(sal_uInt32 a(0L); a < nCount; a++) 785 { 786 ImpSdXMLExpTransObj3DBase* pObj = maList[a]; 787 788 switch(pObj->mnType) 789 { 790 case IMP_SDXMLEXP_TRANSOBJ3D_ROTATE_X : 791 { 792 delete (ImpSdXMLExpTransObj3DRotateX*)pObj; 793 break; 794 } 795 case IMP_SDXMLEXP_TRANSOBJ3D_ROTATE_Y : 796 { 797 delete (ImpSdXMLExpTransObj3DRotateY*)pObj; 798 break; 799 } 800 case IMP_SDXMLEXP_TRANSOBJ3D_ROTATE_Z : 801 { 802 delete (ImpSdXMLExpTransObj3DRotateZ*)pObj; 803 break; 804 } 805 case IMP_SDXMLEXP_TRANSOBJ3D_SCALE : 806 { 807 delete (ImpSdXMLExpTransObj3DScale*)pObj; 808 break; 809 } 810 case IMP_SDXMLEXP_TRANSOBJ3D_TRANSLATE : 811 { 812 delete (ImpSdXMLExpTransObj3DTranslate*)pObj; 813 break; 814 } 815 case IMP_SDXMLEXP_TRANSOBJ3D_MATRIX : 816 { 817 delete (ImpSdXMLExpTransObj3DMatrix*)pObj; 818 break; 819 } 820 default : 821 { 822 DBG_ERROR("SdXMLImExTransform3D: impossible entry!"); 823 break; 824 } 825 } 826 } 827 828 maList.clear(); 829 } 830 831 ////////////////////////////////////////////////////////////////////////////// 832 // add members 833 834 void SdXMLImExTransform3D::AddRotateX(double fNew) 835 { 836 if(fNew != 0.0) 837 maList.push_back(new ImpSdXMLExpTransObj3DRotateX(fNew)); 838 } 839 840 void SdXMLImExTransform3D::AddRotateY(double fNew) 841 { 842 if(fNew != 0.0) 843 maList.push_back(new ImpSdXMLExpTransObj3DRotateY(fNew)); 844 } 845 846 void SdXMLImExTransform3D::AddRotateZ(double fNew) 847 { 848 if(fNew != 0.0) 849 maList.push_back(new ImpSdXMLExpTransObj3DRotateZ(fNew)); 850 } 851 852 void SdXMLImExTransform3D::AddScale(const ::basegfx::B3DTuple& rNew) 853 { 854 if(1.0 != rNew.getX() || 1.0 != rNew.getY() || 1.0 != rNew.getZ()) 855 maList.push_back(new ImpSdXMLExpTransObj3DScale(rNew)); 856 } 857 858 void SdXMLImExTransform3D::AddTranslate(const ::basegfx::B3DTuple& rNew) 859 { 860 if(!rNew.equalZero()) 861 maList.push_back(new ImpSdXMLExpTransObj3DTranslate(rNew)); 862 } 863 864 void SdXMLImExTransform3D::AddMatrix(const ::basegfx::B3DHomMatrix& rNew) 865 { 866 if(!rNew.isIdentity()) 867 maList.push_back(new ImpSdXMLExpTransObj3DMatrix(rNew)); 868 } 869 870 void SdXMLImExTransform3D::AddHomogenMatrix(const drawing::HomogenMatrix& xHomMat) 871 { 872 ::basegfx::B3DHomMatrix aExportMatrix; 873 874 aExportMatrix.set(0, 0, xHomMat.Line1.Column1); 875 aExportMatrix.set(0, 1, xHomMat.Line1.Column2); 876 aExportMatrix.set(0, 2, xHomMat.Line1.Column3); 877 aExportMatrix.set(0, 3, xHomMat.Line1.Column4); 878 aExportMatrix.set(1, 0, xHomMat.Line2.Column1); 879 aExportMatrix.set(1, 1, xHomMat.Line2.Column2); 880 aExportMatrix.set(1, 2, xHomMat.Line2.Column3); 881 aExportMatrix.set(1, 3, xHomMat.Line2.Column4); 882 aExportMatrix.set(2, 0, xHomMat.Line3.Column1); 883 aExportMatrix.set(2, 1, xHomMat.Line3.Column2); 884 aExportMatrix.set(2, 2, xHomMat.Line3.Column3); 885 aExportMatrix.set(2, 3, xHomMat.Line3.Column4); 886 887 AddMatrix(aExportMatrix); 888 } 889 890 ////////////////////////////////////////////////////////////////////////////// 891 // gen string for export 892 const OUString& SdXMLImExTransform3D::GetExportString(const SvXMLUnitConverter& rConv) 893 { 894 OUString aNewString; 895 OUString aClosingBrace(sal_Unicode(')')); 896 OUString aEmptySpace(sal_Unicode(' ')); 897 898 const sal_uInt32 nCount = maList.size(); 899 for(sal_uInt32 a(0L); a < nCount; a++) 900 { 901 ImpSdXMLExpTransObj3DBase* pObj = maList[a]; 902 switch(pObj->mnType) 903 { 904 case IMP_SDXMLEXP_TRANSOBJ3D_ROTATE_X : 905 { 906 aNewString += OUString::createFromAscii("rotatex ("); 907 Imp_PutDoubleChar(aNewString, rConv, ((ImpSdXMLExpTransObj3DRotateX*)pObj)->mfRotateX); 908 aNewString += aClosingBrace; 909 break; 910 } 911 case IMP_SDXMLEXP_TRANSOBJ3D_ROTATE_Y : 912 { 913 aNewString += OUString::createFromAscii("rotatey ("); 914 Imp_PutDoubleChar(aNewString, rConv, ((ImpSdXMLExpTransObj3DRotateY*)pObj)->mfRotateY); 915 aNewString += aClosingBrace; 916 break; 917 } 918 case IMP_SDXMLEXP_TRANSOBJ3D_ROTATE_Z : 919 { 920 aNewString += OUString::createFromAscii("rotatez ("); 921 Imp_PutDoubleChar(aNewString, rConv, ((ImpSdXMLExpTransObj3DRotateZ*)pObj)->mfRotateZ); 922 aNewString += aClosingBrace; 923 break; 924 } 925 case IMP_SDXMLEXP_TRANSOBJ3D_SCALE : 926 { 927 aNewString += OUString::createFromAscii("scale ("); 928 Imp_PutDoubleChar(aNewString, rConv, ((ImpSdXMLExpTransObj3DScale*)pObj)->maScale.getX()); 929 aNewString += aEmptySpace; 930 Imp_PutDoubleChar(aNewString, rConv, ((ImpSdXMLExpTransObj3DScale*)pObj)->maScale.getY()); 931 aNewString += aEmptySpace; 932 Imp_PutDoubleChar(aNewString, rConv, ((ImpSdXMLExpTransObj3DScale*)pObj)->maScale.getZ()); 933 aNewString += aClosingBrace; 934 break; 935 } 936 case IMP_SDXMLEXP_TRANSOBJ3D_TRANSLATE : 937 { 938 aNewString += OUString::createFromAscii("translate ("); 939 Imp_PutDoubleChar(aNewString, rConv, ((ImpSdXMLExpTransObj3DTranslate*)pObj)->maTranslate.getX(), true); 940 aNewString += aEmptySpace; 941 Imp_PutDoubleChar(aNewString, rConv, ((ImpSdXMLExpTransObj3DTranslate*)pObj)->maTranslate.getY(), true); 942 aNewString += aEmptySpace; 943 Imp_PutDoubleChar(aNewString, rConv, ((ImpSdXMLExpTransObj3DTranslate*)pObj)->maTranslate.getZ(), true); 944 aNewString += aClosingBrace; 945 break; 946 } 947 case IMP_SDXMLEXP_TRANSOBJ3D_MATRIX : 948 { 949 aNewString += OUString::createFromAscii("matrix ("); 950 951 // a 952 Imp_PutDoubleChar(aNewString, rConv, ((ImpSdXMLExpTransObj3DMatrix*)pObj)->maMatrix.get(0, 0)); 953 aNewString += aEmptySpace; 954 955 // b 956 Imp_PutDoubleChar(aNewString, rConv, ((ImpSdXMLExpTransObj3DMatrix*)pObj)->maMatrix.get(1, 0)); 957 aNewString += aEmptySpace; 958 959 // c 960 Imp_PutDoubleChar(aNewString, rConv, ((ImpSdXMLExpTransObj3DMatrix*)pObj)->maMatrix.get(2, 0)); 961 aNewString += aEmptySpace; 962 963 // d 964 Imp_PutDoubleChar(aNewString, rConv, ((ImpSdXMLExpTransObj3DMatrix*)pObj)->maMatrix.get(0, 1)); 965 aNewString += aEmptySpace; 966 967 // e 968 Imp_PutDoubleChar(aNewString, rConv, ((ImpSdXMLExpTransObj3DMatrix*)pObj)->maMatrix.get(1, 1)); 969 aNewString += aEmptySpace; 970 971 // f 972 Imp_PutDoubleChar(aNewString, rConv, ((ImpSdXMLExpTransObj3DMatrix*)pObj)->maMatrix.get(2, 1)); 973 aNewString += aEmptySpace; 974 975 // g 976 Imp_PutDoubleChar(aNewString, rConv, ((ImpSdXMLExpTransObj3DMatrix*)pObj)->maMatrix.get(0, 2)); 977 aNewString += aEmptySpace; 978 979 // h 980 Imp_PutDoubleChar(aNewString, rConv, ((ImpSdXMLExpTransObj3DMatrix*)pObj)->maMatrix.get(1, 2)); 981 aNewString += aEmptySpace; 982 983 // i 984 Imp_PutDoubleChar(aNewString, rConv, ((ImpSdXMLExpTransObj3DMatrix*)pObj)->maMatrix.get(2, 2)); 985 aNewString += aEmptySpace; 986 987 // j 988 Imp_PutDoubleChar(aNewString, rConv, ((ImpSdXMLExpTransObj3DMatrix*)pObj)->maMatrix.get(0, 3), true); 989 aNewString += aEmptySpace; 990 991 // k 992 Imp_PutDoubleChar(aNewString, rConv, ((ImpSdXMLExpTransObj3DMatrix*)pObj)->maMatrix.get(1, 3), true); 993 aNewString += aEmptySpace; 994 995 // l 996 Imp_PutDoubleChar(aNewString, rConv, ((ImpSdXMLExpTransObj3DMatrix*)pObj)->maMatrix.get(2, 3), true); 997 998 aNewString += aClosingBrace; 999 break; 1000 } 1001 default : 1002 { 1003 DBG_ERROR("SdXMLImExTransform3D: impossible entry!"); 1004 break; 1005 } 1006 } 1007 1008 // if not the last entry, add one space to next tag 1009 if(a + 1UL != maList.size()) 1010 { 1011 aNewString += aEmptySpace; 1012 } 1013 } 1014 1015 // fill string form OUString 1016 msString = aNewString; 1017 1018 return msString; 1019 } 1020 1021 ////////////////////////////////////////////////////////////////////////////// 1022 // for Import: constructor with string, parses it and generates entries 1023 SdXMLImExTransform3D::SdXMLImExTransform3D(const OUString& rNew, const SvXMLUnitConverter& rConv) 1024 { 1025 SetString(rNew, rConv); 1026 } 1027 1028 ////////////////////////////////////////////////////////////////////////////// 1029 // sets new string, parses it and generates entries 1030 void SdXMLImExTransform3D::SetString(const OUString& rNew, const SvXMLUnitConverter& rConv) 1031 { 1032 msString = rNew; 1033 EmptyList(); 1034 1035 if(msString.getLength()) 1036 { 1037 const OUString aStr(msString.getStr(), (sal_uInt16)msString.getLength()); 1038 const sal_Int32 nLen(aStr.getLength()); 1039 1040 const OUString aString_rotatex(OUString::createFromAscii("rotatex")); 1041 const OUString aString_rotatey(OUString::createFromAscii("rotatey")); 1042 const OUString aString_rotatez(OUString::createFromAscii("rotatez")); 1043 const OUString aString_scale(OUString::createFromAscii("scale")); 1044 const OUString aString_translate(OUString::createFromAscii("translate")); 1045 const OUString aString_matrix(OUString::createFromAscii("matrix")); 1046 1047 sal_Int32 nPos(0); 1048 1049 while(nPos < nLen) 1050 { 1051 // skip spaces 1052 Imp_SkipSpaces(aStr, nPos, nLen); 1053 1054 // look for tag 1055 if(nPos < nLen) 1056 { 1057 if(nPos == aStr.indexOf(aString_rotatex, nPos)) 1058 { 1059 double fValue(0.0); 1060 1061 nPos += 7; 1062 Imp_SkipSpacesAndOpeningBraces(aStr, nPos, nLen); 1063 fValue = Imp_GetDoubleChar(aStr, nPos, nLen, rConv, fValue); 1064 if(fValue != 0.0) 1065 maList.push_back(new ImpSdXMLExpTransObj3DRotateX(fValue)); 1066 1067 Imp_SkipSpacesAndClosingBraces(aStr, nPos, nLen); 1068 } 1069 else if(nPos == aStr.indexOf(aString_rotatey, nPos)) 1070 { 1071 double fValue(0.0); 1072 1073 nPos += 7; 1074 Imp_SkipSpacesAndOpeningBraces(aStr, nPos, nLen); 1075 fValue = Imp_GetDoubleChar(aStr, nPos, nLen, rConv, fValue); 1076 if(fValue != 0.0) 1077 maList.push_back(new ImpSdXMLExpTransObj3DRotateY(fValue)); 1078 1079 Imp_SkipSpacesAndClosingBraces(aStr, nPos, nLen); 1080 } 1081 else if(nPos == aStr.indexOf(aString_rotatez, nPos)) 1082 { 1083 double fValue(0.0); 1084 1085 nPos += 7; 1086 Imp_SkipSpacesAndOpeningBraces(aStr, nPos, nLen); 1087 fValue = Imp_GetDoubleChar(aStr, nPos, nLen, rConv, fValue); 1088 if(fValue != 0.0) 1089 maList.push_back(new ImpSdXMLExpTransObj3DRotateZ(fValue)); 1090 1091 Imp_SkipSpacesAndClosingBraces(aStr, nPos, nLen); 1092 } 1093 else if(nPos == aStr.indexOf(aString_scale, nPos)) 1094 { 1095 ::basegfx::B3DTuple aValue(1.0, 1.0, 1.0); 1096 1097 nPos += 5; 1098 Imp_SkipSpacesAndOpeningBraces(aStr, nPos, nLen); 1099 aValue.setX(Imp_GetDoubleChar(aStr, nPos, nLen, rConv, aValue.getX())); 1100 Imp_SkipSpacesAndCommas(aStr, nPos, nLen); 1101 aValue.setY(Imp_GetDoubleChar(aStr, nPos, nLen, rConv, aValue.getY())); 1102 Imp_SkipSpacesAndCommas(aStr, nPos, nLen); 1103 aValue.setZ(Imp_GetDoubleChar(aStr, nPos, nLen, rConv, aValue.getZ())); 1104 1105 if(1.0 != aValue.getX() || 1.0 != aValue.getY() || 1.0 != aValue.getZ()) 1106 maList.push_back(new ImpSdXMLExpTransObj3DScale(aValue)); 1107 1108 Imp_SkipSpacesAndClosingBraces(aStr, nPos, nLen); 1109 } 1110 else if(nPos == aStr.indexOf(aString_translate, nPos)) 1111 { 1112 ::basegfx::B3DTuple aValue; 1113 1114 nPos += 9; 1115 Imp_SkipSpacesAndOpeningBraces(aStr, nPos, nLen); 1116 aValue.setX(Imp_GetDoubleChar(aStr, nPos, nLen, rConv, aValue.getX(), true)); 1117 Imp_SkipSpacesAndCommas(aStr, nPos, nLen); 1118 aValue.setY(Imp_GetDoubleChar(aStr, nPos, nLen, rConv, aValue.getY(), true)); 1119 Imp_SkipSpacesAndCommas(aStr, nPos, nLen); 1120 aValue.setZ(Imp_GetDoubleChar(aStr, nPos, nLen, rConv, aValue.getZ(), true)); 1121 1122 if(!aValue.equalZero()) 1123 maList.push_back(new ImpSdXMLExpTransObj3DTranslate(aValue)); 1124 1125 Imp_SkipSpacesAndClosingBraces(aStr, nPos, nLen); 1126 } 1127 else if(nPos == aStr.indexOf(aString_matrix, nPos)) 1128 { 1129 ::basegfx::B3DHomMatrix aValue; 1130 1131 nPos += 6; 1132 Imp_SkipSpacesAndOpeningBraces(aStr, nPos, nLen); 1133 1134 // a 1135 aValue.set(0, 0, Imp_GetDoubleChar(aStr, nPos, nLen, rConv, aValue.get(0, 0))); 1136 Imp_SkipSpacesAndCommas(aStr, nPos, nLen); 1137 1138 // b 1139 aValue.set(1, 0, Imp_GetDoubleChar(aStr, nPos, nLen, rConv, aValue.get(1, 0))); 1140 Imp_SkipSpacesAndCommas(aStr, nPos, nLen); 1141 1142 // c 1143 aValue.set(2, 0, Imp_GetDoubleChar(aStr, nPos, nLen, rConv, aValue.get(2, 0))); 1144 Imp_SkipSpacesAndCommas(aStr, nPos, nLen); 1145 1146 // d 1147 aValue.set(0, 1, Imp_GetDoubleChar(aStr, nPos, nLen, rConv, aValue.get(0, 1))); 1148 Imp_SkipSpacesAndCommas(aStr, nPos, nLen); 1149 1150 // e 1151 aValue.set(1, 1, Imp_GetDoubleChar(aStr, nPos, nLen, rConv, aValue.get(1, 1))); 1152 Imp_SkipSpacesAndCommas(aStr, nPos, nLen); 1153 1154 // f 1155 aValue.set(2, 1, Imp_GetDoubleChar(aStr, nPos, nLen, rConv, aValue.get(2, 1))); 1156 Imp_SkipSpacesAndCommas(aStr, nPos, nLen); 1157 1158 // g 1159 aValue.set(0, 2, Imp_GetDoubleChar(aStr, nPos, nLen, rConv, aValue.get(0, 2))); 1160 Imp_SkipSpacesAndCommas(aStr, nPos, nLen); 1161 1162 // h 1163 aValue.set(1, 2, Imp_GetDoubleChar(aStr, nPos, nLen, rConv, aValue.get(1, 2))); 1164 Imp_SkipSpacesAndCommas(aStr, nPos, nLen); 1165 1166 // i 1167 aValue.set(2, 2, Imp_GetDoubleChar(aStr, nPos, nLen, rConv, aValue.get(2, 2))); 1168 Imp_SkipSpacesAndCommas(aStr, nPos, nLen); 1169 1170 // j 1171 aValue.set(0, 3, Imp_GetDoubleChar(aStr, nPos, nLen, rConv, aValue.get(0, 3), true)); 1172 Imp_SkipSpacesAndCommas(aStr, nPos, nLen); 1173 1174 // k 1175 aValue.set(1, 3, Imp_GetDoubleChar(aStr, nPos, nLen, rConv, aValue.get(1, 3), true)); 1176 Imp_SkipSpacesAndCommas(aStr, nPos, nLen); 1177 1178 // l 1179 aValue.set(2, 3, Imp_GetDoubleChar(aStr, nPos, nLen, rConv, aValue.get(2, 3), true)); 1180 Imp_SkipSpacesAndCommas(aStr, nPos, nLen); 1181 1182 if(!aValue.isIdentity()) 1183 maList.push_back(new ImpSdXMLExpTransObj3DMatrix(aValue)); 1184 1185 Imp_SkipSpacesAndClosingBraces(aStr, nPos, nLen); 1186 } 1187 else 1188 { 1189 nPos++; 1190 } 1191 } 1192 } 1193 } 1194 } 1195 1196 bool SdXMLImExTransform3D::GetFullHomogenTransform(com::sun::star::drawing::HomogenMatrix& xHomMat) 1197 { 1198 ::basegfx::B3DHomMatrix aFullTransform; 1199 GetFullTransform(aFullTransform); 1200 1201 if(!aFullTransform.isIdentity()) 1202 { 1203 xHomMat.Line1.Column1 = aFullTransform.get(0, 0); 1204 xHomMat.Line1.Column2 = aFullTransform.get(0, 1); 1205 xHomMat.Line1.Column3 = aFullTransform.get(0, 2); 1206 xHomMat.Line1.Column4 = aFullTransform.get(0, 3); 1207 1208 xHomMat.Line2.Column1 = aFullTransform.get(1, 0); 1209 xHomMat.Line2.Column2 = aFullTransform.get(1, 1); 1210 xHomMat.Line2.Column3 = aFullTransform.get(1, 2); 1211 xHomMat.Line2.Column4 = aFullTransform.get(1, 3); 1212 1213 xHomMat.Line3.Column1 = aFullTransform.get(2, 0); 1214 xHomMat.Line3.Column2 = aFullTransform.get(2, 1); 1215 xHomMat.Line3.Column3 = aFullTransform.get(2, 2); 1216 xHomMat.Line3.Column4 = aFullTransform.get(2, 3); 1217 1218 xHomMat.Line4.Column1 = aFullTransform.get(3, 0); 1219 xHomMat.Line4.Column2 = aFullTransform.get(3, 1); 1220 xHomMat.Line4.Column3 = aFullTransform.get(3, 2); 1221 xHomMat.Line4.Column4 = aFullTransform.get(3, 3); 1222 1223 return true; 1224 } 1225 1226 return false; 1227 } 1228 1229 void SdXMLImExTransform3D::GetFullTransform(::basegfx::B3DHomMatrix& rFullTrans) 1230 { 1231 rFullTrans.identity(); 1232 1233 const sal_uInt32 nCount = maList.size(); 1234 for(sal_uInt32 a(0L); a < nCount; a++) 1235 { 1236 ImpSdXMLExpTransObj3DBase* pObj = maList[a]; 1237 switch(pObj->mnType) 1238 { 1239 case IMP_SDXMLEXP_TRANSOBJ3D_ROTATE_X : 1240 { 1241 rFullTrans.rotate(((ImpSdXMLExpTransObj3DRotateX*)pObj)->mfRotateX, 0.0, 0.0); 1242 break; 1243 } 1244 case IMP_SDXMLEXP_TRANSOBJ3D_ROTATE_Y : 1245 { 1246 rFullTrans.rotate(0.0, ((ImpSdXMLExpTransObj3DRotateY*)pObj)->mfRotateY, 0.0); 1247 break; 1248 } 1249 case IMP_SDXMLEXP_TRANSOBJ3D_ROTATE_Z : 1250 { 1251 rFullTrans.rotate(0.0, 0.0, ((ImpSdXMLExpTransObj3DRotateZ*)pObj)->mfRotateZ); 1252 break; 1253 } 1254 case IMP_SDXMLEXP_TRANSOBJ3D_SCALE : 1255 { 1256 const ::basegfx::B3DTuple& rScale = ((ImpSdXMLExpTransObj3DScale*)pObj)->maScale; 1257 rFullTrans.scale(rScale.getX(), rScale.getY(), rScale.getZ()); 1258 break; 1259 } 1260 case IMP_SDXMLEXP_TRANSOBJ3D_TRANSLATE : 1261 { 1262 const ::basegfx::B3DTuple& rTranslate = ((ImpSdXMLExpTransObj3DTranslate*)pObj)->maTranslate; 1263 rFullTrans.translate(rTranslate.getX(), rTranslate.getY(), rTranslate.getZ()); 1264 break; 1265 } 1266 case IMP_SDXMLEXP_TRANSOBJ3D_MATRIX : 1267 { 1268 rFullTrans *= ((ImpSdXMLExpTransObj3DMatrix*)pObj)->maMatrix; 1269 break; 1270 } 1271 default : 1272 { 1273 DBG_ERROR("SdXMLImExTransform3D: impossible entry!"); 1274 break; 1275 } 1276 } 1277 } 1278 } 1279 1280 ////////////////////////////////////////////////////////////////////////////// 1281 ////////////////////////////////////////////////////////////////////////////// 1282 1283 SdXMLImExViewBox::SdXMLImExViewBox(double fX, double fY, double fW, double fH) 1284 : mfX( fX ), 1285 mfY( fY ), 1286 mfW( fW ), 1287 mfH( fH ) 1288 { 1289 } 1290 1291 // #100617# Asked vincent hardy: svg:viewBox values may be double precision. 1292 SdXMLImExViewBox::SdXMLImExViewBox(const OUString& rNew, const SvXMLUnitConverter& rConv) 1293 : msString(rNew), 1294 mfX( 0.0 ), 1295 mfY( 0.0 ), 1296 mfW( 1000.0 ), 1297 mfH( 1000.0 ) 1298 { 1299 if(msString.getLength()) 1300 { 1301 const OUString aStr(msString.getStr(), (sal_uInt16)msString.getLength()); 1302 const sal_Int32 nLen(aStr.getLength()); 1303 sal_Int32 nPos(0); 1304 1305 // skip starting spaces 1306 Imp_SkipSpaces(aStr, nPos, nLen); 1307 1308 // get mX, #100617# be prepared for doubles 1309 mfX = Imp_GetDoubleChar(aStr, nPos, nLen, rConv, mfX); 1310 1311 // skip spaces and commas 1312 Imp_SkipSpacesAndCommas(aStr, nPos, nLen); 1313 1314 // get mY, #100617# be prepared for doubles 1315 mfY = Imp_GetDoubleChar(aStr, nPos, nLen, rConv, mfY); 1316 1317 // skip spaces and commas 1318 Imp_SkipSpacesAndCommas(aStr, nPos, nLen); 1319 1320 // get mW, #100617# be prepared for doubles 1321 mfW = Imp_GetDoubleChar(aStr, nPos, nLen, rConv, mfW); 1322 1323 // skip spaces and commas 1324 Imp_SkipSpacesAndCommas(aStr, nPos, nLen); 1325 1326 // get mH, #100617# be prepared for doubles 1327 mfH = Imp_GetDoubleChar(aStr, nPos, nLen, rConv, mfH); 1328 } 1329 } 1330 1331 const OUString& SdXMLImExViewBox::GetExportString() 1332 { 1333 OUString aNewString; 1334 OUString aEmptySpace(sal_Unicode(' ')); 1335 1336 Imp_PutDoubleChar(aNewString, mfX); 1337 aNewString += aEmptySpace; 1338 1339 Imp_PutDoubleChar(aNewString, mfY); 1340 aNewString += aEmptySpace; 1341 1342 Imp_PutDoubleChar(aNewString, mfW); 1343 aNewString += aEmptySpace; 1344 1345 Imp_PutDoubleChar(aNewString, mfH); 1346 1347 // set new string 1348 msString = aNewString; 1349 1350 return msString; 1351 } 1352 1353 // eof 1354