filter/source/msfilter/escherex.cxx  |   33 ++++++++++++++++++--------
 filter/source/msfilter/util.cxx      |    1 
 include/filter/msfilter/escherex.hxx |    3 +-
 sd/qa/unit/data/pptx/tdf162283.pptx  |binary
 sd/qa/unit/export-tests.cxx          |   44 +++++++++++++++++++++++++++++++++++
 sd/source/filter/eppt/epptso.cxx     |   27 +++++++++++++++++++--
 6 files changed, 95 insertions(+), 13 deletions(-)

New commits:
commit 38f6f44a2cc854e652c09bbd7ee3511b5fed3f8e
Author:     Tibor Nagy <tibor.nagy.ext...@allotropia.de>
AuthorDate: Tue Aug 20 01:22:51 2024 +0200
Commit:     Nagy Tibor <tibor.nagy.ext...@allotropia.de>
CommitDate: Wed Aug 21 12:57:57 2024 +0200

    tdf#162283 PPT export: fix regression...
    
    ...was made by: Iefb9d97e0eb10a04c39b515b11e549aeb7be8f25
    
    This regression occurred because there is a feature in MSO that allows
    the shape of a placeholder to be changed. In this case, the placeholder
    is converted into a custom shape after the import and saving custom shape 
from .pptx to .ppt didn't work.
    
    Change-Id: I85305b65742da8b4966d4956b9141c59b4563973
    Reviewed-on: https://gerrit.libreoffice.org/c/core/+/172091
    Reviewed-by: Nagy Tibor <tibor.nagy.ext...@allotropia.de>
    Tested-by: Jenkins

diff --git a/filter/source/msfilter/escherex.cxx 
b/filter/source/msfilter/escherex.cxx
index 0e251dfac83c..d3be3f16906b 100644
--- a/filter/source/msfilter/escherex.cxx
+++ b/filter/source/msfilter/escherex.cxx
@@ -2578,7 +2578,7 @@ bool EscherPropertyContainer::GetAdjustmentValue( const 
drawing::EnhancedCustomS
     return true;
 }
 
-void EscherPropertyContainer::CreateCustomShapeProperties( const MSO_SPT 
eShapeType, const uno::Reference< drawing::XShape > & rXShape )
+void EscherPropertyContainer::CreateCustomShapeProperties( const MSO_SPT 
eShapeType, const uno::Reference< drawing::XShape > & rXShape, bool bOOXML )
 {
     uno::Reference< beans::XPropertySet > aXPropSet( rXShape, uno::UNO_QUERY );
     if ( !aXPropSet.is() )
@@ -2618,6 +2618,14 @@ void 
EscherPropertyContainer::CreateCustomShapeProperties( const MSO_SPT eShapeT
             rSdrObjCustomShape,
             eShapeType));
 
+    bool bUseDefaultObject = false;
+    if (bOOXML)
+    {
+        const mso_CustomShape* pDefCustomShape = 
GetCustomShapeContent(eShapeType);
+        if(pDefCustomShape)
+            bUseDefaultObject = true;
+    }
+
     // convert property "Equations" into std::vector< 
EnhancedCustomShapeEquationEquation >
     std::vector< EnhancedCustomShapeEquation >  aEquations;
     std::vector< sal_Int32 >                    aEquationOrder;
