diff --git a/config/credits/sounds/space_asshole.ogg b/config/credits/sounds/space_asshole.ogg index 9d3fd15c6dc2..49c665d67a8b 100644 Binary files a/config/credits/sounds/space_asshole.ogg and b/config/credits/sounds/space_asshole.ogg differ diff --git a/modular_ss220/cinematics/code/cinematics/credits.dm b/modular_ss220/cinematics/code/cinematics/credits.dm index 2e60dd54d497..742473fefd35 100644 --- a/modular_ss220/cinematics/code/cinematics/credits.dm +++ b/modular_ss220/cinematics/code/cinematics/credits.dm @@ -1,5 +1,4 @@ /datum/cinematic/credits - cleanup_time = 40 SECONDS is_global = TRUE backdrop_type = /obj/screen/fullscreen/cinematic_backdrop/credits @@ -8,23 +7,35 @@ screen = new/obj/screen/cinematic/credits(src) /datum/cinematic/credits/start_cinematic(list/watchers) - watching = watchers - if(SEND_GLOBAL_SIGNAL(COMSIG_GLOB_PLAY_CINEMATIC, src) & COMPONENT_GLOB_BLOCK_CINEMATIC) - RegisterSignal(SSdcs, COMSIG_GLOB_CINEMATIC_STOPPED_PLAYING, PROC_REF(queue_gone)) - return - . = ..() + if(!(SEND_GLOBAL_SIGNAL(COMSIG_GLOB_PLAY_CINEMATIC, src) & COMPONENT_GLOB_BLOCK_CINEMATIC)) + . = ..() + RegisterSignal(SSdcs, COMSIG_GLOB_CINEMATIC_STOPPED_PLAYING, PROC_REF(queue_gone)) + for(var/mob/watching_mob in watchers) + if(watching_mob.client) + watching += watching_mob /datum/cinematic/credits/proc/queue_gone(datum/source, datum/cinematic/other) SIGNAL_HANDLER - + UnregisterSignal(SSdcs, COMSIG_GLOB_CINEMATIC_STOPPED_PLAYING) start_cinematic(src.watching) /datum/cinematic/credits/play_cinematic() - play_cinematic_sound(sound(SScredits.title_music)) + play_cinematic_sound(sound(SScredits.title_music, volume = 20)) + SScredits.roll_credits_for_clients(watching) + cleanup_time = SScredits.end_titles.playing_time + 3 SECONDS + special_callback?.Invoke() +/datum/cinematic/credits/stop_cinematic() + for(var/client/client in watching) + SScredits.clear_credits(client) + + UnregisterSignal(SSdcs, COMSIG_GLOB_CINEMATIC_STOPPED_PLAYING) + + . = ..() + /obj/screen/cinematic/credits icon_state = "blank" diff --git a/modular_ss220/credits/code/SScredits.dm b/modular_ss220/credits/code/SScredits.dm index d2d9a6ce4509..40c92eadc401 100644 --- a/modular_ss220/credits/code/SScredits.dm +++ b/modular_ss220/credits/code/SScredits.dm @@ -4,64 +4,122 @@ SUBSYSTEM_DEF(credits) name = "Credits" runlevels = RUNLEVEL_POSTGAME flags = SS_NO_FIRE - var/list/end_titles = list() + + var/datum/credits/end_titles var/title_music = "" - var/credit_roll_speed = 185 - var/credit_spawn_speed = 20 + var/credit_roll_speed = 22 SECONDS + var/credit_spawn_speed = 2 SECONDS var/credit_animate_height - var/credit_ease_duration = 22 /datum/controller/subsystem/credits/Initialize() - credit_animate_height = 14 * world.icon_size + credit_animate_height = 16 * world.icon_size title_music = pick(file2list("config/credits/sounds/title_music.txt")) + /datum/controller/subsystem/credits/proc/roll_credits_for_clients(list/clients) - if(!length(end_titles)) - end_titles = generate_titles() + end_titles = new /datum/credits/default() for(var/client/client in clients) SScredits.roll_credits_for_client(client) + /datum/controller/subsystem/credits/proc/roll_credits_for_client(client/client) LAZYINITLIST(client.credits) - var/list/_credits = client.credits - var/obj/screen/credit/logo = new /obj/screen/credit/logo(null, "", client) - addtimer(CALLBACK(src, PROC_REF(roll_credits), _credits, logo, client), 5 SECONDS, TIMER_CLIENT_TIME) + addtimer(CALLBACK(src, PROC_REF(roll_credits), client.credits, logo, client), 5 SECONDS, TIMER_CLIENT_TIME) /datum/controller/subsystem/credits/proc/roll_credits(list/credits, obj/screen/credit/logo/logo, client/client) credits += logo - logo.rollem() - for(var/item in end_titles) - if(!client?.credits) - return - var/obj/screen/credit/title = new(null, item, client) - credits += title - title.rollem() - sleep(credit_spawn_speed) + addtimer(CALLBACK(logo, TYPE_PROC_REF(/obj/screen/credit/logo, rollem)), credit_roll_speed / 2.5, TIMER_CLIENT_TIME) + + for(var/datum/credit/credit in end_titles.credits) + for(var/item in credit.content) + if(!client?.credits) + return + var/obj/screen/credit/title = new(null, item, client) + credits += title + title.rollem() + sleep(credit_spawn_speed) addtimer(CALLBACK(src, PROC_REF(clear_credits), client), (credit_roll_speed), TIMER_CLIENT_TIME) + /datum/controller/subsystem/credits/proc/clear_credits(client/client) if(!client) return QDEL_NULL(client.credits) -/datum/controller/subsystem/credits/proc/generate_titles() - RETURN_TYPE(/list) - var/list/titles = list() - var/list/cast = list() - var/list/chunk = list() - var/list/streamers = list() - var/chunksize = 0 +/datum/credits + var/list/credits = list() + var/playing_time = 5 SECONDS + +/datum/credits/New() + . = ..() + + fill_credits() + + count_time() + +/datum/credits/proc/fill_credits() + +/datum/credits/proc/count_time() + for(var/datum/credit/credit in credits) + for(var/title in credit.content) + playing_time += SScredits.credit_spawn_speed + + playing_time -= SScredits.credit_spawn_speed + playing_time += SScredits.credit_roll_speed + +/datum/credits/default + +/datum/credits/default/fill_credits() + credits += new /datum/credit/episode_title() + credits += new /datum/credit/streamers() + credits += new /datum/credit/crewlist() + credits += new /datum/credit/corpses() + credits += new /datum/credit/staff() + credits += new /datum/credit/disclaimer() + +/datum/credits/debug_large_credits + +/datum/credits/debug_large_credits/fill_credits() + . = ..() + + credits += new /datum/credit/disclaimer() + credits += new /datum/credit/disclaimer() + credits += new /datum/credit/disclaimer() + credits += new /datum/credit/disclaimer() + credits += new /datum/credit/disclaimer() + credits += new /datum/credit/disclaimer() + credits += new /datum/credit/disclaimer() + credits += new /datum/credit/disclaimer() + credits += new /datum/credit/disclaimer() + credits += new /datum/credit/disclaimer() + credits += new /datum/credit/disclaimer() + credits += new /datum/credit/disclaimer() + credits += new /datum/credit/disclaimer() + credits += new /datum/credit/disclaimer() + credits += new /datum/credit/disclaimer() + credits += new /datum/credit/disclaimer() + credits += new /datum/credit/disclaimer() + credits += new /datum/credit/disclaimer() + credits += new /datum/credit/disclaimer() + credits += new /datum/credit/disclaimer() + +/datum/credit + var/list/content = list() + +/datum/credit/episode_title + +/datum/credit/episode_title/New() + . = ..() var/episode_title = "" switch(rand(1,100)) - if(1 to 10) episode_title += pick(file2list("config/credits/titles/finished_titles.txt")) if(11 to 30) @@ -73,7 +131,36 @@ SUBSYSTEM_DEF(credits) episode_title += pick(file2list("config/credits/titles/random_titles_plural_2_1.txt")) + " " episode_title += pick(file2list("config/credits/titles/random_titles_plural_2_2.txt")) - titles += "

