diff --git a/code/game/objects/effects/spawners/lootdrop.dm b/code/game/objects/effects/spawners/lootdrop.dm index 4dcd2cbdd32..f8abaa7a17e 100644 --- a/code/game/objects/effects/spawners/lootdrop.dm +++ b/code/game/objects/effects/spawners/lootdrop.dm @@ -348,8 +348,8 @@ return var/lootspawn = pickweight(loot) var/obj/vehicle/V = new lootspawn(get_turf(src)) - if(V.keytype) - new V.keytype(get_turf(src)) + if(V.key_type) + new V.key_type(get_turf(src)) qdel(src) diff --git a/code/modules/mining/lavaland/loot/tendril_loot.dm b/code/modules/mining/lavaland/loot/tendril_loot.dm index e5a2c94fa7d..ad936c35bf3 100644 --- a/code/modules/mining/lavaland/loot/tendril_loot.dm +++ b/code/modules/mining/lavaland/loot/tendril_loot.dm @@ -163,7 +163,7 @@ desc = "A boat used for traversing lava." icon_state = "goliath_boat" icon = 'icons/obj/lavaland/dragonboat.dmi' - keytype = /obj/item/oar + held_key_type = /obj/item/oar burn_state = LAVA_PROOF /obj/vehicle/lavaboat/relaymove(mob/user, direction) @@ -174,7 +174,7 @@ ..() else to_chat(user, "Boats don't go on land!") - return 0 + return FALSE /obj/item/oar name = "oar" @@ -218,7 +218,7 @@ /obj/vehicle/lavaboat/dragon name = "mysterious boat" desc = "This boat moves where you will it, without the need for an oar." - keytype = null + held_key_type = null icon_state = "dragon_boat" generic_pixel_y = 2 generic_pixel_x = 1 diff --git a/code/modules/research/xenobiology/xenobiology.dm b/code/modules/research/xenobiology/xenobiology.dm index f7798df7892..eacbd00ee5d 100644 --- a/code/modules/research/xenobiology/xenobiology.dm +++ b/code/modules/research/xenobiology/xenobiology.dm @@ -354,19 +354,31 @@ icon_state = "bottle3" origin_tech = "biotech=5" -/obj/item/slimepotion/speed/afterattack(obj/item/C, mob/user, proximity_flag) +/obj/item/slimepotion/speed/afterattack(obj/O, mob/user, proximity_flag) if(!proximity_flag) return ..() - if(!istype(C)) - to_chat(user, "The potion can only be used on items!") + if(!istype(O)) + to_chat(user, "The potion can only be used on items or vehicles!") return - if(C.slowdown <= 0) - to_chat(user, "[C] can't be made any faster!") - return..() - to_chat(user, "You slather the red gunk over [C], making it faster.") - C.color = "#FF0000" - C.slowdown = 0 + if(isitem(O)) + var/obj/item/I = O + if(I.slowdown <= 0) + to_chat(user, "[I] can't be made any faster!") + return ..() + I.slowdown = 0 + + if(istype(O, /obj/vehicle)) + var/obj/vehicle/V = O + var/vehicle_speed_mod = config.run_speed + if(V.vehicle_move_delay <= vehicle_speed_mod) + to_chat(user, "[V] can't be made any faster!") + return ..() + V.vehicle_move_delay = vehicle_speed_mod + + to_chat(user, "You slather the red gunk over [O], making it faster.") + O.remove_atom_colour(WASHABLE_COLOUR_PRIORITY) + O.add_atom_colour("#FF0000", FIXED_COLOUR_PRIORITY) qdel(src) /obj/item/slimepotion/speed/MouseDrop(obj/over_object) diff --git a/code/modules/vehicle/ambulance.dm b/code/modules/vehicle/ambulance.dm index 29fb4e0108f..7b4797c6fe3 100644 --- a/code/modules/vehicle/ambulance.dm +++ b/code/modules/vehicle/ambulance.dm @@ -2,12 +2,12 @@ name = "ambulance" desc = "This is what the paramedic uses to run over people they need to take to medbay." icon_state = "docwagon2" - keytype = /obj/item/key/ambulance + key_type = /obj/item/key/ambulance var/obj/structure/bed/amb_trolley/bed = null var/datum/action/ambulance_alarm/AA var/datum/looping_sound/ambulance_alarm/soundloop -/obj/vehicle/ambulance/New() +/obj/vehicle/ambulance/Initialize(mapload) . = ..() AA = new(src) soundloop = new(list(src), FALSE) diff --git a/code/modules/vehicle/atv.dm b/code/modules/vehicle/atv.dm index a78791fddea..bd81553dbd7 100644 --- a/code/modules/vehicle/atv.dm +++ b/code/modules/vehicle/atv.dm @@ -2,18 +2,16 @@ name = "all-terrain vehicle" desc = "An all-terrain vehicle built for traversing rough terrain with ease. One of the few old-earth technologies that are still relevant on most planet-bound outposts." icon = 'icons/vehicles/4wheeler.dmi' - icon_state = "fourwheel" - keytype = /obj/item/key + icon_state = "atv" + key_type = /obj/item/key generic_pixel_x = 0 generic_pixel_y = 4 vehicle_move_delay = 1 - var/static/image/atvcover = null + var/static/mutable_appearance/atvcover -/obj/vehicle/atv/New() - ..() - if(!atvcover) - atvcover = image("icons/vehicles/4wheeler.dmi", "4wheeler_north") - atvcover.layer = MOB_LAYER + 0.1 +/obj/vehicle/atv/Initialize(mapload) + . = ..() + atvcover = mutable_appearance(icon, atvcover, ABOVE_MOB_LAYER) /obj/vehicle/atv/post_buckle_mob(mob/living/M) add_overlay(atvcover) @@ -26,7 +24,7 @@ /obj/vehicle/atv/handle_vehicle_layer() if(dir == SOUTH) - layer = MOB_LAYER+0.1 + layer = ABOVE_MOB_LAYER else layer = OBJ_LAYER @@ -40,20 +38,20 @@ emp_vulnerable = 1 density = 0 -/obj/vehicle/atv/turret/New() - ..() +/obj/vehicle/atv/turret/Initialize(mapload) + . = ..() turret = new(loc) //turret.base = src /obj/vehicle/atv/turret/handle_vehicle_layer() if(dir == SOUTH) - layer = MOB_LAYER+0.1 + layer = ABOVE_MOB_LAYER else layer = OBJ_LAYER if(turret) if(dir == NORTH) - turret.layer = MOB_LAYER+0.1 + turret.layer = ABOVE_MOB_LAYER else turret.layer = OBJ_LAYER diff --git a/code/modules/vehicle/janicart.dm b/code/modules/vehicle/janicart.dm index 2445e983fd3..319d2338128 100644 --- a/code/modules/vehicle/janicart.dm +++ b/code/modules/vehicle/janicart.dm @@ -3,10 +3,13 @@ name = "janicart (pimpin' ride)" desc = "A brave janitor cyborg gave its life to produce such an amazing combination of speed and utility." icon_state = "pussywagon" - keytype = /obj/item/key/janitor - var/obj/item/storage/bag/trash/mybag = null - var/floorbuffer = 0 + key_type = /obj/item/key/janitor + var/obj/item/storage/bag/trash/mybag + var/floorbuffer = FALSE +/obj/vehicle/janicart/Destroy() + QDEL_NULL(mybag) + return ..() /obj/vehicle/janicart/handle_vehicle_offsets() ..() @@ -63,35 +66,34 @@ /obj/vehicle/janicart/attackby(obj/item/I, mob/user, params) if(istype(I, /obj/item/storage/bag/trash)) - if(keytype == /obj/item/key/janitor) - if(!user.drop_item()) - return - to_chat(user, "You hook the trashbag onto \the [name].") - I.loc = src - mybag = I - else if(istype(I, /obj/item/janiupgrade)) - if(keytype == /obj/item/key/janitor) - floorbuffer = 1 - qdel(I) - to_chat(user,"You upgrade \the [name] with the floor buffer.") - update_icon() - - ..() - + if(!user.drop_item()) + return + to_chat(user, "You hook [I] onto [src].") + I.forceMove(src) + mybag = I + update_icon() + return + if(istype(I, /obj/item/janiupgrade)) + floorbuffer = TRUE + qdel(I) + to_chat(user,"You upgrade [src] with [I].") + update_icon() + return + return ..() /obj/vehicle/janicart/update_icon() - overlays.Cut() + cut_overlays() if(mybag) - overlays += "cart_garbage" + add_overlay("cart_garbage") if(floorbuffer) - overlays += "cart_buffer" + add_overlay("cart_buffer") /obj/vehicle/janicart/attack_hand(mob/user) if(..()) - return 1 + return TRUE else if(mybag) - mybag.loc = get_turf(user) + mybag.forceMove(get_turf(user)) user.put_in_hands(mybag) mybag = null update_icon() \ No newline at end of file diff --git a/code/modules/vehicle/motorcycle.dm b/code/modules/vehicle/motorcycle.dm index a79f8e3fa12..ea165c1c8df 100644 --- a/code/modules/vehicle/motorcycle.dm +++ b/code/modules/vehicle/motorcycle.dm @@ -6,15 +6,11 @@ generic_pixel_x = 0 generic_pixel_y = 4 vehicle_move_delay = 1 - var/static/image/bikecover = null - - -/obj/vehicle/motorcycle/New() - ..() - if(!bikecover) - bikecover = image("icons/vehicles/motorcycle.dmi", "motorcycle_overlay_4d") - bikecover.layer = MOB_LAYER + 0.1 + var/mutable_appearance/bikecover +/obj/vehicle/motorcycle/Initialize(mapload) + . = ..() + bikecover = mutable_appearance(icon, "motorcycle_overlay_4d", ABOVE_MOB_LAYER) /obj/vehicle/motorcycle/post_buckle_mob(mob/living/M) add_overlay(bikecover) @@ -28,6 +24,6 @@ /obj/vehicle/motorcycle/handle_vehicle_layer() if(dir == SOUTH) - layer = MOB_LAYER+0.1 + layer = ABOVE_MOB_LAYER else layer = OBJ_LAYER \ No newline at end of file diff --git a/code/modules/vehicle/secway.dm b/code/modules/vehicle/secway.dm index 4f7c0bf9cb2..85117222247 100644 --- a/code/modules/vehicle/secway.dm +++ b/code/modules/vehicle/secway.dm @@ -2,9 +2,10 @@ name = "secway" desc = "A brave security cyborg gave its life to help you look like a complete tool." icon_state = "secway" - keytype = /obj/item/key/security + key_type = /obj/item/key/security generic_pixel_x = 0 generic_pixel_y = 4 + vehicle_move_delay = 1 /obj/item/key/security diff --git a/code/modules/vehicle/snowmobile.dm b/code/modules/vehicle/snowmobile.dm index 311eb48c699..c4b8d7aefba 100644 --- a/code/modules/vehicle/snowmobile.dm +++ b/code/modules/vehicle/snowmobile.dm @@ -3,7 +3,7 @@ desc = "Wheeeeeeeeeeee." icon = 'icons/obj/vehicles.dmi' icon_state = "snowmobile" - keytype = /obj/item/key/snowmobile + key_type = /obj/item/key/snowmobile generic_pixel_x = 0 generic_pixel_y = 4 diff --git a/code/modules/vehicle/speedbike.dm b/code/modules/vehicle/speedbike.dm index e1efe63bcbd..75e25c2c5e6 100644 --- a/code/modules/vehicle/speedbike.dm +++ b/code/modules/vehicle/speedbike.dm @@ -3,16 +3,14 @@ icon = 'icons/obj/bike.dmi' icon_state = "speedbike_blue" layer = MOB_LAYER - 0.1 - keytype = null vehicle_move_delay = 0 var/overlay_state = "cover_blue" - var/image/overlay = null + var/mutable_appearance/overlay -/obj/vehicle/space/speedbike/New() - ..() - overlay = image("icons/obj/bike.dmi", overlay_state) - overlay.layer = MOB_LAYER + 0.1 - overlays += overlay +/obj/vehicle/space/speedbike/Initialize(mapload) + . = ..() + overlay = mutable_appearance(icon, overlay_state, ABOVE_MOB_LAYER) + add_overlay(overlay) /obj/vehicle/space/speedbike/Move(newloc,move_dir) if(has_buckled_mobs()) diff --git a/code/modules/vehicle/sportscar.dm b/code/modules/vehicle/sportscar.dm index f52f4b77a92..0f9543d4811 100644 --- a/code/modules/vehicle/sportscar.dm +++ b/code/modules/vehicle/sportscar.dm @@ -6,14 +6,11 @@ generic_pixel_x = 0 generic_pixel_y = 4 vehicle_move_delay = 1 - var/static/image/carcover = null + var/mutable_appearance/carcover - -/obj/vehicle/car/New() - ..() - if(!carcover) - carcover = image("icons/vehicles/sportscar.dmi", "sportscar_cover") - carcover.layer = MOB_LAYER + 0.1 +/obj/vehicle/car/Initialize(mapload) + . = ..() + carcover = mutable_appearance(icon, "sportscar_cover", ABOVE_MOB_LAYER) /obj/vehicle/car/post_buckle_mob(mob/living/M) add_overlay(carcover) @@ -46,6 +43,6 @@ /obj/vehicle/car/handle_vehicle_layer() if(dir == SOUTH) - layer = MOB_LAYER+0.1 + layer = ABOVE_MOB_LAYER else layer = OBJ_LAYER \ No newline at end of file diff --git a/code/modules/vehicle/vehicle.dm b/code/modules/vehicle/vehicle.dm index 9b3a747b7ff..edc6dc63a2e 100644 --- a/code/modules/vehicle/vehicle.dm +++ b/code/modules/vehicle/vehicle.dm @@ -9,8 +9,12 @@ can_buckle = TRUE buckle_lying = FALSE armor = list("melee" = 30, "bullet" = 30, "laser" = 30, "energy" = 0, "bomb" = 30, "bio" = 0, "rad" = 0) - var/keytype = null //item typepath, if non-null an item of this type is needed in your hands to drive this vehicle - var/next_vehicle_move = 0 //used for move delays + var/key_type + var/held_key_type //Similar to above, but the vehicle needs the key in hands as opposed to inserted into the ignition + var/obj/item/key/inserted_key + var/key_type_exact = TRUE //can subtypes work + var/last_vehicle_move = 0 //used for move delays + var/last_move_diagonal = FALSE var/vehicle_move_delay = 2 //tick delay between movements, lower = faster, higher = slower var/auto_door_open = TRUE var/needs_gravity = 0 //To allow non-space vehicles to move in no gravity or not, mostly for adminbus @@ -20,10 +24,56 @@ var/spaceworthy = FALSE -/obj/vehicle/New() - ..() +/obj/vehicle/Initialize(mapload) + . = ..() handle_vehicle_layer() +/obj/vehicle/Destroy() + QDEL_NULL(inserted_key) + return ..() + +/obj/vehicle/examine(mob/user) + . = ..() + if(key_type) + if(!inserted_key) + . += "Put a key inside it by clicking it with the key." + else + . += "Alt-click [src] to remove the key." + +/obj/vehicle/attackby(obj/item/I, mob/user, params) + if(key_type && !is_key(inserted_key) && is_key(I)) + if(user.drop_item()) + I.forceMove(src) + to_chat(user, "You insert [I] into [src].") + if(inserted_key) //just in case there's an invalid key + inserted_key.forceMove(drop_location()) + inserted_key = I + else + to_chat(user, "[I] seems to be stuck to your hand!") + return + return ..() + +/obj/vehicle/AltClick(mob/user) + if(inserted_key && user.Adjacent(user)) + if(!(user in buckled_mobs)) + to_chat(user, "You must be riding [src] to remove [src]'s key!") + return + to_chat(user, "You remove [inserted_key] from [src].") + inserted_key.forceMove(drop_location()) + user.put_in_hands(inserted_key) + inserted_key = null + return ..() + +/obj/vehicle/proc/is_key(obj/item/I) + return I ? (key_type_exact ? (I.type == key_type) : istype(I, key_type)) : FALSE + +/obj/vehicle/proc/held_keycheck(mob/user) + if(held_key_type) + if(istype(user.l_hand, held_key_type) || istype(user.r_hand, held_key_type)) + return TRUE + else + return TRUE + return FALSE //APPEARANCE /obj/vehicle/proc/handle_vehicle_layer() @@ -49,15 +99,6 @@ return -//KEYS -/obj/vehicle/proc/keycheck(mob/user) - if(keytype) - if(istype(user.l_hand, keytype) || istype(user.r_hand, keytype)) - return TRUE - else - return TRUE - return FALSE - /obj/item/key name = "key" desc = "A small grey key." @@ -93,25 +134,30 @@ //MOVEMENT /obj/vehicle/relaymove(mob/user, direction) + if(key_type && !is_key(inserted_key)) + to_chat(user, "[src] has no key inserted!") + return + if(user.incapacitated()) unbuckle_mob(user) return - if(world.time < next_vehicle_move) + if(world.time < last_vehicle_move + ((last_move_diagonal? 2 : 1) * (vehicle_move_delay + config.human_delay))) return - next_vehicle_move = world.time + vehicle_move_delay - if(keycheck(user)) + last_vehicle_move = world.time + + if(held_keycheck(user)) + var/turf/next = get_step(src, direction) if(!Process_Spacemove(direction) || !isturf(loc)) return step(src, direction) - if(has_buckled_mobs()) - for(var/m in buckled_mobs) - var/mob/living/buckled_mob = m - if(buckled_mob.loc != loc) - buckled_mob.buckled = null //Temporary, so Move() succeeds. - buckled_mob.buckled = src //Restoring + if((direction & (direction - 1)) && (loc == next)) //moved diagonally + last_move_diagonal = TRUE + else + last_move_diagonal = FALSE + if(has_buckled_mobs()) if(issimulatedturf(loc)) var/turf/simulated/T = loc if(T.wet == TURF_WET_LUBE) //Lube! Fall off! @@ -125,20 +171,15 @@ handle_vehicle_layer() handle_vehicle_offsets() else - to_chat(user, "You'll need the keys in one of your hands to drive \the [name].") + to_chat(user, "You'll need the keys in one of your hands to drive [src].") -/obj/vehicle/Move(NewLoc,Dir=0,step_x=0,step_y=0) +/obj/vehicle/Move(NewLoc, Dir = 0, step_x = 0, step_y = 0) . = ..() handle_vehicle_layer() handle_vehicle_offsets() -/obj/vehicle/attackby(obj/item/I, mob/user, params) - if(keytype && istype(I, keytype)) - to_chat(user, "Hold [I] in one of your hands while you drive \the [name].") - - /obj/vehicle/Bump(atom/movable/M) if(!spaceworthy && isspaceturf(get_turf(src))) return FALSE diff --git a/icons/vehicles/4wheeler.dmi b/icons/vehicles/4wheeler.dmi index 0378b865fd3..e1bfd5e18fd 100644 Binary files a/icons/vehicles/4wheeler.dmi and b/icons/vehicles/4wheeler.dmi differ