Exemplo n.º 1
0
Arquivo: menu.c Projeto: naev/naev
/**
 * @brief Player death menu, appears when player got creamed.
 */
void menu_death (void)
{
   unsigned int wid;
   char path[PATH_MAX];

   wid = window_create( "Death", -1, -1, DEATH_WIDTH, DEATH_HEIGHT );
   window_onClose( wid, menu_death_close );

   /* Allow the player to continue if the savegame exists, if not, propose to restart */
   nsnprintf(path, PATH_MAX, "%ssaves/%s.ns", nfile_dataPath(), player.name);
   if (!player_isTut() && nfile_fileExists(path))
      window_addButtonKey( wid, 20, 20 + BUTTON_HEIGHT*2 + 20*2, BUTTON_WIDTH, BUTTON_HEIGHT,
         "btnContinue", _("Continue"), menu_death_continue, SDLK_c );
   else
      window_addButtonKey( wid, 20, 20 + BUTTON_HEIGHT*2 + 20*2, BUTTON_WIDTH, BUTTON_HEIGHT,
         "btnRestart", _("Restart"), menu_death_restart, SDLK_r );

   window_addButtonKey( wid, 20, 20 + (BUTTON_HEIGHT+20),
         BUTTON_WIDTH, BUTTON_HEIGHT,
         "btnMain", _("Main Menu"), menu_death_main, SDLK_m );
   window_addButtonKey( wid, 20, 20, BUTTON_WIDTH, BUTTON_HEIGHT,
         "btnExit", _("Exit Game"), menu_exit, SDLK_x );
   menu_Open(MENU_DEATH);

   /* Makes it all look cooler since everything still goes on. */
   unpause_game();
}
Exemplo n.º 2
0
Arquivo: land.c Projeto: Kinniken/naev
/**
 * @brief Opens the mission computer window.
 */
static void misn_open( unsigned int wid )
{
   int w, h;
   int y;

   /* Mark as generated. */
   land_tabGenerate(LAND_WINDOW_MISSION);

   /* Get window dimensions. */
   window_dimWindow( wid, &w, &h );

   /* Set window functions. */
   window_onClose( wid, misn_close );

   /* buttons */
   window_addButtonKey( wid, -20, 20,
         LAND_BUTTON_WIDTH,LAND_BUTTON_HEIGHT, "btnCloseMission",
         "Take Off", land_buttonTakeoff, SDLK_t );
   window_addButtonKey( wid, -20, 40+LAND_BUTTON_HEIGHT,
         LAND_BUTTON_WIDTH,LAND_BUTTON_HEIGHT, "btnAcceptMission",
         "Accept Mission", misn_accept, SDLK_a );

   /* text */
   y = -60;
   window_addText( wid, w/2 + 10, y,
         w/2 - 30, 40, 0,
         "txtSDate", NULL, &cDConsole,
         "Date:\n"
         "Free Space:");
   window_addText( wid, w/2 + 110, y,
         w/2 - 90, 40, 0,
         "txtDate", NULL, &cBlack, NULL );
   y -= 2 * gl_defFont.h + 50;
   window_addText( wid, w/2 + 10, y,
         w/2 - 30, 20, 0,
         "txtSReward", &gl_smallFont, &cDConsole, "Reward:" );
   window_addText( wid, w/2 + 70, y,
         w/2 - 90, 20, 0,
         "txtReward", &gl_smallFont, &cBlack, NULL );
   y -= 20;
   window_addText( wid, w/2 + 10, y,
         w/2 - 30, h/2-90, 0,
         "txtDesc", &gl_smallFont, &cBlack, NULL );

   /* map */
   map_show( wid, 20, 20,
         w/2 - 30, h/2 - 35, 0.75 );

   misn_genList(wid, 1);
   /* Set default keyboard focuse to the list */
   window_setFocus( wid , "lstMission" );
}
Exemplo n.º 3
0
Arquivo: land.c Projeto: Kinniken/naev
/**
 * @brief Opens the spaceport bar window.
 */
