📄 scene.c
字号:
*****************************************************************************/
void TAFinish(LPD3DM_CONTEXT psContext, PVRSRV_DEV_INFO *psDevInfo)
{
D3DM_DPF((DPF_MESSAGE, "TAFinish: Finishing scene"));
PDUMPSTRING(psContext->psPDContext, " \r\n");
PDUMPSTRING(psContext->psPDContext, "---- Finishing scene");
PROFILE_START_FUNC(TA_STOP);
/* Acquire TA and Slave port */
if(D3DMAcquireTAResources(psContext, FALSE) != PVRSRV_OK)
{
/* Scene is invalidated */
goto exit;
}
/* Terminate the TA control-stream */
TACSWriteEndStream(psContext);
exit:
/*
Release TA and Slaveport we need to do this even if the scene
is invalid and we've stopped sending geometry
*/
D3DMReleaseTAResources(psContext, TRUE);
/*
Data should now have been processed, so we can reset the
data sent flag
*/
psContext->psCurrentRenderTarget->sDescription.sSurface.bSceneTADataSent = FALSE;
PROFILE_STOP_FUNC(TA_STOP);
}
/*****************************************************************************
FUNCTION : DoBeginScene
PURPOSE : Processing required to start a new scene
PARAMETERS : psContext - A 3D-rendering context
RETURNS : void
*****************************************************************************/
void DoBeginScene(LPD3DM_CONTEXT psContext)
{
LPD3DM_SURFACE psRenderTarget;
PROFILE_START_FUNC(DO_BEGIN_SCENE);
D3DM_DPF((DPF_MESSAGE, "DoBeginScene"));
psRenderTarget = psContext->psCurrentRenderTarget;
/* Allocate Z buffer if required */
if(psRenderTarget->sDescription.sSurface.psTARenderInfo->psSharedData->bAllocateDepthbuffer &&
psContext->psCurrentDepthBuffer && psContext->psCurrentDepthBuffer->psMemInfo == NULL)
{
/* Allocate the Z-Buffer mem info now */
ZLSAlloc(psContext);
}
/* Set the current frame number for parameter-capture */
PDUMPUPDATEFRAME(psContext->psPDContext);
/* No change in LOD bias for this scene yet */
psContext->dwFlags &= ~D3DM_CONTEXT_SWFLAGS_LOD_BIAS_IN_SCENE;
#if defined(PDUMP)
/* Force all HW-state to be resubmitted before the next primitive */
ResubmitHWState(psContext);
#endif /* #if defined(PDUMP) */
/*
Set Fog Colour registers to whatever
current D3D renderstate is set to.
(Because any extra multiple fog clr changes per scene
will have been sent as special Fog Clear Objects.)
*/
psContext->ps3DRegs[D3DM_SW3DREG_FOGCOLVERT].ui32RegVal = psContext->sTState.dwVertexFogColour;
psContext->sTState.dwLastSentVertexFogColour = psContext->sTState.dwVertexFogColour;
/* Reset number of fog colour changes we've done this scene */
psContext->sTState.dwFogChangeCount = 0;
PROFILE_START_SCENE();
/*
Queue the render for this scene - It wont happen
till the TA has completed for this scene
*/
D3DMQueueRender(psContext, D3DM_SW3DREG_COUNT, psContext->ps3DRegs);
/*
Start the TA so we can begin sending data
*/
TAStart(psContext);
#if defined (SUPPORT_VGP) || defined (SUPPORT_VGP_LITE)
UpdateVGPConstants(psContext);
#endif
/*
Ensure that current viewport ISP clip mask
objects are sent at start of every frame
*/
SetViewPort(psContext, &psContext->sTState.sViewPortRect);
/*
Send background object, to ensure ISP depth & colour
is correct for every rendersurface pixel.
*/
SendBackgroundObject(psContext);
/* Record that a scene has been started on the current render-target */
psRenderTarget->dwFlags |= D3DM_SURFACE_FLAGS_SCENE_STARTED;
PROFILE_STOP_FUNC(DO_BEGIN_SCENE);
}
/*****************************************************************************
FUNCTION : DoMidScene
PURPOSE : Renders a partial scene and stores z info
PARAMETERS : psContext - A 3D-rendering context
RETURNS : none
*****************************************************************************/
void DoMidScene(LPD3DM_CONTEXT psContext)
{
LPD3DM_SURFACE psRenderTarget = psContext->psCurrentRenderTarget;
IMG_BOOL bModifyRequired = IMG_FALSE;
PROFILE_START_FUNC(DO_MID_SCENE);
/* Allocate Z buffer if required */
if(psContext->psCurrentDepthBuffer && psContext->psCurrentDepthBuffer->psMemInfo == IMG_NULL)
{
/* Allocate the Z-Buffer mem info now */
ZLSAlloc(psContext);
bModifyRequired = IMG_TRUE;
}
/* Set up modify registers if required */
if(bModifyRequired)
{
SetupMidSceneModifyRegs(psContext);
}
/* Finish the scene */
TAFinish(psContext, GetDevInfo(psContext));
PROFILE_STOP_SCENE();
PROFILE_STOP_FUNC(DO_MID_SCENE);
}
/*****************************************************************************
FUNCTION : DoEndScene
PURPOSE : Renders a scene and updates state and flags accordingly
PARAMETERS : psContext - A 3D-rendering context
RETURNS : none
*****************************************************************************/
void DoEndScene(LPD3DM_CONTEXT psContext)
{
LPD3DM_SURFACE psRenderTarget;
PVRSRV_DEV_INFO *psDevInfo;
PVR3DIF_SHAREDDATA *ps3DIFSharedData;
PROFILE_START_FUNC(DO_END_SCENE);
psRenderTarget = psContext->psCurrentRenderTarget;
ps3DIFSharedData = psRenderTarget->sDescription.sSurface.psTARenderInfo->psSharedData;
psDevInfo = GetDevInfo(psContext);
if(!psRenderTarget)
{
D3DM_DPF((DPF_MESSAGE, "DoEndScene: No render-target"));
return;
}
/*
For parameter-dumping purposes, write out all the textures
referenced
*/
PDUMPFLUSHTEXLIST(psContext->psPDContext);
/* Finish the scene */
TAFinish(psContext, psDevInfo);
PROFILE_STOP_SCENE();
#ifdef PDUMP
/* Wait for TA idle */
if(PollForValue ((IMG_UINT32*)&GetDevInfo(psContext)->sDeviceSpecific.s3D.bTAIdle,
TRUE,
0xFFFFFFFF,
MAX_HW_TIME_US/WAIT_TRY_COUNT,
WAIT_TRY_COUNT) != PVRSRV_OK)
{
D3DM_DPF((DPF_MESSAGE, "Wait for TA poll failed after 1s"));
}
/* wait for 3Dcomplete ISR */
if(PollForValue ((IMG_UINT32*)&ps3DIFSharedData->aui32ContextStatus[ps3DIFSharedData->ui32CurrentRenderData],
PVR3DIF_3DCTL_FREE,
0xFFFFFFFF,
MAX_HW_TIME_US/WAIT_TRY_COUNT,
WAIT_TRY_COUNT) != PVRSRV_OK)
{
D3DM_DPF((DPF_MESSAGE, "Wait for 3D poll failed after 1s"));
}
#endif // PDUMP
/* PDump 3D regs */
PDUMPREG(psContext->psPDContext, PDUMPTAGS_REG_MBX, MBX1_GLOBREG_3D_RENDER_ID, ps3DIFSharedData->aui32HWContextID[ps3DIFSharedData->ui32CurrentRenderData]);
PDUMPREGARRAY(psContext->psPDContext, PDUMPTAGS_REG_MBX, psContext->ps3DRegs, D3DM_SW3DREG_COUNT);
#if 0//FIXME: defined(DEBUG)
/*
Decode the region headers
*/
//if (dwDBGFlags & DBGFLAG_SCENE_DECODE3DPARAMS)
{
DBGDecode3DParams(psContext, psDevInfo);
}
//if (dwDBGFlags & DBGFLAG_SCENE_DUMPPOSTTAPARAMS)
{
DBGDump3DParams(psContext, psDevInfo);
}
#endif /* #if defined(DEBUG) */
/* Update the context, resetting the flags and frame counter */
psContext->dwFrame++;
PDUMPUPDATEFRAME(psContext->psPDContext);
/* Reset TA data and SURFDATA flags */
psRenderTarget->dwFlags &= ~D3DM_SURFACE_FLAGS_SCENE_STARTED;
PROFILE_STOP_FUNC(DO_END_SCENE);
}
/*****************************************************************************
FUNCTION : FlushGeometryOnSurface
PURPOSE : Does a mid scene render if required
PARAMETERS : psContext - A 3D-rendering context
RETURNS : none
*****************************************************************************/
IMG_VOID FlushGeometryOnSurface(LPD3DM_SURFACE psTarget)
{
LPD3DM_CONTEXT psContext = psTarget->psContext;
PROFILE_START_FUNC(FLUSH_GEOMETRY_ON_SURFACE);
if((psTarget->dwUsage & D3DMUSAGE_RENDERTARGET) &&
((psTarget->sDescription.sSurface.bSceneTADataSent == IMG_TRUE) ||
(psTarget->sDescription.sSurface.dwClearFlags & D3DM_SURFACE_CLEARFLAGS_FULLSCREEN_DEPTH) ||
(psTarget->sDescription.sSurface.dwClearFlags & D3DM_SURFACE_CLEARFLAGS_FULLSCREEN_TARGET)))
{
/*
We're trying to perform a blit or lock to the render target.
Flush all outstanding geometry if required.
*/
if(psTarget == psContext->psCurrentRenderTarget)
{
DoMidScene(psTarget->psContext);
}
else
{
LPD3DM_SURFACE psCurrentRenderTarget = psContext->psCurrentRenderTarget;
/* Target surface has outstanding geometry, but is not the current RT */
SetRenderTarget(psContext,
psTarget,
psTarget->sDescription.sSurface.psAssocDepthSurface,
IMG_TRUE);
/* Do mid scene */
DoMidScene(psTarget->psContext);
/* replace current render target */
SetRenderTarget(psContext,
psCurrentRenderTarget,
psCurrentRenderTarget->sDescription.sSurface.psAssocDepthSurface,
IMG_TRUE);
}
}
PROFILE_STOP_FUNC(FLUSH_GEOMETRY_ON_SURFACE);
}
/*****************************************************************************
End of file (scene.c)
*****************************************************************************/
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -