Daily rewards
Daily rewards are becoming an increasingly popular game mechanic used across all genres of games, and are especially popular with free-to-play titles. They offer an engaging way of bringing players back every day while letting them earn a variety of items, ranging from purely cosmetic skins and avatars to inventory items and in-game currency.
Cloud Code's ability to easily integrate with other Unity services makes it an excellent choice for building the logic around daily rewards. You can define items and currencies in Economy, probabilities in Remote Config, and write the underlying algorithm in Cloud Code. This allows you to alter the logic of daily rewards on the fly without the need to update the game client.
For example, you can:
- Reduce the availability of some items
- Increase the number of items that get rewarded
- Include additional validation that can prevent players from receiving duplicates of rare items
- Alter the items and probabilities through Remote Config Campaigns
Setup
The following example shows how to define multiple pet toys as inventory items in Economy. You can define the daily reward parameters in Remote Config before tying it all together with a Cloud Code script.
Economy
The first step in creating this game mechanic is to define the rewards with the Inventory Item type in Economy.
Navigate to the Unity Cloud Dashboard and select Economy from the left navigation bar.
Create the following inventory items in Economy:
- Inventory item
Choco
with IDTOY_CHOCO
- Inventory item
Jojo
with IDTOY_JOJO
- Inventory item
Kiki
with IDTOY_KIKI
You must publish the Economy configuration before using it in Cloud Code scripts.
Remote Config
You can use Remote Config to define the daily rewards parameters as a custom JSON value under the key DAILY_REWARDS_VARIABLES
:
JSON
{
"rewards": [
{"id": "TOY_CHOCO", "probability": 10},
{"id": "TOY_JOJO", "probability": 65},
{"id": "TOY_KIKI", "probability": 80}
]
}
Save the key-value pair so that it is available in Cloud Code scripts.
Daily rewards script
Once the configuration is in place, you can write a simple script that interacts with Economy and Remote Config to gift a random toy to the player using a simple weighted random algorithm:
JavaScript
/*
* Retrieve the daily rewards configuration from Remote Config
* Select a random item from the configuration and gift the item to the player in Economy
* Note: the Economy configuration needs to be published and Remote Config values need to be saved before they are available in Cloud Code scripts.
*
*/
const { InventoryApi } = require('@unity-services/economy-2.4');
const { SettingsApi } = require('@unity-services/remote-config-1.1');
const _ = require('lodash-4.17');
const REMOTE_CONFIG_VARIABLES_KEY = 'DAILY_REWARDS_VARIABLES';
module.exports = async ({ context }) => {
// Initialize the Economy and Remote Config API clients using the player credentials
const { projectId, environmentId, playerId } = context;
const inventoryApi = new InventoryApi(context);
const remoteConfigApi = new SettingsApi(context);
// Fetch the daily rewards configuration from Remote Config
const remoteConfigResponse = await remoteConfigApi.assignSettingsGet(
projectId,
environmentId,
'settings',
[REMOTE_CONFIG_VARIABLES_KEY]
);
// Extract the daily rewards from the response
const dailyRewardsConfig = remoteConfigResponse?.data?.configs?.settings?.[REMOTE_CONFIG_VARIABLES_KEY];
const dailyRewards = dailyRewardsConfig?.rewards;
// Pick a random reward from the options
const reward = selectRandomReward(dailyRewards);
// Gift the reward to the player
await inventoryApi.addInventoryItem({ projectId, playerId, addInventoryRequest: { inventoryItemId: reward.id } });
return { reward: reward.id };
};
// Select a random item based on the probability of each option
function selectRandomReward(options) {
if (!_.isArray(options)) {
throw Error('Invalid daily reward options');
}
let sumOfProbabilities = 0;
options.forEach((option) => {
sumOfProbabilities += option.probability;
});
let random = _.random(0, sumOfProbabilities);
for (let i = 0; i < options.length; i++) {
if (random < options[i].probability) {
return options[i];
}
random -= options[i].probability;
}
throw Error('Unable to select a daily reward');
}