ooo-build r13762 - in trunk: . patches/dev300
- From: kyoshida svn gnome org
- To: svn-commits-list gnome org
- Subject: ooo-build r13762 - in trunk: . patches/dev300
- Date: Wed, 3 Sep 2008 00:32:12 +0000 (UTC)
Author: kyoshida
Date: Wed Sep 3 00:32:12 2008
New Revision: 13762
URL: http://svn.gnome.org/viewvc/ooo-build?rev=13762&view=rev
Log:
2008-09-02 Kohei Yoshida <kyoshida novell com>
* patches/dev300/calc-external-defined-names-offapi.diff:
* patches/dev300/calc-external-defined-names-sc.diff: updated, with
more change from the upstream, updated API, and more.
* patches/dev300/apply:
* patches/dev300/calc-external-names-additional-fixes.diff: removed, as
this has been combined with the -sc.diff patch above.
Removed:
trunk/patches/dev300/calc-external-names-additional-fixes.diff
Modified:
trunk/ChangeLog
trunk/patches/dev300/apply
trunk/patches/dev300/calc-external-defined-names-offapi.diff
trunk/patches/dev300/calc-external-defined-names-sc.diff
Modified: trunk/patches/dev300/apply
==============================================================================
--- trunk/patches/dev300/apply (original)
+++ trunk/patches/dev300/apply Wed Sep 3 00:32:12 2008
@@ -1724,7 +1724,6 @@
# Implement external range names.
calc-external-defined-names-sc.diff, i#3740, i#4385, n#355685, kohei
calc-external-defined-names-offapi.diff, i#3740, i#4385, n#355685, kohei
-calc-external-names-additional-fixes.diff, kohei
[ CalcSolver ]
SectionOwner => kohei
Modified: trunk/patches/dev300/calc-external-defined-names-offapi.diff
==============================================================================
--- trunk/patches/dev300/calc-external-defined-names-offapi.diff (original)
+++ trunk/patches/dev300/calc-external-defined-names-offapi.diff Wed Sep 3 00:32:12 2008
@@ -1,9 +1,9 @@
diff --git offapi/com/sun/star/sheet/ExternalDocLink.idl offapi/com/sun/star/sheet/ExternalDocLink.idl
new file mode 100644
-index 0000000..7320905
+index 0000000..9c7f70d
--- /dev/null
+++ offapi/com/sun/star/sheet/ExternalDocLink.idl
-@@ -0,0 +1,53 @@
+@@ -0,0 +1,57 @@
+/*************************************************************************
+ *
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
@@ -41,6 +41,8 @@
+
+module com { module sun { module star { module sheet {
+
++//=============================================================================
++
+/** Represents a single external document link.
+
+ <p>An external document link contains cached data used for external cell
@@ -54,6 +56,8 @@
+{
+};
+
++//=============================================================================
++
+}; }; }; };
+
+#endif
@@ -118,6 +122,262 @@
+}; }; }; };
+
+#endif
+diff --git offapi/com/sun/star/sheet/ExternalLinkInfo.idl offapi/com/sun/star/sheet/ExternalLinkInfo.idl
+new file mode 100644
+index 0000000..52758ec
+--- /dev/null
++++ offapi/com/sun/star/sheet/ExternalLinkInfo.idl
+@@ -0,0 +1,81 @@
++/*************************************************************************
++ *
++ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
++ *
++ * Copyright 2008 by Sun Microsystems, Inc.
++ *
++ * OpenOffice.org - a multi-platform office productivity suite
++ *
++ * $RCSfile: ExternalLinkInfo.idl,v $
++ * $Revision: 1.1.2.2 $
++ *
++ * This file is part of OpenOffice.org.
++ *
++ * OpenOffice.org is free software: you can redistribute it and/or modify
++ * it under the terms of the GNU Lesser General Public License version 3
++ * only, as published by the Free Software Foundation.
++ *
++ * OpenOffice.org is distributed in the hope that it will be useful,
++ * but WITHOUT ANY WARRANTY; without even the implied warranty of
++ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
++ * GNU Lesser General Public License version 3 for more details
++ * (a copy is included in the LICENSE file that accompanied this code).
++ *
++ * You should have received a copy of the GNU Lesser General Public License
++ * version 3 along with OpenOffice.org. If not, see
++ * <http://www.openoffice.org/license.html>
++ * for a copy of the LGPLv3 License.
++ *
++ ************************************************************************/
++#ifndef __com_sun_star_sheet_ExternalLinkInfo_idl__
++#define __com_sun_star_sheet_ExternalLinkInfo_idl__
++
++#ifndef __com_sun_star_sheet_ExternalLinkType_idl__
++#include <com/sun/star/sheet/ExternalLinkType.idl>
++#endif
++
++//=============================================================================
++
++module com { module sun { module star { module sheet {
++
++//=============================================================================
++/** describes an external link in a formula.
++
++ @since OOo3.1
++ */
++struct ExternalLinkInfo
++{
++ //-------------------------------------------------------------------------
++
++ /** Link type, one of <type>ExternalLinkType</type> constants.
++ */
++
++ long Type;
++
++ //-------------------------------------------------------------------------
++
++ /** Location of this link type.
++
++ Modes used:
++
++ 1. If <member>Type</member> is <const>ExternalLinkType::EXTERNAL</const>,
++ this member shall contain a string with the <b>URI</b> of a
++ document. The formula that would need this information for example
++ would contain =[1]Sheet1!A1 or ='[1]Sheet name'!A1 where [1] does
++ resolve to the URI contained in this Location member. Note that
++ the quotes cover both, the document name and the sheet name.
++
++ 2. If <member>Type</member> is <type>ExternalLinkType::DDE</type>,
++ this member shall contain a <type>DDELinkType</type> describing
++ service name, topic, and all known items of a DDE link.
++ */
++
++ any Data;
++
++};
++
++//=============================================================================
++
++}; }; }; };
++
++#endif
+diff --git offapi/com/sun/star/sheet/ExternalLinkType.idl offapi/com/sun/star/sheet/ExternalLinkType.idl
+new file mode 100644
+index 0000000..7c1b040
+--- /dev/null
++++ offapi/com/sun/star/sheet/ExternalLinkType.idl
+@@ -0,0 +1,67 @@
++/*************************************************************************
++ *
++ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
++ *
++ * Copyright 2008 by Sun Microsystems, Inc.
++ *
++ * OpenOffice.org - a multi-platform office productivity suite
++ *
++ * $RCSfile: ExternalLinkType.idl,v $
++ * $Revision: 1.1.2.1 $
++ *
++ * This file is part of OpenOffice.org.
++ *
++ * OpenOffice.org is free software: you can redistribute it and/or modify
++ * it under the terms of the GNU Lesser General Public License version 3
++ * only, as published by the Free Software Foundation.
++ *
++ * OpenOffice.org is distributed in the hope that it will be useful,
++ * but WITHOUT ANY WARRANTY; without even the implied warranty of
++ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
++ * GNU Lesser General Public License version 3 for more details
++ * (a copy is included in the LICENSE file that accompanied this code).
++ *
++ * You should have received a copy of the GNU Lesser General Public License
++ * version 3 along with OpenOffice.org. If not, see
++ * <http://www.openoffice.org/license.html>
++ * for a copy of the LGPLv3 License.
++ *
++ ************************************************************************/
++
++#ifndef __com_sun_star_sheet_ExternalLinkType_idl__
++#define __com_sun_star_sheet_ExternalLinkType_idl__
++
++//=============================================================================
++
++module com { module sun { module star { module sheet {
++
++//=============================================================================
++
++/** Constants designating the link type in
++ <type>ExternalLinkInfo</type>, used with
++ <member>FormulaParser::ExternalLinks</member>.
++
++ @since OOo3.1
++ */
++constants ExternalLinkType
++{
++ /** Unknown element type
++ */
++ const long UNKNOWN = 0;
++
++ /** URL of an external document.
++ */
++ const long DOCUMENT = 1;
++
++ /** DDE link.
++ */
++ const long DDE = 2;
++
++};
++
++//=============================================================================
++
++}; }; }; };
++
++#endif
++
+diff --git offapi/com/sun/star/sheet/ExternalReference.idl offapi/com/sun/star/sheet/ExternalReference.idl
+new file mode 100644
+index 0000000..a2bc3c7
+--- /dev/null
++++ offapi/com/sun/star/sheet/ExternalReference.idl
+@@ -0,0 +1,90 @@
++/*************************************************************************
++ *
++ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
++ *
++ * Copyright 2008 by Sun Microsystems, Inc.
++ *
++ * OpenOffice.org - a multi-platform office productivity suite
++ *
++ * $RCSfile: ExternalLinkInfo.idl,v $
++ * $Revision: 1.1.2.2 $
++ *
++ * This file is part of OpenOffice.org.
++ *
++ * OpenOffice.org is free software: you can redistribute it and/or modify
++ * it under the terms of the GNU Lesser General Public License version 3
++ * only, as published by the Free Software Foundation.
++ *
++ * OpenOffice.org is distributed in the hope that it will be useful,
++ * but WITHOUT ANY WARRANTY; without even the implied warranty of
++ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
++ * GNU Lesser General Public License version 3 for more details
++ * (a copy is included in the LICENSE file that accompanied this code).
++ *
++ * You should have received a copy of the GNU Lesser General Public License
++ * version 3 along with OpenOffice.org. If not, see
++ * <http://www.openoffice.org/license.html>
++ * for a copy of the LGPLv3 License.
++ *
++ ************************************************************************/
++
++#ifndef __com_sun_star_sheet_ExternalReference_idl__
++#define __com_sun_star_sheet_ExternalReference_idl__
++
++module com { module sun { module star { module sheet {
++
++//=============================================================================
++
++/** Data structure to store information about an external reference. An
++ external reference can be either a single cell reference, a cell range
++ reference, or a named range.
++
++ @since OOo 3.1
++ */
++struct ExternalReference
++{
++ //-------------------------------------------------------------------------
++
++ /** Index of an externally linked document. Each externally-linked document
++ has a unique index value.
++
++ <p>You can get the index value of an external document from the
++ corresponding <type scope="com::sun::star::sheet">ExternalDocLink</type>
++ instance through its attribute <type scope="com::sun::star::sheet::ExternalDocLink">TokenIndex</type>.</p>
++
++ @see com::sun::star::sheet::ExternalDocLink
++ @see com::sun::star::sheet::ExternalDocLink::TokenIndex
++ */
++ long Index;
++
++ //-------------------------------------------------------------------------
++
++ /** Name of the sheet that the external reference points to.
++
++ <p>In case of a cell range reference that spans across multiple
++ sheets, this is the name of the first sheet in that range.</p>
++
++ <p>Note that an external range name ignores this value at the moment,
++ but <i>it may make use of this data in the future when Calc supports a
++ sheet-specific range name.</i></p>
++ */
++ string SheetName;
++
++ //-------------------------------------------------------------------------
++
++ /** Reference data. This can store either <type scope="com::sun::star::sheet">SingleReference</type>
++ for a single cell reference, <type scope="com::sun::star::sheet">ComplexReference</type>
++ for a cell range reference, or simply a <type>string</type> for a range
++ name.
++
++ @see com::sun::star::sheet::SingleReference
++ @see com::sun::star::sheet::ComplexReference
++ */
++ any Reference;
++};
++
++//=============================================================================
++
++}; }; }; };
++
++#endif
diff --git offapi/com/sun/star/sheet/ExternalSheetCache.idl offapi/com/sun/star/sheet/ExternalSheetCache.idl
new file mode 100644
index 0000000..17af156
@@ -179,12 +439,25 @@
+}; }; }; };
+
+#endif
+diff --git offapi/com/sun/star/sheet/FormulaMapGroupSpecialOffset.idl offapi/com/sun/star/sheet/FormulaMapGroupSpecialOffset.idl
+index 20369b2..6fa02d0 100644
+--- offapi/com/sun/star/sheet/FormulaMapGroupSpecialOffset.idl
++++ offapi/com/sun/star/sheet/FormulaMapGroupSpecialOffset.idl
+@@ -59,6 +59,8 @@ constants FormulaMapGroupSpecialOffset
+ const long MACRO = 11;
+ const long COL_ROW_NAME = 12;
+ const long COL_ROW_NAME_AUTO = 13;
++ /// @since OOo 3.1
++ const long EXTERNAL_REFERENCE = 14;
+ };
+
+ //=============================================================================
diff --git offapi/com/sun/star/sheet/XExternalDocLink.idl offapi/com/sun/star/sheet/XExternalDocLink.idl
new file mode 100644
-index 0000000..65928c5
+index 0000000..0f3e02b
--- /dev/null
+++ offapi/com/sun/star/sheet/XExternalDocLink.idl
-@@ -0,0 +1,62 @@
+@@ -0,0 +1,84 @@
+/*************************************************************************
+ *
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
@@ -222,6 +495,8 @@
+
+module com { module sun { module star { module sheet {
+
++//=============================================================================
++
+/** Primary interface for the <type scope="com::sun::star::sheet">ExternalDocLink</type> service.
+
+ @see com::sun::star::sheet::ExternalDocLink
@@ -230,6 +505,8 @@
+ */
+interface XExternalDocLink
+{
++ //-------------------------------------------------------------------------
++
+ /** <p>This method adds a new sheet cache instance to the extternal document
+ link for a specified sheet name. If a sheet cache instance already
+ exists for the specified name, then the existing instance is returned.</p>
@@ -242,8 +519,26 @@
+ @return com::sun::star::sheet::XExternalSheetCache sheet cache instance
+ */
+ com::sun::star::sheet::XExternalSheetCache addSheetCache( [in] string aSheetName );
++
++ //-------------------------------------------------------------------------
++
++ /** Index corresponding to the external document link.
++
++ <p>This index value corresponds with the external document
++ represented by an instance of
++ <type scope="com::sun::star::sheet">ExternalDocLink</type>. This
++ value is stored within a formula token instance.</p>
++
++ <p>Each external document link has a unique index value.</p>
++
++ @see com::sun::star::sheet::FormulaToken
++ @see com::sun::star::sheet::FormulaMapGroupSpecialOffset::EXTERNAL_REFERENCE
++ */
++ [attribute, readonly] long TokenIndex;
+};
+
++//=============================================================================
++
+}; }; }; };
+
+#endif
@@ -410,20 +705,23 @@
+
+#endif
diff --git offapi/com/sun/star/sheet/makefile.mk offapi/com/sun/star/sheet/makefile.mk
-index c1d2844..16dffda 100644
+index c1d2844..09b33e7 100644
--- offapi/com/sun/star/sheet/makefile.mk
+++ offapi/com/sun/star/sheet/makefile.mk
-@@ -123,6 +123,9 @@ IDLFILES=\
+@@ -123,6 +123,12 @@ IDLFILES=\
DatabaseRangesEnumeration.idl\
DDELinkMode.idl\
DocumentSettings.idl\
+ ExternalDocLink.idl\
+ ExternalDocLinks.idl\
++ ExternalLinkInfo.idl\
++ ExternalLinkType.idl\
++ ExternalReference.idl\
+ ExternalSheetCache.idl\
FillDateMode.idl\
FillDirection.idl\
FillMode.idl\
-@@ -255,6 +258,9 @@ IDLFILES=\
+@@ -255,6 +261,9 @@ IDLFILES=\
XDocumentAuditing.idl\
XDrillDownDataSupplier.idl\
XEnhancedMouseClickBroadcaster.idl\
Modified: trunk/patches/dev300/calc-external-defined-names-sc.diff
==============================================================================
--- trunk/patches/dev300/calc-external-defined-names-sc.diff (original)
+++ trunk/patches/dev300/calc-external-defined-names-sc.diff Wed Sep 3 00:32:12 2008
@@ -1,8 +1,23 @@
diff --git sc/inc/address.hxx sc/inc/address.hxx
-index f92fc8e..f15a341 100644
+index f92fc8e..9757898 100644
--- sc/inc/address.hxx
+++ sc/inc/address.hxx
-@@ -287,6 +287,15 @@ public:
+@@ -44,6 +44,14 @@
+ #endif
+ #include "scdllapi.h"
+
++#include <com/sun/star/uno/Sequence.hxx>
++
++namespace com { namespace sun { namespace star {
++ namespace sheet {
++ struct ExternalLinkInfo;
++ }
++}}}
++
+ class ScDocument;
+
+ // The typedefs
+@@ -287,6 +295,15 @@ public:
};
static const Details detailsOOOa1;
@@ -18,29 +33,36 @@
inline ScAddress() : nRow(0), nCol(0), nTab(0) {}
inline ScAddress( SCCOL nColP, SCROW nRowP, SCTAB nTabP )
: nRow(nRowP), nCol(nColP), nTab(nTabP)
-@@ -317,8 +326,8 @@ public:
+@@ -317,8 +334,12 @@ public:
inline void GetVars( SCCOL& nColP, SCROW& nRowP, SCTAB& nTabP ) const
{ nColP = nCol; nRowP = nRow; nTabP = nTab; }
- USHORT Parse( const String&, ScDocument* = NULL,
- const Details& rDetails = detailsOOOa1);
+ USHORT Parse( const String&, ScDocument* = NULL,
-+ const Details& rDetails = detailsOOOa1, ExternalInfo* pExtInfo = NULL);
++ const Details& rDetails = detailsOOOa1,
++ ExternalInfo* pExtInfo = NULL,
++ const ::com::sun::star::uno::Sequence<
++ const ::com::sun::star::sheet::ExternalLinkInfo > * pExternalLinks = NULL );
++
void Format( String&, USHORT = 0, ScDocument* = NULL,
const Details& rDetails = detailsOOOa1) const;
-@@ -463,7 +472,8 @@ public:
+@@ -463,7 +484,11 @@ public:
inline bool In( const ScRange& ) const; // is Range& in Range?
USHORT Parse( const String&, ScDocument* = NULL,
- const ScAddress::Details& rDetails = ScAddress::detailsOOOa1 );
+ const ScAddress::Details& rDetails = ScAddress::detailsOOOa1,
-+ ScAddress::ExternalInfo* pExtInfo = NULL );
++ ScAddress::ExternalInfo* pExtInfo = NULL,
++ const ::com::sun::star::uno::Sequence<
++ const ::com::sun::star::sheet::ExternalLinkInfo > * pExternalLinks = NULL );
++
USHORT ParseAny( const String&, ScDocument* = NULL,
const ScAddress::Details& rDetails = ScAddress::detailsOOOa1 );
USHORT ParseCols( const String&, ScDocument* = NULL,
diff --git sc/inc/compiler.hrc sc/inc/compiler.hrc
-index 92b7e82..22d77cb 100644
+index 92b7e82..ec67599 100644
--- sc/inc/compiler.hrc
+++ sc/inc/compiler.hrc
@@ -39,25 +39,26 @@
@@ -66,7 +88,7 @@
-#define SC_OPCODE_ARRAY_ROW_SEP 21
-#define SC_OPCODE_ARRAY_COL_SEP 22 /* some convs use sep != col_sep */
-#define SC_OPCODE_STOP_DIV 23
-+#define SC_OPCODE_EXTERNAL_NAME 5
++#define SC_OPCODE_EXTERNAL_REF 5
+#define SC_OPCODE_IF 6 /* jump commands */
+#define SC_OPCODE_CHOSE 7
+#define SC_OPCODE_OPEN 8 /* parentheses and separators */
@@ -90,18 +112,30 @@
/*** error constants #... ***/
#define SC_OPCODE_START_ERRORS 30
diff --git sc/inc/compiler.hxx sc/inc/compiler.hxx
-index 7bb6767..85fdf91 100644
+index 7bb6767..bdffc05 100644
--- sc/inc/compiler.hxx
+++ sc/inc/compiler.hxx
-@@ -45,6 +45,7 @@
+@@ -45,6 +45,8 @@
#include <unotools/charclass.hxx>
#include <rtl/ustrbuf.hxx>
#include <com/sun/star/uno/Sequence.hxx>
++#include <com/sun/star/sheet/ExternalLinkInfo.hpp>
+#include <vector>
namespace com { namespace sun { namespace star {
namespace sheet {
-@@ -100,6 +101,7 @@ namespace com { namespace sun { namespace star {
+@@ -88,8 +90,8 @@ namespace com { namespace sun { namespace star {
+ #define SC_COMPILER_C_VALUE_VALUE 0x00002000
+ #define SC_COMPILER_C_STRING_SEP 0x00004000
+ #define SC_COMPILER_C_NAME_SEP 0x00008000 // there can be only one! '\''
+-#define SC_COMPILER_C_CHAR_IDENT 0x00010000 // identifier (built-in function) start
+-#define SC_COMPILER_C_IDENT 0x00020000 // identifier continuation
++#define SC_COMPILER_C_CHAR_IDENT 0x00010000 // identifier (built-in function) or reference start
++#define SC_COMPILER_C_IDENT 0x00020000 // identifier or reference continuation
+ #define SC_COMPILER_C_ODF_LBRACKET 0x00040000 // ODF '[' reference bracket
+ #define SC_COMPILER_C_ODF_RBRACKET 0x00080000 // ODF ']' reference bracket
+ #define SC_COMPILER_C_ODF_LABEL_OP 0x00100000 // ODF '!!' automatic intersection of labels
+@@ -100,6 +102,7 @@ namespace com { namespace sun { namespace star {
class ScDocument;
class ScMatrix;
class ScRangeData;
@@ -109,7 +143,7 @@
// constants and data types internal to compiler
-@@ -151,6 +153,15 @@ public:
+@@ -151,6 +154,15 @@ public:
bool bHasForceArray;
} sbyte;
ComplRefData aRef;
@@ -125,7 +159,7 @@
ScMatrix* pMat;
USHORT nIndex; // index into name collection
sal_Unicode cStr[ MAXSTRLEN+1 ]; // string (up to 255 characters + 0)
-@@ -180,6 +191,9 @@ public:
+@@ -180,6 +192,9 @@ public:
void SetDouble( double fVal );
void SetInt( int nVal );
void SetName( USHORT n );
@@ -135,7 +169,7 @@
void SetMatrix( ScMatrix* p );
void SetExternal(const sal_Unicode* pStr);
// These methods are ok to use, reference count not cleared.
-@@ -228,6 +242,24 @@ public:
+@@ -228,6 +243,24 @@ public:
xub_StrLen nSrcPos,
const CharClass* pCharClass) const = 0;
@@ -160,7 +194,25 @@
enum SpecialSymbolType
{
/**
-@@ -448,6 +480,7 @@ private:
+@@ -372,6 +405,7 @@ private:
+ static const Convention * const pConvOOO_A1_ODF;
+ static const Convention * const pConvXL_A1;
+ static const Convention * const pConvXL_R1C1;
++ static const Convention * const pConvXL_OOX;
+
+ static struct AddInMap
+ {
+@@ -387,6 +421,9 @@ private:
+ ScDocument* pDoc;
+ ScAddress aPos;
+
++ // For ScAddress::CONV_XL_OOX, may be set via API by MOOXML filter.
++ ::com::sun::star::uno::Sequence< const ::com::sun::star::sheet::ExternalLinkInfo > maExternalLinks;
++
+ String aCorrectedFormula; // autocorrected Formula
+ String aCorrectedSymbol; // autocorrected Symbol
+ sal_Unicode cSymbol[MAXSTRLEN]; // current Symbol
+@@ -448,6 +485,7 @@ private:
BOOL IsDoubleReference( const String& );
BOOL IsMacro( const String& );
BOOL IsNamedRange( const String& );
@@ -168,6 +220,36 @@
BOOL IsDBRange( const String& );
BOOL IsColRowName( const String& );
BOOL IsBoolean( const String& );
+@@ -540,6 +578,29 @@ public:
+ void SetGrammar( const ScGrammar::Grammar eGrammar );
+ inline ScGrammar::Grammar GetGrammar() const { return meGrammar; }
+
++private:
++ /** Set grammar and reference convention from within SetFormulaLanguage()
++ or SetGrammar().
++
++ @param eNewGrammar
++ The new grammar to be set and the associated reference convention.
++
++ @param eOldGrammar
++ The previous grammar that was active before SetFormulaLanguage().
++ */
++ void SetGrammarAndRefConvention(
++ const ScGrammar::Grammar eNewGrammar,
++ const ScGrammar::Grammar eOldGrammar );
++public:
++
++ /// Set external link info for ScAddress::CONV_XL_OOX.
++ inline void SetExternalLinks(
++ const ::com::sun::star::uno::Sequence<
++ const ::com::sun::star::sheet::ExternalLinkInfo > & rLinks )
++ {
++ maExternalLinks = rLinks;
++ }
++
+ void SetExtendedErrorDetection( bool bVal ) { mbExtendedErrorDetection = bVal; }
+
+ BOOL IsCorrected() { return bCorrected; }
diff --git sc/inc/document.hxx sc/inc/document.hxx
index a01f09b..5d4ca1f 100644
--- sc/inc/document.hxx
@@ -207,10 +289,10 @@
diff --git sc/inc/externalrefmgr.hxx sc/inc/externalrefmgr.hxx
new file mode 100644
-index 0000000..46d691d
+index 0000000..c094e14
--- /dev/null
+++ sc/inc/externalrefmgr.hxx
-@@ -0,0 +1,382 @@
+@@ -0,0 +1,383 @@
+/*************************************************************************
+ *
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
@@ -348,17 +430,18 @@
+ * not need to delete this instance since its life cycle is
+ * managed by this class.</i>
+ */
-+ ScToken* getCellData(sal_uInt16 nFileId, const String& rTabName, SCROW nRow, SCCOL nCol);
++ ScExternalRefCache::TokenRef getCellData(sal_uInt16 nFileId, const String& rTabName, SCROW nRow, SCCOL nCol);
+
+ /**
+ * Get a cached cell range data.
+ *
+ * @return a new token array instance. Note that <i>the caller must
-+ * manage the life cycle of the returned instance</i>.
++ * manage the life cycle of the returned instance</i>, which is
++ * guaranteed if the TokenArrayRef is properly used..
+ */
-+ ScTokenArray* getCellRangeData(sal_uInt16 nFileId, const String& rTabName, const ScRange& rRange);
++ ScExternalRefCache::TokenArrayRef getCellRangeData(sal_uInt16 nFileId, const String& rTabName, const ScRange& rRange);
+
-+ ScTokenArray* getRangeNameTokens(sal_uInt16 nFileId, const String& rName);
++ ScExternalRefCache::TokenArrayRef getRangeNameTokens(sal_uInt16 nFileId, const String& rName);
+ void setRangeNameTokens(sal_uInt16 nFileId, const String& rName, TokenArrayRef pArray);
+
+ void setCellData(sal_uInt16 nFileId, const String& rTabName, SCROW nRow, SCCOL nCol, TokenRef pToken);
@@ -388,9 +471,9 @@
+ * @param nFileId file ID
+ * @param rTabName table name
+ *
-+ * @return pointer to the cache table instance
++ * @return shared_ptr to the cache table instance
+ */
-+ Table* getCacheTable(sal_uInt16 nFileId, const String& rTabName, bool bCreateNew);
++ ScExternalRefCache::TableTypeRef getCacheTable(sal_uInt16 nFileId, const String& rTabName, bool bCreateNew);
+
+ void clearCache(sal_uInt16 nFileId);
+
@@ -462,10 +545,10 @@
+ explicit ScExternalRefManager(ScDocument* pDoc);
+ ~ScExternalRefManager();
+
-+ ScExternalRefCache::Table* getCacheTable(sal_uInt16 nFileId, const String& rTabName, bool bCreateNew = true);
++ ScExternalRefCache::TableTypeRef getCacheTable(sal_uInt16 nFileId, const String& rTabName, bool bCreateNew = true);
+ void storeRangeNameTokens(sal_uInt16 nFileId, const String& rName, const ScTokenArray& rArray);
+
-+ ScToken* getSingleRefToken(sal_uInt16 nFileId, const String& rTabName, const ScAddress& rCell, const ScAddress* pCurPos, SCTAB* pTab);
++ ScExternalRefCache::TokenRef getSingleRefToken(sal_uInt16 nFileId, const String& rTabName, const ScAddress& rCell, const ScAddress* pCurPos, SCTAB* pTab);
+
+ /**
+ * Get an array of tokens that consist of the specified external cell
@@ -477,10 +560,10 @@
+ * @param pCurPos current cursor position to keep track of cells that
+ * reference an external data.
+ *
-+ * @return pointer to a token array instance. <i>The caller must not
++ * @return shared_ptr to a token array instance. <i>The caller must not
+ * delete the instance returned by this method.</i>
+ */
-+ ScTokenArray* getDoubleRefTokens(sal_uInt16 nFileId, const String& rTabName, const ScRange& rRange, const ScAddress* pCurPos);
++ ScExternalRefCache::TokenArrayRef getDoubleRefTokens(sal_uInt16 nFileId, const String& rTabName, const ScRange& rRange, const ScAddress* pCurPos);
+
+ /**
+ * Get an array of tokens corresponding with a specified name in a
@@ -491,9 +574,9 @@
+ * external names for refreshing purposes. If this is
+ * NULL, then the cell will not be added to the list.
+ *
-+ * @return array of tokens composing the name
++ * @return shared_ptr to array of tokens composing the name
+ */
-+ ScTokenArray* getRangeNameTokens(sal_uInt16 nFileId, const String& rName, const ScAddress* pCurPos = NULL);
++ ScExternalRefCache::TokenArrayRef getRangeNameTokens(sal_uInt16 nFileId, const String& rName, const ScAddress* pCurPos = NULL);
+
+ const String& getOwnDocumentName() const;
+ bool isOwnDocument(const String& rFile) const;
@@ -594,7 +677,7 @@
+
+#endif
diff --git sc/inc/linkuno.hxx sc/inc/linkuno.hxx
-index b6fc524..926fed7 100644
+index b6fc524..586986e 100644
--- sc/inc/linkuno.hxx
+++ sc/inc/linkuno.hxx
@@ -36,6 +36,9 @@
@@ -623,7 +706,7 @@
class ScAreaLink;
class ScDocShell;
-@@ -493,8 +501,108 @@ public:
+@@ -493,8 +501,112 @@ public:
throw(::com::sun::star::uno::RuntimeException);
};
@@ -632,7 +715,7 @@
+class ScExternalSheetCacheObj : public cppu::WeakImplHelper1< ::com::sun::star::sheet::XExternalSheetCache >
+{
+public:
-+ explicit ScExternalSheetCacheObj(ScExternalRefCache::Table* pTable);
++ explicit ScExternalSheetCacheObj(ScExternalRefCache::TableTypeRef pTable);
+ ~ScExternalSheetCacheObj();
+
+ // XExternalSheetCache
@@ -654,7 +737,7 @@
+ ScExternalSheetCacheObj(const ScExternalSheetCacheObj&);
+
+private:
-+ ScExternalRefCache::Table* mpTable;
++ ScExternalRefCache::TableTypeRef mpTable;
+};
+
+// ============================================================================
@@ -670,25 +753,29 @@
+ SAL_CALL addSheetCache( const ::rtl::OUString& aSheetName )
+ throw (::com::sun::star::uno::RuntimeException);
+
++ // Attributes
++ virtual sal_Int32 SAL_CALL getTokenIndex()
++ throw (::com::sun::star::uno::RuntimeException);
++
+private:
+ ScExternalRefManager* mpRefMgr;
+ sal_uInt16 mnFileId;
+};
+
+// ============================================================================
-
++
+/** This is the UNO API equivalent of ScExternalRefManager. */
+class ScExternalDocLinksObj : public cppu::WeakImplHelper1< ::com::sun::star::sheet::XExternalDocLinks >
+{
+public:
+ ScExternalDocLinksObj(ScDocShell* pDocShell);
+ ~ScExternalDocLinksObj();
-
++
+ // XExternalDocLinks
+ virtual ::com::sun::star::uno::Reference< ::com::sun::star::sheet::XExternalDocLink >
+ SAL_CALL addDocLink( const ::rtl::OUString& aDocName )
+ throw (::com::sun::star::uno::RuntimeException);
-+
+
+ // XNameAccess
+ virtual ::com::sun::star::uno::Any SAL_CALL getByName( const ::rtl::OUString& aName )
+ throw(::com::sun::star::container::NoSuchElementException,
@@ -714,7 +801,7 @@
+ virtual ::com::sun::star::uno::Type SAL_CALL getElementType()
+ throw(::com::sun::star::uno::RuntimeException);
+ virtual sal_Bool SAL_CALL hasElements() throw(::com::sun::star::uno::RuntimeException);
-+
+
+private:
+ ScExternalDocLinksObj();
+ ScExternalDocLinksObj(const ScExternalDocLinksObj&);
@@ -733,14 +820,14 @@
#endif
diff --git sc/inc/opcode.hxx sc/inc/opcode.hxx
-index 285104d..b72ebad 100644
+index 285104d..e0940f7 100644
--- sc/inc/opcode.hxx
+++ sc/inc/opcode.hxx
@@ -44,6 +44,7 @@ enum OpCodeEnum
ocStop = SC_OPCODE_STOP,
ocExternal = SC_OPCODE_EXTERNAL,
ocName = SC_OPCODE_NAME,
-+ ocExternalName = SC_OPCODE_EXTERNAL_NAME,
++ ocExternalRef = SC_OPCODE_EXTERNAL_REF,
// Jump commands
ocIf = SC_OPCODE_IF,
ocChose = SC_OPCODE_CHOSE,
@@ -757,19 +844,21 @@
inline void SingleRefData::InitAddress( SCCOL nColP, SCROW nRowP, SCTAB nTabP )
diff --git sc/inc/token.hxx sc/inc/token.hxx
-index ded3a94..7e49031 100644
+index ded3a94..bc7e993 100644
--- sc/inc/token.hxx
+++ sc/inc/token.hxx
-@@ -64,7 +64,7 @@ enum StackVarEnum
+@@ -64,7 +64,9 @@ enum StackVarEnum
// cell during import, having a double
// and/or string result and a formula
// string to be compiled.
-
++ svExternalSingleRef,
++ svExternalDoubleRef,
+ svExternalName,
svError, // error token
svMissing = 0x70, // 0 or ""
svSep, // separator, ocSep, ocOpen, ocClose
-@@ -448,6 +448,69 @@ public:
+@@ -448,6 +450,69 @@ public:
};
@@ -853,8 +942,31 @@
ScToken* AddExternal( const sal_Unicode* pStr );
/** Xcl import may play dirty tricks with OpCode!=ocExternal.
Others don't use! */
+diff --git sc/inc/tokenuno.hxx sc/inc/tokenuno.hxx
+index a03b6ec..5db0e32 100644
+--- sc/inc/tokenuno.hxx
++++ sc/inc/tokenuno.hxx
+@@ -38,9 +38,8 @@
+ #include <com/sun/star/beans/XPropertySet.hpp>
+ #include <com/sun/star/sheet/XFormulaParser.hpp>
+ #include <com/sun/star/sheet/XFormulaOpCodeMapper.hpp>
+-#ifndef __com_sun_star_sheet_FormulaOpCodeMapEntry_idl__
+ #include <com/sun/star/sheet/FormulaOpCodeMapEntry.hpp>
+-#endif
++#include <com/sun/star/sheet/ExternalLinkInfo.hpp>
+ #include <cppuhelper/implbase3.hxx>
+ #include <cppuhelper/implbase2.hxx>
+ #include "address.hxx"
+@@ -70,6 +69,7 @@ class ScFormulaParserObj : public ::cppu::WeakImplHelper3<
+ {
+ private:
+ ::com::sun::star::uno::Sequence< const ::com::sun::star::sheet::FormulaOpCodeMapEntry > maOpCodeMapping;
++ ::com::sun::star::uno::Sequence< const ::com::sun::star::sheet::ExternalLinkInfo > maExternalLinks;
+ ScCompiler::OpCodeMapPtr mxOpCodeMap;
+ ScDocShell* mpDocShell;
+ ScAddress maRefPos;
diff --git sc/inc/unonames.hxx sc/inc/unonames.hxx
-index b2c45ac..51ebf60 100644
+index b2c45ac..18c858b 100644
--- sc/inc/unonames.hxx
+++ sc/inc/unonames.hxx
@@ -47,6 +47,7 @@
@@ -865,8 +977,16 @@
#define SC_UNO_COLLABELRNG "ColumnLabelRanges"
#define SC_UNO_DATABASERNG "DatabaseRanges"
#define SC_UNO_NAMEDRANGES "NamedRanges"
+@@ -604,6 +605,7 @@
+ #define SC_UNO_FORMULACONVENTION "FormulaConvention"
+ #define SC_UNO_IGNORELEADING "IgnoreLeadingSpaces"
+ #define SC_UNO_OPCODEMAP "OpCodeMap"
++#define SC_UNO_EXTERNALLINKS "ExternalLinks"
+
+ // Chart2
+ #define SC_UNONAME_ISHIDDEN "IsHidden"
diff --git sc/source/core/data/cell.cxx sc/source/core/data/cell.cxx
-index 1c7ac08..4611515 100644
+index 636f46e..fbd55d5 100644
--- sc/source/core/data/cell.cxx
+++ sc/source/core/data/cell.cxx
@@ -689,7 +689,12 @@ ScFormulaCell::ScFormulaCell( ScDocument* pDoc, const ScAddress& rNewPos,
@@ -874,7 +994,7 @@
t = pCode->GetNextReferenceOrName() )
{
- if ( t->GetType() == svIndex )
-+ if ( t->GetOpCode() == ocExternalName )
++ if ( t->GetOpCode() == ocExternalRef )
+ {
+ // External name, cell, and area references.
+ bCompile = true;
@@ -1000,10 +1120,10 @@
{
if (pLinkManager)
diff --git sc/source/core/tool/address.cxx sc/source/core/tool/address.cxx
-index 2cb5dce..e518b27 100644
+index 2cb5dce..4572ccd 100644
--- sc/source/core/tool/address.cxx
+++ sc/source/core/tool/address.cxx
-@@ -35,6 +35,7 @@
+@@ -35,12 +35,15 @@
#include "global.hxx"
#include "compiler.hxx"
#include "document.hxx"
@@ -1011,7 +1131,15 @@
#include "globstr.hrc"
#include <sal/alloca.h>
-@@ -68,6 +69,49 @@ void ScAddress::Details::SetPos ( const ScDocument* pDoc,
+
+ #include <com/sun/star/frame/XModel.hpp>
+ #include <com/sun/star/beans/XPropertySet.hpp>
++#include <com/sun/star/sheet/ExternalLinkInfo.hpp>
++#include <com/sun/star/sheet/ExternalLinkType.hpp>
+ #include <sfx2/objsh.hxx>
+ #include <tools/urlobj.hxx>
+ using namespace ::com::sun::star;
+@@ -68,6 +71,49 @@ void ScAddress::Details::SetPos ( const ScDocument* pDoc,
#include <iostream>
@@ -1061,7 +1189,7 @@
static long int
sal_Unicode_strtol ( const sal_Unicode* p,
const sal_Unicode** pEnd )
-@@ -102,31 +146,18 @@ sal_Unicode_strtol ( const sal_Unicode* p,
+@@ -102,31 +148,18 @@ sal_Unicode_strtol ( const sal_Unicode* p,
// Returns NULL if the string should be a sheet name, but is invalid
// Returns a pointer to the first character after the sheet name
static const sal_Unicode *
@@ -1096,7 +1224,7 @@
return NULL;
}
else
-@@ -190,26 +221,7 @@ lcl_XL_ParseSheetRef( const sal_Unicode *start,
+@@ -190,26 +223,7 @@ lcl_XL_ParseSheetRef( const sal_Unicode *start,
aTabName.Append( start, sal::static_int_cast<xub_StrLen>( p - start ) );
}
@@ -1124,7 +1252,16 @@
return p;
}
-@@ -227,39 +239,33 @@ lcl_ScRange_Parse_XL_Header( ScRange& r,
+@@ -220,46 +234,71 @@ lcl_ScRange_Parse_XL_Header( ScRange& r,
+ String& rExternDocName,
+ String& rStartTabName,
+ String& rEndTabName,
+- USHORT& nFlags )
++ USHORT& nFlags,
++ const uno::Sequence< const sheet::ExternalLinkInfo > * pExternalLinks )
+ {
+ const sal_Unicode* startTabs, *start = p;
+
// Is this an external reference ?
rStartTabName.Erase();
rEndTabName.Erase();
@@ -1161,14 +1298,44 @@
return start;
rExternDocName.Append( start+1, sal::static_int_cast<xub_StrLen>( p-(start+1) ) );
}
++ ++p;
- rExternDocName = ScGlobal::GetAbsDocName( rExternDocName,
- pDoc->GetDocumentShell() );
- if( *p != ']' )
- return start;
- p++;
++ // 1-based, sequence starts with an empty element.
++ if (pExternalLinks && pExternalLinks->getLength() > 1)
++ {
++ // A numeric "document name" is an index into the sequence.
++ if (CharClass::isAsciiNumeric( rExternDocName))
++ {
++ sal_Int32 i = rExternDocName.ToInt32();
++ if (i <= 0 || i >= pExternalLinks->getLength())
++ return start;
++ const sheet::ExternalLinkInfo & rInfo = (*pExternalLinks)[i];
++ switch (rInfo.Type)
++ {
++ case sheet::ExternalLinkType::DOCUMENT :
++ {
++ rtl::OUString aStr;
++ if (!(rInfo.Data >>= aStr))
++ {
++ DBG_ERROR1( "lcl_ScRange_Parse_XL_Header: Data type mismatch for ExternalLinkInfo %d", i);
++ return start;
++ }
++ rExternDocName = aStr;
++ }
++ break;
++ default:
++ DBG_ERROR2( "lcl_ScRange_Parse_XL_Header: unhandled ExternalLinkType %d for index %d",
++ rInfo.Type, i);
++ return start;
++ }
++ }
++ }
+ rExternDocName = ScGlobal::GetAbsDocName(rExternDocName, pDoc->GetDocumentShell());
-+ ++p;
}
startTabs = p;
@@ -1177,7 +1344,7 @@
if( NULL == p )
return start; // invalid tab
if( p != startTabs )
-@@ -267,7 +273,7 @@ lcl_ScRange_Parse_XL_Header( ScRange& r,
+@@ -267,7 +306,7 @@ lcl_ScRange_Parse_XL_Header( ScRange& r,
nFlags |= SCA_VALID_TAB | SCA_TAB_3D | SCA_TAB_ABSOLUTE;
if( *p == ':' ) // 3d ref
{
@@ -1186,7 +1353,7 @@
if( p == NULL )
return start; // invalid tab
nFlags |= SCA_VALID_TAB2 | SCA_TAB2_3D | SCA_TAB2_ABSOLUTE;
-@@ -289,45 +295,36 @@ lcl_ScRange_Parse_XL_Header( ScRange& r,
+@@ -289,45 +328,36 @@ lcl_ScRange_Parse_XL_Header( ScRange& r,
// Use the current tab, it needs to be passed in. : r.aEnd.SetTab( .. );
}
@@ -1255,19 +1422,22 @@
}
-@@ -427,7 +424,7 @@ lcl_ScRange_Parse_XL_R1C1( ScRange& r,
+@@ -427,7 +457,8 @@ lcl_ScRange_Parse_XL_R1C1( ScRange& r,
const sal_Unicode* p,
ScDocument* pDoc,
const ScAddress::Details& rDetails,
- BOOL bOnlyAcceptSingle )
-+ BOOL bOnlyAcceptSingle, ScAddress::ExternalInfo* pExtInfo )
++ BOOL bOnlyAcceptSingle,
++ ScAddress::ExternalInfo* pExtInfo )
{
const sal_Unicode* pTmp = NULL;
String aExternDocName, aStartTabName, aEndTabName;
-@@ -442,6 +439,18 @@ lcl_ScRange_Parse_XL_R1C1( ScRange& r,
+@@ -441,7 +472,19 @@ lcl_ScRange_Parse_XL_R1C1( ScRange& r,
+ }
#endif
p = lcl_ScRange_Parse_XL_Header( r, p, pDoc,
- aExternDocName, aStartTabName, aEndTabName, nFlags );
+- aExternDocName, aStartTabName, aEndTabName, nFlags );
++ aExternDocName, aStartTabName, aEndTabName, nFlags, NULL );
+
+ if (aExternDocName.Len() > 0)
+ {
@@ -1283,7 +1453,7 @@
if( NULL == p )
return 0;
-@@ -480,8 +489,7 @@ lcl_ScRange_Parse_XL_R1C1( ScRange& r,
+@@ -480,8 +523,7 @@ lcl_ScRange_Parse_XL_R1C1( ScRange& r,
r.aStart.SetCol( 0 );
r.aEnd.SetCol( MAXCOL );
@@ -1293,7 +1463,7 @@
}
else if( NULL == (p = lcl_r1c1_get_col( p, rDetails, &r.aStart, &nFlags )))
goto failed;
-@@ -501,8 +509,7 @@ lcl_ScRange_Parse_XL_R1C1( ScRange& r,
+@@ -501,8 +543,7 @@ lcl_ScRange_Parse_XL_R1C1( ScRange& r,
return nFlags;
}
@@ -1303,7 +1473,7 @@
}
p = pTmp;
-@@ -517,8 +524,7 @@ lcl_ScRange_Parse_XL_R1C1( ScRange& r,
+@@ -517,8 +558,7 @@ lcl_ScRange_Parse_XL_R1C1( ScRange& r,
}
nFlags |= (nFlags2 << 4);
@@ -1313,7 +1483,7 @@
}
else if( *p == 'C' || *p == 'c' ) // full col C#
{
-@@ -550,8 +556,7 @@ lcl_ScRange_Parse_XL_R1C1( ScRange& r,
+@@ -550,8 +590,7 @@ lcl_ScRange_Parse_XL_R1C1( ScRange& r,
r.aStart.SetRow( 0 );
r.aEnd.SetRow( MAXROW );
@@ -1323,20 +1493,23 @@
}
failed :
-@@ -604,7 +609,8 @@ static USHORT
+@@ -604,7 +643,9 @@ static USHORT
lcl_ScRange_Parse_XL_A1( ScRange& r,
const sal_Unicode* p,
ScDocument* pDoc,
- BOOL bOnlyAcceptSingle )
+ BOOL bOnlyAcceptSingle,
-+ ScAddress::ExternalInfo* pExtInfo )
++ ScAddress::ExternalInfo* pExtInfo,
++ const uno::Sequence< const sheet::ExternalLinkInfo > * pExternalLinks )
{
const sal_Unicode* tmp1, *tmp2;
String aExternDocName, aStartTabName, aEndTabName; // for external link table
-@@ -619,6 +625,18 @@ lcl_ScRange_Parse_XL_A1( ScRange& r,
+@@ -618,7 +659,19 @@ lcl_ScRange_Parse_XL_A1( ScRange& r,
+ }
#endif
p = lcl_ScRange_Parse_XL_Header( r, p, pDoc,
- aExternDocName, aStartTabName, aEndTabName, nFlags );
+- aExternDocName, aStartTabName, aEndTabName, nFlags );
++ aExternDocName, aStartTabName, aEndTabName, nFlags, pExternalLinks );
+
+ if (aExternDocName.Len() > 0)
+ {
@@ -1352,7 +1525,7 @@
if( NULL == p )
return 0;
-@@ -640,8 +658,7 @@ lcl_ScRange_Parse_XL_A1( ScRange& r,
+@@ -640,8 +693,7 @@ lcl_ScRange_Parse_XL_A1( ScRange& r,
SCA_VALID_COL | SCA_VALID_COL2 |
SCA_COL_ABSOLUTE | SCA_COL2_ABSOLUTE;
nFlags |= (nFlags2 << 4);
@@ -1362,7 +1535,7 @@
}
tmp2 = lcl_a1_get_row( tmp1, &r.aStart, &nFlags );
-@@ -661,8 +678,7 @@ lcl_ScRange_Parse_XL_A1( ScRange& r,
+@@ -661,8 +713,7 @@ lcl_ScRange_Parse_XL_A1( ScRange& r,
SCA_VALID_ROW | SCA_VALID_ROW2 |
SCA_ROW_ABSOLUTE | SCA_ROW2_ABSOLUTE;
nFlags |= (nFlags2 << 4);
@@ -1372,7 +1545,7 @@
}
// prepare as if it's a singleton, in case we want to fall back */
-@@ -672,8 +688,7 @@ lcl_ScRange_Parse_XL_A1( ScRange& r,
+@@ -672,8 +723,7 @@ lcl_ScRange_Parse_XL_A1( ScRange& r,
if ( bOnlyAcceptSingle )
{
if ( *tmp2 == 0 )
@@ -1382,7 +1555,7 @@
else
{
// any trailing invalid character must invalidate the address.
-@@ -692,12 +707,11 @@ lcl_ScRange_Parse_XL_A1( ScRange& r,
+@@ -692,12 +742,11 @@ lcl_ScRange_Parse_XL_A1( ScRange& r,
p = tmp2;
tmp1 = lcl_a1_get_col( p+1, &r.aEnd, &nFlags2 );
if( !tmp1 ) // strange, but valid singleton
@@ -1398,7 +1571,7 @@
if ( *tmp2 != 0 )
{
-@@ -708,45 +722,31 @@ lcl_ScRange_Parse_XL_A1( ScRange& r,
+@@ -708,45 +757,31 @@ lcl_ScRange_Parse_XL_A1( ScRange& r,
}
nFlags |= (nFlags2 << 4);
@@ -1457,7 +1630,7 @@
}
SCCOL nCol = 0;
-@@ -762,25 +762,11 @@ lcl_ScAddress_Parse_OOo( BOOL& bExternal, const sal_Unicode* p,
+@@ -762,25 +797,11 @@ lcl_ScAddress_Parse_OOo( BOOL& bExternal, const sal_Unicode* p,
if (*p == '$')
nRes |= SCA_TAB_ABSOLUTE, p++;
@@ -1488,7 +1661,7 @@
while (*p)
{
-@@ -795,35 +781,11 @@ lcl_ScAddress_Parse_OOo( BOOL& bExternal, const sal_Unicode* p,
+@@ -795,35 +816,11 @@ lcl_ScAddress_Parse_OOo( BOOL& bExternal, const sal_Unicode* p,
}
if( *p++ != '.' )
nBits = 0;
@@ -1528,7 +1701,7 @@
}
else
nBits = 0;
-@@ -884,16 +846,31 @@ lcl_ScAddress_Parse_OOo( BOOL& bExternal, const sal_Unicode* p,
+@@ -884,16 +881,31 @@ lcl_ScAddress_Parse_OOo( BOOL& bExternal, const sal_Unicode* p,
if( !nBits )
p = q;
}
@@ -1552,7 +1725,7 @@
+ pExtInfo->mnFileId = nFileId;
+ }
+
-+ if (pRefMgr->getSingleRefToken(nFileId, aTab, ScAddress(nCol, nRow, 0), NULL, &nTab))
++ if (pRefMgr->getSingleRefToken(nFileId, aTab, ScAddress(nCol, nRow, 0), NULL, &nTab).get())
+ {
+ nRes |= SCA_VALID_TAB;
+ }
@@ -1566,7 +1739,7 @@
if ( !(nRes & SCA_VALID_ROW) && (nRes & SCA_VALID_COL)
&& !( (nRes & SCA_TAB_3D) && (nRes & SCA_VALID_TAB)) )
{ // keine Row, keine Tab, aber Col => DM (...), B (...) o.ae.
-@@ -912,9 +889,8 @@ lcl_ScAddress_Parse_OOo( BOOL& bExternal, const sal_Unicode* p,
+@@ -912,9 +924,10 @@ lcl_ScAddress_Parse_OOo( BOOL& bExternal, const sal_Unicode* p,
}
static USHORT
@@ -1574,11 +1747,13 @@
- ScDocument* pDoc, ScAddress& rAddr,
- const ScAddress::Details& rDetails )
+lcl_ScAddress_Parse ( const sal_Unicode* p, ScDocument* pDoc, ScAddress& rAddr,
-+ const ScAddress::Details& rDetails, ScAddress::ExternalInfo* pExtInfo = NULL )
++ const ScAddress::Details& rDetails,
++ ScAddress::ExternalInfo* pExtInfo = NULL,
++ const uno::Sequence< const sheet::ExternalLinkInfo > * pExternalLinks = NULL )
{
if( !*p )
return 0;
-@@ -924,20 +900,20 @@ lcl_ScAddress_Parse ( BOOL& bExternal, const sal_Unicode* p,
+@@ -924,20 +937,22 @@ lcl_ScAddress_Parse ( BOOL& bExternal, const sal_Unicode* p,
default :
case ScAddress::CONV_OOO:
{
@@ -1587,10 +1762,12 @@
}
case ScAddress::CONV_XL_A1:
++ case ScAddress::CONV_XL_OOX:
{
ScRange r = rAddr;
- USHORT nFlags = lcl_ScRange_Parse_XL_A1( r, p, pDoc, TRUE );
-+ USHORT nFlags = lcl_ScRange_Parse_XL_A1( r, p, pDoc, TRUE, pExtInfo );
++ USHORT nFlags = lcl_ScRange_Parse_XL_A1( r, p, pDoc, TRUE, pExtInfo,
++ (rDetails.eConv == ScAddress::CONV_XL_OOX ? pExternalLinks : NULL) );
rAddr = r.aStart;
return nFlags;
}
@@ -1602,7 +1779,7 @@
rAddr = r.aStart;
return nFlags;
}
-@@ -949,9 +925,8 @@ bool ConvertSingleRef( ScDocument* pDoc, const String& rRefString,
+@@ -949,9 +964,8 @@ bool ConvertSingleRef( ScDocument* pDoc, const String& rRefString,
SCTAB nDefTab, ScRefAddress& rRefAddress,
const ScAddress::Details& rDetails )
{
@@ -1613,20 +1790,22 @@
if( nRes & SCA_VALID )
{
rRefAddress.Set( aAddr,
-@@ -988,10 +963,9 @@ bool ConvertDoubleRef( ScDocument* pDoc, const String& rRefString, SCTAB nDefTab
+@@ -988,10 +1002,11 @@ bool ConvertDoubleRef( ScDocument* pDoc, const String& rRefString, SCTAB nDefTab
USHORT ScAddress::Parse( const String& r, ScDocument* pDoc,
- const Details& rDetails)
-+ const Details& rDetails, ExternalInfo* pExtInfo )
++ const Details& rDetails,
++ ExternalInfo* pExtInfo,
++ const uno::Sequence< const sheet::ExternalLinkInfo > * pExternalLinks )
{
- BOOL bExternal = FALSE;
- return lcl_ScAddress_Parse( bExternal, r.GetBuffer(), pDoc, *this, rDetails );
-+ return lcl_ScAddress_Parse( r.GetBuffer(), pDoc, *this, rDetails, pExtInfo );
++ return lcl_ScAddress_Parse( r.GetBuffer(), pDoc, *this, rDetails, pExtInfo, pExternalLinks );
}
-@@ -1060,7 +1034,7 @@ void ScRange::ExtendTo( const ScRange& rRange )
+@@ -1060,7 +1075,7 @@ void ScRange::ExtendTo( const ScRange& rRange )
}
static USHORT
@@ -1635,7 +1814,7 @@
{
USHORT nRes1 = 0, nRes2 = 0;
xub_StrLen nTmp = 0;
-@@ -1073,13 +1047,12 @@ lcl_ScRange_Parse_OOo( ScRange &aRange, const String& r, ScDocument* pDoc )
+@@ -1073,13 +1088,12 @@ lcl_ScRange_Parse_OOo( ScRange &aRange, const String& r, ScDocument* pDoc )
String aTmp( r );
sal_Unicode* p = aTmp.GetBufferAccess();
p[ nPos ] = 0;
@@ -1652,16 +1831,18 @@
nRes2 &= ~SCA_VALID_TAB; // #REF!
else
{
-@@ -1132,7 +1105,7 @@ lcl_ScRange_Parse_OOo( ScRange &aRange, const String& r, ScDocument* pDoc )
+@@ -1132,7 +1146,9 @@ lcl_ScRange_Parse_OOo( ScRange &aRange, const String& r, ScDocument* pDoc )
}
USHORT ScRange::Parse( const String& r, ScDocument* pDoc,
- const ScAddress::Details& rDetails )
-+ const ScAddress::Details& rDetails, ScAddress::ExternalInfo* pExtInfo )
++ const ScAddress::Details& rDetails,
++ ScAddress::ExternalInfo* pExtInfo,
++ const uno::Sequence< const sheet::ExternalLinkInfo > * pExternalLinks )
{
if ( r.Len() <= 0 )
return 0;
-@@ -1141,13 +1114,13 @@ USHORT ScRange::Parse( const String& r, ScDocument* pDoc,
+@@ -1141,13 +1157,15 @@ USHORT ScRange::Parse( const String& r, ScDocument* pDoc,
{
default :
case ScAddress::CONV_OOO:
@@ -1670,7 +1851,9 @@
case ScAddress::CONV_XL_A1:
- return lcl_ScRange_Parse_XL_A1( *this, r.GetBuffer(), pDoc, FALSE );
-+ return lcl_ScRange_Parse_XL_A1( *this, r.GetBuffer(), pDoc, FALSE, pExtInfo );
++ case ScAddress::CONV_XL_OOX:
++ return lcl_ScRange_Parse_XL_A1( *this, r.GetBuffer(), pDoc, FALSE, pExtInfo,
++ (rDetails.eConv == ScAddress::CONV_XL_OOX ? pExternalLinks : NULL) );
case ScAddress::CONV_XL_R1C1:
- return lcl_ScRange_Parse_XL_R1C1( *this, r.GetBuffer(), pDoc, rDetails, FALSE );
@@ -1678,8 +1861,56 @@
}
}
+@@ -1187,6 +1205,7 @@ USHORT ScRange::ParseCols( const String& rStr, ScDocument* pDoc,
+ default :
+ case ScAddress::CONV_OOO: // No full col refs in OOO yet, assume XL notation
+ case ScAddress::CONV_XL_A1:
++ case ScAddress::CONV_XL_OOX:
+ if (NULL != (p = lcl_a1_get_col( p, &aStart, &ignored ) ) )
+ {
+ if( p[0] == ':')
+@@ -1245,6 +1264,7 @@ USHORT ScRange::ParseRows( const String& rStr, ScDocument* pDoc,
+ default :
+ case ScAddress::CONV_OOO: // No full row refs in OOO yet, assume XL notation
+ case ScAddress::CONV_XL_A1:
++ case ScAddress::CONV_XL_OOX:
+ if (NULL != (p = lcl_a1_get_row( p, &aStart, &ignored ) ) )
+ {
+ if( p[0] == ':')
+@@ -1429,6 +1449,7 @@ void ScAddress::Format( String& r, USHORT nFlags, ScDocument* pDoc,
+
+ case CONV_XL_A1:
+ case CONV_XL_R1C1:
++ case CONV_XL_OOX:
+ if (aDocName.Len() > 0)
+ {
+ r += '[';
+@@ -1446,6 +1467,7 @@ void ScAddress::Format( String& r, USHORT nFlags, ScDocument* pDoc,
+ default :
+ case CONV_OOO:
+ case CONV_XL_A1:
++ case CONV_XL_OOX:
+ if( nFlags & SCA_VALID_COL )
+ lcl_a1_append_c ( r, nCol, nFlags & SCA_COL_ABSOLUTE );
+ if( nFlags & SCA_VALID_ROW )
+@@ -1565,6 +1587,7 @@ void ScRange::Format( String& r, USHORT nFlags, ScDocument* pDoc,
+ break;
+
+ case ScAddress::CONV_XL_A1:
++ case ScAddress::CONV_XL_OOX:
+ lcl_ScRange_Format_XL_Header( r, *this, nFlags, pDoc, rDetails );
+ if( aStart.Col() == 0 && aEnd.Col() >= MAXCOL )
+ {
+@@ -1688,6 +1711,7 @@ String ScAddress::GetColRowString( bool bAbsolute,
+ default :
+ case ScAddress::CONV_OOO:
+ case ScAddress::CONV_XL_A1:
++ case ScAddress::CONV_XL_OOX:
+ if (bAbsolute)
+ aString.Append( '$' );
+
diff --git sc/source/core/tool/compiler.cxx sc/source/core/tool/compiler.cxx
-index 918332d..d9b0549 100644
+index 918332d..f11442e 100644
--- sc/source/core/tool/compiler.cxx
+++ sc/source/core/tool/compiler.cxx
@@ -74,9 +74,11 @@
@@ -1694,7 +1925,180 @@
#if OSL_DEBUG_LEVEL > 1
// For some unknown reason the identical dbg_dump utilities in
-@@ -1191,7 +1193,7 @@ static bool lcl_isValidQuotedText( const String& rFormula, xub_StrLen nSrcPos, P
+@@ -109,7 +111,7 @@ ScCompiler::NonConstOpCodeMapPtr ScCompiler::mxSymbolsPODF;
+ ScCompiler::NonConstOpCodeMapPtr ScCompiler::mxSymbolsNative;
+ ScCompiler::NonConstOpCodeMapPtr ScCompiler::mxSymbolsEnglish;
+ CharClass* ScCompiler::pCharClassEnglish = NULL;
+-const ScCompiler::Convention* ScCompiler::pConventions[ ] = { NULL, NULL, NULL, NULL };
++const ScCompiler::Convention* ScCompiler::pConventions[ ] = { NULL, NULL, NULL, NULL, NULL, NULL };
+
+ enum ScanState
+ {
+@@ -680,20 +682,15 @@ void ScCompiler::SetGrammar( const ScGrammar::Grammar eGrammar )
+ xMap = ScCompiler::GetOpCodeMap( ::com::sun::star::sheet::FormulaLanguage::NATIVE);
+ eMyGrammar = xMap->getGrammar();
+ }
+- SetFormulaLanguage( xMap);
+
++ // Save old grammar for call to SetGrammarAndRefConvention().
+ ScGrammar::Grammar eOldGrammar = GetGrammar();
+- meGrammar = eMyGrammar; //! SetRefConvention needs the new grammar set!
+- ScAddress::Convention eConv = ScGrammar::extractRefConvention( eMyGrammar);
+- if (eConv == ScAddress::CONV_UNSPECIFIED && eOldGrammar == ScGrammar::GRAM_UNSPECIFIED)
+- {
+- if (NULL != pDoc)
+- SetRefConvention( pDoc->GetAddressConvention());
+- else
+- SetRefConvention( pConvOOO_A1);
+- }
+- else
+- SetRefConvention( eConv );
++ // This also sets the grammar associated with the map!
++ SetFormulaLanguage( xMap);
++
++ // Override if necessary.
++ if (eMyGrammar != GetGrammar())
++ SetGrammarAndRefConvention( eMyGrammar, eOldGrammar);
+ }
+
+ // static
+@@ -737,10 +734,28 @@ void ScCompiler::SetFormulaLanguage( const ScCompiler::OpCodeMapPtr & xMap )
+ }
+ else
+ pCharClass = ScGlobal::pCharClass;
++ SetGrammarAndRefConvention( mxSymbols->getGrammar(), GetGrammar());
+ }
+ }
+
+
++void ScCompiler::SetGrammarAndRefConvention(
++ const ScGrammar::Grammar eNewGrammar, const ScGrammar::Grammar eOldGrammar )
++{
++ meGrammar = eNewGrammar; //! SetRefConvention needs the new grammar set!
++ ScAddress::Convention eConv = ScGrammar::extractRefConvention( meGrammar);
++ if (eConv == ScAddress::CONV_UNSPECIFIED && eOldGrammar == ScGrammar::GRAM_UNSPECIFIED)
++ {
++ if (pDoc)
++ SetRefConvention( pDoc->GetAddressConvention());
++ else
++ SetRefConvention( pConvOOO_A1);
++ }
++ else
++ SetRefConvention( eConv );
++}
++
++
+ //-----------------------------------------------------------------------------
+
+ void ScCompiler::OpCodeMap::putOpCode( const String & rStr, const OpCode eOp )
+@@ -866,20 +881,21 @@ ScCompiler::OpCodeMap::createSequenceOfAvailableMappings( const sal_Int32 nGroup
+ sal_Int32 nOff;
+ OpCode eOp;
+ } aMap[] = {
+- { FormulaMapGroupSpecialOffset::PUSH , ocPush } ,
+- { FormulaMapGroupSpecialOffset::CALL , ocCall } ,
+- { FormulaMapGroupSpecialOffset::STOP , ocStop } ,
+- { FormulaMapGroupSpecialOffset::EXTERNAL , ocExternal } ,
+- { FormulaMapGroupSpecialOffset::NAME , ocName } ,
+- { FormulaMapGroupSpecialOffset::NO_NAME , ocNoName } ,
+- { FormulaMapGroupSpecialOffset::MISSING , ocMissing } ,
+- { FormulaMapGroupSpecialOffset::BAD , ocBad } ,
+- { FormulaMapGroupSpecialOffset::SPACES , ocSpaces } ,
+- { FormulaMapGroupSpecialOffset::MAT_REF , ocMatRef } ,
+- { FormulaMapGroupSpecialOffset::DB_AREA , ocDBArea } ,
+- { FormulaMapGroupSpecialOffset::MACRO , ocMacro } ,
+- { FormulaMapGroupSpecialOffset::COL_ROW_NAME , ocColRowName } ,
+- { FormulaMapGroupSpecialOffset::COL_ROW_NAME_AUTO , ocColRowNameAuto }
++ { FormulaMapGroupSpecialOffset::PUSH , ocPush } ,
++ { FormulaMapGroupSpecialOffset::CALL , ocCall } ,
++ { FormulaMapGroupSpecialOffset::STOP , ocStop } ,
++ { FormulaMapGroupSpecialOffset::EXTERNAL , ocExternal } ,
++ { FormulaMapGroupSpecialOffset::NAME , ocName } ,
++ { FormulaMapGroupSpecialOffset::NO_NAME , ocNoName } ,
++ { FormulaMapGroupSpecialOffset::MISSING , ocMissing } ,
++ { FormulaMapGroupSpecialOffset::BAD , ocBad } ,
++ { FormulaMapGroupSpecialOffset::SPACES , ocSpaces } ,
++ { FormulaMapGroupSpecialOffset::MAT_REF , ocMatRef } ,
++ { FormulaMapGroupSpecialOffset::DB_AREA , ocDBArea } ,
++ { FormulaMapGroupSpecialOffset::MACRO , ocMacro } ,
++ { FormulaMapGroupSpecialOffset::COL_ROW_NAME , ocColRowName } ,
++ { FormulaMapGroupSpecialOffset::COL_ROW_NAME_AUTO , ocColRowNameAuto } ,
++ { FormulaMapGroupSpecialOffset::EXTERNAL_REFERENCE , ocExternalRef }
+ };
+ const size_t nCount = sizeof(aMap)/sizeof(aMap[0]);
+ // Preallocate vector elements.
+@@ -1078,7 +1094,7 @@ ScCompiler::Convention::Convention( ScAddress::Convention eConv )
+ /* */ t[32] = SC_COMPILER_C_CHAR_DONTCARE | SC_COMPILER_C_WORD_SEP | SC_COMPILER_C_VALUE_SEP;
+ /* ! */ t[33] = SC_COMPILER_C_CHAR | SC_COMPILER_C_WORD_SEP | SC_COMPILER_C_VALUE_SEP;
+ if (ScAddress::CONV_ODF == meConv)
+- t[33] |= SC_COMPILER_C_ODF_LABEL_OP;
++/* ! */ t[33] |= SC_COMPILER_C_ODF_LABEL_OP;
+ /* " */ t[34] = SC_COMPILER_C_CHAR_STRING | SC_COMPILER_C_STRING_SEP;
+ /* # */ t[35] = SC_COMPILER_C_WORD_SEP;
+ /* $ */ t[36] = SC_COMPILER_C_CHAR_WORD | SC_COMPILER_C_WORD | SC_COMPILER_C_CHAR_IDENT | SC_COMPILER_C_IDENT;
+@@ -1093,8 +1109,10 @@ ScCompiler::Convention::Convention( ScAddress::Convention eConv )
+ /* - */ t[45] = SC_COMPILER_C_CHAR | SC_COMPILER_C_WORD_SEP | SC_COMPILER_C_VALUE_EXP | SC_COMPILER_C_VALUE_SIGN;
+ /* . */ t[46] = SC_COMPILER_C_WORD | SC_COMPILER_C_CHAR_VALUE | SC_COMPILER_C_VALUE | SC_COMPILER_C_IDENT;
+ /* / */ t[47] = SC_COMPILER_C_CHAR | SC_COMPILER_C_WORD_SEP | SC_COMPILER_C_VALUE_SEP;
+-for (i = 48; i < 58; i++)
++
++ for (i = 48; i < 58; i++)
+ /* 0-9 */ t[i] = SC_COMPILER_C_CHAR_VALUE | SC_COMPILER_C_WORD | SC_COMPILER_C_VALUE | SC_COMPILER_C_VALUE_EXP | SC_COMPILER_C_VALUE_VALUE | SC_COMPILER_C_IDENT;
++
+ /* : */ t[58] = SC_COMPILER_C_CHAR | SC_COMPILER_C_WORD;
+ /* ; */ t[59] = SC_COMPILER_C_CHAR | SC_COMPILER_C_WORD_SEP | SC_COMPILER_C_VALUE_SEP;
+ /* < */ t[60] = SC_COMPILER_C_CHAR_BOOL | SC_COMPILER_C_WORD_SEP | SC_COMPILER_C_VALUE_SEP;
+@@ -1102,8 +1120,10 @@ for (i = 48; i < 58; i++)
+ /* > */ t[62] = SC_COMPILER_C_CHAR_BOOL | SC_COMPILER_C_BOOL | SC_COMPILER_C_WORD_SEP | SC_COMPILER_C_VALUE_SEP;
+ /* ? */ t[63] = SC_COMPILER_C_CHAR_WORD | SC_COMPILER_C_WORD;
+ /* @ */ // FREE
+-for (i = 65; i < 91; i++)
++
++ for (i = 65; i < 91; i++)
+ /* A-Z */ t[i] = SC_COMPILER_C_CHAR_WORD | SC_COMPILER_C_WORD | SC_COMPILER_C_CHAR_IDENT | SC_COMPILER_C_IDENT;
++
+ if (ScAddress::CONV_ODF == meConv)
+ {
+ /* [ */ t[91] = SC_COMPILER_C_ODF_LBRACKET;
+@@ -1119,14 +1139,17 @@ for (i = 65; i < 91; i++)
+ /* ^ */ t[94] = SC_COMPILER_C_CHAR | SC_COMPILER_C_WORD_SEP | SC_COMPILER_C_VALUE_SEP;
+ /* _ */ t[95] = SC_COMPILER_C_CHAR_WORD | SC_COMPILER_C_WORD | SC_COMPILER_C_CHAR_IDENT | SC_COMPILER_C_IDENT;
+ /* ` */ // FREE
+-for (i = 97; i < 123; i++)
++
++ for (i = 97; i < 123; i++)
+ /* a-z */ t[i] = SC_COMPILER_C_CHAR_WORD | SC_COMPILER_C_WORD | SC_COMPILER_C_CHAR_IDENT | SC_COMPILER_C_IDENT;
++
+ /* { */ t[123] = SC_COMPILER_C_CHAR | SC_COMPILER_C_WORD_SEP | SC_COMPILER_C_VALUE_SEP; // array open
+ /* | */ t[124] = SC_COMPILER_C_CHAR | SC_COMPILER_C_WORD_SEP | SC_COMPILER_C_VALUE_SEP; // array row sep (Should be OOo specific)
+ /* } */ t[125] = SC_COMPILER_C_CHAR | SC_COMPILER_C_WORD_SEP | SC_COMPILER_C_VALUE_SEP; // array close
+ /* ~ */ t[126] = SC_COMPILER_C_CHAR; // OOo specific
+ /* 127 */ // FREE
+- if( ScAddress::CONV_XL_A1 == meConv || ScAddress::CONV_XL_R1C1 == meConv )
++
++ if( ScAddress::CONV_XL_A1 == meConv || ScAddress::CONV_XL_R1C1 == meConv || ScAddress::CONV_XL_OOX == meConv )
+ {
+ /* */ t[32] |= SC_COMPILER_C_WORD;
+ /* ! */ t[33] |= SC_COMPILER_C_IDENT | SC_COMPILER_C_WORD;
+@@ -1165,9 +1188,14 @@ for (i = 97; i < 123; i++)
+
+ if( ScAddress::CONV_XL_R1C1 == meConv )
+ {
+- /* - */ t[45] |= SC_COMPILER_C_IDENT;
+- /* [ */ t[91] |= SC_COMPILER_C_IDENT;
+- /* ] */ t[93] |= SC_COMPILER_C_IDENT;
++/* - */ t[45] |= SC_COMPILER_C_IDENT;
++/* [ */ t[91] |= SC_COMPILER_C_IDENT;
++/* ] */ t[93] |= SC_COMPILER_C_IDENT;
++ }
++ if( ScAddress::CONV_XL_OOX == meConv )
++ {
++/* [ */ t[91] |= SC_COMPILER_C_CHAR_IDENT;
++/* ] */ t[93] |= SC_COMPILER_C_IDENT;
+ }
+ }
+ }
+@@ -1191,7 +1219,7 @@ static bool lcl_isValidQuotedText( const String& rFormula, xub_StrLen nSrcPos, P
{
rRes.TokenType = KParseType::SINGLE_QUOTE_NAME;
rRes.EndPos = nPos+1;
@@ -1703,7 +2107,7 @@
}
++nPos;
}
-@@ -1199,9 +1201,197 @@ static bool lcl_isValidQuotedText( const String& rFormula, xub_StrLen nSrcPos, P
+@@ -1199,9 +1227,203 @@ static bool lcl_isValidQuotedText( const String& rFormula, xub_StrLen nSrcPos, P
}
}
@@ -1846,16 +2250,22 @@
+ return true;
+}
+
-+static String lcl_makeExternalNameStr( const String& rFile, const String& rName, const sal_Unicode cSep )
++static String lcl_makeExternalNameStr( const String& rFile, const String& rName,
++ const sal_Unicode cSep, bool bODF )
+{
-+ String aStr, aFile = rFile;
++ String aFile( rFile);
+ aFile.SearchAndReplaceAllAscii("'", String::CreateFromAscii("''"));
-+ aStr.Append(sal_Unicode('\''));
-+ aStr.Append(aFile);
-+ aStr.Append(sal_Unicode('\''));
-+ aStr.Append(cSep);
-+ aStr.Append(rName);
-+ return aStr;
++ rtl::OUStringBuffer aBuf( aFile.Len() + rName.Len() + 5);
++ if (bODF)
++ aBuf.append( sal_Unicode( '['));
++ aBuf.append( sal_Unicode( '\''));
++ aBuf.append( aFile);
++ aBuf.append( sal_Unicode( '\''));
++ aBuf.append( cSep);
++ aBuf.append( rName);
++ if (bODF)
++ aBuf.append( sal_Unicode(']'));
++ return String( aBuf.makeStringAndClear());
+}
+
+static bool lcl_getLastTabName( String& rTabName2, const String& rTabName1,
@@ -1901,7 +2311,7 @@
struct Convention_A1 : public ScCompiler::Convention
{
Convention_A1( ScAddress::Convention eConv ) : ScCompiler::Convention( eConv ) { }
-@@ -1215,14 +1405,14 @@ struct Convention_A1 : public ScCompiler::Convention
+@@ -1215,14 +1437,14 @@ struct Convention_A1 : public ScCompiler::Convention
const CharClass* pCharClass) const
{
ParseResult aRet;
@@ -1918,7 +2328,7 @@
return pCharClass->parseAnyToken( rFormula,
nSrcPos, nStartFlags, aAddAllowed, nContFlags, aAddAllowed );
}
-@@ -1405,6 +1595,86 @@ struct ConventionOOO_A1 : public Convention_A1
+@@ -1405,6 +1627,113 @@ struct ConventionOOO_A1 : public Convention_A1
return sal_Unicode(0);
}
@@ -1930,7 +2340,7 @@
+
+ virtual String makeExternalNameStr( const String& rFile, const String& rName ) const
+ {
-+ return lcl_makeExternalNameStr(rFile, rName, sal_Unicode('#'));
++ return lcl_makeExternalNameStr( rFile, rName, sal_Unicode('#'), false);
+ }
+
+ bool makeExternalSingleRefStr( ::rtl::OUStringBuffer& rBuffer, sal_uInt16 nFileId,
@@ -1967,45 +2377,98 @@
+ return true;
+ }
+
-+ virtual void makeExternalRefStr( ::rtl::OUStringBuffer& rBuffer, const ScCompiler& rCompiler,
++ void makeExternalRefStrImpl( ::rtl::OUStringBuffer& rBuffer, const ScCompiler& rCompiler,
+ sal_uInt16 nFileId, const String& rTabName, const SingleRefData& rRef,
-+ ScExternalRefManager* pRefMgr ) const
++ ScExternalRefManager* pRefMgr, bool bODF ) const
+ {
+ SingleRefData aRef(rRef);
+ aRef.CalcAbsIfRel(rCompiler.GetPos());
+
++ if (bODF)
++ rBuffer.append( sal_Unicode('['));
+ makeExternalSingleRefStr(rBuffer, nFileId, rTabName, aRef, pRefMgr, true);
++ if (bODF)
++ rBuffer.append( sal_Unicode(']'));
+ }
+
+ virtual void makeExternalRefStr( ::rtl::OUStringBuffer& rBuffer, const ScCompiler& rCompiler,
-+ sal_uInt16 nFileId, const String& rTabName, const ComplRefData& rRef,
++ sal_uInt16 nFileId, const String& rTabName, const SingleRefData& rRef,
+ ScExternalRefManager* pRefMgr ) const
+ {
++ makeExternalRefStrImpl( rBuffer, rCompiler, nFileId, rTabName, rRef, pRefMgr, false);
++ }
++
++ void makeExternalRefStrImpl( ::rtl::OUStringBuffer& rBuffer, const ScCompiler& rCompiler,
++ sal_uInt16 nFileId, const String& rTabName, const ComplRefData& rRef,
++ ScExternalRefManager* pRefMgr, bool bODF ) const
++ {
+ ComplRefData aRef(rRef);
+ aRef.CalcAbsIfRel(rCompiler.GetPos());
+
-+ if (!makeExternalSingleRefStr(rBuffer, nFileId, rTabName, aRef.Ref1, pRefMgr, true))
-+ return;
++ if (bODF)
++ rBuffer.append( sal_Unicode('['));
++ // Ensure that there's always a closing bracket, no premature returns.
++ do
++ {
++ if (!makeExternalSingleRefStr(rBuffer, nFileId, rTabName, aRef.Ref1, pRefMgr, true))
++ break;
+
-+ rBuffer.append(sal_Unicode(':'));
++ rBuffer.append(sal_Unicode(':'));
+
-+ // Get the name of the last table.
-+ const vector<String>* pTabNames = pRefMgr->getAllCachedTableNames(nFileId);
-+ if (!pTabNames)
-+ return;
++ // Get the name of the last table.
++ const vector<String>* pTabNames = pRefMgr->getAllCachedTableNames(nFileId);
++ if (!pTabNames)
++ break;
+
-+ String aLastTabName;
-+ if (!lcl_getLastTabName(aLastTabName, rTabName, *pTabNames, aRef))
-+ {
-+ rBuffer.append(aLastTabName);
-+ return;
-+ }
-+ makeExternalSingleRefStr(rBuffer, nFileId, aLastTabName, aRef.Ref2, pRefMgr, (aRef.Ref1.nTab != aRef.Ref2.nTab));
++ String aLastTabName;
++ if (!lcl_getLastTabName(aLastTabName, rTabName, *pTabNames, aRef))
++ {
++ rBuffer.append(aLastTabName);
++ break;
++ }
++ makeExternalSingleRefStr( rBuffer, nFileId, aLastTabName,
++ aRef.Ref2, pRefMgr, (aRef.Ref1.nTab != aRef.Ref2.nTab));
++ } while (0);
++ if (bODF)
++ rBuffer.append( sal_Unicode(']'));
++ }
++
++ virtual void makeExternalRefStr( ::rtl::OUStringBuffer& rBuffer, const ScCompiler& rCompiler,
++ sal_uInt16 nFileId, const String& rTabName, const ComplRefData& rRef,
++ ScExternalRefManager* pRefMgr ) const
++ {
++ makeExternalRefStrImpl( rBuffer, rCompiler, nFileId, rTabName, rRef, pRefMgr, false);
+ }
};
-@@ -1526,11 +1796,128 @@ struct ConventionXL
+@@ -1423,6 +1752,25 @@ struct ConventionOOO_A1_ODF : public ConventionOOO_A1
+ {
+ MakeRefStrImpl( rBuffer, rComp, rRef, bSingleRef, true);
+ }
++
++ virtual String makeExternalNameStr( const String& rFile, const String& rName ) const
++ {
++ return lcl_makeExternalNameStr( rFile, rName, sal_Unicode('#'), true);
++ }
++
++ virtual void makeExternalRefStr( ::rtl::OUStringBuffer& rBuffer, const ScCompiler& rCompiler,
++ sal_uInt16 nFileId, const String& rTabName, const SingleRefData& rRef,
++ ScExternalRefManager* pRefMgr ) const
++ {
++ makeExternalRefStrImpl( rBuffer, rCompiler, nFileId, rTabName, rRef, pRefMgr, true);
++ }
++
++ virtual void makeExternalRefStr( ::rtl::OUStringBuffer& rBuffer, const ScCompiler& rCompiler,
++ sal_uInt16 nFileId, const String& rTabName, const ComplRefData& rRef,
++ ScExternalRefManager* pRefMgr ) const
++ {
++ makeExternalRefStrImpl( rBuffer, rCompiler, nFileId, rTabName, rRef, pRefMgr, true);
++ }
+ };
+
+ static const ConventionOOO_A1_ODF ConvOOO_A1_ODF;
+@@ -1526,11 +1874,129 @@ struct ConventionXL
}
return sal_Unicode(0);
}
@@ -2017,7 +2480,7 @@
+
+ static String makeExternalNameStr( const String& rFile, const String& rName )
+ {
-+ return lcl_makeExternalNameStr(rFile, rName, sal_Unicode('!'));
++ return lcl_makeExternalNameStr( rFile, rName, sal_Unicode('!'), false);
+ }
+
+ static void makeExternalDocStr( ::rtl::OUStringBuffer& rBuffer, const String& rFullName )
@@ -2120,6 +2583,7 @@
struct ConventionXL_A1 : public Convention_A1, public ConventionXL
{
ConventionXL_A1() : Convention_A1( ScAddress::CONV_XL_A1 ) { }
++ ConventionXL_A1( ScAddress::Convention eConv ) : Convention_A1( eConv ) { }
+
+ void makeSingleCellStr( ::rtl::OUStringBuffer& rBuf, const SingleRefData& rRef ) const
+ {
@@ -2134,7 +2598,7 @@
void MakeRefStr( rtl::OUStringBuffer& rBuf,
const ScCompiler& rComp,
const ComplRefData& rRef,
-@@ -1584,22 +1971,11 @@ struct ConventionXL_A1 : public Convention_A1, public ConventionXL
+@@ -1584,22 +2050,11 @@ struct ConventionXL_A1 : public Convention_A1, public ConventionXL
}
}
@@ -2159,7 +2623,7 @@
}
}
-@@ -1607,8 +1983,10 @@ struct ConventionXL_A1 : public Convention_A1, public ConventionXL
+@@ -1607,8 +2062,10 @@ struct ConventionXL_A1 : public Convention_A1, public ConventionXL
xub_StrLen nSrcPos,
const CharClass* pCharClass) const
{
@@ -2171,7 +2635,7 @@
return aRet;
static const sal_Int32 nStartFlags = KParseTokens::ANY_LETTER_OR_NUMBER |
-@@ -1624,6 +2002,67 @@ struct ConventionXL_A1 : public Convention_A1, public ConventionXL
+@@ -1624,11 +2081,82 @@ struct ConventionXL_A1 : public Convention_A1, public ConventionXL
{
return ConventionXL::getSpecialSymbol(eSymType);
}
@@ -2239,7 +2703,22 @@
};
static const ConventionXL_A1 ConvXL_A1;
-@@ -1733,8 +2172,10 @@ struct ConventionXL_R1C1 : public ScCompiler::Convention, public ConventionXL
+ const ScCompiler::Convention * const ScCompiler::pConvXL_A1 = &ConvXL_A1;
+
++
++struct ConventionXL_OOX : public ConventionXL_A1
++{
++ ConventionXL_OOX() : ConventionXL_A1( ScAddress::CONV_XL_OOX ) { }
++};
++
++static const ConventionXL_OOX ConvXL_OOX;
++const ScCompiler::Convention * const ScCompiler::pConvXL_OOX = &ConvXL_OOX;
++
++
+ //-----------------------------------------------------------------------------
+
+ static void
+@@ -1733,8 +2261,10 @@ struct ConventionXL_R1C1 : public ScCompiler::Convention, public ConventionXL
xub_StrLen nSrcPos,
const CharClass* pCharClass) const
{
@@ -2251,7 +2730,7 @@
return aRet;
static const sal_Int32 nStartFlags = KParseTokens::ANY_LETTER_OR_NUMBER |
-@@ -1751,6 +2192,95 @@ struct ConventionXL_R1C1 : public ScCompiler::Convention, public ConventionXL
+@@ -1751,6 +2281,95 @@ struct ConventionXL_R1C1 : public ScCompiler::Convention, public ConventionXL
{
return ConventionXL::getSpecialSymbol(eSymType);
}
@@ -2347,7 +2826,32 @@
};
static const ConventionXL_R1C1 ConvXL_R1C1;
-@@ -2208,7 +2738,7 @@ xub_StrLen ScCompiler::NextSymbol(bool bInArray)
+@@ -1817,13 +2436,15 @@ void ScCompiler::CheckTabQuotes( String& rString,
+ KParseType::IDENTNAME, rString, 0, nStartFlags, EMPTY_STRING, nContFlags, EMPTY_STRING);
+ bool bNeedsQuote = !((aRes.TokenType & KParseType::IDENTNAME) && aRes.EndPos == rString.Len());
+
+- switch ( eConv ) {
++ switch ( eConv )
++ {
+ default :
+ case ScAddress::CONV_UNSPECIFIED :
+ break;
+ case ScAddress::CONV_OOO :
+ case ScAddress::CONV_XL_A1 :
+ case ScAddress::CONV_XL_R1C1 :
++ case ScAddress::CONV_XL_OOX :
+ if( bNeedsQuote )
+ {
+ static const String one_quote = static_cast<sal_Unicode>( '\'' );
+@@ -1859,6 +2480,7 @@ void ScCompiler::SetRefConvention( ScAddress::Convention eConv )
+ case ScAddress::CONV_ODF : SetRefConvention( pConvOOO_A1_ODF ); break;
+ case ScAddress::CONV_XL_A1 : SetRefConvention( pConvXL_A1 ); break;
+ case ScAddress::CONV_XL_R1C1 : SetRefConvention( pConvXL_R1C1 ); break;
++ case ScAddress::CONV_XL_OOX : SetRefConvention( pConvXL_OOX ); break;
+ }
+ }
+
+@@ -2208,7 +2830,7 @@ xub_StrLen ScCompiler::NextSymbol(bool bInArray)
static const int kQuote = kInc * 2;
static const int kPast = kInc * 3;
bool bAddToSymbol = true;
@@ -2356,7 +2860,7 @@
{
// eat it, no sheet name
bAddToSymbol = false;
-@@ -2223,7 +2753,7 @@ xub_StrLen ScCompiler::NextSymbol(bool bInArray)
+@@ -2223,7 +2845,7 @@ xub_StrLen ScCompiler::NextSymbol(bool bInArray)
}
else if (nRefInSheetName < kPast)
{
@@ -2365,17 +2869,17 @@
nRefInSheetName += kDollar;
else if ('\'' == c)
{
-@@ -2545,7 +3075,8 @@ BOOL ScCompiler::IsDoubleReference( const String& rName )
+@@ -2545,7 +3167,8 @@ BOOL ScCompiler::IsDoubleReference( const String& rName )
{
ScRange aRange( aPos, aPos );
const ScAddress::Details aDetails( pConv->meConv, aPos );
- USHORT nFlags = aRange.Parse( rName, pDoc, aDetails );
+ ScAddress::ExternalInfo aExtInfo;
-+ USHORT nFlags = aRange.Parse( rName, pDoc, aDetails, &aExtInfo );
++ USHORT nFlags = aRange.Parse( rName, pDoc, aDetails, &aExtInfo, &maExternalLinks );
if( nFlags & SCA_VALID )
{
ScRawToken aToken;
-@@ -2564,7 +3095,14 @@ BOOL ScCompiler::IsDoubleReference( const String& rName )
+@@ -2564,7 +3187,14 @@ BOOL ScCompiler::IsDoubleReference( const String& rName )
aRef.Ref2.SetTabDeleted( TRUE ); // #REF!
aRef.Ref2.SetFlag3D( ( nFlags & SCA_TAB2_3D ) != 0 );
aRef.CalcRelFromAbs( aPos );
@@ -2391,17 +2895,17 @@
pRawToken = aToken.Clone();
}
-@@ -2576,7 +3114,8 @@ BOOL ScCompiler::IsSingleReference( const String& rName )
+@@ -2576,7 +3206,8 @@ BOOL ScCompiler::IsSingleReference( const String& rName )
{
ScAddress aAddr( aPos );
const ScAddress::Details aDetails( pConv->meConv, aPos );
- USHORT nFlags = aAddr.Parse( rName, pDoc, aDetails );
+ ScAddress::ExternalInfo aExtInfo;
-+ USHORT nFlags = aAddr.Parse( rName, pDoc, aDetails, &aExtInfo );
++ USHORT nFlags = aAddr.Parse( rName, pDoc, aDetails, &aExtInfo, &maExternalLinks );
// Something must be valid in order to recognize Sheet1.blah or blah.a1
// as a (wrong) reference.
if( nFlags & ( SCA_VALID_COL|SCA_VALID_ROW|SCA_VALID_TAB ) )
-@@ -2600,7 +3139,11 @@ BOOL ScCompiler::IsSingleReference( const String& rName )
+@@ -2600,7 +3231,11 @@ BOOL ScCompiler::IsSingleReference( const String& rName )
nFlags |= SCA_VALID;
}
aRef.CalcRelFromAbs( aPos );
@@ -2414,7 +2918,7 @@
pRawToken = aToken.Clone();
}
-@@ -2708,6 +3251,27 @@ BOOL ScCompiler::IsNamedRange( const String& rUpperName )
+@@ -2708,6 +3343,27 @@ BOOL ScCompiler::IsNamedRange( const String& rUpperName )
return FALSE;
}
@@ -2442,7 +2946,7 @@
BOOL ScCompiler::IsDBRange( const String& rName )
{
USHORT n;
-@@ -3243,7 +3807,7 @@ BOOL ScCompiler::NextNewToken( bool bInArray )
+@@ -3243,7 +3899,7 @@ BOOL ScCompiler::NextNewToken( bool bInArray )
if (mnPredetectedReference)
{
String aStr( cSymbol);
@@ -2451,7 +2955,7 @@
{
/* TODO: it would be nice to generate a #REF! error here, which
* would need an ocBad token with additional error value.
-@@ -3306,6 +3870,7 @@ BOOL ScCompiler::NextNewToken( bool bInArray )
+@@ -3306,6 +3962,7 @@ BOOL ScCompiler::NextNewToken( bool bInArray )
&& !(bAllowBooleans && IsBoolean( aUpper ))
&& !IsValue( aUpper )
&& !IsNamedRange( aUpper )
@@ -2459,11 +2963,23 @@
&& !IsDBRange( aUpper )
&& !IsColRowName( aUpper )
&& !(bMayBeFuncName && IsMacro( aUpper ))
-@@ -3641,6 +4206,66 @@ BOOL ScCompiler::GetToken()
+@@ -3628,9 +4285,9 @@ BOOL ScCompiler::GetToken()
+ else
+ {
+ if ( nWasColRowName >= 2 && pToken->GetOpCode() == ocColRowName )
+- { // aus einem ocSpaces ein ocIntersect im RPN machen
++ { // convert an ocSpaces to ocIntersect in RPN
+ pToken = new ScByteToken( ocIntersect );
+- pArr->nIndex--; // ganz schweinisch..
++ pArr->nIndex--; // we advanced to the second ocColRowName, step back
+ }
+ }
+ }
+@@ -3641,6 +4298,78 @@ BOOL ScCompiler::GetToken()
}
if( pToken->GetOpCode() == ocSubTotal )
glSubTotal = TRUE;
-+ else if ( pToken->GetOpCode() == ocExternalName )
++ else if ( pToken->GetOpCode() == ocExternalRef )
+ {
+ // Handle external single and double references, or names.
+
@@ -2477,56 +2993,77 @@
+ case svExternalName:
+ {
+ const String& rName = pToken->GetString();
-+ ScTokenArray* pNew = pRefMgr->getRangeNameTokens(pToken->GetIndex(), rName, &aPos);
-+ if (pNew)
++ ScExternalRefCache::TokenArrayRef xNew = pRefMgr->getRangeNameTokens(pToken->GetIndex(), rName, &aPos);
++ if (xNew.get())
+ {
-+ PushTokenArray(pNew->Clone(), true);
++ ScTokenArray* pNew = xNew->Clone();
++ PushTokenArray(pNew, true);
++ pNew->Reset();
+ return GetToken();
+ }
+ }
+ break;
-+ case svSingleRef:
++ case svExternalSingleRef:
+ {
+ SingleRefData aData(pToken->GetSingleRef());
+ if (aData.IsTabRel())
-+ // external single reference must have an absolute table reference!
++ {
++ DBG_ERROR("ScCompiler::GetToken: external single reference must have an absolute table reference!")
+ break;
++ }
+
+ aData.CalcAbsIfRel(aPos);
+ ScAddress aAddr(aData.nCol, aData.nRow, aData.nTab);
-+ ScToken* pNew = pRefMgr->getSingleRefToken(pToken->GetIndex(), pToken->GetString(), aAddr, &aPos, NULL);
-+ if (pNew)
++ ScExternalRefCache::TokenRef xNew = pRefMgr->getSingleRefToken(pToken->GetIndex(), pToken->GetString(), aAddr, &aPos, NULL);
++ if (xNew.get())
+ {
-+ pToken = pNew->Clone();
++ pToken = xNew->Clone();
+ return true;
+ }
+ }
+ break;
-+ case svDoubleRef:
++ case svExternalDoubleRef:
+ {
+ ComplRefData aData(pToken->GetDoubleRef());
+ if (aData.Ref1.IsTabRel() || aData.Ref2.IsTabRel())
-+ // external double reference must have an absolute table reference!
++ {
++ DBG_ERROR("ScCompiler::GetToken: external double reference must have an absolute table reference!")
+ break;
++ }
+
+ aData.CalcAbsIfRel(aPos);
+ ScRange aRange(aData.Ref1.nCol, aData.Ref1.nRow, aData.Ref1.nTab,
+ aData.Ref2.nCol, aData.Ref2.nRow, aData.Ref2.nTab);
-+ ScTokenArray* pNew = pRefMgr->getDoubleRefTokens(pToken->GetIndex(), pToken->GetString(), aRange, &aPos);
-+ if (pNew)
++ ScExternalRefCache::TokenArrayRef xNew = pRefMgr->getDoubleRefTokens(pToken->GetIndex(), pToken->GetString(), aRange, &aPos);
++ if (xNew.get())
+ {
-+ PushTokenArray(pNew->Clone(), true);
++ ScTokenArray* pNew = xNew->Clone();
++ PushTokenArray(pNew, true);
++ pNew->Reset();
+ return GetToken();
+ }
+ }
+ break;
++ default:
++ {
++ DBG_ERROR1( "ScCompiler::GetToken: unhandled ocExternalRef type %d", pToken->GetType());
++ }
+ }
+ SetError(errNoName);
+ }
else if( pToken->GetOpCode() == ocName )
{
ScRangeData* pRangeData = pDoc->GetRangeName()->FindIndex( pToken->GetIndex() );
-@@ -5638,111 +6263,140 @@ ScToken* ScCompiler::CreateStringFromToken( rtl::OUStringBuffer& rBuffer, ScToke
+@@ -3796,7 +4525,7 @@ BOOL ScCompiler::GetToken()
+ { // next defined RowNameRange to the right limits column
+ const ScRange& rRange = pR->GetRange(1);
+ if ( rRange.aStart.Row() <= nRow && nRow <= rRange.aEnd.Row() )
+- { // gleicher Row Bereich
++ { // identical row range
+ SCCOL nTmp = rRange.aStart.Col();
+ if ( nStartCol < nTmp && nTmp <= nMaxCol )
+ nMaxCol = nTmp - 1;
+@@ -5638,111 +6367,140 @@ ScToken* ScCompiler::CreateStringFromToken( rtl::OUStringBuffer& rBuffer, ScToke
DBG_ERRORFILE("unknown OpCode");
rBuffer.append(ScGlobal::GetRscString(STR_NO_NAME_REF));
}
@@ -2544,7 +3081,7 @@
- AppendString( rBuffer, t->GetString() );
- break;
- case svSingleRef:
-+ if (eOp == ocExternalName)
++ if (eOp == ocExternalRef)
{
- SingleRefData& rRef = t->GetSingleRef();
- ComplRefData aRef;
@@ -2769,7 +3306,7 @@
static void lcl_putInOrder( SingleRefData & rRef1, SingleRefData & rRef2 )
{
diff --git sc/source/core/tool/token.cxx sc/source/core/tool/token.cxx
-index a20cbd5..51611ef 100644
+index a20cbd5..87f45c3 100644
--- sc/source/core/tool/token.cxx
+++ sc/source/core/tool/token.cxx
@@ -54,6 +54,8 @@
@@ -2787,8 +3324,8 @@
+void ScRawToken::SetExternalSingleRef( sal_uInt16 nFileId, const String& rTabName, const SingleRefData& rRef )
+{
-+ eOp = ocExternalName;
-+ eType = svSingleRef;
++ eOp = ocExternalRef;
++ eType = svExternalSingleRef;
+ nRefCnt = 0;
+
+ extref.nFileId = nFileId;
@@ -2802,8 +3339,8 @@
+
+void ScRawToken::SetExternalDoubleRef( sal_uInt16 nFileId, const String& rTabName, const ComplRefData& rRef )
+{
-+ eOp = ocExternalName;
-+ eType = svDoubleRef;
++ eOp = ocExternalRef;
++ eType = svExternalDoubleRef;
+ nRefCnt = 0;
+
+ extref.nFileId = nFileId;
@@ -2816,7 +3353,7 @@
+
+void ScRawToken::SetExternalName( sal_uInt16 nFileId, const String& rName )
+{
-+ eOp = ocExternalName;
++ eOp = ocExternalRef;
+ eType = svExternalName;
+ nRefCnt = 0;
+
@@ -2835,7 +3372,7 @@
USHORT n = nOffset;
- switch( eType )
-+ if (eOp == ocExternalName)
++ if (eOp == ocExternalRef)
{
- case svSep: break;
- case svByte: n += sizeof(ScRawToken::sbyte); break;
@@ -2853,9 +3390,9 @@
- }
+ switch (eType)
+ {
-+ case svSingleRef:
-+ case svDoubleRef: n += sizeof(extref); break;
-+ case svExternalName: n += sizeof(extname); break;
++ case svExternalSingleRef:
++ case svExternalDoubleRef: n += sizeof(extref); break;
++ case svExternalName: n += sizeof(extname); break;
+ }
+ }
+ else
@@ -2880,42 +3417,78 @@
}
p = (ScRawToken*) new BYTE[ n ];
memcpy( p, this, n * sizeof(BYTE) );
-@@ -311,12 +367,22 @@ ScToken* ScRawToken::CreateToken() const
+@@ -297,55 +353,57 @@ ScToken* ScRawToken::CreateToken() const
+ {
+ case svByte :
+ return new ScByteToken( eOp, sbyte.cByte, sbyte.bHasForceArray );
+- //break;
+ case svDouble :
+ IF_NOT_OPCODE_ERROR( ocPush, ScDoubleToken);
+ return new ScDoubleToken( nValue );
+- //break;
+ case svString :
+ if (eOp == ocPush)
+ return new ScStringToken( String( cStr ) );
+ else
+ return new ScStringOpToken( eOp, String( cStr ) );
+- //break;
case svSingleRef :
if (eOp == ocPush)
return new ScSingleRefToken( aRef.Ref1 );
-+ else if (eOp == ocExternalName)
-+ {
-+ String aTabName(extref.cTabName);
-+ return new ScExternalSingleRefToken(extref.nFileId, aTabName, extref.aRef.Ref1);
-+ }
else
return new ScSingleRefOpToken( eOp, aRef.Ref1 );
- //break;
+- //break;
case svDoubleRef :
if (eOp == ocPush)
return new ScDoubleRefToken( aRef );
-+ else if (eOp == ocExternalName)
-+ {
-+ String aTabName(extref.cTabName);
-+ return new ScExternalDoubleRefToken(extref.nFileId, aTabName, extref.aRef);
-+ }
else
return new ScDoubleRefOpToken( eOp, aRef );
- //break;
-@@ -327,6 +393,11 @@ ScToken* ScRawToken::CreateToken() const
+- //break;
+ case svMatrix :
+ IF_NOT_OPCODE_ERROR( ocPush, ScMatrixToken);
+ return new ScMatrixToken( pMat );
+- //break;
case svIndex :
return new ScIndexToken( eOp, nIndex );
- //break;
+- //break;
++ case svExternalSingleRef:
++ {
++ String aTabName(extref.cTabName);
++ return new ScExternalSingleRefToken(extref.nFileId, aTabName, extref.aRef.Ref1);
++ }
++ case svExternalDoubleRef:
++ {
++ String aTabName(extref.cTabName);
++ return new ScExternalDoubleRefToken(extref.nFileId, aTabName, extref.aRef);
++ }
+ case svExternalName:
-+ {
-+ String aName(extname.cName);
-+ return new ScExternalNameToken( extname.nFileId, aName );
-+ }
++ {
++ String aName(extname.cName);
++ return new ScExternalNameToken( extname.nFileId, aName );
++ }
case svJump :
return new ScJumpToken( eOp, (short*) nJump );
- //break;
-@@ -478,6 +549,7 @@ BOOL ScToken::IsMatrixFunction() const
+- //break;
+ case svExternal :
+ return new ScExternalToken( eOp, sbyte.cByte, String( cStr+1 ) );
+- //break;
+ case svFAP :
+ return new ScFAPToken( eOp, sbyte.cByte, NULL );
+- //break;
+ case svMissing :
+ IF_NOT_OPCODE_ERROR( ocMissing, ScMissingToken);
+ return new ScMissingToken;
+- //break;
+ case svSep :
+ return new ScOpToken( eOp, svSep );
+- //break;
+ case svUnknown :
+ return new ScUnknownToken( eOp );
+- //break;
+ default:
+ {
+ DBG_ERROR1( "unknown ScRawToken::CreateToken() type %d", int(GetType()));
+@@ -478,68 +536,58 @@ BOOL ScToken::IsMatrixFunction() const
ScToken* ScToken::Clone() const
{
@@ -2923,84 +3496,170 @@
switch ( GetType() )
{
case svByte :
-@@ -487,20 +559,24 @@ ScToken* ScToken::Clone() const
+ return new ScByteToken( *static_cast<const ScByteToken*>(this) );
+- //break;
+ case svDouble :
return new ScDoubleToken( *static_cast<const ScDoubleToken*>(this) );
- //break;
+- //break;
case svString :
- if (GetOpCode() == ocPush)
+ if (nOp == ocPush)
return new ScStringToken( *static_cast<const ScStringToken*>(this) );
else
return new ScStringOpToken( *static_cast<const ScStringOpToken*>(this) );
- //break;
+- //break;
case svSingleRef :
- if (GetOpCode() == ocPush)
+ if (nOp == ocPush)
return new ScSingleRefToken( *static_cast<const ScSingleRefToken*>(this) );
-+ else if (nOp == ocExternalName)
-+ return new ScExternalSingleRefToken( *static_cast<const ScExternalSingleRefToken*>(this) );
else
return new ScSingleRefOpToken( *static_cast<const ScSingleRefOpToken*>(this) );
- //break;
+- //break;
case svDoubleRef :
- if (GetOpCode() == ocPush)
+ if (nOp == ocPush)
return new ScDoubleRefToken( *static_cast<const ScDoubleRefToken*>(this) );
-+ else if (nOp == ocExternalName)
-+ return new ScExternalDoubleRefToken( *static_cast<const ScExternalDoubleRefToken*>(this) );
else
return new ScDoubleRefOpToken( *static_cast<const ScDoubleRefOpToken*>(this) );
- //break;
-@@ -522,6 +598,9 @@ ScToken* ScToken::Clone() const
+- //break;
+ case svMatrix :
+ return new ScMatrixToken( *static_cast<const ScMatrixToken*>(this) );
+- //break;
+ case svIndex :
+ return new ScIndexToken( *static_cast<const ScIndexToken*>(this) );
+- //break;
+ case svJump :
+ return new ScJumpToken( *static_cast<const ScJumpToken*>(this) );
+- //break;
+ case svJumpMatrix :
+ return new ScJumpMatrixToken( *static_cast<const ScJumpMatrixToken*>(this) );
+- //break;
+ case svRefList :
+ return new ScRefListToken( *static_cast<const ScRefListToken*>(this) );
+- //break;
case svExternal :
return new ScExternalToken( *static_cast<const ScExternalToken*>(this) );
- //break;
+- //break;
++ case svExternalSingleRef :
++ return new ScExternalSingleRefToken( *static_cast<const ScExternalSingleRefToken*>(this) );
++ case svExternalDoubleRef :
++ return new ScExternalDoubleRefToken( *static_cast<const ScExternalDoubleRefToken*>(this) );
+ case svExternalName :
+ return new ScExternalNameToken( *static_cast<const ScExternalNameToken*>(this) );
-+ //break;
case svFAP :
return new ScFAPToken( *static_cast<const ScFAPToken*>(this) );
- //break;
-@@ -660,6 +739,7 @@ ScTokenRef ScToken::ExtendRangeReference( ScToken & rTok1, ScToken & rTok2,
+- //break;
+ case svMissing :
+ return new ScMissingToken( *static_cast<const ScMissingToken*>(this) );
+- //break;
+ case svError :
+ return new ScErrorToken( *static_cast<const ScErrorToken*>(this) );
+- //break;
+ case svEmptyCell :
+ return new ScEmptyCellToken( *static_cast<const ScEmptyCellToken*>(this) );
+- //break;
+ case svSep :
+ return new ScOpToken( *static_cast<const ScOpToken*>(this) );
+- //break;
+ case svUnknown :
+ return new ScUnknownToken( *static_cast<const ScUnknownToken*>(this) );
+- //break;
+ default:
+ DBG_ERROR1( "unknown ScToken::Clone() type %d", int(GetType()));
+ return new ScUnknownToken( ocBad );
+@@ -655,26 +703,52 @@ ScTokenRef ScToken::ExtendRangeReference( ScToken & rTok1, ScToken & rTok2,
+ // Doing a RangeOp with RefList is probably utter nonsense, but Xcl
+ // supports it, so do we.
+ if (((p1 = &rTok1) == 0) || ((p2 = &rTok2) == 0) ||
+- ((sv1 = p1->GetType()) != svSingleRef && sv1 != svDoubleRef && sv1 != svRefList) ||
++ ((sv1 = p1->GetType()) != svSingleRef && sv1 != svDoubleRef && sv1 != svRefList &&
++ sv1 != svExternalSingleRef && sv1 != svExternalDoubleRef) ||
+ ((sv2 = p2->GetType()) != svSingleRef && sv2 != svDoubleRef && sv2 != svRefList))
return NULL;
ScTokenRef xRes;
-+ bool bExternal = rTok1.GetOpCode() == ocExternalName;
- if (sv1 == svSingleRef && sv2 == svSingleRef)
+- if (sv1 == svSingleRef && sv2 == svSingleRef)
++ bool bExternal = (sv1 == svExternalSingleRef);
++ if ((sv1 == svSingleRef || bExternal) && sv2 == svSingleRef)
{
// Range references like Sheet1.A1:A2 are generalized and built by
-@@ -671,7 +751,10 @@ ScTokenRef ScToken::ExtendRangeReference( ScToken & rTok1, ScToken & rTok2,
+ // first creating a DoubleRef from the first SingleRef, effectively
+ // generating Sheet1.A1:A1, and then extending that with A2 as if
+ // Sheet1.A1:A1:A2 was encountered, so the mechanisms to adjust the
+ // references apply as well.
++
++ /* Given the current structure of external references an external
++ * reference can only be extended if the second reference does not
++ * point to a different sheet. 'file'#Sheet1.A1:A2 is ok,
++ * 'file'#Sheet1.A1:Sheet2.A2 is not. Since we can't determine from a
++ * svSingleRef whether the sheet would be different from the one given
++ * in the external reference, we have to bail out if there is any sheet
++ * specified. NOTE: Xcl does handle external 3D references as in
++ * '[file]Sheet1:Sheet2'!A1:A2
++ *
++ * FIXME: For OOo syntax be smart and remember an external singleref
++ * encountered and if followed by ocRange and singleref, create an
++ * external singleref for the second singleref. Both could then be
++ * merged here. For Xcl syntax already parse an external range
++ * reference entirely, cumbersome. */
++
++ const SingleRefData& rRef2 = p2->GetSingleRef();
++ if (bExternal && rRef2.IsFlag3D())
++ return NULL;
++
+ ComplRefData aRef;
aRef.Ref1 = aRef.Ref2 = p1->GetSingleRef();
aRef.Ref2.SetFlag3D( false);
- aRef.Extend( p2->GetSingleRef(), rPos);
+- aRef.Extend( p2->GetSingleRef(), rPos);
- xRes = new ScDoubleRefToken( aRef);
++ aRef.Extend( rRef2, rPos);
+ if (bExternal)
-+ xRes = new ScExternalDoubleRefToken(rTok1.GetIndex(), rTok1.GetString(), aRef);
++ xRes = new ScExternalDoubleRefToken( p1->GetIndex(), p1->GetString(), aRef);
+ else
+ xRes = new ScDoubleRefToken( aRef);
}
else
{
-@@ -694,7 +777,10 @@ ScTokenRef ScToken::ExtendRangeReference( ScToken & rTok1, ScToken & rTok2,
++ bExternal |= (sv1 == svExternalDoubleRef);
+ const ScRefList* pRefList = NULL;
+ if (sv1 == svDoubleRef)
+ {
+@@ -694,6 +768,8 @@ ScTokenRef ScToken::ExtendRangeReference( ScToken & rTok1, ScToken & rTok2,
{
if (!pRefList->size())
return NULL;
-- xRes = new ScDoubleRefToken( (*pRefList)[0] );
+ if (bExternal)
-+ xRes = new ScExternalDoubleRefToken(rTok1.GetIndex(), rTok1.GetString(), (*pRefList)[0]);
-+ else
-+ xRes = new ScDoubleRefToken( (*pRefList)[0] );
++ return NULL; // external reference list not possible
+ xRes = new ScDoubleRefToken( (*pRefList)[0] );
}
if (!xRes)
- return NULL; // shouldn't happen..
-@@ -1035,6 +1121,190 @@ BOOL ScIndexToken::operator==( const ScToken& r ) const
+@@ -724,6 +800,18 @@ ScTokenRef ScToken::ExtendRangeReference( ScToken & rTok1, ScToken & rTok2,
+ }
+ }
+ break;
++ case svExternalSingleRef:
++ if (rRef.Ref1.IsFlag3D() || rRef.Ref2.IsFlag3D())
++ return NULL; // no other sheets with external refs
++ else
++ rRef.Extend( pt[i]->GetSingleRef(), rPos);
++ break;
++ case svExternalDoubleRef:
++ if (rRef.Ref1.IsFlag3D() || rRef.Ref2.IsFlag3D())
++ return NULL; // no other sheets with external refs
++ else
++ rRef.Extend( pt[i]->GetDoubleRef(), rPos);
++ break;
+ default:
+ ; // nothing, prevent compiler warning
+ }
+@@ -1035,6 +1123,190 @@ BOOL ScIndexToken::operator==( const ScToken& r ) const
return ScToken::operator==( r ) && nIndex == r.GetIndex();
}
+// ============================================================================
+
+ScExternalSingleRefToken::ScExternalSingleRefToken( sal_uInt16 nFileId, const String& rTabName, const SingleRefData& r ) :
-+ ScOpToken(ocExternalName, svSingleRef),
++ ScOpToken(ocExternalRef, svExternalSingleRef),
+ mnFileId(nFileId),
+ maTabName(rTabName),
+ maSingleRef(r)
@@ -3056,7 +3715,7 @@
+// ============================================================================
+
+ScExternalDoubleRefToken::ScExternalDoubleRefToken( sal_uInt16 nFileId, const String& rTabName, const ComplRefData& r ) :
-+ ScOpToken(ocExternalName, svDoubleRef),
++ ScOpToken(ocExternalRef, svExternalDoubleRef),
+ mnFileId(nFileId),
+ maTabName(rTabName),
+ maDoubleRef(r)
@@ -3132,7 +3791,7 @@
+// ============================================================================
+
+ScExternalNameToken::ScExternalNameToken( sal_uInt16 nFileId, const String& rName ) :
-+ ScOpToken(ocExternalName, svExternalName),
++ ScOpToken(ocExternalRef, svExternalName),
+ mnFileId(nFileId),
+ maName(rName)
+{
@@ -3184,17 +3843,33 @@
short* ScJumpToken::GetJump() const { return pJump; }
BOOL ScJumpToken::operator==( const ScToken& r ) const
-@@ -1237,6 +1507,9 @@ ScToken* ScTokenArray::GetNextReferenceOrName()
- {
- for( ScToken* t = Next(); t; t = Next() )
- {
-+ if ( t->GetOpCode() == ocExternalName )
-+ return t;
-+
- switch( t->GetType() )
- {
+@@ -1242,6 +1514,9 @@ ScToken* ScTokenArray::GetNextReferenceOrName()
case svSingleRef:
-@@ -1893,6 +2166,21 @@ ScToken* ScTokenArray::AddMatrix( ScMatrix* p )
+ case svDoubleRef:
+ case svIndex:
++ case svExternalSingleRef:
++ case svExternalDoubleRef:
++ case svExternalName:
+ return t;
+ default:
+ {
+@@ -1785,10 +2060,11 @@ ScToken* ScTokenArray::MergeRangeReference( const ScAddress & rPos )
+ if (!pCode || !nLen)
+ return NULL;
+ USHORT nIdx = nLen;
+- ScToken *p1, *p2, *p3;
+- if (((p3 = PeekPrev(nIdx)) != 0) && p3->GetType() == svSingleRef &&
+- ((p2 = PeekPrev(nIdx)) != 0) && p2->GetOpCode() == ocRange &&
+- ((p1 = PeekPrev(nIdx)) != 0) && p1->GetType() == svSingleRef)
++ ScToken *p1, *p2, *p3; // ref, ocRange, ref
++ // The actual types are checked in ExtendRangeReference().
++ if (((p3 = PeekPrev(nIdx)) != 0) &&
++ (((p2 = PeekPrev(nIdx)) != 0) && p2->GetOpCode() == ocRange) &&
++ ((p1 = PeekPrev(nIdx)) != 0))
+ {
+ ScTokenRef p = ScToken::ExtendRangeReference( *p1, *p3, rPos, true);
+ if (p)
+@@ -1893,6 +2169,21 @@ ScToken* ScTokenArray::AddMatrix( ScMatrix* p )
return Add( new ScMatrixToken( p ) );
}
@@ -3816,7 +4491,7 @@
diff --git sc/source/filter/excel/xeformula.cxx sc/source/filter/excel/xeformula.cxx
-index 3db8da7..947b4ce 100644
+index 3db8da7..6488f69 100644
--- sc/source/filter/excel/xeformula.cxx
+++ sc/source/filter/excel/xeformula.cxx
@@ -42,6 +42,11 @@
@@ -3876,7 +4551,7 @@
StackVar eTokType = aTokData.GetType();
OpCode eOpCode = aTokData.GetOpCode();
-+ if (eOpCode == ocExternalName)
++ if (eOpCode == ocExternalRef)
+ {
+ ProcessExternalName( aTokData, nExpClass );
+ return GetNextToken();
@@ -3907,8 +4582,8 @@
+ SingleRefData aRef(rTokData.mpScToken->GetSingleRef());
+ aRef.CalcAbsIfRel(*mpScBasePos);
+ const String& rTabName = rTokData.mpScToken->GetString();
-+ ScToken* p = pRefMgr->getSingleRefToken(nFileId, rTabName, ScAddress(aRef.nCol, aRef.nRow, aRef.nTab), NULL, NULL);
-+ if (!p)
++ ScExternalRefCache::TokenRef p = pRefMgr->getSingleRefToken(nFileId, rTabName, ScAddress(aRef.nCol, aRef.nRow, aRef.nTab), NULL, NULL);
++ if (!p.get())
+ {
+ AppendErrorToken(EXC_ERR_REF, rTokData.mnSpaces);
+ break;
@@ -3946,8 +4621,8 @@
+ const SingleRefData& r1 = aRef.Ref1;
+ const SingleRefData& r2 = aRef.Ref2;
+ ScRange aRange(r1.nCol, r1.nRow, r1.nTab, r2.nCol, r2.nRow, r2.nTab);
-+ ScTokenArray* pArray = pRefMgr->getDoubleRefTokens(nFileId, rTabName, aRange, NULL);
-+ if (!pArray)
++ ScExternalRefCache::TokenArrayRef pArray = pRefMgr->getDoubleRefTokens(nFileId, rTabName, aRange, NULL);
++ if (!pArray.get())
+ {
+ AppendErrorToken(EXC_ERR_REF, rTokData.mnSpaces);
+ break;
@@ -3975,8 +4650,8 @@
+ case svExternalName:
+ {
+ const String& aName = rTokData.mpScToken->GetString();
-+ ScTokenArray* pArray = pRefMgr->getRangeNameTokens(nFileId, aName);
-+ if (!pArray || !mpScBasePos)
++ ScExternalRefCache::TokenArrayRef pArray = pRefMgr->getRangeNameTokens(nFileId, aName);
++ if (!pArray.get() || !mpScBasePos)
+ {
+ AppendErrorToken(XclTools::GetXclErrorCode(errNoName), rTokData.mnSpaces);
+ break;
@@ -3986,15 +4661,15 @@
+ // references for CRN records.
+ for (ScToken* p = pArray->First(); p; p = pArray->Next())
+ {
-+ if (p->GetOpCode() == ocExternalName)
++ if (p->GetOpCode() == ocExternalRef)
+ {
-+ if (p->GetType() == svSingleRef)
++ if (p->GetType() == svExternalSingleRef)
+ {
+ SingleRefData aData(p->GetSingleRef());
+ aData.CalcAbsIfRel(*mpScBasePos);
+ mpLinkMgr->StoreCell(nFileId, p->GetString(), aData);
+ }
-+ else if (p->GetType() == svDoubleRef)
++ else if (p->GetType() == svExternalDoubleRef)
+ {
+ ComplRefData aData(p->GetDoubleRef());
+ aData.CalcAbsIfRel(*mpScBasePos);
@@ -4051,7 +4726,7 @@
SCTAB XclExpFmlaCompImpl::GetScTab( const SingleRefData& rRefData ) const
diff --git sc/source/filter/excel/xelink.cxx sc/source/filter/excel/xelink.cxx
-index b1bacad..08517ca 100644
+index b1bacad..90217ae 100644
--- sc/source/filter/excel/xelink.cxx
+++ sc/source/filter/excel/xelink.cxx
@@ -38,6 +38,14 @@
@@ -4081,7 +4756,7 @@
+{
+public:
+ explicit XclExpExtName( const XclExpRoot& rRoot, const XclExpSupbook& rSupbook, const String& rName,
-+ const ScTokenArray* pArray );
++ const ScExternalRefCache::TokenArrayRef pArray );
+
+private:
+ /** Writes additional record contents. */
@@ -4099,7 +4774,7 @@
@return The 1-based (Excel-like) list index of the DDE link. */
sal_uInt16 InsertDde( const String& rApplic, const String& rTopic, const String& rItem );
-+ sal_uInt16 InsertExtName( const XclExpSupbook& rSupbook, const String& rName, const ScTokenArray* pArray );
++ sal_uInt16 InsertExtName( const XclExpSupbook& rSupbook, const String& rName, const ScExternalRefCache::TokenArrayRef pArray );
+
/** Writes the EXTERNNAME record list. */
virtual void Save( XclExpStream& rStrm );
@@ -4131,7 +4806,7 @@
@return The 1-based EXTERNNAME record index; or 0, if the record list is full. */
sal_uInt16 InsertDde( const String& rItem );
-+ sal_uInt16 InsertExtName( const String& rName, const ScTokenArray* pArray );
++ sal_uInt16 InsertExtName( const String& rName, const ScExternalRefCache::TokenArrayRef pArray );
+
/** Writes the SUPBOOK and all EXTERNNAME, XCT and CRN records. */
virtual void Save( XclExpStream& rStrm );
@@ -4152,7 +4827,7 @@
+ bool InsertExtName(
+ sal_uInt16& rnSupbook, sal_uInt16& rnExtName, const String& rUrl,
-+ const String& rName, const ScTokenArray* pArray );
++ const String& rName, const ScExternalRefCache::TokenArrayRef pArray );
+
+ XclExpXti GetXti( sal_uInt16 nFileId, const String& rTabName, sal_uInt16 nXclTabSpan,
+ XclExpRefLogEntry* pRefLogEntry = NULL );
@@ -4215,7 +4890,7 @@
+ virtual bool InsertExtName(
+ sal_uInt16& rnExtSheet, sal_uInt16& rnExtName, const String& rUrl,
-+ const String& rName, const ScTokenArray* pArray ) = 0;
++ const String& rName, const ScExternalRefCache::TokenArrayRef pArray ) = 0;
+
/** Derived classes write the entire link table to the passed stream. */
virtual void Save( XclExpStream& rStrm ) = 0;
@@ -4243,7 +4918,7 @@
+ virtual bool InsertExtName(
+ sal_uInt16& rnExtSheet, sal_uInt16& rnExtName, const String& rUrl,
-+ const String& rName, const ScTokenArray* pArray );
++ const String& rName, const ScExternalRefCache::TokenArrayRef pArray );
+
virtual void Save( XclExpStream& rStrm );
@@ -4271,18 +4946,19 @@
+ virtual bool InsertExtName(
+ sal_uInt16& rnExtSheet, sal_uInt16& rnExtName, const String& rUrl,
-+ const String& rName, const ScTokenArray* pArray );
++ const String& rName, const ScExternalRefCache::TokenArrayRef pArray );
+
virtual void Save( XclExpStream& rStrm );
private:
-@@ -885,6 +968,100 @@ void XclExpExtNameDde::WriteAddData( XclExpStream& rStrm )
+@@ -885,6 +968,101 @@ void XclExpExtNameDde::WriteAddData( XclExpStream& rStrm )
mxMatrix->Save( rStrm );
}
+// ----------------------------------------------------------------------------
+
-+XclExpExtName::XclExpExtName( const XclExpRoot& rRoot, const XclExpSupbook& rSupbook, const String& rName, const ScTokenArray* pArray ) :
++XclExpExtName::XclExpExtName( const XclExpRoot& rRoot, const XclExpSupbook& rSupbook,
++ const String& rName, const ScExternalRefCache::TokenArrayRef pArray ) :
+ XclExpExtNameBase( rRoot, rName ),
+ mrSupbook(rSupbook),
+ mpArray(pArray->Clone())
@@ -4301,12 +4977,12 @@
+ break;
+
+ const ScToken* p = mpArray->First();
-+ if (p->GetOpCode() != ocExternalName)
++ if (p->GetOpCode() != ocExternalRef)
+ break;
+
+ switch (p->GetType())
+ {
-+ case svSingleRef:
++ case svExternalSingleRef:
+ {
+ const SingleRefData& rRef = p->GetSingleRef();
+ if (rRef.IsTabRel())
@@ -4330,7 +5006,7 @@
+ rStrm << nSBTab << nSBTab << nRow << nCol;
+ return;
+ }
-+ case svDoubleRef:
++ case svExternalDoubleRef:
+ {
+ const ComplRefData& rRef = p->GetDoubleRef();
+ const SingleRefData& r1 = rRef.Ref1;
@@ -4377,11 +5053,12 @@
// List of external names =====================================================
XclExpExtNameBuffer::XclExpExtNameBuffer( const XclExpRoot& rRoot ) :
-@@ -920,6 +1097,12 @@ sal_uInt16 XclExpExtNameBuffer::InsertDde(
+@@ -920,6 +1098,13 @@ sal_uInt16 XclExpExtNameBuffer::InsertDde(
return nIndex;
}
-+sal_uInt16 XclExpExtNameBuffer::InsertExtName( const XclExpSupbook& rSupbook, const String& rName, const ScTokenArray* pArray )
++sal_uInt16 XclExpExtNameBuffer::InsertExtName( const XclExpSupbook& rSupbook,
++ const String& rName, const ScExternalRefCache::TokenArrayRef pArray )
+{
+ sal_uInt16 nIndex = GetIndex( rName );
+ return nIndex ? nIndex : AppendNew( new XclExpExtName( GetRoot(), rSupbook, rName, pArray ) );
@@ -4390,7 +5067,7 @@
void XclExpExtNameBuffer::Save( XclExpStream& rStrm )
{
maNameList.Save( rStrm );
-@@ -1066,6 +1249,78 @@ void XclExpXct::StoreCellRange( const XclExpRoot& rRoot, const ScRange& rRange )
+@@ -1066,6 +1251,78 @@ void XclExpXct::StoreCellRange( const XclExpRoot& rRoot, const ScRange& rRange )
maUsedCells.SetMultiMarkArea( rRange );
}
@@ -4469,7 +5146,7 @@
void XclExpXct::Save( XclExpStream& rStrm )
{
XclExpRecord::Save( rStrm );
-@@ -1168,6 +1423,17 @@ XclExpSupbook::XclExpSupbook( const XclExpRoot& rRoot, const String& rUrl ) :
+@@ -1168,6 +1425,17 @@ XclExpSupbook::XclExpSupbook( const XclExpRoot& rRoot, const String& rUrl ) :
mnXclTabCount( 0 )
{
SetRecSize( 2 + maUrlEncoded.GetSize() );
@@ -4487,7 +5164,7 @@
}
XclExpSupbook::XclExpSupbook( const XclExpRoot& rRoot, const String& rApplic, const String& rTopic ) :
-@@ -1206,6 +1472,46 @@ void XclExpSupbook::StoreCellRange( const ScRange& rRange, sal_uInt16 nSBTab )
+@@ -1206,6 +1474,46 @@ void XclExpSupbook::StoreCellRange( const ScRange& rRange, sal_uInt16 nSBTab )
xXct->StoreCellRange( GetRoot(), rRange );
}
@@ -4534,11 +5211,11 @@
sal_uInt16 XclExpSupbook::InsertTabName( const String& rTabName )
{
DBG_ASSERT( meType == EXC_SBTYPE_EXTERN, "XclExpSupbook::InsertTabName - don't insert sheet names here" );
-@@ -1226,6 +1532,11 @@ sal_uInt16 XclExpSupbook::InsertDde( const String& rItem )
+@@ -1226,6 +1534,11 @@ sal_uInt16 XclExpSupbook::InsertDde( const String& rItem )
return GetExtNameBuffer().InsertDde( maUrl, maDdeTopic, rItem );
}
-+sal_uInt16 XclExpSupbook::InsertExtName( const String& rName, const ScTokenArray* pArray )
++sal_uInt16 XclExpSupbook::InsertExtName( const String& rName, const ScExternalRefCache::TokenArrayRef pArray )
+{
+ return GetExtNameBuffer().InsertExtName(*this, rName, pArray);
+}
@@ -4546,7 +5223,7 @@
void XclExpSupbook::Save( XclExpStream& rStrm )
{
// SUPBOOK record
-@@ -1289,11 +1600,6 @@ XclExpSupbookBuffer::XclExpSupbookBuffer( const XclExpRoot& rRoot ) :
+@@ -1289,11 +1602,6 @@ XclExpSupbookBuffer::XclExpSupbookBuffer( const XclExpRoot& rRoot ) :
mnOwnDocSB = Append( xSupbook );
for( sal_uInt16 nXclTab = 0; nXclTab < nXclCnt; ++nXclTab )
maSBIndexVec[ nXclTab ].Set( mnOwnDocSB, nXclTab );
@@ -4558,7 +5235,7 @@
}
}
-@@ -1352,6 +1658,130 @@ void XclExpSupbookBuffer::StoreCellRange( const ScRange& rRange )
+@@ -1352,6 +1660,130 @@ void XclExpSupbookBuffer::StoreCellRange( const ScRange& rRange )
}
}
@@ -4597,8 +5274,8 @@
+ nSupbookId = Append(xSupbook);
+ }
+
-+ ScToken* pToken = pRefMgr->getSingleRefToken(nFileId, rTabName, rCell, NULL, NULL);
-+ if (!pToken)
++ ScExternalRefCache::TokenRef pToken = pRefMgr->getSingleRefToken(nFileId, rTabName, rCell, NULL, NULL);
++ if (!pToken.get())
+ return;
+
+ sal_uInt16 nSheetId = xSupbook->GetTabIndex(rTabName);
@@ -4642,8 +5319,8 @@
+ aMatrixList.reserve(nTabCount);
+
+ // This is a new'ed instance, so we must manage its life cycle here.
-+ ScTokenArray* pArray = pRefMgr->getDoubleRefTokens(nFileId, rTabName, rRange, NULL);
-+ if (!pArray)
++ ScExternalRefCache::TokenArrayRef pArray = pRefMgr->getDoubleRefTokens(nFileId, rTabName, rRange, NULL);
++ if (!pArray.get())
+ return;
+
+ for (ScToken* p = pArray->First(); p; p = pArray->Next())
@@ -4689,13 +5366,13 @@
bool XclExpSupbookBuffer::InsertAddIn(
sal_uInt16& rnSupbook, sal_uInt16& rnExtName, const String& rName )
{
-@@ -1383,6 +1813,78 @@ bool XclExpSupbookBuffer::InsertDde(
+@@ -1383,6 +1815,78 @@ bool XclExpSupbookBuffer::InsertDde(
return rnExtName > 0;
}
+bool XclExpSupbookBuffer::InsertExtName(
+ sal_uInt16& rnSupbook, sal_uInt16& rnExtName, const String& rUrl,
-+ const String& rName, const ScTokenArray* pArray )
++ const String& rName, const ScExternalRefCache::TokenArrayRef pArray )
+{
+ XclExpSupbookRef xSupbook;
+ if (!GetSupbookUrl(xSupbook, rnSupbook, rUrl))
@@ -4768,7 +5445,7 @@
void XclExpSupbookBuffer::Save( XclExpStream& rStrm )
{
maSupbookList.Save( rStrm );
-@@ -1424,27 +1926,6 @@ sal_uInt16 XclExpSupbookBuffer::Append( XclExpSupbookRef xSupbook )
+@@ -1424,27 +1928,6 @@ sal_uInt16 XclExpSupbookBuffer::Append( XclExpSupbookRef xSupbook )
return ulimit_cast< sal_uInt16 >( maSupbookList.GetSize() - 1 );
}
@@ -4796,7 +5473,7 @@
// Export link manager ========================================================
XclExpLinkManagerImpl::XclExpLinkManagerImpl( const XclExpRoot& rRoot ) :
-@@ -1485,11 +1966,29 @@ sal_uInt16 XclExpLinkManagerImpl5::FindExtSheet( sal_Unicode cCode )
+@@ -1485,11 +1968,29 @@ sal_uInt16 XclExpLinkManagerImpl5::FindExtSheet( sal_Unicode cCode )
return nExtSheet;
}
@@ -4826,13 +5503,13 @@
bool XclExpLinkManagerImpl5::InsertAddIn(
sal_uInt16& rnExtSheet, sal_uInt16& rnExtName, const String& rName )
{
-@@ -1510,6 +2009,14 @@ bool XclExpLinkManagerImpl5::InsertDde(
+@@ -1510,6 +2011,14 @@ bool XclExpLinkManagerImpl5::InsertDde(
return false;
}
+bool XclExpLinkManagerImpl5::InsertExtName(
+ sal_uInt16& /*rnExtSheet*/, sal_uInt16& /*rnExtName*/, const String& /*rUrl*/,
-+ const String& /*rName*/, const ScTokenArray* /*pArray*/ )
++ const String& /*rName*/, const ScExternalRefCache::TokenArrayRef /*pArray*/ )
+{
+ // not implemented
+ return false;
@@ -4841,7 +5518,7 @@
void XclExpLinkManagerImpl5::Save( XclExpStream& rStrm )
{
if( sal_uInt16 nExtSheetCount = GetExtSheetCount() )
-@@ -1630,6 +2137,17 @@ sal_uInt16 XclExpLinkManagerImpl8::FindExtSheet( sal_Unicode cCode )
+@@ -1630,6 +2139,17 @@ sal_uInt16 XclExpLinkManagerImpl8::FindExtSheet( sal_Unicode cCode )
return InsertXti( maSBBuffer.GetXti( EXC_TAB_EXTERNAL, EXC_TAB_EXTERNAL ) );
}
@@ -4859,7 +5536,7 @@
void XclExpLinkManagerImpl8::StoreCellRange( const SingleRefData& rRef1, const SingleRefData& rRef2 )
{
if( !rRef1.IsDeleted() && !rRef2.IsDeleted() && (rRef1.nTab >= 0) && (rRef2.nTab >= 0) )
-@@ -1652,6 +2170,19 @@ void XclExpLinkManagerImpl8::StoreCellRange( const SingleRefData& rRef1, const S
+@@ -1652,6 +2172,19 @@ void XclExpLinkManagerImpl8::StoreCellRange( const SingleRefData& rRef1, const S
}
}
@@ -4879,12 +5556,12 @@
bool XclExpLinkManagerImpl8::InsertAddIn(
sal_uInt16& rnExtSheet, sal_uInt16& rnExtName, const String& rName )
{
-@@ -1677,6 +2208,18 @@ bool XclExpLinkManagerImpl8::InsertDde(
+@@ -1677,6 +2210,18 @@ bool XclExpLinkManagerImpl8::InsertDde(
return false;
}
-+bool XclExpLinkManagerImpl8::InsertExtName(
-+ sal_uInt16& rnExtSheet, sal_uInt16& rnExtName, const String& rName, const String& rUrl, const ScTokenArray* pArray )
++bool XclExpLinkManagerImpl8::InsertExtName( sal_uInt16& rnExtSheet, sal_uInt16& rnExtName,
++ const String& rName, const String& rUrl, const ScExternalRefCache::TokenArrayRef pArray )
+{
+ sal_uInt16 nSupbook;
+ if( maSBBuffer.InsertExtName( nSupbook, rnExtName, rUrl, rName, pArray ) )
@@ -4898,7 +5575,7 @@
void XclExpLinkManagerImpl8::Save( XclExpStream& rStrm )
{
if( !maXtiVec.empty() )
-@@ -1745,6 +2288,13 @@ sal_uInt16 XclExpLinkManager::FindExtSheet( sal_Unicode cCode )
+@@ -1745,6 +2290,13 @@ sal_uInt16 XclExpLinkManager::FindExtSheet( sal_Unicode cCode )
return mxImpl->FindExtSheet( cCode );
}
@@ -4912,7 +5589,7 @@
void XclExpLinkManager::StoreCell( const SingleRefData& rRef )
{
mxImpl->StoreCellRange( rRef, rRef );
-@@ -1755,6 +2305,16 @@ void XclExpLinkManager::StoreCellRange( const ComplRefData& rRef )
+@@ -1755,6 +2307,16 @@ void XclExpLinkManager::StoreCellRange( const ComplRefData& rRef )
mxImpl->StoreCellRange( rRef.Ref1, rRef.Ref2 );
}
@@ -4929,13 +5606,13 @@
bool XclExpLinkManager::InsertAddIn(
sal_uInt16& rnExtSheet, sal_uInt16& rnExtName, const String& rName )
{
-@@ -1768,6 +2328,13 @@ bool XclExpLinkManager::InsertDde(
+@@ -1768,6 +2330,13 @@ bool XclExpLinkManager::InsertDde(
return mxImpl->InsertDde( rnExtSheet, rnExtName, rApplic, rTopic, rItem );
}
+bool XclExpLinkManager::InsertExtName(
+ sal_uInt16& rnExtSheet, sal_uInt16& rnExtName, const String& rName, const String& rUrl,
-+ const ScTokenArray* pArray )
++ const ScExternalRefCache::TokenArrayRef pArray )
+{
+ return mxImpl->InsertExtName( rnExtSheet, rnExtName, rUrl, rName, pArray );
+}
@@ -4944,7 +5621,7 @@
{
mxImpl->Save( rStrm );
diff --git sc/source/filter/excel/xilink.cxx sc/source/filter/excel/xilink.cxx
-index 01932a5..ab4c08b 100644
+index 01932a5..0b79f64 100644
--- sc/source/filter/excel/xilink.cxx
+++ sc/source/filter/excel/xilink.cxx
@@ -38,6 +38,13 @@
@@ -4985,7 +5662,7 @@
- void CreateAndFillTable(
- const XclImpRoot& rRoot, const String& rAbsUrl,
- const String& rFilterName, const String& rFilterOpt );
-+ void LoadCachedValues(ScExternalRefCache::Table* pCacheTable);
++ void LoadCachedValues(ScExternalRefCache::TableTypeRef pCacheTable);
private:
typedef ScfDelList< XclImpCrn > XclImpCrnList;
@@ -5165,7 +5842,7 @@
-void XclImpSupbookTab::CreateAndFillTable( const XclImpRoot& rRoot,
- const String& rAbsUrl, const String& rFilterName, const String& rFilterOpt )
-+void XclImpSupbookTab::LoadCachedValues(ScExternalRefCache::Table* pCacheTable)
++void XclImpSupbookTab::LoadCachedValues(ScExternalRefCache::TableTypeRef pCacheTable)
{
- if( mnScTab == SCTAB_INVALID )
- if( rRoot.GetDoc().InsertLinkedEmptyTab( mnScTab, rAbsUrl, rFilterName, rFilterOpt, maTabName ) )
@@ -5286,7 +5963,7 @@
+ return;
+
+ const String& rTabName = pTab->GetTabName();
-+ ScExternalRefCache::Table* pCacheTable = pRefMgr->getCacheTable(nFileId, rTabName, true);
++ ScExternalRefCache::TableTypeRef pCacheTable = pRefMgr->getCacheTable(nFileId, rTabName, true);
+ pTab->LoadCachedValues(pCacheTable);
}
}
@@ -5619,10 +6296,18 @@
#endif
diff --git sc/source/filter/inc/xelink.hxx sc/source/filter/inc/xelink.hxx
-index 795219c..ee53c3a 100644
+index 795219c..b12f064 100644
--- sc/source/filter/inc/xelink.hxx
+++ sc/source/filter/inc/xelink.hxx
-@@ -173,11 +173,19 @@ public:
+@@ -36,6 +36,7 @@
+ #include "xehelper.hxx"
+ #include "xerecord.hxx"
+ #include "xeformula.hxx"
++#include "externalrefmgr.hxx"
+
+ class ScRange;
+ struct SingleRefData;
+@@ -173,11 +174,19 @@ public:
/** Searches for a special EXTERNSHEET index for the own document. */
sal_uInt16 FindExtSheet( sal_Unicode cCode );
@@ -5642,13 +6327,13 @@
/** Finds or inserts an EXTERNNAME record for an add-in function name.
@param rnExtSheet (out-param) Returns the index of the EXTSHEET structure for the add-in function name.
@param rnExtName (out-param) Returns the 1-based EXTERNNAME record index.
-@@ -193,6 +201,10 @@ public:
+@@ -193,6 +202,10 @@ public:
sal_uInt16& rnExtSheet, sal_uInt16& rnExtName,
const String& rApplic, const String& rTopic, const String& rItem );
+ bool InsertExtName(
+ sal_uInt16& rnExtSheet, sal_uInt16& rnExtName, const String& rUrl,
-+ const String& rName, const ScTokenArray* pArray );
++ const String& rName, const ScExternalRefCache::TokenArrayRef pArray );
+
/** Writes the entire Link table. */
virtual void Save( XclExpStream& rStrm );
@@ -6213,7 +6898,7 @@
//------------------------------------------------------------------
diff --git sc/source/filter/xml/xmlexprt.cxx sc/source/filter/xml/xmlexprt.cxx
-index 441f463..535ed45 100644
+index 441f463..d724e25 100644
--- sc/source/filter/xml/xmlexprt.cxx
+++ sc/source/filter/xml/xmlexprt.cxx
@@ -68,6 +68,7 @@
@@ -6643,8 +7328,8 @@
+ for (vector<String>::const_iterator itr = pTabNames->begin(), itrEnd = pTabNames->end();
+ itr != itrEnd; ++itr)
+ {
-+ ScExternalRefCache::Table* pTable = pRefMgr->getCacheTable(nFileId, *itr, false);
-+ if (!pTable)
++ ScExternalRefCache::TableTypeRef pTable = pRefMgr->getCacheTable(nFileId, *itr, false);
++ if (!pTable.get())
+ continue;
+
+ OUStringBuffer aBuf;
@@ -6760,9 +7445,9 @@
+ }
+
+ // Write out this cell.
-+ ScToken* pToken = pTable->getCell(nRow, nCol).get();
++ ScExternalRefCache::TokenRef pToken = pTable->getCell(nRow, nCol);
+ OUString aStrVal;
-+ if (pToken)
++ if (pToken.get())
+ {
+ switch(pToken->GetType())
+ {
@@ -6824,7 +7509,7 @@
void CollectUserDefinedNamespaces(const SfxItemPool* pPool, sal_uInt16 nAttrib);
diff --git sc/source/filter/xml/xmlexternaltabi.cxx sc/source/filter/xml/xmlexternaltabi.cxx
new file mode 100644
-index 0000000..e1d0ebd
+index 0000000..3417206
--- /dev/null
+++ sc/source/filter/xml/xmlexternaltabi.cxx
@@ -0,0 +1,343 @@
@@ -6990,7 +7675,7 @@
+
+void ScXMLExternalRefRowContext::EndElement()
+{
-+ ScExternalRefCache::Table* pTab = mrExternalRefInfo.mpCacheTable;
++ ScExternalRefCache::TableTypeRef pTab = mrExternalRefInfo.mpCacheTable;
+
+ for (sal_Int32 i = 1; i < mnRepeatRowCount; ++i)
+ {
@@ -7504,7 +8189,7 @@
extern const XMLPropertyMapEntry aXMLScColumnStylesProperties[];
extern const XMLPropertyMapEntry aXMLScRowStylesProperties[];
diff --git sc/source/filter/xml/xmltabi.cxx sc/source/filter/xml/xmltabi.cxx
-index 4a0f83e..264901d 100644
+index 4a0f83e..4dd5a55 100644
--- sc/source/filter/xml/xmltabi.cxx
+++ sc/source/filter/xml/xmltabi.cxx
@@ -40,6 +40,7 @@
@@ -7594,7 +8279,7 @@
+}
+
+ScXMLExternalTabData::ScXMLExternalTabData() :
-+ mpCacheTable(NULL), mnRow(0), mnCol(0), mnFileId(0)
++ mpCacheTable(), mnRow(0), mnCol(0), mnFileId(0)
+{
+}
+
@@ -7680,7 +8365,7 @@
if( !pContext )
diff --git sc/source/filter/xml/xmltabi.hxx sc/source/filter/xml/xmltabi.hxx
-index 687cff8..e2960c2 100644
+index 687cff8..5dbfeea 100644
--- sc/source/filter/xml/xmltabi.hxx
+++ sc/source/filter/xml/xmltabi.hxx
@@ -30,13 +30,28 @@
@@ -7697,7 +8382,7 @@
+struct ScXMLExternalTabData
+{
+ String maFileUrl;
-+ ScExternalRefCache::Table* mpCacheTable;
++ ScExternalRefCache::TableTypeRef mpCacheTable;
+ sal_Int32 mnRow;
+ sal_Int32 mnCol;
+ sal_uInt16 mnFileId;
@@ -7746,10 +8431,10 @@
diff --git sc/source/ui/docshell/externalrefmgr.cxx sc/source/ui/docshell/externalrefmgr.cxx
new file mode 100644
-index 0000000..25266aa
+index 0000000..1a06014
--- /dev/null
+++ sc/source/ui/docshell/externalrefmgr.cxx
-@@ -0,0 +1,1328 @@
+@@ -0,0 +1,1319 @@
+/*************************************************************************
+ *
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
@@ -7922,13 +8607,13 @@
+{
+}
+
-+ScToken* ScExternalRefCache::getCellData(sal_uInt16 nFileId, const String& rTabName, SCROW nRow, SCCOL nCol)
++ScExternalRefCache::TokenRef ScExternalRefCache::getCellData(sal_uInt16 nFileId, const String& rTabName, SCROW nRow, SCCOL nCol)
+{
+ DocDataType::const_iterator itrDoc = maDocs.find(nFileId);
+ if (itrDoc == maDocs.end())
+ {
+ // specified document is not cached.
-+ return NULL;
++ return TokenRef();
+ }
+
+ const DocItem& rDoc = itrDoc->second;
@@ -7936,36 +8621,36 @@
+ if (itrTabId == rDoc.maTableNameIndex.end())
+ {
+ // the specified table is not in cache.
-+ return NULL;
++ return TokenRef();
+ }
+
+ const TableTypeRef& pTableData = rDoc.maTables[itrTabId->second];
+ if (!pTableData.get())
+ {
+ // the table data is not instantiated yet.
-+ return NULL;
++ return TokenRef();
+ }
-+ return pTableData->getCell(nRow, nCol).get();
++ return pTableData->getCell(nRow, nCol);
+}
+
-+ScTokenArray* ScExternalRefCache::getCellRangeData(sal_uInt16 nFileId, const String& rTabName, const ScRange& rRange)
++ScExternalRefCache::TokenArrayRef ScExternalRefCache::getCellRangeData(sal_uInt16 nFileId, const String& rTabName, const ScRange& rRange)
+{
+ DocDataType::iterator itrDoc = maDocs.find(nFileId);
+ if (itrDoc == maDocs.end())
+ // specified document is not cached.
-+ return NULL;
++ return TokenArrayRef();
+
+ DocItem& rDoc = itrDoc->second;
+ RangeArrayMap::const_iterator itrRange = rDoc.maRangeArrays.find(rRange);
+ if (itrRange != rDoc.maRangeArrays.end())
+ {
-+ return itrRange->second.get();
++ return itrRange->second;
+ }
+
+ TableNameIndexMap::iterator itrTabId = rDoc.maTableNameIndex.find(rTabName);
+ if (itrTabId == rDoc.maTableNameIndex.end())
+ // the specified table is not in cache.
-+ return NULL;
++ return TokenArrayRef();
+
+ const ScAddress& s = rRange.aStart;
+ const ScAddress& e = rRange.aEnd;
@@ -7979,7 +8664,7 @@
+ size_t nTabLastId = nTabFirstId + nTab2 - nTab1;
+ if (nTabLastId >= rDoc.maTables.size())
+ // not all tables are cached.
-+ return NULL;
++ return TokenArrayRef();
+
+ TokenArrayRef pArray(new ScTokenArray);
+ bool bFirstTab = true;
@@ -7987,7 +8672,7 @@
+ {
+ TableTypeRef pTab = rDoc.maTables[nTab];
+ if (!pTab.get())
-+ return NULL;
++ return TokenArrayRef();
+
+ ScMatrixRef xMat = new ScMatrix(
+ static_cast<SCSIZE>(nCol2-nCol1+1), static_cast<SCSIZE>(nRow2-nRow1+1));
@@ -7998,7 +8683,7 @@
+ {
+ ScToken* pToken = pTab->getCell(nRow, nCol).get();
+ if (!pToken)
-+ return NULL;
++ return TokenArrayRef();
+
+ SCSIZE nC = nCol - nCol1, nR = nRow - nRow1;
+ switch (pToken->GetType())
@@ -8025,21 +8710,21 @@
+ bFirstTab = false;
+ }
+ rDoc.maRangeArrays.insert(RangeArrayMap::value_type(rRange, pArray));
-+ return pArray.get();
++ return pArray;
+}
+
-+ScTokenArray* ScExternalRefCache::getRangeNameTokens(sal_uInt16 nFileId, const String& rName)
++ScExternalRefCache::TokenArrayRef ScExternalRefCache::getRangeNameTokens(sal_uInt16 nFileId, const String& rName)
+{
+ DocItem* pDoc = getDocItem(nFileId);
+ if (!pDoc)
-+ return NULL;
++ return TokenArrayRef();
+
+ RangeNameMap& rMap = pDoc->maRangeNames;
+ RangeNameMap::const_iterator itr = rMap.find(rName);
+ if (itr == rMap.end())
-+ return NULL;
++ return TokenArrayRef();
+
-+ return itr->second.get();
++ return itr->second;
+}
+
+void ScExternalRefCache::setRangeNameTokens(sal_uInt16 nFileId, const String& rName, TokenArrayRef pArray)
@@ -8197,21 +8882,21 @@
+ return &pDoc->maTableNames;
+}
+
-+ScExternalRefCache::Table* ScExternalRefCache::getCacheTable(sal_uInt16 nFileId, const String& rTabName, bool bCreateNew)
++ScExternalRefCache::TableTypeRef ScExternalRefCache::getCacheTable(sal_uInt16 nFileId, const String& rTabName, bool bCreateNew)
+{
+ DocItem* pDoc = getDocItem(nFileId);
+ if (!pDoc)
-+ return NULL;
++ return TableTypeRef();
+
+ DocItem& rDoc = *pDoc;
+
+ size_t nIndex;
+ if (lcl_getTableDataIndex(rDoc.maTableNameIndex, rTabName, nIndex))
+ // specified table found.
-+ return rDoc.maTables[nIndex].get();
++ return rDoc.maTables[nIndex];
+
+ if (!bCreateNew)
-+ return NULL;
++ return TableTypeRef();
+
+ // Specified table doesn't exist yet. Create one.
+ TableTypeRef pTab(new Table);
@@ -8219,7 +8904,7 @@
+ rDoc.maTableNames.push_back(rTabName);
+ rDoc.maTableNameIndex.insert(
+ TableNameIndexMap::value_type(rTabName, rDoc.maTables.size()-1));
-+ return pTab.get();
++ return pTab;
+}
+
+void ScExternalRefCache::clearCache(sal_uInt16 nFileId)
@@ -8453,7 +9138,7 @@
+ clear();
+}
+
-+ScExternalRefCache::Table* ScExternalRefManager::getCacheTable(sal_uInt16 nFileId, const String& rTabName, bool bCreateNew)
++ScExternalRefCache::TableTypeRef ScExternalRefManager::getCacheTable(sal_uInt16 nFileId, const String& rTabName, bool bCreateNew)
+{
+ return maRefCache.getCacheTable(nFileId, rTabName, bCreateNew);
+}
@@ -8464,8 +9149,9 @@
+ maRefCache.setRangeNameTokens(nFileId, rName, pArray);
+}
+
-+ScToken* ScExternalRefManager::getSingleRefToken(sal_uInt16 nFileId, const String& rTabName, const ScAddress& rCell,
-+ const ScAddress* pCurPos, SCTAB* pTab)
++ScExternalRefCache::TokenRef ScExternalRefManager::getSingleRefToken(
++ sal_uInt16 nFileId, const String& rTabName, const ScAddress& rCell,
++ const ScAddress* pCurPos, SCTAB* pTab)
+{
+ if (pCurPos)
+ insertReferencingCell(nFileId, *pCurPos);
@@ -8476,8 +9162,8 @@
+ *pTab = -1;
+
+ // Check if the given table name and the cell position is cached.
-+ ScToken* pToken = maRefCache.getCellData(nFileId, rTabName, rCell.Row(), rCell.Col());
-+ if (pToken)
++ ScExternalRefCache::TokenRef pToken = maRefCache.getCellData(nFileId, rTabName, rCell.Row(), rCell.Col());
++ if (pToken.get())
+ {
+ return pToken;
+ }
@@ -8486,7 +9172,7 @@
+ ScDocument* pSrcDoc = getSrcDocument(nFileId);
+ if (!pSrcDoc)
+ {
-+ return NULL;
++ return ScExternalRefCache::TokenRef();
+ }
+
+ ScBaseCell* pCell = NULL;
@@ -8494,7 +9180,7 @@
+ if (!pSrcDoc->GetTable(rTabName, nTab))
+ {
+ // specified table name doesn't exist in the source document.
-+ return NULL;
++ return ScExternalRefCache::TokenRef();
+ }
+
+ if (pTab)
@@ -8511,10 +9197,10 @@
+
+ // Now, insert the token into cache table.
+ maRefCache.setCellData(nFileId, rTabName, rCell.Row(), rCell.Col(), pTok);
-+ return pTok.get();
++ return pTok;
+}
+
-+ScTokenArray* ScExternalRefManager::getDoubleRefTokens(sal_uInt16 nFileId, const String& rTabName, const ScRange& rRange, const ScAddress* pCurPos)
++ScExternalRefCache::TokenArrayRef ScExternalRefManager::getDoubleRefTokens(sal_uInt16 nFileId, const String& rTabName, const ScRange& rRange, const ScAddress* pCurPos)
+{
+ if (pCurPos)
+ insertReferencingCell(nFileId, *pCurPos);
@@ -8522,18 +9208,18 @@
+ maybeLinkExternalFile(nFileId);
+
+ // Check if the given table name and the cell position is cached.
-+ ScTokenArray* p = maRefCache.getCellRangeData(nFileId, rTabName, rRange);
-+ if (p)
++ ScExternalRefCache::TokenArrayRef p = maRefCache.getCellRangeData(nFileId, rTabName, rRange);
++ if (p.get())
+ return p;
+
+ ScDocument* pSrcDoc = getSrcDocument(nFileId);
+ if (!pSrcDoc)
-+ return NULL;
++ return ScExternalRefCache::TokenArrayRef();
+
+ SCTAB nTab1;
+ if (!pSrcDoc->GetTable(rTabName, nTab1))
+ // specified table name doesn't exist in the source document.
-+ return NULL;
++ return ScExternalRefCache::TokenArrayRef();
+
+ ScRange aRange(rRange);
+ SCTAB nTabSpan = aRange.aEnd.Tab() - aRange.aStart.Tab();
@@ -8563,34 +9249,34 @@
+ // Cache these values.
+ maRefCache.setCellRangeData(nFileId, rRange, aCacheData, pArray);
+
-+ return pArray.get();
++ return pArray;
+}
+
-+ScTokenArray* ScExternalRefManager::getRangeNameTokens(sal_uInt16 nFileId, const String& rName, const ScAddress* pCurPos)
++ScExternalRefCache::TokenArrayRef ScExternalRefManager::getRangeNameTokens(sal_uInt16 nFileId, const String& rName, const ScAddress* pCurPos)
+{
+ if (pCurPos)
+ insertReferencingCell(nFileId, *pCurPos);
+
+ maybeLinkExternalFile(nFileId);
+
-+ ScTokenArray* pArray = maRefCache.getRangeNameTokens(nFileId, rName);
-+ if (pArray)
++ ScExternalRefCache::TokenArrayRef pArray = maRefCache.getRangeNameTokens(nFileId, rName);
++ if (pArray.get())
+ return pArray;
+
+ ScDocument* pSrcDoc = getSrcDocument(nFileId);
+ if (!pSrcDoc)
-+ return NULL;
++ return ScExternalRefCache::TokenArrayRef();
+
+ ScRangeName* pExtNames = pSrcDoc->GetRangeName();
+ String aUpperName = ScGlobal::pCharClass->upper(rName);
+ USHORT n;
+ bool bRes = pExtNames->SearchNameUpper(aUpperName, n);
+ if (!bRes)
-+ return NULL;
++ return ScExternalRefCache::TokenArrayRef();
+
+ ScRangeData* pRangeData = (*pExtNames)[n];
+ if (!pRangeData)
-+ return NULL;
++ return ScExternalRefCache::TokenArrayRef();
+
+ // Parse all tokens in this external range data, and replace each absolute
+ // reference token with an external reference token, and cache them. Also
@@ -8634,7 +9320,7 @@
+ }
+
+ maRefCache.setRangeNameTokens(nFileId, rName, pNew);
-+ return pNew.get();
++ return pNew;
+}
+
+void ScExternalRefManager::refreshAllReferencingCells(sal_uInt16 nFileId)
@@ -8854,21 +9540,11 @@
+
+ ScFormulaCell* pFC = static_cast<ScFormulaCell*>(pCell);
+
-+ // Check to make sure the cell really contains ocExternalName.
-+ bool bCompile = false;
-+ ScTokenArray* pCode = pFC->GetCode();
-+ pCode->Reset();
-+ for (ScToken* p = pCode->First(); p; p = pCode->Next())
-+ {
-+ // External names, external cell and range references all have a
-+ // ocExternalName token.
-+ if (p->GetOpCode() == ocExternalName)
-+ {
-+ bCompile = true;
-+ break;
-+ }
-+ }
-+ if (!bCompile)
++ // Check to make sure the cell really contains ocExternalRef.
++ // External names, external cell and range references all have a
++ // ocExternalRef token.
++ const ScTokenArray* pCode = pFC->GetCode();
++ if (!pCode->HasOpCode( ocExternalRef))
+ return false;
+
+ ScTokenArray* pArray = pFC->GetCode();
@@ -9138,7 +9814,7 @@
{
aRet <<= uno::Reference<container::XNameAccess>(new ScSheetLinksObj( pDocShell ));
diff --git sc/source/ui/unoobj/linkuno.cxx sc/source/ui/unoobj/linkuno.cxx
-index 52a5a62..96a074e 100644
+index 52a5a62..7fb3e01 100644
--- sc/source/ui/unoobj/linkuno.cxx
+++ sc/source/ui/unoobj/linkuno.cxx
@@ -48,8 +48,20 @@
@@ -9162,14 +9838,14 @@
//------------------------------------------------------------------------
-@@ -1480,4 +1492,223 @@ uno::Reference< sheet::XDDELink > ScDDELinksObj::addDDELink(
+@@ -1480,4 +1492,229 @@ uno::Reference< sheet::XDDELink > ScDDELinksObj::addDDELink(
return xLink;
}
-//------------------------------------------------------------------------
+// ============================================================================
+
-+ScExternalSheetCacheObj::ScExternalSheetCacheObj(ScExternalRefCache::Table* pTable) :
++ScExternalSheetCacheObj::ScExternalSheetCacheObj(ScExternalRefCache::TableTypeRef pTable) :
+ mpTable(pTable)
+{
+}
@@ -9278,11 +9954,17 @@
+ throw (RuntimeException)
+{
+ ScUnoGuard aGuard;
-+ ScExternalRefCache::Table* pTable = mpRefMgr->getCacheTable(mnFileId, aSheetName, true);
++ ScExternalRefCache::TableTypeRef pTable = mpRefMgr->getCacheTable(mnFileId, aSheetName, true);
+ Reference< sheet::XExternalSheetCache > aSheetCache(new ScExternalSheetCacheObj(pTable));
+ return aSheetCache;
+}
+
++sal_Int32 SAL_CALL ScExternalDocLinkObj::getTokenIndex()
++ throw (RuntimeException)
++{
++ return static_cast<sal_Int32>(mnFileId);
++}
++
+// ============================================================================
+
+ScExternalDocLinksObj::ScExternalDocLinksObj(ScDocShell* pDocShell) :
@@ -9387,6 +10069,55 @@
+ return static_cast<sal_Bool>(!maDocLinks.empty());
+}
+
+diff --git sc/source/ui/unoobj/tokenuno.cxx sc/source/ui/unoobj/tokenuno.cxx
+index f16b1c5..f968d7b 100644
+--- sc/source/ui/unoobj/tokenuno.cxx
++++ sc/source/ui/unoobj/tokenuno.cxx
+@@ -123,6 +123,8 @@ void ScFormulaParserObj::SetCompilerFlags( ScCompiler& rCompiler ) const
+ eConv = aConvMap[mnConv];
+
+ rCompiler.SetRefConvention( eConv );
++
++ rCompiler.SetExternalLinks( maExternalLinks);
+ }
+
+ uno::Sequence<sheet::FormulaToken> SAL_CALL ScFormulaParserObj::parseFormula( const rtl::OUString& aFormula )
+@@ -220,6 +222,11 @@ void SAL_CALL ScFormulaParserObj::setPropertyValue(
+ else
+ throw lang::IllegalArgumentException();
+ }
++ else if ( aString.EqualsAscii( SC_UNO_EXTERNALLINKS ) )
++ {
++ if (!(aValue >>= maExternalLinks))
++ throw lang::IllegalArgumentException();
++ }
+ else
+ throw beans::UnknownPropertyException();
+ }
+@@ -253,6 +260,10 @@ uno::Any SAL_CALL ScFormulaParserObj::getPropertyValue( const rtl::OUString& aPr
+ {
+ aRet <<= maOpCodeMapping;
+ }
++ else if ( aString.EqualsAscii( SC_UNO_EXTERNALLINKS ) )
++ {
++ aRet <<= maExternalLinks;
++ }
+ else
+ throw beans::UnknownPropertyException();
+ return aRet;
+@@ -473,7 +484,12 @@ bool ScTokenConversion::ConvertToTokenSequence( uno::Sequence<sheet::FormulaToke
+ if (!ScRangeToSequence::FillMixedArray( rAPI.Data, rToken.GetMatrix(), true))
+ rAPI.Data.clear();
+ break;
++ case svExternalSingleRef:
++ case svExternalDoubleRef:
++ case svExternalName:
++ // FIXME: svExternal... are to be transported via API.
+ default:
++ DBG_ERROR1( "ScTokenConversion::ConvertToTokenSequence: unhandled token type SvStackVar %d", rToken.GetType());
+ rAPI.Data.clear(); // no data
+ }
+ }
diff --git sc/source/ui/view/tabvwsh4.cxx sc/source/ui/view/tabvwsh4.cxx
index 436f0eb..2bf1f26 100644
--- sc/source/ui/view/tabvwsh4.cxx
[
Date Prev][
Date Next] [
Thread Prev][
Thread Next]
[
Thread Index]
[
Date Index]
[
Author Index]