Files
fulpstation/code/datums/wires/_wires.dm
Aleksej Komarov 5521c8ebee [READY] tgui-next: Initial PR, speedy new Air Alarm interface. (#46764)
* Initial tgui-next commit

* Improve dev server, slight changes to layout.

* Add more components, fix dragging, finalize scrubber list

* Complete an air alarm interface.

* Multiple improvements based on feedback

- LabeledList now has a "buttons" prop, where you can put buttons.
- Improved Box and Flex components
- Whole UI is now dimmable if non-interactive
- Basic documentation of components (Box and Flex so far).
- Icon and Box now accept a "color" prop.
- Routing improved in "Layout" component, you can now specify whether an interface is scrollable.

* Less harsh dimming

* Redux, Toasts

- Fixed inconsistent backend updates with Redux.
- Added Toasts which are currently unused, but are functional.

* acclimator + ai airlock ui

* Add a progress bar component, implement resizing

* Fix a zero in title bar

* Add a linter to keep shit tidy, fix danger level mapping, add some more docs

* better ai door interact ui

* final ai airlock interface

* Fix issues with code, enforce hard 120 line length cap, automerge binaries

* Implement hot module reloading

* Fix progress bar, add color support

* Fix ProgressBar baseline alignment issues

* Remove unwanted padding on the bottom of the LabeledList.

* Component improvements

- Fix baseline issues with Button and ProgressBar components
- Box how inherits props from Box
- Atomic colors and Button colors are now auto-generated, all range of colors supported

* Chem Dispenser UI, animated numbers, more style fixes

* Add an IE8 polyfill

* Intermediate state of fixing IE8

* Lots of shimming and general misery

* Fully working old TGUI chainloader for IE8, more pipeline improvements

* Support title-less Sections

* Delete Yarn, use Lerna for workspace management

* Improve maths and animated numbers

* Fix loss of focus for scrollable content, activate buttons with keyboard

* Attempt to bust the cache, grab focus on keyboard presses too

* Fix hot module replacement by manually pulling replaced modules.

* backend logging

 un-nuke line endings

changes without insane line endings

* helper procs + href support

* slight optimization

* compiles

* Redux, Hotkeys, Kitchen Sink (for UI testing), Tabs component

* Push logs to backend, small kitchen sink changes, tab fixes

* Update component reference in README

* Small fixes

* Next bunch of IE8 fixes, PureComponent optimization for Inferno

* Delete old tgui html

* Log the event of loading the old tgui

* Enable tgui logging on server by default

* Final solution

* Extract routes into a separate file, fix ChemDispenser bug

- Chem dispenser was needlessly disabling transfer amount buttons

* Disable baseline alignment for vertical tabs

* Fix tabs and box units

- Tab content was not taking full page width
- Box can now accepts strings as units, which will be treated as raw style values.

* Fix tgui on Terry

* Fix sending all logs with an "error" flag

* Some macro UI component changes and improvements

- Refer to README.md diff to see what's new

* Tooltip component

* Add support for themes, nanotrasen logo is back

* Clockwork theme hotfix

* Slight adjustment to logo positioning

* Actually proper solution for logo positioning

* Fix color maps

* tgui-next thermomachine interface

* tgui-next canister interface

* Add icon_class_name proc to asset cache

* Lots of stuff backported from actioninja's repo

* Cleanup oopsies

* Cargo UI adjustments

* Nuke lodash

* Minor fixes and cleanup

- Remove local Inferno package in favor of upstream Inferno
- Fix "initial" prop on AnimatedNumber
- Force fancy=0 for IE8
- Click-through dimmer

* Add a bat file for dummies

* podlauncher interface fix

* Update README, assert code dominance

* Clarify usage of event handlers in Inferno

* Document LabeledList.Divider

* Fukken grammar

* fixes cellular emporium readapt button not working

* fixes incorrect action on button in atmos control interface

* remove unneeded data from airlock electronics ui

* Set +x mode on bin/tgui

* Fix filename cases

- They were untracked by git on windows

* Ignore package lock, make batch more robust

- package-lock.json is very random and unreliable as fuck. Yarn was better.

* Build tgui-next in travis

* bruh

- fixes tgui error reporting

* logging cleanup + always log
2019-10-15 17:20:37 +02:00

301 lines
7.5 KiB
Plaintext

#define MAXIMUM_EMP_WIRES 3
/proc/is_wire_tool(obj/item/I)
if(!I)
return
if(I.tool_behaviour == TOOL_WIRECUTTER || I.tool_behaviour == TOOL_MULTITOOL)
return TRUE
if(istype(I, /obj/item/assembly))
var/obj/item/assembly/A = I
if(A.attachable)
return TRUE
/atom
var/datum/wires/wires = null
/atom/proc/attempt_wire_interaction(mob/user)
if(!wires)
return WIRE_INTERACTION_FAIL
if(!user.CanReach(src))
return WIRE_INTERACTION_FAIL
wires.interact(user)
return WIRE_INTERACTION_BLOCK
/datum/wires
var/atom/holder = null // The holder (atom that contains these wires).
var/holder_type = null // The holder's typepath (used to make wire colors common to all holders).
var/proper_name = "Unknown" // The display name for the wire set shown in station blueprints. Not used if randomize is true or it's an item NT wouldn't know about (Explosives/Nuke)
var/list/wires = list() // List of wires.
var/list/cut_wires = list() // List of wires that have been cut.
var/list/colors = list() // Dictionary of colors to wire.
var/list/assemblies = list() // List of attached assemblies.
var/randomize = 0 // If every instance of these wires should be random.
// Prevents wires from showing up in station blueprints
/datum/wires/New(atom/holder)
..()
if(!istype(holder, holder_type))
CRASH("Wire holder is not of the expected type!")
return
src.holder = holder
if(randomize)
randomize()
else
if(!GLOB.wire_color_directory[holder_type])
randomize()
GLOB.wire_color_directory[holder_type] = colors
GLOB.wire_name_directory[holder_type] = proper_name
else
colors = GLOB.wire_color_directory[holder_type]
/datum/wires/Destroy()
holder = null
assemblies = list()
return ..()
/datum/wires/proc/add_duds(duds)
while(duds)
var/dud = WIRE_DUD_PREFIX + "[--duds]"
if(dud in wires)
continue
wires += dud
/datum/wires/proc/randomize()
var/static/list/possible_colors = list(
"blue",
"brown",
"crimson",
"cyan",
"gold",
"grey",
"green",
"magenta",
"orange",
"pink",
"purple",
"red",
"silver",
"violet",
"white",
"yellow"
)
var/list/my_possible_colors = possible_colors.Copy()
for(var/wire in shuffle(wires))
colors[pick_n_take(my_possible_colors)] = wire
/datum/wires/proc/shuffle_wires()
colors.Cut()
randomize()
/datum/wires/proc/repair()
cut_wires.Cut()
/datum/wires/proc/get_wire(color)
return colors[color]
/datum/wires/proc/get_color_of_wire(wire_type)
for(var/color in colors)
var/other_type = colors[color]
if(wire_type == other_type)
return color
/datum/wires/proc/get_attached(color)
if(assemblies[color])
return assemblies[color]
return null
/datum/wires/proc/is_attached(color)
if(assemblies[color])
return TRUE
/datum/wires/proc/is_cut(wire)
return (wire in cut_wires)
/datum/wires/proc/is_color_cut(color)
return is_cut(get_wire(color))
/datum/wires/proc/is_all_cut()
if(cut_wires.len == wires.len)
return TRUE
/datum/wires/proc/is_dud(wire)
return dd_hasprefix(wire, WIRE_DUD_PREFIX)
/datum/wires/proc/is_dud_color(color)
return is_dud(get_wire(color))
/datum/wires/proc/cut(wire)
if(is_cut(wire))
cut_wires -= wire
on_cut(wire, mend = TRUE)
else
cut_wires += wire
on_cut(wire, mend = FALSE)
/datum/wires/proc/cut_color(color)
cut(get_wire(color))
/datum/wires/proc/cut_random()
cut(wires[rand(1, wires.len)])
/datum/wires/proc/cut_all()
for(var/wire in wires)
cut(wire)
/datum/wires/proc/pulse(wire, user)
if(is_cut(wire))
return
on_pulse(wire, user)
/datum/wires/proc/pulse_color(color, mob/living/user)
pulse(get_wire(color), user)
/datum/wires/proc/pulse_assembly(obj/item/assembly/S)
for(var/color in assemblies)
if(S == assemblies[color])
pulse_color(color)
return TRUE
/datum/wires/proc/attach_assembly(color, obj/item/assembly/S)
if(S && istype(S) && S.attachable && !is_attached(color))
assemblies[color] = S
S.forceMove(holder)
S.connected = src
return S
/datum/wires/proc/detach_assembly(color)
var/obj/item/assembly/S = get_attached(color)
if(S && istype(S))
assemblies -= color
S.connected = null
S.forceMove(holder.drop_location())
return S
/datum/wires/proc/emp_pulse()
var/list/possible_wires = shuffle(wires)
var/remaining_pulses = MAXIMUM_EMP_WIRES
for(var/wire in possible_wires)
if(prob(33))
pulse(wire)
remaining_pulses--
if(!remaining_pulses)
break
// Overridable Procs
/datum/wires/proc/interactable(mob/user)
return TRUE
/datum/wires/proc/get_status()
return list()
/datum/wires/proc/on_cut(wire, mend = FALSE)
return
/datum/wires/proc/on_pulse(wire, user)
return
// End Overridable Procs
/datum/wires/proc/interact(mob/user)
if(!interactable(user))
return
ui_interact(user)
for(var/A in assemblies)
var/obj/item/I = assemblies[A]
if(istype(I) && I.on_found(user))
return
/datum/wires/ui_host()
return holder
/datum/wires/ui_status(mob/user)
if(interactable(user))
return ..()
return UI_CLOSE
/datum/wires/ui_interact(mob/user, ui_key = "wires", datum/tgui/ui = null, force_open = FALSE, \
datum/tgui/master_ui = null, datum/ui_state/state = GLOB.physical_state)
ui = SStgui.try_update_ui(user, src, ui_key, ui, force_open)
if (!ui)
ui = new(user, src, ui_key, "wires", "[holder.name] Wires", 350, 150 + wires.len * 30, master_ui, state)
ui.open()
/datum/wires/ui_data(mob/user)
var/list/data = list()
var/list/payload = list()
var/reveal_wires = FALSE
// Admin ghost can see a purpose of each wire.
if(IsAdminGhost(user))
reveal_wires = TRUE
// Same for anyone with an abductor multitool.
else if(user.is_holding_item_of_type(/obj/item/multitool/abductor))
reveal_wires = TRUE
// Station blueprints do that too, but only if the wires are not randomized.
else if(user.is_holding_item_of_type(/obj/item/areaeditor/blueprints) && !randomize)
reveal_wires = TRUE
for(var/color in colors)
payload.Add(list(list(
"color" = color,
"wire" = ((reveal_wires && !is_dud_color(color)) ? get_wire(color) : null),
"cut" = is_color_cut(color),
"attached" = is_attached(color)
)))
data["wires"] = payload
data["status"] = get_status()
return data
/datum/wires/ui_act(action, params)
if(..() || !interactable(usr))
return
var/target_wire = params["wire"]
var/mob/living/L = usr
var/obj/item/I
switch(action)
if("cut")
I = L.is_holding_tool_quality(TOOL_WIRECUTTER)
if(I || IsAdminGhost(usr))
if(I && holder)
I.play_tool_sound(holder, 20)
cut_color(target_wire)
. = TRUE
else
to_chat(L, "<span class='warning'>You need wirecutters!</span>")
if("pulse")
I = L.is_holding_tool_quality(TOOL_MULTITOOL)
if(I || IsAdminGhost(usr))
if(I && holder)
I.play_tool_sound(holder, 20)
pulse_color(target_wire, L)
. = TRUE
else
to_chat(L, "<span class='warning'>You need a multitool!</span>")
if("attach")
if(is_attached(target_wire))
I = detach_assembly(target_wire)
if(I)
L.put_in_hands(I)
. = TRUE
else
I = L.get_active_held_item()
if(istype(I, /obj/item/assembly))
var/obj/item/assembly/A = I
if(A.attachable)
if(!L.temporarilyRemoveItemFromInventory(A))
return
if(!attach_assembly(target_wire, A))
A.forceMove(L.drop_location())
. = TRUE
else
to_chat(L, "<span class='warning'>You need an attachable assembly!</span>")
#undef MAXIMUM_EMP_WIRES