smltime.cpp
上传用户:dangjiwu
上传日期:2013-07-19
资源大小:42019k
文件大小:225k
- m_pSourceElement->m_bDurationIncludesDelayBeyondSyncbase)
- {
- HX_ASSERT(0 && "ehodge: CHANGE NOT TESTED!");
- }
- if (HXR_OK !=
- m_pSourceElement->getCurrentScheduledStopTime(ulTotalDelay))
- {
- goto doneSettingDependent;
- }
- #else
- ULONG32 ulTotalDelay = m_pSourceElement->m_ulDelay +
- m_pSourceElement->m_ulDuration;
- // /Helps fix PR 6XXXX(media version): if delay is already packed
- // into the duration, then don't count it twice (as can happen in
- // <seq><ref begin="1s" .../><ref begin="1s" .../>...):
- if (m_pSourceElement->m_bDurationIncludesDelayBeyondSyncbase)
- {
- HX_ASSERT(m_pSourceElement->m_ulBeginOffsetFromSyncBase != (UINT32)-1);
- /*OK[]*/ if (m_pSourceElement->m_ulBeginOffsetFromSyncBase !=(UINT32)-1)
- {
- HX_ASSERT(m_pSourceElement->m_ulBeginOffsetFromSyncBase <
- ulTotalDelay);
- if (m_pSourceElement->m_ulBeginOffsetFromSyncBase <
- ulTotalDelay)
- {
- ulTotalDelay -=
- m_pSourceElement->m_ulBeginOffsetFromSyncBase;
- }
- }
- }
- #endif
- if (WAY_IN_THE_FUTURE < ulTotalDelay)
- {
- HX_ASSERT(WAY_IN_THE_FUTURE == ulTotalDelay && "PR 59584");
- ulTotalDelay = WAY_IN_THE_FUTURE; // /For PR 59584.
- }
-
- #if defined(_DEBUG) && defined(XXXEH_DEBUGOUT_ADDDURATION)
- {
- FILE* f1 = ::fopen("c:\smil2AddDuration.txt", bFirstTimeAddDurDebugout?
- ADDDURATION_DEBUGOUT_STR_NEW_FILE :
- ADDDURATION_DEBUGOUT_STR_APPEND_TO_FILE );
- ::fprintf(f1, "nt%s:CSmilTimelinePar::resetDelay(%lu):from %lu to %lu;"
- "tresetting dependent (%s)'s delay to %lun", (const char*)m_pID,
- ulDelay, ulPriorDelay, m_pSourceElement->m_ulDelay,
- (const char*)m_pDependent->m_pID, ulTotalDelay);
- ::fclose(f1);
- bFirstTimeAddDurDebugout = FALSE;
- }
- #endif
-
- m_pDependent->resetDelay(ulTotalDelay);
- #if defined(XXXEH_WAIT_UNTIL_getCurrentScheduledStopTime_IS_FIXED_WHEN_BEGINOFFSETSET_20011022)
- doneSettingDependent:
- #endif
- // /(Added while fixing PR 59851) Let others know our begin time changed:
- m_pParser->m_pTimelineElementManager->notify(m_pID);
- }
- }
- void
- CSmilTimelinePar::adjustDuration()
- {
- BOOL bReset = FALSE;
- UINT32 ulDuration = 0;
- BOOL bDurationSet = FALSE;
- BOOL bEndsyncIdDurationFound = FALSE; // /For endsync="[Some ID]"
- // /Need this for fixing PR 50676 part 6:
- ULONG32 ulPriorPureDuration = m_pSourceElement->getPureDuration();
- if (!m_bDurationSet)
- {
- goto cleanup;
- }
- if(m_pChildren)
- {
- CHXSimpleList::Iterator i = m_pChildren->Begin();
- for(; i != m_pChildren->End(); ++i)
- {
- CSmilTimelineElement* pElement = (CSmilTimelineElement*)(*i);
- // /Checking this fixes PR 69290: if child duration wasn't set,
- // then for crying out loud don't use it here:
- if (!pElement->m_bDurationSet)
- {
- continue;
- }
- HX_ASSERT((UINT32)-1 != pElement->m_pSourceElement->m_ulDuration);
- // /Make sure we take endsync into account here; doing so helps fix
- // PR 50679 (and probably other bugs):
- if (SMILEventSourceFirst == m_pSourceElement->m_nEndsyncEventSourceTag)
- {
- if (!bDurationSet)
- {
- ulDuration = pElement->m_pSourceElement->m_ulDuration;
- }
- else
- {
- ulDuration = (ulDuration < pElement->m_pSourceElement->m_ulDuration) ?
- ulDuration : pElement->m_pSourceElement->m_ulDuration;
- }
- bDurationSet = TRUE;
- }
- else if (SMILEventSourceID == m_pSourceElement->m_nEndsyncEventSourceTag)
- {
- if (pElement->m_pSourceElement->m_pNode &&
- m_pSourceElement->m_EndsyncEventSourceID ==
- pElement->m_pSourceElement->m_pNode->m_id)
- {
- ulDuration = pElement->m_pSourceElement->m_ulDuration;
- bEndsyncIdDurationFound = TRUE;
- bDurationSet = TRUE;
- }
- }
- // /This else-if block fixes problem in PR 62688 repro case where
- // restarting a child, prior to all children playing, caused excl
- // to resolve its dur as if it were endsync="last":
- else if (SMILEventSourceAll ==
- m_pSourceElement->m_nEndsyncEventSourceTag)
- {
- if (m_pChildren &&
- m_nDurationAdded >= m_pChildren->GetCount())
- {
- ulDuration = (ulDuration > pElement->m_pSourceElement->m_ulDuration) ?
- ulDuration : pElement->m_pSourceElement->m_ulDuration;
- bDurationSet = TRUE;
- }
- else
- {
- // /Don't adjust duration until all child durs are in:
- goto cleanup;
- }
- }
- else // /For "last", use the largest child duration:
- {
- ulDuration = (ulDuration > pElement->m_pSourceElement->m_ulDuration) ?
- ulDuration : pElement->m_pSourceElement->m_ulDuration;
- bDurationSet = TRUE;
- }
- // /Fixes PR 50806 (original par version, INTEROP Timing #23.6 as
- // well as par version 2 (endsync="last")): if this has a "min"
- // attribute set, ulDuration shouldn't be less regardless of endSync:
- if (m_pSourceElement->m_ulMinActiveDur > ulDuration)
- {
- ulDuration = m_pSourceElement->m_ulMinActiveDur;
- }
- }
- // /!bDurationSet happens in PR 50588 (case 2: begin="x.end"), when
- // child has begun playing but has not yet resolved its duration:
- if (!bDurationSet)
- {
- goto cleanup;
- }
- if (SMILEventSourceID == m_pSourceElement->m_nEndsyncEventSourceTag)
- {
- if (!bEndsyncIdDurationFound)
- {
- goto cleanup; // /That id'd child not added to timeline yet.
- }
- }
- //check m_ulAuthoredDur here:
- if (!m_pSourceElement->m_bHasExplicitEnd &&
- !m_pSourceElement->m_bHasExplicitDur)
- {
- m_pSourceElement->m_ulDuration = ulDuration;
- }
-
- // /Moved this out of the above if() so it gets called every time, to
- // fix PR 6XXX? and re-fix PR 55117: we should always give our parents
- // a chance to set the outer-time-container duration so it can (re)-
- // state to the core what the group duration should be:
- if(m_pParent)
- {
- m_pParent->adjustDuration();
- }
- // /Moved this out to happen all the time, too:
- if (m_pDependent)
- {
- #if defined(XXXEH_WAIT_UNTIL_getCurrentScheduledStopTime_IS_FIXED_WHEN_BEGINOFFSETSET_20011022)
- ULONG32 ulTotalDelay = 0;
- if (HXR_OK !=
- m_pSourceElement->getCurrentScheduledStopTime(ulTotalDelay))
- {
- goto doneSettingDependent;
- }
- #else
- ULONG32 ulTotalDelay = m_pSourceElement->m_ulDelay +
- m_pSourceElement->m_ulDuration;
- if (m_pSourceElement->m_bDurationIncludesDelayBeyondSyncbase)
- {
- HX_ASSERT(m_pSourceElement->m_ulBeginOffsetFromSyncBase != (UINT32)-1);
- /*OK[]*/ if (m_pSourceElement->m_ulBeginOffsetFromSyncBase !=(UINT32)-1)
- {
- HX_ASSERT(m_pSourceElement->m_ulBeginOffsetFromSyncBase <
- ulTotalDelay);
- if (m_pSourceElement->m_ulBeginOffsetFromSyncBase <
- ulTotalDelay)
- {
- ulTotalDelay -=
- m_pSourceElement->m_ulBeginOffsetFromSyncBase;
- }
- }
- }
- #endif
- if (WAY_IN_THE_FUTURE < ulTotalDelay)
- {
- // /XXXEH- If delay is greater than this, I want to know:
- HX_ASSERT(WAY_IN_THE_FUTURE == ulTotalDelay);
- ulTotalDelay = WAY_IN_THE_FUTURE; // /For PR 59584.
- }
- #if defined(_DEBUG) && defined(XXXEH_DEBUGOUT_ADDDURATION)
- {
- FILE* f1 = ::fopen("c:\smil2AddDuration.txt", bFirstTimeAddDurDebugout?
- ADDDURATION_DEBUGOUT_STR_NEW_FILE :
- ADDDURATION_DEBUGOUT_STR_APPEND_TO_FILE );
- ::fprintf(f1, "nt%s:CSmilTimelinePar::adjustDuration();tresetting dependent (%s)'s delay to %lun",
- (const char*)m_pID, (const char*)m_pDependent->m_pID, ulTotalDelay);
- ::fclose(f1);
- bFirstTimeAddDurDebugout = FALSE;
- }
- #endif
- m_pDependent->resetDelay(ulTotalDelay);
- }
- #if defined(XXXEH_WAIT_UNTIL_getCurrentScheduledStopTime_IS_FIXED_WHEN_BEGINOFFSETSET_20011022)
- doneSettingDependent:
- ;
- #endif
- }
- // /Fixes PR 69410 (with outer par): do this no matter what, even if
- // prior < ulDur; resumed element in excl descendant should extend that
- // excl but we've already told the core to limit the presentation
- // duration, so extend it here as needed:
- // /Helps fix PR 50676 part 6: if our duration got reduced, we need to
- // possibly constrain our children:
- {
- // /For PR 62688 & PR 59584: remove check for ulPriorDuration being
- // WAY_IN_THE_FUTURE since PR 50676 works without it and there are
- // cases where our dur may re-resolve, & updating children is needed.
- // /For PR 59584: the group's outer time container needs to set the
- // duration if its dur is longer than its group's so far:
- if (m_pSourceElement->m_pNode && m_pSourceElement->m_pHandler)
- {
- if (m_pSourceElement->m_pNode->m_pParent && (SMILBody ==
- m_pSourceElement->m_pNode->m_pParent->m_tag ||
- m_pSourceElement->m_pNode->
- m_pParent->m_bIsOuterWrapperTimeContainer) )
- {
- BOOL bDoResolveGroupDur = TRUE;
- UINT32 ulGroup = m_pSourceElement->m_pNode->m_nGroup;
- if (m_pSourceElement->m_pNode->m_bIsOuterWrapperTimeContainer)
- {
- ulGroup = 0;
- // /If we're outer wrapper around multiple groups
- // (or "clips"), then let each group outer time container
- // resolve its group duration:
- if (m_pChildren->GetCount() > 1)
- {
- bDoResolveGroupDur = FALSE;
- }
- }
- if (bDoResolveGroupDur)
- {
- // /The group duration should be the duration of this
- // outer-most time container:
- HX_RESULT pnrs = m_pSourceElement->m_pHandler->
- resolveGroupDurToOuterTimeContainerDur(
- ulGroup, m_pSourceElement->m_ulDuration);
- }
- }
- }
- if(m_pChildren)
- {
- // /Accounting for begin offset of this helps fix PR 65741(par)
- // where excl w/begin="5s' was including that 5s in dur passed
- // to children, thus children were playing 5s too long:
- ULONG32 ulSyncBaseDurationForChildren =
- m_pSourceElement->m_ulDuration;
- if (m_pSourceElement->m_bCurBeginIsOffsetFromSyncBase &&
- m_pSourceElement->m_bDurationIncludesDelayBeyondSyncbase)
- {
- HX_ASSERT(ulSyncBaseDurationForChildren >=
- m_pSourceElement->m_ulBeginOffsetFromSyncBase);
- if (ulSyncBaseDurationForChildren >=
- m_pSourceElement->m_ulBeginOffsetFromSyncBase)
- {
- ulSyncBaseDurationForChildren -=
- m_pSourceElement->m_ulBeginOffsetFromSyncBase;
- }
- }
- CHXSimpleList::Iterator i = m_pChildren->Begin();
- for(; i != m_pChildren->End(); ++i)
- {
- CSmilTimelineElement* pElement = (CSmilTimelineElement*)(*i);
- if (pElement->m_pSourceElement &&
- pElement->m_pSourceElement->m_ulDuration >
- m_pSourceElement->m_ulDuration)
- {
- pElement->setDuration(ulSyncBaseDurationForChildren, TRUE);
- }
- }
- }
- }
- cleanup:
- m_pParser->m_pTimelineElementManager->notify(m_pID);
- return;
- }
- void
- CSmilTimelinePar::addDuration(UINT32 ulDuration,
- UINT32 ulDelay,
- UINT32 ulChildDelayBeyondStartOfThis,
- const char* pElementID)
- {
- BOOL bHandled = FALSE;
- UINT32 ulPriorPureDuration = m_pSourceElement->getPureDuration();
- #if defined(_DEBUG) && defined(XXXEH_DEBUGOUT_ADDDURATION)
- {
- FILE* f1 = ::fopen("c:\smil2AddDuration.txt", bFirstTimeAddDurDebugout?
- ADDDURATION_DEBUGOUT_STR_NEW_FILE :
- ADDDURATION_DEBUGOUT_STR_APPEND_TO_FILE );
- ::fprintf(f1, "CSmilTimelinePar{%s}::addDuration(dur=%lu, delay=%lu, "
- "childDelayBeyondThis=%lu, id=%s) m_bDurationSet=%sEn",
- (const char*)m_pID, ulDuration, ulDelay,
- ulChildDelayBeyondStartOfThis, pElementID,
- m_bDurationSet?"TRU":"FALS");
- ::fclose(f1);
- bFirstTimeAddDurDebugout = FALSE;
- }
- #endif
- // /If we're inside a seq, our true "sync base" is not the seq but rather
- // the prievious seq sibling (if any). We need to adjust the ulDelay, if
- // we're in a seq, down to just ulChildDelayBeyondStartOfThis, which is
- // the delay from the prior sibling, not from the seq:
- ULONG32 ulDelayBeyondSyncBase = 0;
- SMILNode* pSyncBaseNode = NULL;
- if (m_pSourceElement->m_pNode)
- {
- pSyncBaseNode = m_pParser->getSyncAncestor(
- m_pSourceElement->m_pNode);
- }
- if (!pSyncBaseNode || !pSyncBaseNode->m_pElement)
- {
- HX_ASSERT(pSyncBaseNode && pSyncBaseNode->m_pElement);
- }
- // /Do this for all time containers (for part of PR52110 post-fix-delay-
- // offset-bug):
- else
- {
- ulDelayBeyondSyncBase = ulChildDelayBeyondStartOfThis;
- }
- BOOL bSetChildCurEndClippedByParent = FALSE;
- BOOL bSetCompletelyRemovedFromTimeline = FALSE;
- BOOL bIsCurChildsFirstAddDuration = FALSE;
- ULONG32 ulCurChildPriorAddedDuration = (UINT32)-1;
- if (!(*m_pChildDurAddedMap)[pElementID])
- {
- bIsCurChildsFirstAddDuration = TRUE;
- }
- else
- {
- ulCurChildPriorAddedDuration =
- (ULONG32)((*m_pChildDurAddedMap)[pElementID]);
- }
- ULONG32 ulActualDurBeyondSyncBase =
- ulDuration + ulDelayBeyondSyncBase - ulChildDelayBeyondStartOfThis;
- // /XXXEH-20020106-test: HX_ASSERT(WAY_IN_THE_FUTURE >= ulActualDurBeyondSyncBase);
- // /Start of fix for PR 55117: explicit dur or end on par should not be
- // overridden by some punk child's dur; if this has an explicit
- // end or dur, don't do anything to its duration based on children durs:
- // /XXXEH- TODO: determine what wins between endsync VS either end or dur
- // if both are specified; here, I assume end|dur wins over endsync:
- if (m_pSourceElement->m_bHasExplicitDur ||
- m_pSourceElement->m_bHasExplicitEnd)
- {
- if ((UINT32)-1 != m_pSourceElement->m_ulDuration &&
- (!m_bDurationSet ||
- !m_pSourceElement->m_bAddDurationAlreadyDone) )
- {
- HX_ASSERT((UINT32)-1 != m_pSourceElement->m_ulDelay);
- HX_ASSERT(m_pSourceElement->m_ulDuration ==
- m_pSourceElement->getPureDuration());
- durationResolved(m_pSourceElement->m_ulDuration, FALSE);
- }
- // /Helps fix PR 6XXXZ (PR 55117 revisited): par in seq where par has explicit dur and
- // children all have smaller durations, we need to give outer time
- // container a chance to hold the presentation open; this is needed
- // when this par is last one in presentation. (Note: body doesn't set
- // the presentation time during createElements() phase because it
- // doesn't have m_pHandler yet then):
- adjustDuration();
- bHandled = TRUE;
- }
- // /Fixes SMIL 1.0's endsync="id(xyz)" and enables SMIL 2.0's
- // id-based endsync: endsync="xyz":
- else if (m_pSourceElement->m_nEndsyncEventSourceTag == SMILEventSourceID)
- {
- if (!m_pSourceElement->m_EndsyncEventSourceID.IsEmpty() &&
- !strcmp(m_pSourceElement->m_EndsyncEventSourceID,pElementID))
- {
- HX_ASSERT(m_pSourceElement->m_ulDuration ==
- m_pSourceElement->getPureDuration());
- // /Don't just use ulDuration in case child has a begin offset
- // or otherwise has a delay beyond this's delay.
- m_pSourceElement->m_ulDuration = ulActualDurBeyondSyncBase;
- durationResolved(m_pSourceElement->m_ulDuration, TRUE);
- bHandled = TRUE;
- }
- // /Fixes endsync="[ID]" part of PR 59584 where addDuration of X (!=ID)
- // happens after that of lower-duration [ID] sibling and 'X' needs to
- // be restricted to ID's duration:
- else if (!m_pSourceElement->m_EndsyncEventSourceID.IsEmpty() &&
- m_pSourceElement->m_ulDuration < ulActualDurBeyondSyncBase)
- {
- // /Adjust for offset from parent, if any:
- bSetChildCurEndClippedByParent = TRUE;
- if (m_pSourceElement->m_ulDuration >
- ulChildDelayBeyondStartOfThis)
- {
- m_pParser->resetTimelineElementDuration(pElementID,
- m_pSourceElement->getPureDuration(),
- // /Changed to *child* prior dur while fixing PR 66391:
- ulActualDurBeyondSyncBase -
- ulChildDelayBeyondStartOfThis);
- m_pParser->m_pTimelineElementManager->notify(pElementID);
- }
- else // /Begin offset is beyond parent's end, so remove it:
- // /Fixes PR 64158 (endsync="[ID]" version)
- {
- bSetCompletelyRemovedFromTimeline = TRUE;
- HX_RESULT retval2 = m_pSourceElement->m_pHandler->
- handleTrackRemoval((const char*)pElementID,
- (INT32)m_pSourceElement->m_pNode->m_nGroup);
- }
- }
- }
- else if(m_pSourceElement->m_nEndsyncEventSourceTag == SMILEventSourceAll)
- {
- // /Hold par open until all children have had a chance to begin;
- // leave the par's duration unresolved awaiting the final child's
- // call to "addDuration" (which may never come if child's begin
- // never resolves):
- // /Helps fix PR 62688(par version): first, check if all children
- // have resolved already; if so, then duration is set so we can't
- // extend it if begin is after parent par ended:
- if (m_nDurationAdded >= m_pChildren->GetCount() &&
- m_pSourceElement->m_ulDuration < ulActualDurBeyondSyncBase)
- {
- bSetChildCurEndClippedByParent = TRUE;
- HX_ASSERT(m_ulLastDuration == m_pSourceElement->m_ulDuration);
- if (m_ulLastDuration > ulChildDelayBeyondStartOfThis)
- {
- // /Helps fix PR 50660 by removing PR 62688-fix code here that
- // turned out to be unnecessary since code elsewhere completely
- // fixes PR 62688. Child should be allowed to extend its
- // parent's duration except if it begins *after* its parent has
- // already ended, which is how we got here, so do nothing.
- }
- else // /Begin offset is beyond parent's end, so remove it:
- // helps fix PR 62688(par) (endsync="all" version of PR 64158)
- {
- bSetCompletelyRemovedFromTimeline = TRUE;
- HX_RESULT retval2 = m_pSourceElement->m_pHandler->
- handleTrackRemoval((const char*)pElementID,
- (INT32)m_pSourceElement->m_pNode->m_nGroup);
- }
- }
- if(ulActualDurBeyondSyncBase < m_ulFirstDuration ||
- !m_bFirstDurationHasBeenSet)
- {
- m_ulFirstDuration = ulActualDurBeyondSyncBase;
- m_bFirstDurationHasBeenSet = TRUE;
- }
- if(ulActualDurBeyondSyncBase > m_ulLastDuration)
- {
- m_ulLastDuration = ulActualDurBeyondSyncBase;
- }
- // /This helps fix PR 62688(par version): this is used to see if
- // we've already resolved our duration (because all children have
- // weighed in):
- INT32 lTotalDurationsAddedIncludingThisOne = (INT32)m_nDurationAdded;
- if (bIsCurChildsFirstAddDuration)
- {
- lTotalDurationsAddedIncludingThisOne++;
- }
- if (lTotalDurationsAddedIncludingThisOne < m_pChildren->GetCount() &&
- // /To help fix PR 59584(par version), only do this once:
- WAY_IN_THE_FUTURE != m_pSourceElement->m_ulDuration)
- {
- // /XXXEH- need a better way, but for now let's say it's
- // resolved to a very big number until all children have
- // resolved begins:
- durationResolved(WAY_IN_THE_FUTURE, TRUE);
- }
- }
- else if(m_pSourceElement->m_ulDuration == (UINT32)-1)
- {
- // /Added delay to duration which works in:
- // "BUG-20010430_endHappening2sTooEarlyForExclThatHas"...
- // ..."2.7sBeginAndDurBasedOnChild(totalPresentationDur5.7s).smil":
- m_pSourceElement->m_ulDuration = ulDuration + ulDelayBeyondSyncBase -
- // /Added this to fix when par child of seq has child w/begin
- // offset, as in the following smil file:
- // "BUG-20010501_(broke20010501earlyAMCheckin)beginOnFirst"...
- ulChildDelayBeyondStartOfThis;
- m_ulFirstDuration = ulActualDurBeyondSyncBase;
- m_bFirstDurationHasBeenSet = TRUE;
- m_ulLastDuration = ulActualDurBeyondSyncBase;
- }
- else
- {
- m_pSourceElement->m_ulDuration =
- (ulActualDurBeyondSyncBase > m_pSourceElement->m_ulDuration) ?
- ulActualDurBeyondSyncBase : m_pSourceElement->m_ulDuration;
- if(ulActualDurBeyondSyncBase < m_ulFirstDuration ||
- // /Fixes several PRs related to endsync="first"; m_ulFirstDuration
- // gets init'd to 0, so we need to see if it's been set or not:
- !m_bFirstDurationHasBeenSet)
- {
- m_ulFirstDuration = ulActualDurBeyondSyncBase;
- m_bFirstDurationHasBeenSet = TRUE;
- }
- if(ulActualDurBeyondSyncBase > m_ulLastDuration)
- {
- m_ulLastDuration = ulActualDurBeyondSyncBase;
- }
- }
- ULONG32 ulRevisedActualDurBeyondSyncBase = ulActualDurBeyondSyncBase;
- if (m_pSourceElement->m_nEndsyncEventSourceTag == SMILEventSourceFirst)
- {
- // /Helps fix PR 66391: if child is time container, make sure this's
- // duration is set to shortest child's duration:
- m_pSourceElement->m_ulDuration = m_ulFirstDuration;
- // /Fixes endsync="first" version of PR 64157 where addDuration
- // of longer vid happens after that of lower-duration sibling and
- // longer one needs to be clipped to that lower duration (or completely
- // removed if begin offset is beyond parent's end (PR 64158)):
- if (m_bFirstDurationHasBeenSet &&
- m_ulFirstDuration < ulActualDurBeyondSyncBase)
- {
- bSetChildCurEndClippedByParent = TRUE;
- if (m_ulFirstDuration > ulChildDelayBeyondStartOfThis)
- {
- m_pParser->resetTimelineElementDuration(pElementID,
- m_ulFirstDuration -
- // /Fixes PR 64160 (ensync="first" version):
- ulChildDelayBeyondStartOfThis,
- // /Changed to *child* prior dur while fixing PR 66391:
- ulActualDurBeyondSyncBase -
- ulChildDelayBeyondStartOfThis);
-
- // /Update dur to be used:
- ulRevisedActualDurBeyondSyncBase = m_ulFirstDuration -
- ulChildDelayBeyondStartOfThis;
- m_pParser->m_pTimelineElementManager->notify(pElementID);
- }
- else // /Begin offset is beyond parent's end, so remove it:
- // /Fixes PR 64158 (endsync="first" version)
- {
- bSetCompletelyRemovedFromTimeline = TRUE;
- HX_RESULT retval2 = m_pSourceElement->m_pHandler->
- handleTrackRemoval((const char*)pElementID,
- (INT32)m_pSourceElement->m_pNode->m_nGroup);
- }
- }
- }
- if (!(*m_pChildDurAddedMap)[pElementID])
- {
- m_nDurationAdded++;
- (*m_pChildDurAddedMap)[pElementID] = (void*)ulRevisedActualDurBeyondSyncBase;
- }
- ULONG32 ulChildrenCount = m_pChildren->GetCount();
- // /Fixes PR 56481 find children of this par that don't have a scheduled
- // begin, i.e., are awaiting an event to begin. endsync="last" says to
- // ignore any children that never play, and we don't know if those
- // event-based begin children will play or not so ignore them for now,
- // and if they ever do begin, *then* re-compute this par's duration:
- ULONG32 ulNonEventBasedBeginChildCount = 0;
- CSmilElement* pCurChildElem = NULL;
- CHXSimpleList::Iterator i = m_pChildren->Begin();
- for(i; i != m_pChildren->End(); ++i)
- {
- CSmilTimelineElement* pTmlnElement =
- (CSmilTimelineElement*)(*i);
- if (pTmlnElement && pTmlnElement->m_pSourceElement)
- {
- BOOL isCurAddDurElem = FALSE;
- if (!strcmp(pTmlnElement->m_pSourceElement->m_pNode->m_id,
- pElementID))
- {
- isCurAddDurElem = TRUE;
- pCurChildElem = pTmlnElement->m_pSourceElement;
- if (bSetChildCurEndClippedByParent && pCurChildElem)
- {
- pCurChildElem->m_bCurEndClippedByParent = TRUE;
- }
- if (bSetCompletelyRemovedFromTimeline && pCurChildElem)
- {
- pCurChildElem->m_bInsertedIntoTimeline = FALSE;
- }
- }
- if ((pTmlnElement->m_pSourceElement->
- m_bHasAtLeastOneNonEventBasedBegin ||
- // /Do this so this par can re-resolve its duration if &
- // when an event-based-begin child gets added (and thus
- // technically now is a child with a clock-valued begin):
- isCurAddDurElem) )
- {
- ulNonEventBasedBeginChildCount++;
- }
- }
- }
-
- if (!bHandled &&
- (m_nDurationAdded >= ulNonEventBasedBeginChildCount &&
- // /If endsync is all, we need to wait for *all* to be added:
- (SMILEventSourceAll!=m_pSourceElement->m_nEndsyncEventSourceTag ||
- m_nDurationAdded == ulChildrenCount) ) &&
- !m_bDurationEvent)
- {
- BOOL bUpdateDurMightBeNeeded = FALSE;
- // /Helps fix PR 62688(par): if duration was set before, but only to
- // hold the timeline open until all (or a particular) child duration
- // became known, then we want to ignore the durationSet flag so that
- // we call duartionResolved() instead of adjustDuration();
- BOOL bIgnoreDurationSetFlag = bIsCurChildsFirstAddDuration &&
- (WAY_IN_THE_FUTURE <= m_pSourceElement->m_ulDelay +
- m_pSourceElement->m_ulDuration);
- // /First, if duration has already been set, then pElement must be an
- // event-based-begin child that just resolved, so we need to reset
- // our duration appropriately:
- if (m_bDurationSet && pCurChildElem && !bIgnoreDurationSetFlag &&
- !pCurChildElem->m_bHasAtLeastOneNonEventBasedBegin)
- {
- bUpdateDurMightBeNeeded = TRUE; // /(PR 59851 hits this line.)
- }
- // Switch on different endsync values
- if(m_pSourceElement->m_nEndsyncEventSourceTag ==
- SMILEventSourceFirst)
- {
- if (bUpdateDurMightBeNeeded)
- {
- if (ulActualDurBeyondSyncBase == m_ulFirstDuration)
- {
- // /XXXEH- revisit now that addDuration accts for endsync:
- ULONG32 ulOldDur = m_pSourceElement->m_ulDuration;
- adjustDuration();
- HX_ASSERT(m_pSourceElement->m_ulDuration == m_ulFirstDuration);
- // /Other half of fix for PR 50679: if updated duration
- // is less than prior dur, then update timeline element:
- if (ulOldDur > m_pSourceElement->m_ulDuration)
- {
- // /Reset duration-set flag to FALSE since we want to
- // override (reset) the dur now that this last child
- // has been resolved (presumably after playback of
- // this par began):
- m_bDurationSet = FALSE;
- HX_ASSERT(m_pSourceElement->m_ulDuration ==
- m_pSourceElement->getPureDuration());
- durationResolved(m_pSourceElement->m_ulDuration, TRUE);
- }
- }
- }
- else
- {
- HX_ASSERT(m_pSourceElement->m_ulDuration ==
- m_pSourceElement->getPureDuration());
- durationResolved(m_ulFirstDuration, TRUE);
- }
- }
- else if(m_pSourceElement->m_nEndsyncEventSourceTag ==
- SMILEventSourceLast)
- {
- if (bUpdateDurMightBeNeeded)
- {
- if (ulActualDurBeyondSyncBase == m_ulLastDuration)
- {
- adjustDuration();
- }
- }
- else
- {
- // /Helps fix PR 62688(par version when endsync="last" is
- // explicitly declared): if we previously resolved our
- // duration to "unresolved" to hold timeline open, then we
- // need to adjust our duration down from WAY_IN_THE_FUTURE:
- if (WAY_IN_THE_FUTURE == m_pSourceElement->m_ulDuration ||
- WAY_IN_THE_FUTURE == m_ulLastDuration ||
- m_pSourceElement->m_ulDuration != m_ulLastDuration)
- {
- // /Fixes part 3 of PR 79699 (explicit endsync=last version)
- // where it plays as indefinite because outer par wasn't
- // adjusting for new non-indef dur:
- if (WAY_IN_THE_FUTURE == m_pSourceElement->m_ulDuration &&
- bIsCurChildsFirstAddDuration)
- {
- HX_ASSERT(WAY_IN_THE_FUTURE == m_ulLastDuration || m_bDurationSet);
- // /Trick adjustDuration() into doing its thing
- // since this is last child being added for 1st time:
- m_bDurationSet = TRUE;
- }
- adjustDuration();
- m_bDurationSet = FALSE;
- }
- HX_ASSERT(m_pSourceElement->m_ulDuration ==
- m_pSourceElement->getPureDuration());
- // /To fix PR 59584(par w/event-ended child), w/"last"), use
- // m_pSourceE.'s dur, not m_ulLastDuration since latter may
- // be wrong if some elements stopped early
- durationResolved(m_pSourceElement->m_ulDuration, TRUE);
- }
- }
- else if(m_pSourceElement->m_nEndsyncEventSourceTag ==
- SMILEventSourceAll)
- {
- if (bUpdateDurMightBeNeeded)
- {
- if (ulActualDurBeyondSyncBase == m_ulLastDuration)
- {
- // /adjustDuration() assumes endsync=last which is OK
- // since we've got all durations:
- adjustDuration();
- }
- }
- else
- {
- // /Helps fix PR 59584(simplified): if we previously resolved
- // our duration to "unresolved" to hold timeline open, then we
- // need to adjust our duration down from WAY_IN_THE_FUTURE:
- if (WAY_IN_THE_FUTURE == m_pSourceElement->m_ulDuration ||
- WAY_IN_THE_FUTURE == m_ulLastDuration ||
- m_pSourceElement->m_ulDuration != m_ulLastDuration)
- {
- if (WAY_IN_THE_FUTURE == m_pSourceElement->m_ulDuration &&
- bIsCurChildsFirstAddDuration)
- {
- HX_ASSERT(WAY_IN_THE_FUTURE == m_ulLastDuration || m_bDurationSet);
- // /See "part 2 of PR 79699" below; don't want to mess
- // with this unless there's content that asserts here:
- HX_ASSERT(m_bDurationSet);
- }
- adjustDuration();
- }
- HX_ASSERT(m_pSourceElement->m_ulDuration ==
- m_pSourceElement->getPureDuration());
- // /Reset duration-set flag to FALSE since we want to
- // override (reset) the dur now that this last child has been
- // resolved (presumably after playback of this par began):
- m_bDurationSet = FALSE;
- // /To fix PR 59584(par w/event-ended child), w/"all"), use
- // m_pSourceE.'s dur, not m_ulLastDuration since latter may
- // be wrong if some elements stopped early
- durationResolved(m_pSourceElement->m_ulDuration, TRUE);
- }
- }
- else
- {
- if (bUpdateDurMightBeNeeded)
- {
- if (ulActualDurBeyondSyncBase == m_pSourceElement->m_ulDuration)
- {
- adjustDuration();
- }
- }
- else
- {
- // /Helps fix PR 62688(par version): if we previously resolved
- // our duration to "unresolved" to hold timeline open, then we
- // need to adjust our duration down from WAY_IN_THE_FUTURE:
- if (WAY_IN_THE_FUTURE == m_pSourceElement->m_ulDuration ||
- WAY_IN_THE_FUTURE == m_ulLastDuration ||
- m_pSourceElement->m_ulDuration != m_ulLastDuration)
- {
- // /Fixes part 2 of PR 79699 (imlicit endsync=last version)
- // where it plays as indefinite because outer par wasn't
- // adjusting for new non-indef dur:
- if (WAY_IN_THE_FUTURE == m_pSourceElement->m_ulDuration &&
- bIsCurChildsFirstAddDuration)
- {
- HX_ASSERT(WAY_IN_THE_FUTURE == m_ulLastDuration || m_bDurationSet);
- // /Trick adjustDuration() into doing its thing
- // since this is last child being added for 1st time:
- m_bDurationSet = TRUE;
- }
- adjustDuration();
- m_bDurationSet = FALSE;
- }
- HX_ASSERT(m_pSourceElement->m_ulDuration ==
- m_pSourceElement->getPureDuration());
- durationResolved(m_pSourceElement->m_ulDuration, FALSE);
- }
- }
- // /This if() block fixes PR 56686 (version 3) and
- // PR 61174 (version 3): if time container has longer dur than its
- // children and it is not a time-child of the <body>, then its dur
- // was never getting accounted for, but now the outer time container
- // sets the duration if its dur is longer than its group's so far;
- // outer time contnr can only be a par if body has multiple children:
- if (m_pSourceElement->m_pNode && m_pSourceElement->m_pHandler)
- {
- // /XXXEH- handle <body><switch><par> and <body><a><par>
- if (m_pSourceElement->m_pNode->m_pParent && (SMILBody ==
- m_pSourceElement->m_pNode->m_pParent->m_tag ||
- m_pSourceElement->m_pNode->
- m_pParent->m_bIsOuterWrapperTimeContainer) )
- {
- UINT32 ulGroup = m_pSourceElement->m_pNode->m_nGroup;
- // /The group duration should be the duration of this
- // outer-most time container:
- HX_RESULT pnrs = m_pSourceElement->m_pHandler->
- resolveGroupDurToOuterTimeContainerDur(
- ulGroup, m_pSourceElement->m_ulDuration);
- }
- }
- }
- }
- void
- CSmilTimelinePar::elementResolved(CSmilTimelineElement* pEventElement)
- {
- parExclElementResolved(pEventElement);
- }
- void
- CSmilTimelinePar::durationResolved(UINT32 ulDuration, BOOL bUpdateChildren)
- {
- parExclDurationResolved(ulDuration, bUpdateChildren);
- }
- #if 0
- #error: **HEY: if this code ever gets enabled, handle CSmilTimelineExcl as well:
- void
- CSmilTimelinePar::setEndsync(EndsyncType eType,
- const char* pEndsyncID,
- UINT32 ulEndsyncClockValue)
- {
- m_eEndsyncType = eType;
- m_ulEndsyncClockValue = ulEndsyncClockValue;
- if(pEndsyncID)
- {
- m_pEndsyncID = new char[strlen(pEndsyncID)+1];
- strcpy(m_pEndsyncID, pEndsyncID); /* Flawfinder: ignore */
- }
- }
- #endif
- /***************************************************************************/
- /*
- * CSmilTimelineSeq methods
- */
- CSmilTimelineSeq::CSmilTimelineSeq(CSmilElement* pSourceElement,
- CSmilParser* pParser):
- CSmilTimelineElement(pSourceElement, pParser),
- m_nDurationAdded(0)
- {
- }
- void
- CSmilTimelineSeq::addDuration(UINT32 ulDuration,
- UINT32 ulDelay,
- UINT32 ulChildDelayBeyondStartOfItsSyncBase,
- const char* pID)
- {
- HX_ASSERT(m_pChildren);
- #if defined(_DEBUG) && defined(XXXEH_DEBUGOUT_ADDDURATION)
- {
- FILE* f1 = ::fopen("c:\smil2AddDuration.txt", bFirstTimeAddDurDebugout?
- ADDDURATION_DEBUGOUT_STR_NEW_FILE :
- ADDDURATION_DEBUGOUT_STR_APPEND_TO_FILE );
- ::fprintf(f1, "CSmilTimelineSeq{%s}::addDuration(dur=%lu, delay=%lu, "
- "childDelayBeyondThis=%lu, id=%s) m_bDurationSet=%sEn",
- (const char*)m_pID, ulDuration, ulDelay,
- ulChildDelayBeyondStartOfItsSyncBase, pID,
- m_bDurationSet?"TRU":"FALS");
- ::fclose(f1);
- bFirstTimeAddDurDebugout = FALSE;
- }
- #endif
- // /I don't think we want to/need to use ulChildDelay; it is > 0 in
- // "BUG-20010502_repeatedElementWithBeginOf3sAndEndOf15s.smil" but
- // that works (offset-wise) so no need to use ulChildDelay...:
- ULONG32 ulActualDurBeyondSyncBase = ulDuration;
- // /Fixes case where this seq has a begin offset from its parent and
- // doesn't have an explicit end or dur; the child being added here
- // ended up playing too short by the amount of this's begin offset:
- BOOL bDurationIncludesDelayBeyondSyncbase = FALSE;
- if (m_pSourceElement->m_bCurBeginIsOffsetFromSyncBase)
- {
- ulActualDurBeyondSyncBase +=
- m_pSourceElement->m_ulBeginOffsetFromSyncBase;
- bDurationIncludesDelayBeyondSyncbase = TRUE;
- }
- if (ulChildDelayBeyondStartOfItsSyncBase > 0)
- {
- // /Helps fix PR 6XXXX: be sure to account for child's delay beyond
- // its prior sibling in this seq, or the seq itself if no prior sib:
- ulActualDurBeyondSyncBase -= ulChildDelayBeyondStartOfItsSyncBase;
- }
- else
- {
- HX_ASSERT(0 == ulChildDelayBeyondStartOfItsSyncBase &&
- "ehodge: negative delay in seq!?");
- }
- BOOL bIsCurChildsFirstAddDuration = FALSE;
- ULONG32 ulCurChildPriorAddedDuration = (UINT32)-1;
- if (!(*m_pChildDurAddedMap)[pID])
- {
- bIsCurChildsFirstAddDuration = TRUE;
- }
- else
- {
- ulCurChildPriorAddedDuration =
- (ULONG32)((*m_pChildDurAddedMap)[pID]);
- }
- if(!m_bDurationSet)
- {
- if(m_pSourceElement->m_ulDuration == (UINT32)-1)
- {
- m_pSourceElement->m_ulDuration = ulActualDurBeyondSyncBase;
- m_pSourceElement->m_bDurationIncludesDelayBeyondSyncbase =
- bDurationIncludesDelayBeyondSyncbase;
- }
- // /Helps fix PR 62688 and PR 59584: never go higher duration than
- // WAY_IN_THE_FUTURE so overall timeline doesn't further extend:
- else if (WAY_IN_THE_FUTURE == ulActualDurBeyondSyncBase ||
- WAY_IN_THE_FUTURE == m_pSourceElement->m_ulDuration)
- {
- m_pSourceElement->m_ulDuration = WAY_IN_THE_FUTURE;
- if (m_pSourceElement->m_ulDelay > 0)
- {
- if (m_pSourceElement->m_ulDuration >=
- m_pSourceElement->m_ulDelay)
- {
- m_pSourceElement->m_ulDuration -=
- m_pSourceElement->m_ulDelay;
- }
- else
- {
- m_pSourceElement->m_ulDuration = 0;
- }
- }
- m_pSourceElement->m_bDurationIncludesDelayBeyondSyncbase =
- bDurationIncludesDelayBeyondSyncbase;
- }
- else
- {
- m_pSourceElement->m_ulDuration += ulActualDurBeyondSyncBase;
- m_pSourceElement->m_bDurationIncludesDelayBeyondSyncbase =
- bDurationIncludesDelayBeyondSyncbase;
- }
- }
- // /Fixes unfiled(?) bug found when PR 52110 was fixed: seq with begin
- // offset>0 and explicit dur was not accounting for this offset in its
- // duration, but parent's addDuration() counts on that being done:
- else if (m_pSourceElement->m_bHasExplicitDur &&
- !m_pSourceElement->m_bDurationIncludesDelayBeyondSyncbase)
- {
- if (m_pSourceElement->m_bCurBeginIsOffsetFromSyncBase)
- {
- m_pSourceElement->m_bDurationIncludesDelayBeyondSyncbase =
- bDurationIncludesDelayBeyondSyncbase;
- m_pSourceElement->m_ulDuration +=
- m_pSourceElement->m_ulBeginOffsetFromSyncBase;
- }
- }
- if (!(*m_pChildDurAddedMap)[pID])
- {
- m_nDurationAdded++;
- (*m_pChildDurAddedMap)[pID] = (void*)ulActualDurBeyondSyncBase;
- }
- if(m_nDurationAdded == m_pChildren->GetCount() ||
- // /Helps fix PR 59584: if our dur is unresolved, then we need to
- // notify our parent (and on up the chain) that there is an
- // currently-indefinite-duration element in the presentation:
- WAY_IN_THE_FUTURE <= m_pSourceElement->m_ulDuration +
- m_pSourceElement->m_ulDelay)
- {
- m_bDurationSet = TRUE;
- if (m_nDurationAdded == m_pChildren->GetCount())
- {
- // /We need to adjust our duration in case it was temporarily set
- // to indefinite; now that we have all children accounted for, we
- // can correctly calculate it: (fixes PR 59584 overall duration)
- adjustDuration();
- }
- // Add our duration to our parent
- if(m_pParent)
- {
- ULONG32 ulDelayFromSyncBaseBegin = 0;
- if (m_pSourceElement->m_bCurBeginIsOffsetFromSyncBase)
- {
- ulDelayFromSyncBaseBegin =
- m_pSourceElement->m_ulBeginOffsetFromSyncBase;
- // /Fixes PR 68875: be sure to add offset from syncbase if
- // not already included:
- if ((UINT32)-1 != ulDelayFromSyncBaseBegin
- && ulDelayFromSyncBaseBegin > 0 &&
- !m_pSourceElement->m_bDurationIncludesDelayBeyondSyncbase)
- {
- m_pSourceElement->m_ulDuration += ulDelayFromSyncBaseBegin;
- m_pSourceElement->m_bDurationIncludesDelayBeyondSyncbase = TRUE;
- }
- }
- m_pParent->addDuration(
- m_pSourceElement->m_ulDuration,
- m_pSourceElement->m_ulDelay,
- ulDelayFromSyncBaseBegin, m_pID);
- m_pSourceElement->m_bAddDurationAlreadyDone = TRUE;
- }
- // /This if() block fixes PR 56686 (version 2) and
- // PR 61174 (version 2): if time container has longer dur than its
- // children and it is not a time-child of the <body>, then its dur
- // was never getting accounted for, but now the outer time container
- // sets the duration if its dur is longer than its group's so far:
- if (m_pSourceElement->m_pNode && m_pSourceElement->m_pHandler)
- {
- if (m_pSourceElement->m_pNode->m_pParent && (SMILBody ==
- m_pSourceElement->m_pNode->m_pParent->m_tag ||
- m_pSourceElement->m_pNode->
- m_pParent->m_bIsOuterWrapperTimeContainer) )
- {
- BOOL bDoResolveGroupDur = TRUE;
- UINT32 ulGroup = m_pSourceElement->m_pNode->m_nGroup;
- if (m_pSourceElement->m_pNode->m_bIsOuterWrapperTimeContainer)
- {
- ulGroup = 0;
- // /If we're outer seq wrapper around multiple groups
- // (or "clips"), then let each group outer time container
- // resolve its group duration:
- if (m_pChildren->GetCount() > 1)
- {
- bDoResolveGroupDur = FALSE;
- }
- }
- if (bDoResolveGroupDur)
- {
- // /The group duration should be the duration of this
- // outer-most time container:
- HX_RESULT pnrs = m_pSourceElement->m_pHandler->
- resolveGroupDurToOuterTimeContainerDur(
- ulGroup, m_pSourceElement->m_ulDuration);
- }
- }
- }
- // Now we know the duration of this <seq>, so
- // we need to check the fill behavior of all our
- // children
- checkChildrenFillBehavior();
- if(m_pDependent)
- {
- HX_ASSERT(m_bDurationSet);
- adjustDependentDuration(m_pDependent);
- #if defined(XXXEH_WAIT_UNTIL_getCurrentScheduledStopTime_IS_FIXED_WHEN_BEGINOFFSETSET_20011022)
- ULONG32 ulTotalDelay = 0;
- if (m_pSourceElement->m_bCurBeginIsOffsetFromSyncBase &&
- m_pSourceElement->m_bDurationIncludesDelayBeyondSyncbase)
- {
- HX_ASSERT(0 && "ehodge: CHANGE NOT TESTED!");
- }
- if (HXR_OK !=
- m_pSourceElement->getCurrentScheduledStopTime(ulTotalDelay))
- {
- goto doneSettingDependent;
- }
- #else
- ULONG32 ulTotalDelay = m_pSourceElement->m_ulDelay +
- m_pSourceElement->m_ulDuration;
- // /Helps fix PR 6XXXX(seq version): if delay is already packed
- // into the duration, then don't count it twice (as can happen in
- // <seq><seq begin="1s">...</seq><seq begin="1s" ...):
- if (m_pSourceElement->m_bDurationIncludesDelayBeyondSyncbase)
- {
- HX_ASSERT(m_pSourceElement->m_ulBeginOffsetFromSyncBase != (UINT32)-1);
- /*OK[]*/ if (m_pSourceElement->m_ulBeginOffsetFromSyncBase != (UINT32)-1)
- {
- HX_ASSERT(m_pSourceElement->m_ulBeginOffsetFromSyncBase <
- ulTotalDelay);
- if (m_pSourceElement->m_ulBeginOffsetFromSyncBase <
- ulTotalDelay)
- {
- ulTotalDelay -=
- m_pSourceElement->m_ulBeginOffsetFromSyncBase;
- }
- }
- }
- #endif
- if (WAY_IN_THE_FUTURE < ulTotalDelay)
- {
- HX_ASSERT(WAY_IN_THE_FUTURE == ulTotalDelay && "PR 59584");
- ulTotalDelay = WAY_IN_THE_FUTURE; // /For PR 59584.
- }
- // /XXXEH- TODO: figure out if we need to claim this is being set
- // by "parent" (which is really time base) so clip-begin-like
- // action can occur; I don't think so, however:
- m_pDependent->setDelay(ulTotalDelay, FALSE);
- }
- #if defined(XXXEH_WAIT_UNTIL_getCurrentScheduledStopTime_IS_FIXED_WHEN_BEGINOFFSETSET_20011022)
- doneSettingDependent:
- #endif
- // /[SMIL 1.0 Compliance] Fixes PR 23779:
- // if a source has event-based timing based on this seq's
- // duration, then we need to notify that source that we've
- // resolved this value:
- m_pParser->m_pTimelineElementManager->notify(m_pID);
- }
- }
- void
- CSmilTimelineSeq::setDelay(UINT32 ulDelay,
- // /NOTE: we ignore this in time containers that aren't media:
- BOOL bSetByParent)
- {
- #if defined(_DEBUG) && defined(XXXEH_DEBUGOUT_ADDDURATION)
- {
- FILE* f1 = ::fopen("c:\smil2AddDuration.txt", bFirstTimeAddDurDebugout?
- ADDDURATION_DEBUGOUT_STR_NEW_FILE :
- ADDDURATION_DEBUGOUT_STR_APPEND_TO_FILE );
- ::fprintf(f1, "CSmilTimelineSeq{%s}::setDelay(delay=%lu, "
- "bSetByParent=%sE) m_bDelaySet=%sEn",
- (const char*)m_pID, ulDelay,
- bSetByParent?"TRU":"FALS",
- m_bDelaySet?"TRU":"FALS");
- ::fclose(f1);
- bFirstTimeAddDurDebugout = FALSE;
- }
- #endif
- if(m_pSourceElement->m_bBeginOffsetSet)
- {
- m_pSourceElement->m_ulDelay = (
- ((INT32)ulDelay+m_pSourceElement->m_lBeginOffset > 0) ?
- (UINT32)((INT32)ulDelay+m_pSourceElement->m_lBeginOffset):0);
- }
- else
- {
- m_pSourceElement->m_ulDelay = ulDelay;
- }
- //XXXJHUG - we need to prevent overwriting the delay when
- // setInitalDelay is called on THIS element, changing this
- // bool causes initialDelaySet to return TRUE.
- m_bDelaySet = TRUE;
- if(m_pChildren && m_pChildren->GetCount() > 0)
- {
- // set delay on first child of seq
- CSmilTimelineElement* pElement =
- (CSmilTimelineElement*)m_pChildren->GetHead();
- pElement->setDelay(m_pSourceElement->m_ulDelay, TRUE);
- // /To fix it so second group plays (PR6XXX5) after fix for (PR6XXX4),
- // need to set the delay of all children since each is not dependent
- // on the prior; problem is that a child 'n' with an explicit dur will
- // (now) tell its parent its dur during the above setDelay() call and
- // that will end up with this->setDuration() call happening too early,
- // farther below, resulting in all groups > n getting a 0 duration:
- SMILNode* pSyncAncestor = m_pParser? m_pParser->getSyncAncestor(
- m_pSourceElement->m_pNode) : NULL;
- if (!pSyncAncestor || (SMILBody == pSyncAncestor->m_tag &&
- m_pSourceElement->m_pNode->m_bIsOuterWrapperTimeContainer) )
- {
- // /Need to set the delays of all children to 0 since each starts its
- // own "clip" (group):
- CHXSimpleList::Iterator i = m_pChildren->Begin();
- ++i; // /Already done for group 0, above.
- for(; i != m_pChildren->End(); ++i)
- {
- pElement = (CSmilTimelineElement*)(*i);
- // /If 0 != this's delay, then body must have begin="x" on it
- // and subsequent groups should not include that delay:
- HX_ASSERT(0 == m_pSourceElement->m_ulDelay);
- pElement->setDelay(0, TRUE);
- }
- }
- }
- // /Fixes PR 24046 (SMIL 2+ seq version): if there are no children,
- // then the seq's duration is zero, so set it to 0:
- else if (m_pSourceElement->m_ulDuration == (UINT32)-1)
- {
- m_pSourceElement->m_ulDuration = 0;
- }
- if (m_pSourceElement->m_ulDuration != (UINT32)-1)
- {
- setDuration(m_pSourceElement->m_ulDuration);
- #if 0 /* 20011024 */
- // /Fixes seq version of PR 61174(version1) and PR 56686
- // (version1): we know our duration already, so let's declare it
- // resolved so we get added to our parent (in case none of our
- // XXXNH: for some reason, despite being if-zeroed-out, this causes a compiler
- // error on linux!
- //#error: DUDE!?!: children of seq can't have unresolved begins!:
- // children have scheduled begin times in which case our
- // ::addDuration() would not get called up front and the overall
- // presentation would not include our duration at first):
- if (m_pSourceElement->m_bHasExplicitDur ||
- m_pSourceElement->m_bHasExplicitEnd)
- {
- // /Be sure not to override a shorter duration that may have
- // been imposed on us by our parent:
- if (!m_bDurationSet ||
- !m_pSourceElement->m_bAddDurationAlreadyDone)
- {
- HX_ASSERT((UINT32)-1 != m_pSourceElement->m_ulDelay);
- m_bDurationSet = TRUE;
- if (m_pParent)
- {
- ULONG32 ulDelayFromSyncBaseBegin = 0;
- if (m_pSourceElement->m_bCurBeginIsOffsetFromSyncBase)
- {
- ulDelayFromSyncBaseBegin =
- m_pSourceElement->m_ulBeginOffsetFromSyncBase;
- if (ulDelayFromSyncBaseBegin > 0 &&
- !m_pSourceElement->m_bDurationIncludesDelayBeyondSyncbase)
- {
- m_pSourceElement->m_bDurationIncludesDelayBeyondSyncbase =
- TRUE; // /=TRUE,not ULONG32. Helps fix PR 68190.
- m_pSourceElement->m_ulDuration += ulDelayFromSyncBaseBegin;
- }
- }
- m_pParent->addDuration(m_pSourceElement->m_ulDuration,
- m_pSourceElement->m_ulDelay,
- ulDelayFromSyncBaseBegin, m_pID);
- m_pSourceElement->m_bAddDurationAlreadyDone = TRUE;
- }
- }
- HX_ASSERT(m_bDurationSet && m_pSourceElement->m_bAddDurationAlreadyDone);
- }
- #endif
- }
- //[SMIL 1.0 Compliance] Helps fix PR 14420 and 23025:
- // if a source has event-based timing based on this seq's
- // begin time (delay) then we need to notify that source
- // that we've resolved this value:
- m_pParser->m_pTimelineElementManager->notify(m_pID);
- }
- void
- CSmilTimelineSeq::setDuration(UINT32 ulDuration, BOOL bSetFromParent,
- BOOL bDurationExtendingDueToPause)
- {
- ASSERT(m_pChildren || 0==ulDuration);
- if (bDurationExtendingDueToPause)
- {
- // /Need to handle this case:
- HX_ASSERT(!bDurationExtendingDueToPause);
- }
- if(!m_bDurationSet ||
- // /Adding this fixes PR 27644 and other cases where explicit
- // dur|end of parent was being ignored by explicit (and larger)
- // dur|end of child seq. This allows repeatDur to work when
- // parent has explicit dur|end since repeatDur creates a seq
- // with an explicit dur:
- bSetFromParent)
- {
- m_pSourceElement->m_ulDuration = ulDuration;
- m_bDurationSet = TRUE;
- }
- UINT32 ulDurationLeft = m_pSourceElement->m_ulDuration;
- RepeatTag repeatTag = RepeatUnknown;
- if (m_pChildren) // /Fixes crash in case of a "<seq></seq>" (PR 65069).
- {
- CHXSimpleList::Iterator i = m_pChildren->Begin();
- for(; i != m_pChildren->End(); ++i)
- {
- CSmilTimelineElement* pTmLnElement = (CSmilTimelineElement*)(*i);
- CSmilElement* pElement = pTmLnElement->m_pSourceElement;
- if (!setElementDuration(ulDurationLeft, pTmLnElement))
- {
- break;
- }
- // /Fixes PR 99498: make sure m_pSourceElement's time values are
- // in same time-coords as pElement's before comparing the two;
- // in this bug, a seq that began at 15s (15000 delay) had a
- // duration that did not include that delay so the below PR 66391
- // fix's if() was erroneously evaluating to true, thus ending
- // this's children early. Use this's soureElement's dur+delay,
- // not its m_ulDuration (which may or may not include delay):
- UINT32 ulDurationPlusDelayOfThisSeq =
- m_pSourceElement->getPureDuration() +
- m_pSourceElement->m_ulDelay;
- // /Helps fix PR 66391: if this's m_ulDuration has shortened and
- // its child(ren)'s duration is shortened to zero as a result,
- // then remove child track if it begins too late to ever play:
- if (pElement && pElement->m_pHandler &&
- pElement->m_ulDelay > ulDurationPlusDelayOfThisSeq &&
- pElement->m_bInsertedIntoTimeline)
- {
- pElement->m_bCurEndClippedByParent = TRUE;
- HX_ASSERT(0 == ulDurationLeft);
- BOOL bCurElementIsTimeContainer =
- m_pParser->isTimeContainerObject(pElement->m_pNode);
- HX_ASSERT(!bCurElementIsTimeContainer && "ehodge:handle_removing_grandkids");
- HX_RESULT retvl = pElement->m_pHandler->handleTrackRemoval(
- (const char*)pElement->m_pNode->m_id,
- (INT32)pElement->m_pNode->m_nGroup);
- if (HXR_OK == retvl)
- {
- // /Notify syncArc dependents that it ended early:
- m_pParser->m_pTimelineElementManager->notify((const char*)pElement->m_pNode->m_id);
- }
- }
- }
- }
- if(m_pDependent)
- {
- HX_ASSERT(m_bDurationSet);
- adjustDependentDuration(m_pDependent);
- #if defined(XXXEH_WAIT_UNTIL_getCurrentScheduledStopTime_IS_FIXED_WHEN_BEGINOFFSETSET_20011022)
- ULONG32 ulTotalDelay = 0;
- if (m_pSourceElement->m_bCurBeginIsOffsetFromSyncBase &&
- m_pSourceElement->m_bDurationIncludesDelayBeyondSyncbase)
- {
- HX_ASSERT(0 && "ehodge: CHANGE NOT TESTED!");
- }
- if (HXR_OK !=
- m_pSourceElement->getCurrentScheduledStopTime(ulTotalDelay))
- {
- goto doneSettingDependent;
- }
- #else
- ULONG32 ulTotalDelay = m_pSourceElement->m_ulDelay +
- m_pSourceElement->m_ulDuration;
- // /Helps fix PR 6XXXX(seq version): if delay is already packed
- // into the duration, then don't count it twice (as can happen in
- // <seq><seq begin="1s">...</seq><seq begin="1s" ...):
- if (m_pSourceElement->m_bDurationIncludesDelayBeyondSyncbase)
- {
- HX_ASSERT(m_pSourceElement->m_ulBeginOffsetFromSyncBase != (UINT32)-1);
- /*OK[]*/ if (m_pSourceElement->m_ulBeginOffsetFromSyncBase != (UINT32)-1)
- {
- HX_ASSERT(m_pSourceElement->m_ulBeginOffsetFromSyncBase <
- ulTotalDelay);
- if (m_pSourceElement->m_ulBeginOffsetFromSyncBase <
- ulTotalDelay)
- {
- ulTotalDelay -=
- m_pSourceElement->m_ulBeginOffsetFromSyncBase;
- }
- }
- }
- #endif
- if (WAY_IN_THE_FUTURE < ulTotalDelay)
- {
- HX_ASSERT(WAY_IN_THE_FUTURE == ulTotalDelay && "PR 59584");
- ulTotalDelay = WAY_IN_THE_FUTURE; // /For PR 59584.
- }
- // /XXXEH- TODO: figure out if we need to claim this is being set
- // by "parent" (which is really time base) so clip-begin-like
- // action can occur; I don't think so, however:
- m_pDependent->setDelay(ulTotalDelay, FALSE);
- }
- #if defined(XXXEH_WAIT_UNTIL_getCurrentScheduledStopTime_IS_FIXED_WHEN_BEGINOFFSETSET_20011022)
- doneSettingDependent:
- #endif
- //[SMIL 1.0 comliance] Helps fix PR 14420 and 23025:
- m_pParser->m_pTimelineElementManager->notify(m_pID);
- }
- void
- CSmilTimelineSeq::setMaxDuration(UINT32 ulMaxDuration)
- {
- HX_ASSERT(m_pChildren);
- m_bMaxDurationSet = TRUE;
- m_pSourceElement->m_ulMaxDuration = ulMaxDuration;
- if (m_pChildren && m_bDelaySet)
- {
- HX_ASSERT((UINT32)-1 != m_pSourceElement->m_ulDelay);
- CSmilTimelineElement* pElement = (CSmilTimelineElement*)m_pChildren->GetHead();
- pElement->setMaxDuration(ulMaxDuration);
- }
- }
- void
- CSmilTimelineSeq::adjustDependentDuration(CSmilTimelineElement* pDependent)
- {
- if(m_bDurationSet || m_bMaxDurationSet)
- {
- UINT32 ulDurationLeft = m_bDurationSet?m_pSourceElement->m_ulDuration:
- m_pSourceElement->m_ulMaxDuration;
- UINT32 ulOriginalDurationLeft = ulDurationLeft;
- if (m_pSourceElement->m_ulMinActiveDur>ulDurationLeft)
- {
- ulDurationLeft = m_pSourceElement->m_ulMinActiveDur;
- }
- BOOL bAdjusted = FALSE;
- RepeatTag repeatTag = RepeatUnknown;
- if (m_pChildren) // /Fixes crash in case of a "<seq></seq>" (PR 65069).
- {
- CHXSimpleList::Iterator i = m_pChildren->Begin();
- for(; i != m_pChildren->End(); ++i)
- {
- CSmilTimelineElement* pElement = (CSmilTimelineElement*)(*i);
- UINT32 ulChildDuration = pElement->getDuration();
-
- if (pElement == pDependent)
- {
- bAdjusted = TRUE;
- }
-
- if (bAdjusted)
- {
- if (pElement->getDelay() != (UINT32)-1)
- {
- HX_ASSERT(pElement->getDelay() < WAY_IN_THE_FUTURE &&
- "need to reset delay b4 dur!");
- }
- // /Fixes PR 59584(parFollowsPar version): If seq has
- // unresolved-dur child, don't set dur of next sibling
- // if it doesn't have delay set yet:
- else if (0 == ulDurationLeft && WAY_IN_THE_FUTURE ==
- ulOriginalDurationLeft)
- {
- break; // /Don't do anything.
- }
- // /Helps fix full repro case of PR 59584: second par
- // in seq will have delay>0 and interim duration
- // of WAY_IN_THE_FUTURE *minus* delay:
- if (WAY_IN_THE_FUTURE <= ulOriginalDurationLeft)
- {
- ulDurationLeft = WAY_IN_THE_FUTURE;
- setElementDuration(ulDurationLeft, pElement);
- break; // /Go no further for now.
- }
- if (!setElementDuration(ulDurationLeft, pElement))
- {
- break;
- }
- }
- else
- {
- if(ulDurationLeft >= ulChildDuration)
- {
- ulDurationLeft -= ulChildDuration;
- }
- else
- {
- ulDurationLeft = 0;
- }
- }
- }
- }
- if (!bAdjusted && m_pParent)
- {
- m_pParent->adjustDependentDuration(pDependent);
- }
- }
- }
- void
- CSmilTimelineSeq::resetDelay(UINT32 ulDelay)
- {
- INT32 lAdjustedDelay = 0;
- UINT32 ulPriorDelay = m_pSourceElement->m_ulDelay;
- if(m_pSourceElement->m_bBeginOffsetSet)
- {
- lAdjustedDelay = (INT32)ulDelay + m_pSourceElement->m_lBeginOffset;
- m_pSourceElement->m_ulDelay = lAdjustedDelay > 0?lAdjustedDelay:0;
- }
- else
- {
- m_pSourceElement->m_ulDelay = ulDelay;
- }
- if(m_pChildren && m_pChildren->GetCount() > 0)
- {
- // set delay on first child of seq
- CSmilTimelineElement* pElement =
- (CSmilTimelineElement*)m_pChildren->GetHead();
- #if 200110241
- if (m_pSourceElement->m_ulDelay !=
- pElement->m_pSourceElement->m_ulDelay)
- {
- pElement->resetDelay(m_pSourceElement->m_ulDelay);
- }
- #else
- pElement->resetDelay(m_pSourceElement->m_ulDelay);
- #endif
- }
- // /To fix PR 59851(seq of seqs), we need to update our next-in-seq
- // (m_pDependent) as well as make sure sync-arc listeners know we've
- // changed our overall time bounds delay as well;
- if (m_pDependent && m_bDurationSet &&
- ulPriorDelay != m_pSourceElement->m_ulDelay)
- {
- #if defined(XXXEH_WAIT_UNTIL_getCurrentScheduledStopTime_IS_FIXED_WHEN_BEGINOFFSETSET_20011022)
- ULONG32 ulTotalDelay = 0;
- if (m_pSourceElement->m_bCurBeginIsOffsetFromSyncBase &&
- m_pSourceElement->m_bDurationIncludesDelayBeyondSyncbase)
- {
- HX_ASSERT(0 && "ehodge: CHANGE NOT TESTED!");
- }
- if (HXR_OK !=
- m_pSourceElement->getCurrentScheduledStopTime(ulTotalDelay))
- {
- goto doneSettingDependent;
- }
- #else
- ULONG32 ulTotalDelay = m_pSourceElement->m_ulDelay +
- m_pSourceElement->m_ulDuration;
- if (m_pSourceElement->m_bDurationIncludesDelayBeyondSyncbase)
- {
- HX_ASSERT(m_pSourceElement->m_ulBeginOffsetFromSyncBase != (UINT32)-1);
- /*OK[]*/ if (m_pSourceElement->m_ulBeginOffsetFromSyncBase != (UINT32)-1)
- {
- HX_ASSERT(m_pSourceElement->m_ulBeginOffsetFromSyncBase <
- ulTotalDelay);
- if (m_pSourceElement->m_ulBeginOffsetFromSyncBase <
- ulTotalDelay)
- {
- ulTotalDelay -=
- m_pSourceElement->m_ulBeginOffsetFromSyncBase;
- }
- }
- }
- #endif
- if (WAY_IN_THE_FUTURE < ulTotalDelay)
- {
- HX_ASSERT(WAY_IN_THE_FUTURE == ulTotalDelay && "PR 59584");
- ulTotalDelay = WAY_IN_THE_FUTURE; // /For PR 59584.
- }
-
- #if defined(_DEBUG) && defined(XXXEH_DEBUGOUT_ADDDURATION)
- {
- FILE* f1 = ::fopen("c:\smil2AddDuration.txt", bFirstTimeAddDurDebugout?
- ADDDURATION_DEBUGOUT_STR_NEW_FILE :
- ADDDURATION_DEBUGOUT_STR_APPEND_TO_FILE );
- ::fprintf(f1, "nt%s:CSmilTimelineSeq::resetDelay(%lu):from %lu to %lu;"
- "tresetting dependent (%s)'s delay to %lun", (const char*)m_pID,
- ulDelay, ulPriorDelay, m_pSourceElement->m_ulDelay,
- (const char*)m_pDependent->m_pID, ulTotalDelay);
- ::fclose(f1);
- bFirstTimeAddDurDebugout = FALSE;
- }
- #endif
-
- m_pDependent->resetDelay(ulTotalDelay);
- #if defined(XXXEH_WAIT_UNTIL_getCurrentScheduledStopTime_IS_FIXED_WHEN_BEGINOFFSETSET_20011022)
- doneSettingDependent:
- #endif
- // /(Added while fixing PR 59851) Let others know our begin time changed:
- m_pParser->m_pTimelineElementManager->notify(m_pID);
- }
- }
- void
- CSmilTimelineSeq::adjustDuration()
- {
- UINT32 ulDuration = 0;
- // /Fixes seq version of PR 50676 (Added during fix for PR 59584):
- ULONG32 ulPriorPureDuration = m_pSourceElement->getPureDuration();
- if (m_pChildren)
- {
- CHXSimpleList::Iterator i = m_pChildren->Begin();
- for(; i != m_pChildren->End(); ++i)
- {
- CSmilTimelineElement* pElement = (CSmilTimelineElement*)(*i);
- if ((UINT32)-1 == pElement->m_pSourceElement->m_ulDuration)
- {
- // /Helps fix PR 59584 (parFollowsPar version): if child dur
- // is not resolved yet, then we're unresolved:
- ulDuration = WAY_IN_THE_FUTURE;
- break;
- }
- ulDuration += pElement->m_pSourceElement->m_ulDuration;
- // /For PR 59584: don't go past "unresolved" dur value:
- if (ulDuration >= WAY_IN_THE_FUTURE)
- {
- ulDuration = WAY_IN_THE_FUTURE;
- break;
- }
- }
- if (!m_pSourceElement->m_bHasExplicitEnd &&
- !m_pSourceElement->m_bHasExplicitDur)
- {
- // /Use child durs only if seq doesn't have explicit end or dur;
- // This helps fix PR 6XXXY:
- m_pSourceElement->m_ulDuration = ulDuration;
- }
- if(m_pParent)
- {
- m_pParent->adjustDuration();
- }
- // /Fixes PR 69410: need to do this no matter what, even if prior <
- // ulDur; resumed element in excl descendent should extend that excl
- // but we've already told the core to limit the presentation duration,
- // so extend it here as needed (also fixes part of PR 50660):
- // /(Added while fixing PR 59584): if our duration got reduced, we need to
- // possibly constrain the group's duration:
- {
- // This group's outer time container, if this is one, needs
- // to set the duration if its dur is longer than its group's so far
- // or if its previous duration was unresolved and now is resolved:
- if (m_pSourceElement->m_pNode && m_pSourceElement->m_pHandler)
- {
- if (m_pSourceElement->m_pNode->m_pParent && (SMILBody ==
- m_pSourceElement->m_pNode->m_pParent->m_tag ||
- m_pSourceElement->m_pNode->
- m_pParent->m_bIsOuterWrapperTimeContainer) )
- {
- BOOL bDoResolveGroupDur = TRUE;
- UINT32 ulGroup = m_pSourceElement->m_pNode->m_nGroup;
- if (m_pSourceElement->m_pNode->m_bIsOuterWrapperTimeContainer)
- {
- ulGroup = 0;
- // /If we're outer wrapper around multiple groups
- // (or "clips"), then let each group outer time container
- // resolve its group duration:
- if (m_pChildren->GetCount() > 1)
- {
- bDoResolveGroupDur = FALSE;
- }
- }
- if (bDoResolveGroupDur)
- {
- // /The group duration should be the duration of this
- // outer-most time container:
- HX_RESULT pnrs = m_pSourceElement->m_pHandler->
- resolveGroupDurToOuterTimeContainerDur(
- ulGroup, m_pSourceElement->m_ulDuration);
- }
- }
- }
- }
- if(m_pDependent)
- {
- #if defined(XXXEH_WAIT_UNTIL_getCurrentScheduledStopTime_IS_FIXED_WHEN_BEGINOFFSETSET_20011022)
- ULONG32 ulTotalDelay = 0;
- if (m_pSourceElement->m_bCurBeginIsOffsetFromSyncBase &&
- m_pSourceElement->m_bDurationIncludesDelayBeyondSyncbase)
- {
- HX_ASSERT(0 && "ehodge: CHANGE NOT TESTED!");
- }
- if (HXR_OK !=
- m_pSourceElement->getCurrentScheduledStopTime(ulTotalDelay))
- {
- goto doneSettingDependent;
- }
- #else
- ULONG32 ulTotalDelay = m_pSourceElement->m_ulDelay +
- m_pSourceElement->m_ulDuration;
- if (m_pSourceElement->m_bDurationIncludesDelayBeyondSyncbase)
- {
- HX_ASSERT(m_pSourceElement->m_ulBeginOffsetFromSyncBase != (UINT32)-1);
- /*OK[]*/ if (m_pSourceElement->m_ulBeginOffsetFromSyncBase != (UINT32)-1)
- {
- HX_ASSERT(m_pSourceElement->m_ulBeginOffsetFromSyncBase <
- ulTotalDelay);
- if (m_pSourceElement->m_ulBeginOffsetFromSyncBase <
- ulTotalDelay)
- {
- ulTotalDelay -=
- m_pSourceElement->m_ulBeginOffsetFromSyncBase;
- }
- }
- }
- #endif
- if (WAY_IN_THE_FUTURE < ulTotalDelay)
- {
- HX_ASSERT(WAY_IN_THE_FUTURE == ulTotalDelay && "PR 59584");
- ulTotalDelay = WAY_IN_THE_FUTURE; // /For PR 59584.
- }
- #if defined(_DEBUG) && defined(XXXEH_DEBUGOUT_ADDDURATION)
- {
- FILE* f1 = ::fopen("c:\smil2AddDuration.txt", bFirstTimeAddDurDebugout?
- ADDDURATION_DEBUGOUT_STR_NEW_FILE :
- ADDDURATION_DEBUGOUT_STR_APPEND_TO_FILE );
- ::fprintf(f1, "nt%s:CSmilTimelineSeq::adjustDuration();tresetting dependent (%s)'s delay to %lun",
- (const char*)m_pID, (const char*)m_pDependent->m_pID,
- ulTotalDelay);
- ::fclose(f1);
- bFirstTimeAddDurDebugout = FALSE;
- }
- #endif
- m_pDependent->resetDelay(ulTotalDelay);
- }
- #if defined(XXXEH_WAIT_UNTIL_getCurrentScheduledStopTime_IS_FIXED_WHEN_BEGINOFFSETSET_20011022)
- doneSettingDependent:
- ;
- #endif
- }
- }
- BOOL
- CSmilTimelineSeq::setElementDuration(UINT32& ulDurationLeft, CSmilTimelineElement* pElement)
- {
- BOOL bContinue = TRUE;
- UINT32 ulChildDuration = pElement->getDuration();
- RepeatTag repeatTag = pElement->m_pSourceElement->m_pNode->m_repeatTag;
-
- if (repeatTag == RepeatIndefiniteOnMe)
- {
- pElement->setMaxDuration(ulDurationLeft);
- ulDurationLeft = 0;
- goto cleanup;
- }
- else if (repeatTag == RepeatIndefiniteOnGroup)
- {
- pElement->setMaxDuration(ulDurationLeft);
- bContinue = FALSE;
- goto cleanup;
- }
- // no more duration left, take care of the duration of the rest of
- // the elements
- if (0 == ulDurationLeft)
- {
- pElement->setDuration(ulDurationLeft, TRUE);
- }
- // if this is the last child, then enforce the duration whatever
- // left
- else if (pElement == m_pChildren->GetTail())
- {
- if (ulChildDuration == (UINT32)-1 &&
- ulDurationLeft >= WAY_IN_THE_FUTURE)
- {
- // /Doing this instead of setDuration() fixes PR 65741 when outer
- // seq gets held open due to tracks' durations setting in a
- // certain order. In this case, don't override possible child
- // explicit dur or end:
- pElement->setMaxDuration(ulDurationLeft);
- }
- else
- {
- pElement->setDuration(ulDurationLeft, TRUE);
- }
- bContinue = FALSE;
- }
- // unknown duration, so we apply max. duration here
- else if (ulChildDuration == (UINT32)-1)
- {
- pElement->setMaxDuration(ulDurationLeft);
- bContinue = FALSE;
- }
- else
- {
- if(ulDurationLeft >= ulChildDuration)
- {
- ulDurationLeft -= ulChildDuration;
- }
- else
- {
- pElement->setDuration(ulDurationLeft, TRUE);
- ulDurationLeft = 0;
- }
- }
- cleanup:
- return bContinue;
- }
- /***************************************************************************/
- // /XXXEH- see if any or all of the following can be combined with
- // CSmilTimelinePar methods, above (with added params for dealing
- // with Excl in minor places):
- /*
- * CSmilTimelineExcl methods
- */
- CSmilTimelineExcl::CSmilTimelineExcl(CSmilElement* pSourceElement,
- CSmilParser* pParser):
- CSmilTimelineElement(pSourceElement, pParser),
- m_nDurationAdded(0),
- m_ulFirstDuration(0),
- m_bFirstDurationHasBeenSet(FALSE),
- m_ulLastDuration(0)
- {
- }
- CSmilTimelineExcl::~CSmilTimelineExcl()
- {
- }
- void
- CSmilTimelineExcl::setDelay(UINT32 ulDelay,
- // /NOTE: we ignore this in time containers that aren't media:
- BOOL bSetByParent)
- {
- #if defined(_DEBUG) && defined(XXXEH_DEBUGOUT_ADDDURATION)
- {
- FILE* f1 = ::fopen("c:\smil2AddDuration.txt", bFirstTimeAddDurDebugout?
- ADDDURATION_DEBUGOUT_STR_NEW_FILE :
- ADDDURATION_DEBUGOUT_STR_APPEND_TO_FILE );
- ::fprintf(f1, "CSmilTimelineExcl{%s}::setDelay(delay=%lu, "
- "bSetByParent=%sE) m_bDelaySet=%sEn",
- (const char*)m_pID, ulDelay,
- bSetByParent?"TRU":"FALS",
- m_bDelaySet?"TRU":"FALS");
- ::fclose(f1);
- bFirstTimeAddDurDebugout = FALSE;
- }
- #endif
- if(m_pSourceElement->m_bBeginOffsetSet)
- {
- m_pSourceElement->m_ulDelay = (
- ((INT32)ulDelay+m_pSourceElement->m_lBeginOffset > 0) ?
- (UINT32)((INT32)ulDelay+m_pSourceElement->m_lBeginOffset):0);
- }
- else
- {
- m_pSourceElement->m_ulDelay = ulDelay;
- }
- if (!m_bDelayEvent)
- {
- m_bDelaySet = TRUE;
- ULONG32 ulNumChildrenWithNonEventBasedBegins = 0;
- if(m_pChildren)
- {
- CHXSimpleList::Iterator i = m_pChildren->Begin();
- for(; i != m_pChildren->End(); ++i)
- {
- CSmilTimelineElement* pElement = (CSmilTimelineElement*)(*i);
- // /Don't set delay of children with no valid begin time; the
- // default begin of an excl child is "indefinite". Note that
- // sync-arc begins of elements that are skipped during this
- // delay-setting-by-parent operation will be OK when they
- // resolve because the resolved time has the delay built in:
- // /Note: tested this with <a> child and it works fine,
- if (pElement->m_pSourceElement &&
- (pElement->m_pSourceElement->m_bBeginOffsetSet
- #if defined(XXXEH_HANDLE_MULTIPLE_EXCL_CHILD_SCHEDULED_BEGINS)
- /*can't do this fix yet because excl child w/beginOffset>0 must wait*/
- // /If parent excl begins on event, child with non-
- // event begin time won't yet have beginOffsetSet;
- // fixes PR 56686(version 7 and 8):
- || pElement->m_pSourceElement->
- m_bHasAtLeastOneNonEventBasedBegin) )
- #else
- ) )
- #endif
- {
- pElement->setDelay(m_pSourceElement->m_ulDelay, TRUE);
- }
- // /else leave delay unresolved.
- // /However, we need to go ahead and see which children have
- // non-event-based begins (see PR 24046 fix, below, which
- // this part of fix for PR 62688 broke by putting the
- // following code inside the if(), above (which never got hit
- // in an excl):
- // /This helps fix PR 62688(excl version):
- if (pElement->m_pSourceElement &&
- pElement->m_pSourceElement->
- m_bHasAtLeastOneNonEventBasedBegin)
- {
- ulNumChildrenWithNonEventBasedBegins++;
- }
- }
- }
- // /Fixes PR 24046 (SMIL 2+ excl version): if there are no children,
- // then the excl's duration is zero, so set it to 0:
- if ((!m_pChildren && m_pSourceElement->m_ulDuration == (UINT32)-1) ||
- 0 == ulNumChildrenWithNonEventBasedBegins)
- {
- // /Checking 1st for explicit end or dur re-fixes PR 57150(excl)
- // which was broken by fix for PR 24046 (note: PR 57150 has dur=x
- // *and* endsync="all" which is a strange thing to author):
- if (!m_pSourceElement->m_bHasExplicitDur &&
- !m_pSourceElement->m_bHasExplicitEnd)
- {
- m_pSourceElement->m_ulDuration = 0;
- }
- // /Helps fix PR 62688(excl version): if all children are
- // event-begun and there is at least one child, and endsync="all",
- // then we have an indefinite duration until all child ends resolve:
- if (m_pChildren && SMILEventSourceAll ==
- m_pSourceElement->m_nEndsyncEventSourceTag &&
- // /Ignore endsync if it has explicit end or dur:
- !m_pSourceElement->m_bHasExplicitDur &&
- !m_pSourceElement->m_bHasExplicitEnd)
- {
- m_pSourceElement->m_ulDuration = WAY_IN_THE_FUTURE;
- }
- }
- if (m_pSourceElement->m_ulDuration != (UINT32)-1)
- {
- setDuration(m_pSourceElement->m_ulDuration);
- #if 20011024
- // /Fixes PR 61174(version1) and excl version of PR 56686
- // (version1): we know our duration already, so let's declare it
- // resolved so we get added to our parent (in case none of our
- // children have scheduled begin times in which case our
- // ::addDuration() would not get called up front and the overall
- // presentation would not include our duration at first):
- if (m_pSourceElement->m_bHasExplicitDur ||
- m_pSourceElement->m_bHasExplicitEnd ||
- // /For PR 62688(excl version) and other endsync="all" bugs:
- SMILEventSourceAll ==
- m_pSourceElement->m_nEndsyncEventSourceTag)
- {
- // /Be sure not to override a shorter duration that may have
- // been imposed on us by our parent:
- if (!m_bDurationSet ||
- !m_pSourceElement->m_bAddDurationAlreadyDone)
- {
- HX_ASSERT(m_pSourceElement->m_ulDuration ==
- m_pSourceElement->getPureDuration());
- HX_ASSERT((UINT32)-1 != m_pSourceElement->m_ulDelay);
- durationResolved(m_pSourceElement->m_ulDuration, FALSE);
- }
- HX_ASSERT(m_bDurationSet && m_pSourceElement->m_bAddDurationAlreadyDone);
- }
- #endif
- }
- }
- else
- // /Let's not claim that the delay is set when we still
- // are awaiting a delay (begin) event; we *do* need to
- // add the delay of this to the event's begin offset.
- // This is done by setting the new "m_bNonEventDelaySet"
- // variable to TRUE and leaving m_bDelaySet to FALSE
- // until the ElementResolved() call sets it to true:
- {
- // /Parent calls setDelay before we get to ElementResolved,
- // thus m_bDelaySet should never be TRUE if we have a
- // delay event:
- HX_ASSERT(!m_bDelaySet);
- m_bNonEventDelaySet = TRUE; //ElementResolved will look at this.
- m_ulNonEventDelay = ulDelay;
- }
-
- if(m_pDependent && m_bDurationSet)
- {
- adjustDependentDuration(m_pDependent);
- #if defined(XXXEH_WAIT_UNTIL_getCurrentScheduledStopTime_IS_FIXED_WHEN_BEGINOFFSETSET_20011022)
- ULONG32 ulTotalDelay = 0;
- if (m_pSourceElement->m_bCurBeginIsOffsetFromSyncBase &&
- m_pSourceElement->m_bDurationIncludesDelayBeyondSyncbase)
- {
- HX_ASSERT(0 && "ehodge: CHANGE NOT TESTED!");
- }
- if (HXR_OK !=
- m_pSourceElement->getCurrentScheduledStopTime(ulTotalDelay))
- {
- goto doneSettingDependent;
- }
- #else
- ULONG32 ulTotalDelay = m_pSourceElement->m_ulDelay +
- m_pSourceElement->m_ulDuration;
- // /Helps fix PR 6XXXX(excl version): if delay is already packed
- // into the duration, then don't count it twice (as can happen in
- // <seq><excl begin="1s">...</excl><excl begin="1s" ...):
- if (m_pSourceElement->m_bDurationIncludesDelayBeyondSyncbase)
- {
- HX_ASSERT(m_pSourceElement->m_ulBeginOffsetFromSyncBase != (UINT32)-1);
- /*OK[]*/ if (m_pSourceElement->m_ulBeginOffsetFromSyncBase != (UINT32)-1)
- {
- HX_ASSERT(m_pSourceElement->m_ulBeginOffsetFromSyncBase <
- ulTotalDelay);
- if (m_pSourceElement->m_ulBeginOffsetFromSyncBase <
- ulTotalDelay)
- {
- ulTotalDelay -=
- m_pSourceElement->m_ulBeginOffsetFromSyncBase;
- }
- }
- }
- #endif
- if (WAY_IN_THE_FUTURE < ulTotalDelay)
- {
- HX_ASSERT(WAY_IN_THE_FUTURE == ulTotalDelay && "PR 59584");
- ulTotalDelay = WAY_IN_THE_FUTURE; // /For PR 59584.
- }
- #if defined(_DEBUG) && defined(XXXEH_DEBUGOUT_ADDDURATION)
- {
- FILE* f1 = ::fopen("c:\smil2AddDuration.txt", bFirstTimeAddDurDebugout?
- ADDDURATION_DEBUGOUT_STR_NEW_FILE :
- ADDDURATION_DEBUGOUT_STR_APPEND_TO_FILE );
- ::fprintf(f1, "nt%s:CSmilTimelineExcl::setDelay(%lu): to %lu;"
- "tresetting dependent (%s)'s delay to %lun", (const char*)m_pID,
- ulDelay, m_pSourceElement->m_ulDelay,
- (const char*)m_pDependent->m_pID, ulTotalDelay);
- ::fclose(f1);
- bFirstTimeAddDurDebugout = FALSE;
- }
- #endif
-
- // /XXXEH- TODO: figure out if we need to claim this is being set
- // by "parent" (which is really time base) so clip-begin-like
- // action can occur; I don't think so, however:
- m_pDependent->setDelay(ulTotalDelay, FALSE);
- }
- #if defined(XXXEH_WAIT_UNTIL_getCurrentScheduledStopTime_IS_FIXED_WHEN_BEGINOFFSETSET_20011022)
- doneSettingDependent:
- #endif
- m_pParser->m_pTimelineElementManager->notify(m_pID);
- }
- void
- CSmilTimelineExcl::setDuration(UINT32 ulDuration, BOOL bSetFromParent,
- BOOL bDurationExtendingDueToPause)
- {
- if (bDurationExtendingDueToPause)
- {
- // /Need to handle this case:
- HX_ASSERT(!bDurationExtendingDueToPause);
- }
- setParExclDuration(ulDuration, bSetFromParent);
- }
- void
- CSmilTimelineExcl::setMaxDuration(UINT32 ulMaxDuration)
- {
- setParExclMaxDuration(ulMaxDuration);
- }
- void
- CSmilTimelineExcl::resetDelay(UINT32 ulDelay)
- {
- INT32 lAdjustedDelay = 0;
- UINT32 ulPriorDelay = m_pSourceElement->m_ulDelay;
- if(m_pSourceElement->m_bBeginOffsetSet)
- {
- lAdjustedDelay = (INT32)ulDelay + m_pSourceElement->m_lBeginOffset;
- m_pSourceElement->m_ulDelay = lAdjustedDelay > 0?lAdjustedDelay:0;
- }
- else
- {
- m_pSourceElement->m_ulDelay = ulDelay;
- }
- if(m_pChildren)
- {
- CHXSimpleList::Iterator i = m_pChildren->Begin();
- for(; i != m_pChildren->End(); ++i)
- {
- CSmilTimelineElement* pElement = (CSmilTimelineElement*)(*i);
- // /Don't set delay of children with no valid begin time; the
- // default begin of an excl child is "indefinite". Note that
- // sync-arc begins of elements that are skipped during this
- // delay-setting-by-parent operation will be OK when they
- // resolve because the resolved time has the delay built in:
- // /Note: tested this with <a> child and it works fine,
- if (pElement->m_pSourceElement &&
- (pElement->m_pSourceElement->m_bBeginOffsetSet
- #if defined(XXXEH_HANDLE_MULTIPLE_EXCL_CHILD_SCHEDULED_BEGINS)
- /*can't do this fix yet because excl child w/beginOffset>0 must wait*/
- // /If parent excl begins on event, child with non-
- // event begin time won't yet have beginOffsetSet;
- // fixes PR 56686(version 7 and 8):
- || pElement->m_pSourceElement->
- m_bHasAtLeastOneNonEventBasedBegin) )
- #else
- // Fixes PR 86106(version2): if this excl is in
- // 2nd or subsequent child of seq then any updates to
- // any prior sibling's duration wasn't causing this
- // excl to adjust its children's delays accordingly.
- // Now, we do so if and only if m_bDelaySet and has
- // a non-event-based begin:
- || pElement->m_bDelaySet &&
- pElement->m_pSourceElement->
- m_bHasAtLeastOneNonEventBasedBegin
- ) )
- #endif
- {
- pElement->resetDelay(m_pSourceElement->m_ulDelay);
- }
- // /else leave delay unresolved.
- }
- }
- // /To fix PR 59851(seq of excls), we need to update our next-in-seq
- // (m_pDependent) as well as make sure sync-arc listeners know we've
- // changed our overall time bounds delay as well;
- if (m_pDependent && m_bDurationSet &&
- ulPriorDelay != m_pSourceElement->m_ulDelay)
- {
- #if defined(XXXEH_WAIT_UNTIL_getCurrentScheduledStopTime_IS_FIXED_WHEN_BEGINOFFSETSET_20011022)
- ULONG32 ulTotalDelay = 0;
- if (m_pSourceElement->m_bCurBeginIsOffsetFromSyncBase &&
- m_pSourceElement->m_bDurationIncludesDelayBeyondSyncbase)
- {
- HX_ASSERT(0 && "ehodge: CHANGE NOT TESTED!");
- }
- if (HXR_OK !=
- m_pSourceElement->getCurrentScheduledStopTime(ulTotalDelay))
- {
- goto doneSettingDependent;
- }
- #else
- ULONG32 ulTotalDelay = m_pSourceElement->m_ulDelay +
- m_pSourceElement->m_ulDuration;
- if (m_pSourceElement->m_bDurationIncludesDelayBeyondSyncbase)
- {
- HX_ASSERT(m_pSourceElement->m_ulBeginOffsetFromSyncBase != (UINT32)-1);
- /*OK[]*/ if (m_pSourceElement->m_ulBeginOffsetFromSyncBase != (UINT32)-1)
- {
- HX_ASSERT(m_pSourceElement->m_ulBeginOffsetFromSyncBase <
- ulTotalDelay);
- if (m_pSourceElement->m_ulBeginOffsetFromSyncBase <
- ulTotalDelay)
- {
- ulTotalDelay -=
- m_pSourceElement->m_ulBeginOffsetFromSyncBase;
- }
- }
- }
- #endif
- if (WAY_IN_THE_FUTURE < ulTotalDelay)
- {
- HX_ASSERT(WAY_IN_THE_FUTURE == ulTotalDelay && "PR 59584");
- ulTotalDelay = WAY_IN_THE_FUTURE; // /For PR 59584.
- }
-
- #if defined(_DEBUG) && defined(XXXEH_DEBUGOUT_ADDDURATION)
- {
- FILE* f1 = ::fopen("c:\smil2AddDuration.txt", bFirstTimeAddDurDebugout?
- ADDDURATION_DEBUGOUT_STR_NEW_FILE :
- ADDDURATION_DEBUGOUT_STR_APPEND_TO_FILE );
- ::fprintf(f1, "nt%s:CSmilTimelineExcl::resetDelay(%lu):from %lu to %lu;"
- "tresetting dependent (%s)'s delay to %lun", (const char*)m_pID,
- ulDelay, ulPriorDelay, m_pSourceElement->m_ulDelay,
- (const char*)m_pDependent->m_pID, ulTotalDelay);
- ::fclose(f1);
- bFirstTimeAddDurDebugout = FALSE;
- }
- #endif
- m_pDependent->resetDelay(ulTotalDelay);
- #if defined(XXXEH_WAIT_UNTIL_getCurrentScheduledStopTime_IS_FIXED_WHEN_BEGINOFFSETSET_20011022)
- doneSettingDependent:
- #endif
- // /(Added while fixing PR 59851) Let others know our begin time changed:
- m_pParser->m_pTimelineElementManager->notify(m_pID);
- }
- }
- void
- CSmilTimelineExcl::adjustDuration()
- {
- BOOL bReset = FALSE;
- UINT32 ulDuration = 0;
- BOOL bDurationSet = FALSE;
- BOOL bEndsyncIdDurationFound = FALSE; // /For endsync="[Some ID]"
- // /Fixes excl version of PR 50676 (Added during fix for PR 59584):
- ULONG32 ulPriorPureDuration = m_pSourceElement->getPureDuration();
- if (!m_bDurationSet)
- {
- // /NOTE: If this has children who have not yet resolved their begin
- // times (which is why we're in this if(), then other children whose
- // durations have extended due to pausing will have no effect on
- // this parent. We need to let this parent update its duration
- // accordingly (and its parents' durs as well).
- goto cleanup;
- }
- if(m_pChildren)
- {
- CHXSimpleList::Iterator i = m_pChildren->Begin();
- for(; i != m_pChildren->End(); ++i)
- {
- CSmilTimelineElement* pElement = (CSmilTimelineElement*)(*i);
- // /Checking this fixes excl version of PR 69290: if child duration
- // isn't set yet, don't use it here:
- if (!pElement->m_bDurationSet)
- {
- continue;
- }
- HX_ASSERT((UINT32)-1 != pElement->m_pSourceElement->m_ulDuration);
- // /Make sure we take endsync into account here:
- if (SMILEventSourceFirst == m_pSourceElement->m_nEndsyncEventSourceTag)
- {
- if (!bDurationSet)
- {
- ulDuration = pElement->m_pSourceElement->m_ulDuration;
- }
- else
- {
- ulDuration = (ulDuration < pElement->m_pSourceElement->m_ulDuration) ?
- ulDuration : pElement->m_pSourceElement->m_ulDuration;
- }
- bDurationSet = TRUE;
- }
- else if (SMILEventSourceID == m_pSourceElement->m_nEndsyncEventSourceTag)
- {
- if (pElement->m_pSourceElement->m_pNode &&
- m_pSourceElement->m_EndsyncEventSourceID ==
- pElement->m_pSourceElement->m_pNode->m_id)
- {
- ulDuration = pElement->m_pSourceElement->m_ulDuration;
- bEndsyncIdDurationFound = TRUE;
- bDurationSet = TRUE;
- }
- }
- // /This else-if block fixes problem in PR 62688 repro case where
- // restarting a child, prior to all children playing, caused excl
- // to resolve its dur as if it were endsync="last":
- else if (SMILEventSourceAll ==
- m_pSourceElement->m_nEndsyncEventSourceTag)
- {
- if (m_pChildren &&
- m_nDurationAdded >= m_pChildren->GetCount())
- {
- ulDuration = (ulDuration > pElement->m_pSourceElement->m_ulDuration) ?
- ulDuration : pElement->m_pSourceElement->m_ulDuration;
- bDurationSet = TRUE;
- }
- else
- {
- // /Don't adjust duration until all child durs are in:
- goto cleanup;
- }
- }
- else // /For "last", use the largest child duration:
- {
- ulDuration = (ulDuration > pElement->m_pSourceElement->m_ulDuration) ?
- ulDuration : pElement->m_pSourceElement->m_ulDuration;
- bDurationSet = TRUE;
- }
- // /Fixes PR 50806 (excl versions 1 & 2): if this has "min"
- // attribute set, ulDuration shouldn't be less regardless
- // of endSync:
- if (m_pSourceElement->m_ulMinActiveDur > ulDuration)
- {
- ulDuration = m_pSourceElement->m_ulMinActiveDur;
- }
- }
- // /!bDurationSet happens in PR 50588 (case 2: begin="x.end"), when
- // child has begun playing but has not yet resolved its duration:
- if (!bDurationSet)
- { HX_ASSERT(bDurationSet && "contact-ehodge");
- goto cleanup;
- }
- if (SMILEventSourceID == m_pSourceElement->m_nEndsyncEventSourceTag)
- {
- if (!bEndsyncIdDurationFound)
- {
- goto cleanup; // /That id'd child not added to timeline yet.
- }
- }
- //check m_ulAuthoredDur here:
- if (!m_pSourceElement->m_bHasExplicitEnd &&
- !m_pSourceElement->m_bHasExplicitDur)
- {
- m_pSourceElement->m_ulDuration = ulDuration;
- }
-
- // /Moved this out of the above if() so it gets called every time, to
- // fix PR 6XXX? and re-fix PR 55117: we should always give our parents
- // a chance to set the outer-time-container duration so it can (re)-
- // state to the core what the group duration should be:
- if(m_pParent)
- {
- m_pParent->adjustDuration();
- }
- // /Moved this out to happen all the time, too:
- if (m_pDependent)
- {
- #if defined(XXXEH_WAIT_UNTIL_getCurrentScheduledStopTime_IS_FIXED_WHEN_BEGINOFFSETSET_20011022)
- ULONG32 ulTotalDelay = 0;
- if (m_pSourceElement->m_bCurBeginIsOffsetFromSyncBase &&
- m_pSourceElement->m_bDurationIncludesDelayBeyondSyncbase)
- {
- HX_ASSERT(0 && "ehodge: CHANGE NOT TESTED!");
- }
- if (HXR_OK != m_pSourceElement->getCurrentScheduledStopTime(
- ulTotalDelay))
- {
- goto doneSettingDependent;
- }
- #else
- ULONG32 ulTotalDelay = m_pSourceElement->m_ulDelay +
- m_pSourceElement->m_ulDuration;
- if (m_pSourceElement->m_bDurationIncludesDelayBeyondSyncbase)
- {
- HX_ASSERT(m_pSourceElement->m_ulBeginOffsetFromSyncBase != (UINT32)-1);
- /*OK[]*/ if (m_pSourceElement->m_ulBeginOffsetFromSyncBase != (UINT32)-1)
- {
- HX_ASSERT(m_pSourceElement->m_ulBeginOffsetFromSyncBase <
- ulTotalDelay);
- if (m_pSourceElement->m_ulBeginOffsetFromSyncBase <
- ulTotalDelay)
- {
- ulTotalDelay -=
- m_pSourceElement->m_ulBeginOffsetFromSyncBase;
- }
- }
- }
- #endif
- if (WAY_IN_THE_FUTURE < ulTotalDelay)
- {
- // /XXXEH- If delay is greater than this, I want to know:
- HX_ASSERT(WAY_IN_THE_FUTURE == ulTotalDelay && "PR 59584");
- ulTotalDelay = WAY_IN_THE_FUTURE; // /For PR 59584.
- }
- #if defined(_DEBUG) && defined(XXXEH_DEBUGOUT_ADDDURATION)
- {
- FILE* f1 = ::fopen("c:\smil2AddDuration.txt", bFirstTimeAddDurDebugout?
- ADDDURATION_DEBUGOUT_STR_NEW_FILE :
- ADDDURATION_DEBUGOUT_STR_APPEND_TO_FILE );
- ::fprintf(f1, "nt%s:CSmilTimelineExcl::adjustDuration();tresetting dependent (%s)'s delay to %lun",
- (const char*)m_pID, (const char*)m_pDependent->m_pID, ulTotalDelay);
- ::fclose(f1);
- bFirstTimeAddDurDebugout = FALSE;
- }
- #endif
- m_pDependent->resetDelay(ulTotalDelay);
- }
- #if defined(XXXEH_WAIT_UNTIL_getCurrentScheduledStopTime_IS_FIXED_WHEN_BEGINOFFSETSET_20011022)
- doneSettingDependent:
- ;
- #endif
- }
- // /Fixes PR 69410 (with outer excl): do this no matter what, even if
- // prior < ulDur; resumed element in excl should extend this excl but
- // we've already told the core to limit the presentation duration,
- // so extend it here as needed:
- // /(Added while fixing PR 59584): if our duration got reduced, we need to
- // possibly constrain our children:
- {
- // /For PR 62688 & PR 59584: remove check for ulPriorDuration being
- // WAY_IN_THE_FUTURE since PR 50676 works without it and there are
- // cases where our dur may re-resolve, & updating children is needed:
- // This group's outer time container, if this is one, needs
- // to set the duration if its dur is longer than its group's so far
- // or if its previous duration was unresolved and now is resolved:
- if (m_pSourceElement->m_pNode && m_pSourceElement->m_pHandler)
- {
- if (m_pSourceElement->m_pNode->m_pParent && (SMILBody ==
- m_pSourceElement->m_pNode->m_pParent->m_tag ||
- m_pSourceElement->m_pNode->
- /*OK[]*/ m_pParent->m_bIsOuterWrapperTimeContainer) )
- {
- // /The group duration should be the duration of this
- // outer-most time container:
- HX_RESULT pnrs = m_pSourceElement->m_pHandler->
- resolveGroupDurToOuterTimeContainerDur(
- m_pSourceElement->m_pNode->m_nGroup,
- m_pSourceElement->m_ulDuration);
- }
- }
- if(m_pChildren)
- {
- // /Accounting for begin offset of this helps fix PR 65741(excl)
- // where excl w/begin="5s' was including that 5s in dur passed
- // to children, thus children were playing 5s too long:
- ULONG32 ulSyncBaseDurationForChildren =
- m_pSourceElement->m_ulDuration;
- if (m_pSourceElement->m_bCurBeginIsOffsetFromSyncBase &&
- m_pSourceElement->m_bDurationIncludesDelayBeyondSyncbase)
- {
- HX_ASSERT(ulSyncBaseDurationForChildren >=
- m_pSourceElement->m_ulBeginOffsetFromSyncBase);
- if (ulSyncBaseDurationForChildren >=
- m_pSourceElement->m_ulBeginOffsetFromSyncBase)
- {
- ulSyncBaseDurationForChildren -=
- m_pSourceElement->m_ulBeginOffsetFromSyncBase;
- }
- }
- CHXSimpleList::Iterator i = m_pChildren->Begin();
- for(; i != m_pChildren->End(); ++i)
- {
- CSmilTimelineElement* pElement = (CSmilTimelineElement*)(*i);
- if (pElement->m_pSourceElement &&
- pElement->m_pSourceElement->m_ulDuration >
- m_pSourceElement->m_ulDuration)
- {
- pElement->setDuration(ulSyncBaseDurationForChildren, TRUE);
- }
- }
- }
- }
- cleanup:
- m_pParser->m_pTimelineElementManager->notify(m_pID);
- return;
- }
- void
- CSmilTimelineExcl::addDuration(UINT32 ulDuration,
- UINT32 ulDelay,
- UINT32 ulChildDelayBeyondStartOfThis,
- const char* pElementID)
- {
- BOOL bHandled = FALSE;
- UINT32 ulPriorPureDuration = m_pSourceElement->getPureDuration();
- #if defined(_DEBUG) && defined(XXXEH_DEBUGOUT_ADDDURATION)
- {
- FILE* f1 = ::fopen("c:\smil2AddDuration.txt", bFirstTimeAddDurDebugout?
- ADDDURATION_DEBUGOUT_STR_NEW_FILE :
- ADDDURATION_DEBUGOUT_STR_APPEND_TO_FILE );
- ::fprintf(f1, "CSmilTimelineExcl{%s}::addDuration(dur=%lu, delay=%lu, "
- "childDelayBeyondThis=%lu, id=%s) m_bDurationSet=%sEn",
- (const char*)m_pID, ulDuration, ulDelay,
- ulChildDelayBeyondStartOfThis, pElementID,
- m_bDurationSet?"TRU":"FALS");
- ::fclose(f1);
- bFirstTimeAddDurDebugout = FALSE;
- }
- #endif
- // /If we're inside a seq, our true "sync base" is not the seq but rather
- // the prievious seq sibling (if any). We need to adjust the ulDelay, if
- // we're in a seq, down to just ulChildDelayBeyondStartOfThis, which is
- // the delay from the prior sibling, not from the seq:
- ULONG32 ulDelayBeyondSyncBase = 0;
- SMILNode* pSyncBaseNode = NULL;
- if (m_pSourceElement->m_pNode)
- {
- pSyncBaseNode = m_pParser->getSyncAncestor(
- m_pSourceElement->m_pNode);
- }
- if (!pSyncBaseNode || !pSyncBaseNode->m_pElement)
- {
- HX_ASSERT(pSyncBaseNode && pSyncBaseNode->m_pElement);
- }
- // /Do this for all time containers (for part of PR52110 post-fix-delay-
- // offset-bug):
- else
- {
- ulDelayBeyondSyncBase = ulChildDelayBeyondStartOfThis;
- }
- BOOL bSetChildCurEndClippedByParent = FALSE;
- BOOL bSetCompletelyRemovedFromTimeline = FALSE;
- BOOL bIsCurChildsFirstAddDuration = FALSE;
- ULONG32 ulCurChildPriorAddedDuration = (UINT32)-1;
- if (!(*m_pChildDurAddedMap)[pElementID])
- {
- bIsCurChildsFirstAddDuration = TRUE;
- }
- else
- {
- ulCurChildPriorAddedDuration =
- (ULONG32)((*m_pChildDurAddedMap)[pElementID]);
- }
- ULONG32 ulActualDurBeyondSyncBase =
- ulDuration + ulDelayBeyondSyncBase - ulChildDelayBeyondStartOfThis;
- // /XXXEH-20020106-test: HX_ASSERT(WAY_IN_THE_FUTURE >= ulActualDurBeyondSyncBase);
- // /Start of fix for PR 55117: explicit dur or end on par should not be
- // overridden by some punk child's dur; if this has an explicit
- // end or dur, don't do anything to its duration based on children durs:
- // /XXXEH- TODO: determine what wins between endsync VS either end or dur
- // if both are specified; here, I assume end|dur wins over endsync:
- if (m_pSourceElement->m_bHasExplicitDur ||
- m_pSourceElement->m_bHasExplicitEnd)
- {
- if ((UINT32)-1 != m_pSourceElement->m_ulDuration &&
- (!m_bDurationSet ||
- !m_pSourceElement->m_bAddDurationAlreadyDone) )
- {
- HX_ASSERT((UINT32)-1 != m_pSourceElement->m_ulDelay);
- HX_ASSERT(m_pSourceElement->m_ulDuration ==
- m_pSourceElement->getPureDuration());
- durationResolved(m_pSourceElement->m_ulDuration, FALSE);
- }
- // /Helps fix PR 6XXXZ (PR 55117 revisited): par in seq where par has explicit dur and
- // children all have smaller durations, we need to give outer time
- // container a chance to hold the presentation open; this is needed
- // when this par is last one in presentation. (Note: body doesn't set
- // the presentation time during createElements() phase because it
- // doesn't have m_pHandler yet then):
- adjustDuration();
- bHandled = TRUE;
- }
- // /Fixes SMIL 1.0's endsync="id(xyz)" and enables SMIL 2.0's
- // id-based endsync: endsync="xyz":
- else if (m_pSourceElement->m_nEndsyncEventSourceTag == SMILEventSourceID)
- {
- if (!m_pSourceElement->m_EndsyncEventSourceID.IsEmpty() &&
- !strcmp(m_pSourceElement->m_EndsyncEventSourceID,pElementID))
- {
- // /Don't just use ulDuration in case child has a begin offset
- // or otherwise has a delay beyond this's delay.
- m_pSourceElement->m_ulDuration = ulActualDurBeyondSyncBase;
- durationResolved(m_pSourceElement->m_ulDuration, TRUE);
- bHandled = TRUE;
- }
- }
- else if(m_pSourceElement->m_nEndsyncEventSourceTag == SMILEventSourceAll)
- {
- // /Hold excl open until all children have had a chance to begin;
- // leave the excl's duration unresolved awaiting the final child's
- // call to "addDuration" (which may never come if child's begin
- // never resolves):
- // /Helps fix PR 62688(excl version): first, check if all children
- // have resolved already; if so, then duration is set so we can't
- // extend it if begin is after parent excl ended:
- if (m_nDurationAdded >= m_pChildren->GetCount() &&
- m_pSourceElement->m_ulDuration < ulActualDurBeyondSyncBase)
- {
- bSetChildCurEndClippedByParent = TRUE;
- HX_ASSERT(m_ulLastDuration == m_pSourceElement->m_ulDuration);
- if (m_ulLastDuration > ulChildDelayBeyondStartOfThis)
- {
- // /Helps fix PR 50660 by removing PR 62688-fix code here that
- // turned out to be unnecessary since code elsewhere completely
- // fixes PR 62688. Child should be allowed to extend its
- // parent's duration except if it begins *after* its parent has
- // already ended, which is how we got here, so do nothing.
- }
- else // /Begin offset is beyond parent's end, so remove it:
- // helps fix PR 62688(excl) (endsync="all" version of PR 64158)
- {
- bSetCompletelyRemovedFromTimeline = TRUE;
- HX_RESULT retval2 = m_pSourceElement->m_pHandler->
- handleTrackRemoval((const char*)pElementID,
- (INT32)m_pSourceElement->m_pNode->m_nGroup);
- }
- }
- if(ulActualDurBeyondSyncBase < m_ulFirstDuration ||
- !m_bFirstDurationHasBeenSet)
- {
- m_ulFirstDuration = ulActualDurBeyondSyncBase;
- m_bFirstDurationHasBeenSet = TRUE;
- }
- if(ulActualDurBeyondSyncBase > m_ulLastDuration)
- {
- m_ulLastDuration = ulActualDurBeyondSyncBase;
- }
- // /This helps fix PR 62688(par version): this is used to see if
- // we've already resolved our duration (because all children have
- // weighed in):
- INT32 lTotalDurationsAddedIncludingThisOne = (INT32)m_nDurationAdded;
- if (bIsCurChildsFirstAddDuration)
- {
- lTotalDurationsAddedIncludingThisOne++;
- }
- if (lTotalDurationsAddedIncludingThisOne < m_pChildren->GetCount() &&
- // /To help fix PR 59584(excl version), only do this once:
- WAY_IN_THE_FUTURE != m_pSourceElement->m_ulDuration)
- {
- // /XXXEH- need a better way, but for now let's say it's
- // resolved to a very big number until all children have
- // resolved begins:
- durationResolved(WAY_IN_THE_FUTURE, TRUE);
- }
- }
- else if(m_pSourceElement->m_ulDuration == (UINT32)-1)
- {
- // /Added delay to duration which works in:
- // "BUG-20010430_endHappening2sTooEarlyForExclThatHas"...
- // ..."2.7sBeginAndDurBasedOnChild(totalPresentationDur5.7s).smil":
- m_pSourceElement->m_ulDuration = ulDuration + ulDelayBeyondSyncBase -
- // /Works in excl version of
- // "BUG-20010502(at0700hrs))_firstOu"..."2ndChildIsExcl.smil"
- // /(NOTE: this will be non-zero in the case where the parent
- // excl (this) has endsync="first" and is adding first child
- // due to an event:
- ulChildDelayBeyondStartOfThis;
- m_ulFirstDuration = ulActualDurBeyondSyncBase;
- m_bFirstDurationHasBeenSet = TRUE;
- if (WAY_IN_THE_FUTURE >= m_pSourceElement->m_ulDuration &&
- !bIsCurChildsFirstAddDuration &&
- WAY_IN_THE_FUTURE <= ulCurChildPriorAddedDuration)
- {
- HX_ASSERT(0); // /TESTING! PR 59584.
- // then don't do the next line (?):
- }
- m_ulLastDuration = ulActualDurBeyondSyncBase;
- }
- else
- // /An excl time container can only have one active track at a time,
- // but it can know that it will play subsequent ones if they have
- // resolved delays (which is how we entered this "else" block, so we
- // need to calculate the excl's duration as the latest that any resolved
- // element will play as far as we know at this point. Excl's duration
- // in many cases will then vary as childrens' delays become resolved
- // over time:
- // /XXXEH- test this!!! I left it the same as for Par, but we should
- // consider interrupt behavior of the excl's elements since one may
- // not start while another "uninterruptable" element is playing and
- // thus may not affect the excl's initial dur:
- {
- m_pSourceElement->m_ulDuration =
- (ulActualDurBeyondSyncBase > m_pSourceElement->m_ulDuration) ?
- ulActualDurBeyondSyncBase : m_pSourceElement->m_ulDuration;
- // /XXXEH- TODO: handle m_ulFirst...etc. (or make sure they work) now
- // that delay is being added (as it should be) to m_ulDuration, above:
- if(ulActualDurBeyondSyncBase < m_ulFirstDuration ||
- !m_bFirstDurationHasBeenSet)
- {
- m_ulFirstDuration = ulActualDurBeyondSyncBase;
- m_bFirstDurationHasBeenSet = TRUE;
- }
- if(ulActualDurBeyondSyncBase > m_ulLastDuration)
- {
- m_ulLastDuration = ulActualDurBeyondSyncBase;
- }
- }
- if (!(*m_pChildDurAddedMap)[pElementID])
- {
- m_nDurationAdded++;
- (*m_pChildDurAddedMap)[pElementID] = (void*)ulActualDurBeyondSyncBase;
- }
- ULONG32 ulChildrenCount = m_pChildren->GetCount();
- // /Fixes PR 56481(excl version) find children that don't have a scheduled
- // begin, i.e., are awaiting an event to begin. endsync="last" says to
- // ignore any children that never play, and we don't know if those
- // event-based begin children will play or not so ignore them for now,
- // and if they ever do begin, *then* re-compute this excl's duration:
- ULONG32 ulNonEventBasedBeginChildCount = 0;
- CSmilElement* pCurChildElem = NULL;
- CHXSimpleList::Iterator i = m_pChildren->Begin();
- for(i; i != m_pChildren->End(); ++i)
- {
- CSmilTimelineElement* pTmlnElement =
- (CSmilTimelineElement*)(*i);
- if (pTmlnElement && pTmlnElement->m_pSourceElement)
- {
- BOOL isCurAddDurElem = FALSE;
- if (!strcmp(pTmlnElement->m_pSourceElement->m_pNode->m_id,
- pElementID))
- {
- isCurAddDurElem = TRUE;
- pCurChildElem = pTmlnElement->m_pSourceElement;
- if (bSetChildCurEndClippedByParent && pCurChildElem)
- {
- pCurChildElem->m_bCurEndClippedByParent = TRUE;
- }
- if (bSetCompletelyRemovedFromTimeline && pCurChildElem)
- {
- pCurChildElem->m_bInsertedIntoTimeline = FALSE;
- }
- }
- if ((pTmlnElement->m_pSourceElement->
- m_bHasAtLeastOneNonEventBasedBegin ||
- // /Do this so this par can re-resolve its duration if &
- // when an event-based-begin child gets added (and thus
- // technically now is a child with a clock-valued begin):
- isCurAddDurElem) )
- {
- ulNonEventBasedBeginChildCount++;
- }
- }
- }
-
- if (!bHandled &&
- (m_nDurationAdded >= ulNonEventBasedBeginChildCount &&
- // /If endsync is all, we need to wait for *all* to be added:
- (SMILEventSourceAll!=m_pSourceElement->m_nEndsyncEventSourceTag ||
- m_nDurationAdded == ulChildrenCount) ) &&
- !m_bDurationEvent)
- {
- BOOL bUpdateDurMightBeNeeded = FALSE;
- // /Helps fix PR 62688(excl): if duration was set before, but only to
- // hold the timeline open until all (or a particular) child duration
- // became known, then we want to ignore the durationSet flag so that
- // we call duartionResolved() instead of adjustDuration();
- BOOL bIgnoreDurationSetFlag = bIsCurChildsFirstAddDuration &&
- (WAY_IN_THE_FUTURE <= m_pSourceElement->m_ulDelay +
- m_pSourceElement->m_ulDuration);
- // /First, if duration has already been set, then pElement must be an
- // event-based-begin child that just resolved, so we need to reset
- // our duration appropriately:
- if (m_bDurationSet && pCurChildElem && !bIgnoreDurationSetFlag &&
- !pCurChildElem->m_bHasAtLeastOneNonEventBasedBegin)
- {
- bUpdateDurMightBeNeeded = TRUE;
- }
- if(m_pSourceElement->m_nEndsyncEventSourceTag ==
- SMILEventSourceFirst)
- {
- if (bUpdateDurMightBeNeeded)
- {
- if (ulActualDurBeyondSyncBase == m_ulFirstDuration)
- {
- // /XXXEH- revisit now that addDuration accts for endsync:
- ULONG32 ulOldDur = m_pSourceElement->m_ulDuration;
- adjustDuration();
- HX_ASSERT(m_pSourceElement->m_ulDuration == m_ulFirstDuration);
- // /Other half of fix for PR 50679: if updated duration
- // is less than prior dur, then update timeline element:
- if (ulOldDur > m_pSourceElement->m_ulDuration)
- {
- // /Reset duration-set flag to FALSE since we want to
- // override (reset) the dur now that this last child
- // has been resolved (presumably after playback of
- // this par began):
- m_bDurationSet = FALSE;
- durationResolved(m_pSourceElement->m_ulDuration, TRUE);
- }
- }
- }
- else
- {
- durationResolved(m_ulFirstDuration, TRUE);
- }
- }
- else if(m_pSourceElement->m_nEndsyncEventSourceTag ==
- SMILEventSourceLast)
- {
- if (bUpdateDurMightBeNeeded)
- {
- if (ulActualDurBeyondSyncBase == m_ulLastDuration)
- {
- adjustDuration();
- }
- }
- else
- {
- // /Helps fix PR 59584(simplified): if we previously resolved
- // our duration to "unresolved" to hold timeline open, then we
- // need to adjust our duration down from WAY_IN_THE_FUTURE:
- if (WAY_IN_THE_FUTURE == m_pSourceElement->m_ulDuration ||
- WAY_IN_THE_FUTURE == m_ulLastDuration ||
- m_pSourceElement->m_ulDuration != m_ulLastDuration)
- {
- if (WAY_IN_THE_FUTURE == m_pSourceElement->m_ulDuration &&
- bIsCurChildsFirstAddDuration)
- {
- // /See "part 2 of PR 79699" above; don't want to mess
- // with this unless there's content that asserts here:
- HX_ASSERT(m_bDurationSet);
- }
- adjustDuration();
- m_bDurationSet = FALSE;
- }
- HX_ASSERT(m_pSourceElement->m_ulDuration ==
- m_pSourceElement->getPureDuration());
- // /To fix PR 59584(exclVersionSimplified, w/"last"), use
- // m_pSourceE.'s dur, not m_ulLastDuration since latter may
- // be wrong if some elements stopped early
- durationResolved(m_pSourceElement->m_ulDuration, TRUE);
- }
- }
- else if(m_pSourceElement->m_nEndsyncEventSourceTag ==
- SMILEventSourceAll)
- {
- if (bUpdateDurMightBeNeeded)
- {
- if (ulActualDurBeyondSyncBase == m_ulLastDuration)
- {
- // /adjustDuration() assumes endsync=last which is OK
- // since we've got all durations:
- adjustDuration();
- }
- }
- else
- {
- // /Helps fix PR 59584(excl, simpl.): if we previously resolved
- // our duration to "unresolved" to hold timeline open, then we
- // need to adjust our duration down from WAY_IN_THE_FUTURE:
- if (WAY_IN_THE_FUTURE == m_pSourceElement->m_ulDuration ||
- WAY_IN_THE_FUTURE == m_ulLastDuration ||
- m_pSourceElement->m_ulDuration != m_ulLastDuration)
- {
- if (WAY_IN_THE_FUTURE == m_pSourceElement->m_ulDuration &&
- bIsCurChildsFirstAddDuration)
- {
- // /See "part 2 of PR 79699" above; don't want to mess
- // with this unless there's content that asserts here:
- HX_ASSERT(m_bDurationSet);
- }
- adjustDuration();
- }
- HX_ASSERT(m_pSourceElement->m_ulDuration ==
- m_pSourceElement->getPureDuration());
- // /Reset duration-set flag to FALSE since we want to
- // override (reset) the dur now that this last child has been
- // resolved (presumably after playback of this par began):
- m_bDurationSet = FALSE;
- // /To fix PR 59584(exclVersionSimplified), use m_pSourceE.'s
- // duration, not m_ulLastDuration since latter may be wrong
- // if some elements stopped early:
- durationResolved(m_pSourceElement->m_ulDuration, TRUE);
- }
- }
- else
- {
- if (bUpdateDurMightBeNeeded)
- {
- if (ulActualDurBeyondSyncBase == m_pSourceElement->m_ulDuration)
- {
- adjustDuration();
- }
- }
- else
- {
- // /Helps fix PR 62688(excl version): if we previously resolved
- // our duration to "unresolved" to hold timeline open, then we
- // need to adjust our duration down from WAY_IN_THE_FUTURE:
- if (WAY_IN_THE_FUTURE == m_pSourceElement->m_ulDuration ||
- WAY_IN_THE_FUTURE == m_ulLastDuration ||
- m_pSourceElement->m_ulDuration != m_ulLastDuration)
- {
- if (WAY_IN_THE_FUTURE == m_pSourceElement->m_ulDuration &&
- bIsCurChildsFirstAddDuration)
- {
- // /See "part 2 of PR 79699" above; don't want to mess
- // with this unless there's content that asserts here:
- HX_ASSERT(m_bDurationSet);
- }
- adjustDuration();
- m_bDurationSet = FALSE;
- }
- HX_ASSERT(m_pSourceElement->m_ulDuration == m_ulLastDuration);
- durationResolved(m_pSourceElement->m_ulDuration, FALSE);
- }
- }
- // /This if() block fixes PR 56686 (version 4) and
- // PR 61174 (version 4): if time container has longer dur than its
- // children and it is not a time-child of the <body>, then its dur
- // was never getting accounted for, but now the outer time container
- // sets the duration if its dur is longer than its group's so far;
- // outer time contnr can only be a par if body has multiple children:
- if (m_pSourceElement->m_pNode && m_pSourceElement->m_pHandler)
- {
- // /XXXEH- handle <body><switch><par> and <body><a><par>
- if (m_pSourceElement->m_pNode->m_pParent && (SMILBody ==
- m_pSourceElement->m_pNode->m_pParent->m_tag ||
- m_pSourceElement->m_pNode->
- /*OK[]*/ m_pParent->m_bIsOuterWrapperTimeContainer) )
- {
- UINT32 ulGroup = m_pSourceElement->m_pNode->m_nGroup;
- // /The group duration should be the duration of this
- // outer-most time container:
- HX_RESULT pnrs = m_pSourceElement->m_pHandler->
- resolveGroupDurToOuterTimeContainerDur(
- ulGroup, m_pSourceElement->m_ulDuration);
- }
- }
- }
- }
- void
- CSmilTimelineExcl::elementResolved(CSmilTimelineElement* pEventElement)
- {
- parExclElementResolved(pEventElement);
- }
- void
- CSmilTimelineExcl::durationResolved(UINT32 ulDuration, BOOL bUpdateChildren)
- {
- parExclDurationResolved(ulDuration, bUpdateChildren);
- }
- /***************************************************************************/
- /*
- * CSmilTimelineAnchor methods
- */
- CSmilTimelineAnchor::CSmilTimelineAnchor(CSmilElement* pSourceElement,
- CSmilParser* pParser):
- CSmilTimelineElement(pSourceElement, pParser)
- , m_nDurationAdded(0)
- {
- }
- CSmilTimelineAnchor::~CSmilTimelineAnchor()
- {
- }
- void
- CSmilTimelineAnchor::elementResolved(CSmilTimelineElement* pEventElement)
- {
- //First, let's see if we have a begin event to resolve:
- if ( (m_pSourceElement->m_nBeginEventSourceTag == SMILEventSourceBegin ||
- m_pSourceElement->m_nBeginEventSourceTag == SMILEventSourceClock) &&
- m_pSourceElement->m_BeginEventSourceID == pEventElement->m_pID)
- {
- if(pEventElement->m_bDelaySet)
- {
- //[SMIL 1.0 Compliance] Helps fix 14420:
- if (m_bNonEventDelaySet)
- {
- //Add non-event delay to syncArc element's delay + clock offset:
- LONG32 lSum =
- (LONG32)pEventElement->m_pSourceElement->m_ulDelay +
- m_pSourceElement->m_lBeginEventClockValue;
- HX_ASSERT(lSum >= 0 && "ehodge: handle neg delay propogation");
- lSum = (lSum<0? 0 : lSum); //clip off negative vals.
- m_pSourceElement->m_ulDelay = m_ulNonEventDelay + (ULONG32)lSum;
- }
- else
- {
- m_ulNonEventDelay = 0;
- //Just set delay to syncArc element's delay:
- //Do the following in case sum is negative; if so, we
- // want to use zero.
- LONG32 lSum =
- (LONG32)pEventElement->m_pSourceElement->m_ulDelay +
- // /Fixes case where anchor/area has begin="foo.begin+5s"
- // we need to account for the 5s here:
- m_pSourceElement->m_lBeginEventClockValue;
- HX_ASSERT(lSum >= 0 && "ehodge: handle neg delay propogation");
- lSum = (lSum<0? 0 : lSum); //clip off negative vals.
- m_pSourceElement->m_ulDelay = (ULONG32)lSum;
- // /Now, we need to set the vars that keep track of our
- // offset from our syncBase element because isCurrentLink
- // uses times relative to our syncBase:
- SMILNode* pSyncNode = (!m_pParser? NULL :
- m_pParser->getSyncAncestor(m_pSourceElement->m_pNode));
- HX_ASSERT(pSyncNode && pSyncNode->m_pElement);
- if (pSyncNode && pSyncNode->m_pElement)
- {
- ULONG32 ulSyncBaseDelay =
- pSyncNode->m_pElement->m_ulDelay;
- HX_ASSERT((UINT32)-1 != ulSyncBaseDelay);
- if ((UINT32)-1 != ulSyncBaseDelay &&
- (UINT32)-1 != m_pSourceElement->m_ulDelay )
- {
- HX_ASSERT(m_pSourceElement->m_ulDelay >=
- ulSyncBaseDelay);
- m_pSourceElement->m_bCurBeginIsOffsetFromSyncBase =
- TRUE;
- if (m_pSourceElement->m_ulDelay >= ulSyncBaseDelay)
- {
- ULONG32 ulEffectiveBeginOffset =
- m_pSourceElement->m_ulDelay -
- ulSyncBaseDelay;
- m_pSourceElement->m_ulBeginOffsetFromSyncBase =
- ulEffectiveBeginOffset;
- }
- else
- {
- m_pSourceElement->m_ulBeginOffsetFromSyncBase = 0;
- }
- }
- }
- }
- m_bNonEventDelaySet = m_bDelaySet = TRUE;
- if(m_pChildren)
- {
- CHXSimpleList::Iterator i = m_pChildren->Begin();
- for(; i != m_pChildren->End(); ++i)
- {
- CSmilTimelineElement* pElement =
- (CSmilTimelineElement*)(*i);
- pElement->setDelay(m_pSourceElement->m_ulDelay, TRUE);
- }
- }
- }
- }
- else if(m_pSourceElement->m_nBeginEventSourceTag == SMILEventSourceEnd &&
- m_pSourceElement->m_BeginEventSourceID == pEventElement->m_pID)
- {
- // /If event element's duration is "WAY_IN_THE_FUTURE" then it's
- // essentially an unresolved end time, so we should not resolve
- // based on it:
- if(pEventElement->m_bDurationSet && WAY_IN_THE_FUTURE !=
- pEventElement->m_pSourceElement->m_ulDuration)
- {
- //[SMIL 1.0 Compliance] Helps fix 14420:
- if (m_bNonEventDelaySet)
- {
- //Add non-event delay to syncArc element's delay + clock offset:
- LONG32 lSum =
- (LONG32)pEventElement->m_pSourceElement->m_ulDuration +
- (LONG32)pEventElement->m_pSourceElement->m_ulDelay +
- // /Fixes begin="foo.end+5s"; 5s was being ignored:
- m_pSourceElement->m_lBeginEventClockValue;
- HX_ASSERT(lSum >= 0 && "ehodge: handle neg delay propogation");
- lSum = (lSum<0? 0 : lSum); //clip off negative vals.
- m_pSourceElement->m_ulDelay = m_ulNonEventDelay + (ULONG32)lSum;
- }
- else
- {
- //Add non-event delay to syncArc element's delay + clock offset:
- LONG32 lSum =
- (LONG32)pEventElement->m_pSourceElement->m_ulDuration +
- (LONG32)pEventElement->m_pSourceElement->m_ulDelay +
- // /Fixes PR 68495 begin="foo.end+5s"; 5s was ignored
- // without the following:
- m_pSourceElement->m_lBeginEventClockValue;
- HX_ASSERT(lSum >= 0 && "ehodge: handle neg delay propogation");
- lSum = (lSum<0? 0 : lSum); //clip off negative vals.
- m_ulNonEventDelay = 0;
- m_pSourceElement->m_ulDelay = (ULONG32)lSum;
- }
- m_bNonEventDelaySet = m_bDelaySet = TRUE;
- if(m_pChildren)
- {
- CHXSimpleList::Iterator i = m_pChildren->Begin();
- for(; i != m_pChildren->End(); ++i)
- {
- CSmilTimelineElement* pElement =
- (CSmilTimelineElement*)(*i);
- pElement->setDelay(m_pSourceElement->m_ulDelay, TRUE);
- }
- }
- }
- }
-
- //XXXEH-The following cases need to be tested!:
- if ( (m_pSourceElement->m_nEndEventSourceTag == SMILEventSourceBegin ||
- m_pSourceElement->m_nEndEventSourceTag == SMILEventSourceClock) &&
- m_pSourceElement->m_EndEventSourceID == pEventElement->m_pID)
- {
- if(pEventElement->m_bDelaySet)
- {
- LONG32 lSum =(LONG32)pEventElement->m_pSourceElement->m_ulDelay +
- m_pSourceElement->m_lEndEventClockValue;
- HX_ASSERT(lSum >= 0 && "ehodge: handle neg delay propogation");
- lSum = (lSum<0? 0 : lSum); //clip off negative vals.
- durationResolved((ULONG32)lSum);
- }
- }
- else if(m_pSourceElement->m_nEndEventSourceTag == SMILEventSourceEnd &&
- m_pSourceElement->m_EndEventSourceID == pEventElement->m_pID)
- {
- // /If event element's duration is "WAY_IN_THE_FUTURE" then it's
- // essentially an unresolved end time, so we should not resolve
- // based on it:
- if(pEventElement->m_bDurationSet && WAY_IN_THE_FUTURE !=
- pEventElement->m_pSourceElement->m_ulDuration)
- {
- LONG32 lSum =(LONG32)pEventElement->getDuration() +
- m_pSourceElement->m_lEndEventClockValue;
- // /If the event element has a delay, we need to add that:
- if(pEventElement->m_bDelaySet)
- {
- lSum += (LONG32)pEventElement->m_pSourceElement->m_ulDelay;
- if (pEventElement->m_pSourceElement->m_bBeginOffsetSet)
- {
- lSum -= pEventElement->m_pSourceElement->m_lBeginOffset;
- }
- }
- HX_ASSERT(lSum >= 0 && "ehodge: handle neg delay propogation");
- lSum = (lSum<0? 0 : lSum); //clip off negative vals.
- durationResolved((ULONG32)lSum);
- }
- }
- }
- void
- CSmilTimelineAnchor::durationResolved(UINT32 ulDuration)
- {
- if(!m_bDurationSet)
- {
- m_bDurationSet = TRUE;
- m_pSourceElement->m_ulDuration = ulDuration;
- }
- }
- CSmilTimelineAnimate::CSmilTimelineAnimate(CSmilElement* pSourceElement,
- CSmilParser* pParser)
- : CSmilTimelineElement(pSourceElement, pParser)
- {
- }
- CSmilTimelineAnimate::~CSmilTimelineAnimate()
- {
- }
- void CSmilTimelineAnimate::setDuration(UINT32 ulDuration, BOOL bSetFromParent,
- BOOL bDurationExtendingDueToPause)
- {
- if (!bSetFromParent)
- {
- CSmilTimelineElement::setDuration(ulDuration, bSetFromParent,
- bDurationExtendingDueToPause);
- }
- }