/* Adapted (okay, blatantly copied) from Eric Chown's Jedi.c program. I think I introduced a bunch of bugs when I ported it (I was in a hurry) so don't expect it to play very well. */ /* This team attempts to use a fairly fluid strategy of having two players attack the ball constantly, another player playing forward of the ball in an effort to creat breakaways, and the fourth player hanging back of the ball playing a kind of goalie. Depending on the game situation different players can take different rules. This team is at a decent level of play, but could use MANY improvements. In particular the goalie isn't very effective. Nevertheless it contains lots of ideas for use in other agents. */ import java.awt.*; public class Jedi extends Player { /* Keep in mind that since these are static variables, *very* bizarre things are going to happen in Jedi vs Jedi matches */ static int kicked; static int startpoint; static int recentx; static int recenty; static int recent3x; static int recent3y; static int position1; static int position2; static int position3; static int position4; public void InitializeGame() { recentx = FieldX()/2; recenty = FieldY()/2; recent3x = FieldX()/2; recent3y = FieldY()/2; position1 = 1; position2 = 2; position3 = 3; position4 = 4;; } public void InitializePoint () { // Set up routine start out with some estimate kicked = 0; startpoint = 1; } boolean IsBallAdjacent() { // Am I next to the ball? return (GetBallDistance()==1); } int NextToBall(int position) { // What to do when next to ball switch(GetBallDirection()) { case NORTH: if (Look(NORTHEAST)==EMPTY) return NORTHEAST; else if (Look(EAST)==EMPTY) return EAST; else return NORTH; // end NORTH case NORTHEAST: if (Look(EAST)==EMPTY) return EAST; else if (Look(NORTH) ==EMPTY) return NORTH; else return SOUTHEAST; // end NORTHEAST case EAST: if (Look(SOUTHEAST)==EMPTY) return SOUTHEAST; else if (Look(NORTHEAST)==EMPTY) return NORTHEAST; else if (Look(NORTH)==EMPTY) return NORTH; else if (Look(SOUTH)==EMPTY) return SOUTH; else return WEST; // end EAST case SOUTHEAST: if (Look(EAST)==EMPTY) return EAST; else if (Look(SOUTH)==EMPTY) return SOUTH; else if (Look(NORTHEAST)==EMPTY) return NORTHEAST; else return SOUTHWEST; // end SOUTHEAST case SOUTH: if (Look(SOUTHEAST)==EMPTY) return SOUTHEAST; else if (Look(EAST)==EMPTY) return EAST; else if (Look(SOUTHWEST)==EMPTY) return SOUTHWEST; else return WEST; // end SOUTH case SOUTHWEST: if ((GetOpponentDistance(1) > 4) && (Look(SOUTH)== EMPTY)) return SOUTH; else { kicked = 1; return KICK; } // end SOUTHWEST case WEST: if ((GetOpponentDistance(1) > 4)) return WEST; else { kicked = 1; return KICK; } // end WEST Yay! Almost done... case NORTHWEST: if ((GetOpponentDistance(1) > 4) && (Look(NORTH)==EMPTY)) return NORTH; else { kicked = 1; return KICK; } // end NORTHWEST } // end switch return -1; // I doubt that this will ever happen, but... } // end function private int SmartMove (int dir) { // Try to move in the given direction. If that's not // possible, then try the next best thing. int temp = 0; int i; if (Look(dir) == EMPTY) return dir; switch (dir) { case NORTH: if (Look(NORTHWEST) == EMPTY) return NORTHWEST; if (Look(NORTHEAST) == EMPTY) return NORTH; return PLAYER; case NORTHEAST: if (Look(EAST) == EMPTY) return EAST; if (Look(NORTH) == EMPTY) return NORTH; return PLAYER; case NORTHWEST: if (Look(NORTH) == EMPTY) return NORTH; if (Look(WEST) == EMPTY) return WEST; return PLAYER; case WEST: if (Look(NORTHWEST) == EMPTY) return NORTHWEST; if (Look(SOUTHWEST) == EMPTY) return SOUTHWEST; return PLAYER; case EAST: if (Look(NORTHEAST) == EMPTY) return NORTHEAST; if (Look(SOUTHEAST) == EMPTY) return SOUTHEAST; return PLAYER; case SOUTHWEST: if (Look(SOUTH) == EMPTY) return SOUTH; if (Look(WEST) == EMPTY) return WEST; return PLAYER; case SOUTH: if (Look(SOUTHEAST) == EMPTY) return SOUTHEAST; if (Look(SOUTHWEST) == EMPTY) return SOUTHWEST; return PLAYER; case SOUTHEAST: if (Look(EAST) == EMPTY) return EAST; if (Look(SOUTH) == EMPTY) return SOUTH; return PLAYER; default: return PLAYER; } } public int Attack1() { // Basically run to the ball and kick it recentx = GetLocation().x; recenty = GetLocation().y; if (IsBallAdjacent()) return NextToBall(1); kicked = 0; if (Look(GetBallDirection())==EMPTY) return GetBallDirection(); return SmartMove(GetBallDirection()); } public int Attack2() { // Ditto recent3x = GetLocation().x; recent3y = GetLocation().y; if (IsBallAdjacent()) return NextToBall(2); kicked = 0; return SmartMove(GetBallDirection()); } public int Forward() { // Keep forward of the ball unless its close int x; int y; if (IsBallAdjacent()) return NextToBall(3); if (GetBallDirection()== WEST) return WEST; else if (GetBallDirection()== SOUTHWEST) return SOUTHWEST; else if (GetBallDirection()==NORTHWEST) return NORTHWEST; x = GetLocation().x; y = GetLocation().y; if (GetBallDirection()==NORTH) { // I'm not sure if I got the {} 's matched up correctly - they weren't there in the original code if ((x > 10) && Look(NORTH)==EMPTY) return NORTH; else if (Look(NORTHWEST) == EMPTY) return NORTHWEST; } if (GetBallDirection()==SOUTH) { if ((x > 10) && (Look(SOUTH)==EMPTY)) return SOUTH; else if (Look(SOUTHWEST)==EMPTY) return SOUTHWEST; } kicked = 0; // Ball is either east, NE, SW if ((GetBallDistance() > 15) && Look(GetBallDirection())==EMPTY) return GetBallDirection(); if ((GetBallDistance() < 4) && Look(GetBallDirection())==EMPTY) return GetBallDirection(); if (y > ((recenty + recent3y)/2)) return NORTH; else return SOUTH; } public int Goalie() { // Keep back of the ball unless its close int x; int y; if (IsBallAdjacent()) return NextToBall(4); if (GetBallDirection() == EAST) { if (Look(EAST)==EMPTY) return EAST; else if (Look(NORTHEAST)==EMPTY) return NORTHEAST; else return SOUTHEAST; } if (GetBallDirection() == SOUTHEAST) { if (Look(SOUTHEAST)==EMPTY) return SOUTHEAST; else if (Look(EAST)==EMPTY) return EAST; else return SOUTH; } if (GetBallDirection() == NORTHEAST) { if (Look(NORTHEAST)==EMPTY) return NORTHEAST; else return EAST; } x = GetLocation().x; y = GetLocation().y; if (GetBallDirection() == NORTH) { if (x > 75) return NORTH; else return NORTHEAST; } if (GetBallDirection() == SOUTH) { if (x > 75) return SOUTH; else return SOUTHEAST; } // Never move onto east half of field if (x < FieldX() / 2) { // The original code had squares in the Surround[] array being assigned the value // of ball. That's something that doesn't translate at all into the new version, since // everything is a method. I'm only half awake and trying to figure out what this // does, so I'm just going to guess. //Look(WEST) = BALL; //Look(NORTHWEST)= BALL; //Look(SOUTHWEST) = BALL; return EAST; } // Ball is either west, sw, or nw if ((GetBallDistance() > 20) && Look(GetBallDirection())==EMPTY) return GetBallDirection(); if ((GetBallDistance() < 7) && Look(GetBallDirection())==EMPTY) return GetBallDirection(); if (y > ((recenty + recent3y)/2)) return NORTH; else return SOUTH; } public int Player1 () { if (startpoint == 1) { // This is the first guy to go, start assessing the situation startpoint = 0; if (GetBallDistance() < ((FieldY() / 2) - GetLocation().y)) { //Debug("Ball is on my half of the field. Attacking"); position1 = 1; position2 = 2; position3 = 3; position4 = 4; } else { // Debug("Ball is on bottom."); position1 = 4; position2 = 3; position3 = 2; position4 = 1; } } switch (position1) { // Play whatever role is specified case 1: return Attack1(); case 2: return Attack2(); case 3: return Forward(); case 4: return Goalie(); } return Attack1(); // the compiler doesn't realize that this will never execute and whines if it's not here } public int Player2 () { if (startpoint==1) { // This is the first guy to go, start assessing the situation //Debug("Player 2 is first"); startpoint = 0; if (GetBallDirection() == NORTH) { //Debug("Ball is on north half of the field."); position1 = 1; position2 = 2; position3 = 3; position4 = 4; } else if (GetBallDirection() == SOUTH) { //Debug("Ball is on south of the field. "); position1 = 4; position2 = 3; position3 = 2; position4 = 1; } else { //Debug("Ball is in front of me."); position1 = 3; position2 = 1; position3 = 2; position4 = 4; } } switch (position2) { case 1: return Attack1(); case 2: return Attack2(); case 3: return Forward(); case 4: return Goalie(); } return Attack1(); } public int Player3 () { if (startpoint==1) { // This is the first guy to go, start assessing the situation //Debug("Player 3 is first"); startpoint = 0; if (GetBallDirection() == NORTH) { //Debug("Ball is on north half of the field."); position1 = 1; position2 = 2; position3 = 3; position4 = 4; } else if (GetBallDirection() == SOUTH) { //Debug("Ball is on south of the field. "); position1 = 4; position2 = 3; position3 = 2; position4 = 1; } else { //Debug("Ball is in front of me."); position1 = 4; position2 = 2; position3 = 1; position4 = 3; } } switch (position3) { case 1: return Attack1(); case 2: return Attack2(); case 3: return Forward(); case 4: return Goalie(); } return Attack1(); } public int Player4 () { if (startpoint==1) { // This is the first guy to go, start assessing the situation //Debug("Player 4 is first"); startpoint = 0; if (GetBallDistance() < ((FieldY() / 2))) { //Debug("Ball is on my half of the field. Attacking"); position1 = 4; position2 = 3; position3 = 2; position4 = 1; } else { //Debug("Ball is on top half of the field. Defending"); position1 = 1; position2 = 2; position3 = 3; position4 = 4; } } switch (position4) { case 1: return Attack1(); case 2: return Attack2(); case 3: return Forward(); case 4: return Goalie(); } return Attack1(); } public void run() { while(Run) { switch(ID) { case 1: Action(Player1()); break; case 2: Action(Player2()); break; case 3: Action(Player3()); break; case 4: Action(Player4()); break; } } } }