sc/qa/unit/ThemeImportExportTest.cxx   |   34 +++++++++------
 sc/qa/unit/subsequent_export_test4.cxx |    2 
 sc/source/filter/excel/xestyle.cxx     |   72 ++++++++++++++++++++++-----------
 sc/source/filter/inc/xestyle.hxx       |   20 +++++----
 4 files changed, 85 insertions(+), 43 deletions(-)

New commits:
commit 42bbc9fbdf940e55213ee2a259c1d31de2e4cbec
Author:     Tomaž Vajngerl <tomaz.vajng...@collabora.co.uk>
AuthorDate: Sat Jul 1 14:26:08 2023 +0900
Commit:     Tomaž Vajngerl <qui...@gmail.com>
CommitDate: Tue Jul 4 08:42:51 2023 +0200

    sc: add border export and enable round-trip test
    
    Change-Id: I76071185d819b9645d97a3e599ea7f48b341a145
    Reviewed-on: https://gerrit.libreoffice.org/c/core/+/153820
    Tested-by: Jenkins
    Reviewed-by: Tomaž Vajngerl <qui...@gmail.com>

diff --git a/sc/qa/unit/ThemeImportExportTest.cxx 
b/sc/qa/unit/ThemeImportExportTest.cxx
index 95e6d0e2351e..0cf03ea6c010 100644
--- a/sc/qa/unit/ThemeImportExportTest.cxx
+++ b/sc/qa/unit/ThemeImportExportTest.cxx
@@ -60,6 +60,12 @@ CPPUNIT_TEST_FIXTURE(ThemeImportExportTest, testThemeExport)
     assertXPath(pXmlDoc, 
"/x:styleSheet/x:fills/x:fill[4]/x:patternFill/x:fgColor", "theme", "4");
 }
 
+// Round 100th percent to percent value - so that small differences don't fail 
the test
+sal_Int32 roundToPercent(sal_Int16 n100Percent)
+{
+    return sal_Int32(std::round(double(n100Percent) / 100.0));
+}
+
 void checkCellBackgroundThemeColor(ScDocument* pDoc)
 {
     // A1
@@ -90,9 +96,9 @@ void checkCellBackgroundThemeColor(ScDocument* pDoc)
         auto& rTransformations = aComplexColor.getTransformations();
         CPPUNIT_ASSERT_EQUAL(size_t(2), rTransformations.size());
         CPPUNIT_ASSERT_EQUAL(model::TransformationType::LumMod, 
rTransformations[0].meType);
-        CPPUNIT_ASSERT_EQUAL(20, 
sal_Int32(std::round(rTransformations[0].mnValue / 100.0)));
+        CPPUNIT_ASSERT_EQUAL(20, roundToPercent(rTransformations[0].mnValue));
         CPPUNIT_ASSERT_EQUAL(model::TransformationType::LumOff, 
rTransformations[1].meType);
-        CPPUNIT_ASSERT_EQUAL(80, 
sal_Int32(std::round(rTransformations[1].mnValue / 100.0)));
+        CPPUNIT_ASSERT_EQUAL(80, roundToPercent(rTransformations[1].mnValue));
     }
 
     // A3
@@ -109,7 +115,7 @@ void checkCellBackgroundThemeColor(ScDocument* pDoc)
         auto& rTransformations = aComplexColor.getTransformations();
         CPPUNIT_ASSERT_EQUAL(size_t(1), rTransformations.size());
         CPPUNIT_ASSERT_EQUAL(model::TransformationType::LumMod, 
rTransformations[0].meType);
-        CPPUNIT_ASSERT_EQUAL(sal_Int16(5000), rTransformations[0].mnValue);
+        CPPUNIT_ASSERT_EQUAL(50, roundToPercent(rTransformations[0].mnValue));
     }
 }
 
