Working off of the list of improvements for Oracle’s Eye, I managed to improve the hit detection somewhat.
I was originally thinking about changing the movement code completely. Instead of freely moving about, the Player and Ball would move in a tile-based manner. I spent a bit of time thinking and writing about how I would go about implementing a tile-based game, and I still believe that it might make some things easier. I could also start adding different objects easily.
But when I sat down to code, I decided to continue to do what seems to work for me: mold the existing project until it works.
A major problem with the movement is that the Ball can get stuck in Walls. It can bounce back out normally, but if the Player is too close, it will get stuck in the Wall. Unfortunately, one of the ways I tried to avoid problems with movement causes a very annoying bug. If the Ball moves into the Wall, it is supposed to move back out at twice the distance. It looks like it bounces back out. But if the Player is touching the Ball, it stops moving. Well, if it stops moving, it won’t bounce back because the reverse of stationary doesn’t exist! The next update through, if the Player moves, the Ball wants to move with the Player; however, because it is stuck in the Wall, it “bounces back”. The result is that the Ball looks like it is going the exact opposite way that the Player would expect, which makes the game feel buggy. And not the good, on-purpose buggy, either.
I’m not a fan of guessing with my code. If X = X + 1 doesn’t seem to work, I don’t just automatically turn it into X = X – 1. I prefer to analyze my code and try to determine what exactly is going wrong. In this case, I found that each update, the Player moves, then the Ball moves. Then the Kyra engine’s tree is walked, which allows me to accurately handle collision detection. The next step is to check if the Player collided with a Wall. No problem there. I just reverse the direction of the Player, move him, then change his direction to STOPPED. Then I check if the Player collided with the Ball. If it does, then the Ball will take on the direction of the Player. It makes sense in most cases. If the Player touches a stationary Ball, the Ball should act as if it had been kicked in the same direction that the Player was moving.
When the Ball is near a Wall, however, the Player can kick a Ball, and the Ball can bounce off the Wall. Now the Player and the Ball overlap. Again, it is not a big problem. If the Player moves, the Ball follows the Player. The problem occurs when the two overlap AND the Ball is overlapping the Wall. The Player moves, makes the Ball move, but then the Ball wants to reverse itself.
I found that most of the Ball/Wall overlap can be avoided by changing the order of the collision checking code. The Ball will check for collisions first, then the Player will do the same. The Ball might still get stuck in the Wall, but I’ve found that it is a quite a bit more rare and not as dire a situation. It is a lot harder to reproduce the issue, but of course, right when I was about to say that the problem was completely solved, it occurred.
In any case, it was a quick fix and didn’t require any new code. I’ll probably continue to work on this same issue, but for now it has been vastly improved. I think I will also want to change the size of the Ball. The diameter of the Ball is the width of a Tile, which makes it very difficult to maneuver. If there is a single Tile opening between two Walls, a player might find it incredibly frustrating to try to get the Ball in between. It is part of the reason why I was thinking about using Tile based movement. I should eliminate this problem entirely. Of course, Duke Nukem Forever has had its engine gutted and replaced a number of times, and I would actually like to complete this game soon. B-)
Download files: EDIT: I decided to take down this set of downloads. For both tar.gz and .zip files, it comes to about 16.5MB, and I’m running out of space on my server apparently. This update doesn’t exactly merit its own release, so I will remove it and allow space for better uploads.