static void bar_open( unsigned int wid )
{
   int w, h, iw, ih, bw, bh, dh, th;

   /* Mark as generated. */
   land_tabGenerate(LAND_WINDOW_BAR);

   /* Set window functions. */
   window_onClose( wid, bar_close );

   /* Get dimensions. */
   bar_getDim( wid, &w, &h, &iw, &ih, &bw, &bh );
   dh = gl_printHeightRaw( &gl_smallFont, w - iw - 60, land_planet->bar_description );

   /* Approach when pressing enter */
   window_setAccept( wid, bar_approach );

   /* Buttons */
   window_addButtonKey( wid, -20, 20,
         bw, bh, "btnCloseBar",
         "Take Off", land_buttonTakeoff, SDLK_t );
   window_addButtonKey( wid, -20 - bw - 20, 20,
         bw, bh, "btnApproach",
         "Approach", bar_approach, SDLK_a );

   /* Bar description. */
   window_addText( wid, iw + 40, -40,
         w - iw - 60, dh, 0,
         "txtDescription", &gl_smallFont, &cBlack,
         land_planet->bar_description );

   /* Add portrait text. */
   th = -40 - dh - 40;
   window_addText( wid, iw + 40, th,
         w - iw - 60, gl_defFont.h, 1,
         "txtPortrait", &gl_defFont, &cDConsole, NULL );

   /* Add mission description text. */
   th -= 20 + PORTRAIT_HEIGHT + 20 + 20;
   window_addText( wid, iw + 60, th,
         w - iw - 100, h + th - (2*bh+60), 0,
         "txtMission", &gl_smallFont, &cBlack, NULL );

   /* Generate the mission list. */
   bar_genList( wid );
   /* Set default keyboard focuse to the list */
   window_setFocus( wid , "iarMissions" );
}
Exemplo n.º 4
0
Arquivo: land.c Projeto: Dinth/naev
/**
 * @brief Opens the mission computer window.
 */
static void misn_open( unsigned int wid )
{
   int w, h;
   int y;

   /* Get window dimensions. */
   window_dimWindow( wid, &w, &h );

   /* Set window functions. */
   window_onClose( wid, misn_close );

   /* buttons */
   window_addButton( wid, -20, 20,
         LAND_BUTTON_WIDTH,LAND_BUTTON_HEIGHT, "btnCloseMission",
         "Takeoff", land_buttonTakeoff );
   window_addButton( wid, -20, 40+LAND_BUTTON_HEIGHT,
         LAND_BUTTON_WIDTH,LAND_BUTTON_HEIGHT, "btnAcceptMission",
         "Accept Mission", misn_accept );

   /* text */
   y = -60;
   window_addText( wid, w/2 + 10, y,
         w/2 - 30, 40, 0,
         "txtSDate", NULL, &cDConsole,
         "Date:\n"
         "Free Space:");
   window_addText( wid, w/2 + 110, y,
         w/2 - 90, 40, 0,
         "txtDate", NULL, &cBlack, NULL );
   y -= 2 * gl_defFont.h + 50;
   window_addText( wid, w/2 + 10, y,
         w/2 - 30, 20, 0,
         "txtSReward", &gl_smallFont, &cDConsole, "Reward:" );
   window_addText( wid, w/2 + 70, y,
         w/2 - 90, 20, 0,
         "txtReward", &gl_smallFont, &cBlack, NULL );
   y -= 20;
   window_addText( wid, w/2 + 10, y,
         w/2 - 30, h/2-90, 0,
         "txtDesc", &gl_smallFont, &cBlack, NULL );

   /* map */
   map_show( wid, 20, 20,
         w/2 - 30, h/2 - 35, 0.75 );

   misn_genList(wid, 1);
}
Exemplo n.º 5
0
Arquivo: info.c Projeto: AvanWolf/naev
/**
 * @brief Displays the player's standings.
 */
