/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
/*
 * This file is part of the LibreOffice project.
 *
 * This Source Code Form is subject to the terms of the Mozilla Public
 * License, v. 2.0. If a copy of the MPL was not distributed with this
 * file, You can obtain one at http://mozilla.org/MPL/2.0/.
 *
 * This file incorporates work covered by the following license notice:
 *
 *   Licensed to the Apache Software Foundation (ASF) under one or more
 *   contributor license agreements. See the NOTICE file distributed
 *   with this work for additional information regarding copyright
 *   ownership. The ASF licenses this file to you under the Apache
 *   License, Version 2.0 (the "License"); you may not use this file
 *   except in compliance with the License. You may obtain a copy of
 *   the License at http://www.apache.org/licenses/LICENSE-2.0 .
 */
 
#include <sal/config.h>
 
#include <com/sun/star/lang/IndexOutOfBoundsException.hpp>
#include <com/sun/star/lang/ServiceNotRegisteredException.hpp>
#include <com/sun/star/lang/NoSupportException.hpp>
#include <com/sun/star/drawing/XShape.hpp>
#include <vcl/svapp.hxx>
#include <svl/itempool.hxx>
#include <svl/itemprop.hxx>
#include <svtools/unoevent.hxx>
#include <comphelper/sequence.hxx>
#include <cppuhelper/supportsservice.hxx>
 
#include <cppuhelper/implbase.hxx>
#include <svx/unofill.hxx>
#include <editeng/unonrule.hxx>
#include <svtools/unoimap.hxx>
#include <sfx2/event.hxx>
#include <svx/fmdpage.hxx>
#include <svx/fmmodel.hxx>
#include <svx/fmpage.hxx>
#include <svx/unoapi.hxx>
 
#include <svx/svdmodel.hxx>
#include <svx/globl3d.hxx>
#include <svx/svdtypes.hxx>
#include <svx/unoprov.hxx>
#include <svx/unopage.hxx>
#include <editeng/unofield.hxx>
#include <svx/unomod.hxx>
#include <svx/unomodel.hxx>
#include <svx/svdobj.hxx>
#include <svx/svdpage.hxx>
#include <svx/unoshape.hxx>
#include <svx/xmlgrhlp.hxx>
 
#include <com/sun/star/text/textfield/Type.hpp>
 
//-
 
using namespace ::com::sun::star;
 
//-
 
#define QUERYINT( xint ) \
    if( rType == cppu::UnoType<xint>::get() ) \
        aAny <<= uno::Reference< xint >(this)
 
//-
 
class SvxUnoDrawPagesAccess : public ::cppu::WeakImplHelper< css::drawing::XDrawPages, css::lang::XServiceInfo >
{
private:
    SvxUnoDrawingModel& mrModel;
 
public:
    explicit SvxUnoDrawPagesAccess( SvxUnoDrawingModel& rMyModel ) throw();
 
    // XDrawPages
    virtual css::uno::Reference< css::drawing::XDrawPage > SAL_CALL insertNewByIndex( sal_Int32 nIndex ) override;
    virtual void SAL_CALL remove( const css::uno::Reference< css::drawing::XDrawPage >& xPage ) override;
 
    // XIndexAccess
    virtual sal_Int32 SAL_CALL getCount() override ;
    virtual css::uno::Any SAL_CALL getByIndex( sal_Int32 Index ) override;
 
    // XElementAccess
    virtual css::uno::Type SAL_CALL getElementType() override;
    virtual sal_Bool SAL_CALL hasElements() override;
 
    // XServiceInfo
    virtual OUString SAL_CALL getImplementationName(  ) override;
    virtual sal_Bool SAL_CALL supportsService( const OUString& ServiceName ) override;
    virtual css::uno::Sequence< OUString > SAL_CALL getSupportedServiceNames(  ) override;
};
//-
 
static const SvEventDescription* ImplGetSupportedMacroItems()
{
    static const SvEventDescription aMacroDescriptionsImpl[] =
    {
        { SvMacroItemId::OnMouseOver, "OnMouseOver" },
        { SvMacroItemId::OnMouseOut,  "OnMouseOut" },
        { SvMacroItemId::NONE, nullptr }
    };
 
    return aMacroDescriptionsImpl;
}
 
