include/oox/export/drawingml.hxx |   29 ++--
 oox/source/export/drawingml.cxx  |  253 +++++++++++++++++++--------------------
 oox/source/export/shapes.cxx     |   10 -
 3 files changed, 145 insertions(+), 147 deletions(-)

New commits:
commit 1be8b2752d30d3c024e46526e9d31c1e7066799c
Author:     Tomaž Vajngerl <tomaz.vajng...@collabora.co.uk>
AuthorDate: Sun Dec 3 12:53:58 2023 +0900
Commit:     Tomaž Vajngerl <qui...@gmail.com>
CommitDate: Sun Dec 3 11:09:25 2023 +0100

    oox: Refactor and simplify writing to storage with GraphicExport
    
    Change-Id: I743dc99e0228b59050fb4926c8ef56bed8e82060
    Reviewed-on: https://gerrit.libreoffice.org/c/core/+/160252
    Tested-by: Jenkins
    Reviewed-by: Tomaž Vajngerl <qui...@gmail.com>

diff --git a/include/oox/export/drawingml.hxx b/include/oox/export/drawingml.hxx
index d50023be1c17..9028cfdc0f9f 100644
--- a/include/oox/export/drawingml.hxx
+++ b/include/oox/export/drawingml.hxx
@@ -140,28 +140,28 @@ protected:
     virtual ~DMLTextExport() {}
 };
 
-constexpr const char* getComponentDir(DocumentType eDocumentType)
+constexpr std::u16string_view getComponentDir(DocumentType eDocumentType)
 {
     switch (eDocumentType)
     {
-        case DOCUMENT_DOCX: return "word";
-        case DOCUMENT_PPTX: return "ppt";
-        case DOCUMENT_XLSX: return "xl";
+        case DOCUMENT_DOCX: return u"word";
+        case DOCUMENT_PPTX: return u"ppt";
+        case DOCUMENT_XLSX: return u"xl";
     }
 
-    return "";
+    return u"";
 }
 
-constexpr const char* getRelationCompPrefix(DocumentType eDocumentType)
+constexpr std::u16string_view getRelationCompPrefix(DocumentType eDocumentType)
 {
     switch (eDocumentType)
     {
-        case DOCUMENT_DOCX: return "";
+        case DOCUMENT_DOCX: return u"";
         case DOCUMENT_PPTX:
-        case DOCUMENT_XLSX: return "../";
+        case DOCUMENT_XLSX: return u"../";
     }
 
-    return "";
+    return u"";
 }
 
 class OOX_DLLPUBLIC GraphicExportCache
@@ -251,12 +251,15 @@ public:
     }
 };
 
