-
Notifications
You must be signed in to change notification settings - Fork 811
Add a new Mart
This tutorial is for how to add a new Poké Mart. As an example, we'll add an evolution stone merchant to Goldenrod Dept. Store.
- Define a mart constant
- Give it an inventory
- Use it in a map script
- Add a new type of Mart
- Sell more than 10 items per Mart
Edit constants/mart_constants.asm (or constants/item_data_constants.asm in older versions of pokecrystal):
; Marts indexes (see data/items/marts.asm)
const_def
const MART_CHERRYGROVE
const MART_CHERRYGROVE_DEX
const MART_VIOLET
const MART_AZALEA
const MART_CIANWOOD
const MART_GOLDENROD_2F_1
const MART_GOLDENROD_2F_2
const MART_GOLDENROD_3F
+ const MART_GOLDENROD_3F_2
const MART_GOLDENROD_4F
const MART_GOLDENROD_5F_1
const MART_GOLDENROD_5F_2
const MART_GOLDENROD_5F_3
const MART_GOLDENROD_5F_4
...
Edit data/items/marts.asm:
Marts:
; entries correspond to MART_* constants
dw MartCherrygrove
dw MartCherrygroveDex
dw MartViolet
dw MartAzalea
dw MartCianwood
dw MartGoldenrod2F1
dw MartGoldenrod2F2
dw MartGoldenrod3F
+ dw MartGoldenrod3F2
dw MartGoldenrod4F
dw MartGoldenrod5F1
dw MartGoldenrod5F2
dw MartGoldenrod5F3
dw MartGoldenrod5F4
...
.End
...
MartGoldenrod3F:
db 7 ; # items
db X_SPEED
db X_SPECIAL
db X_DEFEND
db X_ATTACK
db DIRE_HIT
db GUARD_SPEC
db X_ACCURACY
db -1 ; end
+
+MartGoldenrod3F2:
+ db 6 ; # items
+ db FIRE_STONE
+ db THUNDERSTONE
+ db WATER_STONE
+ db LEAF_STONE
+ db MOON_STONE
+ db SUN_STONE
+ db -1 ; end
A Mart can sell up to 10 items.
The core idea here is to use the pokemart
script command, passing it a mart type and the new MART_GOLDENROD_3F_2
inventory constant.
Edit maps/GoldenrodDeptStore3F.asm:
object_const_def
const GOLDENRODDEPTSTORE3F_CLERK
+ const GOLDENRODDEPTSTORE3F_CLERK2
const GOLDENRODDEPTSTORE3F_SUPER_NERD
const GOLDENRODDEPTSTORE3F_ROCKER
...
GoldenrodDeptStore3FClerkScript:
faceplayer
opentext
pokemart MARTTYPE_STANDARD, MART_GOLDENROD_3F
closetext
end
+
+GoldenrodDeptStore3FClerk2Script:
+ faceplayer
+ opentext
+ pokemart MARTTYPE_STANDARD, MART_GOLDENROD_3F_2
+ closetext
+ end
...
def_object_events
object_event 6, 1, SPRITE_CLERK, SPRITEMOVEDATA_STANDING_DOWN, 0, 0, -1, -1, 0, OBJECTTYPE_SCRIPT, 0, GoldenrodDeptStore3FClerkScript, -1
+ object_event 7, 1, SPRITE_CLERK, SPRITEMOVEDATA_STANDING_DOWN, 0, 0, -1, -1, 0, OBJECTTYPE_SCRIPT, 0, GoldenrodDeptStore3FClerk2Script, -1
object_event 12, 5, SPRITE_SUPER_NERD, SPRITEMOVEDATA_SPINRANDOM_FAST, 0, 1, -1, -1, PAL_NPC_RED, OBJECTTYPE_SCRIPT, 0, GoldenrodDeptStore3FSuperNerdScript, -1
object_event 2, 5, SPRITE_ROCKER, SPRITEMOVEDATA_WALK_UP_DOWN, 0, 1, -1, -1, 0, OBJECTTYPE_SCRIPT, 0, GoldenrodDeptStore3FRockerScript, -1
That's it!
We used MARTTYPE_STANDARD
before because that's what typical Mart clerks use. But there are other types:
-
MARTTYPE_BITTER
: Uses unique phrases for the bitter herb merchant in Goldenrod Underground. -
MARTTYPE_PHARMACY
: Uses unique phrases for the pharmacist in Cianwood City. -
MARTTYPE_BARGAIN
: Has a special inventory and behavior for the bargain merchant in Goldenrod Underground. (Items are half-price but only sells one of each; see data/items/bargain_shop.asm.) -
MARTTYPE_ROOFTOP
: Has a special inventory and behavior for the rooftop sale merchant in Goldenrod Dept. Store. (Items are low-price; see data/items/rooftop_sale.asm.)
Adding custom behavior like MARTTYPE_BARGAIN
or MARTTYPE_ROOFTOP
is beyond the scope of this tutorial, but it isn't hard to add a type that just has different phrases. We'll add a "shady" mart that sells suspicious items.
Edit constants/mart_constants.asm:
; mart types (see engine/items/mart.asm)
const_def
const MARTTYPE_STANDARD
const MARTTYPE_BITTER
const MARTTYPE_BARGAIN
const MARTTYPE_PHARMACY
const MARTTYPE_ROOFTOP
+ const MARTTYPE_SHADY
Edit engine/items/mart.asm:
OpenMartDialog::
...
.dialogs
dw MartDialog
dw HerbShop
dw BargainShop
dw Pharmacist
dw RooftopSale
+ dw ShadyShop
...
Pharmacist:
call FarReadMart
call LoadStandardMenuHeader
ld hl, Text_Pharmacist_Intro
call MartTextbox
call BuyMenu
ld hl, Text_Pharmacist_ComeAgain
call MartTextbox
ret
+
+ShadyShop:
+ call FarReadMart
+ call LoadStandardMenuHeader
+ ld hl, Text_ShadyShop_Intro
+ call MartTextbox
+ call BuyMenu
+ ld hl, Text_ShadyShop_ComeAgain
+ jp MartTextbox
...
GetMartDialogGroup:
...
.MartTextFunctionPointers:
dwb .StandardMartPointers, 0
dwb .HerbShopPointers, 0
dwb .BargainShopPointers, 1
dwb .PharmacyPointers, 0
dwb .StandardMartPointers, 2
+ dwb .ShadyPointers, 0
...
.PharmacyPointers:
dw Text_Pharmacy_HowMany
dw Text_Pharmacy_CostsThisMuch
dw Text_Pharmacy_InsufficientFunds
dw Text_Pharmacy_BagFull
dw Text_Pharmacy_HereYouGo
dw BuyMenuLoop
+
+.ShadyPointers:
+ dw Text_ShadyShop_HowMany
+ dw Text_ShadyShop_CostsThisMuch
+ dw Text_ShadyShop_InsufficientFunds
+ dw Text_ShadyShop_BagFull
+ dw Text_ShadyShop_HereYouGo
+ dw BuyMenuLoop
...
+
+Text_ShadyShop_Intro:
+ text_far ShadyShop_IntroText
+ text_end
+
+Text_ShadyShop_ComeAgain:
+ text_far ShadyShop_ComeAgainText
+ text_end
+
+Text_ShadyShop_HowMany:
+ text_far ShadyShop_HowManyText
+ text_end
+
+Text_ShadyShop_CostsThisMuch:
+ text_far ShadyShop_CostsThisMuchText
+ text_end
+
+Text_ShadyShop_InsufficientFunds:
+ text_far ShadyShop_InsufficientFundsText
+ text_end
+
+Text_ShadyShop_BagFull:
+ text_far ShadyShop_BagFullText
+ text_end
+
+Text_ShadyShop_HereYouGo:
+ text_far ShadyShop_HereYouGoText
+ text_end
And edit data/text/common_3.asm:
+ShadyShop_IntroText::
+ text "Hello, kiddo!"
+
+ para "Wanna buy any of"
+ line "my goods?"
+
+ para "They fell off the"
+ line "back of a truck!"
+ cont "Hehehe…"
+ done
+
+ShadyShop_ComeAgainText::
+ text "See ya, kid!"
+ done
+
+ShadyShop_HowManyText::
+ text "How many you"
+ line "need?"
+ done
+
+ShadyShop_CostsThisMuchText::
+ text "That'll cost ya"
+ line "¥@"
+ text_decimal hMoneyTemp, 3, 6
+ text ". 'Kay?"
+ done
+
+ShadyShop_InsufficientFundsText::
+ text "That ain't enough!"
+ done
+
+ShadyShop_BagFullText::
+ text "Hehe, you can't"
+ line "carry it!"
+ done
+
+ShadyShop_HereYouGoText::
+ text "Cha-ching!"
+ done
This new Mart type is appropriate for the Team Rocket merchant in Mahogany Town. So edit maps/MahoganyMart1F.asm:
MahogayMart1FPharmacistScript:
faceplayer
opentext
checkevent EVENT_DECIDED_TO_HELP_LANCE
iftrue .LanceEntered
- pokemart MARTTYPE_STANDARD, MART_MAHOGANY_1
+ pokemart MARTTYPE_SHADY, MART_MAHOGANY_1
closetext
end
And it works!
This is a simple improvement.
Edit wram.asm:
SECTION UNION "Miscellaneous WRAM 1", WRAMX
; mart items
wMartItem1BCD:: ds 3
wMartItem2BCD:: ds 3
wMartItem3BCD:: ds 3
wMartItem4BCD:: ds 3
wMartItem5BCD:: ds 3
wMartItem6BCD:: ds 3
wMartItem7BCD:: ds 3
wMartItem8BCD:: ds 3
wMartItem9BCD:: ds 3
wMartItem10BCD:: ds 3
+wMartItem11BCD:: ds 3
+wMartItem12BCD:: ds 3
+wMartItem13BCD:: ds 3
+wMartItem14BCD:: ds 3
+wMartItem15BCD:: ds 3
+wMartItem16BCD:: ds 3
+wMartItem17BCD:: ds 3
+wMartItem18BCD:: ds 3
+wMartItem19BCD:: ds 3
+wMartItem20BCD:: ds 3
...
UNION
; mart data
wCurMartCount:: db
-wCurMartItems:: ds 15
+wCurMartItems:: ds 21
wCurMartItems
stores the inventory from data/items/marts.asm, including the count and the ending −1. So with 21 bytes, a Mart can sell 20 items. Then there just has to be enough space to store 20 prices.