示例#1
0
文件: faction.c 项目: Jazzkovsky/naev
/**
 * @brief Returns an array of faction ids.
 *
 *    @param *n Writes the number of elements.
 *    @param which Which factions to get. (0,1,2,3 : all, friendly, neutral, hostile)
 *    @return A pointer to an array, or NULL.
 */
int *faction_getGroup( int *n, int which )
{
   int *group;
   int i;

   /* Set defaults. */
   group = NULL;
   *n = 0;

   switch(which) {
      case 0: /* 'all' */
         *n = faction_nstack;
         group = malloc(sizeof(int) * *n);
         for(i = 0; i < faction_nstack; i++)
            group[i] = i;
         break;

      case 1: /* 'friendly' */
         for(i = 0; i < faction_nstack; i++)
            if(areAllies(FACTION_PLAYER, i)) {
               (*n)++;
               group = realloc(group, sizeof(int) * *n);
               group[*n - 1] = i;
            }
         break;

      case 2: /* 'neutral' */
         for(i = 0; i < faction_nstack; i++)
            if(!areAllies(FACTION_PLAYER, i) && !areEnemies(FACTION_PLAYER, i)) {
               (*n)++;
               group = realloc(group, sizeof(int) * *n);
               group[*n - 1] = i;
            }
         break;

      case 3: /* 'hostile' */
         for(i = 0; i < faction_nstack; i++)
            if(areEnemies(FACTION_PLAYER, i)) {
               (*n)++;
               group = realloc(group, sizeof(int) * *n);
               group[*n - 1] = i;
            }
         break;

      default:
         /* Defaults have already been set. */
         break;
   }

   return group;
}
示例#2
0
文件: input.c 项目: Kinniken/naev
/**
 * @brief Performs an appropriate action when a planet is clicked.
 *
 *    @param planet Index of the planet.
 *    @param autonav Whether to autonav to the target.
 *    @return Whether the click was used.
 */
int input_clickedPlanet( int planet, int autonav )
{
   Planet *pnt;
   pnt = cur_system->planets[ planet ];

   if (!planet_isKnown(pnt))
      return 0;

   if (autonav) {
      player_targetPlanetSet( planet );
      player_autonavPnt( pnt->name );
      return 1;
   }

   if (planet == player.p->nav_planet && input_isDoubleClick((void*)pnt)) {
      player_hyperspacePreempt(0);
      if (planet_hasService(pnt, PLANET_SERVICE_LAND)) {
         if ((pnt->faction >= 0) && (areEnemies( player.p->faction, pnt->faction ) && !pnt->bribed))
            player_hailPlanet();
         else
            player_land();
      }
   }
   else
      player_targetPlanetSet( planet );

   input_clicked( (void*)pnt );
   return 1;
}
示例#3
0
文件: faction.c 项目: Jazzkovsky/naev
/**
 * @brief Gets the faction character associated to it's standing with the player.
 *
 * Use this to do something like "\e%c", faction_getColourChar( some_faction ) in the
 *  font print routines.
 *
 *    @param f Faction to get the colour of based on player's standing.
 *    @return The character associated to the faction.
 */
char faction_getColourChar( int f )
{
   if (f<0) return 'I';
   else if (areEnemies(FACTION_PLAYER,f)) return 'H';
   else if (areAllies(FACTION_PLAYER,f)) return 'F';
   else return 'N';
}
示例#4
0
文件: faction.c 项目: Jazzkovsky/naev
/**
 * @brief Gets the colour of the faction based on it's standing with the player.
 *
 * Used to unify the colour checks all over.
 *
 *    @param f Faction to get the colour of based on player's standing.
 *    @return Pointer to the colour.
 */
const glColour* faction_getColour( int f )
{
   if (f<0) return &cInert;
   else if (areAllies(FACTION_PLAYER,f)) return &cFriend;
   else if (areEnemies(FACTION_PLAYER,f)) return &cHostile;
   else return &cNeutral;
}
示例#5
0
/**
 * @brief Checks to see if f is an enemy of e.
 *
 * @usage if f:areEnemies( faction.get( "Dvaered" ) ) then
 *
 *    @luaparam f Faction to check against.
 *    @luaparam e Faction to check if is an enemy.
 *    @luareturn true if they are enemies, false if they aren't.
 * @luafunc areEnemies( f, e )
 */
static int factionL_areenemies( lua_State *L )
{
   int f, ff;
   f  = luaL_validfaction(L,1);
   ff = luaL_validfaction(L,2);

   lua_pushboolean(L, areEnemies( f, ff ));
   return 1;
}
示例#6
0
文件: economy.c 项目: Arakash/naev
/**
 * @brief Calculates the resistance between two star systems.
 *
 *    @param A Star system to calculate the resistance between.
 *    @param B Star system to calculate the resistance between.
 *    @return Resistance between A and B.
 */
static double econ_calcJumpR( StarSystem *A, StarSystem *B )
{
   double R;

   /* Set to base to ensure price change. */
   R = ECON_BASE_RES;

   /* Modify based on system conditions. */
   R += (A->nebu_density + B->nebu_density) / 1000.; /* Density shouldn't affect much. */
   R += (A->nebu_volatility + B->nebu_volatility) / 100.; /* Volatility should. */

   /* Modify based on global faction. */
   if ((A->faction != -1) && (B->faction != -1)) {
      if (areEnemies(A->faction, B->faction))
         R += ECON_FACTION_MOD * ECON_BASE_RES;
      else if (areAllies(A->faction, B->faction))
         R -= ECON_FACTION_MOD * ECON_BASE_RES;
   }

   /* @todo Modify based on fleets. */

   return R;
}
示例#7
0
文件: comm.c 项目: zid/naev
/**
 * @brief Opens a communication dialogue with a planet.
 *
 *    @param planet Planet to communicate with.
 *    @return 0 on success.
 */
int comm_openPlanet( Planet *planet )
{
   unsigned int wid;

   /* Must not be disabled. */
   if (!planet_hasService(planet, PLANET_SERVICE_BASIC)) {
      player_message("%s does not respond.", planet->name);
      return 0;
   }

   comm_planet = planet;

   /* Create the generic comm window. */
   wid = comm_open( gl_dupTexture( comm_planet->gfx_space ),
         comm_planet->faction, 0, 0, comm_planet->name );

   /* Add special buttons. */
   if (areEnemies(player->faction, planet->faction) &&
         !planet->bribed)
      window_addButton( wid, -20, 20 + BUTTON_HEIGHT + 20,
            BUTTON_WIDTH, BUTTON_HEIGHT, "btnBribe", "Bribe", comm_bribePlanet );

   return 0;
}
示例#8
0
文件: input.c 项目: Ttech/naev
/**
 * @brief Handles a click event.
 */
