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 <doc.hxx>
28 #include <UndoManager.hxx>
29 #include <hintids.hxx>
30 #include <tools/shl.hxx>
31 #include <tools/globname.hxx>
32 #include <svx/svxids.hrc>
33 #include <com/sun/star/i18n/WordType.hdl>
34 #include <com/sun/star/i18n/ForbiddenCharacters.hdl>
35 #include <com/sun/star/lang/XMultiServiceFactory.hpp>
36 #include <com/sun/star/beans/NamedValue.hpp>
37 #include <com/sun/star/beans/XPropertySet.hpp>
38 #include <com/sun/star/document/XDocumentPropertiesSupplier.hpp>
39 #include <com/sun/star/document/XDocumentProperties.hpp>
40 #include <comphelper/processfactory.hxx>
41 #include <tools/urlobj.hxx>
42 #include <tools/poly.hxx>
43 #include <tools/multisel.hxx>
44 #include <rtl/ustring.hxx>
45 #include <vcl/virdev.hxx>
46 #include <svl/itemiter.hxx>
47 #include <svl/poolitem.hxx>
48 #include <unotools/syslocale.hxx>
49 #include <sfx2/printer.hxx>
50 #include <editeng/keepitem.hxx>
51 #include <editeng/cscoitem.hxx>
52 #include <editeng/brkitem.hxx>
53 #include <sfx2/linkmgr.hxx>
54 #include <editeng/forbiddencharacterstable.hxx>
55 #include <svx/svdmodel.hxx>
56 #include <editeng/pbinitem.hxx>
57 #include <unotools/charclass.hxx>
58 #include <unotools/localedatawrapper.hxx>
59 #include <swatrset.hxx>
60 #include <swmodule.hxx>
61 #include <fmtpdsc.hxx>
62 #include <fmtanchr.hxx>
63 #include <fmtrfmrk.hxx>
64 #include <fmtinfmt.hxx>
65 #include <fmtfld.hxx>
66 #include <txtfld.hxx>
67 #include <dbfld.hxx>
68 #include <txtinet.hxx>
69 #include <txtrfmrk.hxx>
70 #include <frmatr.hxx>
71 #include <linkenum.hxx>
72 #include <errhdl.hxx>
73 #include <pagefrm.hxx>
74 #include <rootfrm.hxx>
75 #include <swtable.hxx>
76 #include <pam.hxx>
77 #include <ndtxt.hxx>
78 #include <swundo.hxx> // for the UndoIds
79 #include <UndoCore.hxx>
80 #include <UndoInsert.hxx>
81 #include <UndoSplitMove.hxx>
82 #include <UndoTable.hxx>
83 #include <pagedesc.hxx> //DTor
84 #include <breakit.hxx>
85 #include <ndole.hxx>
86 #include <ndgrf.hxx>
87 #include <rolbck.hxx> // Undo-Attr
88 #include <doctxm.hxx> // for the directories
89 #include <grfatr.hxx>
90 #include <poolfmt.hxx> // PoolTemplate ID's
91 #include <mvsave.hxx> // for server functionality
92 #include <SwGrammarMarkUp.hxx>
93 #include <scriptinfo.hxx>
94 #include <acorrect.hxx> // AutoCorrect
95 #include <mdiexp.hxx> // status display
96 #include <docstat.hxx>
97 #include <docary.hxx>
98 #include <redline.hxx>
99 #include <fldupde.hxx>
100 #include <swbaslnk.hxx>
101 #include <printdata.hxx>
102 #include <cmdid.h> // for the dflt - Printer in SetJob
103 #include <statstr.hrc> // StatLine string
104 #include <comcore.hrc>
105 #include <SwUndoTOXChange.hxx>
106 #include <SwUndoFmt.hxx>
107 #include <unocrsr.hxx>
108 #include <docsh.hxx>
109 #include <viewopt.hxx>
110 #include <docfld.hxx> // _SetGetExpFld
111 #include <docufld.hxx> // SwPostItField
112 #include <viewsh.hxx>
113 #include <shellres.hxx>
114 #include <txtfrm.hxx>
115 #include <attrhint.hxx>
116 #include <wdocsh.hxx> // SwWebDocShell
117 #include <prtopt.hxx> // SwPrintOptions
118 #include <vector>
119 #include <map>
120 #include <osl/diagnose.h>
121 #include <osl/interlck.h>
122 #include <vbahelper/vbaaccesshelper.hxx>
123 #include "switerator.hxx"
124 #include <layouter.hxx>
125 #include <drawdoc.hxx>
126
127 using namespace ::com::sun::star;
128 using ::rtl::OUString;
129
130
131 // Page descriptors
132 SV_IMPL_PTRARR(SwPageDescs,SwPageDescPtr);
133 // Directories
SV_IMPL_PTRARR(SwTOXTypes,SwTOXTypePtr)134 SV_IMPL_PTRARR( SwTOXTypes, SwTOXTypePtr )
135 // Field types
136 SV_IMPL_PTRARR( SwFldTypes, SwFldTypePtr)
137
138 /** IInterface
139 */
140 sal_Int32 SwDoc::acquire()
141 {
142 OSL_ASSERT(mReferenceCount >= 0 && "Negative reference count detected! This is a sign for unbalanced acquire/release calls.");
143 return osl_incrementInterlockedCount(&mReferenceCount);
144 }
145
release()146 sal_Int32 SwDoc::release()
147 {
148 OSL_PRECOND(mReferenceCount >= 1, "Object is already released! Releasing it again leads to a negative reference count.");
149 return osl_decrementInterlockedCount(&mReferenceCount);
150 }
151
getReferenceCount() const152 sal_Int32 SwDoc::getReferenceCount() const
153 {
154 OSL_ASSERT(mReferenceCount >= 0 && "Negative reference count detected! This is a sign for unbalanced acquire/release calls.");
155 return mReferenceCount;
156 }
157
158 /** IDocumentSettingAccess
159 */
get(DocumentSettingId id) const160 bool SwDoc::get(/*[in]*/ DocumentSettingId id) const
161 {
162 switch (id)
163 {
164 // COMPATIBILITY FLAGS START
165 case PARA_SPACE_MAX: return mbParaSpaceMax; //(n8Dummy1 & DUMMY_PARASPACEMAX);
166 case PARA_SPACE_MAX_AT_PAGES: return mbParaSpaceMaxAtPages; //(n8Dummy1 & DUMMY_PARASPACEMAX_AT_PAGES);
167 case TAB_COMPAT: return mbTabCompat; //(n8Dummy1 & DUMMY_TAB_COMPAT);
168 case ADD_FLY_OFFSETS: return mbAddFlyOffsets; //(n8Dummy2 & DUMMY_ADD_FLY_OFFSETS);
169 case ADD_EXT_LEADING: return mbAddExternalLeading; //(n8Dummy2 & DUMMY_ADD_EXTERNAL_LEADING);
170 case USE_VIRTUAL_DEVICE: return mbUseVirtualDevice; //(n8Dummy1 & DUMMY_USE_VIRTUAL_DEVICE);
171 case USE_HIRES_VIRTUAL_DEVICE: return mbUseHiResolutionVirtualDevice; //(n8Dummy2 & DUMMY_USE_HIRES_VIR_DEV);
172 case OLD_NUMBERING: return mbOldNumbering;
173 case OLD_LINE_SPACING: return mbOldLineSpacing;
174 case ADD_PARA_SPACING_TO_TABLE_CELLS: return mbAddParaSpacingToTableCells;
175 case USE_FORMER_OBJECT_POS: return mbUseFormerObjectPos;
176 case USE_FORMER_TEXT_WRAPPING: return mbUseFormerTextWrapping;
177 case CONSIDER_WRAP_ON_OBJECT_POSITION: return mbConsiderWrapOnObjPos;
178 case DO_NOT_JUSTIFY_LINES_WITH_MANUAL_BREAK: return mbDoNotJustifyLinesWithManualBreak;
179 case IGNORE_FIRST_LINE_INDENT_IN_NUMBERING: return mbIgnoreFirstLineIndentInNumbering;
180 case OUTLINE_LEVEL_YIELDS_OUTLINE_RULE: return mbOutlineLevelYieldsOutlineRule;
181 case TABLE_ROW_KEEP: return mbTableRowKeep;
182 case IGNORE_TABS_AND_BLANKS_FOR_LINE_CALCULATION: return mbIgnoreTabsAndBlanksForLineCalculation;
183 case DO_NOT_CAPTURE_DRAW_OBJS_ON_PAGE: return mbDoNotCaptureDrawObjsOnPage;
184 // --> OD 2006-08-25 #i68949#
185 case CLIP_AS_CHARACTER_ANCHORED_WRITER_FLY_FRAME: return mbClipAsCharacterAnchoredWriterFlyFrames;
186 // <--
187 case UNIX_FORCE_ZERO_EXT_LEADING: return mbUnixForceZeroExtLeading;
188 case USE_OLD_PRINTER_METRICS: return mbOldPrinterMetrics;
189 case TABS_RELATIVE_TO_INDENT : return mbTabRelativeToIndent;
190 case PROTECT_FORM: return mbProtectForm;
191 // --> OD 2008-06-05 #i89181#
192 case TAB_AT_LEFT_INDENT_FOR_PARA_IN_LIST: return mbTabAtLeftIndentForParagraphsInList;
193 // <--
194 // COMPATIBILITY FLAGS END
195
196 case BROWSE_MODE: return mbLastBrowseMode; // Attention: normally the ViewShell has to be asked!
197 case HTML_MODE: return mbHTMLMode;
198 case GLOBAL_DOCUMENT: return mbIsGlobalDoc;
199 case GLOBAL_DOCUMENT_SAVE_LINKS: return mbGlblDocSaveLinks;
200 case LABEL_DOCUMENT: return mbIsLabelDoc;
201 case PURGE_OLE: return mbPurgeOLE;
202 case KERN_ASIAN_PUNCTUATION: return mbKernAsianPunctuation;
203 case DO_NOT_RESET_PARA_ATTRS_FOR_NUM_FONT: return mbDoNotResetParaAttrsForNumFont;
204 case MATH_BASELINE_ALIGNMENT: return mbMathBaselineAlignment;
205 default:
206 ASSERT(false, "Invalid setting id");
207 }
208 return false;
209 }
210
set(DocumentSettingId id,bool value)211 void SwDoc::set(/*[in]*/ DocumentSettingId id, /*[in]*/ bool value)
212 {
213 switch (id)
214 {
215 // COMPATIBILITY FLAGS START
216 case PARA_SPACE_MAX:
217 mbParaSpaceMax = value;
218 break;
219 case PARA_SPACE_MAX_AT_PAGES:
220 mbParaSpaceMaxAtPages = value;
221 break;
222 case TAB_COMPAT:
223 mbTabCompat = value;
224 break;
225 case ADD_FLY_OFFSETS:
226 mbAddFlyOffsets = value;
227 break;
228 case ADD_EXT_LEADING:
229 mbAddExternalLeading = value;
230 break;
231 case USE_VIRTUAL_DEVICE:
232 mbUseVirtualDevice = value;
233 break;
234 case USE_HIRES_VIRTUAL_DEVICE:
235 mbUseHiResolutionVirtualDevice = value;
236 break;
237 case OLD_NUMBERING:
238 if (mbOldNumbering != value)
239 {
240 mbOldNumbering = value;
241
242 const SwNumRuleTbl& rNmTbl = GetNumRuleTbl();
243 for( sal_uInt16 n = 0; n < rNmTbl.Count(); ++n )
244 rNmTbl[n]->SetInvalidRule(sal_True);
245
246 UpdateNumRule();
247
248 if (pOutlineRule)
249 {
250 pOutlineRule->Validate();
251 // counting of phantoms depends on <IsOldNumbering()>
252 pOutlineRule->SetCountPhantoms( !mbOldNumbering );
253 }
254 }
255 break;
256 case OLD_LINE_SPACING:
257 mbOldLineSpacing = value;
258 break;
259 case ADD_PARA_SPACING_TO_TABLE_CELLS:
260 mbAddParaSpacingToTableCells = value;
261 break;
262 case USE_FORMER_OBJECT_POS:
263 mbUseFormerObjectPos = value;
264 break;
265 case USE_FORMER_TEXT_WRAPPING:
266 mbUseFormerTextWrapping = value;
267 break;
268 case CONSIDER_WRAP_ON_OBJECT_POSITION:
269 mbConsiderWrapOnObjPos = value;
270 break;
271 case DO_NOT_JUSTIFY_LINES_WITH_MANUAL_BREAK:
272 mbDoNotJustifyLinesWithManualBreak = value;
273 break;
274 case IGNORE_FIRST_LINE_INDENT_IN_NUMBERING:
275 mbIgnoreFirstLineIndentInNumbering = value;
276 break;
277
278 case OUTLINE_LEVEL_YIELDS_OUTLINE_RULE:
279 mbOutlineLevelYieldsOutlineRule = value;
280 break;
281
282 case TABLE_ROW_KEEP:
283 mbTableRowKeep = value;
284 break;
285
286 case IGNORE_TABS_AND_BLANKS_FOR_LINE_CALCULATION:
287 mbIgnoreTabsAndBlanksForLineCalculation = value;
288 break;
289
290 case DO_NOT_CAPTURE_DRAW_OBJS_ON_PAGE:
291 mbDoNotCaptureDrawObjsOnPage = value;
292 break;
293
294 case CLIP_AS_CHARACTER_ANCHORED_WRITER_FLY_FRAME:
295 mbClipAsCharacterAnchoredWriterFlyFrames = value;
296 break;
297
298 case UNIX_FORCE_ZERO_EXT_LEADING:
299 mbUnixForceZeroExtLeading = value;
300 break;
301
302 case PROTECT_FORM:
303 mbProtectForm = value;
304 break;
305
306 case USE_OLD_PRINTER_METRICS:
307 mbOldPrinterMetrics = value;
308 break;
309
310 case TABS_RELATIVE_TO_INDENT:
311 mbTabRelativeToIndent = value;
312 break;
313
314 case TAB_AT_LEFT_INDENT_FOR_PARA_IN_LIST:
315 mbTabAtLeftIndentForParagraphsInList = value;
316 break;
317
318 // COMPATIBILITY FLAGS END
319
320 case BROWSE_MODE: //can be used temporary (load/save) when no ViewShell is available
321 mbLastBrowseMode = value;
322 break;
323 case HTML_MODE:
324 mbHTMLMode = value;
325 break;
326 case GLOBAL_DOCUMENT:
327 mbIsGlobalDoc = value;
328 break;
329 case GLOBAL_DOCUMENT_SAVE_LINKS:
330 mbGlblDocSaveLinks = value;
331 break;
332 case LABEL_DOCUMENT:
333 mbIsLabelDoc = value;
334 break;
335 case PURGE_OLE:
336 mbPurgeOLE = value;
337 break;
338 case KERN_ASIAN_PUNCTUATION:
339 mbKernAsianPunctuation = value;
340 break;
341 case DO_NOT_RESET_PARA_ATTRS_FOR_NUM_FONT:
342 mbDoNotResetParaAttrsForNumFont = value;
343 break;
344 case MATH_BASELINE_ALIGNMENT:
345 mbMathBaselineAlignment = value;
346 break;
347 default:
348 ASSERT(false, "Invalid setting id");
349 }
350 }
351
352 const i18n::ForbiddenCharacters*
getForbiddenCharacters(sal_uInt16 nLang,bool bLocaleData) const353 SwDoc::getForbiddenCharacters(/*[in]*/ sal_uInt16 nLang, /*[in]*/ bool bLocaleData ) const
354 {
355 const i18n::ForbiddenCharacters* pRet = 0;
356 if( xForbiddenCharsTable.isValid() )
357 pRet = xForbiddenCharsTable->GetForbiddenCharacters( nLang, sal_False );
358 if( bLocaleData && !pRet && pBreakIt )
359 pRet = &pBreakIt->GetForbidden( (LanguageType)nLang );
360 return pRet;
361 }
362
setForbiddenCharacters(sal_uInt16 nLang,const com::sun::star::i18n::ForbiddenCharacters & rFChars)363 void SwDoc::setForbiddenCharacters(/*[in]*/ sal_uInt16 nLang,
364 /*[in]*/ const com::sun::star::i18n::ForbiddenCharacters& rFChars )
365 {
366 if( !xForbiddenCharsTable.isValid() )
367 {
368 uno::Reference<
369 lang::XMultiServiceFactory > xMSF =
370 ::comphelper::getProcessServiceFactory();
371 xForbiddenCharsTable = new SvxForbiddenCharactersTable( xMSF );
372 }
373 xForbiddenCharsTable->SetForbiddenCharacters( nLang, rFChars );
374 if( pDrawModel )
375 {
376 pDrawModel->SetForbiddenCharsTable( xForbiddenCharsTable );
377 if( !mbInReading )
378 pDrawModel->ReformatAllTextObjects();
379 }
380
381 SwRootFrm* pTmpRoot = GetCurrentLayout();
382 if( pTmpRoot && !mbInReading )
383 {
384 pTmpRoot->StartAllAction();
385 std::set<SwRootFrm*> aAllLayouts = GetAllLayouts();
386 std::for_each( aAllLayouts.begin(), aAllLayouts.end(), std::bind2nd(std::mem_fun(&SwRootFrm::InvalidateAllCntnt), INV_SIZE));
387 pTmpRoot->EndAllAction();
388 }//swmod 080310
389 SetModified();
390 }
391
getForbiddenCharacterTable()392 vos::ORef<SvxForbiddenCharactersTable>& SwDoc::getForbiddenCharacterTable()
393 {
394 if( !xForbiddenCharsTable.isValid() )
395 {
396 uno::Reference<
397 lang::XMultiServiceFactory > xMSF =
398 ::comphelper::getProcessServiceFactory();
399 xForbiddenCharsTable = new SvxForbiddenCharactersTable( xMSF );
400 }
401 return xForbiddenCharsTable;
402 }
403
getForbiddenCharacterTable() const404 const vos::ORef<SvxForbiddenCharactersTable>& SwDoc::getForbiddenCharacterTable() const
405 {
406 return xForbiddenCharsTable;
407 }
408
getLinkUpdateMode(bool bGlobalSettings) const409 sal_uInt16 SwDoc::getLinkUpdateMode( /*[in]*/bool bGlobalSettings ) const
410 {
411 sal_uInt16 nRet = nLinkUpdMode;
412 if( bGlobalSettings && GLOBALSETTING == nRet )
413 nRet = SW_MOD()->GetLinkUpdMode(get(IDocumentSettingAccess::HTML_MODE));
414 return nRet;
415 }
416
setLinkUpdateMode(sal_uInt16 eMode)417 void SwDoc::setLinkUpdateMode( /*[in]*/sal_uInt16 eMode )
418 {
419 nLinkUpdMode = eMode;
420 }
421
getFieldUpdateFlags(bool bGlobalSettings) const422 SwFldUpdateFlags SwDoc::getFieldUpdateFlags( /*[in]*/bool bGlobalSettings ) const
423 {
424 SwFldUpdateFlags eRet = eFldUpdMode;
425 if( bGlobalSettings && AUTOUPD_GLOBALSETTING == eRet )
426 eRet = SW_MOD()->GetFldUpdateFlags(get(IDocumentSettingAccess::HTML_MODE));
427 return eRet;
428 }
429
setFieldUpdateFlags(SwFldUpdateFlags eMode)430 void SwDoc::setFieldUpdateFlags(/*[in]*/SwFldUpdateFlags eMode )
431 {
432 eFldUpdMode = eMode;
433 }
434
getCharacterCompressionType() const435 SwCharCompressType SwDoc::getCharacterCompressionType() const
436 {
437 return eChrCmprType;
438 }
439
setCharacterCompressionType(SwCharCompressType n)440 void SwDoc::setCharacterCompressionType( /*[in]*/SwCharCompressType n )
441 {
442 if( eChrCmprType != n )
443 {
444 eChrCmprType = n;
445 if( pDrawModel )
446 {
447 pDrawModel->SetCharCompressType( static_cast<sal_uInt16>(n) );
448 if( !mbInReading )
449 pDrawModel->ReformatAllTextObjects();
450 }
451
452 SwRootFrm* pTmpRoot = GetCurrentLayout();
453 if( pTmpRoot && !mbInReading )
454 {
455 pTmpRoot->StartAllAction();
456 std::set<SwRootFrm*> aAllLayouts = GetAllLayouts();
457 std::for_each( aAllLayouts.begin(), aAllLayouts.end(), std::bind2nd(std::mem_fun(&SwRootFrm::InvalidateAllCntnt), INV_SIZE));
458 pTmpRoot->EndAllAction();
459 }//swmod 080310
460 SetModified();
461 }
462 }
463
464 /** IDocumentDeviceAccess
465 */
getPrinter(bool bCreate) const466 SfxPrinter* SwDoc::getPrinter(/*[in]*/ bool bCreate ) const
467 {
468 SfxPrinter* pRet = 0;
469 if ( !bCreate || pPrt )
470 pRet = pPrt;
471 else
472 pRet = &CreatePrinter_();
473
474 return pRet;
475 }
476
setPrinter(SfxPrinter * pP,bool bDeleteOld,bool bCallPrtDataChanged)477 void SwDoc::setPrinter(/*[in]*/ SfxPrinter *pP,/*[in]*/ bool bDeleteOld,/*[in]*/ bool bCallPrtDataChanged )
478 {
479 if ( pP != pPrt )
480 {
481 if ( bDeleteOld )
482 delete pPrt;
483 pPrt = pP;
484
485 // our printer should always use TWIP. Don't rely on this being set in ViewShell::InitPrt, there
486 // are situations where this isn't called.
487 // #i108712# / 2010-02-26 / frank.schoenheit@sun.com
488 if ( pPrt )
489 {
490 MapMode aMapMode( pPrt->GetMapMode() );
491 aMapMode.SetMapUnit( MAP_TWIP );
492 pPrt->SetMapMode( aMapMode );
493 }
494
495 if ( pDrawModel && !get( IDocumentSettingAccess::USE_VIRTUAL_DEVICE ) )
496 pDrawModel->SetRefDevice( pPrt );
497 }
498
499 if ( bCallPrtDataChanged &&
500 // --> FME 2005-01-21 #i41075# Do not call PrtDataChanged() if we do not
501 // use the printer for formatting:
502 !get(IDocumentSettingAccess::USE_VIRTUAL_DEVICE) )
503 // <--
504 PrtDataChanged();
505 }
506
getVirtualDevice(bool bCreate) const507 VirtualDevice* SwDoc::getVirtualDevice(/*[in]*/ bool bCreate ) const
508 {
509 VirtualDevice* pRet = 0;
510 if ( !bCreate || pVirDev )
511 pRet = pVirDev;
512 else
513 pRet = &CreateVirtualDevice_();
514
515 return pRet;
516 }
517
setVirtualDevice(VirtualDevice * pVd,bool bDeleteOld,bool)518 void SwDoc::setVirtualDevice(/*[in]*/ VirtualDevice* pVd,/*[in]*/ bool bDeleteOld, /*[in]*/ bool )
519 {
520 if ( pVirDev != pVd )
521 {
522 if ( bDeleteOld )
523 delete pVirDev;
524 pVirDev = pVd;
525
526 if ( pDrawModel && get( IDocumentSettingAccess::USE_VIRTUAL_DEVICE ) )
527 pDrawModel->SetRefDevice( pVirDev );
528 }
529 }
530
getReferenceDevice(bool bCreate) const531 OutputDevice* SwDoc::getReferenceDevice(/*[in]*/ bool bCreate ) const
532 {
533 OutputDevice* pRet = 0;
534 if ( !get(IDocumentSettingAccess::USE_VIRTUAL_DEVICE) )
535 {
536 pRet = getPrinter( bCreate );
537
538 if ( bCreate && !pPrt->IsValid() )
539 {
540 pRet = getVirtualDevice( sal_True );
541 }
542 }
543 else
544 {
545 pRet = getVirtualDevice( bCreate );
546 }
547
548 return pRet;
549 }
550
setReferenceDeviceType(bool bNewVirtual,bool bNewHiRes)551 void SwDoc::setReferenceDeviceType(/*[in]*/ bool bNewVirtual,/*[in]*/ bool bNewHiRes )
552 {
553 if ( get(IDocumentSettingAccess::USE_VIRTUAL_DEVICE) != bNewVirtual ||
554 get(IDocumentSettingAccess::USE_HIRES_VIRTUAL_DEVICE) != bNewHiRes )
555 {
556 if ( bNewVirtual )
557 {
558 VirtualDevice* pMyVirDev = getVirtualDevice( true );
559 if ( !bNewHiRes )
560 pMyVirDev->SetReferenceDevice( VirtualDevice::REFDEV_MODE06 );
561 else
562 pMyVirDev->SetReferenceDevice( VirtualDevice::REFDEV_MODE_MSO1 );
563
564 if( pDrawModel )
565 pDrawModel->SetRefDevice( pMyVirDev );
566 }
567 else
568 {
569 // --> FME 2005-01-21 #i41075#
570 // We have to take care that a printer exists before calling
571 // PrtDataChanged() in order to prevent that PrtDataChanged()
572 // triggers this funny situation:
573 // getReferenceDevice()->getPrinter()->CreatePrinter_()
574 // ->setPrinter()-> PrtDataChanged()
575 SfxPrinter* pPrinter = getPrinter( true );
576 // <--
577 if( pDrawModel )
578 pDrawModel->SetRefDevice( pPrinter );
579 }
580
581 set(IDocumentSettingAccess::USE_VIRTUAL_DEVICE, bNewVirtual );
582 set(IDocumentSettingAccess::USE_HIRES_VIRTUAL_DEVICE, bNewHiRes );
583 PrtDataChanged();
584 SetModified();
585 }
586 }
587
getJobsetup() const588 const JobSetup* SwDoc::getJobsetup() const
589 {
590 return pPrt ? &pPrt->GetJobSetup() : 0;
591 }
592
setJobsetup(const JobSetup & rJobSetup)593 void SwDoc::setJobsetup(/*[in]*/ const JobSetup &rJobSetup )
594 {
595 sal_Bool bCheckPageDescs = 0 == pPrt;
596 sal_Bool bDataChanged = sal_False;
597
598 if ( pPrt )
599 {
600 if ( pPrt->GetName() == rJobSetup.GetPrinterName() )
601 {
602 if ( pPrt->GetJobSetup() != rJobSetup )
603 {
604 pPrt->SetJobSetup( rJobSetup );
605 bDataChanged = sal_True;
606 }
607 }
608 else
609 delete pPrt, pPrt = 0;
610 }
611
612 if( !pPrt )
613 {
614 // the ItemSet will be deleted by Sfx!
615 SfxItemSet *pSet = new SfxItemSet( GetAttrPool(),
616 FN_PARAM_ADDPRINTER, FN_PARAM_ADDPRINTER,
617 SID_HTML_MODE, SID_HTML_MODE,
618 SID_PRINTER_NOTFOUND_WARN, SID_PRINTER_NOTFOUND_WARN,
619 SID_PRINTER_CHANGESTODOC, SID_PRINTER_CHANGESTODOC,
620 0 );
621 SfxPrinter *p = new SfxPrinter( pSet, rJobSetup );
622 if ( bCheckPageDescs )
623 setPrinter( p, true, true );
624 else
625 {
626 pPrt = p;
627 bDataChanged = sal_True;
628 }
629 }
630 if ( bDataChanged && !get(IDocumentSettingAccess::USE_VIRTUAL_DEVICE) )
631 PrtDataChanged();
632 }
633
getPrintData() const634 const SwPrintData & SwDoc::getPrintData() const
635 {
636 if(!pPrtData)
637 {
638 SwDoc * pThis = const_cast< SwDoc * >(this);
639 pThis->pPrtData = new SwPrintData;
640
641 // SwPrintData should be initialized from the configuration,
642 // the respective config item is implemented by SwPrintOptions which
643 // is also derived from SwPrintData
644 const SwDocShell *pDocSh = GetDocShell();
645 DBG_ASSERT( pDocSh, "pDocSh is 0, can't determine if this is a WebDoc or not" );
646 bool bWeb = 0 != dynamic_cast< const SwWebDocShell * >(pDocSh);
647 SwPrintOptions aPrintOptions( bWeb );
648 *pThis->pPrtData = aPrintOptions;
649 }
650 return *pPrtData;
651 }
652
setPrintData(const SwPrintData & rPrtData)653 void SwDoc::setPrintData(/*[in]*/ const SwPrintData& rPrtData )
654 {
655 if(!pPrtData)
656 pPrtData = new SwPrintData;
657 *pPrtData = rPrtData;
658 }
659
660 /** Implementations the next Interface here
661 */
662
663 /*
664 * Document editing (Doc-SS) to fill the documents
665 * by the RTF parser and for the EditShell.
666 */
ChgDBData(const SwDBData & rNewData)667 void SwDoc::ChgDBData(const SwDBData& rNewData)
668 {
669 if( rNewData != aDBData )
670 {
671 aDBData = rNewData;
672 SetModified();
673 }
674 GetSysFldType(RES_DBNAMEFLD)->UpdateFlds();
675 }
676
SplitNode(const SwPosition & rPos,bool bChkTableStart)677 bool SwDoc::SplitNode( const SwPosition &rPos, bool bChkTableStart )
678 {
679 SwCntntNode *pNode = rPos.nNode.GetNode().GetCntntNode();
680 if(0 == pNode)
681 return false;
682
683 {
684 // Bug 26675: Sent DataChanged before deletion, then you can
685 // still notice which objects are in the range.
686 // After that the objects can be before/after the position.
687 SwDataChanged aTmp( this, rPos, 0 );
688 }
689
690 SwUndoSplitNode* pUndo = 0;
691 if (GetIDocumentUndoRedo().DoesUndo())
692 {
693 GetIDocumentUndoRedo().ClearRedo();
694 // insert the Undo object, currently only in TextNode
695 if( pNode->IsTxtNode() )
696 {
697 pUndo = new SwUndoSplitNode( this, rPos, bChkTableStart );
698 GetIDocumentUndoRedo().AppendUndo(pUndo);
699 }
700 }
701
702 //JP 28.01.97: Special case for SplitNode at table start:
703 // Are they at Doc/Fly/Footer/..-Start or directly
704 // behind a table, then insert a paragraph before it
705 if( bChkTableStart && !rPos.nContent.GetIndex() && pNode->IsTxtNode() )
706 {
707 sal_uLong nPrevPos = rPos.nNode.GetIndex() - 1;
708 const SwTableNode* pTblNd;
709 const SwNode* pNd = GetNodes()[ nPrevPos ];
710 if( pNd->IsStartNode() &&
711 SwTableBoxStartNode == ((SwStartNode*)pNd)->GetStartNodeType() &&
712 0 != ( pTblNd = GetNodes()[ --nPrevPos ]->GetTableNode() ) &&
713 ((( pNd = GetNodes()[ --nPrevPos ])->IsStartNode() &&
714 SwTableBoxStartNode != ((SwStartNode*)pNd)->GetStartNodeType() )
715 || ( pNd->IsEndNode() && pNd->StartOfSectionNode()->IsTableNode() )
716 || pNd->IsCntntNode() ))
717 {
718 if( pNd->IsCntntNode() )
719 {
720 //JP 30.04.99 Bug 65660:
721 // Outside of the normal BodyArea there are no page breaks,
722 // therefore this is no valid condition for inserting a paragraph
723 if( nPrevPos < GetNodes().GetEndOfExtras().GetIndex() )
724 pNd = 0;
725 else
726 {
727 // only when the table has breaks!
728 const SwFrmFmt* pFrmFmt = pTblNd->GetTable().GetFrmFmt();
729 if( SFX_ITEM_SET != pFrmFmt->GetItemState(RES_PAGEDESC, sal_False) &&
730 SFX_ITEM_SET != pFrmFmt->GetItemState( RES_BREAK, sal_False ) )
731 pNd = 0;
732 }
733 }
734
735 if( pNd )
736 {
737 SwTxtNode* pTxtNd = GetNodes().MakeTxtNode(
738 SwNodeIndex( *pTblNd ),
739 GetTxtCollFromPool( RES_POOLCOLL_TEXT ));
740 if( pTxtNd )
741 {
742 ((SwPosition&)rPos).nNode = pTblNd->GetIndex()-1;
743 ((SwPosition&)rPos).nContent.Assign( pTxtNd, 0 );
744
745 // only move the page break/page style inside the BodyArea
746 if( nPrevPos > GetNodes().GetEndOfExtras().GetIndex() )
747 {
748 SwFrmFmt* pFrmFmt = pTblNd->GetTable().GetFrmFmt();
749 const SfxPoolItem *pItem;
750 if( SFX_ITEM_SET == pFrmFmt->GetItemState( RES_PAGEDESC,
751 sal_False, &pItem ) )
752 {
753 pTxtNd->SetAttr( *pItem );
754 pFrmFmt->ResetFmtAttr( RES_PAGEDESC );
755 }
756 if( SFX_ITEM_SET == pFrmFmt->GetItemState( RES_BREAK,
757 sal_False, &pItem ) )
758 {
759 pTxtNd->SetAttr( *pItem );
760 pFrmFmt->ResetFmtAttr( RES_BREAK );
761 }
762 }
763
764 if( pUndo )
765 pUndo->SetTblFlag();
766 SetModified();
767 return true;
768 }
769 }
770 }
771 }
772
773 SvULongs aBkmkArr( 15, 15 );
774 _SaveCntntIdx( this, rPos.nNode.GetIndex(), rPos.nContent.GetIndex(),
775 aBkmkArr, SAVEFLY_SPLIT );
776 // FIXME: only SwTxtNode has a valid implementation of SplitCntntNode!
777 ASSERT(pNode->IsTxtNode(), "splitting non-text node?");
778 pNode = pNode->SplitCntntNode( rPos );
779 if (pNode)
780 {
781 // now move all Bookmarks/TOXMarks/FlyAtCnt
782 if( aBkmkArr.Count() )
783 _RestoreCntntIdx( this, aBkmkArr, rPos.nNode.GetIndex()-1, 0, sal_True );
784
785 if( IsRedlineOn() || (!IsIgnoreRedline() && pRedlineTbl->Count() ))
786 {
787 SwPaM aPam( rPos );
788 aPam.SetMark();
789 aPam.Move( fnMoveBackward );
790 if( IsRedlineOn() )
791 AppendRedline( new SwRedline( nsRedlineType_t::REDLINE_INSERT, aPam ), true);
792 else
793 SplitRedline( aPam );
794 }
795 }
796
797 SetModified();
798 return true;
799 }
800
AppendTxtNode(SwPosition & rPos)801 bool SwDoc::AppendTxtNode( SwPosition& rPos )
802 {
803 // create new node before EndOfContent
804 SwTxtNode * pCurNode = rPos.nNode.GetNode().GetTxtNode();
805 if( !pCurNode )
806 {
807 // now a node can be created!
808 SwNodeIndex aIdx( rPos.nNode, 1 );
809 pCurNode = GetNodes().MakeTxtNode( aIdx,
810 GetTxtCollFromPool( RES_POOLCOLL_STANDARD ));
811 }
812 else
813 pCurNode = (SwTxtNode*)pCurNode->AppendNode( rPos );
814
815 rPos.nNode++;
816 rPos.nContent.Assign( pCurNode, 0 );
817
818 if (GetIDocumentUndoRedo().DoesUndo())
819 {
820 GetIDocumentUndoRedo().AppendUndo( new SwUndoInsert( rPos.nNode ) );
821 }
822
823 if( IsRedlineOn() || (!IsIgnoreRedline() && pRedlineTbl->Count() ))
824 {
825 SwPaM aPam( rPos );
826 aPam.SetMark();
827 aPam.Move( fnMoveBackward );
828 if( IsRedlineOn() )
829 AppendRedline( new SwRedline( nsRedlineType_t::REDLINE_INSERT, aPam ), true);
830 else
831 SplitRedline( aPam );
832 }
833
834 SetModified();
835 return sal_True;
836 }
837
InsertString(const SwPaM & rRg,const String & rStr,const enum InsertFlags nInsertMode)838 bool SwDoc::InsertString( const SwPaM &rRg, const String &rStr,
839 const enum InsertFlags nInsertMode )
840 {
841 if (GetIDocumentUndoRedo().DoesUndo())
842 {
843 GetIDocumentUndoRedo().ClearRedo(); // AppendUndo not always called!
844 }
845
846 const SwPosition& rPos = *rRg.GetPoint();
847
848 if( pACEWord ) // take it to AutoCorrect
849 {
850 if( 1 == rStr.Len() && pACEWord->IsDeleted() )
851 {
852 pACEWord->CheckChar( rPos, rStr.GetChar( 0 ) );
853 }
854 delete pACEWord, pACEWord = 0;
855 }
856
857 SwTxtNode *const pNode = rPos.nNode.GetNode().GetTxtNode();
858 if(!pNode)
859 {
860 return false;
861 }
862
863 SwDataChanged aTmp( rRg, 0 );
864
865 if (!GetIDocumentUndoRedo().DoesUndo() ||
866 !GetIDocumentUndoRedo().DoesGroupUndo())
867 {
868 pNode->InsertText( rStr, rPos.nContent, nInsertMode );
869
870 if (GetIDocumentUndoRedo().DoesUndo())
871 {
872 SwUndoInsert * const pUndo( new SwUndoInsert(
873 rPos.nNode, rPos.nContent.GetIndex(), rStr.Len(), nInsertMode));
874 GetIDocumentUndoRedo().AppendUndo(pUndo);
875 }
876 }
877 else
878 { // if Undo and Grouping is enabled, then all is different!
879 SwUndoInsert * pUndo = NULL; // #111827#
880
881 // don't group the start if hints at the start should be expanded
882 if (!(nInsertMode & IDocumentContentOperations::INS_FORCEHINTEXPAND))
883 // -> #111827#
884 {
885 SwUndo *const pLastUndo = GetUndoManager().GetLastUndo();
886 SwUndoInsert *const pUndoInsert(
887 dynamic_cast<SwUndoInsert *>(pLastUndo) );
888 if (pUndoInsert && pUndoInsert->CanGrouping(rPos))
889 {
890 pUndo = pUndoInsert;
891 }
892 }
893 // <- #111827#
894
895 CharClass const& rCC = GetAppCharClass();
896 xub_StrLen nInsPos = rPos.nContent.GetIndex();
897
898 if (!pUndo)
899 {
900 pUndo = new SwUndoInsert( rPos.nNode, nInsPos, 0, nInsertMode,
901 !rCC.isLetterNumeric( rStr, 0 ) );
902 GetIDocumentUndoRedo().AppendUndo( pUndo );
903 }
904
905 pNode->InsertText( rStr, rPos.nContent, nInsertMode );
906
907 for( xub_StrLen i = 0; i < rStr.Len(); ++i )
908 {
909 nInsPos++;
910 // if CanGrouping() is returning sal_True, then all is already done
911 if( !pUndo->CanGrouping( rStr.GetChar( i ) ))
912 {
913 pUndo = new SwUndoInsert( rPos.nNode, nInsPos, 1, nInsertMode,
914 !rCC.isLetterNumeric( rStr, i ) );
915 GetIDocumentUndoRedo().AppendUndo( pUndo );
916 }
917 }
918 }
919
920 if( IsRedlineOn() || (!IsIgnoreRedline() && pRedlineTbl->Count() ))
921 {
922 SwPaM aPam( rPos.nNode, aTmp.GetCntnt(),
923 rPos.nNode, rPos.nContent.GetIndex());
924 if( IsRedlineOn() )
925 {
926 AppendRedline(
927 new SwRedline( nsRedlineType_t::REDLINE_INSERT, aPam ), true);
928 }
929 else
930 {
931 SplitRedline( aPam );
932 }
933 }
934
935 SetModified();
936 return true;
937 }
938
_InsNoTxtNode(const SwPosition & rPos,SwNoTxtNode * pNode,const SfxItemSet * pFlyAttrSet,const SfxItemSet * pGrfAttrSet,SwFrmFmt * pFrmFmt)939 SwFlyFrmFmt* SwDoc::_InsNoTxtNode( const SwPosition& rPos, SwNoTxtNode* pNode,
940 const SfxItemSet* pFlyAttrSet,
941 const SfxItemSet* pGrfAttrSet,
942 SwFrmFmt* pFrmFmt)
943 {
944 SwFlyFrmFmt *pFmt = 0;
945 if( pNode )
946 {
947 pFmt = _MakeFlySection( rPos, *pNode, FLY_AT_PARA,
948 pFlyAttrSet, pFrmFmt );
949 if( pGrfAttrSet )
950 pNode->SetAttr( *pGrfAttrSet );
951 }
952 return pFmt;
953 }
954
955
Insert(const SwPaM & rRg,const String & rGrfName,const String & rFltName,const Graphic * pGraphic,const SfxItemSet * pFlyAttrSet,const SfxItemSet * pGrfAttrSet,SwFrmFmt * pFrmFmt)956 SwFlyFrmFmt* SwDoc::Insert(
957 const SwPaM &rRg,
958 const String& rGrfName,
959 const String& rFltName,
960 const Graphic* pGraphic,
961 const SfxItemSet* pFlyAttrSet,
962 const SfxItemSet* pGrfAttrSet,
963 SwFrmFmt* pFrmFmt )
964 {
965 if ( !pFrmFmt )
966 pFrmFmt = GetFrmFmtFromPool( RES_POOLFRM_GRAPHIC );
967 SwGrfNode* pSwGrfNode = GetNodes().MakeGrfNode(
968 SwNodeIndex( GetNodes().GetEndOfAutotext() ),
969 rGrfName, rFltName, pGraphic,
970 pDfltGrfFmtColl );
971 SwFlyFrmFmt* pSwFlyFrmFmt =
972 _InsNoTxtNode( *rRg.GetPoint(), pSwGrfNode, pFlyAttrSet, pGrfAttrSet, pFrmFmt );
973 return pSwFlyFrmFmt;
974 }
975
976
Insert(const SwPaM & rRg,const GraphicObject & rGrfObj,const SfxItemSet * pFlyAttrSet,const SfxItemSet * pGrfAttrSet,SwFrmFmt * pFrmFmt)977 SwFlyFrmFmt* SwDoc::Insert(
978 const SwPaM &rRg,
979 const GraphicObject& rGrfObj,
980 const SfxItemSet* pFlyAttrSet,
981 const SfxItemSet* pGrfAttrSet,
982 SwFrmFmt* pFrmFmt )
983 {
984 if ( !pFrmFmt )
985 pFrmFmt = GetFrmFmtFromPool( RES_POOLFRM_GRAPHIC );
986 SwGrfNode* pSwGrfNode = GetNodes().MakeGrfNode(
987 SwNodeIndex( GetNodes().GetEndOfAutotext() ),
988 rGrfObj, pDfltGrfFmtColl );
989 SwFlyFrmFmt* pSwFlyFrmFmt = _InsNoTxtNode( *rRg.GetPoint(), pSwGrfNode,
990 pFlyAttrSet, pGrfAttrSet, pFrmFmt );
991 return pSwFlyFrmFmt;
992 }
993
Insert(const SwPaM & rRg,const svt::EmbeddedObjectRef & xObj,const SfxItemSet * pFlyAttrSet,const SfxItemSet * pGrfAttrSet,SwFrmFmt * pFrmFmt)994 SwFlyFrmFmt* SwDoc::Insert(const SwPaM &rRg, const svt::EmbeddedObjectRef& xObj,
995 const SfxItemSet* pFlyAttrSet,
996 const SfxItemSet* pGrfAttrSet,
997 SwFrmFmt* pFrmFmt )
998 {
999 if( !pFrmFmt )
1000 {
1001 sal_uInt16 nId = RES_POOLFRM_OLE;
1002 SvGlobalName aClassName( xObj->getClassID() );
1003 if (SotExchange::IsMath(aClassName))
1004 nId = RES_POOLFRM_FORMEL;
1005
1006 pFrmFmt = GetFrmFmtFromPool( nId );
1007 }
1008 return _InsNoTxtNode( *rRg.GetPoint(), GetNodes().MakeOLENode(
1009 SwNodeIndex( GetNodes().GetEndOfAutotext() ),
1010 xObj,
1011 pDfltGrfFmtColl ),
1012 pFlyAttrSet, pGrfAttrSet,
1013 pFrmFmt );
1014 }
1015
InsertOLE(const SwPaM & rRg,const String & rObjName,sal_Int64 nAspect,const SfxItemSet * pFlyAttrSet,const SfxItemSet * pGrfAttrSet,SwFrmFmt * pFrmFmt)1016 SwFlyFrmFmt* SwDoc::InsertOLE(const SwPaM &rRg, const String& rObjName,
1017 sal_Int64 nAspect,
1018 const SfxItemSet* pFlyAttrSet,
1019 const SfxItemSet* pGrfAttrSet,
1020 SwFrmFmt* pFrmFmt )
1021 {
1022 if( !pFrmFmt )
1023 pFrmFmt = GetFrmFmtFromPool( RES_POOLFRM_OLE );
1024
1025 return _InsNoTxtNode( *rRg.GetPoint(),
1026 GetNodes().MakeOLENode(
1027 SwNodeIndex( GetNodes().GetEndOfAutotext() ),
1028 rObjName,
1029 nAspect,
1030 pDfltGrfFmtColl,
1031 0 ),
1032 pFlyAttrSet, pGrfAttrSet,
1033 pFrmFmt );
1034 }
1035
1036 /*************************************************************************
1037 |* SwDoc::GetFldType()
1038 |* Description: delivers the field type back which is arranged at the Doc
1039 *************************************************************************/
1040
GetSysFldType(const sal_uInt16 eWhich) const1041 SwFieldType *SwDoc::GetSysFldType( const sal_uInt16 eWhich ) const
1042 {
1043 for( sal_uInt16 i = 0; i < INIT_FLDTYPES; ++i )
1044 if( eWhich == (*pFldTypes)[i]->Which() )
1045 return (*pFldTypes)[i];
1046 return 0;
1047 }
1048 /*************************************************************************
1049 * void SetDocStat( const SwDocStat& rStat );
1050 *************************************************************************/
1051
SetDocStat(const SwDocStat & rStat)1052 void SwDoc::SetDocStat( const SwDocStat& rStat )
1053 {
1054 *pDocStat = rStat;
1055 }
1056
GetDocStat() const1057 const SwDocStat& SwDoc::GetDocStat() const
1058 {
1059 return *pDocStat;
1060 }
1061
1062 /*************************************************************************/
1063
1064
1065 struct _PostItFld : public _SetGetExpFld
1066 {
_PostItFld_PostItFld1067 _PostItFld( const SwNodeIndex& rNdIdx, const SwTxtFld* pFld, const SwIndex* pIdx = 0 )
1068 : _SetGetExpFld( rNdIdx, pFld, pIdx ) {}
1069
1070 sal_uInt16 GetPageNo( const StringRangeEnumerator &rRangeEnum,
1071 const std::set< sal_Int32 > &rPossiblePages,
1072 sal_uInt16& rVirtPgNo, sal_uInt16& rLineNo );
1073
GetPostIt_PostItFld1074 SwPostItField* GetPostIt() const
1075 {
1076 return (SwPostItField*) GetTxtFld()->GetFmtFld().GetField();
1077 }
1078 };
1079
1080
GetPageNo(const StringRangeEnumerator & rRangeEnum,const std::set<sal_Int32> & rPossiblePages,sal_uInt16 & rVirtPgNo,sal_uInt16 & rLineNo)1081 sal_uInt16 _PostItFld::GetPageNo(
1082 const StringRangeEnumerator &rRangeEnum,
1083 const std::set< sal_Int32 > &rPossiblePages,
1084 /* out */ sal_uInt16& rVirtPgNo, /* out */ sal_uInt16& rLineNo )
1085 {
1086 // Problem:
1087 // When a PostItFld is in a Node that is represented by more than one layout
1088 // instance, then there is the question, whether the PostIt should be printed
1089 // 1 or n-times. Likely only 1 time. Don't seek a random one as page number
1090 // but the first occurrence of the PostIt within the selected area.
1091 rVirtPgNo = 0;
1092 sal_uInt16 nPos = GetCntnt();
1093 SwIterator<SwTxtFrm,SwTxtNode> aIter( GetTxtFld()->GetTxtNode() );
1094 for( SwTxtFrm* pFrm = aIter.First(); pFrm; pFrm = aIter.Next() )
1095 {
1096 if( pFrm->GetOfst() > nPos ||
1097 (pFrm->HasFollow() && pFrm->GetFollow()->GetOfst() <= nPos) )
1098 continue;
1099 sal_uInt16 nPgNo = pFrm->GetPhyPageNum();
1100 if( rRangeEnum.hasValue( nPgNo, &rPossiblePages ))
1101 {
1102 rLineNo = (sal_uInt16)(pFrm->GetLineCount( nPos ) +
1103 pFrm->GetAllLines() - pFrm->GetThisLines());
1104 rVirtPgNo = pFrm->GetVirtPageNum();
1105 return nPgNo;
1106 }
1107 }
1108 return 0;
1109 }
1110
1111
lcl_GetPostIts(IDocumentFieldsAccess * pIDFA,_SetGetExpFlds * pSrtLst)1112 bool lcl_GetPostIts(
1113 IDocumentFieldsAccess* pIDFA,
1114 _SetGetExpFlds * pSrtLst )
1115 {
1116 bool bHasPostIts = false;
1117
1118 SwFieldType* pFldType = pIDFA->GetSysFldType( RES_POSTITFLD );
1119 DBG_ASSERT( pFldType, "kein PostItType ? ");
1120
1121 if( pFldType->GetDepends() )
1122 {
1123 // Modify object found, insert all fields into the array
1124 SwIterator<SwFmtFld,SwFieldType> aIter( *pFldType );
1125 const SwTxtFld* pTxtFld;
1126 for( SwFmtFld* pFld = aIter.First(); pFld; pFld = aIter.Next() )
1127 {
1128 if( 0 != ( pTxtFld = pFld->GetTxtFld() ) &&
1129 pTxtFld->GetTxtNode().GetNodes().IsDocNodes() )
1130 {
1131 bHasPostIts = true;
1132 if (pSrtLst)
1133 {
1134 SwNodeIndex aIdx( pTxtFld->GetTxtNode() );
1135 _PostItFld* pNew = new _PostItFld( aIdx, pTxtFld );
1136 pSrtLst->Insert( pNew );
1137 }
1138 else
1139 break; // we just wanted to check for the existence of postits ...
1140 }
1141 }
1142 }
1143
1144 return bHasPostIts;
1145 }
1146
1147
lcl_FormatPostIt(IDocumentContentOperations * pIDCO,SwPaM & aPam,SwPostItField * pField,bool bNewPage,bool bIsFirstPostIt,sal_uInt16 nPageNo,sal_uInt16 nLineNo)1148 static void lcl_FormatPostIt(
1149 IDocumentContentOperations* pIDCO,
1150 SwPaM& aPam,
1151 SwPostItField* pField,
1152 bool bNewPage, bool bIsFirstPostIt,
1153 sal_uInt16 nPageNo, sal_uInt16 nLineNo )
1154 {
1155 static char __READONLY_DATA sTmp[] = " : ";
1156
1157 DBG_ASSERT( ViewShell::GetShellRes(), "missing ShellRes" );
1158
1159 if (bNewPage)
1160 {
1161 pIDCO->InsertPoolItem( aPam, SvxFmtBreakItem( SVX_BREAK_PAGE_AFTER, RES_BREAK ), 0 );
1162 pIDCO->SplitNode( *aPam.GetPoint(), false );
1163 }
1164 else if (!bIsFirstPostIt)
1165 {
1166 // add an empty line between different notes
1167 pIDCO->SplitNode( *aPam.GetPoint(), false );
1168 pIDCO->SplitNode( *aPam.GetPoint(), false );
1169 }
1170
1171 String aStr( ViewShell::GetShellRes()->aPostItPage );
1172 aStr.AppendAscii(sTmp);
1173
1174 aStr += XubString::CreateFromInt32( nPageNo );
1175 aStr += ' ';
1176 if( nLineNo )
1177 {
1178 aStr += ViewShell::GetShellRes()->aPostItLine;
1179 aStr.AppendAscii(sTmp);
1180 aStr += XubString::CreateFromInt32( nLineNo );
1181 aStr += ' ';
1182 }
1183 aStr += ViewShell::GetShellRes()->aPostItAuthor;
1184 aStr.AppendAscii(sTmp);
1185 aStr += pField->GetPar1();
1186 aStr += ' ';
1187 SvtSysLocale aSysLocale;
1188 aStr += /*(LocaleDataWrapper&)*/aSysLocale.GetLocaleData().getDate( pField->GetDate() );
1189 pIDCO->InsertString( aPam, aStr );
1190
1191 pIDCO->SplitNode( *aPam.GetPoint(), false );
1192 aStr = pField->GetPar2();
1193 #if defined( WNT ) || defined( PM2 )
1194 // Bei Windows und Co alle CR rausschmeissen
1195 aStr.EraseAllChars( '\r' );
1196 #endif
1197 pIDCO->InsertString( aPam, aStr );
1198 }
1199
1200
1201 // provide the paper tray to use according to the page style in use,
1202 // but do that only if the respective item is NOT just the default item
lcl_GetPaperBin(const SwPageFrm * pStartFrm)1203 static sal_Int32 lcl_GetPaperBin( const SwPageFrm *pStartFrm )
1204 {
1205 sal_Int32 nRes = -1;
1206
1207 const SwFrmFmt &rFmt = pStartFrm->GetPageDesc()->GetMaster();
1208 const SfxPoolItem *pItem = NULL;
1209 SfxItemState eState = rFmt.GetItemState( RES_PAPER_BIN, sal_False, &pItem );
1210 const SvxPaperBinItem *pPaperBinItem = dynamic_cast< const SvxPaperBinItem * >(pItem);
1211 if (eState > SFX_ITEM_DEFAULT && pPaperBinItem)
1212 nRes = pPaperBinItem->GetValue();
1213
1214 return nRes;
1215 }
1216
1217
CalculatePagesForPrinting(const SwRootFrm & rLayout,SwRenderData & rData,const SwPrintUIOptions & rOptions,bool bIsPDFExport,sal_Int32 nDocPageCount)1218 void SwDoc::CalculatePagesForPrinting(
1219 const SwRootFrm& rLayout,
1220 /* out */ SwRenderData &rData,
1221 const SwPrintUIOptions &rOptions,
1222 bool bIsPDFExport,
1223 sal_Int32 nDocPageCount )
1224 {
1225 const sal_Int64 nContent = rOptions.getIntValue( "PrintContent", 0 );
1226 const bool bPrintSelection = nContent == 2;
1227
1228 // properties to take into account when calculating the set of pages
1229 // (PDF export UI does not allow for selecting left or right pages only)
1230 bool bPrintLeftPages = bIsPDFExport ? true : rOptions.IsPrintLeftPages();
1231 bool bPrintRightPages = bIsPDFExport ? true : rOptions.IsPrintRightPages();
1232 // #i103700# printing selections should not allow for automatic inserting empty pages
1233 bool bPrintEmptyPages = bPrintSelection ? false : rOptions.IsPrintEmptyPages( bIsPDFExport );
1234
1235 Range aPages( 1, nDocPageCount );
1236
1237 MultiSelection aMulti( aPages );
1238 aMulti.SetTotalRange( Range( 0, RANGE_MAX ) );
1239 aMulti.Select( aPages );
1240
1241 const SwPageFrm *pStPage = dynamic_cast<const SwPageFrm*>( rLayout.Lower() );
1242 const SwFrm *pEndPage = pStPage;
1243
1244 sal_uInt16 nFirstPageNo = 0;
1245 sal_uInt16 nLastPageNo = 0;
1246 sal_uInt16 nPageNo = 1;
1247
1248 for( sal_uInt16 i = 1; i <= (sal_uInt16)aPages.Max(); ++i )
1249 {
1250 if( i < (sal_uInt16)aPages.Min() )
1251 {
1252 if( !pStPage->GetNext() )
1253 break;
1254 pStPage = (SwPageFrm*)pStPage->GetNext();
1255 pEndPage= pStPage;
1256 }
1257 else if( i == (sal_uInt16)aPages.Min() )
1258 {
1259 nFirstPageNo = i;
1260 nLastPageNo = nFirstPageNo;
1261 if( !pStPage->GetNext() || (i == (sal_uInt16)aPages.Max()) )
1262 break;
1263 pEndPage = pStPage->GetNext();
1264 }
1265 else if( i > (sal_uInt16)aPages.Min() )
1266 {
1267 nLastPageNo = i;
1268 if( !pEndPage->GetNext() || (i == (sal_uInt16)aPages.Max()) )
1269 break;
1270 pEndPage = pEndPage->GetNext();
1271 }
1272 }
1273
1274 DBG_ASSERT( nFirstPageNo, "first page not found! Should not happen!" );
1275 if (nFirstPageNo)
1276 {
1277 // Start of HACK:
1278 // Here an acceptable possibility has to be created by the MultiSelection,
1279 // to deselect all pages starting from page x.
1280 // E.g., with SetTotalRange ....
1281
1282 // aMulti.Select( Range( nLastPageNo+1, SELECTION_MAX ), sal_False );
1283 MultiSelection aTmpMulti( Range( 1, nLastPageNo ) );
1284 long nTmpIdx = aMulti.FirstSelected();
1285 static long nEndOfSelection = SFX_ENDOFSELECTION;
1286 while ( nEndOfSelection != nTmpIdx && nTmpIdx <= long(nLastPageNo) )
1287 {
1288 aTmpMulti.Select( nTmpIdx );
1289 nTmpIdx = aMulti.NextSelected();
1290 }
1291 aMulti = aTmpMulti;
1292 // End of HACK
1293
1294 nPageNo = nFirstPageNo;
1295
1296 std::map< sal_Int32, sal_Int32 > &rPrinterPaperTrays = rData.GetPrinterPaperTrays();
1297 std::set< sal_Int32 > &rValidPages = rData.GetValidPagesSet();
1298 std::map< sal_Int32, const SwPageFrm * > &rValidStartFrms = rData.GetValidStartFrames();
1299 rValidPages.clear();
1300 rValidStartFrms.clear();
1301 while ( pStPage )
1302 {
1303 const sal_Bool bRightPg = pStPage->OnRightPage();
1304 if ( aMulti.IsSelected( nPageNo ) &&
1305 ( (bRightPg && bPrintRightPages) ||
1306 (!bRightPg && bPrintLeftPages) ) )
1307 {
1308 // --> FME 2005-12-12 #b6354161# Feature - Print empty pages
1309 if ( bPrintEmptyPages || pStPage->Frm().Height() )
1310 // <--
1311 {
1312 rValidPages.insert( nPageNo );
1313 rValidStartFrms[ nPageNo ] = pStPage;
1314
1315 rPrinterPaperTrays[ nPageNo ] = lcl_GetPaperBin( pStPage );
1316 }
1317 }
1318
1319 if ( pStPage == pEndPage )
1320 {
1321 pStPage = 0;
1322 }
1323 else
1324 { ++nPageNo;
1325 pStPage = (SwPageFrm*)pStPage->GetNext();
1326 }
1327 }
1328 }
1329
1330 // now that we have identified the valid pages for printing according
1331 // to the print settings we need to get the PageRange to use and
1332 // use both results to get the actual pages to be printed
1333 // (post-it settings need to be taken into account later on!)
1334
1335 // get PageRange value to use
1336 OUString aPageRange;
1337 // --> PL, OD #i116085# - adjusting fix for i113919
1338 // if (bIsPDFExport)
1339 // {
1340 // aPageRange = rOptions.getStringValue( "PageRange", OUString() );
1341 // }
1342 // else
1343 if ( !bIsPDFExport )
1344 // <--
1345 {
1346 // PageContent :
1347 // 0 -> print all pages (default if aPageRange is empty)
1348 // 1 -> print range according to PageRange
1349 // 2 -> print selection
1350 if (1 == nContent)
1351 aPageRange = rOptions.getStringValue( "PageRange", OUString() );
1352 if (2 == nContent)
1353 {
1354 // note that printing selections is actually implemented by copying
1355 // the selection to a new temporary document and printing all of that one.
1356 // Thus for Writer "PrintContent" must never be 2.
1357 // See SwXTextDocument::GetRenderDoc for evaluating if a selection is to be
1358 // printed and for creating the temporary document.
1359 }
1360
1361 // please note
1362 }
1363 if (aPageRange.getLength() == 0) // empty string -> print all
1364 {
1365 // set page range to print to 'all pages'
1366 aPageRange = OUString::valueOf( (sal_Int32)1 );
1367 aPageRange += OUString::valueOf( (sal_Unicode)'-');
1368 aPageRange += OUString::valueOf( nDocPageCount );
1369 }
1370 rData.SetPageRange( aPageRange );
1371
1372 // get vector of pages to print according to PageRange and valid pages set from above
1373 // (result may be an empty vector, for example if the range string is not correct)
1374 StringRangeEnumerator::getRangesFromString(
1375 aPageRange, rData.GetPagesToPrint(),
1376 1, nDocPageCount, 0, &rData.GetValidPagesSet() );
1377 }
1378
1379
UpdatePagesForPrintingWithPostItData(SwRenderData & rData,const SwPrintUIOptions & rOptions,bool,sal_Int32 nDocPageCount)1380 void SwDoc::UpdatePagesForPrintingWithPostItData(
1381 /* out */ SwRenderData &rData,
1382 const SwPrintUIOptions &rOptions,
1383 bool /*bIsPDFExport*/,
1384 sal_Int32 nDocPageCount )
1385 {
1386
1387 sal_Int16 nPostItMode = (sal_Int16) rOptions.getIntValue( "PrintAnnotationMode", 0 );
1388 DBG_ASSERT(nPostItMode == POSTITS_NONE || rData.HasPostItData(),
1389 "print post-its without post-it data?" );
1390 const sal_uInt16 nPostItCount = rData.HasPostItData() ? rData.m_pPostItFields->Count() : 0;
1391 if (nPostItMode != POSTITS_NONE && nPostItCount > 0)
1392 {
1393 SET_CURR_SHELL( rData.m_pPostItShell );
1394
1395 // clear document and move to end of it
1396 SwPaM aPam( rData.m_pPostItDoc->GetNodes().GetEndOfContent() );
1397 aPam.Move( fnMoveBackward, fnGoDoc );
1398 aPam.SetMark();
1399 aPam.Move( fnMoveForward, fnGoDoc );
1400 rData.m_pPostItDoc->DeleteRange( aPam );
1401
1402 const StringRangeEnumerator aRangeEnum( rData.GetPageRange(), 1, nDocPageCount, 0 );
1403
1404 // For mode POSTITS_ENDPAGE:
1405 // maps a physical page number to the page number in post-it document that holds
1406 // the first post-it for that physical page . Needed to relate the correct start frames
1407 // from the post-it doc to the physical page of the document
1408 std::map< sal_Int32, sal_Int32 > aPostItLastStartPageNum;
1409
1410 // add all post-its on valid pages within the page range to the
1411 // temporary post-it document.
1412 // Since the array of post-it fields is sorted by page and line number we will
1413 // already get them in the correct order
1414 sal_uInt16 nVirtPg = 0, nLineNo = 0, nLastPageNum = 0, nPhyPageNum = 0;
1415 bool bIsFirstPostIt = true;
1416 for (sal_uInt16 i = 0; i < nPostItCount; ++i)
1417 {
1418 _PostItFld& rPostIt = (_PostItFld&)*(*rData.m_pPostItFields)[ i ];
1419 nLastPageNum = nPhyPageNum;
1420 nPhyPageNum = rPostIt.GetPageNo(
1421 aRangeEnum, rData.GetValidPagesSet(), nVirtPg, nLineNo );
1422 if (nPhyPageNum)
1423 {
1424 // need to insert a page break?
1425 // In POSTITS_ENDPAGE mode for each document page the following
1426 // post-it page needs to start on a new page
1427 const bool bNewPage = nPostItMode == POSTITS_ENDPAGE &&
1428 !bIsFirstPostIt && nPhyPageNum != nLastPageNum;
1429
1430 lcl_FormatPostIt( rData.m_pPostItShell->GetDoc(), aPam,
1431 rPostIt.GetPostIt(), bNewPage, bIsFirstPostIt, nVirtPg, nLineNo );
1432 bIsFirstPostIt = false;
1433
1434 if (nPostItMode == POSTITS_ENDPAGE)
1435 {
1436 // get the correct number of current pages for the post-it document
1437 rData.m_pPostItShell->CalcLayout();
1438 const sal_Int32 nPages = rData.m_pPostItShell->GetPageCount();
1439 aPostItLastStartPageNum[ nPhyPageNum ] = nPages;
1440 }
1441 }
1442 }
1443
1444 // format post-it doc to get correct number of pages
1445 rData.m_pPostItShell->CalcLayout();
1446 const sal_Int32 nPostItDocPageCount = rData.m_pPostItShell->GetPageCount();
1447
1448 if (nPostItMode == POSTITS_ONLY || nPostItMode == POSTITS_ENDDOC)
1449 {
1450 // now add those post-it pages to the vector of pages to print
1451 // or replace them if only post-its should be printed
1452
1453 rData.GetPostItStartFrames().clear();
1454 if (nPostItMode == POSTITS_ENDDOC)
1455 {
1456 // set all values up to number of pages to print currently known to NULL,
1457 // meaning none of the pages currently in the vector is from the
1458 // post-it document, they are the documents pages.
1459 rData.GetPostItStartFrames().resize( rData.GetPagesToPrint().size() );
1460 }
1461 else if (nPostItMode == POSTITS_ONLY)
1462 {
1463 // no document page to be printed
1464 rData.GetPagesToPrint().clear();
1465 }
1466
1467 // now we just need to add the post-it pages to be printed to the end
1468 // of the vector of pages to print and keep the GetValidStartFrames
1469 // data conform with it
1470 sal_Int32 nPageNum = 0;
1471 const SwPageFrm * pPageFrm = (SwPageFrm*)rData.m_pPostItShell->GetLayout()->Lower();
1472 while( pPageFrm && nPageNum < nPostItDocPageCount )
1473 {
1474 DBG_ASSERT( pPageFrm, "Empty page frame. How are we going to print this?" );
1475 ++nPageNum;
1476 rData.GetPagesToPrint().push_back( 0 ); // a page number of 0 indicates this page is from the post-it doc
1477 DBG_ASSERT( pPageFrm, "pPageFrm is NULL!" );
1478 rData.GetPostItStartFrames().push_back( pPageFrm );
1479 pPageFrm = (SwPageFrm*)pPageFrm->GetNext();
1480 }
1481 DBG_ASSERT( nPageNum == nPostItDocPageCount, "unexpected number of pages" );
1482 }
1483 else if (nPostItMode == POSTITS_ENDPAGE)
1484 {
1485 // the next step is to find all the start frames from the post-it
1486 // document that should be printed for a given physical page of the document
1487 std::map< sal_Int32, std::vector< const SwPageFrm * > > aPhysPageToPostItFrames;
1488
1489 // ... thus, first collect all post-it doc start frames in a vector
1490 sal_Int32 nPostItPageNum = 0;
1491 std::vector< const SwPageFrm * > aAllPostItStartFrames;
1492 const SwPageFrm * pPageFrm = (SwPageFrm*)rData.m_pPostItShell->GetLayout()->Lower();
1493 while( pPageFrm && sal_Int32(aAllPostItStartFrames.size()) < nPostItDocPageCount )
1494 {
1495 DBG_ASSERT( pPageFrm, "Empty page frame. How are we going to print this?" );
1496 ++nPostItPageNum;
1497 aAllPostItStartFrames.push_back( pPageFrm );
1498 pPageFrm = (SwPageFrm*)pPageFrm->GetNext();
1499 }
1500 DBG_ASSERT( sal_Int32(aAllPostItStartFrames.size()) == nPostItDocPageCount,
1501 "unexpected number of frames; does not match number of pages" );
1502
1503 // get a map that holds all post-it frames to be printed for a
1504 // given physical page from the document
1505 sal_Int32 nLastStartPageNum = 0;
1506 std::map< sal_Int32, sal_Int32 >::const_iterator aIt;
1507 for (aIt = aPostItLastStartPageNum.begin(); aIt != aPostItLastStartPageNum.end(); ++aIt)
1508 {
1509 const sal_Int32 nFrames = aIt->second - nLastStartPageNum;
1510 const sal_Int32 nFirstStartPageNum = aIt == aPostItLastStartPageNum.begin() ?
1511 1 : aIt->second - nFrames + 1;
1512 DBG_ASSERT( 1 <= nFirstStartPageNum && nFirstStartPageNum <= nPostItDocPageCount,
1513 "page number for first frame out of range" );
1514 std::vector< const SwPageFrm * > aStartFrames;
1515 for (sal_Int32 i = 0; i < nFrames; ++i)
1516 {
1517 const sal_Int32 nIdx = nFirstStartPageNum - 1 + i; // -1 because lowest page num is 1
1518 DBG_ASSERT( 0 <= nIdx && nIdx < sal_Int32(aAllPostItStartFrames.size()),
1519 "index out of range" );
1520 aStartFrames.push_back( aAllPostItStartFrames[ nIdx ] );
1521 }
1522 aPhysPageToPostItFrames[ aIt->first /* phys page num */ ] = aStartFrames;
1523 nLastStartPageNum = aIt->second;
1524 }
1525
1526
1527 // ok, now that aPhysPageToPostItFrames can give the start frames for all
1528 // post-it pages to be printed we need to merge those at the correct
1529 // position into the GetPagesToPrint vector and build and maintain the
1530 // GetValidStartFrames vector as well.
1531 // Since inserting a larger number of entries in the middle of a vector
1532 // isn't that efficient we will create new vectors by copying the required data
1533 std::vector< sal_Int32 > aTmpPagesToPrint;
1534 std::vector< const SwPageFrm * > aTmpPostItStartFrames;
1535 const size_t nNum = rData.GetPagesToPrint().size();
1536 for (size_t i = 0 ; i < nNum; ++i)
1537 {
1538 // add the physical page to print from the document
1539 const sal_Int32 nPhysPage = rData.GetPagesToPrint()[i];
1540 aTmpPagesToPrint.push_back( nPhysPage );
1541 aTmpPostItStartFrames.push_back( NULL );
1542
1543 // add the post-it document pages to print, i.e. those
1544 // post-it pages that have the data for the above physical page
1545 const std::vector< const SwPageFrm * > &rPostItFrames = aPhysPageToPostItFrames[ nPhysPage ];
1546 const size_t nPostItFrames = rPostItFrames.size();
1547 for (size_t k = 0; k < nPostItFrames; ++k)
1548 {
1549 aTmpPagesToPrint.push_back( 0 );
1550 aTmpPostItStartFrames.push_back( rPostItFrames[k] );
1551 }
1552 }
1553
1554 // finally we need to assign those vectors to the resulting ones.
1555 // swapping the data should be more efficient than assigning since
1556 // we won't need the temporary vectors anymore
1557 rData.GetPagesToPrint().swap( aTmpPagesToPrint );
1558 rData.GetPostItStartFrames().swap( aTmpPostItStartFrames );
1559 }
1560 }
1561 }
1562
1563
CalculatePagePairsForProspectPrinting(const SwRootFrm & rLayout,SwRenderData & rData,const SwPrintUIOptions & rOptions,sal_Int32 nDocPageCount)1564 void SwDoc::CalculatePagePairsForProspectPrinting(
1565 const SwRootFrm& rLayout,
1566 /* out */ SwRenderData &rData,
1567 const SwPrintUIOptions &rOptions,
1568 sal_Int32 nDocPageCount )
1569 {
1570 std::map< sal_Int32, sal_Int32 > &rPrinterPaperTrays = rData.GetPrinterPaperTrays();
1571 std::set< sal_Int32 > &rValidPagesSet = rData.GetValidPagesSet();
1572 std::map< sal_Int32, const SwPageFrm * > &rValidStartFrms = rData.GetValidStartFrames();
1573 std::vector< std::pair< sal_Int32, sal_Int32 > > &rPagePairs = rData.GetPagePairsForProspectPrinting();
1574
1575 rPagePairs.clear();
1576 rValidPagesSet.clear();
1577 rValidStartFrms.clear();
1578
1579 rtl::OUString aPageRange = rOptions.getStringValue( "PageRange", rtl::OUString() );
1580 // PageContent :
1581 // 0 -> print all pages (default if aPageRange is empty)
1582 // 1 -> print range according to PageRange
1583 // 2 -> print selection
1584 const sal_Int64 nContent = rOptions.getIntValue( "PrintContent", 0 );
1585 if (0 == nContent)
1586 {
1587 // set page range to print to 'all pages'
1588 aPageRange = OUString::valueOf( (sal_Int32)1 );
1589 aPageRange += OUString::valueOf( (sal_Unicode)'-');
1590 aPageRange += OUString::valueOf( nDocPageCount );
1591 }
1592 StringRangeEnumerator aRange( aPageRange, 1, nDocPageCount, 0 );
1593
1594 if ( aRange.size() <= 0)
1595 return;
1596
1597 const SwPageFrm *pStPage = dynamic_cast<const SwPageFrm*>( rLayout.Lower() );
1598 sal_Int32 i = 0;
1599 for ( i = 1; pStPage && i < nDocPageCount; ++i )
1600 pStPage = (SwPageFrm*)pStPage->GetNext();
1601 if ( !pStPage ) // that's it then
1602 return;
1603
1604 // currently for prospect printing all pages are valid to be printed
1605 // thus we add them all to the respective map and set for later use
1606 sal_Int32 nPageNum = 0;
1607 const SwPageFrm *pPageFrm = dynamic_cast<const SwPageFrm*>( rLayout.Lower() );
1608 while( pPageFrm && nPageNum < nDocPageCount )
1609 {
1610 DBG_ASSERT( pPageFrm, "Empty page frame. How are we going to print this?" );
1611 ++nPageNum;
1612 rValidPagesSet.insert( nPageNum );
1613 rValidStartFrms[ nPageNum ] = pPageFrm;
1614 pPageFrm = (SwPageFrm*)pPageFrm->GetNext();
1615
1616 rPrinterPaperTrays[ nPageNum ] = lcl_GetPaperBin( pStPage );
1617 }
1618 DBG_ASSERT( nPageNum == nDocPageCount, "unexpected number of pages" );
1619
1620 // properties to take into account when calculating the set of pages
1621 // Note: here bPrintLeftPages and bPrintRightPages refer to the (virtual) resulting pages
1622 // of the prospect!
1623 bool bPrintLeftPages = rOptions.IsPrintLeftPages();
1624 bool bPrintRightPages = rOptions.IsPrintRightPages();
1625 bool bPrintProspectRTL = rOptions.getIntValue( "PrintProspectRTL", 0 ) ? true : false;
1626
1627 // get pages for prospect printing according to the 'PageRange'
1628 // (duplicates and any order allowed!)
1629 std::vector< sal_Int32 > aPagesToPrint;
1630 StringRangeEnumerator::getRangesFromString(
1631 aPageRange, aPagesToPrint, 1, nDocPageCount, 0 );
1632
1633 // now fill the vector for calculating the page pairs with the start frames
1634 // from the above obtained vector
1635 std::vector< const SwPageFrm * > aVec;
1636 for ( i = 0; i < sal_Int32(aPagesToPrint.size()); ++i)
1637 {
1638 const sal_Int32 nPage = aPagesToPrint[i];
1639 const SwPageFrm *pFrm = rValidStartFrms[ nPage ];
1640 aVec.push_back( pFrm );
1641 }
1642
1643 // just one page is special ...
1644 if ( 1 == aVec.size() )
1645 aVec.insert( aVec.begin() + 1, 0 ); // insert a second empty page
1646 else
1647 {
1648 // now extend the number of pages to fit a multiple of 4
1649 // (4 'normal' pages are needed for a single prospect paper
1650 // with back and front)
1651 while( aVec.size() & 3 )
1652 aVec.push_back( 0 );
1653 }
1654
1655 // now make sure that all pages are in the correct order
1656 sal_uInt16 nSPg = 0;
1657 sal_uInt32 nEPg = aVec.size();
1658 sal_uInt16 nStep = 1;
1659 if ( 0 == (nEPg & 1 )) // there is no odd!
1660 --nEPg;
1661
1662 if ( !bPrintLeftPages )
1663 ++nStep;
1664 else if ( !bPrintRightPages )
1665 {
1666 ++nStep;
1667 ++nSPg, --nEPg;
1668 }
1669
1670 // the number of 'virtual' pages to be printed
1671 sal_Int32 nCntPage = (( nEPg - nSPg ) / ( 2 * nStep )) + 1;
1672
1673 for ( sal_uInt16 nPrintCount = 0; nSPg < nEPg &&
1674 nPrintCount < nCntPage; ++nPrintCount )
1675 {
1676 pStPage = aVec[ nSPg ];
1677 const SwPageFrm* pNxtPage = nEPg < aVec.size() ? aVec[ nEPg ] : 0;
1678
1679 short nRtlOfs = bPrintProspectRTL ? 1 : 0;
1680 if ( 0 == (( nSPg + nRtlOfs) & 1 ) ) // switch for odd number in LTR, even number in RTL
1681 {
1682 const SwPageFrm* pTmp = pStPage;
1683 pStPage = pNxtPage;
1684 pNxtPage = pTmp;
1685 }
1686
1687 sal_Int32 nFirst = -1, nSecond = -1;
1688 for ( int nC = 0; nC < 2; ++nC )
1689 {
1690 sal_Int32 nPage = -1;
1691 if ( pStPage )
1692 nPage = pStPage->GetPhyPageNum();
1693 if (nC == 0)
1694 nFirst = nPage;
1695 else
1696 nSecond = nPage;
1697
1698 pStPage = pNxtPage;
1699 }
1700 rPagePairs.push_back( std::pair< sal_Int32, sal_Int32 >(nFirst, nSecond) );
1701
1702 nSPg = nSPg + nStep;
1703 nEPg = nEPg - nStep;
1704 }
1705 DBG_ASSERT( size_t(nCntPage) == rPagePairs.size(), "size mismatch for number of page pairs" );
1706
1707 // luckily prospect printing does not make use of post-its so far,
1708 // thus we are done here.
1709 }
1710
1711 /*************************************************************************
1712 * void UpdateDocStat( const SwDocStat& rStat );
1713 *************************************************************************/
1714
UpdateDocStat(SwDocStat & rStat)1715 void SwDoc::UpdateDocStat( SwDocStat& rStat )
1716 {
1717 if( rStat.bModified )
1718 {
1719 rStat.Reset();
1720 rStat.nPara = 0; // default is 1 !!
1721 SwNode* pNd;
1722
1723 for( sal_uLong i = GetNodes().Count(); i; )
1724 {
1725 switch( ( pNd = GetNodes()[ --i ])->GetNodeType() )
1726 {
1727 case ND_TEXTNODE:
1728 ((SwTxtNode*)pNd)->CountWords( rStat, 0, ((SwTxtNode*)pNd)->GetTxt().Len() );
1729 break;
1730 case ND_TABLENODE: ++rStat.nTbl; break;
1731 case ND_GRFNODE: ++rStat.nGrf; break;
1732 case ND_OLENODE: ++rStat.nOLE; break;
1733 case ND_SECTIONNODE: break;
1734 }
1735 }
1736
1737 // #i93174#: notes contain paragraphs that are not nodes
1738 {
1739 SwFieldType * const pPostits( GetSysFldType(RES_POSTITFLD) );
1740 SwIterator<SwFmtFld,SwFieldType> aIter( *pPostits );
1741 for( SwFmtFld* pFmtFld = aIter.First(); pFmtFld; pFmtFld = aIter.Next() )
1742 {
1743 if (pFmtFld->IsFldInDoc())
1744 {
1745 SwPostItField const * const pField(
1746 static_cast<SwPostItField const*>(pFmtFld->GetField()));
1747 rStat.nAllPara += pField->GetNumberOfParagraphs();
1748 }
1749 }
1750 }
1751
1752 rStat.nPage = GetCurrentLayout() ? GetCurrentLayout()->GetPageNum() : 0; //swmod 080218
1753 rStat.bModified = sal_False;
1754 SetDocStat( rStat );
1755
1756 com::sun::star::uno::Sequence < com::sun::star::beans::NamedValue > aStat( rStat.nPage ? 7 : 6);
1757 sal_Int32 n=0;
1758 aStat[n].Name = ::rtl::OUString::createFromAscii("TableCount");
1759 aStat[n++].Value <<= (sal_Int32)rStat.nTbl;
1760 aStat[n].Name = ::rtl::OUString::createFromAscii("ImageCount");
1761 aStat[n++].Value <<= (sal_Int32)rStat.nGrf;
1762 aStat[n].Name = ::rtl::OUString::createFromAscii("ObjectCount");
1763 aStat[n++].Value <<= (sal_Int32)rStat.nOLE;
1764 if ( rStat.nPage )
1765 {
1766 aStat[n].Name = ::rtl::OUString::createFromAscii("PageCount");
1767 aStat[n++].Value <<= (sal_Int32)rStat.nPage;
1768 }
1769 aStat[n].Name = ::rtl::OUString::createFromAscii("ParagraphCount");
1770 aStat[n++].Value <<= (sal_Int32)rStat.nPara;
1771 aStat[n].Name = ::rtl::OUString::createFromAscii("WordCount");
1772 aStat[n++].Value <<= (sal_Int32)rStat.nWord;
1773 aStat[n].Name = ::rtl::OUString::createFromAscii("CharacterCount");
1774 aStat[n++].Value <<= (sal_Int32)rStat.nChar;
1775
1776 // For e.g. autotext documents there is no pSwgInfo (#i79945)
1777 SfxObjectShell * const pObjShell( GetDocShell() );
1778 if (pObjShell)
1779 {
1780 const uno::Reference<document::XDocumentPropertiesSupplier> xDPS(
1781 pObjShell->GetModel(), uno::UNO_QUERY_THROW);
1782 const uno::Reference<document::XDocumentProperties> xDocProps(
1783 xDPS->getDocumentProperties());
1784 // #i96786#: do not set modified flag when updating statistics
1785 const bool bDocWasModified( IsModified() );
1786 const ModifyBlocker_Impl b(pObjShell);
1787 xDocProps->setDocumentStatistics(aStat);
1788 if (!bDocWasModified)
1789 {
1790 ResetModified();
1791 }
1792 }
1793
1794 // if necessary update statistical fields
1795 SwFieldType *pType = GetSysFldType(RES_DOCSTATFLD);
1796 pType->UpdateFlds();
1797 }
1798 }
1799
1800
1801 // Document - Info
1802
DocInfoChgd()1803 void SwDoc::DocInfoChgd( )
1804 {
1805 GetSysFldType( RES_DOCINFOFLD )->UpdateFlds();
1806 GetSysFldType( RES_TEMPLNAMEFLD )->UpdateFlds();
1807 SetModified();
1808 }
1809
1810 // return the reference that is set in the Doc, together with the name
GetRefMark(const String & rName) const1811 const SwFmtRefMark* SwDoc::GetRefMark( const String& rName ) const
1812 {
1813 const SfxPoolItem* pItem;
1814 sal_uInt32 nMaxItems = GetAttrPool().GetItemCount2( RES_TXTATR_REFMARK );
1815 for( sal_uInt32 n = 0; n < nMaxItems; ++n )
1816 {
1817 if( 0 == (pItem = GetAttrPool().GetItem2( RES_TXTATR_REFMARK, n ) ))
1818 continue;
1819
1820 const SwFmtRefMark* pFmtRef = (SwFmtRefMark*)pItem;
1821 const SwTxtRefMark* pTxtRef = pFmtRef->GetTxtRefMark();
1822 if( pTxtRef && &pTxtRef->GetTxtNode().GetNodes() == &GetNodes() &&
1823 rName.Equals( pFmtRef->GetRefName() ) )
1824 return pFmtRef;
1825 }
1826 return 0;
1827 }
1828
1829 // return the RefMark by Index - for Uno
GetRefMark(sal_uInt16 nIndex) const1830 const SwFmtRefMark* SwDoc::GetRefMark( sal_uInt16 nIndex ) const
1831 {
1832 const SfxPoolItem* pItem;
1833 const SwTxtRefMark* pTxtRef;
1834 const SwFmtRefMark* pRet = 0;
1835
1836 sal_uInt32 nMaxItems = GetAttrPool().GetItemCount2( RES_TXTATR_REFMARK );
1837 sal_uInt32 nCount = 0;
1838 for( sal_uInt32 n = 0; n < nMaxItems; ++n )
1839 if( 0 != (pItem = GetAttrPool().GetItem2( RES_TXTATR_REFMARK, n )) &&
1840 0 != (pTxtRef = ((SwFmtRefMark*)pItem)->GetTxtRefMark()) &&
1841 &pTxtRef->GetTxtNode().GetNodes() == &GetNodes() )
1842 {
1843 if(nCount == nIndex)
1844 {
1845 pRet = (SwFmtRefMark*)pItem;
1846 break;
1847 }
1848 nCount++;
1849 }
1850 return pRet;
1851 }
1852
1853 // return the names of all references that are set in the Doc
1854 // JP 24.06.96: If the ArrayPointer is 0 then return only when a RefMark is set in the Doc
1855 // OS 25.06.96: from now on always return the number of the references
GetRefMarks(SvStringsDtor * pNames) const1856 sal_uInt16 SwDoc::GetRefMarks( SvStringsDtor* pNames ) const
1857 {
1858 const SfxPoolItem* pItem;
1859 const SwTxtRefMark* pTxtRef;
1860
1861 const sal_uInt32 nMaxItems = GetAttrPool().GetItemCount2( RES_TXTATR_REFMARK );
1862 sal_uInt16 nCount = 0;
1863 for( sal_uInt32 n = 0; n < nMaxItems; ++n )
1864 if( 0 != (pItem = GetAttrPool().GetItem2( RES_TXTATR_REFMARK, n )) &&
1865 0 != (pTxtRef = ((SwFmtRefMark*)pItem)->GetTxtRefMark()) &&
1866 &pTxtRef->GetTxtNode().GetNodes() == &GetNodes() )
1867 {
1868 if( pNames )
1869 {
1870 String* pTmp = new String( ((SwFmtRefMark*)pItem)->GetRefName() );
1871 pNames->Insert( pTmp, nCount );
1872 }
1873 ++nCount;
1874 }
1875
1876 return nCount;
1877 }
1878
IsLoaded() const1879 bool SwDoc::IsLoaded() const
1880 {
1881 return mbLoaded;
1882 }
1883
IsUpdateExpFld() const1884 bool SwDoc::IsUpdateExpFld() const
1885 {
1886 return mbUpdateExpFld;
1887 }
1888
IsNewDoc() const1889 bool SwDoc::IsNewDoc() const
1890 {
1891 return mbNewDoc;
1892 }
1893
IsPageNums() const1894 bool SwDoc::IsPageNums() const
1895 {
1896 return mbPageNums;
1897 }
1898
SetPageNums(bool b)1899 void SwDoc::SetPageNums(bool b)
1900 {
1901 mbPageNums = b;
1902 }
1903
SetNewDoc(bool b)1904 void SwDoc::SetNewDoc(bool b)
1905 {
1906 mbNewDoc = b;
1907 }
1908
SetUpdateExpFldStat(bool b)1909 void SwDoc::SetUpdateExpFldStat(bool b)
1910 {
1911 mbUpdateExpFld = b;
1912 }
1913
SetLoaded(bool b)1914 void SwDoc::SetLoaded(bool b)
1915 {
1916 mbLoaded = b;
1917 }
1918
IsModified() const1919 bool SwDoc::IsModified() const
1920 {
1921 return mbModified;
1922 }
1923
SetModified()1924 void SwDoc::SetModified()
1925 {
1926 // --> OD 2005-08-29 #125370#
1927 SwLayouter::ClearMovedFwdFrms( *this );
1928 SwLayouter::ClearObjsTmpConsiderWrapInfluence( *this );
1929 SwLayouter::ClearFrmsNotToWrap( *this );
1930 // <--
1931 // --> OD 2006-05-10 #i65250#
1932 SwLayouter::ClearMoveBwdLayoutInfo( *this );
1933 // <--
1934 // return the status to the link, how the flags were and will be
1935 // Bit 0: -> old status
1936 // Bit 1: -> new status
1937 long nCall = mbModified ? 3 : 2;
1938 mbModified = sal_True;
1939 pDocStat->bModified = sal_True;
1940 if( aOle2Link.IsSet() )
1941 {
1942 mbInCallModified = sal_True;
1943 aOle2Link.Call( (void*)nCall );
1944 mbInCallModified = sal_False;
1945 }
1946
1947 if( pACEWord && !pACEWord->IsDeleted() )
1948 delete pACEWord, pACEWord = 0;
1949 }
1950
ResetModified()1951 void SwDoc::ResetModified()
1952 {
1953 // return the status to the link, how the flags were and will be
1954 // Bit 0: -> old status
1955 // Bit 1: -> new status
1956 long nCall = mbModified ? 1 : 0;
1957 mbModified = sal_False;
1958 // If there is already a document statistic, we assume that
1959 // it is correct. In this case we reset the modified flag.
1960 if ( 0 != pDocStat->nChar )
1961 pDocStat->bModified = sal_False;
1962 GetIDocumentUndoRedo().SetUndoNoModifiedPosition();
1963 if( nCall && aOle2Link.IsSet() )
1964 {
1965 mbInCallModified = sal_True;
1966 aOle2Link.Call( (void*)nCall );
1967 mbInCallModified = sal_False;
1968 }
1969 }
1970
1971
ReRead(SwPaM & rPam,const String & rGrfName,const String & rFltName,const Graphic * pGraphic,const GraphicObject * pGrafObj)1972 void SwDoc::ReRead( SwPaM& rPam, const String& rGrfName,
1973 const String& rFltName, const Graphic* pGraphic,
1974 const GraphicObject* pGrafObj )
1975 {
1976 SwGrfNode *pGrfNd;
1977 if( ( !rPam.HasMark()
1978 || rPam.GetPoint()->nNode.GetIndex() == rPam.GetMark()->nNode.GetIndex() )
1979 && 0 != ( pGrfNd = rPam.GetPoint()->nNode.GetNode().GetGrfNode() ) )
1980 {
1981 if (GetIDocumentUndoRedo().DoesUndo())
1982 {
1983 GetIDocumentUndoRedo().AppendUndo(new SwUndoReRead(rPam, *pGrfNd));
1984 }
1985
1986 // Because it's not known if the graphic can be mirrored,
1987 // always set back the MirrorAttribute
1988 if( RES_MIRROR_GRAPH_DONT != pGrfNd->GetSwAttrSet().
1989 GetMirrorGrf().GetValue() )
1990 pGrfNd->SetAttr( SwMirrorGrf() );
1991
1992 pGrfNd->ReRead( rGrfName, rFltName, pGraphic, pGrafObj, sal_True );
1993 SetModified();
1994 }
1995 }
1996
lcl_SpellAndGrammarAgain(const SwNodePtr & rpNd,void * pArgs)1997 sal_Bool lcl_SpellAndGrammarAgain( const SwNodePtr& rpNd, void* pArgs )
1998 {
1999 SwTxtNode *pTxtNode = (SwTxtNode*)rpNd->GetTxtNode();
2000 sal_Bool bOnlyWrong = *(sal_Bool*)pArgs;
2001 if( pTxtNode )
2002 {
2003 if( bOnlyWrong )
2004 {
2005 if( pTxtNode->GetWrong() &&
2006 pTxtNode->GetWrong()->InvalidateWrong() )
2007 pTxtNode->SetWrongDirty( true );
2008 if( pTxtNode->GetGrammarCheck() &&
2009 pTxtNode->GetGrammarCheck()->InvalidateWrong() )
2010 pTxtNode->SetGrammarCheckDirty( true );
2011 }
2012 else
2013 {
2014 pTxtNode->SetWrongDirty( true );
2015 if( pTxtNode->GetWrong() )
2016 pTxtNode->GetWrong()->SetInvalid( 0, STRING_LEN );
2017 pTxtNode->SetGrammarCheckDirty( true );
2018 if( pTxtNode->GetGrammarCheck() )
2019 pTxtNode->GetGrammarCheck()->SetInvalid( 0, STRING_LEN );
2020 }
2021 }
2022 return sal_True;
2023 }
2024
lcl_CheckSmartTagsAgain(const SwNodePtr & rpNd,void *)2025 sal_Bool lcl_CheckSmartTagsAgain( const SwNodePtr& rpNd, void* )
2026 {
2027 SwTxtNode *pTxtNode = (SwTxtNode*)rpNd->GetTxtNode();
2028 // sal_Bool bOnlyWrong = *(sal_Bool*)pArgs;
2029 if( pTxtNode )
2030 {
2031 pTxtNode->SetSmartTagDirty( true );
2032 if( pTxtNode->GetSmartTags() )
2033 {
2034 // if ( bOnlyWrong ) // only some smart tag types have been enabled or disabled
2035 // pTxtNode->GetSmartTags()->SetInvalid( 0, STRING_LEN );
2036 // else // smart tags all have been enabled or disabled
2037 pTxtNode->SetSmartTags( NULL );
2038 }
2039 }
2040 return sal_True;
2041 }
2042
2043
2044 /*************************************************************************
2045 * SwDoc::SpellItAgainSam( sal_Bool bInvalid, sal_Bool bOnlyWrong )
2046 *
2047 * Is activating again the spelling in the Idle handler.
2048 * When bInvalid will be hand over as sal_True, then additionally the WrongLists
2049 * on all Nodes will be invalidated and on all pages the SpellInvalid flag
2050 * will be set.
2051 * With bOnlyWrong you can control, whether only the areas with wrong words
2052 * or the complete areas have to be checked again.
2053 ************************************************************************/
2054
SpellItAgainSam(sal_Bool bInvalid,sal_Bool bOnlyWrong,sal_Bool bSmartTags)2055 void SwDoc::SpellItAgainSam( sal_Bool bInvalid, sal_Bool bOnlyWrong, sal_Bool bSmartTags )
2056 {
2057 std::set<SwRootFrm*> aAllLayouts = GetAllLayouts();//swmod 080307
2058 ASSERT( GetCurrentLayout(), "SpellAgain: Where's my RootFrm?" );
2059 if( bInvalid )
2060 {
2061 std::for_each( aAllLayouts.begin(), aAllLayouts.end(),std::bind2nd(std::mem_fun(&SwRootFrm::AllInvalidateSmartTagsOrSpelling),bSmartTags));//swmod 080305
2062 std::for_each( aAllLayouts.begin(), aAllLayouts.end(),std::bind2nd(std::mem_fun(&SwRootFrm::SetNeedGrammarCheck), true) );
2063 if ( bSmartTags )
2064 GetNodes().ForEach( lcl_CheckSmartTagsAgain, &bOnlyWrong );
2065 GetNodes().ForEach( lcl_SpellAndGrammarAgain, &bOnlyWrong );
2066 }
2067
2068 std::for_each( aAllLayouts.begin(), aAllLayouts.end(),std::mem_fun(&SwRootFrm::SetIdleFlags));//swmod 080307
2069 }
2070
InvalidateAutoCompleteFlag()2071 void SwDoc::InvalidateAutoCompleteFlag()
2072 {
2073 SwRootFrm* pTmpRoot = GetCurrentLayout();
2074 if( pTmpRoot )
2075 {
2076 std::set<SwRootFrm*> aAllLayouts = GetAllLayouts();
2077 std::for_each( aAllLayouts.begin(), aAllLayouts.end(),std::mem_fun(&SwRootFrm::AllInvalidateAutoCompleteWords));//swmod 080305
2078 for( sal_uLong nNd = 1, nCnt = GetNodes().Count(); nNd < nCnt; ++nNd )
2079 {
2080 SwTxtNode* pTxtNode = GetNodes()[ nNd ]->GetTxtNode();
2081 if ( pTxtNode ) pTxtNode->SetAutoCompleteWordDirty( true );
2082 }
2083
2084 std::for_each( aAllLayouts.begin(), aAllLayouts.end(),std::mem_fun(&SwRootFrm::SetIdleFlags));//swmod 080228
2085 } //swmod 080219
2086 }
2087
FindINetAttr(const String & rName) const2088 const SwFmtINetFmt* SwDoc::FindINetAttr( const String& rName ) const
2089 {
2090 const SwFmtINetFmt* pItem;
2091 const SwTxtINetFmt* pTxtAttr;
2092 const SwTxtNode* pTxtNd;
2093 sal_uInt32 n, nMaxItems = GetAttrPool().GetItemCount2( RES_TXTATR_INETFMT );
2094 for( n = 0; n < nMaxItems; ++n )
2095 if( 0 != (pItem = (SwFmtINetFmt*)GetAttrPool().GetItem2(
2096 RES_TXTATR_INETFMT, n ) ) &&
2097 pItem->GetName().Equals( rName ) &&
2098 0 != ( pTxtAttr = pItem->GetTxtINetFmt()) &&
2099 0 != ( pTxtNd = pTxtAttr->GetpTxtNode() ) &&
2100 &pTxtNd->GetNodes() == &GetNodes() )
2101 {
2102 return pItem;
2103 }
2104
2105 return 0;
2106 }
2107
Summary(SwDoc * pExtDoc,sal_uInt8 nLevel,sal_uInt8 nPara,sal_Bool bImpress)2108 void SwDoc::Summary( SwDoc* pExtDoc, sal_uInt8 nLevel, sal_uInt8 nPara, sal_Bool bImpress )
2109 {
2110 const SwOutlineNodes& rOutNds = GetNodes().GetOutLineNds();
2111 if( pExtDoc && rOutNds.Count() )
2112 {
2113 sal_uInt16 i;
2114 ::StartProgress( STR_STATSTR_SUMMARY, 0, rOutNds.Count(), GetDocShell() );
2115 SwNodeIndex aEndOfDoc( pExtDoc->GetNodes().GetEndOfContent(), -1 );
2116 for( i = 0; i < rOutNds.Count(); ++i )
2117 {
2118 ::SetProgressState( i, GetDocShell() );
2119 const sal_uLong nIndex = rOutNds[ i ]->GetIndex();
2120 //sal_uInt8 nLvl = ((SwTxtNode*)GetNodes()[ nIndex ])->GetTxtColl()//#outline level,zhaojianwei
2121 // ->GetOutlineLevel();
2122 const int nLvl = ((SwTxtNode*)GetNodes()[ nIndex ])->GetAttrOutlineLevel()-1;//<-end,zhaojianwei
2123 if( nLvl > nLevel )
2124 continue;
2125 sal_uInt16 nEndOfs = 1;
2126 sal_uInt8 nWish = nPara;
2127 sal_uLong nNextOutNd = i + 1 < rOutNds.Count() ?
2128 rOutNds[ i + 1 ]->GetIndex() : GetNodes().Count();
2129 sal_Bool bKeep = sal_False;
2130 while( ( nWish || bKeep ) && nIndex + nEndOfs < nNextOutNd &&
2131 GetNodes()[ nIndex + nEndOfs ]->IsTxtNode() )
2132 {
2133 SwTxtNode* pTxtNode = (SwTxtNode*)GetNodes()[ nIndex+nEndOfs ];
2134 if( pTxtNode->GetTxt().Len() && nWish )
2135 --nWish;
2136 bKeep = pTxtNode->GetSwAttrSet().GetKeep().GetValue();
2137 ++nEndOfs;
2138 }
2139
2140 SwNodeRange aRange( *rOutNds[ i ], 0, *rOutNds[ i ], nEndOfs );
2141 GetNodes()._Copy( aRange, aEndOfDoc );
2142 }
2143 const SwTxtFmtColls *pColl = pExtDoc->GetTxtFmtColls();
2144 for( i = 0; i < pColl->Count(); ++i )
2145 (*pColl)[ i ]->ResetFmtAttr( RES_PAGEDESC, RES_BREAK );
2146 SwNodeIndex aIndx( pExtDoc->GetNodes().GetEndOfExtras() );
2147 ++aEndOfDoc;
2148 while( aIndx < aEndOfDoc )
2149 {
2150 SwNode *pNode;
2151 sal_Bool bDelete = sal_False;
2152 if( (pNode = &aIndx.GetNode())->IsTxtNode() )
2153 {
2154 SwTxtNode *pNd = (SwTxtNode*)pNode;
2155 if( pNd->HasSwAttrSet() )
2156 pNd->ResetAttr( RES_PAGEDESC, RES_BREAK );
2157 if( bImpress )
2158 {
2159 SwTxtFmtColl* pMyColl = pNd->GetTxtColl();
2160 //sal_uInt16 nHeadLine = static_cast<sal_uInt16>(pMyColl->GetOutlineLevel()==NO_NUMBERING ?//#outlinelevel,zhaojianwei
2161 const sal_uInt16 nHeadLine = static_cast<sal_uInt16>(
2162 !pMyColl->IsAssignedToListLevelOfOutlineStyle() //<-end,zhaojianwei
2163 ? RES_POOLCOLL_HEADLINE2
2164 : RES_POOLCOLL_HEADLINE1 );
2165 pMyColl = pExtDoc->GetTxtCollFromPool( nHeadLine );
2166 pNd->ChgFmtColl( pMyColl );
2167 }
2168 if( !pNd->Len() &&
2169 pNd->StartOfSectionIndex()+2 < pNd->EndOfSectionIndex() )
2170 {
2171 bDelete = sal_True;
2172 pExtDoc->GetNodes().Delete( aIndx );
2173 }
2174 }
2175 if( !bDelete )
2176 ++aIndx;
2177 }
2178 ::EndProgress( GetDocShell() );
2179 }
2180 }
2181
2182 // don't delete the visible content from the document, like e.g.,
2183 // hidden sections, hidden paragraphs
RemoveInvisibleContent()2184 bool SwDoc::RemoveInvisibleContent()
2185 {
2186 sal_Bool bRet = sal_False;
2187 GetIDocumentUndoRedo().StartUndo( UNDO_UI_DELETE_INVISIBLECNTNT, NULL );
2188
2189 {
2190 SwTxtNode* pTxtNd;
2191 SwIterator<SwFmtFld,SwFieldType> aIter( *GetSysFldType( RES_HIDDENPARAFLD ) );
2192 for( SwFmtFld* pFmtFld = aIter.First(); pFmtFld; pFmtFld = aIter.Next() )
2193 {
2194 if( pFmtFld->GetTxtFld() &&
2195 0 != ( pTxtNd = (SwTxtNode*)pFmtFld->GetTxtFld()->GetpTxtNode() ) &&
2196 pTxtNd->GetpSwpHints() && pTxtNd->HasHiddenParaField() &&
2197 &pTxtNd->GetNodes() == &GetNodes() )
2198 {
2199 bRet = sal_True;
2200 SwPaM aPam( *pTxtNd, 0, *pTxtNd, pTxtNd->GetTxt().Len() );
2201
2202 // Remove hidden paragraph or delete contents:
2203 // Delete contents if
2204 // 1. removing the paragraph would result in an empty section or
2205 // 2. if the paragraph is the last paragraph in the section and
2206 // there is no paragraph in front of the paragraph:
2207 if ( ( 2 == pTxtNd->EndOfSectionIndex() - pTxtNd->StartOfSectionIndex() ) ||
2208 ( 1 == pTxtNd->EndOfSectionIndex() - pTxtNd->GetIndex() &&
2209 !GetNodes()[ pTxtNd->GetIndex() - 1 ]->GetTxtNode() ) )
2210 {
2211 DeleteRange( aPam );
2212 }
2213 else
2214 {
2215 aPam.DeleteMark();
2216 DelFullPara( aPam );
2217 }
2218 }
2219 }
2220 }
2221
2222 //
2223 // Remove any hidden paragraph (hidden text attribute)
2224 //
2225 for( sal_uLong n = GetNodes().Count(); n; )
2226 {
2227 SwTxtNode* pTxtNd = GetNodes()[ --n ]->GetTxtNode();
2228 if ( pTxtNd )
2229 {
2230 bool bRemoved = false;
2231 SwPaM aPam( *pTxtNd, 0, *pTxtNd, pTxtNd->GetTxt().Len() );
2232 if ( pTxtNd->HasHiddenCharAttribute( true ) )
2233 {
2234 bRemoved = sal_True;
2235 bRet = sal_True;
2236
2237 // Remove hidden paragraph or delete contents:
2238 // Delete contents if
2239 // 1. removing the paragraph would result in an empty section or
2240 // 2. if the paragraph is the last paragraph in the section and
2241 // there is no paragraph in front of the paragraph:
2242
2243 if ( ( 2 == pTxtNd->EndOfSectionIndex() - pTxtNd->StartOfSectionIndex() ) ||
2244 ( 1 == pTxtNd->EndOfSectionIndex() - pTxtNd->GetIndex() &&
2245 !GetNodes()[ pTxtNd->GetIndex() - 1 ]->GetTxtNode() ) )
2246 {
2247 DeleteRange( aPam );
2248 }
2249 else
2250 {
2251 aPam.DeleteMark();
2252 DelFullPara( aPam );
2253 }
2254 }
2255 else if ( pTxtNd->HasHiddenCharAttribute( false ) )
2256 {
2257 bRemoved = sal_True;
2258 bRet = sal_True;
2259 SwScriptInfo::DeleteHiddenRanges( *pTxtNd );
2260 }
2261
2262 // --> FME 2006-01-11 #120473#
2263 // Footnotes/Frames may have been removed, therefore we have
2264 // to reset n:
2265 if ( bRemoved )
2266 n = aPam.GetPoint()->nNode.GetIndex();
2267 // <--
2268 }
2269 }
2270
2271 {
2272 // now delete/empty all hidden sections
2273 SwSectionFmts aSectFmts;
2274 SwSectionFmts& rSectFmts = GetSections();
2275 sal_uInt16 n;
2276
2277 for( n = rSectFmts.Count(); n; )
2278 {
2279 SwSectionFmt* pSectFmt = rSectFmts[ --n ];
2280 // don't add sections in Undo/Redo
2281 if( !pSectFmt->IsInNodesArr())
2282 continue;
2283 SwSection* pSect = pSectFmt->GetSection();
2284 if( pSect->CalcHiddenFlag() )
2285 {
2286 SwSection* pParent = pSect, *pTmp;
2287 while( 0 != (pTmp = pParent->GetParent() ))
2288 {
2289 if( pTmp->IsHiddenFlag() )
2290 pSect = pTmp;
2291 pParent = pTmp;
2292 }
2293
2294 if( USHRT_MAX == aSectFmts.GetPos( pSect->GetFmt() ) )
2295 aSectFmts.Insert( pSect->GetFmt(), 0 );
2296 }
2297 if( pSect->GetCondition().Len() )
2298 {
2299 SwSectionData aSectionData( *pSect );
2300 aSectionData.SetCondition( aEmptyStr );
2301 aSectionData.SetHidden( false );
2302 UpdateSection( n, aSectionData );
2303 }
2304 }
2305
2306 if( 0 != ( n = aSectFmts.Count() ))
2307 {
2308 while( n )
2309 {
2310 SwSectionFmt* pSectFmt = aSectFmts[ --n ];
2311 SwSectionNode* pSectNd = pSectFmt->GetSectionNode();
2312 if( pSectNd )
2313 {
2314 bRet = sal_True;
2315 SwPaM aPam( *pSectNd );
2316
2317 if( pSectNd->StartOfSectionNode()->StartOfSectionIndex() ==
2318 pSectNd->GetIndex() - 1 &&
2319 pSectNd->StartOfSectionNode()->EndOfSectionIndex() ==
2320 pSectNd->EndOfSectionIndex() + 1 )
2321 {
2322 // delete only the content
2323 SwCntntNode* pCNd = GetNodes().GoNext(
2324 &aPam.GetPoint()->nNode );
2325 aPam.GetPoint()->nContent.Assign( pCNd, 0 );
2326 aPam.SetMark();
2327 aPam.GetPoint()->nNode = *pSectNd->EndOfSectionNode();
2328 pCNd = GetNodes().GoPrevious(
2329 &aPam.GetPoint()->nNode );
2330 aPam.GetPoint()->nContent.Assign( pCNd, pCNd->Len() );
2331
2332 DeleteRange( aPam );
2333 }
2334 else
2335 {
2336 // delete the complete section
2337 aPam.SetMark();
2338 aPam.GetPoint()->nNode = *pSectNd->EndOfSectionNode();
2339 DelFullPara( aPam );
2340 }
2341
2342 }
2343 }
2344 aSectFmts.Remove( 0, aSectFmts.Count() );
2345 }
2346 }
2347
2348 if( bRet )
2349 SetModified();
2350 GetIDocumentUndoRedo().EndUndo( UNDO_UI_DELETE_INVISIBLECNTNT, NULL );
2351 return bRet;
2352 }
2353 /*-- 25.08.2010 14:18:12---------------------------------------------------
2354
2355 -----------------------------------------------------------------------*/
HasInvisibleContent() const2356 bool SwDoc::HasInvisibleContent() const
2357 {
2358 sal_Bool bRet = sal_False;
2359
2360 SwClientIter aIter( *GetSysFldType( RES_HIDDENPARAFLD ) );
2361 if( aIter.First( TYPE( SwFmtFld ) ) )
2362 bRet = sal_True;
2363
2364 //
2365 // Search for any hidden paragraph (hidden text attribute)
2366 //
2367 if( ! bRet )
2368 {
2369 for( sal_uLong n = GetNodes().Count(); !bRet && (n > 0); )
2370 {
2371 SwTxtNode* pTxtNd = GetNodes()[ --n ]->GetTxtNode();
2372 if ( pTxtNd )
2373 {
2374 SwPaM aPam( *pTxtNd, 0, *pTxtNd, pTxtNd->GetTxt().Len() );
2375 if( pTxtNd->HasHiddenCharAttribute( true ) || ( pTxtNd->HasHiddenCharAttribute( false ) ) )
2376 {
2377 bRet = sal_True;
2378 }
2379 }
2380 }
2381 }
2382
2383 if( ! bRet )
2384 {
2385 const SwSectionFmts& rSectFmts = GetSections();
2386 sal_uInt16 n;
2387
2388 for( n = rSectFmts.Count(); !bRet && (n > 0); )
2389 {
2390 SwSectionFmt* pSectFmt = rSectFmts[ --n ];
2391 // don't add sections in Undo/Redo
2392 if( !pSectFmt->IsInNodesArr())
2393 continue;
2394 SwSection* pSect = pSectFmt->GetSection();
2395 if( pSect->IsHidden() )
2396 bRet = sal_True;
2397 }
2398 }
2399 return bRet;
2400 }
2401
RestoreInvisibleContent()2402 bool SwDoc::RestoreInvisibleContent()
2403 {
2404 bool bRet = false;
2405 SwUndoId nLastUndoId(UNDO_EMPTY);
2406 if (GetIDocumentUndoRedo().GetLastUndoInfo(0, & nLastUndoId)
2407 && (UNDO_UI_DELETE_INVISIBLECNTNT == nLastUndoId))
2408 {
2409 GetIDocumentUndoRedo().Undo();
2410 GetIDocumentUndoRedo().ClearRedo();
2411 bRet = true;
2412 }
2413 return bRet;
2414 }
2415
2416 /*-- 11.06.2004 08:34:04---------------------------------------------------
2417
2418 -----------------------------------------------------------------------*/
ConvertFieldsToText()2419 sal_Bool SwDoc::ConvertFieldsToText()
2420 {
2421 sal_Bool bRet = sal_False;
2422 LockExpFlds();
2423 GetIDocumentUndoRedo().StartUndo( UNDO_UI_REPLACE, NULL );
2424
2425 const SwFldTypes* pMyFldTypes = GetFldTypes();
2426 sal_uInt16 nCount = pMyFldTypes->Count();
2427 //go backward, field types are removed
2428 for(sal_uInt16 nType = nCount; nType > 0; --nType)
2429 {
2430 const SwFieldType *pCurType = pMyFldTypes->GetObject(nType - 1);
2431
2432 if ( RES_POSTITFLD == pCurType->Which() )
2433 continue;
2434
2435 SwIterator<SwFmtFld,SwFieldType> aIter( *pCurType );
2436 ::std::vector<const SwFmtFld*> aFieldFmts;
2437 for( SwFmtFld* pCurFldFmt = aIter.First(); pCurFldFmt; pCurFldFmt = aIter.Next() )
2438 aFieldFmts.push_back(pCurFldFmt);
2439
2440 ::std::vector<const SwFmtFld*>::iterator aBegin = aFieldFmts.begin();
2441 ::std::vector<const SwFmtFld*>::iterator aEnd = aFieldFmts.end();
2442 while(aBegin != aEnd)
2443 {
2444 const SwTxtFld *pTxtFld = (*aBegin)->GetTxtFld();
2445 // skip fields that are currently not in the document
2446 // e.g. fields in undo or redo array
2447
2448 sal_Bool bSkip = !pTxtFld ||
2449 !pTxtFld->GetpTxtNode()->GetNodes().IsDocNodes();
2450
2451 if (!bSkip)
2452 {
2453 sal_Bool bInHeaderFooter = IsInHeaderFooter(SwNodeIndex(*pTxtFld->GetpTxtNode()));
2454 const SwFmtFld& rFmtFld = pTxtFld->GetFmtFld();
2455 const SwField* pField = rFmtFld.GetField();
2456
2457 //#i55595# some fields have to be excluded in headers/footers
2458 sal_uInt16 nWhich = pField->GetTyp()->Which();
2459 if(!bInHeaderFooter ||
2460 (nWhich != RES_PAGENUMBERFLD &&
2461 nWhich != RES_CHAPTERFLD &&
2462 nWhich != RES_GETEXPFLD&&
2463 nWhich != RES_SETEXPFLD&&
2464 nWhich != RES_INPUTFLD&&
2465 nWhich != RES_REFPAGEGETFLD&&
2466 nWhich != RES_REFPAGESETFLD))
2467 {
2468 String sText = pField->ExpandField(true);
2469 //database fields should not convert their command into text
2470 if( RES_DBFLD == pCurType->Which() && !static_cast<const SwDBField*>(pField)->IsInitialized())
2471 sText.Erase();
2472
2473 //now remove the field and insert the string
2474 SwPaM aPam1(*pTxtFld->GetpTxtNode(), *pTxtFld->GetStart());
2475 aPam1.Move();
2476 //insert first to keep the field's attributes
2477 InsertString( aPam1, sText );
2478 SwPaM aPam2(*pTxtFld->GetpTxtNode(), *pTxtFld->GetStart());
2479 aPam2.SetMark();
2480 aPam2.Move();
2481 DeleteAndJoin(aPam2);//remove the field
2482 }
2483 }
2484 ++aBegin;
2485 }
2486 }
2487
2488 if( bRet )
2489 SetModified();
2490 GetIDocumentUndoRedo().EndUndo( UNDO_UI_REPLACE, NULL );
2491 UnlockExpFlds();
2492 return bRet;
2493
2494 }
2495
IsVisibleLinks() const2496 bool SwDoc::IsVisibleLinks() const
2497 {
2498 return mbVisibleLinks;
2499 }
2500
SetVisibleLinks(bool bFlag)2501 void SwDoc::SetVisibleLinks(bool bFlag)
2502 {
2503 mbVisibleLinks = bFlag;
2504 }
2505
GetLinkManager()2506 sfx2::LinkManager& SwDoc::GetLinkManager()
2507 {
2508 return *pLinkMgr;
2509 }
2510
GetLinkManager() const2511 const sfx2::LinkManager& SwDoc::GetLinkManager() const
2512 {
2513 return *pLinkMgr;
2514 }
2515
SetLinksUpdated(const bool bNewLinksUpdated)2516 void SwDoc::SetLinksUpdated(const bool bNewLinksUpdated)
2517 {
2518 mbLinksUpdated = bNewLinksUpdated;
2519 }
2520
LinksUpdated() const2521 bool SwDoc::LinksUpdated() const
2522 {
2523 return mbLinksUpdated;
2524 }
2525
2526 // embed all local links (sections/graphics)
lcl_FindNextRemovableLink(const::sfx2::SvBaseLinks & rLinks,sfx2::LinkManager & rLnkMgr)2527 ::sfx2::SvBaseLink* lcl_FindNextRemovableLink( const ::sfx2::SvBaseLinks& rLinks, sfx2::LinkManager& rLnkMgr )
2528 {
2529 for( sal_uInt16 n = 0; n < rLinks.Count(); ++n )
2530 {
2531 ::sfx2::SvBaseLink* pLnk = &(*rLinks[ n ]);
2532 if( pLnk &&
2533 ( OBJECT_CLIENT_GRF == pLnk->GetObjType() ||
2534 OBJECT_CLIENT_FILE == pLnk->GetObjType() ) &&
2535 pLnk->ISA( SwBaseLink ) )
2536 {
2537 ::sfx2::SvBaseLinkRef xLink = pLnk;
2538
2539 String sFName;
2540 rLnkMgr.GetDisplayNames( xLink, 0, &sFName, 0, 0 );
2541
2542 INetURLObject aURL( sFName );
2543 if( INET_PROT_FILE == aURL.GetProtocol() ||
2544 INET_PROT_CID == aURL.GetProtocol() )
2545 return pLnk;
2546 }
2547 }
2548 return 0;
2549 }
EmbedAllLinks()2550 bool SwDoc::EmbedAllLinks()
2551 {
2552 sal_Bool bRet = sal_False;
2553 sfx2::LinkManager& rLnkMgr = GetLinkManager();
2554 const ::sfx2::SvBaseLinks& rLinks = rLnkMgr.GetLinks();
2555 if( rLinks.Count() )
2556 {
2557 ::sw::UndoGuard const undoGuard(GetIDocumentUndoRedo());
2558
2559 ::sfx2::SvBaseLink* pLnk = 0;
2560 while( 0 != (pLnk = lcl_FindNextRemovableLink( rLinks, rLnkMgr ) ) )
2561 {
2562 ::sfx2::SvBaseLinkRef xLink = pLnk;
2563 // tell the link that it will be cleared!
2564 xLink->Closed();
2565
2566 // in the case a link was not deregistered
2567 if( xLink.Is() )
2568 rLnkMgr.Remove( xLink );
2569
2570 bRet = sal_True;
2571 }
2572
2573 GetIDocumentUndoRedo().DelAllUndoObj();
2574 SetModified();
2575 }
2576 return bRet;
2577 }
2578
2579 /*--------------------------------------------------------------------
2580 Description:
2581 --------------------------------------------------------------------*/
2582
IsInsTblFormatNum() const2583 sal_Bool SwDoc::IsInsTblFormatNum() const
2584 {
2585 return SW_MOD()->IsInsTblFormatNum(get(IDocumentSettingAccess::HTML_MODE));
2586 }
2587
IsInsTblChangeNumFormat() const2588 sal_Bool SwDoc::IsInsTblChangeNumFormat() const
2589 {
2590 return SW_MOD()->IsInsTblChangeNumFormat(get(IDocumentSettingAccess::HTML_MODE));
2591 }
2592
2593 /*--------------------------------------------------------------------
2594 Description:
2595 --------------------------------------------------------------------*/
2596
IsInsTblAlignNum() const2597 sal_Bool SwDoc::IsInsTblAlignNum() const
2598 {
2599 return SW_MOD()->IsInsTblAlignNum(get(IDocumentSettingAccess::HTML_MODE));
2600 }
2601
2602 // set the InsertDB as table Undo to:
AppendUndoForInsertFromDB(const SwPaM & rPam,sal_Bool bIsTable)2603 void SwDoc::AppendUndoForInsertFromDB( const SwPaM& rPam, sal_Bool bIsTable )
2604 {
2605 if( bIsTable )
2606 {
2607 const SwTableNode* pTblNd = rPam.GetPoint()->nNode.GetNode().FindTableNode();
2608 if( pTblNd )
2609 {
2610 SwUndoCpyTbl* pUndo = new SwUndoCpyTbl;
2611 pUndo->SetTableSttIdx( pTblNd->GetIndex() );
2612 GetIDocumentUndoRedo().AppendUndo( pUndo );
2613 }
2614 }
2615 else if( rPam.HasMark() )
2616 {
2617 SwUndoCpyDoc* pUndo = new SwUndoCpyDoc( rPam );
2618 pUndo->SetInsertRange( rPam, sal_False );
2619 GetIDocumentUndoRedo().AppendUndo( pUndo );
2620 }
2621 }
2622
ChgTOX(SwTOXBase & rTOX,const SwTOXBase & rNew)2623 void SwDoc::ChgTOX(SwTOXBase & rTOX, const SwTOXBase & rNew)
2624 {
2625 if (GetIDocumentUndoRedo().DoesUndo())
2626 {
2627 GetIDocumentUndoRedo().DelAllUndoObj();
2628
2629 SwUndo * pUndo = new SwUndoTOXChange(&rTOX, rNew);
2630
2631 GetIDocumentUndoRedo().AppendUndo(pUndo);
2632 }
2633
2634 rTOX = rNew;
2635
2636 if (rTOX.ISA(SwTOXBaseSection))
2637 {
2638 static_cast<SwTOXBaseSection &>(rTOX).Update();
2639 static_cast<SwTOXBaseSection &>(rTOX).UpdatePageNum();
2640 }
2641 }
2642
2643 // #111827#
GetPaMDescr(const SwPaM & rPam) const2644 String SwDoc::GetPaMDescr(const SwPaM & rPam) const
2645 {
2646 String aResult;
2647 bool bOK = false;
2648
2649 if (rPam.GetNode(sal_True) == rPam.GetNode(sal_False))
2650 {
2651 SwTxtNode * pTxtNode = rPam.GetNode(sal_True)->GetTxtNode();
2652
2653 if (0 != pTxtNode)
2654 {
2655 xub_StrLen nStart = rPam.Start()->nContent.GetIndex();
2656 xub_StrLen nEnd = rPam.End()->nContent.GetIndex();
2657
2658 aResult += String(SW_RES(STR_START_QUOTE));
2659 aResult += ShortenString(pTxtNode->GetTxt().
2660 Copy(nStart, nEnd - nStart),
2661 nUndoStringLength,
2662 String(SW_RES(STR_LDOTS)));
2663 aResult += String(SW_RES(STR_END_QUOTE));
2664
2665 bOK = true;
2666 }
2667 }
2668 else if (0 != rPam.GetNode(sal_True))
2669 {
2670 if (0 != rPam.GetNode(sal_False))
2671 aResult += String(SW_RES(STR_PARAGRAPHS));
2672
2673 bOK = true;
2674 }
2675
2676 if (! bOK)
2677 aResult += String("??", RTL_TEXTENCODING_ASCII_US);
2678
2679 return aResult;
2680 }
2681
GetFieldAtPos(const SwPosition & rPos)2682 SwField * SwDoc::GetFieldAtPos(const SwPosition & rPos)
2683 {
2684 SwTxtFld * const pAttr = GetTxtFldAtPos(rPos);
2685
2686 return (pAttr) ? const_cast<SwField *>( pAttr->GetFmtFld().GetField() ) : 0;
2687 }
2688
GetTxtFldAtPos(const SwPosition & rPos)2689 SwTxtFld * SwDoc::GetTxtFldAtPos(const SwPosition & rPos)
2690 {
2691 SwTxtNode * const pNode = rPos.nNode.GetNode().GetTxtNode();
2692
2693 return (pNode != NULL)
2694 ? pNode->GetFldTxtAttrAt( rPos.nContent.GetIndex(), true )
2695 : 0;
2696 }
2697
ContainsHiddenChars() const2698 bool SwDoc::ContainsHiddenChars() const
2699 {
2700 for( sal_uLong n = GetNodes().Count(); n; )
2701 {
2702 SwNode* pNd = GetNodes()[ --n ];
2703 if ( ND_TEXTNODE == pNd->GetNodeType() &&
2704 ((SwTxtNode*)pNd)->HasHiddenCharAttribute( false ) )
2705 return true;
2706 }
2707
2708 return false;
2709 }
2710
CreateUnoCrsr(const SwPosition & rPos,sal_Bool bTblCrsr)2711 SwUnoCrsr* SwDoc::CreateUnoCrsr( const SwPosition& rPos, sal_Bool bTblCrsr )
2712 {
2713 SwUnoCrsr* pNew;
2714 if( bTblCrsr )
2715 pNew = new SwUnoTableCrsr( rPos );
2716 else
2717 pNew = new SwUnoCrsr( rPos );
2718
2719 pUnoCrsrTbl->Insert( pNew, pUnoCrsrTbl->Count() );
2720 return pNew;
2721 }
2722
ChkCondColls()2723 void SwDoc::ChkCondColls()
2724 {
2725 for (sal_uInt16 n = 0; n < pTxtFmtCollTbl->Count(); n++)
2726 {
2727 SwTxtFmtColl *pColl = (*pTxtFmtCollTbl)[n];
2728 if (RES_CONDTXTFMTCOLL == pColl->Which())
2729 pColl->CallSwClientNotify( SwAttrHint(RES_CONDTXTFMTCOLL) );
2730 }
2731 }
2732
2733 #ifdef FUTURE_VBA
2734 uno::Reference< script::vba::XVBAEventProcessor >
GetVbaEventProcessor()2735 SwDoc::GetVbaEventProcessor()
2736 {
2737 if( !mxVbaEvents.is() && pDocShell && ooo::vba::isAlienWordDoc( *pDocShell ) )
2738 {
2739 try
2740 {
2741 uno::Reference< frame::XModel > xModel( pDocShell->GetModel(), uno::UNO_SET_THROW );
2742 uno::Sequence< uno::Any > aArgs(1);
2743 aArgs[0] <<= xModel;
2744 mxVbaEvents.set( ooo::vba::createVBAUnoAPIServiceWithArgs( pDocShell, "com.sun.star.script.vba.VBATextEventProcessor" , aArgs ), uno::UNO_QUERY_THROW );
2745 }
2746 catch( uno::Exception& )
2747 {
2748 }
2749 }
2750 return mxVbaEvents;
2751 }
2752 #endif
2753
setExternalData(::sw::tExternalDataType eType,::sw::tExternalDataPointer pPayload)2754 void SwDoc::setExternalData(::sw::tExternalDataType eType,
2755 ::sw::tExternalDataPointer pPayload)
2756 {
2757 m_externalData[eType] = pPayload;
2758 }
2759
getExternalData(::sw::tExternalDataType eType)2760 ::sw::tExternalDataPointer SwDoc::getExternalData(::sw::tExternalDataType eType)
2761 {
2762 return m_externalData[eType];
2763 }
2764
2765