static void info_openStandings( unsigned int wid )
{
   int i;
   int n, m;
   char **str;
   int w, h, lw;

   /* Get dimensions. */
   info_getDim( wid, &w, &h, &lw );

   /* On close. */
   window_onClose( wid, standings_close );

   /* Buttons */
   window_addButton( wid, -20, 20, BUTTON_WIDTH, BUTTON_HEIGHT,
         "closeMissions", "Close", info_close );

   /* Graphics. */
   window_addImage( wid, 0, 0, 0, 0, "imgLogo", NULL, 0 );

   /* Text. */
   window_addText( wid, lw+40, 0, (w-(lw+60)), 20, 1, "txtName",
         &gl_defFont, &cDConsole, NULL );
   window_addText( wid, lw+40, 0, (w-(lw+60)), 20, 1, "txtStanding",
         &gl_smallFont, &cBlack, NULL );

   /* Gets the faction standings. */
   info_factions  = faction_getAll( &n );
   str            = malloc( sizeof(char*) * n );

   /* Create list. */
   for (i=0; i<n; i++) {
      str[i] = malloc( 256 );
      m = round( faction_getPlayer( info_factions[i] ) );
      snprintf( str[i], 256, "%s   [ %+d%% ]",
            faction_name( info_factions[i] ), m );
   }

   /* Display list. */
   window_addList( wid, 20, -40, lw, h-60,
         "lstStandings", str, n, 0, standings_update );

   standings_update( wid , NULL );
}
Exemplo n.º 6
0
Arquivo: land.c Projeto: Dinth/naev
/**
 * @brief Opens the spaceport bar window.
 */
static void bar_open( unsigned int wid )
{
   int w, h, iw, ih, bw, bh, dh, th;

   /* Set window functions. */
   window_onClose( wid, bar_close );

   /* Get dimensions. */
   bar_getDim( wid, &w, &h, &iw, &ih, &bw, &bh );
   dh = gl_printHeightRaw( &gl_smallFont, w - iw - 60, land_planet->bar_description );

   /* Buttons */
   window_addButton( wid, -20, 20,
         bw, bh, "btnCloseBar",
         "Takeoff", land_buttonTakeoff );
   window_addButton( wid, -20 - bw - 20, 20,
         bw, bh, "btnApproach",
         "Approach", bar_approach );

   /* Bar description. */
   window_addText( wid, iw + 40, -40,
         w - iw - 60, dh, 0,
         "txtDescription", &gl_smallFont, &cBlack,
         land_planet->bar_description );

   /* Add portrait text. */
   th = -40 - dh - 40;
   window_addText( wid, iw + 40, th,
         w - iw - 60, gl_defFont.h, 1,
         "txtPortrait", &gl_defFont, &cDConsole, NULL );

   /* Add mission description text. */
   th -= 20 + PORTRAIT_HEIGHT + 20 + 20;
   window_addText( wid, iw + 60, th,
         w - iw - 100, h + th - (2*bh+60), 0,
         "txtMission", &gl_smallFont, &cBlack, NULL );

   /* Generate the mission list. */
   bar_genList( wid );
}
Exemplo n.º 7
0
Arquivo: land.c Projeto: Dinth/naev
/**
 * @brief Recreates the land windows.
 *
 *    @param load Is loading game?
 *    @param changetab Should it change to the last open tab?
 */
