Merge branch 'master' of https://github.com/PolarisSS13/Polaris into woodrat_map

This commit is contained in:
Neerti
2021-06-27 14:01:01 -04:00
466 changed files with 13242 additions and 14329 deletions

View File

@@ -24,6 +24,34 @@ jobs:
tools/ci/validate_files.sh
tools/ci/build_tgui.sh
dreamchecker:
name: DreamChecker
runs-on: ubuntu-18.04
steps:
- uses: actions/checkout@v2
- name: Cache SpacemanDMM
uses: actions/cache@v2
with:
path: ~/SpacemanDMM
key: ${{ runner.os }}-dreamchecker-${{ hashFiles('dependencies.sh')}}
restore-keys: ${{ runner.os }}-dreamchecker
- name: Install Dependencies
run: |
tools/ci/install_spaceman_dmm.sh dreamchecker
- name: Run Linter
id: linter
run: |
~/dreamchecker > ${GITHUB_WORKSPACE}/output-annotations.txt 2>&1
- name: Annotate Linter
uses: yogstation13/DreamAnnotate@v1
if: always()
with:
outputFile: output-annotations.txt
unit_tests:
name: Integration Tests
runs-on: ubuntu-18.04

View File

@@ -1,8 +1,6 @@
[diagnostics]
macro_redefined = "off"
macro_undefined_no_definition = "off"
as_local_var = "off"
tmp_no_effect = "off"
[langserver]
dreamchecker = true
[code_standards]
disallow_relative_type_definitions = true
disallow_relative_proc_definitions = true

View File

@@ -1,6 +1,6 @@
# This file has all the information on what versions of libraries are thrown into the code
# For dreamchecker
export SPACEMANDMM_TAG=suite-1.4
export SPACEMAN_DMM_VERSION=suite-1.7
# For NanoUI + TGUI
export NODE_VERSION=12
# Byond Major

View File

@@ -1,8 +1,5 @@
//node1, air1, network1 correspond to input
//node2, air2, network2 correspond to output
#define ADIABATIC_EXPONENT 0.667 //Actually adiabatic exponent - 1.
/obj/machinery/atmospherics/binary/circulator
name = "circulator"
desc = "A gas circulator turbine and heat exchanger."

View File

@@ -1,288 +0,0 @@
#define ADIABATIC_EXPONENT 0.667 //Actually adiabatic exponent - 1.
/obj/machinery/atmospherics/pipeturbine
name = "turbine"
desc = "A gas turbine. Converting pressure into energy since 1884."
icon = 'icons/obj/pipeturbine.dmi'
icon_state = "turbine"
anchored = 0
density = 1
var/efficiency = 0.4
var/kin_energy = 0
var/datum/gas_mixture/air_in = new
var/datum/gas_mixture/air_out = new
var/volume_ratio = 0.2
var/kin_loss = 0.001
var/dP = 0
var/datum/pipe_network/network1
var/datum/pipe_network/network2
/obj/machinery/atmospherics/pipeturbine/New()
..()
air_in.volume = 200
air_out.volume = 800
volume_ratio = air_in.volume / (air_in.volume + air_out.volume)
switch(dir)
if(NORTH)
initialize_directions = EAST|WEST
if(SOUTH)
initialize_directions = EAST|WEST
if(EAST)
initialize_directions = NORTH|SOUTH
if(WEST)
initialize_directions = NORTH|SOUTH
/obj/machinery/atmospherics/pipeturbine/Destroy()
. = ..()
if(node1)
node1.disconnect(src)
qdel(network1)
if(node2)
node2.disconnect(src)
qdel(network2)
node1 = null
node2 = null
/obj/machinery/atmospherics/pipeturbine/process()
..()
if(anchored && !(stat&BROKEN))
kin_energy *= 1 - kin_loss
dP = max(air_in.return_pressure() - air_out.return_pressure(), 0)
if(dP > 10)
kin_energy += 1/ADIABATIC_EXPONENT * dP * air_in.volume * (1 - volume_ratio**ADIABATIC_EXPONENT) * efficiency
air_in.temperature *= volume_ratio**ADIABATIC_EXPONENT
var/datum/gas_mixture/air_all = new
air_all.volume = air_in.volume + air_out.volume
air_all.merge(air_in.remove_ratio(1))
air_all.merge(air_out.remove_ratio(1))
air_in.merge(air_all.remove(volume_ratio))
air_out.merge(air_all)
update_icon()
if (network1)
network1.update = 1
if (network2)
network2.update = 1
/obj/machinery/atmospherics/pipeturbine/update_icon()
overlays.Cut()
if (dP > 10)
overlays += image('icons/obj/pipeturbine.dmi', "moto-turb")
if (kin_energy > 100000)
overlays += image('icons/obj/pipeturbine.dmi', "low-turb")
if (kin_energy > 500000)
overlays += image('icons/obj/pipeturbine.dmi', "med-turb")
if (kin_energy > 1000000)
overlays += image('icons/obj/pipeturbine.dmi', "hi-turb")
/obj/machinery/atmospherics/pipeturbine/attackby(obj/item/weapon/W as obj, mob/user as mob)
if(W.is_wrench())
anchored = !anchored
playsound(src, W.usesound, 50, 1)
to_chat(user, "<span class='notice'>You [anchored ? "secure" : "unsecure"] the bolts holding \the [src] to the floor.</span>")
if(anchored)
if(dir & (NORTH|SOUTH))
initialize_directions = EAST|WEST
else if(dir & (EAST|WEST))
initialize_directions = NORTH|SOUTH
atmos_init()
build_network()
if (node1)
node1.atmos_init()
node1.build_network()
if (node2)
node2.atmos_init()
node2.build_network()
else
if(node1)
node1.disconnect(src)
qdel(network1)
if(node2)
node2.disconnect(src)
qdel(network2)
node1 = null
node2 = null
return
..()
/obj/machinery/atmospherics/pipeturbine/verb/rotate_clockwise()
set name = "Rotate Turbine Clockwise"
set category = "Object"
set src in view(1)
if (usr.stat || usr.restrained() || anchored)
return
src.set_dir(turn(src.dir, 270))
/obj/machinery/atmospherics/pipeturbine/verb/rotate_counterclockwise()
set name = "Rotate Turbine Counterclockwise"
set category = "Object"
set src in view(1)
if (usr.stat || usr.restrained() || anchored)
return
src.set_dir(turn(src.dir, 90))
//Goddamn copypaste from binary base class because atmospherics machinery API is not damn flexible
/obj/machinery/atmospherics/pipeturbine/get_neighbor_nodes_for_init()
return list(node1, node2)
/obj/machinery/atmospherics/pipeturbine/network_expand(datum/pipe_network/new_network, obj/machinery/atmospherics/pipe/reference)
if(reference == node1)
network1 = new_network
else if(reference == node2)
network2 = new_network
if(new_network.normal_members.Find(src))
return 0
new_network.normal_members += src
return null
/obj/machinery/atmospherics/pipeturbine/atmos_init()
if(node1 && node2)
return
var/node2_connect = turn(dir, -90)
var/node1_connect = turn(dir, 90)
for(var/obj/machinery/atmospherics/target in get_step(src,node1_connect))
if(target.initialize_directions & get_dir(target,src))
node1 = target
break
for(var/obj/machinery/atmospherics/target in get_step(src,node2_connect))
if(target.initialize_directions & get_dir(target,src))
node2 = target
break
/obj/machinery/atmospherics/pipeturbine/build_network()
if(!network1 && node1)
network1 = new /datum/pipe_network()
network1.normal_members += src
network1.build_network(node1, src)
if(!network2 && node2)
network2 = new /datum/pipe_network()
network2.normal_members += src
network2.build_network(node2, src)
/obj/machinery/atmospherics/pipeturbine/return_network(obj/machinery/atmospherics/reference)
build_network()
if(reference==node1)
return network1
if(reference==node2)
return network2
return null
/obj/machinery/atmospherics/pipeturbine/reassign_network(datum/pipe_network/old_network, datum/pipe_network/new_network)
if(network1 == old_network)
network1 = new_network
if(network2 == old_network)
network2 = new_network
return 1
/obj/machinery/atmospherics/pipeturbine/return_network_air(datum/pipe_network/reference)
var/list/results = list()
if(network1 == reference)
results += air_in
if(network2 == reference)
results += air_out
return results
/obj/machinery/atmospherics/pipeturbine/disconnect(obj/machinery/atmospherics/reference)
if(reference==node1)
qdel(network1)
node1 = null
else if(reference==node2)
qdel(network2)
node2 = null
return null
/obj/machinery/power/turbinemotor
name = "motor"
desc = "Electrogenerator. Converts rotation into power."
icon = 'icons/obj/pipeturbine.dmi'
icon_state = "motor"
anchored = 0
density = 1
var/kin_to_el_ratio = 0.1 //How much kinetic energy will be taken from turbine and converted into electricity
var/obj/machinery/atmospherics/pipeturbine/turbine
/obj/machinery/power/turbinemotor/Initialize()
. = ..()
updateConnection()
/obj/machinery/power/turbinemotor/proc/updateConnection()
turbine = null
if(src.loc && anchored)
turbine = locate(/obj/machinery/atmospherics/pipeturbine) in get_step(src,dir)
if (turbine.stat & (BROKEN) || !turbine.anchored || turn(turbine.dir,180) != dir)
turbine = null
/obj/machinery/power/turbinemotor/process()
updateConnection()
if(!turbine || !anchored || stat & (BROKEN))
return
var/power_generated = kin_to_el_ratio * turbine.kin_energy
turbine.kin_energy -= power_generated
add_avail(power_generated)
/obj/machinery/power/turbinemotor/attackby(obj/item/weapon/W as obj, mob/user as mob)
if(W.is_wrench())
anchored = !anchored
playsound(src, W.usesound, 50, 1)
turbine = null
to_chat(user, "<span class='notice'>You [anchored ? "secure" : "unsecure"] the bolts holding \the [src] to the floor.</span>")
updateConnection()
else
..()
/obj/machinery/power/turbinemotor/verb/rotate_clockwise()
set name = "Rotate Motor Clockwise"
set category = "Object"
set src in view(1)
if (usr.stat || usr.restrained() || anchored)
return
src.set_dir(turn(src.dir, 270))
/obj/machinery/power/turbinemotor/verb/rotate_counterclockwise()
set name = "Rotate Motor Counterclockwise"
set category = "Object"
set src in view(1)
if (usr.stat || usr.restrained() || anchored)
return
src.set_dir(turn(src.dir, 90))

View File

@@ -163,7 +163,7 @@
//
// "T" Orientation - Inputs are on oposite sides instead of adjacent
//
obj/machinery/atmospherics/trinary/mixer/t_mixer
/obj/machinery/atmospherics/trinary/mixer/t_mixer
icon_state = "tmap"
construction_type = /obj/item/pipe/trinary // Can't flip a "T", its symmetrical
pipe_state = "t_mixer"

View File

@@ -1,21 +0,0 @@
/obj/machinery/atmospherics/unary/generator_input
icon = 'icons/obj/atmospherics/heat_exchanger.dmi'
icon_state = "intact"
density = 1
name = "Generator Input"
desc = "Placeholder"
var/update_cycle
update_icon()
if(node)
icon_state = "intact"
else
icon_state = "exposed"
return
proc
return_exchange_air()
return air_contents

View File

@@ -11,7 +11,7 @@
var/obj/machinery/atmospherics/unary/heat_exchanger/partner = null
var/update_cycle
update_icon()
/obj/machinery/atmospherics/unary/heat_exchanger/update_icon()
if(node)
icon_state = "intact"
else
@@ -19,7 +19,7 @@
return
atmos_init()
/obj/machinery/atmospherics/unary/heat_exchanger/atmos_init()
if(!partner)
var/partner_connect = turn(dir,180)
@@ -31,7 +31,7 @@
..()
process()
/obj/machinery/atmospherics/unary/heat_exchanger/process()
..()
if(!partner)
return 0
@@ -66,7 +66,7 @@
return 1
attackby(var/obj/item/weapon/W as obj, var/mob/user as mob)
/obj/machinery/atmospherics/unary/heat_exchanger/attackby(var/obj/item/weapon/W as obj, var/mob/user as mob)
if (!W.is_wrench())
return ..()
var/turf/T = src.loc

View File

@@ -1,49 +0,0 @@
obj/machinery/atmospherics/unary/oxygen_generator
icon = 'icons/obj/atmospherics/oxygen_generator.dmi'
icon_state = "intact_off"
density = 1
name = "Oxygen Generator"
desc = ""
dir = SOUTH
initialize_directions = SOUTH
var/on = 0
var/oxygen_content = 10
update_icon()
if(node)
icon_state = "intact_[on?("on"):("off")]"
else
icon_state = "exposed_off"
on = 0
return
New()
..()
air_contents.volume = 50
process()
..()
if(!on)
return 0
var/total_moles = air_contents.total_moles
if(total_moles < oxygen_content)
var/current_heat_capacity = air_contents.heat_capacity()
var/added_oxygen = oxygen_content - total_moles
air_contents.temperature = (current_heat_capacity*air_contents.temperature + 20*added_oxygen*T0C)/(current_heat_capacity+20*added_oxygen)
air_contents.adjust_gas("oxygen", added_oxygen)
if(network)
network.update = 1
return 1

View File

@@ -1,708 +0,0 @@
// internal pipe, don't actually place or use these
obj/machinery/atmospherics/pipe/mains_component
var/obj/machinery/atmospherics/mains_pipe/parent_pipe
var/list/obj/machinery/atmospherics/pipe/mains_component/nodes = new()
New(loc)
..(loc)
parent_pipe = loc
check_pressure(pressure)
var/datum/gas_mixture/environment = loc.loc.return_air()
var/pressure_difference = pressure - environment.return_pressure()
if(pressure_difference > parent_pipe.maximum_pressure)
mains_burst()
else if(pressure_difference > parent_pipe.fatigue_pressure)
//TODO: leak to turf, doing pfshhhhh
if(prob(5))
mains_burst()
else return 1
pipeline_expansion()
return nodes
disconnect(obj/machinery/atmospherics/reference)
if(nodes.Find(reference))
nodes.Remove(reference)
proc/mains_burst()
parent_pipe.burst()
obj/machinery/atmospherics/mains_pipe
icon = 'icons/obj/atmospherics/mainspipe.dmi'
layer = PIPES_LAYER
plane = PLATING_PLANE
var/volume = 0
var/alert_pressure = 80*ONE_ATMOSPHERE
var/initialize_mains_directions = 0
var/list/obj/machinery/atmospherics/mains_pipe/nodes = new()
var/obj/machinery/atmospherics/pipe/mains_component/supply
var/obj/machinery/atmospherics/pipe/mains_component/scrubbers
var/obj/machinery/atmospherics/pipe/mains_component/aux
var/minimum_temperature_difference = 300
var/thermal_conductivity = 0 //WALL_HEAT_TRANSFER_COEFFICIENT No
var/maximum_pressure = 70*ONE_ATMOSPHERE
var/fatigue_pressure = 55*ONE_ATMOSPHERE
alert_pressure = 55*ONE_ATMOSPHERE
New()
..()
supply = new(src)
supply.volume = volume
supply.nodes.len = nodes.len
scrubbers = new(src)
scrubbers.volume = volume
scrubbers.nodes.len = nodes.len
aux = new(src)
aux.volume = volume
aux.nodes.len = nodes.len
hide(var/i)
if(level == 1 && istype(loc, /turf/simulated))
invisibility = i ? 101 : 0
update_icon()
proc/burst()
for(var/obj/machinery/atmospherics/pipe/mains_component/pipe in contents)
burst()
proc/check_pressure(pressure)
var/datum/gas_mixture/environment = loc.return_air()
var/pressure_difference = pressure - environment.return_pressure()
if(pressure_difference > maximum_pressure)
burst()
else if(pressure_difference > fatigue_pressure)
//TODO: leak to turf, doing pfshhhhh
if(prob(5))
burst()
else return 1
get_neighbor_nodes_for_init()
return nodes
disconnect()
..()
for(var/obj/machinery/atmospherics/pipe/mains_component/node in nodes)
node.disconnect()
Destroy()
disconnect()
..()
atmos_init()
for(var/i = 1 to nodes.len)
var/obj/machinery/atmospherics/mains_pipe/node = nodes[i]
if(node)
supply.nodes[i] = node.supply
scrubbers.nodes[i] = node.scrubbers
aux.nodes[i] = node.aux
obj/machinery/atmospherics/mains_pipe/simple
name = "mains pipe"
desc = "A one meter section of 3-line mains pipe"
dir = SOUTH
initialize_mains_directions = SOUTH|NORTH
New()
nodes.len = 2
..()
switch(dir)
if(SOUTH || NORTH)
initialize_mains_directions = SOUTH|NORTH
if(EAST || WEST)
initialize_mains_directions = EAST|WEST
if(NORTHEAST)
initialize_mains_directions = NORTH|EAST
if(NORTHWEST)
initialize_mains_directions = NORTH|WEST
if(SOUTHEAST)
initialize_mains_directions = SOUTH|EAST
if(SOUTHWEST)
initialize_mains_directions = SOUTH|WEST
proc/normalize_dir()
if(dir==3)
set_dir(1)
else if(dir==12)
set_dir(4)
update_icon()
if(nodes[1] && nodes[2])
icon_state = "intact[invisibility ? "-f" : "" ]"
//var/node1_direction = get_dir(src, node1)
//var/node2_direction = get_dir(src, node2)
//set_dir(node1_direction|node2_direction)
else
if(!nodes[1]&&!nodes[2])
qdel(src) //TODO: silent deleting looks weird
var/have_node1 = nodes[1]?1:0
var/have_node2 = nodes[2]?1:0
icon_state = "exposed[have_node1][have_node2][invisibility ? "-f" : "" ]"
atmos_init()
normalize_dir()
var/node1_dir
var/node2_dir
for(var/direction in cardinal)
if(direction&initialize_mains_directions)
if (!node1_dir)
node1_dir = direction
else if (!node2_dir)
node2_dir = direction
for(var/obj/machinery/atmospherics/mains_pipe/target in get_step(src,node1_dir))
if(target.initialize_mains_directions & get_dir(target,src))
nodes[1] = target
break
for(var/obj/machinery/atmospherics/mains_pipe/target in get_step(src,node2_dir))
if(target.initialize_mains_directions & get_dir(target,src))
nodes[2] = target
break
..() // initialize internal pipes
var/turf/T = src.loc // hide if turf is not intact
if(level == 1 && !T.is_plating()) hide(1)
update_icon()
hidden
level = 1
icon_state = "intact-f"
visible
level = 2
icon_state = "intact"
obj/machinery/atmospherics/mains_pipe/manifold
name = "manifold pipe"
desc = "A manifold composed of mains pipes"
dir = SOUTH
initialize_mains_directions = EAST|NORTH|WEST
volume = 105
New()
nodes.len = 3
..()
initialize_mains_directions = (NORTH|SOUTH|EAST|WEST) & ~dir
atmos_init()
var/connect_directions = initialize_mains_directions
for(var/direction in cardinal)
if(direction&connect_directions)
for(var/obj/machinery/atmospherics/mains_pipe/target in get_step(src,direction))
if(target.initialize_mains_directions & get_dir(target,src))
nodes[1] = target
connect_directions &= ~direction
break
if (nodes[1])
break
for(var/direction in cardinal)
if(direction&connect_directions)
for(var/obj/machinery/atmospherics/mains_pipe/target in get_step(src,direction))
if(target.initialize_mains_directions & get_dir(target,src))
nodes[2] = target
connect_directions &= ~direction
break
if (nodes[2])
break
for(var/direction in cardinal)
if(direction&connect_directions)
for(var/obj/machinery/atmospherics/mains_pipe/target in get_step(src,direction))
if(target.initialize_mains_directions & get_dir(target,src))
nodes[3] = target
connect_directions &= ~direction
break
if (nodes[3])
break
..() // initialize internal pipes
var/turf/T = src.loc // hide if turf is not intact
if(level == 1 && !T.is_plating()) hide(1)
update_icon()
update_icon()
icon_state = "manifold[invisibility ? "-f" : "" ]"
hidden
level = 1
icon_state = "manifold-f"
visible
level = 2
icon_state = "manifold"
obj/machinery/atmospherics/mains_pipe/manifold4w
name = "manifold pipe"
desc = "A manifold composed of mains pipes"
dir = SOUTH
initialize_mains_directions = EAST|NORTH|WEST|SOUTH
volume = 105
New()
nodes.len = 4
..()
atmos_init()
for(var/obj/machinery/atmospherics/mains_pipe/target in get_step(src,NORTH))
if(target.initialize_mains_directions & get_dir(target,src))
nodes[1] = target
break
for(var/obj/machinery/atmospherics/mains_pipe/target in get_step(src,SOUTH))
if(target.initialize_mains_directions & get_dir(target,src))
nodes[2] = target
break
for(var/obj/machinery/atmospherics/mains_pipe/target in get_step(src,EAST))
if(target.initialize_mains_directions & get_dir(target,src))
nodes[3] = target
break
for(var/obj/machinery/atmospherics/mains_pipe/target in get_step(src,WEST))
if(target.initialize_mains_directions & get_dir(target,src))
nodes[3] = target
break
..() // initialize internal pipes
var/turf/T = src.loc // hide if turf is not intact
if(level == 1 && !T.is_plating()) hide(1)
update_icon()
update_icon()
icon_state = "manifold4w[invisibility ? "-f" : "" ]"
hidden
level = 1
icon_state = "manifold4w-f"
visible
level = 2
icon_state = "manifold4w"
obj/machinery/atmospherics/mains_pipe/split
name = "mains splitter"
desc = "A splitter for connecting to a single pipe off a mains."
var/obj/machinery/atmospherics/pipe/mains_component/split_node
var/obj/machinery/atmospherics/node3
var/icon_type
New()
nodes.len = 2
..()
initialize_mains_directions = turn(dir, 90) | turn(dir, -90)
initialize_directions = dir // actually have a normal connection too
atmos_init()
var/node1_dir
var/node2_dir
var/node3_dir
node1_dir = turn(dir, 90)
node2_dir = turn(dir, -90)
node3_dir = dir
for(var/obj/machinery/atmospherics/mains_pipe/target in get_step(src,node1_dir))
if(target.initialize_mains_directions & get_dir(target,src))
nodes[1] = target
break
for(var/obj/machinery/atmospherics/mains_pipe/target in get_step(src,node2_dir))
if(target.initialize_mains_directions & get_dir(target,src))
nodes[2] = target
break
for(var/obj/machinery/atmospherics/target in get_step(src,node3_dir))
if(target.initialize_directions & get_dir(target,src))
node3 = target
break
..() // initialize internal pipes
// bind them
spawn(5)
if(node3 && split_node)
var/datum/pipe_network/N1 = node3.return_network(src)
var/datum/pipe_network/N2 = split_node.return_network(split_node)
if(N1 && N2)
N1.merge(N2)
var/turf/T = src.loc // hide if turf is not intact
if(level == 1 && !T.is_plating()) hide(1)
update_icon()
update_icon()
icon_state = "split-[icon_type][invisibility ? "-f" : "" ]"
return_network(A)
return split_node.return_network(A)
supply
icon_type = "supply"
New()
..()
split_node = supply
hidden
level = 1
icon_state = "split-supply-f"
visible
level = 2
icon_state = "split-supply"
scrubbers
icon_type = "scrubbers"
New()
..()
split_node = scrubbers
hidden
level = 1
icon_state = "split-scrubbers-f"
visible
level = 2
icon_state = "split-scrubbers"
aux
icon_type = "aux"
New()
..()
split_node = aux
hidden
level = 1
icon_state = "split-aux-f"
visible
level = 2
icon_state = "split-aux"
obj/machinery/atmospherics/mains_pipe/split3
name = "triple mains splitter"
desc = "A splitter for connecting to the 3 pipes on a mainline."
var/obj/machinery/atmospherics/supply_node
var/obj/machinery/atmospherics/scrubbers_node
var/obj/machinery/atmospherics/aux_node
New()
nodes.len = 1
..()
initialize_mains_directions = dir
initialize_directions = cardinal & ~dir // actually have a normal connection too
atmos_init()
var/node1_dir
var/supply_node_dir
var/scrubbers_node_dir
var/aux_node_dir
node1_dir = dir
aux_node_dir = turn(dir, 180)
if(dir & (NORTH|SOUTH))
supply_node_dir = EAST
scrubbers_node_dir = WEST
else
supply_node_dir = SOUTH
scrubbers_node_dir = NORTH
for(var/obj/machinery/atmospherics/mains_pipe/target in get_step(src, node1_dir))
if(target.initialize_mains_directions & get_dir(target,src))
nodes[1] = target
break
for(var/obj/machinery/atmospherics/target in get_step(src,supply_node_dir))
if(target.initialize_directions & get_dir(target,src))
supply_node = target
break
for(var/obj/machinery/atmospherics/target in get_step(src,scrubbers_node_dir))
if(target.initialize_directions & get_dir(target,src))
scrubbers_node = target
break
for(var/obj/machinery/atmospherics/target in get_step(src,aux_node_dir))
if(target.initialize_directions & get_dir(target,src))
aux_node = target
break
..() // initialize internal pipes
// bind them
spawn(5)
if(supply_node)
var/datum/pipe_network/N1 = supply_node.return_network(src)
var/datum/pipe_network/N2 = supply.return_network(supply)
if(N1 && N2)
N1.merge(N2)
if(scrubbers_node)
var/datum/pipe_network/N1 = scrubbers_node.return_network(src)
var/datum/pipe_network/N2 = scrubbers.return_network(scrubbers)
if(N1 && N2)
N1.merge(N2)
if(aux_node)
var/datum/pipe_network/N1 = aux_node.return_network(src)
var/datum/pipe_network/N2 = aux.return_network(aux)
if(N1 && N2)
N1.merge(N2)
var/turf/T = src.loc // hide if turf is not intact
if(level == 1 && !T.is_plating()) hide(1)
update_icon()
update_icon()
icon_state = "split-t[invisibility ? "-f" : "" ]"
return_network(obj/machinery/atmospherics/reference)
var/obj/machinery/atmospherics/A
A = supply_node.return_network(reference)
if(!A)
A = scrubbers_node.return_network(reference)
if(!A)
A = aux_node.return_network(reference)
return A
hidden
level = 1
icon_state = "split-t-f"
visible
level = 2
icon_state = "split-t"
obj/machinery/atmospherics/mains_pipe/cap
name = "pipe cap"
desc = "A cap for the end of a mains pipe"
dir = SOUTH
initialize_directions = SOUTH
volume = 35
New()
nodes.len = 1
..()
initialize_mains_directions = dir
update_icon()
icon_state = "cap[invisibility ? "-f" : ""]"
atmos_init()
for(var/obj/machinery/atmospherics/mains_pipe/target in get_step(src,dir))
if(target.initialize_mains_directions & get_dir(target,src))
nodes[1] = target
break
..()
var/turf/T = src.loc // hide if turf is not intact
if(level == 1 && !T.is_plating()) hide(1)
update_icon()
hidden
level = 1
icon_state = "cap-f"
visible
level = 2
icon_state = "cap"
//TODO: Get Mains valves working!
/*
obj/machinery/atmospherics/mains_pipe/valve
icon_state = "mvalve0"
name = "mains shutoff valve"
desc = "A mains pipe valve"
var/open = 1
dir = SOUTH
initialize_mains_directions = SOUTH|NORTH
New()
nodes.len = 2
..()
initialize_mains_directions = dir | turn(dir, 180)
update_icon(animation)
var/turf/simulated/floor = loc
var/hide = istype(floor) ? floor.intact : 0
level = 1
for(var/obj/machinery/atmospherics/mains_pipe/node in nodes)
if(node.level == 2)
hide = 0
level = 2
break
if(animation)
flick("[hide?"h":""]mvalve[src.open][!src.open]",src)
else
icon_state = "[hide?"h":""]mvalve[open]"
initialize()
normalize_dir()
var/node1_dir
var/node2_dir
for(var/direction in cardinal)
if(direction&initialize_mains_directions)
if (!node1_dir)
node1_dir = direction
else if (!node2_dir)
node2_dir = direction
for(var/obj/machinery/atmospherics/mains_pipe/target in get_step(src,node1_dir))
if(target.initialize_mains_directions & get_dir(target,src))
nodes[1] = target
break
for(var/obj/machinery/atmospherics/mains_pipe/target in get_step(src,node2_dir))
if(target.initialize_mains_directions & get_dir(target,src))
nodes[2] = target
break
if(open)
..() // initialize internal pipes
update_icon()
proc/normalize_dir()
if(dir==3)
set_dir(1)
else if(dir==12)
set_dir(4)
proc/open()
if(open) return 0
open = 1
update_icon()
initialize()
return 1
proc/close()
if(!open) return 0
open = 0
update_icon()
for(var/obj/machinery/atmospherics/pipe/mains_component/node in src)
for(var/obj/machinery/atmospherics/pipe/mains_component/o in node.nodes)
o.disconnect(node)
o.build_network()
return 1
attack_ai(mob/user as mob)
return
attack_paw(mob/user as mob)
return attack_hand(user)
attack_hand(mob/user as mob)
src.add_fingerprint(usr)
update_icon(1)
sleep(10)
if (open)
close()
else
open()
digital // can be controlled by AI
name = "digital mains valve"
desc = "A digitally controlled valve."
icon_state = "dvalve0"
attack_ai(mob/user as mob)
return src.attack_hand(user)
attack_hand(mob/user as mob)
if(!src.allowed(user))
to_chat(user, "<span class='warning'>Access denied.</span>")
return
..()
//Radio remote control
proc
set_frequency(new_frequency)
radio_controller.remove_object(src, frequency)
frequency = new_frequency
if(frequency)
radio_connection = radio_controller.add_object(src, frequency, RADIO_ATMOSIA)
var/frequency = 0
var/id = null
var/datum/radio_frequency/radio_connection
initialize()
..()
if(frequency)
set_frequency(frequency)
update_icon(animation)
var/turf/simulated/floor = loc
var/hide = istype(floor) ? floor.intact : 0
level = 1
for(var/obj/machinery/atmospherics/mains_pipe/node in nodes)
if(node.level == 2)
hide = 0
level = 2
break
if(animation)
flick("[hide?"h":""]dvalve[src.open][!src.open]",src)
else
icon_state = "[hide?"h":""]dvalve[open]"
receive_signal(datum/signal/signal)
if(!signal.data["tag"] || (signal.data["tag"] != id))
return 0
switch(signal.data["command"])
if("valve_open")
if(!open)
open()
if("valve_close")
if(open)
close()
if("valve_toggle")
if(open)
close()
else
open()
*/

