Skip to content

Commit

Permalink
Merge branch 'master' into adrenaline
Browse files Browse the repository at this point in the history
  • Loading branch information
private-tristan committed Nov 4, 2023
2 parents 4491ab8 + f715314 commit 77ced46
Show file tree
Hide file tree
Showing 18 changed files with 218 additions and 198 deletions.
1 change: 1 addition & 0 deletions code/__DEFINES/xeno.dm
Original file line number Diff line number Diff line change
Expand Up @@ -36,6 +36,7 @@
#define XENO_HITS_TO_DESTROY_WINDOW_FRAME 3
#define XENO_HITS_TO_DESTROY_R_WINDOW_FRAME 5
#define XENO_HITS_TO_DESTROY_BOLTED_DOOR 10
#define XENO_HITS_TO_DESTROY_DOOR 10
#define XENO_HITS_TO_DESTROY_WELDED_DOOR 15
#define XENO_HITS_TO_EXPOSE_WIRES_MIN 3
#define XENO_HITS_TO_EXPOSE_WIRES_MAX 4
Expand Down
2 changes: 2 additions & 0 deletions code/__DEFINES/xeno_ai.dm
Original file line number Diff line number Diff line change
Expand Up @@ -5,9 +5,11 @@
#define DISTANCE_PENALTY 1
#define ASTAR_COST_FUNCTION(n) (abs(n.x - target.x)+abs(n.y - target.y))

#define OPEN_TURF_PENALTY 1
#define DOOR_PENALTY 3
#define OBJECT_PENALTY 20
#define HUMAN_PENALTY 4
#define XENO_PENALTY 20
#define VEHICLE_PENALTY 25
#define SENTRY_PENALTY 25
#define WINDOW_FRAME_PENALTY 25
Expand Down
20 changes: 20 additions & 0 deletions code/controllers/subsystem/minimap.dm
Original file line number Diff line number Diff line change
Expand Up @@ -247,12 +247,19 @@ SUBSYSTEM_DEF(minimaps)
blip.overlays += overlay

images_by_source[target] = blip

for(var/flag in bitfield2list(hud_flags))
minimaps_by_z["[zlevel]"].images_assoc["[flag]"][target] = blip
minimaps_by_z["[zlevel]"].images_raw["[flag]"] += blip

if(ismovableatom(target))
RegisterSignal(target, COMSIG_MOVABLE_Z_CHANGED, PROC_REF(on_z_change))
blip.RegisterSignal(target, COMSIG_MOVABLE_MOVED, TYPE_PROC_REF(/image, minimap_on_move))

if(isitem(target))
blip.RegisterSignal(target, COMSIG_ITEM_PICKUP, TYPE_PROC_REF(/image, minimap_on_pickup))
blip.RegisterSignal(target, COMSIG_ITEM_DROPPED, TYPE_PROC_REF(/image, minimap_on_drop))

removal_cbs[target] = CALLBACK(src, PROC_REF(removeimage), blip, target)
RegisterSignal(target, COMSIG_PARENT_QDELETING, PROC_REF(remove_marker))

Expand Down Expand Up @@ -299,6 +306,19 @@ SUBSYSTEM_DEF(minimaps)
pixel_x = MINIMAP_PIXEL_FROM_WORLD(source.x) + SSminimaps.minimaps_by_z["[source_z]"].x_offset
pixel_y = MINIMAP_PIXEL_FROM_WORLD(source.y) + SSminimaps.minimaps_by_z["[source_z]"].y_offset

/image/proc/minimap_on_pickup(obj/item/source, mob/user)
SIGNAL_HANDLER

RegisterSignal(user, COMSIG_MOVABLE_MOVED, TYPE_PROC_REF(/image, minimap_on_move), override = TRUE)
UnregisterSignal(source, COMSIG_MOVABLE_MOVED)

/image/proc/minimap_on_drop(obj/item/source, mob/user)
SIGNAL_HANDLER