void land_genWindows( int load, int changetab )
{
   int i, j;
   const char *names[LAND_NUMWINDOWS];
   int w, h;
   Planet *p;
   int regen;

   /* Destroy old window if exists. */
   if (land_wid > 0) {
      land_regen = 2; /* Mark we're regenning. */
      window_destroy(land_wid);
   }
   land_loaded = 0;

   /* Get planet. */
   p     = land_planet;
   regen = landed;

   /* Create window. */
   if ((SCREEN_W < 1024) || (SCREEN_H < 768)) {
      w = -1; /* Fullscreen. */
      h = -1;
   }
   else {
      w = 800 + 0.5 * (SCREEN_W - 800);
      h = 600 + 0.5 * (SCREEN_H - 600);
   }
   land_wid = window_create( p->name, -1, -1, w, h );
   window_onClose( land_wid, land_cleanupWindow );

   /* Set window map to invalid. */
   for (i=0; i<LAND_NUMWINDOWS; i++)
      land_windowsMap[i] = -1;

   /* See what is available. */
   j = 0;
   /* Main. */
   land_windowsMap[LAND_WINDOW_MAIN] = j;
   names[j++] = land_windowNames[LAND_WINDOW_MAIN];
   /* Bar. */
   if (planet_hasService(land_planet, PLANET_SERVICE_BAR)) {
      land_windowsMap[LAND_WINDOW_BAR] = j;
      names[j++] = land_windowNames[LAND_WINDOW_BAR];
   }
   /* Missions. */
   if (planet_hasService(land_planet, PLANET_SERVICE_MISSIONS)) {
      land_windowsMap[LAND_WINDOW_MISSION] = j;
      names[j++] = land_windowNames[LAND_WINDOW_MISSION];
   }
   /* Outfits. */
   if (planet_hasService(land_planet, PLANET_SERVICE_OUTFITS)) {
      land_windowsMap[LAND_WINDOW_OUTFITS] = j;
      names[j++] = land_windowNames[LAND_WINDOW_OUTFITS];
   }
   /* Shipyard. */
   if (planet_hasService(land_planet, PLANET_SERVICE_SHIPYARD)) {
      land_windowsMap[LAND_WINDOW_SHIPYARD] = j;
      names[j++] = land_windowNames[LAND_WINDOW_SHIPYARD];
   }
   /* Equipment. */
   if (planet_hasService(land_planet, PLANET_SERVICE_OUTFITS) ||
         planet_hasService(land_planet, PLANET_SERVICE_SHIPYARD)) {
      land_windowsMap[LAND_WINDOW_EQUIPMENT] = j;
      names[j++] = land_windowNames[LAND_WINDOW_EQUIPMENT];
   }
   /* Commodity. */
   if (planet_hasService(land_planet, PLANET_SERVICE_COMMODITY)) {
      land_windowsMap[LAND_WINDOW_COMMODITY] = j;
      names[j++] = land_windowNames[LAND_WINDOW_COMMODITY];
   }

   /* Create tabbed window. */
   land_windows = window_addTabbedWindow( land_wid, -1, -1, -1, -1, "tabLand", j, names );

   /*
    * Order here is very important:
    *
    *  1) Create main tab - must have decent background.
    *  2) Set landed, play music and run land hooks - so hooks run well.
    *  3) Generate missions - so that campaigns are fluid.
    *  4) Create other tabs - lists depend on NPC and missions.
    */

   /* 1) Create main tab. */
   land_createMainTab( land_getWid(LAND_WINDOW_MAIN) );

   /* 2) Set as landed and run hooks. */
   if (!regen) {
      landed = 1;
      music_choose("land"); /* Must be before hooks in case hooks change music. */
      if (!load) {
         events_trigger( EVENT_TRIGGER_LAND );
         hooks_run("land");
      }

      /* 3) Generate computer and bar missions. */
      if (planet_hasService(land_planet, PLANET_SERVICE_MISSIONS))
         mission_computer = missions_genList( &mission_ncomputer,
               land_planet->faction, land_planet->name, cur_system->name,
               MIS_AVAIL_COMPUTER );
      if (planet_hasService(land_planet, PLANET_SERVICE_BAR))
         npc_generate(); /* Generate bar npc. */
   }

   /* 4) Create other tabs. */
   /* Basic - bar + missions */
   if (planet_hasService(land_planet, PLANET_SERVICE_BAR))
      bar_open( land_getWid(LAND_WINDOW_BAR) );
   if (planet_hasService(land_planet, PLANET_SERVICE_MISSIONS))
      misn_open( land_getWid(LAND_WINDOW_MISSION) );
   /* Outfits. */
   if (planet_hasService(land_planet, PLANET_SERVICE_OUTFITS))
      outfits_open( land_getWid(LAND_WINDOW_OUTFITS) );
   /* Shipyard. */
   if (planet_hasService(land_planet, PLANET_SERVICE_SHIPYARD))
      shipyard_open( land_getWid(LAND_WINDOW_SHIPYARD) );
   /* Equipment. */
   if (planet_hasService(land_planet, PLANET_SERVICE_OUTFITS) ||
         planet_hasService(land_planet, PLANET_SERVICE_SHIPYARD))
      equipment_open( land_getWid(LAND_WINDOW_EQUIPMENT) );
   /* Commodity. */
   if (planet_hasService(land_planet, PLANET_SERVICE_COMMODITY))
      commodity_exchange_open( land_getWid(LAND_WINDOW_COMMODITY) );

   if (!regen) {
      /* Reset markers if needed. */
      mission_sysMark();

      /* Check land missions. */
      if (!has_visited(VISITED_LAND)) {
         missions_run(MIS_AVAIL_LAND, land_planet->faction,
               land_planet->name, cur_system->name);
         visited(VISITED_LAND);
      }
   }

   /* Go to last open tab. */
   window_tabWinOnChange( land_wid, "tabLand", land_changeTab );
   if (changetab && land_windowsMap[ last_window ] != -1)
      window_tabWinSetActive( land_wid, "tabLand", land_windowsMap[ last_window ] );

   /* Add fuel button if needed - AFTER missions pay :). */
   land_checkAddRefuel();

   /* Finished loading. */
   land_loaded = 1;
}
Exemplo n.º 8
0
Arquivo: menu.c Projeto: zid/naev
/**
 * @brief Opens the main menu (titlescreen).
 */
void menu_main (void)
{
   int offset_logo, offset_wdw, freespace;
   unsigned int bwid, wid;
   glTexture *tex;

   /* Play load music. */
   music_choose("load");

   /* Load background and friends. */
   tex = gl_newImage( "gfx/NAEV.png", 0 );
   main_naevLogo = tex;
   nebu_prep( 300., 0. ); /* Needed for nebula to not spaz out */

   /* Calculate Logo and window offset. */
   freespace = SCREEN_H - tex->sh - MAIN_HEIGHT;
   if (freespace < 0) { /* Not enough freespace, this can get ugly. */
      offset_logo = SCREEN_W - tex->sh;
      offset_wdw  = 0;
   }
   else {
      /* We'll want a maximum seperation of 30 between logo and text. */
      if (freespace/3 > 25) {
         freespace -= 25;
         offset_logo = -25;
         offset_wdw  = -25 - tex->sh - 25;
      }
      /* Otherwise space evenly. */
      else {
         offset_logo = -freespace/3;
         offset_wdw  = freespace/3;
      }
   }

   /* create background image window */
   bwid = window_create( "BG", -1, -1, SCREEN_W, SCREEN_H );
   window_onClose( bwid, menu_main_cleanBG );
   window_addRect( bwid, 0, 0, SCREEN_W, SCREEN_H, "rctBG", &cBlack, 0 );
   window_addCust( bwid, 0, 0, SCREEN_W, SCREEN_H, "cstBG", 0,
         menu_main_nebu, NULL, &menu_main_lasttick );
   window_addImage( bwid, (SCREEN_W-tex->sw)/2., offset_logo, "imgLogo", tex, 0 );
   window_addText( bwid, 0., 10, SCREEN_W, 30., 1, "txtBG", NULL,
         &cWhite, naev_version(1) );

   /* create menu window */
   wid = window_create( "Main Menu", -1, offset_wdw,
         MAIN_WIDTH, MAIN_HEIGHT );
   window_addButton( wid, 20, 20 + (BUTTON_HEIGHT+20)*4,
         BUTTON_WIDTH, BUTTON_HEIGHT,
         "btnLoad", "Load Game", menu_main_load );
   window_addButton( wid, 20, 20 + (BUTTON_HEIGHT+20)*3,
         BUTTON_WIDTH, BUTTON_HEIGHT,
         "btnNew", "New Game", menu_main_new );
   window_addButton( wid, 20, 20 + (BUTTON_HEIGHT+20)*2,
         BUTTON_WIDTH, BUTTON_HEIGHT,
         "btnOptions", "Options", menu_options_button );
   window_addButton( wid, 20, 20 + (BUTTON_HEIGHT+20),
         BUTTON_WIDTH, BUTTON_HEIGHT,
         "btnCredits", "Credits", menu_main_credits );
   window_addButton( wid, 20, 20, BUTTON_WIDTH, BUTTON_HEIGHT,
         "btnExit", "Exit", menu_exit );

   /* Make the background window a parent of the menu. */
   window_setParent( bwid, wid );

   /* Reset timer. */
   menu_main_lasttick = SDL_GetTicks();

   menu_Open(MENU_MAIN);
}
Exemplo n.º 9
0
Arquivo: menu.c Projeto: naev/naev
/**
 * @brief Opens the main menu (titlescreen).
 */
