LCOV - code coverage report
Current view: top level - oox/source/vml - vmlshape.cxx (source / functions) Hit Total Coverage
Test: commit e02a6cb2c3e2b23b203b422e4e0680877f232636 Lines: 0 557 0.0 %
Date: 2014-04-14 Functions: 0 56 0.0 %
Legend: Lines: hit not hit

          Line data    Source code
       1             : /* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
       2             : /*
       3             :  * This file is part of the LibreOffice project.
       4             :  *
       5             :  * This Source Code Form is subject to the terms of the Mozilla Public
       6             :  * License, v. 2.0. If a copy of the MPL was not distributed with this
       7             :  * file, You can obtain one at http://mozilla.org/MPL/2.0/.
       8             :  *
       9             :  * This file incorporates work covered by the following license notice:
      10             :  *
      11             :  *   Licensed to the Apache Software Foundation (ASF) under one or more
      12             :  *   contributor license agreements. See the NOTICE file distributed
      13             :  *   with this work for additional information regarding copyright
      14             :  *   ownership. The ASF licenses this file to you under the Apache
      15             :  *   License, Version 2.0 (the "License"); you may not use this file
      16             :  *   except in compliance with the License. You may obtain a copy of
      17             :  *   the License at http://www.apache.org/licenses/LICENSE-2.0 .
      18             :  */
      19             : 
      20             : #include <algorithm>
      21             : #include <boost/optional.hpp>
      22             : 
      23             : #include "oox/vml/vmlshape.hxx"
      24             : 
      25             : #include <com/sun/star/beans/PropertyValues.hpp>
      26             : #include <com/sun/star/beans/XPropertySet.hpp>
      27             : #include <com/sun/star/awt/XControlModel.hpp>
      28             : #include <com/sun/star/drawing/PointSequenceSequence.hpp>
      29             : #include <com/sun/star/drawing/PolyPolygonBezierCoords.hpp>
      30             : #include <com/sun/star/drawing/TextVerticalAdjust.hpp>
      31             : #include <com/sun/star/drawing/XEnhancedCustomShapeDefaulter.hpp>
      32             : #include <com/sun/star/drawing/XShapes.hpp>
      33             : #include <com/sun/star/drawing/XControlShape.hpp>
      34             : #include <com/sun/star/graphic/XGraphic.hpp>
      35             : #include <com/sun/star/table/BorderLine2.hpp>
      36             : #include <com/sun/star/text/HoriOrientation.hpp>
      37             : #include <com/sun/star/text/RelOrientation.hpp>
      38             : #include <com/sun/star/text/SizeType.hpp>
      39             : #include <com/sun/star/text/VertOrientation.hpp>
      40             : #include <com/sun/star/text/WrapTextMode.hpp>
      41             : #include <com/sun/star/text/XTextContent.hpp>
      42             : #include <com/sun/star/text/XTextDocument.hpp>
      43             : #include <com/sun/star/text/XTextFrame.hpp>
      44             :  #include <com/sun/star/lang/XServiceInfo.hpp>
      45             : #include <com/sun/star/text/TextContentAnchorType.hpp>
      46             : #include <rtl/math.hxx>
      47             : #include <rtl/ustrbuf.hxx>
      48             : #include <svx/svdtrans.hxx>
      49             : #include "oox/drawingml/shapepropertymap.hxx"
      50             : #include "oox/helper/graphichelper.hxx"
      51             : #include "oox/helper/propertyset.hxx"
      52             : #include "oox/ole/axcontrol.hxx"
      53             : #include "oox/ole/axcontrolfragment.hxx"
      54             : #include "oox/ole/oleobjecthelper.hxx"
      55             : #include "oox/vml/vmldrawing.hxx"
      56             : #include "oox/vml/vmlshapecontainer.hxx"
      57             : #include "oox/vml/vmltextbox.hxx"
      58             : #include "oox/core/xmlfilterbase.hxx"
      59             : #include "oox/helper/containerhelper.hxx"
      60             : 
      61             : using ::com::sun::star::beans::XPropertySet;
      62             : using ::com::sun::star::uno::Any;
      63             : 
      64             : using namespace ::com::sun::star;
      65             : using namespace ::com::sun::star::text;
      66             : 
      67             : namespace oox {
      68             : namespace vml {
      69             : 
      70             : 
      71             : 
      72             : using namespace ::com::sun::star;
      73             : using namespace ::com::sun::star::drawing;
      74             : using namespace ::com::sun::star::graphic;
      75             : using namespace ::com::sun::star::uno;
      76             : using namespace ::com::sun::star::io;
      77             : 
      78             : using ::oox::core::XmlFilterBase;
      79             : 
      80             : 
      81             : 
      82             : namespace {
      83             : 
      84             : const sal_Int32 VML_SHAPETYPE_PICTUREFRAME  = 75;
      85             : const sal_Int32 VML_SHAPETYPE_HOSTCONTROL   = 201;
      86             : 
      87             : 
      88             : 
      89           0 : awt::Point lclGetAbsPoint( const awt::Point& rRelPoint, const awt::Rectangle& rShapeRect, const awt::Rectangle& rCoordSys )
      90             : {
      91           0 :     double fWidthRatio = static_cast< double >( rShapeRect.Width ) / rCoordSys.Width;
      92           0 :     double fHeightRatio = static_cast< double >( rShapeRect.Height ) / rCoordSys.Height;
      93           0 :     awt::Point aAbsPoint;
      94           0 :     aAbsPoint.X = static_cast< sal_Int32 >( rShapeRect.X + fWidthRatio * (rRelPoint.X - rCoordSys.X) + 0.5 );
      95           0 :     aAbsPoint.Y = static_cast< sal_Int32 >( rShapeRect.Y + fHeightRatio * (rRelPoint.Y - rCoordSys.Y) + 0.5 );
      96           0 :     return aAbsPoint;
      97             : }
      98             : 
      99           0 : awt::Rectangle lclGetAbsRect( const awt::Rectangle& rRelRect, const awt::Rectangle& rShapeRect, const awt::Rectangle& rCoordSys )
     100             : {
     101           0 :     double fWidthRatio = static_cast< double >( rShapeRect.Width ) / rCoordSys.Width;
     102           0 :     double fHeightRatio = static_cast< double >( rShapeRect.Height ) / rCoordSys.Height;
     103           0 :     awt::Rectangle aAbsRect;
     104           0 :     aAbsRect.X = static_cast< sal_Int32 >( rShapeRect.X + fWidthRatio * (rRelRect.X - rCoordSys.X) + 0.5 );
     105           0 :     aAbsRect.Y = static_cast< sal_Int32 >( rShapeRect.Y + fHeightRatio * (rRelRect.Y - rCoordSys.Y) + 0.5 );
     106           0 :     aAbsRect.Width = static_cast< sal_Int32 >( fWidthRatio * rRelRect.Width + 0.5 );
     107           0 :     aAbsRect.Height = static_cast< sal_Int32 >( fHeightRatio * rRelRect.Height + 0.5 );
     108           0 :     return aAbsRect;
     109             : }
     110             : 
     111             : } // namespace
     112             : 
     113             : 
     114             : 
     115           0 : ShapeTypeModel::ShapeTypeModel():
     116             :     mbAutoHeight( false ),
     117           0 :     mbVisible( true )
     118             : {
     119           0 : }
     120             : 
     121           0 : void ShapeTypeModel::assignUsed( const ShapeTypeModel& rSource )
     122             : {
     123           0 :     moShapeType.assignIfUsed( rSource.moShapeType );
     124           0 :     moCoordPos.assignIfUsed( rSource.moCoordPos );
     125           0 :     moCoordSize.assignIfUsed( rSource.moCoordSize );
     126             :     /*  The style properties position, left, top, width, height, margin-left,
     127             :         margin-top are not derived from shape template to shape. */
     128           0 :     maStrokeModel.assignUsed( rSource.maStrokeModel );
     129           0 :     maFillModel.assignUsed( rSource.maFillModel );
     130           0 :     moGraphicPath.assignIfUsed( rSource.moGraphicPath );
     131           0 :     moGraphicTitle.assignIfUsed( rSource.moGraphicTitle );
     132           0 : }
     133             : 
     134             : 
     135             : 
     136           0 : ShapeType::ShapeType( Drawing& rDrawing ) :
     137           0 :     mrDrawing( rDrawing )
     138             : {
     139           0 : }
     140             : 
     141           0 : ShapeType::~ShapeType()
     142             : {
     143           0 : }
     144             : 
     145           0 : sal_Int32 ShapeType::getShapeType() const
     146             : {
     147           0 :     return maTypeModel.moShapeType.get( 0 );
     148             : }
     149             : 
     150           0 : OUString ShapeType::getGraphicPath() const
     151             : {
     152           0 :     return maTypeModel.moGraphicPath.get( OUString() );
     153             : }
     154             : 
     155           0 : awt::Rectangle ShapeType::getCoordSystem() const
     156             : {
     157           0 :     Int32Pair aCoordPos = maTypeModel.moCoordPos.get( Int32Pair( 0, 0 ) );
     158           0 :     Int32Pair aCoordSize = maTypeModel.moCoordSize.get( Int32Pair( 1000, 1000 ) );
     159           0 :     if( aCoordSize.first == 0 )
     160           0 :         aCoordSize.first = 1;
     161           0 :     if( aCoordSize.second == 0 )
     162           0 :         aCoordSize.second = 1;
     163           0 :     return awt::Rectangle( aCoordPos.first, aCoordPos.second, aCoordSize.first, aCoordSize.second );
     164             : }
     165             : 
     166           0 : awt::Rectangle ShapeType::getRectangle( const ShapeParentAnchor* pParentAnchor ) const
     167             : {
     168             :     return pParentAnchor ?
     169           0 :         lclGetAbsRect( getRelRectangle(), pParentAnchor->maShapeRect, pParentAnchor->maCoordSys ) :
     170           0 :         getAbsRectangle();
     171             : }
     172             : 
     173           0 : awt::Rectangle ShapeType::getAbsRectangle() const
     174             : {
     175           0 :     const GraphicHelper& rGraphicHelper = mrDrawing.getFilter().getGraphicHelper();
     176             : 
     177           0 :     sal_Int32 nWidth = ConversionHelper::decodeMeasureToHmm( rGraphicHelper, maTypeModel.maWidth, 0, true, true );
     178           0 :     if ( nWidth == 0 )
     179           0 :         nWidth = 1;
     180             : 
     181           0 :     sal_Int32 nHeight = ConversionHelper::decodeMeasureToHmm( rGraphicHelper, maTypeModel.maHeight, 0, false, true );
     182           0 :     if ( nHeight == 0 )
     183           0 :         nHeight = 1;
     184             : 
     185           0 :     sal_Int32 nLeft = ConversionHelper::decodeMeasureToHmm( rGraphicHelper, maTypeModel.maLeft, 0, true, true )
     186           0 :         + ConversionHelper::decodeMeasureToHmm( rGraphicHelper, maTypeModel.maMarginLeft, 0, true, true );
     187           0 :     if (nLeft == 0 && maTypeModel.maPosition == "absolute")
     188           0 :         nLeft = 1;
     189             : 
     190             :     return awt::Rectangle(
     191             :         nLeft,
     192           0 :         ConversionHelper::decodeMeasureToHmm( rGraphicHelper, maTypeModel.maTop, 0, false, true ) + ConversionHelper::decodeMeasureToHmm( rGraphicHelper, maTypeModel.maMarginTop, 0, false, true ),
     193           0 :         nWidth, nHeight );
     194             : }
     195             : 
     196           0 : awt::Rectangle ShapeType::getRelRectangle() const
     197             : {
     198           0 :     sal_Int32 nWidth = maTypeModel.maWidth.toInt32();
     199           0 :     if ( nWidth == 0 )
     200           0 :         nWidth = 1;
     201             : 
     202           0 :     sal_Int32 nHeight = maTypeModel.maHeight.toInt32();
     203           0 :     if ( nHeight == 0 )
     204           0 :         nHeight = 1;
     205             : 
     206             :     return awt::Rectangle(
     207           0 :         maTypeModel.maLeft.toInt32(),
     208           0 :         maTypeModel.maTop.toInt32(),
     209           0 :         nWidth, nHeight );
     210             : }
     211             : 
     212             : 
     213             : 
     214           0 : ClientData::ClientData() :
     215             :     mnObjType( XML_TOKEN_INVALID ),
     216             :     mnTextHAlign( XML_Left ),
     217             :     mnTextVAlign( XML_Top ),
     218             :     mnCol( -1 ),
     219             :     mnRow( -1 ),
     220             :     mnChecked( VML_CLIENTDATA_UNCHECKED ),
     221             :     mnDropStyle( XML_Combo ),
     222             :     mnDropLines( 1 ),
     223             :     mnVal( 0 ),
     224             :     mnMin( 0 ),
     225             :     mnMax( 0 ),
     226             :     mnInc( 0 ),
     227             :     mnPage( 0 ),
     228             :     mnSelType( XML_Single ),
     229             :     mnVTEdit( VML_CLIENTDATA_TEXT ),
     230             :     mbPrintObject( true ),
     231             :     mbVisible( false ),
     232             :     mbDde( false ),
     233             :     mbNo3D( false ),
     234             :     mbNo3D2( false ),
     235             :     mbMultiLine( false ),
     236             :     mbVScroll( false ),
     237           0 :     mbSecretEdit( false )
     238             : {
     239           0 : }
     240             : 
     241             : 
     242             : 
     243           0 : ShapeModel::ShapeModel()
     244             : {
     245           0 : }
     246             : 
     247           0 : ShapeModel::~ShapeModel()
     248             : {
     249           0 : }
     250             : 
     251           0 : TextBox& ShapeModel::createTextBox(ShapeTypeModel& rModel)
     252             : {
     253           0 :     mxTextBox.reset( new TextBox(rModel) );
     254           0 :     return *mxTextBox;
     255             : }
     256             : 
     257           0 : ClientData& ShapeModel::createClientData()
     258             : {
     259           0 :     mxClientData.reset( new ClientData );
     260           0 :     return *mxClientData;
     261             : }
     262             : 
     263             : 
     264             : 
     265           0 : ShapeBase::ShapeBase( Drawing& rDrawing ) :
     266           0 :     ShapeType( rDrawing )
     267             : {
     268           0 : }
     269             : 
     270           0 : void ShapeBase::finalizeFragmentImport()
     271             : {
     272           0 :     if( maShapeModel.maType.getLength() > 1 )
     273             :     {
     274           0 :         OUString aType = maShapeModel.maType;
     275           0 :         if (aType[ 0 ] == '#')
     276           0 :             aType = aType.copy(1);
     277           0 :         if( const ShapeType* pShapeType = mrDrawing.getShapes().getShapeTypeById( aType, true ) )
     278           0 :             maTypeModel.assignUsed( pShapeType->getTypeModel() );
     279             :     }
     280           0 : }
     281             : 
     282           0 : OUString ShapeBase::getShapeName() const
     283             : {
     284           0 :     if( !maTypeModel.maShapeName.isEmpty() )
     285           0 :         return maTypeModel.maShapeName;
     286             : 
     287           0 :     OUString aBaseName = mrDrawing.getShapeBaseName( *this );
     288           0 :     if( !aBaseName.isEmpty() )
     289             :     {
     290           0 :         sal_Int32 nShapeIdx = mrDrawing.getLocalShapeIndex( getShapeId() );
     291           0 :         if( nShapeIdx > 0 )
     292           0 :             return OUStringBuffer( aBaseName ).append( ' ' ).append( nShapeIdx ).makeStringAndClear();
     293             :     }
     294             : 
     295           0 :     return OUString();
     296             : }
     297             : 
     298           0 : const ShapeType* ShapeBase::getChildTypeById( const OUString& ) const
     299             : {
     300           0 :     return 0;
     301             : }
     302             : 
     303           0 : const ShapeBase* ShapeBase::getChildById( const OUString& ) const
     304             : {
     305           0 :     return 0;
     306             : }
     307             : 
     308           0 : Reference< XShape > ShapeBase::convertAndInsert( const Reference< XShapes >& rxShapes, const ShapeParentAnchor* pParentAnchor ) const
     309             : {
     310           0 :     Reference< XShape > xShape;
     311           0 :     if( mrDrawing.isShapeSupported( *this ) )
     312             :     {
     313             :         /*  Calculate shape rectangle. Applications may do something special
     314             :             according to some imported shape client data (e.g. Excel cell anchor). */
     315           0 :         awt::Rectangle aShapeRect = calcShapeRectangle( pParentAnchor );
     316             : 
     317           0 :         if( ((aShapeRect.Width > 0) || (aShapeRect.Height > 0)) && rxShapes.is() )
     318             :         {
     319           0 :             xShape = implConvertAndInsert( rxShapes, aShapeRect );
     320           0 :             if( xShape.is() )
     321             :             {
     322             :                 // set imported or generated shape name (not supported by form controls)
     323           0 :                 PropertySet aShapeProp( xShape );
     324           0 :                 if( aShapeProp.hasProperty( PROP_Name ) )
     325           0 :                     aShapeProp.setProperty( PROP_Name, getShapeName() );
     326           0 :                 uno::Reference< lang::XServiceInfo > xSInfo( xShape, uno::UNO_QUERY_THROW );
     327           0 :                 if (xSInfo->supportsService("com.sun.star.text.TextFrame"))
     328             :                 {
     329           0 :                     uno::Sequence<beans::PropertyValue> aGrabBag;
     330           0 :                     uno::Reference<beans::XPropertySet> propertySet (xShape, uno::UNO_QUERY);
     331           0 :                     propertySet->getPropertyValue("FrameInteropGrabBag") >>= aGrabBag;
     332           0 :                     sal_Int32 length = aGrabBag.getLength();
     333             : 
     334           0 :                     aGrabBag.realloc( length+1 );
     335           0 :                     aGrabBag[length].Name = "VML-Z-ORDER";
     336           0 :                     aGrabBag[length].Value = uno::makeAny( maTypeModel.maZIndex.toInt32() );
     337           0 :                     propertySet->setPropertyValue( "FrameInteropGrabBag", uno::makeAny(aGrabBag) );
     338             :                 }
     339           0 :                 Reference< XControlShape > xControlShape( xShape, uno::UNO_QUERY );
     340           0 :                 if ( xControlShape.is() && !getTypeModel().mbVisible )
     341             :                 {
     342           0 :                     PropertySet aControlShapeProp( xControlShape->getControl() );
     343           0 :                     aControlShapeProp.setProperty( PROP_EnableVisible, uno::makeAny( sal_False ) );
     344             :                 }
     345             :                 /*  Notify the drawing that a new shape has been inserted. For
     346             :                     convenience, pass the rectangle that contains position and
     347             :                     size of the shape. */
     348           0 :                 bool bGroupChild = pParentAnchor != 0;
     349           0 :                 mrDrawing.notifyXShapeInserted( xShape, aShapeRect, *this, bGroupChild );
     350             :             }
     351             :         }
     352             :         else
     353             :             SAL_WARN("oox", "not converting shape, as calculated rectangle is empty");
     354             :     }
     355           0 :     return xShape;
     356             : }
     357             : 
     358           0 : void ShapeBase::convertFormatting( const Reference< XShape >& rxShape, const ShapeParentAnchor* pParentAnchor ) const
     359             : {
     360           0 :     if( rxShape.is() )
     361             :     {
     362             :         /*  Calculate shape rectangle. Applications may do something special
     363             :             according to some imported shape client data (e.g. Excel cell anchor). */
     364           0 :         awt::Rectangle aShapeRect = calcShapeRectangle( pParentAnchor );
     365             : 
     366             :         // convert the shape, if the calculated rectangle is not empty
     367           0 :         if( (aShapeRect.Width > 0) || (aShapeRect.Height > 0) )
     368             :         {
     369           0 :             rxShape->setPosition( awt::Point( aShapeRect.X, aShapeRect.Y ) );
     370           0 :             rxShape->setSize( awt::Size( aShapeRect.Width, aShapeRect.Height ) );
     371           0 :             convertShapeProperties( rxShape );
     372             :         }
     373             :     }
     374           0 : }
     375             : 
     376             : // protected ------------------------------------------------------------------
     377             : 
     378           0 : awt::Rectangle ShapeBase::calcShapeRectangle( const ShapeParentAnchor* pParentAnchor ) const
     379             : {
     380             :     /*  Calculate shape rectangle. Applications may do something special
     381             :         according to some imported shape client data (e.g. Excel cell anchor). */
     382           0 :     awt::Rectangle aShapeRect;
     383           0 :     const ClientData* pClientData = getClientData();
     384           0 :     if( !pClientData || !mrDrawing.convertClientAnchor( aShapeRect, pClientData->maAnchor ) )
     385           0 :         aShapeRect = getRectangle( pParentAnchor );
     386           0 :     return aShapeRect;
     387             : }
     388             : 
     389           0 : void ShapeBase::convertShapeProperties( const Reference< XShape >& rxShape ) const
     390             : {
     391           0 :     ::oox::drawingml::ShapePropertyMap aPropMap( mrDrawing.getFilter().getModelObjectHelper() );
     392           0 :     const GraphicHelper& rGraphicHelper = mrDrawing.getFilter().getGraphicHelper();
     393           0 :     maTypeModel.maStrokeModel.pushToPropMap( aPropMap, rGraphicHelper );
     394           0 :     maTypeModel.maFillModel.pushToPropMap( aPropMap, rGraphicHelper );
     395             : 
     396           0 :     uno::Reference<lang::XServiceInfo> xSInfo(rxShape, uno::UNO_QUERY_THROW);
     397           0 :     if (xSInfo->supportsService("com.sun.star.text.TextFrame"))
     398             :     {
     399             :         // Any other service supporting the ShadowFormat property?
     400           0 :         maTypeModel.maShadowModel.pushToPropMap(aPropMap, rGraphicHelper);
     401             :         // TextFrames have BackColor, not FillColor
     402           0 :         if (aPropMap.hasProperty(PROP_FillColor))
     403             :         {
     404           0 :             aPropMap.setAnyProperty(PROP_BackColor, aPropMap.getProperty(PROP_FillColor));
     405           0 :             aPropMap.erase(PROP_FillColor);
     406             :         }
     407             :         // TextFrames have BackColorTransparency, not FillTransparence
     408           0 :         if (aPropMap.hasProperty(PROP_FillTransparence))
     409             :         {
     410           0 :             aPropMap.setAnyProperty(PROP_BackColorTransparency, aPropMap.getProperty(PROP_FillTransparence));
     411           0 :             aPropMap.erase(PROP_FillTransparence);
     412             :         }
     413             :         // And no LineColor property; individual borders can have colors and widths
     414           0 :         boost::optional<sal_Int32> oLineWidth;
     415           0 :         if (maTypeModel.maStrokeModel.moWeight.has())
     416           0 :             oLineWidth.reset(ConversionHelper::decodeMeasureToHmm(rGraphicHelper, maTypeModel.maStrokeModel.moWeight.get(), 0, false, false));
     417           0 :         if (aPropMap.hasProperty(PROP_LineColor))
     418             :         {
     419           0 :             uno::Reference<beans::XPropertySet> xPropertySet(rxShape, uno::UNO_QUERY);
     420             :             static const sal_Int32 aBorders[] = {
     421             :                 PROP_TopBorder, PROP_LeftBorder, PROP_BottomBorder, PROP_RightBorder
     422             :             };
     423           0 :             for (unsigned int i = 0; i < SAL_N_ELEMENTS(aBorders); ++i)
     424             :             {
     425           0 :                 table::BorderLine2 aBorderLine = xPropertySet->getPropertyValue(PropertyMap::getPropertyName(aBorders[i])).get<table::BorderLine2>();
     426           0 :                 aBorderLine.Color = aPropMap.getProperty(PROP_LineColor).get<sal_Int32>();
     427           0 :                 if (oLineWidth)
     428           0 :                     aBorderLine.LineWidth = *oLineWidth;
     429           0 :                 aPropMap.setProperty(aBorders[i], uno::makeAny(aBorderLine));
     430             :             }
     431           0 :             aPropMap.erase(PROP_LineColor);
     432           0 :         }
     433             :     }
     434           0 :     else if (xSInfo->supportsService("com.sun.star.drawing.CustomShape"))
     435           0 :         maTypeModel.maTextpathModel.pushToPropMap(aPropMap, rxShape);
     436             : 
     437           0 :     PropertySet( rxShape ).setProperties( aPropMap );
     438           0 : }
     439             : 
     440             : 
     441             : 
     442           0 : SimpleShape::SimpleShape( Drawing& rDrawing, const OUString& rService ) :
     443             :     ShapeBase( rDrawing ),
     444           0 :     maService( rService )
     445             : {
     446           0 : }
     447             : 
     448           0 : void lcl_setSurround(PropertySet& rPropSet, const ShapeTypeModel& rTypeModel)
     449             : {
     450           0 :     sal_Int32 nSurround = com::sun::star::text::WrapTextMode_THROUGHT;
     451           0 :     if ( rTypeModel.moWrapType.get() == "square" || rTypeModel.moWrapType .get()== "tight" ||
     452           0 :          rTypeModel.moWrapType.get() == "through" )
     453             :     {
     454           0 :         nSurround = com::sun::star::text::WrapTextMode_PARALLEL;
     455           0 :         if ( rTypeModel.moWrapSide.get() == "left" )
     456           0 :             nSurround = com::sun::star::text::WrapTextMode_LEFT;
     457           0 :         else if ( rTypeModel.moWrapSide.get() == "right" )
     458           0 :             nSurround = com::sun::star::text::WrapTextMode_RIGHT;
     459             :     }
     460           0 :     else if ( rTypeModel.moWrapType.get() == "topAndBottom" )
     461           0 :         nSurround = com::sun::star::text::WrapTextMode_NONE;
     462             : 
     463           0 :     rPropSet.setProperty(PROP_Surround, nSurround);
     464           0 : }
     465             : 
     466           0 : void lcl_SetAnchorType(PropertySet& rPropSet, const ShapeTypeModel& rTypeModel)
     467             : {
     468           0 :     if ( rTypeModel.maPositionHorizontal == "center" )
     469           0 :         rPropSet.setAnyProperty(PROP_HoriOrient, makeAny(text::HoriOrientation::CENTER));
     470             : 
     471           0 :     if ( rTypeModel.maPositionHorizontalRelative == "page" )
     472           0 :         rPropSet.setAnyProperty(PROP_HoriOrientRelation, makeAny(text::RelOrientation::PAGE_FRAME));
     473             : 
     474           0 :     if ( rTypeModel.maPositionVertical == "center" )
     475           0 :         rPropSet.setAnyProperty(PROP_VertOrient, makeAny(text::VertOrientation::CENTER));
     476             : 
     477           0 :     if ( rTypeModel.maPosition == "absolute" )
     478             :     {
     479             :         // Word supports as-character (inline) and at-character only, absolute can't be inline.
     480           0 :         rPropSet.setProperty(PROP_AnchorType, text::TextContentAnchorType_AT_CHARACTER);
     481             : 
     482           0 :         if ( rTypeModel.maPositionVerticalRelative == "page" )
     483             :         {
     484           0 :             rPropSet.setProperty(PROP_VertOrientRelation, text::RelOrientation::PAGE_FRAME);
     485             :         }
     486           0 :         else if ( rTypeModel.maPositionVerticalRelative == "margin" )
     487             :         {
     488           0 :             rPropSet.setProperty(PROP_VertOrientRelation, text::RelOrientation::PAGE_PRINT_AREA);
     489             :         }
     490             :         else
     491             :         {
     492             :             // Vertical placement relative to margin, because parent style must not modify vertical position
     493           0 :             rPropSet.setProperty(PROP_VertOrientRelation, text::RelOrientation::FRAME);
     494             :         }
     495             :     }
     496           0 :     else if( rTypeModel.maPosition == "relative" )
     497             :     {   // I'm not very sure this is correct either.
     498           0 :         rPropSet.setProperty(PROP_AnchorType, text::TextContentAnchorType_AT_PARAGRAPH);
     499             :     }
     500             :     else // static (is the default) means anchored inline
     501             :     {
     502           0 :         rPropSet.setProperty(PROP_AnchorType, text::TextContentAnchorType_AS_CHARACTER);
     503             :     }
     504           0 :     lcl_setSurround( rPropSet, rTypeModel );
     505           0 : }
     506             : 
     507           0 : void lcl_SetRotation(PropertySet& rPropSet, const sal_Int32 nRotation)
     508             : {
     509             :     // See DffPropertyReader::Fix16ToAngle(): in VML, positive rotation angles are clockwise, we have them as counter-clockwise.
     510             :     // Additionally, VML type is 0..360, our is 0..36000.
     511           0 :     rPropSet.setAnyProperty(PROP_RotateAngle, makeAny(sal_Int32(NormAngle360(nRotation * -100))));
     512           0 : }
     513             : 
     514           0 : Reference< XShape > SimpleShape::implConvertAndInsert( const Reference< XShapes >& rxShapes, const awt::Rectangle& rShapeRect ) const
     515             : {
     516           0 :     awt::Rectangle aShapeRect(rShapeRect);
     517           0 :     boost::optional<sal_Int32> oRotation;
     518           0 :     bool bFlipX = false, bFlipY = false;
     519           0 :     if (!maTypeModel.maRotation.isEmpty())
     520           0 :         oRotation.reset(maTypeModel.maRotation.toInt32());
     521           0 :     if (!maTypeModel.maFlip.isEmpty())
     522             :     {
     523           0 :         if (maTypeModel.maFlip.equalsAscii("x"))
     524             :         {
     525           0 :             bFlipX = true;
     526             :         }
     527           0 :         else if (maTypeModel.maFlip.equalsAscii("y"))
     528             :         {
     529           0 :             bFlipY = true;
     530             :         }
     531             :     }
     532             : 
     533           0 :     Reference< XShape > xShape = mrDrawing.createAndInsertXShape( maService, rxShapes, aShapeRect );
     534           0 :     convertShapeProperties( xShape );
     535             : 
     536             :     // Handle left/right/top/bottom wrap distance.
     537             :     // Default value of mso-wrap-distance-left/right is supposed to be 0 (see
     538             :     // 19.1.2.19 of the VML spec), but Word implements a non-zero value.
     539             :     // [MS-ODRAW] says the below default value in 2.3.4.9.
     540           0 :     const GraphicHelper& rGraphicHelper = mrDrawing.getFilter().getGraphicHelper();
     541           0 :     OUString aWrapDistanceLeft = OUString::number(0x0001BE7C);
     542           0 :     if (!maTypeModel.maWrapDistanceLeft.isEmpty())
     543           0 :         aWrapDistanceLeft = maTypeModel.maWrapDistanceLeft;
     544           0 :     sal_Int32 nWrapDistanceLeft = ConversionHelper::decodeMeasureToHmm(rGraphicHelper, aWrapDistanceLeft, 0, true, false);
     545           0 :     PropertySet(xShape).setAnyProperty(PROP_LeftMargin, uno::makeAny(nWrapDistanceLeft));
     546           0 :     OUString aWrapDistanceRight = OUString::number(0x0001BE7C);
     547           0 :     if (!maTypeModel.maWrapDistanceRight.isEmpty())
     548           0 :         aWrapDistanceRight = maTypeModel.maWrapDistanceRight;
     549           0 :     sal_Int32 nWrapDistanceRight = ConversionHelper::decodeMeasureToHmm(rGraphicHelper, aWrapDistanceRight, 0, true, false);
     550           0 :     PropertySet(xShape).setAnyProperty(PROP_RightMargin, uno::makeAny(nWrapDistanceRight));
     551           0 :     sal_Int32 nWrapDistanceTop = 0;
     552           0 :     if (!maTypeModel.maWrapDistanceTop.isEmpty())
     553           0 :         nWrapDistanceTop = ConversionHelper::decodeMeasureToHmm(rGraphicHelper, maTypeModel.maWrapDistanceTop, 0, false, true);
     554           0 :     PropertySet(xShape).setAnyProperty(PROP_TopMargin, uno::makeAny(nWrapDistanceTop));
     555           0 :     sal_Int32 nWrapDistanceBottom = 0;
     556           0 :     if (!maTypeModel.maWrapDistanceBottom.isEmpty())
     557           0 :         nWrapDistanceBottom = ConversionHelper::decodeMeasureToHmm(rGraphicHelper, maTypeModel.maWrapDistanceBottom, 0, false, true);
     558           0 :     PropertySet(xShape).setAnyProperty(PROP_BottomMargin, uno::makeAny(nWrapDistanceBottom));
     559             : 
     560           0 :     if ( maService.equalsAscii( "com.sun.star.text.TextFrame" ) )
     561             :     {
     562           0 :         PropertySet( xShape ).setAnyProperty( PROP_FrameIsAutomaticHeight, makeAny( maTypeModel.mbAutoHeight ) );
     563           0 :         PropertySet( xShape ).setAnyProperty( PROP_SizeType, makeAny( maTypeModel.mbAutoHeight ? SizeType::MIN : SizeType::FIX ) );
     564           0 :         if( getTextBox()->borderDistanceSet )
     565             :         {
     566           0 :             PropertySet( xShape ).setAnyProperty( PROP_LeftBorderDistance, makeAny( sal_Int32( getTextBox()->borderDistanceLeft )));
     567           0 :             PropertySet( xShape ).setAnyProperty( PROP_TopBorderDistance, makeAny( sal_Int32( getTextBox()->borderDistanceTop )));
     568           0 :             PropertySet( xShape ).setAnyProperty( PROP_RightBorderDistance, makeAny( sal_Int32( getTextBox()->borderDistanceRight )));
     569           0 :             PropertySet( xShape ).setAnyProperty( PROP_BottomBorderDistance, makeAny( sal_Int32( getTextBox()->borderDistanceBottom )));
     570             :         }
     571           0 :         if (!maTypeModel.maLayoutFlowAlt.isEmpty())
     572             :         {
     573             :             // Can't handle this property here, as the frame is not attached yet: pass it to writerfilter.
     574           0 :             uno::Reference<beans::XPropertySet> xPropertySet(xShape, uno::UNO_QUERY);
     575           0 :             uno::Sequence<beans::PropertyValue> aGrabBag;
     576           0 :             xPropertySet->getPropertyValue("FrameInteropGrabBag") >>= aGrabBag;
     577           0 :             beans::PropertyValue aPair;
     578           0 :             aPair.Name = "mso-layout-flow-alt";
     579           0 :             aPair.Value = uno::makeAny(maTypeModel.maLayoutFlowAlt);
     580           0 :             if (aGrabBag.hasElements())
     581             :             {
     582           0 :                 sal_Int32 nLength = aGrabBag.getLength();
     583           0 :                 aGrabBag.realloc(nLength + 1);
     584           0 :                 aGrabBag[nLength] = aPair;
     585             :             }
     586             :             else
     587             :             {
     588           0 :                 aGrabBag.realloc(1);
     589           0 :                 aGrabBag[0] = aPair;
     590             :             }
     591           0 :             xPropertySet->setPropertyValue("FrameInteropGrabBag", uno::makeAny(aGrabBag));
     592             :         }
     593             :     }
     594             :     else
     595             :     {
     596             :         // FIXME Setting the relative width/heigh only for everything but text frames as
     597             :         // TextFrames already have relative width/height feature... but currently not working
     598             :         // in the way we need.
     599             : 
     600             :         // Set the relative width / height if any
     601           0 :         if ( !maTypeModel.maWidthPercent.isEmpty( ) )
     602             :         {
     603             :             // Only page-relative width is supported ATM
     604           0 :             if ( maTypeModel.maWidthRelative.isEmpty() || maTypeModel.maWidthRelative == "page" )
     605             :             {
     606           0 :                 sal_Int16 nWidth = maTypeModel.maWidthPercent.toInt32() / 10;
     607             :                 // Only apply if nWidth != 0
     608           0 :                 if ( nWidth )
     609           0 :                     PropertySet( xShape ).setAnyProperty(PROP_RelativeWidth, makeAny( nWidth ) );
     610             :             }
     611             :         }
     612           0 :         if ( !maTypeModel.maHeightPercent.isEmpty( ) )
     613             :         {
     614             :             // Only page-relative height is supported ATM
     615           0 :             if ( maTypeModel.maHeightRelative.isEmpty() || maTypeModel.maHeightRelative == "page" )
     616             :             {
     617           0 :                 sal_Int16 nHeight = maTypeModel.maHeightPercent.toInt32() / 10;
     618             :                 // Only apply if nHeight != 0
     619           0 :                 if ( nHeight )
     620           0 :                     PropertySet( xShape ).setAnyProperty(PROP_RelativeHeight, makeAny( nHeight ) );
     621             :             }
     622             :         }
     623             : 
     624             :         // drawinglayer default is center, MSO default is top.
     625           0 :         drawing::TextVerticalAdjust eTextVerticalAdjust = drawing::TextVerticalAdjust_TOP;
     626           0 :         if (maTypeModel.maVTextAnchor == "middle")
     627           0 :             eTextVerticalAdjust = drawing::TextVerticalAdjust_CENTER;
     628           0 :         else if (maTypeModel.maVTextAnchor == "bottom")
     629           0 :             eTextVerticalAdjust = drawing::TextVerticalAdjust_BOTTOM;
     630           0 :         PropertySet(xShape).setAnyProperty(PROP_TextVerticalAdjust, makeAny(eTextVerticalAdjust));
     631             : 
     632           0 :         if (getTextBox())
     633             :         {
     634           0 :             getTextBox()->convert(xShape);
     635           0 :             if (getTextBox()->borderDistanceSet)
     636             :             {
     637           0 :                 awt::Size aSize = xShape->getSize();
     638           0 :                 PropertySet(xShape).setAnyProperty(PROP_TextLeftDistance, makeAny(sal_Int32(getTextBox()->borderDistanceLeft)));
     639           0 :                 PropertySet(xShape).setAnyProperty(PROP_TextUpperDistance, makeAny(sal_Int32(getTextBox()->borderDistanceTop)));
     640           0 :                 PropertySet(xShape).setAnyProperty(PROP_TextRightDistance, makeAny(sal_Int32(getTextBox()->borderDistanceRight)));
     641           0 :                 PropertySet(xShape).setAnyProperty(PROP_TextLowerDistance, makeAny(sal_Int32(getTextBox()->borderDistanceBottom)));
     642           0 :                 xShape->setSize(aSize);
     643             :             }
     644             :         }
     645             :     }
     646             : 
     647             :     // Import Legacy Fragments (if any)
     648           0 :     if( xShape.is() && !maShapeModel.maLegacyDiagramPath.isEmpty() )
     649             :     {
     650           0 :         Reference< XInputStream > xInStrm( mrDrawing.getFilter().openInputStream( maShapeModel.maLegacyDiagramPath ), UNO_SET_THROW );
     651           0 :         if( xInStrm.is() )
     652           0 :             PropertySet( xShape ).setProperty( PROP_LegacyFragment, xInStrm );
     653             :     }
     654             : 
     655           0 :     PropertySet aPropertySet(xShape);
     656           0 :     if (xShape.is())
     657             :     {
     658           0 :         if (oRotation)
     659             :         {
     660           0 :             lcl_SetRotation(aPropertySet, *oRotation);
     661           0 :             uno::Reference<lang::XServiceInfo> xServiceInfo(rxShapes, uno::UNO_QUERY);
     662           0 :             if (!xServiceInfo->supportsService("com.sun.star.drawing.GroupShape"))
     663             :             {
     664             :                 // If rotation is used, simple setPosition() is not enough.
     665           0 :                 aPropertySet.setAnyProperty(PROP_HoriOrientPosition, makeAny(aShapeRect.X));
     666           0 :                 aPropertySet.setAnyProperty(PROP_VertOrientPosition, makeAny(aShapeRect.Y));
     667           0 :             }
     668             :         }
     669             : 
     670             :         // When flip has 'x' or 'y', the associated ShapeRect will be changed but direction change doesn't occur.
     671             :         // It might occur internally in SdrObject of "sw" module, not here.
     672             :         // The associated properties "PROP_MirroredX" and "PROP_MirroredY" have to be set here so that direction change will occur internally.
     673           0 :         if (bFlipX || bFlipY)
     674             :         {
     675           0 :             com::sun::star::uno::Sequence< com::sun::star::beans::PropertyValue > aPropSequence (2);
     676           0 :             int nPropertyIndex = 0;
     677           0 :             if (bFlipX)
     678             :             {
     679           0 :                 aPropSequence [nPropertyIndex].Name = "MirroredX";
     680           0 :                 aPropSequence [nPropertyIndex].Value = makeAny (bFlipX);
     681           0 :                 nPropertyIndex++;
     682             :             }
     683           0 :             if (bFlipY)
     684             :             {
     685           0 :                 aPropSequence [nPropertyIndex].Name = "MirroredY";
     686           0 :                 aPropSequence [nPropertyIndex].Value = makeAny (bFlipY);
     687           0 :                 nPropertyIndex++;
     688             :             }
     689           0 :             aPropertySet.setAnyProperty(PROP_CustomShapeGeometry, makeAny( aPropSequence ) );
     690             :         }
     691             :     }
     692             : 
     693           0 :     lcl_SetAnchorType(aPropertySet, maTypeModel);
     694             : 
     695           0 :     return xShape;
     696             : }
     697             : 
     698           0 : Reference< XShape > SimpleShape::createPictureObject( const Reference< XShapes >& rxShapes, const awt::Rectangle& rShapeRect, OUString& rGraphicPath ) const
     699             : {
     700           0 :     Reference< XShape > xShape = mrDrawing.createAndInsertXShape( "com.sun.star.drawing.GraphicObjectShape", rxShapes, rShapeRect );
     701           0 :     if( xShape.is() )
     702             :     {
     703           0 :         XmlFilterBase& rFilter = mrDrawing.getFilter();
     704           0 :         OUString aGraphicUrl = rFilter.getGraphicHelper().importEmbeddedGraphicObject( rGraphicPath );
     705           0 :         PropertySet aPropSet( xShape );
     706           0 :         if( !aGraphicUrl.isEmpty() )
     707             :         {
     708           0 :             aPropSet.setProperty( PROP_GraphicURL, aGraphicUrl );
     709             :         }
     710           0 :         uno::Reference< lang::XServiceInfo > xServiceInfo(rxShapes, uno::UNO_QUERY);
     711             :         // If the shape has an absolute position, set the properties accordingly, unless we're inside a group shape.
     712           0 :         if ( maTypeModel.maPosition == "absolute" && !xServiceInfo->supportsService("com.sun.star.drawing.GroupShape"))
     713             :         {
     714           0 :             aPropSet.setProperty(PROP_HoriOrientPosition, rShapeRect.X);
     715           0 :             aPropSet.setProperty(PROP_VertOrientPosition, rShapeRect.Y);
     716           0 :             aPropSet.setProperty(PROP_Opaque, sal_False);
     717             :         }
     718             :         // fdo#70457: preserve rotation information
     719           0 :         if ( !maTypeModel.maRotation.isEmpty() )
     720           0 :             lcl_SetRotation( aPropSet, maTypeModel.maRotation.toInt32() );
     721             : 
     722           0 :         lcl_SetAnchorType(aPropSet, maTypeModel);
     723             :     }
     724           0 :     return xShape;
     725             : }
     726             : 
     727             : 
     728             : 
     729           0 : RectangleShape::RectangleShape( Drawing& rDrawing ) :
     730           0 :     SimpleShape( rDrawing, "com.sun.star.drawing.RectangleShape" )
     731             : {
     732           0 : }
     733             : 
     734           0 : Reference<XShape> RectangleShape::implConvertAndInsert(const Reference<XShapes>& rxShapes, const awt::Rectangle& rShapeRect) const
     735             : {
     736           0 :     OUString aGraphicPath = getGraphicPath();
     737             : 
     738             :     // try to create a picture object
     739           0 :     if(!aGraphicPath.isEmpty())
     740           0 :         return SimpleShape::createPictureObject(rxShapes, rShapeRect, aGraphicPath);
     741             : 
     742             :     // default: try to create a rectangle shape
     743           0 :     Reference<XShape> xShape = SimpleShape::implConvertAndInsert(rxShapes, rShapeRect);
     744           0 :     OUString sArcsize = maTypeModel.maArcsize;
     745           0 :     if ( !sArcsize.isEmpty( ) )
     746             :     {
     747           0 :         sal_Unicode cLastChar = sArcsize[sArcsize.getLength() - 1];
     748           0 :         sal_Int32 nValue = sArcsize.copy( 0, sArcsize.getLength() - 1 ).toInt32( );
     749             :         // Get the smallest half-side
     750           0 :         double size = std::min( rShapeRect.Height, rShapeRect.Width ) / 2.0;
     751           0 :         sal_Int32 nRadius = 0;
     752           0 :         if ( cLastChar == 'f' )
     753           0 :             nRadius = size * nValue / 65536;
     754           0 :         else if ( cLastChar == '%' )
     755           0 :             nRadius = size * nValue / 100;
     756           0 :         PropertySet( xShape ).setAnyProperty( PROP_CornerRadius, makeAny( nRadius ) );
     757             :     }
     758           0 :     return xShape;
     759             : }
     760             : 
     761             : 
     762             : 
     763           0 : EllipseShape::EllipseShape( Drawing& rDrawing ) :
     764           0 :     SimpleShape( rDrawing, "com.sun.star.drawing.EllipseShape" )
     765             : {
     766           0 : }
     767             : 
     768             : 
     769             : 
     770           0 : PolyLineShape::PolyLineShape( Drawing& rDrawing ) :
     771           0 :     SimpleShape( rDrawing, "com.sun.star.drawing.PolyLineShape" )
     772             : {
     773           0 : }
     774             : 
     775           0 : Reference< XShape > PolyLineShape::implConvertAndInsert( const Reference< XShapes >& rxShapes, const awt::Rectangle& rShapeRect ) const
     776             : {
     777           0 :     Reference< XShape > xShape = SimpleShape::implConvertAndInsert( rxShapes, rShapeRect );
     778             :     // polygon path
     779           0 :     awt::Rectangle aCoordSys = getCoordSystem();
     780           0 :     if( !maShapeModel.maPoints.empty() && (aCoordSys.Width > 0) && (aCoordSys.Height > 0) )
     781             :     {
     782           0 :         ::std::vector< awt::Point > aAbsPoints;
     783           0 :         for( ShapeModel::PointVector::const_iterator aIt = maShapeModel.maPoints.begin(), aEnd = maShapeModel.maPoints.end(); aIt != aEnd; ++aIt )
     784           0 :             aAbsPoints.push_back( lclGetAbsPoint( *aIt, rShapeRect, aCoordSys ) );
     785           0 :         PointSequenceSequence aPointSeq( 1 );
     786           0 :         aPointSeq[ 0 ] = ContainerHelper::vectorToSequence( aAbsPoints );
     787           0 :         PropertySet aPropSet( xShape );
     788           0 :         aPropSet.setProperty( PROP_PolyPolygon, aPointSeq );
     789             :     }
     790           0 :     return xShape;
     791             : }
     792             : 
     793           0 : LineShape::LineShape(Drawing& rDrawing)
     794           0 :     : SimpleShape(rDrawing, "com.sun.star.drawing.LineShape")
     795             : {
     796           0 : }
     797             : 
     798           0 : awt::Rectangle LineShape::getAbsRectangle() const
     799             : {
     800           0 :     const GraphicHelper& rGraphicHelper = mrDrawing.getFilter().getGraphicHelper();
     801           0 :     awt::Rectangle aShapeRect;
     802           0 :     sal_Int32 nIndex = 0;
     803             : 
     804           0 :     aShapeRect.X = ConversionHelper::decodeMeasureToHmm(rGraphicHelper, maShapeModel.maFrom.getToken(0, ',', nIndex), 0, true, true);
     805           0 :     aShapeRect.Y = ConversionHelper::decodeMeasureToHmm(rGraphicHelper, maShapeModel.maFrom.getToken(0, ',', nIndex), 0, false, true);
     806           0 :     nIndex = 0;
     807           0 :     aShapeRect.Width = ConversionHelper::decodeMeasureToHmm(rGraphicHelper, maShapeModel.maTo.getToken(0, ',', nIndex), 0, true, true) - aShapeRect.X;
     808           0 :     aShapeRect.Height = ConversionHelper::decodeMeasureToHmm(rGraphicHelper, maShapeModel.maTo.getToken(0, ',', nIndex), 0, false, true) - aShapeRect.Y;
     809           0 :     return aShapeRect;
     810             : }
     811             : 
     812           0 : awt::Rectangle LineShape::getRelRectangle() const
     813             : {
     814           0 :     awt::Rectangle aShapeRect;
     815           0 :     sal_Int32 nIndex = 0;
     816             : 
     817           0 :     aShapeRect.X = maShapeModel.maFrom.getToken(0, ',', nIndex).toInt32();
     818           0 :     aShapeRect.Y = maShapeModel.maFrom.getToken(0, ',', nIndex).toInt32();
     819           0 :     nIndex = 0;
     820           0 :     aShapeRect.Width = maShapeModel.maTo.getToken(0, ',', nIndex).toInt32() - aShapeRect.X;
     821           0 :     aShapeRect.Height = maShapeModel.maTo.getToken(0, ',', nIndex).toInt32() - aShapeRect.Y;
     822           0 :     return aShapeRect;
     823             : }
     824             : 
     825             : 
     826             : 
     827           0 : BezierShape::BezierShape(Drawing& rDrawing)
     828           0 :     : SimpleShape(rDrawing, "com.sun.star.drawing.OpenBezierShape")
     829             : {
     830           0 : }
     831             : 
     832           0 : Reference< XShape > BezierShape::implConvertAndInsert( const Reference< XShapes >& rxShapes, const awt::Rectangle& rShapeRect ) const
     833             : {
     834             :     // If we have an 'x' in the last part of the path it means it is closed...
     835           0 :     sal_Int32 nPos = maShapeModel.maVmlPath.lastIndexOf(',');
     836           0 :     if ( nPos != -1 && maShapeModel.maVmlPath.copy(nPos).indexOf('x') != -1 )
     837             :     {
     838           0 :         const_cast<BezierShape*>( this )->setService( "com.sun.star.drawing.ClosedBezierShape" );
     839             :     }
     840             : 
     841           0 :     awt::Rectangle aCoordSys = getCoordSystem();
     842           0 :     PolyPolygonBezierCoords aBezierCoords;
     843             : 
     844           0 :     if( (aCoordSys.Width > 0) && (aCoordSys.Height > 0) )
     845             :     {
     846           0 :         const GraphicHelper& rGraphicHelper = mrDrawing.getFilter().getGraphicHelper();
     847             : 
     848             :         // Bezier paths may consist of one or more sub-paths
     849             :         typedef ::std::vector< ::std::vector< awt::Point > > SubPathList;
     850             :         typedef ::std::vector< ::std::vector< PolygonFlags > > FlagsList;
     851           0 :         SubPathList aCoordLists;
     852           0 :         FlagsList aFlagLists;
     853           0 :         sal_Int32 nIndex = 0;
     854             : 
     855             :         // Curve defined by to, from, control1 and control2 attributes
     856           0 :         if ( maShapeModel.maVmlPath.isEmpty() )
     857             :         {
     858           0 :             aCoordLists.push_back( ::std::vector< awt::Point >() );
     859           0 :             aFlagLists.push_back( ::std::vector< PolygonFlags >() );
     860             : 
     861             :             // Start point
     862           0 :             aCoordLists[ 0 ].push_back(
     863           0 :                 awt::Point(ConversionHelper::decodeMeasureToHmm( rGraphicHelper, maShapeModel.maFrom.getToken( 0, ',', nIndex ), 0, true, true ),
     864           0 :                   ConversionHelper::decodeMeasureToHmm( rGraphicHelper, maShapeModel.maFrom.getToken( 0, ',', nIndex ), 0, false, true ) ) );
     865             :             // Control point 1
     866           0 :             aCoordLists[ 0 ].push_back(
     867           0 :                 awt::Point( ConversionHelper::decodeMeasureToHmm( rGraphicHelper, maShapeModel.maControl1.getToken( 0, ',', nIndex ), 0, true, true ),
     868           0 :                       ConversionHelper::decodeMeasureToHmm( rGraphicHelper, maShapeModel.maControl1.getToken( 0, ',', nIndex ), 0, false, true ) ) );
     869             :             // Control point 2
     870           0 :             aCoordLists[ 0 ].push_back(
     871           0 :                 awt::Point( ConversionHelper::decodeMeasureToHmm( rGraphicHelper, maShapeModel.maControl2.getToken( 0, ',', nIndex ), 0, true, true ),
     872           0 :                       ConversionHelper::decodeMeasureToHmm( rGraphicHelper, maShapeModel.maControl2.getToken( 0, ',', nIndex ), 0, false, true ) ) );
     873             :             // End point
     874           0 :             aCoordLists[ 0 ].push_back(
     875           0 :                 awt::Point( ConversionHelper::decodeMeasureToHmm( rGraphicHelper, maShapeModel.maTo.getToken( 0, ',', nIndex ), 0, true, true ),
     876           0 :                       ConversionHelper::decodeMeasureToHmm( rGraphicHelper, maShapeModel.maTo.getToken( 0, ',', nIndex ), 0, false, true ) ) );
     877             : 
     878             :             // First and last points are normals, points 2 and 4 are controls
     879           0 :             aFlagLists[ 0 ].resize( aCoordLists[ 0 ].size(), PolygonFlags_CONTROL );
     880           0 :             aFlagLists[ 0 ][ 0 ] = PolygonFlags_NORMAL;
     881           0 :             aFlagLists[ 0 ].back() = PolygonFlags_NORMAL;
     882             :         }
     883             :         // Curve defined by path attribute
     884             :         else
     885             :         {
     886             :             // Parse VML path string and convert to absolute coordinates
     887           0 :             ConversionHelper::decodeVmlPath( aCoordLists, aFlagLists, maShapeModel.maVmlPath );
     888             : 
     889           0 :             for ( SubPathList::iterator aListIt = aCoordLists.begin(); aListIt != aCoordLists.end(); ++aListIt )
     890           0 :                 for ( ::std::vector< awt::Point >::iterator aPointIt = (*aListIt).begin(); aPointIt != (*aListIt).end(); ++aPointIt)
     891             :                 {
     892           0 :                     (*aPointIt) = lclGetAbsPoint( (*aPointIt), rShapeRect, aCoordSys );
     893             :                 }
     894             :         }
     895             : 
     896           0 :         aBezierCoords.Coordinates.realloc( aCoordLists.size() );
     897           0 :         for ( unsigned int i = 0; i < aCoordLists.size(); i++ )
     898           0 :             aBezierCoords.Coordinates[i] = ContainerHelper::vectorToSequence( aCoordLists[i] );
     899             : 
     900           0 :         aBezierCoords.Flags.realloc( aFlagLists.size() );
     901           0 :         for ( unsigned int i = 0; i < aFlagLists.size(); i++ )
     902           0 :             aBezierCoords.Flags[i] = ContainerHelper::vectorToSequence( aFlagLists[i] );
     903             : 
     904           0 :         if( !aCoordLists.front().empty() && !aCoordLists.back().empty()
     905           0 :             && aCoordLists.front().front().X == aCoordLists.back().back().X
     906           0 :             && aCoordLists.front().front().Y == aCoordLists.back().back().Y )
     907             :         { // HACK: If the shape is in fact closed, which can be found out only when the path is known,
     908             :           // force to closed bezier shape (otherwise e.g. fill won't work).
     909           0 :             const_cast< BezierShape* >( this )->setService( "com.sun.star.drawing.ClosedBezierShape" );
     910           0 :         }
     911             :     }
     912             : 
     913           0 :     Reference< XShape > xShape = SimpleShape::implConvertAndInsert( rxShapes, rShapeRect );
     914             : 
     915           0 :     if( aBezierCoords.Coordinates.hasElements())
     916             :     {
     917           0 :         PropertySet aPropSet( xShape );
     918           0 :         aPropSet.setProperty( PROP_PolyPolygonBezier, aBezierCoords );
     919             :     }
     920             : 
     921             :     // Hacky way of ensuring the shape is correctly sized/positioned
     922           0 :     xShape->setSize( awt::Size( rShapeRect.Width, rShapeRect.Height ) );
     923           0 :     xShape->setPosition( awt::Point( rShapeRect.X, rShapeRect.Y ) );
     924           0 :     return xShape;
     925             : }
     926             : 
     927             : 
     928             : 
     929           0 : CustomShape::CustomShape( Drawing& rDrawing ) :
     930           0 :     SimpleShape( rDrawing, "com.sun.star.drawing.CustomShape" )
     931             : {
     932           0 : }
     933             : 
     934           0 : Reference< XShape > CustomShape::implConvertAndInsert( const Reference< XShapes >& rxShapes, const awt::Rectangle& rShapeRect ) const
     935             : {
     936             :     // try to create a custom shape
     937           0 :     Reference< XShape > xShape = SimpleShape::implConvertAndInsert( rxShapes, rShapeRect );
     938           0 :     if( xShape.is() ) try
     939             :     {
     940             :         // create the custom shape geometry
     941           0 :         Reference< XEnhancedCustomShapeDefaulter > xDefaulter( xShape, UNO_QUERY_THROW );
     942           0 :         xDefaulter->createCustomShapeDefaults( OUString::number( getShapeType() ) );
     943             :         // convert common properties
     944           0 :         convertShapeProperties( xShape );
     945             :     }
     946           0 :     catch( Exception& )
     947             :     {
     948             :     }
     949           0 :     return xShape;
     950             : }
     951             : 
     952             : 
     953             : 
     954           0 : ComplexShape::ComplexShape( Drawing& rDrawing ) :
     955           0 :     CustomShape( rDrawing )
     956             : {
     957           0 : }
     958             : 
     959           0 : Reference< XShape > ComplexShape::implConvertAndInsert( const Reference< XShapes >& rxShapes, const awt::Rectangle& rShapeRect ) const
     960             : {
     961           0 :     XmlFilterBase& rFilter = mrDrawing.getFilter();
     962           0 :     sal_Int32 nShapeType = getShapeType();
     963           0 :     OUString aGraphicPath = getGraphicPath();
     964             : 
     965             :     // try to find registered OLE object info
     966           0 :     if( const OleObjectInfo* pOleObjectInfo = mrDrawing.getOleObjectInfo( maTypeModel.maShapeId ) )
     967             :     {
     968             :         SAL_WARN_IF(
     969             :             nShapeType != VML_SHAPETYPE_PICTUREFRAME, "oox",
     970             :             "ComplexShape::implConvertAndInsert - unexpected shape type");
     971             : 
     972             :         // if OLE object is embedded into a DrawingML shape (PPTX), do not create it here
     973           0 :         if( pOleObjectInfo->mbDmlShape )
     974           0 :             return Reference< XShape >();
     975             : 
     976           0 :         PropertyMap aOleProps;
     977           0 :         awt::Size aOleSize( rShapeRect.Width, rShapeRect.Height );
     978           0 :         if( rFilter.getOleObjectHelper().importOleObject( aOleProps, *pOleObjectInfo, aOleSize ) )
     979             :         {
     980           0 :             Reference< XShape > xShape = mrDrawing.createAndInsertXShape( "com.sun.star.drawing.OLE2Shape", rxShapes, rShapeRect );
     981           0 :             if( xShape.is() )
     982             :             {
     983             :                 // set the replacement graphic
     984           0 :                 if( !aGraphicPath.isEmpty() )
     985             :                 {
     986           0 :                     Reference< XGraphic > xGraphic = rFilter.getGraphicHelper().importEmbeddedGraphic( aGraphicPath );
     987           0 :                     if( xGraphic.is() )
     988           0 :                         aOleProps.setProperty( PROP_Graphic, xGraphic);
     989             :                 }
     990             : 
     991           0 :                 PropertySet aPropSet( xShape );
     992           0 :                 aPropSet.setProperties( aOleProps );
     993             : 
     994           0 :                 return xShape;
     995           0 :             }
     996           0 :         }
     997             :     }
     998             : 
     999             :     // try to find registered form control info
    1000           0 :     const ControlInfo* pControlInfo = mrDrawing.getControlInfo( maTypeModel.maShapeId );
    1001           0 :     if( pControlInfo && !pControlInfo->maFragmentPath.isEmpty() )
    1002             :     {
    1003             :         OSL_ENSURE( nShapeType == VML_SHAPETYPE_HOSTCONTROL, "ComplexShape::implConvertAndInsert - unexpected shape type" );
    1004           0 :         OUString aShapeName = getShapeName();
    1005           0 :         if( !aShapeName.isEmpty() )
    1006             :         {
    1007             :             OSL_ENSURE( aShapeName == pControlInfo->maName, "ComplexShape::implConvertAndInsert - control name mismatch" );
    1008             :             // load the control properties from fragment
    1009           0 :             ::oox::ole::EmbeddedControl aControl( aShapeName );
    1010           0 :             if( rFilter.importFragment( new ::oox::ole::AxControlFragment( rFilter, pControlInfo->maFragmentPath, aControl ) ) )
    1011             :             {
    1012             :                 // create and return the control shape (including control model)
    1013           0 :                 sal_Int32 nCtrlIndex = -1;
    1014           0 :                 Reference< XShape > xShape = mrDrawing.createAndInsertXControlShape( aControl, rxShapes, rShapeRect, nCtrlIndex );
    1015             :                 // on error, proceed and try to create picture from replacement image
    1016           0 :                 if( xShape.is() )
    1017           0 :                     return xShape;
    1018           0 :             }
    1019           0 :         }
    1020             :     }
    1021             : 
    1022             :     // host application wants to create the shape (do not try failed OLE controls again)
    1023           0 :     if( (nShapeType == VML_SHAPETYPE_HOSTCONTROL) && !pControlInfo )
    1024             :     {
    1025             :         OSL_ENSURE( getClientData(), "ComplexShape::implConvertAndInsert - missing client data" );
    1026           0 :         Reference< XShape > xShape = mrDrawing.createAndInsertClientXShape( *this, rxShapes, rShapeRect );
    1027           0 :         if( xShape.is() )
    1028           0 :             return xShape;
    1029             :     }
    1030             : 
    1031             :     // try to create a picture object
    1032           0 :     if( !aGraphicPath.isEmpty() )
    1033           0 :         return SimpleShape::createPictureObject(rxShapes, rShapeRect, aGraphicPath);
    1034             : 
    1035             :     // default: try to create a custom shape
    1036           0 :     return CustomShape::implConvertAndInsert( rxShapes, rShapeRect );
    1037             : }
    1038             : 
    1039             : 
    1040             : 
    1041           0 : GroupShape::GroupShape( Drawing& rDrawing ) :
    1042             :     ShapeBase( rDrawing ),
    1043           0 :     mxChildren( new ShapeContainer( rDrawing ) )
    1044             : {
    1045           0 : }
    1046             : 
    1047           0 : GroupShape::~GroupShape()
    1048             : {
    1049           0 : }
    1050             : 
    1051           0 : void GroupShape::finalizeFragmentImport()
    1052             : {
    1053             :     // basic shape processing
    1054           0 :     ShapeBase::finalizeFragmentImport();
    1055             :     // finalize all child shapes
    1056           0 :     mxChildren->finalizeFragmentImport();
    1057           0 : }
    1058             : 
    1059           0 : const ShapeType* GroupShape::getChildTypeById( const OUString& rShapeId ) const
    1060             : {
    1061           0 :     return mxChildren->getShapeTypeById( rShapeId, true );
    1062             : }
    1063             : 
    1064           0 : const ShapeBase* GroupShape::getChildById( const OUString& rShapeId ) const
    1065             : {
    1066           0 :     return mxChildren->getShapeById( rShapeId, true );
    1067             : }
    1068             : 
    1069           0 : Reference< XShape > GroupShape::implConvertAndInsert( const Reference< XShapes >& rxShapes, const awt::Rectangle& rShapeRect ) const
    1070             : {
    1071           0 :     Reference< XShape > xGroupShape;
    1072             :     // check that this shape contains children and a valid coordinate system
    1073           0 :     ShapeParentAnchor aParentAnchor;
    1074           0 :     aParentAnchor.maShapeRect = rShapeRect;
    1075           0 :     aParentAnchor.maCoordSys = getCoordSystem();
    1076           0 :     if( !mxChildren->empty() && (aParentAnchor.maCoordSys.Width > 0) && (aParentAnchor.maCoordSys.Height > 0) ) try
    1077             :     {
    1078           0 :         xGroupShape = mrDrawing.createAndInsertXShape( "com.sun.star.drawing.GroupShape", rxShapes, rShapeRect );
    1079           0 :         Reference< XShapes > xChildShapes( xGroupShape, UNO_QUERY_THROW );
    1080           0 :         mxChildren->convertAndInsert( xChildShapes, &aParentAnchor );
    1081           0 :         if( !xChildShapes->hasElements() )
    1082             :         {
    1083             :             SAL_WARN("oox", "no child shape has been created - deleting the group shape");
    1084           0 :             rxShapes->remove( xGroupShape );
    1085           0 :             xGroupShape.clear();
    1086           0 :         }
    1087             :     }
    1088           0 :     catch( Exception& )
    1089             :     {
    1090             :     }
    1091             : 
    1092           0 :     if (!maTypeModel.maEditAs.isEmpty())
    1093             :     {
    1094           0 :         uno::Reference<beans::XPropertySet> xPropertySet(xGroupShape, uno::UNO_QUERY);
    1095           0 :         uno::Sequence<beans::PropertyValue> aGrabBag;
    1096           0 :         xPropertySet->getPropertyValue("InteropGrabBag") >>= aGrabBag;
    1097           0 :         beans::PropertyValue aPair;
    1098           0 :         aPair.Name = "mso-edit-as";
    1099           0 :         aPair.Value = uno::makeAny(maTypeModel.maEditAs);
    1100           0 :        if (aGrabBag.hasElements())
    1101             :        {
    1102           0 :             sal_Int32 nLength = aGrabBag.getLength();
    1103           0 :             aGrabBag.realloc(nLength + 1);
    1104           0 :             aGrabBag[nLength] = aPair;
    1105             :        }
    1106             :        else
    1107             :        {
    1108           0 :            aGrabBag.realloc(1);
    1109           0 :            aGrabBag[0] = aPair;
    1110             :        }
    1111           0 :        xPropertySet->setPropertyValue("InteropGrabBag", uno::makeAny(aGrabBag));
    1112             :     }
    1113             :     // Make sure group shapes are inline as well, unless there is an explicit different style.
    1114           0 :     PropertySet aPropertySet(xGroupShape);
    1115           0 :     lcl_SetAnchorType(aPropertySet, maTypeModel);
    1116           0 :     if (!maTypeModel.maRotation.isEmpty())
    1117           0 :         lcl_SetRotation(aPropertySet, maTypeModel.maRotation.toInt32());
    1118           0 :     return xGroupShape;
    1119             : }
    1120             : 
    1121             : 
    1122             : 
    1123             : } // namespace vml
    1124           0 : } // namespace oox
    1125             : 
    1126             : /* vim:set shiftwidth=4 softtabstop=4 expandtab: */

Generated by: LCOV version 1.10