Example #1
0
/**
 * @brief Gets the distance from the Vec2.
 *
 * @usage my_vec:dist() -- Gets length of the vector (distance from origin).
 * @usage my_vec:dist( your_vec ) -- Gets distance from both vectors (your_vec - my_vec).
 *
 *    @luaparam v Vector to act as origin.
 *    @luaparam v2 Vector to get distance from, uses origin (0,0) if not set.
 *    @luareturn The distance calculated.
 * @luafunc dist( v, v2 )
 */
static int vectorL_distance( lua_State *L )
{
    LuaVector *v1, *v2;
    double dist;

    /* Get self. */
    v1 = luaL_checkvector(L,1);

    /* Get rest of parameters. */
    v2 = NULL;
    if (lua_gettop(L) > 1) {
        v2 = luaL_checkvector(L,2);
    }

    /* Get distance. */
    if (v2 == NULL)
        dist = vect_odist(&v1->vec);
    else
        dist = vect_dist(&v1->vec, &v2->vec);

    /* Return the distance. */
    lua_pushnumber(L, dist);
    return 1;
}
Example #2
0
File: weapon.c Project: zid/naev
/**
 * @brief The AI of seeker missiles.
 *
 *    @param w Weapon to do the thinking.
 *    @param dt Current delta tick.
 */
static void think_seeker( Weapon* w, const double dt )
{
   double diff;
   double vel;
   Pilot *p;
   int effect;
   Vector2d v;
   double t;

   if (w->target == w->parent) return; /* no self shooting */

   p = pilot_get(w->target); /* no null pilot_nstack */
   if (p==NULL) {
      weapon_setThrust( w, 0. );
      weapon_setTurn( w, 0. );
      return;
   }

   /* Handle by status. */
   switch (w->status) {
      case WEAPON_STATUS_OK:
         if (w->lockon < 0.)
            w->status = WEAPON_STATUS_LOCKEDON;
         break;

      case WEAPON_STATUS_LOCKEDON: /* Check to see if can get jammed */
         if ((p->jam_range != 0.) &&  /* Target has jammer and weapon is in range */
               (vect_dist(&w->solid->pos,&p->solid->pos) < p->jam_range)) {

            /* Check to see if weapon gets jammed */
            if (RNGF() < p->jam_chance - w->outfit->u.amm.resist) {
               w->status = WEAPON_STATUS_JAMMED;
               /* Give it a nice random effect */
               effect = RNG(0,3);
               switch (effect) {
                  case 0: /* Stuck in left loop */
                     weapon_setTurn( w, w->outfit->u.amm.turn );
                     break;
                  case 1: /* Stuck in right loop */
                     weapon_setTurn( w, -w->outfit->u.amm.turn );
                     break;

                  default: /* Blow up. */
                     w->timer = -1.;
                     break;
               }
            }
            else /* Can't get jammed anymore */
               w->status = WEAPON_STATUS_UNJAMMED;
         }

      /* Purpose fallthrough */
      case WEAPON_STATUS_UNJAMMED: /* Work as expected */

         /* Smart seekers take into account ship velocity. */
         if (w->outfit->u.amm.ai == 2) {

            /* Calculate time to reach target. */
            vect_cset( &v, p->solid->pos.x - w->solid->pos.x,
                  p->solid->pos.y - w->solid->pos.y );
            t = vect_odist( &v ) / w->outfit->u.amm.speed;

            /* Calculate target's movement. */
            vect_cset( &v, v.x + t*(p->solid->vel.x - w->solid->vel.x),
                  v.y + t*(p->solid->vel.y - w->solid->vel.y) );

            /* Get the angle now. */
            diff = angle_diff(w->solid->dir, VANGLE(v) );
         }
         /* Other seekers are stupid. */
         else {
            diff = angle_diff(w->solid->dir, /* Get angle to target pos */
                  vect_angle(&w->solid->pos, &p->solid->pos));
         }

         /* Set turn. */
         weapon_setTurn( w, CLAMP( -w->outfit->u.amm.turn, w->outfit->u.amm.turn,
                  10 * diff * w->outfit->u.amm.turn ));
         break;

      case WEAPON_STATUS_JAMMED: /* Continue doing whatever */
         /* Do nothing, dir_vel should be set already if needed */
         break;

      default:
         WARN("Unknown weapon status for '%s'", w->outfit->name);
         break;
   }

   /* Limit speed here */
   vel = MIN(w->outfit->u.amm.speed, VMOD(w->solid->vel) + w->outfit->u.amm.thrust*dt);
   vect_pset( &w->solid->vel, vel, w->solid->dir );
   /*limit_speed( &w->solid->vel, w->outfit->u.amm.speed, dt );*/
}