From d0bb46a26620e21cac3d7f73f00498bd2f5efa31 Mon Sep 17 00:00:00 2001 From: Spades Date: Tue, 14 Jun 2016 00:27:53 -0400 Subject: [PATCH 01/15] Loyalty implant for HoP --- code/game/jobs/job/captain.dm | 9 +++++---- 1 file changed, 5 insertions(+), 4 deletions(-) diff --git a/code/game/jobs/job/captain.dm b/code/game/jobs/job/captain.dm index 69f837d8f9..0551df6c3c 100644 --- a/code/game/jobs/job/captain.dm +++ b/code/game/jobs/job/captain.dm @@ -30,13 +30,13 @@ var/datum/announcement/minor/captain_announcement = new(do_newscast = 1) if(2) H.equip_to_slot_or_del(new /obj/item/weapon/storage/backpack/captain(H), slot_back) if(3) H.equip_to_slot_or_del(new /obj/item/weapon/storage/backpack/satchel/cap(H), slot_back) if(4) H.equip_to_slot_or_del(new /obj/item/weapon/storage/backpack/satchel(H), slot_back) - H.equip_to_slot_or_del(new /obj/item/clothing/under/rank/captain(H), slot_w_uniform) + H.equip_to_slot_or_del(new /obj/item/clothing/under/rank/captain(H), slot_w_uniform) if(H.age>49) - // Since we can have something other than the default uniform at this + // Since we can have something other than the default uniform at this // point, check if we can actually attach the medal var/obj/item/clothing/uniform = H.w_uniform var/obj/item/clothing/accessory/medal/gold/captain/medal = new() - + if(uniform && uniform.can_attach_accessory(medal)) uniform.attach_accessory(null, medal) else @@ -107,4 +107,5 @@ var/datum/announcement/minor/captain_announcement = new(do_newscast = 1) H.equip_to_slot_or_del(new /obj/item/weapon/storage/box/ids(H), slot_l_hand) else H.equip_to_slot_or_del(new /obj/item/weapon/storage/box/ids(H.back), slot_in_backpack) - return 1 + H.implant_loyalty() + return 1 \ No newline at end of file From a26ae98cbdf35b6ef791dda85d46ff6fd99011d6 Mon Sep 17 00:00:00 2001 From: Spades Date: Tue, 14 Jun 2016 00:35:47 -0400 Subject: [PATCH 02/15] Probably could use a changelog entry. --- html/changelogs/JerTheAce_HoPLoyalty.yml | 36 ++++++++++++++++++++++++ 1 file changed, 36 insertions(+) create mode 100644 html/changelogs/JerTheAce_HoPLoyalty.yml diff --git a/html/changelogs/JerTheAce_HoPLoyalty.yml b/html/changelogs/JerTheAce_HoPLoyalty.yml new file mode 100644 index 0000000000..e9daa351da --- /dev/null +++ b/html/changelogs/JerTheAce_HoPLoyalty.yml @@ -0,0 +1,36 @@ +################################ +# Example Changelog File +# +# Note: This file, and files beginning with ".", and files that don't end in ".yml" will not be read. If you change this file, you will look really dumb. +# +# Your changelog will be merged with a master changelog. (New stuff added only, and only on the date entry for the day it was merged.) +# When it is, any changes listed below will disappear. +# +# Valid Prefixes: +# bugfix +# wip (For works in progress) +# tweak +# soundadd +# sounddel +# rscadd (general adding of nice things) +# rscdel (general deleting of nice things) +# imageadd +# imagedel +# maptweak +# spellcheck (typo fixes) +# experiment +################################# + +# Your name. +author: JerTheAce + +# Optional: Remove this file after generating master changelog. Useful for PR changelogs that won't get used again. +delete-after: True + +# Any changes you've made. See valid prefix list above. +# INDENT WITH TWO SPACES. NOT TABS. SPACES. +# SCREW THIS UP AND IT WON'T WORK. +# Also, all entries are changed into a single [] after a master changelog generation. Just remove the brackets when you add new entries. +# Please surround your changes in double quotes ("), as certain characters otherwise screws up compiling. The quotes will not show up in the changelog. +changes: + - rscadd: "Head of Personnel now has a loyalty implant." From 1e2136781c59a4ff1c3a19287a27e0e3f2b0a7b4 Mon Sep 17 00:00:00 2001 From: SinTwo Date: Mon, 20 Jun 2016 11:48:52 -0400 Subject: [PATCH 03/15] Adds NanoUI for multiple computers. --- code/game/machinery/adv_med.dm | 812 ++++++++++++---------- code/game/machinery/atmo_control.dm | 221 +++--- code/game/machinery/computer/Operating.dm | 75 +- code/game/machinery/computer/arcade.dm | 130 ++-- code/game/machinery/computer/cloning.dm | 267 +++---- code/game/machinery/computer/guestpass.dm | 66 +- code/game/machinery/computer3/lapvend.dm | 114 +-- code/modules/holodeck/HolodeckControl.dm | 78 +-- code/modules/paperwork/faxmachine.dm | 72 +- code/modules/paperwork/photocopier.dm | 51 +- nano/templates/adv_med.tmpl | 279 ++++++++ nano/templates/arcade_battle.tmpl | 26 + nano/templates/atmo_control.tmpl | 218 ++++++ nano/templates/chem_master.tmpl | 205 ++++++ nano/templates/cloning.tmpl | 115 +++ nano/templates/fax.tmpl | 32 + nano/templates/guest_pass.tmpl | 59 ++ nano/templates/holodeck.tmpl | 33 + nano/templates/laptop_vendor.tmpl | 175 +++++ nano/templates/operating.tmpl | 75 ++ nano/templates/photocopier.tmpl | 47 ++ 21 files changed, 2159 insertions(+), 991 deletions(-) create mode 100644 nano/templates/adv_med.tmpl create mode 100644 nano/templates/arcade_battle.tmpl create mode 100644 nano/templates/atmo_control.tmpl create mode 100644 nano/templates/chem_master.tmpl create mode 100644 nano/templates/cloning.tmpl create mode 100644 nano/templates/fax.tmpl create mode 100644 nano/templates/guest_pass.tmpl create mode 100644 nano/templates/holodeck.tmpl create mode 100644 nano/templates/laptop_vendor.tmpl create mode 100644 nano/templates/operating.tmpl create mode 100644 nano/templates/photocopier.tmpl diff --git a/code/game/machinery/adv_med.dm b/code/game/machinery/adv_med.dm index 90ff3f0d6b..9b24af92d2 100644 --- a/code/game/machinery/adv_med.dm +++ b/code/game/machinery/adv_med.dm @@ -8,13 +8,17 @@ icon = 'icons/obj/Cryogenic2.dmi' icon_state = "body_scanner_0" density = 1 + dir = 8 anchored = 1 + circuit = /obj/item/weapon/circuitboard/body_scanner use_power = 1 idle_power_usage = 60 active_power_usage = 10000 //10 kW. It's a big all-body scanner. + light_color = "#00FF00" + /obj/machinery/bodyscanner/New() ..() spawn( 5 ) @@ -34,72 +38,12 @@ component_parts += new /obj/item/stack/material/glass/reinforced(src, 2) RefreshParts() -/obj/machinery/bodyscanner/relaymove(mob/user as mob) - if (user.stat) - return - src.go_out() - return - -/obj/machinery/bodyscanner/verb/eject() - set src in oview(1) - set category = "Object" - set name = "Eject Body Scanner" - - if (usr.stat != 0) - return - src.go_out() - add_fingerprint(usr) - return - -/obj/machinery/bodyscanner/verb/move_inside() - set src in oview(1) - set category = "Object" - set name = "Enter Body Scanner" - - if (usr.stat != 0) - return - if (src.occupant) - usr << "The scanner is already occupied!" - return - if (usr.abiotic()) - usr << "The subject cannot have abiotic items on." - return - usr.pulling = null - usr.client.perspective = EYE_PERSPECTIVE - usr.client.eye = src - usr.loc = src - src.occupant = usr - update_use_power(2) - src.icon_state = "body_scanner_1" - for(var/obj/O in src) - //O = null - if(O in component_parts) - continue - if(O == circuit) - continue - qdel(O) - //Foreach goto(124) - src.add_fingerprint(usr) - return - -/obj/machinery/bodyscanner/proc/go_out() - if ((!( src.occupant ) || src.locked)) - return - for(var/obj/O in src) - if(O in component_parts) - continue - if(O == circuit) - continue - O.loc = src.loc - //Foreach goto(30) - if (src.occupant.client) - src.occupant.client.eye = src.occupant.client.mob - src.occupant.client.perspective = MOB_PERSPECTIVE - src.occupant.loc = src.loc - src.occupant = null - update_use_power(1) - src.icon_state = "body_scanner_0" - return +/obj/machinery/bodyscanner/power_change() + ..() + if(!(stat & (BROKEN|NOPOWER))) + set_light(2) + else + set_light(0) /obj/machinery/bodyscanner/attackby(var/obj/item/G, user as mob) if(default_deconstruction_screwdriver(user, G)) @@ -109,42 +53,96 @@ if(istype(G, /obj/item/weapon/grab)) var/obj/item/weapon/grab/H = G - if(!(ismob(H.affecting))) + if(panel_open) + user << "Close the maintenance panel first." return - if (src.occupant) - user << "The scanner is already occupied!" + if(!ismob(H.affecting)) return - if (H.affecting.abiotic()) - user << "Subject cannot have abiotic items on." + if(occupant) + user << "The scanner is already occupied!" return + for(var/mob/living/carbon/slime/M in range(1, H.affecting)) + if(M.Victim == H.affecting) + user << "[H.affecting.name] has a fucking slime attached to them, deal with that first." + return var/mob/M = H.affecting - if (M.client) - M.client.perspective = EYE_PERSPECTIVE - M.client.eye = src - M.loc = src - src.occupant = M - update_use_power(2) - src.icon_state = "body_scanner_1" - for(var/obj/O in src) - if(O in component_parts) - continue - if(O == circuit) - continue - O.loc = src.loc - //Foreach goto(154) - src.add_fingerprint(user) - //G = null + if(M.abiotic()) + user << "Subject cannot have abiotic items on." + return + M.forceMove(src) + occupant = M + icon_state = "body_scanner_1" + add_fingerprint(user) qdel(G) + +/obj/machinery/bodyscanner/MouseDrop_T(mob/living/carbon/O, mob/user as mob) + if(!istype(O)) + return 0 //not a mob + if(user.incapacitated()) + return 0 //user shouldn't be doing things + if(O.anchored) + return 0 //mob is anchored??? + if(get_dist(user, src) > 1 || get_dist(user, O) > 1) + return 0 //doesn't use adjacent() to allow for non-cardinal (fuck my life) + if(!ishuman(user) && !isrobot(user)) + return 0 //not a borg or human + if(panel_open) + user << "Close the maintenance panel first." + return 0 //panel open + if(occupant) + user << "\The [src] is already occupied." + return 0 //occupied + + if(O.buckled) + return 0 + if(O.abiotic()) + user << "Subject cannot have abiotic items on." + return 0 + for(var/mob/living/carbon/slime/M in range(1, O)) + if(M.Victim == O) + user << "[O] has a fucking slime attached to them, deal with that first." + return 0 + + if(O == user) + visible_message("[user] climbs into \the [src].") + else + visible_message("[user] puts [O] into the body scanner.") + + O.forceMove(src) + occupant = O + icon_state = "body_scanner_1" + add_fingerprint(user) + +/obj/machinery/bodyscanner/relaymove(mob/user as mob) + if(user.incapacitated()) + return 0 //maybe they should be able to get out with cuffs, but whatever + go_out() + +/obj/machinery/bodyscanner/verb/eject() + set src in oview(1) + set category = "Object" + set name = "Eject Body Scanner" + + if(usr.incapacitated()) + return + go_out() + add_fingerprint(usr) + +/obj/machinery/bodyscanner/proc/go_out() + if ((!( src.occupant ) || src.locked)) + return + if (src.occupant.client) + src.occupant.client.eye = src.occupant.client.mob + src.occupant.client.perspective = MOB_PERSPECTIVE + src.occupant.loc = src.loc + src.occupant = null + src.icon_state = "body_scanner_0" return /obj/machinery/bodyscanner/ex_act(severity) switch(severity) if(1.0) for(var/atom/movable/A as mob|obj in src) - if(A in component_parts) - continue - if(A == circuit) - continue A.loc = src.loc ex_act(severity) //Foreach goto(35) @@ -154,10 +152,6 @@ if(2.0) if (prob(50)) for(var/atom/movable/A as mob|obj in src) - if(A in component_parts) - continue - if(A == circuit) - continue A.loc = src.loc ex_act(severity) //Foreach goto(108) @@ -167,10 +161,6 @@ if(3.0) if (prob(25)) for(var/atom/movable/A as mob|obj in src) - if(A in component_parts) - continue - if(A == circuit) - continue A.loc = src.loc ex_act(severity) //Foreach goto(181) @@ -180,32 +170,7 @@ else return -/obj/machinery/body_scanconsole/ex_act(severity) - - switch(severity) - if(1.0) - //SN src = null - qdel(src) - return - if(2.0) - if (prob(50)) - //SN src = null - qdel(src) - return - else - return - -/obj/machinery/body_scanconsole/power_change() - ..() - if(stat & BROKEN) - icon_state = "body_scannerconsole-p" - else - if (stat & NOPOWER) - spawn(rand(0, 15)) - src.icon_state = "body_scannerconsole-p" - else - icon_state = initial(icon_state) - +//Body Scan Console /obj/machinery/body_scanconsole var/obj/machinery/bodyscanner/connected var/known_implants = list(/obj/item/weapon/implant/chem, /obj/item/weapon/implant/death_alarm, /obj/item/weapon/implant/loyalty, /obj/item/weapon/implant/tracking) @@ -218,67 +183,12 @@ density = 0 anchored = 1 circuit = /obj/item/weapon/circuitboard/scanner_console + var/printing = null + var/printing_text = null /obj/machinery/body_scanconsole/New() ..() - spawn( 5 ) - src.connected = locate(/obj/machinery/bodyscanner) in range(2,src) - return - return - -/* - -/obj/machinery/body_scanconsole/process() //not really used right now - if(stat & (NOPOWER|BROKEN)) - return - //use_power(250) // power stuff - -// var/mob/M //occupant -// if (!( src.status )) //remove this -// return -// if ((src.connected && src.connected.occupant)) //connected & occupant ok -// M = src.connected.occupant -// else -// if (istype(M, /mob)) -// //do stuff -// else -/// src.temphtml = "Process terminated due to lack of occupant in scanning chamber." -// src.status = null -// src.updateDialog() -// return - -*/ - -/obj/machinery/body_scanconsole/attack_ai(user as mob) - return src.attack_hand(user) - -/obj/machinery/body_scanconsole/attack_hand(user as mob) - if(..()) - return - if(stat & (NOPOWER|BROKEN)) - return - if(!connected || (connected.stat & (NOPOWER|BROKEN))) - user << "This console is not connected to a functioning body scanner." - return - if(!ishuman(connected.occupant)) - user << "This device can only scan compatible lifeforms." - return - - var/dat - if (src.delete && src.temphtml) //Window in buffer but its just simple message, so nothing - src.delete = src.delete - else if (!src.delete && src.temphtml) //Window in buffer - its a menu, dont add clear message - dat = text("[]

Main Menu", src.temphtml, src) - else - if (src.connected) //Is something connected? - dat = format_occupant_data(src.connected.get_occupant_data()) - dat += "
Print
" - else - dat = "Error: No Body Scanner connected." - - dat += text("
Close", user) - user << browse(dat, "window=scanconsole;size=430x600") - return + findscanner() /obj/machinery/body_scanconsole/attackby(var/obj/item/I, var/mob/user) if(istype(I, /obj/item/weapon/screwdriver) && circuit) @@ -311,205 +221,355 @@ src.attack_hand(user) return +/obj/machinery/body_scanconsole/power_change() + if(stat & BROKEN) + icon_state = "body_scannerconsole-p" + else if(powered() && !panel_open) + icon_state = initial(icon_state) + stat &= ~NOPOWER + else + spawn(rand(0, 15)) + src.icon_state = "body_scannerconsole-p" + stat |= NOPOWER + +/obj/machinery/body_scanconsole/ex_act(severity) + switch(severity) + if(1.0) + //SN src = null + qdel(src) + return + if(2.0) + if (prob(50)) + //SN src = null + qdel(src) + return + else + return + +/obj/machinery/body_scanconsole/proc/findscanner() + spawn( 5 ) + var/obj/machinery/bodyscanner/bodyscannernew = null + // Loop through every direction + for(dir in list(NORTH,EAST,SOUTH,WEST)) + // Try to find a scanner in that direction + bodyscannernew = locate(/obj/machinery/bodyscanner, get_step(src, dir)) + src.connected = bodyscannernew + return + return + +/obj/machinery/body_scanconsole/attack_ai(user as mob) + return attack_hand(user) + +/obj/machinery/body_scanconsole/attack_ghost(user as mob) + return attack_hand(user) + +/obj/machinery/body_scanconsole/attack_hand(user as mob) + if(stat & (NOPOWER|BROKEN)) + return + + if (panel_open) + user << "Close the maintenance panel first." + return + + if(!src.connected) + findscanner() + + ui_interact(user) + +/obj/machinery/body_scanconsole/ui_interact(mob/user, ui_key = "main", var/datum/nanoui/ui = null, var/force_open = 1) + var/data[0] + + data["connected"] = connected ? 1 : 0 + + if(connected) + data["occupied"] = connected.occupant ? 1 : 0 + + var/occupantData[0] + if(connected.occupant && ishuman(connected.occupant)) + var/mob/living/carbon/human/H = connected.occupant + occupantData["name"] = H.name + occupantData["stat"] = H.stat + occupantData["health"] = H.health + + occupantData["hasVirus"] = H.virus2.len + + occupantData["bruteLoss"] = H.getBruteLoss() + occupantData["oxyLoss"] = H.getOxyLoss() + occupantData["toxLoss"] = H.getToxLoss() + occupantData["fireLoss"] = H.getFireLoss() + + occupantData["radLoss"] = H.radiation + occupantData["cloneLoss"] = H.getCloneLoss() + occupantData["brainLoss"] = H.getBrainLoss() + occupantData["paralysis"] = H.paralysis + occupantData["paralysisSeconds"] = round(H.paralysis / 4) + occupantData["bodyTempC"] = H.bodytemperature-T0C + occupantData["bodyTempF"] = (((H.bodytemperature-T0C) * 1.8) + 32) + + occupantData["hasBorer"] = H.has_brain_worms() + + var/bloodData[0] + if(H.vessel) + var/blood_volume = round(H.vessel.get_reagent_amount("blood")) + bloodData["volume"] = blood_volume + bloodData["percent"] = round(((blood_volume / 560)*100)) + + occupantData["blood"] = bloodData + + var/reagentData[0] + if(H.reagents) + for(var/datum/reagent/R in H.reagents) + reagentData[++reagentData.len] = list("name" = R.name, "amount" = R.volume) + + occupantData["reagents"] = reagentData + + var/extOrganData[0] + for(var/obj/item/organ/external/E in H.organs) + var/organData[0] + organData["name"] = E.name + organData["open"] = E.open + organData["germ_level"] = E.germ_level + organData["bruteLoss"] = E.brute_dam + organData["fireLoss"] = E.burn_dam + + var/implantData[0] + for(var/obj/I in E.implants) + var/implantSubData[0] + implantSubData["name"] = I.name + if(is_type_in_list(I, known_implants)) + implantSubData["known"] = 1 + + implantData.Add(list(implantSubData)) + + organData["implants"] = implantData + organData["implants_len"] = implantData.len + + var/organStatus[0] + if(E.status & ORGAN_DESTROYED) + organStatus["destroyed"] = 1 + if(E.status & ORGAN_BROKEN) + organStatus["broken"] = E.broken_description + if(E.status & ORGAN_ROBOT) + organStatus["robotic"] = 1 + if(E.status & ORGAN_SPLINTED) + organStatus["splinted"] = 1 + if(E.status & ORGAN_BLEEDING) + organStatus["bleeding"] = 1 + + organData["status"] = organStatus + + if(istype(E, /obj/item/organ/external/chest) && H.is_lung_ruptured()) + organData["lungRuptured"] = 1 + + for(var/datum/wound/W in E.wounds) + if(W.internal) + organData["internalBleeding"] = 1 + break + + extOrganData.Add(list(organData)) + + occupantData["extOrgan"] = extOrganData + + var/intOrganData[0] + for(var/obj/item/organ/I in H.internal_organs) + var/organData[0] + organData["name"] = I.name + organData["desc"] = I.desc + organData["germ_level"] = I.germ_level + organData["damage"] = I.damage + + intOrganData.Add(list(organData)) + + occupantData["intOrgan"] = intOrganData + + occupantData["blind"] = (H.sdisabilities & BLIND) + occupantData["nearsighted"] = (H.disabilities & NEARSIGHTED) + + data["occupant"] = occupantData + + ui = nanomanager.try_update_ui(user, src, ui_key, ui, data, force_open) + if(!ui) + ui = new(user, src, ui_key, "adv_med.tmpl", "Body Scanner", 690, 600) + ui.set_initial_data(data) + ui.open() + ui.set_auto_update(1) + + /obj/machinery/body_scanconsole/Topic(href, href_list) - if (..()) - return + if(..()) + return 1 - if (href_list["print"]) - if (!src.connected) - usr << "\icon[src]Error: No body scanner connected." - return - var/mob/living/carbon/human/occupant = src.connected.occupant - if (!src.connected.occupant) - usr << "\icon[src]The body scanner is empty." - return - if (!istype(occupant,/mob/living/carbon/human)) - usr << "\icon[src]The body scanner cannot scan that lifeform." - return - var/obj/item/weapon/paper/R = new(src.loc) - R.name = "Body scan report" - R.info = format_occupant_data(src.connected.get_occupant_data()) + if (href_list["print_p"]) + generate_printing_text() + if (!(printing) && printing_text) + printing = 1 + visible_message("\The [src] rattles and prints out a sheet of paper.") + var/obj/item/weapon/paper/P = new /obj/item/weapon/paper(loc) + P.info = "
Body Scan - [href_list["name"]]

" + P.info += "Time of scan: [worldtime2text(world.time)]

" + P.info += "[printing_text]" + P.info += "

Notes:
" + P.name = "Body Scan - [href_list["name"]]" + printing = null + printing_text = null -/obj/machinery/bodyscanner/proc/get_occupant_data() - if (!occupant || !istype(occupant, /mob/living/carbon/human)) - return - var/mob/living/carbon/human/H = occupant - var/list/occupant_data = list( - "stationtime" = worldtime2text(), - "stat" = H.stat, - "health" = round(H.health/H.maxHealth)*100, - "virus_present" = H.virus2.len, - "bruteloss" = H.getBruteLoss(), - "fireloss" = H.getFireLoss(), - "oxyloss" = H.getOxyLoss(), - "toxloss" = H.getToxLoss(), - "rads" = H.radiation, - "cloneloss" = H.getCloneLoss(), - "brainloss" = H.getBrainLoss(), - "paralysis" = H.paralysis, - "bodytemp" = H.bodytemperature, - "borer_present" = H.has_brain_worms(), - "inaprovaline_amount" = H.reagents.get_reagent_amount("inaprovaline"), - "dexalin_amount" = H.reagents.get_reagent_amount("dexalin"), - "stoxin_amount" = H.reagents.get_reagent_amount("stoxin"), - "bicaridine_amount" = H.reagents.get_reagent_amount("bicaridine"), - "dermaline_amount" = H.reagents.get_reagent_amount("dermaline"), - "blood_amount" = round((H.vessel.get_reagent_amount("blood") / H.species.blood_volume)*100), - "disabilities" = H.sdisabilities, - "lung_ruptured" = H.is_lung_ruptured(), - "external_organs" = H.organs.Copy(), - "internal_organs" = H.internal_organs.Copy(), - "species_organs" = H.species.has_organ //Just pass a reference for this, it shouldn't ever be modified outside of the datum. - ) - return occupant_data +/obj/machinery/body_scanconsole/proc/generate_printing_text() + var/dat = "" - -/obj/machinery/body_scanconsole/proc/format_occupant_data(var/list/occ) - var/dat = "Scan performed at [occ["stationtime"]]
" - dat += "Occupant Statistics:
" - var/aux - switch (occ["stat"]) - if(0) - aux = "Conscious" - if(1) - aux = "Unconscious" - else - aux = "Dead" - dat += text("[]\tHealth %: [] ([])
", ("Viral pathogen detected in blood stream.
" - dat += text("[]\t-Brute Damage %: []
", (""), occ["bruteloss"]) - dat += text("[]\t-Respiratory Damage %: []
", (""), occ["oxyloss"]) - dat += text("[]\t-Toxin Content %: []
", (""), occ["toxloss"]) - dat += text("[]\t-Burn Severity %: []

", (""), occ["fireloss"]) - - dat += text("[]\tRadiation Level %: []
", (""), occ["rads"]) - dat += text("[]\tGenetic Tissue Damage %: []
", (""), occ["cloneloss"]) - dat += text("[]\tApprox. Brain Damage %: []
", (""), occ["brainloss"]) - dat += text("Paralysis Summary %: [] ([] seconds left!)
", occ["paralysis"], round(occ["paralysis"] / 4)) - dat += text("Body Temperature: [occ["bodytemp"]-T0C]°C ([occ["bodytemp"]*1.8-459.67]°F)

") - - if(occ["borer_present"]) - dat += "Large growth detected in frontal lobe, possibly cancerous. Surgical removal is recommended.
" - - dat += text("[]\tBlood Level %: [] ([] units)

", (""), occ["blood_amount"], occ["blood_amount"]) - - dat += text("Inaprovaline: [] units
", occ["inaprovaline_amount"]) - dat += text("Soporific: [] units
", occ["stoxin_amount"]) - dat += text("[]\tDermaline: [] units

", (""), occ["dermaline_amount"]) - dat += text("[]\tBicaridine: [] units
", (""), occ["bicaridine_amount"]) - dat += text("[]\tDexalin: [] units
", (""), occ["dexalin_amount"]) - - dat += "
" - dat += "" - dat += "" - dat += "" - dat += "" - dat += "" - dat += "" - - for(var/obj/item/organ/external/e in occ["external_organs"]) - var/AN = "" - var/open = "" - var/infected = "" - var/imp = "" - var/bled = "" - var/robot = "" - var/splint = "" - var/internal_bleeding = "" - var/lung_ruptured = "" - - dat += "" - - for(var/datum/wound/W in e.wounds) if(W.internal) - internal_bleeding = "
Internal bleeding" - break - if(istype(e, /obj/item/organ/external/chest) && occ["lung_ruptured"]) - lung_ruptured = "Lung ruptured:" - if(e.status & ORGAN_SPLINTED) - splint = "Splinted:" - if(e.status & ORGAN_BLEEDING) - bled = "Bleeding:" - if(e.status & ORGAN_BROKEN) - AN = "[e.broken_description]:" - if(e.status & ORGAN_ROBOT) - robot = "Prosthetic:" - if(e.open) - open = "Open:" - - switch (e.germ_level) - if (INFECTION_LEVEL_ONE to INFECTION_LEVEL_ONE + 200) - infected = "Mild Infection:" - if (INFECTION_LEVEL_ONE + 200 to INFECTION_LEVEL_ONE + 300) - infected = "Mild Infection+:" - if (INFECTION_LEVEL_ONE + 300 to INFECTION_LEVEL_ONE + 400) - infected = "Mild Infection++:" - if (INFECTION_LEVEL_TWO to INFECTION_LEVEL_TWO + 200) - infected = "Acute Infection:" - if (INFECTION_LEVEL_TWO + 200 to INFECTION_LEVEL_TWO + 300) - infected = "Acute Infection+:" - if (INFECTION_LEVEL_TWO + 300 to INFECTION_LEVEL_TWO + 400) - infected = "Acute Infection++:" - if (INFECTION_LEVEL_THREE to INFINITY) - infected = "Septic:" - if(e.rejecting) - infected += "(being rejected)" - if (e.implants.len) - var/unknown_body = 0 - for(var/I in e.implants) - if(is_type_in_list(I,known_implants)) - imp += "[I] implanted:" + if(connected) + var/mob/living/carbon/human/occupant = connected.occupant + dat = "Occupant Statistics:
" //Blah obvious + if(istype(occupant)) //is there REALLY someone in there? + var/t1 + switch(occupant.stat) // obvious, see what their status is + if(0) + t1 = "Conscious" + if(1) + t1 = "Unconscious" else - unknown_body++ - if(unknown_body) - imp += "Unknown body present:" + t1 = "*dead*" + dat += "[occupant.health > 50 ? "" : ""]\tHealth %: [occupant.health], ([t1])
" - if(!AN && !open && !infected & !imp) - AN = "None:" - if(!e.is_stump()) - dat += "
" + if(occupant.virus2.len) + dat += "Viral pathogen detected in blood stream.
" + + var/extra_font = null + extra_font = (occupant.getBruteLoss() < 60 ? "" : "") + dat += "[extra_font]\t-Brute Damage %: [occupant.getBruteLoss()]
" + + extra_font = (occupant.getOxyLoss() < 60 ? "" : "") + dat += "[extra_font]\t-Respiratory Damage %: [occupant.getOxyLoss()]
" + + extra_font = (occupant.getToxLoss() < 60 ? "" : "") + dat += "[extra_font]\t-Toxin Content %: [occupant.getToxLoss()]
" + + extra_font = (occupant.getFireLoss() < 60 ? "" : "") + dat += "[extra_font]\t-Burn Severity %: [occupant.getFireLoss()]
" + + extra_font = (occupant.radiation < 10 ?"" : "") + dat += "[extra_font]\tRadiation Level %: [occupant.radiation]
" + + extra_font = (occupant.getCloneLoss() < 1 ?"" : "") + dat += "[extra_font]\tGenetic Tissue Damage %: [occupant.getCloneLoss()]
" + + extra_font = (occupant.getBrainLoss() < 1 ?"" : "") + dat += "[extra_font]\tApprox. Brain Damage %: [occupant.getBrainLoss()]
" + + dat += "Paralysis Summary %: [occupant.paralysis] ([round(occupant.paralysis / 4)] seconds left!)
" + dat += "Body Temperature: [occupant.bodytemperature-T0C]°C ([occupant.bodytemperature*1.8-459.67]°F)
" + + dat += "
" + + if(occupant.has_brain_worms()) + dat += "Large growth detected in frontal lobe, possibly cancerous. Surgical removal is recommended.
" + + if(occupant.vessel) + var/blood_volume = round(occupant.vessel.get_reagent_amount("blood")) + var/blood_percent = blood_volume / 560 + blood_percent *= 100 + + extra_font = (blood_volume > 448 ? "" : "") + dat += "[extra_font]\tBlood Level %: [blood_percent] ([blood_volume] units)
" + + if(occupant.reagents) + for(var/datum/reagent/R in occupant.reagents) + dat += "Reagent: [R.name], Amount: [R.volume]
" + + dat += "
OrganBurn DamageBrute DamageOther Wounds
[e.name][e.burn_dam][e.brute_dam][robot][bled][AN][splint][open][infected][imp][internal_bleeding][lung_ruptured]
" + dat += "" + dat += "" + dat += "" + dat += "" + dat += "" + dat += "" + + for(var/obj/item/organ/external/e in occupant.organs) + dat += "" + var/AN = "" + var/open = "" + var/infected = "" + var/robot = "" + var/imp = "" + var/bled = "" + var/splint = "" + var/internal_bleeding = "" + var/lung_ruptured = "" + for(var/datum/wound/W in e.wounds) if(W.internal) + internal_bleeding = "
Internal bleeding" + break + if(istype(e, /obj/item/organ/external/chest) && occupant.is_lung_ruptured()) + lung_ruptured = "Lung ruptured:" + if(e.status & ORGAN_SPLINTED) + splint = "Splinted:" + if(e.status & ORGAN_BLEEDING) + bled = "Bleeding:" + if(e.status & ORGAN_BROKEN) + AN = "[e.broken_description]:" + if(e.status & ORGAN_ROBOT) + robot = "Prosthetic:" + if(e.open) + open = "Open:" + switch (e.germ_level) + if (INFECTION_LEVEL_ONE to INFECTION_LEVEL_ONE + 200) + infected = "Mild Infection:" + if (INFECTION_LEVEL_ONE + 200 to INFECTION_LEVEL_ONE + 300) + infected = "Mild Infection+:" + if (INFECTION_LEVEL_ONE + 300 to INFECTION_LEVEL_ONE + 400) + infected = "Mild Infection++:" + if (INFECTION_LEVEL_TWO to INFECTION_LEVEL_TWO + 200) + infected = "Acute Infection:" + if (INFECTION_LEVEL_TWO + 200 to INFECTION_LEVEL_TWO + 300) + infected = "Acute Infection+:" + if (INFECTION_LEVEL_TWO + 300 to INFECTION_LEVEL_TWO + 400) + infected = "Acute Infection++:" + if (INFECTION_LEVEL_THREE to INFINITY) + infected = "Septic:" + + var/unknown_body = 0 + for(var/I in e.implants) + if(is_type_in_list(I,known_implants)) + imp += "[I] implanted:" + else + unknown_body++ + + if(unknown_body) + imp += "Unknown body present:" + if(!AN && !open && !infected & !imp) + AN = "None:" + if(!(e.status & ORGAN_DESTROYED)) + dat += "
" + else + dat += "" + dat += "" + for(var/obj/item/organ/i in occupant.internal_organs) + var/mech = i.desc + var/infection = "None" + switch (i.germ_level) + if (1 to INFECTION_LEVEL_ONE + 200) + infection = "Mild Infection:" + if (INFECTION_LEVEL_ONE + 200 to INFECTION_LEVEL_ONE + 300) + infection = "Mild Infection+:" + if (INFECTION_LEVEL_ONE + 300 to INFECTION_LEVEL_ONE + 400) + infection = "Mild Infection++:" + if (INFECTION_LEVEL_TWO to INFECTION_LEVEL_TWO + 200) + infection = "Acute Infection:" + if (INFECTION_LEVEL_TWO + 200 to INFECTION_LEVEL_TWO + 300) + infection = "Acute Infection+:" + if (INFECTION_LEVEL_TWO + 300 to INFINITY) + infection = "Acute Infection++:" + + dat += "" + dat += "" + dat += "" + dat += "
OrganBurn DamageBrute DamageOther Wounds
[e.name][e.burn_dam][e.brute_dam][robot][bled][AN][splint][open][infected][imp][internal_bleeding][lung_ruptured][e.name]--Not Found
[i.name]N/A[i.damage][infection]:[mech]
" + if(occupant.sdisabilities & BLIND) + dat += "Cataracts detected.
" + if(occupant.disabilities & NEARSIGHTED) + dat += "Retinal misalignment detected.
" else - dat += "[e.name]--Not [e.is_stump() ? "Found" : "Attached Completely"]" - dat += "" + dat += "\The [src] is empty." + else + dat = " Error: No Body Scanner connected." - for(var/obj/item/organ/i in occ["internal_organs"]) - - var/mech = "" - if(i.status & ORGAN_ASSISTED) - mech = "Assisted:" - if(i.status & ORGAN_ROBOT) - mech = "Mechanical:" - - var/infection = "None" - switch (i.germ_level) - if (1 to INFECTION_LEVEL_ONE + 200) - infection = "Mild Infection:" - if (INFECTION_LEVEL_ONE + 200 to INFECTION_LEVEL_ONE + 300) - infection = "Mild Infection+:" - if (INFECTION_LEVEL_ONE + 300 to INFECTION_LEVEL_ONE + 400) - infection = "Mild Infection++:" - if (INFECTION_LEVEL_TWO to INFECTION_LEVEL_TWO + 200) - infection = "Acute Infection:" - if (INFECTION_LEVEL_TWO + 200 to INFECTION_LEVEL_TWO + 300) - infection = "Acute Infection+:" - if (INFECTION_LEVEL_TWO + 300 to INFINITY) - infection = "Acute Infection++:" - if(i.rejecting) - infection += "(being rejected)" - - dat += "" - dat += "[i.name]N/A[i.damage][infection]:[mech]" - dat += "" - dat += "" - - var/list/species_organs = occ["species_organs"] - for(var/organ_name in species_organs) - if(!locate(species_organs[organ_name]) in occ["internal_organs"]) - dat += text("No [organ_name] detected.
") - - if(occ["sdisabilities"] & BLIND) - dat += text("Cataracts detected.
") - if(occ["sdisabilities"] & NEARSIGHTED) - dat += text("Retinal misalignment detected.
") - return dat + printing_text = dat \ No newline at end of file diff --git a/code/game/machinery/atmo_control.dm b/code/game/machinery/atmo_control.dm index c7b5f3c73a..43b9bf5913 100644 --- a/code/game/machinery/atmo_control.dm +++ b/code/game/machinery/atmo_control.dm @@ -94,13 +94,8 @@ obj/machinery/computer/general_air_control/Destroy() /obj/machinery/computer/general_air_control/attack_hand(mob/user) if(..(user)) return - user << browse(return_text(),"window=computer") - user.set_machine(src) - onclose(user, "computer") -/obj/machinery/computer/general_air_control/process() - ..() - src.updateUsrDialog() + ui_interact(user) /obj/machinery/computer/general_air_control/receive_signal(datum/signal/signal) if(!signal || signal.encryption) return @@ -110,43 +105,27 @@ obj/machinery/computer/general_air_control/Destroy() sensor_information[id_tag] = signal.data -/obj/machinery/computer/general_air_control/proc/return_text() - var/sensor_data +/obj/machinery/computer/general_air_control/ui_interact(mob/user, ui_key = "main", var/datum/nanoui/ui = null, var/force_open = 1) + user.set_machine(src) + + var/list/data = list() + var/sensors_ui[0] if(sensors.len) for(var/id_tag in sensors) var/long_name = sensors[id_tag] - var/list/data = sensor_information[id_tag] - var/sensor_part = "[long_name]:
" - - if(data) - if(data["pressure"]) - sensor_part += " Pressure: [data["pressure"]] kPa
" - if(data["temperature"]) - sensor_part += " Temperature: [data["temperature"]] K
" - if(data["oxygen"]||data["phoron"]||data["nitrogen"]||data["carbon_dioxide"]) - sensor_part += " Gas Composition :" - if(data["oxygen"]) - sensor_part += "[data["oxygen"]]% O2; " - if(data["nitrogen"]) - sensor_part += "[data["nitrogen"]]% N; " - if(data["carbon_dioxide"]) - sensor_part += "[data["carbon_dioxide"]]% CO2; " - if(data["phoron"]) - sensor_part += "[data["phoron"]]% TX; " - sensor_part += "
" - - else - sensor_part = "[long_name] can not be found!
" - - sensor_data += sensor_part - + var/list/sensor_data = sensor_information[id_tag] + sensors_ui[++sensors_ui.len] = list("long_name" = long_name, "sensor_data" = sensor_data) else - sensor_data = "No sensors connected." + sensors_ui = null - var/output = {"[name]
-Sensor Data:

