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 // MARKER(update_precomp.py): autogen include statement, do not remove 23 #include "precompiled_svx.hxx" 24 25 #include <svx/svdorect.hxx> 26 #include <math.h> 27 #include <stdlib.h> 28 #include <svx/xpool.hxx> 29 #include <svx/xpoly.hxx> 30 #include <svx/svdattr.hxx> 31 #include <svx/svdpool.hxx> 32 #include <svx/svdtrans.hxx> 33 #include <svx/svdetc.hxx> 34 #include <svx/svddrag.hxx> 35 #include <svx/svdmodel.hxx> 36 #include <svx/svdpage.hxx> 37 #include <svx/svdocapt.hxx> // für Import von SdrFileVersion 2 38 #include <svx/svdpagv.hxx> // für 39 #include <svx/svdview.hxx> // das 40 #include <svx/svdundo.hxx> // Macro-Beispiel 41 #include <svx/svdopath.hxx> 42 #include "svx/svdglob.hxx" // Stringcache 43 #include "svx/svdstr.hrc" // Objektname 44 #include <svx/xflclit.hxx> 45 #include <svx/xlnclit.hxx> 46 #include <svx/xlnwtit.hxx> 47 #include "svdoimp.hxx" 48 #include <svx/sdr/properties/rectangleproperties.hxx> 49 #include <svx/sdr/contact/viewcontactofsdrrectobj.hxx> 50 #include <basegfx/polygon/b2dpolygon.hxx> 51 #include <basegfx/polygon/b2dpolygontools.hxx> 52 53 ////////////////////////////////////////////////////////////////////////////// 54 // BaseProperties section 55 56 sdr::properties::BaseProperties* SdrRectObj::CreateObjectSpecificProperties() 57 { 58 return new sdr::properties::RectangleProperties(*this); 59 } 60 61 ////////////////////////////////////////////////////////////////////////////// 62 // DrawContact section 63 64 sdr::contact::ViewContact* SdrRectObj::CreateObjectSpecificViewContact() 65 { 66 return new sdr::contact::ViewContactOfSdrRectObj(*this); 67 } 68 69 ////////////////////////////////////////////////////////////////////////////// 70 71 TYPEINIT1(SdrRectObj,SdrTextObj); 72 73 SdrRectObj::SdrRectObj() 74 : mpXPoly(0L) 75 { 76 bClosedObj=sal_True; 77 } 78 79 SdrRectObj::SdrRectObj(const Rectangle& rRect) 80 : SdrTextObj(rRect), 81 mpXPoly(NULL) 82 { 83 bClosedObj=sal_True; 84 } 85 86 SdrRectObj::SdrRectObj(SdrObjKind eNewTextKind) 87 : SdrTextObj(eNewTextKind), 88 mpXPoly(NULL) 89 { 90 DBG_ASSERT(eTextKind==OBJ_TEXT || eTextKind==OBJ_TEXTEXT || 91 eTextKind==OBJ_OUTLINETEXT || eTextKind==OBJ_TITLETEXT, 92 "SdrRectObj::SdrRectObj(SdrObjKind) ist nur für Textrahmen gedacht"); 93 bClosedObj=sal_True; 94 } 95 96 SdrRectObj::SdrRectObj(SdrObjKind eNewTextKind, const Rectangle& rRect) 97 : SdrTextObj(eNewTextKind,rRect), 98 mpXPoly(NULL) 99 { 100 DBG_ASSERT(eTextKind==OBJ_TEXT || eTextKind==OBJ_TEXTEXT || 101 eTextKind==OBJ_OUTLINETEXT || eTextKind==OBJ_TITLETEXT, 102 "SdrRectObj::SdrRectObj(SdrObjKind,...) ist nur für Textrahmen gedacht"); 103 bClosedObj=sal_True; 104 } 105 106 SdrRectObj::SdrRectObj(SdrObjKind eNewTextKind, const Rectangle& rNewRect, SvStream& rInput, const String& rBaseURL, sal_uInt16 eFormat) 107 : SdrTextObj(eNewTextKind,rNewRect,rInput,rBaseURL,eFormat), 108 mpXPoly(NULL) 109 { 110 DBG_ASSERT(eTextKind==OBJ_TEXT || eTextKind==OBJ_TEXTEXT || 111 eTextKind==OBJ_OUTLINETEXT || eTextKind==OBJ_TITLETEXT, 112 "SdrRectObj::SdrRectObj(SdrObjKind,...) ist nur für Textrahmen gedacht"); 113 bClosedObj=sal_True; 114 } 115 116 SdrRectObj::~SdrRectObj() 117 { 118 if(mpXPoly) 119 { 120 delete mpXPoly; 121 } 122 } 123 124 void SdrRectObj::SetXPolyDirty() 125 { 126 if(mpXPoly) 127 { 128 delete mpXPoly; 129 mpXPoly = 0L; 130 } 131 } 132 133 FASTBOOL SdrRectObj::PaintNeedsXPoly(long nEckRad) const 134 { 135 FASTBOOL bNeed=aGeo.nDrehWink!=0 || aGeo.nShearWink!=0 || nEckRad!=0; 136 return bNeed; 137 } 138 139 XPolygon SdrRectObj::ImpCalcXPoly(const Rectangle& rRect1, long nRad1) const 140 { 141 XPolygon aXPoly(rRect1,nRad1,nRad1); 142 const sal_uInt16 nPointCount(aXPoly.GetPointCount()); 143 XPolygon aNewPoly(nPointCount+1); 144 sal_uInt16 nShift=nPointCount-2; 145 if (nRad1!=0) nShift=nPointCount-5; 146 sal_uInt16 j=nShift; 147 for (sal_uInt16 i=1; i<nPointCount; i++) { 148 aNewPoly[i]=aXPoly[j]; 149 aNewPoly.SetFlags(i,aXPoly.GetFlags(j)); 150 j++; 151 if (j>=nPointCount) j=1; 152 } 153 aNewPoly[0]=rRect1.BottomCenter(); 154 aNewPoly[nPointCount]=aNewPoly[0]; 155 aXPoly=aNewPoly; 156 157 // Die Winkelangaben beziehen sich immer auf die linke obere Ecke von !aRect! 158 if (aGeo.nShearWink!=0) ShearXPoly(aXPoly,aRect.TopLeft(),aGeo.nTan); 159 if (aGeo.nDrehWink!=0) RotateXPoly(aXPoly,aRect.TopLeft(),aGeo.nSin,aGeo.nCos); 160 return aXPoly; 161 } 162 163 void SdrRectObj::RecalcXPoly() 164 { 165 mpXPoly = new XPolygon(ImpCalcXPoly(aRect,GetEckenradius())); 166 } 167 168 const XPolygon& SdrRectObj::GetXPoly() const 169 { 170 if(!mpXPoly) 171 { 172 ((SdrRectObj*)this)->RecalcXPoly(); 173 } 174 175 return *mpXPoly; 176 } 177 178 void SdrRectObj::TakeObjInfo(SdrObjTransformInfoRec& rInfo) const 179 { 180 FASTBOOL bNoTextFrame=!IsTextFrame(); 181 rInfo.bResizeFreeAllowed=bNoTextFrame || aGeo.nDrehWink%9000==0; 182 rInfo.bResizePropAllowed=sal_True; 183 rInfo.bRotateFreeAllowed=sal_True; 184 rInfo.bRotate90Allowed =sal_True; 185 rInfo.bMirrorFreeAllowed=bNoTextFrame; 186 rInfo.bMirror45Allowed =bNoTextFrame; 187 rInfo.bMirror90Allowed =bNoTextFrame; 188 189 // allow transparence 190 rInfo.bTransparenceAllowed = sal_True; 191 192 // gradient depends on fillstyle 193 XFillStyle eFillStyle = ((XFillStyleItem&)(GetObjectItem(XATTR_FILLSTYLE))).GetValue(); 194 rInfo.bGradientAllowed = (eFillStyle == XFILL_GRADIENT); 195 196 rInfo.bShearAllowed =bNoTextFrame; 197 rInfo.bEdgeRadiusAllowed=sal_True; 198 199 FASTBOOL bCanConv=!HasText() || ImpCanConvTextToCurve(); 200 if (bCanConv && !bNoTextFrame && !HasText()) { 201 bCanConv=HasFill() || HasLine(); 202 } 203 rInfo.bCanConvToPath =bCanConv; 204 rInfo.bCanConvToPoly =bCanConv; 205 rInfo.bCanConvToContour = (rInfo.bCanConvToPoly || LineGeometryUsageIsNecessary()); 206 } 207 208 sal_uInt16 SdrRectObj::GetObjIdentifier() const 209 { 210 if (IsTextFrame()) return sal_uInt16(eTextKind); 211 else return sal_uInt16(OBJ_RECT); 212 } 213 214 void SdrRectObj::TakeUnrotatedSnapRect(Rectangle& rRect) const 215 { 216 rRect=aRect; 217 if (aGeo.nShearWink!=0) { 218 long nDst=Round((aRect.Bottom()-aRect.Top())*aGeo.nTan); 219 if (aGeo.nShearWink>0) { 220 Point aRef(rRect.TopLeft()); 221 rRect.Left()-=nDst; 222 Point aTmpPt(rRect.TopLeft()); 223 RotatePoint(aTmpPt,aRef,aGeo.nSin,aGeo.nCos); 224 aTmpPt-=rRect.TopLeft(); 225 rRect.Move(aTmpPt.X(),aTmpPt.Y()); 226 } else { 227 rRect.Right()-=nDst; 228 } 229 } 230 } 231 232 void SdrRectObj::TakeObjNameSingul(XubString& rName) const 233 { 234 if (IsTextFrame()) 235 { 236 SdrTextObj::TakeObjNameSingul(rName); 237 } 238 else 239 { 240 sal_uInt16 nResId=STR_ObjNameSingulRECT; 241 if (aGeo.nShearWink!=0) { 242 nResId+=4; // Parallelogramm oder Raute 243 // Raute ist nicht, weil Shear die vertikalen Kanten verlängert! 244 // Wenn Zeit ist, werde ich das mal berechnen. 245 } else { 246 if (aRect.GetWidth()==aRect.GetHeight()) nResId+=2; // Quadrat 247 } 248 if (GetEckenradius()!=0) nResId+=8; // abgerundet 249 rName=ImpGetResStr(nResId); 250 251 String aName( GetName() ); 252 if(aName.Len()) 253 { 254 rName += sal_Unicode(' '); 255 rName += sal_Unicode('\''); 256 rName += aName; 257 rName += sal_Unicode('\''); 258 } 259 } 260 } 261 262 void SdrRectObj::TakeObjNamePlural(XubString& rName) const 263 { 264 if (IsTextFrame()) SdrTextObj::TakeObjNamePlural(rName); 265 else { 266 sal_uInt16 nResId=STR_ObjNamePluralRECT; 267 if (aGeo.nShearWink!=0) { 268 nResId+=4; // Parallelogramm oder Raute 269 } else { 270 if (aRect.GetWidth()==aRect.GetHeight()) nResId+=2; // Quadrat 271 } 272 if (GetEckenradius()!=0) nResId+=8; // abgerundet 273 rName=ImpGetResStr(nResId); 274 } 275 } 276 277 void SdrRectObj::operator=(const SdrObject& rObj) 278 { 279 SdrTextObj::operator=(rObj); 280 } 281 282 basegfx::B2DPolyPolygon SdrRectObj::TakeXorPoly() const 283 { 284 XPolyPolygon aXPP; 285 aXPP.Insert(ImpCalcXPoly(aRect,GetEckenradius())); 286 return aXPP.getB2DPolyPolygon(); 287 } 288 289 void SdrRectObj::RecalcSnapRect() 290 { 291 long nEckRad=GetEckenradius(); 292 if ((aGeo.nDrehWink!=0 || aGeo.nShearWink!=0) && nEckRad!=0) { 293 maSnapRect=GetXPoly().GetBoundRect(); 294 } else { 295 SdrTextObj::RecalcSnapRect(); 296 } 297 } 298 299 void SdrRectObj::NbcSetSnapRect(const Rectangle& rRect) 300 { 301 SdrTextObj::NbcSetSnapRect(rRect); 302 SetXPolyDirty(); 303 } 304 305 void SdrRectObj::NbcSetLogicRect(const Rectangle& rRect) 306 { 307 SdrTextObj::NbcSetLogicRect(rRect); 308 SetXPolyDirty(); 309 } 310 311 sal_uInt32 SdrRectObj::GetHdlCount() const 312 { 313 return IsTextFrame() ? 10 : 9; 314 } 315 316 SdrHdl* SdrRectObj::GetHdl(sal_uInt32 nHdlNum) const 317 { 318 SdrHdl* pH = NULL; 319 Point aPnt; 320 SdrHdlKind eKind = HDL_MOVE; 321 322 if(!IsTextFrame()) 323 { 324 nHdlNum++; 325 } 326 327 switch(nHdlNum) 328 { 329 case 0: 330 { 331 OSL_ENSURE(!IsTextEditActive(), "Do not use a ImpTextframeHdl for hilighting text in active text edit, this will collide with EditEngine paints (!)"); 332 pH = new ImpTextframeHdl(aRect); 333 pH->SetObj((SdrObject*)this); 334 pH->SetDrehWink(aGeo.nDrehWink); 335 break; 336 } 337 case 1: 338 { 339 long a = GetEckenradius(); 340 long b = Max(aRect.GetWidth(),aRect.GetHeight())/2; // Wird aufgerundet, da GetWidth() eins draufaddiert 341 if (a>b) a=b; 342 if (a<0) a=0; 343 aPnt=aRect.TopLeft(); 344 aPnt.X()+=a; 345 eKind = HDL_CIRC; 346 break; 347 } 348 case 2: aPnt=aRect.TopLeft(); eKind = HDL_UPLFT; break; // Oben links 349 case 3: aPnt=aRect.TopCenter(); eKind = HDL_UPPER; break; // Oben 350 case 4: aPnt=aRect.TopRight(); eKind = HDL_UPRGT; break; // Oben rechts 351 case 5: aPnt=aRect.LeftCenter(); eKind = HDL_LEFT ; break; // Left 352 case 6: aPnt=aRect.RightCenter(); eKind = HDL_RIGHT; break; // Right 353 case 7: aPnt=aRect.BottomLeft(); eKind = HDL_LWLFT; break; // Unten links 354 case 8: aPnt=aRect.BottomCenter(); eKind = HDL_LOWER; break; // Unten 355 case 9: aPnt=aRect.BottomRight(); eKind = HDL_LWRGT; break; // Unten rechts 356 } 357 358 if(!pH) 359 { 360 if(aGeo.nShearWink) 361 { 362 ShearPoint(aPnt,aRect.TopLeft(),aGeo.nTan); 363 } 364 365 if(aGeo.nDrehWink) 366 { 367 RotatePoint(aPnt,aRect.TopLeft(),aGeo.nSin,aGeo.nCos); 368 } 369 370 pH = new SdrHdl(aPnt,eKind); 371 pH->SetObj((SdrObject*)this); 372 pH->SetDrehWink(aGeo.nDrehWink); 373 } 374 375 return pH; 376 } 377 378 //////////////////////////////////////////////////////////////////////////////////////////////////// 379 380 bool SdrRectObj::hasSpecialDrag() const 381 { 382 return true; 383 } 384 385 bool SdrRectObj::beginSpecialDrag(SdrDragStat& rDrag) const 386 { 387 const bool bRad(rDrag.GetHdl() && HDL_CIRC == rDrag.GetHdl()->GetKind()); 388 389 if(bRad) 390 { 391 rDrag.SetEndDragChangesAttributes(true); 392 393 return true; 394 } 395 396 return SdrTextObj::beginSpecialDrag(rDrag); 397 } 398 399 bool SdrRectObj::applySpecialDrag(SdrDragStat& rDrag) 400 { 401 const bool bRad(rDrag.GetHdl() && HDL_CIRC == rDrag.GetHdl()->GetKind()); 402 403 if (bRad) 404 { 405 Rectangle aBoundRect0; 406 Point aPt(rDrag.GetNow()); 407 408 if(aGeo.nDrehWink) 409 RotatePoint(aPt,aRect.TopLeft(),-aGeo.nSin,aGeo.nCos); 410 411 sal_Int32 nRad(aPt.X() - aRect.Left()); 412 413 if (nRad < 0) 414 nRad = 0; 415 416 if(nRad != GetEckenradius()) 417 { 418 NbcSetEckenradius(nRad); 419 } 420 421 return true; 422 } 423 else 424 { 425 return SdrTextObj::applySpecialDrag(rDrag); 426 } 427 } 428 429 String SdrRectObj::getSpecialDragComment(const SdrDragStat& rDrag) const 430 { 431 const bool bCreateComment(rDrag.GetView() && this == rDrag.GetView()->GetCreateObj()); 432 433 if(bCreateComment) 434 { 435 return String(); 436 } 437 else 438 { 439 const bool bRad(rDrag.GetHdl() && HDL_CIRC == rDrag.GetHdl()->GetKind()); 440 441 if(bRad) 442 { 443 Point aPt(rDrag.GetNow()); 444 445 // -sin für Umkehrung 446 if(aGeo.nDrehWink) 447 RotatePoint(aPt, aRect.TopLeft(), -aGeo.nSin, aGeo.nCos); 448 449 sal_Int32 nRad(aPt.X() - aRect.Left()); 450 451 if(nRad < 0) 452 nRad = 0; 453 454 XubString aStr; 455 456 ImpTakeDescriptionStr(STR_DragRectEckRad, aStr); 457 aStr.AppendAscii(" ("); 458 aStr += GetMetrStr(nRad); 459 aStr += sal_Unicode(')'); 460 461 return aStr; 462 } 463 else 464 { 465 return SdrTextObj::getSpecialDragComment(rDrag); 466 } 467 } 468 } 469 470 //////////////////////////////////////////////////////////////////////////////////////////////////// 471 472 basegfx::B2DPolyPolygon SdrRectObj::TakeCreatePoly(const SdrDragStat& rDrag) const 473 { 474 Rectangle aRect1; 475 rDrag.TakeCreateRect(aRect1); 476 aRect1.Justify(); 477 478 basegfx::B2DPolyPolygon aRetval; 479 aRetval.append(ImpCalcXPoly(aRect1,GetEckenradius()).getB2DPolygon()); 480 return aRetval; 481 } 482 483 Pointer SdrRectObj::GetCreatePointer() const 484 { 485 if (IsTextFrame()) return Pointer(POINTER_DRAW_TEXT); 486 return Pointer(POINTER_DRAW_RECT); 487 } 488 489 void SdrRectObj::NbcMove(const Size& rSiz) 490 { 491 SdrTextObj::NbcMove(rSiz); 492 SetXPolyDirty(); 493 } 494 495 void SdrRectObj::NbcResize(const Point& rRef, const Fraction& xFact, const Fraction& yFact) 496 { 497 SdrTextObj::NbcResize(rRef,xFact,yFact); 498 SetXPolyDirty(); 499 } 500 501 void SdrRectObj::NbcRotate(const Point& rRef, long nWink, double sn, double cs) 502 { 503 SdrTextObj::NbcRotate(rRef,nWink,sn,cs); 504 SetXPolyDirty(); 505 } 506 507 void SdrRectObj::NbcShear(const Point& rRef, long nWink, double tn, FASTBOOL bVShear) 508 { 509 SdrTextObj::NbcShear(rRef,nWink,tn,bVShear); 510 SetXPolyDirty(); 511 } 512 513 void SdrRectObj::NbcMirror(const Point& rRef1, const Point& rRef2) 514 { 515 SdrTextObj::NbcMirror(rRef1,rRef2); 516 SetXPolyDirty(); 517 } 518 519 FASTBOOL SdrRectObj::DoMacro(const SdrObjMacroHitRec& rRec) 520 { 521 return SdrTextObj::DoMacro(rRec); 522 } 523 524 XubString SdrRectObj::GetMacroPopupComment(const SdrObjMacroHitRec& rRec) const 525 { 526 return SdrTextObj::GetMacroPopupComment(rRec); 527 } 528 529 SdrGluePoint SdrRectObj::GetVertexGluePoint(sal_uInt16 nPosNum) const 530 { 531 sal_Int32 nWdt = ImpGetLineWdt(); // #i25616# ((XLineWidthItem&)(GetObjectItem(XATTR_LINEWIDTH))).GetValue(); 532 533 // #i25616# 534 if(!LineIsOutsideGeometry()) 535 { 536 nWdt++; 537 nWdt /= 2; 538 } 539 540 Point aPt; 541 switch (nPosNum) { 542 case 0: aPt=aRect.TopCenter(); aPt.Y()-=nWdt; break; 543 case 1: aPt=aRect.RightCenter(); aPt.X()+=nWdt; break; 544 case 2: aPt=aRect.BottomCenter(); aPt.Y()+=nWdt; break; 545 case 3: aPt=aRect.LeftCenter(); aPt.X()-=nWdt; break; 546 } 547 if (aGeo.nShearWink!=0) ShearPoint(aPt,aRect.TopLeft(),aGeo.nTan); 548 if (aGeo.nDrehWink!=0) RotatePoint(aPt,aRect.TopLeft(),aGeo.nSin,aGeo.nCos); 549 aPt-=GetSnapRect().Center(); 550 SdrGluePoint aGP(aPt); 551 aGP.SetPercent(sal_False); 552 return aGP; 553 } 554 555 SdrGluePoint SdrRectObj::GetCornerGluePoint(sal_uInt16 nPosNum) const 556 { 557 sal_Int32 nWdt = ImpGetLineWdt(); // #i25616# ((XLineWidthItem&)(GetObjectItem(XATTR_LINEWIDTH))).GetValue(); 558 559 // #i25616# 560 if(!LineIsOutsideGeometry()) 561 { 562 nWdt++; 563 nWdt /= 2; 564 } 565 566 Point aPt; 567 switch (nPosNum) { 568 case 0: aPt=aRect.TopLeft(); aPt.X()-=nWdt; aPt.Y()-=nWdt; break; 569 case 1: aPt=aRect.TopRight(); aPt.X()+=nWdt; aPt.Y()-=nWdt; break; 570 case 2: aPt=aRect.BottomRight(); aPt.X()+=nWdt; aPt.Y()+=nWdt; break; 571 case 3: aPt=aRect.BottomLeft(); aPt.X()-=nWdt; aPt.Y()+=nWdt; break; 572 } 573 if (aGeo.nShearWink!=0) ShearPoint(aPt,aRect.TopLeft(),aGeo.nTan); 574 if (aGeo.nDrehWink!=0) RotatePoint(aPt,aRect.TopLeft(),aGeo.nSin,aGeo.nCos); 575 aPt-=GetSnapRect().Center(); 576 SdrGluePoint aGP(aPt); 577 aGP.SetPercent(sal_False); 578 return aGP; 579 } 580 581 SdrObject* SdrRectObj::DoConvertToPolyObj(sal_Bool bBezier, bool bAddText) const 582 { 583 XPolygon aXP(ImpCalcXPoly(aRect,GetEckenradius())); 584 { // #40608# Nur übergangsweise bis zum neuen TakeContour() 585 aXP.Remove(0,1); 586 aXP[aXP.GetPointCount()-1]=aXP[0]; 587 } 588 589 basegfx::B2DPolyPolygon aPolyPolygon(aXP.getB2DPolygon()); 590 aPolyPolygon.removeDoublePoints(); 591 SdrObject* pRet = 0L; 592 593 // small correction: Do not create something when no fill and no line. To 594 // be sure to not damage something with non-text frames, do this only 595 // when used with bAddText==false from other converters 596 if((bAddText && !IsTextFrame()) || HasFill() || HasLine()) 597 { 598 pRet = ImpConvertMakeObj(aPolyPolygon, sal_True, bBezier); 599 } 600 601 if(bAddText) 602 { 603 pRet = ImpConvertAddText(pRet, bBezier); 604 } 605 606 return pRet; 607 } 608 609 void SdrRectObj::Notify(SfxBroadcaster& rBC, const SfxHint& rHint) 610 { 611 SdrTextObj::Notify(rBC,rHint); 612 SetXPolyDirty(); // wg. Eckenradius 613 } 614 615 void SdrRectObj::RestGeoData(const SdrObjGeoData& rGeo) 616 { 617 SdrTextObj::RestGeoData(rGeo); 618 SetXPolyDirty(); 619 } 620 621 /* vim: set noet sw=4 ts=4: */ 622