Kaydet (Commit) 791431d7 authored tarafından Michael Stahl's avatar Michael Stahl

tdf#103567 xmloff: ODF import: fix loss of events on SVG multi-image

For SVG there are 2 draw:image children in the draw:frame, and the
SdXMLEventContext::EndElement() applies the content of
office:event-listeners to the shape created from the last draw:image
and then MultiImageImportHelper::solveMultipleImages() throws
it away because it's the bitmap fallback of the SVG.

Avoid that problem by calling solveMultipleImages earlier:
The ODF schema ensures that all the draw:image elements occur before
the optional property-bearing child elements of draw:frame,
so we just call solveMultipleImages on the first such optional
element, so that all subsequent properties get applied to the one
surviving shape.

(likely regression from 44cfc7cb)

Change-Id: I2be5f6f424dbfd90ca2179ce6f9057929540e762
üst 725c8161
...@@ -42,6 +42,8 @@ ...@@ -42,6 +42,8 @@
#include <sax/tools/converter.hxx> #include <sax/tools/converter.hxx>
#include <com/sun/star/document/XDocumentPropertiesSupplier.hpp> #include <com/sun/star/document/XDocumentPropertiesSupplier.hpp>
#include <com/sun/star/document/XEventsSupplier.hpp>
#include <com/sun/star/presentation/ClickAction.hpp>
#include <com/sun/star/drawing/GraphicExportFilter.hpp> #include <com/sun/star/drawing/GraphicExportFilter.hpp>
#include <com/sun/star/drawing/XDrawPage.hpp> #include <com/sun/star/drawing/XDrawPage.hpp>
#include <com/sun/star/drawing/XDrawPagesSupplier.hpp> #include <com/sun/star/drawing/XDrawPagesSupplier.hpp>
...@@ -67,6 +69,7 @@ ...@@ -67,6 +69,7 @@
#include <stlpool.hxx> #include <stlpool.hxx>
#include <comphelper/processfactory.hxx> #include <comphelper/processfactory.hxx>
#include <comphelper/sequenceashashmap.hxx>
#include <vcl/pngread.hxx> #include <vcl/pngread.hxx>
#include <vcl/bitmapaccess.hxx> #include <vcl/bitmapaccess.hxx>
#include <vcl/dibtools.hxx> #include <vcl/dibtools.hxx>
...@@ -129,6 +132,7 @@ public: ...@@ -129,6 +132,7 @@ public:
void testTdf99030(); void testTdf99030();
void testTdf49561(); void testTdf49561();
void testTdf103473(); void testTdf103473();
void testTdf103567();
void testTdf103792(); void testTdf103792();
void testTdf103876(); void testTdf103876();
void testTdf104015(); void testTdf104015();
...@@ -192,6 +196,7 @@ public: ...@@ -192,6 +196,7 @@ public:
CPPUNIT_TEST(testTdf99030); CPPUNIT_TEST(testTdf99030);
CPPUNIT_TEST(testTdf49561); CPPUNIT_TEST(testTdf49561);
CPPUNIT_TEST(testTdf103473); CPPUNIT_TEST(testTdf103473);
CPPUNIT_TEST(testTdf103567);
CPPUNIT_TEST(testTdf103792); CPPUNIT_TEST(testTdf103792);
CPPUNIT_TEST(testTdf103876); CPPUNIT_TEST(testTdf103876);
CPPUNIT_TEST(testTdf104015); CPPUNIT_TEST(testTdf104015);
...@@ -1526,6 +1531,48 @@ void SdImportTest::testTdf103473() ...@@ -1526,6 +1531,48 @@ void SdImportTest::testTdf103473()
xDocShRef->DoClose(); xDocShRef->DoClose();
} }
void SdImportTest::testTdf103567()
{
sd::DrawDocShellRef xDocShRef = loadURL(m_directories.getURLFromSrc("/sd/qa/unit/data/odp/tdf103567.odp"), ODP);
for (int i = 0; i < 4; ++i)
{
uno::Reference<beans::XPropertySet> const xShape(getShapeFromPage(i, 0, xDocShRef));
uno::Reference<document::XEventsSupplier> const xEventsSupplier(xShape, uno::UNO_QUERY);
uno::Reference<container::XNameAccess> const xEvents(xEventsSupplier->getEvents());
OString const msg("shape " + OString::number(i) + ": ");
CPPUNIT_ASSERT(xEvents->hasByName("OnClick"));
uno::Sequence<beans::PropertyValue> props;
xEvents->getByName("OnClick") >>= props;
comphelper::SequenceAsHashMap const map(props);
{
auto iter(map.find("EventType"));
CPPUNIT_ASSERT_MESSAGE(OString(msg + "no EventType").getStr(), iter != map.end());
CPPUNIT_ASSERT_EQUAL_MESSAGE(msg.getStr(), OUString("Presentation"), iter->second.get<OUString>());
}
{
auto iter(map.find("ClickAction"));
CPPUNIT_ASSERT_MESSAGE(OString(msg + "no ClickAction").getStr(), iter != map.end());
if (i % 2 == 0)
{
CPPUNIT_ASSERT_EQUAL_MESSAGE(msg.getStr(), css::presentation::ClickAction_DOCUMENT, iter->second.get<css::presentation::ClickAction>());
}
else
{
CPPUNIT_ASSERT_EQUAL_MESSAGE(msg.getStr(), css::presentation::ClickAction_NEXTPAGE, iter->second.get<css::presentation::ClickAction>());
}
}
if (i % 2 == 0)
{
auto iter(map.find("Bookmark"));
CPPUNIT_ASSERT_MESSAGE(OString(msg + "no Bookmark").getStr(), iter != map.end());
CPPUNIT_ASSERT_EQUAL_MESSAGE(msg.getStr(), OUString("http://example.com/"), iter->second.get<OUString>());
}
}
xDocShRef->DoClose();
}
void SdImportTest::testTdf103792() void SdImportTest::testTdf103792()
{ {
// Title text shape on the actual slide contained no text neither a placeholder text. // Title text shape on the actual slide contained no text neither a placeholder text.
......
...@@ -129,6 +129,9 @@ SvXMLImportContextRef MultiImageImportHelper::solveMultipleImages() ...@@ -129,6 +129,9 @@ SvXMLImportContextRef MultiImageImportHelper::solveMultipleImages()
removeGraphicFromImportContext(rCandidate); removeGraphicFromImportContext(rCandidate);
} }
// re-insert it so that solveMultipleImages is idempotent
maImplContextVector.clear();
maImplContextVector.push_back(pContext);
} }
else if (maImplContextVector.size() == 1) else if (maImplContextVector.size() == 1)
{ {
......
...@@ -3558,12 +3558,22 @@ SvXMLImportContext *SdXMLFrameShapeContext::CreateChildContext( sal_uInt16 nPref ...@@ -3558,12 +3558,22 @@ SvXMLImportContext *SdXMLFrameShapeContext::CreateChildContext( sal_uInt16 nPref
(nPrefix == XML_NAMESPACE_DRAW && (IsXMLToken( rLocalName, XML_GLUE_POINT ) || (nPrefix == XML_NAMESPACE_DRAW && (IsXMLToken( rLocalName, XML_GLUE_POINT ) ||
IsXMLToken( rLocalName, XML_THUMBNAIL ) ) ) ) IsXMLToken( rLocalName, XML_THUMBNAIL ) ) ) )
{ {
if (getSupportsMultipleContents())
{ // tdf#103567 ensure props are set on surviving shape
// note: no more draw:image can be added once we get here
mxImplContext = solveMultipleImages();
}
SvXMLImportContext *pImplContext = mxImplContext.get(); SvXMLImportContext *pImplContext = mxImplContext.get();
pContext = dynamic_cast<SdXMLShapeContext&>(*pImplContext).CreateChildContext( nPrefix, pContext = dynamic_cast<SdXMLShapeContext&>(*pImplContext).CreateChildContext( nPrefix,
rLocalName, xAttrList ); rLocalName, xAttrList );
} }
else if ( (XML_NAMESPACE_DRAW == nPrefix) && IsXMLToken( rLocalName, XML_IMAGE_MAP ) ) else if ( (XML_NAMESPACE_DRAW == nPrefix) && IsXMLToken( rLocalName, XML_IMAGE_MAP ) )
{ {
if (getSupportsMultipleContents())
{ // tdf#103567 ensure props are set on surviving shape
// note: no more draw:image can be added once we get here
mxImplContext = solveMultipleImages();
}
SdXMLShapeContext *pSContext = dynamic_cast< SdXMLShapeContext* >( mxImplContext.get() ); SdXMLShapeContext *pSContext = dynamic_cast< SdXMLShapeContext* >( mxImplContext.get() );
if( pSContext ) if( pSContext )
{ {
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment