Skip to content

Make comm order types modder-configurable, and add separate types for fighters and bombers - #7721

Open
Kestrellius wants to merge 3 commits into
scp-fs2open:masterfrom
Kestrellius:split-fighter-bomber-orders
Open

Make comm order types modder-configurable, and add separate types for fighters and bombers#7721
Kestrellius wants to merge 3 commits into
scp-fs2open:masterfrom
Kestrellius:split-fighter-bomber-orders

Conversation

@Kestrellius

Copy link
Copy Markdown
Contributor

Comm order types (that is, the list of things that can be messaged -- ships, wings, reinforcements, etc.) are now no longer a fixed list. Of the eight possible types, the modder may specify an arbitrary list in arbitrary order, with text specified in the table.

This was to facilitate the addition of two new types, All Fighters and All Bombers -- as distinct from the retail type typically called All Fighters, which is really "all fighters and bombers". (All player-facing retail naming remains as default.) My experience as a player suggests that these new options will be extremely useful.

@wookieejedi wookieejedi added enhancement A new feature or upgrade of an existing feature to add additional functionality. HUD A feature or issue related to the HUD labels Aug 21, 2026
@wookieejedi wookieejedi added this to the Release 26.2 milestone Aug 29, 2026
Comment thread code/hud/hudsquadmsg.cpp

