xref: /trunk/main/sw/source/ui/dochdl/swdtflvr.cxx (revision 8e0fc07c)
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_sw.hxx"
26 #ifdef PRECOMPILED
27 #include "ui_pch.hxx"
28 #endif
29 
30 
31 #include <com/sun/star/embed/XVisualObject.hpp>
32 #include <com/sun/star/embed/XTransactedObject.hpp>
33 #include <com/sun/star/embed/Aspects.hpp>
34 #include <com/sun/star/embed/XEmbedObjectClipboardCreator.hpp>
35 #include <com/sun/star/embed/NoVisualAreaSizeException.hpp>
36 
37 #include <svtools/embedtransfer.hxx>
38 #include <svtools/insdlg.hxx>
39 #include <unotools/tempfile.hxx>
40 #include <comphelper/storagehelper.hxx>
41 #include <comphelper/processfactory.hxx>
42 #include <unotools/ucbstreamhelper.hxx>
43 #include <sot/filelist.hxx>
44 #include <svx/svxdlg.hxx>
45 #include <toolkit/helper/vclunohelper.hxx>
46 #include <osl/endian.h>
47 #include <sfx2/linkmgr.hxx>
48 #include <tools/urlobj.hxx>
49 #include <vcl/wrkwin.hxx>
50 #include <vcl/msgbox.hxx>
51 #include <sfx2/dispatch.hxx>
52 #include <svl/stritem.hxx>
53 #include <svtools/imap.hxx>
54 #include <sot/storage.hxx>
55 #include <vcl/graph.hxx>
56 #include <svl/urihelper.hxx>
57 #include <svx/svdmodel.hxx>
58 #include <svx/xexch.hxx>
59 #include <svx/xmlexchg.hxx>
60 #include <svx/dbaexchange.hxx>
61 #include <svx/clipfmtitem.hxx>
62 #include <sfx2/mieclip.hxx>
63 #include <svx/svdetc.hxx>
64 #include <svx/xoutbmp.hxx>
65 #include <svl/urlbmk.hxx>
66 #include <svtools/htmlout.hxx>
67 #include <svx/hlnkitem.hxx>
68 #include <svtools/inetimg.hxx>
69 #include <editeng/paperinf.hxx>
70 #include <svx/fmview.hxx>
71 #include <editeng/scripttypeitem.hxx>
72 #include <sfx2/docfilt.hxx>
73 #include <svtools/imapobj.hxx>
74 #include <sfx2/docfile.hxx>
75 #include <unotools/transliterationwrapper.hxx>
76 #include <unotools/streamwrap.hxx>
77 #include <svtools/filter.hxx>
78 
79 #include <svx/unomodel.hxx>
80 #include <fmturl.hxx>
81 #include <fmtinfmt.hxx>
82 #include <fmtfsize.hxx>
83 #include <swdtflvr.hxx>
84 #include <shellio.hxx>
85 #include <ddefld.hxx>
86 #include <doc.hxx>
87 #include <IDocumentUndoRedo.hxx>
88 #include <pagedesc.hxx>
89 #include <IMark.hxx>
90 #include <bookmrk.hxx>
91 #include <docary.hxx>
92 #include <section.hxx>
93 #include <ndtxt.hxx>
94 #include <edtwin.hxx>
95 #include <navicont.hxx>
96 #include <swcont.hxx>
97 #include <wrtsh.hxx>
98 #include <swmodule.hxx>
99 #include <view.hxx>
100 #include <docsh.hxx>
101 #include <wdocsh.hxx>
102 #include <fldbas.hxx>		//DDE
103 #include <swundo.hxx>		// fuer Undo-Ids
104 #include <pam.hxx>
105 #include <ndole.hxx>
106 #include <swwait.hxx>
107 #include <viewopt.hxx>
108 #include <swunodef.hxx>
109 #include <vcl/sound.hxx>
110 #include <swerror.h>
111 #include <SwCapObjType.hxx>
112 #include <cmdid.h>
113 #include <dochdl.hrc>
114 #include <comcore.hrc> // #111827#
115 #include <sot/stg.hxx>
116 #include <svx/svditer.hxx>
117 #include <editeng/eeitem.hxx>
118 #include <editeng/fhgtitem.hxx>
119 #include <svx/svdpage.hxx>
120 #include <avmedia/mediawindow.hxx>
121 #include <swcrsr.hxx>
122 #include <SwRewriter.hxx>
123 #include <globals.hrc>
124 #include <vos/mutex.hxx>
125 #include <vcl/svapp.hxx>
126 #include <swserv.hxx>
127 #include <switerator.hxx>
128 
129 extern sal_Bool bFrmDrag;
130 extern sal_Bool bDDINetAttr;
131 extern sal_Bool bExecuteDrag;
132 
133 
134 #define OLESIZE	11905 - 2 * lMinBorder, 6 * MM50
135 
136 #define SWTRANSFER_OBJECTTYPE_DRAWMODEL			0x00000001
137 #define SWTRANSFER_OBJECTTYPE_HTML              0x00000002
138 #define SWTRANSFER_OBJECTTYPE_RTF				0x00000004
139 #define SWTRANSFER_OBJECTTYPE_STRING			0x00000008
140 #define SWTRANSFER_OBJECTTYPE_SWOLE				0x00000010
141 #define SWTRANSFER_OBJECTTYPE_DDE				0x00000020
142 
143 #define SWTRANSFER_GRAPHIC_INSERTED             0x00000040
144 
145 using namespace ::svx;
146 using ::rtl::OUString;
147 using namespace ::com::sun::star;
148 using namespace ::com::sun::star::uno;
149 using namespace ::com::sun::star::datatransfer;
150 using namespace nsTransferBufferType;
151 
152 #define DDE_TXT_ENCODING 	gsl_getSystemTextEncoding()
153 
154 class SwTrnsfrDdeLink : public ::sfx2::SvBaseLink
155 {
156 	String sName;
157     ::sfx2::SvLinkSourceRef refObj;
158 	SwTransferable& rTrnsfr;
159 	SwDocShell* pDocShell;
160 	sal_uLong nOldTimeOut;
161 	sal_Bool bDelBookmrk : 1;
162 	sal_Bool bInDisconnect : 1;
163 
164 	sal_Bool FindDocShell();
165 
166     using sfx2::SvBaseLink::Disconnect;
167 
168 protected:
169 	virtual ~SwTrnsfrDdeLink();
170 
171 public:
172 	SwTrnsfrDdeLink( SwTransferable& rTrans, SwWrtShell& rSh );
173 
174 	virtual void DataChanged( const String& rMimeType,
175                               const uno::Any & rValue );
176 	virtual void Closed();
177 
178 	sal_Bool WriteData( SvStream& rStrm );
179 
180 	void Disconnect( sal_Bool bRemoveDataAdvise );
181 };
182 
183 // helper class for Action and Undo enclosing
184 class SwTrnsfrActionAndUndo
185 {
186 	SwWrtShell *pSh;
187     SwUndoId eUndoId;
188 public:
SwTrnsfrActionAndUndo(SwWrtShell * pS,SwUndoId nId,const SwRewriter * pRewriter=0,sal_Bool bDelSel=sal_False)189     SwTrnsfrActionAndUndo( SwWrtShell *pS, SwUndoId nId,
190                            const SwRewriter * pRewriter = 0,
191                            sal_Bool bDelSel = sal_False)
192         : pSh( pS ), eUndoId( nId )
193 	{
194         pSh->StartUndo( eUndoId, pRewriter );
195 		if( bDelSel )
196 			pSh->DelRight();
197 		pSh->StartAllAction();
198 	}
~SwTrnsfrActionAndUndo()199 	~SwTrnsfrActionAndUndo()
200 	{
201         pSh->EndUndo();
202 		pSh->EndAllAction();
203 	}
204 };
205 
206 
207 // -----------------------------------------------------------------------
208 
SwTransferable(SwWrtShell & rSh)209 SwTransferable::SwTransferable( SwWrtShell& rSh )
210 	: pWrtShell( &rSh ),
211 	pCreatorView( 0 ),
212 	pClpDocFac( 0 ),
213 	pClpGraphic( 0 ),
214 	pClpBitmap( 0 ),
215 	pOrigGrf( 0 ),
216 	pBkmk( 0 ),
217 	pImageMap( 0 ),
218 	pTargetURL( 0 ),
219 	eBufferType( TRNSFR_NONE )
220 {
221     rSh.GetView().AddTransferable(*this);
222     SwDocShell* pDShell = rSh.GetDoc()->GetDocShell();
223 	if( pDShell )
224 	{
225 		pDShell->FillTransferableObjectDescriptor( aObjDesc );
226 		if( pDShell->GetMedium() )
227 		{
228 			const INetURLObject& rURLObj = pDShell->GetMedium()->GetURLObject();
229 			aObjDesc.maDisplayName = URIHelper::removePassword(
230 								rURLObj.GetMainURL( INetURLObject::NO_DECODE ),
231 								INetURLObject::WAS_ENCODED,
232 			   					INetURLObject::DECODE_UNAMBIGUOUS );
233 		}
234 
235         PrepareOLE( aObjDesc );
236 	}
237 }
238 
239 // -----------------------------------------------------------------------
240 
~SwTransferable()241 SwTransferable::~SwTransferable()
242 {
243     Application::GetSolarMutex().acquire();
244 
245 	// der DDELink braucht noch die WrtShell!
246 	if( refDdeLink.Is() )
247 	{
248 		((SwTrnsfrDdeLink*)&refDdeLink)->Disconnect( sal_True );
249 		refDdeLink.Clear();
250 	}
251 
252 	pWrtShell = 0;
253 
254     // dvo 2002-05-30, #99239#: release reference to the document so that
255     // aDocShellRef will delete it (if aDocShellRef is set). Otherwise, the OLE
256     // nodes keep references to their sub-storage when the storage is already
257     // dead.
258 	delete pClpDocFac;
259 
260 	//JP 22.04.95: erst schliessen, dann kann die Ref. auch gecleared werden,
261 	//				so das die DocShell auch tatsaechlich geloescht wird!
262 	if( aDocShellRef.Is() )
263 	{
264         SfxObjectShell * pObj = aDocShellRef;
265 		SwDocShell* pDocSh = (SwDocShell*)pObj;
266 		pDocSh->DoClose();
267 	}
268 	aDocShellRef.Clear();
269 
270 	SwModule* pMod = SW_MOD();
271     if(pMod)
272     {
273         if ( pMod->pDragDrop == this )
274             pMod->pDragDrop = 0;
275         else if ( pMod->pXSelection == this )
276             pMod->pXSelection = 0;
277     }
278 
279 	delete pClpGraphic;
280 	delete pClpBitmap;
281 	delete pImageMap;
282 	delete pTargetURL;
283 	delete pBkmk;
284 
285 
286 	eBufferType = TRNSFR_NONE;
287 
288     Application::GetSolarMutex().release();
289 }
290 
291 // -----------------------------------------------------------------------
292 
lcl_GetDoc(SwDocFac & rDocFac)293 static SwDoc * lcl_GetDoc(SwDocFac & rDocFac)
294 {
295     SwDoc *const pDoc = rDocFac.GetDoc();
296     ASSERT( pDoc, "Document not found" );
297     if (pDoc)
298     {
299         pDoc->SetClipBoard( true );
300     }
301     return pDoc;
302 }
303 
304 // -----------------------------------------------------------------------
305 
ObjectReleased()306 void SwTransferable::ObjectReleased()
307 {
308 	SwModule *pMod = SW_MOD();
309 	if( this == pMod->pDragDrop )
310 		pMod->pDragDrop = 0;
311 	else if( this == pMod->pXSelection )
312 		pMod->pXSelection = 0;
313 }
314 
315 // -----------------------------------------------------------------------
316 
AddSupportedFormats()317 void SwTransferable::AddSupportedFormats()
318 {
319 	// only need if we are the current XSelection Object
320 	SwModule *pMod = SW_MOD();
321 	if( this == pMod->pXSelection )
322 	{
323 		SetDataForDragAndDrop( Point( 0,0) );
324 	}
325 }
326 
327 // -----------------------------------------------------------------------
328 
InitOle(SfxObjectShell * pDoc,SwDoc & rDoc)329 void SwTransferable::InitOle( SfxObjectShell* pDoc, SwDoc& rDoc )
330 {
331 	//OleVisArea einstellen. Linke obere Ecke der Seite und Groesse
332 	//der RealSize in Twips.
333 	const Size aSz( OLESIZE );
334 	SwRect aVis( Point( DOCUMENTBORDER, DOCUMENTBORDER ), aSz );
335     pDoc->SetVisArea( aVis.SVRect() );
336 	rDoc.set(IDocumentSettingAccess::BROWSE_MODE, true );
337 }
338 
339 // -----------------------------------------------------------------------
340 
FindOLEObj(sal_Int64 & nAspect) const341 uno::Reference < embed::XEmbeddedObject > SwTransferable::FindOLEObj( sal_Int64& nAspect ) const
342 {
343     uno::Reference < embed::XEmbeddedObject > xObj;
344 	if( pClpDocFac )
345 	{
346 		SwIterator<SwCntntNode,SwFmtColl> aIter( *pClpDocFac->GetDoc()->GetDfltGrfFmtColl() );
347 		for( SwCntntNode* pNd = aIter.First(); pNd; pNd = aIter.Next() )
348 			if( ND_OLENODE == pNd->GetNodeType() )
349 			{
350                 xObj = ((SwOLENode*)pNd)->GetOLEObj().GetOleRef();
351 				nAspect = ((SwOLENode*)pNd)->GetAspect();
352 				break;
353 			}
354 	}
355     return xObj;
356 }
357 
358 // -----------------------------------------------------------------------
359 
FindOLEReplacementGraphic() const360 Graphic* SwTransferable::FindOLEReplacementGraphic() const
361 {
362 	if( pClpDocFac )
363 	{
364 		SwIterator<SwCntntNode,SwFmtColl> aIter( *pClpDocFac->GetDoc()->GetDfltGrfFmtColl() );
365 		for( SwCntntNode* pNd = aIter.First(); pNd; pNd = aIter.Next() )
366 			if( ND_OLENODE == pNd->GetNodeType() )
367 			{
368                 return ((SwOLENode*)pNd)->GetGraphic();
369 			}
370 	}
371 
372     return NULL;
373 }
374 
375 
376 // -----------------------------------------------------------------------
377 
RemoveDDELinkFormat(const Window & rWin)378 void SwTransferable::RemoveDDELinkFormat( const Window& rWin )
379 {
380 	RemoveFormat( SOT_FORMATSTR_ID_LINK );
381 	CopyToClipboard( (Window*)&rWin );
382 }
383 
384 // -----------------------------------------------------------------------
385 
GetData(const DATA_FLAVOR & rFlavor)386 sal_Bool SwTransferable::GetData( const DATA_FLAVOR& rFlavor )
387 {
388 	sal_uInt32	nFormat = SotExchange::GetFormat( rFlavor );
389 
390     // we can only fullfil the request if
391     // 1) we have data for this format
392     // 2) we have either a clipboard document (pClpDocFac), or
393     //    we have a SwWrtShell (so we can generate a new clipboard document)
394     if( !HasFormat( nFormat ) || ( pClpDocFac == NULL && pWrtShell == NULL ) )
395 		return sal_False;
396 
397 	if( !pClpDocFac )
398 	{
399         SelectionType nSelectionType = pWrtShell->GetSelectionType();
400 
401         // when pending we will not get the correct type, but nsSelectionType::SEL_TXT
402         // as fallback. This *happens* durning D&D, so we need to check if we are in
403         // the fallback and just try to get a graphic
404         const bool bPending(pWrtShell->BasicActionPend());
405 
406         // SEL_GRF kommt vom ContentType der editsh
407 		if(bPending || ((nsSelectionType::SEL_GRF | nsSelectionType::SEL_DRW_FORM) & nSelectionType))
408 		{
409 			pClpGraphic = new Graphic;
410 			if( !pWrtShell->GetDrawObjGraphic( FORMAT_GDIMETAFILE, *pClpGraphic ))
411 				pOrigGrf = pClpGraphic;
412 			pClpBitmap = new Graphic;
413 			if( !pWrtShell->GetDrawObjGraphic( FORMAT_BITMAP, *pClpBitmap ))
414 				pOrigGrf = pClpBitmap;
415 
416 			// ist es ein URL-Button ?
417 			String sURL, sDesc;
418 			if( pWrtShell->GetURLFromButton( sURL, sDesc ) )
419 			{
420 				pBkmk = new INetBookmark( sURL, sDesc );
421 				eBufferType = TRNSFR_INETFLD;
422 			}
423 		}
424 
425 		pClpDocFac = new SwDocFac;
426         SwDoc *const pTmpDoc = lcl_GetDoc(*pClpDocFac);
427 
428 		pTmpDoc->LockExpFlds(); 	// nie die Felder updaten - Text so belassen
429 		pWrtShell->Copy( pTmpDoc );
430 
431 		// es wurde in der CORE eine neu angelegt (OLE-Objekte kopiert!)
432         aDocShellRef = pTmpDoc->GetTmpDocShell();
433 		if( aDocShellRef.Is() )
434 			SwTransferable::InitOle( aDocShellRef, *pTmpDoc );
435 		pTmpDoc->SetTmpDocShell( (SfxObjectShell*)NULL );
436 
437 		if( nSelectionType & nsSelectionType::SEL_TXT && !pWrtShell->HasMark() )
438 		{
439 			SwContentAtPos aCntntAtPos( SwContentAtPos::SW_INETATTR );
440 
441 			Point aPos( SwEditWin::GetDDStartPosX(), SwEditWin::GetDDStartPosY());
442 
443 			sal_Bool bSelect = bExecuteDrag &&
444 							pWrtShell->GetView().GetDocShell() &&
445 							!pWrtShell->GetView().GetDocShell()->IsReadOnly();
446 			if( pWrtShell->GetContentAtPos( aPos, aCntntAtPos, bSelect ) )
447 			{
448 				pBkmk = new INetBookmark(
449 						((SwFmtINetFmt*)aCntntAtPos.aFnd.pAttr)->GetValue(),
450 						aCntntAtPos.sStr );
451 				eBufferType = TRNSFR_INETFLD;
452 				if( bSelect )
453 					pWrtShell->SelectTxtAttr( RES_TXTATR_INETFMT );
454 			}
455 		}
456 		if( pWrtShell->IsFrmSelected() )
457 		{
458 		 	SfxItemSet aSet( pWrtShell->GetAttrPool(), RES_URL, RES_URL );
459 			pWrtShell->GetFlyFrmAttr( aSet );
460 			const SwFmtURL& rURL = (SwFmtURL&)aSet.Get( RES_URL );
461 			if( rURL.GetMap() )
462 				pImageMap = new ImageMap( *rURL.GetMap() );
463 			else if( rURL.GetURL().Len() )
464 				pTargetURL = new INetImage( aEmptyStr, rURL.GetURL(),
465 											rURL.GetTargetFrameName(),
466 											aEmptyStr, Size() );
467 		}
468 	}
469 
470 	sal_Bool	bOK = sal_False;
471 	if( TRNSFR_OLE == eBufferType )
472 	{
473         //TODO/MBA: testing - is this the "single OLE object" case?!
474 		// aus dem ClipDoc das OLE-Object besorgen und von dem die Daten
475 		// besorgen.
476 		sal_Int64 nAspect = embed::Aspects::MSOLE_CONTENT; // will be set in the next statement
477         uno::Reference < embed::XEmbeddedObject > xObj = FindOLEObj( nAspect );
478 		Graphic* pOLEGraph = FindOLEReplacementGraphic();
479         if( xObj.is() )
480 		{
481             TransferableDataHelper aD( new SvEmbedTransferHelper( xObj, pOLEGraph, nAspect ) );
482             uno::Any aAny( aD.GetAny( rFlavor ));
483 			if( aAny.hasValue() )
484 				bOK = SetAny( aAny, rFlavor );
485 		}
486 
487 		// the following solution will be used in the case when the object can not generate the image
488 		// TODO/LATER: in future the transferhelper must probably be created based on object and the replacement stream
489 		if ( nFormat == SOT_FORMAT_GDIMETAFILE )
490 		{
491 			pOLEGraph = FindOLEReplacementGraphic();
492 			if ( pOLEGraph )
493 				bOK = SetGDIMetaFile( pOLEGraph->GetGDIMetaFile(), rFlavor );
494 		}
495 	}
496 	else
497 	{
498 		switch( nFormat )
499 		{
500 		case SOT_FORMATSTR_ID_LINK:
501 			if( refDdeLink.Is() )
502 				bOK = SetObject( &refDdeLink,
503 									SWTRANSFER_OBJECTTYPE_DDE, rFlavor );
504 			break;
505 
506 		case SOT_FORMATSTR_ID_OBJECTDESCRIPTOR:
507 		case SOT_FORMATSTR_ID_LINKSRCDESCRIPTOR:
508 			bOK = SetTransferableObjectDescriptor( aObjDesc, rFlavor );
509 			break;
510 
511 		case SOT_FORMATSTR_ID_DRAWING:
512 			{
513                 SwDoc *const pDoc = lcl_GetDoc(*pClpDocFac);
514 				bOK = SetObject( pDoc->GetDrawModel(),
515 								SWTRANSFER_OBJECTTYPE_DRAWMODEL, rFlavor );
516 			}
517 			break;
518 
519 		case SOT_FORMAT_STRING:
520         {
521             SwDoc *const pDoc = lcl_GetDoc(*pClpDocFac);
522             bOK = SetObject( pDoc, SWTRANSFER_OBJECTTYPE_STRING, rFlavor );
523         }
524         break;
525 		case SOT_FORMAT_RTF:
526         {
527             SwDoc *const pDoc = lcl_GetDoc(*pClpDocFac);
528             bOK = SetObject( pDoc, SWTRANSFER_OBJECTTYPE_RTF, rFlavor );
529         }
530 			break;
531 
532 		case SOT_FORMATSTR_ID_HTML:
533         {
534             SwDoc *const pDoc = lcl_GetDoc(*pClpDocFac);
535             bOK = SetObject( pDoc, SWTRANSFER_OBJECTTYPE_HTML, rFlavor );
536         }
537 			break;
538 
539 		case SOT_FORMATSTR_ID_SVXB:
540 			if( eBufferType & TRNSFR_GRAPHIC && pOrigGrf )
541 				bOK = SetGraphic( *pOrigGrf, rFlavor );
542 			break;
543 
544 		case SOT_FORMAT_GDIMETAFILE:
545 			if( eBufferType & TRNSFR_GRAPHIC )
546 				bOK = SetGDIMetaFile( pClpGraphic->GetGDIMetaFile(), rFlavor );
547 			break;
548 		case SOT_FORMAT_BITMAP:
549         case SOT_FORMATSTR_ID_PNG:
550             // #126398#  Neither pClpBitmap nor pClpGraphic are necessarily set
551             if( (eBufferType & TRNSFR_GRAPHIC) && (pClpBitmap != 0 || pClpGraphic != 0))
552 				bOK = SetBitmapEx( (pClpBitmap ? pClpBitmap : pClpGraphic)->GetBitmapEx(), rFlavor );
553 			break;
554 
555 		case SOT_FORMATSTR_ID_SVIM:
556 			if( pImageMap )
557 				bOK = SetImageMap( *pImageMap, rFlavor );
558 			break;
559 
560 		case SOT_FORMATSTR_ID_INET_IMAGE:
561 			if( pTargetURL )
562 				bOK = SetINetImage( *pTargetURL, rFlavor );
563 			break;
564 
565 		case SOT_FORMATSTR_ID_SOLK:
566 		case SOT_FORMATSTR_ID_NETSCAPE_BOOKMARK:
567 		case SOT_FORMATSTR_ID_FILEGRPDESCRIPTOR:
568 		case SOT_FORMATSTR_ID_FILECONTENT:
569 		case SOT_FORMATSTR_ID_UNIFORMRESOURCELOCATOR:
570 		case SOT_FORMAT_FILE:
571 			if( (TRNSFR_INETFLD & eBufferType) && pBkmk )
572 				bOK = SetINetBookmark( *pBkmk, rFlavor );
573 			break;
574 
575 		case SOT_FORMATSTR_ID_EMBED_SOURCE:
576 //		default:
577 			if( !aDocShellRef.Is() )
578 			{
579                 SwDoc *const pDoc = lcl_GetDoc(*pClpDocFac);
580 				SwDocShell* pNewDocSh = new SwDocShell( pDoc,
581 										 SFX_CREATE_MODE_EMBEDDED );
582 				aDocShellRef = pNewDocSh;
583 				aDocShellRef->DoInitNew( NULL );
584 				SwTransferable::InitOle( aDocShellRef, *pDoc );
585 			}
586 			bOK = SetObject( &aDocShellRef, SWTRANSFER_OBJECTTYPE_SWOLE,
587 							rFlavor );
588 			break;
589 		}
590 	}
591 	return bOK;
592 }
593 
594 // -----------------------------------------------------------------------
595 
WriteObject(SotStorageStreamRef & xStream,void * pObject,sal_uInt32 nObjectType,const DATA_FLAVOR &)596 sal_Bool SwTransferable::WriteObject( SotStorageStreamRef& xStream,
597 									void* pObject, sal_uInt32 nObjectType,
598 									const DATA_FLAVOR& /*rFlavor*/ )
599 {
600 	sal_Bool bRet = sal_False;
601 	WriterRef xWrt;
602 
603 	switch( nObjectType )
604 	{
605 	case SWTRANSFER_OBJECTTYPE_DRAWMODEL:
606 		{
607 			//JP 28.02.2001: dont change the sequence of commands - Bug 8
608 			SdrModel *pModel = (SdrModel*)pObject;
609 			xStream->SetBufferSize( 16348 );
610 
611 			// #108584#
612 			// for the changed pool defaults from drawing layer pool set those
613 			// attributes as hard attributes to preserve them for saving
614 			const SfxItemPool& rItemPool = pModel->GetItemPool();
615 			const SvxFontHeightItem& rDefaultFontHeight = (const SvxFontHeightItem&)rItemPool.GetDefaultItem(EE_CHAR_FONTHEIGHT);
616 
617 			// SW should have no MasterPages
618 			DBG_ASSERT(0L == pModel->GetMasterPageCount(), "SW with MasterPages (!)");
619 
620 			for(sal_uInt16 a(0); a < pModel->GetPageCount(); a++)
621 			{
622 				const SdrPage* pPage = pModel->GetPage(a);
623 				SdrObjListIter aIter(*pPage, IM_DEEPNOGROUPS);
624 
625 				while(aIter.IsMore())
626 				{
627 					SdrObject* pObj = aIter.Next();
628 					const SvxFontHeightItem& rItem = (const SvxFontHeightItem&)pObj->GetMergedItem(EE_CHAR_FONTHEIGHT);
629 
630 					if(rItem.GetHeight() == rDefaultFontHeight.GetHeight())
631 					{
632 						pObj->SetMergedItem(rDefaultFontHeight);
633 					}
634 				}
635 			}
636 
637 			{
638                 uno::Reference<io::XOutputStream> xDocOut( new utl::OOutputStreamWrapper( *xStream ) );
639 				if( SvxDrawingLayerExport( pModel, xDocOut ) )
640 					xStream->Commit();
641 			}
642 
643 			bRet = ERRCODE_NONE == xStream->GetError();
644 		}
645 		break;
646 
647 	case SWTRANSFER_OBJECTTYPE_SWOLE:
648 		{
649             SfxObjectShell*   pEmbObj = (SfxObjectShell*) pObject;
650             try
651             {
652                 ::utl::TempFile     aTempFile;
653                 aTempFile.EnableKillingFile();
654                 uno::Reference< embed::XStorage > xWorkStore =
655                     ::comphelper::OStorageHelper::GetStorageFromURL( aTempFile.GetURL(), embed::ElementModes::READWRITE );
656 
657                 // write document storage
658                 pEmbObj->SetupStorage( xWorkStore, SOFFICE_FILEFORMAT_CURRENT, sal_False );
659                 // mba: no BaseURL for clipboard
660                 SfxMedium aMedium( xWorkStore, String() );
661                 bRet = pEmbObj->DoSaveObjectAs( aMedium, sal_False );
662                 pEmbObj->DoSaveCompleted();
663 
664                 uno::Reference< embed::XTransactedObject > xTransact( xWorkStore, uno::UNO_QUERY );
665                 if ( xTransact.is() )
666                     xTransact->commit();
667 
668                 SvStream* pSrcStm = ::utl::UcbStreamHelper::CreateStream( aTempFile.GetURL(), STREAM_READ );
669                 if( pSrcStm )
670                 {
671                     xStream->SetBufferSize( 0xff00 );
672                     *xStream << *pSrcStm;
673                     delete pSrcStm;
674                 }
675 
676                 bRet = sal_True;
677 
678                 xWorkStore->dispose();
679                 xWorkStore = uno::Reference < embed::XStorage >();
680                 xStream->Commit();
681             }
682             catch ( uno::Exception& )
683             {}
684 
685             bRet = ( xStream->GetError() == ERRCODE_NONE );
686 		}
687 		break;
688 
689 
690 	case SWTRANSFER_OBJECTTYPE_DDE:
691 		{
692 			xStream->SetBufferSize( 1024 );
693 			SwTrnsfrDdeLink* pDdeLnk = (SwTrnsfrDdeLink*)pObject;
694 			if( pDdeLnk->WriteData( *xStream ) )
695 			{
696 				xStream->Commit();
697 				bRet = ERRCODE_NONE == xStream->GetError();
698 			}
699 		}
700 		break;
701 
702 	case SWTRANSFER_OBJECTTYPE_HTML:
703         GetHTMLWriter( aEmptyStr, String(), xWrt );
704 		break;
705 
706 	case SWTRANSFER_OBJECTTYPE_RTF:
707         GetRTFWriter( aEmptyStr, String(), xWrt );
708 		break;
709 
710 	case SWTRANSFER_OBJECTTYPE_STRING:
711         GetASCWriter( aEmptyStr, String(), xWrt );
712 		if( xWrt.Is() )
713 		{
714 			SwAsciiOptions aAOpt;
715 			aAOpt.SetCharSet( RTL_TEXTENCODING_UTF8 );
716 			xWrt->SetAsciiOptions( aAOpt );
717 
718             // #102841# no start char for clipboard
719             xWrt->bUCS2_WithStartChar = sal_False;
720 		}
721 		break;
722 	}
723 
724 	if( xWrt.Is() )
725 	{
726 		SwDoc* pDoc = (SwDoc*)pObject;
727 		xWrt->bWriteClipboardDoc = sal_True;
728 		xWrt->bWriteOnlyFirstTable = 0 != (TRNSFR_TABELLE & eBufferType);
729 		xWrt->SetShowProgress( sal_False );
730 		SwWriter aWrt( *xStream, *pDoc );
731 		if( !IsError( aWrt.Write( xWrt )) )
732 		{
733 			*xStream << '\0'; 				// terminate with a zero
734 			xStream->Commit();
735 			bRet = sal_True;
736 		}
737 	}
738 
739 	return bRet;
740 }
741 
742 // -----------------------------------------------------------------------
743 
Cut()744 int SwTransferable::Cut()
745 {
746 	int nRet = Copy( sal_True );
747 	if( nRet )
748 		DeleteSelection();
749 	return nRet;
750 }
751 
752 // -----------------------------------------------------------------------
753 
DeleteSelection()754 void SwTransferable::DeleteSelection()
755 {
756     if(!pWrtShell)
757         return;
758     // Selektionsart vor Action-Klammerung erfragen
759 	const int nSelection = pWrtShell->GetSelectionType();
760 	pWrtShell->StartUndo( UNDO_DELETE );
761 	if( ( nsSelectionType::SEL_TXT | nsSelectionType::SEL_TBL ) & nSelection )
762 		pWrtShell->IntelligentCut( nSelection );
763 	pWrtShell->DelRight();
764 	pWrtShell->EndUndo( UNDO_DELETE );
765 }
766 
767 // -----------------------------------------------------------------------
768 
PrepareForCopy(sal_Bool bIsCut)769 int SwTransferable::PrepareForCopy( sal_Bool bIsCut )
770 {
771 	int nRet = 1;
772     if(!pWrtShell)
773         return 0;;
774 
775 	String sGrfNm;
776 	const int nSelection = pWrtShell->GetSelectionType();
777 	if( nSelection == nsSelectionType::SEL_GRF )
778 	{
779 		pClpGraphic = new Graphic;
780 		if( !pWrtShell->GetDrawObjGraphic( FORMAT_GDIMETAFILE, *pClpGraphic ))
781 			pOrigGrf = pClpGraphic;
782 		pClpBitmap = new Graphic;
783 		if( !pWrtShell->GetDrawObjGraphic( FORMAT_BITMAP, *pClpBitmap ))
784 			pOrigGrf = pClpBitmap;
785 
786 		pClpDocFac = new SwDocFac;
787         SwDoc *const pDoc = lcl_GetDoc(*pClpDocFac);
788         pWrtShell->Copy( pDoc );
789 
790         if (pOrigGrf && !pOrigGrf->GetBitmap().IsEmpty())
791 		  AddFormat( SOT_FORMATSTR_ID_SVXB );
792 
793         PrepareOLE( aObjDesc );
794 		AddFormat( SOT_FORMATSTR_ID_OBJECTDESCRIPTOR );
795 
796         // --> OD 2005-02-09 #119353# - robust
797         const Graphic* pGrf = pWrtShell->GetGraphic();
798         if( pGrf && pGrf->IsSupportedGraphic() )
799         // <--
800 		{
801 			AddFormat( FORMAT_GDIMETAFILE );
802             AddFormat( SOT_FORMATSTR_ID_PNG );
803 			AddFormat( FORMAT_BITMAP );
804 		}
805 		eBufferType = TRNSFR_GRAPHIC;
806 		pWrtShell->GetGrfNms( &sGrfNm, 0 );
807 	}
808 	else if ( nSelection == nsSelectionType::SEL_OLE )
809 	{
810         pClpDocFac = new SwDocFac;
811         SwDoc *const pDoc = lcl_GetDoc(*pClpDocFac);
812 		aDocShellRef = new SwDocShell( pDoc, SFX_CREATE_MODE_EMBEDDED);
813 		aDocShellRef->DoInitNew( NULL );
814 		pWrtShell->Copy( pDoc );
815 
816 		AddFormat( SOT_FORMATSTR_ID_EMBED_SOURCE );
817 
818         // --> OD #i98753#
819         // set size of embedded object at the object description structure
820         aObjDesc.maSize = OutputDevice::LogicToLogic( pWrtShell->GetObjSize(), MAP_TWIP, MAP_100TH_MM );
821         // <--
822         PrepareOLE( aObjDesc );
823 		AddFormat( SOT_FORMATSTR_ID_OBJECTDESCRIPTOR );
824 
825         AddFormat( FORMAT_GDIMETAFILE );
826 		eBufferType = TRNSFR_OLE;
827 	}
828 	//Gibt es ueberhaupt etwas zum bereitstellen?
829 	else if ( pWrtShell->IsSelection() || pWrtShell->IsFrmSelected() ||
830 			  pWrtShell->IsObjSelected() )
831 	{
832 		SwWait *pWait = 0;
833 		if( pWrtShell->ShouldWait() )
834 			pWait = new SwWait( *pWrtShell->GetView().GetDocShell(), true );
835 
836 		pClpDocFac = new SwDocFac;
837 
838 		// zusaetzlichen Cursor erzeugen, damit eine Gleichbehandlung
839 		// von Tastatur- und Mausselektion moeglich ist.
840 		// Im AddMode wird bei Tastaturselektion der neue Cursor erst
841 		// beim Bewegen des Cursors nach Selektionsende erzeugt.
842 		if( pWrtShell->IsAddMode() && pWrtShell->SwCrsrShell::HasSelection() )
843 			pWrtShell->CreateCrsr();
844 
845         SwDoc *const pTmpDoc = lcl_GetDoc(*pClpDocFac);
846 
847 		pTmpDoc->LockExpFlds(); 	// nie die Felder updaten - Text so belassen
848 		pWrtShell->Copy( pTmpDoc );
849 
850         {
851             IDocumentMarkAccess* const pMarkAccess = pTmpDoc->getIDocumentMarkAccess();
852             ::std::vector< ::sw::mark::IMark* > vDdeMarks;
853             // find all DDE-Bookmarks
854             for(IDocumentMarkAccess::const_iterator_t ppMark = pMarkAccess->getAllMarksBegin();
855                 ppMark != pMarkAccess->getAllMarksEnd();
856                 ppMark++)
857             {
858                 if(IDocumentMarkAccess::DDE_BOOKMARK == IDocumentMarkAccess::GetType(**ppMark))
859                     vDdeMarks.push_back(ppMark->get());
860             }
861             // remove all DDE-Bookmarks, they are invalid inside the clipdoc!
862             for(::std::vector< ::sw::mark::IMark* >::iterator ppMark = vDdeMarks.begin();
863                 ppMark != vDdeMarks.end();
864                 ppMark++)
865                 pMarkAccess->deleteMark(*ppMark);
866         }
867 
868 		// es wurde in der CORE eine neu angelegt (OLE-Objekte kopiert!)
869         aDocShellRef = pTmpDoc->GetTmpDocShell();
870 		if( aDocShellRef.Is() )
871 			SwTransferable::InitOle( aDocShellRef, *pTmpDoc );
872 		pTmpDoc->SetTmpDocShell( (SfxObjectShell*)NULL );
873 
874 		if( pWrtShell->IsObjSelected() )
875 			eBufferType = TRNSFR_DRAWING;
876 		else
877 		{
878 			eBufferType = TRNSFR_DOCUMENT;
879 			if (pWrtShell->IntelligentCut(nSelection, sal_False) != SwWrtShell::NO_WORD)
880 				eBufferType = (TransferBufferType)(TRNSFR_DOCUMENT_WORD | eBufferType);
881 		}
882 
883 		int bDDELink = pWrtShell->IsSelection();
884 		if( nSelection & nsSelectionType::SEL_TBL_CELLS )
885 		{
886 			eBufferType = (TransferBufferType)(TRNSFR_TABELLE | eBufferType);
887 			bDDELink = pWrtShell->HasWholeTabSelection();
888 		}
889 
890 		//Wenn's einer braucht OLE'n wir ihm was.
891 		AddFormat( SOT_FORMATSTR_ID_EMBED_SOURCE );
892 
893 		//RTF vor das Metafile von OLE stellen, weil mit weniger verlusten
894 		//behaftet.
895 		if( !pWrtShell->IsObjSelected() )
896 		{
897 			AddFormat( FORMAT_RTF );
898 			AddFormat( SOT_FORMATSTR_ID_HTML );
899 		}
900 		if( pWrtShell->IsSelection() )
901 			AddFormat( FORMAT_STRING );
902 
903 		if( nSelection & ( nsSelectionType::SEL_DRW | nsSelectionType::SEL_DRW_FORM ))
904 		{
905 			AddFormat( SOT_FORMATSTR_ID_DRAWING );
906 			if ( nSelection & nsSelectionType::SEL_DRW )
907 			{
908 				AddFormat( FORMAT_GDIMETAFILE );
909                 AddFormat( SOT_FORMATSTR_ID_PNG );
910 				AddFormat( FORMAT_BITMAP );
911 			}
912 			eBufferType = (TransferBufferType)( TRNSFR_GRAPHIC | eBufferType );
913 
914 			pClpGraphic = new Graphic;
915 			if( !pWrtShell->GetDrawObjGraphic( FORMAT_GDIMETAFILE, *pClpGraphic ))
916 				pOrigGrf = pClpGraphic;
917 			pClpBitmap = new Graphic;
918 			if( !pWrtShell->GetDrawObjGraphic( FORMAT_BITMAP, *pClpBitmap ))
919 				pOrigGrf = pClpBitmap;
920 
921 			// ist es ein URL-Button ?
922 			String sURL, sDesc;
923 			if( pWrtShell->GetURLFromButton( sURL, sDesc ) )
924 			{
925 				AddFormat( FORMAT_STRING );
926  				AddFormat( SOT_FORMATSTR_ID_SOLK );
927  				AddFormat( SOT_FORMATSTR_ID_NETSCAPE_BOOKMARK );
928  				AddFormat( SOT_FORMATSTR_ID_FILECONTENT );
929  				AddFormat( SOT_FORMATSTR_ID_FILEGRPDESCRIPTOR );
930  				AddFormat( SOT_FORMATSTR_ID_UNIFORMRESOURCELOCATOR );
931 				eBufferType = (TransferBufferType)( TRNSFR_INETFLD | eBufferType );
932 				nRet = sal_True;
933 			}
934 		}
935 
936 		// beim Cut hat DDE-Link keinen Sinn!!
937 		SwDocShell* pDShell;
938 		if( !bIsCut && bDDELink &&
939 			0 != ( pDShell = pWrtShell->GetDoc()->GetDocShell()) &&
940 			SFX_CREATE_MODE_STANDARD == pDShell->GetCreateMode() )
941 		{
942 			AddFormat( SOT_FORMATSTR_ID_LINK );
943 			refDdeLink = new SwTrnsfrDdeLink( *this, *pWrtShell );
944 		}
945 
946 		//ObjectDescriptor wurde bereits aus der alten DocShell gefuellt.
947 		//Jetzt noch anpassen. Dadurch kann im GetData die erste Anfrage
948 		//auch noch mit delayed rendering beantwortet werden.
949 		aObjDesc.mbCanLink = sal_False;
950 		Size aSz( OLESIZE );
951 		aObjDesc.maSize = OutputDevice::LogicToLogic( aSz, MAP_TWIP, MAP_100TH_MM );
952 
953         PrepareOLE( aObjDesc );
954         AddFormat( SOT_FORMATSTR_ID_OBJECTDESCRIPTOR );
955 
956 		delete pWait;
957 	}
958 	else
959 		nRet = 0;
960 
961 	if( pWrtShell->IsFrmSelected() )
962 	{
963 		SfxItemSet aSet( pWrtShell->GetAttrPool(), RES_URL, RES_URL );
964 		pWrtShell->GetFlyFrmAttr( aSet );
965 		const SwFmtURL& rURL = (SwFmtURL&)aSet.Get( RES_URL );
966 		if( rURL.GetMap() )
967 		{
968 			pImageMap = new ImageMap( *rURL.GetMap() );
969 			AddFormat( SOT_FORMATSTR_ID_SVIM );
970 		}
971 		else if( rURL.GetURL().Len() )
972 		{
973 			pTargetURL = new INetImage( sGrfNm, rURL.GetURL(),
974 										rURL.GetTargetFrameName(),
975 										aEmptyStr, Size() );
976 			AddFormat( SOT_FORMATSTR_ID_INET_IMAGE );
977 		}
978 	}
979 
980 	return nRet;
981 }
982 
Copy(sal_Bool bIsCut)983 int SwTransferable::Copy( sal_Bool bIsCut )
984 {
985     int nRet = PrepareForCopy( bIsCut );
986     if ( nRet )
987     {
988         CopyToClipboard( &pWrtShell->GetView().GetEditWin() );
989     }
990 	return nRet;
991 }
992 
993 // -----------------------------------------------------------------------
994 
CalculateAndCopy()995 int SwTransferable::CalculateAndCopy()
996 {
997     if(!pWrtShell)
998         return 0;
999     SwWait aWait( *pWrtShell->GetView().GetDocShell(), true );
1000 
1001 	String aStr( pWrtShell->Calculate() );
1002 
1003 	pClpDocFac = new SwDocFac;
1004     SwDoc *const pDoc = lcl_GetDoc(*pClpDocFac);
1005     pWrtShell->Copy(pDoc, & aStr);
1006 	eBufferType = TRNSFR_DOCUMENT;
1007 	AddFormat( FORMAT_STRING );
1008 
1009 	CopyToClipboard( &pWrtShell->GetView().GetEditWin() );
1010 
1011 	return 1;
1012 }
1013 
1014 // -----------------------------------------------------------------------
1015 
CopyGlossary(SwTextBlocks & rGlossary,const String & rStr)1016 int SwTransferable::CopyGlossary( SwTextBlocks& rGlossary,
1017 									const String& rStr )
1018 {
1019     if(!pWrtShell)
1020         return 0;
1021     SwWait aWait( *pWrtShell->GetView().GetDocShell(), true );
1022 
1023 	pClpDocFac = new SwDocFac;
1024     SwDoc *const pCDoc = lcl_GetDoc(*pClpDocFac);
1025 
1026 	SwNodes& rNds = pCDoc->GetNodes();
1027 	SwNodeIndex aNodeIdx( *rNds.GetEndOfContent().StartOfSectionNode() );
1028 	SwCntntNode* pCNd = rNds.GoNext( &aNodeIdx ); // gehe zum 1. ContentNode
1029 	SwPaM aPam( *pCNd );
1030 
1031 	pCDoc->LockExpFlds(); 	// nie die Felder updaten - Text so belassen
1032 
1033 	pCDoc->InsertGlossary( rGlossary, rStr, aPam, 0 );
1034 
1035 	// es wurde in der CORE eine neu angelegt (OLE-Objekte kopiert!)
1036     aDocShellRef = pCDoc->GetTmpDocShell();
1037 	if( aDocShellRef.Is() )
1038 		SwTransferable::InitOle( aDocShellRef, *pCDoc );
1039     pCDoc->SetTmpDocShell( (SfxObjectShell*)NULL );
1040 
1041 	eBufferType = TRNSFR_DOCUMENT;
1042 
1043 	//Wenn's einer braucht OLE'n wir ihm was.
1044 	AddFormat( SOT_FORMATSTR_ID_EMBED_SOURCE );
1045     AddFormat( FORMAT_RTF );
1046 	AddFormat( SOT_FORMATSTR_ID_HTML );
1047 	AddFormat( FORMAT_STRING );
1048 
1049 	//ObjectDescriptor wurde bereits aus der alten DocShell gefuellt.
1050 	//Jetzt noch anpassen. Dadurch kann im GetData die erste Anfrage
1051 	//auch noch mit delayed rendering beantwortet werden.
1052 	aObjDesc.mbCanLink = sal_False;
1053 	Size aSz( OLESIZE );
1054 	aObjDesc.maSize = OutputDevice::LogicToLogic( aSz, MAP_TWIP, MAP_100TH_MM );
1055 
1056     PrepareOLE( aObjDesc );
1057     AddFormat( SOT_FORMATSTR_ID_OBJECTDESCRIPTOR );
1058 
1059 	CopyToClipboard( &pWrtShell->GetView().GetEditWin() );
1060 
1061 	return 1;
1062 }
1063 
lcl_getTransferPointer(uno::Reference<XTransferable> & xRef)1064 static inline uno::Reference < XTransferable > * lcl_getTransferPointer ( uno::Reference < XTransferable > &xRef )
1065 {
1066 	return &xRef;
1067 }
1068 // -----------------------------------------------------------------------
1069 
IsPaste(const SwWrtShell & rSh,const TransferableDataHelper & rData)1070 sal_Bool SwTransferable::IsPaste( const SwWrtShell& rSh,
1071 							  const TransferableDataHelper& rData )
1072 {
1073     // Check the common case first: We can always paste our own data!
1074     // #106503#: If _only_ the internal format can be pasted, this check will
1075     // yield 'true', while the one below would give a (wrong) result 'false'.
1076 
1077     bool bIsPaste = ( GetSwTransferable( rData ) != NULL );
1078 
1079     // if it's not our own data, we need to have a closer look:
1080     if( ! bIsPaste )
1081     {
1082         // determine the proper paste action, and return true if we find one
1083         uno::Reference<XTransferable> xTransferable( rData.GetXTransferable() );
1084 
1085         sal_uInt16 nDestination = SwTransferable::GetSotDestination( rSh );
1086         sal_uInt16 nSourceOptions =
1087 					(( EXCHG_DEST_DOC_TEXTFRAME == nDestination ||
1088 					   EXCHG_DEST_SWDOC_FREE_AREA == nDestination ||
1089 					   EXCHG_DEST_DOC_TEXTFRAME_WEB == nDestination ||
1090 					   EXCHG_DEST_SWDOC_FREE_AREA_WEB == nDestination )
1091 									? EXCHG_IN_ACTION_COPY
1092                      : EXCHG_IN_ACTION_MOVE);
1093 
1094         sal_uLong nFormat;          // output param for GetExchangeAction
1095         sal_uInt16 nEventAction;    // output param for GetExchangeAction
1096         sal_uInt16 nAction = SotExchange::GetExchangeAction(
1097 								rData.GetDataFlavorExVector(),
1098 								nDestination,
1099 								nSourceOptions,  			/* ?? */
1100 								EXCHG_IN_ACTION_DEFAULT,    /* ?? */
1101 								nFormat, nEventAction, 0,
1102 								lcl_getTransferPointer ( xTransferable ) );
1103 
1104         // if we find a suitable action, we can paste!
1105         bIsPaste = (EXCHG_INOUT_ACTION_NONE != nAction);
1106     }
1107 
1108 	return bIsPaste;
1109 }
1110 
1111 // -----------------------------------------------------------------------
1112 
Paste(SwWrtShell & rSh,TransferableDataHelper & rData)1113 int SwTransferable::Paste( SwWrtShell& rSh, TransferableDataHelper& rData )
1114 {
1115     sal_uInt16 nEventAction, nAction=0,
1116 		   nDestination = SwTransferable::GetSotDestination( rSh );
1117     sal_uLong nFormat = 0;
1118 
1119 	if( GetSwTransferable( rData ) )
1120 	{
1121 		nAction = EXCHG_OUT_ACTION_INSERT_PRIVATE;
1122 	}
1123 	else
1124 	{
1125         sal_uInt16 nSourceOptions =
1126                     (( EXCHG_DEST_DOC_TEXTFRAME == nDestination ||
1127                     EXCHG_DEST_SWDOC_FREE_AREA == nDestination ||
1128                     EXCHG_DEST_DOC_TEXTFRAME_WEB == nDestination ||
1129                     EXCHG_DEST_SWDOC_FREE_AREA_WEB == nDestination )
1130                                     ? EXCHG_IN_ACTION_COPY
1131                                     : EXCHG_IN_ACTION_MOVE);
1132         uno::Reference<XTransferable> xTransferable( rData.GetXTransferable() );
1133         nAction = SotExchange::GetExchangeAction(
1134                                     rData.GetDataFlavorExVector(),
1135                                     nDestination,
1136                                     nSourceOptions,             /* ?? */
1137                                     EXCHG_IN_ACTION_DEFAULT,    /* ?? */
1138                                     nFormat, nEventAction, 0,
1139                                     lcl_getTransferPointer ( xTransferable ) );
1140 	}
1141 
1142 	// special case for tables from draw application
1143 	if( EXCHG_OUT_ACTION_INSERT_DRAWOBJ == (nAction & EXCHG_ACTION_MASK) )
1144 	{
1145 		if( rData.HasFormat( SOT_FORMAT_RTF ) )
1146 		{
1147 			nAction = EXCHG_OUT_ACTION_INSERT_STRING | (nAction & !EXCHG_ACTION_MASK);
1148 			nFormat = SOT_FORMAT_RTF;
1149 		}
1150 	}
1151 
1152 	return EXCHG_INOUT_ACTION_NONE != nAction &&
1153 			SwTransferable::PasteData( rData, rSh, nAction, nFormat,
1154                                         nDestination, sal_False, sal_False );
1155 }
1156 
1157 // -----------------------------------------------------------------------
1158 
PasteData(TransferableDataHelper & rData,SwWrtShell & rSh,sal_uInt16 nAction,sal_uLong nFormat,sal_uInt16 nDestination,sal_Bool bIsPasteFmt,sal_Bool bIsDefault,const Point * pPt,sal_Int8 nDropAction,sal_Bool bPasteSelection)1159 int SwTransferable::PasteData( TransferableDataHelper& rData,
1160 							SwWrtShell& rSh, sal_uInt16 nAction, sal_uLong nFormat,
1161 							sal_uInt16 nDestination, sal_Bool bIsPasteFmt,
1162 							sal_Bool bIsDefault,
1163 							const Point* pPt, sal_Int8 nDropAction,
1164 							sal_Bool bPasteSelection )
1165 {
1166 	SwWait aWait( *rSh.GetView().GetDocShell(), false );
1167 	SwTrnsfrActionAndUndo* pAction = 0;
1168 	SwModule* pMod = SW_MOD();
1169 
1170 	int nRet = 0;
1171     bool bCallAutoCaption = false;
1172 
1173 	if( pPt )
1174 	{
1175 		// external Drop
1176 		if( bPasteSelection ? !pMod->pXSelection : !pMod->pDragDrop )
1177 		{
1178 			switch( nDestination )
1179 			{
1180 			case EXCHG_DEST_DOC_LNKD_GRAPH_W_IMAP:
1181 			case EXCHG_DEST_DOC_LNKD_GRAPHOBJ:
1182 			case EXCHG_DEST_DOC_GRAPH_W_IMAP:
1183 			case EXCHG_DEST_DOC_GRAPHOBJ:
1184 			case EXCHG_DEST_DOC_OLEOBJ:
1185 			case EXCHG_DEST_DOC_DRAWOBJ:
1186 			case EXCHG_DEST_DOC_URLBUTTON:
1187 			case EXCHG_DEST_DOC_GROUPOBJ:
1188 				// Rahmen/Objecte selektieren
1189 				SwTransferable::SetSelInShell( rSh, sal_True, pPt );
1190 				break;
1191 
1192 			// case EXCHG_DEST_DOC_TEXTFRAME:
1193 			// case EXCHG_DEST_SWDOC_FREE_AREA:
1194 			// case EXCHG_DEST_DOC_URLFIELD:
1195 			default:
1196 				SwTransferable::SetSelInShell( rSh, sal_False, pPt );
1197 				break;
1198 			}
1199 		}
1200 	}
1201 	else if( ( !GetSwTransferable( rData ) || bIsPasteFmt ) &&
1202 			!rSh.IsTableMode() && rSh.HasSelection() )
1203 	{
1204 		// dann die Selektionen loeschen
1205 
1206 		//Selektierten Inhalt loeschen,
1207 		// - nicht bei Tabellen-Selektion
1208 		// - nicht bei ReRead einer Grafik/DDEDaten
1209 		// - nicht bei D&D, fuer die richtige Selektion wurde im
1210 		//		Drop-Handler gesorgt
1211 		sal_Bool bDelSel = sal_False;
1212 		switch( nDestination )
1213 		{
1214 		case EXCHG_DEST_DOC_TEXTFRAME:
1215 		case EXCHG_DEST_SWDOC_FREE_AREA:
1216 		case EXCHG_DEST_DOC_TEXTFRAME_WEB:
1217 		case EXCHG_DEST_SWDOC_FREE_AREA_WEB:
1218 			bDelSel = sal_True;
1219 			break;
1220 		}
1221 
1222 		if( bDelSel )
1223             // --> FME 2004-10-19 #i34830#
1224 			pAction = new SwTrnsfrActionAndUndo( &rSh, UNDO_PASTE_CLIPBOARD, NULL,
1225                                                  sal_True );
1226             // <--
1227 	}
1228 
1229     SwTransferable *pTrans=0, *pTunneledTrans=GetSwTransferable( rData );
1230 //    uno::Reference<XUnoTunnel> xTunnel( rData.GetTransferable(), UNO_QUERY );
1231 //    if ( xTunnel.is() )
1232 //    {
1233 //        sal_Int64 nHandle = xTunnel->getSomething( getUnoTunnelId() );
1234 //        if ( nHandle )
1235 //            pTunneledTrans = (SwTransferable*) (sal_IntPtr) nHandle;
1236 //    }
1237 
1238     // check for private drop
1239     bool bPrivateDrop(pPt && (bPasteSelection ? 0 != (pTrans = pMod->pXSelection) : 0 != (pTrans = pMod->pDragDrop)));
1240     bool bNeedToSelectBeforePaste(false);
1241 
1242     if(bPrivateDrop && DND_ACTION_LINK == nDropAction)
1243     {
1244         // internal drop on object, suppress bPrivateDrop to change internal fill
1245         bPrivateDrop = false;
1246         bNeedToSelectBeforePaste = true;
1247     }
1248 
1249     if(bPrivateDrop && pPt && DND_ACTION_MOVE == nDropAction)
1250     {
1251         // check if dragged over a useful target. If yes, use as content exchange
1252         // drop as if from external
1253         const SwFrmFmt* pSwFrmFmt = rSh.GetFmtFromObj(*pPt);
1254 
1255         if(pSwFrmFmt && 0 != dynamic_cast< const SwDrawFrmFmt* >(pSwFrmFmt))
1256         {
1257             bPrivateDrop = false;
1258             bNeedToSelectBeforePaste = true;
1259         }
1260     }
1261 
1262     if(bPrivateDrop)
1263 	{
1264 		// then internal Drag & Drop or XSelection
1265 		nRet = pTrans->PrivateDrop( rSh, *pPt, DND_ACTION_MOVE == nDropAction,
1266 									bPasteSelection );
1267 	}
1268     else if( !pPt && pTunneledTrans &&
1269 			EXCHG_OUT_ACTION_INSERT_PRIVATE == nAction )
1270 	{
1271 		// then internal paste
1272         nRet = pTunneledTrans->PrivatePaste( rSh );
1273 	}
1274 	else if( EXCHG_INOUT_ACTION_NONE != nAction )
1275 	{
1276 		if( !pAction )
1277         {
1278             // #111827#
1279 			pAction = new SwTrnsfrActionAndUndo( &rSh, UNDO_PASTE_CLIPBOARD);
1280         }
1281 
1282 		// im Drag&Drop duerfen keine MessageBoxen angezeigt werden
1283 		sal_Bool bMsg = 0 == pPt;
1284         sal_uInt8 nActionFlags = static_cast< sal_uInt8 >(( nAction >> 8 ) & 0xFF);
1285 
1286 		sal_uInt16 nClearedAction = ( nAction & EXCHG_ACTION_MASK );
1287 		// Selektionen loeschen
1288 
1289 		switch( nClearedAction )
1290 		{
1291 		case EXCHG_OUT_ACTION_INSERT_PRIVATE:
1292 ASSERT( pPt, "EXCHG_OUT_ACTION_INSERT_PRIVATE: was soll hier passieren?" );
1293 			break;
1294 
1295 		case EXCHG_OUT_ACTION_MOVE_PRIVATE:
1296 ASSERT( pPt, "EXCHG_OUT_ACTION_MOVE_PRIVATE: was soll hier passieren?" );
1297 			break;
1298 
1299 
1300 		case EXCHG_IN_ACTION_MOVE:
1301 		case EXCHG_IN_ACTION_COPY:
1302 		case EXCHG_IN_ACTION_LINK:
1303 		case EXCHG_OUT_ACTION_INSERT_HTML:
1304 		case EXCHG_OUT_ACTION_INSERT_STRING:
1305 		case EXCHG_OUT_ACTION_INSERT_IMAGEMAP:
1306 		case EXCHG_OUT_ACTION_REPLACE_IMAGEMAP:
1307 
1308 			// dann muss ueber das Format gegangen werden
1309 			switch( nFormat )
1310 			{
1311 			case SOT_FORMATSTR_ID_DRAWING:
1312 				nRet = SwTransferable::_PasteSdrFormat( rData, rSh,
1313 												SW_PASTESDR_INSERT, pPt,
1314 												nActionFlags, bNeedToSelectBeforePaste);
1315 				break;
1316 
1317 			case SOT_FORMATSTR_ID_HTML:
1318 			case SOT_FORMATSTR_ID_HTML_SIMPLE:
1319 			case SOT_FORMATSTR_ID_HTML_NO_COMMENT:
1320 			case SOT_FORMAT_RTF:
1321 			case SOT_FORMAT_STRING:
1322 				nRet = SwTransferable::_PasteFileContent( rData, rSh,
1323 															nFormat, bMsg );
1324 				break;
1325 
1326 			case SOT_FORMATSTR_ID_NETSCAPE_BOOKMARK:
1327 				{
1328 					INetBookmark aBkmk;
1329 					if( rData.GetINetBookmark( nFormat, aBkmk ) )
1330 					{
1331 						SwFmtINetFmt aFmt( aBkmk.GetURL(), aEmptyStr );
1332 						rSh.InsertURL( aFmt, aBkmk.GetDescription() );
1333 						nRet = 1;
1334 					}
1335 				}
1336 				break;
1337 
1338 			case SOT_FORMATSTR_ID_SD_OLE:
1339 				nRet = SwTransferable::_PasteOLE( rData, rSh, nFormat,
1340 													nActionFlags, bMsg );
1341 				break;
1342 
1343 			case SOT_FORMATSTR_ID_SVIM:
1344 				nRet = SwTransferable::_PasteImageMap( rData, rSh );
1345 				break;
1346 
1347 			case SOT_FORMATSTR_ID_SVXB:
1348 			case SOT_FORMAT_BITMAP:
1349             case SOT_FORMATSTR_ID_PNG:
1350 			case SOT_FORMAT_GDIMETAFILE:
1351 				nRet = SwTransferable::_PasteGrf( rData, rSh, nFormat,
1352 												SW_PASTESDR_INSERT,pPt,
1353 												nActionFlags, nDropAction, bNeedToSelectBeforePaste);
1354 				break;
1355 
1356 			case SOT_FORMATSTR_ID_XFORMS:
1357 			case SOT_FORMATSTR_ID_SBA_FIELDDATAEXCHANGE:
1358 			case SOT_FORMATSTR_ID_SBA_DATAEXCHANGE:
1359 			case SOT_FORMATSTR_ID_SBA_CTRLDATAEXCHANGE:
1360 				nRet = SwTransferable::_PasteDBData( rData, rSh, nFormat,
1361 											EXCHG_IN_ACTION_LINK == nClearedAction,
1362 											pPt, bMsg );
1363 				break;
1364 
1365 			case SOT_FORMAT_FILE:
1366 				nRet = SwTransferable::_PasteFileName( rData, rSh, nFormat,
1367 								( EXCHG_IN_ACTION_MOVE == nClearedAction
1368 									? SW_PASTESDR_REPLACE
1369 									: EXCHG_IN_ACTION_LINK == nClearedAction
1370 										? SW_PASTESDR_SETATTR
1371 										: SW_PASTESDR_INSERT),
1372 								pPt, nActionFlags, bMsg );
1373 				break;
1374 
1375 			case SOT_FORMAT_FILE_LIST:
1376 				// dann nur als Grafiken einfuegen
1377 				nRet = SwTransferable::_PasteFileList( rData, rSh,
1378 									EXCHG_IN_ACTION_LINK == nClearedAction,
1379 									pPt, bMsg );
1380 				break;
1381 
1382 			case SOT_FORMATSTR_ID_SONLK:
1383 				if( pPt )
1384 				{
1385 					NaviContentBookmark aBkmk;
1386 					if( aBkmk.Paste( rData ) )
1387 					{
1388                         if(bIsDefault)
1389                         {
1390                             switch(aBkmk.GetDefaultDragType())
1391                             {
1392                                 case REGION_MODE_NONE: nClearedAction = EXCHG_IN_ACTION_COPY; break;
1393                                 case REGION_MODE_EMBEDDED: nClearedAction = EXCHG_IN_ACTION_MOVE; break;
1394                                 case REGION_MODE_LINK: nClearedAction = EXCHG_IN_ACTION_LINK; break;
1395                             }
1396                         }
1397                         rSh.NavigatorPaste( aBkmk, nClearedAction );
1398 						nRet = 1;
1399 					}
1400 				}
1401 				break;
1402 
1403 			case SOT_FORMATSTR_ID_INET_IMAGE:
1404 			case SOT_FORMATSTR_ID_NETSCAPE_IMAGE:
1405 				nRet = SwTransferable::_PasteTargetURL( rData, rSh,
1406 														SW_PASTESDR_INSERT,
1407 														pPt, sal_True );
1408 				break;
1409 
1410 			default:
1411 				ASSERT( pPt, "unbekanntes Format" );
1412 			}
1413 			break;
1414 
1415 		case EXCHG_OUT_ACTION_INSERT_FILE:
1416 			nRet = SwTransferable::_PasteFileName( rData, rSh, nFormat,
1417 										SW_PASTESDR_INSERT, pPt,
1418 										nActionFlags, bMsg );
1419 			if( nRet & SWTRANSFER_GRAPHIC_INSERTED )
1420                 bCallAutoCaption = true;
1421             break;
1422 
1423 		case EXCHG_OUT_ACTION_INSERT_OLE:
1424 			nRet = SwTransferable::_PasteOLE( rData, rSh, nFormat,
1425 												nActionFlags,bMsg );
1426 			break;
1427 
1428 		case EXCHG_OUT_ACTION_INSERT_DDE:
1429 			{
1430 				sal_Bool bReRead = 0 != CNT_HasGrf( rSh.GetCntType() );
1431 				nRet = SwTransferable::_PasteDDE( rData, rSh, bReRead, bMsg );
1432 			}
1433 			break;
1434 
1435 		case EXCHG_OUT_ACTION_INSERT_HYPERLINK:
1436 			{
1437 				String sURL, sDesc;
1438 				if( SOT_FORMAT_FILE == nFormat )
1439 				{
1440 					if( rData.GetString( nFormat, sURL ) && sURL.Len() )
1441 					{
1442 						SwTransferable::_CheckForURLOrLNKFile( rData, sURL, &sDesc );
1443 						if( !sDesc.Len() )
1444 							sDesc = sURL;
1445 						nRet = 1;
1446 					}
1447 				}
1448 				else
1449 				{
1450 					INetBookmark aBkmk;
1451 					if( rData.GetINetBookmark( nFormat, aBkmk ) )
1452 					{
1453 						sURL = aBkmk.GetURL();
1454 						sDesc = aBkmk.GetDescription();
1455 						nRet = 1;
1456 					}
1457 				}
1458 
1459 				if( nRet )
1460 				{
1461 					SwFmtINetFmt aFmt( sURL, aEmptyStr );
1462 					rSh.InsertURL( aFmt, sDesc );
1463 				}
1464 			}
1465 			break;
1466 
1467 		case EXCHG_OUT_ACTION_GET_ATTRIBUTES:
1468 			switch( nFormat )
1469 			{
1470 			case SOT_FORMATSTR_ID_DRAWING:
1471 				nRet = SwTransferable::_PasteSdrFormat( rData, rSh,
1472 												SW_PASTESDR_SETATTR, pPt,
1473 												nActionFlags, bNeedToSelectBeforePaste);
1474 				break;
1475 			case SOT_FORMATSTR_ID_SVXB:
1476 			case SOT_FORMAT_GDIMETAFILE:
1477 			case SOT_FORMAT_BITMAP:
1478             case SOT_FORMATSTR_ID_PNG:
1479 			case SOT_FORMATSTR_ID_NETSCAPE_BOOKMARK:
1480 			case SOT_FORMAT_FILE:
1481 			case SOT_FORMATSTR_ID_FILEGRPDESCRIPTOR:
1482 			case SOT_FORMATSTR_ID_UNIFORMRESOURCELOCATOR:
1483 				nRet = SwTransferable::_PasteGrf( rData, rSh, nFormat,
1484 												SW_PASTESDR_SETATTR, pPt,
1485 												nActionFlags, nDropAction, bNeedToSelectBeforePaste);
1486 				break;
1487 			default:
1488 				ASSERT( sal_False, "unbekanntes Format" );
1489 			}
1490 
1491 			break;
1492 
1493 		case EXCHG_OUT_ACTION_INSERT_DRAWOBJ:
1494 			nRet = SwTransferable::_PasteSdrFormat( rData, rSh,
1495 												SW_PASTESDR_INSERT, pPt,
1496 												nActionFlags, bNeedToSelectBeforePaste);
1497 			break;
1498 		case EXCHG_OUT_ACTION_INSERT_SVXB:
1499 		case EXCHG_OUT_ACTION_INSERT_GDIMETAFILE:
1500 		case EXCHG_OUT_ACTION_INSERT_BITMAP:
1501 		case EXCHG_OUT_ACTION_INSERT_GRAPH:
1502 			nRet = SwTransferable::_PasteGrf( rData, rSh, nFormat,
1503 												SW_PASTESDR_INSERT, pPt,
1504 												nActionFlags, nDropAction, bNeedToSelectBeforePaste);
1505 			break;
1506 
1507 		case EXCHG_OUT_ACTION_REPLACE_DRAWOBJ:
1508 			nRet = SwTransferable::_PasteSdrFormat( rData, rSh,
1509 												SW_PASTESDR_REPLACE, pPt,
1510 												nActionFlags, bNeedToSelectBeforePaste);
1511 			break;
1512 
1513 		case EXCHG_OUT_ACTION_REPLACE_SVXB:
1514 		case EXCHG_OUT_ACTION_REPLACE_GDIMETAFILE:
1515 		case EXCHG_OUT_ACTION_REPLACE_BITMAP:
1516 		case EXCHG_OUT_ACTION_REPLACE_GRAPH:
1517 			nRet = SwTransferable::_PasteGrf( rData, rSh, nFormat,
1518 												SW_PASTESDR_REPLACE,pPt,
1519 												nActionFlags, nDropAction, bNeedToSelectBeforePaste);
1520 			break;
1521 
1522 		case EXCHG_OUT_ACTION_INSERT_INTERACTIVE:
1523 			nRet = SwTransferable::_PasteAsHyperlink( rData, rSh, nFormat );
1524 			break;
1525 
1526 		default:
1527 			ASSERT( sal_False, "unbekannte Action" );
1528 		}
1529 	}
1530 
1531 	if( !bPasteSelection && rSh.IsFrmSelected() )
1532 	{
1533 		rSh.EnterSelFrmMode();
1534 		//force ::SelectShell
1535 		rSh.GetView().StopShellTimer();
1536 	}
1537 
1538 	if( pAction )
1539 		delete pAction;
1540     if( bCallAutoCaption )
1541         rSh.GetView().AutoCaption( GRAPHIC_CAP );
1542 
1543 	return nRet;
1544 }
1545 
1546 // -----------------------------------------------------------------------
1547 
GetSotDestination(const SwWrtShell & rSh,const Point * pPt)1548 sal_uInt16 SwTransferable::GetSotDestination( const SwWrtShell& rSh,
1549 											const Point* pPt )
1550 {
1551 	sal_uInt16 nRet = EXCHG_INOUT_ACTION_NONE;
1552 
1553 	ObjCntType eOType;
1554 	if( pPt )
1555 	{
1556 		SdrObject *pObj = 0;
1557 		eOType = rSh.GetObjCntType( *pPt, pObj );
1558 	}
1559 	else
1560 		eOType = rSh.GetObjCntTypeOfSelection();
1561 
1562 	switch( eOType )
1563 	{
1564 	case OBJCNT_GRF:
1565 		{
1566 			sal_Bool bIMap, bLink;
1567 			if( pPt )
1568 			{
1569 				bIMap = 0 != rSh.GetFmtFromObj( *pPt )->GetURL().GetMap();
1570 				String aDummy;
1571 				rSh.GetGrfAtPos( *pPt, aDummy, bLink );
1572 			}
1573 			else
1574 			{
1575 				bIMap = 0 != rSh.GetFlyFrmFmt()->GetURL().GetMap();
1576 				String aDummy;
1577 				rSh.GetGrfNms( &aDummy, 0 );
1578 				bLink = 0 != aDummy.Len();
1579 			}
1580 
1581 			if( bLink && bIMap )
1582 				nRet = EXCHG_DEST_DOC_LNKD_GRAPH_W_IMAP;
1583 			else if( bLink )
1584 				nRet = EXCHG_DEST_DOC_LNKD_GRAPHOBJ;
1585 			else if( bIMap )
1586 				nRet = EXCHG_DEST_DOC_GRAPH_W_IMAP;
1587 			else
1588 				nRet = EXCHG_DEST_DOC_GRAPHOBJ;
1589 		}
1590 		break;
1591 
1592 	case OBJCNT_FLY:
1593 		if( rSh.GetView().GetDocShell()->ISA(SwWebDocShell) )
1594 			nRet = EXCHG_DEST_DOC_TEXTFRAME_WEB;
1595 		else
1596 			nRet = EXCHG_DEST_DOC_TEXTFRAME;
1597 		break;
1598 	case OBJCNT_OLE:		nRet = EXCHG_DEST_DOC_OLEOBJ;		break;
1599 
1600 	case OBJCNT_CONTROL:	/* no Action avail */
1601 	case OBJCNT_SIMPLE:		nRet = EXCHG_DEST_DOC_DRAWOBJ; 		break;
1602 	case OBJCNT_URLBUTTON:	nRet = EXCHG_DEST_DOC_URLBUTTON; 	break;
1603 	case OBJCNT_GROUPOBJ:	nRet = EXCHG_DEST_DOC_GROUPOBJ;		break;
1604 
1605 // was mmchen wir bei Mehrfachselektion???
1606 //	case OBJCNT_DONTCARE:
1607 	default:
1608 		{
1609 /*
1610 JP 13.07.98: Bug 52637: es wird ein URL-Feld erkannt also werden nur die
1611 						Inhalte zugelassen. Das ist aber bestimmt nicht das
1612 						gewollte.
1613 			SwContentAtPos aCntntAtPos( SwContentAtPos::SW_INETATTR );
1614 			SfxItemSet aSet( (SfxItemPool&)rSh.GetAttrPool(),
1615 							RES_TXTATR_INETFMT, RES_TXTATR_INETFMT );
1616 			if( pPt ? ((SwWrtShell&)rSh).GetContentAtPos( *pPt, aCntntAtPos, sal_False )
1617 					 : (rSh.GetAttr( aSet ) && aSet.Count()) )
1618 				nRet = EXCHG_DEST_DOC_URLFIELD;
1619 			else
1620 */
1621 			if( rSh.GetView().GetDocShell()->ISA(SwWebDocShell) )
1622 				nRet = EXCHG_DEST_SWDOC_FREE_AREA_WEB;
1623 			else
1624 				nRet = EXCHG_DEST_SWDOC_FREE_AREA;
1625 		}
1626 	}
1627 
1628 	return nRet;
1629 }
1630 
1631 // -----------------------------------------------------------------------
1632 
_PasteFileContent(TransferableDataHelper & rData,SwWrtShell & rSh,sal_uLong nFmt,sal_Bool bMsg)1633 int SwTransferable::_PasteFileContent( TransferableDataHelper& rData,
1634 									SwWrtShell& rSh, sal_uLong nFmt, sal_Bool bMsg )
1635 {
1636 	sal_uInt16 nResId = MSG_CLPBRD_FORMAT_ERROR;
1637 	int nRet = 0;
1638 
1639 	MSE40HTMLClipFormatObj aMSE40ClpObj;
1640 
1641 	SotStorageStreamRef xStrm;
1642 	SvStream* pStream = 0;
1643 	SwRead pRead = 0;
1644 	rtl::OUString sData;
1645 	switch( nFmt )
1646 	{
1647 	case SOT_FORMAT_STRING:
1648 		{
1649 			pRead = ReadAscii;
1650 			if( rData.GetString( nFmt, sData ) )
1651 			{
1652 				pStream = new SvMemoryStream( (void*)sData.getStr(),
1653 							sData.getLength() * sizeof( sal_Unicode ),
1654 							STREAM_READ );
1655 #ifdef OSL_BIGENDIAN
1656 				pStream->SetNumberFormatInt( NUMBERFORMAT_INT_BIGENDIAN );
1657 #else
1658 				pStream->SetNumberFormatInt( NUMBERFORMAT_INT_LITTLEENDIAN );
1659 #endif
1660 
1661 				SwAsciiOptions aAOpt;
1662 				aAOpt.SetCharSet( RTL_TEXTENCODING_UCS2 );
1663 				pRead->GetReaderOpt().SetASCIIOpts( aAOpt );
1664 				break;
1665 			}
1666 		}
1667 		// no break - because then test if we get a stream
1668 
1669 	default:
1670 		if( rData.GetSotStorageStream( nFmt, xStrm ) )
1671 		{
1672 			if( ( SOT_FORMATSTR_ID_HTML_SIMPLE == nFmt ) ||
1673                 ( SOT_FORMATSTR_ID_HTML_NO_COMMENT == nFmt ) )
1674 			{
1675 				pStream = aMSE40ClpObj.IsValid( *xStrm );
1676 				pRead = ReadHTML;
1677 				pRead->SetReadUTF8( sal_True );
1678                 //pRead->SetBaseURL( aMSE40ClpObj.GetBaseURL() );
1679 
1680                 sal_Bool bNoComments =
1681                     ( nFmt == SOT_FORMATSTR_ID_HTML_NO_COMMENT );
1682                 pRead->SetIgnoreHTMLComments( bNoComments );
1683 			}
1684 			else
1685 			{
1686 				pStream = &xStrm;
1687 				if( SOT_FORMAT_RTF == nFmt )
1688 					pRead = SwReaderWriter::GetReader( READER_WRITER_RTF );
1689 				else if( !pRead )
1690                 {
1691 					pRead = ReadHTML;
1692     				pRead->SetReadUTF8( sal_True );
1693                 }
1694 			}
1695 		}
1696 		break;
1697 	}
1698 
1699 	if( pStream && pRead )
1700 	{
1701 		Link aOldLink( rSh.GetChgLnk() );
1702 		rSh.SetChgLnk( Link() );
1703 
1704         const SwPosition& rInsPos = *rSh.GetCrsr()->Start();
1705 		SwReader aReader( *pStream, aEmptyStr, String(), *rSh.GetCrsr() );
1706 		rSh.SaveTblBoxCntnt( &rInsPos );
1707 		if( IsError( aReader.Read( *pRead )) )
1708 			nResId = ERR_CLPBRD_READ;
1709 		else
1710 			nResId = 0, nRet = 1;
1711 
1712 		rSh.SetChgLnk( aOldLink );
1713 		if( nRet )
1714 			rSh.CallChgLnk();
1715 	}
1716 	else
1717 		nResId = MSG_CLPBRD_FORMAT_ERROR;
1718 
1719 	// Exist a SvMemoryStream? (data in the OUString and xStrm is empty)
1720 	if( pStream && !xStrm.Is() )
1721 		delete pStream;
1722 
1723 	if( bMsg && nResId )
1724 	{
1725 		InfoBox( 0, SW_RES( nResId )).Execute();
1726 	}
1727 	return nRet;
1728 }
1729 
1730 // -----------------------------------------------------------------------
1731 
_PasteOLE(TransferableDataHelper & rData,SwWrtShell & rSh,sal_uLong nFmt,sal_uInt8 nActionFlags,sal_Bool bMsg)1732 int SwTransferable::_PasteOLE( TransferableDataHelper& rData, SwWrtShell& rSh,
1733 								sal_uLong nFmt, sal_uInt8 nActionFlags, sal_Bool bMsg )
1734 {
1735 	int nRet = 0;
1736 	TransferableObjectDescriptor aObjDesc;
1737     uno::Reference < io::XInputStream > xStrm;
1738     uno::Reference < embed::XStorage > xStore;
1739 	Reader* pRead = 0;
1740 
1741     // Get the preferred format
1742     SotFormatStringId nId;
1743 	if( rData.HasFormat( SOT_FORMATSTR_ID_EMBEDDED_OBJ ) )
1744 		nId = SOT_FORMATSTR_ID_EMBEDDED_OBJ;
1745 	else if( rData.HasFormat( SOT_FORMATSTR_ID_EMBED_SOURCE ) &&
1746 			 rData.HasFormat( SOT_FORMATSTR_ID_OBJECTDESCRIPTOR ))
1747 		nId = SOT_FORMATSTR_ID_EMBED_SOURCE;
1748 	else
1749 		nId = 0;
1750 
1751     if( nId && rData.GetInputStream( nId, xStrm ) && xStrm.is() )
1752 	{
1753         // if there is an embedded object, first try if it's a writer object
1754         // this will be inserted into the document by using a Reader
1755         try
1756         {
1757             xStore = comphelper::OStorageHelper::GetStorageFromInputStream( xStrm );
1758             switch( SotStorage::GetFormatID( xStore ) )
1759             {
1760                 case SOT_FORMATSTR_ID_STARWRITER_60:
1761                 case SOT_FORMATSTR_ID_STARWRITERWEB_60:
1762                 case SOT_FORMATSTR_ID_STARWRITERGLOB_60:
1763 				case SOT_FORMATSTR_ID_STARWRITER_8:
1764 				case SOT_FORMATSTR_ID_STARWRITERWEB_8:
1765 				case SOT_FORMATSTR_ID_STARWRITERGLOB_8:
1766                     pRead = ReadXML;
1767                     break;
1768                 default:
1769                     try
1770                     {
1771                         uno::Reference < lang::XComponent > xComp( xStore, uno::UNO_QUERY );
1772                         xComp->dispose();
1773                         xStore = 0;
1774                     }
1775                     catch ( uno::Exception& )
1776                     {
1777                     }
1778 
1779                     break;
1780             }
1781         }
1782         catch ( uno::Exception& )
1783         {
1784             // it wasn't a storage, but maybe it's a useful stream
1785         }
1786 
1787         nFmt = nId;
1788 	}
1789 
1790     if( pRead )
1791 	{
1792 		SwPaM &rPAM = *rSh.GetCrsr();
1793         SwReader aReader( xStore, aEmptyStr, rPAM );
1794         if( !IsError( aReader.Read( *pRead )) )
1795             nRet = 1;
1796         else if( bMsg )
1797             InfoBox( 0, SW_RES(ERR_CLPBRD_READ) ).Execute();
1798 	}
1799     else
1800 	{
1801        	// temporary storage until the object is inserted
1802 		uno::Reference< embed::XStorage > xTmpStor;
1803         uno::Reference < embed::XEmbeddedObject > xObj;
1804         ::rtl::OUString aName;
1805        	comphelper::EmbeddedObjectContainer aCnt;
1806 
1807 		if ( xStrm.is() )
1808 		{
1809 			if ( !rData.GetTransferableObjectDescriptor( SOT_FORMATSTR_ID_OBJECTDESCRIPTOR, aObjDesc ) )
1810 			{
1811 				DBG_ASSERT( !xStrm.is(), "An object without descriptor in clipboard!");
1812 			}
1813 		}
1814 		else
1815 		{
1816 			if( rData.HasFormat( nFmt = SOT_FORMATSTR_ID_OBJECTDESCRIPTOR_OLE ) && rData.GetTransferableObjectDescriptor( nFmt, aObjDesc ) )
1817  			{
1818             	if ( !rData.GetInputStream( SOT_FORMATSTR_ID_EMBED_SOURCE_OLE, xStrm ) )
1819                 	rData.GetInputStream( SOT_FORMATSTR_ID_EMBEDDED_OBJ_OLE, xStrm );
1820 
1821 				if ( !xStrm.is() )
1822 				{
1823 					// This is MSOLE object that should be created by direct using of system clipboard
1824 					try
1825 					{
1826 						xTmpStor = ::comphelper::OStorageHelper::GetTemporaryStorage();
1827 						uno::Reference < embed::XEmbedObjectClipboardCreator > xClipboardCreator(
1828 							::comphelper::getProcessServiceFactory()->createInstance( ::rtl::OUString(
1829 											RTL_CONSTASCII_USTRINGPARAM("com.sun.star.embed.MSOLEObjectSystemCreator")) ),
1830 							uno::UNO_QUERY_THROW );
1831 
1832 						embed::InsertedObjectInfo aInfo = xClipboardCreator->createInstanceInitFromClipboard(
1833 															xTmpStor,
1834 															::rtl::OUString( RTL_CONSTASCII_USTRINGPARAM ( "DummyName" ) ),
1835 															uno::Sequence< beans::PropertyValue >() );
1836 
1837 						// TODO/LATER: in future InsertedObjectInfo will be used to get container related information
1838 						// for example whether the object should be an iconified one
1839 						xObj = aInfo.Object;
1840 					}
1841 					catch( uno::Exception& )
1842 					{}
1843 				}
1844 			}
1845     	}
1846 
1847 		if ( xStrm.is() && !xObj.is() )
1848         	xObj = aCnt.InsertEmbeddedObject( xStrm, aName );
1849 
1850         if( xObj.is() )
1851 		{
1852 			svt::EmbeddedObjectRef xObjRef( xObj, aObjDesc.mnViewAspect );
1853 
1854 			// try to get the replacement image from the clipboard
1855 			Graphic aGraphic;
1856 			sal_uLong nGrFormat = 0;
1857 
1858 // (wg. Selection Manager bei Trustet Solaris)
1859 #ifndef SOLARIS
1860 /*
1861             if( rData.GetGraphic( SOT_FORMATSTR_ID_SVXB, aGraphic ) )
1862 				nGrFormat = SOT_FORMATSTR_ID_SVXB;
1863 			else if( rData.GetGraphic( FORMAT_GDIMETAFILE, aGraphic ) )
1864 				nGrFormat = SOT_FORMAT_GDIMETAFILE;
1865 			else if( rData.GetGraphic( FORMAT_BITMAP, aGraphic ) )
1866 				nGrFormat = SOT_FORMAT_BITMAP;
1867 */
1868 #endif
1869 
1870 			// insert replacement image ( if there is one ) into the object helper
1871 			if ( nGrFormat )
1872 			{
1873 				datatransfer::DataFlavor aDataFlavor;
1874 				SotExchange::GetFormatDataFlavor( nGrFormat, aDataFlavor );
1875                	xObjRef.SetGraphic( aGraphic, aDataFlavor.MimeType );
1876 			}
1877 			else if ( aObjDesc.mnViewAspect == embed::Aspects::MSOLE_ICON )
1878 			{
1879 				// it is important to have an icon, let an empty graphic be used
1880 				// if no other graphic is provided
1881 				// TODO/LATER: in future a default bitmap could be used
1882 				::rtl::OUString aMimeType;
1883 				MapMode aMapMode( MAP_100TH_MM );
1884 				aGraphic.SetPrefSize( Size( 2500, 2500 ) );
1885 				aGraphic.SetPrefMapMode( aMapMode );
1886                	xObjRef.SetGraphic( aGraphic, aMimeType );
1887 			}
1888 
1889 			//Size einstellen. Ist ein Hack wg. Auslieferung, die Size sollte
1890 			//an das InsertOle uebergeben werden!!!!!!!!!!
1891 			Size aSize;
1892 			if ( aObjDesc.mnViewAspect == embed::Aspects::MSOLE_ICON )
1893 			{
1894                	if( aObjDesc.maSize.Width() && aObjDesc.maSize.Height() )
1895 					aSize = aObjDesc.maSize;
1896 				else
1897 				{
1898 					MapMode aMapMode( MAP_100TH_MM );
1899 					aSize = xObjRef.GetSize( &aMapMode );
1900 				}
1901 			}
1902 			else if( aObjDesc.maSize.Width() && aObjDesc.maSize.Height() )
1903 			{
1904             	aSize = Size( aObjDesc.maSize );    //immer 100TH_MM
1905                 MapUnit aUnit = VCLUnoHelper::UnoEmbed2VCLMapUnit( xObj->getMapUnit( aObjDesc.mnViewAspect ) );
1906                 aSize = OutputDevice::LogicToLogic( aSize, MAP_100TH_MM, aUnit );
1907                 awt::Size aSz;
1908 				try
1909 				{
1910 					aSz = xObj->getVisualAreaSize( aObjDesc.mnViewAspect );
1911 				}
1912 				catch( embed::NoVisualAreaSizeException& )
1913 				{
1914 					// in this case the provided size is used
1915 				}
1916 
1917 				if ( aSz.Width != aSize.Width() || aSz.Height != aSize.Height() )
1918 				{
1919                 	aSz.Width = aSize.Width();
1920                 	aSz.Height = aSize.Height();
1921                 	xObj->setVisualAreaSize( aObjDesc.mnViewAspect, aSz );
1922 				}
1923 			}
1924 			else
1925 			{
1926 				// the descriptor contains the wrong object size
1927 				// the following call will let the MSOLE objects cache the size if it is possible
1928 				// it should be done while the object is running
1929 				try
1930 				{
1931 					xObj->getVisualAreaSize( aObjDesc.mnViewAspect );
1932 				}
1933 				catch( uno::Exception& )
1934 				{
1935 				}
1936 			}
1937 			//Ende mit Hack!
1938 
1939             rSh.InsertOleObject( xObjRef );
1940 			nRet = 1;
1941 
1942 			if( nRet && ( nActionFlags &
1943 				( EXCHG_OUT_ACTION_FLAG_INSERT_TARGETURL >> 8) ))
1944 				SwTransferable::_PasteTargetURL( rData, rSh, 0, 0, sal_False );
1945 
1946 			// let the object be unloaded if possible
1947 			SwOLEObj::UnloadObject( xObj, rSh.GetDoc(), embed::Aspects::MSOLE_CONTENT );
1948 		}
1949 	}
1950 	return nRet;
1951 }
1952 
1953 // -----------------------------------------------------------------------
1954 
1955 
1956 // -----------------------------------------------------------------------
1957 
_PasteTargetURL(TransferableDataHelper & rData,SwWrtShell & rSh,sal_uInt16 nAction,const Point * pPt,sal_Bool bInsertGRF)1958 int SwTransferable::_PasteTargetURL( TransferableDataHelper& rData,
1959 									SwWrtShell& rSh, sal_uInt16 nAction,
1960 									const Point* pPt, sal_Bool bInsertGRF )
1961 {
1962 	int nRet = 0;
1963 	INetImage aINetImg;
1964 	if( ( rData.HasFormat( SOT_FORMATSTR_ID_INET_IMAGE ) &&
1965 		  rData.GetINetImage( SOT_FORMATSTR_ID_INET_IMAGE, aINetImg )) ||
1966 		( rData.HasFormat( SOT_FORMATSTR_ID_NETSCAPE_IMAGE ) &&
1967 		  rData.GetINetImage( SOT_FORMATSTR_ID_NETSCAPE_IMAGE, aINetImg )) )
1968 	{
1969 		if( aINetImg.GetImageURL().Len() && bInsertGRF )
1970 		{
1971 			String sURL( aINetImg.GetImageURL() );
1972 			SwTransferable::_CheckForURLOrLNKFile( rData, sURL );
1973 
1974 			//!!! auf FileSystem abpruefen - nur dann ist es sinnvoll die
1975 			// Grafiken zu testen !!!!
1976 			Graphic aGrf;
1977 			GraphicFilter *pFlt = GraphicFilter::GetGraphicFilter();
1978 			nRet = GRFILTER_OK == GraphicFilter::LoadGraphic( sURL, aEmptyStr, aGrf, pFlt );
1979 			if( nRet )
1980 			{
1981 				switch( nAction )
1982 				{
1983 				case SW_PASTESDR_INSERT:
1984 					SwTransferable::SetSelInShell( rSh, sal_False, pPt );
1985 					rSh.Insert( sURL, aEmptyStr, aGrf );
1986 					break;
1987 
1988 				case SW_PASTESDR_REPLACE:
1989 					if( rSh.IsObjSelected() )
1990 					{
1991 						rSh.ReplaceSdrObj( sURL, aEmptyStr, &aGrf );
1992 						Point aPt( pPt ? *pPt : rSh.GetCrsrDocPos() );
1993 						SwTransferable::SetSelInShell( rSh, sal_True, &aPt );
1994 					}
1995 					else
1996 						rSh.ReRead( sURL, aEmptyStr, &aGrf );
1997 					break;
1998 
1999 				case SW_PASTESDR_SETATTR:
2000 					if( rSh.IsObjSelected() )
2001 						rSh.Paste( aGrf, String() );
2002 					else if( OBJCNT_GRF == rSh.GetObjCntTypeOfSelection() )
2003 						rSh.ReRead( sURL, aEmptyStr, &aGrf );
2004 					else
2005 					{
2006 						SwTransferable::SetSelInShell( rSh, sal_False, pPt );
2007 						rSh.Insert( sURL, aEmptyStr, aGrf );
2008 					}
2009 					break;
2010 				default:
2011 					nRet = 0;
2012 				}
2013 			}
2014 		}
2015 		else
2016 			nRet = 1;
2017 	}
2018 
2019 	if( nRet )
2020 	{
2021 		SfxItemSet aSet( rSh.GetAttrPool(), RES_URL, RES_URL );
2022 		rSh.GetFlyFrmAttr( aSet );
2023 		SwFmtURL aURL( (SwFmtURL&)aSet.Get( RES_URL ) );
2024 
2025 		if( aURL.GetURL() != aINetImg.GetTargetURL() ||
2026 			aURL.GetTargetFrameName() != aINetImg.GetTargetFrame() )
2027 		{
2028 			aURL.SetURL( aINetImg.GetTargetURL(), sal_False );
2029 			aURL.SetTargetFrameName( aINetImg.GetTargetFrame() );
2030 			aSet.Put( aURL );
2031 			rSh.SetFlyFrmAttr( aSet );
2032 		}
2033 	}
2034 	return nRet;
2035 }
2036 
2037 
2038 // -----------------------------------------------------------------------
2039 
SetSelInShell(SwWrtShell & rSh,sal_Bool bSelectFrm,const Point * pPt)2040 void SwTransferable::SetSelInShell( SwWrtShell& rSh, sal_Bool bSelectFrm,
2041 										const Point* pPt )
2042 {
2043 	if( bSelectFrm )
2044 	{
2045 		// Rahmen/Objecte selektieren
2046         if( pPt && !rSh.GetView().GetViewFrame()->GetDispatcher()->IsLocked() )
2047 		{
2048 			rSh.GetView().NoRotate();
2049 			if( rSh.SelectObj( *pPt ))
2050 			{
2051 				rSh.HideCrsr();
2052 				rSh.EnterSelFrmMode( pPt );
2053 				bFrmDrag = sal_True;
2054 			}
2055 		}
2056 	}
2057 	else
2058 	{
2059 		if( rSh.IsFrmSelected() || rSh.IsObjSelected() )
2060 		{
2061 			rSh.UnSelectFrm();
2062 			rSh.LeaveSelFrmMode();
2063 			rSh.GetView().GetEditWin().StopInsFrm();
2064 			bFrmDrag = sal_False;
2065 		}
2066 		else if( rSh.GetView().GetDrawFuncPtr() )
2067 			rSh.GetView().GetEditWin().StopInsFrm();
2068 
2069 		rSh.EnterStdMode();
2070 		if( pPt )
2071 			rSh.SwCrsrShell::SetCrsr( *pPt, sal_True );
2072 	}
2073 }
2074 
2075 // -----------------------------------------------------------------------
2076 
_PasteDDE(TransferableDataHelper & rData,SwWrtShell & rWrtShell,sal_Bool bReReadGrf,sal_Bool bMsg)2077 int SwTransferable::_PasteDDE( TransferableDataHelper& rData,
2078 								SwWrtShell& rWrtShell, sal_Bool bReReadGrf,
2079 								sal_Bool bMsg )
2080 {
2081 	// Daten aus dem Clipboardformat
2082 	String aApp, aTopic, aItem;
2083 
2084 	{
2085 		SotStorageStreamRef xStrm;
2086 		if( !rData.GetSotStorageStream( SOT_FORMATSTR_ID_LINK, xStrm ))
2087 		{
2088 			ASSERT( !&rWrtShell, "DDE Data not found." );
2089 			return 0;
2090 		}	//sinnvollen Fehler melden!!
2091 
2092         rtl_TextEncoding eEncoding = DDE_TXT_ENCODING;
2093         xStrm->ReadCString( aApp, eEncoding );
2094         xStrm->ReadCString( aTopic, eEncoding );
2095         xStrm->ReadCString( aItem, eEncoding );
2096 	}
2097 
2098 	String aCmd;
2099     sfx2::MakeLnkName( aCmd, &aApp, aTopic, aItem );
2100 
2101 	// wollen wir jetzt eine Grafik einlesen ?
2102 	sal_uLong nFormat;
2103 	if( !rData.HasFormat( FORMAT_RTF ) &&
2104 		!rData.HasFormat( SOT_FORMATSTR_ID_HTML ) &&
2105 		!rData.HasFormat( FORMAT_STRING ) &&
2106 		(rData.HasFormat( nFormat = FORMAT_GDIMETAFILE ) ||
2107 		 rData.HasFormat( nFormat = FORMAT_BITMAP )) )
2108 	{
2109 		Graphic aGrf;
2110 		int nRet = rData.GetGraphic( nFormat, aGrf );
2111 		if( nRet )
2112 		{
2113 			String sLnkTyp( String::CreateFromAscii(
2114 						RTL_CONSTASCII_STRINGPARAM( "DDE" )));
2115 			if ( bReReadGrf )
2116 				rWrtShell.ReRead( aCmd, sLnkTyp, &aGrf );
2117 			else
2118 				rWrtShell.Insert( aCmd, sLnkTyp, aGrf );
2119 		}
2120 		return nRet;
2121 	}
2122 
2123     SwFieldType* pTyp = 0;
2124 	sal_uInt16 i = 1,j;
2125 	String aName;
2126 	sal_Bool bAlreadyThere = sal_False, bDoublePaste = sal_False;
2127 	sal_uInt16 nSize = rWrtShell.GetFldTypeCount();
2128 	const ::utl::TransliterationWrapper& rColl = ::GetAppCmpStrIgnore();
2129 
2130 	do {
2131 		aName = aApp;
2132 		aName += String::CreateFromInt32( i );
2133 		for( j = INIT_FLDTYPES; j < nSize; j++ )
2134 		{
2135 			pTyp = rWrtShell.GetFldType( j );
2136 			if( RES_DDEFLD == pTyp->Which() )
2137 			{
2138 				String sTmp( ((SwDDEFieldType*)pTyp)->GetCmd() );
2139 				if( rColl.isEqual( sTmp, aCmd ) &&
2140                     sfx2::LINKUPDATE_ALWAYS == ((SwDDEFieldType*)pTyp)->GetType() )
2141 				{
2142 					aName = pTyp->GetName();
2143 					bDoublePaste = sal_True;
2144 					break;
2145 				}
2146 				else if( rColl.isEqual( aName, pTyp->GetName() ) )
2147 					break;
2148 			}
2149 		}
2150 		if( j == nSize )
2151 			bAlreadyThere = sal_False;
2152 		else
2153 		{
2154 			bAlreadyThere = sal_True;
2155 			i++;
2156 		}
2157 	}
2158 	while( bAlreadyThere && !bDoublePaste );
2159 
2160 	if( !bDoublePaste )
2161 	{
2162         SwDDEFieldType aType( aName, aCmd, sfx2::LINKUPDATE_ALWAYS );
2163 		pTyp = rWrtShell.InsertFldType( aType );
2164 	}
2165 
2166 
2167 	SwDDEFieldType* pDDETyp = (SwDDEFieldType*)pTyp;
2168 
2169 	String aExpand;
2170 	if( rData.GetString( FORMAT_STRING, aExpand ))
2171 	{
2172 		do {			// middle checked loop
2173 
2174 			// Wenn die Daten von einer Tabellenkalkulation kommen
2175 			// fuegen wir eine DDE-Tabelle ein
2176 			if( ( rData.HasFormat( SOT_FORMATSTR_ID_SYLK ) ||
2177 				  rData.HasFormat( SOT_FORMATSTR_ID_SYLK_BIGCAPS ) ) &&
2178 				aExpand.Len() &&
2179 				 ( 1 < aExpand.GetTokenCount( '\n' ) ||
2180 					   aExpand.GetTokenCount( '\t' )) )
2181 			{
2182 				String sTmp( aExpand );
2183 				xub_StrLen nRows = sTmp.GetTokenCount( '\n' );
2184 				if( nRows )
2185 					--nRows;
2186 				sTmp = sTmp.GetToken( 0, '\n' );
2187 				xub_StrLen nCols = sTmp.GetTokenCount( '\t' );
2188 
2189 				// mindestens eine Spalte & Zeile muss vorhanden sein
2190 				if( !nRows || !nCols )
2191 				{
2192 					if( bMsg )
2193 						InfoBox(0, SW_RESSTR(STR_NO_TABLE)).Execute();
2194 					pDDETyp = 0;
2195 					break;
2196 				}
2197 
2198                 rWrtShell.InsertDDETable(
2199                     SwInsertTableOptions( tabopts::HEADLINE_NO_BORDER, 1 ), // TODO MULTIHEADER
2200                     pDDETyp, nRows, nCols );
2201 			}
2202 			else if( 1 < aExpand.GetTokenCount( '\n' ) )
2203 			{
2204 				// mehrere Absaetze -> eine geschuetzte Section einfuegen
2205 				if( rWrtShell.HasSelection() )
2206 					rWrtShell.DelRight();
2207 
2208                 SwSectionData aSect( DDE_LINK_SECTION, aName );
2209 				aSect.SetLinkFileName( aCmd );
2210                 aSect.SetProtectFlag(true);
2211 				rWrtShell.InsertSection( aSect );
2212 
2213 				pDDETyp = 0;				// FeldTypen wieder entfernen
2214 			}
2215 			else
2216 			{
2217 				// Einfuegen
2218 				SwDDEField aSwDDEField( pDDETyp );
2219 				rWrtShell.Insert( aSwDDEField );
2220 			}
2221 
2222 		} while( sal_False );
2223 	}
2224 	else
2225 		pDDETyp = 0;						// FeldTypen wieder entfernen
2226 
2227 	if( !pDDETyp && !bDoublePaste )
2228 	{
2229 		// FeldTyp wieder entfernen - Fehler aufgetreten!
2230 		for( j = nSize; j >= INIT_FLDTYPES; --j )
2231 			if( pTyp == rWrtShell.GetFldType( j ) )
2232 			{
2233 				rWrtShell.RemoveFldType( j );
2234 				break;
2235 			}
2236 	}
2237 
2238 	return 1;
2239 }
2240 
2241 // -----------------------------------------------------------------------
2242 
_PasteSdrFormat(TransferableDataHelper & rData,SwWrtShell & rSh,sal_uInt16 nAction,const Point * pPt,sal_uInt8 nActionFlags,bool bNeedToSelectBeforePaste)2243 int SwTransferable::_PasteSdrFormat(  TransferableDataHelper& rData,
2244 									SwWrtShell& rSh, sal_uInt16 nAction,
2245 									const Point* pPt, sal_uInt8 nActionFlags, bool bNeedToSelectBeforePaste)
2246 {
2247 	int nRet = 0;
2248 	SotStorageStreamRef xStrm;
2249 	if( rData.GetSotStorageStream( SOT_FORMATSTR_ID_DRAWING, xStrm ))
2250 	{
2251 		xStrm->SetVersion( SOFFICE_FILEFORMAT_50 );
2252 
2253         if(bNeedToSelectBeforePaste && pPt)
2254         {
2255             // if this is an internal drag, need to set the target right (select it), else
2256             // still the source will be selected
2257             SwTransferable::SetSelInShell( rSh, sal_True, pPt );
2258         }
2259 
2260 		rSh.Paste( *xStrm, nAction, pPt );
2261 		nRet = 1;
2262 
2263 		if( nRet && ( nActionFlags &
2264 			( EXCHG_OUT_ACTION_FLAG_INSERT_TARGETURL >> 8) ))
2265 			SwTransferable::_PasteTargetURL( rData, rSh, 0, 0, sal_False );
2266 	}
2267 	return nRet;
2268 }
2269 
2270 // -----------------------------------------------------------------------
2271 
_PasteGrf(TransferableDataHelper & rData,SwWrtShell & rSh,sal_uLong nFmt,sal_uInt16 nAction,const Point * pPt,sal_uInt8 nActionFlags,sal_Int8 nDropAction,bool bNeedToSelectBeforePaste)2272 int SwTransferable::_PasteGrf( TransferableDataHelper& rData, SwWrtShell& rSh,
2273 								sal_uLong nFmt, sal_uInt16 nAction, const Point* pPt,
2274 								sal_uInt8 nActionFlags, sal_Int8 nDropAction, bool bNeedToSelectBeforePaste)
2275 {
2276 	int nRet = 0;
2277 
2278 	Graphic aGrf;
2279 	INetBookmark aBkmk;
2280 	sal_Bool bCheckForGrf = sal_False, bCheckForImageMap = sal_False;
2281 
2282 	switch( nFmt )
2283 	{
2284 	case SOT_FORMAT_BITMAP:
2285     case SOT_FORMATSTR_ID_PNG:
2286 	case SOT_FORMAT_GDIMETAFILE:
2287 		nRet = rData.GetGraphic( nFmt, aGrf );
2288 		break;
2289 
2290     case SOT_FORMATSTR_ID_SVXB:
2291     {
2292         SotStorageStreamRef xStm;
2293 
2294         if(rData.GetSotStorageStream(SOT_FORMATSTR_ID_SVXB, xStm))
2295         {
2296             *xStm >> aGrf;
2297             nRet = (GRAPHIC_NONE != aGrf.GetType() && GRAPHIC_DEFAULT != aGrf.GetType());
2298         }
2299 
2300         break;
2301     }
2302 
2303 	case SOT_FORMATSTR_ID_NETSCAPE_BOOKMARK:
2304 	case SOT_FORMATSTR_ID_FILEGRPDESCRIPTOR:
2305 	case SOT_FORMATSTR_ID_UNIFORMRESOURCELOCATOR:
2306 		if( 0 != ( nRet = rData.GetINetBookmark( nFmt, aBkmk ) ))
2307 		{
2308 /*				if( SW_PASTESDR_SETATTR != nAction )
2309 			{
2310 				INetURLObject aURL( aBkmk.GetURL() );
2311 				bCheckForGrf = INET_PROT_FILE == aURL.GetProtocol();
2312 				nRet = 0 != bCheckForGrf;
2313 			}
2314 */
2315 			if( SW_PASTESDR_SETATTR == nAction )
2316 				nFmt = SOT_FORMATSTR_ID_NETSCAPE_BOOKMARK;
2317 			else
2318 				bCheckForGrf = sal_True;
2319 		}
2320 		break;
2321 
2322 	case SOT_FORMAT_FILE:
2323 		{
2324 			String sTxt;
2325 			if( 0 != ( nRet = rData.GetString( nFmt, sTxt ) ) )
2326 			{
2327 				String sDesc;
2328 				SwTransferable::_CheckForURLOrLNKFile( rData, sTxt, &sDesc );
2329 
2330                 aBkmk = INetBookmark(
2331                         URIHelper::SmartRel2Abs(INetURLObject(), sTxt, Link(), false ),
2332                         sDesc );
2333 				bCheckForGrf = sal_True;
2334 				bCheckForImageMap = SW_PASTESDR_REPLACE == nAction;
2335 			}
2336 		}
2337 		break;
2338 
2339 	default:
2340 		nRet = rData.GetGraphic( nFmt, aGrf );
2341 		break;
2342 	}
2343 
2344 	if( bCheckForGrf )
2345 	{
2346 		//!!! auf FileSystem abpruefen - nur dann ist es sinnvoll die
2347 		// Grafiken zu testen !!!!
2348 		GraphicFilter *pFlt = GraphicFilter::GetGraphicFilter();
2349 		nRet = GRFILTER_OK == GraphicFilter::LoadGraphic( aBkmk.GetURL(), aEmptyStr,
2350 											aGrf, pFlt );
2351 		if( !nRet && SW_PASTESDR_SETATTR == nAction &&
2352 			SOT_FORMAT_FILE == nFmt &&
2353 			// Bug 63031 - nur bei Rahmenselektion
2354 			rSh.IsFrmSelected() )
2355 		{
2356 			// dann als Hyperlink hinter die Grafik setzen
2357 			nFmt = SOT_FORMATSTR_ID_NETSCAPE_BOOKMARK;
2358 			nRet = sal_True;
2359 		}
2360 	}
2361 
2362     if(pPt && bNeedToSelectBeforePaste)
2363     {
2364         // when using internal D&Ds, still the source object is selected and
2365         // this is necessary to get the correct source data which is also
2366         // dependent from selection. After receiving the drag data it is
2367         // now tiime to select the correct target object
2368         SwTransferable::SetSelInShell( rSh, sal_True, pPt );
2369     }
2370 
2371 	if( nRet )
2372 	{
2373         String sURL;
2374 
2375         if( rSh.GetView().GetDocShell()->ISA(SwWebDocShell)
2376             // #123922# if link action is noted, also take URL
2377             || DND_ACTION_LINK == nDropAction)
2378         {
2379             sURL = aBkmk.GetURL();
2380         }
2381 
2382         switch( nAction )
2383         {
2384             case SW_PASTESDR_INSERT:
2385             {
2386                 SwTransferable::SetSelInShell( rSh, sal_False, pPt );
2387                 rSh.Insert( sURL, aEmptyStr, aGrf );
2388                 break;
2389             }
2390 
2391             case SW_PASTESDR_REPLACE:
2392             {
2393                 if( rSh.IsObjSelected() )
2394                 {
2395                     // #123922# for D&D on draw objects, do for now the same for
2396                     // SW_PASTESDR_REPLACE (D&D) as for SW_PASTESDR_SETATTR (D&D and
2397                     // CTRL+SHIFT). The code below replaces the draw object with
2398                     // a writer graphic; maybe this is an option later again if wanted
2399                     rSh.Paste( aGrf, sURL );
2400 
2401                     // rSh.ReplaceSdrObj( sURL, aEmptyStr, &aGrf );
2402                     // Point aPt( pPt ? *pPt : rSh.GetCrsrDocPos() );
2403                     // SwTransferable::SetSelInShell( rSh, sal_True, &aPt );
2404                 }
2405                 else
2406                 {
2407                     // set graphic at writer graphic without link
2408                     rSh.ReRead( sURL, aEmptyStr, &aGrf );
2409                 }
2410 
2411                 break;
2412             }
2413 
2414             case SW_PASTESDR_SETATTR:
2415             {
2416                 if( SOT_FORMATSTR_ID_NETSCAPE_BOOKMARK == nFmt )
2417                 {
2418                     if( rSh.IsFrmSelected() )
2419                     {
2420                         SfxItemSet aSet( rSh.GetAttrPool(), RES_URL, RES_URL );
2421                         rSh.GetFlyFrmAttr( aSet );
2422                         SwFmtURL aURL( (SwFmtURL&)aSet.Get( RES_URL ) );
2423                         aURL.SetURL( aBkmk.GetURL(), sal_False );
2424                         aSet.Put( aURL );
2425                         rSh.SetFlyFrmAttr( aSet );
2426                     }
2427                 }
2428                 else if( rSh.IsObjSelected() )
2429                 {
2430                     // set as attribute at DrawObject
2431                     rSh.Paste( aGrf, sURL );
2432                 }
2433                 else if( OBJCNT_GRF == rSh.GetObjCntTypeOfSelection() )
2434                 {
2435                     // set as linked graphic at writer graphic frame
2436                     rSh.ReRead( sURL, aEmptyStr, &aGrf );
2437                 }
2438                 else
2439                 {
2440                     SwTransferable::SetSelInShell( rSh, sal_False, pPt );
2441                     rSh.Insert( aBkmk.GetURL(), aEmptyStr, aGrf );
2442                 }
2443                 break;
2444             }
2445             default:
2446             {
2447                 nRet = 0;
2448                 break;
2449             }
2450         }
2451     }
2452 
2453 	if( nRet )
2454 	{
2455 
2456 		if( nActionFlags &
2457 			(( EXCHG_OUT_ACTION_FLAG_INSERT_IMAGEMAP |
2458 				EXCHG_OUT_ACTION_FLAG_REPLACE_IMAGEMAP ) >> 8) )
2459 			SwTransferable::_PasteImageMap( rData, rSh );
2460 
2461 		if( nActionFlags &
2462 			( EXCHG_OUT_ACTION_FLAG_INSERT_TARGETURL >> 8) )
2463 			SwTransferable::_PasteTargetURL( rData, rSh, 0, 0, sal_False );
2464 	}
2465 	else if( bCheckForImageMap )
2466 	{
2467 		// oder sollte das File ein ImageMap-File sein?
2468 		ImageMap aMap;
2469 		SfxMedium aMed( INetURLObject(aBkmk.GetURL()).GetFull(),
2470 							STREAM_STD_READ, sal_False );
2471         SvStream* pStream = aMed.GetInStream();
2472         if( pStream != NULL  &&
2473             !pStream->GetError()  &&
2474             // mba: no BaseURL for clipboard functionality
2475             aMap.Read( *pStream, IMAP_FORMAT_DETECT, String() ) == IMAP_ERR_OK &&
2476 			aMap.GetIMapObjectCount() )
2477 		{
2478 			SfxItemSet aSet( rSh.GetAttrPool(), RES_URL, RES_URL );
2479 			rSh.GetFlyFrmAttr( aSet );
2480 			SwFmtURL aURL( (SwFmtURL&)aSet.Get( RES_URL ) );
2481 			aURL.SetMap( &aMap );
2482 			aSet.Put( aURL );
2483 			rSh.SetFlyFrmAttr( aSet );
2484 			nRet = 1;
2485 		}
2486 	}
2487 
2488 	return nRet;
2489 }
2490 
2491 // -----------------------------------------------------------------------
2492 
_PasteImageMap(TransferableDataHelper & rData,SwWrtShell & rSh)2493 int SwTransferable::_PasteImageMap( TransferableDataHelper& rData,
2494 									SwWrtShell& rSh )
2495 {
2496 	int nRet = 0;
2497 	if( rData.HasFormat( SOT_FORMATSTR_ID_SVIM ))
2498 	{
2499 		SfxItemSet aSet( rSh.GetAttrPool(), RES_URL, RES_URL );
2500 		rSh.GetFlyFrmAttr( aSet );
2501 		SwFmtURL aURL( (SwFmtURL&)aSet.Get( RES_URL ) );
2502 		const ImageMap* pOld = aURL.GetMap();
2503 
2504 		// setzen oder ersetzen ist hier die Frage
2505 		ImageMap aImageMap;
2506 		if( rData.GetImageMap( SOT_FORMATSTR_ID_SVIM, aImageMap ) &&
2507 			( !pOld || aImageMap != *pOld ))
2508 		{
2509 			aURL.SetMap( &aImageMap );
2510 			aSet.Put( aURL );
2511 			rSh.SetFlyFrmAttr( aSet );
2512 		}
2513 		nRet = 1;
2514 	}
2515 	return nRet;
2516 }
2517 
2518 // -----------------------------------------------------------------------
2519 
_PasteAsHyperlink(TransferableDataHelper & rData,SwWrtShell & rSh,sal_uLong nFmt)2520 int SwTransferable::_PasteAsHyperlink( TransferableDataHelper& rData,
2521 										SwWrtShell& rSh, sal_uLong nFmt )
2522 {
2523 	int nRet = 0;
2524 	String sFile;
2525 	if( rData.GetString( nFmt, sFile ) && sFile.Len() )
2526 	{
2527 		String sDesc;
2528 		SwTransferable::_CheckForURLOrLNKFile( rData, sFile, &sDesc );
2529 
2530 		//#41801# ersteinmal die URL absolut machen
2531 		INetURLObject aURL;
2532 		aURL.SetSmartProtocol( INET_PROT_FILE );
2533 		aURL.SetSmartURL( sFile );
2534 		sFile = aURL.GetMainURL( INetURLObject::NO_DECODE );
2535 
2536 		switch( rSh.GetObjCntTypeOfSelection() )
2537 		{
2538 		case OBJCNT_FLY:
2539 		case OBJCNT_GRF:
2540 		case OBJCNT_OLE:
2541 			{
2542 				SfxItemSet aSet( rSh.GetAttrPool(), RES_URL, RES_URL );
2543 				rSh.GetFlyFrmAttr( aSet );
2544 				SwFmtURL aURL2( (SwFmtURL&)aSet.Get( RES_URL ) );
2545 				aURL2.SetURL( sFile, sal_False );
2546 				if( !aURL2.GetName().Len() )
2547 					aURL2.SetName( sFile );
2548 				aSet.Put( aURL2 );
2549 				rSh.SetFlyFrmAttr( aSet );
2550 			}
2551 			break;
2552 
2553 		default:
2554 			{
2555 				rSh.InsertURL( SwFmtINetFmt( sFile, aEmptyStr ),
2556 								sDesc.Len() ? sDesc : sFile );
2557 			}
2558 		}
2559 		nRet = sal_True;
2560 	}
2561 	return nRet;
2562 }
2563 
2564 // -----------------------------------------------------------------------
2565 
_PasteFileName(TransferableDataHelper & rData,SwWrtShell & rSh,sal_uLong nFmt,sal_uInt16 nAction,const Point * pPt,sal_uInt8 nActionFlags,sal_Bool)2566 int SwTransferable::_PasteFileName( TransferableDataHelper& rData,
2567 									SwWrtShell& rSh, sal_uLong nFmt,
2568 									sal_uInt16 nAction, const Point* pPt,
2569 									sal_uInt8 nActionFlags, sal_Bool /* bMsg */)
2570 {
2571 	int nRet = SwTransferable::_PasteGrf( rData, rSh, nFmt, nAction,
2572 											pPt, nActionFlags, 0, false);
2573     if( nRet )
2574         nRet |= SWTRANSFER_GRAPHIC_INSERTED;
2575     if( !nRet )
2576     {
2577         String sFile, sDesc;
2578         if( rData.GetString( nFmt, sFile ) && sFile.Len() )
2579         {
2580             INetURLObject aMediaURL;
2581 
2582             aMediaURL.SetSmartURL( sFile );
2583             const String aMediaURLStr( aMediaURL.GetMainURL( INetURLObject::NO_DECODE ) );
2584 
2585             if( ::avmedia::MediaWindow::isMediaURL( aMediaURLStr ) )
2586             {
2587                 const SfxStringItem aMediaURLItem( SID_INSERT_AVMEDIA, aMediaURLStr );
2588                 rSh.GetView().GetViewFrame()->GetDispatcher()->Execute(
2589                                 SID_INSERT_AVMEDIA, SFX_CALLMODE_SYNCHRON,
2590                                 &aMediaURLItem, 0L );
2591             }
2592             else
2593             {
2594                 sal_Bool bIsURLFile = SwTransferable::_CheckForURLOrLNKFile( rData, sFile, &sDesc );
2595 
2596                 //Eigenes FileFormat? -->Einfuegen, nicht fuer StarWriter/Web
2597                 String sFileURL = URIHelper::SmartRel2Abs(INetURLObject(), sFile, Link(), false );
2598                 const SfxFilter* pFlt = SW_PASTESDR_SETATTR == nAction
2599                         ? 0 : SwIoSystem::GetFileFilter(
2600                         sFileURL, aEmptyStr );
2601                 if( pFlt && !rSh.GetView().GetDocShell()->ISA(SwWebDocShell)
2602     /*
2603     JP 02.07.98: warum nur fuer die Formate ??
2604                     && ( pFlt->GetUserData() == FILTER_SW5 ||
2605                     pFlt->GetUserData() == FILTER_SW4 ||
2606                     pFlt->GetUserData() == FILTER_SW3 ||
2607                     pFlt->GetUserData() == FILTER_SWG )
2608     */
2609                     )
2610                 {
2611     // und dann per PostUser Event den Bereich-Einfuegen-Dialog hochreissen
2612                     SwSectionData * pSect = new SwSectionData(
2613                                     FILE_LINK_SECTION,
2614                                     rSh.GetDoc()->GetUniqueSectionName() );
2615                     pSect->SetLinkFileName( sFileURL );
2616                     pSect->SetProtectFlag( true );
2617 
2618                     Application::PostUserEvent( STATIC_LINK( &rSh, SwWrtShell,
2619                                                 InsertRegionDialog ), pSect );
2620                     nRet = 1;
2621                     }
2622                 else if( SW_PASTESDR_SETATTR == nAction ||
2623                         ( bIsURLFile && SW_PASTESDR_INSERT == nAction ))
2624                 {
2625                     //Fremde Files koennen wir immerhin noch als Links
2626                     //Einfuegen.
2627 
2628                     //#41801# ersteinmal die URL absolut machen
2629                     INetURLObject aURL;
2630                     aURL.SetSmartProtocol( INET_PROT_FILE );
2631                     aURL.SetSmartURL( sFile );
2632                     sFile = aURL.GetMainURL( INetURLObject::NO_DECODE );
2633 
2634                     switch( rSh.GetObjCntTypeOfSelection() )
2635                     {
2636                     case OBJCNT_FLY:
2637                     case OBJCNT_GRF:
2638                     case OBJCNT_OLE:
2639                         {
2640                             SfxItemSet aSet( rSh.GetAttrPool(), RES_URL, RES_URL );
2641                             rSh.GetFlyFrmAttr( aSet );
2642                             SwFmtURL aURL2( (SwFmtURL&)aSet.Get( RES_URL ) );
2643                             aURL2.SetURL( sFile, sal_False );
2644                             if( !aURL2.GetName().Len() )
2645                                 aURL2.SetName( sFile );
2646                             aSet.Put( aURL2 );
2647                             rSh.SetFlyFrmAttr( aSet );
2648                         }
2649                         break;
2650 
2651                     default:
2652                         {
2653                             rSh.InsertURL( SwFmtINetFmt( sFile, aEmptyStr ),
2654                                             sDesc.Len() ? sDesc : sFile );
2655                         }
2656                     }
2657                     nRet = sal_True;
2658                 }
2659             }
2660 		}
2661 	}
2662 	return nRet;
2663 }
2664 
2665 // -----------------------------------------------------------------------
2666 
_PasteDBData(TransferableDataHelper & rData,SwWrtShell & rSh,sal_uLong nFmt,sal_Bool bLink,const Point * pDragPt,sal_Bool bMsg)2667 int SwTransferable::_PasteDBData( TransferableDataHelper& rData,
2668 									SwWrtShell& rSh, sal_uLong nFmt, sal_Bool bLink,
2669 									const Point* pDragPt, sal_Bool bMsg )
2670 {
2671 	int nRet = 0;
2672 	String sTxt;
2673 	if( rData.GetString( nFmt, sTxt ) && sTxt.Len() )
2674 	{
2675 		sal_uInt16 nWh = SOT_FORMATSTR_ID_SBA_CTRLDATAEXCHANGE == nFmt
2676 					? 0
2677 					: SOT_FORMATSTR_ID_SBA_DATAEXCHANGE == nFmt
2678 								? (bLink
2679 									? FN_QRY_MERGE_FIELD
2680 									: FN_QRY_INSERT)
2681 								: (bLink
2682 									? 0
2683 									: FN_QRY_INSERT_FIELD );
2684         DataFlavorExVector& rVector = rData.GetDataFlavorExVector();
2685 		sal_Bool bHaveColumnDescriptor = OColumnTransferable::canExtractColumnDescriptor(rVector, CTF_COLUMN_DESCRIPTOR | CTF_CONTROL_EXCHANGE);
2686 		if ( SOT_FORMATSTR_ID_XFORMS == nFmt )
2687 		{
2688 			SdrObject* pObj;
2689 			rSh.MakeDrawView();
2690 			FmFormView* pFmView = PTR_CAST( FmFormView, rSh.GetDrawView() );
2691 			if(pFmView) {
2692 				const OXFormsDescriptor &rDesc = OXFormsTransferable::extractDescriptor(rData);
2693                 if(0 != (pObj = pFmView->CreateXFormsControl(rDesc)))
2694                 {
2695                     rSh.SwFEShell::InsertDrawObj( *pObj, *pDragPt );
2696                 }
2697 			}
2698 		}
2699 		else if( nWh )
2700 		{
2701             SfxUsrAnyItem* pConnectionItem	= 0;
2702 			SfxUsrAnyItem* pCursorItem		= 0;
2703             SfxUsrAnyItem* pColumnItem		= 0;
2704             SfxUsrAnyItem* pSourceItem		= 0;
2705             SfxUsrAnyItem* pCommandItem		= 0;
2706             SfxUsrAnyItem* pCommandTypeItem = 0;
2707             SfxUsrAnyItem* pColumnNameItem	= 0;
2708             SfxUsrAnyItem* pSelectionItem	= 0;
2709 
2710             sal_Bool bDataAvailable = sal_True;
2711 	        ODataAccessDescriptor aDesc;
2712             if(bHaveColumnDescriptor)
2713                 aDesc = OColumnTransferable::extractColumnDescriptor(rData);
2714             else if(ODataAccessObjectTransferable::canExtractObjectDescriptor(rVector) )
2715                 aDesc = ODataAccessObjectTransferable::extractObjectDescriptor(rData);
2716             else
2717                 bDataAvailable = sal_False;
2718 
2719             if ( bDataAvailable )
2720             {
2721                 pConnectionItem = new SfxUsrAnyItem(FN_DB_CONNECTION_ANY, aDesc[daConnection]);
2722                 pColumnItem = new SfxUsrAnyItem(FN_DB_COLUMN_ANY, aDesc[daColumnObject]);
2723                 pSourceItem = new SfxUsrAnyItem(FN_DB_DATA_SOURCE_ANY, makeAny(aDesc.getDataSource()));
2724                 pCommandItem = new SfxUsrAnyItem(FN_DB_DATA_COMMAND_ANY, aDesc[daCommand]);
2725                 pCommandTypeItem = new SfxUsrAnyItem(FN_DB_DATA_COMMAND_TYPE_ANY, aDesc[daCommandType]);
2726                 pColumnNameItem = new SfxUsrAnyItem(FN_DB_DATA_COLUMN_NAME_ANY, aDesc[daColumnName]);
2727                 pSelectionItem = new SfxUsrAnyItem(FN_DB_DATA_SELECTION_ANY, aDesc[daSelection]);
2728 				pCursorItem = new SfxUsrAnyItem(FN_DB_DATA_CURSOR_ANY, aDesc[daCursor]);
2729             }
2730 
2731             SwView& rView = rSh.GetView();
2732 			//force ::SelectShell
2733 			rView.StopShellTimer();
2734 
2735 			SfxStringItem aDataDesc( nWh, sTxt );
2736 			rView.GetViewFrame()->GetDispatcher()->Execute(
2737                                 nWh, SFX_CALLMODE_ASYNCHRON, &aDataDesc,
2738                                 pConnectionItem, pColumnItem,
2739                                 pSourceItem, pCommandItem, pCommandTypeItem,
2740                                 pColumnNameItem, pSelectionItem, pCursorItem,0L);
2741             delete pConnectionItem;
2742             delete pColumnItem;
2743             delete pSourceItem;
2744             delete pCommandItem;
2745             delete pCommandTypeItem;
2746             delete pColumnNameItem;
2747             delete pSelectionItem;
2748             delete pCursorItem;
2749 		}
2750 		else
2751 		{
2752 			SdrObject* pObj;
2753 			rSh.MakeDrawView();
2754 			FmFormView* pFmView = PTR_CAST( FmFormView, rSh.GetDrawView() );
2755 			if (pFmView && bHaveColumnDescriptor)
2756 			{
2757 				if ( 0 != (pObj = pFmView->CreateFieldControl( OColumnTransferable::extractColumnDescriptor(rData) ) ) )
2758                     rSh.SwFEShell::InsertDrawObj( *pObj, *pDragPt );
2759 			}
2760 		}
2761 		nRet = 1;
2762 	}
2763 	else if( bMsg )
2764 	{
2765 		InfoBox( 0, SW_RES(MSG_CLPBRD_FORMAT_ERROR)).Execute();
2766 	}
2767 	return nRet;
2768 }
2769 
2770 // -----------------------------------------------------------------------
2771 
_PasteFileList(TransferableDataHelper & rData,SwWrtShell & rSh,sal_Bool bLink,const Point * pPt,sal_Bool bMsg)2772 int SwTransferable::_PasteFileList( TransferableDataHelper& rData,
2773 									SwWrtShell& rSh, sal_Bool bLink,
2774 									const Point* pPt, sal_Bool bMsg )
2775 {
2776 	int nRet = 0;
2777 	FileList aFileList;
2778 	if( rData.GetFileList( SOT_FORMAT_FILE_LIST, aFileList ) &&
2779 		aFileList.Count() )
2780 	{
2781 		sal_uInt16 nAct = bLink ? SW_PASTESDR_SETATTR : SW_PASTESDR_INSERT;
2782 		String sFlyNm;
2783 		// iterate over the filelist
2784 		for( sal_uLong n = 0, nEnd = aFileList.Count(); n < nEnd; ++n )
2785 		{
2786 			TransferDataContainer* pHlp = new TransferDataContainer;
2787 			pHlp->CopyString( FORMAT_FILE, aFileList.GetFile( n ));
2788 			TransferableDataHelper aData( pHlp );
2789 
2790             if( SwTransferable::_PasteFileName( aData, rSh, SOT_FORMAT_FILE, nAct,
2791 											pPt, sal_False, bMsg ))
2792 			{
2793 				if( bLink )
2794 				{
2795 					sFlyNm = rSh.GetFlyName();
2796 					SwTransferable::SetSelInShell( rSh, sal_False, pPt );
2797 				}
2798 				nRet = 1;
2799 			}
2800 		}
2801 		if( sFlyNm.Len() )
2802 			rSh.GotoFly( sFlyNm );
2803 	}
2804 	else if( bMsg )
2805 	{
2806 		InfoBox( 0, SW_RES(MSG_CLPBRD_FORMAT_ERROR)).Execute();
2807 	}
2808 	return nRet;
2809 }
2810 
2811 // -----------------------------------------------------------------------
2812 
_CheckForURLOrLNKFile(TransferableDataHelper & rData,String & rFileName,String * pTitle)2813 sal_Bool SwTransferable::_CheckForURLOrLNKFile( TransferableDataHelper& rData,
2814 										String& rFileName, String* pTitle )
2815 {
2816 	sal_Bool bIsURLFile = sal_False;
2817 	INetBookmark aBkmk;
2818 	if( rData.GetINetBookmark( SOT_FORMATSTR_ID_SOLK, aBkmk ) )
2819 	{
2820 		rFileName = aBkmk.GetURL();
2821 		if( pTitle )
2822 			*pTitle = aBkmk.GetDescription();
2823 		bIsURLFile = sal_True;
2824 	}
2825 	else
2826 	{
2827 		xub_StrLen nLen = rFileName.Len();
2828 		if( 4 < nLen && '.' == rFileName.GetChar( nLen - 4 ))
2829 		{
2830 			String sExt( rFileName.Copy( nLen - 3 ));
2831 			if( sExt.EqualsIgnoreCaseAscii( "url" ))
2832 			{
2833 ASSERT( !&rFileName, "how do we read today .URL - Files?" );
2834 			}
2835 		}
2836 	}
2837 	return bIsURLFile;
2838 }
2839 
2840 // -----------------------------------------------------------------------
2841 
IsPasteSpecial(const SwWrtShell & rWrtShell,const TransferableDataHelper & rData)2842 sal_Bool SwTransferable::IsPasteSpecial( const SwWrtShell& rWrtShell,
2843 									 const TransferableDataHelper& rData )
2844 {
2845     // we can paste-special if there's an entry in the paste-special-format list
2846     SvxClipboardFmtItem aClipboardFmtItem(0);
2847     FillClipFmtItem( rWrtShell, rData, aClipboardFmtItem);
2848     return aClipboardFmtItem.Count() > 0;
2849 }
2850 
2851 // -----------------------------------------------------------------------
2852 
PasteFormat(SwWrtShell & rSh,TransferableDataHelper & rData,sal_uLong nFormat)2853 int SwTransferable::PasteFormat( SwWrtShell& rSh,
2854 									TransferableDataHelper& rData,
2855 									sal_uLong nFormat )
2856 {
2857 	SwWait aWait( *rSh.GetView().GetDocShell(), false );
2858 	int nRet = 0;
2859 
2860 	sal_uLong nPrivateFmt = FORMAT_PRIVATE;
2861 	SwTransferable *pClipboard = GetSwTransferable( rData );
2862 	if( pClipboard &&
2863 		((TRNSFR_DOCUMENT|TRNSFR_GRAPHIC|TRNSFR_OLE) & pClipboard->eBufferType ))
2864 		nPrivateFmt = SOT_FORMATSTR_ID_EMBED_SOURCE;
2865 
2866 	if( pClipboard && nPrivateFmt == nFormat )
2867 		nRet = pClipboard->PrivatePaste( rSh );
2868 	else if( rData.HasFormat( nFormat ) )
2869 	{
2870         uno::Reference<XTransferable> xTransferable( rData.GetXTransferable() );
2871 		sal_uInt16 nEventAction,
2872 			   nDestination = SwTransferable::GetSotDestination( rSh ),
2873 			   nSourceOptions =
2874 					(( EXCHG_DEST_DOC_TEXTFRAME == nDestination ||
2875 					   EXCHG_DEST_SWDOC_FREE_AREA == nDestination ||
2876 					   EXCHG_DEST_DOC_TEXTFRAME_WEB == nDestination ||
2877 					   EXCHG_DEST_SWDOC_FREE_AREA_WEB == nDestination )
2878 										? EXCHG_IN_ACTION_COPY
2879 										: EXCHG_IN_ACTION_MOVE),
2880 			   nAction = SotExchange::GetExchangeAction(
2881 									rData.GetDataFlavorExVector(),
2882 									nDestination,
2883 									nSourceOptions,  			/* ?? */
2884 									EXCHG_IN_ACTION_DEFAULT,    /* ?? */
2885 									nFormat, nEventAction, nFormat,
2886 									lcl_getTransferPointer ( xTransferable ) );
2887 
2888 		if( EXCHG_INOUT_ACTION_NONE != nAction )
2889 			nRet = SwTransferable::PasteData( rData, rSh, nAction, nFormat,
2890                                                 nDestination, sal_True, sal_False );
2891 	}
2892 	return nRet;
2893 }
2894 
2895 // -----------------------------------------------------------------------
2896 
_TestAllowedFormat(const TransferableDataHelper & rData,sal_uLong nFormat,sal_uInt16 nDestination)2897 int SwTransferable::_TestAllowedFormat( const TransferableDataHelper& rData,
2898 										sal_uLong nFormat, sal_uInt16 nDestination )
2899 {
2900 	sal_uInt16 nAction = EXCHG_INOUT_ACTION_NONE, nEventAction;
2901 	if( rData.HasFormat( nFormat )) {
2902         uno::Reference<XTransferable> xTransferable( rData.GetXTransferable() );
2903 		nAction = SotExchange::GetExchangeAction(
2904 						rData.GetDataFlavorExVector(),
2905 						nDestination, EXCHG_IN_ACTION_COPY,
2906 						EXCHG_IN_ACTION_COPY, nFormat,
2907 						nEventAction, nFormat,
2908 						lcl_getTransferPointer ( xTransferable ) );
2909     }
2910 	return EXCHG_INOUT_ACTION_NONE != nAction;
2911 }
2912 
2913 // -----------------------------------------------------------------------
2914 
2915 /**
2916  * the list of formats which will be offered to the user in the 'Paste
2917  * Special...' dialog and the paste button menu
2918  */
2919 static sal_uInt16 aPasteSpecialIds[] =
2920 {
2921     SOT_FORMATSTR_ID_HTML,
2922     SOT_FORMATSTR_ID_HTML_SIMPLE,
2923     SOT_FORMATSTR_ID_HTML_NO_COMMENT,
2924     FORMAT_RTF,
2925     FORMAT_STRING,
2926     SOT_FORMATSTR_ID_SONLK,
2927     SOT_FORMATSTR_ID_NETSCAPE_BOOKMARK,
2928     SOT_FORMATSTR_ID_DRAWING,
2929     SOT_FORMATSTR_ID_SVXB,
2930     FORMAT_GDIMETAFILE,
2931     FORMAT_BITMAP,
2932     SOT_FORMATSTR_ID_SVIM,
2933     SOT_FORMATSTR_ID_FILEGRPDESCRIPTOR,
2934     0
2935 };
2936 
2937 
PasteUnformatted(SwWrtShell & rSh,TransferableDataHelper & rData)2938 int SwTransferable::PasteUnformatted( SwWrtShell& rSh, TransferableDataHelper& rData )
2939 {
2940     // Plain text == unformatted
2941 	return SwTransferable::PasteFormat( rSh, rData, SOT_FORMAT_STRING );
2942 }
2943 
2944 // -----------------------------------------------------------------------
2945 
PasteSpecial(SwWrtShell & rSh,TransferableDataHelper & rData,sal_uLong & rFormatUsed)2946 int SwTransferable::PasteSpecial( SwWrtShell& rSh, TransferableDataHelper& rData, sal_uLong& rFormatUsed )
2947 {
2948 	int nRet = 0;
2949     SvxAbstractDialogFactory* pFact = SvxAbstractDialogFactory::Create();
2950     SfxAbstractPasteDialog* pDlg = pFact->CreatePasteDialog( &rSh.GetView().GetEditWin() );
2951 
2952 	DataFlavorExVector aFormats( rData.GetDataFlavorExVector() );
2953 	TransferableObjectDescriptor aDesc;
2954 
2955 	sal_uInt16 nDest = SwTransferable::GetSotDestination( rSh );
2956 
2957 	SwTransferable *pClipboard = GetSwTransferable( rData );
2958 	if( pClipboard )
2959 	{
2960 		aDesc = pClipboard->aObjDesc;
2961 		sal_uInt16 nResId;
2962 		if( pClipboard->eBufferType & TRNSFR_DOCUMENT )
2963 			nResId = STR_PRIVATETEXT;
2964 		else if( pClipboard->eBufferType & TRNSFR_GRAPHIC )
2965 			nResId = STR_PRIVATEGRAPHIC;
2966 		else if( pClipboard->eBufferType == TRNSFR_OLE )
2967 			nResId = STR_PRIVATEOLE;
2968 		else
2969 			nResId = 0;
2970 
2971 		if( nResId )
2972 		{
2973 			if( STR_PRIVATEOLE == nResId || STR_PRIVATEGRAPHIC == nResId )
2974 			{
2975 				// add SOT_FORMATSTR_ID_EMBED_SOURCE to the formats. This
2976 				// format display then the private format name.
2977 				DataFlavorEx aFlavorEx;
2978 				aFlavorEx.mnSotId = SOT_FORMATSTR_ID_EMBED_SOURCE;
2979 				aFormats.insert( aFormats.begin(), aFlavorEx );
2980 			}
2981 			pDlg->SetObjName( pClipboard->aObjDesc.maClassName,
2982 								SW_RES( nResId ) );
2983 			pDlg->Insert( SOT_FORMATSTR_ID_EMBED_SOURCE, aEmptyStr );
2984 		}
2985 	}
2986 	else
2987 	{
2988 		if( rData.HasFormat( SOT_FORMATSTR_ID_OBJECTDESCRIPTOR ) )
2989 			rData.GetTransferableObjectDescriptor(
2990 								SOT_FORMATSTR_ID_OBJECTDESCRIPTOR, aDesc );
2991 
2992 		if( SwTransferable::_TestAllowedFormat( rData, SOT_FORMATSTR_ID_EMBED_SOURCE, nDest ))
2993 			pDlg->Insert( SOT_FORMATSTR_ID_EMBED_SOURCE, aEmptyStr );
2994 		if( SwTransferable::_TestAllowedFormat( rData, SOT_FORMATSTR_ID_LINK_SOURCE, nDest ))
2995 			pDlg->Insert( SOT_FORMATSTR_ID_LINK_SOURCE, aEmptyStr );
2996 	}
2997 
2998 	if( SwTransferable::_TestAllowedFormat( rData, SOT_FORMATSTR_ID_LINK, nDest ))
2999 		pDlg->Insert( SOT_FORMATSTR_ID_LINK, SW_RES(STR_DDEFORMAT) );
3000 
3001 	for( sal_uInt16* pIds = aPasteSpecialIds; *pIds; ++pIds )
3002 		if( SwTransferable::_TestAllowedFormat( rData, *pIds, nDest ))
3003 			pDlg->Insert( *pIds, aEmptyStr );
3004 
3005     sal_uLong nFormat = pDlg->GetFormat( rData.GetTransferable() );
3006 
3007 	if( nFormat )
3008 		nRet = SwTransferable::PasteFormat( rSh, rData, nFormat );
3009 
3010     if ( nRet )
3011         rFormatUsed = nFormat;
3012 
3013     delete pDlg;
3014 	return nRet;
3015 }
3016 
3017 
FillClipFmtItem(const SwWrtShell & rSh,const TransferableDataHelper & rData,SvxClipboardFmtItem & rToFill)3018 void SwTransferable::FillClipFmtItem( const SwWrtShell& rSh,
3019 								const TransferableDataHelper& rData,
3020 								SvxClipboardFmtItem & rToFill )
3021 {
3022 	sal_uInt16 nDest = SwTransferable::GetSotDestination( rSh );
3023 
3024 	SwTransferable *pClipboard = GetSwTransferable( rData );
3025 	if( pClipboard )
3026 	{
3027 		sal_uInt16 nResId;
3028 		if( pClipboard->eBufferType & TRNSFR_DOCUMENT )
3029 			nResId = STR_PRIVATETEXT;
3030 		else if( pClipboard->eBufferType & TRNSFR_GRAPHIC )
3031 			nResId = STR_PRIVATEGRAPHIC;
3032 		else if( pClipboard->eBufferType == TRNSFR_OLE )
3033 			nResId = STR_PRIVATEOLE;
3034 		else
3035 			nResId = 0;
3036 
3037 		if( nResId )
3038 			rToFill.AddClipbrdFormat( SOT_FORMATSTR_ID_EMBED_SOURCE,
3039 										SW_RES( nResId ) );
3040 	}
3041 	else
3042 	{
3043 		TransferableObjectDescriptor aDesc;
3044 		if( rData.HasFormat( SOT_FORMATSTR_ID_OBJECTDESCRIPTOR ) )
3045 			((TransferableDataHelper&)rData).GetTransferableObjectDescriptor(
3046 								SOT_FORMATSTR_ID_OBJECTDESCRIPTOR, aDesc );
3047 
3048 		if( SwTransferable::_TestAllowedFormat( rData, SOT_FORMATSTR_ID_EMBED_SOURCE, nDest ))
3049 			rToFill.AddClipbrdFormat( SOT_FORMATSTR_ID_EMBED_SOURCE,
3050 											aDesc.maTypeName );
3051 		if( SwTransferable::_TestAllowedFormat( rData, SOT_FORMATSTR_ID_LINK_SOURCE, nDest ))
3052 			rToFill.AddClipbrdFormat( SOT_FORMATSTR_ID_LINK_SOURCE );
3053 
3054 		SotFormatStringId nFormat;
3055 		if ( rData.HasFormat(nFormat = SOT_FORMATSTR_ID_EMBED_SOURCE_OLE) || rData.HasFormat(nFormat = SOT_FORMATSTR_ID_EMBEDDED_OBJ_OLE) )
3056 		{
3057 			String sName,sSource;
3058             if ( SvPasteObjectHelper::GetEmbeddedName(rData,sName,sSource,nFormat) )
3059 				rToFill.AddClipbrdFormat( nFormat, sName );
3060 		}
3061 	}
3062 
3063 	if( SwTransferable::_TestAllowedFormat( rData, SOT_FORMATSTR_ID_LINK, nDest ))
3064 		rToFill.AddClipbrdFormat( SOT_FORMATSTR_ID_LINK, SW_RES(STR_DDEFORMAT) );
3065 
3066 	for( sal_uInt16* pIds = aPasteSpecialIds; *pIds; ++pIds )
3067 		if( SwTransferable::_TestAllowedFormat( rData, *pIds, nDest ))
3068 			rToFill.AddClipbrdFormat( *pIds, aEmptyStr );
3069 }
3070 
SetDataForDragAndDrop(const Point & rSttPos)3071 void SwTransferable::SetDataForDragAndDrop( const Point& rSttPos )
3072 {
3073     if(!pWrtShell)
3074         return;
3075     String sGrfNm;
3076 	const int nSelection = pWrtShell->GetSelectionType();
3077 	if( nsSelectionType::SEL_GRF == nSelection)
3078 	{
3079 		AddFormat( SOT_FORMATSTR_ID_SVXB );
3080         // --> OD 2005-02-09 #119353# - robust
3081         const Graphic* pGrf = pWrtShell->GetGraphic();
3082         if ( pGrf && pGrf->IsSupportedGraphic() )
3083         // <--
3084 		{
3085 			AddFormat( FORMAT_GDIMETAFILE );
3086             AddFormat( SOT_FORMATSTR_ID_PNG );
3087 			AddFormat( FORMAT_BITMAP );
3088 		}
3089 		eBufferType = TRNSFR_GRAPHIC;
3090 		pWrtShell->GetGrfNms( &sGrfNm, 0 );
3091 	}
3092 	else if( nsSelectionType::SEL_OLE == nSelection )
3093 	{
3094 		AddFormat( SOT_FORMATSTR_ID_EMBED_SOURCE );
3095         PrepareOLE( aObjDesc );
3096 		AddFormat( SOT_FORMATSTR_ID_OBJECTDESCRIPTOR );
3097 		AddFormat( FORMAT_GDIMETAFILE );
3098 		eBufferType = TRNSFR_OLE;
3099 	}
3100 	//Gibt es ueberhaupt etwas zum bereitstellen?
3101 	else if ( pWrtShell->IsSelection() || pWrtShell->IsFrmSelected() ||
3102 			  pWrtShell->IsObjSelected() )
3103 	{
3104 		if( pWrtShell->IsObjSelected() )
3105 			eBufferType = TRNSFR_DRAWING;
3106 		else
3107 		{
3108 			eBufferType = TRNSFR_DOCUMENT;
3109 			if( SwWrtShell::NO_WORD !=
3110 				pWrtShell->IntelligentCut( nSelection, sal_False ))
3111 				eBufferType = TransferBufferType( TRNSFR_DOCUMENT_WORD
3112 													| eBufferType);
3113 		}
3114 
3115 		if( nSelection & nsSelectionType::SEL_TBL_CELLS )
3116 			eBufferType = (TransferBufferType)(TRNSFR_TABELLE | eBufferType);
3117 
3118 		AddFormat( SOT_FORMATSTR_ID_EMBED_SOURCE );
3119 
3120 		//RTF vor das Metafile von OLE stellen, weil mit weniger verlusten
3121 		//behaftet.
3122 		if( !pWrtShell->IsObjSelected() )
3123 		{
3124 			AddFormat( FORMAT_RTF );
3125 			AddFormat( SOT_FORMATSTR_ID_HTML );
3126 		}
3127 		if( pWrtShell->IsSelection() )
3128 			AddFormat( FORMAT_STRING );
3129 
3130 		if( nSelection & ( nsSelectionType::SEL_DRW | nsSelectionType::SEL_DRW_FORM ))
3131 		{
3132 			AddFormat( SOT_FORMATSTR_ID_DRAWING );
3133 			if ( nSelection & nsSelectionType::SEL_DRW )
3134 			{
3135 				AddFormat( FORMAT_GDIMETAFILE );
3136                 AddFormat( SOT_FORMATSTR_ID_PNG );
3137 				AddFormat( FORMAT_BITMAP );
3138 			}
3139 			eBufferType = (TransferBufferType)( TRNSFR_GRAPHIC | eBufferType );
3140 
3141 			pClpGraphic = new Graphic;
3142 			if( !pWrtShell->GetDrawObjGraphic( FORMAT_GDIMETAFILE, *pClpGraphic ))
3143 				pOrigGrf = pClpGraphic;
3144 			pClpBitmap = new Graphic;
3145 			if( !pWrtShell->GetDrawObjGraphic( FORMAT_BITMAP, *pClpBitmap ))
3146 				pOrigGrf = pClpBitmap;
3147 
3148 			// ist es ein URL-Button ?
3149 			String sURL, sDesc;
3150 			if( pWrtShell->GetURLFromButton( sURL, sDesc ) )
3151 			{
3152 				AddFormat( FORMAT_STRING );
3153  				AddFormat( SOT_FORMATSTR_ID_SOLK );
3154  				AddFormat( SOT_FORMATSTR_ID_NETSCAPE_BOOKMARK );
3155  				AddFormat( SOT_FORMATSTR_ID_FILECONTENT );
3156  				AddFormat( SOT_FORMATSTR_ID_FILEGRPDESCRIPTOR );
3157  				AddFormat( SOT_FORMATSTR_ID_UNIFORMRESOURCELOCATOR );
3158 				eBufferType = (TransferBufferType)( TRNSFR_INETFLD | eBufferType );
3159 			}
3160 		}
3161 
3162 		//ObjectDescriptor wurde bereits aus der alten DocShell gefuellt.
3163 		//Jetzt noch anpassen. Dadurch kann im GetData die erste Anfrage
3164 		//auch noch mit delayed rendering beantwortet werden.
3165 		aObjDesc.mbCanLink = sal_False;
3166 		aObjDesc.maDragStartPos = rSttPos;
3167 		aObjDesc.maSize = OutputDevice::LogicToLogic( Size( OLESIZE ),
3168 												MAP_TWIP, MAP_100TH_MM );
3169         PrepareOLE( aObjDesc );
3170         AddFormat( SOT_FORMATSTR_ID_OBJECTDESCRIPTOR );
3171 	}
3172 	else if( nSelection & nsSelectionType::SEL_TXT && !pWrtShell->HasMark() )
3173 	{
3174 		// ist nur ein Feld - Selektiert?
3175 		SwContentAtPos aCntntAtPos( SwContentAtPos::SW_INETATTR );
3176 		Point aPos( SwEditWin::GetDDStartPosX(), SwEditWin::GetDDStartPosY());
3177 
3178 		if( pWrtShell->GetContentAtPos( aPos, aCntntAtPos ) )
3179 		{
3180 			AddFormat( FORMAT_STRING );
3181  			AddFormat( SOT_FORMATSTR_ID_SOLK );
3182  			AddFormat( SOT_FORMATSTR_ID_NETSCAPE_BOOKMARK );
3183  			AddFormat( SOT_FORMATSTR_ID_FILECONTENT );
3184  			AddFormat( SOT_FORMATSTR_ID_FILEGRPDESCRIPTOR );
3185  			AddFormat( SOT_FORMATSTR_ID_UNIFORMRESOURCELOCATOR );
3186 			eBufferType = TRNSFR_INETFLD;
3187 		}
3188 	}
3189 
3190 	if( pWrtShell->IsFrmSelected() )
3191 	{
3192 		SfxItemSet aSet( pWrtShell->GetAttrPool(), RES_URL, RES_URL );
3193 		pWrtShell->GetFlyFrmAttr( aSet );
3194 		const SwFmtURL& rURL = (SwFmtURL&)aSet.Get( RES_URL );
3195 		if( rURL.GetMap() )
3196 		{
3197 			pImageMap = new ImageMap( *rURL.GetMap() );
3198 			AddFormat( SOT_FORMATSTR_ID_SVIM );
3199 		}
3200 		else if( rURL.GetURL().Len() )
3201 		{
3202 			pTargetURL = new INetImage( sGrfNm, rURL.GetURL(),
3203 										rURL.GetTargetFrameName(),
3204 										aEmptyStr, Size() );
3205 			AddFormat( SOT_FORMATSTR_ID_INET_IMAGE );
3206 		}
3207 	}
3208 }
3209 
StartDrag(Window * pWin,const Point & rPos)3210 void SwTransferable::StartDrag( Window* pWin, const Point& rPos )
3211 {
3212     if(!pWrtShell)
3213         return;
3214     bOldIdle = pWrtShell->GetViewOptions()->IsIdle();
3215 	bCleanUp = sal_True;
3216 
3217 	((SwViewOption *)pWrtShell->GetViewOptions())->SetIdle( sal_False );
3218 
3219 	if( pWrtShell->IsSelFrmMode() )
3220 		pWrtShell->ShowCrsr();
3221 
3222     SW_MOD()->pDragDrop = this;
3223 
3224 	SetDataForDragAndDrop( rPos );
3225 
3226 	sal_Int8 nDragOptions = DND_ACTION_COPYMOVE | DND_ACTION_LINK;
3227 	SwDocShell* pDShell = pWrtShell->GetView().GetDocShell();
3228 	if( ( pDShell && pDShell->IsReadOnly() ) || pWrtShell->HasReadonlySel() )
3229 		nDragOptions &= ~DND_ACTION_MOVE;
3230 
3231 	TransferableHelper::StartDrag( pWin, nDragOptions );
3232 }
3233 
DragFinished(sal_Int8 nAction)3234 void SwTransferable::DragFinished( sal_Int8 nAction )
3235 {
3236 	//Und noch die letzten Nacharbeiten damit alle Stati stimmen.
3237 	if( DND_ACTION_MOVE == nAction	)
3238 	{
3239 		if( bCleanUp )
3240 		{
3241 			//Es wurde auserhalb des Writers gedroped. Wir muessen noch
3242 			//loeschen.
3243 
3244 			pWrtShell->StartAllAction();
3245             pWrtShell->StartUndo( UNDO_UI_DRAG_AND_MOVE );
3246 			if ( pWrtShell->IsTableMode() )
3247 				pWrtShell->DeleteTblSel();
3248 			else
3249 			{
3250 				if ( !(pWrtShell->IsSelFrmMode() || pWrtShell->IsObjSelected()) )
3251 					//SmartCut, eines der Blanks mitnehmen.
3252 					pWrtShell->IntelligentCut( pWrtShell->GetSelectionType(), sal_True );
3253 				pWrtShell->DelRight();
3254 			}
3255             pWrtShell->EndUndo( UNDO_UI_DRAG_AND_MOVE );
3256 			pWrtShell->EndAllAction();
3257 		}
3258 		else
3259 		{
3260 			const int nSelection = pWrtShell->GetSelectionType();
3261 			if( ( nsSelectionType::SEL_FRM | nsSelectionType::SEL_GRF |
3262 				 nsSelectionType::SEL_OLE | nsSelectionType::SEL_DRW ) & nSelection )
3263 			{
3264 				pWrtShell->EnterSelFrmMode();
3265 			}
3266 		}
3267 	}
3268 	pWrtShell->GetView().GetEditWin().DragFinished();
3269 
3270 	if( pWrtShell->IsSelFrmMode() )
3271 		pWrtShell->HideCrsr();
3272 	else
3273 		pWrtShell->ShowCrsr();
3274 //!!	else if( DND_ACTION_NONE != nAction )
3275 //!!		pWrtShell->ShowCrsr();
3276 //!!	else
3277 //!!	{
3278 //!!		//Muss wohl sein weil gescrollt wurde und ?...?
3279 //!!		pWrtShell->StartAction();
3280 //!!		pWrtShell->EndAction();
3281 //!!	}
3282 
3283 	((SwViewOption *)pWrtShell->GetViewOptions())->SetIdle( bOldIdle );
3284 }
3285 
3286 
3287 /*  */
3288 
PrivatePaste(SwWrtShell & rShell)3289 int SwTransferable::PrivatePaste( SwWrtShell& rShell )
3290 {
3291 	// erst den SelectionType erfragen, dann Action-Klammerung !!!!
3292 	// (sonst wird nicht in eine TabellenSelektion gepastet!!!)
3293 	ASSERT( !rShell.ActionPend(), "Paste darf nie eine Actionklammerung haben" );
3294 	if ( !pClpDocFac )
3295 		return sal_False; // the return value of the SwFEShell::Paste also is sal_Bool!
3296 
3297 	const int nSelection = rShell.GetSelectionType();
3298 
3299     // #111827#
3300     SwRewriter aRewriter;
3301 
3302     SwTrnsfrActionAndUndo aAction( &rShell, UNDO_PASTE_CLIPBOARD);
3303 
3304     bool bKillPaMs = false;
3305 
3306 	//Selektierten Inhalt loeschen, nicht bei Tabellen-Selektion und
3307 	//Tabelle im Clipboard
3308 	if( rShell.HasSelection() && !( nSelection & nsSelectionType::SEL_TBL_CELLS))
3309 	{
3310         bKillPaMs = true;
3311         rShell.SetRetainSelection( true );
3312 		rShell.DelRight();
3313 		// war ein Fly selektiert, so muss jetzt fuer eine gueltige
3314 		// Cursor-Position gesorgt werden! (geparkter Cursor!)
3315 		if( ( nsSelectionType::SEL_FRM | nsSelectionType::SEL_GRF |
3316 			nsSelectionType::SEL_OLE | nsSelectionType::SEL_DRW |
3317 			nsSelectionType::SEL_DRW_FORM ) & nSelection )
3318 		{
3319 			// den Cursor wieder positionieren
3320 			Point aPt( rShell.GetCharRect().Pos() );
3321 			rShell.SwCrsrShell::SetCrsr( aPt, sal_True );
3322 		}
3323         rShell.SetRetainSelection( false );
3324 	}
3325 
3326     sal_Bool bInWrd = sal_False, bEndWrd = sal_False, bSttWrd = sal_False,
3327          bSmart = 0 != (TRNSFR_DOCUMENT_WORD & eBufferType);
3328 	if( bSmart )
3329 	{
3330 // #108491# Why not for other Scripts? If TRNSFR_DOCUMENT_WORD is set, we have
3331 // a word in the buffer, word in this context means 'something with spaces at
3332 // beginning and end'. In this case we definitely want these spaces to be inserted
3333 // here.
3334 //      if( SCRIPTTYPE_LATIN != rShell.GetScriptType() )
3335 //          bSmart = sal_False;
3336 //      else
3337 //      {
3338 			bInWrd = rShell.IsInWrd();
3339 		 	bEndWrd = rShell.IsEndWrd();
3340 			bSmart = bInWrd || bEndWrd;
3341 			if( bSmart )
3342 			{
3343 		 		bSttWrd = rShell.IsSttWrd();
3344 				if( bSmart && !bSttWrd && (bInWrd || bEndWrd) )
3345 					rShell.SwEditShell::Insert(' ');
3346 			}
3347 //      }
3348 	}
3349 
3350 	int nRet = rShell.Paste( pClpDocFac->GetDoc() );
3351 
3352     if( bKillPaMs )
3353         rShell.KillPams();
3354 
3355 	// Wenn Smart Paste dann Leerzeichen einfuegen
3356 	if( nRet && bSmart && ((bInWrd && !bEndWrd )|| bSttWrd) )
3357 		rShell.SwEditShell::Insert(' ');
3358 
3359 	return nRet;
3360 }
3361 
PrivateDrop(SwWrtShell & rSh,const Point & rDragPt,sal_Bool bMove,sal_Bool bIsXSelection)3362 int SwTransferable::PrivateDrop( SwWrtShell& rSh, const Point& rDragPt,
3363 								sal_Bool bMove, sal_Bool bIsXSelection )
3364 {
3365 	int cWord	 = 0;
3366 	sal_Bool bInWrd  = sal_False;
3367 	sal_Bool bEndWrd = sal_False;
3368 	sal_Bool bSttWrd = sal_False;
3369 	sal_Bool bSttPara= sal_False;
3370 	sal_Bool bTblSel = sal_False;
3371 	sal_Bool bFrmSel = sal_False;
3372 
3373 	SwWrtShell& rSrcSh = *GetShell();
3374 
3375 	rSh.UnSetVisCrsr();
3376 
3377 	if( TRNSFR_INETFLD == eBufferType )
3378 	{
3379 		if( rSh.GetFmtFromObj( rDragPt ) )
3380 		{
3381 			INetBookmark aTmp;
3382 			if( (TRNSFR_INETFLD & eBufferType) && pBkmk )
3383 				aTmp = *pBkmk;
3384 
3385 			// Zielgrafik selektieren
3386 			if( rSh.SelectObj( rDragPt ) )
3387 			{
3388 				rSh.HideCrsr();
3389 				rSh.EnterSelFrmMode( &rDragPt );
3390 				bFrmDrag = sal_True;
3391 			}
3392 
3393 			const int nSelection = rSh.GetSelectionType();
3394 
3395 			// Draw-Objekte erstmal noch nicht beruecksichtigen
3396 			if( nsSelectionType::SEL_GRF & nSelection )
3397 			{
3398 				SfxItemSet aSet( rSh.GetAttrPool(), RES_URL, RES_URL );
3399 				rSh.GetFlyFrmAttr( aSet );
3400 				SwFmtURL aURL( (SwFmtURL&)aSet.Get( RES_URL ) );
3401 				aURL.SetURL( aTmp.GetURL(), sal_False );
3402 				aSet.Put( aURL );
3403 				rSh.SetFlyFrmAttr( aSet );
3404 				return 1;
3405 			}
3406 
3407 			if( nsSelectionType::SEL_DRW & nSelection )
3408 			{
3409 				rSh.LeaveSelFrmMode();
3410 				rSh.UnSelectFrm();
3411 				rSh.ShowCrsr();
3412 				bFrmDrag = sal_False;
3413 			}
3414 		}
3415 	}
3416 
3417 	if( &rSh != &rSrcSh && (nsSelectionType::SEL_GRF & rSh.GetSelectionType()) &&
3418 		TRNSFR_GRAPHIC == eBufferType )
3419 	{
3420 		// ReRead auf die Grafik
3421 		String sGrfNm, sFltNm;
3422 		rSrcSh.GetGrfNms( &sGrfNm, &sFltNm );
3423         rSh.ReRead( sGrfNm, sFltNm, rSrcSh.GetGraphic() );
3424 		return 1;
3425 	}
3426 
3427 	//Nicht in Selektionen oder selektierten Rahmen
3428 	if( rSh.ChgCurrPam( rDragPt ) ||
3429 		( rSh.IsSelFrmMode() && rSh.IsInsideSelectedObj( rDragPt )) )
3430 		return 0;
3431 
3432 	if( rSrcSh.IsTableMode() )
3433 		bTblSel = sal_True;
3434 	else if( rSrcSh.IsSelFrmMode() || rSrcSh.IsObjSelected() )
3435 	{
3436 		// keine positionsgeschuetzten Objecte verschieben!
3437 		if( bMove && rSrcSh.IsSelObjProtected( FLYPROTECT_POS ) )
3438 			return 0;
3439 
3440 		bFrmSel = sal_True;
3441 	}
3442 
3443 	const int nSel = rSrcSh.GetSelectionType();
3444 
3445     SwUndoId eUndoId = bMove ? UNDO_UI_DRAG_AND_MOVE : UNDO_UI_DRAG_AND_COPY;
3446 
3447     // #111827#
3448     SwRewriter aRewriter;
3449 
3450     aRewriter.AddRule(UNDO_ARG1, rSrcSh.GetSelDescr());
3451 
3452 	if(rSrcSh.GetDoc() != rSh.GetDoc())
3453         rSrcSh.StartUndo( eUndoId, &aRewriter );
3454     rSh.StartUndo( eUndoId, &aRewriter );
3455 
3456 	rSh.StartAction();
3457 	rSrcSh.StartAction();
3458 
3459 	if( &rSrcSh != &rSh )
3460 	{
3461 		rSh.EnterStdMode();
3462 		rSh.SwCrsrShell::SetCrsr( rDragPt, sal_True );
3463 		cWord = rSrcSh.IntelligentCut( nSel, sal_False );
3464 	}
3465 	else if( !bTblSel && !bFrmSel )
3466 	{
3467 		if( !rSh.IsAddMode() )
3468         {
3469             // --> OD 2008-03-19 #i87233#
3470             if ( rSh.IsBlockMode() )
3471             {
3472                 // preserve order of cursors for block mode
3473                 rSh.GoPrevCrsr();
3474             }
3475             // <--
3476 			rSh.SwCrsrShell::CreateCrsr();
3477         }
3478 		rSh.SwCrsrShell::SetCrsr( rDragPt, sal_True, false );
3479 		rSh.GoPrevCrsr();
3480 		cWord = rSh.IntelligentCut( rSh.GetSelectionType(), sal_False );
3481 		rSh.GoNextCrsr();
3482 	}
3483 
3484 	bInWrd	= rSh.IsInWrd();
3485 	bEndWrd = rSh.IsEndWrd();
3486 	bSttWrd = !bEndWrd && rSh.IsSttWrd();
3487 	bSttPara= rSh.IsSttPara();
3488 
3489 	Point aSttPt( SwEditWin::GetDDStartPosX(), SwEditWin::GetDDStartPosY() );
3490 
3491 	//JP 05.03.96: INetFelder erstmal selektieren !
3492 	if( TRNSFR_INETFLD == eBufferType )
3493 	{
3494 		if( &rSrcSh == &rSh )
3495 		{
3496 			rSh.GoPrevCrsr();
3497 			rSh.SwCrsrShell::SetCrsr( aSttPt, sal_True );
3498 			rSh.SelectTxtAttr( RES_TXTATR_INETFMT );
3499 			if( rSh.ChgCurrPam( rDragPt ) )
3500 			{
3501 				// nicht in sich selbst kopieren/verschieben
3502 				rSh.DestroyCrsr();
3503                 rSh.EndUndo();
3504 				rSh.EndAction();
3505 				rSh.EndAction();
3506 				return 0;
3507 			}
3508 			rSh.GoNextCrsr();
3509 		}
3510 		else
3511 		{
3512 			rSrcSh.SwCrsrShell::SetCrsr( aSttPt, sal_True );
3513 			rSrcSh.SelectTxtAttr( RES_TXTATR_INETFMT );
3514 		}
3515 
3516 		// ist am Einfuege Punkt ein URL-Attribut? Dann das ersetzen,
3517 		// also einfach eine Selektion aufspannen?
3518 		rSh.DelINetAttrWithText();
3519 		bDDINetAttr = sal_True;
3520 	}
3521 
3522 	if ( rSrcSh.IsSelFrmMode() )
3523 	{
3524 		//Hack: Spezialbehandlung austricksen
3525 		aSttPt -= aSttPt - rSrcSh.GetObjRect().Pos();
3526 	}
3527 
3528 	sal_Bool bRet = rSrcSh.SwFEShell::Copy( &rSh, aSttPt, rDragPt, bMove,
3529 											!bIsXSelection );
3530 
3531 	if( !bIsXSelection )
3532 	{
3533 		rSrcSh.Push();
3534 		if ( bRet && bMove && !bFrmSel )
3535 		{
3536 			if ( bTblSel )
3537             {
3538                 /* #109590# delete table contents not cells */
3539 				rSrcSh.Delete();
3540             }
3541 			else
3542 			{
3543 				//SmartCut, eines der Blank mitnehmen.
3544 				rSh.SwCrsrShell::DestroyCrsr();
3545 				if ( cWord == SwWrtShell::WORD_SPACE_BEFORE )
3546 					rSh.ExtendSelection( sal_False );
3547 				else if ( cWord == SwWrtShell::WORD_SPACE_AFTER )
3548 					rSh.ExtendSelection();
3549 				rSrcSh.DelRight();
3550 			}
3551 		}
3552 		rSrcSh.KillPams();
3553 		rSrcSh.Pop( sal_False );
3554 
3555         /* #109590# after dragging a table selection inside one shell
3556             set cursor to the drop position. */
3557         if( &rSh == &rSrcSh && ( bTblSel || rSh.IsBlockMode() ) )
3558         {
3559             rSrcSh.SwCrsrShell::SetCrsr(rDragPt);
3560             rSrcSh.GetSwCrsr()->SetMark();
3561         }
3562 	}
3563 
3564 	if( bRet && !bTblSel && !bFrmSel )
3565 	{
3566 		if( (bInWrd || bEndWrd) &&
3567 			(cWord == SwWrtShell::WORD_SPACE_AFTER ||
3568 				cWord == SwWrtShell::WORD_SPACE_BEFORE) )
3569 		{
3570             if ( bSttWrd || (bInWrd && !bEndWrd))
3571 				rSh.SwEditShell::Insert(' ', bIsXSelection);
3572 			if ( !bSttWrd || (bInWrd && !bSttPara) )
3573 			{
3574 				rSh.SwapPam();
3575 				if ( !bSttWrd )
3576 					rSh.SwEditShell::Insert(' ', bIsXSelection);
3577 				rSh.SwapPam();
3578 			}
3579 		}
3580 
3581 		if( bIsXSelection )
3582 		{
3583 			if( &rSrcSh == &rSh && !rSh.IsAddMode() )
3584 			{
3585 				rSh.SwCrsrShell::DestroyCrsr();
3586 				rSh.GoPrevCrsr();
3587 			}
3588 			else
3589 			{
3590 				rSh.SwapPam();
3591 				rSh.SwCrsrShell::ClearMark();
3592 			}
3593 		}
3594 		else
3595 		{
3596 			if( rSh.IsAddMode() )
3597 				rSh.SwCrsrShell::CreateCrsr();
3598 			else
3599 			{
3600 				// Selektionsmodus einschalten
3601 				rSh.SttSelect();
3602 				rSh.EndSelect();
3603 			}
3604 		}
3605 	}
3606 
3607 	if( bRet && bMove && bFrmSel )
3608 		rSrcSh.LeaveSelFrmMode();
3609 
3610 	if( rSrcSh.GetDoc() != rSh.GetDoc() )
3611         rSrcSh.EndUndo();
3612     rSh.EndUndo();
3613 
3614 		// Shell in den richtigen Status versetzen
3615 	if( &rSrcSh != &rSh && ( rSh.IsFrmSelected() || rSh.IsObjSelected() ))
3616 		rSh.EnterSelFrmMode();
3617 
3618 	rSrcSh.EndAction();
3619 	rSh.EndAction();
3620 	return 1;
3621 }
3622 
3623 // Interfaces for Selection
CreateSelection(SwWrtShell & rSh,const ViewShell * _pCreatorView)3624 void SwTransferable::CreateSelection( SwWrtShell& rSh,
3625 									  const ViewShell * _pCreatorView )
3626 {
3627 	SwModule *pMod = SW_MOD();
3628 	SwTransferable* pNew = new SwTransferable( rSh );
3629 
3630 	/* #96392#*/
3631  	pNew->pCreatorView = _pCreatorView;
3632 
3633     uno::Reference<
3634             datatransfer::XTransferable > xRef( pNew );
3635 	pMod->pXSelection = pNew;
3636 	pNew->CopyToSelection( rSh.GetWin() );
3637 }
3638 
ClearSelection(SwWrtShell & rSh,const ViewShell * _pCreatorView)3639 void SwTransferable::ClearSelection( SwWrtShell& rSh,
3640 									 const ViewShell * _pCreatorView)
3641 {
3642 	SwModule *pMod = SW_MOD();
3643     if( pMod->pXSelection &&
3644         ((!pMod->pXSelection->pWrtShell) || (pMod->pXSelection->pWrtShell == &rSh)) &&
3645 		/* #96392# */
3646         (!_pCreatorView || (pMod->pXSelection->pCreatorView == _pCreatorView)) )
3647 	{
3648 		TransferableHelper::ClearSelection( rSh.GetWin() );
3649 	}
3650 }
3651 /* -----------------3/31/2003 11:46AM----------------
3652 
3653  --------------------------------------------------*/
getUnoTunnelId()3654 const Sequence< sal_Int8 >& SwTransferable::getUnoTunnelId()
3655 {
3656     static Sequence< sal_Int8 > aSeq;
3657     if( !aSeq.getLength() )
3658     {
3659         static osl::Mutex           aCreateMutex;
3660         osl::Guard< osl::Mutex >    aGuard( aCreateMutex );
3661         aSeq.realloc( 16 );
3662         rtl_createUuid( reinterpret_cast< sal_uInt8* >( aSeq.getArray() ), 0, sal_True );
3663     }
3664     return aSeq;
3665 }
3666 /* -----------------3/31/2003 11:46AM----------------
3667 
3668  --------------------------------------------------*/
getSomething(const Sequence<sal_Int8> & rId)3669 sal_Int64 SwTransferable::getSomething( const Sequence< sal_Int8 >& rId ) throw( RuntimeException )
3670 {
3671     sal_Int64 nRet;
3672     if( ( rId.getLength() == 16 ) &&
3673         ( 0 == rtl_compareMemory( getUnoTunnelId().getConstArray(), rId.getConstArray(), 16 ) ) )
3674     {
3675         nRet = sal::static_int_cast< sal_Int64 >( reinterpret_cast< sal_IntPtr >( this ) );
3676     }
3677     else
3678         nRet = TransferableHelper::getSomething(rId);
3679     return nRet;
3680 }
3681 
GetSwTransferable(const TransferableDataHelper & rData)3682 SwTransferable* SwTransferable::GetSwTransferable( const TransferableDataHelper& rData )
3683 {
3684     SwTransferable* pSwTransferable = NULL;
3685 
3686     uno::Reference<XUnoTunnel> xTunnel( rData.GetTransferable(), UNO_QUERY );
3687     if ( xTunnel.is() )
3688     {
3689         sal_Int64 nHandle = xTunnel->getSomething( getUnoTunnelId() );
3690         if ( nHandle )
3691             pSwTransferable = (SwTransferable*) (sal_IntPtr) nHandle;
3692     }
3693 
3694     return pSwTransferable;
3695 
3696 }
3697 
3698 /*  */
3699 
3700 // -----------------------------------------------------------------------
3701 
SwTrnsfrDdeLink(SwTransferable & rTrans,SwWrtShell & rSh)3702 SwTrnsfrDdeLink::SwTrnsfrDdeLink( SwTransferable& rTrans, SwWrtShell& rSh )
3703     : rTrnsfr( rTrans ), pDocShell( 0 ),
3704     bDelBookmrk( sal_False ), bInDisconnect( sal_False )
3705 {
3706     // hier kommen wir nur bei Tabellen- oder Text-Selection an
3707     const int nSelection = rSh.GetSelectionType();
3708     if( nsSelectionType::SEL_TBL_CELLS & nSelection )
3709     {
3710         SwFrmFmt* pFmt = rSh.GetTableFmt();
3711         if( pFmt )
3712             sName = pFmt->GetName();
3713     }
3714     else
3715     {
3716         // creating a temp. bookmark without undo
3717         sal_Bool bUndo = rSh.DoesUndo();
3718         rSh.DoUndo( sal_False );
3719         sal_Bool bIsModified = rSh.IsModified();
3720 
3721         ::sw::mark::IMark* pMark = rSh.SetBookmark(
3722             KeyCode(),
3723             ::rtl::OUString(),
3724             ::rtl::OUString(),
3725             IDocumentMarkAccess::DDE_BOOKMARK);
3726         if(pMark)
3727         {
3728             sName = pMark->GetName();
3729             bDelBookmrk = sal_True;
3730             if( !bIsModified )
3731                 rSh.ResetModified();
3732         }
3733         else
3734             sName.Erase();
3735         rSh.DoUndo( bUndo );
3736     }
3737 
3738     if( sName.Len() &&
3739         0 != ( pDocShell = rSh.GetDoc()->GetDocShell() ) )
3740     {
3741         // dann erzeugen wir uns mal unseren "Server" und connecten uns
3742         // zu diesem
3743         refObj = pDocShell->DdeCreateLinkSource( sName );
3744         if( refObj.Is() )
3745         {
3746             refObj->AddConnectAdvise( this );
3747             refObj->AddDataAdvise( this,
3748 //                          SotExchange::GetFormatMimeType( FORMAT_RTF ),
3749                             aEmptyStr,
3750                             ADVISEMODE_NODATA | ADVISEMODE_ONLYONCE );
3751             nOldTimeOut = refObj->GetUpdateTimeout();
3752             refObj->SetUpdateTimeout( 0 );
3753         }
3754     }
3755 }
3756 
3757 // -----------------------------------------------------------------------
3758 
~SwTrnsfrDdeLink()3759 SwTrnsfrDdeLink::~SwTrnsfrDdeLink()
3760 {
3761 	if( refObj.Is() )
3762 		Disconnect( sal_True );
3763 }
3764 
3765 // -----------------------------------------------------------------------
3766 
DataChanged(const String &,const uno::Any &)3767 void SwTrnsfrDdeLink::DataChanged( const String& ,
3768                                     const uno::Any& )
3769 {
3770 	// tja das wars dann mit dem Link
3771 	if( !bInDisconnect )
3772 	{
3773 		if( FindDocShell() && pDocShell->GetView() )
3774 			rTrnsfr.RemoveDDELinkFormat( pDocShell->GetView()->GetEditWin() );
3775 		Disconnect( sal_False );
3776 	}
3777 }
3778 
3779 // -----------------------------------------------------------------------
3780 
WriteData(SvStream & rStrm)3781 sal_Bool SwTrnsfrDdeLink::WriteData( SvStream& rStrm )
3782 {
3783     if( !refObj.Is() || !FindDocShell() )
3784         return sal_False;
3785 
3786     rtl_TextEncoding eEncoding = DDE_TXT_ENCODING;
3787     const ByteString aAppNm( GetpApp()->GetAppName(), eEncoding );
3788     const ByteString aTopic( pDocShell->GetTitle( SFX_TITLE_FULLNAME ),
3789                             eEncoding );
3790     const ByteString aName( sName, eEncoding );
3791 
3792     sal_Char* pMem = new char[ aAppNm.Len() + aTopic.Len() + aName.Len() + 4 ];
3793 
3794     xub_StrLen nLen = aAppNm.Len();
3795     memcpy( pMem, aAppNm.GetBuffer(), nLen );
3796     pMem[ nLen++ ] = 0;
3797     memcpy( pMem + nLen, aTopic.GetBuffer(), aTopic.Len() );
3798     nLen = nLen + aTopic.Len();
3799     pMem[ nLen++ ] = 0;
3800     memcpy( pMem + nLen, aName.GetBuffer(), aName.Len() );
3801     nLen = nLen + aName.Len();
3802     pMem[ nLen++ ] = 0;
3803     pMem[ nLen++ ] = 0;
3804 
3805     rStrm.Write( pMem, nLen );
3806     delete[] pMem;
3807 
3808     IDocumentMarkAccess* const pMarkAccess = pDocShell->GetDoc()->getIDocumentMarkAccess();
3809     IDocumentMarkAccess::const_iterator_t ppMark = pMarkAccess->findMark(sName);
3810     if(ppMark != pMarkAccess->getAllMarksEnd()
3811         && IDocumentMarkAccess::GetType(**ppMark) != IDocumentMarkAccess::BOOKMARK)
3812     {
3813         // the mark is still a DdeBookmark
3814         // we replace it with a Bookmark, so it will get saved etc.
3815         ::sw::mark::IMark* const pMark = ppMark->get();
3816         SwServerObject* const pServerObject = dynamic_cast<SwServerObject *>(&refObj);
3817 
3818         // collecting state of old mark
3819         SwPaM aPaM(pMark->GetMarkStart());
3820         *aPaM.GetPoint() = pMark->GetMarkStart();
3821         if(pMark->IsExpanded())
3822         {
3823             aPaM.SetMark();
3824             *aPaM.GetMark() = pMark->GetMarkEnd();
3825         }
3826         ::rtl::OUString sMarkName = pMark->GetName();
3827 
3828         // remove mark
3829         pServerObject->SetNoServer(); // this removes the connection between SwServerObject and mark
3830         // N.B. ppMark was not loaded from file and cannot have xml:id
3831         pMarkAccess->deleteMark(ppMark);
3832 
3833         // recreate as Bookmark
3834         ::sw::mark::IMark* const pNewMark = pMarkAccess->makeMark(
3835             aPaM,
3836             sMarkName,
3837             IDocumentMarkAccess::BOOKMARK);
3838         pServerObject->SetDdeBookmark(*pNewMark);
3839     }
3840 
3841     bDelBookmrk = false;
3842     return true;
3843 }
3844 
3845 // -----------------------------------------------------------------------
3846 
Disconnect(sal_Bool bRemoveDataAdvise)3847 void SwTrnsfrDdeLink::Disconnect( sal_Bool bRemoveDataAdvise )
3848 {
3849     //JP 29.01.96 Bug 24432:
3850     //		kein DataChanged mehr entgegen nehmen, wenn man
3851     //		sich schon im Disconnet befindet!
3852     // 		(DTOR vom Bookmark verschickt einen DataChanged!)
3853     const sal_Bool bOldDisconnect = bInDisconnect;
3854     bInDisconnect = sal_True;
3855 
3856     // den nicht verwendeten Bookmark wieder zerstoeren (ohne Undo!)?
3857     if( bDelBookmrk && refObj.Is() && FindDocShell() )
3858     {
3859         SwDoc* pDoc = pDocShell->GetDoc();
3860         ::sw::UndoGuard const undoGuard(pDoc->GetIDocumentUndoRedo());
3861 
3862         // --> OD, CD, OS 2005-11-25 #i58448#
3863         Link aSavedOle2Link( pDoc->GetOle2Link() );
3864         pDoc->SetOle2Link( Link() );
3865         // <--
3866         sal_Bool bIsModified = pDoc->IsModified();
3867 
3868         IDocumentMarkAccess* const pMarkAccess = pDoc->getIDocumentMarkAccess();
3869         // check, if DdeBookmark is already in its destruction
3870         IDocumentMarkAccess::const_iterator_t ppMark = pMarkAccess->findMark(sName);
3871         if ( ppMark != pMarkAccess->getAllMarksEnd() )
3872         {
3873             ::sw::mark::DdeBookmark* const pDdeBookmark = dynamic_cast< ::sw::mark::DdeBookmark* >(ppMark->get());
3874             if ( pDdeBookmark && !pDdeBookmark->IsInDestruction() )
3875             {
3876                 pMarkAccess->deleteMark(ppMark);
3877             }
3878         }
3879 
3880         if( !bIsModified )
3881             pDoc->ResetModified();
3882         pDoc->SetOle2Link( aSavedOle2Link );
3883 
3884         bDelBookmrk = sal_False;
3885     }
3886 
3887     if( refObj.Is() )
3888     {
3889         refObj->SetUpdateTimeout( nOldTimeOut );
3890         refObj->RemoveConnectAdvise( this );
3891         if( bRemoveDataAdvise )
3892             // in einem DataChanged darf das SelectionObject NIE geloescht
3893             // werden; wird schon von der Basisklasse erledigt
3894             // (ADVISEMODE_ONLYONCE!!!!)
3895             // Im normalen Disconnet aber schon!
3896             refObj->RemoveAllDataAdvise( this );
3897         refObj.Clear();
3898     }
3899     bInDisconnect = bOldDisconnect;
3900 }
3901 
3902 // -----------------------------------------------------------------------
3903 
FindDocShell()3904 sal_Bool SwTrnsfrDdeLink::FindDocShell()
3905 {
3906 	TypeId aType( TYPE( SwDocShell ) );
3907 	SfxObjectShell* pTmpSh = SfxObjectShell::GetFirst( &aType );
3908 	while( pTmpSh )
3909 	{
3910 		if( pTmpSh == pDocShell )		// die wollen wir haben
3911 		{
3912 			if( pDocShell->GetDoc() )
3913 				return sal_True;
3914 			break;		// das Doc ist nicht mehr vorhanden, also raus!
3915 		}
3916 		pTmpSh = SfxObjectShell::GetNext( *pTmpSh, &aType );
3917 	}
3918 
3919 	pDocShell = 0;
3920 	return sal_False;
3921 }
3922 
3923 // -----------------------------------------------------------------------
3924 
Closed()3925 void SwTrnsfrDdeLink::Closed()
3926 {
3927 	if( !bInDisconnect && refObj.Is() )
3928 	{
3929 		refObj->RemoveAllDataAdvise( this );
3930 		refObj->RemoveConnectAdvise( this );
3931 		refObj.Clear();
3932 	}
3933 }
3934