1 /*************************************************************************
3 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
5 * Copyright 2008 by Sun Microsystems, Inc.
7 * OpenOffice.org - a multi-platform office productivity suite
9 * $RCSfile: worksheetfragment.cxx,v $
10 * $Revision: 1.5.4.5 $
12 * This file is part of OpenOffice.org.
14 * OpenOffice.org is free software: you can redistribute it and/or modify
15 * it under the terms of the GNU Lesser General Public License version 3
16 * only, as published by the Free Software Foundation.
18 * OpenOffice.org is distributed in the hope that it will be useful,
19 * but WITHOUT ANY WARRANTY; without even the implied warranty of
20 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
21 * GNU Lesser General Public License version 3 for more details
22 * (a copy is included in the LICENSE file that accompanied this code).
24 * You should have received a copy of the GNU Lesser General Public License
25 * version 3 along with OpenOffice.org. If not, see
26 * <http://www.openoffice.org/license.html>
27 * for a copy of the LGPLv3 License.
29 ************************************************************************/
31 #include "oox/xls/worksheetfragment.hxx"
32 #include "oox/helper/attributelist.hxx"
33 #include "oox/helper/recordinputstream.hxx"
34 #include "oox/core/filterbase.hxx"
35 #include "oox/core/relations.hxx"
36 #include "oox/xls/addressconverter.hxx"
37 #include "oox/xls/autofiltercontext.hxx"
38 #include "oox/xls/biffinputstream.hxx"
39 #include "oox/xls/commentsfragment.hxx"
40 #include "oox/xls/condformatcontext.hxx"
41 #include "oox/xls/drawingfragment.hxx"
42 #include "oox/xls/externallinkbuffer.hxx"
43 #include "oox/xls/pagesettings.hxx"
44 #include "oox/xls/pivottablebuffer.hxx"
45 #include "oox/xls/pivottablefragment.hxx"
46 #include "oox/xls/querytablefragment.hxx"
47 #include "oox/xls/scenariobuffer.hxx"
48 #include "oox/xls/scenariocontext.hxx"
49 #include "oox/xls/sheetdatacontext.hxx"
50 #include "oox/xls/tablefragment.hxx"
51 #include "oox/xls/viewsettings.hxx"
52 #include "oox/xls/workbooksettings.hxx"
53 #include "oox/xls/worksheetsettings.hxx"
55 using ::rtl::OUString
;
56 using ::rtl::OUStringBuffer
;
57 using ::com::sun::star::uno::Any
;
58 using ::com::sun::star::uno::Reference
;
59 using ::com::sun::star::uno::Exception
;
60 using ::com::sun::star::table::CellAddress
;
61 using ::com::sun::star::table::CellRangeAddress
;
62 using ::oox::core::ContextHandlerRef
;
63 using ::oox::core::RecordInfo
;
64 using ::oox::core::Relations
;
65 using ::oox::core::RelationsRef
;
70 // ============================================================================
74 const sal_uInt16 BIFF_COLINFO_HIDDEN
= 0x0001;
75 const sal_uInt16 BIFF_COLINFO_SHOWPHONETIC
= 0x0008;
76 const sal_uInt16 BIFF_COLINFO_COLLAPSED
= 0x1000;
78 const sal_uInt16 BIFF_DEFROW_CUSTOMHEIGHT
= 0x0001;
79 const sal_uInt16 BIFF_DEFROW_HIDDEN
= 0x0002;
80 const sal_uInt16 BIFF_DEFROW_THICKTOP
= 0x0004;
81 const sal_uInt16 BIFF_DEFROW_THICKBOTTOM
= 0x0008;
82 const sal_uInt16 BIFF2_DEFROW_DEFHEIGHT
= 0x8000;
83 const sal_uInt16 BIFF2_DEFROW_MASK
= 0x7FFF;
85 const sal_uInt32 BIFF_DATAVAL_STRINGLIST
= 0x00000080;
86 const sal_uInt32 BIFF_DATAVAL_ALLOWBLANK
= 0x00000100;
87 const sal_uInt32 BIFF_DATAVAL_NODROPDOWN
= 0x00000200;
88 const sal_uInt32 BIFF_DATAVAL_SHOWINPUT
= 0x00040000;
89 const sal_uInt32 BIFF_DATAVAL_SHOWERROR
= 0x00080000;
91 const sal_Int32 OOBIN_OLEOBJECT_CONTENT
= 1;
92 const sal_Int32 OOBIN_OLEOBJECT_ICON
= 4;
93 const sal_Int32 OOBIN_OLEOBJECT_ALWAYS
= 1;
94 const sal_Int32 OOBIN_OLEOBJECT_ONCALL
= 3;
95 const sal_uInt16 OOBIN_OLEOBJECT_LINKED
= 0x0001;
96 const sal_uInt16 OOBIN_OLEOBJECT_AUTOLOAD
= 0x0002;
100 // ============================================================================
102 OoxDataValidationsContext::OoxDataValidationsContext( OoxWorksheetFragmentBase
& rFragment
) :
103 OoxWorksheetContextBase( rFragment
)
107 ContextHandlerRef
OoxDataValidationsContext::onCreateContext( sal_Int32 nElement
, const AttributeList
& rAttribs
)
109 switch( getCurrentElement() )
111 case XLS_TOKEN( dataValidations
):
112 if( nElement
== XLS_TOKEN( dataValidation
) )
114 importDataValidation( rAttribs
);
118 case XLS_TOKEN( dataValidation
):
121 case XLS_TOKEN( formula1
):
122 case XLS_TOKEN( formula2
):
123 return this; // collect formulas in onEndElement()
132 ApiTokenSequence
lclImportDataValFormula( FormulaParser
& rParser
, const OUString
& rFormula
, const CellAddress
& rBaseAddress
)
134 TokensFormulaContext
aContext( true, false );
135 aContext
.setBaseAddress( rBaseAddress
);
136 rParser
.importFormula( aContext
, rFormula
);
137 return aContext
.getTokens();
142 void OoxDataValidationsContext::onEndElement( const OUString
& rChars
)
144 if( mxValModel
.get() ) switch( getCurrentElement() )
146 case XLS_TOKEN( formula1
):
147 mxValModel
->maTokens1
= lclImportDataValFormula(
148 getFormulaParser(), rChars
, mxValModel
->maRanges
.getBaseAddress() );
149 // process string list of a list validation (convert to list of string tokens)
150 if( mxValModel
->mnType
== XML_list
)
151 getFormulaParser().convertStringToStringList( mxValModel
->maTokens1
, ',', true );
153 case XLS_TOKEN( formula2
):
154 mxValModel
->maTokens2
= lclImportDataValFormula(
155 getFormulaParser(), rChars
, mxValModel
->maRanges
.getBaseAddress() );
157 case XLS_TOKEN( dataValidation
):
158 setValidation( *mxValModel
);
165 ContextHandlerRef
OoxDataValidationsContext::onCreateRecordContext( sal_Int32 nRecId
, RecordInputStream
& rStrm
)
167 if( nRecId
== OOBIN_ID_DATAVALIDATION
)
168 importDataValidation( rStrm
);
172 void OoxDataValidationsContext::importDataValidation( const AttributeList
& rAttribs
)
174 mxValModel
.reset( new ValidationModel
);
175 getAddressConverter().convertToCellRangeList( mxValModel
->maRanges
, rAttribs
.getString( XML_sqref
, OUString() ), getSheetIndex(), true );
176 mxValModel
->maInputTitle
= rAttribs
.getXString( XML_promptTitle
, OUString() );
177 mxValModel
->maInputMessage
= rAttribs
.getXString( XML_prompt
, OUString() );
178 mxValModel
->maErrorTitle
= rAttribs
.getXString( XML_errorTitle
, OUString() );
179 mxValModel
->maErrorMessage
= rAttribs
.getXString( XML_error
, OUString() );
180 mxValModel
->mnType
= rAttribs
.getToken( XML_type
, XML_none
);
181 mxValModel
->mnOperator
= rAttribs
.getToken( XML_operator
, XML_between
);
182 mxValModel
->mnErrorStyle
= rAttribs
.getToken( XML_errorStyle
, XML_stop
);
183 mxValModel
->mbShowInputMsg
= rAttribs
.getBool( XML_showInputMessage
, false );
184 mxValModel
->mbShowErrorMsg
= rAttribs
.getBool( XML_showErrorMessage
, false );
185 /* The attribute showDropDown@dataValidation is in fact a "suppress
186 dropdown" flag, as it was in the BIFF format! ECMA specification
187 and attribute name are plain wrong! */
188 mxValModel
->mbNoDropDown
= rAttribs
.getBool( XML_showDropDown
, false );
189 mxValModel
->mbAllowBlank
= rAttribs
.getBool( XML_allowBlank
, false );
192 void OoxDataValidationsContext::importDataValidation( RecordInputStream
& rStrm
)
194 ValidationModel aModel
;
197 BinRangeList aRanges
;
198 rStrm
>> nFlags
>> aRanges
>> aModel
.maErrorTitle
>> aModel
.maErrorMessage
>> aModel
.maInputTitle
>> aModel
.maInputMessage
;
200 // equal flags in BIFF and OOBIN
201 aModel
.setBinType( extractValue
< sal_uInt8
>( nFlags
, 0, 4 ) );
202 aModel
.setBinOperator( extractValue
< sal_uInt8
>( nFlags
, 20, 4 ) );
203 aModel
.setBinErrorStyle( extractValue
< sal_uInt8
>( nFlags
, 4, 3 ) );
204 aModel
.mbAllowBlank
= getFlag( nFlags
, BIFF_DATAVAL_ALLOWBLANK
);
205 aModel
.mbNoDropDown
= getFlag( nFlags
, BIFF_DATAVAL_NODROPDOWN
);
206 aModel
.mbShowInputMsg
= getFlag( nFlags
, BIFF_DATAVAL_SHOWINPUT
);
207 aModel
.mbShowErrorMsg
= getFlag( nFlags
, BIFF_DATAVAL_SHOWERROR
);
210 getAddressConverter().convertToCellRangeList( aModel
.maRanges
, aRanges
, getSheetIndex(), true );
212 // condition formula(s)
213 FormulaParser
& rParser
= getFormulaParser();
214 TokensFormulaContext
aContext( true, false );
215 aContext
.setBaseAddress( aModel
.maRanges
.getBaseAddress() );
216 rParser
.importFormula( aContext
, rStrm
);
217 aModel
.maTokens1
= aContext
.getTokens();
218 rParser
.importFormula( aContext
, rStrm
);
219 aModel
.maTokens2
= aContext
.getTokens();
220 // process string list of a list validation (convert to list of string tokens)
221 if( (aModel
.mnType
== XML_list
) && getFlag( nFlags
, BIFF_DATAVAL_STRINGLIST
) )
222 rParser
.convertStringToStringList( aModel
.maTokens1
, ',', true );
224 // set validation data
225 setValidation( aModel
);
228 // ============================================================================
230 OoxWorksheetFragment::OoxWorksheetFragment( const WorkbookHelper
& rHelper
,
231 const OUString
& rFragmentPath
, ISegmentProgressBarRef xProgressBar
, WorksheetType eSheetType
, sal_Int16 nSheet
) :
232 OoxWorksheetFragmentBase( rHelper
, rFragmentPath
, xProgressBar
, eSheetType
, nSheet
)
234 // import data tables related to this worksheet
235 RelationsRef xTableRels
= getRelations().getRelationsFromType( CREATE_OFFICEDOC_RELATIONSTYPE( "table" ) );
236 for( Relations::const_iterator aIt
= xTableRels
->begin(), aEnd
= xTableRels
->end(); aIt
!= aEnd
; ++aIt
)
237 importOoxFragment( new OoxTableFragment( *this, getFragmentPathFromRelation( aIt
->second
) ) );
239 // import comments related to this worksheet
240 OUString aCommentsFragmentPath
= getFragmentPathFromFirstType( CREATE_OFFICEDOC_RELATIONSTYPE( "comments" ) );
241 if( aCommentsFragmentPath
.getLength() > 0 )
242 importOoxFragment( new OoxCommentsFragment( *this, aCommentsFragmentPath
) );
245 // oox.core.ContextHandler2Helper interface -----------------------------------
247 ContextHandlerRef
OoxWorksheetFragment::onCreateContext( sal_Int32 nElement
, const AttributeList
& rAttribs
)
249 switch( getCurrentElement() )
251 case XML_ROOT_CONTEXT
: switch( getSheetType() )
253 case SHEETTYPE_WORKSHEET
: return (nElement
== XLS_TOKEN( worksheet
)) ? this : 0;
254 case SHEETTYPE_CHARTSHEET
: return 0;
255 case SHEETTYPE_MACROSHEET
: return (nElement
== XM_TOKEN( macrosheet
)) ? this : 0;
256 case SHEETTYPE_DIALOGSHEET
: return (nElement
== XM_TOKEN( dialogsheet
)) ? this : 0;
257 case SHEETTYPE_MODULESHEET
: return 0;
258 case SHEETTYPE_EMPTYSHEET
: return 0;
262 case XLS_TOKEN( worksheet
):
263 case XM_TOKEN( macrosheet
):
266 case XLS_TOKEN( sheetData
): return new OoxSheetDataContext( *this );
267 case XLS_TOKEN( autoFilter
): return new OoxAutoFilterContext( *this );
268 case XLS_TOKEN( conditionalFormatting
): return new OoxCondFormatContext( *this );
269 case XLS_TOKEN( dataValidations
): return new OoxDataValidationsContext( *this );
271 case XLS_TOKEN( sheetViews
):
272 case XLS_TOKEN( cols
):
273 case XLS_TOKEN( mergeCells
):
274 case XLS_TOKEN( hyperlinks
):
275 case XLS_TOKEN( rowBreaks
):
276 case XLS_TOKEN( colBreaks
):
277 case XLS_TOKEN( oleObjects
):
278 case XLS_TOKEN( controls
): return this;
280 case XLS_TOKEN( sheetPr
): getWorksheetSettings().importSheetPr( rAttribs
); return this;
281 case XLS_TOKEN( dimension
): importDimension( rAttribs
); break;
282 case XLS_TOKEN( sheetFormatPr
): importSheetFormatPr( rAttribs
); break;
283 case XLS_TOKEN( sheetProtection
): getWorksheetSettings().importSheetProtection( rAttribs
); break;
284 case XLS_TOKEN( phoneticPr
): getWorksheetSettings().importPhoneticPr( rAttribs
); break;
285 case XLS_TOKEN( printOptions
): getPageSettings().importPrintOptions( rAttribs
); break;
286 case XLS_TOKEN( pageMargins
): getPageSettings().importPageMargins( rAttribs
); break;
287 case XLS_TOKEN( pageSetup
): getPageSettings().importPageSetup( getRelations(), rAttribs
); break;
288 case XLS_TOKEN( headerFooter
): getPageSettings().importHeaderFooter( rAttribs
); return this;
289 case XLS_TOKEN( picture
): getPageSettings().importPicture( getRelations(), rAttribs
); break;
290 case XLS_TOKEN( drawing
): importDrawing( rAttribs
); break;
291 case XLS_TOKEN( legacyDrawing
): importLegacyDrawing( rAttribs
); break;
292 case XLS_TOKEN( scenarios
):
293 return new OoxScenariosContext( *this );
297 case XLS_TOKEN( sheetPr
):
300 // TODO: Treat tab color as a sheet setting later.
301 // case XLS_TOKEN( tabColor ): getWorksheetSettings().importTabColor( rAttribs ); break;
302 case XLS_TOKEN( tabColor
): getSheetViewSettings().importTabColor( rAttribs
); break;
303 case XLS_TOKEN( outlinePr
): getWorksheetSettings().importOutlinePr( rAttribs
); break;
304 case XLS_TOKEN( pageSetUpPr
): importPageSetUpPr( rAttribs
); break;
308 case XLS_TOKEN( sheetViews
):
311 case XLS_TOKEN( sheetView
): getSheetViewSettings().importSheetView( rAttribs
); return this;
314 case XLS_TOKEN( sheetView
):
317 case XLS_TOKEN( pane
): getSheetViewSettings().importPane( rAttribs
); break;
318 case XLS_TOKEN( selection
): getSheetViewSettings().importSelection( rAttribs
); break;
322 case XLS_TOKEN( cols
):
323 if( nElement
== XLS_TOKEN( col
) ) importCol( rAttribs
);
325 case XLS_TOKEN( mergeCells
):
326 if( nElement
== XLS_TOKEN( mergeCell
) ) importMergeCell( rAttribs
);
328 case XLS_TOKEN( hyperlinks
):
329 if( nElement
== XLS_TOKEN( hyperlink
) ) importHyperlink( rAttribs
);
331 case XLS_TOKEN( rowBreaks
):
332 if( nElement
== XLS_TOKEN( brk
) ) importBrk( rAttribs
, true );
334 case XLS_TOKEN( colBreaks
):
335 if( nElement
== XLS_TOKEN( brk
) ) importBrk( rAttribs
, false );
338 case XLS_TOKEN( headerFooter
):
341 case XLS_TOKEN( firstHeader
):
342 case XLS_TOKEN( firstFooter
):
343 case XLS_TOKEN( oddHeader
):
344 case XLS_TOKEN( oddFooter
):
345 case XLS_TOKEN( evenHeader
):
346 case XLS_TOKEN( evenFooter
): return this; // collect h/f contents in onEndElement()
350 case XLS_TOKEN( oleObjects
):
351 if( nElement
== XLS_TOKEN( oleObject
) ) importOleObject( rAttribs
);
353 case XLS_TOKEN( controls
):
354 if( nElement
== XLS_TOKEN( control
) ) importControl( rAttribs
);
360 void OoxWorksheetFragment::onEndElement( const OUString
& rChars
)
362 switch( getCurrentElement() )
364 case XLS_TOKEN( firstHeader
):
365 case XLS_TOKEN( firstFooter
):
366 case XLS_TOKEN( oddHeader
):
367 case XLS_TOKEN( oddFooter
):
368 case XLS_TOKEN( evenHeader
):
369 case XLS_TOKEN( evenFooter
):
370 getPageSettings().importHeaderFooterCharacters( rChars
, getCurrentElement() );
375 ContextHandlerRef
OoxWorksheetFragment::onCreateRecordContext( sal_Int32 nRecId
, RecordInputStream
& rStrm
)
377 switch( getCurrentElement() )
379 case XML_ROOT_CONTEXT
:
380 if( nRecId
== OOBIN_ID_WORKSHEET
) return this;
383 case OOBIN_ID_WORKSHEET
:
386 case OOBIN_ID_SHEETDATA
: return new OoxSheetDataContext( *this );
387 case OOBIN_ID_CONDFORMATTING
: return new OoxCondFormatContext( *this );
388 case OOBIN_ID_DATAVALIDATIONS
: return new OoxDataValidationsContext( *this );
390 case OOBIN_ID_SHEETVIEWS
:
392 case OOBIN_ID_MERGECELLS
:
393 case OOBIN_ID_ROWBREAKS
:
394 case OOBIN_ID_COLBREAKS
:
395 case OOBIN_ID_OLEOBJECTS
:
396 case OOBIN_ID_CONTROLS
: return this;
398 case OOBIN_ID_SHEETPR
: getWorksheetSettings().importSheetPr( rStrm
); break;
399 case OOBIN_ID_DIMENSION
: importDimension( rStrm
); break;
400 case OOBIN_ID_SHEETFORMATPR
: importSheetFormatPr( rStrm
); break;
401 case OOBIN_ID_HYPERLINK
: importHyperlink( rStrm
); break;
402 case OOBIN_ID_PAGEMARGINS
: getPageSettings().importPageMargins( rStrm
); break;
403 case OOBIN_ID_PAGESETUP
: getPageSettings().importPageSetup( getRelations(), rStrm
); break;
404 case OOBIN_ID_PRINTOPTIONS
: getPageSettings().importPrintOptions( rStrm
); break;
405 case OOBIN_ID_HEADERFOOTER
: getPageSettings().importHeaderFooter( rStrm
); break;
406 case OOBIN_ID_PICTURE
: getPageSettings().importPicture( getRelations(), rStrm
); break;
407 case OOBIN_ID_SHEETPROTECTION
: getWorksheetSettings().importSheetProtection( rStrm
); break;
408 case OOBIN_ID_PHONETICPR
: getWorksheetSettings().importPhoneticPr( rStrm
); break;
409 case OOBIN_ID_DRAWING
: importDrawing( rStrm
); break;
410 case OOBIN_ID_LEGACYDRAWING
: importLegacyDrawing( rStrm
); break;
411 case OOBIN_ID_SCENARIOS
:
412 return new OoxScenariosContext( *this );
416 case OOBIN_ID_SHEETVIEWS
:
419 case OOBIN_ID_SHEETVIEW
: getSheetViewSettings().importSheetView( rStrm
); return this;
422 case OOBIN_ID_SHEETVIEW
:
425 case OOBIN_ID_PANE
: getSheetViewSettings().importPane( rStrm
); break;
426 case OOBIN_ID_SELECTION
: getSheetViewSettings().importSelection( rStrm
); break;
431 if( nRecId
== OOBIN_ID_COL
) importCol( rStrm
);
433 case OOBIN_ID_MERGECELLS
:
434 if( nRecId
== OOBIN_ID_MERGECELL
) importMergeCell( rStrm
);
436 case OOBIN_ID_ROWBREAKS
:
437 if( nRecId
== OOBIN_ID_BRK
) importBrk( rStrm
, true );
439 case OOBIN_ID_COLBREAKS
:
440 if( nRecId
== OOBIN_ID_BRK
) importBrk( rStrm
, false );
442 case OOBIN_ID_OLEOBJECTS
:
443 if( nRecId
== OOBIN_ID_OLEOBJECT
) importOleObject( rStrm
);
445 case OOBIN_ID_CONTROLS
:
446 if( nRecId
== OOBIN_ID_CONTROL
) importControl( rStrm
);
452 // oox.core.FragmentHandler2 interface ----------------------------------------
454 const RecordInfo
* OoxWorksheetFragment::getRecordInfos() const
456 static const RecordInfo spRecInfos
[] =
458 { OOBIN_ID_CFRULE
, OOBIN_ID_CFRULE
+ 1 },
459 { OOBIN_ID_COLBREAKS
, OOBIN_ID_COLBREAKS
+ 1 },
460 { OOBIN_ID_COLORSCALE
, OOBIN_ID_COLORSCALE
+ 1 },
461 { OOBIN_ID_COLS
, OOBIN_ID_COLS
+ 1 },
462 { OOBIN_ID_CONDFORMATTING
, OOBIN_ID_CONDFORMATTING
+ 1 },
463 { OOBIN_ID_CONTROLS
, OOBIN_ID_CONTROLS
+ 2 },
464 { OOBIN_ID_CUSTOMSHEETVIEW
, OOBIN_ID_CUSTOMSHEETVIEW
+ 1 },
465 { OOBIN_ID_CUSTOMSHEETVIEWS
, OOBIN_ID_CUSTOMSHEETVIEWS
+ 3 },
466 { OOBIN_ID_DATABAR
, OOBIN_ID_DATABAR
+ 1 },
467 { OOBIN_ID_DATAVALIDATIONS
, OOBIN_ID_DATAVALIDATIONS
+ 1 },
468 { OOBIN_ID_HEADERFOOTER
, OOBIN_ID_HEADERFOOTER
+ 1 },
469 { OOBIN_ID_ICONSET
, OOBIN_ID_ICONSET
+ 1 },
470 { OOBIN_ID_MERGECELLS
, OOBIN_ID_MERGECELLS
+ 1 },
471 { OOBIN_ID_OLEOBJECTS
, OOBIN_ID_OLEOBJECTS
+ 2 },
472 { OOBIN_ID_ROW
, -1 },
473 { OOBIN_ID_ROWBREAKS
, OOBIN_ID_ROWBREAKS
+ 1 },
474 { OOBIN_ID_SCENARIO
, OOBIN_ID_SCENARIO
+ 1 },
475 { OOBIN_ID_SCENARIOS
, OOBIN_ID_SCENARIOS
+ 1 },
476 { OOBIN_ID_SHEETDATA
, OOBIN_ID_SHEETDATA
+ 1 },
477 { OOBIN_ID_SHEETVIEW
, OOBIN_ID_SHEETVIEW
+ 1 },
478 { OOBIN_ID_SHEETVIEWS
, OOBIN_ID_SHEETVIEWS
+ 1 },
479 { OOBIN_ID_TABLEPARTS
, OOBIN_ID_TABLEPARTS
+ 2 },
480 { OOBIN_ID_WORKSHEET
, OOBIN_ID_WORKSHEET
+ 1 },
486 void OoxWorksheetFragment::initializeImport()
488 // initial processing in base class WorksheetHelper
489 initializeWorksheetImport();
491 // import query table fragments related to this worksheet
492 RelationsRef xQueryRels
= getRelations().getRelationsFromType( CREATE_OFFICEDOC_RELATIONSTYPE( "queryTable" ) );
493 for( Relations::const_iterator aIt
= xQueryRels
->begin(), aEnd
= xQueryRels
->end(); aIt
!= aEnd
; ++aIt
)
494 importOoxFragment( new OoxQueryTableFragment( *this, getFragmentPathFromRelation( aIt
->second
) ) );
496 // import pivot table fragments related to this worksheet
497 RelationsRef xPivotRels
= getRelations().getRelationsFromType( CREATE_OFFICEDOC_RELATIONSTYPE( "pivotTable" ) );
498 for( Relations::const_iterator aIt
= xPivotRels
->begin(), aEnd
= xPivotRels
->end(); aIt
!= aEnd
; ++aIt
)
499 importOoxFragment( new OoxPivotTableFragment( *this, getFragmentPathFromRelation( aIt
->second
) ) );
502 void OoxWorksheetFragment::finalizeImport()
504 // final processing in base class WorksheetHelper
505 finalizeWorksheetImport();
508 // private --------------------------------------------------------------------
510 void OoxWorksheetFragment::importPageSetUpPr( const AttributeList
& rAttribs
)
512 // for whatever reason, this flag is still stored separated from the page settings
513 getPageSettings().setFitToPagesMode( rAttribs
.getBool( XML_fitToPage
, false ) );
516 void OoxWorksheetFragment::importDimension( const AttributeList
& rAttribs
)
518 CellRangeAddress aRange
;
519 getAddressConverter().convertToCellRangeUnchecked( aRange
, rAttribs
.getString( XML_ref
, OUString() ), getSheetIndex() );
520 setDimension( aRange
);
523 void OoxWorksheetFragment::importSheetFormatPr( const AttributeList
& rAttribs
)
525 // default column settings
526 setBaseColumnWidth( rAttribs
.getInteger( XML_baseColWidth
, 8 ) );
527 setDefaultColumnWidth( rAttribs
.getDouble( XML_defaultColWidth
, 0.0 ) );
528 // default row settings
529 setDefaultRowSettings(
530 rAttribs
.getDouble( XML_defaultRowHeight
, 0.0 ),
531 rAttribs
.getBool( XML_customHeight
, false ),
532 rAttribs
.getBool( XML_zeroHeight
, false ),
533 rAttribs
.getBool( XML_thickTop
, false ),
534 rAttribs
.getBool( XML_thickBottom
, false ) );
537 void OoxWorksheetFragment::importCol( const AttributeList
& rAttribs
)
540 aModel
.mnFirstCol
= rAttribs
.getInteger( XML_min
, -1 );
541 aModel
.mnLastCol
= rAttribs
.getInteger( XML_max
, -1 );
542 aModel
.mfWidth
= rAttribs
.getDouble( XML_width
, 0.0 );
543 aModel
.mnXfId
= rAttribs
.getInteger( XML_style
, -1 );
544 aModel
.mnLevel
= rAttribs
.getInteger( XML_outlineLevel
, 0 );
545 aModel
.mbShowPhonetic
= rAttribs
.getBool( XML_phonetic
, false );
546 aModel
.mbHidden
= rAttribs
.getBool( XML_hidden
, false );
547 aModel
.mbCollapsed
= rAttribs
.getBool( XML_collapsed
, false );
548 // set column properties in the current sheet
549 setColumnModel( aModel
);
552 void OoxWorksheetFragment::importMergeCell( const AttributeList
& rAttribs
)
554 CellRangeAddress aRange
;
555 if( getAddressConverter().convertToCellRange( aRange
, rAttribs
.getString( XML_ref
, OUString() ), getSheetIndex(), true, true ) )
556 setMergedRange( aRange
);
559 void OoxWorksheetFragment::importHyperlink( const AttributeList
& rAttribs
)
561 HyperlinkModel aModel
;
562 if( getAddressConverter().convertToCellRange( aModel
.maRange
, rAttribs
.getString( XML_ref
, OUString() ), getSheetIndex(), true, true ) )
564 aModel
.maTarget
= getRelations().getExternalTargetFromRelId( rAttribs
.getString( R_TOKEN( id
), OUString() ) );
565 aModel
.maLocation
= rAttribs
.getXString( XML_location
, OUString() );
566 aModel
.maDisplay
= rAttribs
.getXString( XML_display
, OUString() );
567 aModel
.maTooltip
= rAttribs
.getXString( XML_tooltip
, OUString() );
568 setHyperlink( aModel
);
572 void OoxWorksheetFragment::importBrk( const AttributeList
& rAttribs
, bool bRowBreak
)
574 PageBreakModel aModel
;
575 aModel
.mnColRow
= rAttribs
.getInteger( XML_id
, 0 );
576 aModel
.mnMin
= rAttribs
.getInteger( XML_id
, 0 );
577 aModel
.mnMax
= rAttribs
.getInteger( XML_id
, 0 );
578 aModel
.mbManual
= rAttribs
.getBool( XML_man
, false );
579 setPageBreak( aModel
, bRowBreak
);
582 void OoxWorksheetFragment::importDrawing( const AttributeList
& rAttribs
)
584 setDrawingPath( getFragmentPathFromRelId( rAttribs
.getString( R_TOKEN( id
), OUString() ) ) );
587 void OoxWorksheetFragment::importLegacyDrawing( const AttributeList
& rAttribs
)
589 setVmlDrawingPath( getFragmentPathFromRelId( rAttribs
.getString( R_TOKEN( id
), OUString() ) ) );
592 void OoxWorksheetFragment::importOleObject( const AttributeList
& rAttribs
)
594 ::oox::vml::OleObjectInfo aInfo
;
595 aInfo
.setShapeId( rAttribs
.getInteger( XML_shapeId
, 0 ) );
596 OSL_ENSURE( rAttribs
.hasAttribute( XML_link
) != rAttribs
.hasAttribute( R_TOKEN( id
) ),
597 "OoxWorksheetFragment::importOleObject - OLE object must be either linked or embedded" );
598 aInfo
.mbLinked
= rAttribs
.hasAttribute( XML_link
);
600 aInfo
.maTargetLink
= getFormulaParser().importOleTargetLink( rAttribs
.getString( XML_link
, OUString() ) );
601 else if( rAttribs
.hasAttribute( R_TOKEN( id
) ) )
602 importEmbeddedOleData( aInfo
.maEmbeddedData
, rAttribs
.getString( R_TOKEN( id
), OUString() ) );
603 aInfo
.maProgId
= rAttribs
.getString( XML_progId
, OUString() );
604 aInfo
.mbShowAsIcon
= rAttribs
.getToken( XML_dvAspect
, XML_DVASPECT_CONTENT
) == XML_DVASPECT_ICON
;
605 aInfo
.mbAutoUpdate
= rAttribs
.getToken( XML_oleUpdate
, XML_OLEUPDATE_ONCALL
) == XML_OLEUPDATE_ALWAYS
;
606 aInfo
.mbAutoLoad
= rAttribs
.getBool( XML_autoLoad
, false );
607 getVmlDrawing().registerOleObject( aInfo
);
610 void OoxWorksheetFragment::importControl( const AttributeList
& rAttribs
)
612 ::oox::vml::ControlInfo aInfo
;
613 aInfo
.setShapeId( rAttribs
.getInteger( XML_shapeId
, 0 ) );
614 aInfo
.maFragmentPath
= getFragmentPathFromRelId( rAttribs
.getString( R_TOKEN( id
), OUString() ) );
615 aInfo
.maName
= rAttribs
.getString( XML_name
, OUString() );
616 getVmlDrawing().registerControl( aInfo
);
619 void OoxWorksheetFragment::importDimension( RecordInputStream
& rStrm
)
622 aBinRange
.read( rStrm
);
623 CellRangeAddress aRange
;
624 getAddressConverter().convertToCellRangeUnchecked( aRange
, aBinRange
, getSheetIndex() );
625 setDimension( aRange
);
628 void OoxWorksheetFragment::importSheetFormatPr( RecordInputStream
& rStrm
)
630 sal_Int32 nDefaultWidth
;
631 sal_uInt16 nBaseWidth
, nDefaultHeight
, nFlags
;
632 rStrm
>> nDefaultWidth
>> nBaseWidth
>> nDefaultHeight
>> nFlags
;
635 setBaseColumnWidth( nBaseWidth
);
636 // default width is stored as 1/256th of a character in OOBIN, convert to entire character
637 setDefaultColumnWidth( static_cast< double >( nDefaultWidth
) / 256.0 );
638 // row height is in twips in OOBIN, convert to points; equal flags in BIFF and OOBIN
639 setDefaultRowSettings(
640 nDefaultHeight
/ 20.0,
641 getFlag( nFlags
, BIFF_DEFROW_CUSTOMHEIGHT
),
642 getFlag( nFlags
, BIFF_DEFROW_HIDDEN
),
643 getFlag( nFlags
, BIFF_DEFROW_THICKTOP
),
644 getFlag( nFlags
, BIFF_DEFROW_THICKBOTTOM
) );
647 void OoxWorksheetFragment::importCol( RecordInputStream
& rStrm
)
653 rStrm
>> aModel
.mnFirstCol
>> aModel
.mnLastCol
>> nWidth
>> aModel
.mnXfId
>> nFlags
;
655 // column indexes are 0-based in OOBIN, but ColumnModel expects 1-based
658 // width is stored as 1/256th of a character in OOBIN, convert to entire character
659 aModel
.mfWidth
= static_cast< double >( nWidth
) / 256.0;
660 // equal flags in BIFF and OOBIN
661 aModel
.mnLevel
= extractValue
< sal_Int32
>( nFlags
, 8, 3 );
662 aModel
.mbShowPhonetic
= getFlag( nFlags
, BIFF_COLINFO_SHOWPHONETIC
);
663 aModel
.mbHidden
= getFlag( nFlags
, BIFF_COLINFO_HIDDEN
);
664 aModel
.mbCollapsed
= getFlag( nFlags
, BIFF_COLINFO_COLLAPSED
);
665 // set column properties in the current sheet
666 setColumnModel( aModel
);
669 void OoxWorksheetFragment::importMergeCell( RecordInputStream
& rStrm
)
673 CellRangeAddress aRange
;
674 if( getAddressConverter().convertToCellRange( aRange
, aBinRange
, getSheetIndex(), true, true ) )
675 setMergedRange( aRange
);
678 void OoxWorksheetFragment::importHyperlink( RecordInputStream
& rStrm
)
682 HyperlinkModel aModel
;
683 if( getAddressConverter().convertToCellRange( aModel
.maRange
, aBinRange
, getSheetIndex(), true, true ) )
685 aModel
.maTarget
= getRelations().getExternalTargetFromRelId( rStrm
.readString() );
686 rStrm
>> aModel
.maLocation
>> aModel
.maTooltip
>> aModel
.maDisplay
;
687 setHyperlink( aModel
);
691 void OoxWorksheetFragment::importBrk( RecordInputStream
& rStrm
, bool bRowBreak
)
693 PageBreakModel aModel
;
695 rStrm
>> aModel
.mnColRow
>> aModel
.mnMin
>> aModel
.mnMax
>> nManual
;
696 aModel
.mbManual
= nManual
!= 0;
697 setPageBreak( aModel
, bRowBreak
);
700 void OoxWorksheetFragment::importDrawing( RecordInputStream
& rStrm
)
702 setDrawingPath( getFragmentPathFromRelId( rStrm
.readString() ) );
705 void OoxWorksheetFragment::importLegacyDrawing( RecordInputStream
& rStrm
)
707 setVmlDrawingPath( getFragmentPathFromRelId( rStrm
.readString() ) );
710 void OoxWorksheetFragment::importOleObject( RecordInputStream
& rStrm
)
712 ::oox::vml::OleObjectInfo aInfo
;
713 sal_Int32 nAspect
, nUpdateMode
, nShapeId
;
715 rStrm
>> nAspect
>> nUpdateMode
>> nShapeId
>> nFlags
>> aInfo
.maProgId
;
716 aInfo
.mbLinked
= getFlag( nFlags
, OOBIN_OLEOBJECT_LINKED
);
718 aInfo
.maTargetLink
= getFormulaParser().importOleTargetLink( rStrm
);
720 importEmbeddedOleData( aInfo
.maEmbeddedData
, rStrm
.readString() );
721 aInfo
.setShapeId( nShapeId
);
722 aInfo
.mbShowAsIcon
= nAspect
== OOBIN_OLEOBJECT_ICON
;
723 aInfo
.mbAutoUpdate
= nUpdateMode
== OOBIN_OLEOBJECT_ALWAYS
;
724 aInfo
.mbAutoLoad
= getFlag( nFlags
, OOBIN_OLEOBJECT_AUTOLOAD
);
725 getVmlDrawing().registerOleObject( aInfo
);
728 void OoxWorksheetFragment::importControl( RecordInputStream
& rStrm
)
730 ::oox::vml::ControlInfo aInfo
;
731 aInfo
.setShapeId( rStrm
.readInt32() );
732 aInfo
.maFragmentPath
= getFragmentPathFromRelId( rStrm
.readString() );
733 rStrm
>> aInfo
.maName
;
734 getVmlDrawing().registerControl( aInfo
);
737 void OoxWorksheetFragment::importEmbeddedOleData( StreamDataSequence
& orEmbeddedData
, const OUString
& rRelId
)
739 OUString aFragmentPath
= getFragmentPathFromRelId( rRelId
);
740 if( aFragmentPath
.getLength() > 0 )
741 getBaseFilter().importBinaryData( orEmbeddedData
, aFragmentPath
);
744 // ============================================================================
746 BiffWorksheetFragment::BiffWorksheetFragment( const BiffWorkbookFragmentBase
& rParent
, ISegmentProgressBarRef xProgressBar
, WorksheetType eSheetType
, sal_Int16 nSheet
) :
747 BiffWorksheetFragmentBase( rParent
, xProgressBar
, eSheetType
, nSheet
)
751 BiffWorksheetFragment::~BiffWorksheetFragment()
755 bool BiffWorksheetFragment::importFragment()
757 // initial processing in base class WorksheetHelper
758 initializeWorksheetImport();
760 // create a SheetDataContext object that implements cell import
761 BiffSheetDataContext
aSheetData( *this );
763 WorkbookSettings
& rWorkbookSett
= getWorkbookSettings();
764 WorksheetSettings
& rWorksheetSett
= getWorksheetSettings();
765 SheetViewSettings
& rSheetViewSett
= getSheetViewSettings();
766 CondFormatBuffer
& rCondFormats
= getCondFormats();
767 PageSettings
& rPageSett
= getPageSettings();
769 // process all record in this sheet fragment
770 while( mrStrm
.startNextRecord() && (mrStrm
.getRecId() != BIFF_ID_EOF
) )
774 // skip unknown embedded fragments (BOF/EOF blocks)
779 // cache base stream position to detect if record is already processed
780 sal_Int64 nStrmPos
= mrStrm
.tellBase();
781 sal_uInt16 nRecId
= mrStrm
.getRecId();
785 // records in all BIFF versions
786 case BIFF_ID_BOTTOMMARGIN
: rPageSett
.importBottomMargin( mrStrm
); break;
787 case BIFF_ID_CALCCOUNT
: rWorkbookSett
.importCalcCount( mrStrm
); break;
788 case BIFF_ID_CALCMODE
: rWorkbookSett
.importCalcMode( mrStrm
); break;
789 case BIFF_ID_DEFCOLWIDTH
: importDefColWidth(); break;
790 case BIFF_ID_DELTA
: rWorkbookSett
.importDelta( mrStrm
); break;
791 case BIFF2_ID_DIMENSION
: importDimension(); break;
792 case BIFF3_ID_DIMENSION
: importDimension(); break;
793 case BIFF_ID_FOOTER
: rPageSett
.importFooter( mrStrm
); break;
794 case BIFF_ID_HEADER
: rPageSett
.importHeader( mrStrm
); break;
795 case BIFF_ID_HORPAGEBREAKS
: importPageBreaks( true ); break;
796 case BIFF_ID_ITERATION
: rWorkbookSett
.importIteration( mrStrm
); break;
797 case BIFF_ID_LEFTMARGIN
: rPageSett
.importLeftMargin( mrStrm
); break;
798 case BIFF_ID_PANE
: rSheetViewSett
.importPane( mrStrm
); break;
799 case BIFF_ID_PASSWORD
: rWorksheetSett
.importPassword( mrStrm
); break;
800 case BIFF_ID_PRINTGRIDLINES
: rPageSett
.importPrintGridLines( mrStrm
); break;
801 case BIFF_ID_PRINTHEADERS
: rPageSett
.importPrintHeaders( mrStrm
); break;
802 case BIFF_ID_PROTECT
: rWorksheetSett
.importProtect( mrStrm
); break;
803 case BIFF_ID_REFMODE
: rWorkbookSett
.importRefMode( mrStrm
); break;
804 case BIFF_ID_RIGHTMARGIN
: rPageSett
.importRightMargin( mrStrm
); break;
805 case BIFF_ID_SELECTION
: rSheetViewSett
.importSelection( mrStrm
); break;
806 case BIFF_ID_TOPMARGIN
: rPageSett
.importTopMargin( mrStrm
); break;
807 case BIFF_ID_VERPAGEBREAKS
: importPageBreaks( false ); break;
809 // BIFF specific records
810 default: switch( getBiff() )
812 case BIFF2
: switch( nRecId
)
814 case BIFF_ID_COLUMNDEFAULT
: importColumnDefault(); break;
815 case BIFF_ID_COLWIDTH
: importColWidth(); break;
816 case BIFF2_ID_DEFROWHEIGHT
: importDefRowHeight(); break;
817 case BIFF2_ID_WINDOW2
: rSheetViewSett
.importWindow2( mrStrm
); break;
821 case BIFF3
: switch( nRecId
)
823 case BIFF_ID_COLINFO
: importColInfo(); break;
824 case BIFF_ID_DEFCOLWIDTH
: importDefColWidth(); break;
825 case BIFF3_ID_DEFROWHEIGHT
: importDefRowHeight(); break;
826 case BIFF_ID_HCENTER
: rPageSett
.importHorCenter( mrStrm
); break;
827 case BIFF_ID_OBJECTPROTECT
: rWorksheetSett
.importObjectProtect( mrStrm
); break;
828 case BIFF_ID_SAVERECALC
: rWorkbookSett
.importSaveRecalc( mrStrm
); break;
829 case BIFF_ID_SHEETPR
: rWorksheetSett
.importSheetPr( mrStrm
); break;
830 case BIFF_ID_UNCALCED
: rWorkbookSett
.importUncalced( mrStrm
); break;
831 case BIFF_ID_VCENTER
: rPageSett
.importVerCenter( mrStrm
); break;
832 case BIFF3_ID_WINDOW2
: rSheetViewSett
.importWindow2( mrStrm
); break;
837 case BIFF4
: switch( nRecId
)
839 case BIFF_ID_COLINFO
: importColInfo(); break;
840 case BIFF3_ID_DEFROWHEIGHT
: importDefRowHeight(); break;
841 case BIFF_ID_HCENTER
: rPageSett
.importHorCenter( mrStrm
); break;
842 case BIFF_ID_OBJECTPROTECT
: rWorksheetSett
.importObjectProtect( mrStrm
); break;
843 case BIFF_ID_PAGESETUP
: rPageSett
.importPageSetup( mrStrm
); break;
844 case BIFF_ID_SAVERECALC
: rWorkbookSett
.importSaveRecalc( mrStrm
); break;
845 case BIFF_ID_SHEETPR
: rWorksheetSett
.importSheetPr( mrStrm
); break;
846 case BIFF_ID_STANDARDWIDTH
: importStandardWidth(); break;
847 case BIFF_ID_UNCALCED
: rWorkbookSett
.importUncalced( mrStrm
); break;
848 case BIFF_ID_VCENTER
: rPageSett
.importVerCenter( mrStrm
); break;
849 case BIFF3_ID_WINDOW2
: rSheetViewSett
.importWindow2( mrStrm
); break;
853 case BIFF5
: switch( nRecId
)
855 case BIFF_ID_COLINFO
: importColInfo(); break;
856 case BIFF3_ID_DEFROWHEIGHT
: importDefRowHeight(); break;
857 case BIFF_ID_HCENTER
: rPageSett
.importHorCenter( mrStrm
); break;
858 case BIFF_ID_MERGEDCELLS
: importMergedCells(); break; // #i62300# also in BIFF5
859 case BIFF_ID_OBJECTPROTECT
: rWorksheetSett
.importObjectProtect( mrStrm
); break;
860 case BIFF_ID_PAGESETUP
: rPageSett
.importPageSetup( mrStrm
); break;
861 case BIFF_ID_PTDEFINITION
: importPTDefinition(); break;
862 case BIFF_ID_SAVERECALC
: rWorkbookSett
.importSaveRecalc( mrStrm
); break;
863 case BIFF_ID_SCENPROTECT
: rWorksheetSett
.importScenProtect( mrStrm
); break;
864 case BIFF_ID_SCL
: rSheetViewSett
.importScl( mrStrm
); break;
865 case BIFF_ID_SHEETPR
: rWorksheetSett
.importSheetPr( mrStrm
); break;
866 case BIFF_ID_STANDARDWIDTH
: importStandardWidth(); break;
867 case BIFF_ID_UNCALCED
: rWorkbookSett
.importUncalced( mrStrm
); break;
868 case BIFF_ID_VCENTER
: rPageSett
.importVerCenter( mrStrm
); break;
869 case BIFF3_ID_WINDOW2
: rSheetViewSett
.importWindow2( mrStrm
); break;
873 case BIFF8
: switch( nRecId
)
875 case BIFF_ID_CFHEADER
: rCondFormats
.importCfHeader( mrStrm
); break;
876 case BIFF_ID_COLINFO
: importColInfo(); break;
877 case BIFF_ID_DATAVALIDATION
: importDataValidation(); break;
878 case BIFF_ID_DATAVALIDATIONS
: importDataValidations(); break;
879 case BIFF3_ID_DEFROWHEIGHT
: importDefRowHeight(); break;
880 case BIFF_ID_HCENTER
: rPageSett
.importHorCenter( mrStrm
); break;
881 case BIFF_ID_HYPERLINK
: importHyperlink(); break;
882 case BIFF_ID_LABELRANGES
: importLabelRanges(); break;
883 case BIFF_ID_MERGEDCELLS
: importMergedCells(); break;
884 case BIFF_ID_OBJECTPROTECT
: rWorksheetSett
.importObjectProtect( mrStrm
); break;
885 case BIFF_ID_PAGESETUP
: rPageSett
.importPageSetup( mrStrm
); break;
886 case BIFF_ID_PHONETICPR
: rWorksheetSett
.importPhoneticPr( mrStrm
); break;
887 case BIFF_ID_PICTURE
: rPageSett
.importPicture( mrStrm
); break;
888 case BIFF_ID_PTDEFINITION
: importPTDefinition(); break;
889 case BIFF_ID_SAVERECALC
: rWorkbookSett
.importSaveRecalc( mrStrm
); break;
890 case BIFF_ID_SCENARIOS
: importScenarios(); break;
891 case BIFF_ID_SCENPROTECT
: rWorksheetSett
.importScenProtect( mrStrm
); break;
892 case BIFF_ID_SCL
: rSheetViewSett
.importScl( mrStrm
); break;
893 case BIFF_ID_SHEETPR
: rWorksheetSett
.importSheetPr( mrStrm
); break;
894 case BIFF_ID_SHEETPROTECTION
: rWorksheetSett
.importSheetProtection( mrStrm
); break;
895 case BIFF_ID_STANDARDWIDTH
: importStandardWidth(); break;
896 case BIFF_ID_UNCALCED
: rWorkbookSett
.importUncalced( mrStrm
); break;
897 case BIFF_ID_VCENTER
: rPageSett
.importVerCenter( mrStrm
); break;
898 case BIFF3_ID_WINDOW2
: rSheetViewSett
.importWindow2( mrStrm
); break;
902 case BIFF_UNKNOWN
: break;
906 // record not processed, try cell records
907 if( mrStrm
.tellBase() == nStrmPos
)
908 aSheetData
.importRecord();
909 // record still not processed, try pivot table records
910 if( mxPTContext
.get() && (mrStrm
.tellBase() == nStrmPos
) )
911 mxPTContext
->importRecord();
915 // final processing in base class WorksheetHelper
916 finalizeWorksheetImport();
917 return mrStrm
.getRecId() == BIFF_ID_EOF
;
920 // private --------------------------------------------------------------------
922 void BiffWorksheetFragment::importColInfo()
924 sal_uInt16 nFirstCol
, nLastCol
, nWidth
, nXfId
, nFlags
;
925 mrStrm
>> nFirstCol
>> nLastCol
>> nWidth
>> nXfId
>> nFlags
;
928 // column indexes are 0-based in BIFF, but ColumnModel expects 1-based
929 aModel
.mnFirstCol
= static_cast< sal_Int32
>( nFirstCol
) + 1;
930 aModel
.mnLastCol
= static_cast< sal_Int32
>( nLastCol
) + 1;
931 // width is stored as 1/256th of a character in BIFF, convert to entire character
932 aModel
.mfWidth
= static_cast< double >( nWidth
) / 256.0;
933 aModel
.mnXfId
= nXfId
;
934 aModel
.mnLevel
= extractValue
< sal_Int32
>( nFlags
, 8, 3 );
935 aModel
.mbShowPhonetic
= getFlag( nFlags
, BIFF_COLINFO_SHOWPHONETIC
);
936 aModel
.mbHidden
= getFlag( nFlags
, BIFF_COLINFO_HIDDEN
);
937 aModel
.mbCollapsed
= getFlag( nFlags
, BIFF_COLINFO_COLLAPSED
);
938 // set column properties in the current sheet
939 setColumnModel( aModel
);
942 void BiffWorksheetFragment::importColumnDefault()
944 sal_uInt16 nFirstCol
, nLastCol
, nXfId
;
945 mrStrm
>> nFirstCol
>> nLastCol
>> nXfId
;
946 setDefaultColumnFormat( nFirstCol
, nLastCol
, nXfId
);
949 void BiffWorksheetFragment::importColWidth()
951 sal_uInt8 nFirstCol
, nLastCol
;
953 mrStrm
>> nFirstCol
>> nLastCol
>> nWidth
;
956 // column indexes are 0-based in BIFF, but ColumnModel expects 1-based
957 aModel
.mnFirstCol
= static_cast< sal_Int32
>( nFirstCol
) + 1;
958 aModel
.mnLastCol
= static_cast< sal_Int32
>( nLastCol
) + 1;
959 // width is stored as 1/256th of a character in BIFF, convert to entire character
960 aModel
.mfWidth
= static_cast< double >( nWidth
) / 256.0;
961 // set column properties in the current sheet
962 setColumnModel( aModel
);
965 void BiffWorksheetFragment::importDefColWidth()
967 /* Stored as entire number of characters without padding pixels, which
968 will be added in setBaseColumnWidth(). Call has no effect, if a
969 width has already been set from the STANDARDWIDTH record. */
970 setBaseColumnWidth( mrStrm
.readuInt16() );
973 void BiffWorksheetFragment::importDefRowHeight()
975 sal_uInt16 nFlags
= BIFF_DEFROW_CUSTOMHEIGHT
, nHeight
;
976 if( getBiff() != BIFF2
)
979 if( getBiff() == BIFF2
)
980 nHeight
&= BIFF2_DEFROW_MASK
;
981 // row height is in twips in BIFF, convert to points
982 setDefaultRowSettings(
984 getFlag( nFlags
, BIFF_DEFROW_CUSTOMHEIGHT
),
985 getFlag( nFlags
, BIFF_DEFROW_HIDDEN
),
986 getFlag( nFlags
, BIFF_DEFROW_THICKTOP
),
987 getFlag( nFlags
, BIFF_DEFROW_THICKBOTTOM
) );
990 void BiffWorksheetFragment::importDataValidations()
995 //! TODO: invalidate object id in drawing object manager
1000 OUString
lclReadDataValMessage( BiffInputStream
& rStrm
)
1002 // empty strings are single NUL characters (string length is 1)
1003 OUString aMessage
= rStrm
.readUniString( true );
1004 if( (aMessage
.getLength() == 1) && (aMessage
[ 0 ] == 0) )
1005 aMessage
= OUString();
1009 ApiTokenSequence
lclReadDataValFormula( BiffInputStream
& rStrm
, FormulaParser
& rParser
)
1011 sal_uInt16 nFmlaSize
= rStrm
.readuInt16();
1013 // enable NUL characters, string list is single tStr token with NUL separators
1014 TokensFormulaContext
aContext( true, false, true );
1015 rParser
.importFormula( aContext
, rStrm
, &nFmlaSize
);
1016 return aContext
.getTokens();
1021 void BiffWorksheetFragment::importDataValidation()
1023 ValidationModel aModel
;
1028 aModel
.setBinType( extractValue
< sal_uInt8
>( nFlags
, 0, 4 ) );
1029 aModel
.setBinOperator( extractValue
< sal_uInt8
>( nFlags
, 20, 4 ) );
1030 aModel
.setBinErrorStyle( extractValue
< sal_uInt8
>( nFlags
, 4, 3 ) );
1031 aModel
.mbAllowBlank
= getFlag( nFlags
, BIFF_DATAVAL_ALLOWBLANK
);
1032 aModel
.mbNoDropDown
= getFlag( nFlags
, BIFF_DATAVAL_NODROPDOWN
);
1033 aModel
.mbShowInputMsg
= getFlag( nFlags
, BIFF_DATAVAL_SHOWINPUT
);
1034 aModel
.mbShowErrorMsg
= getFlag( nFlags
, BIFF_DATAVAL_SHOWERROR
);
1037 aModel
.maInputTitle
= lclReadDataValMessage( mrStrm
);
1038 aModel
.maErrorTitle
= lclReadDataValMessage( mrStrm
);
1039 aModel
.maInputMessage
= lclReadDataValMessage( mrStrm
);
1040 aModel
.maErrorMessage
= lclReadDataValMessage( mrStrm
);
1042 // condition formula(s)
1043 FormulaParser
& rParser
= getFormulaParser();
1044 aModel
.maTokens1
= lclReadDataValFormula( mrStrm
, rParser
);
1045 aModel
.maTokens2
= lclReadDataValFormula( mrStrm
, rParser
);
1046 // process string list of a list validation (convert to list of string tokens)
1047 if( (aModel
.mnType
== XML_list
) && getFlag( nFlags
, BIFF_DATAVAL_STRINGLIST
) )
1048 rParser
.convertStringToStringList( aModel
.maTokens1
, '\0', true );
1051 BinRangeList aRanges
;
1053 getAddressConverter().convertToCellRangeList( aModel
.maRanges
, aRanges
, getSheetIndex(), true );
1055 // set validation data
1056 setValidation( aModel
);
1059 void BiffWorksheetFragment::importDimension()
1062 aBinRange
.read( mrStrm
, true, (mrStrm
.getRecId() == BIFF3_ID_DIMENSION
) && (getBiff() == BIFF8
) );
1063 // first unused row/column index in BIFF, not last used
1064 if( aBinRange
.maFirst
.mnCol
< aBinRange
.maLast
.mnCol
) --aBinRange
.maLast
.mnCol
;
1065 if( aBinRange
.maFirst
.mnRow
< aBinRange
.maLast
.mnRow
) --aBinRange
.maLast
.mnRow
;
1067 CellRangeAddress aRange
;
1068 getAddressConverter().convertToCellRangeUnchecked( aRange
, aBinRange
, getSheetIndex() );
1069 setDimension( aRange
);
1072 void BiffWorksheetFragment::importHyperlink()
1074 HyperlinkModel aModel
;
1076 // read cell range for the hyperlink
1077 BinRange aBiffRange
;
1078 mrStrm
>> aBiffRange
;
1079 // #i80006# Excel silently ignores invalid hi-byte of column index (TODO: everywhere?)
1080 aBiffRange
.maFirst
.mnCol
&= 0xFF;
1081 aBiffRange
.maLast
.mnCol
&= 0xFF;
1082 if( !getAddressConverter().convertToCellRange( aModel
.maRange
, aBiffRange
, getSheetIndex(), true, true ) )
1085 // try to read the StdHlink data
1086 if( !::oox::ole::OleHelper::importStdHlink( aModel
, mrStrm
, getTextEncoding(), true ) )
1089 // try to read the optional following SCREENTIP record
1090 if( (mrStrm
.getNextRecId() == BIFF_ID_SCREENTIP
) && mrStrm
.startNextRecord() )
1092 mrStrm
.skip( 2 ); // repeated record id
1093 // the cell range, again
1094 mrStrm
>> aBiffRange
;
1095 CellRangeAddress aRange
;
1096 if( getAddressConverter().convertToCellRange( aRange
, aBiffRange
, getSheetIndex(), true, true ) &&
1097 (aRange
.StartColumn
== aModel
.maRange
.StartColumn
) &&
1098 (aRange
.StartRow
== aModel
.maRange
.StartRow
) &&
1099 (aRange
.EndColumn
== aModel
.maRange
.EndColumn
) &&
1100 (aRange
.EndRow
== aModel
.maRange
.EndRow
) )
1102 /* This time, we have no string length, no flag field, and a
1103 null-terminated 16-bit character array. */
1104 aModel
.maTooltip
= mrStrm
.readNulUnicodeArray();
1108 // store the hyperlink settings
1109 setHyperlink( aModel
);
1112 void BiffWorksheetFragment::importLabelRanges()
1114 BinRangeList aBiffRowRanges
, aBiffColRanges
;
1115 mrStrm
>> aBiffRowRanges
>> aBiffColRanges
;
1116 ApiCellRangeList aColRanges
, aRowRanges
;
1117 getAddressConverter().convertToCellRangeList( aColRanges
, aBiffColRanges
, getSheetIndex(), true );
1118 getAddressConverter().convertToCellRangeList( aRowRanges
, aBiffRowRanges
, getSheetIndex(), true );
1119 setLabelRanges( aColRanges
, aRowRanges
);
1122 void BiffWorksheetFragment::importMergedCells()
1124 BinRangeList aBiffRanges
;
1125 mrStrm
>> aBiffRanges
;
1126 ApiCellRangeList aRanges
;
1127 getAddressConverter().convertToCellRangeList( aRanges
, aBiffRanges
, getSheetIndex(), true );
1128 for( ApiCellRangeList::const_iterator aIt
= aRanges
.begin(), aEnd
= aRanges
.end(); aIt
!= aEnd
; ++aIt
)
1129 setMergedRange( *aIt
);
1132 void BiffWorksheetFragment::importPageBreaks( bool bRowBreak
)
1134 PageBreakModel aModel
;
1135 aModel
.mbManual
= true; // only manual breaks stored in BIFF
1136 bool bBiff8
= getBiff() == BIFF8
; // skip start/end columns or rows in BIFF8
1140 for( sal_uInt16 nIndex
= 0; !mrStrm
.isEof() && (nIndex
< nCount
); ++nIndex
)
1142 aModel
.mnColRow
= mrStrm
.readuInt16();
1143 setPageBreak( aModel
, bRowBreak
);
1149 void BiffWorksheetFragment::importPTDefinition()
1151 mxPTContext
.reset( new BiffPivotTableContext( *this, getPivotTables().createPivotTable() ) );
1152 mxPTContext
->importRecord();
1155 void BiffWorksheetFragment::importScenarios()
1157 getScenarios().createSheetScenarios( getSheetIndex() ).importScenarios( mrStrm
);
1160 void BiffWorksheetFragment::importStandardWidth()
1164 // width is stored as 1/256th of a character in BIFF, convert to entire character
1165 double fWidth
= static_cast< double >( nWidth
) / 256.0;
1166 // set as default width, will override the width from DEFCOLWIDTH record
1167 setDefaultColumnWidth( fWidth
);
1170 // ============================================================================