offapi/com/sun/star/animations/AnimationNodeType.idl               |    3 
 slideshow/Library_slideshow.mk                                     |    1 
 slideshow/source/engine/animationfactory.cxx                       |  314 
++++++++--
 slideshow/source/engine/animationnodes/animationcolornode.cxx      |    6 
 slideshow/source/engine/animationnodes/animationnodefactory.cxx    |    6 
 slideshow/source/engine/animationnodes/animationpathmotionnode.cxx |    3 
 slideshow/source/engine/animationnodes/animationphysicsnode.cxx    |   48 +
 slideshow/source/engine/animationnodes/animationphysicsnode.hxx    |   54 +
 slideshow/source/engine/animationnodes/animationsetnode.cxx        |    5 
 slideshow/source/engine/animationnodes/animationtransformnode.cxx  |    9 
 slideshow/source/engine/animationnodes/propertyanimationnode.cxx   |   15 
 slideshow/source/engine/box2dtools.cxx                             |   66 +-
 slideshow/source/engine/slide/slideimpl.cxx                        |    7 
 slideshow/source/engine/slideshowcontext.cxx                       |    6 
 slideshow/source/engine/slideshowimpl.cxx                          |    8 
 slideshow/source/engine/transitions/shapetransitionfactory.cxx     |    3 
 slideshow/source/inc/animationfactory.hxx                          |   16 
 slideshow/source/inc/box2dtools.hxx                                |   48 -
 slideshow/source/inc/slideshowcontext.hxx                          |    7 
 19 files changed, 542 insertions(+), 83 deletions(-)

New commits:
commit 28022cee396715bc4b474ed1571074dc721bbe13
Author:     Sarper Akdemir <q.sarperakde...@gmail.com>
AuthorDate: Thu Jun 11 19:29:38 2020 +0300
Commit:     Thorsten Behrens <thorsten.behr...@cib.de>
CommitDate: Sun Aug 9 23:44:00 2020 +0200

    make physics based animation effects part of the animation engine
    
    Wiring up and creating required classes for physics based
    animation effects to be part of the animation engine.
    
    Creating a new animation node AnimationPhysicsNode
    for physics based animation effects and PhysicsAnimation
    class that inherits the NumberAnimation in the animation
    factory.
    
    Change-Id: I1f125df5324673e9937b8164c0fc267c9683afa0
    Reviewed-on: https://gerrit.libreoffice.org/c/core/+/100151
    Tested-by: Jenkins
    Reviewed-by: Thorsten Behrens <thorsten.behr...@cib.de>

diff --git a/offapi/com/sun/star/animations/AnimationNodeType.idl 
b/offapi/com/sun/star/animations/AnimationNodeType.idl
index 31bed11ff728..d0cd6e268fd6 100644
--- a/offapi/com/sun/star/animations/AnimationNodeType.idl
+++ b/offapi/com/sun/star/animations/AnimationNodeType.idl
@@ -68,6 +68,9 @@ constants AnimationNodeType
     /** Defines a command effect. */
     const short COMMAND = 11;
 
+    /** Defines a physics animation */
+    const short ANIMATEPHYSICS = 12;
+
 };
 
 
diff --git a/slideshow/Library_slideshow.mk b/slideshow/Library_slideshow.mk
index 53324ea25dcc..3ff098c01639 100644
--- a/slideshow/Library_slideshow.mk
+++ b/slideshow/Library_slideshow.mk
@@ -75,6 +75,7 @@ $(eval $(call gb_Library_add_exception_objects,slideshow,\
     slideshow/source/engine/animationnodes/animationnodefactory \
     slideshow/source/engine/animationnodes/animationpathmotionnode \
     slideshow/source/engine/animationnodes/animationsetnode \
+    slideshow/source/engine/animationnodes/animationphysicsnode \
     slideshow/source/engine/animationnodes/animationtransformnode \
     slideshow/source/engine/animationnodes/animationtransitionfilternode \
     slideshow/source/engine/animationnodes/basecontainernode \
diff --git a/slideshow/source/engine/animationfactory.cxx 
b/slideshow/source/engine/animationfactory.cxx
index f81c37b77df3..bc1848f68435 100644
--- a/slideshow/source/engine/animationfactory.cxx
+++ b/slideshow/source/engine/animationfactory.cxx
@@ -35,6 +35,7 @@
 #include <basegfx/polygon/b2dpolygontools.hxx>
 #include <basegfx/polygon/b2dpolypolygontools.hxx>
 
+#include <box2dtools.hxx>
 
 using namespace ::com::sun::star;
 
@@ -203,7 +204,8 @@ namespace slideshow::internal
                                sal_Int16                    nAdditive,
                                const ShapeManagerSharedPtr& rShapeManager,
                                const ::basegfx::B2DVector&  rSlideSize,
-                               int                          nFlags ) :
+                               int                          nFlags,
+                               const box2d::utils::Box2DWorldSharedPtr& 
pBox2DWorld ) :
                     maPathPoly(),
                     mpShape(),
                     mpAttrLayer(),
@@ -212,7 +214,8 @@ namespace slideshow::internal
                     maShapeOrig(),
                     mnFlags( nFlags ),
                     mbAnimationStarted( false ),
-                    mnAdditive( nAdditive )
+                    mnAdditive( nAdditive ),
+                    mpBox2DWorld( pBox2DWorld )
                 {
                     ENSURE_OR_THROW( rShapeManager,
                                       "PathAnimation::PathAnimation(): Invalid 
ShapeManager" );
@@ -283,6 +286,10 @@ namespace slideshow::internal
 
                         if( mpShape->isContentChanged() )
                             mpShapeManager->notifyShapeUpdate( mpShape );
+
+                        // since animation ended zero out the linear velocity
+                        if( mpBox2DWorld->isInitialized() )
+                            mpBox2DWorld->queueLinearVelocityUpdate( 
mpShape->getXShape(), {0,0});
                     }
                 }
 
@@ -313,7 +320,11 @@ namespace slideshow::internal
                     mpAttrLayer->setPosition( rOutPos );
 
                     if( mpShape->isContentChanged() )
+                    {
                         mpShapeManager->notifyShapeUpdate( mpShape );
+                        if ( mpBox2DWorld->isInitialized() )
+                            mpBox2DWorld->queuePositionUpdate( 
mpShape->getXShape(), rOutPos );
+                    }
 
                     return true;
                 }
@@ -339,8 +350,152 @@ namespace slideshow::internal
                 const int                          mnFlags;
                 bool                               mbAnimationStarted;
                 sal_Int16                          mnAdditive;
+                box2d::utils::Box2DWorldSharedPtr  mpBox2DWorld;
             };
 