static void input_clickevent( SDL_Event* event )
{
   unsigned int pid;
   Pilot *p;
   int mx, my, mxr, myr, pntid, jpid;
   int rx, ry, rh, rw, res;
   double x, y, m, r, rp, d, dp, px, py;
   double ang, angp, mouseang;
   Planet *pnt;
   JumpPoint *jp;
   HookParam hparam[2];

   /* Generate hook. */
   hparam[0].type    = HOOK_PARAM_NUMBER;
   hparam[0].u.num   = event->button.button;
   hparam[1].type    = HOOK_PARAM_SENTINAL;
   hooks_runParam( "mouse", hparam );

   /* Handle zoom. */
   if (event->button.button == SDL_BUTTON_WHEELUP) {
      input_clickZoom( 1.1 );
      return;
   }
   else if (event->button.button == SDL_BUTTON_WHEELDOWN) {
      input_clickZoom( 0.9 );
      return;
   }

   /* Middle mouse enables mouse flying. */
   if (event->button.button == SDL_BUTTON_MIDDLE) {
      player_toggleMouseFly();
      return;
   }

   /* Mouse targetting is left only. */
   if (event->button.button != SDL_BUTTON_LEFT)
      return;

   /* Player must not be NULL. */
   if (player_isFlag(PLAYER_DESTROYED) || (player.p == NULL))
      return;

   px = player.p->solid->pos.x;
   py = player.p->solid->pos.y;
   gl_windowToScreenPos( &mx, &my, event->button.x, event->button.y );
   gl_screenToGameCoords( &x, &y, (double)mx, (double)my );
   if ((mx <= 15 || my <= 15 ) || (my >= gl_screen.h - 15 || mx >= gl_screen.w - 15)) { /* Border */
      x = (mx - (gl_screen.w / 2.)) + px;
      y = (my - (gl_screen.h / 2.)) + py;
      mouseang = atan2(py - y, px -  x);
      angp = pilot_getNearestAng( player.p, &pid, mouseang, 1 );
      ang  = system_getClosestAng( cur_system, &pntid, &jpid, x, y, mouseang );

      if  ((ABS(angle_diff(mouseang, angp)) > M_PI / 64) ||
            ABS(angle_diff(mouseang, ang)) < ABS(angle_diff(mouseang, angp)))
         pid = PLAYER_ID; /* Pilot angle is too great, or planet/jump is closer. */
      if  (ABS(angle_diff(mouseang, ang)) > M_PI / 64 )
         jpid = pntid = -1; /* Asset angle difference is too great. */
   }
   else { /* Radar targeting requires raw coordinates. */
      mxr = event->button.x;
      myr  = gl_screen.rh - event->button.y;
      gui_radarGetPos( &rx, &ry );
      gui_radarGetDim( &rw, &rh );
      if ((mxr > rx && mxr <= rx + rw ) && (myr > ry && myr <= ry + rh )) { /* Radar */
         m = 1;
         gui_radarGetRes( &res );
         x = (mxr - (rx + rw / 2.)) * res + px;
         y = (myr - (ry + rh / 2.)) * res + py;
      }
      else /* Visual (on-screen) */
         m = res = 1. / cam_getZoom();
      dp = pilot_getNearestPos( player.p, &pid, x, y, 1 );
      d  = system_getClosest( cur_system, &pntid, &jpid, x, y );
      rp = MAX( 1.5 * PILOT_SIZE_APROX * pilot_get(pid)->ship->gfx_space->sw / 2 * m,  10. * res);

      if (pntid >=0) { /* Planet is closer. */
         pnt = cur_system->planets[ pntid ];
         r  = MAX( 1.5 * pnt->radius, 100. );
      }
      else if (jpid >= 0) {
         jp = &cur_system->jumps[ jpid ];
         r  = MAX( 1.5 * jp->radius, 100. );
      }
      else {
         r  = 0.;
      }
      /* Reject pilot if it's too far or a valid asset is closer. */
      if (dp > pow2(rp) || (d < pow2(r) && dp < pow2(rp) && dp >  d))
         pid = PLAYER_ID;
      if (d > pow2(r)) /* Planet or jump point is too far. */
         jpid = pntid = -1;
   }

   if (pid != PLAYER_ID) {
      /* Apply an action if already selected. */
      if (!pilot_isFlag(player.p, PILOT_DEAD) && (pid == player.p->target)) {
         p = pilot_get(pid);
         if (pilot_isDisabled(p) || pilot_isFlag(p, PILOT_BOARDABLE))
            player_board();
         else
            player_hail();
      }
      else
         player_targetSet( pid );
   }
   else if (pntid >= 0) { /* Planet is closest. */
      if (pntid == player.p->nav_planet) {
         pnt = cur_system->planets[ pntid ];
         if (planet_hasService(pnt, PLANET_SERVICE_LAND) &&
               (!areEnemies( player.p->faction, pnt->faction ) || pnt->bribed ))
            player_land();
         else
            player_hailPlanet();
      }
      else
         player_targetPlanetSet( pntid );
   }
   else if (jpid >= 0) { /* Jump point is closest. */
      jp = &cur_system->jumps[ jpid ];
      if (jpid == player.p->nav_hyperspace) {
         if (space_canHyperspace(player.p)) {
            if (!paused) player_autonavAbort(NULL);
            player_jump();
         }
         else
            player_autonavStart();
      }
      else
         player_targetHyperspaceSet( jpid );
   }
}
示例#9
0
文件: weapon.c 项目: zid/naev
/**
 * @brief Renders an individual weapon.
 *
 *    @param w Weapon to render.
 *    @param dt Current delta tick.
 */
