Let's say you're in a corridor with a monster than can breathe fire powerfully and another monster that doesn't resist fire but is powerful enough to tank one breath. The monster breathes fire and lays down a lava tile like this (marked as '*'):
For this case, the code will make M move towards the player and then since the tile is damaging, try to put it to safety, which is out of sight of the player (marked as 'x' in the corridor behind). M will then continue properly as if there was no damaging tile.
Now let's look at the opposite case:
The same code will trigger, so when reaching the damaging tile, M will try to run to the "safe" spot which, being behind it, will make it move away from the player, going back to its previous location. We enter then an endless loop where M moves east to the damaging tile then west then east again.
This is absurd. Once on the damaging tile, the first check that should be made is "can M move forward normally?" If so there's no reason to force the monster to flee, it should simply continue forward.
EDIT: this doesn't happen in V, as "monster hates grid" and "monster is damaged by terrain" are both identical; to properly fix a potential problem, just replace code for monster_taking_terrain_damage() by
And this also removes duplicate code...
Code:
#x# #.######### #..@...*M.D ###########
Now let's look at the opposite case:
Code:
#x# #.######### #..D..M*..@ ###########
This is absurd. Once on the damaging tile, the first check that should be made is "can M move forward normally?" If so there's no reason to force the monster to flee, it should simply continue forward.
EDIT: this doesn't happen in V, as "monster hates grid" and "monster is damaged by terrain" are both identical; to properly fix a potential problem, just replace code for monster_taking_terrain_damage() by
Code:
bool monster_taking_terrain_damage(struct monster *mon) { return monster_hates_grid(cave, mon, mon->grid); }
Comment