naev 0.10.4
player_fleet.c
Go to the documentation of this file.
1/*
2 * See Licensing and Copyright notice in naev.h
3 */
10#include "naev.h"
13#include "player_fleet.h"
14
15#include "array.h"
16#include "dialogue.h"
17#include "escort.h"
18#include "land.h"
19#include "equipment.h"
20
24void pfleet_update (void)
25{
28 for (int i=0; i<array_size(player_ships); i++) {
29 const PlayerShip_t *ps = &player_ships[i];
30 if (ps->deployed)
31 player.fleet_used += ps->p->ship->points;
32 }
33
34 /* Redistribute the cargo. */
36}
37
45int pfleet_toggleDeploy( PlayerShip_t *ps, int deploy )
46{
47 /* When undeploying we want to make sure cargo fits. */
48 if (ps->deployed && !deploy) {
49 int idx;
50 Pilot *p = ps->p;
51 int q = pilot_cargoUsed( p ); /* Amount we have to allocate. */
52 int f = pfleet_cargoFree() - pilot_cargoFree( p ); /* Real free amount. */
53 if (f < q) {
54 char buf_amount[ECON_MASS_STRLEN], buf_free[ECON_MASS_STRLEN], buf_needed[ECON_MASS_STRLEN];
55 tonnes2str( buf_amount, q );
56 tonnes2str( buf_free, -f );
57 tonnes2str( buf_needed, q-f );
58 if (!dialogue_YesNo( _("Not Enough Cargo Space"), _("Your ship '%s' has %s of cargo but there is only %s of free space in the rest of the fleet. Get rid of %s of cargo to shrink your fleet?"), p->name, buf_amount, buf_free, buf_needed ))
59 return -1;
60 }
61 /* Try to make room for the commodities. */
62 idx = -1;
63 for (int i=0; i<array_size(player.p->escorts); i++) {
64 Escort_t *e = &player.p->escorts[i];
65 Pilot *pe = pilot_get( e->id );
66 if (pe == NULL)
67 continue;
68 if (e->type != ESCORT_TYPE_FLEET)
69 continue;
70 if (strcmp( pe->name, p->name )==0) {
71 idx = i;
72 break;
73 }
74 }
75 if (idx < 0)
76 WARN(_("Player deployed ship '%s' not found in escort list!"), p->name);
77 else
79
80 /* Try to add the cargo. */
81 for (int i=0; i<array_size(p->commodities); i++) {
82 PilotCommodity *pc = &p->commodities[i];
84 pilot_cargoRm( p, pc->commodity, pc->quantity );
85 }
86 }
87 ps->deployed = deploy;
88 if (!ps->deployed) {
89 pilot_stackRemove( ps->p );
90 pilot_free( ps->p );
91 }
92 else
93 pfleet_deploy( ps );
95
96 /* Have to update GUI. */
97 equipment_updateShips( land_getWid( LAND_WINDOW_EQUIPMENT ), NULL );
98 return 0;
99}
100
110{
111 double a;
112 vec2 v;
113
114 /* Get the position. */
115 a = RNGF() * 2. * M_PI;
116 vec2_cset( &v, player.p->solid->pos.x + 50.*cos(a),
117 player.p->solid->pos.y + 50.*sin(a) );
118
119 /* Add the escort to the fleet. */
120 escort_createRef( player.p, ps->p, &v, NULL, a, ESCORT_TYPE_FLEET, 1, -1 );
121
122 /* Initialize. */
123 ai_pinit( ps->p, "escort" );
124 pilot_reset( ps->p );
125 pilot_setFlag( ps->p, PILOT_INVINC_PLAYER );
126 pilot_rmFlag( ps->p, PILOT_PLAYER );
127
128 /* AI only knows how to use auto weapon sets. */
129 pilot_weaponAuto( ps->p );
130
131 return 0;
132}
133
134static void shipCargo( PilotCommodity **pclist, Pilot *p, int remove )
135{
136 for (int i=array_size(p->commodities)-1; i>=0; i--) {
137 const PilotCommodity *pc = &p->commodities[i];
138 int q = pc->quantity;
139 int added;
140
141 /* Mission cargo gets added independently. */
142 if (pc->id > 0)
143 array_push_back( pclist, *pc );
144 else {
145 /* See if it can be added. */
146 added = 0;
147 for (int j=0; j<array_size(*pclist); j++) {
148 PilotCommodity *lc = &(*pclist)[j];
149
150 /* Ignore mission cargo. */
151 if (lc->id > 0)
152 continue;
153
154 /* Cargo must match. */
155 if (pc->commodity != lc->commodity)
156 continue;
157
158 lc->quantity += q;
159 added = 1;
160 break;
161 }
162 if (!added)
163 array_push_back( pclist, *pc );
164 }
165
166 /* Remove the cargo. TODO use pilot_cargoRm somehow. */
167 if (remove)
168 array_erase( &p->commodities, &pc[0], &pc[1] );
169 }
170
171 /* Update cargo. */
172 if (remove)
173 pilot_cargoCalc( p );
174}
175
176static int pc_cmp( const void *pa, const void *pb )
177{
178 const PilotCommodity *pca, *pcb;
179 pca = (const PilotCommodity*) pa;
180 pcb = (const PilotCommodity*) pb;
181
182 return pcb->commodity->price - pca->commodity->price;
183}
184
189{
191
192 /* First build up a list of all the potential cargo. */
193 shipCargo( &pclist, player.p, 1 );
194 for (int i=0; i<array_size(player.p->escorts); i++) {
195 Escort_t *e = &player.p->escorts[i];
196 Pilot *pe = pilot_get( e->id );
197 if (pe == NULL)
198 continue;
199 if (e->type != ESCORT_TYPE_FLEET)
200 continue;
201 shipCargo( &pclist, pe, 1 );
202 }
203
204 /* Sort based on base price. */
205 qsort( pclist, array_size(pclist), sizeof(PilotCommodity), pc_cmp );
206
207 /* Re-add the cargo. */
208 for (int i=0; i<array_size(pclist); i++) {
209 int q;
210 PilotCommodity *pc = &pclist[i];
211
212 if (pc->id > 0)
213 q = pilot_cargoAdd( player.p, pc->commodity, pc->quantity, pc->id );
214 else
215 q = pfleet_cargoAdd( pc->commodity, pc->quantity );
216#ifdef DEBUGGING
217 if (q != pc->quantity)
218 WARN(_("Failure to add cargo '%s' to player fleeet. Only %d of %d added."), pc->commodity->name, q, pc->quantity );
219#endif /* DEBUGGING */
220 (void) q;
221 }
222
223 array_free( pclist );
224}
225
232{
233 if (player.p == NULL)
234 return 0;
235 int cargo_used = pilot_cargoUsed( player.p );
236 if (player.fleet_capacity <= 0)
237 return cargo_used;
238 for (int i=0; i<array_size(player.p->escorts); i++) {
239 const Escort_t *e = &player.p->escorts[i];
240 const Pilot *pe = pilot_get( e->id );
241 if (pe == NULL)
242 continue;
243 if (e->type != ESCORT_TYPE_FLEET)
244 continue;
245 cargo_used += pilot_cargoUsed( pe );
246 }
247 return cargo_used;
248}
249
256{
257 if (player.p == NULL)
258 return 0;
259 int cargo_free = pilot_cargoFree( player.p );
260 if (player.fleet_capacity <= 0)
261 return cargo_free;
262 for (int i=0; i<array_size(player.p->escorts); i++) {
263 const Escort_t *e = &player.p->escorts[i];
264 const Pilot *pe = pilot_get( e->id );
265 if (pe == NULL)
266 continue;
267 if (e->type != ESCORT_TYPE_FLEET)
268 continue;
269 cargo_free += pilot_cargoFree( pe );
270 }
271 return cargo_free;
272}
273
281{
282 if (player.p == NULL)
283 return 0;
284 int amount = pilot_cargoOwned( player.p, com );
285 if (player.fleet_capacity <= 0)
286 return amount;
287 for (int i=0; i<array_size(player.p->escorts); i++) {
288 const Escort_t *e = &player.p->escorts[i];
289 const Pilot *pe = pilot_get( e->id );
290 if (pe == NULL)
291 continue;
292 if (e->type != ESCORT_TYPE_FLEET)
293 continue;
294 amount += pilot_cargoOwned( pe, com );
295 }
296 return amount;
297}
298
306int pfleet_cargoAdd( const Commodity *com, int q )
307{
308 if (player.p == NULL)
309 return 0;
310 int added = pilot_cargoAdd( player.p, com, q, 0 );
311 if ((player.fleet_capacity <= 0) || (q-added <= 0))
312 return added;
313 for (int i=0; i<array_size(player.p->escorts); i++) {
314 Escort_t *e = &player.p->escorts[i];
315 Pilot *pe = pilot_get( e->id );
316 if (pe == NULL)
317 continue;
318 if (e->type != ESCORT_TYPE_FLEET)
319 continue;
320 added += pilot_cargoAdd( pe, com, q-added, 0 );
321 if (q-added <= 0)
322 break;
323 }
324 return added;
325}
326
335int pfleet_cargoRm( const Commodity *com, int q, int jet )
336{
337 int removed;
338 if (player.p == NULL)
339 return 0;
340 if (player.fleet_capacity <= 0)
341 return pilot_cargoRm( player.p, com, q );
342 removed = 0;
343 for (int i=0; i<array_size(player.p->escorts); i++) {
344 Escort_t *e = &player.p->escorts[i];
345 Pilot *pe = pilot_get( e->id );
346 if (pe == NULL)
347 continue;
348 if (e->type != ESCORT_TYPE_FLEET)
349 continue;
350
351 if (jet)
352 removed += pilot_cargoJet( pe, com, q-removed, 0 );
353 else
354 removed += pilot_cargoRm( pe, com, q-removed );
355
356 if (q-removed <= 0)
357 break;
358 }
359 if (q-removed > 0) {
360 if (jet)
361 removed += pilot_cargoJet( player.p, com, q, 0 );
362 else
363 removed += pilot_cargoRm( player.p, com, q );
364 }
365 return removed;
366}
367
374{
376 shipCargo( &pclist, player.p, 0 );
377 for (int i=0; i<array_size(player.p->escorts); i++) {
378 Escort_t *e = &player.p->escorts[i];
379 Pilot *pe = pilot_get( e->id );
380 if (pe == NULL)
381 continue;
382 if (e->type != ESCORT_TYPE_FLEET)
383 continue;
384 shipCargo( &pclist, pe, 0 );
385 }
386 return pclist;
387}
388
396{
398 int q = pilot_cargoOwned( player.p, com );
399 if (q > 0) {
400 PFleetCargo fc = { .p=player.p, .q=q };
401 array_push_back( &plist, fc );
402 }
403 for (int i=0; i<array_size(player.p->escorts); i++) {
404 Escort_t *e = &player.p->escorts[i];
405 Pilot *pe = pilot_get( e->id );
406 if (pe == NULL)
407 continue;
408 if (e->type != ESCORT_TYPE_FLEET)
409 continue;
410 q = pilot_cargoOwned( pe, com );
411 if (q > 0) {
412 PFleetCargo fc = { .p=pe, .q=q };
413 array_push_back( &plist, fc );
414 }
415 }
416 return plist;
417}
int ai_pinit(Pilot *p, const char *ai)
Initializes the pilot in the ai.
Definition: ai.c:434
Provides macros to work with dynamic arrays.
#define array_free(ptr_array)
Frees memory allocated and sets array to NULL.
Definition: array.h:158
#define array_erase(ptr_array, first, last)
Erases elements in interval [first, last).
Definition: array.h:140
static ALWAYS_INLINE int array_size(const void *array)
Returns number of elements in the array.
Definition: array.h:168
#define array_push_back(ptr_array, element)
Adds a new element at the end of the array.
Definition: array.h:129
#define array_create(basic_type)
Creates a new dynamic array of ‘basic_type’.
Definition: array.h:93
int dialogue_YesNo(const char *caption, const char *fmt,...)
Runs a dialogue with both yes and no options.
Definition: dialogue.c:344
void equipment_updateShips(unsigned int wid, const char *str)
Updates the player's ship window.
Definition: equipment.c:1698
unsigned int escort_createRef(Pilot *p, Pilot *pe, const vec2 *pos, const vec2 *vel, double dir, EscortType_t type, int add, int dockslot)
Creates an escort from a reference.
Definition: escort.c:187
void escort_rmListIndex(Pilot *p, int i)
Remove from escorts list.
Definition: escort.c:75
unsigned int land_getWid(int window)
Gets the WID of a window by type.
Definition: land.c:963
Header file with generic functions and naev-specifics.
void pilot_free(Pilot *p)
Frees and cleans up a pilot.
Definition: pilot.c:3428
void pilot_stackRemove(Pilot *p)
Tries to remove a pilot from the stack.
Definition: pilot.c:3506
void pilot_reset(Pilot *pilot)
Resets a pilot.
Definition: pilot.c:3088
Pilot * pilot_get(unsigned int id)
Pulls a pilot out of the pilot_stack based on ID.
Definition: pilot.c:589
int pilot_cargoFree(const Pilot *p)
Gets the pilot's free cargo space.
Definition: pilot_cargo.c:51
int pilot_cargoRm(Pilot *pilot, const Commodity *cargo, int quantity)
Tries to get rid of quantity cargo from pilot.
Definition: pilot_cargo.c:390
int pilot_cargoOwned(const Pilot *pilot, const Commodity *cargo)
Gets how many of the commodity a pilot has.
Definition: pilot_cargo.c:36
int pilot_cargoJet(Pilot *p, const Commodity *cargo, int quantity, int simulate)
Tries to get rid of quantity cargo from pilot, jetting it into space.
Definition: pilot_cargo.c:404
int pilot_cargoAdd(Pilot *pilot, const Commodity *cargo, int quantity, unsigned int id)
Tries to add quantity of cargo to pilot.
Definition: pilot_cargo.c:169
int pilot_cargoUsed(const Pilot *p)
Gets how much cargo ship has on board.
Definition: pilot_cargo.c:189
void pilot_cargoCalc(Pilot *pilot)
Calculates how much cargo ship has left and such.
Definition: pilot_cargo.c:220
void pilot_weaponAuto(Pilot *p)
Tries to automatically set and create the pilot's weapon set.
int player_ships(char **sships, glTexture **tships)
Returns a buffer with all the player's ships names.
Definition: player.c:2606
const PlayerShip_t * player_getShipStack(void)
Gets the array (array.h) of the player's ships.
Definition: player.c:2623
Player_t player
Definition: player.c:73
int pfleet_toggleDeploy(PlayerShip_t *ps, int deploy)
Toggles a player ship as deployed.
Definition: player_fleet.c:45
int pfleet_deploy(PlayerShip_t *ps)
Deploys a player's pilot.
Definition: player_fleet.c:109
PilotCommodity * pfleet_cargoList(void)
Gets a list of all the cargo in the fleet.
Definition: player_fleet.c:373
PFleetCargo * pfleet_cargoListShips(const Commodity *com)
Gets the list of ships that are carry a certain commodity in the player fleet and the amount they are...
Definition: player_fleet.c:395
int pfleet_cargoFree(void)
Gets the total amount of free cargo space in the player's fleet.
Definition: player_fleet.c:255
void pfleet_cargoRedistribute(void)
Redistributes the cargo in the player's fleet.
Definition: player_fleet.c:188
int pfleet_cargoOwned(const Commodity *com)
Gets the total amount of a commodity type owned by the player's fleet.
Definition: player_fleet.c:280
int pfleet_cargoAdd(const Commodity *com, int q)
Adds some cargo to the player's fleet.
Definition: player_fleet.c:306
int pfleet_cargoRm(const Commodity *com, int q, int jet)
Removes some cargo from the player's fleet.
Definition: player_fleet.c:335
int pfleet_cargoUsed(void)
Gets the total cargo space used by the player's fleet.
Definition: player_fleet.c:231
void pfleet_update(void)
Updates the used fleet capacity of the player.
Definition: player_fleet.c:24
static const double a[]
Definition: rng.c:247
Represents a commodity.
Definition: commodity.h:43
char * name
Definition: commodity.h:44
double price
Definition: commodity.h:52
Stores an escort.
Definition: pilot.h:199
unsigned int id
Definition: pilot.h:202
EscortType_t type
Definition: pilot.h:201
Stores a pilot commodity.
Definition: pilot.h:172
const Commodity * commodity
Definition: pilot.h:173
unsigned int id
Definition: pilot.h:175
int quantity
Definition: pilot.h:174
The representation of an in-game pilot.
Definition: pilot.h:210
Solid * solid
Definition: pilot.h:220
const Ship * ship
Definition: pilot.h:219
char * name
Definition: pilot.h:212
Escort_t * escorts
Definition: pilot.h:326
Player ship.
Definition: player.h:73
int deployed
Definition: player.h:80
Pilot * p
Definition: player.h:74
Pilot * p
Definition: player.h:101
int fleet_used
Definition: player.h:130
int fleet_capacity
Definition: player.h:131
int points
Definition: ship.h:99
vec2 pos
Definition: physics.h:22
Represents a 2d vector.
Definition: vec2.h:32
double y
Definition: vec2.h:34
double x
Definition: vec2.h:33