void menu_main (void)
{
   int offset_logo, offset_wdw, freespace;
   unsigned int bwid, wid;
   glTexture *tex;
   int h, y;

   if (menu_isOpen(MENU_MAIN)) {
      WARN( _("Menu main is already open.") );
      return;
   }

   /* Clean up GUI - must be done before using SCREEN_W or SCREEN_H. */
   gui_cleanup();
   player_soundStop(); /* Stop sound. */

   /* Play load music. */
   music_choose("load");

   /* Load background and friends. */
   tex = gl_newImage( GFX_PATH"Naev.png", 0 );
   main_naevLogo = tex;
   menu_main_bkg_system();

   /* Set dimensions */
   y  = 20 + (BUTTON_HEIGHT+20)*5;
   h  = y + 80;
   if (conf.devmode) {
      h += BUTTON_HEIGHT + 20;
      y += BUTTON_HEIGHT + 20;
   }

   /* Calculate Logo and window offset. */
   freespace = SCREEN_H - tex->sh - h;
   if (freespace < 0) { /* Not enough freespace, this can get ugly. */
      offset_logo = SCREEN_W - tex->sh;
      offset_wdw  = 0;
   }
   /* Otherwise space evenly. */
   else {
      offset_logo = -freespace/4;
      offset_wdw  = freespace/2;
   }

   /* create background image window */
   bwid = window_create( "BG", -1, -1, -1, -1 );
   window_onClose( bwid, menu_main_cleanBG );
   window_setBorder( bwid, 0 );
   window_addImage( bwid, (SCREEN_W-tex->sw)/2., offset_logo, 0, 0, "imgLogo", tex, 0 );
   window_addText( bwid, 0, 10, SCREEN_W, 30., 1, "txtBG", NULL,
         &cWhite, naev_version(1) );

   /* create menu window */
   wid = window_create( "Main Menu", -1, offset_wdw, MAIN_WIDTH, h );
   window_setCancel( wid, main_menu_promptClose );

   /* Buttons. */
   window_addButtonKey( wid, 20, y, BUTTON_WIDTH, BUTTON_HEIGHT,
         "btnLoad", _("Load Game"), menu_main_load, SDLK_l );
   y -= BUTTON_HEIGHT+20;
   window_addButtonKey( wid, 20, y, BUTTON_WIDTH, BUTTON_HEIGHT,
         "btnNew", _("New Game"), menu_main_new, SDLK_n );
   y -= BUTTON_HEIGHT+20;
   window_addButtonKey( wid, 20, y, BUTTON_WIDTH, BUTTON_HEIGHT,
         "btnTutorial", _("Tutorial"), menu_main_tutorial, SDLK_t );
   y -= BUTTON_HEIGHT+20;
   if (conf.devmode) {
      window_addButtonKey( wid, 20, y, BUTTON_WIDTH, BUTTON_HEIGHT,
            "btnEditor", _("Editors"), menu_editors_open, SDLK_e );
      y -= BUTTON_HEIGHT+20;
   }
   window_addButtonKey( wid, 20, y, BUTTON_WIDTH, BUTTON_HEIGHT,
         "btnOptions", _("Options"), menu_options_button, SDLK_o );
   y -= BUTTON_HEIGHT+20;
   window_addButtonKey( wid, 20, y, BUTTON_WIDTH, BUTTON_HEIGHT,
         "btnCredits", _("Credits"), menu_main_credits, SDLK_c );
   y -= BUTTON_HEIGHT+20;
   window_addButtonKey( wid, 20, y, BUTTON_WIDTH, BUTTON_HEIGHT,
         "btnExit", _("Exit"), menu_exit, SDLK_x );

   /* Disable load button if there are no saves. */
   if (!save_hasSave())
      window_disableButton( wid, "btnLoad" );

   /* Make the background window a child of the menu. */
   window_setParent( bwid, wid );

   unpause_game();
   menu_Open(MENU_MAIN);
}
Exemplo n.º 10
0
Arquivo: land.c Projeto: naev/naev
/**
 * @brief Recreates the land windows.
 *
 *    @param load Is loading game?
 *    @param changetab Should it change to the last open tab?
 */