+            class PhysicsAnimation : public NumberAnimation
+            {
+            public:
+                PhysicsAnimation( const ::box2d::utils::Box2DWorldSharedPtr& 
pBox2DWorld,
+                                    const double                 fDuration,
+                                    const ShapeManagerSharedPtr& rShapeManager,
+                                    const ::basegfx::B2DVector&  rSlideSize,
+                                    int                          nFlags ) :
+                    mpShape(),
+                    mpAttrLayer(),
+                    mpShapeManager( rShapeManager ),
+                    maPageSize( rSlideSize ),
+                    mnFlags( nFlags ),
+                    mbAnimationStarted( false ),
+                    mpBox2DBody(),
+                    mpBox2DWorld( pBox2DWorld ),
+                    mfDuration(fDuration),
+                    mfPreviousElapsedTime(0.00f),
+                    mbIsBox2dWorldStepper(false)
+                {
+                    ENSURE_OR_THROW( rShapeManager,
+                                     "PhysicsAnimation::PhysicsAnimation(): 
Invalid ShapeManager" );
+                }
+
+                virtual ~PhysicsAnimation() override
+                {
+                    end_();
+                }
+
+                // Animation interface
+
+                virtual void prefetch() override
+                {}
+
+                virtual void start( const AnimatableShapeSharedPtr&     rShape,
+                                    const ShapeAttributeLayerSharedPtr& 
rAttrLayer ) override
+                {
+                    OSL_ENSURE( !mpShape,
+                                "PhysicsAnimation::start(): Shape already set" 
);
+                    OSL_ENSURE( !mpAttrLayer,
+                                "PhysicsAnimation::start(): Attribute layer 
already set" );
+
+                    mpShape = rShape;
+                    mpAttrLayer = rAttrLayer;
+
+                    if( !(mpBox2DWorld->isInitialized()) )
+                        mpBox2DWorld->initiateWorld(maPageSize);
+
+                    if( !(mpBox2DWorld->shapesInitialized()) )
+                        mpBox2DWorld->initateAllShapesAsStaticBodies( 
mpShapeManager );
+
+                    ENSURE_OR_THROW( rShape,
+                                     "PhysicsAnimation::start(): Invalid 
shape" );
+                    ENSURE_OR_THROW( rAttrLayer,
+                                     "PhysicsAnimation::start(): Invalid 
attribute layer" );
+
+                    mpBox2DBody = mpBox2DWorld->makeShapeDynamic( rShape );
+
+                    if( !mbAnimationStarted )
+                    {
+                        mbAnimationStarted = true;
+
+                        if( !(mnFlags & AnimationFactory::FLAG_NO_SPRITE) )
+                            mpShapeManager->enterAnimationMode( mpShape );
+                    }
+                }
+
+                virtual void end() override { end_(); }
+                void end_()
+                {
+                    if( mbIsBox2dWorldStepper )
+                    {
+                        mbIsBox2dWorldStepper = false;
+                        mpBox2DWorld->setHasWorldStepper(false);
+                    }
+
+                    if( mbAnimationStarted )
+                    {
+                        mbAnimationStarted = false;
+
+                        // Animation have ended for this body, make it static
+                        mpBox2DWorld->makeBodyStatic( mpBox2DBody );
+
+                        if( !(mnFlags & AnimationFactory::FLAG_NO_SPRITE) )
+                            mpShapeManager->leaveAnimationMode( mpShape );
+
+                        if( mpShape->isContentChanged() )
+                            mpShapeManager->notifyShapeUpdate( mpShape );
+                    }
+                }
+
+                // NumberAnimation interface
+
+
+                virtual bool operator()( double nValue ) override
+                {
+                    ENSURE_OR_RETURN_FALSE( mpAttrLayer && mpShape,
+                                       "PhysicsAnimation::operator(): Invalid 
ShapeAttributeLayer" );
+
+                    // if there are multiple physics animations going in 
parallel
+                    // Only one of them should step the box2d world
+                    if( !mpBox2DWorld->hasWorldStepper() )
+                    {
+                        mbIsBox2dWorldStepper = true;
+                        mpBox2DWorld->setHasWorldStepper(true);
+                    }
+
+                    if( mbIsBox2dWorldStepper )
+                    {
+                        double fPassedTime = (mfDuration * nValue) - 
mfPreviousElapsedTime;
+                        mfPreviousElapsedTime += mpBox2DWorld->stepAmount( 
fPassedTime );
+                    }
+
+                    mpAttrLayer->setPosition( mpBox2DBody->getPosition() );
+                    mpAttrLayer->setRotationAngle( mpBox2DBody->getAngle() );
+
+                    if( mpShape->isContentChanged() )
+                        mpShapeManager->notifyShapeUpdate( mpShape );
+
+                    return true;
+                }
+
+                virtual double getUnderlyingValue() const override
+                {
+                    ENSURE_OR_THROW( mpAttrLayer,
+                                      "PhysicsAnimation::getUnderlyingValue(): 
Invalid ShapeAttributeLayer" );
+
+                    return 0.0;
+                }
+
+            private:
+                AnimatableShapeSharedPtr           mpShape;
+                ShapeAttributeLayerSharedPtr       mpAttrLayer;
+                ShapeManagerSharedPtr              mpShapeManager;
+                const ::basegfx::B2DSize           maPageSize;
+                const int                          mnFlags;
+                bool                               mbAnimationStarted;
+                box2d::utils::Box2DBodySharedPtr   mpBox2DBody;
+                box2d::utils::Box2DWorldSharedPtr  mpBox2DWorld;
+                double                             mfDuration;
+                double                             mfPreviousElapsedTime;
+                bool                               mbIsBox2dWorldStepper;
+            };
 
             /** GenericAnimation template
 
@@ -405,7 +560,9 @@ namespace slideshow::internal
                                   ValueT         
(ShapeAttributeLayer::*pGetValue)() const,
                                   void           
(ShapeAttributeLayer::*pSetValue)( const ValueT& ),
                                   const ModifierFunctor&                
rGetterModifier,
-                                  const ModifierFunctor&                
rSetterModifier ) :
+                                  const ModifierFunctor&                
rSetterModifier,
+                                  const AttributeType                   
eAttrType,
+                                  const box2d::utils::Box2DWorldSharedPtr& 
pBox2DWorld ) :
                     mpShape(),
                     mpAttrLayer(),
                     mpShapeManager( rShapeManager ),
@@ -416,7 +573,9 @@ namespace slideshow::internal
                     maSetterModifier( rSetterModifier ),
                     mnFlags( nFlags ),
                     maDefaultValue(rDefaultValue),
-                    mbAnimationStarted( false )
+                    mbAnimationStarted( false ),
+                    meAttrType( eAttrType ),
+                    mpBox2DWorld ( pBox2DWorld )
                 {
                     ENSURE_OR_THROW( rShapeManager,
                                       "GenericAnimation::GenericAnimation(): 
Invalid ShapeManager" );
@@ -473,6 +632,11 @@ namespace slideshow::internal
 
                     mbAnimationStarted = false;
 
+                    if( mpBox2DWorld && mpBox2DWorld->isInitialized() )
+                    {
+                        mpBox2DWorld->queueShapeAnimationEndUpdate( 
mpShape->getXShape(), meAttrType );
+                    }
+
                     if( !(mnFlags & AnimationFactory::FLAG_NO_SPRITE) )
                         mpShapeManager->leaveAnimationMode( mpShape );
 
@@ -529,6 +693,11 @@ namespace slideshow::internal
 
                     ((*mpAttrLayer).*mpSetValueFunc)( maSetterModifier( x ) );
 
+                    if( mpBox2DWorld && mpBox2DWorld->isInitialized() )
+                    {
+                        mpBox2DWorld->queueShapeAnimationUpdate( 
mpShape->getXShape(), mpAttrLayer, meAttrType );
+                    }
+
                     if( mpShape->isContentChanged() )
                         mpShapeManager->notifyShapeUpdate( mpShape );
 
@@ -564,6 +733,9 @@ namespace slideshow::internal
 
                 const ValueT                       maDefaultValue;
                 bool                               mbAnimationStarted;
+
+                const AttributeType                meAttrType;
+                const box2d::utils::Box2DWorldSharedPtr mpBox2DWorld;
             };
 
             //Current c++0x draft (apparently) has std::identity, but not 
operator()
@@ -585,7 +757,9 @@ namespace slideshow::internal
                                       bool                              
(ShapeAttributeLayer::*pIsValid)() const,
                                       const typename AnimationBase::ValueType& 
                rDefaultValue,
                                       typename AnimationBase::ValueType 
(ShapeAttributeLayer::*pGetValue)() const,
-                                      void                              
(ShapeAttributeLayer::*pSetValue)( const typename AnimationBase::ValueType& ) )
+                                      void                              
(ShapeAttributeLayer::*pSetValue)( const typename AnimationBase::ValueType& ),
+                                      const AttributeType                      
                eAttrType,
+                                      const box2d::utils::Box2DWorldSharedPtr& 
                pBox2DWorld )
             {
                 return std::make_shared<GenericAnimation< AnimationBase,
                                           SGI_identity< typename 
AnimationBase::ValueType > >>(
@@ -597,7 +771,9 @@ namespace slideshow::internal
                                               pSetValue,
                                               // no modification necessary, 
use identity functor here
                                               SGI_identity< typename 
AnimationBase::ValueType >(),
-                                              SGI_identity< typename 
AnimationBase::ValueType >() );
+                                              SGI_identity< typename 
AnimationBase::ValueType >(),
+                                              eAttrType,
+                                              pBox2DWorld );
             }
 
             class Scaler
@@ -625,7 +801,9 @@ namespace slideshow::internal
                                                            double              
                                     nDefaultValue,
                                                            double              
              (ShapeAttributeLayer::*pGetValue)() const,
                                                            void                
              (ShapeAttributeLayer::*pSetValue)( const double& ),
-                                                           double              
                                     nScaleValue )
+                                                           double              
                                     nScaleValue,
+                                                           const AttributeType 
                                     eAttrType,
+                                                           const 
box2d::utils::Box2DWorldSharedPtr&                 pBox2DWorld )
             {
                 return std::make_shared<GenericAnimation< NumberAnimation, 
Scaler >>( rShapeManager,
                                                                      nFlags,
@@ -634,7 +812,9 @@ namespace slideshow::internal
                                                                      pGetValue,
                                                                      pSetValue,
                                                                      Scaler( 
1.0/nScaleValue ),
-                                                                     Scaler( 
nScaleValue ) );
+                                                                     Scaler( 
nScaleValue ),
+                                                                     eAttrType,
+                                                                     
pBox2DWorld );
             }
 
 
@@ -760,11 +940,13 @@ namespace slideshow::internal
                                                                                
   const AnimatableShapeSharedPtr&       rShape,
                                                                                
   const ShapeManagerSharedPtr&          rShapeManager,
                                                                                
   const ::basegfx::B2DVector&           rSlideSize,
+                                                                               
   const box2d::utils::Box2DWorldSharedPtr& pBox2DWorld,
                                                                                
   int                                   nFlags )
         {
             // ATTENTION: When changing this map, also the 
classifyAttributeName() method must
             // be checked and possibly adapted in their switch statement
-            switch( mapAttributeName( rAttrName ) )
+            AttributeType eAttrType = mapAttributeName(rAttrName);
+            switch( eAttrType )
             {
                 default:
                 case AttributeType::Invalid:
@@ -794,7 +976,9 @@ namespace slideshow::internal
                                                                   1.0, // 
CharHeight is a relative attribute, thus
                                                                          // 
default is 1.0
                                                                   
&ShapeAttributeLayer::getCharScale,
-                                                                  
&ShapeAttributeLayer::setCharScale );
+                                                                  
&ShapeAttributeLayer::setCharScale,
+                                                                  eAttrType,
+                                                                  pBox2DWorld 
);
 
                 case AttributeType::CharWeight:
                     return makeGenericAnimation<NumberAnimation>( 
rShapeManager,
@@ -802,7 +986,9 @@ namespace slideshow::internal
                                                                   
&ShapeAttributeLayer::isCharWeightValid,
                                                                   
getDefault<double>( rShape, rAttrName ),
                                                                   
&ShapeAttributeLayer::getCharWeight,
-                                                                  
&ShapeAttributeLayer::setCharWeight );
+                                                                  
&ShapeAttributeLayer::setCharWeight,
+                                                                  eAttrType,
+                                                                  pBox2DWorld 
);
 
                 case AttributeType::Height:
                     return makeGenericAnimation( rShapeManager,
@@ -816,7 +1002,9 @@ namespace slideshow::internal
                                                  
&ShapeAttributeLayer::getHeight,
                                                  
&ShapeAttributeLayer::setHeight,
                                                  // convert expression parser 
value from relative page size
-                                                 rSlideSize.getY() );
+                                                 rSlideSize.getY(),
+                                                 eAttrType,
+                                                 pBox2DWorld );
 
                 case AttributeType::Opacity:
                     return makeGenericAnimation<NumberAnimation>( 
rShapeManager,
@@ -825,7 +1013,9 @@ namespace slideshow::internal
                                                                   // TODO(F1): 
Provide shape default here (FillTransparency?)
                                                                   1.0,
                                                                   
&ShapeAttributeLayer::getAlpha,
-                                                                  
&ShapeAttributeLayer::setAlpha );
+                                                                  
&ShapeAttributeLayer::setAlpha,
+                                                                  eAttrType,
+                                                                  pBox2DWorld 
);
 
                 case AttributeType::Rotate:
                     return makeGenericAnimation<NumberAnimation>( 
rShapeManager,
@@ -835,7 +1025,9 @@ namespace slideshow::internal
                                                                   // rotation 
angle is always 0.0, even for rotated shapes
                                                                   0.0,
                                                                   
&ShapeAttributeLayer::getRotationAngle,
-                                                                  
&ShapeAttributeLayer::setRotationAngle );
+                                                                  
&ShapeAttributeLayer::setRotationAngle,
+                                                                  eAttrType,
+                                                                  pBox2DWorld 
);
 
                 case AttributeType::SkewX:
                     return makeGenericAnimation<NumberAnimation>( 
rShapeManager,
@@ -844,7 +1036,9 @@ namespace slideshow::internal
                                                                   // TODO(F1): 
Is there any shape property for skew?
                                                                   0.0,
                                                                   
&ShapeAttributeLayer::getShearXAngle,
-                                                                  
&ShapeAttributeLayer::setShearXAngle );
+                                                                  
&ShapeAttributeLayer::setShearXAngle,
+                                                                  eAttrType,
+                                                                  pBox2DWorld 
);
 
                 case AttributeType::SkewY:
                     return makeGenericAnimation<NumberAnimation>( 
rShapeManager,
@@ -853,7 +1047,9 @@ namespace slideshow::internal
                                                                   // TODO(F1): 
Is there any shape property for skew?
                                                                   0.0,
                                                                   
&ShapeAttributeLayer::getShearYAngle,
-                                                                  
&ShapeAttributeLayer::setShearYAngle );
+                                                                  
&ShapeAttributeLayer::setShearYAngle,
+                                                                  eAttrType,
+                                                                  pBox2DWorld 
);
 
                 case AttributeType::Width:
                     return makeGenericAnimation( rShapeManager,
@@ -867,7 +1063,9 @@ namespace slideshow::internal
                                                  
&ShapeAttributeLayer::getWidth,
                                                  
&ShapeAttributeLayer::setWidth,
                                                  // convert expression parser 
value from relative page size
-                                                 rSlideSize.getX() );
+                                                 rSlideSize.getX(),
+                                                 eAttrType,
+                                                 pBox2DWorld );
 
                 case AttributeType::PosX:
                     return makeGenericAnimation( rShapeManager,
@@ -881,7 +1079,9 @@ namespace slideshow::internal
                                                  &ShapeAttributeLayer::getPosX,
                                                  &ShapeAttributeLayer::setPosX,
                                                  // convert expression parser 
value from relative page size
-                                                 rSlideSize.getX() );
+                                                 rSlideSize.getX(),
+                                                 eAttrType,
+                                                 pBox2DWorld );
 
                 case AttributeType::PosY:
                     return makeGenericAnimation( rShapeManager,
@@ -895,7 +1095,9 @@ namespace slideshow::internal
                                                  &ShapeAttributeLayer::getPosY,
                                                  &ShapeAttributeLayer::setPosY,
                                                  // convert expression parser 
value from relative page size
-                                                 rSlideSize.getY() );
+                                                 rSlideSize.getY(),
+                                                 eAttrType,
+                                                 pBox2DWorld );
             }
 
             return NumberAnimationSharedPtr();
@@ -905,11 +1107,13 @@ namespace slideshow::internal
                                                                               
const AnimatableShapeSharedPtr&       rShape,
                                                                               
const ShapeManagerSharedPtr&          rShapeManager,
                                                                               
const ::basegfx::B2DVector&           /*rSlideSize*/,
+                                                                              
const box2d::utils::Box2DWorldSharedPtr& pBox2DWorld,
                                                                               
int                                   nFlags )
         {
             // ATTENTION: When changing this map, also the 
classifyAttributeName() method must
             // be checked and possibly adapted in their switch statement
-            switch( mapAttributeName( rAttrName ) )
+            AttributeType eAttrType = mapAttributeName( rAttrName );
+            switch( eAttrType )
             {
                 default:
                 case AttributeType::Invalid:
@@ -946,7 +1150,9 @@ namespace slideshow::internal
                                                                 
sal::static_int_cast<sal_Int16>(
                                                                     
getDefault<drawing::FillStyle>( rShape, rAttrName )),
                                                                 
&ShapeAttributeLayer::getFillStyle,
-                                                                
&ShapeAttributeLayer::setFillStyle );
+                                                                
&ShapeAttributeLayer::setFillStyle,
+                                                                eAttrType,
+                                                                pBox2DWorld );
 
                 case AttributeType::LineStyle:
                     return makeGenericAnimation<EnumAnimation>( rShapeManager,
@@ -955,7 +1161,9 @@ namespace slideshow::internal
                                                                 
sal::static_int_cast<sal_Int16>(
                                                                     
getDefault<drawing::LineStyle>( rShape, rAttrName )),
                                                                 
&ShapeAttributeLayer::getLineStyle,
-                                                                
&ShapeAttributeLayer::setLineStyle );
+                                                                
&ShapeAttributeLayer::setLineStyle,
+                                                                eAttrType,
+                                                                pBox2DWorld );
 
                 case AttributeType::CharPosture:
                     return makeGenericAnimation<EnumAnimation>( rShapeManager,
@@ -964,7 +1172,9 @@ namespace slideshow::internal
                                                                 
sal::static_int_cast<sal_Int16>(
                                                                     
getDefault<awt::FontSlant>( rShape, rAttrName )),
                                                                 
&ShapeAttributeLayer::getCharPosture,
-                                                                
&ShapeAttributeLayer::setCharPosture );
+                                                                
&ShapeAttributeLayer::setCharPosture,
+                                                                eAttrType,
+                                                                pBox2DWorld );
 
                 case AttributeType::CharUnderline:
                     return makeGenericAnimation<EnumAnimation>( rShapeManager,
@@ -972,7 +1182,9 @@ namespace slideshow::internal
                                                                 
&ShapeAttributeLayer::isUnderlineModeValid,
                                                                 
getDefault<sal_Int16>( rShape, rAttrName ),
                                                                 
&ShapeAttributeLayer::getUnderlineMode,
-                                                                
&ShapeAttributeLayer::setUnderlineMode );
+                                                                
&ShapeAttributeLayer::setUnderlineMode,
+                                                                eAttrType,
+                                                                pBox2DWorld );
             }
 
             return EnumAnimationSharedPtr();
@@ -982,11 +1194,13 @@ namespace slideshow::internal
                                                                                
 const AnimatableShapeSharedPtr&     rShape,
                                                                                
 const ShapeManagerSharedPtr&        rShapeManager,
                                                                                
 const ::basegfx::B2DVector&         /*rSlideSize*/,
+                                                                               
 const box2d::utils::Box2DWorldSharedPtr& pBox2DWorld,
                                                                                
 int                                 nFlags )
         {
             // ATTENTION: When changing this map, also the 
classifyAttributeName() method must
             // be checked and possibly adapted in their switch statement
-            switch( mapAttributeName( rAttrName ) )
+            AttributeType eAttrType = mapAttributeName(rAttrName);
+            switch( eAttrType )
             {
                 default:
                 case AttributeType::Invalid:
@@ -1020,7 +1234,9 @@ namespace slideshow::internal
                                                                  
&ShapeAttributeLayer::isCharColorValid,
                                                                  
getDefault<RGBColor>( rShape, rAttrName ),
                                                                  
&ShapeAttributeLayer::getCharColor,
-                                                                 
&ShapeAttributeLayer::setCharColor );
+                                                                 
&ShapeAttributeLayer::setCharColor,
+                                                                 eAttrType,
+                                                                 pBox2DWorld );
 
                 case AttributeType::Color:
                     // TODO(F2): This is just mapped to fill color to make it 
