1 /* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
3 * This file is part of the LibreOffice project.
5 * This Source Code Form is subject to the terms of the Mozilla Public
6 * License, v. 2.0. If a copy of the MPL was not distributed with this
7 * file, You can obtain one at http://mozilla.org/MPL/2.0/.
9 * This file incorporates work covered by the following license notice:
11 * Licensed to the Apache Software Foundation (ASF) under one or more
12 * contributor license agreements. See the NOTICE file distributed
13 * with this work for additional information regarding copyright
14 * ownership. The ASF licenses this file to you under the Apache
15 * License, Version 2.0 (the "License"); you may not use this file
16 * except in compliance with the License. You may obtain a copy of
17 * the License at http://www.apache.org/licenses/LICENSE-2.0 .
20 #include "scitems.hxx"
21 #include <editeng/eeitem.hxx>
23 #include <tools/urlobj.hxx>
24 #include <editeng/editobj.hxx>
25 #include <editeng/editstat.hxx>
26 #include <editeng/frmdiritem.hxx>
27 #include <editeng/langitem.hxx>
28 #include <sfx2/linkmgr.hxx>
29 #include <editeng/scripttypeitem.hxx>
30 #include <editeng/unolingu.hxx>
31 #include <sfx2/bindings.hxx>
32 #include <sfx2/objsh.hxx>
33 #include <sfx2/printer.hxx>
34 #include <sfx2/viewfrm.hxx>
35 #include <sfx2/viewsh.hxx>
36 #include <svl/flagitem.hxx>
37 #include <svl/intitem.hxx>
38 #include <svl/zforlist.hxx>
39 #include <svl/zformat.hxx>
40 #include <unotools/misccfg.hxx>
41 #include <sfx2/app.hxx>
42 #include <unotools/transliterationwrapper.hxx>
43 #include <unotools/securityoptions.hxx>
45 #include <vcl/virdev.hxx>
46 #include <vcl/msgbox.hxx>
48 #include <com/sun/star/i18n/TransliterationModulesExtra.hpp>
50 #include "inputopt.hxx"
54 #include "poolhelp.hxx"
55 #include "docpool.hxx"
56 #include "stlpool.hxx"
57 #include "stlsheet.hxx"
58 #include "docoptio.hxx"
59 #include "viewopti.hxx"
60 #include "scextopt.hxx"
61 #include "rechead.hxx"
62 #include "ddelink.hxx"
63 #include "scmatrix.hxx"
64 #include "arealink.hxx"
65 #include "dociter.hxx"
66 #include "patattr.hxx"
68 #include "editutil.hxx"
69 #include "progress.hxx"
70 #include "document.hxx"
71 #include "chartlis.hxx"
72 #include "chartlock.hxx"
73 #include "refupdat.hxx"
74 #include "validat.hxx"
75 #include "markdata.hxx"
77 #include "printopt.hxx"
78 #include "externalrefmgr.hxx"
79 #include "globstr.hrc"
81 #include "charthelper.hxx"
82 #include "macromgr.hxx"
83 #include "dpobject.hxx"
85 #include "scresid.hxx"
86 #include "columniterator.hxx"
87 #include "globalnames.hxx"
88 #include "stringutil.hxx"
91 #include <boost/scoped_ptr.hpp>
93 using namespace com::sun::star
;
95 // STATIC DATA -----------------------------------------------------------
99 inline sal_uInt16
getScaleValue(SfxStyleSheetBase
& rStyle
, sal_uInt16 nWhich
)
101 return static_cast<const SfxUInt16Item
&>(rStyle
.GetItemSet().Get(nWhich
)).GetValue();
106 void ScDocument::ImplCreateOptions()
108 pDocOptions
= new ScDocOptions();
109 pViewOptions
= new ScViewOptions();
112 //------------------------------------------------------------------------
114 void ScDocument::ImplDeleteOptions()
118 delete pExtDocOptions
;
121 //------------------------------------------------------------------------
123 SfxPrinter
* ScDocument::GetPrinter(bool bCreateIfNotExist
)
125 if ( !pPrinter
&& bCreateIfNotExist
)
128 new SfxItemSet( *xPoolHelper
->GetDocPool(),
129 SID_PRINTER_NOTFOUND_WARN
, SID_PRINTER_NOTFOUND_WARN
,
130 SID_PRINTER_CHANGESTODOC
, SID_PRINTER_CHANGESTODOC
,
131 SID_PRINT_SELECTEDSHEET
, SID_PRINT_SELECTEDSHEET
,
132 SID_SCPRINTOPTIONS
, SID_SCPRINTOPTIONS
,
135 ::utl::MiscCfg aMisc
;
136 sal_uInt16 nFlags
= 0;
137 if ( aMisc
.IsPaperOrientationWarning() )
138 nFlags
|= SFX_PRINTER_CHG_ORIENTATION
;
139 if ( aMisc
.IsPaperSizeWarning() )
140 nFlags
|= SFX_PRINTER_CHG_SIZE
;
141 pSet
->Put( SfxFlagItem( SID_PRINTER_CHANGESTODOC
, nFlags
) );
142 pSet
->Put( SfxBoolItem( SID_PRINTER_NOTFOUND_WARN
, aMisc
.IsNotFoundWarning() ) );
144 pPrinter
= new SfxPrinter( pSet
);
145 pPrinter
->SetMapMode( MAP_100TH_MM
);
147 pPrinter
->SetDigitLanguage( SC_MOD()->GetOptDigitLanguage() );
153 //------------------------------------------------------------------------
155 void ScDocument::SetPrinter( SfxPrinter
* pNewPrinter
)
157 if ( pNewPrinter
== pPrinter
)
159 // #i6706# SetPrinter is called with the same printer again if
160 // the JobSetup has changed. In that case just call UpdateDrawPrinter
161 // (SetRefDevice for drawing layer) because of changed text sizes.
166 SfxPrinter
* pOld
= pPrinter
;
167 pPrinter
= pNewPrinter
;
169 pPrinter
->SetDigitLanguage( SC_MOD()->GetOptDigitLanguage() );
172 InvalidateTextWidth(NULL
, NULL
, false); // in both cases
175 //------------------------------------------------------------------------
177 void ScDocument::SetPrintOptions()
179 if ( !pPrinter
) GetPrinter(); // setzt pPrinter
180 OSL_ENSURE( pPrinter
, "Error in printer creation :-/" );
184 ::utl::MiscCfg aMisc
;
185 SfxItemSet
aOptSet( pPrinter
->GetOptions() );
187 sal_uInt16 nFlags
= 0;
188 if ( aMisc
.IsPaperOrientationWarning() )
189 nFlags
|= SFX_PRINTER_CHG_ORIENTATION
;
190 if ( aMisc
.IsPaperSizeWarning() )
191 nFlags
|= SFX_PRINTER_CHG_SIZE
;
192 aOptSet
.Put( SfxFlagItem( SID_PRINTER_CHANGESTODOC
, nFlags
) );
193 aOptSet
.Put( SfxBoolItem( SID_PRINTER_NOTFOUND_WARN
, aMisc
.IsNotFoundWarning() ) );
195 pPrinter
->SetOptions( aOptSet
);
199 //------------------------------------------------------------------------
201 VirtualDevice
* ScDocument::GetVirtualDevice_100th_mm()
203 if (!pVirtualDevice_100th_mm
)
206 pVirtualDevice_100th_mm
= new VirtualDevice( 8 );
208 pVirtualDevice_100th_mm
= new VirtualDevice( 1 );
210 pVirtualDevice_100th_mm
->SetReferenceDevice(VirtualDevice::REFDEV_MODE_MSO1
);
211 MapMode
aMapMode( pVirtualDevice_100th_mm
->GetMapMode() );
212 aMapMode
.SetMapUnit( MAP_100TH_MM
);
213 pVirtualDevice_100th_mm
->SetMapMode( aMapMode
);
215 return pVirtualDevice_100th_mm
;
218 OutputDevice
* ScDocument::GetRefDevice()
220 // Create printer like ref device, see Writer...
221 OutputDevice
* pRefDevice
= NULL
;
222 if ( SC_MOD()->GetInputOptions().GetTextWysiwyg() )
223 pRefDevice
= GetPrinter();
225 pRefDevice
= GetVirtualDevice_100th_mm();
229 //------------------------------------------------------------------------
231 void ScDocument::ModifyStyleSheet( SfxStyleSheetBase
& rStyleSheet
,
232 const SfxItemSet
& rChanges
)
234 SfxItemSet
& rSet
= rStyleSheet
.GetItemSet();
236 switch ( rStyleSheet
.GetFamily() )
238 case SFX_STYLE_FAMILY_PAGE
:
240 const sal_uInt16 nOldScale
= getScaleValue(rStyleSheet
, ATTR_PAGE_SCALE
);
241 const sal_uInt16 nOldScaleToPages
= getScaleValue(rStyleSheet
, ATTR_PAGE_SCALETOPAGES
);
242 rSet
.Put( rChanges
);
243 const sal_uInt16 nNewScale
= getScaleValue(rStyleSheet
, ATTR_PAGE_SCALE
);
244 const sal_uInt16 nNewScaleToPages
= getScaleValue(rStyleSheet
, ATTR_PAGE_SCALETOPAGES
);
246 if ( (nOldScale
!= nNewScale
) || (nOldScaleToPages
!= nNewScaleToPages
) )
247 InvalidateTextWidth( rStyleSheet
.GetName() );
249 if( SvtLanguageOptions().IsCTLFontEnabled() )
251 const SfxPoolItem
*pItem
= NULL
;
252 if( rChanges
.GetItemState(ATTR_WRITINGDIR
, true, &pItem
) == SFX_ITEM_SET
)
253 ScChartHelper::DoUpdateAllCharts( this );
258 case SFX_STYLE_FAMILY_PARA
:
260 bool bNumFormatChanged
;
261 if ( ScGlobal::CheckWidthInvalidate( bNumFormatChanged
,
263 InvalidateTextWidth( NULL
, NULL
, bNumFormatChanged
);
265 for (SCTAB nTab
=0; nTab
<=MAXTAB
; ++nTab
)
266 if (maTabs
[nTab
] && maTabs
[nTab
]->IsStreamValid())
267 maTabs
[nTab
]->SetStreamValid( false );
269 sal_uLong nOldFormat
=
270 ((const SfxUInt32Item
*)&rSet
.Get(
271 ATTR_VALUE_FORMAT
))->GetValue();
272 sal_uLong nNewFormat
=
273 ((const SfxUInt32Item
*)&rChanges
.Get(
274 ATTR_VALUE_FORMAT
))->GetValue();
275 LanguageType eNewLang
, eOldLang
;
276 eNewLang
= eOldLang
= LANGUAGE_DONTKNOW
;
277 if ( nNewFormat
!= nOldFormat
)
279 SvNumberFormatter
* pFormatter
= GetFormatTable();
280 eOldLang
= pFormatter
->GetEntry( nOldFormat
)->GetLanguage();
281 eNewLang
= pFormatter
->GetEntry( nNewFormat
)->GetLanguage();
284 // Bedeutung der Items in rChanges:
285 // Item gesetzt - Aenderung uebernehmen
286 // Dontcare - Default setzen
287 // Default - keine Aenderung
288 // ("keine Aenderung" geht nicht mit PutExtended, darum Schleife)
289 for (sal_uInt16 nWhich
= ATTR_PATTERN_START
; nWhich
<= ATTR_PATTERN_END
; nWhich
++)
291 const SfxPoolItem
* pItem
;
292 SfxItemState eState
= rChanges
.GetItemState( nWhich
, false, &pItem
);
293 if ( eState
== SFX_ITEM_SET
)
295 else if ( eState
== SFX_ITEM_DONTCARE
)
296 rSet
.ClearItem( nWhich
);
297 // bei Default nichts
300 if ( eNewLang
!= eOldLang
)
302 SvxLanguageItem( eNewLang
, ATTR_LANGUAGE_FORMAT
) );
307 // added to avoid warnings
312 //------------------------------------------------------------------------
314 void ScDocument::CopyStdStylesFrom( ScDocument
* pSrcDoc
)
316 // number format exchange list has to be handled here, too
317 NumFmtMergeHandler
aNumFmtMergeHdl(this, pSrcDoc
);
318 xPoolHelper
->GetStylePool()->CopyStdStylesFrom( pSrcDoc
->xPoolHelper
->GetStylePool() );
321 //------------------------------------------------------------------------
323 void ScDocument::InvalidateTextWidth( const OUString
& rStyleName
)
325 const SCTAB nCount
= GetTableCount();
326 for ( SCTAB i
=0; i
<nCount
&& maTabs
[i
]; i
++ )
327 if ( maTabs
[i
]->GetPageStyle() == rStyleName
)
328 InvalidateTextWidth( i
);
331 //------------------------------------------------------------------------
333 void ScDocument::InvalidateTextWidth( SCTAB nTab
)
335 ScAddress
aAdrFrom( 0, 0, nTab
);
336 ScAddress
aAdrTo ( MAXCOL
, MAXROW
, nTab
);
337 InvalidateTextWidth( &aAdrFrom
, &aAdrTo
, false );
340 //------------------------------------------------------------------------
342 bool ScDocument::IsPageStyleInUse( const OUString
& rStrPageStyle
, SCTAB
* pInTab
)
345 const SCTAB nCount
= GetTableCount();
348 for ( i
= 0; !bInUse
&& i
< nCount
&& maTabs
[i
]; i
++ )
349 bInUse
= ( maTabs
[i
]->GetPageStyle() == rStrPageStyle
);
357 //------------------------------------------------------------------------
359 bool ScDocument::RemovePageStyleInUse( const OUString
& rStyle
)
361 bool bWasInUse
= false;
362 const SCTAB nCount
= GetTableCount();
364 for ( SCTAB i
=0; i
<nCount
&& maTabs
[i
]; i
++ )
365 if ( maTabs
[i
]->GetPageStyle() == rStyle
)
368 maTabs
[i
]->SetPageStyle( ScGlobal::GetRscString(STR_STYLENAME_STANDARD
) );
374 bool ScDocument::RenamePageStyleInUse( const OUString
& rOld
, const OUString
& rNew
)
376 bool bWasInUse
= false;
377 const SCTAB nCount
= GetTableCount();
379 for ( SCTAB i
=0; i
<nCount
&& maTabs
[i
]; i
++ )
380 if ( maTabs
[i
]->GetPageStyle() == rOld
)
383 maTabs
[i
]->SetPageStyle( rNew
);
389 //------------------------------------------------------------------------
391 sal_uInt8
ScDocument::GetEditTextDirection(SCTAB nTab
) const
393 EEHorizontalTextDirection eRet
= EE_HTEXTDIR_DEFAULT
;
395 OUString aStyleName
= GetPageStyle( nTab
);
396 SfxStyleSheetBase
* pStyle
= xPoolHelper
->GetStylePool()->Find( aStyleName
, SFX_STYLE_FAMILY_PAGE
);
399 SfxItemSet
& rStyleSet
= pStyle
->GetItemSet();
400 SvxFrameDirection eDirection
= (SvxFrameDirection
)
401 ((const SvxFrameDirectionItem
&)rStyleSet
.Get( ATTR_WRITINGDIR
)).GetValue();
403 if ( eDirection
== FRMDIR_HORI_LEFT_TOP
)
404 eRet
= EE_HTEXTDIR_L2R
;
405 else if ( eDirection
== FRMDIR_HORI_RIGHT_TOP
)
406 eRet
= EE_HTEXTDIR_R2L
;
407 // else (invalid for EditEngine): keep "default"
410 return sal::static_int_cast
<sal_uInt8
>(eRet
);
413 ScMacroManager
* ScDocument::GetMacroManager()
415 if (!mpMacroMgr
.get())
416 mpMacroMgr
.reset(new ScMacroManager(this));
417 return mpMacroMgr
.get();
420 bool ScDocument::IsEmptyData( SCTAB nTab
, SCCOL nCol
) const
422 const ScTable
* pTab
= FetchTable(nTab
);
426 return pTab
->IsEmptyData(nCol
);
429 void ScDocument::FillMatrix(
430 ScMatrix
& rMat
, SCTAB nTab
, SCCOL nCol1
, SCROW nRow1
, SCCOL nCol2
, SCROW nRow2
) const
432 const ScTable
* pTab
= FetchTable(nTab
);
436 if (nCol1
> nCol2
|| nRow1
> nRow2
)
440 rMat
.GetDimensions(nC
, nR
);
441 if (static_cast<SCROW
>(nR
) != nRow2
- nRow1
+ 1 || static_cast<SCCOL
>(nC
) != nCol2
- nCol1
+ 1)
444 pTab
->FillMatrix(rMat
, nCol1
, nRow1
, nCol2
, nRow2
);
447 void ScDocument::SetFormulaResults( const ScAddress
& rTopPos
, const double* pResults
, size_t nLen
)
449 ScTable
* pTab
= FetchTable(rTopPos
.Tab());
453 pTab
->SetFormulaResults(rTopPos
.Col(), rTopPos
.Row(), pResults
, nLen
);
456 void ScDocument::SetFormulaResults(
457 const ScAddress
& rTopPos
, const formula::FormulaTokenRef
* pResults
, size_t nLen
)
459 ScTable
* pTab
= FetchTable(rTopPos
.Tab());
463 pTab
->SetFormulaResults(rTopPos
.Col(), rTopPos
.Row(), pResults
, nLen
);
466 void ScDocument::InvalidateTextWidth( const ScAddress
* pAdrFrom
, const ScAddress
* pAdrTo
,
467 bool bNumFormatChanged
)
469 bool bBroadcast
= (bNumFormatChanged
&& GetDocOptions().IsCalcAsShown() && !IsImportingXML() && !IsClipboard());
470 if ( pAdrFrom
&& !pAdrTo
)
472 const SCTAB nTab
= pAdrFrom
->Tab();
474 if (nTab
< static_cast<SCTAB
>(maTabs
.size()) && maTabs
[nTab
] )
475 maTabs
[nTab
]->InvalidateTextWidth( pAdrFrom
, NULL
, bNumFormatChanged
, bBroadcast
);
479 const SCTAB nTabStart
= pAdrFrom
? pAdrFrom
->Tab() : 0;
480 const SCTAB nTabEnd
= pAdrTo
? pAdrTo
->Tab() : MAXTAB
;
482 for ( SCTAB nTab
=nTabStart
; nTab
<=nTabEnd
&& nTab
< static_cast<SCTAB
>(maTabs
.size()); nTab
++ )
484 maTabs
[nTab
]->InvalidateTextWidth( pAdrFrom
, pAdrTo
, bNumFormatChanged
, bBroadcast
);
488 //------------------------------------------------------------------------
490 #define CALCMAX 1000 // Berechnungen
491 #define ABORT_EVENTS (VCL_INPUT_ANY & ~VCL_INPUT_TIMER & ~VCL_INPUT_OTHER)
495 class IdleCalcTextWidthScope
498 ScAddress
& mrCalcPos
;
499 MapMode maOldMapMode
;
500 sal_uLong mnStartTime
;
501 ScStyleSheetPool
* mpStylePool
;
502 sal_uInt16 mnOldSearchMask
;
503 SfxStyleFamily meOldFamily
;
508 IdleCalcTextWidthScope(ScDocument
& rDoc
, ScAddress
& rCalcPos
) :
511 mnStartTime(Time::GetSystemTicks()),
512 mpStylePool(rDoc
.GetStyleSheetPool()),
513 mnOldSearchMask(mpStylePool
->GetSearchMask()),
514 meOldFamily(mpStylePool
->GetSearchFamily()),
518 // The old search mask / family flags must be restored so that e.g.
519 // the styles dialog shows correct listing when it's opened in-between
522 mrDoc
.EnableIdle(false);
523 mpStylePool
->SetSearchMask(SFX_STYLE_FAMILY_PAGE
, SFXSTYLEBIT_ALL
);
526 ~IdleCalcTextWidthScope()
528 SfxPrinter
* pDev
= mrDoc
.GetPrinter();
530 pDev
->SetMapMode(maOldMapMode
);
533 ScProgress::DeleteInterpretProgress();
535 mpStylePool
->SetSearchMask(meOldFamily
, mnOldSearchMask
);
536 mrDoc
.EnableIdle(true);
539 SCTAB
Tab() const { return mrCalcPos
.Tab(); }
540 SCCOL
Col() const { return mrCalcPos
.Col(); }
541 SCROW
Row() const { return mrCalcPos
.Row(); }
543 void setTab(SCTAB nTab
) { mrCalcPos
.SetTab(nTab
); }
544 void setCol(SCCOL nCol
) { mrCalcPos
.SetCol(nCol
); }
545 void setRow(SCROW nRow
) { mrCalcPos
.SetRow(nRow
); }
547 void incTab(SCTAB nInc
=1) { mrCalcPos
.IncTab(nInc
); }
548 void incCol(SCCOL nInc
=1) { mrCalcPos
.IncCol(nInc
); }
550 void setOldMapMode(const MapMode
& rOldMapMode
) { maOldMapMode
= rOldMapMode
; }
552 void setNeedMore(bool b
) { mbNeedMore
= b
; }
553 bool getNeedMore() const { return mbNeedMore
; }
555 sal_uLong
getStartTime() const { return mnStartTime
; }
557 void createProgressBar()
559 ScProgress::CreateInterpretProgress(&mrDoc
, false);
563 bool hasProgressBar() const { return mbProgress
; }
565 ScStyleSheetPool
* getStylePool() { return mpStylePool
; }
570 bool ScDocument::IdleCalcTextWidth() // true = demnaechst wieder versuchen
572 // #i75610# if a printer hasn't been set or created yet, don't create one for this
573 if (!mbIdleEnabled
|| IsInLinkUpdate() || GetPrinter(false) == NULL
)
576 IdleCalcTextWidthScope
aScope(*this, aCurTextWidthCalcPos
);
578 if (!ValidRow(aScope
.Row()))
584 if (aScope
.Col() < 0)
586 aScope
.setCol(MAXCOL
);
590 if (!ValidTab(aScope
.Tab()) || aScope
.Tab() >= static_cast<SCTAB
>(maTabs
.size()) || !maTabs
[aScope
.Tab()])
593 ScTable
* pTab
= maTabs
[aScope
.Tab()];
594 ScStyleSheet
* pStyle
= (ScStyleSheet
*)aScope
.getStylePool()->Find(pTab
->aPageStyle
, SFX_STYLE_FAMILY_PAGE
);
595 OSL_ENSURE( pStyle
, "Missing StyleSheet :-/" );
597 if (!pStyle
|| getScaleValue(*pStyle
, ATTR_PAGE_SCALETOPAGES
) == 0)
599 // Move to the next sheet as the current one has scale-to-pages set,
605 sal_uInt16 nZoom
= getScaleValue(*pStyle
, ATTR_PAGE_SCALE
);
606 Fraction
aZoomFract(nZoom
, 100);
608 // Start at specified cell position (nCol, nRow, nTab).
609 ScColumn
* pCol
= &pTab
->aCol
[aScope
.Col()];
610 boost::scoped_ptr
<ScColumnTextWidthIterator
> pColIter(new ScColumnTextWidthIterator(*pCol
, aScope
.Row(), MAXROW
));
612 OutputDevice
* pDev
= NULL
;
613 sal_uInt16 nRestart
= 0;
614 sal_uInt16 nCount
= 0;
615 while ( (nZoom
> 0) && (nCount
< CALCMAX
) && (nRestart
< 2) )
617 if (pColIter
->hasCell())
619 // More cell in this column.
620 SCROW nRow
= pColIter
->getPos();
623 if (pColIter
->getValue() == TEXTWIDTH_DIRTY
)
625 // Calculate text width for this cell.
631 aScope
.setOldMapMode(pDev
->GetMapMode());
632 pDev
->SetMapMode( MAP_PIXEL
); // wichtig fuer GetNeededSize
634 Point aPix1000
= pDev
->LogicToPixel( Point(1000,1000), MAP_TWIP
);
635 nPPTX
= aPix1000
.X() / 1000.0;
636 nPPTY
= aPix1000
.Y() / 1000.0;
639 if (!aScope
.hasProgressBar() && pCol
->IsFormulaDirty(nRow
))
640 aScope
.createProgressBar();
642 sal_uInt16 nNewWidth
= (sal_uInt16
)GetNeededSize(
643 aScope
.Col(), aScope
.Row(), aScope
.Tab(),
644 pDev
, nPPTX
, nPPTY
, aZoomFract
,aZoomFract
, true, true); // bTotalSize
646 pColIter
->setValue(nNewWidth
);
647 aScope
.setNeedMore(true);
653 // No more cell in this column. Move to the left column and start at row 0.
655 bool bNewTab
= false;
660 if (aScope
.Col() < 0)
662 // No more column to the left. Move to the right-most column of the next sheet.
663 aScope
.setCol(MAXCOL
);
668 if (!ValidTab(aScope
.Tab()) || aScope
.Tab() >= static_cast<SCTAB
>(maTabs
.size()) || !maTabs
[aScope
.Tab()] )
670 // Sheet doesn't exist at specified sheet position. Restart at sheet 0.
680 pTab
= maTabs
[aScope
.Tab()];
681 pStyle
= (ScStyleSheet
*)aScope
.getStylePool()->Find(
682 pTab
->aPageStyle
, SFX_STYLE_FAMILY_PAGE
);
686 // Check if the scale-to-pages setting is set. If
687 // set, we exit the loop. If not, get the page
688 // scale factor of the new sheet.
689 if (getScaleValue(*pStyle
, ATTR_PAGE_SCALETOPAGES
) == 0)
691 nZoom
= getScaleValue(*pStyle
, ATTR_PAGE_SCALE
);
692 aZoomFract
= Fraction(nZoom
, 100);
699 OSL_FAIL( "Missing StyleSheet :-/" );
705 pCol
= &pTab
->aCol
[aScope
.Col()];
706 pColIter
.reset(new ScColumnTextWidthIterator(*pCol
, aScope
.Row(), MAXROW
));
710 aScope
.incTab(); // Move to the next sheet as the current one has scale-to-pages set.
718 // Quit if either 1) its duration exceeds 50 ms, or 2) there is any
719 // pending event after processing 32 cells.
720 if ((50L < Time::GetSystemTicks() - aScope
.getStartTime()) || (nCount
> 31 && Application::AnyInput(ABORT_EVENTS
)))
724 return aScope
.getNeedMore();
727 void ScDocument::RepaintRange( const ScRange
& rRange
)
729 if ( bIsVisible
&& pShell
)
731 ScModelObj
* pModel
= ScModelObj::getImplementation( pShell
->GetModel() );
733 pModel
->RepaintRange( rRange
); // locked repaints are checked there
737 void ScDocument::RepaintRange( const ScRangeList
& rRange
)
739 if ( bIsVisible
&& pShell
)
741 ScModelObj
* pModel
= ScModelObj::getImplementation( pShell
->GetModel() );
743 pModel
->RepaintRange( rRange
); // locked repaints are checked there
747 //------------------------------------------------------------------------
749 bool ScDocument::IdleCheckLinks() // true = demnaechst wieder versuchen
751 bool bAnyLeft
= false;
753 if (GetLinkManager())
755 const ::sfx2::SvBaseLinks
& rLinks
= pLinkManager
->GetLinks();
756 sal_uInt16 nCount
= rLinks
.size();
757 for (sal_uInt16 i
=0; i
<nCount
; i
++)
759 ::sfx2::SvBaseLink
* pBase
= *rLinks
[i
];
760 if (pBase
->ISA(ScDdeLink
))
762 ScDdeLink
* pDdeLink
= (ScDdeLink
*)pBase
;
763 if (pDdeLink
->NeedsUpdate())
765 pDdeLink
->TryUpdate();
766 if (pDdeLink
->NeedsUpdate()) // war nix?
776 void ScDocument::SaveDdeLinks(SvStream
& rStream
) const
778 // bei 4.0-Export alle mit Modus != DEFAULT weglassen
779 bool bExport40
= ( rStream
.GetVersion() <= SOFFICE_FILEFORMAT_40
);
781 const ::sfx2::SvBaseLinks
& rLinks
= GetLinkManager()->GetLinks();
782 sal_uInt16 nCount
= rLinks
.size();
784 // erstmal zaehlen...
786 sal_uInt16 nDdeCount
= 0;
788 for (i
=0; i
<nCount
; i
++)
790 ::sfx2::SvBaseLink
* pBase
= *rLinks
[i
];
791 if (pBase
->ISA(ScDdeLink
))
792 if ( !bExport40
|| ((ScDdeLink
*)pBase
)->GetMode() == SC_DDE_DEFAULT
)
798 ScMultipleWriteHeader
aHdr( rStream
);
799 rStream
<< nDdeCount
;
803 for (i
=0; i
<nCount
; i
++)
805 ::sfx2::SvBaseLink
* pBase
= *rLinks
[i
];
806 if (pBase
->ISA(ScDdeLink
))
808 ScDdeLink
* pLink
= (ScDdeLink
*)pBase
;
809 if ( !bExport40
|| pLink
->GetMode() == SC_DDE_DEFAULT
)
810 pLink
->Store( rStream
, aHdr
);
815 void ScDocument::LoadDdeLinks(SvStream
& rStream
)
817 ScMultipleReadHeader
aHdr( rStream
);
822 for (sal_uInt16 i
=0; i
<nCount
; i
++)
824 ScDdeLink
* pLink
= new ScDdeLink( this, rStream
, aHdr
);
825 pLinkManager
->InsertDDELink( pLink
,
826 pLink
->GetAppl(), pLink
->GetTopic(), pLink
->GetItem() );
830 bool ScDocument::HasDdeLinks() const
832 if (GetLinkManager()) // Clipboard z.B. hat keinen LinkManager
834 const ::sfx2::SvBaseLinks
& rLinks
= pLinkManager
->GetLinks();
835 sal_uInt16 nCount
= rLinks
.size();
836 for (sal_uInt16 i
=0; i
<nCount
; i
++)
837 if ((*rLinks
[i
])->ISA(ScDdeLink
))
844 void ScDocument::SetInLinkUpdate(bool bSet
)
846 // called from TableLink and AreaLink
848 OSL_ENSURE( bInLinkUpdate
!= bSet
, "SetInLinkUpdate twice" );
849 bInLinkUpdate
= bSet
;
852 bool ScDocument::IsInLinkUpdate() const
854 return bInLinkUpdate
|| IsInDdeLinkUpdate();
857 void ScDocument::UpdateExternalRefLinks(Window
* pWin
)
859 if (!GetLinkManager())
862 const ::sfx2::SvBaseLinks
& rLinks
= pLinkManager
->GetLinks();
863 sal_uInt16 nCount
= rLinks
.size();
866 for (sal_uInt16 i
= 0; i
< nCount
; ++i
)
868 ::sfx2::SvBaseLink
* pBase
= *rLinks
[i
];
869 ScExternalRefLink
* pRefLink
= dynamic_cast<ScExternalRefLink
*>(pBase
);
872 if (pRefLink
->Update())
876 // Update failed. Notify the user.
879 pLinkManager
->GetDisplayNames(pRefLink
, NULL
, &aFile
, NULL
, NULL
);
880 // Decode encoded URL for display friendliness.
881 INetURLObject
aUrl(aFile
,INetURLObject::WAS_ENCODED
);
882 aFile
= aUrl
.GetMainURL(INetURLObject::DECODE_UNAMBIGUOUS
);
885 aBuf
.append(OUString(ScResId(SCSTR_EXTDOC_NOT_LOADED
)));
886 aBuf
.appendAscii("\n\n");
888 ErrorBox
aBox(pWin
, WB_OK
, aBuf
.makeStringAndClear());
896 pShell
->Broadcast( SfxSimpleHint(FID_DATACHANGED
) );
898 // #i101960# set document modified, as in TrackTimeHdl for DDE links
899 if (!pShell
->IsModified())
901 pShell
->SetModified( true );
902 SfxBindings
* pBindings
= GetViewBindings();
905 pBindings
->Invalidate( SID_SAVEDOC
);
906 pBindings
->Invalidate( SID_DOC_MODIFIED
);
912 void ScDocument::UpdateDdeLinks(Window
* pWin
)
914 if (GetLinkManager())
916 const ::sfx2::SvBaseLinks
& rLinks
= pLinkManager
->GetLinks();
917 sal_uInt16 nCount
= rLinks
.size();
920 // falls das Updaten laenger dauert, erstmal alle Werte
921 // zuruecksetzen, damit nichts altes (falsches) stehen bleibt
923 for (i
=0; i
<nCount
; i
++)
925 ::sfx2::SvBaseLink
* pBase
= *rLinks
[i
];
926 ScDdeLink
* pDdeLink
= dynamic_cast<ScDdeLink
*>(pBase
);
929 if (pDdeLink
->Update())
933 // Update failed. Notify the user.
934 OUString aFile
= pDdeLink
->GetTopic();
935 OUString aElem
= pDdeLink
->GetItem();
936 OUString aType
= pDdeLink
->GetAppl();
939 aBuf
.append(OUString(ScResId(SCSTR_DDEDOC_NOT_LOADED
)));
940 aBuf
.appendAscii("\n\n");
941 aBuf
.appendAscii("Source : ");
943 aBuf
.appendAscii("\nElement : ");
945 aBuf
.appendAscii("\nType : ");
947 ErrorBox
aBox(pWin
, WB_OK
, aBuf
.makeStringAndClear());
954 // Formeln berechnen und painten wie im TrackTimeHdl
956 pShell
->Broadcast( SfxSimpleHint( FID_DATACHANGED
) );
958 // wenn FID_DATACHANGED irgendwann mal asynchron werden sollte
959 // (z.B. mit Invalidate am Window), muss hier ein Update erzwungen werden.
962 pLinkManager
->CloseCachedComps();
966 bool ScDocument::UpdateDdeLink( const OUString
& rAppl
, const OUString
& rTopic
, const OUString
& rItem
)
968 // fuer refresh() per StarOne Api
969 // ResetValue() fuer einzelnen Link nicht noetig
970 //! wenn's mal alles asynchron wird, aber auch hier
973 if (GetLinkManager())
975 const ::sfx2::SvBaseLinks
& rLinks
= pLinkManager
->GetLinks();
976 sal_uInt16 nCount
= rLinks
.size();
977 for (sal_uInt16 i
=0; i
<nCount
; i
++)
979 ::sfx2::SvBaseLink
* pBase
= *rLinks
[i
];
980 if (pBase
->ISA(ScDdeLink
))
982 ScDdeLink
* pDdeLink
= (ScDdeLink
*)pBase
;
983 if ( OUString(pDdeLink
->GetAppl()) == rAppl
&&
984 OUString(pDdeLink
->GetTopic()) == rTopic
&&
985 OUString(pDdeLink
->GetItem()) == rItem
)
987 pDdeLink
->TryUpdate();
988 bFound
= true; // koennen theoretisch mehrere sein (Mode), darum weitersuchen
992 pLinkManager
->CloseCachedComps();
997 void ScDocument::DisconnectDdeLinks()
999 if (GetLinkManager())
1001 const ::sfx2::SvBaseLinks
& rLinks
= pLinkManager
->GetLinks();
1002 sal_uInt16 nCount
= rLinks
.size();
1003 for (sal_uInt16 i
=0; i
<nCount
; i
++)
1005 ::sfx2::SvBaseLink
* pBase
= *rLinks
[i
];
1006 if (pBase
->ISA(ScDdeLink
))
1007 pBase
->Disconnect(); // bleibt im LinkManager eingetragen
1012 void ScDocument::CopyDdeLinks( ScDocument
* pDestDoc
) const
1014 if (bIsClip
) // aus Stream erzeugen
1019 pDestDoc
->LoadDdeLinks(*pClipData
);
1022 else if (GetLinkManager()) // Links direkt kopieren
1024 const ::sfx2::SvBaseLinks
& rLinks
= pLinkManager
->GetLinks();
1025 size_t nCount
= rLinks
.size();
1026 for (size_t i
=0; i
<nCount
; i
++)
1028 ::sfx2::SvBaseLink
* pBase
= *rLinks
[i
];
1029 if (pBase
->ISA(ScDdeLink
))
1031 ScDdeLink
* pNew
= new ScDdeLink( pDestDoc
, *(ScDdeLink
*)pBase
);
1033 pDestDoc
->pLinkManager
->InsertDDELink( pNew
,
1034 pNew
->GetAppl(), pNew
->GetTopic(), pNew
->GetItem() );
1040 size_t ScDocument::GetDdeLinkCount() const
1042 size_t nDdeCount
= 0;
1043 if (GetLinkManager())
1045 const ::sfx2::SvBaseLinks
& rLinks
= pLinkManager
->GetLinks();
1046 size_t nCount
= rLinks
.size();
1047 for (size_t i
=0; i
<nCount
; i
++)
1048 if ((*rLinks
[i
])->ISA(ScDdeLink
))
1054 // ----------------------------------------------------------------------------
1058 /** Tries to find the specified DDE link.
1059 @param pnDdePos (out-param) if not 0, the index of the DDE link is returned here
1060 (does not include other links from link manager).
1061 @return The DDE link, if it exists, otherwise 0. */
1062 ScDdeLink
* lclGetDdeLink(
1063 const sfx2::LinkManager
* pLinkManager
,
1064 const OUString
& rAppl
, const OUString
& rTopic
, const OUString
& rItem
, sal_uInt8 nMode
,
1065 size_t* pnDdePos
= NULL
)
1069 const ::sfx2::SvBaseLinks
& rLinks
= pLinkManager
->GetLinks();
1070 size_t nCount
= rLinks
.size();
1071 if( pnDdePos
) *pnDdePos
= 0;
1072 for( size_t nIndex
= 0; nIndex
< nCount
; ++nIndex
)
1074 ::sfx2::SvBaseLink
* pLink
= *rLinks
[ nIndex
];
1075 if( ScDdeLink
* pDdeLink
= PTR_CAST( ScDdeLink
, pLink
) )
1077 if( (OUString(pDdeLink
->GetAppl()) == rAppl
) &&
1078 (OUString(pDdeLink
->GetTopic()) == rTopic
) &&
1079 (OUString(pDdeLink
->GetItem()) == rItem
) &&
1080 ((nMode
== SC_DDE_IGNOREMODE
) || (nMode
== pDdeLink
->GetMode())) )
1082 if( pnDdePos
) ++*pnDdePos
;
1089 /** Returns a pointer to the specified DDE link.
1090 @param nDdePos Index of the DDE link (does not include other links from link manager).
1091 @return The DDE link, if it exists, otherwise 0. */
1092 ScDdeLink
* lclGetDdeLink( const sfx2::LinkManager
* pLinkManager
, size_t nDdePos
)
1096 const ::sfx2::SvBaseLinks
& rLinks
= pLinkManager
->GetLinks();
1097 size_t nCount
= rLinks
.size();
1098 size_t nDdeIndex
= 0; // counts only the DDE links
1099 for( size_t nIndex
= 0; nIndex
< nCount
; ++nIndex
)
1101 ::sfx2::SvBaseLink
* pLink
= *rLinks
[ nIndex
];
1102 if( ScDdeLink
* pDdeLink
= PTR_CAST( ScDdeLink
, pLink
) )
1104 if( nDdeIndex
== nDdePos
)
1115 // ----------------------------------------------------------------------------
1117 bool ScDocument::FindDdeLink( const OUString
& rAppl
, const OUString
& rTopic
, const OUString
& rItem
,
1118 sal_uInt8 nMode
, size_t& rnDdePos
)
1120 return lclGetDdeLink( GetLinkManager(), rAppl
, rTopic
, rItem
, nMode
, &rnDdePos
) != NULL
;
1123 bool ScDocument::GetDdeLinkData( size_t nDdePos
, OUString
& rAppl
, OUString
& rTopic
, OUString
& rItem
) const
1125 if( const ScDdeLink
* pDdeLink
= lclGetDdeLink( GetLinkManager(), nDdePos
) )
1127 rAppl
= pDdeLink
->GetAppl();
1128 rTopic
= pDdeLink
->GetTopic();
1129 rItem
= pDdeLink
->GetItem();
1135 bool ScDocument::GetDdeLinkMode( size_t nDdePos
, sal_uInt8
& rnMode
) const
1137 if( const ScDdeLink
* pDdeLink
= lclGetDdeLink( GetLinkManager(), nDdePos
) )
1139 rnMode
= pDdeLink
->GetMode();
1145 const ScMatrix
* ScDocument::GetDdeLinkResultMatrix( size_t nDdePos
) const
1147 const ScDdeLink
* pDdeLink
= lclGetDdeLink( GetLinkManager(), nDdePos
);
1148 return pDdeLink
? pDdeLink
->GetResult() : NULL
;
1151 bool ScDocument::CreateDdeLink( const OUString
& rAppl
, const OUString
& rTopic
, const OUString
& rItem
, sal_uInt8 nMode
, ScMatrixRef pResults
)
1153 /* Create a DDE link without updating it (i.e. for Excel import), to prevent
1154 unwanted connections. First try to find existing link. Set result array
1155 on existing and new links. */
1156 //! store DDE links additionally at document (for efficiency)?
1157 OSL_ENSURE( nMode
!= SC_DDE_IGNOREMODE
, "ScDocument::CreateDdeLink - SC_DDE_IGNOREMODE not allowed here" );
1158 if( GetLinkManager() && (nMode
!= SC_DDE_IGNOREMODE
) )
1160 ScDdeLink
* pDdeLink
= lclGetDdeLink( pLinkManager
, rAppl
, rTopic
, rItem
, nMode
);
1163 // create a new DDE link, but without TryUpdate
1164 pDdeLink
= new ScDdeLink( this, rAppl
, rTopic
, rItem
, nMode
);
1165 pLinkManager
->InsertDDELink( pDdeLink
, rAppl
, rTopic
, rItem
);
1168 // insert link results
1170 pDdeLink
->SetResult( pResults
);
1177 bool ScDocument::SetDdeLinkResultMatrix( size_t nDdePos
, ScMatrixRef pResults
)
1179 if( ScDdeLink
* pDdeLink
= lclGetDdeLink( GetLinkManager(), nDdePos
) )
1181 pDdeLink
->SetResult( pResults
);
1187 //------------------------------------------------------------------------
1189 bool ScDocument::HasAreaLinks() const
1191 if (GetLinkManager()) // Clipboard z.B. hat keinen LinkManager
1193 const ::sfx2::SvBaseLinks
& rLinks
= pLinkManager
->GetLinks();
1194 sal_uInt16 nCount
= rLinks
.size();
1195 for (sal_uInt16 i
=0; i
<nCount
; i
++)
1196 if ((*rLinks
[i
])->ISA(ScAreaLink
))
1203 void ScDocument::UpdateAreaLinks()
1205 if (GetLinkManager())
1207 const ::sfx2::SvBaseLinks
& rLinks
= pLinkManager
->GetLinks();
1208 for (sal_uInt16 i
=0; i
<rLinks
.size(); i
++)
1210 ::sfx2::SvBaseLink
* pBase
= *rLinks
[i
];
1211 if (pBase
->ISA(ScAreaLink
))
1217 void ScDocument::DeleteAreaLinksOnTab( SCTAB nTab
)
1219 if (GetLinkManager())
1221 const ::sfx2::SvBaseLinks
& rLinks
= pLinkManager
->GetLinks();
1222 sal_uInt16 nPos
= 0;
1223 while ( nPos
< rLinks
.size() )
1225 const ::sfx2::SvBaseLink
* pBase
= *rLinks
[nPos
];
1226 if ( pBase
->ISA(ScAreaLink
) &&
1227 static_cast<const ScAreaLink
*>(pBase
)->GetDestArea().aStart
.Tab() == nTab
)
1228 pLinkManager
->Remove( nPos
);
1235 void ScDocument::UpdateRefAreaLinks( UpdateRefMode eUpdateRefMode
,
1236 const ScRange
& rRange
, SCsCOL nDx
, SCsROW nDy
, SCsTAB nDz
)
1238 if (GetLinkManager())
1240 bool bAnyUpdate
= false;
1242 const ::sfx2::SvBaseLinks
& rLinks
= pLinkManager
->GetLinks();
1243 sal_uInt16 nCount
= rLinks
.size();
1244 for (sal_uInt16 i
=0; i
<nCount
; i
++)
1246 ::sfx2::SvBaseLink
* pBase
= *rLinks
[i
];
1247 if (pBase
->ISA(ScAreaLink
))
1249 ScAreaLink
* pLink
= (ScAreaLink
*) pBase
;
1250 ScRange aOutRange
= pLink
->GetDestArea();
1252 SCCOL nCol1
= aOutRange
.aStart
.Col();
1253 SCROW nRow1
= aOutRange
.aStart
.Row();
1254 SCTAB nTab1
= aOutRange
.aStart
.Tab();
1255 SCCOL nCol2
= aOutRange
.aEnd
.Col();
1256 SCROW nRow2
= aOutRange
.aEnd
.Row();
1257 SCTAB nTab2
= aOutRange
.aEnd
.Tab();
1259 ScRefUpdateRes eRes
=
1260 ScRefUpdate::Update( this, eUpdateRefMode
,
1261 rRange
.aStart
.Col(), rRange
.aStart
.Row(), rRange
.aStart
.Tab(),
1262 rRange
.aEnd
.Col(), rRange
.aEnd
.Row(), rRange
.aEnd
.Tab(), nDx
, nDy
, nDz
,
1263 nCol1
, nRow1
, nTab1
, nCol2
, nRow2
, nTab2
);
1264 if ( eRes
!= UR_NOTHING
)
1266 pLink
->SetDestArea( ScRange( nCol1
, nRow1
, nTab1
, nCol2
, nRow2
, nTab2
) );
1274 // #i52120# Look for duplicates (after updating all positions).
1275 // If several links start at the same cell, the one with the lower index is removed
1276 // (file format specifies only one link definition for a cell).
1278 sal_uInt16 nFirstIndex
= 0;
1279 while ( nFirstIndex
< nCount
)
1281 bool bFound
= false;
1282 ::sfx2::SvBaseLink
* pFirst
= *rLinks
[nFirstIndex
];
1283 if ( pFirst
->ISA(ScAreaLink
) )
1285 ScAddress aFirstPos
= static_cast<ScAreaLink
*>(pFirst
)->GetDestArea().aStart
;
1286 for ( sal_uInt16 nSecondIndex
= nFirstIndex
+ 1; nSecondIndex
< nCount
&& !bFound
; ++nSecondIndex
)
1288 ::sfx2::SvBaseLink
* pSecond
= *rLinks
[nSecondIndex
];
1289 if ( pSecond
->ISA(ScAreaLink
) &&
1290 static_cast<ScAreaLink
*>(pSecond
)->GetDestArea().aStart
== aFirstPos
)
1292 // remove the first link, exit the inner loop, don't increment nFirstIndex
1293 pLinkManager
->Remove( pFirst
);
1294 nCount
= rLinks
.size();
1306 //------------------------------------------------------------------------
1309 void ScDocument::KeyInput( const KeyEvent
& )
1311 if ( pChartListenerCollection
->hasListeners() )
1312 pChartListenerCollection
->StartTimer();
1313 if( apTemporaryChartLock
.get() )
1314 apTemporaryChartLock
->StartOrContinueLocking();
1317 // ----------------------------------------------------------------------------
1319 bool ScDocument::CheckMacroWarn()
1321 // The check for macro configuration, macro warning and disabling is now handled
1322 // in SfxObjectShell::AdjustMacroMode, called by SfxObjectShell::CallBasic.
1327 //------------------------------------------------------------------------
1329 SfxBindings
* ScDocument::GetViewBindings()
1331 // used to invalidate slots after changes to this document
1334 return NULL
; // no ObjShell -> no view
1336 // first check current view
1337 SfxViewFrame
* pViewFrame
= SfxViewFrame::Current();
1338 if ( pViewFrame
&& pViewFrame
->GetObjectShell() != pShell
) // wrong document?
1341 // otherwise use first view for this doc
1343 pViewFrame
= SfxViewFrame::GetFirst( pShell
);
1346 return &pViewFrame
->GetBindings();
1351 ScDrawLayer
* ScDocument::GetDrawLayer()
1356 //------------------------------------------------------------------------
1358 void ScDocument::TransliterateText( const ScMarkData
& rMultiMark
, sal_Int32 nType
)
1360 OSL_ENSURE( rMultiMark
.IsMultiMarked(), "TransliterateText: no selection" );
1362 utl::TransliterationWrapper
aTranslitarationWrapper( comphelper::getProcessComponentContext(), nType
);
1363 bool bConsiderLanguage
= aTranslitarationWrapper
.needLanguageForTheMode();
1364 sal_uInt16 nLanguage
= LANGUAGE_SYSTEM
;
1366 ScEditEngineDefaulter
* pEngine
= NULL
; // not using pEditEngine member because of defaults
1368 SCTAB nCount
= GetTableCount();
1369 ScMarkData::const_iterator itr
= rMultiMark
.begin(), itrEnd
= rMultiMark
.end();
1370 for (; itr
!= itrEnd
&& *itr
< nCount
; ++itr
)
1377 bool bFound
= rMultiMark
.IsCellMarked( nCol
, nRow
);
1379 bFound
= GetNextMarkedCell( nCol
, nRow
, nTab
, rMultiMark
);
1383 ScRefCellValue aCell
;
1384 aCell
.assign(*this, ScAddress(nCol
, nRow
, nTab
));
1386 // fdo#32786 TITLE_CASE/SENTENCE_CASE need the extra handling in EditEngine (loop over words/sentences).
1387 // Still use TransliterationWrapper directly for text cells with other transliteration types,
1388 // for performance reasons.
1389 if (aCell
.meType
== CELLTYPE_EDIT
||
1390 (aCell
.meType
== CELLTYPE_STRING
&&
1391 ( nType
== i18n::TransliterationModulesExtra::SENTENCE_CASE
|| nType
== i18n::TransliterationModulesExtra::TITLE_CASE
)))
1394 pEngine
= new ScFieldEditEngine(this, GetEnginePool(), GetEditPool());
1396 // defaults from cell attributes must be set so right language is used
1397 const ScPatternAttr
* pPattern
= GetPattern( nCol
, nRow
, nTab
);
1398 SfxItemSet
* pDefaults
= new SfxItemSet( pEngine
->GetEmptyItemSet() );
1399 if ( ScStyleSheet
* pPreviewStyle
= GetPreviewCellStyle( nCol
, nRow
, nTab
) )
1401 ScPatternAttr
* pPreviewPattern
= new ScPatternAttr( *pPattern
);
1402 pPreviewPattern
->SetStyleSheet(pPreviewStyle
);
1403 pPreviewPattern
->FillEditItemSet( pDefaults
);
1404 delete pPreviewPattern
;
1408 SfxItemSet
* pFontSet
= GetPreviewFont( nCol
, nRow
, nTab
);
1409 pPattern
->FillEditItemSet( pDefaults
, pFontSet
);
1411 pEngine
->SetDefaults( pDefaults
, true );
1412 if (aCell
.meType
== CELLTYPE_STRING
)
1413 pEngine
->SetText(aCell
.mpString
->getString());
1414 else if (aCell
.mpEditText
)
1415 pEngine
->SetText(*aCell
.mpEditText
);
1417 pEngine
->ClearModifyFlag();
1419 sal_Int32 nLastPar
= pEngine
->GetParagraphCount();
1422 xub_StrLen nTxtLen
= pEngine
->GetTextLen(nLastPar
);
1423 ESelection
aSelAll( 0, 0, nLastPar
, nTxtLen
);
1425 pEngine
->TransliterateText( aSelAll
, nType
);
1427 if ( pEngine
->IsModified() )
1429 ScEditAttrTester
aTester( pEngine
);
1430 if ( aTester
.NeedsObject() )
1432 // remove defaults (paragraph attributes) before creating text object
1433 SfxItemSet
* pEmpty
= new SfxItemSet( pEngine
->GetEmptyItemSet() );
1434 pEngine
->SetDefaults( pEmpty
, true );
1436 // The cell will take ownership of the text object instance.
1437 SetEditText(ScAddress(nCol
,nRow
,nTab
), pEngine
->CreateTextObject());
1441 ScSetStringParam aParam
;
1442 aParam
.setTextInput();
1443 SetString(ScAddress(nCol
,nRow
,nTab
), pEngine
->GetText(), &aParam
);
1448 else if (aCell
.meType
== CELLTYPE_STRING
)
1450 OUString aOldStr
= aCell
.mpString
->getString();
1451 sal_Int32 nOldLen
= aOldStr
.getLength();
1453 if ( bConsiderLanguage
)
1455 sal_uInt8 nScript
= GetStringScriptType( aOldStr
); //! cell script type?
1456 sal_uInt16 nWhich
= ( nScript
== SCRIPTTYPE_ASIAN
) ? ATTR_CJK_FONT_LANGUAGE
:
1457 ( ( nScript
== SCRIPTTYPE_COMPLEX
) ? ATTR_CTL_FONT_LANGUAGE
:
1458 ATTR_FONT_LANGUAGE
);
1459 nLanguage
= ((const SvxLanguageItem
*)GetAttr( nCol
, nRow
, nTab
, nWhich
))->GetValue();
1462 uno::Sequence
<sal_Int32
> aOffsets
;
1463 OUString aNewStr
= aTranslitarationWrapper
.transliterate( aOldStr
, nLanguage
, 0, nOldLen
, &aOffsets
);
1465 if ( aNewStr
!= aOldStr
)
1467 ScSetStringParam aParam
;
1468 aParam
.setTextInput();
1469 SetString(ScAddress(nCol
,nRow
,nTab
), aNewStr
, &aParam
);
1472 bFound
= GetNextMarkedCell( nCol
, nRow
, nTab
, rMultiMark
);
1478 /* vim:set shiftwidth=4 softtabstop=4 expandtab: */