//-
 
/** fills the given EventObject from the given SdrHint.
    @returns
        true    if the SdrHint could be translated to an EventObject<br>
        false   if not
*/
bool SvxUnoDrawMSFactory::createEvent( const SdrModel* pDoc, const SdrHint* pSdrHint, css::document::EventObject& aEvent )
{
    const SdrObject* pObj = nullptr;
    const SdrPage* pPage = nullptr;
 
    switch( pSdrHint->GetKind() )
    {
//              case SdrHintKind::LayerChange:             // layer definition changed
//              case SdrHintKind::LayerOrderChange:        // layer order changed (Insert/Remove/ChangePos)
//              case HINT_LAYERSETCHG:          // layer set changed
//              case HINT_LAYERSETORDERCHG:     // layer set order changed (Insert/Remove/ChangePos)
 
//      case HINT_PAGECHG:              // page changed
//          aEvent.EventName = "PageModified";
//          pPage = pSdrHint->GetPage();
//          break;
        case SdrHintKind::PageOrderChange:         // draw or master page order changed (Insert/Remove/ChangePos)
            aEvent.EventName = "PageOrderModified";
            pPage = pSdrHint->GetPage();
            break;
        case SdrHintKind::ObjectChange:               // object changed
            aEvent.EventName = "ShapeModified";
            pObj = pSdrHint->GetObject();
            break;
        case SdrHintKind::ObjectInserted:          // add new draw object
            aEvent.EventName = "ShapeInserted";
            pObj = pSdrHint->GetObject();
            break;
        case SdrHintKind::ObjectRemoved:           // removed draw object from list
            aEvent.EventName = "ShapeRemoved";
            pObj = pSdrHint->GetObject();
            break;
//                SdrHintKind::DefaultTabChange,   // default tab width changed
//                SdrHintKind::DefaultFontHeightChange,   // default FontHeight changed
//                SdrHintKind::SwitchToPage,    // #94278# UNDO/REDO at an object evtl. on another page
//                HINT_OBJLISTCLEAR     // Is called before an SdrObjList will be cleared
        default:
            return false;
    }
 
    if( pObj )
        aEvent.Source = const_cast<SdrObject*>(pObj)->getUnoShape();
    else if( pPage )
        aEvent.Source = const_cast<SdrPage*>(pPage)->getUnoPage();
    else
        aEvent.Source = const_cast<SdrModel*>(pDoc)->getUnoModel();
 
    return true;
}
 
namespace {
 
css::uno::Reference<css::uno::XInterface> create(
    OUString const & rServiceSpecifier, OUString const & referer)
{
    if( rServiceSpecifier.startsWith("com.sun.star.drawing.") )
    {
        sal_uInt32 nType = UHashMap::getId( rServiceSpecifier );
        if( nType != UHASHMAP_NOTFOUND )
        {
            sal_uInt16 nT = static_cast<sal_uInt16>(nType & ~E3D_INVENTOR_FLAG);
            SdrInventor nI = (nType & E3D_INVENTOR_FLAG) ? SdrInventor::E3d : SdrInventor::Default;
 
            return uno::Reference< uno::XInterface >( static_cast<drawing::XShape*>(SvxDrawPage::CreateShapeByTypeAndInventor( nT, nI, nullptr, nullptr, referer )) );
        }
    }
    else if (rServiceSpecifier == "com.sun.star.document.ImportGraphicStorageHandler")
    {
        rtl::Reference<SvXMLGraphicHelper> pGraphicHelper = SvXMLGraphicHelper::Create( SvXMLGraphicHelperMode::Read );
        uno::Reference< uno::XInterface> xRet( static_cast< ::cppu::OWeakObject* >( pGraphicHelper.get() ) );
        return xRet;
    }
 
    uno::Reference< uno::XInterface > xRet( SvxUnoDrawMSFactory::createTextField( rServiceSpecifier ) );
    if( !xRet.is() )
        throw lang::ServiceNotRegisteredException("unknown service: " + rServiceSpecifier);
 
    return xRet;
}
 
}
 
