diff --git a/code/__DEFINES/dropships.dm b/code/__DEFINES/dropships.dm
index f7df570a28..d53e7c68d8 100644
--- a/code/__DEFINES/dropships.dm
+++ b/code/__DEFINES/dropships.dm
@@ -10,3 +10,8 @@
#define DROPSHIP_MIN_AUTO_DELAY 10 SECONDS
#define DROPSHIP_AUTO_RETRY_COOLDOWN 20 SECONDS
#define DROPSHIP_MEDEVAC_COOLDOWN 20 SECONDS
+
+//Hatches states
+#define SHUTTLE_DOOR_BROKEN -1
+#define SHUTTLE_DOOR_UNLOCKED 0
+#define SHUTTLE_DOOR_LOCKED 1
diff --git a/code/datums/entities/player.dm b/code/datums/entities/player.dm
index 00c76d7b95..ddb52cb8d0 100644
--- a/code/datums/entities/player.dm
+++ b/code/datums/entities/player.dm
@@ -469,6 +469,7 @@ BSQL_PROTECT_DATUM(/datum/entity/player)
set waitfor=0
WAIT_DB_READY
load_player_data_info(get_player_from_key(ckey))
+ check_discord_link()
/client/proc/load_player_data_info(datum/entity/player/player)
if(ckey != player.ckey)
@@ -482,6 +483,25 @@ BSQL_PROTECT_DATUM(/datum/entity/player)
record_login_triplet(player.ckey, address, computer_id)
player_data.sync()
+/client/proc/check_discord_link()
+ var/datum/view_record/discord_link/current_link = locate() in DB_VIEW(/datum/view_record/discord_link, DB_COMP("player_id", DB_EQUALS, player_data.id))
+
+ if(!current_link)
+
+ if(player_data.discord_link_id != null)
+ player_data.discord_link_id = null
+ player_data.save()
+ player_data.sync()
+
+ return
+
+ if(player_data.discord_link_id == current_link.id)
+ return
+
+ player_data.discord_link_id = current_link.id
+ player_data.save()
+ player_data.sync()
+
/datum/entity/player/proc/check_ban(computer_id, address, is_telemetry)
. = list()
diff --git a/code/datums/skills/uscm.dm b/code/datums/skills/uscm.dm
index 871278ff23..2da19793e5 100644
--- a/code/datums/skills/uscm.dm
+++ b/code/datums/skills/uscm.dm
@@ -287,7 +287,7 @@ COMMAND STAFF
SKILL_OVERWATCH = SKILL_OVERWATCH_TRAINED,
SKILL_MEDICAL = SKILL_MEDICAL_MEDIC,
SKILL_POLICE = SKILL_POLICE_FLASH,
- SKILL_VEHICLE = SKILL_VEHICLE_SMALL,
+ SKILL_VEHICLE = SKILL_VEHICLE_LARGE,
SKILL_JTAC = SKILL_JTAC_EXPERT,
SKILL_INTEL = SKILL_INTEL_TRAINED,
SKILL_SURGERY = SKILL_SURGERY_NOVICE,
diff --git a/code/game/jobs/job/command/cic/staffofficer.dm b/code/game/jobs/job/command/cic/staffofficer.dm
index 9f7d1d09bf..8e4e7c0cfa 100644
--- a/code/game/jobs/job/command/cic/staffofficer.dm
+++ b/code/game/jobs/job/command/cic/staffofficer.dm
@@ -11,7 +11,7 @@
flags_startup_parameters = ROLE_ADD_TO_DEFAULT
gear_preset = /datum/equipment_preset/uscm_ship/so
gear_preset_secondary = /datum/equipment_preset/uscm_ship/so/lesser_rank
- entry_message_body = "Your job is to monitor the Marines, man the CIC, and listen to your superior officers. You are in charge of logistics and the overwatch system. You are also in line to take command after other eligible superior commissioned officers."
+ entry_message_body = "Your job is to conduct the briefing for the platoon, monitor the operation, and listen to your superior officers. You are in charge of the platoon for the current operation and supported by your Company Command.
They will give your orders VIA the telephone in your office once they are ready.
You remember that you've stored your personal gear are located in your personal quarters.
Your job involves heavy roleplay and requires you to behave like an officer and to stay in character at all times."
job_options = list(FIRST_LT_VARIANT = "1stLt", SECOND_LT_VARIANT = "2ndLt")
@@ -52,6 +52,7 @@ AddTimelock(/datum/job/command/bridge, list(
/datum/job/command/bridge/ai
total_positions = 1
spawn_positions = 1
+ prime_priority = TRUE
/datum/job/command/bridge/ai/set_spawn_positions(count)
return spawn_positions
diff --git a/code/game/jobs/job/job.dm b/code/game/jobs/job/job.dm
index 34671be60f..103c826ce5 100644
--- a/code/game/jobs/job/job.dm
+++ b/code/game/jobs/job/job.dm
@@ -41,6 +41,9 @@
/// If TRUE, this job will spawn w/ a cryo emergency kit during evac/red alert
var/gets_emergency_kit = TRUE
+ /// Whether or not linking your discord account can let you get prime priority for this role
+ var/prime_priority = FALSE
+
/datum/job/New()
. = ..()
diff --git a/code/game/jobs/job/marine/marine.dm b/code/game/jobs/job/marine/marine.dm
index e07c1edd31..c50a0420a9 100644
--- a/code/game/jobs/job/marine/marine.dm
+++ b/code/game/jobs/job/marine/marine.dm
@@ -1,5 +1,5 @@
/datum/job/marine
- supervisors = "the acting squad leader"
+ supervisors = "the acting platoon leader"
selection_class = "job_marine"
total_positions = 8
spawn_positions = 8
@@ -7,7 +7,7 @@
/datum/job/marine/generate_entry_message(mob/living/carbon/human/current_human)
if(current_human.assigned_squad)
- entry_message_intro = "You are a [title]!
You have been assigned to: [lowertext(current_human.assigned_squad.name)] squad.[Check_WO() ? "" : " Make your way to the cafeteria for some post-cryosleep chow, and then get equipped in your squad's prep room." ]"
+ entry_message_intro = "You are a [title]!
You have been assigned to the [lowertext(current_human.assigned_squad.name)] platoon.[Check_WO() ? "" : " Make your way to the cafeteria for some post-cryosleep chow, and then get equipped in your team's prep room." ]"
return ..()
/datum/job/marine/generate_entry_conditions(mob/living/carbon/human/current_human)
diff --git a/code/game/jobs/job/marine/squad/leader.dm b/code/game/jobs/job/marine/squad/leader.dm
index 24233c95d5..ebb0cd25a9 100644
--- a/code/game/jobs/job/marine/squad/leader.dm
+++ b/code/game/jobs/job/marine/squad/leader.dm
@@ -10,7 +10,7 @@
flags_startup_parameters = ROLE_ADD_TO_DEFAULT|ROLE_ADD_TO_SQUAD
gear_preset = /datum/equipment_preset/uscm/leader
gear_preset_secondary = /datum/equipment_preset/uscm/leader/lesser_rank
- entry_message_body = "You are responsible for the men and women of your squad. Make sure they are on task, working together, and communicating. You are also in charge of communicating with command and letting them know about the situation first hand. Keep out of harm's way."
+ entry_message_body = "You are responsible for the men and women of your entire platoon. Make sure they are on task, working together, and communicating. You are also in charge of communicating with command and letting them know about the situation first hand. Keep out of harm's way.
You remember that you've stored your personal gear and uniform are located in the dorm or locker rooms."
job_options = list(GYSGT_VARIANT = "GYSGT", SSGT_VARIANT = "SSGT")
@@ -53,6 +53,7 @@ AddTimelock(/datum/job/marine/leader, list(
/datum/job/marine/leader/ai
total_positions = 1
spawn_positions = 1
+ prime_priority = TRUE
/datum/job/marine/leader/ai/upp
title = JOB_SQUAD_LEADER_UPP
diff --git a/code/game/jobs/job/marine/squad/medic.dm b/code/game/jobs/job/marine/squad/medic.dm
index 0b6f9f0702..02b438c048 100644
--- a/code/game/jobs/job/marine/squad/medic.dm
+++ b/code/game/jobs/job/marine/squad/medic.dm
@@ -10,7 +10,7 @@
flags_startup_parameters = ROLE_ADD_TO_DEFAULT|ROLE_ADD_TO_SQUAD
gear_preset = /datum/equipment_preset/uscm/medic
gear_preset_secondary = /datum/equipment_preset/uscm/medic/lesser_rank
- entry_message_body = "You tend the wounds of your squad mates and make sure they are healthy and active. You may not be a fully-fledged doctor, but you stand between life and death when it matters."
+ entry_message_body = "You tend the wounds of your squad mates and make sure they are healthy and active. You may not be a fully-fledged doctor, but you stand between life and death when it matters.
You remember that you've stored your personal gear and uniform are located in your medical office."
job_options = list(CPL_VARIANT = "CPL", LCPL_VARIANT = "LCPL")
diff --git a/code/game/jobs/job/marine/squad/smartgunner.dm b/code/game/jobs/job/marine/squad/smartgunner.dm
index e10724355c..6c27f5ec27 100644
--- a/code/game/jobs/job/marine/squad/smartgunner.dm
+++ b/code/game/jobs/job/marine/squad/smartgunner.dm
@@ -11,7 +11,7 @@
flags_startup_parameters = ROLE_ADD_TO_DEFAULT|ROLE_ADD_TO_SQUAD
gear_preset = /datum/equipment_preset/uscm/sg
gear_preset_secondary = /datum/equipment_preset/uscm/sg/lesser_rank
- entry_message_body = "You are the smartgunner. Your task is to provide heavy weapons support."
+ entry_message_body = "You are a specialized automatic rifleman. Your task is to provide heavy weapons support for your squad.
You remember that you've stored your personal gear and uniform are located in the dorm or locker rooms."
job_options = list(CPL_VARIANT = "CPL", LCPL_VARIANT = "LCPL")
diff --git a/code/game/jobs/job/marine/squad/standard.dm b/code/game/jobs/job/marine/squad/standard.dm
index 0269366bbf..71533679d9 100644
--- a/code/game/jobs/job/marine/squad/standard.dm
+++ b/code/game/jobs/job/marine/squad/standard.dm
@@ -13,7 +13,7 @@
job_options = list(PFC_VARIANT = "PFC", PVT_VARIANT = "PVT")
/datum/job/marine/standard/on_config_load()
- entry_message_body = "You are a rank-and-file Marine of the USCM, and that is your strength. What you lack alone, you gain standing shoulder to shoulder with the men and women of the corps. Ooh-rah!"
+ entry_message_body = "You are a rank-and-file Soldier of your standing army, and that is your strength. What you lack alone, you gain standing shoulder to shoulder with the men and women of the platoon. Ooh-rah!
You remember that you've stored your personal gear and uniform are located in the dorm or locker rooms."
return ..()
/datum/job/marine/standard/set_spawn_positions(count)
diff --git a/code/game/jobs/job/marine/squad/tl.dm b/code/game/jobs/job/marine/squad/tl.dm
index 987c5d58d8..be876dc0b3 100644
--- a/code/game/jobs/job/marine/squad/tl.dm
+++ b/code/game/jobs/job/marine/squad/tl.dm
@@ -8,7 +8,7 @@
allow_additional = 1
flags_startup_parameters = ROLE_ADD_TO_DEFAULT|ROLE_ADD_TO_SQUAD
gear_preset = /datum/equipment_preset/uscm/tl
- entry_message_body = "You are the Team Leader.Your task is to assist the squad leader in leading the squad as well as utilize ordnance such as orbital bombardments, CAS, and mortar as well as coordinating resupply with Requisitions and CIC. If the squad leader dies, you are expected to lead in their place."
+ entry_message_body = "You are the Squad Leader. Your task is leading the designated squad and utilize available ordnance. If the platoon leader dies, you are expected to lead in their place.
You remember that you've stored your personal gear and uniform are located in the dorm or locker rooms."
job_options = list(SGT_VARIANT = "SGT")
diff --git a/code/game/jobs/role_authority.dm b/code/game/jobs/role_authority.dm
index a50e25ae9e..42ffc22570 100644
--- a/code/game/jobs/role_authority.dm
+++ b/code/game/jobs/role_authority.dm
@@ -18,9 +18,10 @@ var/global/datum/authority/branch/role/RoleAuthority
#define RETURN_TO_LOBBY 2
#define NEVER_PRIORITY 0
-#define HIGH_PRIORITY 1
-#define MED_PRIORITY 2
-#define LOW_PRIORITY 3
+#define PRIME_PRIORITY 1
+#define HIGH_PRIORITY 2
+#define MED_PRIORITY 3
+#define LOW_PRIORITY 4
#define SHIPSIDE_ROLE_WEIGHT 0.25
@@ -245,37 +246,19 @@ I hope it's easier to tell what the heck this proc is even doing, unlike previou
if(!length(roles_to_assign) || !length(unassigned_players))
return
+ log_debug("ASSIGNMENT: Starting prime priority assignments.")
+ for(var/mob/new_player/cycled_unassigned in shuffle(unassigned_players))
+ assign_role_to_player_by_priority(cycled_unassigned, roles_to_assign, unassigned_players, PRIME_PRIORITY)
+
+ log_debug("ASSIGNMENT: Starting regular priority assignments.")
for(var/mob/new_player/cycled_unassigned in shuffle(unassigned_players))
var/player_assigned_job = FALSE
- log_debug("ASSIGNMENT: We have started assigning for [cycled_unassigned].")
for(var/priority in HIGH_PRIORITY to LOW_PRIORITY)
- var/wanted_jobs_by_name = shuffle(cycled_unassigned.client?.prefs?.get_jobs_by_priority(priority))
- log_debug("ASSIGNMENT: We have started cycled through priority [priority] for [cycled_unassigned].")
-
- for(var/job_name in wanted_jobs_by_name)
- log_debug("ASSIGNMENT: We are cycling through wanted jobs and are at [job_name] for [cycled_unassigned].")
- if(job_name in roles_to_assign)
- log_debug("ASSIGNMENT: We have found [job_name] in roles to assign for [cycled_unassigned].")
- var/datum/job/actual_job = roles_to_assign[job_name]
-
- if(assign_role(cycled_unassigned, actual_job))
- log_debug("ASSIGNMENT: We have assigned [job_name] to [cycled_unassigned].")
- unassigned_players -= cycled_unassigned
-
- if(actual_job.spawn_positions != -1 && actual_job.current_positions >= actual_job.spawn_positions)
- roles_to_assign -= job_name
- log_debug("ASSIGNMENT: We have ran out of slots for [job_name] and it has been removed from roles to assign.")
-
- player_assigned_job = TRUE
- break
-
+ player_assigned_job = assign_role_to_player_by_priority(cycled_unassigned, roles_to_assign, unassigned_players, priority)
if(player_assigned_job)
- log_debug("ASSIGNMENT: [cycled_unassigned] has been assigned a job and we are breaking.")
break
- log_debug("ASSIGNMENT: [cycled_unassigned] did not get a job at priority [priority], moving to next priority level.")
-
if(!length(roles_to_assign))
log_debug("ASSIGNMENT: No more roles to assign, breaking.")
break
@@ -321,10 +304,39 @@ I hope it's easier to tell what the heck this proc is even doing, unlike previou
log_debug("ASSIGNMENT: [cycled_unassigned] has opted for return to lobby alternate option.")
cycled_unassigned.ready = 0
- log_debug("ASSIGNMENT: Assigning complete. Players unassigned: [length(unassigned_players)] Jobs unassigned: [length(roles_to_assign)]")
+ log_debug("ASSIGNMENT: Assignment complete. Players unassigned: [length(unassigned_players)] Jobs unassigned: [length(roles_to_assign)]")
return roles_to_assign
+/datum/authority/branch/role/proc/assign_role_to_player_by_priority(mob/new_player/cycled_unassigned, list/roles_to_assign, list/unassigned_players, priority)
+ log_debug("ASSIGNMENT: We have started cycled through priority [priority] for [cycled_unassigned].")
+ var/wanted_jobs_by_name = shuffle(cycled_unassigned.client?.prefs?.get_jobs_by_priority(priority))
+ var/player_assigned_job = FALSE
+
+ for(var/job_name in wanted_jobs_by_name)
+ log_debug("ASSIGNMENT: We are cycling through wanted jobs and are at [job_name] for [cycled_unassigned].")
+ if(job_name in roles_to_assign)
+ log_debug("ASSIGNMENT: We have found [job_name] in roles to assign for [cycled_unassigned].")
+ var/datum/job/actual_job = roles_to_assign[job_name]
+
+ if(assign_role(cycled_unassigned, actual_job))
+ log_debug("ASSIGNMENT: We have assigned [job_name] to [cycled_unassigned].")
+ unassigned_players -= cycled_unassigned
+
+ if(actual_job.spawn_positions != -1 && actual_job.current_positions >= actual_job.spawn_positions)
+ roles_to_assign -= job_name
+ log_debug("ASSIGNMENT: We have ran out of slots for [job_name] and it has been removed from roles to assign.")
+
+ player_assigned_job = TRUE
+ break
+
+ if(player_assigned_job)
+ log_debug("ASSIGNMENT: [cycled_unassigned] has been assigned a job.")
+ return player_assigned_job
+
+ log_debug("ASSIGNMENT: [cycled_unassigned] did not get a job at priority [priority].")
+ return player_assigned_job
+
/**
* Calculate role balance weight for one person joining as that role. This weight is used
* when calculating the number of xenos both roundstart and burrowed larva they get for
diff --git a/code/game/machinery/door_control.dm b/code/game/machinery/door_control.dm
index 8b73588f1d..5d6c66309d 100644
--- a/code/game/machinery/door_control.dm
+++ b/code/game/machinery/door_control.dm
@@ -64,7 +64,7 @@
if(is_mainship_level(z)) // on the almayer
return
- shuttle.control_doors("lock", "all", force=FALSE)
+ shuttle.control_doors("force-lock", "all", force=FALSE)
/obj/structure/machinery/door_control/proc/handle_door()
for(var/obj/structure/machinery/door/airlock/D in range(range))
diff --git a/code/game/machinery/doors/airlock_control.dm b/code/game/machinery/doors/airlock_control.dm
index 57e27cc60d..b20a052d26 100644
--- a/code/game/machinery/doors/airlock_control.dm
+++ b/code/game/machinery/doors/airlock_control.dm
@@ -123,15 +123,15 @@
radio_connection.post_signal(src, signal, range = AIRLOCK_CONTROL_RANGE, filter = RADIO_AIRLOCK)
-/obj/structure/machinery/door/airlock/open(surpress_send)
+/obj/structure/machinery/door/airlock/open(forced)
. = ..()
- if(!surpress_send) send_status()
+ if(!forced)
+ send_status()
-
-/obj/structure/machinery/door/airlock/close(surpress_send)
+/obj/structure/machinery/door/airlock/close(forced)
. = ..()
- if(!surpress_send) send_status()
-
+ if(!forced)
+ send_status()
/obj/structure/machinery/door/airlock/proc/set_frequency(new_frequency)
SSradio.remove_object(src, frequency)
diff --git a/code/game/machinery/doors/door.dm b/code/game/machinery/doors/door.dm
index 99353a6688..2e79604e87 100644
--- a/code/game/machinery/doors/door.dm
+++ b/code/game/machinery/doors/door.dm
@@ -214,7 +214,7 @@
flick("door_deny", src)
return
-/obj/structure/machinery/door/proc/open(forced=0)
+/obj/structure/machinery/door/proc/open(forced)
if(!density)
return TRUE
if(operating || !loc)
diff --git a/code/game/machinery/doors/multi_tile.dm b/code/game/machinery/doors/multi_tile.dm
index cddcfae08c..c60c08dc03 100644
--- a/code/game/machinery/doors/multi_tile.dm
+++ b/code/game/machinery/doors/multi_tile.dm
@@ -241,10 +241,42 @@
no_panel = 1
not_weldable = 1
var/queen_pryable = TRUE
+ var/obj/docking_port/mobile/marine_dropship/linked_dropship
/obj/structure/machinery/door/airlock/multi_tile/almayer/dropshiprear/ex_act(severity)
return
+/obj/structure/machinery/door/airlock/multi_tile/almayer/dropshiprear/attackby(obj/item/item, mob/user)
+ if(HAS_TRAIT(item, TRAIT_TOOL_MULTITOOL))
+ var/direction
+ switch(id)
+ if("starboard_door")
+ direction = "starboard"
+ if("port_door")
+ direction = "port"
+ if("aft_door")
+ direction = "aft"
+ if(!linked_dropship || !linked_dropship.door_control.door_controllers[direction])
+ return ..()
+ var/datum/door_controller/single/control = linked_dropship.door_control.door_controllers[direction]
+ if (control.status != SHUTTLE_DOOR_BROKEN)
+ return ..()
+ if(!skillcheck(user, SKILL_ENGINEER, SKILL_ENGINEER_ENGI))
+ to_chat(user, SPAN_WARNING("You don't seem to understand how to restore a remote connection to [src]."))
+ return
+ if(user.action_busy)
+ return
+
+ to_chat(user, SPAN_WARNING("You begin to restore the remote connection to [src]."))
+ if(!do_after(user, 5 SECONDS, INTERRUPT_ALL, BUSY_ICON_BUILD))
+ to_chat(user, SPAN_WARNING("You fail to restore a remote connection to [src]."))
+ return
+ unlock(TRUE)
+ close(FALSE)
+ control.status = SHUTTLE_DOOR_UNLOCKED
+ to_chat(user, SPAN_WARNING("You successfully restored the remote connection to [src]."))
+ return
+ ..()
/obj/structure/machinery/door/airlock/multi_tile/almayer/dropshiprear/unlock()
if(is_reserved_level(z))
@@ -258,13 +290,32 @@
if(!queen_pryable)
return ..()
- if(!locked)
- return ..()
-
- to_chat(xeno, SPAN_NOTICE("You try and force the doors open"))
+ if(xeno.action_busy)
+ return
+
+ var/direction
+ switch(id)
+ if("starboard_door")
+ direction = "starboard"
+ if("port_door")
+ direction = "port"
+ if("aft_door")
+ direction = "aft"
+ var/datum/door_controller/single/control
+ if(linked_dropship && linked_dropship.door_control.door_controllers[direction])
+ control = linked_dropship.door_control.door_controllers[direction]
+
+ if(control && control.status == SHUTTLE_DOOR_BROKEN)
+ to_chat(xeno, SPAN_NOTICE("The door is already disabled."))
+ return
+
+ to_chat(xeno, SPAN_WARNING("You try and force the doors open!"))
if(do_after(xeno, 3 SECONDS, INTERRUPT_ALL, BUSY_ICON_HOSTILE))
+ if(control)
+ control.status = SHUTTLE_DOOR_BROKEN
unlock(TRUE)
open(1)
+ open(TRUE)
lock(TRUE)
/obj/structure/machinery/door/airlock/multi_tile/almayer/dropshiprear/ds1
@@ -275,6 +326,23 @@
name = "\improper Normandy cargo door"
icon = 'icons/obj/structures/doors/dropship2_cargo.dmi'
+/obj/structure/machinery/door/airlock/multi_tile/almayer/dropshiprear/dropshipside
+ width = 2
+
+/obj/structure/machinery/door/airlock/multi_tile/almayer/dropshiprear/dropshipside/ds1
+ name = "\improper Alamo crew hatch"
+ icon = 'icons/obj/structures/doors/dropship1_side2.dmi'
+
+/obj/structure/machinery/door/airlock/multi_tile/almayer/dropshiprear/dropshipside/ds1/midway
+ name = "\improper Midway crew hatch"
+
+/obj/structure/machinery/door/airlock/multi_tile/almayer/dropshiprear/dropshipside/ds2
+ name = "\improper Normandy crew hatch"
+ icon = 'icons/obj/structures/doors/dropship2_side2.dmi'
+
+/obj/structure/machinery/door/airlock/multi_tile/almayer/dropshiprear/dropshipside/ds2/cyclone
+ name = "\improper Cyclone crew hatch"
+
/obj/structure/machinery/door/airlock/multi_tile/almayer/dropshiprear/upp
name = "\improper Akademia Nauk cargo door"
icon = 'icons/obj/structures/doors/dropshipupp_cargo.dmi'
@@ -329,7 +397,7 @@
continue
INVOKE_ASYNC(atom_movable, TYPE_PROC_REF(/atom/movable, throw_atom), projected, 1, SPEED_FAST, null, FALSE)
-/obj/structure/machinery/door/airlock/multi_tile/almayer/dropshiprear/lifeboat/connect_to_shuttle(obj/docking_port/mobile/port, obj/docking_port/stationary/dock, idnum, override)
+/obj/structure/machinery/door/airlock/multi_tile/almayer/dropshiprear/lifeboat/connect_to_shuttle(mapload, obj/docking_port/mobile/port, obj/docking_port/stationary/dock)
. = ..()
if(istype(port, /obj/docking_port/mobile/crashable/lifeboat))
var/obj/docking_port/mobile/crashable/lifeboat/lifeboat = port
diff --git a/code/game/machinery/vending/vendor_types/squad_prep/squad_prep.dm b/code/game/machinery/vending/vendor_types/squad_prep/squad_prep.dm
index 60150ec777..42aa2e13b8 100644
--- a/code/game/machinery/vending/vendor_types/squad_prep/squad_prep.dm
+++ b/code/game/machinery/vending/vendor_types/squad_prep/squad_prep.dm
@@ -95,7 +95,9 @@
list("BACKPACK", -1, null, null, null),
list("Lightweight IMP Backpack", round(scale * 15), /obj/item/storage/backpack/marine, VENDOR_ITEM_REGULAR),
+ list("USCM Technician Backpack", round(scale * 15), /obj/item/storage/backpack/marine/tech, VENDOR_ITEM_REGULAR),
list("USCM Satchel", round(scale * 15), /obj/item/storage/backpack/marine/satchel, VENDOR_ITEM_REGULAR),
+ list("Technician Chestrig", round(scale * 15), /obj/item/storage/backpack/marine/satchel/tech, VENDOR_ITEM_REGULAR),
list("Shotgun Scabbard", round(scale * 5), /obj/item/storage/large_holster/m37, VENDOR_ITEM_REGULAR),
list("RESTRICTED BACKPACKS", -1, null, null),
diff --git a/code/game/objects/structures/gun_rack.dm b/code/game/objects/structures/gun_rack.dm
index ac32b0162d..400002fa35 100644
--- a/code/game/objects/structures/gun_rack.dm
+++ b/code/game/objects/structures/gun_rack.dm
@@ -54,3 +54,24 @@
max_stored = 6
initial_stored = 6
allowed_type = /obj/item/weapon/gun/rifle/type71
+
+/obj/structure/gun_rack/apc
+ name = "APC ammo compartment"
+ icon_state = "frontal"
+ desc = "Uhoh. You shouldn't be seeing this."
+
+/obj/structure/gun_rack/apc/frontal
+ name = "frontal cannon ammo storage compartment"
+ icon_state = "frontal"
+ desc = "A small compartment that stores ammunition for the APC's 'Bleihagel RE-RE700 Frontal Cannon'."
+ max_stored = 2
+ initial_stored = 0
+ allowed_type = /obj/item/ammo_magazine/hardpoint/m56_cupola/frontal_cannon
+
+/obj/structure/gun_rack/apc/boyars
+ name = "dual cannon ammo storage compartment"
+ icon_state = "boyars"
+ desc = "A small compartment that stores ammunition for the APC's 'PARS-159 Boyars Dualcannon'."
+ max_stored = 2
+ initial_stored = 0
+ allowed_type = /obj/item/ammo_magazine/hardpoint/boyars_dualcannon
diff --git a/code/game/objects/structures/tables_racks.dm b/code/game/objects/structures/tables_racks.dm
index 8d6441293f..c059301467 100644
--- a/code/game/objects/structures/tables_racks.dm
+++ b/code/game/objects/structures/tables_racks.dm
@@ -622,6 +622,23 @@
icon_state = "clothtable"
table_prefix = "cloth"
+/obj/structure/surface/table/reinforced/toc
+ name = "operations table"
+ desc = "A square metal surface resting on its fat metal bottom. You can't flip something that doesn't have legs."
+ icon_state = "tocWtable"
+ table_prefix = "toc"
+
+/obj/structure/surface/table/reinforced/toc/update_icon()
+ return
+
+/obj/structure/surface/table/reinforced/toc/west
+ desc = "A square metal surface resting on its fat metal bottom. You can't flip something that doesn't have legs."
+ icon_state = "tocWtable"
+
+/obj/structure/surface/table/reinforced/toc/east
+ desc = "A square metal surface resting on its fat metal bottom. You can't flip something that doesn't have legs."
+ icon_state = "tocEtable"
+
/*
* Racks
*/
diff --git a/code/modules/almayer/machinery.dm b/code/modules/almayer/machinery.dm
index 4c29fe9d5f..9491475ace 100644
--- a/code/modules/almayer/machinery.dm
+++ b/code/modules/almayer/machinery.dm
@@ -113,6 +113,11 @@
minimap_type = MINIMAP_FLAG_PMC
faction = FACTION_PMC
+/obj/structure/machinery/prop/almayer/CICmap/toc
+ name = "tactical map screen"
+ desc = "A screen on the TOC computer displaying the tactical map."
+ icon_state = "toc_map"
+
//Nonpower using props
/obj/structure/prop/almayer
diff --git a/code/modules/client/preferences.dm b/code/modules/client/preferences.dm
index 16b88e6293..262ae11219 100644
--- a/code/modules/client/preferences.dm
+++ b/code/modules/client/preferences.dm
@@ -648,10 +648,14 @@ var/const/MAX_SAVE_SLOTS = 10
//splitJobs - Allows you split the table by job. You can make different tables for each department by including their heads. Defaults to CE to make it look nice.
//width - Screen' width.
//height - Screen's height.
-/datum/preferences/proc/SetChoices(mob/user, limit = 19, list/splitJobs = list(JOB_CHIEF_REQUISITION), width = 450, height = 450)
+/datum/preferences/proc/SetChoices(mob/user, limit = 19, list/splitJobs = list(JOB_CHIEF_REQUISITION), width = 480, height = 450)
if(!RoleAuthority)
return
+ var/host_bypass = FALSE
+ if(user.client?.admin_holder?.check_for_rights(R_HOST))
+ host_bypass = TRUE
+
var/HTML = "
" + HTML += " | ||
"
if(jobban_isbanned(user, job.title))
HTML += " | BANNED |