xref: /aoo42x/main/oox/source/xls/defnamesbuffer.cxx (revision dffa72de)
1ca5ec200SAndrew Rist /**************************************************************
2cdf0e10cSrcweir  *
3ca5ec200SAndrew Rist  * Licensed to the Apache Software Foundation (ASF) under one
4ca5ec200SAndrew Rist  * or more contributor license agreements.  See the NOTICE file
5ca5ec200SAndrew Rist  * distributed with this work for additional information
6ca5ec200SAndrew Rist  * regarding copyright ownership.  The ASF licenses this file
7ca5ec200SAndrew Rist  * to you under the Apache License, Version 2.0 (the
8ca5ec200SAndrew Rist  * "License"); you may not use this file except in compliance
9ca5ec200SAndrew Rist  * with the License.  You may obtain a copy of the License at
10ca5ec200SAndrew Rist  *
11ca5ec200SAndrew Rist  *   http://www.apache.org/licenses/LICENSE-2.0
12ca5ec200SAndrew Rist  *
13ca5ec200SAndrew Rist  * Unless required by applicable law or agreed to in writing,
14ca5ec200SAndrew Rist  * software distributed under the License is distributed on an
15ca5ec200SAndrew Rist  * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
16ca5ec200SAndrew Rist  * KIND, either express or implied.  See the License for the
17ca5ec200SAndrew Rist  * specific language governing permissions and limitations
18ca5ec200SAndrew Rist  * under the License.
19ca5ec200SAndrew Rist  *
20ca5ec200SAndrew Rist  *************************************************************/
21ca5ec200SAndrew Rist 
22ca5ec200SAndrew Rist 
23cdf0e10cSrcweir 
24cdf0e10cSrcweir #include "oox/xls/defnamesbuffer.hxx"
25cdf0e10cSrcweir 
26cdf0e10cSrcweir #include <com/sun/star/sheet/ComplexReference.hpp>
27cdf0e10cSrcweir #include <com/sun/star/sheet/ExternalReference.hpp>
28cdf0e10cSrcweir #include <com/sun/star/sheet/NamedRangeFlag.hpp>
29cdf0e10cSrcweir #include <com/sun/star/sheet/ReferenceFlags.hpp>
30cdf0e10cSrcweir #include <com/sun/star/sheet/SingleReference.hpp>
31cdf0e10cSrcweir #include <com/sun/star/sheet/XFormulaTokens.hpp>
32cdf0e10cSrcweir #include <com/sun/star/sheet/XPrintAreas.hpp>
33cdf0e10cSrcweir #include <rtl/ustrbuf.hxx>
34cdf0e10cSrcweir #include "oox/helper/attributelist.hxx"
35cdf0e10cSrcweir #include "oox/helper/containerhelper.hxx"
36cdf0e10cSrcweir #include "oox/helper/propertyset.hxx"
37cdf0e10cSrcweir #include "oox/xls/addressconverter.hxx"
38cdf0e10cSrcweir #include "oox/xls/biffinputstream.hxx"
39cdf0e10cSrcweir #include "oox/xls/externallinkbuffer.hxx"
40cdf0e10cSrcweir #include "oox/xls/formulaparser.hxx"
41cdf0e10cSrcweir #include "oox/xls/worksheetbuffer.hxx"
42cdf0e10cSrcweir 
43cdf0e10cSrcweir namespace oox {
44cdf0e10cSrcweir namespace xls {
45cdf0e10cSrcweir 
46cdf0e10cSrcweir // ============================================================================
47cdf0e10cSrcweir 
48cdf0e10cSrcweir using namespace ::com::sun::star::sheet;
49cdf0e10cSrcweir using namespace ::com::sun::star::table;
50cdf0e10cSrcweir using namespace ::com::sun::star::uno;
51cdf0e10cSrcweir 
52cdf0e10cSrcweir using ::rtl::OUString;
53cdf0e10cSrcweir using ::rtl::OUStringBuffer;
54cdf0e10cSrcweir 
55cdf0e10cSrcweir // ============================================================================
56cdf0e10cSrcweir 
57cdf0e10cSrcweir namespace {
58cdf0e10cSrcweir 
59cdf0e10cSrcweir const sal_uInt32 BIFF12_DEFNAME_HIDDEN      = 0x00000001;
60cdf0e10cSrcweir const sal_uInt32 BIFF12_DEFNAME_FUNC        = 0x00000002;
61cdf0e10cSrcweir const sal_uInt32 BIFF12_DEFNAME_VBNAME      = 0x00000004;
62cdf0e10cSrcweir const sal_uInt32 BIFF12_DEFNAME_MACRO       = 0x00000008;
63cdf0e10cSrcweir const sal_uInt32 BIFF12_DEFNAME_CALCEXP     = 0x00000010;
64cdf0e10cSrcweir const sal_uInt32 BIFF12_DEFNAME_BUILTIN     = 0x00000020;
65cdf0e10cSrcweir const sal_uInt32 BIFF12_DEFNAME_PUBLISHED   = 0x00008000;
66cdf0e10cSrcweir const sal_uInt32 BIFF12_DEFNAME_WBPARAM     = 0x00010000;
67cdf0e10cSrcweir 
68cdf0e10cSrcweir const sal_uInt16 BIFF_DEFNAME_HIDDEN        = 0x0001;
69cdf0e10cSrcweir const sal_uInt16 BIFF_DEFNAME_FUNC          = 0x0002;
70cdf0e10cSrcweir const sal_uInt16 BIFF_DEFNAME_VBNAME        = 0x0004;
71cdf0e10cSrcweir const sal_uInt16 BIFF_DEFNAME_MACRO         = 0x0008;
72cdf0e10cSrcweir const sal_uInt16 BIFF_DEFNAME_CALCEXP       = 0x0010;
73cdf0e10cSrcweir const sal_uInt16 BIFF_DEFNAME_BUILTIN       = 0x0020;
74cdf0e10cSrcweir const sal_uInt16 BIFF_DEFNAME_BIG           = 0x1000;
75cdf0e10cSrcweir 
76cdf0e10cSrcweir const sal_uInt8 BIFF2_DEFNAME_FUNC          = 0x02;     /// BIFF2 function/command flag.
77cdf0e10cSrcweir 
78cdf0e10cSrcweir const sal_uInt16 BIFF_DEFNAME_GLOBAL        = 0;        /// 0 = Globally defined name.
79cdf0e10cSrcweir 
80cdf0e10cSrcweir const sal_uInt16 BIFF_REFFLAG_COL1REL       = 0x0001;
81cdf0e10cSrcweir const sal_uInt16 BIFF_REFFLAG_ROW1REL       = 0x0002;
82cdf0e10cSrcweir const sal_uInt16 BIFF_REFFLAG_COL2REL       = 0x0004;
83cdf0e10cSrcweir const sal_uInt16 BIFF_REFFLAG_ROW2REL       = 0x0008;
84cdf0e10cSrcweir 
85cdf0e10cSrcweir // ----------------------------------------------------------------------------
86cdf0e10cSrcweir 
87cdf0e10cSrcweir const sal_Char* const spcLegacyPrefix = "Excel_BuiltIn_";
88cdf0e10cSrcweir const sal_Char* const spcOoxPrefix = "_xlnm.";
89cdf0e10cSrcweir 
90cdf0e10cSrcweir const sal_Char* const sppcBaseNames[] =
91cdf0e10cSrcweir {
92cdf0e10cSrcweir     "Consolidate_Area",
93cdf0e10cSrcweir     "Auto_Open",
94cdf0e10cSrcweir     "Auto_Close",
95cdf0e10cSrcweir     "Extract",
96cdf0e10cSrcweir     "Database",
97cdf0e10cSrcweir     "Criteria",
98cdf0e10cSrcweir     "Print_Area",
99cdf0e10cSrcweir     "Print_Titles",
100cdf0e10cSrcweir     "Recorder",
101cdf0e10cSrcweir     "Data_Form",
102cdf0e10cSrcweir     "Auto_Activate",
103cdf0e10cSrcweir     "Auto_Deactivate",
104cdf0e10cSrcweir     "Sheet_Title",
105cdf0e10cSrcweir     "_FilterDatabase"
106cdf0e10cSrcweir };
107cdf0e10cSrcweir 
108cdf0e10cSrcweir /** Localized names for _xlnm._FilterDatabase as used in BIFF5. */
109cdf0e10cSrcweir const sal_Char* const sppcFilterDbNames[] =
110cdf0e10cSrcweir {
111cdf0e10cSrcweir     "_FilterDatabase",      // English
112cdf0e10cSrcweir     "_FilterDatenbank"      // German
113cdf0e10cSrcweir };
114cdf0e10cSrcweir 
lclGetBaseName(sal_Unicode cBuiltinId)115cdf0e10cSrcweir OUString lclGetBaseName( sal_Unicode cBuiltinId )
116cdf0e10cSrcweir {
117cdf0e10cSrcweir     OSL_ENSURE( cBuiltinId < STATIC_ARRAY_SIZE( sppcBaseNames ), "lclGetBaseName - unsupported built-in identifier" );
118cdf0e10cSrcweir     OUStringBuffer aBuffer;
119cdf0e10cSrcweir     if( cBuiltinId < STATIC_ARRAY_SIZE( sppcBaseNames ) )
120cdf0e10cSrcweir         aBuffer.appendAscii( sppcBaseNames[ cBuiltinId ] );
121cdf0e10cSrcweir     else
122cdf0e10cSrcweir         aBuffer.append( static_cast< sal_Int32 >( cBuiltinId ) );
123cdf0e10cSrcweir     return aBuffer.makeStringAndClear();
124cdf0e10cSrcweir }
125cdf0e10cSrcweir 
lclGetPrefixedName(sal_Unicode cBuiltinId)126cdf0e10cSrcweir OUString lclGetPrefixedName( sal_Unicode cBuiltinId )
127cdf0e10cSrcweir {
128cdf0e10cSrcweir     return OUStringBuffer().appendAscii( spcOoxPrefix ).append( lclGetBaseName( cBuiltinId ) ).makeStringAndClear();
129cdf0e10cSrcweir }
130cdf0e10cSrcweir 
131cdf0e10cSrcweir /** returns the built-in name identifier from a perfixed built-in name, e.g. '_xlnm.Print_Area'. */
lclGetBuiltinIdFromPrefixedName(const OUString & rModelName)132cdf0e10cSrcweir sal_Unicode lclGetBuiltinIdFromPrefixedName( const OUString& rModelName )
133cdf0e10cSrcweir {
134cdf0e10cSrcweir     OUString aPrefix = OUString::createFromAscii( spcOoxPrefix );
135cdf0e10cSrcweir     sal_Int32 nPrefixLen = aPrefix.getLength();
136cdf0e10cSrcweir     if( rModelName.matchIgnoreAsciiCase( aPrefix ) )
137cdf0e10cSrcweir     {
138cdf0e10cSrcweir         for( sal_Unicode cBuiltinId = 0; cBuiltinId < STATIC_ARRAY_SIZE( sppcBaseNames ); ++cBuiltinId )
139cdf0e10cSrcweir         {
140cdf0e10cSrcweir             OUString aBaseName = lclGetBaseName( cBuiltinId );
141cdf0e10cSrcweir             sal_Int32 nBaseNameLen = aBaseName.getLength();
142cdf0e10cSrcweir             if( (rModelName.getLength() == nPrefixLen + nBaseNameLen) && rModelName.matchIgnoreAsciiCase( aBaseName, nPrefixLen ) )
143cdf0e10cSrcweir                 return cBuiltinId;
144cdf0e10cSrcweir         }
145cdf0e10cSrcweir     }
146cdf0e10cSrcweir     return BIFF_DEFNAME_UNKNOWN;
147cdf0e10cSrcweir }
148cdf0e10cSrcweir 
149cdf0e10cSrcweir /** returns the built-in name identifier from a built-in base name, e.g. 'Print_Area'. */
lclGetBuiltinIdFromBaseName(const OUString & rModelName)150cdf0e10cSrcweir sal_Unicode lclGetBuiltinIdFromBaseName( const OUString& rModelName )
151cdf0e10cSrcweir {
152cdf0e10cSrcweir     for( sal_Unicode cBuiltinId = 0; cBuiltinId < STATIC_ARRAY_SIZE( sppcBaseNames ); ++cBuiltinId )
153cdf0e10cSrcweir         if( rModelName.equalsIgnoreAsciiCaseAscii( sppcBaseNames[ cBuiltinId ] ) )
154cdf0e10cSrcweir             return cBuiltinId;
155cdf0e10cSrcweir     return BIFF_DEFNAME_UNKNOWN;
156cdf0e10cSrcweir }
157cdf0e10cSrcweir 
lclIsFilterDatabaseName(const OUString & rModelName)158cdf0e10cSrcweir bool lclIsFilterDatabaseName( const OUString& rModelName )
159cdf0e10cSrcweir {
160cdf0e10cSrcweir     for( const sal_Char* const* ppcName = sppcFilterDbNames; ppcName < STATIC_ARRAY_END( sppcFilterDbNames ); ++ppcName )
161cdf0e10cSrcweir         if( rModelName.equalsIgnoreAsciiCaseAscii( *ppcName ) )
162cdf0e10cSrcweir             return true;
163cdf0e10cSrcweir     return false;
164cdf0e10cSrcweir }
165cdf0e10cSrcweir 
lclGetUpcaseModelName(const OUString & rModelName)166cdf0e10cSrcweir OUString lclGetUpcaseModelName( const OUString& rModelName )
167cdf0e10cSrcweir {
168cdf0e10cSrcweir     // TODO: i18n?
169cdf0e10cSrcweir     return rModelName.toAsciiUpperCase();
170cdf0e10cSrcweir }
171cdf0e10cSrcweir 
lclConvertRefFlags(sal_Int32 & ornFlags,sal_Int32 & ornAbsPos,sal_Int32 & ornRelPos,sal_Int32 nBasePos,sal_Int32 nApiRelFlag,bool bRel)172cdf0e10cSrcweir void lclConvertRefFlags( sal_Int32& ornFlags, sal_Int32& ornAbsPos, sal_Int32& ornRelPos, sal_Int32 nBasePos, sal_Int32 nApiRelFlag, bool bRel )
173cdf0e10cSrcweir {
174cdf0e10cSrcweir     if( getFlag( ornFlags, nApiRelFlag ) && !bRel )
175cdf0e10cSrcweir     {
176cdf0e10cSrcweir         // convert relative to absolute
177cdf0e10cSrcweir         setFlag( ornFlags, nApiRelFlag, false );
178cdf0e10cSrcweir         ornAbsPos = nBasePos + ornRelPos;
179cdf0e10cSrcweir     }
180cdf0e10cSrcweir     else if( !getFlag( ornFlags, nApiRelFlag ) && bRel )
181cdf0e10cSrcweir     {
182cdf0e10cSrcweir         // convert absolute to relative
183cdf0e10cSrcweir         setFlag( ornFlags, nApiRelFlag, true );
184cdf0e10cSrcweir         ornRelPos = ornAbsPos - nBasePos;
185cdf0e10cSrcweir     }
186cdf0e10cSrcweir }
187cdf0e10cSrcweir 
lclConvertSingleRefFlags(SingleReference & orApiRef,const CellAddress & rBaseAddr,bool bColRel,bool bRowRel)188cdf0e10cSrcweir void lclConvertSingleRefFlags( SingleReference& orApiRef, const CellAddress& rBaseAddr, bool bColRel, bool bRowRel )
189cdf0e10cSrcweir {
190cdf0e10cSrcweir     using namespace ::com::sun::star::sheet::ReferenceFlags;
191cdf0e10cSrcweir     lclConvertRefFlags(
192cdf0e10cSrcweir         orApiRef.Flags, orApiRef.Column, orApiRef.RelativeColumn,
193cdf0e10cSrcweir         rBaseAddr.Column, COLUMN_RELATIVE, bColRel );
194cdf0e10cSrcweir     lclConvertRefFlags(
195cdf0e10cSrcweir         orApiRef.Flags, orApiRef.Row, orApiRef.RelativeRow,
196cdf0e10cSrcweir         rBaseAddr.Row, ROW_RELATIVE, bRowRel );
197cdf0e10cSrcweir }
198cdf0e10cSrcweir 
lclConvertReference(const Any & rRefAny,const CellAddress & rBaseAddr,sal_uInt16 nRelFlags)199cdf0e10cSrcweir Any lclConvertReference( const Any& rRefAny, const CellAddress& rBaseAddr, sal_uInt16 nRelFlags )
200cdf0e10cSrcweir {
201cdf0e10cSrcweir     if( rRefAny.has< SingleReference >() && !getFlag( nRelFlags, BIFF_REFFLAG_COL2REL ) && !getFlag( nRelFlags, BIFF_REFFLAG_ROW2REL ) )
202cdf0e10cSrcweir     {
203cdf0e10cSrcweir         SingleReference aApiRef;
204cdf0e10cSrcweir         rRefAny >>= aApiRef;
205cdf0e10cSrcweir         lclConvertSingleRefFlags( aApiRef, rBaseAddr, getFlag( nRelFlags, BIFF_REFFLAG_COL1REL ), getFlag( nRelFlags, BIFF_REFFLAG_ROW1REL ) );
206cdf0e10cSrcweir         return Any( aApiRef );
207cdf0e10cSrcweir     }
208cdf0e10cSrcweir     if( rRefAny.has< ComplexReference >() )
209cdf0e10cSrcweir     {
210cdf0e10cSrcweir         ComplexReference aApiRef;
211cdf0e10cSrcweir         rRefAny >>= aApiRef;
212cdf0e10cSrcweir         lclConvertSingleRefFlags( aApiRef.Reference1, rBaseAddr, getFlag( nRelFlags, BIFF_REFFLAG_COL1REL ), getFlag( nRelFlags, BIFF_REFFLAG_ROW1REL ) );
213cdf0e10cSrcweir         lclConvertSingleRefFlags( aApiRef.Reference2, rBaseAddr, getFlag( nRelFlags, BIFF_REFFLAG_COL2REL ), getFlag( nRelFlags, BIFF_REFFLAG_ROW2REL ) );
214cdf0e10cSrcweir         return Any( aApiRef );
215cdf0e10cSrcweir     }
216cdf0e10cSrcweir     return Any();
217cdf0e10cSrcweir }
218cdf0e10cSrcweir 
219cdf0e10cSrcweir } // namespace
220cdf0e10cSrcweir 
221cdf0e10cSrcweir // ============================================================================
222cdf0e10cSrcweir 
DefinedNameModel()223cdf0e10cSrcweir DefinedNameModel::DefinedNameModel() :
224cdf0e10cSrcweir     mnSheet( -1 ),
225cdf0e10cSrcweir     mnFuncGroupId( -1 ),
226cdf0e10cSrcweir     mbMacro( false ),
227cdf0e10cSrcweir     mbFunction( false ),
228cdf0e10cSrcweir     mbVBName( false ),
229cdf0e10cSrcweir     mbHidden( false )
230cdf0e10cSrcweir {
231cdf0e10cSrcweir }
232cdf0e10cSrcweir 
233cdf0e10cSrcweir // ============================================================================
234cdf0e10cSrcweir 
DefinedNameBase(const WorkbookHelper & rHelper)235cdf0e10cSrcweir DefinedNameBase::DefinedNameBase( const WorkbookHelper& rHelper ) :
236cdf0e10cSrcweir     WorkbookHelper( rHelper )
237cdf0e10cSrcweir {
238cdf0e10cSrcweir }
239cdf0e10cSrcweir 
getUpcaseModelName() const240cdf0e10cSrcweir const OUString& DefinedNameBase::getUpcaseModelName() const
241cdf0e10cSrcweir {
242cdf0e10cSrcweir     if( maUpModelName.getLength() == 0 )
243cdf0e10cSrcweir         maUpModelName = lclGetUpcaseModelName( maModel.maName );
244cdf0e10cSrcweir     return maUpModelName;
245cdf0e10cSrcweir }
246cdf0e10cSrcweir 
getReference(const CellAddress & rBaseAddr) const247cdf0e10cSrcweir Any DefinedNameBase::getReference( const CellAddress& rBaseAddr ) const
248cdf0e10cSrcweir {
249cdf0e10cSrcweir     if( maRefAny.hasValue() && (maModel.maName.getLength() >= 2) && (maModel.maName[ 0 ] == '\x01') )
250cdf0e10cSrcweir     {
251cdf0e10cSrcweir         sal_Unicode cFlagsChar = getUpcaseModelName()[ 1 ];
252cdf0e10cSrcweir         if( ('A' <= cFlagsChar) && (cFlagsChar <= 'P') )
253cdf0e10cSrcweir         {
254cdf0e10cSrcweir             sal_uInt16 nRelFlags = static_cast< sal_uInt16 >( cFlagsChar - 'A' );
255cdf0e10cSrcweir             if( maRefAny.has< ExternalReference >() )
256cdf0e10cSrcweir             {
257cdf0e10cSrcweir                 ExternalReference aApiExtRef;
258cdf0e10cSrcweir                 maRefAny >>= aApiExtRef;
259cdf0e10cSrcweir                 Any aRefAny = lclConvertReference( aApiExtRef.Reference, rBaseAddr, nRelFlags );
260cdf0e10cSrcweir                 if( aRefAny.hasValue() )
261cdf0e10cSrcweir                 {
262cdf0e10cSrcweir                     aApiExtRef.Reference <<= aRefAny;
263cdf0e10cSrcweir                     return Any( aApiExtRef );
264cdf0e10cSrcweir                 }
265cdf0e10cSrcweir             }
266cdf0e10cSrcweir             else
267cdf0e10cSrcweir             {
268cdf0e10cSrcweir                 return lclConvertReference( maRefAny, rBaseAddr, nRelFlags );
269cdf0e10cSrcweir             }
270cdf0e10cSrcweir         }
271cdf0e10cSrcweir     }
272cdf0e10cSrcweir     return Any();
273cdf0e10cSrcweir }
274cdf0e10cSrcweir 
importOoxFormula(sal_Int16 nBaseSheet)275cdf0e10cSrcweir ApiTokenSequence DefinedNameBase::importOoxFormula( sal_Int16 nBaseSheet )
276cdf0e10cSrcweir {
277cdf0e10cSrcweir     return (maModel.maFormula.getLength() > 0) ?
278cdf0e10cSrcweir         getFormulaParser().importFormula( CellAddress( nBaseSheet, 0, 0 ), maModel.maFormula ) :
279cdf0e10cSrcweir         getFormulaParser().convertErrorToFormula( BIFF_ERR_NAME );
280cdf0e10cSrcweir }
281cdf0e10cSrcweir 
importBiff12Formula(sal_Int16 nBaseSheet,SequenceInputStream & rStrm)282cdf0e10cSrcweir ApiTokenSequence DefinedNameBase::importBiff12Formula( sal_Int16 nBaseSheet, SequenceInputStream& rStrm )
283cdf0e10cSrcweir {
284cdf0e10cSrcweir     return getFormulaParser().importFormula( CellAddress( nBaseSheet, 0, 0 ), FORMULATYPE_DEFINEDNAME, rStrm );
285cdf0e10cSrcweir }
286cdf0e10cSrcweir 
importBiffFormula(sal_Int16 nBaseSheet,BiffInputStream & rStrm,const sal_uInt16 * pnFmlaSize)287cdf0e10cSrcweir ApiTokenSequence DefinedNameBase::importBiffFormula( sal_Int16 nBaseSheet, BiffInputStream& rStrm, const sal_uInt16* pnFmlaSize )
288cdf0e10cSrcweir {
289cdf0e10cSrcweir     return (!pnFmlaSize || (*pnFmlaSize > 0)) ?
290cdf0e10cSrcweir         getFormulaParser().importFormula( CellAddress( nBaseSheet, 0, 0 ), FORMULATYPE_DEFINEDNAME, rStrm, pnFmlaSize ) :
291cdf0e10cSrcweir         getFormulaParser().convertErrorToFormula( BIFF_ERR_NAME );
292cdf0e10cSrcweir }
293cdf0e10cSrcweir 
extractReference(const ApiTokenSequence & rTokens)294cdf0e10cSrcweir void DefinedNameBase::extractReference( const ApiTokenSequence& rTokens )
295cdf0e10cSrcweir {
296cdf0e10cSrcweir     OSL_ENSURE( (getFilterType() == FILTER_BIFF) && (getBiff() <= BIFF4), "DefinedNameBase::extractReference - unexpected call" );
297cdf0e10cSrcweir     maRefAny = getFormulaParser().extractReference( rTokens );
298cdf0e10cSrcweir }
299cdf0e10cSrcweir 
300cdf0e10cSrcweir // ============================================================================
301cdf0e10cSrcweir 
DefinedName(const WorkbookHelper & rHelper)302cdf0e10cSrcweir DefinedName::DefinedName( const WorkbookHelper& rHelper ) :
303cdf0e10cSrcweir     DefinedNameBase( rHelper ),
304cdf0e10cSrcweir     mnTokenIndex( -1 ),
305cdf0e10cSrcweir     mcBuiltinId( BIFF_DEFNAME_UNKNOWN ),
306cdf0e10cSrcweir     mnFmlaSize( 0 )
307cdf0e10cSrcweir {
308cdf0e10cSrcweir }
309cdf0e10cSrcweir 
importDefinedName(const AttributeList & rAttribs)310cdf0e10cSrcweir void DefinedName::importDefinedName( const AttributeList& rAttribs )
311cdf0e10cSrcweir {
312cdf0e10cSrcweir     maModel.maName        = rAttribs.getXString( XML_name, OUString() );
313cdf0e10cSrcweir     maModel.mnSheet       = rAttribs.getInteger( XML_localSheetId, -1 );
314cdf0e10cSrcweir     maModel.mnFuncGroupId = rAttribs.getInteger( XML_functionGroupId, -1 );
315cdf0e10cSrcweir     maModel.mbMacro       = rAttribs.getBool( XML_xlm, false );
316cdf0e10cSrcweir     maModel.mbFunction    = rAttribs.getBool( XML_function, false );
317cdf0e10cSrcweir     maModel.mbVBName      = rAttribs.getBool( XML_vbProcedure, false );
318cdf0e10cSrcweir     maModel.mbHidden      = rAttribs.getBool( XML_hidden, false );
319cdf0e10cSrcweir     mnCalcSheet = (maModel.mnSheet >= 0) ? getWorksheets().getCalcSheetIndex( maModel.mnSheet ) : -1;
320cdf0e10cSrcweir 
321cdf0e10cSrcweir     /*  Detect built-in state from name itself, there is no built-in flag.
322cdf0e10cSrcweir         Built-in names are prexixed with '_xlnm.' instead. */
323cdf0e10cSrcweir     mcBuiltinId = lclGetBuiltinIdFromPrefixedName( maModel.maName );
324cdf0e10cSrcweir }
325cdf0e10cSrcweir 
setFormula(const OUString & rFormula)326cdf0e10cSrcweir void DefinedName::setFormula( const OUString& rFormula )
327cdf0e10cSrcweir {
328cdf0e10cSrcweir     maModel.maFormula = rFormula;
329cdf0e10cSrcweir }
330cdf0e10cSrcweir 
importDefinedName(SequenceInputStream & rStrm)331cdf0e10cSrcweir void DefinedName::importDefinedName( SequenceInputStream& rStrm )
332cdf0e10cSrcweir {
333cdf0e10cSrcweir     sal_uInt32 nFlags;
334cdf0e10cSrcweir     rStrm >> nFlags;
335cdf0e10cSrcweir     rStrm.skip( 1 );    // keyboard shortcut
336cdf0e10cSrcweir     rStrm >> maModel.mnSheet >> maModel.maName;
337cdf0e10cSrcweir     mnCalcSheet = (maModel.mnSheet >= 0) ? getWorksheets().getCalcSheetIndex( maModel.mnSheet ) : -1;
338cdf0e10cSrcweir 
339cdf0e10cSrcweir     // macro function/command, hidden flag
340cdf0e10cSrcweir     maModel.mnFuncGroupId = extractValue< sal_Int32 >( nFlags, 6, 9 );
341cdf0e10cSrcweir     maModel.mbMacro       = getFlag( nFlags, BIFF12_DEFNAME_MACRO );
342cdf0e10cSrcweir     maModel.mbFunction    = getFlag( nFlags, BIFF12_DEFNAME_FUNC );
343cdf0e10cSrcweir     maModel.mbVBName      = getFlag( nFlags, BIFF12_DEFNAME_VBNAME );
344cdf0e10cSrcweir     maModel.mbHidden      = getFlag( nFlags, BIFF12_DEFNAME_HIDDEN );
345cdf0e10cSrcweir 
346cdf0e10cSrcweir     // get built-in name index from name
347cdf0e10cSrcweir     if( getFlag( nFlags, BIFF12_DEFNAME_BUILTIN ) )
348cdf0e10cSrcweir         mcBuiltinId = lclGetBuiltinIdFromBaseName( maModel.maName );
349cdf0e10cSrcweir 
350cdf0e10cSrcweir     // store token array data
351cdf0e10cSrcweir     sal_Int64 nRecPos = rStrm.tell();
352cdf0e10cSrcweir     sal_Int32 nFmlaSize = rStrm.readInt32();
353cdf0e10cSrcweir     rStrm.skip( nFmlaSize );
354cdf0e10cSrcweir     sal_Int32 nAddDataSize = rStrm.readInt32();
355cdf0e10cSrcweir     if( !rStrm.isEof() && (nFmlaSize > 0) && (nAddDataSize >= 0) && (rStrm.getRemaining() >= nAddDataSize) )
356cdf0e10cSrcweir     {
357cdf0e10cSrcweir         sal_Int32 nTotalSize = 8 + nFmlaSize + nAddDataSize;
358cdf0e10cSrcweir         mxFormula.reset( new StreamDataSequence );
359cdf0e10cSrcweir         rStrm.seek( nRecPos );
360cdf0e10cSrcweir         rStrm.readData( *mxFormula, nTotalSize );
361cdf0e10cSrcweir     }
362cdf0e10cSrcweir }
363cdf0e10cSrcweir 
importDefinedName(BiffInputStream & rStrm,sal_Int16 nCalcSheet)364cdf0e10cSrcweir void DefinedName::importDefinedName( BiffInputStream& rStrm, sal_Int16 nCalcSheet )
365cdf0e10cSrcweir {
366cdf0e10cSrcweir     BiffType eBiff = getBiff();
367cdf0e10cSrcweir     sal_uInt16 nFlags = 0;
368cdf0e10cSrcweir     sal_Int16 nRefId = BIFF_DEFNAME_GLOBAL;
369cdf0e10cSrcweir     sal_Int16 nTabId = BIFF_DEFNAME_GLOBAL;
370cdf0e10cSrcweir     sal_uInt8 nNameLen = 0, nShortCut = 0;
371cdf0e10cSrcweir 
372cdf0e10cSrcweir     switch( eBiff )
373cdf0e10cSrcweir     {
374cdf0e10cSrcweir         case BIFF2:
375cdf0e10cSrcweir         {
376cdf0e10cSrcweir             sal_uInt8 nFlagsBiff2;
377cdf0e10cSrcweir             rStrm >> nFlagsBiff2;
378cdf0e10cSrcweir             rStrm.skip( 1 );
379cdf0e10cSrcweir             rStrm >> nShortCut >> nNameLen;
380cdf0e10cSrcweir             mnFmlaSize = rStrm.readuInt8();
381cdf0e10cSrcweir             setFlag( nFlags, BIFF_DEFNAME_FUNC, getFlag( nFlagsBiff2, BIFF2_DEFNAME_FUNC ) );
382cdf0e10cSrcweir             maModel.maName = rStrm.readCharArrayUC( nNameLen, getTextEncoding(), true );
383cdf0e10cSrcweir         }
384cdf0e10cSrcweir         break;
385cdf0e10cSrcweir         case BIFF3:
386cdf0e10cSrcweir         case BIFF4:
387cdf0e10cSrcweir             rStrm >> nFlags >> nShortCut >> nNameLen >> mnFmlaSize;
388cdf0e10cSrcweir             maModel.maName = rStrm.readCharArrayUC( nNameLen, getTextEncoding(), true );
389cdf0e10cSrcweir         break;
390cdf0e10cSrcweir         case BIFF5:
391cdf0e10cSrcweir             rStrm >> nFlags >> nShortCut >> nNameLen >> mnFmlaSize >> nRefId >> nTabId;
392cdf0e10cSrcweir             rStrm.skip( 4 );
393cdf0e10cSrcweir             maModel.maName = rStrm.readCharArrayUC( nNameLen, getTextEncoding(), true );
394cdf0e10cSrcweir         break;
395cdf0e10cSrcweir         case BIFF8:
396cdf0e10cSrcweir             rStrm >> nFlags >> nShortCut >> nNameLen >> mnFmlaSize >> nRefId >> nTabId;
397cdf0e10cSrcweir             rStrm.skip( 4 );
398cdf0e10cSrcweir             maModel.maName = rStrm.readUniStringBody( nNameLen, true );
399cdf0e10cSrcweir         break;
400cdf0e10cSrcweir         case BIFF_UNKNOWN: break;
401cdf0e10cSrcweir     }
402cdf0e10cSrcweir 
403cdf0e10cSrcweir     // macro function/command, hidden flag
404cdf0e10cSrcweir     maModel.mnFuncGroupId = extractValue< sal_Int32 >( nFlags, 6, 6 );
405cdf0e10cSrcweir     maModel.mbMacro       = getFlag( nFlags, BIFF_DEFNAME_MACRO );
406cdf0e10cSrcweir     maModel.mbFunction    = getFlag( nFlags, BIFF_DEFNAME_FUNC );
407cdf0e10cSrcweir     maModel.mbVBName      = getFlag( nFlags, BIFF_DEFNAME_VBNAME );
408cdf0e10cSrcweir     maModel.mbHidden      = getFlag( nFlags, BIFF_DEFNAME_HIDDEN );
409cdf0e10cSrcweir 
410cdf0e10cSrcweir     // get built-in name index from name
411cdf0e10cSrcweir     if( getFlag( nFlags, BIFF_DEFNAME_BUILTIN ) )
412cdf0e10cSrcweir     {
413cdf0e10cSrcweir         // name may be the built-in identifier or the built-in base name
414cdf0e10cSrcweir         if( maModel.maName.getLength() == 1 )
415cdf0e10cSrcweir             mcBuiltinId = maModel.maName[ 0 ];
416cdf0e10cSrcweir         else
417cdf0e10cSrcweir             mcBuiltinId = lclGetBuiltinIdFromBaseName( maModel.maName );
418cdf0e10cSrcweir     }
419cdf0e10cSrcweir     /*  In BIFF5, '_FilterDatabase' appears as hidden user name without
420cdf0e10cSrcweir         built-in flag, and even worse, localized. */
421cdf0e10cSrcweir     else if( (eBiff == BIFF5) && lclIsFilterDatabaseName( maModel.maName ) )
422cdf0e10cSrcweir     {
423cdf0e10cSrcweir         mcBuiltinId = BIFF_DEFNAME_FILTERDATABASE;
424cdf0e10cSrcweir     }
425cdf0e10cSrcweir 
426cdf0e10cSrcweir     // get sheet index for sheet-local names in BIFF5-BIFF8
427cdf0e10cSrcweir     switch( getBiff() )
428cdf0e10cSrcweir     {
429cdf0e10cSrcweir         case BIFF2:
430cdf0e10cSrcweir         case BIFF3:
431cdf0e10cSrcweir         case BIFF4:
432cdf0e10cSrcweir             // BIFF2-BIFF4: all defined names are sheet-local
433cdf0e10cSrcweir             mnCalcSheet = nCalcSheet;
434cdf0e10cSrcweir         break;
435cdf0e10cSrcweir         case BIFF5:
436cdf0e10cSrcweir             // #i44019# nTabId may be invalid, resolve nRefId to sheet index
437cdf0e10cSrcweir             if( nRefId != BIFF_DEFNAME_GLOBAL )
438cdf0e10cSrcweir                 if( const ExternalLink* pExtLink = getExternalLinks().getExternalLink( nRefId ).get() )
439cdf0e10cSrcweir                     if( pExtLink->getLinkType() == LINKTYPE_INTERNAL )
440cdf0e10cSrcweir                         mnCalcSheet = pExtLink->getCalcSheetIndex();
441cdf0e10cSrcweir         break;
442cdf0e10cSrcweir         case BIFF8:
443cdf0e10cSrcweir             // convert one-based worksheet index to zero-based Calc sheet index
444cdf0e10cSrcweir             OSL_ENSURE( nTabId >= 0, "DefinedName::importDefinedName - invalid local sheet index" );
445cdf0e10cSrcweir             if( nTabId != BIFF_DEFNAME_GLOBAL )
446cdf0e10cSrcweir                 mnCalcSheet = getWorksheets().getCalcSheetIndex( nTabId - 1 );
447cdf0e10cSrcweir         break;
448cdf0e10cSrcweir         case BIFF_UNKNOWN:
449cdf0e10cSrcweir         break;
450cdf0e10cSrcweir     }
451cdf0e10cSrcweir 
452cdf0e10cSrcweir     if( (getBiff() <= BIFF4) && maModel.mbHidden && (maModel.maName.getLength() > 1) && (maModel.maName[ 0 ] == '\x01') )
453cdf0e10cSrcweir     {
454cdf0e10cSrcweir         /*  Read the token array of special internal names containing addresses
455cdf0e10cSrcweir             for BIFF3-BIFF4 3D references immediately. It is expected that
456cdf0e10cSrcweir             these names contain a simple cell reference or range reference.
457cdf0e10cSrcweir             Other regular defined names and external names rely on existence of
458cdf0e10cSrcweir             this reference. */
459cdf0e10cSrcweir         ApiTokenSequence aTokens = importBiffFormula( mnCalcSheet, rStrm, &mnFmlaSize );
460cdf0e10cSrcweir         extractReference( aTokens );
461cdf0e10cSrcweir     }
462cdf0e10cSrcweir     else
463cdf0e10cSrcweir     {
464cdf0e10cSrcweir         /*  Store record position of other defined names to be able to import
465cdf0e10cSrcweir             token array later. This is needed to correctly resolve references
466cdf0e10cSrcweir             to names that are stored later in the defined names list following
467cdf0e10cSrcweir             this name. */
468cdf0e10cSrcweir         mxBiffStrm.reset( new BiffInputStreamPos( rStrm ) );
469cdf0e10cSrcweir     }
470cdf0e10cSrcweir }
471cdf0e10cSrcweir 
createNameObject()472cdf0e10cSrcweir void DefinedName::createNameObject()
473cdf0e10cSrcweir {
474cdf0e10cSrcweir     // do not create names for (macro) functions or VBA procedures
475cdf0e10cSrcweir     // #163146# do not ignore hidden names (may be regular names created by VBA scripts)
476cdf0e10cSrcweir     if( /*maModel.mbHidden ||*/ maModel.mbFunction || maModel.mbVBName )
477cdf0e10cSrcweir         return;
478cdf0e10cSrcweir 
479cdf0e10cSrcweir     // skip BIFF names without stream position (e.g. BIFF3-BIFF4 internal 3D references)
480cdf0e10cSrcweir     if( (getFilterType() == FILTER_BIFF) && !mxBiffStrm.get() )
481cdf0e10cSrcweir         return;
482cdf0e10cSrcweir 
483cdf0e10cSrcweir     // convert original name to final Calc name (TODO: filter invalid characters from model name)
484cdf0e10cSrcweir     maCalcName = isBuiltinName() ? lclGetPrefixedName( mcBuiltinId ) : maModel.maName;
485cdf0e10cSrcweir 
486cdf0e10cSrcweir     // #163146# do not rename sheet-local names by default, this breaks VBA scripts
487cdf0e10cSrcweir #if 0
488cdf0e10cSrcweir     // append sheet index for local names in multi-sheet documents
489cdf0e10cSrcweir     if( isWorkbookFile() && !isGlobalName() )
490cdf0e10cSrcweir         maCalcName = OUStringBuffer( maCalcName ).append( sal_Unicode( '_' ) ).
491cdf0e10cSrcweir             append( static_cast< sal_Int32 >( mnCalcSheet + 1 ) ).makeStringAndClear();
492cdf0e10cSrcweir #endif
493cdf0e10cSrcweir 
494cdf0e10cSrcweir     // special flags for this name
495cdf0e10cSrcweir     sal_Int32 nNameFlags = 0;
496cdf0e10cSrcweir     using namespace ::com::sun::star::sheet::NamedRangeFlag;
497cdf0e10cSrcweir     if( !isGlobalName() ) switch( mcBuiltinId )
498cdf0e10cSrcweir     {
499cdf0e10cSrcweir         case BIFF_DEFNAME_CRITERIA:     nNameFlags = FILTER_CRITERIA;               break;
500cdf0e10cSrcweir         case BIFF_DEFNAME_PRINTAREA:    nNameFlags = PRINT_AREA;                    break;
501cdf0e10cSrcweir         case BIFF_DEFNAME_PRINTTITLES:  nNameFlags = COLUMN_HEADER | ROW_HEADER;    break;
502cdf0e10cSrcweir     }
503cdf0e10cSrcweir 
504cdf0e10cSrcweir     // create the name and insert it into the document, maCalcName will be changed to the resulting name
505*dffa72deSWang Lei     mxNamedRange = createNamedRangeObject( maCalcName, maModel.mnSheet, nNameFlags );
506cdf0e10cSrcweir     // index of this defined name used in formula token arrays
507cdf0e10cSrcweir     PropertySet aPropSet( mxNamedRange );
508cdf0e10cSrcweir     aPropSet.getProperty( mnTokenIndex, PROP_TokenIndex );
509cdf0e10cSrcweir }
510cdf0e10cSrcweir 
convertFormula()511cdf0e10cSrcweir void DefinedName::convertFormula()
512cdf0e10cSrcweir {
513cdf0e10cSrcweir     Reference< XFormulaTokens > xTokens( mxNamedRange, UNO_QUERY );
514cdf0e10cSrcweir     if( !xTokens.is() )
515cdf0e10cSrcweir         return;
516cdf0e10cSrcweir 
517cdf0e10cSrcweir     // convert and set formula of the defined name
518cdf0e10cSrcweir     ApiTokenSequence aTokens;
519cdf0e10cSrcweir     switch( getFilterType() )
520cdf0e10cSrcweir     {
521cdf0e10cSrcweir         case FILTER_OOXML:
522cdf0e10cSrcweir         {
523cdf0e10cSrcweir             if( mxFormula.get() )
524cdf0e10cSrcweir             {
525cdf0e10cSrcweir                 SequenceInputStream aStrm( *mxFormula );
526cdf0e10cSrcweir                 aTokens = importBiff12Formula( mnCalcSheet, aStrm );
527cdf0e10cSrcweir             }
528cdf0e10cSrcweir             else
529cdf0e10cSrcweir                 aTokens = importOoxFormula( mnCalcSheet );
530cdf0e10cSrcweir         }
531cdf0e10cSrcweir         break;
532cdf0e10cSrcweir         case FILTER_BIFF:
533cdf0e10cSrcweir         {
534cdf0e10cSrcweir             OSL_ENSURE( mxBiffStrm.get(), "DefinedName::convertFormula - missing BIFF stream" );
535cdf0e10cSrcweir             if( mxBiffStrm.get() )
536cdf0e10cSrcweir             {
537cdf0e10cSrcweir                 BiffInputStream& rStrm = mxBiffStrm->getStream();
538cdf0e10cSrcweir                 BiffInputStreamPosGuard aStrmGuard( rStrm );
539cdf0e10cSrcweir                 if( mxBiffStrm->restorePosition() )
540cdf0e10cSrcweir                     aTokens = importBiffFormula( mnCalcSheet, rStrm, &mnFmlaSize );
541cdf0e10cSrcweir             }
542cdf0e10cSrcweir         }
543cdf0e10cSrcweir         break;
544cdf0e10cSrcweir         case FILTER_UNKNOWN:
545cdf0e10cSrcweir         break;
546cdf0e10cSrcweir     }
547cdf0e10cSrcweir     xTokens->setTokens( aTokens );
548cdf0e10cSrcweir 
549cdf0e10cSrcweir     // set built-in names (print ranges, repeated titles, filter ranges)
550cdf0e10cSrcweir     if( !isGlobalName() ) switch( mcBuiltinId )
551cdf0e10cSrcweir     {
552cdf0e10cSrcweir         case BIFF_DEFNAME_PRINTAREA:
553cdf0e10cSrcweir         {
554cdf0e10cSrcweir             Reference< XPrintAreas > xPrintAreas( getSheetFromDoc( mnCalcSheet ), UNO_QUERY );
555cdf0e10cSrcweir             ApiCellRangeList aPrintRanges;
556cdf0e10cSrcweir             getFormulaParser().extractCellRangeList( aPrintRanges, xTokens->getTokens(), false, mnCalcSheet );
557cdf0e10cSrcweir             if( xPrintAreas.is() && !aPrintRanges.empty() )
558cdf0e10cSrcweir                 xPrintAreas->setPrintAreas( ContainerHelper::vectorToSequence( aPrintRanges ) );
559cdf0e10cSrcweir         }
560cdf0e10cSrcweir         break;
561cdf0e10cSrcweir         case BIFF_DEFNAME_PRINTTITLES:
562cdf0e10cSrcweir         {
563cdf0e10cSrcweir             Reference< XPrintAreas > xPrintAreas( getSheetFromDoc( mnCalcSheet ), UNO_QUERY );
564cdf0e10cSrcweir             ApiCellRangeList aTitleRanges;
565cdf0e10cSrcweir             getFormulaParser().extractCellRangeList( aTitleRanges, xTokens->getTokens(), false, mnCalcSheet );
566cdf0e10cSrcweir             if( xPrintAreas.is() && !aTitleRanges.empty() )
567cdf0e10cSrcweir             {
568cdf0e10cSrcweir                 bool bHasRowTitles = false;
569cdf0e10cSrcweir                 bool bHasColTitles = false;
570cdf0e10cSrcweir                 const CellAddress& rMaxPos = getAddressConverter().getMaxAddress();
571cdf0e10cSrcweir                 for( ApiCellRangeList::const_iterator aIt = aTitleRanges.begin(), aEnd = aTitleRanges.end(); (aIt != aEnd) && (!bHasRowTitles || !bHasColTitles); ++aIt )
572cdf0e10cSrcweir                 {
573cdf0e10cSrcweir                     bool bFullRow = (aIt->StartColumn == 0) && (aIt->EndColumn >= rMaxPos.Column);
574cdf0e10cSrcweir                     bool bFullCol = (aIt->StartRow == 0) && (aIt->EndRow >= rMaxPos.Row);
575cdf0e10cSrcweir                     if( !bHasRowTitles && bFullRow && !bFullCol )
576cdf0e10cSrcweir                     {
577cdf0e10cSrcweir                         xPrintAreas->setTitleRows( *aIt );
578cdf0e10cSrcweir                         xPrintAreas->setPrintTitleRows( sal_True );
579cdf0e10cSrcweir                         bHasRowTitles = true;
580cdf0e10cSrcweir                     }
581cdf0e10cSrcweir                     else if( !bHasColTitles && bFullCol && !bFullRow )
582cdf0e10cSrcweir                     {
583cdf0e10cSrcweir                         xPrintAreas->setTitleColumns( *aIt );
584cdf0e10cSrcweir                         xPrintAreas->setPrintTitleColumns( sal_True );
585cdf0e10cSrcweir                         bHasColTitles = true;
586cdf0e10cSrcweir                     }
587cdf0e10cSrcweir                 }
588cdf0e10cSrcweir             }
589cdf0e10cSrcweir         }
590cdf0e10cSrcweir         break;
591cdf0e10cSrcweir     }
592cdf0e10cSrcweir }
593cdf0e10cSrcweir 
getAbsoluteRange(CellRangeAddress & orRange) const594cdf0e10cSrcweir bool DefinedName::getAbsoluteRange( CellRangeAddress& orRange ) const
595cdf0e10cSrcweir {
596cdf0e10cSrcweir     /*  ScNamedRangeObj::XCellRangeReferrer::getReferredCells is buggy with
597cdf0e10cSrcweir         relative references, so we extract an absolute reference by hand. */
598cdf0e10cSrcweir     Reference< XFormulaTokens > xTokens( mxNamedRange, UNO_QUERY );
599cdf0e10cSrcweir     return xTokens.is() && getFormulaParser().extractCellRange( orRange, xTokens->getTokens(), false );
600cdf0e10cSrcweir }
601cdf0e10cSrcweir 
602cdf0e10cSrcweir // ============================================================================
603cdf0e10cSrcweir 
DefinedNamesBuffer(const WorkbookHelper & rHelper)604cdf0e10cSrcweir DefinedNamesBuffer::DefinedNamesBuffer( const WorkbookHelper& rHelper ) :
605cdf0e10cSrcweir     WorkbookHelper( rHelper ),
606cdf0e10cSrcweir     mnCalcSheet( -1 )
607cdf0e10cSrcweir {
608cdf0e10cSrcweir }
609cdf0e10cSrcweir 
setLocalCalcSheet(sal_Int16 nCalcSheet)610cdf0e10cSrcweir void DefinedNamesBuffer::setLocalCalcSheet( sal_Int16 nCalcSheet )
611cdf0e10cSrcweir {
612cdf0e10cSrcweir     OSL_ENSURE( (getFilterType() == FILTER_BIFF) && (getBiff() <= BIFF4),
613cdf0e10cSrcweir         "DefinedNamesBuffer::setLocalCalcSheet - invalid call" );
614cdf0e10cSrcweir     mnCalcSheet = nCalcSheet;
615cdf0e10cSrcweir }
616cdf0e10cSrcweir 
importDefinedName(const AttributeList & rAttribs)617cdf0e10cSrcweir DefinedNameRef DefinedNamesBuffer::importDefinedName( const AttributeList& rAttribs )
618cdf0e10cSrcweir {
619cdf0e10cSrcweir     DefinedNameRef xDefName = createDefinedName();
620cdf0e10cSrcweir     xDefName->importDefinedName( rAttribs );
621cdf0e10cSrcweir     return xDefName;
622cdf0e10cSrcweir }
623cdf0e10cSrcweir 
importDefinedName(SequenceInputStream & rStrm)624cdf0e10cSrcweir void DefinedNamesBuffer::importDefinedName( SequenceInputStream& rStrm )
625cdf0e10cSrcweir {
626cdf0e10cSrcweir     createDefinedName()->importDefinedName( rStrm );
627cdf0e10cSrcweir }
628cdf0e10cSrcweir 
importDefinedName(BiffInputStream & rStrm)629cdf0e10cSrcweir void DefinedNamesBuffer::importDefinedName( BiffInputStream& rStrm )
630cdf0e10cSrcweir {
631cdf0e10cSrcweir     createDefinedName()->importDefinedName( rStrm, mnCalcSheet );
632cdf0e10cSrcweir }
633cdf0e10cSrcweir 
finalizeImport()634cdf0e10cSrcweir void DefinedNamesBuffer::finalizeImport()
635cdf0e10cSrcweir {
636cdf0e10cSrcweir     // first insert all names without formula definition into the document, and insert them into the maps
637cdf0e10cSrcweir     for( DefNameVector::iterator aIt = maDefNames.begin(), aEnd = maDefNames.end(); aIt != aEnd; ++aIt )
638cdf0e10cSrcweir     {
639cdf0e10cSrcweir         DefinedNameRef xDefName = *aIt;
640cdf0e10cSrcweir         xDefName->createNameObject();
641cdf0e10cSrcweir         // map by sheet index and original model name
642cdf0e10cSrcweir         maModelNameMap[ SheetNameKey( xDefName->getLocalCalcSheet(), xDefName->getUpcaseModelName() ) ] = xDefName;
643cdf0e10cSrcweir         // map by sheet index and built-in identifier
644cdf0e10cSrcweir         if( !xDefName->isGlobalName() && xDefName->isBuiltinName() )
645cdf0e10cSrcweir             maBuiltinMap[ BuiltinKey( xDefName->getLocalCalcSheet(), xDefName->getBuiltinId() ) ] = xDefName;
646cdf0e10cSrcweir         // map by API formula token identifier
647cdf0e10cSrcweir         sal_Int32 nTokenIndex = xDefName->getTokenIndex();
648cdf0e10cSrcweir         if( nTokenIndex >= 0 )
649cdf0e10cSrcweir             maTokenIdMap[ nTokenIndex ] = xDefName;
650cdf0e10cSrcweir     }
651cdf0e10cSrcweir 
652cdf0e10cSrcweir     /*  Now convert all name formulas, so that the formula parser can find all
653cdf0e10cSrcweir         names in case of circular dependencies. */
654cdf0e10cSrcweir     maDefNames.forEachMem( &DefinedName::convertFormula );
655cdf0e10cSrcweir }
656cdf0e10cSrcweir 
getByIndex(sal_Int32 nIndex) const657cdf0e10cSrcweir DefinedNameRef DefinedNamesBuffer::getByIndex( sal_Int32 nIndex ) const
658cdf0e10cSrcweir {
659cdf0e10cSrcweir     return maDefNames.get( nIndex );
660cdf0e10cSrcweir }
661cdf0e10cSrcweir 
getByTokenIndex(sal_Int32 nIndex) const662cdf0e10cSrcweir DefinedNameRef DefinedNamesBuffer::getByTokenIndex( sal_Int32 nIndex ) const
663cdf0e10cSrcweir {
664cdf0e10cSrcweir     return maTokenIdMap.get( nIndex );
665cdf0e10cSrcweir }
666cdf0e10cSrcweir 
getByModelName(const OUString & rModelName,sal_Int16 nCalcSheet) const667cdf0e10cSrcweir DefinedNameRef DefinedNamesBuffer::getByModelName( const OUString& rModelName, sal_Int16 nCalcSheet ) const
668cdf0e10cSrcweir {
669cdf0e10cSrcweir     OUString aUpcaseName = lclGetUpcaseModelName( rModelName );
670cdf0e10cSrcweir     DefinedNameRef xDefName = maModelNameMap.get( SheetNameKey( nCalcSheet, aUpcaseName ) );
671cdf0e10cSrcweir     // lookup global name, if no local name exists
672cdf0e10cSrcweir     if( !xDefName && (nCalcSheet >= 0) )
673cdf0e10cSrcweir         xDefName = maModelNameMap.get( SheetNameKey( -1, aUpcaseName ) );
674cdf0e10cSrcweir     return xDefName;
675cdf0e10cSrcweir }
676cdf0e10cSrcweir 
getByBuiltinId(sal_Unicode cBuiltinId,sal_Int16 nCalcSheet) const677cdf0e10cSrcweir DefinedNameRef DefinedNamesBuffer::getByBuiltinId( sal_Unicode cBuiltinId, sal_Int16 nCalcSheet ) const
678cdf0e10cSrcweir {
679cdf0e10cSrcweir     return maBuiltinMap.get( BuiltinKey( nCalcSheet, cBuiltinId ) );
680cdf0e10cSrcweir }
681cdf0e10cSrcweir 
createDefinedName()682cdf0e10cSrcweir DefinedNameRef DefinedNamesBuffer::createDefinedName()
683cdf0e10cSrcweir {
684cdf0e10cSrcweir     DefinedNameRef xDefName( new DefinedName( *this ) );
685cdf0e10cSrcweir     maDefNames.push_back( xDefName );
686cdf0e10cSrcweir     return xDefName;
687cdf0e10cSrcweir }
688cdf0e10cSrcweir 
689cdf0e10cSrcweir // ============================================================================
690cdf0e10cSrcweir 
691cdf0e10cSrcweir } // namespace xls
692cdf0e10cSrcweir } // namespace oox
693