uno::Reference< uno::XInterface > SAL_CALL SvxUnoDrawMSFactory::createInstance( const OUString& rServiceSpecifier )
{
    return create(rServiceSpecifier, "");
}
 
uno::Reference< uno::XInterface > SvxUnoDrawMSFactory::createTextField( const OUString& ServiceSpecifier )
{
    return SvxUnoTextCreateTextField( ServiceSpecifier );
}
 
uno::Reference< uno::XInterface > SAL_CALL SvxUnoDrawMSFactory::createInstanceWithArguments( const OUString& ServiceSpecifier, const uno::Sequence< css::uno::Any >& Arguments )
{
    OUString arg;
    if ((ServiceSpecifier == "com.sun.star.drawing.GraphicObjectShape"
         || ServiceSpecifier == "com.sun.star.drawing.MediaShape")
        && Arguments.getLength() == 1 && (Arguments[0] >>= arg))
    {
        return create(ServiceSpecifier, arg);
    }
    throw lang::NoSupportException();
}
 
uno::Sequence< OUString > SAL_CALL SvxUnoDrawMSFactory::getAvailableServiceNames()
{
    return UHashMap::getServiceNames();
}
 
uno::Sequence< OUString > SvxUnoDrawMSFactory::concatServiceNames( uno::Sequence< OUString >& rServices1, uno::Sequence< OUString >& rServices2 ) throw()
{
    const sal_Int32 nLen1 = rServices1.getLength();
    const sal_Int32 nLen2 = rServices2.getLength();
 
    uno::Sequence< OUString > aSeq( nLen1+nLen2 );
    OUString* pStrings = aSeq.getArray();
 
    sal_Int32 nIdx;
    OUString* pStringDst = pStrings;
    const OUString* pStringSrc = rServices1.getArray();
 
    for( nIdx = 0; nIdx < nLen1; nIdx++ )
        *pStringDst++ = *pStringSrc++;
 
    pStringSrc = rServices2.getArray();
 
    for( nIdx = 0; nIdx < nLen2; nIdx++ )
        *pStringDst++ = *pStringSrc++;
 
    return aSeq;
}
 
SdrModel& SvxUnoDrawingModel::getSdrModelFromUnoModel() const
{
    OSL_ENSURE(mpDoc, "No SdrModel in UnoDrawingModel, should not happen");
    return *mpDoc;
}
 
SvxUnoDrawingModel::SvxUnoDrawingModel(SdrModel* pDoc) throw()
:   SfxBaseModel(nullptr),
    SvxFmMSFactory(),
    css::drawing::XDrawPagesSupplier(),
    css::lang::XServiceInfo(),
    css::ucb::XAnyCompareFactory(),
    mpDoc(pDoc),
    mxDrawPagesAccess(),
    mxDashTable(),
    mxGradientTable(),
    mxHatchTable(),
    mxBitmapTable(),
    mxTransGradientTable(),
    mxMarkerTable(),
    maTypeSequence()
{
}
 
SvxUnoDrawingModel::~SvxUnoDrawingModel() throw()
{
}
 
uno::Any SAL_CALL SvxUnoDrawingModel::queryInterface( const uno::Type & rType )
{
    uno::Any aAny;
 
    QUERYINT(lang::XServiceInfo);
    else QUERYINT(lang::XMultiServiceFactory);
    else QUERYINT(drawing::XDrawPagesSupplier);
    else QUERYINT(css::ucb::XAnyCompareFactory);
    else
        return SfxBaseModel::queryInterface( rType );
 
    return aAny;
}
 
void SAL_CALL SvxUnoDrawingModel::acquire() throw ( )
{
    SfxBaseModel::acquire();
}
 
void SAL_CALL SvxUnoDrawingModel::release() throw ( )
{
    SfxBaseModel::release();
}
 
// XTypeProvider
uno::Sequence< uno::Type > SAL_CALL SvxUnoDrawingModel::getTypes(  )
{
    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 = 4;      // !DANGER! Keep this updated!
 
        maTypeSequence.realloc(  nBaseTypes + nOwnTypes );
        uno::Type* pTypes = maTypeSequence.getArray();
 
        *pTypes++ = cppu::UnoType<lang::XServiceInfo>::get();
        *pTypes++ = cppu::UnoType<lang::XMultiServiceFactory>::get();
        *pTypes++ = cppu::UnoType<drawing::XDrawPagesSupplier>::get();
        *pTypes++ = cppu::UnoType<css::ucb::XAnyCompareFactory>::get();
 
        for( sal_Int32 nType = 0; nType < nBaseTypes; nType++ )
            *pTypes++ = *pBaseTypes++;
    }
 
    return maTypeSequence;
}
 
