// GET
#define GetX(a) a.fX
#define GetY(a) a.fY
#define GetZ(a) a.fInvW
#define GetPackedColor(a) a.u32Colour
#define GetU(a) a.fUOverW 
#define GetV(a) a.fVOverW 
// SET
#define SetX(a,b) a.fX = b
#define SetY(a,b) a.fY = b
#define SetZ(a,b) a.fInvW = b
#define SetPackedColor(a,b) a.u32Colour = b
#define SetPackedSpecular(a,b) a.u32Specular = b
#define SetU(a,b) a.fUOverW = b
#define SetV(a,b) a.fVOverW = b
#define SetU_Cpy(a,b) *(unsigned long *)&a.fUOverW = *(unsigned long *)&b
#define SetV_Cpy(a,b) *(unsigned long *)&a.fVOverW = *(unsigned long *)&b

// Fond de roulement SGL2
#define GLI_C_SGL2lMaxTriBuffer 512
#define GLI_C_SGL2lMaxVertBuffer GLI_C_SGL2lMaxTriBuffer * 3L
long GLI_glActualSizeOfVertex;
#define GLI_tdScreenVertx SGLVERTEX
SGLVERTEX aDEFCurrentDestXYZ[GLI_C_SGL2lMaxVertBuffer];
SGLVERTEX *CurrentDestXYZ;
extern SGLCONTEXT SGLContext;
extern SGLCONTEXT2 SGLContext2;

#define GLI_M_RestoreCW()

void GLI_BeforeDraw()
{
    CurrentDestXYZ = aDEFCurrentDestXYZ;
    GLI_glActualSizeOfVertex = 0;
};

void GLI_AfterDraw()
{
    CurrentDestXYZ = aDEFCurrentDestXYZ;
    if (GLI_glActualSizeOfVertex != 0)
        sgltri_triangles(&SGLContext , GLI_glActualSizeOfVertex , NULL , CurrentDestXYZ);
    GLI_glActualSizeOfVertex = 0;
}

void GLI_DrawQuad(void)
{
    /* add 2 triangles */
    CurrentDestXYZ[5] = CurrentDestXYZ[3];
    CurrentDestXYZ[4] = CurrentDestXYZ[2];
    CurrentDestXYZ[3] = CurrentDestXYZ[0];
    if (GLI_glActualSizeOfVertex  > GLI_C_SGL2lMaxTriBuffer - 4)
    {
        CurrentDestXYZ = aDEFCurrentDestXYZ;
        sgltri_triangles(&SGLContext , GLI_glActualSizeOfVertex + 2, NULL , CurrentDestXYZ);
        GLI_glActualSizeOfVertex = 0;
    } else
    {
        CurrentDestXYZ += 6;
        GLI_glActualSizeOfVertex+=2;
    }
}

// Draw 
GLI_FuncNodeBegin(GLI_vDrawTriangle)
{
    /* draw */
    if (GLI_glActualSizeOfVertex  > GLI_C_SGL2lMaxTriBuffer - 4)
    {
        CurrentDestXYZ = aDEFCurrentDestXYZ;
        sgltri_triangles(&SGLContext , GLI_glActualSizeOfVertex + 1, NULL , CurrentDestXYZ);
        GLI_glActualSizeOfVertex = 0;
    } else
    {
        CurrentDestXYZ += 3;
        GLI_glActualSizeOfVertex++;
    }
}

void GLI_vDrawZSortedTriangle(void *p_3Point)
{
}
void GLI_vDrawZSortedQuad(void *p_3Point)
{
}

void GLI_vAddDrawFunc()
{
    GLI_M_AddFunc(GLI_vDrawTriangle);
}



//    GLI_BIG_GLOBALS -> lClippingModeMask
void GLI_ReComputeClippingMask()
{
    *(float *)&fX_CMP_Optimize = 640.0f;
    *(float *)&fY_CMP_Optimize = 480.0f;
    *(float *)&fXMin_CLIP_Optimize = 100.0f;
    *(float *)&fYMin_CLIP_Optimize = 50.0f;
    *(float *)&fXMax_CLIP_Optimize = 540.0f;
    *(float *)&fYMax_CLIP_Optimize = 430.0f;
}





//********************************************************************************************
// Name: GLI_DRV_vSendSpriteToClip
// Goal: draw a sprite
// Code: Philippe Vimont 
// OPTIMMIZED : No
//********************************************************************************************
    
void GLI_DRV_vSendSpriteToClip
(
 GLI_tdstAligned2DVector *a4_st2DVertex ,
 MTH_tdxReal xZ ,
 GLI_tdstInternalGlobalValuesFor3dEngine *p_stGlobaleMT)
{
    GLI_BeforeDraw();
    GLI_M_InitSprite();
    SetU(CurrentDestXYZ[0],0.0f);
    SetV(CurrentDestXYZ[0],1.0f);
    SetU(CurrentDestXYZ[1],1.0f);
    SetV(CurrentDestXYZ[1],1.0f);
    SetU(CurrentDestXYZ[2],1.0f);
    SetV(CurrentDestXYZ[2],0.0f);
    SetU(CurrentDestXYZ[3],0.0f);
    SetV(CurrentDestXYZ[3],0.0f);
    GLI_DrawQuad();
    GLI_AfterDraw();
}

//********************************************************************************************
// Name: GLI_DRV_vSendSpriteToClipWithUV 1.0
// Goal: 
// Code: Philippe Vimont / 1.0
// REM: 
// OPTIMMIZED : No
//********************************************************************************************
void GLI_DRV_vSendSpriteToClipWithUV
(
 GLI_tdstAligned2DVector *a4_st2DVertex ,
 MTH_tdxReal *a8_stUVVertex,
 MTH_tdxReal xZ ,
 GLI_tdstInternalGlobalValuesFor3dEngine *p_stGlobaleMT)
{
    GLI_BeforeDraw();
    GLI_M_InitSprite();
    SetU(CurrentDestXYZ[2],a8_stUVVertex[4]);
    SetV(CurrentDestXYZ[2],a8_stUVVertex[4+1]);
    SetU(CurrentDestXYZ[3],a8_stUVVertex[6]);
    SetV(CurrentDestXYZ[3],a8_stUVVertex[6+1]);
    SetU(CurrentDestXYZ[0],a8_stUVVertex[0]);
    SetV(CurrentDestXYZ[0],a8_stUVVertex[0+1]);
    SetU(CurrentDestXYZ[1],a8_stUVVertex[2]);
    SetV(CurrentDestXYZ[1],a8_stUVVertex[2+1]);
    GLI_DrawQuad();
    GLI_AfterDraw();
}

