1 /*---------------------------------------------------------------------------*
2   Project:  Dolphin GD demo
3   File:     gd-reinit-gx.c
4 
5   Copyright 1998-2001 Nintendo.  All rights reserved.
6 
7   These coded instructions, statements, and computer programs contain
8   proprietary information of Nintendo of America Inc. and/or Nintendo
9   Company Ltd., and are protected by Federal copyright law.  They may
10   not be disclosed to third parties or copied or duplicated in any form,
11   in whole or in part, without the prior written consent of Nintendo.
12 
13   $Log: gd-reinit-gx.c,v $
14   Revision 1.2  02/20/2006 04:13:10  mitu
15   changed include path from dolphin/ to revolution/.
16 
17   Revision 1.1  02/08/2006 11:19:43  mitu
18   1st version.
19 
20 
21     1     02/09/06 11:37 Hirose
22     Re-check-in to resolve future time stamp problem.
23 
24     2     02/08/05 18:20 Hirose
25     Typo fix. "Genmode" -> "GenMode".
26 
27     1     10/24/02 8:39a Hirose
28     Initial check in.
29 
30   $NoKeywords: $
31  *---------------------------------------------------------------------------*/
32 /*---------------------------------------------------------------------------*
33     This is sample code for GX re-initialization for GD users.
34 
35     Display lists made by GD can directly modify state of the graphics
36     processor. Sometimes it causes coherency issues between GX library
37     and actual state in the graphics processor after calling GD display
38     list. The most safest way (and simplest way) is just calling bunch of
39     GX APIs again so that you can make all GX state stable.
40 
41     This code shows an example of such GX re-initialization.
42     It is useful when you want to draw something by using GX after calling
43     GD display lists. It may also help debugging in the early stage of
44     development with GD library.
45 
46     However, these are heavy tasks and some optimization might be necessary
47     if you want to use in the final application. You can edit this code and
48     remove sections that are redundant for your code as you like. We put
49     three levels of the compile option to inform about start point of
50     such work.
51  *---------------------------------------------------------------------------*/
52 
53 
54 #include <revolution.h>
55 
56 
57 /*---------------------------------------------------------------------------*
58     Compile option
59  *---------------------------------------------------------------------------*/
60 // Reinitialize minimum sets at least necessary to guarantee state coherencies.
61 #define REINIT_MINIMUM      0
62 // Reinitialize and set up a typical safe graphics state.
63 #define REINIT_TYPICAL      1
64 // Reinitialize and set all state to defaults.
65 #define REINIT_ALLDEFAULTS  2
66 
67 
68 // You can change this definition as you prefer.
69 #define REINIT_LEVEL    REINIT_ALLDEFAULTS
70 
71 /*---------------------------------------------------------------------------*
72     Forward references
73  *---------------------------------------------------------------------------*/
74 extern void ReInitializeGX      ( void );
75 
76 static void ReInitGenMode       ( void );
77 static void ReInitGeometry      ( void );
78 static void ReInitLighting      ( void );
79 static void ReInitTransform     ( void );
80 static void ReInitTexture       ( void );
81 static void ReInitTevStages     ( void );
82 static void ReInitIndStages     ( void );
83 static void ReInitPixelProc     ( void );
84 
85 
86 /*---------------------------------------------------------------------------*
87     Data
88  *---------------------------------------------------------------------------*/
89 #define NULLTEX_WIDTH   4
90 #define NULLTEX_HEIGHT  4
91 #define NULLTEX_FMT     GX_TF_IA8
92 
93 static u8   NullTexData[] ATTRIBUTE_ALIGN(32) =
94 {
95     0x0000, 0x0000, 0x0000, 0x0000,
96     0x0000, 0x0000, 0x0000, 0x0000,
97     0x0000, 0x0000, 0x0000, 0x0000,
98     0x0000, 0x0000, 0x0000, 0x0000
99 };
100 
101 static f32  IdentityMtx[3][4] =
102 {
103     { 1.0F, 0.0F, 0.0F, 0.0F },
104     { 0.0F, 1.0F, 0.0F, 0.0F },
105     { 0.0F, 0.0F, 1.0F, 0.0F }
106 };
107 
108 static f32  IndMtx[2][3] =
109 {
110     { 0.5F, 0.0F, 0.0F },
111     { 0.0F, 0.5F, 0.0F }
112 };
113 
114 
115 static GXColor  ColorBlack = { 0x00, 0x00, 0x00, 0x00 };
116 static GXColor  ColorWhite = { 0xFF, 0xFF, 0xFF, 0xFF };
117 
118 
119 /*---------------------------------------------------------------------------*
120   Name:         ReInitializeGX
121 
122   Description:  Re-initializes graphics.
123 
124   Arguments:    none
125 
126   Returns:      none
127  *---------------------------------------------------------------------------*/
ReInitializeGX(void)128 void ReInitializeGX( void )
129 {
130     ReInitGenMode();
131     ReInitGeometry();
132     ReInitLighting();
133     ReInitTransform();
134     ReInitTexture();
135     ReInitTevStages();
136     ReInitIndStages();
137     ReInitPixelProc();
138 }
139 
140 /*---------------------------------------------------------------------------*
141             "GenMode" - Rendering Pipe Control API Group
142  *---------------------------------------------------------------------------*/
ReInitGenMode(void)143 static void ReInitGenMode( void )
144 {
145     // RELATED: GDSetCullMode, GDSetCoPlanar, GDSetGenMode, GDSetGenMode2
146     GXSetNumChans(0);
147     GXSetNumTexGens(1);
148     GXSetNumTevStages(1);
149     GXSetNumIndStages(0);
150     GXSetCullMode(GX_CULL_BACK);
151     GXSetCoPlanar(GX_DISABLE);
152 }
153 
154 /*---------------------------------------------------------------------------*
155             Geometry API Group
156  *---------------------------------------------------------------------------*/
ReInitGeometry(void)157 static void ReInitGeometry( void )
158 {
159 #if ( REINIT_LEVEL >= REINIT_ALLDEFAULTS )
160     GXVtxAttrFmtList defAttrList[] =
161     {
162         { GX_VA_POS,  GX_POS_XYZ,   GX_F32,   0 },
163         { GX_VA_NRM,  GX_NRM_XYZ,   GX_F32,   0 },
164         { GX_VA_CLR0, GX_CLR_RGBA,  GX_RGBA8, 0 },
165         { GX_VA_CLR1, GX_CLR_RGBA,  GX_RGBA8, 0 },
166         { GX_VA_TEX0, GX_TEX_ST,    GX_F32,   0 },
167         { GX_VA_TEX1, GX_TEX_ST,    GX_F32,   0 },
168         { GX_VA_TEX2, GX_TEX_ST,    GX_F32,   0 },
169         { GX_VA_TEX3, GX_TEX_ST,    GX_F32,   0 },
170         { GX_VA_TEX4, GX_TEX_ST,    GX_F32,   0 },
171         { GX_VA_TEX5, GX_TEX_ST,    GX_F32,   0 },
172         { GX_VA_TEX6, GX_TEX_ST,    GX_F32,   0 },
173         { GX_VA_TEX7, GX_TEX_ST,    GX_F32,   0 },
174         { GX_VA_NULL, (GXCompCnt)0, (GXCompType)0, 0 }
175     };
176     u32     i;
177 #endif
178 
179     // RELATED: GDSetVtxDescv
180     GXClearVtxDesc();
181     GXSetVtxDesc(GX_VA_POS, GX_DIRECT);
182 
183 
184     // RELATED: GDSetVtxAttrv
185 #if ( REINIT_LEVEL >= REINIT_ALLDEFAULTS )
186     for ( i = 0; i < GX_MAX_VTXFMT; ++i )
187     {
188         GXSetVtxAttrFmtv((GXVtxFmt)i, defAttrList);
189     }
190 #endif
191 
192     // RELATED: GDSetLPSize
193     GXSetLineWidth(6, GX_TO_ZERO);
194     GXSetPointSize(6, GX_TO_ZERO);
195 
196     // RELATED: GDSetTexCoordScaleAndTOEs
197     GXEnableTexOffsets(GX_TEXCOORD0, GX_DISABLE, GX_DISABLE);
198 
199 #if ( REINIT_LEVEL >= REINIT_ALLDEFAULTS )
200     GXEnableTexOffsets(GX_TEXCOORD1, GX_DISABLE, GX_DISABLE);
201     GXEnableTexOffsets(GX_TEXCOORD2, GX_DISABLE, GX_DISABLE);
202     GXEnableTexOffsets(GX_TEXCOORD3, GX_DISABLE, GX_DISABLE);
203     GXEnableTexOffsets(GX_TEXCOORD4, GX_DISABLE, GX_DISABLE);
204     GXEnableTexOffsets(GX_TEXCOORD5, GX_DISABLE, GX_DISABLE);
205     GXEnableTexOffsets(GX_TEXCOORD6, GX_DISABLE, GX_DISABLE);
206     GXEnableTexOffsets(GX_TEXCOORD7, GX_DISABLE, GX_DISABLE);
207 #endif
208 
209 }
210 
211 /*---------------------------------------------------------------------------*
212             Lighting API Group
213  *---------------------------------------------------------------------------*/
ReInitLighting(void)214 static void ReInitLighting( void )
215 {
216 
217 #if ( REINIT_LEVEL >= REINIT_TYPICAL )
218     // RELATED: GDSetChanCtrl
219     GXSetChanCtrl(GX_COLOR0A0, GX_DISABLE, GX_SRC_REG, GX_SRC_VTX,
220                   GX_LIGHT_NULL, GX_DF_NONE, GX_AF_NONE);
221     GXSetChanCtrl(GX_COLOR1A1, GX_DISABLE, GX_SRC_REG, GX_SRC_VTX,
222                   GX_LIGHT_NULL, GX_DF_NONE, GX_AF_NONE);
223 #endif
224 
225 #if ( REINIT_LEVEL >= REINIT_ALLDEFAULTS )
226     // RELATED: GDSetChanAmbColor
227     GXSetChanAmbColor(GX_COLOR0A0, ColorBlack);
228     GXSetChanAmbColor(GX_COLOR1A1, ColorBlack);
229 
230     // RELATED: GDSetChanMatColor
231     GXSetChanMatColor(GX_COLOR0A0, ColorWhite);
232     GXSetChanMatColor(GX_COLOR1A1, ColorWhite);
233 #endif
234 
235 }
236 
237 /*---------------------------------------------------------------------------*
238             Transform + TexGen API Group
239  *---------------------------------------------------------------------------*/
ReInitTransform(void)240 static void ReInitTransform( void )
241 {
242 
243 #if ( REINIT_LEVEL >= REINIT_TYPICAL )
244     // RELATED: GDLoad*MtxImm, GDLoad*MtxIndx
245     GXLoadPosMtxImm(IdentityMtx, GX_PNMTX0);
246     GXLoadNrmMtxImm(IdentityMtx, GX_PNMTX0);
247     GXLoadTexMtxImm(IdentityMtx, GX_IDENTITY, GX_MTX3x4);
248     GXLoadTexMtxImm(IdentityMtx, GX_PTIDENTITY, GX_MTX3x4);
249 #endif
250 
251     // RELATED: GDSetTexCoordGen, GDSetCurrentMtx
252     GXSetCurrentMtx(GX_PNMTX0);
253     GXSetTexCoordGen(GX_TEXCOORD0, GX_TG_MTX2x4, GX_TG_TEX0, GX_IDENTITY);
254 
255 #if ( REINIT_LEVEL >= REINIT_ALLDEFAULTS )
256     GXSetTexCoordGen(GX_TEXCOORD1, GX_TG_MTX2x4, GX_TG_TEX1, GX_IDENTITY);
257     GXSetTexCoordGen(GX_TEXCOORD2, GX_TG_MTX2x4, GX_TG_TEX2, GX_IDENTITY);
258     GXSetTexCoordGen(GX_TEXCOORD3, GX_TG_MTX2x4, GX_TG_TEX3, GX_IDENTITY);
259     GXSetTexCoordGen(GX_TEXCOORD4, GX_TG_MTX2x4, GX_TG_TEX4, GX_IDENTITY);
260     GXSetTexCoordGen(GX_TEXCOORD5, GX_TG_MTX2x4, GX_TG_TEX5, GX_IDENTITY);
261     GXSetTexCoordGen(GX_TEXCOORD6, GX_TG_MTX2x4, GX_TG_TEX6, GX_IDENTITY);
262     GXSetTexCoordGen(GX_TEXCOORD7, GX_TG_MTX2x4, GX_TG_TEX7, GX_IDENTITY);
263 #endif
264 
265     // RELATED: GDSetTexCoordScale, GDSetTexCoordScale2, GDSetTexCoordScaleAndTOEs
266     GXSetTexCoordScaleManually(GX_TEXCOORD0, GX_DISABLE, 0, 0);
267     GXSetTexCoordCylWrap(GX_TEXCOORD0, GX_DISABLE, GX_DISABLE);
268 
269 #if ( REINIT_LEVEL >= REINIT_ALLDEFAULTS )
270     GXSetTexCoordScaleManually(GX_TEXCOORD1, GX_DISABLE, 0, 0);
271     GXSetTexCoordCylWrap(GX_TEXCOORD1, GX_DISABLE, GX_DISABLE);
272     GXSetTexCoordScaleManually(GX_TEXCOORD2, GX_DISABLE, 0, 0);
273     GXSetTexCoordCylWrap(GX_TEXCOORD2, GX_DISABLE, GX_DISABLE);
274     GXSetTexCoordScaleManually(GX_TEXCOORD3, GX_DISABLE, 0, 0);
275     GXSetTexCoordCylWrap(GX_TEXCOORD3, GX_DISABLE, GX_DISABLE);
276     GXSetTexCoordScaleManually(GX_TEXCOORD4, GX_DISABLE, 0, 0);
277     GXSetTexCoordCylWrap(GX_TEXCOORD4, GX_DISABLE, GX_DISABLE);
278     GXSetTexCoordScaleManually(GX_TEXCOORD5, GX_DISABLE, 0, 0);
279     GXSetTexCoordCylWrap(GX_TEXCOORD5, GX_DISABLE, GX_DISABLE);
280     GXSetTexCoordScaleManually(GX_TEXCOORD6, GX_DISABLE, 0, 0);
281     GXSetTexCoordCylWrap(GX_TEXCOORD6, GX_DISABLE, GX_DISABLE);
282     GXSetTexCoordScaleManually(GX_TEXCOORD7, GX_DISABLE, 0, 0);
283     GXSetTexCoordCylWrap(GX_TEXCOORD7, GX_DISABLE, GX_DISABLE);
284 #endif
285 }
286 
287 /*---------------------------------------------------------------------------*
288             Texture API Group
289  *---------------------------------------------------------------------------*/
ReInitTexture(void)290 static void ReInitTexture( void )
291 {
292     GXTexObj    tobj;
293 
294     // RELATED: GDSetTexImgAttr, GDSetTexImgPtr, GDSetTexLookupMode,
295     //          GDSetTexTlut, GDSetTexCached, GDSetTexPreLoaded
296     GXInitTexObj(&tobj, NullTexData, NULLTEX_WIDTH, NULLTEX_HEIGHT,
297                  NULLTEX_FMT, GX_CLAMP, GX_CLAMP, GX_FALSE);
298 
299     GXLoadTexObj(&tobj, GX_TEXMAP0);
300 
301 #if ( REINIT_LEVEL >= REINIT_ALLDEFAULTS )
302     GXLoadTexObj(&tobj, GX_TEXMAP1);
303     GXLoadTexObj(&tobj, GX_TEXMAP2);
304     GXLoadTexObj(&tobj, GX_TEXMAP3);
305     GXLoadTexObj(&tobj, GX_TEXMAP4);
306     GXLoadTexObj(&tobj, GX_TEXMAP5);
307     GXLoadTexObj(&tobj, GX_TEXMAP6);
308     GXLoadTexObj(&tobj, GX_TEXMAP7);
309 #endif
310 
311 }
312 
313 /*---------------------------------------------------------------------------*
314             Texture Environment API Group
315  *---------------------------------------------------------------------------*/
ReInitTevStages(void)316 static void ReInitTevStages( void )
317 {
318     u32     i, max;
319 
320     // RELATED: GDSetTevOrder
321     GXSetTevOrder(GX_TEVSTAGE0, GX_TEXCOORD0, GX_TEXMAP0, GX_COLOR0A0);
322 
323 #if ( REINIT_LEVEL >= REINIT_ALLDEFAULTS )
324     GXSetTevOrder(GX_TEVSTAGE1, GX_TEXCOORD1, GX_TEXMAP1, GX_COLOR0A0);
325     GXSetTevOrder(GX_TEVSTAGE2, GX_TEXCOORD2, GX_TEXMAP2, GX_COLOR0A0);
326     GXSetTevOrder(GX_TEVSTAGE3, GX_TEXCOORD3, GX_TEXMAP3, GX_COLOR0A0);
327     GXSetTevOrder(GX_TEVSTAGE4, GX_TEXCOORD4, GX_TEXMAP4, GX_COLOR0A0);
328     GXSetTevOrder(GX_TEVSTAGE5, GX_TEXCOORD5, GX_TEXMAP5, GX_COLOR0A0);
329     GXSetTevOrder(GX_TEVSTAGE6, GX_TEXCOORD6, GX_TEXMAP6, GX_COLOR0A0);
330     GXSetTevOrder(GX_TEVSTAGE7, GX_TEXCOORD7, GX_TEXMAP7, GX_COLOR0A0);
331     GXSetTevOrder(GX_TEVSTAGE8, GX_TEXCOORD_NULL, GX_TEXMAP_NULL, GX_COLOR_NULL);
332     GXSetTevOrder(GX_TEVSTAGE9, GX_TEXCOORD_NULL, GX_TEXMAP_NULL, GX_COLOR_NULL);
333     GXSetTevOrder(GX_TEVSTAGE10,GX_TEXCOORD_NULL, GX_TEXMAP_NULL, GX_COLOR_NULL);
334     GXSetTevOrder(GX_TEVSTAGE11,GX_TEXCOORD_NULL, GX_TEXMAP_NULL, GX_COLOR_NULL);
335     GXSetTevOrder(GX_TEVSTAGE12,GX_TEXCOORD_NULL, GX_TEXMAP_NULL, GX_COLOR_NULL);
336     GXSetTevOrder(GX_TEVSTAGE13,GX_TEXCOORD_NULL, GX_TEXMAP_NULL, GX_COLOR_NULL);
337     GXSetTevOrder(GX_TEVSTAGE14,GX_TEXCOORD_NULL, GX_TEXMAP_NULL, GX_COLOR_NULL);
338     GXSetTevOrder(GX_TEVSTAGE15,GX_TEXCOORD_NULL, GX_TEXMAP_NULL, GX_COLOR_NULL);
339 #endif
340 
341 #if ( REINIT_LEVEL >= REINIT_ALLDEFAULTS )
342     // RELATED: GDSetTevColor, GDSetTevColorS10
343     GXSetTevColor(GX_TEVREG0, ColorWhite);
344     GXSetTevColor(GX_TEVREG1, ColorWhite);
345     GXSetTevColor(GX_TEVREG2, ColorWhite);
346     // RELATED: GDSetTevKColor
347     GXSetTevKColor(GX_KCOLOR0, ColorWhite);
348     GXSetTevKColor(GX_KCOLOR1, ColorWhite);
349     GXSetTevKColor(GX_KCOLOR2, ColorWhite);
350     GXSetTevKColor(GX_KCOLOR3, ColorWhite);
351 #endif
352 
353     // RELATED: GDSetTevOp, GDSetTevColorCalc, GDSetTevAlphaCalcAndSwap
354     //           GDSetTevKonstantSel, GDSetTevSwapModeTable
355 #if ( REINIT_LEVEL >= REINIT_ALLDEFAULTS )
356     max = GX_MAX_TEVSTAGES;
357 #else
358     max = GX_TEVSTAGE1;
359 #endif
360    for (i = GX_TEVSTAGE0; i < max; i++)
361     {
362         GXSetTevOp((GXTevStageID)i, GX_REPLACE);
363         GXSetTevKColorSel((GXTevStageID)i, GX_TEV_KCSEL_1_4);
364         GXSetTevKAlphaSel((GXTevStageID)i, GX_TEV_KASEL_1);
365         GXSetTevSwapMode ((GXTevStageID)i, GX_TEV_SWAP0, GX_TEV_SWAP0);
366     }
367 #if ( REINIT_LEVEL >= REINIT_TYPICAL )
368     GXSetTevSwapModeTable(GX_TEV_SWAP0,
369                           GX_CH_RED, GX_CH_GREEN, GX_CH_BLUE, GX_CH_ALPHA);
370     GXSetTevSwapModeTable(GX_TEV_SWAP1,
371                           GX_CH_RED, GX_CH_RED, GX_CH_RED, GX_CH_ALPHA);
372     GXSetTevSwapModeTable(GX_TEV_SWAP2,
373                           GX_CH_GREEN, GX_CH_GREEN, GX_CH_GREEN, GX_CH_ALPHA);
374     GXSetTevSwapModeTable(GX_TEV_SWAP3,
375                           GX_CH_BLUE, GX_CH_BLUE, GX_CH_BLUE, GX_CH_ALPHA);
376 #endif
377 
378 
379 #if ( REINIT_LEVEL >= REINIT_TYPICAL )
380     // RELATED: GDSetAlphaCompare
381     GXSetAlphaCompare(GX_ALWAYS, 0, GX_AOP_AND, GX_ALWAYS, 0);
382 
383     // RELATED: GDSetZTexture
384     GXSetZTexture(GX_ZT_DISABLE, GX_TF_Z8, 0);
385 #endif
386 
387 }
388 
389 /*---------------------------------------------------------------------------*
390             Indirect Texture API Group
391  *---------------------------------------------------------------------------*/
ReInitIndStages(void)392 static void ReInitIndStages( void )
393 {
394     u32     i;
395 
396     for (i = GX_TEVSTAGE0; i < GX_MAX_TEVSTAGE; i++)
397     {
398         GXSetTevDirect((GXTevStageID) i);
399     }
400 
401 #if ( REINIT_LEVEL >= REINIT_ALLDEFAULTS )
402     GXSetIndTexOrder(GX_INDTEXSTAGE0, GX_TEXCOORD0, GX_TEXMAP0);
403     GXSetIndTexOrder(GX_INDTEXSTAGE1, GX_TEXCOORD1, GX_TEXMAP1);
404     GXSetIndTexOrder(GX_INDTEXSTAGE2, GX_TEXCOORD2, GX_TEXMAP2);
405     GXSetIndTexOrder(GX_INDTEXSTAGE3, GX_TEXCOORD3, GX_TEXMAP3);
406 
407     GXSetIndTexCoordScale(GX_INDTEXSTAGE0, GX_ITS_1, GX_ITS_1);
408     GXSetIndTexCoordScale(GX_INDTEXSTAGE1, GX_ITS_1, GX_ITS_1);
409     GXSetIndTexCoordScale(GX_INDTEXSTAGE2, GX_ITS_1, GX_ITS_1);
410     GXSetIndTexCoordScale(GX_INDTEXSTAGE3, GX_ITS_1, GX_ITS_1);
411 
412     GXSetIndTexMtx(GX_ITM_0, IndMtx, 1);
413     GXSetIndTexMtx(GX_ITM_1, IndMtx, 1);
414     GXSetIndTexMtx(GX_ITM_2, IndMtx, 1);
415 #endif
416 
417 }
418 
419 /*---------------------------------------------------------------------------*
420             Pixel Processing API Group
421  *---------------------------------------------------------------------------*/
ReInitPixelProc(void)422 static void ReInitPixelProc( void )
423 {
424 
425     // RELATED: GDSetBlendMode, GDSetBlendModeEtc
426     GXSetBlendMode(GX_BM_NONE, GX_BL_SRCALPHA, GX_BL_INVSRCALPHA, GX_LO_CLEAR);
427     GXSetColorUpdate(GX_ENABLE);
428     GXSetAlphaUpdate(GX_ENABLE);
429     GXSetDither(GX_ENABLE);
430 
431 #if ( REINIT_LEVEL >= REINIT_TYPICAL )
432     // RELATED: GDSetFog
433     GXSetFog(GX_FOG_NONE, 0.0F, 1.0F, 0.1F, 1.0F, ColorBlack);
434     GXSetFogRangeAdj(GX_DISABLE, 0, 0);
435 
436     // RELATED: GDSetZMode
437     GXSetZMode(GX_TRUE, GX_LEQUAL, GX_TRUE);
438 
439     // RELATED: GDSetDstAlpha
440     GXSetDstAlpha(GX_DISABLE, 0);
441 #endif
442 
443 }
444 
445 /*===========================================================================*/
446