1*cdf0e10cSrcweir /************************************************************************* 2*cdf0e10cSrcweir * 3*cdf0e10cSrcweir * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. 4*cdf0e10cSrcweir * 5*cdf0e10cSrcweir * Copyright 2000, 2010 Oracle and/or its affiliates. 6*cdf0e10cSrcweir * 7*cdf0e10cSrcweir * OpenOffice.org - a multi-platform office productivity suite 8*cdf0e10cSrcweir * 9*cdf0e10cSrcweir * This file is part of OpenOffice.org. 10*cdf0e10cSrcweir * 11*cdf0e10cSrcweir * OpenOffice.org is free software: you can redistribute it and/or modify 12*cdf0e10cSrcweir * it under the terms of the GNU Lesser General Public License version 3 13*cdf0e10cSrcweir * only, as published by the Free Software Foundation. 14*cdf0e10cSrcweir * 15*cdf0e10cSrcweir * OpenOffice.org is distributed in the hope that it will be useful, 16*cdf0e10cSrcweir * but WITHOUT ANY WARRANTY; without even the implied warranty of 17*cdf0e10cSrcweir * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 18*cdf0e10cSrcweir * GNU Lesser General Public License version 3 for more details 19*cdf0e10cSrcweir * (a copy is included in the LICENSE file that accompanied this code). 20*cdf0e10cSrcweir * 21*cdf0e10cSrcweir * You should have received a copy of the GNU Lesser General Public License 22*cdf0e10cSrcweir * version 3 along with OpenOffice.org. If not, see 23*cdf0e10cSrcweir * <http://www.openoffice.org/license.html> 24*cdf0e10cSrcweir * for a copy of the LGPLv3 License. 25*cdf0e10cSrcweir * 26*cdf0e10cSrcweir ************************************************************************/ 27*cdf0e10cSrcweir 28*cdf0e10cSrcweir // MARKER(update_precomp.py): autogen include statement, do not remove 29*cdf0e10cSrcweir #include "precompiled_sfx2.hxx" 30*cdf0e10cSrcweir 31*cdf0e10cSrcweir 32*cdf0e10cSrcweir #include <sfx2/lnkbase.hxx> 33*cdf0e10cSrcweir #include <sot/exchange.hxx> 34*cdf0e10cSrcweir #include <com/sun/star/uno/Any.hxx> 35*cdf0e10cSrcweir #include <com/sun/star/uno/Sequence.hxx> 36*cdf0e10cSrcweir #include <vcl/msgbox.hxx> 37*cdf0e10cSrcweir #include <sfx2/linkmgr.hxx> 38*cdf0e10cSrcweir #include <vcl/svapp.hxx> 39*cdf0e10cSrcweir #include "app.hrc" 40*cdf0e10cSrcweir #include "sfx2/sfxresid.hxx" 41*cdf0e10cSrcweir #include <sfx2/filedlghelper.hxx> 42*cdf0e10cSrcweir #include <tools/debug.hxx> 43*cdf0e10cSrcweir #include <svl/svdde.hxx> 44*cdf0e10cSrcweir 45*cdf0e10cSrcweir using namespace ::com::sun::star::uno; 46*cdf0e10cSrcweir 47*cdf0e10cSrcweir namespace sfx2 48*cdf0e10cSrcweir { 49*cdf0e10cSrcweir 50*cdf0e10cSrcweir TYPEINIT0( SvBaseLink ) 51*cdf0e10cSrcweir 52*cdf0e10cSrcweir static DdeTopic* FindTopic( const String &, sal_uInt16* = 0 ); 53*cdf0e10cSrcweir 54*cdf0e10cSrcweir class ImplDdeItem; 55*cdf0e10cSrcweir 56*cdf0e10cSrcweir struct BaseLink_Impl 57*cdf0e10cSrcweir { 58*cdf0e10cSrcweir Link m_aEndEditLink; 59*cdf0e10cSrcweir LinkManager* m_pLinkMgr; 60*cdf0e10cSrcweir Window* m_pParentWin; 61*cdf0e10cSrcweir FileDialogHelper* m_pFileDlg; 62*cdf0e10cSrcweir bool m_bIsConnect; 63*cdf0e10cSrcweir 64*cdf0e10cSrcweir BaseLink_Impl() : 65*cdf0e10cSrcweir m_pLinkMgr( NULL ) 66*cdf0e10cSrcweir , m_pParentWin( NULL ) 67*cdf0e10cSrcweir , m_pFileDlg( NULL ) 68*cdf0e10cSrcweir , m_bIsConnect( false ) 69*cdf0e10cSrcweir {} 70*cdf0e10cSrcweir 71*cdf0e10cSrcweir ~BaseLink_Impl() 72*cdf0e10cSrcweir { delete m_pFileDlg; } 73*cdf0e10cSrcweir }; 74*cdf0e10cSrcweir 75*cdf0e10cSrcweir // nur fuer die interne Verwaltung 76*cdf0e10cSrcweir struct ImplBaseLinkData 77*cdf0e10cSrcweir { 78*cdf0e10cSrcweir struct tClientType 79*cdf0e10cSrcweir { 80*cdf0e10cSrcweir // gilt fuer alle Links 81*cdf0e10cSrcweir sal_uIntPtr nCntntType; // Update Format 82*cdf0e10cSrcweir // nicht Ole-Links 83*cdf0e10cSrcweir sal_Bool bIntrnlLnk; // ist es ein interner Link 84*cdf0e10cSrcweir sal_uInt16 nUpdateMode;// UpdateMode 85*cdf0e10cSrcweir }; 86*cdf0e10cSrcweir 87*cdf0e10cSrcweir struct tDDEType 88*cdf0e10cSrcweir { 89*cdf0e10cSrcweir ImplDdeItem* pItem; 90*cdf0e10cSrcweir }; 91*cdf0e10cSrcweir 92*cdf0e10cSrcweir union { 93*cdf0e10cSrcweir tClientType ClientType; 94*cdf0e10cSrcweir tDDEType DDEType; 95*cdf0e10cSrcweir }; 96*cdf0e10cSrcweir ImplBaseLinkData() 97*cdf0e10cSrcweir { 98*cdf0e10cSrcweir ClientType.nCntntType = 0; 99*cdf0e10cSrcweir ClientType.bIntrnlLnk = sal_False; 100*cdf0e10cSrcweir ClientType.nUpdateMode = 0; 101*cdf0e10cSrcweir DDEType.pItem = NULL; 102*cdf0e10cSrcweir } 103*cdf0e10cSrcweir }; 104*cdf0e10cSrcweir 105*cdf0e10cSrcweir 106*cdf0e10cSrcweir class ImplDdeItem : public DdeGetPutItem 107*cdf0e10cSrcweir { 108*cdf0e10cSrcweir SvBaseLink* pLink; 109*cdf0e10cSrcweir DdeData aData; 110*cdf0e10cSrcweir Sequence< sal_Int8 > aSeq; // Datacontainer for DdeData !!! 111*cdf0e10cSrcweir sal_Bool bIsValidData : 1; 112*cdf0e10cSrcweir sal_Bool bIsInDTOR : 1; 113*cdf0e10cSrcweir public: 114*cdf0e10cSrcweir ImplDdeItem( SvBaseLink& rLink, const String& rStr ) 115*cdf0e10cSrcweir : DdeGetPutItem( rStr ), pLink( &rLink ), bIsValidData( sal_False ), 116*cdf0e10cSrcweir bIsInDTOR( sal_False ) 117*cdf0e10cSrcweir {} 118*cdf0e10cSrcweir virtual ~ImplDdeItem(); 119*cdf0e10cSrcweir 120*cdf0e10cSrcweir virtual DdeData* Get( sal_uIntPtr ); 121*cdf0e10cSrcweir virtual sal_Bool Put( const DdeData* ); 122*cdf0e10cSrcweir virtual void AdviseLoop( sal_Bool ); 123*cdf0e10cSrcweir 124*cdf0e10cSrcweir void Notify() 125*cdf0e10cSrcweir { 126*cdf0e10cSrcweir bIsValidData = sal_False; 127*cdf0e10cSrcweir DdeGetPutItem::NotifyClient(); 128*cdf0e10cSrcweir } 129*cdf0e10cSrcweir 130*cdf0e10cSrcweir sal_Bool IsInDTOR() const { return bIsInDTOR; } 131*cdf0e10cSrcweir }; 132*cdf0e10cSrcweir 133*cdf0e10cSrcweir 134*cdf0e10cSrcweir /************************************************************************ 135*cdf0e10cSrcweir |* SvBaseLink::SvBaseLink() 136*cdf0e10cSrcweir |* 137*cdf0e10cSrcweir |* Beschreibung 138*cdf0e10cSrcweir *************************************************************************/ 139*cdf0e10cSrcweir 140*cdf0e10cSrcweir SvBaseLink::SvBaseLink() 141*cdf0e10cSrcweir { 142*cdf0e10cSrcweir pImpl = new BaseLink_Impl(); 143*cdf0e10cSrcweir nObjType = OBJECT_CLIENT_SO; 144*cdf0e10cSrcweir pImplData = new ImplBaseLinkData; 145*cdf0e10cSrcweir bVisible = bSynchron = bUseCache = sal_True; 146*cdf0e10cSrcweir bWasLastEditOK = sal_False; 147*cdf0e10cSrcweir } 148*cdf0e10cSrcweir 149*cdf0e10cSrcweir /************************************************************************ 150*cdf0e10cSrcweir |* SvBaseLink::SvBaseLink() 151*cdf0e10cSrcweir |* 152*cdf0e10cSrcweir |* Beschreibung 153*cdf0e10cSrcweir *************************************************************************/ 154*cdf0e10cSrcweir 155*cdf0e10cSrcweir SvBaseLink::SvBaseLink( sal_uInt16 nUpdateMode, sal_uIntPtr nContentType ) 156*cdf0e10cSrcweir { 157*cdf0e10cSrcweir pImpl = new BaseLink_Impl(); 158*cdf0e10cSrcweir nObjType = OBJECT_CLIENT_SO; 159*cdf0e10cSrcweir pImplData = new ImplBaseLinkData; 160*cdf0e10cSrcweir bVisible = bSynchron = bUseCache = sal_True; 161*cdf0e10cSrcweir bWasLastEditOK = sal_False; 162*cdf0e10cSrcweir 163*cdf0e10cSrcweir // falls es ein Ole-Link wird, 164*cdf0e10cSrcweir pImplData->ClientType.nUpdateMode = nUpdateMode; 165*cdf0e10cSrcweir pImplData->ClientType.nCntntType = nContentType; 166*cdf0e10cSrcweir pImplData->ClientType.bIntrnlLnk = sal_False; 167*cdf0e10cSrcweir } 168*cdf0e10cSrcweir 169*cdf0e10cSrcweir /************************************************************************ 170*cdf0e10cSrcweir |* SvBaseLink::SvBaseLink() 171*cdf0e10cSrcweir |* 172*cdf0e10cSrcweir |* Beschreibung 173*cdf0e10cSrcweir *************************************************************************/ 174*cdf0e10cSrcweir 175*cdf0e10cSrcweir SvBaseLink::SvBaseLink( const String& rLinkName, sal_uInt16 nObjectType, SvLinkSource* pObj ) 176*cdf0e10cSrcweir { 177*cdf0e10cSrcweir bVisible = bSynchron = bUseCache = sal_True; 178*cdf0e10cSrcweir bWasLastEditOK = sal_False; 179*cdf0e10cSrcweir aLinkName = rLinkName; 180*cdf0e10cSrcweir pImplData = new ImplBaseLinkData; 181*cdf0e10cSrcweir nObjType = nObjectType; 182*cdf0e10cSrcweir 183*cdf0e10cSrcweir if( !pObj ) 184*cdf0e10cSrcweir { 185*cdf0e10cSrcweir DBG_ASSERT( pObj, "Wo ist mein zu linkendes Object" ); 186*cdf0e10cSrcweir return; 187*cdf0e10cSrcweir } 188*cdf0e10cSrcweir 189*cdf0e10cSrcweir if( OBJECT_DDE_EXTERN == nObjType ) 190*cdf0e10cSrcweir { 191*cdf0e10cSrcweir sal_uInt16 nItemStt = 0; 192*cdf0e10cSrcweir DdeTopic* pTopic = FindTopic( aLinkName, &nItemStt ); 193*cdf0e10cSrcweir if( pTopic ) 194*cdf0e10cSrcweir { 195*cdf0e10cSrcweir // dann haben wir alles zusammen 196*cdf0e10cSrcweir // MM hat gefummelt ??? 197*cdf0e10cSrcweir // MM_TODO wie kriege ich den Namen 198*cdf0e10cSrcweir String aStr = aLinkName; // xLinkName->GetDisplayName(); 199*cdf0e10cSrcweir aStr = aStr.Copy( nItemStt ); 200*cdf0e10cSrcweir pImplData->DDEType.pItem = new ImplDdeItem( *this, aStr ); 201*cdf0e10cSrcweir pTopic->InsertItem( pImplData->DDEType.pItem ); 202*cdf0e10cSrcweir 203*cdf0e10cSrcweir // dann koennen wir uns auch das Advise merken 204*cdf0e10cSrcweir xObj = pObj; 205*cdf0e10cSrcweir } 206*cdf0e10cSrcweir } 207*cdf0e10cSrcweir else if( pObj->Connect( this ) ) 208*cdf0e10cSrcweir xObj = pObj; 209*cdf0e10cSrcweir } 210*cdf0e10cSrcweir 211*cdf0e10cSrcweir /************************************************************************ 212*cdf0e10cSrcweir |* SvBaseLink::~SvBaseLink() 213*cdf0e10cSrcweir |* 214*cdf0e10cSrcweir |* Beschreibung 215*cdf0e10cSrcweir *************************************************************************/ 216*cdf0e10cSrcweir 217*cdf0e10cSrcweir SvBaseLink::~SvBaseLink() 218*cdf0e10cSrcweir { 219*cdf0e10cSrcweir Disconnect(); 220*cdf0e10cSrcweir 221*cdf0e10cSrcweir switch( nObjType ) 222*cdf0e10cSrcweir { 223*cdf0e10cSrcweir case OBJECT_DDE_EXTERN: 224*cdf0e10cSrcweir if( !pImplData->DDEType.pItem->IsInDTOR() ) 225*cdf0e10cSrcweir delete pImplData->DDEType.pItem; 226*cdf0e10cSrcweir break; 227*cdf0e10cSrcweir } 228*cdf0e10cSrcweir 229*cdf0e10cSrcweir delete pImplData; 230*cdf0e10cSrcweir } 231*cdf0e10cSrcweir 232*cdf0e10cSrcweir IMPL_LINK( SvBaseLink, EndEditHdl, String*, _pNewName ) 233*cdf0e10cSrcweir { 234*cdf0e10cSrcweir String sNewName; 235*cdf0e10cSrcweir if ( _pNewName ) 236*cdf0e10cSrcweir sNewName = *_pNewName; 237*cdf0e10cSrcweir if ( !ExecuteEdit( sNewName ) ) 238*cdf0e10cSrcweir sNewName.Erase(); 239*cdf0e10cSrcweir bWasLastEditOK = ( sNewName.Len() > 0 ); 240*cdf0e10cSrcweir if ( pImpl->m_aEndEditLink.IsSet() ) 241*cdf0e10cSrcweir pImpl->m_aEndEditLink.Call( this ); 242*cdf0e10cSrcweir return 0; 243*cdf0e10cSrcweir } 244*cdf0e10cSrcweir 245*cdf0e10cSrcweir /************************************************************************ 246*cdf0e10cSrcweir |* SvBaseLink::SetObjType() 247*cdf0e10cSrcweir |* 248*cdf0e10cSrcweir |* Beschreibung 249*cdf0e10cSrcweir *************************************************************************/ 250*cdf0e10cSrcweir 251*cdf0e10cSrcweir void SvBaseLink::SetObjType( sal_uInt16 nObjTypeP ) 252*cdf0e10cSrcweir { 253*cdf0e10cSrcweir DBG_ASSERT( nObjType != OBJECT_CLIENT_DDE, "type already set" ); 254*cdf0e10cSrcweir DBG_ASSERT( !xObj.Is(), "object exist" ); 255*cdf0e10cSrcweir 256*cdf0e10cSrcweir nObjType = nObjTypeP; 257*cdf0e10cSrcweir } 258*cdf0e10cSrcweir 259*cdf0e10cSrcweir /************************************************************************ 260*cdf0e10cSrcweir |* SvBaseLink::SetName() 261*cdf0e10cSrcweir |* 262*cdf0e10cSrcweir |* Beschreibung 263*cdf0e10cSrcweir *************************************************************************/ 264*cdf0e10cSrcweir 265*cdf0e10cSrcweir void SvBaseLink::SetName( const String & rNm ) 266*cdf0e10cSrcweir { 267*cdf0e10cSrcweir aLinkName = rNm; 268*cdf0e10cSrcweir } 269*cdf0e10cSrcweir 270*cdf0e10cSrcweir /************************************************************************ 271*cdf0e10cSrcweir |* SvBaseLink::GetName() 272*cdf0e10cSrcweir |* 273*cdf0e10cSrcweir |* Beschreibung 274*cdf0e10cSrcweir *************************************************************************/ 275*cdf0e10cSrcweir 276*cdf0e10cSrcweir String SvBaseLink::GetName() const 277*cdf0e10cSrcweir { 278*cdf0e10cSrcweir return aLinkName; 279*cdf0e10cSrcweir } 280*cdf0e10cSrcweir 281*cdf0e10cSrcweir /************************************************************************ 282*cdf0e10cSrcweir |* SvBaseLink::SetObj() 283*cdf0e10cSrcweir |* 284*cdf0e10cSrcweir |* Beschreibung 285*cdf0e10cSrcweir *************************************************************************/ 286*cdf0e10cSrcweir 287*cdf0e10cSrcweir void SvBaseLink::SetObj( SvLinkSource * pObj ) 288*cdf0e10cSrcweir { 289*cdf0e10cSrcweir DBG_ASSERT( (nObjType & OBJECT_CLIENT_SO && 290*cdf0e10cSrcweir pImplData->ClientType.bIntrnlLnk) || 291*cdf0e10cSrcweir nObjType == OBJECT_CLIENT_GRF, 292*cdf0e10cSrcweir "no intern link" ); 293*cdf0e10cSrcweir xObj = pObj; 294*cdf0e10cSrcweir } 295*cdf0e10cSrcweir 296*cdf0e10cSrcweir /************************************************************************ 297*cdf0e10cSrcweir |* SvBaseLink::SetLinkSourceName() 298*cdf0e10cSrcweir |* 299*cdf0e10cSrcweir |* Beschreibung 300*cdf0e10cSrcweir *************************************************************************/ 301*cdf0e10cSrcweir 302*cdf0e10cSrcweir void SvBaseLink::SetLinkSourceName( const String & rLnkNm ) 303*cdf0e10cSrcweir { 304*cdf0e10cSrcweir if( aLinkName == rLnkNm ) 305*cdf0e10cSrcweir return; 306*cdf0e10cSrcweir 307*cdf0e10cSrcweir AddNextRef(); // sollte ueberfluessig sein 308*cdf0e10cSrcweir // Alte Verbindung weg 309*cdf0e10cSrcweir Disconnect(); 310*cdf0e10cSrcweir 311*cdf0e10cSrcweir aLinkName = rLnkNm; 312*cdf0e10cSrcweir 313*cdf0e10cSrcweir // Neu verbinden 314*cdf0e10cSrcweir _GetRealObject(); 315*cdf0e10cSrcweir ReleaseRef(); // sollte ueberfluessig sein 316*cdf0e10cSrcweir } 317*cdf0e10cSrcweir 318*cdf0e10cSrcweir /************************************************************************ 319*cdf0e10cSrcweir |* SvBaseLink::GetLinkSourceName() 320*cdf0e10cSrcweir |* 321*cdf0e10cSrcweir |* Beschreibung 322*cdf0e10cSrcweir *************************************************************************/ 323*cdf0e10cSrcweir 324*cdf0e10cSrcweir String SvBaseLink::GetLinkSourceName() const 325*cdf0e10cSrcweir { 326*cdf0e10cSrcweir return aLinkName; 327*cdf0e10cSrcweir } 328*cdf0e10cSrcweir 329*cdf0e10cSrcweir 330*cdf0e10cSrcweir /************************************************************************ 331*cdf0e10cSrcweir |* SvBaseLink::SetUpdateMode() 332*cdf0e10cSrcweir |* 333*cdf0e10cSrcweir |* Beschreibung 334*cdf0e10cSrcweir *************************************************************************/ 335*cdf0e10cSrcweir 336*cdf0e10cSrcweir void SvBaseLink::SetUpdateMode( sal_uInt16 nMode ) 337*cdf0e10cSrcweir { 338*cdf0e10cSrcweir if( ( OBJECT_CLIENT_SO & nObjType ) && 339*cdf0e10cSrcweir pImplData->ClientType.nUpdateMode != nMode ) 340*cdf0e10cSrcweir { 341*cdf0e10cSrcweir AddNextRef(); 342*cdf0e10cSrcweir Disconnect(); 343*cdf0e10cSrcweir 344*cdf0e10cSrcweir pImplData->ClientType.nUpdateMode = nMode; 345*cdf0e10cSrcweir _GetRealObject(); 346*cdf0e10cSrcweir ReleaseRef(); 347*cdf0e10cSrcweir } 348*cdf0e10cSrcweir } 349*cdf0e10cSrcweir 350*cdf0e10cSrcweir // --> OD 2008-06-19 #i88291# 351*cdf0e10cSrcweir void SvBaseLink::clearStreamToLoadFrom() 352*cdf0e10cSrcweir { 353*cdf0e10cSrcweir m_xInputStreamToLoadFrom.clear(); 354*cdf0e10cSrcweir if( xObj.Is() ) 355*cdf0e10cSrcweir { 356*cdf0e10cSrcweir xObj->clearStreamToLoadFrom(); 357*cdf0e10cSrcweir } 358*cdf0e10cSrcweir } 359*cdf0e10cSrcweir // <-- 360*cdf0e10cSrcweir 361*cdf0e10cSrcweir sal_Bool SvBaseLink::Update() 362*cdf0e10cSrcweir { 363*cdf0e10cSrcweir if( OBJECT_CLIENT_SO & nObjType ) 364*cdf0e10cSrcweir { 365*cdf0e10cSrcweir AddNextRef(); 366*cdf0e10cSrcweir Disconnect(); 367*cdf0e10cSrcweir 368*cdf0e10cSrcweir _GetRealObject(); 369*cdf0e10cSrcweir ReleaseRef(); 370*cdf0e10cSrcweir if( xObj.Is() ) 371*cdf0e10cSrcweir { 372*cdf0e10cSrcweir xObj->setStreamToLoadFrom(m_xInputStreamToLoadFrom,m_bIsReadOnly); 373*cdf0e10cSrcweir // m_xInputStreamToLoadFrom = 0; 374*cdf0e10cSrcweir String sMimeType( SotExchange::GetFormatMimeType( 375*cdf0e10cSrcweir pImplData->ClientType.nCntntType )); 376*cdf0e10cSrcweir Any aData; 377*cdf0e10cSrcweir 378*cdf0e10cSrcweir if( xObj->GetData( aData, sMimeType ) ) 379*cdf0e10cSrcweir { 380*cdf0e10cSrcweir DataChanged( sMimeType, aData ); 381*cdf0e10cSrcweir //JP 13.07.00: Bug 76817 - for manual Updates there is no 382*cdf0e10cSrcweir // need to hold the ServerObject 383*cdf0e10cSrcweir if( OBJECT_CLIENT_DDE == nObjType && 384*cdf0e10cSrcweir LINKUPDATE_ONCALL == GetUpdateMode() && xObj.Is() ) 385*cdf0e10cSrcweir xObj->RemoveAllDataAdvise( this ); 386*cdf0e10cSrcweir return sal_True; 387*cdf0e10cSrcweir } 388*cdf0e10cSrcweir if( xObj.Is() ) 389*cdf0e10cSrcweir { 390*cdf0e10cSrcweir // sollten wir asynschron sein? 391*cdf0e10cSrcweir if( xObj->IsPending() ) 392*cdf0e10cSrcweir return sal_True; 393*cdf0e10cSrcweir 394*cdf0e10cSrcweir // dann brauchen wir das Object auch nicht mehr 395*cdf0e10cSrcweir AddNextRef(); 396*cdf0e10cSrcweir Disconnect(); 397*cdf0e10cSrcweir ReleaseRef(); 398*cdf0e10cSrcweir } 399*cdf0e10cSrcweir } 400*cdf0e10cSrcweir } 401*cdf0e10cSrcweir return sal_False; 402*cdf0e10cSrcweir } 403*cdf0e10cSrcweir 404*cdf0e10cSrcweir 405*cdf0e10cSrcweir sal_uInt16 SvBaseLink::GetUpdateMode() const 406*cdf0e10cSrcweir { 407*cdf0e10cSrcweir return ( OBJECT_CLIENT_SO & nObjType ) 408*cdf0e10cSrcweir ? pImplData->ClientType.nUpdateMode 409*cdf0e10cSrcweir : sal::static_int_cast< sal_uInt16 >( LINKUPDATE_ONCALL ); 410*cdf0e10cSrcweir } 411*cdf0e10cSrcweir 412*cdf0e10cSrcweir 413*cdf0e10cSrcweir void SvBaseLink::_GetRealObject( sal_Bool bConnect) 414*cdf0e10cSrcweir { 415*cdf0e10cSrcweir if( !pImpl->m_pLinkMgr ) 416*cdf0e10cSrcweir return; 417*cdf0e10cSrcweir 418*cdf0e10cSrcweir DBG_ASSERT( !xObj.Is(), "object already exist" ); 419*cdf0e10cSrcweir 420*cdf0e10cSrcweir if( OBJECT_CLIENT_DDE == nObjType ) 421*cdf0e10cSrcweir { 422*cdf0e10cSrcweir String sServer; 423*cdf0e10cSrcweir if( pImpl->m_pLinkMgr->GetDisplayNames( this, &sServer ) && 424*cdf0e10cSrcweir sServer == GetpApp()->GetAppName() ) // interner Link !!! 425*cdf0e10cSrcweir { 426*cdf0e10cSrcweir // damit der Internal - Link erzeugt werden kann !!! 427*cdf0e10cSrcweir nObjType = OBJECT_INTERN; 428*cdf0e10cSrcweir xObj = pImpl->m_pLinkMgr->CreateObj( this ); 429*cdf0e10cSrcweir 430*cdf0e10cSrcweir pImplData->ClientType.bIntrnlLnk = sal_True; 431*cdf0e10cSrcweir nObjType = OBJECT_CLIENT_DDE; // damit wir wissen was es mal war !! 432*cdf0e10cSrcweir } 433*cdf0e10cSrcweir else 434*cdf0e10cSrcweir { 435*cdf0e10cSrcweir pImplData->ClientType.bIntrnlLnk = sal_False; 436*cdf0e10cSrcweir xObj = pImpl->m_pLinkMgr->CreateObj( this ); 437*cdf0e10cSrcweir } 438*cdf0e10cSrcweir } 439*cdf0e10cSrcweir else if( (OBJECT_CLIENT_SO & nObjType) ) 440*cdf0e10cSrcweir xObj = pImpl->m_pLinkMgr->CreateObj( this ); 441*cdf0e10cSrcweir 442*cdf0e10cSrcweir if( bConnect && ( !xObj.Is() || !xObj->Connect( this ) ) ) 443*cdf0e10cSrcweir Disconnect(); 444*cdf0e10cSrcweir } 445*cdf0e10cSrcweir 446*cdf0e10cSrcweir sal_uIntPtr SvBaseLink::GetContentType() const 447*cdf0e10cSrcweir { 448*cdf0e10cSrcweir if( OBJECT_CLIENT_SO & nObjType ) 449*cdf0e10cSrcweir return pImplData->ClientType.nCntntType; 450*cdf0e10cSrcweir 451*cdf0e10cSrcweir return 0; // alle Formate ? 452*cdf0e10cSrcweir } 453*cdf0e10cSrcweir 454*cdf0e10cSrcweir 455*cdf0e10cSrcweir sal_Bool SvBaseLink::SetContentType( sal_uIntPtr nType ) 456*cdf0e10cSrcweir { 457*cdf0e10cSrcweir if( OBJECT_CLIENT_SO & nObjType ) 458*cdf0e10cSrcweir { 459*cdf0e10cSrcweir pImplData->ClientType.nCntntType = nType; 460*cdf0e10cSrcweir return sal_True; 461*cdf0e10cSrcweir } 462*cdf0e10cSrcweir return sal_False; 463*cdf0e10cSrcweir } 464*cdf0e10cSrcweir 465*cdf0e10cSrcweir LinkManager* SvBaseLink::GetLinkManager() 466*cdf0e10cSrcweir { 467*cdf0e10cSrcweir return pImpl->m_pLinkMgr; 468*cdf0e10cSrcweir } 469*cdf0e10cSrcweir 470*cdf0e10cSrcweir const LinkManager* SvBaseLink::GetLinkManager() const 471*cdf0e10cSrcweir { 472*cdf0e10cSrcweir return pImpl->m_pLinkMgr; 473*cdf0e10cSrcweir } 474*cdf0e10cSrcweir 475*cdf0e10cSrcweir void SvBaseLink::SetLinkManager( LinkManager* _pMgr ) 476*cdf0e10cSrcweir { 477*cdf0e10cSrcweir pImpl->m_pLinkMgr = _pMgr; 478*cdf0e10cSrcweir } 479*cdf0e10cSrcweir 480*cdf0e10cSrcweir void SvBaseLink::Disconnect() 481*cdf0e10cSrcweir { 482*cdf0e10cSrcweir if( xObj.Is() ) 483*cdf0e10cSrcweir { 484*cdf0e10cSrcweir xObj->RemoveAllDataAdvise( this ); 485*cdf0e10cSrcweir xObj->RemoveConnectAdvise( this ); 486*cdf0e10cSrcweir xObj.Clear(); 487*cdf0e10cSrcweir } 488*cdf0e10cSrcweir } 489*cdf0e10cSrcweir 490*cdf0e10cSrcweir void SvBaseLink::DataChanged( const String &, const ::com::sun::star::uno::Any & ) 491*cdf0e10cSrcweir { 492*cdf0e10cSrcweir switch( nObjType ) 493*cdf0e10cSrcweir { 494*cdf0e10cSrcweir case OBJECT_DDE_EXTERN: 495*cdf0e10cSrcweir if( pImplData->DDEType.pItem ) 496*cdf0e10cSrcweir pImplData->DDEType.pItem->Notify(); 497*cdf0e10cSrcweir break; 498*cdf0e10cSrcweir } 499*cdf0e10cSrcweir } 500*cdf0e10cSrcweir 501*cdf0e10cSrcweir void SvBaseLink::Edit( Window* pParent, const Link& rEndEditHdl ) 502*cdf0e10cSrcweir { 503*cdf0e10cSrcweir pImpl->m_pParentWin = pParent; 504*cdf0e10cSrcweir pImpl->m_aEndEditLink = rEndEditHdl; 505*cdf0e10cSrcweir pImpl->m_bIsConnect = ( xObj.Is() != sal_False ); 506*cdf0e10cSrcweir if( !pImpl->m_bIsConnect ) 507*cdf0e10cSrcweir _GetRealObject( xObj.Is() ); 508*cdf0e10cSrcweir 509*cdf0e10cSrcweir bool bAsync = false; 510*cdf0e10cSrcweir Link aLink = LINK( this, SvBaseLink, EndEditHdl ); 511*cdf0e10cSrcweir 512*cdf0e10cSrcweir if( OBJECT_CLIENT_SO & nObjType && pImplData->ClientType.bIntrnlLnk ) 513*cdf0e10cSrcweir { 514*cdf0e10cSrcweir if( pImpl->m_pLinkMgr ) 515*cdf0e10cSrcweir { 516*cdf0e10cSrcweir SvLinkSourceRef ref = pImpl->m_pLinkMgr->CreateObj( this ); 517*cdf0e10cSrcweir if( ref.Is() ) 518*cdf0e10cSrcweir { 519*cdf0e10cSrcweir ref->Edit( pParent, this, aLink ); 520*cdf0e10cSrcweir bAsync = true; 521*cdf0e10cSrcweir } 522*cdf0e10cSrcweir } 523*cdf0e10cSrcweir } 524*cdf0e10cSrcweir else 525*cdf0e10cSrcweir { 526*cdf0e10cSrcweir xObj->Edit( pParent, this, aLink ); 527*cdf0e10cSrcweir bAsync = true; 528*cdf0e10cSrcweir } 529*cdf0e10cSrcweir 530*cdf0e10cSrcweir if ( !bAsync ) 531*cdf0e10cSrcweir { 532*cdf0e10cSrcweir ExecuteEdit( String() ); 533*cdf0e10cSrcweir bWasLastEditOK = sal_False; 534*cdf0e10cSrcweir if ( pImpl->m_aEndEditLink.IsSet() ) 535*cdf0e10cSrcweir pImpl->m_aEndEditLink.Call( this ); 536*cdf0e10cSrcweir } 537*cdf0e10cSrcweir } 538*cdf0e10cSrcweir 539*cdf0e10cSrcweir bool SvBaseLink::ExecuteEdit( const String& _rNewName ) 540*cdf0e10cSrcweir { 541*cdf0e10cSrcweir if( _rNewName.Len() != 0 ) 542*cdf0e10cSrcweir { 543*cdf0e10cSrcweir SetLinkSourceName( _rNewName ); 544*cdf0e10cSrcweir if( !Update() ) 545*cdf0e10cSrcweir { 546*cdf0e10cSrcweir String sApp, sTopic, sItem, sError; 547*cdf0e10cSrcweir pImpl->m_pLinkMgr->GetDisplayNames( this, &sApp, &sTopic, &sItem ); 548*cdf0e10cSrcweir if( nObjType == OBJECT_CLIENT_DDE ) 549*cdf0e10cSrcweir { 550*cdf0e10cSrcweir sError = SfxResId( STR_DDE_ERROR ); 551*cdf0e10cSrcweir 552*cdf0e10cSrcweir sal_uInt16 nFndPos = sError.Search( '%' ); 553*cdf0e10cSrcweir if( STRING_NOTFOUND != nFndPos ) 554*cdf0e10cSrcweir { 555*cdf0e10cSrcweir sError.Erase( nFndPos, 1 ).Insert( sApp, nFndPos ); 556*cdf0e10cSrcweir nFndPos = nFndPos + sApp.Len(); 557*cdf0e10cSrcweir } 558*cdf0e10cSrcweir if( STRING_NOTFOUND != ( nFndPos = sError.Search( '%', nFndPos ))) 559*cdf0e10cSrcweir { 560*cdf0e10cSrcweir sError.Erase( nFndPos, 1 ).Insert( sTopic, nFndPos ); 561*cdf0e10cSrcweir nFndPos = nFndPos + sTopic.Len(); 562*cdf0e10cSrcweir } 563*cdf0e10cSrcweir if( STRING_NOTFOUND != ( nFndPos = sError.Search( '%', nFndPos ))) 564*cdf0e10cSrcweir sError.Erase( nFndPos, 1 ).Insert( sItem, nFndPos ); 565*cdf0e10cSrcweir } 566*cdf0e10cSrcweir else 567*cdf0e10cSrcweir return false; 568*cdf0e10cSrcweir 569*cdf0e10cSrcweir ErrorBox( pImpl->m_pParentWin, WB_OK, sError ).Execute(); 570*cdf0e10cSrcweir } 571*cdf0e10cSrcweir } 572*cdf0e10cSrcweir else if( !pImpl->m_bIsConnect ) 573*cdf0e10cSrcweir Disconnect(); 574*cdf0e10cSrcweir pImpl->m_bIsConnect = false; 575*cdf0e10cSrcweir return true; 576*cdf0e10cSrcweir } 577*cdf0e10cSrcweir 578*cdf0e10cSrcweir void SvBaseLink::Closed() 579*cdf0e10cSrcweir { 580*cdf0e10cSrcweir if( xObj.Is() ) 581*cdf0e10cSrcweir // beim Advise Abmelden 582*cdf0e10cSrcweir xObj->RemoveAllDataAdvise( this ); 583*cdf0e10cSrcweir } 584*cdf0e10cSrcweir 585*cdf0e10cSrcweir FileDialogHelper* SvBaseLink::GetFileDialog( sal_uInt32 nFlags, const String& rFactory ) const 586*cdf0e10cSrcweir { 587*cdf0e10cSrcweir if ( pImpl->m_pFileDlg ) 588*cdf0e10cSrcweir delete pImpl->m_pFileDlg; 589*cdf0e10cSrcweir pImpl->m_pFileDlg = new FileDialogHelper( nFlags, rFactory ); 590*cdf0e10cSrcweir return pImpl->m_pFileDlg; 591*cdf0e10cSrcweir } 592*cdf0e10cSrcweir 593*cdf0e10cSrcweir ImplDdeItem::~ImplDdeItem() 594*cdf0e10cSrcweir { 595*cdf0e10cSrcweir bIsInDTOR = sal_True; 596*cdf0e10cSrcweir // damit im Disconnect nicht jemand auf die Idee kommt, den Pointer zu 597*cdf0e10cSrcweir // loeschen!! 598*cdf0e10cSrcweir SvBaseLinkRef aRef( pLink ); 599*cdf0e10cSrcweir aRef->Disconnect(); 600*cdf0e10cSrcweir } 601*cdf0e10cSrcweir 602*cdf0e10cSrcweir DdeData* ImplDdeItem::Get( sal_uIntPtr nFormat ) 603*cdf0e10cSrcweir { 604*cdf0e10cSrcweir if( pLink->GetObj() ) 605*cdf0e10cSrcweir { 606*cdf0e10cSrcweir // ist das noch gueltig? 607*cdf0e10cSrcweir if( bIsValidData && nFormat == aData.GetFormat() ) 608*cdf0e10cSrcweir return &aData; 609*cdf0e10cSrcweir 610*cdf0e10cSrcweir Any aValue; 611*cdf0e10cSrcweir String sMimeType( SotExchange::GetFormatMimeType( nFormat )); 612*cdf0e10cSrcweir if( pLink->GetObj()->GetData( aValue, sMimeType ) ) 613*cdf0e10cSrcweir { 614*cdf0e10cSrcweir if( aValue >>= aSeq ) 615*cdf0e10cSrcweir { 616*cdf0e10cSrcweir aData = DdeData( (const char *)aSeq.getConstArray(), aSeq.getLength(), nFormat ); 617*cdf0e10cSrcweir 618*cdf0e10cSrcweir bIsValidData = sal_True; 619*cdf0e10cSrcweir return &aData; 620*cdf0e10cSrcweir } 621*cdf0e10cSrcweir } 622*cdf0e10cSrcweir } 623*cdf0e10cSrcweir aSeq.realloc( 0 ); 624*cdf0e10cSrcweir bIsValidData = sal_False; 625*cdf0e10cSrcweir return 0; 626*cdf0e10cSrcweir } 627*cdf0e10cSrcweir 628*cdf0e10cSrcweir 629*cdf0e10cSrcweir sal_Bool ImplDdeItem::Put( const DdeData* ) 630*cdf0e10cSrcweir { 631*cdf0e10cSrcweir DBG_ERROR( "ImplDdeItem::Put not implemented" ); 632*cdf0e10cSrcweir return sal_False; 633*cdf0e10cSrcweir } 634*cdf0e10cSrcweir 635*cdf0e10cSrcweir 636*cdf0e10cSrcweir void ImplDdeItem::AdviseLoop( sal_Bool bOpen ) 637*cdf0e10cSrcweir { 638*cdf0e10cSrcweir // Verbindung wird geschlossen, also Link abmelden 639*cdf0e10cSrcweir if( pLink->GetObj() ) 640*cdf0e10cSrcweir { 641*cdf0e10cSrcweir if( bOpen ) 642*cdf0e10cSrcweir { 643*cdf0e10cSrcweir // es wird wieder eine Verbindung hergestellt 644*cdf0e10cSrcweir if( OBJECT_DDE_EXTERN == pLink->GetObjType() ) 645*cdf0e10cSrcweir { 646*cdf0e10cSrcweir pLink->GetObj()->AddDataAdvise( pLink, String::CreateFromAscii( "text/plain;charset=utf-16" ), ADVISEMODE_NODATA ); 647*cdf0e10cSrcweir pLink->GetObj()->AddConnectAdvise( pLink ); 648*cdf0e10cSrcweir } 649*cdf0e10cSrcweir } 650*cdf0e10cSrcweir else 651*cdf0e10cSrcweir { 652*cdf0e10cSrcweir // damit im Disconnect nicht jemand auf die Idee kommt, 653*cdf0e10cSrcweir // den Pointer zu loeschen!! 654*cdf0e10cSrcweir SvBaseLinkRef aRef( pLink ); 655*cdf0e10cSrcweir aRef->Disconnect(); 656*cdf0e10cSrcweir } 657*cdf0e10cSrcweir } 658*cdf0e10cSrcweir } 659*cdf0e10cSrcweir 660*cdf0e10cSrcweir 661*cdf0e10cSrcweir static DdeTopic* FindTopic( const String & rLinkName, sal_uInt16* pItemStt ) 662*cdf0e10cSrcweir { 663*cdf0e10cSrcweir if( 0 == rLinkName.Len() ) 664*cdf0e10cSrcweir return 0; 665*cdf0e10cSrcweir 666*cdf0e10cSrcweir String sNm( rLinkName ); 667*cdf0e10cSrcweir sal_uInt16 nTokenPos = 0; 668*cdf0e10cSrcweir String sService( sNm.GetToken( 0, cTokenSeperator, nTokenPos ) ); 669*cdf0e10cSrcweir 670*cdf0e10cSrcweir DdeServices& rSvc = DdeService::GetServices(); 671*cdf0e10cSrcweir for( DdeService* pService = rSvc.First(); pService; 672*cdf0e10cSrcweir pService = rSvc.Next() ) 673*cdf0e10cSrcweir if( pService->GetName() == sService ) 674*cdf0e10cSrcweir { 675*cdf0e10cSrcweir // dann suchen wir uns das Topic 676*cdf0e10cSrcweir String sTopic( sNm.GetToken( 0, cTokenSeperator, nTokenPos ) ); 677*cdf0e10cSrcweir if( pItemStt ) 678*cdf0e10cSrcweir *pItemStt = nTokenPos; 679*cdf0e10cSrcweir 680*cdf0e10cSrcweir DdeTopics& rTopics = pService->GetTopics(); 681*cdf0e10cSrcweir 682*cdf0e10cSrcweir for( int i = 0; i < 2; ++i ) 683*cdf0e10cSrcweir { 684*cdf0e10cSrcweir for( DdeTopic* pTopic = rTopics.First(); pTopic; 685*cdf0e10cSrcweir pTopic = rTopics.Next() ) 686*cdf0e10cSrcweir if( pTopic->GetName() == sTopic ) 687*cdf0e10cSrcweir return pTopic; 688*cdf0e10cSrcweir 689*cdf0e10cSrcweir // Topic nicht gefunden ? 690*cdf0e10cSrcweir // dann versuchen wir ihn mal anzulegen 691*cdf0e10cSrcweir if( i || !pService->MakeTopic( sTopic ) ) 692*cdf0e10cSrcweir break; // hat nicht geklappt, also raus 693*cdf0e10cSrcweir } 694*cdf0e10cSrcweir break; 695*cdf0e10cSrcweir } 696*cdf0e10cSrcweir return 0; 697*cdf0e10cSrcweir } 698*cdf0e10cSrcweir 699*cdf0e10cSrcweir } 700