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 // my own include 24 //______________________________________________________________________________________________________________ 25 26 #include "framecontrol.hxx" 27 28 //______________________________________________________________________________________________________________ 29 // includes of other projects 30 //______________________________________________________________________________________________________________ 31 #include <com/sun/star/frame/XDispatchProvider.hpp> 32 #include <com/sun/star/util/XURLTransformer.hpp> 33 #include <com/sun/star/frame/XDispatch.hpp> 34 #include <com/sun/star/frame/FrameSearchFlag.hpp> 35 #include <com/sun/star/frame/FrameSearchFlag.hpp> 36 #include <com/sun/star/beans/PropertyAttribute.hpp> 37 #include <cppuhelper/typeprovider.hxx> 38 #include <vos/diagnose.hxx> 39 40 //______________________________________________________________________________________________________________ 41 // include of my own project 42 //______________________________________________________________________________________________________________ 43 44 //______________________________________________________________________________________________________________ 45 // namespaces 46 //______________________________________________________________________________________________________________ 47 48 using namespace ::rtl ; 49 using namespace ::osl ; 50 using namespace ::cppu ; 51 using namespace ::com::sun::star::uno ; 52 using namespace ::com::sun::star::lang ; 53 using namespace ::com::sun::star::beans ; 54 using namespace ::com::sun::star::awt ; 55 using namespace ::com::sun::star::frame ; 56 using namespace ::com::sun::star::util ; 57 58 namespace unocontrols{ 59 60 //______________________________________________________________________________________________________________ 61 // construct/destruct 62 //______________________________________________________________________________________________________________ 63 64 FrameControl::FrameControl( const Reference< XMultiServiceFactory >& xFactory ) 65 : BaseControl ( xFactory ) 66 , OBroadcastHelper ( m_aMutex ) 67 , OPropertySetHelper ( *SAL_STATIC_CAST( OBroadcastHelper *, this ) ) 68 , m_aInterfaceContainer ( m_aMutex ) 69 , m_aConnectionPointContainer ( m_aMutex ) 70 { 71 } 72 73 FrameControl::~FrameControl() 74 { 75 } 76 77 //____________________________________________________________________________________________________________ 78 // XInterface 79 //____________________________________________________________________________________________________________ 80 81 Any SAL_CALL FrameControl::queryInterface( const Type& rType ) 82 { 83 // Attention: 84 // Don't use mutex or guard in this method!!! Is a method of XInterface. 85 Any aReturn ; 86 Reference< XInterface > xDel = BaseControl::impl_getDelegator(); 87 if ( xDel.is() ) 88 { 89 // If a delegator exists, forward question to his queryInterface. 90 // Delegator will ask his own queryAggregation! 91 aReturn = xDel->queryInterface( rType ); 92 } 93 else 94 { 95 // If a delegator unknown, forward question to own queryAggregation. 96 aReturn = queryAggregation( rType ); 97 } 98 99 return aReturn ; 100 } 101 102 //____________________________________________________________________________________________________________ 103 // XInterface 104 //____________________________________________________________________________________________________________ 105 106 void SAL_CALL FrameControl::acquire() throw() 107 { 108 // Attention: 109 // Don't use mutex or guard in this method!!! Is a method of XInterface. 110 111 // Forward to baseclass 112 BaseControl::acquire(); 113 } 114 115 //____________________________________________________________________________________________________________ 116 // XInterface 117 //____________________________________________________________________________________________________________ 118 119 void SAL_CALL FrameControl::release() throw() 120 { 121 // Attention: 122 // Don't use mutex or guard in this method!!! Is a method of XInterface. 123 124 // Forward to baseclass 125 BaseControl::release(); 126 } 127 128 //____________________________________________________________________________________________________________ 129 // XTypeProvider 130 //____________________________________________________________________________________________________________ 131 132 Sequence< Type > SAL_CALL FrameControl::getTypes() 133 { 134 // Optimize this method ! 135 // We initialize a static variable only one time. And we don't must use a mutex at every call! 136 // For the first call; pTypeCollection is NULL - for the second call pTypeCollection is different from NULL! 137 static OTypeCollection* pTypeCollection = NULL ; 138 139 if ( pTypeCollection == NULL ) 140 { 141 // Ready for multithreading; get global mutex for first call of this method only! see before 142 MutexGuard aGuard( Mutex::getGlobalMutex() ); 143 144 // Control these pointer again ... it can be, that another instance will be faster then these! 145 if ( pTypeCollection == NULL ) 146 { 147 // Create a static typecollection ... 148 static OTypeCollection aTypeCollection ( ::getCppuType(( const Reference< XControlModel >*)NULL ) , 149 ::getCppuType(( const Reference< XControlContainer >*)NULL ) , 150 ::getCppuType(( const Reference< XConnectionPointContainer >*)NULL ) , 151 BaseControl::getTypes() 152 ); 153 // ... and set his address to static pointer! 154 pTypeCollection = &aTypeCollection ; 155 } 156 } 157 158 return pTypeCollection->getTypes(); 159 } 160 161 //____________________________________________________________________________________________________________ 162 // XAggregation 163 //____________________________________________________________________________________________________________ 164 165 Any SAL_CALL FrameControl::queryAggregation( const Type& aType ) 166 { 167 // Ask for my own supported interfaces ... 168 // Attention: XTypeProvider and XInterface are supported by OComponentHelper! 169 Any aReturn ( ::cppu::queryInterface( aType , 170 static_cast< XControlModel* > ( this ) , 171 static_cast< XConnectionPointContainer* > ( this ) 172 ) 173 ); 174 175 // If searched interface not supported by this class ... 176 if ( aReturn.hasValue() == sal_False ) 177 { 178 // ... ask baseclasses. 179 aReturn = OPropertySetHelper::queryInterface( aType ); 180 if ( aReturn.hasValue() == sal_False ) 181 { 182 aReturn = BaseControl::queryAggregation( aType ); 183 } 184 } 185 186 return aReturn ; 187 } 188 189 //____________________________________________________________________________________________________________ 190 // XControl 191 //____________________________________________________________________________________________________________ 192 193 void SAL_CALL FrameControl::createPeer( const Reference< XToolkit >& xToolkit , 194 const Reference< XWindowPeer >& xParentPeer ) 195 { 196 BaseControl::createPeer( xToolkit, xParentPeer ); 197 if ( impl_getPeerWindow().is() ) 198 { 199 if( m_sComponentURL.getLength() > 0 ) 200 { 201 impl_createFrame( getPeer(), m_sComponentURL, m_seqLoaderArguments ); 202 } 203 } 204 } 205 206 //____________________________________________________________________________________________________________ 207 // XControl 208 //____________________________________________________________________________________________________________ 209 210 sal_Bool SAL_CALL FrameControl::setModel( const Reference< XControlModel >& /*xModel*/ ) 211 { 212 // We have no model. 213 return sal_False ; 214 } 215 216 //____________________________________________________________________________________________________________ 217 // XControl 218 //____________________________________________________________________________________________________________ 219 220 Reference< XControlModel > SAL_CALL FrameControl::getModel() 221 { 222 // We have no model. 223 return Reference< XControlModel >(); 224 } 225 226 //____________________________________________________________________________________________________________ 227 // XControl 228 //____________________________________________________________________________________________________________ 229 230 void SAL_CALL FrameControl::dispose() 231 { 232 impl_deleteFrame(); 233 BaseControl::dispose(); 234 } 235 236 //____________________________________________________________________________________________________________ 237 // XView 238 //____________________________________________________________________________________________________________ 239 240 sal_Bool SAL_CALL FrameControl::setGraphics( const Reference< XGraphics >& /*xDevice*/ ) 241 { 242 // it is not possible to print this control 243 return sal_False ; 244 } 245 246 //____________________________________________________________________________________________________________ 247 // XView 248 //____________________________________________________________________________________________________________ 249 250 Reference< XGraphics > SAL_CALL FrameControl::getGraphics() 251 { 252 // when it's not possible to set graphics ! then it's possible to return null 253 return Reference< XGraphics >(); 254 } 255 256 //____________________________________________________________________________________________________________ 257 // XConnectionPointContainer 258 //____________________________________________________________________________________________________________ 259 260 Sequence< Type > SAL_CALL FrameControl::getConnectionPointTypes() 261 { 262 // Forwarded to helper class 263 return m_aConnectionPointContainer.getConnectionPointTypes(); 264 } 265 266 //____________________________________________________________________________________________________________ 267 // XConnectionPointContainer 268 //____________________________________________________________________________________________________________ 269 270 Reference< XConnectionPoint > SAL_CALL FrameControl::queryConnectionPoint( const Type& aType ) 271 { 272 // Forwarded to helper class 273 return m_aConnectionPointContainer.queryConnectionPoint( aType ); 274 } 275 276 //____________________________________________________________________________________________________________ 277 // XConnectionPointContainer 278 //____________________________________________________________________________________________________________ 279 280 void SAL_CALL FrameControl::advise( const Type& aType , 281 const Reference< XInterface >& xListener ) 282 { 283 // Forwarded to helper class 284 m_aConnectionPointContainer.advise( aType, xListener ); 285 } 286 287 //____________________________________________________________________________________________________________ 288 // XConnectionPointContainer 289 //____________________________________________________________________________________________________________ 290 291 void SAL_CALL FrameControl::unadvise( const Type& aType , 292 const Reference< XInterface >& xListener ) 293 { 294 // Forwarded to helper class 295 m_aConnectionPointContainer.unadvise( aType, xListener ); 296 } 297 298 //____________________________________________________________________________________________________________ 299 // impl but public method to register service 300 //____________________________________________________________________________________________________________ 301 302 const Sequence< OUString > FrameControl::impl_getStaticSupportedServiceNames() 303 { 304 MutexGuard aGuard( Mutex::getGlobalMutex() ); 305 Sequence< OUString > seqServiceNames( 1 ); 306 seqServiceNames.getArray() [0] = OUString::createFromAscii( SERVICENAME_FRAMECONTROL ); 307 return seqServiceNames ; 308 } 309 310 //____________________________________________________________________________________________________________ 311 // impl but public method to register service 312 //____________________________________________________________________________________________________________ 313 314 const OUString FrameControl::impl_getStaticImplementationName() 315 { 316 return OUString::createFromAscii( IMPLEMENTATIONNAME_FRAMECONTROL ); 317 } 318 319 //____________________________________________________________________________________________________________ 320 // OPropertySetHelper 321 //____________________________________________________________________________________________________________ 322 323 sal_Bool FrameControl::convertFastPropertyValue( Any& rConvertedValue , 324 Any& rOldValue , 325 sal_Int32 nHandle , 326 const Any& rValue ) 327 { 328 sal_Bool bReturn = sal_False ; 329 switch (nHandle) 330 { 331 case PROPERTYHANDLE_COMPONENTURL : rConvertedValue = rValue ; 332 rOldValue <<= m_sComponentURL ; 333 bReturn = sal_True ; 334 break ; 335 336 case PROPERTYHANDLE_LOADERARGUMENTS : rConvertedValue = rValue ; 337 rOldValue <<= m_seqLoaderArguments ; 338 bReturn = sal_True ; 339 break ; 340 } 341 342 if ( bReturn == sal_False ) 343 { 344 throw IllegalArgumentException(); 345 } 346 347 return bReturn ; 348 } 349 350 //____________________________________________________________________________________________________________ 351 // OPropertySetHelper 352 //____________________________________________________________________________________________________________ 353 354 void FrameControl::setFastPropertyValue_NoBroadcast( sal_Int32 nHandle , 355 const Any& rValue ) 356 { 357 // this method only set the value 358 MutexGuard aGuard (m_aMutex) ; 359 switch (nHandle) 360 { 361 case PROPERTYHANDLE_COMPONENTURL : rValue >>= m_sComponentURL ; 362 if (getPeer().is()) 363 { 364 impl_createFrame ( getPeer(), m_sComponentURL, m_seqLoaderArguments ) ; 365 } 366 break ; 367 368 case PROPERTYHANDLE_LOADERARGUMENTS : rValue >>= m_seqLoaderArguments ; 369 break ; 370 371 default : VOS_ENSHURE ( nHandle == -1, ERRORTEXT_VOSENSHURE ) ; 372 } 373 } 374 375 //____________________________________________________________________________________________________________ 376 // OPropertySetHelper 377 //____________________________________________________________________________________________________________ 378 379 void FrameControl::getFastPropertyValue( Any& rRet , 380 sal_Int32 nHandle ) const 381 { 382 MutexGuard aGuard ( Mutex::getGlobalMutex() ) ; 383 384 switch (nHandle) 385 { 386 case PROPERTYHANDLE_COMPONENTURL : rRet <<= m_sComponentURL ; 387 break ; 388 389 case PROPERTYHANDLE_LOADERARGUMENTS : rRet <<= m_seqLoaderArguments ; 390 break ; 391 392 case PROPERTYHANDLE_FRAME : rRet <<= m_xFrame ; 393 break ; 394 395 default : VOS_ENSHURE ( nHandle == -1, ERRORTEXT_VOSENSHURE ) ; 396 } 397 } 398 399 //____________________________________________________________________________________________________________ 400 // OPropertySetHelper 401 //____________________________________________________________________________________________________________ 402 403 IPropertyArrayHelper& FrameControl::getInfoHelper() 404 { 405 // Create a table that map names to index values. 406 static OPropertyArrayHelper* pInfo ; 407 408 if (!pInfo) 409 { 410 // global method must be guarded 411 MutexGuard aGuard ( Mutex::getGlobalMutex() ) ; 412 413 if (!pInfo) 414 { 415 pInfo = new OPropertyArrayHelper( impl_getStaticPropertyDescriptor(), sal_True ); 416 } 417 } 418 419 return *pInfo ; 420 } 421 /* 422 //-------------------------------------------------------------------------------------------------- 423 // start OConnectionPointContainerHelper 424 //-------------------------------------------------------------------------------------------------- 425 Uik* FrameControl::getConnectionPointUiks ( sal_Int32* pCount ) const 426 { 427 static Uik szUiks[] = 428 { 429 ((XEventListener*)NULL)->getSmartUik (), 430 ::getCppuType((const Reference< XPropertyChangeListener >*)0), 431 ::getCppuType((const Reference< XVetoableChangeListener >*)0), 432 ::getCppuType((const Reference< XPropertiesChangeListener >*)0) 433 } ; 434 435 *pCount = 4 ; 436 437 return szUiks ; 438 } 439 //-------------------------------------------------------------------------------------------------- 440 // end OConnectionPointContainerHelper 441 //-------------------------------------------------------------------------------------------------- 442 */ 443 444 //____________________________________________________________________________________________________________ 445 // OPropertySetHelper 446 //____________________________________________________________________________________________________________ 447 448 Reference< XPropertySetInfo > SAL_CALL FrameControl::getPropertySetInfo() 449 { 450 // Optimize this method ! 451 // We initialize a static variable only one time. And we don't must use a mutex at every call! 452 // For the first call; pInfo is NULL - for the second call pInfo is different from NULL! 453 static Reference< XPropertySetInfo >* pInfo = (Reference< XPropertySetInfo >*)0 ; 454 if ( pInfo == (Reference< XPropertySetInfo >*)0 ) 455 { 456 // Ready for multithreading 457 MutexGuard aGuard ( Mutex::getGlobalMutex () ) ; 458 // Control this pointer again, another instance can be faster then these! 459 if ( pInfo == (Reference< XPropertySetInfo >*)0 ) 460 { 461 // Create structure of propertysetinfo for baseclass "OPropertySetHelper". 462 // (Use method "getInfoHelper()".) 463 static Reference< XPropertySetInfo > xInfo ( createPropertySetInfo ( getInfoHelper () ) ) ; 464 pInfo = &xInfo ; 465 } 466 } 467 return ( *pInfo ) ; 468 } 469 470 //____________________________________________________________________________________________________________ 471 // BaseControl 472 //____________________________________________________________________________________________________________ 473 474 WindowDescriptor* FrameControl::impl_getWindowDescriptor( const Reference< XWindowPeer >& xParentPeer ) 475 { 476 WindowDescriptor* pDescriptor = new WindowDescriptor ; 477 478 pDescriptor->Type = WindowClass_CONTAINER ; 479 pDescriptor->ParentIndex = -1 ; 480 pDescriptor->Parent = xParentPeer ; 481 pDescriptor->Bounds = getPosSize () ; 482 pDescriptor->WindowAttributes = 0 ; 483 484 return pDescriptor ; 485 } 486 487 //____________________________________________________________________________________________________________ 488 // private method 489 //____________________________________________________________________________________________________________ 490 491 void FrameControl::impl_createFrame( const Reference< XWindowPeer >& xPeer , 492 const OUString& rURL , 493 const Sequence< PropertyValue >& rArguments ) 494 { 495 Reference< XFrame > xOldFrame ; 496 Reference< XFrame > xNewFrame ; 497 498 { 499 MutexGuard aGuard ( m_aMutex ) ; 500 xOldFrame = m_xFrame ; 501 } 502 503 xNewFrame = Reference< XFrame > ( impl_getMultiServiceFactory()->createInstance ( OUString::createFromAscii( "com.sun.star.frame.Frame" ) ), UNO_QUERY ) ; 504 Reference< XDispatchProvider > xDSP ( xNewFrame, UNO_QUERY ) ; 505 506 if (xDSP.is()) 507 { 508 Reference< XWindow > xWP ( xPeer, UNO_QUERY ) ; 509 xNewFrame->initialize ( xWP ) ; 510 511 // option 512 //xFrame->setName( "WhatYouWant" ); 513 514 Reference< XURLTransformer > xTrans ( impl_getMultiServiceFactory()->createInstance ( OUString::createFromAscii( "com.sun.star.util.URLTransformer" ) ), UNO_QUERY ) ; 515 if(xTrans.is()) 516 { 517 // load file 518 URL aURL ; 519 520 aURL.Complete = rURL ; 521 xTrans->parseStrict( aURL ) ; 522 523 Reference< XDispatch > xDisp = xDSP->queryDispatch ( aURL, OUString (), FrameSearchFlag::SELF ) ; 524 if (xDisp.is()) 525 { 526 xDisp->dispatch ( aURL, rArguments ) ; 527 } 528 } 529 } 530 531 // set the frame 532 { 533 MutexGuard aGuard ( m_aMutex ) ; 534 m_xFrame = xNewFrame ; 535 } 536 537 // notify the listeners 538 sal_Int32 nFrameId = PROPERTYHANDLE_FRAME ; 539 Any aNewFrame ( &xNewFrame, ::getCppuType((const Reference< XFrame >*)0) ) ; 540 Any aOldFrame ( &xOldFrame, ::getCppuType((const Reference< XFrame >*)0) ) ; 541 542 fire ( &nFrameId, &aNewFrame, &aOldFrame, 1, sal_False ) ; 543 544 if (xOldFrame.is()) 545 { 546 xOldFrame->dispose () ; 547 } 548 } 549 550 //____________________________________________________________________________________________________________ 551 // private method 552 //____________________________________________________________________________________________________________ 553 554 void FrameControl::impl_deleteFrame() 555 { 556 Reference< XFrame > xOldFrame; 557 Reference< XFrame > xNullFrame; 558 559 { 560 // do not dispose the frame in this guarded section (deadlock?) 561 MutexGuard aGuard( m_aMutex ); 562 xOldFrame = m_xFrame; 563 m_xFrame = Reference< XFrame > (); 564 } 565 566 // notify the listeners 567 sal_Int32 nFrameId = PROPERTYHANDLE_FRAME; 568 Any aNewFrame( &xNullFrame, ::getCppuType((const Reference< XFrame >*)0) ); 569 Any aOldFrame( &xOldFrame, ::getCppuType((const Reference< XFrame >*)0) ); 570 fire( &nFrameId, &aNewFrame, &aOldFrame, 1, sal_False ); 571 572 // dispose the frame 573 if( xOldFrame.is() ) 574 xOldFrame->dispose(); 575 } 576 577 //____________________________________________________________________________________________________________ 578 // private method 579 //____________________________________________________________________________________________________________ 580 581 const Sequence< Property > FrameControl::impl_getStaticPropertyDescriptor() 582 { 583 // All Properties of this implementation. The array must be sorted! 584 static const Property pPropertys[PROPERTY_COUNT] = 585 { 586 Property( OUString::createFromAscii( PROPERTYNAME_COMPONENTURL ), PROPERTYHANDLE_COMPONENTURL , ::getCppuType((const OUString*)0) , PropertyAttribute::BOUND | PropertyAttribute::CONSTRAINED ), 587 Property( OUString::createFromAscii( PROPERTYNAME_FRAME ), PROPERTYHANDLE_FRAME , ::getCppuType((const Reference< XFrame >*)0) , PropertyAttribute::BOUND | PropertyAttribute::TRANSIENT ), 588 Property( OUString::createFromAscii( PROPERTYNAME_LOADERARGUMENTS ), PROPERTYHANDLE_LOADERARGUMENTS , ::getCppuType((const Sequence< PropertyValue >*)0), PropertyAttribute::BOUND | PropertyAttribute::CONSTRAINED ) 589 }; 590 591 static const Sequence< Property > seqPropertys( pPropertys, PROPERTY_COUNT ); 592 593 return seqPropertys ; 594 } 595 596 } // namespace unocontrols 597 598 /* vim: set noet sw=4 ts=4: */ 599