work
@@ -1029,7 +1245,9 @@ namespace slideshow::internal
                                                                  
&ShapeAttributeLayer::isFillColorValid,
                                                                  
getDefault<RGBColor>( rShape, rAttrName ),
                                                                  
&ShapeAttributeLayer::getFillColor,
-                                                                 
&ShapeAttributeLayer::setFillColor );
+                                                                 
&ShapeAttributeLayer::setFillColor,
+                                                                 eAttrType,
+                                                                 pBox2DWorld );
 
                 case AttributeType::DimColor:
                     return makeGenericAnimation<ColorAnimation>( rShapeManager,
@@ -1037,7 +1255,9 @@ namespace slideshow::internal
                                                                  
&ShapeAttributeLayer::isDimColorValid,
                                                                  
getDefault<RGBColor>( rShape, rAttrName ),
                                                                  
&ShapeAttributeLayer::getDimColor,
-                                                                 
&ShapeAttributeLayer::setDimColor );
+                                                                 
&ShapeAttributeLayer::setDimColor,
+                                                                 eAttrType,
+                                                                 pBox2DWorld );
 
                 case AttributeType::FillColor:
                     return makeGenericAnimation<ColorAnimation>( rShapeManager,
@@ -1045,7 +1265,9 @@ namespace slideshow::internal
                                                                  
&ShapeAttributeLayer::isFillColorValid,
                                                                  
getDefault<RGBColor>( rShape, rAttrName ),
                                                                  
&ShapeAttributeLayer::getFillColor,
-                                                                 
&ShapeAttributeLayer::setFillColor );
+                                                                 
&ShapeAttributeLayer::setFillColor,
+                                                                 eAttrType,
+                                                                 pBox2DWorld );
 
                 case AttributeType::LineColor:
                     return makeGenericAnimation<ColorAnimation>( rShapeManager,
@@ -1053,7 +1275,9 @@ namespace slideshow::internal
                                                                  
&ShapeAttributeLayer::isLineColorValid,
                                                                  
getDefault<RGBColor>( rShape, rAttrName ),
                                                                  
&ShapeAttributeLayer::getLineColor,
-                                                                 
&ShapeAttributeLayer::setLineColor );
+                                                                 
&ShapeAttributeLayer::setLineColor,
+                                                                 eAttrType,
+                                                                 pBox2DWorld );
             }
 
             return ColorAnimationSharedPtr();
@@ -1114,11 +1338,13 @@ namespace slideshow::internal
                                                                                
   const AnimatableShapeSharedPtr&       rShape,
                                                                                
   const ShapeManagerSharedPtr&          rShapeManager,
                                                                                
   const ::basegfx::B2DVector&           /*rSlideSize*/,
+                                                                               
   const box2d::utils::Box2DWorldSharedPtr& pBox2DWorld,
                                                                                
   int                                   nFlags )
         {
             // ATTENTION: When changing this map, also the 
classifyAttributeName() method must
             // be checked and possibly adapted in their switch statement
-            switch( mapAttributeName( rAttrName ) )
+            AttributeType eAttrType = mapAttributeName(rAttrName);
+            switch( eAttrType )
             {
                 default:
                 case AttributeType::Invalid:
@@ -1156,7 +1382,9 @@ namespace slideshow::internal
                                                                   
&ShapeAttributeLayer::isFontFamilyValid,
                                                                   getDefault< 
OUString >( rShape, rAttrName ),
                                                                   
&ShapeAttributeLayer::getFontFamily,
-                                                                  
&ShapeAttributeLayer::setFontFamily );
+                                                                  
&ShapeAttributeLayer::setFontFamily,
+                                                                  eAttrType,
+                                                                  pBox2DWorld 
);
             }
 
             return StringAnimationSharedPtr();
@@ -1166,11 +1394,13 @@ namespace slideshow::internal
                                                                               
const AnimatableShapeSharedPtr&       /*rShape*/,
                                                                               
const ShapeManagerSharedPtr&          rShapeManager,
                                                                               
const ::basegfx::B2DVector&           /*rSlideSize*/,
+                                                                              
const box2d::utils::Box2DWorldSharedPtr& pBox2DWorld,
                                                                               
int                                   nFlags )
         {
             // ATTENTION: When changing this map, also the 
classifyAttributeName() method must
             // be checked and possibly adapted in their switch statement
-            switch( mapAttributeName( rAttrName ) )
+            AttributeType eAttrType = mapAttributeName(rAttrName);
+            switch( eAttrType )
             {
                 default:
                 case AttributeType::Invalid:
@@ -1209,7 +1439,9 @@ namespace slideshow::internal
                                                                 // TODO(F1): 
Is there a corresponding shape property?
                                                                 true,
                                                                 
&ShapeAttributeLayer::getVisibility,
-                                                                
&ShapeAttributeLayer::setVisibility );
+                                                                
&ShapeAttributeLayer::setVisibility,
+                                                                eAttrType,
+                                                                pBox2DWorld );
             }
 
             return BoolAnimationSharedPtr();
@@ -1220,9 +1452,23 @@ namespace slideshow::internal
                                                                               
const AnimatableShapeSharedPtr&   /*rShape*/,
                                                                               
const ShapeManagerSharedPtr&      rShapeManager,
                                                                               
const ::basegfx::B2DVector&       rSlideSize,
+                                                                              
const box2d::utils::Box2DWorldSharedPtr& pBox2DWorld,
                                                                               
int                               nFlags )
         {
             return std::make_shared<PathAnimation>( rSVGDPath, nAdditive,
+                                   rShapeManager,
+                                   rSlideSize,
+                                   nFlags,
+                                   pBox2DWorld);
+        }
+
+        NumberAnimationSharedPtr AnimationFactory::createPhysicsAnimation(  
const box2d::utils::Box2DWorldSharedPtr& pBox2DWorld,
+                                                                              
const double                      fDuration,
+                                                                              
const ShapeManagerSharedPtr&      rShapeManager,
+                                                                              
const ::basegfx::B2DVector&       rSlideSize,
+                                                                              
int                               nFlags )
+        {
+            return std::make_shared<PhysicsAnimation>( pBox2DWorld, fDuration,
                                    rShapeManager,
                                    rSlideSize,
                                    nFlags );
diff --git a/slideshow/source/engine/animationnodes/animationcolornode.cxx 
b/slideshow/source/engine/animationnodes/animationcolornode.cxx
index 39ca961c478f..14a32aae4af9 100644
--- a/slideshow/source/engine/animationnodes/animationcolornode.cxx
+++ b/slideshow/source/engine/animationnodes/animationcolornode.cxx
@@ -91,7 +91,8 @@ AnimationActivitySharedPtr 
AnimationColorNode::createActivity() const
                 mxColorNode->getAttributeName(),
                 getShape(),
                 getContext().mpSubsettableShapeManager,
-                getSlideSize() ),
+                getSlideSize(),
+                getContext().mpBox2DWorld ),
             getXAnimateNode() );
 
     case animations::AnimationColorSpace::HSL:
@@ -105,7 +106,8 @@ AnimationActivitySharedPtr 
AnimationColorNode::createActivity() const
                         mxColorNode->getAttributeName(),
                         getShape(),
                         getContext().mpSubsettableShapeManager,
-                        getSlideSize() )),
+                        getSlideSize(),
+                        getContext().mpBox2DWorld )),
             mxColorNode );
 
     default:
diff --git a/slideshow/source/engine/animationnodes/animationnodefactory.cxx 
b/slideshow/source/engine/animationnodes/animationnodefactory.cxx
index f9fa01b2f1fd..4df097cb08c0 100644
--- a/slideshow/source/engine/animationnodes/animationnodefactory.cxx
+++ b/slideshow/source/engine/animationnodes/animationnodefactory.cxx
@@ -33,6 +33,7 @@
 #include "propertyanimationnode.hxx"
 #include "animationsetnode.hxx"
 #include "animationpathmotionnode.hxx"
+#include "animationphysicsnode.hxx"
 #include "animationcolornode.hxx"
 #include "animationtransformnode.hxx"
 #include "animationtransitionfilternode.hxx"
@@ -493,6 +494,11 @@ BaseNodeSharedPtr implCreateAnimationNode(
                                 xNode, rParent, rContext );
         break;
 
+    case animations::AnimationNodeType::ANIMATEPHYSICS:
+        pCreatedNode = std::make_shared<AnimationPhysicsNode>(
+                                xNode, rParent, rContext );
+        break;
+
     case animations::AnimationNodeType::TRANSITIONFILTER:
         pCreatedNode = std::make_shared<AnimationTransitionFilterNode>(
                                 xNode, rParent, rContext );
diff --git a/slideshow/source/engine/animationnodes/animationpathmotionnode.cxx 
b/slideshow/source/engine/animationnodes/animationpathmotionnode.cxx
index 2490b6e2cbc8..cbef1f3eabba 100644
--- a/slideshow/source/engine/animationnodes/animationpathmotionnode.cxx
+++ b/slideshow/source/engine/animationnodes/animationpathmotionnode.cxx
@@ -43,7 +43,8 @@ AnimationActivitySharedPtr 
AnimationPathMotionNode::createActivity() const
             mxPathMotionNode->getAdditive(),
             getShape(),
             getContext().mpSubsettableShapeManager,
-            getSlideSize(), 0 ),
+            getSlideSize(),
+            getContext().mpBox2DWorld, 0 ),
         true );
 }
 
diff --git a/slideshow/source/engine/animationnodes/animationphysicsnode.cxx 
b/slideshow/source/engine/animationnodes/animationphysicsnode.cxx
new file mode 100644
index 000000000000..28e247c30d6c
--- /dev/null
+++ b/slideshow/source/engine/animationnodes/animationphysicsnode.cxx
@@ -0,0 +1,48 @@
+/* -*- 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 "animationphysicsnode.hxx"
+#include <animationfactory.hxx>
+
+namespace slideshow::internal
+{
+void AnimationPhysicsNode::dispose()
+{
+    mxPhysicsMotionNode.clear();
+    AnimationBaseNode::dispose();
+}
+
+AnimationActivitySharedPtr AnimationPhysicsNode::createActivity() const
+{
+    double fDuration;
+    ENSURE_OR_THROW((mxPhysicsMotionNode->getDuration() >>= fDuration),
+                    "Couldn't get the animation duration.");
+
+    ActivitiesFactory::CommonParameters const aParms(fillCommonParameters());
+    return ActivitiesFactory::createSimpleActivity(
+        aParms,
+        AnimationFactory::createPhysicsAnimation(getContext().mpBox2DWorld, 
fDuration,
+                                                 
getContext().mpSubsettableShapeManager,
+                                                 getSlideSize(), 0),
+        true);
+}
+
+} // namespace slideshow::internal
+
+/* vim:set shiftwidth=4 softtabstop=4 expandtab: */
diff --git a/slideshow/source/engine/animationnodes/animationphysicsnode.hxx 
b/slideshow/source/engine/animationnodes/animationphysicsnode.hxx
new file mode 100644
index 000000000000..15ac8911e916
--- /dev/null
+++ b/slideshow/source/engine/animationnodes/animationphysicsnode.hxx
@@ -0,0 +1,54 @@
+/* -*- 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 .
+ */
+#pragma once
+
+#include "animationbasenode.hxx"
+#include <com/sun/star/animations/XAnimateMotion.hpp>
+
+namespace slideshow
+{
+namespace internal
+{
+class AnimationPhysicsNode : public AnimationBaseNode
+{
+public:
+    AnimationPhysicsNode(const 
css::uno::Reference<css::animations::XAnimationNode>& xNode,
+                         const BaseContainerNodeSharedPtr& rParent, const 
NodeContext& rContext)
+        : AnimationBaseNode(xNode, rParent, rContext)
+        , mxPhysicsMotionNode(xNode, css::uno::UNO_QUERY_THROW)
+    {
+    }
+
+#if defined(DBG_UTIL)
+    virtual const char* getDescription() const override { return 
"AnimationPhysicsNode"; }
+#endif
+
+protected:
+    virtual void dispose() override;
+
+private:
+    virtual AnimationActivitySharedPtr createActivity() const override;
+
+    css::uno::Reference<css::animations::XAnimateMotion> mxPhysicsMotionNode;
+};
+
+} // namespace internal
+} // namespace slideshow
+
+/* vim:set shiftwidth=4 softtabstop=4 expandtab: */
diff --git a/slideshow/source/engine/animationnodes/animationsetnode.cxx 
b/slideshow/source/engine/animationnodes/animationsetnode.cxx
index 350e80fbcfe7..89747901e73c 100644
--- a/slideshow/source/engine/animationnodes/animationsetnode.cxx
+++ b/slideshow/source/engine/animationnodes/animationsetnode.cxx
@@ -86,6 +86,7 @@ AnimationActivitySharedPtr AnimationSetNode::createActivity() 
const
                 pShape,
                 getContext().mpSubsettableShapeManager,
                 getSlideSize(),
+                getContext().mpBox2DWorld,
                 AnimationFactory::FLAG_NO_SPRITE ),
             aValue );
     }
@@ -109,6 +110,7 @@ AnimationActivitySharedPtr 
AnimationSetNode::createActivity() const
                 pShape,
                 getContext().mpSubsettableShapeManager,
                 getSlideSize(),
+                getContext().mpBox2DWorld,
                 AnimationFactory::FLAG_NO_SPRITE ),
             aValue );
     }
@@ -132,6 +134,7 @@ AnimationActivitySharedPtr 
AnimationSetNode::createActivity() const
                 pShape,
                 getContext().mpSubsettableShapeManager,
                 getSlideSize(),
+                getContext().mpBox2DWorld,
                 AnimationFactory::FLAG_NO_SPRITE ),
             aValue );
     }
@@ -155,6 +158,7 @@ AnimationActivitySharedPtr 
AnimationSetNode::createActivity() const
                 pShape,
                 getContext().mpSubsettableShapeManager,
                 getSlideSize(),
+                getContext().mpBox2DWorld,
                 AnimationFactory::FLAG_NO_SPRITE ),
             aValue );
     }
@@ -178,6 +182,7 @@ AnimationActivitySharedPtr 
AnimationSetNode::createActivity() const
                 pShape,
                 getContext().mpSubsettableShapeManager,
                 getSlideSize(),
+                getContext().mpBox2DWorld,
                 AnimationFactory::FLAG_NO_SPRITE ),
             aValue );
     }
diff --git a/slideshow/source/engine/animationnodes/animationtransformnode.cxx 
b/slideshow/source/engine/animationnodes/animationtransformnode.cxx
index b8019d77e6a1..624bad401e8b 100644
--- a/slideshow/source/engine/animationnodes/animationtransformnode.cxx
+++ b/slideshow/source/engine/animationnodes/animationtransformnode.cxx
@@ -67,7 +67,8 @@ AnimationActivitySharedPtr 
AnimationTransformNode::createActivity() const
                 "Rotate",
                 rShape,
                 getContext().mpSubsettableShapeManager,
-                getSlideSize() ),
+                getSlideSize(),
+                getContext().mpBox2DWorld ),
             getXAnimateNode() );
 
     case animations::AnimationTransformType::SKEWX:
@@ -77,7 +78,8 @@ AnimationActivitySharedPtr 
AnimationTransformNode::createActivity() const
                 "SkewX",
                 rShape,
                 getContext().mpSubsettableShapeManager,
-                getSlideSize() ),
+                getSlideSize(),
+                getContext().mpBox2DWorld ),
             getXAnimateNode() );
 
     case animations::AnimationTransformType::SKEWY:
@@ -87,7 +89,8 @@ AnimationActivitySharedPtr 
AnimationTransformNode::createActivity() const
                 "SkewY",
                 rShape,
                 getContext().mpSubsettableShapeManager,
-                getSlideSize() ),
+                getSlideSize(),
+                getContext().mpBox2DWorld ),
             getXAnimateNode() );
     }
 }
diff --git a/slideshow/source/engine/animationnodes/propertyanimationnode.cxx 
b/slideshow/source/engine/animationnodes/propertyanimationnode.cxx
index 2643c44036d8..3e7d68b4beb7 100644
--- a/slideshow/source/engine/animationnodes/propertyanimationnode.cxx
+++ b/slideshow/source/engine/animationnodes/propertyanimationnode.cxx
@@ -48,7 +48,8 @@ AnimationActivitySharedPtr 
PropertyAnimationNode::createActivity() const
                 attrName,
                 pShape,
                 getContext().mpSubsettableShapeManager,
-                getSlideSize() ),
+                getSlideSize(),
+                getContext().mpBox2DWorld ),
             xAnimateNode );
 
     case AnimationFactory::CLASS_ENUM_PROPERTY:
@@ -58,7 +59,8 @@ AnimationActivitySharedPtr 
PropertyAnimationNode::createActivity() const
                 attrName,
                 pShape,
                 getContext().mpSubsettableShapeManager,
-                getSlideSize(), 0 ),
+                getSlideSize(),
+                getContext().mpBox2DWorld, 0 ),
             xAnimateNode );
 
     case AnimationFactory::CLASS_COLOR_PROPERTY:
@@ -68,7 +70,8 @@ AnimationActivitySharedPtr 
PropertyAnimationNode::createActivity() const
                 attrName,
                 pShape,
                 getContext().mpSubsettableShapeManager,
-                getSlideSize() ),
+                getSlideSize(),
+                getContext().mpBox2DWorld ),
             xAnimateNode );
 
     case AnimationFactory::CLASS_STRING_PROPERTY:
@@ -78,7 +81,8 @@ AnimationActivitySharedPtr 
PropertyAnimationNode::createActivity() const
                 attrName,
                 pShape,
                 getContext().mpSubsettableShapeManager,
-                getSlideSize(), 0 ),
+                getSlideSize(),
+                getContext().mpBox2DWorld, 0 ),
             xAnimateNode );
 
     case AnimationFactory::CLASS_BOOL_PROPERTY:
@@ -88,7 +92,8 @@ AnimationActivitySharedPtr 
PropertyAnimationNode::createActivity() const
                 attrName,
                 pShape,
                 getContext().mpSubsettableShapeManager,
-                getSlideSize(), 0 ),
+                getSlideSize(),
+                getContext().mpBox2DWorld, 0 ),
             xAnimateNode );
     }
 
diff --git a/slideshow/source/engine/box2dtools.cxx 
b/slideshow/source/engine/box2dtools.cxx
index 8729300184f6..c188234105d7 100644
--- a/slideshow/source/engine/box2dtools.cxx
+++ b/slideshow/source/engine/box2dtools.cxx
@@ -211,7 +211,7 @@ void box2DWorld::processUpdateQueue(const double 
fPassedTime)
 }
 
 void box2DWorld::initateAllShapesAsStaticBodies(
-    const slideshow::internal::ShapeManagerSharedPtr pShapeManager)
+    const slideshow::internal::ShapeManagerSharedPtr& pShapeManager)
 {
     assert(mpBox2DWorld);
 
@@ -242,8 +242,9 @@ void box2DWorld::setHasWorldStepper(const bool 
bHasWorldStepper)
     mbHasWorldStepper = bHasWorldStepper;
 }
 
