update credits
[LibreOffice.git] / sc / inc / token.hxx
blob109980fce92a69a834979a2f4dc5363f792bb99a
1 /* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
2 /*
3 * This file is part of the LibreOffice project.
5 * This Source Code Form is subject to the terms of the Mozilla Public
6 * License, v. 2.0. If a copy of the MPL was not distributed with this
7 * file, You can obtain one at http://mozilla.org/MPL/2.0/.
9 * This file incorporates work covered by the following license notice:
11 * Licensed to the Apache Software Foundation (ASF) under one or more
12 * contributor license agreements. See the NOTICE file distributed
13 * with this work for additional information regarding copyright
14 * ownership. The ASF licenses this file to you under the Apache
15 * License, Version 2.0 (the "License"); you may not use this file
16 * except in compliance with the License. You may obtain a copy of
17 * the License at http://www.apache.org/licenses/LICENSE-2.0 .
20 #ifndef SC_TOKEN_HXX
21 #define SC_TOKEN_HXX
23 #include <memory>
24 #include <vector>
25 #include <boost/intrusive_ptr.hpp>
27 #include "formula/opcode.hxx"
28 #include "refdata.hxx"
29 #include "scmatrix.hxx"
30 #include <tools/mempool.hxx>
31 #include "scdllapi.h"
32 #include "formula/IFunctionDescription.hxx"
33 #include "formula/token.hxx"
34 #include "types.hxx"
36 class ScJumpMatrix;
38 typedef ::std::vector< ScComplexRefData > ScRefList;
40 class SC_DLLPUBLIC ScToken : public formula::FormulaToken
42 private:
43 // not implemented, prevent usage
44 ScToken();
45 ScToken& operator=( const ScToken& );
47 protected:
49 ScToken( formula::StackVar eTypeP,OpCode e = ocPush ) : formula::FormulaToken(eTypeP,e) {}
50 ScToken( const ScToken& r ): formula::FormulaToken(r) {}
52 public:
54 virtual ~ScToken();
56 /**
57 Dummy methods to avoid switches and casts where possible,
58 the real token classes have to overload the appropriate method[s].
59 The only methods valid anytime if not overloaded are:
61 - GetByte() since this represents the count of parameters to a function
62 which of course is 0 on non-functions. formula::FormulaByteToken and ScExternal do
63 overload it.
65 - HasForceArray() since also this is only used for operators and
66 functions and is 0 for other tokens.
68 Any other non-overloaded method pops up an assertion.
71 virtual const ScSingleRefData& GetSingleRef() const;
72 virtual ScSingleRefData& GetSingleRef();
73 virtual const ScComplexRefData& GetDoubleRef() const;
74 virtual ScComplexRefData& GetDoubleRef();
75 virtual const ScSingleRefData& GetSingleRef2() const;
76 virtual ScSingleRefData& GetSingleRef2();
77 virtual void CalcAbsIfRel( const ScAddress& );
78 virtual void CalcRelFromAbs( const ScAddress& );
79 virtual const ScMatrix* GetMatrix() const;
80 virtual ScMatrix* GetMatrix();
81 virtual ScJumpMatrix* GetJumpMatrix() const;
82 virtual const ScRefList* GetRefList() const;
83 virtual ScRefList* GetRefList();
85 virtual bool TextEqual( const formula::FormulaToken& rToken ) const;
86 virtual bool Is3DRef() const; // reference with 3D flag set
88 /** If rTok1 and rTok2 both are SingleRef or DoubleRef tokens, extend/merge
89 ranges as needed for ocRange.
90 @param rPos
91 The formula's position, used to calculate absolute positions from
92 relative references.
93 @param bReuseDoubleRef
94 If true, a DoubleRef token is reused if passed as rTok1 or rTok2,
95 else a new DoubleRef token is created and returned.
96 @return
97 A reused or new'ed ScDoubleRefToken, or a NULL TokenRef if rTok1 or
98 rTok2 are not of sv(Single|Double)Ref
100 static formula::FormulaTokenRef ExtendRangeReference( formula::FormulaToken & rTok1, formula::FormulaToken & rTok2, const ScAddress & rPos, bool bReuseDoubleRef );
103 inline void intrusive_ptr_add_ref(const ScToken* p)
105 p->IncRef();
108 inline void intrusive_ptr_release(const ScToken* p)
110 p->DecRef();
113 class ScSingleRefToken : public ScToken
115 private:
116 ScSingleRefData aSingleRef;
117 public:
118 ScSingleRefToken( const ScSingleRefData& r, OpCode e = ocPush ) :
119 ScToken( formula::svSingleRef, e ), aSingleRef( r ) {}
120 ScSingleRefToken( const ScSingleRefToken& r ) :
121 ScToken( r ), aSingleRef( r.aSingleRef ) {}
122 virtual const ScSingleRefData& GetSingleRef() const;
123 virtual ScSingleRefData& GetSingleRef();
124 virtual void CalcAbsIfRel( const ScAddress& );
125 virtual void CalcRelFromAbs( const ScAddress& );
126 virtual bool operator==( const formula::FormulaToken& rToken ) const;
127 virtual FormulaToken* Clone() const { return new ScSingleRefToken(*this); }
129 DECL_FIXEDMEMPOOL_NEWDEL( ScSingleRefToken );
132 class ScDoubleRefToken : public ScToken
134 private:
135 ScComplexRefData aDoubleRef;
136 public:
137 ScDoubleRefToken( const ScComplexRefData& r, OpCode e = ocPush ) :
138 ScToken( formula::svDoubleRef, e ), aDoubleRef( r ) {}
139 ScDoubleRefToken( const ScSingleRefData& r, OpCode e = ocPush ) :
140 ScToken( formula::svDoubleRef, e )
142 aDoubleRef.Ref1 = r;
143 aDoubleRef.Ref2 = r;
145 ScDoubleRefToken( const ScDoubleRefToken& r ) :
146 ScToken( r ), aDoubleRef( r.aDoubleRef ) {}
147 virtual const ScSingleRefData& GetSingleRef() const;
148 virtual ScSingleRefData& GetSingleRef();
149 virtual const ScComplexRefData& GetDoubleRef() const;
150 virtual ScComplexRefData& GetDoubleRef();
151 virtual const ScSingleRefData& GetSingleRef2() const;
152 virtual ScSingleRefData& GetSingleRef2();
153 virtual void CalcAbsIfRel( const ScAddress& );
154 virtual void CalcRelFromAbs( const ScAddress& );
155 virtual bool operator==( const formula::FormulaToken& rToken ) const;
156 virtual FormulaToken* Clone() const { return new ScDoubleRefToken(*this); }
158 DECL_FIXEDMEMPOOL_NEWDEL( ScDoubleRefToken );
161 class ScMatrixToken : public ScToken
163 private:
164 ScMatrixRef pMatrix;
165 public:
166 ScMatrixToken( ScMatrixRef p ) :
167 ScToken( formula::svMatrix ), pMatrix( p ) {}
168 ScMatrixToken( const ScMatrixToken& r ) :
169 ScToken( r ), pMatrix( r.pMatrix ) {}
170 virtual const ScMatrix* GetMatrix() const;
171 virtual ScMatrix* GetMatrix();
172 virtual bool operator==( const formula::FormulaToken& rToken ) const;
173 virtual FormulaToken* Clone() const { return new ScMatrixToken(*this); }
177 class ScExternalSingleRefToken : public ScToken
179 private:
180 sal_uInt16 mnFileId;
181 String maTabName;
182 ScSingleRefData maSingleRef;
184 ScExternalSingleRefToken(); // disabled
185 public:
186 ScExternalSingleRefToken( sal_uInt16 nFileId, const String& rTabName, const ScSingleRefData& r );
187 ScExternalSingleRefToken( const ScExternalSingleRefToken& r );
188 virtual ~ScExternalSingleRefToken();
190 virtual sal_uInt16 GetIndex() const;
191 virtual const String& GetString() const;
192 virtual const ScSingleRefData& GetSingleRef() const;
193 virtual ScSingleRefData& GetSingleRef();
194 virtual void CalcAbsIfRel( const ScAddress& );
195 virtual void CalcRelFromAbs( const ScAddress& );
196 virtual bool operator==( const formula::FormulaToken& rToken ) const;
197 virtual FormulaToken* Clone() const { return new ScExternalSingleRefToken(*this); }
201 class ScExternalDoubleRefToken : public ScToken
203 private:
204 sal_uInt16 mnFileId;
205 String maTabName; // name of the first sheet
206 ScComplexRefData maDoubleRef;
208 ScExternalDoubleRefToken(); // disabled
209 public:
210 ScExternalDoubleRefToken( sal_uInt16 nFileId, const String& rTabName, const ScComplexRefData& r );
211 ScExternalDoubleRefToken( const ScExternalDoubleRefToken& r );
212 virtual ~ScExternalDoubleRefToken();
214 virtual sal_uInt16 GetIndex() const;
215 virtual const String& GetString() const;
216 virtual const ScSingleRefData& GetSingleRef() const;
217 virtual ScSingleRefData& GetSingleRef();
218 virtual const ScSingleRefData& GetSingleRef2() const;
219 virtual ScSingleRefData& GetSingleRef2();
220 virtual const ScComplexRefData& GetDoubleRef() const;
221 virtual ScComplexRefData& GetDoubleRef();
222 virtual void CalcAbsIfRel( const ScAddress& );
223 virtual void CalcRelFromAbs( const ScAddress& );
224 virtual bool operator==( const formula::FormulaToken& rToken ) const;
225 virtual FormulaToken* Clone() const { return new ScExternalDoubleRefToken(*this); }
228 class ScExternalNameToken : public ScToken
230 private:
231 sal_uInt16 mnFileId;
232 String maName;
233 private:
234 ScExternalNameToken(); // disabled
235 public:
236 ScExternalNameToken( sal_uInt16 nFileId, const String& rName );
237 ScExternalNameToken( const ScExternalNameToken& r );
238 virtual ~ScExternalNameToken();
239 virtual sal_uInt16 GetIndex() const;
240 virtual const String& GetString() const;
241 virtual bool operator==( const formula::FormulaToken& rToken ) const;
242 virtual FormulaToken* Clone() const { return new ScExternalNameToken(*this); }
246 // Only created from within the interpreter, no conversion from ScRawToken,
247 // never added to ScTokenArray!
248 class ScJumpMatrixToken : public ScToken
250 private:
251 ScJumpMatrix* pJumpMatrix;
252 public:
253 ScJumpMatrixToken( ScJumpMatrix* p ) :
254 ScToken( formula::svJumpMatrix ), pJumpMatrix( p ) {}
255 ScJumpMatrixToken( const ScJumpMatrixToken& r ) :
256 ScToken( r ), pJumpMatrix( r.pJumpMatrix ) {}
257 virtual ~ScJumpMatrixToken();
258 virtual ScJumpMatrix* GetJumpMatrix() const;
259 virtual bool operator==( const formula::FormulaToken& rToken ) const;
260 virtual FormulaToken* Clone() const { return new ScJumpMatrixToken(*this); }
264 // Only created from within the interpreter, no conversion from ScRawToken,
265 // never added to ScTokenArray!
266 class ScRefListToken : public ScToken
268 private:
269 ScRefList aRefList;
270 public:
271 ScRefListToken() :
272 ScToken( formula::svRefList ) {}
273 ScRefListToken( const ScRefListToken & r ) :
274 ScToken( r ), aRefList( r.aRefList ) {}
275 virtual void CalcAbsIfRel( const ScAddress& );
276 virtual void CalcRelFromAbs( const ScAddress& );
277 virtual const ScRefList* GetRefList() const;
278 virtual ScRefList* GetRefList();
279 virtual bool operator==( const formula::FormulaToken& rToken ) const;
280 virtual FormulaToken* Clone() const { return new ScRefListToken(*this); }
284 class SC_DLLPUBLIC ScEmptyCellToken : public ScToken
286 bool bInherited :1;
287 bool bDisplayedAsString :1;
288 public:
289 explicit ScEmptyCellToken( bool bInheritedP, bool bDisplayAsString ) :
290 ScToken( formula::svEmptyCell ),
291 bInherited( bInheritedP ),
292 bDisplayedAsString( bDisplayAsString ) {}
293 ScEmptyCellToken( const ScEmptyCellToken& r ) :
294 ScToken( r ),
295 bInherited( r.bInherited ),
296 bDisplayedAsString( r.bDisplayedAsString ) {}
297 bool IsInherited() const { return bInherited; }
298 bool IsDisplayedAsString() const { return bDisplayedAsString; }
299 virtual double GetDouble() const;
300 virtual const String & GetString() const;
301 virtual bool operator==( const formula::FormulaToken& rToken ) const;
302 virtual FormulaToken* Clone() const { return new ScEmptyCellToken(*this); }
306 /** Transports the result from the interpreter to the formula cell. */
307 class SC_DLLPUBLIC ScMatrixCellResultToken : public ScToken
309 // No non-const access implemented, silence down unxsols4 complaining about
310 // the public GetMatrix() hiding the one from ScToken.
311 virtual ScMatrix* GetMatrix();
313 protected:
314 ScConstMatrixRef xMatrix;
315 formula::FormulaConstTokenRef xUpperLeft;
316 public:
317 ScMatrixCellResultToken( const ScConstMatrixRef& pMat, formula::FormulaToken* pUL ) :
318 ScToken( formula::svMatrixCell ),
319 xMatrix( pMat), xUpperLeft( pUL) {}
320 ScMatrixCellResultToken( const ScMatrixCellResultToken& r ) :
321 ScToken( r ), xMatrix( r.xMatrix ),
322 xUpperLeft( r.xUpperLeft ) {}
323 virtual double GetDouble() const;
324 virtual const String & GetString() const;
325 virtual const ScMatrix* GetMatrix() const;
326 virtual bool operator==( const formula::FormulaToken& rToken ) const;
327 virtual FormulaToken* Clone() const { return new ScMatrixCellResultToken(*this); }
328 formula::StackVar GetUpperLeftType() const
330 return xUpperLeft ?
331 xUpperLeft->GetType() :
332 static_cast<formula::StackVar>(formula::svUnknown);
334 inline formula::FormulaConstTokenRef GetUpperLeftToken() const { return xUpperLeft; }
335 void Assign( const ScMatrixCellResultToken & r )
337 xMatrix = r.xMatrix;
338 xUpperLeft = r.xUpperLeft;
343 /** Stores the matrix result at the formula cell, additionally the range the
344 matrix formula occupies. */
345 class SC_DLLPUBLIC ScMatrixFormulaCellToken : public ScMatrixCellResultToken
347 private:
348 SCROW nRows;
349 SCCOL nCols;
350 public:
351 ScMatrixFormulaCellToken( SCCOL nC, SCROW nR, const ScConstMatrixRef& pMat, formula::FormulaToken* pUL ) :
352 ScMatrixCellResultToken(pMat, pUL),
353 nRows(nR), nCols(nC) {}
355 ScMatrixFormulaCellToken( SCCOL nC, SCROW nR ) :
356 ScMatrixCellResultToken( NULL, NULL ),
357 nRows( nR ), nCols( nC ) {}
358 ScMatrixFormulaCellToken( const ScMatrixFormulaCellToken& r ) :
359 ScMatrixCellResultToken( r ),
360 nRows( r.nRows ), nCols( r.nCols )
362 // xUpperLeft is modifiable through
363 // SetUpperLeftDouble(), so clone it.
364 if (xUpperLeft)
365 xUpperLeft = xUpperLeft->Clone();
367 virtual bool operator==( const formula::FormulaToken& rToken ) const;
368 virtual FormulaToken* Clone() const { return new ScMatrixFormulaCellToken(*this); }
369 void SetMatColsRows( SCCOL nC, SCROW nR )
371 nRows = nR;
372 nCols = nC;
374 void GetMatColsRows( SCCOL & nC, SCROW & nR ) const
376 nR = nRows;
377 nC = nCols;
379 SCCOL GetMatCols() const { return nCols; }
380 SCROW GetMatRows() const { return nRows; }
382 /** Assign matrix result, keep matrix formula
383 dimension. */
384 void Assign( const ScMatrixCellResultToken & r )
386 ScMatrixCellResultToken::Assign( r);
389 /** Assign any result, keep matrix formula
390 dimension. If token is of type
391 ScMatrixCellResultToken uses the
392 appropriate Assign() call, other tokens
393 are assigned to xUpperLeft and xMatrix will
394 be assigned NULL. */
395 void Assign( const formula::FormulaToken & r );
397 /** Modify xUpperLeft if formula::svDouble, or create
398 new formula::FormulaDoubleToken if not set yet. Does
399 nothing if xUpperLeft is of different type! */
400 void SetUpperLeftDouble( double f);
402 /** Reset matrix and upper left, keep matrix
403 formula dimension. */
404 void ResetResult()
406 xMatrix = NULL;
407 xUpperLeft = NULL;
412 class SC_DLLPUBLIC ScHybridCellToken : public ScToken
414 private:
415 double mfDouble;
416 String maString;
417 OUString maFormula;
418 public:
419 ScHybridCellToken( double f,
420 const OUString & rStr,
421 const OUString & rFormula ) :
422 ScToken( formula::svHybridCell ),
423 mfDouble( f ), maString( rStr ),
424 maFormula( rFormula ) {}
426 const OUString& GetFormula() const { return maFormula; }
427 virtual double GetDouble() const;
428 virtual const String& GetString() const;
429 virtual bool operator==( const formula::FormulaToken& rToken ) const;
430 virtual FormulaToken* Clone() const { return new ScHybridCellToken(*this); }
433 // Simplify argument passing to RefUpdate methods with ScSingleRefToken or
434 // ScDoubleRefToken
435 class SingleDoubleRefModifier
437 ScComplexRefData aDub;
438 ScSingleRefData* pS;
439 ScComplexRefData* pD;
441 // not implemented, prevent usage
442 SingleDoubleRefModifier( const SingleDoubleRefModifier& );
443 SingleDoubleRefModifier& operator=( const SingleDoubleRefModifier& );
445 public:
446 SingleDoubleRefModifier( ScToken& rT )
448 formula::StackVar eType = rT.GetType();
449 if ( eType == formula::svSingleRef || eType == formula::svExternalSingleRef )
451 pS = &rT.GetSingleRef();
452 aDub.Ref1 = aDub.Ref2 = *pS;
453 pD = &aDub;
455 else
457 pS = 0;
458 pD = &rT.GetDoubleRef();
461 SingleDoubleRefModifier( ScSingleRefData& rS )
463 pS = &rS;
464 aDub.Ref1 = aDub.Ref2 = *pS;
465 pD = &aDub;
467 ~SingleDoubleRefModifier()
469 if ( pS )
470 *pS = (*pD).Ref1;
472 inline ScComplexRefData& Ref() { return *pD; }
475 class SingleDoubleRefProvider
477 public:
479 const ScSingleRefData& Ref1;
480 const ScSingleRefData& Ref2;
482 SingleDoubleRefProvider( const ScToken& r )
483 : Ref1( r.GetSingleRef() ),
484 Ref2( (r.GetType() == formula::svDoubleRef ||
485 r.GetType() == formula::svExternalDoubleRef) ?
486 r.GetDoubleRef().Ref2 : Ref1 )
488 SingleDoubleRefProvider( const ScSingleRefData& r )
489 : Ref1( r ), Ref2( r )
491 SingleDoubleRefProvider( const ScComplexRefData& r )
492 : Ref1( r.Ref1 ), Ref2( r.Ref2 )
494 ~SingleDoubleRefProvider()
498 #endif
500 /* vim:set shiftwidth=4 softtabstop=4 expandtab: */