diff options
Diffstat (limited to 'svtools')
-rw-r--r-- | svtools/Library_svt.mk | 9 | ||||
-rw-r--r-- | svtools/inc/pch/precompiled_svt.hxx | 2 | ||||
-rw-r--r-- | svtools/qa/unit/GraphicObjectTest.cxx | 2 | ||||
-rw-r--r-- | svtools/source/graphic/descriptor.cxx | 405 | ||||
-rw-r--r-- | svtools/source/graphic/descriptor.hxx | 120 | ||||
-rw-r--r-- | svtools/source/graphic/graphic.cxx | 206 | ||||
-rw-r--r-- | svtools/source/graphic/graphic.hxx | 87 | ||||
-rw-r--r-- | svtools/source/graphic/graphicunofactory.cxx | 118 | ||||
-rw-r--r-- | svtools/source/graphic/grfattr.cxx | 63 | ||||
-rw-r--r-- | svtools/source/graphic/grfcache.cxx | 1221 | ||||
-rw-r--r-- | svtools/source/graphic/grfcache.hxx | 136 | ||||
-rw-r--r-- | svtools/source/graphic/grfmgr.cxx | 1119 | ||||
-rw-r--r-- | svtools/source/graphic/grfmgr2.cxx | 2066 | ||||
-rw-r--r-- | svtools/source/graphic/provider.cxx | 847 | ||||
-rw-r--r-- | svtools/source/graphic/renderer.cxx | 11 | ||||
-rw-r--r-- | svtools/source/graphic/transformer.cxx | 152 | ||||
-rw-r--r-- | svtools/source/graphic/transformer.hxx | 59 | ||||
-rw-r--r-- | svtools/util/svt.component | 8 |
18 files changed, 6 insertions, 6625 deletions
diff --git a/svtools/Library_svt.mk b/svtools/Library_svt.mk index 263d2646b910..66cdda687dc6 100644 --- a/svtools/Library_svt.mk +++ b/svtools/Library_svt.mk @@ -150,16 +150,7 @@ $(eval $(call gb_Library_add_exception_objects,svt,\ svtools/source/filter/SvFilterOptionsDialog \ svtools/source/filter/DocumentToGraphicRenderer \ svtools/source/filter/exportdialog \ - svtools/source/graphic/descriptor \ - svtools/source/graphic/graphic \ - svtools/source/graphic/graphicunofactory \ - svtools/source/graphic/grfattr \ - svtools/source/graphic/grfcache \ - svtools/source/graphic/grfmgr \ - svtools/source/graphic/grfmgr2 \ - svtools/source/graphic/provider \ svtools/source/graphic/renderer \ - svtools/source/graphic/transformer \ svtools/source/hatchwindow/documentcloser \ svtools/source/hatchwindow/hatchwindow \ svtools/source/hatchwindow/hatchwindowfactory \ diff --git a/svtools/inc/pch/precompiled_svt.hxx b/svtools/inc/pch/precompiled_svt.hxx index 16029ba95cfa..d3ed09986710 100644 --- a/svtools/inc/pch/precompiled_svt.hxx +++ b/svtools/inc/pch/precompiled_svt.hxx @@ -120,6 +120,7 @@ #include <vcl/fntstyle.hxx> #include <vcl/font.hxx> #include <vcl/graph.hxx> +#include <vcl/GraphicObject.hxx> #include <vcl/graphicfilter.hxx> #include <vcl/help.hxx> #include <vcl/i18nhelp.hxx> @@ -415,7 +416,6 @@ #include <svtools/AccessibleBrowseBoxObjType.hxx> #include <svtools/brwbox.hxx> #include <svtools/colorcfg.hxx> -#include <svtools/grfmgr.hxx> #include <svtools/headbar.hxx> #include <svtools/htmlkywd.hxx> #include <svtools/htmltokn.h> diff --git a/svtools/qa/unit/GraphicObjectTest.cxx b/svtools/qa/unit/GraphicObjectTest.cxx index 44a677617091..ee119e46c793 100644 --- a/svtools/qa/unit/GraphicObjectTest.cxx +++ b/svtools/qa/unit/GraphicObjectTest.cxx @@ -11,7 +11,7 @@ #include <cppunit/extensions/HelperMacros.h> #include <cppunit/plugin/TestPlugIn.h> -#include <svtools/grfmgr.hxx> +#include <vcl/GraphicObject.hxx> #include <test/bootstrapfixture.hxx> diff --git a/svtools/source/graphic/descriptor.cxx b/svtools/source/graphic/descriptor.cxx deleted file mode 100644 index b6e630d44083..000000000000 --- a/svtools/source/graphic/descriptor.cxx +++ /dev/null @@ -1,405 +0,0 @@ -/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */ -/* - * This file is part of the LibreOffice project. - * - * This Source Code Form is subject to the terms of the Mozilla Public - * License, v. 2.0. If a copy of the MPL was not distributed with this - * file, You can obtain one at http://mozilla.org/MPL/2.0/. - * - * This file incorporates work covered by the following license notice: - * - * Licensed to the Apache Software Foundation (ASF) under one or more - * contributor license agreements. See the NOTICE file distributed - * with this work for additional information regarding copyright - * ownership. The ASF licenses this file to you under the Apache - * License, Version 2.0 (the "License"); you may not use this file - * except in compliance with the License. You may obtain a copy of - * the License at http://www.apache.org/licenses/LICENSE-2.0 . - */ - -#include "descriptor.hxx" - -#include <unotools/ucbstreamhelper.hxx> -#include <vcl/graphicfilter.hxx> -#include <svl/itemprop.hxx> -#include <comphelper/servicehelper.hxx> -#include <cppuhelper/supportsservice.hxx> - -#include <com/sun/star/beans/PropertyState.hpp> -#include <com/sun/star/beans/PropertyAttribute.hpp> -#include <com/sun/star/awt/Size.hpp> -#include <com/sun/star/graphic/GraphicType.hpp> - -#include <vcl/graph.hxx> -#include <vcl/svapp.hxx> -#include <memory> - - -enum class UnoGraphicProperty -{ - GraphicType = 1 - , MimeType = 2 - , SizePixel = 3 - , Size100thMM = 4 - , BitsPerPixel = 5 - , Transparent = 6 - , Alpha = 7 - , Animated = 8 -}; - - -using namespace ::com::sun::star; - -namespace unographic { - - -GraphicDescriptor::GraphicDescriptor() : - ::comphelper::PropertySetHelper( createPropertySetInfo() ), - mpGraphic( nullptr ), - meType( GraphicType::NONE ), - mnBitsPerPixel ( 0 ), - mbTransparent ( false ) -{ -} - -GraphicDescriptor::~GraphicDescriptor() - throw() -{ -} - -void GraphicDescriptor::init( const ::Graphic& rGraphic ) -{ - mpGraphic = &rGraphic; -} - -void GraphicDescriptor::init( const OUString& rURL ) -{ - std::unique_ptr<SvStream> pIStm(::utl::UcbStreamHelper::CreateStream( rURL, StreamMode::READ )); - - if( pIStm ) - implCreate( *pIStm, &rURL ); -} - -void GraphicDescriptor::init( const uno::Reference< io::XInputStream >& rxIStm, const OUString& rURL ) -{ - std::unique_ptr<SvStream> pIStm(::utl::UcbStreamHelper::CreateStream( rxIStm )); - - if( pIStm ) - implCreate( *pIStm, &rURL ); -} - -void GraphicDescriptor::implCreate( SvStream& rIStm, const OUString* pURL ) -{ - OUString aURL; - if( pURL ) - aURL = *pURL; - ::GraphicDescriptor aDescriptor( rIStm, &aURL ); - - mpGraphic = nullptr; - maMimeType.clear(); - meType = GraphicType::NONE; - mnBitsPerPixel = 0; - mbTransparent = false; - - if( !(aDescriptor.Detect( true ) && aDescriptor.GetFileFormat() != GraphicFileFormat::NOT) ) - return; - - const char* pMimeType = nullptr; - sal_uInt8 cType = graphic::GraphicType::EMPTY; - - switch( aDescriptor.GetFileFormat() ) - { - case GraphicFileFormat::BMP: pMimeType = MIMETYPE_BMP; cType = graphic::GraphicType::PIXEL; break; - case GraphicFileFormat::GIF: pMimeType = MIMETYPE_GIF; cType = graphic::GraphicType::PIXEL; break; - case GraphicFileFormat::JPG: pMimeType = MIMETYPE_JPG; cType = graphic::GraphicType::PIXEL; break; - case GraphicFileFormat::PCD: pMimeType = MIMETYPE_PCD; cType = graphic::GraphicType::PIXEL; break; - case GraphicFileFormat::PCX: pMimeType = MIMETYPE_PCX; cType = graphic::GraphicType::PIXEL; break; - case GraphicFileFormat::PNG: pMimeType = MIMETYPE_PNG; cType = graphic::GraphicType::PIXEL; break; - case GraphicFileFormat::TIF: pMimeType = MIMETYPE_TIF; cType = graphic::GraphicType::PIXEL; break; - case GraphicFileFormat::XBM: pMimeType = MIMETYPE_XBM; cType = graphic::GraphicType::PIXEL; break; - case GraphicFileFormat::XPM: pMimeType = MIMETYPE_XPM; cType = graphic::GraphicType::PIXEL; break; - case GraphicFileFormat::PBM: pMimeType = MIMETYPE_PBM; cType = graphic::GraphicType::PIXEL; break; - case GraphicFileFormat::PGM: pMimeType = MIMETYPE_PGM; cType = graphic::GraphicType::PIXEL; break; - case GraphicFileFormat::PPM: pMimeType = MIMETYPE_PPM; cType = graphic::GraphicType::PIXEL; break; - case GraphicFileFormat::RAS: pMimeType = MIMETYPE_RAS; cType = graphic::GraphicType::PIXEL; break; - case GraphicFileFormat::TGA: pMimeType = MIMETYPE_TGA; cType = graphic::GraphicType::PIXEL; break; - case GraphicFileFormat::PSD: pMimeType = MIMETYPE_PSD; cType = graphic::GraphicType::PIXEL; break; - - case GraphicFileFormat::EPS: pMimeType = MIMETYPE_EPS; cType = graphic::GraphicType::VECTOR; break; - case GraphicFileFormat::DXF: pMimeType = MIMETYPE_DXF; cType = graphic::GraphicType::VECTOR; break; - case GraphicFileFormat::MET: pMimeType = MIMETYPE_MET; cType = graphic::GraphicType::VECTOR; break; - case GraphicFileFormat::PCT: pMimeType = MIMETYPE_PCT; cType = graphic::GraphicType::VECTOR; break; - case GraphicFileFormat::SVM: pMimeType = MIMETYPE_SVM; cType = graphic::GraphicType::VECTOR; break; - case GraphicFileFormat::WMF: pMimeType = MIMETYPE_WMF; cType = graphic::GraphicType::VECTOR; break; - case GraphicFileFormat::EMF: pMimeType = MIMETYPE_EMF; cType = graphic::GraphicType::VECTOR; break; - case GraphicFileFormat::SVG: pMimeType = MIMETYPE_SVG; cType = graphic::GraphicType::VECTOR; break; - - default: - break; - } - - if( graphic::GraphicType::EMPTY != cType ) - { - meType = ( ( graphic::GraphicType::PIXEL == cType ) ? GraphicType::Bitmap : GraphicType::GdiMetafile ); - maMimeType = OUString( pMimeType, strlen(pMimeType), RTL_TEXTENCODING_ASCII_US ); - maSizePixel = aDescriptor.GetSizePixel(); - maSize100thMM = aDescriptor.GetSize_100TH_MM(); - mnBitsPerPixel = aDescriptor.GetBitsPerPixel(); - mbTransparent = ( graphic::GraphicType::VECTOR == cType ); - } -} - - -uno::Any SAL_CALL GraphicDescriptor::queryAggregation( const uno::Type & rType ) -{ - uno::Any aAny; - - if( rType == cppu::UnoType<lang::XServiceInfo>::get()) - aAny <<= uno::Reference< lang::XServiceInfo >(this); - else if( rType == cppu::UnoType<lang::XTypeProvider>::get()) - aAny <<= uno::Reference< lang::XTypeProvider >(this); - else if( rType == cppu::UnoType<beans::XPropertySet>::get()) - aAny <<= uno::Reference< beans::XPropertySet >(this); - else if( rType == cppu::UnoType<beans::XPropertyState>::get()) - aAny <<= uno::Reference< beans::XPropertyState >(this); - else if( rType == cppu::UnoType<beans::XMultiPropertySet>::get()) - aAny <<= uno::Reference< beans::XMultiPropertySet >(this); - else - aAny = OWeakAggObject::queryAggregation( rType ); - - return aAny; -} - - -uno::Any SAL_CALL GraphicDescriptor::queryInterface( const uno::Type & rType ) -{ - return OWeakAggObject::queryInterface( rType ); -} - - -void SAL_CALL GraphicDescriptor::acquire() - throw() -{ - OWeakAggObject::acquire(); -} - - -void SAL_CALL GraphicDescriptor::release() - throw() -{ - OWeakAggObject::release(); -} - - -OUString SAL_CALL GraphicDescriptor::getImplementationName() -{ - return OUString( "com.sun.star.comp.graphic.GraphicDescriptor" ); -} - -sal_Bool SAL_CALL GraphicDescriptor::supportsService( const OUString& ServiceName ) -{ - return cppu::supportsService(this, ServiceName); -} - - -uno::Sequence< OUString > SAL_CALL GraphicDescriptor::getSupportedServiceNames() -{ - return { "com.sun.star.graphic.GraphicDescriptor" }; -} - - -uno::Sequence< uno::Type > SAL_CALL GraphicDescriptor::getTypes() -{ - uno::Sequence< uno::Type > aTypes( 6 ); - uno::Type* pTypes = aTypes.getArray(); - - *pTypes++ = cppu::UnoType<uno::XAggregation>::get(); - *pTypes++ = cppu::UnoType<lang::XServiceInfo>::get(); - *pTypes++ = cppu::UnoType<lang::XTypeProvider>::get(); - *pTypes++ = cppu::UnoType<beans::XPropertySet>::get(); - *pTypes++ = cppu::UnoType<beans::XPropertyState>::get(); - *pTypes++ = cppu::UnoType<beans::XMultiPropertySet>::get(); - - return aTypes; -} - -uno::Sequence< sal_Int8 > SAL_CALL GraphicDescriptor::getImplementationId() -{ - return css::uno::Sequence<sal_Int8>(); -} - - -rtl::Reference<::comphelper::PropertySetInfo> GraphicDescriptor::createPropertySetInfo() -{ - static ::comphelper::PropertyMapEntry const aEntries[] = - { - { OUString( "GraphicType" ), static_cast< sal_Int32 >( UnoGraphicProperty::GraphicType ), cppu::UnoType< sal_Int8 >::get(), beans::PropertyAttribute::READONLY, 0 }, - { OUString( "MimeType" ), static_cast< sal_Int32 >( UnoGraphicProperty::MimeType ), cppu::UnoType< OUString >::get(), beans::PropertyAttribute::READONLY, 0 }, - { OUString( "SizePixel" ), static_cast< sal_Int32 >( UnoGraphicProperty::SizePixel ), cppu::UnoType< awt::Size >::get(), beans::PropertyAttribute::READONLY, 0 }, - { OUString( "Size100thMM" ), static_cast< sal_Int32 >( UnoGraphicProperty::Size100thMM ), cppu::UnoType< awt::Size >::get(), beans::PropertyAttribute::READONLY, 0 }, - { OUString( "BitsPerPixel" ), static_cast< sal_Int32 >( UnoGraphicProperty::BitsPerPixel ), cppu::UnoType< sal_uInt8 >::get(), beans::PropertyAttribute::READONLY, 0 }, - { OUString( "Transparent" ), static_cast< sal_Int32 >( UnoGraphicProperty::Transparent ), cppu::UnoType< sal_Bool >::get(), beans::PropertyAttribute::READONLY, 0 }, - { OUString( "Alpha" ), static_cast< sal_Int32 >( UnoGraphicProperty::Alpha ), cppu::UnoType< sal_Bool >::get(), beans::PropertyAttribute::READONLY, 0 }, - { OUString( "Animated" ), static_cast< sal_Int32 >( UnoGraphicProperty::Animated ), cppu::UnoType< sal_Bool >::get(), beans::PropertyAttribute::READONLY, 0 }, - { OUString(), 0, css::uno::Type(), 0, 0 } - }; - - return rtl::Reference<::comphelper::PropertySetInfo>( new ::comphelper::PropertySetInfo(aEntries) ); -} - - -void GraphicDescriptor::_setPropertyValues( const comphelper::PropertyMapEntry** /*ppEntries*/, const uno::Any* /*pValues*/ ) -{ - // we only have readonly attributes -} - - -void GraphicDescriptor::_getPropertyValues( const comphelper::PropertyMapEntry** ppEntries, uno::Any* pValues ) -{ - SolarMutexGuard aGuard; - - while( *ppEntries ) - { - UnoGraphicProperty theProperty = static_cast< UnoGraphicProperty >( (*ppEntries)->mnHandle ); - switch( theProperty ) - { - case UnoGraphicProperty::GraphicType: - { - const GraphicType eType( mpGraphic ? mpGraphic->GetType() : meType ); - - *pValues <<= ( eType == GraphicType::Bitmap ? graphic::GraphicType::PIXEL : - ( eType == GraphicType::GdiMetafile ? graphic::GraphicType::VECTOR : - graphic::GraphicType::EMPTY ) ); - } - break; - - case UnoGraphicProperty::MimeType: - { - OUString aMimeType; - - if( mpGraphic ) - { - if( mpGraphic->IsLink() ) - { - const char* pMimeType; - - switch( mpGraphic->GetLink().GetType() ) - { - case GfxLinkType::NativeGif: pMimeType = MIMETYPE_GIF; break; - - // #i15508# added BMP type for better exports (checked, works) - case GfxLinkType::NativeBmp: pMimeType = MIMETYPE_BMP; break; - - case GfxLinkType::NativeJpg: pMimeType = MIMETYPE_JPG; break; - case GfxLinkType::NativePng: pMimeType = MIMETYPE_PNG; break; - case GfxLinkType::NativeWmf: pMimeType = MIMETYPE_WMF; break; - case GfxLinkType::NativeMet: pMimeType = MIMETYPE_MET; break; - case GfxLinkType::NativePct: pMimeType = MIMETYPE_PCT; break; - - // added Svg mimetype support - case GfxLinkType::NativeSvg: pMimeType = MIMETYPE_SVG; break; - case GfxLinkType::NativePdf: pMimeType = MIMETYPE_PDF; break; - - default: - pMimeType = nullptr; - break; - } - - if( pMimeType ) - aMimeType = OUString::createFromAscii( pMimeType ); - } - - if( aMimeType.isEmpty() && ( mpGraphic->GetType() != GraphicType::NONE ) ) - aMimeType = MIMETYPE_VCLGRAPHIC; - } - else - aMimeType = maMimeType; - - *pValues <<= aMimeType; - } - break; - - case UnoGraphicProperty::SizePixel: - { - awt::Size aAWTSize( 0, 0 ); - - if( mpGraphic ) - { - if( mpGraphic->GetType() == GraphicType::Bitmap ) - { - const Size aSizePix( mpGraphic->GetBitmapEx().GetSizePixel() ); - aAWTSize = awt::Size( aSizePix.Width(), aSizePix.Height() ); - } - } - else - aAWTSize = awt::Size( maSizePixel.Width(), maSizePixel.Height() ); - - *pValues <<= aAWTSize; - } - break; - - case UnoGraphicProperty::Size100thMM: - { - awt::Size aAWTSize( 0, 0 ); - - if( mpGraphic ) - { - if( mpGraphic->GetPrefMapMode().GetMapUnit() != MapUnit::MapPixel ) - { - const Size aSizeLog( OutputDevice::LogicToLogic( - mpGraphic->GetPrefSize(), - mpGraphic->GetPrefMapMode(), - MapMode(MapUnit::Map100thMM)) ); - aAWTSize = awt::Size( aSizeLog.Width(), aSizeLog.Height() ); - } - } - else - aAWTSize = awt::Size( maSize100thMM.Width(), maSize100thMM.Height() ); - - *pValues <<= aAWTSize; - } - break; - - case UnoGraphicProperty::BitsPerPixel: - { - sal_uInt16 nBitsPerPixel = 0; - - if( mpGraphic ) - { - if( mpGraphic->GetType() == GraphicType::Bitmap ) - nBitsPerPixel = mpGraphic->GetBitmapEx().GetBitmap().GetBitCount(); - } - else - nBitsPerPixel = mnBitsPerPixel; - - *pValues <<= sal::static_int_cast< sal_Int8 >(nBitsPerPixel); - } - break; - - case UnoGraphicProperty::Transparent: - { - *pValues <<= mpGraphic ? mpGraphic->IsTransparent() : mbTransparent; - } - break; - - case UnoGraphicProperty::Alpha: - { - *pValues <<= mpGraphic && mpGraphic->IsAlpha(); - } - break; - - case UnoGraphicProperty::Animated: - { - *pValues <<= mpGraphic && mpGraphic->IsAnimated(); - } - break; - } - - ++ppEntries; - ++pValues; - } -} - -} - -/* vim:set shiftwidth=4 softtabstop=4 expandtab: */ diff --git a/svtools/source/graphic/descriptor.hxx b/svtools/source/graphic/descriptor.hxx deleted file mode 100644 index ba585702d205..000000000000 --- a/svtools/source/graphic/descriptor.hxx +++ /dev/null @@ -1,120 +0,0 @@ -/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */ -/* - * This file is part of the LibreOffice project. - * - * This Source Code Form is subject to the terms of the Mozilla Public - * License, v. 2.0. If a copy of the MPL was not distributed with this - * file, You can obtain one at http://mozilla.org/MPL/2.0/. - * - * This file incorporates work covered by the following license notice: - * - * Licensed to the Apache Software Foundation (ASF) under one or more - * contributor license agreements. See the NOTICE file distributed - * with this work for additional information regarding copyright - * ownership. The ASF licenses this file to you under the Apache - * License, Version 2.0 (the "License"); you may not use this file - * except in compliance with the License. You may obtain a copy of - * the License at http://www.apache.org/licenses/LICENSE-2.0 . - */ - -#ifndef INCLUDED_SVTOOLS_SOURCE_GRAPHIC_DESCRIPTOR_HXX -#define INCLUDED_SVTOOLS_SOURCE_GRAPHIC_DESCRIPTOR_HXX - -#include <comphelper/propertysethelper.hxx> -#include <com/sun/star/lang/XServiceInfo.hpp> - -#include <comphelper/propertysetinfo.hxx> -#include <vcl/graph.hxx> - -#define MIMETYPE_BMP "image/x-MS-bmp" -#define MIMETYPE_GIF "image/gif" -#define MIMETYPE_JPG "image/jpeg" -#define MIMETYPE_PCD "image/x-photo-cd" -#define MIMETYPE_PCX "image/x-pcx" -#define MIMETYPE_PNG "image/png" -#define MIMETYPE_TIF "image/tiff" -#define MIMETYPE_XBM "image/x-xbitmap" -#define MIMETYPE_XPM "image/x-xpixmap" -#define MIMETYPE_PBM "image/x-portable-bitmap" -#define MIMETYPE_PGM "image/x-portable-graymap" -#define MIMETYPE_PPM "image/x-portable-pixmap" -#define MIMETYPE_RAS "image/x-cmu-raster" -#define MIMETYPE_TGA "image/x-targa" -#define MIMETYPE_PSD "image/vnd.adobe.photoshop" -#define MIMETYPE_EPS "image/x-eps" -#define MIMETYPE_DXF "image/vnd.dxf" -#define MIMETYPE_MET "image/x-met" -#define MIMETYPE_PCT "image/x-pict" -#define MIMETYPE_SVM "image/x-svm" -#define MIMETYPE_WMF "image/x-wmf" -#define MIMETYPE_EMF "image/x-emf" -#define MIMETYPE_SVG "image/svg+xml" -#define MIMETYPE_PDF "application/pdf" -#define MIMETYPE_VCLGRAPHIC "image/x-vclgraphic" - -namespace comphelper { class PropertySetInfo; } -namespace com { namespace sun { namespace star { namespace io { class XInputStream; } } } } - -class Graphic; - -namespace unographic { - -class GraphicDescriptor : public ::cppu::OWeakAggObject, - public css::lang::XServiceInfo, - public css::lang::XTypeProvider, - public ::comphelper::PropertySetHelper -{ -public: - - GraphicDescriptor(); - virtual ~GraphicDescriptor() throw() override; - - void init( const ::Graphic& rGraphic ); - void init( const OUString& rURL ); - void init( const css::uno::Reference< css::io::XInputStream >& rxIStm, const OUString& rURL ); - -protected: - - static rtl::Reference<::comphelper::PropertySetInfo> createPropertySetInfo(); - - // XInterface - virtual css::uno::Any SAL_CALL queryAggregation( const css::uno::Type & rType ) override; - virtual css::uno::Any SAL_CALL queryInterface( const css::uno::Type & rType ) override; - virtual void SAL_CALL acquire() throw() override; - virtual void SAL_CALL release() throw() override; - - // XServiceInfo - virtual OUString SAL_CALL getImplementationName() override; - virtual sal_Bool SAL_CALL supportsService( const OUString& ServiceName ) override; - virtual css::uno::Sequence< OUString > SAL_CALL getSupportedServiceNames() override; - - // XTypeProvider - virtual css::uno::Sequence< css::uno::Type > SAL_CALL getTypes( ) override; - virtual css::uno::Sequence< sal_Int8 > SAL_CALL getImplementationId( ) override; - - // PropertySetHelper - virtual void _setPropertyValues( const comphelper::PropertyMapEntry** ppEntries, const css::uno::Any* pValues ) override; - virtual void _getPropertyValues( const comphelper::PropertyMapEntry** ppEntries, css::uno::Any* pValue ) override; - -private: - - const ::Graphic* mpGraphic; - GraphicType meType; - OUString maMimeType; - Size maSizePixel; - Size maSize100thMM; - sal_uInt16 mnBitsPerPixel; - bool mbTransparent; - - GraphicDescriptor( const GraphicDescriptor& rDescriptor ) = delete; - - GraphicDescriptor& operator=( const GraphicDescriptor& ) = delete; - - void implCreate( SvStream& rIStm, const OUString* pPath ); -}; - -} - -#endif - -/* vim:set shiftwidth=4 softtabstop=4 expandtab: */ diff --git a/svtools/source/graphic/graphic.cxx b/svtools/source/graphic/graphic.cxx deleted file mode 100644 index c2969d3cdf67..000000000000 --- a/svtools/source/graphic/graphic.cxx +++ /dev/null @@ -1,206 +0,0 @@ -/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */ -/* - * This file is part of the LibreOffice project. - * - * This Source Code Form is subject to the terms of the Mozilla Public - * License, v. 2.0. If a copy of the MPL was not distributed with this - * file, You can obtain one at http://mozilla.org/MPL/2.0/. - * - * This file incorporates work covered by the following license notice: - * - * Licensed to the Apache Software Foundation (ASF) under one or more - * contributor license agreements. See the NOTICE file distributed - * with this work for additional information regarding copyright - * ownership. The ASF licenses this file to you under the Apache - * License, Version 2.0 (the "License"); you may not use this file - * except in compliance with the License. You may obtain a copy of - * the License at http://www.apache.org/licenses/LICENSE-2.0 . - */ - -#include <vcl/svapp.hxx> -#include <com/sun/star/graphic/GraphicType.hpp> -#include <com/sun/star/graphic/XGraphicTransformer.hpp> -#include <vcl/dibtools.hxx> -#include "graphic.hxx" -#include <comphelper/servicehelper.hxx> -#include <cppuhelper/supportsservice.hxx> -#include <cppuhelper/queryinterface.hxx> -#include <string.h> - -using namespace com::sun::star; - -namespace unographic { - -Graphic::Graphic() : - maGraphic() -{ -} - -Graphic::~Graphic() throw() -{ -} - -void Graphic::init( const ::Graphic& rGraphic ) - throw() -{ - maGraphic = ::Graphic(rGraphic); - unographic::GraphicDescriptor::init(maGraphic); -} - -uno::Any SAL_CALL Graphic::queryAggregation( const uno::Type& rType ) -{ - uno::Any aAny; - if( rType == cppu::UnoType<graphic::XGraphic>::get()) - aAny <<= uno::Reference< graphic::XGraphic >( this ); - else if( rType == cppu::UnoType<awt::XBitmap>::get()) - aAny <<= uno::Reference< awt::XBitmap >( this ); - else if( rType == cppu::UnoType<lang::XUnoTunnel>::get()) - aAny <<= uno::Reference< lang::XUnoTunnel >(this); - else - aAny = ::unographic::GraphicDescriptor::queryAggregation( rType ); - - return aAny; -} - -uno::Any SAL_CALL Graphic::queryInterface( const uno::Type & rType ) -{ - css::uno::Any aReturn = ::unographic::GraphicDescriptor::queryInterface( rType ); - if ( !aReturn.hasValue() ) - aReturn = ::cppu::queryInterface ( rType, static_cast< graphic::XGraphicTransformer*>( this ) ); - return aReturn; -} - -void SAL_CALL Graphic::acquire() - throw() -{ - unographic::GraphicDescriptor::acquire(); -} - -void SAL_CALL Graphic::release() throw() -{ - unographic::GraphicDescriptor::release(); -} - -OUString SAL_CALL Graphic::getImplementationName() -{ - return OUString( "com.sun.star.comp.graphic.Graphic" ); -} - -sal_Bool SAL_CALL Graphic::supportsService( const OUString& rServiceName ) -{ - return cppu::supportsService( this, rServiceName ); -} - -uno::Sequence< OUString > SAL_CALL Graphic::getSupportedServiceNames() -{ - uno::Sequence< OUString > aRet( ::unographic::GraphicDescriptor::getSupportedServiceNames() ); - uno::Sequence< OUString > aNew { "com.sun.star.graphic.Graphic" }; - sal_Int32 nOldCount = aRet.getLength(); - - aRet.realloc( nOldCount + aNew.getLength() ); - - for( sal_Int32 i = 0; i < aNew.getLength(); ++i ) - aRet[ nOldCount++ ] = aNew[ i ]; - - return aRet; -} - -uno::Sequence< uno::Type > SAL_CALL Graphic::getTypes() -{ - uno::Sequence< uno::Type > aRet( ::unographic::GraphicDescriptor::getTypes() ); - sal_Int32 nOldCount = aRet.getLength(); - - aRet.realloc( nOldCount + 2 ); - aRet[ nOldCount ] = cppu::UnoType<graphic::XGraphic>::get(); - aRet[ nOldCount+1 ] = cppu::UnoType<awt::XBitmap>::get(); - - return aRet; -} - -uno::Sequence< sal_Int8 > SAL_CALL Graphic::getImplementationId() -{ - return css::uno::Sequence<sal_Int8>(); -} - -sal_Int8 SAL_CALL Graphic::getType() -{ - sal_Int8 cRet = graphic::GraphicType::EMPTY; - - if (!!maGraphic) - { - ::GraphicType eType = maGraphic.GetType(); - - if (eType != ::GraphicType::NONE) - { - cRet = (eType == ::GraphicType::Bitmap) ? graphic::GraphicType::PIXEL - : graphic::GraphicType::VECTOR; - } - } - - return cRet; -} - -// XBitmap - -awt::Size SAL_CALL Graphic::getSize() -{ - SolarMutexGuard aGuard; - - Size aVclSize; - if (!!maGraphic && maGraphic.GetType() != ::GraphicType::NONE) - { - aVclSize = maGraphic.GetSizePixel(); - } - return awt::Size(aVclSize.Width(), aVclSize.Height()); -} - -uno::Sequence<sal_Int8> SAL_CALL Graphic::getDIB() -{ - SolarMutexGuard aGuard; - - if (!!maGraphic && maGraphic.GetType() != ::GraphicType::NONE) - { - SvMemoryStream aMemoryStream; - - WriteDIB(maGraphic.GetBitmapEx().GetBitmap(), aMemoryStream, false, true); - return css::uno::Sequence<sal_Int8>(static_cast<sal_Int8 const *>(aMemoryStream.GetData()), aMemoryStream.Tell()); - } - else - { - return uno::Sequence<sal_Int8>(); - } -} - -uno::Sequence<sal_Int8> SAL_CALL Graphic::getMaskDIB() -{ - SolarMutexGuard aGuard; - - if (!!maGraphic && maGraphic.GetType() != ::GraphicType::NONE) - { - SvMemoryStream aMemoryStream; - - WriteDIB(maGraphic.GetBitmapEx().GetMask(), aMemoryStream, false, true); - return css::uno::Sequence<sal_Int8>( static_cast<sal_Int8 const *>(aMemoryStream.GetData()), aMemoryStream.Tell() ); - } - else - { - return uno::Sequence<sal_Int8>(); - } -} - -const ::Graphic* Graphic::getImplementation( const uno::Reference< uno::XInterface >& rxIFace ) - throw() -{ - uno::Reference< lang::XUnoTunnel > xTunnel( rxIFace, uno::UNO_QUERY ); - return( xTunnel.is() ? reinterpret_cast< ::Graphic* >( xTunnel->getSomething( ::Graphic::getUnoTunnelId() ) ) : nullptr ); -} - -sal_Int64 SAL_CALL Graphic::getSomething( const uno::Sequence< sal_Int8 >& rId ) -{ - return( ( rId.getLength() == 16 && 0 == memcmp( ::Graphic::getUnoTunnelId().getConstArray(), rId.getConstArray(), 16 ) ) ? - reinterpret_cast<sal_Int64>(&maGraphic) : 0 ); -} - -} - -/* vim:set shiftwidth=4 softtabstop=4 expandtab: */ diff --git a/svtools/source/graphic/graphic.hxx b/svtools/source/graphic/graphic.hxx deleted file mode 100644 index 3f550fb733e1..000000000000 --- a/svtools/source/graphic/graphic.hxx +++ /dev/null @@ -1,87 +0,0 @@ -/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */ -/* - * This file is part of the LibreOffice project. - * - * This Source Code Form is subject to the terms of the Mozilla Public - * License, v. 2.0. If a copy of the MPL was not distributed with this - * file, You can obtain one at http://mozilla.org/MPL/2.0/. - * - * This file incorporates work covered by the following license notice: - * - * Licensed to the Apache Software Foundation (ASF) under one or more - * contributor license agreements. See the NOTICE file distributed - * with this work for additional information regarding copyright - * ownership. The ASF licenses this file to you under the Apache - * License, Version 2.0 (the "License"); you may not use this file - * except in compliance with the License. You may obtain a copy of - * the License at http://www.apache.org/licenses/LICENSE-2.0 . - */ - -#ifndef INCLUDED_SVTOOLS_SOURCE_GRAPHIC_GRAPHIC_HXX -#define INCLUDED_SVTOOLS_SOURCE_GRAPHIC_GRAPHIC_HXX - -#include <com/sun/star/lang/XServiceInfo.hpp> -#include <com/sun/star/graphic/XGraphic.hpp> -#include <com/sun/star/lang/XUnoTunnel.hpp> -#include <com/sun/star/awt/XBitmap.hpp> - -#include "descriptor.hxx" -#include "transformer.hxx" - -#include <vcl/graph.hxx> - -namespace unographic { - -class Graphic : public css::graphic::XGraphic, - public css::awt::XBitmap, - public css::lang::XUnoTunnel, - public ::unographic::GraphicDescriptor, - public ::unographic::GraphicTransformer -{ -public: - Graphic(); - virtual ~Graphic() throw() override; - - using ::unographic::GraphicDescriptor::init; - void init( const ::Graphic& rGraphic ) throw(); - - static const ::Graphic* getImplementation( const css::uno::Reference< css::uno::XInterface >& rxIFace ) throw(); - -protected: - - // XInterface - virtual css::uno::Any SAL_CALL queryAggregation( const css::uno::Type & rType ) override; - virtual css::uno::Any SAL_CALL queryInterface( const css::uno::Type & rType ) override; - virtual void SAL_CALL acquire() throw() override; - virtual void SAL_CALL release() throw() override; - - // XServiceInfo - virtual OUString SAL_CALL getImplementationName() override; - virtual sal_Bool SAL_CALL supportsService( const OUString& ServiceName ) override; - virtual css::uno::Sequence< OUString > SAL_CALL getSupportedServiceNames() override; - - // XTypeProvider - virtual css::uno::Sequence< css::uno::Type > SAL_CALL getTypes( ) override; - virtual css::uno::Sequence< sal_Int8 > SAL_CALL getImplementationId( ) override; - - // XGraphic - virtual ::sal_Int8 SAL_CALL getType( ) override; - - // XBitmap - virtual css::awt::Size SAL_CALL getSize( ) override; - virtual css::uno::Sequence< ::sal_Int8 > SAL_CALL getDIB( ) override; - virtual css::uno::Sequence< ::sal_Int8 > SAL_CALL getMaskDIB( ) override; - - // XUnoTunnel - virtual sal_Int64 SAL_CALL getSomething( const css::uno::Sequence< sal_Int8 >& rId ) override; - -private: - - ::Graphic maGraphic; -}; - -} - -#endif - -/* vim:set shiftwidth=4 softtabstop=4 expandtab: */ diff --git a/svtools/source/graphic/graphicunofactory.cxx b/svtools/source/graphic/graphicunofactory.cxx deleted file mode 100644 index 18553092edf5..000000000000 --- a/svtools/source/graphic/graphicunofactory.cxx +++ /dev/null @@ -1,118 +0,0 @@ -/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */ -/* - * This file is part of the LibreOffice project. - * - * This Source Code Form is subject to the terms of the Mozilla Public - * License, v. 2.0. If a copy of the MPL was not distributed with this - * file, You can obtain one at http://mozilla.org/MPL/2.0/. - * - * This file incorporates work covered by the following license notice: - * - * Licensed to the Apache Software Foundation (ASF) under one or more - * contributor license agreements. See the NOTICE file distributed - * with this work for additional information regarding copyright - * ownership. The ASF licenses this file to you under the Apache - * License, Version 2.0 (the "License"); you may not use this file - * except in compliance with the License. You may obtain a copy of - * the License at http://www.apache.org/licenses/LICENSE-2.0 . - */ - -#include <memory> -#include <cppuhelper/implbase.hxx> -#include <cppuhelper/supportsservice.hxx> -#include <com/sun/star/graphic/XGraphicObject.hpp> -#include <com/sun/star/lang/IllegalArgumentException.hpp> -#include <com/sun/star/lang/XServiceInfo.hpp> -#include <com/sun/star/uno/XComponentContext.hpp> -#include <svtools/grfmgr.hxx> -#include <rtl/ref.hxx> - -using namespace com::sun::star; - -namespace { - -typedef ::cppu::WeakImplHelper< graphic::XGraphicObject, css::lang::XServiceInfo > GObjectAccess_BASE; - // Simple uno wrapper around the GraphicObject class to allow basic - // access. ( and solves a horrible cyclic link problem between - // goodies/toolkit/extensions ) -class GObjectImpl : public GObjectAccess_BASE -{ - ::osl::Mutex m_aMutex; - std::unique_ptr< GraphicObject > mpGObject; -public: - /// @throws uno::RuntimeException - explicit GObjectImpl(uno::Sequence< uno::Any > const & args); - - // XGraphicObject - virtual uno::Reference< graphic::XGraphic > SAL_CALL getGraphic() override; - virtual void SAL_CALL setGraphic( const uno::Reference< graphic::XGraphic >& _graphic ) override; - OUString SAL_CALL getUniqueID() override; - - virtual OUString SAL_CALL getImplementationName() override - { - return OUString("com.sun.star.graphic.GraphicObject"); - } - - virtual sal_Bool SAL_CALL supportsService(OUString const & ServiceName) override - { - return cppu::supportsService(this, ServiceName); - } - - virtual css::uno::Sequence<OUString> SAL_CALL getSupportedServiceNames() override - { - uno::Sequence<OUString> aRet { "com.sun.star.graphic.GraphicObject" }; - return aRet; - } -}; - -GObjectImpl::GObjectImpl(const uno::Sequence< uno::Any >& args) -{ - if ( args.getLength() == 1 ) - { - OUString sId; - if ( !( args[ 0 ] >>= sId ) || sId.isEmpty() ) - throw lang::IllegalArgumentException(); - OString bsId(OUStringToOString(sId, RTL_TEXTENCODING_UTF8)); - mpGObject.reset( new GraphicObject( bsId ) ); - } - else - mpGObject.reset( new GraphicObject() ); -} - -uno::Reference< graphic::XGraphic > SAL_CALL GObjectImpl::getGraphic() -{ - ::osl::MutexGuard aGuard( m_aMutex ); - if ( !mpGObject.get() ) - throw uno::RuntimeException(); - return mpGObject->GetGraphic().GetXGraphic(); -} - -void SAL_CALL GObjectImpl::setGraphic( const uno::Reference< graphic::XGraphic >& _graphic ) -{ - ::osl::MutexGuard aGuard( m_aMutex ); - if ( !mpGObject.get() ) - throw uno::RuntimeException(); - Graphic aGraphic( _graphic ); - mpGObject->SetGraphic( aGraphic ); -} - -OUString SAL_CALL GObjectImpl::getUniqueID() -{ - ::osl::MutexGuard aGuard( m_aMutex ); - OUString sId; - if ( mpGObject.get() ) - sId = OStringToOUString(mpGObject->GetUniqueID(), RTL_TEXTENCODING_ASCII_US); - return sId; -} - -} - -extern "C" SAL_DLLPUBLIC_EXPORT css::uno::XInterface * -com_sun_star_graphic_GraphicObject_get_implementation( - SAL_UNUSED_PARAMETER css::uno::XComponentContext *, - css::uno::Sequence<css::uno::Any> const &arguments) -{ - return cppu::acquire(new GObjectImpl(arguments)); -} - -/* vim:set shiftwidth=4 softtabstop=4 expandtab: */ diff --git a/svtools/source/graphic/grfattr.cxx b/svtools/source/graphic/grfattr.cxx deleted file mode 100644 index df6ebaaf3431..000000000000 --- a/svtools/source/graphic/grfattr.cxx +++ /dev/null @@ -1,63 +0,0 @@ -/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */ -/* - * This file is part of the LibreOffice project. - * - * This Source Code Form is subject to the terms of the Mozilla Public - * License, v. 2.0. If a copy of the MPL was not distributed with this - * file, You can obtain one at http://mozilla.org/MPL/2.0/. - * - * This file incorporates work covered by the following license notice: - * - * Licensed to the Apache Software Foundation (ASF) under one or more - * contributor license agreements. See the NOTICE file distributed - * with this work for additional information regarding copyright - * ownership. The ASF licenses this file to you under the Apache - * License, Version 2.0 (the "License"); you may not use this file - * except in compliance with the License. You may obtain a copy of - * the License at http://www.apache.org/licenses/LICENSE-2.0 . - */ - - -#include <tools/vcompat.hxx> -#include <svtools/grfmgr.hxx> - - -GraphicAttr::GraphicAttr() : - mfGamma ( 1.0 ), - mnMirrFlags ( BmpMirrorFlags::NONE ), - mnLeftCrop ( 0 ), - mnTopCrop ( 0 ), - mnRightCrop ( 0 ), - mnBottomCrop ( 0 ), - mnRotate10 ( 0 ), - mnContPercent ( 0 ), - mnLumPercent ( 0 ), - mnRPercent ( 0 ), - mnGPercent ( 0 ), - mnBPercent ( 0 ), - mbInvert ( false ), - mcTransparency ( 0 ), - meDrawMode ( GraphicDrawMode::Standard ) -{ -} - -bool GraphicAttr::operator==( const GraphicAttr& rAttr ) const -{ - return( ( mfGamma == rAttr.mfGamma ) && - ( mnMirrFlags == rAttr.mnMirrFlags ) && - ( mnLeftCrop == rAttr.mnLeftCrop ) && - ( mnTopCrop == rAttr.mnTopCrop ) && - ( mnRightCrop == rAttr.mnRightCrop ) && - ( mnBottomCrop == rAttr.mnBottomCrop ) && - ( mnRotate10 == rAttr.mnRotate10 ) && - ( mnContPercent == rAttr.mnContPercent ) && - ( mnLumPercent == rAttr.mnLumPercent ) && - ( mnRPercent == rAttr.mnRPercent ) && - ( mnGPercent == rAttr.mnGPercent ) && - ( mnBPercent == rAttr.mnBPercent ) && - ( mbInvert == rAttr.mbInvert ) && - ( mcTransparency == rAttr.mcTransparency ) && - ( meDrawMode == rAttr.meDrawMode ) ); -} - -/* vim:set shiftwidth=4 softtabstop=4 expandtab: */ diff --git a/svtools/source/graphic/grfcache.cxx b/svtools/source/graphic/grfcache.cxx deleted file mode 100644 index 430c2318888b..000000000000 --- a/svtools/source/graphic/grfcache.cxx +++ /dev/null @@ -1,1221 +0,0 @@ -/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */ -/* - * This file is part of the LibreOffice project. - * - * This Source Code Form is subject to the terms of the Mozilla Public - * License, v. 2.0. If a copy of the MPL was not distributed with this - * file, You can obtain one at http://mozilla.org/MPL/2.0/. - * - * This file incorporates work covered by the following license notice: - * - * Licensed to the Apache Software Foundation (ASF) under one or more - * contributor license agreements. See the NOTICE file distributed - * with this work for additional information regarding copyright - * ownership. The ASF licenses this file to you under the Apache - * License, Version 2.0 (the "License"); you may not use this file - * except in compliance with the License. You may obtain a copy of - * the License at http://www.apache.org/licenses/LICENSE-2.0 . - */ - -#include <sal/config.h> - -#include <cstdlib> - -#include <salhelper/timer.hxx> -#include <svtools/grfmgr.hxx> -#include <tools/debug.hxx> -#include <vcl/metaact.hxx> -#include <vcl/outdev.hxx> -#include <tools/poly.hxx> -#include <rtl/strbuf.hxx> -#include "grfcache.hxx" -#include <rtl/crc.h> -#include <memory> - -#define MAX_BMP_EXTENT 4096 - -using namespace com::sun::star; - -static const char aHexData[] = { '0', '1', '2', '3', '4', '5', '6', '7', '8', '9', 'A', 'B', 'C', 'D', 'E', 'F' }; - -class GraphicID -{ -private: - - sal_uInt32 mnID1; - sal_uInt32 mnID2; - sal_uInt32 mnID3; - BitmapChecksum mnID4; - -public: - explicit GraphicID( const GraphicObject& rObj ); - - bool operator==( const GraphicID& rID ) const - { - return( rID.mnID1 == mnID1 && rID.mnID2 == mnID2 && - rID.mnID3 == mnID3 && rID.mnID4 == mnID4 ); - } - - OString GetIDString() const; - bool IsEmpty() const { return( 0 == mnID4 ); } -}; - -GraphicID::GraphicID( const GraphicObject& rObj ) -{ - const Graphic& rGraphic = rObj.GetGraphic(); - - mnID1 = static_cast<sal_uLong>(rGraphic.GetType()) << 28; - - switch( rGraphic.GetType() ) - { - case GraphicType::Bitmap: - { - if(rGraphic.getVectorGraphicData().get()) - { - const VectorGraphicDataPtr& rVectorGraphicDataPtr = rGraphic.getVectorGraphicData(); - const basegfx::B2DRange& rRange = rVectorGraphicDataPtr->getRange(); - - mnID1 |= rVectorGraphicDataPtr->getVectorGraphicDataArrayLength(); - mnID2 = basegfx::fround(rRange.getWidth()); - mnID3 = basegfx::fround(rRange.getHeight()); - mnID4 = vcl_get_checksum(0, rVectorGraphicDataPtr->getVectorGraphicDataArray().getConstArray(), rVectorGraphicDataPtr->getVectorGraphicDataArrayLength()); - } - else if( rGraphic.IsAnimated() ) - { - const Animation aAnimation( rGraphic.GetAnimation() ); - - mnID1 |= ( aAnimation.Count() & 0x0fffffff ); - mnID2 = aAnimation.GetDisplaySizePixel().Width(); - mnID3 = aAnimation.GetDisplaySizePixel().Height(); - mnID4 = rGraphic.GetChecksum(); - } - else - { - const BitmapEx aBmpEx( rGraphic.GetBitmapEx() ); - - mnID1 |= ( ( ( static_cast<sal_uLong>(aBmpEx.GetTransparentType()) << 8 ) | ( aBmpEx.IsAlpha() ? 1 : 0 ) ) & 0x0fffffff ); - mnID2 = aBmpEx.GetSizePixel().Width(); - mnID3 = aBmpEx.GetSizePixel().Height(); - mnID4 = rGraphic.GetChecksum(); - } - } - break; - - case GraphicType::GdiMetafile: - { - const GDIMetaFile& rMtf = rGraphic.GetGDIMetaFile(); - - mnID1 |= ( rMtf.GetActionSize() & 0x0fffffff ); - mnID2 = rMtf.GetPrefSize().Width(); - mnID3 = rMtf.GetPrefSize().Height(); - mnID4 = rGraphic.GetChecksum(); - } - break; - - default: - mnID2 = mnID3 = mnID4 = 0; - break; - } -} - -OString GraphicID::GetIDString() const -{ - OStringBuffer aHexStr; - sal_Int32 nShift, nIndex = 0; - aHexStr.setLength(24 + (2 * BITMAP_CHECKSUM_SIZE)); - - for( nShift = 28; nShift >= 0; nShift -= 4 ) - aHexStr[nIndex++] = aHexData[ ( mnID1 >> static_cast<sal_uInt32>(nShift) ) & 0xf ]; - - for( nShift = 28; nShift >= 0; nShift -= 4 ) - aHexStr[nIndex++] = aHexData[ ( mnID2 >> static_cast<sal_uInt32>(nShift) ) & 0xf ]; - - for( nShift = 28; nShift >= 0; nShift -= 4 ) - aHexStr[nIndex++] = aHexData[ ( mnID3 >> static_cast<sal_uInt32>(nShift) ) & 0xf ]; - - for( nShift = ( 8 * BITMAP_CHECKSUM_SIZE ) - 4; nShift >= 0; nShift -= 4 ) - aHexStr[nIndex++] = aHexData[ ( mnID4 >> static_cast<sal_uInt32>(nShift) ) & 0xf ]; - - return aHexStr.makeStringAndClear(); -} - -class GraphicCacheEntry -{ -private: - - std::vector< GraphicObject* > maGraphicObjectList; - - GraphicID maID; - GfxLink maGfxLink; - std::unique_ptr<BitmapEx> mpBmpEx; - std::unique_ptr<GDIMetaFile> mpMtf; - std::unique_ptr<Animation> mpAnimation; - bool mbSwappedAll; - - // VectorGraphicData support - VectorGraphicDataPtr maVectorGraphicData; - uno::Sequence<sal_Int8> maPdfData; - - bool ImplInit( const GraphicObject& rObj ); - void ImplFillSubstitute( Graphic& rSubstitute ); - -public: - - explicit GraphicCacheEntry( const GraphicObject& rObj ); - ~GraphicCacheEntry(); - - const GraphicID& GetID() const { return maID; } - - void AddGraphicObjectReference( const GraphicObject& rObj, Graphic& rSubstitute ); - bool ReleaseGraphicObjectReference( const GraphicObject& rObj ); - size_t GetGraphicObjectReferenceCount() { return maGraphicObjectList.size(); } - bool HasGraphicObjectReference( const GraphicObject& rObj ); - - void TryToSwapIn(); - void GraphicObjectWasSwappedOut(); - void GraphicObjectWasSwappedIn( const GraphicObject& rObj ); -}; - -GraphicCacheEntry::GraphicCacheEntry( const GraphicObject& rObj ) : - maID ( rObj ), - mbSwappedAll ( true ) -{ - mbSwappedAll = !ImplInit( rObj ); - maGraphicObjectList.push_back( const_cast<GraphicObject*>(&rObj) ); -} - -GraphicCacheEntry::~GraphicCacheEntry() -{ - DBG_ASSERT( - maGraphicObjectList.empty(), - "GraphicCacheEntry::~GraphicCacheEntry(): Not all GraphicObjects are removed from this entry" - ); -} - -bool GraphicCacheEntry::ImplInit( const GraphicObject& rObj ) -{ - bool bRet = false; - - if( !rObj.IsSwappedOut() ) - { - const Graphic& rGraphic = rObj.GetGraphic(); - - mpBmpEx.reset(); - mpMtf.reset(); - mpAnimation.reset(); - - switch( rGraphic.GetType() ) - { - case GraphicType::Bitmap: - { - if(rGraphic.getVectorGraphicData().get()) - { - maVectorGraphicData = rGraphic.getVectorGraphicData(); - } - else if( rGraphic.IsAnimated() ) - { - mpAnimation.reset(new Animation( rGraphic.GetAnimation() )); - } - else - { - mpBmpEx.reset(new BitmapEx( rGraphic.GetBitmapEx() )); - if (rGraphic.getPdfData().hasElements()) - maPdfData = rGraphic.getPdfData(); - } - } - break; - - case GraphicType::GdiMetafile: - { - mpMtf.reset(new GDIMetaFile( rGraphic.GetGDIMetaFile() )); - } - break; - - default: - DBG_ASSERT( GetID().IsEmpty(), "GraphicCacheEntry::ImplInit: Could not initialize graphic! (=>KA)" ); - break; - } - - if( rGraphic.IsLink() ) - maGfxLink = rGraphic.GetLink(); - else - maGfxLink = GfxLink(); - - bRet = true; - } - - return bRet; -} - -void GraphicCacheEntry::ImplFillSubstitute( Graphic& rSubstitute ) -{ - // create substitute for graphic; - const Size aPrefSize( rSubstitute.GetPrefSize() ); - const MapMode aPrefMapMode( rSubstitute.GetPrefMapMode() ); - const Link<Animation*,void> aAnimationNotifyHdl( rSubstitute.GetAnimationNotifyHdl() ); - const GraphicType eOldType = rSubstitute.GetType(); - const bool bDefaultType = ( rSubstitute.GetType() == GraphicType::Default ); - - if( rSubstitute.IsLink() && ( GfxLinkType::NONE == maGfxLink.GetType() ) ) - maGfxLink = rSubstitute.GetLink(); - - if(maVectorGraphicData.get()) - { - rSubstitute = maVectorGraphicData; - } - else if( mpBmpEx ) - { - rSubstitute = *mpBmpEx; - if (maPdfData.hasElements()) - rSubstitute.setPdfData(maPdfData); - } - else if( mpAnimation ) - { - rSubstitute = *mpAnimation; - } - else if( mpMtf ) - { - rSubstitute = *mpMtf; - } - else - { - rSubstitute.Clear(); - } - - if( eOldType != GraphicType::NONE ) - { - rSubstitute.SetPrefSize( aPrefSize ); - rSubstitute.SetPrefMapMode( aPrefMapMode ); - rSubstitute.SetAnimationNotifyHdl( aAnimationNotifyHdl ); - } - - if( GfxLinkType::NONE != maGfxLink.GetType() ) - { - rSubstitute.SetLink( maGfxLink ); - } - - if( bDefaultType ) - { - rSubstitute.SetDefaultType(); - } -} - -void GraphicCacheEntry::AddGraphicObjectReference( const GraphicObject& rObj, Graphic& rSubstitute ) -{ - if( mbSwappedAll ) - mbSwappedAll = !ImplInit( rObj ); - - OUString rOriginURL = rObj.GetGraphic().getOriginURL(); - ImplFillSubstitute( rSubstitute ); - rSubstitute.setOriginURL(rOriginURL); - maGraphicObjectList.push_back( const_cast<GraphicObject*>(&rObj) ); -} - -bool GraphicCacheEntry::ReleaseGraphicObjectReference( const GraphicObject& rObj ) -{ - for( - auto it = maGraphicObjectList.begin(); - it != maGraphicObjectList.end(); - ++it - ) { - if( &rObj == *it ) - { - maGraphicObjectList.erase( it ); - return true; - } - } - - return false; -} - -bool GraphicCacheEntry::HasGraphicObjectReference( const GraphicObject& rObj ) -{ - bool bRet = false; - - for( size_t i = 0, n = maGraphicObjectList.size(); ( i < n ) && !bRet; ++i ) - if( &rObj == maGraphicObjectList[ i ] ) - bRet = true; - - return bRet; -} - -void GraphicCacheEntry::TryToSwapIn() -{ - if( mbSwappedAll && !maGraphicObjectList.empty() ) - maGraphicObjectList.front()->FireSwapInRequest(); -} - -void GraphicCacheEntry::GraphicObjectWasSwappedOut() -{ - mbSwappedAll = true; - - for( size_t i = 0, n = maGraphicObjectList.size(); ( i < n ) && mbSwappedAll; ++i ) - if( !maGraphicObjectList[ i ]->IsSwappedOut() ) - mbSwappedAll = false; - - if( !mbSwappedAll ) - return; - - mpBmpEx.reset(); - mpMtf.reset(); - mpAnimation.reset(); - - // #119176# also reset VectorGraphicData - maVectorGraphicData.reset(); - maPdfData = uno::Sequence<sal_Int8>(); -} - -void GraphicCacheEntry::GraphicObjectWasSwappedIn( const GraphicObject& rObj ) -{ - if( mbSwappedAll ) - mbSwappedAll = !ImplInit( rObj ); -} - -class GraphicDisplayCacheEntry -{ -private: - - ::salhelper::TTimeValue maReleaseTime; - const GraphicCacheEntry* mpRefCacheEntry; - std::unique_ptr<GDIMetaFile> mpMtf; - std::unique_ptr<BitmapEx> mpBmpEx; - GraphicAttr maAttr; - Size maOutSizePix; - sal_uLong mnCacheSize; - DrawModeFlags mnOutDevDrawMode; - sal_uInt16 mnOutDevBitCount; - - static bool IsCacheableAsBitmap( const GDIMetaFile& rMtf, OutputDevice const * pOut, const Size& rSz ); - - // Copy assignment is forbidden and not implemented. - GraphicDisplayCacheEntry (const GraphicDisplayCacheEntry &) = delete; - GraphicDisplayCacheEntry & operator= (const GraphicDisplayCacheEntry &) = delete; - -public: - - static sal_uLong GetNeededSize( OutputDevice const * pOut, const Point& rPt, const Size& rSz, - const GraphicObject& rObj, const GraphicAttr& rAttr ); - -public: - - GraphicDisplayCacheEntry( const GraphicCacheEntry* pRefCacheEntry, - OutputDevice const * pOut, const Point& rPt, const Size& rSz, - const GraphicObject& rObj, const GraphicAttr& rAttr, - const BitmapEx& rBmpEx ) : - mpRefCacheEntry( pRefCacheEntry ), - mpBmpEx( new BitmapEx( rBmpEx ) ), - maAttr( rAttr ), maOutSizePix( pOut->LogicToPixel( rSz ) ), - mnCacheSize( GetNeededSize( pOut, rPt, rSz, rObj, rAttr ) ), - mnOutDevDrawMode( pOut->GetDrawMode() ), - mnOutDevBitCount( pOut->GetBitCount() ) - { - } - - GraphicDisplayCacheEntry( const GraphicCacheEntry* pRefCacheEntry, - OutputDevice const * pOut, const Point& rPt, const Size& rSz, - const GraphicObject& rObj, const GraphicAttr& rAttr, - const GDIMetaFile& rMtf ) : - mpRefCacheEntry( pRefCacheEntry ), - mpMtf( new GDIMetaFile( rMtf ) ), - maAttr( rAttr ), maOutSizePix( pOut->LogicToPixel( rSz ) ), - mnCacheSize( GetNeededSize( pOut, rPt, rSz, rObj, rAttr ) ), - mnOutDevDrawMode( pOut->GetDrawMode() ), - mnOutDevBitCount( pOut->GetBitCount() ) - { - } - - - sal_uLong GetCacheSize() const { return mnCacheSize; } - const GraphicCacheEntry* GetReferencedCacheEntry() const { return mpRefCacheEntry; } - - void SetReleaseTime( const ::salhelper::TTimeValue& rReleaseTime ) { maReleaseTime = rReleaseTime; } - const ::salhelper::TTimeValue& GetReleaseTime() const { return maReleaseTime; } - - bool Matches( OutputDevice const * pOut, const Point& /*rPtPixel*/, const Size& rSzPixel, - const GraphicCacheEntry* pCacheEntry, const GraphicAttr& rAttr ) const - { - // #i46805# Additional match - // criteria: outdev draw mode and - // bit count. One cannot reuse - // this cache object, if it's - // e.g. generated for - // DrawModeFlags::GrayBitmap. - return( ( pCacheEntry == mpRefCacheEntry ) && - ( maAttr == rAttr ) && - ( ( maOutSizePix == rSzPixel ) || ( !maOutSizePix.Width() && !maOutSizePix.Height() ) ) && - ( pOut->GetBitCount() == mnOutDevBitCount ) && - ( pOut->GetDrawMode() == mnOutDevDrawMode ) ); - } - - void Draw( OutputDevice* pOut, const Point& rPt, const Size& rSz ) const; -}; - -// This whole function is based on checkMetadataBitmap() from grfmgr2.cxx, see that one for details. -// If you do changes here, change the original function too. -static void checkMetadataBitmap( const BitmapEx& rBmpEx, - Point /*rSrcPoint*/, - Size rSrcSize, - const Point& rDestPoint, - const Size& rDestSize, - const Size& rRefSize, - bool& o_rbNonBitmapActionEncountered ) -{ - if( rSrcSize == Size()) - rSrcSize = rBmpEx.GetSizePixel(); - - if( rDestPoint != Point( 0, 0 )) - { - o_rbNonBitmapActionEncountered = true; - return; - } - if( rDestSize != rRefSize ) - { if( rBmpEx.GetSizePixel().Width() > 100 && rBmpEx.GetSizePixel().Height() > 100 - && std::abs( rDestSize.Width() - rRefSize.Width()) < 5 - && std::abs( rDestSize.Height() - rRefSize.Height()) < 5 ) - ; // ok, assume it's close enough - else - { // fall back to mtf rendering - o_rbNonBitmapActionEncountered = true; - return; - } - } -} - -// This function is based on GraphicManager::ImplCreateOutput(), in fact it mostly copies -// it, the difference is that this one does not create anything, it only checks if -// ImplCreateOutput() would use the optimization of using the single bitmap. -// If you do changes here, change the original function too. -bool GraphicDisplayCacheEntry::IsCacheableAsBitmap( const GDIMetaFile& rMtf, - OutputDevice const * pOut, const Size& rSz ) -{ - const Size aNewSize( rMtf.GetPrefSize() ); - GDIMetaFile rOutMtf = rMtf; - - // Count bitmap actions, and flag actions that paint, but - // are no bitmaps. - sal_Int32 nNumBitmaps(0); - bool bNonBitmapActionEncountered(false); - if( aNewSize.Width() && aNewSize.Height() && rSz.Width() && rSz.Height() ) - { - const MapMode& rPrefMapMode( rMtf.GetPrefMapMode() ); - const Size rSizePix( pOut->LogicToPixel( aNewSize, rPrefMapMode ) ); - - sal_uInt32 nCurPos; - MetaAction* pAct; - for( nCurPos = 0, pAct = rOutMtf.FirstAction(); pAct; - pAct = rOutMtf.NextAction(), nCurPos++ ) - { - switch( pAct->GetType() ) - { - case MetaActionType::FONT: - // FALLTHROUGH intended - case MetaActionType::NONE: - // FALLTHROUGH intended - - // OutDev state changes (which don't affect bitmap - // output) - case MetaActionType::LINECOLOR: - // FALLTHROUGH intended - case MetaActionType::FILLCOLOR: - // FALLTHROUGH intended - case MetaActionType::TEXTCOLOR: - // FALLTHROUGH intended - case MetaActionType::TEXTFILLCOLOR: - // FALLTHROUGH intended - case MetaActionType::TEXTALIGN: - // FALLTHROUGH intended - case MetaActionType::TEXTLINECOLOR: - // FALLTHROUGH intended - case MetaActionType::TEXTLINE: - // FALLTHROUGH intended - case MetaActionType::PUSH: - // FALLTHROUGH intended - case MetaActionType::POP: - // FALLTHROUGH intended - case MetaActionType::LAYOUTMODE: - // FALLTHROUGH intended - case MetaActionType::TEXTLANGUAGE: - // FALLTHROUGH intended - case MetaActionType::COMMENT: - break; - - // bitmap output methods - case MetaActionType::BMP: - if( !nNumBitmaps && !bNonBitmapActionEncountered ) - { - MetaBmpAction* pAction = static_cast<MetaBmpAction*>(pAct); - - checkMetadataBitmap( - BitmapEx( pAction->GetBitmap()), - Point(), Size(), - pOut->LogicToPixel( pAction->GetPoint(), - rPrefMapMode ), - pAction->GetBitmap().GetSizePixel(), - rSizePix, - bNonBitmapActionEncountered ); - } - ++nNumBitmaps; - break; - - case MetaActionType::BMPSCALE: - if( !nNumBitmaps && !bNonBitmapActionEncountered ) - { - MetaBmpScaleAction* pAction = static_cast<MetaBmpScaleAction*>(pAct); - - checkMetadataBitmap( - BitmapEx( pAction->GetBitmap()), - Point(), Size(), - pOut->LogicToPixel( pAction->GetPoint(), - rPrefMapMode ), - pOut->LogicToPixel( pAction->GetSize(), - rPrefMapMode ), - rSizePix, - bNonBitmapActionEncountered ); - } - ++nNumBitmaps; - break; - - case MetaActionType::BMPSCALEPART: - if( !nNumBitmaps && !bNonBitmapActionEncountered ) - { - MetaBmpScalePartAction* pAction = static_cast<MetaBmpScalePartAction*>(pAct); - - checkMetadataBitmap( BitmapEx( pAction->GetBitmap() ), - pAction->GetSrcPoint(), - pAction->GetSrcSize(), - pOut->LogicToPixel( pAction->GetDestPoint(), - rPrefMapMode ), - pOut->LogicToPixel( pAction->GetDestSize(), - rPrefMapMode ), - rSizePix, - bNonBitmapActionEncountered ); - } - ++nNumBitmaps; - break; - - case MetaActionType::BMPEX: - if( !nNumBitmaps && !bNonBitmapActionEncountered ) - { - MetaBmpExAction* pAction = static_cast<MetaBmpExAction*>(pAct); - - checkMetadataBitmap( - pAction->GetBitmapEx(), - Point(), Size(), - pOut->LogicToPixel( pAction->GetPoint(), - rPrefMapMode ), - pAction->GetBitmapEx().GetSizePixel(), - rSizePix, - bNonBitmapActionEncountered ); - } - ++nNumBitmaps; - break; - - case MetaActionType::BMPEXSCALE: - if( !nNumBitmaps && !bNonBitmapActionEncountered ) - { - MetaBmpExScaleAction* pAction = static_cast<MetaBmpExScaleAction*>(pAct); - - checkMetadataBitmap( - pAction->GetBitmapEx(), - Point(), Size(), - pOut->LogicToPixel( pAction->GetPoint(), - rPrefMapMode ), - pOut->LogicToPixel( pAction->GetSize(), - rPrefMapMode ), - rSizePix, - bNonBitmapActionEncountered ); - } - ++nNumBitmaps; - break; - - case MetaActionType::BMPEXSCALEPART: - if( !nNumBitmaps && !bNonBitmapActionEncountered ) - { - MetaBmpExScalePartAction* pAction = static_cast<MetaBmpExScalePartAction*>(pAct); - - checkMetadataBitmap( pAction->GetBitmapEx(), - pAction->GetSrcPoint(), - pAction->GetSrcSize(), - pOut->LogicToPixel( pAction->GetDestPoint(), - rPrefMapMode ), - pOut->LogicToPixel( pAction->GetDestSize(), - rPrefMapMode ), - rSizePix, - bNonBitmapActionEncountered ); - } - ++nNumBitmaps; - break; - - // these actions actually output something (that's - // different from a bitmap) - case MetaActionType::RASTEROP: - if( static_cast<MetaRasterOpAction*>(pAct)->GetRasterOp() == RasterOp::OverPaint ) - break; - SAL_FALLTHROUGH; - case MetaActionType::PIXEL: - SAL_FALLTHROUGH; - case MetaActionType::POINT: - SAL_FALLTHROUGH; - case MetaActionType::LINE: - SAL_FALLTHROUGH; - case MetaActionType::RECT: - SAL_FALLTHROUGH; - case MetaActionType::ROUNDRECT: - SAL_FALLTHROUGH; - case MetaActionType::ELLIPSE: - SAL_FALLTHROUGH; - case MetaActionType::ARC: - SAL_FALLTHROUGH; - case MetaActionType::PIE: - SAL_FALLTHROUGH; - case MetaActionType::CHORD: - SAL_FALLTHROUGH; - case MetaActionType::POLYLINE: - SAL_FALLTHROUGH; - case MetaActionType::POLYGON: - SAL_FALLTHROUGH; - case MetaActionType::POLYPOLYGON: - SAL_FALLTHROUGH; - - case MetaActionType::TEXT: - SAL_FALLTHROUGH; - case MetaActionType::TEXTARRAY: - SAL_FALLTHROUGH; - case MetaActionType::STRETCHTEXT: - SAL_FALLTHROUGH; - case MetaActionType::TEXTRECT: - SAL_FALLTHROUGH; - - case MetaActionType::MASK: - SAL_FALLTHROUGH; - case MetaActionType::MASKSCALE: - SAL_FALLTHROUGH; - case MetaActionType::MASKSCALEPART: - SAL_FALLTHROUGH; - - case MetaActionType::GRADIENT: - SAL_FALLTHROUGH; - case MetaActionType::HATCH: - SAL_FALLTHROUGH; - case MetaActionType::WALLPAPER: - SAL_FALLTHROUGH; - - case MetaActionType::Transparent: - SAL_FALLTHROUGH; - case MetaActionType::EPS: - SAL_FALLTHROUGH; - case MetaActionType::FLOATTRANSPARENT: - SAL_FALLTHROUGH; - case MetaActionType::GRADIENTEX: - SAL_FALLTHROUGH; - - // OutDev state changes that _do_ affect bitmap - // output - case MetaActionType::CLIPREGION: - SAL_FALLTHROUGH; - case MetaActionType::ISECTRECTCLIPREGION: - SAL_FALLTHROUGH; - case MetaActionType::ISECTREGIONCLIPREGION: - SAL_FALLTHROUGH; - case MetaActionType::MOVECLIPREGION: - SAL_FALLTHROUGH; - - case MetaActionType::MAPMODE: - SAL_FALLTHROUGH; - case MetaActionType::REFPOINT: - SAL_FALLTHROUGH; - default: - bNonBitmapActionEncountered = true; - break; - } - } - } - return nNumBitmaps == 1 && !bNonBitmapActionEncountered; -} - -sal_uLong GraphicDisplayCacheEntry::GetNeededSize( OutputDevice const * pOut, const Point& /*rPt*/, const Size& rSz, - const GraphicObject& rObj, const GraphicAttr& rAttr ) -{ - const Graphic& rGraphic = rObj.GetGraphic(); - const GraphicType eType = rGraphic.GetType(); - - bool canCacheAsBitmap = false; - if( GraphicType::Bitmap == eType ) - canCacheAsBitmap = true; - else if( GraphicType::GdiMetafile == eType ) - canCacheAsBitmap = IsCacheableAsBitmap( rGraphic.GetGDIMetaFile(), pOut, rSz ); - else - return 0; - if( canCacheAsBitmap ) - { - const Size aOutSizePix( pOut->LogicToPixel( rSz ) ); - const long nBitCount = pOut->GetBitCount(); - - if( ( aOutSizePix.Width() > MAX_BMP_EXTENT ) || - ( aOutSizePix.Height() > MAX_BMP_EXTENT ) ) - { - return ULONG_MAX; - } - else if( nBitCount ) - { - sal_uLong nNeededSize = aOutSizePix.Width() * aOutSizePix.Height() * nBitCount / 8; - if( rObj.IsTransparent() || ( rAttr.GetRotation() % 3600 ) ) - nNeededSize += nNeededSize / nBitCount; - return nNeededSize; - } - else - { - OSL_FAIL( "GraphicDisplayCacheEntry::GetNeededSize(): pOut->GetBitCount() == 0" ); - return 256000; - } - } - else - return rGraphic.GetSizeBytes(); -} - -void GraphicDisplayCacheEntry::Draw( OutputDevice* pOut, const Point& rPt, const Size& rSz ) const -{ - if( mpMtf ) - GraphicManager::ImplDraw( pOut, rPt, rSz, *mpMtf, maAttr ); - else if( mpBmpEx ) - { - if( maAttr.IsRotated() ) - { - tools::Polygon aPoly( tools::Rectangle( rPt, rSz ) ); - - aPoly.Rotate( rPt, maAttr.GetRotation() % 3600 ); - const tools::Rectangle aRotBoundRect( aPoly.GetBoundRect() ); - pOut->DrawBitmapEx( aRotBoundRect.TopLeft(), aRotBoundRect.GetSize(), *mpBmpEx ); - } - else - pOut->DrawBitmapEx( rPt, rSz, *mpBmpEx ); - } -} - -GraphicCache::GraphicCache( sal_uLong nDisplayCacheSize, sal_uLong nMaxObjDisplayCacheSize ) : - maReleaseTimer ( "svtools::GraphicCache maReleaseTimer" ), - mnReleaseTimeoutSeconds ( 0 ), - mnMaxDisplaySize ( nDisplayCacheSize ), - mnMaxObjDisplaySize ( nMaxObjDisplayCacheSize ), - mnUsedDisplaySize ( 0 ) -{ - maReleaseTimer.SetInvokeHandler( LINK( this, GraphicCache, ReleaseTimeoutHdl ) ); - maReleaseTimer.SetTimeout( 10000 ); - maReleaseTimer.SetDebugName( "svtools::GraphicCache maReleaseTimer" ); - maReleaseTimer.Start(); -} - -GraphicCache::~GraphicCache() -{ - DBG_ASSERT( !maGraphicCache.size(), "GraphicCache::~GraphicCache(): there are some GraphicObjects in cache" ); - DBG_ASSERT( maDisplayCache.empty(), "GraphicCache::~GraphicCache(): there are some GraphicObjects in display cache" ); -} - -void GraphicCache::AddGraphicObject( - const GraphicObject& rObj, - Graphic& rSubstitute, - const OString* pID, - const GraphicObject* pCopyObj -) -{ - bool bInserted = false; - - if( !rObj.IsSwappedOut() - && ( pID - || ( pCopyObj - && ( pCopyObj->GetType() != GraphicType::NONE ) - ) - || ( rObj.GetType() != GraphicType::NONE ) - ) - ) - { - if( pCopyObj - && !maGraphicCache.empty() - ) - { - for (auto const& elem : maGraphicCache) - { - if( elem->HasGraphicObjectReference( *pCopyObj ) ) - { - elem->AddGraphicObjectReference( rObj, rSubstitute ); - bInserted = true; - break; - } - } - } - - if( !bInserted ) - { - std::unique_ptr< GraphicID > apID; - - if( !pID ) - { - apID.reset( new GraphicID( rObj ) ); - } - - for (auto const& elem : maGraphicCache) - { - const GraphicID& rEntryID = elem->GetID(); - - if( pID ) - { - if( rEntryID.GetIDString() == *pID ) - { - elem->TryToSwapIn(); - - // since pEntry->TryToSwapIn can modify our current list, we have to - // iterate from beginning to add a reference to the appropriate - // CacheEntry object; after this, quickly jump out of the outer iteration - for (auto const& subelem : maGraphicCache) - { - const GraphicID& rID = subelem->GetID(); - - if( rID.GetIDString() == *pID ) - { - subelem->AddGraphicObjectReference( rObj, rSubstitute ); - bInserted = true; - break; - } - } - - if( !bInserted ) - { - maGraphicCache.push_back( new GraphicCacheEntry( rObj ) ); - bInserted = true; - } - } - } - else - { - if( rEntryID == *apID ) - { - elem->AddGraphicObjectReference( rObj, rSubstitute ); - bInserted = true; - } - } - - if(bInserted) - break; - } - } - } - - if( !bInserted ) - maGraphicCache.push_back( new GraphicCacheEntry( rObj ) ); -} - -void GraphicCache::ReleaseGraphicObject( const GraphicObject& rObj ) -{ - // Release cached object - bool bRemoved = false; - GraphicCacheEntryVector::iterator it = maGraphicCache.begin(); - while (!bRemoved && it != maGraphicCache.end()) - { - bRemoved = (*it)->ReleaseGraphicObjectReference( rObj ); - - if( bRemoved && (0 == (*it)->GetGraphicObjectReferenceCount()) ) - { - // if graphic cache entry has no more references, - // the corresponding display cache object can be removed - GraphicDisplayCacheEntryVector::iterator it2 = maDisplayCache.begin(); - while( it2 != maDisplayCache.end() ) - { - GraphicDisplayCacheEntry* pDisplayEntry = *it2; - if( pDisplayEntry->GetReferencedCacheEntry() == *it ) - { - mnUsedDisplaySize -= pDisplayEntry->GetCacheSize(); - it2 = maDisplayCache.erase( it2 ); - delete pDisplayEntry; - } - else - ++it2; - } - - // delete graphic cache entry - delete *it; - it = maGraphicCache.erase( it ); - } - else - ++it; - } - - DBG_ASSERT( bRemoved, "GraphicCache::ReleaseGraphicObject(...): GraphicObject not found in cache" ); -} - -void GraphicCache::GraphicObjectWasSwappedOut( const GraphicObject& rObj ) -{ - // notify cache that rObj is swapped out (and can thus be pruned - // from the cache) - GraphicCacheEntry* pEntry = ImplGetCacheEntry( rObj ); - - if( pEntry ) - pEntry->GraphicObjectWasSwappedOut(); -} - -void GraphicCache::GraphicObjectWasSwappedIn( const GraphicObject& rObj ) -{ - GraphicCacheEntry* pEntry = ImplGetCacheEntry( rObj ); - - if( pEntry ) - { - if( pEntry->GetID().IsEmpty() ) - { - ReleaseGraphicObject( rObj ); - AddGraphicObject( rObj, const_cast<Graphic&>(rObj.GetGraphic()), nullptr, nullptr ); - } - else - pEntry->GraphicObjectWasSwappedIn( rObj ); - } -} - -void GraphicCache::SetMaxDisplayCacheSize( sal_uLong nNewCacheSize ) -{ - mnMaxDisplaySize = nNewCacheSize; - - if( GetMaxDisplayCacheSize() < GetUsedDisplayCacheSize() ) - ImplFreeDisplayCacheSpace( GetUsedDisplayCacheSize() - GetMaxDisplayCacheSize() ); -} - -void GraphicCache::SetCacheTimeout( sal_uLong nTimeoutSeconds ) -{ - if( mnReleaseTimeoutSeconds == nTimeoutSeconds ) - return; - - ::salhelper::TTimeValue aReleaseTime; - - if( ( mnReleaseTimeoutSeconds = nTimeoutSeconds ) != 0 ) - { - osl_getSystemTime( &aReleaseTime ); - aReleaseTime.addTime( ::salhelper::TTimeValue( nTimeoutSeconds, 0 ) ); - } - - for (auto const& elem : maDisplayCache) - { - elem->SetReleaseTime( aReleaseTime ); - } -} - -bool GraphicCache::IsDisplayCacheable( OutputDevice const * pOut, const Point& rPt, const Size& rSz, - const GraphicObject& rObj, const GraphicAttr& rAttr ) const -{ - return( GraphicDisplayCacheEntry::GetNeededSize( pOut, rPt, rSz, rObj, rAttr ) <= - GetMaxObjDisplayCacheSize() ); -} - -bool GraphicCache::IsInDisplayCache( OutputDevice const * pOut, const Point& rPt, const Size& rSz, - const GraphicObject& rObj, const GraphicAttr& rAttr ) const -{ - const Point aPtPixel( pOut->LogicToPixel( rPt ) ); - const Size aSzPixel( pOut->LogicToPixel( rSz ) ); - const GraphicCacheEntry* pCacheEntry = const_cast<GraphicCache*>(this)->ImplGetCacheEntry( rObj ); - bool bFound = false; - - if( pCacheEntry ) - { - for (auto const& elem : maDisplayCache) - { - if( elem->Matches( pOut, aPtPixel, aSzPixel, pCacheEntry, rAttr ) ) - { - bFound = true; - break; - } - } - } - - return bFound; -} - -OString GraphicCache::GetUniqueID( const GraphicObject& rObj ) const -{ - OString aRet; - GraphicCacheEntry* pEntry = const_cast<GraphicCache*>(this)->ImplGetCacheEntry( rObj ); - - // ensure that the entry is correctly initialized (it has to be read at least once) - if( pEntry && pEntry->GetID().IsEmpty() ) - { - pEntry->TryToSwapIn(); - // do another call to ImplGetCacheEntry in case of modified entry list - pEntry = const_cast<GraphicCache*>(this)->ImplGetCacheEntry( rObj ); - } - - if( pEntry ) - aRet = pEntry->GetID().GetIDString(); - - return aRet; -} - -bool GraphicCache::CreateDisplayCacheObj( OutputDevice const * pOut, const Point& rPt, const Size& rSz, - const GraphicObject& rObj, const GraphicAttr& rAttr, - const BitmapEx& rBmpEx ) -{ - const sal_uLong nNeededSize = GraphicDisplayCacheEntry::GetNeededSize( pOut, rPt, rSz, rObj, rAttr ); - bool bRet = false; - - if( nNeededSize <= GetMaxObjDisplayCacheSize() ) - { - if( nNeededSize > GetFreeDisplayCacheSize() ) - ImplFreeDisplayCacheSpace( nNeededSize - GetFreeDisplayCacheSize() ); - - GraphicDisplayCacheEntry* pNewEntry = new GraphicDisplayCacheEntry( ImplGetCacheEntry( rObj ), - pOut, rPt, rSz, rObj, rAttr, rBmpEx ); - - if( GetCacheTimeout() ) - { - ::salhelper::TTimeValue aReleaseTime; - - osl_getSystemTime( &aReleaseTime ); - aReleaseTime.addTime( ::salhelper::TTimeValue( GetCacheTimeout(), 0 ) ); - pNewEntry->SetReleaseTime( aReleaseTime ); - } - - maDisplayCache.push_back( pNewEntry ); - mnUsedDisplaySize += pNewEntry->GetCacheSize(); - bRet = true; - } - - return bRet; -} - -bool GraphicCache::CreateDisplayCacheObj( OutputDevice const * pOut, const Point& rPt, const Size& rSz, - const GraphicObject& rObj, const GraphicAttr& rAttr, - const GDIMetaFile& rMtf ) -{ - const sal_uLong nNeededSize = GraphicDisplayCacheEntry::GetNeededSize( pOut, rPt, rSz, rObj, rAttr ); - bool bRet = false; - - if( nNeededSize <= GetMaxObjDisplayCacheSize() ) - { - if( nNeededSize > GetFreeDisplayCacheSize() ) - ImplFreeDisplayCacheSpace( nNeededSize - GetFreeDisplayCacheSize() ); - - GraphicDisplayCacheEntry* pNewEntry = new GraphicDisplayCacheEntry( ImplGetCacheEntry( rObj ), - pOut, rPt, rSz, rObj, rAttr, rMtf ); - - if( GetCacheTimeout() ) - { - ::salhelper::TTimeValue aReleaseTime; - - osl_getSystemTime( &aReleaseTime ); - aReleaseTime.addTime( ::salhelper::TTimeValue( GetCacheTimeout(), 0 ) ); - pNewEntry->SetReleaseTime( aReleaseTime ); - } - - maDisplayCache.push_back( pNewEntry ); - mnUsedDisplaySize += pNewEntry->GetCacheSize(); - bRet = true; - } - - return bRet; -} - -bool GraphicCache::DrawDisplayCacheObj( OutputDevice* pOut, const Point& rPt, const Size& rSz, - const GraphicObject& rObj, const GraphicAttr& rAttr ) -{ - const Point aPtPixel( pOut->LogicToPixel( rPt ) ); - const Size aSzPixel( pOut->LogicToPixel( rSz ) ); - const GraphicCacheEntry* pCacheEntry = ImplGetCacheEntry( rObj ); - GraphicDisplayCacheEntry* pDisplayCacheEntry = nullptr; - GraphicDisplayCacheEntryVector::iterator it = maDisplayCache.begin(); - bool bRet = false; - - while( !bRet && it != maDisplayCache.end() ) - { - pDisplayCacheEntry = *it; - if( pDisplayCacheEntry->Matches( pOut, aPtPixel, aSzPixel, pCacheEntry, rAttr ) ) - { - ::salhelper::TTimeValue aReleaseTime; - - // put found object at last used position - it = maDisplayCache.erase( it ); - maDisplayCache.push_back( pDisplayCacheEntry ); - - if( GetCacheTimeout() ) - { - osl_getSystemTime( &aReleaseTime ); - aReleaseTime.addTime( ::salhelper::TTimeValue( GetCacheTimeout(), 0 ) ); - } - - pDisplayCacheEntry->SetReleaseTime( aReleaseTime ); - bRet = true; - } - else - ++it; - } - - if( bRet ) - pDisplayCacheEntry->Draw( pOut, rPt, rSz ); - - return bRet; -} - -bool GraphicCache::ImplFreeDisplayCacheSpace( sal_uLong nSizeToFree ) -{ - sal_uLong nFreedSize = 0; - - if( nSizeToFree ) - { - GraphicDisplayCacheEntryVector::iterator it = maDisplayCache.begin(); - - if( nSizeToFree > mnUsedDisplaySize ) - nSizeToFree = mnUsedDisplaySize; - - while( it != maDisplayCache.end() ) - { - GraphicDisplayCacheEntry* pCacheObj = *it; - - nFreedSize += pCacheObj->GetCacheSize(); - mnUsedDisplaySize -= pCacheObj->GetCacheSize(); - it = maDisplayCache.erase( it ); - delete pCacheObj; - - if( nFreedSize >= nSizeToFree ) - break; - } - } - - return( nFreedSize >= nSizeToFree ); -} - -GraphicCacheEntry* GraphicCache::ImplGetCacheEntry( const GraphicObject& rObj ) -{ - GraphicCacheEntry* pRet = nullptr; - - for (auto const& elem : maGraphicCache) - { - if( elem->HasGraphicObjectReference( rObj ) ) - { - return elem; - } - } - - return pRet; -} - -IMPL_LINK( GraphicCache, ReleaseTimeoutHdl, Timer*, pTimer, void ) -{ - pTimer->Stop(); - - ::salhelper::TTimeValue aCurTime; - GraphicDisplayCacheEntryVector::iterator it = maDisplayCache.begin(); - - osl_getSystemTime( &aCurTime ); - - while( it != maDisplayCache.end() ) - { - GraphicDisplayCacheEntry* pDisplayEntry = *it; - const ::salhelper::TTimeValue& rReleaseTime = pDisplayEntry->GetReleaseTime(); - - if( !rReleaseTime.isEmpty() && ( rReleaseTime < aCurTime ) ) - { - mnUsedDisplaySize -= pDisplayEntry->GetCacheSize(); - it = maDisplayCache.erase( it ); - delete pDisplayEntry; - } - else - ++it; - } - - pTimer->Start(); -} - -/* vim:set shiftwidth=4 softtabstop=4 expandtab: */ diff --git a/svtools/source/graphic/grfcache.hxx b/svtools/source/graphic/grfcache.hxx deleted file mode 100644 index 7287192e4d54..000000000000 --- a/svtools/source/graphic/grfcache.hxx +++ /dev/null @@ -1,136 +0,0 @@ -/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */ -/* - * This file is part of the LibreOffice project. - * - * This Source Code Form is subject to the terms of the Mozilla Public - * License, v. 2.0. If a copy of the MPL was not distributed with this - * file, You can obtain one at http://mozilla.org/MPL/2.0/. - * - * This file incorporates work covered by the following license notice: - * - * Licensed to the Apache Software Foundation (ASF) under one or more - * contributor license agreements. See the NOTICE file distributed - * with this work for additional information regarding copyright - * ownership. The ASF licenses this file to you under the Apache - * License, Version 2.0 (the "License"); you may not use this file - * except in compliance with the License. You may obtain a copy of - * the License at http://www.apache.org/licenses/LICENSE-2.0 . - */ - -#ifndef INCLUDED_SVTOOLS_SOURCE_GRAPHIC_GRFCACHE_HXX -#define INCLUDED_SVTOOLS_SOURCE_GRAPHIC_GRFCACHE_HXX - -#include <vcl/graph.hxx> -#include <vcl/timer.hxx> -#include <vector> - - -class GraphicAttr; -class GraphicCacheEntry; -class GraphicDisplayCacheEntry; -class GraphicObject; - -class GraphicCache -{ -private: - typedef std::vector< GraphicCacheEntry* > GraphicCacheEntryVector; - typedef std::vector< GraphicDisplayCacheEntry* > GraphicDisplayCacheEntryVector; - - Timer maReleaseTimer; - GraphicCacheEntryVector maGraphicCache; - GraphicDisplayCacheEntryVector maDisplayCache; - sal_uLong mnReleaseTimeoutSeconds; - sal_uLong mnMaxDisplaySize; - sal_uLong mnMaxObjDisplaySize; - sal_uLong mnUsedDisplaySize; - - bool ImplFreeDisplayCacheSpace( sal_uLong nSizeToFree ); - GraphicCacheEntry* ImplGetCacheEntry( const GraphicObject& rObj ); - - - DECL_LINK( ReleaseTimeoutHdl, Timer*, void ); - -public: - - GraphicCache( - sal_uLong nDisplayCacheSize, - sal_uLong nMaxObjDisplayCacheSize - ); - - ~GraphicCache(); - -public: - - void AddGraphicObject( - const GraphicObject& rObj, - Graphic& rSubstitute, - const OString* pID, - const GraphicObject* pCopyObj - ); - - void ReleaseGraphicObject( const GraphicObject& rObj ); - - void GraphicObjectWasSwappedOut( const GraphicObject& rObj ); - void GraphicObjectWasSwappedIn( const GraphicObject& rObj ); - - OString GetUniqueID( const GraphicObject& rObj ) const; - -public: - - void SetMaxDisplayCacheSize( sal_uLong nNewCacheSize ); - sal_uLong GetMaxDisplayCacheSize() const { return mnMaxDisplaySize; }; - - sal_uLong GetMaxObjDisplayCacheSize() const { return mnMaxObjDisplaySize; } - - sal_uLong GetUsedDisplayCacheSize() const { return mnUsedDisplaySize; } - sal_uLong GetFreeDisplayCacheSize() const { return( mnMaxDisplaySize - mnUsedDisplaySize ); } - - void SetCacheTimeout( sal_uLong nTimeoutSeconds ); - sal_uLong GetCacheTimeout() const { return mnReleaseTimeoutSeconds; } - - bool IsDisplayCacheable( - OutputDevice const * pOut, - const Point& rPt, - const Size& rSz, - const GraphicObject& rObj, - const GraphicAttr& rAttr - ) const; - - bool IsInDisplayCache( - OutputDevice const * pOut, - const Point& rPt, - const Size& rSz, - const GraphicObject& rObj, - const GraphicAttr& rAttr - ) const; - - bool CreateDisplayCacheObj( - OutputDevice const * pOut, - const Point& rPt, - const Size& rSz, - const GraphicObject& rObj, - const GraphicAttr& rAttr, - const BitmapEx& rBmpEx - ); - - bool CreateDisplayCacheObj( - OutputDevice const * pOut, - const Point& rPt, - const Size& rSz, - const GraphicObject& rObj, - const GraphicAttr& rAttr, - const GDIMetaFile& rMtf - ); - - bool DrawDisplayCacheObj( - OutputDevice* pOut, - const Point& rPt, - const Size& rSz, - const GraphicObject& rObj, - const GraphicAttr& rAttr - ); -}; - -#endif // INCLUDED_SVTOOLS_SOURCE_GRAPHIC_GRFCACHE_HXX - -/* vim:set shiftwidth=4 softtabstop=4 expandtab: */ diff --git a/svtools/source/graphic/grfmgr.cxx b/svtools/source/graphic/grfmgr.cxx deleted file mode 100644 index d025275e39f8..000000000000 --- a/svtools/source/graphic/grfmgr.cxx +++ /dev/null @@ -1,1119 +0,0 @@ -/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */ -/* - * This file is part of the LibreOffice project. - * - * This Source Code Form is subject to the terms of the Mozilla Public - * License, v. 2.0. If a copy of the MPL was not distributed with this - * file, You can obtain one at http://mozilla.org/MPL/2.0/. - * - * This file incorporates work covered by the following license notice: - * - * Licensed to the Apache Software Foundation (ASF) under one or more - * contributor license agreements. See the NOTICE file distributed - * with this work for additional information regarding copyright - * ownership. The ASF licenses this file to you under the Apache - * License, Version 2.0 (the "License"); you may not use this file - * except in compliance with the License. You may obtain a copy of - * the License at http://www.apache.org/licenses/LICENSE-2.0 . - */ - -#include <sal/config.h> - -#include <algorithm> - -#include <officecfg/Office/Common.hxx> -#include <osl/file.hxx> -#include <tools/vcompat.hxx> -#include <tools/fract.hxx> -#include <tools/helpers.hxx> -#include <unotools/ucbstreamhelper.hxx> -#include <unotools/tempfile.hxx> -#include <unotools/configmgr.hxx> -#include <vcl/svapp.hxx> -#include <vcl/cvtgrf.hxx> -#include <vcl/metaact.hxx> -#include <vcl/virdev.hxx> -#include <svtools/grfmgr.hxx> - -#include <com/sun/star/container/XNameContainer.hpp> -#include <com/sun/star/beans/XPropertySet.hpp> -#include <memory> - -using com::sun::star::uno::Reference; -using com::sun::star::uno::XInterface; -using com::sun::star::uno::UNO_QUERY; -using com::sun::star::uno::Sequence; -using com::sun::star::container::XNameContainer; -using com::sun::star::beans::XPropertySet; - -GraphicManager* GraphicObject::mpGlobalMgr = nullptr; - -struct GrfSimpleCacheObj -{ - Graphic maGraphic; - GraphicAttr maAttr; - - GrfSimpleCacheObj( const Graphic& rGraphic, const GraphicAttr& rAttr ) : - maGraphic( rGraphic ), maAttr( rAttr ) {} -}; - -// unique increasing ID for being able to detect the GraphicObject with the -// oldest last data changes -static sal_uLong aIncrementingTimeOfLastDataChange = 1; - -void GraphicObject::ImplAfterDataChange() -{ - // set unique timestamp ID of last data change - mnDataChangeTimeStamp = aIncrementingTimeOfLastDataChange++; - - // check memory footprint of all GraphicObjects managed and evtl. take action - mpGlobalMgr->ImplCheckSizeOfSwappedInGraphics(this); -} - -GraphicObject::GraphicObject() - : mbAutoSwapped(false) - , mbIsInSwapIn(false) - , mbIsInSwapOut(false) -{ - ImplEnsureGraphicManager(); - ImplAssignGraphicData(); - mpGlobalMgr->ImplRegisterObj(*this, maGraphic, nullptr, nullptr); -} - -GraphicObject::GraphicObject(const Graphic& rGraphic) - : maGraphic(rGraphic) - , mbAutoSwapped(false) - , mbIsInSwapIn(false) - , mbIsInSwapOut(false) -{ - ImplEnsureGraphicManager(); - ImplAssignGraphicData(); - mpGlobalMgr->ImplRegisterObj(*this, maGraphic, nullptr, nullptr); -} - -GraphicObject::GraphicObject(const GraphicObject& rGraphicObj) - : maGraphic(rGraphicObj.GetGraphic()) - , maAttr(rGraphicObj.maAttr) - , maPrefMapMode(rGraphicObj.maPrefMapMode) - , maLink(rGraphicObj.maLink) - , maUserData(rGraphicObj.maUserData) - , mbAutoSwapped(false) - , mbIsInSwapIn(false) - , mbIsInSwapOut(false) -{ - ImplAssignGraphicData(); - mpGlobalMgr->ImplRegisterObj(*this, maGraphic, nullptr, &rGraphicObj); - if( rGraphicObj.HasUserData() && rGraphicObj.IsSwappedOut() ) - SetSwapState(); -} - -GraphicObject::GraphicObject(const OString& rUniqueID) - : mbAutoSwapped(false) - , mbIsInSwapIn(false) - , mbIsInSwapOut(false) -{ - ImplEnsureGraphicManager(); - - // assign default properties - ImplAssignGraphicData(); - - mpGlobalMgr->ImplRegisterObj(*this, maGraphic, &rUniqueID, nullptr); - - // update properties - ImplAssignGraphicData(); -} - -GraphicObject::~GraphicObject() -{ - mpGlobalMgr->ImplUnregisterObj( *this ); - - if (!mpGlobalMgr->ImplHasObjects()) - { - delete mpGlobalMgr; - mpGlobalMgr = nullptr; - } -} - -void GraphicObject::ImplAssignGraphicData() -{ - maPrefSize = maGraphic.GetPrefSize(); - maPrefMapMode = maGraphic.GetPrefMapMode(); - mnSizeBytes = maGraphic.GetSizeBytes(); - meType = maGraphic.GetType(); - mbTransparent = maGraphic.IsTransparent(); - mbAnimated = maGraphic.IsAnimated(); - mbEPS = maGraphic.IsEPS(); - mnAnimationLoopCount = ( mbAnimated ? maGraphic.GetAnimationLoopCount() : 0 ); - - // Handle evtl. needed AfterDataChanges - ImplAfterDataChange(); -} - -void GraphicObject::ImplEnsureGraphicManager() -{ - if (mpGlobalMgr) - return; - - sal_uLong nCacheSize = 20000; - sal_uLong nMaxObjCacheSize = 20000; - sal_uLong nTimeoutSeconds = 20000; - if (!utl::ConfigManager::IsFuzzing()) - { - try - { - nCacheSize = officecfg::Office::Common::Cache::GraphicManager::TotalCacheSize::get(); - nMaxObjCacheSize = officecfg::Office::Common::Cache::GraphicManager::ObjectCacheSize::get(); - nTimeoutSeconds = officecfg::Office::Common::Cache::GraphicManager::ObjectReleaseTime::get(); - } - catch (...) - { - } - } - mpGlobalMgr = new GraphicManager(nCacheSize, nMaxObjCacheSize); - mpGlobalMgr->SetCacheTimeout(nTimeoutSeconds); -} - -void GraphicObject::ImplAutoSwapIn() -{ - if( !IsSwappedOut() ) - return; - - { - mbIsInSwapIn = true; - - if( maGraphic.SwapIn() ) - mbAutoSwapped = false; - else - { - SvStream* pStream = GetSwapStream(); - - if( GRFMGR_AUTOSWAPSTREAM_NONE != pStream ) - { - if( GRFMGR_AUTOSWAPSTREAM_LINK == pStream ) - { - if( HasLink() ) - { - OUString aURLStr; - - if( osl::FileBase::getFileURLFromSystemPath( GetLink(), aURLStr ) == osl::FileBase::E_None ) - { - std::unique_ptr<SvStream> pIStm(::utl::UcbStreamHelper::CreateStream( aURLStr, StreamMode::READ )); - - if( pIStm ) - { - ReadGraphic( *pIStm, maGraphic ); - mbAutoSwapped = ( maGraphic.GetType() != GraphicType::NONE ); - } - } - } - } - else if( GRFMGR_AUTOSWAPSTREAM_TEMP == pStream ) - mbAutoSwapped = !maGraphic.SwapIn(); - else if( GRFMGR_AUTOSWAPSTREAM_LOADED == pStream ) - mbAutoSwapped = maGraphic.IsSwapOut(); - else - { - mbAutoSwapped = !maGraphic.SwapIn( pStream ); - delete pStream; - } - } - else - { - DBG_ASSERT( ( GraphicType::NONE == meType ) || ( GraphicType::Default == meType ), - "GraphicObject::ImplAutoSwapIn: could not get stream to swap in graphic! (=>KA)" ); - } - } - - mbIsInSwapIn = false; - - if (!mbAutoSwapped) - mpGlobalMgr->ImplGraphicObjectWasSwappedIn( *this ); - } - ImplAssignGraphicData(); -} - -bool GraphicObject::ImplGetCropParams( OutputDevice const * pOut, Point& rPt, Size& rSz, const GraphicAttr* pAttr, - tools::PolyPolygon& rClipPolyPoly, bool& bRectClipRegion ) const -{ - bool bRet = false; - - if( GetType() != GraphicType::NONE ) - { - tools::Polygon aClipPoly( tools::Rectangle( rPt, rSz ) ); - const sal_uInt16 nRot10 = pAttr->GetRotation() % 3600; - const Point aOldOrigin( rPt ); - const MapMode aMap100( MapUnit::Map100thMM ); - Size aSize100; - long nTotalWidth, nTotalHeight; - - if( nRot10 ) - { - aClipPoly.Rotate( rPt, nRot10 ); - bRectClipRegion = false; - } - else - bRectClipRegion = true; - - rClipPolyPoly = aClipPoly; - - if (maGraphic.GetPrefMapMode().GetMapUnit() == MapUnit::MapPixel) - aSize100 = Application::GetDefaultDevice()->PixelToLogic( maGraphic.GetPrefSize(), aMap100 ); - else - { - MapMode m(maGraphic.GetPrefMapMode()); - aSize100 = pOut->LogicToLogic( maGraphic.GetPrefSize(), &m, &aMap100 ); - } - - nTotalWidth = aSize100.Width() - pAttr->GetLeftCrop() - pAttr->GetRightCrop(); - nTotalHeight = aSize100.Height() - pAttr->GetTopCrop() - pAttr->GetBottomCrop(); - - if( aSize100.Width() > 0 && aSize100.Height() > 0 && nTotalWidth > 0 && nTotalHeight > 0 ) - { - double fScale = static_cast<double>(aSize100.Width()) / nTotalWidth; - const long nNewLeft = -FRound( ( ( pAttr->GetMirrorFlags() & BmpMirrorFlags::Horizontal ) ? pAttr->GetRightCrop() : pAttr->GetLeftCrop() ) * fScale ); - const long nNewRight = nNewLeft + FRound( aSize100.Width() * fScale ) - 1; - - fScale = static_cast<double>(rSz.Width()) / aSize100.Width(); - rPt.AdjustX(FRound( nNewLeft * fScale ) ); - rSz.setWidth( FRound( ( nNewRight - nNewLeft + 1 ) * fScale ) ); - - fScale = static_cast<double>(aSize100.Height()) / nTotalHeight; - const long nNewTop = -FRound( ( ( pAttr->GetMirrorFlags() & BmpMirrorFlags::Vertical ) ? pAttr->GetBottomCrop() : pAttr->GetTopCrop() ) * fScale ); - const long nNewBottom = nNewTop + FRound( aSize100.Height() * fScale ) - 1; - - fScale = static_cast<double>(rSz.Height()) / aSize100.Height(); - rPt.AdjustY(FRound( nNewTop * fScale ) ); - rSz.setHeight( FRound( ( nNewBottom - nNewTop + 1 ) * fScale ) ); - - if( nRot10 ) - { - tools::Polygon aOriginPoly( 1 ); - - aOriginPoly[ 0 ] = rPt; - aOriginPoly.Rotate( aOldOrigin, nRot10 ); - rPt = aOriginPoly[ 0 ]; - } - - bRet = true; - } - } - - return bRet; -} - -GraphicObject& GraphicObject::operator=( const GraphicObject& rGraphicObj ) -{ - if( &rGraphicObj != this ) - { - mpGlobalMgr->ImplUnregisterObj( *this ); - - maSwapStreamHdl = Link<const GraphicObject*, SvStream*>(); - mxSimpleCache.reset(); - - maGraphic = rGraphicObj.GetGraphic(); - maAttr = rGraphicObj.maAttr; - maLink = rGraphicObj.maLink; - maUserData = rGraphicObj.maUserData; - ImplAssignGraphicData(); - mbAutoSwapped = false; - mpGlobalMgr->ImplRegisterObj( *this, maGraphic, nullptr, &rGraphicObj ); - if( rGraphicObj.HasUserData() && rGraphicObj.IsSwappedOut() ) - SetSwapState(); - } - - return *this; -} - -bool GraphicObject::operator==( const GraphicObject& rGraphicObj ) const -{ - return( ( rGraphicObj.maGraphic == maGraphic ) && - ( rGraphicObj.maAttr == maAttr ) && - ( rGraphicObj.GetLink() == GetLink() ) ); -} - -OString GraphicObject::GetUniqueID() const -{ - if ( !IsInSwapIn() && IsEPS() ) - const_cast<GraphicObject*>(this)->FireSwapInRequest(); - - return mpGlobalMgr->ImplGetUniqueID(*this); -} - -SvStream* GraphicObject::GetSwapStream() const -{ - if( HasSwapStreamHdl() ) - return maSwapStreamHdl.Call( this ); - else - return GRFMGR_AUTOSWAPSTREAM_NONE; -} - -void GraphicObject::SetAttr( const GraphicAttr& rAttr ) -{ - maAttr = rAttr; - - if (mxSimpleCache && (mxSimpleCache->maAttr != rAttr)) - mxSimpleCache.reset(); -} - -void GraphicObject::SetLink() -{ - maLink.clear(); -} - -void GraphicObject::SetLink( const OUString& rLink ) -{ - maLink = rLink; -} - -void GraphicObject::SetUserData() -{ - maUserData.clear(); -} - -void GraphicObject::SetUserData( const OUString& rUserData ) -{ - maUserData = rUserData; - if( !rUserData.isEmpty() ) - SetSwapState(); -} - -static sal_uInt32 GetCacheTimeInMs() -{ - if (utl::ConfigManager::IsFuzzing()) - return 20000; - - const sal_uInt32 nSeconds = - officecfg::Office::Common::Cache::GraphicManager::ObjectReleaseTime::get( - comphelper::getProcessComponentContext()); - - return nSeconds * 1000; -} - -void GraphicObject::SetSwapStreamHdl(const Link<const GraphicObject*, SvStream*>& rHdl) -{ - maSwapStreamHdl = rHdl; - - sal_uInt32 const nSwapOutTimeout(GetCacheTimeInMs()); - if (nSwapOutTimeout) - { - if (!mxSwapOutTimer) - { - mxSwapOutTimer.reset(new Timer("svtools::GraphicObject mpSwapOutTimer")); - mxSwapOutTimer->SetInvokeHandler( LINK( this, GraphicObject, ImplAutoSwapOutHdl ) ); - } - - mxSwapOutTimer->SetTimeout( nSwapOutTimeout ); - mxSwapOutTimer->Start(); - } - else - { - mxSwapOutTimer.reset(); - } -} - -void GraphicObject::FireSwapInRequest() -{ - ImplAutoSwapIn(); -} - -void GraphicObject::FireSwapOutRequest() -{ - ImplAutoSwapOutHdl( nullptr ); -} - -bool GraphicObject::IsCached( OutputDevice const * pOut, const Size& rSz, - const GraphicAttr* pAttr, GraphicManagerDrawFlags nFlags ) const -{ - bool bRet; - - if( nFlags & GraphicManagerDrawFlags::CACHED ) - { - Point aPt; - Size aSz( rSz ); - if ( pAttr && pAttr->IsCropped() ) - { - tools::PolyPolygon aClipPolyPoly; - bool bRectClip; - ImplGetCropParams( pOut, aPt, aSz, pAttr, aClipPolyPoly, bRectClip ); - } - bRet = mpGlobalMgr->IsInCache( pOut, aPt, aSz, *this, ( pAttr ? *pAttr : GetAttr() ) ); - } - else - bRet = false; - - return bRet; -} - -bool GraphicObject::Draw( OutputDevice* pOut, const Point& rPt, const Size& rSz, - const GraphicAttr* pAttr, GraphicManagerDrawFlags nFlags ) -{ - GraphicAttr aAttr( pAttr ? *pAttr : GetAttr() ); - Point aPt( rPt ); - Size aSz( rSz ); - const DrawModeFlags nOldDrawMode = pOut->GetDrawMode(); - bool bCropped = aAttr.IsCropped(); - bool bCached = false; - bool bRet; - - // #i29534# Provide output rects for PDF writer - tools::Rectangle aCropRect; - - if( !( GraphicManagerDrawFlags::USE_DRAWMODE_SETTINGS & nFlags ) ) - pOut->SetDrawMode( nOldDrawMode & ~DrawModeFlags( DrawModeFlags::SettingsLine | DrawModeFlags::SettingsFill | DrawModeFlags::SettingsText | DrawModeFlags::SettingsGradient ) ); - - // mirrored horizontically - if( aSz.Width() < 0 ) - { - aPt.AdjustX(aSz.Width() + 1 ); - aSz.setWidth( -aSz.Width() ); - aAttr.SetMirrorFlags( aAttr.GetMirrorFlags() ^ BmpMirrorFlags::Horizontal ); - } - - // mirrored vertically - if( aSz.Height() < 0 ) - { - aPt.AdjustY(aSz.Height() + 1 ); - aSz.setHeight( -aSz.Height() ); - aAttr.SetMirrorFlags( aAttr.GetMirrorFlags() ^ BmpMirrorFlags::Vertical ); - } - - if( bCropped ) - { - tools::PolyPolygon aClipPolyPoly; - bool bRectClip; - const bool bCrop = ImplGetCropParams( pOut, aPt, aSz, &aAttr, aClipPolyPoly, bRectClip ); - - pOut->Push( PushFlags::CLIPREGION ); - - if( bCrop ) - { - if( bRectClip ) - { - // #i29534# Store crop rect for later forwarding to - // PDF writer - aCropRect = aClipPolyPoly.GetBoundRect(); - pOut->IntersectClipRegion( aCropRect ); - } - else - { - pOut->IntersectClipRegion(vcl::Region(aClipPolyPoly)); - } - } - } - - bRet = mpGlobalMgr->DrawObj( pOut, aPt, aSz, *this, aAttr, nFlags, bCached ); - - if( bCropped ) - pOut->Pop(); - - pOut->SetDrawMode( nOldDrawMode ); - - // #i29534# Moved below OutDev restoration, to avoid multiple swap-ins - // (code above needs to call GetGraphic twice) - if( bCached ) - { - if (mxSwapOutTimer) - mxSwapOutTimer->Start(); - else - FireSwapOutRequest(); - } - - return bRet; -} - -void GraphicObject::DrawTiled( OutputDevice* pOut, const tools::Rectangle& rArea, const Size& rSize, - const Size& rOffset, GraphicManagerDrawFlags nFlags, int nTileCacheSize1D ) -{ - if( pOut == nullptr || rSize.Width() == 0 || rSize.Height() == 0 ) - return; - - const MapMode aOutMapMode( pOut->GetMapMode() ); - const MapMode aMapMode( aOutMapMode.GetMapUnit(), Point(), aOutMapMode.GetScaleX(), aOutMapMode.GetScaleY() ); - // #106258# Clamp size to 1 for zero values. This is okay, since - // logical size of zero is handled above already - const Size aOutTileSize( ::std::max( 1L, pOut->LogicToPixel( rSize, aOutMapMode ).Width() ), - ::std::max( 1L, pOut->LogicToPixel( rSize, aOutMapMode ).Height() ) ); - - //#i69780 clip final tile size to a sane max size - while ((static_cast<sal_Int64>(rSize.Width()) * nTileCacheSize1D) > SAL_MAX_UINT16) - nTileCacheSize1D /= 2; - while ((static_cast<sal_Int64>(rSize.Height()) * nTileCacheSize1D) > SAL_MAX_UINT16) - nTileCacheSize1D /= 2; - - ImplDrawTiled( pOut, rArea, aOutTileSize, rOffset, nullptr, nFlags, nTileCacheSize1D ); -} - -bool GraphicObject::StartAnimation( OutputDevice* pOut, const Point& rPt, const Size& rSz, - long nExtraData, - OutputDevice* pFirstFrameOutDev ) -{ - bool bRet = false; - - GetGraphic(); - - if( !IsSwappedOut() ) - { - const GraphicAttr aAttr( GetAttr() ); - - if( mbAnimated ) - { - Point aPt( rPt ); - Size aSz( rSz ); - bool bCropped = aAttr.IsCropped(); - - if( bCropped ) - { - tools::PolyPolygon aClipPolyPoly; - bool bRectClip; - const bool bCrop = ImplGetCropParams( pOut, aPt, aSz, &aAttr, aClipPolyPoly, bRectClip ); - - pOut->Push( PushFlags::CLIPREGION ); - - if( bCrop ) - { - if( bRectClip ) - pOut->IntersectClipRegion( aClipPolyPoly.GetBoundRect() ); - else - pOut->IntersectClipRegion(vcl::Region(aClipPolyPoly)); - } - } - - if (!mxSimpleCache || (mxSimpleCache->maAttr != aAttr) || pFirstFrameOutDev) - { - mxSimpleCache.reset(new GrfSimpleCacheObj(GetTransformedGraphic(&aAttr), aAttr)); - mxSimpleCache->maGraphic.SetAnimationNotifyHdl(GetGraphic().GetAnimationNotifyHdl()); - } - - mxSimpleCache->maGraphic.StartAnimation(pOut, aPt, aSz, nExtraData, pFirstFrameOutDev); - - if( bCropped ) - pOut->Pop(); - - bRet = true; - } - else - bRet = Draw( pOut, rPt, rSz, &aAttr ); - } - - return bRet; -} - -void GraphicObject::StopAnimation( OutputDevice* pOut, long nExtraData ) -{ - if (mxSimpleCache) - mxSimpleCache->maGraphic.StopAnimation(pOut, nExtraData); -} - -const Graphic& GraphicObject::GetGraphic() const -{ - GraphicObject *pThis = const_cast<GraphicObject*>(this); - (void)pThis->SwapIn(); - - //fdo#50697 If we've been asked to provide the graphic, then reset - //the cache timeout to start from now and not remain at the - //time of creation - // restart SwapOut timer; this is like touching in a cache to reset to the full timeout value - if (pThis->mxSwapOutTimer && pThis->mxSwapOutTimer->IsActive()) - { - pThis->mxSwapOutTimer->Stop(); - pThis->mxSwapOutTimer->Start(); - } - - return maGraphic; -} - -void GraphicObject::SetGraphic( const Graphic& rGraphic, const GraphicObject* pCopyObj ) -{ - mpGlobalMgr->ImplUnregisterObj( *this ); - - if (mxSwapOutTimer) - mxSwapOutTimer->Stop(); - - maGraphic = rGraphic; - mbAutoSwapped = false; - ImplAssignGraphicData(); - maLink.clear(); - mxSimpleCache.reset(); - - mpGlobalMgr->ImplRegisterObj( *this, maGraphic, nullptr, pCopyObj); - - if (mxSwapOutTimer) - mxSwapOutTimer->Start(); - - -} - -void GraphicObject::SetGraphic( const Graphic& rGraphic, const OUString& rLink ) -{ - // in case we are called from a situation where rLink and maLink are the same thing, - // we need a copy because SetGraphic clears maLink - OUString sLinkCopy = rLink; - SetGraphic( rGraphic ); - maLink = sLinkCopy; -} - -Graphic GraphicObject::GetTransformedGraphic( const Size& rDestSize, const MapMode& rDestMap, const GraphicAttr& rAttr ) const -{ - // #104550# Extracted from svx/source/svdraw/svdograf.cxx - Graphic aTransGraphic( GetGraphic() ); - const GraphicType eType = GetType(); - const Size aSrcSize( aTransGraphic.GetPrefSize() ); - - // #104115# Convert the crop margins to graphic object mapmode - const MapMode aMapGraph( aTransGraphic.GetPrefMapMode() ); - const MapMode aMap100( MapUnit::Map100thMM ); - - Size aCropLeftTop; - Size aCropRightBottom; - - if( GraphicType::GdiMetafile == eType ) - { - GDIMetaFile aMtf( aTransGraphic.GetGDIMetaFile() ); - - if (aMapGraph.GetMapUnit() == MapUnit::MapPixel) - { - // crops are in 1/100th mm -> to aMapGraph -> to MapUnit::MapPixel - aCropLeftTop = Application::GetDefaultDevice()->LogicToPixel( - Size(rAttr.GetLeftCrop(), rAttr.GetTopCrop()), - aMap100); - aCropRightBottom = Application::GetDefaultDevice()->LogicToPixel( - Size(rAttr.GetRightCrop(), rAttr.GetBottomCrop()), - aMap100); - } - else - { - // crops are in GraphicObject units -> to aMapGraph - aCropLeftTop = OutputDevice::LogicToLogic( - Size(rAttr.GetLeftCrop(), rAttr.GetTopCrop()), - aMap100, - aMapGraph); - aCropRightBottom = OutputDevice::LogicToLogic( - Size(rAttr.GetRightCrop(), rAttr.GetBottomCrop()), - aMap100, - aMapGraph); - } - - // #104115# If the metafile is cropped, give it a special - // treatment: clip against the remaining area, scale up such - // that this area later fills the desired size, and move the - // origin to the upper left edge of that area. - if( rAttr.IsCropped() ) - { - const MapMode aMtfMapMode( aMtf.GetPrefMapMode() ); - - tools::Rectangle aClipRect( aMtfMapMode.GetOrigin().X() + aCropLeftTop.Width(), - aMtfMapMode.GetOrigin().Y() + aCropLeftTop.Height(), - aMtfMapMode.GetOrigin().X() + aSrcSize.Width() - aCropRightBottom.Width(), - aMtfMapMode.GetOrigin().Y() + aSrcSize.Height() - aCropRightBottom.Height() ); - - // #104115# To correctly crop rotated metafiles, clip by view rectangle - aMtf.AddAction( new MetaISectRectClipRegionAction( aClipRect ), 0 ); - - // #104115# To crop the metafile, scale larger than the output rectangle - aMtf.Scale( static_cast<double>(rDestSize.Width()) / (aSrcSize.Width() - aCropLeftTop.Width() - aCropRightBottom.Width()), - static_cast<double>(rDestSize.Height()) / (aSrcSize.Height() - aCropLeftTop.Height() - aCropRightBottom.Height()) ); - - // #104115# Adapt the pref size by hand (scale changes it - // proportionally, but we want it to be smaller than the - // former size, to crop the excess out) - aMtf.SetPrefSize( Size( static_cast<long>(static_cast<double>(rDestSize.Width()) * (1.0 + (aCropLeftTop.Width() + aCropRightBottom.Width()) / aSrcSize.Width()) + .5), - static_cast<long>(static_cast<double>(rDestSize.Height()) * (1.0 + (aCropLeftTop.Height() + aCropRightBottom.Height()) / aSrcSize.Height()) + .5) ) ); - - // #104115# Adapt the origin of the new mapmode, such that it - // is shifted to the place where the cropped output starts - Point aNewOrigin( static_cast<long>(static_cast<double>(aMtfMapMode.GetOrigin().X()) + rDestSize.Width() * aCropLeftTop.Width() / (aSrcSize.Width() - aCropLeftTop.Width() - aCropRightBottom.Width()) + .5), - static_cast<long>(static_cast<double>(aMtfMapMode.GetOrigin().Y()) + rDestSize.Height() * aCropLeftTop.Height() / (aSrcSize.Height() - aCropLeftTop.Height() - aCropRightBottom.Height()) + .5) ); - MapMode aNewMap( rDestMap ); - aNewMap.SetOrigin( OutputDevice::LogicToLogic(aNewOrigin, aMtfMapMode, rDestMap) ); - aMtf.SetPrefMapMode( aNewMap ); - } - else - { - aMtf.Scale( Fraction( rDestSize.Width(), aSrcSize.Width() ), Fraction( rDestSize.Height(), aSrcSize.Height() ) ); - aMtf.SetPrefMapMode( rDestMap ); - } - - aTransGraphic = aMtf; - } - else if( GraphicType::Bitmap == eType ) - { - BitmapEx aBitmapEx( aTransGraphic.GetBitmapEx() ); - tools::Rectangle aCropRect; - - // convert crops to pixel - if(rAttr.IsCropped()) - { - if (aMapGraph.GetMapUnit() == MapUnit::MapPixel) - { - // crops are in 1/100th mm -> to MapUnit::MapPixel - aCropLeftTop = Application::GetDefaultDevice()->LogicToPixel( - Size(rAttr.GetLeftCrop(), rAttr.GetTopCrop()), - aMap100); - aCropRightBottom = Application::GetDefaultDevice()->LogicToPixel( - Size(rAttr.GetRightCrop(), rAttr.GetBottomCrop()), - aMap100); - } - else - { - // crops are in GraphicObject units -> to MapUnit::MapPixel - aCropLeftTop = Application::GetDefaultDevice()->LogicToPixel( - Size(rAttr.GetLeftCrop(), rAttr.GetTopCrop()), - aMapGraph); - aCropRightBottom = Application::GetDefaultDevice()->LogicToPixel( - Size(rAttr.GetRightCrop(), rAttr.GetBottomCrop()), - aMapGraph); - } - - // convert from prefmapmode to pixel - Size aSrcSizePixel( - Application::GetDefaultDevice()->LogicToPixel( - aSrcSize, - aMapGraph)); - - if(rAttr.IsCropped() - && (aSrcSizePixel.Width() != aBitmapEx.GetSizePixel().Width() || aSrcSizePixel.Height() != aBitmapEx.GetSizePixel().Height()) - && aSrcSizePixel.Width()) - { - // the size in pixels calculated from Graphic's internal MapMode (aTransGraphic.GetPrefMapMode()) - // and it's internal size (aTransGraphic.GetPrefSize()) is different from its real pixel size. - // This can be interpreted as this values to be set wrong, but needs to be corrected since e.g. - // existing cropping is calculated based on this logic values already. - // aBitmapEx.Scale(aSrcSizePixel); - - // another possibility is to adapt the values created so far with a factor; this - // will keep the original Bitmap untouched and thus quality will not change - // caution: convert to double first, else pretty big errors may occur - const double fFactorX(static_cast<double>(aBitmapEx.GetSizePixel().Width()) / aSrcSizePixel.Width()); - const double fFactorY(static_cast<double>(aBitmapEx.GetSizePixel().Height()) / aSrcSizePixel.Height()); - - aCropLeftTop.setWidth( basegfx::fround(aCropLeftTop.Width() * fFactorX) ); - aCropLeftTop.setHeight( basegfx::fround(aCropLeftTop.Height() * fFactorY) ); - aCropRightBottom.setWidth( basegfx::fround(aCropRightBottom.Width() * fFactorX) ); - aCropRightBottom.setHeight( basegfx::fround(aCropRightBottom.Height() * fFactorY) ); - - aSrcSizePixel = aBitmapEx.GetSizePixel(); - } - - // setup crop rectangle in pixel - aCropRect = tools::Rectangle( aCropLeftTop.Width(), aCropLeftTop.Height(), - aSrcSizePixel.Width() - aCropRightBottom.Width(), - aSrcSizePixel.Height() - aCropRightBottom.Height() ); - } - - // #105641# Also crop animations - if( aTransGraphic.IsAnimated() ) - { - Animation aAnim( aTransGraphic.GetAnimation() ); - - for( size_t nFrame=0; nFrame<aAnim.Count(); ++nFrame ) - { - AnimationBitmap aAnimBmp( aAnim.Get( nFrame ) ); - - if( !aCropRect.IsInside( tools::Rectangle(aAnimBmp.aPosPix, aAnimBmp.aSizePix) ) ) - { - // setup actual cropping (relative to frame position) - tools::Rectangle aCropRectRel( aCropRect ); - aCropRectRel.Move( -aAnimBmp.aPosPix.X(), - -aAnimBmp.aPosPix.Y() ); - - // cropping affects this frame, apply it then - // do _not_ apply enlargement, this is done below - ImplTransformBitmap( aAnimBmp.aBmpEx, rAttr, Size(), Size(), - aCropRectRel, rDestSize, false ); - - aAnim.Replace( aAnimBmp, nFrame ); - } - // else: bitmap completely within crop area, - // i.e. nothing is cropped away - } - - // now, apply enlargement (if any) through global animation size - if( aCropLeftTop.Width() < 0 || - aCropLeftTop.Height() < 0 || - aCropRightBottom.Width() < 0 || - aCropRightBottom.Height() < 0 ) - { - Size aNewSize( aAnim.GetDisplaySizePixel() ); - aNewSize.AdjustWidth(aCropRightBottom.Width() < 0 ? -aCropRightBottom.Width() : 0 ); - aNewSize.AdjustWidth(aCropLeftTop.Width() < 0 ? -aCropLeftTop.Width() : 0 ); - aNewSize.AdjustHeight(aCropRightBottom.Height() < 0 ? -aCropRightBottom.Height() : 0 ); - aNewSize.AdjustHeight(aCropLeftTop.Height() < 0 ? -aCropLeftTop.Height() : 0 ); - aAnim.SetDisplaySizePixel( aNewSize ); - } - - // if topleft has changed, we must move all frames to the - // right and bottom, resp. - if( aCropLeftTop.Width() < 0 || - aCropLeftTop.Height() < 0 ) - { - Point aPosOffset( aCropLeftTop.Width() < 0 ? -aCropLeftTop.Width() : 0, - aCropLeftTop.Height() < 0 ? -aCropLeftTop.Height() : 0 ); - - for( size_t nFrame=0; nFrame<aAnim.Count(); ++nFrame ) - { - AnimationBitmap aAnimBmp( aAnim.Get( nFrame ) ); - - aAnimBmp.aPosPix += aPosOffset; - - aAnim.Replace( aAnimBmp, nFrame ); - } - } - - aTransGraphic = aAnim; - } - else - { - ImplTransformBitmap( aBitmapEx, rAttr, aCropLeftTop, aCropRightBottom, - aCropRect, rDestSize, true ); - - aTransGraphic = aBitmapEx; - } - - aTransGraphic.SetPrefSize( rDestSize ); - aTransGraphic.SetPrefMapMode( rDestMap ); - } - - GraphicObject aGrfObj( aTransGraphic ); - aTransGraphic = aGrfObj.GetTransformedGraphic( &rAttr ); - - return aTransGraphic; -} - -Graphic GraphicObject::GetTransformedGraphic( const GraphicAttr* pAttr ) const // TODO: Change to Impl -{ - GetGraphic(); - - Graphic aGraphic; - GraphicAttr aAttr( pAttr ? *pAttr : GetAttr() ); - - if( maGraphic.IsSupportedGraphic() && !maGraphic.IsSwapOut() ) - { - if( aAttr.IsSpecialDrawMode() || aAttr.IsAdjusted() || aAttr.IsMirrored() || aAttr.IsRotated() || aAttr.IsTransparent() ) - { - if( GetType() == GraphicType::Bitmap ) - { - if( IsAnimated() ) - { - Animation aAnimation( maGraphic.GetAnimation() ); - GraphicManager::ImplAdjust( aAnimation, aAttr, GraphicAdjustmentFlags::ALL ); - aAnimation.SetLoopCount( mnAnimationLoopCount ); - aGraphic = aAnimation; - } - else - { - BitmapEx aBmpEx( maGraphic.GetBitmapEx() ); - GraphicManager::ImplAdjust( aBmpEx, aAttr, GraphicAdjustmentFlags::ALL ); - aGraphic = aBmpEx; - } - } - else - { - GDIMetaFile aMtf( maGraphic.GetGDIMetaFile() ); - GraphicManager::ImplAdjust( aMtf, aAttr, GraphicAdjustmentFlags::ALL ); - aGraphic = aMtf; - } - } - else - { - if( ( GetType() == GraphicType::Bitmap ) && IsAnimated() ) - { - Animation aAnimation( maGraphic.GetAnimation() ); - aAnimation.SetLoopCount( mnAnimationLoopCount ); - aGraphic = aAnimation; - } - else - aGraphic = maGraphic; - } - } - - return aGraphic; -} - -bool GraphicObject::SwapOut() -{ - const bool bRet = !mbAutoSwapped && maGraphic.SwapOut(); - - if (bRet) - mpGlobalMgr->ImplGraphicObjectWasSwappedOut( *this ); - - return bRet; -} - -bool GraphicObject::SwapOut( SvStream* pOStm ) -{ - bool bRet = false; - try - { - bRet = !mbAutoSwapped; - // swap out as a link - if( pOStm == GRFMGR_AUTOSWAPSTREAM_LINK ) - { - maGraphic.SwapOutAsLink(); - } - else - { - bRet = bRet && maGraphic.SwapOut( pOStm ); - } - - if (bRet) - mpGlobalMgr->ImplGraphicObjectWasSwappedOut(*this); - } - catch(...) - { - SAL_WARN( "svtools", "GraphicObject::SwapIn exception"); - } - return bRet; -} - -bool GraphicObject::SwapIn() -{ - bool bRet = false; - try - { - if( mbAutoSwapped ) - { - ImplAutoSwapIn(); - bRet = true; - } - else - { - bRet = maGraphic.SwapIn(); - - if (bRet) - mpGlobalMgr->ImplGraphicObjectWasSwappedIn(*this); - } - - if( bRet ) - { - ImplAssignGraphicData(); - } - } - catch (...) - { - SAL_WARN( "svtools", "GraphicObject::SwapIn exception"); - } - - return bRet; -} - -void GraphicObject::SetSwapState() -{ - if( !IsSwappedOut() ) - { - mbAutoSwapped = true; - - mpGlobalMgr->ImplGraphicObjectWasSwappedOut(*this); - } -} - -IMPL_LINK_NOARG(GraphicObject, ImplAutoSwapOutHdl, Timer *, void) -{ - if( !IsSwappedOut() ) - { - mbIsInSwapOut = true; - - SvStream* pStream = GetSwapStream(); - - if( GRFMGR_AUTOSWAPSTREAM_NONE != pStream ) - { - if( GRFMGR_AUTOSWAPSTREAM_LINK == pStream ) - mbAutoSwapped = SwapOut( GRFMGR_AUTOSWAPSTREAM_LINK ); - else - { - if( GRFMGR_AUTOSWAPSTREAM_TEMP == pStream ) - mbAutoSwapped = SwapOut(); - else - { - mbAutoSwapped = SwapOut( pStream ); - delete pStream; - } - } - } - - mbIsInSwapOut = false; - } - - if (mxSwapOutTimer) - mxSwapOutTimer->Start(); -} - -#define UNO_NAME_GRAPHOBJ_URLPREFIX "vnd.sun.star.GraphicObject:" - -bool GraphicObject::isGraphicObjectUniqueIdURL(OUString const & rURL) -{ - const OUString aPrefix(UNO_NAME_GRAPHOBJ_URLPREFIX); - return rURL.startsWith(aPrefix); -} - -void -GraphicObject::InspectForGraphicObjectImageURL( const Reference< XInterface >& xIf, std::vector< OUString >& rvEmbedImgUrls ) -{ - static const char sImageURL[] = "ImageURL"; - Reference< XPropertySet > xProps( xIf, UNO_QUERY ); - if ( xProps.is() ) - { - - if ( xProps->getPropertySetInfo()->hasPropertyByName( sImageURL ) ) - { - OUString sURL; - xProps->getPropertyValue( sImageURL ) >>= sURL; - if ( !sURL.isEmpty() && sURL.startsWith( UNO_NAME_GRAPHOBJ_URLPREFIX ) ) - rvEmbedImgUrls.push_back( sURL ); - } - } - Reference< XNameContainer > xContainer( xIf, UNO_QUERY ); - if ( xContainer.is() ) - { - Sequence< OUString > sNames = xContainer->getElementNames(); - sal_Int32 nContainees = sNames.getLength(); - for ( sal_Int32 index = 0; index < nContainees; ++index ) - { - Reference< XInterface > xCtrl; - xContainer->getByName( sNames[ index ] ) >>= xCtrl; - InspectForGraphicObjectImageURL( xCtrl, rvEmbedImgUrls ); - } - } -} - -// calculate scalings between real image size and logic object size. This -// is necessary since the crop values are relative to original bitmap size -basegfx::B2DVector GraphicObject::calculateCropScaling( - double fWidth, - double fHeight, - double fLeftCrop, - double fTopCrop, - double fRightCrop, - double fBottomCrop) const -{ - const MapMode aMapMode100thmm(MapUnit::Map100thMM); - Size aBitmapSize(GetPrefSize()); - double fFactorX(1.0); - double fFactorY(1.0); - - if(MapUnit::MapPixel == GetPrefMapMode().GetMapUnit()) - { - aBitmapSize = Application::GetDefaultDevice()->PixelToLogic(aBitmapSize, aMapMode100thmm); - } - else - { - aBitmapSize = OutputDevice::LogicToLogic(aBitmapSize, GetPrefMapMode(), aMapMode100thmm); - } - - const double fDivX(aBitmapSize.Width() - fLeftCrop - fRightCrop); - const double fDivY(aBitmapSize.Height() - fTopCrop - fBottomCrop); - - if(!basegfx::fTools::equalZero(fDivX)) - { - fFactorX = fabs(fWidth) / fDivX; - } - - if(!basegfx::fTools::equalZero(fDivY)) - { - fFactorY = fabs(fHeight) / fDivY; - } - - return basegfx::B2DVector(fFactorX,fFactorY); -} - - -/* vim:set shiftwidth=4 softtabstop=4 expandtab: */ diff --git a/svtools/source/graphic/grfmgr2.cxx b/svtools/source/graphic/grfmgr2.cxx deleted file mode 100644 index d19f8c1eae04..000000000000 --- a/svtools/source/graphic/grfmgr2.cxx +++ /dev/null @@ -1,2066 +0,0 @@ -/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */ -/* - * This file is part of the LibreOffice project. - * - * This Source Code Form is subject to the terms of the Mozilla Public - * License, v. 2.0. If a copy of the MPL was not distributed with this - * file, You can obtain one at http://mozilla.org/MPL/2.0/. - * - * This file incorporates work covered by the following license notice: - * - * Licensed to the Apache Software Foundation (ASF) under one or more - * contributor license agreements. See the NOTICE file distributed - * with this work for additional information regarding copyright - * ownership. The ASF licenses this file to you under the Apache - * License, Version 2.0 (the "License"); you may not use this file - * except in compliance with the License. You may obtain a copy of - * the License at http://www.apache.org/licenses/LICENSE-2.0 . - */ - -#include <sal/config.h> - -#include <cstdlib> - -#include <vcl/bitmapaccess.hxx> -#include <tools/poly.hxx> -#include <vcl/outdev.hxx> -#include <vcl/window.hxx> -#include <vcl/gdimtf.hxx> -#include <vcl/metaact.hxx> -#include <vcl/metric.hxx> -#include <vcl/animate.hxx> -#include <vcl/alpha.hxx> -#include <vcl/virdev.hxx> -#include "grfcache.hxx" -#include <svtools/grfmgr.hxx> -#include <memory> - - -#define WATERMARK_LUM_OFFSET 50 -#define WATERMARK_CON_OFFSET -70 - -namespace { - -constexpr sal_uInt8 MAP(long cVal0, long cVal1, long nFrac) { - return static_cast<sal_uInt8>(((cVal0<<20)+nFrac*(cVal1-cVal0))>>20); -} - -} - -GraphicManager::GraphicManager( sal_uLong nCacheSize, sal_uLong nMaxObjCacheSize ) : - mnUsedSize(0), - mpCache( new GraphicCache( nCacheSize, nMaxObjCacheSize ) ) -{ -} - -GraphicManager::~GraphicManager() -{ - assert(maObjList.empty()); - mpCache.reset(); -} - -void GraphicManager::SetMaxCacheSize( sal_uLong nNewCacheSize ) -{ - mpCache->SetMaxDisplayCacheSize( nNewCacheSize ); -} - -sal_uLong GraphicManager::GetMaxCacheSize() const -{ - return mpCache->GetMaxDisplayCacheSize(); -} - -void GraphicManager::SetCacheTimeout( sal_uLong nTimeoutSeconds ) -{ - mpCache->SetCacheTimeout( nTimeoutSeconds ); -} - -bool GraphicManager::IsInCache( OutputDevice const * pOut, const Point& rPt, - const Size& rSz, const GraphicObject& rObj, - const GraphicAttr& rAttr ) const -{ - return mpCache->IsInDisplayCache( pOut, rPt, rSz, rObj, rAttr ); -} - -bool GraphicManager::DrawObj( OutputDevice* pOut, const Point& rPt, const Size& rSz, - GraphicObject const & rObj, const GraphicAttr& rAttr, - const GraphicManagerDrawFlags nFlags, bool& rCached ) -{ - Point aPt( rPt ); - Size aSz( rSz ); - bool bRet = false; - - rCached = false; - - if( ( rObj.GetType() == GraphicType::Bitmap ) || ( rObj.GetType() == GraphicType::GdiMetafile ) ) - { - // create output and fill cache - - if( rObj.IsAnimated() || ( pOut->GetOutDevType() == OUTDEV_PRINTER ) || - ( !( nFlags & GraphicManagerDrawFlags::NO_SUBSTITUTE ) && - ( ( nFlags & GraphicManagerDrawFlags::SUBSTITUTE ) || - !( nFlags & GraphicManagerDrawFlags::CACHED ) || - ( pOut->GetConnectMetaFile() && !pOut->IsOutputEnabled() ) ) ) ) - { - // simple output of transformed graphic - const Graphic aGraphic( rObj.GetTransformedGraphic( &rAttr ) ); - - if( aGraphic.IsSupportedGraphic() ) - { - const sal_uInt16 nRot10 = rAttr.GetRotation() % 3600; - - if( nRot10 ) - { - tools::Polygon aPoly( tools::Rectangle( aPt, aSz ) ); - - aPoly.Rotate( aPt, nRot10 ); - const tools::Rectangle aRotBoundRect( aPoly.GetBoundRect() ); - aPt = aRotBoundRect.TopLeft(); - aSz = aRotBoundRect.GetSize(); - } - - aGraphic.Draw( pOut, aPt, aSz ); - } - - bRet = true; - } - - if( !bRet ) - { - // cached/direct drawing - if( !mpCache->DrawDisplayCacheObj( pOut, aPt, aSz, rObj, rAttr ) ) - bRet = ImplDraw( pOut, aPt, aSz, rObj, rAttr, rCached ); - else - bRet = rCached = true; - } - } - - return bRet; -} - -void GraphicManager::ImplRegisterObj( const GraphicObject& rObj, Graphic& rSubstitute, - const OString* pID, const GraphicObject* pCopyObj ) -{ - assert(maObjList.find(const_cast<GraphicObject*>(&rObj)) == maObjList.end()); - - maObjList.emplace( const_cast<GraphicObject*>(&rObj) ); - - mpCache->AddGraphicObject( rObj, rSubstitute, pID, pCopyObj ); - if( !rObj.IsSwappedOut() ) - mnUsedSize += rObj.maGraphic.GetSizeBytes(); -} - -void GraphicManager::ImplUnregisterObj( const GraphicObject& rObj ) -{ - mpCache->ReleaseGraphicObject( rObj ); - if( !rObj.IsSwappedOut() ) - { - assert(mnUsedSize >= rObj.maGraphic.GetSizeBytes()); - mnUsedSize -= rObj.maGraphic.GetSizeBytes(); - } - if ( 0 < maObjList.erase( const_cast<GraphicObject*>(&rObj) ) ) - return; - - assert(false); // surely it should have been registered? -} - -void GraphicManager::ImplGraphicObjectWasSwappedOut( const GraphicObject& rObj ) -{ - mpCache->GraphicObjectWasSwappedOut( rObj ); - assert(mnUsedSize >= rObj.GetSizeBytes()); - mnUsedSize -= rObj.GetSizeBytes(); -} - -OString GraphicManager::ImplGetUniqueID( const GraphicObject& rObj ) const -{ - return mpCache->GetUniqueID( rObj ); -} - -namespace -{ - struct simpleSortByDataChangeTimeStamp - { - bool operator() (GraphicObject const * p1, GraphicObject const * p2) const - { - return p1->GetDataChangeTimeStamp() < p2->GetDataChangeTimeStamp(); - } - }; -} // end of anonymous namespace - -void GraphicManager::ImplCheckSizeOfSwappedInGraphics(const GraphicObject* pGraphicToIgnore) -{ - // detect maximum allowed memory footprint. Use the user-settings of MaxCacheSize (defaulted - // to 200MB). - const sal_uLong nMaxCacheSize(GetMaxCacheSize()); - - if(mnUsedSize <= nMaxCacheSize) - return; - - // Copy the object list for now, because maObjList can change in the meantime unexpectedly. - std::vector< GraphicObject* > aCandidates(maObjList.begin(), maObjList.end()); - // if we use more currently, sort by last DataChangeTimeStamp - // sort by DataChangeTimeStamp so that the oldest get removed first - std::sort(aCandidates.begin(), aCandidates.end(), simpleSortByDataChangeTimeStamp()); - - for(decltype(aCandidates)::size_type a(0); mnUsedSize >= nMaxCacheSize && a < aCandidates.size(); a++) - { - // swap out until we have no more or the goal to use less than nMaxCacheSize - // is reached - GraphicObject* pObj = aCandidates[a]; - if( pObj == pGraphicToIgnore ) - { - continue; - } - if (maObjList.find(pObj) == maObjList.end()) - { - // object has been deleted when swapping out another one - continue; - } - - // do not swap out when we have less than 16KB data objects - if(pObj->GetSizeBytes() >= (16 * 1024)) - { - pObj->FireSwapOutRequest(); - } - } -} - -void GraphicManager::ImplGraphicObjectWasSwappedIn( const GraphicObject& rObj ) -{ - mpCache->GraphicObjectWasSwappedIn( rObj ); - mnUsedSize += rObj.maGraphic.GetSizeBytes(); -} - -bool GraphicManager::ImplDraw( OutputDevice* pOut, const Point& rPt, - const Size& rSz, GraphicObject const & rObj, - const GraphicAttr& rAttr, - bool& rCached ) -{ - const Graphic& rGraphic = rObj.GetGraphic(); - bool bRet = false; - - if( rGraphic.IsSupportedGraphic() && !rObj.IsSwappedOut() ) - { - if( GraphicType::Bitmap == rGraphic.GetType() ) - { - const BitmapEx aSrcBmpEx( rGraphic.GetBitmapEx() ); - - // #i46805# No point in caching a bitmap that is rendered - // via RectFill on the OutDev - if( !(pOut->GetDrawMode() & ( DrawModeFlags::BlackBitmap | DrawModeFlags::WhiteBitmap )) && - mpCache->IsDisplayCacheable( pOut, rPt, rSz, rObj, rAttr ) ) - { - BitmapEx aDstBmpEx; - - if( ImplCreateOutput( pOut, rPt, rSz, aSrcBmpEx, rAttr, &aDstBmpEx ) ) - { - rCached = mpCache->CreateDisplayCacheObj( pOut, rPt, rSz, rObj, rAttr, aDstBmpEx ); - bRet = true; - } - } - - if( !bRet ) - bRet = ImplCreateOutput( pOut, rPt, rSz, aSrcBmpEx, rAttr ); - } - else - { - const GDIMetaFile& rSrcMtf = rGraphic.GetGDIMetaFile(); - - if( mpCache->IsDisplayCacheable( pOut, rPt, rSz, rObj, rAttr ) ) - { - GDIMetaFile aDstMtf; - BitmapEx aContainedBmpEx; - - if( ImplCreateOutput( pOut, rPt, rSz, rSrcMtf, rAttr, aDstMtf, aContainedBmpEx ) ) - { - if( !!aContainedBmpEx ) - { - // Use bitmap output method, if metafile basically contains only a single - // bitmap (allows caching the resulting pixmap). - BitmapEx aDstBmpEx; - - if( ImplCreateOutput( pOut, rPt, rSz, aContainedBmpEx, rAttr, &aDstBmpEx ) ) - { - rCached = mpCache->CreateDisplayCacheObj( pOut, rPt, rSz, rObj, rAttr, aDstBmpEx ); - bRet = true; - } - } - else - { - rCached = mpCache->CreateDisplayCacheObj( pOut, rPt, rSz, rObj, rAttr, aDstMtf ); - bRet = true; - } - } - } - - if( !bRet ) - { - const Graphic aGraphic( rObj.GetTransformedGraphic( &rAttr ) ); - - if( aGraphic.IsSupportedGraphic() ) - { - aGraphic.Draw( pOut, rPt, rSz ); - bRet = true; - } - } - } - } - - return bRet; -} - -bool ImplCreateRotatedScaled( const BitmapEx& rBmpEx, const GraphicAttr& rAttributes, - sal_uInt16 nRot10, const Size& rUnrotatedSzPix, - long nStartX, long nEndX, long nStartY, long nEndY, - BitmapEx& rOutBmpEx ) -{ - const long aUnrotatedWidth = rUnrotatedSzPix.Width(); - const long aUnrotatedHeight = rUnrotatedSzPix.Height(); - const long aBitmapWidth = rBmpEx.GetSizePixel().Width(); - const long aBitmapHeight = rBmpEx.GetSizePixel().Height(); - - long nTmpX, nTmpY, nTmpFX, nTmpFY, nTmp; - double fTmp; - - bool bHMirr( rAttributes.GetMirrorFlags() & BmpMirrorFlags::Horizontal ); - bool bVMirr( rAttributes.GetMirrorFlags() & BmpMirrorFlags::Vertical ); - - std::unique_ptr<long[]> pMapIX(new long[ aUnrotatedWidth ]); - std::unique_ptr<long[]> pMapFX(new long[ aUnrotatedWidth ]); - std::unique_ptr<long[]> pMapIY(new long[ aUnrotatedHeight ]); - std::unique_ptr<long[]> pMapFY(new long[ aUnrotatedHeight ]); - - double fRevScaleX; - double fRevScaleY; - - bool scaleByAveraging = false; - - if(aBitmapWidth > 1 && aUnrotatedWidth > 1) - { - fRevScaleX = static_cast<double>( aBitmapWidth - 1 ) / static_cast<double>( aUnrotatedWidth - 1 ); - // create horizontal mapping table - long x; - for( x = 0, nTmpX = aBitmapWidth - 1, nTmp = aBitmapWidth - 2 >= 0 ? aBitmapWidth -2 : 0L; x < aUnrotatedWidth; x++ ) - { - fTmp = x * fRevScaleX; - - if( bHMirr ) - fTmp = nTmpX - fTmp; - - pMapIX[ x ] = MinMax( fTmp, 0, nTmp ); - pMapFX[ x ] = static_cast<long>( ( fTmp - pMapIX[ x ] ) * 1048576.0 ); - } - scaleByAveraging |= fRevScaleX > 5.0/3.0; - } - else - { - if(aBitmapWidth == 1) - { - fRevScaleX = 1.0 / static_cast<double>(aUnrotatedWidth); - for ( long x = 0; x < aUnrotatedWidth ; x++) - { - pMapIX[x] = 0; - pMapFX[x] = 0; - } - scaleByAveraging = true; - } - else - { - fRevScaleX = static_cast<double>(aBitmapWidth) / static_cast<double>(aUnrotatedWidth); - fTmp = static_cast<double>(aBitmapWidth) / 2.0; - - pMapIX[ 0 ] = static_cast<long>(fTmp); - pMapFX[ 0 ] = static_cast<long>( ( fTmp - pMapIX[ 0 ] ) * 1048576.0 ); - scaleByAveraging = true; - } - } - if(aBitmapHeight > 1 && aUnrotatedHeight > 1) - { - fRevScaleY = static_cast<double>( aBitmapHeight - 1 ) / static_cast<double>( aUnrotatedHeight - 1 ); - // create vertical mapping table - long y; - for( y = 0, nTmpY = aBitmapHeight - 1, nTmp = aBitmapHeight - 2 >= 0 ? aBitmapHeight - 2 : 0L; y < aUnrotatedHeight; y++ ) - { - fTmp = y * fRevScaleY; - - if( bVMirr ) - fTmp = nTmpY - fTmp; - - pMapIY[ y ] = MinMax( fTmp, 0, nTmp ); - pMapFY[ y ] = static_cast<long>( ( fTmp - pMapIY[ y ] ) * 1048576.0 ); - } - scaleByAveraging |= fRevScaleY > 5.0/3.0; - } - else - { - if(aBitmapHeight == 1) - { - fRevScaleY = 1.0 / static_cast<double>(aUnrotatedHeight); - for (long y = 0; y < aUnrotatedHeight; ++y) - { - pMapIY[y] = 0; - pMapFY[y] = 0; - } - scaleByAveraging = true; - } - else - { - fRevScaleY = static_cast<double>(aBitmapHeight) / static_cast<double>(aUnrotatedHeight); - fTmp = static_cast<double>(aBitmapHeight) / 2.0; - - pMapIY[ 0 ] = static_cast<long>(fTmp); - pMapFY[ 0 ] = static_cast<long>( ( fTmp - pMapIY[ 0 ] ) * 1048576.0 ); - scaleByAveraging = true; - } - } - - Bitmap aBmp( rBmpEx.GetBitmap() ); - Bitmap aOutBmp; - BitmapReadAccess* pReadAccess = aBmp.AcquireReadAccess(); - BitmapWriteAccess* pWriteAccess; - - const double fCosAngle = cos( nRot10 * F_PI1800 ); - const double fSinAngle = sin( nRot10 * F_PI1800 ); - const long aTargetWidth = nEndX - nStartX + 1; - const long aTargetHeight = nEndY - nStartY + 1; - std::unique_ptr<long[]> pCosX(new long[ aTargetWidth ]); - std::unique_ptr<long[]> pSinX(new long[ aTargetWidth ]); - std::unique_ptr<long[]> pCosY(new long[ aTargetHeight ]); - std::unique_ptr<long[]> pSinY(new long[ aTargetHeight ]); - long nUnRotX, nUnRotY, nSinY, nCosY; - sal_uInt8 cR0, cG0, cB0, cR1, cG1, cB1; - bool bRet = false; - - tools::Polygon aPoly( tools::Rectangle( Point(), rUnrotatedSzPix ) ); - aPoly.Rotate( Point(), nRot10 ); - tools::Rectangle aNewBound( aPoly.GetBoundRect() ); - - // create horizontal mapping table - long x; - for( x = 0, nTmpX = aNewBound.Left() + nStartX; x < aTargetWidth; x++ ) - { - pCosX[ x ] = FRound( fCosAngle * ( fTmp = nTmpX++ << 8 ) ); - pSinX[ x ] = FRound( fSinAngle * fTmp ); - } - - // create vertical mapping table - long y; - for( y = 0, nTmpY = aNewBound.Top() + nStartY; y < aTargetHeight; y++ ) - { - pCosY[ y ] = FRound( fCosAngle * ( fTmp = nTmpY++ << 8 ) ); - pSinY[ y ] = FRound( fSinAngle * fTmp ); - } - - if( pReadAccess ) - { - aOutBmp = Bitmap( Size( aTargetWidth, aTargetHeight ), 24 ); - pWriteAccess = aOutBmp.AcquireWriteAccess(); - - if( pWriteAccess ) - { - BitmapColor aColRes; - - if ( !scaleByAveraging ) - { - if( pReadAccess->HasPalette() ) - { - for( y = 0; y < aTargetHeight; y++ ) - { - nSinY = pSinY[ y ]; - nCosY = pCosY[ y ]; - - Scanline pScanline = pWriteAccess->GetScanline( y ); - for( x = 0; x < aTargetWidth; x++ ) - { - nUnRotX = ( pCosX[ x ] - nSinY ) >> 8; - nUnRotY = ( pSinX[ x ] + nCosY ) >> 8; - - if( ( nUnRotX >= 0 ) && ( nUnRotX < aUnrotatedWidth ) && - ( nUnRotY >= 0 ) && ( nUnRotY < aUnrotatedHeight ) ) - { - nTmpX = pMapIX[ nUnRotX ]; - nTmpFX = pMapFX[ nUnRotX ]; - nTmpY = pMapIY[ nUnRotY ]; - nTmpFY = pMapFY[ nUnRotY ]; - - const BitmapColor& rCol0 = pReadAccess->GetPaletteColor( pReadAccess->GetPixelIndex( nTmpY, nTmpX ) ); - const BitmapColor& rCol1 = pReadAccess->GetPaletteColor( pReadAccess->GetPixelIndex( nTmpY, ++nTmpX ) ); - cR0 = MAP( rCol0.GetRed(), rCol1.GetRed(), nTmpFX ); - cG0 = MAP( rCol0.GetGreen(), rCol1.GetGreen(), nTmpFX ); - cB0 = MAP( rCol0.GetBlue(), rCol1.GetBlue(), nTmpFX ); - - const BitmapColor& rCol3 = pReadAccess->GetPaletteColor( pReadAccess->GetPixelIndex( ++nTmpY, nTmpX ) ); - const BitmapColor& rCol2 = pReadAccess->GetPaletteColor( pReadAccess->GetPixelIndex( nTmpY, --nTmpX ) ); - cR1 = MAP( rCol2.GetRed(), rCol3.GetRed(), nTmpFX ); - cG1 = MAP( rCol2.GetGreen(), rCol3.GetGreen(), nTmpFX ); - cB1 = MAP( rCol2.GetBlue(), rCol3.GetBlue(), nTmpFX ); - - aColRes.SetRed( MAP( cR0, cR1, nTmpFY ) ); - aColRes.SetGreen( MAP( cG0, cG1, nTmpFY ) ); - aColRes.SetBlue( MAP( cB0, cB1, nTmpFY ) ); - pWriteAccess->SetPixelOnData( pScanline, x, aColRes ); - } - } - } - } - else - { - BitmapColor aCol0, aCol1; - - for( y = 0; y < aTargetHeight; y++ ) - { - nSinY = pSinY[ y ]; - nCosY = pCosY[ y ]; - - Scanline pScanline = pWriteAccess->GetScanline( y ); - for( x = 0; x < aTargetWidth; x++ ) - { - nUnRotX = ( pCosX[ x ] - nSinY ) >> 8; - nUnRotY = ( pSinX[ x ] + nCosY ) >> 8; - - if( ( nUnRotX >= 0 ) && ( nUnRotX < aUnrotatedWidth ) && - ( nUnRotY >= 0 ) && ( nUnRotY < aUnrotatedHeight ) ) - { - nTmpX = pMapIX[ nUnRotX ]; - nTmpFX = pMapFX[ nUnRotX ]; - nTmpY = pMapIY[ nUnRotY ]; - nTmpFY = pMapFY[ nUnRotY ]; - - aCol0 = pReadAccess->GetPixel( nTmpY, nTmpX ); - aCol1 = pReadAccess->GetPixel( nTmpY, ++nTmpX ); - cR0 = MAP( aCol0.GetRed(), aCol1.GetRed(), nTmpFX ); - cG0 = MAP( aCol0.GetGreen(), aCol1.GetGreen(), nTmpFX ); - cB0 = MAP( aCol0.GetBlue(), aCol1.GetBlue(), nTmpFX ); - - aCol1 = pReadAccess->GetPixel( ++nTmpY, nTmpX ); - aCol0 = pReadAccess->GetPixel( nTmpY, --nTmpX ); - cR1 = MAP( aCol0.GetRed(), aCol1.GetRed(), nTmpFX ); - cG1 = MAP( aCol0.GetGreen(), aCol1.GetGreen(), nTmpFX ); - cB1 = MAP( aCol0.GetBlue(), aCol1.GetBlue(), nTmpFX ); - - aColRes.SetRed( MAP( cR0, cR1, nTmpFY ) ); - aColRes.SetGreen( MAP( cG0, cG1, nTmpFY ) ); - aColRes.SetBlue( MAP( cB0, cB1, nTmpFY ) ); - pWriteAccess->SetPixelOnData( pScanline, x, aColRes ); - } - } - } - } - } - else // scaleByAveraging - { - double aSumRed, aSumGreen, aSumBlue, aCount; - BitmapColor aColor; - BitmapColor aResultColor; - - for( y = 0; y < aTargetHeight; y++ ) - { - nSinY = pSinY[ y ]; - nCosY = pCosY[ y ]; - - Scanline pScanline = pWriteAccess->GetScanline( y ); - for( x = 0; x < aTargetWidth; x++ ) - { - double aUnrotatedX = ( pCosX[ x ] - nSinY ) / 256.0; - double aUnrotatedY = ( pSinX[ x ] + nCosY ) / 256.0; - - if ( bHMirr ) - aUnrotatedX = aUnrotatedWidth - aUnrotatedX - 1; - if ( bVMirr ) - aUnrotatedY = aUnrotatedHeight - aUnrotatedY - 1; - - if( ( aUnrotatedX >= 0 ) && ( aUnrotatedX < aUnrotatedWidth ) && - ( aUnrotatedY >= 0 ) && ( aUnrotatedY < aUnrotatedHeight ) ) - { - double dYStart = ((aUnrotatedY + 0.5) * fRevScaleY) - 0.5; - double dYEnd = ((aUnrotatedY + 1.5) * fRevScaleY) - 0.5; - - int yStart = MinMax( dYStart, 0, aBitmapHeight - 1); - int yEnd = MinMax( dYEnd, 0, aBitmapHeight - 1); - - double dXStart = ((aUnrotatedX + 0.5) * fRevScaleX) - 0.5; - double dXEnd = ((aUnrotatedX + 1.5) * fRevScaleX) - 0.5; - - int xStart = MinMax( dXStart, 0, aBitmapWidth - 1); - int xEnd = MinMax( dXEnd, 0, aBitmapWidth - 1); - - aSumRed = aSumGreen = aSumBlue = 0.0; - aCount = 0; - - for (int yIn = yStart; yIn <= yEnd; yIn++) - { - Scanline pScanlineRead = pReadAccess->GetScanline( yIn ); - for (int xIn = xStart; xIn <= xEnd; xIn++) - { - if( pReadAccess->HasPalette() ) - aColor = pReadAccess->GetPaletteColor( pReadAccess->GetIndexFromData( pScanlineRead, xIn ) ); - else - aColor = pReadAccess->GetPixelFromData( pScanlineRead, xIn ); - - aSumRed += aColor.GetRed(); - aSumGreen += aColor.GetGreen(); - aSumBlue += aColor.GetBlue(); - - aCount++; - } - } - - aResultColor.SetRed( MinMax( aSumRed / aCount, 0, 255) ); - aResultColor.SetGreen( MinMax( aSumGreen / aCount, 0, 255) ); - aResultColor.SetBlue( MinMax( aSumBlue / aCount, 0, 255) ); - - pWriteAccess->SetPixelOnData( pScanline, x, aResultColor ); - } - } - } - } - - Bitmap::ReleaseAccess( pWriteAccess ); - bRet = true; - } - - Bitmap::ReleaseAccess( pReadAccess ); - } - - // mask processing - if( bRet && ( rBmpEx.IsTransparent() || ( nRot10 != 0 && nRot10 != 900 && nRot10 != 1800 && nRot10 != 2700 ) ) ) - { - bRet = false; - - if( rBmpEx.IsAlpha() ) - { - AlphaMask aAlpha( rBmpEx.GetAlpha() ); - AlphaMask aOutAlpha; - - pReadAccess = aAlpha.AcquireReadAccess(); - - if( pReadAccess ) - { - aOutAlpha = AlphaMask( Size( aTargetWidth, aTargetHeight ) ); - pWriteAccess = aOutAlpha.AcquireWriteAccess(); - - if( pWriteAccess ) - { - if( pReadAccess->GetScanlineFormat() == ScanlineFormat::N8BitPal && - pWriteAccess->GetScanlineFormat() == ScanlineFormat::N8BitPal ) - { - if ( !scaleByAveraging ) - { - Scanline pLine0, pLine1, pLineW; - - for( long nY = 0; nY < aTargetHeight; nY++ ) - { - nSinY = pSinY[ nY ]; - nCosY = pCosY[ nY ]; - pLineW = pWriteAccess->GetScanline( nY ); - - for( long nX = 0; nX < aTargetWidth; nX++ ) - { - nUnRotX = ( pCosX[ nX ] - nSinY ) >> 8; - nUnRotY = ( pSinX[ nX ] + nCosY ) >> 8; - - if( ( nUnRotX >= 0 ) && ( nUnRotX < aUnrotatedWidth ) && - ( nUnRotY >= 0 ) && ( nUnRotY < aUnrotatedHeight ) ) - { - nTmpX = pMapIX[ nUnRotX ]; - nTmpFX = pMapFX[ nUnRotX ]; - nTmpY = pMapIY[ nUnRotY ]; - nTmpFY = pMapFY[ nUnRotY ]; - - pLine0 = pReadAccess->GetScanline( nTmpY++ ); - pLine1 = pReadAccess->GetScanline( nTmpY ); - - const long nAlpha0 = pLine0[ nTmpX ]; - const long nAlpha2 = pLine1[ nTmpX++ ]; - const long nAlpha1 = pLine0[ nTmpX ]; - const long nAlpha3 = pLine1[ nTmpX ]; - const long n0 = MAP( nAlpha0, nAlpha1, nTmpFX ); - const long n1 = MAP( nAlpha2, nAlpha3, nTmpFX ); - - *pLineW++ = MAP( n0, n1, nTmpFY ); - } - else - *pLineW++ = 255; - } - } - } - else // scaleByAveraging - { - const BitmapColor aTrans( pWriteAccess->GetBestMatchingColor( COL_WHITE ) ); - BitmapColor aResultColor( 0 ); - double aSum, aCount; - - for( y = 0; y < aTargetHeight; y++ ) - { - nSinY = pSinY[ y ]; - nCosY = pCosY[ y ]; - Scanline pScanline = pWriteAccess->GetScanline( y ); - - for( x = 0; x < aTargetWidth; x++ ) - { - - double aUnrotatedX = ( pCosX[ x ] - nSinY ) / 256.0; - double aUnrotatedY = ( pSinX[ x ] + nCosY ) / 256.0; - - if ( bHMirr ) - aUnrotatedX = aUnrotatedWidth - aUnrotatedX - 1; - if ( bVMirr ) - aUnrotatedY = aUnrotatedHeight - aUnrotatedY - 1; - - if( ( aUnrotatedX >= 0 ) && ( aUnrotatedX < aUnrotatedWidth ) && - ( aUnrotatedY >= 0 ) && ( aUnrotatedY < aUnrotatedHeight ) ) - { - double dYStart = ((aUnrotatedY + 0.5) * fRevScaleY) - 0.5; - double dYEnd = ((aUnrotatedY + 1.5) * fRevScaleY) - 0.5; - - int yStart = MinMax( dYStart, 0, aBitmapHeight - 1); - int yEnd = MinMax( dYEnd, 0, aBitmapHeight - 1); - - double dXStart = ((aUnrotatedX + 0.5) * fRevScaleX) - 0.5; - double dXEnd = ((aUnrotatedX + 1.5) * fRevScaleX) - 0.5; - - int xStart = MinMax( dXStart, 0, aBitmapWidth - 1); - int xEnd = MinMax( dXEnd, 0, aBitmapWidth - 1); - - aSum = 0.0; - aCount = 0; - - for (int yIn = yStart; yIn <= yEnd; yIn++) - { - Scanline pScanlineRead = pReadAccess->GetScanline( yIn ); - for (int xIn = xStart; xIn <= xEnd; xIn++) - { - aSum += pReadAccess->GetPixelFromData( pScanlineRead, xIn ).GetIndex(); - aCount++; - } - } - aResultColor.SetIndex( MinMax( aSum / aCount, 0, 255) ); - pWriteAccess->SetPixelOnData( pScanline, x, aResultColor ); - } - else - { - pWriteAccess->SetPixelOnData( pScanline, x, aTrans ); - } - } - } - } - } - else - { - const BitmapColor aTrans( pWriteAccess->GetBestMatchingColor( COL_WHITE ) ); - BitmapColor aAlphaVal( 0 ); - - for( long nY = 0; nY < aTargetHeight; nY++ ) - { - nSinY = pSinY[ nY ]; - nCosY = pCosY[ nY ]; - Scanline pScanline = pWriteAccess->GetScanline( nY ); - - for( long nX = 0; nX < aTargetWidth; nX++ ) - { - nUnRotX = ( pCosX[ nX ] - nSinY ) >> 8; - nUnRotY = ( pSinX[ nX ] + nCosY ) >> 8; - - if( ( nUnRotX >= 0 ) && ( nUnRotX < aUnrotatedWidth ) && - ( nUnRotY >= 0 ) && ( nUnRotY < aUnrotatedHeight ) ) - { - nTmpX = pMapIX[ nUnRotX ]; - nTmpFX = pMapFX[ nUnRotX ]; - nTmpY = pMapIY[ nUnRotY ]; - nTmpFY = pMapFY[ nUnRotY ]; - - const long nAlpha0 = pReadAccess->GetPixel( nTmpY, nTmpX ).GetIndex(); - const long nAlpha1 = pReadAccess->GetPixel( nTmpY, ++nTmpX ).GetIndex(); - const long nAlpha3 = pReadAccess->GetPixel( ++nTmpY, nTmpX ).GetIndex(); - const long nAlpha2 = pReadAccess->GetPixel( nTmpY, --nTmpX ).GetIndex(); - const long n0 = MAP( nAlpha0, nAlpha1, nTmpFX ); - const long n1 = MAP( nAlpha2, nAlpha3, nTmpFX ); - - aAlphaVal.SetIndex( MAP( n0, n1, nTmpFY ) ); - pWriteAccess->SetPixelOnData( pScanline, nX, aAlphaVal ); - } - else - pWriteAccess->SetPixelOnData( pScanline, nX, aTrans ); - } - } - } - - aOutAlpha.ReleaseAccess( pWriteAccess ); - bRet = true; - } - - aAlpha.ReleaseAccess( pReadAccess ); - } - - if( bRet ) - rOutBmpEx = BitmapEx( aOutBmp, aOutAlpha ); - } - else - { - Bitmap aOutMsk( Size( aTargetWidth, aTargetHeight ), 1 ); - pWriteAccess = aOutMsk.AcquireWriteAccess(); - - if( pWriteAccess ) - { - Bitmap aMsk( rBmpEx.GetMask() ); - const BitmapColor aB( pWriteAccess->GetBestMatchingColor( COL_BLACK ) ); - const BitmapColor aW( pWriteAccess->GetBestMatchingColor( COL_WHITE ) ); - BitmapReadAccess* pMAcc = nullptr; - - if( !aMsk || ( ( pMAcc = aMsk.AcquireReadAccess() ) != nullptr ) ) - { - std::unique_ptr<long[]> pMapLX(new long[ aUnrotatedWidth ]); - std::unique_ptr<long[]> pMapLY(new long[ aUnrotatedHeight ]); - BitmapColor aTestB; - - if( pMAcc ) - aTestB = pMAcc->GetBestMatchingColor( COL_BLACK ); - - // create new horizontal mapping table - for( long nX = 0; nX < aUnrotatedWidth; nX++ ) - pMapLX[ nX ] = FRound( static_cast<double>(pMapIX[ nX ]) + pMapFX[ nX ] / 1048576.0 ); - - // create new vertical mapping table - for( long nY = 0; nY < aUnrotatedHeight; nY++ ) - pMapLY[ nY ] = FRound( static_cast<double>(pMapIY[ nY ]) + pMapFY[ nY ] / 1048576.0 ); - - // do mask rotation - for( long nY = 0; nY < aTargetHeight; nY++ ) - { - nSinY = pSinY[ nY ]; - nCosY = pCosY[ nY ]; - Scanline pScanline = pWriteAccess->GetScanline( nY ); - - for( long nX = 0; nX < aTargetWidth; nX++ ) - { - nUnRotX = ( pCosX[ nX ] - nSinY ) >> 8; - nUnRotY = ( pSinX[ nX ] + nCosY ) >> 8; - - if( ( nUnRotX >= 0 ) && ( nUnRotX < aUnrotatedWidth ) && - ( nUnRotY >= 0 ) && ( nUnRotY < aUnrotatedHeight ) ) - { - if( pMAcc ) - { - if( pMAcc->GetPixel( pMapLY[ nUnRotY ], pMapLX[ nUnRotX ] ) == aTestB ) - pWriteAccess->SetPixelOnData( pScanline, nX, aB ); - else - pWriteAccess->SetPixelOnData( pScanline, nX, aW ); - } - else - pWriteAccess->SetPixelOnData( pScanline, nX, aB ); - } - else - pWriteAccess->SetPixelOnData( pScanline, nX, aW ); - } - } - - pMapLX.reset(); - pMapLY.reset(); - - if( pMAcc ) - Bitmap::ReleaseAccess( pMAcc ); - - bRet = true; - } - - Bitmap::ReleaseAccess( pWriteAccess ); - } - - if( bRet ) - rOutBmpEx = BitmapEx( aOutBmp, aOutMsk ); - } - - if( !bRet ) - rOutBmpEx = aOutBmp; - } - else - rOutBmpEx = aOutBmp; - - return bRet; -} - -bool GraphicManager::ImplCreateOutput( OutputDevice* pOutputDevice, - const Point& rPoint, const Size& rSize, - const BitmapEx& rBitmapEx, const GraphicAttr& rAttributes, - BitmapEx* pBmpEx ) -{ - sal_uInt16 nRot10 = rAttributes.GetRotation() % 3600; - - Point aOutputPointPix; - Size aOutputSizePix; - Point aUnrotatedPointPix( pOutputDevice->LogicToPixel( rPoint ) ); - Size aUnrotatedSizePix( pOutputDevice->LogicToPixel( rSize ) ); - - bool bRet = false; - - if( nRot10 ) - { - tools::Polygon aPoly( tools::Rectangle( rPoint, rSize ) ); - aPoly.Rotate( rPoint, nRot10 ); - const tools::Rectangle aRotBoundRect( aPoly.GetBoundRect() ); - aOutputPointPix = pOutputDevice->LogicToPixel( aRotBoundRect.TopLeft() ); - aOutputSizePix = pOutputDevice->LogicToPixel( aRotBoundRect.GetSize() ); - } - else - { - aOutputPointPix = aUnrotatedPointPix; - aOutputSizePix = aUnrotatedSizePix; - } - - if( aUnrotatedSizePix.Width() && aUnrotatedSizePix.Height() ) - { - BitmapEx aOutBmpEx; - Point aOutPoint; - Size aOutSize; - const Size& rBmpSzPix = rBitmapEx.GetSizePixel(); - const long nW = rBmpSzPix.Width(); - const long nH = rBmpSzPix.Height(); - long nStartX = -1, nStartY = -1, nEndX = -1, nEndY = -1; - bool bHMirr( rAttributes.GetMirrorFlags() & BmpMirrorFlags::Horizontal ); - bool bVMirr( rAttributes.GetMirrorFlags() & BmpMirrorFlags::Vertical ); - - // calculate output sizes - if( !pBmpEx ) - { - tools::Rectangle aOutRect( Point(), pOutputDevice->GetOutputSizePixel() ); - tools::Rectangle aBmpRect( aOutputPointPix, aOutputSizePix ); - - if( pOutputDevice->GetOutDevType() == OUTDEV_WINDOW ) - { - const vcl::Region aPaintRgn( static_cast<vcl::Window*>( pOutputDevice )->GetPaintRegion() ); - if( !aPaintRgn.IsNull() ) - aOutRect.Intersection( pOutputDevice->LogicToPixel( aPaintRgn.GetBoundRect() ) ); - } - - aOutRect.Intersection( aBmpRect ); - - if( !aOutRect.IsEmpty() ) - { - aOutPoint = pOutputDevice->PixelToLogic( aOutRect.TopLeft() ); - aOutSize = pOutputDevice->PixelToLogic( aOutRect.GetSize() ); - nStartX = aOutRect.Left() - aBmpRect.Left(); - nStartY = aOutRect.Top() - aBmpRect.Top(); - nEndX = aOutRect.Right() - aBmpRect.Left(); - nEndY = aOutRect.Bottom() - aBmpRect.Top(); - } - else - { - nStartX = -1; // invalid - } - } - else - { - aOutPoint = pOutputDevice->PixelToLogic( aOutputPointPix ); - aOutSize = pOutputDevice->PixelToLogic( aOutputSizePix ); - nStartX = nStartY = 0; - nEndX = aOutputSizePix.Width() - 1; - nEndY = aOutputSizePix.Height() - 1; - } - - // do transformation - if( nStartX >= 0 ) - { - const bool bSimple = ( 1 == nW || 1 == nH ); - - if( nRot10 ) - { - if( bSimple ) - { - bRet = ( aOutBmpEx = rBitmapEx ).Scale( aUnrotatedSizePix ); - - if( bRet ) - aOutBmpEx.Rotate( nRot10, COL_TRANSPARENT ); - } - else - { - bRet = ImplCreateRotatedScaled( rBitmapEx, rAttributes, - nRot10, aUnrotatedSizePix, - nStartX, nEndX, nStartY, nEndY, - aOutBmpEx ); - } - } - else - { - if( !bHMirr && !bVMirr && aOutputSizePix == rBmpSzPix ) - { - aOutPoint = pOutputDevice->PixelToLogic( aOutputPointPix ); - aOutSize = pOutputDevice->PixelToLogic( aOutputSizePix ); - aOutBmpEx = rBitmapEx; - bRet = true; - } - else - { - if( bSimple ) - { - bRet = ( aOutBmpEx = rBitmapEx ).Scale( Size( nEndX - nStartX + 1, nEndY - nStartY + 1 ) ); - } - else - { - bRet = ImplCreateRotatedScaled( rBitmapEx, rAttributes, - nRot10, aUnrotatedSizePix, - nStartX, nEndX, nStartY, nEndY, - aOutBmpEx ); - } - } - } - - if( bRet ) - { - // Attribute adjustment if necessary - if( rAttributes.IsSpecialDrawMode() || rAttributes.IsAdjusted() || rAttributes.IsTransparent() ) - ImplAdjust( aOutBmpEx, rAttributes, GraphicAdjustmentFlags::DRAWMODE | GraphicAdjustmentFlags::COLORS | GraphicAdjustmentFlags::TRANSPARENCY ); - - // OutDev adjustment if necessary - if( pOutputDevice->GetOutDevType() != OUTDEV_PRINTER && pOutputDevice->GetBitCount() <= 8 && aOutBmpEx.GetBitCount() >= 8 ) - aOutBmpEx.Dither(); - } - } - - // Create output - if( bRet ) - { - if( !pBmpEx ) - pOutputDevice->DrawBitmapEx( aOutPoint, aOutSize, aOutBmpEx ); - else - { - if( !rAttributes.IsTransparent() && !aOutBmpEx.IsAlpha() ) - aOutBmpEx = BitmapEx( aOutBmpEx.GetBitmap().CreateDisplayBitmap( pOutputDevice ), aOutBmpEx.GetMask() ); - - pOutputDevice->DrawBitmapEx( aOutPoint, aOutSize, *pBmpEx = aOutBmpEx ); - } - } - } - - return bRet; -} - -// This function checks whether the bitmap is usable for skipping -// mtf rendering by using just this one bitmap (i.e. in case the metafile -// contains just this one pixmap that covers the entire metafile area). -static BitmapEx checkMetadataBitmap( const BitmapEx& rBmpEx, - Point rSrcPoint, - Size rSrcSize, - const Point& rDestPoint, - const Size& rDestSize, - const Size& rRefSize, - bool& o_rbNonBitmapActionEncountered ) -{ -// NOTE: If you do changes in this function, change checkMetadataBitmap() in grfcache.cxx too. - BitmapEx aBmpEx; - if( rSrcSize == Size()) - rSrcSize = rBmpEx.GetSizePixel(); - - if( rDestPoint != Point( 0, 0 )) - { // The pixmap in the metafile has an offset (and so would not cover) - // the entire result -> fall back to mtf rendering. - o_rbNonBitmapActionEncountered = true; - return aBmpEx; - } - if( rDestSize != rRefSize ) - { // The pixmap is not fullscale (does not cover the entire metafile area). - // HACK: The code here should refuse to use the bitmap directly - // and fall back to mtf rendering, but there seem to be metafiles - // that do not specify exactly their area (the Windows API requires apps - // the specify it manually, the rectangle is specified as topleft/bottomright - // rather than topleft/size [which may be confusing], and the docs - // on the exact meaning are somewhat confusing as well), so if it turns - // out this metafile really contains just one bitmap and no other painting, - // and if the sizes almost match, just use the pixmap (which will be scaled - // to fit exactly the requested size, so there should not be any actual problem - // caused by this small difference). This will allow caching of the resulting - // (scaled) pixmap, which can make a noticeable performance difference. - if( rBmpEx.GetSizePixel().Width() > 100 && rBmpEx.GetSizePixel().Height() > 100 - && std::abs( rDestSize.Width() - rRefSize.Width()) < 5 - && std::abs( rDestSize.Height() - rRefSize.Height()) < 5 ) - ; // ok, assume it's close enough - else - { // fall back to mtf rendering - o_rbNonBitmapActionEncountered = true; - return aBmpEx; - } - } - - aBmpEx = rBmpEx; - - if( (rSrcPoint.X() != 0 && rSrcPoint.Y() != 0) || - rSrcSize != rBmpEx.GetSizePixel() ) - { - // crop bitmap to given source rectangle (no - // need to copy and convert the whole bitmap) - const tools::Rectangle aCropRect( rSrcPoint, - rSrcSize ); - aBmpEx.Crop( aCropRect ); - } - - return aBmpEx; -} - -bool GraphicManager::ImplCreateOutput( OutputDevice* pOut, - const Point& rPt, const Size& rSz, - const GDIMetaFile& rMtf, const GraphicAttr& rAttr, - GDIMetaFile& rOutMtf, BitmapEx& rOutBmpEx ) -{ - const Size aNewSize( rMtf.GetPrefSize() ); - - rOutMtf = rMtf; - - // Count bitmap actions, and flag actions that paint, but - // are no bitmaps. - sal_Int32 nNumBitmaps(0); - bool bNonBitmapActionEncountered(false); - if( aNewSize.Width() && aNewSize.Height() && rSz.Width() && rSz.Height() ) - { - const double fGrfWH = static_cast<double>(aNewSize.Width()) / aNewSize.Height(); - const double fOutWH = static_cast<double>(rSz.Width()) / rSz.Height(); - - const double fScaleX = fOutWH / fGrfWH; - const double fScaleY = 1.0; - - const MapMode& rPrefMapMode( rMtf.GetPrefMapMode() ); - const Size rSizePix( pOut->LogicToPixel( aNewSize, rPrefMapMode ) ); - -// NOTE: If you do changes in this function, check GraphicDisplayCacheEntry::IsCacheableAsBitmap -// in grfcache.cxx too. - - // Determine whether the metafile basically displays - // a single bitmap (in which case that bitmap is simply used directly - // instead of playing the metafile). Note that - // the solution, as implemented here, is quite suboptimal (the - // cases where a mtf consisting basically of a single bitmap, - // that fail to pass the test below, are probably frequent). A - // better solution would involve FSAA, but that's currently - // expensive, and might trigger bugs on display drivers, if - // VDevs get bigger than the actual screen. - sal_uInt32 nCurPos; - MetaAction* pAct; - for( nCurPos = 0, pAct = rOutMtf.FirstAction(); pAct; - pAct = rOutMtf.NextAction(), nCurPos++ ) - { - MetaAction* pModAct = nullptr; - switch( pAct->GetType() ) - { - case MetaActionType::FONT: - { - // taking care of font width default if scaling metafile. - MetaFontAction* pA = static_cast<MetaFontAction*>(pAct); - vcl::Font aFont( pA->GetFont() ); - if ( !aFont.GetAverageFontWidth() ) - { - FontMetric aFontMetric( pOut->GetFontMetric( aFont ) ); - aFont.SetAverageFontWidth( aFontMetric.GetAverageFontWidth() ); - pModAct = new MetaFontAction( aFont ); - } - SAL_FALLTHROUGH; - } - case MetaActionType::NONE: - SAL_FALLTHROUGH; - - // OutDev state changes (which don't affect bitmap - // output) - case MetaActionType::LINECOLOR: - SAL_FALLTHROUGH; - case MetaActionType::FILLCOLOR: - SAL_FALLTHROUGH; - case MetaActionType::TEXTCOLOR: - SAL_FALLTHROUGH; - case MetaActionType::TEXTFILLCOLOR: - SAL_FALLTHROUGH; - case MetaActionType::TEXTALIGN: - SAL_FALLTHROUGH; - case MetaActionType::TEXTLINECOLOR: - SAL_FALLTHROUGH; - case MetaActionType::TEXTLINE: - SAL_FALLTHROUGH; - case MetaActionType::PUSH: - SAL_FALLTHROUGH; - case MetaActionType::POP: - SAL_FALLTHROUGH; - case MetaActionType::LAYOUTMODE: - SAL_FALLTHROUGH; - case MetaActionType::TEXTLANGUAGE: - SAL_FALLTHROUGH; - case MetaActionType::COMMENT: - break; - - // bitmap output methods - case MetaActionType::BMP: - if( !nNumBitmaps && !bNonBitmapActionEncountered ) - { - MetaBmpAction* pAction = static_cast<MetaBmpAction*>(pAct); - - rOutBmpEx = checkMetadataBitmap( - BitmapEx( pAction->GetBitmap()), - Point(), Size(), - pOut->LogicToPixel( pAction->GetPoint(), - rPrefMapMode ), - pAction->GetBitmap().GetSizePixel(), - rSizePix, - bNonBitmapActionEncountered ); - } - ++nNumBitmaps; - break; - - case MetaActionType::BMPSCALE: - if( !nNumBitmaps && !bNonBitmapActionEncountered ) - { - MetaBmpScaleAction* pAction = static_cast<MetaBmpScaleAction*>(pAct); - - rOutBmpEx = checkMetadataBitmap( - BitmapEx( pAction->GetBitmap()), - Point(), Size(), - pOut->LogicToPixel( pAction->GetPoint(), - rPrefMapMode ), - pOut->LogicToPixel( pAction->GetSize(), - rPrefMapMode ), - rSizePix, - bNonBitmapActionEncountered ); - } - ++nNumBitmaps; - break; - - case MetaActionType::BMPSCALEPART: - if( !nNumBitmaps && !bNonBitmapActionEncountered ) - { - MetaBmpScalePartAction* pAction = static_cast<MetaBmpScalePartAction*>(pAct); - - rOutBmpEx = checkMetadataBitmap( - BitmapEx( pAction->GetBitmap() ), - pAction->GetSrcPoint(), - pAction->GetSrcSize(), - pOut->LogicToPixel( pAction->GetDestPoint(), - rPrefMapMode ), - pOut->LogicToPixel( pAction->GetDestSize(), - rPrefMapMode ), - rSizePix, - bNonBitmapActionEncountered ); - } - ++nNumBitmaps; - break; - - case MetaActionType::BMPEX: - if( !nNumBitmaps && !bNonBitmapActionEncountered ) - { - MetaBmpExAction* pAction = static_cast<MetaBmpExAction*>(pAct); - - rOutBmpEx = checkMetadataBitmap( - pAction->GetBitmapEx(), - Point(), Size(), - pOut->LogicToPixel( pAction->GetPoint(), - rPrefMapMode ), - pAction->GetBitmapEx().GetSizePixel(), - rSizePix, - bNonBitmapActionEncountered ); - } - ++nNumBitmaps; - break; - - case MetaActionType::BMPEXSCALE: - if( !nNumBitmaps && !bNonBitmapActionEncountered ) - { - MetaBmpExScaleAction* pAction = static_cast<MetaBmpExScaleAction*>(pAct); - - rOutBmpEx = checkMetadataBitmap( - pAction->GetBitmapEx(), - Point(), Size(), - pOut->LogicToPixel( pAction->GetPoint(), - rPrefMapMode ), - pOut->LogicToPixel( pAction->GetSize(), - rPrefMapMode ), - rSizePix, - bNonBitmapActionEncountered ); - } - ++nNumBitmaps; - break; - - case MetaActionType::BMPEXSCALEPART: - if( !nNumBitmaps && !bNonBitmapActionEncountered ) - { - MetaBmpExScalePartAction* pAction = static_cast<MetaBmpExScalePartAction*>(pAct); - - rOutBmpEx = checkMetadataBitmap( pAction->GetBitmapEx(), - pAction->GetSrcPoint(), - pAction->GetSrcSize(), - pOut->LogicToPixel( pAction->GetDestPoint(), - rPrefMapMode ), - pOut->LogicToPixel( pAction->GetDestSize(), - rPrefMapMode ), - rSizePix, - bNonBitmapActionEncountered ); - } - ++nNumBitmaps; - break; - - // these actions actually output something (that's - // different from a bitmap) - case MetaActionType::RASTEROP: - if( static_cast<MetaRasterOpAction*>(pAct)->GetRasterOp() == RasterOp::OverPaint ) - break; - SAL_FALLTHROUGH; - case MetaActionType::PIXEL: - SAL_FALLTHROUGH; - case MetaActionType::POINT: - SAL_FALLTHROUGH; - case MetaActionType::LINE: - SAL_FALLTHROUGH; - case MetaActionType::RECT: - SAL_FALLTHROUGH; - case MetaActionType::ROUNDRECT: - SAL_FALLTHROUGH; - case MetaActionType::ELLIPSE: - SAL_FALLTHROUGH; - case MetaActionType::ARC: - SAL_FALLTHROUGH; - case MetaActionType::PIE: - SAL_FALLTHROUGH; - case MetaActionType::CHORD: - SAL_FALLTHROUGH; - case MetaActionType::POLYLINE: - SAL_FALLTHROUGH; - case MetaActionType::POLYGON: - SAL_FALLTHROUGH; - case MetaActionType::POLYPOLYGON: - SAL_FALLTHROUGH; - - case MetaActionType::TEXT: - SAL_FALLTHROUGH; - case MetaActionType::TEXTARRAY: - SAL_FALLTHROUGH; - case MetaActionType::STRETCHTEXT: - SAL_FALLTHROUGH; - case MetaActionType::TEXTRECT: - SAL_FALLTHROUGH; - - case MetaActionType::MASK: - SAL_FALLTHROUGH; - case MetaActionType::MASKSCALE: - SAL_FALLTHROUGH; - case MetaActionType::MASKSCALEPART: - SAL_FALLTHROUGH; - - case MetaActionType::GRADIENT: - SAL_FALLTHROUGH; - case MetaActionType::HATCH: - SAL_FALLTHROUGH; - case MetaActionType::WALLPAPER: - SAL_FALLTHROUGH; - - case MetaActionType::Transparent: - SAL_FALLTHROUGH; - case MetaActionType::EPS: - SAL_FALLTHROUGH; - case MetaActionType::FLOATTRANSPARENT: - SAL_FALLTHROUGH; - case MetaActionType::GRADIENTEX: - SAL_FALLTHROUGH; - - // OutDev state changes that _do_ affect bitmap - // output - case MetaActionType::CLIPREGION: - SAL_FALLTHROUGH; - case MetaActionType::ISECTRECTCLIPREGION: - SAL_FALLTHROUGH; - case MetaActionType::ISECTREGIONCLIPREGION: - SAL_FALLTHROUGH; - case MetaActionType::MOVECLIPREGION: - SAL_FALLTHROUGH; - - case MetaActionType::MAPMODE: - SAL_FALLTHROUGH; - case MetaActionType::REFPOINT: - SAL_FALLTHROUGH; - default: - bNonBitmapActionEncountered = true; - break; - } - if ( pModAct ) - { - MetaAction* pDeleteAction = rOutMtf.ReplaceAction( pModAct, nCurPos ); - assert(pDeleteAction); - pDeleteAction->Delete(); - } - else - { - if( pAct->GetRefCount() > 1 ) - { - MetaAction* pDeleteAction = rOutMtf.ReplaceAction( pModAct = pAct->Clone(), nCurPos ); - assert(pDeleteAction); - pDeleteAction->Delete(); - } - else - pModAct = pAct; - } - pModAct->Scale( fScaleX, fScaleY ); - } - rOutMtf.SetPrefSize( Size( FRound( aNewSize.Width() * fScaleX ), - FRound( aNewSize.Height() * fScaleY ) ) ); - } - - if( nNumBitmaps != 1 || bNonBitmapActionEncountered ) - { - if( rAttr.IsSpecialDrawMode() || rAttr.IsAdjusted() || rAttr.IsMirrored() || rAttr.IsRotated() || rAttr.IsTransparent() ) - ImplAdjust( rOutMtf, rAttr, GraphicAdjustmentFlags::ALL ); - - ImplDraw( pOut, rPt, rSz, rOutMtf, rAttr ); - rOutBmpEx = BitmapEx(); - } - - return true; -} - -void GraphicManager::ImplAdjust( BitmapEx& rBmpEx, const GraphicAttr& rAttr, GraphicAdjustmentFlags nAdjustmentFlags ) -{ - GraphicAttr aAttr( rAttr ); - - if( ( nAdjustmentFlags & GraphicAdjustmentFlags::DRAWMODE ) && aAttr.IsSpecialDrawMode() ) - { - switch( aAttr.GetDrawMode() ) - { - case GraphicDrawMode::Mono: - rBmpEx.Convert( BmpConversion::N1BitThreshold ); - break; - - case GraphicDrawMode::Greys: - rBmpEx.Convert( BmpConversion::N8BitGreys ); - break; - - case GraphicDrawMode::Watermark: - { - aAttr.SetLuminance( aAttr.GetLuminance() + WATERMARK_LUM_OFFSET ); - aAttr.SetContrast( aAttr.GetContrast() + WATERMARK_CON_OFFSET ); - } - break; - - default: - break; - } - } - - if( ( nAdjustmentFlags & GraphicAdjustmentFlags::COLORS ) && aAttr.IsAdjusted() ) - { - rBmpEx.Adjust( aAttr.GetLuminance(), aAttr.GetContrast(), - aAttr.GetChannelR(), aAttr.GetChannelG(), aAttr.GetChannelB(), - aAttr.GetGamma(), aAttr.IsInvert() ); - } - - if( ( nAdjustmentFlags & GraphicAdjustmentFlags::MIRROR ) && aAttr.IsMirrored() ) - { - rBmpEx.Mirror( aAttr.GetMirrorFlags() ); - } - - if( ( nAdjustmentFlags & GraphicAdjustmentFlags::ROTATE ) && aAttr.IsRotated() ) - { - rBmpEx.Rotate( aAttr.GetRotation(), COL_TRANSPARENT ); - } - - if( ( nAdjustmentFlags & GraphicAdjustmentFlags::TRANSPARENCY ) && aAttr.IsTransparent() ) - { - rBmpEx.AdjustTransparency(aAttr.GetTransparency()); - } -} - -void GraphicManager::ImplAdjust( GDIMetaFile& rMtf, const GraphicAttr& rAttr, GraphicAdjustmentFlags nAdjustmentFlags ) -{ - GraphicAttr aAttr( rAttr ); - - if( ( nAdjustmentFlags & GraphicAdjustmentFlags::DRAWMODE ) && aAttr.IsSpecialDrawMode() ) - { - switch( aAttr.GetDrawMode() ) - { - case GraphicDrawMode::Mono: - rMtf.Convert( MtfConversion::N1BitThreshold ); - break; - - case GraphicDrawMode::Greys: - rMtf.Convert( MtfConversion::N8BitGreys ); - break; - - case GraphicDrawMode::Watermark: - { - aAttr.SetLuminance( aAttr.GetLuminance() + WATERMARK_LUM_OFFSET ); - aAttr.SetContrast( aAttr.GetContrast() + WATERMARK_CON_OFFSET ); - } - break; - - default: - break; - } - } - - if( ( nAdjustmentFlags & GraphicAdjustmentFlags::COLORS ) && aAttr.IsAdjusted() ) - { - rMtf.Adjust( aAttr.GetLuminance(), aAttr.GetContrast(), - aAttr.GetChannelR(), aAttr.GetChannelG(), aAttr.GetChannelB(), - aAttr.GetGamma(), aAttr.IsInvert() ); - } - - if( ( nAdjustmentFlags & GraphicAdjustmentFlags::MIRROR ) && aAttr.IsMirrored() ) - { - rMtf.Mirror( aAttr.GetMirrorFlags() ); - } - - if( ( nAdjustmentFlags & GraphicAdjustmentFlags::ROTATE ) && aAttr.IsRotated() ) - { - rMtf.Rotate( aAttr.GetRotation() ); - } - - if( ( nAdjustmentFlags & GraphicAdjustmentFlags::TRANSPARENCY ) && aAttr.IsTransparent() ) - { - OSL_FAIL( "Missing implementation: Mtf-Transparency" ); - } -} - -void GraphicManager::ImplAdjust( Animation& rAnimation, const GraphicAttr& rAttr, GraphicAdjustmentFlags nAdjustmentFlags ) -{ - GraphicAttr aAttr( rAttr ); - - if( ( nAdjustmentFlags & GraphicAdjustmentFlags::DRAWMODE ) && aAttr.IsSpecialDrawMode() ) - { - switch( aAttr.GetDrawMode() ) - { - case GraphicDrawMode::Mono: - rAnimation.Convert( BmpConversion::N1BitThreshold ); - break; - - case GraphicDrawMode::Greys: - rAnimation.Convert( BmpConversion::N8BitGreys ); - break; - - case GraphicDrawMode::Watermark: - { - aAttr.SetLuminance( aAttr.GetLuminance() + WATERMARK_LUM_OFFSET ); - aAttr.SetContrast( aAttr.GetContrast() + WATERMARK_CON_OFFSET ); - } - break; - - default: - break; - } - } - - if( ( nAdjustmentFlags & GraphicAdjustmentFlags::COLORS ) && aAttr.IsAdjusted() ) - { - rAnimation.Adjust( aAttr.GetLuminance(), aAttr.GetContrast(), - aAttr.GetChannelR(), aAttr.GetChannelG(), aAttr.GetChannelB(), - aAttr.GetGamma(), aAttr.IsInvert() ); - } - - if( ( nAdjustmentFlags & GraphicAdjustmentFlags::MIRROR ) && aAttr.IsMirrored() ) - { - rAnimation.Mirror( aAttr.GetMirrorFlags() ); - } - - if( ( nAdjustmentFlags & GraphicAdjustmentFlags::ROTATE ) && aAttr.IsRotated() ) - { - OSL_FAIL( "Missing implementation: Animation-Rotation" ); - } - - if( ( nAdjustmentFlags & GraphicAdjustmentFlags::TRANSPARENCY ) && aAttr.IsTransparent() ) - { - OSL_FAIL( "Missing implementation: Animation-Transparency" ); - } -} - -void GraphicManager::ImplDraw( OutputDevice* pOut, const Point& rPt, const Size& rSz, - const GDIMetaFile& rMtf, const GraphicAttr& rAttr ) -{ - sal_uInt16 nRot10 = rAttr.GetRotation() % 3600; - Point aOutPt( rPt ); - Size aOutSz( rSz ); - - if( nRot10 ) - { - tools::Polygon aPoly( tools::Rectangle( aOutPt, aOutSz ) ); - - aPoly.Rotate( aOutPt, nRot10 ); - const tools::Rectangle aRotBoundRect( aPoly.GetBoundRect() ); - aOutPt = aRotBoundRect.TopLeft(); - aOutSz = aRotBoundRect.GetSize(); - } - - pOut->Push( PushFlags::CLIPREGION ); - pOut->IntersectClipRegion( tools::Rectangle( aOutPt, aOutSz ) ); - - const_cast<GDIMetaFile&>(rMtf).WindStart(); - const_cast<GDIMetaFile&>(rMtf).Play( pOut, aOutPt, aOutSz ); - const_cast<GDIMetaFile&>(rMtf).WindStart(); - - pOut->Pop(); -} - -struct ImplTileInfo -{ - ImplTileInfo() : aTileTopLeft(), aNextTileTopLeft(), aTileSizePixel(), nTilesEmptyX(0), nTilesEmptyY(0) {} - - Point aTileTopLeft; // top, left position of the rendered tile - Point aNextTileTopLeft; // top, left position for next recursion - // level's tile - Size aTileSizePixel; // size of the generated tile (might - // differ from - // aNextTileTopLeft-aTileTopLeft, because - // this is nExponent*prevTileSize. The - // generated tile is always nExponent - // times the previous tile, such that it - // can be used in the next stage. The - // required area coverage is often - // less. The extraneous area covered is - // later overwritten by the next stage) - int nTilesEmptyX; // number of original tiles empty right of - // this tile. This counts from - // aNextTileTopLeft, i.e. the additional - // area covered by aTileSizePixel is not - // considered here. This is for - // unification purposes, as the iterative - // calculation of the next level's empty - // tiles has to be based on this value. - int nTilesEmptyY; // as above, for Y -}; - - -bool GraphicObject::ImplRenderTempTile( VirtualDevice& rVDev, - int nNumTilesX, int nNumTilesY, - const Size& rTileSizePixel, - const GraphicAttr* pAttr, GraphicManagerDrawFlags nFlags ) -{ - // how many tiles to generate per recursion step - const int nExponent = 2; - - // determine MSB factor - int nMSBFactor( 1 ); - while( nNumTilesX / nMSBFactor != 0 || - nNumTilesY / nMSBFactor != 0 ) - { - nMSBFactor *= nExponent; - } - - // one less - if(nMSBFactor > 1) - { - nMSBFactor /= nExponent; - } - ImplTileInfo aTileInfo; - - // #105229# Switch off mapping (converting to logic and back to - // pixel might cause roundoff errors) - bool bOldMap( rVDev.IsMapModeEnabled() ); - rVDev.EnableMapMode( false ); - - bool bRet( ImplRenderTileRecursive( rVDev, nExponent, nMSBFactor, nNumTilesX, nNumTilesY, - nNumTilesX, nNumTilesY, rTileSizePixel, pAttr, nFlags, aTileInfo ) ); - - rVDev.EnableMapMode( bOldMap ); - - return bRet; -} - -// define for debug drawings -//#define DBG_TEST - -// see header comment. this works similar to base conversion of a -// number, i.e. if the exponent is 10, then the number for every tile -// size is given by the decimal place of the corresponding decimal -// representation. -bool GraphicObject::ImplRenderTileRecursive( VirtualDevice& rVDev, int nExponent, int nMSBFactor, - int nNumOrigTilesX, int nNumOrigTilesY, - int nRemainderTilesX, int nRemainderTilesY, - const Size& rTileSizePixel, const GraphicAttr* pAttr, - GraphicManagerDrawFlags nFlags, ImplTileInfo& rTileInfo ) -{ - // gets loaded with our tile bitmap - std::unique_ptr<GraphicObject> xTmpGraphic; - GraphicObject* pTileGraphic; - - // stores a flag that renders the zero'th tile position - // (i.e. (0,0)+rCurrPos) only if we're at the bottom of the - // recursion stack. All other position already have that tile - // rendered, because the lower levels painted their generated tile - // there. - bool bNoFirstTileDraw( false ); - - // what's left when we're done with our tile size - const int nNewRemainderX( nRemainderTilesX % nMSBFactor ); - const int nNewRemainderY( nRemainderTilesY % nMSBFactor ); - - // gets filled out from the recursive call with info of what's - // been generated - ImplTileInfo aTileInfo; - - // check for recursion's end condition: LSB place reached? - if( nMSBFactor == 1 ) - { - pTileGraphic = this; - - // set initial tile size -> orig size - aTileInfo.aTileSizePixel = rTileSizePixel; - aTileInfo.nTilesEmptyX = nNumOrigTilesX; - aTileInfo.nTilesEmptyY = nNumOrigTilesY; - } - else if( ImplRenderTileRecursive( rVDev, nExponent, nMSBFactor/nExponent, - nNumOrigTilesX, nNumOrigTilesY, - nNewRemainderX, nNewRemainderY, - rTileSizePixel, pAttr, nFlags, aTileInfo ) ) - { - // extract generated tile -> see comment on the first loop below - BitmapEx aTileBitmap( rVDev.GetBitmap( aTileInfo.aTileTopLeft, aTileInfo.aTileSizePixel ) ); - - xTmpGraphic.reset(new GraphicObject(aTileBitmap)); - pTileGraphic = xTmpGraphic.get(); - - // fill stripes left over from upstream levels: - - // x0000 - // 0 - // 0 - // 0 - // 0 - - // where x denotes the place filled by our recursive predecessors - - // check whether we have to fill stripes here. Although not - // obvious, there is one case where we can skip this step: if - // the previous recursion level (the one who filled our - // aTileInfo) had zero area to fill, then there are no white - // stripes left, naturally. This happens if the digit - // associated to that level has a zero, and can be checked via - // aTileTopLeft==aNextTileTopLeft. - if( aTileInfo.aTileTopLeft != aTileInfo.aNextTileTopLeft ) - { - // now fill one row from aTileInfo.aNextTileTopLeft.X() all - // the way to the right - // current output position while drawing - Point aCurrPos(aTileInfo.aNextTileTopLeft.X(), aTileInfo.aTileTopLeft.Y()); - for (int nX=0; nX < aTileInfo.nTilesEmptyX; nX += nMSBFactor) - { - if (!pTileGraphic->Draw(&rVDev, aCurrPos, aTileInfo.aTileSizePixel, pAttr, nFlags)) - return false; - - aCurrPos.AdjustX(aTileInfo.aTileSizePixel.Width() ); - } - -#ifdef DBG_TEST -// rVDev.SetFillCOL_WHITE ); - rVDev.SetFillColor(); - rVDev.SetLineColor( Color( 255 * nExponent / nMSBFactor, 255 - 255 * nExponent / nMSBFactor, 128 - 255 * nExponent / nMSBFactor ) ); - rVDev.DrawEllipse( Rectangle(aTileInfo.aNextTileTopLeft.X(), aTileInfo.aTileTopLeft.Y(), - aTileInfo.aNextTileTopLeft.X() - 1 + (aTileInfo.nTilesEmptyX/nMSBFactor)*aTileInfo.aTileSizePixel.Width(), - aTileInfo.aTileTopLeft.Y() + aTileInfo.aTileSizePixel.Height() - 1) ); -#endif - - // now fill one column from aTileInfo.aNextTileTopLeft.Y() all - // the way to the bottom - aCurrPos.setX( aTileInfo.aTileTopLeft.X() ); - aCurrPos.setY( aTileInfo.aNextTileTopLeft.Y() ); - for (int nY=0; nY < aTileInfo.nTilesEmptyY; nY += nMSBFactor) - { - if (!pTileGraphic->Draw(&rVDev, aCurrPos, aTileInfo.aTileSizePixel, pAttr, nFlags)) - return false; - - aCurrPos.AdjustY(aTileInfo.aTileSizePixel.Height() ); - } - -#ifdef DBG_TEST - rVDev.DrawEllipse( Rectangle(aTileInfo.aTileTopLeft.X(), aTileInfo.aNextTileTopLeft.Y(), - aTileInfo.aTileTopLeft.X() + aTileInfo.aTileSizePixel.Width() - 1, - aTileInfo.aNextTileTopLeft.Y() - 1 + (aTileInfo.nTilesEmptyY/nMSBFactor)*aTileInfo.aTileSizePixel.Height()) ); -#endif - } - else - { - // Thought that aTileInfo.aNextTileTopLeft tile has always - // been drawn already, but that's wrong: typically, - // _parts_ of that tile have been drawn, since the - // previous level generated the tile there. But when - // aTileInfo.aNextTileTopLeft!=aTileInfo.aTileTopLeft, the - // difference between these two values is missing in the - // lower right corner of this first tile. So, can do that - // only here. - bNoFirstTileDraw = true; - } - } - else - { - return false; - } - - // calc number of original tiles in our drawing area without - // remainder - nRemainderTilesX -= nNewRemainderX; - nRemainderTilesY -= nNewRemainderY; - - // fill tile info for calling method - rTileInfo.aTileTopLeft = aTileInfo.aNextTileTopLeft; - rTileInfo.aNextTileTopLeft = Point( rTileInfo.aTileTopLeft.X() + rTileSizePixel.Width()*nRemainderTilesX, - rTileInfo.aTileTopLeft.Y() + rTileSizePixel.Height()*nRemainderTilesY ); - rTileInfo.aTileSizePixel = Size( rTileSizePixel.Width()*nMSBFactor*nExponent, - rTileSizePixel.Height()*nMSBFactor*nExponent ); - rTileInfo.nTilesEmptyX = aTileInfo.nTilesEmptyX - nRemainderTilesX; - rTileInfo.nTilesEmptyY = aTileInfo.nTilesEmptyY - nRemainderTilesY; - - // init output position - Point aCurrPos = aTileInfo.aNextTileTopLeft; - - // fill our drawing area. Fill possibly more, to create the next - // bigger tile size -> see bitmap extraction above. This does no - // harm, since everything right or below our actual area is - // overdrawn by our caller. Just in case we're in the last level, - // we don't draw beyond the right or bottom border. - for (int nY=0; nY < aTileInfo.nTilesEmptyY && nY < nExponent*nMSBFactor; nY += nMSBFactor) - { - aCurrPos.setX( aTileInfo.aNextTileTopLeft.X() ); - - for (int nX=0; nX < aTileInfo.nTilesEmptyX && nX < nExponent*nMSBFactor; nX += nMSBFactor) - { - if( bNoFirstTileDraw ) - bNoFirstTileDraw = false; // don't draw first tile position - else if (!pTileGraphic->Draw(&rVDev, aCurrPos, aTileInfo.aTileSizePixel, pAttr, nFlags)) - return false; - - aCurrPos.AdjustX(aTileInfo.aTileSizePixel.Width() ); - } - - aCurrPos.AdjustY(aTileInfo.aTileSizePixel.Height() ); - } - -#ifdef DBG_TEST -// rVDev.SetFillCOL_WHITE ); - rVDev.SetFillColor(); - rVDev.SetLineColor( Color( 255 * nExponent / nMSBFactor, 255 - 255 * nExponent / nMSBFactor, 128 - 255 * nExponent / nMSBFactor ) ); - rVDev.DrawRect( Rectangle((rTileInfo.aTileTopLeft.X())*rTileSizePixel.Width(), - (rTileInfo.aTileTopLeft.Y())*rTileSizePixel.Height(), - (rTileInfo.aNextTileTopLeft.X())*rTileSizePixel.Width()-1, - (rTileInfo.aNextTileTopLeft.Y())*rTileSizePixel.Height()-1) ); -#endif - - return true; -} - -bool GraphicObject::ImplDrawTiled( OutputDevice* pOut, const tools::Rectangle& rArea, const Size& rSizePixel, - const Size& rOffset, const GraphicAttr* pAttr, GraphicManagerDrawFlags nFlags, int nTileCacheSize1D ) -{ - const MapMode aOutMapMode( pOut->GetMapMode() ); - const MapMode aMapMode( aOutMapMode.GetMapUnit(), Point(), aOutMapMode.GetScaleX(), aOutMapMode.GetScaleY() ); - bool bRet( false ); - - // #i42643# Casting to Int64, to avoid integer overflow for - // huge-DPI output devices - if( GetGraphic().GetType() == GraphicType::Bitmap && - static_cast<sal_Int64>(rSizePixel.Width()) * rSizePixel.Height() < - static_cast<sal_Int64>(nTileCacheSize1D)*nTileCacheSize1D ) - { - // First combine very small bitmaps into a larger tile - - - ScopedVclPtrInstance< VirtualDevice > aVDev; - const int nNumTilesInCacheX( (nTileCacheSize1D + rSizePixel.Width()-1) / rSizePixel.Width() ); - const int nNumTilesInCacheY( (nTileCacheSize1D + rSizePixel.Height()-1) / rSizePixel.Height() ); - - aVDev->SetOutputSizePixel( Size( nNumTilesInCacheX*rSizePixel.Width(), - nNumTilesInCacheY*rSizePixel.Height() ) ); - aVDev->SetMapMode( aMapMode ); - - // draw bitmap content - if( ImplRenderTempTile( *aVDev.get(), nNumTilesInCacheX, - nNumTilesInCacheY, rSizePixel, pAttr, nFlags ) ) - { - BitmapEx aTileBitmap( aVDev->GetBitmap( Point(0,0), aVDev->GetOutputSize() ) ); - - // draw alpha content, if any - if( IsTransparent() ) - { - GraphicObject aAlphaGraphic; - - if( GetGraphic().IsAlpha() ) - aAlphaGraphic.SetGraphic( GetGraphic().GetBitmapEx().GetAlpha().GetBitmap() ); - else - aAlphaGraphic.SetGraphic( GetGraphic().GetBitmapEx().GetMask() ); - - if( aAlphaGraphic.ImplRenderTempTile( *aVDev.get(), nNumTilesInCacheX, - nNumTilesInCacheY, rSizePixel, pAttr, nFlags ) ) - { - // Combine bitmap and alpha/mask - if( GetGraphic().IsAlpha() ) - aTileBitmap = BitmapEx( aTileBitmap.GetBitmap(), - AlphaMask( aVDev->GetBitmap( Point(0,0), aVDev->GetOutputSize() ) ) ); - else - aTileBitmap = BitmapEx( aTileBitmap.GetBitmap(), - aVDev->GetBitmap( Point(0,0), aVDev->GetOutputSize() ).CreateMask( COL_WHITE ) ); - } - } - - // paint generated tile - GraphicObject aTmpGraphic( aTileBitmap ); - bRet = aTmpGraphic.ImplDrawTiled( pOut, rArea, - aTileBitmap.GetSizePixel(), - rOffset, pAttr, nFlags, nTileCacheSize1D ); - } - } - else - { - const Size aOutOffset( pOut->LogicToPixel( rOffset, aOutMapMode ) ); - const tools::Rectangle aOutArea( pOut->LogicToPixel( rArea, aOutMapMode ) ); - - // number of invisible (because out-of-area) tiles - int nInvisibleTilesX; - int nInvisibleTilesY; - - // round towards -infty for negative offset - if( aOutOffset.Width() < 0 ) - nInvisibleTilesX = (aOutOffset.Width() - rSizePixel.Width() + 1) / rSizePixel.Width(); - else - nInvisibleTilesX = aOutOffset.Width() / rSizePixel.Width(); - - // round towards -infty for negative offset - if( aOutOffset.Height() < 0 ) - nInvisibleTilesY = (aOutOffset.Height() - rSizePixel.Height() + 1) / rSizePixel.Height(); - else - nInvisibleTilesY = aOutOffset.Height() / rSizePixel.Height(); - - // origin from where to 'virtually' start drawing in pixel - const Point aOutOrigin( pOut->LogicToPixel( Point( rArea.Left() - rOffset.Width(), - rArea.Top() - rOffset.Height() ) ) ); - // position in pixel from where to really start output - const Point aOutStart( aOutOrigin.X() + nInvisibleTilesX*rSizePixel.Width(), - aOutOrigin.Y() + nInvisibleTilesY*rSizePixel.Height() ); - - pOut->Push( PushFlags::CLIPREGION ); - pOut->IntersectClipRegion( rArea ); - - // Paint all tiles - - - bRet = ImplDrawTiled( *pOut, aOutStart, - (aOutArea.GetWidth() + aOutArea.Left() - aOutStart.X() + rSizePixel.Width() - 1) / rSizePixel.Width(), - (aOutArea.GetHeight() + aOutArea.Top() - aOutStart.Y() + rSizePixel.Height() - 1) / rSizePixel.Height(), - rSizePixel, pAttr, nFlags ); - - pOut->Pop(); - } - - return bRet; -} - -bool GraphicObject::ImplDrawTiled( OutputDevice& rOut, const Point& rPosPixel, - int nNumTilesX, int nNumTilesY, - const Size& rTileSizePixel, const GraphicAttr* pAttr, GraphicManagerDrawFlags nFlags ) -{ - Point aCurrPos( rPosPixel ); - Size aTileSizeLogic( rOut.PixelToLogic( rTileSizePixel ) ); - int nX, nY; - - // #107607# Use logical coordinates for metafile playing, too - bool bDrawInPixel( rOut.GetConnectMetaFile() == nullptr && GraphicType::Bitmap == GetType() ); - bool bRet = false; - - // #105229# Switch off mapping (converting to logic and back to - // pixel might cause roundoff errors) - bool bOldMap( rOut.IsMapModeEnabled() ); - - if( bDrawInPixel ) - rOut.EnableMapMode( false ); - - for( nY=0; nY < nNumTilesY; ++nY ) - { - aCurrPos.setX( rPosPixel.X() ); - - for( nX=0; nX < nNumTilesX; ++nX ) - { - // #105229# work with pixel coordinates here, mapping is disabled! - // #104004# don't disable mapping for metafile recordings - // #108412# don't quit the loop if one draw fails - - // update return value. This method should return true, if - // at least one of the looped Draws succeeded. - bRet |= Draw( &rOut, - bDrawInPixel ? aCurrPos : rOut.PixelToLogic( aCurrPos ), - bDrawInPixel ? rTileSizePixel : aTileSizeLogic, - pAttr, nFlags ); - - aCurrPos.AdjustX(rTileSizePixel.Width() ); - } - - aCurrPos.AdjustY(rTileSizePixel.Height() ); - } - - if( bDrawInPixel ) - rOut.EnableMapMode( bOldMap ); - - return bRet; -} - -void GraphicObject::ImplTransformBitmap( BitmapEx& rBmpEx, - const GraphicAttr& rAttr, - const Size& rCropLeftTop, - const Size& rCropRightBottom, - const tools::Rectangle& rCropRect, - const Size& rDstSize, - bool bEnlarge ) const -{ - // #107947# Extracted from svdograf.cxx - - // #104115# Crop the bitmap - if( rAttr.IsCropped() ) - { - rBmpEx.Crop( rCropRect ); - - // #104115# Negative crop sizes mean: enlarge bitmap and pad - if( bEnlarge && ( - rCropLeftTop.Width() < 0 || - rCropLeftTop.Height() < 0 || - rCropRightBottom.Width() < 0 || - rCropRightBottom.Height() < 0 ) ) - { - Size aBmpSize( rBmpEx.GetSizePixel() ); - sal_Int32 nPadLeft( rCropLeftTop.Width() < 0 ? -rCropLeftTop.Width() : 0 ); - sal_Int32 nPadTop( rCropLeftTop.Height() < 0 ? -rCropLeftTop.Height() : 0 ); - sal_Int32 nPadTotalWidth( aBmpSize.Width() + nPadLeft + (rCropRightBottom.Width() < 0 ? -rCropRightBottom.Width() : 0) ); - sal_Int32 nPadTotalHeight( aBmpSize.Height() + nPadTop + (rCropRightBottom.Height() < 0 ? -rCropRightBottom.Height() : 0) ); - - BitmapEx aBmpEx2; - - if( rBmpEx.IsTransparent() ) - { - if( rBmpEx.IsAlpha() ) - aBmpEx2 = BitmapEx( rBmpEx.GetBitmap(), rBmpEx.GetAlpha() ); - else - aBmpEx2 = BitmapEx( rBmpEx.GetBitmap(), rBmpEx.GetMask() ); - } - else - { - // #104115# Generate mask bitmap and init to zero - Bitmap aMask( aBmpSize, 1 ); - aMask.Erase( Color(0,0,0) ); - - // #104115# Always generate transparent bitmap, we need the border transparent - aBmpEx2 = BitmapEx( rBmpEx.GetBitmap(), aMask ); - - // #104115# Add opaque mask to source bitmap, otherwise the destination remains transparent - rBmpEx = aBmpEx2; - } - - aBmpEx2.SetSizePixel( Size(nPadTotalWidth, nPadTotalHeight) ); - aBmpEx2.Erase( Color(0xFF,0,0,0) ); - aBmpEx2.CopyPixel( tools::Rectangle( Point(nPadLeft, nPadTop), aBmpSize ), tools::Rectangle( Point(0, 0), aBmpSize ), &rBmpEx ); - rBmpEx = aBmpEx2; - } - } - - const Size aSizePixel( rBmpEx.GetSizePixel() ); - - if( !(rAttr.GetRotation() != 0 && !IsAnimated()) ) - return; - - if( !(aSizePixel.Width() && aSizePixel.Height() && rDstSize.Width() && rDstSize.Height()) ) - return; - - double fSrcWH = static_cast<double>(aSizePixel.Width()) / aSizePixel.Height(); - double fDstWH = static_cast<double>(rDstSize.Width()) / rDstSize.Height(); - double fScaleX = 1.0, fScaleY = 1.0; - - // always choose scaling to shrink bitmap - if( fSrcWH < fDstWH ) - fScaleY = aSizePixel.Width() / ( fDstWH * aSizePixel.Height() ); - else - fScaleX = fDstWH * aSizePixel.Height() / aSizePixel.Width(); - - rBmpEx.Scale( fScaleX, fScaleY ); -} - -/* vim:set shiftwidth=4 softtabstop=4 expandtab: */ diff --git a/svtools/source/graphic/provider.cxx b/svtools/source/graphic/provider.cxx deleted file mode 100644 index 9e8c8b636d2b..000000000000 --- a/svtools/source/graphic/provider.cxx +++ /dev/null @@ -1,847 +0,0 @@ -/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */ -/* - * This file is part of the LibreOffice project. - * - * This Source Code Form is subject to the terms of the Mozilla Public - * License, v. 2.0. If a copy of the MPL was not distributed with this - * file, You can obtain one at http://mozilla.org/MPL/2.0/. - * - * This file incorporates work covered by the following license notice: - * - * Licensed to the Apache Software Foundation (ASF) under one or more - * contributor license agreements. See the NOTICE file distributed - * with this work for additional information regarding copyright - * ownership. The ASF licenses this file to you under the Apache - * License, Version 2.0 (the "License"); you may not use this file - * except in compliance with the License. You may obtain a copy of - * the License at http://www.apache.org/licenses/LICENSE-2.0 . - */ - -#include <vcl/svapp.hxx> -#include <vcl/image.hxx> -#include <vcl/metaact.hxx> -#include <vcl/msgbox.hxx> -#include <vcl/imagerepository.hxx> -#include <unotools/resmgr.hxx> -#include <tools/fract.hxx> -#include <unotools/ucbstreamhelper.hxx> -#include <vcl/graphicfilter.hxx> -#include <vcl/wmf.hxx> -#include <svl/solar.hrc> -#include <vcl/virdev.hxx> -#include <vcl/settings.hxx> -#include <com/sun/star/awt/XBitmap.hpp> -#include <com/sun/star/graphic/XGraphicProvider2.hpp> -#include <com/sun/star/io/XStream.hpp> -#include <com/sun/star/lang/XServiceInfo.hpp> -#include <com/sun/star/text/GraphicCrop.hpp> -#include <com/sun/star/uno/XComponentContext.hpp> -#include <comphelper/fileformat.h> -#include <comphelper/servicehelper.hxx> -#include <cppuhelper/implbase.hxx> -#include <cppuhelper/supportsservice.hxx> - -#include "descriptor.hxx" -#include "graphic.hxx" -#include <rtl/ref.hxx> -#include <svtools/grfmgr.hxx> -#include <vcl/dibtools.hxx> -#include <comphelper/sequence.hxx> -#include <memory> -#include <svtools/ehdl.hxx> - -using namespace com::sun::star; - -namespace { - -#define UNO_NAME_GRAPHOBJ_URLPREFIX "vnd.sun.star.GraphicObject:" - -class GraphicProvider : public ::cppu::WeakImplHelper< css::graphic::XGraphicProvider2, - css::lang::XServiceInfo > -{ -public: - - GraphicProvider(); - -protected: - - // XServiceInfo - virtual OUString SAL_CALL getImplementationName() override; - virtual sal_Bool SAL_CALL supportsService( const OUString& ServiceName ) override; - virtual css::uno::Sequence< OUString > SAL_CALL getSupportedServiceNames() override; - - // XTypeProvider - virtual css::uno::Sequence< css::uno::Type > SAL_CALL getTypes( ) override; - virtual css::uno::Sequence< sal_Int8 > SAL_CALL getImplementationId( ) override; - - // XGraphicProvider - virtual css::uno::Reference< css::beans::XPropertySet > SAL_CALL queryGraphicDescriptor( const css::uno::Sequence< css::beans::PropertyValue >& MediaProperties ) override; - virtual css::uno::Reference< css::graphic::XGraphic > SAL_CALL queryGraphic( const css::uno::Sequence< css::beans::PropertyValue >& MediaProperties ) override; - virtual void SAL_CALL storeGraphic( const css::uno::Reference< css::graphic::XGraphic >& Graphic, const css::uno::Sequence< css::beans::PropertyValue >& MediaProperties ) override; - - // XGraphicProvider2 - uno::Sequence< uno::Reference<graphic::XGraphic> > SAL_CALL queryGraphics(const uno::Sequence< uno::Sequence<beans::PropertyValue> >& MediaPropertiesSeq ) override; - -private: - - static css::uno::Reference< css::graphic::XGraphic > implLoadMemory( const OUString& rResourceURL ); - static css::uno::Reference< css::graphic::XGraphic > implLoadGraphicObject( const OUString& rResourceURL ); - static css::uno::Reference< css::graphic::XGraphic > implLoadRepositoryImage( const OUString& rResourceURL ); - static css::uno::Reference< css::graphic::XGraphic > implLoadBitmap( const css::uno::Reference< css::awt::XBitmap >& rBitmap ); - static css::uno::Reference< css::graphic::XGraphic > implLoadStandardImage( const OUString& rResourceURL ); -}; - -GraphicProvider::GraphicProvider() -{ -} - -OUString SAL_CALL GraphicProvider::getImplementationName() -{ - return OUString( "com.sun.star.comp.graphic.GraphicProvider" ); -} - -sal_Bool SAL_CALL GraphicProvider::supportsService( const OUString& ServiceName ) -{ - return cppu::supportsService( this, ServiceName ); -} - -uno::Sequence< OUString > SAL_CALL GraphicProvider::getSupportedServiceNames() -{ - uno::Sequence<OUString> aSeq { "com.sun.star.graphic.GraphicProvider" }; - return aSeq; -} - -uno::Sequence< uno::Type > SAL_CALL GraphicProvider::getTypes() -{ - uno::Sequence< uno::Type > aTypes( 3 ); - uno::Type* pTypes = aTypes.getArray(); - - *pTypes++ = cppu::UnoType<lang::XServiceInfo>::get(); - *pTypes++ = cppu::UnoType<lang::XTypeProvider>::get(); - *pTypes++ = cppu::UnoType<graphic::XGraphicProvider>::get(); - - return aTypes; -} - -uno::Sequence< sal_Int8 > SAL_CALL GraphicProvider::getImplementationId() -{ - return css::uno::Sequence<sal_Int8>(); -} - - -uno::Reference< ::graphic::XGraphic > GraphicProvider::implLoadGraphicObject( const OUString& rResourceURL ) -{ - uno::Reference< ::graphic::XGraphic > xRet; - if( rResourceURL.startsWith( UNO_NAME_GRAPHOBJ_URLPREFIX ) ) - { - // graphic manager url - OUString aTmpStr( rResourceURL.copy( sizeof( UNO_NAME_GRAPHOBJ_URLPREFIX ) - 1 ) ); - OString aUniqueID(OUStringToOString(aTmpStr, - RTL_TEXTENCODING_UTF8)); - GraphicObject aGrafObj(aUniqueID); - // I don't call aGrafObj.GetXGraphic because it will call us back - // into implLoadMemory ( with "private:memorygraphic" test ) - ::unographic::Graphic* pUnoGraphic = new ::unographic::Graphic; - pUnoGraphic->init( aGrafObj.GetGraphic() ); - xRet = pUnoGraphic; - } - return xRet; -} - -uno::Reference< ::graphic::XGraphic > GraphicProvider::implLoadMemory( const OUString& rResourceURL ) -{ - uno::Reference< ::graphic::XGraphic > xRet; - sal_Int32 nIndex = 0; - - if( rResourceURL.getToken( 0, '/', nIndex ) == "private:memorygraphic" ) - { - sal_Int64 nGraphicAddress = rResourceURL.getToken( 0, '/', nIndex ).toInt64(); - - if( nGraphicAddress ) - { - ::unographic::Graphic* pUnoGraphic = new ::unographic::Graphic; - - pUnoGraphic->init( *reinterpret_cast< ::Graphic* >( nGraphicAddress ) ); - xRet = pUnoGraphic; - } - } - - return xRet; -} - - -uno::Reference< ::graphic::XGraphic > GraphicProvider::implLoadRepositoryImage( const OUString& rResourceURL ) -{ - uno::Reference< ::graphic::XGraphic > xRet; - sal_Int32 nIndex = 0; - - if( rResourceURL.getToken( 0, '/', nIndex ) == "private:graphicrepository" ) - { - OUString sPathName( rResourceURL.copy( nIndex ) ); - BitmapEx aBitmap; - if ( vcl::ImageRepository::loadImage( sPathName, aBitmap ) ) - { - xRet = Graphic(aBitmap).GetXGraphic(); - } - } - return xRet; -} - - -uno::Reference< ::graphic::XGraphic > GraphicProvider::implLoadStandardImage( const OUString& rResourceURL ) -{ - uno::Reference< ::graphic::XGraphic > xRet; - sal_Int32 nIndex = 0; - - if( rResourceURL.getToken( 0, '/', nIndex ) == "private:standardimage" ) - { - OUString sImageName( rResourceURL.copy( nIndex ) ); - if ( sImageName == "info" ) - { - xRet = Graphic(GetStandardInfoBoxImage().GetBitmapEx()).GetXGraphic(); - } - else if ( sImageName == "warning" ) - { - xRet = Graphic(GetStandardWarningBoxImage().GetBitmapEx()).GetXGraphic(); - } - else if ( sImageName == "error" ) - { - xRet = Graphic(GetStandardErrorBoxImage().GetBitmapEx()).GetXGraphic(); - } - else if ( sImageName == "query" ) - { - xRet = Graphic(GetStandardQueryBoxImage().GetBitmapEx()).GetXGraphic(); - } - } - return xRet; -} - - -uno::Reference< ::graphic::XGraphic > GraphicProvider::implLoadBitmap( const uno::Reference< awt::XBitmap >& xBtm ) -{ - uno::Reference< ::graphic::XGraphic > xRet; - uno::Sequence< sal_Int8 > aBmpSeq( xBtm->getDIB() ); - uno::Sequence< sal_Int8 > aMaskSeq( xBtm->getMaskDIB() ); - SvMemoryStream aBmpStream( aBmpSeq.getArray(), aBmpSeq.getLength(), StreamMode::READ ); - Bitmap aBmp; - BitmapEx aBmpEx; - - ReadDIB(aBmp, aBmpStream, true); - - if( aMaskSeq.getLength() ) - { - SvMemoryStream aMaskStream( aMaskSeq.getArray(), aMaskSeq.getLength(), StreamMode::READ ); - Bitmap aMask; - - ReadDIB(aMask, aMaskStream, true); - aBmpEx = BitmapEx( aBmp, aMask ); - } - else - aBmpEx = BitmapEx( aBmp ); - - if( !aBmpEx.IsEmpty() ) - { - ::unographic::Graphic* pUnoGraphic = new ::unographic::Graphic; - - pUnoGraphic->init( aBmpEx ); - xRet = pUnoGraphic; - } - return xRet; -} - -uno::Reference< beans::XPropertySet > SAL_CALL GraphicProvider::queryGraphicDescriptor( const uno::Sequence< beans::PropertyValue >& rMediaProperties ) -{ - uno::Reference< beans::XPropertySet > xRet; - - OUString aURL; - uno::Reference< io::XInputStream > xIStm; - uno::Reference< awt::XBitmap >xBtm; - - for( sal_Int32 i = 0; ( i < rMediaProperties.getLength() ) && !xRet.is(); ++i ) - { - const OUString aName( rMediaProperties[ i ].Name ); - const uno::Any aValue( rMediaProperties[ i ].Value ); - - if (aName == "URL") - { - aValue >>= aURL; - } - else if (aName == "InputStream") - { - aValue >>= xIStm; - } - else if (aName == "Bitmap") - { - aValue >>= xBtm; - } - } - - SolarMutexGuard g; - - if( xIStm.is() ) - { - unographic::GraphicDescriptor* pDescriptor = new unographic::GraphicDescriptor; - pDescriptor->init( xIStm, aURL ); - xRet = pDescriptor; - } - else if( !aURL.isEmpty() ) - { - uno::Reference< ::graphic::XGraphic > xGraphic( implLoadMemory( aURL ) ); - if( !xGraphic.is() ) - xGraphic = implLoadGraphicObject( aURL ); - - if ( !xGraphic.is() ) - xGraphic = implLoadRepositoryImage( aURL ); - - if ( !xGraphic.is() ) - xGraphic = implLoadStandardImage( aURL ); - - if( xGraphic.is() ) - { - xRet.set( xGraphic, uno::UNO_QUERY ); - } - else - { - unographic::GraphicDescriptor* pDescriptor = new unographic::GraphicDescriptor; - pDescriptor->init( aURL ); - xRet = pDescriptor; - } - } - else if( xBtm.is() ) - { - uno::Reference< ::graphic::XGraphic > xGraphic( implLoadBitmap( xBtm ) ); - if( xGraphic.is() ) - xRet.set( xGraphic, uno::UNO_QUERY ); - } - - return xRet; -} - - -uno::Reference< ::graphic::XGraphic > SAL_CALL GraphicProvider::queryGraphic( const uno::Sequence< ::beans::PropertyValue >& rMediaProperties ) -{ - uno::Reference< ::graphic::XGraphic > xRet; - OUString aPath; - std::unique_ptr<SvStream> pIStm; - - uno::Reference< io::XInputStream > xIStm; - uno::Reference< awt::XBitmap >xBtm; - - uno::Sequence< ::beans::PropertyValue > aFilterData; - - for( sal_Int32 i = 0; ( i < rMediaProperties.getLength() ) && !pIStm && !xRet.is(); ++i ) - { - const OUString aName( rMediaProperties[ i ].Name ); - const uno::Any aValue( rMediaProperties[ i ].Value ); - - if (aName == "URL") - { - OUString aURL; - aValue >>= aURL; - aPath = aURL; - } - else if (aName == "InputStream") - { - aValue >>= xIStm; - } - else if (aName == "Bitmap") - { - aValue >>= xBtm; - } - else if (aName == "FilterData") - { - aValue >>= aFilterData; - } - } - - // Check for the goal width and height if they are defined - sal_uInt16 nExtWidth = 0; - sal_uInt16 nExtHeight = 0; - sal_uInt16 nExtMapMode = 0; - for( sal_Int32 i = 0; i < aFilterData.getLength(); ++i ) - { - const OUString aName( aFilterData[ i ].Name ); - const uno::Any aValue( aFilterData[ i ].Value ); - - if (aName == "ExternalWidth") - { - aValue >>= nExtWidth; - } - else if (aName == "ExternalHeight") - { - aValue >>= nExtHeight; - } - else if (aName == "ExternalMapMode") - { - aValue >>= nExtMapMode; - } - } - - SolarMutexGuard g; - - if( xIStm.is() ) - { - pIStm.reset(::utl::UcbStreamHelper::CreateStream( xIStm )); - } - else if( !aPath.isEmpty() ) - { - xRet = implLoadMemory( aPath ); - - if( !xRet.is() ) - xRet = implLoadGraphicObject( aPath ); - - if ( !xRet.is() ) - xRet = implLoadRepositoryImage( aPath ); - - if ( !xRet.is() ) - xRet = implLoadStandardImage( aPath ); - - if( !xRet.is() ) - pIStm.reset(::utl::UcbStreamHelper::CreateStream( aPath, StreamMode::READ )); - } - else if( xBtm.is() ) - { - xRet = implLoadBitmap( xBtm ); - } - - if( pIStm ) - { - ::GraphicFilter& rFilter = ::GraphicFilter::GetGraphicFilter(); - - { - ::Graphic aVCLGraphic; - - // Define APM Header if goal height and width are defined - WmfExternal aExtHeader; - aExtHeader.xExt = nExtWidth; - aExtHeader.yExt = nExtHeight; - aExtHeader.mapMode = nExtMapMode; - WmfExternal *pExtHeader = nullptr; - if ( nExtMapMode > 0 ) - pExtHeader = &aExtHeader; - - ErrCode error = rFilter.ImportGraphic( aVCLGraphic, aPath, *pIStm, - GRFILTER_FORMAT_DONTKNOW, nullptr, GraphicFilterImportFlags::NONE, pExtHeader ); - if( (error == ERRCODE_NONE ) && - ( aVCLGraphic.GetType() != GraphicType::NONE ) ) - { - ::unographic::Graphic* pUnoGraphic = new ::unographic::Graphic; - - pUnoGraphic->init( aVCLGraphic ); - xRet = pUnoGraphic; - } - else{ - SAL_WARN("svtools", "Could not create graphic: " << error); - } - } - } - - return xRet; -} - -uno::Sequence< uno::Reference<graphic::XGraphic> > SAL_CALL GraphicProvider::queryGraphics(const uno::Sequence< uno::Sequence<beans::PropertyValue> >& rMediaPropertiesSeq) -{ - SolarMutexGuard aGuard; - - // Turn properties into streams. - std::vector< std::shared_ptr<SvStream> > aStreams; - for (const auto& rMediaProperties : rMediaPropertiesSeq) - { - SvStream* pStream = nullptr; - uno::Reference<io::XInputStream> xStream; - - for (sal_Int32 i = 0; rMediaProperties.getLength(); ++i) - { - if (rMediaProperties[i].Name == "InputStream") - { - rMediaProperties[i].Value >>= xStream; - if (xStream.is()) - pStream = utl::UcbStreamHelper::CreateStream(xStream); - break; - } - } - - aStreams.push_back(std::shared_ptr<SvStream>(pStream)); - - } - - // Import: streams to graphics. - std::vector< std::shared_ptr<Graphic> > aGraphics; - GraphicFilter& rFilter = GraphicFilter::GetGraphicFilter(); - rFilter.ImportGraphics(aGraphics, aStreams); - - // Returning: graphics to UNO objects. - std::vector< uno::Reference<graphic::XGraphic> > aRet; - for (const auto& pGraphic : aGraphics) - { - uno::Reference<graphic::XGraphic> xGraphic; - - if (pGraphic) - { - auto pUnoGraphic = new unographic::Graphic(); - pUnoGraphic->init(*pGraphic); - xGraphic = pUnoGraphic; - } - - aRet.push_back(xGraphic); - } - - return comphelper::containerToSequence(aRet); -} - -void ImplCalculateCropRect( ::Graphic const & rGraphic, const text::GraphicCrop& rGraphicCropLogic, tools::Rectangle& rGraphicCropPixel ) -{ - if ( !(rGraphicCropLogic.Left || rGraphicCropLogic.Top || rGraphicCropLogic.Right || rGraphicCropLogic.Bottom) ) - return; - - Size aSourceSizePixel( rGraphic.GetSizePixel() ); - if ( !(aSourceSizePixel.Width() && aSourceSizePixel.Height()) ) - return; - - if ( !(rGraphicCropLogic.Left || rGraphicCropLogic.Top || rGraphicCropLogic.Right || rGraphicCropLogic.Bottom) ) - return; - - Size aSize100thMM( 0, 0 ); - if( rGraphic.GetPrefMapMode().GetMapUnit() != MapUnit::MapPixel ) - { - aSize100thMM = OutputDevice::LogicToLogic(rGraphic.GetPrefSize(), rGraphic.GetPrefMapMode(), MapMode(MapUnit::Map100thMM)); - } - else - { - aSize100thMM = Application::GetDefaultDevice()->PixelToLogic(rGraphic.GetPrefSize(), MapMode(MapUnit::Map100thMM)); - } - if ( aSize100thMM.Width() && aSize100thMM.Height() ) - { - double fSourceSizePixelWidth = static_cast<double>(aSourceSizePixel.Width()); - double fSourceSizePixelHeight= static_cast<double>(aSourceSizePixel.Height()); - rGraphicCropPixel.SetLeft( static_cast< sal_Int32 >((fSourceSizePixelWidth * rGraphicCropLogic.Left ) / aSize100thMM.Width()) ); - rGraphicCropPixel.SetTop( static_cast< sal_Int32 >((fSourceSizePixelHeight * rGraphicCropLogic.Top ) / aSize100thMM.Height()) ); - rGraphicCropPixel.SetRight( static_cast< sal_Int32 >(( fSourceSizePixelWidth * ( aSize100thMM.Width() - rGraphicCropLogic.Right ) ) / aSize100thMM.Width() ) ); - rGraphicCropPixel.SetBottom( static_cast< sal_Int32 >(( fSourceSizePixelHeight * ( aSize100thMM.Height() - rGraphicCropLogic.Bottom ) ) / aSize100thMM.Height() ) ); - } -} - -void ImplApplyBitmapScaling( ::Graphic& rGraphic, sal_Int32 nPixelWidth, sal_Int32 nPixelHeight ) -{ - if ( nPixelWidth && nPixelHeight ) - { - BitmapEx aBmpEx( rGraphic.GetBitmapEx() ); - MapMode aPrefMapMode( aBmpEx.GetPrefMapMode() ); - Size aPrefSize( aBmpEx.GetPrefSize() ); - aBmpEx.Scale( Size( nPixelWidth, nPixelHeight ) ); - aBmpEx.SetPrefMapMode( aPrefMapMode ); - aBmpEx.SetPrefSize( aPrefSize ); - rGraphic = aBmpEx; - } -} - -void ImplApplyBitmapResolution( ::Graphic& rGraphic, sal_Int32 nImageResolution, const Size& rVisiblePixelSize, const awt::Size& rLogicalSize ) -{ - if ( !(nImageResolution && rLogicalSize.Width && rLogicalSize.Height) ) - return; - - const double fImageResolution = static_cast<double>( nImageResolution ); - const double fSourceDPIX = ( static_cast<double>(rVisiblePixelSize.Width()) * 2540.0 ) / static_cast<double>(rLogicalSize.Width); - const double fSourceDPIY = ( static_cast<double>(rVisiblePixelSize.Height()) * 2540.0 ) / static_cast<double>(rLogicalSize.Height); - const sal_Int32 nSourcePixelWidth( rGraphic.GetSizePixel().Width() ); - const sal_Int32 nSourcePixelHeight( rGraphic.GetSizePixel().Height() ); - const double fSourcePixelWidth = static_cast<double>( nSourcePixelWidth ); - const double fSourcePixelHeight= static_cast<double>( nSourcePixelHeight ); - - sal_Int32 nDestPixelWidth = nSourcePixelWidth; - sal_Int32 nDestPixelHeight = nSourcePixelHeight; - - // check, if the bitmap DPI exceeds the maximum DPI - if( fSourceDPIX > fImageResolution ) - { - nDestPixelWidth = static_cast<sal_Int32>(( fSourcePixelWidth * fImageResolution ) / fSourceDPIX); - if ( !nDestPixelWidth || ( nDestPixelWidth > nSourcePixelWidth ) ) - nDestPixelWidth = nSourcePixelWidth; - } - if ( fSourceDPIY > fImageResolution ) - { - nDestPixelHeight= static_cast<sal_Int32>(( fSourcePixelHeight* fImageResolution ) / fSourceDPIY); - if ( !nDestPixelHeight || ( nDestPixelHeight > nSourcePixelHeight ) ) - nDestPixelHeight = nSourcePixelHeight; - } - if ( ( nDestPixelWidth != nSourcePixelWidth ) || ( nDestPixelHeight != nSourcePixelHeight ) ) - ImplApplyBitmapScaling( rGraphic, nDestPixelWidth, nDestPixelHeight ); -} - -void ImplApplyFilterData( ::Graphic& rGraphic, uno::Sequence< beans::PropertyValue >& rFilterData ) -{ - /* this method applies following attributes to the graphic, in the first step the - cropping area (logical size in 100thmm) is applied, in the second step the resolution - is applied, in the third step the graphic is scaled to the corresponding pixelsize. - if a parameter value is zero or not available the corresponding step will be skipped */ - - sal_Int32 nPixelWidth = 0; - sal_Int32 nPixelHeight= 0; - sal_Int32 nImageResolution = 0; - awt::Size aLogicalSize( 0, 0 ); - text::GraphicCrop aCropLogic( 0, 0, 0, 0 ); - bool bRemoveCropArea = true; - - for( sal_Int32 i = 0; i < rFilterData.getLength(); ++i ) - { - const OUString aName( rFilterData[ i ].Name ); - const uno::Any aValue( rFilterData[ i ].Value ); - - if (aName == "PixelWidth") - aValue >>= nPixelWidth; - else if (aName == "PixelHeight") - aValue >>= nPixelHeight; - else if (aName == "LogicalSize") - aValue >>= aLogicalSize; - else if (aName == "GraphicCropLogic") - aValue >>= aCropLogic; - else if (aName == "RemoveCropArea") - aValue >>= bRemoveCropArea; - else if (aName == "ImageResolution") - aValue >>= nImageResolution; - } - if ( rGraphic.GetType() == GraphicType::Bitmap ) - { - if(rGraphic.getVectorGraphicData().get()) - { - // embedded Vector Graphic Data, no need to scale. Also no method to apply crop data currently - } - else - { - tools::Rectangle aCropPixel( Point( 0, 0 ), rGraphic.GetSizePixel() ); - ImplCalculateCropRect( rGraphic, aCropLogic, aCropPixel ); - if ( bRemoveCropArea ) - { - BitmapEx aBmpEx( rGraphic.GetBitmapEx() ); - aBmpEx.Crop( aCropPixel ); - rGraphic = aBmpEx; - } - Size aVisiblePixelSize( bRemoveCropArea ? rGraphic.GetSizePixel() : aCropPixel.GetSize() ); - ImplApplyBitmapResolution( rGraphic, nImageResolution, aVisiblePixelSize, aLogicalSize ); - ImplApplyBitmapScaling( rGraphic, nPixelWidth, nPixelHeight ); - } - } - else if ( ( rGraphic.GetType() == GraphicType::GdiMetafile ) && nImageResolution ) - { - ScopedVclPtrInstance< VirtualDevice > aDummyVDev; - GDIMetaFile aMtf( rGraphic.GetGDIMetaFile() ); - Size aMtfSize( OutputDevice::LogicToLogic(aMtf.GetPrefSize(), aMtf.GetPrefMapMode(), MapMode(MapUnit::Map100thMM)) ); - if ( aMtfSize.Width() && aMtfSize.Height() ) - { - MapMode aNewMapMode( MapUnit::Map100thMM ); - aNewMapMode.SetScaleX( Fraction( aLogicalSize.Width, aMtfSize.Width() ) ); - aNewMapMode.SetScaleY( Fraction( aLogicalSize.Height, aMtfSize.Height() ) ); - aDummyVDev->EnableOutput( false ); - aDummyVDev->SetMapMode( aNewMapMode ); - - for( size_t i = 0, nObjCount = aMtf.GetActionSize(); i < nObjCount; i++ ) - { - MetaAction* pAction = aMtf.GetAction( i ); - switch( pAction->GetType() ) - { - // only optimizing common bitmap actions: - case MetaActionType::MAPMODE: - { - pAction->Execute( aDummyVDev.get() ); - break; - } - case MetaActionType::PUSH: - { - const MetaPushAction* pA = static_cast<const MetaPushAction*>(pAction); - aDummyVDev->Push( pA->GetFlags() ); - break; - } - case MetaActionType::POP: - { - aDummyVDev->Pop(); - break; - } - case MetaActionType::BMPSCALE: - case MetaActionType::BMPEXSCALE: - { - BitmapEx aBmpEx; - Point aPos; - Size aSize; - if ( pAction->GetType() == MetaActionType::BMPSCALE ) - { - MetaBmpScaleAction* pScaleAction = dynamic_cast< MetaBmpScaleAction* >( pAction ); - aBmpEx = pScaleAction->GetBitmap(); - aPos = pScaleAction->GetPoint(); - aSize = pScaleAction->GetSize(); - } - else - { - MetaBmpExScaleAction* pScaleAction = dynamic_cast< MetaBmpExScaleAction* >( pAction ); - aBmpEx = pScaleAction->GetBitmapEx(); - aPos = pScaleAction->GetPoint(); - aSize = pScaleAction->GetSize(); - } - ::Graphic aGraphic( aBmpEx ); - const Size aSize100thmm( aDummyVDev->LogicToPixel( aSize ) ); - Size aSize100thmm2( aDummyVDev->PixelToLogic(aSize100thmm, MapMode(MapUnit::Map100thMM)) ); - - ImplApplyBitmapResolution( aGraphic, nImageResolution, - aGraphic.GetSizePixel(), awt::Size( aSize100thmm2.Width(), aSize100thmm2.Height() ) ); - - MetaAction* pNewAction; - if ( pAction->GetType() == MetaActionType::BMPSCALE ) - pNewAction = new MetaBmpScaleAction ( aPos, aSize, aGraphic.GetBitmap() ); - else - pNewAction = new MetaBmpExScaleAction( aPos, aSize, aGraphic.GetBitmapEx() ); - - MetaAction* pDeleteAction = aMtf.ReplaceAction( pNewAction, i ); - if(pDeleteAction) - pDeleteAction->Delete(); - break; - } - default: - case MetaActionType::BMP: - case MetaActionType::BMPSCALEPART: - case MetaActionType::BMPEX: - case MetaActionType::BMPEXSCALEPART: - case MetaActionType::MASK: - case MetaActionType::MASKSCALE: - break; - } - } - rGraphic = aMtf; - } - } -} - - -void SAL_CALL GraphicProvider::storeGraphic( const uno::Reference< ::graphic::XGraphic >& rxGraphic, const uno::Sequence< beans::PropertyValue >& rMediaProperties ) -{ - SolarMutexGuard g; - - std::unique_ptr<SvStream> pOStm; - OUString aPath; - sal_Int32 i; - - for( i = 0; ( i < rMediaProperties.getLength() ) && !pOStm; ++i ) - { - const OUString aName( rMediaProperties[ i ].Name ); - const uno::Any aValue( rMediaProperties[ i ].Value ); - - if (aName == "URL") - { - OUString aURL; - - aValue >>= aURL; - pOStm.reset(::utl::UcbStreamHelper::CreateStream( aURL, StreamMode::WRITE | StreamMode::TRUNC )); - aPath = aURL; - } - else if (aName == "OutputStream") - { - uno::Reference< io::XStream > xOStm; - - aValue >>= xOStm; - - if( xOStm.is() ) - pOStm.reset(::utl::UcbStreamHelper::CreateStream( xOStm )); - } - } - - if( !pOStm ) - return; - - uno::Sequence< beans::PropertyValue > aFilterDataSeq; - const char* pFilterShortName = nullptr; - - for( i = 0; i < rMediaProperties.getLength(); ++i ) - { - const OUString aName( rMediaProperties[ i ].Name ); - const uno::Any aValue( rMediaProperties[ i ].Value ); - - if (aName == "FilterData") - { - aValue >>= aFilterDataSeq; - } - else if (aName == "MimeType") - { - OUString aMimeType; - - aValue >>= aMimeType; - - if (aMimeType == MIMETYPE_BMP) - pFilterShortName = "bmp"; - else if (aMimeType == MIMETYPE_EPS) - pFilterShortName = "eps"; - else if (aMimeType == MIMETYPE_GIF) - pFilterShortName = "gif"; - else if (aMimeType == MIMETYPE_JPG) - pFilterShortName = "jpg"; - else if (aMimeType == MIMETYPE_MET) - pFilterShortName = "met"; - else if (aMimeType == MIMETYPE_PNG) - pFilterShortName = "png"; - else if (aMimeType == MIMETYPE_PCT) - pFilterShortName = "pct"; - else if (aMimeType == MIMETYPE_PBM) - pFilterShortName = "pbm"; - else if (aMimeType == MIMETYPE_PGM) - pFilterShortName = "pgm"; - else if (aMimeType == MIMETYPE_PPM) - pFilterShortName = "ppm"; - else if (aMimeType == MIMETYPE_RAS) - pFilterShortName = "ras"; - else if (aMimeType == MIMETYPE_SVM) - pFilterShortName = "svm"; - else if (aMimeType == MIMETYPE_TIF) - pFilterShortName = "tif"; - else if (aMimeType == MIMETYPE_EMF) - pFilterShortName = "emf"; - else if (aMimeType == MIMETYPE_WMF) - pFilterShortName = "wmf"; - else if (aMimeType == MIMETYPE_XPM) - pFilterShortName = "xpm"; - else if (aMimeType == MIMETYPE_SVG) - pFilterShortName = "svg"; - else if (aMimeType == MIMETYPE_VCLGRAPHIC) - pFilterShortName = MIMETYPE_VCLGRAPHIC; - } - } - - if( !pFilterShortName ) - return; - - ::GraphicFilter& rFilter = ::GraphicFilter::GetGraphicFilter(); - - { - const uno::Reference< XInterface > xIFace( rxGraphic, uno::UNO_QUERY ); - const ::Graphic* pGraphic = ::unographic::Graphic::getImplementation( xIFace ); - - if( pGraphic && ( pGraphic->GetType() != GraphicType::NONE ) ) - { - ::Graphic aGraphic( *pGraphic ); - ImplApplyFilterData( aGraphic, aFilterDataSeq ); - - /* sj: using a temporary memory stream, because some graphic filters are seeking behind - stream end (which leads to an invalid argument exception then). */ - SvMemoryStream aMemStrm; - aMemStrm.SetVersion( SOFFICE_FILEFORMAT_CURRENT ); - if( 0 == strcmp( pFilterShortName, MIMETYPE_VCLGRAPHIC ) ) - WriteGraphic( aMemStrm, aGraphic ); - else - { - rFilter.ExportGraphic( aGraphic, aPath, aMemStrm, - rFilter.GetExportFormatNumberForShortName( OUString::createFromAscii( pFilterShortName ) ), - ( aFilterDataSeq.getLength() ? &aFilterDataSeq : nullptr ) ); - } - aMemStrm.Seek( STREAM_SEEK_TO_END ); - pOStm->WriteBytes( aMemStrm.GetData(), aMemStrm.Tell() ); - } - } -} - -} - -extern "C" SAL_DLLPUBLIC_EXPORT css::uno::XInterface * -com_sun_star_comp_graphic_GraphicProvider_get_implementation( - css::uno::XComponentContext *, - css::uno::Sequence<css::uno::Any> const &) -{ - return cppu::acquire(new GraphicProvider); -} - -/* vim:set shiftwidth=4 softtabstop=4 expandtab: */ diff --git a/svtools/source/graphic/renderer.cxx b/svtools/source/graphic/renderer.cxx index 0c67524789b1..4280dbe6bf7e 100644 --- a/svtools/source/graphic/renderer.cxx +++ b/svtools/source/graphic/renderer.cxx @@ -34,9 +34,8 @@ #include <cppuhelper/supportsservice.hxx> #include <rtl/ref.hxx> #include <svl/itemprop.hxx> -#include <svtools/grfmgr.hxx> +#include <vcl/GraphicObject.hxx> #include <comphelper/servicehelper.hxx> -#include "graphic.hxx" #define UNOGRAPHIC_DEVICE 1 #define UNOGRAPHIC_DESTINATIONRECT 2 @@ -283,12 +282,10 @@ void SAL_CALL GraphicRendererVCL::render( const uno::Reference< graphic::XGraphi { if( mpOutDev && mxDevice.is() && rxGraphic.is() ) { - const uno::Reference< XInterface > xIFace( rxGraphic, uno::UNO_QUERY ); - const ::Graphic* pGraphic = ::unographic::Graphic::getImplementation( xIFace ); - - if( pGraphic ) + Graphic aGraphic(rxGraphic); + if (aGraphic) { - GraphicObject aGraphicObject( *pGraphic ); + GraphicObject aGraphicObject(aGraphic); aGraphicObject.Draw( mpOutDev, maDestRect.TopLeft(), maDestRect.GetSize() ); } } diff --git a/svtools/source/graphic/transformer.cxx b/svtools/source/graphic/transformer.cxx deleted file mode 100644 index 9c4121a5de31..000000000000 --- a/svtools/source/graphic/transformer.cxx +++ /dev/null @@ -1,152 +0,0 @@ -/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */ -/* - * This file is part of the LibreOffice project. - * - * This Source Code Form is subject to the terms of the Mozilla Public - * License, v. 2.0. If a copy of the MPL was not distributed with this - * file, You can obtain one at http://mozilla.org/MPL/2.0/. - * - * This file incorporates work covered by the following license notice: - * - * Licensed to the Apache Software Foundation (ASF) under one or more - * contributor license agreements. See the NOTICE file distributed - * with this work for additional information regarding copyright - * ownership. The ASF licenses this file to you under the Apache - * License, Version 2.0 (the "License"); you may not use this file - * except in compliance with the License. You may obtain a copy of - * the License at http://www.apache.org/licenses/LICENSE-2.0 . - */ - - -#include <vcl/svapp.hxx> -#include <vcl/image.hxx> -#include <vcl/metaact.hxx> -#include <unotools/ucbstreamhelper.hxx> -#include <svl/solar.hrc> -#include <vcl/salbtype.hxx> -#include <vcl/virdev.hxx> -#include <vcl/bitmapaccess.hxx> -#include <com/sun/star/text/GraphicCrop.hpp> - -#include "graphic.hxx" -#include "transformer.hxx" - -using namespace com::sun::star; - -namespace unographic { - - -GraphicTransformer::GraphicTransformer() -{ -} - - -GraphicTransformer::~GraphicTransformer() -{ -} - - -// XGraphicTransformer -uno::Reference< graphic::XGraphic > SAL_CALL GraphicTransformer::colorChange( - const uno::Reference< graphic::XGraphic >& rxGraphic, sal_Int32 nColorFrom, sal_Int8 nTolerance, sal_Int32 nColorTo, sal_Int8 nAlphaTo ) -{ - ::Graphic aGraphic(rxGraphic); - ::Graphic aReturnGraphic; - - BitmapColor aBmpColorFrom(static_cast< sal_uInt8 >(nColorFrom), static_cast< sal_uInt8 >(nColorFrom >> 8), static_cast< sal_uInt8 >(nColorFrom >> 16)); - BitmapColor aBmpColorTo( static_cast< sal_uInt8 >(nColorTo), static_cast< sal_uInt8 >(nColorTo >> 8), static_cast< sal_uInt8 >(nColorTo >> 16)); - - Color aColorFrom(aBmpColorFrom.GetColor()); - Color aColorTo(aBmpColorTo.GetColor()); - - const sal_uInt8 cIndexFrom = aBmpColorFrom.GetBlueOrIndex(); - - if (aGraphic.GetType() == GraphicType::Bitmap || - aGraphic.GetType() == GraphicType::GdiMetafile) - { - BitmapEx aBitmapEx(aGraphic.GetBitmapEx()); - Bitmap aBitmap(aBitmapEx.GetBitmap()); - - if (aBitmapEx.IsAlpha()) - { - aBitmapEx.setAlphaFrom( cIndexFrom, nAlphaTo ); - aBitmapEx.Replace(aColorFrom, aColorTo, nTolerance); - aReturnGraphic = ::Graphic(aBitmapEx); - } - else if (aBitmapEx.IsTransparent()) - { - if (nAlphaTo == sal::static_int_cast< sal_Int8 >(0xff)) - { - Bitmap aMask(aBitmapEx.GetMask()); - Bitmap aMask2(aBitmap.CreateMask(aColorFrom, nTolerance)); - aMask.CombineSimple(aMask2, BmpCombine::Or); - aBitmap.Replace(aColorFrom, aColorTo, nTolerance); - aReturnGraphic = ::Graphic(BitmapEx(aBitmap, aMask)); - } - else - { - aBitmapEx.setAlphaFrom(cIndexFrom, 0xff - nAlphaTo); - aBitmapEx.Replace(aColorFrom, aColorTo, nTolerance); - aReturnGraphic = ::Graphic(aBitmapEx); - } - } - else - { - if ((nAlphaTo == 0) || (nAlphaTo == sal::static_int_cast< sal_Int8 >(0xff))) - { - Bitmap aMask(aBitmap.CreateMask(aColorFrom, nTolerance)); - aBitmap.Replace(aColorFrom, aColorTo, nTolerance); - aReturnGraphic = ::Graphic(BitmapEx(aBitmap, aMask)); - } - else - { - aBitmapEx.setAlphaFrom(cIndexFrom, nAlphaTo); - aBitmapEx.Replace(aColorFrom, aColorTo, nTolerance); - aReturnGraphic = ::Graphic(aBitmapEx); - } - } - } - - aReturnGraphic.setOriginURL(aGraphic.getOriginURL()); - - unographic::Graphic* pUnoGraphic = new unographic::Graphic(); - pUnoGraphic->init(aReturnGraphic); - return uno::Reference<graphic::XGraphic>(pUnoGraphic); -} - -uno::Reference< graphic::XGraphic > SAL_CALL GraphicTransformer::applyDuotone( - const uno::Reference< graphic::XGraphic >& rxGraphic, sal_Int32 nColorOne, sal_Int32 nColorTwo ) -{ - ::Graphic aGraphic(rxGraphic); - ::Graphic aReturnGraphic; - - BitmapEx aBitmapEx( aGraphic.GetBitmapEx() ); - AlphaMask aMask( aBitmapEx.GetAlpha() ); - Bitmap aBitmap( aBitmapEx.GetBitmap() ); - BmpFilterParam aFilter( static_cast<sal_uLong>(nColorOne), static_cast<sal_uLong>(nColorTwo) ); - aBitmap.Filter( BmpFilter::DuoTone, &aFilter ); - aReturnGraphic = ::Graphic( BitmapEx( aBitmap, aMask ) ); - aReturnGraphic.setOriginURL(aGraphic.getOriginURL()); - ::unographic::Graphic* pUnoGraphic = new ::unographic::Graphic(); - pUnoGraphic->init(aReturnGraphic); - return uno::Reference<graphic::XGraphic>(pUnoGraphic); -} - -uno::Reference< graphic::XGraphic > SAL_CALL GraphicTransformer::applyBrightnessContrast( - const uno::Reference< graphic::XGraphic >& rxGraphic, sal_Int32 nBrightness, sal_Int32 nContrast, sal_Bool mso ) -{ - ::Graphic aGraphic(rxGraphic); - ::Graphic aReturnGraphic; - - BitmapEx aBitmapEx(aGraphic.GetBitmapEx()); - aBitmapEx.Adjust(nBrightness, nContrast, 0, 0, 0, 0, false, mso); - aReturnGraphic = ::Graphic(aBitmapEx); - aReturnGraphic.setOriginURL(aGraphic.getOriginURL()); - ::unographic::Graphic* pUnoGraphic = new ::unographic::Graphic(); - pUnoGraphic->init(aReturnGraphic); - return uno::Reference<graphic::XGraphic>(pUnoGraphic); -} - -} - -/* vim:set shiftwidth=4 softtabstop=4 expandtab: */ diff --git a/svtools/source/graphic/transformer.hxx b/svtools/source/graphic/transformer.hxx deleted file mode 100644 index bb93a5aeef4e..000000000000 --- a/svtools/source/graphic/transformer.hxx +++ /dev/null @@ -1,59 +0,0 @@ -/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */ -/* - * This file is part of the LibreOffice project. - * - * This Source Code Form is subject to the terms of the Mozilla Public - * License, v. 2.0. If a copy of the MPL was not distributed with this - * file, You can obtain one at http://mozilla.org/MPL/2.0/. - * - * This file incorporates work covered by the following license notice: - * - * Licensed to the Apache Software Foundation (ASF) under one or more - * contributor license agreements. See the NOTICE file distributed - * with this work for additional information regarding copyright - * ownership. The ASF licenses this file to you under the Apache - * License, Version 2.0 (the "License"); you may not use this file - * except in compliance with the License. You may obtain a copy of - * the License at http://www.apache.org/licenses/LICENSE-2.0 . - */ - -#ifndef INCLUDED_SVTOOLS_SOURCE_GRAPHIC_TRANSFORMER_HXX -#define INCLUDED_SVTOOLS_SOURCE_GRAPHIC_TRANSFORMER_HXX - -#include <cppuhelper/implbase1.hxx> -#include <com/sun/star/lang/XServiceInfo.hpp> -#include <com/sun/star/graphic/XGraphicTransformer.hpp> - -namespace unographic { - - -typedef ::cppu::WeakAggImplHelper1< - css::graphic::XGraphicTransformer - > GraphicTransformer_UnoImplHelper1; -class GraphicTransformer : public GraphicTransformer_UnoImplHelper1 -{ - public: - - GraphicTransformer(); - virtual ~GraphicTransformer() override; - - // XGraphicTransformer - virtual css::uno::Reference< css::graphic::XGraphic > SAL_CALL colorChange( - const css::uno::Reference< css::graphic::XGraphic >& rGraphic, - sal_Int32 nColorFrom, sal_Int8 nTolerance, sal_Int32 nColorTo, sal_Int8 nAlphaTo ) override; - - virtual css::uno::Reference< css::graphic::XGraphic > SAL_CALL applyDuotone( - const css::uno::Reference< css::graphic::XGraphic >& rGraphic, - sal_Int32 nColorOne, sal_Int32 nColorTwo ) override; - - virtual css::uno::Reference< css::graphic::XGraphic > SAL_CALL applyBrightnessContrast( - const css::uno::Reference< css::graphic::XGraphic >& rxGraphic, - sal_Int32 nBrightness, sal_Int32 nContrast, sal_Bool mso ) override; - -}; - -} - -#endif - -/* vim:set shiftwidth=4 softtabstop=4 expandtab: */ diff --git a/svtools/util/svt.component b/svtools/util/svt.component index f48425fcad47..f840548d9d3e 100644 --- a/svtools/util/svt.component +++ b/svtools/util/svt.component @@ -19,10 +19,6 @@ <component loader="com.sun.star.loader.SharedLibrary" environment="@CPPU_ENV@" prefix="svt" xmlns="http://openoffice.org/2010/uno-components"> - <implementation name="com.sun.star.comp.graphic.GraphicProvider" - constructor="com_sun_star_comp_graphic_GraphicProvider_get_implementation"> - <service name="com.sun.star.graphic.GraphicProvider"/> - </implementation> <implementation name="com.sun.star.comp.graphic.GraphicRendererVCL" constructor="com_sun_star_comp_graphic_GraphicRendererVCL_get_implementation"> <service name="com.sun.star.graphic.GraphicRendererVCL"/> @@ -35,10 +31,6 @@ constructor="com_sun_star_comp_svtools_uno_Wizard_get_implementation"> <service name="com.sun.star.ui.dialogs.Wizard"/> </implementation> - <implementation name="com.sun.star.graphic.GraphicObject" - constructor="com_sun_star_graphic_GraphicObject_get_implementation"> - <service name="com.sun.star.graphic.GraphicObject"/> - </implementation> <implementation name="com.sun.star.svtools.SvFilterOptionsDialog" constructor="com_sun_star_svtools_SvFilterOptionsDialog_get_implementation"> <service name="com.sun.star.ui.dialogs.FilterOptionsDialog"/> |