[sensor_data]"} + data["sensors"] = sensors_ui - return output + ui = nanomanager.try_update_ui(user, src, ui_key, ui, data, force_open) + if (!ui) + ui = new(user, src, ui_key, "atmo_control.tmpl", src.name, 400, 500) + ui.set_initial_data(data) + ui.open() + ui.set_auto_update(5) /obj/machinery/computer/general_air_control/proc/set_frequency(new_frequency) radio_controller.remove_object(src, frequency) @@ -156,7 +135,6 @@ obj/machinery/computer/general_air_control/Destroy() /obj/machinery/computer/general_air_control/initialize() set_frequency(frequency) - /obj/machinery/computer/general_air_control/large_tank_control icon = 'icons/obj/computer.dmi' @@ -171,39 +149,40 @@ obj/machinery/computer/general_air_control/Destroy() var/pressure_setting = ONE_ATMOSPHERE * 45 circuit = /obj/item/weapon/circuitboard/air_management/tank_control +/obj/machinery/computer/general_air_control/large_tank_control/ui_interact(mob/user, ui_key = "main", var/datum/nanoui/ui = null, var/force_open = 1) + user.set_machine(src) -/obj/machinery/computer/general_air_control/large_tank_control/return_text() - var/output = ..() - //if(signal.data) - // input_info = signal.data // Attempting to fix intake control -- TLE + var/list/data = list() + var/sensors_ui[0] + if(sensors.len) + for(var/id_tag in sensors) + var/long_name = sensors[id_tag] + var/list/sensor_data = sensor_information[id_tag] + sensors_ui[++sensors_ui.len] = list("long_name" = long_name, "sensor_data" = sensor_data) + else + sensors_ui = null + + data["sensors"] = sensors_ui + data["tanks"] = 1 - output += "Tank Control System

" if(input_info) - var/power = (input_info["power"]) - var/volume_rate = round(input_info["volume_rate"], 0.1) - output += "Input: [power?("Injecting"):("On Hold")] Refresh
Flow Rate Limit: [volume_rate] L/s
" - output += "Command: Toggle Power Set Flow Rate
" - + data["input_info"] = list("power" = input_info["power"], "volume_rate" = round(input_info["volume_rate"], 0.1)) else - output += "ERROR: Can not find input port Search
" - - output += "Flow Rate Limit: - - - - [round(input_flow_setting, 0.1)] L/s + + + +
" - - output += "
" - + data["input_info"] = null if(output_info) - var/power = (output_info["power"]) - var/output_pressure = output_info["internal"] - output += {"Output: [power?("Open"):("On Hold")] Refresh
-Max Output Pressure: [output_pressure] kPa
"} - output += "Command: Toggle Power Set Pressure
" - + data["output_info"] = list("power" = output_info["power"], "output_pressure" = output_info["internal"]) else - output += "ERROR: Can not find output port Search
" + data["output_info"] = null - output += "Max Output Pressure Set: - - - - [pressure_setting] kPa + + + +
" + data["input_flow_setting"] = round(input_flow_setting, 0.1) + data["pressure_setting"] = pressure_setting - return output + ui = nanomanager.try_update_ui(user, src, ui_key, ui, data, force_open) + if (!ui) + ui = new(user, src, ui_key, "atmo_control.tmpl", src.name, 400, 500) + ui.set_initial_data(data) + ui.open() + ui.set_auto_update(5) /obj/machinery/computer/general_air_control/large_tank_control/receive_signal(datum/signal/signal) if(!signal || signal.encryption) return @@ -222,17 +201,13 @@ Max Output Pressure: [output_pressure] kPa
"} return 1 if(href_list["adj_pressure"]) - var/change = text2num(href_list["adj_pressure"]) + var/change = href_list["adj_pressure"] pressure_setting = between(0, pressure_setting + change, 50*ONE_ATMOSPHERE) - spawn(1) - src.updateUsrDialog() return 1 if(href_list["adj_input_flow_rate"]) - var/change = text2num(href_list["adj_input_flow_rate"]) + var/change = href_list["adj_input_flow_rate"] input_flow_setting = between(0, input_flow_setting + change, ATMOS_DEFAULT_VOLUME_PUMP + 500) //default flow rate limit for air injectors - spawn(1) - src.updateUsrDialog() return 1 if(!radio_connection) @@ -273,9 +248,6 @@ Max Output Pressure: [output_pressure] kPa
"} signal.data["sigtype"]="command" radio_connection.post_signal(src, signal, filter = RADIO_ATMOSIA) - spawn(5) - src.updateUsrDialog() - /obj/machinery/computer/general_air_control/supermatter_core icon = 'icons/obj/computer.dmi' @@ -290,39 +262,40 @@ Max Output Pressure: [output_pressure] kPa
"} var/pressure_setting = 100 circuit = /obj/item/weapon/circuitboard/air_management/supermatter_core +/obj/machinery/computer/general_air_control/supermatter_core/ui_interact(mob/user, ui_key = "main", var/datum/nanoui/ui = null, var/force_open = 1) + user.set_machine(src) -/obj/machinery/computer/general_air_control/supermatter_core/return_text() - var/output = ..() - //if(signal.data) - // input_info = signal.data // Attempting to fix intake control -- TLE + var/list/data = list() + var/sensors_ui[0] + if(sensors.len) + for(var/id_tag in sensors) + var/long_name = sensors[id_tag] + var/list/sensor_data = sensor_information[id_tag] + sensors_ui[++sensors_ui.len] = list("long_name" = long_name, "sensor_data" = sensor_data) + else + sensors_ui = null + + data["sensors"] = sensors_ui + data["core"] = 1 - output += "Core Cooling Control System

" if(input_info) - var/power = (input_info["power"]) - var/volume_rate = round(input_info["volume_rate"], 0.1) - output += "Coolant Input: [power?("Injecting"):("On Hold")] Refresh
Flow Rate Limit: [volume_rate] L/s
" - output += "Command: Toggle Power Set Flow Rate
" - + data["input_info"] = list("power" = input_info["power"], "volume_rate" = round(input_info["volume_rate"], 0.1)) else - output += "ERROR: Can not find input port Search
" - - output += "Flow Rate Limit: - - - - [round(input_flow_setting, 0.1)] L/s + + + +
" - - output += "
" - + data["input_info"] = null if(output_info) - var/power = (output_info["power"]) - var/pressure_limit = output_info["external"] - output += {"Core Outpump: [power?("Open"):("On Hold")] Refresh
-Min Core Pressure: [pressure_limit] kPa
"} - output += "Command: Toggle Power Set Pressure
" - + data["output_info"] = list("power" = output_info["power"], "pressure_limit" = output_info["external"]) else - output += "ERROR: Can not find output port Search
" + data["output_info"] = null - output += "Min Core Pressure Set: - - - - [pressure_setting] kPa + + + +
" + data["input_flow_setting"] = round(input_flow_setting, 0.1) + data["pressure_setting"] = pressure_setting - return output + ui = nanomanager.try_update_ui(user, src, ui_key, ui, data, force_open) + if (!ui) + ui = new(user, src, ui_key, "atmo_control.tmpl", src.name, 400, 500) + ui.set_initial_data(data) + ui.open() + ui.set_auto_update(5) /obj/machinery/computer/general_air_control/supermatter_core/receive_signal(datum/signal/signal) if(!signal || signal.encryption) return @@ -341,17 +314,13 @@ Min Core Pressure: [pressure_limit] kPa
"} return 1 if(href_list["adj_pressure"]) - var/change = text2num(href_list["adj_pressure"]) + var/change = href_list["adj_pressure"] pressure_setting = between(0, pressure_setting + change, 10*ONE_ATMOSPHERE) - spawn(1) - src.updateUsrDialog() return 1 if(href_list["adj_input_flow_rate"]) - var/change = text2num(href_list["adj_input_flow_rate"]) + var/change = href_list["adj_input_flow_rate"] input_flow_setting = between(0, input_flow_setting + change, ATMOS_DEFAULT_VOLUME_PUMP + 500) //default flow rate limit for air injectors - spawn(1) - src.updateUsrDialog() return 1 if(!radio_connection) @@ -392,9 +361,6 @@ Min Core Pressure: [pressure_limit] kPa
"} signal.data["sigtype"]="command" radio_connection.post_signal(src, signal, filter = RADIO_ATMOSIA) - spawn(5) - src.updateUsrDialog() - /obj/machinery/computer/general_air_control/fuel_injection icon = 'icons/obj/computer.dmi' icon_screen = "alert:0" @@ -437,27 +403,34 @@ Min Core Pressure: [pressure_limit] kPa
"} ..() -/obj/machinery/computer/general_air_control/fuel_injection/return_text() - var/output = ..() - - output += "Fuel Injection System
" - if(device_info) - var/power = device_info["power"] - var/volume_rate = device_info["volume_rate"] - output += {"Status: [power?("Injecting"):("On Hold")] Refresh
-Rate: [volume_rate] L/sec
"} - - if(automation) - output += "Automated Fuel Injection: Engaged
" - output += "Injector Controls Locked Out
" - else - output += "Automated Fuel Injection: Disengaged
" - output += "Injector: Toggle Power Inject (1 Cycle)
" +/obj/machinery/computer/general_air_control/fuel_injection/ui_interact(mob/user, ui_key = "main", var/datum/nanoui/ui = null, var/force_open = 1) + user.set_machine(src) + var/list/data = list() + var/sensors_ui[0] + if(sensors.len) + for(var/id_tag in sensors) + var/long_name = sensors[id_tag] + var/list/sensor_data = sensor_information[id_tag] + sensors_ui[++sensors_ui.len] = list("long_name" = long_name, "sensor_data" = sensor_data) else - output += "ERROR: Can not find device Search
" + sensors_ui = null - return output + data["sensors"] = sensors_ui + data["fuel"] = 1 + data["automation"] = automation + + if(device_info) + data["device_info"] = list("power" = device_info["power"], "volume_rate" = device_info["volume_rate"]) + else + data["device_info"] = null + + ui = nanomanager.try_update_ui(user, src, ui_key, ui, data, force_open) + if (!ui) + ui = new(user, src, ui_key, "atmo_control.tmpl", src.name, 400, 500) + ui.set_initial_data(data) + ui.open() + ui.set_auto_update(5) /obj/machinery/computer/general_air_control/fuel_injection/receive_signal(datum/signal/signal) if(!signal || signal.encryption) return diff --git a/code/game/machinery/computer/Operating.dm b/code/game/machinery/computer/Operating.dm index 8427a08418..5cc9801d0f 100644 --- a/code/game/machinery/computer/Operating.dm +++ b/code/game/machinery/computer/Operating.dm @@ -22,62 +22,51 @@ add_fingerprint(user) if(stat & (BROKEN|NOPOWER)) return - interact(user) + ui_interact(user) /obj/machinery/computer/operating/attack_hand(mob/user) add_fingerprint(user) if(stat & (BROKEN|NOPOWER)) return - interact(user) - - -/obj/machinery/computer/operating/interact(mob/user) - if ( (get_dist(src, user) > 1 ) || (stat & (BROKEN|NOPOWER)) ) - if (!istype(user, /mob/living/silicon)) - user.unset_machine() - user << browse(null, "window=op") - return + ui_interact(user) +/** + * Display the NanoUI window for the operating computer. + * + * See NanoUI documentation for details. + */ +/obj/machinery/computer/operating/ui_interact(mob/user, ui_key = "main", var/datum/nanoui/ui = null, var/force_open = 1) user.set_machine(src) - var/dat = "Operating Computer\n" - dat += "Close

