View Issue Details

IDProjectCategoryView StatusLast Update
0002623FSSCPtablespublic2012-09-25 13:24
ReporterMjnMixael Assigned Tokarajorma  
PrioritynormalSeverityfeatureReproducibilityN/A
Status resolvedResolutionfixed 
Fixed in Version3.7.2 
Summary0002623: Ignore Campaign Via Mod.tbl
DescriptionAdd a game_settings.tbl flag to ignore campaign files (if they exist), like freesapce2.fc2.

Useful for mods that are based on Freespace2 but cause the Freespace2 campaign to be unplayable.
TagsNo tags attached.

Activities

MjnMixael

2012-03-11 19:47

manager   ~0013414

Last edited: 2012-03-11 19:53

I thought of an issue that might present itself with an $ignore campaign file flag. If you ignore the campaign file, then all the campaign's missions will be loaded as single missions instead.

You likely have already thought of this though, but the $ignore campaign flag should probably read the campaign file and ignore any missions it calls for or something....

OR, load the campaign, but just make it completely invisible in the campaign room. (This one seems like a cleaner solution to me.)

karajorma

2012-09-24 14:42

administrator  

Ignore_Campaigns.patch (5,118 bytes)   
Index: code/mission/missioncampaign.cpp
===================================================================
--- code/mission/missioncampaign.cpp	(revision 9221)
+++ code/mission/missioncampaign.cpp	(working copy)
@@ -63,6 +63,7 @@
 int	Num_campaigns;
 int Campaign_file_missing;
 int Campaign_names_inited = 0;
+SCP_vector<SCP_string> Ignored_campaigns;
 
 char Default_campaign_file_name[MAX_FILENAME_LEN - 4]  = { 0 };
 
@@ -106,6 +107,8 @@
 #define CAMPAIGN_STATS_FILE_COMPATIBLE_VERSION	1
 #define CAMPAIGN_STATS_FILE_ID						0xabbadaad
 
