xref: /core/sc/source/ui/app/scmod.cxx (revision 87c06415)
1 /* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
2 /*
3  * This file is part of the LibreOffice project.
4  *
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/.
8  *
9  * This file incorporates work covered by the following license notice:
10  *
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 .
18  */
19 
20 #include <config_features.h>
21 
22 #include <com/sun/star/ui/dialogs/XSLTFilterDialog.hpp>
23 #include <comphelper/lok.hxx>
24 #include <comphelper/processfactory.hxx>
25 #include <o3tl/make_unique.hxx>
26 #include <scitems.hxx>
27 #include <sfx2/app.hxx>
28 #include <editeng/eeitem.hxx>
29 
30 #include <editeng/flditem.hxx>
31 #include <editeng/outliner.hxx>
32 #include <basic/sbstar.hxx>
33 
34 #include <sfx2/sfxdlg.hxx>
35 #include <sfx2/viewfrm.hxx>
36 #include <sfx2/objface.hxx>
37 
38 #include <IAnyRefDialog.hxx>
39 #include <anyrefdg.hxx>
40 
41 #include <svtools/ehdl.hxx>
42 #include <svtools/accessibilityoptions.hxx>
43 #include <svl/ctloptions.hxx>
44 #include <unotools/useroptions.hxx>
45 #include <vcl/status.hxx>
46 #include <sfx2/bindings.hxx>
47 #include <sfx2/request.hxx>
48 #include <sfx2/printer.hxx>
49 #include <editeng/langitem.hxx>
50 #include <svtools/colorcfg.hxx>
51 
52 #include <svl/whiter.hxx>
53 #include <svx/dialogs.hrc>
54 #include <svx/selctrl.hxx>
55 #include <svx/insctrl.hxx>
56 #include <svx/zoomctrl.hxx>
57 #include <svx/modctrl.hxx>
58 #include <svx/pszctrl.hxx>
59 #include <svx/zoomsliderctrl.hxx>
60 #include <svl/inethist.hxx>
61 #include <vcl/waitobj.hxx>
62 #include <svx/svxerr.hxx>
63 #include <tools/diagnose_ex.h>
64 #include <unotools/resmgr.hxx>
65 
66 #include <editeng/unolingu.hxx>
67 #include <unotools/lingucfg.hxx>
68 #include <i18nlangtag/mslangid.hxx>
69 #include <i18nlangtag/languagetag.hxx>
70 #include <com/sun/star/i18n/ScriptType.hpp>
71 #include <com/sun/star/linguistic2/XThesaurus.hpp>
72 #include <com/sun/star/lang/Locale.hpp>
73 #include <com/sun/star/datatransfer/XTransferable2.hpp>
74 #include <ooo/vba/XSinkCaller.hpp>
75 
76 #include <scmod.hxx>
77 #include <global.hxx>
78 #include <viewopti.hxx>
79 #include <docoptio.hxx>
80 #include <appoptio.hxx>
81 #include <defaultsoptions.hxx>
82 #include <formulaopt.hxx>
83 #include <inputopt.hxx>
84 #include <printopt.hxx>
85 #include <navicfg.hxx>
86 #include <addincfg.hxx>
87 #include <tabvwsh.hxx>
88 #include <prevwsh.hxx>
89 #include <docsh.hxx>
90 #include <drwlayer.hxx>
91 #include <uiitems.hxx>
92 #include <sc.hrc>
93 #include <scerrors.hrc>
94 #include <scstyles.hrc>
95 #include <globstr.hrc>
96 #include <scresid.hxx>
97 #include <bitmaps.hlst>
98 #include <inputhdl.hxx>
99 #include <inputwin.hxx>
100 #include <msgpool.hxx>
101 #include <dwfunctr.hxx>
102 #include <formdata.hxx>
103 #include <tpprint.hxx>
104 #include <tpdefaults.hxx>
105 #include <transobj.hxx>
106 #include <detfunc.hxx>
107 #include <preview.hxx>
108 #include <dragdata.hxx>
109 #include <markdata.hxx>
110 
111 #include <svx/xmlsecctrl.hxx>
112 
113 #define ShellClass_ScModule
114 #include <scslots.hxx>
115 
116 #include <scabstdlg.hxx>
117 #include <formula/errorcodes.hxx>
118 #include <formulagroup.hxx>
119 #include <documentlinkmgr.hxx>
120 
121 #define SC_IDLE_MIN     150
122 #define SC_IDLE_MAX     3000
123 #define SC_IDLE_STEP    75
124 #define SC_IDLE_COUNT   50
125 
126 static sal_uInt16 nIdleCount = 0;
127 
128 SFX_IMPL_INTERFACE(ScModule, SfxShell)
129 
130 void ScModule::InitInterface_Impl()
131 {
132     GetStaticInterface()->RegisterObjectBar(SFX_OBJECTBAR_APPLICATION,
133                                             SfxVisibilityFlags::Standard | SfxVisibilityFlags::Client | SfxVisibilityFlags::Viewer,
134                                             ToolbarId::Objectbar_App);
135 
136     GetStaticInterface()->RegisterStatusBar(StatusBarId::CalcStatusBar);
137 }
138 
139 ScModule::ScModule( SfxObjectFactory* pFact ) :
140     SfxModule("sc", {pFact}),
141     m_aIdleTimer("sc ScModule IdleTimer"),
142     m_aSpellIdle("sc ScModule SpellIdle"),
143     m_pDragData(new ScDragData),
144     m_pSelTransfer( nullptr ),
145     m_pMessagePool( nullptr ),
146     m_pRefInputHandler( nullptr ),
147     m_nCurRefDlgId( 0 ),
148     m_bIsWaterCan( false ),
149     m_bIsInEditCommand( false ),
150     m_bIsInExecuteDrop( false ),
151     m_bIsInSharedDocLoading( false ),
152     m_bIsInSharedDocSaving( false )
153 {
154     // The ResManager (DLL data) is not yet initialized in the ctor!
155     SetName("StarCalc"); // for Basic
156 
157     ResetDragObject();
158 
159     // InputHandler does not need to be created
160 
161     // Create ErrorHandler - was in Init()
162     // Between OfficeApplication::Init and ScGlobal::Init
163     SvxErrorHandler::ensure();
164     m_pErrorHdl.reset( new SfxErrorHandler(RID_ERRHDLSC,
165                                        ErrCodeArea::Sc,
166                                        ErrCodeArea::Sc,
167                                        GetResLocale()) );
168 
169     m_aSpellIdle.SetInvokeHandler( LINK( this, ScModule, SpellTimerHdl ) );
170 
171     m_aIdleTimer.SetTimeout(SC_IDLE_MIN);
172     m_aIdleTimer.SetInvokeHandler( LINK( this, ScModule, IdleHandler ) );
173     m_aIdleTimer.Start();
174 
175     m_pMessagePool = new ScMessagePool;
176     m_pMessagePool->FreezeIdRanges();
177     SetPool( m_pMessagePool );
178     ScGlobal::InitTextHeight( m_pMessagePool );
179 
180     StartListening( *SfxGetpApp() );       // for SfxHintId::Deinitializing
181 }
182 
183 ScModule::~ScModule()
184 {
185     OSL_ENSURE( !m_pSelTransfer, "Selection Transfer object not deleted" );
186 
187     // InputHandler does not need to be deleted (there's none in the App anymore)
188 
189     SfxItemPool::Free(m_pMessagePool);
190 
191     m_pFormEditData.reset();
192 
193     m_pDragData.reset();
194     m_pErrorHdl.reset();
195 
196     ScGlobal::Clear(); // Also calls ScDocumentPool::DeleteVersionMaps();
197 
198     DeleteCfg(); // Called from Exit()
199 }
200 
201 void ScModule::ConfigurationChanged( utl::ConfigurationBroadcaster* p, ConfigurationHints )
202 {
203     if ( p == m_pColorConfig.get() || p == m_pAccessOptions.get() )
204     {
205         // Test if detective objects have to be updated with new colors
206         // (if the detective colors haven't been used yet, there's nothing to update)
207         if ( ScDetectiveFunc::IsColorsInitialized() )
208         {
209             const svtools::ColorConfig& rColors = GetColorConfig();
210             bool bArrows =
211                 ( ScDetectiveFunc::GetArrowColor() != rColors.GetColorValue(svtools::CALCDETECTIVE).nColor ||
212                   ScDetectiveFunc::GetErrorColor() != rColors.GetColorValue(svtools::CALCDETECTIVEERROR).nColor );
213             bool bComments =
214                 ( ScDetectiveFunc::GetCommentColor() != rColors.GetColorValue(svtools::CALCNOTESBACKGROUND).nColor );
215             if ( bArrows || bComments )
216             {
217                 ScDetectiveFunc::InitializeColors(); // get the new colors
218 
219                 // update detective objects in all open documents
220                 SfxObjectShell* pObjSh = SfxObjectShell::GetFirst();
221                 while ( pObjSh )
222                 {
223                     if ( dynamic_cast<const ScDocShell * >(pObjSh) != nullptr )
224                     {
225                         ScDocShell* pDocSh = static_cast<ScDocShell*>(pObjSh);
226                         if ( bArrows )
227                             ScDetectiveFunc( &pDocSh->GetDocument(), 0 ).UpdateAllArrowColors();
228                         if ( bComments )
229                             ScDetectiveFunc::UpdateAllComments( pDocSh->GetDocument() );
230                     }
231                     pObjSh = SfxObjectShell::GetNext( *pObjSh );
232                 }
233             }
234         }
235 
236         // force all views to repaint, using the new options
237         SfxViewShell* pViewShell = SfxViewShell::GetFirst();
238         while(pViewShell)
239         {
240             if (ScTabViewShell* pViewSh = dynamic_cast<ScTabViewShell*>(pViewShell))
241             {
242                 pViewSh->PaintGrid();
243                 pViewSh->PaintTop();
244                 pViewSh->PaintLeft();
245                 pViewSh->PaintExtras();
246 
247                 ScInputHandler* pHdl = pViewSh->GetInputHandler();
248                 if ( pHdl )
249                     pHdl->ForgetLastPattern(); // EditEngine BackgroundColor may change
250             }
251             else if ( dynamic_cast<const ScPreviewShell*>( pViewShell) !=  nullptr )
252             {
253                 vcl::Window* pWin = pViewShell->GetWindow();
254                 if (pWin)
255                     pWin->Invalidate();
256             }
257             pViewShell = SfxViewShell::GetNext( *pViewShell );
258         }
259     }
260     else if ( p == m_pCTLOptions.get() )
261     {
262         // for all documents: set digit language for printer, recalc output factor, update row heights
263         SfxObjectShell* pObjSh = SfxObjectShell::GetFirst();
264         while ( pObjSh )
265         {
266             if ( dynamic_cast<const ScDocShell *>(pObjSh) != nullptr )
267             {
268                 ScDocShell* pDocSh = static_cast<ScDocShell*>(pObjSh);
269                 OutputDevice* pPrinter = pDocSh->GetPrinter();
270                 if ( pPrinter )
271                     pPrinter->SetDigitLanguage( GetOptDigitLanguage() );
272 
273                 pDocSh->CalcOutputFactor();
274 
275                 SCTAB nTabCount = pDocSh->GetDocument().GetTableCount();
276                 for (SCTAB nTab=0; nTab<nTabCount; nTab++)
277                     pDocSh->AdjustRowHeight( 0, MAXROW, nTab );
278             }
279             pObjSh = SfxObjectShell::GetNext( *pObjSh );
280         }
281 
282         // for all views (table and preview): update digit language
283         SfxViewShell* pSh = SfxViewShell::GetFirst();
284         while ( pSh )
285         {
286             if (ScTabViewShell* pViewSh = dynamic_cast<ScTabViewShell*>(pSh))
287             {
288                 // set ref-device for EditEngine (re-evaluates digit settings)
289                 ScInputHandler* pHdl = GetInputHdl(pViewSh);
290                 if (pHdl)
291                     pHdl->UpdateRefDevice();
292 
293                 pViewSh->DigitLanguageChanged();
294                 pViewSh->PaintGrid();
295             }
296             else if (ScPreviewShell* pPreviewSh = dynamic_cast<ScPreviewShell*>(pSh))
297             {
298                 ScPreview* pPreview = pPreviewSh->GetPreview();
299 
300                 pPreview->SetDigitLanguage( GetOptDigitLanguage() );
301                 pPreview->Invalidate();
302             }
303 
304             pSh = SfxViewShell::GetNext( *pSh );
305         }
306     }
307 }
308 
309 void ScModule::Notify( SfxBroadcaster&, const SfxHint& rHint )
310 {
311     if ( rHint.GetId() == SfxHintId::Deinitializing )
312     {
313         // ConfigItems must be removed before ConfigManager
314         DeleteCfg();
315     }
316 }
317 
318 void ScModule::DeleteCfg()
319 {
320     m_pViewCfg.reset(); // Saving happens automatically before Exit()
321     m_pDocCfg.reset();
322     m_pAppCfg.reset();
323     m_pDefaultsCfg.reset();
324     m_pFormulaCfg.reset();
325     m_pInputCfg.reset();
326     m_pPrintCfg.reset();
327     m_pNavipiCfg.reset();
328     m_pAddInCfg.reset();
329 
330     if ( m_pColorConfig )
331     {
332         m_pColorConfig->RemoveListener(this);
333         m_pColorConfig.reset();
334     }
335     if ( m_pAccessOptions )
336     {
337         m_pAccessOptions->RemoveListener(this);
338         m_pAccessOptions.reset();
339     }
340     if ( m_pCTLOptions )
341     {
342         m_pCTLOptions->RemoveListener(this);
343         m_pCTLOptions.reset();
344     }
345     m_pUserOptions.reset();
346 }
347 
348 // Moved here from the App
349 
350 void ScModule::Execute( SfxRequest& rReq )
351 {
352     SfxViewFrame* pViewFrm = SfxViewFrame::Current();
353     SfxBindings* pBindings = pViewFrm ? &pViewFrm->GetBindings() : nullptr;
354 
355     const SfxItemSet*   pReqArgs    = rReq.GetArgs();
356     sal_uInt16              nSlot       = rReq.GetSlot();
357 
358     switch ( nSlot )
359     {
360         case SID_CHOOSE_DESIGN:
361             SfxApplication::CallAppBasic( "Template.Samples.ShowStyles" );
362             break;
363         case SID_EURO_CONVERTER:
364             SfxApplication::CallAppBasic( "Euro.ConvertRun.Main" );
365             break;
366         case SID_AUTOSPELL_CHECK:
367             {
368                 bool bSet;
369                 const SfxPoolItem* pItem;
370                 if ( pReqArgs && SfxItemState::SET == pReqArgs->GetItemState( nSlot, true, &pItem ) )
371                     bSet = static_cast<const SfxBoolItem*>(pItem)->GetValue();
372                 else
373                 {   // Toggle
374                     ScDocShell* pDocSh = dynamic_cast<ScDocShell*>( SfxObjectShell::Current() );
375                     if ( pDocSh )
376                         bSet = !pDocSh->GetDocument().GetDocOptions().IsAutoSpell();
377                     else
378                         bSet = !GetDocOptions().IsAutoSpell();
379                 }
380 
381                 SfxItemSet aSet( GetPool(), svl::Items<SID_AUTOSPELL_CHECK, SID_AUTOSPELL_CHECK>{} );
382                 aSet.Put( SfxBoolItem( SID_AUTOSPELL_CHECK, bSet ) );
383                 ModifyOptions( aSet );
384                 rReq.Done();
385             }
386             break;
387 
388         case SID_ATTR_METRIC:
389             {
390                 const SfxPoolItem* pItem;
391                 if ( pReqArgs && SfxItemState::SET == pReqArgs->GetItemState( nSlot, true, &pItem ) )
392                 {
393                     FieldUnit eUnit = static_cast<FieldUnit>(static_cast<const SfxUInt16Item*>(pItem)->GetValue());
394                     switch( eUnit )
395                     {
396                         case FUNIT_MM:      // Just the units that are also in the dialog
397                         case FUNIT_CM:
398                         case FUNIT_INCH:
399                         case FUNIT_PICA:
400                         case FUNIT_POINT:
401                             {
402                                 PutItem( *pItem );
403                                 ScAppOptions aNewOpts( GetAppOptions() );
404                                 aNewOpts.SetAppMetric( eUnit );
405                                 SetAppOptions( aNewOpts );
406                                 rReq.Done();
407                             }
408                             break;
409                         default:
410                         {
411                             // added to avoid warnings
412                         }
413                     }
414                 }
415             }
416             break;
417 
418         case FID_AUTOCOMPLETE:
419             {
420                 ScAppOptions aNewOpts( GetAppOptions() );
421                 bool bNew = !aNewOpts.GetAutoComplete();
422                 aNewOpts.SetAutoComplete( bNew );
423                 SetAppOptions( aNewOpts );
424                 ScInputHandler::SetAutoComplete( bNew );
425                 if (pBindings)
426                     pBindings->Invalidate( FID_AUTOCOMPLETE );
427                 rReq.Done();
428             }
429             break;
430 
431         case SID_DETECTIVE_AUTO:
432             {
433                 ScAppOptions aNewOpts( GetAppOptions() );
434                 bool bNew = !aNewOpts.GetDetectiveAuto();
435                 const SfxBoolItem* pAuto = rReq.GetArg<SfxBoolItem>(SID_DETECTIVE_AUTO);
436                 if ( pAuto )
437                     bNew = pAuto->GetValue();
438 
439                 aNewOpts.SetDetectiveAuto( bNew );
440                 SetAppOptions( aNewOpts );
441                 if (pBindings)
442                     pBindings->Invalidate( SID_DETECTIVE_AUTO );
443                 rReq.AppendItem( SfxBoolItem( SID_DETECTIVE_AUTO, bNew ) );
444                 rReq.Done();
445             }
446             break;
447 
448         case SID_PSZ_FUNCTION:
449             if (pReqArgs)
450             {
451                 auto const & p = pReqArgs->Get(SID_PSZ_FUNCTION);
452                 OSL_ENSURE(dynamic_cast<const SfxUInt32Item*>(&p) !=  nullptr,"wrong Parameter");
453                 const SfxUInt32Item& rItem = static_cast<const SfxUInt32Item&>(p);
454 
455                 ScAppOptions aNewOpts( GetAppOptions() );
456                 aNewOpts.SetStatusFunc( rItem.GetValue() );
457                 SetAppOptions( aNewOpts );
458 
459                 if (pBindings)
460                 {
461                     pBindings->Invalidate( SID_TABLE_CELL );
462                     pBindings->Update( SID_TABLE_CELL ); // Immediately
463 
464                     pBindings->Invalidate( SID_PSZ_FUNCTION );
465                     pBindings->Update( SID_PSZ_FUNCTION );
466                     // If the menu is opened again immediately
467                 }
468             }
469             break;
470 
471         case SID_ATTR_LANGUAGE:
472         case SID_ATTR_CHAR_CJK_LANGUAGE:
473         case SID_ATTR_CHAR_CTL_LANGUAGE:
474             {
475                 const SfxPoolItem* pItem;
476                 if ( pReqArgs && SfxItemState::SET == pReqArgs->GetItemState( GetPool().GetWhich(nSlot), true, &pItem ) )
477                 {
478                     ScDocShell* pDocSh = dynamic_cast<ScDocShell*>( SfxObjectShell::Current() );
479                     if ( pDocSh )
480                     {
481                         ScDocument& rDoc = pDocSh->GetDocument();
482                         LanguageType eNewLang = static_cast<const SvxLanguageItem*>(pItem)->GetLanguage();
483                         LanguageType eLatin, eCjk, eCtl;
484                         rDoc.GetLanguage( eLatin, eCjk, eCtl );
485                         LanguageType eOld = ( nSlot == SID_ATTR_CHAR_CJK_LANGUAGE ) ? eCjk :
486                                             ( ( nSlot == SID_ATTR_CHAR_CTL_LANGUAGE ) ? eCtl : eLatin );
487                         if ( eNewLang != eOld )
488                         {
489                             if ( nSlot == SID_ATTR_CHAR_CJK_LANGUAGE )
490                                 eCjk = eNewLang;
491                             else if ( nSlot == SID_ATTR_CHAR_CTL_LANGUAGE )
492                                 eCtl = eNewLang;
493                             else
494                                 eLatin = eNewLang;
495 
496                             rDoc.SetLanguage( eLatin, eCjk, eCtl );
497 
498                             ScInputHandler* pInputHandler = GetInputHdl();
499                             if ( pInputHandler )
500                                 pInputHandler->UpdateSpellSettings(); // EditEngine flags
501                             ScTabViewShell* pViewSh = dynamic_cast<ScTabViewShell*>( SfxViewShell::Current() );
502                             if ( pViewSh )
503                                 pViewSh->UpdateDrawTextOutliner(); // EditEngine flags
504 
505                             pDocSh->SetDocumentModified();
506                         }
507                     }
508                 }
509             }
510             break;
511 
512         case FID_FOCUS_POSWND:
513             {
514                 ScInputHandler* pHdl = GetInputHdl();
515                 if (pHdl)
516                 {
517                     ScInputWindow* pWin = pHdl->GetInputWindow();
518                     if (pWin)
519                         pWin->PosGrabFocus();
520                 }
521                 rReq.Done();
522             }
523             break;
524 
525         case SID_OPEN_XML_FILTERSETTINGS:
526         {
527             try
528             {
529                 css::uno::Reference < css::ui::dialogs::XExecutableDialog > xDialog = css::ui::dialogs::XSLTFilterDialog::create( ::comphelper::getProcessComponentContext());
530                 xDialog->execute();
531             }
532             catch( css::uno::RuntimeException& )
533             {
534                 DBG_UNHANDLED_EXCEPTION("sc.ui");
535             }
536         }
537         break;
538 
539         default:
540             OSL_FAIL( "ScApplication: Unknown Message." );
541             break;
542     }
543 }
544 
545 void ScModule::GetState( SfxItemSet& rSet )
546 {
547     ScDocShell* pDocSh = dynamic_cast<ScDocShell*>( SfxObjectShell::Current() );
548     bool bTabView = pDocSh && (pDocSh->GetBestViewShell() != nullptr);
549 
550     SfxWhichIter aIter(rSet);
551     for (sal_uInt16 nWhich = aIter.FirstWhich(); nWhich; nWhich = aIter.NextWhich())
552     {
553         if (!bTabView)
554         {
555             // Not in the normal calc view shell (most likely in preview shell). Disable all actions.
556             rSet.DisableItem(nWhich);
557             continue;
558         }
559 
560         switch ( nWhich )
561         {
562             case FID_AUTOCOMPLETE:
563                 rSet.Put( SfxBoolItem( nWhich, GetAppOptions().GetAutoComplete() ) );
564                 break;
565             case SID_DETECTIVE_AUTO:
566                 rSet.Put( SfxBoolItem( nWhich, GetAppOptions().GetDetectiveAuto() ) );
567                 break;
568             case SID_PSZ_FUNCTION:
569                 rSet.Put( SfxUInt32Item( nWhich, GetAppOptions().GetStatusFunc() ) );
570                 break;
571             case SID_ATTR_METRIC:
572                 rSet.Put( SfxUInt16Item( nWhich, sal::static_int_cast<sal_uInt16>(GetAppOptions().GetAppMetric()) ) );
573                 break;
574             case SID_AUTOSPELL_CHECK:
575                 rSet.Put( SfxBoolItem( nWhich, pDocSh->GetDocument().GetDocOptions().IsAutoSpell()) );
576                 break;
577             case SID_ATTR_LANGUAGE:
578             case ATTR_CJK_FONT_LANGUAGE:        // WID for SID_ATTR_CHAR_CJK_LANGUAGE
579             case ATTR_CTL_FONT_LANGUAGE:        // WID for SID_ATTR_CHAR_CTL_LANGUAGE
580                 {
581                     LanguageType eLatin, eCjk, eCtl;
582                     pDocSh->GetDocument().GetLanguage( eLatin, eCjk, eCtl );
583                     LanguageType eLang = ( nWhich == ATTR_CJK_FONT_LANGUAGE ) ? eCjk :
584                                         ( ( nWhich == ATTR_CTL_FONT_LANGUAGE ) ? eCtl : eLatin );
585                     rSet.Put( SvxLanguageItem( eLang, nWhich ) );
586                 }
587                 break;
588         }
589     }
590 }
591 
592 void ScModule::HideDisabledSlots( SfxItemSet& rSet )
593 {
594     if( SfxViewFrame* pViewFrm = SfxViewFrame::Current() )
595     {
596         SfxBindings& rBindings = pViewFrm->GetBindings();
597         SfxWhichIter aIter( rSet );
598         for( sal_uInt16 nWhich = aIter.FirstWhich(); nWhich != 0; nWhich = aIter.NextWhich() )
599         {
600             ScViewUtil::HideDisabledSlot( rSet, rBindings, nWhich );
601             // always disable the slots
602             rSet.DisableItem( nWhich );
603         }
604     }
605 }
606 
607 void ScModule::ResetDragObject()
608 {
609     m_pDragData->pCellTransfer = nullptr;
610     m_pDragData->pDrawTransfer = nullptr;
611     m_pDragData->pJumpLocalDoc = nullptr;
612     m_pDragData->aLinkDoc.clear();
613     m_pDragData->aLinkTable.clear();
614     m_pDragData->aLinkArea.clear();
615     m_pDragData->aJumpTarget.clear();
616     m_pDragData->aJumpText.clear();
617 }
618 
619 void ScModule::SetDragObject( ScTransferObj* pCellObj, ScDrawTransferObj* pDrawObj )
620 {
621     ResetDragObject();
622     m_pDragData->pCellTransfer = pCellObj;
623     m_pDragData->pDrawTransfer = pDrawObj;
624 }
625 
626 void ScModule::SetDragLink(
627     const OUString& rDoc, const OUString& rTab, const OUString& rArea )
628 {
629     ResetDragObject();
630     m_pDragData->aLinkDoc   = rDoc;
631     m_pDragData->aLinkTable = rTab;
632     m_pDragData->aLinkArea  = rArea;
633 }
634 
635 void ScModule::SetDragJump(
636     ScDocument* pLocalDoc, const OUString& rTarget, const OUString& rText )
637 {
638     ResetDragObject();
639 
640     m_pDragData->pJumpLocalDoc = pLocalDoc;
641     m_pDragData->aJumpTarget = rTarget;
642     m_pDragData->aJumpText = rText;
643 }
644 
645 
646 void ScModule::SetSelectionTransfer( ScSelectionTransferObj* pNew )
647 {
648     m_pSelTransfer = pNew;
649 }
650 
651 void ScModule::InitFormEditData()
652 {
653     m_pFormEditData.reset( new ScFormEditData );
654 }
655 
656 void ScModule::ClearFormEditData()
657 {
658     m_pFormEditData.reset();
659 }
660 
661 void ScModule::SetViewOptions( const ScViewOptions& rOpt )
662 {
663     if ( !m_pViewCfg )
664         m_pViewCfg.reset(new ScViewCfg);
665 
666     m_pViewCfg->SetOptions( rOpt );
667 }
668 
669 const ScViewOptions& ScModule::GetViewOptions()
670 {
671     if ( !m_pViewCfg )
672         m_pViewCfg.reset( new ScViewCfg );
673 
674     return *m_pViewCfg;
675 }
676 
677 void ScModule::SetDocOptions( const ScDocOptions& rOpt )
678 {
679     if ( !m_pDocCfg )
680         m_pDocCfg.reset( new ScDocCfg );
681 
682     m_pDocCfg->SetOptions( rOpt );
683 }
684 
685 const ScDocOptions& ScModule::GetDocOptions()
686 {
687     if ( !m_pDocCfg )
688         m_pDocCfg.reset( new ScDocCfg );
689 
690     return *m_pDocCfg;
691 }
692 
693 #ifndef LRU_MAX
694 #define LRU_MAX 10
695 #endif
696 
697 void ScModule::InsertEntryToLRUList(sal_uInt16 nFIndex)
698 {
699     if(nFIndex != 0)
700     {
701         const ScAppOptions& rAppOpt = GetAppOptions();
702         sal_uInt16 nLRUFuncCount = std::min( rAppOpt.GetLRUFuncListCount(), sal_uInt16(LRU_MAX) );
703         sal_uInt16* pLRUListIds = rAppOpt.GetLRUFuncList();
704 
705         sal_uInt16  aIdxList[LRU_MAX];
706         sal_uInt16  n = 0;
707         bool    bFound = false;
708 
709         while ((n < LRU_MAX) && n<nLRUFuncCount)                        // Iterate through old list
710         {
711             if (!bFound && (pLRUListIds[n]== nFIndex))
712                 bFound = true;                                          // First hit!
713             else if (bFound)
714                 aIdxList[n  ] = pLRUListIds[n];                         // Copy after hit
715             else if ((n+1) < LRU_MAX)
716                 aIdxList[n+1] = pLRUListIds[n];                         // Move before hit
717             n++;
718         }
719         if (!bFound && (n < LRU_MAX))                                   // Entry not found?
720             n++;                                                        // One more
721         aIdxList[0] = nFIndex;                                          // Current on Top
722 
723         ScAppOptions aNewOpts(rAppOpt);                                 // Let App know
724         aNewOpts.SetLRUFuncList(aIdxList, n);
725         SetAppOptions(aNewOpts);
726     }
727 }
728 
729 void ScModule::SetAppOptions( const ScAppOptions& rOpt )
730 {
731     if ( !m_pAppCfg )
732         m_pAppCfg.reset( new ScAppCfg );
733 
734     m_pAppCfg->SetOptions( rOpt );
735 }
736 
737 void global_InitAppOptions()
738 {
739     SC_MOD()->GetAppOptions();
740 }
741 
742 const ScAppOptions& ScModule::GetAppOptions()
743 {
744     if ( !m_pAppCfg )
745         m_pAppCfg.reset( new ScAppCfg );
746 
747     return *m_pAppCfg;
748 }
749 
750 void ScModule::SetDefaultsOptions( const ScDefaultsOptions& rOpt )
751 {
752     if ( !m_pDefaultsCfg )
753         m_pDefaultsCfg.reset( new ScDefaultsCfg );
754 
755     m_pDefaultsCfg->SetOptions( rOpt );
756 }
757 
758 const ScDefaultsOptions& ScModule::GetDefaultsOptions()
759 {
760     if ( !m_pDefaultsCfg )
761         m_pDefaultsCfg.reset( new ScDefaultsCfg );
762 
763     return *m_pDefaultsCfg;
764 }
765 
766 void ScModule::SetFormulaOptions( const ScFormulaOptions& rOpt )
767 {
768     if ( !m_pFormulaCfg )
769         m_pFormulaCfg.reset( new ScFormulaCfg );
770 
771     m_pFormulaCfg->SetOptions( rOpt );
772 }
773 
774 const ScFormulaOptions& ScModule::GetFormulaOptions()
775 {
776     if ( !m_pFormulaCfg )
777         m_pFormulaCfg.reset( new ScFormulaCfg );
778 
779     return *m_pFormulaCfg;
780 }
781 
782 void ScModule::SetInputOptions( const ScInputOptions& rOpt )
783 {
784     if ( !m_pInputCfg )
785         m_pInputCfg.reset( new ScInputCfg );
786 
787     m_pInputCfg->SetOptions( rOpt );
788 }
789 
790 const ScInputOptions& ScModule::GetInputOptions()
791 {
792     if ( !m_pInputCfg )
793         m_pInputCfg.reset( new ScInputCfg );
794 
795     return *m_pInputCfg;
796 }
797 
798 void ScModule::SetPrintOptions( const ScPrintOptions& rOpt )
799 {
800     if ( !m_pPrintCfg )
801         m_pPrintCfg.reset( new ScPrintCfg );
802 
803     m_pPrintCfg->SetOptions( rOpt );
804 }
805 
806 const ScPrintOptions& ScModule::GetPrintOptions()
807 {
808     if ( !m_pPrintCfg )
809         m_pPrintCfg.reset( new ScPrintCfg );
810 
811     return *m_pPrintCfg;
812 }
813 
814 ScNavipiCfg& ScModule::GetNavipiCfg()
815 {
816     if ( !m_pNavipiCfg )
817         m_pNavipiCfg.reset( new ScNavipiCfg );
818 
819     return *m_pNavipiCfg;
820 }
821 
822 ScAddInCfg& ScModule::GetAddInCfg()
823 {
824     if ( !m_pAddInCfg )
825         m_pAddInCfg.reset( new ScAddInCfg );
826 
827     return *m_pAddInCfg;
828 }
829 
830 svtools::ColorConfig& ScModule::GetColorConfig()
831 {
832     if ( !m_pColorConfig )
833     {
834         m_pColorConfig.reset( new svtools::ColorConfig );
835         m_pColorConfig->AddListener(this);
836     }
837 
838     return *m_pColorConfig;
839 }
840 
841 SvtAccessibilityOptions& ScModule::GetAccessOptions()
842 {
843     if ( !m_pAccessOptions )
844     {
845         m_pAccessOptions.reset( new SvtAccessibilityOptions );
846         m_pAccessOptions->AddListener(this);
847     }
848 
849     return *m_pAccessOptions;
850 }
851 
852 SvtCTLOptions& ScModule::GetCTLOptions()
853 {
854     if ( !m_pCTLOptions )
855     {
856         m_pCTLOptions.reset( new SvtCTLOptions );
857         m_pCTLOptions->AddListener(this);
858     }
859 
860     return *m_pCTLOptions;
861 }
862 
863 SvtUserOptions&  ScModule::GetUserOptions()
864 {
865     if( !m_pUserOptions )
866     {
867         m_pUserOptions.reset( new SvtUserOptions );
868     }
869     return *m_pUserOptions;
870 }
871 
872 LanguageType ScModule::GetOptDigitLanguage()
873 {
874     SvtCTLOptions::TextNumerals eNumerals = GetCTLOptions().GetCTLTextNumerals();
875     return ( eNumerals == SvtCTLOptions::NUMERALS_ARABIC ) ? LANGUAGE_ENGLISH_US :
876            ( eNumerals == SvtCTLOptions::NUMERALS_HINDI)   ? LANGUAGE_ARABIC_SAUDI_ARABIA :
877                                                              LANGUAGE_SYSTEM;
878 }
879 
880 /**
881  * Options
882  *
883  * Items from Calc options dialog and SID_AUTOSPELL_CHECK
884  */
885 void ScModule::ModifyOptions( const SfxItemSet& rOptSet )
886 {
887     LanguageType nOldSpellLang, nOldCjkLang, nOldCtlLang;
888     bool bOldAutoSpell;
889     GetSpellSettings( nOldSpellLang, nOldCjkLang, nOldCtlLang, bOldAutoSpell );
890 
891     if (!m_pAppCfg)
892         GetAppOptions();
893     OSL_ENSURE( m_pAppCfg, "AppOptions not initialised :-(" );
894 
895     if (!m_pInputCfg)
896         GetInputOptions();
897     OSL_ENSURE( m_pInputCfg, "InputOptions not initialised :-(" );
898 
899     SfxViewFrame* pViewFrm = SfxViewFrame::Current();
900     SfxBindings* pBindings = pViewFrm ? &pViewFrm->GetBindings() : nullptr;
901 
902     ScTabViewShell*         pViewSh = dynamic_cast<ScTabViewShell*>( SfxViewShell::Current() );
903     ScDocShell*             pDocSh  = dynamic_cast<ScDocShell*>( SfxObjectShell::Current() );
904     ScDocument*             pDoc    = pDocSh ? &pDocSh->GetDocument() : nullptr;
905     const SfxPoolItem*      pItem   = nullptr;
906     bool bRepaint = false;
907     bool bUpdateMarks = false;
908     bool bUpdateRefDev = false;
909     bool bCalcAll = false;
910     bool bSaveAppOptions = false;
911     bool bSaveInputOptions = false;
912     bool bCompileErrorCells = false;
913 
914     //  SfxGetpApp()->SetOptions( rOptSet );
915 
916     // No more linguistics
917     if (rOptSet.HasItem(SID_ATTR_METRIC, &pItem))
918     {
919         PutItem( *pItem );
920         m_pAppCfg->SetAppMetric( static_cast<FieldUnit>(static_cast<const SfxUInt16Item*>(pItem)->GetValue()) );
921         bSaveAppOptions = true;
922     }
923 
924     if (rOptSet.HasItem(SCITEM_USERLIST, &pItem))
925     {
926         ScGlobal::SetUserList( static_cast<const ScUserListItem*>(pItem)->GetUserList() );
927         bSaveAppOptions = true;
928     }
929 
930     if (rOptSet.HasItem(SID_SC_OPT_SYNCZOOM, &pItem))
931     {
932         m_pAppCfg->SetSynchronizeZoom( static_cast<const SfxBoolItem*>(pItem)->GetValue() );
933         bSaveAppOptions = true;
934     }
935 
936     if (rOptSet.HasItem(SID_SC_OPT_KEY_BINDING_COMPAT, &pItem))
937     {
938         sal_uInt16 nVal = static_cast<const SfxUInt16Item*>(pItem)->GetValue();
939         ScOptionsUtil::KeyBindingType eOld = m_pAppCfg->GetKeyBindingType();
940         ScOptionsUtil::KeyBindingType eNew = static_cast<ScOptionsUtil::KeyBindingType>(nVal);
941         if (eOld != eNew)
942         {
943             m_pAppCfg->SetKeyBindingType(eNew);
944             bSaveAppOptions = true;
945             ScDocShell::ResetKeyBindings(eNew);
946         }
947     }
948 
949     // DefaultsOptions
950     if (rOptSet.HasItem(SID_SCDEFAULTSOPTIONS, &pItem))
951     {
952         const ScDefaultsOptions& rOpt = static_cast<const ScTpDefaultsItem*>(pItem)->GetDefaultsOptions();
953         SetDefaultsOptions( rOpt );
954     }
955 
956     // FormulaOptions
957     if (rOptSet.HasItem(SID_SCFORMULAOPTIONS, &pItem))
958     {
959         const ScFormulaOptions& rOpt = static_cast<const ScTpFormulaItem*>(pItem)->GetFormulaOptions();
960 
961         if (!m_pFormulaCfg || (*m_pFormulaCfg != rOpt))
962             // Formula options have changed. Repaint the column headers.
963             bRepaint = true;
964 
965         if (m_pFormulaCfg && m_pFormulaCfg->GetUseEnglishFuncName() != rOpt.GetUseEnglishFuncName())
966         {
967             // Re-compile formula cells with error as the error may have been
968             // caused by unresolved function names.
969             bCompileErrorCells = true;
970         }
971 
972         // Recalc for interpreter options changes.
973         if (m_pFormulaCfg && m_pFormulaCfg->GetCalcConfig() != rOpt.GetCalcConfig())
974             bCalcAll = true;
975 
976         if ( pDocSh )
977         {
978             pDocSh->SetFormulaOptions( rOpt );
979             pDocSh->SetDocumentModified();
980         }
981 
982         // ScDocShell::SetFormulaOptions() may check for changed settings, so
983         // set the new options here after that has been called.
984         if (!bCalcAll || rOpt.GetWriteCalcConfig())
985         {
986             // CalcConfig is new, didn't change or is global, simply set all.
987             SetFormulaOptions( rOpt );
988         }
989         else
990         {
991             // If "only for current document" was checked, reset those affected
992             // by that setting to previous values.
993             ScFormulaOptions aNewOpt( rOpt);
994             aNewOpt.GetCalcConfig().MergeDocumentSpecific( m_pFormulaCfg->GetCalcConfig());
995             SetFormulaOptions( aNewOpt);
996         }
997     }
998 
999     // ViewOptions
1000     if (rOptSet.HasItem(SID_SCVIEWOPTIONS, &pItem))
1001     {
1002         const ScViewOptions& rNewOpt = static_cast<const ScTpViewItem*>(pItem)->GetViewOptions();
1003 
1004         if ( pViewSh )
1005         {
1006             ScViewData&             rViewData = pViewSh->GetViewData();
1007             const ScViewOptions&    rOldOpt   = rViewData.GetOptions();
1008 
1009             bool bAnchorList = ( rOldOpt.GetOption( VOPT_ANCHOR ) !=
1010                                  rNewOpt.GetOption( VOPT_ANCHOR ) );
1011 
1012             if ( rOldOpt != rNewOpt )
1013             {
1014                 rViewData.SetOptions( rNewOpt ); // Changes rOldOpt
1015                 rViewData.GetDocument()->SetViewOptions( rNewOpt );
1016                 if (pDocSh)
1017                     pDocSh->SetDocumentModified();
1018                 bRepaint = true;
1019             }
1020             if ( bAnchorList )
1021                 pViewSh->UpdateAnchorHandles();
1022         }
1023         SetViewOptions( rNewOpt );
1024         if (pBindings)
1025         {
1026             pBindings->Invalidate(SID_HELPLINES_MOVE);
1027         }
1028     }
1029 
1030     // GridOptions
1031     // Evaluate after ViewOptions, as GridOptions is a member of ViewOptions
1032     if ( rOptSet.HasItem(SID_ATTR_GRID_OPTIONS,&pItem) )
1033     {
1034         ScGridOptions aNewGridOpt( static_cast<const SvxGridItem&>(*pItem ));
1035 
1036         if ( pViewSh )
1037         {
1038             ScViewData&          rViewData = pViewSh->GetViewData();
1039             ScViewOptions        aNewViewOpt( rViewData.GetOptions() );
1040             const ScGridOptions& rOldGridOpt = aNewViewOpt.GetGridOptions();
1041 
1042             if ( rOldGridOpt != aNewGridOpt )
1043             {
1044                 aNewViewOpt.SetGridOptions( aNewGridOpt );
1045                 rViewData.SetOptions( aNewViewOpt );
1046                 rViewData.GetDocument()->SetViewOptions( aNewViewOpt );
1047                 pDocSh->SetDocumentModified();
1048                 bRepaint = true;
1049             }
1050         }
1051         ScViewOptions aNewViewOpt ( GetViewOptions() );
1052         aNewViewOpt.SetGridOptions( aNewGridOpt );
1053         SetViewOptions( aNewViewOpt );
1054         if (pBindings)
1055         {
1056             pBindings->Invalidate(SID_GRID_VISIBLE);
1057             pBindings->Invalidate(SID_GRID_USE);
1058         }
1059     }
1060 
1061     // DocOptions
1062     if ( rOptSet.HasItem(SID_SCDOCOPTIONS,&pItem) )
1063     {
1064         const ScDocOptions& rNewOpt = static_cast<const ScTpCalcItem*>(pItem)->GetDocOptions();
1065 
1066         if ( pDoc )
1067         {
1068             const ScDocOptions& rOldOpt = pDoc->GetDocOptions();
1069 
1070             bRepaint = ( bRepaint || ( rOldOpt != rNewOpt )   );
1071             bCalcAll =   bRepaint &&
1072                          (  rOldOpt.IsIter()       != rNewOpt.IsIter()
1073                          || rOldOpt.GetIterCount() != rNewOpt.GetIterCount()
1074                          || rOldOpt.GetIterEps()   != rNewOpt.GetIterEps()
1075                          || rOldOpt.IsIgnoreCase() != rNewOpt.IsIgnoreCase()
1076                          || rOldOpt.IsCalcAsShown() != rNewOpt.IsCalcAsShown()
1077                          || (rNewOpt.IsCalcAsShown() &&
1078                             rOldOpt.GetStdPrecision() != rNewOpt.GetStdPrecision())
1079                          || rOldOpt.IsMatchWholeCell() != rNewOpt.IsMatchWholeCell()
1080                          || rOldOpt.GetYear2000()   != rNewOpt.GetYear2000()
1081                          || rOldOpt.IsFormulaRegexEnabled() != rNewOpt.IsFormulaRegexEnabled()
1082                          || rOldOpt.IsFormulaWildcardsEnabled() != rNewOpt.IsFormulaWildcardsEnabled()
1083                          );
1084             pDoc->SetDocOptions( rNewOpt );
1085             pDocSh->SetDocumentModified();
1086         }
1087         SetDocOptions( rNewOpt );
1088     }
1089 
1090     // Set TabDistance after the actual DocOptions
1091     if ( rOptSet.HasItem(SID_ATTR_DEFTABSTOP,&pItem) )
1092     {
1093         sal_uInt16 nTabDist = static_cast<const SfxUInt16Item*>(pItem)->GetValue();
1094         ScDocOptions aOpt(GetDocOptions());
1095         aOpt.SetTabDistance(nTabDist);
1096         SetDocOptions( aOpt );
1097 
1098         if ( pDoc )
1099         {
1100             ScDocOptions aDocOpt(pDoc->GetDocOptions());
1101             aDocOpt.SetTabDistance(nTabDist);
1102             pDoc->SetDocOptions( aDocOpt );
1103             pDocSh->SetDocumentModified();
1104             if(pDoc->GetDrawLayer())
1105                 pDoc->GetDrawLayer()->SetDefaultTabulator(nTabDist);
1106         }
1107     }
1108 
1109     // AutoSpell after the DocOptions (due to being a member)
1110     if ( rOptSet.HasItem(SID_AUTOSPELL_CHECK,&pItem) ) // At DocOptions
1111     {
1112         bool bDoAutoSpell = static_cast<const SfxBoolItem*>(pItem)->GetValue();
1113 
1114         if (pDoc)
1115         {
1116             ScDocOptions aNewOpt = pDoc->GetDocOptions();
1117             if ( aNewOpt.IsAutoSpell() != bDoAutoSpell )
1118             {
1119                 aNewOpt.SetAutoSpell( bDoAutoSpell );
1120                 pDoc->SetDocOptions( aNewOpt );
1121 
1122                 if (pViewSh)
1123                     pViewSh->EnableAutoSpell(bDoAutoSpell);
1124 
1125                 bRepaint = true;            // Because HideAutoSpell might be invalid
1126                                             //TODO: Paint all Views?
1127             }
1128         }
1129 
1130         if ( bOldAutoSpell != bDoAutoSpell )
1131             SetAutoSpellProperty( bDoAutoSpell );
1132         if ( pDocSh )
1133             pDocSh->PostPaintGridAll();                     // Due to marks
1134         ScInputHandler* pInputHandler = GetInputHdl();
1135         if ( pInputHandler )
1136             pInputHandler->UpdateSpellSettings();           // EditEngine flags
1137         if ( pViewSh )
1138             pViewSh->UpdateDrawTextOutliner();              // EditEngine flags
1139 
1140         if (pBindings)
1141             pBindings->Invalidate( SID_AUTOSPELL_CHECK );
1142     }
1143 
1144     // InputOptions
1145     if ( rOptSet.HasItem(SID_SC_INPUT_SELECTIONPOS,&pItem) )
1146     {
1147         m_pInputCfg->SetMoveDir( static_cast<const SfxUInt16Item*>(pItem)->GetValue() );
1148         bSaveInputOptions = true;
1149     }
1150     if ( rOptSet.HasItem(SID_SC_INPUT_SELECTION,&pItem) )
1151     {
1152         m_pInputCfg->SetMoveSelection( static_cast<const SfxBoolItem*>(pItem)->GetValue() );
1153         bSaveInputOptions = true;
1154     }
1155     if ( rOptSet.HasItem(SID_SC_INPUT_EDITMODE,&pItem) )
1156     {
1157         m_pInputCfg->SetEnterEdit( static_cast<const SfxBoolItem*>(pItem)->GetValue() );
1158         bSaveInputOptions = true;
1159     }
1160     if ( rOptSet.HasItem(SID_SC_INPUT_FMT_EXPAND,&pItem) )
1161     {
1162         m_pInputCfg->SetExtendFormat( static_cast<const SfxBoolItem*>(pItem)->GetValue() );
1163         bSaveInputOptions = true;
1164     }
1165     if ( rOptSet.HasItem(SID_SC_INPUT_RANGEFINDER,&pItem) )
1166     {
1167         m_pInputCfg->SetRangeFinder( static_cast<const SfxBoolItem*>(pItem)->GetValue() );
1168         bSaveInputOptions = true;
1169     }
1170     if ( rOptSet.HasItem(SID_SC_INPUT_REF_EXPAND,&pItem) )
1171     {
1172         m_pInputCfg->SetExpandRefs( static_cast<const SfxBoolItem*>(pItem)->GetValue() );
1173         bSaveInputOptions = true;
1174     }
1175     if (rOptSet.HasItem(SID_SC_OPT_SORT_REF_UPDATE, &pItem))
1176     {
1177         m_pInputCfg->SetSortRefUpdate(static_cast<const SfxBoolItem*>(pItem)->GetValue());
1178         bSaveInputOptions = true;
1179     }
1180 
1181     if ( rOptSet.HasItem(SID_SC_INPUT_MARK_HEADER,&pItem) )
1182     {
1183         m_pInputCfg->SetMarkHeader( static_cast<const SfxBoolItem*>(pItem)->GetValue() );
1184         bSaveInputOptions = true;
1185         bUpdateMarks = true;
1186     }
1187     if ( rOptSet.HasItem(SID_SC_INPUT_TEXTWYSIWYG,&pItem) )
1188     {
1189         bool bNew = static_cast<const SfxBoolItem*>(pItem)->GetValue();
1190         if ( bNew != m_pInputCfg->GetTextWysiwyg() )
1191         {
1192             m_pInputCfg->SetTextWysiwyg( bNew );
1193             bSaveInputOptions = true;
1194             bUpdateRefDev = true;
1195         }
1196     }
1197     if( rOptSet.HasItem( SID_SC_INPUT_REPLCELLSWARN, &pItem ) )
1198     {
1199         m_pInputCfg->SetReplaceCellsWarn( static_cast<const SfxBoolItem*>(pItem)->GetValue() );
1200         bSaveInputOptions = true;
1201     }
1202 
1203     if( rOptSet.HasItem( SID_SC_INPUT_LEGACY_CELL_SELECTION, &pItem ) )
1204     {
1205         m_pInputCfg->SetLegacyCellSelection( static_cast<const SfxBoolItem*>(pItem)->GetValue() );
1206         bSaveInputOptions = true;
1207     }
1208 
1209     // PrintOptions
1210     if ( rOptSet.HasItem(SID_SCPRINTOPTIONS,&pItem) )
1211     {
1212         const ScPrintOptions& rNewOpt = static_cast<const ScTpPrintItem*>(pItem)->GetPrintOptions();
1213         SetPrintOptions( rNewOpt );
1214 
1215         // broadcast causes all previews to recalc page numbers
1216         SfxGetpApp()->Broadcast( SfxHint( SfxHintId::ScPrintOptions ) );
1217     }
1218 
1219     if ( bSaveAppOptions )
1220         m_pAppCfg->OptionsChanged();
1221 
1222     if ( bSaveInputOptions )
1223         m_pInputCfg->OptionsChanged();
1224 
1225     // Kick off recalculation?
1226     if (pDoc && bCompileErrorCells)
1227     {
1228         // Re-compile cells with name error, and recalc if at least one cell
1229         // has been re-compiled.  In the future we may want to find a way to
1230         // recalc only those that are affected.
1231         if (pDoc->CompileErrorCells(FormulaError::NoName))
1232             bCalcAll = true;
1233     }
1234 
1235     if ( pDoc && bCalcAll )
1236     {
1237         WaitObject aWait( ScDocShell::GetActiveDialogParent() );
1238         pDoc->CalcAll();
1239         if ( pViewSh )
1240             pViewSh->UpdateCharts( true );
1241         else
1242             ScDBFunc::DoUpdateCharts( ScAddress(), pDoc, true );
1243         if (pBindings)
1244             pBindings->Invalidate( SID_ATTR_SIZE ); //SvxPosSize StatusControl Update
1245     }
1246 
1247     if ( pViewSh && bUpdateMarks )
1248         pViewSh->UpdateAutoFillMark();
1249 
1250     // Repaint View?
1251     if ( pViewSh && bRepaint )
1252     {
1253         pViewSh->UpdateFixPos();
1254         pViewSh->PaintGrid();
1255         pViewSh->PaintTop();
1256         pViewSh->PaintLeft();
1257         pViewSh->PaintExtras();
1258         pViewSh->InvalidateBorder();
1259         if (pBindings)
1260         {
1261             pBindings->Invalidate( FID_TOGGLEHEADERS ); // -> Checks in menu
1262             pBindings->Invalidate( FID_TOGGLESYNTAX );
1263         }
1264     }
1265 
1266     // update ref device (for all documents)
1267     if ( bUpdateRefDev )
1268     {
1269         // for all documents: recalc output factor, update row heights
1270         SfxObjectShell* pObjSh = SfxObjectShell::GetFirst();
1271         while ( pObjSh )
1272         {
1273             if ( dynamic_cast<const ScDocShell *>(pObjSh) != nullptr )
1274             {
1275                 ScDocShell* pOneDocSh = static_cast<ScDocShell*>(pObjSh);
1276                 pOneDocSh->CalcOutputFactor();
1277                 SCTAB nTabCount = pOneDocSh->GetDocument().GetTableCount();
1278                 for (SCTAB nTab=0; nTab<nTabCount; nTab++)
1279                     pOneDocSh->AdjustRowHeight( 0, MAXROW, nTab );
1280             }
1281             pObjSh = SfxObjectShell::GetNext( *pObjSh );
1282         }
1283 
1284         // for all (tab-) views:
1285         SfxViewShell* pSh = SfxViewShell::GetFirst( true, checkSfxViewShell<ScTabViewShell> );
1286         while ( pSh )
1287         {
1288             ScTabViewShell* pOneViewSh = static_cast<ScTabViewShell*>(pSh);
1289 
1290             // set ref-device for EditEngine
1291             ScInputHandler* pHdl = GetInputHdl(pOneViewSh);
1292             if (pHdl)
1293                 pHdl->UpdateRefDevice();
1294 
1295             // update view scale
1296             ScViewData& rViewData = pOneViewSh->GetViewData();
1297             pOneViewSh->SetZoom( rViewData.GetZoomX(), rViewData.GetZoomY(), false );
1298 
1299             // repaint
1300             pOneViewSh->PaintGrid();
1301             pOneViewSh->PaintTop();
1302             pOneViewSh->PaintLeft();
1303 
1304             pSh = SfxViewShell::GetNext( *pSh, true, checkSfxViewShell<ScTabViewShell> );
1305         }
1306     }
1307 }
1308 
1309 /**
1310  * Input-Handler
1311  */
1312 ScInputHandler* ScModule::GetInputHdl( ScTabViewShell* pViewSh, bool bUseRef )
1313 {
1314     if ( m_pRefInputHandler && bUseRef )
1315         return m_pRefInputHandler;
1316 
1317     ScInputHandler* pHdl = nullptr;
1318     if ( !pViewSh )
1319     {
1320         // in case a UIActive embedded object has no ViewShell (UNO component)
1321         // the own calc view shell will be set as current, but no handling should happen
1322         ScTabViewShell* pCurViewSh = dynamic_cast<ScTabViewShell*>( SfxViewShell::Current()  );
1323         if ( pCurViewSh && !pCurViewSh->GetUIActiveClient() )
1324             pViewSh = pCurViewSh;
1325     }
1326 
1327     if ( pViewSh )
1328         pHdl = pViewSh->GetInputHandler(); // Viewshell always has one, from now on
1329 
1330     // If no ViewShell passed or active, we can get NULL
1331     OSL_ENSURE( pHdl || !pViewSh, "GetInputHdl: no InputHandler found!" );
1332     return pHdl;
1333 }
1334 
1335 void ScModule::ViewShellChanged(bool bStopEditing /*=true*/)
1336 {
1337     ScInputHandler* pHdl   = GetInputHdl();
1338     ScTabViewShell* pShell = ScTabViewShell::GetActiveViewShell();
1339     if ( pShell && pHdl )
1340         pShell->UpdateInputHandler(false, bStopEditing);
1341 }
1342 
1343 void ScModule::SetInputMode( ScInputMode eMode, const OUString* pInitText )
1344 {
1345     ScInputHandler* pHdl = GetInputHdl();
1346     if (pHdl)
1347         pHdl->SetMode(eMode, pInitText);
1348 }
1349 
1350 bool ScModule::IsEditMode()
1351 {
1352     ScInputHandler* pHdl = GetInputHdl();
1353     return pHdl && pHdl->IsEditMode();
1354 }
1355 
1356 bool ScModule::IsInputMode()
1357 {
1358     ScInputHandler* pHdl = GetInputHdl();
1359     return pHdl && pHdl->IsInputMode();
1360 }
1361 
1362 bool ScModule::InputKeyEvent( const KeyEvent& rKEvt, bool bStartEdit )
1363 {
1364     ScInputHandler* pHdl = GetInputHdl();
1365     return pHdl && pHdl->KeyInput( rKEvt, bStartEdit );
1366 }
1367 
1368 void ScModule::InputEnterHandler( ScEnterMode nBlockMode )
1369 {
1370     if ( !SfxGetpApp()->IsDowning() ) // Not when quitting the program
1371     {
1372         ScInputHandler* pHdl = GetInputHdl();
1373         if (pHdl)
1374             pHdl->EnterHandler( nBlockMode );
1375     }
1376 }
1377 
1378 void ScModule::InputCancelHandler()
1379 {
1380     ScInputHandler* pHdl = GetInputHdl();
1381     if (pHdl)
1382         pHdl->CancelHandler();
1383 }
1384 
1385 void ScModule::InputSelection( const EditView* pView )
1386 {
1387     ScInputHandler* pHdl = GetInputHdl();
1388     if (pHdl)
1389         pHdl->InputSelection( pView );
1390 }
1391 
1392 void ScModule::InputChanged( const EditView* pView )
1393 {
1394     ScInputHandler* pHdl = GetInputHdl();
1395     if (pHdl)
1396         pHdl->InputChanged( pView, false );
1397 }
1398 
1399 void ScModule::ViewShellGone( const ScTabViewShell* pViewSh )
1400 {
1401     ScInputHandler* pHdl = GetInputHdl();
1402     if (pHdl)
1403         pHdl->ViewShellGone( pViewSh );
1404 }
1405 
1406 void ScModule::SetRefInputHdl( ScInputHandler* pNew )
1407 {
1408     m_pRefInputHandler = pNew;
1409 }
1410 
1411 void ScModule::InputGetSelection( sal_Int32& rStart, sal_Int32& rEnd )
1412 {
1413     ScInputHandler* pHdl = GetInputHdl();
1414     if (pHdl)
1415         pHdl->InputGetSelection( rStart, rEnd );
1416 }
1417 
1418 void ScModule::InputSetSelection( sal_Int32 nStart, sal_Int32 nEnd )
1419 {
1420     ScInputHandler* pHdl = GetInputHdl();
1421     if (pHdl)
1422         pHdl->InputSetSelection( nStart, nEnd );
1423 }
1424 
1425 void ScModule::InputReplaceSelection( const OUString& rStr )
1426 {
1427     ScInputHandler* pHdl = GetInputHdl();
1428     if (pHdl)
1429         pHdl->InputReplaceSelection( rStr );
1430 }
1431 
1432 void ScModule::InputTurnOffWinEngine()
1433 {
1434     ScInputHandler* pHdl = GetInputHdl();
1435     if (pHdl)
1436         pHdl->InputTurnOffWinEngine();
1437 }
1438 
1439 OUString ScModule::InputGetFormulaStr()
1440 {
1441     ScInputHandler* pHdl = GetInputHdl();
1442     OUString aStr;
1443     if ( pHdl )
1444         aStr = pHdl->GetFormString();
1445     return aStr;
1446 }
1447 
1448 void ScModule::ActivateInputWindow( const OUString* pStrFormula, bool bMatrix )
1449 {
1450     ScInputHandler* pHdl = GetInputHdl();
1451     if ( pHdl )
1452     {
1453         ScInputWindow* pWin = pHdl->GetInputWindow();
1454         if ( pStrFormula )
1455         {
1456             // Take over formula
1457             if ( pWin )
1458             {
1459                 pWin->SetFuncString( *pStrFormula, false );
1460                 // SetSumAssignMode due to sal_False not necessary
1461             }
1462             ScEnterMode nMode = bMatrix ? ScEnterMode::MATRIX : ScEnterMode::NORMAL;
1463             pHdl->EnterHandler( nMode );
1464 
1465             // Without Invalidate the selection remains active, if the formula has not changed
1466             if (pWin)
1467                 pWin->TextInvalidate();
1468         }
1469         else
1470         {
1471             // Cancel
1472             if ( pWin )
1473             {
1474                 pWin->SetFuncString( EMPTY_OUSTRING, false );
1475                 // SetSumAssignMode due to sal_False no necessary
1476             }
1477             pHdl->CancelHandler();
1478         }
1479     }
1480 }
1481 
1482 /**
1483  * Reference dialogs
1484  */
1485 void ScModule::SetRefDialog( sal_uInt16 nId, bool bVis, SfxViewFrame* pViewFrm )
1486 {
1487     //TODO: Move reference dialog handling to view
1488     //      Just keep function autopilot here for references to other documents
1489     if(m_nCurRefDlgId==0 || (nId==m_nCurRefDlgId && !bVis))
1490     {
1491         if ( !pViewFrm )
1492             pViewFrm = SfxViewFrame::Current();
1493 
1494         // bindings update causes problems with update of stylist if
1495         // current style family has changed
1496         //if ( pViewFrm )
1497         //  pViewFrm->GetBindings().Update();       // to avoid trouble in LockDispatcher
1498 
1499         m_nCurRefDlgId = bVis ? nId : 0 ;             // before SetChildWindow
1500 
1501         if ( pViewFrm )
1502         {
1503             //  store the dialog id also in the view shell
1504             SfxViewShell* pViewSh = pViewFrm->GetViewShell();
1505             if (ScTabViewShell* pTabViewSh = dynamic_cast<ScTabViewShell*>(pViewSh))
1506                 pTabViewSh->SetCurRefDlgId(m_nCurRefDlgId);
1507             else
1508             {
1509                 // no ScTabViewShell - possible for example from a Basic macro
1510                 bVis = false;
1511                 m_nCurRefDlgId = 0;   // don't set nCurRefDlgId if no dialog is created
1512             }
1513 
1514             pViewFrm->SetChildWindow( nId, bVis );
1515         }
1516 
1517         SfxApplication* pSfxApp = SfxGetpApp();
1518         pSfxApp->Broadcast( SfxHint( SfxHintId::ScRefModeChanged ) );
1519     }
1520 }
1521 
1522 static SfxChildWindow* lcl_GetChildWinFromCurrentView( sal_uInt16 nId )
1523 {
1524     SfxViewFrame* pViewFrm = SfxViewFrame::Current();
1525 
1526     // #i46999# current view frame can be null (for example, when closing help)
1527     return pViewFrm ? pViewFrm->GetChildWindow( nId ) : nullptr;
1528 }
1529 
1530 static SfxChildWindow* lcl_GetChildWinFromAnyView( sal_uInt16 nId )
1531 {
1532     // First, try the current view
1533     SfxChildWindow* pChildWnd = lcl_GetChildWinFromCurrentView( nId );
1534     if ( pChildWnd )
1535         return pChildWnd;           // found in the current view
1536 
1537     //  if not found there, get the child window from any open view
1538     //  it can be open only in one view because nCurRefDlgId is global
1539 
1540     SfxViewFrame* pViewFrm = SfxViewFrame::GetFirst();
1541     while ( pViewFrm )
1542     {
1543         pChildWnd = pViewFrm->GetChildWindow( nId );
1544         if ( pChildWnd )
1545             return pChildWnd;       // found in any view
1546 
1547         pViewFrm = SfxViewFrame::GetNext( *pViewFrm );
1548     }
1549 
1550     return nullptr;                    // none found
1551 }
1552 
1553 bool ScModule::IsModalMode(SfxObjectShell* pDocSh)
1554 {
1555     //TODO: Move reference dialog handling to view
1556     //      Just keep function autopilot here for references to other documents
1557     bool bIsModal = false;
1558 
1559     if ( m_nCurRefDlgId )
1560     {
1561         SfxChildWindow* pChildWnd = lcl_GetChildWinFromCurrentView( m_nCurRefDlgId );
1562         if ( pChildWnd )
1563         {
1564             IAnyRefDialog* pRefDlg = dynamic_cast<IAnyRefDialog*>(pChildWnd->GetWindow());
1565             assert(pRefDlg);
1566             bIsModal = pChildWnd->IsVisible() && pRefDlg &&
1567                 !( pRefDlg->IsRefInputMode() && pRefDlg->IsDocAllowed(pDocSh) );
1568         }
1569     }
1570     else if (pDocSh)
1571     {
1572         ScInputHandler* pHdl = GetInputHdl();
1573         if ( pHdl )
1574             bIsModal = pHdl->IsModalMode(pDocSh);
1575     }
1576 
1577     return bIsModal;
1578 }
1579 
1580 bool ScModule::IsTableLocked()
1581 {
1582     //TODO: Move reference dialog handling to view
1583     //      Just keep function autopilot here for references to other documents
1584     bool bLocked = false;
1585 
1586     // Up until now just for ScAnyRefDlg
1587     if ( m_nCurRefDlgId )
1588     {
1589         SfxChildWindow* pChildWnd = lcl_GetChildWinFromAnyView( m_nCurRefDlgId );
1590         if ( pChildWnd )
1591         {
1592             IAnyRefDialog* pRefDlg(dynamic_cast<IAnyRefDialog*>(pChildWnd->GetWindow()));
1593             assert(pRefDlg);
1594             if(pRefDlg)
1595             {
1596                 bLocked = pRefDlg->IsTableLocked();
1597             }
1598         }
1599         else
1600             bLocked = true;     // for other views, see IsModalMode
1601     }
1602 
1603     return bLocked;
1604 }
1605 
1606 bool ScModule::IsRefDialogOpen()
1607 {
1608     //TODO: Move reference dialog handling to view
1609     //      Just keep function autopilot here for references to other documents
1610     bool bIsOpen = false;
1611 
1612     if ( m_nCurRefDlgId )
1613     {
1614         SfxChildWindow* pChildWnd = lcl_GetChildWinFromCurrentView( m_nCurRefDlgId );
1615         if ( pChildWnd )
1616             bIsOpen = pChildWnd->IsVisible();
1617     }
1618 
1619     return bIsOpen;
1620 }
1621 
1622 bool ScModule::IsFormulaMode()
1623 {
1624     //TODO: Move reference dialog handling to view
1625     //      Just keep function autopilot here for references to other documents
1626     bool bIsFormula = false;
1627 
1628     // formula mode in online is not usable in collaborative mode,
1629     // this is a workaround for disabling formula mode in online
1630     // when there is more than a single view
1631     if (comphelper::LibreOfficeKit::isActive() && SfxViewShell::GetActiveShells() > 1)
1632             return false;
1633 
1634     if ( m_nCurRefDlgId )
1635     {
1636         SfxChildWindow* pChildWnd = lcl_GetChildWinFromCurrentView( m_nCurRefDlgId );
1637         if ( pChildWnd )
1638         {
1639             IAnyRefDialog* pRefDlg = dynamic_cast<IAnyRefDialog*>(pChildWnd->GetWindow());
1640             assert(pRefDlg);
1641             bIsFormula = pChildWnd->IsVisible() && pRefDlg && pRefDlg->IsRefInputMode();
1642         }
1643     }
1644     else
1645     {
1646         ScInputHandler* pHdl = GetInputHdl();
1647         if ( pHdl )
1648             bIsFormula = pHdl->IsFormulaMode();
1649     }
1650 
1651     if (m_bIsInEditCommand)
1652         bIsFormula = true;
1653 
1654     return bIsFormula;
1655 }
1656 
1657 static void lcl_MarkedTabs( const ScMarkData& rMark, SCTAB& rStartTab, SCTAB& rEndTab )
1658 {
1659     if (rMark.GetSelectCount() > 1)
1660     {
1661         rEndTab = rMark.GetLastSelected();
1662         rStartTab = rMark.GetFirstSelected();
1663     }
1664 }
1665 
1666 void ScModule::SetReference( const ScRange& rRef, ScDocument* pDoc,
1667                                     const ScMarkData* pMarkData )
1668 {
1669     //TODO: Move reference dialog handling to view
1670     //      Just keep function autopilot here for references to other documents
1671 
1672     // In RefDialogs we also trigger the ZoomIn, if the Ref's Start and End are different
1673     ScRange aNew = rRef;
1674     aNew.PutInOrder(); // Always in the right direction
1675 
1676     if( m_nCurRefDlgId )
1677     {
1678         SfxChildWindow* pChildWnd = lcl_GetChildWinFromAnyView( m_nCurRefDlgId );
1679         OSL_ENSURE( pChildWnd, "NoChildWin" );
1680         if ( pChildWnd )
1681         {
1682             if ( m_nCurRefDlgId == SID_OPENDLG_CONSOLIDATE && pMarkData )
1683             {
1684                 SCTAB nStartTab = aNew.aStart.Tab();
1685                 SCTAB nEndTab   = aNew.aEnd.Tab();
1686                 lcl_MarkedTabs( *pMarkData, nStartTab, nEndTab );
1687                 aNew.aStart.SetTab(nStartTab);
1688                 aNew.aEnd.SetTab(nEndTab);
1689             }
1690 
1691             IAnyRefDialog* pRefDlg = dynamic_cast<IAnyRefDialog*>(pChildWnd->GetWindow());
1692             assert(pRefDlg);
1693             if(pRefDlg)
1694             {
1695                 // hide the (color) selection now instead of later from LoseFocus,
1696                 // don't abort the ref input that causes this call (bDoneRefMode = sal_False)
1697                 pRefDlg->HideReference( false );
1698                 pRefDlg->SetReference( aNew, pDoc );
1699             }
1700         }
1701     }
1702     else
1703     {
1704         ScInputHandler* pHdl = GetInputHdl();
1705         if (pHdl)
1706             pHdl->SetReference( aNew, pDoc );
1707         else
1708         {
1709             OSL_FAIL("SetReference without receiver");
1710         }
1711     }
1712 }
1713 
1714 /**
1715  * Multiple selection
1716  */
1717 void ScModule::AddRefEntry()
1718 {
1719     //TODO: Move reference dialog handling to view
1720     //      Just keep function autopilot here for references to other documents
1721     if ( m_nCurRefDlgId )
1722     {
1723         SfxChildWindow* pChildWnd = lcl_GetChildWinFromAnyView( m_nCurRefDlgId );
1724         OSL_ENSURE( pChildWnd, "NoChildWin" );
1725         if ( pChildWnd )
1726         {
1727             IAnyRefDialog* pRefDlg = dynamic_cast<IAnyRefDialog*>(pChildWnd->GetWindow());
1728             assert(pRefDlg);
1729             if(pRefDlg)
1730             {
1731                 pRefDlg->AddRefEntry();
1732             }
1733         }
1734     }
1735     else
1736     {
1737         ScInputHandler* pHdl = GetInputHdl();
1738         if (pHdl)
1739             pHdl->AddRefEntry();
1740     }
1741 }
1742 
1743 void ScModule::EndReference()
1744 {
1745     //TODO: Move reference dialog handling to view
1746     //      Just keep function autopilot here for references to other documents
1747 
1748     // We also annul the ZoomIn again in RefDialogs
1749 
1750     //FIXME: ShowRefFrame at InputHdl, if the Function AutoPilot is open?
1751     if ( m_nCurRefDlgId )
1752     {
1753         SfxChildWindow* pChildWnd = lcl_GetChildWinFromAnyView( m_nCurRefDlgId );
1754         OSL_ENSURE( pChildWnd, "NoChildWin" );
1755         if ( pChildWnd )
1756         {
1757             IAnyRefDialog* pRefDlg = dynamic_cast<IAnyRefDialog*>(pChildWnd->GetWindow());
1758             assert(pRefDlg);
1759             if(pRefDlg)
1760             {
1761                 pRefDlg->SetActive();
1762             }
1763         }
1764     }
1765 }
1766 
1767 /**
1768  * Idle/OnlineSpelling
1769  */
1770 void ScModule::AnythingChanged()
1771 {
1772     sal_uInt64 nOldTime = m_aIdleTimer.GetTimeout();
1773     if ( nOldTime != SC_IDLE_MIN )
1774         m_aIdleTimer.SetTimeout( SC_IDLE_MIN );
1775 
1776     nIdleCount = 0;
1777 }
1778 
1779 static void lcl_CheckNeedsRepaint( const ScDocShell* pDocShell )
1780 {
1781     SfxViewFrame* pFrame = SfxViewFrame::GetFirst( pDocShell );
1782     while ( pFrame )
1783     {
1784         SfxViewShell* p = pFrame->GetViewShell();
1785         ScTabViewShell* pViewSh = dynamic_cast< ScTabViewShell *>( p );
1786         if ( pViewSh )
1787             pViewSh->CheckNeedsRepaint();
1788         pFrame = SfxViewFrame::GetNext( *pFrame, pDocShell );
1789     }
1790 }
1791 
1792 IMPL_LINK_NOARG(ScModule, IdleHandler, Timer *, void)
1793 {
1794     if ( Application::AnyInput( VclInputFlags::MOUSE | VclInputFlags::KEYBOARD ) )
1795     {
1796         m_aIdleTimer.Start(); // Timeout unchanged
1797         return;
1798     }
1799 
1800     bool bMore = false;
1801     bool bAutoSpell = false;
1802     ScDocShell* pDocSh = dynamic_cast<ScDocShell*>(SfxObjectShell::Current());
1803 
1804     if ( pDocSh )
1805     {
1806         ScDocument& rDoc = pDocSh->GetDocument();
1807         bAutoSpell = rDoc.GetDocOptions().IsAutoSpell();
1808         if (pDocSh->IsReadOnly())
1809             bAutoSpell = false;
1810 
1811         sc::DocumentLinkManager& rLinkMgr = rDoc.GetDocLinkManager();
1812         bool bLinks = rLinkMgr.idleCheckLinks();
1813         bool bWidth = rDoc.IdleCalcTextWidth();
1814 
1815         bMore = bLinks || bWidth; // Still something at all?
1816 
1817         // While calculating a Basic formula, a paint event may have occurred,
1818         // so check the bNeedsRepaint flags for this document's views
1819         if (bWidth)
1820             lcl_CheckNeedsRepaint( pDocSh );
1821     }
1822 
1823     if (bAutoSpell)
1824     {
1825         ScTabViewShell* pViewSh = dynamic_cast<ScTabViewShell*>(SfxViewShell::Current());
1826         if (pViewSh)
1827         {
1828             bool bSpell = pViewSh->ContinueOnlineSpelling();
1829             if (bSpell)
1830             {
1831                 m_aSpellIdle.Start();
1832                 bMore = true;
1833             }
1834         }
1835     }
1836 
1837     sal_uInt64 nOldTime = m_aIdleTimer.GetTimeout();
1838     sal_uInt64 nNewTime = nOldTime;
1839     if ( bMore )
1840     {
1841         nNewTime = SC_IDLE_MIN;
1842         nIdleCount = 0;
1843     }
1844     else
1845     {
1846         // Set SC_IDLE_COUNT to initial Timeout - increase afterwards
1847         if ( nIdleCount < SC_IDLE_COUNT )
1848             ++nIdleCount;
1849         else
1850         {
1851             nNewTime += SC_IDLE_STEP;
1852             if ( nNewTime > SC_IDLE_MAX )
1853                 nNewTime = SC_IDLE_MAX;
1854         }
1855     }
1856     if ( nNewTime != nOldTime )
1857         m_aIdleTimer.SetTimeout( nNewTime );
1858 
1859 
1860     m_aIdleTimer.Start();
1861 }
1862 
1863 IMPL_LINK_NOARG(ScModule, SpellTimerHdl, Timer *, void)
1864 {
1865     if ( Application::AnyInput( VclInputFlags::KEYBOARD ) )
1866     {
1867         m_aSpellIdle.Start();
1868         return; // Later again ...
1869     }
1870 
1871     ScTabViewShell* pViewSh = dynamic_cast<ScTabViewShell*>(SfxViewShell::Current());
1872     if (pViewSh)
1873     {
1874         if (pViewSh->ContinueOnlineSpelling())
1875             m_aSpellIdle.Start();
1876     }
1877 }
1878 
1879 /**
1880  * Virtual methods for the OptionsDialog
1881  */
1882 std::unique_ptr<SfxItemSet> ScModule::CreateItemSet( sal_uInt16 nId )
1883 {
1884     std::unique_ptr<SfxItemSet> pRet;
1885     if(SID_SC_EDITOPTIONS == nId)
1886     {
1887         pRet = o3tl::make_unique<SfxItemSet>(
1888             GetPool(),
1889             svl::Items<
1890                 // TP_USERLISTS:
1891                 SCITEM_USERLIST, SCITEM_USERLIST,
1892                 // TP_GRID:
1893                 SID_ATTR_GRID_OPTIONS, SID_ATTR_GRID_OPTIONS,
1894                 SID_ATTR_METRIC, SID_ATTR_METRIC,
1895                 SID_ATTR_DEFTABSTOP, SID_ATTR_DEFTABSTOP,
1896                 // TP_INPUT:
1897                 SID_SC_INPUT_LEGACY_CELL_SELECTION, SID_SC_OPT_SORT_REF_UPDATE,
1898                 // TP_FORMULA, TP_DEFAULTS:
1899                 SID_SCFORMULAOPTIONS, SID_SCDEFAULTSOPTIONS,
1900                 // TP_VIEW, TP_CALC:
1901                 SID_SCVIEWOPTIONS, SID_SCDOCOPTIONS,
1902                 // TP_PRINT:
1903                 SID_SCPRINTOPTIONS, SID_SCPRINTOPTIONS,
1904                 // TP_INPUT:
1905                 SID_SC_INPUT_SELECTION, SID_SC_INPUT_MARK_HEADER,
1906                 SID_SC_INPUT_TEXTWYSIWYG, SID_SC_INPUT_TEXTWYSIWYG,
1907                 SID_SC_INPUT_REPLCELLSWARN, SID_SC_INPUT_REPLCELLSWARN,
1908                 // TP_VIEW:
1909                 SID_SC_OPT_SYNCZOOM, SID_SC_OPT_KEY_BINDING_COMPAT>{});
1910 
1911         const ScAppOptions& rAppOpt = GetAppOptions();
1912 
1913         ScDocShell*     pDocSh = dynamic_cast< ScDocShell *>( SfxObjectShell::Current() );
1914         ScDocOptions    aCalcOpt = pDocSh
1915                             ? pDocSh->GetDocument().GetDocOptions()
1916                             : GetDocOptions();
1917 
1918         ScTabViewShell* pViewSh = dynamic_cast< ScTabViewShell *>( SfxViewShell::Current() );
1919         ScViewOptions   aViewOpt = pViewSh
1920                             ? pViewSh->GetViewData().GetOptions()
1921                             : GetViewOptions();
1922 
1923         ScUserListItem  aULItem( SCITEM_USERLIST );
1924         ScUserList*     pUL = ScGlobal::GetUserList();
1925 
1926         //  SfxGetpApp()->GetOptions( aSet );
1927 
1928         pRet->Put( SfxUInt16Item( SID_ATTR_METRIC,
1929                         sal::static_int_cast<sal_uInt16>(rAppOpt.GetAppMetric()) ) );
1930 
1931         // TP_CALC
1932         pRet->Put( SfxUInt16Item( SID_ATTR_DEFTABSTOP,
1933                         aCalcOpt.GetTabDistance()));
1934         pRet->Put( ScTpCalcItem( SID_SCDOCOPTIONS, aCalcOpt ) );
1935 
1936         // TP_VIEW
1937         pRet->Put( ScTpViewItem( aViewOpt ) );
1938         pRet->Put( SfxBoolItem( SID_SC_OPT_SYNCZOOM, rAppOpt.GetSynchronizeZoom() ) );
1939 
1940         // TP_INPUT
1941         const ScInputOptions& rInpOpt = GetInputOptions();
1942         pRet->Put( SfxUInt16Item( SID_SC_INPUT_SELECTIONPOS,
1943                     rInpOpt.GetMoveDir() ) );
1944         pRet->Put( SfxBoolItem( SID_SC_INPUT_SELECTION,
1945                     rInpOpt.GetMoveSelection() ) );
1946         pRet->Put( SfxBoolItem( SID_SC_INPUT_EDITMODE,
1947                     rInpOpt.GetEnterEdit() ) );
1948         pRet->Put( SfxBoolItem( SID_SC_INPUT_FMT_EXPAND,
1949                     rInpOpt.GetExtendFormat() ) );
1950         pRet->Put( SfxBoolItem( SID_SC_INPUT_RANGEFINDER,
1951                     rInpOpt.GetRangeFinder() ) );
1952         pRet->Put( SfxBoolItem( SID_SC_INPUT_REF_EXPAND,
1953                     rInpOpt.GetExpandRefs() ) );
1954         pRet->Put( SfxBoolItem(SID_SC_OPT_SORT_REF_UPDATE, rInpOpt.GetSortRefUpdate()));
1955         pRet->Put( SfxBoolItem( SID_SC_INPUT_MARK_HEADER,
1956                     rInpOpt.GetMarkHeader() ) );
1957         pRet->Put( SfxBoolItem( SID_SC_INPUT_TEXTWYSIWYG,
1958                     rInpOpt.GetTextWysiwyg() ) );
1959         pRet->Put( SfxBoolItem( SID_SC_INPUT_REPLCELLSWARN,
1960                     rInpOpt.GetReplaceCellsWarn() ) );
1961         pRet->Put( SfxBoolItem( SID_SC_INPUT_LEGACY_CELL_SELECTION,
1962                     rInpOpt.GetLegacyCellSelection() ) );
1963 
1964         // RID_SC_TP_PRINT
1965         pRet->Put( ScTpPrintItem( GetPrintOptions() ) );
1966 
1967         // TP_GRID
1968         SvxGridItem* pSvxGridItem = aViewOpt.CreateGridItem();
1969         pRet->Put( *pSvxGridItem );
1970         delete pSvxGridItem;
1971 
1972         // TP_USERLISTS
1973         if ( pUL )
1974         {
1975             aULItem.SetUserList( *pUL );
1976             pRet->Put(aULItem);
1977         }
1978 
1979         // TP_COMPATIBILITY
1980         pRet->Put( SfxUInt16Item( SID_SC_OPT_KEY_BINDING_COMPAT,
1981                                    rAppOpt.GetKeyBindingType() ) );
1982 
1983         // TP_DEFAULTS
1984         pRet->Put( ScTpDefaultsItem( GetDefaultsOptions() ) );
1985 
1986         // TP_FORMULA
1987         ScFormulaOptions aOptions = GetFormulaOptions();
1988         if (pDocSh)
1989         {
1990             ScCalcConfig aConfig( aOptions.GetCalcConfig());
1991             aConfig.MergeDocumentSpecific( pDocSh->GetDocument().GetCalcConfig());
1992             aOptions.SetCalcConfig( aConfig);
1993         }
1994         pRet->Put( ScTpFormulaItem( aOptions ) );
1995     }
1996     return pRet;
1997 }
1998 
1999 void ScModule::ApplyItemSet( sal_uInt16 nId, const SfxItemSet& rSet )
2000 {
2001     if(SID_SC_EDITOPTIONS == nId)
2002     {
2003         ModifyOptions( rSet );
2004     }
2005 }
2006 
2007 VclPtr<SfxTabPage> ScModule::CreateTabPage( sal_uInt16 nId, TabPageParent pParent, const SfxItemSet& rSet )
2008 {
2009     VclPtr<SfxTabPage> pRet;
2010     ScAbstractDialogFactory* pFact = ScAbstractDialogFactory::Create();
2011     switch(nId)
2012     {
2013         case SID_SC_TP_LAYOUT:
2014         {
2015             ::CreateTabPage ScTpLayoutOptionsCreate = pFact->GetTabPageCreatorFunc(SID_SC_TP_LAYOUT);
2016             if (ScTpLayoutOptionsCreate)
2017                 pRet = (*ScTpLayoutOptionsCreate)(pParent, &rSet);
2018             break;
2019         }
2020         case SID_SC_TP_CONTENT:
2021         {
2022             ::CreateTabPage ScTpContentOptionsCreate = pFact->GetTabPageCreatorFunc(SID_SC_TP_CONTENT);
2023             if (ScTpContentOptionsCreate)
2024                 pRet = (*ScTpContentOptionsCreate)(pParent, &rSet);
2025             break;
2026         }
2027         case SID_SC_TP_GRID:
2028             pRet = SvxGridTabPage::Create(pParent, rSet);
2029             break;
2030         case SID_SC_TP_USERLISTS:
2031         {
2032             ::CreateTabPage ScTpUserListsCreate = pFact->GetTabPageCreatorFunc(SID_SC_TP_USERLISTS);
2033             if (ScTpUserListsCreate)
2034                 pRet = (*ScTpUserListsCreate)(pParent, &rSet);
2035             break;
2036         }
2037         case SID_SC_TP_CALC:
2038         {
2039             ::CreateTabPage ScTpCalcOptionsCreate = pFact->GetTabPageCreatorFunc(SID_SC_TP_CALC);
2040             if (ScTpCalcOptionsCreate)
2041                 pRet = (*ScTpCalcOptionsCreate)(pParent, &rSet);
2042             break;
2043         }
2044         case SID_SC_TP_FORMULA:
2045         {
2046             ::CreateTabPage ScTpFormulaOptionsCreate = pFact->GetTabPageCreatorFunc(SID_SC_TP_FORMULA);
2047             if (ScTpFormulaOptionsCreate)
2048                 pRet = (*ScTpFormulaOptionsCreate)(pParent, &rSet);
2049             break;
2050         }
2051         case SID_SC_TP_COMPATIBILITY:
2052         {
2053             ::CreateTabPage ScTpCompatOptionsCreate = pFact->GetTabPageCreatorFunc(SID_SC_TP_COMPATIBILITY);
2054             if (ScTpCompatOptionsCreate)
2055                 pRet = (*ScTpCompatOptionsCreate)(pParent, &rSet);
2056             break;
2057         }
2058         case SID_SC_TP_CHANGES:
2059         {
2060             ::CreateTabPage ScRedlineOptionsTabPageCreate = pFact->GetTabPageCreatorFunc(SID_SC_TP_CHANGES);
2061             if (ScRedlineOptionsTabPageCreate)
2062                 pRet =(*ScRedlineOptionsTabPageCreate)(pParent, &rSet);
2063             break;
2064         }
2065         case RID_SC_TP_PRINT:
2066         {
2067             ::CreateTabPage ScTpPrintOptionsCreate = pFact->GetTabPageCreatorFunc(RID_SC_TP_PRINT);
2068             if (ScTpPrintOptionsCreate)
2069                 pRet = (*ScTpPrintOptionsCreate)(pParent, &rSet);
2070             break;
2071         }
2072         case RID_SC_TP_DEFAULTS:
2073         {
2074             ::CreateTabPage ScTpDefaultsOptionsCreate = pFact->GetTabPageCreatorFunc(RID_SC_TP_DEFAULTS);
2075             if (ScTpDefaultsOptionsCreate)
2076                 pRet = (*ScTpDefaultsOptionsCreate)(pParent, &rSet);
2077             break;
2078         }
2079     }
2080 
2081     OSL_ENSURE( pRet, "ScModule::CreateTabPage(): no valid ID for TabPage!" );
2082 
2083     return pRet;
2084 }
2085 
2086 IMPL_LINK( ScModule, CalcFieldValueHdl, EditFieldInfo*, pInfo, void )
2087 {
2088     //TODO: Merge with ScFieldEditEngine!
2089     if (!pInfo)
2090         return;
2091 
2092     const SvxFieldItem& rField = pInfo->GetField();
2093     const SvxFieldData* pField = rField.GetField();
2094 
2095     if (const SvxURLField* pURLField = dynamic_cast<const SvxURLField*>(pField))
2096     {
2097         // URLField
2098         const OUString& aURL = pURLField->GetURL();
2099 
2100         switch ( pURLField->GetFormat() )
2101         {
2102             case SvxURLFormat::AppDefault: //TODO: Settable in the App?
2103             case SvxURLFormat::Repr:
2104             {
2105                 pInfo->SetRepresentation( pURLField->GetRepresentation() );
2106             }
2107             break;
2108 
2109             case SvxURLFormat::Url:
2110             {
2111                 pInfo->SetRepresentation( aURL );
2112             }
2113             break;
2114         }
2115 
2116         svtools::ColorConfigEntry eEntry =
2117             INetURLHistory::GetOrCreate()->QueryUrl( aURL ) ? svtools::LINKSVISITED : svtools::LINKS;
2118         pInfo->SetTextColor( GetColorConfig().GetColorValue(eEntry).nColor );
2119     }
2120     else
2121     {
2122         OSL_FAIL("Unknown Field");
2123         pInfo->SetRepresentation(OUString('?'));
2124     }
2125 }
2126 
2127 void ScModule::RegisterRefWindow( sal_uInt16 nSlotId, vcl::Window *pWnd )
2128 {
2129     std::vector<VclPtr<vcl::Window> > & rlRefWindow = m_mapRefWindow[nSlotId];
2130 
2131     if( std::find( rlRefWindow.begin(), rlRefWindow.end(), pWnd ) == rlRefWindow.end() )
2132     {
2133         rlRefWindow.emplace_back(pWnd );
2134     }
2135 
2136 }
2137 
2138 void  ScModule::UnregisterRefWindow( sal_uInt16 nSlotId, vcl::Window *pWnd )
2139 {
2140     auto iSlot = m_mapRefWindow.find( nSlotId );
2141 
2142     if( iSlot == m_mapRefWindow.end() )
2143         return;
2144 
2145     std::vector<VclPtr<vcl::Window> > & rlRefWindow = iSlot->second;
2146 
2147     auto i = std::find( rlRefWindow.begin(), rlRefWindow.end(), pWnd );
2148 
2149     if( i == rlRefWindow.end() )
2150         return;
2151 
2152     rlRefWindow.erase( i );
2153 
2154     if( rlRefWindow.empty() )
2155         m_mapRefWindow.erase( nSlotId );
2156 }
2157 
2158 vcl::Window *  ScModule::Find1RefWindow( sal_uInt16 nSlotId, vcl::Window *pWndAncestor )
2159 {
2160     if (!pWndAncestor)
2161         return nullptr;
2162 
2163     auto iSlot = m_mapRefWindow.find( nSlotId );
2164 
2165     if( iSlot == m_mapRefWindow.end() )
2166         return nullptr;
2167 
2168     std::vector<VclPtr<vcl::Window> > & rlRefWindow = iSlot->second;
2169 
2170     while( vcl::Window *pParent = pWndAncestor->GetParent() ) pWndAncestor = pParent;
2171 
2172     for (auto const& refWindow : rlRefWindow)
2173         if ( pWndAncestor->IsWindowOrChild( refWindow, refWindow->IsSystemWindow() ) )
2174             return refWindow;
2175 
2176     return nullptr;
2177 }
2178 
2179 using namespace com::sun::star;
2180 
2181 #define LINGUPROP_AUTOSPELL "IsSpellAuto"
2182 
2183 void ScModule::GetSpellSettings( LanguageType& rDefLang, LanguageType& rCjkLang, LanguageType& rCtlLang,
2184         bool& rAutoSpell )
2185 {
2186     // use SvtLinguConfig instead of service LinguProperties to avoid
2187     // loading the linguistic component
2188     SvtLinguConfig aConfig;
2189 
2190     SvtLinguOptions aOptions;
2191     aConfig.GetOptions( aOptions );
2192 
2193     rDefLang = MsLangId::resolveSystemLanguageByScriptType(aOptions.nDefaultLanguage, css::i18n::ScriptType::LATIN);
2194     rCjkLang = MsLangId::resolveSystemLanguageByScriptType(aOptions.nDefaultLanguage_CJK, css::i18n::ScriptType::ASIAN);
2195     rCtlLang = MsLangId::resolveSystemLanguageByScriptType(aOptions.nDefaultLanguage_CTL, css::i18n::ScriptType::COMPLEX);
2196     rAutoSpell = aOptions.bIsSpellAuto;
2197 }
2198 
2199 void ScModule::SetAutoSpellProperty( bool bSet )
2200 {
2201     // use SvtLinguConfig instead of service LinguProperties to avoid
2202     // loading the linguistic component
2203     SvtLinguConfig aConfig;
2204 
2205     aConfig.SetProperty( OUString( LINGUPROP_AUTOSPELL ), uno::Any(bSet) );
2206 }
2207 
2208 bool ScModule::HasThesaurusLanguage( LanguageType nLang )
2209 {
2210     if ( nLang == LANGUAGE_NONE )
2211         return false;
2212 
2213     bool bHasLang = false;
2214     try
2215     {
2216         uno::Reference< linguistic2::XThesaurus > xThes(LinguMgr::GetThesaurus());
2217         if ( xThes.is() )
2218             bHasLang = xThes->hasLocale( LanguageTag::convertToLocale( nLang ) );
2219     }
2220     catch( uno::Exception& )
2221     {
2222         OSL_FAIL("Error in Thesaurus");
2223     }
2224 
2225     return bHasLang;
2226 }
2227 
2228 std::unique_ptr<SfxStyleFamilies> ScModule::CreateStyleFamilies()
2229 {
2230     std::unique_ptr<SfxStyleFamilies> pStyleFamilies(new SfxStyleFamilies);
2231 
2232     pStyleFamilies->emplace_back(SfxStyleFamilyItem(SfxStyleFamily::Para,
2233                                                     ScResId(STR_STYLE_FAMILY_CELL),
2234                                                     Image(BitmapEx(BMP_STYLES_FAMILY_CELL)),
2235                                                     RID_CELLSTYLEFAMILY, SC_MOD()->GetResLocale()));
2236 
2237     pStyleFamilies->emplace_back(SfxStyleFamilyItem(SfxStyleFamily::Page,
2238                                                     ScResId(STR_STYLE_FAMILY_PAGE),
2239                                                     Image(BitmapEx(BMP_STYLES_FAMILY_PAGE)),
2240                                                     RID_PAGESTYLEFAMILY, SC_MOD()->GetResLocale()));
2241 
2242     return pStyleFamilies;
2243 }
2244 
2245 void ScModule::RegisterAutomationApplicationEventsCaller(css::uno::Reference< ooo::vba::XSinkCaller > const& xCaller)
2246 {
2247     mxAutomationApplicationEventsCaller = xCaller;
2248 }
2249 
2250 void ScModule::CallAutomationApplicationEventSinks(const OUString& Method, css::uno::Sequence< css::uno::Any >& Arguments)
2251 {
2252     if (mxAutomationApplicationEventsCaller.is())
2253         mxAutomationApplicationEventsCaller->CallSinks(Method, Arguments);
2254 }
2255 
2256 /* vim:set shiftwidth=4 softtabstop=4 expandtab: */
2257