Nearly all movement systems try to avoid taking damage from opponents. One way of doing this is to know where the enemy's bullets are and move somewhere else. The idea is obvious, of course, but implementing a bullet dodging system can be very difficult, because Robocode bots cannot "see" mid-air bullets. In fact, Robocode does not even tell you that an enemy fired a bullet, but it can be deduced from scanning their energy.
Detecting enemy bullets
The first step is to detect an energy drop, which will require a radar lock on the enemy. If the enemy's energy level drops by a value between 0.1 and 3.0 (valid bullet power values), it is likely he fired a bullet. For a basic bullet dodging system, this could be enough to get started.
There are other events that can affect the enemy's energy level, though, and most of them can also be monitored. By adjusting for these changes in the enemy's energy level (which occur between your last scan and your current scan), you can more accurately detect when he fires a bullet.
- If one of your bullets hits the enemy, he will lose energy, and you will be notified in the
onBulletHit(BulletHitEvent bhe)method. You can calculate the energy he loses with
robocode.Rules.getBulletDamage(bhe.getBullet().getPower()), equal to ((4 * bullet power) + (max(bullet power - 1, 0) * 2)).
- If you are hit by the enemy's bullet, he will gain energy, and you will be notified in the
onHitByBullet(HitByBulletEvent hbbe)method. You can calculate the energy he gains with
robocode.Rules.getBulletHitBonus(hbbe.getBullet().getPower()), equal to (3 * bullet power).
- If the enemy runs into a wall, he will lose energy. The amount of energy he loses can be calculated with
robocode.Rules.getWallHitDamage(<enemySpeed>), equal to (enemySpeed * 0.5 - 1) for AdvancedRobots and zero for Robots. However, you cannot accurately detect the enemy's speed when he hits the wall. In the course of one tick (betwen your last scan and your current scan), the enemy can change his speed, run into the wall, take some amount of damage, and have his speed set to zero, which is the speed that you will detect. You could take a best guess at his wall-hit speed based on his previous speed and acceleration, or you could choose to ignore any energy drop that happens on the same tick as a wall-hit.
Reacting to bullet fire
Once you have detected that the enemy has fired a bullet, you must decide how to react.
Many early bullet dodgers just did something to randomize their movement, such as randomly changing direction or speed. This works well for dodging simple targeting strategies, and, correctly tuned, can also create a flat movement profile that works well against somewhat more advanced guns. Other early bullet dodgers, such as TheArtOfWar, would project Head-On Targeting, Linear Targeting, and/or Circular Targeting (three of the most common basic targeting strategies) and move to a location that would avoid all of them.
A major breakthrough in dodging bullets came in a movement system called Wave Surfing, invented by ABC. Basically, if you can accurately detect when the enemy fires a bullet, and you know when and where you are hit by an enemy bullet (using
onHitByBullet(HitByBulletEvent hbbe)), you can reconstruct how the enemy aimed at you (e.g., what bearing offset or GuessFactor at which they fired). In the future, when you detect a bullet being fired, you can simulate their targeting strategy and avoid the spots where you have been hit. To do this accurately also requires accurate simulation of Robocode physics, so you know to which locations you could move before the bullet hits you.