+bool campaign_is_ignored(char *filename, bool add_extension = false);
+
 /**
  * Returns a string (which is malloced in this routine) of the name of the given freespace campaign file.  
  * In the type field, we return if the campaign is a single player or multiplayer campaign.  
@@ -258,9 +261,14 @@
 {
 	char name[NAME_LENGTH];
 	char *desc = NULL;
-	int type, max_players;
+	int i, type, max_players;
 
 	if ( mission_campaign_get_info( filename, name, &type, &max_players, &desc) ) {
+		// don't add ignored campaigns
+		if (campaign_is_ignored(filename)) {
+			return 0;
+		}
+
 		if ( !MC_multiplayer && (type == CAMPAIGN_TYPE_SINGLE) ) {
 			Campaign_names[Num_campaigns] = vm_strdup(name);
 
@@ -429,6 +437,11 @@
 
 	filename = cf_add_ext(filename, FS_CAMPAIGN_FILE_EXT);
 
+	if (campaign_is_ignored(filename)) {
+		Campaign_file_missing = 1;
+		return CAMPAIGN_ERROR_IGNORED;
+	}
+
 	// open localization
 	lcl_ext_open();	
 
@@ -2338,6 +2351,28 @@
 		Int3();
 }
 
+bool campaign_is_ignored(char *filename, bool add_extension)
+{
+	bool current_campaign_ignored = false;
+	int i;
+	char campaign_name[NAME_LENGTH] = {""};
+
+	strcpy_s(campaign_name, filename);
+
+	if (add_extension) {
+		strcat_s(campaign_name, FS_CAMPAIGN_FILE_EXT);
+	}
+
+	for (i = 0; i < (int)Ignored_campaigns.size(); i++) {
+		if (!stricmp (campaign_name, Ignored_campaigns[i].c_str())) {
+			current_campaign_ignored = true;
+			break;
+		}
+	}
+	
+	return current_campaign_ignored;
+}
+
 // returns 0: loaded, !0: error
 int mission_load_up_campaign( player *pl )
 {
@@ -2345,27 +2380,32 @@
 		pl = Player;
 
 	if ( strlen(pl->current_campaign) ) {
-		return mission_campaign_load(pl->current_campaign, pl);
-	} else {
-		int rc = mission_campaign_load(Default_campaign_file_name, pl);
+		if (!campaign_is_ignored(pl->current_campaign, true)) {
+			return mission_campaign_load(pl->current_campaign, pl);
+		}
+		else {
+			Campaign_file_missing = 1;
+		}
+	}
 
-		// if the builtin campaign is missing/corrupt then try and fall back on whatever is available
-		if (rc) {
-			// no descriptions, and no sorting since we want the actual first entry found
-			mission_campaign_build_list(false, false);
+	int rc = mission_campaign_load(Default_campaign_file_name, pl);
 
-			if ( (Campaign_file_names[0] != NULL) && strlen(Campaign_file_names[0]) )
-				rc = mission_campaign_load(Campaign_file_names[0], pl);
+	// if the builtin campaign is missing/corrupt then try and fall back on whatever is available
+	if (rc) {
+		// no descriptions, and no sorting since we want the actual first entry found
+		mission_campaign_build_list(false, false);
 
-			mission_campaign_free_list();
-		}
-		
-		if (!rc) {
-			pl->main_hall = Campaign.missions[0].main_hall;
-			strcpy_s(pl->current_campaign, Campaign.filename);
-		}
-		return rc;
+		if ( (Campaign_file_names[0] != NULL) && strlen(Campaign_file_names[0]) )
+			rc = mission_campaign_load(Campaign_file_names[0], pl);
+
+		mission_campaign_free_list();
 	}
+	
+	if (!rc) {
+		pl->main_hall = Campaign.missions[0].main_hall;
+		strcpy_s(pl->current_campaign, Campaign.filename);
+	}
+	return rc;
 }
 
 /**
Index: code/mission/missioncampaign.h
===================================================================
--- code/mission/missioncampaign.h	(revision 9221)
+++ code/mission/missioncampaign.h	(working copy)
@@ -24,6 +24,7 @@
 #define CAMPAIGN_ERROR_CORRUPT			-1
 #define CAMPAIGN_ERROR_SEXP_EXHAUSTED	-2
 #define CAMPAIGN_ERROR_MISSING			-3
+#define CAMPAIGN_ERROR_IGNORED			-4
 
 // types of campaigns -- these defines match the string literals listed below which
 // are found in the campaign files.  I don't think that we need campaigns for furball
@@ -143,6 +144,7 @@
 extern char *Campaign_descs[MAX_CAMPAIGNS];
 extern int	Num_campaigns;
 extern int	Campaign_names_inited;
+extern SCP_vector<SCP_string> Ignored_campaigns;
 
 extern char Default_campaign_file_name[MAX_FILENAME_LEN - 4];
 
Index: code/mod_table/mod_table.cpp
===================================================================
--- code/mod_table/mod_table.cpp	(revision 9221)
+++ code/mod_table/mod_table.cpp	(working copy)
@@ -72,6 +72,14 @@
 		strcpy_s(Default_campaign_file_name, temp);
 	}
 
+	if (optional_string("#Ignored Campaign File Names")) {
+		SCP_string campaign_name; 
+		while (optional_string("$Campaign File Name:")) {
+			stuff_string(campaign_name, F_NAME); 
+			Ignored_campaigns.push_back(campaign_name); 
+		}
+	}
+
 	optional_string("#HUD SETTINGS");
 
 	// how long should the game wait before displaying a directive?
Ignore_Campaigns.patch (5,118 bytes)   

karajorma

2012-09-24 14:42

administrator   ~0013971

Patch attached. I'll make some builds and put them up in a bit.

karajorma

2012-09-24 15:09

administrator   ~0013972

http://www.hard-light.net/forums/index.php?topic=82318

MjnMixael

2012-09-25 00:50

manager   ~0013974

Works for me all around.

Issue History

Date Modified Username Field Change
2012-03-06 03:10 MjnMixael New Issue
2012-03-06 03:11 karajorma Assigned To => karajorma
2012-03-06 03:11 karajorma Status new => assigned
2012-03-11 19:47 MjnMixael Note Added: 0013414
2012-03-11 19:53 MjnMixael Note Edited: 0013414
2012-09-24 14:42 karajorma File Added: Ignore_Campaigns.patch
2012-09-24 14:42 karajorma Note Added: 0013971
2012-09-24 15:09 karajorma Note Added: 0013972
2012-09-25 00:50 MjnMixael Note Added: 0013974
2012-09-25 13:24 karajorma Status assigned => resolved
2012-09-25 13:24 karajorma Fixed in Version => 3.7.2
2012-09-25 13:24 karajorma Resolution open => fixed