[xlsb] fix shared formula, add new Ftab functions

This commit is contained in:
Vladimir Gorshenkov
2021-11-12 14:43:19 +03:00
parent 69f2c29679
commit 2f4ae5ebc8
15 changed files with 201 additions and 89 deletions

View File

@ -53,11 +53,11 @@ public:
static const ElementType type = typeArray;
Ref ref_;
ArrayParsedFormula formula;
bool fAlwaysCalc;
Ref ref_;
ArrayParsedFormula formula;
bool fAlwaysCalc;
RFX rfx; //biff12
RFX rfx; //biff12
};
typedef boost::shared_ptr<Array> ArrayPtr;

View File

@ -56,11 +56,11 @@ public:
static const ElementType type = typeShrFmla;
//-----------------------------
RefU ref_;
BackwardOnlyParam<unsigned char> cUse;
SharedParsedFormula formula;
RefU ref_;
BackwardOnlyParam<unsigned char> cUse;
SharedParsedFormula formula;
XLSB::UncheckedRfX rfx; //in biff12
XLSB::UncheckedRfX rfx; //in biff12
};

View File

@ -430,6 +430,110 @@ Ftab_Cetab::ValuesDetermination::ValuesDetermination()
params_fixed.insert(ParamsFixed(0x0179, 1, L"ROUNDBAHTUP"));
params_fixed.insert(ParamsFixed(0x017A, 1, L"THAIYEAR"));
params_fixed.insert(ParamsFixed(0x017B, -1, L"RTD"));
params_fixed.insert(ParamsFixed(0x017C, -1, L"CUBEVALUE"));
params_fixed.insert(ParamsFixed(0x017D, -1, L"CUBEMEMBER"));
params_fixed.insert(ParamsFixed(0x017E, -1, L"CUBEMEMBERPROPERTY"));
params_fixed.insert(ParamsFixed(0x017F, -1, L"CUBERANKEDMEMBER"));
params_fixed.insert(ParamsFixed(0x0180, 1, L"HEX2BIN"));
params_fixed.insert(ParamsFixed(0x0181, 1, L"HEX2DEC"));
params_fixed.insert(ParamsFixed(0x0182, 1, L"HEX2OCT"));
params_fixed.insert(ParamsFixed(0x0183, 1, L"DEC2BIN"));
params_fixed.insert(ParamsFixed(0x0184, 1, L"DEC2HEX"));
params_fixed.insert(ParamsFixed(0x0185, 1, L"DEC2OCT"));
params_fixed.insert(ParamsFixed(0x0186, 1, L"OCT2BIN"));
params_fixed.insert(ParamsFixed(0x0187, 1, L"OCT2HEX"));
params_fixed.insert(ParamsFixed(0x0188, 1, L"OCT2DEC"));
params_fixed.insert(ParamsFixed(0x0189, 1, L"BIN2DEC"));
params_fixed.insert(ParamsFixed(0x018A, 1, L"BIN2OCT"));
params_fixed.insert(ParamsFixed(0x018B, 1, L"BIN2HEX"));
params_fixed.insert(ParamsFixed(0x018C, 2, L"IMSUB"));
params_fixed.insert(ParamsFixed(0x018D, 2, L"IMDIV"));
params_fixed.insert(ParamsFixed(0x018E, 2, L"IMPOWER"));
params_fixed.insert(ParamsFixed(0x018F, 1, L"IMABS"));
params_fixed.insert(ParamsFixed(0x0190, 1, L"IMSQRT"));
params_fixed.insert(ParamsFixed(0x0191, 1, L"IMLN"));
params_fixed.insert(ParamsFixed(0x0192, 1, L"IMLOG2"));
params_fixed.insert(ParamsFixed(0x0193, 1, L"IMLOG10"));
params_fixed.insert(ParamsFixed(0x0194, 1, L"IMSIN"));
params_fixed.insert(ParamsFixed(0x0195, 1, L"IMCOS"));
params_fixed.insert(ParamsFixed(0x0196, 1, L"IMEXP"));
params_fixed.insert(ParamsFixed(0x0197, 1, L"IMARGUMENT"));
params_fixed.insert(ParamsFixed(0x0198, 1, L"IMCONJUGATE"));
params_fixed.insert(ParamsFixed(0x0199, 1, L"IMAGINARY"));
params_fixed.insert(ParamsFixed(0x019A, 1, L"IMREAL"));
params_fixed.insert(ParamsFixed(0x019B, 2, L"COMPLEX"));
params_fixed.insert(ParamsFixed(0x019C, -1, L"IMSUM"));
params_fixed.insert(ParamsFixed(0x019D, -1, L"IMPRODUCT"));
params_fixed.insert(ParamsFixed(0x019E, 4, L"SERIESSUM"));
params_fixed.insert(ParamsFixed(0x019F, 1, L"FACTDOUBLE"));
params_fixed.insert(ParamsFixed(0x01A0, 1, L"SQRTPI"));
params_fixed.insert(ParamsFixed(0x01A1, 2, L"QUOTIENT"));
params_fixed.insert(ParamsFixed(0x01A2, 1, L"DELTA"));
params_fixed.insert(ParamsFixed(0x01A3, 1, L"GESTEP"));
params_fixed.insert(ParamsFixed(0x01A4, 1, L"ISEVEN"));
params_fixed.insert(ParamsFixed(0x01A5, 1, L"ISODD"));
params_fixed.insert(ParamsFixed(0x01A6, 2, L"MROUND"));
params_fixed.insert(ParamsFixed(0x01A7, 1, L"ERF"));
params_fixed.insert(ParamsFixed(0x01A8, 1, L"ERFC"));
params_fixed.insert(ParamsFixed(0x01A9, 2, L"BESSELJ"));
params_fixed.insert(ParamsFixed(0x01AA, 2, L"BESSELK"));
params_fixed.insert(ParamsFixed(0x01AB, 2, L"BESSELY"));
params_fixed.insert(ParamsFixed(0x01AC, 2, L"BESSELI"));
params_fixed.insert(ParamsFixed(0x01AD, 1, L"XIRR"));
params_fixed.insert(ParamsFixed(0x01AE, 3, L"XNPV"));
params_fixed.insert(ParamsFixed(0x01AF, 5, L"PRICEMAT"));
params_fixed.insert(ParamsFixed(0x01B0, 5, L"YIELDMAT"));
params_fixed.insert(ParamsFixed(0x01B1, 4, L"INTRATE"));
params_fixed.insert(ParamsFixed(0x01B2, 4, L"RECEIVED"));
params_fixed.insert(ParamsFixed(0x01B3, 4, L"DISC"));
params_fixed.insert(ParamsFixed(0x01B4, 4, L"PRICEDISC"));
params_fixed.insert(ParamsFixed(0x01B5, 4, L"YIELDDISC"));
params_fixed.insert(ParamsFixed(0x01B6, 3, L"TBILLEQ"));
params_fixed.insert(ParamsFixed(0x01B7, 3, L"TBILLPRICE"));
params_fixed.insert(ParamsFixed(0x01B8, 3, L"TBILLYIELD"));
params_fixed.insert(ParamsFixed(0x01B9, 6, L"PRICE"));
params_fixed.insert(ParamsFixed(0x01BA, 6, L"YIELD"));
params_fixed.insert(ParamsFixed(0x01BB, 2, L"DOLLARDE"));
params_fixed.insert(ParamsFixed(0x01BC, 2, L"DOLLARFR"));
params_fixed.insert(ParamsFixed(0x01BD, 2, L"NOMINAL"));
params_fixed.insert(ParamsFixed(0x01BE, 2, L"EFFECT"));
params_fixed.insert(ParamsFixed(0x01BF, 6, L"CUMPRINC"));
params_fixed.insert(ParamsFixed(0x01C0, 6, L"CUMIPMT"));
params_fixed.insert(ParamsFixed(0x01C1, 2, L"EDATE"));
params_fixed.insert(ParamsFixed(0x01C2, 2, L"EOMONTH"));
params_fixed.insert(ParamsFixed(0x01C3, 2, L"YEARFRAC"));
params_fixed.insert(ParamsFixed(0x01C4, 3, L"COUPDAYBS"));
params_fixed.insert(ParamsFixed(0x01C5, 3, L"COUPDAYS"));
params_fixed.insert(ParamsFixed(0x01C6, 3, L"COUPDAYSNC"));
params_fixed.insert(ParamsFixed(0x01C7, 3, L"COUPNCD"));
params_fixed.insert(ParamsFixed(0x01C8, 3, L"COUPNUM"));
params_fixed.insert(ParamsFixed(0x01C9, 3, L"COUPPCD"));
params_fixed.insert(ParamsFixed(0x01CA, 5, L"DURATION"));
params_fixed.insert(ParamsFixed(0x01CB, 5, L"MDURATION"));
params_fixed.insert(ParamsFixed(0x01CC, 7, L"ODDLPRICE"));
params_fixed.insert(ParamsFixed(0x01CD, 7, L"ODDLYIELD"));
params_fixed.insert(ParamsFixed(0x01CE, 8, L"ODDFPRICE"));
params_fixed.insert(ParamsFixed(0x01CF, 8, L"ODDFYIELD"));
params_fixed.insert(ParamsFixed(0x01D0, 2, L"RANDBETWEEN"));
params_fixed.insert(ParamsFixed(0x01D1, 1, L"WEEKNUM"));
params_fixed.insert(ParamsFixed(0x01D2, 6, L"AMORDEGRC"));
params_fixed.insert(ParamsFixed(0x01D3, 6, L"AMORLINC"));
params_fixed.insert(ParamsFixed(0x01D5, 6, L"ACCRINT"));
params_fixed.insert(ParamsFixed(0x01D6, 4, L"ACCRINTM"));
params_fixed.insert(ParamsFixed(0x01D7, 2, L"WORKDAY"));
params_fixed.insert(ParamsFixed(0x01D8, 2, L"NETWORKDAYS"));
params_fixed.insert(ParamsFixed(0x01D9, 1, L"GCD"));
params_fixed.insert(ParamsFixed(0x01DA, 1, L"MULTINOMIAL"));
params_fixed.insert(ParamsFixed(0x01DB, 1, L"LCM"));
params_fixed.insert(ParamsFixed(0x01DC, 2, L"FVSCHEDULE"));
params_fixed.insert(ParamsFixed(0x01DD, 3, L"CUBEKPIMEMBER"));
params_fixed.insert(ParamsFixed(0x01DE, 1, L"CUBESET"));
params_fixed.insert(ParamsFixed(0x01DF, 1, L"CUBESETCOUNT"));
params_fixed.insert(ParamsFixed(0x01E0, 2, L"IFERROR"));
params_fixed.insert(ParamsFixed(0x01E1, 2, L"COUNTIFS"));
params_fixed.insert(ParamsFixed(0x01E2, 3, L"SUMIFS"));
params_fixed.insert(ParamsFixed(0x01E3, 2, L"AVERAGEIF"));
params_fixed.insert(ParamsFixed(0x01E4, 3, L"AVERAGEIFS"));
// Cetab values
params_fixed.insert(ParamsFixed(0x8000, -1, L"BEEP"));

View File

@ -48,15 +48,18 @@ PtgAreaN::PtgAreaN(const std::wstring& word, const PtgDataType data_type, const
cell_base_ref(cell_base_ref_init)
{
area -= cell_base_ref;
areaXlsb -= cell_base_ref;
}
void PtgAreaN::set_base_ref(const CellRef& cell_base_ref_new)
{
area += cell_base_ref;
areaXlsb += cell_base_ref;
cell_base_ref = cell_base_ref_new;
area -= cell_base_ref;
areaXlsb -= cell_base_ref;
}

View File

@ -42,7 +42,7 @@ namespace XLSB
{
BASE_OBJECT_DEFINE_CLASS_NAME(CELL)
public:
CELL(_INT32 row);
CELL(_INT32 row, std::vector<XLS::CellRangeRef>& shared_formulas_locations_ref);
virtual ~CELL();
XLS::BaseObjectPtr clone();
@ -55,8 +55,10 @@ namespace XLSB
XLS::BaseObjectPtr m_SHRFMLACELL;
XLS::BaseObjectPtr m_CELLMETA;
std::vector<XLS::BaseObjectPtr> m_arFRT;
_INT32 m_Row;
//_INT32 m_Col;
_INT32 m_Row;
//_INT32 m_Col;
std::vector<XLS::CellRangeRef>& shared_formulas_locations_ref_;
};

View File

@ -43,7 +43,8 @@ using namespace XLS;
namespace XLSB
{
CELLTABLE::CELLTABLE()
CELLTABLE::CELLTABLE(std::vector<CellRangeRef>& shared_formulas_locations_ref) :
shared_formulas_locations_ref_(shared_formulas_locations_ref)
{
}
@ -55,6 +56,11 @@ namespace XLSB
{
BASE_OBJECT_DEFINE_CLASS_NAME(Parenthesis_CELLTABLE)
public:
Parenthesis_CELLTABLE(std::vector<CellRangeRef>& shared_formulas_locations_ref) :
shared_formulas_locations_ref_(shared_formulas_locations_ref)
{
}
BaseObjectPtr clone()
{
return BaseObjectPtr(new Parenthesis_CELLTABLE(*this));
@ -75,7 +81,7 @@ namespace XLSB
else return false;
CELL cell(static_cast<RowHdr*>(m_BrtRowHdr.get())->rw + 1);
CELL cell(static_cast<RowHdr*>(m_BrtRowHdr.get())->rw + 1, shared_formulas_locations_ref_);
int countCELL = proc.repeated(cell, 0, 16384);
@ -102,6 +108,8 @@ namespace XLSB
BaseObjectPtr m_BrtRowHdr;
std::vector<XLS::BaseObjectPtr> m_arCELL;
std::vector<XLS::BaseObjectPtr> m_arFRT;
std::vector<CellRangeRef>& shared_formulas_locations_ref_;
};
BaseObjectPtr CELLTABLE::clone()
@ -117,8 +125,8 @@ namespace XLSB
m_BrtBeginSheetData = elements_.back();
elements_.pop_back();
}
int countParenthesis_CELLTABLE = proc.repeated<Parenthesis_CELLTABLE>(0, 1048576);
Parenthesis_CELLTABLE cell_group(shared_formulas_locations_ref_);
int countParenthesis_CELLTABLE = proc.repeated(cell_group, 0, 1048576);
while(!elements_.empty())
{
_data data;

View File

@ -42,7 +42,7 @@ namespace XLSB
{
BASE_OBJECT_DEFINE_CLASS_NAME(CELLTABLE)
public:
CELLTABLE();
CELLTABLE(std::vector<XLS::CellRangeRef>& shared_formulas_locations_ref);
virtual ~CELLTABLE();
XLS::BaseObjectPtr clone();
@ -57,9 +57,11 @@ namespace XLSB
};
XLS::BaseObjectPtr m_BrtBeginSheetData;
std::vector<_data> m_arParenthesis_CELLTABLE;
XLS::BaseObjectPtr m_BrtEndSheetData;
XLS::BaseObjectPtr m_BrtBeginSheetData;
std::vector<_data> m_arParenthesis_CELLTABLE;
XLS::BaseObjectPtr m_BrtEndSheetData;
std::vector<XLS::CellRangeRef>& shared_formulas_locations_ref_;
};

View File

@ -43,7 +43,8 @@ using namespace XLS;
namespace XLSB
{
CELL::CELL(_INT32 row) : m_Row(row)
CELL::CELL(_INT32 row, std::vector<XLS::CellRangeRef>& shared_formulas_locations_ref)
: m_Row(row), shared_formulas_locations_ref_(shared_formulas_locations_ref)
{
}
@ -69,11 +70,12 @@ namespace XLSB
if(!proc.optional<DATACELL>())
{
if(proc.optional<FMLACELL>())
FMLACELL fmlacell(m_Row, shared_formulas_locations_ref_);
if(proc.optional(fmlacell))
{
m_FMLACELL = elements_.back();
elements_.pop_back();
SHRFMLACELL shrfmlacell(static_cast<FMLACELL*>(m_FMLACELL.get())->m_Col, m_Row);
SHRFMLACELL shrfmlacell(m_Row, static_cast<FMLACELL*>(m_FMLACELL.get())->m_Col, shared_formulas_locations_ref_);
if(proc.optional(shrfmlacell))
{
m_SHRFMLACELL = elements_.back();

View File

@ -33,13 +33,15 @@
#include "FMLACELL.h"
#include "../Biff12_records/CommonRecords.h"
#include "../Biff12_records/Fmla.h"
#include "../Biff12_structures/CellRef.h"
using namespace XLS;
namespace XLSB
{
FMLACELL::FMLACELL()
FMLACELL::FMLACELL(_INT32 row, std::vector<XLS::CellRangeRef>& shared_formulas_locations_ref)
: m_Row(row), shared_formulas_locations_ref_(shared_formulas_locations_ref), isShared(false), m_sharedIndex(-1)
{
}
@ -81,6 +83,16 @@ namespace XLSB
return false;
}
for (size_t i = 0; i < shared_formulas_locations_ref_.size(); i++)
{
auto location = XLSB::RgceLoc(m_Row - 1, m_Col, true, true);
if (shared_formulas_locations_ref_[i].inRange(location))
{
m_sharedIndex = i;
isShared = true;
}
}
m_source = elements_.back();
elements_.pop_back();
return true;

View File

@ -42,17 +42,20 @@ namespace XLSB
{
BASE_OBJECT_DEFINE_CLASS_NAME(FMLACELL)
public:
FMLACELL();
FMLACELL(_INT32 row, std::vector<XLS::CellRangeRef>& shared_formulas_locations_ref);
virtual ~FMLACELL();
XLS::BaseObjectPtr clone();
virtual const bool loadContent(XLS::BinProcessor& proc);
XLS::BaseObjectPtr m_source;
_INT32 m_Col;
XLS::BaseObjectPtr m_source;
_INT32 m_Col;
_INT32 m_Row;
std::vector<XLS::CellRangeRef>& shared_formulas_locations_ref_;
int m_sharedIndex;
bool isShared;
};
} // namespace XLSB

View File

@ -39,7 +39,8 @@ using namespace XLS;
namespace XLSB
{
SHRFMLACELL::SHRFMLACELL(_INT32 row, _INT32 col) : m_Row(row), m_Col(col)
SHRFMLACELL::SHRFMLACELL(_INT32 row, _INT32 col, std::vector<XLS::CellRangeRef>& shared_formulas_locations_ref)
: m_Row(row), m_Col(col), shared_formulas_locations_ref_(shared_formulas_locations_ref), m_sharedIndex(-1)
{
}
@ -55,15 +56,26 @@ namespace XLSB
// SHRFMLACELL = FMLACELL (BrtShrFmla / BrtArrFmla)
const bool SHRFMLACELL::loadContent(BinProcessor& proc)
{
ShrFmla shrFmla(XLSB::RgceLoc(m_Row, m_Col, true, true));
ArrFmla arrFmla(XLSB::RgceLoc(m_Row, m_Col, true, true));
bool isShared = true;
ShrFmla shrFmla(XLSB::RgceLoc(m_Row - 1, m_Col, true, true));
ArrFmla arrFmla(XLSB::RgceLoc(m_Row - 1, m_Col, true, true));
if(!proc.optional(shrFmla))
{
if(!proc.optional(arrFmla))
{
return false;
}
}
else
{
isShared = false;
}
}
m_sharedIndex = shared_formulas_locations_ref_.size();
if(isShared)
shared_formulas_locations_ref_.push_back(shrFmla.rfx);
else
shared_formulas_locations_ref_.push_back(arrFmla.rfx);
m_source = elements_.back();
elements_.pop_back();

View File

@ -42,16 +42,19 @@ namespace XLSB
{
BASE_OBJECT_DEFINE_CLASS_NAME(SHRFMLACELL)
public:
SHRFMLACELL(_INT32 row, _INT32 col);
SHRFMLACELL(_INT32 row, _INT32 col, std::vector<XLS::CellRangeRef>& shared_formulas_locations_ref);
virtual ~SHRFMLACELL();
XLS::BaseObjectPtr clone();
virtual const bool loadContent(XLS::BinProcessor& proc);
XLS::BaseObjectPtr m_source;
_INT32 m_Row;
_INT32 m_Col;
XLS::BaseObjectPtr m_source;
_INT32 m_Row;
_INT32 m_Col;
std::vector<XLS::CellRangeRef>& shared_formulas_locations_ref_;
int m_sharedIndex;
};

View File

@ -75,7 +75,7 @@ BaseObjectPtr WorkSheetStream::clone()
const bool WorkSheetStream::loadContent(BinProcessor& proc)
{
int count = 0;
std::vector<CellRangeRef> shared_formulas_locations;
while (true)
{
CFRecordType::TypeId type = proc.getNextRecordType();
@ -160,7 +160,8 @@ const bool WorkSheetStream::loadContent(BinProcessor& proc)
case rt_BeginSheetData:
{
if (proc.optional<CELLTABLE>())
CELLTABLE cell_table_temlate(shared_formulas_locations);
if (proc.optional(cell_table_temlate))
{
m_CELLTABLE = elements_.back();
elements_.pop_back();

View File

@ -64,7 +64,7 @@ namespace XLSB
static const XLS::ElementType type = XLS::typeWorksheetSubstream;
XLS::BaseObjectPtr m_BrtBeginSheet;
std::vector<XLS::BaseObjectPtr> m_arCOLINFOS;
std::vector<XLS::BaseObjectPtr> m_arCOLINFOS;
XLS::BaseObjectPtr m_BrtWsDim;
XLS::BaseObjectPtr m_BrtDrawing;
XLS::BaseObjectPtr m_BrtLegacyDrawing;
@ -77,9 +77,9 @@ namespace XLSB
XLS::BaseObjectPtr m_BrtSheetProtectionIso;
XLS::BaseObjectPtr m_BrtSheetProtection;
XLS::BaseObjectPtr m_LISTPARTS;
XLS::BaseObjectPtr m_AUTOFILTER;
XLS::BaseObjectPtr m_AUTOFILTER;
XLS::BaseObjectPtr m_SORTSTATE;
std::vector<XLS::BaseObjectPtr> m_arCONDITIONALFORMATTING;
std::vector<XLS::BaseObjectPtr> m_arCONDITIONALFORMATTING;
XLS::BaseObjectPtr m_FRTWORKSHEET;
XLS::BaseObjectPtr m_BrtEndSheet;

View File

@ -908,7 +908,7 @@ namespace OOX
auto formula = dynamic_cast<XLSB::ShrFmla*>(obj.get());
m_sText = formula->formula.getAssembledFormula();
m_oRef.Init();
m_oRef = formula->rfx.toString();
m_oRef = formula->rfx.toString();
}
break;
case SimpleTypes::Spreadsheet::ECellFormulaType::cellformulatypeArray:
@ -1738,6 +1738,8 @@ namespace OOX
if(pFMLACELL->m_source != nullptr)
{
m_oFormula.Init();
if(pFMLACELL->isShared)
m_oFormula->m_oSi = pFMLACELL->m_sharedIndex;
m_oFormula->fromBin(pFMLACELL->m_source, SimpleTypes::Spreadsheet::cellformulatypeNormal);
}
@ -1747,9 +1749,14 @@ namespace OOX
{
m_oFormula.Init();
if(static_cast<BiffRecord*>(pSHRFMLACELL->m_source.get())->getTypeId() == XLSB::rt_ArrFmla)
{
m_oFormula->fromBin(pSHRFMLACELL->m_source, SimpleTypes::Spreadsheet::cellformulatypeArray);
}
else if(static_cast<BiffRecord*>(pSHRFMLACELL->m_source.get())->getTypeId() == XLSB::rt_ShrFmla)
{
m_oFormula->m_oSi = pSHRFMLACELL->m_sharedIndex;
m_oFormula->fromBin(pSHRFMLACELL->m_source, SimpleTypes::Spreadsheet::cellformulatypeShared);
}
}
}
@ -1843,55 +1850,8 @@ namespace OOX
break;
}
}
}
}
/*
if (XLSB::rt_FmlaString <= nType && nType <= XLSB::rt_FmlaError)
{
m_oFormula.Init();
m_oFormula->fromXLSB(oStream);
}
//todo it breaks xslb format
_UINT16 nFlags = oStream.GetUShort();
if(0 != (nFlags & 0x4))
{
if(!m_oFormula.IsInit())
{
m_oFormula.Init();
}
m_oFormula->fromXLSBExt(oStream, nFlags);
if(0 != (nFlags & 0x4000))
{
m_oType.reset(NULL);
m_oValue.reset(NULL);
}
}
if(0 != (nFlags & 0x2000))
{
m_oType.Init();
m_oType->SetValue(SimpleTypes::Spreadsheet::celltypeInlineStr);
m_oRichText.Init();
m_oRichText->fromXLSBExt(oStream);
}
nullable<CFormula> m_oFormula;
nullable<CSi> m_oRichText;
nullable<CText> m_oValue;
else if (strcmp("ss:Formula", wsName) == 0)
{
m_oFormula.Init();
m_oFormula->m_sText = oReader.GetText();
m_oFormula->m_sText = m_oFormula->m_sText.substr(1);
//convert R1C1 to ..
}*/
}
}
void CRow::toXMLStart(NSStringUtils::CStringBuilder& writer) const