1 /*---------------------------------------------------------------------------*
2 Project: Dolphin/Revolution gx demo
3 File: mgt-single-buf.c
4
5 Copyright 1998-2006 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
14 #include <demo.h>
15
16 /*---------------------------------------------------------------------------*
17 The macro ATTRIBUTE_ALIGN provides a convenient way to align initialized
18 arrays. Alignment of vertex arrays to 32B IS NOT required, but may result
19 in a slight performance improvement.
20 *---------------------------------------------------------------------------*/
21 f32 Verts_f32[] ATTRIBUTE_ALIGN(32) =
22 {
23 // x, y, z
24 0.0f, 0.0f, 1.0f, // 0:0
25 0.0f, 1.0f, 0.0f, // 0:1
26 1.0f, 0.0f, 0.0f, // 0:2
27 0.0f, 0.0f, 1.0f, // 1:0
28 -1.0f, 0.0f, 0.0f, // 1:1
29 0.0f, 1.0f, 0.0f, // 1:2
30 0.0f, 0.0f, 1.0f, // 2:0
31 0.0f, -1.0f, 0.0f, // 2:1
32 -1.0f, 0.0f, 0.0f, // 2:2
33 0.0f, 0.0f, 1.0f, // 3:0
34 1.0f, 0.0f, 0.0f, // 3:1
35 0.0f, -1.0f, 0.0f, // 3:2
36 0.0f, 0.0f, -1.0f, // 4:0
37 1.0f, 0.0f, 0.0f, // 4:1
38 0.0f, 1.0f, 0.0f, // 4:2
39 0.0f, 0.0f, -1.0f, // 5:0
40 0.0f, 1.0f, 0.0f, // 5:1
41 -1.0f, 0.0f, 0.0f, // 5:2
42 0.0f, 0.0f, -1.0f, // 6:0
43 -1.0f, 0.0f, 0.0f, // 6:1
44 0.0f, -1.0f, 0.0f, // 6:2
45 0.0f, 0.0f, -1.0f, // 7:0
46 0.0f, -1.0f, 0.0f, // 7:1
47 1.0f, 0.0f, 0.0f // 7:2
48 };
49
50 u8 Colors_rgba8[] ATTRIBUTE_ALIGN(32) =
51 {
52 // r, g, b, a
53 0, 0, 0, 255, // 0:0
54 0, 0, 0, 255, // 0:1
55 0, 0, 0, 255, // 0:2
56 255, 255, 255, 255, // 1:0
57 255, 255, 255, 255, // 1:1
58 255, 255, 255, 255, // 1:2
59 0, 0, 0, 255, // 2:0
60 0, 0, 0, 255, // 2:1
61 0, 0, 0, 255, // 2:2
62 255, 255, 255, 255, // 3:0
63 255, 255, 255, 255, // 3:1
64 255, 255, 255, 255, // 3:2
65 255, 255, 255, 255, // 4:0
66 255, 255, 255, 255, // 4:1
67 255, 255, 255, 255, // 4:2
68 0, 0, 0, 255, // 5:0
69 0, 0, 0, 255, // 5:1
70 0, 0, 0, 255, // 5:2
71 255, 255, 255, 255, // 6:0
72 255, 255, 255, 255, // 6:1
73 255, 255, 255, 255, // 6:2
74 0, 0, 0, 255, // 7:0
75 0, 0, 0, 255, // 7:1
76 0, 0, 0, 255 // 7:2
77 };
78
79
80 u32 ticks = 0; // time counter
81
82 GXBool do_copy = GX_FALSE;
83
84 /*---------------------------------------------------------------------------*
85 Forward references
86 *---------------------------------------------------------------------------*/
87
88 void VIPostCallback ( u32 retraceCount );
89 void main ( void );
90 static void CameraInit ( Mtx v );
91 static void DrawInit ( void );
92 static void DrawTick ( Mtx v );
93 static void AnimTick ( void );
94 static void PrintIntro ( void );
95
96 /*---------------------------------------------------------------------------*
97 VI Post Callback (VBlank interrupt)
98
99 We use a post callback (instead of a pre) because we don't need to
100 change any VI registers during the VBlank period.
101
102 *---------------------------------------------------------------------------*/
103
VIPostCallback(u32 retraceCount)104 void VIPostCallback ( u32 retraceCount )
105 {
106 #pragma unused (retraceCount)
107
108 if (do_copy) {
109 GXCopyDisp(DEMOGetCurrentBuffer(), GX_TRUE);
110 GXFlush();
111 do_copy = FALSE;
112 }
113 }
114
115 /*---------------------------------------------------------------------------*
116 Application main loop
117 *---------------------------------------------------------------------------*/
118
main(void)119 void main ( void )
120 {
121 Mtx v; // view matrix
122 PADStatus pad[PAD_MAX_CONTROLLERS]; // game pad state
123
124 pad[0].button = 0;
125
126 DEMOInit(NULL); // Init os, pad, gx, vi
127
128 CameraInit(v); // Initialize the camera.
129 DrawInit(); // Define my vertex formats and set array pointers.
130
131 PrintIntro(); // Print demo directions
132
133 (void) VISetPostRetraceCallback(VIPostCallback);
134 VISetNextFrameBuffer(DEMOGetCurrentBuffer());
135 VISetBlack(FALSE);
136 VIFlush();
137
138 while(!(pad[0].button & PAD_BUTTON_MENU))
139 {
140 DEMOBeforeRender();
141 DrawTick(v); // Draw the model.
142
143 GXDrawDone();
144 do_copy = GX_TRUE;
145 VIWaitForRetrace();
146
147 AnimTick(); // Update animation.
148 PADRead(pad);
149 }
150
151 OSHalt("End of demo");
152 }
153
154
155 /*---------------------------------------------------------------------------*
156 Functions
157 *---------------------------------------------------------------------------*/
158
159 /*---------------------------------------------------------------------------*
160 Name: CameraInit
161
162 Description: Initialize the projection matrix and load into hardware.
163 Initialize the view matrix.
164
165 Arguments: v view matrix
166
167 Returns: none
168 *---------------------------------------------------------------------------*/
CameraInit(Mtx v)169 static void CameraInit ( Mtx v )
170 {
171 Mtx44 p; // projection matrix
172 Vec up = {0.0F, 0.0F, 1.0F};
173 Vec camLoc = {0.25F, 3.0F, 0.5F};
174 Vec objPt = {0.0F, 0.0F, 0.0F};
175 f32 left = 0.0375F;
176 f32 top = 0.050F;
177 f32 znear = 0.1F;
178 f32 zfar = 10.0F;
179
180 MTXFrustum(p, left, -left, -top, top, znear, zfar);
181 GXSetProjection(p, GX_PERSPECTIVE);
182
183 MTXLookAt(v, &camLoc, &up, &objPt);
184 }
185
186 /*---------------------------------------------------------------------------*
187 Name: DrawInit
188
189 Description: Initializes the vertex attribute format 0, and sets
190 the array pointers and strides for the indexed data.
191
192 Arguments: none
193
194 Returns: none
195 *---------------------------------------------------------------------------*/
DrawInit(void)196 static void DrawInit( void )
197 {
198 GXColor blue = {0, 0, 255, 0};
199
200 GXSetCopyClear(blue, 0x00ffffff);
201
202 // Set current vertex descriptor to enable position and color0.
203 // Both use 8b index to access their data arrays.
204 GXClearVtxDesc();
205 GXSetVtxDesc(GX_VA_POS, GX_INDEX8);
206 GXSetVtxDesc(GX_VA_CLR0, GX_INDEX8);
207
208 // Position has 3 elements (x,y,z), each of type f32
209 GXSetVtxAttrFmt(GX_VTXFMT0, GX_VA_POS, GX_POS_XYZ, GX_F32, 0);
210
211 // Color 0 has 4 components (r, g, b, a), each component is 8b.
212 GXSetVtxAttrFmt(GX_VTXFMT0, GX_VA_CLR0, GX_CLR_RGBA, GX_RGBA8, 0);
213
214 // stride = 3 elements (x,y,z) each of type s16
215 GXSetArray(GX_VA_POS, Verts_f32, 3*sizeof(f32));
216 // stride = 4 elements (r,g,b,a) each of type u8
217 GXSetArray(GX_VA_CLR0, Colors_rgba8, 4*sizeof(u8));
218
219 // Initialize lighting, texgen, and tev parameters
220 GXSetNumChans(1); // default, color = vertex color
221 GXSetNumTexGens(0); // no texture in this demo
222 GXSetTevOrder(GX_TEVSTAGE0, GX_TEXCOORD_NULL, GX_TEXMAP_NULL, GX_COLOR0A0);
223 GXSetTevOp(GX_TEVSTAGE0, GX_PASSCLR);
224 }
225
226 /*---------------------------------------------------------------------------*
227 Name: Vertex
228
229 Description: Create my vertex format
230
231 Arguments: t 8-bit triangle index
232 v 8-bit vertex index
233
234 Returns: none
235 *---------------------------------------------------------------------------*/
Vertex(u8 t,u8 v)236 static inline void Vertex( u8 t, u8 v )
237 {
238 u8 tv = (u8) (3 * t + v);
239 GXPosition1x8(tv);
240 GXColor1x8(tv);
241 }
242
243 /*---------------------------------------------------------------------------*
244 Name: DrawTick
245
246 Description: Draw the model once.
247
248 Arguments: v view matrix
249
250 Returns: none
251 *---------------------------------------------------------------------------*/
DrawTick(Mtx v)252 static void DrawTick( Mtx v )
253 {
254 Mtx m; // Model matrix.
255 Mtx mv; // Modelview matrix.
256 u8 iTri; // index of triangle
257 u8 iVert; // index of vertex
258
259 GXSetNumTexGens( 0 );
260 GXSetNumTevStages( 1 );
261 GXSetTevOp( GX_TEVSTAGE0, GX_PASSCLR );
262
263 // model has a rotation about z axis
264 MTXRotDeg(m, 'z', 8 * ticks);
265 MTXConcat(v, m, mv);
266 GXLoadPosMtxImm(mv, GX_PNMTX0);
267
268 GXBegin(GX_TRIANGLES, GX_VTXFMT0, 24);
269
270 // for all triangles of octahedron, ...
271 for (iTri = 0; iTri < 8; ++iTri)
272 {
273 // for all vertices of triangle, ...
274 for (iVert = 0; iVert < 3; ++iVert)
275 {
276 Vertex(iTri, iVert);
277 }
278 }
279
280 GXEnd();
281 }
282
283 /*---------------------------------------------------------------------------*
284 Name: AnimTick
285
286 Description: Computes next time step.
287
288 Arguments: none
289
290 Returns: none
291 *---------------------------------------------------------------------------*/
AnimTick(void)292 static void AnimTick( void )
293 {
294 ticks++;
295 }
296
297 /*---------------------------------------------------------------------------*
298 Name: PrintIntro
299
300 Description: Prints the directions on how to use this demo.
301
302 Arguments: none
303
304 Returns: none
305 *---------------------------------------------------------------------------*/
PrintIntro(void)306 static void PrintIntro( void )
307 {
308 OSReport("\n\n******************************************\n");
309 OSReport("frb-single - double-buffer with only 1 XFB\n");
310 OSReport("******************************************\n");
311 OSReport("to quit:\n");
312 OSReport(" hit the start button\n");
313 OSReport("********************************\n");
314 }
315