Les transactions sur l'île vous permettent de commercialiser des objets, des offres et des packs d'offres sur votre île à l'aide de Verse.
Dans ce guide, vous apprendrez à configurer vos propres objets, offres et packs. À l'aide du module Marché de l'API Verse, vous pourrez alors gérer la vente d'objets dans le jeu.
Objets
Dans Verse, les objets sont définis comme des objets et se divisent en deux catégories : les objets à usage unique, qui sont retirés de l'inventaire du joueur une fois utilisés, et les objets durables, que le joueur peut continuer à utiliser et qui sont conservés dans son inventaire.
Chaque objet Verse dispose des propriétés suivantes :
Nom : le nom de l'objet, qui peut comporter 50 caractères maximum.
Description : la description détaillée qui s'affiche avec l'objet, pouvant comporter jusqu'à 500 caractères.
Brève description : une brève description qui décrit l'objet dans une petite boîte de dialogue de 100 caractères maximum.
Icône : une illustration de l'objet.
Si votre objet est un objet aléatoire payant, il est impératif d'inclure dans la description les probabilités numériques exactes de ce que le joueur peut recevoir. Pour en savoir plus, consultez la page Objets aléatoires payants.
Un objet Verse peut également disposer des propriétés facultatives suivantes :
Nombre max. : le nombre maximal de cet objet que le joueur peut posséder à un moment donné.
Objet à usage unique : si cette option est activée, l'objet peut être consommé, ce qui réduit le nombre total d'utilisations. Si cette option est désactivée, l'objet est permanent et est conservé à mesure de son utilisation.
Zone payante : si cette option est activée, l'objet permet d'accéder à une zone soumise à un paiement.
Objet aléatoire payant : si cette option est activée, ces objets sont achetés ou échangés contre du contenu pour obtenir une récompense aléatoire.
ConsequentialToGameplay : si cette option est activée, l'objet procure un avantage significatif sur votre île. Pour en savoir plus, consultez la rubrique Incidence sur le jeu.
Si vous avez des objets actifs qui ne sont pas utilisés et que vous ne confirmez pas les achats intégrés dans le questionnaire IARC, votre île échouera à l'étape de modération.
Pour contourner ce problème, vous pouvez commenter vos objets dans Verse jusqu'à ce que vous soyez prêt à les utiliser dans une partie en direct. Une fois les objets commentés, vous n'avez pas besoin de déclarer les achats intégrés dans le questionnaire IARC.
Créer un objet à usage unique dans Verse
Les objets sont définis dans Verse et sont dérivés de la classe de base de l'objet. L'extrait suivant illustre la création d'un objet à usage unique. Dans cet exemple, vous allez créer des semences de maïs comme objet à usage unique. Une icône représentant les semences est fournie ci-dessous pour votre usage.
# The base entitlement you should define for ALL of your entitlements in your experience.
my_island_entitlement := class<abstract><castable>(entitlement){}
CornSeedPacket<public> := module:
Name<public><localizes> : message = "Corn seed pack"
Description<public><localizes> : message = "A pack of corn seeds. Opening a pack yields 10 corn seeds for planting."
ShortDescription<public><localizes> : message = "Contains 10 corn seeds for planting."
cornseedpacket<public> := class<concrete>(my_island_entitlement):
var Name<override>:message = CornSeedPacket.Name
Lorsque vous créez un objet, il est nécessaire d'inclure un chemin d'accès à une texture d'icône valide pour pouvoir compiler correctement votre code Verse. Considérez le paquet de semences de maïs et les autres icônes incluses dans ce guide comme un cadeau.
Assurez-vous que les icônes de vos objets utilisent une
Créer des objets durables dans Verse
Dans Verse, les objets durables suivent le même format que les objets à usage unique, mais avec une différence essentielle : l'option Objet à usage unique est désactivée et non activée. Les joueurs ne peuvent acheter les objets durables qu'une seule fois et ne peuvent posséder qu'un seul exemplaire d'un objet durable donné.
Dans cet exemple, vous allez créer une pelle comme objet durable. Une icône représentant la texture de la pelle est incluse après l'extrait ci-dessous.
Shovel<public> := module:
Name<public><localizes>: message = "Shovel"
Description<public><localizes>: message = "An unbreakable shovel used to dig holes for planting."
ShortDescription<public><localizes>: message = "Digs holes."
shovel<public> := class<concrete>(my_island_entitlement):
var Name<override>:message = Shovel.Name
var Description<override>:message = Shovel.Description
var ShortDescription<override>:message = Shovel.ShortDescription
var Icon<override>:texture = # path to your texture here
Par défaut, les accessoires ne sont pas des objets à usage unique et leur paramètre Nombre max. est défini sur 1. Il est important que les champs concernés de votre code déterminent si l'objet est une zone payante, un objet aléatoire payant ou offrant un avantage significatif ayant une incidence sur le jeu.
Règles de validation des objets
Dans Verse, un objet valide doit respecter les directives ci-dessous. Si vous tentez d'acheter un objet qui ne répond pas à ces critères, l'achat échoue.
Les règles qui définissent un objet valide sont les suivantes :
Le champ Nom ne doit pas comporter plus de 50 caractères.
Le champ Description ne doit pas comporter plus de 500 caractères.
Le champ Brève description ne doit pas comporter plus de 100 caractères.
Le paramètre Nombre max. doit être de 1 lorsque Consumable=false.
La valeur maximale du paramètre Nombre max. est de 10 000 000.
Le paramètre Nombre max. < 1 n'est pas appliqué mais échouera, car il n'est pas possible d'attribuer moins d'un objet à un joueur.
Le catalogue d'objets
Vous pouvez utiliser le catalogue d'objets pour visualiser l'ensemble des objets que vous proposez aux joueurs.
Vous pouvez consulter un rapport répertoriant vos objets dans l'UEFN en cliquant sur Outils > Catalogue d'objets, ou directement à partir du catalogue dans le portail de créateur de votre île.
Offres
Une offre précise le prix en V-bucks d'un objet ou d'une ressource. Chaque offre possède son propre nom, sa propre description et sa propre icône, distincts des spécifications de l'objet. Une offre est définie dans Verse.
Chaque offre présente les propriétés suivantes :
Nom : le nom de l'offre.
Description : la description détaillée qui accompagne l'offre.
Brève description : une brève description que vous pouvez utiliser pour décrire rapidement l'offre dans des boîtes de dialogue plus petites.
Icône : une illustration de l'offre.
Type d'objet : une déclaration de l'objet inclus dans l'offre.
Prix : un prix, en V-bucks. Le prix doit être compris entre 50 V-bucks et 5 000 V-bucks. Vous devez le définir en multiples de 50.
Créer une offre simple
Cet extrait définit une offre de base pour une offre simple : le paquet de semences de maïs. Vous pouvez réutiliser l'icône représentant une graine de maïs de l'exemple d'objet comme icône de cette offre.
CornSeedPacket<public> := module:
Name<public><localizes> : message = "Corn seed pack"
Description<public><localizes> : message = "A pack of corn seeds. Opening a pack yields 10 corn seeds for planting."
ShortDescription<public><localizes> : message = "Contains 10 corn seeds for planting."
corn_seed_pack<public> := class(entitlement_offer):
var Name<override> : message = CornSeedPacket.Name
var Description<override> : message = CornSeedPacket.Description
var ShortDescription<override> : message = CornSeedPacket.ShortDescription
Le prix en V-bucks doit être un multiple de 50 et être compris entre 50 et 5 000 V-bucks.
Il est impératif de garantir que les joueurs puissent consulter les probabilités numériques exactes d'obtenir chaque objet aléatoire payant avant de l'acheter. Le non-respect de cette consigne sera considéré comme une violation des règles du programme Développeurs d'îles de Fortnite et vous exposera, vous et votre île, aux sanctions pertinentes.
Pour en savoir plus, consultez la page Restrictions relatives aux transactions sur l'île.
Créer et modifier des offres fixes et alternatives
Vous pouvez présenter différentes offres pour le même objet afin de proposer des prix spéciaux pour les fêtes et des bonus de bienvenue, et de varier le prix selon les régions. Vous pouvez également les utiliser pour tester des objets en créant une offre identique, mais en utilisant une icône différente afin de déterminer laquelle intéresse le plus les joueurs. Prenons cette icône comme exemple.
CornSeedPacketAlternate<public> := module:
Name<public><localizes> : message = "Corn seed pack"
Description<public><localizes> : message = "Special price! Only today!"
ShortDescription<public><localizes> : message = "Special offer half price!"
corn_seed_pack_alternate<public> := class(entitlement_offer):
var Name<override> : message = CornSeedPacketAlternate.Name
var Description<override> : message = CornSeedPacketAlternate.Description
var ShortDescription<override> : message = CornSeedPacketAlternate.ShortDescription
var Icon<override> : texture = # Your texture here
Packs d'offres
Les packs sont définis dans Verse et peuvent contenir différentes offres, plusieurs exemplaires de la même offre ou une combinaison des deux. À l'instar des offres simples, les packs indiquent leur propre prix, leur nom et leur description, et sont accompagnés d'une icône distincte de celle des objets et des offres. Il est également possible d'imbriquer les offres en incluant des lots dans un pack. Par exemple : pack à durée limitée comprenant une pelle et un lot de paquets de semences de maïs. Cela vous permet d'utiliser des packs plus petits comme éléments constitutifs de packs combinés plus volumineux.
Les types de packs standard sont les suivants :
Pack empilé : un pack comprenant plusieurs offres du même objet, généralement à un prix réduit.
Pack à plusieurs offres : un pack combinant des offres pour plusieurs objets, pouvant également inclure une combinaison d'offres empilées et d'offres régulières.
La profondeur des offres imbriquées ne peut pas dépasser 5 niveaux, auquel cas la transaction échouera. Limitez autant que possible les offres imbriquées.
Créer un pack empilé
Cet extrait définit un pack empilé de semences de maïs. Un pack inclut une matrice de tuples d'offres, qui contient l'offre définie et un entier indiquant le nombre d'offres. Dans ce cas, ce pack contiendrait deux offres corn_seed_pack. Une icône est fournie pour illustrer cet exemple.
CornSeedPacketBundle<public> := module:
Name<public><localizes> : message = "Corn seed pack bundle"
Description<public><localizes> : message = "Two packs of corn seeds. Opening a pack yields 10 corn seeds for planting."
ShortDescription<public><localizes> : message = "Two packs of corn seeds containing 10 corn seeds for planting."
corn_seed_pack_bundle<public> := class(bundle_offer):
var Name<override> : message = CornSeedPacketBundle.Name
var Description<override> : message = CornSeedPacketBundle.Description
var ShortDescription<override> : message = CornSeedPacketBundle.ShortDescription
var Icon<override> : texture = # your texture here
Créer des packs à plusieurs offres
Il est possible que les joueurs souhaitent éviter les transactions multiples ; vous pouvez donc proposer un pack comprenant plusieurs offres avec différents objets. Cet extrait de code crée un pack à plusieurs offres qui fournit au joueur le nombre maximal de paquets de semences de maïs et une pelle.
StarterBundle<public> := module:
Name<public><localizes> : message = "Starter bundle"
Description<public><localizes> : message = "Everything a new player needs. Get fully stocked to start quickly! A shovel that digs holes, and ten packs of corn seeds each containing 10 corn seeds for planting."
ShortDescription<public><localizes> : message = "A shovel that digs holes, and ten packs of corn seeds each containing 10 corn seeds for planting."
starter_bundle<public> := class(bundle_offer):
var Name<override> : message = StarterBundle.Name
var Description<override> : message = StarterBundle.Description
var ShortDescription<override> : message = StarterBundle.ShortDescription
var Icon<override> : texture = # your texture here
Dans Verse, les packs ne contiennent pas directement des objets. Ils contiennent plutôt des offres qui possèdent elles-mêmes des définitions d'objet.
Offres créées de manière dynamique
Une offre créée de manière dynamique est une offre (ou un pack) générée au moment de l'exécution dans Verse. Voici les cas d'utilisation des offres dynamiques les plus courants :
Une offre pour la quantité maximale de bois qu'un joueur peut détenir dans un jeu de survie.
Un pack permettant d'optimiser les PV et les potions de mana à l'entrée d'un donjon pour un jeu de type dungeon crawler.
Pour simplifier, associez-les à un élément simple, par exemple un bouton ou un signe. Dans le code Verse, la procédure serait la suivante : à l'interaction, appeler BuyOffer.
Cet extrait présente une méthode pour vendre un lot de paquets de semences de maïs jusqu'à la quantité maximale qu'un joueur peut posséder. Un message d'erreur s'affiche si l'achat échoue.
TryBuyOffer(Player : player)<suspends>:void =
Purchases := GetPurchasedEntitlements(Player, Entitlements.corn_seed_pack)
var NumPlayerCornSeedPacks : int = 0
if (Purchase := Purchases[0]):
set NumPlayerCornSeedPacks = Purchase(1)
# Limit to at least 1 packet.
# If the player has the maximum amount, the offer displays with a disabled purchase button.
NumCornSeedPacks := Max(1, Entitlements.corn_seed_pack{}.MaxCount - NumPlayerCornSeedPacks)
Règles de validation des offres
Une offre ou un pack d'offres valide doit respecter les règles ci-dessous. Les achats qui ne respectent pas ces conditions ne seront pas approuvés. Les règles qui définissent une offre valide sont les suivantes :
Il est impossible de définir plus de 5 offres imbriquées.
Le nombre total d'identificateurs d'objet ne peut dépasser 100 par offre. Autrement dit, le nombre total d'objets différents vendus en une seule fois est de 100 maximum.
Le prix de l'offre doit être compris entre 50 et 5 000 V-bucks, et ne peut être qu'un multiple de 50.
Le texte par défaut du
nomd'une offre ne doit pas comporter plus de 50 caractères.Le texte par défaut de la
descriptionde l'offre ne doit pas comporter plus de 500 caractères.Le texte par défaut de la
description courted'une offre ne doit pas comporter plus de 100 caractères.Une offre doit contenir au moins un objet.
Une offre ne peut pas contenir une quantité d'objet supérieure au
nombre maximalde cet objet.Une offre ne contient pas d'objet durable dont la propriété
MaxCount> 1.
Vous pouvez choisir d'ajouter des restrictions concernant l'emplacement de diffusion de vos offres et les personnes pouvant les consulter. Pour en savoir plus, consultez la page Restrictions relatives aux transactions sur l'île.
Créer une vitrine
Maintenant que vos objets, vos offres et vos packs sont configurés, vous devez disposer d'un endroit pour les vendre.
L'interface utilisateur par défaut
L'IU de la vitrine par défaut s'ouvre sur une liste de tous les objets et offres que vous avez ajoutés. Le premier objet de la liste est mis en évidence, et l'aperçu correspondant s'affiche dans une fenêtre en regard de la liste.
Les vitrines peuvent comporter plusieurs pages.
Si les listes comportent plus de cinq éléments, vous pouvez les faire défiler.
Un joueur déclenche le processus d'achat en appelant la méthode BuyOffer ou en utilisant la vitrine par défaut avec la méthode ShowOffersDialog. Vous trouverez ci-dessous des exemples d'appareils que vous pouvez utiliser pour intégrer le processus d'achat via la vitrine à la conception de votre jeu :
Appareil Volume
Chronomètre de Scene Graph
PNJ
Appareil de conversation
Lors de la conception d'une vitrine, il est préférable de laisser le joueur décider quand ouvrir la fenêtre d'achat. Si vous ignorez ce choix et imposez aux joueurs le processus d'achat, vous limitez leur liberté d'action et risquez de provoquer leur mécontentement.
Toutes les offres comportent les boutons Acheter et Inspecter, qui ouvrent des fenêtres du marché permettant d'acheter un objet ou d'examiner le contenu d'une offre. Seuls les packs disposent d'un bouton Inspecter le pack.
Le marché se ferme lorsque vous sélectionnez le bouton Fermer.
Le développeur contrôle entièrement l'expérience dans la boutique :
Vous déterminez les objets ou les propriétés de jeu que vous souhaitez proposer à vos joueurs.
Vous fixez le prix de chaque offre ou pack.
Vous avez la possibilité de présenter votre propre vitrine ou d'utiliser l'interface utilisateur prédéfinie de la vitrine Fortnite.
IU de la vitrine
Cet extrait de code définit un rappel d'événement générique qui ouvre l'interface utilisateur prédéfinie de la vitrine Fortnite. Le rappel peut se produire suite à un abonnement, à l'appui sur une touche, à un événement de conversation, etc.
OnEvent(Agent:agent):void=
if(Player:= player[Agent]):
spawn{ShowOffersDialog(Player, array{
ExampleOffers.shovel{},
ExampleOffers.cornseedpacket{}
})}
Gérer les achats
Cet extrait contient une offre d'achat générique. Un message d'erreur s'affiche si l'achat échoue.
TryBuyOffer(Player:player, Offer : offer)<suspends>:void =
Result := BuyOffer(Player, Offer)
if (not Result?):
Print("Failed to buy the {offer.name} offer.")Afin de faciliter le dépannage des achats ayant échoué, vous devez inclure un moyen permettant d'identifier l'achat concerné dans le message d'erreur, par exemple en mentionnant le nom de l'offre dans le message d'erreur ci-dessus.
Fonctions supplémentaires
Objets aléatoires payants
Il existe deux méthodes pour proposer des objets aléatoires payants sur votre île :
Vous pouvez les proposer directement à la vente contre des V-bucks.
Vous pouvez les proposer indirectement en permettant aux joueurs d'acheter avec des V-Bucks des objets échangeables contre une récompense aléatoire ou un objet ayant une incidence sur la probabilité d'en recevoir une.
Lors de la création d'un objet qui accorde une récompense aléatoire, vous devez définir PaidRandomItem sur true.
Si vous proposez du contenu pouvant être utilisé pour obtenir une récompense aléatoire, vous devez utiliser la fonction RestrictPaidRandomItems afin d'empêcher les joueurs n'y ayant pas accès d'acquérir la récompense aléatoire.
OnEvent(Agent:agent):void=
if (Player := player[Agent]):
if (RestrictPaidRandomItems[Player]):
Print("Player is not allowed to purchase PaidRandomItems.")
else:
Print("Player is allowed to purchase PaidRandomItems.")
Incitations directes à l'achat
Si votre île comporte des incitations directes à l'achat, vous devez utiliser la fonction RestrictDirectPromptsToPurchase pour déterminer si un joueur peut ou non recevoir l'incitation.
OnEvent(Agent:agent):void=
if (Player:= player[Agent]):
if (RestrictDirectPromptsToPurchase[Player]):
Print("Player is not allowed to receive direct purchase prompts.")
else:
Print("Player is allowed to receive direct purchase prompts.")
Incidence sur le jeu
Si l'objet que vous vendez procure un avantage significatif sur votre île, vous devez activer la propriété ConsequentialToGameplay.
Les objets qui ont une incidence sur le jeu procurent aux joueurs qui les achètent un avantage significatif dans le jeu. Cet avantage peut être direct (par exemple, en augmentant la vitesse de progression, la force ou les capacités du joueur) ou indirect (par exemple, un objet qui donne accès à un autre objet ayant un impact significatif sur la vitesse de progression du joueur ou sur ses chances de gagner).
S'il existe une alternative à l'objet que vous vendez, accessible gratuitement à tous les joueurs au moment où l'offre est présentée, et qui offre le même avantage, alors il n'est pas nécessaire d'activer ConsequentialToGameplay. Si un objet de gameplay a un impact secondaire, mais sans conséquence sur le jeu, comme c'est le cas des programmes de couleurs des tenues dont la visibilité est légèrement différente selon les environnements, ou des différentes emotes qui produisent des mouvements corporels distincts, il n'est pas considéré comme ayant une incidence sur le jeu.
# The base entitlement you should define for ALL of your entitlements in your experience.
my_island_entitlement := class<abstract><castable>(entitlement){}
CornSeedPacket<public> := module:
Name<public><localizes> : message = "Corn seed pack"
Description<public><localizes> : message = "A pack of corn seeds. Opening a pack yields 10 corn seeds for planting."
ShortDescription<public><localizes> : message = "Contains 10 corn seeds for planting."
cornseedpacket<public> := class<concrete>(my_island_entitlement):
var Name<override>:message = CornSeedPacket.Name