1 /************************************************************** 2 * 3 * Licensed to the Apache Software Foundation (ASF) under one 4 * or more contributor license agreements. See the NOTICE file 5 * distributed with this work for additional information 6 * regarding copyright ownership. The ASF licenses this file 7 * to you under the Apache License, Version 2.0 (the 8 * "License"); you may not use this file except in compliance 9 * with the License. You may obtain a copy of the License at 10 * 11 * http://www.apache.org/licenses/LICENSE-2.0 12 * 13 * Unless required by applicable law or agreed to in writing, 14 * software distributed under the License is distributed on an 15 * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY 16 * KIND, either express or implied. See the License for the 17 * specific language governing permissions and limitations 18 * under the License. 19 * 20 *************************************************************/ 21 22 23 24 // MARKER(update_precomp.py): autogen include statement, do not remove 25 #include "precompiled_sw.hxx" 26 27 #include <tools/resid.hxx> 28 #include <hintids.hxx> 29 #include <swtypes.hxx> 30 #include <errhdl.hxx> 31 #include <txtatr.hxx> 32 #include <ndtxt.hxx> 33 #include <txttxmrk.hxx> 34 #include <tox.hxx> 35 #include <poolfmt.hrc> 36 #include <doc.hxx> 37 #include <docary.hxx> 38 #include <paratr.hxx> 39 #include <editeng/tstpitem.hxx> 40 #include <SwStyleNameMapper.hxx> 41 #include <hints.hxx> // SwPtrMsgPoolItem 42 #include <algorithm> 43 #include <functional> 44 #include <switerator.hxx> 45 46 using namespace std; 47 48 const sal_Char* SwForm::aFormEntry = "<E>"; 49 const sal_Char* SwForm::aFormTab = "<T>"; 50 const sal_Char* SwForm::aFormPageNums = "<#>"; 51 const sal_Char* SwForm::aFormLinkStt = "<LS>"; 52 const sal_Char* SwForm::aFormLinkEnd = "<LE>"; 53 const sal_Char* SwForm::aFormEntryNum = "<E#>"; 54 const sal_Char* SwForm::aFormEntryTxt = "<ET>"; 55 const sal_Char* SwForm::aFormChapterMark= "<C>"; 56 const sal_Char* SwForm::aFormText = "<X>"; 57 const sal_Char* SwForm::aFormAuth = "<A>"; 58 sal_uInt8 SwForm::nFormTabLen = 3; 59 sal_uInt8 SwForm::nFormEntryLen = 3; 60 sal_uInt8 SwForm::nFormPageNumsLen = 3; 61 sal_uInt8 SwForm::nFormLinkSttLen = 4; 62 sal_uInt8 SwForm::nFormLinkEndLen = 4; 63 sal_uInt8 SwForm::nFormEntryNumLen = 4; 64 sal_uInt8 SwForm::nFormEntryTxtLen = 4; 65 sal_uInt8 SwForm::nFormChapterMarkLen = 3; 66 sal_uInt8 SwForm::nFormTextLen = 3; 67 sal_uInt8 SwForm::nFormAuthLen = 5; 68 69 SV_IMPL_PTRARR(SwTOXMarks, SwTOXMark*) 70 71 TYPEINIT2( SwTOXMark, SfxPoolItem, SwClient ); // fuers rtti 72 73 struct PatternIni 74 { 75 sal_uInt16 n1; 76 sal_uInt16 n2; 77 sal_uInt16 n3; 78 sal_uInt16 n4; 79 sal_uInt16 n5; 80 }; 81 const PatternIni aPatternIni[] = 82 { 83 {USHRT_MAX, USHRT_MAX, USHRT_MAX, USHRT_MAX, USHRT_MAX}, //Header - no pattern 84 {AUTH_FIELD_AUTHOR, AUTH_FIELD_TITLE, AUTH_FIELD_YEAR, USHRT_MAX, USHRT_MAX}, //AUTH_TYPE_ARTICLE, 85 {AUTH_FIELD_AUTHOR, AUTH_FIELD_TITLE, AUTH_FIELD_YEAR, USHRT_MAX, USHRT_MAX}, //AUTH_TYPE_BOOK, 86 {AUTH_FIELD_AUTHOR, AUTH_FIELD_TITLE, AUTH_FIELD_YEAR, USHRT_MAX, USHRT_MAX}, //AUTH_TYPE_BOOKLET, 87 {AUTH_FIELD_AUTHOR, AUTH_FIELD_TITLE, AUTH_FIELD_YEAR, USHRT_MAX, USHRT_MAX}, //AUTH_TYPE_CONFERENCE, 88 {AUTH_FIELD_AUTHOR, AUTH_FIELD_TITLE, AUTH_FIELD_YEAR, USHRT_MAX, USHRT_MAX}, //AUTH_TYPE_INBOOK, 89 {AUTH_FIELD_AUTHOR, AUTH_FIELD_TITLE, AUTH_FIELD_YEAR, USHRT_MAX, USHRT_MAX}, //AUTH_TYPE_INCOLLECTION, 90 {AUTH_FIELD_AUTHOR, AUTH_FIELD_TITLE, AUTH_FIELD_YEAR, USHRT_MAX, USHRT_MAX}, //AUTH_TYPE_INPROCEEDINGS, 91 {AUTH_FIELD_AUTHOR, AUTH_FIELD_TITLE, AUTH_FIELD_YEAR, USHRT_MAX, USHRT_MAX}, //AUTH_TYPE_JOURNAL, 92 {AUTH_FIELD_AUTHOR, AUTH_FIELD_TITLE, AUTH_FIELD_YEAR, USHRT_MAX, USHRT_MAX}, //AUTH_TYPE_MANUAL, 93 {AUTH_FIELD_AUTHOR, AUTH_FIELD_TITLE, AUTH_FIELD_YEAR, USHRT_MAX, USHRT_MAX}, //AUTH_TYPE_MASTERSTHESIS, 94 {AUTH_FIELD_AUTHOR, AUTH_FIELD_TITLE, AUTH_FIELD_YEAR, USHRT_MAX, USHRT_MAX}, //AUTH_TYPE_MISC, 95 {AUTH_FIELD_AUTHOR, AUTH_FIELD_TITLE, AUTH_FIELD_YEAR, USHRT_MAX, USHRT_MAX}, //AUTH_TYPE_PHDTHESIS, 96 {AUTH_FIELD_AUTHOR, AUTH_FIELD_TITLE, AUTH_FIELD_YEAR, USHRT_MAX, USHRT_MAX}, //AUTH_TYPE_PROCEEDINGS, 97 {AUTH_FIELD_AUTHOR, AUTH_FIELD_TITLE, AUTH_FIELD_YEAR, USHRT_MAX, USHRT_MAX}, //AUTH_TYPE_TECHREPORT, 98 {AUTH_FIELD_AUTHOR, AUTH_FIELD_TITLE, AUTH_FIELD_YEAR, USHRT_MAX, USHRT_MAX}, //AUTH_TYPE_UNPUBLISHED, 99 {AUTH_FIELD_AUTHOR, AUTH_FIELD_TITLE, AUTH_FIELD_YEAR, USHRT_MAX, USHRT_MAX}, //AUTH_TYPE_EMAIL, 100 {AUTH_FIELD_AUTHOR, AUTH_FIELD_TITLE, AUTH_FIELD_YEAR, AUTH_FIELD_URL, USHRT_MAX},//AUTH_TYPE_WWW, 101 {AUTH_FIELD_AUTHOR, AUTH_FIELD_TITLE, AUTH_FIELD_YEAR, USHRT_MAX, USHRT_MAX}, //AUTH_TYPE_CUSTOM1, 102 {AUTH_FIELD_AUTHOR, AUTH_FIELD_TITLE, AUTH_FIELD_YEAR, USHRT_MAX, USHRT_MAX}, //AUTH_TYPE_CUSTOM2, 103 {AUTH_FIELD_AUTHOR, AUTH_FIELD_TITLE, AUTH_FIELD_YEAR, USHRT_MAX, USHRT_MAX}, //AUTH_TYPE_CUSTOM3, 104 {AUTH_FIELD_AUTHOR, AUTH_FIELD_TITLE, AUTH_FIELD_YEAR, USHRT_MAX, USHRT_MAX}, //AUTH_TYPE_CUSTOM4, 105 {AUTH_FIELD_AUTHOR, AUTH_FIELD_TITLE, AUTH_FIELD_YEAR, USHRT_MAX, USHRT_MAX}, //AUTH_TYPE_CUSTOM5, 106 {AUTH_FIELD_AUTHOR, AUTH_FIELD_TITLE, AUTH_FIELD_YEAR, USHRT_MAX, USHRT_MAX}, //AUTH_FIELD_YEAR, 107 {AUTH_FIELD_AUTHOR, AUTH_FIELD_TITLE, AUTH_FIELD_YEAR, USHRT_MAX, USHRT_MAX}, //AUTH_FIELD_URL, 108 {AUTH_FIELD_AUTHOR, AUTH_FIELD_TITLE, AUTH_FIELD_YEAR, USHRT_MAX, USHRT_MAX}, //AUTH_FIELD_CUSTOM1, 109 {AUTH_FIELD_AUTHOR, AUTH_FIELD_TITLE, AUTH_FIELD_YEAR, USHRT_MAX, USHRT_MAX}, //AUTH_FIELD_CUSTOM2, 110 {AUTH_FIELD_AUTHOR, AUTH_FIELD_TITLE, AUTH_FIELD_YEAR, USHRT_MAX, USHRT_MAX}, //AUTH_FIELD_CUSTOM3, 111 {AUTH_FIELD_AUTHOR, AUTH_FIELD_TITLE, AUTH_FIELD_YEAR, USHRT_MAX, USHRT_MAX}, //AUTH_FIELD_CUSTOM4, 112 {AUTH_FIELD_AUTHOR, AUTH_FIELD_TITLE, AUTH_FIELD_YEAR, USHRT_MAX, USHRT_MAX}, //AUTH_FIELD_CUSTOM5, 113 {USHRT_MAX, USHRT_MAX, USHRT_MAX, USHRT_MAX, USHRT_MAX} 114 }; 115 116 SwFormTokens lcl_GetAuthPattern(sal_uInt16 nTypeId) 117 { 118 SwFormTokens aRet; 119 120 PatternIni aIni = aPatternIni[nTypeId]; 121 sal_uInt16 nVals[5]; 122 nVals[0] = aIni.n1; 123 nVals[1] = aIni.n2; 124 nVals[2] = aIni.n3; 125 nVals[3] = aIni.n4; 126 nVals[4] = aIni.n5; 127 128 SwFormToken aStartToken( TOKEN_AUTHORITY ); 129 aStartToken.nAuthorityField = AUTH_FIELD_IDENTIFIER; 130 aRet.push_back( aStartToken ); 131 SwFormToken aSeparatorToken( TOKEN_TEXT ); 132 aSeparatorToken.sText = String::CreateFromAscii( ": " ); 133 aRet.push_back( aSeparatorToken ); 134 SwFormToken aTextToken( TOKEN_TEXT ); 135 aTextToken.sText = String::CreateFromAscii( ", " ); 136 137 for(sal_uInt16 i = 0; i < 5 ; i++) 138 { 139 if(nVals[i] == USHRT_MAX) 140 break; 141 if( i > 0 ) 142 aRet.push_back( aTextToken ); 143 144 // -> #i21237# 145 SwFormToken aToken(TOKEN_AUTHORITY); 146 147 aToken.nAuthorityField = nVals[i]; 148 aRet.push_back(aToken); 149 // <- #i21237# 150 } 151 152 return aRet; 153 } 154 /*-------------------------------------------------------------------- 155 Beschreibung: Verzeichnis-Markierungen D/Ctor 156 --------------------------------------------------------------------*/ 157 158 159 /// pool default constructor 160 SwTOXMark::SwTOXMark() 161 : SfxPoolItem( RES_TXTATR_TOXMARK ) 162 , SwModify( 0 ) 163 , 164 pTxtAttr( 0 ), 165 bAutoGenerated(sal_False), 166 bMainEntry(sal_False) 167 { 168 } 169 170 171 SwTOXMark::SwTOXMark( const SwTOXType* pTyp ) 172 : SfxPoolItem( RES_TXTATR_TOXMARK ) 173 , SwModify( const_cast<SwTOXType*>(pTyp) ) 174 , 175 pTxtAttr( 0 ), nLevel( 0 ), 176 bAutoGenerated(sal_False), 177 bMainEntry(sal_False) 178 { 179 } 180 181 182 SwTOXMark::SwTOXMark( const SwTOXMark& rCopy ) 183 : SfxPoolItem( RES_TXTATR_TOXMARK ) 184 , SwModify(rCopy.GetRegisteredInNonConst()) 185 , 186 aPrimaryKey( rCopy.aPrimaryKey ), aSecondaryKey( rCopy.aSecondaryKey ), 187 aTextReading( rCopy.aTextReading ), 188 aPrimaryKeyReading( rCopy.aPrimaryKeyReading ), 189 aSecondaryKeyReading( rCopy.aSecondaryKeyReading ), 190 pTxtAttr( 0 ), nLevel( rCopy.nLevel ), 191 bAutoGenerated( rCopy.bAutoGenerated), 192 bMainEntry(rCopy.bMainEntry) 193 { 194 // AlternativString kopieren 195 aAltText = rCopy.aAltText; 196 } 197 198 199 SwTOXMark::~SwTOXMark() 200 { 201 } 202 203 204 void SwTOXMark::RegisterToTOXType( SwTOXType& rMark ) 205 { 206 rMark.Add(this); 207 } 208 209 int SwTOXMark::operator==( const SfxPoolItem& rAttr ) const 210 { 211 ASSERT( SfxPoolItem::operator==( rAttr ), "keine gleichen Attribute" ); 212 return GetRegisteredIn() == ((SwTOXMark&)rAttr).GetRegisteredIn(); 213 } 214 215 216 SfxPoolItem* SwTOXMark::Clone( SfxItemPool* ) const 217 { 218 return new SwTOXMark( *this ); 219 } 220 221 void SwTOXMark::Modify( const SfxPoolItem* pOld, const SfxPoolItem* pNew) 222 { 223 NotifyClients(pOld, pNew); 224 if (pOld && (RES_REMOVE_UNO_OBJECT == pOld->Which())) 225 { // invalidate cached uno object 226 SetXTOXMark(::com::sun::star::uno::Reference< 227 ::com::sun::star::text::XDocumentIndexMark>(0)); 228 } 229 } 230 231 void SwTOXMark::InvalidateTOXMark() 232 { 233 SwPtrMsgPoolItem aMsgHint( RES_REMOVE_UNO_OBJECT, 234 &static_cast<SwModify&>(*this) ); // cast to base class! 235 NotifyClients(&aMsgHint, &aMsgHint); 236 } 237 238 String SwTOXMark::GetText() const 239 { 240 String aStr; 241 if( aAltText.Len() ) 242 aStr = aAltText; 243 else if( pTxtAttr && pTxtAttr->GetpTxtNd() ) 244 { 245 const xub_StrLen* pEndIdx = pTxtAttr->GetEnd(); 246 ASSERT( pEndIdx, "TOXMark ohne Mark!!"); 247 if( pEndIdx ) 248 { 249 const xub_StrLen nStt = *pTxtAttr->GetStart(); 250 aStr = pTxtAttr->GetpTxtNd()->GetExpandTxt( nStt, *pEndIdx-nStt ); 251 } 252 } 253 return aStr; 254 } 255 256 void SwTOXMark::InsertTOXMarks( SwTOXMarks& aMarks, const SwTOXType& rType ) 257 { 258 SwIterator<SwTOXMark,SwTOXType> aIter(rType); 259 SwTOXMark* pMark = aIter.First(); 260 while( pMark ) 261 { 262 if(pMark->GetTxtTOXMark()) 263 aMarks.C40_INSERT(SwTOXMark, pMark, aMarks.Count()); 264 pMark = aIter.Next(); 265 } 266 } 267 268 /*-------------------------------------------------------------------- 269 Beschreibung: Typen von Verzeichnissen verwalten 270 --------------------------------------------------------------------*/ 271 272 SwTOXType::SwTOXType( TOXTypes eTyp, const String& rName ) 273 : SwModify(0), 274 aName(rName), 275 eType(eTyp) 276 { 277 } 278 279 280 SwTOXType::SwTOXType(const SwTOXType& rCopy) 281 : SwModify( (SwModify*)rCopy.GetRegisteredIn() ), 282 aName(rCopy.aName), 283 eType(rCopy.eType) 284 { 285 } 286 287 /*-------------------------------------------------------------------- 288 Beschreibung: Formen bearbeiten 289 --------------------------------------------------------------------*/ 290 291 SwForm::SwForm( TOXTypes eTyp ) // #i21237# 292 : eType( eTyp ), nFormMaxLevel( SwForm::GetFormMaxLevel( eTyp )), 293 // nFirstTabPos( lNumIndent ), 294 bCommaSeparated(sal_False) 295 { 296 //bHasFirstTabPos = 297 bGenerateTabPos = sal_False; 298 bIsRelTabPos = sal_True; 299 300 // Inhaltsverzeichnis hat entsprechend Anzahl Headlines + Ueberschrift 301 // Benutzer hat 10 Ebenen + Ueberschrift 302 // Stichwort hat 3 Ebenen + Ueberschrift + Trenner 303 // indexes of tables, objects illustrations and authorities consist of a heading and one level 304 305 sal_uInt16 nPoolId; 306 switch( eType ) 307 { 308 case TOX_INDEX: nPoolId = STR_POOLCOLL_TOX_IDXH; break; 309 case TOX_USER: nPoolId = STR_POOLCOLL_TOX_USERH; break; 310 case TOX_CONTENT: nPoolId = STR_POOLCOLL_TOX_CNTNTH; break; 311 case TOX_ILLUSTRATIONS: nPoolId = STR_POOLCOLL_TOX_ILLUSH; break; 312 case TOX_OBJECTS : nPoolId = STR_POOLCOLL_TOX_OBJECTH; break; 313 case TOX_TABLES : nPoolId = STR_POOLCOLL_TOX_TABLESH; break; 314 case TOX_AUTHORITIES : nPoolId = STR_POOLCOLL_TOX_AUTHORITIESH; break; 315 default: 316 ASSERT( !this, "ungueltiger TOXTyp"); 317 return ; 318 } 319 320 SwFormTokens aTokens; 321 if (TOX_CONTENT == eType) 322 { 323 aTokens.push_back(SwFormToken(TOKEN_ENTRY_NO)); 324 aTokens.push_back(SwFormToken(TOKEN_ENTRY_TEXT)); 325 } 326 else 327 aTokens.push_back(SwFormToken(TOKEN_ENTRY)); 328 329 if (TOX_AUTHORITIES != eType) 330 { 331 SwFormToken aToken(TOKEN_TAB_STOP); 332 aToken.nTabStopPosition = 0; 333 334 // --> FME 2004-12-10 #i36870# right aligned tab for all 335 aToken.cTabFillChar = '.'; 336 aToken.eTabAlign = SVX_TAB_ADJUST_END; 337 // <-- 338 339 aTokens.push_back(aToken); 340 aTokens.push_back(SwFormToken(TOKEN_PAGE_NUMS)); 341 } 342 343 SetTemplate( 0, SW_RESSTR( nPoolId++ )); 344 345 if(TOX_INDEX == eType) 346 { 347 for( sal_uInt16 i = 1; i < 5; ++i ) 348 { 349 if(1 == i) 350 { 351 SwFormTokens aTmpTokens; 352 SwFormToken aTmpToken(TOKEN_ENTRY); 353 aTmpTokens.push_back(aTmpToken); 354 355 SetPattern( i, aTmpTokens ); 356 SetTemplate( i, SW_RESSTR( STR_POOLCOLL_TOX_IDXBREAK )); 357 } 358 else 359 { 360 SetPattern( i, aTokens ); 361 SetTemplate( i, SW_RESSTR( STR_POOLCOLL_TOX_IDX1 + i - 2 )); 362 } 363 } 364 } 365 else 366 for( sal_uInt16 i = 1; i < GetFormMax(); ++i, ++nPoolId ) // Nr 0 ist der Titel 367 { 368 if(TOX_AUTHORITIES == eType) 369 SetPattern(i, lcl_GetAuthPattern(i)); 370 else 371 SetPattern( i, aTokens ); 372 373 if( TOX_CONTENT == eType && 6 == i ) 374 nPoolId = STR_POOLCOLL_TOX_CNTNT6; 375 else if( TOX_USER == eType && 6 == i ) 376 nPoolId = STR_POOLCOLL_TOX_USER6; 377 else if( TOX_AUTHORITIES == eType ) 378 nPoolId = STR_POOLCOLL_TOX_AUTHORITIES1; 379 SetTemplate( i, SW_RESSTR( nPoolId ) ); 380 } 381 } 382 383 384 SwForm::SwForm(const SwForm& rForm) 385 : eType( rForm.eType ) 386 { 387 *this = rForm; 388 } 389 390 391 SwForm& SwForm::operator=(const SwForm& rForm) 392 { 393 eType = rForm.eType; 394 nFormMaxLevel = rForm.nFormMaxLevel; 395 // nFirstTabPos = rForm.nFirstTabPos; 396 // bHasFirstTabPos = rForm.bHasFirstTabPos; 397 bGenerateTabPos = rForm.bGenerateTabPos; 398 bIsRelTabPos = rForm.bIsRelTabPos; 399 bCommaSeparated = rForm.bCommaSeparated; 400 for(sal_uInt16 i=0; i < nFormMaxLevel; ++i) 401 { 402 aPattern[i] = rForm.aPattern[i]; 403 aTemplate[i] = rForm.aTemplate[i]; 404 } 405 return *this; 406 } 407 408 sal_uInt16 SwForm::GetFormMaxLevel( TOXTypes eTOXType ) 409 { 410 sal_uInt16 nRet = 0; 411 switch( eTOXType ) 412 { 413 case TOX_INDEX: nRet = 5; break; 414 case TOX_USER: nRet = MAXLEVEL+1; break; 415 case TOX_CONTENT: nRet = MAXLEVEL+1; break; 416 case TOX_ILLUSTRATIONS: 417 case TOX_OBJECTS : 418 case TOX_TABLES : nRet = 2; break; 419 case TOX_AUTHORITIES : nRet = AUTH_TYPE_END + 1; break; 420 } 421 return nRet; 422 } 423 424 // #i21237# 425 bool operator == (const SwFormToken & rToken, FormTokenType eType) 426 { 427 return rToken.eTokenType == eType; 428 } 429 430 //----------------------------------------------------------------------------- 431 void SwForm::AdjustTabStops( SwDoc& rDoc ) // #i21237# 432 { 433 for(sal_uInt16 nLevel = 1; nLevel < GetFormMax(); nLevel++) 434 { 435 const String& sTemplateName = GetTemplate(nLevel); 436 437 SwTxtFmtColl* pColl = rDoc.FindTxtFmtCollByName( sTemplateName ); 438 if( pColl == NULL ) 439 { 440 const sal_uInt16 nId = 441 SwStyleNameMapper::GetPoolIdFromUIName( sTemplateName, nsSwGetPoolIdFromName::GET_POOLID_TXTCOLL ); 442 if ( USHRT_MAX != nId ) 443 pColl = rDoc.GetTxtCollFromPool( nId ); 444 } 445 446 const SvxTabStopItem* pTabStops = pColl != NULL ? &pColl->GetTabStops(sal_False) : 0; 447 const sal_uInt16 nTabCount = pTabStops != NULL ? pTabStops->Count() : 0; 448 if( pTabStops != NULL 449 && nTabCount != 0 ) 450 { 451 SwFormTokens aCurrentPattern = GetPattern(nLevel); 452 SwFormTokens::iterator aIt = aCurrentPattern.begin(); 453 454 bool bChanged = false; 455 for(sal_uInt16 nTab = 0; nTab < nTabCount; ++nTab) 456 { 457 const SvxTabStop& rTab = (*pTabStops)[nTab]; 458 459 aIt = find_if( aIt, aCurrentPattern.end(), SwFormTokenEqualToFormTokenType(TOKEN_TAB_STOP) ); 460 if ( aIt != aCurrentPattern.end() ) 461 { 462 bChanged = true; 463 aIt->nTabStopPosition = rTab.GetTabPos(); 464 aIt->eTabAlign = 465 ( nTab == nTabCount - 1 466 && rTab.GetAdjustment() == SVX_TAB_ADJUST_RIGHT ) 467 ? SVX_TAB_ADJUST_END 468 : rTab.GetAdjustment(); 469 aIt->cTabFillChar = rTab.GetFill(); 470 ++aIt; 471 } 472 else 473 break; // no more tokens to replace 474 } 475 476 if ( bChanged ) 477 SetPattern( nLevel, aCurrentPattern ); 478 } 479 } 480 } 481 /*-------------------------------------------------------------------- 482 Beschreibung: Ctor TOXBase 483 --------------------------------------------------------------------*/ 484 485 486 SwTOXBase::SwTOXBase(const SwTOXType* pTyp, const SwForm& rForm, 487 sal_uInt16 nCreaType, const String& rTitle ) 488 : SwClient((SwModify*)pTyp) 489 , aForm(rForm) 490 , aTitle(rTitle) 491 , eLanguage((LanguageType)::GetAppLanguage()) 492 , nCreateType(nCreaType) 493 , nOLEOptions(0) 494 , eCaptionDisplay(CAPTION_COMPLETE) 495 , bProtected( sal_True ) 496 , bFromChapter(sal_False) 497 , bFromObjectNames(sal_False) 498 , bLevelFromChapter(sal_False) 499 , maMSTOCExpression() 500 , mbKeepExpression(sal_True) 501 { 502 aData.nOptions = 0; 503 } 504 505 506 SwTOXBase::SwTOXBase( const SwTOXBase& rSource, SwDoc* pDoc ) 507 : SwClient( rSource.GetRegisteredInNonConst() ) 508 , mbKeepExpression(sal_True) 509 { 510 CopyTOXBase( pDoc, rSource ); 511 } 512 513 void SwTOXBase::RegisterToTOXType( SwTOXType& rType ) 514 { 515 rType.Add( this ); 516 } 517 518 SwTOXBase& SwTOXBase::CopyTOXBase( SwDoc* pDoc, const SwTOXBase& rSource ) 519 { 520 maMSTOCExpression = rSource.maMSTOCExpression; 521 SwTOXType* pType = (SwTOXType*)rSource.GetTOXType(); 522 if( pDoc && USHRT_MAX == pDoc->GetTOXTypes().GetPos( pType )) 523 { 524 // type not in pDoc, so create it now 525 const SwTOXTypes& rTypes = pDoc->GetTOXTypes(); 526 sal_Bool bFound = sal_False; 527 for( sal_uInt16 n = rTypes.Count(); n; ) 528 { 529 const SwTOXType* pCmp = rTypes[ --n ]; 530 if( pCmp->GetType() == pType->GetType() && 531 pCmp->GetTypeName() == pType->GetTypeName() ) 532 { 533 pType = (SwTOXType*)pCmp; 534 bFound = sal_True; 535 break; 536 } 537 } 538 539 if( !bFound ) 540 pType = (SwTOXType*)pDoc->InsertTOXType( *pType ); 541 } 542 pType->Add( this ); 543 544 nCreateType = rSource.nCreateType; 545 aTitle = rSource.aTitle; 546 aForm = rSource.aForm; 547 bProtected = rSource.bProtected; 548 bFromChapter = rSource.bFromChapter; 549 bFromObjectNames = rSource.bFromObjectNames; 550 sMainEntryCharStyle = rSource.sMainEntryCharStyle; 551 sSequenceName = rSource.sSequenceName; 552 eCaptionDisplay = rSource.eCaptionDisplay; 553 nOLEOptions = rSource.nOLEOptions; 554 eLanguage = rSource.eLanguage; 555 sSortAlgorithm = rSource.sSortAlgorithm; 556 557 for( sal_uInt16 i = 0; i < MAXLEVEL; ++i ) 558 aStyleNames[i] = rSource.aStyleNames[i]; 559 560 // its the same data type! 561 aData.nOptions = rSource.aData.nOptions; 562 563 if( !pDoc || pDoc->IsCopyIsMove() ) 564 aName = rSource.GetTOXName(); 565 else 566 aName = pDoc->GetUniqueTOXBaseName( *pType, &rSource.GetTOXName() ); 567 568 return *this; 569 } 570 571 /*-------------------------------------------------------------------- 572 Beschreibung: Verzeichnisspezifische Funktionen 573 --------------------------------------------------------------------*/ 574 575 SwTOXBase::~SwTOXBase() 576 { 577 // if( GetTOXType()->GetType() == TOX_USER ) 578 // delete aData.pTemplateName; 579 } 580 581 void SwTOXBase::SetTitle(const String& rTitle) 582 { aTitle = rTitle; } 583 584 585 SwTOXBase & SwTOXBase::operator = (const SwTOXBase & rSource) 586 { 587 ByteString aTmpStr(aTitle, RTL_TEXTENCODING_ASCII_US); 588 ByteString aTmpStr1(rSource.aTitle, RTL_TEXTENCODING_ASCII_US); 589 590 aForm = rSource.aForm; 591 aName = rSource.aName; 592 aTitle = rSource.aTitle; 593 sMainEntryCharStyle = rSource.sMainEntryCharStyle; 594 for(sal_uInt16 nLevel = 0; nLevel < MAXLEVEL; nLevel++) 595 aStyleNames[nLevel] = rSource.aStyleNames[nLevel]; 596 sSequenceName = rSource.sSequenceName; 597 eLanguage = rSource.eLanguage; 598 sSortAlgorithm = rSource.sSortAlgorithm; 599 aData = rSource.aData; 600 nCreateType = rSource.nCreateType; 601 nOLEOptions = rSource.nOLEOptions; 602 eCaptionDisplay = rSource.eCaptionDisplay; 603 bProtected = rSource.bProtected; 604 bFromChapter = rSource.bFromChapter; 605 bFromObjectNames = rSource.bFromObjectNames; 606 bLevelFromChapter = rSource.bLevelFromChapter; 607 608 if (rSource.GetAttrSet()) 609 SetAttrSet(*rSource.GetAttrSet()); 610 611 return *this; 612 } 613 614 /* -----------------16.07.99 16:02------------------- 615 616 SwTOXBase & SwTOXBase::operator = (const SwTOXBase & rSource) 617 { 618 aForm = rSource.aForm; 619 aName = rSource.aName; 620 aTitle = rSource.aTitle; 621 sMainEntryCharStyle = rSource.sMainEntryCharStyle; 622 sSequenceName = rSource.sSequenceName; 623 eLanguage = rSource.eLanguage; 624 sSortAlgorithm = rSource.sSortAlgorithm; 625 aData = rSource.aData; 626 nCreateType = rSource.nCreateType; 627 nOLEOptions = rSource.nOLEOptions; 628 eCaptionDisplay = rSource.eCaptionDisplay; 629 bProtected = rSource.bProtected; 630 bFromChapter = rSource.bFromChapter; 631 bFromObjectNames = rSource.bFromObjectNames; 632 bLevelFromChapter = rSource.bLevelFromChapter; 633 634 if (rSource.GetAttrSet()) 635 SetAttrSet(*rSource.GetAttrSet()); 636 637 return *this; 638 } 639 640 --------------------------------------------------*/ 641 642 String SwFormToken::GetString() const 643 { 644 String sRet; 645 646 sal_Bool bAppend = sal_True; 647 switch( eTokenType ) 648 { 649 case TOKEN_ENTRY_NO: 650 sRet.AssignAscii( SwForm::aFormEntryNum ); 651 break; 652 case TOKEN_ENTRY_TEXT: 653 sRet.AssignAscii( SwForm::aFormEntryTxt ); 654 break; 655 case TOKEN_ENTRY: 656 sRet.AssignAscii( SwForm::aFormEntry ); 657 break; 658 case TOKEN_TAB_STOP: 659 sRet.AssignAscii( SwForm::aFormTab ); 660 break; 661 case TOKEN_TEXT: 662 sRet.AssignAscii( SwForm::aFormText ); 663 break; 664 case TOKEN_PAGE_NUMS: 665 sRet.AssignAscii( SwForm::aFormPageNums ); 666 break; 667 case TOKEN_CHAPTER_INFO: 668 sRet.AssignAscii( SwForm::aFormChapterMark ); 669 break; 670 case TOKEN_LINK_START: 671 sRet.AssignAscii( SwForm::aFormLinkStt ); 672 break; 673 case TOKEN_LINK_END: 674 sRet.AssignAscii( SwForm::aFormLinkEnd ); 675 break; 676 case TOKEN_AUTHORITY: 677 { 678 sRet.AssignAscii( SwForm::aFormAuth ); 679 String sTmp( String::CreateFromInt32( nAuthorityField )); 680 if( sTmp.Len() < 2 ) 681 sTmp.Insert('0', 0); 682 sRet.Insert( sTmp, 2 ); 683 } 684 break; 685 case TOKEN_END: 686 break; 687 } 688 sRet.Erase( sRet.Len() - 1 ); 689 sRet += ' '; 690 sRet += sCharStyleName; 691 sRet += ','; 692 sRet += String::CreateFromInt32( nPoolId ); 693 sRet += ','; 694 695 // TabStopPosition and TabAlign or ChapterInfoFormat 696 if(TOKEN_TAB_STOP == eTokenType) 697 { 698 sRet += String::CreateFromInt32( nTabStopPosition ); 699 sRet += ','; 700 sRet += String::CreateFromInt32( static_cast< sal_Int32 >(eTabAlign) ); 701 sRet += ','; 702 sRet += cTabFillChar; 703 sRet += ','; 704 sRet += String::CreateFromInt32( bWithTab ); 705 } 706 else if(TOKEN_CHAPTER_INFO == eTokenType) 707 { 708 sRet += String::CreateFromInt32( nChapterFormat ); 709 //add maximum permetted level 710 sRet += ','; 711 sRet += String::CreateFromInt32( nOutlineLevel ); 712 } 713 else if(TOKEN_TEXT == eTokenType) 714 { 715 //append Text if Len() > 0 only! 716 if( sText.Len() ) 717 { 718 sRet += TOX_STYLE_DELIMITER; 719 String sTmp( sText ); 720 sTmp.EraseAllChars( TOX_STYLE_DELIMITER ); 721 sRet += sTmp; 722 sRet += TOX_STYLE_DELIMITER; 723 } 724 else 725 bAppend = sal_False; 726 } 727 else if(TOKEN_ENTRY_NO == eTokenType) 728 { 729 sRet += String::CreateFromInt32( nChapterFormat ); 730 //add maximum permitted level 731 sRet += ','; 732 sRet += String::CreateFromInt32( nOutlineLevel ); 733 } 734 735 if(bAppend) 736 { 737 sRet += '>'; 738 } 739 else 740 { 741 // don't append empty text tokens 742 sRet.Erase(); 743 } 744 745 return sRet; 746 } 747 748 // -> #i21237# 749 SwFormTokensHelper::SwFormTokensHelper(const String & rPattern) 750 { 751 xub_StrLen nCurPatternPos = 0; 752 xub_StrLen nCurPatternLen = 0; 753 754 while (nCurPatternPos < rPattern.Len()) 755 { 756 nCurPatternPos = nCurPatternPos + nCurPatternLen; 757 758 SwFormToken aToken = BuildToken(rPattern, nCurPatternPos); 759 aTokens.push_back(aToken); 760 } 761 } 762 763 SwFormToken SwFormTokensHelper::BuildToken( const String & sPattern, 764 xub_StrLen & nCurPatternPos ) const 765 { 766 String sToken( SearchNextToken(sPattern, nCurPatternPos) ); 767 nCurPatternPos = nCurPatternPos + sToken.Len(); 768 xub_StrLen nTokenLen; 769 FormTokenType eTokenType = GetTokenType(sToken, &nTokenLen); 770 771 // at this point sPattern contains the 772 // character style name, the PoolId, tab stop position, tab stop alignment, chapter info format 773 // the form is: CharStyleName, PoolId[, TabStopPosition|ChapterInfoFormat[, TabStopAlignment[, TabFillChar]]] 774 // in text tokens the form differs from the others: CharStyleName, PoolId[,\0xffinserted text\0xff] 775 SwFormToken eRet( eTokenType ); 776 String sAuthFieldEnum = sToken.Copy( 2, 2 ); 777 sToken = sToken.Copy( nTokenLen, sToken.Len() - nTokenLen - 1); 778 779 eRet.sCharStyleName = sToken.GetToken( 0, ','); 780 String sTmp( sToken.GetToken( 1, ',' )); 781 if( sTmp.Len() ) 782 eRet.nPoolId = static_cast<sal_uInt16>(sTmp.ToInt32()); 783 784 switch( eTokenType ) 785 { 786 //i53420 787 case TOKEN_ENTRY_NO: 788 if( (sTmp = sToken.GetToken( 2, ',' ) ).Len() ) 789 eRet.nChapterFormat = static_cast<sal_uInt16>(sTmp.ToInt32()); 790 if( (sTmp = sToken.GetToken( 3, ',' ) ).Len() ) 791 eRet.nOutlineLevel = static_cast<sal_uInt16>(sTmp.ToInt32()); //the maximum outline level to examine 792 break; 793 794 case TOKEN_TEXT: 795 { 796 xub_StrLen nStartText = sToken.Search( TOX_STYLE_DELIMITER ); 797 if( STRING_NOTFOUND != nStartText ) 798 { 799 xub_StrLen nEndText = sToken.Search( TOX_STYLE_DELIMITER, 800 nStartText + 1); 801 if( STRING_NOTFOUND != nEndText ) 802 { 803 eRet.sText = sToken.Copy( nStartText + 1, 804 nEndText - nStartText - 1); 805 } 806 } 807 } 808 break; 809 810 case TOKEN_TAB_STOP: 811 if( (sTmp = sToken.GetToken( 2, ',' ) ).Len() ) 812 eRet.nTabStopPosition = sTmp.ToInt32(); 813 814 if( (sTmp = sToken.GetToken( 3, ',' ) ).Len() ) 815 eRet.eTabAlign = static_cast<SvxTabAdjust>(sTmp.ToInt32()); 816 817 if( (sTmp = sToken.GetToken( 4, ',' ) ).Len() ) 818 eRet.cTabFillChar = sTmp.GetChar(0); 819 820 if( (sTmp = sToken.GetToken( 5, ',' ) ).Len() ) 821 eRet.bWithTab = 0 != sTmp.ToInt32(); 822 break; 823 824 case TOKEN_CHAPTER_INFO: 825 if( (sTmp = sToken.GetToken( 2, ',' ) ).Len() ) 826 eRet.nChapterFormat = static_cast<sal_uInt16>(sTmp.ToInt32()); //SwChapterFormat; 827 //i53420 828 if( (sTmp = sToken.GetToken( 3, ',' ) ).Len() ) 829 eRet.nOutlineLevel = static_cast<sal_uInt16>(sTmp.ToInt32()); //the maximum outline level to examine 830 831 break; 832 833 case TOKEN_AUTHORITY: 834 eRet.nAuthorityField = static_cast<sal_uInt16>(sAuthFieldEnum.ToInt32()); 835 break; 836 default: break; 837 } 838 return eRet; 839 } 840 841 String SwFormTokensHelper::SearchNextToken( const String & sPattern, 842 xub_StrLen nStt ) const 843 { 844 //it's not so easy - it doesn't work if the text part contains a '>' 845 //sal_uInt16 nTokenEnd = sPattern.Search('>'); 846 847 String aResult; 848 849 xub_StrLen nEnd = sPattern.Search( '>', nStt ); 850 if( STRING_NOTFOUND == nEnd ) 851 { 852 nEnd = sPattern.Len(); 853 } 854 else 855 { 856 xub_StrLen nTextSeparatorFirst = sPattern.Search( TOX_STYLE_DELIMITER, nStt ); 857 if( STRING_NOTFOUND != nTextSeparatorFirst ) 858 { 859 xub_StrLen nTextSeparatorSecond = sPattern.Search( TOX_STYLE_DELIMITER, 860 nTextSeparatorFirst + 1 ); 861 if( STRING_NOTFOUND != nTextSeparatorSecond && 862 nEnd > nTextSeparatorFirst ) 863 nEnd = sPattern.Search( '>', nTextSeparatorSecond ); 864 } 865 866 ++nEnd; 867 868 aResult = sPattern.Copy( nStt, nEnd - nStt ); 869 } 870 871 return aResult; 872 } 873 874 FormTokenType SwFormTokensHelper::GetTokenType(const String & sToken, 875 xub_StrLen * pTokenLen) const 876 { 877 static struct 878 { 879 const sal_Char* pNm; 880 sal_uInt16 nLen; 881 sal_uInt16 nOffset; 882 FormTokenType eToken; 883 } __READONLY_DATA aTokenArr[] = { 884 { SwForm::aFormTab, SwForm::nFormEntryLen, 1, TOKEN_TAB_STOP }, 885 { SwForm::aFormPageNums, SwForm::nFormPageNumsLen, 1, TOKEN_PAGE_NUMS }, 886 { SwForm::aFormLinkStt, SwForm::nFormLinkSttLen, 1, TOKEN_LINK_START }, 887 { SwForm::aFormLinkEnd, SwForm::nFormLinkEndLen, 1, TOKEN_LINK_END }, 888 { SwForm::aFormEntryNum, SwForm::nFormEntryNumLen, 1, TOKEN_ENTRY_NO }, 889 { SwForm::aFormEntryTxt, SwForm::nFormEntryTxtLen, 1, TOKEN_ENTRY_TEXT }, 890 { SwForm::aFormChapterMark,SwForm::nFormChapterMarkLen,1,TOKEN_CHAPTER_INFO }, 891 { SwForm::aFormText, SwForm::nFormTextLen, 1, TOKEN_TEXT }, 892 { SwForm::aFormEntry, SwForm::nFormEntryLen, 1, TOKEN_ENTRY }, 893 { SwForm::aFormAuth, SwForm::nFormAuthLen, 3, TOKEN_AUTHORITY }, 894 { 0, 0, 0, TOKEN_END } 895 }; 896 897 FormTokenType eTokenType = TOKEN_TEXT; 898 xub_StrLen nTokenLen = 0; 899 const sal_Char* pNm; 900 for( int i = 0; 0 != ( pNm = aTokenArr[ i ].pNm ); ++i ) 901 if( COMPARE_EQUAL == sToken.CompareToAscii( pNm, 902 aTokenArr[ i ].nLen - aTokenArr[ i ].nOffset )) 903 { 904 eTokenType = aTokenArr[ i ].eToken; 905 nTokenLen = aTokenArr[ i ].nLen; 906 break; 907 } 908 909 ASSERT( pNm, "wrong token" ); 910 if (pTokenLen) 911 *pTokenLen = nTokenLen; 912 913 return eTokenType; 914 } 915 916 // <- #i21237# 917 918 void SwForm::SetPattern(sal_uInt16 nLevel, const SwFormTokens& rTokens) 919 { 920 ASSERT(nLevel < GetFormMax(), "Index >= FORM_MAX"); 921 aPattern[nLevel] = rTokens; 922 } 923 924 void SwForm::SetPattern(sal_uInt16 nLevel, const String & rStr) 925 { 926 ASSERT(nLevel < GetFormMax(), "Index >= FORM_MAX"); 927 928 SwFormTokensHelper aHelper(rStr); 929 aPattern[nLevel] = aHelper.GetTokens(); 930 } 931 932 const SwFormTokens& SwForm::GetPattern(sal_uInt16 nLevel) const 933 { 934 ASSERT(nLevel < GetFormMax(), "Index >= FORM_MAX"); 935 return aPattern[nLevel]; 936 } 937 938