Skip to content

HTTPS clone URL

Subversion checkout URL

You can clone with
or
.
Download ZIP
Fetching contributors…

Cannot retrieve contributors at this time

1104 lines (937 sloc) 28.203 kB
/*
* See Licensing and Copyright notice in naev.h
*/
#include "map_find.h"
#include "naev.h"
#include "log.h"
#include "toolkit.h"
#include "map.h"
#include "dialogue.h"
#include "player.h"
#include "tech.h"
#include "space.h"
#include "nstring.h"
#define MAP_WDWNAME "Star Map" /**< Map window name. */
#define BUTTON_WIDTH 80 /**< Map button width. */
#define BUTTON_HEIGHT 30 /**< Map button height. */
/* Stored checkbox values. */
static int map_find_systems = 1; /**< Systems checkbox value. */
static int map_find_planets = 0; /**< Planets checkbox value. */
static int map_find_outfits = 0; /**< Outfits checkbox value. */
static int map_find_ships = 0; /**< Ships checkbox value. */
/* Misc ugly globals. */
/* Current found stuff. */
static map_find_t *map_found_cur = NULL; /**< Pointer to found stuff. */
static int map_found_ncur = 0; /**< Number of found stuff. */
/* Tech hack. */
static tech_group_t **map_known_techs = NULL; /**< Known techs. */
static Planet **map_known_planets = NULL; /**< Known planets with techs. */
static int map_nknown = 0; /**< Number of known. */
/*
* Prototypes.
*/
/* Init/cleanup. */
static int map_knownInit (void);
static void map_knownClean (void);
/* Toolkit-related. */
static void map_find_check_update( unsigned int wid, char *str );
static void map_findClose( unsigned int wid, char* str );
static int map_findSearchSystems( unsigned int parent, const char *name );
static int map_findSearchPlanets( unsigned int parent, const char *name );
static int map_findSearchOutfits( unsigned int parent, const char *name );
static int map_findSearchShips( unsigned int parent, const char *name );
static void map_findSearch( unsigned int wid, char* str );
/* Misc. */
static int map_sortCompare( const void *p1, const void *p2 );
static void map_sortFound( map_find_t *found, int n );
static char map_getPlanetColourChar( Planet *p );
/* Fuzzy outfit/ship stuff. */
static char **map_fuzzyOutfits( Outfit **o, int n, const char *name, int *len );
static char **map_outfitsMatch( const char *name, int *len );
static char **map_fuzzyShips( Ship **o, int n, const char *name, int *len );
static char **map_shipsMatch( const char *name, int *len );
/**
* @brief Initializes stuff the pilot knows.
*/
static int map_knownInit (void)
{
int i, j;
int ntech, nsys, npnt;
Planet *pnt, **planets;
StarSystem *sys;
tech_group_t **t;
/* Allocate techs. */
planet_getAll( &npnt );
t = malloc( sizeof(tech_group_t*) * npnt );
planets = malloc( sizeof(Planet*) * npnt );
sys = system_getAll( &nsys );
/* Get techs. */
ntech = 0;
for (i=0; i<nsys; i++) {
if (!sys_isKnown( &sys[i] ))
continue;
for (j=0; j<sys[i].nplanets; j++) {
pnt = sys[i].planets[j];
/* Must be real. */
if (pnt->real != ASSET_REAL)
continue;
/* Must be known. */
if (!planet_isKnown( pnt ))
continue;
/* Must have techs. */
if (pnt->tech != NULL) {
planets[ntech] = pnt;
t[ntech] = pnt->tech;
ntech++;
}
}
}
/* Pointer voodoo. */
map_known_techs = t;
map_known_planets = planets;
map_nknown = ntech;
return 0;
}
/**
* @brief Cleans up stuff the pilot knows.
*/
static void map_knownClean (void)
{
if (map_known_techs != NULL)
free( map_known_techs );
map_known_techs = NULL;
if (map_known_planets != NULL)
free( map_known_planets );
map_known_planets = NULL;
map_nknown = 0;
}
/**
* @brief Updates the checkboxes.
*/
static void map_find_check_update( unsigned int wid, char* str )
{
(void) str;
map_find_systems ^= window_checkboxState( wid, "chkSystem" );
map_find_planets ^= window_checkboxState( wid, "chkPlanet" );
map_find_outfits ^= window_checkboxState( wid, "chkOutfit" );
map_find_ships ^= window_checkboxState( wid, "chkShip" );
window_checkboxSet( wid, "chkSystem", map_find_systems );
window_checkboxSet( wid, "chkPlanet", map_find_planets );
window_checkboxSet( wid, "chkOutfit", map_find_outfits );
window_checkboxSet( wid, "chkShip", map_find_ships );
}
/**
* @brief Starts the map search with a specific default type.
*
* @param Parent window's ID.
* @param Default type to search for.
*/
void map_inputFindType( unsigned int parent, char *type )
{
map_find_systems = 0;
map_find_planets = 0;
map_find_outfits = 0;
map_find_ships = 0;
if (strcmp(type,"system")==0)
map_find_systems = 1;
else if (strcmp(type,"planet")==0)
map_find_planets = 1;
else if (strcmp(type,"outfit")==0)
map_find_outfits = 1;
else if (strcmp(type,"ship")==0)
map_find_ships = 1;
map_inputFind(parent, NULL);
}
/**
* @brief Closes the find window.
*/
static void map_findClose( unsigned int wid, char* str )
{
window_close( wid, str );
/* Clean up if necessary. */
if (map_found_cur != NULL)
free( map_found_cur );
map_found_cur = NULL;
/* Clean up. */
map_knownClean();
}
/**
* @brief Goes to a found system to display it.
*/
static void map_findDisplayMark( unsigned int wid, char* str )
{
int pos;
StarSystem *sys;
/* Get system. */
pos = toolkit_getListPos( wid, "lstResult" );
sys = map_found_cur[ pos ].sys;
/* Select. */
map_select( sys, 0 );
map_center( sys->name );
/* Close parent. */
window_close( window_getParent(wid), str );
}
/**
* @brief Displays the results of the find.
*/
static void map_findDisplayResult( unsigned int parent, map_find_t *found, int n )
{
int i;
unsigned int wid;
char **ll;
/* Globals. */
map_found_cur = found;
map_found_ncur = n;
/* Create window. */
wid = window_create( "Search Results", -1, -1, 500, 452 );
window_setParent( wid, parent );
window_setAccept( wid, map_findDisplayMark );
window_setCancel( wid, window_close );
/* The list. */
ll = malloc( sizeof(char*) * n );
for (i=0; i<n; i++)
ll[i] = strdup( found[i].display );
window_addList( wid, 20, -40, 460, 300,
"lstResult", ll, n, 0, NULL );
/* Buttons. */
window_addButton( wid, 100, 20, 100, BUTTON_HEIGHT,
"btnSelect", "Select", map_findDisplayMark );
window_addButton( wid, -100, 20, 100, BUTTON_HEIGHT,
"btnClose", "Cancel", window_close );
}
/**
* @brief qsort compare function for map finds.
*/
static int map_sortCompare( const void *p1, const void *p2 )
{
map_find_t *f1, *f2;
/* Convert pointer. */
f1 = (map_find_t*) p1;
f2 = (map_find_t*) p2;
/* Compare jumps. */
if (f1->jumps > f2->jumps)
return +1;
else if (f1->jumps < f2->jumps)
return -1;
/* Compare distance. */
if (f1->distance > f2->distance)
return +1;
else if (f1->distance < f2->distance)
return -1;
/* If they're the same it doesn't matter, so we'll sort by name. */
return strcasecmp( f1->sys->name, f2->sys->name );
}
/**
* @brief Sorts the map findings.
*/
static void map_sortFound( map_find_t *found, int n )
{
qsort( found, n, sizeof(map_find_t), map_sortCompare );
}
/**
* @brief Gets the distance.
*/
static int map_findDistance( StarSystem *sys, Planet *pnt, int *jumps, double *distance )
{
int i, j;
StarSystem **slist, *ss;
double d;
Vector2d *vs, *ve;
/* Defaults. */
ve = NULL;
/* Special case it's the current system. */
if (sys == cur_system) {
*jumps = 0;
if (pnt != NULL)
*distance = vect_dist( &player.p->solid->pos, &pnt->pos );
else
*distance = 0.;
return 0;
}
/* Calculate jump path. */
slist = map_getJumpPath( jumps, cur_system->name, sys->name, 0, 1, NULL );
if (slist==NULL)
/* Unknown. */
return -1;
/* Distance to first jump point. */
vs = &player.p->solid->pos;
for (j=0; j < cur_system->njumps; j++) {
if (cur_system->jumps[j].target == slist[0]) {
ve = &cur_system->jumps[j].pos;
break;
}
}
if (ve == NULL) {
WARN("Jump to first system not found!");
d = 0.;
}
else
d = vect_dist( vs, ve );
/* Calculate distance. */
for (i=0; i<(*jumps-1); i++) {
ss = slist[i];
/* Search jump points. */
for (j=0; j < ss->njumps; j++) {
/* Get previous jump. */
if (i == 0) {
if (ss->jumps[j].target == cur_system)
vs = &ss->jumps[j].pos;
}
else {
if (ss->jumps[j].target == slist[i-1])
vs = &ss->jumps[j].pos;
}
/* Get next jump. */
if (ss->jumps[j].target == slist[i+1]) {
ve = &ss->jumps[j].pos;
break;
}
}
/* Use current position. */
if (i==0)
vs = &player.p->solid->pos;
#ifdef DEBUGGING
if ((vs==NULL) || (ve==NULL)) {
WARN( "Matching jumps not found, something is up..." );
continue;
}
#endif /* DEBUGGING */
/* Calculate. */
d += vect_dist( vs, ve );
}
/* Account final travel to planet for planet targets. */
if (pnt != NULL) {
ss = slist[ i ];
for (j=0; j < ss->njumps; j++)
if (ss->jumps[j].target == slist[i-1])
vs = &ss->jumps[j].pos;
ve = &pnt->pos;
d += vect_dist( vs, ve );
}
/* Cleanup. */
free(slist);
*distance = d;
return 0;
}
/**
* @brief Searches for a system.
*
* @param name Name to match.
* @return 0 on success.
*/
static int map_findSearchSystems( unsigned int parent, const char *name )
{
int i;
const char *sysname;
StarSystem *sys;
char **names;
int len, n, ret;
map_find_t *found;
/* Search for names. */
sysname = system_existsCase( name );
names = system_searchFuzzyCase( name, &len );
if (names == NULL)
return -1;
/* Exact match. */
if ((sysname != NULL) && (len == 1)) {
/* Select and show. */
sys = system_get(sysname);
if (sys_isKnown(sys)) {
map_select( sys, 0 );
map_center( sysname );
free(names);
return 1;
}
}
/* Construct found table. */
found = NULL;
n = 0;
for (i=0; i<len; i++) {
/* System must be known. */
sys = system_get( names[i] );
if (!sys_isKnown(sys))
continue;
if (found == NULL) /* Allocate results array on first match. */
found = malloc( sizeof(map_find_t) * len );
/* Set more values. */
ret = map_findDistance( sys, NULL, &found[n].jumps, &found[n].distance );
if (ret) {
found[n].jumps = 10000;
found[n].distance = 1e6;
}
/* Set some values. */
found[n].pnt = NULL;
found[n].sys = sys;
/* Set fancy name. */
if (ret)
nsnprintf( found[n].display, sizeof(found[n].display),
"%s (unknown route)", sys->name );
else
nsnprintf( found[n].display, sizeof(found[n].display),
"%s (%d jumps, %.0fk distance)",
sys->name, found[n].jumps, found[n].distance/1000. );
n++;
}
free(names);
/* No visible match. */
if (n==0)
return -1;
/* Sort the found by distance. */
map_sortFound( found, n );
/* Display results. */
map_findDisplayResult( parent, found, n );
return 0;
}
/**
* @brief Searches for a planet.
*
* @param name Name to match.
* @return 0 on success.
*/
static int map_findSearchPlanets( unsigned int parent, const char *name )
{
int i;
char **names;
int len, n, ret;
map_find_t *found;
const char *sysname, *pntname;
StarSystem *sys;
Planet *pnt;
/* Match planet first. */
pntname = planet_existsCase( name );
names = planet_searchFuzzyCase( name, &len );
if (names == NULL)
return -1;
/* Exact match. */
if ((pntname != NULL) && (len == 1)) {
/* Check exact match. */
sysname = planet_getSystem( pntname );
if (sysname != NULL) {
/* Make sure it's known. */
pnt = planet_get( pntname );
if ((pnt != NULL) && planet_isKnown(pnt)) {
/* Select and show. */
sys = system_get(sysname);
if (sys_isKnown(sys)) {
map_select( sys, 0 );
map_center( sysname );
free(names);
return 1;
}
}
}
}
/* Construct found table. */
found = NULL;
n = 0;
for (i=0; i<len; i++) {
/* Planet must be real. */
pnt = planet_get( names[i] );
if (pnt == NULL)
continue;
if (pnt->real != ASSET_REAL)
continue;
if (!planet_isKnown(pnt))
continue;
/* System must be known. */
sysname = planet_getSystem( names[i] );
if (sysname == NULL)
continue;
sys = system_get( sysname );
if (!sys_isKnown(sys))
continue;
if (found == NULL) /* Allocate results array on first match. */
found = malloc( sizeof(map_find_t) * len );
/* Set more values. */
ret = map_findDistance( sys, pnt, &found[n].jumps, &found[n].distance );
if (ret) {
found[n].jumps = 10000;
found[n].distance = 1e6;
}
/* Set some values. */
found[n].pnt = pnt;
found[n].sys = sys;
/* Set fancy name. */
if (ret)
nsnprintf( found[n].display, sizeof(found[n].display),
"\e%c%s (%s, unknown route)", map_getPlanetColourChar(pnt),
names[i], sys->name );
else
nsnprintf( found[n].display, sizeof(found[n].display),
"\e%c%s (%s, %d jumps, %.0fk distance)", map_getPlanetColourChar(pnt),
names[i], sys->name, found[n].jumps, found[n].distance/1000. );
n++;
}
free(names);
/* No visible match. */
if (n==0)
return -1;
/* Sort the found by distance. */
map_sortFound( found, n );
/* Display results. */
map_findDisplayResult( parent, found, n );
return 0;
}
/**
* @brief Gets a colour char for a planet, simplified for map use.
*/
static char map_getPlanetColourChar( Planet *p )
{
char colcode;
planet_updateLand(p);
colcode = planet_getColourChar(p);
/* Remap colour codes bit for simplicity and contrast. */
if (colcode == 'N' || colcode == 'F')
colcode = 'M';
else if (colcode == 'R')
colcode = 'S';
return colcode;
}
/**
* @brief Does fuzzy name matching for outfits.
*/
static char **map_fuzzyOutfits( Outfit **o, int n, const char *name, int *len )
{
int i, l;
char **names;
/* Overallocate to maximum. */
names = malloc( sizeof(char*) * n );
/* Do fuzzy search. */
l = 0;
for (i=0; i<n; i++) {
if (nstrcasestr( o[i]->name, name ) != NULL) {
names[l] = o[i]->name;
l++;
}
}
/* Free if empty. */
if (l == 0) {
free(names);
names = NULL;
}
*len = l;
return names;
}
/**
* @brief Gets the possible names the outfit name matches.
*/
static char **map_outfitsMatch( const char *name, int *len )
{
int n;
Outfit **o;
char **names;
/* Get outfits and names. */
o = tech_getOutfitArray( map_known_techs, map_nknown, &n );
names = map_fuzzyOutfits( o, n, name, len );
free(o);
return names;
}
/**
* @brief Add widgets to the extended area on the outfit search
* listpanel.
*
* @param wid The windowid we're adding widgets to
* @param x The x offset where we can start drawing
* @param y the y offset where we can start drawing
* @param w The width of the area where we can draw
* @param h The height of the area where we can draw
*/
static void map_addOutfitDetailFields(unsigned int wid, int x, int y, int w, int h)
{
(void) h;
(void) y;
int iw;
iw = x;
window_addRect( wid, -1 + iw, -50, 128, 129, "rctImage", &cBlack, 0 );
window_addImage( wid, iw, -50-128, 0, 0, "imgOutfit", NULL, 1 );
window_addText( wid, iw + 128 + 20, -60,
280, 160, 0, "txtOutfitName", &gl_defFont, &cBlack, NULL );
window_addText( wid, iw + 128 + 20, -60 - gl_defFont.h - 20,
280, 160, 0, "txtDescShort", &gl_smallFont, &cBlack, NULL );
window_addText( wid, iw+20, -60-128-10,
60, 160, 0, "txtSDesc", &gl_smallFont, &cDConsole,
"Owned:\n"
"\n"
"Slot:\n"
"Size:\n"
"Mass:\n"
"\n"
"Price:\n"
"Money:\n"
"License:\n" );
window_addText( wid, iw+20, -60-128-10,
280, 160, 0, "txtDDesc", &gl_smallFont, &cBlack, NULL );
window_addText( wid, iw+20, -60-128-10-160,
w-(iw+80), 180, 0, "txtDescription",
&gl_smallFont, NULL, NULL );
}
/**
* @brief Update the listPanel outfit details to the outfit selected.
*
* @param wid The windowid of the window we're updating.
* @param wgtname The name of the list that was selected.
* @param x The x offset where we can start drawing
* @param y the y offset where we can start drawing
* @param w The width of the area where we can draw
* @param h The height of the area where we can draw
*/
static void map_showOutfitDetail(unsigned int wid, char* wgtname, int x, int y, int w, int h)
{
(void) x;
(void) y;
(void) h;
Outfit *outfit;
char buf[PATH_MAX], buf2[ECON_CRED_STRLEN], buf3[ECON_CRED_STRLEN];
double th;
int iw;
/* 452 px is the sum of the 128 px outfit image width, its 4 px border,
* a 20 px gap, 280 px for the outfit's name and a final 20 px gap. */
iw = w - 452;
outfit = outfit_get( toolkit_getList(wid, wgtname) );
window_modifyText( wid, "txtOutfitName", outfit->name );
window_modifyImage( wid, "imgOutfit", outfit->gfx_store, 0, 0 );
window_modifyText( wid, "txtDescription", outfit->description );
credits2str( buf2, outfit->price, 2 );
credits2str( buf3, player.p->credits, 2 );
nsnprintf( buf, PATH_MAX,
"%d\n"
"\n"
"%s\n"
"%s\n"
"%.0f tons\n"
"\n"
"%s credits\n"
"%s credits\n"
"%s\n",
player_outfitOwned(outfit),
outfit_slotName(outfit),
outfit_slotSize(outfit),
outfit->mass,
buf2,
buf3,
(outfit->license != NULL) ? outfit->license : "None" );
window_modifyText( wid, "txtDDesc", buf );
window_modifyText( wid, "txtOutfitName", outfit->name );
window_modifyText( wid, "txtDescShort", outfit->desc_short );
th = MAX( 128, gl_printHeightRaw( &gl_smallFont, 280, outfit->desc_short ) );
window_moveWidget( wid, "txtSDesc", iw+20, -60-th-20 );
window_moveWidget( wid, "txtDDesc", iw+20+60, -60-th-20 );
th += gl_printHeightRaw( &gl_smallFont, 280, buf );
window_moveWidget( wid, "txtDescription", iw+20, -60-th-40 );
}
/**
* @brief Searches for a outfit.
*
* @param name Name to match.
* @return 0 on success.
*/
static int map_findSearchOutfits( unsigned int parent, const char *name )
{
int i, j;
char **names;
int len, n, ret;
map_find_t *found;
Planet *pnt;
StarSystem *sys;
const char *oname, *sysname;
char **list;
Outfit *o, **olist;
int nolist;
/* Match planet first. */
o = NULL;
oname = outfit_existsCase( name );
names = map_outfitsMatch( name, &len );
if (len <= 0)
return -1;
else if ((oname != NULL) && (len == 1))
o = outfit_get( oname );
/* Do fuzzy match. */
else {
/* Ask which one player wants. */
list = malloc( len*sizeof(char*) );
for (i=0; i<len; i++)
list[i] = strdup( names[i] );
i = dialogue_listPanel( "Search Results", list, len, 452, 550,
map_addOutfitDetailFields, map_showOutfitDetail,
"Search results for outfits matching '%s':", name );
if (i < 0) {
free(names);
return 0;
}
o = outfit_get( names[i] );
}
if (names != NULL)
free(names);
if (o == NULL)
return -1;
/* Construct found table. */
found = NULL;
n = 0;
for (i=0; i<map_nknown; i++) {
/* Try to find the outfit in the planet. */
olist = tech_getOutfit( map_known_techs[i], &nolist );
for (j=0; j<nolist; j++)
if (olist[j] == o)
break;
if (olist != NULL)
free(olist);
if (j >= nolist)
continue;
pnt = map_known_planets[i];
/* System must be known. */
sysname = planet_getSystem( pnt->name );
if (sysname == NULL)
continue;
sys = system_get( sysname );
if (!sys_isKnown(sys))
continue;
if (found == NULL) /* Allocate results array on first match. */
found = malloc( sizeof(map_find_t) * map_nknown );
/* Set more values. */
ret = map_findDistance( sys, pnt, &found[n].jumps, &found[n].distance );
if (ret) {
found[n].jumps = 10000;
found[n].distance = 1e6;
}
/* Set some values. */
found[n].pnt = pnt;
found[n].sys = sys;
/* Set fancy name. */
if (ret)
nsnprintf( found[n].display, sizeof(found[n].display),
"\e%c%s (%s, unknown route)", map_getPlanetColourChar(pnt),
pnt->name, sys->name );
else
nsnprintf( found[n].display, sizeof(found[n].display),
"\e%c%s (%s, %d jumps, %.0fk distance)", map_getPlanetColourChar(pnt),
pnt->name, sys->name, found[n].jumps, found[n].distance/1000. );
n++;
}
/* No visible match. */
if (n==0)
return -1;
/* Sort the found by distance. */
map_sortFound( found, n );
/* Display results. */
map_findDisplayResult( parent, found, n );
return 0;
}
/**
* @brief Does fuzzy name matching for ships;
*/
static char **map_fuzzyShips( Ship **s, int n, const char *name, int *len )
{
int i, l;
char **names;
/* Overallocate to maximum. */
names = malloc( sizeof(char*) * n );
/* Do fuzzy search. */
l = 0;
for (i=0; i<n; i++) {
if (nstrcasestr( s[i]->name, name ) != NULL) {
names[l] = s[i]->name;
l++;
}
}
/* Free if empty. */
if (l == 0) {
free(names);
names = NULL;
}
*len = l;
return names;
}
/**
* @brief Gets the possible names the ship name matches.
*/
static char **map_shipsMatch( const char *name, int *len )
{
int n;
Ship **s;
char **names;
/* Get ships and names. */
s = tech_getShipArray( map_known_techs, map_nknown, &n );
names = map_fuzzyShips( s, n, name, len );
free(s);
return names;
}
/**
* @brief Searches for a ship.
*
* @param name Name to match.
* @return 0 on success.
*/
static int map_findSearchShips( unsigned int parent, const char *name )
{
int i, j;
char **names;
int len, n, ret;
map_find_t *found;
Planet *pnt;
StarSystem *sys;
const char *sname, *sysname;
char **list;
Ship *s, **slist;
int nslist;
/* Match planet first. */
s = NULL;
sname = ship_existsCase( name );
names = map_shipsMatch( name, &len );
if (len <= 0)
return -1;
else if ((sname != NULL) && (len == 1))
s = ship_get( sname );
/* Handle fuzzy matching. */
else {
/* Ask which one player wants. */
list = malloc( len*sizeof(char*) );
for (i=0; i<len; i++)
list[i] = strdup( names[i] );
i = dialogue_list( "Search Results", list, len,
"Search results for ships matching '%s':", name );
if (i < 0) {
free(names);
return 0;
}
s = ship_get( names[i] );
}
if (names != NULL)
free(names);
if (s == NULL)
return -1;
/* Construct found table. */
found = NULL;
n = 0;
for (i=0; i<map_nknown; i++) {
/* Try to find the ship in the planet. */
slist = tech_getShip( map_known_techs[i], &nslist );
for (j=0; j<nslist; j++)
if (slist[j] == s)
break;
if (slist != NULL)
free(slist);
if (j >= nslist)
continue;
pnt = map_known_planets[i];
/* System must be known. */
sysname = planet_getSystem( pnt->name );
if (sysname == NULL)
continue;
sys = system_get( sysname );
if (!sys_isKnown(sys))
continue;
if (found == NULL) /* Allocate results array on first match. */
found = malloc( sizeof(map_find_t) * map_nknown );
/* Set more values. */
ret = map_findDistance( sys, pnt, &found[n].jumps, &found[n].distance );
if (ret) {
found[n].jumps = 10000;
found[n].distance = 1e6;
}
/* Set some values. */
found[n].pnt = pnt;
found[n].sys = sys;
/* Set fancy name. */
if (ret)
nsnprintf( found[n].display, sizeof(found[n].display),
"\e%c%s (%s, unknown route)", map_getPlanetColourChar(pnt),
pnt->name, sys->name );
else
nsnprintf( found[n].display, sizeof(found[n].display),
"\e%c%s (%s, %d jumps, %.0fk distance)", map_getPlanetColourChar(pnt),
pnt->name, sys->name, found[n].jumps, found[n].distance/1000. );
n++;
}
/* No visible match. */
if (n==0)
return -1;
/* Sort the found by distance. */
map_sortFound( found, n );
/* Display results. */
map_findDisplayResult( parent, found, n );
return 0;
}
/**
* @brief Does a search.
*/
static void map_findSearch( unsigned int wid, char* str )
{
int ret;
char *name;
char *searchname;
/* Get the name. */
name = window_getInput( wid, "inpSearch" );
if (name == NULL || !strcmp("",name))
return;
/* Clean up if necessary. */
if (map_found_cur != NULL)
free( map_found_cur );
map_found_cur = NULL;
/* Handle different search cases. */
if (map_find_systems) {
ret = map_findSearchSystems( wid, name );
searchname = "System";
}
else if (map_find_planets) {
ret = map_findSearchPlanets( wid, name );
searchname = "Planet";
}
else if (map_find_outfits) {
ret = map_findSearchOutfits( wid, name );
searchname = "Outfit";
}
else if (map_find_ships) {
ret = map_findSearchShips( wid, name );
searchname = "Ship";
}
else
ret = 1;
if (ret < 0)
dialogue_alert( "%s matching '%s' not found!", searchname, name );
if (ret > 0)
map_findClose( wid, str );
}
/**
* @brief Opens a search input box to find a system or planet.
*/
void map_inputFind( unsigned int parent, char* str )
{
(void) str;
unsigned int wid;
int x, y;
/* initialize known. */
map_knownInit();
/* Create the window. */
wid = window_create( "Find...", -1, -1, 300, 220 );
window_setAccept( wid, map_findSearch );
window_setCancel( wid, map_findClose );
window_setParent( wid, parent );
/* Text. */
y = -40;
window_addText( wid, 20, y, 300, gl_defFont.h+4, 0,
"txtDescription", &gl_defFont, &cDConsole,
"Enter keyword to search for:" );
y -= 30;
/* Create input. */
window_addInput( wid, 30, y, 240, 20,
"inpSearch", 32, 1, &gl_defFont );
y -= 40;
/* Create buttons. */
window_addButton( wid,300-BUTTON_WIDTH-30, 20+BUTTON_HEIGHT+20, BUTTON_WIDTH, BUTTON_HEIGHT,
"btnSearch", "Find", map_findSearch );
window_addButton( wid,300-BUTTON_WIDTH-30, 20, BUTTON_WIDTH, BUTTON_HEIGHT,
"btnClose", "Close", map_findClose );
/* Create check boxes. */
x = 40;
window_addCheckbox( wid, x, y, 100, 20,
"chkSystem", "Systems", map_find_check_update, map_find_systems );
y -= 20;
window_addCheckbox( wid, x, y, 100, 20,
"chkPlanet", "Planets", map_find_check_update, map_find_planets );
y -= 20;
window_addCheckbox( wid, x, y, 100, 20,
"chkOutfit", "Outfits", map_find_check_update, map_find_outfits );
y -= 20;
window_addCheckbox( wid, x, y, 100, 20,
"chkShip", "Ships", map_find_check_update, map_find_ships );
}
Jump to Line
Something went wrong with that request. Please try again.