summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorTünde Tóth <toth.tunde@nisz.hu>2022-04-04 11:49:59 +0200
committerLászló Németh <nemeth@numbertext.org>2022-04-26 18:07:40 +0200
commitcf2dc247ff5f726238856e9b46a4926a30430e14 (patch)
tree8c319026977124ce3c6bbd1fdef418d09149325d
parent2fbf0f418ccb25010add33449d4e42b8b3f7fd0b (diff)
DOCX export: image deduplication and clean up
Follow-up to commit aea8043bc5f5187498fa450505d6de9d6986e2a6 "tdf#74670 tdf#91286 PPTX XLSX export: save image once". This reverts commit 797fef38612fb2fd62d1f6591619b9361e526bca "tdf#118535 DOCX export: save header image once" and commit 32ada80a9f47b095d7b0c4d16e3422f6ef7f2ac2 "DOCX export: make sure a graphic is only written once" and commit b484e9814c66d8d51cea974390963a6944bc9d73 "tdf#83227 oox: reuse RelId in DML/VML export for the same graphic". Change-Id: I2d90249808174290b6b3e4eb957b3ac87ad41f95 Reviewed-on: https://gerrit.libreoffice.org/c/core/+/132506 Tested-by: László Németh <nemeth@numbertext.org> Reviewed-by: László Németh <nemeth@numbertext.org>
-rw-r--r--include/oox/export/drawingml.hxx8
-rw-r--r--include/oox/export/vmlexport.hxx4
-rw-r--r--oox/source/export/drawingml.cxx35
-rw-r--r--oox/source/export/vmlexport.cxx20
-rw-r--r--sw/source/filter/ww8/docxattributeoutput.cxx87
-rw-r--r--sw/source/filter/ww8/docxattributeoutput.hxx13
-rw-r--r--sw/source/filter/ww8/docxexport.cxx2
7 files changed, 13 insertions, 156 deletions
diff --git a/include/oox/export/drawingml.hxx b/include/oox/export/drawingml.hxx
index 9a7f744520c8..43aba83b6531 100644
--- a/include/oox/export/drawingml.hxx
+++ b/include/oox/export/drawingml.hxx
@@ -130,12 +130,6 @@ public:
virtual void WriteOutliner(const OutlinerParaObject& rParaObj) = 0;
/// Write the contents of the textbox that is associated to this shape.
virtual void WriteTextBox(css::uno::Reference<css::drawing::XShape> xShape) = 0;
- /// Look up the RelId of a graphic based on its checksum.
- virtual OUString FindRelId(BitmapChecksum nChecksum) = 0;
- /// Look up the filename of a graphic based on its checksum.
- virtual OUString FindFileName(BitmapChecksum nChecksum) = 0;
- /// Store the RelId and filename of a graphic based on its checksum.
- virtual void CacheRelId(BitmapChecksum nChecksum, const OUString& rRelId, const OUString& rFileName) = 0;
/// Get textbox which belongs to the shape.
virtual css::uno::Reference<css::text::XTextFrame> GetUnoTextFrame(
css::uno::Reference<css::drawing::XShape> xShape) = 0;
@@ -224,7 +218,7 @@ public:
void SetBackgroundDark(bool bIsDark) { mbIsBackgroundDark = bIsDark; }
/// If bRelPathToMedia is true add "../" to image folder path while adding the image relationship
- OUString WriteImage( const Graphic &rGraphic , bool bRelPathToMedia = false, OUString* pFileName = nullptr );
+ OUString WriteImage( 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/include/oox/export/vmlexport.hxx b/include/oox/export/vmlexport.hxx
index 5efdb34a90ff..fa54f27aa250 100644
--- a/include/oox/export/vmlexport.hxx
+++ b/include/oox/export/vmlexport.hxx
@@ -65,10 +65,6 @@ public:
virtual oox::drawingml::DrawingML& GetDrawingML() = 0;
/// Write the contents of the textbox that is associated to this shape in VML format.
virtual void WriteVMLTextBox(css::uno::Reference<css::drawing::XShape> xShape) = 0;
- /// Look up the RelId of a graphic based on its checksum.
- virtual OUString FindRelId(BitmapChecksum nChecksum) = 0;
- /// Store the RelId and filename of a graphic based on its checksum.
- virtual void CacheRelId(BitmapChecksum nChecksum, const OUString& rRelId, const OUString& rFileName) = 0;
protected:
VMLTextExport() {}
virtual ~VMLTextExport() {}
diff --git a/oox/source/export/drawingml.cxx b/oox/source/export/drawingml.cxx
index 78eac3d00f60..87ca05452513 100644
--- a/oox/source/export/drawingml.cxx
+++ b/oox/source/export/drawingml.cxx
@@ -1271,7 +1271,7 @@ const char* DrawingML::GetRelationCompPrefix() const
return "unknown";
}
-OUString DrawingML::WriteImage( const Graphic& rGraphic , bool bRelPathToMedia, OUString* pFileName )
+OUString DrawingML::WriteImage( const Graphic& rGraphic , bool bRelPathToMedia )
{
GfxLink aLink = rGraphic.GetGfxLink ();
BitmapChecksum aChecksum = rGraphic.GetChecksum();
@@ -1280,8 +1280,8 @@ OUString DrawingML::WriteImage( const Graphic& rGraphic , bool bRelPathToMedia,
OUString sRelId;
OUString sPath;
- // tdf#74670 tdf#91286 Save image only once (this is no problem for DOCX)
- if (GetDocumentType() != DOCUMENT_DOCX && !maExportGraphics.empty())
+ // tdf#74670 tdf#91286 Save image only once
+ if (!maExportGraphics.empty())
{
auto aIterator = maExportGraphics.top().find(aChecksum);
if (aIterator != maExportGraphics.top().end())
@@ -1394,7 +1394,7 @@ OUString DrawingML::WriteImage( const Graphic& rGraphic , bool bRelPathToMedia,
.appendAscii(pExtension)
.makeStringAndClear();
- if (GetDocumentType() != DOCUMENT_DOCX && !maExportGraphics.empty())
+ if (!maExportGraphics.empty())
maExportGraphics.top()[aChecksum] = sPath;
}
@@ -1402,8 +1402,6 @@ OUString DrawingML::WriteImage( const Graphic& rGraphic , bool bRelPathToMedia,
oox::getRelationship(Relationship::IMAGE),
sPath );
- if (pFileName)
- *pFileName = sPath;
return sRelId;
}
@@ -1566,35 +1564,12 @@ OUString DrawingML::WriteXGraphicBlip(uno::Reference<beans::XPropertySet> const
bool bRelPathToMedia)
{
OUString sRelId;
- OUString sFileName;
if (!rxGraphic.is())
return sRelId;
Graphic aGraphic(rxGraphic);
- if (mpTextExport)
- {
- BitmapChecksum nChecksum = aGraphic.GetChecksum();
- sRelId = mpTextExport->FindRelId(nChecksum);
- sFileName = mpTextExport->FindFileName(nChecksum);
- }
- if (sRelId.isEmpty())
- {
- sRelId = WriteImage(aGraphic, bRelPathToMedia, &sFileName);
- if (mpTextExport)
- {
- BitmapChecksum nChecksum = aGraphic.GetChecksum();
- mpTextExport->CacheRelId(nChecksum, sRelId, sFileName);
- }
- }
- else
- {
- // Include the same relation again. This makes it possible to
- // reuse an image across different headers.
- sRelId = mpFB->addRelation( mpFS->getOutputStream(),
- oox::getRelationship(Relationship::IMAGE),
- sFileName );
- }
+ sRelId = WriteImage(aGraphic, bRelPathToMedia);
mpFS->startElementNS(XML_a, XML_blip, FSNS(XML_r, XML_embed), sRelId);
diff --git a/oox/source/export/vmlexport.cxx b/oox/source/export/vmlexport.cxx
index 544a5599c932..32f60ff65c9a 100644
--- a/oox/source/export/vmlexport.cxx
+++ b/oox/source/export/vmlexport.cxx
@@ -718,15 +718,7 @@ void VMLExport::Commit( EscherPropertyContainer& rProps, const tools::Rectangle&
const uno::Reference<graphic::XGraphic>& xGraphic
= pSdrGrafObj->getSignatureLineUnsignedGraphic();
Graphic aGraphic(xGraphic);
-
- BitmapChecksum nChecksum = aGraphic.GetChecksum();
- OUString aImageId = m_pTextExport->FindRelId(nChecksum);
- if (aImageId.isEmpty())
- {
- OUString aFileName;
- aImageId = m_pTextExport->GetDrawingML().WriteImage(aGraphic, false, &aFileName);
- m_pTextExport->CacheRelId(nChecksum, aImageId, aFileName);
- }
+ OUString aImageId = m_pTextExport->GetDrawingML().WriteImage(aGraphic, false);
pAttrList->add(FSNS(XML_r, XML_id), aImageId);
imageData = true;
}
@@ -740,15 +732,7 @@ void VMLExport::Commit( EscherPropertyContainer& rProps, const tools::Rectangle&
aStream.Seek(0);
Graphic aGraphic;
GraphicConverter::Import(aStream, aGraphic);
-
- BitmapChecksum nChecksum = aGraphic.GetChecksum();
- OUString aImageId = m_pTextExport->FindRelId(nChecksum);
- if (aImageId.isEmpty())
- {
- OUString aFileName;
- aImageId = m_pTextExport->GetDrawingML().WriteImage(aGraphic, false, &aFileName);
- m_pTextExport->CacheRelId(nChecksum, aImageId, aFileName);
- }
+ OUString aImageId = m_pTextExport->GetDrawingML().WriteImage(aGraphic, false);
pAttrList->add(FSNS(XML_r, XML_id), aImageId);
imageData = true;
}
diff --git a/sw/source/filter/ww8/docxattributeoutput.cxx b/sw/source/filter/ww8/docxattributeoutput.cxx
index ca52bace2012..9a554b9d4a5c 100644
--- a/sw/source/filter/ww8/docxattributeoutput.cxx
+++ b/sw/source/filter/ww8/docxattributeoutput.cxx
@@ -5360,67 +5360,12 @@ void DocxAttributeOutput::WriteSrcRect(
XML_b, OString::number(bottom) );
}
-void DocxAttributeOutput::PushRelIdCache()
-{
- m_aRelIdCache.emplace();
- m_aSdrRelIdCache.emplace();
-}
-
-OUString DocxAttributeOutput::FindRelId(BitmapChecksum nChecksum)
-{
- OUString aRet;
-
- if (!m_aSdrRelIdCache.empty() && m_aSdrRelIdCache.top().find(nChecksum) != m_aSdrRelIdCache.top().end())
- aRet = m_aSdrRelIdCache.top()[nChecksum].first;
-
- return aRet;
-}
-
-OUString DocxAttributeOutput::FindFileName(BitmapChecksum nChecksum)
-{
- OUString aRet;
-
- if (!m_aSdrRelIdCache.empty() && m_aSdrRelIdCache.top().find(nChecksum) != m_aSdrRelIdCache.top().end())
- aRet = m_aSdrRelIdCache.top()[nChecksum].second;
-
- return aRet;
-}
-
-void DocxAttributeOutput::CacheRelId(BitmapChecksum nChecksum, const OUString& rRelId, const OUString& rFileName)
-{
- if (!m_aSdrRelIdCache.empty())
- m_aSdrRelIdCache.top()[nChecksum] = std::pair(rRelId, rFileName);
-}
-
uno::Reference<css::text::XTextFrame> DocxAttributeOutput::GetUnoTextFrame(
css::uno::Reference<css::drawing::XShape> xShape)
{
return SwTextBoxHelper::getUnoTextFrame(xShape);
}
-std::pair<OString, OUString> DocxAttributeOutput::getExistingGraphicRelId(BitmapChecksum nChecksum)
-{
- std::pair<OString, OUString> aResult;
-
- if (m_aRelIdCache.empty())
- return aResult;
-
- auto pIterator = m_aRelIdCache.top().find(nChecksum);
-
- if (pIterator != m_aRelIdCache.top().end())
- {
- aResult = pIterator->second;
- }
-
- return aResult;
-}
-
-void DocxAttributeOutput::cacheGraphicRelId(BitmapChecksum nChecksum, OString const & rRelId, OUString const & rFileName)
-{
- if (!m_aRelIdCache.empty())
- m_aRelIdCache.top().emplace(nChecksum, std::pair(rRelId, rFileName));
-}
-
void DocxAttributeOutput::FlyFrameGraphic( const SwGrfNode* pGrfNode, const Size& rSize, const SwFlyFrameFormat* pOLEFrameFormat, SwOLENode* pOLENode, const SdrObject* pSdrObj )
{
SAL_INFO("sw.ww8", "TODO DocxAttributeOutput::FlyFrameGraphic( const SwGrfNode* pGrfNode, const Size& rSize, const SwFlyFrameFormat* pOLEFrameFormat, SwOLENode* pOLENode, const SdrObject* pSdrObj ) - some stuff still missing" );
@@ -5466,31 +5411,9 @@ void DocxAttributeOutput::FlyFrameGraphic( const SwGrfNode* pGrfNode, const Size
else
aGraphic = *pOLENode->GetGraphic();
- BitmapChecksum aChecksum = aGraphic.GetChecksum();
- OUString aFileName;
- std::tie(aRelId, aFileName) = getExistingGraphicRelId(aChecksum);
- OUString aImageId;
-
- if (aRelId.isEmpty())
- {
- // Not in cache, then need to write it.
- m_rDrawingML.SetFS( m_pSerializer ); // to be sure that we write to the right stream
-
- aImageId = m_rDrawingML.WriteImage(aGraphic, false, &aFileName);
-
- aRelId = OUStringToOString( aImageId, RTL_TEXTENCODING_UTF8 );
- cacheGraphicRelId(aChecksum, aRelId, aFileName);
- }
- else
- {
- // Include the same relation again. This makes it possible to
- // reuse an image across different headers.
- aImageId = m_rDrawingML.GetFB()->addRelation( m_pSerializer->getOutputStream(),
- oox::getRelationship(Relationship::IMAGE),
- aFileName );
-
- aRelId = OUStringToOString( aImageId, RTL_TEXTENCODING_UTF8 );
- }
+ m_rDrawingML.SetFS(m_pSerializer); // to be sure that we write to the right stream
+ OUString aImageId = m_rDrawingML.WriteImage(aGraphic, false);
+ aRelId = OUStringToOString(aImageId, RTL_TEXTENCODING_UTF8);
nImageType = XML_embed;
}
@@ -10396,10 +10319,6 @@ DocxAttributeOutput::DocxAttributeOutput( DocxExport &rExport, const FSHelperPtr
m_nParaAfterSpacing(0)
, m_nStateOfFlyFrame( FLY_NOT_PROCESSED )
{
- // Push initial items to the RelId cache. In case the document contains no
- // special streams (headers, footers, etc.) then these items are used
- // during the full export.
- PushRelIdCache();
}
DocxAttributeOutput::~DocxAttributeOutput()
diff --git a/sw/source/filter/ww8/docxattributeoutput.hxx b/sw/source/filter/ww8/docxattributeoutput.hxx
index 2c847e0e5320..33168b872b11 100644
--- a/sw/source/filter/ww8/docxattributeoutput.hxx
+++ b/sw/source/filter/ww8/docxattributeoutput.hxx
@@ -399,7 +399,6 @@ public:
void WriteBookmarks_Impl( std::vector< OUString >& rStarts, std::vector< OUString >& rEnds, const SwRedlineData* pRedlineData = nullptr );
void WriteFinalBookmarks_Impl( std::vector< OUString >& rStarts, std::vector< OUString >& rEnds );
void WriteAnnotationMarks_Impl( std::vector< OUString >& rStarts, std::vector< OUString >& rEnds );
- void PushRelIdCache();
/// End possibly opened paragraph sdt block.
void EndParaSdtBlock();
@@ -1019,15 +1018,6 @@ private:
// store hardcoded value which was set during import.
sal_Int32 m_nParaBeforeSpacing,m_nParaAfterSpacing;
- std::pair<OString, OUString> getExistingGraphicRelId(BitmapChecksum aChecksum);
- void cacheGraphicRelId(BitmapChecksum nChecksum, OString const & rRelId, OUString const & rFileName);
-
- /// RelId <-> Graphic* cache, so that in case of alternate content, the same graphic only gets written once.
- std::stack< std::map<BitmapChecksum, std::pair<OString, OUString>> > m_aRelIdCache;
-
- /// RelId <-> BitmapChecksum cache, similar to m_aRelIdCache, but used for non-Writer graphics, handled in oox.
- std::stack< std::map<BitmapChecksum, std::pair<OUString, OUString>> > m_aSdrRelIdCache;
-
SdtBlockHelper m_aParagraphSdt;
SdtBlockHelper m_aRunSdt;
@@ -1078,9 +1068,6 @@ public:
virtual void WriteVMLTextBox(css::uno::Reference<css::drawing::XShape> xShape) override;
/// DMLTextExport
virtual void WriteTextBox(css::uno::Reference<css::drawing::XShape> xShape) override;
- virtual OUString FindRelId(BitmapChecksum nChecksum) override;
- virtual OUString FindFileName(BitmapChecksum nChecksum) override;
- virtual void CacheRelId(BitmapChecksum nChecksum, const OUString& rRelId, const OUString& rFileName) override;
virtual css::uno::Reference<css::text::XTextFrame> GetUnoTextFrame(
css::uno::Reference<css::drawing::XShape> xShape) override;
virtual oox::drawingml::DrawingML& GetDrawingML() override;
diff --git a/sw/source/filter/ww8/docxexport.cxx b/sw/source/filter/ww8/docxexport.cxx
index 51534eda5e7c..7c30e25e4f55 100644
--- a/sw/source/filter/ww8/docxexport.cxx
+++ b/sw/source/filter/ww8/docxexport.cxx
@@ -526,6 +526,7 @@ ErrCode DocxExport::ExportDocument_Impl()
// Make sure images are counted from one, even when exporting multiple documents.
oox::drawingml::DrawingML::ResetCounters();
+ oox::drawingml::DrawingML::PushExportGraphics();
WriteMainText();
@@ -552,6 +553,7 @@ ErrCode DocxExport::ExportDocument_Impl()
m_aLinkedTextboxesHelper.clear(); //final cleanup
m_pStyles.reset();
m_pSections.reset();
+ oox::drawingml::DrawingML::PopExportGraphics();
return ERRCODE_NONE;
}