uno::Sequence< sal_Int8 > SAL_CALL SvxUnoDrawingModel::getImplementationId(  )
{
    return css::uno::Sequence<sal_Int8>();
}
 
void SAL_CALL SvxUnoDrawingModel::lockControllers(  )
{
    if( mpDoc )
        mpDoc->setLock(true);
}
 
void SAL_CALL SvxUnoDrawingModel::unlockControllers(  )
{
    if( mpDoc && mpDoc->isLocked() )
    {
        mpDoc->setLock(false);
    }
}
 
sal_Bool SAL_CALL SvxUnoDrawingModel::hasControllersLocked(  )
{
    return mpDoc && mpDoc->isLocked();
}
 
// XDrawPagesSupplier
uno::Reference< drawing::XDrawPages > SAL_CALL SvxUnoDrawingModel::getDrawPages()
{
    ::SolarMutexGuard aGuard;
 
    uno::Reference< drawing::XDrawPages >  xDrawPages( mxDrawPagesAccess );
 
    if( !xDrawPages.is() )
        mxDrawPagesAccess = xDrawPages = static_cast<drawing::XDrawPages*>(new SvxUnoDrawPagesAccess(*this));
 
    return xDrawPages;
}
 
// XMultiServiceFactory ( SvxFmMSFactory )
uno::Reference< uno::XInterface > SAL_CALL SvxUnoDrawingModel::createInstance( const OUString& aServiceSpecifier )
{
    ::SolarMutexGuard aGuard;
 
    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.image.ImageMapRectangleObject" )
    {
        return SvUnoImageMapRectangleObject_createInstance( ImplGetSupportedMacroItems() );
    }
 
    if ( aServiceSpecifier == "com.sun.star.image.ImageMapCircleObject" )
    {
        return SvUnoImageMapCircleObject_createInstance( ImplGetSupportedMacroItems() );
    }
 
    if ( aServiceSpecifier == "com.sun.star.image.ImageMapPolygonObject" )
    {
        return SvUnoImageMapPolygonObject_createInstance( ImplGetSupportedMacroItems() );
    }
 
    if( aServiceSpecifier == "com.sun.star.text.TextField.DateTime" )
    {
        return static_cast<cppu::OWeakObject *>(new SvxUnoTextField(text::textfield::Type::DATE));
    }
 
    uno::Reference< uno::XInterface > xRet;
 
    const OUString aPackagePrefix( "com.sun.star.presentation." );
    if( aServiceSpecifier.startsWith( aPackagePrefix ) )
    {
        SvxShape* pShape = nullptr;
 
        sal_uInt16 nType = OBJ_TEXT;
        OUString aTypeName = aServiceSpecifier.copy( aPackagePrefix.getLength() );
        // create a shape wrapper
        if( aTypeName.startsWith("TitleTextShape") )
        {
            nType = OBJ_TEXT;
        }
        else if( aTypeName.startsWith( "OutlinerShape" ) )
        {
            nType = OBJ_TEXT;
        }
        else if( aTypeName.startsWith( "SubtitleShape" ) )
        {
            nType = OBJ_TEXT;
        }
        else if( aTypeName.startsWith( "GraphicObjectShape" ) )
        {
            nType = OBJ_GRAF;
        }
        else if( aTypeName.startsWith( "PageShape" ) )
        {
            nType = OBJ_PAGE;
        }
        else if( aTypeName.startsWith( "OLE2Shape" ) )
        {
            nType = OBJ_OLE2;
        }
        else if( aTypeName.startsWith( "ChartShape" ) )
        {
            nType = OBJ_OLE2;
        }
        else if( aTypeName.startsWith( "OrgChartShape" ) )
        {
            nType = OBJ_OLE2;
        }
        else if( aTypeName.startsWith( "NotesShape" ) )
        {
            nType = OBJ_TEXT;
        }
        else if( aTypeName.startsWith( "HandoutShape" ) )
        {
            nType = OBJ_PAGE;
        }
        else if( aTypeName.startsWith( "FooterShape" ) )
        {
            nType = OBJ_TEXT;
        }
        else if( aTypeName.startsWith( "HeaderShape" ) )
        {
            nType = OBJ_TEXT;
        }
        else if( aTypeName.startsWith( "SlideNumberShape" ) )
        {
            nType = OBJ_TEXT;
        }
        else if( aTypeName.startsWith( "DateTimeShape" ) )
        {
            nType = OBJ_TEXT;
        }
        else if( aTypeName.startsWith( "TableShape" ) )
        {
            nType = OBJ_TABLE;
        }
        else
        {
            throw lang::ServiceNotRegisteredException();
        }
 
        // create the API wrapper
        pShape = CreateSvxShapeByTypeAndInventor( nType, SdrInventor::Default, "" );
 
        // set shape type
        if( pShape )
            pShape->SetShapeType(aServiceSpecifier);
 
        xRet = static_cast<uno::XWeak*>(pShape);
    }
    else
    {
        xRet = SvxFmMSFactory::createInstance( aServiceSpecifier );
    }
 
    return xRet;
}
 
