This OSP script of the week fills in the functionality for the Military Academy from the previous combat modifier buildings. If you would rather not add in the framework some extra buildings, simply replace all references of slot_center_has_academy with slot_town_prosperity, which should limit the number of troops available for upgrade in a semi-reasonable fashion.
To use this, go through the party list on the left and select one of the two options below the troop's tableau. This is intended for usage in promoting troops to alternative branches (i.e. knighthood, bandits into faction recruits) but that implementation is left as an exercise for the reader. Holding shift/ctrl has the same effect as it would in the party menu, and up/down or mwheel goes through the stacks. There are also some gamepad buttons that you can experiment with, but are untested.
This mesh used for the background requires a planar mesh and a duplicate material with the following settings - otherwise you get psychedelic transparency issues.
Alternatively, download the following WIP with some extra bits, you still need to add the two lines above
To access the presentation drop this in the appropriate menu (the recommended being the default town in which buildings are probably present)
Credits for the original party stack interface go to rubik's Custom Commander - "Sort the Defender" presentation.
To use this, go through the party list on the left and select one of the two options below the troop's tableau. This is intended for usage in promoting troops to alternative branches (i.e. knighthood, bandits into faction recruits) but that implementation is left as an exercise for the reader. Holding shift/ctrl has the same effect as it would in the party menu, and up/down or mwheel goes through the stacks. There are also some gamepad buttons that you can experiment with, but are untested.
("upgrade_troops", 0, mesh_face_gen_window, [
(ti_on_presentation_load,
[
(presentation_set_duration, 999999),
(set_fixed_point_multiplier, 1000),
## next presentation
(assign, "$g_presentation_next_presentation", -1),
(assign, "$g_talk_troop", -1),
(assign, "$g_talk_troop_met", -1),
(str_clear, s0),
(create_text_overlay, "$g_presentation_obj_1", s0, tf_scrollable),
(position_set_x, pos1, 510),
(position_set_y, pos1, 100),
(overlay_set_position, "$g_presentation_obj_1", pos1),
(position_set_x, pos1, 400),
(position_set_y, pos1, 600),
(overlay_set_area_size, "$g_presentation_obj_1", pos1),
(set_container_overlay, "$g_presentation_obj_1"),
(assign, ":pos_x", 150),
(party_get_num_companion_stacks, ":num_stacks", "p_main_party"),
(try_begin), #limit stack range to updated stacks
(val_clamp, "$g_cur_stack", -1, ":num_stacks"),
(party_stack_get_troop_id, ":troop_no", "p_main_party", "$g_cur_stack"),
(this_or_next|le, ":troop_no", 0),
(troop_is_hero, ":troop_no"),
(assign, "$g_cur_stack", -1),
(try_end),
(store_mul, ":pos_y", ":num_stacks", 40),
(val_sub, ":pos_y", 40),
(val_max, ":pos_y", 560),
(try_for_range, ":slot_no", 0, ":num_stacks"),
(party_stack_get_troop_id, ":troop_no", "p_main_party", ":slot_no"),
(troop_is_hero, ":troop_no"), #discard results from displaying
(troop_set_slot, "trp_temp_array_a", ":slot_no", -1),
(else_try),
(party_stack_get_size, ":stack_size", "p_main_party", ":slot_no"),
(party_stack_get_num_wounded, ":num_wounded", "p_main_party", ":slot_no"),
(str_store_troop_name, s1, ":troop_no"),
(assign, reg2, ":stack_size"),
(try_begin),
(gt, ":num_wounded", 0),
(store_sub, reg3, ":stack_size", ":num_wounded"),
(str_store_string, s1, "@{s1} ({reg3}/{reg2})"),
(else_try),
(str_store_string, s1, "@{s1} ({reg2})"),
(try_end),
(create_game_button_overlay, reg1, s1),
(position_set_x, pos1, ":pos_x"),
(position_set_y, pos1, ":pos_y"),
(overlay_set_position, reg1, pos1),
(position_set_x, pos1, 300),
(position_set_y, pos1, 32),
(overlay_set_size, reg1, pos1),
(troop_set_slot, "trp_temp_array_a", ":slot_no", reg1),
(val_sub, ":pos_y", 40),
(try_end),
(try_begin),
(gt, "$g_cur_stack", -1),
(troop_get_slot, ":dest_obj", "trp_temp_array_a", "$g_cur_stack"),
(gt, ":dest_obj", 0),
(overlay_set_alpha, ":dest_obj", 0x80),
(party_stack_get_troop_id, "$g_talk_troop", "p_main_party", "$g_cur_stack"),
(neg|troop_is_hero, "$g_talk_troop"),
(party_stack_get_size, "$g_talk_troop_met", "p_main_party", "$g_cur_stack"),
(party_stack_get_num_wounded, ":num_wounded", "p_main_party", "$g_cur_stack"),
(val_sub, "$g_talk_troop_met", ":num_wounded"),
(try_begin),
(gt, "$g_talk_troop_met", 0),
(store_faction_of_troop, ":color", "$g_talk_troop"),
(faction_get_color, ":color", ":color"),
(overlay_set_color, ":dest_obj", ":color"),
(else_try), #all wounded - cannot upgrade
(overlay_set_color, ":dest_obj", 0xFF0000),
(overlay_set_alpha, ":dest_obj", 0xFF),
(try_end),
(try_end),
(set_container_overlay, -1),
#availability description
(party_get_slot, "$g_talk_troop_relation", "$current_town", slot_center_has_academy),
(assign, reg1, "$g_talk_troop_relation"),
(faction_get_color, ":color", "$g_encountered_party_faction"),
(position_set_x, pos1, 275),
(position_set_y, pos1, 210),
(create_text_overlay, reg1, "@There are {reg1} upgrade available", tf_with_outline|tf_center_justify),
(overlay_set_position, reg1, pos1),
(overlay_set_color, reg1, ":color"),
(store_troop_gold, "$g_talk_agent", "trp_player"),
(try_begin),
(gt, "$g_talk_troop", 0),
(position_set_x, pos1, 275),
(try_begin),
(troop_get_upgrade_troop, ":upgrade_troop", "$g_talk_troop", 0),
(gt, ":upgrade_troop", 0),
(str_store_troop_name, s2, ":upgrade_troop"),
(create_button_overlay, "$g_presentation_obj_2", "@Upgrade to {s2}", tf_center_justify),
(call_script, "script_game_get_join_cost", ":upgrade_troop"),
(try_begin),
(lt, "$g_talk_agent", reg0),
(str_store_string, s1, "@Insufficient funds"),
(overlay_set_color, "$g_presentation_obj_2", 0xFF1111),
(else_try),
(call_script, "script_game_get_money_text", reg0),
(try_end),
(overlay_set_tooltip, "$g_presentation_obj_2", s1),
(position_set_y, pos1, 100),
(overlay_set_position, "$g_presentation_obj_2", pos1),
(try_end),
(try_begin),
(troop_get_upgrade_troop, ":upgrade_troop", "$g_talk_troop", 1),
(gt, ":upgrade_troop", 0),
(str_store_troop_name, s3, ":upgrade_troop"),
(create_button_overlay, "$g_presentation_obj_3", "@Promote to {s3}", tf_center_justify),
(call_script, "script_game_get_join_cost", ":upgrade_troop"),
(try_begin),
(lt, "$g_talk_agent", reg0),
(str_store_string, s1, "@Insufficient funds"),
(overlay_set_color, "$g_presentation_obj_3", 0xFF1111),
(else_try),
(call_script, "script_game_get_money_text", reg0),
(try_end),
(overlay_set_tooltip, "$g_presentation_obj_3", s1),
(position_set_y, pos1, 150),
(overlay_set_position, "$g_presentation_obj_3", pos1),
(try_end),
(try_end),
# cur troop
(try_begin),
(gt, "$g_cur_stack", -1),
(party_stack_get_troop_id, ":troop_no", "p_main_party", "$g_cur_stack"),
(store_mul, ":cur_troop", ":troop_no", 2), #with weapons
(create_image_button_overlay_with_tableau_material, "$g_presentation_obj_6", -1, "tableau_game_party_window", ":cur_troop"),
(position_set_x, pos1, 1750),
(position_set_y, pos1, 1750),
(overlay_set_size, "$g_presentation_obj_6", pos1),
(position_set_x, pos1, 50),
(position_set_y, pos1, 240),
(overlay_set_position, "$g_presentation_obj_6", pos1),
(else_try), #default, startup
(create_mesh_overlay, "$g_presentation_obj_6", "mesh_pic_mb_warrior_1"),
(position_set_x, pos1, -500),
(position_set_y, pos1, 250),
(overlay_set_position, "$g_presentation_obj_6", pos1),
# (overlay_set_display, "$g_presentation_obj_6", 0),
(display_message, "@Press Shift or Ctrl to upgrade up to 5 or all members"),
(try_end),
#gold overlay (image button so we can click on it)
(position_set_x, pos1, 500),
(position_set_y, pos1, 500),
(create_image_button_overlay, "$g_presentation_obj_10", "mesh_icon_gold", "mesh_icon_gold"),
(overlay_set_size, "$g_presentation_obj_10", pos1),
(position_set_x, pos1, 580),
(position_set_y, pos1, 40),
(overlay_set_position, "$g_presentation_obj_10", pos1),
(overlay_set_tooltip, "$g_presentation_obj_10", "@Click here or press ESC to finish recruiting"),
#gold display
(call_script, "script_game_get_money_text", "$g_talk_agent"),
(create_text_overlay, reg1, "@You have {s1}", tf_with_outline),
(position_set_x, pos1, 690),
(position_set_y, pos1, 60),
(overlay_set_position, reg1, pos1),
(overlay_set_color, reg1, 0xFFFFFF),
# done
# (create_game_button_overlay, "$g_presentation_obj_10", "str_done"),
# (position_set_x, pos1, 900),
# (position_set_y, pos1, 50),
# (overlay_set_position, "$g_presentation_obj_10", pos1),
]
),
(ti_on_presentation_event_state_change,
[
(store_trigger_param_1, "bject"),
(party_get_num_companion_stacks, ":num_stacks", "p_main_party"),
(try_for_range, ":slot_no", 0, ":num_stacks"),
(troop_slot_eq, "trp_temp_array_a", ":slot_no", "bject"),
(assign, "$g_cur_stack", ":slot_no"),
(assign, ":num_stacks", -1),
(start_presentation, "prsnt_upgrade_troops"),
(try_end),
(try_begin),
(gt, "$g_cur_stack", -1),
(assign, ":quantity", 1),
(try_begin),
(this_or_next|key_is_down, key_left_shift),
(this_or_next|key_is_down, key_right_shift),
(key_is_down, key_xbox_lbumber),
(assign, ":quantity", 5),
(else_try),
(this_or_next|key_is_down, key_left_control),
(this_or_next|key_is_down, key_right_control),
(key_is_down, key_xbox_rbumber),
(assign, ":quantity", 9999),
(try_end),
(val_min, ":quantity", "$g_talk_troop_met"),
(val_min, ":quantity", "$g_talk_troop_relation"),
(try_begin),
(this_or_next|key_is_down, key_xbox_dpad_right),
(this_or_next|key_is_down, key_xbox_dpad_left),
(this_or_next|eq, "bject", "$g_presentation_obj_2"),
(eq, "bject", "$g_presentation_obj_3"),
(gt, "$g_talk_troop", 0),
(try_begin),
(this_or_next|key_is_down, key_xbox_dpad_left),
(eq, "bject", "$g_presentation_obj_3"),
(troop_get_upgrade_troop, ":upgrade_troop", "$g_talk_troop", 1),
(else_try),
(this_or_next|key_is_down, key_xbox_dpad_right),
(eq, "bject", "$g_presentation_obj_2"),
(troop_get_upgrade_troop, ":upgrade_troop", "$g_talk_troop", 0),
(try_end),
(call_script, "script_game_get_join_cost", ":upgrade_troop"),
(assign, ":cost", reg0),
(gt, ":upgrade_troop", 0),
#gold check
(store_mul, ":gold", ":cost", ":quantity"),
(try_begin), #sufficient funds
(ge, "$g_talk_agent", ":gold"),
(val_sub, "$g_talk_agent", ":gold"),
(else_try),
(store_div, ":quantity", "$g_talk_agent", ":cost"),
(store_mul, ":gold", ":cost", ":quantity"),
(try_end),
(gt, ":quantity", 0),
(party_remove_members, "p_main_party", "$g_talk_troop", ":quantity"),
(troop_remove_gold, "trp_player", ":gold"),
(party_add_members, "p_main_party", ":upgrade_troop", ":quantity"),
(val_sub, "$g_talk_troop_relation", ":quantity"),
(party_set_slot, "$current_town", slot_center_has_academy, "$g_talk_troop_relation"),
#do stack reassignment
(party_stack_get_troop_id, ":troop", "p_main_party", "$g_cur_stack"),
(try_begin),
(neq, ":troop", "$g_talk_troop"), #if we don't have any of the cur stack remaining
(neq, ":troop", ":upgrade_troop"), #or if we haven't upgraded all of them at once
(party_get_num_companion_stacks, ":no_stacks", "p_main_party"),
(try_for_range, ":stacks", 1, ":no_stacks"),
(party_stack_get_troop_id, ":troop", "p_main_party", ":stacks"),
(eq, ":troop", ":upgrade_troop"), #since we already upgraded at least 1
(assign, "$g_cur_stack", ":stacks"),
(assign, ":no_stacks", -1),
(try_end),
(try_end),
(start_presentation, "prsnt_upgrade_troops"),
(else_try), #this can be expanded with
(eq, "bject", "$g_presentation_obj_6"), # troop note
(assign, "$g_presentation_next_presentation", "prsnt_upgrade_troops"),
(assign, "$temp", "$g_talk_troop"),
# (start_presentation, "prsnt_troop_note"),
(try_end),
(try_end),
(try_begin),
# (this_or_next|key_clicked, key_escape),
(this_or_next|le, "$g_talk_troop_relation", 1),
(eq, "bject", "$g_presentation_obj_10"),
#unset globals
(assign, "$g_talk_troop", -1),
(assign, "$g_talk_troop_relation", -1),
(assign, "$g_presentation_next_presentation", -1),
(assign, "$g_talk_troop_met", -1),
(play_sound, "snd_enemy_flag_taken"),
(presentation_set_duration, 0),
(try_end),
]),
(ti_on_presentation_run,
[
(party_get_num_companion_stacks, ":num_stacks", "p_main_party"),
(assign, ":cur_slots", "$g_cur_stack"),
(try_begin),
(this_or_next|key_clicked, key_escape),
(key_clicked, key_xbox_start),
(presentation_set_duration, 0),
(else_try),
(this_or_next|key_clicked, key_xbox_dpad_down),
(this_or_next|key_clicked, key_mouse_scroll_down),
(key_clicked, key_down),
(store_add, ":cur_slots", "$g_cur_stack", 1),
(try_begin),
(val_mod, ":cur_slots", ":num_stacks"),
(try_end),
(assign, ":dir", 1),
(else_try),
(this_or_next|key_clicked, key_xbox_dpad_up),
(this_or_next|key_clicked, key_mouse_scroll_up),
(key_clicked, key_up),
(store_sub, ":cur_slots", "$g_cur_stack", 1),
(try_begin),
(lt, ":cur_slots", 1),
(store_sub, ":cur_slots", ":num_stacks", 1),
(try_end),
(assign, ":dir", -1),
(try_end),
(try_begin), #do actual offset calcs - loopover already done previously
(neq, ":cur_slots", "$g_cur_stack"),
(assign, ":prev", 0),
(assign, ":next", ":num_stacks"),
(try_for_range, ":slot_no", ":prev", ":next"),
(neg|troop_slot_eq, "trp_temp_array_a", ":slot_no", -1),
(try_begin), #find previous
(le, ":slot_no", ":cur_slots"),
(assign, ":prev", ":slot_no"),
(try_end),
(try_begin),
(ge, ":slot_no", ":cur_slots"),
(assign, ":next", ":slot_no"),
(try_end),
(try_end),
(try_begin),
(eq, ":dir", 1),
(assign, "$g_cur_stack", ":next"),
(else_try),
(eq, ":dir", -1),
(assign, "$g_cur_stack", ":prev"),
(try_end),
(start_presentation, "prsnt_upgrade_troops"),
(try_end),
]),
]),
(ti_on_presentation_load,
[
(presentation_set_duration, 999999),
(set_fixed_point_multiplier, 1000),
## next presentation
(assign, "$g_presentation_next_presentation", -1),
(assign, "$g_talk_troop", -1),
(assign, "$g_talk_troop_met", -1),
(str_clear, s0),
(create_text_overlay, "$g_presentation_obj_1", s0, tf_scrollable),
(position_set_x, pos1, 510),
(position_set_y, pos1, 100),
(overlay_set_position, "$g_presentation_obj_1", pos1),
(position_set_x, pos1, 400),
(position_set_y, pos1, 600),
(overlay_set_area_size, "$g_presentation_obj_1", pos1),
(set_container_overlay, "$g_presentation_obj_1"),
(assign, ":pos_x", 150),
(party_get_num_companion_stacks, ":num_stacks", "p_main_party"),
(try_begin), #limit stack range to updated stacks
(val_clamp, "$g_cur_stack", -1, ":num_stacks"),
(party_stack_get_troop_id, ":troop_no", "p_main_party", "$g_cur_stack"),
(this_or_next|le, ":troop_no", 0),
(troop_is_hero, ":troop_no"),
(assign, "$g_cur_stack", -1),
(try_end),
(store_mul, ":pos_y", ":num_stacks", 40),
(val_sub, ":pos_y", 40),
(val_max, ":pos_y", 560),
(try_for_range, ":slot_no", 0, ":num_stacks"),
(party_stack_get_troop_id, ":troop_no", "p_main_party", ":slot_no"),
(troop_is_hero, ":troop_no"), #discard results from displaying
(troop_set_slot, "trp_temp_array_a", ":slot_no", -1),
(else_try),
(party_stack_get_size, ":stack_size", "p_main_party", ":slot_no"),
(party_stack_get_num_wounded, ":num_wounded", "p_main_party", ":slot_no"),
(str_store_troop_name, s1, ":troop_no"),
(assign, reg2, ":stack_size"),
(try_begin),
(gt, ":num_wounded", 0),
(store_sub, reg3, ":stack_size", ":num_wounded"),
(str_store_string, s1, "@{s1} ({reg3}/{reg2})"),
(else_try),
(str_store_string, s1, "@{s1} ({reg2})"),
(try_end),
(create_game_button_overlay, reg1, s1),
(position_set_x, pos1, ":pos_x"),
(position_set_y, pos1, ":pos_y"),
(overlay_set_position, reg1, pos1),
(position_set_x, pos1, 300),
(position_set_y, pos1, 32),
(overlay_set_size, reg1, pos1),
(troop_set_slot, "trp_temp_array_a", ":slot_no", reg1),
(val_sub, ":pos_y", 40),
(try_end),
(try_begin),
(gt, "$g_cur_stack", -1),
(troop_get_slot, ":dest_obj", "trp_temp_array_a", "$g_cur_stack"),
(gt, ":dest_obj", 0),
(overlay_set_alpha, ":dest_obj", 0x80),
(party_stack_get_troop_id, "$g_talk_troop", "p_main_party", "$g_cur_stack"),
(neg|troop_is_hero, "$g_talk_troop"),
(party_stack_get_size, "$g_talk_troop_met", "p_main_party", "$g_cur_stack"),
(party_stack_get_num_wounded, ":num_wounded", "p_main_party", "$g_cur_stack"),
(val_sub, "$g_talk_troop_met", ":num_wounded"),
(try_begin),
(gt, "$g_talk_troop_met", 0),
(store_faction_of_troop, ":color", "$g_talk_troop"),
(faction_get_color, ":color", ":color"),
(overlay_set_color, ":dest_obj", ":color"),
(else_try), #all wounded - cannot upgrade
(overlay_set_color, ":dest_obj", 0xFF0000),
(overlay_set_alpha, ":dest_obj", 0xFF),
(try_end),
(try_end),
(set_container_overlay, -1),
#availability description
(party_get_slot, "$g_talk_troop_relation", "$current_town", slot_center_has_academy),
(assign, reg1, "$g_talk_troop_relation"),
(faction_get_color, ":color", "$g_encountered_party_faction"),
(position_set_x, pos1, 275),
(position_set_y, pos1, 210),
(create_text_overlay, reg1, "@There are {reg1} upgrade available", tf_with_outline|tf_center_justify),
(overlay_set_position, reg1, pos1),
(overlay_set_color, reg1, ":color"),
(store_troop_gold, "$g_talk_agent", "trp_player"),
(try_begin),
(gt, "$g_talk_troop", 0),
(position_set_x, pos1, 275),
(try_begin),
(troop_get_upgrade_troop, ":upgrade_troop", "$g_talk_troop", 0),
(gt, ":upgrade_troop", 0),
(str_store_troop_name, s2, ":upgrade_troop"),
(create_button_overlay, "$g_presentation_obj_2", "@Upgrade to {s2}", tf_center_justify),
(call_script, "script_game_get_join_cost", ":upgrade_troop"),
(try_begin),
(lt, "$g_talk_agent", reg0),
(str_store_string, s1, "@Insufficient funds"),
(overlay_set_color, "$g_presentation_obj_2", 0xFF1111),
(else_try),
(call_script, "script_game_get_money_text", reg0),
(try_end),
(overlay_set_tooltip, "$g_presentation_obj_2", s1),
(position_set_y, pos1, 100),
(overlay_set_position, "$g_presentation_obj_2", pos1),
(try_end),
(try_begin),
(troop_get_upgrade_troop, ":upgrade_troop", "$g_talk_troop", 1),
(gt, ":upgrade_troop", 0),
(str_store_troop_name, s3, ":upgrade_troop"),
(create_button_overlay, "$g_presentation_obj_3", "@Promote to {s3}", tf_center_justify),
(call_script, "script_game_get_join_cost", ":upgrade_troop"),
(try_begin),
(lt, "$g_talk_agent", reg0),
(str_store_string, s1, "@Insufficient funds"),
(overlay_set_color, "$g_presentation_obj_3", 0xFF1111),
(else_try),
(call_script, "script_game_get_money_text", reg0),
(try_end),
(overlay_set_tooltip, "$g_presentation_obj_3", s1),
(position_set_y, pos1, 150),
(overlay_set_position, "$g_presentation_obj_3", pos1),
(try_end),
(try_end),
# cur troop
(try_begin),
(gt, "$g_cur_stack", -1),
(party_stack_get_troop_id, ":troop_no", "p_main_party", "$g_cur_stack"),
(store_mul, ":cur_troop", ":troop_no", 2), #with weapons
(create_image_button_overlay_with_tableau_material, "$g_presentation_obj_6", -1, "tableau_game_party_window", ":cur_troop"),
(position_set_x, pos1, 1750),
(position_set_y, pos1, 1750),
(overlay_set_size, "$g_presentation_obj_6", pos1),
(position_set_x, pos1, 50),
(position_set_y, pos1, 240),
(overlay_set_position, "$g_presentation_obj_6", pos1),
(else_try), #default, startup
(create_mesh_overlay, "$g_presentation_obj_6", "mesh_pic_mb_warrior_1"),
(position_set_x, pos1, -500),
(position_set_y, pos1, 250),
(overlay_set_position, "$g_presentation_obj_6", pos1),
# (overlay_set_display, "$g_presentation_obj_6", 0),
(display_message, "@Press Shift or Ctrl to upgrade up to 5 or all members"),
(try_end),
#gold overlay (image button so we can click on it)
(position_set_x, pos1, 500),
(position_set_y, pos1, 500),
(create_image_button_overlay, "$g_presentation_obj_10", "mesh_icon_gold", "mesh_icon_gold"),
(overlay_set_size, "$g_presentation_obj_10", pos1),
(position_set_x, pos1, 580),
(position_set_y, pos1, 40),
(overlay_set_position, "$g_presentation_obj_10", pos1),
(overlay_set_tooltip, "$g_presentation_obj_10", "@Click here or press ESC to finish recruiting"),
#gold display
(call_script, "script_game_get_money_text", "$g_talk_agent"),
(create_text_overlay, reg1, "@You have {s1}", tf_with_outline),
(position_set_x, pos1, 690),
(position_set_y, pos1, 60),
(overlay_set_position, reg1, pos1),
(overlay_set_color, reg1, 0xFFFFFF),
# done
# (create_game_button_overlay, "$g_presentation_obj_10", "str_done"),
# (position_set_x, pos1, 900),
# (position_set_y, pos1, 50),
# (overlay_set_position, "$g_presentation_obj_10", pos1),
]
),
(ti_on_presentation_event_state_change,
[
(store_trigger_param_1, "bject"),
(party_get_num_companion_stacks, ":num_stacks", "p_main_party"),
(try_for_range, ":slot_no", 0, ":num_stacks"),
(troop_slot_eq, "trp_temp_array_a", ":slot_no", "bject"),
(assign, "$g_cur_stack", ":slot_no"),
(assign, ":num_stacks", -1),
(start_presentation, "prsnt_upgrade_troops"),
(try_end),
(try_begin),
(gt, "$g_cur_stack", -1),
(assign, ":quantity", 1),
(try_begin),
(this_or_next|key_is_down, key_left_shift),
(this_or_next|key_is_down, key_right_shift),
(key_is_down, key_xbox_lbumber),
(assign, ":quantity", 5),
(else_try),
(this_or_next|key_is_down, key_left_control),
(this_or_next|key_is_down, key_right_control),
(key_is_down, key_xbox_rbumber),
(assign, ":quantity", 9999),
(try_end),
(val_min, ":quantity", "$g_talk_troop_met"),
(val_min, ":quantity", "$g_talk_troop_relation"),
(try_begin),
(this_or_next|key_is_down, key_xbox_dpad_right),
(this_or_next|key_is_down, key_xbox_dpad_left),
(this_or_next|eq, "bject", "$g_presentation_obj_2"),
(eq, "bject", "$g_presentation_obj_3"),
(gt, "$g_talk_troop", 0),
(try_begin),
(this_or_next|key_is_down, key_xbox_dpad_left),
(eq, "bject", "$g_presentation_obj_3"),
(troop_get_upgrade_troop, ":upgrade_troop", "$g_talk_troop", 1),
(else_try),
(this_or_next|key_is_down, key_xbox_dpad_right),
(eq, "bject", "$g_presentation_obj_2"),
(troop_get_upgrade_troop, ":upgrade_troop", "$g_talk_troop", 0),
(try_end),
(call_script, "script_game_get_join_cost", ":upgrade_troop"),
(assign, ":cost", reg0),
(gt, ":upgrade_troop", 0),
#gold check
(store_mul, ":gold", ":cost", ":quantity"),
(try_begin), #sufficient funds
(ge, "$g_talk_agent", ":gold"),
(val_sub, "$g_talk_agent", ":gold"),
(else_try),
(store_div, ":quantity", "$g_talk_agent", ":cost"),
(store_mul, ":gold", ":cost", ":quantity"),
(try_end),
(gt, ":quantity", 0),
(party_remove_members, "p_main_party", "$g_talk_troop", ":quantity"),
(troop_remove_gold, "trp_player", ":gold"),
(party_add_members, "p_main_party", ":upgrade_troop", ":quantity"),
(val_sub, "$g_talk_troop_relation", ":quantity"),
(party_set_slot, "$current_town", slot_center_has_academy, "$g_talk_troop_relation"),
#do stack reassignment
(party_stack_get_troop_id, ":troop", "p_main_party", "$g_cur_stack"),
(try_begin),
(neq, ":troop", "$g_talk_troop"), #if we don't have any of the cur stack remaining
(neq, ":troop", ":upgrade_troop"), #or if we haven't upgraded all of them at once
(party_get_num_companion_stacks, ":no_stacks", "p_main_party"),
(try_for_range, ":stacks", 1, ":no_stacks"),
(party_stack_get_troop_id, ":troop", "p_main_party", ":stacks"),
(eq, ":troop", ":upgrade_troop"), #since we already upgraded at least 1
(assign, "$g_cur_stack", ":stacks"),
(assign, ":no_stacks", -1),
(try_end),
(try_end),
(start_presentation, "prsnt_upgrade_troops"),
(else_try), #this can be expanded with
(eq, "bject", "$g_presentation_obj_6"), # troop note
(assign, "$g_presentation_next_presentation", "prsnt_upgrade_troops"),
(assign, "$temp", "$g_talk_troop"),
# (start_presentation, "prsnt_troop_note"),
(try_end),
(try_end),
(try_begin),
# (this_or_next|key_clicked, key_escape),
(this_or_next|le, "$g_talk_troop_relation", 1),
(eq, "bject", "$g_presentation_obj_10"),
#unset globals
(assign, "$g_talk_troop", -1),
(assign, "$g_talk_troop_relation", -1),
(assign, "$g_presentation_next_presentation", -1),
(assign, "$g_talk_troop_met", -1),
(play_sound, "snd_enemy_flag_taken"),
(presentation_set_duration, 0),
(try_end),
]),
(ti_on_presentation_run,
[
(party_get_num_companion_stacks, ":num_stacks", "p_main_party"),
(assign, ":cur_slots", "$g_cur_stack"),
(try_begin),
(this_or_next|key_clicked, key_escape),
(key_clicked, key_xbox_start),
(presentation_set_duration, 0),
(else_try),
(this_or_next|key_clicked, key_xbox_dpad_down),
(this_or_next|key_clicked, key_mouse_scroll_down),
(key_clicked, key_down),
(store_add, ":cur_slots", "$g_cur_stack", 1),
(try_begin),
(val_mod, ":cur_slots", ":num_stacks"),
(try_end),
(assign, ":dir", 1),
(else_try),
(this_or_next|key_clicked, key_xbox_dpad_up),
(this_or_next|key_clicked, key_mouse_scroll_up),
(key_clicked, key_up),
(store_sub, ":cur_slots", "$g_cur_stack", 1),
(try_begin),
(lt, ":cur_slots", 1),
(store_sub, ":cur_slots", ":num_stacks", 1),
(try_end),
(assign, ":dir", -1),
(try_end),
(try_begin), #do actual offset calcs - loopover already done previously
(neq, ":cur_slots", "$g_cur_stack"),
(assign, ":prev", 0),
(assign, ":next", ":num_stacks"),
(try_for_range, ":slot_no", ":prev", ":next"),
(neg|troop_slot_eq, "trp_temp_array_a", ":slot_no", -1),
(try_begin), #find previous
(le, ":slot_no", ":cur_slots"),
(assign, ":prev", ":slot_no"),
(try_end),
(try_begin),
(ge, ":slot_no", ":cur_slots"),
(assign, ":next", ":slot_no"),
(try_end),
(try_end),
(try_begin),
(eq, ":dir", 1),
(assign, "$g_cur_stack", ":next"),
(else_try),
(eq, ":dir", -1),
(assign, "$g_cur_stack", ":prev"),
(try_end),
(start_presentation, "prsnt_upgrade_troops"),
(try_end),
]),
]),
This mesh used for the background requires a planar mesh and a duplicate material with the following settings - otherwise you get psychedelic transparency issues.
Code:
("face_gen_window", 0, "upgrade_window", 0, 0, 0, 0, 0, 0, 1, 1, 1),
("icon_gold", 0, "mp_ico_gold", 0, 0, 0, 0, 0, 0, 1, 1, 1),
To access the presentation drop this in the appropriate menu (the recommended being the default town in which buildings are probably present)
Code:
("town_upgrade",
[
(party_get_slot, reg12, "$current_town", slot_center_has_academy),
(is_between, "$g_encountered_party_faction", kingdoms_begin, kingdoms_end),
(ge, reg12, 1), #this value is used later
(eq, "$g_encountered_party_faction", "$players_kingdom"),
(this_or_next|party_slot_eq, "$current_town", slot_town_lord, "trp_player"),
(faction_slot_eq, "$players_kingdom", slot_faction_marshall, "trp_player"),
],"Enlist troops in the military academy ({reg12} available).",
[
(assign, "$g_cur_stack", -1),
(start_presentation, "prsnt_upgrade_troops"),
]),
Credits for the original party stack interface go to rubik's Custom Commander - "Sort the Defender" presentation.