/* -*- 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 <boost/property_tree/json_parser.hpp>
#include <com/sun/star/presentation/XPresentation2.hpp>
#include <com/sun/star/lang/DisposedException.hpp>
#include <com/sun/star/lang/IndexOutOfBoundsException.hpp>
#include <com/sun/star/lang/ServiceNotRegisteredException.hpp>
#include <com/sun/star/lang/Locale.hpp>
#include <com/sun/star/style/XStyle.hpp>
#include <com/sun/star/awt/XDevice.hpp>
#include <com/sun/star/document/IndexedPropertyValues.hpp>
#include <com/sun/star/embed/Aspects.hpp>
#include <comphelper/lok.hxx>
#include <comphelper/sequence.hxx>
#include <comphelper/servicehelper.hxx>
#include <cppuhelper/supportsservice.hxx>
#include <comphelper/processfactory.hxx>
#include <comphelper/profilezone.hxx>
#include <sal/log.hxx>
#include <editeng/unofield.hxx>
#include <notifydocumentevent.hxx>
#include <unomodel.hxx>
#include "unopool.hxx"
#include <sfx2/dispatch.hxx>
#include <sfx2/bindings.hxx>
#include <vcl/commandevent.hxx>
#include <vcl/svapp.hxx>
#include <vcl/settings.hxx>
#include <LibreOfficeKit/LibreOfficeKitEnums.h>
#include <editeng/UnoForbiddenCharsTable.hxx>
#include <svx/svdoutl.hxx>
#include <editeng/forbiddencharacterstable.hxx>
#include <o3tl/safeint.hxx>
#include <svx/UnoNamespaceMap.hxx>
#include <svx/svdlayer.hxx>
#include <svx/svdsob.hxx>
#include <svx/svdundo.hxx>
#include <svx/unoapi.hxx>
#include <svx/unofill.hxx>
#include <svx/unopool.hxx>
#include <svx/svdorect.hxx>
#include <editeng/flditem.hxx>
#include <editeng/fontitem.hxx>
#include <toolkit/awt/vclxdevice.hxx>
#include <svx/svdpool.hxx>
#include <editeng/unolingu.hxx>
#include <svx/svdpagv.hxx>
#include <svtools/unoimap.hxx>
#include <svx/unoshape.hxx>
#include <editeng/unonrule.hxx>
#include <editeng/eeitem.hxx>
#include <unotools/datetime.hxx>
#include <unotools/saveopt.hxx>
#include <xmloff/autolayout.hxx>
// Support creation of GraphicStorageHandler and EmbeddedObjectResolver
#include <svx/xmleohlp.hxx>
#include <svx/xmlgrhlp.hxx>
#include <DrawDocShell.hxx>
#include <ViewShellBase.hxx>
#include "UnoDocumentSettings.hxx"
#include <Annotation.hxx>
#include <drawdoc.hxx>
#include <sdmod.hxx>
#include <sdresid.hxx>
#include <sdpage.hxx>
#include <strings.hrc>
#include <strings.hxx>
#include "unolayer.hxx"
#include <unoprnms.hxx>
#include <unopage.hxx>
#include "unocpres.hxx"
#include "unoobj.hxx"
#include <stlpool.hxx>
#include "unopback.hxx"
#include <unokywds.hxx>
#include <FrameView.hxx>
#include <ClientView.hxx>
#include <DrawViewShell.hxx>
#include <ViewShell.hxx>
#include <Window.hxx>
#include <app.hrc>
#include <optsitem.hxx>
#include <vcl/pdfextoutdevdata.hxx>
#include <com/sun/star/presentation/AnimationSpeed.hpp>
#include <com/sun/star/presentation/ClickAction.hpp>
#include <svx/sdr/contact/viewobjectcontact.hxx>
#include <svx/sdr/contact/viewcontact.hxx>
#include <svx/sdr/contact/displayinfo.hxx>
#include <com/sun/star/office/XAnnotation.hpp>
#include <com/sun/star/office/XAnnotationAccess.hpp>
#include <com/sun/star/office/XAnnotationEnumeration.hpp>
#include <com/sun/star/geometry/RealPoint2D.hpp>
#include <com/sun/star/util/DateTime.hpp>
#include <drawinglayer/primitive2d/structuretagprimitive2d.hxx>
#include <sfx2/lokcharthelper.hxx>
#define TWIPS_PER_PIXEL 15
using namespace ::cppu;
using namespace ::com::sun::star;
using namespace ::sd;
class SdUnoForbiddenCharsTable : public SvxUnoForbiddenCharsTable,
public SfxListener
{
public:
explicit SdUnoForbiddenCharsTable(SdrModel* pModel);
virtual ~SdUnoForbiddenCharsTable() override;
// SfxListener
virtual void Notify( SfxBroadcaster& rBC, const SfxHint& rHint ) throw () override;
protected:
virtual void onChange() override;
private:
SdrModel* mpModel;
};
SdUnoForbiddenCharsTable::SdUnoForbiddenCharsTable( SdrModel* pModel )
: SvxUnoForbiddenCharsTable( pModel->GetForbiddenCharsTable() ), mpModel( pModel )
{
StartListening( *pModel );
}
void SdUnoForbiddenCharsTable::onChange()
{
if( mpModel )
{
mpModel->ReformatAllTextObjects();
}
}
SdUnoForbiddenCharsTable::~SdUnoForbiddenCharsTable()
{
SolarMutexGuard g;
if( mpModel )
EndListening( *mpModel );
}
void SdUnoForbiddenCharsTable::Notify( SfxBroadcaster&, const SfxHint& rHint ) throw()
{
const SdrHint* pSdrHint = dynamic_cast<const SdrHint*>( &rHint );
if( pSdrHint )
{
if( SdrHintKind::ModelCleared == pSdrHint->GetKind() )
{
mpModel = nullptr;
}
}
}
const sal_uInt16 WID_MODEL_LANGUAGE = 1;
const sal_uInt16 WID_MODEL_TABSTOP = 2;
const sal_uInt16 WID_MODEL_VISAREA = 3;
const sal_uInt16 WID_MODEL_MAPUNIT = 4;
const sal_uInt16 WID_MODEL_FORBCHARS = 5;
const sal_uInt16 WID_MODEL_CONTFOCUS = 6;
const sal_uInt16 WID_MODEL_DSGNMODE = 7;
const sal_uInt16 WID_MODEL_BASICLIBS = 8;
const sal_uInt16 WID_MODEL_RUNTIMEUID = 9;
const sal_uInt16 WID_MODEL_BUILDID = 10;
const sal_uInt16 WID_MODEL_HASVALIDSIGNATURES = 11;
const sal_uInt16 WID_MODEL_DIALOGLIBS = 12;
const sal_uInt16 WID_MODEL_FONTS = 13;
const sal_uInt16 WID_MODEL_INTEROPGRABBAG = 14;
const SvxItemPropertySet* ImplGetDrawModelPropertySet()
{
// Attention: the first parameter HAS TO BE sorted!!!
const static SfxItemPropertyMapEntry aDrawModelPropertyMap_Impl[] =
{
{ OUString("BuildId"), WID_MODEL_BUILDID, ::cppu::UnoType<OUString>::get(), 0, 0},
{ OUString(sUNO_Prop_CharLocale), WID_MODEL_LANGUAGE, ::cppu::UnoType<lang::Locale>::get(), 0, 0},
{ OUString(sUNO_Prop_TabStop), WID_MODEL_TABSTOP, ::cppu::UnoType<sal_Int32>::get(), 0, 0},
{ OUString(sUNO_Prop_VisibleArea), WID_MODEL_VISAREA, ::cppu::UnoType<awt::Rectangle>::get(), 0, 0},
{ OUString(sUNO_Prop_MapUnit), WID_MODEL_MAPUNIT, ::cppu::UnoType<sal_Int16>::get(), beans::PropertyAttribute::READONLY, 0},
{ OUString(sUNO_Prop_ForbiddenCharacters), WID_MODEL_FORBCHARS, cppu::UnoType<i18n::XForbiddenCharacters>::get(), beans::PropertyAttribute::READONLY, 0},
{ OUString(sUNO_Prop_AutomContFocus), WID_MODEL_CONTFOCUS, cppu::UnoType<bool>::get(), 0, 0},
{ OUString(sUNO_Prop_ApplyFrmDsgnMode), WID_MODEL_DSGNMODE, cppu::UnoType<bool>::get(), 0, 0},
{ OUString("BasicLibraries"), WID_MODEL_BASICLIBS, cppu::UnoType<script::XLibraryContainer>::get(), beans::PropertyAttribute::READONLY, 0},
{ OUString("DialogLibraries"), WID_MODEL_DIALOGLIBS, cppu::UnoType<script::XLibraryContainer>::get(), beans::PropertyAttribute::READONLY, 0},
{ OUString(sUNO_Prop_RuntimeUID), WID_MODEL_RUNTIMEUID, ::cppu::UnoType<OUString>::get(), beans::PropertyAttribute::READONLY, 0},
{ OUString(sUNO_Prop_HasValidSignatures), WID_MODEL_HASVALIDSIGNATURES, ::cppu::UnoType<sal_Bool>::get(), beans::PropertyAttribute::READONLY, 0},
{ OUString("Fonts"), WID_MODEL_FONTS, cppu::UnoType<uno::Sequence<uno::Any>>::get(), beans::PropertyAttribute::READONLY, 0},
{ OUString(sUNO_Prop_InteropGrabBag), WID_MODEL_INTEROPGRABBAG, cppu::UnoType<uno::Sequence< beans::PropertyValue >>::get(), 0, 0},
{ OUString(), 0, css::uno::Type(), 0, 0 }
};
static SvxItemPropertySet aDrawModelPropertySet_Impl( aDrawModelPropertyMap_Impl, SdrObject::GetGlobalDrawObjectItemPool() );
return &aDrawModelPropertySet_Impl;
}
// this ctor is used from the DocShell
SdXImpressDocument::SdXImpressDocument(::sd::DrawDocShell* pShell, bool bClipBoard)
: SfxBaseModel( pShell ),
mpDocShell( pShell ),
mpDoc( pShell ? pShell->GetDoc() : nullptr ),
mbDisposed(false),
mbImpressDoc( pShell && pShell->GetDoc() && pShell->GetDoc()->GetDocumentType() == DocumentType::Impress ),
mbClipBoard( bClipBoard ),
mpPropSet( ImplGetDrawModelPropertySet() )
{
if( mpDoc )
{
StartListening( *mpDoc );
}
else
{
OSL_FAIL("DocShell is invalid");
}
}
SdXImpressDocument::SdXImpressDocument(SdDrawDocument* pDoc, bool bClipBoard)
: SfxBaseModel( nullptr ),
mpDocShell( nullptr ),
mpDoc( pDoc ),
mbDisposed(false),
mbImpressDoc( pDoc && pDoc->GetDocumentType() == DocumentType::Impress ),
mbClipBoard( bClipBoard ),
mpPropSet( ImplGetDrawModelPropertySet() )
{
if( mpDoc )
{
StartListening( *mpDoc );
}
else
{
OSL_FAIL("SdDrawDocument is invalid");
}
}
/***********************************************************************
* *
***********************************************************************/
SdXImpressDocument::~SdXImpressDocument() throw()
{
}
// XInterface
uno::Any SAL_CALL SdXImpressDocument::queryInterface( 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<beans::XPropertySet>::get())
aAny <<= uno::Reference<beans::XPropertySet>(this);
else if (rType == cppu::UnoType<lang::XMultiServiceFactory>::get())
aAny <<= uno::Reference<lang::XMultiServiceFactory>(this);
else if (rType == cppu::UnoType<drawing::XDrawPageDuplicator>::get())
aAny <<= uno::Reference<drawing::XDrawPageDuplicator>(this);
else if (rType == cppu::UnoType<drawing::XLayerSupplier>::get())
aAny <<= uno::Reference<drawing::XLayerSupplier>(this);
else if (rType == cppu::UnoType<drawing::XMasterPagesSupplier>::get())
aAny <<= uno::Reference<drawing::XMasterPagesSupplier>(this);
else if (rType == cppu::UnoType<drawing::XDrawPagesSupplier>::get())
aAny <<= uno::Reference<drawing::XDrawPagesSupplier>(this);
else if (rType == cppu::UnoType<presentation::XHandoutMasterSupplier>::get())
aAny <<= uno::Reference<presentation::XHandoutMasterSupplier>(this);
else if (rType == cppu::UnoType<document::XLinkTargetSupplier>::get())
aAny <<= uno::Reference<document::XLinkTargetSupplier>(this);
else if (rType == cppu::UnoType<style::XStyleFamiliesSupplier>::get())
aAny <<= uno::Reference<style::XStyleFamiliesSupplier>(this);
else if (rType == cppu::UnoType<css::ucb::XAnyCompareFactory>::get())
aAny <<= uno::Reference<css::ucb::XAnyCompareFactory>(this);
else if (rType == cppu::UnoType<view::XRenderable>::get())
aAny <<= uno::Reference<view::XRenderable>(this);
else if (mbImpressDoc && rType == cppu::UnoType<presentation::XPresentationSupplier>::get())
aAny <<= uno::Reference< presentation::XPresentationSupplier >(this);
else if (mbImpressDoc && rType == cppu::UnoType<presentation::XCustomPresentationSupplier>::get())
aAny <<= uno::Reference< presentation::XCustomPresentationSupplier >(this);
else
return SfxBaseModel::queryInterface(rType);
return aAny;
}
void SAL_CALL SdXImpressDocument::acquire() throw ( )
{
SfxBaseModel::acquire();
}
void SAL_CALL SdXImpressDocument::release() throw ( )
{
if (osl_atomic_decrement( &m_refCount ) == 0)
{
// restore reference count:
osl_atomic_increment( &m_refCount );
if(!mbDisposed)
{
try
{
dispose();
}
catch (const uno::RuntimeException& exc)
{ // don't break throw ()
SAL_WARN( "sd", exc );
}
}
SfxBaseModel::release();
}
}
namespace
{
class theSdXImpressDocumentUnoTunnelId : public rtl::Static< UnoTunnelIdInit, theSdXImpressDocumentUnoTunnelId> {};
}
// XUnoTunnel
const css::uno::Sequence< sal_Int8 > & SdXImpressDocument::getUnoTunnelId() throw()
{
return theSdXImpressDocumentUnoTunnelId::get().getSeq();
}
SdXImpressDocument* SdXImpressDocument::getImplementation( const uno::Reference< uno::XInterface >& xInt )
{
css::uno::Reference< css::lang::XUnoTunnel > xUT( xInt, uno::UNO_QUERY );
if( xUT.is() )
return reinterpret_cast<SdXImpressDocument*>(sal::static_int_cast<sal_IntPtr>(xUT->getSomething( SdXImpressDocument::getUnoTunnelId() )));
else
return nullptr;
}
sal_Int64 SAL_CALL SdXImpressDocument::getSomething( const css::uno::Sequence< sal_Int8 >& rIdentifier )
{
if( rIdentifier.getLength() == 16 )
{
if( 0 == memcmp( SdXImpressDocument::getUnoTunnelId().getConstArray(), rIdentifier.getConstArray(), 16 ) )
return sal::static_int_cast<sal_Int64>(reinterpret_cast<sal_IntPtr>(this));
if( 0 == memcmp( SdrModel::getUnoTunnelImplementationId().getConstArray(), rIdentifier.getConstArray(), 16 ) )
return sal::static_int_cast<sal_Int64>(reinterpret_cast<sal_IntPtr>(mpDoc));
}
return SfxBaseModel::getSomething( rIdentifier );
}
// XTypeProvider
uno::Sequence< uno::Type > SAL_CALL SdXImpressDocument::getTypes( )
{
::SolarMutexGuard aGuard;
if( maTypeSequence.getLength() == 0 )
{
const uno::Sequence< uno::Type > aBaseTypes( SfxBaseModel::getTypes() );
const sal_Int32 nBaseTypes = aBaseTypes.getLength();
const uno::Type* pBaseTypes = aBaseTypes.getConstArray();
const sal_Int32 nOwnTypes = mbImpressDoc ? 14 : 11; // !DANGER! Keep this updated!
maTypeSequence.realloc( nBaseTypes + nOwnTypes );
uno::Type* pTypes = maTypeSequence.getArray();
*pTypes++ = cppu::UnoType<beans::XPropertySet>::get();
*pTypes++ = cppu::UnoType<lang::XServiceInfo>::get();
*pTypes++ = cppu::UnoType<lang::XMultiServiceFactory>::get();
*pTypes++ = cppu::UnoType<drawing::XDrawPageDuplicator>::get();
*pTypes++ = cppu::UnoType<drawing::XLayerSupplier>::get();
*pTypes++ = cppu::UnoType<drawing::XMasterPagesSupplier>::get();
*pTypes++ = cppu::UnoType<drawing::XDrawPagesSupplier>::get();
*pTypes++ = cppu::UnoType<document::XLinkTargetSupplier>::get();
*pTypes++ = cppu::UnoType<style::XStyleFamiliesSupplier>::get();
*pTypes++ = cppu::UnoType<css::ucb::XAnyCompareFactory>::get();
*pTypes++ = cppu::UnoType<view::XRenderable>::get();
if( mbImpressDoc )
{
*pTypes++ = cppu::UnoType<presentation::XPresentationSupplier>::get();
*pTypes++ = cppu::UnoType<presentation::XCustomPresentationSupplier>::get();
*pTypes++ = cppu::UnoType<presentation::XHandoutMasterSupplier>::get();
}
for( sal_Int32 nType = 0; nType < nBaseTypes; nType++ )
*pTypes++ = *pBaseTypes++;
}
return maTypeSequence;
}
uno::Sequence< sal_Int8 > SAL_CALL SdXImpressDocument::getImplementationId( )
{
return css::uno::Sequence<sal_Int8>();
}
/***********************************************************************
* *
***********************************************************************/
void SdXImpressDocument::Notify( SfxBroadcaster& rBC, const SfxHint& rHint )
{
if( mpDoc )
{
const SdrHint* pSdrHint = dynamic_cast<const SdrHint*>( &rHint );
if( pSdrHint )
{
if( hasEventListeners() )
{
document::EventObject aEvent;
if( SvxUnoDrawMSFactory::createEvent( mpDoc, pSdrHint, aEvent ) )
notifyEvent( aEvent );
}
if( pSdrHint->GetKind() == SdrHintKind::ModelCleared )
{
if( mpDoc )
EndListening( *mpDoc );
mpDoc = nullptr;
mpDocShell = nullptr;
}
}
else
{
// did our SdDrawDocument just died?
if(rHint.GetId() == SfxHintId::Dying)
{
// yes, so we ask for a new one
if( mpDocShell )
{
SdDrawDocument *pNewDoc = mpDocShell->GetDoc();
// is there a new one?
if( pNewDoc != mpDoc )
{
mpDoc = pNewDoc;
if(mpDoc)
StartListening( *mpDoc );
}
}
}
}
}
SfxBaseModel::Notify( rBC, rHint );
}
/******************************************************************************
* *
******************************************************************************/
SdPage* SdXImpressDocument::InsertSdPage( sal_uInt16 nPage, bool bDuplicate )
{
sal_uInt16 nPageCount = mpDoc->GetSdPageCount( PageKind::Standard );
SdrLayerAdmin& rLayerAdmin = mpDoc->GetLayerAdmin();
SdrLayerID aBckgrnd = rLayerAdmin.GetLayerID(SdResId(STR_LAYER_BCKGRND));
SdrLayerID aBckgrndObj = rLayerAdmin.GetLayerID(SdResId(STR_LAYER_BCKGRNDOBJ));
SdPage* pStandardPage = nullptr;
if( 0 == nPageCount )
{
// this is only used for clipboard where we only have one page
pStandardPage = mpDoc->AllocSdPage(false);
Size aDefSize(21000, 29700); // A4-Hochformat
pStandardPage->SetSize( aDefSize );
mpDoc->InsertPage(pStandardPage, 0);
}
else
{
// here we determine the page after which we should insert
SdPage* pPreviousStandardPage = mpDoc->GetSdPage( std::min( static_cast<sal_uInt16>(nPageCount - 1), nPage ), PageKind::Standard );
SdrLayerIDSet aVisibleLayers = pPreviousStandardPage->TRG_GetMasterPageVisibleLayers();
bool bIsPageBack = aVisibleLayers.IsSet( aBckgrnd );
bool bIsPageObj = aVisibleLayers.IsSet( aBckgrndObj );
// AutoLayouts must be ready
mpDoc->StopWorkStartupDelay();
/* First we create a standard page and then a notes page. It is
guaranteed, that after a standard page the corresponding notes page
follows. */
sal_uInt16 nStandardPageNum = pPreviousStandardPage->GetPageNum() + 2;
SdPage* pPreviousNotesPage = static_cast<SdPage*>( mpDoc->GetPage( nStandardPageNum - 1 ) );
sal_uInt16 nNotesPageNum = nStandardPageNum + 1;
/**************************************************************
* standard page
**************************************************************/
if( bDuplicate )
pStandardPage = static_cast<SdPage*>( pPreviousStandardPage->CloneSdrPage(*mpDoc) );
else
pStandardPage = mpDoc->AllocSdPage(false);
pStandardPage->SetSize( pPreviousStandardPage->GetSize() );
pStandardPage->SetBorder( pPreviousStandardPage->GetLeftBorder(),
pPreviousStandardPage->GetUpperBorder(),
pPreviousStandardPage->GetRightBorder(),
pPreviousStandardPage->GetLowerBorder() );
pStandardPage->SetOrientation( pPreviousStandardPage->GetOrientation() );
pStandardPage->SetName(OUString());
// insert page after current page
mpDoc->InsertPage(pStandardPage, nStandardPageNum);
if( !bDuplicate )
{
// use MasterPage of the current page
pStandardPage->TRG_SetMasterPage(pPreviousStandardPage->TRG_GetMasterPage());
pStandardPage->SetLayoutName( pPreviousStandardPage->GetLayoutName() );
pStandardPage->SetAutoLayout(AUTOLAYOUT_NONE, true );
}
aBckgrnd = rLayerAdmin.GetLayerID(SdResId(STR_LAYER_BCKGRND));
aBckgrndObj = rLayerAdmin.GetLayerID(SdResId(STR_LAYER_BCKGRNDOBJ));
aVisibleLayers.Set(aBckgrnd, bIsPageBack);
aVisibleLayers.Set(aBckgrndObj, bIsPageObj);
pStandardPage->TRG_SetMasterPageVisibleLayers(aVisibleLayers);
/**************************************************************
* notes page
**************************************************************/
SdPage* pNotesPage = nullptr;
if( bDuplicate )
pNotesPage = static_cast<SdPage*>( pPreviousNotesPage->CloneSdrPage(*mpDoc) );
else
pNotesPage = mpDoc->AllocSdPage(false);
pNotesPage->SetSize( pPreviousNotesPage->GetSize() );
pNotesPage->SetBorder( pPreviousNotesPage->GetLeftBorder(),
pPreviousNotesPage->GetUpperBorder(),
pPreviousNotesPage->GetRightBorder(),
pPreviousNotesPage->GetLowerBorder() );
pNotesPage->SetOrientation( pPreviousNotesPage->GetOrientation() );
pNotesPage->SetName(OUString());
pNotesPage->SetPageKind(PageKind::Notes);
// insert page after current page
mpDoc->InsertPage(pNotesPage, nNotesPageNum);
if( !bDuplicate )
{
// use MasterPage of the current page
pNotesPage->TRG_SetMasterPage(pPreviousNotesPage->TRG_GetMasterPage());
pNotesPage->SetLayoutName( pPreviousNotesPage->GetLayoutName() );
pNotesPage->SetAutoLayout(AUTOLAYOUT_NOTES, true );
}
}
SetModified();
return pStandardPage;
}
void SdXImpressDocument::SetModified() throw()
{
if( mpDoc )
mpDoc->SetChanged();
}
// XModel
void SAL_CALL SdXImpressDocument::lockControllers( )
{
::SolarMutexGuard aGuard;
if( nullptr == mpDoc )
throw lang::DisposedException();
mpDoc->setLock(true);
}
void SAL_CALL SdXImpressDocument::unlockControllers( )
{
::SolarMutexGuard aGuard;
if( nullptr == mpDoc )
throw lang::DisposedException();
if( mpDoc->isLocked() )
{
mpDoc->setLock(false);
}
}
sal_Bool SAL_CALL SdXImpressDocument::hasControllersLocked( )
{
::SolarMutexGuard aGuard;
if( nullptr == mpDoc )
throw lang::DisposedException();
return mpDoc && mpDoc->isLocked();
}
uno::Reference < container::XIndexAccess > SAL_CALL SdXImpressDocument::getViewData()
{
::SolarMutexGuard aGuard;
if( nullptr == mpDoc )
throw lang::DisposedException();
uno::Reference < container::XIndexAccess > xRet( SfxBaseModel::getViewData() );
if( !xRet.is() )
{
const std::vector<std::unique_ptr<sd::FrameView>> &rList = mpDoc->GetFrameViewList();
if( !rList.empty() )
{
xRet.set(document::IndexedPropertyValues::create( ::comphelper::getProcessComponentContext() ), uno::UNO_QUERY);
uno::Reference < container::XIndexContainer > xCont( xRet, uno::UNO_QUERY );
DBG_ASSERT( xCont.is(), "SdXImpressDocument::getViewData() failed for OLE object" );
if( xCont.is() )
{
for( sal_uInt32 i = 0, n = rList.size(); i < n; i++ )
{
::sd::FrameView* pFrameView = rList[ i ].get();
uno::Sequence< beans::PropertyValue > aSeq;
pFrameView->WriteUserDataSequence( aSeq );
xCont->insertByIndex( i, uno::makeAny( aSeq ) );
}
}
}
}
return xRet;
}
void SAL_CALL SdXImpressDocument::setViewData( const uno::Reference < container::XIndexAccess >& xData )
{
::SolarMutexGuard aGuard;
if( nullptr == mpDoc )
throw lang::DisposedException();
SfxBaseModel::setViewData( xData );
if( mpDocShell && (mpDocShell->GetCreateMode() == SfxObjectCreateMode::EMBEDDED) && xData.is() )
{
const sal_Int32 nCount = xData->getCount();
std::vector<std::unique_ptr<sd::FrameView>> &rViews = mpDoc->GetFrameViewList();
rViews.clear();
uno::Sequence< beans::PropertyValue > aSeq;
for( sal_Int32 nIndex = 0; nIndex < nCount; nIndex++ )
{
if( xData->getByIndex( nIndex ) >>= aSeq )
{
std::unique_ptr<::sd::FrameView> pFrameView(new ::sd::FrameView( mpDoc ));
pFrameView->ReadUserDataSequence( aSeq );
rViews.push_back( std::move(pFrameView) );
}
}
}
}
// XDrawPageDuplicator
uno::Reference< drawing::XDrawPage > SAL_CALL SdXImpressDocument::duplicate( const uno::Reference< drawing::XDrawPage >& xPage )
{
::SolarMutexGuard aGuard;
if( nullptr == mpDoc )
throw lang::DisposedException();
// get pPage from xPage and determine the Id (nPos ) afterwards
SvxDrawPage* pSvxPage = SvxDrawPage::getImplementation( xPage );
if( pSvxPage )
{
SdPage* pPage = static_cast<SdPage*>( pSvxPage->GetSdrPage() );
sal_uInt16 nPos = pPage->GetPageNum();
nPos = ( nPos - 1 ) / 2;
pPage = InsertSdPage( nPos, true );
if( pPage )
{
uno::Reference< drawing::XDrawPage > xDrawPage( pPage->getUnoPage(), uno::UNO_QUERY );
return xDrawPage;
}
}
uno::Reference< drawing::XDrawPage > xDrawPage;
return xDrawPage;
}
// XDrawPagesSupplier
uno::Reference< drawing::XDrawPages > SAL_CALL SdXImpressDocument::getDrawPages()
{
::SolarMutexGuard aGuard;
if( nullptr == mpDoc )
throw lang::DisposedException();
uno::Reference< drawing::XDrawPages > xDrawPages( mxDrawPagesAccess );
if( !xDrawPages.is() )
{
initializeDocument();
mxDrawPagesAccess = xDrawPages = static_cast<drawing::XDrawPages*>(new SdDrawPagesAccess(*this));
}
return xDrawPages;
}
// XMasterPagesSupplier
uno::Reference< drawing::XDrawPages > SAL_CALL SdXImpressDocument::getMasterPages()
{
::SolarMutexGuard aGuard;
if( nullptr == mpDoc )
throw lang::DisposedException();
uno::Reference< drawing::XDrawPages > xMasterPages( mxMasterPagesAccess );
if( !xMasterPages.is() )
{
if ( !hasControllersLocked() )
initializeDocument();
mxMasterPagesAccess = xMasterPages = new SdMasterPagesAccess(*this);
}
return xMasterPages;
}
// XLayerManagerSupplier
uno::Reference< container::XNameAccess > SAL_CALL SdXImpressDocument::getLayerManager( )
{
::SolarMutexGuard aGuard;
if( nullptr == mpDoc )
throw lang::DisposedException();
uno::Reference< container::XNameAccess > xLayerManager( mxLayerManager );
if( !xLayerManager.is() )
mxLayerManager = xLayerManager = new SdLayerManager(*this);
return xLayerManager;
}
// XCustomPresentationSupplier
uno::Reference< container::XNameContainer > SAL_CALL SdXImpressDocument::getCustomPresentations()
{
::SolarMutexGuard aGuard;
if( nullptr == mpDoc )
throw lang::DisposedException();
uno::Reference< container::XNameContainer > xCustomPres( mxCustomPresentationAccess );
if( !xCustomPres.is() )
mxCustomPresentationAccess = xCustomPres = new SdXCustomPresentationAccess(*this);
return xCustomPres;
}
// XPresentationSupplier
uno::Reference< presentation::XPresentation > SAL_CALL SdXImpressDocument::getPresentation()
{
::SolarMutexGuard aGuard;
if( nullptr == mpDoc )
throw lang::DisposedException();
return uno::Reference< presentation::XPresentation >( mpDoc->getPresentation().get() );
}
// XHandoutMasterSupplier
uno::Reference< drawing::XDrawPage > SAL_CALL SdXImpressDocument::getHandoutMasterPage()
{
::SolarMutexGuard aGuard;
if( nullptr == mpDoc )
throw lang::DisposedException();
uno::Reference< drawing::XDrawPage > xPage;
if( mpDoc )
{
initializeDocument();
SdPage* pPage = mpDoc->GetMasterSdPage( 0, PageKind::Handout );
if( pPage )
xPage.set( pPage->getUnoPage(), uno::UNO_QUERY );
}
return xPage;
}
// XMultiServiceFactory ( SvxFmMSFactory )
css::uno::Reference<css::uno::XInterface> SdXImpressDocument::create(
OUString const & aServiceSpecifier, OUString const & referer)
{
::SolarMutexGuard aGuard;
if( nullptr == mpDoc )
throw lang::DisposedException();
if( aServiceSpecifier == "com.sun.star.drawing.DashTable" )
{
if( !mxDashTable.is() )
mxDashTable = SvxUnoDashTable_createInstance( mpDoc );
return mxDashTable;
}
if( aServiceSpecifier == "com.sun.star.drawing.GradientTable" )
{
if( !mxGradientTable.is() )
mxGradientTable = SvxUnoGradientTable_createInstance( mpDoc );
return mxGradientTable;
}
if( aServiceSpecifier == "com.sun.star.drawing.HatchTable" )
{
if( !mxHatchTable.is() )
mxHatchTable = SvxUnoHatchTable_createInstance( mpDoc );
return mxHatchTable;
}
if( aServiceSpecifier == "com.sun.star.drawing.BitmapTable" )
{
if( !mxBitmapTable.is() )
mxBitmapTable = SvxUnoBitmapTable_createInstance( mpDoc );
return mxBitmapTable;
}
if( aServiceSpecifier == "com.sun.star.drawing.TransparencyGradientTable" )
{
if( !mxTransGradientTable.is() )
mxTransGradientTable = SvxUnoTransGradientTable_createInstance( mpDoc );
return mxTransGradientTable;
}
if( aServiceSpecifier == "com.sun.star.drawing.MarkerTable" )
{
if( !mxMarkerTable.is() )
mxMarkerTable = SvxUnoMarkerTable_createInstance( mpDoc );
return mxMarkerTable;
}
if( aServiceSpecifier == "com.sun.star.text.NumberingRules" )
{
return uno::Reference< uno::XInterface >( SvxCreateNumRule( mpDoc ), uno::UNO_QUERY );
}
if( aServiceSpecifier == "com.sun.star.drawing.Background" )
{
return uno::Reference< uno::XInterface >(
static_cast<uno::XWeak*>(new SdUnoPageBackground( mpDoc )));
}
if( aServiceSpecifier == "com.sun.star.drawing.Defaults" )
{
if( !mxDrawingPool.is() )
mxDrawingPool = SdUnoCreatePool( mpDoc );
return mxDrawingPool;
}
if ( aServiceSpecifier == sUNO_Service_ImageMapRectangleObject )
{
return SvUnoImageMapRectangleObject_createInstance( ImplGetSupportedMacroItems() );
}
if ( aServiceSpecifier == sUNO_Service_ImageMapCircleObject )
{
return SvUnoImageMapCircleObject_createInstance( ImplGetSupportedMacroItems() );
}
if ( aServiceSpecifier == sUNO_Service_ImageMapPolygonObject )
{
return SvUnoImageMapPolygonObject_createInstance( ImplGetSupportedMacroItems() );
}
if( aServiceSpecifier == "com.sun.star.document.Settings" ||
( !mbImpressDoc && ( aServiceSpecifier == "com.sun.star.drawing.DocumentSettings" ) ) ||
( mbImpressDoc && ( aServiceSpecifier == "com.sun.star.presentation.DocumentSettings" ) ) )
{
return sd::DocumentSettings_createInstance( this );
}
if( aServiceSpecifier == "com.sun.star.text.TextField.DateTime" ||
aServiceSpecifier == "com.sun.star.text.textfield.DateTime" )
{
return static_cast<cppu::OWeakObject *>(new SvxUnoTextField( text::textfield::Type::DATE ));
}
if( aServiceSpecifier == "com.sun.star.presentation.TextField.Header" ||
aServiceSpecifier == "com.sun.star.presentation.textfield.Header" )
{
return static_cast<cppu::OWeakObject *>(new SvxUnoTextField( text::textfield::Type::PRESENTATION_HEADER ));
}
if( aServiceSpecifier == "com.sun.star.presentation.TextField.Footer" ||
aServiceSpecifier == "com.sun.star.presentation.textfield.Footer" )
{
return static_cast<cppu::OWeakObject *>(new SvxUnoTextField( text::textfield::Type::PRESENTATION_FOOTER ));
}
if( aServiceSpecifier == "com.sun.star.presentation.TextField.DateTime" ||
aServiceSpecifier == "com.sun.star.presentation.textfield.DateTime" )
{
return static_cast<cppu::OWeakObject *>(new SvxUnoTextField( text::textfield::Type::PRESENTATION_DATE_TIME ));
}
if( aServiceSpecifier == "com.sun.star.text.TextField.PageName" ||
aServiceSpecifier == "com.sun.star.text.textfield.PageName" )
{
return static_cast<cppu::OWeakObject *>(new SvxUnoTextField( text::textfield::Type::PAGE_NAME ));
}
if (aServiceSpecifier == "com.sun.star.text.TextField.DocInfo.Custom" ||
aServiceSpecifier == "com.sun.star.text.textfield.DocInfo.Custom")
{
return static_cast<cppu::OWeakObject *>(new SvxUnoTextField(text::textfield::Type::DOCINFO_CUSTOM));
}
if( aServiceSpecifier == "com.sun.star.xml.NamespaceMap" )
{
static sal_uInt16 aWhichIds[] = { SDRATTR_XMLATTRIBUTES, EE_CHAR_XMLATTRIBS, EE_PARA_XMLATTRIBS, 0 };
return svx::NamespaceMap_createInstance( aWhichIds, &mpDoc->GetItemPool() );
}
// Support creation of GraphicStorageHandler and EmbeddedObjectResolver
if (aServiceSpecifier == "com.sun.star.document.ExportGraphicStorageHandler")
{
return static_cast<cppu::OWeakObject *>(new SvXMLGraphicHelper( SvXMLGraphicHelperMode::Write ));
}
if (aServiceSpecifier == "com.sun.star.document.ImportGraphicStorageHandler")
{
return static_cast<cppu::OWeakObject *>(new SvXMLGraphicHelper( SvXMLGraphicHelperMode::Read ));
}
if( aServiceSpecifier == "com.sun.star.document.ExportEmbeddedObjectResolver" )
{
::comphelper::IEmbeddedHelper *pPersist = mpDoc ? mpDoc->GetPersist() : nullptr;
if( nullptr == pPersist )
throw lang::DisposedException();
return static_cast<cppu::OWeakObject *>(new SvXMLEmbeddedObjectHelper( *pPersist, SvXMLEmbeddedObjectHelperMode::Write ));
}
if( aServiceSpecifier == "com.sun.star.document.ImportEmbeddedObjectResolver" )
{
::comphelper::IEmbeddedHelper *pPersist = mpDoc ? mpDoc->GetPersist() : nullptr;
if( nullptr == pPersist )
throw lang::DisposedException();
return static_cast<cppu::OWeakObject *>(new SvXMLEmbeddedObjectHelper( *pPersist, SvXMLEmbeddedObjectHelperMode::Read ));
}
uno::Reference< uno::XInterface > xRet;
if( aServiceSpecifier.startsWith( "com.sun.star.presentation.") )
{
const OUString aType( aServiceSpecifier.copy(26) );
SvxShape* pShape = nullptr;
sal_uInt16 nType = OBJ_TEXT;
// create a shape wrapper
if( aType.startsWith( "TitleTextShape" ) )
{
nType = OBJ_TEXT;
}
else if( aType.startsWith( "OutlinerShape" ) )
{
nType = OBJ_TEXT;
}
else if( aType.startsWith( "SubtitleShape" ) )
{
nType = OBJ_TEXT;
}
else if( aType.startsWith( "GraphicObjectShape" ) )
{
nType = OBJ_GRAF;
}
else if( aType.startsWith( "PageShape" ) )
{
nType = OBJ_PAGE;
}
else if( aType.startsWith( "OLE2Shape" ) )
{
nType = OBJ_OLE2;
}
else if( aType.startsWith( "ChartShape" ) )
{
nType = OBJ_OLE2;
}
else if( aType.startsWith( "CalcShape" ) )
{
nType = OBJ_OLE2;
}
else if( aType.startsWith( "TableShape" ) )
{
nType = OBJ_TABLE;
}
else if( aType.startsWith( "OrgChartShape" ) )
{
nType = OBJ_OLE2;
}
else if( aType.startsWith( "NotesShape" ) )
{
nType = OBJ_TEXT;
}
else if( aType.startsWith( "HandoutShape" ) )
{
nType = OBJ_PAGE;
}
else if( aType.startsWith( "FooterShape" ) )
{
nType = OBJ_TEXT;
}
else if( aType.startsWith( "HeaderShape" ) )
{
nType = OBJ_TEXT;
}
else if( aType.startsWith( "SlideNumberShape" ) )
{
nType = OBJ_TEXT;
}
else if( aType.startsWith( "DateTimeShape" ) )
{
nType = OBJ_TEXT;
}
else if( aType.startsWith( "MediaShape" ) )
{
nType = OBJ_MEDIA;
}
else
{
throw lang::ServiceNotRegisteredException();
}
// create the API wrapper
pShape = CreateSvxShapeByTypeAndInventor( nType, SdrInventor::Default, referer );
// set shape type
if( pShape && !mbClipBoard )
pShape->SetShapeType(aServiceSpecifier);
xRet = static_cast<uno::XWeak*>(pShape);
}
else if ( aServiceSpecifier == "com.sun.star.drawing.TableShape" )
{
SvxShape* pShape = CreateSvxShapeByTypeAndInventor( OBJ_TABLE, SdrInventor::Default, referer );
if( pShape && !mbClipBoard )
pShape->SetShapeType(aServiceSpecifier);
xRet = static_cast<uno::XWeak*>(pShape);
}
else
{
xRet = SvxFmMSFactory::createInstance( aServiceSpecifier );
}
uno::Reference< drawing::XShape > xShape( xRet, uno::UNO_QUERY );
SvxShape* pShape = xShape.is() ? SvxShape::getImplementation(xShape) : nullptr;
if (pShape)
{
xRet.clear();
new SdXShape( pShape, this );
xRet = xShape;
xShape.clear();
}
return xRet;
}
uno::Reference< uno::XInterface > SAL_CALL SdXImpressDocument::createInstance( const OUString& aServiceSpecifier )
{
return create(aServiceSpecifier, "");
}
css::uno::Reference<css::uno::XInterface>
SdXImpressDocument::createInstanceWithArguments(
OUString const & ServiceSpecifier,
css::uno::Sequence<css::uno::Any> const & Arguments)
{
OUString arg;
if ((ServiceSpecifier == "com.sun.star.drawing.GraphicObjectShape"
|| ServiceSpecifier == "com.sun.star.drawing.MediaShape"
|| ServiceSpecifier == "com.sun.star.presentation.MediaShape")
&& Arguments.getLength() == 1 && (Arguments[0] >>= arg))
{
return create(ServiceSpecifier, arg);
}
return SvxFmMSFactory::createInstanceWithArguments(
ServiceSpecifier, Arguments);
}
uno::Sequence< OUString > SAL_CALL SdXImpressDocument::getAvailableServiceNames()
{
::SolarMutexGuard aGuard;
if( nullptr == mpDoc )
throw lang::DisposedException();
const uno::Sequence< OUString > aSNS_ORG( SvxFmMSFactory::getAvailableServiceNames() );
uno::Sequence< OUString > aSNS( mbImpressDoc ? 36 : 19 );
sal_uInt16 i(0);
aSNS[i++] = "com.sun.star.drawing.DashTable";
aSNS[i++] = "com.sun.star.drawing.GradientTable";
aSNS[i++] = "com.sun.star.drawing.HatchTable";
aSNS[i++] = "com.sun.star.drawing.BitmapTable";
aSNS[i++] = "com.sun.star.drawing.TransparencyGradientTable";
aSNS[i++] = "com.sun.star.drawing.MarkerTable";
aSNS[i++] = "com.sun.star.text.NumberingRules";
aSNS[i++] = "com.sun.star.drawing.Background";
aSNS[i++] = "com.sun.star.document.Settings";
aSNS[i++] = sUNO_Service_ImageMapRectangleObject;
aSNS[i++] = sUNO_Service_ImageMapCircleObject;
aSNS[i++] = sUNO_Service_ImageMapPolygonObject;
aSNS[i++] = "com.sun.star.xml.NamespaceMap";
// Support creation of GraphicStorageHandler and EmbeddedObjectResolver
aSNS[i++] = "com.sun.star.document.ExportGraphicStorageHandler";
aSNS[i++] = "com.sun.star.document.ImportGraphicStorageHandler";
aSNS[i++] = "com.sun.star.document.ExportEmbeddedObjectResolver";
aSNS[i++] = "com.sun.star.document.ImportEmbeddedObjectResolver";
aSNS[i++] = "com.sun.star.drawing.TableShape";
if(mbImpressDoc)
{
aSNS[i++] = "com.sun.star.presentation.TitleTextShape";
aSNS[i++] = "com.sun.star.presentation.OutlinerShape";
aSNS[i++] = "com.sun.star.presentation.SubtitleShape";
aSNS[i++] = "com.sun.star.presentation.GraphicObjectShape";
aSNS[i++] = "com.sun.star.presentation.ChartShape";
aSNS[i++] = "com.sun.star.presentation.PageShape";
aSNS[i++] = "com.sun.star.presentation.OLE2Shape";
aSNS[i++] = "com.sun.star.presentation.TableShape";
aSNS[i++] = "com.sun.star.presentation.OrgChartShape";
aSNS[i++] = "com.sun.star.presentation.NotesShape";
aSNS[i++] = "com.sun.star.presentation.HandoutShape";
aSNS[i++] = "com.sun.star.presentation.DocumentSettings";
aSNS[i++] = "com.sun.star.presentation.FooterShape";
aSNS[i++] = "com.sun.star.presentation.HeaderShape";
aSNS[i++] = "com.sun.star.presentation.SlideNumberShape";
aSNS[i++] = "com.sun.star.presentation.DateTimeShape";
aSNS[i++] = "com.sun.star.presentation.CalcShape";
aSNS[i++] = "com.sun.star.presentation.MediaShape";
}
else
{
aSNS[i++] = "com.sun.star.drawing.DocumentSettings";
}
DBG_ASSERT( i == aSNS.getLength(), "Sequence overrun!" );
return comphelper::concatSequences( aSNS_ORG, aSNS );
}
// lang::XServiceInfo
OUString SAL_CALL SdXImpressDocument::getImplementationName()
{
return OUString( "SdXImpressDocument" );
/* // Matching the .component information:
return mbImpressDoc
? OUString("com.sun.star.comp.Draw.PresentationDocument")
: OUString("com.sun.star.comp.Draw.DrawingDocument");
*/
}
sal_Bool SAL_CALL SdXImpressDocument::supportsService( const OUString& ServiceName )
{
return cppu::supportsService(this, ServiceName);
}
uno::Sequence< OUString > SAL_CALL SdXImpressDocument::getSupportedServiceNames()
{
::SolarMutexGuard aGuard;
uno::Sequence< OUString > aSeq( 4 );
OUString* pServices = aSeq.getArray();
*pServices++ = "com.sun.star.document.OfficeDocument";
*pServices++ = "com.sun.star.drawing.GenericDrawingDocument";
*pServices++ = "com.sun.star.drawing.DrawingDocumentFactory";
if( mbImpressDoc )
*pServices++ = "com.sun.star.presentation.PresentationDocument";
else
*pServices++ = "com.sun.star.drawing.DrawingDocument";
return aSeq;
}
// XPropertySet
uno::Reference< beans::XPropertySetInfo > SAL_CALL SdXImpressDocument::getPropertySetInfo( )
{
::SolarMutexGuard aGuard;
return mpPropSet->getPropertySetInfo();
}
void SAL_CALL SdXImpressDocument::setPropertyValue( const OUString& aPropertyName, const uno::Any& aValue )
{
::SolarMutexGuard aGuard;
if( nullptr == mpDoc )
throw lang::DisposedException();
const SfxItemPropertySimpleEntry* pEntry = mpPropSet->getPropertyMapEntry(aPropertyName);
switch( pEntry ? pEntry->nWID : -1 )
{
case WID_MODEL_LANGUAGE:
{
lang::Locale aLocale;
if(!(aValue >>= aLocale))
throw lang::IllegalArgumentException();
mpDoc->SetLanguage( LanguageTag::convertToLanguageType(aLocale), EE_CHAR_LANGUAGE );
break;
}
case WID_MODEL_TABSTOP:
{
sal_Int32 nValue = 0;
if(!(aValue >>= nValue) || nValue < 0 )
throw lang::IllegalArgumentException();
mpDoc->SetDefaultTabulator(static_cast<sal_uInt16>(nValue));
break;
}
case WID_MODEL_VISAREA:
{
SfxObjectShell* pEmbeddedObj = mpDoc->GetDocSh();
if( !pEmbeddedObj )
break;
awt::Rectangle aVisArea;
if( !(aValue >>= aVisArea) || (aVisArea.Width < 0) || (aVisArea.Height < 0) )
throw lang::IllegalArgumentException();
sal_Int32 nRight, nTop;
if (o3tl::checked_add(aVisArea.X, aVisArea.Width, nRight) || o3tl::checked_add(aVisArea.Y, aVisArea.Height, nTop))
throw lang::IllegalArgumentException();
pEmbeddedObj->SetVisArea(::tools::Rectangle(aVisArea.X, aVisArea.Y, nRight, nTop));
}
break;
case WID_MODEL_CONTFOCUS:
{
bool bFocus = false;
if( !(aValue >>= bFocus ) )
throw lang::IllegalArgumentException();
mpDoc->SetAutoControlFocus( bFocus );
}
break;
case WID_MODEL_DSGNMODE:
{
bool bMode = false;
if( !(aValue >>= bMode ) )
throw lang::IllegalArgumentException();
mpDoc->SetOpenInDesignMode( bMode );
}
break;
case WID_MODEL_BUILDID:
aValue >>= maBuildId;
return;
case WID_MODEL_MAPUNIT:
case WID_MODEL_BASICLIBS:
case WID_MODEL_RUNTIMEUID: // is read-only
case WID_MODEL_DIALOGLIBS:
case WID_MODEL_FONTS:
throw beans::PropertyVetoException();
case WID_MODEL_INTEROPGRABBAG:
setGrabBagItem(aValue);
break;
default:
throw beans::UnknownPropertyException( aPropertyName, static_cast<cppu::OWeakObject*>(this));
}
SetModified();
}
uno::Any SAL_CALL SdXImpressDocument::getPropertyValue( const OUString& PropertyName )
{
::SolarMutexGuard aGuard;
uno::Any aAny;
if( nullptr == mpDoc )
throw lang::DisposedException();
const SfxItemPropertySimpleEntry* pEntry = mpPropSet->getPropertyMapEntry(PropertyName);
switch( pEntry ? pEntry->nWID : -1 )
{
case WID_MODEL_LANGUAGE:
{
LanguageType eLang = mpDoc->GetLanguage( EE_CHAR_LANGUAGE );
aAny <<= LanguageTag::convertToLocale( eLang);
break;
}
case WID_MODEL_TABSTOP:
aAny <<= static_cast<sal_Int32>(mpDoc->GetDefaultTabulator());
break;
case WID_MODEL_VISAREA:
{
SfxObjectShell* pEmbeddedObj = mpDoc->GetDocSh();
if( !pEmbeddedObj )
break;
const ::tools::Rectangle& aRect = pEmbeddedObj->GetVisArea();
awt::Rectangle aVisArea( aRect.Left(), aRect.Top(), aRect.getWidth(), aRect.getHeight() );
aAny <<= aVisArea;
}
break;
case WID_MODEL_MAPUNIT:
{
SfxObjectShell* pEmbeddedObj = mpDoc->GetDocSh();
if( !pEmbeddedObj )
break;
sal_Int16 nMeasureUnit = 0;
SvxMapUnitToMeasureUnit( pEmbeddedObj->GetMapUnit(), nMeasureUnit );
aAny <<= nMeasureUnit;
}
break;
case WID_MODEL_FORBCHARS:
{
aAny <<= getForbiddenCharsTable();
}
break;
case WID_MODEL_CONTFOCUS:
aAny <<= mpDoc->GetAutoControlFocus();
break;
case WID_MODEL_DSGNMODE:
aAny <<= mpDoc->GetOpenInDesignMode();
break;
case WID_MODEL_BASICLIBS:
aAny <<= mpDocShell->GetBasicContainer();
break;
case WID_MODEL_DIALOGLIBS:
aAny <<= mpDocShell->GetDialogContainer();
break;
case WID_MODEL_RUNTIMEUID:
aAny <<= getRuntimeUID();
break;
case WID_MODEL_BUILDID:
return uno::Any( maBuildId );
case WID_MODEL_HASVALIDSIGNATURES:
aAny <<= hasValidSignatures();
break;
case WID_MODEL_FONTS:
{
uno::Sequence<uno::Any> aSeq;
int nSeqIndex = 0;
sal_uInt16 const aWhichIds[] { EE_CHAR_FONTINFO, EE_CHAR_FONTINFO_CJK,
EE_CHAR_FONTINFO_CTL };
const SfxItemPool& rPool = mpDoc->GetPool();
const SfxPoolItem* pItem;
for(sal_uInt16 nWhichId : aWhichIds)
{
sal_uInt32 nItems = rPool.GetItemCount2( nWhichId );
aSeq.realloc( aSeq.getLength() + nItems*5 + 5 );
for( sal_uInt32 j = 0; j < nItems; ++j )
{
if( nullptr != (pItem = rPool.GetItem2( nWhichId, j ) ) )
{
const SvxFontItem *pFont = static_cast<const SvxFontItem *>(pItem);
aSeq[nSeqIndex++] <<= pFont->GetFamilyName();
aSeq[nSeqIndex++] <<= pFont->GetStyleName();
aSeq[nSeqIndex++] <<= sal_Int16(pFont->GetFamily());
aSeq[nSeqIndex++] <<= sal_Int16(pFont->GetPitch());
aSeq[nSeqIndex++] <<= sal_Int16(pFont->GetCharSet());
}
}
const SvxFontItem& rFont = static_cast<const SvxFontItem&>(rPool.GetDefaultItem( nWhichId ));
aSeq[nSeqIndex++] <<= rFont.GetFamilyName();
aSeq[nSeqIndex++] <<= rFont.GetStyleName();
aSeq[nSeqIndex++] <<= sal_Int16(rFont.GetFamily());
aSeq[nSeqIndex++] <<= sal_Int16(rFont.GetPitch());
aSeq[nSeqIndex++] <<= sal_Int16(rFont.GetCharSet());
}
aSeq.realloc( nSeqIndex );
aAny <<= aSeq;
break;
}
case WID_MODEL_INTEROPGRABBAG:
getGrabBagItem(aAny);
break;
default:
throw beans::UnknownPropertyException( PropertyName, static_cast<cppu::OWeakObject*>(this));
}
return aAny;
}
void SAL_CALL SdXImpressDocument::addPropertyChangeListener( const OUString& , const uno::Reference< beans::XPropertyChangeListener >& ) {}
void SAL_CALL SdXImpressDocument::removePropertyChangeListener( const OUString& , const uno::Reference< beans::XPropertyChangeListener >& ) {}
void SAL_CALL SdXImpressDocument::addVetoableChangeListener( const OUString& , const uno::Reference< beans::XVetoableChangeListener >& ) {}
void SAL_CALL SdXImpressDocument::removeVetoableChangeListener( const OUString& , const uno::Reference< beans::XVetoableChangeListener >& ) {}
// XLinkTargetSupplier
uno::Reference< container::XNameAccess > SAL_CALL SdXImpressDocument::getLinks()
{
::SolarMutexGuard aGuard;
if( nullptr == mpDoc )
throw lang::DisposedException();
uno::Reference< container::XNameAccess > xLinks( mxLinks );
if( !xLinks.is() )
mxLinks = xLinks = new SdDocLinkTargets( *this );
return xLinks;
}
// XStyleFamiliesSupplier
uno::Reference< container::XNameAccess > SAL_CALL SdXImpressDocument::getStyleFamilies( )
{
::SolarMutexGuard aGuard;
if( nullptr == mpDoc )
throw lang::DisposedException();
uno::Reference< container::XNameAccess > xStyles( dynamic_cast< container::XNameAccess* >( mpDoc->GetStyleSheetPool()) );
return xStyles;
}
// XAnyCompareFactory
uno::Reference< css::ucb::XAnyCompare > SAL_CALL SdXImpressDocument::createAnyCompareByName( const OUString& )
{
return SvxCreateNumRuleCompare();
}
// XRenderable
sal_Int32 SAL_CALL SdXImpressDocument::getRendererCount( const uno::Any& rSelection,
const uno::Sequence< beans::PropertyValue >& )
{
::SolarMutexGuard aGuard;
sal_Int32 nRet = 0;
if( nullptr == mpDoc )
throw lang::DisposedException();
if( mpDocShell && mpDoc )
{
uno::Reference< frame::XModel > xModel;
rSelection >>= xModel;
if( xModel == mpDocShell->GetModel() )
nRet = mpDoc->GetSdPageCount( PageKind::Standard );
else
{
uno::Reference< drawing::XShapes > xShapes;
rSelection >>= xShapes;
if( xShapes.is() && xShapes->getCount() )
nRet = 1;
}
}
return nRet;
}
uno::Sequence< beans::PropertyValue > SAL_CALL SdXImpressDocument::getRenderer( sal_Int32 , const uno::Any& ,
const uno::Sequence< beans::PropertyValue >& rxOptions )
{
::SolarMutexGuard aGuard;
if( nullptr == mpDoc )
throw lang::DisposedException();
bool bExportNotesPages = false;
for( sal_Int32 nProperty = 0, nPropertyCount = rxOptions.getLength(); nProperty < nPropertyCount; ++nProperty )
{
if ( rxOptions[ nProperty ].Name == "ExportNotesPages" )
rxOptions[ nProperty].Value >>= bExportNotesPages;
}
uno::Sequence< beans::PropertyValue > aRenderer;
if( mpDocShell && mpDoc )
{
awt::Size aPageSize;
if ( bExportNotesPages )
{
Size aNotesPageSize = mpDoc->GetSdPage( 0, PageKind::Notes )->GetSize();
aPageSize = awt::Size( aNotesPageSize.Width(), aNotesPageSize.Height() );
}
else
{
const ::tools::Rectangle aVisArea( mpDocShell->GetVisArea( embed::Aspects::MSOLE_DOCPRINT ) );
aPageSize = awt::Size( aVisArea.GetWidth(), aVisArea.GetHeight() );
}
aRenderer.realloc( 1 );
aRenderer[ 0 ].Name = "PageSize" ;
aRenderer[ 0 ].Value <<= aPageSize;
}
return aRenderer;
}
class ImplRenderPaintProc : public sdr::contact::ViewObjectContactRedirector
{
const SdrLayerAdmin& rLayerAdmin;
SdrPageView* pSdrPageView;
vcl::PDFExtOutDevData* pPDFExtOutDevData;
vcl::PDFWriter::StructElement ImplBegStructureTag( SdrObject& rObject );
public:
bool IsVisible ( const SdrObject* pObj ) const;
bool IsPrintable( const SdrObject* pObj ) const;
ImplRenderPaintProc( const SdrLayerAdmin& rLA, SdrPageView* pView, vcl::PDFExtOutDevData* pData );
// all default implementations just call the same methods at the original. To do something
// different, override the method and at least do what the method does.
virtual drawinglayer::primitive2d::Primitive2DContainer createRedirectedPrimitive2DSequence(
const sdr::contact::ViewObjectContact& rOriginal,
const sdr::contact::DisplayInfo& rDisplayInfo) override;
};
ImplRenderPaintProc::ImplRenderPaintProc( const SdrLayerAdmin& rLA, SdrPageView* pView, vcl::PDFExtOutDevData* pData )
: ViewObjectContactRedirector(),
rLayerAdmin ( rLA ),
pSdrPageView ( pView ),
pPDFExtOutDevData ( pData )
{
}
sal_Int32 ImplPDFGetBookmarkPage( const OUString& rBookmark, SdDrawDocument const & rDoc )
{
sal_Int32 nPage = -1;
OUString aBookmark( rBookmark );
if( rBookmark.startsWith("#") )
aBookmark = rBookmark.copy( 1 );
// is the bookmark a page ?
bool bIsMasterPage;
sal_uInt16 nPgNum = rDoc.GetPageByName( aBookmark, bIsMasterPage );
SdrObject* pObj = nullptr;
if ( nPgNum == SDRPAGE_NOTFOUND )
{
// is the bookmark a object ?
pObj = rDoc.GetObj( aBookmark );
if (pObj)
nPgNum = pObj->getSdrPageFromSdrObject()->GetPageNum();
}
if ( nPgNum != SDRPAGE_NOTFOUND )
nPage = ( nPgNum - 1 ) / 2;
return nPage;
}
void ImplPDFExportComments( const uno::Reference< drawing::XDrawPage >& xPage, vcl::PDFExtOutDevData& rPDFExtOutDevData )
{
try
{
uno::Reference< office::XAnnotationAccess > xAnnotationAccess( xPage, uno::UNO_QUERY_THROW );
uno::Reference< office::XAnnotationEnumeration > xAnnotationEnumeration( xAnnotationAccess->createAnnotationEnumeration() );
LanguageType eLanguage = Application::GetSettings().GetLanguageTag().getLanguageType();
while( xAnnotationEnumeration->hasMoreElements() )
{
uno::Reference< office::XAnnotation > xAnnotation( xAnnotationEnumeration->nextElement() );
geometry::RealPoint2D aRealPoint2D( xAnnotation->getPosition() );
uno::Reference< text::XText > xText( xAnnotation->getTextRange() );
util::DateTime aDateTime( xAnnotation->getDateTime() );
Date aDate( aDateTime.Day, aDateTime.Month, aDateTime.Year );
::tools::Time aTime( ::tools::Time::EMPTY );
OUString aStr = SvxDateTimeField::GetFormatted( aDate, aTime,
SvxDateFormat::B, SvxTimeFormat::AppDefault,
*(SD_MOD()->GetNumberFormatter()), eLanguage );
vcl::PDFNote aNote;
OUString sTitle( xAnnotation->getAuthor() );
sTitle += ", ";
sTitle += aStr;
aNote.Title = sTitle;
aNote.Contents = xText->getString();
rPDFExtOutDevData.CreateNote( ::tools::Rectangle( Point( static_cast< long >( aRealPoint2D.X * 100 ),
static_cast< long >( aRealPoint2D.Y * 100 ) ), Size( 1000, 1000 ) ), aNote );
}
}
catch (const uno::Exception&)
{
}
}
void ImplPDFExportShapeInteraction( const uno::Reference< drawing::XShape >& xShape, SdDrawDocument& rDoc, vcl::PDFExtOutDevData& rPDFExtOutDevData )
{
if ( xShape->getShapeType() == "com.sun.star.drawing.GroupShape" )
{
uno::Reference< container::XIndexAccess > xIndexAccess( xShape, uno::UNO_QUERY );
if ( xIndexAccess.is() )
{
sal_Int32 i, nCount = xIndexAccess->getCount();
for ( i = 0; i < nCount; i++ )
{
uno::Reference< drawing::XShape > xSubShape( xIndexAccess->getByIndex( i ), uno::UNO_QUERY );
if ( xSubShape.is() )
ImplPDFExportShapeInteraction( xSubShape, rDoc, rPDFExtOutDevData );
}
}
}
else
{
uno::Reference< beans::XPropertySet > xShapePropSet( xShape, uno::UNO_QUERY );
if( xShapePropSet.is() )
{
Size aPageSize( rDoc.GetSdPage( 0, PageKind::Standard )->GetSize() );
Point aPoint( 0, 0 );
::tools::Rectangle aPageRect( aPoint, aPageSize );
awt::Point aShapePos( xShape->getPosition() );
awt::Size aShapeSize( xShape->getSize() );
::tools::Rectangle aLinkRect( Point( aShapePos.X, aShapePos.Y ), Size( aShapeSize.Width, aShapeSize.Height ) );
// Handle linked videos.
if (xShape->getShapeType() == "com.sun.star.drawing.MediaShape" || xShape->getShapeType() == "com.sun.star.presentation.MediaShape")
{
OUString aMediaURL;
xShapePropSet->getPropertyValue("MediaURL") >>= aMediaURL;
if (!aMediaURL.isEmpty())
{
sal_Int32 nScreenId = rPDFExtOutDevData.CreateScreen(aLinkRect, rPDFExtOutDevData.GetCurrentPageNumber());
if (aMediaURL.startsWith("vnd.sun.star.Package:"))
{
OUString aTempFileURL;
xShapePropSet->getPropertyValue("PrivateTempFileURL") >>= aTempFileURL;
rPDFExtOutDevData.SetScreenStream(nScreenId, aTempFileURL);
}
else
rPDFExtOutDevData.SetScreenURL(nScreenId, aMediaURL);
}
}
presentation::ClickAction eCa;
uno::Any aAny( xShapePropSet->getPropertyValue( "OnClick" ) );
if ( aAny >>= eCa )
{
switch ( eCa )
{
case presentation::ClickAction_LASTPAGE :
{
sal_Int32 nCount = rDoc.GetSdPageCount( PageKind::Standard );
sal_Int32 nDestId = rPDFExtOutDevData.CreateDest( aPageRect, nCount - 1, vcl::PDFWriter::DestAreaType::FitRectangle );
sal_Int32 nLinkId = rPDFExtOutDevData.CreateLink( aLinkRect );
rPDFExtOutDevData.SetLinkDest( nLinkId, nDestId );
}
break;
case presentation::ClickAction_FIRSTPAGE :
{
sal_Int32 nDestId = rPDFExtOutDevData.CreateDest( aPageRect, 0, vcl::PDFWriter::DestAreaType::FitRectangle );
sal_Int32 nLinkId = rPDFExtOutDevData.CreateLink( aLinkRect );
rPDFExtOutDevData.SetLinkDest( nLinkId, nDestId );
}
break;
case presentation::ClickAction_PREVPAGE :
{
sal_Int32 nDestPage = rPDFExtOutDevData.GetCurrentPageNumber();
if ( nDestPage )
nDestPage--;
sal_Int32 nDestId = rPDFExtOutDevData.CreateDest( aPageRect, nDestPage, vcl::PDFWriter::DestAreaType::FitRectangle );
sal_Int32 nLinkId = rPDFExtOutDevData.CreateLink( aLinkRect );
rPDFExtOutDevData.SetLinkDest( nLinkId, nDestId );
}
break;
case presentation::ClickAction_NEXTPAGE :
{
sal_Int32 nDestPage = rPDFExtOutDevData.GetCurrentPageNumber() + 1;
sal_Int32 nLastPage = rDoc.GetSdPageCount( PageKind::Standard ) - 1;
if ( nDestPage > nLastPage )
nDestPage = nLastPage;
sal_Int32 nDestId = rPDFExtOutDevData.CreateDest( aPageRect, nDestPage, vcl::PDFWriter::DestAreaType::FitRectangle );
sal_Int32 nLinkId = rPDFExtOutDevData.CreateLink( aLinkRect );
rPDFExtOutDevData.SetLinkDest( nLinkId, nDestId );
}
break;
case presentation::ClickAction_PROGRAM :
case presentation::ClickAction_BOOKMARK :
case presentation::ClickAction_DOCUMENT :
{
OUString aBookmark;
xShapePropSet->getPropertyValue( "Bookmark" ) >>= aBookmark;
if( !aBookmark.isEmpty() )
{
switch( eCa )
{
case presentation::ClickAction_DOCUMENT :
case presentation::ClickAction_PROGRAM :
{
sal_Int32 nLinkId = rPDFExtOutDevData.CreateLink( aLinkRect );
rPDFExtOutDevData.SetLinkURL( nLinkId, aBookmark );
}
break;
case presentation::ClickAction_BOOKMARK :
{
sal_Int32 nPage = ImplPDFGetBookmarkPage( aBookmark, rDoc );
if ( nPage != -1 )
{
sal_Int32 nDestId = rPDFExtOutDevData.CreateDest( aPageRect, nPage, vcl::PDFWriter::DestAreaType::FitRectangle );
sal_Int32 nLinkId = rPDFExtOutDevData.CreateLink( aLinkRect );
rPDFExtOutDevData.SetLinkDest( nLinkId, nDestId );
}
}
break;
default:
break;
}
}
}
break;
case presentation::ClickAction_STOPPRESENTATION :
case presentation::ClickAction_SOUND :
case presentation::ClickAction_INVISIBLE :
case presentation::ClickAction_VERB :
case presentation::ClickAction_VANISH :
case presentation::ClickAction_MACRO :
default :
break;
}
}
}
}
}
vcl::PDFWriter::StructElement ImplRenderPaintProc::ImplBegStructureTag( SdrObject& rObject )
{
vcl::PDFWriter::StructElement eElement(vcl::PDFWriter::NonStructElement);
if ( pPDFExtOutDevData && pPDFExtOutDevData->GetIsExportTaggedPDF() )
{
SdrInventor nInventor = rObject.GetObjInventor();
sal_uInt16 nIdentifier = rObject.GetObjIdentifier();
bool bIsTextObj = dynamic_cast< const SdrTextObj *>( &rObject ) != nullptr;
if ( nInventor == SdrInventor::Default )
{
if ( nIdentifier == OBJ_GRUP )
eElement = vcl::PDFWriter::Section;
else if ( nIdentifier == OBJ_TITLETEXT )
eElement = vcl::PDFWriter::Heading;
else if ( nIdentifier == OBJ_OUTLINETEXT )
eElement = vcl::PDFWriter::Division;
else if ( !bIsTextObj || !static_cast<SdrTextObj&>(rObject).HasText() )
eElement = vcl::PDFWriter::Figure;
}
}
return eElement;
}
drawinglayer::primitive2d::Primitive2DContainer ImplRenderPaintProc::createRedirectedPrimitive2DSequence(
const sdr::contact::ViewObjectContact& rOriginal,
const sdr::contact::DisplayInfo& rDisplayInfo)
{
SdrObject* pObject = rOriginal.GetViewContact().TryToGetSdrObject();
if(pObject)
{
drawinglayer::primitive2d::Primitive2DContainer xRetval;
if(pObject->getSdrPageFromSdrObject())
{
if(pObject->getSdrPageFromSdrObject()->checkVisibility(rOriginal, rDisplayInfo, false))
{
if(IsVisible(pObject) && IsPrintable(pObject))
{
const vcl::PDFWriter::StructElement eElement(ImplBegStructureTag( *pObject ));
const bool bTagUsed(vcl::PDFWriter::NonStructElement != eElement);
xRetval = sdr::contact::ViewObjectContactRedirector::createRedirectedPrimitive2DSequence(rOriginal, rDisplayInfo);
if(!xRetval.empty() && bTagUsed)
{
// embed Primitive2DSequence in a structure tag element for
// exactly this purpose (StructureTagPrimitive2D)
const drawinglayer::primitive2d::Primitive2DReference xReference(new drawinglayer::primitive2d::StructureTagPrimitive2D(eElement, xRetval));
xRetval = drawinglayer::primitive2d::Primitive2DContainer { xReference };
}
}
}
}
return xRetval;
}
else
{
// not an object, maybe a page
return sdr::contact::ViewObjectContactRedirector::createRedirectedPrimitive2DSequence(rOriginal, rDisplayInfo);
}
}
bool ImplRenderPaintProc::IsVisible( const SdrObject* pObj ) const
{
bool bVisible = true;
SdrLayerID nLayerId = pObj->GetLayer();
if( pSdrPageView )
{
const SdrLayer* pSdrLayer = rLayerAdmin.GetLayerPerID( nLayerId );
if ( pSdrLayer )
{
OUString aLayerName = pSdrLayer->GetName();
bVisible = pSdrPageView->IsLayerVisible( aLayerName );
}
}
return bVisible;
}
bool ImplRenderPaintProc::IsPrintable( const SdrObject* pObj ) const
{
bool bPrintable = true;
SdrLayerID nLayerId = pObj->GetLayer();
if( pSdrPageView )
{
const SdrLayer* pSdrLayer = rLayerAdmin.GetLayerPerID( nLayerId );
if ( pSdrLayer )
{
OUString aLayerName = pSdrLayer->GetName();
bPrintable = pSdrPageView->IsLayerPrintable( aLayerName );
}
}
return bPrintable;
}
namespace
{
sal_Int16 CalcOutputPageNum(vcl::PDFExtOutDevData const * pPDFExtOutDevData, SdDrawDocument const *pDoc, sal_Int16 nPageNumber)
{
//export all pages, simple one to one case
if (pPDFExtOutDevData && pPDFExtOutDevData->GetIsExportHiddenSlides())
return nPageNumber-1;
//check all preceding pages, and only count non-hidden ones
sal_Int16 nRet = 0;
for (sal_Int16 i = 0; i < nPageNumber-1; ++i)
{
if (!pDoc->GetSdPage(i, PageKind::Standard)->IsExcluded())
++nRet;
}
return nRet;
}
}
void SAL_CALL SdXImpressDocument::render( sal_Int32 nRenderer, const uno::Any& rSelection,
const uno::Sequence< beans::PropertyValue >& rxOptions )
{
::SolarMutexGuard aGuard;
if( nullptr == mpDoc )
throw lang::DisposedException();
if( mpDocShell && mpDoc )
{
uno::Reference< awt::XDevice > xRenderDevice;
const sal_Int32 nPageNumber = nRenderer + 1;
PageKind ePageKind = PageKind::Standard;
bool bExportNotesPages = false;
for( sal_Int32 nProperty = 0, nPropertyCount = rxOptions.getLength(); nProperty < nPropertyCount; ++nProperty )
{
if ( rxOptions[ nProperty ].Name == "RenderDevice" )
rxOptions[ nProperty ].Value >>= xRenderDevice;
else if ( rxOptions[ nProperty ].Name == "ExportNotesPages" )
{
rxOptions[ nProperty].Value >>= bExportNotesPages;
if ( bExportNotesPages )
ePageKind = PageKind::Notes;
}
}
if( xRenderDevice.is() && nPageNumber && ( nPageNumber <= mpDoc->GetSdPageCount( ePageKind ) ) )
{
VCLXDevice* pDevice = VCLXDevice::GetImplementation( xRenderDevice );
VclPtr< OutputDevice> pOut = pDevice ? pDevice->GetOutputDevice() : VclPtr< OutputDevice >();
if( pOut )
{
vcl::PDFExtOutDevData* pPDFExtOutDevData = dynamic_cast<vcl::PDFExtOutDevData* >( pOut->GetExtOutDevData() );
if ( !( mpDoc->GetSdPage(static_cast<sal_Int16>(nPageNumber)-1, PageKind::Standard)->IsExcluded() ) ||
(pPDFExtOutDevData && pPDFExtOutDevData->GetIsExportHiddenSlides()) )
{
std::unique_ptr<::sd::ClientView> pView( new ::sd::ClientView( mpDocShell, pOut ) );
::tools::Rectangle aVisArea = ::tools::Rectangle( Point(), mpDoc->GetSdPage( static_cast<sal_uInt16>(nPageNumber) - 1, ePageKind )->GetSize() );
vcl::Region aRegion( aVisArea );
::sd::ViewShell* pOldViewSh = mpDocShell->GetViewShell();
::sd::View* pOldSdView = pOldViewSh ? pOldViewSh->GetView() : nullptr;
if ( pOldSdView )
pOldSdView->SdrEndTextEdit();
pView->SetHlplVisible( false );
pView->SetGridVisible( false );
pView->SetBordVisible( false );
pView->SetPageVisible( false );
pView->SetGlueVisible( false );
pOut->SetMapMode(MapMode(MapUnit::Map100thMM));
pOut->IntersectClipRegion( aVisArea );
uno::Reference< frame::XModel > xModel;
rSelection >>= xModel;
if( xModel == mpDocShell->GetModel() )
{
pView->ShowSdrPage( mpDoc->GetSdPage( static_cast<sal_uInt16>(nPageNumber) - 1, ePageKind ));
SdrPageView* pPV = pView->GetSdrPageView();
if( pOldSdView )
{
SdrPageView* pOldPV = pOldSdView->GetSdrPageView();
if( pPV && pOldPV )
{
pPV->SetVisibleLayers( pOldPV->GetVisibleLayers() );
pPV->SetPrintableLayers( pOldPV->GetPrintableLayers() );
}
}
ImplRenderPaintProc aImplRenderPaintProc( mpDoc->GetLayerAdmin(),
pPV, pPDFExtOutDevData );
// background color for outliner :o
SdPage* pPage = pPV ? static_cast<SdPage*>(pPV->GetPage()) : nullptr;
if( pPage )
{
SdrOutliner& rOutl = mpDoc->GetDrawOutliner();
bool bScreenDisplay(true);
if(bScreenDisplay && pOut && OUTDEV_PRINTER == pOut->GetOutDevType())
{
// #i75566# printing; suppress AutoColor BackgroundColor generation
// for visibility reasons by giving GetPageBackgroundColor()
// the needed hint
bScreenDisplay = false;
}
if(bScreenDisplay && pOut && pOut->GetPDFWriter())
{
// #i75566# PDF export; suppress AutoColor BackgroundColor generation (see above)
bScreenDisplay = false;
}
// #i75566# Name change GetBackgroundColor -> GetPageBackgroundColor and
// hint value if screen display. Only then the AutoColor mechanisms shall be applied
rOutl.SetBackgroundColor( pPage->GetPageBackgroundColor( pPV, bScreenDisplay ) );
}
pView->SdrPaintView::CompleteRedraw( pOut, aRegion, &aImplRenderPaintProc );
if ( pPDFExtOutDevData && pPage )
{
try
{
uno::Any aAny;
uno::Reference< drawing::XDrawPage > xPage( uno::Reference< drawing::XDrawPage >::query( pPage->getUnoPage() ) );
if ( xPage.is() )
{
if ( pPDFExtOutDevData->GetIsExportNotes() )
ImplPDFExportComments( xPage, *pPDFExtOutDevData );
uno::Reference< beans::XPropertySet > xPagePropSet( xPage, uno::UNO_QUERY );
if( xPagePropSet.is() )
{
// exporting object interactions to pdf
// if necessary, the master page interactions will be exported first
bool bIsBackgroundObjectsVisible = false; // #i39428# IsBackgroundObjectsVisible not available for Draw
if ( mbImpressDoc && xPagePropSet->getPropertySetInfo()->hasPropertyByName( "IsBackgroundObjectsVisible" ) )
xPagePropSet->getPropertyValue( "IsBackgroundObjectsVisible" ) >>= bIsBackgroundObjectsVisible;
if ( bIsBackgroundObjectsVisible && !pPDFExtOutDevData->GetIsExportNotesPages() )
{
uno::Reference< drawing::XMasterPageTarget > xMasterPageTarget( xPage, uno::UNO_QUERY );
if ( xMasterPageTarget.is() )
{
uno::Reference< drawing::XDrawPage > xMasterPage = xMasterPageTarget->getMasterPage();
if ( xMasterPage.is() )
{
uno::Reference< drawing::XShapes> xShapes( xMasterPage, uno::UNO_QUERY );
sal_Int32 i, nCount = xShapes->getCount();
for ( i = 0; i < nCount; i++ )
{
aAny = xShapes->getByIndex( i );
uno::Reference< drawing::XShape > xShape;
if ( aAny >>= xShape )
ImplPDFExportShapeInteraction( xShape, *mpDoc, *pPDFExtOutDevData );
}
}
}
}
// exporting slide page object interactions
uno::Reference< drawing::XShapes> xShapes( xPage, uno::UNO_QUERY );
sal_Int32 i, nCount = xShapes->getCount();
for ( i = 0; i < nCount; i++ )
{
aAny = xShapes->getByIndex( i );
uno::Reference< drawing::XShape > xShape;
if ( aAny >>= xShape )
ImplPDFExportShapeInteraction( xShape, *mpDoc, *pPDFExtOutDevData );
}
// exporting transition effects to pdf
if ( mbImpressDoc && !pPDFExtOutDevData->GetIsExportNotesPages() && pPDFExtOutDevData->GetIsExportTransitionEffects() )
{
const OUString sEffect( "Effect" );
const OUString sSpeed ( "Speed" );
sal_Int32 nTime = 800;
presentation::AnimationSpeed aAs;
if ( xPagePropSet->getPropertySetInfo( )->hasPropertyByName( sSpeed ) )
{
aAny = xPagePropSet->getPropertyValue( sSpeed );
if ( aAny >>= aAs )
{
switch( aAs )
{
case presentation::AnimationSpeed_SLOW : nTime = 1500; break;
case presentation::AnimationSpeed_FAST : nTime = 300; break;
default:
case presentation::AnimationSpeed_MEDIUM : nTime = 800;
}
}
}
presentation::FadeEffect eFe;
vcl::PDFWriter::PageTransition eType = vcl::PDFWriter::PageTransition::Regular;
if ( xPagePropSet->getPropertySetInfo( )->hasPropertyByName( sEffect ) )
{
aAny = xPagePropSet->getPropertyValue( sEffect );
if ( aAny >>= eFe )
{
switch( eFe )
{
case presentation::FadeEffect_HORIZONTAL_LINES :
case presentation::FadeEffect_HORIZONTAL_CHECKERBOARD :
case presentation::FadeEffect_HORIZONTAL_STRIPES : eType = vcl::PDFWriter::PageTransition::BlindsHorizontal; break;
case presentation::FadeEffect_VERTICAL_LINES :
case presentation::FadeEffect_VERTICAL_CHECKERBOARD :
case presentation::FadeEffect_VERTICAL_STRIPES : eType = vcl::PDFWriter::PageTransition::BlindsVertical; break;
case presentation::FadeEffect_UNCOVER_TO_RIGHT :
case presentation::FadeEffect_UNCOVER_TO_UPPERRIGHT :
case presentation::FadeEffect_ROLL_FROM_LEFT :
case presentation::FadeEffect_FADE_FROM_UPPERLEFT :
case presentation::FadeEffect_MOVE_FROM_UPPERLEFT :
case presentation::FadeEffect_FADE_FROM_LEFT :
case presentation::FadeEffect_MOVE_FROM_LEFT : eType = vcl::PDFWriter::PageTransition::WipeLeftToRight; break;
case presentation::FadeEffect_UNCOVER_TO_BOTTOM :
case presentation::FadeEffect_UNCOVER_TO_LOWERRIGHT :
case presentation::FadeEffect_ROLL_FROM_TOP :
case presentation::FadeEffect_FADE_FROM_UPPERRIGHT :
case presentation::FadeEffect_MOVE_FROM_UPPERRIGHT :
case presentation::FadeEffect_FADE_FROM_TOP :
case presentation::FadeEffect_MOVE_FROM_TOP : eType = vcl::PDFWriter::PageTransition::WipeTopToBottom; break;
case presentation::FadeEffect_UNCOVER_TO_LEFT :
case presentation::FadeEffect_UNCOVER_TO_LOWERLEFT :
case presentation::FadeEffect_ROLL_FROM_RIGHT :
case presentation::FadeEffect_FADE_FROM_LOWERRIGHT :
case presentation::FadeEffect_MOVE_FROM_LOWERRIGHT :
case presentation::FadeEffect_FADE_FROM_RIGHT :
case presentation::FadeEffect_MOVE_FROM_RIGHT : eType = vcl::PDFWriter::PageTransition::WipeRightToLeft; break;
case presentation::FadeEffect_UNCOVER_TO_TOP :
case presentation::FadeEffect_UNCOVER_TO_UPPERLEFT :
case presentation::FadeEffect_ROLL_FROM_BOTTOM :
case presentation::FadeEffect_FADE_FROM_LOWERLEFT :
case presentation::FadeEffect_MOVE_FROM_LOWERLEFT :
case presentation::FadeEffect_FADE_FROM_BOTTOM :
case presentation::FadeEffect_MOVE_FROM_BOTTOM : eType = vcl::PDFWriter::PageTransition::WipeBottomToTop; break;
case presentation::FadeEffect_OPEN_VERTICAL : eType = vcl::PDFWriter::PageTransition::SplitHorizontalInward; break;
case presentation::FadeEffect_CLOSE_HORIZONTAL : eType = vcl::PDFWriter::PageTransition::SplitHorizontalOutward; break;
case presentation::FadeEffect_OPEN_HORIZONTAL : eType = vcl::PDFWriter::PageTransition::SplitVerticalInward; break;
case presentation::FadeEffect_CLOSE_VERTICAL : eType = vcl::PDFWriter::PageTransition::SplitVerticalOutward; break;
case presentation::FadeEffect_FADE_TO_CENTER : eType = vcl::PDFWriter::PageTransition::BoxInward; break;
case presentation::FadeEffect_FADE_FROM_CENTER : eType = vcl::PDFWriter::PageTransition::BoxOutward; break;
case presentation::FadeEffect_NONE : eType = vcl::PDFWriter::PageTransition::Regular; break;
case presentation::FadeEffect_RANDOM :
case presentation::FadeEffect_DISSOLVE :
default: eType = vcl::PDFWriter::PageTransition::Dissolve; break;
}
}
}
if ( xPagePropSet->getPropertySetInfo( )->hasPropertyByName( sEffect ) ||
xPagePropSet->getPropertySetInfo( )->hasPropertyByName( sSpeed ) )
{
pPDFExtOutDevData->SetPageTransition( eType, nTime );
}
}
}
}
Size aPageSize( mpDoc->GetSdPage( 0, PageKind::Standard )->GetSize() );
Point aPoint( 0, 0 );
::tools::Rectangle aPageRect( aPoint, aPageSize );
// resolving links found in this page by the method ImpEditEngine::Paint
std::vector< vcl::PDFExtOutDevBookmarkEntry >& rBookmarks = pPDFExtOutDevData->GetBookmarks();
std::vector< vcl::PDFExtOutDevBookmarkEntry >::iterator aIBeg = rBookmarks.begin();
std::vector< vcl::PDFExtOutDevBookmarkEntry >::iterator aIEnd = rBookmarks.end();
while ( aIBeg != aIEnd )
{
sal_Int32 nPage = ImplPDFGetBookmarkPage( aIBeg->aBookmark, *mpDoc );
if ( nPage != -1 )
{
if ( aIBeg->nLinkId != -1 )
pPDFExtOutDevData->SetLinkDest( aIBeg->nLinkId, pPDFExtOutDevData->CreateDest( aPageRect, nPage, vcl::PDFWriter::DestAreaType::FitRectangle ) );
else
pPDFExtOutDevData->DescribeRegisteredDest( aIBeg->nDestId, aPageRect, nPage, vcl::PDFWriter::DestAreaType::FitRectangle );
}
else
pPDFExtOutDevData->SetLinkURL( aIBeg->nLinkId, aIBeg->aBookmark );
++aIBeg;
}
rBookmarks.clear();
//---> #i56629, #i40318
//get the page name, will be used as outline element in PDF bookmark pane
OUString aPageName = mpDoc->GetSdPage( static_cast<sal_uInt16>(nPageNumber) - 1 , PageKind::Standard )->GetName();
if( !aPageName.isEmpty() )
{
// Destination PageNum
const sal_Int32 nDestPageNum = CalcOutputPageNum(pPDFExtOutDevData, mpDoc, nPageNumber);
// insert the bookmark to this page into the NamedDestinations
if( pPDFExtOutDevData->GetIsExportNamedDestinations() )
pPDFExtOutDevData->CreateNamedDest(aPageName, aPageRect, nDestPageNum);
// add the name to the outline, (almost) same code as in sc/source/ui/unoobj/docuno.cxx
// issue #i40318.
if( pPDFExtOutDevData->GetIsExportBookmarks() )
{
// Destination Export
const sal_Int32 nDestId =
pPDFExtOutDevData->CreateDest(aPageRect , nDestPageNum);
// Create a new outline item:
pPDFExtOutDevData->CreateOutlineItem( -1 , aPageName, nDestId );
}
}
//<--- #i56629, #i40318
}
catch (const uno::Exception&)
{
}
}
}
else
{
uno::Reference< drawing::XShapes > xShapes;
rSelection >>= xShapes;
if( xShapes.is() && xShapes->getCount() )
{
SdrPageView* pPV = nullptr;
ImplRenderPaintProc aImplRenderPaintProc( mpDoc->GetLayerAdmin(),
pOldSdView ? pOldSdView->GetSdrPageView() : nullptr, pPDFExtOutDevData );
for( sal_uInt32 i = 0, nCount = xShapes->getCount(); i < nCount; i++ )
{
uno::Reference< drawing::XShape > xShape;
xShapes->getByIndex( i ) >>= xShape;
if( xShape.is() )
{
SvxShape* pShape = SvxShape::getImplementation( xShape );
if( pShape )
{
SdrObject* pObj = pShape->GetSdrObject();
if( pObj && pObj->getSdrPageFromSdrObject()
&& aImplRenderPaintProc.IsVisible( pObj )
&& aImplRenderPaintProc.IsPrintable( pObj ) )
{
if( !pPV )
pPV = pView->ShowSdrPage( pObj->getSdrPageFromSdrObject() );
if( pPV )
pView->MarkObj( pObj, pPV );
}
}
}
}
pView->DrawMarkedObj(*pOut);
}
}
}
}
}
}
}
DrawViewShell* SdXImpressDocument::GetViewShell()
{
DrawViewShell* pViewSh = dynamic_cast<DrawViewShell*>(mpDocShell->GetViewShell());
if (!pViewSh)
{
SAL_WARN("sd", "DrawViewShell not available!");
return nullptr;
}
return pViewSh;
}
void SdXImpressDocument::paintTile( VirtualDevice& rDevice,
int nOutputWidth, int nOutputHeight,
int nTilePosX, int nTilePosY,
long nTileWidth, long nTileHeight )
{
DrawViewShell* pViewSh = GetViewShell();
if (!pViewSh)
return;
// Scaling. Must convert from pixels to twips. We know
// that VirtualDevices use a DPI of 96.
// We specifically calculate these scales first as we're still
// in TWIPs, and might as well minimize the number of conversions.
Fraction scaleX = Fraction( nOutputWidth, 96 ) * Fraction(1440) /
Fraction( nTileWidth);
Fraction scaleY = Fraction( nOutputHeight, 96 ) * Fraction(1440) /
Fraction( nTileHeight);
// svx seems to be the only component that works natively in
// 100th mm rather than TWIP. It makes most sense just to
// convert here and in getDocumentSize, and leave the tiled
// rendering API working in TWIPs.
long nTileWidthHMM = convertTwipToMm100( nTileWidth );
long nTileHeightHMM = convertTwipToMm100( nTileHeight );
int nTilePosXHMM = convertTwipToMm100( nTilePosX );
int nTilePosYHMM = convertTwipToMm100( nTilePosY );
MapMode aMapMode = rDevice.GetMapMode();
aMapMode.SetMapUnit( MapUnit::Map100thMM );
aMapMode.SetOrigin( Point( -nTilePosXHMM,
-nTilePosYHMM) );
aMapMode.SetScaleX( scaleX );
aMapMode.SetScaleY( scaleY );
rDevice.SetMapMode( aMapMode );
rDevice.SetOutputSizePixel( Size(nOutputWidth, nOutputHeight) );
Point aPoint(nTilePosXHMM, nTilePosYHMM);
Size aSize(nTileWidthHMM, nTileHeightHMM);
::tools::Rectangle aRect(aPoint, aSize);
pViewSh->GetView()->CompleteRedraw(&rDevice, vcl::Region(aRect));
LokChartHelper::PaintAllChartsOnTile(rDevice, nOutputWidth, nOutputHeight,
nTilePosX, nTilePosY, nTileWidth, nTileHeight);
}
void SdXImpressDocument::setPart( int nPart )
{
DrawViewShell* pViewSh = GetViewShell();
if (!pViewSh)
return;
pViewSh->SwitchPage( nPart );
}
int SdXImpressDocument::getParts()
{
// TODO: master pages?
// Read: drviews1.cxx
return mpDoc->GetSdPageCount(PageKind::Standard);
}
int SdXImpressDocument::getPart()
{
DrawViewShell* pViewSh = GetViewShell();
if (!pViewSh)
return 0;
return pViewSh->GetViewShellBase().getPart();
}
OUString SdXImpressDocument::getPartName( int nPart )
{
SdPage* pPage = mpDoc->GetSdPage( nPart, PageKind::Standard );
if (!pPage)
{
SAL_WARN("sd", "DrawViewShell not available!");
return OUString();
}
return pPage->GetName();
}
OUString SdXImpressDocument::getPartHash( int nPart )
{
SdPage* pPage = mpDoc->GetSdPage( nPart, PageKind::Standard );
if (!pPage)
{
SAL_WARN("sd", "DrawViewShell not available!");
return OUString();
}
return OUString::number(pPage->GetHashCode());
}
VclPtr<vcl::Window> SdXImpressDocument::getDocWindow()
{
SolarMutexGuard aGuard;
DrawViewShell* pViewShell = GetViewShell();
VclPtr<vcl::Window> pWindow;
if (pViewShell)
pWindow = pViewShell->GetActiveWindow();
LokChartHelper aChartHelper(pViewShell->GetViewShell());
VclPtr<vcl::Window> pChartWindow = aChartHelper.GetWindow();
if (pChartWindow)
pWindow = pChartWindow;
return pWindow;
}
void SdXImpressDocument::setPartMode( int nPartMode )
{
DrawViewShell* pViewSh = GetViewShell();
if (!pViewSh)
return;
PageKind aPageKind( PageKind::Standard );
switch ( nPartMode )
{
case LOK_PARTMODE_SLIDES:
break;
case LOK_PARTMODE_NOTES:
aPageKind = PageKind::Notes;
break;
}
pViewSh->SetPageKind( aPageKind );
}
Size SdXImpressDocument::getDocumentSize()
{
DrawViewShell* pViewSh = GetViewShell();
if (!pViewSh)
return Size();
SdrView *pSdrView = pViewSh->GetView();
if (!pSdrView)
return Size();
SdrPageView* pCurPageView = pSdrView->GetSdrPageView();
if (!pCurPageView)
return Size();
Size aSize = pCurPageView->GetPageRect().GetSize();
// Convert the size in 100th mm to TWIP
// See paintTile above for further info.
return Size(convertMm100ToTwip(aSize.getWidth()), convertMm100ToTwip(aSize.getHeight()));
}
OUString SdXImpressDocument::getPostIts()
{
boost::property_tree::ptree aAnnotations;
// Return annotations on master pages too ?
const sal_uInt16 nMaxPages = mpDoc->GetPageCount();
SdPage* pPage;
for (sal_uInt16 nPage = 0; nPage < nMaxPages; ++nPage)
{
pPage = static_cast<SdPage*>(mpDoc->GetPage(nPage));
const sd::AnnotationVector& aPageAnnotations = pPage->getAnnotations();
for (const auto& aPageAnnotation : aPageAnnotations)
{
uno::Reference<office::XAnnotation> xAnnotation(aPageAnnotation);
boost::property_tree::ptree aAnnotation;
aAnnotation.put("id", sd::getAnnotationId(xAnnotation));
aAnnotation.put("author", xAnnotation->getAuthor());
aAnnotation.put("dateTime", utl::toISO8601(xAnnotation->getDateTime()));
uno::Reference<text::XText> xText(xAnnotation->getTextRange());
aAnnotation.put("text", xText->getString());
aAnnotation.put("parthash", OUString::number(pPage->GetHashCode()));
aAnnotations.push_back(std::make_pair("", aAnnotation));
}
}
boost::property_tree::ptree aTree;
aTree.add_child("comments", aAnnotations);
std::stringstream aStream;
boost::property_tree::write_json(aStream, aTree);
return OUString::fromUtf8(aStream.str().c_str());
}
void SdXImpressDocument::initializeForTiledRendering(const css::uno::Sequence<css::beans::PropertyValue>& rArguments)
{
SolarMutexGuard aGuard;
if (DrawViewShell* pViewShell = GetViewShell())
{
DrawView* pDrawView = pViewShell->GetDrawView();
for (sal_Int32 i = 0; i < rArguments.getLength(); ++i)
{
const beans::PropertyValue& rValue = rArguments[i];
if (rValue.Name == ".uno:ShowBorderShadow" && rValue.Value.has<bool>())
pDrawView->SetPageShadowVisible(rValue.Value.get<bool>());
else if (rValue.Name == ".uno:Author" && rValue.Value.has<OUString>())
pDrawView->SetAuthor(rValue.Value.get<OUString>());
}
// Disable comments if requested
SdOptions* pOptions = SD_MOD()->GetSdOptions(mpDoc->GetDocumentType());
pOptions->SetShowComments(comphelper::LibreOfficeKit::isTiledAnnotations());
pViewShell->SetRuler(false);
pViewShell->SetScrollBarsVisible(false);
if (sd::Window* pWindow = pViewShell->GetActiveWindow())
{
// get the full page size in pixels
pWindow->EnableMapMode();
Size aSize(pWindow->LogicToPixel(pDrawView->GetSdrPageView()->GetPage()->GetSize()));
// Disable map mode, so that it's possible to send mouse event
// coordinates in logic units
pWindow->EnableMapMode(false);
// arrange UI elements again with new view size
pViewShell->GetParentWindow()->SetSizePixel(aSize);
pViewShell->Resize();
}
// Forces all images to be swapped in synchronously, this
// ensures that images are available when paintTile is called
// (whereas with async loading images start being loaded after
// we have painted the tile, resulting in an invalidate, followed
// by the tile being rerendered - which is wasteful and ugly).
pDrawView->SetSwapAsynchron(false);
}
// when the "This document may contain formatting or content that cannot
// be saved..." dialog appears, it is auto-cancelled with tiled rendering,
// causing 'Save' being disabled; so let's always save to the original
// format
SvtSaveOptions().SetWarnAlienFormat(false);
}
void SdXImpressDocument::postKeyEvent(int nType, int nCharCode, int nKeyCode)
{
SolarMutexGuard aGuard;
VclPtr<vcl::Window> pWindow = getDocWindow();
if (!pWindow)
return;
LOKAsyncEventData* pLOKEv = new LOKAsyncEventData;
pLOKEv->mpWindow = pWindow;
switch (nType)
{
case LOK_KEYEVENT_KEYINPUT:
pLOKEv->mnEvent = VclEventId::WindowKeyInput;
break;
case LOK_KEYEVENT_KEYUP:
pLOKEv->mnEvent = VclEventId::WindowKeyUp;
break;
default:
assert(false);
}
pLOKEv->maKeyEvent = KeyEvent(nCharCode, nKeyCode, 0);
Application::PostUserEvent(Link<void*, void>(pLOKEv, ITiledRenderable::LOKPostAsyncEvent));
}
void SdXImpressDocument::postMouseEvent(int nType, int nX, int nY, int nCount, int nButtons, int nModifier)
{
SolarMutexGuard aGuard;
DrawViewShell* pViewShell = GetViewShell();
if (!pViewShell)
return;
double fScale = 1.0/TWIPS_PER_PIXEL;
// check if user hit a chart which is being edited by him
LokChartHelper aChartHelper(pViewShell->GetViewShell());
if (aChartHelper.postMouseEvent(nType, nX, nY,
nCount, nButtons, nModifier,
fScale, fScale))
return;
// check if the user hit a chart which is being edited by someone else
// and, if so, skip current mouse event
if (nType != LOK_MOUSEEVENT_MOUSEMOVE)
{
if (LokChartHelper::HitAny(Point(nX, nY)))
return;
}
LOKAsyncEventData* pLOKEv = new LOKAsyncEventData;
pLOKEv->mpWindow = pViewShell->GetActiveWindow();
switch (nType)
{
case LOK_MOUSEEVENT_MOUSEBUTTONDOWN:
pLOKEv->mnEvent = VclEventId::WindowMouseButtonDown;
break;
case LOK_MOUSEEVENT_MOUSEBUTTONUP:
pLOKEv->mnEvent = VclEventId::WindowMouseButtonUp;
break;
case LOK_MOUSEEVENT_MOUSEMOVE:
pLOKEv->mnEvent = VclEventId::WindowMouseMove;
break;
default:
assert(false);
}
const Point aPos(Point(convertTwipToMm100(nX), convertTwipToMm100(nY)));
pLOKEv->maMouseEvent = MouseEvent(aPos, nCount,
MouseEventModifiers::SIMPLECLICK,
nButtons, nModifier);
Application::PostUserEvent(Link<void*, void>(pLOKEv, ITiledRenderable::LOKPostAsyncEvent));
}
void SdXImpressDocument::setTextSelection(int nType, int nX, int nY)
{
SolarMutexGuard aGuard;
DrawViewShell* pViewShell = GetViewShell();
if (!pViewShell)
return;
LokChartHelper aChartHelper(pViewShell->GetViewShell());
if (aChartHelper.setTextSelection(nType, nX, nY))
return;
Point aPoint(convertTwipToMm100(nX), convertTwipToMm100(nY));
switch (nType)
{
case LOK_SETTEXTSELECTION_START:
pViewShell->SetCursorMm100Position(aPoint, /*bPoint=*/false, /*bClearMark=*/false);
break;
case LOK_SETTEXTSELECTION_END:
pViewShell->SetCursorMm100Position(aPoint, /*bPoint=*/true, /*bClearMark=*/false);
break;
case LOK_SETTEXTSELECTION_RESET:
pViewShell->SetCursorMm100Position(aPoint, /*bPoint=*/true, /*bClearMark=*/true);
break;
default:
assert(false);
break;
}
}
OString SdXImpressDocument::getTextSelection(const char* pMimeType, OString& rUsedMimeType)
{
SolarMutexGuard aGuard;
DrawViewShell* pViewShell = GetViewShell();
if (!pViewShell)
return OString();
return pViewShell->GetTextSelection(pMimeType, rUsedMimeType);
}
void SdXImpressDocument::setGraphicSelection(int nType, int nX, int nY)
{
SolarMutexGuard aGuard;
DrawViewShell* pViewShell = GetViewShell();
if (!pViewShell)
return;
double fScale = 1.0/TWIPS_PER_PIXEL;
LokChartHelper aChartHelper(pViewShell->GetViewShell());
if (aChartHelper.setGraphicSelection(nType, nX, nY, fScale, fScale))
return;
Point aPoint(convertTwipToMm100(nX), convertTwipToMm100(nY));
switch (nType)
{
case LOK_SETGRAPHICSELECTION_START:
pViewShell->SetGraphicMm100Position(/*bStart=*/true, aPoint);
break;
case LOK_SETGRAPHICSELECTION_END:
pViewShell->SetGraphicMm100Position(/*bStart=*/false, aPoint);
break;
default:
assert(false);
break;
}
}
void SdXImpressDocument::resetSelection()
{
SolarMutexGuard aGuard;
DrawViewShell* pViewShell = GetViewShell();
if (!pViewShell)
return;
SdrView* pSdrView = pViewShell->GetView();
if (!pSdrView)
return;
if (pSdrView->IsTextEdit())
{
// Reset the editeng selection.
pSdrView->UnmarkAll();
// Finish editing.
pSdrView->SdrEndTextEdit();
}
// Reset graphic selection.
pSdrView->UnmarkAll();
}
void SdXImpressDocument::setClipboard(const uno::Reference<datatransfer::clipboard::XClipboard>& xClipboard)
{
SolarMutexGuard aGuard;
DrawViewShell* pViewShell = GetViewShell();
if (!pViewShell)
return;
pViewShell->GetActiveWindow()->SetClipboard(xClipboard);
}
bool SdXImpressDocument::isMimeTypeSupported()
{
SolarMutexGuard aGuard;
DrawViewShell* pViewShell = GetViewShell();
if (!pViewShell)
return false;
TransferableDataHelper aDataHelper(TransferableDataHelper::CreateFromSystemClipboard(pViewShell->GetActiveWindow()));
return EditEngine::HasValidData(aDataHelper.GetTransferable());
}
Pointer SdXImpressDocument::getPointer()
{
SolarMutexGuard aGuard;
DrawViewShell* pViewShell = GetViewShell();
if (!pViewShell)
return Pointer();
Window* pWindow = pViewShell->GetActiveWindow();
if (!pWindow)
return Pointer();
return pWindow->GetPointer();
}
uno::Reference< i18n::XForbiddenCharacters > SdXImpressDocument::getForbiddenCharsTable()
{
uno::Reference< i18n::XForbiddenCharacters > xForb(mxForbiddenCharacters);
if( !xForb.is() )
mxForbiddenCharacters = xForb = new SdUnoForbiddenCharsTable( mpDoc );
return xForb;
}
void SdXImpressDocument::initializeDocument()
{
if( !mbClipBoard )
{
switch( mpDoc->GetPageCount() )
{
case 1:
{
// nasty hack to detect clipboard document
mbClipBoard = true;
break;
}
case 0:
{
mpDoc->CreateFirstPages();
mpDoc->StopWorkStartupDelay();
break;
}
}
}
}
SdrModel& SdXImpressDocument::getSdrModelFromUnoModel() const
{
OSL_ENSURE(GetDoc(), "No SdrModel in draw/Impress, should not happen");
return *GetDoc(); // TTTT should be reference
}
void SAL_CALL SdXImpressDocument::dispose()
{
if( !mbDisposed )
{
::SolarMutexGuard aGuard;
if( mpDoc )
{
EndListening( *mpDoc );
mpDoc = nullptr;
}
// Call the base class dispose() before setting the mbDisposed flag
// to true. The reason for this is that if close() has not yet been
// called this is done in SfxBaseModel::dispose(). At the end of
// that dispose() is called again. It is important to forward this
// second dispose() to the base class, too.
// As a consequence the following code has to be able to be run twice.
SfxBaseModel::dispose();
mbDisposed = true;
uno::Reference< container::XNameAccess > xLinks( mxLinks );
if( xLinks.is() )
{
uno::Reference< lang::XComponent > xComp( xLinks, uno::UNO_QUERY );
if( xComp.is() )
xComp->dispose();
xLinks = nullptr;
}
uno::Reference< drawing::XDrawPages > xDrawPagesAccess( mxDrawPagesAccess );
if( xDrawPagesAccess.is() )
{
uno::Reference< lang::XComponent > xComp( xDrawPagesAccess, uno::UNO_QUERY );
if( xComp.is() )
xComp->dispose();
xDrawPagesAccess = nullptr;
}
uno::Reference< drawing::XDrawPages > xMasterPagesAccess( mxMasterPagesAccess );
if( xDrawPagesAccess.is() )
{
uno::Reference< lang::XComponent > xComp( xMasterPagesAccess, uno::UNO_QUERY );
if( xComp.is() )
xComp->dispose();
xDrawPagesAccess = nullptr;
}
uno::Reference< container::XNameAccess > xLayerManager( mxLayerManager );
if( xLayerManager.is() )
{
uno::Reference< lang::XComponent > xComp( xLayerManager, uno::UNO_QUERY );
if( xComp.is() )
xComp->dispose();
xLayerManager = nullptr;
}
uno::Reference< container::XNameContainer > xCustomPresentationAccess( mxCustomPresentationAccess );
if( xCustomPresentationAccess.is() )
{
uno::Reference< lang::XComponent > xComp( xCustomPresentationAccess, uno::UNO_QUERY );
if( xComp.is() )
xComp->dispose();
xCustomPresentationAccess = nullptr;
}
mxDashTable = nullptr;
mxGradientTable = nullptr;
mxHatchTable = nullptr;
mxBitmapTable = nullptr;
mxTransGradientTable = nullptr;
mxMarkerTable = nullptr;
mxDrawingPool = nullptr;
}
}
// class SdDrawPagesAccess
SdDrawPagesAccess::SdDrawPagesAccess( SdXImpressDocument& rMyModel ) throw()
: mpModel( &rMyModel)
{
}
SdDrawPagesAccess::~SdDrawPagesAccess() throw()
{
}
// XIndexAccess
sal_Int32 SAL_CALL SdDrawPagesAccess::getCount()
{
::SolarMutexGuard aGuard;
if( nullptr == mpModel )
throw lang::DisposedException();
return mpModel->mpDoc->GetSdPageCount( PageKind::Standard );
}
uno::Any SAL_CALL SdDrawPagesAccess::getByIndex( sal_Int32 Index )
{
::SolarMutexGuard aGuard;
if( nullptr == mpModel )
throw lang::DisposedException();
uno::Any aAny;
if( (Index < 0) || (Index >= mpModel->mpDoc->GetSdPageCount( PageKind::Standard ) ) )
throw lang::IndexOutOfBoundsException();
SdPage* pPage = mpModel->mpDoc->GetSdPage( static_cast<sal_uInt16>(Index), PageKind::Standard );
if( pPage )
{
uno::Reference< drawing::XDrawPage > xDrawPage( pPage->getUnoPage(), uno::UNO_QUERY );
aAny <<= xDrawPage;
}
return aAny;
}
// XNameAccess
uno::Any SAL_CALL SdDrawPagesAccess::getByName( const OUString& aName )
{
::SolarMutexGuard aGuard;
if( nullptr == mpModel )
throw lang::DisposedException();
if( !aName.isEmpty() )
{
const sal_uInt16 nCount = mpModel->mpDoc->GetSdPageCount( PageKind::Standard );
sal_uInt16 nPage;
for( nPage = 0; nPage < nCount; nPage++ )
{
SdPage* pPage = mpModel->mpDoc->GetSdPage( nPage, PageKind::Standard );
if(nullptr == pPage)
continue;
if( aName == SdDrawPage::getPageApiName( pPage ) )
{
uno::Any aAny;
uno::Reference< drawing::XDrawPage > xDrawPage( pPage->getUnoPage(), uno::UNO_QUERY );
aAny <<= xDrawPage;
return aAny;
}
}
}
throw container::NoSuchElementException();
}
uno::Sequence< OUString > SAL_CALL SdDrawPagesAccess::getElementNames()
{
::SolarMutexGuard aGuard;
if( nullptr == mpModel )
throw lang::DisposedException();
const sal_uInt16 nCount = mpModel->mpDoc->GetSdPageCount( PageKind::Standard );
uno::Sequence< OUString > aNames( nCount );
OUString* pNames = aNames.getArray();
sal_uInt16 nPage;
for( nPage = 0; nPage < nCount; nPage++ )
{
SdPage* pPage = mpModel->mpDoc->GetSdPage( nPage, PageKind::Standard );
*pNames++ = SdDrawPage::getPageApiName( pPage );
}
return aNames;
}
sal_Bool SAL_CALL SdDrawPagesAccess::hasByName( const OUString& aName )
{
::SolarMutexGuard aGuard;
if( nullptr == mpModel )
throw lang::DisposedException();
const sal_uInt16 nCount = mpModel->mpDoc->GetSdPageCount( PageKind::Standard );
sal_uInt16 nPage;
for( nPage = 0; nPage < nCount; nPage++ )
{
SdPage* pPage = mpModel->mpDoc->GetSdPage( nPage, PageKind::Standard );
if(nullptr == pPage)
continue;
if( aName == SdDrawPage::getPageApiName( pPage ) )
return true;
}
return false;
}
// XElementAccess
uno::Type SAL_CALL SdDrawPagesAccess::getElementType()
{
return cppu::UnoType<drawing::XDrawPage>::get();
}
sal_Bool SAL_CALL SdDrawPagesAccess::hasElements()
{
return getCount() > 0;
}
// XDrawPages
/**
* Creates a new page with model at the specified position.
* @returns corresponding SdDrawPage
*/
uno::Reference< drawing::XDrawPage > SAL_CALL SdDrawPagesAccess::insertNewByIndex( sal_Int32 nIndex )
{
::SolarMutexGuard aGuard;
comphelper::ProfileZone aZone("insertNewByIndex");
if( nullptr == mpModel )
throw lang::DisposedException();
if( mpModel->mpDoc )
{
SdPage* pPage = mpModel->InsertSdPage( static_cast<sal_uInt16>(nIndex), false );
if( pPage )
{
uno::Reference< drawing::XDrawPage > xDrawPage( pPage->getUnoPage(), uno::UNO_QUERY );
return xDrawPage;
}
}
uno::Reference< drawing::XDrawPage > xDrawPage;
return xDrawPage;
}
/**
* Removes the specified SdDrawPage from the model and the internal list. It
* only works, if there is at least one *normal* page in the model after
* removing this page.
*/
void SAL_CALL SdDrawPagesAccess::remove( const uno::Reference< drawing::XDrawPage >& xPage )
{
::SolarMutexGuard aGuard;
if( nullptr == mpModel || mpModel->mpDoc == nullptr )
throw lang::DisposedException();
SdDrawDocument& rDoc = *mpModel->mpDoc;
sal_uInt16 nPageCount = rDoc.GetSdPageCount( PageKind::Standard );
if( nPageCount > 1 )
{
// get pPage from xPage and determine the Id (nPos ) afterwards
SdDrawPage* pSvxPage = SdDrawPage::getImplementation( xPage );
if( pSvxPage )
{
SdPage* pPage = static_cast<SdPage*>(pSvxPage->GetSdrPage());
if(pPage && ( pPage->GetPageKind() == PageKind::Standard ) )
{
sal_uInt16 nPage = pPage->GetPageNum();
SdPage* pNotesPage = static_cast< SdPage* >( rDoc.GetPage( nPage+1 ) );
bool bUndo = rDoc.IsUndoEnabled();
if( bUndo )
{
// Add undo actions and delete the pages. The order of adding
// the undo actions is important.
rDoc.BegUndo( SdResId( STR_UNDO_DELETEPAGES ) );
rDoc.AddUndo(rDoc.GetSdrUndoFactory().CreateUndoDeletePage(*pNotesPage));
rDoc.AddUndo(rDoc.GetSdrUndoFactory().CreateUndoDeletePage(*pPage));
}
rDoc.RemovePage( nPage ); // the page
rDoc.RemovePage( nPage ); // the notes page
if( bUndo )
{
rDoc.EndUndo();
}
else
{
delete pNotesPage;
delete pPage;
}
}
}
}
mpModel->SetModified();
}
// XServiceInfo
OUString SAL_CALL SdDrawPagesAccess::getImplementationName( )
{
return OUString( "SdDrawPagesAccess" );
}
sal_Bool SAL_CALL SdDrawPagesAccess::supportsService( const OUString& ServiceName )
{
return cppu::supportsService(this, ServiceName);
}
uno::Sequence< OUString > SAL_CALL SdDrawPagesAccess::getSupportedServiceNames( )
{
OUString aService( "com.sun.star.drawing.DrawPages" );
uno::Sequence< OUString > aSeq( &aService, 1 );
return aSeq;
}
// XComponent
void SAL_CALL SdDrawPagesAccess::dispose( )
{
mpModel = nullptr;
}
void SAL_CALL SdDrawPagesAccess::addEventListener( const uno::Reference< lang::XEventListener >& )
{
OSL_FAIL( "not implemented!" );
}
void SAL_CALL SdDrawPagesAccess::removeEventListener( const uno::Reference< lang::XEventListener >& )
{
OSL_FAIL( "not implemented!" );
}
// class SdMasterPagesAccess
SdMasterPagesAccess::SdMasterPagesAccess( SdXImpressDocument& rMyModel ) throw()
: mpModel(&rMyModel)
{
}
SdMasterPagesAccess::~SdMasterPagesAccess() throw()
{
}
// XComponent
void SAL_CALL SdMasterPagesAccess::dispose( )
{
mpModel = nullptr;
}
void SAL_CALL SdMasterPagesAccess::addEventListener( const uno::Reference< lang::XEventListener >& )
{
OSL_FAIL( "not implemented!" );
}
void SAL_CALL SdMasterPagesAccess::removeEventListener( const uno::Reference< lang::XEventListener >& )
{
OSL_FAIL( "not implemented!" );
}
// XIndexAccess
sal_Int32 SAL_CALL SdMasterPagesAccess::getCount()
{
::SolarMutexGuard aGuard;
if( nullptr == mpModel->mpDoc )
throw lang::DisposedException();
return mpModel->mpDoc->GetMasterSdPageCount(PageKind::Standard);
}
/**
* Provides a drawing::XDrawPage interface for accessing the Masterpage at the
* specified position in the model.
*/
uno::Any SAL_CALL SdMasterPagesAccess::getByIndex( sal_Int32 Index )
{
::SolarMutexGuard aGuard;
comphelper::ProfileZone aZone("SdMasterPagesAccess::getByIndex");
if( nullptr == mpModel )
throw lang::DisposedException();
uno::Any aAny;
if( (Index < 0) || (Index >= mpModel->mpDoc->GetMasterSdPageCount( PageKind::Standard ) ) )
throw lang::IndexOutOfBoundsException();
SdPage* pPage = mpModel->mpDoc->GetMasterSdPage( static_cast<sal_uInt16>(Index), PageKind::Standard );
if( pPage )
{
uno::Reference< drawing::XDrawPage > xDrawPage( pPage->getUnoPage(), uno::UNO_QUERY );
aAny <<= xDrawPage;
}
return aAny;
}
// XElementAccess
uno::Type SAL_CALL SdMasterPagesAccess::getElementType()
{
return cppu::UnoType<drawing::XDrawPage>::get();
}
sal_Bool SAL_CALL SdMasterPagesAccess::hasElements()
{
return getCount() > 0;
}
// XDrawPages
uno::Reference< drawing::XDrawPage > SAL_CALL SdMasterPagesAccess::insertNewByIndex( sal_Int32 nInsertPos )
{
::SolarMutexGuard aGuard;
if( nullptr == mpModel )
throw lang::DisposedException();
uno::Reference< drawing::XDrawPage > xDrawPage;
SdDrawDocument* pDoc = mpModel->mpDoc;
if( pDoc )
{
// calculate internal index and check for range errors
const sal_Int32 nMPageCount = pDoc->GetMasterPageCount();
nInsertPos = nInsertPos * 2 + 1;
if( nInsertPos < 0 || nInsertPos > nMPageCount )
nInsertPos = nMPageCount;
// now generate a unique name for the new masterpage
const OUString aStdPrefix( SdResId(STR_LAYOUT_DEFAULT_NAME) );
OUString aPrefix( aStdPrefix );
bool bUnique = true;
std::vector<OUString> aPageNames;
for (sal_Int32 nMaster = 1; nMaster < nMPageCount; ++nMaster)
{
const SdPage* pPage = static_cast<const SdPage*>(pDoc->GetMasterPage(static_cast<sal_uInt16>(nMaster)));
if (!pPage)
continue;
aPageNames.push_back(pPage->GetName());
if (aPageNames.back() == aPrefix)
bUnique = false;
}
sal_Int32 i = 0;
while (!bUnique)
{
aPrefix = aStdPrefix + " " + OUString::number(++i);
bUnique = std::find(aPageNames.begin(), aPageNames.end(), aPrefix) == aPageNames.end();
}
OUString aLayoutName( aPrefix );
aLayoutName += SD_LT_SEPARATOR;
aLayoutName += STR_LAYOUT_OUTLINE;
// create styles
static_cast<SdStyleSheetPool*>(pDoc->GetStyleSheetPool())->CreateLayoutStyleSheets( aPrefix );
// get the first page for initial size and border settings
SdPage* pPage = mpModel->mpDoc->GetSdPage( sal_uInt16(0), PageKind::Standard );
SdPage* pRefNotesPage = mpModel->mpDoc->GetSdPage( sal_uInt16(0), PageKind::Notes);
// create and insert new draw masterpage
SdPage* pMPage = mpModel->mpDoc->AllocSdPage(true);
pMPage->SetSize( pPage->GetSize() );
pMPage->SetBorder( pPage->GetLeftBorder(),
pPage->GetUpperBorder(),
pPage->GetRightBorder(),
pPage->GetLowerBorder() );
pMPage->SetLayoutName( aLayoutName );
pDoc->InsertMasterPage(pMPage, static_cast<sal_uInt16>(nInsertPos));
{
// ensure default MasterPage fill
pMPage->EnsureMasterPageDefaultBackground();
}
xDrawPage.set( pMPage->getUnoPage(), uno::UNO_QUERY );
// create and insert new notes masterpage
SdPage* pMNotesPage = mpModel->mpDoc->AllocSdPage(true);
pMNotesPage->SetSize( pRefNotesPage->GetSize() );
pMNotesPage->SetPageKind(PageKind::Notes);
pMNotesPage->SetBorder( pRefNotesPage->GetLeftBorder(),
pRefNotesPage->GetUpperBorder(),
pRefNotesPage->GetRightBorder(),
pRefNotesPage->GetLowerBorder() );
pMNotesPage->SetLayoutName( aLayoutName );
pDoc->InsertMasterPage(pMNotesPage, static_cast<sal_uInt16>(nInsertPos) + 1);
pMNotesPage->SetAutoLayout(AUTOLAYOUT_NOTES, true, true);
mpModel->SetModified();
}
return xDrawPage;
}
/**
* Removes the specified SdMasterPage from the model and the internal list. It
* only works, if there is no *normal* page using this page as MasterPage in
* the model.
*/
void SAL_CALL SdMasterPagesAccess::remove( const uno::Reference< drawing::XDrawPage >& xPage )
{
::SolarMutexGuard aGuard;
if( nullptr == mpModel || mpModel->mpDoc == nullptr )
throw lang::DisposedException();
SdDrawDocument& rDoc = *mpModel->mpDoc;
SdMasterPage* pSdPage = SdMasterPage::getImplementation( xPage );
if(pSdPage == nullptr)
return;
SdPage* pPage = dynamic_cast< SdPage* > (pSdPage->GetSdrPage());
DBG_ASSERT( pPage && pPage->IsMasterPage(), "SdMasterPage is not masterpage?");
if( !pPage || !pPage->IsMasterPage() || (mpModel->mpDoc->GetMasterPageUserCount(pPage) > 0))
return; //Todo: this should be excepted
// only standard pages can be removed directly
if( pPage->GetPageKind() == PageKind::Standard )
{
sal_uInt16 nPage = pPage->GetPageNum();
SdPage* pNotesPage = static_cast< SdPage* >( rDoc.GetMasterPage( nPage+1 ) );
bool bUndo = rDoc.IsUndoEnabled();
if( bUndo )
{
// Add undo actions and delete the pages. The order of adding
// the undo actions is important.
rDoc.BegUndo( SdResId( STR_UNDO_DELETEPAGES ) );
rDoc.AddUndo(rDoc.GetSdrUndoFactory().CreateUndoDeletePage(*pNotesPage));
rDoc.AddUndo(rDoc.GetSdrUndoFactory().CreateUndoDeletePage(*pPage));
}
// remove both pages
rDoc.RemoveMasterPage( nPage );
rDoc.RemoveMasterPage( nPage );
if( bUndo )
{
rDoc.EndUndo();
}
else
{
delete pNotesPage;
delete pPage;
}
}
}
// XServiceInfo
OUString SAL_CALL SdMasterPagesAccess::getImplementationName( )
{
return OUString( "SdMasterPagesAccess" );
}
sal_Bool SAL_CALL SdMasterPagesAccess::supportsService( const OUString& ServiceName )
{
return cppu::supportsService(this, ServiceName);
}
uno::Sequence< OUString > SAL_CALL SdMasterPagesAccess::getSupportedServiceNames( )
{
OUString aService( "com.sun.star.drawing.MasterPages" );
uno::Sequence< OUString > aSeq( &aService, 1 );
return aSeq;
}
// class SdDocLinkTargets
SdDocLinkTargets::SdDocLinkTargets( SdXImpressDocument& rMyModel ) throw()
: mpModel( &rMyModel )
{
}
SdDocLinkTargets::~SdDocLinkTargets() throw()
{
}
// XComponent
void SAL_CALL SdDocLinkTargets::dispose( )
{
mpModel = nullptr;
}
void SAL_CALL SdDocLinkTargets::addEventListener( const uno::Reference< lang::XEventListener >& )
{
OSL_FAIL( "not implemented!" );
}
void SAL_CALL SdDocLinkTargets::removeEventListener( const uno::Reference< lang::XEventListener >& )
{
OSL_FAIL( "not implemented!" );
}
// XNameAccess
uno::Any SAL_CALL SdDocLinkTargets::getByName( const OUString& aName )
{
::SolarMutexGuard aGuard;
if( nullptr == mpModel )
throw lang::DisposedException();
SdPage* pPage = FindPage( aName );
if( pPage == nullptr )
throw container::NoSuchElementException();
uno::Any aAny;
uno::Reference< beans::XPropertySet > xProps( pPage->getUnoPage(), uno::UNO_QUERY );
if( xProps.is() )
aAny <<= xProps;
return aAny;
}
uno::Sequence< OUString > SAL_CALL SdDocLinkTargets::getElementNames()
{
::SolarMutexGuard aGuard;
if( nullptr == mpModel )
throw lang::DisposedException();
SdDrawDocument* pDoc = mpModel->GetDoc();
if( pDoc == nullptr )
{
uno::Sequence< OUString > aSeq;
return aSeq;
}
if( pDoc->GetDocumentType() == DocumentType::Draw )
{
const sal_uInt16 nMaxPages = pDoc->GetSdPageCount( PageKind::Standard );
const sal_uInt16 nMaxMasterPages = pDoc->GetMasterSdPageCount( PageKind::Standard );
uno::Sequence< OUString > aSeq( nMaxPages + nMaxMasterPages );
OUString* pStr = aSeq.getArray();
sal_uInt16 nPage;
// standard pages
for( nPage = 0; nPage < nMaxPages; nPage++ )
*pStr++ = pDoc->GetSdPage( nPage, PageKind::Standard )->GetName();
// master pages
for( nPage = 0; nPage < nMaxMasterPages; nPage++ )
*pStr++ = pDoc->GetMasterSdPage( nPage, PageKind::Standard )->GetName();
return aSeq;
}
else
{
const sal_uInt16 nMaxPages = pDoc->GetPageCount();
const sal_uInt16 nMaxMasterPages = pDoc->GetMasterPageCount();
uno::Sequence< OUString > aSeq( nMaxPages + nMaxMasterPages );
OUString* pStr = aSeq.getArray();
sal_uInt16 nPage;
// standard pages
for( nPage = 0; nPage < nMaxPages; nPage++ )
*pStr++ = static_cast<SdPage*>(pDoc->GetPage( nPage ))->GetName();
// master pages
for( nPage = 0; nPage < nMaxMasterPages; nPage++ )
*pStr++ = static_cast<SdPage*>(pDoc->GetMasterPage( nPage ))->GetName();
return aSeq;
}
}
sal_Bool SAL_CALL SdDocLinkTargets::hasByName( const OUString& aName )
{
::SolarMutexGuard aGuard;
if( nullptr == mpModel )
throw lang::DisposedException();
return FindPage( aName ) != nullptr;
}
// container::XElementAccess
uno::Type SAL_CALL SdDocLinkTargets::getElementType()
{
return cppu::UnoType<beans::XPropertySet>::get();
}
sal_Bool SAL_CALL SdDocLinkTargets::hasElements()
{
::SolarMutexGuard aGuard;
if( nullptr == mpModel )
throw lang::DisposedException();
return mpModel->GetDoc() != nullptr;
}
SdPage* SdDocLinkTargets::FindPage( const OUString& rName ) const
{
SdDrawDocument* pDoc = mpModel->GetDoc();
if( pDoc == nullptr )
return nullptr;
const sal_uInt16 nMaxPages = pDoc->GetPageCount();
const sal_uInt16 nMaxMasterPages = pDoc->GetMasterPageCount();
sal_uInt16 nPage;
SdPage* pPage;
const bool bDraw = pDoc->GetDocumentType() == DocumentType::Draw;
// standard pages
for( nPage = 0; nPage < nMaxPages; nPage++ )
{
pPage = static_cast<SdPage*>(pDoc->GetPage( nPage ));
if( (pPage->GetName() == rName) && (!bDraw || (pPage->GetPageKind() == PageKind::Standard)) )
return pPage;
}
// master pages
for( nPage = 0; nPage < nMaxMasterPages; nPage++ )
{
pPage = static_cast<SdPage*>(pDoc->GetMasterPage( nPage ));
if( (pPage->GetName() == rName) && (!bDraw || (pPage->GetPageKind() == PageKind::Standard)) )
return pPage;
}
return nullptr;
}
// XServiceInfo
OUString SAL_CALL SdDocLinkTargets::getImplementationName()
{
return OUString( "SdDocLinkTargets" );
}
sal_Bool SAL_CALL SdDocLinkTargets::supportsService( const OUString& ServiceName )
{
return cppu::supportsService( this, ServiceName );
}
uno::Sequence< OUString > SAL_CALL SdDocLinkTargets::getSupportedServiceNames()
{
const OUString aSN( "com.sun.star.document.LinkTargets" );
uno::Sequence< OUString > aSeq( &aSN, 1 );
return aSeq;
}
rtl::Reference< SdXImpressDocument > SdXImpressDocument::GetModel( SdDrawDocument const & rDocument )
{
rtl::Reference< SdXImpressDocument > xRet;
::sd::DrawDocShell* pDocShell(rDocument.GetDocSh());
if( pDocShell )
{
uno::Reference<frame::XModel> xModel(pDocShell->GetModel());
xRet.set( dynamic_cast< SdXImpressDocument* >( xModel.get() ) );
}
return xRet;
}
void NotifyDocumentEvent( SdDrawDocument const & rDocument, const OUString& rEventName )
{
rtl::Reference< SdXImpressDocument > xModel( SdXImpressDocument::GetModel( rDocument ) );
if( xModel.is() )
{
uno::Reference< uno::XInterface > xSource( static_cast<uno::XWeak*>( xModel.get() ) );
css::document::EventObject aEvent( xSource, rEventName );
xModel->notifyEvent(aEvent );
}
}
void NotifyDocumentEvent( SdDrawDocument const & rDocument, const OUString& rEventName, const uno::Reference< uno::XInterface >& xSource )
{
rtl::Reference< SdXImpressDocument > xModel( SdXImpressDocument::GetModel( rDocument ) );
if( xModel.is() )
{
css::document::EventObject aEvent( xSource, rEventName );
xModel->notifyEvent(aEvent );
}
}
/* vim:set shiftwidth=4 softtabstop=4 expandtab: */
↑ V560 A part of conditional expression is always true: mpDoc.
↑ V572 It is odd that the object which was created using 'new' operator is immediately cast to another type.
↑ V547 Expression 'mpDoc' is always true.
↑ V547 Expression 'mpDoc' is always true.
↑ V1019 Compound assignment expression 'Arguments[0] >>= arg' is used inside condition.
↑ V560 A part of conditional expression is always true: mpDoc.
↑ V560 A part of conditional expression is always true: mpDoc.
↑ V560 A part of conditional expression is always true: mpDoc.
↑ V1004 The 'pViewShell' pointer was used unsafely after it was verified against nullptr. Check lines: 2348, 2351.
↑ V547 Expression 'mpDoc' is always true.