xref: /trunk/main/svx/source/svdraw/svdpoev.cxx (revision 67f7bfb15893aaa2f3b1ee7ec6b966aaaad422fc)
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/svdpoev.hxx>
26 #include <math.h>
27 #include <svx/svdpagv.hxx>
28 #include <svx/svdpage.hxx>
29 #include <svx/svdopath.hxx>
30 #include <svx/svdundo.hxx>
31 #include "svx/svdstr.hrc" // Names from resource
32 #include "svx/svdglob.hxx" // StringCache
33 #include <svx/svdtrans.hxx>
34 #include <basegfx/polygon/b2dpolygon.hxx>
35 #include <basegfx/polygon/b2dpolygontools.hxx>
36 #include <vcl/salbtype.hxx> // FRound
37 
38 #include <svx/polypolygoneditor.hxx>
39 
40 using namespace sdr;
41 
42 ////////////////////////////////////////////////////////////////////////////////////////////////////
43 
44 void SdrPolyEditView::ImpResetPolyPossibilityFlags()
45 {
46     eMarkedPointsSmooth=SDRPATHSMOOTH_DONTCARE;
47     eMarkedSegmentsKind=SDRPATHSEGMENT_DONTCARE;
48     bSetMarkedPointsSmoothPossible=sal_False;
49     bSetMarkedSegmentsKindPossible=sal_False;
50 }
51 
52 void SdrPolyEditView::ImpClearVars()
53 {
54     ImpResetPolyPossibilityFlags();
55 }
56 
57 SdrPolyEditView::SdrPolyEditView(SdrModel* pModel1, OutputDevice* pOut):
58     SdrEditView(pModel1,pOut)
59 {
60     ImpClearVars();
61 }
62 
63 SdrPolyEditView::~SdrPolyEditView()
64 {
65 }
66 
67 void SdrPolyEditView::ImpCheckPolyPossibilities()
68 {
69     ImpResetPolyPossibilityFlags();
70     const sal_uIntPtr nMarkAnz(GetMarkedObjectCount());
71 
72     if(nMarkAnz && !ImpIsFrameHandles())
73     {
74         bool b1stSmooth(true);
75         bool b1stSegm(true);
76         bool bCurve(false);
77         bool bSmoothFuz(false);
78         bool bSegmFuz(false);
79         basegfx::B2VectorContinuity eSmooth = basegfx::CONTINUITY_NONE;
80 
81         for(sal_uIntPtr nMarkNum(0L); nMarkNum < nMarkAnz; nMarkNum++)
82         {
83             SdrMark* pM = GetSdrMarkByIndex(nMarkNum);
84             CheckPolyPossibilitiesHelper( pM, b1stSmooth, b1stSegm, bCurve, bSmoothFuz, bSegmFuz, eSmooth );
85         }
86     }
87 }
88 
89 void SdrPolyEditView::CheckPolyPossibilitiesHelper( SdrMark* pM, bool& b1stSmooth, bool& b1stSegm, bool& bCurve, bool& bSmoothFuz, bool& bSegmFuz, basegfx::B2VectorContinuity& eSmooth )
90 {
91     SdrObject* pObj = pM->GetMarkedSdrObj();
92     SdrUShortCont* pPts = pM->GetMarkedPoints();
93     SdrPathObj* pPath = PTR_CAST(SdrPathObj,pObj);
94 
95     if(pPath && pPts)
96     {
97         const sal_uInt32 nMarkedPntAnz(pPts->GetCount());
98 
99         if(nMarkedPntAnz)
100         {
101             bool bClosed(pPath->IsClosed());
102             bSetMarkedPointsSmoothPossible = true;
103 
104             if(bClosed)
105             {
106                 bSetMarkedSegmentsKindPossible = true;
107             }
108 
109             for(sal_uInt32 nMarkedPntNum(0L); nMarkedPntNum < nMarkedPntAnz; nMarkedPntNum++)
110             {
111                 sal_uInt32 nNum(pPts->GetObject(nMarkedPntNum));
112                 sal_uInt32 nPolyNum, nPntNum;
113 
114                 if(PolyPolygonEditor::GetRelativePolyPoint(pPath->GetPathPoly(), nNum, nPolyNum, nPntNum))
115                 {
116                     const basegfx::B2DPolygon aLocalPolygon(pPath->GetPathPoly().getB2DPolygon(nPolyNum));
117                     bool bCanSegment(bClosed || nPntNum < aLocalPolygon.count() - 1L);
118 
119                     if(!bSetMarkedSegmentsKindPossible && bCanSegment)
120                     {
121                         bSetMarkedSegmentsKindPossible = true;
122                     }
123 
124                     if(!bSmoothFuz)
125                     {
126                         if (b1stSmooth)
127                         {
128                             b1stSmooth = false;
129                             eSmooth = basegfx::tools::getContinuityInPoint(aLocalPolygon, nPntNum);
130                         }
131                         else
132                         {
133                             bSmoothFuz = (eSmooth != basegfx::tools::getContinuityInPoint(aLocalPolygon, nPntNum));
134                         }
135                     }
136 
137                     if(!bSegmFuz)
138                     {
139                         if(bCanSegment)
140                         {
141                             bool bCrv(aLocalPolygon.isNextControlPointUsed(nPntNum));
142 
143                             if(b1stSegm)
144                             {
145                                 b1stSegm = false;
146                                 bCurve = bCrv;
147                             }
148                             else
149                             {
150                                 bSegmFuz = (bCrv != bCurve);
151                             }
152                         }
153                     }
154                 }
155             }
156 
157             if(!b1stSmooth && !bSmoothFuz)
158             {
159                 if(basegfx::CONTINUITY_NONE == eSmooth)
160                 {
161                     eMarkedPointsSmooth = SDRPATHSMOOTH_ANGULAR;
162                 }
163 
164                 if(basegfx::CONTINUITY_C1 == eSmooth)
165                 {
166                     eMarkedPointsSmooth = SDRPATHSMOOTH_ASYMMETRIC;
167                 }
168 
169                 if(basegfx::CONTINUITY_C2 == eSmooth)
170                 {
171                     eMarkedPointsSmooth = SDRPATHSMOOTH_SYMMETRIC;
172                 }
173             }
174 
175             if(!b1stSegm && !bSegmFuz)
176             {
177                 eMarkedSegmentsKind = (bCurve) ? SDRPATHSEGMENT_CURVE : SDRPATHSEGMENT_LINE;
178             }
179         }
180     }
181 }
182 
183 void SdrPolyEditView::SetMarkedPointsSmooth(SdrPathSmoothKind eKind)
184 {
185     basegfx::B2VectorContinuity eFlags;
186 
187     if(SDRPATHSMOOTH_ANGULAR == eKind)
188     {
189         eFlags = basegfx::CONTINUITY_NONE;
190     }
191     else if(SDRPATHSMOOTH_ASYMMETRIC == eKind)
192     {
193         eFlags = basegfx::CONTINUITY_C1;
194     }
195     else if(SDRPATHSMOOTH_SYMMETRIC == eKind)
196     {
197         eFlags = basegfx::CONTINUITY_C2;
198     }
199     else
200     {
201         return;
202     }
203 
204     if(HasMarkedPoints())
205     {
206         SortMarkedObjects();
207 
208         const bool bUndo = IsUndoEnabled();
209         if( bUndo )
210             BegUndo(ImpGetResStr(STR_EditSetPointsSmooth), GetDescriptionOfMarkedPoints());
211         sal_uIntPtr nMarkAnz(GetMarkedObjectCount());
212 
213         for(sal_uIntPtr nMarkNum(nMarkAnz); nMarkNum > 0L;)
214         {
215             nMarkNum--;
216             SdrMark* pM = GetSdrMarkByIndex(nMarkNum);
217             SdrUShortCont* pPts = pM->GetMarkedPoints();
218             SdrPathObj* pPath = dynamic_cast< SdrPathObj* >( pM->GetMarkedSdrObj() );
219 
220             if(pPts && pPath)
221             {
222                 PolyPolygonEditor aEditor( pPath->GetPathPoly(), pPath->IsClosed() );
223                 if(aEditor.SetPointsSmooth( eFlags, pPts->getContainer() ) )
224                 {
225                     if( bUndo )
226                         AddUndo(GetModel()->GetSdrUndoFactory().CreateUndoGeoObject(*pPath));
227                     pPath->SetPathPoly(aEditor.GetPolyPolygon());
228                 }
229             }
230         }
231 
232         if( bUndo )
233             EndUndo();
234     }
235 }
236 
237 void SdrPolyEditView::SetMarkedSegmentsKind(SdrPathSegmentKind eKind)
238 {
239     if(HasMarkedPoints())
240     {
241         SortMarkedObjects();
242 
243         const bool bUndo = IsUndoEnabled();
244         if( bUndo )
245             BegUndo(ImpGetResStr(STR_EditSetSegmentsKind), GetDescriptionOfMarkedPoints());
246         sal_uIntPtr nMarkAnz(GetMarkedObjectCount());
247 
248         for(sal_uIntPtr nMarkNum(nMarkAnz); nMarkNum > 0L;)
249         {
250             nMarkNum--;
251             SdrMark* pM = GetSdrMarkByIndex(nMarkNum);
252             SdrUShortCont* pPts = pM->GetMarkedPoints();
253             SdrPathObj* pPath = dynamic_cast< SdrPathObj* >( pM->GetMarkedSdrObj() );
254 
255             if(pPts && pPath)
256             {
257                 PolyPolygonEditor aEditor( pPath->GetPathPoly(), pPath->IsClosed() );
258                 if(aEditor.SetSegmentsKind( eKind, pPts->getContainer()) )
259                 {
260                     if( bUndo )
261                         AddUndo(GetModel()->GetSdrUndoFactory().CreateUndoGeoObject(*pPath));
262                     pPath->SetPathPoly(aEditor.GetPolyPolygon());
263                 }
264             }
265         }
266 
267         if( bUndo )
268             EndUndo();
269     }
270 }
271 
272 sal_Bool SdrPolyEditView::IsSetMarkedPointsSmoothPossible() const
273 {
274     ForcePossibilities();
275     return bSetMarkedPointsSmoothPossible;
276 }
277 
278 SdrPathSmoothKind SdrPolyEditView::GetMarkedPointsSmooth() const
279 {
280     ForcePossibilities();
281     return eMarkedPointsSmooth;
282 }
283 
284 sal_Bool SdrPolyEditView::IsSetMarkedSegmentsKindPossible() const
285 {
286     ForcePossibilities();
287     return bSetMarkedSegmentsKindPossible;
288 }
289 
290 SdrPathSegmentKind SdrPolyEditView::GetMarkedSegmentsKind() const
291 {
292     ForcePossibilities();
293     return eMarkedSegmentsKind;
294 }
295 
296 sal_Bool SdrPolyEditView::IsDeleteMarkedPointsPossible() const
297 {
298     return HasMarkedPoints();
299 }
300 
301 void SdrPolyEditView::DeleteMarkedPoints()
302 {
303     if (HasMarkedPoints())
304     {
305         BrkAction();
306         SortMarkedObjects();
307         sal_uIntPtr nMarkAnz=GetMarkedObjectCount();
308 
309         const bool bUndo = IsUndoEnabled();
310         if( bUndo )
311         {
312             // Description
313             BegUndo(ImpGetResStr(STR_EditDelete),GetDescriptionOfMarkedPoints(),SDRREPFUNC_OBJ_DELETE);
314         }
315 
316         for (sal_uIntPtr nMarkNum=nMarkAnz; nMarkNum>0;)
317         {
318             nMarkNum--;
319             SdrMark* pM=GetSdrMarkByIndex(nMarkNum);
320             SdrUShortCont* pPts=pM->GetMarkedPoints();
321             SdrPathObj* pPath = dynamic_cast< SdrPathObj* >( pM->GetMarkedSdrObj() );
322 
323             if( pPath && pPts )
324             {
325                 PolyPolygonEditor aEditor( pPath ->GetPathPoly(), pPath->IsClosed() );
326                 if( aEditor.DeletePoints( pPts->getContainer() ) )
327                 {
328                     if( aEditor.GetPolyPolygon().count() )
329                     {
330                         if( bUndo )
331                             AddUndo(GetModel()->GetSdrUndoFactory().CreateUndoGeoObject(*pPath ));
332                         pPath->SetPathPoly( aEditor.GetPolyPolygon() );
333                     }
334                     else
335                     {
336                         if( bUndo )
337                             AddUndo( GetModel()->GetSdrUndoFactory().CreateUndoDeleteObject(*pPath ) );
338                         pM->GetPageView()->GetObjList()->RemoveObject(pPath->GetOrdNum());
339                         if( !bUndo )
340                         {
341                             SdrObject* pObj = pPath;
342                             SdrObject::Free(pObj);
343                         }
344                     }
345                 }
346             }
347         }
348 
349         if( bUndo )
350             EndUndo();
351         UnmarkAllPoints();
352         MarkListHasChanged();
353     }
354 }
355 
356 void SdrPolyEditView::RipUpAtMarkedPoints()
357 {
358     if(HasMarkedPoints())
359     {
360         SortMarkedObjects();
361         sal_uInt32 nMarkAnz(GetMarkedObjectCount());
362 
363         const bool bUndo = IsUndoEnabled();
364         if( bUndo )
365             BegUndo(ImpGetResStr(STR_EditRipUp), GetDescriptionOfMarkedPoints());
366 
367         for(sal_uInt32 nMarkNum(nMarkAnz); nMarkNum > 0L;)
368         {
369             nMarkNum--;
370             SdrMark* pM = GetSdrMarkByIndex(nMarkNum);
371             SdrUShortCont* pPts = pM->GetMarkedPoints();
372             SdrPathObj* pObj = PTR_CAST(SdrPathObj, pM->GetMarkedSdrObj());
373 
374             if(pPts && pObj)
375             {
376                 pPts->ForceSort();
377                 if( bUndo )
378                     AddUndo(GetModel()->GetSdrUndoFactory().CreateUndoGeoObject(*pObj));
379                 sal_Bool bKorregFlag(sal_False);
380                 sal_Bool bInsAny(sal_False);
381                 sal_uInt32 nMarkPtsAnz(pPts->GetCount());
382                 sal_uInt32 nMax(pObj->GetHdlCount());
383 
384                 for(sal_uInt32 i(nMarkPtsAnz); i > 0L;)
385                 {
386                     i--;
387                     sal_uInt32 nNewPt0Idx(0L);
388                     SdrObject* pNewObj = pObj->RipPoint(pPts->GetObject(i), nNewPt0Idx);
389 
390                     if(pNewObj)
391                     {
392                         bInsAny = sal_True;
393                         SdrInsertReason aReason(SDRREASON_VIEWCALL, pObj);
394                         pM->GetPageView()->GetObjList()->InsertObject(pNewObj, pObj->GetOrdNum() + 1, &aReason);
395                         if( bUndo )
396                             AddUndo(GetModel()->GetSdrUndoFactory().CreateUndoNewObject(*pNewObj));
397                         MarkObj(pNewObj, pM->GetPageView(), sal_False, sal_True);
398                     }
399 
400                     if(nNewPt0Idx)
401                     {
402                         // Korrektur notwendig?
403                         DBG_ASSERT(bKorregFlag==sal_False,"Mehrfache Indexkorrektur bei SdrPolyEditView::RipUp()");
404                         if(!bKorregFlag)
405                         {
406                             bKorregFlag = sal_True;
407 
408                             for(sal_uInt32 nBla(0L); nBla < nMarkPtsAnz; nBla++)
409                             {
410                                 sal_uInt32 nPntNum(pPts->GetObject(nBla));
411                                 nPntNum += nNewPt0Idx;
412 
413                                 if(nPntNum >= nMax)
414                                 {
415                                     nPntNum -= nMax;
416                                 }
417 
418                                 pPts->Replace((sal_uInt16)nPntNum, nBla);
419                             }
420 
421                             i = nMarkPtsAnz; // ... und nochmal von vorn
422                         }
423                     }
424                 }
425             }
426         }
427 
428         UnmarkAllPoints();
429         if( bUndo )
430             EndUndo();
431         MarkListHasChanged();
432     }
433 }
434 
435 bool SdrPolyEditView::IsRipUpAtMarkedPointsPossible() const
436 {
437     bool bRetval(false);
438     const sal_uInt32 nMarkCount(GetMarkedObjectCount());
439 
440     for(sal_uInt32 a(0); a < nMarkCount; a++)
441     {
442         const SdrMark* pMark = GetSdrMarkByIndex(a);
443         const SdrPathObj* pMarkedPathObject = dynamic_cast< const SdrPathObj* >(pMark->GetMarkedSdrObj());
444 
445         if(pMarkedPathObject)
446         {
447             const SdrUShortCont* pSelectedPoints = pMark->GetMarkedPoints();
448 
449             if(pSelectedPoints && pSelectedPoints->GetCount())
450             {
451                 const basegfx::B2DPolyPolygon& rPathPolyPolygon = pMarkedPathObject->GetPathPoly();
452 
453                 if(1 == rPathPolyPolygon.count())
454                 {
455                     // #i76617# Do not yet use basegfx::B2DPolygon since curve definitions
456                     // are different and methods need to be changed thoroughly with interaction rework
457                     const Polygon aPathPolygon(rPathPolyPolygon.getB2DPolygon(0));
458                     const sal_uInt16 nPointCount(aPathPolygon.GetSize());
459 
460                     if(nPointCount >= 3)
461                     {
462                         bRetval = pMarkedPathObject->IsClosedObj(); // #i76617# aPathPolygon.isClosed();
463 
464                         for(sal_uInt32 b(0); !bRetval && b < pSelectedPoints->GetCount(); b++)
465                         {
466                             const sal_uInt16 nMarkedPointNum(pSelectedPoints->GetObject(b));
467 
468                             bRetval = (nMarkedPointNum > 0 && nMarkedPointNum < nPointCount - 1);
469                         }
470                     }
471                 }
472             }
473         }
474     }
475 
476     return bRetval;
477 }
478 
479 bool SdrPolyEditView::IsOpenCloseMarkedObjectsPossible() const
480 {
481     bool bRetval(false);
482     const sal_uInt32 nMarkCount(GetMarkedObjectCount());
483 
484     for(sal_uInt32 a(0); a < nMarkCount; a++)
485     {
486         const SdrMark* pMark = GetSdrMarkByIndex(a);
487         const SdrPathObj* pMarkedPathObject = dynamic_cast< const SdrPathObj* >(pMark->GetMarkedSdrObj());
488 
489         if(pMarkedPathObject)
490         {
491             // #i76617# Do not yet use basegfx::B2DPolygon since curve definitions
492             // are different and methods need to be changed thoroughly with interaction rework
493             const PolyPolygon aPathPolyPolygon(pMarkedPathObject->GetPathPoly());
494             const sal_uInt16 nPolygonCount(aPathPolyPolygon.Count());
495 
496             for(sal_uInt16 b(0); !bRetval && b < nPolygonCount; b++)
497             {
498                 const Polygon& rPathPolygon = aPathPolyPolygon[b];
499                 const sal_uInt16 nPointCount(rPathPolygon.GetSize());
500 
501                 bRetval = (nPointCount >= 3);
502             }
503         }
504     }
505 
506     return bRetval;
507 }
508 
509 SdrObjClosedKind SdrPolyEditView::GetMarkedObjectsClosedState() const
510 {
511     bool bOpen(false);
512     bool bClosed(false);
513     const sal_uInt32 nMarkCount(GetMarkedObjectCount());
514 
515     for(sal_uInt32 a(0); !(bOpen && bClosed) && a < nMarkCount; a++)
516     {
517         const SdrMark* pMark = GetSdrMarkByIndex(a);
518         const SdrPathObj* pMarkedPathObject = dynamic_cast< const SdrPathObj* >(pMark->GetMarkedSdrObj());
519 
520         if(pMarkedPathObject)
521         {
522             if(pMarkedPathObject->IsClosedObj())
523             {
524                 bClosed = true;
525             }
526             else
527             {
528                 bOpen = true;
529             }
530         }
531     }
532 
533     if(bOpen && bClosed)
534     {
535         return SDROBJCLOSED_DONTCARE;
536     }
537     else if(bOpen)
538     {
539         return SDROBJCLOSED_OPEN;
540     }
541     else
542     {
543         return SDROBJCLOSED_CLOSED;
544     }
545 }
546 
547 void SdrPolyEditView::ShutMarkedObjects()
548 {
549     CloseMarkedObjects();
550 }
551 
552 void SdrPolyEditView::CloseMarkedObjects(sal_Bool bToggle, sal_Bool bOpen) // , long nOpenDistance)
553 {
554     if (AreObjectsMarked())
555     {
556         const bool bUndo = IsUndoEnabled();
557         if( bUndo )
558             BegUndo(ImpGetResStr(STR_EditShut),GetDescriptionOfMarkedPoints());
559 
560         bool bChg=false;
561         sal_uIntPtr nMarkAnz=GetMarkedObjectCount();
562         for (sal_uIntPtr nm=0; nm<nMarkAnz; nm++)
563         {
564             SdrMark* pM=GetSdrMarkByIndex(nm);
565             SdrObject* pO=pM->GetMarkedSdrObj();
566             sal_Bool bClosed=pO->IsClosedObj();
567             if (pO->IsPolyObj() && (bClosed==bOpen) || bToggle)
568             {
569                 if( bUndo )
570                     AddUndo(GetModel()->GetSdrUndoFactory().CreateUndoGeoObject(*pO));
571 
572                 SdrPathObj* pPathObj = dynamic_cast< SdrPathObj* >( pO );
573                 if(pPathObj)
574                     pPathObj->ToggleClosed();
575                 bChg=true;
576             }
577         }
578 
579         if( bUndo )
580             EndUndo();
581 
582         if (bChg)
583         {
584             UnmarkAllPoints();
585             MarkListHasChanged();
586         }
587     }
588 }
589 
590 ////////////////////////////////////////////////////////////////////////////////////////////////////
591 
592 void SdrPolyEditView::ImpCopyMarkedPoints()
593 {
594 }
595 
596 ////////////////////////////////////////////////////////////////////////////////////////////////////
597 
598 void SdrPolyEditView::ImpTransformMarkedPoints(PPolyTrFunc pTrFunc, const void* p1, const void* p2, const void* p3, const void* p4, const void* p5)
599 {
600     const bool bUndo = IsUndoEnabled();
601 
602     sal_uIntPtr nMarkAnz=GetMarkedObjectCount();
603     for (sal_uIntPtr nm=0; nm<nMarkAnz; nm++)
604     {
605         SdrMark* pM=GetSdrMarkByIndex(nm);
606         SdrObject* pObj=pM->GetMarkedSdrObj();
607         const SdrUShortCont* pPts=pM->GetMarkedPoints();
608         sal_uIntPtr nPtAnz=pPts==NULL ? 0 : pPts->GetCount();
609         SdrPathObj* pPath=PTR_CAST(SdrPathObj,pObj);
610         if (nPtAnz!=0 && pPath!=NULL)
611         {
612             if( bUndo )
613                 AddUndo(GetModel()->GetSdrUndoFactory().CreateUndoGeoObject(*pObj));
614 
615             basegfx::B2DPolyPolygon aXPP(pPath->GetPathPoly());
616 
617             for(sal_uInt32 nPtNum(0L); nPtNum < nPtAnz; nPtNum++)
618             {
619                 sal_uInt32 nPt(pPts->GetObject(nPtNum));
620                 sal_uInt32 nPolyNum, nPointNum;
621 
622                 if(PolyPolygonEditor::GetRelativePolyPoint(aXPP, nPt, nPolyNum, nPointNum))
623                 {
624                     //#i83671# used nLocalPointNum (which was the polygon point count)
625                     // instead of the point index (nPointNum). This of course leaded
626                     // to a wrong point access to the B2DPolygon.
627                     basegfx::B2DPolygon aNewXP(aXPP.getB2DPolygon(nPolyNum));
628                     Point aPos, aC1, aC2;
629                     bool bC1(false);
630                     bool bC2(false);
631 
632                     const basegfx::B2DPoint aB2DPos(aNewXP.getB2DPoint(nPointNum));
633                     aPos = Point(FRound(aB2DPos.getX()), FRound(aB2DPos.getY()));
634 
635                     if(aNewXP.isPrevControlPointUsed(nPointNum))
636                     {
637                         const basegfx::B2DPoint aB2DC1(aNewXP.getPrevControlPoint(nPointNum));
638                         aC1 = Point(FRound(aB2DC1.getX()), FRound(aB2DC1.getY()));
639                         bC1 = true;
640                     }
641 
642                     if(aNewXP.isNextControlPointUsed(nPointNum))
643                     {
644                         const basegfx::B2DPoint aB2DC2(aNewXP.getNextControlPoint(nPointNum));
645                         aC2 = Point(FRound(aB2DC2.getX()), FRound(aB2DC2.getY()));
646                         bC2 = true;
647                     }
648 
649                     (*pTrFunc)(aPos,&aC1,&aC2,p1,p2,p3,p4,p5);
650                     aNewXP.setB2DPoint(nPointNum, basegfx::B2DPoint(aPos.X(), aPos.Y()));
651 
652                     if (bC1)
653                     {
654                         aNewXP.setPrevControlPoint(nPointNum, basegfx::B2DPoint(aC1.X(), aC1.Y()));
655                     }
656 
657                     if (bC2)
658                     {
659                         aNewXP.setNextControlPoint(nPointNum, basegfx::B2DPoint(aC2.X(), aC2.Y()));
660                     }
661 
662                     aXPP.setB2DPolygon(nPolyNum, aNewXP);
663                 }
664             }
665 
666             pPath->SetPathPoly(aXPP);
667         }
668     }
669 }
670 
671 ////////////////////////////////////////////////////////////////////////////////////////////////////
672 
673 static void ImpMove(Point& rPt, Point* pC1, Point* pC2, const void* p1, const void* /*p2*/, const void* /*p3*/, const void* /*p4*/, const void* /*p5*/)
674 {
675     MovePoint(rPt,*(const Size*)p1);
676     if (pC1!=NULL) MovePoint(*pC1,*(const Size*)p1);
677     if (pC2!=NULL) MovePoint(*pC2,*(const Size*)p1);
678 }
679 
680 void SdrPolyEditView::MoveMarkedPoints(const Size& rSiz, bool bCopy)
681 {
682     bCopy=sal_False; // noch nicht implementiert
683     ForceUndirtyMrkPnt();
684     XubString aStr(ImpGetResStr(STR_EditMove));
685     if (bCopy) aStr+=ImpGetResStr(STR_EditWithCopy);
686     BegUndo(aStr,GetDescriptionOfMarkedPoints(),SDRREPFUNC_OBJ_MOVE);
687     if (bCopy) ImpCopyMarkedPoints();
688     ImpTransformMarkedPoints(ImpMove,&rSiz);
689     EndUndo();
690     AdjustMarkHdl();
691 }
692 
693 ////////////////////////////////////////////////////////////////////////////////////////////////////
694 
695 static void ImpResize(Point& rPt, Point* pC1, Point* pC2, const void* p1, const void* p2, const void* p3, const void* /*p4*/, const void* /*p5*/)
696 {
697     ResizePoint(rPt,*(const Point*)p1,*(const Fraction*)p2,*(const Fraction*)p3);
698     if (pC1!=NULL) ResizePoint(*pC1,*(const Point*)p1,*(const Fraction*)p2,*(const Fraction*)p3);
699     if (pC2!=NULL) ResizePoint(*pC2,*(const Point*)p1,*(const Fraction*)p2,*(const Fraction*)p3);
700 }
701 
702 void SdrPolyEditView::ResizeMarkedPoints(const Point& rRef, const Fraction& xFact, const Fraction& yFact, bool bCopy)
703 {
704     bCopy=sal_False; // noch nicht implementiert
705     ForceUndirtyMrkPnt();
706     XubString aStr(ImpGetResStr(STR_EditResize));
707     if (bCopy) aStr+=ImpGetResStr(STR_EditWithCopy);
708     BegUndo(aStr,GetDescriptionOfMarkedPoints(),SDRREPFUNC_OBJ_RESIZE);
709     if (bCopy) ImpCopyMarkedPoints();
710     ImpTransformMarkedPoints(ImpResize,&rRef,&xFact,&yFact);
711     EndUndo();
712     AdjustMarkHdl();
713 }
714 
715 ////////////////////////////////////////////////////////////////////////////////////////////////////
716 
717 static void ImpRotate(Point& rPt, Point* pC1, Point* pC2, const void* p1, const void* /*p2*/, const void* p3, const void* p4, const void* /*p5*/)
718 {
719     RotatePoint(rPt,*(const Point*)p1,*(const double*)p3,*(const double*)p4);
720     if (pC1!=NULL) RotatePoint(*pC1,*(const Point*)p1,*(const double*)p3,*(const double*)p4);
721     if (pC2!=NULL) RotatePoint(*pC2,*(const Point*)p1,*(const double*)p3,*(const double*)p4);
722 }
723 
724 void SdrPolyEditView::RotateMarkedPoints(const Point& rRef, long nWink, bool bCopy)
725 {
726     bCopy=sal_False; // noch nicht implementiert
727     ForceUndirtyMrkPnt();
728     XubString aStr(ImpGetResStr(STR_EditResize));
729     if (bCopy) aStr+=ImpGetResStr(STR_EditWithCopy);
730     BegUndo(aStr,GetDescriptionOfMarkedPoints(),SDRREPFUNC_OBJ_ROTATE);
731     if (bCopy) ImpCopyMarkedPoints();
732     double nSin=sin(nWink*nPi180);
733     double nCos=cos(nWink*nPi180);
734     ImpTransformMarkedPoints(ImpRotate,&rRef,&nWink,&nSin,&nCos);
735     EndUndo();
736     AdjustMarkHdl();
737 }
738 
739 /* vim: set noet sw=4 ts=4: */
740