LCOV - code coverage report
Current view: top level - svtools/source/graphic - provider.cxx (source / functions) Hit Total Coverage
Test: commit 10e77ab3ff6f4314137acd6e2702a6e5c1ce1fae Lines: 194 453 42.8 %
Date: 2014-11-03 Functions: 17 24 70.8 %
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 <osl/mutex.hxx>
      21             : #include <vcl/svapp.hxx>
      22             : #include <vcl/image.hxx>
      23             : #include <vcl/metaact.hxx>
      24             : #include <vcl/msgbox.hxx>
      25             : #include <vcl/imagerepository.hxx>
      26             : #include <tools/rcid.h>
      27             : #include <tools/resid.hxx>
      28             : #include <tools/resmgr.hxx>
      29             : #include <unotools/ucbstreamhelper.hxx>
      30             : #include <vcl/graphicfilter.hxx>
      31             : #include <vcl/wmf.hxx>
      32             : #include <svl/solar.hrc>
      33             : #include <vcl/virdev.hxx>
      34             : #include <vcl/settings.hxx>
      35             : #include <com/sun/star/io/XStream.hpp>
      36             : #include <com/sun/star/text/GraphicCrop.hpp>
      37             : #include <com/sun/star/uno/XComponentContext.hpp>
      38             : #include <comphelper/servicehelper.hxx>
      39             : #include <cppuhelper/supportsservice.hxx>
      40             : 
      41             : #include "descriptor.hxx"
      42             : #include "graphic.hxx"
      43             : #include <rtl/ref.hxx>
      44             : #include <svtools/grfmgr.hxx>
      45             : #include "provider.hxx"
      46             : #include <vcl/dibtools.hxx>
      47             : #include <boost/scoped_ptr.hpp>
      48             : 
      49             : using namespace com::sun::star;
      50             : 
      51             : namespace {
      52             : 
      53             : #define UNO_NAME_GRAPHOBJ_URLPREFIX                             "vnd.sun.star.GraphicObject:"
      54             : 
      55      145945 : GraphicProvider::GraphicProvider()
      56             : {
      57      145945 : }
      58             : 
      59      291886 : GraphicProvider::~GraphicProvider()
      60             : {
      61      291886 : }
      62             : 
      63           0 : OUString SAL_CALL GraphicProvider::getImplementationName()
      64             :     throw( uno::RuntimeException, std::exception )
      65             : {
      66           0 :     return OUString( "com.sun.star.comp.graphic.GraphicProvider" );
      67             : }
      68             : 
      69           0 : sal_Bool SAL_CALL GraphicProvider::supportsService( const OUString& ServiceName )
      70             :     throw( uno::RuntimeException, std::exception )
      71             : {
      72           0 :     return cppu::supportsService( this, ServiceName );
      73             : }
      74             : 
      75           0 : uno::Sequence< OUString > SAL_CALL GraphicProvider::getSupportedServiceNames()
      76             :     throw( uno::RuntimeException, std::exception )
      77             : {
      78           0 :     uno::Sequence< OUString > aSeq( 1 );
      79           0 :     aSeq.getArray()[ 0 ] = "com.sun.star.graphic.GraphicProvider";
      80           0 :     return aSeq;
      81             : }
      82             : 
      83           0 : uno::Sequence< uno::Type > SAL_CALL GraphicProvider::getTypes()
      84             :     throw(uno::RuntimeException, std::exception)
      85             : {
      86           0 :     uno::Sequence< uno::Type >  aTypes( 3 );
      87           0 :     uno::Type*                  pTypes = aTypes.getArray();
      88             : 
      89           0 :     *pTypes++ = cppu::UnoType<lang::XServiceInfo>::get();
      90           0 :     *pTypes++ = cppu::UnoType<lang::XTypeProvider>::get();
      91           0 :     *pTypes++ = cppu::UnoType<graphic::XGraphicProvider>::get();
      92             : 
      93           0 :     return aTypes;
      94             : }
      95             : 
      96           0 : uno::Sequence< sal_Int8 > SAL_CALL GraphicProvider::getImplementationId()
      97             :     throw(uno::RuntimeException, std::exception)
      98             : {
      99           0 :     return css::uno::Sequence<sal_Int8>();
     100             : }
     101             : 
     102             : 
     103             : 
     104        5871 : uno::Reference< ::graphic::XGraphic > GraphicProvider::implLoadGraphicObject( const OUString& rResourceURL ) const
     105             : {
     106        5871 :     uno::Reference< ::graphic::XGraphic >   xRet;
     107        5871 :     if( rResourceURL.startsWith( UNO_NAME_GRAPHOBJ_URLPREFIX ) )
     108             :     {
     109             :         // graphic manager url
     110         448 :         OUString aTmpStr( rResourceURL.copy( sizeof( UNO_NAME_GRAPHOBJ_URLPREFIX ) - 1 ) );
     111             :         OString aUniqueID(OUStringToOString(aTmpStr,
     112         896 :             RTL_TEXTENCODING_UTF8));
     113         896 :         GraphicObject aGrafObj(aUniqueID);
     114             :         // I don't call aGrafObj.GetXGraphic because it will call us back
     115             :         // into implLoadMemory ( with "private:memorygraphic" test )
     116         448 :         ::unographic::Graphic* pUnoGraphic = new ::unographic::Graphic;
     117         448 :         pUnoGraphic->init( aGrafObj.GetGraphic() );
     118         896 :         xRet = pUnoGraphic;
     119             :     }
     120        5871 :     return xRet;
     121             : }
     122             : 
     123      141949 : uno::Reference< ::graphic::XGraphic > GraphicProvider::implLoadMemory( const OUString& rResourceURL ) const
     124             : {
     125      141949 :     uno::Reference< ::graphic::XGraphic >   xRet;
     126      141949 :     sal_Int32                               nIndex = 0;
     127             : 
     128      141949 :     if( rResourceURL.getToken( 0, '/', nIndex ).equalsAscii( "private:memorygraphic" ) )
     129             :     {
     130      136078 :         sal_Int64 nGraphicAddress = rResourceURL.getToken( 0, '/', nIndex ).toInt64();
     131             : 
     132      136078 :         if( nGraphicAddress )
     133             :         {
     134      136078 :             ::unographic::Graphic* pUnoGraphic = new ::unographic::Graphic;
     135             : 
     136      136078 :             pUnoGraphic->init( *reinterpret_cast< ::Graphic* >( nGraphicAddress ) );
     137      136078 :             xRet = pUnoGraphic;
     138             :         }
     139             :     }
     140             : 
     141      141949 :     return xRet;
     142             : }
     143             : 
     144             : 
     145             : 
     146        5423 : uno::Reference< ::graphic::XGraphic > GraphicProvider::implLoadRepositoryImage( const OUString& rResourceURL ) const
     147             : {
     148        5423 :     uno::Reference< ::graphic::XGraphic >   xRet;
     149        5423 :     sal_Int32                               nIndex = 0;
     150             : 
     151        5423 :     if( rResourceURL.getToken( 0, '/', nIndex ).equalsAscii( "private:graphicrepository" ) )
     152             :     {
     153        5364 :         OUString sPathName( rResourceURL.copy( nIndex ) );
     154       10728 :         BitmapEx aBitmap;
     155        5364 :         if ( ::vcl::ImageRepository::loadImage( sPathName, aBitmap, false ) )
     156             :         {
     157        5364 :             Image aImage( aBitmap );
     158        5364 :             xRet = aImage.GetXGraphic();
     159        5364 :         }
     160             :     }
     161        5423 :     return xRet;
     162             : }
     163             : 
     164             : 
     165             : 
     166             : 
     167          59 : uno::Reference< ::graphic::XGraphic > GraphicProvider::implLoadStandardImage( const OUString& rResourceURL ) const
     168             : {
     169          59 :     uno::Reference< ::graphic::XGraphic >   xRet;
     170          59 :     sal_Int32                               nIndex = 0;
     171             : 
     172          59 :     if( rResourceURL.getToken( 0, '/', nIndex ).equalsAscii( "private:standardimage" ) )
     173             :     {
     174           0 :         OUString sImageName( rResourceURL.copy( nIndex ) );
     175           0 :         if ( sImageName == "info" )
     176             :         {
     177           0 :             xRet = InfoBox::GetStandardImage().GetXGraphic();
     178             :         }
     179           0 :         else if ( sImageName == "warning" )
     180             :         {
     181           0 :             xRet = WarningBox::GetStandardImage().GetXGraphic();
     182             :         }
     183           0 :         else if ( sImageName == "error" )
     184             :         {
     185           0 :             xRet = ErrorBox::GetStandardImage().GetXGraphic();
     186             :         }
     187           0 :         else if ( sImageName == "query" )
     188             :         {
     189           0 :             xRet = QueryBox::GetStandardImage().GetXGraphic();
     190           0 :         }
     191             :     }
     192          59 :     return xRet;
     193             : }
     194             : 
     195             : 
     196             : 
     197           0 : uno::Reference< ::graphic::XGraphic > GraphicProvider::implLoadBitmap( const uno::Reference< awt::XBitmap >& xBtm ) const
     198             : {
     199           0 :     uno::Reference< ::graphic::XGraphic > xRet;
     200           0 :     uno::Sequence< sal_Int8 > aBmpSeq( xBtm->getDIB() );
     201           0 :     uno::Sequence< sal_Int8 > aMaskSeq( xBtm->getMaskDIB() );
     202           0 :     SvMemoryStream aBmpStream( aBmpSeq.getArray(), aBmpSeq.getLength(), STREAM_READ );
     203           0 :     Bitmap aBmp;
     204           0 :     BitmapEx aBmpEx;
     205             : 
     206           0 :     ReadDIB(aBmp, aBmpStream, true);
     207             : 
     208           0 :     if( aMaskSeq.getLength() )
     209             :     {
     210           0 :         SvMemoryStream aMaskStream( aMaskSeq.getArray(), aMaskSeq.getLength(), STREAM_READ );
     211           0 :         Bitmap aMask;
     212             : 
     213           0 :         ReadDIB(aMask, aMaskStream, true);
     214           0 :         aBmpEx = BitmapEx( aBmp, aMask );
     215             :     }
     216             :     else
     217           0 :         aBmpEx = BitmapEx( aBmp );
     218             : 
     219           0 :     if( !aBmpEx.IsEmpty() )
     220             :     {
     221           0 :         ::unographic::Graphic* pUnoGraphic = new ::unographic::Graphic;
     222             : 
     223           0 :         pUnoGraphic->init( aBmpEx );
     224           0 :         xRet = pUnoGraphic;
     225             :     }
     226           0 :     return xRet;
     227             : }
     228             : 
     229             : 
     230             : 
     231        5423 : uno::Reference< ::graphic::XGraphic > GraphicProvider::implLoadResource( const OUString& rResourceURL ) const
     232             : {
     233        5423 :     uno::Reference< ::graphic::XGraphic >   xRet;
     234        5423 :     sal_Int32                               nIndex = 0;
     235             : 
     236        5423 :     if( rResourceURL.getToken( 0, '/', nIndex ).equalsAscii( "private:resource" ) )
     237             :     {
     238             :         OString aResMgrName(OUStringToOString(
     239           0 :             rResourceURL.getToken(0, '/', nIndex), RTL_TEXTENCODING_ASCII_US));
     240             : 
     241           0 :         boost::scoped_ptr<ResMgr> pResMgr(ResMgr::CreateResMgr( aResMgrName.getStr(), Application::GetSettings().GetUILanguageTag() ));
     242             : 
     243           0 :         if( pResMgr )
     244             :         {
     245           0 :             const OUString   aResourceType( rResourceURL.getToken( 0, '/', nIndex ) );
     246           0 :             const ResId             aResId( rResourceURL.getToken( 0, '/', nIndex ).toInt32(), *pResMgr );
     247             : 
     248           0 :             if( !aResourceType.isEmpty() )
     249             :             {
     250           0 :                 BitmapEx aBmpEx;
     251             : 
     252           0 :                 if( aResourceType.equalsAscii( "bitmap" ) ||
     253           0 :                     aResourceType.equalsAscii( "bitmapex" ) )
     254             :                 {
     255           0 :                     aResId.SetRT( RSC_BITMAP );
     256             : 
     257           0 :                     if( pResMgr->IsAvailable( aResId ) )
     258             :                     {
     259           0 :                         aBmpEx = BitmapEx( aResId );
     260             :                     }
     261             :                 }
     262           0 :                 else if( aResourceType.equalsAscii( "image" ) )
     263             :                 {
     264           0 :                     aResId.SetRT( RSC_IMAGE );
     265             : 
     266           0 :                     if( pResMgr->IsAvailable( aResId ) )
     267             :                     {
     268           0 :                         const Image aImage( aResId );
     269           0 :                         aBmpEx = aImage.GetBitmapEx();
     270             :                     }
     271             :                 }
     272           0 :                 else if( aResourceType.equalsAscii( "imagelist" ) )
     273             :                 {
     274           0 :                     aResId.SetRT( RSC_IMAGELIST );
     275             : 
     276           0 :                     if( pResMgr->IsAvailable( aResId ) )
     277             :                     {
     278           0 :                         const ImageList aImageList( aResId );
     279           0 :                         sal_Int32       nImageId = ( nIndex > -1 ) ? rResourceURL.getToken( 0, '/', nIndex ).toInt32() : 0;
     280             : 
     281           0 :                         if( 0 < nImageId )
     282             :                         {
     283           0 :                             const Image aImage( aImageList.GetImage( sal::static_int_cast< sal_uInt16 >(nImageId) ) );
     284           0 :                             aBmpEx = aImage.GetBitmapEx();
     285             :                         }
     286             :                         else
     287             :                         {
     288           0 :                             aBmpEx = aImageList.GetAsHorizontalStrip();
     289           0 :                         }
     290             :                     }
     291             :                 }
     292             : 
     293           0 :                 if( !aBmpEx.IsEmpty() )
     294             :                 {
     295           0 :                     ::unographic::Graphic* pUnoGraphic = new ::unographic::Graphic;
     296             : 
     297           0 :                     pUnoGraphic->init( aBmpEx );
     298           0 :                     xRet = pUnoGraphic;
     299           0 :                 }
     300           0 :             }
     301           0 :         }
     302             :     }
     303             : 
     304        5423 :     return xRet;
     305             : }
     306             : 
     307             : 
     308             : 
     309           0 : uno::Reference< beans::XPropertySet > SAL_CALL GraphicProvider::queryGraphicDescriptor( const uno::Sequence< beans::PropertyValue >& rMediaProperties )
     310             :     throw ( io::IOException, lang::IllegalArgumentException, lang::WrappedTargetException, uno::RuntimeException, std::exception)
     311             : {
     312           0 :     uno::Reference< beans::XPropertySet > xRet;
     313             : 
     314           0 :     OUString aURL;
     315           0 :     uno::Reference< io::XInputStream > xIStm;
     316           0 :     uno::Reference< awt::XBitmap >xBtm;
     317             : 
     318           0 :     for( sal_Int32 i = 0; ( i < rMediaProperties.getLength() ) && !xRet.is(); ++i )
     319             :     {
     320           0 :         const OUString   aName( rMediaProperties[ i ].Name );
     321           0 :         const uno::Any          aValue( rMediaProperties[ i ].Value );
     322             : 
     323           0 :         if (aName == "URL")
     324             :         {
     325           0 :             aValue >>= aURL;
     326             :         }
     327           0 :         else if (aName == "InputStream")
     328             :         {
     329           0 :             aValue >>= xIStm;
     330             :         }
     331           0 :         else if (aName == "Bitmap")
     332             :         {
     333           0 :             aValue >>= xBtm;
     334             :         }
     335           0 :     }
     336             : 
     337           0 :     SolarMutexGuard g;
     338             : 
     339           0 :     if( xIStm.is() )
     340             :     {
     341           0 :         unographic::GraphicDescriptor* pDescriptor = new unographic::GraphicDescriptor;
     342           0 :         pDescriptor->init( xIStm, aURL );
     343           0 :         xRet = pDescriptor;
     344             :     }
     345           0 :     else if( !aURL.isEmpty() )
     346             :     {
     347           0 :         uno::Reference< ::graphic::XGraphic > xGraphic( implLoadMemory( aURL ) );
     348           0 :         if( !xGraphic.is() )
     349           0 :             xGraphic = implLoadResource( aURL );
     350           0 :         if( !xGraphic.is() )
     351           0 :             xGraphic = implLoadGraphicObject( aURL );
     352             : 
     353           0 :         if ( !xGraphic.is() )
     354           0 :             xGraphic = implLoadRepositoryImage( aURL );
     355             : 
     356           0 :         if ( !xGraphic.is() )
     357           0 :             xGraphic = implLoadStandardImage( aURL );
     358             : 
     359           0 :         if( xGraphic.is() )
     360             :         {
     361           0 :             xRet = uno::Reference< beans::XPropertySet >( xGraphic, uno::UNO_QUERY );
     362             :         }
     363             :         else
     364             :         {
     365           0 :             unographic::GraphicDescriptor* pDescriptor = new unographic::GraphicDescriptor;
     366           0 :             pDescriptor->init( aURL );
     367           0 :             xRet = pDescriptor;
     368           0 :         }
     369             :     }
     370           0 :     else if( xBtm.is() )
     371             :     {
     372           0 :         uno::Reference< ::graphic::XGraphic > xGraphic( implLoadBitmap( xBtm ) );
     373           0 :         if( xGraphic.is() )
     374           0 :             xRet = uno::Reference< beans::XPropertySet >( xGraphic, uno::UNO_QUERY );
     375             :     }
     376             : 
     377           0 :     return xRet;
     378             : }
     379             : 
     380             : 
     381             : 
     382      143049 : uno::Reference< ::graphic::XGraphic > SAL_CALL GraphicProvider::queryGraphic( const uno::Sequence< ::beans::PropertyValue >& rMediaProperties )
     383             :     throw ( io::IOException, lang::IllegalArgumentException, lang::WrappedTargetException, uno::RuntimeException, std::exception)
     384             : {
     385      143049 :     uno::Reference< ::graphic::XGraphic >   xRet;
     386      286098 :     OUString                                aPath;
     387      286098 :     boost::scoped_ptr<SvStream>             pIStm;
     388             : 
     389      286098 :     uno::Reference< io::XInputStream > xIStm;
     390      286098 :     uno::Reference< awt::XBitmap >xBtm;
     391             : 
     392      286098 :     uno::Sequence< ::beans::PropertyValue > aFilterData;
     393             : 
     394      286112 :     for( sal_Int32 i = 0; ( i < rMediaProperties.getLength() ) && !pIStm && !xRet.is(); ++i )
     395             :     {
     396      143063 :         const OUString   aName( rMediaProperties[ i ].Name );
     397      286126 :         const uno::Any          aValue( rMediaProperties[ i ].Value );
     398             : 
     399      143063 :         if (aName == "URL")
     400             :         {
     401      142121 :             OUString aURL;
     402      142121 :             aValue >>= aURL;
     403      142121 :             aPath = aURL;
     404             :         }
     405         942 :         else if (aName == "InputStream")
     406             :         {
     407         928 :             aValue >>= xIStm;
     408             :         }
     409          14 :         else if (aName == "Bitmap")
     410             :         {
     411           0 :             aValue >>= xBtm;
     412             :         }
     413          14 :         else if (aName == "FilterData")
     414             :         {
     415          14 :             aValue >>= aFilterData;
     416             :         }
     417      143063 :     }
     418             : 
     419             :     // Check for the goal width and height if they are defined
     420      143049 :     sal_uInt16 nExtWidth = 0;
     421      143049 :     sal_uInt16 nExtHeight = 0;
     422      143049 :     sal_uInt16 nExtMapMode = 0;
     423      143091 :     for( sal_Int32 i = 0; i < aFilterData.getLength(); ++i )
     424             :     {
     425          42 :         const OUString   aName( aFilterData[ i ].Name );
     426          84 :         const uno::Any          aValue( aFilterData[ i ].Value );
     427             : 
     428          42 :         if (aName == "ExternalWidth")
     429             :         {
     430          14 :             aValue >>= nExtWidth;
     431             :         }
     432          28 :         else if (aName == "ExternalHeight")
     433             :         {
     434          14 :             aValue >>= nExtHeight;
     435             :         }
     436          14 :         else if (aName == "ExternalMapMode")
     437             :         {
     438          14 :             aValue >>= nExtMapMode;
     439             :         }
     440          42 :     }
     441             : 
     442      286098 :     SolarMutexGuard g;
     443             : 
     444      143049 :     if( xIStm.is() )
     445             :     {
     446         928 :         pIStm.reset(::utl::UcbStreamHelper::CreateStream( xIStm ));
     447             :     }
     448      142121 :     else if( !aPath.isEmpty() )
     449             :     {
     450      141949 :         xRet = implLoadMemory( aPath );
     451             : 
     452      141949 :         if( !xRet.is() )
     453        5871 :             xRet = implLoadGraphicObject( aPath );
     454             : 
     455      141949 :         if( !xRet.is() )
     456        5423 :             xRet = implLoadResource( aPath );
     457             : 
     458      141949 :         if ( !xRet.is() )
     459        5423 :             xRet = implLoadRepositoryImage( aPath );
     460             : 
     461      141949 :         if ( !xRet.is() )
     462          59 :             xRet = implLoadStandardImage( aPath );
     463             : 
     464      141949 :         if( !xRet.is() )
     465          59 :             pIStm.reset(::utl::UcbStreamHelper::CreateStream( aPath, STREAM_READ ));
     466             :     }
     467         172 :     else if( xBtm.is() )
     468             :     {
     469           0 :         xRet = implLoadBitmap( xBtm );
     470             :     }
     471             : 
     472      143049 :     if( pIStm )
     473             :     {
     474         987 :         ::GraphicFilter& rFilter = ::GraphicFilter::GetGraphicFilter();
     475             : 
     476             :         {
     477         987 :             ::Graphic aVCLGraphic;
     478             : 
     479             :             // Define APM Header if goal height and width are defined
     480         987 :             WMF_EXTERNALHEADER aExtHeader;
     481         987 :             aExtHeader.xExt = nExtWidth;
     482         987 :             aExtHeader.yExt = nExtHeight;
     483         987 :             aExtHeader.mapMode = nExtMapMode;
     484         987 :             WMF_EXTERNALHEADER *pExtHeader = NULL;
     485         987 :             if ( nExtMapMode > 0 )
     486          14 :                 pExtHeader = &aExtHeader;
     487             : 
     488        1974 :             if( ( rFilter.ImportGraphic( aVCLGraphic, aPath, *pIStm,
     489        1913 :                                          GRFILTER_FORMAT_DONTKNOW, NULL, 0, pExtHeader ) == GRFILTER_OK ) &&
     490         926 :                 ( aVCLGraphic.GetType() != GRAPHIC_NONE ) )
     491             :             {
     492         926 :                 ::unographic::Graphic* pUnoGraphic = new ::unographic::Graphic;
     493             : 
     494         926 :                 pUnoGraphic->init( aVCLGraphic );
     495         926 :                 xRet = pUnoGraphic;
     496         987 :             }
     497             :         }
     498             :     }
     499             : 
     500      286098 :     return xRet;
     501             : }
     502             : 
     503           2 : void ImplCalculateCropRect( ::Graphic& rGraphic, const text::GraphicCrop& rGraphicCropLogic, Rectangle& rGraphicCropPixel )
     504             : {
     505           2 :     if ( rGraphicCropLogic.Left || rGraphicCropLogic.Top || rGraphicCropLogic.Right || rGraphicCropLogic.Bottom )
     506             :     {
     507           0 :         Size aSourceSizePixel( rGraphic.GetSizePixel() );
     508           0 :         if ( aSourceSizePixel.Width() && aSourceSizePixel.Height() )
     509             :         {
     510           0 :             if ( rGraphicCropLogic.Left || rGraphicCropLogic.Top || rGraphicCropLogic.Right || rGraphicCropLogic.Bottom )
     511             :             {
     512           0 :                 Size aSize100thMM( 0, 0 );
     513           0 :                 if( rGraphic.GetPrefMapMode().GetMapUnit() != MAP_PIXEL )
     514             :                 {
     515           0 :                     aSize100thMM = OutputDevice::LogicToLogic( rGraphic.GetPrefSize(), rGraphic.GetPrefMapMode(), MAP_100TH_MM );
     516             :                 }
     517             :                 else
     518             :                 {
     519           0 :                     aSize100thMM = Application::GetDefaultDevice()->PixelToLogic( rGraphic.GetPrefSize(), MAP_100TH_MM );
     520             :                 }
     521           0 :                 if ( aSize100thMM.Width() && aSize100thMM.Height() )
     522             :                 {
     523           0 :                     double fSourceSizePixelWidth = static_cast<double>(aSourceSizePixel.Width());
     524           0 :                     double fSourceSizePixelHeight= static_cast<double>(aSourceSizePixel.Height());
     525           0 :                     rGraphicCropPixel.Left() = static_cast< sal_Int32 >((fSourceSizePixelWidth * rGraphicCropLogic.Left ) / aSize100thMM.Width());
     526           0 :                     rGraphicCropPixel.Top() = static_cast< sal_Int32 >((fSourceSizePixelHeight * rGraphicCropLogic.Top ) / aSize100thMM.Height());
     527           0 :                     rGraphicCropPixel.Right() = static_cast< sal_Int32 >(( fSourceSizePixelWidth * ( aSize100thMM.Width() - rGraphicCropLogic.Right ) ) / aSize100thMM.Width() );
     528           0 :                     rGraphicCropPixel.Bottom() = static_cast< sal_Int32 >(( fSourceSizePixelHeight * ( aSize100thMM.Height() - rGraphicCropLogic.Bottom ) ) / aSize100thMM.Height() );
     529             :                 }
     530             :             }
     531             :         }
     532             :     }
     533           2 : }
     534             : 
     535           2 : void ImplApplyBitmapScaling( ::Graphic& rGraphic, sal_Int32 nPixelWidth, sal_Int32 nPixelHeight )
     536             : {
     537           2 :     if ( nPixelWidth && nPixelHeight )
     538             :     {
     539           0 :         BitmapEx aBmpEx( rGraphic.GetBitmapEx() );
     540           0 :         MapMode aPrefMapMode( aBmpEx.GetPrefMapMode() );
     541           0 :         Size    aPrefSize( aBmpEx.GetPrefSize() );
     542           0 :         aBmpEx.Scale( Size( nPixelWidth, nPixelHeight ) );
     543           0 :         aBmpEx.SetPrefMapMode( aPrefMapMode );
     544           0 :         aBmpEx.SetPrefSize( aPrefSize );
     545           0 :         rGraphic = aBmpEx;
     546             :     }
     547           2 : }
     548             : 
     549           2 : void ImplApplyBitmapResolution( ::Graphic& rGraphic, sal_Int32 nImageResolution, const Size& rVisiblePixelSize, const awt::Size& rLogicalSize )
     550             : {
     551           2 :     if ( nImageResolution && rLogicalSize.Width && rLogicalSize.Height )
     552             :     {
     553           0 :         const double fImageResolution = static_cast<double>( nImageResolution );
     554           0 :         const double fSourceDPIX = ( static_cast<double>(rVisiblePixelSize.Width()) * 2540.0 ) / static_cast<double>(rLogicalSize.Width);
     555           0 :         const double fSourceDPIY = ( static_cast<double>(rVisiblePixelSize.Height()) * 2540.0 ) / static_cast<double>(rLogicalSize.Height);
     556           0 :         const sal_Int32 nSourcePixelWidth( rGraphic.GetSizePixel().Width() );
     557           0 :         const sal_Int32 nSourcePixelHeight( rGraphic.GetSizePixel().Height() );
     558           0 :         const double fSourcePixelWidth = static_cast<double>( nSourcePixelWidth );
     559           0 :         const double fSourcePixelHeight= static_cast<double>( nSourcePixelHeight );
     560             : 
     561           0 :         sal_Int32 nDestPixelWidth = nSourcePixelWidth;
     562           0 :         sal_Int32 nDestPixelHeight = nSourcePixelHeight;
     563             : 
     564             :         // check, if the bitmap DPI exceeds the maximum DPI
     565           0 :         if( fSourceDPIX > fImageResolution )
     566             :         {
     567           0 :             nDestPixelWidth = static_cast<sal_Int32>(( fSourcePixelWidth * fImageResolution ) / fSourceDPIX);
     568           0 :             if ( !nDestPixelWidth || ( nDestPixelWidth > nSourcePixelWidth ) )
     569           0 :                 nDestPixelWidth = nSourcePixelWidth;
     570             :         }
     571           0 :         if ( fSourceDPIY > fImageResolution )
     572             :         {
     573           0 :             nDestPixelHeight= static_cast<sal_Int32>(( fSourcePixelHeight* fImageResolution ) / fSourceDPIY);
     574           0 :             if ( !nDestPixelHeight || ( nDestPixelHeight > nSourcePixelHeight ) )
     575           0 :                 nDestPixelHeight = nSourcePixelHeight;
     576             :         }
     577           0 :         if ( ( nDestPixelWidth != nSourcePixelWidth ) || ( nDestPixelHeight != nSourcePixelHeight ) )
     578           0 :             ImplApplyBitmapScaling( rGraphic, nDestPixelWidth, nDestPixelHeight );
     579             :     }
     580           2 : }
     581             : 
     582           2 : void ImplApplyFilterData( ::Graphic& rGraphic, uno::Sequence< beans::PropertyValue >& rFilterData )
     583             : {
     584             :     /* this method applies following attributes to the graphic, in the first step the
     585             :        cropping area (logical size in 100thmm) is applied, in the second step the resolution
     586             :        is applied, in the third step the graphic is scaled to the corresponding pixelsize.
     587             :        if a parameter value is zero or not available the corresponding step will be skipped */
     588             : 
     589           2 :     sal_Int32 nPixelWidth = 0;
     590           2 :     sal_Int32 nPixelHeight= 0;
     591           2 :     sal_Int32 nImageResolution = 0;
     592           2 :     awt::Size aLogicalSize( 0, 0 );
     593           2 :     text::GraphicCrop aCropLogic( 0, 0, 0, 0 );
     594           2 :     bool bRemoveCropArea = true;
     595             : 
     596           2 :     for( sal_Int32 i = 0; i < rFilterData.getLength(); ++i )
     597             :     {
     598           0 :         const OUString   aName(  rFilterData[ i ].Name );
     599           0 :         const uno::Any          aValue( rFilterData[ i ].Value );
     600             : 
     601           0 :         if (aName == "PixelWidth")
     602           0 :             aValue >>= nPixelWidth;
     603           0 :         else if (aName == "PixelHeight")
     604           0 :             aValue >>= nPixelHeight;
     605           0 :         else if (aName == "LogicalSize")
     606           0 :             aValue >>= aLogicalSize;
     607           0 :         else if (aName == "GraphicCropLogic")
     608           0 :             aValue >>= aCropLogic;
     609           0 :         else if (aName == "RemoveCropArea")
     610           0 :             aValue >>= bRemoveCropArea;
     611           0 :         else if (aName == "ImageResolution")
     612           0 :             aValue >>= nImageResolution;
     613           0 :     }
     614           2 :     if ( rGraphic.GetType() == GRAPHIC_BITMAP )
     615             :     {
     616           2 :         if(rGraphic.getSvgData().get())
     617             :         {
     618             :             // embedded Svg, no need to scale. Also no method to apply crop data currently
     619             :         }
     620             :         else
     621             :         {
     622           2 :             Rectangle aCropPixel( Point( 0, 0 ), rGraphic.GetSizePixel() );
     623           2 :             ImplCalculateCropRect( rGraphic, aCropLogic, aCropPixel );
     624           2 :             if ( bRemoveCropArea )
     625             :             {
     626           2 :                 BitmapEx aBmpEx( rGraphic.GetBitmapEx() );
     627           2 :                 aBmpEx.Crop( aCropPixel );
     628           2 :                 rGraphic = aBmpEx;
     629             :             }
     630           2 :             Size aVisiblePixelSize( bRemoveCropArea ? rGraphic.GetSizePixel() : aCropPixel.GetSize() );
     631           2 :             ImplApplyBitmapResolution( rGraphic, nImageResolution, aVisiblePixelSize, aLogicalSize );
     632           2 :             ImplApplyBitmapScaling( rGraphic, nPixelWidth, nPixelHeight );
     633             :         }
     634             :     }
     635           0 :     else if ( ( rGraphic.GetType() == GRAPHIC_GDIMETAFILE ) && nImageResolution )
     636             :     {
     637           0 :         VirtualDevice aDummyVDev;
     638           0 :         GDIMetaFile aMtf( rGraphic.GetGDIMetaFile() );
     639           0 :         Size aMtfSize( OutputDevice::LogicToLogic( aMtf.GetPrefSize(), aMtf.GetPrefMapMode(), MAP_100TH_MM ) );
     640           0 :         if ( aMtfSize.Width() && aMtfSize.Height() )
     641             :         {
     642           0 :             MapMode aNewMapMode( MAP_100TH_MM );
     643           0 :             aNewMapMode.SetScaleX( static_cast< double >( aLogicalSize.Width ) / static_cast< double >( aMtfSize.Width() ) );
     644           0 :             aNewMapMode.SetScaleY( static_cast< double >( aLogicalSize.Height ) / static_cast< double >( aMtfSize.Height() ) );
     645           0 :             aDummyVDev.EnableOutput( false );
     646           0 :             aDummyVDev.SetMapMode( aNewMapMode );
     647             : 
     648           0 :             for( size_t i = 0, nObjCount = aMtf.GetActionSize(); i < nObjCount; i++ )
     649             :             {
     650           0 :                 MetaAction* pAction = aMtf.GetAction( i );
     651           0 :                 switch( pAction->GetType() )
     652             :                 {
     653             :                     // only optimizing common bitmap actions:
     654             :                     case( META_MAPMODE_ACTION ):
     655             :                     {
     656           0 :                         const_cast< MetaAction* >( pAction )->Execute( &aDummyVDev );
     657           0 :                         break;
     658             :                     }
     659             :                     case( META_PUSH_ACTION ):
     660             :                     {
     661           0 :                         const MetaPushAction* pA = static_cast<const MetaPushAction*>(pAction);
     662           0 :                         aDummyVDev.Push( pA->GetFlags() );
     663           0 :                         break;
     664             :                     }
     665             :                     case( META_POP_ACTION ):
     666             :                     {
     667           0 :                         aDummyVDev.Pop();
     668           0 :                         break;
     669             :                     }
     670             :                     case( META_BMPSCALE_ACTION ):
     671             :                     case( META_BMPEXSCALE_ACTION ):
     672             :                     {
     673           0 :                         BitmapEx aBmpEx;
     674           0 :                         Point aPos;
     675           0 :                         Size aSize;
     676           0 :                         if ( pAction->GetType() == META_BMPSCALE_ACTION )
     677             :                         {
     678           0 :                             MetaBmpScaleAction* pScaleAction = dynamic_cast< MetaBmpScaleAction* >( pAction );
     679           0 :                             aBmpEx = pScaleAction->GetBitmap();
     680           0 :                             aPos = pScaleAction->GetPoint();
     681           0 :                             aSize = pScaleAction->GetSize();
     682             :                         }
     683             :                         else
     684             :                         {
     685           0 :                             MetaBmpExScaleAction* pScaleAction = dynamic_cast< MetaBmpExScaleAction* >( pAction );
     686           0 :                             aBmpEx = pScaleAction->GetBitmapEx();
     687           0 :                             aPos = pScaleAction->GetPoint();
     688           0 :                             aSize = pScaleAction->GetSize();
     689             :                         }
     690           0 :                         ::Graphic aGraphic( aBmpEx );
     691           0 :                         const Size aSize100thmm( aDummyVDev.LogicToPixel( aSize ) );
     692           0 :                         Size aSize100thmm2( aDummyVDev.PixelToLogic( aSize100thmm, MAP_100TH_MM ) );
     693             : 
     694             :                         ImplApplyBitmapResolution( aGraphic, nImageResolution,
     695           0 :                             aGraphic.GetSizePixel(), awt::Size( aSize100thmm2.Width(), aSize100thmm2.Height() ) );
     696             : 
     697             :                         MetaAction* pNewAction;
     698           0 :                         if ( pAction->GetType() == META_BMPSCALE_ACTION )
     699           0 :                             pNewAction = new MetaBmpScaleAction ( aPos, aSize, aGraphic.GetBitmap() );
     700             :                         else
     701           0 :                             pNewAction = new MetaBmpExScaleAction( aPos, aSize, aGraphic.GetBitmapEx() );
     702             : 
     703           0 :                         MetaAction* pDeleteAction = aMtf.ReplaceAction( pNewAction, i );
     704           0 :                         if(pDeleteAction)
     705           0 :                             pDeleteAction->Delete();
     706           0 :                         break;
     707             :                     }
     708             :                     default:
     709             :                     case( META_BMP_ACTION ):
     710             :                     case( META_BMPSCALEPART_ACTION ):
     711             :                     case( META_BMPEX_ACTION ):
     712             :                     case( META_BMPEXSCALEPART_ACTION ):
     713             :                     case( META_MASK_ACTION ):
     714             :                     case( META_MASKSCALE_ACTION ):
     715           0 :                     break;
     716             :                 }
     717             :             }
     718           0 :             rGraphic = aMtf;
     719           0 :         }
     720             :     }
     721           2 : }
     722             : 
     723             : 
     724             : 
     725           2 : void SAL_CALL GraphicProvider::storeGraphic( const uno::Reference< ::graphic::XGraphic >& rxGraphic, const uno::Sequence< beans::PropertyValue >& rMediaProperties )
     726             :     throw ( io::IOException, lang::IllegalArgumentException, lang::WrappedTargetException, uno::RuntimeException, std::exception)
     727             : {
     728           2 :     SolarMutexGuard g;
     729             : 
     730           4 :     boost::scoped_ptr<SvStream> pOStm;
     731           4 :     OUString    aPath;
     732             :     sal_Int32   i;
     733             : 
     734           6 :     for( i = 0; ( i < rMediaProperties.getLength() ) && !pOStm; ++i )
     735             :     {
     736           4 :         const OUString   aName( rMediaProperties[ i ].Name );
     737           8 :         const uno::Any          aValue( rMediaProperties[ i ].Value );
     738             : 
     739           4 :         if (aName == "URL")
     740             :         {
     741           0 :             OUString aURL;
     742             : 
     743           0 :             aValue >>= aURL;
     744           0 :             pOStm.reset(::utl::UcbStreamHelper::CreateStream( aURL, STREAM_WRITE | STREAM_TRUNC ));
     745           0 :             aPath = aURL;
     746             :         }
     747           4 :         else if (aName == "OutputStream")
     748             :         {
     749           2 :             uno::Reference< io::XStream > xOStm;
     750             : 
     751           2 :             aValue >>= xOStm;
     752             : 
     753           2 :             if( xOStm.is() )
     754           2 :                 pOStm.reset(::utl::UcbStreamHelper::CreateStream( xOStm ));
     755             :         }
     756           4 :     }
     757             : 
     758           2 :     if( pOStm )
     759             :     {
     760           2 :         uno::Sequence< beans::PropertyValue >   aFilterDataSeq;
     761           2 :         const char*                             pFilterShortName = NULL;
     762             : 
     763           6 :         for( i = 0; i < rMediaProperties.getLength(); ++i )
     764             :         {
     765           4 :             const OUString   aName( rMediaProperties[ i ].Name );
     766           8 :             const uno::Any          aValue( rMediaProperties[ i ].Value );
     767             : 
     768           4 :             if (aName == "FilterData")
     769             :             {
     770           0 :                 aValue >>= aFilterDataSeq;
     771             :             }
     772           4 :             else if (aName == "MimeType")
     773             :             {
     774           2 :                 OUString aMimeType;
     775             : 
     776           2 :                 aValue >>= aMimeType;
     777             : 
     778           2 :                 if (aMimeType == MIMETYPE_BMP)
     779           0 :                     pFilterShortName = "bmp";
     780           2 :                 else if (aMimeType == MIMETYPE_EPS)
     781           0 :                     pFilterShortName = "eps";
     782           2 :                 else if (aMimeType == MIMETYPE_GIF)
     783           0 :                     pFilterShortName = "gif";
     784           2 :                 else if (aMimeType == MIMETYPE_JPG)
     785           0 :                     pFilterShortName = "jpg";
     786           2 :                 else if (aMimeType == MIMETYPE_MET)
     787           0 :                     pFilterShortName = "met";
     788           2 :                 else if (aMimeType == MIMETYPE_PNG)
     789           2 :                     pFilterShortName = "png";
     790           0 :                 else if (aMimeType == MIMETYPE_PCT)
     791           0 :                     pFilterShortName = "pct";
     792           0 :                 else if (aMimeType == MIMETYPE_PBM)
     793           0 :                     pFilterShortName = "pbm";
     794           0 :                 else if (aMimeType == MIMETYPE_PGM)
     795           0 :                     pFilterShortName = "pgm";
     796           0 :                 else if (aMimeType == MIMETYPE_PPM)
     797           0 :                     pFilterShortName = "ppm";
     798           0 :                 else if (aMimeType == MIMETYPE_RAS)
     799           0 :                     pFilterShortName = "ras";
     800           0 :                 else if (aMimeType == MIMETYPE_SVM)
     801           0 :                     pFilterShortName = "svm";
     802           0 :                 else if (aMimeType == MIMETYPE_TIF)
     803           0 :                     pFilterShortName = "tif";
     804           0 :                 else if (aMimeType == MIMETYPE_EMF)
     805           0 :                     pFilterShortName = "emf";
     806           0 :                 else if (aMimeType == MIMETYPE_WMF)
     807           0 :                     pFilterShortName = "wmf";
     808           0 :                 else if (aMimeType == MIMETYPE_XPM)
     809           0 :                     pFilterShortName = "xpm";
     810           0 :                 else if (aMimeType == MIMETYPE_SVG)
     811           0 :                     pFilterShortName = "svg";
     812           0 :                 else if (aMimeType == MIMETYPE_VCLGRAPHIC)
     813           0 :                     pFilterShortName = MIMETYPE_VCLGRAPHIC;
     814             :             }
     815           4 :         }
     816             : 
     817           2 :         if( pFilterShortName )
     818             :         {
     819           2 :             ::GraphicFilter& rFilter = ::GraphicFilter::GetGraphicFilter();
     820             : 
     821             :             {
     822           2 :                 const uno::Reference< XInterface >  xIFace( rxGraphic, uno::UNO_QUERY );
     823           2 :                 const ::Graphic*                    pGraphic = ::unographic::Graphic::getImplementation( xIFace );
     824             : 
     825           2 :                 if( pGraphic && ( pGraphic->GetType() != GRAPHIC_NONE ) )
     826             :                 {
     827           2 :                     ::Graphic aGraphic( *pGraphic );
     828           2 :                     ImplApplyFilterData( aGraphic, aFilterDataSeq );
     829             : 
     830             :                     /* sj: using a temporary memory stream, because some graphic filters are seeking behind
     831             :                        stream end (which leads to an invalid argument exception then). */
     832           4 :                     SvMemoryStream aMemStrm;
     833           2 :                     aMemStrm.SetVersion( SOFFICE_FILEFORMAT_CURRENT );
     834           2 :                     if( 0 == strcmp( pFilterShortName, MIMETYPE_VCLGRAPHIC ) )
     835           0 :                         WriteGraphic( aMemStrm, aGraphic );
     836             :                     else
     837             :                     {
     838             :                         rFilter.ExportGraphic( aGraphic, aPath, aMemStrm,
     839           4 :                                                 rFilter.GetExportFormatNumberForShortName( OUString::createFromAscii( pFilterShortName ) ),
     840           4 :                                                     ( aFilterDataSeq.getLength() ? &aFilterDataSeq : NULL ) );
     841             :                     }
     842           2 :                     aMemStrm.Seek( STREAM_SEEK_TO_END );
     843           4 :                     pOStm->Write( aMemStrm.GetData(), aMemStrm.Tell() );
     844           2 :                 }
     845             :             }
     846           2 :         }
     847           2 :     }
     848           2 : }
     849             : 
     850             : }
     851             : 
     852             : extern "C" SAL_DLLPUBLIC_EXPORT css::uno::XInterface * SAL_CALL
     853      145945 : com_sun_star_comp_graphic_GraphicProvider_get_implementation(
     854             :     css::uno::XComponentContext *,
     855             :     css::uno::Sequence<css::uno::Any> const &)
     856             : {
     857      145945 :     return cppu::acquire(new GraphicProvider);
     858        1227 : }
     859             : 
     860             : /* vim:set shiftwidth=4 softtabstop=4 expandtab: */

Generated by: LCOV version 1.10