EPISODE [GLOB.round_id]
[episode_title]

" + content += "

EPISODE [GLOB.round_id]

[episode_title]

" + +/datum/credit/streamers + +/datum/credit/streamers/New() + . = ..() + var/list/streamers = list() + + for(var/iterator_key in GLOB.configuration.admin.ckey_rank_map) + if(!(GLOB.configuration.admin.ckey_rank_map[iterator_key] == "Банда")) + continue + + var/ckey = ckey(iterator_key) + var/client/client = get_client_by_ckey(ckey) + if(!client) + continue + streamers += "
[client.mob.name] a.k.a. ([ckey])
" + + if(length(streamers)) + content += "
" + content += "

Приглашенные звезды:
[jointext(streamers, "
")]
" + +/datum/credit/enormeus_crewlist_debug + +/datum/credit/enormeus_crewlist_debug/New() + . = ..() + + var/list/cast = list() + var/list/chunk = list() + var/chunksize = 0 for(var/mob/living/carbon/human/human in GLOB.alive_mob_list | GLOB.dead_mob_list) if(findtext(human.real_name,"(mannequin)")) @@ -82,25 +169,63 @@ SUBSYSTEM_DEF(credits) continue if(!human.last_known_ckey) continue - if(human.client?.holder?.rank == "Банда") - streamers += "
[human.real_name]([human.ckey]) в роли [human.job]
" + + for(var/i = 0, i < 100, i++) + if(!length(cast) && !chunksize) + cast += "
" + chunk += "
В съемках участвовали:" + chunk += "[human.real_name] в роли [uppertext(human.job)]" + chunksize++ + if(chunksize > 2) + cast += "
[jointext(chunk,"
")]
" + chunk.Cut() + chunksize = 0 + + if(length(chunk)) + cast += "
[jointext(chunk,"
")]
" + + + content += cast + + +/datum/credit/crewlist + +/datum/credit/crewlist/New() + . = ..() + + var/list/cast = list() + var/list/chunk = list() + var/chunksize = 0 + + for(var/mob/living/carbon/human/human in GLOB.alive_mob_list | GLOB.dead_mob_list) + if(findtext(human.real_name,"(mannequin)")) + continue + if(ismonkeybasic(human)) + continue + if(!human.last_known_ckey) continue + if(!length(cast) && !chunksize) - chunk += "В съемках участвовали:" + cast += "
" + chunk += "
В съемках участвовали:" chunk += "[human.real_name] в роли [uppertext(human.job)]" chunksize++ if(chunksize > 2) cast += "
[jointext(chunk,"
")]
" chunk.Cut() chunksize = 0 + if(length(chunk)) cast += "
[jointext(chunk,"
")]
" - if(length(streamers)) - titles += "
Приглашенные звезды:

" - titles += streamers - titles += cast + content += cast + + +/datum/credit/corpses + +/datum/credit/corpses/New() + . = ..() var/list/corpses = list() @@ -109,11 +234,15 @@ SUBSYSTEM_DEF(credits) continue else if(human.real_name) corpses += human.real_name - if(length(corpses)) - titles += "
Основано на реальных событиях:
В память о [english_list(corpses)].

" + content += "
Основано на реальных событиях:
В память о [english_list(corpses)].
" + +/datum/credit/staff - var/list/staff = list("Съемочная группа:") +/datum/credit/staff/New() + . = ..() + + var/list/staff = list() var/list/staffjobs = file2list("config/credits/jobs/staffjobs.txt") var/list/goodboys = list() for(var/client/client in GLOB.clients) @@ -125,9 +254,17 @@ SUBSYSTEM_DEF(credits) else if(check_rights_client(R_MENTOR, FALSE, client)) goodboys += "[client.key]" - titles += "
[jointext(staff,"
")]
" + if(length(staff)) + content += "
Съемочная группа:
" + content += "
[jointext(staff,"
")]
" + if(length(goodboys)) - titles += "
Мальчики на побегушках:
[english_list(goodboys)]

" + content += "
Мальчики на побегушках:
[english_list(goodboys)]

" + +/datum/credit/disclaimer + +/datum/credit/disclaimer/New() + . = ..() var/disclaimer = "
Sponsored by WYCCSTATION.
All rights reserved.
\ This motion picture is protected under the copyright laws of the Sol Central Government
and other nations throughout the galaxy.
\ @@ -136,28 +273,17 @@ SUBSYSTEM_DEF(credits) disclaimer += pick("Use for parody prohibited. PROHIBITED.", "All stunts were performed by underpaid interns. Do NOT try at home.", "WYCCSTATION does not endorse behaviour depicted. Attempt at your own risk.", - "Any unauthorized exhibition, distribution, or copying of this film or any part thereof (including soundtrack)
\ - may result in an ERT being called to storm your home and take it back by force.", - "The story, all names, characters, and incidents portrayed in this production are fictitious. No identification with actual
\ - persons (living or deceased), places, buildings, and products is intended or should be inferred.
\ - This film is based on a true story and all individuals depicted are based on real people, despite what we just said.", - "No person or entity associated with this film received payment or anything of value, or entered into any agreement, in connection
\ - with the depiction of tobacco products, despite the copious amounts of smoking depicted within.
\ - (This disclaimer sponsored by Carcinoma - Carcinogens are our Business!(TM)).", "No animals were harmed in the making of this motion picture except for those listed previously as dead. Do not try this at home.") - titles += "
" - titles += "
[jointext(disclaimer, null)]
" - - return titles + content += "
" + content += "
[jointext(disclaimer, null)]
" /obj/screen/credit icon_state = "blank" mouse_opacity = 0 - alpha = 0 + alpha = 255 screen_loc = "CENTER-7,CENTER-7" plane = CREDITS_PLANE - var/matrix/target var/client/parent /obj/screen/credit/Initialize(mapload, credited, client/client) @@ -169,18 +295,16 @@ SUBSYSTEM_DEF(credits) maptext_width = world.icon_size * 14 /obj/screen/credit/proc/rollem() - var/matrix/M = matrix(transform) - M.Translate(0, SScredits.credit_animate_height) - animate(src, transform = M, time = SScredits.credit_roll_speed) - target = M - animate(src, alpha = 255, time = SScredits.credit_ease_duration, flags = ANIMATION_PARALLEL) - addtimer(CALLBACK(src, PROC_REF(delete_credit)), SScredits.credit_roll_speed - SScredits.credit_ease_duration, TIMER_CLIENT_TIME) + var/matrix/matrix = matrix(transform) + transform = matrix.Translate(0, -world.icon_size) + + matrix.Translate(0, SScredits.credit_animate_height) + animate(src, transform = matrix, time = SScredits.credit_roll_speed) + addtimer(CALLBACK(src, PROC_REF(delete_credit)), SScredits.credit_roll_speed, TIMER_CLIENT_TIME) parent.screen += src /obj/screen/credit/proc/delete_credit() if(!QDELETED(src)) - animate(src, alpha = 0, transform = target, time = SScredits.credit_ease_duration) - sleep(SScredits.credit_ease_duration) qdel(src) /obj/screen/credit/Destroy() @@ -193,7 +317,7 @@ SUBSYSTEM_DEF(credits) /obj/screen/credit/logo icon = 'modular_ss220/credits/icons/logo.dmi' icon_state = "ss220" - screen_loc = "CENTER - 2,CENTER - 3" + screen_loc = "CENTER - 2,CENTER" alpha = 100 @@ -203,18 +327,14 @@ SUBSYSTEM_DEF(credits) parent.screen += src /obj/screen/credit/logo/rollem() - var/matrix/M = matrix(transform) - M.Translate(0, SScredits.credit_animate_height / 2) - animate(src, transform = M, time = SScredits.credit_roll_speed / 2) - target = M - animate(src, alpha = 255, time = SScredits.credit_ease_duration / 2, flags = ANIMATION_PARALLEL) - addtimer(CALLBACK(src, PROC_REF(delete_credit)),(SScredits.credit_roll_speed - SScredits.credit_ease_duration) / 2, TIMER_CLIENT_TIME) + var/matrix/matrix = matrix(transform) + matrix.Translate(0, SScredits.credit_animate_height) + animate(src, transform = matrix, time = SScredits.credit_roll_speed) + addtimer(CALLBACK(src, PROC_REF(delete_credit)), SScredits.credit_roll_speed, TIMER_CLIENT_TIME) /obj/screen/credit/logo/delete_credit() if(!QDELETED(src)) - animate(src, alpha = 0, transform = target, time = SScredits.credit_ease_duration / 2) - sleep(SScredits.credit_ease_duration / 2) qdel(src) /client/var/list/credits