GLES2N64: Added WIP fix for CBFD from mupen64plus-ae
[mupen64plus-pandora.git] / source / gles2n64 / src / F3DCBFD.cpp
1 #include "Common.h"
2 #include "gles2N64.h"
3 #include "Debug.h"
4 #include "F3D.h"
5 #include "F3DEX.h"
6 #include "F3DEX2.h"
7 #include "F3DCBFD.h"
8 #include "S2DEX.h"
9 #include "S2DEX2.h"
10 #include "N64.h"
11 #include "RSP.h"
12 #include "RDP.h"
13 #include "gSP.h"
14 #include "gDP.h"
15 #include "GBI.h"
16 #include "OpenGL.h"
17 #include "Config.h"
18
19 //BASED ON GLIDE64 Implementation
20
21 u32 normal_address = 0;
22
23 void F3DCBFD_Vtx(u32 w0, u32 w1)
24 {
25         s32 v0, n;
26     u32 address;
27         n = (w0 >> 12)&0xFF;
28         v0 = ((w0 >> 1)&0x7F) - n;
29         address = RSP_SegmentToPhysical(w1);
30
31         if (v0 < 0)
32         {
33                 return;
34         }
35
36     gSPFlushTriangles();
37
38     Vertex* vertex = (Vertex*)&RDRAM[address];
39         u32 v;
40         
41         for (s32 i=0; i < n; i++)
42         {
43 #ifdef __TRIBUFFER_OPT
44         v = __indexmap_getnew(v0 + i, 1);
45 #else
46         v = v0 + i;
47 #endif
48
49                 OGL.triangles.vertices[v].x = vertex->x;
50                 OGL.triangles.vertices[v].y = vertex->y;
51                 OGL.triangles.vertices[v].z = vertex->z;
52                 OGL.triangles.vertices[v].w = 1.0f;
53
54                 OGL.triangles.vertices[v].s = _FIXED2FLOAT(vertex->s, 5);
55                 OGL.triangles.vertices[v].t = _FIXED2FLOAT(vertex->t, 5);
56
57         if (config.enableLighting && gSP.geometryMode & G_LIGHTING)
58                 {
59                         OGL.triangles.vertices[v].nx = ((s8*)RDRAM)[(normal_address + (i<<1) + (v0<<1) + 0)^3];
60                         OGL.triangles.vertices[v].ny = ((s8*)RDRAM)[(normal_address + (i<<1) + (v0<<1) + 1)^3];
61                         OGL.triangles.vertices[v].nz = (s8)(vertex->flag&0xff);
62                 }
63
64         gSPProcessVertex(v);
65
66                 u32 nonblack = 0;
67                 nonblack += OGL.triangles.vertices[v].r;
68                 nonblack += OGL.triangles.vertices[v].g;
69                 nonblack += OGL.triangles.vertices[v].b;
70         if (config.enableLighting && (gSP.geometryMode & G_LIGHTING) && (nonblack != 0))
71                 {
72             OGL.triangles.vertices[v].r = OGL.triangles.vertices[v].r * vertex->color.r * 0.0039215689f;
73             OGL.triangles.vertices[v].g = OGL.triangles.vertices[v].g * vertex->color.g * 0.0039215689f;
74             OGL.triangles.vertices[v].b = OGL.triangles.vertices[v].b * vertex->color.b * 0.0039215689f;
75             OGL.triangles.vertices[v].a = vertex->color.a * 0.0039215689f;
76                 }
77                 else
78                 {
79             OGL.triangles.vertices[v].r = vertex->color.r * 0.0039215689f;
80             OGL.triangles.vertices[v].g = vertex->color.g * 0.0039215689f;
81             OGL.triangles.vertices[v].b = vertex->color.b * 0.0039215689f;
82             OGL.triangles.vertices[v].a = vertex->color.a * 0.0039215689f;
83                 }
84                 vertex++;
85     }
86 }
87
88 void F3DCBFD_MoveWord(u32 w0, u32 w1)
89 {
90         u8 index = (u8)((w0 >> 16) & 0xFF);
91         u16 offset = (u16)(w0 & 0xFFFF);
92
93         switch (index)
94         {
95         case G_MW_NUMLIGHT:
96                         gSPNumLights(w1 / 48);
97             break;
98
99         case G_MW_CLIP:
100             if (offset == 0x04)
101             {
102                 gSPClipRatio( w1 );
103             }
104             break;
105
106         case G_MW_SEGMENT:
107             gSPSegment(_SHIFTR(offset, 2, 4), w1 & 0x00FFFFFF);
108             break;
109
110         case G_MW_FOG:
111             gSPFogFactor( (s16)_SHIFTR( w1, 16, 16 ), (s16)_SHIFTR( w1, 0, 16 ) );
112             break;
113
114         case G_MV_COORDMOD:  // moveword coord mod
115             break;
116
117         default:
118             break;
119     }
120 }
121
122 #define F3DCBFD_MV_VIEWPORT     8
123 #define F3DCBFD_MV_LIGHT        10
124 #define F3DCBFD_MV_NORMAL       14
125
126 void F3DCBFD_MoveMem(u32 w0, u32 w1)
127 {
128 #ifdef __TRIBUFFER_OPT
129     gSPFlushTriangles();
130 #endif
131     switch (_SHIFTR( w0, 0, 8 ))
132     {
133         case F3DCBFD_MV_VIEWPORT:
134             gSPViewport(w1);
135             break;
136
137         case F3DCBFD_MV_LIGHT:
138         {
139                         u32 offset = (w0 >> 5) & 0x3FFF;
140                         u32 n = offset / 48;
141                         if (n < 2) {
142                                 //LookAt
143                                 return;
144                         }
145                         n--;
146                         gSPLight(w1, n);
147             break;
148         }
149
150         case F3DCBFD_MV_NORMAL:
151                         normal_address = RSP_SegmentToPhysical(w1);
152             break;
153
154     }
155 }
156
157 void F3DCBFD_Tri4(u32 w0, u32 w1)
158 {
159     gSP4Triangles( _SHIFTR(w0, 23, 5), _SHIFTR(w0, 18, 5), (_SHIFTR(w0, 15, 3 ) << 2) | _SHIFTR(w1, 30, 2),
160                    _SHIFTR(w0, 10, 5), _SHIFTR(w0, 5, 5), _SHIFTR(w0, 0, 5),
161                    _SHIFTR(w1, 25, 5), _SHIFTR(w1, 20, 5), _SHIFTR(w1, 15, 5),
162                    _SHIFTR(w1, 10, 5), _SHIFTR(w1, 5, 5), _SHIFTR(w1, 0, 5));
163 }
164
165
166 void F3DCBFD_Init()
167 {
168     LOG(LOG_VERBOSE, "USING CBFD ucode!\n");
169
170     // Set GeometryMode flags
171     GBI_InitFlags(F3DEX2);
172
173     GBI.PCStackSize = 10;
174
175     // GBI Command                      Command Value               Command Function
176     GBI_SetGBI( G_RDPHALF_2,            F3DEX2_RDPHALF_2,           F3D_RDPHalf_2 );
177     GBI_SetGBI( G_SETOTHERMODE_H,       F3DEX2_SETOTHERMODE_H,      F3DEX2_SetOtherMode_H );
178     GBI_SetGBI( G_SETOTHERMODE_L,       F3DEX2_SETOTHERMODE_L,      F3DEX2_SetOtherMode_L );
179     GBI_SetGBI( G_RDPHALF_1,            F3DEX2_RDPHALF_1,           F3D_RDPHalf_1 );
180     GBI_SetGBI( G_SPNOOP,               F3DEX2_SPNOOP,              F3D_SPNoOp );
181     GBI_SetGBI( G_ENDDL,                F3DEX2_ENDDL,               F3D_EndDL );
182     GBI_SetGBI( G_DL,                   F3DEX2_DL,                  F3D_DList );
183     GBI_SetGBI( G_LOAD_UCODE,           F3DEX2_LOAD_UCODE,          F3DEX_Load_uCode );
184     GBI_SetGBI( G_MOVEMEM,              F3DEX2_MOVEMEM,             F3DCBFD_MoveMem);
185     GBI_SetGBI( G_MOVEWORD,             F3DEX2_MOVEWORD,            F3DCBFD_MoveWord);
186     GBI_SetGBI( G_MTX,                  F3DEX2_MTX,                 F3DEX2_Mtx );
187     GBI_SetGBI( G_GEOMETRYMODE,         F3DEX2_GEOMETRYMODE,        F3DEX2_GeometryMode );
188     GBI_SetGBI( G_POPMTX,               F3DEX2_POPMTX,              F3DEX2_PopMtx );
189     GBI_SetGBI( G_TEXTURE,              F3DEX2_TEXTURE,             F3DEX2_Texture );
190     GBI_SetGBI( G_DMA_IO,               F3DEX2_DMA_IO,              F3DEX2_DMAIO );
191     GBI_SetGBI( G_SPECIAL_1,            F3DEX2_SPECIAL_1,           F3DEX2_Special_1 );
192     GBI_SetGBI( G_SPECIAL_2,            F3DEX2_SPECIAL_2,           F3DEX2_Special_2 );
193     GBI_SetGBI( G_SPECIAL_3,            F3DEX2_SPECIAL_3,           F3DEX2_Special_3 );
194
195
196
197     GBI_SetGBI(G_VTX,                   F3DEX2_VTX,                 F3DCBFD_Vtx);
198     GBI_SetGBI(G_MODIFYVTX,             F3DEX2_MODIFYVTX,           F3DEX_ModifyVtx);
199     GBI_SetGBI(G_CULLDL,                F3DEX2_CULLDL,              F3DEX_CullDL);
200     GBI_SetGBI(G_BRANCH_Z,              F3DEX2_BRANCH_Z,            F3DEX_Branch_Z);
201     GBI_SetGBI(G_TRI1,                  F3DEX2_TRI1,                F3DEX2_Tri1);
202     GBI_SetGBI(G_TRI2,                  F3DEX2_TRI2,                F3DEX_Tri2);
203     GBI_SetGBI(G_QUAD,                  F3DEX2_QUAD,                F3DEX2_Quad);
204 //  GBI_SetGBI( G_LINE3D,               F3DEX2_LINE3D,              F3DEX2_Line3D );
205
206     //for some reason glide64 maps TRI4 to these locations:
207
208     for(int i = 0x10; i <= 0x1F; i++)
209     {
210         GBI_SetGBI(G_TRI4, i, F3DCBFD_Tri4);
211     }
212
213     GBI_SetGBI( G_BG_1CYC,              S2DEX2_BG_1CYC,             S2DEX_BG_1Cyc);
214     GBI_SetGBI( G_BG_COPY,              S2DEX2_BG_COPY,             S2DEX_BG_Copy);
215     GBI_SetGBI( G_OBJ_RENDERMODE,       S2DEX2_OBJ_RENDERMODE,      S2DEX_Obj_RenderMode);
216
217 }
218