tdf#144694 In direct SQL dialog, activate options 'Run SQL command
[LibreOffice.git] / oox / source / ppt / timenode.cxx
blob1e0aa84ce0369fa27b788feee1abb6903b7e8896
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 <oox/ppt/timenode.hxx>
22 #include <com/sun/star/beans/NamedValue.hpp>
23 #include <com/sun/star/container/XEnumerationAccess.hpp>
24 #include <com/sun/star/lang/XMultiServiceFactory.hpp>
25 #include <com/sun/star/animations/XAnimateColor.hpp>
26 #include <com/sun/star/animations/XAnimateMotion.hpp>
27 #include <com/sun/star/animations/XAnimateTransform.hpp>
28 #include <com/sun/star/animations/XCommand.hpp>
29 #include <com/sun/star/animations/XAudio.hpp>
30 #include <com/sun/star/animations/XIterateContainer.hpp>
31 #include <com/sun/star/animations/XTimeContainer.hpp>
32 #include <com/sun/star/animations/XTransitionFilter.hpp>
33 #include <com/sun/star/animations/AnimationNodeType.hpp>
34 #include <com/sun/star/animations/Event.hpp>
35 #include <com/sun/star/animations/EventTrigger.hpp>
36 #include <com/sun/star/io/WrongFormatException.hpp>
37 #include <com/sun/star/presentation/EffectNodeType.hpp>
38 #include <com/sun/star/uno/XComponentContext.hpp>
40 #include <oox/core/xmlfilterbase.hxx>
41 #include <oox/ppt/pptfilterhelpers.hxx>
42 #include <oox/token/tokens.hxx>
43 #include <sal/log.hxx>
44 #include <comphelper/diagnose_ex.hxx>
46 using namespace ::oox::core;
47 using namespace ::com::sun::star::beans;
48 using namespace ::com::sun::star::container;
49 using namespace ::com::sun::star::uno;
50 using namespace ::com::sun::star::lang;
51 using namespace ::com::sun::star::animations;
52 using namespace ::com::sun::star::presentation;
54 namespace {
56 void lcl_setAncestorSubItem( const Reference<XAnimationNode>& xParent, sal_Int16 nSubItem )
59 Reference<XAnimationNode> xNode = xParent;
61 while ( xNode.is() )
63 if ( xNode->getType() == AnimationNodeType::ANIMATE )
65 Reference<XAnimate> xAnimate( xNode, UNO_QUERY );
66 if ( xAnimate.is() )
67 xAnimate->setSubItem( nSubItem );
68 break;
70 else if ( xNode->getType() == AnimationNodeType::ITERATE )
72 Reference<XIterateContainer> xIterateContainer( xNode, UNO_QUERY );
73 if ( xIterateContainer.is() )
74 xIterateContainer->setSubItem( nSubItem );
75 break;
78 xNode.set( xNode->getParent(), UNO_QUERY );
84 namespace oox::ppt {
85 OUString TimeNode::getServiceName( sal_Int16 nNodeType )
87 OUString sServiceName;
88 switch( nNodeType )
90 case AnimationNodeType::PAR:
91 sServiceName = "com.sun.star.animations.ParallelTimeContainer";
92 break;
93 case AnimationNodeType::SEQ:
94 sServiceName = "com.sun.star.animations.SequenceTimeContainer";
95 break;
96 case AnimationNodeType::ANIMATE:
97 sServiceName = "com.sun.star.animations.Animate";
98 break;
99 case AnimationNodeType::ITERATE:
100 sServiceName = "com.sun.star.animations.IterateContainer";
101 break;
102 case AnimationNodeType::ANIMATECOLOR:
103 sServiceName = "com.sun.star.animations.AnimateColor";
104 break;
105 case AnimationNodeType::TRANSITIONFILTER:
106 sServiceName = "com.sun.star.animations.TransitionFilter";
107 break;
108 case AnimationNodeType::ANIMATEMOTION:
109 sServiceName = "com.sun.star.animations.AnimateMotion";
110 break;
111 case AnimationNodeType::ANIMATETRANSFORM:
112 sServiceName = "com.sun.star.animations.AnimateTransform";
113 break;
114 case AnimationNodeType::COMMAND:
115 sServiceName = "com.sun.star.animations.Command";
116 break;
117 case AnimationNodeType::SET:
118 sServiceName = "com.sun.star.animations.AnimateSet";
119 break;
120 case AnimationNodeType::AUDIO:
121 sServiceName = "com.sun.star.animations.Audio";
122 break;
123 default:
124 SAL_INFO("oox.ppt","OOX: unhandled type " << nNodeType );
125 break;
127 return sServiceName;
130 TimeNode::TimeNode( sal_Int16 nNodeType )
131 : mnNodeType( nNodeType )
132 , mbHasEndSyncValue( false )
136 TimeNode::~TimeNode()
140 void fixMainSequenceTiming( const css::uno::Reference< css::animations::XAnimationNode >& xNode )
144 bool bFirst = true;
145 Reference< XEnumerationAccess > xEA( xNode, UNO_QUERY_THROW );
146 Reference< XEnumeration > xE( xEA->createEnumeration(), UNO_SET_THROW );
147 while( xE->hasMoreElements() )
149 // click node
150 Reference< XAnimationNode > xClickNode( xE->nextElement(), UNO_QUERY );
152 Event aEvent;
153 aEvent.Trigger = EventTrigger::ON_NEXT;
154 aEvent.Repeat = 0;
155 xClickNode->setBegin( Any( aEvent ) );
157 if( bFirst )
159 bFirst = false;
160 Reference< XEnumerationAccess > xEA2( xClickNode, UNO_QUERY_THROW );
161 Reference< XEnumeration > xE2( xEA2->createEnumeration(), UNO_SET_THROW );
162 if( xE2->hasMoreElements() )
164 // with node
165 xE2->nextElement() >>= xEA2;
166 if( xEA2.is() )
167 xE2 = xEA2->createEnumeration();
168 else
169 xE2.clear();
171 if( xE2.is() && xE2->hasMoreElements() )
173 Reference< XAnimationNode > xEffectNode( xE2->nextElement(), UNO_QUERY_THROW );
174 const Sequence< NamedValue > aUserData( xEffectNode->getUserData() );
175 for( const NamedValue& rProp : aUserData )
177 if ( rProp.Name == "node-type" )
179 sal_Int16 nNodeType = 0;
180 rProp.Value >>= nNodeType;
181 if( nNodeType != css::presentation::EffectNodeType::ON_CLICK )
183 // first effect does not start on click, so correct
184 // first click nodes begin to 0s
185 xClickNode->setBegin( Any( 0.0 ) );
186 break;
195 catch( Exception& )
197 SAL_INFO("oox.ppt","fixMainSequenceTiming(), exception caught!" );
201 void fixInteractiveSequenceTiming( const css::uno::Reference< css::animations::XAnimationNode >& xNode )
205 Any aBegin( xNode->getBegin() );
206 Any aEmpty;
207 xNode->setBegin( aEmpty );
209 Reference< XEnumerationAccess > xEA( xNode, UNO_QUERY_THROW );
210 Reference< XEnumeration > xE( xEA->createEnumeration(), UNO_SET_THROW );
211 while( xE->hasMoreElements() )
213 // click node
214 Reference< XAnimationNode > xClickNode( xE->nextElement(), UNO_QUERY );
215 xClickNode->setBegin( aBegin );
218 catch( Exception& )
220 SAL_INFO("oox.ppt","fixInteractiveSequenceTiming(), exception caught!" );
224 void TimeNode::addNode( const XmlFilterBase& rFilter, const Reference< XAnimationNode >& rxNode, const SlidePersistPtr & pSlide )
226 try {
227 sal_Int16 nNodeType = mnNodeType;
229 if (mnNodeType == AnimationNodeType::PAR && maNodeProperties[NP_ITERATETYPE].hasValue())
230 nNodeType = AnimationNodeType::ITERATE;
232 OUString sServiceName = getServiceName(nNodeType);
234 Reference< XAnimationNode > xNode = createAndInsert( rFilter, sServiceName, rxNode );
235 if (!xNode)
236 return;
237 setNode(rFilter, xNode, pSlide, rxNode);
239 catch( const Exception& )
241 TOOLS_INFO_EXCEPTION("oox.ppt","OOX: exception raised in TimeNode::addNode()" );
245 void TimeNode::setNode(const XmlFilterBase& rFilter, const Reference< XAnimationNode >& xNode, const SlidePersistPtr & pSlide, const Reference<XAnimationNode>& xParent)
247 SAL_WARN_IF( !xNode.is(), "oox.ppt", "null node passed" );
249 try {
250 if( !msId.isEmpty() )
252 pSlide->getAnimNodesMap()[ msId ] = xNode;
255 if( mpTarget )
257 sal_Int16 nSubItem(0);
258 maNodeProperties[ NP_TARGET ] = mpTarget->convert( pSlide, nSubItem );
259 if( mpTarget->mnType == XML_spTgt )
261 if ( xNode->getType() == AnimationNodeType::ANIMATE ||
262 xNode->getType() == AnimationNodeType::ITERATE )
264 maNodeProperties[ NP_SUBITEM ] <<= nSubItem;
266 else
267 lcl_setAncestorSubItem( xParent, nSubItem );
271 if( !maStCondList.empty() )
273 Any aAny = AnimationCondition::convertList( pSlide, maStCondList );
274 if( aAny.hasValue() )
276 xNode->setBegin( aAny );
280 if( !maEndCondList.empty() )
282 Any aAny = AnimationCondition::convertList( pSlide, maEndCondList );
283 if( aAny.hasValue() )
285 xNode->setEnd( aAny );
288 if( mbHasEndSyncValue )
290 Any aValue = maEndSyncValue.convert( pSlide );
291 xNode->setEndSync(aValue);
294 if( !maUserData.empty() )
296 Sequence< NamedValue > aUserDataSeq( static_cast< sal_Int32 >( maUserData.size() ) );
297 NamedValue* pValues = aUserDataSeq.getArray();
298 for (auto const& elem : maUserData)
300 pValues->Name = elem.first;
301 pValues->Value = elem.second;
302 ++pValues;
304 maNodeProperties[ NP_USERDATA ] <<= aUserDataSeq;
307 Reference< XAnimate > xAnimate( xNode, UNO_QUERY );
308 Reference< XAnimateColor > xAnimateColor( xNode, UNO_QUERY );
309 Reference< XAnimateMotion > xAnimateMotion( xNode, UNO_QUERY );
310 Reference< XAnimateTransform > xAnimateTransform( xNode, UNO_QUERY );
311 Reference< XCommand > xCommand( xNode, UNO_QUERY );
312 Reference< XAudio > xAudio( xNode, UNO_QUERY );
313 Reference< XIterateContainer > xIterateContainer( xNode, UNO_QUERY );
314 sal_Int16 nInt16 = 0;
315 bool bBool = false;
316 double fDouble = 0;
317 OUString sString;
318 Sequence< NamedValue > aSeq;
320 for( int i = 0; i < NP_SIZE_; i++)
322 Any & aValue( maNodeProperties[ i ] );
323 if( aValue.hasValue() )
325 switch( i )
327 case NP_TO:
328 if( xAnimate.is() )
329 xAnimate->setTo( aValue );
330 break;
331 case NP_FROM:
332 if( xAnimate.is() )
333 xAnimate->setFrom( aValue );
334 break;
335 case NP_BY:
336 if( xAnimate.is() )
337 xAnimate->setBy( aValue );
338 break;
339 case NP_HIDEDURINGSHOW:
340 if (xAudio.is() && (aValue >>= bBool))
342 xAudio->setHideDuringShow(bBool);
344 break;
345 case NP_ISNARRATION:
346 if (xAudio.is() && (aValue >>= bBool))
348 xAudio->setNarration(bBool);
350 break;
351 case NP_TARGET:
353 if (xParent.is() && xParent->getType() == AnimationNodeType::ITERATE)
355 Reference<XIterateContainer> xParentContainer(xParent, UNO_QUERY);
356 if (xParentContainer.is())
357 xParentContainer->setTarget(aValue);
359 else
361 if (xAnimate.is())
362 xAnimate->setTarget(aValue);
363 if (xCommand.is())
364 xCommand->setTarget(aValue);
365 if (xAudio.is())
366 xAudio->setSource(aValue);
368 break;
369 case NP_SUBITEM:
370 if( aValue >>= nInt16 )
372 if( xAnimate.is() )
374 xAnimate->setSubItem( nInt16 );
376 else if ( xIterateContainer.is() )
378 xIterateContainer->setSubItem( nInt16 );
381 else
383 SAL_INFO("oox.ppt","any >>= failed " << __LINE__ );
385 break;
386 case NP_ATTRIBUTENAME:
387 if( xAnimate.is() )
389 if( aValue >>= sString )
390 xAnimate->setAttributeName( sString );
391 else
393 SAL_INFO("oox.ppt","any >>= failed " << __LINE__ );
396 break;
397 case NP_CALCMODE:
398 if( xAnimate.is() )
400 if( aValue >>= nInt16 )
401 xAnimate->setCalcMode( nInt16 );
402 else
404 SAL_INFO("oox.ppt","any >>= failed " << __LINE__ );
407 break;
408 case NP_KEYTIMES:
409 if( xAnimate.is() )
411 Sequence<double> aKeyTimes;
412 if( aValue >>= aKeyTimes )
413 xAnimate->setKeyTimes(aKeyTimes);
414 else
416 SAL_INFO("oox.ppt","any >>= failed " << __LINE__ );
419 break;
420 case NP_VALUES:
421 if( xAnimate.is() )
423 Sequence<Any> aValues;
424 if( aValue >>= aValues )
425 xAnimate->setValues(aValues);
426 else
428 SAL_INFO("oox.ppt","any >>= failed " << __LINE__ );
431 break;
432 case NP_FORMULA:
433 if( xAnimate.is() )
435 if( aValue >>= sString )
436 xAnimate->setFormula(sString);
437 else
439 SAL_INFO("oox.ppt","any >>= failed " << __LINE__ );
442 break;
443 case NP_COLORINTERPOLATION:
444 if( xAnimateColor.is() )
446 if( aValue >>= nInt16 )
447 xAnimateColor->setColorInterpolation( nInt16 );
448 else
450 SAL_INFO("oox.ppt","any >>= failed " << __LINE__ );
453 break;
454 case NP_DIRECTION:
455 if( xAnimateColor.is() )
457 if( aValue >>= bBool )
458 xAnimateColor->setDirection( bBool );
459 else
461 SAL_INFO("oox.ppt","any >>= failed " << __LINE__ );
464 break;
465 case NP_PATH:
466 if( xAnimateMotion.is() )
467 xAnimateMotion->setPath( aValue );
468 break;
469 case NP_TRANSFORMTYPE:
470 if( xAnimateTransform.is() )
472 if( aValue >>= nInt16 )
473 xAnimateTransform->setTransformType( nInt16 );
474 else
476 SAL_INFO("oox.ppt","any >>= failed " << __LINE__ );
479 break;
480 case NP_USERDATA:
481 if( aValue >>= aSeq )
482 xNode->setUserData( aSeq );
483 else
485 SAL_INFO("oox.ppt","any >>= failed " << __LINE__ );
487 break;
488 case NP_ACCELERATION:
489 if( aValue >>= fDouble )
490 xNode->setAcceleration( fDouble );
491 else
493 SAL_INFO("oox.ppt","any >>= failed " << __LINE__ );
495 break;
496 case NP_DECELERATE:
497 if( aValue >>= fDouble )
498 xNode->setDecelerate( fDouble );
499 else
501 SAL_INFO("oox.ppt","any >>= failed " << __LINE__ );
503 break;
504 case NP_AUTOREVERSE:
505 if( aValue >>= bBool )
506 xNode->setAutoReverse( bBool );
507 else
509 SAL_INFO("oox.ppt","any >>= failed " << __LINE__ );
511 break;
512 case NP_DURATION:
513 xNode->setDuration( aValue );
514 break;
515 case NP_FILL:
516 if( aValue >>= nInt16 )
517 xNode->setFill( nInt16 );
518 else
520 SAL_INFO("oox.ppt","any >>= failed " << __LINE__ );
522 break;
523 case NP_REPEATCOUNT:
524 xNode->setRepeatCount( aValue );
525 break;
526 case NP_REPEATDURATION:
527 xNode->setRepeatDuration( aValue );
528 break;
529 case NP_RESTART:
530 if( aValue >>= nInt16 )
531 xNode->setRestart( nInt16 );
532 else
534 SAL_INFO("oox.ppt","any >>= failed " << __LINE__ );
536 break;
537 case NP_COMMAND:
538 if( xCommand.is() )
540 if( aValue >>= nInt16 )
541 xCommand->setCommand( nInt16 );
542 else
544 SAL_INFO("oox.ppt","any >>= failed " << __LINE__ );
547 break;
548 case NP_PARAMETER:
549 if( xCommand.is() )
550 xCommand->setParameter( aValue );
551 break;
552 case NP_ITERATETYPE:
553 if( xIterateContainer.is() )
555 if( aValue >>= nInt16 )
556 xIterateContainer->setIterateType( nInt16 );
557 else
559 SAL_INFO("oox.ppt","any >>= failed " << __LINE__ );
562 break;
563 case NP_ITERATEINTERVAL:
564 if( xIterateContainer.is() )
566 if( aValue >>= fDouble )
567 xIterateContainer->setIterateInterval( fDouble );
568 else
570 SAL_INFO("oox.ppt","any >>= failed " << __LINE__ );
573 break;
574 default:
575 SAL_INFO("oox.ppt","ERR-OOX: unknown prop index " << i );
576 break;
581 if (xAnimate.is() && xAnimate->getValues().getLength() != xAnimate->getKeyTimes().getLength())
582 throw css::io::WrongFormatException();
584 if( mnNodeType == AnimationNodeType::TRANSITIONFILTER )
587 Reference< XTransitionFilter > xFilter( xNode, UNO_QUERY );
588 maTransitionFilter.setTransitionFilterProperties( xFilter );
591 std::for_each(
592 maChildren.begin(), maChildren.end(),
593 [&rFilter, &xNode, &pSlide] (TimeNodePtr const & child) {
594 child->addNode(rFilter, xNode, pSlide);
595 } );
597 switch( mnNodeType )
599 case AnimationNodeType::SEQ:
601 sal_Int16 nEnum = 0;
602 if( maUserData[ u"node-type"_ustr ] >>= nEnum )
604 if( nEnum == EffectNodeType::MAIN_SEQUENCE )
606 fixMainSequenceTiming( xNode );
608 else if( nEnum == EffectNodeType::INTERACTIVE_SEQUENCE )
610 fixInteractiveSequenceTiming( xNode );
613 break;
615 case AnimationNodeType::PAR:
616 // some other cut&paste... from AnimationImporter::importAnimationContainer()
617 break;
620 catch( const Exception& )
622 TOOLS_INFO_EXCEPTION("oox.ppt","OOX: exception raised in TimeNode::setNode()");
626 Reference< XAnimationNode > TimeNode::createAndInsert(
627 const XmlFilterBase& rFilter,
628 const OUString& rServiceName,
629 const Reference< XAnimationNode >& rxNode )
631 try {
632 Reference< XAnimationNode > xNode( Reference<css::lang::XMultiServiceFactory>(rFilter.getComponentContext()->getServiceManager(), UNO_QUERY_THROW)->createInstance( rServiceName ), UNO_QUERY_THROW );
633 Reference< XTimeContainer > xParentContainer( rxNode, UNO_QUERY_THROW );
635 xParentContainer->appendChild( xNode );
636 return xNode;
638 catch( const Exception& )
640 TOOLS_INFO_EXCEPTION("oox.ppt", "OOX: exception raised in TimeNode::createAndInsert() trying to create a service " << rServiceName);
643 return Reference< XAnimationNode >();
646 void TimeNode::setId( sal_Int32 nId )
648 msId = OUString::number(nId);
651 void TimeNode::setTo( const Any & aTo )
653 maNodeProperties[ NP_TO ] = aTo;
656 void TimeNode::setFrom( const Any & aFrom )
658 maNodeProperties[ NP_FROM ] = aFrom;
661 void TimeNode::setBy( const Any & aBy )
663 maNodeProperties[ NP_BY ] = aBy;
668 /* vim:set shiftwidth=4 softtabstop=4 expandtab: */