-void 
box2DWorld::queuePositionUpdate(css::uno::Reference<com::sun::star::drawing::XShape>
 xShape,
-                                     const basegfx::B2DPoint& rOutPos)
+void box2DWorld::queuePositionUpdate(
+    const css::uno::Reference<com::sun::star::drawing::XShape>& xShape,
+    const basegfx::B2DPoint& rOutPos)
 {
     Box2DShapeUpdateInformation aQueueElement = { xShape, {}, 
BOX2D_UPDATE_POSITION };
     aQueueElement.maPosition = rOutPos;
@@ -251,7 +252,7 @@ void 
box2DWorld::queuePositionUpdate(css::uno::Reference<com::sun::star::drawing
 }
 
 void box2DWorld::queueLinearVelocityUpdate(
-    css::uno::Reference<com::sun::star::drawing::XShape> xShape,
+    const css::uno::Reference<com::sun::star::drawing::XShape>& xShape,
     const basegfx::B2DVector& rVelocity)
 {
     Box2DShapeUpdateInformation aQueueElement = { xShape, {}, 
BOX2D_UPDATE_LINEAR_VELOCITY, 1 };
@@ -259,8 +260,8 @@ void box2DWorld::queueLinearVelocityUpdate(
     maShapeUpdateQueue.push(aQueueElement);
 }
 
-void 
box2DWorld::queueRotationUpdate(css::uno::Reference<com::sun::star::drawing::XShape>
 xShape,
-                                     const double fAngle)
+void box2DWorld::queueRotationUpdate(
+    const css::uno::Reference<com::sun::star::drawing::XShape>& xShape, const 
double fAngle)
 {
     Box2DShapeUpdateInformation aQueueElement = { xShape, {}, 
BOX2D_UPDATE_ANGLE };
     aQueueElement.mfAngle = fAngle;
@@ -268,7 +269,8 @@ void 
box2DWorld::queueRotationUpdate(css::uno::Reference<com::sun::star::drawing
 }
 
 void box2DWorld::queueAngularVelocityUpdate(
-    css::uno::Reference<com::sun::star::drawing::XShape> xShape, const double 
fAngularVelocity)
+    const css::uno::Reference<com::sun::star::drawing::XShape>& xShape,
+    const double fAngularVelocity)
 {
     Box2DShapeUpdateInformation aQueueElement = { xShape, {}, 
BOX2D_UPDATE_ANGULAR_VELOCITY, 1 };
     aQueueElement.mfAngularVelocity = fAngularVelocity;
@@ -276,13 +278,53 @@ void box2DWorld::queueAngularVelocityUpdate(
 }
 
 void box2DWorld::queueShapeVisibilityUpdate(
-    css::uno::Reference<com::sun::star::drawing::XShape> xShape, const bool 
bVisibility)
+    const css::uno::Reference<com::sun::star::drawing::XShape>& xShape, const 
bool bVisibility)
 {
     Box2DShapeUpdateInformation aQueueElement = { xShape, {}, 
BOX2D_UPDATE_VISIBILITY };
     aQueueElement.mbVisibility = bVisibility;
     maShapeUpdateQueue.push(aQueueElement);
 }
 
+void box2DWorld::queueShapeAnimationUpdate(
+    const css::uno::Reference<com::sun::star::drawing::XShape>& xShape,
+    const slideshow::internal::ShapeAttributeLayerSharedPtr& pAttrLayer,
+    const slideshow::internal::AttributeType eAttrType)
+{
+    switch (eAttrType)
+    {
+        case slideshow::internal::AttributeType::Visibility:
+            queueShapeVisibilityUpdate(xShape, pAttrLayer->getVisibility());
+            return;
+        case slideshow::internal::AttributeType::Rotate:
+            queueRotationUpdate(xShape, pAttrLayer->getRotationAngle());
+            return;
+        case slideshow::internal::AttributeType::PosX:
+        case slideshow::internal::AttributeType::PosY:
+            queuePositionUpdate(xShape, { pAttrLayer->getPosX(), 
pAttrLayer->getPosY() });
+            return;
+        default:
+            return;
+    }
+}
+
+void box2DWorld::queueShapeAnimationEndUpdate(
+    const css::uno::Reference<com::sun::star::drawing::XShape>& xShape,
+    const slideshow::internal::AttributeType eAttrType)
+{
+    switch (eAttrType)
+    {
+        case slideshow::internal::AttributeType::Rotate:
+            queueAngularVelocityUpdate(xShape, 0.0f);
+            return;
+        case slideshow::internal::AttributeType::PosX:
+        case slideshow::internal::AttributeType::PosY:
+            queueLinearVelocityUpdate(xShape, { 0, 0 });
+            return;
+        default:
+            return;
+    }
+}
+
 void box2DWorld::step(const float fTimeStep, const int nVelocityIterations,
                       const int nPositionIterations)
 {
@@ -318,14 +360,14 @@ bool box2DWorld::isInitialized()
         return false;
 }
 
-Box2DBodySharedPtr box2DWorld::makeShapeDynamic(const 
slideshow::internal::ShapeSharedPtr pShape)
+Box2DBodySharedPtr box2DWorld::makeShapeDynamic(const 
slideshow::internal::ShapeSharedPtr& pShape)
 {
     assert(mpBox2DWorld);
     Box2DBodySharedPtr pBox2DBody = 
mpXShapeToBodyMap.find(pShape->getXShape())->second;
     return makeBodyDynamic(pBox2DBody);
 }
 
-Box2DBodySharedPtr box2DWorld::makeBodyDynamic(const Box2DBodySharedPtr 
pBox2DBody)
+Box2DBodySharedPtr box2DWorld::makeBodyDynamic(const Box2DBodySharedPtr& 
pBox2DBody)
 {
     assert(mpBox2DWorld);
     if (pBox2DBody->getType() != BOX2D_DYNAMIC_BODY)
@@ -335,14 +377,14 @@ Box2DBodySharedPtr box2DWorld::makeBodyDynamic(const 
Box2DBodySharedPtr pBox2DBo
     return pBox2DBody;
 }
 
-Box2DBodySharedPtr box2DWorld::makeShapeStatic(const 
slideshow::internal::ShapeSharedPtr pShape)
+Box2DBodySharedPtr box2DWorld::makeShapeStatic(const 
slideshow::internal::ShapeSharedPtr& pShape)
 {
     assert(mpBox2DWorld);
     Box2DBodySharedPtr pBox2DBody = 
mpXShapeToBodyMap.find(pShape->getXShape())->second;
     return makeBodyStatic(pBox2DBody);
 }
 
-Box2DBodySharedPtr box2DWorld::makeBodyStatic(const Box2DBodySharedPtr 
pBox2DBody)
+Box2DBodySharedPtr box2DWorld::makeBodyStatic(const Box2DBodySharedPtr& 
pBox2DBody)
 {
     assert(mpBox2DWorld);
     if (pBox2DBody->getType() != BOX2D_STATIC_BODY)
diff --git a/slideshow/source/engine/slide/slideimpl.cxx 
b/slideshow/source/engine/slide/slideimpl.cxx
index b70f8b5abe4e..569b7fea09a9 100644
--- a/slideshow/source/engine/slide/slideimpl.cxx
+++ b/slideshow/source/engine/slide/slideimpl.cxx
@@ -47,6 +47,7 @@
 #include "userpaintoverlay.hxx"
 #include "targetpropertiescreator.hxx"
 #include <tools.hxx>
+#include <box2dtools.hxx>
 
 using namespace ::com::sun::star;
 
@@ -193,6 +194,7 @@ private:
     LayerManagerSharedPtr                               mpLayerManager;
     std::shared_ptr<ShapeManagerImpl>                 mpShapeManager;
     std::shared_ptr<SubsettableShapeManager>          
mpSubsettableShapeManager;
+    box2d::utils::Box2DWorldSharedPtr                   mpBox2DWorld;
 
     /// Contains common objects needed throughout the slideshow
     SlideShowContext                                    maContext;
@@ -316,6 +318,8 @@ SlideImpl::SlideImpl( const uno::Reference< 
drawing::XDrawPage >&           xDra
                         rShapeCursorMap,
                         xDrawPage)),
     mpSubsettableShapeManager( mpShapeManager ),
+    mpBox2DWorld( std::make_shared<box2d::utils::box2DWorld>(
+                        basegfx::B2DSize( getSlideSizeImpl() ) ) ),
     maContext( mpSubsettableShapeManager,
                rEventQueue,
                rEventMultiplexer,
@@ -325,7 +329,8 @@ SlideImpl::SlideImpl( const uno::Reference< 
drawing::XDrawPage >&           xDra
                *this,
                rMediaFileManager,
                rViewContainer,
-               xComponentContext ),
+               xComponentContext,
+               mpBox2DWorld ),
     mrCursorManager( rCursorManager ),
     maAnimations( maContext,
                   basegfx::B2DSize( getSlideSizeImpl() ) ),
diff --git a/slideshow/source/engine/slideshowcontext.cxx 
b/slideshow/source/engine/slideshowcontext.cxx
index 8c0811e9ecf7..f0433b9d846b 100644
--- a/slideshow/source/engine/slideshowcontext.cxx
+++ b/slideshow/source/engine/slideshowcontext.cxx
@@ -45,7 +45,8 @@ SlideShowContext::SlideShowContext( 
SubsettableShapeManagerSharedPtr& rSubsettab
                                     MediaFileManager&                    
rMediaFileManager,
                                     const UnoViewContainer&           
rViewContainer,
                                     const uno::Reference<
-                                          uno::XComponentContext>&    
rComponentContext ) :
+                                          uno::XComponentContext>&    
rComponentContext,
+                                    box2d::utils::Box2DWorldSharedPtr& 
rBox2DWorldPtr ) :
         mpSubsettableShapeManager( rSubsettableShapeManager ),
         mrEventQueue( rEventQueue ),
         mrEventMultiplexer( rEventMultiplexer ),
@@ -55,7 +56,8 @@ SlideShowContext::SlideShowContext( 
SubsettableShapeManagerSharedPtr& rSubsettab
         mrCursorManager( rCursorManager ),
         mrMediaFileManager( rMediaFileManager ),
         mrViewContainer( rViewContainer ),
-        mxComponentContext( rComponentContext )
+        mxComponentContext( rComponentContext ),
+        mpBox2DWorld( rBox2DWorldPtr )
     {}
 
 void SlideShowContext::dispose()
diff --git a/slideshow/source/engine/slideshowimpl.cxx 
b/slideshow/source/engine/slideshowimpl.cxx
index cbc468d9f17b..a91d5857bc7d 100644
--- a/slideshow/source/engine/slideshowimpl.cxx
+++ b/slideshow/source/engine/slideshowimpl.cxx
@@ -85,6 +85,9 @@
 using namespace com::sun::star;
 using namespace ::slideshow::internal;
 
+namespace box2d::utils { class box2DWorld;
+                         typedef ::std::shared_ptr< box2DWorld > 
Box2DWorldSharedPtr; }
+
 namespace {
 
 /** During animations the update() method tells its caller to call it as
@@ -422,6 +425,7 @@ private:
     ActivitiesQueue                         maActivitiesQueue;
     UserEventQueue                          maUserEventQueue;
     SubsettableShapeManagerSharedPtr        mpDummyPtr;
+    box2d::utils::Box2DWorldSharedPtr       mpBox2DDummyPtr;
 
     std::shared_ptr<SeparateListenerImpl> mpListener;
 
@@ -550,6 +554,7 @@ SlideShowImpl::SlideShowImpl(
                         maEventQueue,
                         *this ),
       mpDummyPtr(),
+      mpBox2DDummyPtr(),
       mpListener(),
       mpRehearseTimingsActivity(),
       mpWaitSymbol(),
@@ -1694,7 +1699,8 @@ sal_Bool SlideShowImpl::setProperty( beans::PropertyValue 
const& rProperty )
                     *this,
                     *this,
                     maViewContainer,
-                    mxComponentContext) );
+                    mxComponentContext,
+                    mpBox2DDummyPtr ) );
         }
         else if (mpRehearseTimingsActivity)
         {
diff --git a/slideshow/source/engine/transitions/shapetransitionfactory.cxx 
b/slideshow/source/engine/transitions/shapetransitionfactory.cxx
index d0ff5325e252..3586cff71d39 100644
--- a/slideshow/source/engine/transitions/shapetransitionfactory.cxx
+++ b/slideshow/source/engine/transitions/shapetransitionfactory.cxx
@@ -324,7 +324,8 @@ AnimationActivitySharedPtr createShapeTransitionByType(
                                 "Opacity",
                                 rShape,
                                 rShapeManager,
-                                rSlideSize ),
+                                rSlideSize,
+                                nullptr ),
                             xTransition->getMode() );
                     }
                     break;
diff --git a/slideshow/source/inc/animationfactory.hxx 
b/slideshow/source/inc/animationfactory.hxx
index db24dbb55094..af3b9b9a4e49 100644
--- a/slideshow/source/inc/animationfactory.hxx
+++ b/slideshow/source/inc/animationfactory.hxx
@@ -30,6 +30,8 @@
 
 #include "shapemanager.hxx"
 
+namespace box2d::utils { typedef ::std::shared_ptr< class box2DWorld > 
Box2DWorldSharedPtr; }
+
 /* Definition of AnimationFactory class */
 
 namespace slideshow::internal
@@ -79,18 +81,21 @@ namespace slideshow::internal
                                                                            
const AnimatableShapeSharedPtr&      rShape,
                                                                            
const ShapeManagerSharedPtr&         rShapeManager,
                                                                            
const ::basegfx::B2DVector&          rSlideSize,
+                                                                           
const box2d::utils::Box2DWorldSharedPtr& pBox2DWorld,
                                                                            int 
                                 nFlags=0 );
 
             EnumAnimationSharedPtr createEnumPropertyAnimation( const 
OUString&                   rAttrName,
                                                                        const 
AnimatableShapeSharedPtr&          rShape,
                                                                        const 
ShapeManagerSharedPtr&             rShapeManager,
                                                                        const 
::basegfx::B2DVector&              rSlideSize,
+                                                                       const 
box2d::utils::Box2DWorldSharedPtr& pBox2DWorld,
                                                                        int     
                                 nFlags );
 
             ColorAnimationSharedPtr  createColorPropertyAnimation( const 
OUString&                rAttrName,
                                                                           
const AnimatableShapeSharedPtr&       rShape,
                                                                           
const ShapeManagerSharedPtr&          rShapeManager,
                                                                           
const ::basegfx::B2DVector&           rSlideSize,
+                                                                          
const box2d::utils::Box2DWorldSharedPtr& pBox2DWorld,
                                                                           int  
                                 nFlags=0 );
 
             /** Create scale or move animation
@@ -110,12 +115,14 @@ namespace slideshow::internal
                                                                            
const AnimatableShapeSharedPtr&      rShape,
                                                                            
const ShapeManagerSharedPtr&         rShapeManager,
                                                                            
const ::basegfx::B2DVector&          rSlideSize,
+                                                                           
const box2d::utils::Box2DWorldSharedPtr& pBox2DWorld,
                                                                            int 
                                 nFlags );
 
             BoolAnimationSharedPtr   createBoolPropertyAnimation( const 
OUString&                 rAttrName,
                                                                          const 
AnimatableShapeSharedPtr&        rShape,
                                                                          const 
ShapeManagerSharedPtr&           rShapeManager,
                                                                          const 
::basegfx::B2DVector&            rSlideSize,
+                                                                         const 
box2d::utils::Box2DWorldSharedPtr& pBox2DWorld,
                                                                          int   
                                 nFlags );
 
             NumberAnimationSharedPtr createPathMotionAnimation( const 
OUString&                   rSVGDPath,
@@ -123,7 +130,14 @@ namespace slideshow::internal
                                                                        const 
AnimatableShapeSharedPtr&          rShape,
                                                                        const 
ShapeManagerSharedPtr&             rShapeManager,
                                                                        const 
::basegfx::B2DVector&              rSlideSize,
-                                                                       int     
                                 nFlags);
+                                                                       const 
box2d::utils::Box2DWorldSharedPtr& pBox2DWorld,
+                                                                       int     
                                 nFlags );
+
+            NumberAnimationSharedPtr createPhysicsAnimation( const 
box2d::utils::Box2DWorldSharedPtr& pBox2DWorld,
+                                                               const double    
                        fDuration,
+                                                               const 
ShapeManagerSharedPtr&            rShapeManager,
+                                                               const 
::basegfx::B2DVector&             rSlideSize,
+                                                               int             
                        nFlags );
         }
 
 }
diff --git a/slideshow/source/inc/box2dtools.hxx 
b/slideshow/source/inc/box2dtools.hxx
index 0824a3c260c5..dacf24845b45 100644
--- a/slideshow/source/inc/box2dtools.hxx
+++ b/slideshow/source/inc/box2dtools.hxx
@@ -11,6 +11,7 @@
 
 #include "shape.hxx"
 #include "shapeattributelayer.hxx"
+#include "attributemap.hxx"
 #include <unordered_map>
 #include <queue>
 
@@ -155,6 +156,21 @@ private:
     void step(const float fTimeStep = 1.0f / 100.0f, const int 
nVelocityIterations = 6,
               const int nPositionIterations = 2);
 
+    /// Queue a rotation update on the next step of the box2DWorld for the 
corresponding body
+    void queueRotationUpdate(const 
css::uno::Reference<com::sun::star::drawing::XShape>& xShape,
+                             const double fAngle);
+
+    /// Queue an angular velocity update for the corresponding body
+    /// to take place after the next step of the box2DWorld
+    void
+    queueAngularVelocityUpdate(const 
css::uno::Reference<com::sun::star::drawing::XShape>& xShape,
+                               const double fAngularVelocity);
+
+    /// Queue an update that changes collision of the corresponding body
+    /// on the next step of the box2DWorld, used for animations that change 
visibility
+    void queueShapeVisibilityUpdate(const 
css::uno::Reference<css::drawing::XShape>& xShape,
+                                    const bool bVisibility);
+
 public:
     box2DWorld(const ::basegfx::B2DVector& rSlideSize);
     ~box2DWorld();
@@ -184,7 +200,7 @@ public:
         @param pShape
         Pointer to the shape to alter the corresponding Box2D body of
      */
-    Box2DBodySharedPtr makeShapeDynamic(const 
slideshow::internal::ShapeSharedPtr pShape);
+    Box2DBodySharedPtr makeShapeDynamic(const 
slideshow::internal::ShapeSharedPtr& pShape);
 
     /** Make the Box2D body a dynamic one
 
@@ -193,7 +209,7 @@ public:
         @param pBox2DBody
         Pointer to the Box2D body
      */
-    Box2DBodySharedPtr makeBodyDynamic(const Box2DBodySharedPtr pBox2DBody);
+    Box2DBodySharedPtr makeBodyDynamic(const Box2DBodySharedPtr& pBox2DBody);
 
     /** Make the Box2D body corresponding to the given shape a static one
 
@@ -202,7 +218,7 @@ public:
         @param pShape
         Pointer to the shape to alter the corresponding Box2D body of
      */
-    Box2DBodySharedPtr makeShapeStatic(const 
slideshow::internal::ShapeSharedPtr pShape);
+    Box2DBodySharedPtr makeShapeStatic(const 
slideshow::internal::ShapeSharedPtr& pShape);
 
     /** Make the Box2D body a dynamic one
 
@@ -211,7 +227,7 @@ public:
         @param pBox2DBody
         Pointer to the Box2D body
      */
-    Box2DBodySharedPtr makeBodyStatic(const Box2DBodySharedPtr pBox2DBody);
+    Box2DBodySharedPtr makeBodyStatic(const Box2DBodySharedPtr& pBox2DBody);
 
     /// Create a static body from the given shape's bounding box
     Box2DBodySharedPtr
@@ -220,7 +236,7 @@ public:
 
     /// Initiate all the shapes in the current slide in the box2DWorld as 
static ones
     void
-    initateAllShapesAsStaticBodies(const 
slideshow::internal::ShapeManagerSharedPtr pShapeManager);
+    initateAllShapesAsStaticBodies(const 
slideshow::internal::ShapeManagerSharedPtr& pShapeManager);
 
     /// @return whether the box2DWorld has a stepper or not
     bool hasWorldStepper();
@@ -229,27 +245,21 @@ public:
     void setHasWorldStepper(const bool bHasWorldStepper);
 
     /// Queue a position update the next step of the box2DWorld for the 
corresponding body
-    void queuePositionUpdate(css::uno::Reference<css::drawing::XShape> xShape,
+    void queuePositionUpdate(const css::uno::Reference<css::drawing::XShape>& 
xShape,
                              const ::basegfx::B2DPoint& rOutPos);
 
     /// Queue a linear velocity update for the corresponding body
     /// to take place after the next step of the box2DWorld
-    void queueLinearVelocityUpdate(css::uno::Reference<css::drawing::XShape> 
xShape,
+    void queueLinearVelocityUpdate(const 
css::uno::Reference<css::drawing::XShape>& xShape,
                                    const ::basegfx::B2DVector& rVelocity);
 
-    /// Queue a rotation update on the next step of the box2DWorld for the 
corresponding body
-    void 
queueRotationUpdate(css::uno::Reference<com::sun::star::drawing::XShape> xShape,
-                             const double fAngle);
-
-    /// Queue an angular velocity update for the corresponding body
-    /// to take place after the next step of the box2DWorld
-    void 
queueAngularVelocityUpdate(css::uno::Reference<com::sun::star::drawing::XShape> 
xShape,
-                                    const double fAngularVelocity);
+    void
+    queueShapeAnimationUpdate(const css::uno::Reference<css::drawing::XShape>& 
xShape,
+                              const 
slideshow::internal::ShapeAttributeLayerSharedPtr& pAttrLayer,
+                              const slideshow::internal::AttributeType 
eAttrType);
 
-    /// Queue an update that changes collision of the corresponding body
-    /// on the next step of the box2DWorld, used for animations that change 
visibility
-    void queueShapeVisibilityUpdate(css::uno::Reference<css::drawing::XShape> 
xShape,
-                                    const bool bVisibility);
+    void queueShapeAnimationEndUpdate(const 
css::uno::Reference<css::drawing::XShape>& xShape,
+                                      const slideshow::internal::AttributeType 
eAttrType);
 };
 
 /// Class that manages a single box2D Body
diff --git a/slideshow/source/inc/slideshowcontext.hxx 
b/slideshow/source/inc/slideshowcontext.hxx
index 558ee6f037c0..565f0ff411aa 100644
--- a/slideshow/source/inc/slideshowcontext.hxx
+++ b/slideshow/source/inc/slideshowcontext.hxx
@@ -24,6 +24,9 @@
 #include <memory>
 
 namespace com::sun::star::uno { class XComponentContext; }
+namespace box2d::utils { class box2DWorld;
+                         typedef ::std::shared_ptr< box2DWorld > 
Box2DWorldSharedPtr; }
+
 
 
 namespace slideshow::internal
@@ -90,7 +93,8 @@ namespace slideshow::internal
                               CursorManager&                                   
 rCursorManager,
                               MediaFileManager&                                
 rMediaFileManager,
                               const UnoViewContainer&                          
 rViewContainer,
-                              const css::uno::Reference< 
css::uno::XComponentContext>&    rComponentContext );
+                              const css::uno::Reference< 
css::uno::XComponentContext>&    rComponentContext,
+                              box2d::utils::Box2DWorldSharedPtr&               
 rBox2DWorldPtr );
             void dispose();
 
             std::shared_ptr<SubsettableShapeManager>&     
mpSubsettableShapeManager;
@@ -103,6 +107,7 @@ namespace slideshow::internal
             MediaFileManager&                               mrMediaFileManager;
             const UnoViewContainer&                         mrViewContainer;
             css::uno::Reference< css::uno::XComponentContext>   
mxComponentContext;
+            box2d::utils::Box2DWorldSharedPtr&              mpBox2DWorld;
         };
 
 }
_______________________________________________
Libreoffice-commits mailing list
libreoffice-comm...@lists.freedesktop.org
https://lists.freedesktop.org/mailman/listinfo/libreoffice-commits

Reply via email to