1 /*---------------------------------------------------------------------------*
2 Project: TwlSDK - GX - demos - UnitTours/2D_CharBg_Direct
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-17#$
14 $Rev: 8556 $
15 $Author: okubata_ryoma $
16 *---------------------------------------------------------------------------*/
17
18 //---------------------------------------------------------------------------
19 // A sample that use direct color BITMAP BG:
20 //
21 // This sample display picture on the display by direct color BITMAP BG
22 //
23 // USAGE:
24 // UP, DOWN, LEFT, RIGHT : Slide the BG
25 // A, B : Scale the BG
26 // L, R : Rotate the BG
27 // SELECT + [UP, DOWN, LEFT, RIGHT] : Change the center of rotation
28 // SELECT : Toggle the BG area over mode between
29 // loop and transparent
30 //
31 // HOWTO:
32 // 1. Transfer the bitmap data with GX_LoadBGxScr
33 // 2. Set the direct color BG mode with G2_SetBGxControlDCBmp
34 //---------------------------------------------------------------------------
35
36
37 #ifdef SDK_TWL
38 #include <twl.h>
39 #else
40 #include <nitro.h>
41 #endif
42 #include "DEMO.h"
43 #include "data.h"
44 //---------------------------------------------------------------------------
45 // Summary:
46 // V-Blank interrupt process
47 // Description:
48 // Enables a flag that confirms that a V-Blank interrupt has been performed
49 //
50 // The following steps will be performed during common initialization (DEMOInitCommon), causing this function to be called during V-Blanks
51 // * Select IRQ interrupt (OS_SetIrqMask)
52 // * Register this function, which performs IRQ interrupts (OS_SetIRQFunction)
53 // * Enable IRQ interrupts (OS_EnableIrq)
54 //
55 //---------------------------------------------------------------------------
VBlankIntr(void)56 void VBlankIntr(void)
57 {
58 OS_SetIrqCheckFlag(OS_IE_V_BLANK); // Sets a V-Blank interrupt confirmation flag
59 }
60
61 //---------------------------------------------------------------------------
62 // Summary:
63 // Display affine extended direct color bit map BG
64 // Description:
65 // Performs affine conversions (rotate / scale) on a 256-color bitmap background and displays the result
66 //
67 //
68 // 1. Use BG surface 3 with BGMODE number 3
69 // 2. Perform the configuration in G2_SetBG3ControlDCBmp, and transmit the character data to the specified location
70 //
71 // 3. Transfer screen data to the specified location
72 // Controls:
73 // PLUS_KEY : BG screen offset operation
74 // SELECT + PLUS_KEY: Manipulate center position for rotating and scaling
75 // BUTTON_A, B : Enlarge, reduce
76 // BUTTON_L, R : Rotate
77 // SELECT : Area over process switch
78 // START : Initialize settings values
79 //---------------------------------------------------------------------------
80 #ifdef SDK_TWL
TwlMain(void)81 void TwlMain(void)
82 #else
83 void NitroMain(void)
84 #endif
85 {
86 int trg = 0;
87 int offset_H = 0;
88 int offset_V = 30;
89 fx32 scale = FX32_ONE;
90 s16 x_0 = 0, y_0 = 0;
91 s16 x_1 = 0, y_1 = 0;
92 u16 rotate = 0;
93
94 GXBGAreaOver area_over = GX_BG_AREAOVER_XLU;
95
96 //---------------------
97 // Initialization
98 //---------------------
99 DEMOInitCommon();
100 DEMOInitVRAM();
101
102 /* BG configuration */
103 GX_SetBankForBG(GX_VRAM_BG_256_AB); // Allocate VRAM-A, B banks to BG
104
105 GX_SetGraphicsMode(GX_DISPMODE_GRAPHICS, // 2D/3D mode
106 GX_BGMODE_3, // BGMODE 3
107 GX_BG0_AS_2D); // 2D display to BG0
108
109 GX_SetBGScrOffset(GX_BGSCROFFSET_0x00000); // Set screen offset value
110 GX_SetBGCharOffset(GX_BGCHAROFFSET_0x10000); // Set character offset
111
112 GX_SetVisiblePlane(GX_PLANEMASK_BG3); // Select BG3 for display
113 G2_SetBG3Priority(0); // Set BG3 priority to top
114 G2_BG3Mosaic(FALSE); // Do not apply mosaic to BG3
115
116 /* Set BG3 to a screen size of 256x256 dots, and a direct color bitmap */
117 {
118 // Set BG3 to direct color bitmap BG
119 // Screen size: Use a screen size of 256x256 pixels
120 // Area overflow processing: Determined by area_over
121 // Screen base block: 0x00000
122 G2_SetBG3ControlDCBmp(GX_BG_SCRSIZE_DCBMP_256x256, area_over, GX_BG_BMPSCRBASE_0x00000);
123 }
124
125 /* Transfer bitmap data to BG3 */
126 GX_LoadBG3Bmp(bitmapBG_directcolor_Texel, 0, SCREEN_SIZE);
127
128 DEMOStartDisplay();
129
130 //---------------------
131 // Main loop
132 //---------------------
133 while (1)
134 {
135 MtxFx22 mtx;
136
137 /* Reading pad information and controls */
138 DEMOReadKey();
139
140 #ifdef SDK_AUTOTEST // Code for auto-test
141 {
142 const EXTKeys keys[8] =
143 { {PAD_BUTTON_A, 10}, {PAD_BUTTON_L, 10}, {PAD_KEY_UP | PAD_KEY_RIGHT, 20} };
144 EXT_AutoKeys(keys, &gKeyWork.press, &gKeyWork.trigger);
145 }
146 #endif
147
148 if (DEMO_IS_PRESS(PAD_BUTTON_SELECT))
149 {
150 if (DEMO_IS_PRESS(PAD_KEY_UP))
151 y_0 -= 2;
152 if (DEMO_IS_PRESS(PAD_KEY_DOWN))
153 y_0 += 2;
154 if (DEMO_IS_PRESS(PAD_KEY_RIGHT))
155 x_0 += 2;
156 if (DEMO_IS_PRESS(PAD_KEY_LEFT))
157 x_0 -= 2;
158 }
159 else
160 {
161 if (DEMO_IS_PRESS(PAD_KEY_UP))
162 offset_V += 2;
163 if (DEMO_IS_PRESS(PAD_KEY_DOWN))
164 offset_V -= 2;
165 if (DEMO_IS_PRESS(PAD_KEY_RIGHT))
166 offset_H -= 2;
167 if (DEMO_IS_PRESS(PAD_KEY_LEFT))
168 offset_H += 2;
169 }
170 if (DEMO_IS_PRESS(PAD_BUTTON_A))
171 scale += 2 << (FX32_SHIFT - 8);
172 if (DEMO_IS_PRESS(PAD_BUTTON_B))
173 scale -= 2 << (FX32_SHIFT - 8);
174 if (DEMO_IS_PRESS(PAD_BUTTON_L))
175 rotate -= 256;
176 if (DEMO_IS_PRESS(PAD_BUTTON_R))
177 rotate += 256;
178 if (DEMO_IS_TRIG(PAD_BUTTON_SELECT))
179 {
180 trg = (trg + 1) & 0x01;
181 OS_Printf("area_over=%d\n", trg);
182 }
183
184 if (DEMO_IS_TRIG(PAD_BUTTON_START))
185 {
186 offset_H = 0;
187 offset_V = 0;
188 x_0 = 32;
189 y_0 = 32;
190 scale = 1 << FX32_SHIFT;
191 rotate = 0;
192 }
193
194 /* Set BG3 to a screen size of 256x256 dots, and a direct color bitmap */
195 {
196 GXBGAreaOver area_over = (trg ? GX_BG_AREAOVER_REPEAT : GX_BG_AREAOVER_XLU);
197
198 // Set BG3 to direct color bitmap BG
199 // Screen size: Use a screen size of 256x256 pixels
200 // Area overflow processing: Determined by area_over
201 // Screen base block: 0x00000
202 G2_SetBG3ControlDCBmp(GX_BG_SCRSIZE_DCBMP_256x256, area_over, GX_BG_BMPSCRBASE_0x00000);
203 }
204
205 /* Generate affine conversion matrix */
206 {
207 fx16 sinVal = FX_SinIdx(rotate);
208 fx16 cosVal = FX_CosIdx(rotate);
209 fx32 rScale = FX_Inv(scale);
210
211 mtx._00 = (fx32)((cosVal * rScale) >> FX32_SHIFT);
212 mtx._01 = (fx32)((sinVal * rScale) >> FX32_SHIFT);
213 mtx._10 = -(fx32)((sinVal * rScale) >> FX32_SHIFT);
214 mtx._11 = (fx32)((cosVal * rScale) >> FX32_SHIFT);
215 }
216
217 #ifdef SDK_AUTOTEST // Code for auto-test
218 GX_SetBankForLCDC(GX_VRAM_LCDC_C);
219 EXT_TestSetVRAMForScreenShot(GX_VRAM_LCDC_C);
220 EXT_TestScreenShot(100, 0x874F90B5);
221 EXT_TestTickCounter();
222 #endif //SDK_AUTOTEST
223
224 /* V-Blank wait */
225 OS_WaitVBlankIntr();
226
227 /* configure the affine conversion that is applied to the BG3 surface */
228 G2_SetBG3Affine(&mtx, // Conversion matrix
229 x_0, // Rotation center (x) coordinate
230 y_0, // Rotation center (y) coordinate
231 offset_H, // Pre-rotation coordinate (x)
232 offset_V); // Pre-rotation coordinate (y)
233 }
234 }
235