void GoToPoint::call() { double dis_to_point; double dir_to_point; Vector2D agent_p = m_world->me().pos; double ang_permisible; double turn_parameter; Vector2D velocidad; double dash_parameter; double const dash_power_rate = 0.006, effort = 0.8; double const inertia_moment = 5.0; dis_to_point = (m_target - agent_p).mag(); dir_to_point = Rad2Deg( atan2( m_target.y - agent_p.y , m_target.x - agent_p.x) ); if( dis_to_point > m_radius ) // El agente no ha llegado al punto { ang_permisible = Rad2Deg( atan2( m_radius , dis_to_point ) ); turn_parameter = dir_to_point - m_world->me().angleDeg(); turn_parameter = entre180( turn_parameter ); velocidad.x = m_world->me().speed_amount; velocidad.y = m_world->me().speed_dir; if( ang_permisible < turn_parameter * 0.1 || dis_to_point > 25.0 ) ang_permisible = 25.0; if( fabs(turn_parameter) > ang_permisible ) // el agente no esta bien alineado al punto { velocidad = Vector2D::fromPolar( velocidad.x, Deg2Rad(velocidad.y) ); turn_parameter = turn_parameter *(1.0 + inertia_moment*velocidad.mag() ); turn_parameter = entre180( turn_parameter ); m_command->append_turn( turn_parameter ); } else { velocidad = Vector2D::fromPolar( velocidad.x, Deg2Rad(velocidad.y - m_world->me().angleDeg()) ); dash_parameter = ( dis_to_point - velocidad.x ) / ( dash_power_rate * effort ); if( dash_parameter > 100.0) dash_parameter = 100.0; if( m_dash_override ) m_command->append_dash( m_dash_power ); else m_command->append_dash( dash_parameter ); } } else { // El agente llegó al punto } }
void FreezeBall::call() { const BodySensor & body = m_world->gameData().sensor_handler.last_sense; const ServerParam & param = m_world->gameData().game_parameter.server_param; double pow_needed; double angle_needed; Vector2D zero_vel(0.0, 0.0); Vector2D p = m_world->me().pos; // Posición del agente double theta = m_world->me().angleDeg(); // Orientación del agente Vector2D vn = m_world->estBallVelocity(); Vector2D bn = m_world->estBallPosition(); Vector2D pv = Vector2D::fromPolar( body.speed_amount, Deg2Rad( body.speed_direction + theta ) ); Vector2D pn_bn; // vector de bn a pn Vector2D pn = p + pv; //Posición del agente en el siguiente ciclo pn_bn = pn-bn; double dist = pn_bn.mag(); double dir_diff = std::abs( entre180( theta - Rad2Deg( pn_bn.angle() ) ) ); double f = 1 - 0.25*(dir_diff/180.0) -0.25*(dist/param.kickable_margin); if( f == 0.0 ) f = 0.001; if( vn.x == 0.0 && vn.y == 0.0 ) { pow_needed = 0.0; angle_needed = 0.0; } else { pow_needed = vn.mag() / ( param.kick_power_rate * f ) ; angle_needed = entre180( Rad2Deg( std::atan2( vn.y, vn.x ) ) + 180 - theta); } m_command->append_kick( pow_needed, angle_needed ); }