void land_genWindows( int load, int changetab )
{
   int i, j;
   const char *names[LAND_NUMWINDOWS];
   int w, h;
   Planet *p;
   int regen;

   /* Destroy old window if exists. */
   if (land_wid > 0) {
      land_regen = 2; /* Mark we're regenning. */
      window_destroy(land_wid);

      /* Mark tabs as not generated. */
      land_generated = 0;
   }
   land_loaded = 0;

   /* Get planet. */
   p     = land_planet;
   regen = landed;

   /* Create window. */
   if ((gl_screen.rw < 1024) || (gl_screen.rh < 768)) {
      w = -1; /* Fullscreen. */
      h = -1;
   }
   else {
      w = 800 + 0.5 * (SCREEN_W - 800);
      h = 600 + 0.5 * (SCREEN_H - 600);
   }
   land_wid = window_create( p->name, -1, -1, w, h );
   window_onClose( land_wid, land_cleanupWindow );

   /* Set window map to invalid. */
   for (i=0; i<LAND_NUMWINDOWS; i++)
      land_windowsMap[i] = -1;

   /* See what is available. */
   j = 0;
   /* Main. */
   land_windowsMap[LAND_WINDOW_MAIN] = j;
   names[j++] = _("Landing Main");
   /* Bar. */
   if (planet_hasService(land_planet, PLANET_SERVICE_BAR)) {
      land_windowsMap[LAND_WINDOW_BAR] = j;
      names[j++] = _("Spaceport Bar");
   }
   /* Missions. */
   if (planet_hasService(land_planet, PLANET_SERVICE_MISSIONS)) {
      land_windowsMap[LAND_WINDOW_MISSION] = j;
      names[j++] = _("Missions");
   }
   /* Outfits. */
   if (planet_hasService(land_planet, PLANET_SERVICE_OUTFITS)) {
      land_windowsMap[LAND_WINDOW_OUTFITS] = j;
      names[j++] = _("Outfits");
   }
   /* Shipyard. */
   if (planet_hasService(land_planet, PLANET_SERVICE_SHIPYARD)) {
      land_windowsMap[LAND_WINDOW_SHIPYARD] = j;
      names[j++] = _("Shipyard");
   }
   /* Equipment. */
   if (planet_hasService(land_planet, PLANET_SERVICE_OUTFITS) ||
         planet_hasService(land_planet, PLANET_SERVICE_SHIPYARD)) {
      land_windowsMap[LAND_WINDOW_EQUIPMENT] = j;
      names[j++] = _("Equipment");
   }
   /* Commodity. */
   if (planet_hasService(land_planet, PLANET_SERVICE_COMMODITY)) {
      land_windowsMap[LAND_WINDOW_COMMODITY] = j;
      names[j++] = _("Commodity");
   }

   /* Create tabbed window. */
   land_windows = window_addTabbedWindow( land_wid, -1, -1, -1, -1, "tabLand", j, names, 0 );

   /*
    * Order here is very important:
    *
    *  1) Create main tab - must have decent background.
    *  2) Set landed, play music and run land hooks - so hooks run well.
    *  3) Generate missions - so that campaigns are fluid.
    *  4) Create other tabs - lists depend on NPC and missions.
    */

   /* 1) Create main tab. */
   land_createMainTab( land_getWid(LAND_WINDOW_MAIN) );

   /* Add local system map button. */
   land_checkAddMap();

   /* 2) Set as landed and run hooks. */
   if (!regen) {
      landed = 1;
      music_choose("land"); /* Must be before hooks in case hooks change music. */
      if (!load) {
         hooks_run("land");
      }
      events_trigger( EVENT_TRIGGER_LAND );

      /* 3) Generate computer and bar missions. */
      if (planet_hasService(land_planet, PLANET_SERVICE_MISSIONS))
         mission_computer = missions_genList( &mission_ncomputer,
               land_planet->faction, land_planet->name, cur_system->name,
               MIS_AVAIL_COMPUTER );
      if (planet_hasService(land_planet, PLANET_SERVICE_BAR))
         npc_generate(); /* Generate bar npc. */
   }

   /* 4) Create other tabs. */
#define should_open(s, w) \
   (planet_hasService(land_planet, s) && (!land_tabGenerated(w)))

   /* Things get a bit hairy here. Hooks may have triggered a GUI reload via
    * e.g. player.swapShip, so the land tabs may have been generated already
    * and we need to check that before regenerating them.
    */

   /* Basic - bar + missions */
   if (should_open( PLANET_SERVICE_BAR, LAND_WINDOW_BAR ))
      bar_open( land_getWid(LAND_WINDOW_BAR) );
   if (should_open( PLANET_SERVICE_MISSIONS, LAND_WINDOW_MISSION ))
      misn_open( land_getWid(LAND_WINDOW_MISSION) );
   /* Outfits. */
   if (should_open( PLANET_SERVICE_OUTFITS, LAND_WINDOW_OUTFITS ))
      outfits_open( land_getWid(LAND_WINDOW_OUTFITS) );
   /* Shipyard. */
   if (should_open( PLANET_SERVICE_SHIPYARD, LAND_WINDOW_SHIPYARD ))
      shipyard_open( land_getWid(LAND_WINDOW_SHIPYARD) );
   /* Equipment. */
   if ((planet_hasService(land_planet, PLANET_SERVICE_OUTFITS) ||
         planet_hasService(land_planet, PLANET_SERVICE_SHIPYARD)) &&
         !land_tabGenerated( LAND_WINDOW_EQUIPMENT ))
      equipment_open( land_getWid(LAND_WINDOW_EQUIPMENT) );
   /* Commodity. */
   if (should_open( PLANET_SERVICE_COMMODITY, LAND_WINDOW_COMMODITY ))
      commodity_exchange_open( land_getWid(LAND_WINDOW_COMMODITY) );
#undef should_open

   if (!regen) {
      /* Reset markers if needed. */
      mission_sysMark();

      /* Check land missions. */
      if (!has_visited(VISITED_LAND)) {
         missions_run(MIS_AVAIL_LAND, land_planet->faction,
               land_planet->name, cur_system->name);
         visited(VISITED_LAND);
      }
   }

   /* Go to last open tab. */
   window_tabWinOnChange( land_wid, "tabLand", land_changeTab );
   if (changetab && land_windowsMap[ last_window ] != -1)
      window_tabWinSetActive( land_wid, "tabLand", land_windowsMap[ last_window ] );

   /* Refresh the map button in case the player couldn't afford it prior to
    * mission payment.
    */
   land_checkAddMap();

   /* Refuel if necessary. */
   land_refuel();

   /* Finished loading. */
   land_loaded = 1;
}