diff --git a/code/__DEFINES/layers.dm b/code/__DEFINES/layers.dm index c568e9fe7bc..fb3b61cd80f 100644 --- a/code/__DEFINES/layers.dm +++ b/code/__DEFINES/layers.dm @@ -39,6 +39,7 @@ #define SPACEVINE_LAYER 4.8 #define SPACEVINE_MOB_LAYER 4.9 //#define FLY_LAYER 5 //For easy recordkeeping; this is a byond define +#define RIPPLE_LAYER 5.1 #define GHOST_LAYER 6 #define AREA_LAYER 10 diff --git a/code/__DEFINES/shuttles.dm b/code/__DEFINES/shuttles.dm index 9fbd05691e1..7fbaf6d8c9c 100644 --- a/code/__DEFINES/shuttles.dm +++ b/code/__DEFINES/shuttles.dm @@ -25,3 +25,7 @@ #define UNLAUNCHED 0 #define ENDGAME_LAUNCHED 1 #define EARLY_LAUNCHED 2 + +// Ripples, effects that signal a shuttle's arrival +#define SHUTTLE_RIPPLE_TIME 100 +#define SHUTTLE_RIPPLE_FADEIN 50 diff --git a/code/modules/shuttle/emergency.dm b/code/modules/shuttle/emergency.dm index ff9439ecfba..9c93968aced 100644 --- a/code/modules/shuttle/emergency.dm +++ b/code/modules/shuttle/emergency.dm @@ -259,8 +259,18 @@ /obj/docking_port/mobile/emergency/check() if(!timer) return - var/time_left = timeLeft(1) + + // The emergency shuttle doesn't work like others so this + // ripple check is slightly different + if(!ripples.len && (time_left <= SHUTTLE_RIPPLE_TIME) && ((mode == SHUTTLE_CALL) || (mode == SHUTTLE_ESCAPE))) + var/destination + if(mode == SHUTTLE_CALL) + destination = SSshuttle.getDock("emergency_home") + else if(mode == SHUTTLE_ESCAPE) + destination = SSshuttle.getDock("emergency_away") + create_ripples(destination) + switch(mode) if(SHUTTLE_RECALL) if(time_left <= 0) diff --git a/code/modules/shuttle/ripple.dm b/code/modules/shuttle/ripple.dm new file mode 100644 index 00000000000..a2a0947d5c3 --- /dev/null +++ b/code/modules/shuttle/ripple.dm @@ -0,0 +1,20 @@ +/obj/effect/ripple + name = "hyperspace ripple" + desc = "Something is coming through hyperspace, you can see the \ + visual disturbances. It's probably best not to be on top of these \ + when whatever is tunneling comes through." + icon = 'icons/effects/effects.dmi' + icon_state = "medi_holo" + anchored = TRUE + density = FALSE + layer = RIPPLE_LAYER + alpha = 0 + +/obj/effect/ripple/New() + . = ..() + animate(src, alpha=255, time=SHUTTLE_RIPPLE_TIME) + // In case something goes wrong, delete us in a bit + addtimer(src, "delself", 3 * SHUTTLE_RIPPLE_TIME, FALSE) + +/obj/effect/ripple/proc/delself() + qdel(src) diff --git a/code/modules/shuttle/shuttle.dm b/code/modules/shuttle/shuttle.dm index 147c9f37444..5caccb742d3 100644 --- a/code/modules/shuttle/shuttle.dm +++ b/code/modules/shuttle/shuttle.dm @@ -189,6 +189,8 @@ // All shuttle templates are timid var/timid = FALSE + var/list/ripples = list() + /obj/docking_port/mobile/New() ..() if(!timid) @@ -296,6 +298,10 @@ /obj/docking_port/mobile/proc/cancel() if(mode != SHUTTLE_CALL) return + if(ripples.len) + for(var/i in ripples) + qdel(i) + ripples.Cut() timer = world.time - timeLeft(1) mode = SHUTTLE_RECALL @@ -365,6 +371,28 @@ qdel(src, force=TRUE) +/obj/docking_port/mobile/proc/create_ripples(obj/docking_port/stationary/S1) + var/list/turfs = ripple_area(S1) + for(var/i in turfs) + ripples += new /obj/effect/ripple(i) + +/obj/docking_port/mobile/proc/ripple_area(obj/docking_port/stationary/S1) + var/list/L0 = return_ordered_turfs(x, y, z, dir, areaInstance) + var/list/L1 = return_ordered_turfs(S1.x, S1.y, S1.z, S1.dir) + + var/list/ripple_turfs = list() + + for(var/i in 1 to L0.len) + var/turf/T0 = L0[i] + if(!T0) + continue + var/turf/T1 = L1[i] + if(!T1) + continue + if(T0.type != T0.baseturf) + ripple_turfs += T1 + + return ripple_turfs //this is the main proc. It instantly moves our mobile port to stationary port S1 //it handles all the generic behaviour, such as sanity checks, closing doors on the shuttle, stunning mobs, etc /obj/docking_port/mobile/proc/dock(obj/docking_port/stationary/S1, force=FALSE) @@ -374,11 +402,9 @@ if(status == SHUTTLE_ALREADY_DOCKED) return status else if(status) - spawn(0) - var/msg = "dock(): shuttle [src] cannot dock at [S1], \ - error: [status]" - message_admins(msg) - throw EXCEPTION(msg) + var/msg = "dock(): shuttle [src] cannot dock at [S1], \ + error: [status]" + message_admins(msg) return status if(canMove()) @@ -416,9 +442,14 @@ A0.contents += T0 //move or squish anything in the way ship at destination - roadkill(L1, S1.dir) + roadkill(L0, L1, S1.dir) - for(var/i=1, i<=L0.len, ++i) + // Removes ripples + for(var/i in ripples) + qdel(i) + ripples.Cut() + + for(var/i in 1 to L0.len) var/turf/T0 = L0[i] if(!T0) continue @@ -475,8 +506,7 @@ . = ..() if(!.) return - spawn(0) - close() + addtimer(src, "close", 0) /mob/onShuttleMove() if(!move_on_shuttle) @@ -545,13 +575,20 @@ if(T) var/obj/machinery/door/Door = locate() in T if(Door) - spawn(0) - Door.close() + addtimer(Door, "close", 0) -/obj/docking_port/mobile/proc/roadkill(list/L, dir, x, y) +/obj/docking_port/mobile/proc/roadkill(list/L0, list/L1, dir) var/list/hurt_mobs = list() - for(var/turf/T in L) - for(var/atom/movable/AM in T) + for(var/i in 1 to L0.len) + var/turf/T0 = L0[i] + var/turf/T1 = L1[i] + if(!T0 || !T1) + continue + if(T0.type == T0.baseturf) + continue + // The corresponding tile will not be changed, so no roadkill + + for(var/atom/movable/AM in T1) if(isliving(AM) && (!(AM in hurt_mobs))) hurt_mobs |= AM var/mob/living/M = AM @@ -561,7 +598,7 @@ M.pulledby.stop_pulling() M.stop_pulling() M.visible_message("[M] is hit by \ - a bluespace ripple[M.anchored ? "":" and is thrown clear"]!", + a hyperspace ripple[M.anchored ? "":" and is thrown clear"]!", "You feel an immense \ crushing pressure as the space around you ripples.") if(M.anchored) @@ -597,6 +634,9 @@ //used by shuttle subsystem to check timers /obj/docking_port/mobile/proc/check() var/timeLeft = timeLeft(1) + if(!ripples.len && (timeLeft <= SHUTTLE_RIPPLE_TIME) && ((mode == SHUTTLE_CALL) || (mode == SHUTTLE_RECALL))) + create_ripples(destination) + if(timeLeft <= 0) switch(mode) if(SHUTTLE_CALL) diff --git a/tgstation.dme b/tgstation.dme index 37d6a5bf53f..05db1566206 100644 --- a/tgstation.dme +++ b/tgstation.dme @@ -1699,6 +1699,7 @@ #include "code\modules\shuttle\emergency.dm" #include "code\modules\shuttle\ferry.dm" #include "code\modules\shuttle\manipulator.dm" +#include "code\modules\shuttle\ripple.dm" #include "code\modules\shuttle\shuttle.dm" #include "code\modules\shuttle\special.dm" #include "code\modules\shuttle\supply.dm"