summaryrefslogtreecommitdiff
path: root/xmloff
diff options
context:
space:
mode:
authorZolnai Tamás <tamas.zolnai@collabora.com>2014-06-16 12:59:19 +0200
committerZolnai Tamás <tamas.zolnai@collabora.com>2014-06-16 12:59:19 +0200
commit4d8c4e7fe3e9b0ec6e14b5475a29d119e2023065 (patch)
tree7cd73eaaf291ec1d945b5f9e0da20916b861b6f3 /xmloff
parent9ee69cbd6f1143160aa96001462b933770cc6b76 (diff)
glTF import/export: fallback must be the second one inside the frame
The previous solution was good because older LO versions import the fallback image without changing their code, but it came out it does not fit to ODF standard so export fallback image as the second object after the glTF model. Change-Id: Ib9b2044b1f36b32d980cb79f6dac8dcf94d6209b
Diffstat (limited to 'xmloff')
-rw-r--r--xmloff/source/draw/shapeexport.cxx67
-rw-r--r--xmloff/source/draw/ximpshap.cxx32
-rw-r--r--xmloff/source/draw/ximpshap.hxx2
3 files changed, 77 insertions, 24 deletions
diff --git a/xmloff/source/draw/shapeexport.cxx b/xmloff/source/draw/shapeexport.cxx
index 56c2e6426c02..68965edfdbfc 100644
--- a/xmloff/source/draw/shapeexport.cxx
+++ b/xmloff/source/draw/shapeexport.cxx
@@ -3160,9 +3160,8 @@ lcl_StoreMediaAndGetURL(SvXMLExport & rExport,
}
#if HAVE_FEATURE_GLTF
-static void lcl_StoreJsonExternalsAndFallback(
+static void lcl_StoreGltfExternals(
SvXMLExport& rExport,
- const uno::Reference<beans::XPropertySet> xPropSet,
const OUString& rURL )
{
OUString sUrlPath;
@@ -3198,16 +3197,60 @@ static void lcl_StoreJsonExternalsAndFallback(
xModelStorage->copyToStorage(xModelTarget);
- /* Save the fallback image under the 'Model/Fallback/' folder
- Place fallback image before the plugin tag otherwise older LO versions will parse an empty
- plugin shape instead of the image. In current version this image will be ingored during import.*/
+ const uno::Reference<embed::XTransactedObject> xModelsTransaction(xModelsTarget, uno::UNO_QUERY);
+ if (xModelsTransaction.is())
+ {
+ xModelsTransaction->commit();
+ }
+ }
+ catch (uno::Exception const& e)
+ {
+ SAL_INFO("xmloff", "exception while saving embedded model: '" << e.Message << "'");
+ }
+ }
+}
+
+static void lcl_StoreGltfFallback(
+ SvXMLExport& rExport,
+ const uno::Reference<beans::XPropertySet> xPropSet,
+ const OUString& rURL )
+{
+ OUString sUrlPath;
+ if (rURL.startsWithIgnoreAsciiCase("vnd.sun.star.Package:", &sUrlPath))
+ {
+ sUrlPath = sUrlPath.copy(0,sUrlPath.lastIndexOf("/"));
+ try
+ {
+ // Base storage
+ uno::Reference<document::XStorageBasedDocument> const xSBD(
+ rExport.GetModel(), uno::UNO_QUERY_THROW);
+ const uno::Reference<embed::XStorage> xStorage(
+ xSBD->getDocumentStorage(), uno::UNO_QUERY_THROW);
+
+ // Model source
+ ::comphelper::LifecycleProxy proxy;
+ const uno::Reference<embed::XStorage> xModelStorage(
+ ::comphelper::OStorageHelper::GetStorageAtPath(xStorage, sUrlPath,
+ embed::ElementModes::READ, proxy));
+
+ // Target storage
+ uno::Reference<embed::XStorage> const xTarget(
+ rExport.GetTargetStorage(), uno::UNO_QUERY_THROW);
+
+ // Target of all models
+ const uno::Reference<embed::XStorage> xModelsTarget(
+ xTarget->openStorageElement(sUrlPath.copy(0,sUrlPath.lastIndexOf("/")), embed::ElementModes::WRITE));
+
+ /// Save the fallback image under the 'Models/Fallbacks/' folder
uno::Reference< graphic::XGraphic > xGraphic( xPropSet->getPropertyValue("FallbackGraphic"), uno::UNO_QUERY );
if( xGraphic.is() )
{
// Fallback storage
+ const OUString sFallbackFolder("Fallbacks");
const uno::Reference<embed::XStorage> xFallbackTarget(
- xModelsTarget->openStorageElement(OUString("Fallbacks"), embed::ElementModes::WRITE));
+ xModelsTarget->openStorageElement(sFallbackFolder, embed::ElementModes::WRITE));
+ const OUString sModelName = sUrlPath.copy(sUrlPath.lastIndexOf("/")+1);
uno::Reference< io::XStream > xPictureStream(
xFallbackTarget->openStreamElement( sModelName + ".png", embed::ElementModes::WRITE ), uno::UNO_QUERY_THROW );
@@ -3225,7 +3268,7 @@ static void lcl_StoreJsonExternalsAndFallback(
xFallbackTransaction->commit();
}
- const OUString sFallbackURL( sUrlPath.copy(0,sUrlPath.lastIndexOf("/")) + "/Fallbacks/" + sModelName + ".png");
+ const OUString sFallbackURL( sUrlPath.copy(0,sUrlPath.lastIndexOf("/")) + "/" + sFallbackFolder + "/" + sModelName + ".png");
rExport.AddAttribute(XML_NAMESPACE_XLINK, XML_HREF, sFallbackURL );
rExport.AddAttribute( XML_NAMESPACE_XLINK, XML_TYPE, XML_SIMPLE );
rExport.AddAttribute( XML_NAMESPACE_XLINK, XML_SHOW, XML_EMBED );
@@ -3242,10 +3285,11 @@ static void lcl_StoreJsonExternalsAndFallback(
}
catch (uno::Exception const& e)
{
- SAL_INFO("xmloff", "exception while saving embedded model: '" << e.Message << "'");
+ SAL_INFO("xmloff", "exception while saving fallback image of glTF model: '" << e.Message << "'");
}
}
}
+
#endif
void XMLShapeExport::ImpExportMediaShape(
@@ -3276,7 +3320,7 @@ void XMLShapeExport::ImpExportMediaShape(
lcl_StoreMediaAndGetURL(GetExport(), xPropSet, aMediaURL, sMimeType);
#if HAVE_FEATURE_GLTF
if( sMimeType == "model/vnd.gltf+json" )
- lcl_StoreJsonExternalsAndFallback(GetExport(), xPropSet, aMediaURL);
+ lcl_StoreGltfExternals(GetExport(), aMediaURL);
#endif
mrExport.AddAttribute ( XML_NAMESPACE_XLINK, XML_HREF, persistentURL );
@@ -3339,6 +3383,11 @@ void XMLShapeExport::ImpExportMediaShape(
mrExport.AddAttribute( XML_NAMESPACE_DRAW, XML_VALUE, aZoomValue );
delete( new SvXMLElementExport( mrExport, XML_NAMESPACE_DRAW, XML_PARAM, false, true ) );
}
+
+#if HAVE_FEATURE_GLTF
+ if( sMimeType == "model/vnd.gltf+json" )
+ lcl_StoreGltfFallback(GetExport(), xPropSet, aMediaURL);
+#endif
}
}
diff --git a/xmloff/source/draw/ximpshap.cxx b/xmloff/source/draw/ximpshap.cxx
index d1caa4e08496..4bc580dc2603 100644
--- a/xmloff/source/draw/ximpshap.cxx
+++ b/xmloff/source/draw/ximpshap.cxx
@@ -3526,7 +3526,6 @@ SvXMLImportContext *SdXMLFrameShapeContext::CreateChildContext( sal_uInt16 nPref
if( !mxImplContext.Is() )
{
-
SvXMLShapeContext* pShapeContext= GetImport().GetShapeImport()->CreateFrameChildContext(
GetImport(), nPrefix, rLocalName, xAttrList, mxShapes, mxAttrList );
@@ -3536,6 +3535,23 @@ SvXMLImportContext *SdXMLFrameShapeContext::CreateChildContext( sal_uInt16 nPref
if ( !msHyperlink.isEmpty() )
pShapeContext->setHyperlink( msHyperlink );
+ // Ignore gltf model if necessary and so the fallback image will be imported
+ bool bIngoreGltf;
+#if !HAVE_FEATURE_GLTF
+ bIngoreGltf = true;
+#else
+ bIngoreGltf = !SvtMiscOptions().IsExperimentalMode();
+#endif
+ if( bIngoreGltf && IsXMLToken(rLocalName, XML_PLUGIN ) )
+ {
+ SdXMLPluginShapeContext* pPluginContext = dynamic_cast<SdXMLPluginShapeContext*>(pShapeContext);
+ if( pPluginContext && pPluginContext->getMimeType() == "model/vnd.gltf+json" )
+ {
+ mxImplContext = 0;
+ return this;
+ }
+ }
+
mxImplContext = pContext;
mbSupportsReplacement = IsXMLToken(rLocalName, XML_OBJECT ) || IsXMLToken(rLocalName, XML_OBJECT_OLE);
setSupportsMultipleContents(IsXMLToken(rLocalName, XML_IMAGE));
@@ -3600,20 +3616,6 @@ SvXMLImportContext *SdXMLFrameShapeContext::CreateChildContext( sal_uInt16 nPref
}
}
}
-#if HAVE_FEATURE_GLTF
- // For glTF models the fallback image is placed before the real shape.
- // So we need to remove the fallback image after real shape is detected.
- else if ( mxImplContext.Is() && IsXMLToken(mxImplContext->GetLocalName(), XML_IMAGE) &&
- IsXMLToken( rLocalName, XML_PLUGIN ) && SvtMiscOptions().IsExperimentalMode() )
- {
- SvXMLShapeContext* pShapeContext= GetImport().GetShapeImport()->CreateFrameChildContext(
- GetImport(), nPrefix, rLocalName, xAttrList, mxShapes, mxAttrList );
-
- pContext = pShapeContext;
- if( pContext )
- removeGraphicFromImportContext(*mxImplContext);
- }
-#endif
// call parent for content
if(!pContext)
pContext = SvXMLImportContext::CreateChildContext( nPrefix, rLocalName, xAttrList );
diff --git a/xmloff/source/draw/ximpshap.hxx b/xmloff/source/draw/ximpshap.hxx
index 4f987af9a545..ff4ae6a81661 100644
--- a/xmloff/source/draw/ximpshap.hxx
+++ b/xmloff/source/draw/ximpshap.hxx
@@ -530,6 +530,8 @@ public:
// this is called from the parent group for each unparsed attribute in the attribute list
virtual void processAttribute( sal_uInt16 nPrefix, const OUString& rLocalName, const OUString& rValue ) SAL_OVERRIDE;
+
+ const OUString& getMimeType() const { return maMimeType; }
};
// draw:floating-frame