/* * Copyright (C) Volition, Inc. 1999. All rights reserved. * * All source code herein is the property of Volition, Inc. You may not sell * or otherwise commercially exploit the source or things you created based on the * source. * */ // DumpStats.cpp : implementation file // #include "stdafx.h" #include "FRED.h" #include "DumpStats.h" #include "starfield/starfield.h" #include "nebula/neb.h" #include "cfile/cfile.h" #include "globalincs/linklist.h" #include "object/object.h" #include "object/waypoint.h" #include "jumpnode/jumpnode.h" #include "mission/missiongoals.h" #include "gamesnd/eventmusic.h" #include "asteroid/asteroid.h" #include "species_defs/species_defs.h" #include "weapon/weapon.h" #ifdef _DEBUG #undef THIS_FILE static char THIS_FILE[] = __FILE__; #endif ///////////////////////////////////////////////////////////////////////////// // DumpStats dialog DumpStats::DumpStats(CWnd* pParent /*=NULL*/) : CDialog(DumpStats::IDD, pParent) { //{{AFX_DATA_INIT(DumpStats) // NOTE: the ClassWizard will add member initialization here //}}AFX_DATA_INIT } void DumpStats::DoDataExchange(CDataExchange* pDX) { CDialog::DoDataExchange(pDX); //{{AFX_DATA_MAP(DumpStats) // NOTE: the ClassWizard will add DDX and DDV calls here //}}AFX_DATA_MAP } BEGIN_MESSAGE_MAP(DumpStats, CDialog) //{{AFX_MSG_MAP(DumpStats) ON_BN_CLICKED(IDC_DUMP_TO_FILE, OnDumpToFile) //}}AFX_MSG_MAP END_MESSAGE_MAP() ///////////////////////////////////////////////////////////////////////////// // DumpStats message handlers BOOL DumpStats::OnInitDialog() { CDialog::OnInitDialog(); CString buffer; int i; // get author, title, etc get_mission_stats(buffer); // get nebula, stars, etc. get_background_stats(buffer); // get number or ships, waypoints, start points, etc. get_object_stats(buffer); // get objectives / goals get_objectives_and_goals(buffer); // get ship selection for player wings get_ship_weapon_selection(buffer); // get messaging info get_messaging_info(buffer); // get species ship breakdown get_species_ship_breakdown(buffer); // get default loadouts get_default_ship_loadouts(buffer); int num_tab_stops = 5; int tab_stops[5]; for (i=0; i<5; i++) { tab_stops[i] = (i+1) * 16; } ((CEdit*) GetDlgItem(IDC_STATS_TEXT))->SetTabStops(num_tab_stops, tab_stops); ((CEdit*) GetDlgItem(IDC_STATS_TEXT))->SetWindowText(buffer); return TRUE; // return TRUE unless you set the focus to a control // EXCEPTION: OCX Property Pages should return FALSE } void DumpStats::OnDumpToFile() { // TODO: Add your control notification handler code here // get dump from window CString buffer; ((CEdit*) GetDlgItem(IDC_STATS_TEXT))->GetWindowText(buffer); CString dump_filename; dump_filename.Format("%s.dmp", Mission_filename); CFILE *fp; fp = cfopen((char *)LPCTSTR(dump_filename), "wt", CFILE_NORMAL, CF_TYPE_MISSIONS); cfputs((char *)LPCTSTR(buffer), fp); cfclose(fp); } void DumpStats::get_mission_stats(CString &buffer) { CString temp; // Mission info buffer += "\t MISSION INFO\r\n"; temp.Format("Title: %s\r\n", The_mission.name); buffer += temp; temp.Format("Filename: %s\r\n", Mission_filename); buffer += temp; temp.Format("Author: %s\r\n", The_mission.author); buffer += temp; temp.Format("Description: %s\r\n", The_mission.mission_desc); buffer += temp; temp.Format("Notes: %s\r\n", The_mission.notes); buffer += temp; if (The_mission.game_type & MISSION_TYPE_SINGLE) { temp.Format("Mission type: Single Player\r\n"); } else if (The_mission.game_type & MISSION_TYPE_MULTI_COOP) { temp.Format("Mission type: Multi Coop\r\n"); } else if (The_mission.game_type & MISSION_TYPE_MULTI_TEAMS) { temp.Format("Mission type: Multi Team vs. Team\r\n"); } else if (The_mission.game_type & MISSION_TYPE_MULTI_DOGFIGHT) { temp.Format("Mission type: Dogfight\r\n"); } buffer += temp; if (The_mission.game_type & MISSION_TYPE_MULTI) { temp.Format("\tNum respawns: %d\r\n", The_mission.num_respawns); buffer += temp; } if (Current_soundtrack_num >= 0) { temp.Format("\tMusic: %s\r\n", Soundtracks[Current_soundtrack_num].name); buffer += temp; } if (The_mission.flags[Mission::Mission_Flags::Red_alert]) { buffer += "\tRed Alert\r\n"; } if (The_mission.flags[Mission::Mission_Flags::Scramble]) { buffer += "\tScramble\r\n"; } if (The_mission.flags[Mission::Mission_Flags::No_promotion]) { buffer += "\tNo Promotions\r\n"; } if (The_mission.support_ships.max_support_ships == 0) { buffer += "\tNo Support ships\r\n"; } temp.Format("Squadron: %s, Squadron logo: %s\r\n", The_mission.squad_name, The_mission.squad_filename); buffer += temp; } void DumpStats::get_background_stats(CString &buffer) { CString temp; int i; // Background buffer += "\r\n\tBACKGROUND INFO\r\n"; // Num stars temp.Format("Num_stars: %d\r\n", Num_stars); buffer += temp; // Suns temp.Format("Num_suns: %d\r\n", stars_get_num_suns()); buffer += temp; for (i=0; i 0) { // active or passive if (Asteroid_field.field_type == FT_ACTIVE) { temp.Format("\tActive Field\r\n"); buffer += temp; temp.Format("\tAsteroid Debris\r\n"); buffer += temp; } else { // passive temp.Format("\tPassive Field\r\n"); buffer += temp; if (Asteroid_field.debris_genre == DG_ASTEROID) { temp.Format("\tAsteroid Debris\r\n"); buffer += temp; } else { temp.Format("\tShip Debris\r\n"); buffer += temp; // species temp.Format("\t\tSpecies: "); for (i=0; i<(int)Species_info.size(); i++) { if (Asteroid_field.field_debris_type[i] >= 0) { temp += CString(Species_info[(Asteroid_field.field_debris_type[i] / NUM_DEBRIS_SIZES) - 1].species_name) + " "; } } temp += "\r\n"; buffer += temp; } } } // Nebula mission int nebula_mission = (The_mission.flags[Mission::Mission_Flags::Fullneb]); temp = "Nebula mission:"; if (nebula_mission) { temp += " Yes\r\n"; } else { temp += " No\r\n"; } buffer += temp; if (nebula_mission) { // range temp.Format("\tNebula awacs range: %.0f\r\n", Neb2_awacs); buffer += temp; // list of poofs for (i=0; i 0) { //-V805 temp.Format("\tNebula texture: %s\r\n", Neb2_texture_name); buffer += temp; } } else { // FS! nebula pattern if (Nebula_index > 0) { temp.Format("\tOld style FS1 nebula filename: %s\r\n", Nebula_filenames[Nebula_index]); buffer += temp; } } // Subspace mission temp = "Subspace mission:"; if (The_mission.flags[Mission::Mission_Flags::Subspace]) { temp += " Yes\r\n"; } else { temp += " No\r\n"; } buffer += temp; } void DumpStats::get_object_stats(CString &buffer) { object *objp; int obj_type_count[MAX_OBJECT_TYPES]; CString temp; int num_small_ships, num_big_ships, num_huge_ships; int i; memset(obj_type_count,0, sizeof(obj_type_count)); num_small_ships = num_big_ships = num_huge_ships= 0; for ( objp = GET_FIRST(&obj_used_list); objp != END_OF_LIST(&obj_used_list); objp = GET_NEXT(objp) ) { // inc big ship or small ship count if ( (objp->type == OBJ_SHIP) || (objp->type == OBJ_START) ) { if ( Ship_info[Ships[objp->instance].ship_info_index].is_small_ship() ) { num_small_ships++; } else if ( Ship_info[Ships[objp->instance].ship_info_index].is_big_or_huge() ) { num_big_ships++; } } obj_type_count[objp->type]++; } // Statistics buffer += "\r\n\tMISSION STATISTICS\r\n"; // OBJ_START is also a OBJ_SHIP // not counting num_waves (for wings) obj_type_count[OBJ_SHIP] += obj_type_count[OBJ_START]; for (i=0; i 0) { switch(i) { case OBJ_SHIP: temp.Format("Ship Count: %d\r\n", obj_type_count[i]); buffer += temp; break; case OBJ_START: temp.Format("Start Count: %d\r\n", obj_type_count[i]); buffer += temp; break; case OBJ_WAYPOINT: temp.Format("Waypoint Count: %d\r\n", obj_type_count[i]); buffer += temp; break; case OBJ_WING: temp.Format("Wing Count: %d\r\n", obj_type_count[i]); buffer += temp; break; case OBJ_JUMP_NODE: temp.Format("Jump Node Count: %d\r\n", obj_type_count[i]); buffer += temp; break; default: Int3(); break; } } } buffer += "\r\nSHIPS\r\n"; temp.Format("\tNum small ships: %d\r\n", num_small_ships); buffer += temp; temp.Format("\tNum big ships: %d\r\n", num_big_ships); buffer += temp; temp.Format("\tNum huge ships: %d\r\n", num_huge_ships); buffer += temp; // Waypoints size_t total_waypoints = 0; buffer += "\r\nWAYPOINTS\r\n"; SCP_list::iterator ii; for (ii = Waypoint_lists.begin(); ii != Waypoint_lists.end(); ++ii) { temp.Format("\tWaypoint: %s, count: %d\r\n", ii->get_name(), ii->get_waypoints().size()); buffer += temp; total_waypoints += ii->get_waypoints().size(); } if (total_waypoints > 0) { temp.Format("\ttotal_waypoints: " SIZE_T_ARG "\r\n", total_waypoints); buffer += temp; } // Jumpnodes buffer += "\r\nJUMPNODES\r\n"; SCP_list::iterator jnp; for (jnp = Jump_nodes.begin(); jnp != Jump_nodes.end(); ++jnp) { temp.Format("\tJumpnode: %s\r\n", jnp->GetName()); buffer += temp; } if (!Jump_nodes.empty()) { temp.Format("\ttotal_jumpnodes: " SIZE_T_ARG "\r\n", Jump_nodes.size()); buffer += temp; } // Wings int num_counted_wings = 0; buffer += "\r\nWINGS\r\n"; for (i=0; i 0) { temp.Format("\tWing Name: %s, wave_count: %d, num_waves: %d\r\n", Wings[i].name, Wings[i].wave_count, Wings[i].num_waves); buffer += temp; num_counted_wings++; if (num_counted_wings == Num_wings) { break; } } } // Escort buffer += "\r\nESCORT\r\n"; for ( objp = GET_FIRST(&obj_used_list); objp != END_OF_LIST(&obj_used_list); objp = GET_NEXT(objp) ) { if ( (objp->type == OBJ_SHIP) || (objp->type == OBJ_START) ) { if (Ships[objp->instance].flags[Ship::Ship_Flags::Escort]) { temp.Format("\tShip name: %s, priority: %d\r\n", Ships[objp->instance].ship_name, Ships[objp->instance].escort_priority); buffer += temp; } } } // Hotkeys buffer += "\r\nHOTKEYS\r\n"; // ship hotkeys for ( objp = GET_FIRST(&obj_used_list); objp != END_OF_LIST(&obj_used_list); objp = GET_NEXT(objp) ) { if ( (objp->type == OBJ_SHIP) || (objp->type == OBJ_START) ) { if (Ships[objp->instance].hotkey != -1) { temp.Format("\tShip name: %s, hotkey: F%d\r\n", Ships[objp->instance].ship_name, (Ships[objp->instance].hotkey + 5)); buffer += temp; } } } // wing hotkeys for (i=0; i 0) { if (Wings[i].hotkey != -1) { temp.Format("\tWing name: %s, hotkey: F%d\r\n", Wings[i].name, (Wings[i].hotkey + 5)); buffer += temp; } } } } void DumpStats::get_objectives_and_goals(CString &buffer) { CString temp; int i; buffer += "\r\nOBJECTIVES AND GOALS\r\n"; // objectives for (i=0; i 0) temp.Format("\tWeapon name: %s, count %d\r\n", Weapon_info[Team_data[i].weaponry_pool[j]].name, Team_data[i].weaponry_count[j]); buffer += temp; } } } void DumpStats::get_messaging_info(CString &buffer) { CString temp; object *objp; ship *shipp; buffer += "\r\nSHIP ACCEPTED ORDERS\r\n"; // go through all ships and check (.orders_accepted against default_orders) for ( objp = GET_FIRST(&obj_used_list); objp != END_OF_LIST(&obj_used_list); objp = GET_NEXT(objp) ) { if (objp->type == OBJ_START || objp->type == OBJ_SHIP) { shipp = &Ships[objp->instance]; if (shipp->orders_accepted != ship_get_default_orders_accepted(&Ship_info[shipp->ship_info_index])) { temp.Format("\tShip: %s with nonstandard accepted orders\r\n", shipp->ship_name); buffer += temp; } } } } void DumpStats::get_species_ship_breakdown(CString &buffer) { CString temp; int i; int species; object *objp; ship *shipp; buffer += "\r\nSHIP SPECIES BREAKDOWN\r\n"; for (species=0; (uint) species < Species_info.size(); species++) { buffer += Species_info[species].species_name; buffer += "\r\n"; // fighter wings buffer += "\tFighter wings:\r\n"; for (i=0; i 0) { int wing_leader_shipnum = Wings[i].ship_index[Wings[i].special_ship]; if (Ship_info[Ships[wing_leader_shipnum].ship_info_index].species == species) { if (Ship_info[Ships[wing_leader_shipnum].ship_info_index].flags[Ship::Info_Flags::Fighter]) { temp.Format("\t\tWing: %s, count: %d, waves: %d, type: %s\r\n", Wings[i].name, Wings[i].wave_count, Wings[i].num_waves, Ship_info[Ships[wing_leader_shipnum].ship_info_index].name); buffer += temp; } } } } // bomber wings buffer += "\tBomber wings:\r\n"; for (i=0; i 0) { int wing_leader_shipnum = Wings[i].ship_index[Wings[i].special_ship]; if (Ship_info[Ships[wing_leader_shipnum].ship_info_index].species == species) { if (Ship_info[Ships[wing_leader_shipnum].ship_info_index].flags[Ship::Info_Flags::Bomber]) { temp.Format("\t\tWing: %s, count: %d, waves: %d, type: %s\r\n", Wings[i].name, Wings[i].wave_count, Wings[i].num_waves, Ship_info[Ships[wing_leader_shipnum].ship_info_index].name); buffer += temp; } } } } buffer += "\tFreighters, Cargo, Transports:\r\n"; // freighters and transports (cargo) for ( objp = GET_FIRST(&obj_used_list); objp != END_OF_LIST(&obj_used_list); objp = GET_NEXT(objp) ) { if (objp->type == OBJ_START || objp->type == OBJ_SHIP) { shipp = &Ships[objp->instance]; if (Ship_info[shipp->ship_info_index].species == species) { //if (shipp->wingnum == -1) //if (shipp->cargo1 > 0) if (Ship_info[shipp->ship_info_index].flags[Ship::Info_Flags::Freighter] || Ship_info[shipp->ship_info_index].flags[Ship::Info_Flags::Transport] || Ship_info[shipp->ship_info_index].flags[Ship::Info_Flags::Cargo]) { temp.Format("\t\tName: %s Type: %s, Cargo: %s\r\n", shipp->ship_name, Ship_info[shipp->ship_info_index].name, Cargo_names[shipp->cargo1]); buffer += temp; } } } } buffer += "\tNav buoy, Escape pod, Sentry gun:\r\n"; for ( objp = GET_FIRST(&obj_used_list); objp != END_OF_LIST(&obj_used_list); objp = GET_NEXT(objp) ) { if (objp->type == OBJ_START || objp->type == OBJ_SHIP) { shipp = &Ships[objp->instance]; if (Ship_info[shipp->ship_info_index].species == species) { //if (shipp->wingnum == -1) //if (shipp->cargo1 > 0) if (Ship_info[shipp->ship_info_index].flags[Ship::Info_Flags::Navbuoy] || Ship_info[shipp->ship_info_index].flags[Ship::Info_Flags::Escapepod] || Ship_info[shipp->ship_info_index].flags[Ship::Info_Flags::Sentrygun]) { temp.Format("\t\tName: %s, Type: %s Cargo: %s\r\n", shipp->ship_name, Ship_info[shipp->ship_info_index].name, Cargo_names[shipp->cargo1]); buffer += temp; } } } } // cruiser buffer += "\tCruiser:\r\n"; for ( objp = GET_FIRST(&obj_used_list); objp != END_OF_LIST(&obj_used_list); objp = GET_NEXT(objp) ) { if (objp->type == OBJ_START || objp->type == OBJ_SHIP) { shipp = &Ships[objp->instance]; if (Ship_info[shipp->ship_info_index].species == species) { //if (shipp->wingnum == -1) //if (shipp->cargo1 > 0) if (Ship_info[shipp->ship_info_index].flags[Ship::Info_Flags::Cruiser]) { temp.Format("\t\tName: %s, Type: %s, Cargo: %s\r\n", shipp->ship_name, Ship_info[shipp->ship_info_index].name, Cargo_names[shipp->cargo1]); buffer += temp; } } } } // dry dock, cap, super cap buffer += "\tDry dock, Capital, Supercap:\r\n"; for ( objp = GET_FIRST(&obj_used_list); objp != END_OF_LIST(&obj_used_list); objp = GET_NEXT(objp) ) { if (objp->type == OBJ_START || objp->type == OBJ_SHIP) { shipp = &Ships[objp->instance]; if (Ship_info[shipp->ship_info_index].species == species) { //if (shipp->wingnum == -1) //if (shipp->cargo1 > 0) if (Ship_info[shipp->ship_info_index].flags[Ship::Info_Flags::Drydock] || Ship_info[shipp->ship_info_index].flags[Ship::Info_Flags::Capital] || Ship_info[shipp->ship_info_index].flags[Ship::Info_Flags::Supercap]) { temp.Format("\t\tName: %s, Type: %s, Cargo: %s\r\n", shipp->ship_name, Ship_info[shipp->ship_info_index].name, Cargo_names[shipp->cargo1]); buffer += temp; } } } } buffer += "\r\n"; } } void dump_loadout(ship *shipp, CString &loadout) { CString temp; char *weapon_name; loadout = ""; // PRIMARY int pri_idx, sec_idx; for (pri_idx=0; pri_idx < shipp->weapons.num_primary_banks; pri_idx++) { if (shipp->weapons.primary_bank_weapons[pri_idx] == -1) { weapon_name = "none"; } else { weapon_name = Weapon_info[shipp->weapons.primary_bank_weapons[pri_idx]].name; } temp.Format("\t\t\tPrimary[%d]: %s\r\n", pri_idx+1, weapon_name); loadout += temp; } // SECONDARY for (sec_idx=0; sec_idx < shipp->weapons.num_secondary_banks; sec_idx++) { if (shipp->weapons.secondary_bank_weapons[sec_idx] == -1) { weapon_name = "none"; } else { weapon_name = Weapon_info[shipp->weapons.secondary_bank_weapons[sec_idx]].name; } temp.Format("\t\t\tSecondary[%d]: %s\r\n", sec_idx+1, weapon_name); loadout += temp; } // TURRET ship_subsys *ss; for (ss = GET_FIRST(&shipp->subsys_list); ss != END_OF_LIST(&shipp->subsys_list); ss = GET_NEXT(ss) ) { if ( (ss->system_info->type == SUBSYSTEM_TURRET) ) { // ss->weapons.num_primary_banks, ss->weapons.num_secondary_banks, ss->weapons.primary_bank_weapons[3], ss->weapons.secondary_bank_weapons[2] // ss->system_info->primary_banks, ss->system_info->secondary_banks temp.Format("\t\t\tTurret: %s\r\n", ss->system_info->subobj_name); loadout += temp; // PRIMARY for (pri_idx=0; pri_idx < ss->weapons.num_primary_banks; pri_idx++) { if (ss->weapons.primary_bank_weapons[pri_idx] == -1) { weapon_name = "none"; } else { weapon_name = Weapon_info[ss->weapons.primary_bank_weapons[pri_idx]].name; } temp.Format("\t\t\t\tPrimary[%d]: %s\r\n", pri_idx+1, weapon_name); loadout += temp; } // SECONDARY for (sec_idx=0; sec_idx < ss->weapons.num_secondary_banks; sec_idx++) { if (ss->weapons.secondary_bank_weapons[sec_idx] == -1) { weapon_name = "none"; } else { weapon_name = Weapon_info[ss->weapons.secondary_bank_weapons[sec_idx]].name; } temp.Format("\t\t\t\tSecondary[%d]: %s\r\n", sec_idx+1, weapon_name); loadout += temp; } } } } void DumpStats::get_default_ship_loadouts(CString &buffer) { int i; int species; object *objp; ship *shipp; CString temp, loadout; buffer += "\r\nSHIP SPECIES BREAKDOWN\r\n"; for (species=0; (uint) species < Species_info.size(); species++) { buffer += Species_info[species].species_name; buffer += "\r\n"; // fighter wings buffer += "\tFighter wings:\r\n"; for (i=0; i 0) { int wing_leader_shipnum = Wings[i].ship_index[Wings[i].special_ship]; if (Ship_info[Ships[wing_leader_shipnum].ship_info_index].species == species) { if (Ship_info[Ships[wing_leader_shipnum].ship_info_index].flags[Ship::Info_Flags::Fighter]) { temp.Format("\t\tWing: %s\r\n", Wings[i].name); buffer += temp; dump_loadout(&Ships[wing_leader_shipnum], loadout); buffer += loadout; } } } } // bomber wings buffer += "\tBomber wings:\r\n"; for (i=0; i 0) { int wing_leader_shipnum = Wings[i].ship_index[Wings[i].special_ship]; if (Ship_info[Ships[wing_leader_shipnum].ship_info_index].species == species) { if (Ship_info[Ships[wing_leader_shipnum].ship_info_index].flags[Ship::Info_Flags::Bomber]) { temp.Format("\t\tWing: %s\r\n", Wings[i].name); buffer += temp; dump_loadout(&Ships[wing_leader_shipnum], loadout); buffer += loadout; } } } } buffer += "\tFreighters, Cargo, Transports:\r\n"; // freighters and transports (cargo) for ( objp = GET_FIRST(&obj_used_list); objp != END_OF_LIST(&obj_used_list); objp = GET_NEXT(objp) ) { if (objp->type == OBJ_START || objp->type == OBJ_SHIP) { shipp = &Ships[objp->instance]; if (Ship_info[shipp->ship_info_index].species == species) { //if (shipp->wingnum == -1) //if (shipp->cargo1 > 0) if (Ship_info[shipp->ship_info_index].flags[Ship::Info_Flags::Freighter] || Ship_info[shipp->ship_info_index].flags[Ship::Info_Flags::Transport]) { temp.Format("\t\tName: %s\r\n", shipp->ship_name); buffer += temp; dump_loadout(shipp, loadout); buffer += loadout; } } } } buffer += "\tEscape pod, Sentry gun:\r\n"; for ( objp = GET_FIRST(&obj_used_list); objp != END_OF_LIST(&obj_used_list); objp = GET_NEXT(objp) ) { if (objp->type == OBJ_START || objp->type == OBJ_SHIP) { shipp = &Ships[objp->instance]; if (Ship_info[shipp->ship_info_index].species == species) { //if (shipp->wingnum == -1) //if (shipp->cargo1 > 0) if (Ship_info[shipp->ship_info_index].flags[Ship::Info_Flags::Escapepod] || Ship_info[shipp->ship_info_index].flags[Ship::Info_Flags::Sentrygun]) { temp.Format("\t\tName: %s\r\n", shipp->ship_name); buffer += temp; dump_loadout(shipp, loadout); buffer += loadout; } } } } // cruiser buffer += "\tCruiser:\r\n"; for ( objp = GET_FIRST(&obj_used_list); objp != END_OF_LIST(&obj_used_list); objp = GET_NEXT(objp) ) { if (objp->type == OBJ_START || objp->type == OBJ_SHIP) { shipp = &Ships[objp->instance]; if (Ship_info[shipp->ship_info_index].species == species) { //if (shipp->wingnum == -1) //if (shipp->cargo1 > 0) if (Ship_info[shipp->ship_info_index].flags[Ship::Info_Flags::Cruiser]) { temp.Format("\t\tName: %s\r\n", shipp->ship_name); buffer += temp; dump_loadout(shipp, loadout); buffer += loadout; } } } } // dry dock, cap, super cap buffer += "\tCapital, Supercap:\r\n"; for ( objp = GET_FIRST(&obj_used_list); objp != END_OF_LIST(&obj_used_list); objp = GET_NEXT(objp) ) { if (objp->type == OBJ_START || objp->type == OBJ_SHIP) { shipp = &Ships[objp->instance]; if (Ship_info[shipp->ship_info_index].species == species) { //if (shipp->wingnum == -1) //if (shipp->cargo1 > 0) if (Ship_info[shipp->ship_info_index].flags[Ship::Info_Flags::Capital] || Ship_info[shipp->ship_info_index].flags[Ship::Info_Flags::Supercap]) { temp.Format("\t\tName: %s\r\n", shipp->ship_name); buffer += temp; dump_loadout(shipp, loadout); buffer += loadout; } } } } buffer += "\r\n"; } // go through all wings // go through all ships not in wings and FLYABLE // print primary, secondary, and BIG turrets }