mirror of
https://github.com/CHOMPStation2/CHOMPStation2.git
synced 2025-12-10 10:12:45 +00:00
Merge pull request #9867 from VOREStation/upstream-merge-7928
[MIRROR] Added a GPS compass.
This commit is contained in:
committed by
Chompstation Bot
parent
4dafc3196e
commit
1d0ca9dd1e
@@ -1277,6 +1277,10 @@ var/list/WALLITEMS = list(
|
||||
colour += temp_col
|
||||
return colour
|
||||
|
||||
/proc/color_square(red, green, blue, hex)
|
||||
var/color = hex ? hex : "#[num2hex(red, 2)][num2hex(green, 2)][num2hex(blue, 2)]"
|
||||
return "<span style='font-face: fixedsys; font-size: 14px; background-color: [color]; color: [color]'>___</span>"
|
||||
|
||||
var/mob/dview/dview_mob = new
|
||||
|
||||
//Version of view() which ignores darkness, because BYOND doesn't have it.
|
||||
|
||||
@@ -9,24 +9,119 @@ var/list/GPS_list = list()
|
||||
slot_flags = SLOT_BELT
|
||||
origin_tech = list(TECH_MATERIAL = 2, TECH_BLUESPACE = 2, TECH_MAGNET = 1)
|
||||
matter = list(DEFAULT_WALL_MATERIAL = 500)
|
||||
|
||||
var/gps_tag = "GEN0"
|
||||
var/emped = FALSE
|
||||
var/updating = TRUE // Lets users lock the UI so they don't have to deal with constantly shifting signals
|
||||
var/tracking = FALSE // Will not show other signals or emit its own signal if false.
|
||||
var/long_range = FALSE // If true, can see farther, depending on get_map_levels().
|
||||
var/local_mode = FALSE // If true, only GPS signals of the same Z level are shown.
|
||||
var/hide_signal = FALSE // If true, signal is not visible to other GPS devices.
|
||||
var/can_hide_signal = FALSE // If it can toggle the above var.
|
||||
|
||||
var/mob/holder
|
||||
var/is_in_processing_list = FALSE
|
||||
var/list/tracking_devices
|
||||
var/list/showing_tracked_names
|
||||
var/obj/compass_holder/compass
|
||||
|
||||
/obj/item/device/gps/Initialize()
|
||||
. = ..()
|
||||
compass = new(src)
|
||||
GPS_list += src
|
||||
name = "global positioning system ([gps_tag])"
|
||||
update_holder()
|
||||
update_icon()
|
||||
|
||||
/obj/item/device/gps/proc/check_visible_to_holder()
|
||||
. = (holder && (holder.get_active_hand() == src || holder.get_inactive_hand() == src))
|
||||
|
||||
/obj/item/device/gps/proc/update_holder()
|
||||
|
||||
if(holder && loc != holder)
|
||||
GLOB.moved_event.unregister(holder, src)
|
||||
GLOB.dir_set_event.unregister(holder, src)
|
||||
holder.client?.screen -= compass
|
||||
holder = null
|
||||
|
||||
if(istype(loc, /mob))
|
||||
holder = loc
|
||||
GLOB.moved_event.register(holder, src, .proc/update_compass)
|
||||
GLOB.dir_set_event.register(holder, src, .proc/update_compass)
|
||||
|
||||
if(holder && tracking)
|
||||
if(!is_in_processing_list)
|
||||
START_PROCESSING(SSobj, src)
|
||||
is_in_processing_list = TRUE
|
||||
if(holder.client)
|
||||
if(check_visible_to_holder())
|
||||
holder.client.screen |= compass
|
||||
else
|
||||
holder.client.screen -= compass
|
||||
else
|
||||
STOP_PROCESSING(SSobj, src)
|
||||
is_in_processing_list = FALSE
|
||||
if(holder?.client)
|
||||
holder.client.screen -= compass
|
||||
|
||||
/obj/item/device/gps/pickup()
|
||||
. = ..()
|
||||
update_holder()
|
||||
|
||||
/obj/item/device/gps/equipped()
|
||||
. = ..()
|
||||
update_holder()
|
||||
|
||||
/obj/item/device/gps/dropped()
|
||||
. = ..()
|
||||
update_holder()
|
||||
|
||||
/obj/item/device/gps/process()
|
||||
if(!tracking)
|
||||
is_in_processing_list = FALSE
|
||||
return PROCESS_KILL
|
||||
update_holder()
|
||||
if(holder)
|
||||
update_compass(TRUE)
|
||||
|
||||
/obj/item/device/gps/Destroy()
|
||||
STOP_PROCESSING(SSobj, src)
|
||||
is_in_processing_list = FALSE
|
||||
GPS_list -= src
|
||||
return ..()
|
||||
. = ..()
|
||||
update_holder()
|
||||
QDEL_NULL(compass)
|
||||
|
||||
/obj/item/device/gps/proc/can_track(var/obj/item/device/gps/other, var/reachable_z_levels)
|
||||
if(!other.tracking || other.emped || other.hide_signal)
|
||||
return FALSE
|
||||
var/turf/origin = get_turf(src)
|
||||
var/turf/target = get_turf(other)
|
||||
if(!istype(origin) || !istype(target))
|
||||
return FALSE
|
||||
if(origin.z == target.z)
|
||||
return TRUE
|
||||
if(local_mode)
|
||||
return FALSE
|
||||
reachable_z_levels = reachable_z_levels || using_map.get_map_levels(origin.z, long_range)
|
||||
return (target.z in reachable_z_levels)
|
||||
|
||||
/obj/item/device/gps/proc/update_compass(var/update_compass_icon)
|
||||
compass.hide_waypoints(FALSE)
|
||||
for(var/thing in tracking_devices)
|
||||
var/obj/item/device/gps/gps = locate(thing)
|
||||
if(!istype(gps) || QDELETED(gps))
|
||||
LAZYREMOVE(tracking_devices, thing)
|
||||
LAZYREMOVE(showing_tracked_names, thing)
|
||||
continue
|
||||
var/turf/gps_turf = get_turf(gps)
|
||||
var/gps_tag = LAZYACCESS(showing_tracked_names, thing) ? gps.gps_tag : null
|
||||
if(istype(gps_turf))
|
||||
compass.set_waypoint("\ref[gps]", gps_tag, gps_turf.x, gps_turf.y, gps_turf.z, LAZYACCESS(tracking_devices, "\ref[gps]"))
|
||||
else
|
||||
compass.set_waypoint("\ref[gps]", gps_tag, 0, 0, 0, LAZYACCESS(tracking_devices, "\ref[gps]"))
|
||||
if(can_track(gps))
|
||||
compass.show_waypoint("\ref[gps]")
|
||||
compass.rebuild_overlay_lists(update_compass_icon)
|
||||
|
||||
/obj/item/device/gps/AltClick(mob/user)
|
||||
toggletracking(user)
|
||||
@@ -37,13 +132,24 @@ var/list/GPS_list = list()
|
||||
if(emped)
|
||||
to_chat(user, "It's busted!")
|
||||
return
|
||||
|
||||
toggle_tracking()
|
||||
if(tracking)
|
||||
to_chat(user, "[src] is no longer tracking, or visible to other GPS devices.")
|
||||
tracking = FALSE
|
||||
update_icon()
|
||||
else
|
||||
to_chat(user, "[src] is now tracking, and visible to other GPS devices.")
|
||||
tracking = TRUE
|
||||
|
||||
/obj/item/device/gps/proc/toggle_tracking()
|
||||
tracking = !tracking
|
||||
if(tracking)
|
||||
if(!is_in_processing_list)
|
||||
is_in_processing_list = TRUE
|
||||
START_PROCESSING(SSobj, src)
|
||||
else
|
||||
is_in_processing_list = FALSE
|
||||
STOP_PROCESSING(SSobj, src)
|
||||
update_compass()
|
||||
update_holder()
|
||||
update_icon()
|
||||
|
||||
/obj/item/device/gps/emp_act(severity)
|
||||
@@ -67,11 +173,7 @@ var/list/GPS_list = list()
|
||||
add_overlay("working")
|
||||
|
||||
/obj/item/device/gps/attack_self(mob/user)
|
||||
tgui_interact(user)
|
||||
|
||||
/obj/item/device/gps/examine(mob/user)
|
||||
. = ..()
|
||||
. += display()
|
||||
display(user)
|
||||
|
||||
// Compiles all the data not available directly from the GPS
|
||||
// Like the positions and directions to all other GPS units
|
||||
@@ -90,15 +192,8 @@ var/list/GPS_list = list()
|
||||
dat["z_level_detection"] = using_map.get_map_levels(curr.z, long_range)
|
||||
|
||||
for(var/obj/item/device/gps/G in GPS_list - src)
|
||||
if(!G.tracking || G.emped || G.hide_signal)
|
||||
continue
|
||||
|
||||
var/turf/T = get_turf(G)
|
||||
if(!T)
|
||||
continue
|
||||
if(local_mode && curr.z != T.z)
|
||||
continue
|
||||
if(!(T.z in dat["z_level_detection"]))
|
||||
if(!can_track(G, dat["z_level_detection"]))
|
||||
continue
|
||||
|
||||
var/gps_data[0]
|
||||
@@ -108,6 +203,7 @@ var/list/GPS_list = list()
|
||||
var/area/A = get_area(G)
|
||||
gps_data["area_name"] = A.get_name()
|
||||
|
||||
var/turf/T = get_turf(G)
|
||||
gps_data["z_name"] = using_map.get_zlevel_name(T.z)
|
||||
gps_data["direction"] = get_adir(curr, T)
|
||||
gps_data["degrees"] = round(Get_Angle(curr,T))
|
||||
@@ -122,37 +218,102 @@ var/list/GPS_list = list()
|
||||
|
||||
return dat
|
||||
|
||||
/obj/item/device/gps/proc/display()
|
||||
if(!tracking)
|
||||
. = "The device is off. Alt-click it to turn it on."
|
||||
return
|
||||
/obj/item/device/gps/proc/display(mob/user)
|
||||
|
||||
if(emped)
|
||||
. = "It's busted!"
|
||||
to_chat(user, "It's busted!")
|
||||
return
|
||||
|
||||
var/list/dat = list()
|
||||
var/list/gps_data = display_list()
|
||||
|
||||
dat += "Current location: [gps_data["my_area_name"]] <b>([gps_data["curr_x"]], [gps_data["curr_y"]], [gps_data["curr_z_name"]])</b>"
|
||||
dat += "[hide_signal ? "Tagged" : "Broadcasting"] as '[gps_tag]'. <a href='?src=\ref[src];tag=1'>\[Change Tag\]</a> \
|
||||
<a href='?src=\ref[src];range=1'>\[Toggle Scan Range\]</a> \
|
||||
[can_hide_signal ? "<a href='?src=\ref[src];hide=1'>\[Toggle Signal Visibility\]</a>":""]"
|
||||
dat += "<table width = '100%'>"
|
||||
if(!tracking)
|
||||
dat += "<tr><td colspan = 6></td><a href='?src=\ref[src];toggle_power=1'>\[Switch On]\]</a></tr>"
|
||||
else
|
||||
dat += "<tr><td colspan = 6></td><a href='?src=\ref[src];toggle_power=1'>\[Switch Off]\]</a></tr>"
|
||||
dat += "<tr><td colspan = 2><b>Current location</b></td><td colspan = 2>[gps_data["my_area_name"]]</td><td colspan = 2><b>([gps_data["curr_x"]], [gps_data["curr_y"]], [gps_data["curr_z_name"]])</b></td></tr>"
|
||||
dat += "<tr><td colspan = 4>[hide_signal ? "Tagged" : "Broadcasting"] as '[gps_tag]'.</td>"
|
||||
dat += "<td><a href='?src=\ref[src];tag=1'>\[Change Tag\]</a><a href='?src=\ref[src];range=1'>\[Toggle Scan Range\]</a>[can_hide_signal ? "<a href='?src=\ref[src];hide=1'>\[Toggle Signal Visibility\]</a>":""]</td></tr>"
|
||||
|
||||
if(gps_data["gps_list"].len)
|
||||
dat += "Detected signals;"
|
||||
dat += "<tr><td colspan = 6><b>Detected signals</b></td></tr>"
|
||||
for(var/gps in gps_data["gps_list"])
|
||||
if(istype(gps_data["ref"], /obj/item/device/gps/internal/poi))
|
||||
dat += " [gps["gps_tag"]]: [gps["area_name"]] - [gps["local"] ? "[gps["direction"]] Dist: [round(gps["distance"], 10)]m" : "in \the [gps["z_name"]]"]"
|
||||
else
|
||||
dat += " [gps["gps_tag"]]: [gps["area_name"]], ([gps["x"]], [gps["y"]]) - [gps["local"] ? "[gps["direction"]] Dist: [gps["distX"] ? "[abs(round(gps["distX"], 1))]m [(gps["distX"] > 0) ? "E" : "W"], " : ""][gps["distY"] ? "[abs(round(gps["distY"], 1))]m [(gps["distY"] > 0) ? "N" : "S"]" : ""]" : "in \the [gps["z_name"]]"]"
|
||||
else
|
||||
dat += "No other signals detected."
|
||||
dat += "<tr>"
|
||||
var/gps_ref = "\ref[gps["ref"]]"
|
||||
dat += "<td>[gps["gps_tag"]]</td><td>[gps["area_name"]]</td>"
|
||||
|
||||
. = dat
|
||||
if(istype(gps_data["ref"], /obj/item/device/gps/internal/poi))
|
||||
dat += "<td>[gps["local"] ? "[gps["direction"]] Dist: [round(gps["distance"], 10)]m" : "in \the [gps["z_name"]]"]</td>"
|
||||
else
|
||||
dat += "<td>([gps["x"]], [gps["y"]], [gps["z_name"]])</td>"
|
||||
|
||||
if(gps["local"])
|
||||
dat += "<td>[gps["distance"]]m</td>"
|
||||
dat += "<td>[gps["degrees"]]° ([gps["direction"]])</td>"
|
||||
else
|
||||
dat += "<td colspan = 2>Non-local signal.</td>"
|
||||
|
||||
if(LAZYACCESS(tracking_devices, gps_ref))
|
||||
dat += "<td><a href='?src=\ref[src];stop_track=[gps_ref]'>\[Stop Tracking\]</a> <a href='?src=\ref[src];track_color=[gps_ref]'>\[Colour [color_square(hex = LAZYACCESS(tracking_devices, gps_ref))]\]</a> <a href='?src=\ref[src];track_label=[gps_ref]'>Show/Hide Label</a></td>"
|
||||
else
|
||||
dat += "<td><a href='?src=\ref[src];start_track=[gps_ref]'>\[Start Tracking\]</a></td>"
|
||||
dat += "</tr>"
|
||||
else
|
||||
dat += "<tr><td colspan = 5>No other signals detected.</td></tr>"
|
||||
dat += "</table>"
|
||||
|
||||
var/datum/browser/popup = new(user, "gps_\ref[src]", "Global Positioning System", 700, 1000)
|
||||
popup.set_content(dat.Join(null))
|
||||
popup.open()
|
||||
|
||||
/obj/item/device/gps/Topic(var/href, var/list/href_list)
|
||||
if(..())
|
||||
return 1
|
||||
return TRUE
|
||||
|
||||
if(href_list["toggle_power"])
|
||||
toggle_tracking()
|
||||
. = TRUE
|
||||
|
||||
if(href_list["track_label"])
|
||||
var/gps_ref = href_list["track_label"]
|
||||
var/obj/item/device/gps/gps = locate(gps_ref)
|
||||
if(istype(gps) && !QDELETED(gps) && !LAZYACCESS(showing_tracked_names, gps_ref))
|
||||
LAZYSET(showing_tracked_names, gps_ref, TRUE)
|
||||
else
|
||||
LAZYREMOVE(showing_tracked_names, gps_ref)
|
||||
to_chat(usr, SPAN_NOTICE("\The [src] is [LAZYACCESS(showing_tracked_names, gps_ref) ? "now showing" : "no longer showing"] labels for [gps.gps_tag]."))
|
||||
|
||||
if(href_list["stop_track"])
|
||||
var/gps_ref = href_list["stop_track"]
|
||||
var/obj/item/device/gps/gps = locate(gps_ref)
|
||||
compass.clear_waypoint(gps_ref)
|
||||
LAZYREMOVE(tracking_devices, gps_ref)
|
||||
LAZYREMOVE(showing_tracked_names, gps_ref)
|
||||
if(istype(gps) && !QDELETED(gps))
|
||||
to_chat(usr, SPAN_NOTICE("\The [src] is no longer tracking [gps.gps_tag]."))
|
||||
update_compass()
|
||||
. = TRUE
|
||||
|
||||
if(href_list["start_track"])
|
||||
var/gps_ref = href_list["start_track"]
|
||||
var/obj/item/device/gps/gps = locate(gps_ref)
|
||||
if(istype(gps) && !QDELETED(gps))
|
||||
LAZYSET(tracking_devices, gps_ref, "#00ffff")
|
||||
LAZYSET(showing_tracked_names, gps_ref, TRUE)
|
||||
to_chat(usr, SPAN_NOTICE("\The [src] is now tracking [gps.gps_tag]."))
|
||||
update_compass()
|
||||
. = TRUE
|
||||
|
||||
if(href_list["track_color"])
|
||||
var/obj/item/device/gps/gps = locate(href_list["track_color"])
|
||||
if(istype(gps) && !QDELETED(gps))
|
||||
var/new_colour = input("Enter a new tracking color.", "GPS Waypoint Color") as color|null
|
||||
if(new_colour && istype(gps) && !QDELETED(gps) && holder == usr && !usr.incapacitated())
|
||||
to_chat(usr, SPAN_NOTICE("You adjust the colour \the [src] is using to highlight [gps.gps_tag]."))
|
||||
LAZYSET(tracking_devices, href_list["track_color"], new_colour)
|
||||
update_compass()
|
||||
. = TRUE
|
||||
|
||||
if(href_list["tag"])
|
||||
var/a = input("Please enter desired tag.", name, gps_tag) as text
|
||||
@@ -161,95 +322,22 @@ var/list/GPS_list = list()
|
||||
gps_tag = a
|
||||
name = "global positioning system ([gps_tag])"
|
||||
to_chat(usr, "You set your GPS's tag to '[gps_tag]'.")
|
||||
. = TRUE
|
||||
|
||||
if(href_list["range"])
|
||||
local_mode = !local_mode
|
||||
to_chat(usr, "You set the signal receiver to [local_mode ? "'NARROW'" : "'BROAD'"].")
|
||||
. = TRUE
|
||||
|
||||
if(href_list["hide"])
|
||||
if(!can_hide_signal)
|
||||
return
|
||||
hide_signal = !hide_signal
|
||||
to_chat(usr, "You set the device to [hide_signal ? "not " : ""]broadcast a signal while scanning for other signals.")
|
||||
|
||||
/obj/item/device/gps/tgui_interact(mob/user, datum/tgui/ui)
|
||||
if(emped)
|
||||
to_chat(user, "<span class='hear'>[src] fizzles weakly.</span>")
|
||||
return
|
||||
ui = SStgui.try_update_ui(user, src, ui)
|
||||
if(!ui)
|
||||
ui = new(user, src, "Gps", name)
|
||||
ui.open()
|
||||
ui.set_autoupdate(updating)
|
||||
|
||||
/obj/item/device/gps/tgui_data(mob/user)
|
||||
var/list/data = list()
|
||||
data["power"] = tracking
|
||||
data["tag"] = gps_tag
|
||||
data["updating"] = updating
|
||||
data["globalmode"] = !local_mode
|
||||
if(!tracking || emped) //Do not bother scanning if the GPS is off or EMPed
|
||||
return data
|
||||
|
||||
var/turf/curr = get_turf(src)
|
||||
data["currentArea"] = "[get_area_name(curr, TRUE)]"
|
||||
data["currentCoords"] = list(curr.x, curr.y, curr.z)
|
||||
data["currentCoordsText"] = "[curr.x], [curr.y], [using_map.get_zlevel_name(curr.z)]"
|
||||
|
||||
data["zLevelDetection"] = using_map.get_map_levels(curr.z, long_range)
|
||||
|
||||
var/list/signals = list()
|
||||
data["signals"] = list()
|
||||
|
||||
for(var/obj/item/device/gps/G in GPS_list - src)
|
||||
if(!G.tracking || G.emped || G.hide_signal)
|
||||
continue
|
||||
|
||||
var/turf/T = get_turf(G)
|
||||
if(!T)
|
||||
continue
|
||||
if(local_mode && curr.z != T.z)
|
||||
continue
|
||||
if(!(T.z in data["zLevelDetection"]))
|
||||
continue
|
||||
|
||||
var/list/signal = list()
|
||||
signal["entrytag"] = G.gps_tag //Name or 'tag' of the GPS
|
||||
signal["coords"] = list(T.x, T.y, T.z)
|
||||
signal["coordsText"] = "[T.x], [T.y], [using_map.get_zlevel_name(T.z)]"
|
||||
if(T.z == curr.z) //Distance/Direction calculations for same z-level only
|
||||
signal["dist"] = max(get_dist(curr, T), 0) //Distance between the src and remote GPS turfs
|
||||
signal["degrees"] = round(Get_Angle(curr, T)) //0-360 degree directional bearing, for more precision.
|
||||
signals += list(signal) //Add this signal to the list of signals
|
||||
data["signals"] = signals
|
||||
return data
|
||||
|
||||
/obj/item/device/gps/tgui_act(action, params)
|
||||
if(..())
|
||||
return TRUE
|
||||
|
||||
switch(action)
|
||||
if("rename")
|
||||
var/a = stripped_input(usr, "Please enter desired tag.", name, gps_tag, 20)
|
||||
|
||||
if(!a)
|
||||
return
|
||||
|
||||
gps_tag = a
|
||||
name = "global positioning system ([gps_tag])"
|
||||
. = TRUE
|
||||
|
||||
if("power")
|
||||
toggletracking(usr)
|
||||
. = TRUE
|
||||
|
||||
if("updating")
|
||||
updating = !updating
|
||||
. = TRUE
|
||||
|
||||
if("globalmode")
|
||||
local_mode = !local_mode
|
||||
. = TRUE
|
||||
if(. && loc == usr)
|
||||
display(usr)
|
||||
|
||||
/obj/item/device/gps/on // Defaults to off to avoid polluting the signal list with a bunch of GPSes without owners. If you need to spawn active ones, use these.
|
||||
tracking = TRUE
|
||||
@@ -373,26 +461,43 @@ var/list/GPS_list = list()
|
||||
can_hide_signal = TRUE
|
||||
|
||||
/obj/item/device/gps/syndie/display(mob/user)
|
||||
if(!tracking)
|
||||
. = "The device is off. Alt-click it to turn it on."
|
||||
return
|
||||
|
||||
if(emped)
|
||||
. = "It's busted!"
|
||||
to_chat(user, "It's busted!")
|
||||
return
|
||||
|
||||
var/list/dat = list()
|
||||
var/list/gps_data = display_list()
|
||||
|
||||
dat += "Current location: [gps_data["my_area_name"]] <b>([gps_data["curr_x"]], [gps_data["curr_y"]], [gps_data["curr_z_name"]])</b>"
|
||||
dat += "[hide_signal ? "Tagged" : "Broadcasting"] as '[gps_tag]'. <a href='?src=\ref[src];tag=1'>\[Change Tag\]</a> \
|
||||
<a href='?src=\ref[src];range=1'>\[Toggle Scan Range\]</a> \
|
||||
[can_hide_signal ? "<a href='?src=\ref[src];hide=1'>\[Toggle Signal Visibility\]</a>":""]"
|
||||
dat += "<table width = '100%'>"
|
||||
if(!tracking)
|
||||
dat += "<tr><td colspan = 6></td><a href='?src=\ref[src];toggle_power=1'>\[Switch On]\]</a></tr>"
|
||||
else
|
||||
dat += "<tr><td colspan = 6></td><a href='?src=\ref[src];toggle_power=1'>\[Switch Off]\]</a></tr>"
|
||||
dat += "<tr><td colspan = 2><b>Current location</b></td><td colspan = 2>[gps_data["my_area_name"]]</td><td colspan = 2><b>([gps_data["curr_x"]], [gps_data["curr_y"]], [gps_data["curr_z_name"]])</b></td></tr>"
|
||||
dat += "<tr><td colspan = 4>[hide_signal ? "Tagged" : "Broadcasting"] as '[gps_tag]'.</td>"
|
||||
dat += "<td><a href='?src=\ref[src];tag=1'>\[Change Tag\]</a><a href='?src=\ref[src];range=1'>\[Toggle Scan Range\]</a>[can_hide_signal ? "<a href='?src=\ref[src];hide=1'>\[Toggle Signal Visibility\]</a>":""]</td></tr>"
|
||||
|
||||
if(gps_data["gps_list"].len)
|
||||
dat += "Detected signals;"
|
||||
dat += "<tr><td colspan = 6><b>Detected signals</b></td></tr>"
|
||||
for(var/gps in gps_data["gps_list"])
|
||||
dat += " [gps["gps_tag"]]: [gps["area_name"]] ([gps["x"]], [gps["y"]], [gps["z_name"]]) [gps["local"] ? "Dist: [gps["distance"]]m Dir: [gps["degrees"]]° ([gps["direction"]])" :""]"
|
||||
dat += "<tr>"
|
||||
var/gps_ref = "\ref[gps["ref"]]"
|
||||
dat += "<td>[gps["gps_tag"]]</td><td>[gps["area_name"]] ([gps["x"]], [gps["y"]], [gps["z_name"]])</td>"
|
||||
if(gps["local"])
|
||||
dat += "<td>[gps["distance"]]m</td>"
|
||||
dat += "<td>[gps["degrees"]]° ([gps["direction"]])</td>"
|
||||
else
|
||||
dat += "No other signals detected."
|
||||
dat += "<td colspan = 2>Non-local signal.</td>"
|
||||
if(LAZYACCESS(tracking_devices, gps_ref))
|
||||
dat += "<td><a href='?src=\ref[src];stop_track=[gps_ref]'>\[Stop Tracking\]</a> <a href='?src=\ref[src];track_color=[gps_ref]'>\[Colour [color_square(hex = LAZYACCESS(tracking_devices, gps_ref))]\]</a> <a href='?src=\ref[src];track_label=[gps_ref]'>Show/Hide Label</a></td>"
|
||||
else
|
||||
dat += "<td><a href='?src=\ref[src];start_track=[gps_ref]'>\[Start Tracking\]</a></td>"
|
||||
dat += "</tr>"
|
||||
else
|
||||
dat += "<tr><td colspan = 6>No other signals detected.</td></tr>"
|
||||
dat += "</table>"
|
||||
|
||||
. = dat
|
||||
var/datum/browser/popup = new(user, "gps_\ref[src]", "Global Positioning System", 700, 1000)
|
||||
popup.set_content(dat.Join(null))
|
||||
popup.open()
|
||||
|
||||
@@ -299,7 +299,3 @@
|
||||
if(PREF_FBP_SOFTWARE)
|
||||
return 150
|
||||
return S.max_age // welp
|
||||
|
||||
/datum/category_item/player_setup_item/proc/color_square(red, green, blue, hex)
|
||||
var/color = hex ? hex : "#[num2hex(red, 2)][num2hex(green, 2)][num2hex(blue, 2)]"
|
||||
return "<span style='font-face: fixedsys; font-size: 14px; background-color: [color]; color: [color]'>___</span>"
|
||||
3
code/modules/compass/^compass.dm
Normal file
3
code/modules/compass/^compass.dm
Normal file
@@ -0,0 +1,3 @@
|
||||
#undef COMPASS_INTERVAL
|
||||
#undef COMPASS_PERIOD
|
||||
#undef COMPASS_LABEL_OFFSET
|
||||
15
code/modules/compass/_compass.dm
Normal file
15
code/modules/compass/_compass.dm
Normal file
@@ -0,0 +1,15 @@
|
||||
#define COMPASS_INTERVAL 3
|
||||
#define COMPASS_PERIOD 15
|
||||
#define COMPASS_LABEL_OFFSET 150
|
||||
|
||||
/*
|
||||
This folder contains an abstract type (/obj/compass_holder) which contains a set of
|
||||
waypoints (/datum/compass_waypoint) and generates a circular compass with markers for
|
||||
mobs that have the object in their screen list. See GPS for an example implementation.
|
||||
*/
|
||||
|
||||
/image/compass_marker
|
||||
maptext_height = 64
|
||||
maptext_width = 128
|
||||
maptext_x = -48
|
||||
maptext_y = -32
|
||||
127
code/modules/compass/compass_holder.dm
Normal file
127
code/modules/compass/compass_holder.dm
Normal file
@@ -0,0 +1,127 @@
|
||||
/obj/compass_holder
|
||||
name = null
|
||||
icon = null
|
||||
icon_state = null
|
||||
screen_loc = "CENTER,CENTER"
|
||||
|
||||
var/show_heading = FALSE
|
||||
var/numeric_directions = FALSE
|
||||
|
||||
var/image/compass_heading_marker
|
||||
var/list/compass_static_labels
|
||||
var/list/compass_waypoints
|
||||
var/list/compass_waypoint_markers
|
||||
|
||||
var/static/list/angle_step_to_dir = list(
|
||||
"N",
|
||||
"NE",
|
||||
"E",
|
||||
"SE",
|
||||
"S",
|
||||
"SW",
|
||||
"W",
|
||||
"NW",
|
||||
"N"
|
||||
)
|
||||
|
||||
/obj/compass_holder/Initialize(mapload, ...)
|
||||
. = ..()
|
||||
if(show_heading)
|
||||
compass_heading_marker = new /image/compass_marker
|
||||
compass_heading_marker.maptext = "<center><font color = '#00ffffff' size = 2><b>△</b></font></center>"
|
||||
compass_heading_marker.filters = filter(type="drop_shadow", color = "#00ffffaa", size = 2, offset = 1,x = 0, y = 0)
|
||||
compass_heading_marker.layer = LAYER_HUD_UNDER
|
||||
compass_heading_marker.plane = PLANE_PLAYER_HUD
|
||||
|
||||
for(var/i in 0 to (360/(COMPASS_PERIOD))-1)
|
||||
var/image/I = new /image/compass_marker
|
||||
I.loc = src
|
||||
var/str
|
||||
var/str_col
|
||||
if(i % COMPASS_INTERVAL == 0)
|
||||
var/angle = (i * COMPASS_PERIOD)
|
||||
if(numeric_directions)
|
||||
str = "[angle]"
|
||||
else
|
||||
str = angle_step_to_dir[CLAMP(round(angle/45)+1, 1, length(angle_step_to_dir))]
|
||||
str_col = "#ffffffaa"
|
||||
else
|
||||
str = "〡"
|
||||
str_col = "#aaaaaa88"
|
||||
I.maptext = "<center><font color = '[str_col]' size = '1px'><b>[str]</b></font></center>"
|
||||
var/matrix/M = matrix()
|
||||
M.Translate(0, COMPASS_LABEL_OFFSET)
|
||||
M.Turn(COMPASS_PERIOD * i)
|
||||
I.transform = M
|
||||
I.filters = filter(type="drop_shadow", color = "#77777777", size = 2, offset = 1,x = 0, y = 0)
|
||||
I.layer = LAYER_HUD_UNDER
|
||||
I.plane = PLANE_PLAYER_HUD
|
||||
LAZYADD(compass_static_labels, I)
|
||||
|
||||
rebuild_overlay_lists(TRUE)
|
||||
|
||||
/obj/compass_holder/Destroy()
|
||||
QDEL_NULL_LIST(compass_waypoints)
|
||||
. = ..()
|
||||
|
||||
/obj/compass_holder/proc/get_heading()
|
||||
var/atom/A = loc?.loc // is there a get_holder_recursive() equivalent on Polaris?
|
||||
if(istype(A))
|
||||
. = dir2angle(A.dir)
|
||||
else
|
||||
. = 0
|
||||
|
||||
/obj/compass_holder/update_icon()
|
||||
var/set_overlays = (compass_static_labels | compass_waypoint_markers)
|
||||
if(show_heading)
|
||||
set_overlays |= compass_heading_marker
|
||||
overlays = set_overlays
|
||||
|
||||
/obj/compass_holder/proc/clear_waypoint(var/id)
|
||||
LAZYREMOVE(compass_waypoints, id)
|
||||
rebuild_overlay_lists(TRUE)
|
||||
|
||||
/obj/compass_holder/proc/set_waypoint(var/id, var/label, var/heading_x, var/heading_y, var/heading_z, var/label_color)
|
||||
var/datum/compass_waypoint/wp = LAZYACCESS(compass_waypoints, id)
|
||||
if(!wp)
|
||||
wp = new /datum/compass_waypoint()
|
||||
wp.set_values(label, heading_x, heading_y, heading_z, label_color)
|
||||
LAZYSET(compass_waypoints, id, wp)
|
||||
rebuild_overlay_lists(TRUE)
|
||||
|
||||
/obj/compass_holder/proc/recalculate_heading(var/rebuild_icon = TRUE)
|
||||
if(show_heading)
|
||||
var/matrix/M = matrix()
|
||||
M.Translate(0, round(COMPASS_LABEL_OFFSET - 35))
|
||||
M.Turn(get_heading())
|
||||
compass_heading_marker.transform = M
|
||||
if(rebuild_icon)
|
||||
update_icon()
|
||||
|
||||
/obj/compass_holder/proc/show_waypoint(var/id)
|
||||
var/datum/compass_waypoint/wp = compass_waypoints[id]
|
||||
wp.hidden = FALSE
|
||||
|
||||
/obj/compass_holder/proc/hide_waypoint(var/id)
|
||||
var/datum/compass_waypoint/wp = compass_waypoints[id]
|
||||
wp.hidden = TRUE
|
||||
|
||||
/obj/compass_holder/proc/hide_waypoints(var/rebuild_overlays = FALSE)
|
||||
for(var/id in compass_waypoints)
|
||||
hide_waypoint(id)
|
||||
if(rebuild_overlays)
|
||||
rebuild_overlay_lists(TRUE)
|
||||
|
||||
/obj/compass_holder/proc/rebuild_overlay_lists(var/update_icon = FALSE)
|
||||
compass_waypoint_markers = null
|
||||
var/turf/T = get_turf(src)
|
||||
if(istype(T))
|
||||
for(var/id in compass_waypoints)
|
||||
var/datum/compass_waypoint/wp = compass_waypoints[id]
|
||||
if(!wp.hidden)
|
||||
wp.recalculate_heading(T.x, T.y)
|
||||
LAZYADD(compass_waypoint_markers, wp.compass_overlay)
|
||||
if(show_heading)
|
||||
recalculate_heading(FALSE)
|
||||
if(update_icon)
|
||||
update_icon()
|
||||
30
code/modules/compass/compass_waypoint.dm
Normal file
30
code/modules/compass/compass_waypoint.dm
Normal file
@@ -0,0 +1,30 @@
|
||||
/datum/compass_waypoint
|
||||
var/name
|
||||
var/x
|
||||
var/y
|
||||
var/z
|
||||
var/color
|
||||
var/hidden = FALSE
|
||||
var/image/compass_overlay
|
||||
|
||||
/datum/compass_waypoint/proc/set_values(var/_name, var/_x, var/_y, var/_z, var/_color)
|
||||
name = _name
|
||||
x = _x
|
||||
y = _y
|
||||
z = _z
|
||||
color = _color
|
||||
compass_overlay = new /image/compass_marker
|
||||
compass_overlay.loc = src
|
||||
compass_overlay.maptext = "<center><font color = '[color]' size = '2px'><b>|</b>\n[name]</font></center>"
|
||||
compass_overlay.filters = filter(type="drop_shadow", color = "[color]" + "aa", size = 2, offset = 1,x = 0, y = 0)
|
||||
compass_overlay.layer = LAYER_HUD_UNDER
|
||||
compass_overlay.plane = PLANE_PLAYER_HUD
|
||||
|
||||
/datum/compass_waypoint/proc/recalculate_heading(var/cx, var/cy)
|
||||
var/matrix/M = matrix()
|
||||
M.Translate(0, (name ? COMPASS_LABEL_OFFSET-4 : COMPASS_LABEL_OFFSET))
|
||||
M.Turn(ATAN2(cy-y, cx-x)+180)
|
||||
compass_overlay.transform = M
|
||||
|
||||
#undef COMPASS_PERIOD
|
||||
#undef COMPASS_INTERVAL
|
||||
@@ -2151,6 +2151,10 @@
|
||||
#include "code\modules\clothing\under\jobs\security.dm"
|
||||
#include "code\modules\clothing\under\xenos\seromi.dm"
|
||||
#include "code\modules\clothing\under\xenos\vox.dm"
|
||||
#include "code\modules\compass\^compass.dm"
|
||||
#include "code\modules\compass\_compass.dm"
|
||||
#include "code\modules\compass\compass_holder.dm"
|
||||
#include "code\modules\compass\compass_waypoint.dm"
|
||||
#include "code\modules\customitems\item_spawning.dm"
|
||||
#include "code\modules\detectivework\footprints.dm"
|
||||
#include "code\modules\detectivework\forensics.dm"
|
||||
|
||||
Reference in New Issue
Block a user