View File

@@ -2,8 +2,8 @@
Contains helper procs for airflow, handled in /connection_group.
*/
mob/var/tmp/last_airflow_stun = 0
mob/proc/airflow_stun()
/mob/var/tmp/last_airflow_stun = 0
/mob/proc/airflow_stun()
if(stat == 2)
return 0
if(last_airflow_stun > world.time - vsc.airflow_stun_cooldown) return 0
@@ -19,16 +19,16 @@ mob/proc/airflow_stun()
Weaken(5)
last_airflow_stun = world.time
mob/living/silicon/airflow_stun()
/mob/living/silicon/airflow_stun()
return
mob/living/carbon/human/airflow_stun()
/mob/living/carbon/human/airflow_stun()
if(shoes && (shoes.item_flags & NOSLIP))
to_chat(src, "<span class='notice'>Air suddenly rushes past you!</span>")
return 0
..()
atom/movable/proc/check_airflow_movable(n)
/atom/movable/proc/check_airflow_movable(n)
if(!simulated) return 0
if(anchored && !ismob(src)) return 0
@@ -37,19 +37,19 @@ atom/movable/proc/check_airflow_movable(n)
return 1
mob/check_airflow_movable(n)
/mob/check_airflow_movable(n)
if(n < vsc.airflow_heavy_pressure)
return 0
return 1
mob/observer/check_airflow_movable()
/mob/observer/check_airflow_movable()
return 0
mob/living/silicon/check_airflow_movable()
/mob/living/silicon/check_airflow_movable()
return 0
obj/check_airflow_movable(n)
/obj/check_airflow_movable(n)
if (!(. = ..()))
return 0
if(isnull(w_class))
@@ -90,11 +90,11 @@ obj/check_airflow_movable(n)
airflow_time = 0
. = ..()
atom/movable/proc/airflow_hit(atom/A)
/atom/movable/proc/airflow_hit(atom/A)
airflow_speed = 0
airflow_dest = null
mob/airflow_hit(atom/A)
/mob/airflow_hit(atom/A)
for(var/mob/M in hearers(src))
M.show_message("<span class='danger'>\The [src] slams into \a [A]!</span>",1,"<span class='danger'>You hear a loud slam!</span>",2)
playsound(src, "smash.ogg", 25, 1, -1)
@@ -102,17 +102,17 @@ mob/airflow_hit(atom/A)
Weaken(weak_amt)
. = ..()
obj/airflow_hit(atom/A)
/obj/airflow_hit(atom/A)
for(var/mob/M in hearers(src))
M.show_message("<span class='danger'>\The [src] slams into \a [A]!</span>",1,"<span class='danger'>You hear a loud slam!</span>",2)
playsound(src, "smash.ogg", 25, 1, -1)
. = ..()
obj/item/airflow_hit(atom/A)
/obj/item/airflow_hit(atom/A)
airflow_speed = 0
airflow_dest = null
mob/living/carbon/human/airflow_hit(atom/A)
/mob/living/carbon/human/airflow_hit(atom/A)
// for(var/mob/M in hearers(src))
// M.show_message("<span class='danger'>[src] slams into [A]!</span>",1,"<span class='danger'>You hear a loud slam!</span>",2)
playsound(src, "punch", 25, 1, -1)
@@ -140,7 +140,7 @@ mob/living/carbon/human/airflow_hit(atom/A)
Stun(round(airflow_speed * vsc.airflow_stun/2))
. = ..()
zone/proc/movables()
/zone/proc/movables()
. = list()
for(var/turf/T in contents)
for(var/atom/movable/A in T)

View File

@@ -64,13 +64,13 @@
// AIR_BLOCKED - Blocked
// ZONE_BLOCKED - Not blocked, but zone boundaries will not cross.
// BLOCKED - Blocked, zone boundaries will not cross even if opened.
atom/proc/c_airblock(turf/other)
/atom/proc/c_airblock(turf/other)
#ifdef ZASDBG
ASSERT(isturf(other))
#endif
return (AIR_BLOCKED*!CanZASPass(other, FALSE))|(ZONE_BLOCKED*!CanZASPass(other, TRUE))
turf/c_airblock(turf/other)
/turf/c_airblock(turf/other)
#ifdef ZASDBG
ASSERT(isturf(other))
#endif

View File

@@ -242,7 +242,7 @@ Class Procs:
if(!A.air.compare(air, vacuum_exception = 1))
air_master.mark_edge_active(src)
proc/ShareHeat(datum/gas_mixture/A, datum/gas_mixture/B, connecting_tiles)
/proc/ShareHeat(datum/gas_mixture/A, datum/gas_mixture/B, connecting_tiles)
//This implements a simplistic version of the Stefan-Boltzmann law.
var/energy_delta = ((A.temperature - B.temperature) ** 4) * STEFAN_BOLTZMANN_CONSTANT * connecting_tiles * 2.5
var/maximum_energy_delta = max(0, min(A.temperature * A.heat_capacity() * A.group_multiplier, B.temperature * B.heat_capacity() * B.group_multiplier))

View File

@@ -16,5 +16,5 @@ var/image/mark = image('icons/Testing/Zone.dmi', icon_state = "mark")
overlays += img
dbg_img = img
proc/soft_assert(thing,fail)
/proc/soft_assert(thing,fail)
if(!thing) message_admins(fail)

View File

@@ -1,4 +1,4 @@
client/proc/ZoneTick()
/client/proc/ZoneTick()
set category = "Debug"
set name = "Process Atmos"
set desc = "Manually run a single tick of the air subsystem"
@@ -16,7 +16,7 @@ client/proc/ZoneTick()
to_chat(src, "Failed to process! ([air_master.tick_progress])")
*/
client/proc/Zone_Info(turf/T as null|turf)
/client/proc/Zone_Info(turf/T as null|turf)
set category = "Debug"
if(T)
if(istype(T,/turf/simulated) && T:zone)
@@ -33,9 +33,9 @@ client/proc/Zone_Info(turf/T as null|turf)
images -= zone_debug_images[zone]
zone_debug_images = null
client/var/list/zone_debug_images
/client/var/list/zone_debug_images
client/proc/Test_ZAS_Connection(var/turf/simulated/T as turf)
/client/proc/Test_ZAS_Connection(var/turf/simulated/T as turf)
set category = "Debug"
if(!istype(T))
return
@@ -94,7 +94,7 @@ client/proc/Test_ZAS_Connection(var/turf/simulated/T as turf)
else
to_chat(mob, "both turfs can merge.")
client/proc/ZASSettings()
/client/proc/ZASSettings()
set category = "Debug"
vsc.SetDefault(mob)

View File

@@ -11,11 +11,11 @@ If it gains pressure too slowly, it may leak or just rupture instead of explodin
/turf/var/obj/fire/fire = null
//Some legacy definitions so fires can be started.
atom/proc/temperature_expose(datum/gas_mixture/air, exposed_temperature, exposed_volume)
/atom/proc/temperature_expose(datum/gas_mixture/air, exposed_temperature, exposed_volume)
return null
turf/proc/hotspot_expose(exposed_temperature, exposed_volume, soh = 0)
/turf/proc/hotspot_expose(exposed_temperature, exposed_volume, soh = 0)
/turf/simulated/hotspot_expose(exposed_temperature, exposed_volume, soh)
@@ -320,7 +320,7 @@ turf/proc/hotspot_expose(exposed_temperature, exposed_volume, soh = 0)
return firelevel
datum/gas_mixture/proc/check_recombustability(list/fuel_objs)
/datum/gas_mixture/proc/check_recombustability(list/fuel_objs)
. = 0
for(var/g in gas)
if(gas_data.flags[g] & XGM_GAS_OXIDIZER && gas[g] >= 0.1)

View File

@@ -38,7 +38,7 @@ var/image/contamination_overlay = image('icons/effects/contamination.dmi')
var/N2O_HALLUCINATION_DESC = "Does being in sleeping gas cause you to hallucinate?"
obj/var/contaminated = 0
/obj/var/contaminated = 0
/obj/item/proc/can_contaminate()
@@ -173,7 +173,7 @@ obj/var/contaminated = 0
gloves.contaminate()
turf/Entered(obj/item/I)
/turf/Entered(obj/item/I)
. = ..()
//Items that are in phoron, but not on a mob, can still be contaminated.
if(istype(I) && vsc.plc.CLOTH_CONTAMINATION && I.can_contaminate())

View File

@@ -39,7 +39,7 @@
#define LAZYACCESSASSOC(L, I, K) L ? L[I] ? L[I][K] ? L[I][K] : null : null : null
// Null-safe L.Cut()
#define LAZYCLEARLIST(L) if(L) L.Cut()
#define LAZYCLEARLIST(L) if(L) { L.Cut(); L = null; }
// Reads L or an empty list if L is not a list. Note: Does NOT assign, L may be an expression.
#define SANITIZE_LIST(L) ( islist(L) ? L : list() )

View File

@@ -94,6 +94,8 @@ What is the naming convention for planes or layers?
#define BELOW_MOB_LAYER 3.9 // Should be converted to plane swaps
#define ABOVE_MOB_LAYER 4.1 // Should be converted to plane swaps
#define ABOVE_MOB_PLANE -24
// Invisible things plane
#define CLOAKED_PLANE -15
@@ -123,6 +125,7 @@ What is the naming convention for planes or layers?
#define PLANE_PLANETLIGHTING 4 //Lighting on planets
#define PLANE_LIGHTING 5 //Where the lighting (and darkness) lives
#define PLANE_LIGHTING_ABOVE 6 //For glowy eyes etc. that shouldn't be affected by darkness
#define PLANE_RUNECHAT 7
#define PLANE_GHOSTS 10 //Spooooooooky ghooooooosts
#define PLANE_AI_EYE 11 //The AI eye lives here
@@ -154,6 +157,9 @@ What is the naming convention for planes or layers?
#define CRIT_LAYER 18.3
//Client UI HUD stuff
#define PLANE_HOLOMAP_FRAME 92
#define PLANE_HOLOMAP 93 // Holomap rendered here
#define PLANE_HOLOMAP_ICONS 94 // Holomap markers and bobbins
#define PLANE_PLAYER_HUD 95 //The character's UI is on this plane
#define LAYER_HUD_UNDER 1 //Under the HUD items
#define LAYER_HUD_BASE 2 //The HUD items themselves

View File

@@ -94,3 +94,7 @@
#define ATMOSTANK_CO2 25000 // CO2 and PH are not critically important for station, only for toxins and alternative coolants, no need to store a lot of those.
#define ATMOSTANK_PHORON 25000
#define ATMOSTANK_NITROUSOXIDE 10000 // N2O doesn't have a real useful use, i guess it's on station just to allow refilling of sec's riot control canisters?
// Used in various things like tanks and oxygen pumps.
#define TANK_MAX_RELEASE_PRESSURE (3*ONE_ATMOSPHERE)
#define TANK_DEFAULT_RELEASE_PRESSURE ONE_ATMOSPHERE

View File

@@ -163,9 +163,6 @@
#define COLOR_ASSEMBLY_PURPLE "#6F6192"
#define COLOR_ASSEMBLY_HOT_PINK "#FF69B4"
#define COLOR_ASTEROID_ROCK "#735555"
#define COLOR_GOLD "#ffcc33"
// Discord requires colors to be in decimal instead of hexadecimal.
#define COLOR_WEBHOOK_DEFAULT 0x8bbbd5 // "#8bbbd5"
#define COLOR_WEBHOOK_GOOD 0x2ECC71 // "#2ECC71"

View File

@@ -50,7 +50,6 @@
#define PIPING_LAYER_DEFAULT PIPING_LAYER_REGULAR
// We offset the layer values of the different pipe types to ensure they look nice
#define PIPES_SCRUBBER_LAYER (PIPES_LAYER - 0.05)
#define PIPES_AUX_LAYER (PIPES_LAYER - 0.04)
#define PIPES_FUEL_LAYER (PIPES_LAYER - 0.03)
#define PIPES_SCRUBBER_LAYER (PIPES_LAYER - 0.02)

View File

