📄 smldoc.cpp
字号:
// Lock the composition if necessary
BOOL bIsLocked = isSiteCompositionLocked();
if (!bIsLocked)
{
lockSiteComposition();
}
// Now run through and adjust the size of the sites
resetSites(pBox, FALSE);
// Unlock the composition if necessary
if (!bIsLocked)
{
unlockSiteComposition();
}
// If we're supposed to turn composition mode off,
// then do it now. Otherwise, if we were already
// in composition mode, then blt the site composition
if (!bInCompositionMode)
{
turnSiteCompositionModeOFF();
}
}
}
}
void CSmilDocumentRenderer::zoomRect(CSmilBasicBox* pBox,
double dScaleX,
double dScaleY)
{
if (pBox)
{
// Set the zoom scale factors for this box
pBox->m_dZoomScaleFactorX = dScaleX;
pBox->m_dZoomScaleFactorY = dScaleY;
// Save off the unscaled rect
pBox->m_RectNoZoom = pBox->m_Rect;
// Apply these scale factors to the rect (with rounding)
// Make sure we don't round the left/right and top/bottom
// independently - this can result in spurious width/height
// changes, even when the actual floating point scaled width
// and height doesn't change.
double dWidth = (double) HXxRECT_WIDTH(pBox->m_Rect);
double dHeight = (double) HXxRECT_HEIGHT(pBox->m_Rect);
pBox->m_Rect.left = (INT32) floor((((double) pBox->m_Rect.left) * dScaleX) + 0.5);
pBox->m_Rect.top = (INT32) floor((((double) pBox->m_Rect.top) * dScaleY) + 0.5);
INT32 lScaledWidth = (INT32) floor(dWidth * dScaleX + 0.5);
INT32 lScaledHeight = (INT32) floor(dHeight * dScaleY + 0.5);
pBox->m_Rect.right = pBox->m_Rect.left + lScaledWidth;
pBox->m_Rect.bottom = pBox->m_Rect.top + lScaledHeight;
// Run through any renderer site children and update
// the scale factors of their site watchers
if (pBox->m_pChildRendererSiteList &&
m_pSiteWatcherMap)
{
LISTPOSITION pos = pBox->m_pChildRendererSiteList->GetHeadPosition();
while (pos)
{
IHXSite* pRndSite = (IHXSite*) pBox->m_pChildRendererSiteList->GetNext(pos);
if (pRndSite)
{
// Look up the site watcher in the site watcher map
void* pVoid = NULL;
if (m_pSiteWatcherMap->Lookup((void*) pRndSite, pVoid) && pVoid)
{
CSmilSiteWatcher* pWatcher = (CSmilSiteWatcher*) pVoid;
pWatcher->SetZoomScaleFactors(dScaleX, dScaleY);
}
}
}
}
// Is this a region? If it has a parent, then it
// must be a region
if (pBox->m_pParent)
{
// XXXMEH - these are holdover members which currently
// need to be set, but should be taken out soon
CSmilBasicRegion* pRegion = (CSmilBasicRegion*) pBox;
pRegion->m_rect = pRegion->m_Rect;
pRegion->m_originalRect = pRegion->m_Rect;
}
// Recurse through the children
if (pBox->m_pChildList)
{
LISTPOSITION pos = pBox->m_pChildList->GetHeadPosition();
while (pos)
{
CSmilBasicBox* pListBox =
(CSmilBasicBox*) pBox->m_pChildList->GetNext(pos);
zoomRect(pListBox, dScaleX, dScaleY);
}
}
}
}
void CSmilDocumentRenderer::recomputeBoxLayout(CSmilBasicBox* pBox, BOOL bOptimizeRedraws)
{
if (pBox)
{
// Clear the resolved flags
clearResolvedFlags(pBox);
// Compute left and right of the region rects
computeBoxDimension(pBox, BoxDimensionWidth);
// Compute top and bottom of the region rects
computeBoxDimension(pBox, BoxDimensionHeight);
// We may currently be zoomed. If so, then
// adjust for the zoom
if (pBox->m_eResizeBehavior == ResizeZoom && !m_bDoNotZoom &&
(pBox->m_dZoomScaleFactorX != 1.0 ||
pBox->m_dZoomScaleFactorY != 1.0))
{
// Set all the scale factors
zoomRect(pBox, pBox->m_dZoomScaleFactorX, pBox->m_dZoomScaleFactorY);
}
// Now run through and adjust the size of the sites
resetSites(pBox, bOptimizeRedraws);
}
}
HX_RESULT
CSmilDocumentRenderer::handleRegion(CSmilRegion* pElement)
{
HX_RESULT retVal = HXR_OK;
if (pElement)
{
// Create the CSmilBasicRegion element
CSmilBasicRegion* pRegion = new CSmilBasicRegion(pElement);
if (pRegion)
{
// Set the parent child relationships
retVal = setRegionParentChild(pRegion);
if (SUCCEEDED(retVal))
{
// Add this region to the map - m_pRegionMap is
// the "owner" of the CSmilBasicRegion, so when it
// goes away, all of the CSmilBasicRegion's go away.
if (m_pRegionMap)
{
m_pRegionMap->SetAt((const char*) pElement->m_pNode->m_id,
(void*) pRegion);
}
}
}
else
{
retVal = HXR_OUTOFMEMORY;
}
}
else
{
retVal = HXR_FAIL;
}
return retVal;
}
HX_RESULT
CSmilDocumentRenderer::handleRegPoint(CSmilRegPoint* pElement)
{
HX_RESULT retVal = HXR_OK;
if (pElement && pElement->m_pNode)
{
// Does the map already exist
if (!m_pRegPointMap)
{
// Create the map
m_pRegPointMap = new CHXMapStringToOb();
}
if (m_pRegPointMap)
{
// Add this regPoint to the map
m_pRegPointMap->SetAt((const char*) pElement->m_pNode->m_id,
(void*) pElement);
}
else
{
retVal = HXR_OUTOFMEMORY;
}
}
else
{
retVal = HXR_FAIL;
}
return retVal;
}
#if defined(HELIX_FEATURE_SMIL2_MULTIWINDOWLAYOUT)
HX_RESULT
CSmilDocumentRenderer::handleViewport(CSmilViewport* pElement)
{
HX_RESULT retVal = HXR_FAIL;
if (pElement)
{
// Does the viewport list exist yet?
if (!m_pViewportList)
{
// Create the list
m_pViewportList = new CHXSimpleList();
}
if (m_pViewportList)
{
// Create a viewport object
CSmilBasicViewport* pPort = new CSmilBasicViewport(pElement);
if (pPort)
{
// Add it to the list
m_pViewportList->AddTail((void*) pPort);
// Clear the return value
retVal = HXR_OK;
}
}
}
return retVal;
}
#endif /* #if defined(HELIX_FEATURE_SMIL2_MULTIWINDOWLAYOUT) */
#if defined(HELIX_FEATURE_SMIL2_TRANSITIONS)
HX_RESULT CSmilDocumentRenderer::handleTransition(CSmilTransition* pTrans)
{
HX_RESULT retVal = HXR_FAIL;
if (pTrans)
{
// Create the transition map if necessary
if (!m_pTransitionMap)
{
m_pTransitionMap = new CHXMapStringToOb();
}
if (m_pTransitionMap)
{
// Create a transition info object
CSmilTransitionInfo* pInfo = new CSmilTransitionInfo(pTrans, m_pContext);
if (pInfo)
{
// Put this info object in the map
m_pTransitionMap->SetAt((const char*) pTrans->m_pNode->m_id,
(void*) pInfo);
// Clear the return value
retVal = HXR_OK;
}
}
}
return retVal;
}
#endif /* #if defined(HELIX_FEATURE_SMIL2_TRANSITIONS) */
#if defined(HELIX_FEATURE_SMIL2_ANIMATION)
HX_RESULT CSmilDocumentRenderer::handleAnimate(CSmilAnimateElement* pAnimate)
{
MLOG_ANIM(m_pErrorMessages,"CSmilDocumentRenderer::handleAnimate() id=%s tel=%s t=%lu\n",
(const char*) pAnimate->m_pNode->m_id,
(const char*) *pAnimate->m_pTargetElementID,
pAnimate->m_ulDelay);
HX_RESULT retVal = HXR_OK;
if (pAnimate)
{
// XXXMEH - try here to schedule other animations and
// elements that may be using this animate element as
// a sync-arc. This should get us through interop, but this
// needs to be re-examined later.
m_pSmilParser->durationResolved(pAnimate->m_pNode->m_id,
pAnimate->m_ulActiveDuration);
// Add this to the animation map
if (!m_pAnimationMap)
{
m_pAnimationMap = new CHXMapStringToOb();
}
if (m_pAnimationMap)
{
m_pAnimationMap->SetAt(pAnimate->m_pNode->m_id, (void*) pAnimate);
}
// Update the duration contributed to
// only by animations
UINT32 ulAnimEnd = pAnimate->m_ulDelay + pAnimate->m_ulActiveDuration;
if (ulAnimEnd > m_ulAnimDuration)
{
m_ulAnimDuration = ulAnimEnd;
}
// See if we've already scheduled an event for
// this animate element
CSmilAnimateEvent* pAnimEvent = getAnimateEvent(pAnimate);
if (pAnimEvent)
{
// We HAVE already scheduled an event
// for this animate element. This is most likely
// an interactive animation which can begin
// several times. We should adjust the time for
// this event instead of adding a new event.
//
// Remove the event from the queue
removeEvent(pAnimEvent);
// Update the event time
pAnimEvent->m_ulEventTime = pAnimate->m_ulDelay;
// Re-insert into the queue with the new time
insertEvent(pAnimEvent);
}
else
{
// We have NOT already scheduled an event
// for this animate element
//
// Schedule the begin animation event
UINT16 usGroupIndexShifted = m_usAnimBaseGroupIndex + pAnimate->m_pNode->m_nGroup;
CSmilAnimateEvent* pEvent = new CSmilAnimateEvent(usGroupIndexShifted,
pAnimate->m_ulDelay,
FALSE,
pAnimate,
this,
m_pSmilParser);
if (pEvent)
{
// Put the event only the timeline
insertEvent(pEvent);
}
}
}
else
{
retVal = HXR_FAIL;
}
return retVal;
}
#endif /* #if defined(HELIX_FEATURE_SMIL2_ANIMATION) */
HX_RESULT CSmilDocumentRenderer::handleRemoveTimeUpdate(CSmilElement* pElement,
UINT32 ulRemoveTime)
{
MLOG_EVENT(m_pErrorMessages,
"handleRemoveTimeUpdate(0x%08x,%lu)\n\tmediaID=%s\n\ttick=%lu\n",
pElement, ulRemoveTime,
(const char*) pElement->m_pNode->m_id,
HX_GET_BETTERTICKCOUNT());
HX_RESULT retVal = HXR_OK;
if (pElement && pElement->m_pNode &&
m_pEventList && m_pEventList->GetCount() > 0)
{
// Search through the event queue to find
// the hide event for this element.
CHXSimpleList cTmp;
const char* pszID = (const char*) pElement->m_pNode->m_id;
LISTPOSITION pos = m_pEventList->GetHeadPosition();
while (pos)
{
BOOL bRemoved = FALSE;
CSmilLayoutEvent* pListEvent = (CSmilLayoutEvent*) m_pEventList->GetAt(pos);
if (pListEvent && pListEvent->m_type == CSmilLayoutEvent::eHideSite)
{
CSmilShowSiteEvent* pListHide = (CSmilShowSiteEvent*) pListEvent;
if (!strcmp(pszID, pListHide->getMediaID()) &&
pListHide->m_ulEventTime != ulRemoveTime)
{
MLOG_EVENT(m_pErrorMessages,
"\tRemoving event from list (%s,%lu,%u,%lu,%lu,%s,%s) tick=%lu\n",
pListHide->getEventTypeName(),
pListHide->m_ulEventTime,
pListHide->m_uGroupIndex,
pListHide->m_bOnlyHideSite,
pListHide->m_bIgnorEvent,
pListHide->getMediaID(),
pListHide->getRegionID(),
HX_GET_BETTERTICKCOUNT());
// Remove the event from the list
pos = m_pEventList->RemoveAt(pos);
// Set the flag
bRemoved = TRUE;
// Save onto the temporary list
cTmp.AddTail((void*) pListHide);
}
}
if (!bRemoved)
{
m_pEventList->GetNext(pos);
}
}
// Did we remove any events?
if (cTmp.GetCount() > 0)
{
// Loop through the removed events
pos = cTmp.GetHeadPosition();
while (pos)
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -