From c17d8edaa627981e1597339f0669558f4b87f77e Mon Sep 17 00:00:00 2001 From: Doubleumc Date: Sat, 28 Oct 2023 03:53:28 -0400 Subject: [PATCH] Vehicle lights (#31) Co-authored-by: Morrow --- code/datums/components/overlay_lighting.dm | 56 +++++++++++++++++- code/modules/vehicles/apc/apc.dm | 2 + code/modules/vehicles/multitile/multitile.dm | 45 ++++++--------- .../multitile/multitile_interaction.dm | 57 +++++++++++-------- code/modules/vehicles/tank/tank.dm | 2 +- code/modules/vehicles/van/van.dm | 3 +- 6 files changed, 108 insertions(+), 57 deletions(-) diff --git a/code/datums/components/overlay_lighting.dm b/code/datums/components/overlay_lighting.dm index 00a5e86b5d..e14066ffb7 100644 --- a/code/datums/components/overlay_lighting.dm +++ b/code/datums/components/overlay_lighting.dm @@ -74,6 +74,8 @@ ///Cast range for the directional cast (how far away the atom is moved) var/cast_range = 2 + var/base_offset + /datum/component/overlay_lighting/Initialize(_range, _power, _color, starts_on, is_directional) if(!ismovable(parent)) @@ -191,6 +193,9 @@ return if(directional) cast_directional_light() + else if(length(current_holder?.locs) > 1) + handle_multitile_light() + get_new_turfs() @@ -335,9 +340,9 @@ if(pixel_bounds == 32) visible_mask.transform = null return - var/offset = (pixel_bounds - 32) * 0.5 + base_offset = (pixel_bounds - 32) * 0.5 var/matrix/transform = new - transform.Translate(-offset, -offset) + transform.Translate(-base_offset, -base_offset) visible_mask.transform = transform directional_offset_x = 0 directional_offset_y = 0 @@ -419,6 +424,8 @@ add_dynamic_lumi(current_holder) if(directional) cast_directional_light() + else if(length(current_holder?.locs) > 1) + handle_multitile_light() if(current_holder && current_holder != parent && current_holder != parent_attached_to) RegisterSignal(current_holder, COMSIG_MOVABLE_MOVED, PROC_REF(on_holder_moved)) get_new_turfs() @@ -462,6 +469,7 @@ scanning = next_turf current_holder.underlays -= visible_mask + current_holder.underlays -= cone var/translate_x = -((range - 1) * 32) var/translate_y = translate_x @@ -474,14 +482,58 @@ translate_x += 32 * final_distance if(WEST) translate_x += -32 * final_distance + + var/multitile_light = length(current_holder?.locs) > 1 + var/multitile_translate_x = 0 + var/multitile_translate_y = 0 + + if(multitile_light) + switch(current_direction) + if(NORTH) + multitile_translate_x += current_holder.bound_width * 0.5 + multitile_translate_y += current_holder.bound_height + if(SOUTH) + multitile_translate_x += current_holder.bound_width * 0.5 + if(EAST) + multitile_translate_x += current_holder.bound_width + multitile_translate_y += current_holder.bound_height * 0.5 + if(WEST) + multitile_translate_y += current_holder.bound_height * 0.5 + + translate_x += multitile_translate_x + translate_y += multitile_translate_y + if((directional_offset_x != translate_x) || (directional_offset_y != translate_y)) directional_offset_x = translate_x directional_offset_y = translate_y var/matrix/transform = matrix() transform.Translate(translate_x, translate_y) visible_mask.transform = transform + if(multitile_light) + var/matrix/cone_transform = matrix() + cone_transform.Translate(multitile_translate_x - 32, multitile_translate_y - 32) + cone.transform = cone_transform if(overlay_lighting_flags & LIGHTING_ON) current_holder.underlays += visible_mask + current_holder.underlays += cone + +/datum/component/overlay_lighting/proc/handle_multitile_light() + var/multitile_translate_x = 0 + var/multitile_translate_y = 0 + switch(current_holder.dir) + if(NORTH, SOUTH) + multitile_translate_x = current_holder.bound_width * 0.5 + multitile_translate_y = current_holder.bound_height * 0.5 + if(EAST, WEST) + multitile_translate_x = current_holder.bound_height * 0.5 + multitile_translate_y = current_holder.bound_width * 0.5 + if(current_holder && overlay_lighting_flags & LIGHTING_ON) + current_holder.underlays -= visible_mask + var/matrix/transform = new + transform.Translate(multitile_translate_x - base_offset, multitile_translate_y - base_offset) + visible_mask.transform = transform + if(current_holder && overlay_lighting_flags & LIGHTING_ON) + current_holder.underlays += visible_mask ///Called when current_holder changes loc. /datum/component/overlay_lighting/proc/on_holder_dir_change(atom/movable/source, olddir, newdir) diff --git a/code/modules/vehicles/apc/apc.dm b/code/modules/vehicles/apc/apc.dm index 60d21f7090..55e2cf2d11 100644 --- a/code/modules/vehicles/apc/apc.dm +++ b/code/modules/vehicles/apc/apc.dm @@ -34,6 +34,8 @@ GLOBAL_LIST_EMPTY(command_apc_list) movement_sound = 'sound/vehicles/tank_driving.ogg' + light_range = 4 + var/gunner_view_buff = 10 hardpoints_allowed = list( diff --git a/code/modules/vehicles/multitile/multitile.dm b/code/modules/vehicles/multitile/multitile.dm index 9e4d2c9d29..148af24e0d 100644 --- a/code/modules/vehicles/multitile/multitile.dm +++ b/code/modules/vehicles/multitile/multitile.dm @@ -21,11 +21,13 @@ can_buckle = FALSE + //Vehicle self-illumination light_system = MOVABLE_LIGHT light_range = 5 + light_power = 2 - var/atom/movable/vehicle_light_holder/lighting_holder - + //Vehicle headlights + var/atom/movable/vehicle_light/light_holder var/vehicle_light_range = 5 var/vehicle_light_power = 2 @@ -176,15 +178,13 @@ rotate_bounds(angle_to_turn) if(bound_width > world.icon_size || bound_height > world.icon_size) - lighting_holder = new(src) - lighting_holder.set_light_range(vehicle_light_range) - lighting_holder.set_light_power(vehicle_light_power) - lighting_holder.set_light_on(vehicle_light_range || vehicle_light_power) - else if(light_range) - set_light_on(TRUE) + light_holder = new(src) + light_holder.set_light_flags(LIGHT_ATTACHED) + light_holder.set_light_range(vehicle_light_range) + light_holder.set_light_power(vehicle_light_power) + light_holder.set_light_on(vehicle_light_range && vehicle_light_power) - light_pixel_x = -bound_x - light_pixel_y = -bound_y + set_light_on(light_range && light_power) healthcheck() update_icon() @@ -209,6 +209,8 @@ return /obj/vehicle/multitile/Destroy() + QDEL_NULL(light_holder) + if(!QDELETED(interior)) QDEL_NULL(interior) @@ -383,8 +385,9 @@ handle_all_modules_broken() //vehicle is dead, no more lights - if(health <= 0 && lighting_holder.light_range) - lighting_holder.set_light_on(FALSE) + if(health <= 0 && light_holder.light_range) + set_light_on(FALSE) + light_holder.set_light_on(FALSE) update_icon() /* @@ -441,19 +444,5 @@ for(var/obj/item/hardpoint/locomotion/Loco in hardpoints) Loco.handle_acid_damage(A) -/atom/movable/vehicle_light_holder - light_system = MOVABLE_LIGHT - mouse_opacity = MOUSE_OPACITY_TRANSPARENT - -/atom/movable/vehicle_light_holder/Initialize(mapload, ...) - . = ..() - - var/atom/attached_to = loc - - forceMove(attached_to.loc) - RegisterSignal(attached_to, COMSIG_MOVABLE_MOVED, PROC_REF(handle_parent_move)) - -/atom/movable/vehicle_light_holder/proc/handle_parent_move(atom/movable/mover, atom/oldloc, direction) - SIGNAL_HANDLER - - forceMove(get_turf(mover)) +/atom/movable/vehicle_light + light_system = DIRECTIONAL_LIGHT diff --git a/code/modules/vehicles/multitile/multitile_interaction.dm b/code/modules/vehicles/multitile/multitile_interaction.dm index 42b141327b..c4f1ed2d3d 100644 --- a/code/modules/vehicles/multitile/multitile_interaction.dm +++ b/code/modules/vehicles/multitile/multitile_interaction.dm @@ -134,22 +134,23 @@ take_damage_type(O.force * 0.05, "blunt", user) //Melee weapons from people do very little damage // Frame repairs on the vehicle itself -/obj/vehicle/multitile/proc/handle_repairs(obj/item/O, mob/user) +/obj/vehicle/multitile/proc/handle_repairs(obj/item/repairing_item, mob/user) if(user.action_busy) return + var/max_hp = initial(health) if(health > max_hp) health = max_hp to_chat(user, SPAN_NOTICE("The hull is fully intact.")) for(var/obj/item/hardpoint/holder/H in hardpoints) if(H.health > 0) - if(!iswelder(O)) - to_chat(user, SPAN_WARNING("You need welding tool to repair \the [H.name].")) + if(!iswelder(repairing_item)) + to_chat(user, SPAN_WARNING("You need welding tool to repair [H.name].")) return - if(!HAS_TRAIT(O, TRAIT_TOOL_BLOWTORCH)) + if(!HAS_TRAIT(repairing_item, TRAIT_TOOL_BLOWTORCH)) to_chat(user, SPAN_WARNING("You need a stronger blowtorch!")) return - H.handle_repair(O, user) + H.handle_repair(repairing_item, user) update_icon() return else @@ -158,25 +159,25 @@ var/repair_message = "welding structural struts back in place" var/sound_file = 'sound/items/weldingtool_weld.ogg' - var/obj/item/tool/weldingtool/WT + var/obj/item/tool/weldingtool/welder // For health < 75%, the frame needs welderwork, otherwise wrench if(health < max_hp * 0.75) - if(!iswelder(O)) + if(!iswelder(repairing_item)) to_chat(user, SPAN_NOTICE("The frame is way too busted! Try using a [SPAN_HELPFUL("welder")].")) return - if(!HAS_TRAIT(O, TRAIT_TOOL_BLOWTORCH)) + if(!HAS_TRAIT(repairing_item, TRAIT_TOOL_BLOWTORCH)) to_chat(user, SPAN_NOTICE("You need a more powerful blowtorch!")) return - WT = O - if(!WT.isOn()) - to_chat(user, SPAN_WARNING("\The [WT] needs to be on!")) + welder = repairing_item + if(!welder.isOn()) + to_chat(user, SPAN_WARNING("[welder] needs to be on!")) return else - if(!HAS_TRAIT(O, TRAIT_TOOL_WRENCH)) + if(!HAS_TRAIT(repairing_item, TRAIT_TOOL_WRENCH)) to_chat(user, SPAN_NOTICE("The frame is structurally sound, but there are a lot of loose nuts and bolts. Try using a [SPAN_HELPFUL("wrench")].")) return @@ -184,7 +185,7 @@ sound_file = 'sound/items/Ratchet.ogg' var/amount_fixed_adjustment = user.get_skill_duration_multiplier(SKILL_ENGINEER) - user.visible_message(SPAN_WARNING("[user] [repair_message] on \the [src]."), SPAN_NOTICE("You begin [repair_message] on \the [src].")) + user.visible_message(SPAN_WARNING("[user] [repair_message] on [src]."), SPAN_NOTICE("You begin [repair_message] on [src].")) playsound(get_turf(user), sound_file, 25) while(health < max_hp) @@ -192,27 +193,33 @@ playsound(get_turf(user), sound_file, 25) if(!do_after(user, 1 SECONDS, INTERRUPT_ALL, BUSY_ICON_BUILD)) - user.visible_message(SPAN_WARNING("[user] stops [repair_message] on \the [src]."), SPAN_NOTICE("You stop [repair_message] on \the [src]. Hull integrity is at [SPAN_HELPFUL(100.0*health/max_hp)]%.")) + user.visible_message(SPAN_WARNING("[user] stops [repair_message] on [src]."), SPAN_NOTICE("You stop [repair_message] on [src]. Hull integrity is at [SPAN_HELPFUL(100.0*health/max_hp)]%.")) return health = min(health + max_hp/100 * (5 / amount_fixed_adjustment), max_hp) - - if(WT) - WT.remove_fuel(1, user) - if(WT.get_fuel() < 1) - user.visible_message(SPAN_WARNING("[user] stops [repair_message] on \the [src]."), SPAN_NOTICE("You stop [repair_message] on \the [src]. Hull integrity is at [SPAN_HELPFUL(100.0*health/max_hp)]%.")) - return - if(health >= max_hp * 0.75) - user.visible_message(SPAN_WARNING("[user] finishes [repair_message] on \the [src]."), SPAN_NOTICE("You finish [repair_message] on \the [src]. The frame is structurally sound now, but there are a lot of loose nuts and bolts. Try using a [SPAN_HELPFUL("wrench")].")) - return + if(health >= max_hp * 0.50) + set_light_on(vehicle_light_range && vehicle_light_power) + light_holder.set_light_on(vehicle_light_range && vehicle_light_power) + to_chat(user, SPAN_NOTICE("[src]'s lights flicker to life!")) to_chat(user, SPAN_NOTICE("Hull integrity is at [SPAN_HELPFUL(100.0*health/max_hp)]%.")) + if(!welder) + continue + + welder.remove_fuel(1, user) + if(welder.get_fuel() < 1) + user.visible_message(SPAN_WARNING("[user] stops [repair_message] on [src]."), SPAN_NOTICE("You stop [repair_message] on [src]. Hull integrity is at [SPAN_HELPFUL(100.0*health/max_hp)]%.")) + return + if(health >= max_hp * 0.75) + user.visible_message(SPAN_WARNING("[user] finishes [repair_message] on [src]."), SPAN_NOTICE("You finish [repair_message] on [src]. The frame is structurally sound now, but there are a lot of loose nuts and bolts. Try using a [SPAN_HELPFUL("wrench")].")) + return + health = initial(health) - lighting_holder.set_light_range(vehicle_light_range) + toggle_cameras_status(TRUE) update_icon() - user.visible_message(SPAN_NOTICE("[user] finishes [repair_message] on \the [src]."), SPAN_NOTICE("You finish [repair_message] on \the [src]. Hull integrity is at [SPAN_HELPFUL(100.0*health/max_hp)]%. ")) + user.visible_message(SPAN_NOTICE("[user] finishes [repair_message] on [src]."), SPAN_NOTICE("You finish [repair_message] on [src]. Hull integrity is at [SPAN_HELPFUL(100.0*health/max_hp)]%. ")) return //Special case for entering the vehicle without using the verb diff --git a/code/modules/vehicles/tank/tank.dm b/code/modules/vehicles/tank/tank.dm index ad69f80cdf..87f17458aa 100644 --- a/code/modules/vehicles/tank/tank.dm +++ b/code/modules/vehicles/tank/tank.dm @@ -36,7 +36,7 @@ move_momentum_build_factor = 1.8 move_turn_momentum_loss_factor = 0.6 - vehicle_light_range = 7 + light_range = 4 // Rest (all the guns) is handled by the tank turret hardpoint hardpoints_allowed = list( diff --git a/code/modules/vehicles/van/van.dm b/code/modules/vehicles/van/van.dm index fdb2f397bb..5969b73957 100644 --- a/code/modules/vehicles/van/van.dm +++ b/code/modules/vehicles/van/van.dm @@ -41,7 +41,8 @@ movement_sound = 'sound/vehicles/tank_driving.ogg' honk_sound = 'sound/vehicles/honk_2_truck.ogg' - vehicle_light_range = 8 + light_range = 3 + vehicle_light_range = 6 move_max_momentum = 3