In an object-oriented design, there's always one object that's responsible for something to happen. I often get stuck when trying to figure out which object is most suited for executing the code of a specific task. Let me give you some examples:
1) A shot hitting an enemy. Which object is responsible for carrying out the consequences of this event, the shot or the enemy? In a very simple game it probably wouldn't matter which object hosted the code. It could either look something like this:
function Shot:handleCollision(o)
if o:getType() == "enemy" then
o:makeDamage(10)
playSound("shot_hit.wav")
self:destroy()
end
end
or:
function Enemy:handleCollision(o)
if o:getType() == "shot" then
self:makeDamage(10)
playSound("shot_hit.wav")
o:destroy()
end
end
This looks simple and good and all, but what if you decide to implement an enemy which gets hurt when being hit by the shot, but letting the it through itself, continuing in the same direction? Or what if you want an enemy where the sound isn't played if it gets hit in its left leg? These are quite silly scenarios, but I hope they make my wonderings clear.
2) Moving platforms. One easy way to implement it is to make the platform move every object whose positions correspond with the position of an object standing on the platform the same length that the platform is moved, but it could also be implemented the other way round: make each movable object search for moving platforms in its own update() method, and move itself if the position of the platform relative to its own position is right. Problems like the ones in the collison case can arise regardless of which method is chosen, for example: what if certain objects shouldn't be moved by moving platforms? And what if the platforms only want to move objects standing on it upon certain conditions?
So, what I want to know is simply your own views and experiences with issues like these. How do you normally decide which object to make responsible for which actions?
I can also imagine a third place to put the logic: some kind of "manager" that handles interaction between objects, for example a "moving platform manager" to which both the objects that want to be moved and the platforms register, and then special cases are handled by the manager alone. I can see this being a dangerous solution though, moving out logic from the classes into a hardcoded hive mind, which could make the code less maintainable and readable.
So, please bombard me with your thoughts about this! And please be indulgent with the quality of my writing, my mother tongue is Swedish and I have some difficulties with expressing my ideas in English.
Thanks!