From: Andrew K. <aja...@us...> - 2005-12-14 17:26:09
|
Update of /cvsroot/aaf/AAF/Utilities/AAFAnalyzer/BaseTestImpl In directory sc8-pr-cvs1.sourceforge.net:/tmp/cvs-serv1565/BaseTestImpl Modified Files: ResolveRefVisitor.h ResolveRefVisitor.cpp Log Message: Improved/Fixed component reference resolution Index: ResolveRefVisitor.h =================================================================== RCS file: /cvsroot/aaf/AAF/Utilities/AAFAnalyzer/BaseTestImpl/ResolveRefVisitor.h,v retrieving revision 1.4 retrieving revision 1.5 diff -C2 -d -r1.4 -r1.5 *** ResolveRefVisitor.h 14 Nov 2005 19:46:50 -0000 1.4 --- ResolveRefVisitor.h 14 Dec 2005 17:25:59 -0000 1.5 *************** *** 25,28 **** --- 25,42 ---- #include <TypedVisitor.h> + //AAF files + #include <AAFSmartPointer2.h> + + //STL files + #include <set> + #include <stack> + + class AxSourceClip; + class AxSegment; + class AxComponent; + class AxTimelineMobSlot; + class AxEventMobSlot; + class AxMobSlot; + namespace aafanalyzer { *************** *** 40,51 **** virtual ~ResolveRefVisitor(); virtual bool PostOrderVisit(AAFTypedObjNode<IAAFSourceClip>& node); ! shared_ptr<const DetailLevelTestResult> GetTestResult() const; private: wostream& _os; shared_ptr<EdgeMap> _spEdgeMap; shared_ptr< DetailLevelTestResult > _spResult; // prohibited --- 54,81 ---- virtual ~ResolveRefVisitor(); + virtual bool PreOrderVisit(AAFTypedObjNode<IAAFTimelineMobSlot>& node); + virtual bool PreOrderVisit(AAFTypedObjNode<IAAFEventMobSlot>& node); + virtual bool PreOrderVisit(AAFTypedObjNode<IAAFStaticMobSlot>& node); + virtual bool PreOrderVisit(AAFTypedObjNode<IAAFMobSlot>& node); + virtual bool PostOrderVisit(AAFTypedObjNode<IAAFSourceClip>& node); ! virtual bool PostOrderVisit(AAFTypedObjNode<IAAFTimelineMobSlot>& node); ! virtual bool PostOrderVisit(AAFTypedObjNode<IAAFEventMobSlot>& node); ! virtual bool PostOrderVisit(AAFTypedObjNode<IAAFStaticMobSlot>& node); ! virtual bool PostOrderVisit(AAFTypedObjNode<IAAFMobSlot>& node); ! shared_ptr<const DetailLevelTestResult> GetTestResult() const; private: + + shared_ptr<set<IAAFSmartPointer2<IAAFComponent> > > GetComponentsInRange( shared_ptr<Node> spMobSlotNode, AxSourceClip& axSrcClp ); + shared_ptr<set<IAAFSmartPointer2<IAAFComponent> > > GetComponentsToTimelineSlot( AxTimelineMobSlot& axMobSlot, AxSourceClip& axSrcClp, AxSegment& asSegment, double startTime ); + shared_ptr<set<IAAFSmartPointer2<IAAFComponent> > > GetComponentsToEventSlot( AxEventMobSlot& axMobSlot, AxSourceClip& axSrcClp ); + shared_ptr<set<IAAFSmartPointer2<IAAFComponent> > > GetComponentsToFromGenericSlot( AxSegment& axSegment ); + wostream& _os; shared_ptr<EdgeMap> _spEdgeMap; shared_ptr< DetailLevelTestResult > _spResult; + stack<pair<aafUID_t, aafRational_t> > _parentSlots; // prohibited Index: ResolveRefVisitor.cpp =================================================================== RCS file: /cvsroot/aaf/AAF/Utilities/AAFAnalyzer/BaseTestImpl/ResolveRefVisitor.cpp,v retrieving revision 1.6 retrieving revision 1.7 diff -C2 -d -r1.6 -r1.7 *** ResolveRefVisitor.cpp 14 Nov 2005 19:46:50 -0000 1.6 --- ResolveRefVisitor.cpp 14 Dec 2005 17:25:59 -0000 1.7 *************** *** 47,53 **** //AAF files #include <AAFResult.h> ! ! //STL files ! #include <set> namespace { --- 47,51 ---- //AAF files #include <AAFResult.h> ! #include <AAFClassDefUIDs.h> namespace { *************** *** 60,64 **** { public: ! ResolveSlotRefVisitor(wostream& os, aafSlotID_t slotId) : _os(os), --- 58,62 ---- { public: ! ResolveSlotRefVisitor(wostream& os, aafSlotID_t slotId) : _os(os), *************** *** 75,79 **** AxTimelineMobSlot axMobSlot( node.GetAAFObjectOfType() ); aafSlotID_t slotId = axMobSlot.GetSlotID(); ! if ( slotId == _slotId ) { --- 73,77 ---- AxTimelineMobSlot axMobSlot( node.GetAAFObjectOfType() ); aafSlotID_t slotId = axMobSlot.GetSlotID(); ! if ( slotId == _slotId ) { *************** *** 85,94 **** return true; } ! virtual bool PreOrderVisit(AAFTypedObjNode<IAAFStaticMobSlot>& node) { AxStaticMobSlot axMobSlot( node.GetAAFObjectOfType() ); aafSlotID_t slotId = axMobSlot.GetSlotID(); ! if ( slotId == _slotId ) { --- 83,92 ---- return true; } ! virtual bool PreOrderVisit(AAFTypedObjNode<IAAFStaticMobSlot>& node) { AxStaticMobSlot axMobSlot( node.GetAAFObjectOfType() ); aafSlotID_t slotId = axMobSlot.GetSlotID(); ! if ( slotId == _slotId ) { *************** *** 100,109 **** return true; } ! virtual bool PreOrderVisit(AAFTypedObjNode<IAAFEventMobSlot>& node) { AxEventMobSlot axMobSlot( node.GetAAFObjectOfType() ); aafSlotID_t slotId = axMobSlot.GetSlotID(); ! if ( slotId == _slotId ) { --- 98,107 ---- return true; } ! virtual bool PreOrderVisit(AAFTypedObjNode<IAAFEventMobSlot>& node) { AxEventMobSlot axMobSlot( node.GetAAFObjectOfType() ); aafSlotID_t slotId = axMobSlot.GetSlotID(); ! if ( slotId == _slotId ) { *************** *** 120,124 **** AxMobSlot axMobSlot( node.GetAAFObjectOfType() ); aafSlotID_t slotId = axMobSlot.GetSlotID(); ! if ( slotId == _slotId ) { --- 118,122 ---- AxMobSlot axMobSlot( node.GetAAFObjectOfType() ); aafSlotID_t slotId = axMobSlot.GetSlotID(); ! if ( slotId == _slotId ) { *************** *** 130,134 **** return true; } ! virtual bool EdgeVisit(AAFContainment& edge) { --- 128,132 ---- return true; } ! virtual bool EdgeVisit(AAFContainment& edge) { *************** *** 136,140 **** return !_spMobSlot; } ! shared_ptr<Node> GetMobSlot() const { --- 134,138 ---- return !_spMobSlot; } ! shared_ptr<Node> GetMobSlot() const { *************** *** 156,166 **** { public: ! typedef set<shared_ptr<Node> > NodeSet; typedef shared_ptr<NodeSet> NodeSetSP; ! ! ResolveComponentRefVisitor(wostream& os) : _os(os), ! _spNodes( new NodeSet ) {} --- 154,165 ---- { public: ! typedef set<shared_ptr<Node> > NodeSet; typedef shared_ptr<NodeSet> NodeSetSP; ! ! ResolveComponentRefVisitor(wostream& os, shared_ptr<set<IAAFSmartPointer2<IAAFComponent> > > componentsToReference) : _os(os), ! _spNodes( new NodeSet ), ! _componentsToReference( componentsToReference ) {} *************** *** 168,180 **** {} ! virtual bool PreOrderVisit(AAFTypedObjNode<IAAFSourceClip>& node) { ! //Add the source clip to the set of source clips. ! _spNodes->insert( node.GetSharedPointerToNode() ); ! ! //We have reached the source clip, there is no need to traverse any further. return false; } ! NodeSetSP GetReferencedNodes() const { --- 167,307 ---- {} ! virtual bool PreOrderVisit(AAFTypedObjNode<IAAFSequence>& node) { ! //We want to expand all sequences, so, continue the traversal. ! return true; ! } ! ! virtual bool PreOrderVisit(AAFTypedObjNode<IAAFComponent>& node) ! { ! //All components that are not sequences should end up executing this code. ! //Add the component to the set of nodes if it is in the correct time range: ! AxComponent axComponent( node.GetAAFObjectOfType() ); ! IAAFSmartPointer2<IAAFComponent> spComponent; ! spComponent = axComponent; ! if ( _componentsToReference->find( spComponent ) != _componentsToReference->end() ) ! { ! _spNodes->insert( node.GetSharedPointerToNode() ); ! } ! ! //We have reached a non-sequence component, there is no need to traverse any ! //further. return false; } ! ! virtual bool PreOrderVisit(AAFTypedObjNode<IAAFTransition>& node) ! { ! shared_ptr<AAFTypedObjNode<IAAFComponent> > spGeneric( node.DownCastToAAF<IAAFComponent>() ); ! return this->PreOrderVisit( *spGeneric ); ! } ! ! virtual bool PreOrderVisit(AAFTypedObjNode<IAAFSegment>& node) ! { ! shared_ptr<AAFTypedObjNode<IAAFComponent> > spGeneric( node.DownCastToAAF<IAAFComponent>() ); ! return this->PreOrderVisit( *spGeneric ); ! } ! ! virtual bool PreOrderVisit(AAFTypedObjNode<IAAFFiller>& node) ! { ! shared_ptr<AAFTypedObjNode<IAAFComponent> > spGeneric( node.DownCastToAAF<IAAFComponent>() ); ! return this->PreOrderVisit( *spGeneric ); ! } ! ! virtual bool PreOrderVisit(AAFTypedObjNode<IAAFSourceReference>& node) ! { ! shared_ptr<AAFTypedObjNode<IAAFComponent> > spGeneric( node.DownCastToAAF<IAAFComponent>() ); ! return this->PreOrderVisit( *spGeneric ); ! } ! ! virtual bool PreOrderVisit(AAFTypedObjNode<IAAFSourceClip>& node) ! { ! shared_ptr<AAFTypedObjNode<IAAFComponent> > spGeneric( node.DownCastToAAF<IAAFComponent>() ); ! return this->PreOrderVisit( *spGeneric ); ! } ! ! virtual bool PreOrderVisit(AAFTypedObjNode<IAAFEvent>& node) ! { ! shared_ptr<AAFTypedObjNode<IAAFComponent> > spGeneric( node.DownCastToAAF<IAAFComponent>() ); ! return this->PreOrderVisit( *spGeneric ); ! } ! ! virtual bool PreOrderVisit(AAFTypedObjNode<IAAFGPITrigger>& node) ! { ! shared_ptr<AAFTypedObjNode<IAAFComponent> > spGeneric( node.DownCastToAAF<IAAFComponent>() ); ! return this->PreOrderVisit( *spGeneric ); ! } ! ! virtual bool PreOrderVisit(AAFTypedObjNode<IAAFCommentMarker>& node) ! { ! shared_ptr<AAFTypedObjNode<IAAFComponent> > spGeneric( node.DownCastToAAF<IAAFComponent>() ); ! return this->PreOrderVisit( *spGeneric ); ! } ! ! virtual bool PreOrderVisit(AAFTypedObjNode<IAAFDescriptiveMarker>& node) ! { ! shared_ptr<AAFTypedObjNode<IAAFComponent> > spGeneric( node.DownCastToAAF<IAAFComponent>() ); ! return this->PreOrderVisit( *spGeneric ); ! } ! ! virtual bool PreOrderVisit(AAFTypedObjNode<IAAFEdgecode>& node) ! { ! shared_ptr<AAFTypedObjNode<IAAFComponent> > spGeneric( node.DownCastToAAF<IAAFComponent>() ); ! return this->PreOrderVisit( *spGeneric ); ! } ! ! virtual bool PreOrderVisit(AAFTypedObjNode<IAAFTimecode>& node) ! { ! shared_ptr<AAFTypedObjNode<IAAFComponent> > spGeneric( node.DownCastToAAF<IAAFComponent>() ); ! return this->PreOrderVisit( *spGeneric ); ! } ! ! virtual bool PreOrderVisit(AAFTypedObjNode<IAAFTimecodeStream>& node) ! { ! shared_ptr<AAFTypedObjNode<IAAFComponent> > spGeneric( node.DownCastToAAF<IAAFComponent>() ); ! return this->PreOrderVisit( *spGeneric ); ! } ! ! virtual bool PreOrderVisit(AAFTypedObjNode<IAAFTimecodeStream12M>& node) ! { ! shared_ptr<AAFTypedObjNode<IAAFComponent> > spGeneric( node.DownCastToAAF<IAAFComponent>() ); ! return this->PreOrderVisit( *spGeneric ); ! } ! ! virtual bool PreOrderVisit(AAFTypedObjNode<IAAFPulldown>& node) ! { ! shared_ptr<AAFTypedObjNode<IAAFComponent> > spGeneric( node.DownCastToAAF<IAAFComponent>() ); ! return this->PreOrderVisit( *spGeneric ); ! } ! ! virtual bool PreOrderVisit(AAFTypedObjNode<IAAFOperationGroup>& node) ! { ! shared_ptr<AAFTypedObjNode<IAAFComponent> > spGeneric( node.DownCastToAAF<IAAFComponent>() ); ! return this->PreOrderVisit( *spGeneric ); ! } ! ! virtual bool PreOrderVisit(AAFTypedObjNode<IAAFNestedScope>& node) ! { ! shared_ptr<AAFTypedObjNode<IAAFComponent> > spGeneric( node.DownCastToAAF<IAAFComponent>() ); ! return this->PreOrderVisit( *spGeneric ); ! } ! ! virtual bool PreOrderVisit(AAFTypedObjNode<IAAFScopeReference>& node) ! { ! shared_ptr<AAFTypedObjNode<IAAFComponent> > spGeneric( node.DownCastToAAF<IAAFComponent>() ); ! return this->PreOrderVisit( *spGeneric ); ! } ! ! virtual bool PreOrderVisit(AAFTypedObjNode<IAAFEssenceGroup>& node) ! { ! shared_ptr<AAFTypedObjNode<IAAFComponent> > spGeneric( node.DownCastToAAF<IAAFComponent>() ); ! return this->PreOrderVisit( *spGeneric ); ! } ! ! virtual bool PreOrderVisit(AAFTypedObjNode<IAAFSelector>& node) ! { ! shared_ptr<AAFTypedObjNode<IAAFComponent> > spGeneric( node.DownCastToAAF<IAAFComponent>() ); ! return this->PreOrderVisit( *spGeneric ); ! } ! NodeSetSP GetReferencedNodes() const { *************** *** 185,188 **** --- 312,316 ---- wostream& _os; NodeSetSP _spNodes; + shared_ptr<set<IAAFSmartPointer2<IAAFComponent> > > _componentsToReference; // prohibited *************** *** 206,210 **** : _os(os), _spEdgeMap(spEdgeMap), ! _spResult( new DetailLevelTestResult( L"ResolveRefVisitor", L"Visit source clip objects and resolve references..", --- 334,338 ---- : _os(os), _spEdgeMap(spEdgeMap), ! _spResult( new DetailLevelTestResult( L"ResolveRefVisitor", L"Visit source clip objects and resolve references..", *************** *** 220,223 **** --- 348,407 ---- } + bool ResolveRefVisitor::PreOrderVisit(AAFTypedObjNode<IAAFTimelineMobSlot>& node) + { + AxTimelineMobSlot axMobSlot( node.GetAAFObjectOfType() ); + _parentSlots.push( make_pair( kAAFClassID_TimelineMobSlot, axMobSlot.GetEditRate() ) ); + return true; + } + + bool ResolveRefVisitor::PreOrderVisit(AAFTypedObjNode<IAAFEventMobSlot>& node) + { + AxEventMobSlot axMobSlot( node.GetAAFObjectOfType() ); + _parentSlots.push( make_pair( kAAFClassID_EventMobSlot, axMobSlot.GetEditRate() ) ); + return true; + } + + bool ResolveRefVisitor::PreOrderVisit(AAFTypedObjNode<IAAFStaticMobSlot>& node) + { + aafRational_t editRate; + editRate.numerator = 0; + editRate.denominator = 0; + _parentSlots.push( make_pair( kAAFClassID_StaticMobSlot, editRate ) ); + return true; + } + + bool ResolveRefVisitor::PreOrderVisit(AAFTypedObjNode<IAAFMobSlot>& node) + { + aafRational_t editRate; + editRate.numerator = 0; + editRate.denominator = 0; + _parentSlots.push( make_pair( kAAFClassID_MobSlot, editRate ) ); + return true; + } + + bool ResolveRefVisitor::PostOrderVisit(AAFTypedObjNode<IAAFTimelineMobSlot>& node) + { + _parentSlots.pop(); + return true; + } + + bool ResolveRefVisitor::PostOrderVisit(AAFTypedObjNode<IAAFEventMobSlot>& node) + { + _parentSlots.pop(); + return true; + } + + bool ResolveRefVisitor::PostOrderVisit(AAFTypedObjNode<IAAFStaticMobSlot>& node) + { + _parentSlots.pop(); + return true; + } + + bool ResolveRefVisitor::PostOrderVisit(AAFTypedObjNode<IAAFMobSlot>& node) + { + _parentSlots.pop(); + return true; + } + bool ResolveRefVisitor::PostOrderVisit(AAFTypedObjNode<IAAFSourceClip>& node) { *************** *** 231,238 **** return true; } ! shared_ptr<Node> spNode; spNode = MobNodeMap::GetInstance().GetMobNode(mobid); ! //Assert it really is a mob. (i.e. to verify the MobNodeMap is delivering good data.) //Then resolve the reference. --- 415,422 ---- return true; } ! shared_ptr<Node> spNode; spNode = MobNodeMap::GetInstance().GetMobNode(mobid); ! //Assert it really is a mob. (i.e. to verify the MobNodeMap is delivering good data.) //Then resolve the reference. *************** *** 245,258 **** AxObject axObj(spObjNode->GetAAFObject()); assert(AxIsA(axObj, spVerify)); ! //mob has been verified, proceed to the sourceclip shared_ptr<AAFTypedObjNode<IAAFSourceClip> > spSrcClp; shared_ptr<Node> temp = node.GetSharedPointerToNode(); spSrcClp = dynamic_pointer_cast<AAFTypedObjNode<IAAFSourceClip> >( temp ); ! //ensure we have the two proper nodes (spNode, spSrcClp), create a Mob Edge and add to Edgemap if(spSrcClp) { ! shared_ptr<AAFMobReference> spMobRefEdge(new AAFMobReference(spSrcClp, spNode)); _spEdgeMap->AddEdge(spMobRefEdge); --- 429,442 ---- AxObject axObj(spObjNode->GetAAFObject()); assert(AxIsA(axObj, spVerify)); ! //mob has been verified, proceed to the sourceclip shared_ptr<AAFTypedObjNode<IAAFSourceClip> > spSrcClp; shared_ptr<Node> temp = node.GetSharedPointerToNode(); spSrcClp = dynamic_pointer_cast<AAFTypedObjNode<IAAFSourceClip> >( temp ); ! //ensure we have the two proper nodes (spNode, spSrcClp), create a Mob Edge and add to Edgemap if(spSrcClp) { ! shared_ptr<AAFMobReference> spMobRefEdge(new AAFMobReference(spSrcClp, spNode)); _spEdgeMap->AddEdge(spMobRefEdge); *************** *** 262,266 **** slotDFT.TraverseDown( spSlotVisitor ); shared_ptr<Node> spMobSlotNode = spSlotVisitor->GetMobSlot(); ! if ( spMobSlotNode ) { --- 446,450 ---- slotDFT.TraverseDown( spSlotVisitor ); shared_ptr<Node> spMobSlotNode = spSlotVisitor->GetMobSlot(); ! if ( spMobSlotNode ) { *************** *** 268,280 **** _spEdgeMap->AddEdge( spSlotEdge ); ! //Now make a reference from the source clip to all source clips ! //referenced from this mob slot. ! shared_ptr<ResolveComponentRefVisitor> spCompVisitor( new ResolveComponentRefVisitor( _os ) ); DepthFirstTraversal dfs( _spEdgeMap, spMobSlotNode ); dfs.TraverseDown( spCompVisitor ); ResolveComponentRefVisitor::NodeSetSP spNodes = spCompVisitor->GetReferencedNodes(); ! ResolveComponentRefVisitor::NodeSet::const_iterator iter; ! for ( iter = spNodes->begin(); iter != spNodes->end(); iter++ ) { --- 452,469 ---- _spEdgeMap->AddEdge( spSlotEdge ); ! //Now make a reference from the source clip to all non-sequence ! //components referenced from this mob slot. ! ! //Find all components below the MobSlot that need referencing. ! shared_ptr<set<IAAFSmartPointer2<IAAFComponent> > > componentsToReference = ! GetComponentsInRange( spMobSlotNode, axSrcClp ); ! ! shared_ptr<ResolveComponentRefVisitor> spCompVisitor( new ResolveComponentRefVisitor( _os, componentsToReference ) ); DepthFirstTraversal dfs( _spEdgeMap, spMobSlotNode ); dfs.TraverseDown( spCompVisitor ); ResolveComponentRefVisitor::NodeSetSP spNodes = spCompVisitor->GetReferencedNodes(); ! ResolveComponentRefVisitor::NodeSet::const_iterator iter; ! for ( iter = spNodes->begin(); iter != spNodes->end(); iter++ ) { *************** *** 282,286 **** _spEdgeMap->AddEdge( spCompEdge ); } ! } } --- 471,475 ---- _spEdgeMap->AddEdge( spCompEdge ); } ! } } *************** *** 292,299 **** explain += AxStringUtil::mobid2Str( mobid ); shared_ptr<const DetailLevelTestResult> spWarning( new DetailLevelTestResult( _spResult->GetName(), ! L"-", // desc ! explain, ! L"-", // docref ! TestResult::WARN, *(new Requirement::RequirementMapSP(new Requirement::RequirementMap())) ) ); //TODO: Pass a real RequirementVectorSP --- 481,488 ---- explain += AxStringUtil::mobid2Str( mobid ); shared_ptr<const DetailLevelTestResult> spWarning( new DetailLevelTestResult( _spResult->GetName(), ! L"-", // desc ! explain, ! L"-", // docref ! TestResult::WARN, *(new Requirement::RequirementMapSP(new Requirement::RequirementMap())) ) ); //TODO: Pass a real RequirementVectorSP *************** *** 305,308 **** --- 494,884 ---- } + /* + * + * Note: EventMobSlots can only contain Events or Sequences of Events. + * Therefore, an EventMobSlot cannot contain a SourceClip, so, there will + * never be any references to resolve. + * + */ + shared_ptr<set<IAAFSmartPointer2<IAAFComponent> > > ResolveRefVisitor::GetComponentsInRange( shared_ptr<Node> spMobSlotNode, AxSourceClip& axSrcClp ) + { + + /* + * + * Note: Currently, references from TimelineMobSlots to TimelineMobSlots and + * EventMobSlots are being properly resolved. References from + * TimelineMobSlots to StaticMobSlots are being resolved by referencing + * all non-Sequence Components in the StaticMobSlot. However, this is + * not necessarily correct. + * + * Consider: In a StaticMobSlot, Components shall not have a length + * property. However, any non-Event component that is + * added to a Sequence must have a length property (giving + * the Sequence a Length property), which violates the + * condition that Coomponents in StaticMobSlots do not have + * length properties. This requirement is not enforced in + * the code so references are resolved. + * + * Realistically, it seems that a SourceClip referencing a StaticMobSlot + * should be required to reference a Segment that does not have a length + * property, which would be a non-Sequence component or a Sequence of + * Events with no length property. + * + * As it stands, regression tests exist to test that references are + * resolved as the implementation has intended. Therefore, if the + * semantics of what can be stored in a StaticMobSlot are changed, and + * the resolution code is updated, the regression test will fail. + * + * Currently, references from EventMobSlots are not being resolved since + * SourceReferences are illegal within EventMobSlots. + * + * Currently, references from StaticMobSlots to TimelineMobSlots, + * EventMobSlots and StaticMobSlots are being resolved by referencing + * all non-Sequence components within the referenced MobSlot. For + * TimelineMobSlots and EventMobSlots, this seems incorrect. + * Realistically, it seems that the reference should be to the + * components that are in the referenced MobSlots timeline at the + * StartTime specified by the SourceClip (think a SourceClip with + * length = 0). However, this presents a problem since the StartTime + * property is specified in edit units of the SourceClip's object + * context, and the StaticMobSlot containing the SourceClip does not + * have an EditRate property. Also, the references from StaticMobSlots + * to StaticMobSlots is most likely incorrect. The argument made above + * for referencing StaticMobSlots from TimelineMobSlots also applies to + * this situation. + * + * Currently regression tests are implemented to ensure that references + * are resolved as the implementation has intended. Therefore, if the + * mentioned issues are corrected, and the reference resolution is + * changed, then the regression test will fail. + * + */ + + //We need to figure out which nodes fall in the referenced part of the + //timeline. This invloves considering the type of MobSlot that contains + //the clip, and the type of mob slot that is being linked. + shared_ptr<AAFObjNode> spAAFMobSlotNode = dynamic_pointer_cast<AAFObjNode>( spMobSlotNode ); + AxObject axObjSlot( spAAFMobSlotNode->GetAAFObject() ); + + IAAFTimelineMobSlotSP spTimelineMobSlot; + IAAFEventMobSlotSP spEventMobSlot; + IAAFStaticMobSlotSP spStaticMobSlot; + IAAFMobSlotSP spMobSlot; + + aafUID_t slotType = _parentSlots.top().first; + + //Consider the type of the mob slot we are referencing. + if ( AxIsA( axObjSlot, spTimelineMobSlot ) ) + { + AxTimelineMobSlot axMobSlot( spTimelineMobSlot ); + if ( slotType == kAAFClassID_TimelineMobSlot ) + { + //We should reference everything in the range specified in the + //source clip. References from EventMobSlots to TimelineMobSlots + //will be resolved regardless of the correctness of the conversion. + AxSegment axSegment( axMobSlot.GetSegment() ); + return GetComponentsToTimelineSlot( axMobSlot, axSrcClp, axSegment, 0.0 ); + } + else if ( slotType == kAAFClassID_StaticMobSlot || + slotType == kAAFClassID_MobSlot ) + { + //Components in StaticMobSlots do not have length properties. + //SourceClips in StaticMobSlots do not have StartTime properties. + //Therefore, resolve all references, from StaticMobSlots to + //TimelineMobSlots regardless of the correctness of the conversion. + AxSegment axSegment( axMobSlot.GetSegment() ); + return GetComponentsToFromGenericSlot( axSegment ); + } + } + + else if ( AxIsA( axObjSlot, spEventMobSlot ) ) + { + AxEventMobSlot axMobSlot( spEventMobSlot ); + aafUID_t slotType = _parentSlots.top().first; + if ( slotType == kAAFClassID_TimelineMobSlot ) + { + //We should reference everything in the range specified in the + //source clip. References from TimelineMobSlots to EventMobSlots + //will be resolved regardless of the correctness of the conversion. + return GetComponentsToEventSlot( axMobSlot, axSrcClp ); + } + else if ( slotType == kAAFClassID_StaticMobSlot || + slotType == kAAFClassID_MobSlot ) + { + //Components in StaticMobSlots do not have length properties. + //SourceClips in StaticMobSlots do not have StartTime properties. + //Therefore, resolve all references, from StaticMobSlots to + //EventMobSlots regardless of the correctness of the conversion. + AxSegment axSegment( axMobSlot.GetSegment() ); + return GetComponentsToFromGenericSlot( axSegment ); + } + } + + else if ( AxIsA( axObjSlot, spStaticMobSlot ) ) + { + //StaticMobSlots do not have any time information, therefore resolve + //references to all components in the StaticMobSlot. References are + //resolved from TimelineMobSlots and EventMobSlots regardless of + //whether of not the conversion is correct. + AxStaticMobSlot axMobSlot( spStaticMobSlot ); + AxSegment axSegment( axMobSlot.GetSegment() ); + return GetComponentsToFromGenericSlot( axSegment ); + } + + else if ( AxIsA( axObjSlot, spMobSlot ) ) + { + //There is no aditional information about this type of MobSlot, so treat it + //like a StaticMobSlot. + + AxMobSlot axMobSlot( spMobSlot ); + AxSegment axSegment( axMobSlot.GetSegment() ); + return GetComponentsToFromGenericSlot( axSegment ); + } + + //If the node was not a MobSlot, return an empty set. + shared_ptr<set<IAAFSmartPointer2<IAAFComponent> > > referencedComponents( new set<IAAFSmartPointer2<IAAFComponent> > ); + return referencedComponents; + + } + + shared_ptr<set<IAAFSmartPointer2<IAAFComponent> > > ResolveRefVisitor::GetComponentsToTimelineSlot( AxTimelineMobSlot& axMobSlot, AxSourceClip& axSrcClp, AxSegment& axSegment, double startTime ) + { + + shared_ptr<set<IAAFSmartPointer2<IAAFComponent> > > referencedComponents( new set<IAAFSmartPointer2<IAAFComponent> > ); + + //Find the Source Clip's start time and length + aafRational_t clipRate = _parentSlots.top().second; + double clipStart = (double)axSrcClp.GetSourceReference().startTime * (double)clipRate.numerator / (double)clipRate.denominator; + double clipLen = (double)axSrcClp.GetLength() * (double)clipRate.numerator / (double)clipRate.denominator; + + //Find the referenced materials offset and adjust the start + //time accordingly + aafRational_t segmentRate = axMobSlot.GetEditRate(); + double offset = (double)axMobSlot.GetOrigin() * (double)segmentRate.numerator / (double)segmentRate.denominator; + clipStart -= offset; + + //If the component in the referenced slot ends before or begins + //after the referenced time, we do not want to add a reference + //to the graph. + double segmentLen = (double)axSegment.GetLength() * (double)segmentRate.numerator / (double)segmentRate.denominator; + + if ( !( startTime + segmentLen <= clipStart || clipStart + clipLen <= startTime ) ) + { + //We need to references this segment. If it is not a sequence, + //this is trivial. + IAAFSequenceSP spSequence; + if ( AxIsA( axSegment, spSequence ) ) + { + //Now, we have to consider every component in the sequence. + AxSequence axSequence( spSequence ); + aafUInt32 numComponents = axSequence.CountComponents(); + double time = startTime; + for ( unsigned int i = 0; i < numComponents; i++ ) + { + + IAAFTransitionSP spTransition; + + AxComponent axComp( axSequence.GetComponentAt( i ) ); + double compLen = (double)axComp.GetLength() * (double)segmentRate.numerator / (double)segmentRate.denominator; + + //If this is a sequence, we need to consider all of the components + //within it. + if ( AxIsA( axComp, spSequence ) ) + { + AxSequence childSequence( spSequence ); + shared_ptr<set<IAAFSmartPointer2<IAAFComponent> > > childComponents = + GetComponentsToTimelineSlot( axMobSlot, axSrcClp, childSequence, time ); + set<IAAFSmartPointer2<IAAFComponent> >::const_iterator iter; + for ( iter = childComponents->begin(); iter != childComponents->end(); iter++ ) + { + referencedComponents->insert( *iter ); + } + } + else + { + //If this is a transition, we need to consider it from the begining of + //the transition (not the end which was given by the end of the + //previous component). + if ( AxIsA( axComp, spTransition ) ) + { + time -= compLen; + } + + if ( !( clipStart + clipLen <= time || time + compLen <= clipStart ) ) + { + IAAFSmartPointer2<IAAFComponent> spComp; + spComp = axComp; + referencedComponents->insert( spComp ); + } + } + + //If this is not a transition, then the time should be adjusted. If it + //is a transition, the begining of the next segment is the same as the + //begining of the transition. + if ( !AxIsA( axComp, spTransition ) ) + { + time += compLen; + } + + } + } + else + { + IAAFSmartPointer2<IAAFComponent> spComp; + spComp = AxQueryInterface<IAAFSegment, IAAFComponent>( axSegment ); + referencedComponents->insert( spComp ); + } + } + + return referencedComponents; + + } + + shared_ptr<set<IAAFSmartPointer2<IAAFComponent> > > ResolveRefVisitor::GetComponentsToEventSlot( AxEventMobSlot& axMobSlot, AxSourceClip& axSrcClp ) + { + + shared_ptr<set<IAAFSmartPointer2<IAAFComponent> > > referencedComponents( new set<IAAFSmartPointer2<IAAFComponent> > ); + + //Find the Source Clip's start time and length + aafRational_t clipRate = _parentSlots.top().second; + double clipStart = (double)axSrcClp.GetSourceReference().startTime * (double)clipRate.numerator / (double)clipRate.denominator; + double clipLen = (double)axSrcClp.GetLength() * (double)clipRate.numerator / (double)clipRate.denominator; + + //If the component in the referenced slot ends before or begins + //after the referenced time, we do not want to add a reference + //to the graph. + + aafRational_t segmentRate = axMobSlot.GetEditRate(); + AxSegment axSegment( axMobSlot.GetSegment() ); + + //We need to determine if this is an Event or a Sequence to properly + //continue. + IAAFSequenceSP spSequence; + + if ( AxIsA( axSegment, spSequence ) ) + { + //Now, we have to consider every event in the sequence. + AxSequence axSequence( spSequence ); + aafUInt32 numComponents = axSequence.CountComponents(); + + for ( unsigned int i = 0; i < numComponents; i++ ) + { + AxComponent axComp( axSequence.GetComponentAt( i ) ); + AxEvent axEvent( AxQueryInterface<IAAFComponent, IAAFEvent>( axComp ) ); + + double eventStart = (double)axEvent.GetPosition() * (double)segmentRate.numerator / (double)segmentRate.denominator; + + //If the event doesn't have a length it is an instantaneous event. + double eventLen; + try + { + eventLen = (double)axEvent.GetLength() * (double)segmentRate.numerator / (double)segmentRate.denominator; + } + catch ( const AxExHResult& ex ) + { + if ( ex.getHResult() == AAFRESULT_PROP_NOT_PRESENT ) + { + eventLen = 0.0; + } + else + { + throw ex; + } + } + + if ( !( eventStart + eventLen <= clipStart || clipStart + clipLen <= eventStart ) ) + { + IAAFSmartPointer2<IAAFComponent> spComp; + spComp = axComp; + referencedComponents->insert( spComp ); + } + + } + + } + else + { + AxEvent axEvent( AxQueryInterface<IAAFSegment, IAAFEvent>( axSegment ) ); + + double eventStart = (double)axEvent.GetPosition() * (double)segmentRate.numerator / (double)segmentRate.denominator; + + //If the event doesn't have a length it is an instantaneous event. + double eventLen; + try + { + eventLen = (double)axEvent.GetLength() * (double)segmentRate.numerator / (double)segmentRate.denominator; + } + catch ( const AxExHResult& ex ) + { + if ( ex.getHResult() == AAFRESULT_PROP_NOT_PRESENT ) + { + eventLen = 0.0; + } + else + { + throw ex; + } + } + + if ( !( eventStart + eventLen <= clipStart || clipStart + clipLen <= eventStart ) ) + { + IAAFSmartPointer2<IAAFComponent> spComp; + spComp = AxQueryInterface<IAAFSegment, IAAFComponent>( axSegment ); + referencedComponents->insert( spComp ); + } + + } + + return referencedComponents; + + } + + shared_ptr<set<IAAFSmartPointer2<IAAFComponent> > > ResolveRefVisitor::GetComponentsToFromGenericSlot( AxSegment& axSegment ) + { + + shared_ptr<set<IAAFSmartPointer2<IAAFComponent> > > referencedComponents( new set<IAAFSmartPointer2<IAAFComponent> > ); + + //We need to references this segment. If it is not a sequence, + //this is trivial. + IAAFSequenceSP spSequence; + if ( AxIsA( axSegment, spSequence ) ) + { + //Now, we have to consider every component in the sequence. + AxSequence axSequence( spSequence ); + aafUInt32 numComponents = axSequence.CountComponents(); + for ( unsigned int i = 0; i < numComponents; i++ ) + { + AxComponent axComp( axSequence.GetComponentAt( i ) ); + + if ( AxIsA( axComp, spSequence ) ) + { + AxSequence childSequence( spSequence ); + shared_ptr<set<IAAFSmartPointer2<IAAFComponent> > > childComponents = + GetComponentsToFromGenericSlot( childSequence ); + set<IAAFSmartPointer2<IAAFComponent> >::const_iterator iter; + for ( iter = childComponents->begin(); iter != childComponents->end(); iter++ ) + { + referencedComponents->insert( *iter ); + } + } + else + { + IAAFSmartPointer2<IAAFComponent> spComp; + spComp = axComp; + referencedComponents->insert( spComp ); + } + } + } + else + { + IAAFSmartPointer2<IAAFComponent> spComp; + spComp = AxQueryInterface<IAAFSegment, IAAFComponent>( axSegment ); + referencedComponents->insert( spComp ); + } + + return referencedComponents; + + } + shared_ptr<const DetailLevelTestResult> ResolveRefVisitor::GetTestResult() const { |