uno::Sequence< OUString > SAL_CALL SvxUnoDrawingModel::getAvailableServiceNames()
{
    const uno::Sequence< OUString > aSNS_ORG( SvxFmMSFactory::getAvailableServiceNames() );
 
    uno::Sequence< OUString > aSNS( 21 );
 
    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.image.ImageMapRectangleObject";
    aSNS[i++] = "com.sun.star.image.ImageMapCircleObject";
    aSNS[i++] = "com.sun.star.image.ImageMapPolygonObject";
 
    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";
 
    DBG_ASSERT( i == aSNS.getLength(), "Sequence overrun!" );
 
    return comphelper::concatSequences( aSNS_ORG, aSNS );
}
 
// lang::XServiceInfo
OUString SAL_CALL SvxUnoDrawingModel::getImplementationName()
{
    return OUString("SvxUnoDrawingModel");
}
 
sal_Bool SAL_CALL SvxUnoDrawingModel::supportsService( const OUString& ServiceName )
{
    return cppu::supportsService( this, ServiceName );
}
 
uno::Sequence< OUString > SAL_CALL SvxUnoDrawingModel::getSupportedServiceNames()
{
    OUString aSN("com.sun.star.drawing.DrawingDocument");
    uno::Sequence< OUString > aSeq( &aSN, 1 );
    return aSeq;
}
 
// XAnyCompareFactory
uno::Reference< css::ucb::XAnyCompare > SAL_CALL SvxUnoDrawingModel::createAnyCompareByName( const OUString& )
{
    return SvxCreateNumRuleCompare();
}
 
SvxUnoDrawPagesAccess::SvxUnoDrawPagesAccess( SvxUnoDrawingModel& rMyModel )  throw()
:   mrModel(rMyModel)
{
}
 
// XIndexAccess
sal_Int32 SAL_CALL SvxUnoDrawPagesAccess::getCount()
{
    ::SolarMutexGuard aGuard;
 
    sal_Int32 nCount = 0;
 
    if( mrModel.mpDoc )
        nCount = mrModel.mpDoc->GetPageCount();
 
    return nCount;
}
 
uno::Any SAL_CALL SvxUnoDrawPagesAccess::getByIndex( sal_Int32 Index )
{
    ::SolarMutexGuard aGuard;
 
    uno::Any aAny;
 
    if( mrModel.mpDoc )
    {
        if( (Index < 0) || (Index >= mrModel.mpDoc->GetPageCount() ) )
            throw lang::IndexOutOfBoundsException();
 
        SdrPage* pPage = mrModel.mpDoc->GetPage( static_cast<sal_uInt16>(Index) );
        if( pPage )
        {
            uno::Reference< uno::XInterface > xPage( pPage->mxUnoPage );
 
            if( !xPage.is() )
            {
                if( dynamic_cast<FmFormModel*>( mrModel.mpDoc )  )
                    xPage = static_cast<drawing::XDrawPage*>(new SvxFmDrawPage( pPage ));
                else
                    xPage = static_cast<drawing::XDrawPage*>(new SvxDrawPage( pPage ));
 
                pPage->mxUnoPage = xPage;
            }
 
            aAny <<= xPage;
        }
    }
    return aAny;
}
 
