1 /*---------------------------------------------------------------------------*
2   Project:  TwlSDK - GX - demos - UnitTours/Capture
3   File:     main.c
4 
5   Copyright 2003-2008 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   $Date:: 2008-09-18#$
14   $Rev: 8573 $
15   $Author: okubata_ryoma $
16  *---------------------------------------------------------------------------*/
17 //---------------------------------------------------------------------------
18 //      A sample for capture display.
19 //
20 //      Rotating cube is displayed.
21 //      There is motion blur effect by capturing display.
22 //
23 //      HOWTO:
24 //      1.      Call "GX_SetCapture" to capture display and blend with rendered image.
25 //
26 //      OPERATION:
27 //      1.      Push cross button to move cube position.
28 //      2.      Push start button to reset cube position.
29 //      3.      Push A or B button to change blending parameter for captured data.
30 //
31 //---------------------------------------------------------------------------
32 #ifdef SDK_TWL
33 #include <twl.h>
34 #else
35 #include <nitro.h>
36 #endif
37 #include "DEMO.h"
38 #include "tex_32768.h"
39 
40 //---------------------------------------------------------------------------
41 //      Cube model data
42 //---------------------------------------------------------------------------
43 // Vertex data
44 static s16 s_Vertex[3 * 8] = {
45     FX16_ONE, FX16_ONE, FX16_ONE,
46     FX16_ONE, FX16_ONE, -FX16_ONE,
47     FX16_ONE, -FX16_ONE, FX16_ONE,
48     FX16_ONE, -FX16_ONE, -FX16_ONE,
49     -FX16_ONE, FX16_ONE, FX16_ONE,
50     -FX16_ONE, FX16_ONE, -FX16_ONE,
51     -FX16_ONE, -FX16_ONE, FX16_ONE,
52     -FX16_ONE, -FX16_ONE, -FX16_ONE
53 };
54 // Normal data
55 static VecFx10 s_Normal[6] = {
56     GX_VECFX10(0, 0, FX32_ONE - 1),
57     GX_VECFX10(0, FX32_ONE - 1, 0),
58     GX_VECFX10(FX32_ONE - 1, 0, 0),
59     GX_VECFX10(0, 0, -FX32_ONE + 1),
60     GX_VECFX10(0, -FX32_ONE + 1, 0),
61     GX_VECFX10(-FX32_ONE + 1, 0, 0)
62 };
63 // Texture coordinate data
64 static GXSt s_TextureCoord[] = {
65     GX_ST(0, 0),
66     GX_ST(0, 64 * FX32_ONE),
67     GX_ST(64 * FX32_ONE, 0),
68     GX_ST(64 * FX32_ONE, 64 * FX32_ONE)
69 };
70 
71 //---------------------------------------------------------------------------
72 //      Set vertex coordinate.
73 //      input:
74 //              i_idx:  ID of vertex data
75 //---------------------------------------------------------------------------
Vertex(int i_idx)76 inline void Vertex(int i_idx)
77 {
78     G3_Vtx(s_Vertex[i_idx * 3], s_Vertex[i_idx * 3 + 1], s_Vertex[i_idx * 3 + 2]);
79 }
80 
81 //---------------------------------------------------------------------------
82 //      Set normal setting.
83 //      input:
84 //              i_idx:  ID of normal data
85 //---------------------------------------------------------------------------
Normal(int i_idx)86 inline void Normal(int i_idx)
87 {
88     G3_Direct1(G3OP_NORMAL, s_Normal[i_idx]);
89 }
90 
91 //---------------------------------------------------------------------------
92 //      Set texture coordinate.
93 //      input:
94 //              i_idx:  ID of texture data
95 //---------------------------------------------------------------------------
TextureCoord(int i_idx)96 inline void TextureCoord(int i_idx)
97 {
98     G3_Direct1(G3OP_TEXCOORD, s_TextureCoord[i_idx]);
99 }
100 
101 //---------------------------------------------------------------------------
102 //  Draw a cube and set texture.
103 //---------------------------------------------------------------------------
DrawCube(void)104 static void DrawCube(void)
105 {
106     G3_Begin(GX_BEGIN_QUADS);          // start to set vertex.(use square polygon)
107     {
108         TextureCoord(1);
109         Normal(0);
110         Vertex(2);
111         TextureCoord(0);
112         Normal(0);
113         Vertex(0);
114         TextureCoord(2);
115         Normal(0);
116         Vertex(4);
117         TextureCoord(3);
118         Normal(0);
119         Vertex(6);
120 
121         TextureCoord(1);
122         Normal(3);
123         Vertex(7);
124         TextureCoord(0);
125         Normal(3);
126         Vertex(5);
127         TextureCoord(2);
128         Normal(3);
129         Vertex(1);
130         TextureCoord(3);
131         Normal(3);
132         Vertex(3);
133 
134         TextureCoord(1);
135         Normal(5);
136         Vertex(6);
137         TextureCoord(0);
138         Normal(5);
139         Vertex(4);
140         TextureCoord(2);
141         Normal(5);
142         Vertex(5);
143         TextureCoord(3);
144         Normal(5);
145         Vertex(7);
146 
147         TextureCoord(1);
148         Normal(2);
149         Vertex(3);
150         TextureCoord(0);
151         Normal(2);
152         Vertex(1);
153         TextureCoord(2);
154         Normal(2);
155         Vertex(0);
156         TextureCoord(3);
157         Normal(2);
158         Vertex(2);
159 
160         TextureCoord(1);
161         Normal(1);
162         Vertex(5);
163         TextureCoord(0);
164         Normal(1);
165         Vertex(4);
166         TextureCoord(2);
167         Normal(1);
168         Vertex(0);
169         TextureCoord(3);
170         Normal(1);
171         Vertex(1);
172 
173         TextureCoord(1);
174         Normal(4);
175         Vertex(6);
176         TextureCoord(0);
177         Normal(4);
178         Vertex(7);
179         TextureCoord(2);
180         Normal(4);
181         Vertex(3);
182         TextureCoord(3);
183         Normal(4);
184         Vertex(2);
185     }
186 
187     G3_End();                          // end
188 }
189 
190 
191 //---------------------------------------------------------------------------
192 // VBlank interrupt function:
193 //
194 // Interrupt handlers are registered on the interrupt table by OS_SetIRQFunction.
195 // OS_EnableIrqMask selects IRQ interrupts to enable, and
196 // OS_EnableIrq enables IRQ interrupts.
197 // Notice that you have to call 'OS_SetIrqCheckFlag' to check a VBlank interrupt.
198 //---------------------------------------------------------------------------
VBlankIntr(void)199 void VBlankIntr(void)
200 {
201     // Set flag which checks VBlank interrupt.
202     OS_SetIrqCheckFlag(OS_IE_V_BLANK);
203 }
204 
205 //---------------------------------------------------------------------------
206 //      main
207 //---------------------------------------------------------------------------
208 #ifdef  SDK_CW_WA_CONSTPOOLS
209 #pragma optimization_level 1
210 #endif
211 #ifdef SDK_TWL
TwlMain(void)212 void TwlMain(void)
213 #else
214 void NitroMain(void)
215 #endif
216 {
217     unsigned int count = 0;
218     u16     Rotate = 0;
219     u32     myTexAddr = 0x00000;       // Address of texture image slot
220     fx32    pos_x = 0;
221     fx32    pos_y = 0;
222     int     eva = 0x04;
223     int     evb = 0x0c;
224 
225     // Initialize
226     DEMOInitCommon();
227     DEMOInitVRAM();
228     DEMOInitDisplay3D();
229 
230     // Set VRAM-C to LCDC
231     GX_SetBankForLCDC(GX_VRAM_LCDC_C);
232 
233     // Set display mode
234     GX_SetGraphicsMode(GX_DISPMODE_VRAM_C, GX_BGMODE_4, // value used by capture circuit
235                        GX_BG0_AS_3D);  // can't pass dummy value
236 
237     // Load texture image into texture image slot.
238     GX_BeginLoadTex();
239     {
240         GX_LoadTex((void *)&tex_32768_64x64[0], // Src address
241                    myTexAddr,          // Destination slot address
242                    8192);              // Size to load
243     }
244     GX_EndLoadTex();
245 
246     DEMOStartDisplay();
247 
248     // Show information message
249     OS_Printf("If EVB is over 8/16, the afterimage of blur stay eternally.\n");
250     OS_Printf("eva=%d : evb=%d\n", eva, evb);
251 
252     // main loop
253     while (1)
254     {
255         G3X_Reset();
256         Rotate += 256;
257 
258         // Read input
259         DEMOReadKey();
260         // Move cube position
261         if (DEMO_IS_PRESS(PAD_KEY_UP))
262         {
263             pos_y += 500;
264         }
265         else if (DEMO_IS_PRESS(PAD_KEY_DOWN))
266         {
267             pos_y -= 500;
268         }
269         if (DEMO_IS_PRESS(PAD_KEY_RIGHT))
270         {
271             pos_x += 500;
272         }
273         else if (DEMO_IS_PRESS(PAD_KEY_LEFT))
274         {
275             pos_x -= 500;
276         }
277         if (DEMO_IS_TRIG(PAD_BUTTON_START))
278         {
279             pos_x = pos_y = 0;
280         }
281 
282         // Change blending parameter
283         if (DEMO_IS_TRIG(PAD_BUTTON_A))
284         {
285             if (++evb > 0x10)
286             {
287                 evb = 0x10;
288             }
289             eva = 0x10 - evb;
290             OS_Printf("eva=%d : evb=%d\n", eva, evb);
291         }
292         else if (DEMO_IS_TRIG(PAD_BUTTON_B))
293         {
294             if (--evb < 0x00)
295             {
296                 evb = 0x00;
297             }
298             eva = 0x10 - evb;
299             OS_Printf("eva=%d : evb=%d\n", eva, evb);
300         }
301 
302         // Camera setting
303         {
304             VecFx32 Eye = { 0, 0, FX32_ONE };   // Sight position
305             VecFx32 at = { 0, 0, 0 };  // Viewpoint
306             VecFx32 vUp = { 0, FX32_ONE, 0 };   // Up
307             G3_LookAt(&Eye, &vUp, &at, NULL);   // Sight setting
308         }
309 
310         // Light setting
311         G3_LightVector(GX_LIGHTID_0, 0, -FX32_ONE + 1, 0);
312         G3_LightColor(GX_LIGHTID_0, GX_RGB(31, 31, 31));
313 
314         // Matrix setting
315         G3_MtxMode(GX_MTXMODE_TEXTURE);
316         G3_Identity();
317         G3_MtxMode(GX_MTXMODE_POSITION_VECTOR);
318         G3_PushMtx();
319 
320         // Rotate and translate cube
321         {
322             fx16    s = FX_SinIdx(Rotate);
323             fx16    c = FX_CosIdx(Rotate);
324 
325             G3_Translate(pos_x, pos_y, -5 * FX32_ONE);
326             G3_RotX(s, c);
327             G3_RotY(s, c);
328             G3_RotZ(s, c);
329         }
330 
331         // Draw setting
332         G3_MaterialColorDiffAmb(GX_RGB(31, 31, 31),     // Diffuse
333                                 GX_RGB(16, 16, 16),     // Ambient
334                                 TRUE); // Color
335         G3_MaterialColorSpecEmi(GX_RGB(16, 16, 16),     // Specular
336                                 GX_RGB(0, 0, 0),        // Emission
337                                 FALSE); // Shininess
338         G3_TexImageParam(GX_TEXFMT_DIRECT,      // Texture format
339                          GX_TEXGEN_TEXCOORD,    // Texture generation
340                          GX_TEXSIZE_S64,        // Texture width
341                          GX_TEXSIZE_T64,        // Texture hight
342                          GX_TEXREPEAT_NONE,     // Texture repeat
343                          GX_TEXFLIP_NONE,       // Texture flip
344                          GX_TEXPLTTCOLOR0_USE,  // Palette color
345                          myTexAddr);   // Texture address
346         G3_PolygonAttr(GX_LIGHTMASK_0, // Light
347                        GX_POLYGONMODE_MODULATE, // Polygon mode
348                        GX_CULL_NONE,   // Culling
349                        0,              // Polygon ID
350                        31,             // Alpha
351                        0);             // Misc
352 
353         // Draw cube
354         DrawCube();
355 
356         G3_PopMtx(1);
357 
358         // swapping the polygon list RAM, the vertex RAM, etc.
359         G3_SwapBuffers(GX_SORTMODE_AUTO, GX_BUFFERMODE_W);
360 
361         // Wait VBlank
362         OS_WaitVBlankIntr();
363 
364         //---------------------------------------------------------------------------
365         // Execute capture
366         // Blend rendered image and displayed image (VRAM), and output to VRAM-C
367         GX_SetCapture(GX_CAPTURE_SIZE_256x192,  // Capture size
368                       GX_CAPTURE_MODE_AB,       // Capture mode
369                       GX_CAPTURE_SRCA_2D3D,     // Blend src A
370                       GX_CAPTURE_SRCB_VRAM_0x00000,     // Blend src B
371                       GX_CAPTURE_DEST_VRAM_C_0x00000,   // Output VRAM
372                       eva,             // Blend parameter for src A
373                       evb);            // Blend parameter for src B
374         //---------------------------------------------------------------------------
375     }
376 }
377