avmedia: implement video crop support in the ODP filter
And also import/export the video preview as well. The naming follows the style used for table shape previews. The preview is important, since the cropping is relative to the bitmap's preferred logic size. Change-Id: I6115284c1f4cf342b3296cd0ac3beb70a809fd1b Reviewed-on: https://gerrit.libreoffice.org/c/core/+/138959 Reviewed-by: Miklos Vajna <vmiklos@collabora.com> Tested-by: Jenkins
This commit is contained in:
parent
690458889f
commit
cbc6e67d3c
@ -858,6 +858,8 @@ private:
|
||||
// override these for special property handling in subcasses. Return true if property is handled
|
||||
virtual bool setPropertyValueImpl( const OUString& rName, const SfxItemPropertyMapEntry* pProperty, const css::uno::Any& rValue ) override;
|
||||
virtual bool getPropertyValueImpl( const OUString& rName, const SfxItemPropertyMapEntry* pProperty, css::uno::Any& rValue ) override;
|
||||
bool getPropertyStateImpl(const SfxItemPropertyMapEntry* pProperty,
|
||||
css::beans::PropertyState& rState) override;
|
||||
|
||||
OUString referer_;
|
||||
};
|
||||
|
@ -1071,4 +1071,29 @@ bool SvxMediaShape::getPropertyValueImpl( const OUString& rName, const SfxItemPr
|
||||
}
|
||||
}
|
||||
|
||||
bool SvxMediaShape::getPropertyStateImpl(const SfxItemPropertyMapEntry* pProperty,
|
||||
css::beans::PropertyState& rState)
|
||||
{
|
||||
#if HAVE_FEATURE_AVMEDIA
|
||||
if (pProperty->nWID == SDRATTR_GRAFCROP)
|
||||
{
|
||||
auto pMedia = static_cast<SdrMediaObj*>(GetSdrObject());
|
||||
const avmedia::MediaItem& rItem = pMedia->getMediaProperties();
|
||||
const text::GraphicCrop& rCrop = rItem.getCrop();
|
||||
if (rCrop.Bottom > 0 || rCrop.Left > 0 || rCrop.Right > 0 || rCrop.Top > 0)
|
||||
{
|
||||
// The media has a crop, expose it to UNO-based export filters.
|
||||
rState = beans::PropertyState_DIRECT_VALUE;
|
||||
}
|
||||
else
|
||||
{
|
||||
rState = beans::PropertyState_AMBIGUOUS_VALUE;
|
||||
}
|
||||
return true;
|
||||
}
|
||||
#endif
|
||||
|
||||
return SvxShape::getPropertyStateImpl(pProperty, rState);
|
||||
}
|
||||
|
||||
/* vim:set shiftwidth=4 softtabstop=4 expandtab: */
|
||||
|
@ -28,6 +28,9 @@ $(eval $(call gb_CppunitTest_use_libraries,xmloff_draw, \
|
||||
test \
|
||||
unotest \
|
||||
utl \
|
||||
avmedia \
|
||||
svxcore \
|
||||
vcl \
|
||||
))
|
||||
|
||||
$(eval $(call gb_CppunitTest_use_sdk_api,xmloff_draw))
|
||||
|
BIN
xmloff/qa/unit/data/video-snapshot.odp
Normal file
BIN
xmloff/qa/unit/data/video-snapshot.odp
Normal file
Binary file not shown.
@ -24,6 +24,7 @@
|
||||
#include <com/sun/star/util/Color.hpp>
|
||||
#include <com/sun/star/text/XTextRange.hpp>
|
||||
#include <com/sun/star/text/XTextTable.hpp>
|
||||
#include <com/sun/star/text/GraphicCrop.hpp>
|
||||
|
||||
#include <comphelper/propertyvalue.hxx>
|
||||
#include <comphelper/sequence.hxx>
|
||||
@ -31,6 +32,9 @@
|
||||
#include <unotools/tempfile.hxx>
|
||||
#include <unotools/ucbstreamhelper.hxx>
|
||||
#include <unotools/saveopt.hxx>
|
||||
#include <svx/unopage.hxx>
|
||||
#include <svx/svdpage.hxx>
|
||||
#include <svx/svdomedia.hxx>
|
||||
|
||||
using namespace ::com::sun::star;
|
||||
|
||||
@ -173,6 +177,52 @@ CPPUNIT_TEST_FIXTURE(XmloffDrawTest, testThemeExport)
|
||||
assertXPath(pXmlDoc, "//style:master-page/loext:theme/loext:color-table/loext:color", 12);
|
||||
}
|
||||
|
||||
CPPUNIT_TEST_FIXTURE(XmloffDrawTest, testVideoSnapshot)
|
||||
{
|
||||
// Execute ODP import:
|
||||
OUString aURL = m_directories.getURLFromSrc(u"xmloff/qa/unit/data/video-snapshot.odp");
|
||||
getComponent() = loadFromDesktop(aURL, "com.sun.star.presentation.PresentationDocument");
|
||||
uno::Reference<drawing::XDrawPagesSupplier> xDrawPagesSupplier(getComponent(),
|
||||
uno::UNO_QUERY_THROW);
|
||||
CPPUNIT_ASSERT(xDrawPagesSupplier.is());
|
||||
uno::Reference<drawing::XDrawPages> xDrawPages(xDrawPagesSupplier->getDrawPages());
|
||||
uno::Reference<drawing::XDrawPage> xDrawPage(xDrawPages->getByIndex(0), uno::UNO_QUERY_THROW);
|
||||
CPPUNIT_ASSERT(xDrawPage.is());
|
||||
auto pUnoPage = dynamic_cast<SvxDrawPage*>(xDrawPage.get());
|
||||
SdrPage* pSdrPage = pUnoPage->GetSdrPage();
|
||||
auto pMedia = dynamic_cast<SdrMediaObj*>(pSdrPage->GetObj(0));
|
||||
|
||||
// Check that the preview was imported:
|
||||
const avmedia::MediaItem& rItem = pMedia->getMediaProperties();
|
||||
const Graphic& rGraphic = rItem.getGraphic();
|
||||
CPPUNIT_ASSERT(!rGraphic.IsNone());
|
||||
|
||||
// Check that the crop was imported:
|
||||
const text::GraphicCrop& rCrop = rItem.getCrop();
|
||||
CPPUNIT_ASSERT_EQUAL(static_cast<sal_Int32>(0), rCrop.Top);
|
||||
CPPUNIT_ASSERT_EQUAL(static_cast<sal_Int32>(0), rCrop.Bottom);
|
||||
CPPUNIT_ASSERT_EQUAL(static_cast<sal_Int32>(1356), rCrop.Left);
|
||||
CPPUNIT_ASSERT_EQUAL(static_cast<sal_Int32>(1356), rCrop.Right);
|
||||
|
||||
// Execute ODP export:
|
||||
utl::TempFile aTempFile;
|
||||
save("impress8", aTempFile);
|
||||
|
||||
std::unique_ptr<SvStream> pStream = parseExportStream(aTempFile, "content.xml");
|
||||
xmlDocUniquePtr pXmlDoc = parseXmlStream(pStream.get());
|
||||
// Check that the preview was exported:
|
||||
// Without the accompanying fix in place, this test would have failed with:
|
||||
// - Expected: 1
|
||||
// - Actual : 0
|
||||
// - XPath '//draw:frame[@draw:style-name='gr1']/draw:image' number of nodes is incorrect
|
||||
// i.e. the preview wasn't exported to ODP.
|
||||
assertXPath(pXmlDoc, "//draw:frame[@draw:style-name='gr1']/draw:image", "href",
|
||||
"Pictures/MediaPreview1.png");
|
||||
// Check that the crop was exported:
|
||||
assertXPath(pXmlDoc, "//style:style[@style:name='gr1']/style:graphic-properties", "clip",
|
||||
"rect(0cm, 1.356cm, 0cm, 1.356cm)");
|
||||
}
|
||||
|
||||
CPPUNIT_TEST_FIXTURE(XmloffDrawTest, testThemeImport)
|
||||
{
|
||||
// Given a document that has a master page with a theme associated:
|
||||
|
@ -103,6 +103,7 @@
|
||||
#include <tools/globname.hxx>
|
||||
#include <tools/helpers.hxx>
|
||||
#include <comphelper/diagnose_ex.hxx>
|
||||
#include <vcl/graph.hxx>
|
||||
|
||||
#include <xmloff/contextid.hxx>
|
||||
#include <xmloff/families.hxx>
|
||||
@ -3400,7 +3401,7 @@ void XMLShapeExport::ImpExportMediaShape(
|
||||
mrExport.AddAttribute( XML_NAMESPACE_DRAW, XML_MIME_TYPE, sMimeType );
|
||||
|
||||
// write plugin
|
||||
SvXMLElementExport aPluginOBJ(mrExport, XML_NAMESPACE_DRAW, XML_PLUGIN, !( nFeatures & XMLShapeExportFlags::NO_WS ), true);
|
||||
auto pPluginOBJ = std::make_unique<SvXMLElementExport>(mrExport, XML_NAMESPACE_DRAW, XML_PLUGIN, !( nFeatures & XMLShapeExportFlags::NO_WS ), true);
|
||||
|
||||
// export parameters
|
||||
const OUString aFalseStr( "false" ), aTrueStr( "true" );
|
||||
@ -3450,6 +3451,57 @@ void XMLShapeExport::ImpExportMediaShape(
|
||||
delete new SvXMLElementExport( mrExport, XML_NAMESPACE_DRAW, XML_PARAM, false, true );
|
||||
}
|
||||
|
||||
pPluginOBJ.reset();
|
||||
|
||||
uno::Reference<graphic::XGraphic> xGraphic;
|
||||
xPropSet->getPropertyValue("Graphic") >>= xGraphic;
|
||||
Graphic aGraphic(xGraphic);
|
||||
if (!aGraphic.IsNone())
|
||||
{
|
||||
// The media has a preview, export it.
|
||||
uno::Reference<embed::XStorage> xPictureStorage;
|
||||
uno::Reference<embed::XStorage> xStorage;
|
||||
uno::Reference<io::XStream> xPictureStream;
|
||||
OUString sPictureName;
|
||||
xStorage.set(GetExport().GetTargetStorage(), uno::UNO_SET_THROW);
|
||||
xPictureStorage.set(
|
||||
xStorage->openStorageElement("Pictures", embed::ElementModes::READWRITE),
|
||||
uno::UNO_SET_THROW);
|
||||
sal_Int32 nIndex = 0;
|
||||
while (true)
|
||||
{
|
||||
sPictureName = "MediaPreview" + OUString::number(++nIndex) + ".png";
|
||||
if (!xPictureStorage->hasByName(sPictureName))
|
||||
{
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
xPictureStream.set(
|
||||
xPictureStorage->openStreamElement(sPictureName, ::embed::ElementModes::READWRITE),
|
||||
uno::UNO_SET_THROW);
|
||||
|
||||
uno::Reference<uno::XComponentContext> xContext = GetExport().getComponentContext();
|
||||
uno::Reference<graphic::XGraphicProvider> xProvider(
|
||||
graphic::GraphicProvider::create(xContext));
|
||||
uno::Sequence<beans::PropertyValue> aArgs{
|
||||
comphelper::makePropertyValue("MimeType", OUString("image/png")),
|
||||
comphelper::makePropertyValue("OutputStream", xPictureStream->getOutputStream())
|
||||
};
|
||||
xProvider->storeGraphic(xGraphic, aArgs);
|
||||
if (xPictureStorage.is())
|
||||
{
|
||||
uno::Reference<embed::XTransactedObject> xTrans(xPictureStorage, uno::UNO_QUERY);
|
||||
if (xTrans.is())
|
||||
xTrans->commit();
|
||||
}
|
||||
OUString sURL = "Pictures/" + sPictureName;
|
||||
mrExport.AddAttribute(XML_NAMESPACE_XLINK, XML_HREF, sURL);
|
||||
mrExport.AddAttribute(XML_NAMESPACE_XLINK, XML_TYPE, XML_SIMPLE);
|
||||
mrExport.AddAttribute(XML_NAMESPACE_XLINK, XML_SHOW, XML_EMBED);
|
||||
mrExport.AddAttribute(XML_NAMESPACE_XLINK, XML_ACTUATE, XML_ONLOAD);
|
||||
SvXMLElementExport aImageElem(GetExport(), XML_NAMESPACE_DRAW, XML_IMAGE, false, true);
|
||||
}
|
||||
}
|
||||
|
||||
void XMLShapeExport::ImpExport3DSceneShape( const uno::Reference< drawing::XShape >& xShape, XMLShapeExportFlags nFeatures, awt::Point* pRefPoint)
|
||||
|
@ -2918,6 +2918,12 @@ void SdXMLPluginShapeContext::startFastElement (sal_Int32 /*nElement*/,
|
||||
if( !mxShape.is() )
|
||||
return;
|
||||
|
||||
if (mbMedia)
|
||||
{
|
||||
// The media may have a crop, apply it.
|
||||
SetStyle(/*bSupportsStyle=*/false);
|
||||
}
|
||||
|
||||
SetLayer();
|
||||
|
||||
if(bIsPresShape)
|
||||
@ -3312,6 +3318,7 @@ css::uno::Reference< css::xml::sax::XFastContextHandler > SdXMLFrameShapeContext
|
||||
pShapeContext->setHyperlink( msHyperlink );
|
||||
|
||||
auto nToken = nElement & TOKEN_MASK;
|
||||
bool bMedia = false;
|
||||
// Ignore gltf model if necessary and so the fallback image will be imported
|
||||
if( nToken == XML_PLUGIN )
|
||||
{
|
||||
@ -3321,10 +3328,15 @@ css::uno::Reference< css::xml::sax::XFastContextHandler > SdXMLFrameShapeContext
|
||||
mxImplContext = nullptr;
|
||||
return new SvXMLImportContext(GetImport());
|
||||
}
|
||||
else if (pPluginContext && pPluginContext->getMimeType() == "application/vnd.sun.star.media")
|
||||
{
|
||||
// The media may have a preview, import it.
|
||||
bMedia = true;
|
||||
}
|
||||
}
|
||||
|
||||
mxImplContext = xContext;
|
||||
mbSupportsReplacement = (nToken == XML_OBJECT ) || (nToken == XML_OBJECT_OLE);
|
||||
mbSupportsReplacement = (nToken == XML_OBJECT ) || (nToken == XML_OBJECT_OLE) || bMedia;
|
||||
setSupportsMultipleContents(nToken == XML_IMAGE);
|
||||
|
||||
if(getSupportsMultipleContents() && dynamic_cast< SdXMLGraphicObjectShapeContext* >(xContext.get()))
|
||||
|
Loading…
x
Reference in New Issue
Block a user