// XElementAccess
uno::Type SAL_CALL SvxUnoDrawPagesAccess::getElementType()
{
    return cppu::UnoType<drawing::XDrawPage>::get();
}
 
sal_Bool SAL_CALL SvxUnoDrawPagesAccess::hasElements()
{
    return getCount() > 0;
}
 
// XDrawPages
 
// create a new page with model at given position
// and return corresponding SdDrawPage
uno::Reference< drawing::XDrawPage > SAL_CALL SvxUnoDrawPagesAccess::insertNewByIndex( sal_Int32 nIndex )
{
    ::SolarMutexGuard aGuard;
 
    uno::Reference< drawing::XDrawPage > xDrawPage;
 
    if( mrModel.mpDoc )
    {
        SdrPage* pPage;
 
        if( dynamic_cast<FmFormModel*>( mrModel.mpDoc )  )
            pPage = new FmFormPage(*static_cast<FmFormModel*>(mrModel.mpDoc));
        else
            pPage = new SdrPage(*mrModel.mpDoc);
 
        mrModel.mpDoc->InsertPage( pPage, static_cast<sal_uInt16>(nIndex) );
        xDrawPage.set( pPage->getUnoPage(), uno::UNO_QUERY );
    }
 
    return xDrawPage;
}
 
void SAL_CALL SvxUnoDrawPagesAccess::remove( const uno::Reference< drawing::XDrawPage >& xPage )
{
    ::SolarMutexGuard aGuard;
 
    sal_uInt16 nPageCount = mrModel.mpDoc->GetPageCount();
    if( nPageCount > 1 )
    {
        // get pPage from xPage and get Id (nPos)
        SvxDrawPage* pSvxPage = SvxDrawPage::getImplementation( xPage );
        if( pSvxPage )
        {
            SdrPage* pPage = pSvxPage->GetSdrPage();
            if(pPage)
            {
                sal_uInt16 nPage = pPage->GetPageNum();
                mrModel.mpDoc->DeletePage( nPage );
            }
        }
    }
}
 
// XServiceInfo
 
OUString SAL_CALL SvxUnoDrawPagesAccess::getImplementationName(  )
{
    return OUString( "SvxUnoDrawPagesAccess" );
}
 
sal_Bool SAL_CALL SvxUnoDrawPagesAccess::supportsService( const OUString& ServiceName )
{
    return cppu::supportsService(this, ServiceName);
}
 
uno::Sequence< OUString > SAL_CALL SvxUnoDrawPagesAccess::getSupportedServiceNames(  )
{
    OUString aService( "com.sun.star.drawing.DrawPages" );
    uno::Sequence< OUString > aSeq( &aService, 1 );
    return aSeq;
}
 
css::uno::Reference< css::container::XIndexReplace > SvxCreateNumRule(SdrModel* pModel)
{
    const SvxNumRule* pDefaultRule = nullptr;
    if( pModel )
    {
        const SvxNumBulletItem* pItem = pModel->GetItemPool().GetSecondaryPool()->GetPoolDefaultItem(EE_PARA_NUMBULLET);
        if( pItem )
        {
            pDefaultRule = pItem->GetNumRule();
        }
    }
 
    if( pDefaultRule )
    {
        return SvxCreateNumRule( pDefaultRule );
    }
    else
    {
        SvxNumRule aTempRule( SvxNumRuleFlags::NONE, 10, false );
        return SvxCreateNumRule( &aTempRule );
    }
}
 
 
/* vim:set shiftwidth=4 softtabstop=4 expandtab: */

V572 It is odd that the object which was created using 'new' operator is immediately cast to another type.

V572 It is odd that the object which was created using 'new' operator is immediately cast to another type.

V572 It is odd that the object which was created using 'new' operator is immediately cast to another type.

V1019 Compound assignment expression 'Arguments[0] >>= arg' is used inside condition.