if(recursive_holder_check(source, recursion_limit = 5) != user)
UnregisterSignal(user, COMSIG_MOVABLE_MOVED)
RegisterSignal(source, COMSIG_MOVABLE_MOVED, TYPE_PROC_REF(/image, minimap_on_move))

/**
* Removes an atom and it's blip from the subsystem.
* Force has no effect on this proc, but is here because we are a COMSIG_PARENT_QDELETING handler.
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,12 @@
/datum/component/ai_behavior_override/attack
behavior_icon_state = "attack_order"

/datum/component/ai_behavior_override/attack/Destroy(force, silent, ...)
for(var/mob/living/carbon/xenomorph/assigned_xeno in currently_assigned)
assigned_xeno.current_target = null

. = ..()

/datum/component/ai_behavior_override/attack/check_behavior_validity(mob/living/carbon/xenomorph/checked_xeno, distance)
. = ..()
if(!.)
Expand Down
141 changes: 43 additions & 98 deletions code/game/jobs/role_authority.dm
Original file line number Diff line number Diff line change
Expand Up @@ -234,55 +234,16 @@ I hope it's easier to tell what the heck this proc is even doing, unlike previou
if(length(overwritten_roles_for_mode))
temp_roles_for_mode = overwritten_roles_for_mode

// Get balancing weight for the readied players.
// Squad marine roles have a weight of 1, and shipside roles have a lower weight of SHIPSIDE_ROLE_WEIGHT.
players_preassigned = assign_roles(temp_roles_for_mode.Copy(), unassigned_players.Copy(), TRUE)

// Even though we pass a copy of temp_roles_for_mode, job counters still change, so we reset them here.
for(var/title in temp_roles_for_mode)
var/datum/job/J = temp_roles_for_mode[title]
J.current_positions = 0

// Set up limits for other roles based on our balancing weight number.
// Set the xeno starting amount based on marines assigned
var/datum/job/antag/xenos/XJ = temp_roles_for_mode[JOB_XENOMORPH]
if(istype(XJ))
XJ.set_spawn_positions(players_preassigned)

// Limit the number of SQUAD MARINE roles players can roll initially
var/datum/job/SMJ = GET_MAPPED_ROLE(JOB_SQUAD_MARINE)
if(istype(SMJ))
SMJ.set_spawn_positions(players_preassigned)

// Set survivor starting amount based on marines assigned
var/datum/job/SJ = temp_roles_for_mode[JOB_SURVIVOR]
if(istype(SJ))
SJ.set_spawn_positions(players_preassigned)

var/datum/job/CO_surv_job = temp_roles_for_mode[JOB_CO_SURVIVOR]
if(istype(CO_surv_job))
CO_surv_job.set_spawn_positions(players_preassigned)

if(SSnightmare.get_scenario_value("predator_round"))
SSticker.mode.flags_round_type |= MODE_PREDATOR
// Set predators starting amount based on marines assigned
var/datum/job/PJ = temp_roles_for_mode[JOB_PREDATOR]
if(istype(PJ))
PJ.set_spawn_positions(players_preassigned)

// Assign the roles, this time for real, respecting limits we have established.
var/list/roles_left = assign_roles(temp_roles_for_mode, unassigned_players)

var/alternate_option_assigned = 0;
for(var/mob/new_player/M in unassigned_players)
switch(M.client.prefs.alternate_option)
if(GET_RANDOM_JOB)
roles_left = assign_random_role(M, roles_left) //We want to keep the list between assignments.
alternate_option_assigned++
if(BE_MARINE)
var/datum/job/marine_job = GET_MAPPED_ROLE(JOB_SQUAD_MARINE)
assign_role(M, marine_job) //Should always be available, in all game modes, as a candidate. Even if it may not be a marine.
alternate_option_assigned++
if(BE_XENOMORPH)
assign_role(M, temp_roles_for_mode[JOB_XENOMORPH])
if(RETURN_TO_LOBBY)
Expand All @@ -295,70 +256,54 @@ I hope it's easier to tell what the heck this proc is even doing, unlike previou

unassigned_players = null

// Now we take spare unfilled xeno slots and make them larva NEW
var/datum/hive_status/hive = GLOB.hive_datum[XENO_HIVE_NORMAL]
if(istype(hive) && istype(XJ))
hive.stored_larva += max(0, (XJ.total_positions - XJ.current_positions) \
+ (XJ.calculate_extra_spawn_positions(alternate_option_assigned)))

/*===============================================================*/

