xref: /trunk/main/sd/source/ui/func/fucopy.cxx (revision c7be74b1)
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_sd.hxx"
26 
27 
28 #include "fucopy.hxx"
29 #include <sfx2/progress.hxx>
30 #include <svx/svxids.hrc>
31 
32 #include "sdresid.hxx"
33 #include "sdattr.hxx"
34 #include "strings.hrc"
35 #include "ViewShell.hxx"
36 #include "View.hxx"
37 #include "drawdoc.hxx"
38 #include "DrawDocShell.hxx"
39 #include <vcl/wrkwin.hxx>
40 #include <svx/svdobj.hxx>
41 #include <vcl/msgbox.hxx>
42 #include <sfx2/app.hxx>
43 #include <svx/xcolit.hxx>
44 #include <svx/xflclit.hxx>
45 #include <svx/xdef.hxx>
46 #include <svx/xfillit0.hxx>
47 #include <sfx2/request.hxx>
48 #include "sdabstdlg.hxx"
49 #include "copydlg.hrc"
50 namespace sd {
51 
52 TYPEINIT1( FuCopy, FuPoor );
53 
54 /*************************************************************************
55 |*
56 |* Konstruktor
57 |*
58 \************************************************************************/
59 
FuCopy(ViewShell * pViewSh,::sd::Window * pWin,::sd::View * pView,SdDrawDocument * pDoc,SfxRequest & rReq)60 FuCopy::FuCopy (
61     ViewShell* pViewSh,
62     ::sd::Window* pWin,
63     ::sd::View* pView,
64     SdDrawDocument* pDoc,
65     SfxRequest& rReq)
66 	: FuPoor(pViewSh, pWin, pView, pDoc, rReq)
67 {
68 }
69 
Create(ViewShell * pViewSh,::sd::Window * pWin,::sd::View * pView,SdDrawDocument * pDoc,SfxRequest & rReq)70 FunctionReference FuCopy::Create( ViewShell* pViewSh, ::sd::Window* pWin, ::sd::View* pView, SdDrawDocument* pDoc, SfxRequest& rReq )
71 {
72 	FunctionReference xFunc( new FuCopy( pViewSh, pWin, pView, pDoc, rReq ) );
73 	xFunc->DoExecute(rReq);
74 	return xFunc;
75 }
76 
DoExecute(SfxRequest & rReq)77 void FuCopy::DoExecute( SfxRequest& rReq )
78 {
79 	if( mpView->AreObjectsMarked() )
80 	{
81 		// Undo
82 		String aString( mpView->GetDescriptionOfMarkedObjects() );
83 		aString.Append( sal_Unicode(' ') );
84 		aString.Append( String( SdResId( STR_UNDO_COPYOBJECTS ) ) );
85 		mpView->BegUndo( aString );
86 
87 		const SfxItemSet* pArgs = rReq.GetArgs();
88 
89 		if( !pArgs )
90 		{
91 			SfxItemSet aSet( mpViewShell->GetPool(),
92 								ATTR_COPY_START, ATTR_COPY_END, 0 );
93 
94 			// Farb-Attribut angeben
95 			SfxItemSet aAttr( mpDoc->GetPool() );
96 			mpView->GetAttributes( aAttr );
97 			const SfxPoolItem*	pPoolItem = NULL;
98 
99 			if( SFX_ITEM_SET == aAttr.GetItemState( XATTR_FILLSTYLE, sal_True, &pPoolItem ) )
100 			{
101 				XFillStyle eStyle = ( ( const XFillStyleItem* ) pPoolItem )->GetValue();
102 
103 				if( eStyle == XFILL_SOLID &&
104 					SFX_ITEM_SET == aAttr.GetItemState( XATTR_FILLCOLOR, sal_True, &pPoolItem ) )
105 				{
106 					const XFillColorItem* pItem = ( const XFillColorItem* ) pPoolItem;
107 					XColorItem aXColorItem( ATTR_COPY_START_COLOR, pItem->GetName(),
108 														pItem->GetColorValue() );
109 					aSet.Put( aXColorItem );
110 
111 				}
112 			}
113 
114 			SdAbstractDialogFactory* pFact = SdAbstractDialogFactory::Create();
115 			if( pFact )
116 			{
117 				AbstractCopyDlg* pDlg = pFact->CreateCopyDlg(NULL, aSet, mpDoc->GetColorTableFromSdrModel(), mpView );
118 				if( pDlg )
119 				{
120 					sal_uInt16 nResult = pDlg->Execute();
121 
122 					switch( nResult )
123 					{
124 						case RET_OK:
125 							pDlg->GetAttr( aSet );
126 							rReq.Done( aSet );
127 							pArgs = rReq.GetArgs();
128 						break;
129 
130 						default:
131 						{
132 							delete pDlg;
133 							mpView->EndUndo();
134 						}
135 						return; // Abbruch
136 					}
137 					delete( pDlg );
138 				}
139 			}
140 		}
141 
142 		Rectangle	        aRect;
143 		sal_Int32		        lWidth = 0, lHeight = 0, lSizeX = 0L, lSizeY = 0L, lAngle = 0L;
144 		sal_uInt16		        nNumber = 0;
145 		Color		        aStartColor, aEndColor;
146 		sal_Bool		        bColor = sal_False;
147 		const SfxPoolItem*  pPoolItem = NULL;
148 
149 		// Anzahl
150 		if( SFX_ITEM_SET == pArgs->GetItemState( ATTR_COPY_NUMBER, sal_True, &pPoolItem ) )
151 			nNumber = ( ( const SfxUInt16Item* ) pPoolItem )->GetValue();
152 
153 		// Verschiebung
154 		if( SFX_ITEM_SET == pArgs->GetItemState( ATTR_COPY_MOVE_X, sal_True, &pPoolItem ) )
155 			lSizeX = ( ( const SfxInt32Item* ) pPoolItem )->GetValue();
156 		if( SFX_ITEM_SET == pArgs->GetItemState( ATTR_COPY_MOVE_Y, sal_True, &pPoolItem ) )
157 			lSizeY = ( ( const SfxInt32Item* ) pPoolItem )->GetValue();
158 		if( SFX_ITEM_SET == pArgs->GetItemState( ATTR_COPY_ANGLE, sal_True, &pPoolItem ) )
159 			lAngle = ( ( const SfxInt32Item* )pPoolItem )->GetValue();
160 
161 		// Verrgroesserung / Verkleinerung
162 		if( SFX_ITEM_SET == pArgs->GetItemState( ATTR_COPY_WIDTH, sal_True, &pPoolItem ) )
163 			lWidth = ( ( const SfxInt32Item* ) pPoolItem )->GetValue();
164 		if( SFX_ITEM_SET == pArgs->GetItemState( ATTR_COPY_HEIGHT, sal_True, &pPoolItem ) )
165 			lHeight = ( ( const SfxInt32Item* ) pPoolItem )->GetValue();
166 
167 		// Startfarbe / Endfarbe
168 		if( SFX_ITEM_SET == pArgs->GetItemState( ATTR_COPY_START_COLOR, sal_True, &pPoolItem ) )
169 		{
170 			aStartColor = ( ( const XColorItem* ) pPoolItem )->GetColorValue();
171 			bColor = sal_True;
172 		}
173 		if( SFX_ITEM_SET == pArgs->GetItemState( ATTR_COPY_END_COLOR, sal_True, &pPoolItem ) )
174 		{
175 			aEndColor = ( ( const XColorItem* ) pPoolItem )->GetColorValue();
176 			if( aStartColor == aEndColor )
177 				bColor = sal_False;
178 		}
179 		else
180 			bColor = sal_False;
181 
182 		// Handles wegnehmen
183 		//HMHmpView->HideMarkHdl();
184 
185 		SfxProgress*    pProgress = NULL;
186 		sal_Bool            bWaiting = sal_False;
187 
188 		if( nNumber > 1 )
189 		{
190 			String aStr( SdResId( STR_OBJECTS ) );
191 			aStr.Append( sal_Unicode(' ') );
192 			aStr.Append( String( SdResId( STR_UNDO_COPYOBJECTS ) ) );
193 
194 			pProgress = new SfxProgress( mpDocSh, aStr, nNumber );
195 			mpDocSh->SetWaitCursor( sal_True );
196 			bWaiting = sal_True;
197 		}
198 
199 		const SdrMarkList 	aMarkList( mpView->GetMarkedObjectList() );
200 		const sal_uLong			nMarkCount = aMarkList.GetMarkCount();
201 		SdrObject*		    pObj = NULL;
202 
203 		// Anzahl moeglicher Kopien berechnen
204 		aRect = mpView->GetAllMarkedRect();
205 
206 		if( lWidth < 0L )
207 		{
208 			long nTmp = ( aRect.Right() - aRect.Left() ) / -lWidth;
209 			nNumber = (sal_uInt16) Min( nTmp, (long)nNumber );
210 		}
211 
212 		if( lHeight < 0L )
213 		{
214 			long nTmp = ( aRect.Bottom() - aRect.Top() ) / -lHeight;
215 			nNumber = (sal_uInt16) Min( nTmp, (long)nNumber );
216 		}
217 
218 		for( sal_uInt16 i = 1; i <= nNumber; i++ )
219 		{
220 			if( pProgress )
221 				pProgress->SetState( i );
222 
223 			aRect = mpView->GetAllMarkedRect();
224 
225 			if( ( 1 == i ) && bColor )
226 			{
227 				SfxItemSet aNewSet( mpViewShell->GetPool(), XATTR_FILLSTYLE, XATTR_FILLCOLOR, 0L );
228 				aNewSet.Put( XFillStyleItem( XFILL_SOLID ) );
229 				aNewSet.Put( XFillColorItem( String(), aStartColor ) );
230 				mpView->SetAttributes( aNewSet );
231 			}
232 
233 			// make a copy of selected objects
234 			mpView->CopyMarked();
235 
236     		// get newly selected objects
237     		SdrMarkList aCopyMarkList( mpView->GetMarkedObjectList() );
238 	    	sal_uLong		j, nCopyMarkCount = aMarkList.GetMarkCount();
239 
240 			// set protection flags at marked copies to null
241 			for( j = 0; j < nCopyMarkCount; j++ )
242 			{
243 				pObj = aCopyMarkList.GetMark( j )->GetMarkedSdrObj();
244 
245 				if( pObj )
246 				{
247 					pObj->SetMoveProtect( sal_False );
248 					pObj->SetResizeProtect( sal_False );
249 				}
250 			}
251 
252 			Fraction aWidth( aRect.Right() - aRect.Left() + lWidth, aRect.Right() - aRect.Left() );
253 			Fraction aHeight( aRect.Bottom() - aRect.Top() + lHeight, aRect.Bottom() - aRect.Top() );
254 
255 			if( mpView->IsResizeAllowed() )
256 				mpView->ResizeAllMarked( aRect.TopLeft(), aWidth, aHeight );
257 
258 			if( mpView->IsRotateAllowed() )
259 				mpView->RotateAllMarked( aRect.Center(), lAngle * 100 );
260 
261 			if( mpView->IsMoveAllowed() )
262 				mpView->MoveAllMarked( Size( lSizeX, lSizeY ) );
263 
264 			// set protection flags at marked copies to original values
265 			if( nMarkCount == nCopyMarkCount )
266 			{
267 			    for( j = 0; j < nMarkCount; j++ )
268 			    {
269 			        SdrObject* pSrcObj = aMarkList.GetMark( j )->GetMarkedSdrObj();
270 			        SdrObject* pDstObj = aCopyMarkList.GetMark( j )->GetMarkedSdrObj();
271 
272 				    if( pSrcObj && pDstObj &&
273 				        ( pSrcObj->GetObjInventor() == pDstObj->GetObjInventor() ) &&
274 				        ( pSrcObj->GetObjIdentifier() == pDstObj->GetObjIdentifier() ) )
275 				    {
276 					    pDstObj->SetMoveProtect( pSrcObj->IsMoveProtect() );
277 					    pDstObj->SetResizeProtect( pSrcObj->IsResizeProtect() );
278 				    }
279 			    }
280 			}
281 
282 			if( bColor )
283 			{
284 				// Koennte man sicher noch optimieren, wuerde aber u.U.
285 				// zu Rundungsfehlern fuehren
286 				sal_uInt8 nRed = aStartColor.GetRed() + (sal_uInt8) ( ( (long) aEndColor.GetRed() - (long) aStartColor.GetRed() ) * (long) i / (long) nNumber  );
287 				sal_uInt8 nGreen = aStartColor.GetGreen() + (sal_uInt8) ( ( (long) aEndColor.GetGreen() - (long) aStartColor.GetGreen() ) *  (long) i / (long) nNumber );
288 				sal_uInt8 nBlue = aStartColor.GetBlue() + (sal_uInt8) ( ( (long) aEndColor.GetBlue() - (long) aStartColor.GetBlue() ) * (long) i / (long) nNumber );
289 				Color aNewColor( nRed, nGreen, nBlue );
290 				SfxItemSet aNewSet( mpViewShell->GetPool(), XATTR_FILLSTYLE, XATTR_FILLCOLOR, 0L );
291 				aNewSet.Put( XFillStyleItem( XFILL_SOLID ) );
292 				aNewSet.Put( XFillColorItem( String(), aNewColor ) );
293 				mpView->SetAttributes( aNewSet );
294 			}
295 		}
296 
297 		if ( pProgress )
298 			delete pProgress;
299 
300 		if ( bWaiting )
301 			mpDocSh->SetWaitCursor( sal_False );
302 
303 		// Handles zeigen
304 		mpView->AdjustMarkHdl(); //HMH sal_True );
305 		//HMHpView->ShowMarkHdl();
306 
307 		mpView->EndUndo();
308 	}
309 }
310 
311 } // end of namespace
312