Tuesday, April 23, 2019

architecture - How should my game characters store their abilities/spells?


I'm new to game development and a bit confused about how to effectively store an object's access to certain spells/abilities.


The player and mob objects are all generated from the same class. However, each object may have access to different abilities and spells. How do I keep track of a specific object's access to these?


Example: My player object might have access to Fireball and Haste, while a goblin might have access to Confusion.


I followed the RogueBasin Python Libtcod tutorial, and I understand how to attach a spell function to scroll use. I'm just not sure how to emulate a character memorizing a spell and using it as an ability.



Answer



The idea is to have spell objects hold some reference to the in-code action you want that spell to do.



Python's first-class functions make this quite nice (I'll assume Python 2.7.x):


class Spell:
def __init__(self, name, description, activationFunction):
self.name = name
self.description = description
self.activationFunction = activationFunction
def cast(self, gameState):
return self.activationFunction(self, gameState)

# Create a function to be called when the spell is cast. Give it as many

# parameters as you like.
def activationFunction(thisSpell, gameState):
print thisSpell.name, 'was cast at game state', gameState

# Pass the function to a spell when instantiating it
fireballSpell = Spell('Fireball','standard spam spell', activationFunction)

# Cast the spell (with a dummy value representing the gameState parameter)
fireballSpell.cast("zero")


This prints


Fireball was cast at game state zero

You could then store instances of Spell in some class Creature if you like. You could add a caster parameter to every spell to which the creature passes self, or whatever other parameters you'd like.


Instead of defing the activationFunction, you could also create an anonymous function with lambda. (Though only if it fits on one line… Sorry if I got your hopes up.)




For language-completeness:


In JavaScript, Lua, CL, and other FP-languages or languages with first-class functions, the above works with few conceptual modifications.


For a similar idea in C#, Java, C++ and OOP-languages, the strategy pattern is a good analogue for this. (Some even write Python in this style. I wouldn't bother.)


In C or other system programming languages you could use function pointers, but those can quickly get fiddly to work with. It may just be best to declare one big function struct SpellResult castSpell(...) that takes all spell parameters, then switches on a passed-in enum spellType specifying which particular spell was meant. Values of that enum could then be stored by other game objects, for passing to castSpell.



No comments:

Post a Comment

Simple past, Present perfect Past perfect

Can you tell me which form of the following sentences is the correct one please? Imagine two friends discussing the gym... I was in a good s...