@@ -151,9 +157,9 @@ void checkCellTextThemeColor(ScDocument* pDoc)
         auto& rTransformations = aComplexColor.getTransformations();
         CPPUNIT_ASSERT_EQUAL(size_t(2), rTransformations.size());
         CPPUNIT_ASSERT_EQUAL(model::TransformationType::LumMod, 
rTransformations[0].meType);
-        CPPUNIT_ASSERT_EQUAL(60, 
sal_Int32(std::round(rTransformations[0].mnValue / 100.0)));
+        CPPUNIT_ASSERT_EQUAL(60, roundToPercent(rTransformations[0].mnValue));
         CPPUNIT_ASSERT_EQUAL(model::TransformationType::LumOff, 
rTransformations[1].meType);
-        CPPUNIT_ASSERT_EQUAL(40, 
sal_Int32(std::round(rTransformations[1].mnValue / 100.0)));
+        CPPUNIT_ASSERT_EQUAL(40, roundToPercent(rTransformations[1].mnValue));
     }
 
     // B3
@@ -170,7 +176,7 @@ void checkCellTextThemeColor(ScDocument* pDoc)
         auto& rTransformations = aComplexColor.getTransformations();
         CPPUNIT_ASSERT_EQUAL(size_t(1), rTransformations.size());
         CPPUNIT_ASSERT_EQUAL(model::TransformationType::LumMod, 
rTransformations[0].meType);
-        CPPUNIT_ASSERT_EQUAL(sal_Int16(5000), rTransformations[0].mnValue);
+        CPPUNIT_ASSERT_EQUAL(50, roundToPercent(rTransformations[0].mnValue));
     }
 }
 
@@ -226,9 +232,9 @@ void checkCellBorderThemeColor(ScDocument* pDoc)
             auto& rTransformations = aComplexColor.getTransformations();
             CPPUNIT_ASSERT_EQUAL(size_t(2), rTransformations.size());
             CPPUNIT_ASSERT_EQUAL(model::TransformationType::LumMod, 
rTransformations[0].meType);
-            CPPUNIT_ASSERT_EQUAL(sal_Int16(2000), rTransformations[0].mnValue);
+            CPPUNIT_ASSERT_EQUAL(20, 
roundToPercent(rTransformations[0].mnValue));
             CPPUNIT_ASSERT_EQUAL(model::TransformationType::LumOff, 
rTransformations[1].meType);
-            CPPUNIT_ASSERT_EQUAL(sal_Int16(7999), rTransformations[1].mnValue);
+            CPPUNIT_ASSERT_EQUAL(80, 
roundToPercent(rTransformations[1].mnValue));
         }
         {
             auto* pTop = pBoxItem->GetRight();
@@ -239,9 +245,9 @@ void checkCellBorderThemeColor(ScDocument* pDoc)
             auto& rTransformations = aComplexColor.getTransformations();
             CPPUNIT_ASSERT_EQUAL(size_t(2), rTransformations.size());
             CPPUNIT_ASSERT_EQUAL(model::TransformationType::LumMod, 
rTransformations[0].meType);
-            CPPUNIT_ASSERT_EQUAL(sal_Int16(2000), rTransformations[0].mnValue);
+            CPPUNIT_ASSERT_EQUAL(20, 
roundToPercent(rTransformations[0].mnValue));
             CPPUNIT_ASSERT_EQUAL(model::TransformationType::LumOff, 
rTransformations[1].meType);
-            CPPUNIT_ASSERT_EQUAL(sal_Int16(7999), rTransformations[1].mnValue);
+            CPPUNIT_ASSERT_EQUAL(80, 
roundToPercent(rTransformations[1].mnValue));
         }
         {
             auto* pTop = pBoxItem->GetBottom();
@@ -252,7 +258,7 @@ void checkCellBorderThemeColor(ScDocument* pDoc)
             auto& rTransformations = aComplexColor.getTransformations();
             CPPUNIT_ASSERT_EQUAL(size_t(1), rTransformations.size());
             CPPUNIT_ASSERT_EQUAL(model::TransformationType::LumMod, 
rTransformations[0].meType);
-            CPPUNIT_ASSERT_EQUAL(sal_Int16(5000), rTransformations[0].mnValue);
+            CPPUNIT_ASSERT_EQUAL(50, 
roundToPercent(rTransformations[0].mnValue));
         }
     }
 