@@ -91,7 +91,6 @@ var/list/be_special_flags = list(
#define MODE_MONKEY "monkey"
#define MODE_RENEGADE "renegade"
#define MODE_REVOLUTIONARY "revolutionary"
#define MODE_LOYALIST "loyalist"
#define MODE_MALFUNCTION "malf"
#define MODE_TRAITOR "traitor"
#define MODE_AUTOTRAITOR "autotraitor"
@@ -140,3 +139,27 @@ var/list/be_special_flags = list(
#define Sp_HOLDVAR "holdervar"
#define CHANGELING_STASIS_COST 20
//Spell stuff, for Technomancer and Cult.
//cast_method flags
#define CAST_USE 1 // Clicking the spell in your hand.
#define CAST_MELEE 2 // Clicking an atom in melee range.
#define CAST_RANGED 4 // Clicking an atom beyond melee range.
#define CAST_THROW 8 // Throwing the spell and hitting an atom.
#define CAST_COMBINE 16 // Clicking another spell with this spell.
#define CAST_INNATE 32 // Activates upon verb usage, used for mobs without hands.
//Aspects
#define ASPECT_FIRE "fire" //Damage over time and raising body-temp. Firesuits protect from this.
#define ASPECT_FROST "frost" //Slows down the affected, also involves imbedding with icicles. Winter coats protect from this.
#define ASPECT_SHOCK "shock" //Energy-expensive, usually stuns. Insulated armor protects from this.
#define ASPECT_AIR "air" //Mostly involves manipulation of atmos, useless in a vacuum. Magboots protect from this.
#define ASPECT_FORCE "force" //Manipulates gravity to push things away or towards a location.
#define ASPECT_TELE "tele" //Teleportation of self, other objects, or other people.
#define ASPECT_DARK "dark" //Makes all those photons vanish using magic-- WITH SCIENCE. Used for sneaky stuff.
#define ASPECT_LIGHT "light" //The opposite of dark, usually blinds, makes holo-illusions, or makes laser lightshows.
#define ASPECT_BIOMED "biomed" //Mainly concerned with healing and restoration.
#define ASPECT_EMP "emp" //Unused now.
#define ASPECT_UNSTABLE "unstable" //Heavily RNG-based, causes instability to the victim.
#define ASPECT_CHROMATIC "chromatic" //Used to combine with other spells.
#define ASPECT_UNHOLY "unholy" //Involves the dead, blood, and most things against divine beings.

View File

@@ -2,12 +2,50 @@
// Constants and standard colors for the holomap
//
#define WORLD_ICON_SIZE 32 // Size of a standard tile in pixels (world.icon_size)
#define PIXEL_MULTIPLIER WORLD_ICON_SIZE/32 // Convert from normal icon size of 32 to whatever insane thing this server is using.
#define HOLOMAP_ICON 'icons/480x480.dmi' // Icon file to start with when drawing holomaps (to get a 480x480 canvas).
#define HOLOMAP_ICON_SIZE 480 // Pixel width & height of the holomap icon. Used for auto-centering etc.
#define ui_holomap "CENTER-7, CENTER-7" // Screen location of the holomap "hud"
//Holomap filters
#define HOLOMAP_FILTER_DEATHSQUAD 1
#define HOLOMAP_FILTER_ERT 2
#define HOLOMAP_FILTER_NUKEOPS 4
#define HOLOMAP_FILTER_ELITESYNDICATE 8
#define HOLOMAP_FILTER_VOX 16
#define HOLOMAP_FILTER_STATIONMAP 32
#define HOLOMAP_FILTER_STATIONMAP_STRATEGIC 64//features markers over the captain's office, the armory, the SMES
#define HOLOMAP_FILTER_CULT 128//bloodstone locators
#define HOLOMAP_EXTRA_STATIONMAP "stationmapformatted"
#define HOLOMAP_EXTRA_STATIONMAP_STRATEGIC "stationmapstrategic"
#define HOLOMAP_EXTRA_STATIONMAPAREAS "stationareas"
#define HOLOMAP_EXTRA_STATIONMAPSMALL "stationmapsmall"
#define HOLOMAP_EXTRA_STATIONMAPSMALL_NORTH "stationmapsmallnorth"
#define HOLOMAP_EXTRA_STATIONMAPSMALL_SOUTH "stationmapsmallsouth"
#define HOLOMAP_EXTRA_STATIONMAPSMALL_EAST "stationmapsmalleast"
#define HOLOMAP_EXTRA_STATIONMAPSMALL_WEST "stationmapsmallwest"
#define HOLOMAP_EXTRA_CULTMAP "cultmap"
#define HOLOMAP_MARKER_SMES "smes"
#define HOLOMAP_MARKER_DISK "diskspawn"
#define HOLOMAP_MARKER_SKIPJACK "skipjack"
#define HOLOMAP_MARKER_SYNDISHUTTLE "syndishuttle"
#define HOLOMAP_MARKER_BLOODSTONE "bloodstone"
#define HOLOMAP_MARKER_BLOODSTONE_BROKEN "bloodstone-broken"
#define HOLOMAP_MARKER_BLOODSTONE_ANCHOR "bloodstone-narsie"
#define HOLOMAP_MARKER_CULT_ALTAR "altar"
#define HOLOMAP_MARKER_CULT_FORGE "forge"
#define HOLOMAP_MARKER_CULT_SPIRE "spire"
#define HOLOMAP_MARKER_CULT_ENTRANCE "path_entrance"
#define HOLOMAP_MARKER_CULT_EXIT "path_exit"
#define HOLOMAP_MARKER_CULT_RUNE "rune"
#define HOLOMAP_DRAW_NORMAL 0
#define HOLOMAP_DRAW_FULL 1
#define HOLOMAP_DRAW_EMPTY 2
#define HOLOMAP_DRAW_PATH 3
#define HOLOMAP_DRAW_HALLWAY 4
// Holomap colors
#define HOLOMAP_OBSTACLE "#FFFFFFDD" // Color of walls and barriers
#define HOLOMAP_PATH "#66666699" // Color of floors
@@ -46,7 +84,3 @@
// #define HOLOMAP_MARKER_DISK "diskspawn"
// #define HOLOMAP_MARKER_SKIPJACK "skipjack"
// #define HOLOMAP_MARKER_SYNDISHUTTLE "syndishuttle"
#define HOLOMAP_EXTRA_STATIONMAP "stationmapformatted"
#define HOLOMAP_EXTRA_STATIONMAPAREAS "stationareas"
#define HOLOMAP_EXTRA_STATIONMAPSMALL "stationmapsmall"

View File

@@ -57,3 +57,5 @@
//#define isturf(D) istype(D, /turf) //Built in
#define isopenspace(A) istype(A, /turf/simulated/open)
#define isspace(A) istype(A, /turf/space)
#define istaurtail(A) istype(A, /datum/sprite_accessory/tail/taur)

View File

@@ -101,11 +101,9 @@
#define slot_r_ear_str "slot_r_ear"
#define slot_belt_str "slot_belt"
#define slot_shoes_str "slot_shoes"
#define slot_head_str "slot_head"
#define slot_wear_mask_str "slot_wear_mask"
#define slot_handcuffed_str "slot_handcuffed"
#define slot_legcuffed_str "slot_legcuffed"
#define slot_wear_mask_str "slot_wear_mask"
#define slot_wear_id_str "slot_wear_id"
#define slot_gloves_str "slot_gloves"
#define slot_glasses_str "slot_glasses"

View File

@@ -8,6 +8,7 @@
#define MAP_LEVEL_CONSOLES 0x040 // Z-levels available to various consoles, such as the crew monitor (when that gets coded in). Defaults to station_levels if unset.
#define MAP_LEVEL_XENOARCH_EXEMPT 0x080 // Z-levels exempt from xenoarch digsite generation.
#define MAP_LEVEL_PERSIST 0x100 // Z-levels where SSpersistence should persist between rounds
#define MAP_LEVEL_MAPPABLE 0x200 // Z-levels where mapping units will work fully
// Misc map defines.
#define SUBMAP_MAP_EDGE_PAD 15 // Automatically created submaps are forbidden from being this close to the main map's edge.

View File

@@ -57,7 +57,4 @@
#define MATERIAL_BRITTLE 0x2
#define MATERIAL_PADDING 0x4
#define DEFAULT_TABLE_MATERIAL "plastic"
#define DEFAULT_WALL_MATERIAL "steel"
#define TABLE_BRITTLE_MATERIAL_MULTIPLIER 4 // Amount table damage is multiplied by if it is made of a brittle material (e.g. glass)

View File

@@ -2,6 +2,7 @@
#define R_IDEAL_GAS_EQUATION 8.31 // kPa*L/(K*mol).
#define ONE_ATMOSPHERE 101.325 // kPa.
#define IDEAL_GAS_ENTROPY_CONSTANT 1164 // (mol^3 * s^3) / (kg^3 * L).
#define ADIABATIC_EXPONENT 0.667 //Actually adiabatic exponent - 1.
#define T0C 273.15 // 0.0 degrees celcius
#define T20C 293.15 // 20.0 degrees celcius

View File

@@ -196,8 +196,6 @@
#define MIDNIGHT_ROLLOVER 864000 //number of deciseconds in a day
#define WORLD_ICON_SIZE 32 //Needed for the R-UST port
#define PIXEL_MULTIPLIER WORLD_ICON_SIZE/32 //Needed for the R-UST port
#define MAX_CLIENT_VIEW 34 // Maximum effective value of client.view (According to DM references)
// Maploader bounds indices
@@ -453,3 +451,5 @@ GLOBAL_LIST_INIT(all_volume_channels, list(
#ifndef HTTP_POST_DLL_LOCATION
#define HTTP_POST_DLL_LOCATION (world.system_type == MS_WINDOWS ? WINDOWS_HTTP_POST_DLL_LOCATION : UNIX_HTTP_POST_DLL_LOCATION)
#endif
#define DOCK_ATTEMPT_TIMEOUT 200 //how long in ticks we wait before assuming the docking controller is broken or blown up.

View File

@@ -25,19 +25,18 @@
#define EMP_OXY_DMG 0x100 // EMPs inflict oxy damage
// Species allergens
#define MEAT 0x1 // Skrell won't like this.
#define FISH 0x2 // Seperate for completion's sake. Still bad for skrell.
#define FRUIT 0x4 // An apple a day only keeps the doctor away if they're allergic.
#define VEGETABLE 0x8 // Taters 'n' carrots. Potato allergy is a thing, apparently.
#define GRAINS 0x10 // Wheat, oats, etc.
#define BEANS 0x20 // The musical fruit! Includes soy.
#define SEEDS 0x40 // Hope you don't have a nut allergy.
#define DAIRY 0x80 // Lactose intolerance, ho! Also bad for skrell.
#define FUNGI 0x100 // Delicious shrooms.
#define COFFEE 0x200 // Mostly here for tajara.
#define GENERIC 0x400 // Catchall for stuff that doesn't fall into the groups above. You shouldn't be allergic to this type, ever.
#define SUGARS 0x800 // For unathi-like reactions
#define EGGS 0x1000 // For Skrell eggs allergy
#define ALLERGEN_MEAT 0x1 // Skrell won't like this.
#define ALLERGEN_FISH 0x2 // Seperate for completion's sake. Still bad for skrell.
#define ALLERGEN_FRUIT 0x4 // An apple a day only keeps the doctor away if they're allergic.
#define ALLERGEN_VEGETABLE 0x8 // Taters 'n' carrots. Potato allergy is a thing, apparently.
#define ALLERGEN_GRAINS 0x10 // Wheat, oats, etc.
#define ALLERGEN_BEANS 0x20 // The musical fruit! Includes soy.
#define ALLERGEN_SEEDS 0x40 // Hope you don't have a nut allergy.
#define ALLERGEN_DAIRY 0x80 // Lactose intolerance, ho! Also bad for skrell.
#define ALLERGEN_FUNGI 0x100 // Delicious shrooms.
#define ALLERGEN_COFFEE 0x200 // Mostly here for tajara.
#define ALLERGEN_SUGARS 0x400 // For unathi-like reactions
#define ALLERGEN_EGGS 0x800 // For Skrell eggs allergy
// Allergen reactions
#define AG_TOX_DMG 0x1 // the classic

View File

@@ -19,6 +19,8 @@
#define isCardinal(x) (x == NORTH || x == SOUTH || x == EAST || x == WEST)
#define isDiagonal(x) (x == NORTHEAST || x == SOUTHEAST || x == NORTHWEST || x == SOUTHWEST)
#define FOOTSTEP_SPRITE_AMT 2
// Used to designate if a turf (or its area) should initialize as outdoors or not.
#define OUTDOORS_YES 1 // This needs to be 1 for backwards compatibility.
#define OUTDOORS_NO 0 // Ditto.

View File

@@ -2,6 +2,38 @@ GLOBAL_LIST_INIT(bitfields, list(
"datum_flags" = list(
"DF_VAR_EDITED" = DF_VAR_EDITED,
"DF_ISPROCESSING" = DF_ISPROCESSING
)
),
"appearance_flags" = list(
"KEEP_APART" = KEEP_APART,
"KEEP_TOGETHER" = KEEP_TOGETHER,
"LONG_GLIDE" = LONG_GLIDE,
"NO_CLIENT_COLOR" = NO_CLIENT_COLOR,
"PIXEL_SCALE" = PIXEL_SCALE,
"PLANE_MASTER" = PLANE_MASTER,
"RESET_ALPHA" = RESET_ALPHA,
"RESET_COLOR" = RESET_COLOR,
"RESET_TRANSFORM" = RESET_TRANSFORM,
"TILE_BOUND" = TILE_BOUND,
),
"vis_flags" = list(
"VIS_HIDE" = VIS_HIDE,
"VIS_INHERIT_DIR" = VIS_INHERIT_DIR,
"VIS_INHERIT_ICON" = VIS_INHERIT_ICON,
"VIS_INHERIT_ICON_STATE" = VIS_INHERIT_ICON_STATE,
"VIS_INHERIT_ID" = VIS_INHERIT_ID,
"VIS_INHERIT_LAYER" = VIS_INHERIT_LAYER,
"VIS_INHERIT_PLANE" = VIS_INHERIT_PLANE,
"VIS_UNDERLAY" = VIS_UNDERLAY,
),
"sight" = list(
"BLIND" = BLIND,
"SEE_BLACKNESS" = SEE_BLACKNESS,
"SEE_INFRA" = SEE_INFRA,
"SEE_MOBS" = SEE_MOBS,
"SEE_OBJS" = SEE_OBJS,
"SEE_PIXELS" = SEE_PIXELS,
"SEE_SELF" = SEE_SELF,
"SEE_THRU" = SEE_THRU,
"SEE_TURFS" = SEE_TURFS,
),
))

View File

@@ -79,7 +79,7 @@
return counting_english_list(input, output_icons, determiners, nothing_text, and_text, comma_text, final_comma_text)
//Returns list element or null. Should prevent "index out of bounds" error.
proc/listgetindex(var/list/list,index)
/proc/listgetindex(var/list/list,index)
if(istype(list) && list.len)
if(isnum(index))
if(InRange(index,1,list.len))
@@ -89,13 +89,13 @@ proc/listgetindex(var/list/list,index)
return
//Return either pick(list) or null if list is not of type /list or is empty
proc/safepick(list/list)
/proc/safepick(list/list)
if(!islist(list) || !list.len)
return
return pick(list)
//Checks if the list is empty
proc/isemptylist(list/list)
/proc/isemptylist(list/list)
if(!list.len)
return 1
return 0
@@ -177,13 +177,13 @@ proc/isemptylist(list/list)
//////////////////////////////////////////////////////
//Empties the list by setting the length to 0. Hopefully the elements get garbage collected
proc/clearlist(list/list)
/proc/clearlist(list/list)
if(istype(list))
list.len = 0
return
//Removes any null entries from the list
proc/listclearnulls(list/list)
/proc/listclearnulls(list/list)
if(istype(list))
while(null in list)
list -= null
@@ -611,7 +611,7 @@ This actually tests if they have the same entries and values.
min = mid+1
/*
proc/dd_sortedObjectList(list/incoming)
/proc/dd_sortedObjectList(list/incoming)
/*
Use binary search to order by dd_SortValue().
This works by going to the half-point of the list, seeing if the node in
@@ -669,7 +669,7 @@ proc/dd_sortedObjectList(list/incoming)
return sorted_list
*/
proc/dd_sortedtextlist(list/incoming, case_sensitive = 0)
/proc/dd_sortedtextlist(list/incoming, case_sensitive = 0)
// Returns a new list with the text values sorted.
// Use binary search to order by sortValue.
// This works by going to the half-point of the list, seeing if the node in question is higher or lower cost,
@@ -728,7 +728,7 @@ proc/dd_sortedtextlist(list/incoming, case_sensitive = 0)
return sorted_text
proc/dd_sortedTextList(list/incoming)
/proc/dd_sortedTextList(list/incoming)
var/case_sensitive = 1
return dd_sortedtextlist(incoming, case_sensitive)

View File

@@ -314,10 +314,7 @@
return list("mobs" = mobs, "objs" = objs)
#define SIGN(X) ((X<0)?-1:1)
proc
inLineOfSight(X1,Y1,X2,Y2,Z=1,PX1=16.5,PY1=16.5,PX2=16.5,PY2=16.5)
/proc/inLineOfSight(X1,Y1,X2,Y2,Z=1,PX1=16.5,PY1=16.5,PX2=16.5,PY2=16.5)
var/turf/T
if(X1==X2)
if(Y1==Y2)
@@ -346,7 +343,6 @@ proc
if(T.opacity)
return 0
return 1
#undef SIGN
/proc/flick_overlay(image/I, list/show_to, duration, gc_after)
for(var/client/C in show_to)
@@ -365,7 +361,7 @@ proc
viewing += M.client
flick_overlay(I, viewing, duration, gc_after)
proc/isInSight(var/atom/A, var/atom/B)
/proc/isInSight(var/atom/A, var/atom/B)
var/turf/Aturf = get_turf(A)
var/turf/Bturf = get_turf(B)
@@ -446,7 +442,7 @@ proc/isInSight(var/atom/A, var/atom/B)
for(var/client/C in group)
C.screen -= O
datum/projectile_data
/datum/projectile_data
var/src_x
var/src_y
var/time

View File

@@ -31,9 +31,10 @@ GLOBAL_LIST_EMPTY(closet_appearances)
// Times that players are allowed to respawn ("ckey" = world.time)
GLOBAL_LIST_EMPTY(respawn_timers)
// Posters
var/global/list/poster_designs = list()
var/global/list/NT_poster_designs = list()
// Holomaps
var/global/list/holomap_markers = list()
var/global/list/mapping_units = list()
var/global/list/mapping_beacons = list()
//Preferences stuff
//Hairstyles
@@ -207,18 +208,6 @@ var/global/list/string_slot_flags = list(
if(S.spawn_flags & SPECIES_IS_WHITELISTED)
GLOB.whitelisted_species += S.name
//Posters
paths = typesof(/datum/poster) - /datum/poster
paths -= typesof(/datum/poster/nanotrasen)
for(var/T in paths)
var/datum/poster/P = new T
poster_designs += P
paths = typesof(/datum/poster/nanotrasen)
for(var/T in paths)
var/datum/poster/P = new T
NT_poster_designs += P
//Ores
paths = typesof(/ore)-/ore
for(var/oretype in paths)
@@ -230,10 +219,7 @@ var/global/list/string_slot_flags = list(
GLOB.alloy_data += new alloytype()
//Closet appearances
paths = typesof(/decl/closet_appearance)
for(var/T in paths)
var/decl/closet_appearance/app = new T()
GLOB.closet_appearances[T] = app
GLOB.closet_appearances = decls_repository.get_decls_of_type(/decl/closet_appearance)
paths = typesof(/datum/sprite_accessory/ears) - /datum/sprite_accessory/ears
for(var/path in paths)

View File

@@ -199,7 +199,7 @@ mob
getFlatIcon(src)
Browse_Icon()
obj/effect/overlayTest
/obj/effect/overlayTest
icon = 'old_or_unused.dmi'
icon_state = "blue"
pixel_x = -24
@@ -215,26 +215,25 @@ world
#define TO_HEX_DIGIT(n) ascii2text((n&15) + ((n&15)<10 ? 48 : 87))
icon
proc/MakeLying()
/icon/proc/MakeLying()
var/icon/I = new(src,dir=SOUTH)
I.BecomeLying()
return I
proc/BecomeLying()
/icon/proc/BecomeLying()
Turn(90)
Shift(SOUTH,6)
Shift(EAST,1)
// Multiply all alpha values by this float
proc/ChangeOpacity(opacity = 1.0)
/icon/proc/ChangeOpacity(opacity = 1.0)
MapColors(1,0,0,0, 0,1,0,0, 0,0,1,0, 0,0,0,opacity, 0,0,0,0)
// Convert to grayscale
proc/GrayScale()
/icon/proc/GrayScale()
MapColors(0.3,0.3,0.3, 0.59,0.59,0.59, 0.11,0.11,0.11, 0,0,0)
proc/ColorTone(tone)
/icon/proc/ColorTone(tone)
GrayScale()
var/list/TONE = ReadRGB(tone)
@@ -252,14 +251,14 @@ icon
Blend(upper, ICON_ADD)
// Take the minimum color of two icons; combine transparency as if blending with ICON_ADD
proc/MinColors(icon)
/icon/proc/MinColors(icon)
var/icon/I = new(src)
I.Opaque()
I.Blend(icon, ICON_SUBTRACT)
Blend(I, ICON_SUBTRACT)
// Take the maximum color of two icons; combine opacity as if blending with ICON_OR
proc/MaxColors(icon)
/icon/proc/MaxColors(icon)
var/icon/I
if(isicon(icon))
I = new(icon)
@@ -275,21 +274,21 @@ icon
Blend(I, ICON_OR)
// make this icon fully opaque--transparent pixels become black
proc/Opaque(background = "#000000")
/icon/proc/Opaque(background = "#000000")
SwapColor(null, background)
MapColors(1,0,0,0, 0,1,0,0, 0,0,1,0, 0,0,0,0, 0,0,0,1)
// Change a grayscale icon into a white icon where the original color becomes the alpha
// I.e., black -> transparent, gray -> translucent white, white -> solid white
proc/BecomeAlphaMask()
/icon/proc/BecomeAlphaMask()
SwapColor(null, "#000000ff") // don't let transparent become gray
MapColors(0,0,0,0.3, 0,0,0,0.59, 0,0,0,0.11, 0,0,0,0, 1,1,1,0)
proc/UseAlphaMask(mask)
/icon/proc/UseAlphaMask(mask)
Opaque()
AddAlphaMask(mask)
proc/AddAlphaMask(mask)
/icon/proc/AddAlphaMask(mask)
var/icon/M = new(mask)
M.Blend("#ffffff", ICON_SUBTRACT)
// apply mask
@@ -317,7 +316,7 @@ icon
Higher value means brighter color
*/
proc/ReadRGB(rgb)
/proc/ReadRGB(rgb)
if(!rgb) return
// interpret the HSV or HSVA value
@@ -367,7 +366,7 @@ proc/ReadRGB(rgb)
. = list(r, g, b)
if(usealpha) . += alpha
proc/ReadHSV(hsv)
/proc/ReadHSV(hsv)
if(!hsv) return
// interpret the HSV or HSVA value
@@ -406,7 +405,7 @@ proc/ReadHSV(hsv)
. = list(hue, sat, val)
if(usealpha) . += alpha
proc/HSVtoRGB(hsv)
/proc/HSVtoRGB(hsv)
if(!hsv) return "#000000"
var/list/HSV = ReadHSV(hsv)
if(!HSV) return "#000000"
@@ -434,7 +433,7 @@ proc/HSVtoRGB(hsv)
return (HSV.len > 3) ? rgb(r,g,b,HSV[4]) : rgb(r,g,b)
proc/RGBtoHSV(rgb)
/proc/RGBtoHSV(rgb)
if(!rgb) return "#0000000"
var/list/RGB = ReadRGB(rgb)
if(!RGB) return "#0000000"
@@ -465,7 +464,7 @@ proc/RGBtoHSV(rgb)
return hsv(hue, sat, val, (RGB.len>3 ? RGB[4] : null))
proc/hsv(hue, sat, val, alpha)
/proc/hsv(hue, sat, val, alpha)
if(hue < 0 || hue >= 1536) hue %= 1536
if(hue < 0) hue += 1536
if((hue & 0xFF) == 0xFF)
@@ -498,7 +497,7 @@ proc/hsv(hue, sat, val, alpha)
amount<0 or amount>1 are allowed
*/
proc/BlendHSV(hsv1, hsv2, amount)
/proc/BlendHSV(hsv1, hsv2, amount)
var/list/HSV1 = ReadHSV(hsv1)
var/list/HSV2 = ReadHSV(hsv2)
@@ -552,7 +551,7 @@ proc/BlendHSV(hsv1, hsv2, amount)
amount<0 or amount>1 are allowed
*/
proc/BlendRGB(rgb1, rgb2, amount)
/proc/BlendRGB(rgb1, rgb2, amount)
var/list/RGB1 = ReadRGB(rgb1)
var/list/RGB2 = ReadRGB(rgb2)
@@ -568,10 +567,10 @@ proc/BlendRGB(rgb1, rgb2, amount)
return isnull(alpha) ? rgb(r, g, b) : rgb(r, g, b, alpha)
proc/BlendRGBasHSV(rgb1, rgb2, amount)
/proc/BlendRGBasHSV(rgb1, rgb2, amount)
return HSVtoRGB(RGBtoHSV(rgb1), RGBtoHSV(rgb2), amount)
proc/HueToAngle(hue)
/proc/HueToAngle(hue)
// normalize hsv in case anything is screwy
if(hue < 0 || hue >= 1536) hue %= 1536
if(hue < 0) hue += 1536
@@ -579,7 +578,7 @@ proc/HueToAngle(hue)
hue -= hue >> 8
return hue / (1530/360)
proc/AngleToHue(angle)
/proc/AngleToHue(angle)
// normalize hsv in case anything is screwy
if(angle < 0 || angle >= 360) angle -= 360 * round(angle / 360)
var/hue = angle * (1530/360)
@@ -589,7 +588,7 @@ proc/AngleToHue(angle)
// positive angle rotates forward through red->green->blue
proc/RotateHue(hsv, angle)
/proc/RotateHue(hsv, angle)
var/list/HSV = ReadHSV(hsv)
// normalize hsv in case anything is screwy
@@ -611,13 +610,13 @@ proc/RotateHue(hsv, angle)
return hsv(HSV[1], HSV[2], HSV[3], (HSV.len > 3 ? HSV[4] : null))
// Convert an rgb color to grayscale
proc/GrayScale(rgb)
/proc/GrayScale(rgb)
var/list/RGB = ReadRGB(rgb)
var/gray = RGB[1]*0.3 + RGB[2]*0.59 + RGB[3]*0.11
return (RGB.len > 3) ? rgb(gray, gray, gray, RGB[4]) : rgb(gray, gray, gray)
// Change grayscale color to black->tone->white range
proc/ColorTone(rgb, tone)
/proc/ColorTone(rgb, tone)
var/list/RGB = ReadRGB(rgb)
var/list/TONE = ReadRGB(tone)
@@ -925,7 +924,7 @@ GLOBAL_LIST_EMPTY(cached_examine_icons)
/proc/uncache_examine_icon(var/weakref/WR)
GLOB.cached_examine_icons -= WR
proc/adjust_brightness(var/color, var/value)
/proc/adjust_brightness(var/color, var/value)
if (!color) return "#FFFFFF"
if (!value) return color
@@ -935,7 +934,7 @@ proc/adjust_brightness(var/color, var/value)
RGB[3] = CLAMP(RGB[3]+value,0,255)
return rgb(RGB[1],RGB[2],RGB[3])
proc/sort_atoms_by_layer(var/list/atoms)
/proc/sort_atoms_by_layer(var/list/atoms)
// Comb sort icons based on levels
var/list/result = atoms.Copy()
var/gap = result.len

View File

@@ -1,4 +1,4 @@
proc/random_hair_style(gender, species = SPECIES_HUMAN)
/proc/random_hair_style(gender, species = SPECIES_HUMAN)
var/h_style = "Bald"
var/list/valid_hairstyles = list()
@@ -17,7 +17,7 @@ proc/random_hair_style(gender, species = SPECIES_HUMAN)
return h_style
proc/random_facial_hair_style(gender, species = SPECIES_HUMAN)
/proc/random_facial_hair_style(gender, species = SPECIES_HUMAN)
var/f_style = "Shaved"
var/list/valid_facialhairstyles = list()
@@ -37,14 +37,14 @@ proc/random_facial_hair_style(gender, species = SPECIES_HUMAN)
return f_style
proc/sanitize_name(name, species = SPECIES_HUMAN, robot = 0)
/proc/sanitize_name(name, species = SPECIES_HUMAN, robot = 0)
var/datum/species/current_species
if(species)
current_species = GLOB.all_species[species]
return current_species ? current_species.sanitize_name(name, robot) : sanitizeName(name, MAX_NAME_LEN, robot)
proc/random_name(gender, species = SPECIES_HUMAN)
/proc/random_name(gender, species = SPECIES_HUMAN)
var/datum/species/current_species
if(species)
@@ -58,7 +58,7 @@ proc/random_name(gender, species = SPECIES_HUMAN)
else
return current_species.get_random_name(gender)
proc/random_skin_tone()
/proc/random_skin_tone()
switch(pick(60;"caucasian", 15;"afroamerican", 10;"african", 10;"latino", 5;"albino"))
if("caucasian") . = -10
if("afroamerican") . = -115
@@ -68,7 +68,7 @@ proc/random_skin_tone()
else . = rand(-185,34)
return min(max( .+rand(-25, 25), -185),34)
proc/skintone2racedescription(tone)
/proc/skintone2racedescription(tone)
switch (tone)
if(30 to INFINITY) return "albino"
if(20 to 30) return "pale"
@@ -80,7 +80,7 @@ proc/skintone2racedescription(tone)
if(-INFINITY to -65) return "black"
else return "unknown"
proc/age2agedescription(age)
/proc/age2agedescription(age)
switch(age)
if(0 to 1) return "infant"
if(1 to 3) return "toddler"

View File

@@ -57,12 +57,6 @@
if (!.)
. = B[STAT_ENTRY_COUNT] - A[STAT_ENTRY_COUNT]
// Compares complexity of recipes for use in cooking, etc. This is for telling which recipe to make, not for showing things to the player.
/proc/cmp_recipe_complexity_dsc(datum/recipe/A, datum/recipe/B)
var/a_score = LAZYLEN(A.items) + LAZYLEN(A.reagents) + LAZYLEN(A.fruit)
var/b_score = LAZYLEN(B.items) + LAZYLEN(B.reagents) + LAZYLEN(B.fruit)
return b_score - a_score
/proc/cmp_typepaths_asc(A, B)
return sorttext("[B]","[A]")

View File

@@ -319,7 +319,7 @@
//Used in preferences' SetFlavorText and human's set_flavor verb
//Previews a string of len or less length
proc/TextPreview(var/string,var/len=40)
/proc/TextPreview(var/string,var/len=40)
if(length(string) <= len)
if(!length(string))
return "\[...\]"

View File

@@ -20,6 +20,8 @@
#define TICKS2DS(T) ((T) TICKS) // Convert ticks to deciseconds
#define DS2NEARESTTICK(DS) TICKS2DS(-round(-(DS2TICKS(DS))))
var/world_startup_time
/proc/get_game_time()
var/global/time_offset = 0
var/global/last_time = 0
@@ -78,7 +80,7 @@ var/next_station_date_change = 1 DAY
return time2text(wtime - GLOB.timezoneOffset, format)
/* Returns 1 if it is the selected month and day */
proc/isDay(var/month, var/day)
/proc/isDay(var/month, var/day)
if(isnum(month) && isnum(day))
var/MM = text2num(time2text(world.timeofday, "MM")) // get the current month
var/DD = text2num(time2text(world.timeofday, "DD")) // get the current day

View File

@@ -595,7 +595,7 @@ Turf and target are seperate in case you want to teleport some distance from a t
return max(min(middle, high), low)
//returns random gauss number
proc/GaussRand(var/sigma)
/proc/GaussRand(var/sigma)
var/x,y,rsq
do
x=2*rand()-1
@@ -605,7 +605,7 @@ proc/GaussRand(var/sigma)
return sigma*y*sqrt(-2*log(rsq)/rsq)
//returns random gauss number, rounded to 'roundto'
proc/GaussRandRound(var/sigma,var/roundto)
/proc/GaussRandRound(var/sigma,var/roundto)
return round(GaussRand(sigma),roundto)
//Will return the contents of an atom recursivly to a depth of 'searchDepth'
@@ -866,7 +866,7 @@ proc/GaussRandRound(var/sigma,var/roundto)
refined_trg -= B
continue moving
proc/DuplicateObject(obj/original, var/perfectcopy = 0 , var/sameloc = 0)
/proc/DuplicateObject(obj/original, var/perfectcopy = 0 , var/sameloc = 0)
if(!original)
return null
@@ -1014,16 +1014,16 @@ proc/DuplicateObject(obj/original, var/perfectcopy = 0 , var/sameloc = 0)
proc/get_cardinal_dir(atom/A, atom/B)
/proc/get_cardinal_dir(atom/A, atom/B)
var/dx = abs(B.x - A.x)
var/dy = abs(B.y - A.y)
return get_dir(A, B) & (rand() * (dx+dy) < dy ? 3 : 12)
//chances are 1:value. anyprob(1) will always return true
proc/anyprob(value)
/proc/anyprob(value)
return (rand(1,value)==value)
proc/view_or_range(distance = world.view , center = usr , type)
/proc/view_or_range(distance = world.view , center = usr , type)
switch(type)
if("view")
. = view(distance,center)
@@ -1031,7 +1031,7 @@ proc/view_or_range(distance = world.view , center = usr , type)
. = range(distance,center)
return
proc/oview_or_orange(distance = world.view , center = usr , type)
/proc/oview_or_orange(distance = world.view , center = usr , type)
switch(type)
if("view")
. = oview(distance,center)
@@ -1039,7 +1039,7 @@ proc/oview_or_orange(distance = world.view , center = usr , type)
. = orange(distance,center)
return
proc/get_mob_with_client_list()
/proc/get_mob_with_client_list()
var/list/mobs = list()
for(var/mob/M in mob_list)
if (M.client)
@@ -1096,7 +1096,7 @@ var/global/list/common_tools = list(
return TRUE
return
proc/is_hot(obj/item/W as obj)
/proc/is_hot(obj/item/W as obj)
switch(W.type)
if(/obj/item/weapon/weldingtool)
var/obj/item/weapon/weldingtool/WT = W
@@ -1478,8 +1478,6 @@ var/mob/dview/dview_mob = new
/proc/pass()
return
#define NAMEOF(datum, X) (#X || ##datum.##X)
/proc/pick_closest_path(value, list/matches = get_fancy_list_of_atom_types())
if (value == FALSE) //nothing should be calling us with a number, so this is safe
value = input("Enter type to find (blank for all, cancel to cancel)", "Search for type") as null|text

View File

@@ -40,5 +40,6 @@
#define ARGS_DEBUG log_debug("[__FILE__] - [__LINE__]") ; for(var/arg in args) { log_debug("\t[log_info_line(arg)]") }
#define isitem(A) istype(A, /obj/item)
#define isTaurTail(A) istype(A, /datum/sprite_accessory/tail/taur)
#define WORLD_ICON_SIZE 32 //Needed for the R-UST port
#define PIXEL_MULTIPLIER WORLD_ICON_SIZE/32 //Needed for the R-UST port

View File

@@ -87,12 +87,6 @@ var/list/global_huds = list(
science = setup_overlay("science_hud")
material = setup_overlay("material_hud")
// The holomap screen object is actually totally invisible.
// Station maps work by setting it as an images location before sending to client, not
// actually changing the icon or icon state of the screen object itself!
// Why do they work this way? I don't know really, that is how /vg designed them, but since they DO
// work this way, we can take advantage of their immutability by making them part of
// the global_hud (something we have and /vg doesn't) instead of an instance per mob.
holomap = new /obj/screen()
holomap.name = "holomap"
holomap.icon = null
@@ -191,13 +185,14 @@ var/list/global_huds = list(
var/list/minihuds = list()
datum/hud/New(mob/owner)
/datum/hud/New(mob/owner)
mymob = owner
instantiate()
..()
/datum/hud/Destroy()
. = ..()
qdel_null(minihuds)
grab_intent = null
hurt_intent = null
disarm_intent = null
@@ -216,7 +211,6 @@ datum/hud/New(mob/owner)
hotkeybuttons = null
// item_action_list = null // ?
mymob = null
qdel_null(minihuds)
/datum/hud/proc/hidden_inventory_update()
if(!mymob) return

View File

@@ -0,0 +1,36 @@
/datum/mini_hud
var/datum/hud/main_hud
var/list/screenobjs
var/needs_processing = FALSE
/datum/mini_hud/New(var/datum/hud/other)
apply_to_hud(other)
if(needs_processing)
START_PROCESSING(SSprocessing, src)
/datum/mini_hud/Destroy()
unapply_to_hud()
if(needs_processing)
STOP_PROCESSING(SSprocessing, src)
QDEL_LIST_NULL(screenobjs)
return ..()
// Apply to a real /datum/hud
/datum/mini_hud/proc/apply_to_hud(var/datum/hud/other)
if(main_hud)
unapply_to_hud(main_hud)
main_hud = other
main_hud.apply_minihud(src)
// Remove from a real /datum/hud
/datum/mini_hud/proc/unapply_to_hud()
main_hud?.remove_minihud(src)
main_hud = null
// Update the hud
/datum/mini_hud/process()
return PROCESS_KILL // You shouldn't be here!
// Return a list of screen objects we use
/datum/mini_hud/proc/get_screen_objs(var/mob/M)
return screenobjs.Copy()

View File

@@ -0,0 +1,13 @@
// Specific types
/datum/mini_hud/mapper
var/obj/item/device/mapping_unit/owner
/datum/mini_hud/mapper/New(var/datum/hud/other, owner)
src.owner = owner
screenobjs = list(new /obj/screen/movable/mapper_holder(null, owner))
..()
/datum/mini_hud/mapper/Destroy()
owner?.hud_item = null
owner?.hud_datum = null
return ..()

View File

@@ -1,40 +1,3 @@
/datum/mini_hud
var/datum/hud/main_hud
var/list/screenobjs = list()
var/list/types_to_instantiate
var/needs_processing = FALSE
/datum/mini_hud/New(var/datum/hud/other)
apply_to_hud(other)
if(needs_processing)
START_PROCESSING(SSprocessing, src)
/datum/mini_hud/Destroy()
main_hud?.remove_minihud(src)
main_hud = null
if(needs_processing)
STOP_PROCESSING(SSprocessing, src)
return ..()
// Apply to a real /datum/hud
/datum/mini_hud/proc/apply_to_hud(var/datum/hud/other)
if(main_hud)
unapply_to_hud(main_hud)
main_hud = other
main_hud.apply_minihud(src)
// Remove from a real /datum/hud
/datum/mini_hud/proc/unapply_to_hud(var/datum/hud/other)
main_hud.remove_minihud(src)
// Update the hud
/datum/mini_hud/process()
return PROCESS_KILL // You shouldn't be here!
// Return a list of screen objects we use
/datum/mini_hud/proc/get_screen_objs(var/mob/M)
return screenobjs
// Specific types
/datum/mini_hud/rig
var/obj/item/weapon/rig/owner_rig

View File

@@ -655,3 +655,218 @@
holder.screen -= src
holder = null
return ..()
/**
* This object holds all the on-screen elements of the mapping unit.
* It has a decorative frame and onscreen buttons. The map itself is drawn
* using a white mask and multiplying the mask against it to crop it to the
* size of the screen. This is not ideal, as filter() is faster, and has
* alpha masks, but the alpha masks it has can't be animated, so the 'ping'
* mode of this device isn't possible using that technique.
*
* The markers use that technique, though, so at least there's that.
*/
/obj/screen/movable/mapper_holder
name = "gps unit"
icon = null
icon_state = ""
screen_loc = "CENTER,CENTER"
alpha = 255
appearance_flags = KEEP_TOGETHER
mouse_opacity = 1
plane = PLANE_HOLOMAP
var/running = FALSE
var/obj/screen/mapper/mask_full/mask_full
var/obj/screen/mapper/mask_ping/mask_ping
var/obj/screen/mapper/bg/bg
var/obj/screen/mapper/frame/frame
var/obj/screen/mapper/powbutton/powbutton
var/obj/screen/mapper/mapbutton/mapbutton
var/obj/item/device/mapping_unit/owner
var/obj/screen/mapper/extras_holder/extras_holder
/obj/screen/movable/mapper_holder/Initialize(mapload, newowner)
owner = newowner
mask_full = new(src) // Full white square mask
mask_ping = new(src) // Animated 'pinging' mask
bg = new(src) // Background color, holds map in vis_contents, uses mult against masks
frame = new(src) // Decorative frame
powbutton = new(src) // Clickable button
mapbutton = new(src) // Clickable button
frame.icon_state = initial(frame.icon_state)+owner.hud_frame_hint
/**
* The vis_contents layout is: this(frame,extras_holder,mask(bg(map)))
* bg is set to BLEND_MULTIPLY against the mask to crop it.
*/
mask_full.vis_contents.Add(bg)
mask_ping.vis_contents.Add(bg)
frame.vis_contents.Add(powbutton,mapbutton)
vis_contents.Add(frame)
/obj/screen/movable/mapper_holder/Destroy()
qdel_null(mask_full)
qdel_null(mask_ping)
qdel_null(bg)
qdel_null(frame)
qdel_null(powbutton)
qdel_null(mapbutton)
extras_holder = null
owner = null
return ..()
/obj/screen/movable/mapper_holder/proc/update(var/obj/screen/mapper/map, var/obj/screen/mapper/extras_holder/extras, ping = FALSE)
if(!running)
running = TRUE
if(ping)
vis_contents.Add(mask_ping)
else
vis_contents.Add(mask_full)
bg.vis_contents.Cut()
bg.vis_contents.Add(map)
if(extras && !extras_holder)
extras_holder = extras
vis_contents += extras_holder
if(!extras && extras_holder)
vis_contents -= extras_holder
extras_holder = null
/obj/screen/movable/mapper_holder/proc/powerClick()
if(running)
off()
else
on()
/obj/screen/movable/mapper_holder/proc/mapClick()
if(owner)
if(running)
off()
owner.pinging = !owner.pinging
on()
/obj/screen/movable/mapper_holder/proc/off(var/inform = TRUE)
frame.cut_overlay("powlight")
bg.vis_contents.Cut()
vis_contents.Remove(mask_ping, mask_full, extras_holder)
extras_holder = null
running = FALSE
if(inform)
owner.stop_updates()
/obj/screen/movable/mapper_holder/proc/on(var/inform = TRUE)
frame.add_overlay("powlight")
if(inform)
owner.start_updates()
// Prototype
/obj/screen/mapper
plane = PLANE_HOLOMAP
mouse_opacity = 0
var/obj/screen/movable/mapper_holder/parent
/obj/screen/mapper/New()
..()
parent = loc
/obj/screen/mapper/Destroy()
parent = null
return ..()
// Holds the actual map image
/obj/screen/mapper/map
var/offset_x = 32
var/offset_y = 32
// I really wish I could use filters for this instead of this multiplication-masking technique
// but alpha filters can't be animated, which means I can't use them for the 'sonar ping' mode.
// If filters start supporting animated icons in the future (for the alpha mask filter),
// you should definitely replace these with that technique instead.
/obj/screen/mapper/mask_full
icon = 'icons/effects/64x64.dmi'
icon_state = "mapper_mask"
/obj/screen/mapper/mask_ping
icon = 'icons/effects/64x64.dmi'
icon_state = "mapper_ping"
/obj/screen/mapper/bg
icon = 'icons/effects/64x64.dmi'
icon_state = "mapper_bg"
blend_mode = BLEND_MULTIPLY
appearance_flags = KEEP_TOGETHER
// Frame/deco components
/obj/screen/mapper/frame
icon = 'icons/effects/gpshud.dmi'
icon_state = "frame"
plane = PLANE_HOLOMAP_FRAME
pixel_x = -18
pixel_y = -29
mouse_opacity = 1
vis_flags = VIS_INHERIT_ID
/obj/screen/mapper/powbutton
icon = 'icons/effects/gpshud.dmi'
icon_state = "powbutton"
plane = PLANE_HOLOMAP_FRAME
mouse_opacity = 1
/obj/screen/mapper/powbutton/Click()
if(!usr.checkClickCooldown())
return TRUE
if(usr.stat || usr.paralysis || usr.stunned || usr.weakened)
return TRUE
if(istype(usr.loc,/obj/mecha)) // stops inventory actions in a mech
return TRUE
parent.powerClick()
flick("powClick",src)
usr << get_sfx("button")
return TRUE
/obj/screen/mapper/mapbutton
icon = 'icons/effects/gpshud.dmi'
icon_state = "mapbutton"
plane = PLANE_HOLOMAP_FRAME
mouse_opacity = 1
/obj/screen/mapper/mapbutton/Click()
if(!usr.checkClickCooldown())
return TRUE
if(usr.stat || usr.paralysis || usr.stunned || usr.weakened)
return TRUE
if(istype(usr.loc,/obj/mecha)) // stops inventory actions in a mech
return TRUE
parent.mapClick()
flick("mapClick",src)
usr << get_sfx("button")
return TRUE
// Markers are 16x16, people have apparently settled on centering them on the 8,8 pixel
/obj/screen/mapper/marker
icon = 'icons/holomap_markers.dmi'
plane = PLANE_HOLOMAP_ICONS
var/offset_x = -8
var/offset_y = -8
// Holds markers in its vis_contents. It uses an alpha filter to crop them to the HUD screen size
/obj/screen/mapper/extras_holder
icon = null
icon_state = null
plane = PLANE_HOLOMAP_ICONS
appearance_flags = KEEP_TOGETHER

View File

@@ -62,6 +62,5 @@
client.update_skybox()
client.skybox?.scale_to_view(client.view)
#undef SKYBOX_BORDER
#undef SKYBOX_PIXELS
#undef SKYBOX_TURFS

View File

@@ -4,14 +4,14 @@ These are the default click code call sequences used when clicking on stuff with
Atoms:
mob/ClickOn() calls the item's resolve_attackby() proc.
/mob/ClickOn() calls the item's resolve_attackby() proc.
item/resolve_attackby() calls the target atom's attackby() proc.
Mobs:
mob/living/attackby() after checking for surgery, calls the item's attack() proc.
/mob/living/attackby() after checking for surgery, calls the item's attack() proc.
item/attack() generates attack logs, sets click cooldown and calls the mob's attacked_with_item() proc. If you override this, consider whether you need to set a click cooldown, play attack animations, and generate logs yourself.
mob/attacked_with_item() should then do mob-type specific stuff (like determining hit/miss, handling shields, etc) and then possibly call the item's apply_hit_effect() proc to actually apply the effects of being hit.
/mob/attacked_with_item() should then do mob-type specific stuff (like determining hit/miss, handling shields, etc) and then possibly call the item's apply_hit_effect() proc to actually apply the effects of being hit.
Item Hit Effects:
@@ -41,11 +41,6 @@ avoid code duplication. This includes items that may sometimes act as a standard
return TRUE
return FALSE
/atom/movable/attackby(obj/item/W, mob/user, var/attack_modifier, var/click_parameters)
. = ..()
if(!. && !(W.flags & NOBLUDGEON))
visible_message("<span class='danger'>[src] has been hit by [user] with [W].</span>")
/mob/living/attackby(obj/item/I, mob/user, var/attack_modifier, var/click_parameters)
if(!ismob(user))
return 0

View File

@@ -1,16 +1,16 @@
var/datum/controller/transfer_controller/transfer_controller
datum/controller/transfer_controller
/datum/controller/transfer_controller
var/timerbuffer = 0 //buffer for time check
var/currenttick = 0
datum/controller/transfer_controller/New()
/datum/controller/transfer_controller/New()
timerbuffer = config.vote_autotransfer_initial
START_PROCESSING(SSprocessing, src)
datum/controller/transfer_controller/Destroy()
/datum/controller/transfer_controller/Destroy()
STOP_PROCESSING(SSprocessing, src)
datum/controller/transfer_controller/process()
/datum/controller/transfer_controller/process()
currenttick = currenttick + 1
if (round_duration_in_ds >= timerbuffer - 1 MINUTE)
SSvote.autotransfer()

View File

@@ -154,9 +154,6 @@ var/list/ANTAG_FREQS = list(SYND_FREQ, RAID_FREQ)
//Department channels, arranged lexically
var/list/DEPT_FREQS = list(AI_FREQ, COMM_FREQ, ENG_FREQ, ENT_FREQ, MED_FREQ, SEC_FREQ, SCI_FREQ, SRV_FREQ, SUP_FREQ)
#define TRANSMISSION_WIRE 0
#define TRANSMISSION_RADIO 1
/proc/frequency_span_class(var/frequency)
// Antags!
if (frequency in ANTAG_FREQS)

View File

@@ -56,23 +56,23 @@ var/datum/controller/failsafe/Failsafe
if(4,5)
--defcon
if(3)
to_chat(admins, "<span class='adminnotice'>Notice: DEFCON [defcon_pretty()]. The Master Controller has not fired in the last [(5-defcon) * processing_interval] ticks.</span>")
log_and_message_admins("<span class='adminnotice'>SSfailsafe Notice: DEFCON [defcon_pretty()]. The Master Controller (\ref[Master]) has not fired in the last [(5-defcon) * processing_interval] ticks.</span>")
--defcon
if(2)
to_chat(admins, "<span class='boldannounce'>Warning: DEFCON [defcon_pretty()]. The Master Controller has not fired in the last [(5-defcon) * processing_interval] ticks. Automatic restart in [processing_interval] ticks.</span>")
log_and_message_admins("<span class='boldannounce'>SSfailsafe Warning: DEFCON [defcon_pretty()]. The Master Controller (\ref[Master]) has not fired in the last [(5-defcon) * processing_interval] ticks. Automatic restart in [processing_interval] ticks.</span>")
--defcon
if(1)
to_chat(admins, "<span class='boldannounce'>Warning: DEFCON [defcon_pretty()]. The Master Controller has still not fired within the last [(5-defcon) * processing_interval] ticks. Killing and restarting...</span>")
log_and_message_admins("<span class='boldannounce'>SSfailsafe Warning: DEFCON [defcon_pretty()]. The Master Controller (\ref[Master]) has still not fired within the last [(5-defcon) * processing_interval] ticks. Killing and restarting...</span>")
--defcon
var/rtn = Recreate_MC()
if(rtn > 0)
defcon = 4
master_iteration = 0
to_chat(admins, "<span class='adminnotice'>MC restarted successfully</span>")
log_and_message_admins("<span class='adminnotice'>SSfailsafe Notice: MC (New:\ref[Master]) restarted successfully</span>")
else if(rtn < 0)
log_game("FailSafe: Could not restart MC, runtime encountered. Entering defcon 0")
to_chat(admins, "<span class='boldannounce'>ERROR: DEFCON [defcon_pretty()]. Could not restart MC, runtime encountered. I will silently keep retrying.</span>")
log_game("SSfailsafe Notice: Could not restart MC (\ref[Master]), runtime encountered. Entering defcon 0")
log_and_message_admins("<span class='boldannounce'>SSFAILSAFE ERROR: DEFCON [defcon_pretty()]. Could not restart MC (\ref[Master]), runtime encountered. I will silently keep retrying.</span>")
//if the return number was 0, it just means the mc was restarted too recently, and it just needs some time before we try again
//no need to handle that specially when defcon 0 can handle it
if(0) //DEFCON 0! (mc failed to restart)
@@ -80,7 +80,7 @@ var/datum/controller/failsafe/Failsafe
if(rtn > 0)
defcon = 4
master_iteration = 0
to_chat(admins, "<span class='adminnotice'>MC restarted successfully</span>")
log_and_message_admins("<span class='adminnotice'>SSfailsafe Notice: MC (New:\ref[Master]) restarted successfully</span>")
else
defcon = min(defcon + 1,5)
master_iteration = Master.iteration

View File

@@ -132,10 +132,10 @@ GLOBAL_REAL(Master, /datum/controller/master) = new
LAZYINITLIST(BadBoy.failure_strikes)
switch(++BadBoy.failure_strikes[BadBoy.type])
if(2)
msg = "The [BadBoy.name] subsystem was the last to fire for 2 controller restarts. It will be recovered now and disabled if it happens again."
msg = "MC Notice: The [BadBoy.name] subsystem was the last to fire for 2 controller restarts. It will be recovered now and disabled if it happens again."
FireHim = TRUE
if(3)
msg = "The [BadBoy.name] subsystem seems to be destabilizing the MC and will be offlined."
msg = "MC Notice: The [BadBoy.name] subsystem seems to be destabilizing the MC and will be offlined."
BadBoy.flags |= SS_NO_FIRE
if(msg)
log_game(msg)
@@ -150,7 +150,7 @@ GLOBAL_REAL(Master, /datum/controller/master) = new
current_runlevel = Master.current_runlevel
StartProcessing(10)
else
to_chat(world, "<span class='boldannounce'>The Master Controller is having some issues, we will need to re-initialize EVERYTHING</span>")
to_world("<span class='boldannounce'>The Master Controller is having some issues, we will need to re-initialize EVERYTHING</span>")
Initialize(20, TRUE)
@@ -165,7 +165,7 @@ GLOBAL_REAL(Master, /datum/controller/master) = new
if(init_sss)
init_subtypes(/datum/controller/subsystem, subsystems)
to_chat(world, "<span class='boldannounce'>Initializing subsystems...</span>")
to_chat(world, "<span class='boldannounce'>MC: Initializing subsystems...</span>")
// Sort subsystems by init_order, so they initialize in the correct order.
sortTim(subsystems, /proc/cmp_subsystem_init)
@@ -181,7 +181,7 @@ GLOBAL_REAL(Master, /datum/controller/master) = new
current_ticklimit = TICK_LIMIT_RUNNING
var/time = (REALTIMEOFDAY - start_timeofday) / 10
var/msg = "Initializations complete within [time] second[time == 1 ? "" : "s"]!"
var/msg = "MC: Initializations complete within [time] second[time == 1 ? "" : "s"]!"
to_chat(world, "<span class='boldannounce'>[msg]</span>")
log_world(msg)
@@ -219,13 +219,17 @@ GLOBAL_REAL(Master, /datum/controller/master) = new
if (rtn > 0 || processing < 0)
return //this was suppose to happen.
//loop ended, restart the mc
log_game("MC crashed or runtimed, restarting")
message_admins("MC crashed or runtimed, restarting")
log_and_message_admins("MC Notice: MC crashed or runtimed, self-restarting (\ref[src])")
var/rtn2 = Recreate_MC()
if (rtn2 <= 0)
log_game("Failed to recreate MC (Error code: [rtn2]), it's up to the failsafe now")
message_admins("Failed to recreate MC (Error code: [rtn2]), it's up to the failsafe now")
switch(rtn2)
if(-1)
log_and_message_admins("MC Warning: Failed to self-recreate MC (Return code: [rtn2]), it's up to the failsafe now (\ref[src])")
Failsafe.defcon = 2
if(0)
log_and_message_admins("MC Warning: Too soon for MC self-restart (Return code: [rtn2]), going to let failsafe handle it (\ref[src])")
Failsafe.defcon = 2
if(1)
log_and_message_admins("MC Notice: MC self-recreated, old MC departing (Return code: [rtn2]) (\ref[src])")
// Main loop.
/datum/controller/master/proc/Loop()

View File

@@ -13,10 +13,10 @@ var/global/last_tick_duration = 0
var/global/pipe_processing_killed = 0
datum/controller/game_controller
/datum/controller/game_controller
var/list/shuttle_list // For debugging and VV
datum/controller/game_controller/New()
/datum/controller/game_controller/New()
//There can be only one master_controller. Out with the old and in with the new.
if(master_controller != src)
log_debug("Rebuilding Master Controller")
@@ -33,7 +33,7 @@ datum/controller/game_controller/New()
if(!syndicate_code_phrase) syndicate_code_phrase = generate_code_phrase()
if(!syndicate_code_response) syndicate_code_response = generate_code_phrase()
datum/controller/game_controller/proc/setup()
/datum/controller/game_controller/proc/setup()
setup_objects()
// setupgenetics() Moved to SSatoms
@@ -48,7 +48,7 @@ datum/controller/game_controller/proc/setup()
// #define CHECK_SLEEP_MASTER if(++initialized_objects > 500) { initialized_objects=0;sleep(world.tick_lag); }
// #endif
datum/controller/game_controller/proc/setup_objects()
/datum/controller/game_controller/proc/setup_objects()
// Set up antagonists.
populate_antag_type_list()

View File

@@ -68,8 +68,12 @@ Total Unsimulated Turfs: [world.maxx*world.maxy*world.maxz - simulated_turf_coun
/datum/controller/subsystem/air/fire(resumed = 0)
var/timer
if(!resumed)
ASSERT(LAZYLEN(currentrun) == 0) // Santity checks to make sure we don't somehow have items left over from last cycle
ASSERT(current_step == null) // Or somehow didn't finish all the steps from last cycle
// Santity checks to make sure we don't somehow have items left over from last cycle
// Or somehow didn't finish all the steps from last cycle
if(LAZYLEN(currentrun) || current_step)
log_and_message_admins("SSair: Was told to start a new run, but the previous run wasn't finished! currentrun.len=[currentrun.len], current_step=[current_step]")
resumed = TRUE
else
current_cycle++ // Begin a new air_master cycle!
current_step = SSAIR_TURFS // Start with Step 1 of course
@@ -80,8 +84,9 @@ Total Unsimulated Turfs: [world.maxx*world.maxy*world.maxz - simulated_turf_coun
INTERNAL_PROCESS_STEP(SSAIR_ZONES, FALSE, process_zones_to_update, cost_zones, SSAIR_DONE)
// Okay, we're done! Woo! Got thru a whole air_master cycle!
ASSERT(LAZYLEN(currentrun) == 0) // Sanity checks to make sure there are really none left
ASSERT(current_step == SSAIR_DONE) // And that we didn't somehow skip past the last step
if(LAZYLEN(currentrun) || current_step != SSAIR_DONE)
log_and_message_admins("SSair: Was not able to complete a full air cycle despite reaching the end of fire(). This shouldn't happen.")
else
currentrun = null
current_step = null

View File

@@ -45,8 +45,12 @@ SUBSYSTEM_DEF(lighting)
/datum/controller/subsystem/lighting/fire(resumed = FALSE)
var/timer
if(!resumed)
ASSERT(LAZYLEN(currentrun) == 0) // Santity checks to make sure we don't somehow have items left over from last cycle
ASSERT(stage == null) // Or somehow didn't finish all the steps from last cycle
// Santity checks to make sure we don't somehow have items left over from last cycle
// Or somehow didn't finish all the steps from last cycle
if(LAZYLEN(currentrun) || stage)
log_and_message_admins("SSlighting: Was told to start a new run, but the previous run wasn't finished! currentrun.len=[currentrun.len], stage=[stage]")
resumed = TRUE
else
stage = SSLIGHTING_STAGE_LIGHTS // Start with Step 1 of course
if(stage == SSLIGHTING_STAGE_LIGHTS)
@@ -77,8 +81,9 @@ SUBSYSTEM_DEF(lighting)
stage = SSLIGHTING_STAGE_DONE
// Okay, we're done! Woo! Got thru a whole air_master cycle!
ASSERT(LAZYLEN(currentrun) == 0) // Sanity checks to make sure there are really none left
ASSERT(stage == SSLIGHTING_STAGE_DONE) // And that we didn't somehow skip past the last step
if(LAZYLEN(currentrun) || stage != SSLIGHTING_STAGE_DONE)
log_and_message_admins("SSlighting: Was not able to complete a full lighting cycle despite reaching the end of fire(). This shouldn't happen.")
else
currentrun = null
stage = null
@@ -163,4 +168,3 @@ SUBSYSTEM_DEF(lighting)
#undef SSLIGHTING_STAGE_LIGHTS
#undef SSLIGHTING_STAGE_CORNERS
#undef SSLIGHTING_STAGE_OVERLAYS
#undef SSLIGHTING_STAGE_STATS

View File

@@ -175,5 +175,4 @@ SUBSYSTEM_DEF(machines)
#undef SSMACHINES_PIPENETS
#undef SSMACHINES_MACHINERY
#undef SSMACHINES_POWER
#undef SSMACHINES_POWER_OBJECTS

View File

@@ -200,10 +200,11 @@ SUBSYSTEM_DEF(supply)
else if(islist(SP.access) && SP.one_access)
var/list/L = SP.access // access var is a plain var, we need a list
A.req_one_access = L.Copy()
A.req_access.Cut()
LAZYCLEARLIST(A.req_access)
else if(islist(SP.access) && !SP.one_access)
var/list/L = SP.access
A.req_access = L.Copy()
LAZYCLEARLIST(A.req_one_access)
else
log_debug("<span class='danger'>Supply pack with invalid access restriction [SP.access] encountered!</span>")

View File

@@ -305,8 +305,7 @@
div_slider = "locked"
output += {"<li>
<label class="switch">
<input type="[inputtype]" value="1" name="[i["name"]]"[i["checked"] ? " checked" : ""][i["allowed_edit"] ? "" : " onclick='return false' onkeydown='return false'"]>
<div class="slider [div_slider ? "[div_slider]" : ""]"></div>
<input type="[inputtype]" value="1" name="[i["name"]]"[i["checked"] ? " checked" : ""][i["allowed_edit"] ? "" : " disabled onclick='return false' onkeydown='return false'"]>
<span>[i["name"]]</span>
</label>
</li>"}

View File

@@ -58,7 +58,7 @@
collection = null
return ..()
datum/category_group/dd_SortValue()
/datum/category_group/dd_SortValue()
return name
@@ -77,5 +77,5 @@ datum/category_group/dd_SortValue()
category = null
return ..()
datum/category_item/dd_SortValue()
/datum/category_item/dd_SortValue()
return name

336
code/datums/chat_message.dm Normal file
View File

@@ -0,0 +1,336 @@
#define CHAT_MESSAGE_SPAWN_TIME 0.2 SECONDS
#define CHAT_MESSAGE_LIFESPAN 5 SECONDS
#define CHAT_MESSAGE_EOL_FADE 0.7 SECONDS
#define CHAT_MESSAGE_EXP_DECAY 0.8 // Messages decay at pow(factor, idx in stack)
#define CHAT_MESSAGE_HEIGHT_DECAY 0.7 // Increase message decay based on the height of the message
#define CHAT_MESSAGE_APPROX_LHEIGHT 11 // Approximate height in pixels of an 'average' line, used for height decay
#define CHAT_MESSAGE_WIDTH 96 // pixels
#define CHAT_MESSAGE_EXT_WIDTH 128
#define CHAT_MESSAGE_LENGTH 68 // characters
#define CHAT_MESSAGE_EXT_LENGTH 150
#define CHAT_MESSAGE_MOB 1
#define CHAT_MESSAGE_OBJ 2
#define WXH_TO_HEIGHT(x) text2num(copytext((x), findtextEx((x), "x") + 1)) // thanks lummox
#define CHAT_RUNE_EMOTE 0x1
#define CHAT_RUNE_RADIO 0x2
/**
* # Chat Message Overlay
*
* Datum for generating a message overlay on the map
* Ported from TGStation; https://github.com/tgstation/tgstation/pull/50608/, author: bobbahbrown
*/
// Cached runechat icon
var/list/runechat_image_cache = list()
/hook/startup/proc/runechat_images()
var/image/radio_image = image('icons/UI_Icons/chat/chat_icons.dmi', icon_state = "radio")
runechat_image_cache["radio"] = radio_image
var/image/emote_image = image('icons/UI_Icons/chat/chat_icons.dmi', icon_state = "emote")
runechat_image_cache["emote"] = emote_image
return TRUE
/datum/chatmessage
/// The visual element of the chat messsage
var/image/message
/// The location in which the message is appearing
var/atom/message_loc
/// The client who heard this message
var/client/owned_by
/// Contains the scheduled destruction time
var/scheduled_destruction
/// Contains the approximate amount of lines for height decay
var/approx_lines
/// If we are currently processing animation and cleanup at EOL
var/ending_life
/**
* Constructs a chat message overlay
*
* Arguments:
* * text - The text content of the overlay
* * target - The target atom to display the overlay at
* * owner - The mob that owns this overlay, only this mob will be able to view it
* * extra_classes - Extra classes to apply to the span that holds the text
* * lifespan - The lifespan of the message in deciseconds
*/
/datum/chatmessage/New(text, atom/target, mob/owner, list/extra_classes = null, lifespan = CHAT_MESSAGE_LIFESPAN)
. = ..()
if(!istype(target))
CRASH("Invalid target given for chatmessage")
if(!istype(owner) || QDELETED(owner) || !owner.client)
stack_trace("/datum/chatmessage created with [isnull(owner) ? "null" : "invalid"] mob owner")
qdel(src)
return
generate_image(text, target, owner, extra_classes, lifespan)
/datum/chatmessage/Destroy()
if(owned_by)
UnregisterSignal(owned_by, COMSIG_PARENT_QDELETING)
LAZYREMOVEASSOC(owned_by.seen_messages, message_loc, src)
owned_by.images.Remove(message)
if(message_loc)
UnregisterSignal(message_loc, COMSIG_PARENT_QDELETING)
owned_by = null
message_loc = null
message = null
return ..()
/**
* Generates a chat message image representation
*
* Arguments:
* * text - The text content of the overlay
* * target - The target atom to display the overlay at
* * owner - The mob that owns this overlay, only this mob will be able to view it
* * extra_classes - Extra classes to apply to the span that holds the text
* * lifespan - The lifespan of the message in deciseconds
*/
/datum/chatmessage/proc/generate_image(text, atom/target, mob/owner, list/extra_classes, lifespan)
set waitfor = FALSE
if(!target || !owner)
qdel(src)
return
// Register client who owns this message
owned_by = owner.client
RegisterSignal(owned_by, COMSIG_PARENT_QDELETING, .proc/qdel_self)
var/extra_length = owned_by.is_preference_enabled(/datum/client_preference/runechat_long_messages)
var/maxlen = extra_length ? CHAT_MESSAGE_EXT_LENGTH : CHAT_MESSAGE_LENGTH
var/msgwidth = extra_length ? CHAT_MESSAGE_EXT_WIDTH : CHAT_MESSAGE_WIDTH
// Clip message
if(length_char(text) > maxlen)
text = copytext_char(text, 1, maxlen + 1) + "..." // BYOND index moment
// Calculate target color if not already present
if(!target.chat_color || target.chat_color_name != target.name)
target.chat_color = colorize_string(target.name)
target.chat_color_darkened = colorize_string(target.name, 0.85, 0.85)
target.chat_color_name = target.name
// Get rid of any URL schemes that might cause BYOND to automatically wrap something in an anchor tag
var/static/regex/url_scheme = new(@"[A-Za-z][A-Za-z0-9+-\.]*:\/\/", "g")
text = replacetext(text, url_scheme, "")
// Reject whitespace
var/static/regex/whitespace = new(@"^\s*$")
if(whitespace.Find(text))
qdel(src)
return
// Non mobs speakers can be small
if(!ismob(target))
extra_classes |= "small"
// If we heard our name, it's important
// Differnt from our own system of name emphasis, maybe unify
var/list/names = splittext(owner.name, " ")
for (var/word in names)
text = replacetext(text, word, "<b>[word]</b>")
var/list/prefixes
// Append prefixes
if(extra_classes.Find("virtual-speaker"))
LAZYADD(prefixes, "\icon[runechat_image_cache["radio"]]")
if(extra_classes.Find("emote"))
// Icon on both ends?
//var/image/I = runechat_image_cache["emote"]
//text = "\icon[I][text]\icon[I]"
// Icon on one end?
//LAZYADD(prefixes, "\icon[runechat_image_cache["emote"]]")
// Asterisks instead?
text = "*&nbsp;[text]&nbsp;*"
text = "[prefixes?.Join("&nbsp;")][text]"
text = encode_html_emphasis(text)
// We dim italicized text to make it more distinguishable from regular text
var/tgt_color = extra_classes.Find("italics") ? target.chat_color_darkened : target.chat_color
// Approximate text height
var/complete_text = "<span class='center maptext [extra_classes != null ? extra_classes.Join(" ") : ""]' style='color: [tgt_color];'>[text]</span>"
var/mheight = WXH_TO_HEIGHT(owned_by.MeasureText(complete_text, null, msgwidth))
approx_lines = max(1, mheight / CHAT_MESSAGE_APPROX_LHEIGHT)
// Translate any existing messages upwards, apply exponential decay factors to timers
message_loc = target
RegisterSignal(message_loc, COMSIG_PARENT_QDELETING, .proc/qdel_self)
if(owned_by.seen_messages)
var/idx = 1
var/combined_height = approx_lines
for(var/msg in owned_by.seen_messages[message_loc])
var/datum/chatmessage/m = msg
animate(m.message, pixel_y = m.message.pixel_y + mheight, time = CHAT_MESSAGE_SPAWN_TIME)
combined_height += m.approx_lines
if(!m.ending_life) // Don't bother!
var/sched_remaining = m.scheduled_destruction - world.time
if(sched_remaining > CHAT_MESSAGE_SPAWN_TIME)
var/remaining_time = (sched_remaining) * (CHAT_MESSAGE_EXP_DECAY ** idx++) * (CHAT_MESSAGE_HEIGHT_DECAY ** combined_height)
m.scheduled_destruction = world.time + remaining_time
spawn(remaining_time)
m.end_of_life()
// Build message image
message = image(loc = message_loc, layer = ABOVE_MOB_LAYER)
message.plane = PLANE_RUNECHAT
message.appearance_flags = APPEARANCE_UI_IGNORE_ALPHA | KEEP_APART
message.alpha = 0
message.pixel_y = owner.bound_height * 0.95
message.maptext_width = msgwidth
message.maptext_height = mheight
message.maptext_x = (CHAT_MESSAGE_WIDTH - owner.bound_width) * -0.5
message.maptext = complete_text
if(owner.contains(target)) // Special case, holding an atom speaking (pAI, recorder...)
message.plane = PLANE_PLAYER_HUD_ABOVE
// View the message
LAZYADDASSOCLIST(owned_by.seen_messages, message_loc, src)
owned_by.images += message
animate(message, alpha = 255, time = CHAT_MESSAGE_SPAWN_TIME)
// Prepare for destruction
scheduled_destruction = world.time + (lifespan - CHAT_MESSAGE_EOL_FADE)
spawn(lifespan - CHAT_MESSAGE_EOL_FADE)
end_of_life()
/**
* Applies final animations to overlay CHAT_MESSAGE_EOL_FADE deciseconds prior to message deletion
*/
/datum/chatmessage/proc/end_of_life(fadetime = CHAT_MESSAGE_EOL_FADE)
if(gc_destroyed || ending_life)
return
ending_life = TRUE
animate(message, alpha = 0, time = fadetime, flags = ANIMATION_PARALLEL)
spawn(fadetime)
qdel(src)
/**
* Creates a message overlay at a defined location for a given speaker
*
* Arguments:
* * speaker - The atom who is saying this message
* * message - The text content of the message
* * italics - Decides if this should be small or not, as generally italics text are for whisper/radio overhear
* * existing_extra_classes - Additional classes to add to the message
*/
/mob/proc/create_chat_message(atom/movable/speaker, message, italics, list/existing_extra_classes, audible = TRUE)
if(!client)
return
// Doesn't want to hear
if(ismob(speaker) && !client.is_preference_enabled(/datum/client_preference/runechat_mob))
return
else if(isobj(speaker) && !client.is_preference_enabled(/datum/client_preference/runechat_obj))
return
// Incapable of receiving
if((audible && is_deaf()) || (!audible && is_blind()))
return
// Check for virtual speakers (aka hearing a message through a radio)
if(existing_extra_classes.Find("radio"))
return
/* Not currently necessary
message = strip_html_properly(message)
if(!message)
return
*/
var/list/extra_classes = list()
extra_classes += existing_extra_classes
if(italics)
extra_classes |= "italics"
if(client.is_preference_enabled(/datum/client_preference/runechat_border))
extra_classes |= "black_outline"
var/dist = get_dist(src, speaker)
switch (dist)
if(4 to 5)
extra_classes |= "small"
if(5 to 16)
extra_classes |= "very_small"
// Display visual above source
new /datum/chatmessage(message, speaker, src, extra_classes)
// Tweak these defines to change the available color ranges
#define CM_COLOR_SAT_MIN 0.6
#define CM_COLOR_SAT_MAX 0.95
#define CM_COLOR_LUM_MIN 0.70
#define CM_COLOR_LUM_MAX 0.90
/**
* Gets a color for a name, will return the same color for a given string consistently within a round.atom
*
* Note that this proc aims to produce pastel-ish colors using the HSL colorspace. These seem to be favorable for displaying on the map.
*
* Arguments:
* * name - The name to generate a color for
* * sat_shift - A value between 0 and 1 that will be multiplied against the saturation
* * lum_shift - A value between 0 and 1 that will be multiplied against the luminescence
*/
/datum/chatmessage/proc/colorize_string(name, sat_shift = 1, lum_shift = 1)
// seed to help randomness
var/static/rseed = rand(1,26)
// get hsl using the selected 6 characters of the md5 hash
var/hash = copytext(md5(name + "[world_startup_time]"), rseed, rseed + 6)
var/h = hex2num(copytext(hash, 1, 3)) * (360 / 255)
var/s = (hex2num(copytext(hash, 3, 5)) >> 2) * ((CM_COLOR_SAT_MAX - CM_COLOR_SAT_MIN) / 63) + CM_COLOR_SAT_MIN
var/l = (hex2num(copytext(hash, 5, 7)) >> 2) * ((CM_COLOR_LUM_MAX - CM_COLOR_LUM_MIN) / 63) + CM_COLOR_LUM_MIN
// adjust for shifts
s *= clamp(sat_shift, 0, 1)
l *= clamp(lum_shift, 0, 1)
// convert to rgba
var/h_int = round(h/60) // mapping each section of H to 60 degree sections
var/c = (1 - abs(2 * l - 1)) * s
var/x = c * (1 - abs((h / 60) % 2 - 1))
var/m = l - c * 0.5
x = (x + m) * 255
c = (c + m) * 255
m *= 255
switch(h_int)
if(0)
return rgb(c,x,m)
if(1)
return rgb(x,c,m)
if(2)
return rgb(m,c,x)
if(3)
return rgb(m,x,c)
if(4)
return rgb(x,m,c)
if(5)
return rgb(c,m,x)
/atom/proc/runechat_message(message, range = world.view, italics, list/classes = list(), audible = TRUE)
var/list/hear = get_mobs_and_objs_in_view_fast(get_turf(src), range, remote_ghosts = FALSE)
var/list/hearing_mobs = hear["mobs"]
for(var/mob in hearing_mobs)
var/mob/M = mob
if(!M.client)
continue
M.create_chat_message(src, message, italics, classes, audible)

View File

@@ -213,10 +213,10 @@
*
* Arguments:
* * datum/target Datum to stop listening to signals from
* * sig_typeor_types Signal string key or list of signal keys to stop listening to specifically
* * sig_type_or_types Signal string key or list of signal keys to stop listening to specifically
*/
/datum/proc/UnregisterSignal(datum/target, sig_type_or_types)
var/list/lookup = target.comp_lookup
var/list/lookup = target?.comp_lookup
if(!signal_procs || !signal_procs[target] || !lookup)
return
if(!islist(sig_type_or_types))

View File

@@ -1,7 +0,0 @@
datum
computer
var/name
folder
var/list/datum/computer/contents = list()
file

View File

@@ -6,11 +6,11 @@
/datum/events
var/list/events
New()
/datum/events/New()
..()
events = new
proc/addEventType(event_type as text)
/datum/events/proc/addEventType(event_type as text)
if(!(event_type in events) || !islist(events[event_type]))
events[event_type] = list()
return 1
@@ -19,7 +19,7 @@
// Arguments: event_type as text, proc_holder as datum, proc_name as text
// Returns: New event, null on error.
proc/addEvent(event_type as text, proc_holder, proc_name as text)
/datum/events/proc/addEvent(event_type as text, proc_holder, proc_name as text)
if(!event_type || !proc_holder || !proc_name)
return
addEventType(event_type)
@@ -30,7 +30,7 @@
// Arguments: event_type as text, any number of additional arguments to pass to event handler
// Returns: null
proc/fireEvent()
/datum/events/proc/fireEvent()
//to_world("Events in [args[1]] called")
var/list/event = listgetindex(events,args[1])
if(istype(event))
@@ -42,7 +42,7 @@
// Arguments: event_type as text, E as /datum/event
// Returns: 1 if event cleared, null on error
proc/clearEvent(event_type as text, datum/event/E)
/datum/events/proc/clearEvent(event_type as text, datum/event/E)
if(!event_type || !E)
return
var/list/event = listgetindex(events,event_type)
@@ -54,12 +54,12 @@
var/listener
var/proc_name
New(tlistener,tprocname)
/datum/event/New(tlistener,tprocname)
listener = tlistener
proc_name = tprocname
return ..()
proc/Fire()
/datum/event/proc/Fire()
//to_world("Event fired")
if(listener)
call(listener,proc_name)(arglist(args))

View File

@@ -29,7 +29,7 @@ var/global/datum/getrev/revdata = new()
to_world_log(date)
to_world_log(revision)
client/verb/showrevinfo()
/client/verb/showrevinfo()
set category = "OOC"
set name = "Show Server Revision"
set desc = "Check the current server code revision"

View File

@@ -1,160 +0,0 @@
/*
DO NOT USE THIS. THIS IS BEING DEPRECATED BY PROCESSING SUBSYSTEMS (controllers/subsystems/processing) AND TIMERS.
*/
/*
README:
The global_iterator datum is supposed to provide a simple and robust way to
create some constantly "looping" processes with ability to stop and restart them at will.
Generally, the only thing you want to play with (meaning, redefine) is the process() proc.
It must contain all the things you want done.
Control functions:
new - used to create datum. First argument (optional) - var list(to use in process() proc) as list,
second (optional) - autostart control.
If autostart == TRUE, the loop will be started immediately after datum creation.
start(list/arguments) - starts the loop. Takes arguments(optional) as a list, which is then used
by process() proc. Returns null if datum already active, 1 if loop started succesfully and 0 if there's
an error in supplied arguments (not list or empty list).
stop() - stops the loop. Returns null if datum is already inactive and 1 on success.
set_delay(new_delay) - sets the delay between iterations. Pretty selfexplanatory.
Returns 0 on error(new_delay is not numerical), 1 otherwise.
set_process_args(list/arguments) - passes the supplied arguments to the process() proc.
active() - Returns 1 if datum is active, 0 otherwise.
toggle() - toggles datum state. Returns new datum state (see active()).
Misc functions:
get_last_exec_time() - Returns the time of last iteration.
get_last_exec_time_as_text() - Returns the time of last iteration as text
Control vars:
delay - delay between iterations
check_for_null - if equals TRUE, on each iteration the supplied arguments will be checked for nulls.
If some varible equals null (and null only), the loop is stopped.
Usefull, if some var unexpectedly becomes null - due to object deletion, for example.
Of course, you can also check the variables inside process() proc to prevent runtime errors.
Data storage vars:
result - stores the value returned by process() proc
*/
/datum/global_iterator
var/control_switch = 0
var/delay = 10
var/list/arg_list = new
var/last_exec = null
var/check_for_null = 1
var/forbid_garbage = 0
var/result
var/state = 0
New(list/arguments=null,autostart=1)
delay = delay>0?(delay):1
if(forbid_garbage) //prevents garbage collection with tag != null
tag = "\ref[src]"
set_process_args(arguments)
if(autostart)
start()
return
proc/main()
state = 1
while(src && control_switch)
last_exec = world.timeofday
if(check_for_null && has_null_args())
stop()
return 0
result = process(arglist(arg_list))
for(var/sleep_time=delay;sleep_time>0;sleep_time--) //uhh, this is ugly. But I see no other way to terminate sleeping proc. Such disgrace.
if(!control_switch)
return 0
sleep(1)
return 0
proc/start(list/arguments=null)
if(active())
return
if(arguments)
if(!set_process_args(arguments))
return 0
if(!state_check()) //the main loop is sleeping, wait for it to terminate.
return
control_switch = 1
spawn()
state = main()
return 1
proc/stop()
if(!active())
return
control_switch = 0
spawn(-1) //report termination error but don't wait for state_check().
state_check()
return 1
proc/state_check()
var/lag = 0
while(state)
sleep(1)
if(++lag>10)
CRASH("The global_iterator loop \ref[src] failed to terminate in designated timeframe. This may be caused by server lagging.")
return 1
proc/active()
return control_switch
proc/has_null_args()
if(null in arg_list)
return 1
return 0
proc/set_delay(new_delay)
if(isnum(new_delay))
delay = max(1, round(new_delay))
return 1
else
return 0
proc/get_last_exec_time()
return (last_exec||0)
proc/get_last_exec_time_as_text()
return (time2text(last_exec)||"Wasn't executed yet")
proc/set_process_args(list/arguments)
if(arguments && istype(arguments, /list) && arguments.len)
arg_list = arguments
return 1
else
// to_world("<span class='danger'>Invalid arguments supplied for [src.type], ref = \ref[src]</span>")
return 0
proc/toggle_null_checks()
check_for_null = !check_for_null
return check_for_null
proc/toggle()
if(!stop())
start()
return active()
/datum/global_iterator/Destroy()
tag = null
arg_list.Cut()
stop()
return QDEL_HINT_LETMELIVE
//Do not call ..()

View File

@@ -2,59 +2,59 @@
var/href
var/list/href_list
New(thref,list/thref_list)
/datum/topic_input/New(thref,list/thref_list)
href = thref
href_list = thref_list.Copy()
return
proc/get(i)
/datum/topic_input/proc/get(i)
return listgetindex(href_list,i)
proc/getAndLocate(i)
/datum/topic_input/proc/getAndLocate(i)
var/t = get(i)
if(t)
t = locate(t)
return t || null
proc/getNum(i)
/datum/topic_input/proc/getNum(i)
var/t = get(i)
if(t)
t = text2num(t)
return isnum(t) ? t : null
proc/getObj(i)
/datum/topic_input/proc/getObj(i)
var/t = getAndLocate(i)
return isobj(t) ? t : null
proc/getMob(i)
/datum/topic_input/proc/getMob(i)
var/t = getAndLocate(i)
return ismob(t) ? t : null
proc/getTurf(i)
/datum/topic_input/proc/getTurf(i)
var/t = getAndLocate(i)
return isturf(t) ? t : null
proc/getAtom(i)
/datum/topic_input/proc/getAtom(i)
return getType(i,/atom)
proc/getArea(i)
/datum/topic_input/proc/getArea(i)
var/t = getAndLocate(i)
return isarea(t) ? t : null
proc/getStr(i)//params should always be text, but...
/datum/topic_input/proc/getStr(i)//params should always be text, but...
var/t = get(i)
return istext(t) ? t : null
proc/getType(i,type)
/datum/topic_input/proc/getType(i,type)
var/t = getAndLocate(i)
return istype(t,type) ? t : null
proc/getPath(i)
/datum/topic_input/proc/getPath(i)
var/t = get(i)
if(t)
t = text2path(t)
return ispath(t) ? t : null
proc/getList(i)
/datum/topic_input/proc/getList(i)
var/t = getAndLocate(i)
return islist(t) ? t : null

View File

@@ -4,7 +4,7 @@
/client/can_vv_get(var_name)
return var_name != NAMEOF(src, feedback_form) // No snooping.
GENERAL_PROTECT_DATUM(datum/managed_browser/feedback_form)
GENERAL_PROTECT_DATUM(/datum/managed_browser/feedback_form)
// A fairly simple object to hold information about a player's feedback as it's being written.
// Having this be it's own object instead of being baked into /mob/new_player allows for it to be used

View File

@@ -14,7 +14,7 @@
// III. Thou shalt not write a decl that relies on arguments supplied to New().
// IV. Thou shalt not call Initialize() on a /decl.
var/repository/decls/decls_repository = new()
var/repository/decls/decls_repository // Initialiozed in /datum/global_init/New()
/repository/decls
var/list/fetched_decls

View File

@@ -109,7 +109,7 @@
containertype = /obj/structure/closet/crate/gilthari
containername = "Formal suit crate"
datum/supply_pack/costumes/witch
/datum/supply_pack/costumes/witch
name = "Witch costume"
containername = "Witch costume"
containertype = /obj/structure/closet/crate/nanothreads

View File

@@ -51,7 +51,7 @@
/obj/item/weapon/reagent_containers/glass/paint/purple,
/obj/item/weapon/reagent_containers/glass/paint/black,
/obj/item/weapon/reagent_containers/glass/paint/white,
/obj/item/weapon/contraband/poster/custom,
/obj/item/poster/custom,
/obj/item/weapon/wrapping_paper = 3
)
cost = 10

View File

@@ -419,7 +419,8 @@
/obj/item/clothing/accessory/holster,
/obj/item/clothing/accessory/holster/armpit,
/obj/item/clothing/accessory/holster/waist,
/obj/item/clothing/accessory/holster/hip
/obj/item/clothing/accessory/holster/hip,
/obj/item/clothing/accessory/holster/leg
)
cost = 15
containertype = /obj/structure/closet/crate/hedberg
@@ -663,9 +664,9 @@
/datum/supply_pack/security/posters
name = "Gear - Morale Posters"
contains = list(
/obj/item/weapon/contraband/poster/nanotrasen = 6
/obj/item/poster/nanotrasen = 6
)
cost = 20
cost = 10
containertype = /obj/structure/closet/crate/secure/nanotrasen
containername = "Morale Posters"
access = access_maint_tunnels

View File

@@ -12,7 +12,7 @@
var/display_name // For displaying in text
var/gender = NEUTER
datum/category_group/underwear/dd_SortValue()
/datum/category_group/underwear/dd_SortValue()
return sort_order
/datum/category_group/underwear/top

View File

@@ -6,7 +6,7 @@
..()
items = list()
datum/uplink_category/ammunition
/datum/uplink_category/ammunition
name = "Ammunition"
/datum/uplink_category/services

View File

@@ -95,7 +95,7 @@ var/datum/uplink/uplink = new()
log_and_message_admins("\the [M] bought \a [src] through the uplink")
M.mind.purchase_log[src] += 1
datum/uplink_item/dd_SortValue()
/datum/uplink_item/dd_SortValue()
return item_cost
/********************************

View File

@@ -4,10 +4,10 @@
anchored = 1
density = 1
attackby(obj/item/weapon/W as obj, mob/user as mob)
/obj/structure/signpost/attackby(obj/item/weapon/W as obj, mob/user as mob)
return attack_hand(user)
attack_hand(mob/user as mob)
/obj/structure/signpost/attack_hand(mob/user as mob)
switch(alert("Travel back to ss13?",,"Yes","No"))
if("Yes")
if(user.z != src.z) return
@@ -99,7 +99,7 @@
drop_sound = 'sound/items/drop/rubber.ogg'
pickup_sound = 'sound/items/pickup/rubber.ogg'
afterattack(atom/target as mob|obj|turf|area, mob/user as mob)
/obj/item/weapon/beach_ball/afterattack(atom/target as mob|obj|turf|area, mob/user as mob)
user.drop_item()
src.throw_at(target, throw_range, throw_speed, user)

View File

@@ -37,18 +37,18 @@ length to avoid portals or something i guess?? Not that they're counted right no
// Also added 'exclude' turf to avoid travelling over; defaults to null
PriorityQueue
/PriorityQueue
var/list/queue
var/comparison_function
New(compare)
/PriorityQueue/New(compare)
queue = list()
comparison_function = compare
proc/IsEmpty()
/PriorityQueue/proc/IsEmpty()
return !queue.len
proc/Enqueue(var/data)
/PriorityQueue/proc/Enqueue(var/data)
queue.Add(data)
var/index = queue.len
@@ -57,12 +57,12 @@ PriorityQueue
queue.Swap(index, index / 2)
index /= 2
proc/Dequeue()
/PriorityQueue/proc/Dequeue()
if(!queue.len)
return 0
return Remove(1)
proc/Remove(var/index)
/PriorityQueue/proc/Remove(var/index)
if(index > queue.len)
return 0
@@ -73,7 +73,7 @@ PriorityQueue
FixQueue(index)
return thing
proc/FixQueue(var/index)
/PriorityQueue/proc/FixQueue(var/index)
var/child = 2 * index
var/item = queue[index]
@@ -88,18 +88,18 @@ PriorityQueue
child = 2 * index
queue[index] = item
proc/List()
/PriorityQueue/proc/List()
return queue.Copy()
proc/Length()
/PriorityQueue/proc/Length()
return queue.len
proc/RemoveItem(data)
/PriorityQueue/proc/RemoveItem(data)
var/index = queue.Find(data)
if(index)
return Remove(index)
PathNode
/PathNode
var/datum/position
var/PathNode/previous_node
@@ -109,7 +109,7 @@ PathNode
var/cost
var/nodes_traversed
New(_position, _previous_node, _known_cost, _cost, _nodes_traversed)
/PathNode/New(_position, _previous_node, _known_cost, _cost, _nodes_traversed)
position = _position
previous_node = _previous_node
@@ -120,10 +120,10 @@ PathNode
best_estimated_cost = estimated_cost
nodes_traversed = _nodes_traversed
proc/PathWeightCompare(PathNode/a, PathNode/b)
/proc/PathWeightCompare(PathNode/a, PathNode/b)
return a.estimated_cost - b.estimated_cost
proc/AStar(var/start, var/end, var/adjacent, var/dist, var/max_nodes, var/max_node_depth = 30, var/min_target_dist = 0, var/min_node_dist, var/id, var/datum/exclude)
/proc/AStar(var/start, var/end, var/adjacent, var/dist, var/max_nodes, var/max_node_depth = 30, var/min_target_dist = 0, var/min_node_dist, var/id, var/datum/exclude)
var/PriorityQueue/open = new /PriorityQueue(/proc/PathWeightCompare)
var/list/closed = list()
var/list/path

View File

@@ -50,7 +50,7 @@
Sound(message_sound, zlevels)
Log(message, message_title)
datum/announcement/proc/Message(message as text, message_title as text, var/list/zlevels)
/datum/announcement/proc/Message(message as text, message_title as text, var/list/zlevels)
for(var/mob/M in player_list)
if(!istype(M,/mob/new_player) && !isdeaf(M))
to_chat(M, "<h2 class='alert'>[title]</h2>")
@@ -59,17 +59,17 @@ datum/announcement/proc/Message(message as text, message_title as text, var/list
to_chat(M, "<span class='alert'> -[html_encode(announcer)]</span>")
// You'll need to update these to_world usages if you want to make these z-level specific ~Aro
datum/announcement/minor/Message(message as text, message_title as text)
/datum/announcement/minor/Message(message as text, message_title as text)
to_world("<b>[message]</b>")
datum/announcement/priority/Message(message as text, message_title as text)
/datum/announcement/priority/Message(message as text, message_title as text)
to_world("<h1 class='alert'>[message_title]</h1>")
to_world("<span class='alert'>[message]</span>")
if(announcer)
to_world("<span class='alert'> -[html_encode(announcer)]</span>")
to_world("<br>")
datum/announcement/priority/command/Message(message as text, message_title as text, var/list/zlevels)
/datum/announcement/priority/command/Message(message as text, message_title as text, var/list/zlevels)
var/command
command += "<h1 class='alert'>[command_name()] Update</h1>"
if (message_title)
@@ -83,11 +83,11 @@ datum/announcement/priority/command/Message(message as text, message_title as te
if(!istype(M,/mob/new_player) && !isdeaf(M))
to_chat(M, command)
datum/announcement/priority/security/Message(message as text, message_title as text)
/datum/announcement/priority/security/Message(message as text, message_title as text)
to_world("<font size=4 color='red'>[message_title]</font>")
to_world("<font color='red'>[message]</font>")
datum/announcement/proc/NewsCast(message as text, message_title as text)
/datum/announcement/proc/NewsCast(message as text, message_title as text)
if(!newscast)
return
@@ -99,7 +99,7 @@ datum/announcement/proc/NewsCast(message as text, message_title as text)
news.can_be_redacted = 0
announce_newscaster_news(news)
datum/announcement/proc/PlaySound(var/message_sound, var/list/zlevels)
/datum/announcement/proc/PlaySound(var/message_sound, var/list/zlevels)
if(!message_sound)
return
@@ -109,17 +109,17 @@ datum/announcement/proc/PlaySound(var/message_sound, var/list/zlevels)
if(!istype(M,/mob/new_player) && !isdeaf(M))
M << message_sound
datum/announcement/proc/Sound(var/message_sound, var/list/zlevels)
/datum/announcement/proc/Sound(var/message_sound, var/list/zlevels)
PlaySound(message_sound, zlevels)
datum/announcement/priority/Sound(var/message_sound)
/datum/announcement/priority/Sound(var/message_sound)
if(message_sound)
world << message_sound
datum/announcement/priority/command/Sound(var/message_sound)
/datum/announcement/priority/command/Sound(var/message_sound)
PlaySound(message_sound)
datum/announcement/proc/Log(message as text, message_title as text)
/datum/announcement/proc/Log(message as text, message_title as text)
if(log)
log_game("[key_name(usr)] has made \a [announcement_type]: [message_title] - [message] - [announcer]")
message_admins("[key_name_admin(usr)] has made \a [announcement_type].", 1)

View File

@@ -38,7 +38,7 @@ var/DB_SERVER = "" // This is the location of your MySQL server (localhost is US
var/DB_PORT = 3306 // This is the port your MySQL server is running on (3306 is the default)
*/
DBConnection
/DBConnection
var/_db_con // This variable contains a reference to the actual database connection.
var/dbi // This variable is a string containing the DBI MySQL requires.
var/user // This variable contains the username data.
@@ -48,14 +48,14 @@ DBConnection
var/server = ""
var/port = 3306
DBConnection/New(dbi_handler,username,password_handler,cursor_handler)
/DBConnection/New(dbi_handler,username,password_handler,cursor_handler)
src.dbi = dbi_handler
src.user = username
src.password = password_handler
src.default_cursor = cursor_handler
_db_con = _dm_db_new_con()
DBConnection/proc/Connect(dbi_handler=src.dbi,user_handler=src.user,password_handler=src.password,cursor_handler)
/DBConnection/proc/Connect(dbi_handler=src.dbi,user_handler=src.user,password_handler=src.password,cursor_handler)
if(!config.sql_enabled)
return 0
if(!src) return 0
@@ -63,24 +63,24 @@ DBConnection/proc/Connect(dbi_handler=src.dbi,user_handler=src.user,password_han
if(!cursor_handler) cursor_handler = Default_Cursor
return _dm_db_connect(_db_con,dbi_handler,user_handler,password_handler,cursor_handler,null)
DBConnection/proc/Disconnect() return _dm_db_close(_db_con)
/DBConnection/proc/Disconnect() return _dm_db_close(_db_con)
DBConnection/proc/IsConnected()
/DBConnection/proc/IsConnected()
if(!config.sql_enabled) return 0
var/success = _dm_db_is_connected(_db_con)
return success
DBConnection/proc/Quote(str) return _dm_db_quote(_db_con,str)
/DBConnection/proc/Quote(str) return _dm_db_quote(_db_con,str)
DBConnection/proc/ErrorMsg() return _dm_db_error_msg(_db_con)
DBConnection/proc/SelectDB(database_name,dbi)
/DBConnection/proc/ErrorMsg() return _dm_db_error_msg(_db_con)
/DBConnection/proc/SelectDB(database_name,dbi)
if(IsConnected()) Disconnect()
//return Connect("[dbi?"[dbi]":"dbi:mysql:[database_name]:[DB_SERVER]:[DB_PORT]"]",user,password)
return Connect("[dbi?"[dbi]":"dbi:mysql:[database_name]:[sqladdress]:[sqlport]"]",user,password)
DBConnection/proc/NewQuery(sql_query,cursor_handler=src.default_cursor) return new/DBQuery(sql_query,src,cursor_handler)
/DBConnection/proc/NewQuery(sql_query,cursor_handler=src.default_cursor) return new/DBQuery(sql_query,src,cursor_handler)
DBQuery/New(sql_query,DBConnection/connection_handler,cursor_handler)
/DBQuery/New(sql_query,DBConnection/connection_handler,cursor_handler)
if(sql_query) src.sql = sql_query
if(connection_handler) src.db_connection = connection_handler
if(cursor_handler) src.default_cursor = cursor_handler
@@ -88,7 +88,7 @@ DBQuery/New(sql_query,DBConnection/connection_handler,cursor_handler)
return ..()
DBQuery
/DBQuery
var/sql // The sql query being executed.
var/default_cursor
var/list/columns //list of DB Columns populated by Columns()
@@ -98,26 +98,26 @@ DBQuery
var/DBConnection/db_connection
var/_db_query
DBQuery/proc/Connect(DBConnection/connection_handler) src.db_connection = connection_handler
/DBQuery/proc/Connect(DBConnection/connection_handler) src.db_connection = connection_handler
DBQuery/proc/Execute(sql_query=src.sql,cursor_handler=default_cursor)
/DBQuery/proc/Execute(sql_query=src.sql,cursor_handler=default_cursor)
Close()
return _dm_db_execute(_db_query,sql_query,db_connection._db_con,cursor_handler,null)
DBQuery/proc/NextRow() return _dm_db_next_row(_db_query,item,conversions)
/DBQuery/proc/NextRow() return _dm_db_next_row(_db_query,item,conversions)
DBQuery/proc/RowsAffected() return _dm_db_rows_affected(_db_query)
/DBQuery/proc/RowsAffected() return _dm_db_rows_affected(_db_query)
DBQuery/proc/RowCount() return _dm_db_row_count(_db_query)
/DBQuery/proc/RowCount() return _dm_db_row_count(_db_query)
DBQuery/proc/ErrorMsg() return _dm_db_error_msg(_db_query)
/DBQuery/proc/ErrorMsg() return _dm_db_error_msg(_db_query)
DBQuery/proc/Columns()
/DBQuery/proc/Columns()
if(!columns)
columns = _dm_db_columns(_db_query,/DBColumn)
return columns
DBQuery/proc/GetRowData()
/DBQuery/proc/GetRowData()
var/list/columns = Columns()
var/list/results
if(columns.len)
@@ -128,23 +128,23 @@ DBQuery/proc/GetRowData()
results[C] = src.item[(cur_col.position+1)]
return results
DBQuery/proc/Close()
/DBQuery/proc/Close()
item.len = 0
columns = null
conversions = null
return _dm_db_close(_db_query)
DBQuery/proc/Quote(str)
/DBQuery/proc/Quote(str)
return db_connection.Quote(str)
DBQuery/proc/SetConversion(column,conversion)
/DBQuery/proc/SetConversion(column,conversion)
if(istext(column)) column = columns.Find(column)
if(!conversions) conversions = new/list(column)
else if(conversions.len < column) conversions.len = column
conversions[column] = conversion
DBColumn
/DBColumn
var/name
var/table
var/position //1-based index into item data
@@ -153,7 +153,7 @@ DBColumn
var/length
var/max_length
DBColumn/New(name_handler,table_handler,position_handler,type_handler,flag_handler,length_handler,max_length_handler)
/DBColumn/New(name_handler,table_handler,position_handler,type_handler,flag_handler,length_handler,max_length_handler)
src.name = name_handler
src.table = table_handler
src.position = position_handler
@@ -164,7 +164,7 @@ DBColumn/New(name_handler,table_handler,position_handler,type_handler,flag_handl
return ..()
DBColumn/proc/SqlTypeName(type_handler=src.sql_type)
/DBColumn/proc/SqlTypeName(type_handler=src.sql_type)
switch(type_handler)
if(TINYINT) return "TINYINT"
if(SMALLINT) return "SMALLINT"

View File

@@ -1,168 +0,0 @@
/* sd_Alert library
by Shadowdarke (shadowdarke@byond.com)
sd_Alert() is a powerful and flexible alternative to the built in BYOND
alert() proc. sd_Alert offers timed popups, unlimited buttons, custom
appearance, and even the option to popup without stealing keyboard focus
from the map or command line.
Please see demo.dm for detailed examples.
FORMAT
sd_Alert(who, message, title, buttons, default, duration, unfocus, \
size, table, style, tag, select, flags)
ARGUMENTS
who - the client or mob to display the alert to.
message - text message to display
title - title of the alert box
buttons - list of buttons
Default Value: list("Ok")
default - default button selestion
Default Value: the first button in the list
duration - the number of ticks before this alert expires. If not
set, the alert lasts until a button is clicked.
Default Value: 0 (unlimited)
unfocus - if this value is set, the popup will not steal keyboard
focus from the map or command line.
Default Value: 1 (do not take focus)
size - size of the popup window in px
Default Value: "300x200"
table - optional parameters for the HTML table in the alert
Default Value: "width=100% height=100%" (fill the window)
style - optional style sheet information
tag - lets you specify a certain tag for this sd_Alert so you may manipulate it
externally. (i.e. force the alert to close, change options and redisplay,
reuse the same window, etc.)
select - if set, the buttons will be replaced with a selection box with a number of
lines displayed equal to this value.
Default value: 0 (use buttons)
flags - optional flags effecting the alert display. These flags may be ORed (|)
together for multiple effects.
SD_ALERT_SCROLL = display a scrollbar
SD_ALERT_SELECT_MULTI = forces selection box display (instead of
buttons) allows the user to select multiple
choices.
SD_ALERT_LINKS = display each choice as a plain text link.
Any selection box style overrides this flag.
SD_ALERT_NOVALIDATE = don't validate responses
Default value: SD_ALERT_SCROLL
(button display with scroll bar, validate responses)
RETURNS
The text of the selected button, or null if the alert duration expired
without a button click.
Version 1 changes (from version 0):
* Added the tag, select, and flags arguments, thanks to several suggestions from Foomer.
* Split the sd_Alert/Alert() proc into New(), Display(), and Response() to allow more
customization by developers. Primarily developers would want to use Display() to change
the display of active tagged windows
*/
#define SD_ALERT_SCROLL 1
#define SD_ALERT_SELECT_MULTI 2
#define SD_ALERT_LINKS 4
#define SD_ALERT_NOVALIDATE 8
proc/sd_Alert(client/who, message, title, buttons = list("Ok"),\
default, duration = 0, unfocus = 1, size = "300x200", \
table = "width=100% height=100%", style, tag, select, flags = SD_ALERT_SCROLL)
if(ismob(who))
var/mob/M = who
who = M.client
if(!istype(who)) CRASH("sd_Alert: Invalid target:[who] (\ref[who])")
var/sd_alert/T = locate(tag)
if(T)
if(istype(T)) qdel(T)
else CRASH("sd_Alert: tag \"[tag]\" is already in use by datum '[T]' (type: [T.type])")
T = new(who, tag)
if(duration)
spawn(duration)
if(T) qdel(T)
return
T.Display(message,title,buttons,default,unfocus,size,table,style,select,flags)
. = T.Response()
sd_alert
var
client/target
response
list/validation
Destroy()
target << browse(null,"window=\ref[src]")
..()
New(who, tag)
..()
target = who
src.tag = tag
Topic(href,params[])
if(usr.client != target) return
response = params["clk"]
proc/Display(message,title,list/buttons,default,unfocus,size,table,style,select,flags)
if(unfocus) spawn() target << browse(null,null)
if(istext(buttons)) buttons = list(buttons)
if(!default) default = buttons[1]
if(!(flags & SD_ALERT_NOVALIDATE)) validation = buttons.Copy()
var/html = {"<head><title>[title]</title>[style]<script>\
function c(x) {document.location.href='BYOND://?src=\ref[src];'+x;}\
</script></head><body onLoad="fcs.focus();"\
[(flags&SD_ALERT_SCROLL)?"":" scroll=no"]><table [table]><tr>\
<td>[message]</td></tr><tr><th>"}
if(select || (flags & SD_ALERT_SELECT_MULTI)) // select style choices
html += {"<FORM ID=fcs ACTION='BYOND://?' METHOD=GET>\
<INPUT TYPE=HIDDEN NAME=src VALUE='\ref[src]'>
<SELECT NAME=clk SIZE=[select]\
[(flags & SD_ALERT_SELECT_MULTI)?" MULTIPLE":""]>"}
for(var/b in buttons)
html += "<OPTION[(b == default)?" SELECTED":""]>\
[html_encode(b)]</OPTION>"
html += "</SELECT><BR><INPUT TYPE=SUBMIT VALUE=Submit></FORM>"
else if(flags & SD_ALERT_LINKS) // text link style
for(var/b in buttons)
var/list/L = list()
L["clk"] = b
var/html_string=list2params(L)
var/focus
if(b == default) focus = " ID=fcs"
html += "<A[focus] href=# onClick=\"c('[html_string]')\">[html_encode(b)]</A>\
<BR>"
else // button style choices
for(var/b in buttons)
var/list/L = list()
L["clk"] = b
var/html_string=list2params(L)
var/focus
if(b == default) focus = " ID=fcs"
html += "<INPUT[focus] TYPE=button VALUE='[html_encode(b)]' \
onClick=\"c('[html_string]')\"> "
html += "</th></tr></table></body>"
target << browse(html,"window=\ref[src];size=[size];can_close=0")
proc/Response()
var/validated
while(!validated)
while(target && !response) // wait for a response
sleep(2)
if(response && validation)
if(istype(response, /list))
var/list/L = response - validation
if(L.len) response = null
else validated = 1
else if(response in validation) validated = 1
else response=null
else validated = 1
spawn(2) qdel(src)
return response

View File

@@ -1,4 +1,4 @@
proc/sql_poll_population()
/proc/sql_poll_population()
if(!sqllogging)
return
var/admincount = admins.len
@@ -16,16 +16,16 @@ proc/sql_poll_population()
var/err = query.ErrorMsg()
log_game("SQL ERROR during population polling. Error : \[[err]\]\n")
proc/sql_report_round_start()
/proc/sql_report_round_start()
// TODO
if(!sqllogging)
return
proc/sql_report_round_end()
/proc/sql_report_round_end()
// TODO
if(!sqllogging)
return
proc/sql_report_death(var/mob/living/carbon/human/H)
/proc/sql_report_death(var/mob/living/carbon/human/H)
if(!sqllogging)
return
if(!H)
@@ -59,7 +59,7 @@ proc/sql_report_death(var/mob/living/carbon/human/H)
log_game("SQL ERROR during death reporting. Error : \[[err]\]\n")
proc/sql_report_cyborg_death(var/mob/living/silicon/robot/H)
/proc/sql_report_cyborg_death(var/mob/living/silicon/robot/H)
if(!sqllogging)
return
if(!H)
@@ -93,7 +93,7 @@ proc/sql_report_cyborg_death(var/mob/living/silicon/robot/H)
log_game("SQL ERROR during death reporting. Error : \[[err]\]\n")
proc/statistic_cycle()
/proc/statistic_cycle()
set waitfor = 0
if(!sqllogging)
return
@@ -102,7 +102,7 @@ proc/statistic_cycle()
sleep(6000)
//This proc is used for feedback. It is executed at round end.
proc/sql_commit_feedback()
/proc/sql_commit_feedback()
if(!blackbox)
log_game("Round ended without a blackbox recorder. No feedback was sent to the database.")
return

View File

@@ -14,19 +14,6 @@
- To skip equipping with appropriate gear, supply a positive third argument.
*/
// Antagonist datum flags.
#define ANTAG_OVERRIDE_JOB 1 // Assigned job is set to MODE when spawning.
#define ANTAG_OVERRIDE_MOB 2 // Mob is recreated from datum mob_type var when spawning.
#define ANTAG_CLEAR_EQUIPMENT 4 // All preexisting equipment is purged.
#define ANTAG_CHOOSE_NAME 8 // Antagonists are prompted to enter a name.
#define ANTAG_IMPLANT_IMMUNE 16 // Cannot be loyalty implanted.
#define ANTAG_SUSPICIOUS 32 // Shows up on roundstart report.
#define ANTAG_HAS_LEADER 64 // Generates a leader antagonist.
#define ANTAG_HAS_NUKE 128 // Will spawn a nuke at supplied location.
#define ANTAG_RANDSPAWN 256 // Potentially randomly spawns due to events.
#define ANTAG_VOTABLE 512 // Can be voted as an additional antagonist before roundstart.
#define ANTAG_SET_APPEARANCE 1024 // Causes antagonists to use an appearance modifier on spawn.
// Globals.
var/global/list/all_antag_types = list()
var/global/list/all_antag_spawnpoints = list()

View File

@@ -105,7 +105,7 @@ var/datum/antagonist/wizard/wizards
for(var/spell/spell_to_remove in src.spell_list)
remove_spell(spell_to_remove)
obj/item/clothing
/obj/item/clothing
var/wizard_garb = 0
// Does this clothing slot count as wizard garb? (Combines a few checks)

View File

@@ -1473,27 +1473,27 @@ NOTE: there are two lists of areas in the end of this file: centcom and station
dynamic_lighting = 0
ambience = AMBIENCE_SPACE
auxport
/area/solar/auxport
name = "\improper Fore Port Solar Array"
icon_state = "panelsA"
auxstarboard
/area/solar/auxstarboard
name = "\improper Fore Starboard Solar Array"
icon_state = "panelsA"
fore
/area/solar/fore
name = "\improper Fore Solar Array"
icon_state = "yellow"
aft
/area/solar/aft
name = "\improper Aft Solar Array"
icon_state = "aft"
starboard
/area/solar/starboard
name = "\improper Aft Starboard Solar Array"
icon_state = "panelsS"
port
/area/solar/port
name = "\improper Aft Port Solar Array"
icon_state = "panelsP"

View File

@@ -129,7 +129,7 @@
always_unpowered = 1
dynamic_lighting = 0
aft
/area/outpost/engineering/solarsoutside/aft
name = "\improper Engineering Outpost Solar Array"
icon_state = "yellow"

View File

@@ -34,6 +34,15 @@
// Track if we are already had initialize() called to prevent double-initialization.
var/initialized = FALSE
/// Last name used to calculate a color for the chatmessage overlays
var/chat_color_name
/// Last color calculated for the the chatmessage overlays
var/chat_color
/// A luminescence-shifted value of the last color calculated for chatmessage overlays
var/chat_color_darkened
/// The chat color var, without alpha.
var/chat_color_hover
/atom/New(loc, ...)
// Don't call ..() unless /datum/New() ever exists
@@ -476,7 +485,7 @@
// Use for objects performing visible actions
// message is output to anyone who can see, e.g. "The [src] does something!"
// blind_message (optional) is what blind people will hear e.g. "You hear something!"
/atom/proc/visible_message(var/message, var/blind_message, var/list/exclude_mobs, var/range = world.view)
/atom/proc/visible_message(var/message, var/blind_message, var/list/exclude_mobs, var/range = world.view, var/runemessage = "<span style='font-size: 1.5em'>👁</span>")
var/list/see = get_mobs_and_objs_in_view_fast(get_turf(src), range, remote_ghosts = FALSE)
@@ -492,6 +501,8 @@
var/mob/M = mob
if(M.see_invisible >= invisibility && MOB_CAN_SEE_PLANE(M, plane))
M.show_message(message, VISIBLE_MESSAGE, blind_message, AUDIBLE_MESSAGE)
if(runemessage != -1)
M.create_chat_message(src, "[runemessage]", FALSE, list("emote"), audible = FALSE)
else if(blind_message)
M.show_message(blind_message, AUDIBLE_MESSAGE)
@@ -500,7 +511,7 @@
// message is the message output to anyone who can hear.
// deaf_message (optional) is what deaf people will see.
// hearing_distance (optional) is the range, how many tiles away the message can be heard.
/atom/proc/audible_message(var/message, var/deaf_message, var/hearing_distance, var/radio_message)
/atom/proc/audible_message(var/message, var/deaf_message, var/hearing_distance, var/radio_message, var/runemessage)
var/range = hearing_distance || world.view
var/list/hear = get_mobs_and_objs_in_view_fast(get_turf(src),range,remote_ghosts = FALSE)
@@ -521,6 +532,8 @@
var/mob/M = mob
var/msg = message
M.show_message(msg, AUDIBLE_MESSAGE, deaf_message, VISIBLE_MESSAGE)
if(runemessage != -1)
M.create_chat_message(src, "[runemessage || message]", FALSE, list("emote"))
/atom/movable/proc/dropInto(var/atom/destination)
while(istype(destination))

View File

@@ -1,12 +1,12 @@
// Returns the lowest turf available on a given Z-level, defaults to asteroid for Polaris.
proc/get_base_turf(var/z)
/proc/get_base_turf(var/z)
if(!using_map.base_turf_by_z["[z]"])
using_map.base_turf_by_z["[z]"] = /turf/space
return using_map.base_turf_by_z["[z]"]
//An area can override the z-level base turf, so our solar array areas etc. can be space-based.
proc/get_base_turf_by_area(var/turf/T)
/proc/get_base_turf_by_area(var/turf/T)
var/area/A = T.loc
if(A.base_turf)
return A.base_turf

View File

@@ -58,10 +58,6 @@ var/global/list/datum/dna/gene/dna_genes[0]
// Used for genes that check for value rather than a binary on/off.
#define GENE_ALWAYS_ACTIVATE 1
// Skip checking if it's already active.
// Used for genes that check for value rather than a binary on/off.
#define GENE_ALWAYS_ACTIVATE 1
/datum/dna
// READ-ONLY, GETS OVERWRITTEN
// DO NOT FUCK WITH THESE OR BYOND WILL EAT YOUR FACE

View File

@@ -57,7 +57,7 @@
activation_message="Your mind says 'Hello'."
mutation=mHallucination
New()
/datum/dna/gene/disability/hallucinate/New()
block=HALLUCINATIONBLOCK
/datum/dna/gene/disability/epilepsy
@@ -65,7 +65,7 @@
activation_message="You get a headache."
disability=EPILEPSY
New()
/datum/dna/gene/disability/epilepsy/New()
block=HEADACHEBLOCK
/datum/dna/gene/disability/cough
@@ -73,7 +73,7 @@
activation_message="You start coughing."
disability=COUGHING
New()
/datum/dna/gene/disability/cough/New()
block=COUGHBLOCK
/datum/dna/gene/disability/clumsy
@@ -81,7 +81,7 @@
activation_message="You feel lightheaded."
mutation=CLUMSY
New()
/datum/dna/gene/disability/clumsy/New()
block=CLUMSYBLOCK
/datum/dna/gene/disability/tourettes
@@ -89,7 +89,7 @@
activation_message="You twitch."
disability=TOURETTES
New()
/datum/dna/gene/disability/tourettes/New()
block=TWITCHBLOCK
/datum/dna/gene/disability/nervousness
@@ -97,7 +97,7 @@
activation_message="You feel nervous."
disability=NERVOUS
New()
/datum/dna/gene/disability/nervousness/New()
block=NERVOUSBLOCK
/datum/dna/gene/disability/blindness
@@ -105,7 +105,7 @@
activation_message="You can't seem to see anything."
sdisability=BLIND
New()
/datum/dna/gene/disability/blindness/New()
block=BLINDBLOCK
/datum/dna/gene/disability/deaf
@@ -113,10 +113,10 @@
activation_message="It's kinda quiet."
sdisability=DEAF
New()
/datum/dna/gene/disability/deaf/New()
block=DEAFBLOCK
activate(var/mob/M, var/connected, var/flags)
/datum/dna/gene/disability/deaf/activate(var/mob/M, var/connected, var/flags)
..(M,connected,flags)
M.ear_deaf = 1
@@ -125,5 +125,5 @@
activation_message="Your eyes feel weird..."
disability=NEARSIGHTED
New()
/datum/dna/gene/disability/nearsighted/New()
block=GLASSESBLOCK

View File

@@ -7,7 +7,7 @@
activation_messages=list("You feel no need to breathe.")
mutation=mNobreath
New()
/datum/dna/gene/basic/nobreath/New()
block=NOBREATHBLOCK
/datum/dna/gene/basic/remoteview
@@ -15,10 +15,10 @@
activation_messages=list("Your mind expands.")
mutation=mRemote
New()
/datum/dna/gene/basic/remoteview/New()
block=REMOTEVIEWBLOCK
activate(var/mob/M, var/connected, var/flags)
/datum/dna/gene/basic/remoteview/activate(var/mob/M, var/connected, var/flags)
..(M,connected,flags)
M.verbs += /mob/living/carbon/human/proc/remoteobserve
@@ -27,7 +27,7 @@
activation_messages=list("You feel better.")
mutation=mRegen
New()
/datum/dna/gene/basic/regenerate/New()
block=REGENERATEBLOCK
/datum/dna/gene/basic/increaserun
@@ -35,7 +35,7 @@
activation_messages=list("Your leg muscles pulsate.")
mutation=mRun
New()
/datum/dna/gene/basic/increaserun/New()
block=INCREASERUNBLOCK
/datum/dna/gene/basic/remotetalk
@@ -43,10 +43,10 @@
activation_messages=list("You expand your mind outwards.")
mutation=mRemotetalk
New()
/datum/dna/gene/basic/remotetalk/New()
block=REMOTETALKBLOCK
activate(var/mob/M, var/connected, var/flags)
/datum/dna/gene/basic/remotetalk/activate(var/mob/M, var/connected, var/flags)
..(M,connected,flags)
M.verbs += /mob/living/carbon/human/proc/remotesay
@@ -55,56 +55,29 @@
activation_messages=list("Your skin feels strange.")
mutation=mMorph
New()
/datum/dna/gene/basic/morph/New()
block=MORPHBLOCK
activate(var/mob/M)
/datum/dna/gene/basic/morph/activate(var/mob/M)
..(M)
M.verbs += /mob/living/carbon/human/proc/morph
/* Not used on bay
/datum/dna/gene/basic/heat_resist
name="Heat Resistance"
activation_messages=list("Your skin is icy to the touch.")
mutation=mHeatres
New()
block=COLDBLOCK
can_activate(var/mob/M,var/flags)
if(flags & MUTCHK_FORCED)
return !(/datum/dna/gene/basic/cold_resist in M.active_genes)
// Probability check
var/_prob = 15
if(COLD_RESISTANCE in M.mutations)
_prob=5
if(probinj(_prob,(flags&MUTCHK_FORCED)))
return 1
OnDrawUnderlays(var/mob/M,var/g,var/fat)
return "cold[fat]_s"
*/
/datum/dna/gene/basic/cold_resist
name="Cold Resistance"
activation_messages=list("Your body is filled with warmth.")
mutation=COLD_RESISTANCE
New()
/datum/dna/gene/basic/cold_resist/New()
block=FIREBLOCK
can_activate(var/mob/M,var/flags)
/datum/dna/gene/basic/cold_resist/can_activate(var/mob/M,var/flags)
if(flags & MUTCHK_FORCED)
return 1
// return !(/datum/dna/gene/basic/heat_resist in M.active_genes)
// Probability check
var/_prob=30
//if(mHeatres in M.mutations)
// _prob=5
if(probinj(_prob,(flags&MUTCHK_FORCED)))
return 1
OnDrawUnderlays(var/mob/M,var/g,var/fat)
/datum/dna/gene/basic/cold_resist/OnDrawUnderlays(var/mob/M,var/g,var/fat)
return "fire[fat]_s"
/datum/dna/gene/basic/noprints
@@ -112,7 +85,7 @@
activation_messages=list("Your fingers feel numb.")
mutation=mFingerprints
New()
/datum/dna/gene/basic/noprints/New()
block=NOPRINTSBLOCK
/datum/dna/gene/basic/noshock
@@ -120,7 +93,7 @@
activation_messages=list("Your skin feels strange.")
mutation=mShock
New()
/datum/dna/gene/basic/noshock/New()
block=SHOCKIMMUNITYBLOCK
/datum/dna/gene/basic/midget
@@ -128,20 +101,20 @@
activation_messages=list("Your skin feels rubbery.")
mutation=mSmallsize
New()
/datum/dna/gene/basic/midget/New()
block=SMALLSIZEBLOCK
can_activate(var/mob/M,var/flags)
/datum/dna/gene/basic/midget/can_activate(var/mob/M,var/flags)
// Can't be big and small.
if(HULK in M.mutations)
return 0
return ..(M,flags)
activate(var/mob/M, var/connected, var/flags)
/datum/dna/gene/basic/midget/activate(var/mob/M, var/connected, var/flags)
..(M,connected,flags)
M.pass_flags |= 1
deactivate(var/mob/M, var/connected, var/flags)
/datum/dna/gene/basic/midget/deactivate(var/mob/M, var/connected, var/flags)
..(M,connected,flags)
M.pass_flags &= ~1 //This may cause issues down the track, but offhand I can't think of any other way for humans to get passtable short of varediting so it should be fine. ~Z
@@ -150,22 +123,22 @@
activation_messages=list("Your muscles hurt.")
mutation=HULK
New()
/datum/dna/gene/basic/hulk/New()
block=HULKBLOCK
can_activate(var/mob/M,var/flags)
/datum/dna/gene/basic/hulk/can_activate(var/mob/M,var/flags)
// Can't be big and small.
if(mSmallsize in M.mutations)
return 0
return ..(M,flags)
OnDrawUnderlays(var/mob/M,var/g,var/fat)
/datum/dna/gene/basic/hulk/OnDrawUnderlays(var/mob/M,var/g,var/fat)
if(fat)
return "hulk_[fat]_s"
else
return "hulk_[g]_s"
OnMobLife(var/mob/living/carbon/human/M)
/datum/dna/gene/basic/hulk/OnMobLife(var/mob/living/carbon/human/M)
if(!istype(M)) return
if(M.health <= 25)
M.mutations.Remove(HULK)
@@ -179,7 +152,7 @@
activation_messages=list("The walls suddenly disappear.")
mutation=XRAY
New()
/datum/dna/gene/basic/xray/New()
block=XRAYBLOCK
/datum/dna/gene/basic/tk
@@ -188,7 +161,7 @@
mutation=TK
activation_prob=15
New()
/datum/dna/gene/basic/tk/New()
block=TELEBLOCK
OnDrawUnderlays(var/mob/M,var/g,var/fat)
/datum/dna/gene/basic/tk/OnDrawUnderlays(var/mob/M,var/g,var/fat)
return "telekinesishead[fat]_s"

View File

@@ -160,7 +160,7 @@ var/global/list/possible_changeling_IDs = list("Alpha","Beta","Gamma","Delta","E
//STINGS// //They get a pretty header because there's just so fucking many of them ;_;
//////////
turf/proc/AdjacentTurfsRangedSting()
/turf/proc/AdjacentTurfsRangedSting()
//Yes this is snowflakey, but I couldn't get it to work any other way.. -Luke
var/list/allowed = list(
/obj/structure/table,

View File

@@ -1,29 +1,6 @@
//cast_method flags, needs to be up to date with Technomancer's. They were, for some reason, not working outside it.
#define CAST_USE 1 // Clicking the spell in your hand.
#define CAST_MELEE 2 // Clicking an atom in melee range.
#define CAST_RANGED 4 // Clicking an atom beyond melee range.
#define CAST_THROW 8 // Throwing the spell and hitting an atom.
#define CAST_COMBINE 16 // Clicking another spell with this spell.
#define CAST_INNATE 32 // Activates upon verb usage, used for mobs without hands.
//Aspects
#define ASPECT_FIRE "fire" //Damage over time and raising body-temp. Firesuits protect from this.
#define ASPECT_FROST "frost" //Slows down the affected, also involves imbedding with icicles. Winter coats protect from this.
#define ASPECT_SHOCK "shock" //Energy-expensive, usually stuns. Insulated armor protects from this.
#define ASPECT_AIR "air" //Mostly involves manipulation of atmos, useless in a vacuum. Magboots protect from this.
#define ASPECT_FORCE "force" //Manipulates gravity to push things away or towards a location.
#define ASPECT_TELE "tele" //Teleportation of self, other objects, or other people.
#define ASPECT_DARK "dark" //Makes all those photons vanish using magic-- WITH SCIENCE. Used for sneaky stuff.
#define ASPECT_LIGHT "light" //The opposite of dark, usually blinds, makes holo-illusions, or makes laser lightshows.
#define ASPECT_BIOMED "biomed" //Mainly concerned with healing and restoration.
#define ASPECT_EMP "emp" //Unused now.
#define ASPECT_UNSTABLE "unstable" //Heavily RNG-based, causes instability to the victim.
#define ASPECT_CHROMATIC "chromatic" //Used to combine with other spells.
#define ASPECT_UNHOLY "unholy" //Involves the dead, blood, and most things against divine beings.
//////////////////////////////Construct Spells/////////////////////////
proc/findNullRod(var/atom/target)
/proc/findNullRod(var/atom/target)
if(istype(target,/obj/item/weapon/nullrod))
return 1
else if(target.contents)

View File

@@ -65,8 +65,8 @@ var/global/list/rnwords = list("ire","ego","nahlizet","certum","veri","jatkaa","
// self other technology - Communication rune //was other hear blood
// join hide technology - stun rune. Rune color: bright pink.
New()
..()
/obj/effect/rune/Initialize()
. = ..()
blood_image = image(loc = src)
blood_image.override = 1
for(var/mob/living/silicon/ai/AI in player_list)
@@ -74,7 +74,7 @@ var/global/list/rnwords = list("ire","ego","nahlizet","certum","veri","jatkaa","
AI.client.images += blood_image
rune_list.Add(src)
Destroy()
/obj/effect/rune/Destroy()
for(var/mob/living/silicon/ai/AI in player_list)
if(AI.client)
AI.client.images -= blood_image
@@ -83,13 +83,13 @@ var/global/list/rnwords = list("ire","ego","nahlizet","certum","veri","jatkaa","
rune_list.Remove(src)
..()
examine(mob/user)
/obj/effect/rune/examine(mob/user)
. = ..()
if(iscultist(user))
. += "This spell circle reads: <i>[word1] [word2] [word3]</i>."
attackby(I as obj, user as mob)
/obj/effect/rune/attackby(I as obj, user as mob)
if(istype(I, /obj/item/weapon/book/tome) && iscultist(user))
to_chat(user, "You retrace your steps, carefully undoing the lines of the rune.")
qdel(src)
@@ -101,7 +101,7 @@ var/global/list/rnwords = list("ire","ego","nahlizet","certum","veri","jatkaa","
return
attack_hand(mob/living/user as mob)
/obj/effect/rune/attack_hand(mob/living/user as mob)
if(!iscultist(user))
to_chat(user, "You can't mouth the arcane scratchings without fumbling over them.")
return
@@ -164,8 +164,7 @@ var/global/list/rnwords = list("ire","ego","nahlizet","certum","veri","jatkaa","
return fizzle()
proc
fizzle()
/obj/effect/rune/proc/fizzle()
if(istype(src,/obj/effect/rune))
usr.say(pick("Hakkrutju gopoenjim.", "Nherasai pivroiashan.", "Firjji prhiv mazenhor.", "Tanah eh wakantahe.", "Obliyae na oraie.", "Miyf hon vnor'c.", "Wakabai hij fen juswix."))
else
@@ -174,7 +173,7 @@ var/global/list/rnwords = list("ire","ego","nahlizet","certum","veri","jatkaa","
V.show_message("<span class='warning'>The markings pulse with a small burst of light, then fall dark.</span>", 3, "<span class='warning'>You hear a faint fizzle.</span>", 2)
return
check_icon()
/obj/effect/rune/proc/check_icon()
icon = get_uristrune_cult(word1, word2, word3)
/obj/item/weapon/book/tome
@@ -289,14 +288,14 @@ var/global/list/rnwords = list("ire","ego","nahlizet","certum","veri","jatkaa","
</html>
"}
New()
..()
/obj/item/weapon/book/tome/Initialize()
. = ..()
if(!cultwords["travel"])
runerandom()
for(var/V in cultwords)
words[cultwords[V]] = V
attack(mob/living/M as mob, mob/living/user as mob)
/obj/item/weapon/book/tome/attack(mob/living/M as mob, mob/living/user as mob)
add_attack_logs(user,M,"Hit with [name]")
if(istype(M,/mob/observer/dead))
@@ -315,7 +314,7 @@ var/global/list/rnwords = list("ire","ego","nahlizet","certum","veri","jatkaa","
to_chat(M, "<span class='danger'>You feel searing heat inside!</span>")
attack_self(mob/living/user as mob)
/obj/item/weapon/book/tome/attack_self(mob/living/user as mob)
usr = user
if(!usr.canmove || usr.stat || usr.restrained())
return
@@ -426,7 +425,7 @@ var/global/list/rnwords = list("ire","ego","nahlizet","certum","veri","jatkaa","
to_chat(user, "The book seems full of illegible scribbles. Is this a joke?")
return
examine(mob/user)
/obj/item/weapon/book/tome/examine(mob/user)
. = ..()
if(!iscultist(user))
. += "An old, dusty tome with frayed edges and a sinister looking cover."
@@ -439,7 +438,7 @@ var/global/list/rnwords = list("ire","ego","nahlizet","certum","veri","jatkaa","
/obj/item/weapon/book/tome/imbued //admin tome, spawns working runes without waiting
w_class = ITEMSIZE_SMALL
var/cultistsonly = 1
attack_self(mob/user as mob)
/obj/item/weapon/book/tome/imbued/attack_self(mob/user as mob)
if(src.cultistsonly && !iscultist(usr))
return
if(!cultwords["travel"])

View File

@@ -3,8 +3,6 @@ var/list/sacrificed = list()
/obj/effect/rune/cultify()
return
/obj/effect/rune
/*
* Use as a general guideline for this and related files:
* * <span class='warning'>...</span> - when something non-trivial or an error happens, so something similar to "Sparks come out of the machine!"
@@ -14,13 +12,11 @@ var/list/sacrificed = list()
/////////////////////////////////////////FIRST RUNE
proc
teleport(var/key)
/obj/effect/rune/proc/teleport(var/key)
var/mob/living/user = usr
var/allrunesloc[]
allrunesloc = new/list()
var/index = 0
// var/tempnum = 0
for(var/obj/effect/rune/R in rune_list)
if(R == src)
continue
@@ -50,11 +46,7 @@ var/list/sacrificed = list()
return
itemport(var/key)
// var/allrunesloc[]
// allrunesloc = new/list()
// var/index = 0
// var/tempnum = 0
/obj/effect/rune/proc/itemport(var/key)
var/culcount = 0
var/runecount = 0
var/obj/effect/rune/IP = null
@@ -90,7 +82,7 @@ var/list/sacrificed = list()
/////////////////////////////////////////SECOND RUNE
tomesummon()
/obj/effect/rune/proc/tomesummon()
if(istype(src,/obj/effect/rune))
usr.say("N[pick("'","`")]ath reth sh'yro eth d'raggathnor!")
else
@@ -109,7 +101,7 @@ var/list/sacrificed = list()
/////////////////////////////////////////THIRD RUNE
convert()
/obj/effect/rune/proc/convert()
var/mob/attacker = usr
var/mob/living/carbon/target = null
for(var/mob/living/carbon/M in src.loc)
@@ -192,7 +184,7 @@ var/list/sacrificed = list()
/////////////////////////////////////////FOURTH RUNE
tearreality()
/obj/effect/rune/proc/tearreality()
if(!cult.allow_narsie)
return fizzle()
@@ -217,14 +209,13 @@ var/list/sacrificed = list()
emergency_shuttle.launch_time = 0 // Cannot recall
log_and_message_admins_many(cultists, "summoned the end of days.")
// new /obj/singularity/narsie/large(src.loc)
return
else
return fizzle()
/////////////////////////////////////////FIFTH RUNE
emp(var/U,var/range_red) //range_red - var which determines by which number to reduce the default emp range, U is the source loc, needed because of talisman emps which are held in hand at the moment of using and that apparently messes things up -- Urist
/obj/effect/rune/proc/emp(var/U,var/range_red) //range_red - var which determines by which number to reduce the default emp range, U is the source loc, needed because of talisman emps which are held in hand at the moment of using and that apparently messes things up -- Urist
log_and_message_admins("activated an EMP rune.")
if(istype(src,/obj/effect/rune))
usr.say("Ta'gh fara[pick("'","`")]qha fel d'amar det!")
@@ -241,7 +232,7 @@ var/list/sacrificed = list()
/////////////////////////////////////////SIXTH RUNE
drain()
/obj/effect/rune/proc/drain()
var/drain = 0
for(var/obj/effect/rune/R in rune_list)
if(R.word1==cultwords["travel"] && R.word2==cultwords["blood"] && R.word3==cultwords["self"])
@@ -301,7 +292,7 @@ var/list/sacrificed = list()
/////////////////////////////////////////SEVENTH RUNE
seer()
/obj/effect/rune/proc/seer()
if(usr.loc==src.loc)
if(usr.seer==1)
usr.say("Rash'tla sektath mal[pick("'","`")]zua. Zasan therium viortia.")
@@ -322,7 +313,7 @@ var/list/sacrificed = list()
/////////////////////////////////////////EIGHTH RUNE
raise()
/obj/effect/rune/proc/raise()
var/mob/living/carbon/human/corpse_to_raise
var/mob/living/carbon/human/body_to_sacrifice
@@ -390,11 +381,6 @@ var/list/sacrificed = list()
"<span class='danger'>You hear a thousand voices, all crying in pain.</span>")
body_to_sacrifice.gib()
// if(ticker.mode.name == "cult")
// ticker.mode:add_cultist(corpse_to_raise.mind)
// else
// ticker.mode.cult |= corpse_to_raise.mind
to_chat(corpse_to_raise, "<span class='cult'>Your blood pulses. Your head throbs. The world goes red. All at once you are aware of a horrible, horrible truth. The veil of reality has been ripped away and in the festering wound left behind something sinister takes root.</span>")
to_chat(corpse_to_raise, "<span class='cult'>Assist your new compatriots in their dark dealings. Their goal is yours, and yours is theirs. You serve the Dark One above all else. Bring It back.</span>")
@@ -406,7 +392,7 @@ var/list/sacrificed = list()
/////////////////////////////////////////NINETH RUNE
obscure(var/rad)
/obj/effect/rune/proc/obscure(var/rad)
var/S=0
for(var/obj/effect/rune/R in orange(rad,src))
if(R!=src)
@@ -434,7 +420,7 @@ var/list/sacrificed = list()
/////////////////////////////////////////TENTH RUNE
ajourney() //some bits copypastaed from admin tools - Urist
/obj/effect/rune/proc/ajourney() //some bits copypastaed from admin tools - Urist
if(usr.loc==src.loc)
var/mob/living/carbon/human/L = usr
var/datum/gender/TU = gender_datums[L.get_visible_gender()]
@@ -458,7 +444,7 @@ var/list/sacrificed = list()
/////////////////////////////////////////ELEVENTH RUNE
manifest()
/obj/effect/rune/proc/manifest()
var/obj/effect/rune/this_rune = src
src = null
if(usr.loc!=this_rune.loc)
@@ -521,7 +507,7 @@ var/list/sacrificed = list()
/////////////////////////////////////////TWELFTH RUNE
talisman()//only hide, emp, teleport, deafen, blind and tome runes can be imbued atm
/obj/effect/rune/proc/talisman()//only hide, emp, teleport, deafen, blind and tome runes can be imbued atm
var/obj/item/weapon/paper/newtalisman
var/unsuitable_newtalisman = 0
for(var/obj/item/weapon/paper/P in src.loc)
@@ -602,7 +588,7 @@ var/list/sacrificed = list()
/////////////////////////////////////////THIRTEENTH RUNE
mend()
/obj/effect/rune/proc/mend()
var/mob/living/user = usr
var/datum/gender/TU = gender_datums[usr.get_visible_gender()]
src = null
@@ -623,7 +609,7 @@ var/list/sacrificed = list()
/////////////////////////////////////////FOURTEETH RUNE
// returns 0 if the rune is not used. returns 1 if the rune is used.
communicate()
/obj/effect/rune/proc/communicate()
. = 1 // Default output is 1. If the rune is deleted it will return 1
var/input = input(usr, "Please choose a message to tell to the other acolytes.", "Voice of Blood", "")//sanitize() below, say() and whisper() have their own
if(!input)
@@ -650,7 +636,7 @@ var/list/sacrificed = list()
/////////////////////////////////////////FIFTEENTH RUNE
sacrifice()
/obj/effect/rune/proc/sacrifice()
var/list/mob/living/carbon/human/cultsinrange = list()
var/list/mob/living/carbon/human/victims = list()
for(var/mob/living/carbon/human/V in src.loc)//Checks for non-cultist humans to sacrifice
@@ -771,7 +757,7 @@ var/list/sacrificed = list()
/////////////////////////////////////////SIXTEENTH RUNE
revealrunes(var/obj/W as obj)
/obj/effect/rune/proc/revealrunes(var/obj/W as obj)
var/go=0
var/rad
var/S=0
@@ -815,7 +801,7 @@ var/list/sacrificed = list()
/////////////////////////////////////////SEVENTEENTH RUNE
wall()
/obj/effect/rune/proc/wall()
usr.say("Khari[pick("'","`")]d! Eske'te tannin!")
src.density = !src.density
var/mob/living/user = usr
@@ -828,7 +814,7 @@ var/list/sacrificed = list()
/////////////////////////////////////////EIGHTTEENTH RUNE
freedom()
/obj/effect/rune/proc/freedom()
var/mob/living/user = usr
var/list/mob/living/carbon/cultists = new
for(var/datum/mind/H in cult.current_antagonists)
@@ -875,7 +861,7 @@ var/list/sacrificed = list()
/////////////////////////////////////////NINETEENTH RUNE
cultsummon()
/obj/effect/rune/proc/cultsummon()
var/mob/living/user = usr
var/list/mob/living/carbon/cultists = new
for(var/datum/mind/H in cult.current_antagonists)
@@ -916,7 +902,7 @@ var/list/sacrificed = list()
/////////////////////////////////////////TWENTIETH RUNES
deafen()
/obj/effect/rune/proc/deafen()
if(istype(src,/obj/effect/rune))
var/list/affected = new()
for(var/mob/living/carbon/C in range(7,src))
@@ -958,7 +944,7 @@ var/list/sacrificed = list()
V.show_message("<span class='warning'>Dust flows from [usr]'s hands for a moment, and the world suddenly becomes quiet..</span>", 3)
return
blind()
/obj/effect/rune/proc/blind()
if(istype(src,/obj/effect/rune))
var/list/affected = new()
for(var/mob/living/carbon/C in viewers(src))
@@ -1002,7 +988,7 @@ var/list/sacrificed = list()
return
bloodboil() //cultists need at least one DANGEROUS rune. Even if they're all stealthy.
/obj/effect/rune/proc/bloodboil() //cultists need at least one DANGEROUS rune. Even if they're all stealthy.
/*
var/list/mob/living/carbon/cultists = new
for(var/datum/mind/H in ticker.mode.cult)
@@ -1043,7 +1029,7 @@ var/list/sacrificed = list()
// WIP rune, I'll wait for Rastaf0 to add limited blood.
burningblood()
/obj/effect/rune/proc/burningblood()
var/culcount = 0
for(var/mob/living/carbon/C in orange(1,src))
if(iscultist(C) && !C.stat)
@@ -1071,7 +1057,7 @@ var/list/sacrificed = list()
////////// Rune 24 (counting burningblood, which kinda doesnt work yet.)
runestun(var/mob/living/T as mob)
/obj/effect/rune/proc/runestun(var/mob/living/T as mob)
if(istype(src,/obj/effect/rune)) ///When invoked as rune, flash and stun everyone around.
usr.say("Fuu ma[pick("'","`")]jin!")
for(var/mob/living/L in viewers(src))
@@ -1116,7 +1102,7 @@ var/list/sacrificed = list()
/////////////////////////////////////////TWENTY-FIFTH RUNE
armor()
/obj/effect/rune/proc/armor()
var/mob/living/carbon/human/user = usr
if(istype(src,/obj/effect/rune))
usr.say("N'ath reth sh'yro eth d[pick("'","`")]raggathnor!")

View File

@@ -4,7 +4,7 @@
var/uses = 0
info = "<center><img src='talisman.png'></center><br/><br/>"
attack_self(mob/living/user as mob)
/obj/item/weapon/paper/talisman/attack_self(mob/living/user as mob)
if(iscultist(user))
var/delete = 1
// who the hell thought this was a good idea :(
@@ -43,7 +43,7 @@
return
attack(mob/living/carbon/T as mob, mob/living/user as mob)
/obj/item/weapon/paper/talisman/attack(mob/living/carbon/T as mob, mob/living/user as mob)
if(iscultist(user))
if(imbue == "runestun")
user.take_organ_damage(5, 0)
@@ -55,7 +55,7 @@
..()
proc/supply(var/key)
/obj/item/weapon/paper/talisman/proc/supply(var/key)
if (!src.uses)
qdel(src)
return
@@ -76,7 +76,7 @@
return
Topic(href, href_list)
/obj/item/weapon/paper/talisman/Topic(href, href_list)
if(!src) return
if (usr.stat || usr.restrained() || !in_range(src, usr)) return

View File

@@ -16,7 +16,7 @@ In my current plan for it, 'solid' will be defined as anything with density == 1
density = 1
anchored = 1
Bump(atom/clong)
/obj/effect/immovablerod/Bump(atom/clong)
if(istype(clong, /turf/simulated/shuttle)) //Skip shuttles without actually deleting the rod
return
@@ -41,7 +41,7 @@ In my current plan for it, 'solid' will be defined as anything with density == 1
if(clong && prob(25))
src.loc = clong.loc
Destroy()
/obj/effect/immovablerod/Destroy()
walk(src, 0) // Because we might have called walk_towards, we must stop the walk loop or BYOND keeps an internal reference to us forever.
return ..()

View File

@@ -469,7 +469,7 @@ var/global/list/additional_antag_types = list()
//////////////////////////
//Reports player logouts//
//////////////////////////
proc/display_roundstart_logout_report()
/proc/display_roundstart_logout_report()
var/msg = "<span class='notice'><b>Roundstart logout report</b>\n\n"
for(var/mob/living/L in mob_list)
@@ -521,7 +521,7 @@ proc/display_roundstart_logout_report()
if(M.client && M.client.holder)
to_chat(M,msg)
proc/get_nt_opposed()
/proc/get_nt_opposed()
var/list/dudes = list()
for(var/mob/living/carbon/human/man in player_list)
if(man.client)

View File

@@ -1453,7 +1453,7 @@ datum
return 0
return 1
datum/objective/silence
/datum/objective/silence
explanation_text = "Do not allow anyone to escape the station. Only allow the shuttle to be called when everyone is dead and your story is the only one left."
check_completion()

View File

@@ -1,27 +1,27 @@
//This file was auto-corrected by findeclaration.exe on 25.5.2012 20:42:31
var/global/list/all_objectives = list()
datum/objective
/datum/objective
var/datum/mind/owner = null //Who owns the objective.
var/explanation_text = "Nothing" //What that person is supposed to do.
var/datum/mind/target = null //If they are focused on a particular person.
var/target_amount = 0 //If they are focused on a particular number. Steal objectives have their own counter.
var/completed = 0 //currently only used for custom objectives.
New(var/text)
/datum/objective/New(var/text)
all_objectives |= src
if(text)
explanation_text = text
..()
Destroy()
/datum/objective/Destroy()
all_objectives -= src
..()
proc/check_completion()
/datum/objective/proc/check_completion()
return completed
proc/find_target()
/datum/objective/proc/find_target()
var/list/possible_targets = list()
for(var/datum/mind/possible_target in ticker.minds)
if(possible_target != owner && ishuman(possible_target.current) && (possible_target.current.stat != 2))
@@ -30,7 +30,7 @@ datum/objective
target = pick(possible_targets)
proc/find_target_by_role(role, role_type=0)//Option sets either to check assigned role or special role. Default to assigned.
/datum/objective/proc/find_target_by_role(role, role_type=0)//Option sets either to check assigned role or special role. Default to assigned.
for(var/datum/mind/possible_target in ticker.minds)
if((possible_target != owner) && ishuman(possible_target.current) && ((role_type ? possible_target.special_role : possible_target.assigned_role) == role) )
target = possible_target
@@ -38,8 +38,7 @@ datum/objective
datum/objective/assassinate
find_target()
/datum/objective/assassinate/find_target()
..()
if(target && target.current)
explanation_text = "Assassinate [target.current.real_name], the [target.assigned_role]."
@@ -48,7 +47,7 @@ datum/objective/assassinate
return target
find_target_by_role(role, role_type=0)
/datum/objective/assassinate/find_target_by_role(role, role_type=0)
..(role, role_type)
if(target && target.current)
explanation_text = "Assassinate [target.current.real_name], the [!role_type ? target.assigned_role : target.special_role]."
@@ -57,7 +56,7 @@ datum/objective/assassinate
return target
check_completion()
/datum/objective/assassinate/check_completion()
if(target && target.current)
if(target.current.stat == DEAD || issilicon(target.current) || isbrain(target.current) || target.current.z > 6 || !target.current.ckey) //Borgs/brains/AIs count as dead for traitor objectives. --NeoFite
return 1
@@ -65,8 +64,7 @@ datum/objective/assassinate
return 1
datum/objective/anti_revolution/execute
find_target()
/datum/objective/anti_revolution/execute/find_target()
..()
if(target && target.current)
var/datum/gender/T = gender_datums[target.current.get_visible_gender()]
@@ -76,7 +74,7 @@ datum/objective/anti_revolution/execute
return target
find_target_by_role(role, role_type=0)
/datum/objective/anti_revolution/execute/find_target_by_role(role, role_type=0)
..(role, role_type)
if(target && target.current)
var/datum/gender/T = gender_datums[target.current.get_visible_gender()]
@@ -85,17 +83,17 @@ datum/objective/anti_revolution/execute
explanation_text = "Free Objective"
return target
check_completion()
/datum/objective/anti_revolution/execute/check_completion()
if(target && target.current)
if(target.current.stat == DEAD || !ishuman(target.current))
return 1
return 0
return 1
datum/objective/anti_revolution/brig
/datum/objective/anti_revolution/brig
var/already_completed = 0
find_target()
/datum/objective/anti_revolution/brig/find_target()
..()
if(target && target.current)
explanation_text = "Brig [target.current.real_name], the [target.assigned_role] for 20 minutes to set an example."
@@ -104,7 +102,7 @@ datum/objective/anti_revolution/brig
return target
find_target_by_role(role, role_type=0)
/datum/objective/anti_revolution/brig/find_target_by_role(role, role_type=0)
..(role, role_type)
if(target && target.current)
explanation_text = "Brig [target.current.real_name], the [!role_type ? target.assigned_role : target.special_role] for 20 minutes to set an example."
@@ -112,7 +110,7 @@ datum/objective/anti_revolution/brig
explanation_text = "Free Objective"
return target
check_completion()
/datum/objective/anti_revolution/brig/check_completion()
if(already_completed)
return 1
@@ -125,8 +123,7 @@ datum/objective/anti_revolution/brig
return 0
return 0
datum/objective/anti_revolution/demote
find_target()
/datum/objective/anti_revolution/demote/find_target()
..()
if(target && target.current)
var/datum/gender/T = gender_datums[target.current.get_visible_gender()]
@@ -135,7 +132,7 @@ datum/objective/anti_revolution/demote
explanation_text = "Free Objective"
return target
find_target_by_role(role, role_type=0)
/datum/objective/anti_revolution/demote/find_target_by_role(role, role_type=0)
..(role, role_type)
if(target && target.current)
var/datum/gender/T = gender_datums[target.current.get_visible_gender()]
@@ -144,7 +141,7 @@ datum/objective/anti_revolution/demote
explanation_text = "Free Objective"
return target
check_completion()
/datum/objective/anti_revolution/demote/check_completion()
if(target && target.current && istype(target,/mob/living/carbon/human))
var/obj/item/weapon/card/id/I = target.current:wear_id
if(istype(I, /obj/item/device/pda))
@@ -159,8 +156,8 @@ datum/objective/anti_revolution/demote
return 0
return 1
datum/objective/debrain//I want braaaainssss
find_target()
//I want braaaainssss
/datum/objective/debrain/find_target()
..()
if(target && target.current)
explanation_text = "Steal the brain of [target.current.real_name]."
@@ -169,7 +166,7 @@ datum/objective/debrain//I want braaaainssss
return target
find_target_by_role(role, role_type=0)
/datum/objective/debrain/find_target_by_role(role, role_type=0)
..(role, role_type)
if(target && target.current)
explanation_text = "Steal the brain of [target.current.real_name] the [!role_type ? target.assigned_role : target.special_role]."
@@ -177,7 +174,7 @@ datum/objective/debrain//I want braaaainssss
explanation_text = "Free Objective"
return target
check_completion()
/datum/objective/debrain/check_completion()
if(!target)//If it's a free objective.
return 1
if( !owner.current || owner.current.stat==DEAD )//If you're otherwise dead.
@@ -192,8 +189,8 @@ datum/objective/debrain//I want braaaainssss
return 0
datum/objective/protect//The opposite of killing a dude.
find_target()
//The opposite of killing a dude.
/datum/objective/protect/find_target()
..()
if(target && target.current)
explanation_text = "Protect [target.current.real_name], the [target.assigned_role]."
@@ -202,7 +199,7 @@ datum/objective/protect//The opposite of killing a dude.
return target
find_target_by_role(role, role_type=0)
/datum/objective/protect/find_target_by_role(role, role_type=0)
..(role, role_type)
if(target && target.current)
explanation_text = "Protect [target.current.real_name], the [!role_type ? target.assigned_role : target.special_role]."
@@ -210,7 +207,7 @@ datum/objective/protect//The opposite of killing a dude.
explanation_text = "Free Objective"
return target
check_completion()
/datum/objective/protect/check_completion()
if(!target) //If it's a free objective.
return 1
if(target.current)
@@ -220,10 +217,10 @@ datum/objective/protect//The opposite of killing a dude.
return 0
datum/objective/hijack
/datum/objective/hijack
explanation_text = "Hijack the emergency shuttle by escaping alone."
check_completion()
/datum/objective/hijack/check_completion()
if(!owner.current || owner.current.stat)
return 0
if(!emergency_shuttle.returned())
@@ -241,11 +238,11 @@ datum/objective/hijack
return 1
datum/objective/block
/datum/objective/block
explanation_text = "Do not allow any organic lifeforms to escape on the shuttle alive."
check_completion()
/datum/objective/block/check_completion()
if(!istype(owner.current, /mob/living/silicon))
return 0
if(!emergency_shuttle.returned())
@@ -262,10 +259,10 @@ datum/objective/block
return 0
return 1
datum/objective/silence
/datum/objective/silence
explanation_text = "Do not allow anyone to escape the station. Only allow the shuttle to be called when everyone is dead and your story is the only one left."
check_completion()
/datum/objective/silence/check_completion()
if(!emergency_shuttle.returned())
return 0
@@ -282,11 +279,11 @@ datum/objective/silence
return 1
datum/objective/escape
/datum/objective/escape
explanation_text = "Escape on the shuttle or an escape pod alive and free."
check_completion()
/datum/objective/escape/check_completion()
if(issilicon(owner.current))
return 0
if(isbrain(owner.current))
@@ -322,10 +319,10 @@ datum/objective/escape
datum/objective/survive
/datum/objective/survive
explanation_text = "Stay alive until the end."
check_completion()
/datum/objective/survive/check_completion()
if(!owner.current || owner.current.stat == DEAD || isbrain(owner.current))
return 0 //Brains no longer win survive objectives. --NEO
if(issilicon(owner.current) && owner.current != owner.original)
@@ -333,10 +330,10 @@ datum/objective/survive
return 1
// Similar to the anti-rev objective, but for traitors
datum/objective/brig
/datum/objective/brig
var/already_completed = 0
find_target()
/datum/objective/brig/find_target()
..()
if(target && target.current)
explanation_text = "Have [target.current.real_name], the [target.assigned_role] brigged for 10 minutes."
@@ -345,7 +342,7 @@ datum/objective/brig
return target
find_target_by_role(role, role_type=0)
/datum/objective/brig/find_target_by_role(role, role_type=0)
..(role, role_type)
if(target && target.current)
explanation_text = "Have [target.current.real_name], the [!role_type ? target.assigned_role : target.special_role] brigged for 10 minutes."
@@ -353,7 +350,7 @@ datum/objective/brig
explanation_text = "Free Objective"
return target
check_completion()
/datum/objective/brig/check_completion()
if(already_completed)
return 1
@@ -368,10 +365,10 @@ datum/objective/brig
return 0
// Harm a crew member, making an example of them
datum/objective/harm
/datum/objective/harm
var/already_completed = 0
find_target()
/datum/objective/harm/find_target()
..()
if(target && target.current)
explanation_text = "Make an example of [target.current.real_name], the [target.assigned_role]. Break one of their bones, detach one of their limbs or disfigure their face. Make sure they're alive when you do it."
@@ -380,7 +377,7 @@ datum/objective/harm
return target
find_target_by_role(role, role_type=0)
/datum/objective/harm/find_target_by_role(role, role_type=0)
..(role, role_type)
if(target && target.current)
explanation_text = "Make an example of [target.current.real_name], the [!role_type ? target.assigned_role : target.special_role]. Break one of their bones, detach one of their limbs or disfigure their face. Make sure they're alive when you do it."
@@ -388,7 +385,7 @@ datum/objective/harm
explanation_text = "Free Objective"
return target
check_completion()
/datum/objective/harm/check_completion()
if(already_completed)
return 1
@@ -417,12 +414,12 @@ datum/objective/harm
return 0
datum/objective/nuclear
/datum/objective/nuclear
explanation_text = "Destroy the station with a nuclear device."
datum/objective/steal
/datum/objective/steal
var/obj/item/steal_target
var/target_name
@@ -461,7 +458,7 @@ datum/objective/steal
)
proc/set_target(item_name)
/datum/objective/steal/proc/set_target(item_name)
target_name = item_name
steal_target = possible_items[target_name]
if (!steal_target )
@@ -470,11 +467,11 @@ datum/objective/steal
return steal_target
find_target()
/datum/objective/steal/find_target()
return set_target(pick(possible_items))
proc/select_target()
/datum/objective/steal/proc/select_target()
var/list/possible_items_all = possible_items+possible_items_special+"custom"
var/new_target = input("Select target:", "Objective target", steal_target) as null|anything in possible_items_all
if (!new_target) return
@@ -493,7 +490,7 @@ datum/objective/steal
set_target(new_target)
return steal_target
check_completion()
/datum/objective/steal/check_completion()
if(!steal_target || !owner.current) return 0
if(!isliving(owner.current)) return 0
var/list/all_items = owner.current.get_contents()
@@ -547,14 +544,13 @@ datum/objective/steal
datum/objective/download
proc/gen_amount_goal()
/datum/objective/download/proc/gen_amount_goal()
target_amount = rand(10,20)
explanation_text = "Download [target_amount] research levels."
return target_amount
check_completion()
/datum/objective/download/check_completion()
if(!ishuman(owner.current))
return 0
if(!owner.current || owner.current.stat == 2)
@@ -579,14 +575,13 @@ datum/objective/download
return (current_amount<target_amount) ? 0 : 1
datum/objective/capture
proc/gen_amount_goal()
/datum/objective/capture/proc/gen_amount_goal()
target_amount = rand(5,10)
explanation_text = "Accumulate [target_amount] capture points."
return target_amount
check_completion()//Basically runs through all the mobs in the area to determine how much they are worth.
/datum/objective/capture/check_completion()//Basically runs through all the mobs in the area to determine how much they are worth.
var/captured_amount = 0
var/area/centcom/holding/A = locate()
@@ -609,8 +604,7 @@ datum/objective/capture
return 1
/datum/objective/absorb
proc/gen_amount_goal(var/lowbound = 4, var/highbound = 6)
/datum/objective/absorb/proc/gen_amount_goal(var/lowbound = 4, var/highbound = 6)
target_amount = rand (lowbound,highbound)
if (ticker)
var/n_p = 1 //autowin
@@ -627,19 +621,17 @@ datum/objective/capture
explanation_text = "Absorb [target_amount] compatible genomes."
return target_amount
check_completion()
/datum/objective/absorb/check_completion()
if(owner && owner.changeling && owner.changeling.absorbed_dna && (owner.changeling.absorbedcount >= target_amount))
return 1
else
return 0
// Heist objectives.
datum/objective/heist
proc/choose_target()
/datum/objective/heist/proc/choose_target()
return
datum/objective/heist/kidnap
choose_target()
/datum/objective/heist/kidnap/choose_target()
var/list/roles = list("Chief Engineer","Research Director","Roboticist","Chemist","Station Engineer")
var/list/possible_targets = list()
var/list/priority_targets = list()
@@ -663,7 +655,7 @@ datum/objective/heist/kidnap
explanation_text = "Free Objective"
return target
check_completion()
/datum/objective/heist/kidnap/check_completion()
if(target && target.current)
if (target.current.stat == 2)
return 0 // They're dead. Fail.
@@ -677,9 +669,7 @@ datum/objective/heist/kidnap
else
return 0
datum/objective/heist/loot
choose_target()
/datum/objective/heist/loot/choose_target()
var/loot = "an object"
switch(rand(1,8))
if(1)
@@ -717,8 +707,8 @@ datum/objective/heist/loot
explanation_text = "It's a buyer's market out here. Steal [loot] for resale."
check_completion()
/datum/objective/heist/loot/check_completion()
var/total_amount = 0
for(var/obj/O in locate(/area/skipjack_station/start))
@@ -735,9 +725,7 @@ datum/objective/heist/loot
return 0
datum/objective/heist/salvage
choose_target()
/datum/objective/heist/salvage/choose_target()
switch(rand(1,8))
if(1)
target = DEFAULT_WALL_MATERIAL
@@ -766,7 +754,7 @@ datum/objective/heist/salvage
explanation_text = "Ransack the station and escape with [target_amount] [target]."
check_completion()
/datum/objective/heist/salvage/check_completion()
var/total_amount = 0
@@ -798,7 +786,7 @@ datum/objective/heist/salvage
/datum/objective/heist/preserve_crew
explanation_text = "Do not leave anyone behind, alive or dead."
check_completion()
/datum/objective/heist/preserve_crew/check_completion()
if(raiders && raiders.is_raider_crew_safe()) return 1
return 0

Some files were not shown because too many files have changed in this diff Show More