📄 prim.c
字号:
/**********************
Depth bias
**********************/
if(psContext->sTState.dwRSFlags & TSTATE_RSFLAGS_DEPTHBIAS)
{
/* Calculate value of m */
NTV_TYPE ntvNewDepthM = TriangleMaxDepthSlope(apsVertex[0]);
/* if m is different from previous m then calculate depth bias offset */
if(ntvNewDepthM != ntvDepthM)
{
CalculateDepthBias(psContext,ntvNewDepthM);
ntvDepthM = ntvNewDepthM;
}
}
/* any vertices clipped? */
ui32ClipCode = (apsVertex[0]->ui32Flags
| apsVertex[1]->ui32Flags
| apsVertex[2]->ui32Flags) & D3DM_CLIPFLAG_MASK;
if (ui32ClipCode == 0) /* no clipping: */
{
if(bNewFan)
{
if (ui32NumFans)
{
TACSWriteEndPrim(psContext);
}
else
{
TACSWritePrimHdr(psContext, psContext->dwTAPrimCtl, MBX1_TAOBJTYPE_VERTEXLINESTRIP);
TACSWriteLinePointSize(psContext, 0x3F000000/*0.5*/);
}
ui32NumFans++;
ValidateVertex(psContext, &apsVertex[0], 3);
OutputVertices(psContext, &apsVertex[0], 4);
bNewFan = IMG_FALSE;
}
else
{
/* draw segments 1->2, 2->0 */
ValidateVertex(psContext, &apsVertex[2], 1);
OutputVertices(psContext, &apsVertex[1], 3);
}
}
else if (!( apsVertex[0]->ui32Flags
& apsVertex[1]->ui32Flags
& apsVertex[2]->ui32Flags & D3DM_CLIPFLAG_MASK))
{
ValidateVertex(psContext, &apsVertex[0], 3);
/* go through segments */
for (j=0; j<3; j++)
{
ui32NumVerts = DoLineClip(psContext, apsVertex[j], apsVertex[j+1], ui32ClipCode);
if(ui32NumVerts)
{
if (ui32NumFans)
{
TACSWriteEndPrim(psContext);
}
else
{
/* Start a new primitive block */
TACSWritePrimHdr(psContext, psContext->dwTAPrimCtl, MBX1_TAOBJTYPE_VERTEXLINESTRIP);
TACSWriteLinePointSize(psContext, 0x3F000000/*0.5*/);
}
ui32NumFans++;
ppsVertex = psContext->sTState.sSWTNLState.ppsOutputArray;
OutputVertices(psContext, ppsVertex, ui32NumVerts);
}
}
bNewFan = IMG_TRUE;
}
else
{
bNewFan = IMG_TRUE;
}
/* advance vertices */
psVTmp = apsVertex[1];
apsVertex[1] = apsVertex[2];
apsVertex[2] = psVTmp;
}
/*
Finish the primitive block
*/
if(ui32NumFans)
{
TACSWriteLastPrim(psContext);
#ifdef FIX_HW_PRN_299
TACSWriteTACtlAnd3DState ( psContext,
MBX1_TASTATEPRES_ISPCTL,
&psContext->sHWState.sTACtl3DState,
TRUE);
#endif
}
}
/***********************************************************************************
Function Name : TriFanLine
************************************************************************************/
IMG_VOID TriangleFan(LPD3DM_CONTEXT psContext,
IMG_UINT32 *pui32Data,
IMG_UINT32 ui32FVFcode,
IMG_UINT32 ui32Stride,
IMG_UINT32 ui32PrimCount)
{
IMG_UINT32 i;
PVR_NATIVE_VERTEX asVertex[3], *apsVertex[3], *psVTmp, **ppsVertex;
IMG_UINT32 ui32ClipCode;
IMG_BOOL bNewFan = IMG_TRUE;
IMG_UINT32 ui32NumFans = 0;
IMG_INT32 i32NumVerts/*, j*/;
NTV_TYPE ntvDepthM = D3DM_Zero;
/* initialise the vertex ptr array */
apsVertex[0] = &asVertex[0];
apsVertex[1] = &asVertex[1];
apsVertex[2] = &asVertex[2];
/* and quarter index stride for dword ptr arithmetic */
ui32Stride >>= 2;
/* construct native vertices */
SetupNativeVertex(psContext, pui32Data, ui32FVFcode, apsVertex[0]);
pui32Data += ui32Stride;
SetupNativeVertex(psContext, pui32Data, ui32FVFcode, apsVertex[1]);
pui32Data += ui32Stride;
/************************
first time clip test
************************/
DoClipTestandVPTransform(psContext, &apsVertex[0], 2);
for(i=0; i<ui32PrimCount; i++)
{
IMG_BOOL bPassCullTest;
IMG_BOOL bIsCounterClockWise;
SetupNativeVertex(psContext, pui32Data, ui32FVFcode, apsVertex[2]);
pui32Data += ui32Stride;
/* Store pointers to colours for flat shading */
psContext->sTState.sSWTNLState.psCurrentFlatShadeDiffuse = &apsVertex[1]->sDiffuseOut;
psContext->sTState.sSWTNLState.psCurrentFlatShadeSpecular = &apsVertex[1]->sSpecularOut;
/**********************
clip test
**********************/
DoClipTestandVPTransform(psContext, &apsVertex[2], 1);
/**********************
Depth bias
**********************/
if(psContext->sTState.dwRSFlags & TSTATE_RSFLAGS_DEPTHBIAS)
{
/* Calculate value of m */
NTV_TYPE ntvNewDepthM = TriangleMaxDepthSlope(apsVertex[0]);
/* if m is different from previous m then calculate depth bias offset */
if(ntvNewDepthM != ntvDepthM)
{
CalculateDepthBias(psContext,ntvNewDepthM);
ntvDepthM = ntvNewDepthM;
}
}
/* any vertices clipped? */
ui32ClipCode = (apsVertex[0]->ui32Flags
| apsVertex[1]->ui32Flags
| apsVertex[2]->ui32Flags) & D3DM_CLIPFLAG_MASK;
if ((ui32ClipCode & D3DM_CLIPFLAG_NEAR) == 0)
{
/* Check cull status */
bIsCounterClockWise = IsCounterClockWise(&apsVertex[0]);
switch(psContext->dwTAPrimCtl & MBX1_TAPRIM_CULLMODEMASK)
{
case MBX1_TAPRIM_CULLMODENONE:
bPassCullTest = IMG_TRUE;
break;
case MBX1_TAPRIM_CULLMODECW:
bPassCullTest = bIsCounterClockWise;
break;
case MBX1_TAPRIM_CULLMODECCW:
bPassCullTest = !bIsCounterClockWise;
break;
default:
///error
break;
}
}
else
{
bPassCullTest = IMG_TRUE;
}
if(!bPassCullTest)
{
bNewFan = IMG_TRUE;
}
else if(ui32ClipCode == 0) /* no clipping: */
{
if(bNewFan)
{
if(ui32NumFans)
{
TACSWriteEndPrim(psContext);
}
else
{
TACSWritePrimHdr(psContext, psContext->dwTAPrimCtl, MBX1_TAOBJTYPE_VERTEXFACEFAN);
}
ui32NumFans++;
ValidateVertex(psContext, &apsVertex[0], 3);
OutputVertices(psContext, &apsVertex[0], 3);
bNewFan = IMG_FALSE;
}
else
{
ValidateVertex(psContext, &apsVertex[2], 1);
OutputVertices(psContext, &apsVertex[2], 1);
}
}
else if (!( apsVertex[0]->ui32Flags
& apsVertex[1]->ui32Flags
& apsVertex[2]->ui32Flags & D3DM_CLIPFLAG_MASK))
{
ValidateVertex(psContext, &apsVertex[0], 3);
i32NumVerts = DoPolygonClip(psContext, &apsVertex[0], 3, ui32ClipCode);
ppsVertex = psContext->sTState.sSWTNLState.ppsOutputArray;
if(ui32NumFans)
{
TACSWriteEndPrim(psContext);
}
else
{
TACSWritePrimHdr(psContext, psContext->dwTAPrimCtl, MBX1_TAOBJTYPE_VERTEXFACEFAN);
}
ui32NumFans++;
OutputVertices(psContext, ppsVertex, i32NumVerts);
bNewFan = IMG_TRUE;
}
else
{
bNewFan = IMG_TRUE;
}
/* advance vertices, leaving first one as is */
psVTmp = apsVertex[1];
apsVertex[1] = apsVertex[2];
apsVertex[2] = psVTmp;
}
/*
Finish the primitive block
*/
if(ui32NumFans)
{
TACSWriteLastPrim(psContext);
}
}
/***********************************************************************************
Function Name : PointList
************************************************************************************/
IMG_VOID PointList( LPD3DM_CONTEXT psContext,
IMG_UINT32 *pui32Data,
IMG_UINT32 ui32FVFcode,
IMG_UINT32 ui32Stride,
IMG_UINT32 ui32PrimCount)
{
IMG_UINT32 i;
PVR_NATIVE_VERTEX asVertex[1], *apsVertex[1];
IMG_UINT32 ui32ClipCode;
IMG_BOOL bStartPrimitive = IMG_TRUE;
/* adjust for non-point types in point fill mode */
if(psContext->ePrimFillMode == PRIM_FILLMODE_POINT)
{
switch(psContext->eCurrentPrimType)
{
case D3DMPT_TRIANGLELIST:
ui32PrimCount *= 3;
break;
case D3DMPT_TRIANGLESTRIP:
case D3DMPT_TRIANGLEFAN:
ui32PrimCount += 2;
break;
case D3DMPT_LINELIST:
ui32PrimCount *= 2;
break;
case D3DMPT_LINESTRIP:
ui32PrimCount += 1;
break;
case D3DMPT_POINTLIST:
default:
break;
}
}
/* initialise the vertex ptr array */
apsVertex[0] = &asVertex[0];
/* and quarter index stride for dword ptr arithmetic */
ui32Stride >>= 2;
for(i=0; i<ui32PrimCount; i++)
{
SetupNativeVertex(psContext, pui32Data, ui32FVFcode, apsVertex[0]);
pui32Data += ui32Stride;
/* Store pointers to colours for flat shading */
psContext->sTState.sSWTNLState.psCurrentFlatShadeDiffuse = &apsVertex[0]->sDiffuseOut;
psContext->sTState.sSWTNLState.psCurrentFlatShadeSpecular = &apsVertex[0]->sSpecularOut;
/**********************
clip test
**********************/
DoClipTestandVPTransform(psContext, &apsVertex[0], 1);
/* any vertices clipped? */
ui32ClipCode = apsVertex[0]->ui32Flags & D3DM_CLIPFLAG_MASK;
if (ui32ClipCode == 0) /* no clipping: */
{
if (bStartPrimitive)
{
/*
Start a new primitive block
*/
TACSWritePrimHdr(psContext, psContext->dwTAPrimCtl, MBX1_TAOBJTYPE_POINTS);
TACSWriteLinePointSize(psContext, 0x3F000000/*0.5*/);
bStartPrimitive = IMG_FALSE;
}
ValidateVertex(psContext, &apsVertex[0], 1);
OutputVertices(psContext, &apsVertex[0], 1);
}
}
/*
Finish the primitive block
*/
if(!bStartPrimitive)
{
TACSWriteLastPrim(psContext);
#ifdef FIX_HW_PRN_299
TACSWriteTACtlAnd3DState ( psContext,
MBX1_TASTATEPRES_ISPCTL,
&psContext->sHWState.sTACtl3DState,
TRUE);
#endif
}
}
/***********************************************************************************
Function Name : DrawPrimitive
:
Returns : -
Description : Selects and calls correct primitive draw function
************************************************************************************/
IMG_VOID DrawPrimitive ( LPD3DM_CONTEXT psContext,
D3DMPRIMITIVETYPE PrimType,
IMG_UINT32 ui32StartVertex,
IMG_UINT32 ui32PrimitiveCount)
{
/* select current vertex buffer */
LPD3DM_VBUFFER psCurrentVB = psContext->psVertexSource;
LPVOID pvData;
PRIM_FILLMODE eFillMode = psContext->ePrimFillMode;
IMG_UINT32 ui32StrideInBytes = psCurrentVB->dwStrideDW<<2;
#if defined (FIX_HW_PRN_725_MBXLITE)
/* Initialise Flags */
psContext->dwHWPRN725Flags &= ~HW_PRN_725_FLAGS_INDEXED;
psContext->dwHWPRN725Flags |= HW_PRN_725_FLAGS_STOREVERTS;
psContext->dwHWPRN725Flags &= ~HW_PRN_725_FLAGS_FAN_MODE;
#endif
/* address to vertex data */
pvData = (LPVOID)((IMG_UINT32)psCurrentVB->pvVertexData + (ui32StartVertex * ui32StrideInBytes));
psContext->eCurrentPrimType = PrimType;
PROFILE_START_PRIM(PrimType, eFillMode);
/* FIXME - Validate buffer access - i.e. that we're not goint to exceed the buffer length /*
/* copy vertex data (and transform if SW TnL) */
switch(PrimType)
{
case D3DMPT_TRIANGLELIST:
{
#if defined (FIX_HW_PRN_725_MBXLITE)
if(eFillMode != PRIM_FILLMODE_WIREFRAME)
{
psContext->dwHWPRN725Flags &= ~HW_PRN_725_FLAGS_STOREVERTS;
}
#endif
apfnTriList[eFillMode] (psContext,
pvData,
psCurrentVB->dwFVFFlags,
ui32StrideInBytes,
ui32PrimitiveCount);
break;
}
case D3DMPT_TRIANGLESTRIP:
{
apfnTriStrip[eFillMode] (psContext,
pvData,
psCurrentVB->dwFVFFlags,
ui32StrideInBytes,
ui32PrimitiveCount);
break;
}
case D3DMPT_TRIANGLEFAN:
{
#if defined (FIX_HW_PRN_725_MBXLITE)
if(eFillMode != PRIM_FILLMODE_WIREFRAME)
{
psContext->dwHWPRN725Flags &= ~HW_PRN_725_FLAGS_STOREVERTS;
}
#endif
apfnTriFan[eFillMode] (psContext,
pvData,
psCurrentVB->dwFVFFlags,
ui32StrideInBytes,
ui32PrimitiveCount);
break;
}
case D3DMPT_POINTLIST:
{
#if defined (FIX_HW_PRN_725_MBXLITE)
psContext->dwHWPRN725Flags &= ~HW_PRN_725_FLAGS_STOREVERTS;
#endif
apfnPointList[eFillMode](psContext,
pvData,
psCurrentVB->dwFVFFlags,
ui32StrideInBytes,
ui32PrimitiveCount);
break;
}
case D3DMPT_LINELIST:
{
apfnLineList[eFillMode] (psContext,
pvData,
psCurrentVB->dwFVFFlags,
ui32StrideInBytes,
ui32PrimitiveCount);
break;
}
case D3DMPT_LINESTRIP:
{
apfnLineStrip[eFillMode](psContext,
pvData,
psCurrentVB->dwFVFFlags,
ui32StrideInBytes,
ui32PrimitiveCount);
break;
}
default:
break;
///error!!!!!!!!!!!!!!!!!!!!!!!!!!
}
PROFILE_STOP_PRIM(PrimType, eFillMode);
}
#endif /* SUPPORT_VGP */
/*****************************************************************************
End of file (prim.c)
*****************************************************************************/
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -