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_svl.hxx" 26 27 #ifndef _COM_SUN_STAR_LANG_XCOMPONENT_HPP_ 28 #include <com/sun/star/lang/XComponent.hpp> 29 #endif 30 31 #define _SVSTDARR_STRINGS 32 #define _SVSTDARR_STRINGSSORTDTOR 33 #define _SVSTDARR_BYTESTRINGS 34 #define _SVSTDARR_BYTESTRINGSSORTDTOR 35 36 #include <rtl/uuid.h> 37 #include <tools/tenccvt.hxx> 38 #include <comphelper/processfactory.hxx> 39 #include <unotools/intlwrapper.hxx> 40 #include <svl/smplhint.hxx> 41 #include <svl/poolitem.hxx> 42 #include <svl/itemset.hxx> 43 #include <svl/itempool.hxx> 44 #include <poolio.hxx> 45 #include <svl/filerec.hxx> 46 #include <svl/itemiter.hxx> 47 #include <svl/style.hxx> 48 #include <svl/svstdarr.hxx> 49 #include <unotools/syslocale.hxx> 50 #include <algorithm> 51 52 #define STYLESTREAM "SfxStyleSheets" 53 #define STYLESTREAM_VERSION sal_uInt16(50) 54 55 #ifdef DBG_UTIL 56 class DbgStyleSheetReferences 57 { 58 public: 59 DbgStyleSheetReferences() : mnStyles(0), mnPools(0) {} 60 ~DbgStyleSheetReferences() 61 { 62 OSL_TRACE("DbgStyleSheetReferences\nSfxStyleSheetBase left %ld\nSfxStyleSheetBasePool left %ld\n", mnStyles, mnPools ); 63 } 64 65 sal_uInt32 mnStyles; 66 sal_uInt32 mnPools; 67 } 68 aDbgStyleSheetReferences; 69 70 #endif 71 72 TYPEINIT0(SfxStyleSheetBase) 73 74 TYPEINIT3(SfxStyleSheet, SfxStyleSheetBase, SfxListener, SfxBroadcaster) 75 76 77 //========================================================================= 78 79 TYPEINIT1(SfxStyleSheetHint, SfxHint); 80 TYPEINIT1(SfxStyleSheetHintExtended, SfxStyleSheetHint); 81 TYPEINIT1(SfxStyleSheetPoolHint, SfxHint); 82 83 SfxStyleSheetHintExtended::SfxStyleSheetHintExtended 84 ( 85 sal_uInt16 nAction, // SFX_STYLESHEET_... (s.o.) 86 const String& rOldName 87 ) 88 : SfxStyleSheetHint( nAction ), 89 aName( rOldName ) 90 {} 91 SfxStyleSheetHintExtended::SfxStyleSheetHintExtended 92 ( 93 sal_uInt16 nAction, // SFX_STYLESHEET_... (s.o.) 94 const String& rOldName, 95 SfxStyleSheetBase& rStyleSheet // geh"ort weiterhin dem Aufrufer 96 ) 97 : SfxStyleSheetHint( nAction, rStyleSheet ), 98 aName( rOldName ) 99 {} 100 101 //------------------------------------------------------------------------- 102 103 SfxStyleSheetHint::SfxStyleSheetHint 104 ( 105 sal_uInt16 nAction, // SFX_STYLESHEET_... (s.o.) 106 SfxStyleSheetBase& rStyleSheet // geh"ort weiterhin dem Aufrufer 107 ) 108 : pStyleSh( &rStyleSheet ), 109 nHint( nAction ) 110 {} 111 112 SfxStyleSheetHint::SfxStyleSheetHint 113 ( 114 sal_uInt16 nAction // SFX_STYLESHEET_... (s.o.) 115 ) 116 : pStyleSh( NULL ), 117 nHint( nAction ) 118 {} 119 120 //========================================================================= 121 122 class SfxStyleSheetBasePool_Impl 123 { 124 public: 125 SfxStyles aStyles; 126 SfxStyleSheetIterator *pIter; 127 SfxStyleSheetBasePool_Impl() : pIter(0){} 128 ~SfxStyleSheetBasePool_Impl(){delete pIter;} 129 }; 130 131 132 //////////////////////////// SfxStyleSheetBase /////////////////////////////// 133 134 // Konstruktoren 135 136 SfxStyleSheetBase::SfxStyleSheetBase( const XubString& rName, SfxStyleSheetBasePool& r, SfxStyleFamily eFam, sal_uInt16 mask ) 137 : rPool( r ) 138 , nFamily( eFam ) 139 , aName( rName ) 140 , aParent() 141 , aFollow( rName ) 142 , pSet( NULL ) 143 , nMask(mask) 144 , nHelpId( 0 ) 145 , bMySet( sal_False ) 146 { 147 #ifdef DBG_UTIL 148 aDbgStyleSheetReferences.mnStyles++; 149 #endif 150 } 151 152 SfxStyleSheetBase::SfxStyleSheetBase( const SfxStyleSheetBase& r ) 153 : comphelper::OWeakTypeObject() 154 , rPool( r.rPool ) 155 , nFamily( r.nFamily ) 156 , aName( r.aName ) 157 , aParent( r.aParent ) 158 , aFollow( r.aFollow ) 159 , aHelpFile( r.aHelpFile ) 160 , nMask( r.nMask ) 161 , nHelpId( r.nHelpId ) 162 , bMySet( r.bMySet ) 163 { 164 #ifdef DBG_UTIL 165 aDbgStyleSheetReferences.mnStyles++; 166 #endif 167 if( r.pSet ) 168 pSet = bMySet ? new SfxItemSet( *r.pSet ) : r.pSet; 169 else 170 pSet = NULL; 171 } 172 173 static SfxStyleSheetBasePool& implGetStaticPool() 174 { 175 static SfxStyleSheetBasePool* pSheetPool = 0; 176 static SfxItemPool* pBasePool = 0; 177 if( !pSheetPool ) 178 { 179 UniString aName; 180 pBasePool = new SfxItemPool( aName, 0, 0, 0 ); 181 pSheetPool = new SfxStyleSheetBasePool(*pBasePool); 182 } 183 return *pSheetPool; 184 } 185 186 SfxStyleSheetBase::SfxStyleSheetBase() 187 : comphelper::OWeakTypeObject() 188 , rPool( implGetStaticPool() ) 189 { 190 } 191 192 SfxStyleSheetBase::~SfxStyleSheetBase() 193 { 194 #ifdef DBG_UTIL 195 --aDbgStyleSheetReferences.mnStyles; 196 #endif 197 198 if( bMySet ) 199 { 200 delete pSet; 201 pSet = 0; 202 } 203 } 204 205 sal_uInt16 SfxStyleSheetBase::GetVersion() const 206 { 207 return 0x0000; 208 } 209 210 // Namen aendern 211 212 const XubString& SfxStyleSheetBase::GetName() const 213 { 214 return aName; 215 } 216 217 sal_Bool SfxStyleSheetBase::SetName( const XubString& rName ) 218 { 219 if(rName.Len() == 0) 220 return sal_False; 221 if( aName != rName ) 222 { 223 String aOldName = aName; 224 SfxStyleSheetBase *pOther = rPool.Find( rName, nFamily ) ; 225 if ( pOther && pOther != this ) 226 return sal_False; 227 228 SfxStyleFamily eTmpFam=rPool.GetSearchFamily(); 229 sal_uInt16 nTmpMask=rPool.GetSearchMask(); 230 231 rPool.SetSearchMask(nFamily); 232 233 if ( aName.Len() ) 234 rPool.ChangeParent( aName, rName, sal_False ); 235 if ( aFollow.Equals( aName ) ) 236 aFollow = rName; 237 aName = rName; 238 rPool.SetSearchMask(eTmpFam, nTmpMask); 239 rPool.Broadcast( SfxStyleSheetHintExtended( 240 SFX_STYLESHEET_MODIFIED, aOldName, *this ) ); 241 } 242 return sal_True; 243 } 244 245 rtl::OUString SfxStyleSheetBase::GetDisplayName() const 246 { 247 if( maDisplayName.getLength() == 0 ) 248 { 249 return aName; 250 } 251 else 252 { 253 return maDisplayName; 254 } 255 } 256 257 void SfxStyleSheetBase::SetDisplayName( const rtl::OUString& rDisplayName ) 258 { 259 maDisplayName = rDisplayName; 260 } 261 262 // Parent aendern 263 264 const XubString& SfxStyleSheetBase::GetParent() const 265 { 266 return aParent; 267 } 268 269 sal_Bool SfxStyleSheetBase::SetParent( const XubString& rName ) 270 { 271 if ( rName == aName ) 272 return sal_False; 273 274 if( aParent != rName ) 275 { 276 SfxStyleSheetBase* pIter = rPool.Find(rName, nFamily); 277 if( rName.Len() && !pIter ) 278 { 279 DBG_ERROR( "StyleSheet-Parent nicht gefunden" ); 280 return sal_False; 281 } 282 // rekursive Verknuepfungen verhindern 283 if( aName.Len() ) 284 while(pIter) 285 { 286 if(pIter->GetName() == aName && aName != rName) 287 return sal_False; 288 pIter = rPool.Find(pIter->GetParent(), nFamily); 289 } 290 aParent = rName; 291 } 292 rPool.Broadcast( SfxStyleSheetHint( SFX_STYLESHEET_MODIFIED, *this ) ); 293 return sal_True; 294 } 295 296 // Follow aendern 297 298 const XubString& SfxStyleSheetBase::GetFollow() const 299 { 300 return aFollow; 301 } 302 303 sal_Bool SfxStyleSheetBase::SetFollow( const XubString& rName ) 304 { 305 if( aFollow != rName ) 306 { 307 if( !rPool.Find( rName, nFamily ) ) 308 { 309 DBG_ERROR( "StyleSheet-Follow nicht gefunden" ); 310 return sal_False; 311 } 312 aFollow = rName; 313 } 314 rPool.Broadcast( SfxStyleSheetHint( SFX_STYLESHEET_MODIFIED, *this ) ); 315 return sal_True; 316 } 317 318 // Itemset setzen. Die Dflt-Implementation legt ein neues Set an. 319 320 SfxItemSet& SfxStyleSheetBase::GetItemSet() 321 { 322 if( !pSet ) 323 { 324 pSet = new SfxItemSet( rPool.GetPool() ); 325 bMySet = sal_True; 326 } 327 return *pSet; 328 } 329 330 // Hilfe-Datei und -ID setzen und abfragen 331 332 sal_uLong SfxStyleSheetBase::GetHelpId( String& rFile ) 333 { 334 rFile = aHelpFile; 335 return nHelpId; 336 } 337 338 void SfxStyleSheetBase::SetHelpId( const String& rFile, sal_uLong nId ) 339 { 340 aHelpFile = rFile; 341 nHelpId = nId; 342 } 343 344 // Folgevorlage m"oglich? Default: Ja 345 346 sal_Bool SfxStyleSheetBase::HasFollowSupport() const 347 { 348 return sal_True; 349 } 350 351 // Basisvorlage m"oglich? Default: Ja 352 353 sal_Bool SfxStyleSheetBase::HasParentSupport() const 354 { 355 return sal_True; 356 } 357 358 // Basisvorlage uf NULL setzen m"oglich? Default: Nein 359 360 sal_Bool SfxStyleSheetBase::HasClearParentSupport() const 361 { 362 return sal_False; 363 } 364 365 // Defaultmaessig sind alle StyleSheets Used 366 367 sal_Bool SfxStyleSheetBase::IsUsed() const 368 { 369 return sal_True; 370 } 371 372 // eingestellte Attribute ausgeben 373 374 375 XubString SfxStyleSheetBase::GetDescription() 376 { 377 return GetDescription( SFX_MAPUNIT_CM ); 378 } 379 380 // eingestellte Attribute ausgeben 381 382 XubString SfxStyleSheetBase::GetDescription( SfxMapUnit eMetric ) 383 { 384 SfxItemIter aIter( GetItemSet() ); 385 XubString aDesc; 386 const SfxPoolItem* pItem = aIter.FirstItem(); 387 388 IntlWrapper aIntlWrapper(comphelper::getProcessServiceFactory(), 389 SvtSysLocale().GetLanguage()); 390 while ( pItem ) 391 { 392 XubString aItemPresentation; 393 394 if ( !IsInvalidItem( pItem ) && 395 rPool.GetPool().GetPresentation( 396 *pItem, SFX_ITEM_PRESENTATION_COMPLETE, 397 eMetric, aItemPresentation, &aIntlWrapper ) ) 398 { 399 if ( aDesc.Len() && aItemPresentation.Len() ) 400 aDesc.AppendAscii(RTL_CONSTASCII_STRINGPARAM(" + ")); 401 if ( aItemPresentation.Len() ) 402 aDesc += aItemPresentation; 403 } 404 pItem = aIter.NextItem(); 405 } 406 return aDesc; 407 } 408 409 /////////////////////////// SfxStyleSheetIterator /////////////////////////////// 410 411 SfxStyleFamily SfxStyleSheetIterator::GetSearchFamily() const 412 { 413 return nSearchFamily; 414 } 415 416 inline sal_Bool SfxStyleSheetIterator::IsTrivialSearch() 417 { 418 return nMask == 0xFFFF && GetSearchFamily() == SFX_STYLE_FAMILY_ALL; 419 } 420 421 sal_Bool SfxStyleSheetIterator::DoesStyleMatch(SfxStyleSheetBase *pStyle) 422 { 423 return ((GetSearchFamily() == SFX_STYLE_FAMILY_ALL) || 424 ( pStyle->GetFamily() == GetSearchFamily() )) 425 && (( pStyle->GetMask() & ( GetSearchMask() & ~SFXSTYLEBIT_USED )) || 426 ( bSearchUsed ? pStyle->IsUsed() : sal_False ) || 427 GetSearchMask() == SFXSTYLEBIT_ALL ); 428 } 429 430 431 SfxStyleSheetIterator::SfxStyleSheetIterator(SfxStyleSheetBasePool *pBase, 432 SfxStyleFamily eFam, sal_uInt16 n) 433 { 434 pBasePool=pBase; 435 nSearchFamily=eFam; 436 bSearchUsed=sal_False; 437 if((n != SFXSTYLEBIT_ALL ) && ((n & SFXSTYLEBIT_USED) == SFXSTYLEBIT_USED)) 438 { 439 bSearchUsed = sal_True; 440 n &= ~SFXSTYLEBIT_USED; 441 } 442 nMask=n; 443 } 444 445 SfxStyleSheetIterator::~SfxStyleSheetIterator() 446 { 447 } 448 449 450 sal_uInt16 SfxStyleSheetIterator::Count() 451 { 452 sal_uInt16 n = 0; 453 if( IsTrivialSearch()) 454 n = (sal_uInt16) pBasePool->aStyles.size(); 455 else 456 for(sal_uInt16 i=0; i<pBasePool->aStyles.size(); i++) 457 { 458 SfxStyleSheetBase* pStyle = pBasePool->aStyles[i].get(); 459 if(DoesStyleMatch(pStyle)) 460 n++; 461 } 462 return n; 463 } 464 465 SfxStyleSheetBase* SfxStyleSheetIterator::operator[](sal_uInt16 nIdx) 466 { 467 if( IsTrivialSearch()) 468 return pBasePool->aStyles[nIdx].get(); 469 470 sal_uInt16 z = 0; 471 for(sal_uInt16 n=0; n<pBasePool->aStyles.size(); n++) 472 { 473 SfxStyleSheetBase* pStyle = pBasePool->aStyles[n].get(); 474 if( DoesStyleMatch(pStyle)) 475 { 476 if(z == nIdx) 477 { 478 nAktPosition=n; 479 return pAktStyle=pStyle; 480 } 481 ++z; 482 } 483 } 484 DBG_ERROR("falscher Index"); 485 return 0; 486 } 487 488 SfxStyleSheetBase* SfxStyleSheetIterator::First() 489 { 490 sal_Int32 nIdx = -1; 491 492 if ( IsTrivialSearch() && pBasePool->aStyles.size() ) 493 nIdx = 0; 494 else 495 for( sal_uInt16 n = 0; n < pBasePool->aStyles.size(); n++ ) 496 { 497 SfxStyleSheetBase* pStyle = pBasePool->aStyles[n].get(); 498 499 if ( DoesStyleMatch( pStyle ) ) 500 { 501 nIdx = n; 502 break; 503 } 504 } 505 506 if ( nIdx != -1 ) 507 { 508 nAktPosition = (sal_uInt16)nIdx; 509 return pAktStyle = pBasePool->aStyles[nIdx].get(); 510 } 511 return 0; 512 } 513 514 515 SfxStyleSheetBase* SfxStyleSheetIterator::Next() 516 { 517 sal_Int32 nIdx = -1; 518 519 if ( IsTrivialSearch() && 520 (sal_uInt16)pBasePool->aStyles.size() > nAktPosition + 1 ) 521 nIdx = nAktPosition + 1; 522 else 523 for( sal_uInt16 n = nAktPosition + 1; n < pBasePool->aStyles.size(); n++ ) 524 { 525 SfxStyleSheetBase* pStyle = pBasePool->aStyles[n].get(); 526 527 if ( DoesStyleMatch( pStyle ) ) 528 { 529 nIdx = n; 530 break; 531 } 532 } 533 534 if ( nIdx != -1 ) 535 { 536 nAktPosition = (sal_uInt16)nIdx; 537 return pAktStyle = pBasePool->aStyles[nIdx].get(); 538 } 539 return 0; 540 } 541 542 543 SfxStyleSheetBase* SfxStyleSheetIterator::Find(const XubString& rStr) 544 { 545 for ( sal_uInt16 n = 0; n < pBasePool->aStyles.size(); n++ ) 546 { 547 SfxStyleSheetBase* pStyle = pBasePool->aStyles[n].get(); 548 549 // #98454# performance: in case of bSearchUsed==sal_True it may be 550 // significant to first compare the name and only if it matches to call 551 // the style sheet IsUsed() method in DoesStyleMatch(). 552 if ( pStyle->GetName().Equals( rStr ) && DoesStyleMatch( pStyle ) ) 553 { 554 nAktPosition = n; 555 return pAktStyle = pStyle; 556 } 557 } 558 return 0; 559 } 560 561 562 sal_uInt16 SfxStyleSheetIterator::GetSearchMask() const 563 { 564 sal_uInt16 mask = nMask; 565 566 if ( bSearchUsed ) 567 mask |= SFXSTYLEBIT_USED; 568 return mask; 569 } 570 571 /////////////////////////// SfxStyleSheetBasePool /////////////////////////////// 572 573 void SfxStyleSheetBasePool::Replace( 574 SfxStyleSheetBase& rSource, SfxStyleSheetBase& rTarget ) 575 { 576 rTarget.SetFollow( rSource.GetFollow() ); 577 rTarget.SetParent( rSource.GetParent() ); 578 SfxItemSet& rSourceSet = rSource.GetItemSet(); 579 SfxItemSet& rTargetSet = rTarget.GetItemSet(); 580 rTargetSet.Intersect( rSourceSet ); 581 rTargetSet.Put( rSourceSet ); 582 } 583 584 SfxStyleSheetIterator& SfxStyleSheetBasePool::GetIterator_Impl() 585 { 586 SfxStyleSheetIterator*& rpIter = pImp->pIter; 587 if( !rpIter || (rpIter->GetSearchMask() != nMask) || (rpIter->GetSearchFamily() != nSearchFamily) ) 588 { 589 delete rpIter; 590 rpIter = CreateIterator( nSearchFamily, nMask ); 591 } 592 return *rpIter; 593 } 594 595 596 SfxStyleSheetBasePool::SfxStyleSheetBasePool( SfxItemPool& r ) 597 : aAppName(r.GetName()) 598 , rPool(r) 599 , nSearchFamily(SFX_STYLE_FAMILY_PARA) 600 , nMask(0xFFFF) 601 { 602 #ifdef DBG_UTIL 603 aDbgStyleSheetReferences.mnPools++; 604 #endif 605 606 pImp = new SfxStyleSheetBasePool_Impl; 607 } 608 609 SfxStyleSheetBasePool::SfxStyleSheetBasePool( const SfxStyleSheetBasePool& r ) 610 : SfxBroadcaster( r ) 611 , comphelper::OWeakTypeObject() 612 , aAppName(r.aAppName) 613 , rPool(r.rPool) 614 , nSearchFamily(r.nSearchFamily) 615 , nMask( r.nMask ) 616 { 617 #ifdef DBG_UTIL 618 aDbgStyleSheetReferences.mnPools++; 619 #endif 620 621 pImp = new SfxStyleSheetBasePool_Impl; 622 *this += r; 623 } 624 625 SfxStyleSheetBasePool::~SfxStyleSheetBasePool() 626 { 627 #ifdef DBG_UTIL 628 aDbgStyleSheetReferences.mnPools--; 629 #endif 630 631 Broadcast( SfxSimpleHint(SFX_HINT_DYING) ); 632 Clear(); 633 delete pImp; 634 } 635 636 sal_Bool SfxStyleSheetBasePool::SetParent(SfxStyleFamily eFam, const XubString& rStyle, const XubString& rParent) 637 { 638 SfxStyleSheetIterator aIter(this,eFam,SFXSTYLEBIT_ALL); 639 SfxStyleSheetBase *pStyle = 640 aIter.Find(rStyle); 641 DBG_ASSERT(pStyle, "Vorlage nicht gefunden. Writer mit Solar <2541??"); 642 if(pStyle) 643 return pStyle->SetParent(rParent); 644 else 645 return sal_False; 646 } 647 648 649 void SfxStyleSheetBasePool::SetSearchMask(SfxStyleFamily eFam, sal_uInt16 n) 650 { 651 nSearchFamily = eFam; nMask = n; 652 } 653 654 sal_uInt16 SfxStyleSheetBasePool::GetSearchMask() const 655 { 656 return nMask; 657 } 658 659 660 // Der Name des Streams 661 662 String SfxStyleSheetBasePool::GetStreamName() 663 { 664 return String::CreateFromAscii(RTL_CONSTASCII_STRINGPARAM(STYLESTREAM)); 665 } 666 667 /////////////////////////////////// Factory //////////////////////////////// 668 669 670 671 SfxStyleSheetIterator* SfxStyleSheetBasePool::CreateIterator 672 ( 673 SfxStyleFamily eFam, 674 sal_uInt16 mask 675 ) 676 { 677 return new SfxStyleSheetIterator(this,eFam,mask); 678 } 679 680 681 SfxStyleSheetBase* SfxStyleSheetBasePool::Create 682 ( 683 const XubString& rName, 684 SfxStyleFamily eFam, 685 sal_uInt16 mask 686 ) 687 { 688 return new SfxStyleSheetBase( rName, *this, eFam, mask ); 689 } 690 691 SfxStyleSheetBase* SfxStyleSheetBasePool::Create( const SfxStyleSheetBase& r ) 692 { 693 return new SfxStyleSheetBase( r ); 694 } 695 696 SfxStyleSheetBase& SfxStyleSheetBasePool::Make( const XubString& rName, SfxStyleFamily eFam, sal_uInt16 mask, sal_uInt16 nPos) 697 { 698 DBG_ASSERT( eFam != SFX_STYLE_FAMILY_ALL, "svl::SfxStyleSheetBasePool::Make(), FamilyAll is not a allowed Familie" ); 699 700 SfxStyleSheetIterator aIter(this, eFam, mask); 701 rtl::Reference< SfxStyleSheetBase > xStyle( aIter.Find( rName ) ); 702 DBG_ASSERT( !xStyle.is(), "svl::SfxStyleSheetBasePool::Make(), StyleSheet already exists" ); 703 SfxStyleSheetIterator& rIter = GetIterator_Impl(); 704 705 if( !xStyle.is() ) 706 { 707 xStyle = Create( rName, eFam, mask ); 708 if(0xffff == nPos || nPos == aStyles.size() || nPos == rIter.Count()) 709 { 710 aStyles.push_back( xStyle ); 711 } 712 else 713 { 714 rIter[nPos]; 715 aStyles.insert( aStyles.begin() + rIter.GetPos(), xStyle ); 716 } 717 Broadcast( SfxStyleSheetHint( SFX_STYLESHEET_CREATED, *xStyle.get() ) ); 718 } 719 return *xStyle.get(); 720 } 721 722 /////////////////////////////// Kopieren /////////////////////////////////// 723 724 // Hilfsroutine: Falls eine Vorlage dieses Namens existiert, wird 725 // sie neu erzeugt. Alle Vorlagen, die diese Vorlage zum Parent haben, 726 // werden umgehaengt. 727 728 SfxStyleSheetBase& SfxStyleSheetBasePool::Add( SfxStyleSheetBase& rSheet ) 729 { 730 SfxStyleSheetIterator aIter(this, rSheet.GetFamily(), nMask); 731 SfxStyleSheetBase* pOld = aIter.Find( rSheet.GetName() ); 732 Remove( pOld ); 733 rtl::Reference< SfxStyleSheetBase > xNew( Create( rSheet ) ); 734 aStyles.push_back( xNew ); 735 Broadcast( SfxStyleSheetHint( SFX_STYLESHEET_CHANGED, *xNew.get() ) ); 736 return *xNew.get(); 737 } 738 739 SfxStyleSheetBasePool& SfxStyleSheetBasePool::operator=( const SfxStyleSheetBasePool& r ) 740 { 741 if( &r != this ) 742 { 743 Clear(); 744 *this += r; 745 } 746 return *this; 747 } 748 749 SfxStyleSheetBasePool& SfxStyleSheetBasePool::operator+=( const SfxStyleSheetBasePool& r ) 750 { 751 if( &r != this ) 752 { 753 SfxStyles::const_iterator aIter( r.aStyles.begin() ); 754 while( aIter != r.aStyles.end() ) 755 { 756 Add(*(*aIter++).get()); 757 } 758 } 759 return *this; 760 } 761 762 //////////////////////////////// Suchen //////////////////////////////////// 763 764 sal_uInt16 SfxStyleSheetBasePool::Count() 765 { 766 return GetIterator_Impl().Count(); 767 } 768 769 SfxStyleSheetBase *SfxStyleSheetBasePool::operator[](sal_uInt16 nIdx) 770 { 771 return GetIterator_Impl()[nIdx]; 772 } 773 774 SfxStyleSheetBase* SfxStyleSheetBasePool::Find(const XubString& rName, 775 SfxStyleFamily eFam, 776 sal_uInt16 mask) 777 { 778 SfxStyleSheetIterator aIter(this,eFam,mask); 779 return aIter.Find(rName); 780 } 781 782 const SfxStyles& SfxStyleSheetBasePool::GetStyles() 783 { 784 return aStyles; 785 } 786 787 SfxStyleSheetBase* SfxStyleSheetBasePool::First() 788 { 789 return GetIterator_Impl().First(); 790 } 791 792 SfxStyleSheetBase* SfxStyleSheetBasePool::Next() 793 { 794 return GetIterator_Impl().Next(); 795 } 796 797 //////////////////////////////// Loeschen ///////////////////////////////// 798 799 void SfxStyleSheetBasePool::Remove( SfxStyleSheetBase* p ) 800 { 801 if( p ) 802 { 803 SfxStyles::iterator aIter( std::find( aStyles.begin(), aStyles.end(), rtl::Reference< SfxStyleSheetBase >( p ) ) ); 804 if( aIter != aStyles.end() ) 805 { 806 // Alle Styles umsetzen, deren Parent dieser hier ist 807 ChangeParent( p->GetName(), p->GetParent() ); 808 809 com::sun::star::uno::Reference< com::sun::star::lang::XComponent > xComp( static_cast< ::cppu::OWeakObject* >((*aIter).get()), com::sun::star::uno::UNO_QUERY ); 810 if( xComp.is() ) try 811 { 812 xComp->dispose(); 813 } 814 catch( com::sun::star::uno::Exception& ) 815 { 816 } 817 818 aStyles.erase(aIter); 819 Broadcast( SfxStyleSheetHint( SFX_STYLESHEET_ERASED, *p ) ); 820 } 821 } 822 } 823 824 void SfxStyleSheetBasePool::Insert( SfxStyleSheetBase* p ) 825 { 826 DBG_ASSERT( p, "svl::SfxStyleSheetBasePool::Insert(), no stylesheet?" ); 827 828 SfxStyleSheetIterator aIter(this, p->GetFamily(), p->GetMask()); 829 SfxStyleSheetBase* pOld = aIter.Find( p->GetName() ); 830 DBG_ASSERT( !pOld, "svl::SfxStyleSheetBasePool::Insert(), StyleSheet already inserted" ); 831 if( p->GetParent().Len() ) 832 { 833 pOld = aIter.Find( p->GetParent() ); 834 DBG_ASSERT( pOld, "svl::SfxStyleSheetBasePool::Insert(), Parent not found!" ); 835 } 836 aStyles.push_back( rtl::Reference< SfxStyleSheetBase >( p ) ); 837 Broadcast( SfxStyleSheetHint( SFX_STYLESHEET_CREATED, *p ) ); 838 } 839 840 void SfxStyleSheetBasePool::Clear() 841 { 842 SfxStyles aClearStyles; 843 aClearStyles.swap( aStyles ); 844 845 SfxStyles::iterator aIter( aClearStyles.begin() ); 846 while( aIter != aClearStyles.end() ) 847 { 848 com::sun::star::uno::Reference< com::sun::star::lang::XComponent > xComp( static_cast< ::cppu::OWeakObject* >((*aIter).get()), com::sun::star::uno::UNO_QUERY ); 849 if( xComp.is() ) try 850 { 851 xComp->dispose(); 852 } 853 catch( com::sun::star::uno::Exception& ) 854 { 855 } 856 857 Broadcast( SfxStyleSheetHint( SFX_STYLESHEET_ERASED, *(*aIter++).get() ) ); 858 } 859 } 860 861 /////////////////////////// Parents umsetzen //////////////////////////////// 862 863 void SfxStyleSheetBasePool::ChangeParent(const XubString& rOld, 864 const XubString& rNew, 865 sal_Bool bVirtual) 866 { 867 const sal_uInt16 nTmpMask = GetSearchMask(); 868 SetSearchMask(GetSearchFamily(), 0xffff); 869 for( SfxStyleSheetBase* p = First(); p; p = Next() ) 870 { 871 if( p->GetParent().Equals( rOld ) ) 872 { 873 if(bVirtual) 874 p->SetParent( rNew ); 875 else 876 p->aParent = rNew; 877 } 878 } 879 SetSearchMask(GetSearchFamily(), nTmpMask); 880 } 881 882 /////////////////////////// Laden/Speichern ///////////////////////////////// 883 884 void SfxStyleSheetBase::Load( SvStream&, sal_uInt16 ) 885 { 886 } 887 888 void SfxStyleSheetBase::Store( SvStream& ) 889 { 890 } 891 892 893 sal_Bool SfxStyleSheetBasePool::Load( SvStream& rStream ) 894 { 895 // alte Version? 896 if ( !rPool.IsVer2_Impl() ) 897 return Load1_Impl( rStream ); 898 899 // gesamten StyleSheetPool in neuer Version aus einem MiniRecord lesen 900 SfxMiniRecordReader aPoolRec( &rStream, SFX_STYLES_REC ); 901 902 // Header-Record lesen 903 short nCharSet = 0; 904 if ( !rStream.GetError() ) 905 { 906 SfxSingleRecordReader aHeaderRec( &rStream, SFX_STYLES_REC_HEADER ); 907 if ( !aHeaderRec.IsValid() ) 908 return sal_False; 909 910 aAppName = rPool.GetName(); 911 rStream >> nCharSet; 912 } 913 914 // Styles-Record lesen 915 if ( !rStream.GetError() ) 916 { 917 SfxMultiRecordReader aStylesRec( &rStream, SFX_STYLES_REC_STYLES ); 918 if ( !aStylesRec.IsValid() ) 919 return sal_False; 920 921 rtl_TextEncoding eEnc = GetSOLoadTextEncoding( 922 (rtl_TextEncoding)nCharSet, 923 sal::static_int_cast< sal_uInt16 >(rStream.GetVersion()) ); 924 rtl_TextEncoding eOldEnc = rStream.GetStreamCharSet(); 925 rStream.SetStreamCharSet( eEnc ); 926 927 sal_uInt16 nStyles; 928 for ( nStyles = 0; aStylesRec.GetContent(); nStyles++ ) 929 { 930 // kann nicht mehr weiterlesen? 931 if ( rStream.GetError() ) 932 break; 933 934 // Globale Teile 935 XubString aName, aParent, aFollow; 936 String aHelpFile; 937 sal_uInt16 nFamily, nStyleMask,nCount; 938 sal_uInt32 nHelpId; 939 rStream.ReadByteString(aName, eEnc ); 940 rStream.ReadByteString(aParent, eEnc ); 941 rStream.ReadByteString(aFollow, eEnc ); 942 rStream >> nFamily >> nStyleMask; 943 SfxPoolItem::readByteString(rStream, aHelpFile); 944 rStream >> nHelpId; 945 946 SfxStyleSheetBase& rSheet = Make( aName, (SfxStyleFamily)nFamily , nStyleMask); 947 rSheet.SetHelpId( aHelpFile, nHelpId ); 948 // Hier erst einmal Parent und Follow zwischenspeichern 949 rSheet.aParent = aParent; 950 rSheet.aFollow = aFollow; 951 sal_uInt32 nPos = rStream.Tell(); 952 rStream >> nCount; 953 if(nCount) 954 { 955 rStream.Seek( nPos ); 956 // Das Laden des ItemSets bedient sich der Methode GetItemSet(), 957 // damit eigene ItemSets untergeschoben werden koennen 958 SfxItemSet& rSet = rSheet.GetItemSet(); 959 rSet.ClearItem(); 960 //! SfxItemSet aTmpSet( *pTmpPool ); 961 /*!aTmpSet*/ rSet.Load( rStream ); 962 //! rSet.Put( aTmpSet ); 963 } 964 // Lokale Teile 965 sal_uInt32 nSize; 966 sal_uInt16 nVer; 967 rStream >> nVer >> nSize; 968 nPos = rStream.Tell() + nSize; 969 rSheet.Load( rStream, nVer ); 970 rStream.Seek( nPos ); 971 } 972 973 // #72939# only loop through the styles that were really inserted 974 sal_uLong n = aStyles.size(); 975 976 //! delete pTmpPool; 977 // Jetzt Parent und Follow setzen. Alle Sheets sind geladen. 978 // Mit Setxxx() noch einmal den String eintragen, da diese 979 // virtuellen Methoden evtl. ueberlagert sind. 980 for ( sal_uLong i = 0; i < n; i++ ) 981 { 982 SfxStyleSheetBase* p = aStyles[ i ].get(); 983 XubString aText = p->aParent; 984 p->aParent.Erase(); 985 p->SetParent( aText ); 986 aText = p->aFollow; 987 p->aFollow.Erase(); 988 p->SetFollow( aText ); 989 } 990 991 rStream.SetStreamCharSet( eOldEnc ); 992 } 993 994 // alles klar? 995 return sal_Bool( rStream.GetError() == SVSTREAM_OK ); 996 } 997 998 sal_Bool SfxStyleSheetBasePool::Load1_Impl( SvStream& rStream ) 999 { 1000 aAppName = rPool.GetName(); 1001 sal_uInt16 nVersion; 1002 short nCharSet; 1003 rStream >> nVersion; 1004 1005 if(nVersion!=STYLESTREAM_VERSION) 1006 nCharSet=nVersion; 1007 else 1008 rStream >> nCharSet; 1009 1010 rtl_TextEncoding eEnc = GetSOLoadTextEncoding( 1011 (rtl_TextEncoding)nCharSet, 1012 sal::static_int_cast< sal_uInt16 >(rStream.GetVersion()) ); 1013 rtl_TextEncoding eOldEnc = rStream.GetStreamCharSet(); 1014 rStream.SetStreamCharSet( eEnc ); 1015 1016 sal_uInt16 nStyles; 1017 rStream >> nStyles; 1018 sal_uInt16 i; 1019 for ( i = 0; i < nStyles; i++ ) 1020 { 1021 // kann nicht mehr weiterlesen? 1022 if ( rStream.GetError() ) 1023 { 1024 nStyles = i; 1025 break; 1026 } 1027 1028 // Globale Teile 1029 XubString aName, aParent, aFollow; 1030 String aHelpFile; 1031 sal_uInt16 nFamily, nStyleMask,nCount; 1032 sal_uInt32 nHelpId; 1033 rStream.ReadByteString(aName, eEnc ); 1034 rStream.ReadByteString(aParent, eEnc ); 1035 rStream.ReadByteString(aFollow, eEnc ); 1036 rStream >> nFamily >> nStyleMask; 1037 SfxPoolItem::readByteString(rStream, aHelpFile); 1038 if(nVersion!=STYLESTREAM_VERSION) 1039 { 1040 sal_uInt16 nTmpHelpId; 1041 rStream >> nTmpHelpId; 1042 nHelpId=nTmpHelpId; 1043 } 1044 else 1045 rStream >> nHelpId; 1046 1047 SfxStyleSheetBase& rSheet = Make( aName, (SfxStyleFamily)nFamily , nStyleMask); 1048 rSheet.SetHelpId( aHelpFile, nHelpId ); 1049 // Hier erst einmal Parent und Follow zwischenspeichern 1050 rSheet.aParent = aParent; 1051 rSheet.aFollow = aFollow; 1052 sal_uInt32 nPos = rStream.Tell(); 1053 rStream >> nCount; 1054 if(nCount) { 1055 rStream.Seek( nPos ); 1056 // Das Laden des ItemSets bedient sich der Methode GetItemSet(), 1057 // damit eigene ItemSets untergeschoben werden koennen 1058 SfxItemSet& rSet = rSheet.GetItemSet(); 1059 rSet.ClearItem(); 1060 //! SfxItemSet aTmpSet( *pTmpPool ); 1061 /*!aTmpSet*/ rSet.Load( rStream ); 1062 //! rSet.Put( aTmpSet ); 1063 } 1064 // Lokale Teile 1065 sal_uInt32 nSize; 1066 sal_uInt16 nVer; 1067 rStream >> nVer >> nSize; 1068 nPos = rStream.Tell() + nSize; 1069 rSheet.Load( rStream, nVer ); 1070 rStream.Seek( nPos ); 1071 } 1072 1073 //! delete pTmpPool; 1074 // Jetzt Parent und Follow setzen. Alle Sheets sind geladen. 1075 // Mit Setxxx() noch einmal den String eintragen, da diese 1076 // virtuellen Methoden evtl. ueberlagert sind. 1077 for ( i = 0; i < nStyles; i++ ) 1078 { 1079 SfxStyleSheetBase* p = aStyles[ i ].get(); 1080 XubString aText = p->aParent; 1081 p->aParent.Erase(); 1082 p->SetParent( aText ); 1083 aText = p->aFollow; 1084 p->aFollow.Erase(); 1085 p->SetFollow( aText ); 1086 } 1087 1088 rStream.SetStreamCharSet( eOldEnc ); 1089 1090 return sal_Bool( rStream.GetError() == SVSTREAM_OK ); 1091 } 1092 1093 sal_Bool SfxStyleSheetBasePool::Store( SvStream& rStream, sal_Bool bUsed ) 1094 { 1095 // den ganzen StyleSheet-Pool in einen Mini-Record 1096 SfxMiniRecordWriter aPoolRec( &rStream, SFX_STYLES_REC ); 1097 1098 // Erst einmal die Dummies rauszaehlen; die werden nicht gespeichert 1099 sal_uInt16 nCount = 0; 1100 for( SfxStyleSheetBase* p = First(); p; p = Next() ) 1101 { 1102 if(!bUsed || p->IsUsed()) 1103 nCount++; 1104 } 1105 1106 // einen Header-Record vorweg 1107 rtl_TextEncoding eEnc 1108 = ::GetSOStoreTextEncoding( 1109 rStream.GetStreamCharSet(), 1110 sal::static_int_cast< sal_uInt16 >(rStream.GetVersion()) ); 1111 rtl_TextEncoding eOldEnc = rStream.GetStreamCharSet(); 1112 rStream.SetStreamCharSet( eEnc ); 1113 1114 { 1115 SfxSingleRecordWriter aHeaderRec( &rStream, 1116 SFX_STYLES_REC_HEADER, 1117 STYLESTREAM_VERSION ); 1118 rStream << (short) eEnc; 1119 } 1120 1121 // die StyleSheets in einen MultiVarRecord 1122 { 1123 // Bug 79478: 1124 // make a check loop, to be shure, that the converted names are also 1125 // unique like the originals! In other cases we get a loop. 1126 SvStringsSortDtor aSortOrigNames( 0, 128 ); 1127 SvStrings aOrigNames( 0, 128 ); 1128 SvByteStringsSortDtor aSortConvNames( 0, 128 ); 1129 SvByteStrings aConvNames( 0, 128 ); 1130 1131 { 1132 1133 for( SfxStyleSheetBase* p = First(); p; p = Next() ) 1134 { 1135 if(!bUsed || p->IsUsed()) 1136 { 1137 sal_uInt16 nFamily = (sal_uInt16)p->GetFamily(); 1138 String* pName = new String( p->GetName() ); 1139 ByteString* pConvName = new ByteString( *pName, eEnc ); 1140 1141 pName->Insert( (sal_Unicode)nFamily, 0 ); 1142 pConvName->Insert( " ", 0 ); 1143 pConvName->SetChar( 1144 0, 1145 sal::static_int_cast< char >(0xff & (nFamily >> 8)) ); 1146 pConvName->SetChar( 1147 1, sal::static_int_cast< char >(0xff & nFamily) ); 1148 1149 sal_uInt16 nInsPos, nAdd = aSortConvNames.Count(); 1150 while( !aSortConvNames.Insert( pConvName, nInsPos ) ) 1151 (pConvName->Append( '_' )).Append( 1152 ByteString::CreateFromInt32( nAdd++ )); 1153 aOrigNames.Insert( pName, nInsPos ); 1154 } 1155 } 1156 1157 // now we have the list of the names, sorted by convertede names 1158 // But now we need the sorted list of orignames. 1159 { 1160 sal_uInt16 nInsPos, nEnd = aOrigNames.Count(); 1161 const ByteStringPtr* ppB = aSortConvNames.GetData(); 1162 for( sal_uInt16 n = 0; n < nEnd; ++n, ++ppB ) 1163 { 1164 String* p = aOrigNames.GetObject( n ); 1165 aSortOrigNames.Insert( p, nInsPos ); 1166 aConvNames.Insert( *ppB, nInsPos ); 1167 } 1168 1169 } 1170 } 1171 1172 1173 ByteString sEmpty; 1174 sal_uInt16 nFndPos; 1175 String sNm; 1176 SfxMultiVarRecordWriter aStylesRec( &rStream, SFX_STYLES_REC_STYLES, 0 ); 1177 for( SfxStyleSheetBase* p = First(); p; p = Next() ) 1178 { 1179 if(!bUsed || p->IsUsed()) 1180 { 1181 aStylesRec.NewContent(); 1182 1183 // Globale Teile speichern 1184 String aHelpFile; 1185 sal_uInt32 nHelpId = p->GetHelpId( aHelpFile ); 1186 sal_uInt16 nFamily = sal::static_int_cast< sal_uInt16 >(p->GetFamily()); 1187 String sFamily( (sal_Unicode)nFamily ); 1188 1189 (sNm = sFamily) += p->GetName(); 1190 if( aSortOrigNames.Seek_Entry( &sNm, &nFndPos )) 1191 rStream.WriteByteString( aConvNames.GetObject( nFndPos )->Copy( 2 )); 1192 else 1193 rStream.WriteByteString( sEmpty ); 1194 1195 (sNm = sFamily) += p->GetParent(); 1196 if( aSortOrigNames.Seek_Entry( &sNm, &nFndPos )) 1197 rStream.WriteByteString( aConvNames.GetObject( nFndPos )->Copy( 2 )); 1198 else 1199 rStream.WriteByteString( sEmpty ); 1200 1201 (sNm = sFamily) += p->GetFollow(); 1202 if( aSortOrigNames.Seek_Entry( &sNm, &nFndPos )) 1203 rStream.WriteByteString( aConvNames.GetObject( nFndPos )->Copy( 2 )); 1204 else 1205 rStream.WriteByteString( sEmpty ); 1206 1207 rStream << nFamily << p->GetMask(); 1208 SfxPoolItem::writeByteString(rStream, aHelpFile); 1209 rStream << nHelpId; 1210 if(p->pSet) 1211 p->pSet->Store( rStream ); 1212 else 1213 rStream << (sal_uInt16)0; 1214 1215 // Lokale Teile speichern 1216 // Vor dem lokalen Teil wird die Laenge der lokalen Daten 1217 // als sal_uInt32 sowie die Versionsnummer gespeichert. 1218 rStream << (sal_uInt16) p->GetVersion(); 1219 sal_uLong nPos1 = rStream.Tell(); 1220 rStream << (sal_uInt32) 0; 1221 p->Store( rStream ); 1222 sal_uLong nPos2 = rStream.Tell(); 1223 rStream.Seek( nPos1 ); 1224 rStream << (sal_uInt32) ( nPos2 - nPos1 - sizeof( sal_uInt32 ) ); 1225 rStream.Seek( nPos2 ); 1226 if( rStream.GetError() != SVSTREAM_OK ) 1227 break; 1228 } 1229 } 1230 } 1231 1232 rStream.SetStreamCharSet( eOldEnc ); 1233 1234 return sal_Bool( rStream.GetError() == SVSTREAM_OK ); 1235 } 1236 1237 SfxItemPool& SfxStyleSheetBasePool::GetPool() 1238 { 1239 return rPool; 1240 } 1241 1242 const SfxItemPool& SfxStyleSheetBasePool::GetPool() const 1243 { 1244 return rPool; 1245 } 1246 1247 /////////////////////// SfxStyleSheet ///////////////////////////////// 1248 1249 SfxStyleSheet::SfxStyleSheet(const XubString &rName, 1250 const SfxStyleSheetBasePool& r_Pool, 1251 SfxStyleFamily eFam, 1252 sal_uInt16 mask ): 1253 SfxStyleSheetBase(rName, const_cast< SfxStyleSheetBasePool& >( r_Pool ), eFam, mask) 1254 {} 1255 1256 SfxStyleSheet::SfxStyleSheet(const SfxStyleSheet& rStyle) : 1257 SfxStyleSheetBase(rStyle), 1258 SfxListener( rStyle ), 1259 SfxBroadcaster( rStyle ) 1260 {} 1261 1262 SfxStyleSheet::SfxStyleSheet() 1263 { 1264 } 1265 1266 SfxStyleSheet::~SfxStyleSheet() 1267 { 1268 Broadcast( SfxStyleSheetHint( SFX_STYLESHEET_INDESTRUCTION, *this ) ); 1269 } 1270 1271 1272 sal_Bool SfxStyleSheet::SetParent( const XubString& rName ) 1273 { 1274 if(aParent == rName) 1275 return sal_True; 1276 const XubString aOldParent(aParent); 1277 if(SfxStyleSheetBase::SetParent(rName)) { 1278 // aus der Benachrichtigungskette des alten 1279 // Parents gfs. austragen 1280 if(aOldParent.Len()) { 1281 SfxStyleSheet *pParent = (SfxStyleSheet *)rPool.Find(aOldParent, nFamily, 0xffff); 1282 if(pParent) 1283 EndListening(*pParent); 1284 } 1285 // in die Benachrichtigungskette des neuen 1286 // Parents eintragen 1287 if(aParent.Len()) { 1288 SfxStyleSheet *pParent = (SfxStyleSheet *)rPool.Find(aParent, nFamily, 0xffff); 1289 if(pParent) 1290 StartListening(*pParent); 1291 } 1292 return sal_True; 1293 } 1294 return sal_False; 1295 } 1296 1297 // alle Zuhoerer benachtichtigen 1298 1299 void SfxStyleSheet::Notify(SfxBroadcaster& rBC, const SfxHint& rHint ) 1300 { 1301 Forward(rBC, rHint); 1302 } 1303 1304 //////////////////////// SfxStyleSheetPool /////////////////////////////// 1305 1306 SfxStyleSheetPool::SfxStyleSheetPool( SfxItemPool const& rSet) 1307 : SfxStyleSheetBasePool( const_cast< SfxItemPool& >( rSet ) ) 1308 { 1309 } 1310 1311 /////////////////////////////////// Factory //////////////////////////////// 1312 1313 SfxStyleSheetBase* SfxStyleSheetPool::Create( const XubString& rName, 1314 SfxStyleFamily eFam, sal_uInt16 mask ) 1315 { 1316 return new SfxStyleSheet( rName, *this, eFam, mask ); 1317 } 1318 1319 SfxStyleSheetBase* SfxStyleSheetPool::Create( const SfxStyleSheet& r ) 1320 { 1321 return new SfxStyleSheet( r ); 1322 } 1323 /* 1324 sal_Bool SfxStyleSheetPool::CopyTo(SfxStyleSheetPool &, const String &) 1325 { 1326 return sal_False; 1327 } 1328 */ 1329 1330 // -------------------------------------------------------------------- 1331 // class SfxUnoStyleSheet 1332 // -------------------------------------------------------------------- 1333 1334 SfxUnoStyleSheet::SfxUnoStyleSheet( const UniString& _rName, const SfxStyleSheetBasePool& _rPool, SfxStyleFamily _eFamily, sal_uInt16 _nMaske ) 1335 : ::cppu::ImplInheritanceHelper2< SfxStyleSheet, ::com::sun::star::style::XStyle, ::com::sun::star::lang::XUnoTunnel >( _rName, _rPool, _eFamily, _nMaske ) 1336 { 1337 } 1338 1339 // -------------------------------------------------------------------- 1340 SfxUnoStyleSheet::SfxUnoStyleSheet( const SfxStyleSheet& _rSheet ) 1341 : ::cppu::ImplInheritanceHelper2< SfxStyleSheet, ::com::sun::star::style::XStyle, ::com::sun::star::lang::XUnoTunnel >( _rSheet ) 1342 { 1343 } 1344 1345 // -------------------------------------------------------------------- 1346 1347 SfxUnoStyleSheet* SfxUnoStyleSheet::getUnoStyleSheet( const ::com::sun::star::uno::Reference< ::com::sun::star::style::XStyle >& xStyle ) 1348 { 1349 SfxUnoStyleSheet* pRet = dynamic_cast< SfxUnoStyleSheet* >( xStyle.get() ); 1350 if( !pRet ) 1351 { 1352 ::com::sun::star::uno::Reference< ::com::sun::star::lang::XUnoTunnel > xUT( xStyle, ::com::sun::star::uno::UNO_QUERY ); 1353 if( xUT.is() ) 1354 pRet = reinterpret_cast<SfxUnoStyleSheet*>(sal::static_int_cast<sal_uIntPtr>(xUT->getSomething( SfxUnoStyleSheet::getIdentifier()))); 1355 } 1356 return pRet; 1357 } 1358 1359 // -------------------------------------------------------------------- 1360 // XUnoTunnel 1361 // -------------------------------------------------------------------- 1362 1363 ::sal_Int64 SAL_CALL SfxUnoStyleSheet::getSomething( const ::com::sun::star::uno::Sequence< ::sal_Int8 >& rId ) throw (::com::sun::star::uno::RuntimeException) 1364 { 1365 if( rId.getLength() == 16 && 0 == rtl_compareMemory( getIdentifier().getConstArray(), rId.getConstArray(), 16 ) ) 1366 { 1367 return sal::static_int_cast<sal_Int64>(reinterpret_cast<sal_uIntPtr>(this)); 1368 } 1369 else 1370 { 1371 return 0; 1372 } 1373 } 1374 1375 // -------------------------------------------------------------------- 1376 1377 const ::com::sun::star::uno::Sequence< ::sal_Int8 >& SfxUnoStyleSheet::getIdentifier() 1378 { 1379 static ::com::sun::star::uno::Sequence< sal_Int8 > * pSeq = 0; 1380 if( !pSeq ) 1381 { 1382 ::osl::Guard< ::osl::Mutex > aGuard( ::osl::Mutex::getGlobalMutex() ); 1383 if( !pSeq ) 1384 { 1385 static ::com::sun::star::uno::Sequence< sal_Int8 > aSeq( 16 ); 1386 rtl_createUuid( (sal_uInt8*)aSeq.getArray(), 0, sal_True ); 1387 pSeq = &aSeq; 1388 } 1389 } 1390 return *pSeq; 1391 } 1392 1393 // -------------------------------------------------------------------- 1394