fdo#74697 Add Bluez 5 support for impress remote.
[LibreOffice.git] / svx / source / customshapes / EnhancedCustomShapeEngine.cxx
blob46bca87b1b5b139ae163821380fe8e51e005a370
1 /* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
2 /*
3 * This file is part of the LibreOffice project.
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/.
9 * This file incorporates work covered by the following license notice:
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 .
20 #include "EnhancedCustomShapeEngine.hxx"
21 #include "svx/EnhancedCustomShape2d.hxx"
22 #include "EnhancedCustomShape3d.hxx"
23 #include "EnhancedCustomShapeFontWork.hxx"
24 #include "EnhancedCustomShapeHandle.hxx"
25 #include "svx/EnhancedCustomShapeGeometry.hxx"
26 #include <svx/unoshape.hxx>
27 #include "svx/unopage.hxx"
28 #include "svx/unoapi.hxx"
29 #include <svx/svdobj.hxx>
30 #include <svx/svdoashp.hxx>
31 #include <svx/svdogrp.hxx>
32 #include <svx/svdorect.hxx>
33 #include <editeng/outlobj.hxx>
34 #include <editeng/outliner.hxx>
35 #include <svx/svdoutl.hxx>
36 #include <svl/itemset.hxx>
37 #include <svx/svdopath.hxx>
38 #include <svx/svdpage.hxx>
39 #include <svx/svdmodel.hxx>
40 #include "svx/svditer.hxx"
41 #include <uno/mapping.hxx>
42 #include <basegfx/polygon/b2dpolypolygontools.hxx>
43 #include <basegfx/tools/unotools.hxx>
44 #include <com/sun/star/document/XActionLockable.hpp>
46 using namespace css;
47 using namespace css::uno;
49 // ---------------------------
50 // - EnhancedCustomShapeEngine -
51 // ---------------------------
53 OUString EnhancedCustomShapeEngine_getImplementationName()
54 throw( RuntimeException )
56 return OUString( "com.sun.star.drawing.EnhancedCustomShapeEngine" );
58 sal_Bool SAL_CALL EnhancedCustomShapeEngine_supportsService( const OUString& ServiceName )
59 throw( RuntimeException )
61 return ServiceName == "com.sun.star.drawing.CustomShapeEngine";
63 Sequence< OUString > SAL_CALL EnhancedCustomShapeEngine_getSupportedServiceNames()
64 throw( RuntimeException )
66 Sequence< OUString > aRet(1);
67 OUString* pArray = aRet.getArray();
68 pArray[0] = "com.sun.star.drawing.CustomShapeEngine";
69 return aRet;
72 // -----------------------------------------------------------------------------
74 EnhancedCustomShapeEngine::EnhancedCustomShapeEngine( const Reference< lang::XMultiServiceFactory >& rxMgr ) :
75 mxFact ( rxMgr ),
76 mbForceGroupWithText ( sal_False )
79 EnhancedCustomShapeEngine::~EnhancedCustomShapeEngine()
83 // XInterface -----------------------------------------------------------------
85 void SAL_CALL EnhancedCustomShapeEngine::acquire() throw()
87 OWeakObject::acquire();
89 void SAL_CALL EnhancedCustomShapeEngine::release() throw()
91 OWeakObject::release();
94 // XInitialization ------------------------------------------------------------
96 void SAL_CALL EnhancedCustomShapeEngine::initialize( const Sequence< Any >& aArguments )
97 throw ( Exception, RuntimeException )
99 sal_Int32 i;
100 Sequence< beans::PropertyValue > aParameter;
101 for ( i = 0; i < aArguments.getLength(); i++ )
103 if ( aArguments[ i ] >>= aParameter )
104 break;
106 for ( i = 0; i < aParameter.getLength(); i++ )
108 const beans::PropertyValue& rProp = aParameter[ i ];
109 if ( rProp.Name == "CustomShape" )
110 rProp.Value >>= mxShape;
111 else if ( rProp.Name == "ForceGroupWithText" )
112 rProp.Value >>= mbForceGroupWithText;
116 // XServiceInfo ---------------------------------------------------------------
118 OUString SAL_CALL EnhancedCustomShapeEngine::getImplementationName()
119 throw( RuntimeException )
121 return EnhancedCustomShapeEngine_getImplementationName();
123 sal_Bool SAL_CALL EnhancedCustomShapeEngine::supportsService( const OUString& rServiceName )
124 throw( RuntimeException )
126 return EnhancedCustomShapeEngine_supportsService( rServiceName );
128 Sequence< OUString > SAL_CALL EnhancedCustomShapeEngine::getSupportedServiceNames()
129 throw ( RuntimeException )
131 return EnhancedCustomShapeEngine_getSupportedServiceNames();
134 // XCustomShapeEngine -----------------------------------------------------------
136 SdrObject* EnhancedCustomShapeEngine::ImplForceGroupWithText( const SdrObjCustomShape* pCustoObj, SdrObject* pRenderedShape )
138 bool bHasText = pCustoObj->HasText();
139 if ( pRenderedShape || bHasText )
141 // applying shadow
142 const SdrObject* pShadowGeometry = pCustoObj->GetSdrObjectShadowFromCustomShape();
143 if ( pShadowGeometry )
145 if ( pRenderedShape )
147 if ( !pRenderedShape->ISA( SdrObjGroup ) )
149 SdrObject* pTmp = pRenderedShape;
150 pRenderedShape = new SdrObjGroup();
151 ((SdrObjGroup*)pRenderedShape)->GetSubList()->NbcInsertObject( pTmp );
153 ((SdrObjGroup*)pRenderedShape)->GetSubList()->NbcInsertObject( pShadowGeometry->Clone(), 0 );
155 else
156 pRenderedShape = pShadowGeometry->Clone();
159 // apply text
160 if ( bHasText )
162 // #i37011# also create a text object and add at rPos + 1
163 SdrTextObj* pTextObj = (SdrTextObj*)SdrObjFactory::MakeNewObject(
164 pCustoObj->GetObjInventor(), OBJ_TEXT, 0L, pCustoObj->GetModel());
166 // Copy text content
167 OutlinerParaObject* pParaObj = pCustoObj->GetOutlinerParaObject();
168 if( pParaObj )
169 pTextObj->NbcSetOutlinerParaObject( new OutlinerParaObject(*pParaObj) );
171 // copy all attributes
172 SfxItemSet aTargetItemSet( pCustoObj->GetMergedItemSet() );
174 // clear fill and line style
175 aTargetItemSet.Put(XLineStyleItem(XLINE_NONE));
176 aTargetItemSet.Put(XFillStyleItem(XFILL_NONE));
178 // get the text bounds and set at text object
179 Rectangle aTextBounds = pCustoObj->GetSnapRect();
180 SdrObject* pSdrObjCustomShape( GetSdrObjectFromXShape( mxShape ) );
181 if ( pSdrObjCustomShape )
183 EnhancedCustomShape2d aCustomShape2d( pSdrObjCustomShape );
184 aTextBounds = aCustomShape2d.GetTextRect();
186 pTextObj->SetSnapRect( aTextBounds );
188 // if rotated, copy GeoStat, too.
189 const GeoStat& rSourceGeo = pCustoObj->GetGeoStat();
190 if ( rSourceGeo.nDrehWink )
192 pTextObj->NbcRotate(
193 pCustoObj->GetSnapRect().Center(), rSourceGeo.nDrehWink,
194 rSourceGeo.nSin, rSourceGeo.nCos);
197 // set modified ItemSet at text object
198 pTextObj->SetMergedItemSet(aTargetItemSet);
200 if ( pRenderedShape )
202 if ( !pRenderedShape->ISA( SdrObjGroup ) )
204 SdrObject* pTmp = pRenderedShape;
205 pRenderedShape = new SdrObjGroup();
206 ((SdrObjGroup*)pRenderedShape)->GetSubList()->NbcInsertObject( pTmp );
208 ((SdrObjGroup*)pRenderedShape)->GetSubList()->NbcInsertObject( pTextObj, LIST_APPEND );
210 else
211 pRenderedShape = pTextObj;
214 // force group
215 if ( pRenderedShape )
217 if ( !pRenderedShape->ISA( SdrObjGroup ) )
219 SdrObject* pTmp = pRenderedShape;
220 pRenderedShape = new SdrObjGroup();
221 ((SdrObjGroup*)pRenderedShape)->GetSubList()->NbcInsertObject( pTmp );
223 pRenderedShape->SetPage( pCustoObj->GetPage() );
224 pRenderedShape->SetModel( pCustoObj->GetModel() );
227 return pRenderedShape;
230 void SetTemporary( uno::Reference< drawing::XShape >& xShape )
232 if ( xShape.is() )
234 SvxShape* pShape = SvxShape::getImplementation( xShape );
235 if ( pShape )
236 pShape->TakeSdrObjectOwnership();
240 Reference< drawing::XShape > SAL_CALL EnhancedCustomShapeEngine::render()
241 throw ( RuntimeException )
243 Reference< drawing::XShape > xShape;
244 SdrObject* pSdrObjCustomShape( GetSdrObjectFromXShape( mxShape ) );
245 if ( pSdrObjCustomShape )
247 // retrieving the TextPath property to check if feature is enabled
248 SdrCustomShapeGeometryItem& rGeometryItem = (SdrCustomShapeGeometryItem&)
249 pSdrObjCustomShape->GetMergedItem( SDRATTR_CUSTOMSHAPE_GEOMETRY );
250 sal_Bool bTextPathOn = sal_False;
251 const OUString sTextPath( "TextPath" );
252 uno::Any* pAny = rGeometryItem.GetPropertyValueByName( sTextPath, sTextPath );
253 if ( pAny )
254 *pAny >>= bTextPathOn;
256 EnhancedCustomShape2d aCustomShape2d( pSdrObjCustomShape );
257 sal_Int32 nRotateAngle = aCustomShape2d.GetRotateAngle();
258 bool bPostRotateAngle = aCustomShape2d.IsPostRotate();
260 sal_Bool bFlipV = aCustomShape2d.IsFlipVert();
261 sal_Bool bFlipH = aCustomShape2d.IsFlipHorz();
262 sal_Bool bLineGeometryNeededOnly = bTextPathOn;
264 SdrObject* pRenderedShape = aCustomShape2d.CreateObject( bLineGeometryNeededOnly );
265 if ( pRenderedShape )
267 if ( bTextPathOn )
269 SdrObject* pRenderedFontWork = EnhancedCustomShapeFontWork::CreateFontWork( pRenderedShape, pSdrObjCustomShape );
270 if ( pRenderedFontWork )
272 SdrObject::Free( pRenderedShape );
273 pRenderedShape = pRenderedFontWork;
276 SdrObject* pRenderedShape3d = EnhancedCustomShape3d::Create3DObject( pRenderedShape, pSdrObjCustomShape );
277 if ( pRenderedShape3d )
279 bFlipV = bFlipH = sal_False;
280 nRotateAngle = 0;
281 SdrObject::Free( pRenderedShape );
282 pRenderedShape = pRenderedShape3d;
284 Rectangle aRect( pSdrObjCustomShape->GetSnapRect() );
286 const GeoStat& rGeoStat = ((SdrObjCustomShape*)pSdrObjCustomShape)->GetGeoStat();
287 if ( rGeoStat.nShearWink )
289 long nShearWink = rGeoStat.nShearWink;
290 double nTan = rGeoStat.nTan;
291 if ((bFlipV&&!bFlipH )||(bFlipH&&!bFlipV))
293 nShearWink = -nShearWink;
294 nTan = -nTan;
296 pRenderedShape->Shear( pSdrObjCustomShape->GetSnapRect().Center(), nShearWink, nTan, sal_False);
298 if( !bPostRotateAngle && nRotateAngle )
300 double a = nRotateAngle * F_PI18000;
301 pRenderedShape->NbcRotate( pSdrObjCustomShape->GetSnapRect().Center(), nRotateAngle, sin( a ), cos( a ) );
303 if ( bFlipV )
305 Point aLeft( aRect.Left(), ( aRect.Top() + aRect.Bottom() ) >> 1 );
306 Point aRight( aLeft.X() + 1000, aLeft.Y() );
307 pRenderedShape->NbcMirror( aLeft, aRight );
309 if ( bFlipH )
311 Point aTop( ( aRect.Left() + aRect.Right() ) >> 1, aRect.Top() );
312 Point aBottom( aTop.X(), aTop.Y() + 1000 );
313 pRenderedShape->NbcMirror( aTop, aBottom );
315 // Specifically for pptx imports
316 if( bPostRotateAngle && nRotateAngle )
318 double a = nRotateAngle * F_PI18000;
319 pRenderedShape->NbcRotate( pSdrObjCustomShape->GetSnapRect().Center(), nRotateAngle, sin( a ), cos( a ) );
321 pRenderedShape->NbcSetStyleSheet( pSdrObjCustomShape->GetStyleSheet(), sal_True );
322 pRenderedShape->RecalcSnapRect();
325 if ( mbForceGroupWithText )
326 pRenderedShape = ImplForceGroupWithText( (SdrObjCustomShape*)pSdrObjCustomShape, pRenderedShape );
328 if ( pRenderedShape )
330 aCustomShape2d.ApplyGluePoints( pRenderedShape );
331 xShape = SvxDrawPage::CreateShapeByTypeAndInventor( pRenderedShape->GetObjIdentifier(),
332 pRenderedShape->GetObjInventor(), pRenderedShape, NULL );
334 SetTemporary( xShape );
336 return xShape;
339 awt::Rectangle SAL_CALL EnhancedCustomShapeEngine::getTextBounds()
340 throw ( RuntimeException )
342 awt::Rectangle aTextRect;
343 SdrObject* pSdrObjCustomShape( GetSdrObjectFromXShape( mxShape ) );
344 uno::Reference< document::XActionLockable > xLockable( mxShape, uno::UNO_QUERY );
345 if ( pSdrObjCustomShape && pSdrObjCustomShape->GetModel() && xLockable.is() && !xLockable->isActionLocked() )
347 if ( pSdrObjCustomShape )
349 EnhancedCustomShape2d aCustomShape2d( pSdrObjCustomShape );
350 Rectangle aRect( aCustomShape2d.GetTextRect() );
351 aTextRect.X = aRect.Left();
352 aTextRect.Y = aRect.Top();
353 aTextRect.Width = aRect.GetWidth();
354 aTextRect.Height = aRect.GetHeight();
357 return aTextRect;
360 drawing::PolyPolygonBezierCoords SAL_CALL EnhancedCustomShapeEngine::getLineGeometry()
361 throw ( RuntimeException )
363 drawing::PolyPolygonBezierCoords aPolyPolygonBezierCoords;
364 SdrObject* pSdrObjCustomShape( GetSdrObjectFromXShape( mxShape ) );
365 if ( pSdrObjCustomShape )
367 EnhancedCustomShape2d aCustomShape2d( pSdrObjCustomShape );
368 SdrObject* pObj = aCustomShape2d.CreateLineGeometry();
369 if ( pObj )
371 Rectangle aRect( pSdrObjCustomShape->GetSnapRect() );
372 sal_Bool bFlipV = aCustomShape2d.IsFlipVert();
373 sal_Bool bFlipH = aCustomShape2d.IsFlipHorz();
375 const GeoStat& rGeoStat = ((SdrObjCustomShape*)pSdrObjCustomShape)->GetGeoStat();
376 if ( rGeoStat.nShearWink )
378 long nShearWink = rGeoStat.nShearWink;
379 double nTan = rGeoStat.nTan;
380 if ((bFlipV&&!bFlipH )||(bFlipH&&!bFlipV))
382 nShearWink = -nShearWink;
383 nTan = -nTan;
385 pObj->Shear( aRect.Center(), nShearWink, nTan, sal_False);
387 sal_Int32 nRotateAngle = aCustomShape2d.GetRotateAngle();
388 if( nRotateAngle )
390 double a = nRotateAngle * F_PI18000;
391 pObj->NbcRotate( aRect.Center(), nRotateAngle, sin( a ), cos( a ) );
393 if ( bFlipH )
395 Point aTop( ( aRect.Left() + aRect.Right() ) >> 1, aRect.Top() );
396 Point aBottom( aTop.X(), aTop.Y() + 1000 );
397 pObj->NbcMirror( aTop, aBottom );
399 if ( bFlipV )
401 Point aLeft( aRect.Left(), ( aRect.Top() + aRect.Bottom() ) >> 1 );
402 Point aRight( aLeft.X() + 1000, aLeft.Y() );
403 pObj->NbcMirror( aLeft, aRight );
406 basegfx::B2DPolyPolygon aPolyPolygon;
407 SdrObjListIter aIter( *pObj, IM_DEEPWITHGROUPS );
409 while ( aIter.IsMore() )
411 SdrObject* pNewObj = NULL;
412 basegfx::B2DPolyPolygon aPP;
413 const SdrObject* pNext = aIter.Next();
415 if ( pNext->ISA( SdrPathObj ) )
417 aPP = ((SdrPathObj*)pNext)->GetPathPoly();
419 else
421 pNewObj = pNext->ConvertToPolyObj( sal_False, sal_False );
422 SdrPathObj* pPath = PTR_CAST( SdrPathObj, pNewObj );
423 if ( pPath )
424 aPP = pPath->GetPathPoly();
427 if ( aPP.count() )
428 aPolyPolygon.append(aPP);
430 SdrObject::Free( pNewObj );
432 SdrObject::Free( pObj );
433 basegfx::unotools::b2DPolyPolygonToPolyPolygonBezier( aPolyPolygon,
434 aPolyPolygonBezierCoords );
438 return aPolyPolygonBezierCoords;
441 Sequence< Reference< drawing::XCustomShapeHandle > > SAL_CALL EnhancedCustomShapeEngine::getInteraction()
442 throw ( RuntimeException )
444 sal_uInt32 i, nHdlCount = 0;
445 SdrObject* pSdrObjCustomShape = GetSdrObjectFromXShape( mxShape );
446 if ( pSdrObjCustomShape )
448 EnhancedCustomShape2d aCustomShape2d( pSdrObjCustomShape );
449 nHdlCount = aCustomShape2d.GetHdlCount();
451 Sequence< Reference< drawing::XCustomShapeHandle > > aSeq( nHdlCount );
452 for ( i = 0; i < nHdlCount; i++ )
453 aSeq[ i ] = new EnhancedCustomShapeHandle( mxShape, i );
454 return aSeq;
457 /* vim:set shiftwidth=4 softtabstop=4 expandtab: */