mirror of
https://github.com/VOREStation/VOREStation.git
synced 2026-07-20 03:26:37 +01:00
Move some ghosty stuff to async
This commit is contained in:
@@ -8,6 +8,7 @@ var/global/list/silicon_mob_list = list() //List of all silicon mobs, includin
|
||||
var/global/list/ai_list = list() //List of all AIs, including clientless
|
||||
var/global/list/living_mob_list = list() //List of all alive mobs, including clientless. Excludes /mob/new_player
|
||||
var/global/list/dead_mob_list = list() //List of all dead mobs, including clientless. Excludes /mob/new_player
|
||||
var/global/list/observer_mob_list = list() //List of all /mob/observer/dead, including clientless.
|
||||
var/global/list/listening_objects = list() //List of all objects which care about receiving messages (communicators, radios, etc)
|
||||
var/global/list/cleanbot_reserved_turfs = list() //List of all turfs currently targeted by some cleanbot
|
||||
|
||||
|
||||
+66
-34
@@ -11,18 +11,13 @@
|
||||
var/wait_time = 60 SECONDS // How long to wait until returning the list of candidates.
|
||||
var/cutoff_number = 0 // If above 0, when candidates list reaches this number, further potential candidates are rejected.
|
||||
|
||||
/// Begin the ghost asking
|
||||
/datum/ghost_query/proc/query()
|
||||
// First, ask all the ghosts who want to be asked.
|
||||
for(var/mob/observer/dead/D in player_list)
|
||||
if(!D.MayRespawn())
|
||||
continue // They can't respawn for whatever reason.
|
||||
if(D.client)
|
||||
if(be_special_flag && !(D.client.prefs.be_special & be_special_flag) )
|
||||
continue // They don't want to see the prompt.
|
||||
for(var/ban in check_bans)
|
||||
if(jobban_isbanned(D, ban))
|
||||
continue // They're banned from this role.
|
||||
ask_question(D.client)
|
||||
for(var/mob/observer/dead/D as anything in observer_mob_list)
|
||||
if(evaluate_candidate(D))
|
||||
ask_question(D)
|
||||
|
||||
// Then wait awhile.
|
||||
while(!finished)
|
||||
sleep(1 SECOND)
|
||||
@@ -31,36 +26,73 @@
|
||||
finished = TRUE
|
||||
|
||||
// Prune the list after the wait, incase any candidates logged out.
|
||||
for(var/mob/observer/dead/D in candidates)
|
||||
if(!D.client || !D.key)
|
||||
candidates.Remove(D)
|
||||
for(var/mob/observer/dead/D as anything in candidates)
|
||||
if(!evaluate_candidate(D))
|
||||
candidates -= D
|
||||
|
||||
// Now we're done.
|
||||
finished = TRUE
|
||||
return candidates
|
||||
|
||||
/datum/ghost_query/proc/ask_question(var/client/C)
|
||||
spawn(0)
|
||||
if(!C)
|
||||
return
|
||||
window_flash(C)
|
||||
if(query_sound)
|
||||
SEND_SOUND(C, sound(query_sound))
|
||||
var/response = tgui_alert(C, question, "[role_name] request", list("Yes", "No", "Never for this round"))
|
||||
if(response == "Yes")
|
||||
response = tgui_alert(C, "Are you sure you want to play as a [role_name]?", "[role_name] request", list("Yes", "No")) // Protection from a misclick.
|
||||
if(!C || !src)
|
||||
return
|
||||
if(response == "Yes")
|
||||
if(finished || (cutoff_number && candidates.len >= cutoff_number) )
|
||||
to_chat(C, "<span class='warning'>Unfortunately, you were not fast enough, and there are no more available roles. Sorry.</span>")
|
||||
return
|
||||
candidates.Add(C.mob)
|
||||
if(cutoff_number && candidates.len >= cutoff_number)
|
||||
finished = TRUE // Finish now if we're full.
|
||||
else if(response == "Never for this round")
|
||||
/// Test a candidate for allowance to join as this
|
||||
/datum/ghost_query/proc/evaluate_candidate(mob/observer/dead/candidate)
|
||||
if(!istype(candidate))
|
||||
return FALSE // Changed mobs or something who knows
|
||||
if(!candidate.client)
|
||||
return FALSE // No client to ask
|
||||
if(!candidate.MayRespawn())
|
||||
return FALSE // They can't respawn for whatever reason.
|
||||
if(be_special_flag && !(candidate.client.prefs.be_special & be_special_flag) )
|
||||
return FALSE // They don't want to see the prompt.
|
||||
for(var/ban in check_bans)
|
||||
if(jobban_isbanned(candidate, ban))
|
||||
return FALSE // They're banned from this role.
|
||||
|
||||
return TRUE
|
||||
|
||||
/// Send async alerts and ask for responses. Expects you to have tested D for client and type already
|
||||
/datum/ghost_query/proc/ask_question(var/mob/observer/dead/D)
|
||||
var/client/C = D.client
|
||||
window_flash(C)
|
||||
|
||||
if(query_sound)
|
||||
SEND_SOUND(C, sound(query_sound))
|
||||
|
||||
tgui_alert_async(D, question, "[role_name] request", list("Yes", "No", "Never for this round"), CALLBACK(src, .proc/get_reply), wait_time SECONDS)
|
||||
|
||||
/// Process an async alert response
|
||||
/datum/ghost_query/proc/get_reply(response)
|
||||
var/mob/observer/dead/D = usr
|
||||
if(!D?.client)
|
||||
return
|
||||
|
||||
// Unhandled are "No" and "Nevermind" responses, which should just do nothing
|
||||
|
||||
// This response is always fine, doesn't warrant retesting
|
||||
switch(response)
|
||||
if("Never for this round")
|
||||
if(be_special_flag)
|
||||
C.prefs.be_special ^= be_special_flag
|
||||
D.client.prefs.be_special ^= be_special_flag
|
||||
to_chat(D, "<span class='notice'>You will not be prompted to join similar roles to [role_name] for the rest of this round. Note: If you save your character now, it will save this permanently.</span>")
|
||||
else
|
||||
to_chat(D, "<span class='warning'>This type of ghost-joinable role doesn't have a role type flag associated with it, so I can't prevent future requests, sorry. Bug a dev!</span>")
|
||||
if("Yes")
|
||||
if(!evaluate_candidate(D)) // Failed revalidation
|
||||
to_chat(D, "<span class='warning'>Unfortunately, you no longer qualify for this role. Sorry.</span>")
|
||||
else if(finished) // Already finished candidate list
|
||||
to_chat(D, "<span class='warning'>Unfortunately, you were not fast enough, and there are no more available roles. Sorry.</span>")
|
||||
else // Prompt a second time
|
||||
tgui_alert_async(D, "Are you sure you want to play as a [role_name]?", "[role_name] request", list("I'm Sure", "Nevermind"), CALLBACK(src, .proc/get_reply), wait_time SECONDS)
|
||||
|
||||
if("I'm Sure")
|
||||
if(!evaluate_candidate(D)) // Failed revalidation
|
||||
to_chat(D, "<span class='warning'>Unfortunately, you no longer qualify for this role. Sorry.</span>")
|
||||
else if(finished) // Already finished candidate list
|
||||
to_chat(D, "<span class='warning'>Unfortunately, you were not fast enough, and there are no more available roles. Sorry.</span>")
|
||||
else // Accept their nomination
|
||||
candidates.Add(D)
|
||||
if(cutoff_number && candidates.len >= cutoff_number)
|
||||
finished = TRUE // Finish now if we're full.
|
||||
|
||||
// Normal things.
|
||||
/datum/ghost_query/promethean
|
||||
|
||||
@@ -16,33 +16,63 @@
|
||||
/mob/living/simple_mob/animal/giant_spider/carrier //or the ones who fart babies when they die
|
||||
ic_revivable = 0
|
||||
|
||||
//WHEN GHOSTS ATTACK!!!!!
|
||||
/// A ghost has clicked us
|
||||
/mob/living/simple_mob/attack_ghost(mob/observer/dead/user as mob)
|
||||
if(!ghostjoin)
|
||||
return ..()
|
||||
|
||||
var/reply = tgui_alert(usr, "Would you like to become [src]? It is bound to [revivedby].","Bind To",list("Yes","No"))
|
||||
if(reply == "No")
|
||||
return
|
||||
if(!evaluate_ghost_join(user))
|
||||
return ..()
|
||||
|
||||
if(ckey) //FIRST ONE TO CLICK YES GETS IT!!!!!! Channel your inner youtube commenter.
|
||||
to_chat(src, "<span class='notice'>Sorry, someone else has already inhabited [src].</span>")
|
||||
return
|
||||
|
||||
log_and_message_admins("[key_name_admin(user)] joined [src] as a ghost [ADMIN_FLW(src)]")
|
||||
tgui_alert_async(usr, "Would you like to become [src]? It is bound to [revivedby].", "Become Mob", list("Yes","No"), CALLBACK(src, .proc/reply_ghost_join), 20 SECONDS)
|
||||
|
||||
/// A reply to an async alert request was received
|
||||
/mob/living/simple_mob/proc/reply_ghost_join(response)
|
||||
if(response != "Yes")
|
||||
return // ok
|
||||
|
||||
var/mob/observer/dead/D = usr
|
||||
if(evaluate_ghost_join(D))
|
||||
ghost_join(D)
|
||||
|
||||
/// Inject a ghost into this mob. Assumes you've done all sanity before this point.
|
||||
/mob/living/simple_mob/proc/ghost_join(mob/observer/dead/D)
|
||||
log_and_message_admins("[key_name_admin(D)] joined [src] as a ghost [ADMIN_FLW(src)]")
|
||||
active_ghost_pods -= src
|
||||
if(user.mind)
|
||||
user.mind.active = TRUE
|
||||
user.mind.transfer_to(src)
|
||||
|
||||
// Move the ghost in
|
||||
if(D.mind)
|
||||
D.mind.active = TRUE
|
||||
D.mind.transfer_to(src)
|
||||
else
|
||||
src.ckey = user.ckey
|
||||
qdel(user)
|
||||
ghostjoin = 0
|
||||
src.ckey = D.ckey
|
||||
qdel(D)
|
||||
|
||||
// Clean up the simplemob
|
||||
ghostjoin = FALSE
|
||||
ghostjoin_icon()
|
||||
if(revivedby != "no one")
|
||||
to_chat(src, "<span class='notice'>Where once your life had been rough and scary, you have been assisted by [revivedby]. They seem to be the reason you are on your feet again... so perhaps you should help them out.</span> <span class= warning> Being as you were revived, you are allied with the station. Do not attack anyone unless they are threatening the one who revived you. And try to listen to the one who revived you within reason. Of course, you may do scenes as you like, but you must still respect preferences.</span>")
|
||||
visible_message("[src]'s eyes flicker with a curious intelligence.")
|
||||
visible_message("[src]'s eyes flicker with a curious intelligence.", runemessage = "looks around")
|
||||
|
||||
/// Evaluate someone for being allowed to join as this mob from being a ghost
|
||||
/mob/living/simple_mob/proc/evaluate_ghost_join(mob/observer/dead/D)
|
||||
if(!istype(D) || !D.client)
|
||||
stack_trace("A non-ghost mob was evaluated for joining into a simplemob...")
|
||||
return FALSE
|
||||
|
||||
// At this point we can at least send them messages as to why they can't join, since they are a mob with a client
|
||||
if(!ghostjoin)
|
||||
to_chat(D, "<span class='notice'>Sorry, [src] is no longer ghost-joinable.</span>")
|
||||
return FALSE
|
||||
|
||||
if(ckey)
|
||||
to_chat(D, "<span class='notice'>Sorry, someone else has already inhabited [src].</span>")
|
||||
return FALSE
|
||||
|
||||
// Insert whatever ban checks you want here if we ever add simplemob bans
|
||||
|
||||
return TRUE
|
||||
|
||||
/obj/item/device/denecrotizer //Away map reward. FOR TRAINED NECROMANCERS ONLY. >:C
|
||||
name = "experimental denecrotizer"
|
||||
|
||||
@@ -130,6 +130,7 @@
|
||||
name = capitalize(pick(first_names_male)) + " " + capitalize(pick(last_names))
|
||||
real_name = name
|
||||
animate(src, pixel_y = 2, time = 10, loop = -1)
|
||||
observer_mob_list += src
|
||||
..()
|
||||
|
||||
/mob/observer/dead/Topic(href, href_list)
|
||||
@@ -504,6 +505,7 @@ This is the proc mobs get to turn into a ghost. Forked from ghostize due to comp
|
||||
var/mob/M = following
|
||||
M.following_mobs -= src
|
||||
stop_following()
|
||||
observer_mob_list -= src
|
||||
return ..()
|
||||
|
||||
/mob/Moved(atom/old_loc, direction, forced = FALSE)
|
||||
|
||||
Reference in New Issue
Block a user