Updating Items #
Games often allow players to upgrade or reforge their items. Pragma Engine can handle this scenario via the InstancedItemPlugin.update()
method.
Create the proto definitions and store entry #
- Complete the Setting Up the Item Catalog and Store and Purchasing Items sections, then shut down the engine if it’s still running.
- In IntelliJ, define the update-related protos in
5-ext/ext-protos/src/main/proto/shared/inventoryContentExt.proto
:
message ExtUpdateEntry {
oneof data {
WeaponUpdateSpec weapon_update_spec = 1;
}
}
message WeaponUpdateSpec {
int64 damage_upgrade = 1;
int32 awesomeness_upgrade = 2;
}
- Edit
5-ext/content/src/UpdateEntries.json
to provide actual upgrade data. The following json states that each upgrade will cost 350 ofcatalogId
coins
, will upgrade thedamage
by 3, and will upgrade theawesomeness
by 1.
[
{
"ext": {
"weaponUpdateSpec": {
"damageUpgrade": 3,
"awesomenessUpgrade": 1
}
},
"id": "upgradeWeapon",
"costByCatalogId": {
"coins": {
"cost": 350
}
},
"tags": []
}
]
- Run
make ext
from a terminal. Make sure the working directory is theplatform
directory.
Apply content data #
In order to register the content you just defined with Pragma Engine, you must apply your content data changes. You may apply content data either using the command line with make
or via an IntelliJ run configuration.
Update InstancedItemPlugin #
- Implement the update method in
DemoInstancedItemPlugin
:
Due to known issues with IntelliJ performing type inferences on protos, using a value nested in anext
field can cause false syntax error. Create a local variable with a manually assigned type to hold protoext
fields, as we’ve done withspecExt
,updateExt
, andinitialInstancedItemExt
below.
override fun update(
initialInstancedItem: InstancedItem,
instancedSpec: InventoryContent.InstancedSpec,
updateEntry: InventoryContent.UpdateEntry,
inventoryContent: InventoryServiceContent,
startingInventory: InventoryData,
pendingInventory: InventoryData,
clientRequestExt: ExtInstancedItemUpdate?,
serverRequestExt: ExtInstancedItemServerUpdate?
): InstancedItemPlugin.InstancedItemPluginResult {
val extInstancedItemBuilder = ExtInstancedItem.newBuilder()
// check which item type is being processed
val specExt: ExtInstancedSpec = instancedSpec.ext
return when (specExt.dataCase) {
ExtInstancedSpec.DataCase.LASER_SWORD_SPEC -> {
// this describes specific attributes of a laser sword
val laserSwordSpec = specExt.laserSwordSpec
// this describes how to update weapons, including the laser sword.
val updateExt: ExtUpdateEntry = updateEntry.ext
val weaponUpdateSpec = updateExt.weaponUpdateSpec
// calculate updates
val initialInstancedItemExt: ExtInstancedItem = initialInstancedItem.ext
val existingLaserSword = initialInstancedItemExt.laserSword
val updatedDamage = existingLaserSword.damage + weaponUpdateSpec.damageUpgrade
val currentAwesomenessIndex =
laserSwordSpec
.awesomenessList
.indexOf(existingLaserSword.awesomeness)
val updatedAwesomenessIndex = min(
currentAwesomenessIndex + weaponUpdateSpec.awesomenessUpgrade,
laserSwordSpec.awesomenessCount - 1
)
// build laser sword data with the updated values
val laserSwordBuilder = extInstancedItemBuilder.laserSwordBuilder
val updatedLaserSword = laserSwordBuilder
.setAwesomeness(laserSwordSpec.getAwesomeness(updatedAwesomenessIndex))
.setDamage(updatedDamage)
.build()
InstancedItemPlugin.InstancedItemPluginResult(
extInstancedItemBuilder.setLaserSword(updatedLaserSword).build(),
emptyList()
)
}
else -> error("Unknown item!")
}
}
Theupdate()
method can be extended to support additional items by adding conditions to thewhen
statement.
- Run
make ext
using a terminal from theplatform
directory. - Run Pragma Engine via one of the following methods.
Once the engine has started successfully, it prints the message [main] INFO main - Pragma server startup complete
.
- In Postman, send
PragmaDev ➨ Public ➨ Player - AuthenticateOrCreateV2
to log into the engine as a player. - Send
PragmaDev ➨ Game ➨ RPC - Player ➨ Inventory ➨ storePurchaseV4
with the following request body to getcoins
:
{
"requestId": 1,
"type": "InventoryRpc.StorePurchaseV4Request",
"payload": {
"data" : {
"ext": {},
"storeId": "freeVendor",
"storeEntryId": "starterBundle",
"amount": 1
}
}
}
- Change the
storeId
to shopkeeper and thestoreEntryId
tolaserSword
, then resend thestorePurchaseV4
call to purchase alaserSword
. Copy theinstanceId
of thelaserSword
from the body of the response as this will be used in the next step.
{
"requestId": 1,
"type": "InventoryRpc.StorePurchaseV4Request",
"payload": {
"data" : {
"ext": {},
"storeId": "shopkeeper",
"storeEntryId": "laserSword",
"amount": 1
}
}
}
- In Postman, navigate to
PragmaDev ➨ Game ➨ RPC - Player ➨ Inventory ➨ updateItemV4
. Edit theinstanceId
in the body of the request with the value copied from the previous step. Also change the value ofupdateEntryId
to"upgradeWeapon"
. Send the service call to upgrade thelaserSword
.
{
"requestId": 1,
"type": "InventoryRpc.UpdateItemV4Request",
"payload": {
"itemUpdate": {
"instanced":
{
"ext": {},
"instanceId": "your item's instanceId here",
"updateEntryId": "upgradeWeapon",
"tags": [""]
}
}
}
}
- Confirm that the
damage
of thelaserSword
increased by 3 and theawesomeness
was incremented froma little
tosomewhat
.