@@ -2632,7 +2640,7 @@ void 
EscherPropertyContainer::CreateCustomShapeProperties( const MSO_SPT eShapeT
         const beans::PropertyValue& rProp = aGeoPropSeq[ i ];
         if ( rProp.Name == sViewBox )
         {
-            if ( !bIsDefaultObject )
+            if (!bIsDefaultObject && !bUseDefaultObject)
             {
                 awt::Rectangle aViewBox;
                 if ( rProp.Value >>= aViewBox )
@@ -2949,7 +2957,7 @@ void 
EscherPropertyContainer::CreateCustomShapeProperties( const MSO_SPT eShapeT
         }
         else if ( rProp.Name == sEquations )
         {
-            if ( !bIsDefaultObject )
+            if (!bIsDefaultObject && !bUseDefaultObject)
             {
                 sal_uInt16 nElements = 
static_cast<sal_uInt16>(aEquations.size());
                 if ( nElements )
@@ -3039,7 +3047,7 @@ void 
EscherPropertyContainer::CreateCustomShapeProperties( const MSO_SPT eShapeT
                     }
                     else if ( rrProp.Name == "Coordinates" )
                     {
-                        if ( !bIsDefaultObject )
+                        if (!bIsDefaultObject && !bUseDefaultObject)
                         {
                             aPathCoordinatesProp = rrProp.Value;
                             bPathCoordinatesProp = true;
@@ -3047,7 +3055,7 @@ void 
EscherPropertyContainer::CreateCustomShapeProperties( const MSO_SPT eShapeT
                     }
                     else if ( rrProp.Name == "GluePoints" )
                     {
-                        if ( !bIsDefaultObject )
+                        if (!bIsDefaultObject && !bUseDefaultObject)
                         {
                             
uno::Sequence<drawing::EnhancedCustomShapeParameterPair> aGluePoints;
                             if ( rrProp.Value >>= aGluePoints )
@@ -3087,7 +3095,7 @@ void 
EscherPropertyContainer::CreateCustomShapeProperties( const MSO_SPT eShapeT
                     }
                     else if ( rrProp.Name == "Segments" )
                     {
-                        if ( !bIsDefaultObject )
+                        if (!bIsDefaultObject && !bUseDefaultObject)
                         {
                             uno::Sequence<drawing::EnhancedCustomShapeSegment> 
aSegments;
                             if ( rrProp.Value >>= aSegments )
@@ -3207,7 +3215,7 @@ void 
EscherPropertyContainer::CreateCustomShapeProperties( const MSO_SPT eShapeT
                     }
                     else if ( rrProp.Name == "StretchX" )
                     {
-                        if ( !bIsDefaultObject )
+                        if (!bIsDefaultObject && !bUseDefaultObject)
                         {
                             sal_Int32 nStretchX = 0;
                             if ( rrProp.Value >>= nStretchX )
@@ -3216,7 +3224,7 @@ void 
EscherPropertyContainer::CreateCustomShapeProperties( const MSO_SPT eShapeT
                     }
                     else if ( rrProp.Name == "StretchY" )
                     {
-                        if ( !bIsDefaultObject )
+                        if (!bIsDefaultObject && !bUseDefaultObject)
                         {
                             sal_Int32 nStretchY = 0;
                             if ( rrProp.Value >>= nStretchY )
@@ -3225,7 +3233,7 @@ void 
EscherPropertyContainer::CreateCustomShapeProperties( const MSO_SPT eShapeT
                     }
                     else if ( rrProp.Name == "TextFrames" )
                     {
-                        if ( !bIsDefaultObject )
+                        if (!bIsDefaultObject && !bUseDefaultObject)
                         {
                             
uno::Sequence<drawing::EnhancedCustomShapeTextFrame> aPathTextFrames;
                             if ( rrProp.Value >>= aPathTextFrames )
@@ -3470,7 +3478,7 @@ void 
EscherPropertyContainer::CreateCustomShapeProperties( const MSO_SPT eShapeT
         }
         else if ( rProp.Name == sHandles )
         {
-            if ( !bIsDefaultObject )
+            if (!bIsDefaultObject && !bUseDefaultObject)
             {
                 bPredefinedHandlesUsed = false;
                 if ( rProp.Value >>= aHandlesPropSeq )
@@ -3657,7 +3665,12 @@ void 
EscherPropertyContainer::CreateCustomShapeProperties( const MSO_SPT eShapeT
             sal_Int32 k, nValue = 0, nAdjustmentValues = 
aAdjustmentSeq.getLength();
             for ( k = 0; k < nAdjustmentValues; k++ )
                 if( GetAdjustmentValue( aAdjustmentSeq[ k ], k, 
nAdjustmentsWhichNeedsToBeConverted, nValue ) )
+                {
+                    if (bUseDefaultObject)
+                        nValue = 21600 * (nValue / 100000.00);
+
                     AddOpt( static_cast<sal_uInt16>( DFF_Prop_adjustValue + k 
), static_cast<sal_uInt32>(nValue) );
+                }
         }
     }
     if( !bPathCoordinatesProp )
diff --git a/filter/source/msfilter/util.cxx b/filter/source/msfilter/util.cxx
index 2415f3ea4bcb..837a33a67342 100644
--- a/filter/source/msfilter/util.cxx
+++ b/filter/source/msfilter/util.cxx
@@ -1277,6 +1277,7 @@ MSO_SPT GETVMLShapeType(std::u16string_view aType)
         {"actionButtonMovie", mso_sptActionButtonMovie},
         {"hostControl", mso_sptHostControl},
         {"textBox", mso_sptTextBox},
+        {"roundRect", mso_sptRoundRectangle},
     };
 
     auto i(aDMLToVMLMap.find(GetOOXMLPresetGeometry(aType)));
diff --git a/include/filter/msfilter/escherex.hxx 
b/include/filter/msfilter/escherex.hxx
index 196dc7918f6e..91606bca13a2 100644
--- a/include/filter/msfilter/escherex.hxx
+++ b/include/filter/msfilter/escherex.hxx
@@ -824,7 +824,8 @@ public:
         // creates all necessary CustomShape properties, this includes also 
Text-, Shadow-, Fill-, and LineProperties
     void        CreateCustomShapeProperties(
                     const MSO_SPT eShapeType,
-                    const css::uno::Reference< css::drawing::XShape > &
+                    const css::uno::Reference< css::drawing::XShape > &,
+                    bool bOOXML = false
                 );
     bool        IsFontWork() const;
 
diff --git a/sd/qa/unit/data/pptx/tdf162283.pptx 
b/sd/qa/unit/data/pptx/tdf162283.pptx
new file mode 100644
index 000000000000..414937d321a9
Binary files /dev/null and b/sd/qa/unit/data/pptx/tdf162283.pptx differ
diff --git a/sd/qa/unit/export-tests.cxx b/sd/qa/unit/export-tests.cxx
index 69b9db9d58f8..04ce872ffe10 100644
--- a/sd/qa/unit/export-tests.cxx
+++ b/sd/qa/unit/export-tests.cxx
@@ -14,6 +14,7 @@
 #include <sdpage.hxx>
 
 #include <comphelper/sequenceashashmap.hxx>
+#include <comphelper/sequence.hxx>
 #include <editeng/editobj.hxx>
 #include <editeng/outlobj.hxx>
 #include <editeng/colritem.hxx>
@@ -30,6 +31,7 @@
 #include <com/sun/star/drawing/XDrawPage.hpp>
 #include <com/sun/star/drawing/XDrawPagesSupplier.hpp>
 #include <com/sun/star/drawing/XMasterPagesSupplier.hpp>
+#include <com/sun/star/drawing/EnhancedCustomShapeAdjustmentValue.hpp>
 #include <com/sun/star/beans/XPropertySet.hpp>
 #include <com/sun/star/awt/XBitmap.hpp>
 #include <com/sun/star/graphic/XGraphic.hpp>
@@ -199,6 +201,48 @@ CPPUNIT_TEST_FIXTURE(SdExportTest, 
testTransparentBackground)
     checkFontAttributes<Color, SvxColorItem>(pObj2, COL_YELLOW, 
EE_CHAR_BKGCOLOR);
 }
 
+CPPUNIT_TEST_FIXTURE(SdExportTest, testTdf162283)
+{
+    createSdImpressDoc("pptx/tdf162283.pptx");
+    saveAndReload(u"MS PowerPoint 97"_ustr);
+
+    uno::Reference<drawing::XDrawPage> xPage(getPage(0));
+    uno::Reference<beans::XPropertySet> xPropSet(getShape(0, xPage));
+
+    CPPUNIT_ASSERT(xPropSet.is());
+    auto aGeomPropSeq = xPropSet->getPropertyValue(u"CustomShapeGeometry"_ustr)
+                            .get<uno::Sequence<beans::PropertyValue>>();
+    auto aGeomPropVec
+        = 
comphelper::sequenceToContainer<std::vector<beans::PropertyValue>>(aGeomPropSeq);
+
+    sal_Int32 nWidth = 0, nHeight = 0, nAdjValue = 0;
+
+    auto aIt1 = std::find_if(
+        aGeomPropVec.begin(), aGeomPropVec.end(),
+        [](const beans::PropertyValue& rValue) { return rValue.Name == 
u"ViewBox"_ustr; });
+    if (aIt1 != aGeomPropVec.end())
+    {
+        awt::Rectangle aViewBox;
+        aIt1->Value >>= aViewBox;
+        nWidth = aViewBox.Width;
+        nHeight = aViewBox.Height;
+    }
+
+    auto aIt2 = std::find_if(
+        aGeomPropVec.begin(), aGeomPropVec.end(),
+        [](const beans::PropertyValue& rValue) { return rValue.Name == 
u"AdjustmentValues"_ustr; });
+    if (aIt2 != aGeomPropVec.end())
+    {
+        uno::Sequence<drawing::EnhancedCustomShapeAdjustmentValue> aAdjustment;
+        aIt2->Value >>= aAdjustment;
+        aAdjustment[0].Value >>= nAdjValue;
+    }
+
+    CPPUNIT_ASSERT_EQUAL(sal_Int32(21600), nWidth);
+    CPPUNIT_ASSERT_EQUAL(sal_Int32(21600), nHeight);
+    CPPUNIT_ASSERT_EQUAL(sal_Int32(6688), nAdjValue);
+}
+
 CPPUNIT_TEST_FIXTURE(SdExportTest, testDecorative)
 {
     createSdImpressDoc("pptx/tdf141058-1.pptx");
diff --git a/sd/source/filter/eppt/epptso.cxx b/sd/source/filter/eppt/epptso.cxx
index 87510606c43b..a5305e60404c 100644
--- a/sd/source/filter/eppt/epptso.cxx
+++ b/sd/source/filter/eppt/epptso.cxx
@@ -1738,7 +1738,30 @@ void PPTWriter::ImplWritePage( const PHLayout& rLayout, 
EscherSolverContainer& a
                 mpPptEscherEx->OpenContainer( ESCHER_SpContainer );
                 ShapeFlag nMirrorFlags;
                 OUString sCustomShapeType;
-                MSO_SPT eShapeType = 
EscherPropertyContainer::GetCustomShapeType( mXShape, nMirrorFlags, 
sCustomShapeType );
+                bool bOOXML = false;
+                css::uno::Any aAny;
+                if (GetPropertyValue(aAny, mXPropSet, 
u"CustomShapeGeometry"_ustr, true))
+                {
+                    uno::Sequence<beans::PropertyValue> aGeoPropSeq;
+                    if (aAny >>= aGeoPropSeq)
+                    {
+                        sal_Int32 i, nCount = aGeoPropSeq.getLength();
+                        for (i = 0; i < nCount; ++i)
+                        {
+                            const beans::PropertyValue& rProp = aGeoPropSeq[i];
+                            if (rProp.Name == "Type")
+                            {
+                                if (rProp.Value >>= sCustomShapeType)
+                                {
+                                    if (sCustomShapeType.startsWith("ooxml"))
+                                        bOOXML = true;
+                                    break;
+                                }
+                            }
+                        }
+                    }
+                }
+                MSO_SPT eShapeType = 
EscherPropertyContainer::GetCustomShapeType( mXShape, nMirrorFlags, 
sCustomShapeType, bOOXML );
                 if ( sCustomShapeType == "col-502ad400" || sCustomShapeType == 
"col-60da8460" )
                 {   // sj: creating metafile for customshapes that can't be 
saved to ms format properly
                     ImplCreateShape( ESCHER_ShpInst_PictureFrame,
@@ -1763,7 +1786,7 @@ void PPTWriter::ImplWritePage( const PHLayout& rLayout, 
EscherSolverContainer& a
                     ImplCreateShape( eShapeType,
                                      nMirrorFlags | ShapeFlag::HaveAnchor | 
ShapeFlag::HaveShapeProperty,
                                      aSolverContainer );
-                    aPropOpt.CreateCustomShapeProperties( eShapeType, mXShape 
);
+                    aPropOpt.CreateCustomShapeProperties( eShapeType, mXShape, 
bOOXML );
                     aPropOpt.CreateFillProperties( mXPropSet, true, mXShape);
                     if ( ImplGetText() )
                     {

Reply via email to