@@ -276,7 +282,7 @@ void checkCellBorderThemeColor(ScDocument* pDoc)
             auto& rTransformations = aComplexColor.getTransformations();
             CPPUNIT_ASSERT_EQUAL(size_t(1), rTransformations.size());
             CPPUNIT_ASSERT_EQUAL(model::TransformationType::LumMod, 
rTransformations[0].meType);
-            CPPUNIT_ASSERT_EQUAL(sal_Int16(5000), rTransformations[0].mnValue);
+            CPPUNIT_ASSERT_EQUAL(50, 
roundToPercent(rTransformations[0].mnValue));
         }
 
         {
@@ -288,7 +294,7 @@ void checkCellBorderThemeColor(ScDocument* pDoc)
             auto& rTransformations = aComplexColor.getTransformations();
             CPPUNIT_ASSERT_EQUAL(size_t(1), rTransformations.size());
             CPPUNIT_ASSERT_EQUAL(model::TransformationType::LumMod, 
rTransformations[0].meType);
-            CPPUNIT_ASSERT_EQUAL(sal_Int16(5000), rTransformations[0].mnValue);
+            CPPUNIT_ASSERT_EQUAL(50, 
roundToPercent(rTransformations[0].mnValue));
         }
     }
 }
@@ -297,6 +303,8 @@ CPPUNIT_TEST_FIXTURE(ThemeImportExportTest, 
testCellBorderThemeColor)
 {
     loadFromURL(u"xlsx/Test_ThemeColor_Text_Background_Border.xlsx");
     checkCellBorderThemeColor(getScDoc());
+    saveAndReload("Calc Office Open XML");
+    checkCellBorderThemeColor(getScDoc());
 }
 
 } // end anonymous namespace
diff --git a/sc/qa/unit/subsequent_export_test4.cxx 
b/sc/qa/unit/subsequent_export_test4.cxx
index 096b1d5603c7..74313ef67c27 100644
--- a/sc/qa/unit/subsequent_export_test4.cxx
+++ b/sc/qa/unit/subsequent_export_test4.cxx
@@ -923,7 +923,7 @@ CPPUNIT_TEST_FIXTURE(ScExportTest4, 
testTdf152581_bordercolorNotExportedToXLSX)
     CPPUNIT_ASSERT(pStyles);
 
     // Check if conditional format border color is exported
-    assertXPath(pStyles, "/x:styleSheet/x:dxfs/x:dxf/x:border/x:left/x:color", 
"rgb", "FFED7D31");
+    assertXPath(pStyles, "/x:styleSheet/x:dxfs/x:dxf/x:border/x:left/x:color", 
"theme", "5");
 }
 
 CPPUNIT_TEST_FIXTURE(ScExportTest4, testTdf140431)
diff --git a/sc/source/filter/excel/xestyle.cxx 
b/sc/source/filter/excel/xestyle.cxx
index 87421c525fa2..02fb6c1a90d6 100644
--- a/sc/source/filter/excel/xestyle.cxx
+++ b/sc/source/filter/excel/xestyle.cxx
@@ -1612,7 +1612,7 @@ void XclExpCellAlign::SaveXml( XclExpXmlStream& rStrm ) 
const
 namespace {
 
 void lclGetBorderLine(
-        sal_uInt8& rnXclLine, sal_uInt32& rnColorId,
+        sal_uInt8& rnXclLine, sal_uInt32& rnColorId, model::ComplexColor& 
rComplexColor,
         const ::editeng::SvxBorderLine* pLine, XclExpPalette& rPalette, 
XclBiff eBiff )
 {
     // Document: sc/qa/unit/data/README.cellborders
@@ -1690,9 +1690,15 @@ void lclGetBorderLine(
     if( (eBiff == EXC_BIFF2) && (rnXclLine != EXC_LINE_NONE) )
         rnXclLine = EXC_LINE_THIN;
 
-    rnColorId = (pLine && (rnXclLine != EXC_LINE_NONE)) ?
-        rPalette.InsertColor( pLine->GetColor(), EXC_COLOR_CELLBORDER ) :
-        XclExpPalette::GetColorIdFromIndex( 0 );
+    if (pLine && (rnXclLine != EXC_LINE_NONE))
+    {
+        rnColorId = rPalette.InsertColor(pLine->GetColor(), 
EXC_COLOR_CELLBORDER);
+        rComplexColor = pLine->getComplexColor();
+    }
+    else
+    {
+        rnColorId = XclExpPalette::GetColorIdFromIndex(0);
+    }
 }
 
 } // namespace
@@ -1718,13 +1724,15 @@ bool XclExpCellBorder::FillFromItemSet(
             const SvxLineItem& rTLBRItem = rItemSet.Get( ATTR_BORDER_TLBR );
             sal_uInt8 nTLBRLine;
             sal_uInt32 nTLBRColorId;
-            lclGetBorderLine( nTLBRLine, nTLBRColorId, rTLBRItem.GetLine(), 
rPalette, eBiff );
+            model::ComplexColor aTLBRComplexColor;
+            lclGetBorderLine( nTLBRLine, nTLBRColorId, aTLBRComplexColor, 
rTLBRItem.GetLine(), rPalette, eBiff );
             mbDiagTLtoBR = (nTLBRLine != EXC_LINE_NONE);
 
             const SvxLineItem& rBLTRItem = rItemSet.Get( ATTR_BORDER_BLTR );
             sal_uInt8 nBLTRLine;
             sal_uInt32 nBLTRColorId;
-            lclGetBorderLine( nBLTRLine, nBLTRColorId, rBLTRItem.GetLine(), 
rPalette, eBiff );
+            model::ComplexColor aBLTRComplexColor;
+            lclGetBorderLine( nBLTRLine, nBLTRColorId, aBLTRComplexColor, 
rBLTRItem.GetLine(), rPalette, eBiff );
             mbDiagBLtoTR = (nBLTRLine != EXC_LINE_NONE);
 
             if( ::ScHasPriority( rTLBRItem.GetLine(), rBLTRItem.GetLine() ) )
@@ -1750,10 +1758,12 @@ bool XclExpCellBorder::FillFromItemSet(
         case EXC_BIFF2:
         {
             const SvxBoxItem& rBoxItem = rItemSet.Get( ATTR_BORDER );
-            lclGetBorderLine( mnLeftLine,   mnLeftColorId,   
rBoxItem.GetLeft(),   rPalette, eBiff );
-            lclGetBorderLine( mnRightLine,  mnRightColorId,  
rBoxItem.GetRight(),  rPalette, eBiff );
-            lclGetBorderLine( mnTopLine,    mnTopColorId,    
rBoxItem.GetTop(),    rPalette, eBiff );
-            lclGetBorderLine( mnBottomLine, mnBottomColorId, 
rBoxItem.GetBottom(), rPalette, eBiff );
+
+            lclGetBorderLine(mnLeftLine, mnLeftColorId, maComplexColorLeft, 
rBoxItem.GetLeft(), rPalette, eBiff);
+            lclGetBorderLine(mnRightLine, mnRightColorId, maComplexColorRight, 
rBoxItem.GetRight(), rPalette, eBiff);
+            lclGetBorderLine(mnTopLine, mnTopColorId, maComplexColorTop, 
rBoxItem.GetTop(), rPalette, eBiff);
+            lclGetBorderLine(mnBottomLine, mnBottomColorId, 
maComplexColorBottom, rBoxItem.GetBottom(), rPalette, eBiff);
+
             bUsed |= ScfTools::CheckItem( rItemSet, ATTR_BORDER, bStyle );
         }
 
@@ -1835,13 +1845,29 @@ static const char* ToLineStyle( sal_uInt8 nLineStyle )
     return "*unknown*";
 }
 
-static void lcl_WriteBorder( XclExpXmlStream& rStrm, sal_Int32 nElement, 
sal_uInt8 nLineStyle, const Color& rColor )
+static void lcl_WriteBorder(XclExpXmlStream& rStrm, sal_Int32 nElement, 
sal_uInt8 nLineStyle, const Color& rColor, model::ComplexColor const& 
rComplexColor)
 {
     sax_fastparser::FSHelperPtr& rStyleSheet = rStrm.GetCurrentStream();
     if( nLineStyle == EXC_LINE_NONE )
+    {
         rStyleSheet->singleElement(nElement);
-    else if( rColor == Color( 0, 0, 0 ) )
+    }
+    else if (rComplexColor.isValidSchemeType())
+    {
+        rStyleSheet->startElement(nElement, XML_style, 
ToLineStyle(nLineStyle));
+
+        sal_Int32 nTheme = 
oox::convertThemeColorTypeToExcelThemeNumber(rComplexColor.getSchemeType());
+        double fTintShade = 
oox::convertColorTransformsToTintOrShade(rComplexColor);
+        rStyleSheet->singleElement(XML_color,
+                    XML_theme, OString::number(nTheme),
+                    XML_tint, 
sax_fastparser::UseIf(OString::number(fTintShade), fTintShade != 0.0));
+
+        rStyleSheet->endElement(nElement);
+    }
+    else if (rColor == Color(0, 0, 0))
+    {
         rStyleSheet->singleElement(nElement, XML_style, 
ToLineStyle(nLineStyle));
+    }
     else
     {
         rStyleSheet->startElement(nElement, XML_style, 
ToLineStyle(nLineStyle));
@@ -1850,22 +1876,24 @@ static void lcl_WriteBorder( XclExpXmlStream& rStrm, 
sal_Int32 nElement, sal_uIn
     }
 }
 
-void XclExpCellBorder::SaveXml( XclExpXmlStream& rStrm ) const
+void XclExpCellBorder::SaveXml(XclExpXmlStream& rStream) const
 {
-    sax_fastparser::FSHelperPtr& rStyleSheet = rStrm.GetCurrentStream();
+    sax_fastparser::FSHelperPtr& rStyleSheet = rStream.GetCurrentStream();
 
-    XclExpPalette& rPalette = rStrm.GetRoot().GetPalette();
+    XclExpPalette& rPalette = rStream.GetRoot().GetPalette();
 
     rStyleSheet->startElement( XML_border,
             XML_diagonalUp,     ToPsz( mbDiagBLtoTR ),
             XML_diagonalDown,   ToPsz( mbDiagTLtoBR )
             // OOXTODO: XML_outline
     );
-    lcl_WriteBorder( rStrm, XML_left,       mnLeftLine,     rPalette.GetColor( 
mnLeftColor ) );
-    lcl_WriteBorder( rStrm, XML_right,      mnRightLine,    rPalette.GetColor( 
mnRightColor ) );
-    lcl_WriteBorder( rStrm, XML_top,        mnTopLine,      rPalette.GetColor( 
mnTopColor ) );
-    lcl_WriteBorder( rStrm, XML_bottom,     mnBottomLine,   rPalette.GetColor( 
mnBottomColor ) );
-    lcl_WriteBorder( rStrm, XML_diagonal,   mnDiagLine,     rPalette.GetColor( 
mnDiagColor ) );
+
+    lcl_WriteBorder(rStream, XML_left, mnLeftLine, 
rPalette.GetColor(mnLeftColor), maComplexColorLeft);
+    lcl_WriteBorder(rStream, XML_right, mnRightLine, 
rPalette.GetColor(mnRightColor), maComplexColorRight);
+    lcl_WriteBorder(rStream, XML_top, mnTopLine, 
rPalette.GetColor(mnTopColor), maComplexColorTop);
+    lcl_WriteBorder(rStream, XML_bottom, mnBottomLine, 
rPalette.GetColor(mnBottomColor), maComplexColorBottom);
+    lcl_WriteBorder(rStream, XML_diagonal, mnDiagLine, 
rPalette.GetColor(mnDiagColor), maComplexColorDiagonal);
+
     // OOXTODO: XML_vertical, XML_horizontal
     rStyleSheet->endElement( XML_border );
 }
@@ -2017,7 +2045,7 @@ void XclExpCellArea::SaveXml( XclExpXmlStream& rStrm ) 
const
                 rStyleSheet->singleElement(XML_fgColor, XML_rgb, 
XclXmlUtils::ToOString(rPalette.GetColor(mnForeColor)));
             }
 
-            if (maBackgroundComplexColor.getType() == model::ColorType::Scheme)
+            if (maBackgroundComplexColor.isValidSchemeType())
             {
                 sal_Int32 nTheme = 
oox::convertThemeColorTypeToExcelThemeNumber(maBackgroundComplexColor.getSchemeType());
                 double fTintShade = 
oox::convertColorTransformsToTintOrShade(maBackgroundComplexColor);
@@ -2054,7 +2082,7 @@ void XclExpColor::SaveXml( XclExpXmlStream& rStrm ) const
     sax_fastparser::FSHelperPtr& rStyleSheet = rStrm.GetCurrentStream();
     rStyleSheet->startElement(XML_fill);
     rStyleSheet->startElement(XML_patternFill);
-    if (maComplexColor.getType() == model::ColorType::Scheme)
+    if (maComplexColor.isValidSchemeType())
     {
         sal_Int32 nTheme = 
oox::convertThemeColorTypeToExcelThemeNumber(maComplexColor.getSchemeType());
         double fTintShade = 
oox::convertColorTransformsToTintOrShade(maComplexColor);
diff --git a/sc/source/filter/inc/xestyle.hxx b/sc/source/filter/inc/xestyle.hxx
index 04e0a752bc6b..dd290af06825 100644
--- a/sc/source/filter/inc/xestyle.hxx
+++ b/sc/source/filter/inc/xestyle.hxx
@@ -339,13 +339,19 @@ struct XclExpCellAlign : public XclCellAlign
     @descr  Provides functions to fill from item sets and to fill to Excel 
record data. */
 struct XclExpCellBorder : public XclCellBorder
 {
-    sal_uInt32          mnLeftColorId;      /// Color ID for left line.
-    sal_uInt32          mnRightColorId;     /// Color ID for right line.
-    sal_uInt32          mnTopColorId;       /// Color ID for top line.
-    sal_uInt32          mnBottomColorId;    /// Color ID for bottom line.
-    sal_uInt32          mnDiagColorId;      /// Color ID for diagonal line(s).
-
-    explicit            XclExpCellBorder();
+    sal_uInt32 mnLeftColorId;   /// Color ID for left line.
+    sal_uInt32 mnRightColorId;  /// Color ID for right line.
+    sal_uInt32 mnTopColorId;    /// Color ID for top line.
+    sal_uInt32 mnBottomColorId; /// Color ID for bottom line.
+    sal_uInt32 mnDiagColorId;   /// Color ID for diagonal line(s).
+
+    model::ComplexColor maComplexColorLeft;
+    model::ComplexColor maComplexColorRight;
+    model::ComplexColor maComplexColorTop;
+    model::ComplexColor maComplexColorBottom;
+    model::ComplexColor maComplexColorDiagonal;
+
+    explicit XclExpCellBorder();
 
     /** Fills the border attributes from the passed item set.
         @descr  Fills only the attributes exported in the passed BIFF version.

Reply via email to