Per un roguelike a cui stavo lavorando, ho implementato un sistema flessibile basato sui dati per generare drop. L'ho documentato qui . È essenzialmente un piccolo DSL per la selezione di un numero di elementi scelti a caso.
Una semplice goccia assomiglia a:
1-10 copper coin
Dice solo di far cadere un numero casuale di monete di rame tra 1 e 10. Le cose diventano più flessibili quando aggiungi rami:
one of
turquoise stone (50%)
onyx stone (25%)
malachite stone (15%)
jade stone (10%)
Un "uno di" seleziona uno dei suoi rami figlio in base alle probabilità date e quindi lo valuta. Le gocce possono far cadere più di un oggetto:
any of
turquoise stone (50%)
onyx stone (25%)
malachite stone (15%)
jade stone (10%)
Questo valuterà tutti i sottogruppi e li lascerà cadere se passa un tiro contro la loro probabilità. Ci sono anche alcuni altri rami per selezionare un oggetto in base al livello del dungeon e del giocatore.
Poiché questi possono diventare complessi, consente anche di definire macro denominate, essenzialmente funzioni che espandono un'espressione di ramo e che possono essere riutilizzate in più drop. In questo modo se, ad esempio, tutti i nani rilasciano lo stesso tipo di bottino, puoi creare una singola macro per quello e usarla in tutti quei tipi di mostri invece di copiare e incollare enormi tavoli di lancio.
Un esempio della caduta di un mostro :
:: ancient dragon
glyph = D
groups = dragon
drops
(coins)
2-3(1:8) one of
(any-weapon)
(any-armor)
Qui, (coins)
, (any-weapon)
, e (any-armor)
sono tutte le chiamate di macro:
(any-armor)
one of
(shield)
(helm)
(boots)
(gloves)
(cloak)
(robe)
(soft-armor)
(hard-armor)
che a sua volta chiama cose come:
(cloak)
one near level
cloak (10)
velvet cloak (20)
fur-lined cloak (50)
Puoi annidare le espressioni di rilascio in modo arbitrario profondamente come un vero linguaggio di programmazione. Questo ti dà la componibilità che un semplice approccio basato su tabella non darà.
Come tutti i sistemi basati sui dati, puoi sopraffarti costruendo drop impenetrabilmente complessi, ma soddisfa i miei obiettivi:
- Essere in grado di specificare quali elementi vengono eliminati completamente al di fuori del codice.
- Semplice da implementare il sistema principale nel codice.
- Essere in grado di sintonizzare ciò che i mostri specifici rilasciano in modo che il giocatore possa fare esplorazioni mirate. ("Ho bisogno di una collana. Cercherò i nani poiché tendono a lasciarli cadere.")
Il codice C # che implementa questo è qui .