xref: /trunk/main/svx/source/svdraw/svdcrtv.cxx (revision 1cd65da9)
1 /**************************************************************
2  *
3  * Licensed to the Apache Software Foundation (ASF) under one
4  * or more contributor license agreements.  See the NOTICE file
5  * distributed with this work for additional information
6  * regarding copyright ownership.  The ASF licenses this file
7  * to you under the Apache License, Version 2.0 (the
8  * "License"); you may not use this file except in compliance
9  * with the License.  You may obtain a copy of the License at
10  *
11  *   http://www.apache.org/licenses/LICENSE-2.0
12  *
13  * Unless required by applicable law or agreed to in writing,
14  * software distributed under the License is distributed on an
15  * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
16  * KIND, either express or implied.  See the License for the
17  * specific language governing permissions and limitations
18  * under the License.
19  *
20  *************************************************************/
21 
22 
23 
24 // MARKER(update_precomp.py): autogen include statement, do not remove
25 #include "precompiled_svx.hxx"
26 
27 #include <svx/svdcrtv.hxx>
28 #include "svx/xattr.hxx"
29 #include <svx/svdundo.hxx>
30 #include <svx/svdocapt.hxx> // Spezialbehandlung: Nach dem Create transparente Fuellung
31 #include <svx/svdoedge.hxx>
32 #include <svx/svdpagv.hxx>
33 #include <svx/svdpage.hxx>
34 #include <svx/svdetc.hxx>
35 #include <svx/scene3d.hxx>
36 #include <svx/view3d.hxx>
37 #include <svx/sdr/contact/objectcontactofobjlistpainter.hxx>
38 #include <svx/sdr/contact/displayinfo.hxx>
39 #include <svx/svdouno.hxx>
40 #define XOR_CREATE_PEN			PEN_SOLID
41 #include <svx/svdopath.hxx>
42 #include <svx/sdr/overlay/overlaypolypolygon.hxx>
43 #include <svx/sdr/overlay/overlaymanager.hxx>
44 #include <svx/sdrpaintwindow.hxx>
45 #include "fmobj.hxx"
46 #include <svx/svdocirc.hxx>
47 #include <svx/sdr/contact/viewcontact.hxx>
48 #include <svx/sdr/overlay/overlayprimitive2dsequenceobject.hxx>
49 #include <svx/sdr/overlay/overlaymanager.hxx>
50 
51 ////////////////////////////////////////////////////////////////////////////////////////////////////
52 
53 class ImplConnectMarkerOverlay
54 {
55 	// The OverlayObjects
56 	::sdr::overlay::OverlayObjectList				maObjects;
57 
58 	// The remembered target object
59 	const SdrObject&								mrObject;
60 
61 public:
62 	ImplConnectMarkerOverlay(const SdrCreateView& rView, SdrObject& rObject);
63 	~ImplConnectMarkerOverlay();
64 
GetTargetObject() const65 	const SdrObject& GetTargetObject() const { return mrObject; }
66 };
67 
ImplConnectMarkerOverlay(const SdrCreateView & rView,SdrObject & rObject)68 ImplConnectMarkerOverlay::ImplConnectMarkerOverlay(const SdrCreateView& rView, SdrObject& rObject)
69 :	mrObject(rObject)
70 {
71 	basegfx::B2DPolyPolygon aB2DPolyPolygon(rObject.TakeXorPoly());
72 
73 	for(sal_uInt32 a(0L); a < rView.PaintWindowCount(); a++)
74 	{
75 		SdrPaintWindow* pCandidate = rView.GetPaintWindow(a);
76 		::sdr::overlay::OverlayManager* pTargetOverlay = pCandidate->GetOverlayManager();
77 
78 		if(pTargetOverlay)
79 		{
80 			Size aHalfLogicSize(pTargetOverlay->getOutputDevice().PixelToLogic(Size(4, 4)));
81 
82 			// object
83 			::sdr::overlay::OverlayPolyPolygonStripedAndFilled* pNew = new ::sdr::overlay::OverlayPolyPolygonStripedAndFilled(
84                 aB2DPolyPolygon);
85 			pTargetOverlay->add(*pNew);
86 			maObjects.append(*pNew);
87 
88 			// gluepoints
89 			if(rView.IsAutoVertexConnectors())
90 			{
91 				for(sal_uInt16 i(0); i < 4; i++)
92 				{
93 					SdrGluePoint aGluePoint(rObject.GetVertexGluePoint(i));
94 					const Point& rPosition = aGluePoint.GetAbsolutePos(rObject);
95 
96 					basegfx::B2DPoint aTopLeft(rPosition.X() - aHalfLogicSize.Width(), rPosition.Y() - aHalfLogicSize.Height());
97 					basegfx::B2DPoint aBottomRight(rPosition.X() + aHalfLogicSize.Width(), rPosition.Y() + aHalfLogicSize.Height());
98 
99 					basegfx::B2DPolygon aTempPoly;
100 					aTempPoly.append(aTopLeft);
101 					aTempPoly.append(basegfx::B2DPoint(aBottomRight.getX(), aTopLeft.getY()));
102 					aTempPoly.append(aBottomRight);
103 					aTempPoly.append(basegfx::B2DPoint(aTopLeft.getX(), aBottomRight.getY()));
104 					aTempPoly.setClosed(true);
105 
106 					basegfx::B2DPolyPolygon aTempPolyPoly;
107 					aTempPolyPoly.append(aTempPoly);
108 
109 					pNew = new ::sdr::overlay::OverlayPolyPolygonStripedAndFilled(
110                         aTempPolyPoly);
111 					pTargetOverlay->add(*pNew);
112 					maObjects.append(*pNew);
113 				}
114 			}
115 		}
116 	}
117 }
118 
~ImplConnectMarkerOverlay()119 ImplConnectMarkerOverlay::~ImplConnectMarkerOverlay()
120 {
121 	// The OverlayObjects are cleared using the destructor of OverlayObjectList.
122 	// That destructor calls clear() at the list which removes all objects from the
123 	// OverlayManager and deletes them.
124 }
125 
126 ////////////////////////////////////////////////////////////////////////////////////////////////////
127 
128 class ImpSdrCreateViewExtraData
129 {
130 	// The OverlayObjects for XOR replacement
131 	::sdr::overlay::OverlayObjectList				maObjects;
132 
133 public:
134 	ImpSdrCreateViewExtraData();
135 	~ImpSdrCreateViewExtraData();
136 
137 	void CreateAndShowOverlay(const SdrCreateView& rView, const SdrObject* pObject, const basegfx::B2DPolyPolygon& rPolyPoly);
138 	void HideOverlay();
139 };
140 
ImpSdrCreateViewExtraData()141 ImpSdrCreateViewExtraData::ImpSdrCreateViewExtraData()
142 {
143 }
144 
~ImpSdrCreateViewExtraData()145 ImpSdrCreateViewExtraData::~ImpSdrCreateViewExtraData()
146 {
147 	HideOverlay();
148 }
149 
CreateAndShowOverlay(const SdrCreateView & rView,const SdrObject * pObject,const basegfx::B2DPolyPolygon & rPolyPoly)150 void ImpSdrCreateViewExtraData::CreateAndShowOverlay(const SdrCreateView& rView, const SdrObject* pObject, const basegfx::B2DPolyPolygon& rPolyPoly)
151 {
152 	for(sal_uInt32 a(0L); a < rView.PaintWindowCount(); a++)
153 	{
154 		SdrPaintWindow* pCandidate = rView.GetPaintWindow(a);
155 		::sdr::overlay::OverlayManager* pOverlayManager = pCandidate->GetOverlayManager();
156 
157 		if(pOverlayManager)
158 		{
159 			if(pObject)
160 			{
161 				const sdr::contact::ViewContact& rVC = pObject->GetViewContact();
162 				const drawinglayer::primitive2d::Primitive2DSequence aSequence = rVC.getViewIndependentPrimitive2DSequence();
163 				sdr::overlay::OverlayObject* pNew = new sdr::overlay::OverlayPrimitive2DSequenceObject(aSequence);
164 
165 				pOverlayManager->add(*pNew);
166 			    maObjects.append(*pNew);
167 			}
168 
169 			if(rPolyPoly.count())
170 			{
171 				::sdr::overlay::OverlayPolyPolygonStripedAndFilled* pNew = new ::sdr::overlay::OverlayPolyPolygonStripedAndFilled(
172                     rPolyPoly);
173 				pOverlayManager->add(*pNew);
174 				maObjects.append(*pNew);
175 			}
176 		}
177 	}
178 }
179 
HideOverlay()180 void ImpSdrCreateViewExtraData::HideOverlay()
181 {
182 	// the clear() call at the list removes all objects from the
183 	// OverlayManager and deletes them.
184 	maObjects.clear();
185 }
186 
187 ////////////////////////////////////////////////////////////////////////////////////////////////////
188 ////////////////////////////////////////////////////////////////////////////////////////////////////
189 //
190 //   @@@@  @@@@@  @@@@@  @@@@  @@@@@@ @@@@@  @@ @@ @@ @@@@@ @@   @@
191 //  @@  @@ @@  @@ @@    @@  @@   @@   @@     @@ @@ @@ @@    @@   @@
192 //  @@     @@  @@ @@    @@  @@   @@   @@     @@ @@ @@ @@    @@ @ @@
193 //  @@     @@@@@  @@@@  @@@@@@   @@   @@@@   @@@@@ @@ @@@@  @@@@@@@
194 //  @@     @@  @@ @@    @@  @@   @@   @@      @@@  @@ @@    @@@@@@@
195 //  @@  @@ @@  @@ @@    @@  @@   @@   @@      @@@  @@ @@    @@@ @@@
196 //   @@@@  @@  @@ @@@@@ @@  @@   @@   @@@@@    @   @@ @@@@@ @@   @@
197 //
198 ////////////////////////////////////////////////////////////////////////////////////////////////////
199 ////////////////////////////////////////////////////////////////////////////////////////////////////
200 
ImpClearConnectMarker()201 void SdrCreateView::ImpClearConnectMarker()
202 {
203 	if(mpCoMaOverlay)
204 	{
205 		delete mpCoMaOverlay;
206 		mpCoMaOverlay = 0L;
207 	}
208 }
209 
ImpClearVars()210 void SdrCreateView::ImpClearVars()
211 {
212 	nAktInvent=SdrInventor;
213 	nAktIdent=OBJ_NONE;
214 	pAktCreate=NULL;
215 	pCreatePV=NULL;
216 	bAutoTextEdit=sal_False;
217 	b1stPointAsCenter=sal_False;
218 	aAktCreatePointer=Pointer(POINTER_CROSS);
219 	bUseIncompatiblePathCreateInterface=sal_False;
220 	bAutoClosePolys=sal_True;
221 	nAutoCloseDistPix=5;
222 	nFreeHandMinDistPix=10;
223 
224 	ImpClearConnectMarker();
225 }
226 
ImpMakeCreateAttr()227 void SdrCreateView::ImpMakeCreateAttr()
228 {
229 }
230 
SdrCreateView(SdrModel * pModel1,OutputDevice * pOut)231 SdrCreateView::SdrCreateView(SdrModel* pModel1, OutputDevice* pOut)
232 :	SdrDragView(pModel1,pOut),
233 	mpCoMaOverlay(0L),
234 	mpCreateViewExtraData(new ImpSdrCreateViewExtraData())
235 {
236 	ImpClearVars();
237 	ImpMakeCreateAttr();
238 }
239 
~SdrCreateView()240 SdrCreateView::~SdrCreateView()
241 {
242 	ImpClearConnectMarker();
243 	delete mpCreateViewExtraData;
244     SdrObject::Free( pAktCreate );
245 }
246 
ImpDelCreateAttr()247 void SdrCreateView::ImpDelCreateAttr()
248 {
249 }
250 
IsAction() const251 sal_Bool SdrCreateView::IsAction() const
252 {
253 	return SdrDragView::IsAction() || pAktCreate!=NULL;
254 }
255 
MovAction(const Point & rPnt)256 void SdrCreateView::MovAction(const Point& rPnt)
257 {
258 	SdrDragView::MovAction(rPnt);
259 	if (pAktCreate!=NULL) {
260 		MovCreateObj(rPnt);
261 	}
262 }
263 
EndAction()264 void SdrCreateView::EndAction()
265 {
266 	if (pAktCreate!=NULL) EndCreateObj(SDRCREATE_FORCEEND);
267 	SdrDragView::EndAction();
268 }
269 
BckAction()270 void SdrCreateView::BckAction()
271 {
272 	if (pAktCreate!=NULL) BckCreateObj();
273 	SdrDragView::BckAction();
274 }
275 
BrkAction()276 void SdrCreateView::BrkAction()
277 {
278 	SdrDragView::BrkAction();
279 	BrkCreateObj();
280 }
281 
TakeActionRect(Rectangle & rRect) const282 void SdrCreateView::TakeActionRect(Rectangle& rRect) const
283 {
284 	if (pAktCreate!=NULL)
285 	{
286 		rRect=aDragStat.GetActionRect();
287 		if (rRect.IsEmpty())
288 		{
289 			rRect=Rectangle(aDragStat.GetPrev(),aDragStat.GetNow());
290 		}
291 	}
292 	else
293 	{
294 		SdrDragView::TakeActionRect(rRect);
295 	}
296 }
297 
CheckEdgeMode()298 sal_Bool SdrCreateView::CheckEdgeMode()
299 {
300 	sal_uInt32 nInv=nAktInvent;
301 	sal_uInt16 nIdn=nAktIdent;
302 	if (pAktCreate!=NULL)
303 	{
304 		nInv=pAktCreate->GetObjInventor();
305 		nIdn=pAktCreate->GetObjIdentifier();
306 		// wird vom EdgeObj gemanaged
307 		if (nAktInvent==SdrInventor && nAktIdent==OBJ_EDGE) return sal_False;
308 	}
309 
310 	if (!IsCreateMode() || nAktInvent!=SdrInventor || nAktIdent!=OBJ_EDGE)
311 	{
312 		ImpClearConnectMarker();
313 		return sal_False;
314 	}
315 	else
316 	{
317 		// sal_True heisst: MouseMove soll Connect checken
318 		return !IsAction();
319 	}
320 }
321 
SetConnectMarker(const SdrObjConnection & rCon,const SdrPageView &)322 void SdrCreateView::SetConnectMarker(const SdrObjConnection& rCon, const SdrPageView& /*rPV*/)
323 {
324 	SdrObject* pTargetObject = rCon.pObj;
325 
326 	if(pTargetObject)
327 	{
328 		// if target object changes, throw away overlay object to make room for changes
329 		if(mpCoMaOverlay && pTargetObject != &mpCoMaOverlay->GetTargetObject())
330 		{
331 			ImpClearConnectMarker();
332 		}
333 
334 		if(!mpCoMaOverlay)
335 		{
336 			mpCoMaOverlay = new ImplConnectMarkerOverlay(*this, *pTargetObject);
337 		}
338 	}
339 	else
340 	{
341 		ImpClearConnectMarker();
342 	}
343 }
344 
HideConnectMarker()345 void SdrCreateView::HideConnectMarker()
346 {
347 	ImpClearConnectMarker();
348 }
349 
MouseMove(const MouseEvent & rMEvt,Window * pWin)350 sal_Bool SdrCreateView::MouseMove(const MouseEvent& rMEvt, Window* pWin)
351 {
352 	if(CheckEdgeMode() && pWin)
353 	{
354 		SdrPageView* pPV = GetSdrPageView();
355 
356 		if(pPV)
357 		{
358 			// Defaultete Hit-Toleranz bei IsMarkedHit() mal aendern !!!!
359 			Point aPos(pWin->PixelToLogic(rMEvt.GetPosPixel()));
360 			sal_Bool bMarkHit=PickHandle(aPos)!=NULL || IsMarkedObjHit(aPos);
361 			SdrObjConnection aCon;
362 			if (!bMarkHit) SdrEdgeObj::ImpFindConnector(aPos,*pPV,aCon,NULL,pWin);
363 			SetConnectMarker(aCon,*pPV);
364 		}
365 	}
366 	return SdrDragView::MouseMove(rMEvt,pWin);
367 }
368 
IsTextTool() const369 sal_Bool SdrCreateView::IsTextTool() const
370 {
371 	return eEditMode==SDREDITMODE_CREATE && nAktInvent==SdrInventor && (nAktIdent==OBJ_TEXT || nAktIdent==OBJ_TEXTEXT || nAktIdent==OBJ_TITLETEXT || nAktIdent==OBJ_OUTLINETEXT);
372 }
373 
IsEdgeTool() const374 sal_Bool SdrCreateView::IsEdgeTool() const
375 {
376 	return eEditMode==SDREDITMODE_CREATE && nAktInvent==SdrInventor && (nAktIdent==OBJ_EDGE);
377 }
378 
IsMeasureTool() const379 sal_Bool SdrCreateView::IsMeasureTool() const
380 {
381 	return eEditMode==SDREDITMODE_CREATE && nAktInvent==SdrInventor && (nAktIdent==OBJ_MEASURE);
382 }
383 
SetCurrentObj(sal_uInt16 nIdent,sal_uInt32 nInvent)384 void SdrCreateView::SetCurrentObj(sal_uInt16 nIdent, sal_uInt32 nInvent)
385 {
386 	if (nAktInvent!=nInvent || nAktIdent!=nIdent)
387 	{
388 		nAktInvent=nInvent;
389 		nAktIdent=nIdent;
390 		SdrObject* pObj = SdrObjFactory::MakeNewObject(nInvent,nIdent,NULL,NULL);
391 
392 		if(pObj)
393 		{
394 			// Auf pers. Wunsch von Marco:
395 			// Mauszeiger bei Textwerkzeug immer I-Beam. Fadenkreuz
396 			// mit kleinem I-Beam erst bai MouseButtonDown
397 			if(IsTextTool())
398 			{
399 				// #81944# AW: Here the correct pointer needs to be used
400 				// if the default is set to vertical writing
401 				aAktCreatePointer = POINTER_TEXT;
402 			}
403 			else
404 				aAktCreatePointer = pObj->GetCreatePointer();
405 
406 			SdrObject::Free( pObj );
407 		}
408 		else
409 		{
410 			aAktCreatePointer = Pointer(POINTER_CROSS);
411 		}
412 	}
413 
414 	CheckEdgeMode();
415 	ImpSetGlueVisible3(IsEdgeTool());
416 }
417 
ImpBegCreateObj(sal_uInt32 nInvent,sal_uInt16 nIdent,const Point & rPnt,OutputDevice * pOut,short nMinMov,SdrPageView * pPV,const Rectangle & rLogRect,SdrObject * pPreparedFactoryObject)418 sal_Bool SdrCreateView::ImpBegCreateObj(sal_uInt32 nInvent, sal_uInt16 nIdent, const Point& rPnt, OutputDevice* pOut,
419 	short nMinMov, SdrPageView* pPV, const Rectangle& rLogRect, SdrObject* pPreparedFactoryObject)
420 {
421 	sal_Bool bRet=sal_False;
422 	UnmarkAllObj();
423 	BrkAction();
424 
425 	ImpClearConnectMarker();
426 
427 	if (pPV!=NULL)
428 	{
429 		pCreatePV=pPV;
430 	}
431 	else
432 	{
433 		pCreatePV = GetSdrPageView();
434 	}
435 	if (pCreatePV!=NULL)
436 	{ // ansonsten keine Seite angemeldet!
437 		String aLay(aAktLayer);
438 
439 		if(nInvent == SdrInventor && nIdent == OBJ_MEASURE && aMeasureLayer.Len())
440 		{
441 			aLay = aMeasureLayer;
442 		}
443 
444 		SdrLayerID nLayer=pCreatePV->GetPage()->GetLayerAdmin().GetLayerID(aLay,sal_True);
445 		if (nLayer==SDRLAYER_NOTFOUND) nLayer=0;
446 		if (!pCreatePV->GetLockedLayers().IsSet(nLayer) && pCreatePV->GetVisibleLayers().IsSet(nLayer))
447 		{
448 			if(pPreparedFactoryObject)
449 			{
450 				pAktCreate = pPreparedFactoryObject;
451 
452 				if(pCreatePV->GetPage())
453 				{
454 					pAktCreate->SetPage(pCreatePV->GetPage());
455 				}
456 				else if (pMod)
457 				{
458 					pAktCreate->SetModel(pMod);
459 				}
460 			}
461 			else
462 			{
463 				pAktCreate = SdrObjFactory::MakeNewObject(nInvent, nIdent, pCreatePV->GetPage(), pMod);
464 			}
465 
466 			Point aPnt(rPnt);
467 			if (nAktInvent!=SdrInventor || (nAktIdent!=sal_uInt16(OBJ_EDGE) &&
468 											nAktIdent!=sal_uInt16(OBJ_FREELINE) &&
469 											nAktIdent!=sal_uInt16(OBJ_FREEFILL) )) { // Kein Fang fuer Edge und Freihand!
470 				aPnt=GetSnapPos(aPnt,pCreatePV);
471 			}
472 			if (pAktCreate!=NULL)
473 			{
474 				sal_Bool bStartEdit=sal_False; // nach Ende von Create automatisch TextEdit starten
475 				if (pDefaultStyleSheet!=NULL) pAktCreate->NbcSetStyleSheet(pDefaultStyleSheet, sal_False);
476 
477 				// #101618# SW uses a naked SdrObject for frame construction. Normally, such an
478 				// object should not be created. Since it is possible to use it as a helper
479 				// object (e.g. in letting the user define an area with the interactive
480 				// construction) at least no items should be set at that object.
481 				if(nInvent != SdrInventor || nIdent != OBJ_NONE)
482 				{
483 					pAktCreate->SetMergedItemSet(aDefaultAttr);
484 				}
485 
486 				if (HAS_BASE(SdrCaptionObj,pAktCreate))
487 				{
488 					SfxItemSet aSet(pMod->GetItemPool());
489 					aSet.Put(XFillColorItem(String(),Color(COL_WHITE))); // Falls einer auf Solid umschaltet
490 					aSet.Put(XFillStyleItem(XFILL_NONE));
491 
492 					pAktCreate->SetMergedItemSet(aSet);
493 
494 					bStartEdit=sal_True;
495 				}
496 				if (nInvent==SdrInventor && (nIdent==OBJ_TEXT || nIdent==OBJ_TEXTEXT ||
497 					nIdent==OBJ_TITLETEXT || nIdent==OBJ_OUTLINETEXT))
498 				{
499 					// Fuer alle Textrahmen default keinen Hintergrund und keine Umrandung
500 					SfxItemSet aSet(pMod->GetItemPool());
501 					aSet.Put(XFillColorItem(String(),Color(COL_WHITE))); // Falls einer auf Solid umschaltet
502 					aSet.Put(XFillStyleItem(XFILL_NONE));
503 					aSet.Put(XLineColorItem(String(),Color(COL_BLACK))); // Falls einer auf Solid umschaltet
504 					aSet.Put(XLineStyleItem(XLINE_NONE));
505 
506 					pAktCreate->SetMergedItemSet(aSet);
507 
508 					bStartEdit=sal_True;
509 				}
510 				if (!rLogRect.IsEmpty()) pAktCreate->NbcSetLogicRect(rLogRect);
511 
512 				// #90129# make sure drag start point is inside WorkArea
513 				const Rectangle& rWorkArea = ((SdrDragView*)this)->GetWorkArea();
514 
515 				if(!rWorkArea.IsEmpty())
516 				{
517 					if(aPnt.X() < rWorkArea.Left())
518 					{
519 						aPnt.X() = rWorkArea.Left();
520 					}
521 
522 					if(aPnt.X() > rWorkArea.Right())
523 					{
524 						aPnt.X() = rWorkArea.Right();
525 					}
526 
527 					if(aPnt.Y() < rWorkArea.Top())
528 					{
529 						aPnt.Y() = rWorkArea.Top();
530 					}
531 
532 					if(aPnt.Y() > rWorkArea.Bottom())
533 					{
534 						aPnt.Y() = rWorkArea.Bottom();
535 					}
536 				}
537 
538 				aDragStat.Reset(aPnt);
539 				aDragStat.SetView((SdrView*)this);
540 				aDragStat.SetPageView(pCreatePV);
541 				aDragStat.SetMinMove(ImpGetMinMovLogic(nMinMov,pOut));
542 				pDragWin=pOut;
543 				if (pAktCreate->BegCreate(aDragStat))
544 				{
545 					ShowCreateObj(/*pOut,sal_True*/);
546 					bRet=sal_True;
547 				}
548 				else
549 				{
550 					SdrObject::Free( pAktCreate );
551 					pAktCreate=NULL;
552 					pCreatePV=NULL;
553 				}
554 			}
555 		}
556 	}
557 	return bRet;
558 }
559 
BegCreateObj(const Point & rPnt,OutputDevice * pOut,short nMinMov,SdrPageView * pPV)560 sal_Bool SdrCreateView::BegCreateObj(const Point& rPnt, OutputDevice* pOut, short nMinMov, SdrPageView* pPV)
561 {
562 	return ImpBegCreateObj(nAktInvent,nAktIdent,rPnt,pOut,nMinMov,pPV,Rectangle(), 0L);
563 }
564 
BegCreatePreparedObject(const Point & rPnt,sal_Int16 nMinMov,SdrObject * pPreparedFactoryObject)565 sal_Bool SdrCreateView::BegCreatePreparedObject(const Point& rPnt, sal_Int16 nMinMov, SdrObject* pPreparedFactoryObject)
566 {
567 	sal_uInt32 nInvent(nAktInvent);
568 	sal_uInt16 nIdent(nAktIdent);
569 
570 	if(pPreparedFactoryObject)
571 	{
572 		nInvent = pPreparedFactoryObject->GetObjInventor();
573 		nIdent = pPreparedFactoryObject->GetObjIdentifier();
574 	}
575 
576 	return ImpBegCreateObj(nInvent, nIdent, rPnt, 0L, nMinMov, 0L, Rectangle(), pPreparedFactoryObject);
577 }
578 
BegCreateCaptionObj(const Point & rPnt,const Size & rObjSiz,OutputDevice * pOut,short nMinMov,SdrPageView * pPV)579 sal_Bool SdrCreateView::BegCreateCaptionObj(const Point& rPnt, const Size& rObjSiz,
580 	OutputDevice* pOut, short nMinMov, SdrPageView* pPV)
581 {
582 	return ImpBegCreateObj(SdrInventor,OBJ_CAPTION,rPnt,pOut,nMinMov,pPV,
583 		Rectangle(rPnt,Size(rObjSiz.Width()+1,rObjSiz.Height()+1)), 0L);
584 }
585 
MovCreateObj(const Point & rPnt)586 void SdrCreateView::MovCreateObj(const Point& rPnt)
587 {
588 	if (pAktCreate!=NULL) {
589 		Point aPnt(rPnt);
590 		if (!aDragStat.IsNoSnap())
591 		{
592 			aPnt=GetSnapPos(aPnt,pCreatePV);
593 		}
594 		if (IsOrtho())
595 		{
596 			if (aDragStat.IsOrtho8Possible()) OrthoDistance8(aDragStat.GetPrev(),aPnt,IsBigOrtho());
597 			else if (aDragStat.IsOrtho4Possible()) OrthoDistance4(aDragStat.GetPrev(),aPnt,IsBigOrtho());
598 		}
599 
600 		// #77734# If the drag point was limited and Ortho is active, do
601 		// the small ortho correction (reduction) -> last parameter to FALSE.
602 		sal_Bool bDidLimit(ImpLimitToWorkArea(aPnt));
603 		if(bDidLimit && IsOrtho())
604 		{
605 			if(aDragStat.IsOrtho8Possible())
606 				OrthoDistance8(aDragStat.GetPrev(), aPnt, sal_False);
607 			else if(aDragStat.IsOrtho4Possible())
608 				OrthoDistance4(aDragStat.GetPrev(), aPnt, sal_False);
609 		}
610 
611 		if (aPnt==aDragStat.GetNow()) return;
612 		bool bMerk(aDragStat.IsMinMoved());
613 		if (aDragStat.CheckMinMoved(aPnt))
614 		{
615 			Rectangle aBound;
616 			if (!bMerk) aDragStat.NextPoint();
617 			aDragStat.NextMove(aPnt);
618 			pAktCreate->MovCreate(aDragStat);
619 
620 			// MovCreate changes the object, so use ActionChanged() on it
621 			pAktCreate->ActionChanged();
622 
623 			// replace for DrawCreateObjDiff
624 			HideCreateObj();
625 			ShowCreateObj();
626 		}
627 	}
628 }
629 
EndCreateObj(SdrCreateCmd eCmd)630 sal_Bool SdrCreateView::EndCreateObj(SdrCreateCmd eCmd)
631 {
632 	sal_Bool bRet=sal_False;
633 	SdrObject* pObjMerk=pAktCreate;
634 	SdrPageView* pPVMerk=pCreatePV;
635 
636 	if (pAktCreate!=NULL)
637 	{
638 		sal_uIntPtr nAnz=aDragStat.GetPointAnz();
639 
640 		if (nAnz<=1 && eCmd==SDRCREATE_FORCEEND)
641 		{
642 			BrkCreateObj(); // Objekte mit nur einem Punkt gibt's nicht (zumindest noch nicht)
643 			return sal_False; // sal_False=Event nicht ausgewertet
644 		}
645 
646 		sal_Bool bPntsEq=nAnz>1;
647 		sal_uIntPtr i=1;
648 		Point aP0=aDragStat.GetPoint(0);
649 		while (bPntsEq && i<nAnz) { bPntsEq=aP0==aDragStat.GetPoint(i); i++; }
650 
651 		if (pAktCreate->EndCreate(aDragStat,eCmd))
652 		{
653 			HideCreateObj();
654 
655 			if (!bPntsEq)
656 			{
657 				// sonst Brk, weil alle Punkte gleich sind.
658 				SdrObject* pObj=pAktCreate;
659 				pAktCreate=NULL;
660 
661 				const SdrLayerAdmin& rAd = pCreatePV->GetPage()->GetLayerAdmin();
662 				SdrLayerID nLayer(0);
663 
664 				// #i72535#
665 				if(pObj->ISA(FmFormObj))
666 				{
667 					// for FormControls, force to form layer
668 					nLayer = rAd.GetLayerID(rAd.GetControlLayerName(), true);
669 				}
670 				else
671 				{
672 					nLayer = rAd.GetLayerID(aAktLayer, sal_True);
673 				}
674 
675 				if(SDRLAYER_NOTFOUND == nLayer)
676 				{
677 					nLayer=0;
678 				}
679 
680 				pObj->SetLayer(nLayer);
681 
682 				// #83403# recognize creation of a new 3D object inside a 3D scene
683 				sal_Bool bSceneIntoScene(sal_False);
684 
685 				if(pObjMerk
686 					&& pObjMerk->ISA(E3dScene)
687 					&& pCreatePV
688 					&& pCreatePV->GetAktGroup()
689 					&& pCreatePV->GetAktGroup()->ISA(E3dScene))
690 				{
691 					sal_Bool bDidInsert = ((E3dView*)this)->ImpCloneAll3DObjectsToDestScene(
692 						(E3dScene*)pObjMerk, (E3dScene*)pCreatePV->GetAktGroup(), Point(0, 0));
693 
694 					if(bDidInsert)
695 					{
696 						// delete object, it's content is cloned and inserted
697                         SdrObject::Free( pObjMerk );
698 						pObjMerk = 0L;
699 						bRet = sal_False;
700 						bSceneIntoScene = sal_True;
701 					}
702 				}
703 
704 				if(!bSceneIntoScene)
705 				{
706 					// do the same as before
707 					InsertObjectAtView(pObj, *pCreatePV);
708 				}
709 
710 				pCreatePV=NULL;
711 				bRet=sal_True; // sal_True=Event ausgewertet
712 			}
713 			else
714 			{
715 				BrkCreateObj();
716 			}
717 		}
718 		else
719 		{ // Mehr Punkte
720 			if (eCmd==SDRCREATE_FORCEEND || // nix da, Ende erzwungen
721 				nAnz==0 ||                             // keine Punkte da (kann eigentlich nicht vorkommen)
722 				(nAnz<=1 && !aDragStat.IsMinMoved())) { // MinMove nicht erfuellt
723 				BrkCreateObj();
724 			}
725 			else
726 			{
727 				// replace for DrawCreateObjDiff
728 				HideCreateObj();
729 				ShowCreateObj();
730 				aDragStat.ResetMinMoved(); // NextPoint gibt's bei MovCreateObj()
731 				bRet=sal_True;
732 			}
733 		}
734 		if (bRet && pObjMerk!=NULL && IsTextEditAfterCreate())
735 		{
736 			SdrTextObj* pText=PTR_CAST(SdrTextObj,pObjMerk);
737 			if (pText!=NULL && pText->IsTextFrame())
738 			{
739 				SdrBeginTextEdit(pText, pPVMerk, (Window*)0L, sal_True, (SdrOutliner*)0L, (OutlinerView*)0L);
740 			}
741 		}
742 	}
743 	return bRet;
744 }
745 
BckCreateObj()746 void SdrCreateView::BckCreateObj()
747 {
748 	if (pAktCreate!=NULL)
749 	{
750 		if (aDragStat.GetPointAnz()<=2 )
751 		{
752 			BrkCreateObj();
753 		}
754 		else
755 		{
756 			HideCreateObj();
757 			aDragStat.PrevPoint();
758 			if (pAktCreate->BckCreate(aDragStat))
759 			{
760 				ShowCreateObj();
761 			}
762 			else
763 			{
764 				BrkCreateObj();
765 			}
766 		}
767 	}
768 }
769 
BrkCreateObj()770 void SdrCreateView::BrkCreateObj()
771 {
772 	if (pAktCreate!=NULL)
773 	{
774 		HideCreateObj();
775 		pAktCreate->BrkCreate(aDragStat);
776 		SdrObject::Free( pAktCreate );
777 		pAktCreate=NULL;
778 		pCreatePV=NULL;
779 	}
780 }
781 
ShowCreateObj()782 void SdrCreateView::ShowCreateObj(/*OutputDevice* pOut, sal_Bool bFull*/)
783 {
784 	if(IsCreateObj() && !aDragStat.IsShown())
785 	{
786 		if(pAktCreate)
787 		{
788 			// for migration from XOR, replace DrawDragObj here to create
789 			// overlay objects instead.
790 			sal_Bool bUseSolidDragging(IsSolidDragging());
791 
792 			// #i101648# check if dragged object is a naked SdrObject (no
793 			// derivation of). This is e.g. used in SW Frame construction
794 			// as placeholder. Do not use SolidDragging for naked SDrObjects,
795 			// they cannot have a valid optical representation
796 			if(bUseSolidDragging && OBJ_NONE == pAktCreate->GetObjIdentifier())
797 			{
798 				bUseSolidDragging = false;
799 			}
800 
801 			// check for objects with no fill and no line
802 			if(bUseSolidDragging)
803 			{
804 				const SfxItemSet& rSet = pAktCreate->GetMergedItemSet();
805 				const XFillStyle eFill(((XFillStyleItem&)(rSet.Get(XATTR_FILLSTYLE))).GetValue());
806 				const XLineStyle eLine(((XLineStyleItem&)(rSet.Get(XATTR_LINESTYLE))).GetValue());
807 
808 				if(XLINE_NONE == eLine && XFILL_NONE == eFill)
809 				{
810 					bUseSolidDragging = sal_False;
811 				}
812 			}
813 
814 			// check for form controls
815 			if(bUseSolidDragging)
816 			{
817 				if(pAktCreate->ISA(SdrUnoObj))
818 				{
819 					bUseSolidDragging = sal_False;
820 				}
821 			}
822 
823   			// #i101781# force to non-solid dragging when not creating a full circle
824 			if(bUseSolidDragging)
825             {
826                 SdrCircObj* pCircObj = dynamic_cast< SdrCircObj* >(pAktCreate);
827 
828                 if(pCircObj && OBJ_CIRC != pCircObj->GetObjIdentifier())
829                 {
830                     // #i103058# Allow SolidDragging with four points
831                     if(aDragStat.GetPointAnz() < 4)
832                     {
833         				bUseSolidDragging = false;
834                     }
835                 }
836             }
837 
838 			if(bUseSolidDragging)
839 			{
840 				basegfx::B2DPolyPolygon aDragPolyPolygon;
841 
842 				if(pAktCreate->ISA(SdrRectObj))
843 				{
844 					// ensure object has some size, necessary for SdrTextObj because
845 					// there are still untested divisions by that sizes
846 					Rectangle aCurrentSnapRect(pAktCreate->GetSnapRect());
847 
848 					if(!(aCurrentSnapRect.GetWidth() > 1 && aCurrentSnapRect.GetHeight() > 1))
849 					{
850 						Rectangle aNewRect(aDragStat.GetStart(), aDragStat.GetStart() + Point(2, 2));
851 						pAktCreate->NbcSetSnapRect(aNewRect);
852 					}
853 				}
854 
855 				if(pAktCreate->ISA(SdrPathObj))
856 				{
857 					// The up-to-now created path needs to be set at the object to have something
858 					// that can be visualized
859 					SdrPathObj& rPathObj((SdrPathObj&)(*pAktCreate));
860 					const basegfx::B2DPolyPolygon aCurrentPolyPolygon(rPathObj.getObjectPolyPolygon(aDragStat));
861 
862 					if(aCurrentPolyPolygon.count())
863 					{
864 						rPathObj.NbcSetPathPoly(aCurrentPolyPolygon);
865 					}
866 
867 					aDragPolyPolygon = rPathObj.getDragPolyPolygon(aDragStat);
868 				}
869 
870 				// use directly the SdrObject for overlay
871 				mpCreateViewExtraData->CreateAndShowOverlay(*this, pAktCreate, aDragPolyPolygon);
872 			}
873 			else
874 			{
875 				mpCreateViewExtraData->CreateAndShowOverlay(*this, 0, pAktCreate->TakeCreatePoly(aDragStat));
876 			}
877 
878 			// #i101679# Force changed overlay to be shown
879 			for(sal_uInt32 a(0); a < PaintWindowCount(); a++)
880 			{
881 				SdrPaintWindow* pCandidate = GetPaintWindow(a);
882 				sdr::overlay::OverlayManager* pOverlayManager = pCandidate->GetOverlayManager();
883 
884 				if(pOverlayManager)
885 				{
886 					pOverlayManager->flush();
887 				}
888 			}
889 		}
890 
891 		aDragStat.SetShown(sal_True);
892 	}
893 }
894 
HideCreateObj()895 void SdrCreateView::HideCreateObj()
896 {
897 	if(IsCreateObj() && aDragStat.IsShown())
898 	{
899 		// for migration from XOR, replace DrawDragObj here to create
900 		// overlay objects instead.
901 		mpCreateViewExtraData->HideOverlay();
902 
903 		//DrawCreateObj(pOut,bFull);
904 		aDragStat.SetShown(sal_False);
905 	}
906 }
907 
908 ////////////////////////////////////////////////////////////////////////////////////////////////////
909 
910 /* new interface src537 */
GetAttributes(SfxItemSet & rTargetSet,sal_Bool bOnlyHardAttr) const911 sal_Bool SdrCreateView::GetAttributes(SfxItemSet& rTargetSet, sal_Bool bOnlyHardAttr) const
912 {
913 	if(pAktCreate)
914 	{
915 		rTargetSet.Put(pAktCreate->GetMergedItemSet());
916 		return sal_True;
917 	}
918 	else
919 	{
920 		return SdrDragView::GetAttributes(rTargetSet, bOnlyHardAttr);
921 	}
922 }
923 
SetAttributes(const SfxItemSet & rSet,sal_Bool bReplaceAll)924 sal_Bool SdrCreateView::SetAttributes(const SfxItemSet& rSet, sal_Bool bReplaceAll)
925 {
926 	if(pAktCreate)
927 	{
928 		pAktCreate->SetMergedItemSetAndBroadcast(rSet, bReplaceAll);
929 
930 		return sal_True;
931 	}
932 	else
933 	{
934 		return SdrDragView::SetAttributes(rSet,bReplaceAll);
935 	}
936 }
937 
GetStyleSheet() const938 SfxStyleSheet* SdrCreateView::GetStyleSheet() const // SfxStyleSheet* SdrCreateView::GetStyleSheet(sal_Bool& rOk) const
939 {
940 	if (pAktCreate!=NULL)
941 	{
942 		//rOk=sal_True;
943 		return pAktCreate->GetStyleSheet();
944 	}
945 	else
946 	{
947 		return SdrDragView::GetStyleSheet(); // SdrDragView::GetStyleSheet(rOk);
948 	}
949 }
950 
SetStyleSheet(SfxStyleSheet * pStyleSheet,sal_Bool bDontRemoveHardAttr)951 sal_Bool SdrCreateView::SetStyleSheet(SfxStyleSheet* pStyleSheet, sal_Bool bDontRemoveHardAttr)
952 {
953 	if (pAktCreate!=NULL)
954 	{
955 		pAktCreate->SetStyleSheet(pStyleSheet,bDontRemoveHardAttr);
956 		return sal_True;
957 	}
958 	else
959 	{
960 		return SdrDragView::SetStyleSheet(pStyleSheet,bDontRemoveHardAttr);
961 	}
962 }
963 
964