" //| Update" - if(src.table && (src.table.check_victim())) - src.victim = src.table.victim - dat += {" -Patient Information:
-
-Name: [src.victim.real_name]
-Age: [src.victim.age]
-Blood Type: [src.victim.b_type]
-
-Health: [src.victim.health]
-Brute Damage: [src.victim.getBruteLoss()]
-Toxins Damage: [src.victim.getToxLoss()]
-Fire Damage: [src.victim.getFireLoss()]
-Suffocation Damage: [src.victim.getOxyLoss()]
-Patient Status: [src.victim.stat ? "Non-Responsive" : "Stable"]
-Heartbeat rate: [victim.get_pulse(GETPULSE_TOOL)]
-"} - else - src.victim = null - dat += {" -Patient Information:
-
-No Patient Detected -"} - user << browse(dat, "window=op") - onclose(user, "op") + var/list/data = list() + var/list/victim_ui = list() + + if(table && (table.check_victim())) + victim = table.victim + + victim_ui = list("real_name" = victim.real_name, "age" = victim.age, "b_type" = victim.b_type, "health" = victim.health, + "brute" = victim.getBruteLoss(), "tox" = src.victim.getToxLoss(), "burn" = victim.getFireLoss(), "oxy" = victim.getOxyLoss(), + "stat" = (victim.stat ? "Non-Responsive" : "Stable"), "pulse" = victim.get_pulse(GETPULSE_TOOL)) + else + victim = null + victim_ui = null + + data["table"] = table + data["victim"] = victim_ui + + ui = nanomanager.try_update_ui(user, src, ui_key, ui, data, force_open) + if (!ui) + ui = new(user, src, ui_key, "operating.tmpl", src.name, 380, 400) + ui.set_initial_data(data) + ui.open() + ui.set_auto_update(5) /obj/machinery/computer/operating/Topic(href, href_list) if(..()) return 1 if ((usr.contents.Find(src) || (in_range(src, usr) && istype(src.loc, /turf))) || (istype(usr, /mob/living/silicon))) usr.set_machine(src) - return - -/obj/machinery/computer/operating/process() - if(..()) - src.updateDialog() + src.add_fingerprint(usr) + nanomanager.update_uis(src) \ No newline at end of file diff --git a/code/game/machinery/computer/arcade.dm b/code/game/machinery/computer/arcade.dm index 189fe5b40a..68b62bd1ab 100644 --- a/code/game/machinery/computer/arcade.dm +++ b/code/game/machinery/computer/arcade.dm @@ -53,7 +53,7 @@ prize.loc = src.loc /obj/machinery/computer/arcade/attack_ai(mob/user as mob) - return src.attack_hand(user) + return attack_hand(user) /obj/machinery/computer/arcade/emp_act(severity) @@ -103,81 +103,79 @@ name_part1 = pick("the Automatic ", "Farmer ", "Lord ", "Professor ", "the Cuban ", "the Evil ", "the Dread King ", "the Space ", "Lord ", "the Great ", "Duke ", "General ") name_part2 = pick("Melonoid", "Murdertron", "Sorcerer", "Ruin", "Jeff", "Ectoplasm", "Crushulon", "Uhangoid", "Vhakoid", "Peteoid", "slime", "Griefer", "ERPer", "Lizard Man", "Unicorn", "Bloopers") - src.enemy_name = replacetext((name_part1 + name_part2), "the ", "") - src.name = (name_action + name_part1 + name_part2) + enemy_name = replacetext((name_part1 + name_part2), "the ", "") + name = (name_action + name_part1 + name_part2) /obj/machinery/computer/arcade/battle/attack_hand(mob/user as mob) if(..()) return user.set_machine(src) - var/dat = "Close" - dat += "

[src.enemy_name]

" + ui_interact(user) - dat += "

[src.temp]

" - dat += "
Health: [src.player_hp] | Magic: [src.player_mp] | Enemy Health: [src.enemy_hp]
" +/** + * Display the NanoUI window for the arcade machine. + * + * See NanoUI documentation for details. + */ +/obj/machinery/computer/arcade/battle/ui_interact(mob/user, ui_key = "main", var/datum/nanoui/ui = null, var/force_open = 1) + user.set_machine(src) - dat += "
" - if (src.gameover) - dat += "New Game" - else - dat += "Attack | " - dat += "Heal | " - dat += "Recharge Power" + var/list/data = list() + data["temp"] = temp + data["enemyName"] = enemy_name + data["playerHP"] = player_hp + data["playerMP"] = player_mp + data["enemyHP"] = enemy_hp + data["gameOver"] = gameover - dat += "
" - - user << browse(dat, "window=arcade") - onclose(user, "arcade") - return + ui = nanomanager.try_update_ui(user, src, ui_key, ui, data, force_open) + if (!ui) + ui = new(user, src, ui_key, "arcade_battle.tmpl", src.name, 400, 500) + ui.set_initial_data(data) + ui.open() + //ui.set_auto_update(2) /obj/machinery/computer/arcade/battle/Topic(href, href_list) if(..()) return 1 - if (!src.blocked && !src.gameover) + if (!blocked && !gameover) if (href_list["attack"]) - src.blocked = 1 + blocked = 1 var/attackamt = rand(2,6) - src.temp = "You attack for [attackamt] damage!" - src.updateUsrDialog() + temp = "You attack for [attackamt] damage!" if(turtle > 0) turtle-- sleep(10) - src.enemy_hp -= attackamt - src.arcade_action() + enemy_hp -= attackamt + arcade_action() else if (href_list["heal"]) - src.blocked = 1 + blocked = 1 var/pointamt = rand(1,3) var/healamt = rand(6,8) - src.temp = "You use [pointamt] magic to heal for [healamt] damage!" - src.updateUsrDialog() + temp = "You use [pointamt] magic to heal for [healamt] damage!" turtle++ sleep(10) - src.player_mp -= pointamt - src.player_hp += healamt - src.blocked = 1 - src.updateUsrDialog() - src.arcade_action() + player_mp -= pointamt + player_hp += healamt + blocked = 1 + arcade_action() else if (href_list["charge"]) - src.blocked = 1 + blocked = 1 var/chargeamt = rand(4,7) - src.temp = "You regain [chargeamt] points" - src.player_mp += chargeamt + temp = "You regain [chargeamt] points" + player_mp += chargeamt if(turtle > 0) turtle-- - src.updateUsrDialog() sleep(10) - src.arcade_action() + arcade_action() - if (href_list["close"]) - usr.unset_machine() - usr << browse(null, "window=arcade") else if (href_list["newgame"]) //Reset everything temp = "New Round" @@ -193,14 +191,14 @@ emagged = 0 src.add_fingerprint(usr) - src.updateUsrDialog() + nanomanager.update_uis(src) return /obj/machinery/computer/arcade/battle/proc/arcade_action() - if ((src.enemy_mp <= 0) || (src.enemy_hp <= 0)) + if ((enemy_mp <= 0) || (enemy_hp <= 0)) if(!gameover) - src.gameover = 1 - src.temp = "[src.enemy_name] has fallen! Rejoice!" + gameover = 1 + temp = "[enemy_name] has fallen! Rejoice!" if(emagged) feedback_inc("arcade_win_emagged") @@ -212,53 +210,52 @@ emagged = 0 else if(!contents.len) feedback_inc("arcade_win_normal") - src.prizevend() + prizevend() else feedback_inc("arcade_win_normal") - src.prizevend() + prizevend() else if (emagged && (turtle >= 4)) var/boomamt = rand(5,10) - src.temp = "[src.enemy_name] throws a bomb, exploding you for [boomamt] damage!" - src.player_hp -= boomamt + temp = "[enemy_name] throws a bomb, exploding you for [boomamt] damage!" + player_hp -= boomamt - else if ((src.enemy_mp <= 5) && (prob(70))) + else if ((enemy_mp <= 5) && (prob(70))) var/stealamt = rand(2,3) - src.temp = "[src.enemy_name] steals [stealamt] of your power!" - src.player_mp -= stealamt - src.updateUsrDialog() + temp = "[enemy_name] steals [stealamt] of your power!" + player_mp -= stealamt - if (src.player_mp <= 0) - src.gameover = 1 + if (player_mp <= 0) + gameover = 1 sleep(10) - src.temp = "You have been drained! GAME OVER" + temp = "You have been drained! GAME OVER" if(emagged) feedback_inc("arcade_loss_mana_emagged") usr.gib() else feedback_inc("arcade_loss_mana_normal") - else if ((src.enemy_hp <= 10) && (src.enemy_mp > 4)) - src.temp = "[src.enemy_name] heals for 4 health!" - src.enemy_hp += 4 - src.enemy_mp -= 4 + else if ((enemy_hp <= 10) && (enemy_mp > 4)) + temp = "[enemy_name] heals for 4 health!" + enemy_hp += 4 + enemy_mp -= 4 else var/attackamt = rand(3,6) - src.temp = "[src.enemy_name] attacks for [attackamt] damage!" - src.player_hp -= attackamt + temp = "[enemy_name] attacks for [attackamt] damage!" + player_hp -= attackamt - if ((src.player_mp <= 0) || (src.player_hp <= 0)) - src.gameover = 1 - src.temp = "You have been crushed! GAME OVER" + if ((player_mp <= 0) || (player_hp <= 0)) + gameover = 1 + temp = "You have been crushed! GAME OVER" if(emagged) feedback_inc("arcade_loss_hp_emagged") usr.gib() else feedback_inc("arcade_loss_hp_normal") - src.blocked = 0 + blocked = 0 return @@ -276,7 +273,6 @@ enemy_name = "Cuban Pete" name = "Outbomb Cuban Pete" - src.updateUsrDialog() return 1 diff --git a/code/game/machinery/computer/cloning.dm b/code/game/machinery/computer/cloning.dm index 83b6f2ce86..68bac8ec1e 100644 --- a/code/game/machinery/computer/cloning.dm +++ b/code/game/machinery/computer/cloning.dm @@ -16,6 +16,7 @@ var/obj/item/weapon/disk/data/diskette = null //Mostly so the geneticist can steal everything. var/loading = 0 // Nice loading text + /obj/machinery/computer/cloning/initialize() ..() updatemodules() @@ -25,7 +26,7 @@ ..() /obj/machinery/computer/cloning/proc/updatemodules() - src.scanner = findscanner() + scanner = findscanner() releasecloner() findcloner() @@ -63,12 +64,12 @@ /obj/machinery/computer/cloning/attackby(obj/item/W as obj, mob/user as mob) if (istype(W, /obj/item/weapon/disk/data)) //INSERT SOME DISKETTES - if (!src.diskette) + if (!diskette) user.drop_item() W.loc = src - src.diskette = W + diskette = W user << "You insert [W]." - src.updateUsrDialog() + updateUsrDialog() return else if(istype(W, /obj/item/device/multitool)) var/obj/item/device/multitool/M = W @@ -78,6 +79,15 @@ P.connected = src P.name = "[initial(P.name)] #[pods.len]" user << "You connect [P] to [src]." + + else if (menu == 4 && (istype(W, /obj/item/weapon/card/id) || istype(W, /obj/item/device/pda))) + if(check_access(W)) + records.Remove(active_record) + qdel(active_record) + temp = "Record deleted." + menu = 2 + else + temp = "Access Denied." else ..() return @@ -94,109 +104,53 @@ updatemodules() - var/dat = "

Cloning System Control

" - dat += "Refresh" + ui_interact(user) - dat += "
[temp]
" +/obj/machinery/computer/cloning/ui_interact(mob/user, ui_key = "main", var/datum/nanoui/ui = null, var/force_open = 1) + user.set_machine(src) - switch(src.menu) - if(1) - // Modules - dat += "

Modules

" - //dat += "Reload Modules" - if (isnull(src.scanner)) - dat += " DNA scanner not found.
" - else - dat += " DNA scanner found.
" - if (pods.len) - dat += " [pods.len] cloning vat\s found.
" - else - dat += " No cloning vats found.
" + var/data[0] - // Scanner - dat += "

Scanner Functions

" + var/records_list_ui[0] + for(var/datum/dna2/record/R in records) + records_list_ui[++records_list_ui.len] = list("record" = R, "name" = R.dna.real_name) - if(loading) - dat += "Scanning...
" - else - dat += "[scantemp]
" + var/pods_list_ui[0] + for(var/obj/machinery/clonepod/pod in pods) + pods_list_ui[++pods_list_ui.len] = list("pod" = pod, "biomass" = pod.biomass) - if (isnull(src.scanner)) - dat += "No scanner connected!
" - else - if (src.scanner.occupant) - if(scantemp == "Scanner unoccupied") scantemp = "" // Stupid check to remove the text + if(pods) + data["pods"] = pods + else + data["pods"] = null - dat += "Scan - [src.scanner.occupant]
" - else - scantemp = "Scanner unoccupied" + if(records) + data["records"] = records_list_ui + else + data["records"] = null - dat += "Lock status: [src.scanner.locked ? "Locked" : "Unlocked"]
" + if(active_record) + data["activeRecord"] = list("active_record" = active_record, "real_name" = active_record.dna.real_name, \ + "ui" = active_record.dna.uni_identity, "se" = active_record.dna.struc_enzymes) + else + data["activeRecord"] = null - if (pods.len) - for (var/obj/machinery/clonepod/pod in pods) - dat += "[pod] biomass: [pod.biomass]
" + data["menu"] = menu + data["connected"] = scanner + data["podsLen"] = pods.len + data["loading"] = loading + data["scantemp"] = scantemp + data["occupant"] = scanner.occupant + data["locked"] = scanner.locked + data["diskette"] = diskette + data["temp"] = temp - // Database - dat += "

Database Functions

" - dat += "View Records
" - if (src.diskette) - dat += "Eject Disk" - - - if(2) - dat += "

Current records

" - dat += "Back

" - for(var/datum/dna2/record/R in src.records) - dat += "
  • [R.dna.real_name]
  • " - - if(3) - dat += "

    Selected Record

    " - dat += "Back
    " - - if (!src.active_record) - dat += "ERROR: Record not found." - else - dat += {"
    Delete Record
    - Name: [src.active_record.dna.real_name]
    "} - var/obj/item/weapon/implant/health/H = null - if(src.active_record.implant) - H=locate(src.active_record.implant) - - if ((H) && (istype(H))) - dat += "Health: [H.sensehealth()] | OXY-BURN-TOX-BRUTE
    " - else - dat += "Unable to locate implant.
    " - - if (!isnull(src.diskette)) - dat += "Load from disk." - - dat += " | Save: UI + UE" - dat += " | Save: UI" - dat += " | Save: SE" - dat += "
    " - else - dat += "
    " //Keeping a line empty for appearances I guess. - - dat += {"UI: [src.active_record.dna.uni_identity]
    - SE: [src.active_record.dna.struc_enzymes]

    "} - - if(pods.len) - dat += {"Clone
    "} - - if(4) - if (!src.active_record) - src.menu = 2 - dat = "[src.temp]
    " - dat += "

    Confirm Record Deletion

    " - - dat += "Scan card to confirm.
    " - dat += "No" - - - user << browse(dat, "window=cloning") - onclose(user, "cloning") - return + ui = nanomanager.try_update_ui(user, src, ui_key, ui, data, force_open) + if (!ui) + ui = new(user, src, ui_key, "cloning.tmpl", src.name, 400, 300) + ui.set_initial_data(data) + ui.open() + ui.set_auto_update(5) /obj/machinery/computer/cloning/Topic(href, href_list) if(..()) @@ -205,98 +159,80 @@ if(loading) return - if ((href_list["scan"]) && (!isnull(src.scanner))) + if ((href_list["scan"]) && (!isnull(scanner))) scantemp = "" loading = 1 - src.updateUsrDialog() spawn(20) - src.scan_mob(src.scanner.occupant) + scan_mob(scanner.occupant) loading = 0 - src.updateUsrDialog() - //No locking an open scanner. - else if ((href_list["lock"]) && (!isnull(src.scanner))) - if ((!src.scanner.locked) && (src.scanner.occupant)) - src.scanner.locked = 1 + else if ((href_list["lock"]) && (!isnull(scanner))) + if ((!scanner.locked) && (scanner.occupant)) + scanner.locked = 1 else - src.scanner.locked = 0 + scanner.locked = 0 else if (href_list["view_rec"]) - src.active_record = locate(href_list["view_rec"]) - if(istype(src.active_record,/datum/dna2/record)) - if ((isnull(src.active_record.ckey))) - qdel(src.active_record) - src.temp = "ERROR: Record Corrupt" + active_record = locate(href_list["view_rec"]) + if(istype(active_record,/datum/dna2/record)) + if ((isnull(active_record.ckey))) + qdel(active_record) + temp = "ERROR: Record Corrupt" else - src.menu = 3 + menu = 3 else - src.active_record = null - src.temp = "Record missing." + active_record = null + temp = "Record missing." else if (href_list["del_rec"]) - if ((!src.active_record) || (src.menu < 3)) + if ((!active_record) || (menu < 3)) return - if (src.menu == 3) //If we are viewing a record, confirm deletion - src.temp = "Delete record?" - src.menu = 4 - - else if (src.menu == 4) - var/obj/item/weapon/card/id/C = usr.get_active_hand() - if (istype(C)||istype(C, /obj/item/device/pda)) - if(src.check_access(C)) - src.records.Remove(src.active_record) - qdel(src.active_record) - src.temp = "Record deleted." - src.menu = 2 - else - src.temp = "Access Denied." + if (menu == 3) //If we are viewing a record, confirm deletion + temp = "Delete record?" + menu = 4 else if (href_list["disk"]) //Load or eject. switch(href_list["disk"]) if("load") - if ((isnull(src.diskette)) || isnull(src.diskette.buf)) - src.temp = "Load error." - src.updateUsrDialog() + if ((isnull(diskette)) || isnull(diskette.buf)) + temp = "Load error." return - if (isnull(src.active_record)) - src.temp = "Record error." - src.menu = 1 - src.updateUsrDialog() + if (isnull(active_record)) + temp = "Record error." + menu = 1 return - src.active_record = src.diskette.buf + active_record = diskette.buf - src.temp = "Load successful." + temp = "Load successful." if("eject") - if (!isnull(src.diskette)) - src.diskette.loc = src.loc - src.diskette = null + if (!isnull(diskette)) + diskette.loc = loc + diskette = null else if (href_list["save_disk"]) //Save to disk! - if ((isnull(src.diskette)) || (src.diskette.read_only) || (isnull(src.active_record))) - src.temp = "Save error." - src.updateUsrDialog() - return + if ((isnull(diskette)) || (diskette.read_only) || (isnull(active_record))) + temp = "Save error." // DNA2 makes things a little simpler. - src.diskette.buf=src.active_record - src.diskette.buf.types=0 + diskette.buf = active_record + diskette.buf.types = 0 switch(href_list["save_disk"]) //Save as Ui/Ui+Ue/Se if("ui") - src.diskette.buf.types=DNA2_BUF_UI + diskette.buf.types = DNA2_BUF_UI if("ue") - src.diskette.buf.types=DNA2_BUF_UI|DNA2_BUF_UE + diskette.buf.types = DNA2_BUF_UI | DNA2_BUF_UE if("se") - src.diskette.buf.types=DNA2_BUF_SE - src.diskette.name = "data disk - '[src.active_record.dna.real_name]'" - src.temp = "Save \[[href_list["save_disk"]]\] successful." + diskette.buf.types = DNA2_BUF_SE + diskette.name = "data disk - '[active_record.dna.real_name]'" + temp = "Save \[[href_list["save_disk"]]\] successful." else if (href_list["refresh"]) - src.updateUsrDialog() + updateUsrDialog() else if (href_list["clone"]) var/datum/dna2/record/C = locate(href_list["clone"]) @@ -340,11 +276,10 @@ temp = "Error: Data corruption." else if (href_list["menu"]) - src.menu = text2num(href_list["menu"]) + menu = href_list["menu"] - src.add_fingerprint(usr) - src.updateUsrDialog() - return + nanomanager.update_uis(src) + add_fingerprint(usr) /obj/machinery/computer/cloning/proc/scan_mob(mob/living/carbon/human/subject as mob) if ((isnull(subject)) || (!(ishuman(subject))) || (!subject.dna)) @@ -381,13 +316,13 @@ subject.dna.check_integrity() var/datum/dna2/record/R = new /datum/dna2/record() - R.dna=subject.dna + R.dna = subject.dna R.ckey = subject.ckey - R.id= copytext(md5(subject.real_name), 2, 6) - R.name=R.dna.real_name - R.types=DNA2_BUF_UI|DNA2_BUF_UE|DNA2_BUF_SE - R.languages=subject.languages - R.flavor=subject.flavor_texts.Copy() + R.id = copytext(md5(subject.real_name), 2, 6) + R.name = R.dna.real_name + R.types = DNA2_BUF_UI|DNA2_BUF_UE|DNA2_BUF_SE + R.languages = subject.languages + R.flavor = subject.flavor_texts.Copy() //Add an implant if needed var/obj/item/weapon/implant/health/imp = locate(/obj/item/weapon/implant/health, subject) @@ -402,13 +337,13 @@ if (!isnull(subject.mind)) //Save that mind so traitors can continue traitoring after cloning. R.mind = "\ref[subject.mind]" - src.records += R + records += R scantemp = "Subject successfully scanned." //Find a specific record by key. /obj/machinery/computer/cloning/proc/find_record(var/find_key) var/selected_record = null - for(var/datum/dna2/record/R in src.records) + for(var/datum/dna2/record/R in records) if (R.ckey == find_key) selected_record = R break diff --git a/code/game/machinery/computer/guestpass.dm b/code/game/machinery/computer/guestpass.dm index a4553403bc..eeec3a703e 100644 --- a/code/game/machinery/computer/guestpass.dm +++ b/code/game/machinery/computer/guestpass.dm @@ -102,40 +102,51 @@ return user.set_machine(src) - var/dat - if (mode == 1) //Logs - dat += "

    Activity log


    " - for (var/entry in internal_log) - dat += "[entry]

    " - dat += "Print
    " - dat += "Back
    " - else - dat += "

    Guest pass terminal #[uid]


    " - dat += "View activity log

    " - dat += "Issuing ID: [giver]
    " - dat += "Issued to: [giv_name]
    " - dat += "Reason: [reason]
    " - dat += "Duration (minutes): [duration] m
    " - dat += "Access to areas:
    " - if (giver && giver.access) - for (var/A in giver.access) - var/area = get_access_desc(A) - if (A in accesses) - area = "[area]" - dat += "[area]
    " - dat += "
    Issue pass
    " + ui_interact(user) - user << browse(dat, "window=guestpass;size=400x520") - onclose(user, "guestpass") +/** + * Display the NanoUI window for the guest pass console. + * + * See NanoUI documentation for details. + */ +/obj/machinery/computer/guestpass/ui_interact(mob/user, ui_key = "main", var/datum/nanoui/ui = null, var/force_open = 1) + user.set_machine(src) + var/list/data = list() + + var/area_list[0] + + if (giver && giver.access) + data["access"] = giver.access + for (var/A in giver.access) + if(A in accesses) + area_list[++area_list.len] = list("area" = A, "area_name" = get_access_desc(A), "on" = 1) + else + area_list[++area_list.len] = list("area" = A, "area_name" = get_access_desc(A), "on" = null) + + data["giver"] = giver + data["giveName"] = giv_name + data["reason"] = reason + data["duration"] = duration + data["area"] = area_list + data["mode"] = mode + data["log"] = internal_log + data["uid"] = uid + + ui = nanomanager.try_update_ui(user, src, ui_key, ui, data, force_open) + if (!ui) + ui = new(user, src, ui_key, "guest_pass.tmpl", src.name, 400, 520) + ui.set_initial_data(data) + ui.open() + //ui.set_auto_update(5) /obj/machinery/computer/guestpass/Topic(href, href_list) if(..()) return 1 usr.set_machine(src) if (href_list["mode"]) - mode = text2num(href_list["mode"]) + mode = href_list["mode"] if (href_list["choice"]) switch(href_list["choice"]) @@ -182,7 +193,6 @@ if (istype(I, /obj/item/weapon/card/id) && usr.unEquip(I)) I.loc = src giver = I - updateUsrDialog() if ("print") var/dat = "

    Activity log of guest pass terminal #[uid]


    " @@ -213,6 +223,4 @@ pass.reason = reason pass.name = "guest pass #[number]" else - usr << "Cannot issue pass without issuing ID." - updateUsrDialog() - return + usr << "Cannot issue pass without issuing ID." \ No newline at end of file diff --git a/code/game/machinery/computer3/lapvend.dm b/code/game/machinery/computer3/lapvend.dm index efd0747b35..ceb66a68bd 100644 --- a/code/game/machinery/computer3/lapvend.dm +++ b/code/game/machinery/computer3/lapvend.dm @@ -6,12 +6,10 @@ layer = 2.9 anchored = 1 density = 1 - var/datum/browser/popup = null var/obj/machinery/computer3/laptop/vended/newlap = null var/obj/item/device/laptop/relap = null var/vendmode = 0 - var/cardreader = 0 var/floppy = 0 var/radionet = 0 @@ -34,7 +32,7 @@ if(vendmode == 1 && I) scan_id(I, W) vendmode = 0 - if(vendmode == 3 && I) + if(vendmode == 2 && I) if(reimburse_id(I, W)) vendmode = 0 if(vendmode == 0) @@ -44,84 +42,48 @@ calc_reimburse(L) usr.drop_item() L.loc = src - vendmode = 3 + vendmode = 2 usr << "You slot your [L.name] into \The [src.name]" else ..() /obj/machinery/lapvend/attack_hand(mob/user as mob) + if(stat & (BROKEN|NOPOWER)) + return + + ui_interact(user) + +/** + * Display the NanoUI window for the vending machine. + * + * See NanoUI documentation for details. + */ +/obj/machinery/lapvend/ui_interact(mob/user, ui_key = "main", var/datum/nanoui/ui = null, var/force_open = 1) user.set_machine(src) - var/vendorname = (src.name) //import the machine's name - var/dat = "
    [vendorname]


    " //display the name, and added a horizontal rule - if(vendmode == 0) - dat += "
    Please choose your laptop customization options

    " - dat += "
    Your comptuer will automatically be loaded with any programs you can use after the transaction is complete.
    " - dat += "
    Some programs will require additional components to be installed!


    " - dat += "
    HDD (Required) : Added

    " - dat += "
    Card Reader : Single (50) | Dual (125)

    " - dat += "
    Floppy Drive: Add (50)

    " - dat += "
    Radio Network card Add (50)

    " - dat += "
    Camera Card Add (100)

    " - dat += "
    Network card Area (75) Adjacent (50)Powernet (25)

    " - dat += "
    Power source upgrade
    Extended (175) Unreal (250)" - if(vendmode == 0 || vendmode == 1) - dat += "

    Cart

    " - dat += "Total: [total()]
    " - if(cardreader == 1) - dat += "Card Reader: (single) (50)
    " - else if (cardreader == 2) - dat += "Card Reader: (double) (125)
    " - else - dat += "Card Reader: None
    " - if(floppy == 0) - dat += "Floppy Drive: None
    " - else - dat += "Floppy Drive: Added (50)
    " - if(radionet == 1) - dat += "Radio Card: Added (50)
    " - else - dat += "Radio Card: None
    " - if(camera == 1) - dat += "Camera Card: Added (100)
    " - else - dat += "Camera Card: None
    " - if(network == 1) - dat += "Network card: Area (75)
    " - else if(network == 2) - dat += "Network card: Adjacent (50)
    " - else if(network == 3) - dat += "Network card: Powernet (25)
    " - else - dat += "Network card: None" - if (power == 0) - dat += "Power source: Regular" - else if (power == 1) - dat += "Power source: Extended (175)
    " - else - dat += "Power source: Unreal (250)
    " - - if(vendmode == 0) - dat += "
    Vend Laptop" - - if(vendmode == 1) - dat += "Please swipe your card and enter your PIN to complete the transaction" - - if(vendmode == 3) - dat += "Please swipe your card and enter your PIN to be finish returning your computer
    " - dat += "Cancel" - - - - - popup = new(user, "lapvend", name, 450, 500) - popup.set_content(dat) - popup.open() - return + var/list/data = list() + data["mode"] = vendmode + data["cardreader"] = cardreader + data["floppy"] = floppy + data["radionet"] = radionet + data["camera"] = camera + data["network"] = network + data["power"] = power + data["total"] = total() + ui = nanomanager.try_update_ui(user, src, ui_key, ui, data, force_open) + if (!ui) + ui = new(user, src, ui_key, "laptop_vendor.tmpl", src.name, 480, 500) + ui.set_initial_data(data) + ui.open() + //ui.set_auto_update(5) /obj/machinery/lapvend/Topic(href, href_list) + if(stat & (BROKEN|NOPOWER)) + return + if(usr.stat || usr.restrained()) + return if ((usr.contents.Find(src) || (in_range(src, usr) && istype(src.loc, /turf)))) usr.set_machine(src) switch(href_list["choice"]) @@ -146,7 +108,7 @@ if ("super_add") power = 2 - if ("single_rem" || "dual_rem") + if ("cardreader_rem") cardreader = 0 if ("floppy_rem") floppy = 0 @@ -154,9 +116,9 @@ radionet = 0 if ("camnet_rem") camera = 0 - if ("area_rem" || "prox_rem" || "cable_rem") + if ("network_rem") network = 0 - if ("high_rem" || "super_rem") + if ("power_rem") power = 0 if("vend") @@ -168,9 +130,8 @@ relap = null vendmode = 0 - src.updateUsrDialog() - return - + src.add_fingerprint(usr) + nanomanager.update_uis(src) /obj/machinery/lapvend/proc/vend() if(cardreader > 0) @@ -253,7 +214,6 @@ choose_progs(C) vend() - popup.close() newlap.close_laptop() newlap = null cardreader = 0 diff --git a/code/modules/holodeck/HolodeckControl.dm b/code/modules/holodeck/HolodeckControl.dm index 4c0d0a755e..fd887db55e 100644 --- a/code/modules/holodeck/HolodeckControl.dm +++ b/code/modules/holodeck/HolodeckControl.dm @@ -30,62 +30,60 @@ "Snow Field" = "snowfield", \ "Theatre" = "theatre", \ "Meeting Hall" = "meetinghall", \ - "Courtroom" = "courtroom" \ + "Courtroom" = "courtroom", \ + "Turn Off" = "turnoff" \ ) var/list/restricted_programs = list("Atmospheric Burn Simulation" = "burntest", "Wildlife Simulation" = "wildlifecarp") + var/current_program = "turnoff" /obj/machinery/computer/HolodeckControl/attack_ai(var/mob/user as mob) return src.attack_hand(user) /obj/machinery/computer/HolodeckControl/attack_hand(var/mob/user as mob) - if(..()) return user.set_machine(src) - var/dat - dat += "Holodeck Control System
    " - dat += "
    Current Loaded Programs:
    " - for(var/prog in supported_programs) - dat += "([prog])
    " + ui_interact(user) - dat += "
    " - dat += "(Turn Off)
    " +/** + * Display the NanoUI window for the Holodeck Computer. + * + * See NanoUI documentation for details. + */ +/obj/machinery/computer/HolodeckControl/ui_interact(mob/user, ui_key = "main", var/datum/nanoui/ui = null, var/force_open = 1) + user.set_machine(src) - dat += "
    " - dat += "Please ensure that only holographic weapons are used in the holodeck if a combat simulation has been loaded.
    " + var/list/data = list() + var/program_list[0] + var/restricted_program_list[0] + for(var/P in supported_programs) + program_list[++program_list.len] = list("name" = P, "program" = supported_programs[P]) + + for(var/P in restricted_programs) + restricted_program_list[++restricted_program_list.len] = list("name" = P, "program" = restricted_programs[P]) + + data["supportedPrograms"] = program_list + data["restrictedPrograms"] = restricted_program_list + data["currentProgram"] = current_program if(issilicon(user)) - dat += "
    " - if(safety_disabled) - if (emagged) - dat += "ERROR: Cannot re-enable Safety Protocols.
    " - else - dat += "(Re-Enable Safety Protocols?)
    " - else - dat += "(Override Safety Protocols?)
    " - - dat += "
    " - - if(safety_disabled) - for(var/prog in restricted_programs) - dat += "(Begin [prog])
    " - dat += "Ensure the holodeck is empty before testing.
    " - dat += "
    " - dat += "Safety Protocols are DISABLED
    " + data["isSilicon"] = 1 else - dat += "Safety Protocols are ENABLED
    " - + data["isSilicon"] = null + data["safetyDisabled"] = safety_disabled + data["emagged"] = emagged if(linkedholodeck.has_gravity) - dat += "Gravity is (ON)
    " + data["gravity"] = 1 else - dat += "Gravity is (OFF)
    " - - user << browse(dat, "window=computer;size=400x500") - onclose(user, "computer") - - return + data["gravity"] = null + ui = nanomanager.try_update_ui(user, src, ui_key, ui, data, force_open) + if (!ui) + ui = new(user, src, ui_key, "holodeck.tmpl", src.name, 400, 500) + ui.set_initial_data(data) + ui.open() + //ui.set_auto_update(5) /obj/machinery/computer/HolodeckControl/Topic(href, href_list) if(..()) @@ -97,6 +95,7 @@ var/prog = href_list["program"] if(prog in holodeck_programs) loadProgram(holodeck_programs[prog]) + current_program = href_list["program"] else if(href_list["AIoverride"]) if(!issilicon(usr)) @@ -118,8 +117,8 @@ toggleGravity(linkedholodeck) src.add_fingerprint(usr) - src.updateUsrDialog() - return + + nanomanager.update_uis(src) /obj/machinery/computer/HolodeckControl/emag_act(var/remaining_charges, var/mob/user as mob) playsound(src.loc, 'sound/effects/sparks4.ogg', 75, 1) @@ -132,7 +131,6 @@ user << "Warning. Automatic shutoff and derezing protocols have been corrupted. Please call [company_name] maintenance and do not use the simulator." log_game("[key_name(usr)] emagged the Holodeck Control Computer") return 1 - src.updateUsrDialog() return /obj/machinery/computer/HolodeckControl/proc/update_projections() diff --git a/code/modules/paperwork/faxmachine.dm b/code/modules/paperwork/faxmachine.dm index a0f515ac13..27474a75c6 100644 --- a/code/modules/paperwork/faxmachine.dm +++ b/code/modules/paperwork/faxmachine.dm @@ -41,54 +41,37 @@ var/list/adminfaxes = list() //cache for faxes that have been sent to admins /obj/machinery/photocopier/faxmachine/attack_hand(mob/user as mob) user.set_machine(src) - var/dat = "Fax Machine
    " + ui_interact(user) - var/scan_name +/** + * Display the NanoUI window for the fax machine. + * + * See NanoUI documentation for details. + */ +/obj/machinery/photocopier/faxmachine/ui_interact(mob/user, ui_key = "main", var/datum/nanoui/ui = null, var/force_open = 1) + user.set_machine(src) + + var/list/data = list() if(scan) - scan_name = scan.name + data["scanName"] = scan.name else - scan_name = "--------" - - dat += "Confirm Identity: [scan_name]
    " - - if(authenticated) - dat += "{Log Out}" + data["scanName"] = null + data["bossName"] = boss_name + data["authenticated"] = authenticated + data["copyItem"] = copyitem + if(copyitem) + data["copyItemName"] = copyitem.name else - dat += "{Log In}" + data["copyItemName"] = null + data["cooldown"] = sendcooldown + data["destination"] = destination - dat += "
    " - - if(authenticated) - dat += "Logged in to: [boss_name] Quantum Entanglement Network

    " - - if(copyitem) - dat += "Remove Item

    " - - if(sendcooldown) - dat += "Transmitter arrays realigning. Please stand by.
    " - - else - - dat += "Send
    " - dat += "Currently sending: [copyitem.name]
    " - dat += "Sending to: [destination]
    " - - else - if(sendcooldown) - dat += "Please insert paper to send via secure connection.

    " - dat += "Transmitter arrays realigning. Please stand by.
    " - else - dat += "Please insert paper to send via secure connection.

    " - - else - dat += "Proper authentication is required to use this device.

    " - - if(copyitem) - dat += "Remove Item
    " - - user << browse(dat, "window=copier") - onclose(user, "copier") - return + ui = nanomanager.try_update_ui(user, src, ui_key, ui, data, force_open) + if (!ui) + ui = new(user, src, ui_key, "fax.tmpl", src.name, 400, 500) + ui.set_initial_data(data) + ui.open() + ui.set_auto_update(10) //this machine is so unimportant let's not have it update that often. /obj/machinery/photocopier/faxmachine/Topic(href, href_list) if(href_list["send"]) @@ -108,7 +91,6 @@ var/list/adminfaxes = list() //cache for faxes that have been sent to admins usr.put_in_hands(copyitem) usr << "You take \the [copyitem] out of \the [src]." copyitem = null - updateUsrDialog() if(href_list["scan"]) if (scan) @@ -140,7 +122,7 @@ var/list/adminfaxes = list() //cache for faxes that have been sent to admins if(href_list["logout"]) authenticated = 0 - updateUsrDialog() + nanomanager.update_uis(src) /obj/machinery/photocopier/faxmachine/proc/sendfax(var/destination) if(stat & (BROKEN|NOPOWER)) diff --git a/code/modules/paperwork/photocopier.dm b/code/modules/paperwork/photocopier.dm index dcee1fb3fa..cee22ff30b 100644 --- a/code/modules/paperwork/photocopier.dm +++ b/code/modules/paperwork/photocopier.dm @@ -30,24 +30,32 @@ /obj/machinery/photocopier/attack_hand(mob/user as mob) user.set_machine(src) - var/dat = "Photocopier

    " - if(copyitem) - dat += "Remove Item
    " - if(toner) - dat += "Copy
    " - dat += "Printing: [copies] copies." - dat += "- " - dat += "+

    " - else if(toner) - dat += "Please insert something to copy.

    " + ui_interact(user) + +/** + * Display the NanoUI window for the photocopier. + * + * See NanoUI documentation for details. + */ +/obj/machinery/photocopier/ui_interact(mob/user, ui_key = "main", var/datum/nanoui/ui = null, var/force_open = 1) + user.set_machine(src) + + var/list/data = list() + data["copyItem"] = copyitem + data["toner"] = toner + data["copies"] = copies + data["maxCopies"] = maxcopies if(istype(user,/mob/living/silicon)) - dat += "Print photo from database

    " - dat += "Current toner level: [toner]" - if(!toner) - dat +="
    Please insert a new toner cartridge!" - user << browse(dat, "window=copier") - onclose(user, "copier") - return + data["isSilicon"] = 1 + else + data["isSilicon"] = null + + ui = nanomanager.try_update_ui(user, src, ui_key, ui, data, force_open) + if (!ui) + ui = new(user, src, ui_key, "photocopier.tmpl", src.name, 400, 500) + ui.set_initial_data(data) + ui.open() + ui.set_auto_update(10) /obj/machinery/photocopier/Topic(href, href_list) if(href_list["copy"]) @@ -72,22 +80,18 @@ break use_power(active_power_usage) - updateUsrDialog() else if(href_list["remove"]) if(copyitem) copyitem.loc = usr.loc usr.put_in_hands(copyitem) usr << "You take \the [copyitem] out of \the [src]." copyitem = null - updateUsrDialog() else if(href_list["min"]) if(copies > 1) copies-- - updateUsrDialog() else if(href_list["add"]) if(copies < maxcopies) copies++ - updateUsrDialog() else if(href_list["aipic"]) if(!istype(usr,/mob/living/silicon)) return if(stat & (BROKEN|NOPOWER)) return @@ -109,7 +113,8 @@ p.desc += " - Copied by [tempAI.name]" toner -= 5 sleep(15) - updateUsrDialog() + + nanomanager.update_uis(src) /obj/machinery/photocopier/attackby(obj/item/O as obj, mob/user as mob) if(istype(O, /obj/item/weapon/paper) || istype(O, /obj/item/weapon/photo) || istype(O, /obj/item/weapon/paper_bundle)) @@ -119,7 +124,6 @@ O.loc = src user << "You insert \the [O] into \the [src]." flick(insert_anim, src) - updateUsrDialog() else user << "There is already something in \the [src]." else if(istype(O, /obj/item/device/toner)) @@ -129,7 +133,6 @@ var/obj/item/device/toner/T = O toner += T.toner_amount qdel(O) - updateUsrDialog() else user << "This cartridge is not yet ready for replacement! Use up the rest of the toner." else if(istype(O, /obj/item/weapon/wrench)) diff --git a/nano/templates/adv_med.tmpl b/nano/templates/adv_med.tmpl new file mode 100644 index 0000000000..5dc8c5e427 --- /dev/null +++ b/nano/templates/adv_med.tmpl @@ -0,0 +1,279 @@ + +{{if !data.occupied}} +

    No occupant detected.

    +{{else}} +

    Occupant Data:

    +
    +
    + Name: +
    +
    + {{:data.occupant.name}} +
    +
    +
    +
    + Health: +
    + {{:helper.displayBar(data.occupant.health, 0, 100, (data.occupant.health >= 50) ? 'good' : (data.occupant.health >= 25) ? 'average' : 'bad')}} +
    + {{:helper.round(data.occupant.health*10)/10}}% +
    +
    +
    + Status: +
    +
    + {{if data.occupant.stat==0}} + Alive + {{else data.occupant.stat==1}} + Critical + {{else}} + Dead + {{/if}} +
    +
    + {{:helper.link('Print', 'document', {'print_p' : 1, 'name' : data.occupant.name})}} +
    +

    Damage:

    +
    + Brute: +
    +
    + {{:data.occupant.bruteLoss}} +

    +
    + Burn: +
    +
    + {{:data.occupant.fireLoss}} +

    +
    + Oxygen: +
    +
    + {{:data.occupant.oxyLoss}} +

    +
    + Toxins: +
    +
    + {{:data.occupant.toxLoss}} +

    +
    + Brain: +
    +
    + {{:data.occupant.brainLoss}} +

    +
    + Radiation Level: +
    +
    + {{:data.occupant.radLoss}} +

    +
    + Genetic: +
    +
    + {{:data.occupant.cloneLoss}} +

    +
    + Paralysis: +
    +
    + {{:data.occupant.paralysis}}% ({{:data.occupant.paralysisSeconds}} seconds left!) +

    +
    +
    +
    + Body Temperature: +
    +
    + {{:data.occupant.bodyTempC}}°C, {{:data.occupant.bodyTempF}}°F +
    +
    + {{if data.occupant.hasVirus}} +
    + Viral pathogen detected in blood stream. +
    + {{/if}} + {{if data.occupant.hasBorer}} +
    + Large growth detected in frontal lobe, possibly cancerous. Surgical removal is recommended. +
    + {{/if}} + {{if data.occupant.blind}} + Pupils unresponsive.
    + {{/if}} + {{if data.occupant.nearsighted}} + Retinal Misalignment Detected + {{/if}} +
    +
    + Blood +
    +
    +
    + Volume +
    +
    + {{:data.occupant.blood.volume}} +
    +
    + Percent +
    +
    + {{:data.occupant.blood.percent}}% +
    +
    +
    +
    + Reagents +
    +
    + {{for data.occupant.reagents}} +
    + {{:value.name}} +
    +
    + {{:value.amount}} +
    + {{/for}} +
    +
    + External Organs +
    + {{for data.occupant.extOrgan}} +
    + {{if value.status.destroyed}} +
    + {{:value.name}} - DESTROYED +
    + {{else}} +
    +
    + {{:value.name}} +
    +
    +
    + {{if value.status.broken}} + {{:value.status.broken}} + {{else value.status.splinted}} + Splinted + {{else value.status.robotic}} + Robotic + {{/if}} +
    +
    +  Brute/Burn +
    +
    + {{:value.bruteLoss}}/{{:value.fireLoss}} +
    +
    +  Injuries +
    +
    + {{if !value.status.bleeding}} + {{if !value.status.internalBleeding}} + No Injuries Detected + {{else}} + Internal Bleeding Detected + {{/if}} + {{else}} + {{if value.status.internalBleeding}} +
    Internal Bleeding Detected. External Bleeding Detected.
    + {{else}} + External Bleeding Detected + {{/if}} + {{/if}} +
    + {{if value.germ_level > 100}} +
    +  Infection +
    +
    + {{if value.germ_level < 300}} + Mild Infection + {{else value.germ_level < 400}} + Mild Infection+ + {{else value.germ_level < 500}} + Mild Infection++ + {{else value.germ_level < 700}} + Acute Infection + {{else value.germ_level < 800}} + Acute Infection+ + {{else value.germ_level < 900}} + Acute Infection++ + {{else value.germ_level >= 900}} + Septic + {{/if}} +
    + {{/if}} + {{if value.open}} +
    +  Operation Status +
    +
    + Open Incision +
    + {{/if}} + {{if value.implants_len}} +
    +  Implants +

    + {{for value.implants :impValue:impindex}} +
    +   {{:impValue.known ? impValue.name : "Unknown"}} +

    + {{/for}} + {{/if}} + {{/if}} +

    + {{/for}} +
    + Internal Organs +
    + {{for data.occupant.intOrgan}} +
    +
    + {{:value.name}} +
    +
    +
    + {{if value.germ_level > 100}} +
    +  Infection +
    +
    + {{if value.germ_level < 300}} + Mild Infection + {{else value.germ_level < 400}} + Mild Infection+ + {{else value.germ_level < 500}} + Mild Infection++ + {{else value.germ_level < 700}} + Acute Infection + {{else value.germ_level < 800}} + Acute Infection+ + {{else value.germ_level < 900}} + Acute Infection++ + {{else value.germ_level >= 900}} + Septic + {{/if}} +
    + {{/if}} +
    +  Damage +
    +
    + {{:value.damage}} +
    +
    + {{/for}} +
    +{{/if}} \ No newline at end of file diff --git a/nano/templates/arcade_battle.tmpl b/nano/templates/arcade_battle.tmpl new file mode 100644 index 0000000000..0455649404 --- /dev/null +++ b/nano/templates/arcade_battle.tmpl @@ -0,0 +1,26 @@ + + +

    {{:data.enemyName}}

    + +
    {{:data.temp}}
    +
    +
    Health:
    +
    {{:data.playerHP}}
    +
    Magic:
    +
    {{:data.playerMP}}
    +
    Enemy Health:
    +
    {{:data.enemyHP}}
    +
    + +{{if data.gameOver}} +
    {{:helper.link('New Game', null, {'newgame' : 1})}}
    +{{else}} +
    + {{:helper.link('Attack', null, {'attack' : 1})}} + {{:helper.link('Heal', null, {'heal' : 1})}} + {{:helper.link('Recharge Power', null, {'charge' : 1})}} +
    +{{/if}} \ No newline at end of file diff --git a/nano/templates/atmo_control.tmpl b/nano/templates/atmo_control.tmpl new file mode 100644 index 0000000000..503f15458f --- /dev/null +++ b/nano/templates/atmo_control.tmpl @@ -0,0 +1,218 @@ + +{{if data.sensors}} + {{for data.sensors}} + {{if value.sensor_data}} +
    + {{:value.long_name}} + {{if value.sensor_data.pressure}} +
    Pressure:
    + {{:value.sensor_data.pressure}} kPa + {{/if}} + {{if value.sensor_data.temperature}} +
    Temperature:
    + {{:value.sensor_data.temperature}} kPa + {{/if}} + {{if value.sensor_data.oxygen || value.sensor_data.nitrogen || value.sensor_data.carbon_dioxide || value.sensor_data.phoron}} +
    Gas Composition:
    + {{if value.sensor_data.oxygen}} + {{:value.sensor_data.pressure}} % O2 + {{/if}} + {{if value.sensor_data.nitrogen}} + {{:value.sensor_data.pressure}} % N + {{/if}} + {{if value.sensor_data.carbon_dioxide}} + {{:value.sensor_data.pressure}} % CO2 + {{/if}} + {{if value.sensor_data.phoron}} + {{:value.sensor_data.pressure}} % TX + {{/if}} + {{/if}} +
    + {{else}} +
    +
    {{:value.long_name}} can not be found!
    +
    + {{/if}} + {{/for}} +{{else}} +
    + No sensors connected. +
    +{{/if}} + +{{if data.tanks || data.core}} +

    + {{if data.tanks}} + Tank Control System + {{else data.core}} + Core Cooling Control System + {{/if}} +

    + + {{if data.input_info}} +
    +
    + {{if data.tanks}} + Input: + {{else data.core}} + Coolant Input: + {{/if}} +
    +
    + {{if data.input_info.power}} + Injecting + {{else}} + On Hold + {{/if}} +
    + {{:helper.link('Refresh', null, {'in_refresh_status' : 1})}} +
    +
    +
    Flow Rate Limit:
    +
    {{:data.input_info.volume_rate}} L/s
    +
    +
    +
    Command:
    + {{:helper.link('Toggle Power', null, {'in_toggle_injector' : 1})}} + {{:helper.link('Set Flow Rate', null, {'in_set_flowrate' : 1})}} +
    + {{else}} +
    +
    ERROR: Can not find input port
    + {{:helper.link('Search', null, {'in_refresh_status' : 1})}} +
    + {{/if}} +
    +
    + Flow Rate Limit: +
    +
    + {{:helper.link('-', null, {'adj_input_flow_rate' : -100})}} + {{:helper.link('-', null, {'adj_input_flow_rate' : -10})}} + {{:helper.link('-', null, {'adj_input_flow_rate' : -1})}} + {{:helper.link('-', null, {'adj_input_flow_rate' : -0.1})}} +
     {{:data.input_flow_setting}} L/s 
    + {{:helper.link('+', null, {'adj_input_flow_rate' : 0.1})}} + {{:helper.link('+', null, {'adj_input_flow_rate' : 1})}} + {{:helper.link('+', null, {'adj_input_flow_rate' : 10})}} + {{:helper.link('+', null, {'adj_input_flow_rate' : 100})}} +
    +
    + + {{if data.output_info}} +
    +
    + {{if data.tanks}} + Output: + {{else data.core}} + Core Outpump: + {{/if}} +
    +
    + {{if data.input_info.power}} + Open + {{else}} + On Hold + {{/if}} +
    + {{:helper.link('Refresh', null, {'out_refresh_status' : 1})}} +
    +
    + {{if data.tanks}} +
    Max Output Pressure:
    +
    {{:data.output_info.output_pressure}} kPa
    + {{else data.core}} +
    Min Core Pressure:
    +
    {{:data.output_info.pressure_limit}} kPa
    + {{/if}} +
    +
    +
    Command:
    + {{:helper.link('Toggle Power', null, {'out_toggle_power' : 1})}} + {{:helper.link('Set Pressure', null, {'out_set_pressure' : 1})}} +
    + {{else}} +
    +
    ERROR: Can not find output port
    + {{:helper.link('Search', null, {'out_refresh_status' : 1})}} +
    + {{/if}} + +
    + {{if data.tanks}} +
    + Max Output Pressure Set: +
    +
    + {{:helper.link('-', null, {'adj_pressure' : -1000})}} + {{:helper.link('-', null, {'adj_pressure' : -100})}} + {{:helper.link('-', null, {'adj_pressure' : -10})}} + {{:helper.link('-', null, {'adj_pressure' : -1})}} +
     {{:data.pressure_setting}} kPa 
    + {{:helper.link('+', null, {'adj_pressure' : 1})}} + {{:helper.link('+', null, {'adj_pressure' : 10})}} + {{:helper.link('+', null, {'adj_pressure' : 100})}} + {{:helper.link('+', null, {'adj_pressure' : 1000})}} +
    + {{else data.core}} +
    + Min Core Pressure Set: +
    +
    + {{:helper.link('-', null, {'adj_pressure' : -100})}} + {{:helper.link('-', null, {'adj_pressure' : -50})}} + {{:helper.link('-', null, {'adj_pressure' : -10})}} + {{:helper.link('-', null, {'adj_pressure' : -1})}} +
     {{:data.pressure_setting}} kPa 
    + {{:helper.link('+', null, {'adj_pressure' : 1})}} + {{:helper.link('+', null, {'adj_pressure' : 10})}} + {{:helper.link('+', null, {'adj_pressure' : 50})}} + {{:helper.link('+', null, {'adj_pressure' : 100})}} +
    + {{/if}} +
    +{{/if}} + +{{if data.fuel}} +

    Fuel Injection System

    + + {{if data.device_info}} +
    +
    + Status: +
    +
    + {{if data.device_info.power}} + Injecting + {{else}} + On Hold + {{/if}} +
    + {{:helper.link('Refresh', null, {'refresh_status' : 1})}} +
    +
    +
    Rate:
    +
    {{:data.device_info.volume_rate}} L/s
    +
    +
    +
    Automated Fuel Injection:
    + {{if data.automation}} + {{:helper.link('Engaged', null, {'toggle_automation' : 1})}} +
    Injector Controls Locked Out
    + {{else}} + {{:helper.link('Disengaged', null, {'toggle_automation' : 1})}} +
    Injector:
    + {{:helper.link('Toggle Power', null, {'toggle_injector' : 1})}} + {{:helper.link('Inject (1 Cycle)', null, {'injection' : 1})}} + {{/if}} +
    + {{else}} +
    +
    ERROR: Can not find device
    + {{:helper.link('Search', null, {'refresh_status' : 1})}} +
    + {{/if}} +{{/if}} \ No newline at end of file diff --git a/nano/templates/chem_master.tmpl b/nano/templates/chem_master.tmpl new file mode 100644 index 0000000000..f163447dbf --- /dev/null +++ b/nano/templates/chem_master.tmpl @@ -0,0 +1,205 @@ +/obj/machinery/chem_master/attackby(var/obj/item/weapon/B as obj, var/mob/user as mob) + + if(beaker) + var/datum/reagents/R = beaker:reagents + if (href_list["analyze"]) + var/dat = "" + if(!condi) + if(href_list["name"] == "Blood") + var/datum/reagent/blood/G + for(var/datum/reagent/F in R.reagent_list) + if(F.name == href_list["name"]) + G = F + break + var/A = G.name + var/B = G.data["blood_type"] + var/C = G.data["blood_DNA"] + dat += "Chemmaster 3000Chemical infos:

    Name:
    [A]

    Description:
    Blood Type: [B]
    DNA: [C]


    (Back)" + else + dat += "Chemmaster 3000Chemical infos:

    Name:
    [href_list["name"]]

    Description:
    [href_list["desc"]]


    (Back)" + else + dat += "Condimaster 3000Condiment infos:

    Name:
    [href_list["name"]]

    Description:
    [href_list["desc"]]


    (Back)" + usr << browse(dat, "window=chem_master;size=575x400") + return + + else if (href_list["add"]) + + if(href_list["amount"]) + var/id = href_list["add"] + var/amount = Clamp((text2num(href_list["amount"])), 0, 200) + R.trans_id_to(src, id, amount) + + else if (href_list["addcustom"]) + + var/id = href_list["addcustom"] + useramount = input("Select the amount to transfer.", 30, useramount) as num + useramount = Clamp(useramount, 0, 200) + src.Topic(null, list("amount" = "[useramount]", "add" = "[id]")) + + else if (href_list["remove"]) + + if(href_list["amount"]) + var/id = href_list["remove"] + var/amount = Clamp((text2num(href_list["amount"])), 0, 200) + if(mode) + reagents.trans_id_to(beaker, id, amount) + else + reagents.remove_reagent(id, amount) + + + else if (href_list["removecustom"]) + + var/id = href_list["removecustom"] + useramount = input("Select the amount to transfer.", 30, useramount) as num + useramount = Clamp(useramount, 0, 200) + src.Topic(null, list("amount" = "[useramount]", "remove" = "[id]")) + + else if (href_list["toggle"]) + mode = !mode + + else if (href_list["main"]) + attack_hand(usr) + return + else if (href_list["eject"]) + if(beaker) + beaker:loc = src.loc + beaker = null + reagents.clear_reagents() + icon_state = "mixer0" + else if (href_list["createpill"] || href_list["createpill_multiple"]) + var/count = 1 + + if(reagents.total_volume/count < 1) //Sanity checking. + return + + if (href_list["createpill_multiple"]) + count = input("Select the number of pills to make.", "Max [max_pill_count]", pillamount) as num + count = Clamp(count, 1, max_pill_count) + + if(reagents.total_volume/count < 1) //Sanity checking. + return + + var/amount_per_pill = reagents.total_volume/count + if (amount_per_pill > 60) amount_per_pill = 60 + + var/name = sanitizeSafe(input(usr,"Name:","Name your pill!","[reagents.get_master_reagent_name()] ([amount_per_pill] units)"), MAX_NAME_LEN) + + if(reagents.total_volume/count < 1) //Sanity checking. + return + while (count--) + var/obj/item/weapon/reagent_containers/pill/P = new/obj/item/weapon/reagent_containers/pill(src.loc) + if(!name) name = reagents.get_master_reagent_name() + P.name = "[name] pill" + P.pixel_x = rand(-7, 7) //random position + P.pixel_y = rand(-7, 7) + P.icon_state = "pill"+pillsprite + reagents.trans_to_obj(P,amount_per_pill) + if(src.loaded_pill_bottle) + if(loaded_pill_bottle.contents.len < loaded_pill_bottle.storage_slots) + P.loc = loaded_pill_bottle + src.updateUsrDialog() + + else if (href_list["createbottle"]) + if(!condi) + var/name = sanitizeSafe(input(usr,"Name:","Name your bottle!",reagents.get_master_reagent_name()), MAX_NAME_LEN) + var/obj/item/weapon/reagent_containers/glass/bottle/P = new/obj/item/weapon/reagent_containers/glass/bottle(src.loc) + if(!name) name = reagents.get_master_reagent_name() + P.name = "[name] bottle" + P.pixel_x = rand(-7, 7) //random position + P.pixel_y = rand(-7, 7) + P.icon_state = bottlesprite + reagents.trans_to_obj(P,60) + P.update_icon() + else + var/obj/item/weapon/reagent_containers/food/condiment/P = new/obj/item/weapon/reagent_containers/food/condiment(src.loc) + reagents.trans_to_obj(P,50) + else if(href_list["change_pill"]) + #define MAX_PILL_SPRITE 20 //max icon state of the pill sprites + var/dat = "" + for(var/i = 1 to MAX_PILL_SPRITE) + dat += "" + dat += "
    " + usr << browse(dat, "window=chem_master") + return + else if(href_list["change_bottle"]) + var/dat = "" + for(var/sprite in BOTTLE_SPRITES) + dat += "" + dat += "
    " + usr << browse(dat, "window=chem_master") + return + else if(href_list["pill_sprite"]) + pillsprite = href_list["pill_sprite"] + else if(href_list["bottle_sprite"]) + bottlesprite = href_list["bottle_sprite"] + + src.updateUsrDialog() + return + + +{{:helper.link(data.beaker ? 'Eject Beaker and Clear Buffer' : 'Please insert beaker', 'eject', {'eject' : 1}), data.beaker ? null : 'linkOff'}} +{{:helper.link(data.pillBottle ? 'Eject Pill Bottle' : 'Please insert beaker', 'eject', {'ejectp' : 1}), data.pillBottle ? null : 'linkOff'}} +{{:data.pillBottleTotal}} / {{:data.pillBottleMax}} + +{{if data.beakerReagent}} + Add to buffer: + {{for data.beakerReagent}} + {{:value.name}} , {{:value.volume}} Units - + {{:helper.link('Analyze', 'signal-diag', {'analyze' : 1, 'desc' : value.description, 'name' : value.name})}} + {{:helper.link('1', 'plus', {'add' : value.id, 'amount' : 1})}} + {{:helper.link('5', 'plus', {'add' : value.id, 'amount' : 5})}} + {{:helper.link('10', 'plus', {'add' : value.id, 'amount' : 10})}} + {{:helper.link('30', 'plus', {'add' : value.id, 'amount' : 30})}} + {{:helper.link('60', 'plus', {'add' : value.id, 'amount' : 60})}} + {{:helper.link('All', 'plus', {'add' : value.id, 'amount' : value.volume})}} + {{:helper.link('Custom', 'plus', {'addcustom' : value.id})}} + +if(!beaker) data.beaker +if(src.loaded_pill_bottle) data.pillBottle +[[loaded_pill_bottle.contents.len]/[loaded_pill_bottle.storage_slots]\] data.pillBottleTotal data.pillBottleMax + +var/datum/reagents/R = beaker:reagents +if(!R.total_volume) + dat += "Beaker is empty." + else + dat += "Add to buffer:
    " + for(var/datum/reagent/G in R.reagent_list) + dat += "[G.name] , [G.volume] Units - " + dat += "(Analyze) " + dat += "(1) " + dat += "(5) " + dat += "(10) " + dat += "(30) " + dat += "(60) " + dat += "(All) " + dat += "(Custom)
    " + + dat += "
    Transfer to [(!mode ? "disposal" : "beaker")]:
    " + if(reagents.total_volume) + for(var/datum/reagent/N in reagents.reagent_list) + dat += "[N.name] , [N.volume] Units - " + dat += "(Analyze) " + dat += "(1) " + dat += "(5) " + dat += "(10) " + dat += "(30) " + dat += "(60) " + dat += "(All) " + dat += "(Custom)
    " + else + dat += "Empty
    " + if(!condi) + dat += "

    Create pill (60 units max)
    " + dat += "Create multiple pills
    " + dat += "Create bottle (60 units max)" + else + dat += "Create bottle (50 units max)" + if(!condi) + user << browse("Chemmaster 3000Chemmaster menu:

    [dat]", "window=chem_master;size=575x400") + else + user << browse("Condimaster 3000Condimaster menu:

    [dat]", "window=chem_master;size=575x400") + onclose(user, "chem_master") + return \ No newline at end of file diff --git a/nano/templates/cloning.tmpl b/nano/templates/cloning.tmpl new file mode 100644 index 0000000000..d1ea7df3ad --- /dev/null +++ b/nano/templates/cloning.tmpl @@ -0,0 +1,115 @@ + + +{{:data.temp}} + +{{if data.menu == 1}} + +

    Modules

    + {{if data.scanner}} + DNA scanner found. + {{else}} + DNA scanner not found. + {{/if}} + + {{if data.podsLen > 0}} + {{:data.podsLen}} cloning vat\s found. + {{else}} + No cloning vats found. + {{/if}} + + +

    Scanner Functions

    + + {{if data.loading}} + Scanning... + {{else}} + {{:data.scantemp}} + {{/if}} + + {{if data.scanner}} + {{if data.occupant}} + + {{:helper.link('Scan - ' + {{:data.occupant}}, 'play', {'scan' : 1})}} + {{else}} + Scanner unoccupied + {{/if}} + + {{if data.locked}} + {{:helper.link('Unlock', 'locked', {'lock' : 1}, null, 'redButton')}} + {{else}} + {{:helper.link('Lock', 'unlocked', {'lock' : 1})}} + {{/if}} + + {{else}} + No scanner connected! + {{/if}} + + {{if data.podsLen}} + {{for data.pods}} + {{:value.pod}} biomass: {{:value.biomass}} + {{/for}} + {{/if}} + + +

    Database Functions

    + + {{:helper.link('View Records', 'list', {'menu' : 2})}} + + {{:helper.link('Eject Disk', 'eject', {'disk' : 'eject'}, data.diskette ? null : 'linkOff')}} + +{{else data.menu == 2}} +

    Current records

    + + {{:helper.link('Back', 'arrowreturn-1-w', {'menu' : 1})}} + + {{for data.records}} +
  • {{:helper.link(value.name, 'document', {'view_rec' : value.record})}}
  • + {{/for}} + +{{else data.menu == 3}} +

    Selected Record

    + {{:helper.link('Back', 'arrowreturn-1-w', {'menu' : 2})}} + + {{if activeRecord}} + {{:helper.link('Delete Record', 'trash', {'del_rec' : 1}, null, 'redButton')}} + Name: {{:data.activeRecord.real_name}} + + + + {{:helper.link('Load from disk', 'transfer-e-w', {'disk' : 'load'}, data.disk ? null : 'linkOff')}} + + Save: {{:helper.link('UI + UE', 'disk', {'save_disk' : 'ue'}, data.disk ? null : 'linkOff')}} + {{:helper.link('UI', 'disk', {'save_disk' : 'ui'}, data.disk ? null : 'linkOff')}} + {{:helper.link('SE', 'disk', {'save_disk' : 'se'}, data.disk ? null : 'linkOff')}} + + UI: {{:data.activeRecord.ui}} + SE: {{:data.activeRecord.se}} + + {{:helper.link('Clone', 'play', {'clone' : data.activeRecord.active_record}, data.podsLen ? null : 'linkOff')}} + + {{else}} + ERROR: Record not found. + {{/if}} + +{{else data.menu == 4}} + {{:data.temp}} + +

    Confirm Record Deletion

    + + Scan card to confirm. + + {{:helper.link('Cancel', 'cancel', {'menu' : 3})}} + +{{/if}} \ No newline at end of file diff --git a/nano/templates/fax.tmpl b/nano/templates/fax.tmpl new file mode 100644 index 0000000000..5af31d6adc --- /dev/null +++ b/nano/templates/fax.tmpl @@ -0,0 +1,32 @@ + + +Confirm Identity: {{:helper.link(data.scanName, 'check', {'scan' : 1})}} +{{if data.authenticated}} + {{:helper.link('Log Out', 'eject', {'logout' : 1}, null, 'linkDanger')}} +
    + Logged in to: {{:data.bossName}} Quantum Entanglement Network + {{if data.copyItem}} + {{:helper.link('Remove Item', 'eject', {'remove' : 1})}} + {{if data.cooldown}} + Transmitter arrays realigning. Please stand by. + {{else}} + {{:helper.link('Send', 'signal-diag', {'send' : 1})}} + Currently sending: {{:data.copyItemName}} + Sending to: {{:helper.link(data.destination, 'tag', {'dept' : 1})}} + {{/if}} + {{else}} + Please insert paper to send via secure connection. + {{if data.cooldown}} + Transmitter arrays realigning. Please stand by. + {{/if}} + {{/if}} +{{else}} + {{:helper.link('Log In', 'person', {'auth' : 1})}} + Proper authentication is required to use this device. + {{if data.copyItem}} + {{:helper.link('Remove Item', 'eject', {'remove' : 1})}} + {{/if}} +{{/if}} \ No newline at end of file diff --git a/nano/templates/guest_pass.tmpl b/nano/templates/guest_pass.tmpl new file mode 100644 index 0000000000..bed279b51a --- /dev/null +++ b/nano/templates/guest_pass.tmpl @@ -0,0 +1,59 @@ + + +{{if data.mode == 1}} +
    +
    + Activity Log +
    + {{:helper.link('Print', 'print', {'print' : 1})}} {{:helper.link('Back', 'arrowreturn-1-w', {'mode' : 0})}} +
    +
    + {{for data.log}} +
    + {{:value}} +
    + {{/for}} +{{else}} +

    Guest pass terminal #{{:data.uid}}

    +
    + {{:helper.link('View activity log', 'list', {'mode' : 1})}} {{:helper.link('Issure Pass', 'eject', {'action' : 'issue'})}} +
    +
    +
    +
    + Issuing ID: +
    + {{:helper.link(data.giver, 'person', {'action' : 'id'})}} +
    +
    +
    + Issued to: +
    + {{:helper.link(data.giveName, 'pencil', {'choice' : 'giv_name'})}} +
    +
    +
    + Reason: +
    + {{:helper.link(data.reason, 'pencil', {'choice' : 'reason'})}} +
    +
    +
    + Duration (minutes): +
    + {{:helper.link(data.duration, 'clock', {'choice' : 'duration'})}} +
    +
    +
    + Access to areas: +
    +
    + {{for data.area}} +
    + {{:helper.link(value.area_name, value.on ? 'check' : 'close', {'choice' : 'access', 'access' : value.area}, null, value.on ? 'linkOn' : null)}} +
    + {{/for}} +{{/if}} \ No newline at end of file diff --git a/nano/templates/holodeck.tmpl b/nano/templates/holodeck.tmpl new file mode 100644 index 0000000000..6c813944dd --- /dev/null +++ b/nano/templates/holodeck.tmpl @@ -0,0 +1,33 @@ + + +Current Loaded Programs: +{{for data.supportedPrograms}} + {{:helper.link(value.name, data.currentProgram == value.program ? 'check' : 'clear', {'program' : value.program}, data.currentProgram == value.program ? 'linkOn' : null)}} +{{/for}} +Please ensure that only holographic weapons are used in the holodeck if a combat simulation has been loaded. +{{if data.isSilicon}} + {{if data.safetyDisabled}} + {{if data.emagged}} + ERROR: Cannot re-enable Safety Protocols. + {{else}} + {{:helper.link('Re-Enable Safety Protocols?', 'help', {'AIoverride' : 1}, null, 'linkOn')}} + {{/if}} + {{else}} + {{:helper.link('Re-Enable Safety Protocols?', 'help', {'AIoverride' : 1}, null, 'linkDanger')}} + {{/if}} +{{/if}} + +{{if data.safetyDisabled}} + {{for data.restrictedPrograms}} + {{:helper.link('Begin ' + value.name, data.currentProgram == value.program ? 'check' : 'clear', {'program' : value.program}, data.currentProgram == value.program ? 'linkOn' : null)}} + Ensure the holodeck is empty before testing. + {{/for}} + Safety Protocols are DISABLED +{{else}} + Safety Protocols are ENABLED +{{/if}} + +{{:helper.link(data.gravity ? 'On ' : 'Off', data.gravity ? 'check' : 'clear', {'gravity' : 1}, null, data.gravity ? 'linkOn' : linkDanger')}} \ No newline at end of file diff --git a/nano/templates/laptop_vendor.tmpl b/nano/templates/laptop_vendor.tmpl new file mode 100644 index 0000000000..6854619b19 --- /dev/null +++ b/nano/templates/laptop_vendor.tmpl @@ -0,0 +1,175 @@ + + +{{if data.mode == 0}} +
    +
    + Please choose your laptop customization options.
    + Your comptuer will automatically be loaded with any programs you can use after the transaction is complete.
    + Some programs will require additional components to be installed! +
    +
    + +
    + +
    +
    HDD (Required):
    +
    Added
    +
    + +
    +
    + Card Reader: +
    + {{:helper.link('Single (50)', data.cardreader == 1 ? 'check' : 'plus', {'choice' : 'single_add'}, data.cardreader == 1 ? 'selected' : null)}} + {{:helper.link('Dual (125)', data.cardreader == 2 ? 'check' : 'plus', {'choice' : 'dual_add'}, data.cardreader == 2 ? 'selected' : null)}} + {{:helper.link('None', 'close', {'choice' : 'cardreader_rem'}, data.cardreader == 0 ? 'redButton' : null)}} +
    + +
    +
    + Floppy Drive: +
    + {{:helper.link('Add (50)', data.floppy == 1 ? 'check' : 'plus', {'choice' : 'floppy_add'}, data.floppy == 1 ? 'selected' : null)}} + {{:helper.link('None', 'close', {'choice' : 'floppy_rem'}, data.floppy == 0 ? 'redButton' : null)}} +
    + +
    +
    + Radio card: +
    + {{:helper.link('Add (50)', data.radionet == 1 ? 'check' : 'plus', {'choice' : 'radio_add'}, data.radionet == 1 ? 'selected' : null)}} + {{:helper.link('None', 'close', {'choice' : 'radio_rem'}, data.radionet == 0 ? 'redButton' : null)}} +
    + +
    +
    + Camera Card: +
    + {{:helper.link('Add (100)', data.camera == 1 ? 'check' : 'plus', {'choice' : 'camnet_add'}, data.camera == 1 ? 'selected' : null)}} + {{:helper.link('None', 'close', {'choice' : 'camnet_rem'}, data.camera == 0 ? 'redButton' : null)}} +
    + +
    +
    + Network card: +
    +
    + {{:helper.link('Area (75)', data.network == 1 ? 'check' : 'plus', {'choice' : 'area_add'}, data.network == 1 ? 'selected' : null)}} + {{:helper.link('Adjacent (50)', data.network == 2 ? 'check' : 'plus', {'choice' : 'prox_add'}, data.network == 2 ? 'selected' : null)}} + {{:helper.link('Powernet (25)', data.network == 3 ? 'check' : 'plus', {'choice' : 'cable_add'}, data.network == 3 ? 'selected' : null)}} + {{:helper.link('None', 'close', {'choice' : 'network_rem'}, data.network == 0 ? 'redButton' : null)}} +
    +
    + +
    + +
    +
    + Power Source: +
    + {{:helper.link('Extended (175)', data.power == 1 ? 'check' : 'plus', {'choice' : 'high_add'}, data.power == 1 ? 'selected' : null)}} + {{:helper.link('Unreal (250)', data.power == 2 ? 'check' : 'plus', {'choice' : 'super_add'}, data.power == 2 ? 'selected' : null)}} + {{:helper.link('Default', data.power == 0 ? 'check' : 'plus', {'choice' : 'power_rem'}, data.power == 0 ? 'selected' : null)}} +
    + +
    +
    +
    Total:
    +
    {{:data.total}}
    + {{:helper.link('Vend Laptop', 'cart', {'choice' : 'vend'})}} +
    + +{{else data.mode == 1}} +

    Cart

    + +
    + +
    +
    Total:
    +
    {{:data.total}}
    +
    + +
    +
    Card Reader:
    + {{if data.cardreader == 1}} + {{:helper.link('(single) (50)', 'close', {'choice' : 'cardreader_rem'})}} + {{else data.cardreader == 2}} + {{:helper.link('(double) (125)', 'close', {'choice' : 'cardreader_rem'})}} + {{else}} +
    None
    + {{/if}} +
    + +
    +
    Floppy Drive:
    + {{if data.floppy == 1}} + {{:helper.link('Added (50)', 'close', {'choice' : 'floppy_rem'})}} + {{else}} +
    None
    + {{/if}} +
    + +
    +
    Radio Card:
    + {{if data.radionet == 1}} + {{:helper.link('Added (50)', 'close', {'choice' : 'radio_rem'})}} + {{else}} +
    None
    + {{/if}} +
    + +
    +
    Camera Card:
    + {{if data.camera == 1}} + {{:helper.link('Added (100)', 'close', {'choice' : 'camnet_rem'})}} + {{else}} +
    None
    + {{/if}} +
    + +
    +
    Network Card:
    + {{if data.network == 1}} + {{:helper.link('Area (75)', 'close', {'choice' : 'network_rem'})}} + {{else data.network == 2}} + {{:helper.link('Adjacent (50)', 'close', {'choice' : 'network_rem'})}} + {{else data.network == 3}} + {{:helper.link('Powernet (25)', 'close', {'choice' : 'network_rem'})}} + {{else}} +
    None
    + {{/if}} +
    + +
    +
    Power Source:
    + {{if data.power == 1}} + {{:helper.link('Unreal (250)', 'close', {'choice' : 'power_rem'})}} + {{else data.power == 2}} + {{:helper.link('Extended (175)', 'close', {'choice' : 'power_rem'})}} + {{else}} +
    Regular
    + {{/if}} +
    + +
    + +
    +
    Please swipe your card and enter your PIN to complete the transaction
    +
    + +
    + + {{:helper.link('Cancel', 'close', {'choice' : 'cancel'}, null, 'redButton')}} + +{{else data.mode == 2}} +
    + Please swipe your card and enter your PIN to finish returning your computer. + +
    + + {{:helper.link('Cancel', 'close', {'choice' : 'cancel'}, null, 'redButton')}} +
    +{{/if}} \ No newline at end of file diff --git a/nano/templates/operating.tmpl b/nano/templates/operating.tmpl new file mode 100644 index 0000000000..3772639915 --- /dev/null +++ b/nano/templates/operating.tmpl @@ -0,0 +1,75 @@ + + +{{if data.table}} +

    Patient Information:

    + {{if data.victim}} +
    +
    + Name: +
    + {{:data.victim.real_name}} +
    +
    +
    + Age: +
    + {{:data.victim.age}} +
    +
    +
    + Blood Type: +
    + {{:data.victim.b_type}} +
    +
    +
    +
    + Health: +
    + {{:data.victim.health}} +
    +
    +
    + Brute Damage: +
    + {{:data.victim.brute}} +
    +
    +
    + Toxins Damage: +
    + {{:data.victim.tox}} +
    +
    +
    + Fire Damage: +
    + {{:data.victim.burn}} +
    +
    +
    + Suffocation Damage: +
    + {{:data.victim.oxy}} +
    +
    +
    + Patient Status: +
    + {{:data.victim.stat}} +
    +
    +
    + Heartbeat Rate: +
    + {{:data.victim.pulse}} +
    + {{else}} + No Patient Detected + {{/if}} +{{else}} + No Table Detected +{{/if}} diff --git a/nano/templates/photocopier.tmpl b/nano/templates/photocopier.tmpl new file mode 100644 index 0000000000..9d1bcf7918 --- /dev/null +++ b/nano/templates/photocopier.tmpl @@ -0,0 +1,47 @@ + + +{{if data.copyItem}} +
    + {{:helper.link('Remove Item', 'eject', {'remove' : 1})}} + {{if data.toner}} + {{:helper.link('Copy', 'copy', {'copy' : 1})}}
    +
    +
    +
    + Printing: +
    +
    +
    + {{:helper.link('-', null, {'min' : 1}, data.copies == 1 ? 'linkOff' : null)}} +
    {{:data.copies}}
    + {{:helper.link('+', null, {'add' : 1}, data.copies == data.maxCopies ? 'linkOff' : null)}} +
    +
    +
    +
    +
    +
    Current toner level:
    +
    {{:data.toner}}u
    +
    + {{else}} +
    + Please insert a new toner cartridge! +
    + {{/if}} +{{else data.toner}} +

    Please insert something to copy.

    + {{if data.isSilicon}} + {{:helper.link('Print photo from database', 'image', {'aipic' : 1})}} + {{/if}} +
    +
    Current toner level:
    +
    {{:data.toner}}u
    +
    +{{else}} +
    + Please insert a new toner cartridge! +
    +{{/if}} \ No newline at end of file From 244fb40de80d1561c44d0bda953f479bd76ef150 Mon Sep 17 00:00:00 2001 From: SinTwo Date: Mon, 20 Jun 2016 23:32:18 -0400 Subject: [PATCH 04/15] Fixes part 1 --- code/game/machinery/atmo_control.dm | 15 +- code/game/machinery/computer/arcade.dm | 12 +- code/game/machinery/computer/cloning.dm | 2 +- code/game/machinery/computer3/lapvend.dm | 5 +- code/modules/holodeck/HolodeckControl.dm | 4 +- code/modules/paperwork/faxmachine.dm | 2 +- code/modules/paperwork/photocopier.dm | 2 +- code/modules/reagents/Chemistry-Machinery.dm | 193 +++++------- nano/css/icons.css | 26 ++ nano/css/shared.css | 15 +- nano/images/pills32.png | Bin 0 -> 2317 bytes nano/templates/adv_med.tmpl | 8 +- nano/templates/arcade_battle.tmpl | 8 +- nano/templates/atmo_control.tmpl | 53 ++-- nano/templates/chem_master.tmpl | 313 +++++++------------ nano/templates/cloning.tmpl | 4 +- nano/templates/fax.tmpl | 55 +++- nano/templates/holodeck.tmpl | 25 +- nano/templates/laptop_vendor.tmpl | 8 +- nano/templates/operating.tmpl | 90 ++---- nano/templates/photocopier.tmpl | 4 +- 21 files changed, 388 insertions(+), 456 deletions(-) create mode 100644 nano/images/pills32.png diff --git a/code/game/machinery/atmo_control.dm b/code/game/machinery/atmo_control.dm index 43b9bf5913..629d962f51 100644 --- a/code/game/machinery/atmo_control.dm +++ b/code/game/machinery/atmo_control.dm @@ -122,7 +122,7 @@ obj/machinery/computer/general_air_control/Destroy() ui = nanomanager.try_update_ui(user, src, ui_key, ui, data, force_open) if (!ui) - ui = new(user, src, ui_key, "atmo_control.tmpl", src.name, 400, 500) + ui = new(user, src, ui_key, "atmo_control.tmpl", src.name, 525, 500) ui.set_initial_data(data) ui.open() ui.set_auto_update(5) @@ -169,6 +169,7 @@ obj/machinery/computer/general_air_control/Destroy() data["input_info"] = list("power" = input_info["power"], "volume_rate" = round(input_info["volume_rate"], 0.1)) else data["input_info"] = null + if(output_info) data["output_info"] = list("power" = output_info["power"], "output_pressure" = output_info["internal"]) else @@ -179,7 +180,7 @@ obj/machinery/computer/general_air_control/Destroy() ui = nanomanager.try_update_ui(user, src, ui_key, ui, data, force_open) if (!ui) - ui = new(user, src, ui_key, "atmo_control.tmpl", src.name, 400, 500) + ui = new(user, src, ui_key, "atmo_control.tmpl", src.name, 525, 500) ui.set_initial_data(data) ui.open() ui.set_auto_update(5) @@ -201,12 +202,12 @@ obj/machinery/computer/general_air_control/Destroy() return 1 if(href_list["adj_pressure"]) - var/change = href_list["adj_pressure"] + var/change = text2num(href_list["adj_pressure"]) pressure_setting = between(0, pressure_setting + change, 50*ONE_ATMOSPHERE) return 1 if(href_list["adj_input_flow_rate"]) - var/change = href_list["adj_input_flow_rate"] + var/change = text2num(href_list["adj_input_flow_rate"]) input_flow_setting = between(0, input_flow_setting + change, ATMOS_DEFAULT_VOLUME_PUMP + 500) //default flow rate limit for air injectors return 1 @@ -292,7 +293,7 @@ obj/machinery/computer/general_air_control/Destroy() ui = nanomanager.try_update_ui(user, src, ui_key, ui, data, force_open) if (!ui) - ui = new(user, src, ui_key, "atmo_control.tmpl", src.name, 400, 500) + ui = new(user, src, ui_key, "atmo_control.tmpl", src.name, 525, 500) ui.set_initial_data(data) ui.open() ui.set_auto_update(5) @@ -314,12 +315,12 @@ obj/machinery/computer/general_air_control/Destroy() return 1 if(href_list["adj_pressure"]) - var/change = href_list["adj_pressure"] + var/change = text2num(href_list["adj_pressure"]) pressure_setting = between(0, pressure_setting + change, 10*ONE_ATMOSPHERE) return 1 if(href_list["adj_input_flow_rate"]) - var/change = href_list["adj_input_flow_rate"] + var/change = text2num(href_list["adj_input_flow_rate"]) input_flow_setting = between(0, input_flow_setting + change, ATMOS_DEFAULT_VOLUME_PUMP + 500) //default flow rate limit for air injectors return 1 diff --git a/code/game/machinery/computer/arcade.dm b/code/game/machinery/computer/arcade.dm index 68b62bd1ab..d338edacc1 100644 --- a/code/game/machinery/computer/arcade.dm +++ b/code/game/machinery/computer/arcade.dm @@ -84,6 +84,7 @@ circuit = /obj/item/weapon/circuitboard/arcade/battle var/enemy_name = "Space Villian" var/temp = "Winners don't use space drugs" //Temporary message, for attack messages, etc + var/enemy_action = "" var/player_hp = 30 //Player health/attack points var/player_mp = 10 var/enemy_hp = 45 //Enemy health/attack points @@ -123,6 +124,7 @@ var/list/data = list() data["temp"] = temp + data["enemyAction"] = enemy_action data["enemyName"] = enemy_name data["playerHP"] = player_hp data["playerMP"] = player_mp @@ -131,7 +133,7 @@ ui = nanomanager.try_update_ui(user, src, ui_key, ui, data, force_open) if (!ui) - ui = new(user, src, ui_key, "arcade_battle.tmpl", src.name, 400, 500) + ui = new(user, src, ui_key, "arcade_battle.tmpl", src.name, 400, 300) ui.set_initial_data(data) ui.open() //ui.set_auto_update(2) @@ -218,12 +220,12 @@ else if (emagged && (turtle >= 4)) var/boomamt = rand(5,10) - temp = "[enemy_name] throws a bomb, exploding you for [boomamt] damage!" + enemy_action = "[enemy_name] throws a bomb, exploding you for [boomamt] damage!" player_hp -= boomamt else if ((enemy_mp <= 5) && (prob(70))) var/stealamt = rand(2,3) - temp = "[enemy_name] steals [stealamt] of your power!" + enemy_action = "[enemy_name] steals [stealamt] of your power!" player_mp -= stealamt if (player_mp <= 0) @@ -237,13 +239,13 @@ feedback_inc("arcade_loss_mana_normal") else if ((enemy_hp <= 10) && (enemy_mp > 4)) - temp = "[enemy_name] heals for 4 health!" + enemy_action = "[enemy_name] heals for 4 health!" enemy_hp += 4 enemy_mp -= 4 else var/attackamt = rand(3,6) - temp = "[enemy_name] attacks for [attackamt] damage!" + enemy_action = "[enemy_name] attacks for [attackamt] damage!" player_hp -= attackamt if ((player_mp <= 0) || (player_hp <= 0)) diff --git a/code/game/machinery/computer/cloning.dm b/code/game/machinery/computer/cloning.dm index 37108a268b..b96d557b32 100644 --- a/code/game/machinery/computer/cloning.dm +++ b/code/game/machinery/computer/cloning.dm @@ -120,7 +120,7 @@ pods_list_ui[++pods_list_ui.len] = list("pod" = pod, "biomass" = pod.biomass) if(pods) - data["pods"] = pods + data["pods"] = pods_list_ui else data["pods"] = null diff --git a/code/game/machinery/computer3/lapvend.dm b/code/game/machinery/computer3/lapvend.dm index ceb66a68bd..6acb530acc 100644 --- a/code/game/machinery/computer3/lapvend.dm +++ b/code/game/machinery/computer3/lapvend.dm @@ -32,9 +32,11 @@ if(vendmode == 1 && I) scan_id(I, W) vendmode = 0 + nanomanager.update_uis(src) if(vendmode == 2 && I) if(reimburse_id(I, W)) vendmode = 0 + nanomanager.update_uis(src) if(vendmode == 0) if(istype(W, /obj/item/device/laptop)) var/obj/item/device/laptop/L = W @@ -44,6 +46,7 @@ L.loc = src vendmode = 2 usr << "You slot your [L.name] into \The [src.name]" + nanomanager.update_uis(src) else ..() @@ -74,7 +77,7 @@ ui = nanomanager.try_update_ui(user, src, ui_key, ui, data, force_open) if (!ui) - ui = new(user, src, ui_key, "laptop_vendor.tmpl", src.name, 480, 500) + ui = new(user, src, ui_key, "laptop_vendor.tmpl", src.name, 480, 425) ui.set_initial_data(data) ui.open() //ui.set_auto_update(5) diff --git a/code/modules/holodeck/HolodeckControl.dm b/code/modules/holodeck/HolodeckControl.dm index fd887db55e..1bc0c721c7 100644 --- a/code/modules/holodeck/HolodeckControl.dm +++ b/code/modules/holodeck/HolodeckControl.dm @@ -80,10 +80,10 @@ ui = nanomanager.try_update_ui(user, src, ui_key, ui, data, force_open) if (!ui) - ui = new(user, src, ui_key, "holodeck.tmpl", src.name, 400, 500) + ui = new(user, src, ui_key, "holodeck.tmpl", src.name, 400, 550) ui.set_initial_data(data) ui.open() - //ui.set_auto_update(5) + ui.set_auto_update(20) /obj/machinery/computer/HolodeckControl/Topic(href, href_list) if(..()) diff --git a/code/modules/paperwork/faxmachine.dm b/code/modules/paperwork/faxmachine.dm index 00b34fb04b..8c30f1d486 100644 --- a/code/modules/paperwork/faxmachine.dm +++ b/code/modules/paperwork/faxmachine.dm @@ -59,7 +59,7 @@ var/list/adminfaxes = list() //cache for faxes that have been sent to admins ui = nanomanager.try_update_ui(user, src, ui_key, ui, data, force_open) if (!ui) - ui = new(user, src, ui_key, "fax.tmpl", src.name, 400, 500) + ui = new(user, src, ui_key, "fax.tmpl", src.name, 500, 500) ui.set_initial_data(data) ui.open() ui.set_auto_update(10) //this machine is so unimportant let's not have it update that often. diff --git a/code/modules/paperwork/photocopier.dm b/code/modules/paperwork/photocopier.dm index 924ed8334d..ec0d7acf19 100644 --- a/code/modules/paperwork/photocopier.dm +++ b/code/modules/paperwork/photocopier.dm @@ -52,7 +52,7 @@ ui = nanomanager.try_update_ui(user, src, ui_key, ui, data, force_open) if (!ui) - ui = new(user, src, ui_key, "photocopier.tmpl", src.name, 400, 500) + ui = new(user, src, ui_key, "photocopier.tmpl", src.name, 300, 250) ui.set_initial_data(data) ui.open() ui.set_auto_update(10) diff --git a/code/modules/reagents/Chemistry-Machinery.dm b/code/modules/reagents/Chemistry-Machinery.dm index 5c4dc8c169..c0bf6b4f33 100644 --- a/code/modules/reagents/Chemistry-Machinery.dm +++ b/code/modules/reagents/Chemistry-Machinery.dm @@ -2,7 +2,6 @@ #define LIQUID 2 #define GAS 3 -#define BOTTLE_SPRITES list("bottle-1", "bottle-2", "bottle-3", "bottle-4") //list of available bottle sprites #define REAGENTS_PER_SHEET 20 @@ -23,10 +22,11 @@ var/condi = 0 var/useramount = 15 // Last used amount var/pillamount = 10 - var/bottlesprite = "bottle-1" //yes, strings - var/pillsprite = "1" - var/client/has_sprites = list() + var/bottlesprite = 1 + var/pillsprite = 1 var/max_pill_count = 20 + var/tab = "home" + var/analyze_data[0] flags = OPENCONTAINER /obj/machinery/chem_master/New() @@ -56,7 +56,6 @@ user.drop_item() B.loc = src user << "You add the beaker to the machine!" - src.updateUsrDialog() icon_state = "mixer1" else if(istype(B, /obj/item/weapon/storage/pill_bottle)) @@ -69,9 +68,74 @@ user.drop_item() B.loc = src user << "You add the pill bottle into the dispenser slot!" - src.updateUsrDialog() return +/obj/machinery/chem_master/attack_hand(mob/user as mob) + if(stat & BROKEN) + return + user.set_machine(src) + ui_interact(user) + +/** + * Display the NanoUI window for the chem master. + * + * See NanoUI documentation for details. + */ +/obj/machinery/chem_master/ui_interact(mob/user, ui_key = "main", var/datum/nanoui/ui = null, var/force_open = 1) + user.set_machine(src) + + var/list/data = list() + data["tab"] = tab + data["condi"] = condi + + if(loaded_pill_bottle) + data["pillBottle"] = list("total" = loaded_pill_bottle.contents.len, "max" = loaded_pill_bottle.storage_slots) + else + data["pillBottle"] = null + + if(beaker) + var/datum/reagents/R = beaker:reagents + var/ui_reagent_beaker_list[0] + for(var/datum/reagent/G in R.reagent_list) + ui_reagent_beaker_list[++ui_reagent_beaker_list.len] = list("name" = G.name, "volume" = G.volume, "description" = G.description, "id" = G.id) + + data["beaker"] = list("total_volume" = R.total_volume, "reagent_list" = ui_reagent_beaker_list) + else + data["beaker"] = null + + if(reagents.total_volume) + var/ui_reagent_list[0] + for(var/datum/reagent/N in reagents.reagent_list) + ui_reagent_list[++ui_reagent_list.len] = list("name" = N.name, "volume" = N.volume, "description" = N.description, "id" = N.id) + + data["reagents"] = list("total_volume" = reagents.total_volume, "reagent_list" = ui_reagent_list) + else + data["reagents"] = null + + data["mode"] = mode + + if(analyze_data) + data["analyzeData"] = list("name" = analyze_data["name"], "desc" = analyze_data["desc"], "blood_type" = analyze_data["blood_type"], "blood_DNA" = analyze_data["blood_DNA"]) + else + data["analyzeData"] = null + + data["pillSprite"] = pillsprite + data["bottleSprite"] = bottlesprite + + var/P[20] //how many pill sprites there are. Sprites are taken from chemical.dmi and can be found in nano/images/pill.png + for(var/i = 1 to P.len) + P[i] = i + data["pillSpritesAmount"] = P + + data["bottleSpritesAmount"] = list(1, 2, 3, 4) //how many bottle sprites there are. Sprites are taken from chemical.dmi and can be found in nano/images/pill.png + + ui = nanomanager.try_update_ui(user, src, ui_key, ui, data, force_open) + if (!ui) + ui = new(user, src, ui_key, "chem_master.tmpl", src.name, 575, 400) + ui.set_initial_data(data) + ui.open() + ui.set_auto_update(5) + /obj/machinery/chem_master/Topic(href, href_list) if(stat & (BROKEN|NOPOWER)) return if(usr.stat || usr.restrained()) return @@ -80,20 +144,19 @@ src.add_fingerprint(usr) usr.set_machine(src) + if(href_list["tab_select"]) + tab = href_list["tab_select"] if (href_list["ejectp"]) if(loaded_pill_bottle) loaded_pill_bottle.loc = src.loc loaded_pill_bottle = null - else if(href_list["close"]) - usr << browse(null, "window=chemmaster") - usr.unset_machine() - return if(beaker) var/datum/reagents/R = beaker:reagents - if (href_list["analyze"]) - var/dat = "" + if (tab == "analyze") + analyze_data["name"] = href_list["name"] + analyze_data["desc"] = href_list["desc"] if(!condi) if(href_list["name"] == "Blood") var/datum/reagent/blood/G @@ -101,16 +164,9 @@ if(F.name == href_list["name"]) G = F break - var/A = G.name - var/B = G.data["blood_type"] - var/C = G.data["blood_DNA"] - dat += "Chemmaster 3000Chemical infos:

    Name:
    [A]

    Description:
    Blood Type: [B]
    DNA: [C]


    (Back)" - else - dat += "Chemmaster 3000Chemical infos:

    Name:
    [href_list["name"]]

    Description:
    [href_list["desc"]]


    (Back)" - else - dat += "Condimaster 3000Condiment infos:

    Name:
    [href_list["name"]]

    Description:
    [href_list["desc"]]


    (Back)" - usr << browse(dat, "window=chem_master;size=575x400") - return + analyze_data["name"] = G.name + analyze_data["blood_type"] = G.data["blood_type"] + analyze_data["blood_DNA"] = G.data["blood_DNA"] else if (href_list["add"]) @@ -147,9 +203,6 @@ else if (href_list["toggle"]) mode = !mode - else if (href_list["main"]) - attack_hand(usr) - return else if (href_list["eject"]) if(beaker) beaker:loc = src.loc @@ -187,7 +240,6 @@ if(src.loaded_pill_bottle) if(loaded_pill_bottle.contents.len < loaded_pill_bottle.storage_slots) P.loc = loaded_pill_bottle - src.updateUsrDialog() else if (href_list["createbottle"]) if(!condi) @@ -197,106 +249,23 @@ P.name = "[name] bottle" P.pixel_x = rand(-7, 7) //random position P.pixel_y = rand(-7, 7) - P.icon_state = bottlesprite + P.icon_state = "bottle"+bottlesprite reagents.trans_to_obj(P,60) P.update_icon() else var/obj/item/weapon/reagent_containers/food/condiment/P = new/obj/item/weapon/reagent_containers/food/condiment(src.loc) reagents.trans_to_obj(P,50) - else if(href_list["change_pill"]) - #define MAX_PILL_SPRITE 20 //max icon state of the pill sprites - var/dat = "" - for(var/i = 1 to MAX_PILL_SPRITE) - dat += "" - dat += "
    " - usr << browse(dat, "window=chem_master") - return - else if(href_list["change_bottle"]) - var/dat = "" - for(var/sprite in BOTTLE_SPRITES) - dat += "" - dat += "
    " - usr << browse(dat, "window=chem_master") - return + else if(href_list["pill_sprite"]) pillsprite = href_list["pill_sprite"] else if(href_list["bottle_sprite"]) bottlesprite = href_list["bottle_sprite"] - src.updateUsrDialog() - return + nanomanager.update_uis(src) /obj/machinery/chem_master/attack_ai(mob/user as mob) return src.attack_hand(user) -/obj/machinery/chem_master/attack_hand(mob/user as mob) - if(stat & BROKEN) - return - user.set_machine(src) - if(!(user.client in has_sprites)) - spawn() - has_sprites += user.client - for(var/i = 1 to MAX_PILL_SPRITE) - usr << browse_rsc(icon('icons/obj/chemical.dmi', "pill" + num2text(i)), "pill[i].png") - for(var/sprite in BOTTLE_SPRITES) - usr << browse_rsc(icon('icons/obj/chemical.dmi', sprite), "[sprite].png") - var/dat = "" - if(!beaker) - dat = "Please insert beaker.
    " - if(src.loaded_pill_bottle) - dat += "Eject Pill Bottle \[[loaded_pill_bottle.contents.len]/[loaded_pill_bottle.storage_slots]\]

    " - else - dat += "No pill bottle inserted.

    " - dat += "Close" - else - var/datum/reagents/R = beaker:reagents - dat += "Eject beaker and Clear Buffer
    " - if(src.loaded_pill_bottle) - dat += "Eject Pill Bottle \[[loaded_pill_bottle.contents.len]/[loaded_pill_bottle.storage_slots]\]

    " - else - dat += "No pill bottle inserted.

    " - if(!R.total_volume) - dat += "Beaker is empty." - else - dat += "Add to buffer:
    " - for(var/datum/reagent/G in R.reagent_list) - dat += "[G.name] , [G.volume] Units - " - dat += "(Analyze) " - dat += "(1) " - dat += "(5) " - dat += "(10) " - dat += "(30) " - dat += "(60) " - dat += "(All) " - dat += "(Custom)
    " - - dat += "
    Transfer to [(!mode ? "disposal" : "beaker")]:
    " - if(reagents.total_volume) - for(var/datum/reagent/N in reagents.reagent_list) - dat += "[N.name] , [N.volume] Units - " - dat += "(Analyze) " - dat += "(1) " - dat += "(5) " - dat += "(10) " - dat += "(30) " - dat += "(60) " - dat += "(All) " - dat += "(Custom)
    " - else - dat += "Empty
    " - if(!condi) - dat += "

    Create pill (60 units max)
    " - dat += "Create multiple pills
    " - dat += "Create bottle (60 units max)" - else - dat += "Create bottle (50 units max)" - if(!condi) - user << browse("Chemmaster 3000Chemmaster menu:

    [dat]", "window=chem_master;size=575x400") - else - user << browse("Condimaster 3000Condimaster menu:

    [dat]", "window=chem_master;size=575x400") - onclose(user, "chem_master") - return - /obj/machinery/chem_master/condimaster name = "CondiMaster 3000" condi = 1 diff --git a/nano/css/icons.css b/nano/css/icons.css index a6bec0f0d0..b2eacc0ab8 100644 --- a/nano/css/icons.css +++ b/nano/css/icons.css @@ -245,6 +245,32 @@ .uiIcon16.icon-note64 { background-image: url(uiIcons64.png); background-position: -64px -64px; width: 64px; height: 64px; } .uiIcon16.icon-close64 { background-image: url(uiIcons64.png); background-position: -128px -64px; width: 64px; height: 64px; } +.uiIcon16.icon-pill { background-image: url(pills32.png); width: 32px; height: 32px;} +.uiIcon16.icon-pill.pill1 { background-position: 0 0; } +.uiIcon16.icon-pill.pill2 { background-position: -32px 0; } +.uiIcon16.icon-pill.pill3 { background-position: -64px 0; } +.uiIcon16.icon-pill.pill4 { background-position: -96px 0; } +.uiIcon16.icon-pill.pill5 { background-position: -128px 0; } +.uiIcon16.icon-pill.pill6 { background-position: 0 -32px; } +.uiIcon16.icon-pill.pill7 { background-position: -32px -32px; } +.uiIcon16.icon-pill.pill8 { background-position: -64px -32px; } +.uiIcon16.icon-pill.pill9 { background-position: -96px -32px; } +.uiIcon16.icon-pill.pill10 { background-position: -128px -32px; } +.uiIcon16.icon-pill.pill11 { background-position: 0 -64px; } +.uiIcon16.icon-pill.pill12 { background-position: -32px -64px; } +.uiIcon16.icon-pill.pill13 { background-position: -64px -64px; } +.uiIcon16.icon-pill.pill14 { background-position: -96px -64px; } +.uiIcon16.icon-pill.pill15 { background-position: -128px -64px; } +.uiIcon16.icon-pill.pill16 { background-position: 0 -96px; } +.uiIcon16.icon-pill.pill17 { background-position: -32px -96px; } +.uiIcon16.icon-pill.pill18 { background-position: -64px -96px; } +.uiIcon16.icon-pill.pill19 { background-position: -96px -96px; } +.uiIcon16.icon-pill.pill20 { background-position: -128px -96px; } +.uiIcon16.icon-pill.bottle1 { background-position: 0 -128px; } +.uiIcon16.icon-pill.bottle2 { background-position: -32px -128px; } +.uiIcon16.icon-pill.bottle3 { background-position: -64px -128px; } +.uiIcon16.icon-pill.bottle4 { background-position: -96px -128px; } + .mapIcon16 { position: absolute; width: 16px; diff --git a/nano/css/shared.css b/nano/css/shared.css index a50f96a3c7..16dfecc648 100644 --- a/nano/css/shared.css +++ b/nano/css/shared.css @@ -45,6 +45,19 @@ hr { white-space: nowrap; } +.link32 { + float: left; + min-width: 15px; + max-width: 31px; + height: 31px; + text-align: center; + text-decoration: none; + background: #40628a; + border: 1px solid #161616; + margin: 0 2px 2px 0; + cursor: default; +} + .hasIcon { padding: 0px 4px 4px 0px; } @@ -649,7 +662,7 @@ th.misc { } .oxyloss { - color: blue; + color: #0000A9; } /* 75px width used in power monitoring console buttons */ diff --git a/nano/images/pills32.png b/nano/images/pills32.png new file mode 100644 index 0000000000000000000000000000000000000000..61459093c1cac55e1f6309e08afa82bcb56e82dd GIT binary patch literal 2317 zcmZux2{@bS7XBlsgxGqOQln}{bwOLH7DHmYU8qtFS{kaFpwuPyEp5emRXe5&O$2Q% zkpxwP)ZPWRL|VJrTT2AdDk>St{HZ(lxik0v&-woIednC#d%ov=&w0}v9Zn$N>Tm!6 z5T{PsoCAHnc*#hE|BP;|KIkN|mS-#hpfXGLHyOhy(K}55gKBtN zcf9kpEBHvCP(L8V$3GZv5bTHFjWjr9U~<(c!2tkdGEUi8x4WX)D?H^6TH?+yb(1TyB7D6bw3Qt8;xa=MmtuTSEg7w=1nu#uWK)=fzSKn zYbLkd3)+@$89d%N8twh&-gQ3be3f8%tT0X0@Zzo#3gajR72lXz0B+h|k2%SGzQBvC zF+%>-cXlARJkgsb&X^a>QI)-oHt}@WE0^%gP#5oP-walE8wSSoZIhop(3Z7c7bT3N z1X;Vd`(___i23BacTE8w9L(q@5{VY?lS@KkGKee1iGmYsqjKR}e+*_Ldn@c4OBz^P zLd483JtwcNzA}&HU)3mV^-#lvPb-jX_VPDJtKGoF)R^nIaGpxH{vItc;t1&{x~t|_ z2ND8_IOwwoM1{diCP4Rs(qtls^+={0nzsQBPI2HF zy&|fP*6u%G{i{bGWc|2;R(hwfclLURk?lzoiNxV>_B_^dU`1L8?ZHHrMZwq8n<1fA zpYHM}KPF8bSbfm}d*wEt@}bgiye-`_VYzYLl$RLt9=(YtJK?T1ME`4J>PZ`^MikSZ zV`@WO+bpXgwk#c(Gducm}ie`s$QRWT?E44sg@0|>O6eYPD>z&KF>u2tL|JGdCZ=69q8 zIiTVLbEWmdq{QYd6~&pbV=;jrKty#F*l|(=r2qxB$;pQ=TWclU?>RfJu94rV@^1r4 z-PHvUt!QC%ijRe<@VjCP!^qf1s$_O>(&K6>+_AgzMb)69N`9Vi3bs;vzxX9*lM2gD z6C@uXn={j`sz5~bkY!p9xBj#JF8+Uj&fcD0-m3upD|O$_XmbH2mL|hV$u_DB!+zs2 zZ#zZrG-brRuNWjTtu!|MohO&#RmY_cXK6W{)oVNla_kuQB;mM;o5n@aSecNUQtqmS z_L|;asYk*IN8H5rGXVW`S9u~;N^jok7ZB-QqTUwH1TFKCu-C!~edCut<=3oT2tBAF zp8bxz-DrtU^?XO%PbktZ;uWxuol^PD&WX!A;@NfmZmFTT$+RtCwmM$sP#EF=f(|^q zPgcm&rzU*-SVIPJ!IIN&&QG;Y+2w#-+HA9T*eC`c*7;UQuQE&QLZhE#vI* zEEa0y)K8_Uu0R#%VoN*_EhU4-TGvC&)@7+FPkq8?CR}r%diwCZgvN0f-+|& zIcNxx2YHHI9(>j#{k6B;EziwfrLZ-oHnLOP<21$9mafjufaBEk=l;0nNx0r-I;V^t!{ z9yTQ;a|fhwK@E+tEq#(4{J99C=v^ePny!F8+uzJ~=P;qT+C~YPEiqb+Z7{clg^-a5 z0+8~z{0i;;&Cmu9?85TFZ^OWt^!U=!*U^0_Ct=(7&91PJb_krP=bVCd0-2C|BoC4J zGs?{;D+31@<%oAph}{TK!ud5V?V*d5Yw}1X_|@p>x{?6VzL?L7)>uZa8oAs-^sACC zp5wZ`KvuU|I6)Hz>7>@pRf&YWI%>p-$Q6li8InNG#;##r*|{#(ipp?vo_2P2w(a+^ zSaJu8q8ZjAd6E!ap&E21$-wvmVGn+Wn#QgJr%*ZHKFQ!70AqXM7u_5K+)+IKP)9t3 zMv2_KI!72Amc3p1X=ON^-qEjmRG`++d>RpN68ZotzbWxseS}xw(^cCpi{xqs%?oo& zPKaJ>4&1r8C$!v9eMx74**_;}|ND|`dqX3xHp`QH{t-_{V@6^}MnYMN0a?^dB^x%= z%upx{^6;uf@F>$&?i??pf#Jy&(#h+0G{ckvy#NTK(Qu6!N*B~bjGc(+v_&=$Slf2 z!6p3-_{Dh4Lij-7Z2aZoXvgX*-mjW>uh{s9Mniz_gaKf Brute:
    -
    +
    {{:data.occupant.bruteLoss}}

    Burn:
    -
    +
    {{:data.occupant.fireLoss}}

    Oxygen:
    -
    +
    {{:data.occupant.oxyLoss}}

    Toxins:
    -
    +
    {{:data.occupant.toxLoss}}

    diff --git a/nano/templates/arcade_battle.tmpl b/nano/templates/arcade_battle.tmpl index 0455649404..7725698634 100644 --- a/nano/templates/arcade_battle.tmpl +++ b/nano/templates/arcade_battle.tmpl @@ -4,8 +4,12 @@ -->

    {{:data.enemyName}}

    - -
    {{:data.temp}}
    +{{if data.gameOver}} +
    {{:data.temp}}
    +{{else}} +
    {{:data.temp}}
    +
    {{:data.enemyAction}}
    +{{/if}}
    Health:
    {{:data.playerHP}}
    diff --git a/nano/templates/atmo_control.tmpl b/nano/templates/atmo_control.tmpl index 503f15458f..d4033f41e0 100644 --- a/nano/templates/atmo_control.tmpl +++ b/nano/templates/atmo_control.tmpl @@ -5,30 +5,37 @@ {{if data.sensors}} {{for data.sensors}} {{if value.sensor_data}} -
    - {{:value.long_name}} +
    +
    {{:value.long_name}}
    {{if value.sensor_data.pressure}} -
    Pressure:
    - {{:value.sensor_data.pressure}} kPa +
    +
    Pressure:
    +
    {{:value.sensor_data.pressure}} kPa
    +
    {{/if}} {{if value.sensor_data.temperature}} -
    Temperature:
    - {{:value.sensor_data.temperature}} kPa +
    +
    Temperature:
    +
    {{:value.sensor_data.temperature}} kPa
    +
    {{/if}} {{if value.sensor_data.oxygen || value.sensor_data.nitrogen || value.sensor_data.carbon_dioxide || value.sensor_data.phoron}} -
    Gas Composition:
    - {{if value.sensor_data.oxygen}} - {{:value.sensor_data.pressure}} % O2 - {{/if}} - {{if value.sensor_data.nitrogen}} - {{:value.sensor_data.pressure}} % N - {{/if}} - {{if value.sensor_data.carbon_dioxide}} - {{:value.sensor_data.pressure}} % CO2 - {{/if}} - {{if value.sensor_data.phoron}} - {{:value.sensor_data.pressure}} % TX - {{/if}} +
    +
    Gas Composition:
    + {{if value.sensor_data.oxygen}} +
    {{:value.sensor_data.pressure}} % O2
    + {{/if}} + {{if value.sensor_data.nitrogen}} +
    {{:value.sensor_data.pressure}} % N
    + {{/if}} + {{if value.sensor_data.carbon_dioxide}} +
    {{:value.sensor_data.pressure}} % CO2
    + {{/if}} + {{if value.sensor_data.phoron}} +
    {{:value.sensor_data.pressure}} % TX
    + {{/if}} + +
    {{/if}}
    {{else}} @@ -68,7 +75,6 @@ On Hold {{/if}}
    - {{:helper.link('Refresh', null, {'in_refresh_status' : 1})}}
    Flow Rate Limit:
    @@ -78,6 +84,7 @@
    Command:
    {{:helper.link('Toggle Power', null, {'in_toggle_injector' : 1})}} {{:helper.link('Set Flow Rate', null, {'in_set_flowrate' : 1})}} + {{:helper.link('Refresh', null, {'in_refresh_status' : 1})}}
    {{else}}
    @@ -112,13 +119,12 @@ {{/if}}
    - {{if data.input_info.power}} + {{if data.output_info.power}} Open {{else}} On Hold {{/if}}
    - {{:helper.link('Refresh', null, {'out_refresh_status' : 1})}}
    {{if data.tanks}} @@ -133,6 +139,7 @@
    Command:
    {{:helper.link('Toggle Power', null, {'out_toggle_power' : 1})}} {{:helper.link('Set Pressure', null, {'out_set_pressure' : 1})}} + {{:helper.link('Refresh', null, {'out_refresh_status' : 1})}}
    {{else}}
    @@ -190,8 +197,8 @@ {{else}} On Hold {{/if}} +
    {{:helper.link('Refresh', null, {'refresh_status' : 1})}}
    - {{:helper.link('Refresh', null, {'refresh_status' : 1})}}
    Rate:
    diff --git a/nano/templates/chem_master.tmpl b/nano/templates/chem_master.tmpl index f163447dbf..1b8315154a 100644 --- a/nano/templates/chem_master.tmpl +++ b/nano/templates/chem_master.tmpl @@ -1,205 +1,116 @@ /obj/machinery/chem_master/attackby(var/obj/item/weapon/B as obj, var/mob/user as mob) + Interface for chem master + See: code/modules/reagents/Chemistry-Machinery.dm +--> +{{if data.tab == 'home'}} +
    +
    {{:helper.link(data.pillBottle ? 'Eject Pill Bottle' : 'No pill bottle inserted', 'eject', {'ejectp' : 1}, data.pillBottle ? null : 'linkOff')}}
    - if(beaker) - var/datum/reagents/R = beaker:reagents - if (href_list["analyze"]) - var/dat = "" - if(!condi) - if(href_list["name"] == "Blood") - var/datum/reagent/blood/G - for(var/datum/reagent/F in R.reagent_list) - if(F.name == href_list["name"]) - G = F - break - var/A = G.name - var/B = G.data["blood_type"] - var/C = G.data["blood_DNA"] - dat += "Chemmaster 3000Chemical infos:

    Name:
    [A]

    Description:
    Blood Type: [B]
    DNA: [C]


    (Back)" - else - dat += "Chemmaster 3000Chemical infos:

    Name:
    [href_list["name"]]

    Description:
    [href_list["desc"]]


    (Back)" - else - dat += "Condimaster 3000Condiment infos:

    Name:
    [href_list["name"]]

    Description:
    [href_list["desc"]]


    (Back)" - usr << browse(dat, "window=chem_master;size=575x400") - return + {{if data.pillBottle}} +
    {{:data.pillBottle.total}} / {{:data.pillBottle.max}}
    + {{/if}} +
    +
    {{:helper.link(data.beaker ? 'Eject Beaker and Clear Buffer' : 'Please insert beaker', 'eject', {'eject' : 1}, data.beaker ? null : 'linkOff')}}
    + + {{if data.beaker}} + {{if data.beaker.total_volume}} + Add to buffer: + {{for data.beaker.reagent_list}} +
    +
    {{:value.name}}
    +
    {{:value.volume}} Units
    +
    +
    + {{:helper.link('Analyze', 'signal-diag', {'tab_select' : 'analyze', 'desc' : value.description, 'name' : value.name})}} + {{:helper.link('1', 'plus', {'add' : value.id, 'amount' : 1})}} + {{:helper.link('5', 'plus', {'add' : value.id, 'amount' : 5})}} + {{:helper.link('10', 'plus', {'add' : value.id, 'amount' : 10})}} + {{:helper.link('30', 'plus', {'add' : value.id, 'amount' : 30})}} + {{:helper.link('60', 'plus', {'add' : value.id, 'amount' : 60})}} + {{:helper.link('All', 'plus', {'add' : value.id, 'amount' : value.volume})}} + {{:helper.link('Custom', 'plus', {'addcustom' : value.id})}} +
    + {{/for}} + {{else}} + Beaker is empty. + {{/if}} +
    +
    +
    Transfer to
    + {{:helper.link(!data.mode ? 'disposal' : 'beaker', null, {'toggle' : 1})}} +
    + {{if data.reagents}} + {{if data.reagents.total_volume}} + {{for data.reagents.reagent_list}} +
    +
    {{:value.name}}
    +
    {{:value.volume}} Units
    +
    +
    + {{:helper.link('Analyze', 'signal-diag', {'tab_select' : 'analyze', 'desc' : value.description, 'name' : value.name})}} + {{:helper.link('1', 'minus', {'remove' : value.id, 'amount' : 1})}} + {{:helper.link('5', 'minus', {'remove' : value.id, 'amount' : 5})}} + {{:helper.link('10', 'minus', {'remove' : value.id, 'amount' : 10})}} + {{:helper.link('30', 'minus', {'remove' : value.id, 'amount' : 30})}} + {{:helper.link('60', 'minus', {'remove' : value.id, 'amount' : 60})}} + {{:helper.link('All', 'minus', {'remove' : value.id, 'amount' : value.volume})}} + {{:helper.link('Custom', 'minus', {'removecustom' : value.id})}} +
    + {{/for}} + {{/if}} + {{else}} + Empty + {{/if}} + {{if !data.condi}} +
    +
    + {{:helper.link('Create pill (60 units max)', null, {'createpill' : 1})}} + {{:helper.link('Create multiple pills', null, {'createpill_multiple' : 1})}} + {{:helper.link('Create bottle (60 units max)', null, {'createbottle' : 1})}} +
    +
    + {{:helper.link('', 'pill pill' + data.pillSprite, {'tab_select' : 'pill'}, null, 'link32')}} + {{:helper.link('', 'pill bottle' + data.bottleSprite, {'tab_select' : 'bottle'}, null, 'link32')}} +
    + {{/if}} + {{/if}} - else if (href_list["add"]) +{{else data.tab == 'analyze'}} + {{if !data.condi}} +

    Chemical Info:

    + {{else}} +

    Condiment Info:

    + {{/if}} +
    +
    Name:
    +
    {{:data.analyzeData.name}}
    +
    + {{if data.analyzeData.name == 'Blood'}} +
    +
    Blood Type:
    +
    {{:data.analyzeData.blood_type}}
    +
    +
    +
    DNA:
    +
    {{:data.analyzeData.blood_DNA}}
    +
    + {{else}} +
    +
    Description:
    +
    {{:data.analyzeData.desc}}
    +
    + {{/if}} + {{:helper.link('Back', 'arrowreturn-1-w', {'tab_select' : 'home'})}} - if(href_list["amount"]) - var/id = href_list["add"] - var/amount = Clamp((text2num(href_list["amount"])), 0, 200) - R.trans_id_to(src, id, amount) - - else if (href_list["addcustom"]) - - var/id = href_list["addcustom"] - useramount = input("Select the amount to transfer.", 30, useramount) as num - useramount = Clamp(useramount, 0, 200) - src.Topic(null, list("amount" = "[useramount]", "add" = "[id]")) - - else if (href_list["remove"]) - - if(href_list["amount"]) - var/id = href_list["remove"] - var/amount = Clamp((text2num(href_list["amount"])), 0, 200) - if(mode) - reagents.trans_id_to(beaker, id, amount) - else - reagents.remove_reagent(id, amount) - - - else if (href_list["removecustom"]) - - var/id = href_list["removecustom"] - useramount = input("Select the amount to transfer.", 30, useramount) as num - useramount = Clamp(useramount, 0, 200) - src.Topic(null, list("amount" = "[useramount]", "remove" = "[id]")) - - else if (href_list["toggle"]) - mode = !mode - - else if (href_list["main"]) - attack_hand(usr) - return - else if (href_list["eject"]) - if(beaker) - beaker:loc = src.loc - beaker = null - reagents.clear_reagents() - icon_state = "mixer0" - else if (href_list["createpill"] || href_list["createpill_multiple"]) - var/count = 1 - - if(reagents.total_volume/count < 1) //Sanity checking. - return - - if (href_list["createpill_multiple"]) - count = input("Select the number of pills to make.", "Max [max_pill_count]", pillamount) as num - count = Clamp(count, 1, max_pill_count) - - if(reagents.total_volume/count < 1) //Sanity checking. - return - - var/amount_per_pill = reagents.total_volume/count - if (amount_per_pill > 60) amount_per_pill = 60 - - var/name = sanitizeSafe(input(usr,"Name:","Name your pill!","[reagents.get_master_reagent_name()] ([amount_per_pill] units)"), MAX_NAME_LEN) - - if(reagents.total_volume/count < 1) //Sanity checking. - return - while (count--) - var/obj/item/weapon/reagent_containers/pill/P = new/obj/item/weapon/reagent_containers/pill(src.loc) - if(!name) name = reagents.get_master_reagent_name() - P.name = "[name] pill" - P.pixel_x = rand(-7, 7) //random position - P.pixel_y = rand(-7, 7) - P.icon_state = "pill"+pillsprite - reagents.trans_to_obj(P,amount_per_pill) - if(src.loaded_pill_bottle) - if(loaded_pill_bottle.contents.len < loaded_pill_bottle.storage_slots) - P.loc = loaded_pill_bottle - src.updateUsrDialog() - - else if (href_list["createbottle"]) - if(!condi) - var/name = sanitizeSafe(input(usr,"Name:","Name your bottle!",reagents.get_master_reagent_name()), MAX_NAME_LEN) - var/obj/item/weapon/reagent_containers/glass/bottle/P = new/obj/item/weapon/reagent_containers/glass/bottle(src.loc) - if(!name) name = reagents.get_master_reagent_name() - P.name = "[name] bottle" - P.pixel_x = rand(-7, 7) //random position - P.pixel_y = rand(-7, 7) - P.icon_state = bottlesprite - reagents.trans_to_obj(P,60) - P.update_icon() - else - var/obj/item/weapon/reagent_containers/food/condiment/P = new/obj/item/weapon/reagent_containers/food/condiment(src.loc) - reagents.trans_to_obj(P,50) - else if(href_list["change_pill"]) - #define MAX_PILL_SPRITE 20 //max icon state of the pill sprites - var/dat = "" - for(var/i = 1 to MAX_PILL_SPRITE) - dat += "" - dat += "
    " - usr << browse(dat, "window=chem_master") - return - else if(href_list["change_bottle"]) - var/dat = "" - for(var/sprite in BOTTLE_SPRITES) - dat += "" - dat += "
    " - usr << browse(dat, "window=chem_master") - return - else if(href_list["pill_sprite"]) - pillsprite = href_list["pill_sprite"] - else if(href_list["bottle_sprite"]) - bottlesprite = href_list["bottle_sprite"] - - src.updateUsrDialog() - return - - -{{:helper.link(data.beaker ? 'Eject Beaker and Clear Buffer' : 'Please insert beaker', 'eject', {'eject' : 1}), data.beaker ? null : 'linkOff'}} -{{:helper.link(data.pillBottle ? 'Eject Pill Bottle' : 'Please insert beaker', 'eject', {'ejectp' : 1}), data.pillBottle ? null : 'linkOff'}} -{{:data.pillBottleTotal}} / {{:data.pillBottleMax}} - -{{if data.beakerReagent}} - Add to buffer: - {{for data.beakerReagent}} - {{:value.name}} , {{:value.volume}} Units - - {{:helper.link('Analyze', 'signal-diag', {'analyze' : 1, 'desc' : value.description, 'name' : value.name})}} - {{:helper.link('1', 'plus', {'add' : value.id, 'amount' : 1})}} - {{:helper.link('5', 'plus', {'add' : value.id, 'amount' : 5})}} - {{:helper.link('10', 'plus', {'add' : value.id, 'amount' : 10})}} - {{:helper.link('30', 'plus', {'add' : value.id, 'amount' : 30})}} - {{:helper.link('60', 'plus', {'add' : value.id, 'amount' : 60})}} - {{:helper.link('All', 'plus', {'add' : value.id, 'amount' : value.volume})}} - {{:helper.link('Custom', 'plus', {'addcustom' : value.id})}} - -if(!beaker) data.beaker -if(src.loaded_pill_bottle) data.pillBottle -[[loaded_pill_bottle.contents.len]/[loaded_pill_bottle.storage_slots]\] data.pillBottleTotal data.pillBottleMax - -var/datum/reagents/R = beaker:reagents -if(!R.total_volume) - dat += "Beaker is empty." - else - dat += "Add to buffer:
    " - for(var/datum/reagent/G in R.reagent_list) - dat += "[G.name] , [G.volume] Units - " - dat += "(Analyze) " - dat += "(1) " - dat += "(5) " - dat += "(10) " - dat += "(30) " - dat += "(60) " - dat += "(All) " - dat += "(Custom)
    " - - dat += "
    Transfer to [(!mode ? "disposal" : "beaker")]:
    " - if(reagents.total_volume) - for(var/datum/reagent/N in reagents.reagent_list) - dat += "[N.name] , [N.volume] Units - " - dat += "(Analyze) " - dat += "(1) " - dat += "(5) " - dat += "(10) " - dat += "(30) " - dat += "(60) " - dat += "(All) " - dat += "(Custom)
    " - else - dat += "Empty
    " - if(!condi) - dat += "

    Create pill (60 units max)
    " - dat += "Create multiple pills
    " - dat += "Create bottle (60 units max)" - else - dat += "Create bottle (50 units max)" - if(!condi) - user << browse("Chemmaster 3000Chemmaster menu:

    [dat]", "window=chem_master;size=575x400") - else - user << browse("Condimaster 3000Condimaster menu:

    [dat]", "window=chem_master;size=575x400") - onclose(user, "chem_master") - return \ No newline at end of file +{{else data.tab == 'pill'}} + {{for data.pillSpritesAmount}} + {{:helper.link('', 'pill pill' + value, {'pill_sprite' : value}, null, data.pillSprite == value ? 'linkOn link32' : 'link32')}} + {{/for}} +

    {{:helper.link('Return', 'arrowreturn-1-w', {'tab_select' : 'home'})}}
    + +{{else data.tab == 'bottle'}} + {{for data.bottleSpritesAmount}} + {{:helper.link('', 'pill bottle' + value, {'bottle_sprite' : value}, null, data.bottleSprite == value ? 'linkOn link32' : 'link32')}} + {{/for}} +

    {{:helper.link('Return', 'arrowreturn-1-w', {'tab_select' : 'home'})}}
    +{{/if}} \ No newline at end of file diff --git a/nano/templates/cloning.tmpl b/nano/templates/cloning.tmpl index d1ea7df3ad..a6e0a2544c 100644 --- a/nano/templates/cloning.tmpl +++ b/nano/templates/cloning.tmpl @@ -77,7 +77,7 @@ {{:helper.link('Delete Record', 'trash', {'del_rec' : 1}, null, 'redButton')}} Name: {{:data.activeRecord.real_name}} - + --> {{:helper.link('Load from disk', 'transfer-e-w', {'disk' : 'load'}, data.disk ? null : 'linkOff')}} diff --git a/nano/templates/fax.tmpl b/nano/templates/fax.tmpl index 5af31d6adc..4745a7aeb3 100644 --- a/nano/templates/fax.tmpl +++ b/nano/templates/fax.tmpl @@ -3,30 +3,53 @@ See: code/modules/paperwork/faxmachine.dm --> -Confirm Identity: {{:helper.link(data.scanName, 'check', {'scan' : 1})}} +
    +
    + Confirm Identity: +
    + {{:helper.link(data.scanName ? data.scanName : 'Insert Card', 'check', {'scan' : 1})}} + {{if data.authenticated}} + {{:helper.link('Log Out', 'eject', {'logout' : 1}, null, 'redButton')}} + {{else}} + {{:helper.link('Log In', 'person', {'auth' : 1}, data.scanName ? null : 'linkOff')}} + {{/if}} +
    {{if data.authenticated}} - {{:helper.link('Log Out', 'eject', {'logout' : 1}, null, 'linkDanger')}} +
    - Logged in to: {{:data.bossName}} Quantum Entanglement Network + +
    +
    + Logged in to: +
    +
    + {{:data.bossName}} Quantum Entanglement Network +
    +
    {{if data.copyItem}} - {{:helper.link('Remove Item', 'eject', {'remove' : 1})}} {{if data.cooldown}} - Transmitter arrays realigning. Please stand by. +
    Transmitter arrays realigning. Please stand by.
    {{else}} - {{:helper.link('Send', 'signal-diag', {'send' : 1})}} - Currently sending: {{:data.copyItemName}} - Sending to: {{:helper.link(data.destination, 'tag', {'dept' : 1})}} +
    +
    Currently sending:
    +
    {{:data.copyItemName}}
    +
    +
    +
    Sending to:
    + {{:helper.link(data.destination, 'tag', {'dept' : 1})}} +
    +
    {{:helper.link('Send', 'signal-diag', {'send' : 1})}}
    {{/if}} {{else}} - Please insert paper to send via secure connection. +
    Please insert paper to send via secure connection.
    {{if data.cooldown}} - Transmitter arrays realigning. Please stand by. +
    Transmitter arrays realigning. Please stand by.
    {{/if}} {{/if}} {{else}} - {{:helper.link('Log In', 'person', {'auth' : 1})}} - Proper authentication is required to use this device. - {{if data.copyItem}} - {{:helper.link('Remove Item', 'eject', {'remove' : 1})}} - {{/if}} -{{/if}} \ No newline at end of file +
    Proper authentication is required to use this device.
    +{{/if}} +{{if data.copyItem}} +
    {{:helper.link('Remove Item', 'eject', {'remove' : 1})}}
    +{{/if}} + diff --git a/nano/templates/holodeck.tmpl b/nano/templates/holodeck.tmpl index 6c813944dd..71d4ad5605 100644 --- a/nano/templates/holodeck.tmpl +++ b/nano/templates/holodeck.tmpl @@ -3,31 +3,34 @@ See: code/modules/holodeck/HolodeckControl.dm --> -Current Loaded Programs: +

    Current Loaded Programs:

    {{for data.supportedPrograms}} - {{:helper.link(value.name, data.currentProgram == value.program ? 'check' : 'clear', {'program' : value.program}, data.currentProgram == value.program ? 'linkOn' : null)}} +
    {{:helper.link(value.name, data.currentProgram == value.program ? 'check' : 'close', {'program' : value.program}, null, data.currentProgram == value.program ? 'linkOn' : null)}}
    {{/for}} -Please ensure that only holographic weapons are used in the holodeck if a combat simulation has been loaded. +
    Please ensure that only holographic weapons are used in the holodeck if a combat simulation has been loaded.
    {{if data.isSilicon}} {{if data.safetyDisabled}} {{if data.emagged}} - ERROR: Cannot re-enable Safety Protocols. +
    ERROR: Cannot re-enable Safety Protocols.
    {{else}} - {{:helper.link('Re-Enable Safety Protocols?', 'help', {'AIoverride' : 1}, null, 'linkOn')}} +
    {{:helper.link('Re-Enable Safety Protocols?', 'help', {'AIoverride' : 1}, null, 'linkOn')}}
    {{/if}} {{else}} - {{:helper.link('Re-Enable Safety Protocols?', 'help', {'AIoverride' : 1}, null, 'linkDanger')}} +
    {{:helper.link('Re-Enable Safety Protocols?', 'help', {'AIoverride' : 1}, null, 'redButton')}}
    {{/if}} {{/if}} {{if data.safetyDisabled}} {{for data.restrictedPrograms}} - {{:helper.link('Begin ' + value.name, data.currentProgram == value.program ? 'check' : 'clear', {'program' : value.program}, data.currentProgram == value.program ? 'linkOn' : null)}} - Ensure the holodeck is empty before testing. +
    {{:helper.link('Begin ' + value.name, data.currentProgram == value.program ? 'check' : 'close', {'program' : value.program}, null, data.currentProgram == value.program ? 'linkOn' : null)}}
    {{/for}} - Safety Protocols are DISABLED +
    Ensure the holodeck is empty before testing.
    +
    Safety Protocols are DISABLED
    {{else}} - Safety Protocols are ENABLED +
    Safety Protocols are ENABLED
    {{/if}} -{{:helper.link(data.gravity ? 'On ' : 'Off', data.gravity ? 'check' : 'clear', {'gravity' : 1}, null, data.gravity ? 'linkOn' : linkDanger')}} \ No newline at end of file +
    +
    Gravity:
    + {{:helper.link(data.gravity ? 'On ' : 'Off', data.gravity ? 'check' : 'close', {'gravity' : 1}, null, data.gravity ? 'linkOn' : 'redButton')}} +
    \ No newline at end of file diff --git a/nano/templates/laptop_vendor.tmpl b/nano/templates/laptop_vendor.tmpl index 6854619b19..e0de4f7272 100644 --- a/nano/templates/laptop_vendor.tmpl +++ b/nano/templates/laptop_vendor.tmpl @@ -5,11 +5,9 @@ {{if data.mode == 0}}
    -
    - Please choose your laptop customization options.
    - Your comptuer will automatically be loaded with any programs you can use after the transaction is complete.
    - Some programs will require additional components to be installed! -
    + Please choose your laptop customization options.
    + Your comptuer will automatically be loaded with any programs you can use after the transaction is complete.
    + Some programs will require additional components to be installed!

    diff --git a/nano/templates/operating.tmpl b/nano/templates/operating.tmpl index 3772639915..c53bd94c65 100644 --- a/nano/templates/operating.tmpl +++ b/nano/templates/operating.tmpl @@ -6,67 +6,39 @@ {{if data.table}}

    Patient Information:

    {{if data.victim}} -
    -
    - Name: +
    +
    Name:
    +
    {{:data.victim.real_name}}
    + +
    Age:
    +
    {{:data.victim.age}}
    + +
    Blood Type:
    +
    {{:data.victim.b_type}}
    - {{:data.victim.real_name}} -
    -
    -
    - Age: +
    +
    +
    Health:
    +
    {{:data.victim.health}}
    + +
    Brute Damage:
    +
    {{:data.victim.brute}}
    + +
    Toxins Damage:
    +
    {{:data.victim.tox}}
    + +
    Fire Damage:
    +
    {{:data.victim.burn}}
    + +
    Suffocation Damage:
    +
    {{:data.victim.oxy}}
    + +
    Patient Status:
    +
    {{:data.victim.stat}}
    + +
    Heartbeat Rate:
    +
    {{:data.victim.pulse}}
    - {{:data.victim.age}} -
    -
    -
    - Blood Type: -
    - {{:data.victim.b_type}} -
    -
    -
    -
    - Health: -
    - {{:data.victim.health}} -
    -
    -
    - Brute Damage: -
    - {{:data.victim.brute}} -
    -
    -
    - Toxins Damage: -
    - {{:data.victim.tox}} -
    -
    -
    - Fire Damage: -
    - {{:data.victim.burn}} -
    -
    -
    - Suffocation Damage: -
    - {{:data.victim.oxy}} -
    -
    -
    - Patient Status: -
    - {{:data.victim.stat}} -
    -
    -
    - Heartbeat Rate: -
    - {{:data.victim.pulse}} -
    {{else}} No Patient Detected {{/if}} diff --git a/nano/templates/photocopier.tmpl b/nano/templates/photocopier.tmpl index 9d1bcf7918..9c9910e969 100644 --- a/nano/templates/photocopier.tmpl +++ b/nano/templates/photocopier.tmpl @@ -10,7 +10,7 @@ {{:helper.link('Copy', 'copy', {'copy' : 1})}}

    -
    +
    Printing:
    @@ -23,7 +23,7 @@

    -
    Current toner level:
    +
    Current toner level:
    {{:data.toner}}u
    {{else}} From bc606ba9a481b6a2603f79c0a13420a29f7e3366 Mon Sep 17 00:00:00 2001 From: SinTwo Date: Tue, 21 Jun 2016 23:56:36 -0400 Subject: [PATCH 05/15] more fixes and updates. cloning ui fixed. --- code/game/machinery/adv_med.dm | 21 ++- code/game/machinery/atmo_control.dm | 8 +- code/game/machinery/computer/cloning.dm | 18 ++- code/game/machinery/computer/guestpass.dm | 7 +- nano/css/shared.css | 7 +- nano/templates/adv_med.tmpl | 165 +++++++++------------- nano/templates/atmo_control.tmpl | 139 +++++++++--------- nano/templates/cloning.tmpl | 111 +++++++-------- nano/templates/guest_pass.tmpl | 2 +- 9 files changed, 225 insertions(+), 253 deletions(-) diff --git a/code/game/machinery/adv_med.dm b/code/game/machinery/adv_med.dm index 9b24af92d2..1c9720ffbc 100644 --- a/code/game/machinery/adv_med.dm +++ b/code/game/machinery/adv_med.dm @@ -317,9 +317,11 @@ occupantData["blood"] = bloodData var/reagentData[0] - if(H.reagents) - for(var/datum/reagent/R in H.reagents) + if(H.reagents.reagent_list.len >= 1) + for(var/datum/reagent/R in H.reagents.reagent_list) reagentData[++reagentData.len] = list("name" = R.name, "amount" = R.volume) + else + reagentData = null occupantData["reagents"] = reagentData @@ -374,7 +376,12 @@ for(var/obj/item/organ/I in H.internal_organs) var/organData[0] organData["name"] = I.name - organData["desc"] = I.desc + if(I.status & ORGAN_ASSISTED) + organData["desc"] = "Assisted" + else if(I.robotic >= ORGAN_ROBOT) + organData["desc"] = "Mechanical" + else + organData["desc"] = null organData["germ_level"] = I.germ_level organData["damage"] = I.damage @@ -389,7 +396,7 @@ ui = nanomanager.try_update_ui(user, src, ui_key, ui, data, force_open) if(!ui) - ui = new(user, src, ui_key, "adv_med.tmpl", "Body Scanner", 690, 600) + ui = new(user, src, ui_key, "adv_med.tmpl", "Body Scanner", 690, 800) ui.set_initial_data(data) ui.open() ui.set_auto_update(1) @@ -543,7 +550,11 @@ dat += "[e.name]--Not Found" dat += "" for(var/obj/item/organ/i in occupant.internal_organs) - var/mech = i.desc + var/mech = "" + if(i.status & ORGAN_ASSISTED) + mech = "Assisted:" + if(i.robotic >= ORGAN_ROBOT) + mech = "Mechanical:" var/infection = "None" switch (i.germ_level) if (1 to INFECTION_LEVEL_ONE + 200) diff --git a/code/game/machinery/atmo_control.dm b/code/game/machinery/atmo_control.dm index 629d962f51..19d1ee1253 100644 --- a/code/game/machinery/atmo_control.dm +++ b/code/game/machinery/atmo_control.dm @@ -122,7 +122,7 @@ obj/machinery/computer/general_air_control/Destroy() ui = nanomanager.try_update_ui(user, src, ui_key, ui, data, force_open) if (!ui) - ui = new(user, src, ui_key, "atmo_control.tmpl", src.name, 525, 500) + ui = new(user, src, ui_key, "atmo_control.tmpl", src.name, 525, 600) ui.set_initial_data(data) ui.open() ui.set_auto_update(5) @@ -180,7 +180,7 @@ obj/machinery/computer/general_air_control/Destroy() ui = nanomanager.try_update_ui(user, src, ui_key, ui, data, force_open) if (!ui) - ui = new(user, src, ui_key, "atmo_control.tmpl", src.name, 525, 500) + ui = new(user, src, ui_key, "atmo_control.tmpl", src.name, 660, 500) ui.set_initial_data(data) ui.open() ui.set_auto_update(5) @@ -293,7 +293,7 @@ obj/machinery/computer/general_air_control/Destroy() ui = nanomanager.try_update_ui(user, src, ui_key, ui, data, force_open) if (!ui) - ui = new(user, src, ui_key, "atmo_control.tmpl", src.name, 525, 500) + ui = new(user, src, ui_key, "atmo_control.tmpl", src.name, 650, 500) ui.set_initial_data(data) ui.open() ui.set_auto_update(5) @@ -428,7 +428,7 @@ obj/machinery/computer/general_air_control/Destroy() ui = nanomanager.try_update_ui(user, src, ui_key, ui, data, force_open) if (!ui) - ui = new(user, src, ui_key, "atmo_control.tmpl", src.name, 400, 500) + ui = new(user, src, ui_key, "atmo_control.tmpl", src.name, 650, 500) ui.set_initial_data(data) ui.open() ui.set_auto_update(5) diff --git a/code/game/machinery/computer/cloning.dm b/code/game/machinery/computer/cloning.dm index b96d557b32..da165448da 100644 --- a/code/game/machinery/computer/cloning.dm +++ b/code/game/machinery/computer/cloning.dm @@ -113,7 +113,7 @@ var/records_list_ui[0] for(var/datum/dna2/record/R in records) - records_list_ui[++records_list_ui.len] = list("record" = R, "name" = R.dna.real_name) + records_list_ui[++records_list_ui.len] = list("ckey" = R.ckey, "name" = R.dna.real_name) var/pods_list_ui[0] for(var/obj/machinery/clonepod/pod in pods) @@ -130,7 +130,7 @@ data["records"] = null if(active_record) - data["activeRecord"] = list("active_record" = active_record, "real_name" = active_record.dna.real_name, \ + data["activeRecord"] = list("ckey" = active_record.ckey, "real_name" = active_record.dna.real_name, \ "ui" = active_record.dna.uni_identity, "se" = active_record.dna.struc_enzymes) else data["activeRecord"] = null @@ -139,6 +139,8 @@ data["connected"] = scanner data["podsLen"] = pods.len data["loading"] = loading + if(!scanner.occupant) + scantemp = "" data["scantemp"] = scantemp data["occupant"] = scanner.occupant data["locked"] = scanner.locked @@ -147,7 +149,7 @@ ui = nanomanager.try_update_ui(user, src, ui_key, ui, data, force_open) if (!ui) - ui = new(user, src, ui_key, "cloning.tmpl", src.name, 400, 300) + ui = new(user, src, ui_key, "cloning.tmpl", src.name, 400, 450) ui.set_initial_data(data) ui.open() ui.set_auto_update(5) @@ -176,8 +178,12 @@ else scanner.locked = 0 + else if ((href_list["eject"]) && (!isnull(scanner))) + if ((!scanner.locked) && (scanner.occupant)) + scanner.eject_occupant() + else if (href_list["view_rec"]) - active_record = locate(href_list["view_rec"]) + active_record = find_record(href_list["view_rec"]) if(istype(active_record,/datum/dna2/record)) if ((isnull(active_record.ckey))) qdel(active_record) @@ -235,7 +241,7 @@ updateUsrDialog() else if (href_list["clone"]) - var/datum/dna2/record/C = locate(href_list["clone"]) + var/datum/dna2/record/C = find_record(href_list["clone"]) //Look for that player! They better be dead! if(istype(C)) //Can't clone without someone to clone. Or a pod. Or if the pod is busy. Or full of gibs. @@ -277,6 +283,8 @@ else if (href_list["menu"]) menu = href_list["menu"] + temp = "" + scantemp = "" nanomanager.update_uis(src) add_fingerprint(usr) diff --git a/code/game/machinery/computer/guestpass.dm b/code/game/machinery/computer/guestpass.dm index eeec3a703e..b3f9765746 100644 --- a/code/game/machinery/computer/guestpass.dm +++ b/code/game/machinery/computer/guestpass.dm @@ -88,7 +88,7 @@ if(!giver && user.unEquip(I)) I.forceMove(src) giver = I - updateUsrDialog() + nanomanager.update_uis(src) else if(giver) user << "There is already ID card inside." return @@ -223,4 +223,7 @@ pass.reason = reason pass.name = "guest pass #[number]" else - usr << "Cannot issue pass without issuing ID." \ No newline at end of file + usr << "Cannot issue pass without issuing ID." + + src.add_fingerprint(usr) + nanomanager.update_uis(src) \ No newline at end of file diff --git a/nano/css/shared.css b/nano/css/shared.css index 16dfecc648..8728102b08 100644 --- a/nano/css/shared.css +++ b/nano/css/shared.css @@ -262,7 +262,7 @@ div.notice { overflow: auto; } -.itemContentNarrow, .itemContent { +.itemContentNarrow, .itemContent, .itemContentWide, .itemContentSmall, .itemContentMedium { float: left; } @@ -300,17 +300,14 @@ div.notice { } .itemContentWide { - float: left; width: 79%; } .itemContentSmall { - float: left; width: 33%; } .itemContentMedium { - float: left; width: 55%; } @@ -662,7 +659,7 @@ th.misc { } .oxyloss { - color: #0000A9; + color: #4444FF; } /* 75px width used in power monitoring console buttons */ diff --git a/nano/templates/adv_med.tmpl b/nano/templates/adv_med.tmpl index b9b6a59e30..7f7e931caf 100644 --- a/nano/templates/adv_med.tmpl +++ b/nano/templates/adv_med.tmpl @@ -28,73 +28,46 @@ Used In File(s): \code\game\machinery\adv_med.dm
    {{if data.occupant.stat==0}} - Alive + Stable {{else data.occupant.stat==1}} - Critical + Non-Responsive {{else}} Dead {{/if}}
    {{:helper.link('Print', 'document', {'print_p' : 1, 'name' : data.occupant.name})}} -
    -

    Damage:

    -
    - Brute: -
    -
    - {{:data.occupant.bruteLoss}} -

    -
    - Burn: -
    -
    - {{:data.occupant.fireLoss}} -

    -
    - Oxygen: -
    -
    - {{:data.occupant.oxyLoss}} -

    -
    - Toxins: -
    -
    - {{:data.occupant.toxLoss}} -

    -
    - Brain: -
    -
    - {{:data.occupant.brainLoss}} -

    -
    - Radiation Level: -
    -
    - {{:data.occupant.radLoss}} -

    -
    - Genetic: -
    -
    - {{:data.occupant.cloneLoss}} -

    -
    - Paralysis: -
    -
    - {{:data.occupant.paralysis}}% ({{:data.occupant.paralysisSeconds}} seconds left!) -

    -
    -
    -
    - Body Temperature: -
    -
    - {{:data.occupant.bodyTempC}}°C, {{:data.occupant.bodyTempF}}°F -
    +

    Damage:

    + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
    Brute:{{:data.occupant.bruteLoss}}Brain:{{:data.occupant.brainLoss}}
    Burn:{{:data.occupant.fireLoss}}Radiation:{{:data.occupant.radLoss}}
    Oxygen:{{:data.occupant.oxyLoss}}Genetic:{{:data.occupant.cloneLoss}}
    Toxins:{{:data.occupant.toxLoss}}Paralysis:{{:data.occupant.paralysis}}% ({{:data.occupant.paralysisSeconds}} seconds left!)
    Body Temperature:{{:helper.round(data.occupant.bodyTempC*10)/10}}°C, {{:helper.round(data.occupant.bodyTempF*10)/10}}°F
    {{if data.occupant.hasVirus}}
    @@ -107,45 +80,34 @@ Used In File(s): \code\game\machinery\adv_med.dm
    {{/if}} {{if data.occupant.blind}} - Pupils unresponsive.
    +
    Pupils unresponsive.
    {{/if}} {{if data.occupant.nearsighted}} - Retinal Misalignment Detected +
    Retinal Misalignment Detected
    {{/if}} -
    -
    - Blood -
    -
    -
    - Volume -
    -
    - {{:data.occupant.blood.volume}} -
    -
    - Percent -
    -
    - {{:data.occupant.blood.percent}}% -
    -
    -
    -
    - Reagents -
    -
    - {{for data.occupant.reagents}} -
    - {{:value.name}} -
    -
    - {{:value.amount}} -
    - {{/for}} -
    -
    - External Organs +

    Blood

    + + + + + + + +
    Volume:{{:data.occupant.blood.volume}}Percent:{{:data.occupant.blood.percent}}%
    +

    Reagents

    + {{if data.occupant.reagents}} + + {{for data.occupant.reagents}} + + + + + {{/for}} +
    {{:value.name}}:{{:value.amount}}
    + {{else}} +
    No reagents detected.
    + {{/if}} +

    External Organs

    {{for data.occupant.extOrgan}}
    @@ -225,24 +187,27 @@ Used In File(s): \code\game\machinery\adv_med.dm {{if value.implants_len}}
     Implants -

    +
    {{for value.implants :impValue:impindex}}
      {{:impValue.known ? impValue.name : "Unknown"}} -

    +
    {{/for}} {{/if}} {{/if}} -

    +
    {{/for}}
    - Internal Organs +

    Internal Organs

    {{for data.occupant.intOrgan}}
    {{:value.name}}
    +
    + {{:value.desc != null ? value.desc : ""}} +
    {{if value.germ_level > 100}} diff --git a/nano/templates/atmo_control.tmpl b/nano/templates/atmo_control.tmpl index d4033f41e0..be2f30d482 100644 --- a/nano/templates/atmo_control.tmpl +++ b/nano/templates/atmo_control.tmpl @@ -9,32 +9,31 @@
    {{:value.long_name}}
    {{if value.sensor_data.pressure}}
    -
    Pressure:
    +
    Pressure:
    {{:value.sensor_data.pressure}} kPa
    {{/if}} {{if value.sensor_data.temperature}}
    -
    Temperature:
    +
    Temperature:
    {{:value.sensor_data.temperature}} kPa
    {{/if}} {{if value.sensor_data.oxygen || value.sensor_data.nitrogen || value.sensor_data.carbon_dioxide || value.sensor_data.phoron}}
    -
    Gas Composition:
    - {{if value.sensor_data.oxygen}} -
    {{:value.sensor_data.pressure}} % O2
    - {{/if}} - {{if value.sensor_data.nitrogen}} -
    {{:value.sensor_data.pressure}} % N
    - {{/if}} - {{if value.sensor_data.carbon_dioxide}} -
    {{:value.sensor_data.pressure}} % CO2
    - {{/if}} - {{if value.sensor_data.phoron}} -
    {{:value.sensor_data.pressure}} % TX
    - {{/if}} - +
    Gas Composition:
    + {{if value.sensor_data.oxygen}} +
    {{:value.sensor_data.pressure}}% O2
    + {{/if}} + {{if value.sensor_data.nitrogen}} +
    {{:value.sensor_data.pressure}}% N
    + {{/if}} + {{if value.sensor_data.carbon_dioxide}} +
    {{:value.sensor_data.pressure}}% CO2
    + {{/if}} + {{if value.sensor_data.phoron}} +
    {{:value.sensor_data.pressure}}% TX
    + {{/if}}
    {{/if}}
    @@ -61,7 +60,7 @@ {{if data.input_info}}
    -
    +
    {{if data.tanks}} Input: {{else data.core}} @@ -77,41 +76,41 @@
    -
    Flow Rate Limit:
    +
    Flow Rate Limit:
    {{:data.input_info.volume_rate}} L/s
    -
    Command:
    - {{:helper.link('Toggle Power', null, {'in_toggle_injector' : 1})}} - {{:helper.link('Set Flow Rate', null, {'in_set_flowrate' : 1})}} - {{:helper.link('Refresh', null, {'in_refresh_status' : 1})}} +
    Command:
    + {{:helper.link('Toggle Power', 'power', {'in_toggle_injector' : 1})}} + {{:helper.link('Set Flow Rate', 'pencil', {'in_set_flowrate' : 1})}} + {{:helper.link('Refresh', 'refresh', {'in_refresh_status' : 1})}}
    {{else}}
    ERROR: Can not find input port
    - {{:helper.link('Search', null, {'in_refresh_status' : 1})}} + {{:helper.link('Search', 'search', {'in_refresh_status' : 1})}}
    {{/if}}
    -
    +
    Flow Rate Limit:
    -
    - {{:helper.link('-', null, {'adj_input_flow_rate' : -100})}} - {{:helper.link('-', null, {'adj_input_flow_rate' : -10})}} - {{:helper.link('-', null, {'adj_input_flow_rate' : -1})}} - {{:helper.link('-', null, {'adj_input_flow_rate' : -0.1})}} -
     {{:data.input_flow_setting}} L/s 
    - {{:helper.link('+', null, {'adj_input_flow_rate' : 0.1})}} - {{:helper.link('+', null, {'adj_input_flow_rate' : 1})}} - {{:helper.link('+', null, {'adj_input_flow_rate' : 10})}} - {{:helper.link('+', null, {'adj_input_flow_rate' : 100})}} +
    + {{:helper.link('100', 'minus', {'adj_input_flow_rate' : -100})}} + {{:helper.link('10', 'minus', {'adj_input_flow_rate' : -10})}} + {{:helper.link('1', 'minus', {'adj_input_flow_rate' : -1})}} + {{:helper.link('0.1', 'minus', {'adj_input_flow_rate' : -0.1})}} +
     {{:data.input_flow_setting}} L/s 
    + {{:helper.link('0.1', 'plus', {'adj_input_flow_rate' : 0.1})}} + {{:helper.link('1', 'plus', {'adj_input_flow_rate' : 1})}} + {{:helper.link('10', 'plus', {'adj_input_flow_rate' : 10})}} + {{:helper.link('100', 'plus', {'adj_input_flow_rate' : 100})}}
    {{if data.output_info}}
    -
    +
    {{if data.tanks}} Output: {{else data.core}} @@ -128,56 +127,56 @@
    {{if data.tanks}} -
    Max Output Pressure:
    +
    Max Output Pressure:
    {{:data.output_info.output_pressure}} kPa
    {{else data.core}} -
    Min Core Pressure:
    +
    Min Core Pressure:
    {{:data.output_info.pressure_limit}} kPa
    {{/if}}
    -
    Command:
    - {{:helper.link('Toggle Power', null, {'out_toggle_power' : 1})}} - {{:helper.link('Set Pressure', null, {'out_set_pressure' : 1})}} - {{:helper.link('Refresh', null, {'out_refresh_status' : 1})}} +
    Command:
    + {{:helper.link('Toggle Power', 'power', {'out_toggle_power' : 1})}} + {{:helper.link('Set Pressure', 'pencil', {'out_set_pressure' : 1})}} + {{:helper.link('Refresh', 'refresh', {'out_refresh_status' : 1})}}
    {{else}}
    ERROR: Can not find output port
    - {{:helper.link('Search', null, {'out_refresh_status' : 1})}} + {{:helper.link('Search', 'search', {'out_refresh_status' : 1})}}
    {{/if}}
    {{if data.tanks}} -
    +
    Max Output Pressure Set:
    -
    - {{:helper.link('-', null, {'adj_pressure' : -1000})}} - {{:helper.link('-', null, {'adj_pressure' : -100})}} - {{:helper.link('-', null, {'adj_pressure' : -10})}} - {{:helper.link('-', null, {'adj_pressure' : -1})}} -
     {{:data.pressure_setting}} kPa 
    - {{:helper.link('+', null, {'adj_pressure' : 1})}} - {{:helper.link('+', null, {'adj_pressure' : 10})}} - {{:helper.link('+', null, {'adj_pressure' : 100})}} - {{:helper.link('+', null, {'adj_pressure' : 1000})}} +
    + {{:helper.link('1000', 'minus', {'adj_pressure' : -1000})}} + {{:helper.link('100', 'minus', {'adj_pressure' : -100})}} + {{:helper.link('10', 'minus', {'adj_pressure' : -10})}} + {{:helper.link('1', 'minus', {'adj_pressure' : -1})}} +
     {{:data.pressure_setting}} kPa 
    + {{:helper.link('1', 'plus', {'adj_pressure' : 1})}} + {{:helper.link('10', 'plus', {'adj_pressure' : 10})}} + {{:helper.link('100', 'plus', {'adj_pressure' : 100})}} + {{:helper.link('1000', 'plus', {'adj_pressure' : 1000})}}
    {{else data.core}} -
    +
    Min Core Pressure Set:
    -
    - {{:helper.link('-', null, {'adj_pressure' : -100})}} - {{:helper.link('-', null, {'adj_pressure' : -50})}} - {{:helper.link('-', null, {'adj_pressure' : -10})}} - {{:helper.link('-', null, {'adj_pressure' : -1})}} -
     {{:data.pressure_setting}} kPa 
    - {{:helper.link('+', null, {'adj_pressure' : 1})}} - {{:helper.link('+', null, {'adj_pressure' : 10})}} - {{:helper.link('+', null, {'adj_pressure' : 50})}} - {{:helper.link('+', null, {'adj_pressure' : 100})}} +
    + {{:helper.link('100', 'minus', {'adj_pressure' : -100})}} + {{:helper.link('50', 'minus', {'adj_pressure' : -50})}} + {{:helper.link('10', 'minus', {'adj_pressure' : -10})}} + {{:helper.link('1', 'minus', {'adj_pressure' : -1})}} +
     {{:data.pressure_setting}} kPa 
    + {{:helper.link('1', 'plus', {'adj_pressure' : 1})}} + {{:helper.link('10', 'plus', {'adj_pressure' : 10})}} + {{:helper.link('50', 'plus', {'adj_pressure' : 50})}} + {{:helper.link('100', 'plus', {'adj_pressure' : 100})}}
    {{/if}}
    @@ -197,7 +196,7 @@ {{else}} On Hold {{/if}} -
    {{:helper.link('Refresh', null, {'refresh_status' : 1})}}
    +
    {{:helper.link('Refresh', 'refresh', {'refresh_status' : 1})}}
    @@ -207,19 +206,19 @@
    Automated Fuel Injection:
    {{if data.automation}} - {{:helper.link('Engaged', null, {'toggle_automation' : 1})}} + {{:helper.link('Engaged', 'check', {'toggle_automation' : 1})}}
    Injector Controls Locked Out
    {{else}} - {{:helper.link('Disengaged', null, {'toggle_automation' : 1})}} + {{:helper.link('Disengaged', 'close', {'toggle_automation' : 1})}}
    Injector:
    - {{:helper.link('Toggle Power', null, {'toggle_injector' : 1})}} - {{:helper.link('Inject (1 Cycle)', null, {'injection' : 1})}} + {{:helper.link('Toggle Power', 'power', {'toggle_injector' : 1})}} + {{:helper.link('Inject (1 Cycle)', 'syringe', {'injection' : 1})}} {{/if}}
    {{else}}
    ERROR: Can not find device
    - {{:helper.link('Search', null, {'refresh_status' : 1})}} + {{:helper.link('Search', 'search', {'refresh_status' : 1})}}
    {{/if}} {{/if}} \ No newline at end of file diff --git a/nano/templates/cloning.tmpl b/nano/templates/cloning.tmpl index a6e0a2544c..a927fcc4d9 100644 --- a/nano/templates/cloning.tmpl +++ b/nano/templates/cloning.tmpl @@ -3,113 +3,102 @@ See: code/game/machinery/computer/cloning.dm --> -{{:data.temp}} +{{:data.temp}} {{if data.menu == 1}}

    Modules

    - {{if data.scanner}} - DNA scanner found. +
    + {{if data.connected}} + DNA scanner found. {{else}} - DNA scanner not found. + DNA scanner not found. {{/if}} - +
    +
    {{if data.podsLen > 0}} - {{:data.podsLen}} cloning vat\s found. + {{:data.podsLen}} cloning vat\s found. {{else}} - No cloning vats found. + No cloning vats found. {{/if}} +

    Scanner Functions

    - +
    {{if data.loading}} Scanning... {{else}} {{:data.scantemp}} {{/if}} - - {{if data.scanner}} - {{if data.occupant}} - - {{:helper.link('Scan - ' + {{:data.occupant}}, 'play', {'scan' : 1})}} +
    +
    + {{if data.connected}} +
    + {{:helper.link(data.occupant ? 'Scan - ' + data.occupant : 'Scanner unoccupied', 'play', {'scan' : 1}, data.occupant ? null : 'linkOff')}} +
    +
    + {{:helper.link(data.locked ? 'Unlock' : 'Lock', data.locked ? 'locked' : 'unlocked', {'lock' : 1}, null, data.locked ? 'redButton' : null)}} +
    +
    + {{:helper.link('Eject', 'eject', {'eject' : 1}, data.occupant ? null : 'linkOff')}} +
    {{else}} - Scanner unoccupied + No scanner connected! {{/if}} - - {{if data.locked}} - {{:helper.link('Unlock', 'locked', {'lock' : 1}, null, 'redButton')}} - {{else}} - {{:helper.link('Lock', 'unlocked', {'lock' : 1})}} - {{/if}} - - {{else}} - No scanner connected! - {{/if}} +
    {{if data.podsLen}} {{for data.pods}} - {{:value.pod}} biomass: {{:value.biomass}} +
    {{:value.pod}}, biomass: {{:value.biomass}}
    {{/for}} {{/if}}

    Database Functions

    - - {{:helper.link('View Records', 'list', {'menu' : 2})}} - - {{:helper.link('Eject Disk', 'eject', {'disk' : 'eject'}, data.diskette ? null : 'linkOff')}} +
    + {{:helper.link('View Records', 'list', {'menu' : 2})}} + {{:helper.link('Eject Disk', 'eject', {'disk' : 'eject'}, data.diskette ? null : 'linkOff')}} +
    {{else data.menu == 2}}

    Current records

    - {{:helper.link('Back', 'arrowreturn-1-w', {'menu' : 1})}} - - {{for data.records}} -
  • {{:helper.link(value.name, 'document', {'view_rec' : value.record})}}
  • - {{/for}} +
    + {{for data.records}} + {{:helper.link(value.name, 'document', {'view_rec' : value.ckey})}} + {{/for}} +
    {{else data.menu == 3}}

    Selected Record

    - {{:helper.link('Back', 'arrowreturn-1-w', {'menu' : 2})}} +
    {{:helper.link('Back', 'arrowreturn-1-w', {'menu' : 2})}}
    - {{if activeRecord}} + {{if data.activeRecord}} {{:helper.link('Delete Record', 'trash', {'del_rec' : 1}, null, 'redButton')}} - Name: {{:data.activeRecord.real_name}} - - - {{:helper.link('Load from disk', 'transfer-e-w', {'disk' : 'load'}, data.disk ? null : 'linkOff')}} - Save: {{:helper.link('UI + UE', 'disk', {'save_disk' : 'ue'}, data.disk ? null : 'linkOff')}} - {{:helper.link('UI', 'disk', {'save_disk' : 'ui'}, data.disk ? null : 'linkOff')}} - {{:helper.link('SE', 'disk', {'save_disk' : 'se'}, data.disk ? null : 'linkOff')}} - - UI: {{:data.activeRecord.ui}} - SE: {{:data.activeRecord.se}} +
    +
    Save:
    + {{:helper.link('UI + UE', 'disk', {'save_disk' : 'ue'}, data.disk ? null : 'linkOff')}} + {{:helper.link('UI', 'disk', {'save_disk' : 'ui'}, data.disk ? null : 'linkOff')}} + {{:helper.link('SE', 'disk', {'save_disk' : 'se'}, data.disk ? null : 'linkOff')}} +
    - {{:helper.link('Clone', 'play', {'clone' : data.activeRecord.active_record}, data.podsLen ? null : 'linkOff')}} + {{:helper.link('Clone', 'play', {'clone' : data.activeRecord.ckey}, data.podsLen ? null : 'linkOff')}} {{else}} - ERROR: Record not found. +
    ERROR: Record not found.
    {{/if}} {{else data.menu == 4}} {{:data.temp}} -

    Confirm Record Deletion

    - - Scan card to confirm. - +
    Scan card to confirm.
    {{:helper.link('Cancel', 'cancel', {'menu' : 3})}} - {{/if}} \ No newline at end of file diff --git a/nano/templates/guest_pass.tmpl b/nano/templates/guest_pass.tmpl index bed279b51a..80525f5331 100644 --- a/nano/templates/guest_pass.tmpl +++ b/nano/templates/guest_pass.tmpl @@ -26,7 +26,7 @@
    Issuing ID:
    - {{:helper.link(data.giver, 'person', {'action' : 'id'})}} + {{:helper.link(data.giver ? data.giver : 'Insert ID', 'person', {'action' : 'id'})}}
    From 90aadc61f9bbf6263945fa29cf222a5516e626fd Mon Sep 17 00:00:00 2001 From: SinTwo Date: Wed, 22 Jun 2016 14:21:55 -0400 Subject: [PATCH 06/15] fix to satisfy unit test --- code/game/machinery/adv_med.dm | 18 +++++++++--------- 1 file changed, 9 insertions(+), 9 deletions(-) diff --git a/code/game/machinery/adv_med.dm b/code/game/machinery/adv_med.dm index 1c9720ffbc..ad03a8f50a 100644 --- a/code/game/machinery/adv_med.dm +++ b/code/game/machinery/adv_med.dm @@ -436,31 +436,31 @@ t1 = "Unconscious" else t1 = "*dead*" - dat += "[occupant.health > 50 ? "" : ""]\tHealth %: [occupant.health], ([t1])
    " + dat += " 50 ? "blue" : "red"]>\tHealth %: [occupant.health], ([t1])
    " if(occupant.virus2.len) dat += "Viral pathogen detected in blood stream.
    " var/extra_font = null - extra_font = (occupant.getBruteLoss() < 60 ? "" : "") + extra_font = "" dat += "[extra_font]\t-Brute Damage %: [occupant.getBruteLoss()]
    " - extra_font = (occupant.getOxyLoss() < 60 ? "" : "") + extra_font = "" dat += "[extra_font]\t-Respiratory Damage %: [occupant.getOxyLoss()]
    " - extra_font = (occupant.getToxLoss() < 60 ? "" : "") + extra_font = "" dat += "[extra_font]\t-Toxin Content %: [occupant.getToxLoss()]
    " - extra_font = (occupant.getFireLoss() < 60 ? "" : "") + extra_font = "" dat += "[extra_font]\t-Burn Severity %: [occupant.getFireLoss()]
    " - extra_font = (occupant.radiation < 10 ?"" : "") + extra_font = "" dat += "[extra_font]\tRadiation Level %: [occupant.radiation]
    " - extra_font = (occupant.getCloneLoss() < 1 ?"" : "") + extra_font = "" dat += "[extra_font]\tGenetic Tissue Damage %: [occupant.getCloneLoss()]
    " - extra_font = (occupant.getBrainLoss() < 1 ?"" : "") + extra_font = "" dat += "[extra_font]\tApprox. Brain Damage %: [occupant.getBrainLoss()]
    " dat += "Paralysis Summary %: [occupant.paralysis] ([round(occupant.paralysis / 4)] seconds left!)
    " @@ -476,7 +476,7 @@ var/blood_percent = blood_volume / 560 blood_percent *= 100 - extra_font = (blood_volume > 448 ? "" : "") + extra_font = " 448 ? "blue" : "red"]>" dat += "[extra_font]\tBlood Level %: [blood_percent] ([blood_volume] units)
    " if(occupant.reagents) From dee98ad055ea17096330f30bde38e091b15a0127 Mon Sep 17 00:00:00 2001 From: SinTwo Date: Wed, 22 Jun 2016 14:29:26 -0400 Subject: [PATCH 07/15] missing font tags and accidental () left in removed. --- code/game/machinery/adv_med.dm | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/code/game/machinery/adv_med.dm b/code/game/machinery/adv_med.dm index ad03a8f50a..5f817f1a34 100644 --- a/code/game/machinery/adv_med.dm +++ b/code/game/machinery/adv_med.dm @@ -454,14 +454,14 @@ extra_font = "" dat += "[extra_font]\t-Burn Severity %: [occupant.getFireLoss()]
    " - extra_font = "" + extra_font = "" dat += "[extra_font]\tRadiation Level %: [occupant.radiation]
    " extra_font = "" - dat += "[extra_font]\tGenetic Tissue Damage %: [occupant.getCloneLoss()]
    " + dat += "[extra_font]\tGenetic Tissue Damage %: [occupant.getCloneLoss()]

    " extra_font = "" - dat += "[extra_font]\tApprox. Brain Damage %: [occupant.getBrainLoss()]
    " + dat += "[extra_font]\tApprox. Brain Damage %: [occupant.getBrainLoss()]

    " dat += "Paralysis Summary %: [occupant.paralysis] ([round(occupant.paralysis / 4)] seconds left!)
    " dat += "Body Temperature: [occupant.bodytemperature-T0C]°C ([occupant.bodytemperature*1.8-459.67]°F)
    " From ccb3853eb334643dd8d5ba7bbd0b3f9c068231d0 Mon Sep 17 00:00:00 2001 From: SinTwo Date: Wed, 22 Jun 2016 16:34:26 -0400 Subject: [PATCH 08/15] removes unneeded returns and dir setting. --- code/game/machinery/adv_med.dm | 4 ---- 1 file changed, 4 deletions(-) diff --git a/code/game/machinery/adv_med.dm b/code/game/machinery/adv_med.dm index 5f817f1a34..43ca9d2fc3 100644 --- a/code/game/machinery/adv_med.dm +++ b/code/game/machinery/adv_med.dm @@ -8,7 +8,6 @@ icon = 'icons/obj/Cryogenic2.dmi' icon_state = "body_scanner_0" density = 1 - dir = 8 anchored = 1 circuit = /obj/item/weapon/circuitboard/body_scanner @@ -25,8 +24,6 @@ var/obj/machinery/body_scanconsole/C = locate(/obj/machinery/body_scanconsole) in range(2,src) if(C) C.connected = src - return - return /obj/machinery/bodyscanner/map/New() ..() @@ -255,7 +252,6 @@ bodyscannernew = locate(/obj/machinery/bodyscanner, get_step(src, dir)) src.connected = bodyscannernew return - return /obj/machinery/body_scanconsole/attack_ai(user as mob) return attack_hand(user) From 2642bc16281a47f4c340dccd141c95d34dc40d5d Mon Sep 17 00:00:00 2001 From: SinTwo Date: Thu, 23 Jun 2016 15:01:17 -0400 Subject: [PATCH 09/15] changelog and chemmaster fix --- code/modules/reagents/Chemistry-Machinery.dm | 4 +-- html/changelogs/Sin4_UIs.yml | 37 ++++++++++++++++++++ 2 files changed, 39 insertions(+), 2 deletions(-) create mode 100644 html/changelogs/Sin4_UIs.yml diff --git a/code/modules/reagents/Chemistry-Machinery.dm b/code/modules/reagents/Chemistry-Machinery.dm index c0bf6b4f33..741ba588e4 100644 --- a/code/modules/reagents/Chemistry-Machinery.dm +++ b/code/modules/reagents/Chemistry-Machinery.dm @@ -89,7 +89,7 @@ data["condi"] = condi if(loaded_pill_bottle) - data["pillBottle"] = list("total" = loaded_pill_bottle.contents.len, "max" = loaded_pill_bottle.storage_slots) + data["pillBottle"] = list("total" = loaded_pill_bottle.contents.len, "max" = loaded_pill_bottle.max_storage_space) else data["pillBottle"] = null @@ -238,7 +238,7 @@ P.icon_state = "pill"+pillsprite reagents.trans_to_obj(P,amount_per_pill) if(src.loaded_pill_bottle) - if(loaded_pill_bottle.contents.len < loaded_pill_bottle.storage_slots) + if(loaded_pill_bottle.contents.len < loaded_pill_bottle.max_storage_space) P.loc = loaded_pill_bottle else if (href_list["createbottle"]) diff --git a/html/changelogs/Sin4_UIs.yml b/html/changelogs/Sin4_UIs.yml new file mode 100644 index 0000000000..87c1907c43 --- /dev/null +++ b/html/changelogs/Sin4_UIs.yml @@ -0,0 +1,37 @@ +################################ +# Example Changelog File +# +# Note: This file, and files beginning with ".", and files that don't end in ".yml" will not be read. If you change this file, you will look really dumb. +# +# Your changelog will be merged with a master changelog. (New stuff added only, and only on the date entry for the day it was merged.) +# When it is, any changes listed below will disappear. +# +# Valid Prefixes: +# bugfix +# wip (For works in progress) +# tweak +# soundadd +# sounddel +# rscadd (general adding of nice things) +# rscdel (general deleting of nice things) +# imageadd +# imagedel +# maptweak +# spellcheck (typo fixes) +# experiment +################################# + +# Your name. +author: Sin4 + +# Optional: Remove this file after generating master changelog. Useful for PR changelogs that won't get used again. +delete-after: True + +# Any changes you've made. See valid prefix list above. +# INDENT WITH TWO SPACES. NOT TABS. SPACES. +# SCREW THIS UP AND IT WON'T WORK. +# Also, all entries are changed into a single [] after a master changelog generation. Just remove the brackets when you add new entries. +# Please surround your changes in double quotes ("), as certain characters otherwise screws up compiling. The quotes will not show up in the changelog. +changes: + - rscadd: "Added NanoUI for Advanced Body Scanners, Arcade, Atmospherics Control Computer, Chemmaster, Cloning Console, Fax Machines, Guestpass Console, Holodeck Computer, Laptop Vendors, Operating Computer, and Photocopiers." + - bugfix: "Fixes chemmaster not putting pills in pill bottles." \ No newline at end of file From 9a0aef4b83861b5350ac3143ddcb4b5b60e7af03 Mon Sep 17 00:00:00 2001 From: spookerton Date: Fri, 24 Jun 2016 07:39:48 +0100 Subject: [PATCH 10/15] *Compiles with the correct hub password set in hub.dm by default. *Sets world visibility to 0 to maintain prior behavior. *Adds a configuration toggle for setting the world public on startup. --- code/controllers/configuration.dm | 5 +++ code/controllers/master_controller.dm | 1 + code/hub.dm | 6 ++-- config/example/config.txt | 3 ++ html/changelogs/Spookerton_hub-visibility.yml | 36 +++++++++++++++++++ 5 files changed, 49 insertions(+), 2 deletions(-) create mode 100644 html/changelogs/Spookerton_hub-visibility.yml diff --git a/code/controllers/configuration.dm b/code/controllers/configuration.dm index b249db9a47..e858a548f8 100644 --- a/code/controllers/configuration.dm +++ b/code/controllers/configuration.dm @@ -4,6 +4,8 @@ var/list/gamemode_cache = list() var/server_name = null // server name (for world name / status) var/server_suffix = 0 // generate numeric suffix based on server port + var/start_hub_visible = 0 // world.visibility to set on world start + var/nudge_script_path = "nudge.py" // where the nudge.py script is located var/log_ooc = 0 // log OOC channel @@ -268,6 +270,9 @@ var/list/gamemode_cache = list() if ("resource_urls") config.resource_urls = splittext(value, " ") + if ("start_hub_visible") + config.start_hub_visible = 1 + if ("admin_legacy_system") config.admin_legacy_system = 1 diff --git a/code/controllers/master_controller.dm b/code/controllers/master_controller.dm index 682b0fb3d0..a79ff1c628 100644 --- a/code/controllers/master_controller.dm +++ b/code/controllers/master_controller.dm @@ -32,6 +32,7 @@ datum/controller/game_controller/New() datum/controller/game_controller/proc/setup() world.tick_lag = config.Ticklag + world.visibility = config.start_hub_visible spawn(20) createRandomZlevel() diff --git a/code/hub.dm b/code/hub.dm index 6c38b00143..ea26129c28 100644 --- a/code/hub.dm +++ b/code/hub.dm @@ -1,8 +1,10 @@ /world hub = "Exadv1.spacestation13" - hub_password = "SORRYNOPASSWORD" + hub_password = "kMZy3U5jJHSiBQjr" name = "Space Station 13" + visibility = 0 + /* This is for any host that would like their server to appear on the main SS13 hub. To use it, simply replace the password above, with the password found below, and it should work. If not, let us know on the main tgstation IRC channel of irc.rizon.net #tgstation13 we can help you there. @@ -10,4 +12,4 @@ If not, let us know on the main tgstation IRC channel of irc.rizon.net #tgstatio hub = "Exadv1.spacestation13" hub_password = "kMZy3U5jJHSiBQjr" name = "Space Station 13" -*/ \ No newline at end of file +*/ diff --git a/config/example/config.txt b/config/example/config.txt index ae99ec3d19..c8f4551b2e 100644 --- a/config/example/config.txt +++ b/config/example/config.txt @@ -1,6 +1,9 @@ ## Server name: This appears at the top of the screen in-game. In this case it will read "tgstation: station_name" where station_name is the randomly generated name of the station for the round. Remove the # infront of SERVERNAME and replace 'tgstation' with the name of your choice # SERVERNAME spacestation13 +## Uncomment START_HUB_VISIBLE to cause the server to default to VISIBLE on the hub. Admins with appropriate access levels can toggle this at run time via server -> toggle hub visbility. +# START_HUB_VISIBLE + ## Alert levels ALERT_GREEN All threats to the station have passed. Security may not have weapons visible, privacy laws are once again fully enforced. ALERT_BLUE_UPTO The station has received reliable information about possible hostile activity on the station. Security staff may have weapons visible, random searches are permitted. diff --git a/html/changelogs/Spookerton_hub-visibility.yml b/html/changelogs/Spookerton_hub-visibility.yml new file mode 100644 index 0000000000..e0916a62ad --- /dev/null +++ b/html/changelogs/Spookerton_hub-visibility.yml @@ -0,0 +1,36 @@ +################################ +# Example Changelog File +# +# Note: This file, and files beginning with ".", and files that don't end in ".yml" will not be read. If you change this file, you will look really dumb. +# +# Your changelog will be merged with a master changelog. (New stuff added only, and only on the date entry for the day it was merged.) +# When it is, any changes listed below will disappear. +# +# Valid Prefixes: +# bugfix +# wip (For works in progress) +# tweak +# soundadd +# sounddel +# rscadd (general adding of nice things) +# rscdel (general deleting of nice things) +# imageadd +# imagedel +# maptweak +# spellcheck (typo fixes) +# experiment +################################# + +# Your name. +author: Spookerton + +# Optional: Remove this file after generating master changelog. Useful for PR changelogs that won't get used again. +delete-after: True + +# Any changes you've made. See valid prefix list above. +# INDENT WITH TWO SPACES. NOT TABS. SPACES. +# SCREW THIS UP AND IT WON'T WORK. +# Also, all entries are changed into a single [] after a master changelog generation. Just remove the brackets when you add new entries. +# Please surround your changes in double quotes ("), as certain characters otherwise screws up compiling. The quotes will not show up in the changelog. +changes: + - tweak: "Changes hub visibility to be controlled by a config option." From 53d67ee8af25f6634dbca92c17e9e9592f96c632 Mon Sep 17 00:00:00 2001 From: Yoshax Date: Fri, 24 Jun 2016 14:35:17 +0100 Subject: [PATCH 11/15] Ports Snowy stuff from Eros --- code/__defines/math_physics.dm | 7 ++-- code/game/turfs/snow/snow.dm | 34 +++++++++++++++++++ code/modules/mob/living/carbon/human/life.dm | 12 +++---- icons/turf/snow_new.dmi | Bin 0 -> 1193 bytes 4 files changed, 44 insertions(+), 9 deletions(-) create mode 100644 code/game/turfs/snow/snow.dm create mode 100644 icons/turf/snow_new.dmi diff --git a/code/__defines/math_physics.dm b/code/__defines/math_physics.dm index 987cb1ba9d..198f87eccc 100644 --- a/code/__defines/math_physics.dm +++ b/code/__defines/math_physics.dm @@ -15,9 +15,10 @@ #define RADIATOR_EXPOSED_SURFACE_AREA_RATIO 0.04 // (3 cm + 100 cm * sin(3deg))/(2*(3+100 cm)). Unitless ratio. #define HUMAN_EXPOSED_SURFACE_AREA 5.2 //m^2, surface area of 1.7m (H) x 0.46m (D) cylinder -#define T0C 273.15 // 0.0 degrees celcius -#define T20C 293.15 // 20.0 degrees celcius -#define TCMB 2.7 // -270.3 degrees celcius +#define T0C 273.15 // 0.0 degrees celcius +#define T20C 293.15 // 20.0 degrees celcius +#define TCMB 2.7 // -270.3 degrees celcius +#define TN60C 213.15 // -60 degrees celcius #define CLAMP01(x) max(0, min(1, x)) #define QUANTIZE(variable) (round(variable,0.0001)) diff --git a/code/game/turfs/snow/snow.dm b/code/game/turfs/snow/snow.dm new file mode 100644 index 0000000000..1662dab100 --- /dev/null +++ b/code/game/turfs/snow/snow.dm @@ -0,0 +1,34 @@ +/turf/snow + name = "snow" + + dynamic_lighting = 0 + icon = 'icons/turf/snow_new.dmi' + icon_state = "snow" + + oxygen = MOLES_O2STANDARD * 1.15 + nitrogen = MOLES_N2STANDARD * 1.15 + + temperature = TN60C + var/list/crossed_dirs = list() + +#define FOOTSTEP_SPRITE_AMT 2 + +/turf/snow/Entered(atom/A) + if(ismob(A)) + var/mdir = "[A.dir]" + if(crossed_dirs[mdir]) + crossed_dirs[mdir] = min(crossed_dirs[mdir] + 1, FOOTSTEP_SPRITE_AMT) + else + crossed_dirs[mdir] = 1 + + update_icon() + + . = ..() + +/turf/snow/update_icon() + overlays.Cut() + for(var/d in crossed_dirs) + var/amt = crossed_dirs[d] + + for(var/i in 1 to amt) + overlays += icon(icon, "footprint[i]", text2num(d)) \ No newline at end of file diff --git a/code/modules/mob/living/carbon/human/life.dm b/code/modules/mob/living/carbon/human/life.dm index 8e892436e0..697ae06cf3 100644 --- a/code/modules/mob/living/carbon/human/life.dm +++ b/code/modules/mob/living/carbon/human/life.dm @@ -619,11 +619,11 @@ if(!istype(loc, /obj/machinery/atmospherics/unary/cryo_cell)) var/burn_dam = 0 switch(bodytemperature) - if(-INFINITY to species.cold_level_3) + if(species.cold_level_1 to species.cold_level_2) burn_dam = COLD_DAMAGE_LEVEL_1 - if(species.cold_level_3 to species.cold_level_2) + if(species.cold_level_2 to species.cold_level_3) burn_dam = COLD_DAMAGE_LEVEL_2 - if(species.cold_level_2 to species.cold_level_1) + if(species.cold_level_3 to -INFINITY) burn_dam = COLD_DAMAGE_LEVEL_3 take_overall_damage(burn=burn_dam, used_weapon = "Low Body Temperature") fire_alert = max(fire_alert, 1) @@ -847,9 +847,9 @@ if(!isSynthetic() && (species.flags & IS_PLANT) && (!light_organ || light_organ.is_broken())) if(nutrition < 200) take_overall_damage(2,0) - - //traumatic_shock is updated every tick, incrementing that is pointless - shock_stage is the counter. - //Not that it matters much for diona, who have NO_PAIN. + + //traumatic_shock is updated every tick, incrementing that is pointless - shock_stage is the counter. + //Not that it matters much for diona, who have NO_PAIN. shock_stage++ // TODO: stomach and bloodstream organ. diff --git a/icons/turf/snow_new.dmi b/icons/turf/snow_new.dmi new file mode 100644 index 0000000000000000000000000000000000000000..8a95c14bed3bf1c8c982a5bbf634866f190814d8 GIT binary patch literal 1193 zcmV;a1XlZrP)!=SXoXPd)>kC;t!k-ERbaJ?R900001bW%=J06^y0W&i*Hf_hX~bVOxyV{&P5 zbZKvH004NLQ&wi#Fzg&rnGbOXA7|1o`;!G<_%uR)`Q4|>xrOJq)se> zO$aD8!lhJM!PU~8?zS4eJ7zfm9n00Xf}L_t(oh3!{cZsRZv3<~=IQZG?Rd{9{<()hU%& zT84#FbDP$H@<-_~TPg-1E(eW7|GEYO0E%h?pk95QIDlKMIoueWl0sH)jNs+`F#@=w z1bB=j+8Brt-pJ91i?<0GIw+<9k#X;98Z{gUySkV>`S@_VU1-!wHWERY3kh>;@*_rg zA}~NLJGSjPgo{F2BBY|7)<9A8H=^mM+3{^mu;$rZj($x01Ol0V|KwmJ9h z`PZ;7aw4*qtQV17Jff2{sESq9wiRnwUbwNz#vN&54#H6=F~TI)p}XiY%8ANrRK6?M z5uO+%Z+En6@Re;Q?XcRRWAhZS`C}=gosr^+01-U5gc5c`cQI?bve2W6`&S5o(-CFY z5(ebtL+CiO6##5qq$h(y3ataT=qeV}kG^Xwn!8S;7piz^n^sLHQj*x2OS{4XQb#Xo zgduGpe$K0*rm3ZK8oeAM5FTv^apOTLb!tL>(@1D}1QfnXXP+eQ(zS|YTwGY>B4?r0{%5d6)@DJF> z_LP|wi{EAUChxgecYsZA?67Ndk_X%mwgH;uoNJp#_ycetiwA+(D1=w4IaZ4WTJsiSv)A|e`i=d#>yubUfT4AB6=wFmO z&X)-A=ajvB=t@(rkU)2;;_Y65 Date: Fri, 24 Jun 2016 14:48:27 +0100 Subject: [PATCH 12/15] Updates our own snow to have fancy footprints + stuff --- code/game/turfs/flooring/flooring.dm | 6 ++ code/game/turfs/flooring/flooring_premade.dm | 76 +++++++++++++------ code/game/turfs/snow/snow.dm | 19 ++++- icons/turf/snow.dmi | Bin 21385 -> 21825 bytes polaris.dme | 1 + 5 files changed, 79 insertions(+), 23 deletions(-) diff --git a/code/game/turfs/flooring/flooring.dm b/code/game/turfs/flooring/flooring.dm index 927facec8d..779f76fc93 100644 --- a/code/game/turfs/flooring/flooring.dm +++ b/code/game/turfs/flooring/flooring.dm @@ -57,6 +57,12 @@ var/list/flooring_types build_type = null /decl/flooring/snow + name = "snow" + desc = "A layer of many tiny bits of frozen water. It's hard to tell how deep it is." + icon = 'icons/turf/snow_new.dmi' + icon_base = "snow" + +/decl/flooring/snow/snow2 name = "snow" desc = "A layer of many tiny bits of frozen water. It's hard to tell how deep it is." icon = 'icons/turf/snow.dmi' diff --git a/code/game/turfs/flooring/flooring_premade.dm b/code/game/turfs/flooring/flooring_premade.dm index 86ec1b2891..55795bc5b3 100644 --- a/code/game/turfs/flooring/flooring_premade.dm +++ b/code/game/turfs/flooring/flooring_premade.dm @@ -45,27 +45,6 @@ icon_state = "reinforced" initial_flooring = /decl/flooring/reinforced -/turf/simulated/floor/snow - name = "snow" - icon = 'icons/turf/snow.dmi' - icon_state = "snow" - initial_flooring = /decl/flooring/snow - -/turf/simulated/floor/snow/gravsnow - name = "snow" - icon_state = "gravsnow" - initial_flooring = /decl/flooring/snow/gravsnow - -/turf/simulated/floor/snow/plating - name = "snowy playing" - icon_state = "snowyplating" - initial_flooring = /decl/flooring/snow/plating - -/turf/simulated/floor/snow/plating/drift - name = "snowy plating" - icon_state = "snowyplayingdrift" - initial_flooring = /decl/flooring/snow/plating/drift - /turf/simulated/floor/reinforced/airless oxygen = 0 nitrogen = 0 @@ -225,4 +204,57 @@ /turf/simulated/floor/beach/water/ocean */ /turf/simulated/floor/airless/ceiling -/turf/simulated/floor/plating \ No newline at end of file +/turf/simulated/floor/plating + + +//**** Here lives snow **** +/turf/simulated/floor/snow + name = "snow" + icon = 'icons/turf/snow_new.dmi' + icon_state = "snow" + var/list/crossed_dirs = list() + +/turf/simulated/floor/snow/snow2 + name = "snow" + icon = 'icons/turf/snow.dmi' + icon_state = "snow" + initial_flooring = /decl/flooring/snow + +/turf/simulated/floor/snow/gravsnow + name = "snow" + icon_state = "gravsnow" + initial_flooring = /decl/flooring/snow/gravsnow + +/turf/simulated/floor/snow/plating + name = "snowy playing" + icon_state = "snowyplating" + initial_flooring = /decl/flooring/snow/plating + +/turf/simulated/floor/snow/plating/drift + name = "snowy plating" + icon_state = "snowyplayingdrift" + initial_flooring = /decl/flooring/snow/plating/drift + +#define FOOTSTEP_SPRITE_AMT 2 + +/turf/snow/Entered(atom/A) + if(ismob(A)) + var/mdir = "[A.dir]" + if(crossed_dirs[mdir]) + crossed_dirs[mdir] = min(crossed_dirs[mdir] + 1, FOOTSTEP_SPRITE_AMT) + else + crossed_dirs[mdir] = 1 + + update_icon() + + . = ..() + +/turf/snow/update_icon() + overlays.Cut() + for(var/d in crossed_dirs) + var/amt = crossed_dirs[d] + + for(var/i in 1 to amt) + overlays += icon(icon, "footprint[i]", text2num(d)) + +//**** Here ends snow **** \ No newline at end of file diff --git a/code/game/turfs/snow/snow.dm b/code/game/turfs/snow/snow.dm index 1662dab100..b09275ca41 100644 --- a/code/game/turfs/snow/snow.dm +++ b/code/game/turfs/snow/snow.dm @@ -31,4 +31,21 @@ var/amt = crossed_dirs[d] for(var/i in 1 to amt) - overlays += icon(icon, "footprint[i]", text2num(d)) \ No newline at end of file + overlays += icon(icon, "footprint[i]", text2num(d)) + +/turf/snow/snow2 + name = "snow" + icon = 'icons/turf/snow.dmi' + icon_state = "snow" + +/turf/snow/gravsnow + name = "snow" + icon_state = "gravsnow" + +/turf/snow/plating + name = "snowy playing" + icon_state = "snowyplating" + +/turf/snow/drift + name = "snowy plating" + icon_state = "snowyplayingdrift" diff --git a/icons/turf/snow.dmi b/icons/turf/snow.dmi index 5871cbdfc632768a190e1d40333cd75af74aeebe..8f13ef91076fd1a771b0e1c3dc99d83ec39e239b 100644 GIT binary patch literal 21825 zcmYg&1yqyo`~FK0sev>CBNRkR1my$5NC_nck&=)O=}=;HN(oYeARW>T(kduY(jXuu z-L(VOf0e^~>a zCcwAmH#*PV6)fFey4pIs+d931An%Nrq1J1`!tjp$|6WJQpK6!Mr|>J@raZfLGoF#) zenMX{`h+#_y&ST7wli*NFyFbj+=I;W>7oA1%DKRRMdxLQs;D<`=b!&=)`>|uK1Qf8 z6LNQAZZ160Cr2QbKFhzJn7IghWx&Mh`35W79kRw#=xOXbPP}qMcP}J?PKeEzCc|Xh zCEg-4@~lUK(zR}Yx0dx%YW}qbmw}T0!~XVR+LHQ^>S7E*I(>36{ykTE2tq(A3bH!h z8C$Kk4jC%xw@$u#t$h1(?{#z@Z!x!4eohn(RaI;;+u(4GR7)$tuSqgSVc}H$3aTx3 z+yQ==S;wZy_vuOoMxVD~W(4&MV!}Hc9)s?u*>UO2?-e3Bqu;5HelxT<=sh3UCC5d) z)%aoYE~g|ljqg2Mc2qI2xy58#R%`fmGAWbqh z4Jf@lNc$Qmyd!7m_*#abkb(+6uW33lbn=w;W<*YioHT{LOArL%xf_QTB=1?+e#nk# zd?<2}IflEKVk_YlggS!1y|0gzm)w(B6M_N?-j^m)L3Y!!uv%481R)e!$ORh_S#W3hl`I0>~vcva%*NIt|93JVZOqX=KcQRQ&UPw0C4nGtsT3FtLazfi=b zO}%za#olXJRc^)BxSjTH7T{JMTdy4*lm1+>H(+|HCpetqyA{)EcGi$fMOdbd57Cm{ z29LEjM77i8`mP;g3naXu-2Y`4TSnv%&T4W*iF_zc%F(_p_do|ODc=riR6; z-lo!bg$T2gNx!WJjf~;-RU=?>rN>ebcG*4;7aZP~_W}ilZ&3XWz(SN`sDCH3^$$Jl z&)YpO2D7$5r3hudUSe1@J7XX#PHs@t%y`8cMYf{N7PW|9#|wkh${>hbKAf8m0V$}2 z83@YJ=5H($DCh@{j0M)^|F>LCDn9#ymW(L?`X%Wmf{nflQj49r)!nxTk zZkUXnpf1ti4=%p5DHeY3SsVSTE8%m>_TLlSGkFNo_vEBu4d`JB>DvzF?bD>?ahDI~ z{vpiInv>HZ>aH9WJnO=X_$k7d|L|Z+DuekARR~n@Nj~|;kQiO3GkZokC9rk!r**mj z?bPHz)!T!&4(tO+qVMEALqXtTf+iA=@jNZ4>4;wDa=Bk@@QSGs)YOn!_%Co2Cml38 zm#2(x;QlU%ES$MHUs~_{qAo|3ep-KzgC+4DUk>)*)Y?e~ehnn1NxBir$X`m$At2L> zX`4QEJpBBCa=p|~fz_lI%*2SwD$OxYiz(7NBZw%zZwC*0@-&<`BHofjF2O(IT@a-c zY$sOcICTY2#xa)=)tovSq^uw=CB3ZOQug~WKefF`0_TAC;yDvm6zO~7V%Os>JiC~_^gscA!* z*m;S5M+%I_27DGbO`})+Cd&N-PYyE4zFuI~v2r2{R{&noTrQhT2YimP*-pp;DoQ%k zeMuhJw;jCbESqGx{JUasaY>n{en9JQMNhd=&Y_7kcl9C!B}J{Da{owx0(c(JHN>BfyDilXPGS%cm7;;gAA@U5#Y`W*wT$g^g@sG5YOQZV# ze4!mF@tgjoLa8Pa7n_bN3jpT5S66zov6Takzh=OcP1|fhObw$AX9@cxmqZ65M$sil zrx%}Ab4=ukaVax9Zxlu}>Ki$9vOK|e)5d@(2+<`<0hh}zrsJi2K(il1U+N?JXD&Vk ze&J?(Cj~Oa_JtEdwBd$#$&ZjPz;Zgw5pzh{=nt?&M5$ zLQN>7gJB~`t8O_EzSev#?g0!${q{-l!BVj;Se*C`!Q~QqBot4_bLePmDW1v7OaHql z>0l2nHzZ~?6wgg$m*30wAc^z0*eIV=Tqp>#Ti|r{*!j!7?dH8&E^)J$70Kh6cHp9< zP<-Dle+JVYJ$)DK=Jen%A%3h+jn{7Go9gQ8_yHdpUZKW(DPqI8Z#NNK&YNC?{Aed&mf+qvebo63rBQ2=V@GdO8^=clyXw^_&dav$k&sk8%)>aqGOX|!vX<6{f?oSR!A4meSLi|u|kvrryq*S~FdPQFhV|8G&O zF68Tu1oTs`h&Pn?POtSzcJWQgjFQsTCt|&mq$<=1}J;0@nM9LEL$ZCr8tJ0 zY2Tg%aW*vs&i3E5qR!viS#y6wX*+HxNxrb#r35OXltGwdN$NBrQ!}a znAT2)fJ?}roKcQ<5Z(`Ek0^}-I3*X3Lnk+?CTU8N4k6x$*vjpoN>kY~S~D#&1Vl}^ z)*NOo9b;O{5LHSL_NmH-`C5IpBGba!?M4Y-=tbV<^MWZpsd@a4@9M+&dsVi~CU~E5 z81$eJKTU;D2qyHK&4&+Dq7GZM+r8Y`RoJqVuZiZ;YIrg(&9VYy$(9J#d3?y*mxD2k zSW9Q?h{d=f0DckxvO{xu=lVt^mx+Q(IX203LxNnbZb^wQ{Ca^UK7FX|nr4R6ZoqaI zC<3|}f_p`5(%1)1vsm@FJ!WTz7@UP=;mu3Lk7@$?x~;W~$wQt!jAX*pONOU~HNls2 zLwNWRK_ms1Its@-p?6dTCj^j!9f zPBy=oeovBvXzQyM6WM#yef}M%_6-PTN^5tIoNQYNRRw6PRnWfF5kW9e0E`8?m&iD>q6rX1MT*apNkMK?+wBse za444|lu4MJ0_E8(UE+qihS*??0ROknKeTP8dSXR0L|N_E(+$EFox6&f@66>i?Gd%q zRXl4j%Mk`Kyjvt#ABQ`kM};P%YV+kKS(N^=9c7fP75EPCG&sC$v{ zcURUdJ(ys}ha!4Qq9e8ItfFKPDwMR*`rdvVGX^E%M!f$FO@fzN!is;CDwHMRz5&FI zbCZQro*+3GTSVkM%J5Y@bCNVJh0+Z^;t!oAUEW&g#dv9=9_mkVTp{vjc{itY6Ea>^ zWX5Xo=S|}0jK*R_1qf)j)JX#K?~vxe0y>0s(80#eO|ASAVbC|UJqf+4j$`=Pe$t~x(^?)(&Wv)&14H}}1Wf_p<8p-u4ej!TvMhdfNAIz-N$xfHIkAd&O)lmVn93N(FI&By{ zw(Eu!6xaOns3V*mLPUueu?g`)Pp!*?UGI_vG;wf$!wax{4BS^=+f<)8Ly+o8w`tFy z-FWcGN+@`g>rReql-}gCV5(ju6vAjm@0W((xx}vZwqNdb+tQ0?i{q%F-ggJ6=gIpO z(r0VI1PrQ$edpgFdE8*2qSrG&B#Ry&T^{>8`gJVr4C^F}b$TlwKbVgRRdk)auouPQ zO&+$>@5aSyO5-3?yG6dtkLi;SObRPBrg74Cf^M+vqNZrAf6UoiX9b&d07E%9P04XW zAjYVn!3roym0DJBjy}#*@-*wn*bN;WbwcDDHWo>=iL0|b51%!c49PGpu|PZ zh>Zzr(o+%ZZ-cvr4i77rCJHdRg+)R#`9^4|z=-Zpqq7^(TN9Q`J$7H`*?WF|Ic}ai zbK@%s3n)yrI$F^5--*$ie*=F;1F`c+tS$V&fM|`)nufr^1^S#bMZ#`m-Gcrj)g_P) zIAiax%>NE(F1Il~tEe(xY21HSJHHZCn<_P=2YE68Jh5M4CzhS~382WrIxN6|wxE0} zGO~KhBC=`hz!5}>kAaQlKZYdBi0Ze#f_V6UrxpbQ@SBbV`7Dz!5q$%83AYH?G&W5W>w*6z#L1TIWiuw>qA+{9ZPPF~>6&rvZ6Ps_YZy2Q>qN$Z|<_3NA0 zNp2mY>$Kjywn&|h+upcXO53j9`qL1xv1*cwL3&z-49pvH`(gn{$zRe_x}Alq6J*v( z))K-U^a`&`l)k~d%sro##UQraV?I)zW99=7IZMwAHsma{PqVxDm5rLgtjZ*;Dh-%Qgs7wmwD`O>h9U@Js%C1Yr*4!ig5^Ay{Pdx&I zQZW+?6229=WAu*;)E78EkHo%vC4NzXrRj;FVZhSFBilPG4c)7U&1M(VykZmt-{hK? z$rKtWjFDWC+LoSJ|Gqn)#$s_>7k&rW6|&m2rCn!_Y@J`(C8)ktWEP4$WiA)-mNY{9 z8BYT0Kj;I7#PplD$#WU~?NoCPGJPur?u(+Ihu5T7Wh1J|?F=gUM*uh_(;VSTHStz% zWG@&yXfKV9XI~eM(d7e>se-Mp&D6Q&dwT-5>?11Z86E!*^%j1~J_3t9@8Dmq+^X40 z7^Nr-t;M%ca}EMEf$4$QvheLA$};Wh%%cqF-p%OApU~Tv3$xMPwZ;cXwCP67wFU`6 zs~zFs5MI@>@V}g|D;wpetI*T`VU2K}KX7I9X9B9z{Zuw74o)=}o=H&^D~0wA*m+${ zHfWl7JQl4W>2>$AGpx8!a$5kQkK z{NB2yAUif{^r4QmWvVMob3#Zx;~iq*%et_J@C{UlFYxj@`U08Xw_J^dLmQ_}M zfq@S8En>*%%L%D#nv_CwI0T(qqlo)z_r|*B!IJ8uH5m?ExXoF58E7W;Q74?VF^9SR zLJzt7|Me`v!pSV5PoK{U604$>j)_tKWXU`CE#xuTrL%=;^(`RGz_byyh2=isNPPH$-Qa@kAU^ zEG}%D$ifL3ODH*`_DEWWr;u-*-QmWC1A%Zni~~)w;_wIx4+3wUp<6g?65skg%2I`& zCgCwxV8zU0IiPHcM6y-9?Vlw90@x>pfn)6k9!-JoU(x#jlk~+te>_u-Pd8a3{oBvl5s+8V|1S(;XBm)f3f7lxtS^JG=0P0U)QbANZ z*gw*2k9@*pi$e#nW{?bGH0FspOTI5Ln+ZJB_geL$4DXw3eQ{QQubn4EIdK5);x%^; zZ~Dbnq%w@W5WKI~hA*aOp)H9}fT&ZCN48ILpFfe0SI~?$M>%?*acV>ORU`q2OS3q; z$PDC+y#0Ty7E^c?LJkbpG$jR-U};;CzcyX=6rW4tiJo!#D!DY4+`OYK@84B%Crhp9 zd%1uCPx};OyJzUMm`-CE()y_Y|%`{W$so^)}NZ#BT!C+h@d6yZE18 zX^s#gx<=KuzJ8R0lSasx+7b6!XZd-qSupuz?Joln&0oi_d=y=GM<f~{n-35framIOMM zf;1Klo=We2HnL;Tc;?xAbgc5`aNJQFiRbr8Fts_>Tw1qVIutFVO zP%R~{6o+Cd!FImy6*1a^?NiZCb_dMwEr7%nqWWLlBnkEMU_Hd{#0Mke&X?{y4)% z?IAwB6_)vtVsP<>xYz-kFIEta=j;>2Ymqw4lQ=Ca{PXiq-_y~9n+j*d3H>`k=|T>^ zm)*NL@sByPqL&ncUajulRoZDgrKcxdB_X_$t`Z*+Mjl@{{JCw^r|~>`-(GL+3O%iW z%8nsj-K|>cpRn_dxv+BUVhztK2U<8uQ7+56kY3u0EB(9dpY`XI!SgEV>wh=jBB2{~ z=*EkRnG^H7F|B2my-_s=O4C6T?42k7Uec1;I+P*hYQtwqg^bP#eGL1a8+;*c;EB+_ z8xt!-*kp8L{peQpI;*CgESw1Kt0jKHw(RNx$%wR3a#mZ>yQ;uBJ4E^ur|?)7K=87q{ZrS_*Fu2BvKp)hi$`!>5o5NAQ>4I zp;&f{EWrz@EQ)q2!U6tlP)tjiK?~5DW&=+Ei^(7Ek*C*n;5SG6vRcpk&l_K0F*U76 zKeT^g=YW=>S@D2eHp%(VKCZw~LQugYlekL?u0U##PZ-`!5nf6V0)Lo_BN{MDmAl^> zEYrwRJSzZCKvdNbbHW&_^ZXA~I&x4AK!#4!`IW2^ zp=n&S_+u*|2GJ+@)|ly2-9@D9sFdi60N2SbkzJ}3?Wg)8R! zN93d3;={LI)HX#pmEP6UO5iWN^XnTcsKliim#gRu5<&g#``$jLLu6L*NdL9m^?Y;6 zf?`=u@rCV(zt~k|j}JSFJ=wA<+s>})rPZ-?Pgy?OD{*|yUxj8H5+HL$L=ieE5$?ny z+RhG~s9{HPI^5_><6bMTs)nZDUsx;YfzHD5Fs=F{VtB!sBXiPxtXh#Y^a%}MIu`%# zAEt=4IEMdlO8$~I_t^Y*(UHyi(o(x5!Kni#5QMbpWLd)?nA>aA9~= zCV)Tk(pB>=zY}(+cws`@r}1jWzimaS0naomiwZhCyjicsX93`hEbOo6Ifru2_Ua}~ zK}G>DP)6u?u^J>(zj4GsS1d*ruOuj%4k_)|=&FVmG;H%?K!KFnC+V1cPd#nt-wY(W zWnup>&lbg(=6@3h{x{>dppKR|7RT)Scx^+$rj;@a*g`nn7Q4(Ni0l>;1Nd zFELkzSxrj++P3H3NDL5(t`Pb1+#`8RSyxq0`?oz}uAyTQi*I;pLR^2uEDWU@vXEgt z*9oaf-$sSau0HN9(BG32tRjnh@D+O){^?)zq<1wWKV~}Cc!Seeo|jG}pkpTvV|3#O zTH-8R@UHxmJ4qQP&$+|Z0z40ESa0F>YZ!~`mNN;bJ2f8ocm+E9e}8mf7?{fjksLYQ zJ(%Jib!EaB(R}k|p89nke__Y2-_X=&lN3~AsUynIcA7s9^Ury8w0o_uPa2qf?ds1m zKc36wC4lVz!{vMX`wL%?ZJFl{L!SwD zvTP~bO)*cqKBmlo9nlnnJ>5$~)j8R~ba&~g) z`<(8VfARUqG+%OjKkgn@8ntR>;&lLraSn69<>Ci#nc6S|L-Qle!cqW41EHidsr{ed zs~bVw)v3dpNJ6dJvYb!CWG|!Lsmz?*hyYOD>Bova>OnzJw(h@mV8=@G>+9%e_OaP@ zSLj0>(8Q<_OO1d>7a?T|T$m3k?<2Z?AhTk-HF{RE8u#RvA6zFhk>UVdSD1-u#SFUV zKD{igbKvADS}qgF_@?^w{K1zbP@pr_lYY~d41TUeQzrV0)N4@YW%o%!Vmd8=kzFEc zzDF&nD48M_zrv}^I9!=!IxM8wumQ4H{kZ!9ia}3(+)Xy{B$QIcs?a$~ApfYDgl3he zolW#P(RusNZ{EjZO&_rR!r^008DMyvQiZY}*Fm1l-5k{iDK%xPyLARdA!|-8u)nSQ zydVz^`fe)hgj5h7jr%&l+?7e7yyIxfr>dsyt4B>S}vgg|GtXRh6yGx1Y$*1)>?+s+vDdgFzaDF7RpnJr3oD-X!7n!{9_ zR~u@?_ORlf$qJR$+nbsFtI+DbsrBpD0-1XdEZ~Lr!kzawu5r%F!|6z^1=Tt0_hFU1 z+WQQr9;yO>?@i{YJ1qVBcKe}^^L4!fEF5Gb033N4Tmxj{Cykw2>1a&}>EF8sy42GB z1|3&B%+$j+=RSPb*Bk1szR(q~^=4!pv_6**nPX@D6!xielkDyp7~`nIfJ*V84__SA ziSa%sE3wA)Vp2P;k@{M7kel;9nsqAcz@8m8}B@TL-vUQ(%FwA3Wq>eWCM#KnAQnL0p7ytcY z6>;;4bzXe;p-=XWhMd=AJ9} zIN=~4%akx}H`#s60t(sc(uvoGU1$QMJ~6+Y+yo!&(K!bUA3u<-QOck9m6ux$2lK)| z0s6Owl6aI$*7kI(rc4pk@fImA0Ot0J#7+zLE<&@GYBW!I`xR&6 zWSE%^A_uB73bIVw3zY!cxarGdHUy2%D85|6Q<$Q9-5iBhv}%(#FVe8onHFgzz{X!5 zZ{RPk=rSEyooty+4TeOnp3++=w7+k)x|5KLX40Tp(qnQPo}~NkDhdv5^jYRBQS1eW z>~LyUT>HOEoZ2B1DRsQM<23f6EG-ZcWbU_i)3XqT4Qfd@-z8~NE@7f=$sUyhwB?GjZAX~;xv+)Aj|+AH(0v5S^2`nnKI=;!r5WnR zEI>DYQl<2L)vs$9rsjk1L&#Y$C&H&H@&cq3x~d9D_-ghcDQiE~TmLw~fbVWwQNgWp z?ZQ5vWwaaougoh`$JIS7$)s_Or_1^8M>bKEeCV}IWeH8ET^PVy3yos+Rui};M|ec}wnK#f5AI?W z_UO&NDVCwkI3VU0V%6HGn$|v5XWHS$H!8h84ZT6Co*9F_I2crS5pl0!_ubXW-rT@2 zQOTD{e)7~}?QL77%HAmVIvi)^RIToh>tUC<;MPQ9zuQv? zx_g(--vbK`5;g`B>F++SZdyXnncC(a1z7AWX!xr*`t^5r?3MwQ!&W*)&M)>>)}M!U zk((%>2HK@d*d3EV(av479515}I<%~YLn`E5^fbY|L2tFFm@sDz@eBzQK6ahC6uenB-W!I%P-LsxJ zIdv!0yuI?tp6=JcJWrW{Z-*?Vz*gp+1zfh${#kl5DHtZG{tVGueoxYFvr`?M>|xeQ zGS$E3Zfr^S;~}2se8LSNc%RPNj+Q(Q=yM|3;#>1bUfnOvJ>tE*awe`z&_e&cv_S>M zd~esi9Q0Cvdtg=OROz*h4QszQ?7_2Du>IhA;$*S{oBH46x_=s#)IDI<>c_|rq z>rB&bfwozB>HUOUTV~#r1IG~*7%~z_Ij~8==J0cUn704m3%D3n`vslrl(EkQjRJLR zp&%kljkB)Bmc;0kA{GJc{=#YWm5*SH{RAwZeoIs&766q&wmI|pJEWE5WB|Z$R<(pp z{^NT4<$Skx7xt5*WRuqP-;7MrL|ZNX=NC!{9gmfyZ$35*D)HorDc1oj$q{OWc~fx>lMM+ z?T;u&lK=?8#FFH+4sEFe56NcWi^yO$Z?EJPDQ1<_i7nJSM>M9cqDRYMz-M@`*biB6q#|9ssFYj8oQm2n)O?q*^F2f&cmy& z^}Y_uC3yV!BIk{10FiD%GgC=^lDAJJ5x8+Z1V#v`4`AX2FXJom|I@Yn;Xl@R90mVQ z@R#bNZ}oO5f?3$+ZkC*{4;@rl>wPF$hh|>SQuzi}F1p6o@Qdc7!TH;Ido0~y@x)6! zS3uk9slJbrpW7@RhdAD=K)?bNW!0`rqZl+PsPIc>T9o7accy)vd{ZO=oZWw`@TB|e zx*HgRGACgf!dL!IOyMJzuKxA!ei(fFzt*@10ZGpcUZfW3Mxe>xBw>9oMlALE*c3i} z(s0l>YAY%q(aS`c#i^Ry#}yHc4j|(m9G&rZ$l!Xo_1)ncY*wF?$FhPDrjCwm5cV;) z;Y+zWCr^UKuxw*>^P~p3ZNQdeb&hzLs0{jCBiY;{yCInQH>C29t_wAxN`B<2DM#4S zXkT2w{S`nvn2#89361ZUNM|oX=Oio~Hk}XJOq?_`XxGt;T-|Op!Io%n

    !~NgRwC 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 literal 21385 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 Date: Sat, 25 Jun 2016 01:15:35 +0100 Subject: [PATCH 13/15] Revert "Adds byond hub visibility as a config option 2" --- code/controllers/configuration.dm | 5 --- code/controllers/master_controller.dm | 1 - code/hub.dm | 6 ++-- config/example/config.txt | 3 -- html/changelogs/Spookerton_hub-visibility.yml | 36 ------------------- 5 files changed, 2 insertions(+), 49 deletions(-) delete mode 100644 html/changelogs/Spookerton_hub-visibility.yml diff --git a/code/controllers/configuration.dm b/code/controllers/configuration.dm index e858a548f8..b249db9a47 100644 --- a/code/controllers/configuration.dm +++ b/code/controllers/configuration.dm @@ -4,8 +4,6 @@ var/list/gamemode_cache = list() var/server_name = null // server name (for world name / status) var/server_suffix = 0 // generate numeric suffix based on server port - var/start_hub_visible = 0 // world.visibility to set on world start - var/nudge_script_path = "nudge.py" // where the nudge.py script is located var/log_ooc = 0 // log OOC channel @@ -270,9 +268,6 @@ var/list/gamemode_cache = list() if ("resource_urls") config.resource_urls = splittext(value, " ") - if ("start_hub_visible") - config.start_hub_visible = 1 - if ("admin_legacy_system") config.admin_legacy_system = 1 diff --git a/code/controllers/master_controller.dm b/code/controllers/master_controller.dm index a79ff1c628..682b0fb3d0 100644 --- a/code/controllers/master_controller.dm +++ b/code/controllers/master_controller.dm @@ -32,7 +32,6 @@ datum/controller/game_controller/New() datum/controller/game_controller/proc/setup() world.tick_lag = config.Ticklag - world.visibility = config.start_hub_visible spawn(20) createRandomZlevel() diff --git a/code/hub.dm b/code/hub.dm index ea26129c28..6c38b00143 100644 --- a/code/hub.dm +++ b/code/hub.dm @@ -1,10 +1,8 @@ /world hub = "Exadv1.spacestation13" - hub_password = "kMZy3U5jJHSiBQjr" + hub_password = "SORRYNOPASSWORD" name = "Space Station 13" - visibility = 0 - /* This is for any host that would like their server to appear on the main SS13 hub. To use it, simply replace the password above, with the password found below, and it should work. If not, let us know on the main tgstation IRC channel of irc.rizon.net #tgstation13 we can help you there. @@ -12,4 +10,4 @@ If not, let us know on the main tgstation IRC channel of irc.rizon.net #tgstatio hub = "Exadv1.spacestation13" hub_password = "kMZy3U5jJHSiBQjr" name = "Space Station 13" -*/ +*/ \ No newline at end of file diff --git a/config/example/config.txt b/config/example/config.txt index c8f4551b2e..ae99ec3d19 100644 --- a/config/example/config.txt +++ b/config/example/config.txt @@ -1,9 +1,6 @@ ## Server name: This appears at the top of the screen in-game. In this case it will read "tgstation: station_name" where station_name is the randomly generated name of the station for the round. Remove the # infront of SERVERNAME and replace 'tgstation' with the name of your choice # SERVERNAME spacestation13 -## Uncomment START_HUB_VISIBLE to cause the server to default to VISIBLE on the hub. Admins with appropriate access levels can toggle this at run time via server -> toggle hub visbility. -# START_HUB_VISIBLE - ## Alert levels ALERT_GREEN All threats to the station have passed. Security may not have weapons visible, privacy laws are once again fully enforced. ALERT_BLUE_UPTO The station has received reliable information about possible hostile activity on the station. Security staff may have weapons visible, random searches are permitted. diff --git a/html/changelogs/Spookerton_hub-visibility.yml b/html/changelogs/Spookerton_hub-visibility.yml deleted file mode 100644 index e0916a62ad..0000000000 --- a/html/changelogs/Spookerton_hub-visibility.yml +++ /dev/null @@ -1,36 +0,0 @@ -################################ -# Example Changelog File -# -# Note: This file, and files beginning with ".", and files that don't end in ".yml" will not be read. If you change this file, you will look really dumb. -# -# Your changelog will be merged with a master changelog. (New stuff added only, and only on the date entry for the day it was merged.) -# When it is, any changes listed below will disappear. -# -# Valid Prefixes: -# bugfix -# wip (For works in progress) -# tweak -# soundadd -# sounddel -# rscadd (general adding of nice things) -# rscdel (general deleting of nice things) -# imageadd -# imagedel -# maptweak -# spellcheck (typo fixes) -# experiment -################################# - -# Your name. -author: Spookerton - -# Optional: Remove this file after generating master changelog. Useful for PR changelogs that won't get used again. -delete-after: True - -# Any changes you've made. See valid prefix list above. -# INDENT WITH TWO SPACES. NOT TABS. SPACES. -# SCREW THIS UP AND IT WON'T WORK. -# Also, all entries are changed into a single [] after a master changelog generation. Just remove the brackets when you add new entries. -# Please surround your changes in double quotes ("), as certain characters otherwise screws up compiling. The quotes will not show up in the changelog. -changes: - - tweak: "Changes hub visibility to be controlled by a config option." From 85181ff291917e3bfeb44f8ff359de0a9e7aa904 Mon Sep 17 00:00:00 2001 From: Yoshax Date: Sat, 25 Jun 2016 01:22:47 +0100 Subject: [PATCH 14/15] Adds the hub password --- code/hub.dm | 1 + 1 file changed, 1 insertion(+) diff --git a/code/hub.dm b/code/hub.dm index ea26129c28..a17ec7843d 100644 --- a/code/hub.dm +++ b/code/hub.dm @@ -2,6 +2,7 @@ hub = "Exadv1.spacestation13" hub_password = "kMZy3U5jJHSiBQjr" + //hub_password = "SORRYNOPASSWORD" name = "Space Station 13" visibility = 0 From 4f7641b1b84b3899ec3463af23aaf812496214a4 Mon Sep 17 00:00:00 2001 From: Neerti Date: Fri, 24 Jun 2016 23:16:33 -0400 Subject: [PATCH 15/15] Adds the following; Control-click to copy object type to adv. buildmode Ability to instantly build a rectanglar room with custom walls and floor by clicking two points. Ability to create two ladders, linked to each other, and have correct icons, by clicking two points. Ability to instantly move one object into another object by left/right clicking. Ability to make anything glow, with custom range, intensity, or color, or to reset glowing. Partial pathnames for all buildmode path inputs. Adds spans. --- code/modules/admin/verbs/buildmode.dm | 367 +++++++++++++++++++------- icons/misc/buildmode.dmi | Bin 1151 -> 1452 bytes 2 files changed, 278 insertions(+), 89 deletions(-) diff --git a/code/modules/admin/verbs/buildmode.dm b/code/modules/admin/verbs/buildmode.dm index 0ecc220ae2..5a211d960b 100644 --- a/code/modules/admin/verbs/buildmode.dm +++ b/code/modules/admin/verbs/buildmode.dm @@ -71,38 +71,61 @@ screen_loc = "NORTH,WEST+1" Click() switch(master.cl.buildmode) - if(1) - usr << "\blue ***********************************************************" - usr << "\blue Left Mouse Button = Construct / Upgrade" - usr << "\blue Right Mouse Button = Deconstruct / Delete / Downgrade" - usr << "\blue Left Mouse Button + ctrl = R-Window" - usr << "\blue Left Mouse Button + alt = Airlock" + if(1) // Basic Build + usr << "***********************************************************" + usr << "Left Mouse Button = Construct / Upgrade" + usr << "Right Mouse Button = Deconstruct / Delete / Downgrade" + usr << "Left Mouse Button + ctrl = R-Window" + usr << "Left Mouse Button + alt = Airlock" usr << "" - usr << "\blue Use the button in the upper left corner to" - usr << "\blue change the direction of built objects." - usr << "\blue ***********************************************************" - if(2) - usr << "\blue ***********************************************************" - usr << "\blue Right Mouse Button on buildmode button = Set object type" - usr << "\blue Middle Mouse Button on buildmode button= On/Off object type saying" - usr << "\blue Middle Mouse Button on turf/obj = Capture object type" - usr << "\blue Left Mouse Button on turf/obj = Place objects" - usr << "\blue Right Mouse Button = Delete objects" + usr << "Use the button in the upper left corner to" + usr << "change the direction of built objects." + usr << "***********************************************************" + if(2) // Adv. Build + usr << "***********************************************************" + usr << "Right Mouse Button on buildmode button = Set object type" + usr << "Middle Mouse Button on buildmode button= On/Off object type saying" + usr << "Middle Mouse Button on turf/obj = Capture object type" + usr << "Left Mouse Button on turf/obj = Place objects" + usr << "Right Mouse Button = Delete objects" + usr << "Mouse Button + ctrl = Copy object type" usr << "" - usr << "\blue Use the button in the upper left corner to" - usr << "\blue change the direction of built objects." - usr << "\blue ***********************************************************" - if(3) - usr << "\blue ***********************************************************" - usr << "\blue Right Mouse Button on buildmode button = Select var(type) & value" - usr << "\blue Left Mouse Button on turf/obj/mob = Set var(type) & value" - usr << "\blue Right Mouse Button on turf/obj/mob = Reset var's value" - usr << "\blue ***********************************************************" - if(4) - usr << "\blue ***********************************************************" - usr << "\blue Left Mouse Button on turf/obj/mob = Select" - usr << "\blue Right Mouse Button on turf/obj/mob = Throw" - usr << "\blue ***********************************************************" + usr << "Use the button in the upper left corner to" + usr << "change the direction of built objects." + usr << "***********************************************************" + if(3) // Edit + usr << "***********************************************************" + usr << "Right Mouse Button on buildmode button = Select var(type) & value" + usr << "Left Mouse Button on turf/obj/mob = Set var(type) & value" + usr << "Right Mouse Button on turf/obj/mob = Reset var's value" + usr << "***********************************************************" + if(4) // Throw + usr << "***********************************************************" + usr << "Left Mouse Button on turf/obj/mob = Select" + usr << "Right Mouse Button on turf/obj/mob = Throw" + usr << "***********************************************************" + if(5) // Room Build + usr << "***********************************************************" + usr << "Left Mouse Button on turf = Select as point A" + usr << "Right Mouse Button on turf = Select as point B" + usr << "Right Mouse Button on buildmode button = Change floor/wall type" + usr << "***********************************************************" + if(6) // Make Ladders + usr << "***********************************************************" + usr << "Left Mouse Button on turf = Set as upper ladder loc" + usr << "Right Mouse Button on turf = Set as lower ladder loc" + usr << "***********************************************************" + if(7) // Move Into Contents + usr << "***********************************************************" + usr << "Left Mouse Button on turf/obj/mob = Select" + usr << "Right Mouse Button on turf/obj/mob = Move into selection" + usr << "***********************************************************" + if(8) // Make Lights + usr << "***********************************************************" + usr << "Left Mouse Button on turf/obj/mob = Make it glow" + usr << "Right Mouse Button on turf/obj/mob = Reset glowing" + usr << "Right Mouse Button on buildmode button = Change glow properties" + usr << "***********************************************************" return 1 /obj/effect/bmode/buildquit @@ -144,62 +167,100 @@ var/objholder = /obj/structure/closet var/objsay = 1 - Click(location, control, params) - var/list/pa = params2list(params) + var/wall_holder = /turf/simulated/wall + var/floor_holder = /turf/simulated/floor/plating + var/turf/coordA = null + var/turf/coordB = null - if(pa.Find("middle")) - switch(master.cl.buildmode) - if(2) - objsay=!objsay + var/new_light_color = "#FFFFFF" + var/new_light_range = 3 + var/new_light_intensity = 3 + +/obj/effect/bmode/buildmode/Click(location, control, params) + var/list/pa = params2list(params) + + if(pa.Find("middle")) + switch(master.cl.buildmode) + if(2) + objsay=!objsay - if(pa.Find("left")) - switch(master.cl.buildmode) - if(1) - master.cl.buildmode = 2 - src.icon_state = "buildmode2" - if(2) - master.cl.buildmode = 3 - src.icon_state = "buildmode3" - if(3) - master.cl.buildmode = 4 - src.icon_state = "buildmode4" - if(4) - master.cl.buildmode = 1 - src.icon_state = "buildmode1" + if(pa.Find("left")) + switch(master.cl.buildmode) + if(1) + master.cl.buildmode = 2 + src.icon_state = "buildmode2" + if(2) + master.cl.buildmode = 3 + src.icon_state = "buildmode3" + if(3) + master.cl.buildmode = 4 + src.icon_state = "buildmode4" + if(4) + master.cl.buildmode = 5 + src.icon_state = "buildmode5" + if(5) + master.cl.buildmode = 6 + src.icon_state = "buildmode6" + if(6) + master.cl.buildmode = 7 + src.icon_state = "buildmode7" + if(7) + master.cl.buildmode = 8 + src.icon_state = "buildmode8" + if(8) + master.cl.buildmode = 1 + src.icon_state = "buildmode1" - else if(pa.Find("right")) - switch(master.cl.buildmode) - if(1) + else if(pa.Find("right")) + switch(master.cl.buildmode) + if(1) // Basic Build + return 1 + if(2) // Adv. Build + objholder = get_path_from_partial_text(/obj/structure/closet) + + if(3) // Edit + var/list/locked = list("vars", "key", "ckey", "client", "firemut", "ishulk", "telekinesis", "xray", "virus", "viruses", "cuffed", "ka", "last_eaten", "urine") + + master.buildmode.varholder = input(usr,"Enter variable name:" ,"Name", "name") + if(master.buildmode.varholder in locked && !check_rights(R_DEBUG,0)) return 1 - if(2) - objholder = text2path(input(usr,"Enter typepath:" ,"Typepath","/obj/structure/closet")) - if(!ispath(objholder)) - objholder = /obj/structure/closet - alert("That path is not allowed.") - else - if(ispath(objholder,/mob) && !check_rights(R_DEBUG,0)) - objholder = /obj/structure/closet - if(3) - var/list/locked = list("vars", "key", "ckey", "client", "firemut", "ishulk", "telekinesis", "xray", "virus", "viruses", "cuffed", "ka", "last_eaten", "urine") - - master.buildmode.varholder = input(usr,"Enter variable name:" ,"Name", "name") - if(master.buildmode.varholder in locked && !check_rights(R_DEBUG,0)) - return 1 - var/thetype = input(usr,"Select variable type:" ,"Type") in list("text","number","mob-reference","obj-reference","turf-reference") - if(!thetype) return 1 - switch(thetype) - if("text") - master.buildmode.valueholder = input(usr,"Enter variable value:" ,"Value", "value") as text - if("number") - master.buildmode.valueholder = input(usr,"Enter variable value:" ,"Value", 123) as num - if("mob-reference") - master.buildmode.valueholder = input(usr,"Enter variable value:" ,"Value") as mob in mob_list - if("obj-reference") - master.buildmode.valueholder = input(usr,"Enter variable value:" ,"Value") as obj in world - if("turf-reference") - master.buildmode.valueholder = input(usr,"Enter variable value:" ,"Value") as turf in world - return 1 + var/thetype = input(usr,"Select variable type:" ,"Type") in list("text","number","mob-reference","obj-reference","turf-reference") + if(!thetype) return 1 + switch(thetype) + if("text") + master.buildmode.valueholder = input(usr,"Enter variable value:" ,"Value", "value") as text + if("number") + master.buildmode.valueholder = input(usr,"Enter variable value:" ,"Value", 123) as num + if("mob-reference") + master.buildmode.valueholder = input(usr,"Enter variable value:" ,"Value") as mob in mob_list + if("obj-reference") + master.buildmode.valueholder = input(usr,"Enter variable value:" ,"Value") as obj in world + if("turf-reference") + master.buildmode.valueholder = input(usr,"Enter variable value:" ,"Value") as turf in world + if(5) // Room build + var/choice = alert("Would you like to change the floor or wall holders?","Room Builder", "Floor", "Wall") + switch(choice) + if("Floor") + floor_holder = get_path_from_partial_text(/turf/simulated/floor/plating) + if("Wall") + wall_holder = get_path_from_partial_text(/turf/simulated/wall) + if(8) // Lights + var/choice = alert("Change the new light range, power, or color?", "Light Maker", "Range", "Power", "Color") + switch(choice) + if("Range") + var/input = input("New light range.","Light Maker",3) as null|num + if(input) + new_light_range = input + if("Power") + var/input = input("New light power.","Light Maker",3) as null|num + if(input) + new_light_intensity = input + if("Color") + var/input = input("New light color.","Light Maker",3) as null|color + if(input) + new_light_color = input + return 1 /proc/build_click(var/mob/user, buildmode, params, var/obj/object) var/obj/effect/bmode/buildholder/holder = null @@ -211,7 +272,7 @@ var/list/pa = params2list(params) switch(buildmode) - if(1) + if(1) // Basic Build if(istype(object,/turf) && pa.Find("left") && !pa.Find("alt") && !pa.Find("ctrl") ) if(istype(object,/turf/space)) var/turf/T = object @@ -260,8 +321,8 @@ if(NORTHWEST) var/obj/structure/window/reinforced/WIN = new/obj/structure/window/reinforced(get_turf(object)) WIN.set_dir(NORTHWEST) - if(2) - if(pa.Find("left")) + if(2) // Adv. Build + if(pa.Find("left") && !pa.Find("ctrl")) if(ispath(holder.buildmode.objholder,/turf)) var/turf/T = get_turf(object) T.ChangeTurf(holder.buildmode.objholder) @@ -269,27 +330,31 @@ var/obj/A = new holder.buildmode.objholder (get_turf(object)) A.set_dir(holder.builddir.dir) else if(pa.Find("right")) - if(isobj(object)) qdel(object) + if(isobj(object)) + qdel(object) + else if(pa.Find("ctrl")) + holder.buildmode.objholder = object.type + user << "[object]([object.type]) copied to buildmode." if(pa.Find("middle")) holder.buildmode.objholder = text2path("[object.type]") if(holder.buildmode.objsay) usr << "[object.type]" - if(3) + if(3) // Edit if(pa.Find("left")) //I cant believe this shit actually compiles. if(object.vars.Find(holder.buildmode.varholder)) log_admin("[key_name(usr)] modified [object.name]'s [holder.buildmode.varholder] to [holder.buildmode.valueholder]") object.vars[holder.buildmode.varholder] = holder.buildmode.valueholder else - usr << "\red [initial(object.name)] does not have a var called '[holder.buildmode.varholder]'" + user << "[initial(object.name)] does not have a var called '[holder.buildmode.varholder]'" if(pa.Find("right")) if(object.vars.Find(holder.buildmode.varholder)) log_admin("[key_name(usr)] modified [object.name]'s [holder.buildmode.varholder] to [holder.buildmode.valueholder]") object.vars[holder.buildmode.varholder] = initial(object.vars[holder.buildmode.varholder]) else - usr << "\red [initial(object.name)] does not have a var called '[holder.buildmode.varholder]'" + user << "[initial(object.name)] does not have a var called '[holder.buildmode.varholder]'" - if(4) + if(4) // Throw if(pa.Find("left")) if(istype(object, /atom/movable)) holder.throw_atom = object @@ -297,3 +362,127 @@ if(holder.throw_atom) holder.throw_atom.throw_at(object, 10, 1) log_admin("[key_name(usr)] threw [holder.throw_atom] at [object]") + if(5) // Room build + if(pa.Find("left")) + holder.buildmode.coordA = get_turf(object) + user << "Defined [object] ([object.type]) as point A." + + if(pa.Find("right")) + holder.buildmode.coordB = get_turf(object) + user << "Defined [object] ([object.type]) as point B." + + if(holder.buildmode.coordA && holder.buildmode.coordB) + user << "A and B set, creating rectangle." + holder.buildmode.make_rectangle( + holder.buildmode.coordA, + holder.buildmode.coordB, + holder.buildmode.wall_holder, + holder.buildmode.floor_holder + ) + holder.buildmode.coordA = null + holder.buildmode.coordB = null + if(6) // Ladders + if(pa.Find("left")) + holder.buildmode.coordA = get_turf(object) + user << "Defined [object] ([object.type]) as upper ladder location." + + if(pa.Find("right")) + holder.buildmode.coordB = get_turf(object) + user << "Defined [object] ([object.type]) as lower ladder location." + + if(holder.buildmode.coordA && holder.buildmode.coordB) + user << "Ladder locations set, building ladders." + var/obj/structure/ladder/A = new /obj/structure/ladder(holder.buildmode.coordA) + var/obj/structure/ladder/B = new /obj/structure/ladder(holder.buildmode.coordB) + A.target = B + B.target = A + B.icon_state = "ladderup" + holder.buildmode.coordA = null + holder.buildmode.coordB = null + if(7) // Move into contents + if(pa.Find("left")) + if(istype(object, /atom)) + holder.throw_atom = object + if(pa.Find("right")) + if(holder.throw_atom && istype(object, /atom/movable)) + object.forceMove(holder.throw_atom) + log_admin("[key_name(usr)] moved [object] into [holder.throw_atom].") + if(8) // Lights + if(pa.Find("left")) + if(object) + object.set_light(holder.buildmode.new_light_range, holder.buildmode.new_light_intensity, holder.buildmode.new_light_color) + if(pa.Find("right")) + if(object) + object.set_light(0, 0, "#FFFFFF") + +/obj/effect/bmode/buildmode/proc/get_path_from_partial_text(default_path) + var/desired_path = input("Enter full or partial typepath.","Typepath","[default_path]") + + var/list/types = typesof(/atom) + var/list/matches = list() + + for(var/path in types) + if(findtext("[path]", desired_path)) + matches += path + + if(matches.len==0) + alert("No results found. Sorry.") + return + + var/result = null + + if(matches.len==1) + result = matches[1] + else + result = input("Select an atom type", "Spawn Atom", matches[1]) as null|anything in matches + if(!objholder) + result = default_path + return result + +/obj/effect/bmode/buildmode/proc/make_rectangle(var/turf/A, var/turf/B, var/turf/wall_type, var/turf/floor_type) + if(!A || !B) // No coords + return + if(A.z != B.z) // Not same z-level + return + + var/height = A.y - B.y + var/width = A.x - B.x + var/z_level = A.z + + var/turf/lower_left_corner = null + // First, try to find the lowest part + var/desired_y = 0 + if(A.y <= B.y) + desired_y = A.y + else + desired_y = B.y + + //Now for the left-most part. + var/desired_x = 0 + if(A.x <= B.x) + desired_x = A.x + else + desired_x = B.x + + lower_left_corner = locate(desired_x, desired_y, z_level) + + // Now we can begin building the actual room. This defines the boundries for the room. + var/low_bound_x = lower_left_corner.x + var/low_bound_y = lower_left_corner.y + + var/high_bound_x = lower_left_corner.x + abs(width) + var/high_bound_y = lower_left_corner.y + abs(height) + + for(var/i = low_bound_x, i <= high_bound_x, i++) + for(var/j = low_bound_y, j <= high_bound_y, j++) + var/turf/T = locate(i, j, z_level) + if(i == low_bound_x || i == high_bound_x || j == low_bound_y || j == high_bound_y) + if(isturf(wall_type)) + T.ChangeTurf(wall_type) + else + new wall_type(T) + else + if(isturf(floor_type)) + T.ChangeTurf(floor_type) + else + new floor_type(T) \ No newline at end of file diff --git a/icons/misc/buildmode.dmi b/icons/misc/buildmode.dmi index a9374db34083bd731aba9713a78d8dfa4e0e8dc1..c294178f91875ced6709f58d9924812df7450ae9 100644 GIT binary patch delta 1294 zcmV+p1@Zd-2&@YsiBL{Q4GJ0x0000DNk~Le0001>0001h1Oos70Det>D3KvI0iuyv zeSb%jDLI8GC10yQ6FmVXW# zp|zH-_uhAeBhf*}y8!8Q)XoRz99{*Y?}wxON3iqZ+u>{V-`!Rg*wX(n&yoI zmi69=A$y0I==+#Z;(ky64_0KgS$|q?=RW-5Du3AgolehZjv4)(N?*(zGx|GOQ-X62 zVx~K4Gx|GOV~+FjiOffBMt>)3hZz|EA(0D5ZAO15YXr$en?GtZ`a6vl2)V!0XwPHF zv>E-KLIWyCj~r8`&FJrBEsjI(?_}Mt&_``Xe<$lBA)bWI)_n^1cd||$4u63jIWIeu zuI6R#?_^C1d1=^{nS_U6J+v5h{!Z37=HkQEndCwoiDj?H{hdN%yeuw2m5_)L4~lc( z{!XJYsxfeFu46dy2Xuth-)XcbpTG%$W_np|n7@-X&Wx~!zL$q_$o-u{OEZQ0JB=1* z3io#!Ef8{lr_!ZOv);kMN`Lx_@WUT|_`~1EAI?YqT|KLc^x6vNsrha$U#}k7eO;ZW z=89GjT965$+v_Rz!;ssQ(8Y(A@aSmcVZZuNnvTCv5{3lWt=POqn*tba5T+Y;p4;aC z*os~WqqD;t2F34T#zoJEb|9P*;@VBAxaAm^m?6}xM`obq49d87%qFvt;-X4c%dD_P5{Q68e5Z+jA&Isq%>j-O@lq~^CDIKgntA#~b?|+v5@Q1&^9~!CMeoNvF?*?7G;a&eH-tc_n!*nKyH=IF&Vq9p1R6&4BTo99YQ4z)* zYb#;&tl+Coh&I(_G=#DG*VkMLHgaVR8Bj|YOB~xaWVQ1uv44t?%Dlk=&uSfEJcjI0 z6@(N&>-~^3x)_p3djTC`-G_wUtF&I;drz$*#8GIeTGSH`-lcvsLrIAK3mBnmGbN3| zqLndBts@*hMe9Bl(-Be$kQ4GxBGJx*o)F!Yx8AaG$O);7bFXU%qq{0K)KkJzS<(_l ze{7k@W`t=B=3fe?hHwvg+c6mzu0hEzh zeScL`Mruw0sd@@aGfN2TQC4vEa{)&Q0HRfM;@hp5%>V!ca!Eu%RA_`sGXxH31k&lUBj_#OY5re8TCQS8FuP|n!9%aV z7WWlD1z&S@bF@zu%OqvM1 z_vFtx;$f$-Dc99kz$@OWgLsXW zJ+-MdWh6|n-UDY^&N!WJBky6ijyX2)8+#7UIGvsoV1~yZwCGdLJL)+BWPgh(=XLro z5MYft_@L8s0>EnT>6KQY(>q^5q}EVAM?U-;tc_6@2h8GXP9(lG#^(pEW^ee~Cq|Dr zRGfzdnDohH?h75TONIo}aN(r*N_pR-^ra5m6OeiQ3tu7;Cl9pjxf8`pZ~+EBcn}Bt z@}(2?ks~2nOsi0P<@-oP2!9B!seJ*>!$XUY3B2bUue~tdA^rm8Zp0f#Yexd03aF37 zxW{%CCUMadOe1kdV6*rq2>y9ie)b2`36|NIB2FimIcYkb286QTGXmE_6@LLAhp=7QZGzyq zE~p5&HnH7wMgj>yOCV!#N~7|@ek9;)J}9yfG(I4~02YE~754UfCN)8Ks$0J4(h~R@ zi4p@@YYDnj-R7xGOK?2d#`XiQ5YQ5&RXInHpG?mZNDN4aa*9A=fDlZ3p%4fFBUtuA zC4hWB0Ox#=0SG}w&@g|?`@No#{5F`HH$)q?G*q3 N002ovPDHLkV1is8!yo_v