static void weapon_render( Weapon* w, const double dt )
{
   double x,y, cx,cy, gx,gy;
   glTexture *gfx;
   double z;
   glColour c = { .r=1., .g=1., .b=1. };

   switch (w->outfit->type) {
      /* Weapons that use sprites. */
      case OUTFIT_TYPE_AMMO:
      case OUTFIT_TYPE_TURRET_AMMO:
      case OUTFIT_TYPE_BOLT:
      case OUTFIT_TYPE_TURRET_BOLT:
         gfx = outfit_gfx(w->outfit);

         /* Alpha based on strength. */
         c.a = w->strength;

         /* Outfit spins around. */
         if (outfit_isProp(w->outfit, OUTFIT_PROP_WEAP_SPIN)) {
            /* Check timer. */
            w->anim -= dt;
            if (w->anim < 0.) {
               w->anim = outfit_spin(w->outfit);

               /* Increment sprite. */
               w->sprite++;
               if (w->sprite >= gfx->sx*gfx->sy)
                  w->sprite = 0;
            }

            /* Render. */
            if (outfit_isBolt(w->outfit) && w->outfit->u.blt.gfx_end)
               gl_blitSpriteInterpolate( gfx, w->outfit->u.blt.gfx_end,
                     w->timer / w->life,
                     w->solid->pos.x, w->solid->pos.y,
                     w->sprite % (int)gfx->sx, w->sprite / (int)gfx->sx, &c );
            else
               gl_blitSprite( gfx, w->solid->pos.x, w->solid->pos.y,
                     w->sprite % (int)gfx->sx, w->sprite / (int)gfx->sx, &c );
         }
         /* Outfit faces direction. */
         else {
            if (outfit_isBolt(w->outfit) && w->outfit->u.blt.gfx_end)
               gl_blitSpriteInterpolate( gfx, w->outfit->u.blt.gfx_end,
                     w->timer / w->life,
                     w->solid->pos.x, w->solid->pos.y, w->sx, w->sy, &c );
            else
               gl_blitSprite( gfx, w->solid->pos.x, w->solid->pos.y, w->sx, w->sy, &c );
         }
         break;

      /* Beam weapons. */
      case OUTFIT_TYPE_BEAM:
      case OUTFIT_TYPE_TURRET_BEAM:
         gfx = outfit_gfx(w->outfit);

         /* Zoom. */
         gl_cameraZoomGet( &z );

         /* Position. */
         gl_cameraGet( &cx, &cy );
         gui_getOffset( &gx, &gy );
         x = (w->solid->pos.x - cx)*z + gx;
         y = (w->solid->pos.y - cy)*z + gy;

         /* Set up the matrix. */
         glMatrixMode(GL_PROJECTION);
         glPushMatrix();
            glTranslated( x, y, 0. );
            glRotated( 270. + w->solid->dir / M_PI * 180., 0., 0., 1. );

         /* Preparatives. */
         glEnable(GL_TEXTURE_2D);
         glBindTexture( GL_TEXTURE_2D, gfx->texture);
         glShadeModel(GL_SMOOTH);

         /* Actual rendering. */
         glBegin(GL_QUAD_STRIP);

            /* Start faded. */
            ACOLOUR(cWhite, 0.);

            glTexCoord2d( w->anim, 0. );
            glVertex2d( -gfx->sh/2.*z, 0. );

            glTexCoord2d( w->anim, 1. );
            glVertex2d( +gfx->sh/2.*z, 0. );

            /* Full strength. */
            COLOUR(cWhite);

            glTexCoord2d( w->anim + 10. / gfx->sw, 0. );
            glVertex2d( -gfx->sh/2.*z, 10.*z );

            glTexCoord2d( w->anim + 10. / gfx->sw, 1. );
            glVertex2d( +gfx->sh/2.*z, 10.*z );

            glTexCoord2d( w->anim + 0.8*w->outfit->u.bem.range / gfx->sw, 0. );
            glVertex2d( -gfx->sh/2.*z, 0.8*w->outfit->u.bem.range*z );

            glTexCoord2d( w->anim + 0.8*w->outfit->u.bem.range / gfx->sw, 1. );
            glVertex2d( +gfx->sh/2.*z, 0.8*w->outfit->u.bem.range*z );

            /* Fades out. */
            ACOLOUR(cWhite, 0.);

            glTexCoord2d( w->anim + w->outfit->u.bem.range / gfx->sw, 0. );
            glVertex2d( -gfx->sh/2.*z, w->outfit->u.bem.range*z );

            glTexCoord2d( w->anim + w->outfit->u.bem.range / gfx->sw, 1. );
            glVertex2d( +gfx->sh/2.*z, w->outfit->u.bem.range*z );
         glEnd(); /* GL_QUAD_STRIP */

         /* Do the beam movement. */
         w->anim -= 5. * dt;
         if (w->anim <= -gfx->sw)
            w->anim += gfx->sw;

         /* Clean up. */
         glDisable(GL_TEXTURE_2D);
         glShadeModel(GL_FLAT);
         glPopMatrix(); /* GL_PROJECTION */
         gl_checkErr();
         break;

      default:
         WARN("Weapon of type '%s' has no render implemented yet!",
               w->outfit->name);
         break;
   }
}