if ((Player_ship != NULL) && !hud_squadmsg_reinforcements_available(Player_ship->team)) {
MsgItems[TYPE_REINFORCEMENT_ITEM].active = 0;
for ( auto item : MsgItems ) {

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I think this should be for (auto &item : MsgItems) similar to how the traitor check right above this uses for (auto &item : MsgItems)

Comment thread code/hud/hudsquadmsg.cpp
} else {
// in config mode, so create just the first page of the Comms Menu
// as other functions, such as hud_squadmsg_type_select() will not be run in config mode
const char* temp_comm_order_types[] = {XSTR("Ships", 293),

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I reckon the config mode section shown on the HUD Config screen also be updated to reflect these changes so that players/mods get shown an accurate representation of what the comms menu will look like.

Comment thread code/hud/hudsquadmsg.cpp
int item_num;
bool isSelectedItem = (i == Selected_menu_item);
char text[256];
mmode_item item = MsgItems[First_menu_item + i];

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This should possibly be guarded by the !config flag? IE since the default config screen may have a different number that could end up being out of bounds

Comment thread code/hud/hudsquadmsg.cpp
item.active = hud_squadmsg_exist_fighters_bombers(SmallCraftFlavor::ALL_BOMBERS);
break;
case CommOrderType::REINFORCEMENTS:
item.active = (Player_ship != nullptr) && !hud_squadmsg_reinforcements_available(Player_ship->team) && Msg_shortcut_command == -1;

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Original logic was (Player_ship != NULL) && !hud_squadmsg_reinforcements_available(Player_ship->team) -> 0 so looks like we need to remove the ! here for the hud_squadmsg_reinforcements_available function.

Also, C++ should be smart enough to realize the returned bools are 0 or 1 but would it make sense to clearly stated it with ? 0 :1?

Comment thread code/hud/hudsquadmsg.cpp
void hud_init_comm_orders()
{
int i;

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Old code overwrote a fixed array while the new one emplace_backs, so you may consider adding a clear() for extra safety

Comment thread code/hud/hudsquadmsg.cpp
switch (flavor) {
case SmallCraftFlavor::ALL_FIGHTERS_AND_BOMBERS:
return sinfop->is_fighter_bomber();
break;

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Minor, but may not need the 'breakif you are already usingreturn`

Comment thread code/hud/hudsquadmsg.cpp
}
}


Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Minor, but extra whitespace. May be on purpose though?

@wookieejedi

wookieejedi commented Sep 4, 2026

Copy link
Copy Markdown
Member

Very useful feature to have! Added some in-line comments and here are four more general ones:

  1. Order flavor is lost for multiplayer clients (see around multimsgs.cpp:4553)

hud_squadmsg_send_to_all_fighters() short-circuits for MULTIPLAYER_CLIENT into send_player_order_packet(SQUAD_MSG_ALL, 0, command) (hudsquadmsg.cpp:1027), which does not have the new small flavor aspect in the packet. As such, the server-side handler calls hud_squadmsg_send_to_all_fighters(command, player_num), defaulting to ALL_FIGHTERS_AND_BOMBERS. As a result, a client choosing "All Bombers" orders every fighter and bomber. To fix this the packet needs a flavor field (note, this will also result in a multiplayer version version bump, which is fine since we can merge this the same day the other multiplayer version bump PRs for 26.2 are needed).

  1. FS2_VOICER builds break (see around voicerec.cpp:80)

Local declaration extern void hud_squadmsg_msg_all_fighters(); has it no longer match the definition, which gained a non-defaulted SmallCraftFlavor parameter (has a link error at the call on line 500). Separately, line 128's Msg_instance == MESSAGE_ALL_FIGHTERS || Squad_msg_mode == SM_MODE_ALL_FIGHTERS silently changed meaning: those now denote fighters-only, so voice recognition no longer recognizes the fighters+bombers mode. I reckon both need MESSAGE_ALL_FIGHTERS_BOMBERS / SM_MODE_ALL_FIGHTERS_BOMBERS added.

  1. Mixed wings are classified by the leader alone (see around hudsquadmsg.cpp:1074)

hud_squadmsg_send_to_all_fighters() tests wings via Wings[i].special_ship_ship_info_index, and the loose-ship loop below skips anything with wingnum != -1. So for a fighter/bomber mixed wing:

"All Bombers" on a fighter-led wing = the wing's bombers get nothing, and they're unreachable by the second loop too.
"All Fighters" on a fighter-led wing = the wing's bombers get the order anyway.

This was harmless when the only flavor was fighters-or-bombers, though now with the split it gets tricky. As an added complication, the greying-out check in hud_squadmsg_ship_command() (line 2178) iterates ships individually, so the menu enables an order based on per-ship class while the send filters by wing leader. Note sure the best way to handle this. It might be that just keeping the wingleader as what the wing is useful, but that of course does not work for mixed wings (such as those with 2 bomber and 2 fighters).

  1. Order history can't distinguish the three flavors (see around hudsquadmsg.cpp:1086, 1124)

All three flavors call hud_add_issued_order("All Fighters", command), which maps to at line 2613. A mission using the query-orders SEXP will see an "all bombers" order as satisfying , and can't detect the new flavors at all.

Comment thread code/hud/hudsquadmsg.cpp
MsgItems.push_back({Comm_order_types[i].first, 1, Comm_order_types[i].second}); // assume active
} else {
MsgItems.push_back({0, 1, lua_cat_list[i - NUM_COMM_ORDER_TYPES]}); // assume active
MsgItems.push_back({0, 1, lua_cat_list[i - sz2i(Comm_order_types.size())]}); // assume active

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The old dispatch code compared k (index), which was correct; this PR switches to comparing instance, which Lua items leave at 0. As such, Lua category items are pushed with instance = 0, which is now CommOrderType::MSG_SHIPS. Dispatch at line 1861 tests MsgItems[k].instance == CommOrderType::MSG_SHIPS first, so selecting any Lua category opens the ship-select menu instead of SM_MODE_GENERAL: the k >= Comm_order_types.size() branch at 1877 is unreachable. Same problem in the switch at 1805: Lua items get active = hud_squadmsg_count_ships(0).

I think the best way to fix this would be to give them a sentinel instance (MAX_COMM_ORDER_TYPES, or a dedicated LUA_GENERAL value) and run the logic on that.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

enhancement A new feature or upgrade of an existing feature to add additional functionality. HUD A feature or issue related to the HUD

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants