📄 sm1doc.cpp
字号:
pRegion->m_rect.left = cPos.x;
pRegion->m_rect.top = cPos.y;
pRegion->m_rect.right = cPos.x + cSize.cx;
pRegion->m_rect.bottom = cPos.y + cSize.cy;
CHXxRect updateRect(0, 0, cSize.cx, cSize.cy);
pRegion->m_pSite->DamageRect(updateRect);
#ifndef _WIN32
pRegion->m_pSite->ForceRedraw();
#endif
}
}
void
CSmil1DocumentRenderer::resizeSite(HXxSize newSize)
{
double dXScale = 1.0;
double dYScale = 1.0;
if(newSize.cx > 0 &&
newSize.cy > 0 &&
m_topSiteSize.cx > 0 &&
m_topSiteSize.cy > 0)
{
dXScale = (double)newSize.cx / (double)m_topSiteSize.cx;
dYScale = (double)newSize.cy / (double)m_topSiteSize.cy;
}
double dXAbsScale = 1.0;
double dYAbsScale = 1.0;
if (m_topSiteOriginalSize.cx > 0 &&
m_topSiteOriginalSize.cy > 0)
{
dXAbsScale = (double) newSize.cx / (double) m_topSiteOriginalSize.cx;
dYAbsScale = (double) newSize.cy / (double) m_topSiteOriginalSize.cy;
}
m_topSiteSize.cx = newSize.cx;
m_topSiteSize.cy = newSize.cy;
BOOL bSetOriginalSize = FALSE;
if(m_topSiteSize.cx == m_topSiteOriginalSize.cx &&
m_topSiteSize.cy == m_topSiteOriginalSize.cy)
{
bSetOriginalSize = TRUE;
m_dResizeXScale = 1.0;
m_dResizeYScale = 1.0;
}
else
{
m_dResizeXScale = dXScale;
m_dResizeYScale = dYScale;
}
if(m_pRegionMap)
{
// scale regions
CHXMapStringToOb::Iterator i = m_pRegionMap->Begin();
for(; i != m_pRegionMap->End(); ++i)
{
BOOL bAbs = FALSE;
CSmil1BasicRegion* pRegion = (CSmil1BasicRegion*)(*i);
if ((m_bRootLayoutWidthSet || m_ulNoRootLayoutWidth) &&
(m_bRootLayoutHeightSet || m_ulNoRootLayoutHeight) &&
!pRegion->m_bWidthUnspecified &&
!pRegion->m_bHeightUnspecified)
{
bAbs = TRUE;
// char szDbgStr[128];
// DEBUGPRINTF(szDbgStr, "region %s abs resizing to ", (const char*) pRegion->m_region);
resizeRegionSiteAbs(pRegion, dXAbsScale, dYAbsScale);
}
else
{
// char szDbgStr[128];
// DEBUGPRINTF(szDbgStr, "region %s resizing to ", (const char*) pRegion->m_region);
resizeSite(pRegion->m_pSite, dXScale, dYScale);
}
SMIL1PlayToAssoc* pAssoc = getPlayToAssoc(pRegion->m_region);
if(bSetOriginalSize)
{
pRegion->m_rect = pRegion->m_originalRect;
//Helps fix PR 11265:
pRegion->m_mediaSize.cx = pRegion->m_originalMediaSize.cx;
pRegion->m_mediaSize.cy = pRegion->m_originalMediaSize.cy;
if(pAssoc && pAssoc->m_pHyperlinks)
{
CHXSimpleList::Iterator i = pAssoc->m_pHyperlinks->Begin();
for(; i != pAssoc->m_pHyperlinks->End(); ++i)
{
CSmil1AAnchorElement* pAnchor =
(CSmil1AAnchorElement*)(*i);
pAnchor->rescale(0.0, 0.0, TRUE); // set to original coords
}
}
}
else
{
if (!bAbs)
{
// Fix for PR 17415
// dXScale & dYScale are reletive to the current size,
UINT32 ulNewLeft = (INT32)(dXScale *
(double)(pRegion->m_rect.left) + 0.5);
UINT32 ulNewTop = (INT32)(dYScale *
(double)(pRegion->m_rect.top) + 0.5);
UINT32 ulNewWidth = (INT32)(dXScale *
(double)(pRegion->m_rect.right -
pRegion->m_rect.left) + 0.5);
UINT32 ulNewHeight = (INT32)(dYScale *
(double)(pRegion->m_rect.bottom -
pRegion->m_rect.top) + 0.5);
pRegion->m_rect.left = ulNewLeft;
pRegion->m_rect.top = ulNewTop;
pRegion->m_rect.right = ulNewLeft + ulNewWidth;
pRegion->m_rect.bottom = ulNewTop + ulNewHeight;
//Fixes PR 11265:
pRegion->m_mediaSize.cx = ulNewWidth;
pRegion->m_mediaSize.cy = ulNewHeight;
}
if(pAssoc && pAssoc->m_pHyperlinks)
{
CHXSimpleList::Iterator i = pAssoc->m_pHyperlinks->Begin();
for(; i != pAssoc->m_pHyperlinks->End(); ++i)
{
CSmil1AAnchorElement* pAnchor =
(CSmil1AAnchorElement*)(*i);
pAnchor->rescale(dXScale, dYScale, FALSE);
}
}
}
}
}
if(m_pSiteInfoList)
{
// scale current renderer sites
CHXSimpleList::Iterator i = m_pSiteInfoList->Begin();
for(; i != m_pSiteInfoList->End(); ++i)
{
SMIL1SiteInfo* pSiteInfo = (SMIL1SiteInfo*)(*i);
// char szDbgStr[128];
// DEBUGPRINTF(szDbgStr, "media in region %s resizing to ",
// (const char*) pSiteInfo->m_regionID);
// See if we can look up a region
CSmil1BasicRegion* pReg = getRegion((const char*) pSiteInfo->m_regionID);
if (pReg)
{
// Compute the media layout at original scale
HXxSize cOrigRegSize = {0, 0};
cOrigRegSize.cx = HXxRECT_WIDTH(pReg->m_originalRect);
cOrigRegSize.cy = HXxRECT_HEIGHT(pReg->m_originalRect);
HXxSize cFitSize = pReg->m_originalMediaSize;
computeMediaFitSize(cOrigRegSize, pReg->m_originalMediaSize,
pReg->m_fit, cFitSize);
// Now scale the original media size
HXxSize cScaledFitSize = {0, 0};
cScaledFitSize.cx = (INT32) ((double) cFitSize.cx * dXAbsScale + 0.5);
cScaledFitSize.cy = (INT32) ((double) cFitSize.cy * dYAbsScale + 0.5);
// Get the site watcher
CSmil1SiteWatcher* pSW = NULL;
if(m_pSiteWatcherMap)
{
void* pVoid = NULL;
if (m_pSiteWatcherMap->Lookup(pSiteInfo->m_pRendererSite, pVoid))
{
pSW = (CSmil1SiteWatcher*) pVoid;
}
}
// Set the "disable" flag in the site watcher
if (pSW) pSW->SiteChangingSize(TRUE);
// Set the size
// DEBUGPRINTF(szDbgStr, "(%ld,%ld)\n", cScaledFitSize.cx, cScaledFitSize.cy);
if(pSiteInfo && pSiteInfo->m_pRendererSite)
pSiteInfo->m_pRendererSite->SetSize(cScaledFitSize);
// Clear the "disable" flag in the site watcher
if (pSW) pSW->SiteChangingSize(FALSE);
}
else
{
// Do what we normally do
resizeSite(pSiteInfo->m_pRendererSite, dXScale, dYScale);
}
}
}
}
HX_RESULT
CSmil1DocumentRenderer::onTimeSync(UINT32 ulTimeValue)
{
// char szDbgStr[128];
// DEBUGPRINTF(szDbgStr, "onTimeSync(%lu)\n", ulTimeValue);
HX_RESULT rc = HXR_OK;
m_ulCurrentTime = ulTimeValue;
if(!m_bFirstTimeSync)
{
// draw background and regions
m_bFirstTimeSync = TRUE;
// now I should force a background redraw...
if(m_pMISUSSite)
{
HXxSize siteWinSize;
m_pMISUSSite->GetSize(siteWinSize);
CHXxRect updateRect(0, 0, siteWinSize.cx, siteWinSize.cy);
m_pMISUSSite->DamageRect(updateRect);
m_pMISUSSite->ForceRedraw();
if(m_pRegionMap)
{
CHXMapStringToOb::Iterator i = m_pRegionMap->Begin();
for(; i != m_pRegionMap->End(); ++i)
{
CSmil1BasicRegion* pRegion = (CSmil1BasicRegion*)(*i);
if(pRegion->m_pSite)
{
pRegion->m_pSite->GetSize(siteWinSize);
CHXxRect siteRect(0, 0, siteWinSize.cx, siteWinSize.cy);
pRegion->m_pSite->DamageRect(siteRect);
pRegion->m_pSite->ForceRedraw();
}
}
}
}
}
rc = flushAllEvents( ulTimeValue, TRUE );
return rc;
}
void
CSmil1DocumentRenderer::RemoveEvents(UINT32 ulGroupIndex, IHXSite* pSite)
{
// handle all events up to time ulFlushToTime + ulGranularity
HX_RESULT rc = HXR_OK;
if(m_pEventList)
{
LISTPOSITION lPos = m_pEventList->GetHeadPosition();
while(lPos && m_pEventList->GetCount())
{
// handle all events at or before ulTimeValue
CSmil1ShowSiteEvent* pEvent = (CSmil1ShowSiteEvent*)m_pEventList->GetAt(lPos);
if(pEvent->m_uGroupIndex == ulGroupIndex &&
pEvent->getRendererSite() == pSite)
{
HX_DELETE(pEvent);
lPos = m_pEventList->RemoveAt(lPos);
}
else
{
m_pEventList->GetNext(lPos);
}
}
// set list position member
m_ulEventListPosition = m_pEventList->GetHeadPosition();
}
return;
}
HX_RESULT CSmil1DocumentRenderer::flushAllEvents( UINT32 ulFlushToTime, BOOL bBreak)
{
// handle all events up to time ulFlushToTime + ulGranularity
HX_RESULT rc = HXR_OK;
if(m_pEventList && m_pEventList->GetCount() > 0)
{
//LISTPOSITION lPos = m_pEventList->GetHeadPosition();
while(m_ulEventListPosition)
{
// handle events which have eventTime<=ulFlushToTime+ulGranularity
CSmil1LayoutEvent* pEvent
= (CSmil1LayoutEvent*) m_pEventList->GetAt(m_ulEventListPosition);
//{FILE* f1 = ::fopen("c:\\temp\\out.txt", "a+"); ::fprintf(f1, "Flush Events pEvent=%lu\n", pEvent);::fclose(f1);}
#ifdef _MACINTOSH
// XXXBobClark:
// On the Mac side, our site's ShowSite implementation
// draws synchronously: right then. On Windows, it draws
// asynchronously by setting up a callback. The upshot is
// that on Windows you can get away with a ShowSite(TRUE)
// followed immediately by a ShowSite(FALSE), because the
// actual screen won't get updated while the site is
// briefly visible. But on the Mac it will show a visible
// flicker. So the interim workaround here is to check the
// events we're flushing; if we're showing a site that will
// be hidden by the time the flush is done (or vice versa),
// we ignore that event.
LISTPOSITION tempPos = m_ulEventListPosition;
BOOL bCurrentEventCancelledOutByFutureEvent = FALSE;
CSmil1ShowSiteEvent* pCurrentEvent = (CSmil1ShowSiteEvent*)pEvent;
m_pEventList->GetNext(tempPos); // to start with the next position...
while (tempPos)
{
CSmil1ShowSiteEvent* pFutureEvent = (CSmil1ShowSiteEvent*)m_pEventList->GetAt(tempPos);
if ( !pFutureEvent
|| pFutureEvent->m_ulEventTime > ulFlushToTime)
{
break;
}
if ( pFutureEvent && pCurrentEvent
&& pCurrentEvent->m_pSite == pFutureEvent->m_pSite
&& pCurrentEvent->m_pRegionSite == pFutureEvent->m_pRegionSite
&& pCurrentEvent->m_bShowSite != pFutureEvent->m_bShowSite )
{
bCurrentEventCancelledOutByFutureEvent = TRUE;
break;
}
m_pEventList->GetNext(tempPos);
}
#endif
// no need of granularity since the core will
// ensure we call OnTimeSync at the end of its duration
if (pEvent &&
pEvent->m_ulEventTime <= ulFlushToTime)
{
#ifdef _MACINTOSH
if (!bCurrentEventCancelledOutByFutureEvent)
#endif
rc = pEvent->handleEvent();
//lPos = m_pEventList->RemoveAt(lPos);
}
else if( bBreak )
{
break;
}
m_pEventList->GetNext(m_ulEventListPosition);
}
}
return rc;
}
BOOL
CSmil1DocumentRenderer::IsFullScreen()
{
BOOL bRet = FALSE;
if (m_pMISUSSite)
{
IHXSiteFullScreen* pFull = NULL;
m_pMISUSSite->QueryInterface(IID_IHXSiteFullScreen, (void**) &pFull);
if (pFull)
{
bRet = pFull->IsFullScreen();
}
HX_RELEASE(pFull);
}
return bRet;
}
void CSmil1DocumentRenderer::computeMediaFitSize(HXxSize cRegSize,
HXxSize cMedSize,
const char* pszFitAttr,
REF(HXxSize) rcFitSize)
{
UINT32 ulFit = 0; // 0=hidden, 1=fill, 2=meet, 3=slice, 4=scroll
if (pszFitAttr)
{
if (!strcmp(pszFitAttr, "hidden"))
{
ulFit = 0;
}
else if (!strcmp(pszFitAttr, "fill"))
{
ulFit = 1;
}
else if (!strcmp(pszFitAttr, "meet"))
{
ulFit = 2;
}
else if (!strcmp(pszFitAttr, "slice"))
{
ulFit = 3;
}
else if (!strcmp(pszFitAttr, "scroll"))
{
ulFit = 4;
}
}
switch (ulFit)
{
case 0:
{
// fit="hidden"
rcFitSize = cMedSize;
}
break;
case 1:
{
// fit="fill"
rcFitSize = cRegSize;
}
break;
case 2:
{
// fit="meet"
double dMedAspectRatio = 1.0;
if(cMedSize.cx != 0 && cMedSize.cy != 0)
{
dMedAspectRatio = (double) cMedSize.cx / (double) cMedSize.cy;
}
INT32 lTryHeight = (INT32)((double) cRegSize.cx / dMedAspectRatio + 0.5);
if(lTryHeight > cRegSize.cy)
{
rcFitSize.cx = (INT32) ((double) cRegSize.cy * dMedAspectRatio + 0.5);
rcFitSize.cy = cRegSize.cy;
}
else
{
rcFitSize.cx = cRegSize.cx;
rcFitSize.cy = lTryHeight;
}
}
break;
case 3:
{
// fit="slice"
double dMedAspectRatio = 1.0;
if(cMedSize.cx != 0 && cMedSize.cy != 0)
{
dMedAspectRatio = (double) cMedSize.cx / (double) cMedSize.cy;
}
double dRegAspectRatio = 1.0;
if (cRegSize.cx != 0 && cRegSize.cy != 0)
{
dRegAspectRatio = (double) cRegSize.cx / (double) cRegSize.cy;
}
// fit to greater of region height or width
if(dRegAspectRatio > dMedAspectRatio)
{
rcFitSize.cx = cRegSize.cx;
rcFitSize.cy = (INT32)((double) cRegSize.cx / dMedAspectRatio + 0.5);
}
else
{
rcFitSize.cx = (INT32)((double) cRegSize.cy * dMedAspectRatio + 0.5);
rcFitSize.cy = cRegSize.cy;
}
}
break;
case 4:
{
// fit="scroll"
rcFitSize = cMedSize;
}
break;
}
}
HX_RESULT CSmil1DocumentRenderer::getPreference(IUnknown* pContext,
const char* pszKey,
REF(IHXBuffer*) rpValue)
{
HX_RESULT retVal = HXR_FAIL;
if (pContext && pszKey)
{
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -