dev/null |binary sc/qa/unit/data/xls/data-table/mortgage.xls |binary sc/qa/unit/data/xlsx/data-table/multi-table.xlsx |binary sc/qa/unit/data/xlsx/data-table/one-variable.xlsx |binary sc/qa/unit/subsequent_filters-test.cxx | 95 ++++++++++++++++ sc/source/filter/inc/sheetdatabuffer.hxx | 5 sc/source/filter/oox/sheetdatabuffer.cxx | 124 +++++++++++----------- 7 files changed, 160 insertions(+), 64 deletions(-)
New commits: commit 380d36f32a6980c770c52e30d54a153a447549bf Author: Kohei Yoshida <kohei.yosh...@collabora.com> Date: Mon Nov 4 13:57:34 2013 -0500 Two new test cases for importing data tables from XLSX. Change-Id: I87da806612ae50fe1d64b851c5180ff1792752cb diff --git a/sc/qa/unit/data/xlsx/data-table/multi-table.xlsx b/sc/qa/unit/data/xlsx/data-table/multi-table.xlsx new file mode 100644 index 0000000..c2bf488 Binary files /dev/null and b/sc/qa/unit/data/xlsx/data-table/multi-table.xlsx differ diff --git a/sc/qa/unit/data/xlsx/data-table/one-variable.xlsx b/sc/qa/unit/data/xlsx/data-table/one-variable.xlsx new file mode 100644 index 0000000..7ff098b2 Binary files /dev/null and b/sc/qa/unit/data/xlsx/data-table/one-variable.xlsx differ diff --git a/sc/qa/unit/subsequent_filters-test.cxx b/sc/qa/unit/subsequent_filters-test.cxx index 2361f9f..6662dcd 100644 --- a/sc/qa/unit/subsequent_filters-test.cxx +++ b/sc/qa/unit/subsequent_filters-test.cxx @@ -108,6 +108,8 @@ public: void testRepeatedColumnsODS(); void testDataValidityODS(); void testDataTableMortgageXLS(); + void testDataTableOneVarXLSX(); + void testDataTableMultiTableXLSX(); void testDataBarODS(); void testDataBarXLSX(); @@ -171,6 +173,8 @@ public: CPPUNIT_TEST(testRepeatedColumnsODS); CPPUNIT_TEST(testDataValidityODS); CPPUNIT_TEST(testDataTableMortgageXLS); + CPPUNIT_TEST(testDataTableOneVarXLSX); + CPPUNIT_TEST(testDataTableMultiTableXLSX); CPPUNIT_TEST(testBrokenQuotesCSV); CPPUNIT_TEST(testCellValueXLSX); CPPUNIT_TEST(testControlImport); @@ -1073,6 +1077,8 @@ void ScFiltersTest::testDataValidityODS() void ScFiltersTest::testDataTableMortgageXLS() { ScDocShellRef xDocSh = loadDoc("data-table/mortgage.", XLS); + CPPUNIT_ASSERT_MESSAGE("Failed to load the document.", xDocSh.Is()); + ScFormulaOptions aOptions; aOptions.SetFormulaSepArg(","); aOptions.SetFormulaSepArrayCol(","); @@ -1121,6 +1127,87 @@ void ScFiltersTest::testDataTableMortgageXLS() xDocSh->DoClose(); } +void ScFiltersTest::testDataTableOneVarXLSX() +{ + ScDocShellRef xDocSh = loadDoc("data-table/one-variable.", XLSX); + CPPUNIT_ASSERT_MESSAGE("Failed to load the document.", xDocSh.Is()); + + ScFormulaOptions aOptions; + aOptions.SetFormulaSepArg(","); + aOptions.SetFormulaSepArrayCol(","); + aOptions.SetFormulaSepArrayRow(";"); + xDocSh->SetFormulaOptions(aOptions); + + ScDocument* pDoc = xDocSh->GetDocument(); + + // Right now, we have a bug that prevents Calc from re-calculating these + // cells automatically upon file load. We can remove this call if/when we + // fix the aforementioned bug. + pDoc->CalcAll(); + + // B5:B11 should have multiple operations formula cells. Just check the + // top and bottom cells. + + if (!checkFormula(*pDoc, ScAddress(1,4,0), "MULTIPLE.OPERATIONS(B$4,$A$2,$A5)")) + CPPUNIT_FAIL("Wrong formula!"); + + CPPUNIT_ASSERT_EQUAL(2.0, pDoc->GetValue(ScAddress(1,4,0))); + + if (!checkFormula(*pDoc, ScAddress(1,10,0), "MULTIPLE.OPERATIONS(B$4,$A$2,$A11)")) + CPPUNIT_FAIL("Wrong formula!"); + + CPPUNIT_ASSERT_EQUAL(14.0, pDoc->GetValue(ScAddress(1,10,0))); + + // Likewise, E5:I5 should have multiple operations formula cells. Just + // check the left- and right-most cells. + + if (!checkFormula(*pDoc, ScAddress(4,4,0), "MULTIPLE.OPERATIONS($D5,$B$2,E$4)")) + CPPUNIT_FAIL("Wrong formula!"); + + CPPUNIT_ASSERT_EQUAL(10.0, pDoc->GetValue(ScAddress(4,4,0))); + + if (!checkFormula(*pDoc, ScAddress(8,4,0), "MULTIPLE.OPERATIONS($D5,$B$2,I$4)")) + CPPUNIT_FAIL("Wrong formula!"); + + CPPUNIT_ASSERT_EQUAL(50.0, pDoc->GetValue(ScAddress(8,4,0))); + + xDocSh->DoClose(); +} + +void ScFiltersTest::testDataTableMultiTableXLSX() +{ + ScDocShellRef xDocSh = loadDoc("data-table/multi-table.", XLSX); + CPPUNIT_ASSERT_MESSAGE("Failed to load the document.", xDocSh.Is()); + + ScFormulaOptions aOptions; + aOptions.SetFormulaSepArg(","); + aOptions.SetFormulaSepArrayCol(","); + aOptions.SetFormulaSepArrayRow(";"); + xDocSh->SetFormulaOptions(aOptions); + + ScDocument* pDoc = xDocSh->GetDocument(); + + // Right now, we have a bug that prevents Calc from re-calculating these + // cells automatically upon file load. We can remove this call if/when we + // fix the aforementioned bug. + pDoc->CalcAll(); + + // B4:M15 should have multiple operations formula cells. We'll just check + // the top-left and bottom-right ones. + + if (!checkFormula(*pDoc, ScAddress(1,3,0), "MULTIPLE.OPERATIONS($A$3,$E$1,$A4,$D$1,B$3)")) + CPPUNIT_FAIL("Wrong formula!"); + + CPPUNIT_ASSERT_EQUAL(1.0, pDoc->GetValue(ScAddress(1,3,0))); + + if (!checkFormula(*pDoc, ScAddress(12,14,0), "MULTIPLE.OPERATIONS($A$3,$E$1,$A15,$D$1,M$3)")) + CPPUNIT_FAIL("Wrong formula!"); + + CPPUNIT_ASSERT_EQUAL(144.0, pDoc->GetValue(ScAddress(12,14,0))); + + xDocSh->DoClose(); +} + void ScFiltersTest::testBrokenQuotesCSV() { const OUString aFileNameBase("fdo48621_broken_quotes."); commit ed39603f8eb27fc5d03eab00dbc4ed175d0ff9d6 Author: Kohei Yoshida <kohei.yosh...@collabora.com> Date: Mon Nov 4 13:27:44 2013 -0500 Create data-table directory and move the test file into it. Change-Id: I1007525a7d2e1135f0388975f9cb7b0cef9b3142 diff --git a/sc/qa/unit/data/xls/data-table-mortgage.xls b/sc/qa/unit/data/xls/data-table/mortgage.xls similarity index 100% rename from sc/qa/unit/data/xls/data-table-mortgage.xls rename to sc/qa/unit/data/xls/data-table/mortgage.xls diff --git a/sc/qa/unit/subsequent_filters-test.cxx b/sc/qa/unit/subsequent_filters-test.cxx index 4083993..2361f9f 100644 --- a/sc/qa/unit/subsequent_filters-test.cxx +++ b/sc/qa/unit/subsequent_filters-test.cxx @@ -107,7 +107,7 @@ public: void testMergedCellsODS(); void testRepeatedColumnsODS(); void testDataValidityODS(); - void testDataTableXLS(); + void testDataTableMortgageXLS(); void testDataBarODS(); void testDataBarXLSX(); @@ -170,7 +170,7 @@ public: CPPUNIT_TEST(testMergedCellsODS); CPPUNIT_TEST(testRepeatedColumnsODS); CPPUNIT_TEST(testDataValidityODS); - CPPUNIT_TEST(testDataTableXLS); + CPPUNIT_TEST(testDataTableMortgageXLS); CPPUNIT_TEST(testBrokenQuotesCSV); CPPUNIT_TEST(testCellValueXLSX); CPPUNIT_TEST(testControlImport); @@ -1070,9 +1070,9 @@ void ScFiltersTest::testDataValidityODS() xDocSh->DoClose(); } -void ScFiltersTest::testDataTableXLS() +void ScFiltersTest::testDataTableMortgageXLS() { - ScDocShellRef xDocSh = loadDoc("data-table-mortgage.", XLS); + ScDocShellRef xDocSh = loadDoc("data-table/mortgage.", XLS); ScFormulaOptions aOptions; aOptions.SetFormulaSepArg(","); aOptions.SetFormulaSepArrayCol(","); commit d81441dc3b235a5fd0366ef6ad0d3e6885ff70b0 Author: Kohei Yoshida <kohei.yosh...@collabora.com> Date: Mon Nov 4 11:50:18 2013 -0500 Import data tables from xlsx via ScDocumentImport. Change-Id: Id3d526720f99b7557476915beab35b429ec97c1d diff --git a/sc/source/filter/inc/sheetdatabuffer.hxx b/sc/source/filter/inc/sheetdatabuffer.hxx index 192f359..ceb3a80 100644 --- a/sc/source/filter/inc/sheetdatabuffer.hxx +++ b/sc/source/filter/inc/sheetdatabuffer.hxx @@ -176,9 +176,8 @@ private: const ::com::sun::star::table::CellRangeAddress& rRange, const ApiTokenSequence& rTokens ) const; /** Inserts the passed table operation into the sheet. */ - void finalizeTableOperation( - const ::com::sun::star::table::CellRangeAddress& rRange, - const DataTableModel& rModel ) const; + void finalizeTableOperation( + const ::com::sun::star::table::CellRangeAddress& rRange, const DataTableModel& rModel ); /** Writes all cell formatting attributes to the passed cell range list. (depreciates writeXfIdRangeProperties) */ void applyCellMerging( const ::com::sun::star::table::CellRangeAddress& rRange ); diff --git a/sc/source/filter/oox/sheetdatabuffer.cxx b/sc/source/filter/oox/sheetdatabuffer.cxx index 7f9c8e4..ebc7dca 100644 --- a/sc/source/filter/oox/sheetdatabuffer.cxx +++ b/sc/source/filter/oox/sheetdatabuffer.cxx @@ -50,6 +50,8 @@ #include "document.hxx" #include "scitems.hxx" #include "formulacell.hxx" +#include "paramisc.hxx" +#include "documentimport.hxx" namespace oox { namespace xls { @@ -563,71 +565,79 @@ void SheetDataBuffer::finalizeArrayFormula( const CellRangeAddress& rRange, cons xTokens->setArrayTokens( rTokens ); } -void SheetDataBuffer::finalizeTableOperation( const CellRangeAddress& rRange, const DataTableModel& rModel ) const +void SheetDataBuffer::finalizeTableOperation( const CellRangeAddress& rRange, const DataTableModel& rModel ) { + if (rModel.mbRef1Deleted) + return; + + if (rModel.maRef1.isEmpty()) + return; + + if (rRange.StartColumn <= 0 || rRange.StartRow <= 0) + return; + sal_Int16 nSheet = getSheetIndex(); - bool bOk = false; - if( !rModel.mbRef1Deleted && !rModel.maRef1.isEmpty() && (rRange.StartColumn > 0) && (rRange.StartRow > 0) ) + + CellAddress aRef1; + if (!getAddressConverter().convertToCellAddress(aRef1, rModel.maRef1, nSheet, true)) + return; + + ScDocumentImport& rDoc = getDocImport(); + ScTabOpParam aParam; + + ScRange aScRange; + ScUnoConversion::FillScRange(aScRange, rRange); + + if (rModel.mb2dTable) { - CellRangeAddress aOpRange = rRange; - CellAddress aRef1; - if( getAddressConverter().convertToCellAddress( aRef1, rModel.maRef1, nSheet, true ) ) try - { - if( rModel.mb2dTable ) - { - CellAddress aRef2; - if( !rModel.mbRef2Deleted && getAddressConverter().convertToCellAddress( aRef2, rModel.maRef2, nSheet, true ) ) - { - // API call expects input values inside operation range - --aOpRange.StartColumn; - --aOpRange.StartRow; - // formula range is top-left cell of operation range - CellRangeAddress aFormulaRange( nSheet, aOpRange.StartColumn, aOpRange.StartRow, aOpRange.StartColumn, aOpRange.StartRow ); - // set multiple operation - Reference< XMultipleOperation > xMultOp( getCellRange( aOpRange ), UNO_QUERY_THROW ); - xMultOp->setTableOperation( aFormulaRange, TableOperationMode_BOTH, aRef2, aRef1 ); - bOk = true; - } - } - else if( rModel.mbRowTable ) - { - // formula range is column to the left of operation range - CellRangeAddress aFormulaRange( nSheet, aOpRange.StartColumn - 1, aOpRange.StartRow, aOpRange.StartColumn - 1, aOpRange.EndRow ); - // API call expects input values (top row) inside operation range - --aOpRange.StartRow; - // set multiple operation - Reference< XMultipleOperation > xMultOp( getCellRange( aOpRange ), UNO_QUERY_THROW ); - xMultOp->setTableOperation( aFormulaRange, TableOperationMode_ROW, aRef1, aRef1 ); - bOk = true; - } - else - { - // formula range is row above operation range - CellRangeAddress aFormulaRange( nSheet, aOpRange.StartColumn, aOpRange.StartRow - 1, aOpRange.EndColumn, aOpRange.StartRow - 1 ); - // API call expects input values (left column) inside operation range - --aOpRange.StartColumn; - // set multiple operation - Reference< XMultipleOperation > xMultOp( getCellRange( aOpRange ), UNO_QUERY_THROW ); - xMultOp->setTableOperation( aFormulaRange, TableOperationMode_COLUMN, aRef1, aRef1 ); - bOk = true; - } - } - catch( Exception& ) - { - } + // Two-variable data table. + if (rModel.mbRef2Deleted) + return; + + if (rModel.maRef2.isEmpty()) + return; + + CellAddress aRef2; + if (!getAddressConverter().convertToCellAddress(aRef2, rModel.maRef2, nSheet, true)) + return; + + aParam.meMode = ScTabOpParam::Both; + + aParam.aRefFormulaCell.Set(rRange.StartColumn-1, rRange.StartRow-1, nSheet, false, false, false); + aParam.aRefFormulaEnd = aParam.aRefFormulaCell; + + aScRange.aStart.IncRow(-1); + aScRange.aStart.IncCol(-1); + + // Ref1 is row input cell and Ref2 is column input cell. + aParam.aRefRowCell.Set(aRef1.Column, aRef1.Row, aRef1.Sheet, false, false, false); + aParam.aRefColCell.Set(aRef2.Column, aRef2.Row, aRef2.Sheet, false, false, false); + rDoc.setTableOpCells(aScRange, aParam); + + return; } - // on error: fill cell range with #REF! error codes - if( !bOk ) try + // One-variable data table. + + if (rModel.mbRowTable) { - Reference< XCellRangeData > xCellRangeData( getCellRange( rRange ), UNO_QUERY_THROW ); - size_t nWidth = static_cast< size_t >( rRange.EndColumn - rRange.StartColumn + 1 ); - size_t nHeight = static_cast< size_t >( rRange.EndRow - rRange.StartRow + 1 ); - Matrix< Any > aErrorCells( nWidth, nHeight, Any( getFormulaParser().convertErrorToFormula( BIFF_ERR_REF ) ) ); - xCellRangeData->setDataArray( ContainerHelper::matrixToSequenceSequence( aErrorCells ) ); + // One-variable row input cell (horizontal). + aParam.meMode = ScTabOpParam::Row; + aParam.aRefRowCell.Set(aRef1.Column, aRef1.Row, aRef1.Sheet, false, false, false); + aParam.aRefFormulaCell.Set(rRange.StartColumn-1, rRange.StartRow, nSheet, false, true, false); + aParam.aRefFormulaEnd = aParam.aRefFormulaCell; + aScRange.aStart.IncRow(-1); + rDoc.setTableOpCells(aScRange, aParam); } - catch( Exception& ) + else { + // One-variable column input cell (vertical). + aParam.meMode = ScTabOpParam::Column; + aParam.aRefColCell.Set(aRef1.Column, aRef1.Row, aRef1.Sheet, false, false, false); + aParam.aRefFormulaCell.Set(rRange.StartColumn, rRange.StartRow-1, nSheet, true, false, false); + aParam.aRefFormulaEnd = aParam.aRefFormulaCell; + aScRange.aStart.IncCol(-1); + rDoc.setTableOpCells(aScRange, aParam); } } _______________________________________________ Libreoffice-commits mailing list libreoffice-comm...@lists.freedesktop.org http://lists.freedesktop.org/mailman/listinfo/libreoffice-commits