chart2/source/model/template/PieChartTypeTemplate.cxx             |   23 +
 officecfg/registry/schema/org/openoffice/Office/Compatibility.xcs |    8 
 sw/qa/extras/uiwriter/uiwriter2.cxx                               |  121 
++++++++++
 3 files changed, 149 insertions(+), 3 deletions(-)

New commits:
commit 47c4921dca9f911fa3744e4c78d0e8c72afccf6c
Author:     Tünde Tóth <[email protected]>
AuthorDate: Mon Aug 10 10:26:06 2020 +0200
Commit:     Gabor Kelemen <[email protected]>
CommitDate: Thu Feb 18 12:38:40 2021 +0100

    tdf#123218 tdf#108067 config key ReverseXAxisOrientationDoughnutChart
    
    for OOXML compatibility of newly created doughnut charts.
    
    The X axis orientation of doughnut charts is the opposite of the primary
    writing direction in LibreOffice but not in Microsoft Office. Default
    value is "true" to keep current behavior. Using "false", the inner and
    outer data series of new doughnut charts are the same, as after DOCX
    export.
    
    Change-Id: If431d5717e70599f07231bd673cd90c196450ae6
    Reviewed-on: https://gerrit.libreoffice.org/c/core/+/100417
    Tested-by: László Németh <[email protected]>
    Reviewed-by: László Németh <[email protected]>
    (cherry picked from commit 22cd7d8b679d238559820d3c4cd5ff0b9153ffce)
    Reviewed-on: https://gerrit.libreoffice.org/c/core/+/111134
    Tested-by: Gabor Kelemen <[email protected]>
    Reviewed-by: Gabor Kelemen <[email protected]>

diff --git a/chart2/source/model/template/PieChartTypeTemplate.cxx 
b/chart2/source/model/template/PieChartTypeTemplate.cxx
index 964b5d96d5c2..ec08764a7509 100644
--- a/chart2/source/model/template/PieChartTypeTemplate.cxx
+++ b/chart2/source/model/template/PieChartTypeTemplate.cxx
@@ -32,6 +32,7 @@
 #include <com/sun/star/chart2/XCoordinateSystemContainer.hpp>
 #include <com/sun/star/uno/XComponentContext.hpp>
 #include <com/sun/star/lang/XMultiServiceFactory.hpp>
+#include <officecfg/Office/Compatibility.hxx>
 #include <tools/diagnose_ex.h>
 
 #include <rtl/math.hxx>
@@ -245,7 +246,12 @@ void PieChartTypeTemplate::adaptScales(
             if( xAxis.is() )
             {
                 chart2::ScaleData aScaleData( xAxis->getScaleData() );
-                aScaleData.Orientation = chart2::AxisOrientation_REVERSE;
+
+                //tdf#123218 Don't reverse the orientation in OOXML-heavy 
environments
+                if( 
officecfg::Office::Compatibility::View::ReverseXAxisOrientationDoughnutChart::get()
 )
+                    aScaleData.Orientation = chart2::AxisOrientation_REVERSE;
+                else
+                    aScaleData.Orientation = 
chart2::AxisOrientation_MATHEMATICAL;
                 xAxis->setScaleData( aScaleData );
             }
         }
