1 /*---------------------------------------------------------------------------*
2 Project: TwlSDK - MB - demos - multiboot
3 File: dispfunc.c
4
5 Copyright 2006-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 #include <nitro.h>
19 #include <string.h>
20
21 #include "dispfunc.h"
22
23 /*
24 =================================================================================
25
26 OBJ character drawing
27
28 =================================================================================
29 */
30
31 // --- global value
32 GXOamAttr oamBak[128];
33
34 // --- constant value
35 static const char NumString[] = "0123456789ABCDEF";
36
37
38 // Set OBJ
ObjSet(int objNo,int x,int y,int charNo,int paletteNo)39 void ObjSet(int objNo, int x, int y, int charNo, int paletteNo)
40 {
41 G2_SetOBJAttr((GXOamAttr *)&oamBak[objNo],
42 x,
43 y,
44 0,
45 GX_OAM_MODE_NORMAL,
46 FALSE,
47 GX_OAM_EFFECT_NONE, GX_OAM_SHAPE_8x8, GX_OAM_COLOR_16, charNo, paletteNo, 0);
48 }
49
50 // Set OBJ character string
ObjSetString(int startobjNo,int x,int y,char * string,int paletteNo)51 void ObjSetString(int startobjNo, int x, int y, char *string, int paletteNo)
52 {
53 int i;
54 for (i = 0; string[i] != 0 && i < 24; i++)
55 {
56 ObjSet(startobjNo + i, x + i * 8, y, (int)string[i], paletteNo);
57 }
58 }
59
60 // Clears OBJ
ObjClear(int objNo)61 void ObjClear(int objNo)
62 {
63 ObjSet(objNo, 256 * 8, 192 * 8, 0, 0);
64 }
65
66 // Clears OBJ (specified range)
ObjClearRange(int start,int end)67 void ObjClearRange(int start, int end)
68 {
69 int i;
70 for (i = start; i <= end; i++)
71 ObjClear(i);
72 }
73
74
75 // Set message
ObjSetMessage(int objNo,char * message)76 void ObjSetMessage(int objNo, char *message)
77 {
78 ObjSetString(objNo, 4 * 8, 22 * 8, message, WHITE);
79 }
80
81 /*
82 =================================================================================
83
84 BG character drawing (BG0 fixed)
85
86 =================================================================================
87 */
88
89
90 #define BG_LINES (24)
91 #define PROMPT ">"
92
93 // --- static value
94 static u16 vscr[32 * 32] ATTRIBUTE_ALIGN(32); // Virtual screen
95 static u16 vscr_sub[32 * 32] ATTRIBUTE_ALIGN(32); // Virtual screen (sub)
96 static u16 cur_line = 0;
97
98 // --- static functions
99 static void BgiPutChar(s16 x, s16 y, u8 palette, char c, u8 lcd);
100 static void BgiPutStringN(s16 x, s16 y, u8 palette, char *text, u32 num, u8 lcd);
101
102
BgiPutChar(s16 x,s16 y,u8 palette,char c,u8 lcd)103 static void BgiPutChar(s16 x, s16 y, u8 palette, char c, u8 lcd)
104 {
105 if (lcd)
106 {
107 vscr[((y * 32) + x) % (32 * 32)] = (u16)((palette << 12) | c);
108 }
109 else
110 {
111 vscr_sub[((y * 32) + x) % (32 * 32)] = (u16)((palette << 12) | c);
112 }
113 }
114
BgiPutStringN(s16 x,s16 y,u8 palette,char * text,u32 num,u8 lcd)115 static void BgiPutStringN(s16 x, s16 y, u8 palette, char *text, u32 num, u8 lcd)
116 {
117 s32 i;
118
119 for (i = 0; i < num; i++)
120 {
121 if (text[i] == 0x00)
122 {
123 break;
124 }
125
126 BgiPutChar((s16)(x + i), y, palette, text[i], lcd);
127 }
128
129 }
130
131 /*
132 --- initialize
133 */
BgInitForPrintStr(void)134 void BgInitForPrintStr(void)
135 {
136 // Main lcd
137 GX_SetBankForBG(GX_VRAM_BG_64_E);
138 G2_SetBG0Control(GX_BG_SCRSIZE_TEXT_256x256, GX_BG_COLORMODE_16, GX_BG_SCRBASE_0xf000, // SCR base block 31
139 GX_BG_CHARBASE_0x00000, // CHR base block 0
140 GX_BG_EXTPLTT_01);
141 G2_SetBG0Priority(0);
142 G2_BG0Mosaic(FALSE);
143 GX_SetGraphicsMode(GX_DISPMODE_GRAPHICS, GX_BGMODE_0, GX_BG0_AS_2D);
144
145 GX_LoadBG0Char(sampleCharData, 0, sizeof(sampleCharData));
146 GX_LoadBGPltt(samplePlttData, 0, sizeof(samplePlttData));
147
148 MI_CpuFillFast((void *)vscr, 0, sizeof(vscr));
149 DC_FlushRange(vscr, sizeof(vscr));
150 /* I/O register is accessed using DMA operation, so cache wait is not needed */
151 // DC_WaitWriteBufferEmpty();
152 GX_LoadBG0Scr(vscr, 0, sizeof(vscr));
153
154 // Sub lcd
155 GX_SetBankForSubBG(GX_VRAM_SUB_BG_128_C);
156 G2S_SetBG0Control(GX_BG_SCRSIZE_TEXT_256x256, GX_BG_COLORMODE_16, GX_BG_SCRBASE_0xf800, // SCR base block 31
157 GX_BG_CHARBASE_0x10000, // CHR base block 0
158 GX_BG_EXTPLTT_01);
159 G2S_SetBG0Priority(0);
160 G2S_BG0Mosaic(FALSE);
161 GXS_SetGraphicsMode(GX_BGMODE_0);
162
163 GXS_LoadBG0Char(sampleCharData, 0, sizeof(sampleCharData));
164 GXS_LoadBGPltt(samplePlttData, 0, sizeof(samplePlttData));
165 MI_CpuFillFast((void *)vscr_sub, 0, sizeof(vscr_sub));
166 DC_FlushRange(vscr_sub, sizeof(vscr_sub));
167 /* I/O register is accessed using DMA operation, so cache wait is not needed */
168 // DC_WaitWriteBufferEmpty();
169 GXS_LoadBG0Scr(vscr_sub, 0, sizeof(vscr_sub));
170
171 cur_line = 0;
172 }
173
174 /*
175 --- for main LCD
176 */
177
178 // Formatted character string output
BgPrintf(s16 x,s16 y,u8 palette,char * text,...)179 void BgPrintf(s16 x, s16 y, u8 palette, char *text, ...)
180 {
181 va_list vlist;
182 char temp[32 * 2 + 2];
183
184 MI_CpuClear8(&temp[0], sizeof(temp));
185
186 va_start(vlist, text);
187 (void)OS_VSNPrintf(temp, 32 * 2 + 2, text, vlist);
188 va_end(vlist);
189
190 BgPutString(x, y, palette, temp);
191 }
192
193
194 // String output
BgPutString(s16 x,s16 y,u8 palette,char * text)195 void BgPutString(s16 x, s16 y, u8 palette, char *text)
196 {
197 BgPutStringN(x, y, palette, text, 32);
198 }
199
200 // Character string output with the character number restriction
BgPutStringN(s16 x,s16 y,u8 palette,char * text,u32 num)201 void BgPutStringN(s16 x, s16 y, u8 palette, char *text, u32 num)
202 {
203 BgiPutStringN(x, y, palette, text, num, 1);
204 }
205
206
207 // 1 character output
BgPutChar(s16 x,s16 y,u8 palette,char c)208 void BgPutChar(s16 x, s16 y, u8 palette, char c)
209 {
210 BgiPutChar(x, y, palette, c, 1);
211 }
212
213 // Clear BG
BgClear(void)214 void BgClear(void)
215 {
216 MI_CpuClearFast((void *)vscr, sizeof(vscr));
217 }
218
219 /*
220 --- for sub LCD
221 */
222
223 // Formatted character string output
BgPrintfSub(s16 x,s16 y,u8 palette,char * text,...)224 void BgPrintfSub(s16 x, s16 y, u8 palette, char *text, ...)
225 {
226 va_list vlist;
227 char temp[32 + 2];
228
229 MI_CpuClear8(&temp[0], sizeof(temp));
230
231 va_start(vlist, text);
232 (void)OS_VSNPrintf(temp, 33, text, vlist);
233 va_end(vlist);
234
235 BgPutStringSub(x, y, palette, temp);
236 }
237
238 // String output
BgPutStringSub(s16 x,s16 y,u8 palette,char * text)239 void BgPutStringSub(s16 x, s16 y, u8 palette, char *text)
240 {
241 BgPutStringNSub(x, y, palette, text, 32);
242 }
243
244 // Character string output with the character number restriction
BgPutStringNSub(s16 x,s16 y,u8 palette,char * text,u32 num)245 void BgPutStringNSub(s16 x, s16 y, u8 palette, char *text, u32 num)
246 {
247 BgiPutStringN(x, y, palette, text, num, 0);
248 }
249
250 // 1 character output
BgPutCharSub(s16 x,s16 y,u8 palette,char c)251 void BgPutCharSub(s16 x, s16 y, u8 palette, char c)
252 {
253 BgiPutChar(x, y, palette, c, 0);
254 }
255
256 // Clear BG
BgClearSub(void)257 void BgClearSub(void)
258 {
259 MI_CpuClearFast((void *)vscr_sub, sizeof(vscr_sub));
260 }
261
262 /*
263 --- v blank process
264 */
265
BgScrSetVblank(void)266 void BgScrSetVblank(void)
267 {
268 // Reflect virtual screen in VRAM
269 DC_FlushRange(vscr, sizeof(vscr));
270 /* I/O register is accessed using DMA operation, so cache wait is not needed */
271 // DC_WaitWriteBufferEmpty();
272 GX_LoadBG0Scr(vscr, 0, sizeof(vscr));
273 DC_FlushRange(vscr_sub, sizeof(vscr_sub));
274 /* I/O register is accessed using DMA operation, so cache wait is not needed */
275 // DC_WaitWriteBufferEmpty();
276 GXS_LoadBG0Scr(vscr_sub, 0, sizeof(vscr_sub));
277 }
278
279
280 /*
281 --- message print
282 */
283
284 // Output message
BgSetMessage(u8 palette,char * message,...)285 void BgSetMessage(u8 palette, char *message, ...)
286 {
287 va_list vlist;
288 char temp[32 * 2 + 2];
289 MI_CpuClear8(&temp[0], sizeof(temp));
290
291 va_start(vlist, message);
292 (void)OS_VSNPrintf(temp, 32 * 2 + 2, message, vlist);
293 va_end(vlist);
294
295 BgPutString(4, 22, palette, " ");
296 BgPutString(4, 22, palette, temp);
297
298
299 BgSetMessageLogSub(palette, temp);
300
301 }
302
BgSetMessageSub(u8 palette,char * message,...)303 void BgSetMessageSub(u8 palette, char *message, ...)
304 {
305 va_list vlist;
306 char temp[32 + 2];
307 MI_CpuClear8(&temp[0], sizeof(temp));
308
309 va_start(vlist, message);
310 (void)OS_VSNPrintf(temp, 33, message, vlist);
311 va_end(vlist);
312
313 BgSetMessageLogSub(palette, temp);
314 }
315
316 // Output message log on sub LCD
BgSetMessageLogSub(u8 palette,char * text)317 void BgSetMessageLogSub(u8 palette, char *text)
318 {
319 if (cur_line == BG_LINES)
320 {
321 MI_CpuCopy16((void *)&vscr_sub[1 * 32], (void *)vscr_sub,
322 sizeof(u16) * 32 * (BG_LINES - 1));
323 cur_line--;
324 }
325
326 BgPutStringSub(0, (s16)cur_line, palette, " ");
327 BgPutStringSub(0, (s16)cur_line, palette, PROMPT);
328 BgPutStringSub((s16)(1 + strlen(PROMPT)), (s16)cur_line, palette, text);
329
330 if (cur_line < BG_LINES)
331 cur_line++;
332 }
333
334 // Get main LCD screen buffer
BgGetScreenBuf(void)335 u16 *BgGetScreenBuf(void)
336 {
337 return (u16 *)vscr;
338 }
339
340 // Get sub LCD screen buffer
BgGetScreenBufSub(void)341 u16 *BgGetScreenBufSub(void)
342 {
343 return (u16 *)vscr_sub;
344 }
345