-class GraphicExport
+class OOX_DLLPUBLIC GraphicExport
 {
+private:
     sax_fastparser::FSHelperPtr mpFS;
     oox::core::XmlFilterBase* mpFilterBase;
     DocumentType meDocumentType;
 
+    OUString writeNewEntryToStorage(const Graphic& rGraphic, bool 
bRelPathToMedia);
+
 public:
     GraphicExport(sax_fastparser::FSHelperPtr pFS, ::oox::core::XmlFilterBase* 
pFilterBase, DocumentType eDocumentType)
         : mpFS(pFS)
@@ -320,8 +323,8 @@ protected:
 
     void WriteStyleProperties( sal_Int32 nTokenId, const css::uno::Sequence< 
css::beans::PropertyValue >& aProperties );
 
-    const char* GetComponentDir() const;
-    const char* GetRelationCompPrefix() const;
+    OUString GetComponentDir() const;
+    OUString GetRelationCompPrefix() const;
 
     static bool EqualGradients( const css::awt::Gradient2& rGradient1, const 
css::awt::Gradient2& rGradient2 );
     bool IsFontworkShape(const css::uno::Reference< css::beans::XPropertySet 
>& rXShapePropSet);
@@ -350,7 +353,7 @@ public:
 
     void SetBackgroundDark(bool bIsDark) { mbIsBackgroundDark = bIsDark; }
     /// If bRelPathToMedia is true add "../" to image folder path while adding 
the image relationship
-    OUString writeGraphicToStorage( const Graphic &rGraphic , bool 
bRelPathToMedia = false );
+    OUString writeGraphicToStorage(const Graphic &rGraphic , bool 
bRelPathToMedia = false);
 
     void WriteColor( ::Color nColor, sal_Int32 nAlpha = MAX_PERCENT );
     void WriteColor( const OUString& sColorSchemeName, const 
css::uno::Sequence< css::beans::PropertyValue >& aTransformations, sal_Int32 
nAlpha = MAX_PERCENT );
diff --git a/oox/source/export/drawingml.cxx b/oox/source/export/drawingml.cxx
index 8c2abb6b07cc..87c693a9cd75 100644
--- a/oox/source/export/drawingml.cxx
+++ b/oox/source/export/drawingml.cxx
@@ -1273,14 +1273,14 @@ void DrawingML::WriteOutline( const 
Reference<XPropertySet>& rXPropSet, Referenc
     mpFS->endElementNS( XML_a, XML_ln );
 }
 
-const char* DrawingML::GetComponentDir() const
+OUString DrawingML::GetComponentDir() const
 {
-    return getComponentDir(meDocumentType);
+    return OUString(getComponentDir(meDocumentType));
 }
 
-const char* DrawingML::GetRelationCompPrefix() const
+OUString DrawingML::GetRelationCompPrefix() const
 {
-    return getRelationCompPrefix(meDocumentType);
+    return OUString(getRelationCompPrefix(meDocumentType));
 }
 
 void GraphicExport::writeBlip(Graphic const& rGraphic, 
std::vector<model::BlipEffect> const& rEffects, bool bRelPathToMedia)
@@ -1401,134 +1401,135 @@ void GraphicExport::writeBlip(Graphic const& 
rGraphic, std::vector<model::BlipEf
     mpFS->endElementNS(XML_a, XML_blip);
 }
 
-OUString GraphicExport::writeToStorage(const Graphic& rGraphic , bool 
bRelPathToMedia)
+OUString GraphicExport::writeNewEntryToStorage(const Graphic& rGraphic, bool 
bRelPathToMedia)
 {
-    GfxLink aLink = rGraphic.GetGfxLink ();
-    BitmapChecksum aChecksum = rGraphic.GetChecksum();
+    GfxLink const& rLink = rGraphic.GetGfxLink();
+
     OUString sMediaType;
-    const char* pExtension = "";
-    OUString sRelId;
-    OUString sPath;
+    OUString aExtension;
 
-    // tdf#74670 tdf#91286 Save image only once
-    GraphicExportCache& rGraphicExportCache = GraphicExportCache::get();
-    sPath = rGraphicExportCache.findExportGraphics(aChecksum);
+    SvMemoryStream aStream;
+    const void* aData = rLink.GetData();
+    std::size_t nDataSize = rLink.GetDataSize();
 
-    if (sPath.isEmpty())
+    switch (rLink.GetType())
     {
-        SvMemoryStream aStream;
-        const void* aData = aLink.GetData();
-        std::size_t nDataSize = aLink.GetDataSize();
-
-        switch (aLink.GetType())
-        {
-            case GfxLinkType::NativeGif:
-                sMediaType = "image/gif";
-                pExtension = ".gif";
-                break;
+        case GfxLinkType::NativeGif:
+            sMediaType = u"image/gif"_ustr;
+            aExtension = u"gif"_ustr;
+            break;
 
-            // #i15508# added BMP type for better exports
-            // export not yet active, so adding for reference (not checked)
-            case GfxLinkType::NativeBmp:
-                sMediaType = "image/bmp";
-                pExtension = ".bmp";
-                break;
+        // #i15508# added BMP type for better exports
+        // export not yet active, so adding for reference (not checked)
+        case GfxLinkType::NativeBmp:
+            sMediaType = u"image/bmp"_ustr;
+            aExtension = u"bmp"_ustr;
+            break;
 
-            case GfxLinkType::NativeJpg:
-                sMediaType = "image/jpeg";
-                pExtension = ".jpeg";
-                break;
-            case GfxLinkType::NativePng:
-                sMediaType = "image/png";
-                pExtension = ".png";
-                break;
-            case GfxLinkType::NativeSvg:
-                sMediaType = "image/svg";
-                pExtension = ".svg";
-                break;
-            case GfxLinkType::NativeTif:
-                sMediaType = "image/tiff";
-                pExtension = ".tif";
-                break;
-            case GfxLinkType::NativeWmf:
-                sMediaType = "image/x-wmf";
-                pExtension = ".wmf";
-                break;
-            case GfxLinkType::NativeMet:
-                sMediaType = "image/x-met";
-                pExtension = ".met";
-                break;
-            case GfxLinkType::NativePct:
-                sMediaType = "image/x-pict";
-                pExtension = ".pct";
-                break;
-            case GfxLinkType::NativeMov:
-                sMediaType = "application/movie";
-                pExtension = ".MOV";
-                break;
-            default:
+        case GfxLinkType::NativeJpg:
+            sMediaType = u"image/jpeg"_ustr;
+            aExtension = u"jpeg"_ustr;
+            break;
+        case GfxLinkType::NativePng:
+            sMediaType = u"image/png"_ustr;
+            aExtension = u"png"_ustr;
+            break;
+        case GfxLinkType::NativeTif:
+            sMediaType = u"image/tiff"_ustr;
+            aExtension = u"tif"_ustr;
+            break;
+        case GfxLinkType::NativeWmf:
+            sMediaType = u"image/x-wmf"_ustr;
+            aExtension = u"wmf"_ustr;
+            break;
+        case GfxLinkType::NativeMet:
+            sMediaType = u"image/x-met"_ustr;
+            aExtension = u"met"_ustr;
+            break;
+        case GfxLinkType::NativePct:
+            sMediaType = u"image/x-pict"_ustr;
+            aExtension = u"pct"_ustr;
+            break;
+        case GfxLinkType::NativeMov:
+            sMediaType = u"application/movie"_ustr;
+            aExtension = u"MOV"_ustr;
+            break;
+        default:
+        {
+            GraphicType aType = rGraphic.GetType();
+            if (aType == GraphicType::Bitmap || aType == 
GraphicType::GdiMetafile)
             {
-                GraphicType aType = rGraphic.GetType();
-                if (aType == GraphicType::Bitmap || aType == 
GraphicType::GdiMetafile)
+                if (aType == GraphicType::Bitmap)
                 {
-                    if (aType == GraphicType::Bitmap)
-                    {
-                        (void)GraphicConverter::Export(aStream, rGraphic, 
ConvertDataFormat::PNG);
-                        sMediaType = "image/png";
-                        pExtension = ".png";
-                    }
-                    else
-                    {
-                        (void)GraphicConverter::Export(aStream, rGraphic, 
ConvertDataFormat::EMF);
-                        sMediaType = "image/x-emf";
-                        pExtension = ".emf";
-                    }
+                    (void)GraphicConverter::Export(aStream, rGraphic, 
ConvertDataFormat::PNG);
+                    sMediaType = u"image/png"_ustr;
+                    aExtension = u"png"_ustr;
                 }
                 else
                 {
-                    SAL_WARN("oox.shape", "unhandled graphic type " << 
static_cast<int>(aType));
-                    /*Earlier, even in case of unhandled graphic types we were
-                      proceeding to write the image, which would eventually
-                      write an empty image with a zero size, and return a valid
-                      relationID, which is incorrect.
-                      */
-                    return sRelId;
+                    (void)GraphicConverter::Export(aStream, rGraphic, 
ConvertDataFormat::EMF);
+                    sMediaType = u"image/x-emf"_ustr;
+                    aExtension = u"emf"_ustr;
                 }
-
-                aData = aStream.GetData();
-                nDataSize = aStream.GetEndOfData();
-                break;
             }
+            else
+            {
+                SAL_WARN("oox.shape", "unhandled graphic type " << 
static_cast<int>(aType));
+
+                /*Earlier, even in case of unhandled graphic types we were
+                  proceeding to write the image, which would eventually
+                  write an empty image with a zero size, and return a valid
+                  relationID, which is incorrect.
+                  */
+                return OUString();
+            }
+
+            aData = aStream.GetData();
+            nDataSize = aStream.GetEndOfData();
         }
+        break;
+    }
 
-        sal_Int32 nImageCount = rGraphicExportCache.nextImageCount();
-        Reference<XOutputStream> xOutStream = mpFilterBase->openFragmentStream(
-            OUStringBuffer()
-                .appendAscii(getComponentDir(meDocumentType))
-                .append("/media/image" + OUString::number(nImageCount))
-                .appendAscii(pExtension)
-                .makeStringAndClear(),
-            sMediaType);
-        xOutStream->writeBytes(Sequence<sal_Int8>(static_cast<const 
sal_Int8*>(aData), nDataSize));
-        xOutStream->closeOutput();
+    GraphicExportCache& rGraphicExportCache = GraphicExportCache::get();
+    auto sImageCountString = 
OUString::number(rGraphicExportCache.nextImageCount());
 
-        const char* sRelationCompPrefix;
-        if (bRelPathToMedia)
-            sRelationCompPrefix = "../";
-        else
-            sRelationCompPrefix = getRelationCompPrefix(meDocumentType);
-        sPath = OUStringBuffer()
-                    .appendAscii(sRelationCompPrefix)
-                    .append("media/image" + OUString::number(nImageCount))
-                    .appendAscii(pExtension)
-                    .makeStringAndClear();
+    OUString sComponentDir(getComponentDir(meDocumentType));
+
+    OUString sImagePath = sComponentDir + u"/media/image"_ustr + 
sImageCountString + u"."_ustr + aExtension;
+
+    Reference<XOutputStream> xOutStream = 
mpFilterBase->openFragmentStream(sImagePath, sMediaType);
+    xOutStream->writeBytes(Sequence<sal_Int8>(static_cast<const 
sal_Int8*>(aData), nDataSize));
+    xOutStream->closeOutput();
 
-        rGraphicExportCache.addExportGraphics(aChecksum, sPath);
+    OUString sRelationCompPrefix;
+    if (bRelPathToMedia)
+        sRelationCompPrefix = u"../"_ustr;
+    else
+        sRelationCompPrefix = getRelationCompPrefix(meDocumentType);
+
+    OUString sPath = sRelationCompPrefix + u"media/image"_ustr + 
sImageCountString + u"."_ustr + aExtension;
+
+    rGraphicExportCache.addExportGraphics(rGraphic.GetChecksum(), sPath);
+
+    return sPath;
+}
+
+OUString GraphicExport::writeToStorage(const Graphic& rGraphic , bool 
bRelPathToMedia)
+{
+    OUString sPath;
+
+    GraphicExportCache& rGraphicExportCache = GraphicExportCache::get();
+    sPath = rGraphicExportCache.findExportGraphics(rGraphic.GetChecksum());
+
+    if (sPath.isEmpty())
+    {
+        sPath = writeNewEntryToStorage(rGraphic, bRelPathToMedia);
+
+        if (sPath.isEmpty())
+            return OUString(); // couldn't store - just return empty string
     }
 
-    sRelId = mpFilterBase->addRelation( mpFS->getOutputStream(),
-                                oox::getRelationship(Relationship::IMAGE),
-                                sPath );
+    OUString sRelId = mpFilterBase->addRelation(mpFS->getOutputStream(), 
oox::getRelationship(Relationship::IMAGE), sPath);
 
     return sRelId;
 }
@@ -1606,10 +1607,7 @@ void DrawingML::WriteMediaNonVisualProperties(const 
css::uno::Reference<css::dra
     {
         sal_Int32  nImageCount = GraphicExportCache::get().nextImageCount();
 
-        OUString sFileName = OUStringBuffer()
-            .appendAscii(GetComponentDir())
-            .append("/media/media" + OUString::number(nImageCount) + 
aExtension)
-            .makeStringAndClear();
+        OUString sFileName = GetComponentDir() + u"/media/media"_ustr + 
OUString::number(nImageCount) + aExtension;
 
         // copy the video stream
         Reference<XOutputStream> xOutStream = 
mpFB->openFragmentStream(sFileName, aMimeType);
@@ -1620,9 +1618,8 @@ void DrawingML::WriteMediaNonVisualProperties(const 
css::uno::Reference<css::dra
         xOutStream->closeOutput();
 
         // create the relation
-        OUString aPath = OUStringBuffer().appendAscii(GetRelationCompPrefix())
-                                         .append("media/media" + 
OUString::number(nImageCount) + aExtension)
-                                         .makeStringAndClear();
+        OUString aPath = GetRelationCompPrefix() + u"media/media"_ustr + 
OUString::number(nImageCount) + aExtension;
+
         aVideoFileRelId = mpFB->addRelation(mpFS->getOutputStream(), 
oox::getRelationship(eMediaType), aPath);
         aMediaRelId = mpFB->addRelation(mpFS->getOutputStream(), 
oox::getRelationship(Relationship::MEDIA), aPath);
     }
@@ -6142,17 +6139,15 @@ OString DrawingML::WriteWdpPicture( const OUString& 
rFileId, const Sequence< sal
         return OUStringToOString(aId, RTL_TEXTENCODING_UTF8);
 
     sal_Int32 nWdpImageCount = rGraphicExportCache.nextWdpImageCount();
-    OUString sFileName = "media/hdphoto" + OUString::number(nWdpImageCount) + 
".wdp";
-    OUString sFragment = 
OUStringBuffer().appendAscii(GetComponentDir()).append( "/" + 
sFileName).makeStringAndClear();
+    OUString sFileName = u"media/hdphoto"_ustr + 
OUString::number(nWdpImageCount) + u".wdp"_ustr;
+    OUString sFragment = GetComponentDir() + u"/"_ustr + sFileName;
     Reference< XOutputStream > xOutStream = 
mpFB->openFragmentStream(sFragment, "image/vnd.ms-photo");
     xOutStream->writeBytes( rPictureData );
     xOutStream->closeOutput();
 
-    aId = mpFB->addRelation( mpFS->getOutputStream(),
-                             oox::getRelationship(Relationship::HDPHOTO),
-                             OUStringBuffer()
-                             .appendAscii( GetRelationCompPrefix() )
-                             .append( sFileName ) );
+    aId = mpFB->addRelation(mpFS->getOutputStream(),
+                            oox::getRelationship(Relationship::HDPHOTO),
+                            Concat2View(GetRelationCompPrefix() + sFileName));
 
     rGraphicExportCache.addToWdpCache(rFileId, aId);
 
@@ -6256,7 +6251,7 @@ void DrawingML::WriteDiagram(const 
css::uno::Reference<css::drawing::XShape>& rX
     mpFS->startElementNS(XML_a, XML_graphicData, XML_uri,
                          
"http://schemas.openxmlformats.org/drawingml/2006/diagram";);
 
-    OUString sRelationCompPrefix = 
OUString::createFromAscii(GetRelationCompPrefix());
+    OUString sRelationCompPrefix = GetRelationCompPrefix();
 
     // add data relation
     OUString dataFileName = "diagrams/data" + OUString::number(nDiagramId) + 
".xml";
@@ -6322,7 +6317,7 @@ void DrawingML::WriteDiagram(const 
css::uno::Reference<css::drawing::XShape>& rX
     uno::Reference<xml::sax::XWriter> writer
         = xml::sax::Writer::create(comphelper::getProcessComponentContext());
 
-    OUString sDir = OUString::createFromAscii(GetComponentDir());
+    OUString sDir = GetComponentDir();
 
     // write data file
     serializer.set(dataDom, uno::UNO_QUERY);
@@ -6422,7 +6417,7 @@ void DrawingML::writeDiagramRels(const 
uno::Sequence<uno::Sequence<uno::Any>>& x
 
         mpFB->addRelation(xOutStream, sType, Concat2View("../" + sFragment));
 
-        OUString sDir = OUString::createFromAscii(GetComponentDir());
+        OUString sDir = GetComponentDir();
         uno::Reference<io::XOutputStream> xBinOutStream
             = mpFB->openFragmentStream(sDir + "/" + sFragment, sContentType);
 
diff --git a/oox/source/export/shapes.cxx b/oox/source/export/shapes.cxx
index 87f2cfb7277b..5997728e316b 100644
--- a/oox/source/export/shapes.cxx
+++ b/oox/source/export/shapes.cxx
@@ -2758,10 +2758,10 @@ ShapeExport& ShapeExport::WriteOLE2Shape( const 
Reference< XShape >& xShape )
         assert(!sRelationType.isEmpty());
         assert(!sSuffix.isEmpty());
 
-        OUString sFileName
-            = "embeddings/oleObject" + OUString::number(++m_nEmbeddedObjects) 
+ "." + sSuffix;
-        uno::Reference<io::XOutputStream> const 
xOutStream(mpFB->openFragmentStream(
-            OUString::createFromAscii(GetComponentDir()) + "/" + sFileName, 
sMediaType));
+        OUString sNumber = OUString::number(++m_nEmbeddedObjects);
+        OUString sFileName = u"embeddings/oleObject"_ustr + sNumber + 
u"."_ustr + sSuffix;
+        OUString sFilePath = GetComponentDir() + u"/"_ustr + sFileName;
+        uno::Reference<io::XOutputStream> const 
xOutStream(mpFB->openFragmentStream(sFilePath, sMediaType));
         assert(xOutStream.is()); // no reason why that could fail
 
         try
@@ -2775,7 +2775,7 @@ ShapeExport& ShapeExport::WriteOLE2Shape( const 
Reference< XShape >& xShape )
 
         sRelId = mpFB->addRelation(
             mpFS->getOutputStream(), sRelationType,
-            Concat2View(OUString::createFromAscii(GetRelationCompPrefix()) + 
sFileName));
+            Concat2View(GetRelationCompPrefix() + sFileName));
     }
 
     sal_Int64 nAspect;

Reply via email to