/**
* Assign roles to the players. Return roles that are still avialable.
* If count is true, return role balancing weight instead.
*/
/datum/authority/branch/role/proc/assign_roles(list/roles_for_mode, list/unassigned_players, count = FALSE)
var/list/roles_left = list()
var/assigned = 0
for(var/priority in HIGH_PRIORITY to LOW_PRIORITY)
// Assigning xenos first.
assigned += assign_initial_roles(priority, roles_for_mode & ROLES_XENO, unassigned_players)
// Assigning special roles second. (survivor, predator)
assigned += assign_initial_roles(priority, roles_for_mode & (ROLES_WHITELISTED|ROLES_SPECIAL), unassigned_players)
// Assigning command third.
assigned += assign_initial_roles(priority, roles_for_mode & ROLES_COMMAND, unassigned_players)
// Assigning the rest
var/rest_roles_for_mode = roles_for_mode - (roles_for_mode & ROLES_XENO) - (roles_for_mode & ROLES_COMMAND) - (roles_for_mode & (ROLES_WHITELISTED|ROLES_SPECIAL))
if(count)
assigned += assign_initial_roles(priority, rest_roles_for_mode, unassigned_players)
else
roles_left= assign_initial_roles(priority, rest_roles_for_mode, unassigned_players, FALSE)
if(count)
return assigned
return roles_left

/datum/authority/branch/role/proc/assign_initial_roles(priority, list/roles_to_iterate, list/unassigned_players, count = TRUE)
var/assigned = 0
if(!length(roles_to_iterate) || !length(unassigned_players))
/// Assign roles to the players. Return roles that are still available.
/datum/authority/branch/role/proc/assign_roles(list/roles_to_assign, list/unassigned_players)
if(!length(roles_to_assign) || !length(unassigned_players))
return