@@ -316,15 +322,20 @@ sal_Bool SAL_CALL PieChartTypeTemplate::matchesTemplate(
         {
             double fOffset=0.0;
             bool bAllOffsetsEqual = true;
+            sal_Int32 nOuterSeriesIndex = 0;
 
             std::vector< Reference< chart2::XDataSeries > > aSeriesVec(
                 DiagramHelper::getDataSeriesFromDiagram( xDiagram ));
 
+            //tdf#108067 The outer series is the last series in OOXML-heavy 
environments
+            if( 
!officecfg::Office::Compatibility::View::ReverseXAxisOrientationDoughnutChart::get()
 )
+                nOuterSeriesIndex = aSeriesVec.size() - 1;
+
             //check offset of outer series
             if( !aSeriesVec.empty() )
             {
                 //@todo in future this will depend on Orientation of the 
radius axis scale
-                Reference< chart2::XDataSeries > xSeries( aSeriesVec[0] );
+                Reference< chart2::XDataSeries > xSeries( 
aSeriesVec[nOuterSeriesIndex] );
                 Reference< beans::XPropertySet > xProp( xSeries, 
uno::UNO_QUERY_THROW );
                 xProp->getPropertyValue( "Offset") >>= fOffset;
 
@@ -450,8 +461,14 @@ void SAL_CALL PieChartTypeTemplate::applyStyle(
         uno::Reference< beans::XPropertySet > xProp( xSeries, 
uno::UNO_QUERY_THROW );
 
         bool bTemplateUsesRings = false;
+        sal_Int32 nOuterSeriesIndex = 0;
         getFastPropertyValue( PROP_PIE_TEMPLATE_USE_RINGS ) >>= 
bTemplateUsesRings;
-        if( nSeriesIndex == 0 ) //@todo in future this will depend on 
Orientation of the radius axis scale
+
+        //tdf#108067 The outer series is the last series in OOXML-heavy 
environments
+        if( 
!officecfg::Office::Compatibility::View::ReverseXAxisOrientationDoughnutChart::get()
 )
+            nOuterSeriesIndex = nSeriesCount - 1;
+
+        if( nSeriesIndex == nOuterSeriesIndex ) //@todo in future this will 
depend on Orientation of the radius axis scale
         {
             const OUString aOffsetPropName( "Offset" );
             // get offset mode
diff --git a/officecfg/registry/schema/org/openoffice/Office/Compatibility.xcs 
b/officecfg/registry/schema/org/openoffice/Office/Compatibility.xcs
index 9c93c9513301..5b89f9498005 100644
--- a/officecfg/registry/schema/org/openoffice/Office/Compatibility.xcs
+++ b/officecfg/registry/schema/org/openoffice/Office/Compatibility.xcs
@@ -185,6 +185,14 @@
         </info>
         <value>true</value>
       </prop>
+      <prop oor:name="ReverseXAxisOrientationDoughnutChart" 
oor:type="xs:boolean" oor:nillable="false">
+        <info>
+          <!-- See tdf#123218, tdf#108067 for rationale -->
+          <desc>Specifies the X axis orientation of doughnut charts.</desc>
+          <label>Reverse the X axis orientation of doughnut charts. Disable 
for better OOXML interoperability.</label>
+        </info>
+        <value>true</value>
+      </prop>
     </group>
   </component>
 </oor:component-schema>
diff --git a/sw/qa/extras/uiwriter/uiwriter2.cxx 
b/sw/qa/extras/uiwriter/uiwriter2.cxx
index 1354244a8fc1..88fd3099ce2f 100644
--- a/sw/qa/extras/uiwriter/uiwriter2.cxx
+++ b/sw/qa/extras/uiwriter/uiwriter2.cxx
@@ -14,10 +14,16 @@
 #include <boost/property_tree/json_parser.hpp>
 
 #include <com/sun/star/awt/FontWeight.hpp>
+#include <com/sun/star/chart/XChartDocument.hpp>
+#include <com/sun/star/chart2/XChartDocument.hpp>
+#include <com/sun/star/chart2/AxisOrientation.hpp>
+#include <com/sun/star/chart2/XCoordinateSystemContainer.hpp>
+#include <com/sun/star/lang/XMultiServiceFactory.hpp>
 #include <com/sun/star/style/LineSpacing.hpp>
 #include <com/sun/star/text/TableColumnSeparator.hpp>
 #include <com/sun/star/view/XSelectionSupplier.hpp>
 #include <comphelper/propertysequence.hxx>
+#include <comphelper/configuration.hxx>
 #include <LibreOfficeKit/LibreOfficeKitEnums.h>
 #include <i18nlangtag/languagetag.hxx>
 #include <vcl/scheduler.hxx>
@@ -3020,4 +3026,119 @@ CPPUNIT_TEST_FIXTURE(SwUiWriterTest2, testTdf129655)
     xmlDocUniquePtr pXmlDoc = parseLayoutDump();
     assertXPath(pXmlDoc, "//fly/txt[@WritingMode='Vertical']", 1);
 }
+
+static uno::Reference<text::XTextRange> getAssociatedTextRange(uno::Any object)
+{
+    // possible cases:
+    // 1. a container of other objects - e.g. selection of 0 to n text 
portions, or 1 to n drawing objects
+    try
+    {
+        uno::Reference<container::XIndexAccess> xIndexAccess(object, 
uno::UNO_QUERY_THROW);
+        if (xIndexAccess.is() && xIndexAccess->getCount() > 0)
+        {
+            for (int i = 0; i < xIndexAccess->getCount(); ++i)
+            {
+                uno::Reference<text::XTextRange> xRange
+                    = getAssociatedTextRange(xIndexAccess->getByIndex(i));
+                if (xRange.is())
+                    return xRange;
+            }
+        }
+    }
+    catch (const uno::Exception&)
+    {
+    }
+
+    // 2. another TextContent, having an anchor we can use
+    try
+    {
+        uno::Reference<text::XTextContent> xTextContent(object, 
uno::UNO_QUERY_THROW);
+        if (xTextContent.is())
+        {
+            uno::Reference<text::XTextRange> xRange = 
xTextContent->getAnchor();
+            if (xRange.is())
+                return xRange;
+        }
+    }
+    catch (const uno::Exception&)
+    {
+    }
+
+    // an object which supports XTextRange directly
+    try
+    {
+        uno::Reference<text::XTextRange> xRange(object, uno::UNO_QUERY_THROW);
+        if (xRange.is())
+            return xRange;
+    }
+    catch (const uno::Exception&)
+    {
+    }
+
+    return nullptr;
+}
+
+CPPUNIT_TEST_FIXTURE(SwUiWriterTest2, testTdf123218)
+{
+    struct ReverseXAxisOrientationDoughnutChart
+        : public 
comphelper::ConfigurationProperty<ReverseXAxisOrientationDoughnutChart, bool>
+    {
+        static OUString path()
+        {
+            return 
"/org.openoffice.Office.Compatibility/View/ReverseXAxisOrientationDoughnutChart";
+        }
+        ~ReverseXAxisOrientationDoughnutChart() = delete;
+    };
+    auto batch = comphelper::ConfigurationChanges::create();
+
+    ReverseXAxisOrientationDoughnutChart::set(false, batch);
+    batch->commit();
+
+    createDoc();
+    SwXTextDocument* pTextDoc = 
dynamic_cast<SwXTextDocument*>(mxComponent.get());
+    CPPUNIT_ASSERT(pTextDoc);
+
+    // create an OLE shape in the document
+    uno::Reference<lang::XMultiServiceFactory> xMSF(mxComponent, 
uno::UNO_QUERY_THROW);
+    CPPUNIT_ASSERT(xMSF);
+    uno::Reference<beans::XPropertySet> xShapeProps(
+        xMSF->createInstance("com.sun.star.text.TextEmbeddedObject"), 
uno::UNO_QUERY);
+    xShapeProps->setPropertyValue("CLSID",
+                                  
uno::makeAny(OUString("12dcae26-281f-416f-a234-c3086127382e")));
+    uno::Reference<drawing::XShape> xShape(xShapeProps, uno::UNO_QUERY_THROW);
+    xShape->setSize(awt::Size(16000, 9000));
+    uno::Reference<text::XTextContent> chartTextContent(xShapeProps, 
uno::UNO_QUERY_THROW);
+    uno::Reference<view::XSelectionSupplier> 
xSelSupplier(pTextDoc->getCurrentController(),
+                                                          
uno::UNO_QUERY_THROW);
+    uno::Any aSelection = xSelSupplier->getSelection();
+    uno::Reference<text::XTextRange> xTextRange = 
getAssociatedTextRange(aSelection);
+    CPPUNIT_ASSERT(xTextRange);
+    xTextRange->getText()->insertTextContent(xTextRange, chartTextContent, 
false);
+
+    // insert a doughnut chart
+    uno::Reference<frame::XModel> xDocModel;
+    xShapeProps->getPropertyValue("Model") >>= xDocModel;
+    CPPUNIT_ASSERT(xDocModel);
+    uno::Reference<chart::XChartDocument> xChartDoc(xDocModel, 
uno::UNO_QUERY_THROW);
+    CPPUNIT_ASSERT(xChartDoc);
+    uno::Reference<lang::XMultiServiceFactory> xChartMSF(xChartDoc, 
uno::UNO_QUERY_THROW);
+    CPPUNIT_ASSERT(xChartMSF);
+    uno::Reference<chart::XDiagram> xDiagram(
+        xChartMSF->createInstance("com.sun.star.chart.DonutDiagram"), 
uno::UNO_QUERY);
+    xChartDoc->setDiagram(xDiagram);
+
+    // test primary X axis Orientation value
+    uno::Reference<chart2::XChartDocument> xChartDoc2(xChartDoc, 
uno::UNO_QUERY_THROW);
+    CPPUNIT_ASSERT(xChartDoc2);
+    uno::Reference<chart2::XCoordinateSystemContainer> xCooSysContainer(
+        xChartDoc2->getFirstDiagram(), uno::UNO_QUERY_THROW);
+    uno::Sequence<uno::Reference<chart2::XCoordinateSystem>> xCooSysSequence
+        = xCooSysContainer->getCoordinateSystems();
+    uno::Reference<chart2::XCoordinateSystem> xCoord = xCooSysSequence[0];
+    CPPUNIT_ASSERT(xCoord.is());
+    uno::Reference<chart2::XAxis> xAxis = xCoord->getAxisByDimension(0, 0);
+    CPPUNIT_ASSERT(xAxis.is());
+    chart2::ScaleData aScaleData = xAxis->getScaleData();
+    CPPUNIT_ASSERT_EQUAL(chart2::AxisOrientation_MATHEMATICAL, 
aScaleData.Orientation);
+}
 /* vim:set shiftwidth=4 softtabstop=4 expandtab: */
_______________________________________________
Libreoffice-commits mailing list
[email protected]
https://lists.freedesktop.org/mailman/listinfo/libreoffice-commits

Reply via email to