Book a Demo!
CoCalc Logo Icon
StoreFeaturesDocsShareSupportNewsAboutPoliciesSign UpSign In
pret
GitHub Repository: pret/pokered
Path: blob/master/home/list_menu.asm
2023 views
1
; INPUT:
2
; [wListMenuID] = list menu ID
3
; [wListPointer] = address of the list (2 bytes)
4
DisplayListMenuID::
5
xor a
6
ldh [hAutoBGTransferEnabled], a ; disable auto-transfer
7
ld a, 1
8
ldh [hJoy7], a ; joypad state update flag
9
ld a, [wBattleType]
10
and a ; is it the Old Man battle?
11
jr nz, .specialBattleType
12
ld a, $01 ; hardcoded bank
13
jr .bankswitch
14
.specialBattleType ; Old Man battle
15
ld a, BANK(DisplayBattleMenu)
16
.bankswitch
17
call BankswitchHome
18
ld hl, wStatusFlags5
19
set BIT_NO_TEXT_DELAY, [hl]
20
xor a
21
ld [wMenuItemToSwap], a ; 0 means no item is currently being swapped
22
ld [wListCount], a
23
ld a, [wListPointer]
24
ld l, a
25
ld a, [wListPointer + 1]
26
ld h, a ; hl = address of the list
27
ld a, [hl] ; the first byte is the number of entries in the list
28
ld [wListCount], a
29
ld a, LIST_MENU_BOX
30
ld [wTextBoxID], a
31
call DisplayTextBoxID ; draw the menu text box
32
call UpdateSprites ; disable sprites behind the text box
33
; the code up to .skipMovingSprites appears to be useless
34
hlcoord 4, 2 ; coordinates of upper left corner of menu text box
35
lb de, 9, 14 ; height and width of menu text box
36
ld a, [wListMenuID]
37
and a ; PCPOKEMONLISTMENU?
38
jr nz, .skipMovingSprites
39
call UpdateSprites
40
.skipMovingSprites
41
ld a, 1 ; max menu item ID is 1 if the list has less than 2 entries
42
ld [wMenuWatchMovingOutOfBounds], a
43
ld a, [wListCount]
44
cp 2 ; does the list have less than 2 entries?
45
jr c, .setMenuVariables
46
ld a, 2 ; max menu item ID is 2 if the list has at least 2 entries
47
.setMenuVariables
48
ld [wMaxMenuItem], a
49
ld a, 4
50
ld [wTopMenuItemY], a
51
ld a, 5
52
ld [wTopMenuItemX], a
53
ld a, PAD_A | PAD_B | PAD_SELECT
54
ld [wMenuWatchedKeys], a
55
ld c, 10
56
call DelayFrames
57
58
DisplayListMenuIDLoop::
59
xor a
60
ldh [hAutoBGTransferEnabled], a ; disable transfer
61
call PrintListMenuEntries
62
ld a, 1
63
ldh [hAutoBGTransferEnabled], a ; enable transfer
64
call Delay3
65
ld a, [wBattleType]
66
and a ; is it the Old Man battle?
67
jr z, .notOldManBattle
68
; Old Man battle
69
ld a, ''
70
ldcoord_a 5, 4 ; place menu cursor in front of first menu entry
71
ld c, 80
72
call DelayFrames
73
xor a
74
ld [wCurrentMenuItem], a
75
hlcoord 5, 4
76
ld a, l
77
ld [wMenuCursorLocation], a
78
ld a, h
79
ld [wMenuCursorLocation + 1], a
80
jr .buttonAPressed
81
.notOldManBattle
82
call LoadGBPal
83
call HandleMenuInput
84
push af
85
call PlaceMenuCursor
86
pop af
87
bit B_PAD_A, a
88
jp z, .checkOtherKeys
89
.buttonAPressed
90
ld a, [wCurrentMenuItem]
91
call PlaceUnfilledArrowMenuCursor
92
93
; pointless because both values are overwritten before they are read
94
ld a, $01
95
ld [wMenuExitMethod], a
96
ld [wChosenMenuItem], a
97
98
xor a
99
ld [wMenuWatchMovingOutOfBounds], a
100
ld a, [wCurrentMenuItem]
101
ld c, a
102
ld a, [wListScrollOffset]
103
add c
104
ld c, a
105
ld a, [wListCount]
106
and a ; is the list empty?
107
jp z, ExitListMenu ; if so, exit the menu
108
dec a
109
cp c ; did the player select Cancel?
110
jp c, ExitListMenu ; if so, exit the menu
111
ld a, c
112
ld [wWhichPokemon], a
113
ld a, [wListMenuID]
114
cp ITEMLISTMENU
115
jr nz, .skipMultiplying
116
; if it's an item menu
117
sla c ; item entries are 2 bytes long, so multiply by 2
118
.skipMultiplying
119
ld a, [wListPointer]
120
ld l, a
121
ld a, [wListPointer + 1]
122
ld h, a
123
inc hl ; hl = beginning of list entries
124
ld b, 0
125
add hl, bc
126
ld a, [hl]
127
ld [wCurListMenuItem], a
128
ld a, [wListMenuID]
129
and a ; PCPOKEMONLISTMENU?
130
jr z, .pokemonList
131
; if it's an item menu
132
ASSERT wCurListMenuItem == wCurItem
133
push hl
134
call GetItemPrice
135
pop hl
136
ld a, [wListMenuID]
137
cp ITEMLISTMENU
138
jr nz, .skipGettingQuantity
139
inc hl
140
ld a, [hl] ; a = item quantity
141
ld [wMaxItemQuantity], a
142
.skipGettingQuantity
143
ld a, [wCurItem]
144
ld [wNameListIndex], a
145
ld a, BANK(ItemNames)
146
ld [wPredefBank], a
147
call GetName
148
jr .storeChosenEntry
149
.pokemonList
150
ASSERT wCurListMenuItem == wCurPartySpecies
151
ld hl, wPartyCount
152
ld a, [wListPointer]
153
cp l ; is it a list of party pokemon or box pokemon?
154
ld hl, wPartyMonNicks
155
jr z, .getPokemonName
156
ld hl, wBoxMonNicks ; box pokemon names
157
.getPokemonName
158
ld a, [wWhichPokemon]
159
call GetPartyMonName
160
.storeChosenEntry ; store the menu entry that the player chose and return
161
ld de, wNameBuffer
162
call CopyToStringBuffer
163
ld a, CHOSE_MENU_ITEM
164
ld [wMenuExitMethod], a
165
ld a, [wCurrentMenuItem]
166
ld [wChosenMenuItem], a
167
xor a
168
ldh [hJoy7], a ; joypad state update flag
169
ld hl, wStatusFlags5
170
res BIT_NO_TEXT_DELAY, [hl]
171
jp BankswitchBack
172
.checkOtherKeys ; check B, SELECT, Up, and Down keys
173
bit B_PAD_B, a
174
jp nz, ExitListMenu ; if so, exit the menu
175
bit B_PAD_SELECT, a
176
jp nz, HandleItemListSwapping ; if so, allow the player to swap menu entries
177
ld b, a
178
bit B_PAD_DOWN, b
179
ld hl, wListScrollOffset
180
jr z, .upPressed
181
; Down pressed
182
ld a, [hl]
183
add 3
184
ld b, a
185
ld a, [wListCount]
186
cp b ; will going down scroll past the Cancel button?
187
jp c, DisplayListMenuIDLoop
188
inc [hl] ; if not, go down
189
jp DisplayListMenuIDLoop
190
.upPressed
191
ld a, [hl]
192
and a
193
jp z, DisplayListMenuIDLoop
194
dec [hl]
195
jp DisplayListMenuIDLoop
196
197
DisplayChooseQuantityMenu::
198
; text box dimensions/coordinates for just quantity
199
hlcoord 15, 9
200
ld b, 1 ; height
201
ld c, 3 ; width
202
ld a, [wListMenuID]
203
cp PRICEDITEMLISTMENU
204
jr nz, .drawTextBox
205
; text box dimensions/coordinates for quantity and price
206
hlcoord 7, 9
207
ld b, 1 ; height
208
ld c, 11 ; width
209
.drawTextBox
210
call TextBoxBorder
211
hlcoord 16, 10
212
ld a, [wListMenuID]
213
cp PRICEDITEMLISTMENU
214
jr nz, .printInitialQuantity
215
hlcoord 8, 10
216
.printInitialQuantity
217
ld de, InitialQuantityText
218
call PlaceString
219
xor a
220
ld [wItemQuantity], a ; initialize current quantity to 0
221
jp .incrementQuantity
222
.waitForKeyPressLoop
223
call JoypadLowSensitivity
224
ldh a, [hJoyPressed] ; newly pressed buttons
225
bit B_PAD_A, a
226
jp nz, .buttonAPressed
227
bit B_PAD_B, a
228
jp nz, .buttonBPressed
229
bit B_PAD_UP, a
230
jr nz, .incrementQuantity
231
bit B_PAD_DOWN, a
232
jr nz, .decrementQuantity
233
jr .waitForKeyPressLoop
234
.incrementQuantity
235
ld a, [wMaxItemQuantity]
236
inc a
237
ld b, a
238
ld hl, wItemQuantity ; current quantity
239
inc [hl]
240
ld a, [hl]
241
cp b
242
jr nz, .handleNewQuantity
243
; wrap to 1 if the player goes above the max quantity
244
ld a, 1
245
ld [hl], a
246
jr .handleNewQuantity
247
.decrementQuantity
248
ld hl, wItemQuantity ; current quantity
249
dec [hl]
250
jr nz, .handleNewQuantity
251
; wrap to the max quantity if the player goes below 1
252
ld a, [wMaxItemQuantity]
253
ld [hl], a
254
.handleNewQuantity
255
hlcoord 17, 10
256
ld a, [wListMenuID]
257
cp PRICEDITEMLISTMENU
258
jr nz, .printQuantity
259
.printPrice
260
ld c, $03
261
ld a, [wItemQuantity]
262
ld b, a
263
ld hl, hMoney ; total price
264
; initialize total price to 0
265
xor a
266
ld [hli], a
267
ld [hli], a
268
ld [hl], a
269
.addLoop ; loop to multiply the individual price by the quantity to get the total price
270
ld de, hMoney + 2
271
ld hl, hItemPrice + 2
272
push bc
273
predef AddBCDPredef ; add the individual price to the current sum
274
pop bc
275
dec b
276
jr nz, .addLoop
277
ldh a, [hHalveItemPrices]
278
and a ; should the price be halved (for selling items)?
279
jr z, .skipHalvingPrice
280
xor a
281
ldh [hDivideBCDDivisor], a
282
ldh [hDivideBCDDivisor + 1], a
283
ld a, $02
284
ldh [hDivideBCDDivisor + 2], a
285
predef DivideBCDPredef3 ; halves the price
286
; store the halved price
287
ldh a, [hDivideBCDQuotient]
288
ldh [hMoney], a
289
ldh a, [hDivideBCDQuotient + 1]
290
ldh [hMoney + 1], a
291
ldh a, [hDivideBCDQuotient + 2]
292
ldh [hMoney + 2], a
293
.skipHalvingPrice
294
hlcoord 12, 10
295
ld de, SpacesBetweenQuantityAndPriceText
296
call PlaceString
297
ld de, hMoney ; total price
298
ld c, 3 | LEADING_ZEROES | MONEY_SIGN
299
call PrintBCDNumber
300
hlcoord 9, 10
301
.printQuantity
302
ld de, wItemQuantity ; current quantity
303
lb bc, LEADING_ZEROES | 1, 2 ; 1 byte, 2 digits
304
call PrintNumber
305
jp .waitForKeyPressLoop
306
.buttonAPressed ; the player chose to make the transaction
307
xor a
308
ld [wMenuItemToSwap], a ; 0 means no item is currently being swapped
309
ret
310
.buttonBPressed ; the player chose to cancel the transaction
311
xor a
312
ld [wMenuItemToSwap], a ; 0 means no item is currently being swapped
313
ld a, $ff
314
ret
315
316
InitialQuantityText::
317
db "×01@"
318
319
SpacesBetweenQuantityAndPriceText::
320
db " @"
321
322
ExitListMenu::
323
ld a, [wCurrentMenuItem]
324
ld [wChosenMenuItem], a
325
ld a, CANCELLED_MENU
326
ld [wMenuExitMethod], a
327
ld [wMenuWatchMovingOutOfBounds], a
328
xor a
329
ldh [hJoy7], a
330
ld hl, wStatusFlags5
331
res BIT_NO_TEXT_DELAY, [hl]
332
call BankswitchBack
333
xor a
334
ld [wMenuItemToSwap], a ; 0 means no item is currently being swapped
335
scf
336
ret
337
338
PrintListMenuEntries::
339
hlcoord 5, 3
340
ld b, 9
341
ld c, 14
342
call ClearScreenArea
343
ld a, [wListPointer]
344
ld e, a
345
ld a, [wListPointer + 1]
346
ld d, a
347
inc de ; de = beginning of list entries
348
ld a, [wListScrollOffset]
349
ld c, a
350
ld a, [wListMenuID]
351
cp ITEMLISTMENU
352
ld a, c
353
jr nz, .skipMultiplying
354
; if it's an item menu
355
; item entries are 2 bytes long, so multiply by 2
356
sla a
357
sla c
358
.skipMultiplying
359
add e
360
ld e, a
361
jr nc, .noCarry
362
inc d
363
.noCarry
364
hlcoord 6, 4 ; coordinates of first list entry name
365
ld b, 4 ; print 4 names
366
.loop
367
ld a, b
368
ld [wWhichPokemon], a
369
ld a, [de]
370
ld [wNamedObjectIndex], a
371
cp $ff
372
jp z, .printCancelMenuItem
373
push bc
374
push de
375
push hl
376
push hl
377
push de
378
ld a, [wListMenuID]
379
and a ; PCPOKEMONLISTMENU?
380
jr z, .pokemonPCMenu
381
cp MOVESLISTMENU
382
jr z, .movesMenu
383
; item menu
384
call GetItemName
385
jr .placeNameString
386
.pokemonPCMenu
387
push hl
388
ld hl, wPartyCount
389
ld a, [wListPointer]
390
cp l ; is it a list of party pokemon or box pokemon?
391
ld hl, wPartyMonNicks
392
jr z, .getPokemonName
393
ld hl, wBoxMonNicks ; box pokemon names
394
.getPokemonName
395
ld a, [wWhichPokemon]
396
ld b, a
397
ld a, 4
398
sub b
399
ld b, a
400
ld a, [wListScrollOffset]
401
add b
402
call GetPartyMonName
403
pop hl
404
jr .placeNameString
405
.movesMenu
406
call GetMoveName
407
.placeNameString
408
call PlaceString
409
pop de
410
pop hl
411
ld a, [wPrintItemPrices]
412
and a ; should prices be printed?
413
jr z, .skipPrintingItemPrice
414
; print item price
415
push hl
416
ld a, [de]
417
ld de, ItemPrices
418
ld [wCurItem], a
419
call GetItemPrice
420
pop hl
421
ld bc, SCREEN_WIDTH + 5 ; 1 row down and 5 columns right
422
add hl, bc
423
ld c, 3 | LEADING_ZEROES | MONEY_SIGN
424
call PrintBCDNumber
425
.skipPrintingItemPrice
426
ld a, [wListMenuID]
427
and a ; PCPOKEMONLISTMENU?
428
jr nz, .skipPrintingPokemonLevel
429
; print Pokemon level
430
ld a, [wNamedObjectIndex]
431
push af
432
push hl
433
ld hl, wPartyCount
434
ld a, [wListPointer]
435
cp l ; is it a list of party pokemon or box pokemon?
436
ld a, PLAYER_PARTY_DATA
437
jr z, .next
438
ld a, BOX_DATA
439
.next
440
ld [wMonDataLocation], a
441
ld hl, wWhichPokemon
442
ld a, [hl]
443
ld b, a
444
ld a, $04
445
sub b
446
ld b, a
447
ld a, [wListScrollOffset]
448
add b
449
ld [hl], a
450
call LoadMonData
451
ld a, [wMonDataLocation]
452
and a ; is it a list of party pokemon or box pokemon?
453
jr z, .skipCopyingLevel
454
; copy level
455
ld a, [wLoadedMonBoxLevel]
456
ld [wLoadedMonLevel], a
457
.skipCopyingLevel
458
pop hl
459
ld bc, SCREEN_WIDTH + 8 ; 1 row down and 8 columns right
460
add hl, bc
461
call PrintLevel
462
pop af
463
ld [wNamedObjectIndex], a
464
.skipPrintingPokemonLevel
465
pop hl
466
pop de
467
inc de
468
ld a, [wListMenuID]
469
cp ITEMLISTMENU
470
jr nz, .nextListEntry
471
; print item quantity
472
ld a, [wNamedObjectIndex]
473
ld [wCurItem], a
474
call IsKeyItem ; check if item is unsellable
475
ld a, [wIsKeyItem]
476
and a ; is the item unsellable?
477
jr nz, .skipPrintingItemQuantity ; if so, don't print the quantity
478
push hl
479
ld bc, SCREEN_WIDTH + 8 ; 1 row down and 8 columns right
480
add hl, bc
481
ld a, '×'
482
ld [hli], a
483
ld a, [wNamedObjectIndex]
484
push af
485
ld a, [de]
486
ld [wMaxItemQuantity], a
487
push de
488
ld de, wTempByteValue
489
ld [de], a
490
lb bc, 1, 2
491
call PrintNumber
492
pop de
493
pop af
494
ld [wNamedObjectIndex], a
495
pop hl
496
.skipPrintingItemQuantity
497
inc de
498
pop bc
499
inc c
500
push bc
501
inc c
502
ld a, [wMenuItemToSwap] ; ID of item chosen for swapping (counts from 1)
503
and a ; is an item being swapped?
504
jr z, .nextListEntry
505
sla a
506
cp c ; is it this item?
507
jr nz, .nextListEntry
508
dec hl
509
ld a, ''
510
ld [hli], a
511
.nextListEntry
512
ld bc, 2 * SCREEN_WIDTH ; 2 rows
513
add hl, bc
514
pop bc
515
inc c
516
dec b
517
jp nz, .loop
518
ld bc, -8
519
add hl, bc
520
ld a, ''
521
ld [hl], a
522
ret
523
.printCancelMenuItem
524
ld de, ListMenuCancelText
525
jp PlaceString
526
527
ListMenuCancelText::
528
db "CANCEL@"
529
530