for(var/job in roles_to_iterate)
var/datum/job/J = roles_to_iterate[job]
if(!istype(J)) //Shouldn't happen, but who knows.
to_world(SPAN_DEBUG("Error setting up jobs, no job datum set for: [job]."))
log_debug("Error setting up jobs, no job datum set for: [job].")
continue
for(var/mob/new_player/cycled_unassigned in shuffle(unassigned_players))
var/player_assigned_job = FALSE
log_debug("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("We have started cycled through priority [priority] for [cycled_unassigned]")

for(var/job_name in wanted_jobs_by_name)
log_debug("We are cycling through wanted jobs and are at [job_name] for [cycled_unassigned]")
if(job_name in roles_to_assign)
log_debug("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("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("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("[cycled_unassigned] has been assigned a job and we are breaking")
break

log_debug("[cycled_unassigned] did not get a job at priority [priority], moving to next priority level")

if(!length(roles_to_assign))
log_debug("No more roles to assign, breaking")
break

if(!player_assigned_job)
log_debug("[cycled_unassigned] was unable to be assigned a job based on preferences and roles to assign. We still have roles to assign, continuing to next player")

log_debug("Assigning complete. Players unassigned: [length(unassigned_players)] Jobs unassigned: [length(roles_to_assign)]")

var/role_weight = calculate_role_weight(J)
for(var/M in unassigned_players)
var/mob/new_player/NP = M
if(!(NP.client.prefs.get_job_priority(J.title) == priority))
continue //If they don't want the job. //TODO Change the name of the prefs proc?

if(assign_role(NP, J))
assigned += role_weight
unassigned_players -= NP
// -1 check is not strictly needed here, since standard marines are
// supposed to have an actual spawn_positions number at this point
if(J.spawn_positions != -1 && J.current_positions >= J.spawn_positions)
roles_to_iterate -= job //Remove the position, since we no longer need it.
break //Maximum position is reached?

if(!length(unassigned_players))
break //No players left to assign? Break.
if(count)
return assigned
return roles_to_iterate
return roles_to_assign

/**
* Calculate role balance weight for one person joining as that role. This weight is used
Expand Down
11 changes: 10 additions & 1 deletion code/game/objects/items/fulton.dm
Original file line number Diff line number Diff line change
Expand Up @@ -119,7 +119,7 @@ var/global/list/deployed_fultons = list()
return
for(var/obj/item/stack/fulton/F in get_turf(target_atom))
return
var/obj/item/stack/fulton/F = new /obj/item/stack/fulton(get_turf(target_atom), 1, target_atom)
var/obj/item/stack/fulton/F = new type(get_turf(target_atom), 1, target_atom)
transfer_fingerprints_to(F)
src.add_fingerprint(user)
F.add_fingerprint(user)
Expand Down Expand Up @@ -172,3 +172,12 @@ var/global/list/deployed_fultons = list()
qdel(reservation)
qdel(src)
return

/obj/item/stack/fulton/destroy_on_use

/obj/item/stack/fulton/destroy_on_use/deploy_fulton()
. = ..()

qdel(attached_atom)
qdel(reservation)
qdel(src)
3 changes: 1 addition & 2 deletions code/modules/admin/game_master/game_master.dm
Original file line number Diff line number Diff line change
Expand Up @@ -55,8 +55,7 @@ GLOBAL_VAR_INIT(radio_communication_clarity, 100)

/// Associated list of game master submenus organized by object_type = game_master_submenu
var/list/submenu_types = list(
/obj/structure/pipes/vents/scrubber = /datum/game_master_submenu/vents,
/obj/structure/pipes/vents/pump = /datum/game_master_submenu/vents,
/obj/structure/pipes/vents = /datum/game_master_submenu/vents,
)

/// List of current submenus
Expand Down
2 changes: 1 addition & 1 deletion code/modules/admin/player_panel/actions/physical.dm
Original file line number Diff line number Diff line change
Expand Up @@ -98,7 +98,7 @@
SSticker.mode.latejoin_tally-- //Cryoing someone out removes someone from the Marines, blocking further larva spawns until accounted for

//Handle job slot/tater cleanup.
RoleAuthority.free_role(GET_MAPPED_ROLE(occupant.job), TRUE)
RoleAuthority.free_role(GET_MAPPED_ROLE(target.job), TRUE)

//Delete them from datacore.
var/target_ref = WEAKREF(target)
Expand Down
14 changes: 14 additions & 0 deletions code/modules/client/preferences.dm
Original file line number Diff line number Diff line change
Expand Up @@ -908,6 +908,20 @@ var/const/MAX_SAVE_SLOTS = 10

return job_preference_list[J]

/// Returns a list of all the proference's jobs set to the priority argument
/datum/preferences/proc/get_jobs_by_priority(priority)
var/list/jobs_to_return = list()

if(!length(job_preference_list))
ResetJobs()
return jobs_to_return

for(var/job in job_preference_list)
if(job_preference_list[job] == priority)
jobs_to_return += job

return jobs_to_return

/datum/preferences/proc/SetJobDepartment(datum/job/J, priority)
if(!J || priority < 0 || priority > 4)
return FALSE
Expand Down
14 changes: 12 additions & 2 deletions code/modules/defenses/sentry.dm
Original file line number Diff line number Diff line change
Expand Up @@ -62,6 +62,12 @@

can_be_near_defense = TRUE

/// Delay sending no ammo messages
COOLDOWN_DECLARE(no_ammo_message_cooldown)

/// Delay for the beep before firing after not firing for a while
COOLDOWN_DECLARE(beep_fire_sound_cooldown)

/obj/structure/machinery/defenses/sentry/Initialize()
. = ..()
spark_system = new /datum/effect_system/spark_spread
Expand Down Expand Up @@ -317,14 +323,18 @@
if(!(world.time-last_fired >= fire_delay) || !turned_on || !ammo || QDELETED(target))
return

if(world.time-last_fired >= 30 SECONDS) //if we haven't fired for a while, beep first
if(COOLDOWN_FINISHED(src, beep_fire_sound_cooldown)) //if we haven't fired for a while, beep first
playsound(loc, 'sound/machines/twobeep.ogg', 50, 1)

if(ammo && ammo.current_rounds <= 0)
to_chat(usr, SPAN_WARNING("[name] does not have any ammo."))
if(COOLDOWN_FINISHED(src, no_ammo_message_cooldown))
visible_message(SPAN_WARNING("[src] beeps steadily and its ammo light blinks red."))
COOLDOWN_START(src, no_ammo_message_cooldown, (3 SECONDS))

return

last_fired = world.time
COOLDOWN_START(src, beep_fire_sound_cooldown, (30 SECONDS))

if(QDELETED(owner_mob))
owner_mob = src
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -247,7 +247,7 @@
registered_turfs += cycled_open_turf

var/mob/living/carbon/human/possible_target = locate() in cycled_open_turf
if(possible_target && (!parent.current_target || get_dist(parent, possible_target) < get_dist(parent, parent.current_target)))
if(possible_target && (!parent.current_target || get_dist(parent, possible_target) < get_dist(parent, parent.current_target)) && parent.check_mob_target(possible_target))
parent.current_target = possible_target

/datum/xeno_ai_movement/linger/lurking/proc/unregister_turf_signals()
Expand All @@ -261,8 +261,9 @@
if(!istype(entering_atom, /mob/living/carbon/human))
return

if(!parent.current_target || get_dist(parent, entering_atom) < get_dist(parent, parent.current_target))
parent.current_target = entering_atom
var/mob/living/carbon/human/possible_target = entering_atom
if(!parent.current_target || get_dist(parent, possible_target) < get_dist(parent, parent.current_target) && parent.check_mob_target(possible_target))
parent.current_target = possible_target

/datum/xeno_ai_movement/linger/lurking/proc/lurking_parent_moved(atom/movable/moving_atom, atom/oldloc, direction, Forced)
SIGNAL_HANDLER
Expand Down
12 changes: 2 additions & 10 deletions code/modules/mob/living/carbon/xenomorph/ai/xeno_ai.dm
Original file line number Diff line number Diff line change
Expand Up @@ -23,15 +23,6 @@
QDEL_NULL(ai_movement_handler)
return ..()

GLOBAL_LIST_INIT(ai_target_limbs, list(
"head",
"chest",
"l_leg",
"r_leg",
"l_arm",
"r_arm"
))

/mob/living/carbon/xenomorph/proc/init_movement_handler()
return new /datum/xeno_ai_movement(src)

Expand Down Expand Up @@ -143,7 +134,8 @@ GLOBAL_LIST_INIT(ai_target_limbs, list(
// Called whenever an obstacle is encountered but xeno_ai_obstacle returned something else than infinite
// and now it is considered a valid path.
/atom/proc/xeno_ai_act(mob/living/carbon/xenomorph/X)
return
X.do_click(src, "", list())
return TRUE

/mob/living/carbon/xenomorph/proc/can_move_and_apply_move_delay()
// Unable to move, try next time.
Expand Down
Loading

0 comments on commit 77ced46

Please sign in to comment.