private void kickBall(PlayerInterface player) { // calculate the dot product of the vector pointing to the ball // and the player's heading Vector2D ToBall = player.Ball().Pos().subtractToCopy(player.Pos()); double dot = player.Heading().Dot(ToBall.normalizeToCopy()); // the dot product is used to adjust the shooting force. The more // directly the ball is ahead, the more forceful the kick double power = Prm.MaxShootingForce * dot; // Try to setup a pass PlayerInterface receiver = player.Team().getSomeoneElse(player); if (receiver != null) { Vector2D BallTarget = receiver.Pos().subtractToCopy(player.Ball().Pos()); // BallTarget=AddNoiseToKick(player.Ball().Pos(), BallTarget); if (player.isReadyForNextKick()) { receiver.receiveMessage(new ReceivePassTelegram()); player.Kick(BallTarget, Prm.MaxShootingForce); } } else { System.err.println("In RL-kickBall, no receivers?"); Vector2D KickDirection = new Vector2D(Math.random() - .5d, Math.random() - .5d); if (player.isReadyForNextKick()) { player.Kick(KickDirection, power); } else { System.err.println( "RL Version ofkickBall was called when agent was not ready for kick, shouldn't happen"); } } // change state player.GetFSM().changeState(ChaseBall.Instance()); }