?? crazytank.java
字號:
/*
該機器人的雷達具有跟蹤功能。
該機器人在遠離敵人時做無規則運動。
該機器人根據敵人的運動狀態提前開槍
*/
package Robot;
import AIRobot.event.*;
import AIRobot.robot.*;
public class CrazyTank extends Robot
{
private double scannedTime;
private double enemyX; //敵人的x坐標
private double enemyY; //敵人的Y坐標
private double velocity; //運動速度
private double enemyVelocity; //敵人運動速度
private double enemyDirection; //敵人車身方向
private double enemyEnergy;//敵人的能量
private double moveTime; //朝一個方向運動的時間
private int bulletPower = 1 ;
private boolean enemyDeath = false;
//執行函數
public void work()
{
doRadar();
if (enemyEnergy == 0)
{
doMove3();
doGun1();
}
else
{
if (distance(getBody().getX(),getBody().getY(),enemyX,enemyY) < 150)
{
doMove3();
doGun3();
}
else
{
doMove1();
doGun1();
}
}
}
//一輪戰斗開始
public void onBegin(BeginEvent beginevent)
{ //初始化
scannedTime = -5;
velocity = 8;
moveTime = 25;
}
//掃描到敵人
public void onScannedRobot( ScannedRobotEvent e )
{
scannedTime = e.getTime();
enemyX = e.getX();
enemyY = e.getY();
enemyVelocity = e.getVelocity();
enemyDirection = e.getHeading();
enemyEnergy = e.getEnergy();
// enemyX[posIndex] = e.getX();
// enemyY[posIndex] = e.getY();
// enemyVelocity[posIndex] = e.getVelocity();
// enemyDirection[posIndex] = e.getHeading();
}
//撞到其他機器人
public void onHitRobot( HitRobotEvent e )
{
//運動改變方向
doGun3();
doMove3();
}
//撞到墻
public void onHitWall( HitWallEvent e )
{
//運動改變方向
changeDirection();
}
//被子彈擊中
//被敵人擊中,改變運動方向
public void onHitByBullet( HitByBulletEvent e )
{
}
public void onRobotDeathEvent( RobotDeathEvent e )
{
enemyDeath = true;
}
/////////////////////////////////////////////////////////////////////
//控制雷達單元
private void doRadar()
{
//雷達鎖定
if( getTime() - scannedTime > 3 ) getRadar().turn(Math.PI);
else{
//雷達轉向敵人,以實現鎖定
double h = heading(getBody().getX(),getBody().getY(),enemyX,enemyY);
double angle = turnAngle(getRadar().getHeading(),h);
getRadar().turn(angle);
}
}
//控制車身單元
private void doMove1()
{
//運動改變方向
if( moveTime-- < 0 ) moveTime = 30;
getBody().move(velocity);
//隨機改變運動方向
java.util.Random random = new java.util.Random();
getBody().turn(random.nextFloat() * Math.PI* 2/3-Math.PI/3);
}
private void doMove2()
{
//改變運動方向始終側對敵人
if( moveTime-- < 0 ) moveTime = 25;
getBody().move(velocity);
double h = heading(getBody().getX(),getBody().getY(),enemyX,enemyY);
double angle = turnAngle(getBody().getHeading(),h + Math.PI/2);
getBody().turn(angle);
}
private void doMove3()
{
//改變運動方向面向敵人運動
if( moveTime-- < 0 ) moveTime = 25;
getBody().move(velocity);
double h = heading(getBody().getX(),getBody().getY(),enemyX,enemyY);
double angle = turnAngle(getBody().getHeading(),h);
getBody().turn(angle);
}
//控制炮管單元
private void doGun1()
{
//炮管轉向敵人要到達的位置
double h = heading(getBody().getX(),getBody().getY(),enemyX,enemyY);
double angle = turnAngle(enemyDirection,h);//敵人運動方向與h的夾角
double bulletVelocity = 20 - 3 * 1;//子彈速度
double gunangle = Math.asin( enemyVelocity * Math.sin(angle) / bulletVelocity);
gunangle = h - gunangle ;//提前射擊的方向
angle = turnAngle( getGun().getHeading(),gunangle );//提前射擊炮口需要轉過的角度
getGun().turn(angle);//轉炮口
if( !enemyDeath )
{
if ( getEnergy() > 1 ) getGun().fire(1);//開炮(能量1)
else if ( enemyEnergy < 4 )getGun().fire(1);
}
}
private void doGun3()
{
//炮管轉向敵人要到達的位置
double h = heading(getBody().getX(),getBody().getY(),enemyX,enemyY);
double angle = turnAngle(enemyDirection,h);//敵人運動方向與h的夾角
double bulletVelocity = 20 - 3 * 3;//子彈速度
double gunangle = Math.asin( enemyVelocity * Math.sin(angle) / bulletVelocity);
gunangle = h - gunangle ;//提前射擊的方向
angle = turnAngle( getGun().getHeading(),gunangle );//提前射擊炮口需要轉過的角度
getGun().turn(angle);//轉炮口
if( !enemyDeath )
{
if ( getEnergy() > 3 ) getGun().fire(3);//開炮(能量3)
else if ( enemyEnergy < 6 )getGun().fire(3);
}
}
//改變運動方向
private void changeDirection()
{
moveTime = 50;
velocity = - velocity ;
}
private void changeDirection2()
{
moveTime = 25;
double h = heading(getBody().getX(),getBody().getY(),enemyX,enemyY);
double angle = turnAngle(getBody().getHeading(),h + Math.PI/2);
getBody().turn(angle);
}
/**
* 標準化一個弧度值,使得 0<= angle <2*PI
*/
public static double stdAngle(double angle)
{
while( angle >= 2*Math.PI ) angle -= 2*Math.PI;
while( angle < 0 ) angle += 2*Math.PI;
return angle;
}
/**
* 計算從 from 到 to 的最小轉動角度
*/
public static double turnAngle(double from, double to)
{
double turnAngle = stdAngle(to) - stdAngle(from);
if( turnAngle > Math.PI ) turnAngle = turnAngle - 2*Math.PI;
else if( turnAngle < -Math.PI ) turnAngle = turnAngle + 2*Math.PI;
return turnAngle;
}
/**
* 計算兩點間的距離
*/
public static double distance(double x1, double y1, double x2, double y2)
{
return Math.sqrt((x1-x2)*(x1-x2)+(y1-y2)*(y1-y2));
}
/**
* 計算兩點連線的方向,此方向角在0到PI*2之間
*/
public static double heading(double x1, double y1, double x2, double y2)
{
double heading;
// special check
double distance = distance(x1,y1,x2,y2);
if( distance == 0 ) return 0;
// normal condition
heading = Math.acos((x2-x1)/distance); //一二象限
if( y1 > y2 ) heading = 2 * Math.PI - heading; //三四象限
return heading;
}
}
?? 快捷鍵說明
復制代碼
Ctrl + C
搜索代碼
Ctrl + F
全屏模式
F11
切換主題
Ctrl + Shift + D
顯示快捷鍵
?
增大字號
Ctrl + =
減小字號
Ctrl + -