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 .
21 #include <rtl/strbuf.hxx>
22 #include <com/sun/star/awt/XDevice.hpp>
23 #include <com/sun/star/frame/Desktop.hpp>
24 #include <com/sun/star/frame/XFrame.hpp>
25 #include <com/sun/star/frame/XFramesSupplier.hpp>
26 #include <com/sun/star/i18n/ScriptType.hpp>
27 #include <comphelper/processfactory.hxx>
28 #include <vcl/svapp.hxx>
29 #include <svl/stritem.hxx>
30 #include <svl/languageoptions.hxx>
31 #include <sfx2/objsh.hxx>
32 #include <sfx2/printer.hxx>
33 #include <sfx2/docfile.hxx>
34 #include <vcl/font.hxx>
35 #include <vcl/settings.hxx>
37 #include <editeng/editstat.hxx>
38 #include "scitems.hxx"
39 #include <editeng/eeitem.hxx>
40 #include "document.hxx"
41 #include "docpool.hxx"
43 #include "editutil.hxx"
44 #include "drwlayer.hxx"
45 #include "scextopt.hxx"
46 #include "patattr.hxx"
47 #include "fapihelper.hxx"
48 #include "xlconst.hxx"
49 #include "xlstyle.hxx"
50 #include "xlchart.hxx"
51 #include "xltracer.hxx"
52 #include <unotools/useroptions.hxx>
55 namespace ApiScriptType
= ::com::sun::star::i18n::ScriptType
;
57 using ::com::sun::star::uno::Exception
;
58 using ::com::sun::star::uno::Reference
;
59 using ::com::sun::star::uno::UNO_QUERY_THROW
;
60 using ::com::sun::star::uno::UNO_SET_THROW
;
61 using ::com::sun::star::awt::XDevice
;
62 using ::com::sun::star::awt::DeviceInfo
;
63 using ::com::sun::star::frame::XFrame
;
64 using ::com::sun::star::frame::XFramesSupplier
;
65 using ::com::sun::star::lang::XMultiServiceFactory
;
67 using namespace ::com::sun::star
;
69 // Global data ================================================================
72 XclDebugObjCounter::~XclDebugObjCounter()
74 OSL_ENSURE( mnObjCnt
== 0, "XclDebugObjCounter::~XclDebugObjCounter - wrong root object count" );
78 XclRootData::XclRootData( XclBiff eBiff
, SfxMedium
& rMedium
,
79 tools::SvRef
<SotStorage
> xRootStrg
, ScDocument
& rDoc
, rtl_TextEncoding eTextEnc
, bool bExport
) :
81 meOutput( EXC_OUTPUT_BINARY
),
83 mxRootStrg( xRootStrg
),
86 maDefPassword( "VelvetSweatshop" ),
87 meTextEnc( eTextEnc
),
88 meSysLang( Application::GetSettings().GetLanguageTag().getLanguageType() ),
89 meDocLang( Application::GetSettings().GetLanguageTag().getLanguageType() ),
90 meUILang( Application::GetSettings().GetUILanguageTag().getLanguageType() ),
91 mnDefApiScript( ApiScriptType::LATIN
),
92 maScMaxPos( MAXCOL
, MAXROW
, MAXTAB
),
93 maXclMaxPos( EXC_MAXCOL2
, EXC_MAXROW2
, EXC_MAXTAB2
),
94 maMaxPos( EXC_MAXCOL2
, EXC_MAXROW2
, EXC_MAXTAB2
),
95 mxFontPropSetHlp( new XclFontPropSetHelper
),
96 mxChPropSetHlp( new XclChPropSetHelper
),
98 mfScreenPixelX( 50.0 ),
99 mfScreenPixelY( 50.0 ),
104 maUserName
= SvtUserOptions().GetLastName();
105 if( maUserName
.isEmpty() )
108 switch( ScGlobal::GetDefaultScriptType() )
110 case SvtScriptType::LATIN
: mnDefApiScript
= ApiScriptType::LATIN
; break;
111 case SvtScriptType::ASIAN
: mnDefApiScript
= ApiScriptType::ASIAN
; break;
112 case SvtScriptType::COMPLEX
: mnDefApiScript
= ApiScriptType::COMPLEX
; break;
113 default: SAL_WARN( "sc", "XclRootData::XclRootData - unknown script type" );
116 // maximum cell position
119 case EXC_BIFF2
: maXclMaxPos
.Set( EXC_MAXCOL2
, EXC_MAXROW2
, EXC_MAXTAB2
); break;
120 case EXC_BIFF3
: maXclMaxPos
.Set( EXC_MAXCOL3
, EXC_MAXROW3
, EXC_MAXTAB3
); break;
121 case EXC_BIFF4
: maXclMaxPos
.Set( EXC_MAXCOL4
, EXC_MAXROW4
, EXC_MAXTAB4
); break;
122 case EXC_BIFF5
: maXclMaxPos
.Set( EXC_MAXCOL5
, EXC_MAXROW5
, EXC_MAXTAB5
); break;
123 case EXC_BIFF8
: maXclMaxPos
.Set( EXC_MAXCOL8
, EXC_MAXROW8
, EXC_MAXTAB8
); break;
124 default: DBG_ERROR_BIFF();
126 maMaxPos
.SetCol( ::std::min( maScMaxPos
.Col(), maXclMaxPos
.Col() ) );
127 maMaxPos
.SetRow( ::std::min( maScMaxPos
.Row(), maXclMaxPos
.Row() ) );
128 maMaxPos
.SetTab( ::std::min( maScMaxPos
.Tab(), maXclMaxPos
.Tab() ) );
130 // document URL and path
131 if( const SfxItemSet
* pItemSet
= mrMedium
.GetItemSet() )
132 if( const SfxStringItem
* pItem
= static_cast< const SfxStringItem
* >( pItemSet
->GetItem( SID_FILE_NAME
) ) )
133 maDocUrl
= pItem
->GetValue();
134 maBasePath
= maDocUrl
.copy( 0, maDocUrl
.lastIndexOf( '/' ) + 1 );
136 // extended document options - always own object, try to copy existing data from document
137 if( const ScExtDocOptions
* pOldDocOpt
= mrDoc
.GetExtDocOptions() )
138 mxExtDocOpt
.reset( new ScExtDocOptions( *pOldDocOpt
) );
140 mxExtDocOpt
.reset( new ScExtDocOptions
);
145 Reference
< frame::XDesktop2
> xFramesSupp
= frame::Desktop::create( ::comphelper::getProcessComponentContext() );
146 Reference
< XFrame
> xFrame( xFramesSupp
->getActiveFrame(), UNO_SET_THROW
);
147 Reference
< XDevice
> xDevice( xFrame
->getContainerWindow(), UNO_QUERY_THROW
);
148 DeviceInfo aDeviceInfo
= xDevice
->getInfo();
149 mfScreenPixelX
= (aDeviceInfo
.PixelPerMeterX
> 0) ? (100000.0 / aDeviceInfo
.PixelPerMeterX
) : 50.0;
150 mfScreenPixelY
= (aDeviceInfo
.PixelPerMeterY
> 0) ? (100000.0 / aDeviceInfo
.PixelPerMeterY
) : 50.0;
152 catch( const Exception
& e
)
154 SAL_WARN( "sc", "XclRootData::XclRootData - cannot get output device info: " << e
.Message
);
158 XclRootData::~XclRootData()
162 XclRoot::XclRoot( XclRootData
& rRootData
) :
165 #if defined(DBG_UTIL) && OSL_DEBUG_LEVEL > 0
170 mrData
.mxTracer
.reset( new XclTracer( GetDocUrl() ) );
173 XclRoot::XclRoot( const XclRoot
& rRoot
) :
174 mrData( rRoot
.mrData
)
176 #if defined(DBG_UTIL) && OSL_DEBUG_LEVEL > 0
183 #if defined(DBG_UTIL) && OSL_DEBUG_LEVEL > 0
188 XclRoot
& XclRoot::operator=( const XclRoot
& rRoot
)
190 (void)rRoot
; // avoid compiler warning
191 // allowed for assignment in derived classes - but test if the same root data is used
192 OSL_ENSURE( &mrData
== &rRoot
.mrData
, "XclRoot::operator= - incompatible root data" );
196 void XclRoot::SetTextEncoding( rtl_TextEncoding eTextEnc
)
198 if( eTextEnc
!= RTL_TEXTENCODING_DONTKNOW
)
199 mrData
.meTextEnc
= eTextEnc
;
202 void XclRoot::SetCharWidth( const XclFontData
& rFontData
)
204 mrData
.mnCharWidth
= 0;
205 if( OutputDevice
* pPrinter
= GetPrinter() )
207 vcl::Font
aFont( rFontData
.maName
, Size( 0, rFontData
.mnHeight
) );
208 aFont
.SetFamily( rFontData
.GetScFamily( GetTextEncoding() ) );
209 aFont
.SetCharSet( rFontData
.GetFontEncoding() );
210 aFont
.SetWeight( rFontData
.GetScWeight() );
211 pPrinter
->SetFont( aFont
);
212 mrData
.mnCharWidth
= pPrinter
->GetTextWidth( OUString('0') );
214 if( mrData
.mnCharWidth
<= 0 )
216 // #i48717# Win98 with HP LaserJet returns 0
217 SAL_WARN( "sc", "XclRoot::SetCharWidth - invalid character width (no printer?)" );
218 mrData
.mnCharWidth
= 11 * rFontData
.mnHeight
/ 20;
222 sal_Int32
XclRoot::GetHmmFromPixelX( double fPixelX
) const
224 return static_cast< sal_Int32
>( fPixelX
* mrData
.mfScreenPixelX
+ 0.5 );
227 sal_Int32
XclRoot::GetHmmFromPixelY( double fPixelY
) const
229 return static_cast< sal_Int32
>( fPixelY
* mrData
.mfScreenPixelY
+ 0.5 );
232 uno::Sequence
< beans::NamedValue
> XclRoot::RequestEncryptionData( ::comphelper::IDocPasswordVerifier
& rVerifier
) const
234 ::std::vector
< OUString
> aDefaultPasswords
;
235 aDefaultPasswords
.push_back( mrData
.maDefPassword
);
236 return ScfApiHelper::QueryEncryptionDataForMedium( mrData
.mrMedium
, rVerifier
, &aDefaultPasswords
);
239 bool XclRoot::HasVbaStorage() const
241 tools::SvRef
<SotStorage
> xRootStrg
= GetRootStorage();
242 return xRootStrg
.Is() && xRootStrg
->IsContained( EXC_STORAGE_VBA_PROJECT
);
245 tools::SvRef
<SotStorage
> XclRoot::OpenStorage( tools::SvRef
<SotStorage
> xStrg
, const OUString
& rStrgName
) const
247 return mrData
.mbExport
?
248 ScfTools::OpenStorageWrite( xStrg
, rStrgName
) :
249 ScfTools::OpenStorageRead( xStrg
, rStrgName
);
252 tools::SvRef
<SotStorage
> XclRoot::OpenStorage( const OUString
& rStrgName
) const
254 return OpenStorage( GetRootStorage(), rStrgName
);
257 tools::SvRef
<SotStorageStream
> XclRoot::OpenStream( tools::SvRef
<SotStorage
> xStrg
, const OUString
& rStrmName
) const
259 return mrData
.mbExport
?
260 ScfTools::OpenStorageStreamWrite( xStrg
, rStrmName
) :
261 ScfTools::OpenStorageStreamRead( xStrg
, rStrmName
);
264 tools::SvRef
<SotStorageStream
> XclRoot::OpenStream( const OUString
& rStrmName
) const
266 return OpenStream( GetRootStorage(), rStrmName
);
269 ScDocument
& XclRoot::GetDoc() const
274 ScDocument
* XclRoot::GetDocPtr() const
276 return &mrData
.mrDoc
;
279 SfxObjectShell
* XclRoot::GetDocShell() const
281 return GetDoc().GetDocumentShell();
284 ScModelObj
* XclRoot::GetDocModelObj() const
286 SfxObjectShell
* pDocShell
= GetDocShell();
287 return pDocShell
? ScModelObj::getImplementation( pDocShell
->GetModel() ) : 0;
290 OutputDevice
* XclRoot::GetPrinter() const
292 return GetDoc().GetRefDevice();
295 ScStyleSheetPool
& XclRoot::GetStyleSheetPool() const
297 return *GetDoc().GetStyleSheetPool();
300 ScRangeName
& XclRoot::GetNamedRanges() const
302 return *GetDoc().GetRangeName();
305 SdrPage
* XclRoot::GetSdrPage( SCTAB nScTab
) const
307 return ((nScTab
>= 0) && GetDoc().GetDrawLayer()) ?
308 GetDoc().GetDrawLayer()->GetPage( static_cast< sal_uInt16
>( nScTab
) ) : 0;
311 SvNumberFormatter
& XclRoot::GetFormatter() const
313 return *GetDoc().GetFormatTable();
316 DateTime
XclRoot::GetNullDate() const
318 return *GetFormatter().GetNullDate();
321 sal_uInt16
XclRoot::GetBaseYear() const
323 // return 1904 for 1904-01-01, and 1900 for 1899-12-30
324 return (GetNullDate().GetYear() == 1904) ? 1904 : 1900;
327 double XclRoot::GetDoubleFromDateTime( const DateTime
& rDateTime
) const
329 double fValue
= rDateTime
- GetNullDate();
330 // adjust dates before 1900-03-01 to get correct time values in the range [0.0,1.0)
331 if( rDateTime
< DateTime( Date( 1, 3, 1900 ) ) )
336 DateTime
XclRoot::GetDateTimeFromDouble( double fValue
) const
338 DateTime aDateTime
= GetNullDate() + fValue
;
339 // adjust dates before 1900-03-01 to get correct time values
340 if( aDateTime
< DateTime( Date( 1, 3, 1900 ) ) )
345 ScEditEngineDefaulter
& XclRoot::GetEditEngine() const
347 if( !mrData
.mxEditEngine
.get() )
349 mrData
.mxEditEngine
.reset( new ScEditEngineDefaulter( GetDoc().GetEnginePool() ) );
350 ScEditEngineDefaulter
& rEE
= *mrData
.mxEditEngine
;
351 rEE
.SetRefMapMode( MAP_100TH_MM
);
352 rEE
.SetEditTextObjectPool( GetDoc().GetEditPool() );
353 rEE
.SetUpdateMode( false );
354 rEE
.EnableUndo( false );
355 rEE
.SetControlWord( rEE
.GetControlWord() & ~EEControlBits::ALLOWBIGOBJS
);
357 return *mrData
.mxEditEngine
;
360 ScHeaderEditEngine
& XclRoot::GetHFEditEngine() const
362 if( !mrData
.mxHFEditEngine
.get() )
364 mrData
.mxHFEditEngine
.reset( new ScHeaderEditEngine( EditEngine::CreatePool(), true ) );
365 ScHeaderEditEngine
& rEE
= *mrData
.mxHFEditEngine
;
366 rEE
.SetRefMapMode( MAP_TWIP
); // headers/footers use twips as default metric
367 rEE
.SetUpdateMode( false );
368 rEE
.EnableUndo( false );
369 rEE
.SetControlWord( rEE
.GetControlWord() & ~EEControlBits::ALLOWBIGOBJS
);
371 // set Calc header/footer defaults
372 SfxItemSet
* pEditSet
= new SfxItemSet( rEE
.GetEmptyItemSet() );
373 SfxItemSet
aItemSet( *GetDoc().GetPool(), ATTR_PATTERN_START
, ATTR_PATTERN_END
);
374 ScPatternAttr::FillToEditItemSet( *pEditSet
, aItemSet
);
375 // FillToEditItemSet() adjusts font height to 1/100th mm, we need twips
376 pEditSet
->Put( aItemSet
.Get( ATTR_FONT_HEIGHT
), EE_CHAR_FONTHEIGHT
);
377 pEditSet
->Put( aItemSet
.Get( ATTR_CJK_FONT_HEIGHT
), EE_CHAR_FONTHEIGHT_CJK
);
378 pEditSet
->Put( aItemSet
.Get( ATTR_CTL_FONT_HEIGHT
), EE_CHAR_FONTHEIGHT_CTL
);
379 rEE
.SetDefaults( pEditSet
); // takes ownership
381 return *mrData
.mxHFEditEngine
;
384 EditEngine
& XclRoot::GetDrawEditEngine() const
386 if( !mrData
.mxDrawEditEng
.get() )
388 mrData
.mxDrawEditEng
.reset( new EditEngine( &GetDoc().GetDrawLayer()->GetItemPool() ) );
389 EditEngine
& rEE
= *mrData
.mxDrawEditEng
;
390 rEE
.SetRefMapMode( MAP_100TH_MM
);
391 rEE
.SetUpdateMode( false );
392 rEE
.EnableUndo( false );
393 rEE
.SetControlWord( rEE
.GetControlWord() & ~EEControlBits::ALLOWBIGOBJS
);
395 return *mrData
.mxDrawEditEng
;
398 XclFontPropSetHelper
& XclRoot::GetFontPropSetHelper() const
400 return *mrData
.mxFontPropSetHlp
;
403 XclChPropSetHelper
& XclRoot::GetChartPropSetHelper() const
405 return *mrData
.mxChPropSetHlp
;
408 ScExtDocOptions
& XclRoot::GetExtDocOptions() const
410 return *mrData
.mxExtDocOpt
;
413 XclTracer
& XclRoot::GetTracer() const
415 return *mrData
.mxTracer
;
418 /* vim:set shiftwidth=4 softtabstop=4 expandtab: */