LibreOffice Module svx (master)  1
svdmrkv.cxx
Go to the documentation of this file.
1 /* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
2 /*
3  * This file is part of the LibreOffice project.
4  *
5  * This Source Code Form is subject to the terms of the Mozilla Public
6  * License, v. 2.0. If a copy of the MPL was not distributed with this
7  * file, You can obtain one at http://mozilla.org/MPL/2.0/.
8  *
9  * This file incorporates work covered by the following license notice:
10  *
11  * Licensed to the Apache Software Foundation (ASF) under one or more
12  * contributor license agreements. See the NOTICE file distributed
13  * with this work for additional information regarding copyright
14  * ownership. The ASF licenses this file to you under the Apache
15  * License, Version 2.0 (the "License"); you may not use this file
16  * except in compliance with the License. You may obtain a copy of
17  * the License at http://www.apache.org/licenses/LICENSE-2.0 .
18  */
19 
20 
21 #include <svx/svdmrkv.hxx>
22 #include <svx/svdview.hxx>
23 #include <svx/svdpagv.hxx>
24 #include <svx/svdpage.hxx>
25 #include <svx/svdotable.hxx>
26 
27 #include <osl/diagnose.h>
28 #include <osl/thread.h>
29 #include <rtl/strbuf.hxx>
30 #include <svx/svdoole2.hxx>
31 #include <svx/xgrad.hxx>
32 #include <svx/xfillit0.hxx>
33 #include <svx/xflgrit.hxx>
34 #include "gradtrns.hxx"
35 #include <svx/xflftrit.hxx>
36 #include <svx/dialmgr.hxx>
37 #include <svx/strings.hrc>
38 #include <svx/svdundo.hxx>
39 #include <svx/svdopath.hxx>
40 #include <svx/scene3d.hxx>
41 #include <svx/svdovirt.hxx>
48 #include <svx/sdrpaintwindow.hxx>
49 #include <svx/sdrpagewindow.hxx>
50 #include <svx/sdrhittesthelper.hxx>
51 #include <vcl/uitest/logger.hxx>
53 #include <vcl/window.hxx>
54 
55 #include <LibreOfficeKit/LibreOfficeKitEnums.h>
56 #include <comphelper/lok.hxx>
57 #include <sfx2/lokhelper.hxx>
58 #include <sfx2/lokcharthelper.hxx>
59 #include <sfx2/viewsh.hxx>
61 
62 #include <array>
63 
64 #include <com/sun/star/frame/XController.hpp>
65 #include <com/sun/star/view/XSelectionSupplier.hpp>
66 
67 #include <boost/property_tree/json_parser.hpp>
68 #include <boost/optional/optional.hpp>
69 #include <tools/UnitConversion.hxx>
70 
71 using namespace com::sun::star;
72 
73 // Migrate Marking of Objects, Points and GluePoints
74 
76 {
77  // The OverlayObjects
79 
80  // The remembered second position in logical coordinates
82 
83  // A flag to remember if the action is for unmarking.
84  bool mbUnmarking : 1;
85 
86 public:
87  ImplMarkingOverlay(const SdrPaintView& rView, const basegfx::B2DPoint& rStartPos, bool bUnmarking);
88 
89  // The OverlayObjects are cleared using the destructor of OverlayObjectList.
90  // That destructor calls clear() at the list which removes all objects from the
91  // OverlayManager and deletes them.
92 
93  void SetSecondPosition(const basegfx::B2DPoint& rNewPosition);
94  bool IsUnmarking() const { return mbUnmarking; }
95 };
96 
97 ImplMarkingOverlay::ImplMarkingOverlay(const SdrPaintView& rView, const basegfx::B2DPoint& rStartPos, bool bUnmarking)
98 : maSecondPosition(rStartPos),
99  mbUnmarking(bUnmarking)
100 {
102  return; // We do client-side object manipulation with the Kit API
103 
104  for(sal_uInt32 a(0); a < rView.PaintWindowCount(); a++)
105  {
106  SdrPaintWindow* pCandidate = rView.GetPaintWindow(a);
107  const rtl::Reference< sdr::overlay::OverlayManager >& xTargetOverlay = pCandidate->GetOverlayManager();
108 
109  if (xTargetOverlay.is())
110  {
111  std::unique_ptr<sdr::overlay::OverlayRollingRectangleStriped> pNew(new sdr::overlay::OverlayRollingRectangleStriped(
112  rStartPos, rStartPos, false));
113  xTargetOverlay->add(*pNew);
114  maObjects.append(std::move(pNew));
115  }
116  }
117 }
118 
120 {
121  if(rNewPosition != maSecondPosition)
122  {
123  // apply to OverlayObjects
124  for(sal_uInt32 a(0); a < maObjects.count(); a++)
125  {
127  rCandidate.setSecondPosition(rNewPosition);
128  }
129 
130  // remember new position
131  maSecondPosition = rNewPosition;
132  }
133 }
134 
136 {
138 
139 public:
140  MarkingSubSelectionOverlay(const SdrPaintView& rView, std::vector<basegfx::B2DRectangle> const & rSelections)
141  {
143  return; // We do client-side object manipulation with the Kit API
144 
145  for (sal_uInt32 a(0); a < rView.PaintWindowCount(); a++)
146  {
147  SdrPaintWindow* pCandidate = rView.GetPaintWindow(a);
148  const rtl::Reference<sdr::overlay::OverlayManager>& xTargetOverlay = pCandidate->GetOverlayManager();
149 
150  if (xTargetOverlay.is())
151  {
152  const Color aHighlightColor = SvtOptionsDrawinglayer::getHilightColor();
153 
154  std::unique_ptr<sdr::overlay::OverlaySelection> pNew =
155  std::make_unique<sdr::overlay::OverlaySelection>(
157  aHighlightColor, rSelections, false);
158 
159  xTargetOverlay->add(*pNew);
160  maObjects.append(std::move(pNew));
161  }
162  }
163  }
164 };
165 
167  : SdrSnapView(rSdrModel, pOut)
168  , mpMarkedObj(nullptr)
169  , mpMarkedPV(nullptr)
170  , maHdlList(this)
171  , meDragMode(SdrDragMode::Move)
172  , meEditMode(SdrViewEditMode::Edit)
173  , meEditMode0(SdrViewEditMode::Edit)
174  , mbDesignMode(false)
175  , mbForceFrameHandles(false)
176  , mbPlusHdlAlways(false)
177  , mbInsPolyPoint(false)
178  , mbMarkedObjRectDirty(false)
179  , mbMrkPntDirty(false)
180  , mbMarkedPointsRectsDirty(false)
181  , mbMarkHandlesHidden(false)
182 {
183 
184  BrkMarkObj();
185  BrkMarkPoints();
187 
188  StartListening(rSdrModel);
189 }
190 
192 {
193  // Migrate selections
194  BrkMarkObj();
195  BrkMarkPoints();
197 }
198 
200 {
201  if (rHint.GetId() == SfxHintId::ThisIsAnSdrHint)
202  {
203  const SdrHint* pSdrHint = static_cast<const SdrHint*>(&rHint);
204  SdrHintKind eKind=pSdrHint->GetKind();
206  {
209  }
210  }
211  SdrSnapView::Notify(rBC,rHint);
212 }
213 
215 {
220  // Example: Obj is selected and maMarkedObjectList is sorted.
221  // In another View 2, the ObjOrder is changed (e. g. MovToTop())
222  // Then we need to re-sort MarkList.
225  mbMrkPntDirty=true;
226  UndirtyMrkPnt();
227  SdrView* pV=static_cast<SdrView*>(this);
228  if (pV!=nullptr && !pV->IsDragObj() && !pV->IsInsObjPoint()) {
229  AdjustMarkHdl();
230  }
231 
233  return;
234 
235  //TODO: Is MarkedObjRect valid at this point?
236  tools::Rectangle aSelection(GetMarkedObjRect());
237  tools::Rectangle* pResultSelection;
238  if (aSelection.IsEmpty())
239  pResultSelection = nullptr;
240  else
241  {
242  sal_uInt32 nTotalPaintWindows = this->PaintWindowCount();
243  if (nTotalPaintWindows == 1)
244  {
245  const OutputDevice* pOut = this->GetFirstOutputDevice();
246  const vcl::Window* pWin = pOut ? pOut->GetOwnerWindow() : nullptr;
247  if (pWin && pWin->IsChart())
248  {
249  const vcl::Window* pViewShellWindow = GetSfxViewShell()->GetEditWindowForActiveOLEObj();
250  if (pViewShellWindow && pViewShellWindow->IsAncestorOf(*pWin))
251  {
252  Point aOffsetPx = pWin->GetOffsetPixelFrom(*pViewShellWindow);
253  Point aLogicOffset = pWin->PixelToLogic(aOffsetPx);
254  aSelection.Move(aLogicOffset.getX(), aLogicOffset.getY());
255  }
256  }
257  }
258 
259  // In case the map mode is in 100th MM, then need to convert the coordinates over to twips for LOK.
260  if (mpMarkedPV)
261  {
262  if (OutputDevice* pOutputDevice = mpMarkedPV->GetView().GetFirstOutputDevice())
263  {
264  if (pOutputDevice->GetMapMode().GetMapUnit() == MapUnit::Map100thMM)
265  aSelection = o3tl::convert(aSelection, o3tl::Length::mm100, o3tl::Length::twip);
266  }
267  }
268 
269  pResultSelection = &aSelection;
270  }
271 
272  if(SfxViewShell* pViewShell = GetSfxViewShell())
273  SfxLokHelper::notifyInvalidation(pViewShell, pResultSelection);
274 }
275 
276 
278 {
280 }
281 
282 void SdrMarkView::MovAction(const Point& rPnt)
283 {
285 
286  if(IsMarkObj())
287  {
288  MovMarkObj(rPnt);
289  }
290  else if(IsMarkPoints())
291  {
292  MovMarkPoints(rPnt);
293  }
294  else if(IsMarkGluePoints())
295  {
296  MovMarkGluePoints(rPnt);
297  }
298 }
299 
301 {
302  if(IsMarkObj())
303  {
304  EndMarkObj();
305  }
306  else if(IsMarkPoints())
307  {
308  EndMarkPoints();
309  }
310  else if(IsMarkGluePoints())
311  {
313  }
314 
316 }
317 
319 {
321  BrkMarkObj();
322  BrkMarkPoints();
324 }
325 
327 {
329  BrkMarkObj();
330  BrkMarkPoints();
332 }
333 
335 {
336  if(IsMarkObj() || IsMarkPoints() || IsMarkGluePoints())
337  {
339  }
340  else
341  {
343  }
344 }
345 
346 
348 {
349  UnmarkAllObj();
351 }
352 
354 {
355  bool bMrkChg(false);
356 
357  SdrPageView* pPageView = GetSdrPageView();
358  if (pPageView)
359  {
360  // break all creation actions when hiding page (#75081#)
361  BrkAction();
362 
363  // Discard all selections on this page
364  bMrkChg = GetMarkedObjectListWriteAccess().DeletePageView(*pPageView);
365  }
366 
368 
369  if(bMrkChg)
370  {
372  AdjustMarkHdl();
373  }
374 }
375 
376 
377 void SdrMarkView::BegMarkObj(const Point& rPnt, bool bUnmark)
378 {
379  BrkAction();
380 
381  DBG_ASSERT(!mpMarkObjOverlay, "SdrMarkView::BegMarkObj: There exists a mpMarkObjOverlay (!)");
382 
383  basegfx::B2DPoint aStartPos(rPnt.X(), rPnt.Y());
384  mpMarkObjOverlay.reset(new ImplMarkingOverlay(*this, aStartPos, bUnmark));
385 
386  maDragStat.Reset(rPnt);
389 }
390 
391 void SdrMarkView::MovMarkObj(const Point& rPnt)
392 {
393  if(IsMarkObj() && maDragStat.CheckMinMoved(rPnt))
394  {
395  maDragStat.NextMove(rPnt);
396  DBG_ASSERT(mpMarkObjOverlay, "SdrSnapView::MovSetPageOrg: no ImplPageOriginOverlay (!)");
397  basegfx::B2DPoint aNewPos(rPnt.X(), rPnt.Y());
398  mpMarkObjOverlay->SetSecondPosition(aNewPos);
399  }
400 }
401 
403 {
404  bool bRetval(false);
405 
406  if(IsMarkObj())
407  {
408  if(maDragStat.IsMinMoved())
409  {
411  aRect.Justify();
412  MarkObj(aRect, mpMarkObjOverlay->IsUnmarking());
413  bRetval = true;
414  }
415 
416  // cleanup
417  BrkMarkObj();
418  }
419 
420  return bRetval;
421 }
422 
424 {
425  if(IsMarkObj())
426  {
427  DBG_ASSERT(mpMarkObjOverlay, "SdrSnapView::MovSetPageOrg: no ImplPageOriginOverlay (!)");
428  mpMarkObjOverlay.reset();
429  }
430 }
431 
432 
433 bool SdrMarkView::BegMarkPoints(const Point& rPnt, bool bUnmark)
434 {
435  if(HasMarkablePoints())
436  {
437  BrkAction();
438 
439  DBG_ASSERT(!mpMarkPointsOverlay, "SdrMarkView::BegMarkObj: There exists a mpMarkPointsOverlay (!)");
440  basegfx::B2DPoint aStartPos(rPnt.X(), rPnt.Y());
441  mpMarkPointsOverlay.reset(new ImplMarkingOverlay(*this, aStartPos, bUnmark));
442 
443  maDragStat.Reset(rPnt);
446 
447  return true;
448  }
449 
450  return false;
451 }
452 
453 void SdrMarkView::MovMarkPoints(const Point& rPnt)
454 {
455  if(IsMarkPoints() && maDragStat.CheckMinMoved(rPnt))
456  {
457  maDragStat.NextMove(rPnt);
458 
459  DBG_ASSERT(mpMarkPointsOverlay, "SdrSnapView::MovSetPageOrg: no ImplPageOriginOverlay (!)");
460  basegfx::B2DPoint aNewPos(rPnt.X(), rPnt.Y());
461  mpMarkPointsOverlay->SetSecondPosition(aNewPos);
462  }
463 }
464 
466 {
467  bool bRetval(false);
468 
469  if(IsMarkPoints())
470  {
471  if(maDragStat.IsMinMoved())
472  {
474  aRect.Justify();
475  MarkPoints(&aRect, mpMarkPointsOverlay->IsUnmarking());
476 
477  bRetval = true;
478  }
479 
480  // cleanup
481  BrkMarkPoints();
482  }
483 
484  return bRetval;
485 }
486 
488 {
489  if(IsMarkPoints())
490  {
491  DBG_ASSERT(mpMarkPointsOverlay, "SdrSnapView::MovSetPageOrg: no ImplPageOriginOverlay (!)");
492  mpMarkPointsOverlay.reset();
493  }
494 }
495 
496 
497 bool SdrMarkView::BegMarkGluePoints(const Point& rPnt, bool bUnmark)
498 {
500  {
501  BrkAction();
502 
503  DBG_ASSERT(!mpMarkGluePointsOverlay, "SdrMarkView::BegMarkObj: There exists a mpMarkGluePointsOverlay (!)");
504 
505  basegfx::B2DPoint aStartPos(rPnt.X(), rPnt.Y());
506  mpMarkGluePointsOverlay.reset(new ImplMarkingOverlay(*this, aStartPos, bUnmark));
507  maDragStat.Reset(rPnt);
510 
511  return true;
512  }
513 
514  return false;
515 }
516 
517 void SdrMarkView::MovMarkGluePoints(const Point& rPnt)
518 {
520  {
521  maDragStat.NextMove(rPnt);
522 
523  DBG_ASSERT(mpMarkGluePointsOverlay, "SdrSnapView::MovSetPageOrg: no ImplPageOriginOverlay (!)");
524  basegfx::B2DPoint aNewPos(rPnt.X(), rPnt.Y());
525  mpMarkGluePointsOverlay->SetSecondPosition(aNewPos);
526  }
527 }
528 
530 {
531  if(IsMarkGluePoints())
532  {
533  if(maDragStat.IsMinMoved())
534  {
536  aRect.Justify();
537  MarkGluePoints(&aRect, mpMarkGluePointsOverlay->IsUnmarking());
538  }
539 
540  // cleanup
542  }
543 }
544 
546 {
547  if(IsMarkGluePoints())
548  {
549  DBG_ASSERT(mpMarkGluePointsOverlay, "SdrSnapView::MovSetPageOrg: no ImplPageOriginOverlay (!)");
550  mpMarkGluePointsOverlay.reset();
551  }
552 }
553 
555 {
556  SdrPageView* pPV = GetSdrPageView();
557  if (!pPV)
558  return false;
559 
560  SdrObjList* pOL=pPV->GetObjList();
561  const size_t nObjCount = pOL->GetObjCount();
562  for (size_t nObjNum=0; nObjNum<nObjCount; ++nObjNum) {
563  SdrObject* pObj=pOL->GetObj(nObjNum);
564  if (IsObjMarkable(pObj,pPV) && --n<0)
565  return true;
566  }
567 
568  return false;
569 }
570 
572 {
574  {
575  mbMarkHandlesHidden = true;
576  AdjustMarkHdl();
577  }
578 }
579 
581 {
583  {
584  mbMarkHandlesHidden = false;
585  AdjustMarkHdl();
586  }
587 }
588 
590 {
591  const size_t nMarkCount=GetMarkedObjectCount();
592  bool bFrmHdl=nMarkCount>static_cast<size_t>(mnFrameHandlesLimit) || mbForceFrameHandles;
593  bool bStdDrag=meDragMode==SdrDragMode::Move;
594  if (nMarkCount==1 && bStdDrag && bFrmHdl)
595  {
596  const SdrObject* pObj=GetMarkedObjectByIndex(0);
597  if (pObj && pObj->GetObjInventor()==SdrInventor::Default)
598  {
599  sal_uInt16 nIdent=pObj->GetObjIdentifier();
600  if (nIdent==OBJ_LINE || nIdent==OBJ_EDGE || nIdent==OBJ_CAPTION || nIdent==OBJ_MEASURE || nIdent==OBJ_CUSTOMSHAPE || nIdent==OBJ_TABLE )
601  {
602  bFrmHdl=false;
603  }
604  }
605  }
606  if (!bStdDrag && !bFrmHdl) {
607  // all other drag modes only with FrameHandles
608  bFrmHdl=true;
610  // when rotating, use ObjOwn drag, if there's at least 1 PolyObj
611  for (size_t nMarkNum=0; nMarkNum<nMarkCount && bFrmHdl; ++nMarkNum) {
612  const SdrMark* pM=GetSdrMarkByIndex(nMarkNum);
613  const SdrObject* pObj=pM->GetMarkedSdrObj();
614  bFrmHdl=!pObj->IsPolyObj();
615  }
616  }
617  }
618  if (!bFrmHdl) {
619  // FrameHandles, if at least 1 Obj can't do SpecialDrag
620  for (size_t nMarkNum=0; nMarkNum<nMarkCount && !bFrmHdl; ++nMarkNum) {
621  const SdrMark* pM=GetSdrMarkByIndex(nMarkNum);
622  const SdrObject* pObj=pM->GetMarkedSdrObj();
623  bFrmHdl=!pObj->hasSpecialDrag();
624  }
625  }
626 
627  // no FrameHdl for crop
628  if(bFrmHdl && SdrDragMode::Crop == meDragMode)
629  {
630  bFrmHdl = false;
631  }
632 
633  return bFrmHdl;
634 }
635 
636 namespace
637 {
638 OUString lcl_getDragMethodServiceName( const OUString& rCID )
639 {
640  OUString aRet;
641 
642  sal_Int32 nIndexStart = rCID.indexOf( "DragMethod=" );
643  if( nIndexStart != -1 )
644  {
645  nIndexStart = rCID.indexOf( '=', nIndexStart );
646  if( nIndexStart != -1 )
647  {
648  nIndexStart++;
649  sal_Int32 nNextSlash = rCID.indexOf( '/', nIndexStart );
650  if( nNextSlash != -1 )
651  {
652  sal_Int32 nIndexEnd = nNextSlash;
653  sal_Int32 nNextColon = rCID.indexOf( ':', nIndexStart );
654  if( nNextColon < nNextSlash )
655  nIndexEnd = nNextColon;
656  aRet = rCID.copy(nIndexStart,nIndexEnd-nIndexStart);
657  }
658  }
659  }
660  return aRet;
661 }
662 
663 OUString lcl_getDragParameterString( const OUString& rCID )
664 {
665  OUString aRet;
666 
667  sal_Int32 nIndexStart = rCID.indexOf( "DragParameter=" );
668  if( nIndexStart != -1 )
669  {
670  nIndexStart = rCID.indexOf( '=', nIndexStart );
671  if( nIndexStart != -1 )
672  {
673  nIndexStart++;
674  sal_Int32 nNextSlash = rCID.indexOf( '/', nIndexStart );
675  if( nNextSlash != -1 )
676  {
677  sal_Int32 nIndexEnd = nNextSlash;
678  sal_Int32 nNextColon = rCID.indexOf( ':', nIndexStart );
679  if( nNextColon < nNextSlash )
680  nIndexEnd = nNextColon;
681  aRet = rCID.copy(nIndexStart,nIndexEnd-nIndexStart);
682  }
683  }
684  }
685  return aRet;
686 }
687 } // anonymous namespace
688 
689 bool SdrMarkView::dumpGluePointsToJSON(boost::property_tree::ptree& rTree)
690 {
691  bool result = false;
692  if (OutputDevice* pOutDev = mpMarkedPV ? mpMarkedPV->GetView().GetFirstOutputDevice() : nullptr)
693  {
694  bool bConvertUnit = false;
695  if (pOutDev->GetMapMode().GetMapUnit() == MapUnit::Map100thMM)
696  bConvertUnit = true;
697  const SdrObjList* pOL = mpMarkedPV->GetObjList();
698  if (!pOL)
699  return false;
700  const size_t nObjCount = pOL->GetObjCount();
701  boost::property_tree::ptree elements;
702  for (size_t nObjNum = 0; nObjNum < nObjCount; ++nObjNum)
703  {
704  SdrObject* pObj = pOL->GetObj(nObjNum);
705  if (!pObj)
706  continue;
707  if (pObj == GetMarkedObjectByIndex(0))
708  continue;
709  const SdrGluePointList* pGPL = pObj->GetGluePointList();
710  bool VertexObject = !(pGPL && pGPL->GetCount());
711  const size_t count = !VertexObject ? pGPL->GetCount() : 4;
712  boost::property_tree::ptree object;
713  boost::property_tree::ptree points;
714  for (size_t i = 0; i < count; ++i)
715  {
716  boost::property_tree::ptree node;
717  boost::property_tree::ptree point;
718  const SdrGluePoint& rGP = !VertexObject ? (*pGPL)[i] : pObj->GetVertexGluePoint(i);
719  Point rPoint = rGP.GetAbsolutePos(*pObj);
720  if (bConvertUnit)
721  {
723  }
724  point.put("x", rPoint.getX());
725  point.put("y", rPoint.getY());
726  node.add_child("point", point);
727  points.push_back(std::make_pair("", node));
728  }
729  basegfx::B2DVector aGridOffset(0.0, 0.0);
730  Point objLogicRectTopLeft = pObj->GetLogicRect().TopLeft();
731  if(getPossibleGridOffsetForPosition(aGridOffset, basegfx::B2DPoint(objLogicRectTopLeft.X(), objLogicRectTopLeft.Y()), GetSdrPageView()))
732  {
733  Point p(aGridOffset.getX(), aGridOffset.getY());
734  if (bConvertUnit)
735  {
737  }
738  boost::property_tree::ptree gridOffset;
739  gridOffset.put("x", p.getX());
740  gridOffset.put("y", p.getY());
741  object.add_child("gridoffset", gridOffset);
742  }
743  object.put("ordnum", pObj->GetOrdNum());
744  object.add_child("gluepoints", points);
745  elements.push_back(std::make_pair("", object));
746  result = true;
747  }
748  rTree.add_child("shapes", elements);
749  }
750  return result;
751 }
752 
754 {
755  SfxViewShell* pViewShell = GetSfxViewShell();
756 
757  tools::Rectangle aSelection(rRect);
758  bool bIsChart = false;
759  Point addLogicOffset(0, 0);
760  bool convertMapMode = false;
761  if (!rRect.IsEmpty())
762  {
763  sal_uInt32 nTotalPaintWindows = this->PaintWindowCount();
764  if (nTotalPaintWindows == 1)
765  {
766  const OutputDevice* pOut = this->GetFirstOutputDevice();
767  const vcl::Window* pWin = pOut ? pOut->GetOwnerWindow() : nullptr;
768  if (pWin && pWin->IsChart())
769  {
770  bIsChart = true;
771  const vcl::Window* pViewShellWindow = GetSfxViewShell()->GetEditWindowForActiveOLEObj();
772  if (pViewShellWindow && pViewShellWindow->IsAncestorOf(*pWin))
773  {
774  Point aOffsetPx = pWin->GetOffsetPixelFrom(*pViewShellWindow);
775  Point aLogicOffset = pWin->PixelToLogic(aOffsetPx);
776  addLogicOffset = aLogicOffset;
777  aSelection.Move(aLogicOffset.getX(), aLogicOffset.getY());
778  }
779  }
780  }
781  }
782 
783  if (!aSelection.IsEmpty())
784  {
785  // In case the map mode is in 100th MM, then need to convert the coordinates over to twips for LOK.
786  if (mpMarkedPV)
787  {
788  if (OutputDevice* pOutputDevice = mpMarkedPV->GetView().GetFirstOutputDevice())
789  {
790  if (pOutputDevice->GetMapMode().GetMapUnit() == MapUnit::Map100thMM)
791  {
792  aSelection = o3tl::convert(aSelection, o3tl::Length::mm100, o3tl::Length::twip);
793  convertMapMode = true;
794  }
795  }
796  }
797 
798  // hide the text selection too
799  pViewShell->libreOfficeKitViewCallback(LOK_CALLBACK_TEXT_SELECTION, "");
800  }
801 
802  {
803  OString sSelectionText;
804  OString sSelectionTextView;
805  boost::property_tree::ptree aTableJsonTree;
806  boost::property_tree::ptree aGluePointsTree;
807  bool bTableSelection = false;
808  bool bConnectorSelection = false;
809 
811  {
812  auto& rTableObject = dynamic_cast<sdr::table::SdrTableObj&>(*mpMarkedObj);
813  bTableSelection = rTableObject.createTableEdgesJson(aTableJsonTree);
814  }
816  {
817  bConnectorSelection = dumpGluePointsToJSON(aGluePointsTree);
818  }
819  if (GetMarkedObjectCount())
820  {
821  SdrMark* pM = GetSdrMarkByIndex(0);
822  SdrObject* pO = pM->GetMarkedSdrObj();
823  Degree100 nRotAngle = pO->GetRotateAngle();
824  // true if we are dealing with a RotGrfFlyFrame
825  // (SwVirtFlyDrawObj with a SwGrfNode)
826  bool bWriterGraphic = pO->HasLimitedRotation();
827 
828  OStringBuffer aExtraInfo;
829  OString handleArrayStr;
830 
831  aExtraInfo.append("{\"id\":\"");
832  aExtraInfo.append(reinterpret_cast<sal_IntPtr>(pO));
833  aExtraInfo.append("\",\"type\":");
834  aExtraInfo.append(static_cast<sal_Int32>(pO->GetObjIdentifier()));
835 
836  // In core, the gridOffset is calculated based on the LogicRect's TopLeft coordinate
837  // In online, we have the SnapRect and we calculate it based on its TopLeft coordinate
838  // SnapRect's TopLeft and LogicRect's TopLeft match unless there is rotation
839  // but the rotation is not applied to the LogicRect. Therefore,
840  // what we calculate in online does not match with the core in case of the rotation.
841  // Here we can send the correct gridOffset in the selection callback, this way
842  // whether the shape is rotated or not, we will always have the correct gridOffset
843  // Note that the gridOffset is calculated from the first selected obj
844  basegfx::B2DVector aGridOffset(0.0, 0.0);
846  {
847  Point p(aGridOffset.getX(), aGridOffset.getY());
848  if (convertMapMode)
850  aExtraInfo.append(",\"gridOffsetX\":");
851  aExtraInfo.append(p.getX());
852  aExtraInfo.append(",\"gridOffsetY\":");
853  aExtraInfo.append(p.getY());
854  }
855 
856  if (bWriterGraphic)
857  {
858  aExtraInfo.append(", \"isWriterGraphic\": true");
859  }
860  else if (bIsChart)
861  {
862  LokChartHelper aChartHelper(pViewShell);
863  css::uno::Reference<css::frame::XController>& xChartController = aChartHelper.GetXController();
864  css::uno::Reference<css::view::XSelectionSupplier> xSelectionSupplier( xChartController, uno::UNO_QUERY);
865  if (xSelectionSupplier.is())
866  {
867  uno::Any aSel = xSelectionSupplier->getSelection();
868  OUString aValue;
869  if (aSel >>= aValue)
870  {
871  OString aObjectCID(aValue.getStr(), aValue.getLength(), osl_getThreadTextEncoding());
872  const std::vector<OString> aProps{"Draggable", "Resizable", "Rotatable"};
873  for (const auto& rProp: aProps)
874  {
875  sal_Int32 nPos = aObjectCID.indexOf(rProp);
876  if (nPos == -1) continue;
877  nPos += rProp.getLength() + 1; // '='
878  if (aExtraInfo.getLength() > 2) // != "{ "
879  aExtraInfo.append(", ");
880  aExtraInfo.append("\"is");
881  aExtraInfo.append(rProp);
882  aExtraInfo.append("\": ");
883  aExtraInfo.append(OString::boolean(aObjectCID[nPos] == '1'));
884  }
885 
886  OUString sDragMethod = lcl_getDragMethodServiceName(aValue);
887  if (sDragMethod == "PieSegmentDragging")
888  {
889  // old initial offset inside the CID returned by xSelectionSupplier->getSelection()
890  // after a pie segment dragging; using SdrObject::GetName for getting a CID with the updated offset
891  aValue = pO->GetName();
892  OUString sDragParameters = lcl_getDragParameterString(aValue);
893  if (!sDragParameters.isEmpty())
894  {
895  aExtraInfo.append(", \"dragInfo\": { ");
896  aExtraInfo.append("\"dragMethod\": \"");
897  aExtraInfo.append(sDragMethod.toUtf8());
898  aExtraInfo.append("\"");
899 
900  OUString sParam;
901  sal_Int32 nStartIndex = 0;
902  std::array<int, 5> aDragParameters;
903  for (auto& rParam : aDragParameters)
904  {
905  sParam = sDragParameters.getToken(0, ',', nStartIndex);
906  if (sParam.isEmpty())
907  break;
908  rParam = sParam.toInt32();
909  }
910 
911  // initial offset in %
912  if (aDragParameters[0] < 0)
913  aDragParameters[0] = 0;
914  else if (aDragParameters[0] > 100)
915  aDragParameters[0] = 100;
916 
917  aExtraInfo.append(", \"initialOffset\": ");
918  aExtraInfo.append(static_cast<sal_Int32>(aDragParameters[0]));
919 
920  // drag direction constraint
921  Point aMinPos(aDragParameters[1], aDragParameters[2]);
922  Point aMaxPos(aDragParameters[3], aDragParameters[4]);
923  Point aDragDirection = aMaxPos - aMinPos;
924  aDragDirection = o3tl::convert(aDragDirection, o3tl::Length::mm100, o3tl::Length::twip);
925 
926  aExtraInfo.append(", \"dragDirection\": [");
927  aExtraInfo.append(aDragDirection.toString());
928  aExtraInfo.append("]");
929 
930  // polygon approximating the pie segment or donut segment
931  if (pO->GetObjIdentifier() == OBJ_PATHFILL)
932  {
933  const basegfx::B2DPolyPolygon aPolyPolygon(pO->TakeXorPoly());
934  if (aPolyPolygon.count() == 1)
935  {
936  const basegfx::B2DPolygon aPolygon = aPolyPolygon.getB2DPolygon(0);
937  if (sal_uInt32 nPolySize = aPolygon.count())
938  {
939  const OutputDevice* pOut = this->GetFirstOutputDevice();
940  const vcl::Window* pWin = pOut ? pOut->GetOwnerWindow() : nullptr;
941  const vcl::Window* pViewShellWindow = pViewShell->GetEditWindowForActiveOLEObj();
942  if (pWin && pViewShellWindow && pViewShellWindow->IsAncestorOf(*pWin))
943  {
944  // in the following code escaping sequences used inside raw literal strings
945  // are for making them understandable by the JSON parser
946 
947  Point aOffsetPx = pWin->GetOffsetPixelFrom(*pViewShellWindow);
948  Point aLogicOffset = pWin->PixelToLogic(aOffsetPx);
949  OString sPolygonElem("<polygon points=\\\"");
950  for (sal_uInt32 nIndex = 0; nIndex < nPolySize; ++nIndex)
951  {
952  const basegfx::B2DPoint aB2Point = aPolygon.getB2DPoint(nIndex);
953  Point aPoint(aB2Point.getX(), aB2Point.getY());
954  aPoint.Move(aLogicOffset.getX(), aLogicOffset.getY());
955  if (nIndex > 0)
956  sPolygonElem += " ";
957  sPolygonElem += aPoint.toString();
958  }
959  sPolygonElem += R"elem(\" style=\"stroke: none; fill: rgb(114,159,207); fill-opacity: 0.8\"/>)elem";
960 
961  OString sSVGElem = R"elem(<svg version=\"1.2\" width=\")elem" +
962  OString::number(aSelection.GetWidth() / 100.0) +
963  R"elem(mm\" height=\")elem" +
964  OString::number(aSelection.GetHeight() / 100.0) +
965  R"elem(mm\" viewBox=\")elem" +
966  aSelection.toString() +
967  R"elem(\" preserveAspectRatio=\"xMidYMid\" xmlns=\"http://www.w3.org/2000/svg\">)elem";
968 
969  aExtraInfo.append(", \"svg\": \"");
970  aExtraInfo.append(sSVGElem);
971  aExtraInfo.append("\\n ");
972  aExtraInfo.append(sPolygonElem);
973  aExtraInfo.append("\\n</svg>");
974  aExtraInfo.append("\""); // svg
975  }
976  }
977  }
978  }
979  aExtraInfo.append("}"); // dragInfo
980  }
981  }
982  }
983  }
984  }
985  if (!bTableSelection && !pOtherShell && maHdlList.GetHdlCount())
986  {
987  boost::property_tree::ptree responseJSON;
988  boost::property_tree::ptree others;
989  boost::property_tree::ptree anchor;
990  boost::property_tree::ptree rectangle;
991  boost::property_tree::ptree poly;
992  boost::property_tree::ptree custom;
993  boost::property_tree::ptree nodes;
994  for (size_t i = 0; i < maHdlList.GetHdlCount(); i++)
995  {
996  SdrHdl *pHdl = maHdlList.GetHdl(i);
997  boost::property_tree::ptree child;
998  boost::property_tree::ptree point;
999  sal_Int32 kind = static_cast<sal_Int32>(pHdl->GetKind());
1000  child.put("id", pHdl->GetObjHdlNum());
1001  child.put("kind", kind);
1002  child.put("pointer", static_cast<sal_Int32>(pHdl->GetPointer()));
1003  Point pHdlPos = pHdl->GetPos();
1004  pHdlPos.Move(addLogicOffset.getX(), addLogicOffset.getY());
1005  if (convertMapMode)
1006  {
1008  }
1009  point.put("x", pHdlPos.getX());
1010  point.put("y", pHdlPos.getY());
1011  child.add_child("point", point);
1012  const auto node = std::make_pair("", child);
1013  boost::property_tree::ptree* selectedNode = nullptr;
1014  if (kind >= static_cast<sal_Int32>(SdrHdlKind::UpperLeft) && kind <= static_cast<sal_Int32>(SdrHdlKind::LowerRight))
1015  {
1016  selectedNode = &rectangle;
1017  }
1018  else if (kind == static_cast<sal_Int32>(SdrHdlKind::Poly))
1019  {
1020  selectedNode = &poly;
1021  }
1022  else if (kind == static_cast<sal_Int32>(SdrHdlKind::CustomShape1))
1023  {
1024  selectedNode = &custom;
1025  }
1026  else if (kind == static_cast<sal_Int32>(SdrHdlKind::Anchor) || kind == static_cast<sal_Int32>(SdrHdlKind::Anchor_TR))
1027  {
1028  if (getSdrModelFromSdrView().IsWriter())
1029  selectedNode = &anchor;
1030  else
1031  // put it to others as we don't render them except in writer
1032  selectedNode = &others;
1033  }
1034  else
1035  {
1036  selectedNode = &others;
1037  }
1038  std::string sKind = std::to_string(kind);
1039  boost::optional< boost::property_tree::ptree& > kindNode = selectedNode->get_child_optional(sKind.c_str());
1040  if (!kindNode)
1041  {
1042  boost::property_tree::ptree newChild;
1043  newChild.push_back(node);
1044  selectedNode->add_child(sKind.c_str(), newChild);
1045  }
1046  else
1047  kindNode.get().push_back(node);
1048  }
1049  nodes.add_child("rectangle", rectangle);
1050  nodes.add_child("poly", poly);
1051  nodes.add_child("custom", custom);
1052  nodes.add_child("anchor", anchor);
1053  nodes.add_child("others", others);
1054  responseJSON.add_child("kinds", nodes);
1055  std::stringstream aStream;
1056  boost::property_tree::write_json(aStream, responseJSON, /*pretty=*/ false);
1057  handleArrayStr = ", \"handles\":";
1058  handleArrayStr = handleArrayStr + aStream.str().c_str();
1059  if (bConnectorSelection)
1060  {
1061  aStream.str("");
1062  boost::property_tree::write_json(aStream, aGluePointsTree, /*pretty=*/ false);
1063  handleArrayStr = handleArrayStr + ", \"GluePoints\":";
1064  handleArrayStr = handleArrayStr + aStream.str().c_str();
1065  }
1066  }
1067  sSelectionText = aSelection.toString() +
1068  ", " + OString::number(nRotAngle.get());
1069  if (!aExtraInfo.isEmpty())
1070  {
1071  sSelectionTextView = sSelectionText + ", " + aExtraInfo.toString() + "}";
1072  aExtraInfo.append(handleArrayStr);
1073  aExtraInfo.append("}");
1074  sSelectionText += ", " + aExtraInfo.makeStringAndClear();
1075  }
1076  }
1077 
1078  if (sSelectionText.isEmpty())
1079  {
1080  sSelectionText = "EMPTY";
1081  sSelectionTextView = "EMPTY";
1082  }
1083 
1084  if (bTableSelection)
1085  {
1086  boost::property_tree::ptree aTableRectangle;
1087  aTableRectangle.put("x", aSelection.Left());
1088  aTableRectangle.put("y", aSelection.Top());
1089  aTableRectangle.put("width", aSelection.GetWidth());
1090  aTableRectangle.put("height", aSelection.GetHeight());
1091  aTableJsonTree.push_back(std::make_pair("rectangle", aTableRectangle));
1092 
1093  std::stringstream aStream;
1094  boost::property_tree::write_json(aStream, aTableJsonTree);
1095  pViewShell->libreOfficeKitViewCallback(LOK_CALLBACK_TABLE_SELECTED, aStream.str().c_str());
1096  }
1097  else if (!getSdrModelFromSdrView().IsWriter())
1098  {
1099  pViewShell->libreOfficeKitViewCallback(LOK_CALLBACK_TABLE_SELECTED, "{}");
1100  }
1101 
1102  if (pOtherShell)
1103  {
1104  // Another shell wants to know about our existing
1105  // selection.
1106  if (pViewShell != pOtherShell)
1107  SfxLokHelper::notifyOtherView(pViewShell, pOtherShell, LOK_CALLBACK_GRAPHIC_VIEW_SELECTION, "selection", sSelectionTextView);
1108  }
1109  else
1110  {
1111  // We have a new selection, so both pViewShell and the
1112  // other views want to know about it.
1113  pViewShell->libreOfficeKitViewCallback(LOK_CALLBACK_GRAPHIC_SELECTION, sSelectionText.getStr());
1114  SfxLokHelper::notifyOtherViews(pViewShell, LOK_CALLBACK_GRAPHIC_VIEW_SELECTION, "selection", sSelectionTextView);
1115  }
1116  }
1117 }
1118 
1120 {
1121  // remember old focus handle values to search for it again
1122  const SdrHdl* pSaveOldFocusHdl = maHdlList.GetFocusHdl();
1123  bool bSaveOldFocus(false);
1124  sal_uInt32 nSavePolyNum(0), nSavePointNum(0);
1125  SdrHdlKind eSaveKind(SdrHdlKind::Move);
1126  SdrObject* pSaveObj = nullptr;
1127 
1129 
1130  if(pSaveOldFocusHdl
1131  && pSaveOldFocusHdl->GetObj()
1132  && dynamic_cast<const SdrPathObj*>(pSaveOldFocusHdl->GetObj()) != nullptr
1133  && (pSaveOldFocusHdl->GetKind() == SdrHdlKind::Poly || pSaveOldFocusHdl->GetKind() == SdrHdlKind::BezierWeight))
1134  {
1135  bSaveOldFocus = true;
1136  nSavePolyNum = pSaveOldFocusHdl->GetPolyNum();
1137  nSavePointNum = pSaveOldFocusHdl->GetPointNum();
1138  pSaveObj = pSaveOldFocusHdl->GetObj();
1139  eSaveKind = pSaveOldFocusHdl->GetKind();
1140  }
1141 
1142  // delete/clear all handles. This will always be done, even with areMarkHandlesHidden()
1143  maHdlList.Clear();
1146  mpMarkedObj=nullptr;
1147  mpMarkedPV=nullptr;
1148 
1149  // are handles enabled at all? Create only then
1150  if(areMarkHandlesHidden())
1151  return;
1152 
1153  // There can be multiple mark views, but we're only interested in the one that has a window associated.
1155 
1156  const size_t nMarkCount=GetMarkedObjectCount();
1157  bool bStdDrag=meDragMode==SdrDragMode::Move;
1158  bool bSingleTextObjMark=false;
1159  bool bLimitedRotation(false);
1160 
1161  if (nMarkCount==1)
1162  {
1164 
1165  if(nullptr != mpMarkedObj)
1166  {
1167  bSingleTextObjMark =
1168  dynamic_cast<const SdrTextObj*>( mpMarkedObj) != nullptr &&
1169  static_cast<SdrTextObj*>(mpMarkedObj)->IsTextFrame();
1170 
1171  // RotGrfFlyFrame: we may have limited rotation
1172  bLimitedRotation = SdrDragMode::Rotate == meDragMode && mpMarkedObj->HasLimitedRotation();
1173  }
1174  }
1175 
1176  bool bFrmHdl=ImpIsFrameHandles();
1177 
1178  if (nMarkCount>0)
1179  {
1181 
1182  for (size_t nMarkNum=0; nMarkNum<nMarkCount && (mpMarkedPV!=nullptr || !bFrmHdl); ++nMarkNum)
1183  {
1184  const SdrMark* pM=GetSdrMarkByIndex(nMarkNum);
1185 
1186  if (mpMarkedPV!=pM->GetPageView())
1187  {
1188  mpMarkedPV=nullptr;
1189  }
1190  }
1191  }
1192 
1193  SfxViewShell* pViewShell = GetSfxViewShell();
1194 
1195  // check if text edit or ole is active and handles need to be suppressed. This may be the case
1196  // when a single object is selected
1197  // Using a strict return statement is okay here; no handles means *no* handles.
1198  if(mpMarkedObj)
1199  {
1200  // formerly #i33755#: If TextEdit is active the EditEngine will directly paint
1201  // to the window, so suppress Overlay and handles completely; a text frame for
1202  // the active text edit will be painted by the repaint mechanism in
1203  // SdrObjEditView::ImpPaintOutlinerView in this case. This needs to be reworked
1204  // in the future
1205  // Also formerly #122142#: Pretty much the same for SdrCaptionObj's in calc.
1206  if(static_cast<SdrView*>(this)->IsTextEdit())
1207  {
1208  const SdrTextObj* pSdrTextObj = dynamic_cast< const SdrTextObj* >(mpMarkedObj);
1209 
1210  if (pSdrTextObj && pSdrTextObj->IsInEditMode())
1211  {
1212  if (!bTiledRendering)
1213  return;
1214  }
1215  }
1216 
1217  // formerly #i118524#: if inplace activated OLE is selected, suppress handles
1218  const SdrOle2Obj* pSdrOle2Obj = dynamic_cast< const SdrOle2Obj* >(mpMarkedObj);
1219 
1220  if(pSdrOle2Obj && (pSdrOle2Obj->isInplaceActive() || pSdrOle2Obj->isUiActive()))
1221  {
1222  return;
1223  }
1224 
1225  if (!maSubSelectionList.empty())
1226  {
1227  mpMarkingSubSelectionOverlay = std::make_unique<MarkingSubSelectionOverlay>(*this, maSubSelectionList);
1228  }
1229  }
1230 
1232 
1233  if (bFrmHdl)
1234  {
1235  if(!aRect.IsEmpty())
1236  {
1237  // otherwise nothing is found
1238  const size_t nSiz0(maHdlList.GetHdlCount());
1239 
1240  if( bSingleTextObjMark )
1241  {
1243  }
1244  else
1245  {
1246  const bool bWdt0(aRect.Left() == aRect.Right());
1247  const bool bHgt0(aRect.Top() == aRect.Bottom());
1248 
1249  if (bWdt0 && bHgt0)
1250  {
1251  maHdlList.AddHdl(std::make_unique<SdrHdl>(aRect.TopLeft(), SdrHdlKind::UpperLeft));
1252  }
1253  else if (!bStdDrag && (bWdt0 || bHgt0))
1254  {
1255  maHdlList.AddHdl(std::make_unique<SdrHdl>(aRect.TopLeft(), SdrHdlKind::UpperLeft));
1256  maHdlList.AddHdl(std::make_unique<SdrHdl>(aRect.BottomRight(), SdrHdlKind::LowerRight));
1257  }
1258  else
1259  {
1260  if (!bWdt0 && !bHgt0)
1261  {
1262  maHdlList.AddHdl(std::make_unique<SdrHdl>(aRect.TopLeft(), SdrHdlKind::UpperLeft));
1263  }
1264 
1265  if (!bLimitedRotation && !bHgt0)
1266  {
1267  maHdlList.AddHdl(std::make_unique<SdrHdl>(aRect.TopCenter(), SdrHdlKind::Upper));
1268  }
1269 
1270  if (!bWdt0 && !bHgt0)
1271  {
1272  maHdlList.AddHdl(std::make_unique<SdrHdl>(aRect.TopRight(), SdrHdlKind::UpperRight));
1273  }
1274 
1275  if (!bLimitedRotation && !bWdt0)
1276  {
1277  maHdlList.AddHdl(std::make_unique<SdrHdl>(aRect.LeftCenter(), SdrHdlKind::Left ));
1278  maHdlList.AddHdl(std::make_unique<SdrHdl>(aRect.RightCenter(), SdrHdlKind::Right));
1279  }
1280 
1281  if (!bWdt0 && !bHgt0)
1282  {
1283  maHdlList.AddHdl(std::make_unique<SdrHdl>(aRect.BottomLeft(), SdrHdlKind::LowerLeft));
1284  }
1285 
1286  if (!bLimitedRotation && !bHgt0)
1287  {
1288  maHdlList.AddHdl(std::make_unique<SdrHdl>(aRect.BottomCenter(), SdrHdlKind::Lower));
1289  }
1290 
1291  if (!bWdt0 && !bHgt0)
1292  {
1293  maHdlList.AddHdl(std::make_unique<SdrHdl>(aRect.BottomRight(), SdrHdlKind::LowerRight));
1294  }
1295  }
1296  }
1297 
1298  const size_t nSiz1(maHdlList.GetHdlCount());
1299 
1300  // moved setting the missing parameters at SdrHdl here from the
1301  // single loop above (bSingleTextObjMark), this was missing all
1302  // the time. Setting SdrObject is now required to correctly get
1303  // the View-Dependent evtl. GridOffset adapted
1304  for (size_t i=nSiz0; i<nSiz1; ++i)
1305  {
1306  SdrHdl* pHdl=maHdlList.GetHdl(i);
1307  pHdl->SetObj(mpMarkedObj);
1308  pHdl->SetPageView(mpMarkedPV);
1309  pHdl->SetObjHdlNum(sal_uInt16(i-nSiz0));
1310  }
1311  }
1312  }
1313  else
1314  {
1315  bool bDone(false);
1316 
1317  // moved crop handling to non-frame part and the handle creation to SdrGrafObj
1318  if(1 == nMarkCount && mpMarkedObj && SdrDragMode::Crop == meDragMode)
1319  {
1320  // Default addCropHandles from SdrObject does nothing. When pMarkedObj is SdrGrafObj, previous
1321  // behaviour occurs (code in svx/source/svdraw/svdograf.cxx). When pMarkedObj is SwVirtFlyDrawObj
1322  // writer takes the responsibility of adding handles (code in sw/source/core/draw/dflyobj.cxx)
1323  const size_t nSiz0(maHdlList.GetHdlCount());
1325  const size_t nSiz1(maHdlList.GetHdlCount());
1326 
1327  // Was missing: Set infos at SdrCropHdl
1328  for (size_t i=nSiz0; i<nSiz1; ++i)
1329  {
1330  SdrHdl* pHdl=maHdlList.GetHdl(i);
1331  pHdl->SetObj(mpMarkedObj);
1332  pHdl->SetPageView(mpMarkedPV);
1333  pHdl->SetObjHdlNum(sal_uInt16(i-nSiz0));
1334  }
1335 
1336  bDone = true;
1337  }
1338 
1339  if(!bDone)
1340  {
1341  for (size_t nMarkNum=0; nMarkNum<nMarkCount; ++nMarkNum)
1342  {
1343  const SdrMark* pM=GetSdrMarkByIndex(nMarkNum);
1344  SdrObject* pObj=pM->GetMarkedSdrObj();
1345  SdrPageView* pPV=pM->GetPageView();
1346  const size_t nSiz0=maHdlList.GetHdlCount();
1347  pObj->AddToHdlList(maHdlList);
1348  const size_t nSiz1=maHdlList.GetHdlCount();
1349  bool bPoly=pObj->IsPolyObj();
1350  const SdrUShortCont& rMrkPnts = pM->GetMarkedPoints();
1351  for (size_t i=nSiz0; i<nSiz1; ++i)
1352  {
1353  SdrHdl* pHdl=maHdlList.GetHdl(i);
1354  pHdl->SetObj(pObj);
1355  pHdl->SetPageView(pPV);
1356  pHdl->SetObjHdlNum(sal_uInt16(i-nSiz0));
1357 
1358  if (bPoly)
1359  {
1360  bool bSelected= rMrkPnts.find( sal_uInt16(i-nSiz0) ) != rMrkPnts.end();
1361  pHdl->SetSelected(bSelected);
1362  if (mbPlusHdlAlways || bSelected)
1363  {
1364  SdrHdlList plusList(nullptr);
1365  pObj->AddToPlusHdlList(plusList, *pHdl);
1366  sal_uInt32 nPlusHdlCnt=plusList.GetHdlCount();
1367  for (sal_uInt32 nPlusNum=0; nPlusNum<nPlusHdlCnt; nPlusNum++)
1368  {
1369  SdrHdl* pPlusHdl=plusList.GetHdl(nPlusNum);
1370  pPlusHdl->SetObj(pObj);
1371  pPlusHdl->SetPageView(pPV);
1372  pPlusHdl->SetPlusHdl(true);
1373  }
1374  plusList.MoveTo(maHdlList);
1375  }
1376  }
1377  }
1378  }
1379  }
1380  }
1381 
1382  // GluePoint handles
1383  for (size_t nMarkNum=0; nMarkNum<nMarkCount; ++nMarkNum)
1384  {
1385  const SdrMark* pM=GetSdrMarkByIndex(nMarkNum);
1386  SdrObject* pObj=pM->GetMarkedSdrObj();
1387  const SdrGluePointList* pGPL=pObj->GetGluePointList();
1388  if (!pGPL)
1389  continue;
1390 
1391  SdrPageView* pPV=pM->GetPageView();
1392  const SdrUShortCont& rMrkGlue=pM->GetMarkedGluePoints();
1393  for (sal_uInt16 nId : rMrkGlue)
1394  {
1395  //nNum changed to nNumGP because already used in for loop
1396  sal_uInt16 nNumGP=pGPL->FindGluePoint(nId);
1397  if (nNumGP!=SDRGLUEPOINT_NOTFOUND)
1398  {
1399  const SdrGluePoint& rGP=(*pGPL)[nNumGP];
1400  Point aPos(rGP.GetAbsolutePos(*pObj));
1401  std::unique_ptr<SdrHdl> pGlueHdl(new SdrHdl(aPos,SdrHdlKind::Glue));
1402  pGlueHdl->SetObj(pObj);
1403  pGlueHdl->SetPageView(pPV);
1404  pGlueHdl->SetObjHdlNum(nId);
1405  maHdlList.AddHdl(std::move(pGlueHdl));
1406  }
1407  }
1408  }
1409 
1410  // rotation point/axis of reflection
1411  if(!bLimitedRotation)
1412  {
1414  }
1415 
1416  // sort handles
1417  maHdlList.Sort();
1418 
1419  // add custom handles (used by other apps, e.g. AnchorPos)
1420  AddCustomHdl();
1421 
1422  // moved it here to access all the handles for callback.
1423  if (bTiledRendering && pViewShell)
1424  {
1425  SetMarkHandlesForLOKit(aRect, pOtherShell);
1426  }
1427 
1428  // try to restore focus handle index from remembered values
1429  if(!bSaveOldFocus)
1430  return;
1431 
1432  for(size_t a = 0; a < maHdlList.GetHdlCount(); ++a)
1433  {
1434  SdrHdl* pCandidate = maHdlList.GetHdl(a);
1435 
1436  if(pCandidate->GetObj()
1437  && pCandidate->GetObj() == pSaveObj
1438  && pCandidate->GetKind() == eSaveKind
1439  && pCandidate->GetPolyNum() == nSavePolyNum
1440  && pCandidate->GetPointNum() == nSavePointNum)
1441  {
1442  maHdlList.SetFocusHdl(pCandidate);
1443  break;
1444  }
1445  }
1446 }
1447 
1449 {
1450  // add custom handles (used by other apps, e.g. AnchorPos)
1451 }
1452 
1454 {
1455  SdrDragMode eMode0=meDragMode;
1456  meDragMode=eMode;
1458  if (meDragMode!=eMode0) {
1459  ForceRefToMarked();
1460  SetMarkHandles(nullptr);
1461  {
1463  }
1464  }
1465 }
1466 
1468 {
1469  switch(eMode)
1470  {
1471  case SdrDragMode::Rotate:
1472  {
1473  // add rotation center
1474  maHdlList.AddHdl(std::make_unique<SdrHdl>(maRef1, SdrHdlKind::Ref1));
1475  break;
1476  }
1477  case SdrDragMode::Mirror:
1478  {
1479  // add axis of reflection
1480  std::unique_ptr<SdrHdl> pHdl3(new SdrHdl(maRef2, SdrHdlKind::Ref2));
1481  std::unique_ptr<SdrHdl> pHdl2(new SdrHdl(maRef1, SdrHdlKind::Ref1));
1482  std::unique_ptr<SdrHdl> pHdl1(new SdrHdlLine(*pHdl2, *pHdl3, SdrHdlKind::MirrorAxis));
1483 
1484  pHdl1->SetObjHdlNum(1); // for sorting
1485  pHdl2->SetObjHdlNum(2); // for sorting
1486  pHdl3->SetObjHdlNum(3); // for sorting
1487 
1488  maHdlList.AddHdl(std::move(pHdl1)); // line comes first, so it is the last in HitTest
1489  maHdlList.AddHdl(std::move(pHdl2));
1490  maHdlList.AddHdl(std::move(pHdl3));
1491 
1492  break;
1493  }
1495  {
1496  // add interactive transparency handle
1497  const size_t nMarkCount = GetMarkedObjectCount();
1498  if(nMarkCount == 1)
1499  {
1500  SdrObject* pObj = GetMarkedObjectByIndex(0);
1501  SdrModel* pModel = GetModel();
1502  const SfxItemSet& rSet = pObj->GetMergedItemSet();
1503 
1504  if(SfxItemState::SET != rSet.GetItemState(XATTR_FILLFLOATTRANSPARENCE, false))
1505  {
1506  // add this item, it's not yet there
1508  XGradient aGrad = aNewItem.GetGradientValue();
1509 
1510  aNewItem.SetEnabled(true);
1511  aGrad.SetStartIntens(100);
1512  aGrad.SetEndIntens(100);
1513  aNewItem.SetGradientValue(aGrad);
1514 
1515  // add undo to allow user to take back this step
1516  if( pModel->IsUndoEnabled() )
1517  {
1518  pModel->BegUndo(SvxResId(SIP_XA_FILLTRANSPARENCE));
1519  pModel->AddUndo(pModel->GetSdrUndoFactory().CreateUndoAttrObject(*pObj));
1520  pModel->EndUndo();
1521  }
1522 
1523  SfxItemSet aNewSet(pModel->GetItemPool());
1524  aNewSet.Put(aNewItem);
1525  pObj->SetMergedItemSetAndBroadcast(aNewSet);
1526  }
1527 
1528  // set values and transform to vector set
1529  GradTransVector aGradTransVector;
1530  GradTransGradient aGradTransGradient;
1531 
1532  aGradTransGradient.aGradient = rSet.Get(XATTR_FILLFLOATTRANSPARENCE).GetGradientValue();
1533  GradTransformer::GradToVec(aGradTransGradient, aGradTransVector, pObj);
1534 
1535  // build handles
1536  const Point aTmpPos1(basegfx::fround(aGradTransVector.maPositionA.getX()), basegfx::fround(aGradTransVector.maPositionA.getY()));
1537  const Point aTmpPos2(basegfx::fround(aGradTransVector.maPositionB.getX()), basegfx::fround(aGradTransVector.maPositionB.getY()));
1538  std::unique_ptr<SdrHdlColor> pColHdl1(new SdrHdlColor(aTmpPos1, aGradTransVector.aCol1, SDR_HANDLE_COLOR_SIZE_NORMAL, true));
1539  std::unique_ptr<SdrHdlColor> pColHdl2(new SdrHdlColor(aTmpPos2, aGradTransVector.aCol2, SDR_HANDLE_COLOR_SIZE_NORMAL, true));
1540  std::unique_ptr<SdrHdlGradient> pGradHdl(new SdrHdlGradient(aTmpPos1, aTmpPos2, false));
1541  DBG_ASSERT(pColHdl1 && pColHdl2 && pGradHdl, "Could not get all necessary handles!");
1542 
1543  // link them
1544  pGradHdl->SetColorHandles(pColHdl1.get(), pColHdl2.get());
1545  pGradHdl->SetObj(pObj);
1546  pColHdl1->SetColorChangeHdl(LINK(pGradHdl.get(), SdrHdlGradient, ColorChangeHdl));
1547  pColHdl2->SetColorChangeHdl(LINK(pGradHdl.get(), SdrHdlGradient, ColorChangeHdl));
1548 
1549  // insert them
1550  maHdlList.AddHdl(std::move(pColHdl1));
1551  maHdlList.AddHdl(std::move(pColHdl2));
1552  maHdlList.AddHdl(std::move(pGradHdl));
1553  }
1554  break;
1555  }
1556  case SdrDragMode::Gradient:
1557  {
1558  // add interactive gradient handle
1559  const size_t nMarkCount = GetMarkedObjectCount();
1560  if(nMarkCount == 1)
1561  {
1562  SdrObject* pObj = GetMarkedObjectByIndex(0);
1563  const SfxItemSet& rSet = pObj->GetMergedItemSet();
1564  drawing::FillStyle eFillStyle = rSet.Get(XATTR_FILLSTYLE).GetValue();
1565 
1566  if(eFillStyle == drawing::FillStyle_GRADIENT)
1567  {
1568  // set values and transform to vector set
1569  GradTransVector aGradTransVector;
1570  GradTransGradient aGradTransGradient;
1571  Size aHdlSize(15, 15);
1572 
1573  aGradTransGradient.aGradient = rSet.Get(XATTR_FILLGRADIENT).GetGradientValue();
1574  GradTransformer::GradToVec(aGradTransGradient, aGradTransVector, pObj);
1575 
1576  // build handles
1577  const Point aTmpPos1(basegfx::fround(aGradTransVector.maPositionA.getX()), basegfx::fround(aGradTransVector.maPositionA.getY()));
1578  const Point aTmpPos2(basegfx::fround(aGradTransVector.maPositionB.getX()), basegfx::fround(aGradTransVector.maPositionB.getY()));
1579  std::unique_ptr<SdrHdlColor> pColHdl1(new SdrHdlColor(aTmpPos1, aGradTransVector.aCol1, aHdlSize, false));
1580  std::unique_ptr<SdrHdlColor> pColHdl2(new SdrHdlColor(aTmpPos2, aGradTransVector.aCol2, aHdlSize, false));
1581  std::unique_ptr<SdrHdlGradient> pGradHdl(new SdrHdlGradient(aTmpPos1, aTmpPos2, true));
1582  DBG_ASSERT(pColHdl1 && pColHdl2 && pGradHdl, "Could not get all necessary handles!");
1583 
1584  // link them
1585  pGradHdl->SetColorHandles(pColHdl1.get(), pColHdl2.get());
1586  pGradHdl->SetObj(pObj);
1587  pColHdl1->SetColorChangeHdl(LINK(pGradHdl.get(), SdrHdlGradient, ColorChangeHdl));
1588  pColHdl2->SetColorChangeHdl(LINK(pGradHdl.get(), SdrHdlGradient, ColorChangeHdl));
1589 
1590  // insert them
1591  maHdlList.AddHdl(std::move(pColHdl1));
1592  maHdlList.AddHdl(std::move(pColHdl2));
1593  maHdlList.AddHdl(std::move(pGradHdl));
1594  }
1595  }
1596  break;
1597  }
1598  case SdrDragMode::Crop:
1599  {
1600  // TODO
1601  break;
1602  }
1603  default: break;
1604  }
1605 }
1606 
1609 {
1610  if(maHdlList.GetHdlCount())
1611  {
1612  SdrHdl* pMouseOverHdl = nullptr;
1613  if( !rMEvt.IsLeaveWindow() && pWin )
1614  {
1615  Point aMDPos( pWin->PixelToLogic( rMEvt.GetPosPixel() ) );
1616  pMouseOverHdl = PickHandle(aMDPos);
1617  }
1618 
1619  // notify last mouse over handle that he lost the mouse
1620  const size_t nHdlCount = maHdlList.GetHdlCount();
1621 
1622  for(size_t nHdl = 0; nHdl < nHdlCount; ++nHdl)
1623  {
1624  SdrHdl* pCurrentHdl = GetHdl(nHdl);
1625  if( pCurrentHdl->mbMouseOver )
1626  {
1627  if( pCurrentHdl != pMouseOverHdl )
1628  {
1629  pCurrentHdl->mbMouseOver = false;
1630  pCurrentHdl->onMouseLeave();
1631  }
1632  break;
1633  }
1634  }
1635 
1636  // notify current mouse over handle
1637  if( pMouseOverHdl )
1638  {
1639  pMouseOverHdl->mbMouseOver = true;
1640  pMouseOverHdl->onMouseEnter(rMEvt);
1641  }
1642  }
1643  return SdrSnapView::MouseMove(rMEvt, pWin);
1644 }
1645 
1647 {
1648  if (maHdlList.GetHdlCount())
1649  {
1650  const size_t nHdlCount = maHdlList.GetHdlCount();
1651 
1652  for (size_t nHdl = 0; nHdl < nHdlCount; ++nHdl)
1653  {
1654  SdrHdl* pCurrentHdl = GetHdl(nHdl);
1655  if (pCurrentHdl->mbMouseOver)
1656  {
1657  pCurrentHdl->onHelpRequest();
1658  return true;
1659  }
1660  }
1661  }
1662  return SdrSnapView::RequestHelp(rHEvt);
1663 }
1664 
1666 {
1667  switch(meDragMode)
1668  {
1669  case SdrDragMode::Rotate:
1670  {
1672  maRef1 = aR.Center();
1673 
1674  break;
1675  }
1676 
1677  case SdrDragMode::Mirror:
1678  {
1679  // first calculate the length of the axis of reflection
1680  tools::Long nOutMin=0;
1681  tools::Long nOutMax=0;
1682  tools::Long nMinLen=0;
1683  tools::Long nObjDst=0;
1684  tools::Long nOutHgt=0;
1686  if (pOut!=nullptr) {
1687  // minimum length: 50 pixels
1688  nMinLen=pOut->PixelToLogic(Size(0,50)).Height();
1689  // 20 pixels distance to the Obj for the reference point
1690  nObjDst=pOut->PixelToLogic(Size(0,20)).Height();
1691  // MinY/MaxY
1692  // margin = minimum length = 10 pixels
1693  tools::Long nDst=pOut->PixelToLogic(Size(0,10)).Height();
1694  nOutMin=-pOut->GetMapMode().GetOrigin().Y();
1695  nOutMax=pOut->GetOutputSize().Height()-1+nOutMin;
1696  nOutMin+=nDst;
1697  nOutMax-=nDst;
1698  // absolute minimum length, however, is 10 pixels
1699  if (nOutMax-nOutMin<nDst) {
1700  nOutMin+=nOutMax+1;
1701  nOutMin/=2;
1702  nOutMin-=(nDst+1)/2;
1703  nOutMax=nOutMin+nDst;
1704  }
1705  nOutHgt=nOutMax-nOutMin;
1706  // otherwise minimum length = 1/4 OutHgt
1707  tools::Long nTemp=nOutHgt/4;
1708  if (nTemp>nMinLen) nMinLen=nTemp;
1709  }
1710 
1712  Point aCenter(aR.Center());
1713  tools::Long nMarkHgt=aR.GetHeight()-1;
1714  tools::Long nHgt=nMarkHgt+nObjDst*2; // 20 pixels overlapping above and below
1715  if (nHgt<nMinLen) nHgt=nMinLen; // minimum length 50 pixels or 1/4 OutHgt, respectively
1716 
1717  tools::Long nY1=aCenter.Y()-(nHgt+1)/2;
1718  tools::Long nY2=nY1+nHgt;
1719 
1720  if (pOut!=nullptr && nMinLen>nOutHgt) nMinLen=nOutHgt; // TODO: maybe shorten this a little
1721 
1722  if (pOut!=nullptr) { // now move completely into the visible area
1723  if (nY1<nOutMin) {
1724  nY1=nOutMin;
1725  if (nY2<nY1+nMinLen) nY2=nY1+nMinLen;
1726  }
1727  if (nY2>nOutMax) {
1728  nY2=nOutMax;
1729  if (nY1>nY2-nMinLen) nY1=nY2-nMinLen;
1730  }
1731  }
1732 
1733  maRef1.setX(aCenter.X() );
1734  maRef1.setY(nY1 );
1735  maRef2.setX(aCenter.X() );
1736  maRef2.setY(nY2 );
1737 
1738  break;
1739  }
1740 
1742  case SdrDragMode::Gradient:
1743  case SdrDragMode::Crop:
1744  {
1746  maRef1 = aRect.TopLeft();
1747  maRef2 = aRect.BottomRight();
1748  break;
1749  }
1750  default: break;
1751  }
1752 }
1753 
1754 void SdrMarkView::SetRef1(const Point& rPt)
1755 {
1757  {
1758  maRef1 = rPt;
1760  if(pH)
1761  pH->SetPos(rPt);
1762  }
1763 }
1764 
1765 void SdrMarkView::SetRef2(const Point& rPt)
1766 {
1768  {
1769  maRef2 = rPt;
1771  if(pH)
1772  pH->SetPos(rPt);
1773  }
1774 }
1775 
1777 {
1778  return SfxViewShell::Current();
1779 }
1780 
1782 {
1783  for (size_t nm=GetMarkedObjectCount(); nm>0;) {
1784  --nm;
1785  SdrMark* pM = GetSdrMarkByIndex(nm);
1786  SdrObject* pObj = pM->GetMarkedSdrObj();
1787  SdrPageView* pPV = pM->GetPageView();
1788  bool bRaus = !pObj || !pPV->IsObjMarkable(pObj);
1789  if (bRaus)
1790  {
1792  }
1793  else
1794  {
1795  if (!IsGluePointEditMode()) { // selected gluepoints only in GlueEditMode
1796  SdrUShortCont& rPts = pM->GetMarkedGluePoints();
1797  rPts.clear();
1798  }
1799  }
1800  }
1801 
1802  // at least reset the remembered BoundRect to prevent handle
1803  // generation if bForceFrameHandles is TRUE.
1804  mbMarkedObjRectDirty = true;
1805 }
1806 
1808 {
1809  SdrPageView* pPV = GetSdrPageView();
1810 
1811  if(pPV)
1812  {
1813  pPV->SetHasMarkedObj(GetMarkedObjectList().TakeSnapRect(pPV, pPV->MarkSnap()));
1815  }
1816 }
1817 
1819 {
1820  if (bOn!=mbForceFrameHandles) {
1821  bool bOld=ImpIsFrameHandles();
1822  mbForceFrameHandles=bOn;
1823  bool bNew=ImpIsFrameHandles();
1824  if (bNew!=bOld) {
1825  AdjustMarkHdl();
1827  }
1828  }
1829 }
1830 
1832 {
1833  if (eMode==meEditMode) return;
1834 
1836  bool bEdge0=static_cast<SdrCreateView*>(this)->IsEdgeTool();
1838  meEditMode=eMode;
1840  bool bEdge1=static_cast<SdrCreateView*>(this)->IsEdgeTool();
1841  // avoid flickering when switching between GlueEdit and EdgeTool
1842  if (bGlue1 && !bGlue0) ImpSetGlueVisible2(bGlue1);
1843  if (bEdge1!=bEdge0) ImpSetGlueVisible3(bEdge1);
1844  if (!bGlue1 && bGlue0) ImpSetGlueVisible2(bGlue1);
1845  if (bGlue0 && !bGlue1) UnmarkAllGluePoints();
1846 }
1847 
1848 
1849 bool SdrMarkView::IsObjMarkable(SdrObject const * pObj, SdrPageView const * pPV) const
1850 {
1851  if (pObj)
1852  {
1853  if (pObj->IsMarkProtect() ||
1854  (!mbDesignMode && pObj->IsUnoObj()))
1855  {
1856  // object not selectable or
1857  // SdrUnoObj not in DesignMode
1858  return false;
1859  }
1860  }
1861  return pPV==nullptr || pPV->IsObjMarkable(pObj);
1862 }
1863 
1864 bool SdrMarkView::IsMarkedObjHit(const Point& rPnt, short nTol) const
1865 {
1866  bool bRet=false;
1867  nTol=ImpGetHitTolLogic(nTol,nullptr);
1868  for (size_t nm=0; nm<GetMarkedObjectCount() && !bRet; ++nm) {
1869  SdrMark* pM=GetSdrMarkByIndex(nm);
1870  bRet = nullptr != CheckSingleSdrObjectHit(rPnt,sal_uInt16(nTol),pM->GetMarkedSdrObj(),pM->GetPageView(),SdrSearchOptions::NONE,nullptr);
1871  }
1872  return bRet;
1873 }
1874 
1875 SdrHdl* SdrMarkView::PickHandle(const Point& rPnt) const
1876 {
1877  if (mbSomeObjChgdFlag) { // recalculate handles, if necessary
1879  }
1880  return maHdlList.IsHdlListHit(rPnt);
1881 }
1882 
1883 bool SdrMarkView::MarkObj(const Point& rPnt, short nTol, bool bToggle, bool bDeep)
1884 {
1885  SdrPageView* pPV;
1886  nTol=ImpGetHitTolLogic(nTol,nullptr);
1888  if (bDeep) nOptions=nOptions|SdrSearchOptions::DEEP;
1889  SdrObject* pObj = PickObj(rPnt, static_cast<sal_uInt16>(nTol), pPV, nOptions);
1890  if (pObj) {
1891  bool bUnmark=bToggle && IsObjMarked(pObj);
1892  MarkObj(pObj,pPV,bUnmark);
1893  }
1894  return pObj != nullptr;
1895 }
1896 
1898 {
1899  SdrPageView* pPageView = GetSdrPageView();
1900 
1901  if(!pPageView)
1902  {
1903  return false;
1904  }
1905 
1907  const size_t nMarkCount=GetMarkedObjectCount();
1908  size_t nChgMarkNum = SAL_MAX_SIZE; // number of the MarkEntry we want to replace
1909  size_t nSearchObjNum = bPrev ? 0 : SAL_MAX_SIZE;
1910  if (nMarkCount!=0) {
1911  nChgMarkNum=bPrev ? 0 : nMarkCount-1;
1912  SdrMark* pM=GetSdrMarkByIndex(nChgMarkNum);
1913  OSL_ASSERT(pM!=nullptr);
1914  if (pM->GetMarkedSdrObj() != nullptr)
1915  nSearchObjNum = pM->GetMarkedSdrObj()->GetNavigationPosition();
1916  }
1917 
1918  SdrObject* pMarkObj=nullptr;
1919  SdrObjList* pSearchObjList=pPageView->GetObjList();
1920  const size_t nObjCount = pSearchObjList->GetObjCount();
1921  if (nObjCount!=0) {
1922  if (nSearchObjNum>nObjCount) nSearchObjNum=nObjCount;
1923  while (pMarkObj==nullptr && ((!bPrev && nSearchObjNum>0) || (bPrev && nSearchObjNum<nObjCount)))
1924  {
1925  if (!bPrev)
1926  nSearchObjNum--;
1927  SdrObject* pSearchObj = pSearchObjList->GetObjectForNavigationPosition(nSearchObjNum);
1928  if (IsObjMarkable(pSearchObj,pPageView))
1929  {
1930  if (TryToFindMarkedObject(pSearchObj)==SAL_MAX_SIZE)
1931  {
1932  pMarkObj=pSearchObj;
1933  }
1934  }
1935  if (bPrev) nSearchObjNum++;
1936  }
1937  }
1938 
1939  if(!pMarkObj)
1940  {
1941  return false;
1942  }
1943 
1944  if (nChgMarkNum!=SAL_MAX_SIZE)
1945  {
1947  }
1948  MarkObj(pMarkObj,pPageView); // also calls MarkListHasChanged(), AdjustMarkHdl()
1949  return true;
1950 }
1951 
1952 bool SdrMarkView::MarkNextObj(const Point& rPnt, short nTol, bool bPrev)
1953 {
1955  nTol=ImpGetHitTolLogic(nTol,nullptr);
1956  SdrMark* pTopMarkHit=nullptr;
1957  SdrMark* pBtmMarkHit=nullptr;
1958  size_t nTopMarkHit=0;
1959  size_t nBtmMarkHit=0;
1960  // find topmost of the selected objects that is hit by rPnt
1961  const size_t nMarkCount=GetMarkedObjectCount();
1962  for (size_t nm=nMarkCount; nm>0 && pTopMarkHit==nullptr;) {
1963  --nm;
1964  SdrMark* pM=GetSdrMarkByIndex(nm);
1965  if(CheckSingleSdrObjectHit(rPnt,sal_uInt16(nTol),pM->GetMarkedSdrObj(),pM->GetPageView(),SdrSearchOptions::NONE,nullptr))
1966  {
1967  pTopMarkHit=pM;
1968  nTopMarkHit=nm;
1969  }
1970  }
1971  // nothing found, in this case, just select an object
1972  if (pTopMarkHit==nullptr) return MarkObj(rPnt,sal_uInt16(nTol));
1973 
1974  SdrObject* pTopObjHit=pTopMarkHit->GetMarkedSdrObj();
1975  SdrObjList* pObjList=pTopObjHit->getParentSdrObjListFromSdrObject();
1976  SdrPageView* pPV=pTopMarkHit->GetPageView();
1977  // find lowermost of the selected objects that is hit by rPnt
1978  // and is placed on the same PageView as pTopMarkHit
1979  for (size_t nm=0; nm<nMarkCount && pBtmMarkHit==nullptr; ++nm) {
1980  SdrMark* pM=GetSdrMarkByIndex(nm);
1981  SdrPageView* pPV2=pM->GetPageView();
1982  if (pPV2==pPV && CheckSingleSdrObjectHit(rPnt,sal_uInt16(nTol),pM->GetMarkedSdrObj(),pPV2,SdrSearchOptions::NONE,nullptr))
1983  {
1984  pBtmMarkHit=pM;
1985  nBtmMarkHit=nm;
1986  }
1987  }
1988  if (pBtmMarkHit==nullptr) { pBtmMarkHit=pTopMarkHit; nBtmMarkHit=nTopMarkHit; }
1989  SdrObject* pBtmObjHit=pBtmMarkHit->GetMarkedSdrObj();
1990  const size_t nObjCount = pObjList->GetObjCount();
1991 
1992  size_t nSearchBeg(0);
1993  E3dScene* pScene(nullptr);
1994  SdrObject* pObjHit(bPrev ? pBtmObjHit : pTopObjHit);
1995  bool bRemap =
1996  nullptr != dynamic_cast< const E3dCompoundObject* >(pObjHit);
1997  if (bRemap)
1998  {
1999  pScene = dynamic_cast< E3dScene* >(pObjHit->getParentSdrObjectFromSdrObject());
2000  bRemap = nullptr != pScene;
2001  }
2002 
2003  if(bPrev)
2004  {
2005  sal_uInt32 nOrdNumBtm(pBtmObjHit->GetOrdNum());
2006 
2007  if(bRemap)
2008  {
2009  nOrdNumBtm = pScene->RemapOrdNum(nOrdNumBtm);
2010  }
2011 
2012  nSearchBeg = nOrdNumBtm + 1;
2013  }
2014  else
2015  {
2016  sal_uInt32 nOrdNumTop(pTopObjHit->GetOrdNum());
2017 
2018  if(bRemap)
2019  {
2020  nOrdNumTop = pScene->RemapOrdNum(nOrdNumTop);
2021  }
2022 
2023  nSearchBeg = nOrdNumTop;
2024  }
2025 
2026  size_t no=nSearchBeg;
2027  SdrObject* pFndObj=nullptr;
2028  while (pFndObj==nullptr && ((!bPrev && no>0) || (bPrev && no<nObjCount))) {
2029  if (!bPrev) no--;
2030  SdrObject* pObj;
2031 
2032  if(bRemap)
2033  {
2034  pObj = pObjList->GetObj(pScene->RemapOrdNum(no));
2035  }
2036  else
2037  {
2038  pObj = pObjList->GetObj(no);
2039  }
2040 
2041  if (CheckSingleSdrObjectHit(rPnt,sal_uInt16(nTol),pObj,pPV,SdrSearchOptions::TESTMARKABLE,nullptr))
2042  {
2043  if (TryToFindMarkedObject(pObj)==SAL_MAX_SIZE) {
2044  pFndObj=pObj;
2045  } else {
2046  // TODO: for performance reasons set on to Top or Btm, if necessary
2047  }
2048  }
2049  if (bPrev) no++;
2050  }
2051  if (pFndObj!=nullptr)
2052  {
2053  GetMarkedObjectListWriteAccess().DeleteMark(bPrev?nBtmMarkHit:nTopMarkHit);
2056  AdjustMarkHdl();
2057  }
2058  return pFndObj!=nullptr;
2059 }
2060 
2061 void SdrMarkView::MarkObj(const tools::Rectangle& rRect, bool bUnmark)
2062 {
2063  bool bFnd=false;
2064  tools::Rectangle aR(rRect);
2065  SdrObjList* pObjList;
2066  BrkAction();
2067  SdrPageView* pPV = GetSdrPageView();
2068 
2069  if(pPV)
2070  {
2071  pObjList=pPV->GetObjList();
2072  tools::Rectangle aFrm1(aR);
2073  const size_t nObjCount = pObjList->GetObjCount();
2074  for (size_t nO=0; nO<nObjCount; ++nO) {
2075  SdrObject* pObj=pObjList->GetObj(nO);
2076  tools::Rectangle aRect(pObj->GetCurrentBoundRect());
2077  if (aFrm1.IsInside(aRect)) {
2078  if (!bUnmark) {
2079  if (IsObjMarkable(pObj,pPV))
2080  {
2082  bFnd=true;
2083  }
2084  } else {
2085  const size_t nPos=TryToFindMarkedObject(pObj);
2086  if (nPos!=SAL_MAX_SIZE)
2087  {
2089  bFnd=true;
2090  }
2091  }
2092  }
2093  }
2094  }
2095  if (bFnd) {
2098  AdjustMarkHdl();
2099  }
2100 }
2101 
2102 namespace {
2103 
2104 void collectUIInformation(const SdrObject* pObj)
2105 {
2106  EventDescription aDescription;
2107  aDescription.aAction = "SELECT";
2108  aDescription.aParent = "MainWindow";
2109  aDescription.aKeyWord = "CurrentApp";
2110 
2111  if (!pObj->GetName().isEmpty())
2112  aDescription.aParameters = {{"OBJECT", pObj->GetName()}};
2113  else
2114  aDescription.aParameters = {{"OBJECT", "Unnamed_Obj_" + OUString::number(pObj->GetOrdNum())}};
2115 
2116  UITestLogger::getInstance().logEvent(aDescription);
2117 }
2118 
2119 }
2120 
2121  void SdrMarkView::MarkObj(SdrObject* pObj, SdrPageView* pPV, bool bUnmark, bool bDoNoSetMarkHdl,
2122  std::vector<basegfx::B2DRectangle> const & rSubSelections)
2123 {
2124  if (!(pObj!=nullptr && pPV!=nullptr && IsObjMarkable(pObj, pPV)))
2125  return;
2126 
2127  BrkAction();
2128  if (!bUnmark)
2129  {
2131  collectUIInformation(pObj);
2132  }
2133  else
2134  {
2135  const size_t nPos=TryToFindMarkedObject(pObj);
2136  if (nPos!=SAL_MAX_SIZE)
2137  {
2139  }
2140  }
2141 
2142  maSubSelectionList = rSubSelections;
2143 
2144  if (!bDoNoSetMarkHdl) {
2146  AdjustMarkHdl();
2147  }
2148 }
2149 
2150 bool SdrMarkView::IsObjMarked(SdrObject const * pObj) const
2151 {
2152  return TryToFindMarkedObject(pObj)!=SAL_MAX_SIZE;
2153 }
2154 
2156 {
2157  return maHdlList.GetHdlSize()*2+1;
2158 }
2159 
2161 {
2162  if (nSiz<3) nSiz=3;
2163  nSiz/=2;
2164  if (nSiz!=maHdlList.GetHdlSize()) {
2165  maHdlList.SetHdlSize(nSiz);
2166  }
2167 }
2168 
2170  basegfx::B2DVector& rOffset,
2171  const SdrObject* pObj,
2172  const SdrPageView* pPV) const
2173 {
2174  if(nullptr == pObj || nullptr == pPV)
2175  {
2176  return false;
2177  }
2178 
2179  const OutputDevice* pOutputDevice(GetFirstOutputDevice());
2180 
2181  if(nullptr == pOutputDevice)
2182  {
2183  return false;
2184  }
2185 
2186  const SdrPageWindow* pSdrPageWindow(pPV->FindPageWindow(*pOutputDevice));
2187 
2188  if(nullptr == pSdrPageWindow)
2189  {
2190  return false;
2191  }
2192 
2193  const sdr::contact::ObjectContact& rObjectContact(pSdrPageWindow->GetObjectContact());
2194 
2195  if(!rObjectContact.supportsGridOffsets())
2196  {
2197  return false;
2198  }
2199 
2201  const_cast<sdr::contact::ObjectContact&>(rObjectContact)));
2202 
2203  rOffset = rVOC.getGridOffset();
2204 
2205  return !rOffset.equalZero();
2206 }
2207 
2209  basegfx::B2DVector& rOffset,
2210  const basegfx::B2DPoint& rPoint,
2211  const SdrPageView* pPV) const
2212 {
2213  if(nullptr == pPV)
2214  {
2215  return false;
2216  }
2217 
2218  const OutputDevice* pOutputDevice(GetFirstOutputDevice());
2219 
2220  if(nullptr == pOutputDevice)
2221  {
2222  return false;
2223  }
2224 
2225  const SdrPageWindow* pSdrPageWindow(pPV->FindPageWindow(*pOutputDevice));
2226 
2227  if(nullptr == pSdrPageWindow)
2228  {
2229  return false;
2230  }
2231 
2232  const sdr::contact::ObjectContact& rObjectContact(pSdrPageWindow->GetObjectContact());
2233 
2234  if(!rObjectContact.supportsGridOffsets())
2235  {
2236  return false;
2237  }
2238 
2239  rObjectContact.calculateGridOffsetForB2DRange(rOffset, basegfx::B2DRange(rPoint));
2240 
2241  return !rOffset.equalZero();
2242 }
2243 
2244 SdrObject* SdrMarkView::CheckSingleSdrObjectHit(const Point& rPnt, sal_uInt16 nTol, SdrObject* pObj, SdrPageView* pPV, SdrSearchOptions nOptions, const SdrLayerIDSet* pMVisLay) const
2245 {
2246  if(((nOptions & SdrSearchOptions::IMPISMASTER) && pObj->IsNotVisibleAsMaster()) || (!pObj->IsVisible()))
2247  {
2248  return nullptr;
2249  }
2250 
2251  const bool bCheckIfMarkable(nOptions & SdrSearchOptions::TESTMARKABLE);
2252  const bool bDeep(nOptions & SdrSearchOptions::DEEP);
2253  const bool bOLE(dynamic_cast< const SdrOle2Obj* >(pObj) != nullptr);
2254  auto pTextObj = dynamic_cast<const SdrTextObj*>( pObj);
2255  const bool bTXT(pTextObj && pTextObj->IsTextFrame());
2256  SdrObject* pRet=nullptr;
2257  tools::Rectangle aRect(pObj->GetCurrentBoundRect());
2258 
2259  // add possible GridOffset to up-to-now view-independent BoundRect data
2260  basegfx::B2DVector aGridOffset(0.0, 0.0);
2261  if(getPossibleGridOffsetForSdrObject(aGridOffset, pObj, pPV))
2262  {
2263  aRect += Point(
2264  basegfx::fround(aGridOffset.getX()),
2265  basegfx::fround(aGridOffset.getY()));
2266  }
2267 
2268  sal_uInt16 nTol2(nTol);
2269 
2270  // double tolerance for OLE, text frames and objects in
2271  // active text edit
2272  if(bOLE || bTXT || pObj==static_cast<const SdrObjEditView*>(this)->GetTextEditObject())
2273  {
2274  nTol2*=2;
2275  }
2276 
2277  aRect.AdjustLeft( -nTol2 ); // add 1 tolerance for all objects
2278  aRect.AdjustTop( -nTol2 );
2279  aRect.AdjustRight(nTol2 );
2280  aRect.AdjustBottom(nTol2 );
2281 
2282  if (aRect.IsInside(rPnt))
2283  {
2284  if (!bCheckIfMarkable || IsObjMarkable(pObj,pPV))
2285  {
2286  SdrObjList* pOL=pObj->GetSubList();
2287 
2288  if (pOL!=nullptr && pOL->GetObjCount()!=0)
2289  {
2290  SdrObject* pTmpObj;
2291  // adjustment hit point for virtual objects
2292  Point aPnt( rPnt );
2293 
2294  if ( auto pVirtObj = dynamic_cast<const SdrVirtObj*>( pObj) )
2295  {
2296  Point aOffset = pVirtObj->GetOffset();
2297  aPnt.Move( -aOffset.X(), -aOffset.Y() );
2298  }
2299 
2300  pRet=CheckSingleSdrObjectHit(aPnt,nTol,pOL,pPV,nOptions,pMVisLay,pTmpObj);
2301  }
2302  else
2303  {
2304  if(!pMVisLay || pMVisLay->IsSet(pObj->GetLayer()))
2305  {
2306  pRet = SdrObjectPrimitiveHit(*pObj, rPnt, nTol2, *pPV, &pPV->GetVisibleLayers(), false);
2307  }
2308  }
2309  }
2310  }
2311 
2312  if (!bDeep && pRet!=nullptr)
2313  {
2314  pRet=pObj;
2315  }
2316 
2317  return pRet;
2318 }
2319 
2320 SdrObject* SdrMarkView::CheckSingleSdrObjectHit(const Point& rPnt, sal_uInt16 nTol, SdrObjList const * pOL, SdrPageView* pPV, SdrSearchOptions nOptions, const SdrLayerIDSet* pMVisLay, SdrObject*& rpRootObj) const
2321 {
2322  return (*this).CheckSingleSdrObjectHit(rPnt,nTol,pOL,pPV,nOptions,pMVisLay,rpRootObj,nullptr);
2323 }
2324 SdrObject* SdrMarkView::CheckSingleSdrObjectHit(const Point& rPnt, sal_uInt16 nTol, SdrObjList const * pOL, SdrPageView* pPV, SdrSearchOptions nOptions, const SdrLayerIDSet* pMVisLay, SdrObject*& rpRootObj,const SdrMarkList * pMarkList) const
2325 {
2326  SdrObject* pRet=nullptr;
2327  rpRootObj=nullptr;
2328  if (pOL!=nullptr)
2329  {
2330  const bool bRemap(
2331  nullptr != pOL->getSdrObjectFromSdrObjList()
2332  && nullptr != dynamic_cast< const E3dScene* >(pOL->getSdrObjectFromSdrObjList()));
2333  const E3dScene* pRemapScene(bRemap ? static_cast< E3dScene* >(pOL->getSdrObjectFromSdrObjList()) : nullptr);
2334  const size_t nObjCount(pOL->GetObjCount());
2335  size_t nObjNum(nObjCount);
2336 
2337  while (pRet==nullptr && nObjNum>0)
2338  {
2339  nObjNum--;
2340  SdrObject* pObj;
2341 
2342  if(bRemap)
2343  {
2344  pObj = pOL->GetObj(pRemapScene->RemapOrdNum(nObjNum));
2345  }
2346  else
2347  {
2348  pObj = pOL->GetObj(nObjNum);
2349  }
2350  if (nOptions & SdrSearchOptions::BEFOREMARK)
2351  {
2352  if (pMarkList!=nullptr)
2353  {
2354  if ((*pMarkList).FindObject(pObj)!=SAL_MAX_SIZE)
2355  {
2356  return nullptr;
2357  }
2358  }
2359  }
2360  pRet=CheckSingleSdrObjectHit(rPnt,nTol,pObj,pPV,nOptions,pMVisLay);
2361  if (pRet!=nullptr) rpRootObj=pObj;
2362  }
2363  }
2364  return pRet;
2365 }
2366 
2367 SdrObject* SdrMarkView::PickObj(const Point& rPnt, short nTol, SdrPageView*& rpPV, SdrSearchOptions nOptions) const
2368 {
2369  return PickObj(rPnt, nTol, rpPV, nOptions, nullptr);
2370 }
2371 
2372 SdrObject* SdrMarkView::PickObj(const Point& rPnt, short nTol, SdrPageView*& rpPV, SdrSearchOptions nOptions, SdrObject** ppRootObj, bool* pbHitPassDirect) const
2373 { // TODO: lacks a Pass2,Pass3
2375  if (ppRootObj!=nullptr) *ppRootObj=nullptr;
2376  if (pbHitPassDirect!=nullptr) *pbHitPassDirect=true;
2377  SdrObject* pRet = nullptr;
2378  rpPV=nullptr;
2379  bool bMarked(nOptions & SdrSearchOptions::MARKED);
2380  bool bMasters=!bMarked && bool(nOptions & SdrSearchOptions::ALSOONMASTER);
2381  // nOptions & SdrSearchOptions::NEXT: n.i.
2382  // nOptions & SdrSearchOptions::PASS2BOUND: n.i.
2383  // nOptions & SdrSearchOptions::PASS3NEAREST// n.i.
2384  if (nTol<0) nTol=ImpGetHitTolLogic(nTol,nullptr);
2385  SdrObject* pObj=nullptr;
2386  SdrObject* pHitObj=nullptr;
2387  SdrPageView* pPV=nullptr;
2388  if (static_cast<const SdrObjEditView*>(this)->IsTextEditFrameHit(rPnt)) {
2389  pObj=static_cast<const SdrObjEditView*>(this)->GetTextEditObject();
2390  pHitObj=pObj;
2391  pPV=static_cast<const SdrObjEditView*>(this)->GetTextEditPageView();
2392  }
2393  if (bMarked) {
2394  const size_t nMrkCnt=GetMarkedObjectCount();
2395  size_t nMrkNum=nMrkCnt;
2396  while (pHitObj==nullptr && nMrkNum>0) {
2397  nMrkNum--;
2398  SdrMark* pM=GetSdrMarkByIndex(nMrkNum);
2399  pObj=pM->GetMarkedSdrObj();
2400  pPV=pM->GetPageView();
2401  pHitObj=CheckSingleSdrObjectHit(rPnt,nTol,pObj,pPV,nOptions,nullptr);
2402  }
2403  }
2404  else
2405  {
2406  pPV = GetSdrPageView();
2407 
2408  if(pPV)
2409  {
2410  SdrPage* pPage=pPV->GetPage();
2411  sal_uInt16 nPgCount=1;
2412 
2413  if(bMasters && pPage->TRG_HasMasterPage())
2414  {
2415  nPgCount++;
2416  }
2417  bool bWholePage(nOptions & SdrSearchOptions::WHOLEPAGE);
2418  bool bExtraPassForWholePage=bWholePage && pPage!=pPV->GetObjList();
2419  if (bExtraPassForWholePage) nPgCount++; // First search in AktObjList, then on the entire page
2420  sal_uInt16 nPgNum=nPgCount;
2421  while (pHitObj==nullptr && nPgNum>0) {
2422  SdrSearchOptions nTmpOptions=nOptions;
2423  nPgNum--;
2424  const SdrLayerIDSet* pMVisLay=nullptr;
2425  SdrObjList* pObjList=nullptr;
2426  if (pbHitPassDirect!=nullptr) *pbHitPassDirect = true;
2427  if (nPgNum>=nPgCount-1 || (bExtraPassForWholePage && nPgNum>=nPgCount-2))
2428  {
2429  pObjList=pPV->GetObjList();
2430  if (bExtraPassForWholePage && nPgNum==nPgCount-2) {
2431  pObjList=pPage;
2432  if (pbHitPassDirect!=nullptr) *pbHitPassDirect = false;
2433  }
2434  }
2435  else
2436  {
2437  // otherwise MasterPage
2438  SdrPage& rMasterPage = pPage->TRG_GetMasterPage();
2439  pMVisLay = &pPage->TRG_GetMasterPageVisibleLayers();
2440  pObjList = &rMasterPage;
2441 
2442  if (pbHitPassDirect!=nullptr) *pbHitPassDirect = false;
2443  nTmpOptions=nTmpOptions | SdrSearchOptions::IMPISMASTER;
2444  }
2445  pHitObj=CheckSingleSdrObjectHit(rPnt,nTol,pObjList,pPV,nTmpOptions,pMVisLay,pObj,&(GetMarkedObjectList()));
2446  }
2447  }
2448  }
2449  if (pHitObj!=nullptr) {
2450  if (ppRootObj!=nullptr) *ppRootObj=pObj;
2451  if (nOptions & SdrSearchOptions::DEEP) pObj=pHitObj;
2452  if (nOptions & SdrSearchOptions::TESTTEXTEDIT) {
2453  if (!pObj->HasTextEdit() || pPV->GetLockedLayers().IsSet(pObj->GetLayer())) {
2454  pObj=nullptr;
2455  }
2456  }
2457  if (pObj!=nullptr && (nOptions & SdrSearchOptions::TESTMACRO)) {
2458  SdrObjMacroHitRec aHitRec;
2459  aHitRec.aPos=rPnt;
2460  aHitRec.nTol=nTol;
2461  aHitRec.pVisiLayer=&pPV->GetVisibleLayers();
2462  aHitRec.pPageView=pPV;
2463  if (!pObj->HasMacro() || !pObj->IsMacroHit(aHitRec)) pObj=nullptr;
2464  }
2465  if (pObj!=nullptr) {
2466  pRet=pObj;
2467  rpPV=pPV;
2468  }
2469  }
2470  return pRet;
2471 }
2472 
2473 bool SdrMarkView::PickMarkedObj(const Point& rPnt, SdrObject*& rpObj, SdrPageView*& rpPV, SdrSearchOptions nOptions) const
2474 {
2476  const bool bBoundCheckOn2ndPass(nOptions & SdrSearchOptions::PASS2BOUND);
2477  rpObj=nullptr;
2478  rpPV=nullptr;
2479  const size_t nMarkCount=GetMarkedObjectCount();
2480  for (size_t nMarkNum=nMarkCount; nMarkNum>0;) {
2481  --nMarkNum;
2482  SdrMark* pM=GetSdrMarkByIndex(nMarkNum);
2483  SdrPageView* pPV=pM->GetPageView();
2484  SdrObject* pObj=pM->GetMarkedSdrObj();
2486  rpObj=pObj;
2487  rpPV=pPV;
2488  return true;
2489  }
2490  }
2491  if (bBoundCheckOn2ndPass) {
2492  for (size_t nMarkNum=nMarkCount; nMarkNum>0;) {
2493  --nMarkNum;
2494  SdrMark* pM=GetSdrMarkByIndex(nMarkNum);
2495  SdrPageView* pPV=pM->GetPageView();
2496  SdrObject* pObj=pM->GetMarkedSdrObj();
2497  tools::Rectangle aRect(pObj->GetCurrentBoundRect());
2498  aRect.AdjustLeft( -mnHitTolLog );
2499  aRect.AdjustTop( -mnHitTolLog );
2500  aRect.AdjustRight(mnHitTolLog );
2501  aRect.AdjustBottom(mnHitTolLog );
2502  if (aRect.IsInside(rPnt)) {
2503  rpObj=pObj;
2504  rpPV=pPV;
2505  return true;
2506  }
2507  }
2508  }
2509  return false;
2510 }
2511 
2512 
2514 {
2515  if (GetMarkedObjectCount()==0)
2516  return;
2517 
2518  BrkAction();
2519  if (pPV!=nullptr)
2520  {
2522  }
2523  else
2524  {
2526  }
2527  mpMarkedObj=nullptr;
2528  mpMarkedPV=nullptr;
2530  AdjustMarkHdl();
2531 }
2532 
2534 {
2535  BrkAction();
2536 
2537  if(!pPV)
2538  {
2539  pPV = GetSdrPageView();
2540  }
2541 
2542  // #i69171# pPV may still be NULL if there is no SDrPageView (!), e.g. when inserting
2543  // other files
2544  if(pPV)
2545  {
2546  const bool bMarkChg(GetMarkedObjectListWriteAccess().InsertPageView(*pPV));
2547 
2548  if(bMarkChg)
2549  {
2551  }
2552  }
2553 
2554  if(GetMarkedObjectCount())
2555  {
2556  AdjustMarkHdl();
2557  }
2558 }
2559 
2561 {
2562  CheckMarked();
2563  SetMarkRects();
2564  SetMarkHandles(pOtherShell);
2565 }
2566 
2567 // BoundRect in model coordinates, no GridOffset added
2569 {
2570  tools::Rectangle aRect;
2571  for (size_t nm=0; nm<GetMarkedObjectCount(); ++nm) {
2572  SdrMark* pM=GetSdrMarkByIndex(nm);
2573  SdrObject* pO=pM->GetMarkedSdrObj();
2575  if (aRect.IsEmpty()) aRect=aR1;
2576  else aRect.Union(aR1);
2577  }
2578  return aRect;
2579 }
2580 
2581 // ObjRect in model coordinates, no GridOffset added
2583 {
2584  if (mbMarkedObjRectDirty) {
2585  const_cast<SdrMarkView*>(this)->mbMarkedObjRectDirty=false;
2586  tools::Rectangle aRect;
2587  for (size_t nm=0; nm<GetMarkedObjectCount(); ++nm) {
2588  SdrMark* pM=GetSdrMarkByIndex(nm);
2589  SdrObject* pO = pM->GetMarkedSdrObj();
2590  if (!pO)
2591  continue;
2592  tools::Rectangle aR1(pO->GetSnapRect());
2593  if (aRect.IsEmpty()) aRect=aR1;
2594  else aRect.Union(aR1);
2595  }
2596  const_cast<SdrMarkView*>(this)->maMarkedObjRect=aRect;
2597  }
2598  return maMarkedObjRect;
2599 }
2600 
2601 
2603 {
2604  OUString sStr = SvxResId(pStrCacheID);
2605  const sal_Int32 nPos = sStr.indexOf("%1");
2606 
2607  if(nPos != -1)
2608  {
2610  {
2611  sStr = sStr.replaceAt(nPos, 2, GetDescriptionOfMarkedPoints());
2612  }
2613  else if(nOpt == ImpGetDescriptionOptions::GLUEPOINTS)
2614  {
2615  sStr = sStr.replaceAt(nPos, 2, GetDescriptionOfMarkedGluePoints());
2616  }
2617  else
2618  {
2619  sStr = sStr.replaceAt(nPos, 2, GetDescriptionOfMarkedObjects());
2620  }
2621  }
2622 
2623  return sStr.replaceFirst("%2", "0");
2624 }
2625 
2626 
2628 {
2629  // We enter only the first group found (in only one PageView), because
2630  // PageView::EnterGroup calls an AdjustMarkHdl.
2631  // TODO: I'll have to prevent that via a flag.
2632  SdrPageView* pPV = GetSdrPageView();
2633 
2634  if(!pPV)
2635  return;
2636 
2637  bool bEnter=false;
2638  for (size_t nm = GetMarkedObjectCount(); nm > 0 && !bEnter;)
2639  {
2640  --nm;
2641  SdrMark* pM=GetSdrMarkByIndex(nm);
2642  if (pM->GetPageView()==pPV) {
2643  SdrObject* pObj=pM->GetMarkedSdrObj();
2644  if (pObj->IsGroupObject()) {
2645  if (pPV->EnterGroup(pObj)) {
2646  bEnter=true;
2647  }
2648  }
2649  }
2650  }
2651 }
2652 
2653 
2655 {
2657  maSdrViewSelection.SetEdgesOfMarkedNodesDirty();
2658 
2659  mbMarkedObjRectDirty=true;
2661  bool bOneEdgeMarked=false;
2662  if (GetMarkedObjectCount()==1) {
2663  const SdrObject* pObj=GetMarkedObjectByIndex(0);
2664  if (pObj->GetObjInventor()==SdrInventor::Default) {
2665  sal_uInt16 nIdent=pObj->GetObjIdentifier();
2666  bOneEdgeMarked=nIdent==OBJ_EDGE;
2667  }
2668  }
2669  ImpSetGlueVisible4(bOneEdgeMarked);
2670 }
2671 
2672 
2674 {
2676 }
2677 
2679 {
2680  if ( mbDesignMode != bOn )
2681  {
2682  mbDesignMode = bOn;
2683  SdrPageView* pPageView = GetSdrPageView();
2684  if ( pPageView )
2685  pPageView->SetDesignMode( bOn );
2686  }
2687 }
2688 
2689 /* vim:set shiftwidth=4 softtabstop=4 expandtab: */
sal_uInt16 mnMinMovLog
Definition: svdpntv.hxx:150
void EndMarkGluePoints()
Definition: svdmrkv.cxx:529
SdrPage & TRG_GetMasterPage() const
Definition: svdpage.cxx:1631
virtual bool HasTextEdit() const
Definition: svdobj.cxx:1757
void UnmarkAllObj(SdrPageView const *pPV=nullptr)
Definition: svdmrkv.cxx:2513
OutDevType GetOutDevType() const
virtual void HideSdrPage()
Definition: svdpntv.cxx:373
double getY() const
void SetEditMode(SdrViewEditMode eMode)
Definition: svdmrkv.cxx:1831
const SdrUShortCont & GetMarkedGluePoints() const
Definition: svdmark.hxx:115
virtual basegfx::B2DPolyPolygon TakeXorPoly() const
The Xor-Polygon is required by the View to drag the object.
Definition: svdobj.cxx:1126
bool IsMacroHit(const SdrObjMacroHitRec &rRec) const
Definition: svdobj.cxx:1893
void SetMinMove(sal_uInt16 nDist)
Definition: svddrag.hxx:121
static void notifyOtherViews(const SfxViewShell *pThisView, int nType, std::string_view rKey, const OString &rPayload)
anchor
sal_Int32 nIndex
void Reset()
Definition: svddrag.cxx:36
const tools::Rectangle & MarkSnap() const
Definition: svdpagv.hxx:181
static void notifyInvalidation(SfxViewShell const *pThisView, tools::Rectangle const *)
void BrkMarkGluePoints()
Definition: svdmrkv.cxx:545
virtual bool IsTextEdit() const
Definition: svdpntv.cxx:297
bool IsNotVisibleAsMaster() const
Definition: svdobj.hxx:832
SdrHintKind GetKind() const
Definition: svdmodel.hxx:127
sal_uInt32 GetPolyNum() const
Definition: svdhdl.hxx:219
virtual const tools::Rectangle & GetCurrentBoundRect() const
Definition: svdobj.cxx:957
XGradient aGradient
Definition: gradtrns.hxx:40
void SetPos(const Point &rPnt)
Definition: svdhdl.cxx:342
virtual void SetMarkHandles(SfxViewShell *pOtherShell)
Definition: svdmrkv.cxx:1119
void SortMarkedObjects() const
Definition: svdmrkv.hxx:258
void SetDesignMode(bool bOn=true)
Definition: svdmrkv.cxx:2678
void UndirtyMrkPnt() const
Definition: svdmrkv1.cxx:287
bool mbMarkHandlesHidden
Definition: svdmrkv.hxx:131
bool UnmarkAllGluePoints()
Definition: svdmrkv.hxx:391
std::unique_ptr< ImplMarkingOverlay > mpMarkObjOverlay
Definition: svdmrkv.hxx:95
const SdrUShortCont & GetMarkedPoints() const
Definition: svdmark.hxx:110
basegfx::B2DPoint maPositionB
Definition: gradtrns.hxx:32
rtl::Reference< sdr::overlay::OverlayManager > const & GetOverlayManager() const
virtual void ModelHasChanged()
Definition: svdpntv.cxx:254
void SetSecondPosition(const basegfx::B2DPoint &rNewPosition)
Definition: svdmrkv.cxx:119
sdr::overlay::OverlayObjectList maObjects
Definition: svdmrkv.cxx:78
bool IsObjMarkable(SdrObject const *pObj, SdrPageView const *pPV) const
Definition: svdmrkv.cxx:1849
virtual bool IsPolyObj() const
Definition: svdobj.cxx:1729
constexpr tools::Long Left() const
const Point & GetStart() const
Definition: svddrag.hxx:102
SdrView & GetView()
Definition: svdpagv.hxx:130
SdrHdlKind
Definition: svdhdl.hxx:52
constexpr Point RightCenter() const
bool isInplaceActive() const
Definition: svdoole2.cxx:812
bool AreObjectsMarked() const
Definition: svdmrkv.hxx:259
SdrSearchOptions
Definition: svdmrkv.hxx:34
long Long
bool CheckMinMoved(const Point &rPnt)
Definition: svddrag.cxx:86
bool ImpIsFrameHandles() const
Definition: svdmrkv.cxx:589
object group
Definition: svdobjkind.hxx:28
constexpr TypedWhichId< XFillStyleItem > XATTR_FILLSTYLE(XATTR_FILL_FIRST)
sdr::ViewSelection maSdrViewSelection
Definition: svdmrkv.hxx:109
void FlushComeBackTimer() const
Definition: svdpntv.cxx:245
bool IsTextFrame() const
Definition: svdotext.hxx:334
virtual ~SdrMarkView() override
Definition: svdmrkv.cxx:191
constexpr Point convert(const Point &rPoint, o3tl::Length eFrom, o3tl::Length eTo)
bool IsInsObjPoint() const
Definition: svddrgv.hxx:123
bool isUiActive() const
Definition: svdoole2.cxx:817
SdrViewEditMode
Definition: svdmrkv.hxx:73
SdrHintKind
Definition: svdmodel.hxx:96
SdrObject * GetObj(size_t nNum) const
Definition: svdpage.cxx:822
virtual void BckAction() override
Definition: svdmrkv.cxx:318
size_t GetObjCount() const
Definition: svdpage.cxx:816
sal_uInt32 GetPointNum() const
Definition: svdhdl.hxx:222
bool IsInEditMode() const
Definition: svdotext.hxx:314
void SetSelected(bool bJa=true)
Definition: svdhdl.cxx:354
bool mbPlusHdlAlways
Definition: svdmrkv.hxx:124
virtual void addCropHandles(SdrHdlList &rTarget) const
Definition: svdobj.cxx:1252
sal_Int16 nId
virtual bool hasSpecialDrag() const
The standard transformations (Move,Resize,Rotate,Mirror,Shear) are taken over by the View (TakeXorPol...
Definition: svdobj.cxx:1328
SdrObject * GetObjectForNavigationPosition(const sal_uInt32 nNavigationPosition) const
Return the object for the given navigation position.
Definition: svdpage.cxx:942
virtual void Notify(SfxBroadcaster &rBC, const SfxHint &rHint) override
Definition: svdpntv.cxx:194
OUString const & GetDescriptionOfMarkedGluePoints() const
Definition: svdmrkv.hxx:262
const_iterator find(const Value &x) const
ViewObjectContact & GetViewObjectContact(ObjectContact &rObjectContact)
Definition: viewcontact.cxx:64
const MapMode & GetMapMode() const
OUString const & GetDescriptionOfMarkedPoints() const
Definition: svdmrkv.hxx:261
SdrObject * GetObj() const
Definition: svdhdl.hxx:203
def point()
SdrDragStat maDragStat
Definition: svdpntv.hxx:140
SdrPageView * GetSdrPageViewOfMarkedByIndex(size_t nNum) const
Definition: svdmrkv.hxx:254
constexpr Point BottomCenter() const
void append(std::unique_ptr< OverlayObject > pOverlayObject)
void SetUnsorted()
Definition: svdmark.hxx:173
const Point & GetPos() const
Definition: svdhdl.hxx:197
void Clear()
Definition: svdmark.cxx:201
virtual void AddToHdlList(SdrHdlList &rHdlList) const
Definition: svdobj.cxx:1228
bool HasMarkableGluePoints() const
Definition: svdmrkv1.cxx:351
virtual void BrkAction() override
Definition: svdmrkv.cxx:326
size_t TryToFindMarkedObject(const SdrObject *pObj) const
Definition: svdmrkv.hxx:253
void ImpSetGlueVisible4(bool bOn)
Definition: svdpntv.hxx:236
sal_uInt16 GetCount() const
Definition: svdglue.hxx:196
virtual SdrObjKind GetObjIdentifier() const
Definition: svdobj.cxx:659
bool MarkGluePoints(const tools::Rectangle *pRect, bool bUnmark)
Definition: svdmrkv1.cxx:391
media shape
Definition: svdobjkind.hxx:57
bool mbDesignMode
Definition: svdmrkv.hxx:122
void DeleteMark(size_t nNum)
Definition: svdmark.cxx:316
virtual SdrObjList * GetSubList() const
Definition: svdobj.cxx:748
void BegUndo()
Definition: svdmodel.cxx:366
SfxHintId GetId() const
virtual void AddToPlusHdlList(SdrHdlList &rHdlList, SdrHdl &rHdl) const
Definition: svdobj.cxx:1248
sdr::contact::ViewContact & GetViewContact() const
Definition: svdobj.cxx:251
virtual PointerStyle GetPointer() const
Definition: svdhdl.cxx:952
bool BegMarkPoints(const Point &rPnt, bool bUnmark=false)
Definition: svdmrkv.cxx:433
const tools::Rectangle & GetMarkedObjRect() const
Definition: svdmrkv.cxx:2582
virtual const tools::Rectangle & GetSnapRect() const
Definition: svdobj.cxx:1666
virtual void BrkAction() override
Definition: svdsnpv.cxx:237
virtual bool MouseMove(const MouseEvent &rMEvt, OutputDevice *pWin) override
handle mouse over effects for handles
Definition: svdmrkv.cxx:1608
bool IsVisible() const
Definition: svdobj.hxx:754
void EnterMarkedGroup()
Definition: svdmrkv.cxx:2627
virtual void MarkListHasChanged()
Definition: svdmrkv.cxx:2654
bool equalZero() const
SdrPageWindow * FindPageWindow(SdrPaintWindow &rPaintWindow) const
Definition: svdpagv.cxx:43
static UITestLogger & getInstance()
SdrMarkView(SdrModel &rSdrModel, OutputDevice *pOut)
Definition: svdmrkv.cxx:166
void logEvent(const EventDescription &rDescription)
sal_uInt16 mnHitTolLog
Definition: svdpntv.hxx:149
void SetNameDirty()
Definition: svdmark.hxx:193
bool IsUnmarking() const
Definition: svdmrkv.cxx:94
sal_uInt16 ImpGetHitTolLogic(short nHitTol, const OutputDevice *pOut) const
Definition: svdpntv.cxx:316
bool IsAncestorOf(const vcl::Window &rWindow) const
virtual SdrGluePoint GetVertexGluePoint(sal_uInt16 nNum) const
Definition: svdobj.cxx:2251
OUTDEV_WINDOW
virtual void TakeActionRect(tools::Rectangle &rRect) const override
Definition: svdsnpv.cxx:244
void AddUndo(std::unique_ptr< SdrUndoAction > pUndo)
Definition: svdmodel.cxx:500
constexpr Point BottomLeft() const
SdrHdl * GetHdl(size_t nHdlNum) const
Definition: svdmrkv.hxx:352
virtual bool MouseMove(const MouseEvent &, OutputDevice *)
Definition: svdpntv.hxx:450
OUString SvxResId(TranslateId aId)
Definition: dialmgr.cxx:24
constexpr Point TopCenter() const
static SfxViewShell * Current()
void libreOfficeKitViewCallback(int nType, const char *pPayload) const override
oslFileHandle & pOut
SdrObject * SdrObjectPrimitiveHit(const SdrObject &rObject, const Point &rPnt, sal_uInt16 nTol, const SdrPageView &rSdrPageView, const SdrLayerIDSet *pVisiLayer, bool bTextOnly, drawinglayer::primitive2d::Primitive2DContainer *pHitContainer)
void MovMarkObj(const Point &rPnt)
Definition: svdmrkv.cxx:391
constexpr tools::Long GetWidth() const
void Clear()
Definition: svdhdl.cxx:2245
virtual bool RequestHelp(const HelpEvent &)
Definition: svdpntv.hxx:451
sdr::overlay::OverlayObjectList maObjects
Definition: svdmrkv.cxx:137
OutputDevice * GetFirstOutputDevice() const
Definition: svdpntv.cxx:89
bool IsMarkGluePoints() const
Definition: svdmrkv.hxx:407
sal_uInt16 GetHdlSize() const
Definition: svdhdl.hxx:463
bool BegMarkGluePoints(const Point &rPnt, bool bUnmark=false)
Definition: svdmrkv.cxx:497
void showMarkHandles()
Definition: svdmrkv.cxx:580
Point maRef1
Definition: svdmrkv.hxx:105
virtual SdrObject * CheckSingleSdrObjectHit(const Point &rPnt, sal_uInt16 nTol, SdrObject *pObj, SdrPageView *pPV, SdrSearchOptions nOptions, const SdrLayerIDSet *pMVisLay) const
Definition: svdmrkv.cxx:2244
void AddDragModeHdl(SdrDragMode eMode)
Definition: svdmrkv.cxx:1467
void SetDistortShear(bool bOn)
Definition: svdhdl.cxx:2225
B2IRange fround(const B2DRange &rRange)
Point maRef2
Definition: svdmrkv.hxx:106
bool TakeBoundRect(SdrPageView const *pPageView, tools::Rectangle &rRect) const
Definition: svdmark.cxx:588
virtual bool HasLimitedRotation() const
Definition: svdobj.cxx:1071
bool mbMarkedObjRectDirty
Definition: svdmrkv.hxx:126
bool IsMinMoved() const
Definition: svddrag.hxx:118
constexpr bool IsEmpty() const
sal_uInt32 PaintWindowCount() const
Definition: svdpntv.hxx:218
SdrHdl * IsHdlListHit(const Point &rPnt) const
Definition: svdhdl.cxx:2296
bool PickMarkedObj(const Point &rPnt, SdrObject *&rpObj, SdrPageView *&rpPV, SdrSearchOptions nOptions) const
Definition: svdmrkv.cxx:2473
void Sort()
Definition: svdhdl.cxx:2253
SdrObjList * GetObjList() const
Return current List.
Definition: svdpagv.hxx:169
SdrObject * GetMarkedSdrObj() const
Definition: svdmark.hxx:68
void SetMoveOutside(bool bOn)
Definition: svdmrkv.cxx:2673
Everything a View needs to know about a selected object.
Definition: svdmark.hxx:44
void MarkAllObj(SdrPageView *pPV=nullptr)
Definition: svdmrkv.cxx:2533
virtual void ClearPageView()
Definition: svdpntv.cxx:345
bool mbMrkPntDirty
Definition: svdmrkv.hxx:127
SdrObject * PickObj(const Point &rPnt, short nTol, SdrPageView *&rpPV, SdrSearchOptions nOptions, SdrObject **ppRootObj, bool *pbHitPassDirect=nullptr) const
Definition: svdmrkv.cxx:2372
bool getPossibleGridOffsetForPosition(basegfx::B2DVector &rOffset, const basegfx::B2DPoint &rPoint, const SdrPageView *pPV) const
Definition: svdmrkv.cxx:2208
SdrDragMode meDragMode
Definition: svdmrkv.hxx:118
const SdrLayerIDSet & GetVisibleLayers() const
Definition: svdpagv.hxx:210
void ImpSetGlueVisible3(bool bOn)
Definition: svdpntv.hxx:235
open Bezier-curve
Definition: svdobjkind.hxx:37
UNDERLYING_TYPE get() const
virtual const SdrGluePointList * GetGluePointList() const
Definition: svdobj.cxx:2288
sal_uInt32 RemapOrdNum(sal_uInt32 nOrdNum) const
Definition: scene3d.cxx:276
void SetObj(SdrObject *pNewObj)
Definition: svdhdl.cxx:378
constexpr TypedWhichId< XFillGradientItem > XATTR_FILLGRADIENT(XATTR_FILL_FIRST+2)
SfxItemState GetItemState(sal_uInt16 nWhich, bool bSrchInParent=true, const SfxPoolItem **ppItem=nullptr) const
#define DBG_ASSERT(sCon, aError)
bool IsLeaveWindow() const
int i
uno_Any a
#define SDRGLUEPOINT_NOTFOUND
Definition: svdglue.hxx:183
void MoveTo(SdrHdlList &rOther)
Definition: svdhdl.cxx:2323
bool IsWriter() const
Definition: svdmodel.hxx:573
const tools::Rectangle & MarkBound() const
Definition: svdpagv.hxx:180
bool IsUndoEnabled() const
returns true if undo is currently enabled This returns false if undo was disabled using EnableUndo( f...
Definition: svdmodel.cxx:531
void SetObjHdlNum(sal_uInt32 nNum)
Definition: svdhdl.hxx:215
virtual void MovAction(const Point &rPnt) override
Definition: svdmrkv.cxx:282
basegfx::B2DPoint maPositionA
Definition: gradtrns.hxx:31
bool IsMarkObj() const
Definition: svdmrkv.hxx:211
std::vector< basegfx::B2DRectangle > maSubSelectionList
Definition: svdmrkv.hxx:111
size_t GetMarkedObjectCount() const
Definition: svdmrkv.hxx:257
virtual void EndAction() override
Definition: svdmrkv.cxx:300
const SdrLayerIDSet & TRG_GetMasterPageVisibleLayers() const
Definition: svdpage.cxx:1637
bool MarkableObjectsExceed(int n) const
Definition: svdmrkv.cxx:554
bool IsMarkedObjHit(const Point &rPnt, short nTol=-2) const
Definition: svdmrkv.cxx:1864
OUString const & GetDescriptionOfMarkedObjects() const
Definition: svdmrkv.hxx:260
void ForceRefToMarked()
Definition: svdmrkv.cxx:1665
void hideMarkHandles()
Definition: svdmrkv.cxx:571
virtual bool IsAction() const override
Definition: svdmrkv.cxx:277
connector object
Definition: svdobjkind.hxx:48
virtual void onHelpRequest()
is called when help is requested for the area of this handle
Definition: svdhdl.cxx:1065
const SdrMarkList & GetMarkedObjectList() const
Definition: svdmrkv.hxx:251
Size GetOutputSize() const
SdrPageView * GetPageView() const
Definition: svdmark.hxx:70
void SetHasMarkedObj(bool bOn)
Definition: svdpagv.hxx:178
virtual bool IsAction() const override
Definition: svdsnpv.cxx:203
void ImpSetGlueVisible2(bool bOn)
Definition: svdpntv.hxx:234
bool mbMouseOver
Definition: svdhdl.hxx:165
bool IsGluePointEditMode() const
Definition: svdmrkv.hxx:232
constexpr tools::Long Right() const
void SetMergedItemSetAndBroadcast(const SfxItemSet &rSet, bool bClearAllItems=false)
Definition: svdobj.cxx:2018
void MovMarkGluePoints(const Point &rPnt)
Definition: svdmrkv.cxx:517
SdrHdl * PickHandle(const Point &rPnt) const
Definition: svdmrkv.cxx:1875
void setSecondPosition(const basegfx::B2DPoint &rNew)
sal_uInt32 GetOrdNum() const
The order number (aka ZOrder, aka z-index) determines whether a SdrObject is located above or below a...
Definition: svdobj.cxx:900
void BrkMarkObj()
Definition: svdmrkv.cxx:423
#define SDR_HANDLE_COLOR_SIZE_NORMAL
Definition: svdhdl.hxx:252
void SetMarkHandlesForLOKit(tools::Rectangle const &rRect, const SfxViewShell *pOtherShell)
Definition: svdmrkv.cxx:753
virtual bool HasMacro() const
Definition: svdobj.cxx:1851
void SetMoveOutside(bool bOn)
Definition: svdhdl.cxx:2204
constexpr tools::Long Top() const
bool IsGroupObject() const
Definition: svdobj.cxx:743
void NextMove(const Point &rPnt)
Definition: svddrag.cxx:66
virtual void calculateGridOffsetForB2DRange(basegfx::B2DVector &rTarget, const basegfx::B2DRange &rB2DRange) const
void BegMarkObj(const Point &rPnt, bool bUnmark=false)
Definition: svdmrkv.cxx:377
bool IsInside(const Point &rPOINT) const
void NextPoint()
Definition: svddrag.cxx:73
bool mbSomeObjChgdFlag
Definition: svdpntv.hxx:164
SdrPageView * mpMarkedPV
Definition: svdmrkv.hxx:103
static constexpr sal_uInt16 mnFrameHandlesLimit
Definition: svdmrkv.hxx:116
void StartListening(SfxBroadcaster &rBroadcaster, DuplicateHandling eDuplicateHanding=DuplicateHandling::Unexpected)
const_iterator end() const
void SetHdlSize(sal_uInt16 nSiz)
Definition: svdhdl.cxx:2188
Point PixelToLogic(const Point &rDevicePt) const
bool TRG_HasMasterPage() const
Definition: svdpage.hxx:487
tools::Rectangle GetMarkedObjBoundRect() const
Definition: svdmrkv.cxx:2568
const SdrLayerIDSet * pVisiLayer
Definition: svdobj.hxx:139
Abstract DrawObject.
Definition: svdobj.hxx:259
Point GetOffsetPixelFrom(const vcl::Window &rWindow) const
virtual SfxViewShell * GetSfxViewShell() const
Get access to the view shell owning this draw view, if any.
Definition: svdmrkv.cxx:1776
bool getPossibleGridOffsetForSdrObject(basegfx::B2DVector &rOffset, const SdrObject *pObj, const SdrPageView *pPV) const
Definition: svdmrkv.cxx:2169
bool MarkNextObj(bool bPrev=false)
Definition: svdmrkv.cxx:1897
constexpr Point LeftCenter() const
SdrUndoFactory & GetSdrUndoFactory() const
returns the models undo factory.
Definition: svdmodel.cxx:1850
Point GetAbsolutePos(const SdrObject &rObj) const
Definition: svdglue.cxx:48
OUString GetName() const
Definition: svdobj.cxx:802
virtual bool IsChart() const
virtual void AddCustomHdl()
Definition: svdmrkv.cxx:1448
virtual SdrInventor GetObjInventor() const
Definition: svdobj.cxx:654
constexpr Point Center() const
sal_uInt16 FindGluePoint(sal_uInt16 nId) const
Definition: svdglue.cxx:336
void MovMarkPoints(const Point &rPnt)
Definition: svdmrkv.cxx:453
constexpr Point TopLeft() const
virtual SdrLayerID GetLayer() const
Definition: svdobj.cxx:678
SdrObject * mpMarkedObj
Definition: svdmrkv.hxx:102
bool IsMarkProtect() const
Definition: svdobj.hxx:756
constexpr tools::Long Bottom() const
virtual void ClearPageView() override
Definition: svdmrkv.cxx:347
SAL_WARN_UNUSED_RESULT Point PixelToLogic(const Point &rDevicePt) const
void EndUndo()
Definition: svdmodel.cxx:437
const SdrLayerIDSet & GetLockedLayers() const
Definition: svdpagv.hxx:214
void SetStartIntens(sal_uInt16 nNewIntens)
Definition: xgrad.hxx:64
SdrHdl * GetFocusHdl() const
Definition: svdhdl.cxx:2127
void SetRef1(const Point &rPt)
Definition: svdmrkv.cxx:1754
bool IsSet(SdrLayerID a) const
Definition: svdsob.hxx:64
SdrViewEditMode meEditMode
Definition: svdmrkv.hxx:119
size_t GetHdlCount() const
Definition: svdhdl.hxx:459
const SfxPoolItem * Put(const SfxPoolItem &rItem, sal_uInt16 nWhich)
SdrHdl * GetHdl(size_t nNum) const
Definition: svdhdl.hxx:460
SdrViewEditMode meEditMode0
Definition: svdmrkv.hxx:120
bool IsUnoObj() const
Definition: svdobj.hxx:746
def rectangle(l)
bool IsMarkPoints() const
Definition: svdmrkv.hxx:361
void SetMarkRects()
Definition: svdmrkv.cxx:1807
constexpr TypedWhichId< XFillFloatTransparenceItem > XATTR_FILLFLOATTRANSPARENCE(XATTR_FILL_FIRST+11)
bool mbMarkedPointsRectsDirty
Definition: svdmrkv.hxx:128
sal_uInt32 GetObjHdlNum() const
Definition: svdhdl.hxx:216
OverlayObject & getOverlayObject(sal_uInt32 nIndex) const
bool EndMarkObj()
Definition: svdmrkv.cxx:402
virtual void Notify(SfxBroadcaster &rBC, const SfxHint &rHint) override
Definition: svdmrkv.cxx:199
const SfxPoolItem & Get(sal_uInt16 nWhich, bool bSrchInParent=true) const
basegfx::B2DPoint maSecondPosition
tools::Rectangle & Union(const tools::Rectangle &rRect)
constexpr tools::Long Height() const
SdrDragMode
Definition: svdtypes.hxx:33
bool dumpGluePointsToJSON(boost::property_tree::ptree &rTree)
Definition: svdmrkv.cxx:689
SdrPage * GetPage() const
Definition: svdpagv.hxx:166
object that represents a SdrPage
Definition: svdobjkind.hxx:52
ImplMarkingOverlay(const SdrPaintView &rView, const basegfx::B2DPoint &rStartPos, bool bUnmarking)
Definition: svdmrkv.cxx:97
virtual void MovAction(const Point &rPnt) override
Definition: svdsnpv.cxx:208
virtual void TakeActionRect(tools::Rectangle &rRect) const override
Definition: svdmrkv.cxx:334
eFillStyle
Definition: fillctrl.cxx:54
void SetPageView(SdrPageView *pNewPV)
Definition: svdhdl.hxx:201
const SfxItemSet & GetMergedItemSet() const
Definition: svdobj.cxx:1978
constexpr Point TopRight() const
std::unique_ptr< MarkingSubSelectionOverlay > mpMarkingSubSelectionOverlay
Definition: svdmrkv.hxx:99
virtual void BckAction() override
Definition: svdsnpv.cxx:230
void AdjustMarkHdl(SfxViewShell *pOtherShell=nullptr)
Definition: svdmrkv.cxx:2560
MarkingSubSelectionOverlay(const SdrPaintView &rView, std::vector< basegfx::B2DRectangle > const &rSelections)
Definition: svdmrkv.cxx:140
void SetFocusHdl(SdrHdl *pNew)
Definition: svdhdl.cxx:2135
void * p
virtual void EndAction() override
Definition: svdsnpv.cxx:219
void SetDesignMode(bool _bDesignMode) const
Sets all elements in the view which support a design and an alive mode into the given mode...
Definition: svdpagv.cxx:340
void SetDragMode(SdrDragMode eMode)
Definition: svdmrkv.cxx:1453
sal_uInt32 GetNavigationPosition() const
Definition: svdobj.cxx:936
bool EndMarkPoints()
Definition: svdmrkv.cxx:465
bool areMarkHandlesHidden() const
Definition: svdmrkv.hxx:276
const Point & GetPosPixel() const
SdrObject * GetMarkedObjectByIndex(size_t nNum) const
Definition: svdmrkv.hxx:256
const Point & GetOrigin() const
void SetFrameHandles(bool bOn)
Definition: svdmrkv.cxx:1818
const Point & GetNow() const
Definition: svddrag.hxx:105
SdrObject * getParentSdrObjectFromSdrObject() const
Definition: svdobj.cxx:753
ImpGetDescriptionOptions
options for ImpGetDescriptionString()
Definition: svdmrkv.hxx:80
virtual bool MarkPoints(const tools::Rectangle *pRect, bool bUnmark)
Definition: svdmrkv1.cxx:186
void BrkMarkPoints()
Definition: svdmrkv.cxx:487
SdrPageView * GetSdrPageView() const
Definition: svdpntv.hxx:299
Universal Network Object packed into SvDraw object.
Definition: svdobjkind.hxx:55
constexpr Point BottomRight() const
bool EnterGroup(SdrObject *pObj)
Entering (editing) an object group After that, we have direct access to all member objects of the gro...
Definition: svdpagv.cxx:727
void SetPlusHdl(bool bOn)
Definition: svdhdl.hxx:224
sal_uInt16 GetMarkHdlSizePixel() const
Definition: svdmrkv.cxx:2155
virtual void ModelHasChanged() override
Definition: svdmrkv.cxx:214
void Move(tools::Long nHorzMoveDelta, tools::Long nVertMoveDelta)
bool IsDragObj() const
Definition: svddrgv.hxx:103
SdrHdlList maHdlList
Definition: svdmrkv.hxx:107
Any result
tools::Long AdjustLeft(tools::Long nHorzMoveDelta)
std::unique_ptr< ImplMarkingOverlay > mpMarkGluePointsOverlay
Definition: svdmrkv.hxx:97
double getX() const
SdrModel & getSdrModelFromSdrView() const
Definition: svdpntv.hxx:257
virtual void onMouseEnter(const MouseEvent &rMEvt)
is called when the mouse enters the area of this handle.
Definition: svdhdl.cxx:1061
const SfxItemPool & GetItemPool() const
Definition: svdmodel.hxx:311
virtual Degree100 GetRotateAngle() const
Definition: svdobj.cxx:1709
bool MarkObj(const Point &rPnt, short nTol=-2, bool bToggle=false, bool bDeep=false)
Definition: svdmrkv.cxx:1883
virtual const tools::Rectangle & GetLogicRect() const
Definition: svdobj.cxx:1676
sal_uInt16 nTol
Definition: svdobj.hxx:141
basegfx::B2DPoint maSecondPosition
Definition: svdmrkv.cxx:81
SdrMark * GetSdrMarkByIndex(size_t nNum) const
Definition: svdmrkv.hxx:255
A SdrPage contains exactly one SdrObjList and a description of the physical page dimensions (size / m...
Definition: svdpage.hxx:365
OLE object.
Definition: svdobjkind.hxx:47
SdrObjList * getParentSdrObjListFromSdrObject() const
Definition: svdobj.cxx:305
OUString ImpGetDescriptionString(TranslateId pStrCacheID, ImpGetDescriptionOptions nOpt=ImpGetDescriptionOptions::NONE) const
Definition: svdmrkv.cxx:2602
tools::Rectangle maMarkedObjRect
Definition: svdmrkv.hxx:112
std::map< OUString, OUString > aParameters
virtual void onMouseLeave()
is called when the mouse leaves the area of this handle.
Definition: svdhdl.cxx:1069
virtual std::unique_ptr< SdrUndoAction > CreateUndoAttrObject(SdrObject &rObject, bool bStyleSheet1=false, bool bSaveText=false)
Definition: svdundo.cxx:1636
rtl::OString toString() const
void InsertEntry(const SdrMark &rMark, bool bChkSort=true)
Definition: svdmark.cxx:260
void SetMarkHdlSizePixel(sal_uInt16 nSiz)
Definition: svdmrkv.cxx:2160
virtual void HideSdrPage() override
Definition: svdmrkv.cxx:353
static void GradToVec(GradTransGradient const &rG, GradTransVector &rV, const SdrObject *pObj)
Definition: gradtrns.cxx:30
css::uno::Reference< css::frame::XController > & GetXController()
SdrMarkList & GetMarkedObjectListWriteAccess()
Definition: svdmrkv.hxx:247
SdrModel * GetModel() const
Definition: svdpntv.hxx:260
void SetRef2(const Point &rPt)
Definition: svdmrkv.cxx:1765
virtual vcl::Window * GetOwnerWindow() const
virtual SdrObject * getSdrObjectFromSdrObjList() const
Definition: svdpage.cxx:128
std::unique_ptr< ImplMarkingOverlay > mpMarkPointsOverlay
Definition: svdmrkv.hxx:96
void CheckMarked()
Definition: svdmrkv.cxx:1781
bool mbForceFrameHandles
Definition: svdmrkv.hxx:123
SdrPaintWindow * GetPaintWindow(sal_uInt32 nIndex) const
Definition: svdpntv.cxx:73
virtual vcl::Window * GetEditWindowForActiveOLEObj() const override
const SdrPageView * pPageView
Definition: svdobj.hxx:140
void SetRotateShear(bool bOn)
Definition: svdhdl.cxx:2220
bool IsObjMarkable(SdrObject const *pObj) const
At least one member must be visible for the Group object and it must not be locked.
Definition: svdpagv.cxx:591
void AddHdl(std::unique_ptr< SdrHdl > pHdl)
Definition: svdhdl.cxx:2289
sal_uInt16 nPos
static void notifyOtherView(const SfxViewShell *pThisView, SfxViewShell const *pOtherView, int nType, std::string_view rKey, const OString &rPayload)
SdrHdlKind GetKind() const
Definition: svdhdl.hxx:194
virtual bool HasMarkablePoints() const
Definition: svdmrkv1.cxx:29
sal_uInt32 count() const
bool DeletePageView(const SdrPageView &rPV)
Definition: svdmark.cxx:372
constexpr tools::Long GetHeight() const
bool createTableEdgesJson(boost::property_tree::ptree &rJsonRoot)
Definition: svdotable.cxx:2454
basegfx::B2DPoint const & getB2DPoint(sal_uInt32 nIndex) const
bool IsObjMarked(SdrObject const *pObj) const
Definition: svdmrkv.cxx:2150
virtual bool RequestHelp(const HelpEvent &rHEvt) override
Definition: svdmrkv.cxx:1646