/**
 * @brief Checks to see if the weapon can hit the pilot.
 *
 *    @param w Weapon to check if hits pilot.
 *    @param p Pilot to check if is hit by weapon.
 *    @return 1 if can be hit, 0 if can't.
 */
static int weapon_checkCanHit( Weapon* w, Pilot *p )
{
   Pilot *parent;

   /* Can't hit invincible stuff. */
   if (pilot_isFlag(p, PILOT_INVINCIBLE))
      return 0;

   /* Can never hit same faction. */
   if (p->faction == w->faction)
      return 0;

   /* Go "through" dead pilots. */
   if (pilot_isFlag(p, PILOT_DEAD))
      return 0;

   /* Player behaves differently. */
   if (w->faction == FACTION_PLAYER) {

      /* Always hit without safety. */
      if (!weapon_safety)
         return 1;

      /* Always hit target. */
      else if (w->target == p->id)
         return 1;

      /* Always hit hostiles. */
      else if (pilot_isFlag(p, PILOT_HOSTILE))
         return 1;

      /* Always hit unbribed enemies. */
      else if (!pilot_isFlag(p, PILOT_BRIBED) &&
            areEnemies(w->faction, p->faction))
        return 1;

      /* Miss rest - can be neutral/ally. */
      else
         return 0;
   }

   /* Let hostiles hit player. */
   if (p->faction == FACTION_PLAYER) {
      parent = pilot_get(w->parent);
      if (parent != NULL) {
         if (pilot_isFlag(parent, PILOT_BRIBED))
            return 0;
         if (pilot_isFlag(parent, PILOT_HOSTILE))
            return 1;
      }
   }

   /* Hit non-allies. */
   if (areEnemies(w->faction, p->faction))
      return 1;

   return 0;
}
示例#10
0
文件: unidiff.c 项目: naev/naev
/**
 * @brief Applies a hunk and adds it to the diff.
 *
 *    @param diff Diff to which the hunk belongs.
 *    @param hunk Hunk to apply.
 *    @return 0 on success.
 */
static int diff_patchHunk( UniHunk_t *hunk )
{
   Planet *p;
   int a, b;

   switch (hunk->type) {

      /* Adding an asset. */
      case HUNK_TYPE_ASSET_ADD:
         planet_updateLand( planet_get(hunk->u.name) );
         return system_addPlanet( system_get(hunk->target.u.name), hunk->u.name );
      /* Removing an asset. */
      case HUNK_TYPE_ASSET_REMOVE:
         return system_rmPlanet( system_get(hunk->target.u.name), hunk->u.name );
      /* Making an asset a black market. */
      case HUNK_TYPE_ASSET_BLACKMARKET:
         planet_addService( planet_get(hunk->u.name), PLANET_SERVICE_BLACKMARKET );
         return 0;
      /* Making an asset a legal market. */
      case HUNK_TYPE_ASSET_LEGALMARKET:
         planet_rmService( planet_get(hunk->u.name), PLANET_SERVICE_BLACKMARKET );
         return 0;

      /* Adding a Jump. */
      case HUNK_TYPE_JUMP_ADD:
         return system_addJumpDiff( system_get(hunk->target.u.name), hunk->node );
      /* Removing a jump. */
      case HUNK_TYPE_JUMP_REMOVE:
         return system_rmJump( system_get(hunk->target.u.name), hunk->u.name );

      /* Adding a tech. */
      case HUNK_TYPE_TECH_ADD:
         return tech_addItem( hunk->target.u.name, hunk->u.name );
      /* Removing a tech. */
      case HUNK_TYPE_TECH_REMOVE:
         return tech_rmItem( hunk->target.u.name, hunk->u.name );

      /* Changing asset faction. */
      case HUNK_TYPE_ASSET_FACTION:
         p = planet_get( hunk->target.u.name );
         if (p==NULL)
            return -1;
         hunk->o.name = faction_name( p->faction );
         return planet_setFaction( p, faction_get(hunk->u.name) );
      case HUNK_TYPE_ASSET_FACTION_REMOVE:
         return planet_setFaction( planet_get(hunk->target.u.name), faction_get(hunk->o.name) );

      /* Making a faction visible. */
      case HUNK_TYPE_FACTION_VISIBLE:
         return faction_setInvisible( faction_get(hunk->target.u.name), 0 );
      /* Making a faction invisible. */
      case HUNK_TYPE_FACTION_INVISIBLE:
         return faction_setInvisible( faction_get(hunk->target.u.name), 1 );
      /* Making two factions allies. */
      case HUNK_TYPE_FACTION_ALLY:
         a = faction_get( hunk->target.u.name );
         b = faction_get( hunk->u.name );
         if (areAllies(a, b))
            hunk->o.data = 'A';
         else if (areEnemies(a, b))
            hunk->o.data = 'E';
         else
            hunk->o.data = 0;
         faction_addAlly( a, b );
         faction_addAlly( b, a );
         return 0;
      /* Making two factions enemies. */
      case HUNK_TYPE_FACTION_ENEMY:
         a = faction_get( hunk->target.u.name );
         b = faction_get( hunk->u.name );
         if (areAllies(a, b))
            hunk->o.data = 'A';
         else if (areEnemies(a, b))
            hunk->o.data = 'E';
         else
            hunk->o.data = 0;
         faction_addEnemy( a, b );
         faction_addEnemy( b, a );
         return 0;
      /* Making two factions neutral (removing enemy/ally statuses). */
      case HUNK_TYPE_FACTION_NEUTRAL:
         a = faction_get( hunk->target.u.name );
         b = faction_get( hunk->u.name );
         if (areAllies(a, b))
            hunk->o.data = 'A';
         else if (areEnemies(a, b))
            hunk->o.data = 'E';
         else
            hunk->o.data = 0;
         faction_rmAlly( a, b );
         faction_rmAlly( b, a );
         faction_rmEnemy( a, b );
         faction_rmEnemy( b, a );
         return 0;
      /* Resetting the alignment state of two factions. */
      case HUNK_TYPE_FACTION_REALIGN:
         a = faction_get( hunk->target.u.name );
         b = faction_get( hunk->u.name );
         if (hunk->o.data == 'A') {
            faction_rmEnemy(a, b);
            faction_rmEnemy(b, a);
            faction_addAlly(a, b);
            faction_addAlly(b, a);
         }
         else if (hunk->o.data == 'E') {
            faction_rmAlly(a, b);
            faction_rmAlly(b, a);
            faction_addEnemy(a, b);
            faction_addAlly(b, a);
         }
         else {
            faction_rmAlly( a, b );
            faction_rmAlly( b, a );
            faction_rmEnemy( a, b );
            faction_rmEnemy( b, a );
         }
         return 0;

      default:
         WARN(_("Unknown hunk type '%d'."), hunk->type);
         break;
   }

   return -1;
}