sc/qa/unit/subsequent_export_test4.cxx | 20 ++++++++++++++++++++ sc/source/filter/excel/xename.cxx | 14 +++++++++++--- sc/source/filter/excel/xihelper.cxx | 8 ++++++++ sc/source/filter/inc/xihelper.hxx | 5 +++++ 4 files changed, 44 insertions(+), 3 deletions(-)
New commits: commit 2d472fae8f1223dc969172951d08ff6e4b4f98ba Author: Andreas Heinisch <andreas.heini...@yahoo.de> AuthorDate: Wed Mar 6 13:48:46 2024 +0100 Commit: Andreas Heinisch <andreas.heini...@yahoo.de> CommitDate: Wed Mar 13 09:28:43 2024 +0100 tdf#148170 - Convert print range to an excel cell range During export from Calc to XLS, ensure that the print range is converted to a valid XLS print range. If the print range exceeds XLS format limitations, it will be appropriately cropped to fit within the constraints. Change-Id: I2b233e4d57dfbe30f491448d2ee2972b8b717ea3 Reviewed-on: https://gerrit.libreoffice.org/c/core/+/164469 Tested-by: Jenkins Reviewed-by: Andreas Heinisch <andreas.heini...@yahoo.de> diff --git a/sc/qa/unit/subsequent_export_test4.cxx b/sc/qa/unit/subsequent_export_test4.cxx index 41d76cc9698d..ff453d2ca7ed 100644 --- a/sc/qa/unit/subsequent_export_test4.cxx +++ b/sc/qa/unit/subsequent_export_test4.cxx @@ -761,6 +761,26 @@ CPPUNIT_TEST_FIXTURE(ScExportTest4, testTdf51022_lostPrintRange) CPPUNIT_ASSERT_EQUAL(aRange2, *pDoc->GetPrintRange(0, 1)); } +CPPUNIT_TEST_FIXTURE(ScExportTest4, testTdf148170_ExceedXlsPrintRange) +{ + createScDoc(); + + // Create print range that exceeds the xls limitations + const auto aScSheeLimits = ScSheetLimits::CreateDefault(); + ScRange aCalcPrintRange(0, 0, 0, aScSheeLimits.MaxCol(), aScSheeLimits.MaxRow(), 0); + ScDocument* pDoc = getScDoc(); + pDoc->AddPrintRange(0, aCalcPrintRange); + + saveAndReload("MS Excel 97"); + + // Check if print range was shrunk to xls limitations + pDoc = getScDoc(); + CPPUNIT_ASSERT_EQUAL(static_cast<sal_uInt16>(1), pDoc->GetPrintRangeCount(0)); + // Check sc/source/filter/inc/xlconst.hxx for xls limitations + ScRange aXlsPrintRange(0, 0, 0, 16383, 65535, 0); + CPPUNIT_ASSERT_EQUAL(aXlsPrintRange, *pDoc->GetPrintRange(0, 0)); +} + CPPUNIT_TEST_FIXTURE(ScExportTest4, testTdf138741_externalLinkSkipUnusedsCrash) { createScDoc("xlsx/tdf138741_externalLinkSkipUnusedsCrash.xlsx"); diff --git a/sc/source/filter/excel/xename.cxx b/sc/source/filter/excel/xename.cxx index 84073da8ff90..8d97ffaadda9 100644 --- a/sc/source/filter/excel/xename.cxx +++ b/sc/source/filter/excel/xename.cxx @@ -36,6 +36,7 @@ #include <oox/export/utils.hxx> #include <oox/token/tokens.hxx> #include <com/sun/star/sheet/NamedRangeFlag.hdl> +#include <xihelper.hxx> using namespace ::oox; using namespace ::com::sun::star; @@ -713,10 +714,17 @@ void XclExpNameManagerImpl::CreateBuiltInNames() aRange.aStart.SetTab( nScTab ); aRange.aEnd.SetTab( nScTab ); aRange.PutInOrder(); - aRangeList.push_back( aRange ); + + // tdf#148170 - convert print range to an excel cell range + XclRange aXclRange(ScAddress::UNINITIALIZED); + // create no warning if ranges are shrunken + if (GetAddressConverter().ConvertRange(aXclRange, aRange, false)) + { + XclImpAddressConverter::FillRange(aXclRange, aRange); + aRangeList.push_back(aRange); + } } - // create the NAME record (do not warn if ranges are shrunken) - GetAddressConverter().ValidateRangeList( aRangeList, false ); + // create the NAME record if( !aRangeList.empty() ) GetNameManager().InsertBuiltInName( EXC_BUILTIN_PRINTAREA, aRangeList ); } diff --git a/sc/source/filter/excel/xihelper.cxx b/sc/source/filter/excel/xihelper.cxx index e095d22018ac..2f05d6722d7a 100644 --- a/sc/source/filter/excel/xihelper.cxx +++ b/sc/source/filter/excel/xihelper.cxx @@ -98,6 +98,14 @@ ScAddress XclImpAddressConverter::CreateValidAddress( // cell range ----------------------------------------------------------------- +void XclImpAddressConverter::FillRange(const XclRange& rXclRange, ScRange& rScRange) +{ + const XclAddress aXclStartAdr = rXclRange.maFirst; + lclFillAddress(rScRange.aStart, aXclStartAdr.mnCol, aXclStartAdr.mnRow, rScRange.aStart.Tab()); + const XclAddress aXclEndAdr = rXclRange.maLast; + lclFillAddress(rScRange.aEnd, aXclEndAdr.mnCol, aXclEndAdr.mnRow, rScRange.aEnd.Tab()); +} + bool XclImpAddressConverter::ConvertRange( ScRange& rScRange, const XclRange& rXclRange, SCTAB nScTab1, SCTAB nScTab2, bool bWarn ) { diff --git a/sc/source/filter/inc/xihelper.hxx b/sc/source/filter/inc/xihelper.hxx index 746259e844e4..fe6ba7ce7a63 100644 --- a/sc/source/filter/inc/xihelper.hxx +++ b/sc/source/filter/inc/xihelper.hxx @@ -71,6 +71,11 @@ public: // cell range ------------------------------------------------------------- + /** Fills the passed Calc cell range with the passed Excel cell range. + @param XclRange The Excel cell range to be transfered. + @param ScRange (Out) The filled Calc cell range. */ + static void FillRange(const XclRange& rXclRange, ScRange& rScRange); + /** Converts the passed Excel cell range to a Calc cell range. @param rScRange (Out) The converted Calc cell range, if valid. @param rXclRange The Excel cell range to convert.