1 /*---------------------------------------------------------------------------*
2 Project: TwlSDK - GX - demos - UnitTours/3D_PolAttr_1Dot
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 //---------------------------------------------------------------------------
19 // A sample that controls the display of 1-dot polygons by depth value
20 //
21 // This sample displays three cubes, and allows the user to change scale and depth using the +Control Pad.
22 // If the cubes are smaller than 1 dot, toggle visibility by pressing A.
23 //
24 // USAGE:
25 // UP, DOWN: Change the value of the depth limit at which a 1-pixel polygon is visible
26 // L, R: Change the scale of the object
27 // A: Toggle visibility of 1-dot polygons
28 //
29 //---------------------------------------------------------------------------
30
31 #ifdef SDK_TWL
32 #include <twl.h>
33 #else
34 #include <nitro.h>
35 #endif
36 #include "DEMO.h"
37 #include "data.h"
38
39 //---------------------------------------------------------------------------
40 // Summary:
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 GXSt s_TextureCoord[] = {
56 GX_ST(0, 0),
57 GX_ST(0, 64 * FX32_ONE),
58 GX_ST(64 * FX32_ONE, 0),
59 GX_ST(64 * FX32_ONE, 64 * FX32_ONE)
60 };
61
62 //---------------------------------------------------------------------------
63 // Summary:
64 // Set vertex coordinates
65 // Description:
66 // Use specified vertex data to set vertex coordinates
67 // Input:
68 // i_idx: Vertex data ID
69 //---------------------------------------------------------------------------
Vertex(int i_idx)70 inline void Vertex(int i_idx)
71 {
72 G3_Vtx(s_Vertex[i_idx * 3], s_Vertex[i_idx * 3 + 1], s_Vertex[i_idx * 3 + 2]);
73 }
74
75 //---------------------------------------------------------------------------
76 // Summary:
77 // Set vertex color
78 //---------------------------------------------------------------------------
Color(void)79 inline void Color(void)
80 {
81 G3_Color(GX_RGB(31, 31, 31));
82 }
83
84 //---------------------------------------------------------------------------
85 // Summary:
86 // Texture coordinate settings
87 // Description:
88 //
89 // Input:
90 // i_idx: Texture data ID
91 //---------------------------------------------------------------------------
TextureCoord(int i_idx)92 inline void TextureCoord(int i_idx)
93 {
94 G3_Direct1(G3OP_TEXCOORD, s_TextureCoord[i_idx]);
95 }
96
97 //---------------------------------------------------------------------------
98 // Summary:
99 // Cube drawing information type
100 // Description:
101 //---------------------------------------------------------------------------
102 #pragma warn_padding off
103 typedef struct
104 {
105 int trg;
106 fx32 scale;
107 fx32 depth;
108 u32 texAddr;
109 u16 rotate;
110 // [PADDING 2 BYTE HERE]
111 }
112 cubu_c;
113 #pragma warn_padding reset
114
115
116 //---------------------------------------------------------------------------
117 // Summary:
118 // Draw cube
119 // Description:
120 //
121 // Input:
122 // *p : Cube information pointer
123 // x: x position
124 // y: y position
125 // z: z position
126 //---------------------------------------------------------------------------
Cube(cubu_c * p,fx32 x,fx32 y,fx32 z)127 static void Cube(cubu_c * p, fx32 x, fx32 y, fx32 z)
128 {
129 G3_PushMtx();
130
131 /* Cube rotation and position configuration */
132 {
133 fx16 s = FX_SinIdx(p->rotate);
134 fx16 c = FX_CosIdx(p->rotate);
135
136 G3_Translate(x, y, z);
137
138 G3_RotX(s, c);
139 G3_RotY(s, c);
140 G3_RotZ(s, c);
141
142 G3_Scale(p->scale, p->scale, p->scale);
143 }
144
145 /* Cube rendering configuration */
146 // Set material's diffuse reflection color and ambient reflection color
147 G3_MaterialColorDiffAmb(GX_RGB(31, 31, 31), // Diffuse reflection color
148 GX_RGB(16, 16, 16), // Ambient reflection color
149 TRUE); // Set vertex color
150 // Configure the specular color and the emission color of the material
151 G3_MaterialColorSpecEmi(GX_RGB(16, 16, 16), // Specular reflection color
152 GX_RGB(0, 0, 0), // The emission color
153 FALSE); // Specular reflection not used
154 // Polygon attribute settings
155
156 // Specify texture parameters
157 G3_TexImageParam(GX_TEXFMT_DIRECT, // Use direct texture
158 GX_TEXGEN_TEXCOORD, // Set texture coordinate conversion mode
159 GX_TEXSIZE_S64, // 64 texture s size
160 GX_TEXSIZE_T64, // 64 texture t size
161 GX_TEXREPEAT_NONE, // No repeat
162 GX_TEXFLIP_NONE, // No flip
163 GX_TEXPLTTCOLOR0_USE, // Enable palette color 0 set value
164 p->texAddr); // Texture address
165
166 {
167 int attr;
168
169 if (p->trg)
170 {
171 attr = GX_POLYGON_ATTR_MISC_DISP_1DOT;
172 }
173 else
174 {
175 attr = GX_POLYGON_ATTR_MISC_NONE;
176 }
177 // Polygon attribute settings
178 G3_PolygonAttr(GX_LIGHTMASK_NONE, // Do not reflect light
179 GX_POLYGONMODE_MODULATE, // Modulation mode
180 GX_CULL_NONE, // No culling
181 0, // Polygon ID 0
182 31, // Alpha value
183 attr); // 1-dot polygon display setting
184 }
185 //
186 G3X_SetDisp1DotDepth(p->depth); // 1-dot polygon display border depth value
187
188 G3_Begin(GX_BEGIN_QUADS); // Start vertex list (draw with quadrilateral polygons)
189 {
190 TextureCoord(1);
191 Color();
192 Vertex(2);
193 TextureCoord(0);
194 Color();
195 Vertex(0);
196 TextureCoord(2);
197 Color();
198 Vertex(4);
199 TextureCoord(3);
200 Color();
201 Vertex(6);
202
203 TextureCoord(1);
204 Color();
205 Vertex(7);
206 TextureCoord(0);
207 Color();
208 Vertex(5);
209 TextureCoord(2);
210 Color();
211 Vertex(1);
212 TextureCoord(3);
213 Color();
214 Vertex(3);
215
216 TextureCoord(1);
217 Color();
218 Vertex(6);
219 TextureCoord(0);
220 Color();
221 Vertex(4);
222 TextureCoord(2);
223 Color();
224 Vertex(5);
225 TextureCoord(3);
226 Color();
227 Vertex(7);
228
229 TextureCoord(1);
230 Color();
231 Vertex(3);
232 TextureCoord(0);
233 Color();
234 Vertex(1);
235 TextureCoord(2);
236 Color();
237 Vertex(0);
238 TextureCoord(3);
239 Color();
240 Vertex(2);
241
242 TextureCoord(1);
243 Color();
244 Vertex(5);
245 TextureCoord(0);
246 Color();
247 Vertex(4);
248 TextureCoord(2);
249 Color();
250 Vertex(0);
251 TextureCoord(3);
252 Color();
253 Vertex(1);
254
255 TextureCoord(1);
256 Color();
257 Vertex(6);
258 TextureCoord(0);
259 Color();
260 Vertex(7);
261 TextureCoord(2);
262 Color();
263 Vertex(3);
264 TextureCoord(3);
265 Color();
266 Vertex(2);
267 }
268 G3_End(); // End vertex list
269
270 G3_PopMtx(1);
271 }
272
273 //---------------------------------------------------------------------------
274 // Summary:
275 // V-Blank interrupt process
276 // Description:
277 // Enables a flag that confirms that a V-Blank interrupt has been performed.
278 //
279 // The following steps will be performed during common initialization (DEMOInitCommon), causing this function to be called during V-Blanks
280 // * Select IRQ interrupt (OS_SetIrqMask)
281 // * Register this function, which performs IRQ interrupts (OS_SetIRQFunction)
282 // * Enable IRQ interrupts (OS_EnableIrq)
283 //
284 //---------------------------------------------------------------------------
VBlankIntr(void)285 void VBlankIntr(void)
286 {
287 OS_SetIrqCheckFlag(OS_IE_V_BLANK); // Sets a V-Blank interrupt confirmation flag
288 }
289
290 //---------------------------------------------------------------------------
291 // Summary:
292 // Setting GX_POLYGON_ATTR_MISC_DISP_1DOT in G3_PolygonAttr
293 // (Use depth value to suppress 1-dot polygon display)
294 // Description:
295 // Use depth value to suppress 1-dot polygon display
296 //
297 // 1. When the sample starts up, press BUTTON_L and set the object's Scale value to 0
298 //
299 // 2. The scale value becomes 0, and three objects are displayed as 1 dot
300 // 3. By pressing UP and DOWN on the +Control Pad and increasing or decreasing the depth value, objects displayed in the background will blink in order, starting from the object on the left (which is the deepest object)
301 //
302 // Controls:
303 // BUTTON_L, R: Object scale value
304 // UP, DOWN: Increase and decrease the object's depth value
305 // START: Return to initial value
306 // SELECT: Update the depth value with a close value in the position test
307 //---------------------------------------------------------------------------
308 #ifdef SDK_TWL
TwlMain(void)309 void TwlMain(void)
310 #else
311 void NitroMain(void)
312 #endif
313 {
314 cubu_c cubu;
315
316 cubu.trg = 1;
317 cubu.scale = FX32_ONE;
318 cubu.depth = 16384;
319 cubu.texAddr = 0x01000; // Slot address of the texture image
320 cubu.rotate = 0;
321
322 /*
323 * Initialize (enable IRQ, initialize VRAM, use BG0 in 3D mode)
324 */
325 DEMOInitCommon();
326 DEMOInitVRAM();
327 DEMOInitDisplay3D();
328
329 /* Load the texture image to the texture image slot */
330 GX_BeginLoadTex(); // Map the bank allocated to the slot to LCDC memory
331 {
332 GX_LoadTex((void *)&tex_32768_64x64[0], // Load source pointer
333 cubu.texAddr, // Load destination slot address
334 8192); // Load size
335 }
336 GX_EndLoadTex(); // Restore the slot mapped to LCDC to its original state
337
338 DEMOStartDisplay();
339
340 while (1)
341 {
342 G3X_Reset();
343 cubu.rotate += 256;
344
345 DEMOReadKey();
346 #ifdef SDK_AUTOTEST // Code for auto-test
347 {
348 const EXTKeys keys[8] =
349 { {PAD_BUTTON_L, 80}, {PAD_KEY_DOWN, 8}, {PAD_BUTTON_A, 1}, {0, 0} };
350 EXT_AutoKeys(keys, &gKeyWork.press, &gKeyWork.trigger);
351 }
352 #endif
353
354 if (DEMO_IS_PRESS(PAD_BUTTON_R))
355 {
356 cubu.scale += 64;
357 OS_Printf("Scale=%d Depth=%d\n", cubu.scale, cubu.depth);
358 }
359 else if (DEMO_IS_PRESS(PAD_BUTTON_L))
360 {
361 cubu.scale -= 64;
362 if (cubu.scale < 0)
363 {
364 cubu.scale = 0;
365 }
366 OS_Printf("Scale=%d Depth=%d\n", cubu.scale, cubu.depth);
367 }
368 if (DEMO_IS_PRESS(PAD_KEY_UP))
369 {
370 cubu.depth += 256;
371 if (cubu.depth > 0xffffff)
372 {
373 cubu.depth = 0xffffff;
374 }
375 OS_Printf("Scale=%d Depth=%d\n", cubu.scale, cubu.depth);
376 }
377 else if (DEMO_IS_PRESS(PAD_KEY_DOWN))
378 {
379 cubu.depth -= 256;
380 if (cubu.depth < 0)
381 {
382 cubu.depth = 0;
383 }
384 OS_Printf("Scale=%d Depth=%d\n", cubu.scale, cubu.depth);
385 }
386 if (DEMO_IS_TRIG(PAD_BUTTON_A))
387 {
388 cubu.trg = (cubu.trg + 1) & 0x01;
389 OS_Printf("PolygonAttr_1DotPoly=%s\n", (cubu.trg ? "ON" : "OFF"));
390 }
391 if (DEMO_IS_TRIG(PAD_BUTTON_START))
392 {
393 cubu.scale = FX32_ONE;
394 cubu.depth = 16384;
395 OS_Printf("Scale=%d Depth=%d\n", cubu.scale, cubu.depth);
396 }
397 if (DEMO_IS_TRIG(PAD_BUTTON_SELECT))
398 {
399 fx16 s = FX_SinIdx(cubu.rotate);
400 fx16 c = FX_CosIdx(cubu.rotate);
401
402 G3_Translate(-FX32_ONE, 0, -4 * FX32_ONE);
403
404 G3_RotX(s, c);
405 G3_RotY(s, c);
406 G3_RotZ(s, c);
407
408 G3_Scale(cubu.scale, cubu.scale, cubu.scale);
409
410 {
411 VecFx32 m;
412 fx32 w;
413
414 G3_PositionTest(FX16_ONE, FX16_ONE, FX16_ONE);
415 while (G3X_GetPositionTestResult(&m, &w))
416 {
417 // Wait for position test
418 }
419
420 OS_Printf("Position Test : Pos(%d, %d, %d) W(%d)\n", m.x, m.y, m.z, w);
421 cubu.depth = w;
422 }
423 }
424
425 /* Camera configuration */
426 {
427 VecFx32 Eye = { 0, 0, FX32_ONE }; // Eye position
428 VecFx32 at = { 0, 0, 0 }; // Viewpoint
429 VecFx32 vUp = { 0, FX32_ONE, 0 }; // Up
430
431 G3_LookAt(&Eye, &vUp, &at, NULL); // Eye point settings
432 }
433
434 G3_MtxMode(GX_MTXMODE_TEXTURE); // Set matrix to texture mode
435 G3_Identity(); // Initialize current matrix to a unit matrix
436 // The matrix is set to Position-Vector simultaneous set mode
437 G3_MtxMode(GX_MTXMODE_POSITION_VECTOR);
438
439 /* Draw cube */
440 Cube(&cubu, FX32_ONE, 0, -2 * FX32_ONE);
441 Cube(&cubu, 0, 0, -3 * FX32_ONE);
442 Cube(&cubu, -FX32_ONE, 0, -4 * FX32_ONE);
443
444 // Swapping the polygon list RAM, the vertex RAM, etc.
445 G3_SwapBuffers(GX_SORTMODE_AUTO, GX_BUFFERMODE_W);
446
447 /* V-Blank wait */
448 OS_WaitVBlankIntr();
449
450 #ifdef SDK_AUTOTEST // For auto test
451 GX_SetBankForLCDC(GX_VRAM_LCDC_C);
452 EXT_TestSetVRAMForScreenShot(GX_VRAM_LCDC_C);
453 EXT_TestScreenShot(150, 0xA00DF599);
454 EXT_TestTickCounter();
455 #endif //SDK_AUTOTEST
456
457 }
458 }
459