LCOV - code coverage report
Current view: top level - filter/source/msfilter - msoleexp.cxx (source / functions) Hit Total Coverage
Test: commit e02a6cb2c3e2b23b203b422e4e0680877f232636 Lines: 0 134 0.0 %
Date: 2014-04-14 Functions: 0 5 0.0 %
Legend: Lines: hit not hit

          Line data    Source code
       1             : /* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
       2             : /*
       3             :  * This file is part of the LibreOffice project.
       4             :  *
       5             :  * This Source Code Form is subject to the terms of the Mozilla Public
       6             :  * License, v. 2.0. If a copy of the MPL was not distributed with this
       7             :  * file, You can obtain one at http://mozilla.org/MPL/2.0/.
       8             :  *
       9             :  * This file incorporates work covered by the following license notice:
      10             :  *
      11             :  *   Licensed to the Apache Software Foundation (ASF) under one or more
      12             :  *   contributor license agreements. See the NOTICE file distributed
      13             :  *   with this work for additional information regarding copyright
      14             :  *   ownership. The ASF licenses this file to you under the Apache
      15             :  *   License, Version 2.0 (the "License"); you may not use this file
      16             :  *   except in compliance with the License. You may obtain a copy of
      17             :  *   the License at http://www.apache.org/licenses/LICENSE-2.0 .
      18             :  */
      19             : 
      20             : #include <com/sun/star/uno/Reference.hxx>
      21             : #include <com/sun/star/uno/Sequence.hxx>
      22             : #include <com/sun/star/uno/Any.hxx>
      23             : #include <com/sun/star/lang/XMultiServiceFactory.hpp>
      24             : #include <com/sun/star/configuration/theDefaultProvider.hpp>
      25             : #include <com/sun/star/container/XNameAccess.hpp>
      26             : #include <com/sun/star/embed/XEmbedPersist.hpp>
      27             : #include <com/sun/star/embed/NoVisualAreaSizeException.hpp>
      28             : #include <com/sun/star/embed/EmbedStates.hpp>
      29             : #include <com/sun/star/frame/XStorable.hpp>
      30             : #include <com/sun/star/awt/Size.hpp>
      31             : #include <com/sun/star/embed/Aspects.hpp>
      32             : #include <comphelper/classids.hxx>
      33             : #include <sfx2/objsh.hxx>
      34             : #include <sfx2/docfac.hxx>
      35             : #include <sfx2/docfilt.hxx>
      36             : #include <sfx2/docfile.hxx>
      37             : #include <sfx2/fcontnr.hxx>
      38             : #include <sot/formats.hxx>
      39             : #include <comphelper/processfactory.hxx>
      40             : #include <unotools/streamwrap.hxx>
      41             : #include <comphelper/storagehelper.hxx>
      42             : #include <svtools/embedhlp.hxx>
      43             : #include <filter/msfilter/msdffimp.hxx>
      44             : 
      45             : #include "filter/msfilter/msoleexp.hxx"
      46             : 
      47             : using namespace ::com::sun::star;
      48             : 
      49           0 : SvGlobalName GetEmbeddedVersion( const SvGlobalName& aAppName )
      50             : {
      51           0 :     if ( aAppName == SvGlobalName( SO3_SM_CLASSID_60 ) )
      52           0 :             return SvGlobalName( SO3_SM_OLE_EMBED_CLASSID_8 );
      53           0 :     else if ( aAppName == SvGlobalName( SO3_SW_CLASSID_60 ) )
      54           0 :             return SvGlobalName( SO3_SW_OLE_EMBED_CLASSID_8 );
      55           0 :     else if ( aAppName == SvGlobalName( SO3_SC_CLASSID_60 ) )
      56           0 :             return SvGlobalName( SO3_SC_OLE_EMBED_CLASSID_8 );
      57           0 :     else if ( aAppName == SvGlobalName( SO3_SDRAW_CLASSID_60 ) )
      58           0 :             return SvGlobalName( SO3_SDRAW_OLE_EMBED_CLASSID_8 );
      59           0 :     else if ( aAppName == SvGlobalName( SO3_SIMPRESS_CLASSID_60 ) )
      60           0 :             return SvGlobalName( SO3_SIMPRESS_OLE_EMBED_CLASSID_8 );
      61           0 :     else if ( aAppName == SvGlobalName( SO3_SCH_CLASSID_60 ) )
      62           0 :             return SvGlobalName( SO3_SCH_OLE_EMBED_CLASSID_8 );
      63             : 
      64           0 :     return SvGlobalName();
      65             : }
      66             : 
      67           0 : OUString GetStorageType( const SvGlobalName& aEmbName )
      68             : {
      69           0 :     if ( aEmbName == SvGlobalName( SO3_SM_OLE_EMBED_CLASSID_8 ) )
      70           0 :         return OUString( "LibreOffice.MathDocument.1" );
      71           0 :     else if ( aEmbName == SvGlobalName( SO3_SW_OLE_EMBED_CLASSID_8 ) )
      72           0 :         return OUString( "LibreOffice.WriterDocument.1" );
      73           0 :     else if ( aEmbName == SvGlobalName( SO3_SC_OLE_EMBED_CLASSID_8 ) )
      74           0 :         return OUString( "LibreOffice.CalcDocument.1" );
      75           0 :     else if ( aEmbName == SvGlobalName( SO3_SDRAW_OLE_EMBED_CLASSID_8 ) )
      76           0 :         return OUString( "LibreOffice.DrawDocument.1" );
      77           0 :     else if ( aEmbName == SvGlobalName( SO3_SIMPRESS_OLE_EMBED_CLASSID_8 ) )
      78           0 :         return OUString( "LibreOffice.ImpressDocument.1" );
      79           0 :     else if ( aEmbName == SvGlobalName( SO3_SCH_OLE_EMBED_CLASSID_8 ) )
      80           0 :         return OUString("LibreOffice.ChartDocument.1");
      81           0 :     return OUString();
      82             : }
      83             : 
      84           0 : sal_Bool UseOldMSExport()
      85             : {
      86             :     uno::Reference< lang::XMultiServiceFactory > xProvider(
      87             :         configuration::theDefaultProvider::get(
      88           0 :             comphelper::getProcessComponentContext()));
      89             :     try {
      90           0 :         uno::Sequence< uno::Any > aArg( 1 );
      91           0 :         aArg[0] <<= OUString( "/org.openoffice.Office.Common/InternalMSExport" );
      92             :         uno::Reference< container::XNameAccess > xNameAccess(
      93           0 :             xProvider->createInstanceWithArguments(
      94             :                 "com.sun.star.configuration.ConfigurationUpdateAccess",
      95           0 :                 aArg ),
      96           0 :             uno::UNO_QUERY );
      97           0 :         if ( xNameAccess.is() )
      98             :         {
      99           0 :             uno::Any aResult = xNameAccess->getByName( "UseOldExport" );
     100             : 
     101           0 :             sal_Bool bResult = sal_Bool();
     102           0 :             if ( aResult >>= bResult )
     103           0 :                 return bResult;
     104           0 :         }
     105             :     }
     106           0 :     catch( const uno::Exception& )
     107             :     {
     108             :     }
     109             : 
     110             :     OSL_FAIL( "Could not get access to configuration entry!\n" );
     111           0 :     return sal_False;
     112             : }
     113             : 
     114           0 : void SvxMSExportOLEObjects::ExportOLEObject( const com::sun::star::uno::Reference < com::sun::star::embed::XEmbeddedObject>& rObj, SotStorage& rDestStg )
     115             : {
     116           0 :     svt::EmbeddedObjectRef aObj( rObj, embed::Aspects::MSOLE_CONTENT );
     117           0 :     ExportOLEObject( aObj, rDestStg );
     118           0 : }
     119             : 
     120           0 : void SvxMSExportOLEObjects::ExportOLEObject( svt::EmbeddedObjectRef& rObj, SvStorage& rDestStg )
     121             : {
     122           0 :     SvGlobalName aOwnGlobalName;
     123           0 :     SvGlobalName aObjName( rObj->getClassID() );
     124           0 :     const SfxFilter* pExpFilter = NULL;
     125             :     {
     126             :         static struct _ObjExpType {
     127             :             sal_uInt32 nFlag;
     128             :             const char* pFilterNm;
     129             :             // GlobalNameId
     130             :             struct _GlobalNameIds {
     131             :                 sal_uInt32 n1;
     132             :                 sal_uInt16 n2, n3;
     133             :                 sal_uInt8 b8, b9, b10, b11, b12, b13, b14, b15;
     134             :             }
     135             :             aGlNmIds[4];
     136             :         } aArr[] = {
     137             :             { OLE_STARMATH_2_MATHTYPE, "MathType 3.x",
     138             :                 {{SO3_SM_CLASSID_60}, {SO3_SM_CLASSID_50},
     139             :                  {SO3_SM_CLASSID_40}, {SO3_SM_CLASSID_30 }}},
     140             :             { OLE_STARWRITER_2_WINWORD, "MS Word 97",
     141             :                 {{SO3_SW_CLASSID_60}, {SO3_SW_CLASSID_50},
     142             :                  {SO3_SW_CLASSID_40}, {SO3_SW_CLASSID_30 }}},
     143             :             { OLE_STARCALC_2_EXCEL, "MS Excel 97",
     144             :                 {{SO3_SC_CLASSID_60}, {SO3_SC_CLASSID_50},
     145             :                  {SO3_SC_CLASSID_40}, {SO3_SC_CLASSID_30 }}},
     146             :             { OLE_STARIMPRESS_2_POWERPOINT, "MS PowerPoint 97",
     147             :                 {{SO3_SIMPRESS_CLASSID_60}, {SO3_SIMPRESS_CLASSID_50},
     148             :                  {SO3_SIMPRESS_CLASSID_40}, {SO3_SIMPRESS_CLASSID_30 }}},
     149             :             { 0, "",
     150             :                 {{SO3_SCH_CLASSID_60}, {SO3_SCH_CLASSID_50},
     151             :                  {SO3_SCH_CLASSID_40}, {SO3_SCH_CLASSID_30 }}},
     152             :             { 0, "",
     153             :                 {{SO3_SDRAW_CLASSID_60}, {SO3_SDRAW_CLASSID_50},    // SJ: !!!! SO3_SDRAW_CLASSID is only available up from
     154             :                  {SO3_SDRAW_CLASSID_60}, {SO3_SDRAW_CLASSID_50 }}}, // ver 5.0, it is purpose to have double entrys here.
     155             : 
     156             :             { 0xffff,0,
     157             :                 {{SO3_SDRAW_CLASSID_60}, {SO3_SDRAW_CLASSID_50},
     158             :                 {SO3_SDRAW_CLASSID_60}, {SO3_SDRAW_CLASSID_50}}}
     159             :         };
     160             : 
     161           0 :         for( const _ObjExpType* pArr = aArr; !pExpFilter && ( pArr->nFlag != 0xffff ); ++pArr )
     162             :         {
     163           0 :             for ( int n = 0; n < 4; ++n )
     164             :             {
     165           0 :                 const _ObjExpType::_GlobalNameIds& rId = pArr->aGlNmIds[ n ];
     166             :                 SvGlobalName aGlbNm( rId.n1, rId.n2, rId.n3,
     167             :                             rId.b8, rId.b9, rId.b10, rId.b11,
     168           0 :                             rId.b12, rId.b13, rId.b14, rId.b15 );
     169           0 :                 if( aObjName == aGlbNm )
     170             :                 {
     171           0 :                     aOwnGlobalName = aGlbNm;
     172             : 
     173             :                     // flags for checking if conversion is wanted at all (SaveOptions?!)
     174           0 :                     if( GetFlags() & pArr->nFlag )
     175             :                     {
     176           0 :                         pExpFilter = SfxFilterMatcher().GetFilter4FilterName(OUString::createFromAscii(pArr->pFilterNm));
     177           0 :                         break;
     178             :                     }
     179             :                 }
     180           0 :             }
     181             :         }
     182             :     }
     183             : 
     184           0 :     if( pExpFilter )                        // use this filter for the export
     185             :     {
     186             :         try
     187             :         {
     188           0 :             if ( rObj->getCurrentState() == embed::EmbedStates::LOADED )
     189           0 :                 rObj->changeState( embed::EmbedStates::RUNNING );
     190             :             //TODO/LATER: is stream instead of outputstream a better choice?!
     191             :             //TODO/LATER: a "StoreTo" method at embedded object would be nice
     192           0 :             uno::Sequence < beans::PropertyValue > aSeq(2);
     193           0 :             SvStream* pStream = new SvMemoryStream;
     194           0 :             aSeq[0].Name = "OutputStream";
     195           0 :             ::uno::Reference < io::XOutputStream > xOut = new ::utl::OOutputStreamWrapper( *pStream );
     196           0 :             aSeq[0].Value <<= xOut;
     197           0 :             aSeq[1].Name = "FilterName";
     198           0 :             aSeq[1].Value <<= OUString( pExpFilter->GetName() );
     199           0 :             uno::Reference < frame::XStorable > xStor( rObj->getComponent(), uno::UNO_QUERY );
     200             :         try
     201             :         {
     202           0 :             xStor->storeToURL( "private:stream", aSeq );
     203             :         }
     204           0 :         catch( const uno::Exception& ) {} // #TODO really handle exceptions - interactionalhandler etc. ?
     205             : 
     206           0 :             SotStorageRef xOLEStor = new SotStorage( pStream, true );
     207           0 :             xOLEStor->CopyTo( &rDestStg );
     208           0 :             rDestStg.Commit();
     209             :         }
     210           0 :         catch( const uno::Exception& )
     211             :         {
     212             :             // TODO/LATER: Error handling
     213             :             OSL_FAIL( "The object could not be exported!" );
     214             :         }
     215             :     }
     216           0 :     else if( aOwnGlobalName != SvGlobalName() )
     217             :     {
     218             :         // own format, maybe SO6 format or lower
     219           0 :         SvGlobalName aEmbName = GetEmbeddedVersion( aOwnGlobalName );
     220           0 :         if ( aEmbName != SvGlobalName() && !UseOldMSExport() )
     221             :         {
     222             :             // this is a SO6 embedded object, save in old binary format
     223           0 :             rDestStg.SetVersion( SOFFICE_FILEFORMAT_31 );
     224             :             rDestStg.SetClass( aEmbName,
     225             :                                 SOT_FORMATSTR_ID_EMBEDDED_OBJ_OLE,
     226           0 :                                 GetStorageType( aEmbName ) );
     227             :             SotStorageStreamRef xExtStm = rDestStg.OpenSotStream(
     228             :                                             OUString( "properties_stream" ),
     229           0 :                                             STREAM_STD_READWRITE);
     230             : 
     231           0 :             sal_Bool bExtentSuccess = sal_False;
     232           0 :             if( !xExtStm->GetError() )
     233             :             {
     234             :                 // write extent
     235             :                 //TODO/MBA: check if writing a size is enough
     236           0 :                 if( rObj.GetObject().is() )
     237             :                 {
     238             :                     // MSOLE objects don't need to be in running state for VisualArea access
     239           0 :                     awt::Size aSize;
     240             :                     try
     241             :                     {
     242             :                         // this is an own object, the content size must be stored in the
     243             :                         // extension stream
     244           0 :                         aSize = rObj->getVisualAreaSize( embed::Aspects::MSOLE_CONTENT );
     245             :                     }
     246           0 :                     catch( const embed::NoVisualAreaSizeException& )
     247             :                     {
     248             :                         OSL_FAIL( "Could not get visual area size!\n" );
     249           0 :                         aSize.Width = 5000;
     250           0 :                         aSize.Height = 5000;
     251             :                     }
     252           0 :                     catch( const uno::Exception& )
     253             :                     {
     254             :                         OSL_FAIL( "Unexpected exception while getting visual area size!\n" );
     255           0 :                         aSize.Width = 5000;
     256           0 :                         aSize.Height = 5000;
     257             :                     }
     258             : 
     259             :                     sal_Int32 pRect[4];
     260           0 :                     pRect[0] = 0;
     261           0 :                     pRect[1] = aSize.Width;
     262           0 :                     pRect[2] = 0;
     263           0 :                     pRect[3] = aSize.Height;
     264             : 
     265             :                     sal_Int8 aWriteSet[16];
     266           0 :                     for ( int ind = 0; ind < 4; ind++ )
     267             :                     {
     268           0 :                         sal_Int32 nVal = pRect[ind];
     269           0 :                         for ( int nByte = 0; nByte < 4; nByte++ )
     270             :                         {
     271           0 :                             aWriteSet[ind*4+nByte] = (sal_Int8) nVal % 0x100;
     272           0 :                             nVal /= 0x100;
     273             :                         }
     274             :                     }
     275             : 
     276           0 :                     bExtentSuccess = ( xExtStm->Write( aWriteSet, 16 ) == 16 );
     277             :                 }
     278             :             }
     279             : 
     280           0 :             if ( bExtentSuccess )
     281             :             {
     282             :                 SotStorageStreamRef xEmbStm = rDestStg.OpenSotStream(
     283             :                                                 OUString( "package_stream" ),
     284           0 :                                                 STREAM_STD_READWRITE);
     285           0 :                 if( !xEmbStm->GetError() )
     286             :                 {
     287             :                     try
     288             :                     {
     289           0 :                         if ( rObj->getCurrentState() == embed::EmbedStates::LOADED )
     290           0 :                             rObj->changeState( embed::EmbedStates::RUNNING );
     291             :                         //TODO/LATER: is stream instead of outputstream a better choice?!
     292             :                         //TODO/LATER: a "StoreTo" method at embedded object would be nice
     293           0 :                         uno::Sequence < beans::PropertyValue > aSeq(1);
     294           0 :                         aSeq[0].Name = "OutputStream";
     295           0 :                         ::uno::Reference < io::XOutputStream > xOut = new ::utl::OOutputStreamWrapper( *xEmbStm );
     296           0 :                         aSeq[0].Value <<= xOut;
     297           0 :                         uno::Reference < frame::XStorable > xStor( rObj->getComponent(), uno::UNO_QUERY );
     298           0 :                         xStor->storeToURL( "private:stream", aSeq );
     299             :                     }
     300           0 :                     catch( const uno::Exception& )
     301             :                     {
     302             :                         // TODO/LATER: Error handling
     303             :                         OSL_FAIL( "The object could not be exported!" );
     304             :                     }
     305           0 :                 }
     306           0 :             }
     307             :         }
     308             :         else
     309             :         {
     310             :             OSL_FAIL("Own binary format inside own container document!");
     311           0 :         }
     312             :     }
     313             :     else
     314             :     {
     315             :         // alien objects
     316             :         //TODO/LATER: a "StoreTo" method at embedded object would be nice
     317           0 :         rDestStg.SetVersion( SOFFICE_FILEFORMAT_31 );
     318           0 :         uno::Reference < embed::XStorage > xStor = ::comphelper::OStorageHelper::GetTemporaryStorage();
     319           0 :         uno::Reference < embed::XEmbedPersist > xPers( rObj.GetObject(), uno::UNO_QUERY );
     320           0 :         if ( xPers.is() )
     321             :         {
     322           0 :             uno::Sequence < beans::PropertyValue > aEmptySeq;
     323           0 :             OUString aTempName( "bla" );
     324             :             try
     325             :             {
     326           0 :                 xPers->storeToEntry( xStor, aTempName, aEmptySeq, aEmptySeq );
     327             :             }
     328           0 :             catch ( const uno::Exception& )
     329             :             {}
     330             : 
     331           0 :             SotStorageRef xOLEStor = SotStorage::OpenOLEStorage( xStor, aTempName, STREAM_STD_READ );
     332           0 :             xOLEStor->CopyTo( &rDestStg );
     333           0 :             rDestStg.Commit();
     334           0 :         }
     335             :     }
     336             : 
     337             :     //We never need this stream: See #99809# and #i2179#
     338           0 :     rDestStg.Remove( OUString(SVEXT_PERSIST_STREAM) );
     339           0 : }
     340             : 
     341             : 
     342             : 
     343             : /* vim:set shiftwidth=4 softtabstop=4 expandtab: */

Generated by: LCOV version 1.10