Digimon World 3 decomp
The European version, SLES_039.36
Loading...
Searching...
No Matches
editor.c
Go to the documentation of this file.
1/* The deck editor: the list of the cards owned, and the deck being built; and
2 an idle task nothing creates */
3
5
6/* Creates the editor's windows: the title, the deck's name and counts of each
7 kind, the hint, the card under the cursor's name, numbers and text, the
8 list's lines and cursor, the same for the list's card, and the message */
10 s32 i;
11
12 children->title = createTextWindow(task->layer, 1, 0xC1, 0x17);
13 children->title->setDepth(children->title, task->depth - 1);
14 children->deckName = createTextWindow(task->layer, 1, 0x15, 0x18);
15 children->deckName->setDepth(children->deckName, task->depth - 1);
16 for (i = 0; i < 6; i++) {
17 children->kinds[i] = createTextWindow(task->layer, 1, 0x34 + i * 0x23, 0x29);
18 children->kinds[i]->setDepth(children->kinds[i], task->depth - 1);
19 }
20 children->hint = createTextWindow(task->layer, 1, 0x96, 0xCC);
21 children->cardName = createTextWindow(task->layer, 1, 0x96, 0xBD);
22 children->pointsLabel = createTextWindow(task->layer, 1, 0x115, 0x26);
23 children->points = createTextWindow(task->layer, 1, 0x126, 0x26);
24 children->effect = createTextWindow(task->layer, 1, 0x50, 0x17);
25 children->apLabel = createTextWindow(task->layer, 1, 0xCE, 0x17);
26 children->ap = createTextWindow(task->layer, 1, 0xF0, 0x17);
27 children->hpLabel = createTextWindow(task->layer, 1, 0xCE, 0x24);
28 children->hp = createTextWindow(task->layer, 1, 0xF0, 0x24);
29 for (i = 0; i < 8; i++) {
30 children->lines[i].name = createTextWindow(task->layer, 1, 0xA3, 0x27 + i * 0xE);
31 children->lines[i].name->setDepth(children->lines[i].name, task->depth - 1);
32 children->lines[i].label = createTextWindow(task->layer, 1, 0x111, 0x27 + i * 0xE);
33 children->lines[i].label->setDepth(children->lines[i].label, task->depth - 1);
34 children->lines[i].count = createTextWindow(task->layer, 1, 0x120, 0x27 + i * 0xE);
35 children->lines[i].count->setDepth(children->lines[i].count, task->depth - 1);
36 }
37 children->cursor = createCursor(task->layer, task->depth - 1, 0x89, 0x27);
38 children->cursor->setVisible(children->cursor, 0);
39 children->listCardName = createTextWindow(task->layer, 1, 0x88, 0xA1);
40 children->listPointsLabel = createTextWindow(task->layer, 1, 0x115, 0xA1);
41 children->listPoints = createTextWindow(task->layer, 1, 0x126, 0xA1);
42 children->listEffect = createTextWindow(task->layer, 1, 0x50, 0xB8);
43 children->listApLabel = createTextWindow(task->layer, 1, 0xCE, 0xB8);
44 children->listAp = createTextWindow(task->layer, 1, 0xF0, 0xB8);
45 children->listHpLabel = createTextWindow(task->layer, 1, 0xCE, 0xC5);
46 children->listHp = createTextWindow(task->layer, 1, 0xF0, 0xC5);
47 children->message = createTextWindow(task->layer, 1, 0x3E, 0x6B);
48 children->message->setLines(children->message, 2);
49}
50
51/* Shows the title, the deck's name and counts of each kind, the hint (taking
52 turns with another one) and the card under the cursor's name, with its
53 numbers or its text while the info panel is open; or hides them */
55 CardDrawer card;
56 s32 i;
57 s32 id;
58
59 if (show != 0) {
60 children->title->setString(children->title, FILE_CACHE.load(TEXT_FILE(TEXT_CARD_SHOP)), 4);
61 children->deckName->setString(children->deckName, GAME.decks[task->deck].name, -1);
62 for (i = 0; i < 6; i++) {
63 children->kinds[i]->setNumber(children->kinds[i], 0, task->screen->kinds[task->deck][i]);
64 children->kinds[i]->setRightAlign(children->kinds[i], 1);
65 }
66 id = task->blinkTime < 60 ? task->infoShown + 0x1C : 0x1F;
67 children->hint->setString(children->hint, FILE_CACHE.load(TEXT_FILE(TEXT_CARD_SHOP)), id);
68 id = GAME.decks[task->deck].cards[task->column + task->row * 9];
70 if (task->infoShown) {
71 initCardDrawer(&card);
72 card.setCard(id);
73 if (card.getKind()) {
74 children->pointsLabel->setVisible(children->pointsLabel, 0);
75 children->points->setVisible(children->points, 0);
77 children->apLabel->setVisible(children->apLabel, 0);
78 children->ap->setVisible(children->ap, 0);
79 children->hpLabel->setVisible(children->hpLabel, 0);
80 children->hp->setVisible(children->hp, 0);
81 } else {
83 children->points->setNumber(children->points, 0, card.card->points);
84 children->points->setRightAlign(children->points, 1);
85 if (id == 0x45 || id == 0x70 || id == 0x9B || id == 0xC6 || id == 0xF1) {
87 children->apLabel->setVisible(children->apLabel, 0);
88 children->ap->setVisible(children->ap, 0);
89 children->hpLabel->setVisible(children->hpLabel, 0);
90 children->hp->setVisible(children->hp, 0);
91 } else {
92 children->effect->setVisible(children->effect, 0);
93 children->apLabel->setString(children->apLabel, FILE_CACHE.load(TEXT_FILE(TEXT_CARD_SHOP)), 0x11);
94 children->ap->setNumber(children->ap, 0, card.card->ap);
95 children->ap->setRightAlign(children->ap, 1);
96 children->hpLabel->setString(children->hpLabel, FILE_CACHE.load(TEXT_FILE(TEXT_CARD_SHOP)), 0x12);
97 children->hp->setNumber(children->hp, 0, card.card->hp);
98 children->hp->setRightAlign(children->hp, 1);
99 }
100 }
101 } else {
102 children->pointsLabel->setVisible(children->pointsLabel, 0);
103 children->points->setVisible(children->points, 0);
104 children->effect->setVisible(children->effect, 0);
105 children->apLabel->setVisible(children->apLabel, 0);
106 children->ap->setVisible(children->ap, 0);
107 children->hpLabel->setVisible(children->hpLabel, 0);
108 children->hp->setVisible(children->hp, 0);
109 }
110 } else {
111 children->title->setVisible(children->title, 0);
112 children->deckName->setVisible(children->deckName, 0);
113 for (i = 0; i < 6; i++) {
114 children->kinds[i]->setVisible(children->kinds[i], 0);
115 }
116 children->hint->setVisible(children->hint, 0);
117 children->cardName->setVisible(children->cardName, 0);
118 children->pointsLabel->setVisible(children->pointsLabel, 0);
119 children->points->setVisible(children->points, 0);
120 children->effect->setVisible(children->effect, 0);
121 children->apLabel->setVisible(children->apLabel, 0);
122 children->ap->setVisible(children->ap, 0);
123 children->hpLabel->setVisible(children->hpLabel, 0);
124 children->hp->setVisible(children->hp, 0);
125 }
126}
127
128/* Shows the eight lines of the list of the cards owned from listTop (each card's
129 name and how many are not in the deck), or hides them */
131 s32 i;
132 s32 id;
133
134 if (show != 0) {
135 for (i = 0; i < 8; i++) {
136 id = task->list[task->listTop + i];
137 if (id != 0) {
138 children->lines[i].name->setString(children->lines[i].name, FILE_CACHE.load(TEXT_FILE(TEXT_CARD_NAMES)), id);
139 children->lines[i].label->setString(children->lines[i].label, FILE_CACHE.load(TEXT_FILE(TEXT_CARD_SHOP)), 8);
140 children->lines[i].count->setNumber(children->lines[i].count, 0, task->owned[id]);
141 children->lines[i].count->setRightAlign(children->lines[i].count, 1);
142 } else {
143 children->lines[i].name->setVisible(children->lines[i].name, 0);
144 children->lines[i].label->setVisible(children->lines[i].label, 0);
145 children->lines[i].count->setVisible(children->lines[i].count, 0);
146 }
147 }
148 } else {
149 for (i = 0; i < 8; i++) {
150 children->lines[i].name->setVisible(children->lines[i].name, 0);
151 children->lines[i].label->setVisible(children->lines[i].label, 0);
152 children->lines[i].count->setVisible(children->lines[i].count, 0);
153 }
154 }
155}
156
157/* Shows the list's card under the cursor: its name and its numbers or its text, or hides them */
159 CardDrawer card;
160 s32 id;
161
162 if (show != 0) {
163 id = task->list[task->listTop + task->listCursor];
165 initCardDrawer(&card);
166 card.setCard(id);
167 if (card.getKind()) {
168 children->listPointsLabel->setVisible(children->listPointsLabel, 0);
169 children->listPoints->setVisible(children->listPoints, 0);
171 children->listApLabel->setVisible(children->listApLabel, 0);
172 children->listAp->setVisible(children->listAp, 0);
173 children->listHpLabel->setVisible(children->listHpLabel, 0);
174 children->listHp->setVisible(children->listHp, 0);
175 } else {
177 children->listPoints->setNumber(children->listPoints, 0, card.card->points);
178 children->listPoints->setRightAlign(children->listPoints, 1);
179 if (id == 0x45 || id == 0x70 || id == 0x9B || id == 0xC6 || id == 0xF1) {
181 children->listApLabel->setVisible(children->listApLabel, 0);
182 children->listAp->setVisible(children->listAp, 0);
183 children->listHpLabel->setVisible(children->listHpLabel, 0);
184 children->listHp->setVisible(children->listHp, 0);
185 } else {
186 children->listEffect->setVisible(children->listEffect, 0);
188 children->listAp->setNumber(children->listAp, 0, card.card->ap);
189 children->listAp->setRightAlign(children->listAp, 1);
191 children->listHp->setNumber(children->listHp, 0, card.card->hp);
192 children->listHp->setRightAlign(children->listHp, 1);
193 }
194 }
195 } else {
196 children->listCardName->setVisible(children->listCardName, 0);
197 children->listPointsLabel->setVisible(children->listPointsLabel, 0);
198 children->listPoints->setVisible(children->listPoints, 0);
199 children->listEffect->setVisible(children->listEffect, 0);
200 children->listApLabel->setVisible(children->listApLabel, 0);
201 children->listAp->setVisible(children->listAp, 0);
202 children->listHpLabel->setVisible(children->listHpLabel, 0);
203 children->listHp->setVisible(children->listHp, 0);
204 }
205}
206
207/* Lists the cards owned but not in the deck: owned holds each card's copies
208 left over, list the cards that have some (listCount of them) */
210 s32 i;
211 s32 n;
212 s16 *cards;
213
214 for (i = 0; i < 315; i++) {
215 task->list[i] = 0;
216 task->owned[i] = GAME.cards[i];
217 }
218 cards = GAME.decks[task->deck].cards;
219 for (n = 0; n < 40; n++, cards++) {
220 task->owned[*cards]--;
221 }
222 task->listCount = 0;
223 for (i = 0, n = 0; i < 315; i++) {
224 if (task->owned[i] > 0) {
225 task->list[n++] = i;
226 task->listCount++;
227 }
228 }
229}
230
231/* Draws the editor: the cursor on the deck's grid, the info panel, the deck's
232 panel, the list of the cards owned with their icons and scroll arrows,
233 the list card's panel and the message's panel, as they open */
235 SpriteDrawer sprite;
236 CardDrawer card;
237 s32 i;
238 s32 id;
239 s32 kind;
240
241 initSpriteDrawer(&sprite);
242 sprite.setTexture(0x280, 0);
243 sprite.setLayerId(task->layer, task->depth - 2);
244 if (task->cursorShown) {
245 if (GFX.funcs.getTime() - task->cursorTime >= 5) {
246 task->cursorTime = GFX.funcs.getTime();
247 if (++task->cursorFrame >= 6) {
248 task->cursorFrame = 0;
249 }
250 }
252 sprite.draw(FILE_CACHE.getEntry(STCRDDEK_SPRITES), 0x43, (task->column << 5) | 0x10, (task->row << 5) + 0x3A);
253 sprite.setClutRow(0);
254 }
255 if (task->panels[1].level != 0) {
256 if (task->panels[1].level != ONE) {
257 sprite.setScale(task->panels[1].level, ONE, ONE);
258 sprite.setPivot(0x140, 0x25);
259 }
260 initCardDrawer(&card);
261 id = GAME.decks[task->deck].cards[task->column + task->row * 9];
262 card.setCard(id);
263 kind = card.getKind();
264 if (kind) {
265 sprite.draw(FILE_CACHE.getEntry(STCRDDEK_SPRITES), kind + 0x11, 0x103, 0x24);
266 sprite.draw(FILE_CACHE.getEntry(STCRDDEK_SPRITES), 0xD, 0xFC, 0x22);
267 sprite.draw(FILE_CACHE.getEntry(STCRDDEK_SPRITES), 0xB, 0x4A, 0x12);
268 } else {
269 kind = card.card->color;
270 sprite.draw(FILE_CACHE.getEntry(STCRDDEK_SPRITES), kind + 0x13, 0x103, 0x24);
271 sprite.draw(FILE_CACHE.getEntry(STCRDDEK_SPRITES), 0xD, 0xFC, 0x22);
272 if (id == 0x45 || id == 0x70 || id == 0x9B || id == 0xC6 || id == 0xF1) {
273 sprite.draw(FILE_CACHE.getEntry(STCRDDEK_SPRITES), 0xB, 0x4A, 0x12);
274 } else {
275 sprite.draw(FILE_CACHE.getEntry(STCRDDEK_SPRITES), 0xC, 0xC7, 0x12);
276 }
277 }
278 }
279 if (task->panels[0].level != 0) {
280 sprite.setScale(ONE, task->panels[0].level, ONE);
281 if (task->panels[0].level != ONE) {
282 sprite.setPivot(0xA0, 0x74);
283 }
284 sprite.setLayerId(task->layer, task->depth);
285 sprite.draw(FILE_CACHE.getEntry(STCRDDEK_SPRITES), 0x40, 0x10, 0x15);
286 }
287 initSpriteDrawer(&sprite);
288 sprite.setTexture(0x280, 0);
289 sprite.setLayerId(task->layer, task->depth);
290 if (task->panels[2].level != 0) {
291 if (task->panels[2].level != ONE) {
292 sprite.setScale(task->panels[2].level, ONE, ONE);
293 sprite.setPivot(0x140, 0x5C);
294 } else {
295 /* the match depends on i being set before initCardDrawer */
296 i = 0;
297 initCardDrawer(&card);
298 for (; i < 8; i++) {
299 id = task->list[task->listTop + i];
300 if (id != 0) {
301 card.setCard(id);
302 if (card.getKind()) {
303 sprite.setClutRow(card.card->color - 1);
304 sprite.draw(FILE_CACHE.getEntry(STCRDDEK_SPRITES), 0x4B, 0x94, 0x27 + i * 14);
305 } else {
306 sprite.setClutRow(0);
307 sprite.draw(FILE_CACHE.getEntry(STCRDDEK_SPRITES), card.card->color + 0x4B, 0x94, 0x27 + i * 14);
308 }
309 sprite.setClutRow(0);
310 sprite.draw(FILE_CACHE.getEntry(STCRDDEK_SPRITES), 0x31, 0x94, 0x27 + i * 14);
311 }
312 }
313 if (task->listCount >= 9) {
314 if (GFX.funcs.getTime() - task->arrowTime >= 9) {
315 task->arrowTime = GFX.funcs.getTime();
316 task->arrowsShown = 1 - task->arrowsShown;
317 }
318 if (task->arrowsShown) {
319 if (task->listTop > 0) {
320 sprite.draw(FILE_CACHE.getEntry(STCRDDEK_SPRITES), 0x45, 0x126, 0x22);
321 }
322 if (task->listTop < task->listCount - 8) {
323 sprite.draw(FILE_CACHE.getEntry(STCRDDEK_SPRITES), 0x46, 0x126, 0x8F);
324 }
325 }
326 }
327 }
328 sprite.draw(FILE_CACHE.getEntry(STCRDDEK_SPRITES), 0x3F, 0x81, 0x1E);
329 }
330 if (task->panels[3].level != 0) {
331 if (task->panels[3].level != ONE) {
332 sprite.setScale(task->panels[3].level, ONE, ONE);
333 sprite.setPivot(0x140, 0x25);
334 }
335 initCardDrawer(&card);
336 id = task->list[task->listTop + task->listCursor];
337 card.setCard(id);
338 kind = card.getKind();
339 if (kind) {
340 sprite.draw(FILE_CACHE.getEntry(STCRDDEK_SPRITES), kind + 0x11, 0x103, 0x9F);
341 sprite.draw(FILE_CACHE.getEntry(STCRDDEK_SPRITES), 0xD, 0xFC, 0x9D);
342 sprite.draw(FILE_CACHE.getEntry(STCRDDEK_SPRITES), 0xB, 0x4A, 0xB3);
343 } else {
344 kind = card.card->color;
345 sprite.draw(FILE_CACHE.getEntry(STCRDDEK_SPRITES), kind + 0x13, 0x103, 0x9F);
346 sprite.draw(FILE_CACHE.getEntry(STCRDDEK_SPRITES), 0xD, 0xFC, 0x9D);
347 if (id == 0x45 || id == 0x70 || id == 0x9B || id == 0xC6 || id == 0xF1) {
348 sprite.draw(FILE_CACHE.getEntry(STCRDDEK_SPRITES), 0xB, 0x4A, 0xB3);
349 } else {
350 sprite.draw(FILE_CACHE.getEntry(STCRDDEK_SPRITES), 0xC, 0xC7, 0xB3);
351 }
352 }
353 if (task->panels[3].level != ONE) {
354 sprite.setPivot(0x140, 0xA8);
355 }
356 sprite.draw(FILE_CACHE.getEntry(STCRDDEK_SPRITES), 0xA, 0x82, 0x9D);
357 }
358 if (task->panels[4].level != 0) {
359 if (task->panels[4].level != ONE) {
360 sprite.setScale(ONE, task->panels[4].level, ONE);
361 sprite.setPivot(0, 0x78);
362 }
363 sprite.setLayerId(task->layer, task->depth - 3);
364 sprite.draw(FILE_CACHE.getEntry(STCRDDEK_SPRITES), 0x36, 0, 0x64);
365 }
366}
367
368/* The cursor on the deck's grid (9 columns, the last row 4): the pad moves it,
369 R1 opens or closes the card's info panel, cross goes on to the list of the
370 cards owned, triangle leaves and circle sorts the deck */
371static inline void STCRDDEK_moveDeckCursor(DeckEditor *task, DeckEditorChildren *children) {
372 s32 prev;
373
374 prev = task->column + task->row * 9;
376 if (--task->column < 0) {
377 task->column = 0;
378 }
380 if (task->row == 4) {
381 if (++task->column >= 4) {
382 task->column = 3;
383 }
384 } else {
385 if (++task->column >= 9) {
386 task->column = 8;
387 }
388 }
389 }
391 if (--task->row < 0) {
392 task->row = 0;
393 }
394 } else if (PAD_PRESSED(PAD_DOWN) || PAD_REPEATED(PAD_DOWN)) {
395 task->row++;
396 if (task->column >= 4) {
397 if (task->row >= 4) {
398 task->row = 3;
399 }
400 } else {
401 if (task->row >= 5) {
402 task->row = 4;
403 }
404 }
405 }
406 STCRDDEK_showEditorWindows(task, children, 1);
407 if (prev != task->column + task->row * 9) {
409 } else if (!PAD_HELD(PAD_L1) && PAD_PRESSED(PAD_R1)) {
411 task->substate = 10;
412 } else if (PAD_PRESSED(PAD_CROSS)) {
413 if (task->listCount != 0) {
415 task->substate = 20;
416 }
417 } else if (PAD_PRESSED(PAD_TRIANGLE)) {
419 task->substate = 50;
420 } else if (PAD_PRESSED(PAD_CIRCLE)) {
422 task->substate = 30;
423 }
424}
425
426/* Opens or closes the info panel of the card under the cursor */
427static inline void STCRDDEK_toggleCardInfo(DeckEditor *task, DeckEditorChildren *children) {
428 task->cursorShown = 0;
429 task->infoShown = 1 - task->infoShown;
430 if (task->infoShown) {
431 STCRDDEK_funcs.startFade(&task->panels[1], 1);
432 task->substate = 11;
433 task->step = 0;
434 } else {
435 STCRDDEK_showEditorWindows(task, children, 1);
436 STCRDDEK_funcs.startFade(&task->panels[1], 0);
437 task->substate = 11;
438 task->step = 1;
439 }
440}
441
442/* Leaves the deck's grid for the list of the cards owned: fills the list and
443 keeps its cursor on a card, closes the grid's panels and opens the list's */
444static inline void STCRDDEK_openCardList(DeckEditor *task, DeckEditorChildren *children) {
445 children->cards->state = TASK_KILL;
447 STCRDDEK_funcs.startFade(&task->panels[2], 1);
448 while (task->list[task->listTop + task->listCursor] == 0) {
449 if (--task->listTop < 0) {
450 task->listTop = 0;
451 if (--task->listCursor < 0) {
452 task->listCursor = 0;
453 }
454 }
455 }
456 task->cursorShown = 0;
457 STCRDDEK_funcs.startFade(&task->panels[0], 0);
458 if (task->infoShown) {
459 task->panels[1].level = 0;
460 task->infoShown = 0;
461 }
462 STCRDDEK_showEditorWindows(task, children, 0);
463 task->substate++;
464}
465
466/* Once the list card's panel has opened: adds a scroll bar to a list longer
467 than a page and shows the cursor and the card under it */
468static inline void STCRDDEK_showCardListCursor(DeckEditor *task, DeckEditorChildren *children) {
469 if (STCRDDEK_funcs.updateFade(&task->panels[3])) {
470 if (task->listCount >= 9 && children->scrollBar == NULL) {
472 children->scrollBar->setX(children->scrollBar, 0x125, 0xC);
473 children->scrollBar->setRange(children->scrollBar, 0x2A, 0x8F);
474 children->scrollBar->setCount(children->scrollBar, 8, task->listCount);
475 children->scrollBar->setPos(children->scrollBar, task->listCursor);
476 }
477 children->cursor->setPos(children->cursor, 0x89, task->listCursor * 14 + 0x27);
478 children->cursor->setVisible(children->cursor, 1);
479 STCRDDEK_showListCard(task, children, 1);
480 task->substate++;
481 }
482}
483
484/* The cursor on the list of the cards owned: L1/R1 turn a page, up/down move
485 it (scrolling the list); cross puts the card in the deck's slot unless the
486 deck already has four of it (a message), triangle goes back to the grid */
487static inline void STCRDDEK_chooseListCard(DeckEditor *task, DeckEditorChildren *children) {
488 s32 prev;
489#if VERSION_EU || VERSION_JP
490 s32 prevTop;
491#endif
492 s32 id;
493 s32 old;
494
495 prev = task->listTop + task->listCursor;
496#if VERSION_EU || VERSION_JP
497 prevTop = task->listTop;
498#endif
499 if (task->listCount >= 9) {
501 task->listTop -= 7;
502 if (task->listTop < 0) {
503 task->listTop = 0;
504 }
505 } else if ((!PAD_HELD(PAD_L1) && PAD_PRESSED(PAD_R1)) || (!PAD_HELD(PAD_L1) && PAD_REPEATED(PAD_R1))) {
506 s32 k;
507
508 for (k = 0; k < 7; k++) {
509 if (++task->listTop > task->listCount - 8) {
510 task->listTop = task->listCount - 8;
511 break;
512 }
513 }
514 }
515 }
516 if (prev == task->listTop + task->listCursor) {
518 if (--task->listCursor < 0) {
519 task->listCursor = 0;
520 if (--task->listTop < 0) {
521 task->listTop = 0;
522 }
523 }
524 } else if (PAD_PRESSED(PAD_DOWN) || PAD_REPEATED(PAD_DOWN)) {
525 if (task->listCount >= 9) {
526 if (++task->listCursor >= 8) {
527 task->listCursor = 7;
528 if (++task->listTop > task->listCount - 8) {
529 task->listTop = task->listCount - 8;
530 }
531 }
532 } else {
533 if (++task->listCursor > task->listCount - 1) {
534 task->listCursor = task->listCount - 1;
535 }
536 }
537 }
538 }
539#if VERSION_EU || VERSION_JP
540 if (children->scrollBar != NULL && prevTop != task->listTop) {
541 children->scrollBar->setPos(children->scrollBar, task->listTop);
542 }
543#endif
544 if (prev != task->listTop + task->listCursor) {
546 children->cursor->setPos(children->cursor, 0x89, task->listCursor * 14 + 0x27);
547 STCRDDEK_showCardList(task, children, 1);
548 STCRDDEK_showListCard(task, children, 1);
549#if VERSION_US
550 if (children->scrollBar != NULL) {
551 children->scrollBar->setPos(children->scrollBar, task->listTop + task->listCursor);
552 }
553#endif
554 } else if (PAD_PRESSED(PAD_CROSS)) {
555 id = task->list[task->listTop + task->listCursor];
556 old = GAME.decks[task->deck].cards[task->column + task->row * 9];
558 if (id != old && GAME.cards[id] - task->owned[id] >= 4) {
559 task->substate = 60;
560 } else {
561 GAME.decks[task->deck].cards[task->column + task->row * 9] = id;
562 task->screen->countKinds(task->screen);
563 task->substate++;
564 }
565 } else if (PAD_PRESSED(PAD_TRIANGLE)) {
567 task->substate++;
568 }
569}
570
571/* Hides the list, its card and its cursor and closes their panels, and ends
572 the scroll bar */
573static inline void STCRDDEK_closeCardList(DeckEditor *task, DeckEditorChildren *children) {
574 STCRDDEK_funcs.startFade(&task->panels[2], 0);
575 STCRDDEK_showCardList(task, children, 0);
576 STCRDDEK_funcs.startFade(&task->panels[3], 0);
577 STCRDDEK_showListCard(task, children, 0);
578 children->cursor->setVisible(children->cursor, 0);
579 if (children->scrollBar != NULL) {
580 children->scrollBar->state = TASK_KILL;
581 }
582 task->substate++;
583}
584
585/* Before sorting the deck: closes the grid's panels and hides its windows */
586static inline void STCRDDEK_startSort(DeckEditor *task, DeckEditorChildren *children) {
587 children->cards->state = TASK_KILL;
589 task->counter = 0;
590 task->substate++;
591 STCRDDEK_funcs.startFade(&task->panels[0], 0);
592 task->cursorShown = 0;
593 STCRDDEK_funcs.startFade(&task->panels[0], 0);
594 task->panels[1].level = 0;
595 task->infoShown = 0;
596 STCRDDEK_showEditorWindows(task, children, 0);
597}
598
599/* Sorts the deck's 40 cards by id, then shows the grid again */
600static inline void STCRDDEK_sortDeck(DeckEditor *task, DeckEditorChildren *children) {
601 s32 i;
602 s32 j;
603 s32 card;
604
605 for (i = 0; i < 39; i++) {
606 for (j = i + 1; j < 40; j++) {
607 if (GAME.decks[task->deck].cards[i] > GAME.decks[task->deck].cards[j]) {
608 card = GAME.decks[task->deck].cards[i];
609 GAME.decks[task->deck].cards[i] = GAME.decks[task->deck].cards[j];
610 GAME.decks[task->deck].cards[j] = card;
611 }
612 }
613 }
614 task->substate = 0;
615}
616
617/* Leaving: ends the deck's cards and closes the grid's panels and windows */
618static inline void STCRDDEK_closeEditor(DeckEditor *task, DeckEditorChildren *children) {
619 children->cards->state = TASK_KILL;
620 task->cursorShown = 0;
621 STCRDDEK_funcs.startFade(&task->panels[0], 0);
622 if (task->infoShown) {
623 task->panels[1].level = 0;
624 task->infoShown = 0;
625 }
626 STCRDDEK_showEditorWindows(task, children, 0);
627 task->substate++;
628}
629
630/* Once the grid's panel has opened: shows the deck's windows, fills the list
631 of the cards owned and starts laying out the deck's cards */
632static inline void STCRDDEK_openEditor(DeckEditor *task, DeckEditorChildren *children) {
633 if (STCRDDEK_funcs.updateFade(&task->panels[0])) {
634 task->blinkTime = 0;
635 STCRDDEK_showEditorWindows(task, children, 1);
637 children->cards = STCRDDEK_createDeckCards(task);
638 task->substate++;
639 }
640}
641
642/* The editor's states: picks a card of the deck (R1 its info panel, circle sorts
643 the deck, triangle leaves), then a card of the list to take its place (L1/R1
644 a page, triangle back), refusing with a message one the deck has 4 of */
646 switch (task->substate) {
647 case 0:
648 default:
649 STCRDDEK_funcs.startFade(&task->panels[0], 1);
650 task->substate++;
651 break;
652 case 1:
653 STCRDDEK_openEditor(task, children);
654 break;
655 case 2:
656 if (children->cards->state == TASK_DONE) {
657 task->cursorShown = 1;
658 task->substate = 5;
659 }
660 break;
661 case 5:
662 STCRDDEK_moveDeckCursor(task, children);
663 break;
664 case 10:
665 STCRDDEK_toggleCardInfo(task, children);
666 break;
667 case 11:
668 if (STCRDDEK_funcs.updateFade(&task->panels[1])) {
669 if (task->step == 0) {
670 STCRDDEK_showEditorWindows(task, children, 1);
671 }
672 task->cursorShown = 1;
673 task->setSubstate(task, 5);
674 }
675 break;
676 case 20:
677 STCRDDEK_openCardList(task, children);
678 break;
679 case 21:
680 if (STCRDDEK_funcs.updateFade(&task->panels[0])) {
681 task->substate++;
682 }
683 break;
684 case 22:
685 if (STCRDDEK_funcs.updateFade(&task->panels[2])) {
686 STCRDDEK_showCardList(task, children, 1);
687 STCRDDEK_funcs.startFade(&task->panels[3], 1);
688 task->substate++;
689 }
690 break;
691 case 23:
692 STCRDDEK_showCardListCursor(task, children);
693 break;
694 case 24:
695 STCRDDEK_chooseListCard(task, children);
696 break;
697 case 25:
698 STCRDDEK_closeCardList(task, children);
699 break;
700 case 26:
702 if (STCRDDEK_funcs.updateFade(&task->panels[3])) {
703 task->listCursor = 0;
704 task->listTop = 0;
705 task->substate = 0;
706 }
707 break;
708 case 30:
709 STCRDDEK_startSort(task, children);
710 break;
711 case 31:
712 if (STCRDDEK_funcs.updateFade(&task->panels[3])) {
713 task->substate++;
714 }
715 break;
716 case 32:
717 STCRDDEK_sortDeck(task, children);
718 break;
719 case 50:
720 STCRDDEK_closeEditor(task, children);
721 break;
722 case 51:
723 if (STCRDDEK_funcs.updateFade(&task->panels[0])) {
724 task->state = TASK_KILL;
725 }
726 break;
727 case 60:
728 children->cursor->setPalette(children->cursor, PALETTE_GREY);
729 children->cursor->setStill(children->cursor, 1);
730 STCRDDEK_funcs.startFade(&task->panels[4], 1);
731 task->substate++;
732 break;
733 case 61:
734 if (STCRDDEK_funcs.updateFade(&task->panels[4])) {
735 children->message->setString(children->message, FILE_CACHE.load(TEXT_FILE(TEXT_CARD_SHOP)), 0x1E);
736 task->substate++;
737 }
738 break;
739 case 62:
740 if (PAD_PRESSED(PAD_CROSS)) {
742 children->message->setVisible(children->message, 0);
743 STCRDDEK_funcs.startFade(&task->panels[4], 0);
744 task->substate++;
745 }
746 break;
747 case 63:
748 if (STCRDDEK_funcs.updateFade(&task->panels[4])) {
749 children->cursor->setPalette(children->cursor, PALETTE_WHITE);
750 children->cursor->setStill(children->cursor, 0);
751 task->substate = 23;
752 }
753 break;
754 }
755 task->blinkTime += GFX.funcs.getFrameTime();
756 if (task->blinkTime > 120) {
757 task->blinkTime -= 120;
758 }
759}
760
761/* The editor's task: creates its windows, then runs and draws it */
763 switch (task->state) {
764 case TASK_INIT:
765 default:
766 task->nextState(task);
767 STCRDDEK_createEditorWindows(task, children);
768 task->panels[0].duration = 10;
769 task->panels[1].duration = 10;
770 task->panels[2].duration = 10;
771 task->panels[3].duration = 10;
772 task->panels[4].duration = 10;
773 break;
774 case TASK_RUN:
775 STCRDDEK_stepEditor(task, children);
777 break;
778 case TASK_DONE:
779 case TASK_KILL:
780 break;
781 }
782}
783
784/* Creates the editor (task) of one of GAME.decks */
787
788 task->layer = SCREEN_LAYER;
789 task->depth = 6;
790 task->screen = screen;
791 task->deck = deck;
792 return task;
793}
794
795/* Left empty */
796void STCRDDEK_initIdle(DeckIdle *task, void *children) {
797}
798
799/* Only sets up a sprite drawer */
801 SpriteDrawer drawer;
802
803 initSpriteDrawer(&drawer);
804 drawer.setLayerId(task->layer, task->depth);
805}
806
807/* Ends the idle task on triangle */
808void STCRDDEK_stepIdle(DeckIdle *task, void *children) {
810 task->state = TASK_KILL;
811 }
812}
813
814/* A task that waits for triangle, then ends; nothing creates it */
815void STCRDDEK_updateIdle(DeckIdle *task, void *children) {
816 switch (task->state) {
817 case TASK_INIT:
818 default:
819 task->nextState(task);
820 STCRDDEK_initIdle(task, children);
821 break;
822 case TASK_RUN:
823 STCRDDEK_stepIdle(task, children);
824 STCRDDEK_drawIdle(task);
825 break;
826 case TASK_DONE:
827 case TASK_KILL:
828 break;
829 }
830}
831
832/* Creates the idle task; nothing calls it */
834 DeckIdle *task = createTask(STCRDDEK_updateIdle, sizeof(DeckIdle), 0);
835
836 task->layer = SCREEN_LAYER;
837 task->depth = 6;
838 task->parent = parent;
839 return task;
840}
void initCardDrawer(CardDrawer *obj)
Clears a card drawer, gives it its methods and binds it.
#define NULL
Definition common.h:17
signed int s32
Definition common.h:11
signed short s16
Definition common.h:9
DeckCards * STCRDDEK_createDeckCards(DeckEditor *editor)
Creates the deck's cards (task) on the editor's grid.
Definition deck_cards.c:78
STCRDDEK: the deck editor, where the player builds the three decks from the cards they own and rename...
ScrollBar * STCRDDEK_createScrollBar(void)
#define STCRDDEK_SPRITES
sprite bank
Definition deck_editor.h:34
GfxState GFX
GFX: the graphics state and its methods.
Definition display.c:209
void STCRDDEK_showEditorWindows(DeckEditor *task, DeckEditorChildren *children, s32 show)
Shows the title, the deck's name and counts of each kind, the hint (taking turns with another one) an...
Definition editor.c:54
void STCRDDEK_stepIdle(DeckIdle *task, void *children)
Ends the idle task on triangle.
Definition editor.c:808
static void STCRDDEK_showCardListCursor(DeckEditor *task, DeckEditorChildren *children)
Once the list card's panel has opened: adds a scroll bar to a list longer than a page and shows the c...
Definition editor.c:468
void STCRDDEK_drawIdle(DeckIdle *task)
Only sets up a sprite drawer.
Definition editor.c:800
void STCRDDEK_drawEditor(DeckEditor *task)
Draws the editor: the cursor on the deck's grid, the info panel, the deck's panel,...
Definition editor.c:234
void STCRDDEK_showListCard(DeckEditor *task, DeckEditorChildren *children, s32 show)
Shows the list's card under the cursor: its name and its numbers or its text, or hides them.
Definition editor.c:158
void STCRDDEK_updateIdle(DeckIdle *task, void *children)
A task that waits for triangle, then ends; nothing creates it.
Definition editor.c:815
void STCRDDEK_showCardList(DeckEditor *task, DeckEditorChildren *children, s32 show)
Shows the eight lines of the list of the cards owned from listTop (each card's name and how many are ...
Definition editor.c:130
static void STCRDDEK_chooseListCard(DeckEditor *task, DeckEditorChildren *children)
The cursor on the list of the cards owned: L1/R1 turn a page, up/down move it (scrolling the list); c...
Definition editor.c:487
static void STCRDDEK_openCardList(DeckEditor *task, DeckEditorChildren *children)
Leaves the deck's grid for the list of the cards owned: fills the list and keeps its cursor on a card...
Definition editor.c:444
void STCRDDEK_buildCardList(DeckEditor *task)
Lists the cards owned but not in the deck: owned holds each card's copies left over,...
Definition editor.c:209
void STCRDDEK_initIdle(DeckIdle *task, void *children)
Left empty.
Definition editor.c:796
static void STCRDDEK_startSort(DeckEditor *task, DeckEditorChildren *children)
Before sorting the deck: closes the grid's panels and hides its windows.
Definition editor.c:586
void STCRDDEK_updateEditor(DeckEditor *task, DeckEditorChildren *children)
The editor's task: creates its windows, then runs and draws it.
Definition editor.c:762
DeckEditor * STCRDDEK_createEditor(DeckScreen *screen, s32 deck)
Creates the editor (task) of one of GAME.decks.
Definition editor.c:785
static void STCRDDEK_closeCardList(DeckEditor *task, DeckEditorChildren *children)
Hides the list, its card and its cursor and closes their panels, and ends the scroll bar.
Definition editor.c:573
static void STCRDDEK_closeEditor(DeckEditor *task, DeckEditorChildren *children)
Leaving: ends the deck's cards and closes the grid's panels and windows.
Definition editor.c:618
static void STCRDDEK_moveDeckCursor(DeckEditor *task, DeckEditorChildren *children)
The cursor on the deck's grid (9 columns, the last row 4): the pad moves it, R1 opens or closes the c...
Definition editor.c:371
static void STCRDDEK_openEditor(DeckEditor *task, DeckEditorChildren *children)
Once the grid's panel has opened: shows the deck's windows, fills the list of the cards owned and sta...
Definition editor.c:632
static void STCRDDEK_toggleCardInfo(DeckEditor *task, DeckEditorChildren *children)
Opens or closes the info panel of the card under the cursor.
Definition editor.c:427
DeckIdle * STCRDDEK_createIdle(void *parent)
Creates the idle task; nothing calls it.
Definition editor.c:833
void STCRDDEK_createEditorWindows(DeckEditor *task, DeckEditorChildren *children)
Creates the editor's windows: the title, the deck's name and counts of each kind, the hint,...
Definition editor.c:9
void STCRDDEK_stepEditor(DeckEditor *task, DeckEditorChildren *children)
The editor's states: picks a card of the deck (R1 its info panel, circle sorts the deck,...
Definition editor.c:645
static void STCRDDEK_sortDeck(DeckEditor *task, DeckEditorChildren *children)
Sorts the deck's 40 cards by id, then shows the grid again.
Definition editor.c:600
GameState GAME
The save data, the game mode and the methods.
Definition state.c:64
#define TASK_RUN
Definition task.h:35
#define TASK_KILL
Definition task.h:37
#define TASK_INIT
Tasks: every game object is a task, a heap block that starts with this header and is updated once per...
Definition task.h:34
#define TASK_DONE
Definition task.h:36
Cursor * createCursor(s16 layerId, s32 depth, s16 x, s16 y)
A menu cursor on a layer at (x, y)
Definition cursor.c:92
#define TEXT_CARD_SHOP
CRDSHP: STCRDSHP's, and STCRDDEK's.
Definition file.h:207
#define TEXT_CARD_NAMES
CARDNM.
Definition file.h:203
#define TEXT_CARD_EFFECTS
CARDST.
Definition file.h:204
#define TEXT_FILE(file)
Definition file.h:190
FileCache FILE_CACHE
The file cache.
Definition file_cache.c:7
#define SCREEN_LAYER
The layer over the whole screen that most modes create first and draw their menus on (FIELDSTG and ST...
Definition gfx.h:45
#define PAD_CROSS
Definition pad.h:31
#define PAD_CIRCLE
Definition pad.h:30
#define PAD_DOWN
Definition pad.h:24
#define PAD_RIGHT
Definition pad.h:23
#define PAD_TRIANGLE
Definition pad.h:32
#define PAD_PRESSED(button)
One button of pad 1: newly pressed, auto-repeated while held, or held.
Definition pad.h:140
#define PAD_UP
Definition pad.h:22
#define PAD_L1
Definition pad.h:28
#define PAD_LEFT
Definition pad.h:25
#define PAD_HELD(button)
Definition pad.h:142
#define PAD_R1
Definition pad.h:29
#define PAD_REPEATED(button)
Definition pad.h:141
SoundState SOUND
rsin and rcos (libgte) read rsin_tbl[a - 0x800] and the like: their addresses before the table fall i...
Definition sound.c:180
#define SOUND_MENU_CONFIRM
SYSTEM07.
Definition sound.h:44
#define SOUND_SELECT
Sounds the overlays share, with SOUNDTST's names.
Definition sound.h:38
#define SOUND_MENU_CANCEL
SYSTEM01.
Definition sound.h:39
#define SOUND_MENU_MOVE
SYSTEM06.
Definition sound.h:43
#define SOUND_CURSOR
SYSTEM02: a cursor moves.
Definition sound.h:40
void initSpriteDrawer(SpriteDrawer *obj)
Clears a sprite drawer to neutral (no scale, gray tint, follows the scroll), gives it its methods and...
DeckFuncs STCRDDEK_funcs
Definition stcrddek.c:781
s32 STCRDDEK_cursorCluts[]
The CLUT rows of the cursor's frames.
Definition stcrddek.c:6
Draws the cards' images (CardImage), from files 0x7E7-0x7EB.
Definition gfx.h:193
void(* setCard)()
(id)
Definition gfx.h:205
s32(* getKind)(void)
Definition gfx.h:214
CardImage * card
Definition gfx.h:194
u8 hp
Definition gfx.h:175
u8 color
from 1
Definition gfx.h:173
u8 ap
Definition gfx.h:174
u8 points
what it adds to its colour
Definition gfx.h:179
TextWindow * count
Definition deck_editor.h:76
TextWindow * name
Definition deck_editor.h:74
TextWindow * label
Definition deck_editor.h:75
void(* setPalette)()
Definition text.h:35
void(* setPos)()
(cursor, x, y)
Definition text.h:34
void(* setStill)()
Definition text.h:38
void(* setVisible)()
(cursor, visible)
Definition text.h:33
CardLine lines[8]
TextWindow * listHpLabel
Definition deck_editor.h:97
struct DeckCards * cards
TextWindow * kinds[6]
Definition deck_editor.h:83
TextWindow * listEffect
Definition deck_editor.h:99
ScrollBar * scrollBar
TextWindow * ap
Definition deck_editor.h:88
TextWindow * listCardName
Definition deck_editor.h:92
TextWindow * listPoints
Definition deck_editor.h:94
TextWindow * deckName
Definition deck_editor.h:82
TextWindow * effect
Definition deck_editor.h:91
TextWindow * points
Definition deck_editor.h:86
TextWindow * listApLabel
Definition deck_editor.h:95
TextWindow * title
Definition deck_editor.h:80
TextWindow * cardName
Definition deck_editor.h:84
TextWindow * message
TextWindow * listHp
Definition deck_editor.h:98
TextWindow * hint
Definition deck_editor.h:81
TextWindow * apLabel
Definition deck_editor.h:87
TextWindow * listPointsLabel
Definition deck_editor.h:93
TextWindow * pointsLabel
Definition deck_editor.h:85
TextWindow * hp
Definition deck_editor.h:90
TextWindow * hpLabel
Definition deck_editor.h:89
TextWindow * listAp
Definition deck_editor.h:96
The deck being edited.
Definition deck_editor.h:49
void(* nextState)(struct DeckEditor *task)
Definition deck_editor.h:50
PanelAnim panels[5]
Definition deck_editor.h:69
s32 cursorFrame
Definition deck_editor.h:57
void(* setSubstate)(struct DeckEditor *task, s32 substate)
Definition deck_editor.h:50
s32 column
of the deck's grid, 9 cards a row
Definition deck_editor.h:55
s32 cursorShown
Definition deck_editor.h:59
s8 owned[315]
how many of each card are not in the deck
Definition deck_editor.h:66
s32 infoShown
the card's info panel
Definition deck_editor.h:67
s16 list[315]
the cards owned and not in the deck
Definition deck_editor.h:65
s32 deck
GAME.decks[].
Definition deck_editor.h:54
s32 arrowsShown
Definition deck_editor.h:63
s32 listCursor
in the list of the cards owned
Definition deck_editor.h:60
struct DeckScreen * screen
Definition deck_editor.h:51
void(* startFade)(PanelAnim *fade, s32 fadeIn)
Definition deck_editor.h:42
s32(* updateFade)(PanelAnim *fade)
Definition deck_editor.h:43
A task that waits for triangle; nothing creates it.
void(* nextState)(struct DeckIdle *task)
void * parent
The screen's controller: the three decks to choose from.
s32 kinds[3][6]
how many cards of each kind a deck has
void(* countKinds)(struct DeckScreen *task)
STCRDDEK_countCardKinds.
char name[0x16]
Definition game_state.h:274
s16 cards[40]
Definition game_state.h:275
void *(* load)(u32 file)
Definition file.h:92
void *(* getEntry)(u32 fileAndIndex)
Definition file.h:96
s8 cards[0x13D]
counts, up to CARD_COPIES_MAX
Definition game_state.h:514
Deck decks[3]
Definition game_state.h:516
s32(* getFrameTime)(void)
Definition gfx.h:32
s32(* getTime)(void)
Definition gfx.h:31
GfxFuncs funcs
Definition gfx.h:77
s32 level
Definition menu.h:21
s32 duration
Definition menu.h:19
void(* setCount)(struct ScrollBar *bar, s32 pageSize, s32 count)
Definition menu.h:57
void(* setPos)(struct ScrollBar *bar, s32 pos)
Definition menu.h:58
void(* setRange)(struct ScrollBar *bar, s32 top, s32 bottom)
Definition menu.h:56
s32 state
Definition menu.h:39
void(* setX)(struct ScrollBar *bar, s32 x, s32 width)
Definition menu.h:55
short(* playSound)(s32 id)
returns the voice of a key-on
Definition sound.h:187
Draws sprites from a sprite sheet (such as file 0x277, the menu graphics): a sheet has a table of fra...
Definition gfx.h:223
void(* setPivot)()
(x, y)
Definition gfx.h:250
void(* setScale)()
(x, y, z), ONE = 1.0
Definition gfx.h:248
void(* setLayerId)()
(id, depth)
Definition gfx.h:244
void(* setClutRow)()
(row)
Definition gfx.h:247
void(* draw)()
(sheet, frame, x, y)
Definition gfx.h:246
void(* setTexture)()
(x, y)
Definition gfx.h:242
void(* setDepth)()
Definition text.h:183
void(* setRightAlign)()
no prototype: callers would truncate u8 args
Definition text.h:178
void(* setLines)()
no prototype: callers would truncate u8 args
Definition text.h:184
void(* setNumber)()
Definition text.h:166
void(* setString)()
Definition text.h:165
void(* setVisible)(struct TextWindow *obj, u8 arg)
Definition text.h:177
void * createTask(void(*update)(), s32 size, s32 childrenSize)
createTaskWithId for a task nothing needs to find
Definition task.c:105
#define PALETTE_WHITE
The text windows' palettes (TextWindow.palette, setPalette): rows of the font's CLUTs,...
Definition text.h:112
#define PALETTE_GREY
what is unavailable
Definition text.h:119
TextWindow * createTextWindow(s16 layerId, s16 style, s16 x, s16 y)
A text window on a layer, in a font style, at (x, y)