Initial Commit

This commit is contained in:
Tobba
2016-03-06 20:52:14 +01:00
commit b181d0b552
4325 changed files with 579453 additions and 0 deletions
+460
View File
@@ -0,0 +1,460 @@
/obj/item/clothing/head/wig
name = "toupée"
desc = "You can't tell the difference, Honest!"
icon_state= "wig"
/obj/item/clothing/head/bald_cap
name = "bald cap"
desc = "You can't tell the difference, Honest!"
icon_state= "baldcap"
item_state= "baldcap"
/obj/item/scissors
name = "Scissors"
desc = "Used to cut hair. Make sure you aim at the head, where the hair is."
icon = 'icons/obj/barber_shop.dmi'
icon_state = "scissors"
flags = FPRINT | TABLEPASS | CONDUCT
force = 10.0
w_class = 1.0
hit_type = DAMAGE_STAB
hitsound = 'sound/effects/bloody_stab.ogg'
throwforce = 5.0
throw_speed = 3
throw_range = 5
m_amt = 10000
g_amt = 5000
suicide(var/mob/user as mob)
user.visible_message("<span style=\"color:red\"><b>[user] slashes \his own throat with [src]!</b></span>")
blood_slash(user, 25)
user.TakeDamage("head", 150, 0)
user.updatehealth()
spawn(100)
if (user)
user.suiciding = 0
return 1
/obj/item/razor_blade
name = "Razor Blade"
desc = "Used to cut facial hair"
icon = 'icons/obj/barber_shop.dmi'
icon_state = "razorblade"
flags = FPRINT | TABLEPASS | CONDUCT
force = 10.0
w_class = 1.0
hit_type = DAMAGE_CUT
hitsound = 'sound/weapons/slashcut.ogg'
throwforce = 5.0
throw_speed = 3
throw_range = 5
m_amt = 10000
g_amt = 5000
suicide(var/mob/user as mob)
user.visible_message("<span style=\"color:red\"><b>[user] slashes \his own throat with [src]!</b></span>")
blood_slash(user, 25)
user.TakeDamage("head", 150, 0)
user.updatehealth()
spawn(100)
if (user)
user.suiciding = 0
return 1
/obj/item/dye_bottle
name = "Hair Dye Bottle"
desc = "Used to dye hair a different color. Seems to be made of tough, unshatterable plastic."
icon = 'icons/obj/barber_shop.dmi'
icon_state = "dye-e"
flags = FPRINT | TABLEPASS
//Default Colors
var/customization_first_color = "#FFFFFF"
var/empty = 1
/obj/item/reagent_containers/food/drinks/hairgrowth
name = "EZ-Hairgrowth"
desc = "The #1 hair growth product on the market! WARNING: Some side effects may occur."
icon = 'icons/obj/barber_shop.dmi'
icon_state = "tonic1"
New()
var/datum/reagents/R = new/datum/reagents(50)
reagents = R
R.my_atom = src
R.add_reagent("hairgrownium", 40)
on_reagent_change()
src.icon_state = "tonic[src.reagents.total_volume ? "1" : "0"]"
/obj/stool/barber_chair
name = "Barber Chair"
desc = "Chair where hair can be cut"
icon = 'icons/obj/barber_shop.dmi'
icon_state = "barberchair"
anchored = 1
/obj/barber_pole
name = "Barber Pole"
icon = 'icons/obj/barber_shop.dmi'
icon_state = "pole"
density = 1
anchored = 1
desc = "Barber poles historically were signage used to convey that the barber would perform services such as blood letting and other medical procedures, with the red representing blood, and the white representing the bandaging. In America, long after the time when blood-letting was offered, a third colour was added to bring it in line with the colours of their national flag. This one is in space."
///////////////////////////////////////////
///////////Barber Chair Code///////////////
///////////////////////////////////////////
/obj/stool/barber_chair/MouseDrop_T(mob/M as mob, mob/user as mob)
if (!ticker)
boutput(user, "You can't buckle anyone in before the game starts.")
return
if ((!( iscarbon(M) ) || get_dist(src, user) > 1 || M.loc != src.loc || user.restrained() || usr.stat))
return
if (M == usr)
user.visible_message("<span style=\"color:blue\">[M] buckles in!</span>", "<span style=\"color:blue\">You buckle yourself in.</span>")
else
user.visible_message("<span style=\"color:blue\">[M] is buckled in by [user].</span>", "<span style=\"color:blue\">You buckle in [M].</span>")
M.anchored = 1
M.buckled = src
M.set_loc(src.loc)
src.add_fingerprint(user)
return
/obj/stool/barber_chair/attack_hand(mob/user as mob)
for(var/mob/M in src.loc)
if (M.buckled)
if (M != user)
user.visible_message("<span style=\"color:blue\">[M] is unbuckled by [user].</span>", "<span style=\"color:blue\">You unbuckle [M].</span>")
else
user.visible_message("<span style=\"color:blue\">[M] unbuckles.</span>", "<span style=\"color:blue\">You unbuckle.</span>")
M.anchored = 0
M.buckled = null
src.add_fingerprint(user)
return
/obj/stool/barber_chair/ex_act(severity)
for(var/mob/M in src.loc)
if(M.buckled == src)
M.buckled = null
switch(severity)
if(1.0)
qdel(src)
return
if(2.0)
if (prob(50))
qdel(src)
return
if(3.0)
if (prob(5))
qdel(src)
return
return
/obj/stool/barber_chair/blob_act(var/power)
if(prob(power * 2.5))
for(var/mob/M in src.loc)
if(M.buckled == src)
M.buckled = null
qdel(src)
/*
/obj/stool/barber_chair/verb/rotate()
set src in oview(1)
set category = "Local"
src.dir = turn(src.dir, 90)
if (src.dir == NORTH)
src.layer = FLY_LAYER
else
src.layer = OBJ_LAYER
return
*/
///////////////////////////////////////////////////
//////Hair Dye Bottle Code ///////
///////////////////////////////////////////////////
/obj/item/dye_bottle/attack(mob/living/carbon/human/M as mob, mob/user as mob)
if(!istype(M,/mob/living/carbon/human)) return
if(user.zone_sel.selecting != "head" || user.a_intent != "help")
..()
return
if(src.empty)
boutput(user, "<span style=\"color:red\">Bottle is empty!</span>")
else //if(istype(M.buckled, /obj/stool/barber_chair))
var/mob/living/carbon/human/H = M
if(istype(M, /mob/living/carbon/human) && ((H.head && H.head.c_flags & COVERSEYES) || (H.wear_mask && H.wear_mask.c_flags & COVERSEYES)))
// you can't stab someone in the eyes wearing a mask!
boutput(user, "<span style=\"color:blue\">You're going to need to remove that mask/helmet first.</span>")
return
/*
var/turf/T = M.loc
var/turf/TM = user.loc
boutput(user, "<span style=\"color:blue\">You begin dying [M]'s hair.</span>")
boutput(M, "<span style=\"color:blue\">[user] begins dying your hair.</span>")
sleep(30)
if(M.loc == T && TM.loc == user.loc && (user.equipped() == src || istype(user, /mob/living/silicon)))
return
*/
boutput(user, "<span style=\"color:blue\">You dye [M]'s hair.</span>")
boutput(M, "<span style=\"color:blue\">[user] dyes your hair.</span>")
M.bioHolder.mobAppearance.customization_first_color = src.customization_first_color
M.bioHolder.mobAppearance.customization_second_color = src.customization_first_color
M.set_face_icon_dirty()
M.set_body_icon_dirty()
M.update_clothing()
src.empty = 1
src.icon_state= "dye-e"
//else
// boutput(user, "<span style=\"color:red\">They need to be in a barber chair!</span>")
/////////////////////////////////////////////////////
//////Scissors Code /////
////////////////////////////////////////////////////
/obj/item/scissors/attack(mob/living/carbon/human/M as mob, mob/user as mob)
if (src.remove_bandage(M, user))
return
if(user.zone_sel.selecting != "head" || user.a_intent != "help")
..()
return
if (user == M)
boutput(user, "<span style=\"color:red\">You can't cut your own hair!</span>")
return
if(istype(M.buckled, /obj/stool/barber_chair))
var/mob/living/carbon/human/H = M
if(istype(M, /mob/living/carbon/human) && ((H.head && H.head.c_flags & COVERSEYES) || (H.wear_mask && H.wear_mask.c_flags & COVERSEYES) || (H.glasses && H.glasses.c_flags & COVERSEYES)))
// you can't stab someone in the eyes wearing a mask!
boutput(user, "<span style=\"color:blue\">You're going to need to remove that mask/helmet/glasses first.</span>")
return
if(M.bioHolder.mobAppearance.customization_first == "None")
boutput(user, "<span style=\"color:red\">There is nothing to cut!</span>")
return
var/new_style = input(user, "Please select style", "Style") as null|anything in customization_styles
if (new_style)
if(M.bioHolder.mobAppearance.customization_first == "Balding" && new_style != "None")
boutput(user, "<span style=\"color:red\">Not enough hair!</span>")
return
if(!new_style)
return
var/turf/T = M.loc
var/turf/TM = user.loc
boutput(user, "<span style=\"color:blue\">You begin cutting [M]'s hair.</span>")
boutput(M, "<span style=\"color:blue\">[user] begins cutting your hair.</span>")
playsound(src.loc, "sound/items/Scissor.ogg", 100, 1)
sleep(70)
if(M.loc == T && TM.loc == user.loc && (user.equipped() == src || istype(user, /mob/living/silicon)))
return
if (new_style == "None")
var/obj/item/I = M.create_wig()
I.set_loc(user.loc)
M.bioHolder.mobAppearance.customization_first = new_style
boutput(M, "<span style=\"color:blue\">[user] cuts your hair.</span>")
boutput(user, "<span style=\"color:blue\">you cut [M]'s hair.</span>")
M.cust_one_state = customization_styles[new_style]
M.set_clothing_icon_dirty() // why the fuck is hair updated in clothing
//////////////////////////////////////////////////////////
////Razor Blade /////
/////////////////////////////////////////////////////////
/obj/item/razor_blade/attack(mob/living/carbon/human/M as mob, mob/user as mob)
if(scalpel_surgery(M,user)) return
if(user.zone_sel.selecting != "head" || user.a_intent != "help")
..()
return
if( istype(M, /mob/living/silicon))
boutput(user, "<span style=\"color:red\">Shave a robot? Shave a robot!?? SHAVE A ROBOT?!?!??</span>")
return
if(M.cust_two_state == "wiz")
if (user == M)
boutput(user, "<span style=\"color:red\">No!!! This is the worst idea you've ever had!</span>")
return
src.visible_message("<span style=\"color:red\"><b>[user]</b> quickly shaves off [M]'s beard!</span>")
M.bioHolder.AddEffect("arcane_shame", timeleft = 120)
M.bioHolder.mobAppearance.customization_second = "None"
M.cust_two_state = "None"
M.set_face_icon_dirty()
M.emote("cry")
return
if(istype(M.buckled, /obj/stool/barber_chair))
var/mob/living/carbon/human/H = M
if(istype(M, /mob/living/carbon/human) && ((H.head && H.head.c_flags & COVERSEYES) || (H.wear_mask && H.wear_mask.c_flags & COVERSEYES) || (H.glasses && H.glasses.c_flags & COVERSEYES)))
// you can't stab someone in the eyes wearing a mask!
boutput(user, "<span style=\"color:blue\">You're going to need to remove that mask/helmet/glasses first.</span>")
return
if(M.bioHolder.mobAppearance.customization_second == "None")
boutput(user, "<span style=\"color:red\">There is nothing to shave!</span>")
return
var/new_style = input(user, "Please select facial style", "Facial Style") as null|anything in customization_styles
if (new_style)
var/list/mustaches =list("Watson", "Chaplin", "Selleck", "Van Dyke", "Hogan")
var/list/beards = list("Neckbeard", "Elvis", "Abe", "Chinstrap", "Hipster", "Wizard")
var/list/full = list("Goatee", "Full Beard", "Long Beard")
if((new_style in full) && (!(M.bioHolder.mobAppearance.customization_second in full)))
boutput(user, "<span style=\"color:red\">[M] doesn't have enough facial hair!</span>")
return
if((new_style in beards) && (M.bioHolder.mobAppearance.customization_second in mustaches))
boutput(user, "<span style=\"color:red\">[M] doesn't have a beard!</span>")
return
if((new_style in mustaches) && (M.bioHolder.mobAppearance.customization_second in beards))
boutput(user, "<span style=\"color:red\">[M] doesn't have a mustache!</span>")
return
var/turf/T = M.loc
var/turf/TM = user.loc
boutput(user, "<span style=\"color:blue\">You begin shaving [M].</span>")
boutput(M, "<span style=\"color:blue\">[user] begins shaving you.</span>")
//playsound(src.loc, "Scissor.ogg", 100, 1)
sleep(70)
if(M.loc == T && TM.loc == user.loc && (user.equipped() == src || istype(user, /mob/living/silicon)))
return
M.bioHolder.mobAppearance.customization_second = new_style
boutput(M, "<span style=\"color:blue\">[user] shaves your face</span>")
boutput(user, "<span style=\"color:blue\">You shave [M]'s face.</span>")
M.cust_two_state = customization_styles[new_style]
M.set_face_icon_dirty()
//////////////////////////////////////////////////////////////////
/////Dye Bottle Dispenser /////
/////////////////////////////////////////////////////////////////
/obj/machinery/hair_dye_dispenser
name = "Hair Dye Mixer 3000"
desc = "Mixes hair dye for whatever color you want"
icon = 'icons/obj/barber_shop.dmi'
icon_state = "dyedispenser"
density = 1
anchored = 1.0
mats = 15
var/obj/item/dye_bottle/bottle = null
New()
..()
UnsubscribeProcess()
ex_act(severity)
switch(severity)
if(1.0)
//SN src = null
qdel(src)
return
if(2.0)
if (prob(50))
//SN src = null
qdel(src)
return
else
return
blob_act(var/power)
if (prob(power * 1.25))
qdel(src)
meteorhit()
qdel(src)
return
process()
return
attack_ai(mob/user as mob)
return src.attack_hand(user)
attack_hand(mob/user as mob)
if(stat & BROKEN)
return
user.machine = src
var/dat = "<TT><B>Dye Bottle Dispenser Unit</B><BR><HR><BR>"
if(src.bottle)
dat += {"Dye Bottle Loaded: <A href='?src=\ref[src];eject=1'>(Eject)</A><BR><BR><BR>Dye Color:<BR>"}
if(!src.bottle.empty)
dat += "<A href='?src=\ref[src];emptyb=1'>Empty Dye Bottle</A><BR>"
else
dat += {"<A href='?src=\ref[src];fillb=1'>Fill Dye Bottle</A>"}
else
dat += "No Dye Bottle Loaded<BR>"
user << browse(dat, "window=dye_dispenser")
onclose(user, "dye_dispenser")
return
attackby(obj/item/W, mob/user as mob)
if(istype(W, /obj/item/dye_bottle))
if(src.bottle)
boutput(user, "<span style=\"color:blue\">The dispenser already has a dye bottle in it.</span>")
else
boutput(user, "<span style=\"color:blue\">You insert the dye bottle into the dispenser.</span>")
if(W)
user.drop_item(W)
W.set_loc(src)
src.bottle = W
return
..()
return
Topic(href, href_list)
if(stat & BROKEN)
return
if(usr.stat || usr.restrained())
return
if (istype(usr, /mob/living/silicon/ai))
boutput(usr, "<span style=\"color:red\">You are unable to dispense anything, since the controls are physical levers which don't go through any other kind of input.</span>")
return
if ((usr.contents.Find(src) || ((get_dist(src, usr) <= 1) && istype(src.loc, /turf))))
usr.machine = src
if (href_list["eject"])
if(src.bottle)
src.bottle.set_loc(src.loc)
src.bottle = null
if(href_list["fillb"])
if(src.bottle)
var/new_dye = input(usr, "Please select hair color.", "Dye Color") as color
if(new_dye)
bottle.customization_first_color = new_dye
bottle.empty = 0
bottle.icon_state = "dye-f"
src.updateDialog()
if(href_list["emptyb"])
if(src.bottle)
bottle.empty = 1
bottle.icon_state = "dye-e"
src.updateDialog()
src.add_fingerprint(usr)
for(var/mob/M in viewers(1, src))
if ((M.client && M.machine == src))
src.attack_hand(M)
else
usr << browse(null, "window=dye_dispenser")
return
return
+584
View File
@@ -0,0 +1,584 @@
//Config stuff
#define SUPPLY_DOCKZ 2 //Z-level of the Dock.
#define SUPPLY_STATIONZ 1 //Z-level of the Station.
#define SUPPLY_POINTSPER 1 //Points per tick.
#define SUPPLY_POINTDELAY 450 //Delay between ticks in milliseconds.
#define SUPPLY_MOVETIME 1800 //Time to station is milliseconds. 1800 default
#define SUPPLY_POINTSPERCRATE 10 //Points per crate sent back.
var/list/supply_requestlist = new/list()
var/list/supply_history = new/list()
var/supply_shuttle_can_send = 1
var/supply_shuttle_time = 0
var/supply_shuttle_timeleft = 0
var/supply_shuttle_moving = 0
var/supply_shuttle_at_station = 0
var/door_id = "qm_dock"
/area/supply/spawn_point //the area supplies are spawned at and fired from
name = "supply spawn point"
icon_state = "shuttle3"
luminosity = 1
RL_Lighting = 0
requires_power = 0
/area/supply/delivery_point //the area supplies are fired at
name = "supply target point"
icon_state = "shuttle3"
luminosity = 1
RL_Lighting = 0
requires_power = 0
/area/supply/sell_point //the area where supplies move from the station z level
name = "supply sell region"
icon_state = "shuttle3"
luminosity = 1
RL_Lighting = 0
requires_power = 0
Entered(var/atom/movable/AM)
..()
if(istype(AM,/obj/storage/crate))
if(can_sell(AM))
for(var/datum/trader/T in shippingmarket.active_traders)
if (T.crate_tag == AM.delivery_destination)
sell_to_trader(AM,T)
return
sell_crate(AM)
/obj/plasticflaps //HOW DO YOU CALL THOSE THINGS ANYWAY
name = "Plastic flaps"
desc = "I definitely cant get past those. no way."
icon = 'icons/obj/stationobjs.dmi' //Change this.
icon_state = "plasticflaps"
density = 0
anchored = 1
layer = EFFECTS_LAYER_UNDER_1
/obj/plasticflaps/CanPass(atom/A, turf/T)
if (istype(A, /mob/living)) // You Shall Not Pass!
var/mob/living/M = A
if(!M.lying) // unless you're lying down
return 0
return ..()
/obj/plasticflaps/ex_act(severity)
switch(severity)
if (1)
qdel(src)
if (2)
if (prob(50))
qdel(src)
if (3)
if (prob(5))
qdel(src)
/obj/marker/supplymarker
icon_state = "X"
icon = 'icons/misc/mark.dmi'
name = "X"
invisibility = 101
anchored = 1
opacity = 0
/proc/supply_ticker()
wagesystem.shipping_budget += SUPPLY_POINTSPER
spawn(SUPPLY_POINTDELAY) supply_ticker()
/proc/can_sell(var/obj/storage/crate/sellcrate)
/*var/filterdead = 0
if (shippingmarket.trader)
if (shippingmarket.trader:goodsname == "corpses") filterdead = 1
for(var/mob/living/M in sellcrate)
if(filterdead && M.stat == 2) continue
return 0
for(var/atom/ATM in sellcrate)
for(var/mob/living/N in ATM:contents)
if(filterdead && N.stat == 2) continue
return 0*/
// Is this even necessary anymore?
return 1
/proc/sell_crate(var/obj/storage/crate/sell_crate)
if (istype(sell_crate, /obj/storage/crate/biohazard/cdc))
for (var/R in sell_crate)
if (istype(R, /obj/item/reagent_containers) || istype(R, /mob/living/carbon/human)) //heh
var/obj/item/reagent_containers/RC = R
var/list/patho = RC.reagents.aggregate_pathogens()
for (var/uid in patho)
if (!(uid in QM_CDC.analysis_by_uid))
var/datum/pathogen/P = patho[uid]
var/datum/cdc_contact_analysis/D = new
D.uid = uid
var/sym_count = max(min(length(P.effects), 7), 2)
D.time_factor = sym_count * rand(200, 600)
D.cure_cost = sym_count * rand(2100, 4300)
D.name = P.name
var/rating = max(P.advance_speed, P.mutation_speed, P.mutativeness, P.suppression_threshold, P.maliciousness)
var/ds = "weak"
switch (P.stages)
if (4)
ds = "potent"
if (5)
ds = "deadly"
var/df = "a relatively one-sided"
switch (sym_count)
if (3 to 4)
df = "a somewhat colorful"
if (5 to 6)
df = "a rather diverse"
if (7)
df = "an incredibly symptomatic"
D.desc = "It is [df] pathogen with a hazard rating of [rating]. We identify it to be a [ds] organism made up of [P.body_type.plural]. [P.suppressant.desc]"
var/datum/pathogen/copy = unpool(/datum/pathogen)
copy.setup(0, P, 0, null)
D.assoc_pathogen = copy
QM_CDC.analysis_by_uid[uid] = D
QM_CDC.ready_to_analyze += D
if (ishuman(RC))
var/mob/living/carbon/human/H = RC
H.ghostize()
qdel(RC)
qdel(sell_crate)
var/datum/radio_frequency/transmit_connection = radio_controller.return_frequency("1149")
var/datum/signal/pdaSignal = get_free_signal()
pdaSignal.data = list("address_1"="00000000", "command"="text_message", "sender_name"="CARGO-MAILBOT", "group"="cargo", "sender"="00000000", "message"="Notification: Pathogen sample crate delivered to the CDC.")
pdaSignal.transmission_method = TRANSMISSION_RADIO
if(transmit_connection != null)
transmit_connection.post_signal(src, pdaSignal)
return
var/amount = 1
// log account information for QM sales
var/obj/item/card/id/scan = sell_crate.scan
var/datum/data/record/account = sell_crate.account
var/list/to_sell = new/list()
for(var/obj/M in sell_crate.contents)
amount = hasvar(M, "amount") && M:amount > 1 ? M:amount : 1
if (isnum(to_sell.Find(M.type)))
to_sell[M.type] += amount
//boutput(world, "<span style=\"color:red\"><b> HEY I SHOULD BE SELLING [M.type]</b></span>")
else
to_sell[M.type] = amount
//boutput(world, "<span style=\"color:red\"><b> [M.type] in the house</b></span>")
qdel(M)
qdel(sell_crate)
var/duckets = 0 // fuck yeah duckets
duckets += SUPPLY_POINTSPERCRATE
for(var/item_type in to_sell)
////////////////////////////////////////////////////////////////////////////////////////////////////////////////
// cogwerks - child types weren't inheriting their parent value properly, here is an ugly patch for the problem
//boutput(world, "<b>PRESANITIZED SWITCH FOR [item_type]</b>") ////////////////////////////////////////////////////////
var/sanitizer = item_type
if(ispath(item_type, /obj/item/reagent_containers/food/snacks/ingredient/meat))
sanitizer = /obj/item/reagent_containers/food/snacks/ingredient/meat
if(ispath(item_type, /obj/item/reagent_containers/food/snacks/plant))
sanitizer = /obj/item/reagent_containers/food/snacks/plant
if(ispath(item_type, /obj/item/plant/herb))
sanitizer = /obj/item/plant/herb
if(ispath(item_type, /obj/item/electronics))
sanitizer = /obj/item/electronics
if(ispath(item_type, /obj/item/parts/robot_parts))
sanitizer = /obj/item/parts/robot_parts
if(ispath(item_type, /obj/item/sheet/steel))
sanitizer = /obj/item/sheet/steel
if(ispath(item_type, /obj/item/sheet/glass))
sanitizer = /obj/item/sheet/glass
//boutput(world, "[sanitizer] is our intermediary")
////////////////////////////////////////////////////////////////////////////////////////////////////////////////
///////////// add more ispath checks as needed, or get someone more competent to write a better workaround /////
////////////////////////////////////////////////////////////////////////////////////////////////////////////////
var/datum/commodity/C = shippingmarket.commodities["[sanitizer]"]
//boutput(world, "<b> WE ARE LOOKING FOR [item_type]")
amount = to_sell[item_type]
if (C)
//boutput(world, "<b> [C] should fetch [C.price]")
if (C.indemand)
//wagesystem.shipping_budget += amount * C.price * shippingmarket.demand_multiplier
duckets += amount * C.price * shippingmarket.demand_multiplier
//boutput(world, "<b> IN DEMAND: SELLING [amount] of [C] for [C.price] times [shippingmarket.demand_multiplier]</b>")
else
//wagesystem.shipping_budget += amount * C.price
duckets += amount * C.price
//boutput(world, "<b> NOT IN DEMAND: SELLING [amount] of [C] for [C.price]</b>")
else
//wagesystem.shipping_budget += amount
duckets += amount
//boutput(world, "<b> [C] NEVER SOLD RIGHT, FUCKIN HELL</b>")
score_stuffshipped += amount
if(scan && account)
wagesystem.shipping_budget += duckets / 2
account.fields["current_money"] += duckets / 2
//////PDA NOTIFY/////
var/datum/radio_frequency/transmit_connection = radio_controller.return_frequency("1149")
var/datum/signal/pdaSignal = get_free_signal()
pdaSignal.data = list("address_1"="00000000", "command"="text_message", "sender_name"="CARGO-MAILBOT", "group"="cargo", "sender"="00000000", "message"="Notification: [duckets] credits earned from last outgoing shipment. Splitting half of profits with [scan.registered].")
pdaSignal.transmission_method = TRANSMISSION_RADIO
if(transmit_connection != null)
transmit_connection.post_signal(src, pdaSignal)
//////////
else
wagesystem.shipping_budget += duckets
//////PDA NOTIFY/////
var/datum/radio_frequency/transmit_connection = radio_controller.return_frequency("1149")
var/datum/signal/pdaSignal = get_free_signal()
pdaSignal.data = list("address_1"="00000000", "command"="text_message", "sender_name"="CARGO-MAILBOT", "group"="cargo", "sender"="00000000", "message"="Notification: [duckets] credits earned from last outgoing shipment.")
pdaSignal.transmission_method = TRANSMISSION_RADIO
if(transmit_connection != null)
transmit_connection.post_signal(src, pdaSignal)
//////////
////transaction is over ///
/proc/sell_to_trader(var/obj/storage/crate/sellcrate,var/datum/trader/the_trader)
//return
var/sellcount = 0
var/amount = 1
//var/sellmax = shippingmarket.trader:limit
// log account information for QM sales // for some stupid reason this was getting a bad var bug and i have no idea why - cogwerks
var/obj/item/card/id/scan = null
if(sellcrate.scan)
scan = sellcrate.scan
var/datum/data/record/account = null
if(sellcrate.account)
account = sellcrate.account
var/duckets = 0
var/itemchecklimit = 0
for(var/obj/M in sellcrate:contents)
itemchecklimit++
if (itemchecklimit > 50)
break
if (!the_trader)
break
//if (sellmax && (sellcount >= sellmax)) break
/*if(ispath(M, /obj/item/reagent_containers/food/snacks/ingredient/meat))
M = /obj/item/reagent_containers/food/snacks/ingredient/meat
if(ispath(M, /obj/item/reagent_containers/food/snacks/plant))
M = /obj/item/reagent_containers/food/snacks/plant
if(ispath(M, /obj/item/plant/herb))
M = /obj/item/plant/herb
if(ispath(M, /obj/item/electronics))
M = /obj/item/electronics
if(ispath(M, /obj/item/parts/robot_parts))
M = /obj/item/parts/robot_parts
if(ispath(M, /obj/item/sheet/steel))
M = /obj/item/sheet/steel
if(ispath(M, /obj/item/sheet/glass))
M = /obj/item/sheet/glass
if(istype(M,shippingmarket.trader:tradegoods))
amount = hasvar(M, "amount") && M:amount > 1 ? M:amount : 1
duckets += amount * shippingmarket.trader:price
score_stufftraded += amount
sellcount++
qdel(M)*/
for(var/datum/commodity/C in the_trader.goods_buy)
//if (M.type == C.comtype)
if (istype(M,C.comtype))
amount = hasvar(M, "amount") && M:amount > 1 ? M:amount : 1
duckets += amount * C.price
score_stufftraded += amount
sellcount++
qdel(M)
qdel(sellcrate)
if (sellcount)
if(scan && account)
wagesystem.shipping_budget += duckets / 2
account.fields["current_money"] += duckets / 2
//////PDA NOTIFY/////
var/datum/radio_frequency/transmit_connection = radio_controller.return_frequency("1149")
var/datum/signal/pdaSignal = get_free_signal()
pdaSignal.data = list("address_1"="00000000", "command"="text_message", "sender_name"="CARGO-MAILBOT", "group"="cargo", "sender"="00000000", "message"="Deal with \"[the_trader.name]\" concluded. Net Profit: [duckets] credits. Splitting half of profits with [scan.registered].")
pdaSignal.transmission_method = TRANSMISSION_RADIO
if(transmit_connection != null)
transmit_connection.post_signal(src, pdaSignal)
//////////
else
wagesystem.shipping_budget += duckets
//////PDA NOTIFY/////
var/datum/radio_frequency/transmit_connection = radio_controller.return_frequency("1149")
var/datum/signal/pdaSignal = get_free_signal()
pdaSignal.data = list("address_1"="00000000", "command"="text_message", "sender_name"="CARGO-MAILBOT", "group"="cargo", "sender"="00000000", "message"="Deal with \"[the_trader.name]\" concluded. Net Profit: [duckets] credits.")
pdaSignal.transmission_method = TRANSMISSION_RADIO
if(transmit_connection != null)
transmit_connection.post_signal(src, pdaSignal)
/*/proc/sell_corpses(var/obj/storage/crate/sellcrate)
// special case sell proc for Vurdalak
// he doesnt do this anymore it was a phase he was going through ok
set background = 1
var/sellcount = 0
var/sellmax = shippingmarket.trader:limit
for(var/mob/living/carbon/I in sellcrate)
if (sellmax && (sellcount >= sellmax)) break
if (I.stat != 2)
shippingmarket.trader = null
var/datum/radio_frequency/transmit_connection = radio_controller.return_frequency("1149")
var/datum/signal/pdaSignal = get_free_signal()
pdaSignal.data = list("address_1"="00000000", "command"="text_message", "sender_name"="CARGO-MAILBOT", "group"="cargo", "sender"="00000000", "message"="Alert: \"[shippingmarket.trader:name]\" has abruptly rescinded their trade offer and left")
pdaSignal.transmission_method = TRANSMISSION_RADIO
transmit_connection.post_signal(src, pdaSignal)
return
wagesystem.shipping_budget += shippingmarket.trader:price
score_stufftraded += 1
sellcount++
if (I.mind || I.client) // if the player is waiting in the corpse, ghost them so we dont get respawn exploits
var/mob/dead/observer/newmob = new/mob/dead/observer(I)
if(I.client) I:client:mob = newmob
I.mind.transfer_to(newmob)
spawn(0)
qdel(I)
qdel(sellcrate)
if (sellcount)
var/datum/radio_frequency/transmit_connection = radio_controller.return_frequency("1149")
var/datum/signal/pdaSignal = get_free_signal()
pdaSignal.data = list("address_1"="00000000", "command"="text_message", "sender_name"="CARGO-MAILBOT", "group"="cargo", "sender"="00000000", "message"="Deal with \"[shippingmarket.trader:name]\" concluded. Net Profit: [sellcount * shippingmarket.trader:price] credits")
pdaSignal.transmission_method = TRANSMISSION_RADIO
transmit_connection.post_signal(src, pdaSignal)
shippingmarket.trader = null*/
// fuck it doing this with more globals
var/crate_firing = 0
/proc/buy_thing(var/atom/movable/O as obj|mob)
var/turf/spawnpoint
for(var/turf/T in get_area_turfs(/area/supply/spawn_point))
spawnpoint = T
break
var/turf/target
for(var/turf/T in get_area_turfs(/area/supply/delivery_point))
target = T
break
spawn(0)
while(crate_firing)
sleep(20)
if (!spawnpoint)
logTheThing("debug", null, null, "<b>Shipping: </b> No spawn turfs found! Can't deliver crate")
return
if (!target)
logTheThing("debug", null, null, "<b>Shipping: </b> No target turfs found! Can't deliver crate")
return
crate_firing = 1
spawn(80)
crate_firing = 0
O.set_loc(spawnpoint)
var/datum/radio_frequency/transmit_connection = radio_controller.return_frequency("1149")
var/datum/signal/pdaSignal = get_free_signal()
pdaSignal.data = list("address_1"="00000000", "command"="text_message", "sender_name"="CARGO-MAILBOT", "group"="cargo", "sender"="00000000", "message"="Shipment arriving to Cargo Bay: [O.name].")
pdaSignal.transmission_method = TRANSMISSION_RADIO
transmit_connection.post_signal(src, pdaSignal)
for(var/obj/machinery/door/poddoor/P)
if (P.id == door_id)
playsound(P.loc, "sound/machines/bellalert.ogg", 50, 0)
spawn(10)
if (P && P.density)
P.open()
spawn(130)
if (P && !P.density)
P.close()
spawn(20)
O.throw_at(target, 100, 1)
/proc/buy_from_trader(var/datum/trader/the_trader)
//could be multiple possible spawn turfs
var/turf/spawnpoint
for(var/turf/T in get_area_turfs(/area/supply/spawn_point))
spawnpoint = T
break
//shouldn't be multiple delivery spots but it's possible
var/turf/target
for(var/turf/T in get_area_turfs(/area/supply/delivery_point))
target = T
break
if (!the_trader)
return
the_trader.currently_selling = 1
spawn(0)
var/sanity = 0
while(crate_firing && sanity < 30) // give up after 1 minute, should only take 15 seconds at most
sleep(20)
sanity++
if (sanity == 30)
logTheThing("debug", null, null, "<b>Shipping: </b> Timed out waiting to fire crate, what a bummer!")
the_trader.currently_selling = 0
return
if (!spawnpoint)
logTheThing("debug", null, null, "<b>Shipping: </b> No spawn turfs found! Can't deliver crate")
the_trader.currently_selling = 0
return
if (!target)
logTheThing("debug", null, null, "<b>Shipping: </b> No target turfs found! Can't deliver crate")
the_trader.currently_selling = 0
return
crate_firing = 1
spawn(80)
crate_firing = 0
var/atom/movable/A = new /obj/storage/crate(spawnpoint)
A.name = "Goods Crate ([the_trader.name])"
/*var/putincrate = purchaseamt
if (putincrate < 1) putincrate = 1
if(prob(shippingmarket.trader:bullshit * 10)) // oh no! you got ripped off!
while(putincrate > 1)
new ourTrader.scamgoods(A)
putincrate--
else // a good deal
while(putincrate > 1)
new ourTrader.tradegoods(A)
putincrate--*/
var/obj/item/paper/invoice = new /obj/item/paper(A)
invoice.name = "Sale Invoice ([the_trader.name])"
invoice.info = "Invoice of Sale from [the_trader.name]<br><br>"
var/total_price = 0
for (var/datum/commodity/trader/C in the_trader.shopping_cart)
if (!C.comtype || C.amount < 1) continue
total_price += C.price * C.amount
invoice.info += "* [C.amount] units of [C.comname], [C.price * C.amount] credits<br>"
var/putamount = C.amount
while(putamount > 0)
putamount--
new C.comtype(A)
invoice.info += "<br>Final Cost of Goods: [total_price] credits."
wagesystem.shipping_budget -= total_price
the_trader.wipe_cart(1) //This tells wipe_cart to not increase the amount in stock when clearing it out.
the_trader.currently_selling = 0 //At this point the shopping cart has been processed
var/datum/radio_frequency/transmit_connection = radio_controller.return_frequency("1149")
var/datum/signal/pdaSignal = get_free_signal()
pdaSignal.data = list("address_1"="00000000", "command"="text_message", "sender_name"="CARGO-MAILBOT", "group"="cargo", "sender"="00000000", "message"="Deal with \"[the_trader.name]\" concluded. Total Cost: [total_price] credits")
pdaSignal.transmission_method = TRANSMISSION_RADIO
transmit_connection.post_signal(src, pdaSignal)
for(var/obj/machinery/door/poddoor/P)
if (P.id == door_id)
playsound(P.loc, "sound/machines/bellalert.ogg", 50, 0)
spawn(10)
if (P && P.density)
P.open()
spawn(130)
if (P && !P.density)
P.close()
spawn(20)
A.throw_at(target, 100, 1)
/proc/process_supply_order(var/datum/supply_order/SO)
//could be multiple possible spawn turfs
var/turf/spawnpoint
for(var/turf/T in get_area_turfs(/area/supply/spawn_point))
spawnpoint = T
break
//shouldn't be multiple delivery spots but it's possible
var/turf/target
for(var/turf/T in get_area_turfs(/area/supply/delivery_point))
target = T
break
spawn(0)
var/sanity = 0
while(crate_firing && sanity < 30) // give up after 1 minute, should only take 15 seconds at most
sleep(20)
sanity++
if (sanity == 30)
logTheThing("debug", null, null, "<b>Shipping: </b> Timed out waiting to fire crate, what a bummer!")
return
if (!spawnpoint)
logTheThing("debug", null, null, "<b>Shipping: </b> No spawn turfs found! Can't deliver crate")
return
if (!target)
logTheThing("debug", null, null, "<b>Shipping: </b> No target turfs found! Can't deliver crate")
return
crate_firing = 1
spawn(80)
crate_firing = 0
var/atom/movable/A = SO.create(spawnpoint)
for(var/obj/machinery/door/poddoor/P)
if (P.id == door_id)
playsound(P.loc, "sound/machines/bellalert.ogg", 50, 0)
spawn(10)
if (P && P.density)
P.open()
spawn(130)
if (P && !P.density)
P.close()
spawn(20)
if (A)
A.throw_at(target, 100, 1)
/*
#ifdef HALLOWEEN
else if (halloween)
halloween.throw_at(target, 100, 1)
#endif
*/
proc/prisontothestation()
if(turd_location == 0)
var/area/start_location = locate(/area/shuttle/prison/prison)
var/area/end_location = locate(/area/shuttle/prison/station)
var/list/dstturfs = list()
var/throwy = world.maxy
for(var/turf/T in end_location)
dstturfs += T
if(T.y < throwy)
throwy = T.y
for(var/turf/T in dstturfs)
var/turf/D = locate(T.x, throwy - 1, 1)
for(var/atom/movable/AM as mob|obj in T)
if(istype(AM, /mob/dead))
continue
AM.Move(D)
if(istype(T, /turf/simulated))
qdel(T)
start_location.move_contents_to(end_location)
turd_location = 1
else
if(turd_location == 1)
var/area/start_location = locate(/area/shuttle/prison/prison)
var/area/end_location = locate(/area/shuttle/prison/station)
end_location.move_contents_to(start_location)
turd_location = 0
return
+319
View File
@@ -0,0 +1,319 @@
//NOTE:
//This file contains the worst code ive ever written.
//I dont fucking care. It looks pretty awesome.
//////////////////////////////////////////////////////////
/obj/dummy/liquid
name = "water"
icon = 'icons/effects/effects.dmi'
icon_state = "nothing"
invisibility = 101
var/canmove = 1
density = 0
anchored = 1
//
/obj/item/reagent_containers/glass/vial
name = "glass test tube"
icon = 'icons/obj/chemical.dmi'
desc = "an incredibly fragile glass test tube"
icon_state = "vial0"
item_state = "vial"
throwforce = 3.0
throw_speed = 1
throw_range = 8
force = 3.0
w_class = 1.0
amount_per_transfer_from_this = 5
flags = FPRINT | TABLEPASS | OPENCONTAINER
var/contained = null
New()
var/datum/reagents/R = new/datum/reagents(30)
reagents = R
R.my_atom = src
/obj/item/reagent_containers/glass/vial/green
name = "glass test tube"
icon = 'icons/obj/chemical.dmi'
desc = "a glass vial filled with a strange green liquid"
icon_state = "vialgreen"
item_state = "vialgreen"
contained = /datum/ailment/disease/gbs
/obj/item/reagent_containers/glass/blue
name = "glass test tube"
icon = 'icons/obj/chemical.dmi'
desc = "a glass vial filled with a shimmering blue liquid"
icon_state = "vialblue"
item_state = "vialblue"
//This isn't a disease! I should make it one
// contained = new
//////////////////////////////////////////////////////////
///////////////////////////////////////////////////////***
/obj/item/reagent_containers/glass/vial/throw_impact(atom/hit_atom)
..(hit_atom)
src.shatter()
////////////////////////////////////////////////////////////////Generic Vial Shatter
/obj/item/reagent_containers/glass/vial/proc/shatter()
var/A = src
var/atom/sourceloc = get_turf(src.loc)
src = null
qdel(A)
var/obj/overlay/O = new /obj/overlay( sourceloc )
var/obj/overlay/O2 = new /obj/overlay( sourceloc )
O.name = "green liquid"
O.density = 0
O.anchored = 1
O.icon = 'icons/effects/effects.dmi'
O.icon_state = "greenshatter"
O2.name = "broken bits of glass"
O2.density = 0
O2.anchored = 1
O2.icon = 'icons/obj/objects.dmi'
O2.icon_state = "shards"
if(istype(src.contained,/datum/ailment/))
for(var/mob/living/carbon/H in view(5, sourceloc))
H.contract_disease(src.contained,null,null,0)
var/i
for(i=0, i<5, i++)
for(var/mob/living/carbon/H in view(5, sourceloc))
H.contract_disease(src.contained,null,null,0)
sleep(20)
flick("greenshatter2",O)
O.icon_state = "nothing"
sleep(5)
qdel(O)
return
//Generic Vial Drink
/obj/item/reagent_containers/glass/vial/proc/drink(user)
var/A = src
src = null
qdel(A)
if(istype(src.contained,/datum/ailment/))
var/mob/living/M = user
switch(pick(1,2))
if(1)
M.weakened += 5
M.contract_disease(src.contained,null,null,1)
if(2)
spawn(200)
M.contract_disease(src.contained,null,null,1)
return
/obj/item/reagent_containers/glass/vial/blue/drink(user)
var/A = src
var/atom/sourceloc = get_turf(src.loc)
src = null
qdel(A)
var/obj/overlay/O = new /obj/overlay( sourceloc )
var/obj/overlay/O2 = new /obj/overlay( sourceloc )
O.name = "green liquid"
O.density = 0
O.anchored = 1
O.icon = 'icons/effects/effects.dmi'
O.icon_state = "blueshatter"
O2.name = "broken bits of glass"
O2.density = 0
O2.anchored = 1
O2.icon = 'icons/obj/objects.dmi'
O2.icon_state = "shards"
liquify(user)
sleep(20)
flick("blueshatter2",O)
O.icon_state = "nothing"
sleep(5)
qdel(O)
/obj/item/reagent_containers/glass/vial/blue/shatter()
var/A = src
var/atom/sourceloc = get_turf(src.loc)
src = null
qdel(A)
var/obj/overlay/O = new /obj/overlay( sourceloc )
var/obj/overlay/O2 = new /obj/overlay( sourceloc )
O.name = "green liquid"
O.density = 0
O.anchored = 1
O.icon = 'icons/effects/effects.dmi'
O.icon_state = "blueshatter"
O2.name = "broken bits of glass"
O2.density = 0
O2.anchored = 1
O2.icon = 'icons/obj/objects.dmi'
O2.icon_state = "shards"
for(var/mob/living/carbon/human/H in view(1, sourceloc))
liquify(H)
sleep(20)
flick("blueshatter2",O)
O.icon_state = "nothing"
sleep(5)
qdel(O)
/mob/proc/drop_vial()
var/obj/item/reagent_containers/glass/vial/W = src.equipped()
if (W)
u_equip(W)
if (W)
W.set_loc(src.loc)
// W.dropped(src) Get rid of this as it would smash a vial
if (W)
W.layer = initial(W.layer)
var/turf/T = get_turf(src.loc)
T.Entered(W)
return
/proc/liquify(var/mob/H, time = 150)
if(H.stat) return
spawn(0)
var/mobloc = get_turf(H.loc)
var/obj/dummy/liquid/holder = new /obj/dummy/liquid( mobloc )
var/atom/movable/overlay/animation = new /atom/movable/overlay( mobloc )
animation.name = "water"
animation.density = 0
animation.anchored = 1
animation.icon = 'icons/mob/mob.dmi'
animation.icon_state = "liquify"
animation.layer = MOB_EFFECT_LAYER
animation.master = holder
flick("liquify",animation)
H.canmove = 0
sleep(4)
H.set_loc(holder)
H.canmove = 1
spawn(0)
var/i
for(i=0, i<10, i++)
spawn(0)
var/obj/effects/water/water1 = new /obj/effects/water( mobloc )
var/direction = pick(alldirs)
water1.name = "water"
water1.density = 0
water1.icon = 'icons/effects/water.dmi'
water1.icon_state = "extinguish"
for(i=0, i<pick(1,2,3), i++)
sleep(5)
step(water1,direction)
spawn(20)
qdel(water1)
sleep(time)
H.canmove = 0
mobloc = get_turf(H.loc)
animation.set_loc(mobloc)
var/b
for(b=0, b<10, b++)
spawn(0)
var/turf = mobloc
var/direction = pick(alldirs)
var/c
for(c=0, c<pick(1,2,3), c++)
turf = get_step(turf,direction)
var/obj/effects/water/water2 = new /obj/effects/water( turf )
water2.name = "water"
water2.icon = 'icons/effects/water.dmi'
water2.icon_state = "extinguish"
walk_to(water2,mobloc,-1,5)
sleep(20)
qdel(water2)
sleep(20)
flick("reappear",animation)
sleep(5)
H.set_loc(mobloc)
H.canmove = 1
qdel(animation)
qdel(holder)
/obj/dummy/liquid/relaymove(var/mob/user, direction)
if (!src.canmove) return
//writing my own movement because step is broken.
switch(direction)
if(NORTH)
src.y++
if(SOUTH)
src.y--
if(EAST)
src.x++
if(WEST)
src.x--
if(NORTHEAST)
src.y++
src.x++
if(NORTHWEST)
src.y++
src.x--
if(SOUTHEAST)
src.y--
src.x++
if(SOUTHWEST)
src.y--
src.x--
src.canmove = 0
spawn(20) canmove = 1
/obj/dummy/liquid/ex_act(blah)
return
/obj/dummy/liquid/bullet_act(blah,blah)
return
///atom/relaymove - change to obj to restore
/obj/relaymove(var/mob/user, direction) //testing something
//if(anchored) return
//step(src, direction)
/////////////////////////////////////////////////////blue
/*
/obj/testtuberack
name = "test tube rack"
icon = 'icons/obj/items.dmi'
icon_state = "clipboard00"
attackby(obj/item/W, mob/user as mob)
if (src.contents.len >= 7)
boutput(user, "<span style=\"color:blue\">The test tube rack is full</span>")
return
if(istype(W, /obj/item/reagent_containers/glass/vial))
boutput(user, "<span style=\"color:blue\">You insert the test tube into the test tube rack</span>")
user.drop_vial()
W.set_loc(src)
return
..()
return
attack_hand(mob/user as mob)
if(src.contents.len > 0)
boutput(user, "<span style=\"color:blue\">You slide a random test tube carefully out of the rack</span>")
var/obj/item/reagent_containers/glass/vial/V = pick(src.contents)
src.contents -= V
V.set_loc(src.loc)
else
boutput(user, "<span style=\"color:blue\">There are no test tubes in the rack</span>")
return
*/
+487
View File
@@ -0,0 +1,487 @@
// Includes:
// - Airbridge controllers
// - Airbridge computers
// - Airbridge test buttons
// - Dummy turfs
//air bridge controlers of the same id will automatically establish and destroy air bridges between each other if told to.
//air bridges have a width of 3 not including the walls.
//dont create more than 2 controlers with the same id or stuff will break. And itll be your fault.
//Also, make sure the bridges can extend in a straight line. Or you're gonna have a really bad time
var/global/list/airbridge_controllers = list()
/* -------------------- Controller -------------------- */
/obj/airbridge_controler
name = "Airbridge Controller"
desc = "This is an invisible thing. Yet you can see it. You notice reality unraveling around you."
icon = 'icons/misc/mark.dmi'
icon_state = "airbr"
invisibility = 99
anchored = 1
density = 0
var/tunnel_width = 1
var/id = "noodles"
var/working = 0
var/maintaining_bridge = 0
var/obj/airbridge_controler/linked = null
var/list/path = new/list()
var/list/maintaining_turfs = new/list()
var/primary_controller = 0 // if 1, the bridge extends from this controller to the other one when toggled by an airbridge computer
// ONLY SET ONE CONTROLLER TO 1 OR IT'S TOTALLY POINTLESS
New()
airbridge_controllers += src
..()
proc/get_link()
for(var/obj/airbridge_controler/C in world)
if(C.z == src.z && C.id == src.id && C != src)
linked = C
break
proc/toggle_bridge()
if(linked == null) get_link()
if(linked == null) return
if(linked.maintaining_bridge)
return linked.remove_bridge()
else if(maintaining_bridge)
return linked.remove_bridge()
else
return establish_bridge()
proc/pressurize()
if(linked == null) get_link()
if(linked == null) return
if(linked.working || working) return
if(!linked.maintaining_bridge && !maintaining_bridge) return
if(!maintaining_turfs.len) return
working = 1
spawn(0)
sleep(50)
for(var/turf/simulated/T in maintaining_turfs)
if(!T.air && T.density)
continue
T.air.toxins = 0
T.air.toxins_archived = null
T.air.oxygen = MOLES_O2STANDARD
T.air.oxygen_archived = null
T.air.carbon_dioxide = 0
T.air.carbon_dioxide_archived = null
T.air.nitrogen = MOLES_N2STANDARD
T.air.nitrogen_archived = null
T.air.fuel_burnt = 0
T.air.trace_gases = null
T.air.temperature = T20C
T.air.temperature_archived = null
sleep(-1)
working = 0
return
proc/get_state_string()
if(linked == null) get_link()
if(linked == null) return "ERROR: Connection to secondary Airbridge controller lost."
if(linked.working || working) return "Airbridge controller working. Please wait."
if(linked.maintaining_bridge || maintaining_bridge) return "Airbridge established."
if(!linked.maintaining_bridge && !maintaining_bridge) return "No active Airbridge."
return "Unknown State."
proc/is_working()
if(linked == null) get_link()
if(linked == null) return 0
if(linked.working || working) return 1
else return 0
proc/establish_bridge()
if(linked == null) get_link()
if(linked == null) return
if(linked.working || working) return
if(linked.maintaining_bridge || maintaining_bridge) return
working = 1
maintaining_bridge = 1
spawn(0)
path.Cut()
var/turf/current = src.loc
path.Add(current)
var/direction = get_dir(current, get_step(current,get_dir(current, linked.loc)))
path[current] = direction
while(current != linked.loc)
var/previous = current
current = get_step(current,get_dir(current, linked.loc))
path.Add(current)
direction = get_dir(previous,current)
path[current] = direction
for(var/turf/T in path)
var/list/added = list()
var/turf/curr = new/turf/simulated/shuttle/floor { RL_Ignore = 1 } (T)
maintaining_turfs.Add(curr)
added.Add(curr)
for(var/i = 1, i <= tunnel_width, i++)
if(i == tunnel_width)
curr = new/turf/simulated/shuttle/wall/destroyable { RL_Ignore = 1 } ( get_steps(T, turn(path[T], 90),i) )
maintaining_turfs.Add(curr)
added.Add(curr)
curr = new/turf/simulated/shuttle/wall/destroyable { RL_Ignore = 1 } ( get_steps(T, turn(path[T], -90),i) )
maintaining_turfs.Add(curr)
added.Add(curr)
else
curr = new/turf/simulated/shuttle/floor { RL_Ignore = 1 } ( get_steps(T, turn(path[T], 90),i) )
maintaining_turfs.Add(curr)
added.Add(curr)
curr = new/turf/simulated/shuttle/floor { RL_Ignore = 1 } ( get_steps(T, turn(path[T], -90),i) )
maintaining_turfs.Add(curr)
added.Add(curr)
//Please don't look at the following stuff or you might forget how to code properly.
if(path.Find(T) != path.len)
for(var/turf/A in added)
var/obj/shuttledummy/D = null
if(A.density)
D = new/obj/shuttledummy/wall(A)
else
D = new/obj/shuttledummy/floor(A)
if(added.Find(A) == added.len)
if(D.slide(path[T]))
D.layer = 3 // TODO LAYER
spawn(20) qdel(D)
else
spawn(0)
if(D && D.slide(path[T]))
D.layer = 3 // TODO LAYER
spawn(20) qdel(D)
playsound(T, "sound/effects/airbridge_dpl.ogg", 50, 1)
sleep(1)
working = 0
return
proc/remove_bridge()
if(linked == null) get_link()
if(linked == null) return
if(linked.working || working) return
if(!linked.maintaining_bridge && !maintaining_bridge) return
if(!maintaining_bridge && linked.maintaining_bridge)
linked.remove_bridge()
return
working = 1
maintaining_bridge = 0
playsound(src.loc, "sound/machines/warning-buzzer.ogg", 50, 1)
spawn(20)
var/list/path_reverse = reverse_list(path)
for(var/turf/T in path_reverse)
maintaining_turfs.Add(new/turf/space(T))
harmless_smoke_puff(T)
for(var/i = 1, i <= tunnel_width, i++)
maintaining_turfs.Add(new/turf/space( get_steps(T, turn(path[T], 90),i) ) )
//new/obj/effects/harmless_smoke(get_steps(T, turn(path[T], 90),i))
maintaining_turfs.Add(new/turf/space( get_steps(T, turn(path[T], -90),i) ) )
//new/obj/effects/harmless_smoke(get_steps(T, turn(path[T], -90),i))
playsound(T, "sound/effects/airbridge_dpl.ogg", 50, 1)
sleep(7)
maintaining_turfs.Cut()
working = 0
return
/* -------------------- Computer -------------------- */
/obj/machinery/computer/airbr
name = "Airbridge Computer"
desc = "Used to control the airbridge."
var/id = "noodles"
icon_state = "airbr0"
// set this var to 1 in the map editor if you want the airbridge to establish and pressurize when the round starts
// only do it to ONE of the computers for the airbridge ID or they will both try to do it and get confused
var/starts_established = 0
var/working = 0
var/state_str = ""
req_access = list(access_heads)
var/list/links = list()
var/obj/airbridge_controler/primary_controller = null
var/emergency = 0 // 1 to automatically extend when the emergency shuttle docks
New()
..()
if (src.emergency && emergency_shuttle) // emergency_shuttle is the controller datum
emergency_shuttle.airbridges += src
proc/get_links()
if (!airbridge_controllers.len)
return
for (var/obj/airbridge_controler/C in airbridge_controllers)//world)
if (C.id == src.id)
links.Add(C)
if (C.primary_controller)
src.primary_controller = C
process()
..()
update_status()
if (starts_established && links.len)
spawn(10)
do_initial_extend()
return
proc/pick_controller()
if (istype(src.primary_controller))
return src.primary_controller
var/obj/airbridge_controler/C = pick(links)
if (istype(C))
return C
proc/do_initial_extend()
var/obj/airbridge_controler/C = src.pick_controller()
if (!istype(C))
return
C.establish_bridge()
var/sanity_counter = 0
while (C.working && sanity_counter < 30)
sanity_counter++
sleep(20)
C.pressurize()
starts_established = 0
proc/update_status()
if (!links.len)
get_links()
if (!links.len)
working = 0
starts_established = 0
state_str = "ERROR: No controlers found."
return
var/obj/airbridge_controler/C = src.pick_controller()
if (!istype(C))
return
working = C.is_working()
icon_state = "airbr[working]"
state_str = C.get_state_string()
attack_hand(var/mob/user as mob)
if (..(user))
return
update_status()
var/dat = ""
dat += "<b>Controller Status:</b><BR>"
dat += "[state_str]<BR>"
dat += "[working ? "Working..." : "Idle..."]<BR><BR>"
dat += "<b>Airbridge Control:</b><BR>"
dat += "<A href='?src=\ref[src];create=1'>Establish</A><BR>"
dat += "<A href='?src=\ref[src];remove=1'>Retract</A><BR>"
dat += "<A href='?src=\ref[src];air=1'>Pressurize</A><BR>"
user.machine = src
user << browse("<TITLE>Airbridge Computer</TITLE><BR>[dat]", "window=t_computer;size=400x300")
onclose(user, "airbr_computer")
return
proc/ensure_links()
if (!src.links.len)
src.get_links()
if (!src.links.len)
src.working = 0
src.state_str = "ERROR: No controllers found."
return 0
else
return 1
proc/establish_bridge()
if (!src.ensure_links())
return 0
var/obj/airbridge_controler/C = src.pick_controller()
if (istype(C))
C.establish_bridge()
return 1
proc/remove_bridge()
if (!src.ensure_links())
return 0
var/obj/airbridge_controler/C = src.pick_controller()
if (istype(C))
C.remove_bridge()
return 1
proc/pressurize()
if (!src.ensure_links())
return 0
var/obj/airbridge_controler/C = src.pick_controller()
if (istype(C))
C.pressurize()
return 1
Topic(href, href_list)
if (..(href, href_list))
return
if (href_list["create"])
if (src.emergency && emergency_shuttle)
if (emergency_shuttle.location != SHUTTLE_LOC_STATION)
boutput(usr, "<span style=\"color:red\">The airbridge cannot be deployed while the shuttle is not in position.</span>")
return
if (!(src.allowed(usr, req_only_one_required)))
boutput(usr, "<span style=\"color:red\">Access denied.</span>")
return
if (src.establish_bridge())
logTheThing("station", usr, null, "extended the airbridge at [usr.loc.loc] ([showCoords(usr.x, usr.y, usr.z)])")
else if (href_list["remove"])
if (!(src.allowed(usr, req_only_one_required)))
boutput(usr, "<span style=\"color:red\">Access denied.</span>")
return
if (src.remove_bridge())
logTheThing("station", usr, null, "retracted the airbridge at [usr.loc.loc] ([showCoords(usr.x, usr.y, usr.z)])")
else if (href_list["air"])
if (!(src.allowed(usr, req_only_one_required)))
boutput(usr, "<span style=\"color:red\">Access denied.</span>")
return
if (src.pressurize())
logTheThing("station", usr, null, "pressurized the airbridge at [usr.loc.loc] ([showCoords(usr.x, usr.y, usr.z)])")
update_status()
usr << browse(null, "window=airbr_computer")
//src.updateUsrDialog()
src.updateDialog()
return
power_change()
if(stat & BROKEN)
icon_state = "airbrbr"
light.disable()
else if(powered())
icon_state = "airbr0"
stat &= ~NOPOWER
light.enable()
else
spawn(rand(0, 15))
icon_state = "airbroff"
stat |= NOPOWER
light.disable()
set_broken()
if (stat & BROKEN) return
var/datum/effects/system/harmless_smoke_spread/smoke = new /datum/effects/system/harmless_smoke_spread()
smoke.set_up(5, 0, src)
smoke.start()
icon_state = initial(icon_state)
icon_state = "airbrbr"
light.disable()
stat |= BROKEN
/obj/machinery/computer/airbr/emergency_shuttle
icon = 'icons/obj/airtunnel.dmi'
emergency = 1
/* -------------------- Button -------------------- */
/obj/machinery/airbr_test_button
name = "Airbridge Button"
icon = 'icons/obj/objects.dmi'
icon_state = "launcherbtt"
desc = ""
var/id = "noodles"
var/state = 0
anchored = 1.0
attack_hand(mob/user as mob)
for(var/obj/airbridge_controler/C in range(3, src))
boutput(usr, "<span style=\"color:blue\">[C.toggle_bridge()]</span>")
break
return
/* -------------------- Dummy Turfs -------------------- */
/obj/shuttledummy
desc = ""
density = 0
opacity = 1
anchored = 1
layer = FLOOR_EQUIP_LAYER1
proc/slide(var/direction)
switch(direction)
if(NORTH)
while(pixel_y < 32)
pixel_y += 4
sleep(1)
return 1
if(SOUTH)
while(pixel_y > -32)
pixel_y -= 4
sleep(1)
return 1
if(EAST)
while(pixel_x < 32)
pixel_x += 4
sleep(1)
return 1
if(WEST)
while(pixel_x > -32)
pixel_x -= 4
sleep(1)
return 1
return 0
/obj/shuttledummy/wall
name = "wall"
icon = 'icons/turf/shuttle.dmi'
icon_state = "wall"
density = 1
opacity = 1
/obj/shuttledummy/floor
name = "floor"
icon = 'icons/turf/shuttle.dmi'
icon_state = "floor"
density = 1
opacity = 0
+29
View File
@@ -0,0 +1,29 @@
/obj/alien
name = "alien thing"
desc = "theres something alien about this"
icon = 'alien.dmi'
/obj/alien/head
name = "severed head"
desc = "a severed head..."
icon_state = "weeds"
density = 0
anchored = 0
/obj/alien/skin_suit
name = "skin"
desc = "a persons skin, disgusting"
icon_state = "weeds"
density = 0
anchored = 0
/obj/alien/resin
name = "resin"
desc = "Looks like some kind of slimy growth."
icon_state = "resin"
density = 0
opacity = 0
anchored = 1
+62
View File
@@ -0,0 +1,62 @@
/*
Better way to do this might be to make it a verb on a person and to cocoon the person in some kind of resin
If they're next to a wall this would change their pixel and attach them to the wall, otherwise it'd cause
Them to lie down and attach them to the floor, this could be easily done by changing the bed code.
This would mean having a variable affected_mob or something that we could keep the person stunned/alive while
they're trapped
*/
/obj/alien/cocoon
name = "cocoon"
desc = "a strange... something..."
density = 1.0
anchored = 1.0
icon = 'icons/obj/objects.dmi'
icon_state = "toilet"
var/health = 10
MouseDrop_T(mob/M as mob, mob/user as mob)
if (!ticker)
boutput(user, "You can't buckle anyone in before the game starts.")
return
if ((!( istype(M, /mob) ) || get_dist(src, user) > 1 || user.restrained() || usr.stat))
return
for(var/mob/O in viewers(user, null))
if ((O.client && !( O.blinded )))
boutput(O, text("<span style=\"color:blue\">[M] is absorbed by the cocoon!</span>"))
M.anchored = 1
M.buckled = src
M.set_loc(src.loc)
src.add_fingerprint(user)
return
attack_hand(mob/user as mob)
if(health <= 0)
for(var/mob/M in src.loc)
if (M.buckled)
src.visible_message("<span style=\"color:blue\">[M] appears from the cocoon.</span>")
// boutput(world, "[M] is no longer buckled to [src]")
M.anchored = 0
M.buckled = null
src.add_fingerprint(user)
return
attackby(obj/item/W as obj, mob/user as mob)
if (src.health <= 0)
src.visible_message("<span style=\"color:red\"><B>[user] has destroyed the cocoon.</B></span>")
src.death()
return
switch(W.damtype)
if("fire")
src.health -= W.force * 0.75
if("brute")
src.health -= W.force * 0.1
else
..()
proc/death()
src.icon_state = "egg_destroyed" //need an icon for this
src.density = 0
+38
View File
@@ -0,0 +1,38 @@
/obj/alien/egg
desc = "It looks like a weird egg"
name = "egg"
icon_state = "egg"
layer = MOB_LAYER
density = 1
anchored = 1
var/health = 25
New()
spawn(900)
if(src.health > 0)
src.open()
proc/open()
spawn(10)
src.density = 0
src.icon_state = "egg_hatched"
new /obj/alien/facehugger(src.loc)
attackby(obj/item/W as obj, mob/user as mob)
if (src.health <= 0)
src.visible_message("<span style=\"color:red\"><B>[user] has destroyed the egg!</B></span>")
src.death()
return
switch(W.damtype)
if("fire")
src.health -= W.force * 0.75
if("brute")
src.health -= W.force * 0.1
else
..()
proc/death()
src.icon_state = "egg_destroyed" //need an icon for this
src.density = 0
+385
View File
@@ -0,0 +1,385 @@
#define cycle_pause 5 //min 1
#define viewrange 7 //min 2
// Returns the surrounding cardinal turfs with open links
// Including through doors openable with the ID
// Includes spacetiles
/turf/proc/CardinalTurfsWithAccessSpace(var/obj/item/card/id/ID)
var/L[] = new()
for(var/d in cardinal)
var/turf/simulated/T = get_step(src, d)
if((istype(T) || istype(T,/turf/space))&& !T.density)
if(!LinkBlockedWithAccess(src, T, ID))
L.Add(T)
return L
/obj/alien/facehugger
name = "alien"
desc = "An alien, looks pretty scary!"
icon_state = "facehugger"
layer = MOB_LAYER
density = 1
anchored = 0
var/state = 0
var/list/path = null
var/frustration = 0
var/mob/living/carbon/target
var/list/path_target = null
var/turf/trg_idle
var/list/path_idle = null
var/alive = 1 //1 alive, 0 dead
var/health = 25
var/maxhealth = 25
flags = FPRINT | TABLEPASS
New()
..()
health = maxhealth
src.process()
examine()
set src in view()
..()
if(!alive)
boutput(usr, text("<span style=\"color:red\"><B>the alien is not moving</B></span>"))
else if (src.health > 15)
boutput(usr, text("<span style=\"color:red\"><B>the alien looks fresh, just out of the egg</B></span>"))
else
boutput(usr, text("<span style=\"color:red\"><B>the alien looks pretty beat up</B></span>"))
return
attack_hand(user as mob)
return
attackby(obj/item/W as obj, mob/user as mob)
switch(W.damtype)
if("fire")
src.health -= W.force * 0.75
if("brute")
src.health -= W.force * 0.5
else
if (src.health <= 0)
src.death()
else if (W.force)
if(ishuman(user) || ismonkey(user))
src.target = user
src.state = 1
..()
bullet_act(var/obj/projectile/P)
var/damage = 0
damage = round((P.power*P.ks_ratio), 1.0)
if((P.damage_type == D_KINETIC)||(P.damage_type == D_SLASHING))
src.health -= (damage*2)
else if(P.damage_type == D_PIERCING)
src.health -= damage
else if(P.damage_type == D_ENERGY)
src.health -= damage
else if(P.damage_type == D_BURNING)
src.health -= damage
else if(P.damage_type == D_RADIOACTIVE)
src.health -= damage
else if(P.damage_type == D_TOXIC)
src.health += damage
healthcheck()
ex_act(severity)
switch(severity)
if(1.0)
src.death()
if(2.0)
src.health -= 15
healthcheck()
return
meteorhit()
src.death()
return
blob_act(var/power)
if(prob(25))
src.death()
return
Bumped(AM as mob|obj)
if(ismob(AM) && (ishuman(AM) || ismonkey(AM)) )
src.target = AM
set_attack()
else if(ismob(AM))
spawn(0)
var/turf/T = get_turf(src)
AM:set_loc(T)
Bump(atom/A)
if(ismob(A) && (ishuman(A) || ismonkey(A)))
src.target = A
set_attack()
else if(ismob(A))
src.set_loc(A:loc)
/*
verb/follow()
set src in view()
set name = "follow me"
if(!alive) return
if(!isalien(usr))
boutput(usr, text("<span style=\"color:red\"><B>The alien ignores you.</B></span>"))
return
if(state != 2 || health < maxhealth)
boutput(usr, text("<span style=\"color:red\"><B>The alien is too busy to follow you.</B></span>"))
return
boutput(usr, text("<span style=\"color:green\"><B>The alien will now try to follow you.</B></span>"))
trg_idle = usr
path_idle = new/list()
return
verb/stop()
set src in view()
set name = "stop following"
if(!alive) return
if(!isalien(usr))
boutput(usr, text("<span style=\"color:red\"><B>The alien ignores you.</B></span>"))
return
if(state != 2)
boutput(usr, text("<span style=\"color:red\"><B>The alien is too busy to follow you.</B></span>"))
return
boutput(usr, text("<span style=\"color:green\"><B>The alien stops following you.</B></span>"))
set_null()
return
*/
proc/call_to(var/mob/user)
if(!alive || !isalien(user) || state != 2) return
trg_idle = user
path_idle = null
return
proc/set_attack()
state = 1
path_idle = null
trg_idle = null
proc/set_idle()
state = 2
path_target = null
target = null
frustration = 0
proc/set_null()
state = 0
path_target = null
path_idle = null
target = null
trg_idle = null
frustration = 0
proc/process()
var/quick_move = 0
if (!alive)
return
if (!target)
path_target = null
var/last_health = INFINITY
for (var/mob/living/carbon/C in range(viewrange-2,src.loc))
if (isalien(C) || C.alien_egg_flag || !can_see(src,C,viewrange))
continue
if(C:stunned || C:paralysis || C:weakened)
target = C
break
if(C:health < last_health)
last_health = C:health
target = C
if(target)
set_attack()
else if(state != 2)
set_idle()
idle()
else if(target)
var/turf/distance = get_dist(src, target)
set_attack()
if(can_see(src,target,viewrange))
// This doesn't work, it only returns whenever a human is lying down on a tile
// TO-DO think of a way to make it so they can't go through windows
//var/turf/trg_turf = get_turf(target)
if(distance <= 1) //&& trg_turf.Enter(src))
for(var/mob/O in AIviewers(world.view,src))
O.show_message("<span style=\"color:red\"><B>[src.target] has been leapt on by the alien!</B></span>", 1, "<span style=\"color:red\">You hear someone fall</span>", 2)
random_brute_damage(target, 10)
target:paralysis = max(target:paralysis, 10)
src.set_loc(target.loc)
if(!target.alien_egg_flag && ( ishuman(target) || ismonkey(target) ) )
target.alien_egg_flag = 1
var/mob/trg = target
src.death()
trg.contract_disease(new /datum/ailment/parasite/alien_embryo, 1)
return
else
set_null()
spawn(cycle_pause) src.process()
return
step_towards(src,get_step_towards2(src , target))
else
if(!path_target || !path_target.len )
path_attack(target)
if(!path_target)
set_null()
spawn(cycle_pause) src.process()
return
else
var/turf/next = path_target[1]
if(next in range(1,src))
path_attack(target)
if(!path_target || !path_target.len)
src.frustration += 5
else
next = path_target[1]
path_target -= next
step_towards(src,next)
quick_move = 1
if (get_dist(src, src.target) >= distance) src.frustration++
else src.frustration--
if(frustration >= 35) set_null()
if(quick_move)
spawn(1)
src.process()
else
spawn(cycle_pause)
src.process()
proc/idle()
var/quick_move = 0
if(state != 2 || !alive || target) return
if(locate(/obj/alien/weeds) in src.loc && health < maxhealth)
health++
spawn(cycle_pause) idle()
return
if(!path_idle || !path_idle.len)
if(isalien(trg_idle))
if(can_see(src,trg_idle,viewrange))
step_towards(src,get_step_towards2(src , trg_idle))
else
path_idle(trg_idle)
if(!path_idle)
trg_idle = null
set_idle()
spawn(cycle_pause) src.idle()
return
else
var/obj/alien/weeds/W = null
if(health < maxhealth)
var/list/the_weeds = new/list()
find_weeds:
for(var/obj/alien/weeds/weed in range(viewrange,src.loc))
if(!can_see(src,weed,viewrange)) continue
for(var/atom/A in get_turf(weed))
if(A.density) continue find_weeds
the_weeds += weed
W = pick(the_weeds)
if(W)
path_idle(W)
if(!path_idle)
trg_idle = null
spawn(cycle_pause) src.idle()
return
else
for(var/mob/living/carbon/alien/humanoid/H in range(1,src))
spawn(cycle_pause) src.idle()
return
step(src,pick(cardinal))
else
if(can_see(src,trg_idle,viewrange))
switch(get_dist(src, trg_idle))
if(1)
if(istype(trg_idle,/obj/alien/weeds))
step_towards(src,get_step_towards2(src , trg_idle))
if(2 to INFINITY)
step_towards(src,get_step_towards2(src , trg_idle))
path_idle = null
/*
if(viewrange+1 to INFINITY)
step_towards(src,get_step_towards2(src , trg_idle))
if(path_idle.len) path_idle = new/list()
quick_move = 1
*/
else
var/turf/next = path_idle[1]
if(!next in range(1,src))
path_idle(trg_idle)
if(!path_idle)
spawn(cycle_pause) src.idle()
return
else
next = path_idle[1]
path_idle -= next
step_towards(src,next)
quick_move = 1
if(quick_move)
spawn(1)
idle()
else
spawn(cycle_pause)
idle()
proc/path_idle(var/atom/trg)
path_idle = AStar(src.loc, get_turf(trg), /turf/proc/CardinalTurfsWithAccess, /turf/proc/Distance)
proc/path_attack(var/atom/trg)
target = trg
path_target = AStar(src.loc, target.loc, /turf/proc/CardinalTurfsWithAccess, /turf/proc/Distance)
proc/death()
if(!alive) return
src.alive = 0
density = 0
icon_state = "facehugger_l"
set_null()
for(var/mob/O in hearers(src, null))
O.show_message("<span style=\"color:red\"><B>[src] curls up into a ball!</B></span>", 1)
proc/healthcheck()
if (src.health <= 0)
src.death()
+80
View File
@@ -0,0 +1,80 @@
/obj/alien/weeds
name = "weeds"
desc = "weird purple weeds"
icon_state = "weeds"
layer = TURF_LAYER
anchored = 1
density = 0
New()
if(istype(src.loc, /turf/space))
qdel(src)
return
attackby(obj/item/W as obj, mob/user as mob)
if (!W) return
if (!user) return
if (istype(W, /obj/item/axe)) qdel(src)
else if (istype(W, /obj/item/circular_saw)) qdel(src)
else if (istype(W, /obj/item/kitchen/utensil/knife)) qdel(src)
else if (istype(W, /obj/item/scalpel)) qdel(src)
else if (istype(W, /obj/item/screwdriver))(qdel src)
else if (istype(W, /obj/item/shard)) qdel(src)
else if (istype(W, /obj/item/sword)) qdel(src)
else if (istype(W, /obj/item/saw)) qdel(src)
else if (istype(W, /obj/item/weldingtool)) qdel(src)
else if (istype(W, /obj/item/wirecutters)) qdel(src)
..()
proc/Life()
var/count = 0
while(count < 6)
if (!src) return
var/Vspread
if (prob(50)) Vspread = locate(src.x + rand(-1,1),src.y,src.z)
else Vspread = locate(src.x,src.y + rand(-1, 1),src.z)
var/dogrowth = 1
if (!istype(Vspread, /turf/simulated/floor)) dogrowth = 0
for(var/obj/O in Vspread)
if (istype(O, /obj/window) || istype(O, /obj/forcefield) || istype(O, /obj/blob) || istype(O, /obj/spacevine) || istype(O, /obj/alien/weeds)) dogrowth = 0
if (istype(O, /obj/machinery/door/))
if(!O:p_open && prob(70))
O:open()
O:operating = -1
else dogrowth = 0
if (dogrowth == 1)
var/obj/alien/weeds/B = new /obj/alien/weeds(Vspread)
spawn(50)
if(B)
B.Life()
count++
sleep(50)
ex_act(severity)
switch(severity)
if(1.0)
qdel(src)
return
if(2.0)
if (prob(50))
qdel(src)
return
if(3.0)
if (prob(5))
qdel(src)
return
else
return
/*
/obj/alien/weeds/burn(fi_amount)
if (fi_amount > 18000)
spawn( 0 )
qdel(src)
return
return 0
return 1
*/
@@ -0,0 +1,24 @@
/obj/item/artifact/activator_key
// can activate any artifact simply by smacking it. very very rare
name = "artifact activator key"
associated_datum = /datum/artifact/activator_key
var/universal = 1 // normally it only activates its own type, but sometimes it can do all
var/activator = 1 // can also be a DEactivator key sometimes!
module_research_no_diminish = 1
New(var/loc, var/forceartitype)
..()
/*if (prob(10))
src.universal = 1
if (prob(10))
src.activator = 0*/
/datum/artifact/activator_key
associated_object = /obj/item/artifact/activator_key
rarity_class = 4
validtypes = list("ancient","martian","wizard","eldritch","precursor")
automatic_activation = 1
react_xray = list(12,80,95,8,"COMPLEX")
examine_hint = "It kinda looks like it's supposed to be inserted into something."
module_research = list("tools" = 20)
module_research_insight = 5
@@ -0,0 +1,130 @@
/obj/item/artifact/attack_wand
name = "artifact attack wand"
associated_datum = /datum/artifact/attack_wand
flags = FPRINT | CONDUCT | EXTRADELAY
module_research_no_diminish = 1
afterattack(atom/target as mob|obj|turf|area, mob/user as mob, flag)
if (user.equipped() == src)
if (!src.ArtifactSanityCheck())
return
var/datum/artifact/attack_wand/A = src.artifact
if (!istype(A))
return
if (!A.activated)
return
var/turf/U = (istype(target, /atom/movable) ? target.loc : target)
A.effect_click_tile(src,user,U)
src.ArtifactFaultUsed(user)
/datum/artifact/attack_wand
associated_object = /obj/item/artifact/attack_wand
rarity_class = 3
validtypes = list("wizard")
validtriggers = list(/datum/artifact_trigger/force,/datum/artifact_trigger/electric,/datum/artifact_trigger/heat,
/datum/artifact_trigger/radiation,/datum/artifact_trigger/force)
react_xray = list(8,80,60,11,"COMPLEX")
examine_hint = "It seems to have a handle you're supposed to hold it by."
var/ready = 1
var/cooldown = 180
var/attack_type = null
var/recharge_phrase = ""
var/error_phrase = ""
module_research = list("weapons" = 5, "energy" = 5, "tools" = 5)
module_research_insight = 2
New()
..()
recharge_phrase = pick("crackles with static.","emits a quiet tone.","bristles with energy!","heats up.")
error_phrase = pick("shudders briefly.","grows heavy for a moment.","emits a quiet buzz.","makes a small pop sound.")
attack_type = pick("lightning","fire","ice","sonic")
cooldown = rand(25,900)
if (prob(5))
cooldown = 0
effect_click_tile(var/obj/O,var/mob/living/user,var/turf/T)
if (..())
return
if (!ready)
return
ready = 0
spawn(cooldown)
if (O.loc == user)
boutput(user, "<b>[O]</b> [recharge_phrase]")
ready = 1
switch(attack_type)
if("fire")
playsound(T, "sound/effects/bamf.ogg", 50, 1, 0)
fireflash(T, 2)
ArtifactLogs(user, T, O, "used", "creating fireball on target turf", 0) // Attack wands need special log handling (Convair880).
if("ice")
playsound(T, "sound/effects/mag_iceburstlaunch.ogg", 50, 1, 0)
for (var/turf/TT in range(T,2))
if(locate(/obj/decal/icefloor) in TT.contents)
continue
var/obj/decal/icefloor/B = new /obj/decal/icefloor(TT)
spawn(800)
B.dispose()
for (var/mob/living/M in range(T,2))
if (M.bioHolder)
if (!M.is_cold_resistant())
new /obj/icecube(get_turf(M), M)
ArtifactLogs(user, M, O, "weapon", "trapping them in an ice cube", 0)
if("lightning")
var/attack_amt = 0
for (var/mob/living/M in range(T,1))
ArtifactLogs(user, M, O, "weapon", "zapping them with electricity", 0)
attack_amt = 1
var/list/affected = DrawLine(M, user, /obj/line_obj/elec ,'icons/obj/projectiles.dmi',"WholeLghtn",1,1,"HalfStartLghtn","HalfEndLghtn",OBJ_LAYER,1,PreloadedIcon='icons/effects/LghtLine.dmi')
for(var/obj/OB in affected)
spawn(6)
pool(OB)
M.TakeDamage("chest", 0, 25)
M.stunned += 5
if (attack_amt)
playsound(user, "sound/effects/elec_bigzap.ogg", 40, 1)
else
boutput(user, "<span style=\"color:red\"><b>[O]</b> crackles with electricity for a moment. Perhaps it couldn't find a target?</span>")
if("sonic")
playsound(T, "sound/effects/screech.ogg", 100, 1, 0)
particleMaster.SpawnSystem(new /datum/particleSystem/sonic_burst(T))
for (var/mob/living/M in all_hearers(world.view, T))
if (isintangible(M))
continue
if (!M.ears_protected_from_sound())
shake_camera(M, 10, 0)
else
continue
ArtifactLogs(user, M, O, "weapon", "inflicting ear damage", 0)
// Here used to be a C&P of what sonic powder does anyway (Convair880).
var/datum/reagents/R = O.reagents
if (!R || !istype(R))
R = new /datum/reagents(15)
O.reagents = R
R.my_atom = O
else if (R && istype(R) && R.my_atom != O)
R.my_atom = O
R.clear_reagents()
if (R.maximum_volume < 15)
R.maximum_volume = 15
R.add_reagent("sonicpowder_nofluff", 15, null, T0C + 200)
R.temperature_react()
if (R.total_volume)
R.clear_reagents()
return
@@ -0,0 +1,109 @@
/obj/item/gun/energy/artifact
// an energy gun, it shoots things as you might expect
name = "artifact energy gun"
icon = 'icons/obj/artifacts/artifactsitem.dmi'
icon_state = "laser"
force = 5.0
artifact = 1
is_syndicate = 1
module_research_no_diminish = 1
mat_changename = 0
mat_changedesc = 0
New(var/loc, var/forceartitype)
var/datum/artifact/energygun/AS = new /datum/artifact/energygun(src)
if (forceartitype)
AS.validtypes = list("[forceartitype]")
src.artifact = AS
// The other three are normal for energy gun setup, so proceed as usual i guess
cell = null
spawn(0)
src.ArtifactSetup()
var/datum/artifact/A = src.artifact
cell = new/obj/item/ammo/power_cell/self_charging/artifact(src,A.artitype)
src.ArtifactDevelopFault(15)
current_projectile = AS.bullet
projectiles = list(src.current_projectile)
cell.max_charge = max(cell.max_charge, current_projectile.cost)
examine()
set src in oview()
boutput(usr, "You have no idea what this thing is!")
if (!src.ArtifactSanityCheck())
return
var/datum/artifact/A = src.artifact
if (istext(A.examine_hint))
boutput(usr, "[A.examine_hint]")
UpdateName()
src.name = "[name_prefix(null, 1)][src.real_name][name_suffix(null, 1)]"
attackby(obj/item/W as obj, mob/user as mob)
if (src.Artifact_attackby(W,user))
..()
process_ammo(var/mob/user)
if(istype(user,/mob/living/silicon/robot))
var/mob/living/silicon/robot/R = user
if(R.cell)
if(R.cell.charge >= src.robocharge)
R.cell.charge -= src.robocharge
return 1
return 0
else
if(src.current_projectile)
if(src.cell)
if(src.cell.use(src.current_projectile.cost))
return 1
return 0
shoot(var/target,var/start,var/mob/user)
if (!src.ArtifactSanityCheck())
return
var/datum/artifact/energygun/A = src.artifact
if (!istype(A))
return
if (!A.activated)
return
..()
A.ReduceHealth(src)
src.ArtifactFaultUsed(user)
return
/datum/artifact/energygun
associated_object = /obj/item/gun/energy/artifact
rarity_class = 2
validtypes = list("ancient","eldritch","precursor")
react_elec = list(0.02,0,5)
react_xray = list(10,75,100,11,"CAVITY")
var/integrity = 100
var/integrity_loss = 5
var/datum/projectile/artifact/bullet = null
examine_hint = "It seems to have a handle you're supposed to hold it by."
module_research = list("weapons" = 8, "energy" = 8)
module_research_insight = 3
New()
..()
bullet = new/datum/projectile/artifact
bullet.randomise()
integrity = rand(50, 100)
integrity_loss = rand(1, 7)
react_xray[3] = integrity
proc/ReduceHealth(var/obj/item/gun/energy/artifact/O)
var/prev_health = integrity
integrity -= integrity_loss
if (integrity <= 20 && prev_health > 20)
O.visible_message("<span style=\"color:red\">[O] emits a terrible cracking noise.</span>")
if (integrity <= 0)
O.visible_message("<span style=\"color:red\">[O] crumbles into nothingness.</span>")
qdel(O)
react_xray[3] = integrity
@@ -0,0 +1,56 @@
/obj/item/ammo/power_cell/self_charging/artifact
name = "artifact energy gun power cell"
icon = 'icons/obj/artifacts/artifactsitemS.dmi'
artifact = 1
charge = 400.0
max_charge = 400.0
recharge_rate = 0.0
module_research_no_diminish = 1
mat_changename = 0
mat_changedesc = 0
New(var/loc, var/forceartitype)
//src.artifact = new /datum/artifact/energyammo(src)
var/datum/artifact/energyammo/A = new /datum/artifact/energyammo(src)
if (forceartitype)
A.validtypes = list("[forceartitype]")
src.artifact = A
spawn(0)
src.ArtifactSetup()
src.max_charge = rand(5,100)
src.max_charge *= 10
A.react_elec[2] = src.max_charge
src.recharge_rate = rand(5,60)
..()
examine()
set src in oview()
boutput(usr, "You have no idea what this thing is!")
if (!src.ArtifactSanityCheck())
return
var/datum/artifact/A = src.artifact
if (istext(A.examine_hint))
boutput(usr, "[A.examine_hint]")
UpdateName()
src.name = "[name_prefix(null, 1)][src.real_name][name_suffix(null, 1)]"
attackby(obj/item/W as obj, mob/user as mob)
if (src.Artifact_attackby(W,user))
..()
/datum/artifact/energyammo
associated_object = /obj/item/ammo/power_cell/self_charging/artifact
rarity_class = 0
validtypes = list("ancient","eldritch","precursor")
automatic_activation = 1
react_elec = list("equal",0,0)
react_xray = list(8,80,95,11,"SEGMENTED")
examine_hint = "It kinda looks like it's supposed to be inserted into something."
module_research = list("energy" = 15, "weapons" = 1, "miniaturization" = 15)
module_research_insight = 1
New()
..()
src.react_heat[2] = "VOLATILE REACTION DETECTED"
@@ -0,0 +1,74 @@
/obj/item/artifact/melee_weapon
name = "artifact melee weapon"
artifact = 1
associated_datum = /datum/artifact/melee
module_research_no_diminish = 1
attack(mob/M as mob, mob/user as mob)
if (!src.ArtifactSanityCheck())
return
var/datum/artifact/A = src.artifact
if (A.activated)
A.effect_melee_attack(src,user,M)
src.ArtifactFaultUsed(user)
src.ArtifactFaultUsed(M)
else
..()
/datum/artifact/melee
associated_object = /obj/item/artifact/melee_weapon
rarity_class = 2
validtypes = list("ancient","martian","wizard","eldritch","precursor")
react_xray = list(14,95,95,7,"DENSE")
var/damtype = "brute"
var/dmg_amount = 5
var/stun_time = 0
var/KO_time = 0
var/deadly = 0
var/sound/hitsound = null
examine_hint = "It seems to have a handle you're supposed to hold it by."
module_research = list("weapons" = 8, "miniaturization" = 8)
module_research_insight = 1
New()
..()
src.damtype = pick("brute", "fire", "toxin")
src.dmg_amount = rand(3,6)
src.dmg_amount *= rand(1,5)
if (prob(5))
src.dmg_amount *= rand(1,5)
if (prob(40))
src.stun_time = rand(3,12)
if (prob(15))
src.KO_time = rand(3,12)
if (prob(1))
src.deadly = 1
src.hitsound = pick('sound/effects/bang.ogg','sound/effects/zhit.ogg','sound/effects/exlow.ogg','sound/effects/mag_magmisimpact.ogg','sound/effects/shieldhit2.ogg',
'sound/effects/snap.ogg','sound/machines/mixer.ogg','sound/misc/meteorimpact.ogg','sound/weapons/ACgun2.ogg','sound/weapons/Egloves.ogg','sound/weapons/flashbang.ogg',
'sound/weapons/grenade.ogg','sound/weapons/railgun.ogg')
effect_melee_attack(var/obj/O,var/mob/living/user,var/mob/living/target)
if (..())
return
if (!istype(user,/mob/living/) || !istype(target,/mob/living/))
return
user.visible_message("<span style=\"color:red\"><b>[user.name]</b> attacks [target.name] with [O]!</span>")
var/turf/T = get_turf(user)
playsound(T, hitsound, 50, 1, -1)
if (src.deadly)
user.visible_message("<span style=\"color:red\"><b>[target] is utterly destroyed!</b></span>")
target.gib()
else
switch(damtype)
if ("brute")
random_brute_damage(target, dmg_amount)
if ("fire")
random_burn_damage(target, dmg_amount)
if ("toxin")
if (ishuman(target))
var/mob/living/carbon/human/H = target
H.toxloss += rand(1, dmg_amount)
if (src.stun_time)
target.stunned = src.stun_time
if (src.KO_time)
target.paralysis = src.KO_time
@@ -0,0 +1,34 @@
/obj/item/artifact/mining_tool
name = "artifact mining tool"
artifact = 1
associated_datum = /datum/artifact/mining
var/dig_power = 1
var/extrahit = 0
var/dig_sound = 'sound/effects/exlow.ogg'
// mining.dm line 373
module_research_no_diminish = 1
New(var/loc, var/forceartitype)
..()
src.dig_power = rand(1,5)
if (prob(33))
src.extrahit = rand(0,4)
src.dig_sound = pick('sound/effects/exlow.ogg','sound/effects/mag_magmisimpact.ogg','sound/effects/shieldhit2.ogg')
examine()
set src in oview()
boutput(usr, "You have no idea what this thing is!")
if (!src.ArtifactSanityCheck())
return
var/datum/artifact/A = src.artifact
if (istext(A.examine_hint))
boutput(usr, "[A.examine_hint]")
/datum/artifact/mining
associated_object = /obj/item/artifact/mining_tool
rarity_class = 1
validtypes = list("ancient","martian","wizard","eldritch","precursor")
react_xray = list(12,80,95,5,"DENSE")
examine_hint = "It seems to have a handle you're supposed to hold it by."
module_research = list("mining" = 10, "engineering" = 5, "miniaturization" = 10)
module_research_insight = 3
@@ -0,0 +1,55 @@
/obj/item/cell/artifact
name = "artifact power cell"
icon = 'icons/obj/artifacts/artifactsitemS.dmi'
maxcharge = 10000
genrate = 50
specialicon = 1
artifact = 1
module_research_no_diminish = 1
mat_changename = 0
mat_changedesc = 0
New(var/loc, var/forceartitype)
//src.artifact = new /datum/artifact/powercell(src)
var/datum/artifact/powercell/AS = new /datum/artifact/powercell(src)
if (forceartitype)
AS.validtypes = list("[forceartitype]")
src.artifact = AS
spawn(0)
src.ArtifactSetup()
var/datum/artifact/A = src.artifact
src.maxcharge = rand(15,1000)
src.maxcharge *= 100
A.react_elec[2] = src.maxcharge
..()
examine()
set src in oview()
boutput(usr, "You have no idea what this thing is!")
if (!src.ArtifactSanityCheck())
return
var/datum/artifact/A = src.artifact
if (istext(A.examine_hint))
boutput(usr, "[A.examine_hint]")
UpdateName()
src.name = "[name_prefix(null, 1)][src.real_name][name_suffix(null, 1)]"
attackby(obj/item/W as obj, mob/user as mob)
if (src.Artifact_attackby(W,user))
..()
/datum/artifact/powercell
associated_object = /obj/item/cell/artifact
rarity_class = 1
validtypes = list("ancient","martian","wizard","precursor")
automatic_activation = 1
react_elec = list("equal",0,10)
react_xray = list(10,80,95,11,"SEGMENTED")
examine_hint = "It kinda looks like it's supposed to be inserted into something."
module_research = list("energy" = 15, "miniaturization" = 20)
module_research_insight = 1
New()
..()
src.react_heat[2] = "VOLATILE REACTION DETECTED"
@@ -0,0 +1,79 @@
/obj/item/artifact/teleport_wand
name = "artifact teleport wand"
artifact = 1
associated_datum = /datum/artifact/telewand
flags = FPRINT | CONDUCT | EXTRADELAY
module_research_no_diminish = 1
afterattack(atom/target as mob|obj|turf|area, mob/user as mob, flag)
if (!src.ArtifactSanityCheck())
return
var/datum/artifact/telewand/A = src.artifact
if (!istype(A))
return
var/turf/U = (istype(target, /atom/movable) ? target.loc : target)
//var/turf/T = get_turf(target)
if (A.activated)
if (A.can_teleport_here(U))
A.effect_click_tile(src,user,U)
else
boutput(user, "<b>[src]</b> [A.error_phrase]")
src.ArtifactFaultUsed(user)
/datum/artifact/telewand
associated_object = /obj/item/artifact/teleport_wand
rarity_class = 3
validtypes = list("wizard","eldritch","precursor")
react_xray = list(10,75,90,11,"ANOMALOUS")
var/sound/wand_sound = 'sound/effects/mag_warp.ogg'
var/on_cooldown = 0
var/cooldown_delay = 0
var/particle_color = "#000000"
var/particle_sprite = ""
var/recharge_phrase = ""
var/error_phrase = ""
examine_hint = "It seems to have a handle you're supposed to hold it by."
module_research = list("energy" = 15, "engineering" = 3, "science" = 8)
module_research_insight = 4
New()
..()
particle_color = copytext(rgb(rand(0,255), rand(0,255), rand(0,255)),1,0)
particle_sprite = pick("8x8circle","8x8ring","8x8triangle","8x8square","8x8bubblegrid")
wand_sound = pick('sound/effects/mag_warp.ogg','sound/effects/mag_teleport.ogg','sound/effects/mag_phase.ogg','sound/effects/teleport.ogg','sound/effects/warp2.ogg','sound/weapons/ACgun2.ogg',
'sound/weapons/laserultra.ogg','sound/weapons/radxbow.ogg','sound/machines/ArtifactWiz1.ogg','sound/machines/ArtifactPre1.ogg','sound/machines/ArtifactAnc1.ogg','sound/machines/engine_alert3.ogg', 'sound/voice/wizard/BlinkLoud.ogg')
recharge_phrase = pick("crackles with static.","emits a quiet tone.","shakes violently!","heats up.")
error_phrase = pick("shudders briefly.","grows heavy for a moment.","emits a quiet buzz.","makes a small pop sound.")
cooldown_delay = rand(1,20) * 10
if (prob(5))
cooldown_delay = 0
effect_click_tile(var/obj/O,var/mob/living/user,var/turf/T)
if (..())
return
if (on_cooldown)
return
on_cooldown = 1
spawn(cooldown_delay)
if (O.loc == user)
boutput(user, "<b>[O]</b> [recharge_phrase]")
on_cooldown = 0
user.set_loc(T)
var/turf/start_loc = get_turf(user)
playsound(start_loc, wand_sound, 50, 1, -1)
particleMaster.SpawnSystem(new /datum/particleSystem/tele_wand(T,particle_sprite,particle_color))
return
proc/can_teleport_here(var/turf/T)
if (!istype(T,/turf/simulated/floor/))
return 0
if (T.density)
return 0
for(var/atom/X in T.contents)
if (X.density)
return 0
return 1
@@ -0,0 +1,66 @@
/obj/item/artifact/forcewall_wand
name = "artifact forcewall wand"
icon = 'icons/obj/artifacts/artifactsitem.dmi'
artifact = 1
associated_datum = /datum/artifact/wallwand
module_research_no_diminish = 1
afterattack(atom/target, mob/user , flag)
if (!src.ArtifactSanityCheck())
return
var/datum/artifact/A = src.artifact
if (A.activated)
var/turf/T = get_turf(target)
A.effect_click_tile(src,user,T)
src.ArtifactFaultUsed(user)
/datum/artifact/wallwand
associated_object = /obj/item/artifact/forcewall_wand
rarity_class = 2
validtypes = list("ancient","wizard","eldritch","precursor")
react_xray = list(10,60,92,11,"COMPLEX")
var/wall_duration = 5
var/wall_size = 1
var/icon_state = "shieldsparkles"
var/sound/wand_sound = 'sound/effects/mag_forcewall.ogg'
examine_hint = "It seems to have a handle you're supposed to hold it by."
module_research = list("energy" = 10, "weapons" = 3, "miniaturization" = 5, "engineering" = 3, "tools" = 3)
module_research_insight = 3
New()
..()
src.wall_duration = rand(3,30)
src.wall_size = rand(1,4)
if(prob(10))
src.wall_size += rand(3,6)
if(prob(5))
src.wall_duration *= rand(2,5)
src.icon_state = pick("shieldsparkles","empdisable","greenglow","enshield","energyorb","forcewall","meteor_shield")
src.wand_sound = pick('sound/effects/mag_forcewall.ogg','sound/effects/mag_golem.ogg','sound/effects/mag_iceburstlaunch.ogg','sound/effects/bamf.ogg','sound/weapons/ACgun2.ogg')
effect_click_tile(var/obj/O,var/mob/living/user,var/turf/T)
if (..())
return
if (!T)
return
var/wallloc
playsound(user.loc, wand_sound, 50, 1, -1)
if (user.dir == NORTH || user.dir == SOUTH)
for(wallloc = T.x - (src.wall_size - 1),wallloc < T.x + src.wall_size,wallloc++)
var/obj/forcefield/wand/FW = new /obj/forcefield/wand(locate(wallloc,T.y,T.z),src.wall_duration,src.icon_state)
FW.icon_state = src.icon_state
else
for(wallloc = T.y - (src.wall_size - 1),wallloc < T.y + src.wall_size,wallloc++)
var/obj/forcefield/wand/FW = new /obj/forcefield/wand(locate(T.x,wallloc,T.z),src.wall_duration,src.icon_state)
FW.icon_state = src.icon_state
/obj/forcefield/wand
name = "force field"
icon = 'icons/effects/effects.dmi'
icon_state = "shieldsparkles"
desc = "Some kind of strange energy barrier. You can't get past it."
New(var/loc,var/duration,var/wallsprite)
icon_state = wallsprite
if (duration > 0)
spawn(duration * 10)
qdel(src)
@@ -0,0 +1,51 @@
/obj/item/reagent_containers/glass/wateringcan/artifact
name = "artifact watering can"
icon = 'icons/obj/artifacts/artifactsitem.dmi'
desc = "You have no idea what this thing is!"
artifact = 1
module_research_no_diminish = 1
mat_changename = 0
mat_changedesc = 0
New(var/loc, var/forceartitype)
..()
var/datum/artifact/watercan/AS = new /datum/artifact/watercan(src)
if (forceartitype)
AS.validtypes = list("[forceartitype]")
src.artifact = AS
spawn(0)
src.ArtifactSetup()
var/capacity = rand(1,20)
capacity *= 1000
var/datum/reagents/R = new/datum/reagents(capacity)
reagents = R
R.my_atom = src
R.add_reagent("water", capacity / 2)
R.add_reagent("saltpetre", capacity / 2)
attackby(obj/item/W as obj, mob/user as mob)
if (src.Artifact_attackby(W,user))
..()
examine()
boutput(usr, "[desc]")
return
UpdateName()
src.name = "[name_prefix(null, 1)][src.real_name][name_suffix(null, 1)]"
/datum/artifact/watercan
associated_object = /obj/item/reagent_containers/glass/wateringcan/artifact
rarity_class = 1
validtypes = list("martian","wizard","precursor")
min_triggers = 0
max_triggers = 0
react_xray = list(2,90,15,11,"HOLLOW")
module_research = list("medicine" = 5, "science" = 5, "miniaturization" = 15)
module_research_insight = 3
New()
..()
src.react_heat[2] = "HIGH INTERNAL CONVECTION"
@@ -0,0 +1,42 @@
/obj/machinery/artifact/gravity_well_generator
name = "artifact gravity well generator"
associated_datum = /datum/artifact/gravity_well_generator
/datum/artifact/gravity_well_generator
associated_object = /obj/machinery/artifact/gravity_well_generator
rarity_class = 2
validtypes = list("wizard","precursor")
validtriggers = list(/datum/artifact_trigger/force,/datum/artifact_trigger/electric,/datum/artifact_trigger/heat,
/datum/artifact_trigger/radiation,/datum/artifact_trigger/carbon_touch)
activated = 0
activ_text = "activates and begins to warp gravity around it!"
deact_text = "shuts down, returning gravity to normal!"
activ_sound = 'sound/effects/mag_warp.ogg'
deact_sound = 'sound/effects/singsuck.ogg'
react_xray = list(20,80,99,0,"ULTRADENSE")
touch_descriptors = list("You seem to have a little difficulty taking your hand off its surface.")
var/field_radius = 7
var/gravity_type = 0 // push or pull?
examine_hint = "It is covered in very conspicuous markings."
New()
..()
src.field_radius = rand(4,9) // well radius
src.gravity_type = rand(0,1) // 0 for pull, 1 for push
effect_process(var/obj/O)
if (..())
return
for (var/obj/V in orange(src.field_radius,O))
if (V.anchored)
continue
if (src.gravity_type)
step_away(V,O)
else
step_towards(V,O)
for (var/mob/living/M in orange(src.field_radius,O))
if (src.gravity_type)
step_away(M,O)
else
step_towards(M,O)
@@ -0,0 +1,42 @@
/obj/machinery/artifact/bio_damage_field_generator
name = "artifact bio damage field generator"
associated_datum = /datum/artifact/bio_damage_field_generator
/datum/artifact/bio_damage_field_generator
associated_object = /obj/machinery/artifact/bio_damage_field_generator
rarity_class = 3
validtypes = list("martian","wizard","eldritch","precursor")
validtriggers = list(/datum/artifact_trigger/force,/datum/artifact_trigger/electric,/datum/artifact_trigger/heat,
/datum/artifact_trigger/radiation,/datum/artifact_trigger/carbon_touch)
activated = 0
activ_text = "begins to radiate a strange energy field!"
deact_text = "shuts down, causing the energy field to vanish!"
react_xray = list(12,70,90,11,"COMPLEX")
var/field_radius = 7
var/field_type = 0 // 0 healing, 1 harming
var/field_strength = 2
New()
..()
src.field_radius = rand(2,9) // field radius
src.field_type = rand(0,1)
src.field_strength = rand(1,5)
var/harmprob = 33
if (src.artitype == "eldritch")
harmprob += 42 // total of 75% chance of it being nasty
if (prob(harmprob))
src.field_type = 1
if (src.field_type && src.artitype == "eldritch")
src.field_strength *= 2
effect_process(var/obj/O)
if (..())
return
for (var/mob/living/carbon/M in range(O,src.field_radius))
if (src.field_type)
random_brute_damage(M, src.field_strength)
boutput(M, "<span style=\"color:red\">Waves of painful energy wrack your body!</span>")
else
M.HealDamage("All", src.field_strength, src.field_strength)
boutput(M, "<span style=\"color:blue\">Waves of soothing energy wash over you!</span>")
@@ -0,0 +1,46 @@
/obj/machinery/artifact/heater
name = "artifact heater"
associated_datum = /datum/artifact/heater
/datum/artifact/heater
associated_object = /obj/machinery/artifact/heater
rarity_class = 2
validtypes = list("ancient","martian","eldritch","precursor")
validtriggers = list(/datum/artifact_trigger/force,/datum/artifact_trigger/electric,/datum/artifact_trigger/heat,
/datum/artifact_trigger/radiation,/datum/artifact_trigger/cold)
activ_text = "begins to radiate air!"
deact_text = "stops pumping out air."
react_xray = list(10,85,80,5,"COMPLEX")
var/heat_target = 310
var/heat_amount = 40000
examine_hint = "It is covered in very conspicuous markings."
post_setup()
heat_target = rand(0,620)
if (artitype == "eldritch" && prob(66))
if (heat_target > 310)
heat_target *= 2
if (heat_target < 310 && heat_target != 0)
heat_target /= 2
heat_amount = rand(20000,60000)
if (heat_target > 310)
activ_text = "begins to radiate hot air!"
deact_text = "stops pumping out hot air."
if (heat_target < 310)
activ_text = "begins to radiate cold air!"
deact_text = "stops pumping out cold air."
effect_process(var/obj/O)
if (..())
return
var/turf/simulated/L = get_turf(O)
if(istype(L))
var/datum/gas_mixture/env = L.return_air()
if(env.temperature < (heat_target+T0C))
var/transfer_moles = 0.25 * env.total_moles()
var/datum/gas_mixture/removed = env.remove(transfer_moles)
if(removed)
var/heat_capacity = removed.heat_capacity()
if(heat_capacity)
removed.temperature = (removed.temperature*heat_capacity + heat_amount)/heat_capacity
env.merge(removed)
@@ -0,0 +1,73 @@
/obj/machinery/artifact/noisy_thing
name = "artifact noisy thing"
associated_datum = /datum/artifact/noisy_thing
ArtifactDeactivated()
return // hahaha nope
/datum/artifact/noisy_thing
associated_object = /obj/machinery/artifact/noisy_thing
rarity_class = 1
validtypes = list("ancient","martian","wizard","eldritch","precursor")
validtriggers = list(/datum/artifact_trigger/force,/datum/artifact_trigger/electric,/datum/artifact_trigger/heat,
/datum/artifact_trigger/radiation,/datum/artifact_trigger/carbon_touch,/datum/artifact_trigger/silicon_touch)
activated = 0
activ_text = "begins making horrible noises!"
deact_text = "shuts down, falling silent. Thank god for that."
react_xray = list(9,50,40,3,"TUBULAR")
var/spamsound = 'sound/effects/screech2.ogg'
var/harmful = 0
var/evil = 0
var/sound_pitch = 1
var/times_to_play = 1
var/list/sounds = list('sound/machines/fortune_greeting_broken.ogg','sound/machines/engine_highpower.ogg','sound/machines/engine_grump1.ogg','sound/machines/engine_alert1.ogg',
'sound/machines/engine_alert2.ogg','sound/machines/engine_alert3.ogg','sound/machines/lavamoon_alarm1.ogg','sound/machines/lavamoon_plantalarm.ogg','sound/machines/pod_alarm.ogg',
'sound/machines/printer_dotmatrix.ogg','sound/machines/printer_thermal.ogg','sound/machines/romhack1.ogg','sound/machines/satcrash.ogg','sound/machines/siren_generalquarters.ogg',
'sound/machines/signal.ogg','sound/machines/ufo_move.ogg','sound/machines/modem.ogg','sound/ambience/ambimo1.ogg','sound/ambience/creaking_metal.ogg','sound/ambience/voidfx2.ogg','sound/ambience/precursorfx2.ogg')
New(var/loc, var/forceartitype)
..()
src.react_heat[2] = "HIGH INTERNAL CONVECTION"
src.spamsound = pick(sounds)
src.sound_pitch = rand(2,20)
src.sound_pitch /= 10
src.times_to_play = rand(1,3)
var/harmprob = 5
if (src.artitype == "eldritch")
harmprob += 20
if (prob(harmprob))
src.harmful = 1
if (prob(1))
evil = 1
effect_process(var/obj/O)
if (..())
return
var/loops = src.times_to_play
var/turf/T = get_turf(O)
if (evil)
for(var/X in src.sounds)
playsound(T, X, 200, 1, 0, sound_pitch)
else
while (loops > 0)
loops--
playsound(T, src.spamsound, 200, 1, 0, sound_pitch)
if (src.harmful)
for (var/mob/living/M in hearers(world.view, O))
if (issilicon(M) || isintangible(M))
continue
if (!M.ears_protected_from_sound())
boutput(M, "<span style=\"color:red\">The loud, horrible noises painfully batter your eardrums!</span>")
else
continue
var/weak = 0
var/ear_damage = 2
var/ear_tempdeaf = 4
if (prob(10))
weak = 2
M.apply_sonic_stun(weak, 0, 0, 0, 0, ear_damage, ear_tempdeaf)
return
@@ -0,0 +1,51 @@
/obj/machinery/artifact/plant_helper
name = "artifact plant_helper"
associated_datum = /datum/artifact/plant_helper
/datum/artifact/plant_helper
associated_object = /obj/machinery/artifact/plant_helper
rarity_class = 2
validtypes = list("martian","precursor")
validtriggers = list(/datum/artifact_trigger/force,/datum/artifact_trigger/electric,/datum/artifact_trigger/carbon_touch)
activated = 0
activ_text = "begins to radiate a strange energy field!"
deact_text = "shuts down, causing the energy field to vanish!"
react_xray = list(9,45,85,11,"ORGANIC")
var/field_radius = 7
var/list/helpers = list("water") // make it a bit more modular
New()
..()
src.react_heat[2] = "SUPERFICIAL DAMAGE DETECTED"
src.field_radius = rand(2,9) // field radius
if (prob(80))
src.helpers.Add("growth")
if (prob(60))
src.helpers.Add("health")
if (prob(40))
src.helpers.Add("weedkiller")
if (prob(20))
src.helpers.Add("mutation")
effect_process(var/obj/O)
if (..())
return
for (var/obj/machinery/plantpot/P in range(O,src.field_radius))
var/datum/plant/growing = P.current
for (var/X in src.helpers)
if (X == "water")
var/wateramt = P.reagents.get_reagent_amount("water")
if(wateramt > 200)
P.reagents.remove_reagent("water", 1)
if(wateramt < 100)
P.reagents.add_reagent("water", 1)
if (X == "growth" && growing)
P.growth++
if (X == "health" && growing)
P.health++
if (X == "weedkiller" && growing)
if (growing.growthmode == "weed")
P.health -= 3
if (X == "mutation" && growing)
if (prob(8))
P.HYPmutateplant()
@@ -0,0 +1,72 @@
/obj/machinery/artifact/turret
name = "artifact turret"
associated_datum = /datum/artifact/turret
/datum/artifact/turret
associated_object = /obj/machinery/artifact/turret
rarity_class = 3
validtypes = list("wizard","eldritch","precursor")
validtriggers = list(/datum/artifact_trigger/force,/datum/artifact_trigger/electric,/datum/artifact_trigger/heat,
/datum/artifact_trigger/radiation,/datum/artifact_trigger/carbon_touch,/datum/artifact_trigger/silicon_touch)
activated = 0
activ_text = "uncovers an array of guns!"
deact_text = "retracts the guns back into itself and falls quiet!"
react_xray = list(9,40,80,8,"SEGMENTED")
var/cycles_without_target = 0
var/cycles_until_shutdown = 10
var/capricious = 0
var/shot_range = 3
var/datum/projectile/artifact/bullet = null
var/mob/living/friend = null
var/mob/living/current_target = null
examine_hint = "It is covered in very conspicuous markings."
New()
bullet = new /datum/projectile/artifact
shot_range = rand(2,6)
if (prob(20))
capricious = 1
bullet.randomise()
effect_touch(var/obj/O,var/mob/living/user)
if (..())
return
if (src.capricious > -1)
if (!src.friend || src.capricious)
src.friend = user
effect_process(var/obj/O)
if (..())
return
var/turf/T = get_turf(O)
if (!current_target)
var/list/valid_targets = list()
for (var/mob/living/M in view(shot_range,O))
if (!target_is_valid(M,O))
continue
valid_targets += M
if (valid_targets.len > 0)
current_target = pick(valid_targets)
T.visible_message("<b>[O]</b> turns to face [current_target]!")
cycles_without_target = 0
else
cycles_without_target++
if (cycles_without_target >= cycles_until_shutdown)
cycles_without_target = 0
O.ArtifactDeactivated()
else
if (target_is_valid(current_target,O) && istype(bullet,/datum/projectile/artifact))
shoot_projectile_ST(O, bullet, current_target)
else
current_target = null
proc/target_is_valid(var/mob/living/M,var/obj/O)
if (!M || !O)
return 0
if (M.stat == 2)
return 0
if (M == friend)
return 0
if (get_dist(M,O) > shot_range)
return 0
return 1
@@ -0,0 +1,223 @@
// base
/datum/artifact/bomb
associated_object = null
rarity_class = 0
validtypes = list("ancient","eldritch","precursor")
validtriggers = list(/datum/artifact_trigger/force,/datum/artifact_trigger/electric,/datum/artifact_trigger/heat,
/datum/artifact_trigger/cold,/datum/artifact_trigger/radiation)
react_xray = list(12,75,30,11,"COMPLEX")
var/explode_delay = 600
var/dud = 0
var/warning_initial = "begins catastrophically overloading!"
var/warning_final = "reaches critical energy levels!"
var/text_disarmed = "goes quiet."
var/text_dud = "sputters and rattles a bit, then falls quiet."
var/flascustomization_first_color = "#FF0000"
var/sound/alarm_initial = 'sound/machines/lavamoon_plantalarm.ogg'
var/sound/alarm_final = 'sound/machines/engine_alert1.ogg'
examine_hint = "It is covered in very conspicuous markings."
New()
..()
src.react_heat[2] = "VOLATILE REACTION DETECTED"
if (artitype != "eldritch" && prob(5))
dud = 1
effect_activate(var/obj/O)
if (..())
return
if (explode_delay < 1)
deploy_payload(O)
return
var/turf/T = get_turf(O)
if (warning_initial)
T.visible_message("<b>[O] [warning_initial]</b>")
if (alarm_initial)
playsound(T, alarm_initial, 50, 1, -1)
spawn(src.explode_delay)
if (warning_final)
T.visible_message("<b>[O] [warning_final]</b>")
if (alarm_final)
playsound(T, alarm_final, 50, 1, -1)
animate_flash_color_fill(O,flascustomization_first_color,10,3)
spawn(30)
if (src.activated)
deploy_payload(O)
else
T.visible_message("<b>[O] [text_disarmed]")
proc/deploy_payload(var/obj/O)
if (!O)
return 1
if (dud)
var/turf/T = get_turf(O)
T.visible_message("<b>[O] [text_dud]")
O.ArtifactDeactivated()
return 1
// Added (Convair880).
ArtifactLogs(usr, null, O, "detonated", null, 1)
return 0
// regular explosives
/obj/artifact/bomb
name = "artifact bomb"
associated_datum = /datum/artifact/bomb/explosive
/datum/artifact/bomb/explosive
associated_object = /obj/artifact/bomb
rarity_class = 3
var/exp_deva = 1
var/exp_hevy = 2
var/exp_lite = 3
New()
..()
src.exp_deva = rand(0,3)
src.exp_hevy = rand(3,6)
src.exp_lite = rand(6,9)
deploy_payload(var/obj/O)
if (..())
return
explosion(O, O.loc, src.exp_deva, src.exp_hevy, src.exp_lite, src.exp_lite * 2)
O.ArtifactDestroyed()
/obj/artifact/bomb/devastating
name = "artifact devastating bomb"
associated_datum = /datum/artifact/bomb/explosive/devastating
/datum/artifact/bomb/explosive/devastating
associated_object = /obj/artifact/bomb/devastating
rarity_class = 4
New()
..()
src.exp_deva *= rand(3,5)
src.exp_hevy *= rand(4,6)
src.exp_lite *= rand(5,7)
src.explode_delay *= 2
// black hole bomb
/obj/artifact/bomb/blackhole
name = "artifact black hole bomb"
associated_datum = /datum/artifact/bomb/blackhole
/datum/artifact/bomb/blackhole
associated_object = /obj/artifact/bomb/blackhole
rarity_class = 4
react_xray = list(12,75,30,11,"ULTRADENSE")
warning_initial = "begins intensifying its own gravity!"
warning_final = "begins to collapse in on itself!"
deploy_payload(var/obj/O)
if (..())
return
var/turf/T = get_turf(O)
playsound(T, "sound/machines/satcrash.ogg", 100, 0, 3, 0.8)
new /obj/bhole(O.loc,rand(100,300))
if (O)
O.ArtifactDestroyed()
// chemical bombs
/obj/artifact/bomb/chemical
name = "artifact chemical bomb"
associated_datum = /datum/artifact/bomb/chemical
New()
..()
var/datum/reagents/R = new/datum/reagents(10000)
reagents = R
R.my_atom = src
/datum/artifact/bomb/chemical
explode_delay = 0
react_xray = list(5,65,20,11,"HOLLOW")
validtypes = list("ancient","martian","eldritch","precursor")
validtriggers = list(/datum/artifact_trigger/force,/datum/artifact_trigger/heat,/datum/artifact_trigger/carbon_touch)
var/payload_type = 0 // 0 for smoke, 1 for foam
var/recharge_delay = 600
var/list/payload_reagents = list()
post_setup()
payload_type = rand(0,1)
var/list/potential_reagents = list()
switch(artitype)
if ("ancient")
// industrial heavy machinery kinda stuff
potential_reagents = list("nanites","liquid plasma","mercury","lithium","plasma","radium","uranium","napalm",
"thermite","fuel","acid","silicate","lube","cryostylane","oil")
if ("martian")
// medicine, some poisons, some gross stuff
potential_reagents = list("charcoal","stypic_powder","salbutamol","anti_rad","silver_sulfadiazine","synaptizine",
"omnizine","synthflesh","cyanide","sonambutril","toxin","neurotoxin","mutagen","fake_initropidril",
"toxic_slurry","jenkem","space_fungus","blood","vomit","gvomit","urine","meat_slurry","grease")
if ("eldritch")
// all the worst stuff. all of it
potential_reagents = list("chlorine","fluorine","lithium","mercury","plasma","radium","uranium","strange_reagent",
"napalm","thermite","infernite","foof","fuel","blackpowder","acid","amanitin","coniine","cyanide","curare",
"formaldehyde","lipolicide","initropidril","cholesterol","itching","pacid","pancuronium","polonium",
"sodium_thiopental","sonambutril","sulfonal","toxin","venom","neurotoxin","mutagen","wolfsbane",
"toxic_slurry","histamine","sarin")
else
// absolutely everything
potential_reagents = all_functional_reagent_ids
if (potential_reagents.len > 0)
var/looper = rand(2,8)
while (looper > 0)
looper--
payload_reagents += pick(potential_reagents)
recharge_delay = rand(200,800)
deploy_payload(var/obj/O)
if (..())
return
var/list/reaction_reagents = list()
for (var/X in payload_reagents)
reaction_reagents += X
if (payload_type)
reaction_reagents += "fluorosurfactant"
reaction_reagents += "water"
else
reaction_reagents += "potassium"
reaction_reagents += "sugar"
reaction_reagents += "phosphorus"
var/amountper = 0
if (reaction_reagents.len > 0)
amountper = round(O.reagents.maximum_volume / reaction_reagents.len)
else
amountper = 20
for (var/X in reaction_reagents)
O.reagents.add_reagent(X,amountper)
if (payload_type)
var/turf/location = get_turf(O)
var/datum/effects/system/foam_spread/s = new()
s.set_up(O.reagents.total_volume, location, O.reagents, 0)
s.start()
else
smoke_reaction(O.reagents, 4, get_turf(O))
O.reagents.clear_reagents()
spawn(recharge_delay)
if (O)
O.ArtifactDeactivated()
@@ -0,0 +1,62 @@
/obj/artifact/borgifier
name = "artifact human2cyborg converter"
associated_datum = /datum/artifact/borgifier
/datum/artifact/borgifier
associated_object = /obj/artifact/borgifier
rarity_class = 3
validtypes = list("ancient")
validtriggers = list(/datum/artifact_trigger/force,/datum/artifact_trigger/electric,/datum/artifact_trigger/heat,
/datum/artifact_trigger/radiation,/datum/artifact_trigger/carbon_touch)
activated = 0
react_xray = list(13,60,80,6,"COMPLEX")
touch_descriptors = list("You seem to have a little difficulty taking your hand off its surface.")
var/converting = 0
var/list/work_sounds = list('sound/effects/bloody_stab.ogg','sound/effects/clang.ogg','sound/effects/airbridge_dpl.ogg','sound/effects/splat.ogg','sound/misc/loudcrunch2.ogg','sound/effects/attackblob.ogg')
effect_touch(var/obj/O,var/mob/living/user)
if (..())
return
if (!user)
return
if (converting)
return
if (istype(user,/mob/living/carbon/human/))
O.visible_message("<span style=\"color:red\"><b>[O]</b> suddenly pulls [user.name] inside and slams shut!</span>")
user.emote("scream")
user.set_loc(O.loc)
converting = 1
var/loops = rand(10,20)
while (loops > 0)
loops--
random_brute_damage(user, 15)
user.paralysis = 5
playsound(user.loc, pick(work_sounds), 50, 1, -1)
sleep(4)
var/bdna = null // For forensics (Convair880).
var/btype = null
if (user.bioHolder.Uid && user.bioHolder.bloodType)
bdna = user.bioHolder.Uid
btype = user.bioHolder.bloodType
var/turf/T = find_loc(user)
gibs(T, null, null, bdna, btype)
ArtifactLogs(user, null, O, "touched", "robotizing user", 0) // Added (Convair880).
if (ismonkey(user))
user.ghostize()
var/robopath = pick(/obj/machinery/bot/guardbot,/obj/machinery/bot/secbot,
/obj/machinery/bot/medbot,/obj/machinery/bot/firebot,/obj/machinery/bot/cleanbot,
/obj/machinery/bot/floorbot)
new robopath (T)
qdel(user)
else
var/mob/living/carbon/human/M = user
M.Robotize_MK2(1)
score_cyborgsmade += 1
converting = 0
else if (istype(user,/mob/living/silicon/))
boutput(user, "<span style=\"color:red\">An imperious voice rings out in your head... \"<b>HUNT BIOLOGICALS FOR UPGRADING\"</span>")
else
return
@@ -0,0 +1,73 @@
/obj/artifact/container
name = "artifact sealed container"
associated_datum = /datum/artifact/container
New(var/loc, var/forceartitype)
..()
ArtifactActivated(var/mob/living/user as mob)
var/datum/artifact/A = src.artifact
if (A.activated)
return
A.activated = 1
playsound(src.loc, A.activ_sound, 100, 1)
src.overlays += A.fx_image
src.visible_message("<b>[src] seems like it has something inside it...</b>")
switch(rand(1,4))
if(1)
if(prob(5))
new/obj/item/artifact/activator_key(src)
else
new/obj/item/cell/artifact(src)
new/obj/item/cell/artifact(src)
new/obj/item/cell/artifact(src)
if(2)
if(prob(5))
new/obj/critter/domestic_bee/buddy(src)
new/obj/item/clothing/suit/bee(src)
else
new/obj/critter/domestic_bee_larva(src)
new/obj/critter/domestic_bee_larva(src)
new/obj/critter/domestic_bee_larva(src)
new/obj/critter/domestic_bee_larva(src)
new/obj/critter/domestic_bee_larva(src)
if(3)
if(prob(5))
new/obj/item/gimmickbomb/owlclothes(src)
new/obj/item/gimmickbomb/owlclothes(src)
new/obj/item/gimmickbomb/owlclothes(src)
new/obj/item/gimmickbomb/owlclothes(src)
new/obj/item/gimmickbomb/owlclothes(src)
else
new/obj/item/gimmickbomb/owlclothes(src)
if(4)
new/obj/item/old_grenade/light_gimmick(src)
/datum/artifact/container
associated_object = /obj/artifact/container
rarity_class = 1
validtypes = list("ancient","martian","wizard","eldritch","precursor")
validtriggers = list(/datum/artifact_trigger/force,/datum/artifact_trigger/electric,/datum/artifact_trigger/heat,
/datum/artifact_trigger/radiation,/datum/artifact_trigger/carbon_touch,/datum/artifact_trigger/silicon_touch)
activ_text = "deposits its contents on the ground."
deact_text = "ceases functioning."
react_xray = list(7,50,40,11,"HOLLOW")
New()
..()
src.react_heat[2] = "HIGH INTERNAL CONVECTION"
effect_touch(var/obj/O,var/mob/living/user)
if (..())
return
for(var/obj/I in O.contents)
I.set_loc(O.loc)
for(var/mob/N in viewers(O, null))
N.flash(30)
if(N.client)
shake_camera(N, 6, 4)
O.visible_message("<span style=\"color:red\"><b>With a blinding light [O] vanishes, leaving its contents behind.</b></span>")
playsound(O.loc, "sound/effects/warp2.ogg", 50, 1)
artifact_controls.artifacts -= src
qdel(O)
return
@@ -0,0 +1,53 @@
/obj/artifact/darkness_field
name = "artifact darkness field"
associated_datum = /datum/artifact/darkness_field
/datum/artifact/darkness_field
associated_object = /obj/artifact/darkness_field
rarity_class = 2
max_triggers = 3
validtypes = list("wizard","eldritch","precursor")
react_xray = list(15,90,90,11,"NONE")
var/field_radius = 0
var/field_time = 0
New()
..()
field_radius = rand(2,8)
if (prob(1))
field_radius *= 2
field_time = rand(300,1800)
effect_activate(var/obj/O)
if (..())
return
O.visible_message("<span style=\"color:red\"><b>[O]</b> emits a wave of absolute darkness!</span>")
O.anchored = 1
for(var/turf/T in circular_range(O,field_radius))
new /obj/darkness_field(T,field_time)
spawn(field_time)
if (O)
O.anchored = 0
O.ArtifactDeactivated()
return
/obj/darkness_field
name = ""
desc = ""
alpha = 0
icon = 'icons/turf/walls.dmi'
color = "#000000"
blend_mode = 1
anchored = 1
density = 0
opacity = 0
layer = NOLIGHT_EFFECTS_LAYER_BASE
mouse_opacity = 0
New(var/loc,var/duration)
..()
animate(src, time = 20, alpha = 255, easing = LINEAR_EASING)
spawn(duration)
animate(src, time = 20, alpha = 0, easing = LINEAR_EASING)
spawn(0)
qdel(src)
@@ -0,0 +1,55 @@
/obj/artifact/forcefield_generator
name = "artifact forcefield generator"
associated_datum = /datum/artifact/forcefield_gen
/datum/artifact/forcefield_gen
associated_object = /obj/artifact/forcefield_generator
rarity_class = 1
validtypes = list("wizard","eldritch","precursor")
validtriggers = list(/datum/artifact_trigger/force,/datum/artifact_trigger/carbon_touch,
/datum/artifact_trigger/silicon_touch)
activated = 0
activ_text = "comes to life, projecting out a wall of force!"
deact_text = "shuts down, causing the forcefield to vanish!"
react_xray = list(13,60,95,11,"NONE")
var/cooldown = 80
var/field_radius = 3
var/field_time = 80
var/icon_state = "shieldsparkles"
var/next_activate = 0
New()
..()
src.icon_state = pick("shieldsparkles","empdisable","greenglow","enshield","energyorb","forcewall","meteor_shield")
src.field_radius = rand(2,6) // forcefield radius
src.field_time = rand(15,1500) // forcefield duration
src.cooldown = rand(50, 1200)
src.activ_sound = pick('sound/effects/mag_forcewall.ogg','sound/effects/mag_warp.ogg','sound/effects/MagShieldUp.ogg')
src.deact_sound = pick('sound/effects/MagShieldDown.ogg','sound/effects/shielddown2.ogg','sound/effects/singsuck.ogg')
may_activate(var/obj/O)
if (!..())
return 0
if (ticker.round_elapsed_ticks < next_activate)
O.visible_message("<span style=\"color:red\">[O] emits a loud pop and lights up momentarily but nothing happens!</span>")
return 0
return 1
effect_activate(var/obj/O,var/mob/living/user)
if (..())
return
O.anchored = 1
var/turf/Aloc = get_turf(O)
var/list/forcefields = list()
for (var/turf/T in range(field_radius,Aloc))
if(get_dist(O,T) == field_radius)
var/obj/forcefield/wand/FF = new /obj/forcefield/wand(T,0,src.icon_state)
forcefields += FF
spawn(field_time)
for (var/obj/forcefield/F in forcefields)
forcefields -= F
qdel(F)
next_activate = ticker.round_elapsed_ticks + cooldown
if (O)
O.ArtifactDeactivated()
O.anchored = 0
@@ -0,0 +1,54 @@
/obj/artifact/healer_bio
name = "artifact carbon healer"
associated_datum = /datum/artifact/healer_bio
/datum/artifact/healer_bio
associated_object = /obj/artifact/healer_bio
rarity_class = 1
validtypes = list("martian","precursor")
validtriggers = list(/datum/artifact_trigger/force,/datum/artifact_trigger/electric,/datum/artifact_trigger/heat,
/datum/artifact_trigger/radiation,/datum/artifact_trigger/carbon_touch)
activated = 0
activ_text = "begins to pulse softly."
deact_text = "ceases pulsing."
react_xray = list(11,70,90,9,"NONE")
var/heal_amt = 20
var/field_range = 0
var/recharge_time = 600
var/recharging = 0
New()
..()
src.react_heat[2] = "SUPERFICIAL DAMAGE DETECTED"
if(prob(20))
src.field_range = rand(3,10) // range
src.heal_amt = rand(5,75) // amount of healing
src.recharge_time = rand(1,10) * 10
if(prob(5))
src.recharge_time = 0
effect_touch(var/obj/O,var/mob/living/user)
if (..())
return
if (!user)
return
var/turf/T = get_turf(O)
if (recharging)
boutput(user, "<span style=\"color:red\">The artifact pulses briefly, but nothing else happens.</span>")
return
if (recharge_time > 0)
recharging = 1
T.visible_message("<b>[O]</b> emits a wave of energy!")
if(istype(user,/mob/living/carbon/))
var/mob/living/carbon/C = user
C.HealDamage("All", heal_amt, heal_amt)
boutput(C, "<span style=\"color:blue\">Soothing energy saturates your body, making you feel refreshed and healthy.</span>")
if (field_range > 0)
for (var/mob/living/carbon/C in range(field_range,T))
if (C == user)
continue
C.HealDamage("All", heal_amt, heal_amt)
boutput(C, "<span style=\"color:blue\">Waves of soothing energy wash over you, making you feel refreshed and healthy.</span>")
spawn(recharge_time)
recharging = 0
T.visible_message("<b>[O]</b> becomes energized.")
@@ -0,0 +1,56 @@
/obj/artifact/injector
name = "artifact injector"
associated_datum = /datum/artifact/injector
/datum/artifact/injector
associated_object = /obj/artifact/injector
rarity_class = 2
validtypes = list("ancient","martian","eldritch","precursor")
validtriggers = list(/datum/artifact_trigger/force,/datum/artifact_trigger/electric,/datum/artifact_trigger/heat,
/datum/artifact_trigger/radiation,/datum/artifact_trigger/carbon_touch,/datum/artifact_trigger/silicon_touch,
/datum/artifact_trigger/cold)
activ_text = "opens up, revealing an array of strange needles!"
deact_text = "closes itself up."
react_xray = list(8,60,75,11,"SEGMENTED")
var/list/injection_reagents = list()
var/injection_amount = 10
post_setup()
var/list/potential_reagents = list()
switch(artitype)
if ("ancient")
// industrial heavy machinery kinda stuff
potential_reagents = list("nanites","liquid plasma","mercury","lithium","plasma","radium","uranium","cryostylane")
if ("martian")
// medicine, some poisons, some gross stuff
potential_reagents = list("charcoal","salbutamol","anti_rad","synaptizine","omnizine","synthflesh",
"cyanide","sonambutril","toxin","neurotoxin","mutagen","fake_initropidril",
"toxic_slurry","space_fungus","blood","urine","meat_slurry")
if ("eldritch")
// all the worst stuff. all of it
potential_reagents = list("chlorine","fluorine","lithium","mercury","plasma","radium","uranium","strange_reagent",
"amanitin","coniine","cyanide","curare",
"formaldehyde","lipolicide","initropidril","cholesterol","itching","pancuronium","polonium",
"sodium_thiopental","sonambutril","sulfonal","toxin","venom","neurotoxin","mutagen","wolfsbane",
"toxic_slurry","histamine","sarin")
else
// absolutely everything
potential_reagents = all_functional_reagent_ids
if (potential_reagents.len > 0)
var/looper = rand(1,3)
while (looper > 0)
looper--
injection_reagents += pick(potential_reagents)
injection_amount = rand(3,25)
effect_touch(var/obj/O,var/mob/living/user)
if (..())
return
if (user.reagents && injection_reagents.len > 0)
var/turf/T = get_turf(O)
T.visible_message("<b>[O]</b> jabs [user] with a needle and injects something!")
for (var/X in injection_reagents)
ArtifactLogs(user, null, O, "touched by [user.real_name]", "injecting [X]", 0) // Added (Convair880).
user.reagents.add_reagent(X,injection_amount)
@@ -0,0 +1,44 @@
/obj/artifact/lamp
name = "artifact lamp"
associated_datum = /datum/artifact/lamp
var/light_brightness = 1
var/light_R = 1
var/light_G = 1
var/light_B = 1
var/datum/light/light
New()
..()
light_brightness = max(0.5, (rand(5, 20) / 10))
light_R = rand(25,100) / 100
light_G = rand(25,100) / 100
light_B = rand(25,100) / 100
light = new /datum/light/point
light.set_brightness(light_brightness)
light.set_color(light_R, light_G, light_B)
light.attach(src)
/datum/artifact/lamp
associated_object = /obj/artifact/lamp
rarity_class = 1
validtypes = list("martian","wizard","precursor")
validtriggers = list(/datum/artifact_trigger/force,/datum/artifact_trigger/electric,/datum/artifact_trigger/heat,
/datum/artifact_trigger/radiation,/datum/artifact_trigger/carbon_touch,/datum/artifact_trigger/silicon_touch,
/datum/artifact_trigger/cold)
activ_text = "begins to emit a steady light!"
deact_text = "goes dark and quiet."
react_xray = list(10,90,90,11,"NONE")
effect_activate(var/obj/O)
if (..())
return
var/obj/artifact/lamp/L = O
if (L.light)
L.light.enable()
effect_deactivate(var/obj/O)
if (..())
return
var/obj/artifact/lamp/L = O
if (L.light)
L.light.disable()
@@ -0,0 +1,45 @@
/obj/artifact/power_giver
name = "artifact power giver"
associated_datum = /datum/artifact/power_giver
/datum/artifact/power_giver
associated_object = /obj/artifact/power_giver
rarity_class = 3
validtypes = list("martian","wizard","eldritch","precursor")
validtriggers = list(/datum/artifact_trigger/force,/datum/artifact_trigger/electric,/datum/artifact_trigger/heat,
/datum/artifact_trigger/radiation,/datum/artifact_trigger/carbon_touch,/datum/artifact_trigger/silicon_touch,
/datum/artifact_trigger/cold)
activ_text = "begins glowing with an eerie light!"
deact_text = "falls dark and quiet."
react_xray = list(10,90,80,10,"NONE")
var/power_granted = null
var/power_time = 0
var/recharge_time = 300
var/ready = 1
New()
..()
power_granted = pick("blind","mute","clumsy","fat","dwarf","fire_resist","cold_resist","resist_electric",
"psy_resist","glowy","hulk","xray","horns","stinky","monkey","mattereater","jumpy","telepathy","empath",
"immolate","eyebeams","melt")
power_time = rand(30,180)
if (prob(5))
power_time = 0
recharge_time = rand(100,600)
if (prob(5))
recharge_time = 0
effect_touch(var/obj/O,var/mob/living/user)
if (..())
return
if (!istype(user,/mob/living/carbon/))
return
if (user.bioHolder && ready)
var/turf/T = get_turf(O)
T.visible_message("<b>[O]</b> envelops [user] in a strange light!")
user.bioHolder.AddEffect(power_granted,0,power_time)
if (recharge_time > 0)
ready = 0
spawn(recharge_time)
T.visible_message("<b>[O]</b> begins to glow again.")
ready = 1
@@ -0,0 +1,39 @@
/obj/artifact/prison
name = "artifact imprisoner"
associated_datum = /datum/artifact/prison
/datum/artifact/prison
associated_object = /obj/artifact/prison
rarity_class = 2
min_triggers = 2
max_triggers = 2
validtypes = list("ancient","martian","wizard","eldritch","precursor")
validtriggers = list(/datum/artifact_trigger/carbon_touch,/datum/artifact_trigger/silicon_touch)
react_xray = list(15,90,90,11,"HOLLOW")
touch_descriptors = list("You seem to have a little difficulty taking your hand off its surface.")
var/mob/living/prisoner = null
var/imprison_time = 0
New()
..()
imprison_time = rand(50,1200)
effect_touch(var/obj/O,var/mob/living/user)
if (..())
return
if (!user)
return
if (prisoner)
return
if (istype(user,/mob/living/))
O.visible_message("<span style=\"color:red\"><b>[O]</b> suddenly pulls [user.name] inside and slams shut!</span>")
user.set_loc(O)
prisoner = user
spawn(imprison_time)
for(var/obj/I in O.contents)
I.set_loc(get_turf(O))
prisoner.set_loc(get_turf(O))
prisoner = null
O.visible_message("<span style=\"color:red\"><b>[O]</b> releases [user.name] and shuts down!</span>")
O.ArtifactDeactivated()
return
@@ -0,0 +1,31 @@
/obj/artifact/teleport_recaller
name = "artifact recaller"
associated_datum = /datum/artifact/recaller
/datum/artifact/recaller
associated_object = /obj/artifact/teleport_recaller
rarity_class = 2
validtypes = list("wizard","eldritch","precursor")
validtriggers = list(/datum/artifact_trigger/force,/datum/artifact_trigger/electric,/datum/artifact_trigger/heat,
/datum/artifact_trigger/radiation,/datum/artifact_trigger/carbon_touch,/datum/artifact_trigger/silicon_touch)
activated = 0
react_xray = list(15,75,90,3,"ANOMALOUS")
var/recall_delay = 10
New()
..()
src.recall_delay = rand(2,600) // how long *10 it takes for the recall to happen
src.recall_delay *= 10
effect_touch(var/obj/O,var/mob/living/user)
if (..())
return
if (!user)
return
spawn(src.recall_delay)
user.visible_message("<span style=\"color:red\"><b>[user]</b> is suddenly pulled through space!</span>")
playsound(user.loc, "sound/effects/mag_warp.ogg", 50, 1, -1)
var/turf/T = get_turf(O)
if (T)
user.set_loc(T)
@@ -0,0 +1,92 @@
/obj/artifact/wish_granter
name = "artifact wish granter"
associated_datum = /datum/artifact/wish_granter
/datum/artifact/wish_granter
associated_object = /obj/artifact/wish_granter
rarity_class = 4
validtypes = list("wizard","eldritch")
validtriggers = list(/datum/artifact_trigger/force,/datum/artifact_trigger/electric,/datum/artifact_trigger/heat,
/datum/artifact_trigger/radiation,/datum/artifact_trigger/cold)
activ_text = "begins glowing with an enticing light!"
deact_text = "falls dark and quiet."
react_xray = list(666,666,666,11,"NONE")
var/list/wish_granted = list()
var/evil = 0
New()
..()
if (prob(50))
evil = 1
effect_touch(var/obj/O,var/mob/living/user)
if (..())
return
if (!istype(user,/mob/living/))
return
if (user.key in wish_granted)
boutput(user, "<b>[O]</b> is silent.")
return
boutput(user, "<b>[O]</b> resonates, \"<big>I SHALL GRANT YOU ONE WISH...</big>\"")
var/list/wishes = list("I wish to become rich!","I wish for great power!")
var/wish = input("Make a wish?","[O]") as null|anything in wishes
if (!wish)
boutput(user, "You say nothing.")
boutput(user, "<b>[O]</b> resonates, \"<big>YOU MAY RETURN LATER...</big>\"")
return
wish_granted += user.key
user.say(wish)
sleep(5)
boutput(user, "<b>[O]</b> resonates, \"<big>SO BE IT...</big>\"")
playsound(O, "sound/effects/gong_rumble.ogg", 40, 1)
O.visible_message("<span style=\"color:red\"><b>[O]</b> begins to charge up...</span>")
sleep(30)
if (prob(2))
evil = !evil
if (evil)
switch(wish)
if("I wish to become rich!")
O.visible_message("<span style=\"color:red\"><b>[O]</b> envelops [user] in a golden light!</span>")
playsound(user, "sound/weapons/flashbang.ogg", 50, 1)
for(var/mob/N in viewers(user, null))
N.flash(30)
if(N.client)
shake_camera(N, 6, 4)
user.desc = "A statue of someone very wealthy"
user.become_gold_statue()
if("I wish for great power!")
O.visible_message("<span style=\"color:red\"><b>[O] discharges a massive bolt of electricity!</b></span>")
playsound(user, "sound/effects/elec_bigzap.ogg", 40, 1)
var/list/affected = DrawLine(O,user,/obj/line_obj/elec,'icons/obj/projectiles.dmi',"WholeLghtn",1,1,"HalfStartLghtn","HalfEndLghtn",OBJ_LAYER,1,PreloadedIcon='icons/effects/LghtLine.dmi')
for(var/obj/OB in affected)
spawn(6)
pool(OB)
user.elecgib()
else
switch(wish)
if("I wish to become rich!")
O.visible_message("<span style=\"color:red\">A ton of money falls out of thin air! Woah!</span>")
for(var/turf/T in range(user,3))
if (T.density)
continue
new /obj/item/spacecash/million(T)
if("I wish for great power!")
O.visible_message("<span style=\"color:red\"><b>[O]</b> envelops [user] in a brilliant light!</span>")
if (ishuman(user))
var/mob/living/carbon/human/H = user
if (H.bioHolder)
H.bioHolder.RandomEffect("good")
H.bioHolder.RandomEffect("good")
H.bioHolder.RandomEffect("good")
else if (istype(user,/mob/living/silicon/robot))
var/mob/living/silicon/robot/R = user
if (istype(R.cell))
R.cell.genrate = 100
R.cell.maxcharge = 1000000
R.cell.charge = R.cell.maxcharge
+175
View File
@@ -0,0 +1,175 @@
// MASTER DATUMS
/datum/artifact/
var/associated_object = null
var/rarity_class = 0
var/datum/artifact_origin/artitype = null
var/list/validtypes = list("ancient","martian","wizard","eldritch","precursor")
// During setup, artitype will be set from a pick() from within the validtypes list.
// Keep it to only the five here or shit will probably get a bit weird. This allows us to exclude things that don't make
// any sense such as martian robot builders or ancient robot plant seeds.
var/internal_name = null
var/image/fx_image = null
//var/image/effects_overlay = null
var/obj/holder = null
// These are automatically handled. They're used to make the artifact glow different colors.
var/activated = 0 // Is the artifact currently switched on?
var/automatic_activation = 0 // Does the artifact switch itself on on spawn?
var/activ_sound = null // What noise the artifact makes when it activates
var/activ_text = null // What message the artifact transmits when it activates
var/deact_sound = null // Guess.
var/deact_text = null // No really, have a wild guess.
var/scramblechance = 10 // how likely this artifact is to look like a type it isnt
var/list/faults = list() // Automatically handled
var/list/fault_types = list() // this is set up based on the artifact's origin type
var/list/triggers = list()
var/validtriggers = list(/datum/artifact_trigger/force,/datum/artifact_trigger/electric,/datum/artifact_trigger/heat,
/datum/artifact_trigger/radiation,/datum/artifact_trigger/carbon_touch,/datum/artifact_trigger/silicon_touch)
var/min_triggers = 1
var/max_triggers = 1
var/hint_text = "emits a faint noise."
var/examine_hint = null
// These are used for module research
var/list/module_research = list()
var/module_research_insight = 1 // insight level into the origin of the artifact
var/health = 100
// This is mostly used in the stimulus procs that deal with damaging the artifact and whatnot.
// Once it hits 0 or below, the artifact is destroyed.
// these below are holders for data that will come back from the various artifact sensor test apparatus
var/list/react_mpct = list(0,0)
// Impact Pad - returns Vibration Amplitude, Vibration Frequency
// react_mpct should be set up in the ArtifactSetup proc
var/list/react_elec = list(0.1,0,0)
// Electrobox - returns Returned Current, Circuit Capacity, Circuit Interference
// react_elec should be set up in the item's New proc (NOT the datum's!)
var/list/react_heat = list(1,"NONE")
// Heat Plate - returns Artifact Temp, Heat Response, Cold Response, Details
// react_heat - set up first var in ArtifactSetup, the rest in the individual datums
var/list/react_xray = list(10,100,100,11,"NONE")
// X-ray - returns Density, Structural Consistency, Structural Integrity, Response, Special Features
// react_xray should be set as a variable on the artifact datum
var/list/touch_descriptors = list()
proc/post_setup()
return
proc/may_activate(var/obj/O)
if (!O)
return 0
return 1
// Added log entry calls here. See artifactprocs.dm for the proc (Convair880).
proc/effect_activate(var/obj/O)
if (!O)
return 1
O.add_fingerprint(usr)
ArtifactLogs(usr, null, O, "activated", null, istype(src, /datum/artifact/bomb/) ? 1 : 0)
return 0
proc/effect_deactivate(var/obj/O)
if (!O)
return 1
O.add_fingerprint(usr)
ArtifactLogs(usr, null, O, "deactivated", null, 0)
return 0
proc/effect_process(var/obj/O)
if (!O)
return 1
return 0
proc/effect_touch(var/obj/O,var/mob/living/user)
if (!O || !user)
return 1
O.add_fingerprint(user)
return 0
proc/effect_melee_attack(var/obj/O,var/mob/living/user,var/mob/living/target)
if (!O || !user || !target)
return 1
O.add_fingerprint(user)
ArtifactLogs(user, target, O, "weapon", null, 0)
return 0
proc/effect_click_tile(var/obj/O,var/mob/living/user,var/turf/T)
if (!O || !user || !T)
return 1
O.add_fingerprint(user)
if (!istype(O, /obj/item/artifact/attack_wand)) // Special log handling required there.
ArtifactLogs(user, T, O, "used", "triggering its effect on target turf", 0)
return 0
proc/get_trigger_by_string(var/string)
if (!istext(string))
return null
for (var/datum/artifact_trigger/AT in src.triggers)
if (AT.stimulus_required == string)
return AT
return null
proc/get_trigger_by_path(var/path)
if (!ispath(path))
return null
for (var/datum/artifact_trigger/AT in src.triggers)
if (AT.type == path)
return AT
return null
// SPECIFIC DATUMS
/datum/artifact/art
validtypes = list("ancient","martian","wizard","eldritch","precursor")
activated = 0
min_triggers = 0
max_triggers = 0
react_xray = list(10,100,100,11,"NONE")
// DATUMS USED BY ARTIFACTS
/datum/projectile/artifact
name = "energy bolt"
icon = 'icons/obj/projectiles.dmi'
icon_state = "u_laser"
power = 75
cost = 25
dissipation_rate = 0
dissipation_delay = 50
ks_ratio = 1.0
sname = "energy bolt"
shot_sound = 'sound/weapons/Taser.ogg'
shot_number = 1
damage_type = D_PIERCING
hit_ground_chance = 90
window_pass = 0
on_hit(atom/hit)
return
proc/randomise()
icon_state = pick("spark","laser","ibeam","u_laser","phaser_heavy","phaser_light","phaser_med","phaser_ultra","blue_spark","disrupt","disrupt_lethal","radbolt","crescent",
"goo","40mmgatling","elecorb","purple_orb","triple")
src.shot_sound = pick('sound/weapons/Taser.ogg','sound/weapons/flaregun.ogg','sound/weapons/Laser.ogg','sound/weapons/laserheavy.ogg','sound/weapons/laserlight.ogg','sound/weapons/lasermed.ogg','sound/weapons/laserultra.ogg','sound/weapons/grenade.ogg','sound/weapons/rocket.ogg','sound/weapons/snipershot.ogg','sound/weapons/TaserOLD.ogg','sound/weapons/ACgun1.ogg','sound/weapons/ACgun2.ogg')
var/namep1 = pick("neutrino","meson","photon","quark","disruptor","atomic","zero point","tachyon","plasma","quantum","neutron","baryon","hadron","electron","positron")
var/namep2 = pick("bolt","ray","beam","wave","burst","blast","torpedo","missile","bomb","shard","stream","string")
src.name = "[namep1] [namep2]"
// Now randomise the damage type, power, energy cost and other fun stuff
src.damage_type = pick(D_KINETIC,D_PIERCING,D_SLASHING,D_ENERGY,D_BURNING,D_RADIOACTIVE,D_TOXIC)
src.power = rand(2,50)
src.dissipation_rate = rand(1,power)
src.dissipation_delay = rand(1,10)
src.ks_ratio = pick(0, 1, prob(10); (rand(0, 10000) / 10000))
src.cost = rand(50,150)
if (prob(20))
src.window_pass = 1
// Rare chance of the gun firing several shots in a burst
shot_number = pick(1, prob(25); 2, prob(5); 3, prob(1); 4)
+436
View File
@@ -0,0 +1,436 @@
// Artifact Infrastructure Procs
/obj/landmark/artifact
name = "artifact spawner"
icon = 'icons/mob/screen1.dmi'
icon_state = "x3"
anchored = 1.0
var/spawnchance = 100 // prob chance out of 100 to spawn artifact at game start
var/spawnpath = null // if you want a landmark to spawn a specific artifact rather than a random one
/obj/landmark/artifact/seed
name = "artifact seed spawner"
spawnpath = /obj/item/seed/alien
/obj/landmark/artifact/cannabis_seed
name = "cannabis seed spawner"
spawnpath = /obj/item/seed/cannabis
// not actually an artifact but eh seeds are behaving oddly
/proc/Artifact_Spawn(var/atom/T,var/forceartitype)
if (!T)
return
if (!istype(T,/turf/) && !istype(T,/obj/))
return
var/rarityroll = 1
switch(rand(1,100))
if (63 to 88)
rarityroll = 2
// 1 in 25
if (89 to 99)
rarityroll = 3
// 1 in 10
if (100)
rarityroll = 4
// 1 in 100
else
rarityroll = 1
// 1 in 62
var/list/selection_pool = list()
for (var/datum/artifact/A in artifact_controls.artifact_types)
if (A.rarity_class != rarityroll)
continue
if (istext(forceartitype) && !forceartitype in A.validtypes)
continue
selection_pool += A
if (selection_pool.len < 1)
return
var/datum/artifact/picked = pick(selection_pool)
if (!istype(picked,/datum/artifact/))
return
if (istext(forceartitype))
new picked.associated_object(T,forceartitype)
else
new picked.associated_object(T)
/obj/proc/ArtifactSanityCheck()
// This proc is called in any other proc or thing that uses the new artifact shit. If there was an improper artifact variable
// involved when trying to do the new shit, it would probably spew errors fucking everywhere and generally be horrible so if
// the sanity check detects that an artifact doesn't have the proper shit set up it'll just wipe out the artifact and stop
// the rest of the proc from occurring.
// This proc should be called in an if statement at the start of every artifact proc, since it returns 0 or 1.
if (!src.artifact)
return 0
// if the artifact var isn't set at all, it's probably not an artifact so don't bother continuing
if (!istype(src.artifact,/datum/artifact/))
logTheThing("debug", null, null, "<b>I Said No/Artifact:</b> Invalid artifact variable in [src.type] at [showCoords(src.x, src.y, src.z)]")
qdel(src) // wipes itself out since if it's processing it'd be calling procs it can't use again and again
return 0 // uh oh, we've got a poorly set up artifact and now we need to stop the proc that called it!
else
return 1 // give the all clear
/obj/proc/ArtifactSetup()
// This proc gets called in every artifact's New() proc, after src.artifact is turned from a 1 into its appropriate datum.
//It scrambles the name and appearance of the artifact so we can't tell what it is on sight or cursory examination.
// Could potentially go in /obj/New(), but...
if (!src.ArtifactSanityCheck())
return
var/datum/artifact/A = src.artifact
A.holder = src
var/datum/artifact_origin/AO = artifact_controls.get_origin_from_string(pick(A.validtypes))
if (!istype(AO,/datum/artifact_origin/))
qdel(src)
return
A.artitype = AO
// Refers to the artifact datum's list of origins it's allowed to be from and selects one at random. This way we can avoid
// stuff that doesn't make sense like ancient robot plant seeds or eldritch healing devices
var/datum/artifact_origin/appearance = artifact_controls.get_origin_from_string(AO.name)
if (prob(A.scramblechance))
appearance = null
// rare-ish chance of an artifact appearing to be a different origin, just to throw things off
if (!istype(appearance,/datum/artifact_origin/))
var/list/all_origin_names = list()
for (var/datum/artifact_origin/O in artifact_controls.artifact_origins)
all_origin_names += O.name
appearance = artifact_controls.get_origin_from_string(pick(all_origin_names))
var/name1 = pick(appearance.adjectives)
var/name2 = "thingy"
if (istype(src,/obj/item/))
name2 = pick(appearance.nouns_small)
else
name2 = pick(appearance.nouns_large)
src.name = "[name1] [name2]"
src:real_name = "[name1] [name2]"
desc = "You have no idea what this thing is!"
A.touch_descriptors |= appearance.touch_descriptors
src.icon_state = appearance.name + "-[rand(1,appearance.max_sprites)]"
if (istype(src,/obj/item/))
var/obj/item/I = src
I.item_state = appearance.name
A.fx_image = image(src.icon, src.icon_state + "fx")
A.fx_image.color = rgb(rand(AO.fx_red_min,AO.fx_red_max),rand(AO.fx_green_min,AO.fx_green_max),rand(AO.fx_blue_min,AO.fx_blue_max))
A.react_mpct[1] = AO.impact_reaction_one
A.react_mpct[2] = AO.impact_reaction_two
A.react_heat[1] = AO.heat_reaction_one
A.activ_sound = pick(AO.activation_sounds)
A.fault_types |= AO.fault_types
A.internal_name = AO.generate_name()
ArtifactDevelopFault(10)
if (A.automatic_activation)
src.ArtifactActivated()
else
var/list/valid_triggers = A.validtriggers
var/trigger_amount = rand(A.min_triggers,A.max_triggers)
var/selection = null
while (trigger_amount > 0)
trigger_amount--
selection = pick(valid_triggers)
if (ispath(selection))
var/datum/artifact_trigger/AT = new selection
A.triggers += AT
valid_triggers -= selection
artifact_controls.artifacts += src
A.post_setup()
/obj/proc/ArtifactActivated()
if (!src)
return
if (!src.ArtifactSanityCheck())
return 1
var/datum/artifact/A = src.artifact
if (A.activated)
return 1
if (A.triggers.len < 1 && !A.automatic_activation)
return 1 // can't activate these ones at all by design
if (!A.may_activate(src))
return 1
if (A.activ_sound)
playsound(src.loc, A.activ_sound, 100, 1)
if (A.activ_text)
var/turf/T = get_turf(src)
T.visible_message("<b>[src] [A.activ_text]</b>")
A.activated = 1
src.overlays += A.fx_image
A.effect_activate(src)
/obj/proc/ArtifactDeactivated()
if (!src.ArtifactSanityCheck())
return
var/datum/artifact/A = src.artifact
if (A.deact_sound)
playsound(src.loc, A.deact_sound, 100, 1)
if (A.deact_text)
var/turf/T = get_turf(src)
T.visible_message("<b>[src] [A.deact_text]</b>")
A.activated = 0
src.overlays = null
A.effect_deactivate(src)
/obj/proc/Artifact_attackby(obj/item/W as obj, mob/user as mob)
if (istype(W, /obj/item/cargotele)) // Re-added (Convair880).
var/obj/item/cargotele/CT = W
CT.cargoteleport(src, user)
return
if (istype(user,/mob/living/silicon/robot))
src.ArtifactStimulus("silitouch", 1)
if (istype(W,/obj/item/artifact/activator_key))
var/obj/item/artifact/activator_key/ACT = W
if (!src.ArtifactSanityCheck())
return
if (!W.ArtifactSanityCheck())
return
var/datum/artifact/A = src.artifact
var/datum/artifact/K = ACT.artifact
if (K.activated)
if (ACT.universal || A.artitype == K.artitype)
if (ACT.activator && !A.activated)
src.ArtifactActivated()
else if (!ACT.activator && A.activated)
src.ArtifactDeactivated()
else
..()
if (istype(W,/obj/item/weldingtool))
var/obj/item/weldingtool/WELD = W
if (WELD.welding)
WELD.eyecheck(user)
src.ArtifactStimulus("heat", 800)
playsound(src.loc, "sound/items/Welder.ogg", 100, 1)
src.visible_message("<span style=\"color:red\">[user.name] burns the artifact with [WELD]!</span>")
return 0
if (istype(W,/obj/item/zippo))
var/obj/item/zippo/ZIP = W
if (ZIP.lit)
src.ArtifactStimulus("heat", 400)
src.visible_message("<span style=\"color:red\">[user.name] burns the artifact with [ZIP]!</span>")
return 0
if(istype(W,/obj/item/baton))
var/obj/item/baton/BAT = W
if (BAT.can_stun(1, 1, user) == 1)
src.ArtifactStimulus("force", BAT.force)
src.ArtifactStimulus("elec", 1500)
playsound(src.loc, "sound/weapons/Egloves.ogg", 100, 1)
src.visible_message("<span style=\"color:red\">[user.name] beats the artifact with [BAT]!</span>")
BAT.process_charges(-1, user)
return 0
if (W.force)
src.ArtifactStimulus("force", W.force)
return 1
/obj/proc/ArtifactFaultUsed(var/mob/user)
// This is for a tool/item artifact that you can use. If it has a fault, whoever is using it is basically rolling the dice
// every time the thing is used (a check to see if rand(1,faultcount) hits 1 most of the time) and if they're unlucky, the
// thing will deliver it's payload onto them.
// There's also no reason this can't be used whoever the artifact is being used *ON*, also!
if (!src.ArtifactSanityCheck())
return
var/datum/artifact/A = src.artifact
if (!A.faults.len)
return // no faults, so dont waste any more time
if (!A.activated)
return // doesn't make a lot of sense for an inert artifact to go haywire
var/halt = 0
for (var/datum/artifact_fault/F in A.faults)
if (prob(F.trigger_prob))
if (F.halt_loop)
halt = 1
F.deploy(src,user)
if (halt)
break
/obj/proc/ArtifactStimulus(var/stimtype, var/strength = 0)
// This is what will be used for most of the testing equipment stuff. Stimtype is what kind of stimulus the artifact is being
// exposed to (such as brute force, high temperatures, electricity, etc) and strength is how powerful the stimulus is. This
// one here is intended as a master proc with individual items calling back to this one and then rolling their own version of
// it alongside this. This one mainly deals with accidentally damaging an artifact due to hitting it with a poor choice of
// stimulus, such as hitting crystals with brute force and so forth.
if (!stimtype)
return
if (!src.ArtifactSanityCheck())
return
var/turf/T = get_turf(src)
var/datum/artifact/A = src.artifact
// Possible stimuli = force, elec, radiate, heat
switch(A.artitype)
if("martian") // biotech, so anything that'd probably kill a living thing works on them too
if(stimtype == "force")
if (strength >= 30)
T.visible_message("<span style=\"color:red\">[src] bruises from the impact!</span>")
playsound(src.loc, "sound/effects/attackblob.ogg", 100, 1)
ArtifactDevelopFault(33)
src.ArtifactTakeDamage(strength / 1.5)
if(stimtype == "elec")
if (strength >= 3000) // max you can get from the electrobox is 5000
if (prob(10))
T.visible_message("<span style=\"color:red\">[src] seems to quiver in pain!</span>")
src.ArtifactTakeDamage(strength / 1000)
if(stimtype == "radiate")
if (strength >= 6)
ArtifactDevelopFault(50)
if (strength >= 9)
ArtifactDevelopFault(75)
src.ArtifactTakeDamage(strength * 1.25)
if("wizard") // these are big crystals, thus you probably shouldn't smack them around too hard!
if(stimtype == "force")
if (strength >= 20)
T.visible_message("<span style=\"color:red\">[src] cracks and splinters!</span>")
playsound(src.loc, "sound/misc/glass_step.ogg", 100, 1)
ArtifactDevelopFault(80)
src.ArtifactTakeDamage(strength * 1.5)
if (!src || !A)
return
if (!A.activated)
for (var/datum/artifact_trigger/AT in A.triggers)
if (A.activated)
break
if (AT.stimulus_required == stimtype)
if (AT.do_amount_check)
if (AT.stimulus_type == ">=" && strength >= AT.stimulus_amount)
src.ArtifactActivated()
else if (AT.stimulus_type == "<=" && strength <= AT.stimulus_amount)
src.ArtifactActivated()
else if (AT.stimulus_type == "==" && strength == AT.stimulus_amount)
src.ArtifactActivated()
else
if (istext(A.hint_text))
if (strength >= AT.stimulus_amount - AT.hint_range && strength <= AT.stimulus_amount + AT.hint_range)
if (prob(AT.hint_prob))
T.visible_message("<b>[src]</b> [A.hint_text]")
else
src.ArtifactActivated()
/obj/proc/ArtifactTouched(mob/user as mob)
if (istype(user,/mob/living/silicon/ai))
return
if (istype(user,/mob/dead/))
return
var/datum/artifact/A = src.artifact
if (istype(A,/datum/artifact/))
if (istype(user,/mob/living/carbon/))
src.ArtifactStimulus("carbtouch", 1)
if (istype(user,/mob/living/silicon/))
src.ArtifactStimulus("silitouch", 1)
src.ArtifactStimulus("force", 1)
user.visible_message("<b>[user.name]</b> touches [src].")
if (istype(src.artifact,/datum/artifact))
if (A.touch_descriptors.len > 0)
boutput(user, "[pick(A.touch_descriptors)]")
else
boutput(user, "You can't really tell how it feels.")
if (A.activated)
A.effect_touch(src,user)
return
/obj/proc/ArtifactTakeDamage(var/dmg_amount)
if (!src.ArtifactSanityCheck() || !isnum(dmg_amount))
return
var/datum/artifact/A = src.artifact
A.health -= dmg_amount
A.health = max(0,min(A.health,100))
if (A.health <= 0)
src.ArtifactDestroyed()
return
/obj/proc/ArtifactDestroyed()
// Call this rather than straight Del() on an artifact if you want to destroy it. This way, artifacts can have their own
// version of this for ones that will deliver a payload if broken.
if (!src.ArtifactSanityCheck())
return
var/datum/artifact/A = src.artifact
ArtifactLogs(usr, null, src, "destroyed", null, 0)
artifact_controls.artifacts -= src
var/turf/T = get_turf(src)
if (istype(T,/turf/))
switch(A.artitype)
if("ancient")
T.visible_message("<span style=\"color:red\"><B>[src] sparks and sputters violently before falling apart!</B></span>")
if("martian")
T.visible_message("<span style=\"color:red\"><B>[src] bursts open, and rapidly liquefies!</B></span>")
if("wizard")
T.visible_message("<span style=\"color:red\"><B>[src] shatters and disintegrates!</B></span>")
if("eldritch")
T.visible_message("<span style=\"color:red\"><B>[src] warps in on itself and vanishes!</B></span>")
if("precursor")
T.visible_message("<span style=\"color:red\"><B>[src] implodes, crushing itself into dust!</B></span>")
qdel(src)
return
/obj/proc/ArtifactDevelopFault(var/faultprob)
// This proc is used for randomly giving an artifact a fault. It's usually used in the New() proc of an artifact so that
// newly spawned artifacts have a chance of being faulty by default, though this can also be called whenever an artifact is
// damaged or otherwise poorly handled, so you could potentially turn a good artifact into a dangerous piece of shit if you
// abuse it too much.
// I'm probably going to change this one up to use a list of fault datum rather than some kind of variable, that way multiple
// faults can be on one artifact.
if (!isnum(faultprob))
return
if (!src.ArtifactSanityCheck())
return
var/datum/artifact/A = src.artifact
if (A.artitype == "eldritch")
faultprob *= 2 // eldritch artifacts fucking hate you and are twice as likely to go faulty
faultprob = max(0,min(faultprob,100))
if (prob(faultprob) && A.fault_types.len)
var/new_fault = pick(A.fault_types)
if (ispath(new_fault))
var/datum/artifact_fault/F = new new_fault(A)
F.holder = A
A.faults += F
// Added. Very little related to artifacts was logged (Convair880).
/proc/ArtifactLogs(var/mob/user, var/mob/target, var/obj/O, var/type_of_action, var/special_addendum, var/trigger_alert = 0)
if (!O || !istype(O.artifact, /datum/artifact) || !type_of_action)
return
var/datum/artifact/A = O.artifact
if ((target && ismob(target)) && type_of_action == "weapon")
logTheThing("combat", user, target, "attacks %target% with an active artifact ([A.type])[special_addendum ? ", [special_addendum]" : ""] at [log_loc(target)].")
else
logTheThing(type_of_action == "detonated" ? "bombing" : "station", user, target, "an artifact ([A.type]) was [type_of_action] [special_addendum ? "([special_addendum])" : ""] at [target && isturf(target) ? "[log_loc(target)]" : "[log_loc(O)]"].[type_of_action == "detonated" ? " Last touched by: [O.fingerprintslast ? "[O.fingerprintslast]" : "*null*"]" : ""]")
if (trigger_alert)
message_admins("An artifact ([A.type]) was [type_of_action] [special_addendum ? "([special_addendum])" : ""] at [log_loc(O)]. Last touched by: [O.fingerprintslast ? "[O.fingerprintslast]" : "*null*"]")
return
+331
View File
@@ -0,0 +1,331 @@
/obj/artifact
// a totally inert piece of shit that does nothing (alien art)
// might as well use it as the category header for non-machinery artifacts just to be efficient
name = "artifact large art piece"
icon = 'icons/obj/artifacts/artifacts.dmi'
icon_state = "wizard-1" // it's technically pointless to set this but it makes it easier to find in the dreammaker tree
opacity = 0
density = 1
anchored = 0
artifact = 1
mat_changename = 0
mat_changedesc = 0
var/associated_datum = /datum/artifact/art
New(var/loc, var/forceartitype)
var/datum/artifact/AS = new src.associated_datum(src)
if (forceartitype) AS.validtypes = list("[forceartitype]")
src.artifact = AS
spawn(0)
src.ArtifactSetup()
UpdateName()
src.name = "[name_prefix(null, 1)][src.real_name][name_suffix(null, 1)]"
attack_hand(mob/user as mob)
src.ArtifactTouched(user)
return
attack_ai(mob/user as mob)
return attack_hand(user)
attackby(obj/item/W as obj, mob/user as mob)
if (src.Artifact_attackby(W,user))
..()
meteorhit(obj/O as obj)
src.ArtifactStimulus("force", 60)
..()
examine()
set src in oview()
boutput(usr, "You have no idea what this thing is!")
if (!src.ArtifactSanityCheck())
return
var/datum/artifact/A = src.artifact
if (istext(A.examine_hint))
boutput(usr, "[A.examine_hint]")
ex_act(severity)
switch(severity)
if(1.0)
src.ArtifactStimulus("force", 200)
src.ArtifactStimulus("heat", 500)
if(2.0)
src.ArtifactStimulus("force", 75)
src.ArtifactStimulus("heat", 450)
if(3.0)
src.ArtifactStimulus("force", 25)
src.ArtifactStimulus("heat", 380)
return
reagent_act(reagent_id,volume)
if (..())
return
if (!src.ArtifactSanityCheck())
return
var/datum/artifact/A = src.artifact
src.ArtifactStimulus(reagent_id, volume)
switch(reagent_id)
if("radium","porktonium")
src.ArtifactStimulus("radiate", round(volume / 10))
if("polonium","strange_reagent")
src.ArtifactStimulus("radiate", round(volume / 5))
if("uranium")
src.ArtifactStimulus("radiate", round(volume / 2))
if("dna_mutagen","mutagen","omega_mutagen")
if (A.artitype == "martian")
ArtifactDevelopFault(80)
if("napalm","dbreath","el_diablo")
src.ArtifactStimulus("heat", 310 + (volume * 5))
if("infernite","foof","ghostchilijuice")
src.ArtifactStimulus("heat", 310 + (volume * 10))
if("cryostylane")
src.ArtifactStimulus("heat", 310 - (volume * 10))
if("acid")
src.ArtifactTakeDamage(volume * 2)
if("pacid")
src.ArtifactTakeDamage(volume * 10)
if("george_melonium")
var/random_stimulus = pick("heat","force","radiate","elec")
var/random_strength = 0
switch(random_stimulus)
if ("heat")
random_strength = rand(200,400)
if ("elec")
random_strength = rand(5,5000)
if ("force")
random_strength = rand(3,30)
if ("radiate")
random_strength = rand(1,10)
src.ArtifactStimulus(random_stimulus,random_strength)
return
emp_act()
src.ArtifactStimulus("elec", 800)
src.ArtifactStimulus("radiate", 3)
blob_act(var/power)
src.ArtifactStimulus("force", power)
src.ArtifactStimulus("carbtouch", 1)
bullet_act(var/obj/projectile/P)
if(src.material) src.material.triggerOnAttacked(src, P.shooter, src, (ismob(P.shooter) ? P.shooter:equipped() : P.shooter))
for(var/atom/A in src)
if(A.material)
A.material.triggerOnAttacked(A, P.shooter, src, (ismob(P.shooter) ? P.shooter:equipped() : P.shooter))
switch (P.proj_data.damage_type)
if(D_KINETIC,D_PIERCING,D_SLASHING)
src.ArtifactStimulus("force", P.power)
for (var/obj/machinery/networked/test_apparatus/impact_pad/I in src.loc.contents)
I.impactpad_senseforce_shot(src, P)
if(D_ENERGY)
src.ArtifactStimulus("elec", P.power * 10)
if(D_BURNING)
src.ArtifactStimulus("heat", 310 + (P.power * 5))
if(D_RADIOACTIVE)
src.ArtifactStimulus("radiate", P.power)
..()
Bumped(M as mob|obj)
if (istype(M,/obj/item/))
var/obj/item/ITM = M
src.ArtifactStimulus("force", ITM.throwforce)
for (var/obj/machinery/networked/test_apparatus/impact_pad/I in src.loc.contents)
I.impactpad_senseforce(src, ITM)
..()
/obj/machinery/artifact
name = "artifact large art piece"
icon = 'icons/obj/artifacts/artifacts.dmi'
icon_state = "wizard-1" // it's technically pointless to set this but it makes it easier to find in the dreammaker tree
opacity = 0
density = 1
anchored = 0
artifact = 1
mat_changename = 0
mat_changedesc = 0
var/associated_datum = /datum/artifact/art
New(var/loc, var/forceartitype)
..()
var/datum/artifact/AS = new src.associated_datum(src)
if (forceartitype)
AS.validtypes = list("[forceartitype]")
src.artifact = AS
spawn(0)
src.ArtifactSetup()
examine()
set src in oview()
boutput(usr, "You have no idea what this thing is!")
if (!src.ArtifactSanityCheck())
return
var/datum/artifact/A = src.artifact
if (istext(A.examine_hint))
boutput(usr, "[A.examine_hint]")
UpdateName()
src.name = "[name_prefix(null, 1)][src.real_name][name_suffix(null, 1)]"
process()
..()
if (!src.ArtifactSanityCheck())
return
var/datum/artifact/A = src.artifact
if (A.activated)
A.effect_process(src)
attack_hand(mob/user as mob)
src.ArtifactTouched(user)
return
attack_ai(mob/user as mob)
return attack_hand(user)
attackby(obj/item/W as obj, mob/user as mob)
if (src.Artifact_attackby(W,user))
..()
meteorhit(obj/O as obj)
src.ArtifactStimulus("force", 60)
..()
ex_act(severity)
switch(severity)
if(1.0)
src.ArtifactStimulus("force", 200)
src.ArtifactStimulus("heat", 500)
if(2.0)
src.ArtifactStimulus("force", 75)
src.ArtifactStimulus("heat", 450)
if(3.0)
src.ArtifactStimulus("force", 25)
src.ArtifactStimulus("heat", 380)
return
reagent_act(reagent_id,volume)
if (..())
return
if (!src.ArtifactSanityCheck())
return
var/datum/artifact/A = src.artifact
src.ArtifactStimulus(reagent_id, volume)
switch(reagent_id)
if("radium","porktonium")
src.ArtifactStimulus("radiate", round(volume / 10))
if("polonium","strange_reagent")
src.ArtifactStimulus("radiate", round(volume / 5))
if("uranium")
src.ArtifactStimulus("radiate", round(volume / 2))
if("dna_mutagen","mutagen","omega_mutagen")
if (A.artitype == "martian")
ArtifactDevelopFault(80)
if("napalm","dbreath","el_diablo")
src.ArtifactStimulus("heat", 310 + (volume * 5))
if("infernite","foof","ghostchilijuice")
src.ArtifactStimulus("heat", 310 + (volume * 10))
if("cryostylane")
src.ArtifactStimulus("heat", 310 - (volume * 10))
if("acid")
src.ArtifactTakeDamage(volume * 2)
if("pacid")
src.ArtifactTakeDamage(volume * 10)
if("george_melonium")
var/random_stimulus = pick("heat","force","radiate","elec")
var/random_strength = 0
switch(random_stimulus)
if ("heat")
random_strength = rand(200,400)
if ("elec")
random_strength = rand(5,5000)
if ("force")
random_strength = rand(3,30)
if ("radiate")
random_strength = rand(1,10)
src.ArtifactStimulus(random_stimulus,random_strength)
return
emp_act()
src.ArtifactStimulus("elec", 800)
src.ArtifactStimulus("radiate", 3)
blob_act(var/power)
src.ArtifactStimulus("force", power)
src.ArtifactStimulus("carbtouch", 1)
bullet_act(var/obj/projectile/P)
switch (P.proj_data.damage_type)
if(D_KINETIC,D_PIERCING,D_SLASHING)
src.ArtifactStimulus("force", P.power)
if (istype(src.loc,/turf/))
for (var/obj/machinery/networked/test_apparatus/impact_pad/I in src.loc.contents)
I.impactpad_senseforce_shot(src, P)
if(D_ENERGY)
src.ArtifactStimulus("elec", P.power * 10)
if(D_BURNING)
src.ArtifactStimulus("heat", P.power * 5)
if(D_RADIOACTIVE)
src.ArtifactStimulus("radiate", P.power)
..()
Bumped(M as mob|obj)
if (istype(M,/obj/item/))
var/obj/item/ITM = M
src.ArtifactStimulus("force", ITM.throwforce)
for (var/obj/machinery/networked/test_apparatus/impact_pad/I in src.loc.contents)
I.impactpad_senseforce(src, ITM)
..()
/obj/item/artifact
name = "artifact small art piece"
icon = 'icons/obj/artifacts/artifactsitem.dmi'
icon_state = "wizard-1"
artifact = 1
mat_changename = 0
mat_changedesc = 0
var/associated_datum = /datum/artifact/art
New(var/loc, var/forceartitype)
var/datum/artifact/AS = new src.associated_datum(src)
if (forceartitype)
AS.validtypes = list("[forceartitype]")
src.artifact = AS
spawn(0)
src.ArtifactSetup()
examine()
set src in oview()
boutput(usr, "You have no idea what this thing is!")
if (!src.ArtifactSanityCheck())
return
var/datum/artifact/A = src.artifact
if (istext(A.examine_hint))
boutput(usr, "[A.examine_hint]")
UpdateName()
src.name = "[name_prefix(null, 1)][src.real_name][name_suffix(null, 1)]"
attackby(obj/item/W as obj, mob/user as mob)
if (src.Artifact_attackby(W,user))
..()
/obj/artifact_spawner
// pretty much entirely for debugging/gimmick use
New(var/loc,var/forceartitype = null,var/cinematic = 0)
var/turf/T = get_turf(src)
if (cinematic)
T.visible_message("<span style=\"color:red\"><b>An artifact suddenly warps into existance!</b></span>")
playsound(T,"sound/effects/teleport.ogg",50,1)
var/obj/decal/teleport_swirl/swirl = unpool(/obj/decal/teleport_swirl)
swirl.set_loc(T)
spawn(15)
pool(swirl)
Artifact_Spawn(T,forceartitype)
qdel(src)
return
+154
View File
@@ -0,0 +1,154 @@
// FAULTS
/datum/artifact_fault
// these are booby traps, self-defense mechanisms, hardware faults or just other nasty shit that can fuck you up when you
// use the artifact for anything
var/trigger_prob = 0
var/tmp/datum/artifact/holder = null
var/halt_loop = 0
proc/deploy(var/obj/O,var/mob/living/user)
if (!O || !user)
return 1
return 0
/datum/artifact_fault/burn
// sets the victim on fire
trigger_prob = 8
var/burn_amount = 40
deploy(var/obj/O,var/mob/living/user)
if (..())
return
var/turf/T = get_turf(user)
T.visible_message("<span style=\"color:red\">The [O.name] suddenly bursts into flames!</span>")
user.update_burning(40)
playsound(T, "sound/effects/bamf.ogg", 100, 1)
/datum/artifact_fault/irradiate
// irradiates the victim
trigger_prob = 8
var/rads_amount = 20
deploy(var/obj/O,var/mob/living/user)
if (..())
return
boutput(user, "<span style=\"color:red\">You feel strange.</span>")
user.irradiate(src.rads_amount)
/datum/artifact_fault/shutdown
// deactivates the artifact
trigger_prob = 10
halt_loop = 1
deploy(var/obj/O,var/mob/living/user)
if (..())
return
var/turf/T = get_turf(O)
T.visible_message("<span style=\"color:red\">The [O.name] suddenly deactivates!</span>")
playsound(T, "sound/effects/shielddown2.ogg", 100, 1)
O.ArtifactDeactivated()
/datum/artifact_fault/warp
// warps the user off somewhere random
trigger_prob = 15
deploy(var/obj/O,var/mob/living/user)
if (..())
return
var/turf/T = get_turf(O)
T.visible_message("<span style=\"color:red\">The [O.name] warps [user.name] away!</span>")
playsound(T, "sound/effects/mag_warp.ogg", 100, 1)
user.set_loc(pick(wormholeturfs))
/datum/artifact_fault/murder
// gibs the user
trigger_prob = 1
halt_loop = 1
deploy(var/obj/O,var/mob/living/user)
if (..())
return
if (istype(src,/obj/item/))
var/obj/item/I = src
if (I.loc == user)
user.u_equip(I)
I.dropped()
var/turf/T = get_turf(O)
T.visible_message("<span style=\"color:red\"><b>The [O.name] utterly annihilates [user.name]!</b></span>")
playsound(T, "sound/effects/elec_bigzap.ogg", 100, 1)
user.elecgib()
/datum/artifact_fault/explode
// causes an explosion and destroys the artifact
trigger_prob = 1
halt_loop = 1
deploy(var/obj/O,var/mob/living/user)
if (..())
return
var/turf/T = get_turf(O)
T.visible_message("<span style=\"color:red\">The [O.name] suddenly explodes!</span>")
if (istype(src,/obj/item/))
var/obj/item/I = src
user.u_equip(I)
I.dropped()
explosion(O, T, 1, 2, 4, 8)
O.ArtifactDestroyed()
/datum/artifact_fault/zap
// electrocutes the user
trigger_prob = 6
deploy(var/obj/O,var/mob/living/user)
if (..())
return
var/turf/T = get_turf(O)
T.visible_message("<span style=\"color:red\"><b>[user.name]</b> is shocked by a surge of energy from [O.name]!</span>")
var/datum/effects/system/spark_spread/s = unpool(/datum/effects/system/spark_spread)
s.set_up(4, 1, user)
s.start()
user.stunned += 15
user.weakened += 15
user.stuttering += 30
/datum/artifact_fault/messager
trigger_prob = 30
var/text_style = null
var/list/messages = list()
deploy(var/obj/O,var/mob/living/user)
if (..())
return
if (messages.len < 1)
return
switch(text_style)
if ("small")
boutput(user, "<small>[pick(messages)]</small>")
if ("big")
boutput(user, "<big>[pick(messages)]</big>")
if ("red")
boutput(user, "<span style=\"color:red\">[pick(messages)]</span>")
if ("blue")
boutput(user, "<span style=\"color:blue\">[pick(messages)]</span>")
else
boutput(user, "[pick(messages)]")
/datum/artifact_fault/messager/creepy_whispers
text_style = "small"
messages = list("its your fault","theyre going to get you","no escape","youre going to die here","no hope",
"die","stop","give up","no","theyre watching you","theres nothing you can do","you have failed","run","i see you",
"surrender","its hopeless","you are in hell","its all lies","hate","there is only despair","your heart will stop",
"they will all forget you","they have abandoned you","please stop","no one will mourn you")
/datum/artifact_fault/poison
trigger_prob = 8
var/poison_type = "toxin"
var/poison_amount = 10
deploy(var/obj/O,var/mob/living/user)
if (..())
return
boutput(user, "<span style=\"color:red\">The [O.name] stings you!</span>")
if (user.reagents)
user.reagents.add_reagent(poison_type,poison_amount)
+73
View File
@@ -0,0 +1,73 @@
// TRIGGERS
/datum/artifact_trigger
var/stimulus_required = null
var/do_amount_check = 1
var/stimulus_amount = null
var/stimulus_type = ">="
var/hint_range = 0
var/hint_prob = 33
/datum/artifact_trigger/carbon_touch
// touched by a carbon lifeform
stimulus_required = "carbtouch"
do_amount_check = 0
/datum/artifact_trigger/silicon_touch
// touched by a silicon lifeform
stimulus_required = "silitouch"
do_amount_check = 0
/datum/artifact_trigger/force
stimulus_required = "force"
hint_range = 20
hint_prob = 75
New()
stimulus_amount = rand(3,30)
/datum/artifact_trigger/heat
stimulus_required = "heat"
hint_range = 20
New()
stimulus_amount = rand(320,400)
/datum/artifact_trigger/cold
stimulus_required = "heat"
stimulus_type = "<="
hint_range = 20
New()
stimulus_amount = rand(200,300)
/datum/artifact_trigger/radiation
stimulus_required = "radiate"
hint_range = 2
hint_prob = 75
New()
stimulus_type = pick(">=","<=")
stimulus_amount = rand(1,10)
/datum/artifact_trigger/electric
stimulus_required = "elec"
hint_range = 500
hint_prob = 66
New()
stimulus_type = pick(">=","<=")
stimulus_amount = rand(5,5000)
/datum/artifact_trigger/reagent
stimulus_required = "reagent"
// can just use the above var as the required reagent field really
stimulus_type = ">="
hint_range = 50
hint_prob = 100
New()
stimulus_amount = rand(10,100)
/datum/artifact_trigger/reagent/blood
stimulus_required = "blood"
+1203
View File
File diff suppressed because it is too large Load Diff
+86
View File
@@ -0,0 +1,86 @@
/obj/construction_frame
icon = 'icons/obj/construction_frame.dmi'
anchored = 0
density = 1
proc/updateicon()
/obj/item/circuit // not to be confused with /obj/item/circuitboard (i'll merge these someday okay)
name = "circuit board"
icon = 'icons/obj/module.dmi'
smes
name = "SMES control circuit"
icon_state = "smes"
/obj/construction_frame/smes
name = "SMES frame"
desc = "An unfinished SMES."
icon_state = "smes0"
var/obj/item/coil/large/coil
var/obj/item/circuit/circuitboard
var/circuit_secured = 0
var/wired = 0
updateicon()
if (!coil)
icon_state = "smes0"
else if (!circuitboard)
icon_state = "smes2"
else if (!wired)
icon_state = "smes3"
else
icon_state = "smes4"
attackby(obj/item/W, mob/user)
if (!coil)
if (istype(W, /obj/item/coil/large))
playsound(src.loc, "sound/items/Deconstruct.ogg", 50, 1)
user.drop_item()
W.loc = src
coil = W
boutput(user, "<span style=\"color:blue\">You insert the coil.</span>")
else if (!circuitboard)
if (istype(W, /obj/item/circuit/smes))
playsound(src.loc, "sound/items/Deconstruct.ogg", 50, 1)
user.drop_item()
W.loc = src
circuitboard = W
circuit_secured = 0
boutput(user, "<span style=\"color:blue\">You insert the control circuitry.</span>")
else if (!circuit_secured)
if (istype(W, /obj/item/screwdriver))
playsound(src.loc, "sound/items/Screwdriver.ogg", 50, 1)
circuit_secured = 1
boutput(user, "<span style=\"color:blue\">You secure the control circuitry.</span>")
else if (!wired)
if (istype(W, /obj/item/cable_coil))
var/obj/item/cable_coil/coil = W
if (coil.amount >= 5)
playsound(src.loc, "sound/items/Deconstruct.ogg", 50, 1)
coil.amount -= 5
if (!coil.amount)
qdel(coil)
wired = 1
boutput(user, "<span style=\"color:blue\">You wire up the circuitry.</span>")
else
boutput(user, "<span style=\"color:blue\">You're going to need more cable for this.</span>")
else
if (istype(W, /obj/item/sheet))
var/obj/item/sheet/sheet = W
if (!sheet.material)
boutput(user, "<span style=\"color:blue\">This kind of sheets wont work!</span>")
return
if (sheet.amount >= 3)
playsound(src.loc, "sound/items/Deconstruct.ogg", 50, 1)
sheet.amount -= 3
if (!sheet.amount)
qdel(sheet)
boutput(user, "<span style=\"color:blue\">You add the outer shell.</span>")
var/obj/machinery/power/smes/smes = new(src.loc)
smes.setMaterial(sheet.material)
qdel(src)
else
boutput(user, "<span style=\"color:blue\">You're going to need more sheets for this.</span>")
src.updateicon()
+106
View File
@@ -0,0 +1,106 @@
/obj/critter/alien/larva
name = "alien larva"
icon_state = "larva" // icon_state = "larva_l" - dead
dead_state = "larva_l"
health = 10
aggressive = 0
defensive = 1
var/amount_grown = 0
desc = "You know, it'd be kind of cute if it wasn't trying to eat you."
process() //overriding default sleeping behavior
if (!src.alive) // and completely ruining their ability to die by not including some very important bits I guess
return 0
check_health()
src.amount_grown++
if(amount_grown >= 100)
new /obj/critter/alien/humanoid( src.loc )
qdel(src)
else
ai_think()
/obj/critter/alien/humanoid
density = 1
/obj/critter/alien
name = "Alien"
desc = "An alien."
icon_state = "alien"
density = 1
anchored = 0
health = 40
aggressive = 1
defensive = 0
wanderer = 1
opensdoors = 1
atkcarbon = 1
atksilicon = 1
firevuln = 1
brutevuln = 1
atcritter = 1
seek_target()
if (!src.alive) return
src.anchored = 0
for (var/mob/living/C in hearers(src.seekrange,src))
if ((C.name == src.oldtarget_name) && (world.time < src.last_found + 100)) continue
if (iscarbon(C) && !src.atkcarbon) continue
//if(isalien(C)) continue
if (istype(C, /mob/living/silicon/) && !src.atksilicon) continue
if (C.health < 0) continue
if (C.name == src.attacker) src.attack = 1
if (iscarbon(C) && src.atkcarbon) src.attack = 1
if (istype(C, /mob/living/silicon/) && src.atksilicon) src.attack = 1
if (src.attack)
src.target = C
src.oldtarget_name = C.name
src.visible_message("<span class='combat'><b>[src]</b> charges at [C:name]!</span>")
src.task = "chasing"
return
else
continue
if(!src.atcritter) return
for (var/obj/critter/C in view(src.seekrange,src))
if (!C.alive) continue
if (C.health < 0) continue
if (!istype(C, /obj/critter/alien)) src.attack = 1
if (src.attack)
src.target = C
src.oldtarget_name = C.name
src.visible_message("<span class='combat'><b>[src]</b> lunges at [C.name]!</span>")
src.task = "chasing"
return
else continue
CritterAttack(mob/M)
src.attacking = 1
if(istype(M,/obj/critter))
var/obj/critter/C = M
src.visible_message("<span class='combat'><B>[src]</B> claws [src.target]!</span>")
playsound(C.loc, "punch", 25, 1, -1)
C.health -= 10
if(C.health <= 0)
C.CritterDeath()
spawn(15)
src.attacking = 0
return
src.visible_message("<span class='combat'><B>[src]</B> claws at [src.target]!</span>")
random_brute_damage(src.target, rand(5,10))
spawn(10)
src.attacking = 0
ChaseAttack(mob/M)
src.visible_message("<span class='combat'><B>[src]</B> jumps at [M]!</span>")
if(iscarbon(M))
if (prob(60)) M.stunned += rand(1,5)
random_brute_damage(M, rand(2,5))
+418
View File
@@ -0,0 +1,418 @@
/////// cogwerks spooky automaton thing that kinda just sits there being weird and ominous
var/global/the_automaton = null
#define AUTOMATON_MAX_KEYS 7
/obj/critter/automaton
name = "automaton"
desc = "What is this thing? A toy? A machine? What is it doing? Why does it seem to be watching you?"
icon_state = "automaton"
health = 1000 // what kind of jerk would kill it
anchored = 1
aggressive = 0
defensive = 0
wanderer = 0
opensdoors = 0
atkcarbon = 0
atksilicon = 0
firevuln = 0.5
brutevuln = 1
generic = 0
var/atom/admiring_target = null
var/keycount = 0
var/vacation = 0
var/pied = 0
var/saw_moon_bee = 0
var/sun_spin = 0
var/spin_lock = null // for making sure the sun keeps spinning in the direction it's already going
var/got_cheget_key = 0 // Don't keep handing me this you fuck
New()
..()
spawn (10)
if (!the_automaton)
the_automaton = src
disposing()
if (the_automaton == src)
the_automaton = null
..()
Del()
if (the_automaton == src)
the_automaton = null
..()
angry
aggressive = 1
atkcarbon = 1
atksilicon = 1
wanderer = 1
opensdoors = 1
CritterAttack(mob/M)
src.attacking = 1
src.visible_message("<span style=\"color:red\"><B>[src]</B> smashes [src.target]!</span>")
random_brute_damage(src.target, rand(5,15))
playsound(src.loc, "sound/misc/automaton_spaz.ogg", 50, 1)
spawn(10)
src.attacking = 0
process()
if(!..())
return 0
if (!alive)
return
if (prob(6))
playsound(src.loc, "sound/misc/automaton_tickhum.ogg", 60, 1)
if (!src.muted)
src.visible_message("<span style=\"color:red\"><b>[src] emits [pick("a soft", "a quiet", "a curious", "an odd", "an ominous", "a strange", "a forboding", "a peculiar", "a faint")] [pick("ticking", "tocking", "humming", "droning", "clicking")] sound.</span>")
if (prob(6))
playsound(src.loc, "sound/misc/automaton_ratchet.ogg", 60, 1)
if (!src.muted)
src.visible_message("<span style=\"color:red\"><b>[src] emits [pick("a peculiar", "a worried", "a suspicious", "a reassuring", "a gentle", "a perturbed", "a calm", "an annoyed", "an unusual")] [pick("ratcheting", "rattling", "clacking", "whirring")] noise.</span>")
if (prob(5))
playsound(src.loc, "sound/misc/automaton_spaz.ogg", 50, 1)
spin()
if ((src.aggressive || prob(6)) && locate(/obj/critter/domestic_bee) in view(7,src))
for (var/obj/critter/domestic_bee/moonbeeMaybe in view(7, src))
if (moonbeeMaybe.desc == "A moon bee. It's like a regular space bee, but it has a peculiar gleam in its eyes...") //Because bee names are customizable, but desc isn't!
src.visible_message("<span style=\"color:red\"><b>[src]</b> [pick("points at", "stares at", "gesticulates at", "madly gestures towards")] [moonbeeMaybe]!</span>")
if (!saw_moon_bee)
saw_moon_bee = 1
if (saw_moon_bee == 1 && keycount == INFINITY && !aggressive)
ending_event()
if (moonbeeMaybe.alive && prob(75))
if (!moonbeeMaybe.muted)
moonbeeMaybe.visible_message("<span style=\"color:red\"><b>[moonbeeMaybe]</b> buzzes [pick("grumpily","in a confused manner", "excitedly")] at [src]!</span>")
return
else if (moonbeeMaybe.desc == "A sun bee. It's like a regular space bee, but it has a look of fiery passion. Passion for doing bee stuff.") //Oh, it's the sun bee
if (src.aggressive)
src.visible_message("<span style=\"color:red\"><b>[src]</b> sees [moonbeeMaybe] and seems to calm down. Phew!</span>")
src.aggressive = 0
src.attacking = 0
src.atkcarbon = 0
src.atksilicon = 0
saw_moon_bee = 2
src.visible_message("<span style=\"color:red\"><b>[src]</b> [pick("points at", "stares at", "gesticulates at", "madly gestures towards")] [moonbeeMaybe]!</span>")
if (moonbeeMaybe.alive && prob(75))
if (!moonbeeMaybe.muted)
moonbeeMaybe.visible_message("<span style=\"color:red\"><b>[moonbeeMaybe]</b> buzzes [pick("grumpily","in a confused manner", "excitedly")] at [src]!</span>")
return
if (prob(5)) // adapted chunk of peeker code
var/list/mobsnearby = list()
for (var/mob/M in view(7,src))
mobsnearby.Add("[M.name]")
var/mob/M1 = null
if (mobsnearby.len > 0) // somehow this returned a blank list once wtf
M1 = pick(mobsnearby)
if (M1 && prob(50)) // do we see anyone
if (!src.muted)
src.visible_message("<span style=\"color:red\"><b>[src]</b> stares at [M1].</span>")
else
var/area/current_loc = get_area(src)
switch (current_loc.type)
if (/area/solarium)
src.dir = 4
if (!src.muted)
src.visible_message("<span style=\"color:red\"><b>[src]</b> stares into the sun.</span>")
if (/area/station/engine/core)
if (!admiring_target)
for (var/obj/machinery/power/generatorTemp/G in range(7, src))
admiring_target = G
break
var/obj/machinery/power/generatorTemp/G = admiring_target
if (istype(G) && G.lastgenlev >= 26)
src.dir = get_dir(src, G)
src.visible_message("<span style=\"color:red\"><b>[src]</b> [pick("stares","gazes","glares","looks")] [pick("alluringly", "enticingly", "lovingly", "fanatically", "zealously", "warmly", "obediently", "calmly")] at the [G.name].</span>")
proc/spin()
if (!src.muted)
src.visible_message("<span style=\"color:red\"><b>[src]</b> [pick("turns", "pivots", "twitches", "spins")].</span>")
src.dir = pick(alldirs)
proc/inserted_key()
switch (keycount)
if (2)
for (var/mob/M in range(5))
M.flash(30)
random_events.force_event("Solar Flare","Solarium Event (2 keys)")
if (4)
for (var/mob/M in range(5))
M.flash(30)
random_events.force_event("Radiation Storm","Solarium Event (4 keys)")
if (6)
for (var/mob/M in range(5))
M.flash(30)
random_events.force_event("Solar Flare","Solarium Event (6 keys)")
attackby(obj/item/W as obj, mob/living/user as mob)
if (!alive)
return ..()
if (aggressive)
return ..()
if (istype(W, /obj/item/device/key))
if (keycount >= AUTOMATON_MAX_KEYS)
boutput(user, "<span style=\"color:red\"><b>[src]</b> ignores you. Perhaps the time for that has passed?</span>")
return
user.visible_message("<span style=\"color:red\">[user] hands [W] to [src]!</span>", "You hand [W] to [src].")
if (istype(W, /obj/item/device/key/skull) && W.icon_state == "bloodyskull")
src.visible_message("<span style=\"color:red\"><b>[src]</b> studies [W] intently for a while, then hands it back. It doesn't seem to want it in the state it's in.</span>")
return
if (istype(W, /obj/item/reagent_containers/food/snacks/pizza) && W.name == "cheese keyzza") // vOv
src.visible_message("<span style=\"color:red\"><b>[src]</b> studies [W] intently for a while, then hands it back.</span>")
return
if (istype(W, /obj/item/device/key/cheget)) //I don' like yer new-fangled mumbo-jumbo
user.u_equip(W)
W.dropped(user)
W.loc = src
src.visible_message("<span style=\"color:red\"><b>[src]</b> takes \the [W] and studies it intently for a moment.</span>")
sleep(30)
if (!got_cheget_key)
got_cheget_key = 1
src.visible_message("<span style=\"color:red\"><B>[src]</B> clacks angrily and throws \the [W] at [user]!</span>")
playsound(src.loc, "sound/misc/automaton_spaz.ogg", 60, 1)
W.loc = src.loc
W.throw_at(user, 20, 2)
else
src.visible_message("<span style=\"color:red\"><B>[src]</B> makes a loud ratcheting noise and crumples up \the [W]!</span>")
playsound(src.loc, "sound/effects/thunk.ogg", 60, 1)
new /obj/item/raw_material/scrap_metal(src.loc)
qdel(W)
return
if (istype(W, /obj/item/device/key/filing_cabinet))
boutput(user, "<span style=\"color:red\"><B>[src]</B> ignores you. This may be related to their lack of circular key holes.")
return
if (istype(W, /obj/item/device/key/hospital))
user.visible_message("<span style=\"color:red\"><b>[src]</b> studies [src]'s open hand for a moment, then looks disappointed.</span>", "<span style=\"color:red\"><b>[src]</b> studies [W] intently for a moment, then hands it back. Maybe it's not yet time?</span>")
return
//Normal keys below
if (dd_hasprefix(ckey(W.name), "iridium"))
if (keycount < (AUTOMATON_MAX_KEYS-1))
src.visible_message("<span style=\"color:red\"><b>[src]</b> studies [W] intently for a moment, then hands it back. Maybe it's not yet time?</span>")
else
keycount = AUTOMATON_MAX_KEYS
src.visible_message("<span style=\"color:red\"><b>[src]</b> studies [W] intently for a moment, before secreting it away into a central key hole in its chest.</span>")
playsound(src.loc, "sound/effects/thunk.ogg", 60, 1)
playsound(src.loc, "sound/effects/gong_rumble.ogg", 60, 1)
qdel(W)
sleep(5)
playsound(src.loc, "sound/misc/automaton_spaz.ogg", 60, 1)
sleep(8)
src.visible_message("<span style=\"color:red\"><b>[src]</b> twitches before locking into a pose of contemplation. Its hand held before it, as if reading from a text.</span>")
else if (dd_hasprefix(ckey(W.name), "lead"))
src.visible_message("<span style=\"color:red\"><b>[src]</b> studies [W] intently for a moment, then hands it back. Maybe the material is off?</span>")
return
else if (dd_hasprefix(ckey(W.name), "solar"))
keycount = AUTOMATON_MAX_KEYS
src.visible_message("<span style=\"color:red\"><b>[src]</b> studies [W] intently for a moment, before secreting it away into a central key hole in its chest.</span>")
playsound(src.loc, "sound/effects/thunk.ogg", 60, 1)
playsound(src.loc, "sound/effects/gong_rumble.ogg", 60, 1)
qdel(W)
sleep(5)
playsound(src.loc, "sound/misc/automaton_spaz.ogg", 60, 1)
sleep(8)
src.visible_message("<span style=\"color:red\"><b>[src]</b> makes a curious sign in the air. Huh.</span>")
for (var/mob/M in range(5))
M.flash(30)
//var/obj/overlay/the_sun = locate("the_sun")
//if (istype(the_sun))
if (the_sun)
var/obj/Sun = the_sun
Sun.icon_state = "sun"
Sun.desc = "Hey, it looks better again!"
sleep(8)
src.visible_message("<span style=\"color:red\"><b>[src]</b> tips over.</span>")
src.health = 0
src.CritterDeath() // rip
else
keycount = min(keycount+1, AUTOMATON_MAX_KEYS-1)
src.visible_message("<span style=\"color:red\"><b>[src]</b> studies [W] intently for a moment, before secreting it away into one of many key holes in its chest.</span>")
playsound(src.loc, "sound/effects/thunk.ogg", 60, 1)
playsound(src.loc, "sound/effects/gong_rumble.ogg", 60, 1)
qdel (W)
sleep(5)
inserted_key()
playsound(src.loc, "sound/misc/automaton_spaz.ogg", 60, 1)
else if (istype(W, /obj/item/reagent_containers/food/snacks/pie/lime) && keycount < AUTOMATON_MAX_KEYS)
user.visible_message("<span style=\"color:red\">[user] hands [W] to [src]!</span>", "You hand [W] to [src].")
if (keycount < (AUTOMATON_MAX_KEYS-1) && !pied)
keycount++
inserted_key()
pied = 1
src.visible_message("<span style=\"color:red\"><b>[src]</b> studies [W] intently for a moment, before secreting it away into a pie-shaped hole in its chest. How did you not notice that before?</span>")
playsound(src.loc, "sound/effects/gong_rumble.ogg", 50, 1)
qdel (W)
else if (istype(W, /obj/item/skull))
if (keycount != AUTOMATON_MAX_KEYS)
user.visible_message("<span style=\"color:red\"><b>[src]</b> ignores [user]. Perhaps it's not time for that?</span>",\
"<span style=\"color:red\"><b>[src]</b> ignores you. Perhaps it's not time for that?</span>")
return
if (!istype(W, /obj/item/skull/crystal) || W.icon_state != "skull_crystal")
src.visible_message("<span style=\"color:red\"><b>[src]</b> holds [W] out for a moment, staring into its empty face, then hands it back </span>")
return
src.visible_message("<span style=\"color:red\"><b>[src]</b> holds [W] out, staring into its empty eye sockets.<br>Alas, poor Yorick?</span>")
qdel(W)
//todo: good ending???? egg ending????
else if (istype(W, /obj/item/iomoon_key))
user.visible_message("<span style=\"color:red\"><b>[src]</b> totally ignores [user]. Maybe this is the wrong puzzle for [W] or something, sheesh.</span>",\
"<span style=\"color:red\">Okay, no. Good thought, but this is totally the wrong puzzle for that.</span>")
else if (istype(W, /obj/item/alchemy/stone))
src.visible_message("<span style=\"color:red\">[src] studies [W] intently. It looks impressed, but hands [W] back. Perhaps it's not the right time for this yet?</span>")
else if (istype(W, /obj/item/onyxphoto))
if (!W:used)
src.visible_message("<span style=\"color:blue\"><b>[src]</b> studies [W] intently, then hands it back after a short pause.</span>")
W:used = 1
W.name = "empty photo"
W.desc = "The key seems to be gone from the photo."
if (keycount < (AUTOMATON_MAX_KEYS-1))
keycount++
inserted_key()
playsound(src.loc, "sound/effects/gong_rumble.ogg", 60, 1)
else
boutput(user, "<span style=\"color:red\">[src] no longer seems interested in [W].</span>")
else if (istype(W, /obj/item/space_thing)) // if I'm gunna make a weird widget it may as well have some interaction with the automaton
var/obj/item/space_thing/ST = W
if (ST.icon_state == "thing")
src.visible_message("<span style=\"color:red\">[src] studies [ST] for a moment. It rotates it, and then hands it back.</span>")
ST.icon_state = "thing2"
//var/obj/overlay/the_sun = locate("the_sun")
//if (istype(the_sun))
if (the_sun)
if (!src.spin_lock)
src.spin_lock = pick("L", "R")
DEBUG("<B>HAINE DEBUG:</b> spin set to [src.spin_lock]")
var/final_spin = 1000 - min(src.sun_spin, 999)
DEBUG("<B>HAINE DEBUG:</b> final spin set to [final_spin]")
animate_spin(the_sun, src.spin_lock, final_spin, -1)
if (src.sun_spin >= 990)
src.sun_spin += 1
DEBUG("<B>HAINE DEBUG:</b> spin now [src.sun_spin]")
else if (src.sun_spin >= 900)
src.sun_spin += 10
DEBUG("<B>HAINE DEBUG:</b> spin now [src.sun_spin]")
else
src.sun_spin += 100
DEBUG("<B>HAINE DEBUG:</b> spin now [src.sun_spin]")
else
user.visible_message("<span style=\"color:red\">[src] studies [ST] for a moment. It hands it back.</span>")
else if (istype(W, /obj/item/book_kinginyellow))
if (keycount < AUTOMATON_MAX_KEYS || derelict_mode)
user.visible_message("<span style=\"color:red\"><b>[src]</b> ignores [user]'s attempts to hand over the book, even if \he waves it right in its face and get all obnoxious about it. Maybe this isn't the right time?</span>",\
"<span style=\"color:red\"><b>[src]</b> ignores your attempts to hand over the book, even if you wave it right in its face and get all obnoxious about it. Maybe this isn't the right time?</span>")
return
user.visible_message("<span style=\"color:red\">[user] hands [W] to [src]!</span>", "You hand [W] to [src].")
src.visible_message("<span style=\"color:red\"><b>[src]</b> appears to read from [W].</span>")
user.drop_item()
W.set_loc(src)
sleep(10)
playsound(src.loc, 'sound/weapons/genhit3.ogg', 50, 1)
src.visible_message("<span style=\"color:red\"><b>[src] frantically tears [W] to pieces! What!</b></span>")
if (narrator_mode)
playsound(src.loc, 'sound/vox/ghost.ogg', 60, 1)
else
playsound(src.loc, 'sound/effects/ghost.ogg', 60, 1)
spawn(0)
var/i = rand(4,8)
while (i-- > 0)
var/obj/item/paper/tornpaper = new /obj/item/paper(src.loc)
tornpaper.name = "torn page"
tornpaper.info = "A page torn from a book. Most of the text is illegible."
sleep(3)
tornpaper.combust()
keycount = INFINITY
world << sound('sound/effects/gong_rumble.ogg')
//var/obj/overlay/the_sun = locate("the_sun")
//if (istype(the_sun))
if (the_sun)
var/obj/Sun = the_sun
Sun.icon_state = "sun_ripple"
Sun.desc = "Uhhh...."
if (W)
for (var/mob/living/carbon/C in hearers(src.seekrange,src))
W:readers += C
if (saw_moon_bee == 1)
ending_event()
else
return ..()
proc/ending_event()
if (saw_moon_bee == 2)
return
saw_moon_bee = 2
var/turf/target_turf = locate(src.x - 1, src.y, src.z)
var/obj/decal/teleport_swirl/swirl = unpool(/obj/decal/teleport_swirl)
swirl.set_loc(target_turf)
swirl.pixel_y = 10
playsound(target_turf, "sound/effects/teleport.ogg", 50, 1)
spawn(15)
swirl.pixel_y = 0
pool(swirl)
src.visible_message("<span style=\"color:red\">[src.name] seems to tense up and freeze.</span>")
playsound(src.loc, "sound/machines/glitch1.ogg", 50, 1)
alive = 0
it_is_okay_to_do_the_endgame_thing = 1
if(!src.vacation)
new /obj/the_server_ingame_whoa(target_turf)
else
new /obj/item/sticker/gold_star(target_turf)
src.visible_message("<span style=\"color:red\">[src.name] looks very annoyed. It just wanted to relax!</span>")
#undef AUTOMATON_MAX_KEYS
alohamaton
icon_state = "alohamaton"
vacation = 1
/obj/item/paper/postcard
name = "postcard"
info = "<font face='Comic Sans MS' color='#F75AA4' size=5><b>Wish you were here!</b></font>"
icon_state = "postcard"
File diff suppressed because it is too large Load Diff
+421
View File
@@ -0,0 +1,421 @@
/obj/critter/bear
name = "space bear"
desc = "WOORGHHH"
icon_state = "abear"
health = 60
aggressive = 1
defensive = 1
wanderer = 1
opensdoors = 0
atkcarbon = 1
atksilicon = 1
butcherable = 1
var/loveometer = 0
var/left_arm_stage = 0
var/right_arm_stage = 0
var/obj/item/parts/human_parts/arm/left/bear/left_arm
var/obj/item/parts/human_parts/arm/right/bear/right_arm
skinresult = /obj/item/material_piece/cloth/leather
max_skins = 2
New()
..()
src.left_arm = new /obj/item/parts/human_parts/arm/left/bear(src)
src.right_arm = new /obj/item/parts/human_parts/arm/right/bear(src)
on_revive()
if (!src.left_arm)
src.left_arm = new /obj/item/parts/human_parts/arm/left/bear(src)
src.left_arm_stage = 0
src.visible_message("<span style=\"color:red\">[src]'s left arm regrows!</span>")
if (!src.right_arm)
src.right_arm = new /obj/item/parts/human_parts/arm/right/bear(src)
src.right_arm_stage = 0
src.visible_message("<span style=\"color:red\">[src]'s right arm regrows!</span>")
..()
CritterDeath()
if (!alive)
return
..()
src.update_dead_icon()
proc/update_dead_icon()
if (src.alive)
return
. = initial(icon_state)
if (!src.left_arm)
. += "-l"
if (!src.right_arm)
. += "-r"
. += "-dead"
icon_state = .
attackby(obj/item/W as obj, mob/living/user as mob)
if (!src.alive)
// TODO: tie this into surgery()
if (istype(W, /obj/item/scalpel))
if (user.zone_sel.selecting == "l_arm")
if (src.left_arm_stage == 0)
user.visible_message("<span class='combat'>[user] slices through the skin and flesh of [src]'s left arm with [W].</span>", "<span style=\"color:red\">You slice through the skin and flesh of [src]'s left arm with [W].</span>")
src.left_arm_stage++
else if (src.left_arm_stage == 2)
user.visible_message("<span class='combat'>[user] cuts through the remaining strips of skin holding [src]'s left arm on with [W].</span>", "<span style=\"color:red\">You cut through the remaining strips of skin holding [src]'s left arm on with [W].</span>")
src.left_arm_stage++
var/turf/location = get_turf(src)
if (location)
src.left_arm.set_loc(location)
src.left_arm = null
src.update_dead_icon()
else if (user.zone_sel.selecting == "r_arm")
if (src.right_arm_stage == 0)
user.visible_message("<span class='combat'>[user] slices through the skin and flesh of [src]'s right arm with [W].</span>", "<span style=\"color:red\">You slice through the skin and flesh of [src]'s right arm with [W].</span>")
src.right_arm_stage++
else if (src.right_arm_stage == 2)
user.visible_message("<span class='combat'>[user] cuts through the remaining strips of skin holding [src]'s right arm on with [W].</span>", "<span style=\"color:red\">You cut through the remaining strips of skin holding [src]'s right arm on with [W].</span>")
src.right_arm_stage++
var/turf/location = get_turf(src)
if (location)
src.right_arm.set_loc(location)
src.right_arm = null
src.update_dead_icon()
else if (istype(W, /obj/item/circular_saw))
if (user.zone_sel.selecting == "l_arm")
if (src.left_arm_stage == 1)
user.visible_message("<span class='combat'>[user] saws through the bone of [src]'s left arm with [W].</span>", "<span style=\"color:red\">You saw through the bone of [src]'s left arm with [W].</span>")
src.left_arm_stage++
else if (user.zone_sel.selecting == "r_arm")
if (src.right_arm_stage == 1)
user.visible_message("<span class='combat'>[user] saws through the bone of [src]'s right arm with [W].</span>", "<span style=\"color:red\">You saw through the bone of [src]'s right arm with [W].</span>")
src.right_arm_stage++
else
..()
return
else
..()
CritterAttack(mob/M)
if(ismob(M))
src.attacking = 1
src.visible_message("<span class='combat'><B>[src]</B> claws at [src.target]!</span>")
if(ishuman(target))
random_brute_damage(src.target, rand(6,18))
else if (isrobot(target))
target:compborg_take_critter_damage(null, rand(4,8))
spawn(10)
src.attacking = 0
ChaseAttack(mob/M)
src.visible_message("<span class='combat'><B>[src]</B> mauls [M]!</span>")
playsound(src.loc, pick("sound/voice/MEraaargh.ogg"), 40, 0)
M.weakened += rand(2,4)
M.stunned += rand(1,3)
random_brute_damage(M, rand(2,5))
obj/critter/bear/care
name = "space carebear"
desc = "I love you!"
icon_state = "carebear"
New()
..()
src.name = pick("Lovealot Bear", "Stuffums", "World Destroyer", "Pookie", "Colonel Sanders", "Hugbeast", "Lovely Bear", "HUG ME", "Empathy Bear", "Steve", "Mr. Pants")
ChaseAttack(mob/M)
src.visible_message("<span class='combat'><B>[src]</B> snuggles [M]!</span>")
playsound(src.loc, pick("sound/misc/babynoise.ogg"), 50, 0)
M.weakened += rand(2,4)
M.stunned += rand(1,3)
random_brute_damage(M, rand(2,5))
/obj/critter/yeti
name = "space yeti"
desc = "Well-known as the single most aggressive, dangerous and hungry thing in the universe."
icon_state = "yeti"
density = 1
health = 75
aggressive = 1
defensive = 1
wanderer = 1
opensdoors = 0
atkcarbon = 1
atksilicon = 1
firevuln = 3
brutevuln = 1
angertext = "starts chasing" // comes between critter name and target name
butcherable = 1
skinresult = /obj/item/material_piece/cloth/leather
max_skins = 2
New()
..()
src.seek_target()
seek_target()
src.anchored = 0
for (var/mob/living/C in hearers(src.seekrange,src))
if (src.target)
src.task = "chasing"
break
if ((C.name == src.oldtarget_name) && (world.time < src.last_found + 100)) continue
if (C.health < 0) continue
if (C.name == src.attacker) src.attack = 1
if (iscarbon(C)) src.attack = 1
if (istype(C, /mob/living/silicon/)) src.attack = 1
if (src.attack)
src.target = C
src.oldtarget_name = C.name
src.visible_message("<span class='combat'><b>[src]</b> [src.angertext] [src.target]!</span>")
playsound(src.loc, pick("sound/voice/YetiGrowl.ogg"), 40, 0)
src.task = "chasing"
break
else
continue
ChaseAttack(mob/M)
src.visible_message("<span class='combat'><B>[src]</B> punches out [M]!</span>")
playsound(src.loc, "sound/effects/bang.ogg", 40, 1, -1)
M.stunned = 10
M.weakened = 10
CritterAttack(mob/M)
src.attacking = 1
src.visible_message("<span class='combat'><B>[src]</B> devours [M] in one bite!</span>")
logTheThing("combat", M, null, "was devoured by [src] at [log_loc(src)].") // Some logging for instakill critters would be nice (Convair880).
playsound(src.loc, "sound/items/eatfood.ogg", 30, 1, -2)
M.death(1)
var/atom/movable/overlay/animation = null
M.transforming = 1
M.canmove = 0
M.icon = null
M.invisibility = 101
if(ishuman(M))
animation = new(src.loc)
animation.icon_state = "blank"
animation.icon = 'icons/mob/mob.dmi'
animation.master = src
if (M.client)
var/mob/dead/observer/newmob
newmob = new/mob/dead/observer(M)
M.client:mob = newmob
M.mind.transfer_to(newmob)
qdel(M)
src.task = "thinking"
src.seek_target()
src.attacking = 0
playsound(src.loc, pick("sound/misc/burp_alien.ogg"), 50, 0)
sleeping = 1
/obj/critter/shark
name = "space shark"
desc = "This is the third most terrifying thing you've ever laid eyes on."
icon = 'icons/misc/banshark.dmi'
icon_state = "banshark1"
density = 1
health = 75
aggressive = 1
defensive = 1
wanderer = 1
opensdoors = 0
atkcarbon = 1
atksilicon = 1
firevuln = 3
brutevuln = 1
angertext = "swims after" // comes between critter name and target name
generic = 0
var/recentsound = 0
butcherable = 1
CritterDeath()
..()
src.reagents.add_reagent("shark_dna", 50, null)
return
New()
..()
src.seek_target()
seek_target()
src.anchored = 0
for (var/mob/living/C in hearers(src.seekrange,src))
if (src.target)
src.task = "chasing"
break
if ((C.name == src.oldtarget_name) && (world.time < src.last_found + 100)) continue
if (C.health < 0) continue
if (C.name == src.attacker) src.attack = 1
if (iscarbon(C)) src.attack = 1
if (istype(C, /mob/living/silicon/)) src.attack = 1
if (src.attack)
src.target = C
src.oldtarget_name = C.name
src.visible_message("<span class='combat'><b>[src]</b> [src.angertext] [src.target]!</span>")
if(!recentsound)
playsound(src.loc, pick("sound/misc/jaws.ogg"), 50, 0)
recentsound = 1
spawn(600) recentsound = 0
src.task = "chasing"
break
else
continue
ChaseAttack(mob/M)
src.visible_message("<span class='combat'><B>[src]</B> bashes into [M]!</span>")
playsound(src.loc, "sound/effects/bang.ogg", 50, 1, -1)
M.stunned = 10
M.weakened = 10
CritterAttack(mob/M)
src.attacking = 1
src.visible_message("<span class='combat'><B>[src]</B> gibs [M] in one bite!</span>")
logTheThing("combat", M, null, "was gibbed by [src] at [log_loc(src)].") // Some logging for instakill critters would be nice (Convair880).
playsound(src.loc, "sound/items/eatfood.ogg", 30, 1, -2)
M.gib()
src.task = "thinking"
src.seek_target()
src.attacking = 0
spawn(30) playsound(src.loc, pick("sound/misc/burp_alien.ogg"), 50, 0)
sleeping = 1
/obj/item/reagent_containers/food/snacks/ingredient/egg/critter/shark
name = "shark egg"
critter_type = /obj/critter/shark
warm_count = 50
/obj/critter/bat
name = "bat"
desc = "skreee!"
icon_state = "bat"
density = 1
health = 5
aggressive = 0
defensive = 1
wanderer = 1
opensdoors = 0
atkcarbon = 0
atksilicon = 0
firevuln = 1
brutevuln = 1
CritterDeath()
..()
src.reagents.add_reagent("woolofbat", 50, null)
return
CritterAttack(mob/M)
src.attacking = 1
src.visible_message("<span class='combat'><B>[src]</B> bites [src.target]!</span>")
random_brute_damage(src.target, 1)
spawn(10)
src.attacking = 0
Move()
if(prob(15))
playsound(src.loc, "rustle", 10, 1)
..()
/obj/critter/bat/doctor
name = "Dr. Acula"
desc = "If you ask nicely he might even write you a preskreeeption!"
icon_state = "batdoctor"
health = 30
generic = 0
// A slightly scarier (but still cute) bat for vampires
/obj/critter/bat/buff
name = "angry bat"
desc = "It doesn't look too happy!"
icon_state = "scarybat"
health = 25
aggressive = 1
defensive = 1
wanderer = 1
atkcarbon = 1
atksilicon = 1
brutevuln = 0.7
opensdoors = 0
seekrange = 5
density = 1 // so lasers can hit them
angertext = "screeches at"
seek_target()
src.anchored = 0
for (var/mob/living/C in hearers(src.seekrange,src))
if (src.target)
src.task = "chasing"
break
if ((C.name == src.oldtarget_name) && (world.time < src.last_found + 100)) continue
if (iscarbon(C) && !src.atkcarbon) continue
if (istype(C, /mob/living/silicon/) && !src.atksilicon) continue
if (C.health < 0) continue
if (C in src.friends) continue
if (isvampire(C)) continue
if (C.name == src.attacker) src.attack = 1
if (iscarbon(C) && src.atkcarbon) src.attack = 1
if (istype(C, /mob/living/silicon/) && src.atksilicon) src.attack = 1
if (src.attack)
src.target = C
src.oldtarget_name = C.name
src.visible_message("<span class='combat'><b>[src]</b> [src.angertext] [C.name]!</span>")
src.task = "chasing"
break
else
continue
ChaseAttack(mob/M)
src.visible_message("<span class='combat'><B>[src]</B> hits [M]!</span>")
if (prob(30)) M.weakened += rand(1,2)
CritterAttack(mob/M)
src.attacking = 1
src.visible_message("<span class='combat'><B>[src]</B> bites and claws at [src.target]!</span>")
random_brute_damage(src.target, rand(3,5))
spawn(10)
src.attacking = 0
/obj/item/reagent_containers/food/snacks/ingredient/egg/critter/bat
name = "bat egg"
critter_type = /obj/critter/bat
/obj/critter/lion
name = "lion"
desc = "Oh christ"
icon_state = "lion"
density = 1
health = 20
aggressive = 1
defensive = 0
wanderer = 1
opensdoors = 1
atkcarbon = 1
atksilicon = 1
atcritter = 1
firevuln = 0.5
brutevuln = 0.5
butcherable = 1
death_text = "%src% gives up the ghost!"
CritterAttack(mob/M)
src.attacking = 1
M.visible_message("<span class='combat'><b>[src]</b> savagely bites [src.target]!</span>")
random_brute_damage(M, rand(8,16))
spawn(10)
src.attacking = 0
ChaseAttack(mob/M)
src.visible_message("<span class='combat'><b>[src]</b> lunges upon [M]!</span>")
if(iscarbon(M))
if(prob(50)) M.stunned += rand(2,4)
random_brute_damage(M, rand(4,8))
+878
View File
@@ -0,0 +1,878 @@
// p much straight up copied from secbot code =I
/obj/critter/
name = "critter"
desc = "you shouldnt be able to see this"
icon = 'icons/misc/critter.dmi'
var/living_state = null
var/dead_state = null
layer = 5.0
density = 1
anchored = 0
flags = FPRINT | CONDUCT | USEDELAY
var/is_template = 0
var/alive = 1
var/health = 10
// "sleeping" is a special state that sleeps for 10 cycles, wakes up, sleeps again unless someone is found
// "hibernating" is another special state where it does nothing unless explicitly woken up
var/task = "thinking"
var/list/followed_path = null
var/followed_path_retries = 0
var/followed_path_retry_target = null
var/follow_path_blindly = 0
var/report_state = 0
var/quality_name = null
var/mobile = 1
var/aggressive = 0
var/defensive = 0
var/wanderer = 1
var/opensdoors = 0
var/frustration = 0
var/last_found = null
var/target = null
var/oldtarget_name = null
var/target_lastloc = null
var/atkcarbon = 0
var/atksilicon = 0
var/atcritter = 0
var/atkintangible = 0
var/attack = 0
var/attacking = 0
var/steps = 0
var/firevuln = 1
var/brutevuln = 1
var/miscvuln = 0.2
var/attack_range = 1 // how many tiles away it will attack from
var/seekrange = 7 // how many tiles away it will look for a target
var/list/friends = list() // used for tracking hydro-grown monsters's creator
var/attacker = null // used for defensive tracking
var/angertext = "charges at" // comes between critter name and target name
var/pet_text = "pets"
var/death_text = "%src% dies!"
var/hitsound = null
var/flying = 0
//flags = OPENCONTAINER
var/sleeping = 0 //countdown, when hits 0 does a wake check
var/sleep_check = 10 //countdown, when hits 0 does a sleep check
var/hibernate_check = 2
var/sleeping_icon_state = null
var/mob/living/wrangler = null
var/butcherable = 0
var/meat_type = /obj/item/reagent_containers/food/snacks/ingredient/meat/mysterymeat
var/name_the_meat = 1
var/generic = 1 // if yes, critter can be randomized a bit
var/max_quality = 100
var/min_quality = -100
var/can_revive = 1 // resurrectable with strange reagent
var/skinresult = null //type path of hide/leather item from skinning
var/max_skins = 1 //How many skins you can get at most from this critter. It's 1 to the max amound defined here. random.
var/muted = 0 // shut UP
var/chases_food = 0
var/health_gain_from_food = 0
var/obj/item/reagent_containers/food/snacks/food_target = null
var/eat_text = "nibbles at"
var/feed_text = null
var/area/registered_area = null //the area this critter is registered in
proc/tokenized_message(var/message, var/target)
if (!message || !length(message))
return
var/msg = dd_replacetext(message, "%src%", "<b>[src]</b>")
msg = dd_replacetext(msg, "%target%", "[target]")
src.visible_message("<span style=\"color:red\">[msg]</span>")
proc/report_spawn()
if (!report_state)
report_state = 1
if (src in gauntlet_controller.gauntlet)
gauntlet_controller.increaseCritters(src)
if (src in colosseum_controller.colosseum)
colosseum_controller.increaseCritters(src)
proc/report_death()
if (report_state == 1)
report_state = 0
if (src in gauntlet_controller.gauntlet)
gauntlet_controller.decreaseCritters(src)
if (src in colosseum_controller.colosseum)
colosseum_controller.decreaseCritters(src)
serialize(var/savefile/F, var/path, var/datum/sandbox/sandbox)
..()
F["[path].aggressive"] << src.aggressive
F["[path].atkcarbon"] << src.atkcarbon
F["[path].atksilicon"] << src.atksilicon
F["[path].health"] << src.health
F["[path].opensdoors"] << src.opensdoors
F["[path].wanderer"] << src.wanderer
F["[path].mobile"] << src.mobile
F["[path].brutevuln"] << src.brutevuln
F["[path].firevuln"] << src.firevuln
deserialize(var/savefile/F, var/path, var/datum/sandbox/sandbox)
. = ..()
F["[path].aggressive"] >> src.aggressive
F["[path].atkcarbon"] >> src.atkcarbon
F["[path].atksilicon"] >> src.atksilicon
F["[path].health"] >> src.health
F["[path].opensdoors"] >> src.opensdoors
F["[path].wanderer"] >> src.wanderer
F["[path].mobile"] >> src.mobile
F["[path].brutevuln"] >> src.brutevuln
F["[path].firevuln"] >> src.firevuln
clone()
var/obj/critter/C = ..()
C.mobile = mobile
C.aggressive = aggressive
C.defensive = defensive
C.atkcarbon = atkcarbon
C.atksilicon = atksilicon
C.health = health
C.wanderer = wanderer
C.brutevuln = brutevuln
C.firevuln = firevuln
return C
proc/wake_from_hibernation()
if(task != "hibernating") return
//DEBUG("[src] woke from hibernation at [showCoords(src.x, src.y, src.z)] in [registered_area ? registered_area.name : "nowhere"] due to [usr ? usr : "some mysterious fucking reason"]")
//Ok, now we look to see if we should get murdlin'
task = "sleeping"
hibernate_check = 20 //20 sleep_checks
do_wake_check(1)
if(registered_area)
registered_area.registered_critters -= src
registered_area = null
anchored = initial(anchored)
//critters |= src //Resume processing this critter
proc/hibernate()
registered_area = get_area(src)
hibernate_check = 20 //Reset this counter in case of failure
if(registered_area)
task = "hibernating"
registered_area.registered_critters |= src
anchored = 1
//DEBUG("[src] started hibernating at [showCoords(src.x, src.y, src.z)] in [registered_area ? registered_area.name : "nowhere"].")
//critters -= src //Stop processing this critter
HasProximity(atom/movable/AM as mob|obj)
if(task == "hibernating" && istype(AM, /mob))
var/mob/M = AM
if(M.client) wake_from_hibernation()
..()
set_loc(var/atom/newloc)
..()
wake_from_hibernation() //Critters hibernate lightly enough to wake up when moved
proc/on_revive()
return
proc/on_sleep()
proc/on_wake()
var/area/A = get_area(src)
if(A) A.wake_critters() //HLEP!
proc/on_grump()
attackby(obj/item/W as obj, mob/living/user as mob)
..()
if (!src.alive)
if (src.skinresult && max_skins)
if (istype(W, /obj/item/circular_saw) || istype(W, /obj/item/kitchen/utensil/knife) || istype(W, /obj/item/scalpel) || istype(W, /obj/item/raw_material/shard) || istype(W, /obj/item/sword) || istype(W, /obj/item/saw) || istype(W, /obj/item/wirecutters))
for(var/i, i<rand(1, max_skins), i++)
new src.skinresult (src.loc)
src.skinresult = null
user.visible_message("<span style=\"color:red\">[user] skins [src].</span>","You skin [src].")
if (src.butcherable && (istype(W, /obj/item/kitchen/utensil/knife) || istype(W, /obj/item/knife_butcher)))
user.visible_message("<span style=\"color:red\">[user] butchers [src].[src.butcherable == 2 ? "<b>WHAT A MONSTER</b>" : null]","You butcher [src].</span>")
var/i = rand(2,4)
var/transfer = src.reagents.total_volume / i
while (i-- > 0)
var/obj/item/reagent_containers/food/newmeat = new meat_type
newmeat.set_loc(src.loc)
src.reagents.trans_to(newmeat, transfer)
if (name_the_meat)
newmeat.name = "[src.name] meat"
newmeat.real_name = newmeat.name
qdel (src)
return
..()
return
if (src.health_gain_from_food && (istype(W, /obj/item/reagent_containers/food/snacks) || istype(W, /obj/item/seed)))
user.visible_message("<b>[user]</b> feeds [W] to [src]!","You feed [W] to [src].")
if (src.feed_text)
src.visible_message("[src] [src.feed_text]")
src.health += src.health_gain_from_food
qdel(W)
return
var/attack_force = 0
var/damage_type = "brute"
if (istype(W, /obj/item/artifact/melee_weapon))
var/datum/artifact/melee/ME = W.artifact
attack_force = ME.dmg_amount
damage_type = ME.damtype
else
attack_force = W.force
damage_type = W.damtype
if (!attack_force)
return
if (src.sleeping)
sleeping = 0
on_wake()
switch(damage_type)
if("fire")
src.health -= attack_force * src.firevuln
if("brute")
src.health -= attack_force * src.brutevuln
else
src.health -= attack_force * src.miscvuln
if (hitsound)
playsound(src, hitsound, 50, 1)
if (src.alive && src.health <= 0) src.CritterDeath()
if (src.alive)
on_damaged(user)
if (src.defensive)
if (src.target == user && src.task == "attacking")
if (prob(50 - attack_force))
return
else
src.visible_message("<span style=\"color:red\"><b>[src]</b> flinches!</span>")
src.target = user
src.oldtarget_name = user.name
src.visible_message("<span style=\"color:red\"><b>[src]</b> [src.angertext] [user.name]!</span>")
src.task = "chasing"
on_grump()
proc/on_damaged(mob/user)
if(registered_area) //In case some butt fiddles with a hibernating critter
registered_area.wake_critters()
return
proc/on_pet()
if(registered_area) //In case some nice person fiddles with a hibernating critter
registered_area.wake_critters()
return
attack_hand(var/mob/user as mob)
..()
if (!src.alive)
..()
return
if (src.sleeping)
sleeping = 0
on_wake()
if (user.a_intent == INTENT_HARM)
src.health -= rand(1,2) * src.brutevuln
src.visible_message("<span style=\"color:red\"><b>[user]</b> punches [src]!</span>")
playsound(src.loc, pick('sound/weapons/punch1.ogg','sound/weapons/punch2.ogg','sound/weapons/punch3.ogg','sound/weapons/punch4.ogg'), 100, 1)
if (hitsound)
playsound(src, hitsound, 50, 1)
if (src.alive && src.health <= 0) src.CritterDeath()
if (src.alive)
on_damaged(user)
if (src.defensive)
if (src.target == user && src.task == "attacking")
if (prob(50))
return
else
src.visible_message("<span style=\"color:red\"><b>[src]</b> flinches!</span>")
src.target = user
src.oldtarget_name = user.name
src.visible_message("<span style=\"color:red\"><b>[src]</b> [src.angertext] [user.name]!</span>")
src.task = "chasing"
on_grump()
else
var/pet_verb = islist(src.pet_text) ? pick(src.pet_text) : src.pet_text
src.visible_message("<span style=\"color:blue\"><b>[user]</b> [pet_verb] [src]!</span>", 1)
on_pet()
proc/patrol_step()
if (!mobile)
return
var/turf/moveto = locate(src.x + rand(-1,1),src.y + rand(-1, 1),src.z)
if(isturf(moveto) && !moveto.density) step_towards(src, moveto)
if(src.aggressive) seek_target()
steps += 1
if (steps == rand(5,20)) src.task = "thinking"
Bump(M as mob|obj)
spawn(0)
if (istype(M, /obj/machinery/door/))
var/obj/machinery/door/D = M
D.Bumped(src) // Doesn't call that automatically for some inexplicable reason.
else if ((istype(M, /mob/living/)) && (!src.anchored))
src.set_loc(M:loc)
src.frustration = 0
return
return
bullet_act(var/obj/projectile/P)
var/damage = 0
damage = round((P.power*P.proj_data.ks_ratio), 1.0)
if (src.sleeping)
sleeping = 0
on_wake()
if(src.material) src.material.triggerOnAttacked(src, P.shooter, src, (ismob(P.shooter) ? P.shooter:equipped() : P.shooter) )
for(var/atom/A in src)
if(A.material)
A.material.triggerOnAttacked(A, P.shooter, src, (ismob(P.shooter) ? P.shooter:equipped() : P.shooter) )
switch(P.proj_data.damage_type)
if(D_KINETIC,D_PIERCING,D_SLASHING)
src.health -= (damage*brutevuln)
if(D_ENERGY)
src.health -= damage
if(D_BURNING)
src.health -= (damage*firevuln)
if(D_RADIOACTIVE)
src.health -= 1
if(D_TOXIC)
src.health -= 1
on_damaged(usr)
if (src.health <= 0)
src.CritterDeath()
ex_act(severity)
if (src.sleeping)
sleeping = 0
on_wake()
on_damaged()
switch(severity)
if(1.0)
src.health -= 200
if (src.health <= 0)
src.CritterDeath()
return
if(2.0)
src.health -= 75
if (src.health <= 0)
src.CritterDeath()
return
else
src.health -= 25
if (src.health <= 0)
src.CritterDeath()
return
return
meteorhit()
src.health -= 150 // no more instakill
on_damaged()
if (src.health <= 0)
src.CritterDeath()
return
proc/check_health()
if (src.health <= 0)
src.CritterDeath()
blob_act(var/power)
src.health -= power
on_damaged()
if (src.health <= 0)
src.CritterDeath()
return
proc/follow_path()
if (!mobile)
task = "thinking"
return
if (src.loc == followed_path_retry_target)
logTheThing("debug", null, null, "<B>Marquesas/Critter Astar:</b> Critter arrived at target location.")
task = "thinking"
followed_path = null
followed_path_retries = 0
followed_path_retry_target = null
else if (!followed_path)
logTheThing("debug", null, null, "<B>Marquesas/Critter Astar:</b> Critter following empty path.")
task = "thinking"
else if (!followed_path.len)
logTheThing("debug", null, null, "<B>Marquesas/Critter Astar:</b> Critter path ran out.")
task = "thinking"
else
var/turf/nextturf = followed_path[1]
var/retry = 0
if (nextturf.density)
retry = 1
if (!retry)
for (var/obj/O in nextturf)
if (O.density)
retry = 1
break
if (retry)
if (!followed_path_retry_target)
task = "thinking"
else if (followed_path_retries > 10)
logTheThing("debug", null, null, "<B>Marquesas/Critter Astar:</b> Critter out of retries.")
task = "thinking"
else
logTheThing("debug", null, null, "<B>Marquesas/Critter Astar:</b> Hit a wall, retrying.")
followed_path = findPath(src.loc, followed_path_retry_target)
return
else
set_loc(nextturf)
followed_path -= nextturf
if (!follow_path_blindly)
seek_target()
proc/do_wake_check(var/force = 0)
if(!force && sleeping-- > 0) return
var/waking = 0
for(var/mob/M in range(10, src))
if(M.client)
waking = 1
break
if (!waking)
if (get_area(src) == colosseum_controller.colosseum)
waking = 1
if(waking)
hibernate_check = 20
sleeping = 0
task = "thinking"
on_wake()
if (sleeping_icon_state)
src.icon_state = initial(src.icon_state)
return 1
else
sleeping = 10
if(--hibernate_check <= 0)
src.hibernate()
return 0
proc/do_sleep_check(var/force = 0)
if(!force && sleep_check-- > 0) return
var/stay_awake = 0
for(var/mob/M in range(10, src))
if(M.client)
stay_awake = 1
break
if(!stay_awake)
sleeping = 10
on_sleep()
if (sleeping_icon_state)
src.icon_state = sleeping_icon_state
task = "sleeping"
return 0
else
sleep_check = 10
proc/process()
if (is_template || task == "hibernating")
return 0
if (!src.alive) return 0
if(sleeping > 0)
sleeping--
return 0
check_health()
if(task == "following path")
follow_path()
spawn(10)
follow_path()
else if(task == "sleeping")
do_wake_check()
else
do_sleep_check()
return ai_think()
proc/ai_think()
switch(task)
if ("thinking")
src.attack = 0
src.target = null
walk_to(src,0)
if (src.aggressive) seek_target()
if (src.wanderer && src.mobile && !src.target) src.task = "wandering"
if ("chasing")
if (src.frustration >= 8)
src.target = null
src.last_found = world.time
src.frustration = 0
src.task = "thinking"
if (mobile)
walk_to(src,0)
if (target)
if (get_dist(src, src.target) <= src.attack_range)
var/mob/living/carbon/M = src.target
if (M)
ChaseAttack(M)
src.task = "attacking"
src.anchored = 1
src.target_lastloc = M.loc
else
if (mobile)
var/turf/olddist = get_dist(src, src.target)
walk_to(src, src.target,1,4)
if ((get_dist(src, src.target)) >= (olddist))
src.frustration++
else
src.frustration = 0
else
if (get_dist(src, src.target) > attack_range)
src.frustration++
else
src.frustration = 0
else src.task = "thinking"
if ("chasing food")
if (!src.chases_food || src.food_target == null)
src.task = "thinking"
else if (get_dist(src, src.food_target) <= src.attack_range)
src.task = "eating"
else
walk_to(src, src.food_target,1,4)
if ("eating")
if (get_dist(src, src.food_target) > src.attack_range)
src.task = "chasing food"
else
src.visible_message("<b>[src]</b> [src.eat_text] [src.food_target].")
playsound(src.loc,"sound/items/eatfood.ogg", rand(10,50), 1)
if (food_target.reagents.total_volume > 0 && src.reagents.total_volume < 30)
food_target.reagents.trans_to(src, 5)
src.food_target.amount--
spawn(rand(20,30))
if (src.food_target != null && src.food_target.amount <= 0)
qdel(src.food_target)
src.task = "thinking"
src.food_target = null
src.health += src.health_gain_from_food
if ("attacking")
// see if he got away
if ((get_dist(src, src.target) > src.attack_range) || ((src.target:loc != src.target_lastloc)))
src.anchored = initial(src.anchored)
src.task = "chasing"
else
if (get_dist(src, src.target) <= src.attack_range)
var/mob/living/carbon/M = src.target
if (!src.attacking) CritterAttack(src.target)
if (!src.aggressive)
src.task = "thinking"
src.target = null
src.anchored = initial(src.anchored)
src.last_found = world.time
src.frustration = 0
src.attacking = 0
else
if(M!=null)
if (M.health < 0)
src.task = "thinking"
src.target = null
src.anchored = initial(src.anchored)
src.last_found = world.time
src.frustration = 0
src.attacking = 0
else
src.anchored = initial(src.anchored)
src.attacking = 0
src.task = "chasing"
if ("wandering")
patrol_step()
return 1
New()
if(!src.reagents) src.create_reagents(100)
critters += src
report_spawn()
if(generic)
src.quality = rand(min_quality,max_quality)
var/nickname = getCritterQuality(src.quality)
if(nickname)
src.quality_name = nickname
src.name = "[nickname] [src.name]"
..()
proc/seek_target()
src.anchored = initial(src.anchored)
if (src.target)
src.task = "chasing"
return
if (src.chases_food)
var/list/visible = new()
for (var/obj/item/reagent_containers/food/snacks/S in view(src.seekrange,src))
visible.Add(S)
if (src.food_target && visible.Find(src.food_target))
src.task = "chasing food"
return
else
src.task = "thinking"
if (visible.len)
src.food_target = visible[1]
src.task = "chasing food"
for (var/mob/living/C in hearers(src.seekrange,src))
//if (src.target)
// src.task = "chasing"
// break
if ((C.name == src.oldtarget_name) && (world.time < src.last_found + 100)) continue
if (iscarbon(C) && !src.atkcarbon) continue
if (istype(C, /mob/living/silicon/) && !src.atksilicon) continue
if (istype(C, /mob/living/intangible/) && !src.atkintangible) continue
if (C.health < 0) continue
if(!filter_target(C)) continue
if (C in src.friends) continue
if (ishuman(C))
if (C:bioHolder && C:bioHolder.HasEffect("revenant"))
continue
if (C.name == src.attacker) src.attack = 1
if (iscarbon(C) && src.atkcarbon) src.attack = 1
if (istype(C, /mob/living/silicon/) && src.atksilicon) src.attack = 1
if (src.attack)
src.target = C
src.oldtarget_name = C.name
src.visible_message("<span class='combat'><b>[src]</b> [src.angertext] [C.name]!</span>")
src.task = "chasing"
on_grump()
break
else
continue
proc/filter_target(var/mob/living/M) //Better to have specialized filters in it's own proc rather than overriding the main seek_target thing imo
return 1
proc/CritterDeath()
if (!src.alive) return
if (!dead_state)
src.icon_state = "[initial(src.icon_state)]-dead"
else
src.icon_state = dead_state
src.alive = 0
src.anchored = 0
src.density = 0
walk_to(src,0)
report_death()
src.tokenized_message(death_text)
proc/ChaseAttack(mob/M)
src.visible_message("<span class='combat'><B>[src]</B> leaps at [src.target]!</span>")
//playsound(src.loc, "sound/weapons/genhit1.ogg", 50, 1, -1)
proc/CritterAttack(mob/M)
src.attacking = 1
src.visible_message("<span class='combat'><B>[src]</B> bites [src.target]!</span>")
random_brute_damage(src.target, 1)
spawn(25)
src.attacking = 0
proc/getCritterQuality(var/quality)
switch(quality)
if(-INFINITY to -100)
return "abysmal"
if(-100 to -99)
return "worst"
if(-98 to -91)
return pick("shameful", "hideous", "grotesque", "vile", "misshapen", "garbage", "illegal", "dreadful", "god-awful")
if(-90 to -75)
return pick("ugly", "grody", "stinky", "awful", "diseased", "filthy", "lousy", "overweight", "broken", "unfortunate", "unacceptable", "sad", "slipshod", "crappy", "faulty", "fraudulent")
if(-74 to -50)
return pick("shabby", "mangy", "dented", "dusty", "sub-par", "slightly less nice", "weird", "crummy", "busted", "funky", "bad news", "deficient", "cruddy", "icky", "not good")
if(-49 to 50)
return ""
if(51 to 64)
return pick("nice", "cute", "healthy", "buff", "strong")
if(65 to 74)
return pick("suave", "buff", "robust", "handsome", "fine", "slightly nicer", "pretty good")
if(75 to 85)
return pick("high-class", "great", "burly", "superb", "excellent", "admirable")
if(86 to 90)
return pick("majestic", "fantastic", "high-quality", "marvelous", "deluxe")
if(91 to 94)
return pick("show-quality", "finest", "superb")
if(95 to 97)
return "champion"
if(98 to 99)
src.material = getCachedMaterial("gold")
if (src.material)
src.material.owner = src
src.material.triggerOnAdd(src)
return "best"
if(100 to INFINITY)
src.material = getCachedMaterial("gold")
if (src.material)
src.material.owner = src
src.material.triggerOnAdd(src)
return "mystical"
else
return "odd"
return
proc/Shoot(var/target, var/start, var/user, var/bullet = 0)
if(target == start)
return
// playsound(user, "mp5gunshot.ogg", 100, 1)
/* if(bullet == 0)
A = new /obj/bullet/mpbullet( user:loc )
else if(bullet == 1)
playsound(user, "sound/weapons/shotgunshot.ogg", 100, 1)
A = new /obj/bullet/slug( user:loc )
else if(bullet == 2)
playsound(user, "fivegunshot.ogg", 100, 1)
A = new /obj/bullet/medbullet( user:loc )*/
if (!isturf(target))
return
// FUCK YOU WHOEVER IS USING THIS
// FUCK YOU
shoot_projectile_ST(src, new/datum/projectile/bullet/revolver_38(), target)
return
/obj/item/reagent_containers/food/snacks/ingredient/egg/critter
name = "egg"
desc = "Looks like this could hatch into something."
icon_state = "critter_egg"
var/critter_name = null
var/hatched = 0
var/critter_type = null
var/warm_count = 10 // how many times you gotta warm it before it hatches
var/critter_reagent = null
rand_pos = 1
New()
..()
var/amt_to_mod = round(src.warm_count / 10, 1)
src.warm_count += rand(-amt_to_mod,amt_to_mod)
src.color = random_saturated_hex_color(1)
if (src.reagents && src.critter_reagent)
src.reagents.add_reagent(src.critter_reagent, 10)
attack_hand(mob/user as mob)
if (src.anchored)
return
else
..()
attackby(obj/item/W as obj, mob/user as mob)
if (istype(W, /obj/item/pen))
var/t = input(user, "Enter new name", src.name, src.critter_name) as null|text
logTheThing("debug", user, null, "names a critter egg \"[t]\"")
if (!t)
return
t = strip_html(dd_replacetext(t, "'",""))
t = copytext(t, 1, 65)
if (!t)
return
if (!in_range(src, usr) && src.loc != usr)
return
src.critter_name = t
else if ((istype(W, /obj/item/weldingtool) && W:welding) || (istype(W, /obj/item/clothing/head/cakehat) && W:on) || istype(W, /obj/item/device/igniter) || ((istype(W, /obj/item/zippo) || istype(W, /obj/item/match) || istype(W, /obj/item/device/candle)) && W:lit) || W.burning || W.hit_type == DAMAGE_BURN) // jesus motherfucking christ
user.visible_message("<span style=\"color:red\"><b>[user]</b> warms [src] with [W].</span>",\
"<span style=\"color:red\">You warm [src] with [W].</span>")
src.warm_count -= 2
src.warm_count = max(src.warm_count, 0)
src.hatch_check(0, user)
else
return ..()
attack_self(mob/user as mob)
if (src.anchored)
return
user.visible_message("[user] warms [src] with [his_or_her(user)] hands.",\
"You warm [src] with your hands.")
src.warm_count --
src.warm_count = max(src.warm_count, 0)
src.hatch_check(0, user)
throw_impact(var/turf/T)
//..() <- Fuck off mom, I'm 25 and I do what I want =I
src.hatch_check(1, null, T)
proc/hatch_check(var/shouldThrow = 0, var/mob/user, var/turf/T)
if (hatched || anchored)
return
if (src.warm_count <= 0 || shouldThrow)
if (shouldThrow && T)
new /obj/decal/cleanable/eggsplat(T)
src.set_loc(T)
else
src.anchored = 1
src.layer = initial(src.layer)
if (user)
user.u_equip(src)
src.set_loc(get_turf(src))
spawn(0)
if (shouldThrow && T)
src.visible_message("<span style=\"color:red\">[src] splats onto the floor messily!</span>")
playsound(T, "sound/effects/splat.ogg", 100, 1)
else
var/hatch_wiggle_counter = rand(3,8)
while (hatch_wiggle_counter-- > 0)
src.pixel_x++
sleep(2)
src.pixel_x--
sleep(10)
src.visible_message("[src] hatches!")
if (!ispath(critter_type))
if (istext(critter_type))
critter_type = text2path(critter_type)
else
logTheThing("debug", null, null, "EGG: [src] has invalid critter path!")
src.visible_message("Looks like there wasn't anything inside of [src]!")
qdel(src)
return
var/obj/critter/newCritter = new critter_type(T ? T : get_turf(src))
if (critter_name)
newCritter.name = critter_name
if (shouldThrow && T)
newCritter.throw_at(get_edge_target_turf(src, src.dir), 2, 1)
sleep(1)
qdel(src)
return
else
return
File diff suppressed because it is too large Load Diff
+96
View File
@@ -0,0 +1,96 @@
/obj/critter/gunbot
name = "Robot"
desc = "A Security Robot, something seems a bit off."
icon = 'icons/mob/robots.dmi'
icon_state = "syndibot"
density = 1
health = 50
aggressive = 1
defensive = 0
wanderer = 1
opensdoors = 1
atkcarbon = 1
atksilicon = 0
atcritter = 1
firevuln = 0.5
brutevuln = 1
is_syndicate = 1
mats = 8
seek_target()
src.anchored = 0
for (var/mob/living/C in hearers(src.seekrange,src))
if (!src.alive) break
if (C.health < 0) continue
if (C.name == src.attacker) src.attack = 1
if (iscarbon(C) && src.atkcarbon) src.attack = 1
if (istype(C, /mob/living/silicon/) && src.atksilicon) src.attack = 1
if (src.attack)
src.target = C
src.oldtarget_name = C.name
src.visible_message("<span style=\"color:red\"><b>[src]</b> fires at [src.target]!</span>")
playsound(src.loc, "sound/weapons/Gunshot.ogg", 50, 1)
var/tturf = get_turf(target)
spawn(1)
Shoot(tturf, src.loc, src)
spawn(4)
Shoot(tturf, src.loc, src)
spawn(6)
Shoot(tturf, src.loc, src)
src.attack = 0
return
else continue
if(!src.atcritter) return
for (var/obj/critter/C in view(src.seekrange,src))
if (!C.alive) break
if (C.health < 0) continue
if (C.name == src.attacker) src.attack = 1
if (!istype(C, /obj/critter/gunbot)) src.attack = 1
if (src.attack)
src.target = C
src.oldtarget_name = C.name
src.visible_message("<span style=\"color:red\"><b>[src]</b> fires at [src.target]!</span>")
playsound(src.loc, "sound/weapons/Gunshot.ogg", 50, 1)
var/tturf = get_turf(target)
spawn(1)
Shoot(tturf, src.loc, src)
spawn(4)
Shoot(tturf, src.loc, src)
spawn(6)
Shoot(tturf, src.loc, src)
src.attack = 0
return
else continue
task = "thinking"
CritterDeath()
if (!src.alive) return
..()
if (get_area(src) != colosseum_controller.colosseum)
var/turf/Ts = get_turf(src)
var/obj/item/drop1 = pick(/obj/item/electronics/battery,/obj/item/electronics/board,/obj/item/electronics/buzzer,/obj/item/electronics/frame,/obj/item/electronics/resistor,/obj/item/electronics/screen,/obj/item/electronics/relay, /obj/item/parts/robot_parts/arm/left, /obj/item/parts/robot_parts/arm/right)
var/obj/item/drop2 = pick(/obj/item/electronics/battery,/obj/item/electronics/board,/obj/item/electronics/buzzer,/obj/item/electronics/frame,/obj/item/electronics/resistor,/obj/item/electronics/screen,/obj/item/electronics/relay, /obj/item/parts/robot_parts/arm/left, /obj/item/parts/robot_parts/arm/right)
new /obj/decal/cleanable/robot_debris(Ts)
new drop1(Ts)
new /obj/decal/cleanable/robot_debris(Ts)
new drop2(Ts)
new /obj/decal/cleanable/robot_debris(Ts)
spawn()
var/datum/effects/system/spark_spread/s = unpool(/datum/effects/system/spark_spread)
s.set_up(3, 1, src)
s.start()
qdel(src)
+62
View File
@@ -0,0 +1,62 @@
/obj/critter/headspider
name = "headspider"
desc = "Oh my god!"
icon_state = "headspider"
density = 1
anchored = 0
aggressive = 1
atkcarbon = 1
atksilicon = 0
opensdoors = 1
health = 80
var/datum/abilityHolder/changeling/changeling = null
var/datum/mind/owner = null
examine()
set src in view()
..()
if(!alive)
boutput(usr, text("<span style=\"color:red\"><B>the disgusting creature is not moving</B></span>"))
else if (src.health > 40)
boutput(usr, text("<span style=\"color:red\"><B>the spindly-legged head looks healthy and strong</B></span>"))
else
boutput(usr, text("<span style=\"color:red\"><B>the ugly thing is missing several limbs</B></span>"))
return
filter_target(var/mob/living/C)
//Don't want a dead mob, don't want a mob with the same mind as the owner
return C.stat != 2 && (!owner || C.mind != owner)
ChaseAttack(var/mob/M)
if(attacking) return
if(ishuman(M))
var/mob/living/carbon/human/H = M
src.visible_message("<font color='#FF0000'><B>\The [src]</B> leaps on [H.name]!</font>")
H.weakened += rand(3,5)
CritterAttack(var/mob/M)
if(attacking) return
if(ishuman(M))
var/mob/living/carbon/human/H = M
src.set_loc(H.loc)
random_brute_damage(H, 10)
src.set_loc(H.loc)
src.visible_message("<font color='#FF0000'><B>\The [src]</B> crawls down [H.name]'s throat!</font>")
H.paralysis = max(H.paralysis, 10)
attacking = 1
var/datum/ailment_data/parasite/HS = new /datum/ailment_data/parasite
HS.master = get_disease_from_path(/datum/ailment/parasite/headspider)
HS.affected_mob = H
HS.source = owner
var/datum/ailment/parasite/headspider/HSD = HS.master
HSD.changeling = changeling
H.ailments += HS
if(owner)
logTheThing("combat", owner.current ? owner.current : owner, H, "'s headspider enters %target% at [log_loc(src)].")
qdel(src)
return
+312
View File
@@ -0,0 +1,312 @@
/obj/item/clothing/head/tinfoil_hat
name = "tinfoil hat"
desc = "Protects the wearer from mindcontrol and, apparently, weak martian psychic blasts which do not involve the liquification of brains."
icon_state = "tinfoil"
item_state = "tinfoil"
/obj/critter/martian
name = "martian"
desc = "Genocidal monsters from Mars."
icon_state = "martian"
density = 1
health = 20
aggressive = 0
defensive = 1
wanderer = 1
opensdoors = 1
atkcarbon = 1
atksilicon = 1
firevuln = 1.5
brutevuln = 1
butcherable = 1
flying = 1
on_damaged(mob/user)
if (src.alive && src.defensive && prob(10))
MartianPsyblast(user)
if (!(src in gauntlet_controller.gauntlet))
src.visible_message("<span style=\"color:red\"><b>[src]</b> teleports away!</span>")
CritterTeleport(8, 1, 0)
on_pet()
for(var/mob/O in hearers(src, null))
O.show_message("<b>[src]</b> screeches, 'KXBQUB IJFDQVW??'", 1)
proc/MartianPsyblast(mob/target as mob)
for(var/mob/O in hearers(src, null))
O.show_message("<b>[src]</b> screeches, 'GBVQW UVQWIBJZ PKDDR!!!'", 1)
if (!ishuman(target))
return
playsound(target.loc, "sound/effects/ghost2.ogg", 100, 1)
var/mob/living/carbon/human/H = target
if (istype(H.head, /obj/item/clothing/head/tinfoil_hat))
boutput(H, "<span style=\"color:blue\">Your tinfoil hat protects you from the psyblast!</span>")
else
boutput(H, "<span style=\"color:red\">You are blasted by psychic energy!</span>")
H.paralysis += 5
H.stuttering += 60
H.take_brain_damage(20)
H.TakeDamage("head", 0, 5)
proc/CritterTeleport(var/telerange, var/dospark, var/dosmoke)
if (!src.alive) return
var/list/randomturfs = new/list()
for(var/turf/T in orange(src, telerange))
if(istype(T, /turf/space) || T.density) continue
randomturfs.Add(T)
src.set_loc(pick(randomturfs))
if (dospark)
spawn()
var/datum/effects/system/spark_spread/s = unpool(/datum/effects/system/spark_spread)
s.set_up(5, 1, src)
s.start()
if (dosmoke)
var/datum/effects/system/harmless_smoke_spread/smoke = new /datum/effects/system/harmless_smoke_spread()
smoke.set_up(10, 0, src.loc)
smoke.start()
src.task = "thinking"
/obj/critter/martian/soldier
name = "martian soldier"
icon_state = "martianS"
health = 35
aggressive = 1
seekrange = 7
dead
icon_state = "martianS-dead"
health = 0
New()
..()
CritterDeath()
icon_state = initial(icon_state)
seek_target()
src.anchored = 0
for (var/mob/living/C in hearers(src.seekrange,src))
if (!src.alive) break
if (C.health < 0) continue
if (C.name == src.attacker) src.attack = 1
if (iscarbon(C) && src.atkcarbon) src.attack = 1
if (istype(C, /mob/living/silicon/) && src.atksilicon) src.attack = 1
if (src.attack)
src.target = C
src.oldtarget_name = C.name
src.visible_message("<span style=\"color:red\"><b>[src]</b> shoots at [C.name]!</span>")
playsound(src.loc, "sound/weapons/lasermed.ogg", 100, 1)
if (prob(66))
C.TakeDamage("chest", 0, rand(3,5))
spawn()
var/datum/effects/system/spark_spread/s = unpool(/datum/effects/system/spark_spread)
s.set_up(3, 1, C)
s.start()
else boutput(target, "<span style=\"color:red\">The shot missed!</span>")
src.attack = 0
sleeping = 1
return
else
continue
task = "thinking"
/obj/critter/martian/psychic
name = "martian mutant"
icon_state = "martianP"
health = 10
aggressive = 1
seekrange = 4
var/gib_delay = 55
var/do_stun = 1
var/max_gib_distance = 6
var/gib_counter = 0
dead
icon_state = "martianP-dead"
health = 0
New()
..()
CritterDeath()
icon_state = initial(icon_state)
seek_target()
src.anchored = 0
for (var/mob/living/C in hearers(src.seekrange,src))
if (!src.alive) break
if (C.health < 0) continue
if (C.name == src.attacker) src.attack = 1
if (iscarbon(C) && src.atkcarbon) src.attack = 1
if (istype(C, /mob/living/silicon/) && src.atksilicon) src.attack = 1
if (src.attack)
src.target = C
src.oldtarget_name = C.name
src.visible_message("<span style=\"color:red\"><b>[src]</b> stares at [C.name]!</span>")
playsound(src.loc, "sound/weapons/phaseroverload.ogg", 100, 1)
boutput(C, "<span style=\"color:red\">You feel a horrible pain in your head!</span>")
gib_counter = 0
if (do_stun)
C.stunned += rand(1,2)
spawn(0)
for (var/i = 0, i <= round(gib_delay / 10), i++)
if ((get_dist(src, C) <= max_gib_distance) && src.alive)
if (gib_counter == gib_delay)
C.visible_message("<span style=\"color:red\"><b>[C.name]'s</b> head explodes!</span>")
logTheThing("combat", C, null, "was gibbed by [src] at [log_loc(src)].") // Some logging for instakill critters would be nice (Convair880).
C.gib()
else
C.show_message("<span style=\"color:red\">You no longer feel the [name]'s psychic glare.</span>")
break
if (gib_delay - gib_counter >= 10)
gib_delay += 10
sleep(10)
else
var/slp = gib_delay - gib_counter
gib_delay = gib_counter
sleep(slp)
src.attack = 0
sleeping = 7
return
else continue
src.task = "thinking"
/obj/critter/martian/psychic/weak
name = "martian mutant initiate"
gib_delay = 55
do_stun = 0
seekrange = 3
max_gib_distance = 4
/obj/critter/martian/warrior
name = "martian warrior"
icon_state = "martianW"
health = 35
aggressive = 1
seekrange = 7
dead
icon_state = "martianW-dead"
health = 0
New()
..()
CritterDeath()
icon_state = initial(icon_state)
ChaseAttack(mob/M)
for(var/mob/O in viewers(src, null))
O.show_message("<span style=\"color:red\"><B>[src]</B> grabs at [M]!</span>", 1)
if (prob(33)) M.weakened += rand(2,4)
spawn(25)
if (get_dist(src, M) <= 1)
src.visible_message("<span style=\"color:red\"><B>[src]</B> starts strangling [M]!</span>")
CritterAttack(mob/M)
src.attacking = 1
if (prob(95))
if (prob(10))
src.visible_message("<span style=\"color:red\"><B>[src]</B> wraps its tentacles around [M]'s neck!</span>")
M.take_oxygen_deprivation(2)
M.weakened += 1
else
src.visible_message("<span style=\"color:red\"><B>[src]'s</B> grip slips!</span>")
M.stunned = 0
sleeping = 1
spawn(10)
for(var/mob/O in hearers(src, null))
O.show_message("<span style=\"color:red\"><b>[src]</b> screeches, 'KBWKB WVYPGD!!'</span>", 1)
src.task = "thinking"
src.attacking = 0
/obj/critter/martian/sapper
name = "martian sapper"
icon_state = "martianSP"
health = 10
aggressive = 0
defensive = 0
atkcarbon = 0
atksilicon = 0
task = "wandering"
ai_think()
switch(task)
if("thinking")
var/obj/machinery/martianbomb/B = new(src.loc)
B.icon_state = "mbomb-timing"
B.active = 1
src.visible_message("<span style=\"color:red\"><B>[src]</B> plants a bomb and teleports away!</span>")
qdel(src)
else
patrol_step()
sleeping = 1
/obj/machinery/martianbomb
name = "martian bomb"
desc = "You'd best destroy this thing fast."
icon = 'icons/misc/critter.dmi'
icon_state = "mbomb-off"
anchored = 1
density = 1
var/health = 100
var/active = 0
var/timeleft = 300
process()
if (src.active)
src.icon_state = "mbomb-timing"
src.timeleft -= 1
if (src.timeleft <= 30) src.icon_state = "mbomb-det"
if (src.timeleft == 0)
explosion_new(src, src.loc, 62)
qdel (src)
//proc/explosion(turf/epicenter, devastation_range, heavy_impact_range, light_impact_range, flash_range)
else
src.icon_state = "mbomb-off"
ex_act(severity)
if(severity)
src.visible_message("<span style=\"color:blue\"><B>[src]</B> crumbles away into dust!</span>")
qdel (src)
return
bullet_act(var/obj/projectile/P)
var/damage = 0
damage = round((P.power*P.proj_data.ks_ratio), 1.0)
if(src.material) src.material.triggerOnAttacked(src, P.shooter, src, (ismob(P.shooter) ? P.shooter:equipped() : P.shooter))
for(var/atom/A in src)
if(A.material)
A.material.triggerOnAttacked(A, P.shooter, src, (ismob(P.shooter) ? P.shooter:equipped() : P.shooter))
if(P.proj_data.damage_type == D_KINETIC)
if(damage >= 20)
src.health -= damage
else
damage = 0
else if(P.proj_data.damage_type == D_PIERCING)
src.health -= (damage*2)
else if(P.proj_data.damage_type == D_ENERGY)
src.health -= damage
else
damage = 0
if(damage >= 15)
if (src.active && src.timeleft > 10)
for(var/mob/O in hearers(src, null))
O.show_message("<span style=\"color:red\"><B>[src]</B> begins buzzing loudly!</span>", 1)
src.timeleft = 10
if (src.health <= 0)
src.visible_message("<span style=\"color:blue\"><B>[src]</B> crumbles away into dust!</span>")
qdel (src)
attackby(obj/item/W as obj, mob/user as mob)
..()
src.health -= W.force
if (src.active && src.timeleft > 10)
for(var/mob/O in hearers(src, null))
O.show_message("<span style=\"color:red\"><B>[src]</B> begins buzzing loudly!</span>", 1)
src.timeleft = 10
if (src.health <= 0)
src.visible_message("<span style=\"color:blue\"><B>[src]</B> crumbles away into dust!</span>")
qdel (src)
File diff suppressed because it is too large Load Diff
File diff suppressed because it is too large Load Diff
+143
View File
@@ -0,0 +1,143 @@
/obj/critter/maneater
name = "man-eating plant"
desc = "It looks hungry..."
icon_state = "maneater"
density = 1
health = 30
aggressive = 1
defensive = 0
wanderer = 1
opensdoors = 0
atkcarbon = 1
atksilicon = 0
firevuln = 2
brutevuln = 0.5
butcherable = 1
name_the_meat = 0
meat_type = /obj/item/reagent_containers/food/snacks/salad
generic = 0 // get this using the plant quality
New()
..()
playsound(src.loc, pick("sound/voice/MEilive.ogg"), 45, 0)
seek_target()
src.anchored = 0
for (var/mob/living/C in hearers(src.seekrange,src))
if ((C.name == src.oldtarget_name) && (world.time < src.last_found + 100)) continue
if (iscarbon(C) && !src.atkcarbon) continue
if (istype(C, /mob/living/silicon/) && !src.atksilicon) continue
if (C.job == "Botanist") continue
if (C.health < 0) continue
if (C in src.friends) continue
if (iscarbon(C) && src.atkcarbon) src.attack = 1
if (istype(C, /mob/living/silicon/) && src.atksilicon) src.attack = 1
if (src.attack)
src.target = C
src.oldtarget_name = C.name
src.visible_message("<span class='combat'><b>[src]</b> charges at [C.name]!</span>")
playsound(src.loc, pick('sound/voice/MEhunger.ogg', 'sound/voice/MEraaargh.ogg', 'sound/voice/MEruncoward.ogg', 'sound/voice/MEbewarecoward.ogg'), 40, 0)
src.task = "chasing"
break
else continue
ChaseAttack(mob/M)
src.visible_message("<span class='combat'><B>[src]</B> slams into [M]!</span>")
playsound(src.loc, "sound/weapons/genhit1.ogg", 50, 1, -1)
M.stunned += rand(1,4)
M.weakened += rand(1,4)
CritterAttack(mob/M)
src.attacking = 1
src.visible_message("<span class='combat'><B>[src]</B> starts trying to eat [M]!</span>")
spawn(70)
if (get_dist(src, M) <= 1 && ((M:loc == target_lastloc)) && src.alive) // added a health check so dead maneaters stop eating people - cogwerks
if(iscarbon(M))
src.visible_message("<span class='combat'><B>[src]</B> ravenously wolfs down [M]!</span>")
logTheThing("combat", M, null, "was devoured by [src] at [log_loc(src)].") // Some logging for instakill critters would be nice (Convair880).
playsound(src.loc, "sound/items/eatfood.ogg", 30, 1, -2)
M.death(1)
var/atom/movable/overlay/animation = null
M.transforming = 1
M.canmove = 0
M.icon = null
M.invisibility = 101
if(ishuman(M))
animation = new(src.loc)
animation.icon_state = "blank"
animation.icon = 'icons/mob/mob.dmi'
animation.master = src
if (M.client)
M.ghostize()
qdel(M)
sleeping = 2
src.target = null
src.task = "thinking"
playsound(src.loc, pick("sound/misc/burp_alien.ogg"), 50, 0)
else
if(src.alive) // don't gnash teeth if dead
src.visible_message("<span class='combat'><B>[src]</B> gnashes its teeth in fustration!</span>")
src.attacking = 0
/obj/critter/killertomato
name = "killer tomato"
desc = "Today, Space Station 13 - tomorrow, THE WORLD!"
icon_state = "ktomato"
density = 1
health = 15
aggressive = 1
defensive = 0
wanderer = 1
opensdoors = 1
atkcarbon = 1
atksilicon = 1
firevuln = 2
brutevuln = 2
butcherable = 1
name_the_meat = 0
death_text = "%src% messily splatters into a puddle of tomato sauce!"
meat_type = /obj/item/reagent_containers/food/snacks/plant/tomato/explosive
generic = 0
seek_target()
src.anchored = 0
for (var/mob/living/C in hearers(src.seekrange,src))
if ((C.name == src.oldtarget_name) && (world.time < src.last_found + 100)) continue
if (iscarbon(C) && !src.atkcarbon) continue
if (istype(C, /mob/living/silicon/) && !src.atksilicon) continue
if (C.health < 0) continue
if (C in src.friends) continue
if (C.name == src.attacker) src.attack = 1
if (iscarbon(C) && src.atkcarbon) src.attack = 1
if (istype(C, /mob/living/silicon/) && src.atksilicon) src.attack = 1
if (src.attack)
src.target = C
src.oldtarget_name = C.name
src.visible_message("<span class='combat'><b>[src]</b> charges at [C:name]!</span>")
playsound(src.loc, pick('sound/voice/MEhunger.ogg', 'sound/voice/MEraaargh.ogg', 'sound/voice/MEruncoward.ogg', 'sound/voice/MEbewarecoward.ogg'), 40, 0)
src.task = "chasing"
break
else
continue
ChaseAttack(mob/M)
src.visible_message("<span class='combat'><B>[src]</B> viciously lunges at [M]!</span>")
if (prob(20)) M.stunned += rand(1,3)
random_brute_damage(M, rand(2,5))
CritterAttack(mob/M)
src.attacking = 1
src.visible_message("<span class='combat'><B>[src]</B> bites [src.target]!</span>")
random_brute_damage(src.target, rand(1,2))
spawn(10)
src.attacking = 0
CritterDeath()
..()
playsound(src.loc, "sound/effects/splat.ogg", 100, 1)
var/obj/decal/cleanable/blood/B = new(src.loc)
B.name = "ruined tomato"
qdel (src)
+405
View File
@@ -0,0 +1,405 @@
/obj/critter/nicespider
name = "bumblespider"
desc = "It seems pretty friendly. D'aww."
icon_state = "bumblespider"
health = 30
aggressive = 1
defensive = 1
wanderer = 1
opensdoors = 0
atkcarbon = 0
atksilicon = 0
density = 0
sleeping_icon_state = "bumblespider-sleep"
var/venom1 = "venom"
var/spazzing = 0
CritterAttack(mob/M)
src.attacking = 1
M.visible_message("<span style=\"color:red\"><b>[src]</b> nibbles [src.target]!</span>")
random_brute_damage(M, rand(2,4))
if(iscarbon(M) && M.reagents)
M.reagents.add_reagent("[venom1]", 3)
if(prob(15))
spiderspaz(src.target)
spawn(10)
src.attacking = 0
attack_hand(mob/user as mob)
if (src.alive)
if (user.a_intent == INTENT_HARM)
return ..()
else
src.visible_message("<span style=\"color:red\"><b>[user]</b> [pick("pets","hugs","snuggles","cuddles")] [src]!</span>")
if (prob(15))
for (var/mob/O in hearers(src, null))
O.show_message("[src] coos[prob(50) ? " happily!" : ""]!",2)
playsound(src.loc, "sound/misc/babynoise.ogg", 40, 0)
return
else
..()
return
proc/spiderspaz(mob/M) //todo: centralize this fucking mess of spiders into one base type
if (spazzing)
return
spazzing = 10
playsound(src.loc, "rustle", 50, 0)
spawn(0)
while(spazzing-- > 0 && src.alive)
src.set_loc(M.loc)
src.pixel_x = rand(-2,2) * 2
src.pixel_y = rand(-2,2) * 2
src.dir = pick(alldirs)
if(prob(30))
src.visible_message("<span style=\"color:red\"><B>[src]</B> bites [src.target]!</span>")
playsound(src.loc, "rustle", 50, 1)
random_brute_damage(src.target, rand(1,2))
M.reagents.add_reagent("[venom1]", 2)
sleep(4)
src.pixel_x = 0
src.pixel_y = 0
if(spazzing < 0)
spazzing = 0
/obj/item/reagent_containers/food/snacks/ingredient/egg/critter/nicespider
name = "bumblespider egg"
critter_type = /obj/critter/nicespider
/obj/critter/spider
name = "space spider"
desc = "A big ol' spider, from space. In space. A space spider."
density = 1
health = 50
aggressive = 0
defensive = 1
wanderer = 1
opensdoors = 0
atkcarbon = 1
atksilicon = 1
firevuln = 0.65
brutevuln = 0.45
angertext = "scuttles towards"
butcherable = 1
var/spazzing = 0
var/feeding = 0
var/venom1 = "venom" // making these modular so i don't have to rewrite this gigantic goddamn section for all the subtypes
var/venom2 = "spiders"
var/babyspider = 0
var/adultpath = null
var/bitesound = 'sound/weapons/handcuffs.ogg'
var/stepsound = null
var/deathsound = 'sound/effects/snap.ogg'
death_text = "%src% crumples up into a ball!"
var/encase_in_web = 1 // do they encase people in web or ice?
var/reacting = 1 // when they inject their venom, does it react immediately or not?
skinresult = /obj/item/material_piece/cloth/spidersilk
max_skins = 4
New()
..()
if (!icon_state && !babyspider)
icon_state = pick("big_spide", "big_spide-red", "big_spide-green", "big_spide-blue")
src.dead_state = "[src.icon_state]-dead"
CritterDeath()
if(!src.alive) return
..()
playsound(src.loc, src.deathsound, 50, 0)
src.reagents.add_reagent(venom1, 50, null)
src.reagents.add_reagent(venom2, 50, null)
seek_target()
src.anchored = 0
if (src.target)
src.task = "chasing"
return
for (var/mob/living/C in hearers(src.seekrange,src))
if ((C.name == src.oldtarget_name) && (world.time < src.last_found + 100)) continue
//if (C.stat || C.health < 0) continue
if (C.bioHolder.HasEffect("husk")) continue
src.target = C
src.oldtarget_name = C.name
src.task = "chasing"
playsound(src.loc, "sound/effects/cat_hiss.ogg", 50, 1)
src.visible_message("<span style=\"color:red\"><B>[src]</B> hisses!</span>")
break
Move()
if (src.stepsound)
if(prob(30))
playsound(src.loc, src.stepsound, 50, 0)
..()
CritterAttack(mob/M)
if(ismob(M))
src.attacking = 1
if (prob(20))
src.visible_message("<span style=\"color:red\"><B>[src]</B> dives on [M]!</span>")
playsound(src.loc, "sound/weapons/thudswoosh.ogg", 50, 0)
M.weakened += rand(2,4)
M.stunned += rand(1,3)
random_brute_damage(M, rand(2,5))
src.spiderspaz(src.target)
if(!M.stat) M.emote("scream") // don't scream while dead/asleep // why?
else
src.visible_message("<span style=\"color:red\"><B>[src]</B> bites [src.target]!</span>")
playsound(src.loc, src.bitesound, 50, 1)
if(ishuman(M))
random_brute_damage(src.target, rand(1,2))
src.reagents.add_reagent("[venom1]", 2) // doing this instead of directly adding reagents to M should give people the correct messages
src.reagents.add_reagent("[venom2]", 2)
if (src.reacting)
src.reagents.reaction(M, INGEST)
else
src.reagents.trans_to(M, 4)
else if(issilicon(M))
switch(rand(1,4))
if(1)
M:compborg_take_critter_damage("r_arm", rand(2,4))
if(2)
M:compborg_take_critter_damage("l_arm", rand(2,4))
if(3)
M:compborg_take_critter_damage("r_leg", rand(2,4))
if(4)
M:compborg_take_critter_damage("l_leg", rand(2,4))
if(ishuman(M))
if(M.stat == 1) // kill KOd people faster
src.set_loc(M.loc)
src.visible_message("<span style=\"color:red\"><B>[src]</B> jumps onto [src.target]!</span>")
sleep(5)
src.visible_message("<span style=\"color:red\"><B>[src]</B> sinks its fangs into [src.target]!</span>")
playsound(src.loc, "sound/misc/fuse.ogg", 50, 1)
src.reagents.add_reagent("[venom1]", 5) // doing this instead of directly adding reagents to M should give people the correct messages
src.reagents.add_reagent("[venom2]", 5)
if (src.reacting)
src.reagents.reaction(M, INGEST)
else
src.reagents.trans_to(M, 10)
random_brute_damage(M, rand(2,5))
if(M.stat == 2 && !feeding) // drain corpses into husks
if(ishuman(M))
var/mob/living/carbon/human/T = M
feeding = 1
src.spiderspaz(src.target)
src.visible_message("<span style=\"color:red\"><B>[src]</B> starts draining the fluids out of [T]!</span>")
src.set_loc(T.loc)
sleep(20)
playsound(src.loc, "sound/misc/pourdrink.ogg", 50, 1)
sleep(50)
if(src.target && T.stat && src.loc == T.loc) // check to see if the target is still passed out and under the spider
src.visible_message("<span style=\"color:red\"><B>[src]</B> drains [T] dry!</span>")
T.death(0)
T.real_name = "Unknown"
T.bioHolder.AddEffect("husk")
sleep(2)
playsound(src.loc, "sound/misc/fuse.ogg", 50, 1)
src.set_loc(get_step(src, pick(alldirs))) // get the fuck out of the way of the ice cube
sleep(2)
var/obj/icecube/cube = new /obj/icecube(get_turf(M), M)
M.set_loc(cube)
if (src.encase_in_web)
src.visible_message("<span style=\"color:red\"><B>[src]</B> encases [src.target] in web!</span>")
cube.name = "bundle of web"
cube.desc = "A big wad of web. Someone seems to be stuck inside it."
cube.icon_state = "web2"
cube.steam_on_death = 0
else
src.visible_message("<span style=\"color:red\"><B>[src]</B> encases [src.target] in ice!</span>")
feeding = 0
if (babyspider) // dawww
src.visible_message("<span style=\"color:red\"><B>[src]</B> grows up!</span>")
var/adult = text2path(src.adultpath)
new adult(src.loc)
qdel(src)
else
feeding = 0
spawn(20)
src.attacking = 0
ChaseAttack(mob/M)
playsound(src.loc, "sound/effects/cat_hiss.ogg", 50, 1)
src.visible_message("<span style=\"color:red\"><B>[src]</B> hisses!</span>")
if (prob(30))
src.visible_message("<span style=\"color:red\"><B>[src]</B> dives on [M]!</span>")
playsound(src.loc, pick("sound/weapons/thudswoosh.ogg"), 50, 0)
M.weakened += rand(2,4)
M.stunned += rand(1,3)
random_brute_damage(M, rand(2,5))
src.spiderspaz(src.target)
if(!M.stat) M.emote("scream") // don't scream while dead or KOd
else src.visible_message("<span style=\"color:red\"><B>[src]</B> dives at [M], but misses!</span>")
on_pet()
playsound(src.loc, 'sound/misc/babynoise.ogg', 50, 1)
src.visible_message("<span style=\"color:red\"><b>[src] coos!</b></span>", 1)
proc/spiderspaz(mob/M)
if (spazzing)
return
spazzing = 10
if (src.stepsound)
playsound(src.loc, src.stepsound, 50, 0)
spawn(0)
while(spazzing-- > 0 && src.alive)
src.set_loc(M.loc)
src.pixel_x = rand(-2,2) * 2
src.pixel_y = rand(-2,2) * 2
src.dir = pick(alldirs)
if(prob(30))
src.visible_message("<span style=\"color:red\"><B>[src]</B> bites [src.target]!</span>")
playsound(src.loc, src.bitesound, 50, 1)
if(ishuman(M))
random_brute_damage(src.target, rand(1,2))
src.reagents.add_reagent("[venom1]", 2) // doing this instead of directly adding reagents to M should give people the correct messages
src.reagents.add_reagent("[venom2]", 2)
if (src.reacting)
src.reagents.reaction(M, INGEST)
else
src.reagents.trans_to(M, 4)
else if(issilicon(M))
switch(rand(1,4))
if(1)
M:compborg_take_critter_damage("r_arm", rand(2,4))
if(2)
M:compborg_take_critter_damage("l_arm", rand(2,4))
if(3)
M:compborg_take_critter_damage("r_leg", rand(2,4))
if(4)
M:compborg_take_critter_damage("l_leg", rand(2,4))
sleep(4)
src.pixel_x = 0
src.pixel_y = 0
if(spazzing < 0)
spazzing = 0
/obj/critter/spider/baby
name = "li'l space spider"
desc = "A li'l tiny spider, from space. In space. A space spider."
icon_state = "lil_spide"
density = 0
health = 1
venom1 = "toxin"
venom2 = "black_goop"
babyspider = 1
max_skins = 1
adultpath = "/obj/critter/spider"
// don't ask
proc/streak(var/list/directions)
spawn (0)
for (var/i = 0, i < pick(1, 200; 2, 150; 3, 50; 4), i++)
sleep(3)
if (step_to(src, get_step(src, pick(directions)), 0))
break
/obj/item/reagent_containers/food/snacks/ingredient/egg/critter/spider
name = "spider egg"
critter_type = /obj/critter/spider/baby
critter_reagent = "spiders"
/obj/critter/spider/ice
name = "ice spider"
desc = "It seems to be adapted to a frozen climate."
icon_state = "icespider"
density = 1
health = 20
aggressive = 1
firevuln = 1.5
brutevuln = 0.5
hitsound = 'sound/effects/crystalhit.ogg'
venom1 = "toxin"
venom2 = "cryostylane"
babyspider = 0
bitesound = 'sound/effects/crystalhit.ogg'
stepsound = 'sound/misc/glass_step.ogg'
deathsound = 'sound/effects/crystalshatter.ogg'
encase_in_web = 0
max_skins = 4
reacting = 0
/// subtypes
/obj/critter/spider/ice/baby
name = "baby ice spider"
desc = "Dawww."
icon_state = "babyicespider"
density = 0
health = 1
venom1 = "toxin"
venom2 = "cryostylane"
babyspider = 1
max_skins = 1
adultpath = "/obj/critter/spider/ice"
/obj/item/reagent_containers/food/snacks/ingredient/egg/critter/icespider
name = "ice spider egg"
critter_type = /obj/critter/spider/ice/baby
warm_count = 25
critter_reagent = "spidereggs"
/obj/critter/spider/ice/queen
name = "queen ice spider"
desc = "AHHHHHHH"
icon_state = "gianticespider"
density = 1
health = 100
venom1 = "morphine"
venom2 = "spidereggs"
skinresult = /obj/item/material_piece/cloth/spidersilk
max_skins = 8
/obj/critter/spider/ice/nice
name = "nice spider"
desc = "Aww, hi there!"
aggressive = 0
defensive = 0
atkcarbon = 0
atksilicon = 0
venom1 = "hugs"
venom2 = "glitter_harmless"
/obj/critter/spider/ice/queen/nice
name = "queen nice spider"
desc = "AWWWWWWW!"
icon_state = "gianticespider"
aggressive = 0
defensive = 0
atkcarbon = 0
atksilicon = 0
venom1 = "hugs"
venom2 = "glitter_harmless"
/obj/critter/spider/spacerachnid // you get to be in here TOO
name = "spacerachnid"
desc = "A rather large spider."
icon_state = "spider"
density = 1
health = 10
aggressive = 1
defensive = 0
wanderer = 1
opensdoors = 1
atkcarbon = 1
atksilicon = 1
atcritter = 1
firevuln = 0.65
brutevuln = 0.45
venom1 = "venom"
venom2 = "venom"
death_text = "%src% is squashed!"
/obj/item/reagent_containers/food/snacks/ingredient/egg/critter/spacerachnid
name = "spacerachnid egg"
critter_type = /obj/critter/spider/spacerachnid
critter_reagent = "spiders"
+419
View File
@@ -0,0 +1,419 @@
/////////// cogwerks - hideous wendigo beast
/obj/critter/wendigo
name = "wendigo"
desc = "Oh god."
icon_state = "wendigo"
invisibility = 16
health = 60
firevuln = 1
brutevuln = 0.5
aggressive = 1
defensive = 1
wanderer = 1
opensdoors = 0
seekrange = 6
density = 0
butcherable = 1
can_revive = 1
var/boredom_countdown = 0
var/spazzing = 0
var/frenzied = 0
var/king = 0
var/left_arm_stage = 0
var/right_arm_stage = 0
var/obj/item/parts/human_parts/arm/left/wendigo/left_arm
var/obj/item/parts/human_parts/arm/right/wendigo/right_arm
skinresult = /obj/item/material_piece/cloth/wendigohide
New()
src.left_arm = new /obj/item/parts/human_parts/arm/left/wendigo(src)
src.right_arm = new /obj/item/parts/human_parts/arm/right/wendigo(src)
..()
on_revive()
if (!src.left_arm)
src.left_arm = new /obj/item/parts/human_parts/arm/left/wendigo(src)
src.left_arm_stage = 0
src.visible_message("<span style=\"color:red\">[src]'s left arm regrows!</span>")
if (!src.right_arm)
src.right_arm = new /obj/item/parts/human_parts/arm/right/wendigo(src)
src.right_arm_stage = 0
src.visible_message("<span style=\"color:red\">[src]'s right arm regrows!</span>")
..()
CritterDeath()
if (src.alive)
playsound(src.loc, "sound/misc/wendigo_cry.ogg", 60, 1)
src.visible_message("<b>[src]</b> dies!")
src.alive = 0
walk_to(src,0)
src.update_dead_icon()
anchored = 0
density = 0
layer = initial(layer)
seek_target()
src.anchored = 0
if (src.target)
src.task = "chasing"
return
for (var/mob/living/C in hearers(src.seekrange,src))
if (!istype(C,/mob/living/silicon/robot/) && !istype(C,/mob/living/carbon/human/)) continue
if ((C.name == src.oldtarget_name) && (world.time < src.last_found + 100)) continue
//if (C.stat || C.health < 0) continue
if(ishuman(C))
var/mob/living/carbon/human/H = C
if(!king && iswerewolf(H))
src.visible_message("<span style=\"color:red\"><b>[src] backs away in fear!</b></span>")
step_away(src, H, 15)
src.dir = get_dir(src, H)
continue
src.boredom_countdown = rand(2,5)
if(king)
boredom_countdown = rand(0,1) // king wendigos are pretty much grump elementals
src.target = C
src.oldtarget_name = C.name
src.task = "chasing"
src.appear()
if(king)
playsound(src.loc, "sound/misc/wendigo_roar.ogg", 75, 1)
src.visible_message("<span style=\"color:red\"><b>[src] roars!</b></span>", 1)
break
proc/update_dead_icon()
if (src.alive)
return
. = "wendigo"
if (!src.left_arm)
. += "-l"
if (!src.right_arm)
. += "-r"
. += "-dead"
icon_state = .
attackby(obj/item/W as obj, mob/living/user as mob)
if (!src.alive)
// TODO: tie this into surgery()
if (istype(W, /obj/item/scalpel))
if (user.zone_sel.selecting == "l_arm")
if (src.left_arm_stage == 0)
user.visible_message("<span style=\"color:red\">[user] slices through the skin and flesh of [src]'s left arm with [W].</span>", "<span style=\"color:red\">You slice through the skin and flesh of [src]'s left arm with [W].</span>")
src.left_arm_stage++
else if (src.left_arm_stage == 2)
user.visible_message("<span style=\"color:red\">[user] cuts through the remaining strips of skin holding [src]'s left arm on with [W].</span>", "<span style=\"color:red\">You cut through the remaining strips of skin holding [src]'s left arm on with [W].</span>")
src.left_arm_stage++
src.left_arm.quality = (src.quality + 150) / 350.0
var/nickname = "king"
if (src.quality < 200)
nickname = src.quality_name
if (nickname)
src.left_arm.name = "[nickname] [initial(src.left_arm.name)]"
var/turf/location = get_turf(src)
if (location)
src.left_arm.set_loc(location)
src.left_arm = null
src.update_dead_icon()
else if (user.zone_sel.selecting == "r_arm")
if (src.right_arm_stage == 0)
user.visible_message("<span style=\"color:red\">[user] slices through the skin and flesh of [src]'s right arm with [W].</span>", "<span style=\"color:red\">You slice through the skin and flesh of [src]'s right arm with [W].</span>")
src.right_arm_stage++
else if (src.right_arm_stage == 2)
user.visible_message("<span style=\"color:red\">[user] cuts through the remaining strips of skin holding [src]'s right arm on with [W].</span>", "<span style=\"color:red\">You cut through the remaining strips of skin holding [src]'s right arm on with [W].</span>")
src.right_arm_stage++
src.right_arm.quality = (src.quality + 100) / 350.0
var/nickname = "king"
if (src.quality < 200)
nickname = src.quality_name
if (nickname)
src.right_arm.name = "[nickname] [initial(src.right_arm.name)]"
var/turf/location = get_turf(src)
if (location)
src.right_arm.set_loc(location)
src.right_arm = null
src.update_dead_icon()
else if (istype(W, /obj/item/circular_saw))
if (user.zone_sel.selecting == "l_arm")
if (src.left_arm_stage == 1)
user.visible_message("<span style=\"color:red\">[user] saws through the bone of [src]'s left arm with [W].</span>", "<span style=\"color:red\">You saw through the bone of [src]'s left arm with [W].</span>")
src.left_arm_stage++
else if (user.zone_sel.selecting == "r_arm")
if (src.right_arm_stage == 1)
user.visible_message("<span style=\"color:red\">[user] saws through the bone of [src]'s right arm with [W].</span>", "<span style=\"color:red\">You saw through the bone of [src]'s right arm with [W].</span>")
src.right_arm_stage++
else
..()
return
var/attack_force = 0
var/damage_type = "brute"
if (istype(W, /obj/item/artifact/melee_weapon))
var/datum/artifact/melee/ME = W.artifact
attack_force = ME.dmg_amount
damage_type = ME.damtype
else
attack_force = W.force
damage_type = W.damtype
switch(damage_type)
if("fire")
src.health -= attack_force * src.firevuln
if("brute")
src.health -= attack_force * src.brutevuln
else
src.health -= attack_force * src.miscvuln
for(var/mob/O in viewers(src, null))
O.show_message("<span style=\"color:red\"><b>[user]</b> hits [src] with [W]!</span>", 1)
if(prob(30))
playsound(src.loc, "sound/misc/wendigo_cry.ogg", 60, 1)
src.visible_message("<span style=\"color:red\"><b>[src] cries!</b></span>", 1)
if(prob(25) && alive) // crowds shouldn't be able to beat the fuck out of a confused wendigo with impunity, fuck that
src.target = user
src.oldtarget_name = user.name
src.task = "chasing"
playsound(src.loc, "sound/weapons/genhit1.ogg", 60, 1)
src.visible_message("<span style=\"color:red\"><b>[src]</b> slams into [src.target]!</span>")
target:weakened += 2
frenzy(src.target)
if (src.alive && src.health <= 0) src.CritterDeath()
//src.boredom_countdown = rand(5,10)
src.target = user
src.oldtarget_name = user.name
src.task = "chasing"
attack_hand(var/mob/user as mob)
if (!src.alive)
..()
return
if (user.a_intent == INTENT_HARM)
src.health -= rand(1,2) * src.brutevuln
on_damaged(src)
for(var/mob/O in viewers(src, null))
O.show_message("<span style=\"color:red\"><b>[user]</b> punches [src]!</span>", 1)
playsound(src.loc, "punch", 50, 1)
if(prob(30))
playsound(src.loc, "sound/misc/wendigo_cry.ogg", 60, 1)
src.visible_message("<span style=\"color:red\"><b>[src] cries!</b></span>", 1)
if(prob(20) && alive) // crowd beatdown fix
src.target = user
src.oldtarget_name = user.name
src.task = "chasing"
playsound(src.loc, "sound/weapons/genhit1.ogg", 50, 1)
src.visible_message("<span style=\"color:red\"><b>[src]</b> slams into [src.target]!</span>")
target:weakened += 20
frenzy(src.target)
if (src.alive && src.health <= 0) src.CritterDeath()
//src.boredom_countdown = rand(5,10)
src.target = user
src.oldtarget_name = user.name
src.task = "chasing"
else
src.visible_message("<span style=\"color:red\"><b>[user]</b> pets [src]!</span>", 1)
playsound(src.loc, "sound/misc/wendigo_laugh.ogg", 60, 1)
src.visible_message("<span style=\"color:red\"><b>[src] laughs!</b></span>", 1)
on_sleep()
..()
src.disappear()
ChaseAttack(mob/M)
if(prob(10))
playsound(src.loc, "sound/misc/wendigo_scream.ogg", 75, 1)
src.visible_message("<span style=\"color:red\"><b>[src] howls!</b></span>", 1)
src.visible_message("<span style=\"color:red\"><B>[src]</B> tackles [M]!</span>")
playsound(src.loc, "sound/weapons/genhit1.ogg", 50, 1, -1)
if(ismob(M))
M.stunned += rand(1,2)
M.weakened += rand(1,2)
CritterAttack(mob/M) // nominating this for scariest goddamn critter 2013
src.attacking = 1
var/attack_delay = rand(10,30) // needs to attack more often, changed from 30
if (istype(M,/mob/living/silicon/robot/))
var/mob/living/silicon/robot/BORG = M
if (!BORG.part_head)
src.visible_message("<span style=\"color:red\"><B>[src]</B> sniffs at [BORG.name].</span>")
sleep(15)
src.visible_message("<span style=\"color:red\"><B>[src]</B> throws a tantrum and smashes [BORG.name] to pieces!</span>")
playsound(src.loc, "sound/misc/wendigo_scream.ogg", 75, 1)
playsound(src.loc, "sound/effects/wbreak.wav", 70, 1)
BORG.gib()
src.target = null
src.boredom_countdown = 0
else
if (BORG.part_head.ropart_get_damage_percentage() >= 85)
src.visible_message("<span style=\"color:red\"><B>[src]</B> grabs [BORG.name]'s head and wrenches it right off!</span>")
playsound(src.loc, "sound/misc/wendigo_laugh.ogg", 70, 1)
playsound(src.loc, "sound/effects/wbreak.wav", 70, 1)
BORG.compborg_lose_limb(BORG.part_head)
sleep(15)
src.visible_message("<span style=\"color:red\"><B>[src]</B> ravenously eats the mangled brain remnants out of the decapitated head!</span>")
playsound(src.loc, "sound/misc/wendigo_maul.ogg", 80, 1)
new /obj/decal/cleanable/blood(src.loc)
src.target = null
else
src.visible_message("<span style=\"color:red\"><B>[src]</B> pounds on [BORG.name]'s head furiously!</span>")
playsound(src.loc, "sound/effects/zhit.ogg", 50, 1)
BORG.part_head.ropart_take_damage(rand(20,40),0)
if (prob(33)) playsound(src.loc, "sound/misc/wendigo_scream.ogg", 75, 1)
attack_delay = 5
else
if (boredom_countdown-- > 0)
if(prob(70))
src.visible_message("<span style=\"color:red\"><B>[src]</B> [pick("bites", "nibbles", "chews on", "gnaws on")] [src.target]!</span>")
playsound(src.loc, "sound/effects/bloody_stab.ogg", 50, 1)
playsound(src.loc, "sound/items/eatfood.ogg", 50, 1)
random_brute_damage(target, 10)
take_bleeding_damage(target, null, 5, DAMAGE_STAB, 1, get_turf(target))
if(prob(40))
playsound(src.loc, "sound/misc/wendigo_laugh.ogg", 70, 1)
src.visible_message("<span style=\"color:red\"><b>[src] laughs!</b></span>", 1)
else
src.visible_message("<span style=\"color:red\"><B>[src]</B> [pick("slashes", "swipes", "claws", "tears")] a chunk out of [src.target]!</span>")
playsound(src.loc, "sound/effects/bloody_stab.ogg", 50, 1)
random_brute_damage(target, 20)
take_bleeding_damage(target, null, 10, DAMAGE_CUT, 0, get_turf(target))
playsound(src.loc, "sound/effects/splat.ogg", 50, 1)
playsound(src.loc, "sound/misc/wendigo_scream.ogg", 75, 1)
src.visible_message("<span style=\"color:red\"><b>[src] howls!</b></span>", 1)
if(!M.stat) M.emote("scream") // don't scream while dead/asleep
else // flip the fuck out
playsound(src.loc, "sound/weapons/genhit1.ogg", 50, 1)
src.visible_message("<span style=\"color:red\"><b>[src]</b> slams into [src.target]!</span>")
target:weakened += 3
frenzy(src.target)
if (M.stat == 2) // devour corpses
src.visible_message("<span style=\"color:red\"><b>[src] devours [src.target]! Holy shit!</b></span>")
playsound(src.loc, "sound/effects/fleshbr1.ogg", 50, 1)
M.ghostize()
new /obj/decal/skeleton(M.loc)
M.gib()
src.target = null
spawn(attack_delay)
src.attacking = 0
proc/appear()
if (!invisibility)
return
src.icon_state = "wendigo_appear"
src.invisibility = 0
density = 1
spawn(12)
if(king)
src.icon_state = "wendigoking"
else
src.icon_state = "wendigo"
playsound(src.loc, "sound/misc/wendigo_scream.ogg", 85, 1)
src.visible_message("<span style=\"color:red\"><B>[src]</B> howls!</span>")
return
proc/disappear()
if (invisibility)
return
src.icon_state = "wendigo_melt"
density = 0
spawn(12)
src.invisibility = 16
if(king)
src.icon_state = "wendigoking"
else
src.icon_state = "wendigo"
return
proc/spaz()
if (spazzing)
return
spazzing = 25
spawn(0)
while(spazzing-- > 0)
src.pixel_x = rand(-2,2) * 2
src.pixel_y = rand(-2,2) * 2
src.dir = pick(alldirs)
sleep(4)
src.pixel_x = 0
src.pixel_y = 0
if(spazzing < 0)
spazzing = 0
// go crazy and make a huge goddamn mess
proc/frenzy(mob/M)
if (src.frenzied)
return
spawn(0)
src.visible_message("<span style=\"color:red\"><b>[src] goes [pick("into a frenzy", "into a bloodlust", "berserk", "hog wild", "crazy")]!</b></span>")
playsound(src.loc, "sound/misc/wendigo_maul.ogg", 80, 1)
if(king)
playsound(src.loc, "sound/misc/wendigo_roar.ogg", 80, 1)
src.visible_message("<span style=\"color:red\"><b>[src] roars!</b></span>")
spawn(1)
if(!spazzing) src.spaz()
src.set_loc(M.loc)
src.frenzied = 20
while(src.target && src.frenzied && src.alive && src.loc == M.loc )
src.visible_message("<span style=\"color:red\"><b>[src] [pick("mauls", "claws", "slashes", "tears at", "lacerates", "mangles")] [src.target]!</b></span>")
random_brute_damage(target, 10)
take_bleeding_damage(target, null, 5, DAMAGE_CUT, 0, get_turf(target))
if(prob(33)) // don't make quite so much mess
bleed(target, 5, 5, get_step(src.loc, pick(alldirs)), 1)
if(king && prob(33))
bleed(target, 5, 5, get_step(src.loc, pick(alldirs)), 1)
sleep(4)
src.frenzied--
src.frenzied = 0
////////////////
//////king wendigo, why not
///////////////
/obj/critter/wendigo/king
name = "wendigo king"
desc = "You should run."
health = 500
icon_state = "wendigoking"
king = 1
skinresult = /obj/item/material_piece/cloth/kingwendigohide
New()
..()
quality = 200 // for the limbs
CritterDeath()
playsound(src.loc, "sound/misc/wendigo_roar.ogg", 75, 1)
playsound(src.loc, "sound/misc/wendigo_cry.ogg", 75, 1)
src.visible_message("<b>[src]</b> collapses in a heap!")
src.alive = 0
walk_to(src,0)
icon_state = "wendigoking-dead"
density = 0
////////////////
////// e-egg?
///////////////
/obj/item/reagent_containers/food/snacks/ingredient/egg/critter/wendigo
name = "wendigo egg"
desc = "They lay eggs?!"
critter_type = /obj/critter/wendigo
warm_count = 100
critter_reagent = "ice"
+308
View File
@@ -0,0 +1,308 @@
/obj/critter/zombie
name = "Zombie"
desc = "BraaAAAinnsSSs..."
icon_state = "zombie"
density = 1
health = 20
aggressive = 1
defensive = 0
wanderer = 1
opensdoors = 1
atkcarbon = 1
atksilicon = 1
atcritter = 1
firevuln = 0.25
brutevuln = 0.5
butcherable = 1
var/punch_damage_max = 9
var/punch_damage_min = 3
var/hulk = 0 //A zombie hulk? Oh god.
var/eats_brains = 1
skinresult = /obj/item/material_piece/cloth/leather
max_skins = 2
New()
..()
playsound(src.loc, pick('sound/voice/Zgroan1.ogg', 'sound/voice/Zgroan2.ogg', 'sound/voice/Zgroan3.ogg', 'sound/voice/Zgroan4.ogg'), 25, 0)
seek_target()
src.anchored = 0
for (var/mob/living/C in hearers(src.seekrange,src))
if ((C.name == src.oldtarget_name) && (world.time < src.last_found + 100)) continue
if (iscarbon(C) && !src.atkcarbon) continue
if (istype(C, /mob/living/silicon/) && !src.atksilicon) continue
if (C.health < 0) continue
if (istype(C,/mob/living/carbon/human))
if (C:mutantrace && istype(C:mutantrace, /datum/mutantrace/zombie)) continue
if (istype(C:head, /obj/item/clothing/head/void_crown)) continue
if (iscarbon(C) && src.atkcarbon) src.attack = 1
if (istype(C, /mob/living/silicon/) && src.atksilicon) src.attack = 1
if (src.attack)
src.target = C
src.oldtarget_name = C.name
src.visible_message("<span style=\"color:red\"><b>[src]</b> lunges at [C.name]!</span>")
playsound(src.loc, pick('sound/voice/Zgroan1.ogg', 'sound/voice/Zgroan2.ogg', 'sound/voice/Zgroan3.ogg', 'sound/voice/Zgroan4.ogg'), 25, 0)
src.task = "chasing"
return
else
continue
if(!src.atcritter) return
for (var/obj/critter/C in view(src.seekrange,src))
if (!C.alive) continue
if (C.health < 0) continue
if (!istype(C, /obj/critter/zombie)) src.attack = 1
if (src.attack)
src.target = C
src.oldtarget_name = C.name
src.visible_message("<span style=\"color:red\"><b>[src]</b> lunges at [C.name]!</span>")
playsound(src.loc, pick('sound/voice/Zgroan1.ogg', 'sound/voice/Zgroan2.ogg', 'sound/voice/Zgroan3.ogg', 'sound/voice/Zgroan4.ogg'), 25, 0)
src.task = "chasing"
return
else continue
ChaseAttack(mob/M)
if(iscarbon(M) && prob(15))
src.visible_message("<span style=\"color:red\"><B>[src]</B> slams into [src.target]!</span>")
playsound(src.loc, "sound/weapons/genhit1.ogg", 50, 1, -1)
random_brute_damage(M, rand(0,3))
M.stunned += rand(0,4)
M.weakened += rand(1,4)
else
src.visible_message("<span style=\"color:red\"><B>[src]</B> tries to knock down [src.target] but misses!</span>")
CritterAttack(mob/living/M)
src.attacking = 1
if(istype(M,/obj/critter))
var/obj/critter/C = M
src.visible_message("<span style=\"color:red\"><B>[src]</B> punches [src.target]!</span>")
playsound(C.loc, "punch", 25, 1, -1)
C.health -= 4
if(C.health <= 0)
C.CritterDeath()
spawn(25)
src.attacking = 0
return
if (M.health > 40 && !M.weakened)
src.visible_message("<span style=\"color:red\"><B>[src]</B> punches [src.target]!</span>")
playsound(M.loc, "punch", 25, 1, -1)
var/to_deal = rand(punch_damage_min,punch_damage_max)
random_brute_damage(M, to_deal)
if(iscarbon(M))
if(to_deal > (((punch_damage_max-punch_damage_min)/2)+punch_damage_min) && prob(50))
src.visible_message("<span style=\"color:red\"><B>[src] knocks down [M]!</B></span>")
M:weakened += 8
// if(prob(4) && eats_brains) //Give the gift of being a zombie (unless we eat them too fast)
// M.contract_disease(/datum/ailment/disease/necrotic_degeneration, null, null, 1) // path, name, strain, bypass resist
if(src.hulk) //TANK!
spawn(0)
M:paralysis += 1
step_away(M,src,15)
spawn(3) step_away(M,src,15)
spawn(25)
src.attacking = 0
else
if(istype(M,/mob/living/carbon/human) && src.eats_brains) //These only make human zombies anyway!
src.visible_message("<span style=\"color:red\"><B>[src]</B> starts trying to eat [M]'s brain!</span>")
else
src.visible_message("<span style=\"color:red\"><B>[src]</B> attacks [src.target]!</span>")
playsound(src.loc, "sound/weapons/genhit1.ogg", 50, 1, -1)
random_brute_damage(src.target, rand(punch_damage_min,punch_damage_max))
spawn(25)
src.attacking = 0
return
spawn(60)
if (get_dist(src, M) <= 1 && ((M:loc == target_lastloc)))
if(iscarbon(M))
logTheThing("combat", M, null, "was zombified by [src] at [log_loc(src)].") // Some logging for instakill critters would be nice (Convair880).
M.death(1)
src.visible_message("<span style=\"color:red\"><B>[src]</B> slurps up [M]'s brain!</span>")
playsound(src.loc, "sound/items/eatfood.ogg", 30, 1, -2)
M.canmove = 0
M.icon = null
M.invisibility = 101
M:death()
var/obj/critter/zombie/P = new(M.loc)
///this little bit of code prevents multiple zombies from the same victim
if (M == null)
qdel(P)
return
src.visible_message("<span style=\"color:red\">[M]'s corpse reanimates!</span>")
//Zombie is all dressed up and no place to go
var/stealthy = 0 //High enough and people won't even see it's undead right away.
if(istype(M,/mob/living/carbon/human))
var/mob/living/carbon/human/H = M
//Uniform
if(H.w_uniform)
if (istype(H.w_uniform, /obj/item/clothing/under))
P.overlays += image("icon" = 'icons/mob/jumpsuits/worn_js.dmi', "icon_state" = H.w_uniform.icon_state, "layer" = FLOAT_LAYER)
stealthy += 4
//Suit
if(H.wear_suit)
if (istype(H.wear_suit, /obj/item/clothing/suit))
P.overlays += image("icon" = 'icons/mob/overcoats/worn_suit.dmi', "icon_state" = H.wear_suit.icon_state, "layer" = FLOAT_LAYER)
stealthy += 2
//Back
if(H.back)
var/t1 = H.back.icon_state
P.overlays += image("icon" = 'icons/mob/back.dmi', "icon_state" = t1, "layer" = FLOAT_LAYER)
//Mask
if (H.wear_mask)
if (istype(H.wear_mask, /obj/item/clothing/mask))
var/t1 = H.wear_mask.icon_state
P.overlays += image("icon" = 'icons/mob/mask.dmi', "icon_state" = t1, "layer" = FLOAT_LAYER)
if (H.wear_mask.c_flags & COVERSEYES)
stealthy += 2
//Shoes
if (H.shoes)
if (istype(H.shoes))
var/t1 = H.shoes.icon_state
P.overlays += image("icon" = 'icons/mob/feet.dmi', "icon_state" = t1, "layer" = FLOAT_LAYER)
stealthy++
//Gloves. Zombie boxers??
if (H.gloves)
if (istype(H.gloves))
var/t1 = H.gloves.item_state
P.overlays += image("icon" = 'icons/mob/hands.dmi', "icon_state" = t1, "layer" = FLOAT_LAYER)
stealthy++
//Head
if (H.head)
var/t1 = H.head.icon_state
var/icon/head_icon = icon('icons/mob/head.dmi', "[t1]")
if (istype(H.head, /obj/item/clothing/head/butt))
var/obj/item/clothing/head/butt/B = H.head
if (B.s_tone >= 0)
head_icon.Blend(rgb(B.s_tone, B.s_tone, B.s_tone), ICON_ADD)
else
head_icon.Blend(rgb(-B.s_tone, -B.s_tone, -B.s_tone), ICON_SUBTRACT)
P.overlays += image("icon" = head_icon, "layer" = FLOAT_LAYER)
if (H.head.c_flags & COVERSEYES)
stealthy += 2
if (H.head.c_flags & COVERSMOUTH)
stealthy += 2
//Oh no, a tank!
if(H.bioHolder.HasEffect("hulk"))
P.hulk = 1
P.punch_damage_max += 4
P.health = src.health
if(stealthy >= 10)
P.name = M.real_name
else
P.name += " [M.real_name]"
var/atom/movable/overlay/animation = null
if(ishuman(M))
animation = new(src.loc)
animation.icon_state = "blank"
animation.icon = 'icons/mob/mob.dmi'
animation.master = src
if (M.client)
var/mob/dead/observer/newmob
newmob = new/mob/dead/observer(M)
M.client:mob = newmob
M.mind.transfer_to(newmob)
qdel(M)
qdel(animation)
sleeping = 2
spawn(20) playsound(src.loc, pick("sound/misc/burp_alien.ogg"), 50, 0)
else
src.visible_message("<span style=\"color:red\"><B>[src]</B> gnashes its teeth in fustration!</span>")
src.attacking = 0
CritterDeath()
src.alive = 0
playsound(src.loc, "sound/effects/splat.ogg", 100, 1)
var/obj/decal/cleanable/blood/gibs/gib = null
gib = new /obj/decal/cleanable/blood/gibs(src.loc)
if (prob(30))
gib.icon_state = "gibup1"
gib.streak(list(NORTH, NORTHEAST, NORTHWEST))
qdel (src)
/obj/critter/zombie/scientist
name = "Shambling Scientist"
desc = "Physician, heal thyself! Welp, so much for that."
icon_state = "scizombie"
health = 10
firevuln = 0.15
generic = 0
ChaseAttack(mob/M)
if(!attacking)
src.CritterAttack(M)
return
/obj/critter/zombie/security
name = "Undead Guard"
desc = "Eh, couldn't be any worse than regular security."
icon_state = "seczombie"
health = 18
brutevuln = 0.6
generic = 0
ChaseAttack(mob/M)
if(!attacking)
src.CritterAttack(M)
return
CritterDeath()
src.alive = 0
playsound(src.loc, "sound/effects/splat.ogg", 100, 1)
gibs(src.loc)
qdel (src)
/obj/critter/zombie/h7
name = "Biosuit Shambler"
desc = "This does not reassure one about biosuit reliability."
icon_state = "suitzombie"
health = 10
brutevuln = 0.6
atcritter = 0
eats_brains = 0
generic = 0
ChaseAttack(mob/M)
if(!attacking)
src.CritterAttack(M)
return
CritterDeath()
src.alive = 0
src.visible_message("<span style=\"color:red\">Black mist flows from the broken suit!</span>")
playsound(src.loc, "sound/machines/hiss.ogg", 50, 1)
harmless_smoke_puff(src.loc)
new /obj/critter/aberration(src.loc)
new /obj/item/clothing/suit/bio_suit(src.loc)
new /obj/item/clothing/gloves/latex(src.loc)
new /obj/item/clothing/head/bio_hood(src.loc)
qdel (src)
//It's like the jam mansion is back!
/obj/critter/zombie/hogan
name = "Zombie Hogan"
desc = "Hulkamania is shambling wiilllldd in space!"
icon_state = "hoganzombie"
health = 25
firevuln = 0.15
hulk = 1
generic = 0
ChaseAttack(mob/M)
if(!attacking)
src.CritterAttack(M)
return
+217
View File
@@ -0,0 +1,217 @@
/obj/datacore
name = "datacore"
var/list/medical = list( )
var/list/general = list( )
var/list/security = list( )
var/list/bank = list ( )
var/list/fines = list ( )
var/list/tickets = list ( )
var/obj/machinery/networked/mainframe/mainframe = null
/obj/datacore/proc/addManifest(var/mob/living/carbon/human/H as mob)
if (!H || !H.mind)
return
var/datum/data/record/G = new /datum/data/record( )
var/datum/data/record/M = new /datum/data/record( )
var/datum/data/record/S = new /datum/data/record( )
var/datum/data/record/B = new /datum/data/record( )
if (H.mind.assigned_role)
G.fields["rank"] = H.mind.assigned_role
else
G.fields["rank"] = "Unassigned"
G.fields["name"] = H.real_name
G.fields["id"] = text("[]", add_zero(num2hex(rand(1, 1.6777215E7)), 6))
M.fields["name"] = G.fields["name"]
M.fields["id"] = G.fields["id"]
S.fields["name"] = G.fields["name"]
S.fields["id"] = G.fields["id"]
B.fields["name"] = G.fields["name"]
B.fields["id"] = G.fields["id"]
if (H.gender == FEMALE)
G.fields["sex"] = "Female"
else
G.fields["sex"] = "Male"
G.fields["age"] ="[H.bioHolder.age]"
G.fields["fingerprint"] = "[md5(H.bioHolder.Uid)]"
G.fields["dna"] = H.bioHolder.Uid
G.fields["p_stat"] = "Active"
G.fields["m_stat"] = "Stable"
spawn(10)
G.fields["file_photo"] = H.build_flat_icon()
M.fields["bioHolder.bloodType"] = "[H.bioHolder.bloodType]"
M.fields["mi_dis"] = "None"
M.fields["mi_dis_d"] = "No minor disabilities have been declared."
M.fields["ma_dis"] = "None"
M.fields["ma_dis_d"] = "No major disabilities have been diagnosed."
M.fields["alg"] = "None"
M.fields["alg_d"] = "No allergies have been detected in this patient."
M.fields["cdi"] = "None"
M.fields["cdi_d"] = "No diseases have been diagnosed at the moment."
M.fields["h_imp"] = "No health implant detected."
M.fields["notes"] = "No notes."
M.fields["dnasample"] = create_new_dna_sample_file(H)
var/traitStr = ""
if(H.traitHolder)
for(var/X in H.traitHolder.traits)
var/obj/trait/T = getTraitById(X)
if(length(traitStr)) traitStr += " | [T.cleanName]"
else traitStr = T.name
M.fields["traits"] = traitStr
S.fields["criminal"] = "None"
S.fields["mi_crim"] = "None"
S.fields["mi_crim_d"] = "No minor crime convictions."
S.fields["ma_crim"] = "None"
S.fields["ma_crim_d"] = "No major crime convictions."
S.fields["notes"] = "No notes."
B.fields["job"] = H.job
B.fields["current_money"] = 100.0
B.fields["notes"] = "No notes."
// If it exists for a job give them the correct wage
var/wageMult = 1
if(H.traitHolder.hasTrait("unionized"))
wageMult = 1.5
if(wagesystem.jobs[H.job])
B.fields["wage"] = round(wagesystem.jobs[H.job] * wageMult)
// Otherwise give them a default wage
else
var/datum/job/J = find_job_in_controller_by_string(G.fields["rank"])
if (J && J.wages)
B.fields["wage"] = round(J.wages * wageMult)
else
B.fields["wage"] = 0
src.general += G
src.medical += M
src.security += S
src.bank += B
//Add email group
if ("[H.mind.assigned_role]" in job_mailgroup_list)
var/mailgroup = job_mailgroup_list["[H.mind.assigned_role]"]
if (!mailgroup)
return
var/username = format_username(H.real_name)
if (!src.mainframe || !src.mainframe.hd || !(src.mainframe.hd in src.mainframe))
for (var/obj/machinery/networked/mainframe/newMainframe in machines)
if (newMainframe.z != 1 || newMainframe.stat)
continue
if (newMainframe.hd)
src.mainframe = newMainframe
break
if (src.mainframe)
for (var/datum/computer/folder/folder in src.mainframe.hd.root.contents)
if (ckey(folder.name) == "etc")
for (var/datum/computer/folder/folder2 in folder.contents)
if (ckey(folder2.name) == "mail")
for (var/datum/computer/file/record/groups in folder2.contents)
if (ckey(groups.name) != "groups")
continue
if (!groups.fields)
break
for (var/mailgroupEntry in groups.fields)
if (dd_hasprefix(mailgroupEntry, "[mailgroup]:"))
groups.fields -= mailgroupEntry
groups.fields += "[mailgroupEntry][username],"
break
groups.fields += "[mailgroup]:[username],"
break
break
break
return
return
/datum/ticket
var/name = "ticket"
var/target = null
var/reason = null
var/issuer = null
var/issuer_job = null
var/text = null
var/target_byond_key = null
var/issuer_byond_key = null
New()
spawn(10)
statlog_ticket(src, usr)
/datum/fine
var/ID = null
var/name = "fine"
var/target = null
var/reason = null
var/amount = 0
var/issuer = null
var/issuer_job = null
var/approver = null
var/approver_job = null
var/paid_amount = 0
var/paid = 0
var/datum/data/record/bank_record = null
var/target_byond_key = null
var/issuer_byond_key = null
var/approver_byond_key = null
New()
generate_ID()
spawn(10)
for(var/datum/data/record/B in data_core.bank) //gross
if(B.fields["name"] == target)
bank_record = B
break
if(!bank_record) qdel(src)
statlog_fine(src, usr)
/datum/fine/proc/approve(var/approved_by,var/their_job)
if(approver || paid) return
if(!(their_job in list("Captain","Head of Security","Head of Personnel"))) return
approver = approved_by
approver_job = their_job
approver_byond_key = get_byond_key(approver)
if(bank_record.fields["current_money"] >= amount)
bank_record.fields["current_money"] -= amount
paid = 1
paid_amount = amount
else
paid_amount += bank_record.fields["current_money"]
bank_record.fields["current_money"] = 0
spawn(300) process_payment()
/datum/fine/proc/process_payment()
if(bank_record.fields["current_money"] >= (amount-paid_amount))
bank_record.fields["current_money"] -= (amount-paid_amount)
paid = 1
paid_amount = amount
else
paid_amount += bank_record.fields["current_money"]
bank_record.fields["current_money"] = 0
spawn(300) process_payment()
/datum/fine/proc/generate_ID()
if(!ID) ID = (data_core.fines.len + 1)
+177
View File
@@ -0,0 +1,177 @@
/obj/particle_maker
name = "Particle Effect Maker"
desc = "A thing for making nice particles with. It's an admin tool so if you see it ingame please adminhelp about it!"
icon = 'icons/obj/stationobjs.dmi'
icon_state = "holo_console1"
var/datum/particle_maker_var_holder/P = null
New()
P = new /datum/particle_maker_var_holder
proc/Run()
set background = 1
src.visible_message("<b>[src]</b> beginning particle emission.")
for(var/i=0, i < P.particle_amount, i++)
SpawnNew()
sleep(P.particle_delay)
src.visible_message("<b>[src]</b> particle emission finished.")
return
proc/SpawnNew()
if(!istype(src))
return
var/obj/particle/par = unpool(/obj/particle)
if(!istype(par))
return
spawn(P.particle_lifespan)
if (par)
par.alpha = 255
par.blend_mode = 0
par.color = null
par.pixel_x = 0
par.pixel_y = 0
par.transform = null
par.override_state = null
animate(par)
pool(par)
par.set_loc(get_turf(src.loc))
par.blend_mode = P.particle_blend_mode
par.color = P.particle_color
par.icon = P.particle_icon
par.icon_state = P.particle_icon_state
par.pixel_x = P.initial_pixel_x + rand((0 - P.initial_pixel_x_variance),P.initial_pixel_x_variance)
par.pixel_y = P.initial_pixel_y + rand((0 - P.initial_pixel_y_variance),P.initial_pixel_y_variance)
var/x_destination = P.destination_pixel_x + rand((0 - P.destination_pixel_x_variance),P.destination_pixel_x_variance)
var/y_destination = P.destination_pixel_y + rand((0 - P.destination_pixel_y_variance),P.destination_pixel_y_variance)
var/alpha_initial = P.initial_alpha + rand((0 - P.initial_alpha_variance),P.initial_alpha_variance)
var/alpha_destination = P.destination_alpha + rand((0 - P.destination_alpha_variance),P.destination_alpha_variance)
par.alpha = max(0,min(alpha_initial,255))
var/end_alpha = max(0,min(alpha_destination,255))
var/matrix/M = turn(matrix(), rand(P.destination_turn_min, P.destination_turn_max))
M.Scale(rand(P.destination_scale_min,P.destination_scale_max))
animate(par, color = P.particle_destination_color, time = P.animation_time, loop = P.animation_loops, transform = M, pixel_x = x_destination, pixel_y = y_destination, alpha = end_alpha, easing = P.easing)
return
attack_hand(mob/user as mob)
Run()
verb/change_easing()
set src in view(1)
var/ptype = input("Choose easing type","Particles") as null|anything in easing_types
if (ptype)
P.easing = easing_types[ptype]
verb/change_blend()
set src in view(1)
var/ptype = input("Choose blend type","Particles") as null|anything in blend_types
if (ptype)
P.particle_blend_mode = blend_types[ptype]
/datum/particle_maker_var_holder
var/particle_color = "#FF0000"
var/particle_icon = 'icons/effects/particles.dmi'
var/particle_icon_state = "8x8circle"
var/particle_blend_mode = BLEND_ADD
var/particle_delay = 1
var/particle_amount = 20
var/particle_lifespan = 35
var/initial_alpha = 255
var/initial_alpha_variance = 0
var/initial_pixel_x = 0
var/initial_pixel_y = 0
var/initial_pixel_x_variance = 0
var/initial_pixel_y_variance = 0
var/destination_turn_max = 180
var/destination_turn_min = -180
var/destination_scale_min = 0.5
var/destination_scale_max = 0.5
var/destination_alpha = 100
var/destination_alpha_variance = 0
var/animation_time = 10
var/animation_loops = 1
var/destination_pixel_x = 0
var/destination_pixel_y = 0
var/destination_pixel_x_variance = 0
var/destination_pixel_y_variance = 0
var/particle_destination_color = "#0000FF"
var/easing = LINEAR_EASING
/obj/jumpsuit_maker_experiment
name = "jumpsuit making thing"
desc = "this is an admin thing ok just ignore it"
icon = 'icons/obj/stationobjs.dmi'
icon_state = "holo_console1"
var/list/components = list("jumpsuit", "overalls", "jacket", "jacket_heavy", "vest", "shirt", "sleeves", "pants",
"zipper", "belt", "stripe_sides", "stripe_shoulder", "stripe_belt", "stripe_captain", "trim_feet", "trim_hands",
"decal_medic")
var/list/current_pieces = list()
var/list/current_colors = list()
var/list/current_alphas = list()
attack_hand(var/mob/user as mob)
var/dat = "<B>[src.name]</B><HR>"
dat += "<B>Current Jumpsuit:</B><BR>"
var/list_counter = 0
if (current_pieces.len > 0)
for (var/X as anything in current_pieces)
list_counter++
dat += "<b>Piece:</b> [X], <b>Color:</b> [current_colors[list_counter]], <b>Alpha:</b> [current_alphas[list_counter]]<br>"
dat += "<HR>"
if (current_pieces.len > 0)
dat += "<A href='?src=\ref[src];dispense=1'>Dispense Jumpsuit</A><BR>"
dat += "<A href='?src=\ref[src];add=1'>Add New Element</A><BR>"
dat += "<A href='?src=\ref[src];wipe=1'>Erase All Elements</A><BR>"
user << browse(dat, "window=jumpsuitmaker;size=575x450")
onclose(user, "jumpsuitmaker")
return
Topic(href, href_list)
if(..())
return
if (href_list["dispense"])
var/obj/item/clothing/under/experimental/E = new /obj/item/clothing/under/experimental(src.loc)
E.component_images = src.current_pieces
E.component_colors = src.current_colors
E.component_alphas = src.current_alphas
E.update_images()
else if (href_list["add"])
src.current_pieces += input("Select Piece","Jumpsuit Maker") as anything in src.components
src.current_colors += input("Select Color","Jumpsuit Maker") as color
var/new_alpha = input("Input Alpha","Jumpsuit Maker") as num
new_alpha = max(0,min(255,new_alpha))
src.current_alphas += new_alpha
else if (href_list["wipe"])
src.current_pieces = list()
src.current_colors = list()
src.current_alphas = list()
src.updateUsrDialog()
return
/obj/circular_range_tester
name = "circle tester"
desc = "IGNORE ME!!!"
icon = 'icons/obj/stationobjs.dmi'
icon_state = "holo_console1"
attack_hand(mob/user as mob)
var/user_input = input("What size?","Circle Tester") as num
if (user_input <= 0 || user_input > 30)
alert("fuck you nerd","what are you doing")
return
for(var/turf/T in circular_range(get_turf(src),user_input))
animate_flash_color_fill(T,"#FF0000",1,5)
+1993
View File
File diff suppressed because it is too large Load Diff
+303
View File
@@ -0,0 +1,303 @@
/obj/poolwater
name = "water"
density = 0
anchored = 1
icon = 'icons/obj/stationobjs.dmi'
icon_state = "poolwater"
layer = EFFECTS_LAYER_UNDER_3
mouse_opacity = 0
New()
var/datum/reagents/R = new/datum/reagents(10)
reagents = R
R.my_atom = src
R.add_reagent("cleaner",5)
R.add_reagent("water",5)
HasEntered(atom/A)
reagents.reaction(A, TOUCH, 2)
return
/obj/tree1
name = "Tree"
desc = "It's a tree."
icon = 'icons/effects/96x96.dmi' // changed from worlds.dmi
icon_state = "tree" // changed from 0.0
anchored = 1
layer = EFFECTS_LAYER_UNDER_3
pixel_x = -20
density = 1
opacity = 0 // this causes some of the super ugly lighting issues too
// what the hell is all this and why wasn't it just using a big icon? the lighting system gets all fucked up with this stuff
/*
New()
var/image/tile10 = image('icons/misc/worlds.dmi',null,"1,0",10)
tile10.pixel_x = 32
var/image/tile01 = image('icons/misc/worlds.dmi',null,"0,1",10)
tile01.pixel_y = 32
var/image/tile11 = image('icons/misc/worlds.dmi',null,"1,1",10)
tile11.pixel_y = 32
tile11.pixel_x = 32
overlays += tile10
overlays += tile01
overlays += tile11
var/image/tile20 = image('icons/misc/worlds.dmi',null,"2,0",10)
tile20.pixel_x = 64
var/image/tile02 = image('icons/misc/worlds.dmi',null,"0,2",10)
tile02.pixel_y = 64
var/image/tile22 = image('icons/misc/worlds.dmi',null,"2,2",10)
tile22.pixel_y = 64
tile22.pixel_x = 64
var/image/tile21 = image('icons/misc/worlds.dmi',null,"2,1",10)
tile21.pixel_y = 32
tile21.pixel_x = 64
var/image/tile12 = image('icons/misc/worlds.dmi',null,"1,2",10)
tile12.pixel_y = 64
tile12.pixel_x = 32
overlays += tile20
overlays += tile02
overlays += tile22
overlays += tile21
overlays += tile12 */
/obj/river
name = "River"
desc = "Its a river."
icon = 'icons/misc/worlds.dmi'
icon_state = "river"
anchored = 1
/obj/stone
name = "Stone"
desc = "Its a stone."
icon = 'icons/misc/worlds.dmi'
icon_state = "stone"
anchored = 1
density=1
/obj/shrub
name = "shrub"
icon = 'icons/misc/worlds.dmi'
icon_state = "shrub"
anchored = 1
density = 0
layer = EFFECTS_LAYER_UNDER_1
var/destroyed = 0
/obj/shrub/captainshrub
name = "\improper Captain's bonsai tree"
icon = 'icons/misc/worlds.dmi'
icon_state = "shrub"
desc = "The Captain's most prized possession. Don't touch it. Don't even look at it."
anchored = 1
density = 1
layer = EFFECTS_LAYER_UNDER_1
dir = EAST
// Added ex_act and meteorhit handling here (Convair880).
proc/update_icon()
if (!src) return
src.dir = NORTHEAST
src.destroyed = 1
src.density = 0
src.desc = "The scattered remains of a once-beautiful bonsai tree."
playsound(src, "sound/effects/attackblob.ogg", 100, 0)
return
attackby(obj/item/W as obj, mob/user as mob)
if (!W) return
if (!user) return
if (src.destroyed) return
if ((user.mind && user.mind.assigned_role == "Captain") && istype(W, /obj/item/wirecutters))
boutput(user, "<span style=\"color:blue\">You carefully and lovingly sculpt your bonsai tree.</span>")
if ((user.mind && user.mind.assigned_role == "Captain") && (!(istype(W, /obj/item/wirecutters))))
boutput(user, "<span style=\"color:red\">Why would you ever destroy your precious bonsai tree?</span>")
else if(istype(W, /obj/item/) && (user.mind && user.mind.assigned_role != "Captain"))
src.update_icon()
boutput(user, "<span style=\"color:red\">I don't think the Captain is going to be too happy about this...</span>")
src.visible_message(text("<b><span style=\"color:red\">[] ravages the [] with the [].</span></b>", user, src, W), 1)
return
meteorhit(obj/O as obj)
src.visible_message("<b><span style=\"color:red\">The meteor smashes right through [src]!</span></b>")
src.update_icon()
return
ex_act(severity)
src.visible_message("<b><span style=\"color:red\">[src] is ripped to pieces by the blast!</span></b>")
src.update_icon()
return
/obj/grassplug
name = "grass"
icon = 'icons/misc/worlds.dmi'
icon_state = "grassplug"
anchored = 1
/obj/window_blinds
name = "blinds"
icon = 'icons/obj/decoration.dmi'
icon_state = "blindsH-o"
anchored = 1
density = 0
opacity = 0
layer = 30.1 // just above windows
var/base_state = "blindsH"
var/open = 1
var/id = null
var/obj/blind_switch/mySwitch = null
attack_hand(mob/user as mob)
src.toggle()
src.toggle_group()
attackby(obj/item/W, mob/user)
src.toggle()
src.toggle_group()
proc/toggle(var/force_state as null|num)
if (!isnull(force_state))
src.open = force_state
else
src.open = !(src.open)
src.update_icon()
proc/toggle_group()
if (istype(src.mySwitch))
src.mySwitch.toggle()
proc/update_icon()
if (src.open)
src.icon_state = "[src.base_state]-c"
src.opacity = 1
else
src.icon_state = "[src.base_state]-o"
src.opacity = 0
left
icon_state = "blindsH-L-o"
base_state = "blindsH-L"
middle
icon_state = "blindsH-M-o"
base_state = "blindsH-M"
right
icon_state = "blindsH-R-o"
base_state = "blindsH-R"
vertical
icon_state = "blindsV-o"
base_state = "blindsV"
left
icon_state = "blindsV-L-o"
base_state = "blindsV-L"
middle
icon_state = "blindsV-M-o"
base_state = "blindsV-M"
right
icon_state = "blindsV-R-o"
base_state = "blindsV-R"
cog2
icon_state = "blinds_cog2-o"
base_state = "blinds_cog2"
left
icon_state = "blinds_cog2-L-o"
base_state = "blinds_cog2-L"
middle
icon_state = "blinds_cog2-M-o"
base_state = "blinds_cog2-M"
right
icon_state = "blinds_cog2-R-o"
base_state = "blinds_cog2-R"
/obj/blind_switch
name = "blind switch"
desc = "A switch for opening the blinds."
icon = 'icons/obj/power.dmi'
icon_state = "light1"
anchored = 1
density = 0
var/on = 0
var/id = null
var/list/myBlinds = list()
New()
..()
if (!src.name || src.name in list("N blind switch", "E blind switch", "S blind switch", "W blind switch"))//== "N light switch" || name == "E light switch" || name == "S light switch" || name == "W light switch")
src.name = "blind switch"
spawn(5)
src.locate_blinds()
proc/locate_blinds()
for (var/obj/window_blinds/blind in world)
if (blind.id == src.id)
if (!(blind in src.myBlinds))
src.myBlinds += blind
blind.mySwitch = src
proc/toggle()
src.on = !(src.on)
src.icon_state = "light[!(src.on)]"
if (!islist(myBlinds) || !myBlinds.len)
return
for (var/obj/window_blinds/blind in myBlinds)
blind.toggle(src.on)
attack_hand(mob/user as mob)
src.toggle()
attackby(obj/item/W, mob/user)
src.toggle()
/obj/blind_switch/north
name = "N blind switch"
pixel_y = 24
/obj/blind_switch/east
name = "E blind switch"
pixel_x = 24
/obj/blind_switch/south
name = "S blind switch"
pixel_y = -24
/obj/blind_switch/west
name = "W blind switch"
pixel_x = -24
/obj/blind_switch/area
locate_blinds()
var/area/A = get_area(src)
for (var/obj/window_blinds/blind in A)
if (!(blind in src.myBlinds))
src.myBlinds += blind
blind.mySwitch = src
/obj/blind_switch/area/north
name = "N blind switch"
pixel_y = 24
/obj/blind_switch/area/east
name = "E blind switch"
pixel_x = 24
/obj/blind_switch/area/south
name = "S blind switch"
pixel_y = -24
/obj/blind_switch/area/west
name = "W blind switch"
pixel_x = -24
+326
View File
@@ -0,0 +1,326 @@
/obj/displaycase
name = "Display Case"
icon = 'icons/obj/stationobjs.dmi'
icon_state = "glassbox1"
desc = "A display case for antique possessions."
density = 1
anchored = 1
var/health = 30
var/occupied = 1
var/destroyed = 0
/obj/displaycase/ex_act(severity)
switch(severity)
if (1)
new /obj/item/raw_material/shard/glass( src.loc )
if (occupied)
new /obj/item/captaingun( src.loc )
occupied = 0
qdel(src)
if (2)
if (prob(50))
src.health -= 15
src.healthcheck()
if (3)
if (prob(50))
src.health -= 5
src.healthcheck()
/obj/displaycase/bullet_act(var/obj/projectile/P)
var/damage = 0
damage = round((P.power*P.proj_data.ks_ratio), 1.0)
if (damage < 1)
return
if(src.material) src.material.triggerOnAttacked(src, P.shooter, src, (ismob(P.shooter) ? P.shooter:equipped() : P.shooter) )
for(var/atom/A in src)
if(A.material)
A.material.triggerOnAttacked(A, P.shooter, src, (ismob(P.shooter) ? P.shooter:equipped() : P.shooter))
switch(P.proj_data.damage_type)
if(D_KINETIC)
src.health -= (damage*2)
if(D_PIERCING)
src.health -= (damage/2)
if(D_ENERGY)
src.health -= (damage/4)
src.healthcheck()
return
/obj/displaycase/blob_act(var/power)
if (prob(50))
new /obj/item/raw_material/shard/glass( src.loc )
if (occupied)
new /obj/item/captaingun( src.loc )
occupied = 0
qdel(src)
/obj/displaycase/meteorhit(obj/O as obj)
new /obj/item/raw_material/shard/glass( src.loc )
new /obj/item/captaingun( src.loc )
qdel(src)
/obj/displaycase/proc/healthcheck()
if (src.health <= 0)
if (!( src.destroyed ))
src.density = 0
src.destroyed = 1
new /obj/item/raw_material/shard/glass( src.loc )
playsound(src, "shatter", 70, 1)
update_icon()
else
playsound(src.loc, "sound/effects/Glasshit.ogg", 75, 1)
return
/obj/displaycase/proc/update_icon()
if(src.destroyed)
src.icon_state = "glassboxb[src.occupied]"
else
src.icon_state = "glassbox[src.occupied]"
return
/obj/displaycase/attackby(obj/item/W as obj, mob/user as mob)
src.health -= W.force
src.healthcheck()
..()
return
/obj/displaycase/attack_hand(mob/user as mob)
if (src.destroyed && src.occupied)
new /obj/item/captaingun( src.loc )
boutput(user, "<b>You deactivate the hover field built into the case.</b>")
src.occupied = 0
src.add_fingerprint(user)
update_icon()
return
else
user.visible_message("<span style=\"color:red\">[user] kicks the display case.</span>")
src.health -= 2
healthcheck()
return
// Added a little mini-quest here. Gun can be repaired, and the player will be rewarded for using
// high-quality materials, which will make the weapon more powerful (Convair880).
/obj/item/captaingun
name = "antique laser gun"
icon = 'icons/obj/gun.dmi'
icon_state = "caplaser"
inhand_image_icon = 'icons/mob/inhand/hand_weapons.dmi'
item_state = "gun"
force = 1.0
flags = FPRINT | TABLEPASS | CONDUCT | ONBELT
var/stability = 10
var/repair_stage = 0
var/quality_counter = 0 // Simply the sum of all material.quality values of every component.
var/q_threshold1 = 100 // Decent quality.
var/q_threshold2 = 200 // Superb quality.
var/datum/projectile/our_projectile = null
var/datum/projectile/our_projectile2 = null // Reserved for top-notch replacement parts.
var/list/our_projectiles = null
var/obj/item/ammo/power_cell/our_cell = null
New()
src.stability = rand(6,20)
..()
return
examine()
set src in usr
if (usr.mind && usr.mind.assigned_role == "Captain")
boutput(usr, "It's your laser gun! It's really just for show and made of plastic but man it looks cool. Everybody thinks you're awesome, and you know it.")
else
boutput(usr, "On closer inspection, it looks like it's just a display model...? What a cheapskate. Fuck our captain.")
if (src.repair_stage > 0)
switch (src.repair_stage)
if (1)
boutput(usr, "<br><span style=\"color:blue\">The maintenance panel is open, revealing a largely empty circuit board.</span>")
if (2)
boutput(usr, "<br><span style=\"color:blue\">The wiring has been replaced, but there's still an empty spot in the circuit board.</span>")
if (3)
boutput(usr, "<br><span style=\"color:blue\">A new coil has been inserted, but not secured yet.</span>")
if (4)
boutput(usr, "<br><span style=\"color:blue\">The coil has been soldered into place, but there's nothing to focus the laser beam.</span>")
if (5)
boutput(usr, "<br><span style=\"color:blue\">A lens has been installed, but the control circuits aren't set up yet.</span>")
if (6)
boutput(usr, "<br><span style=\"color:blue\">The gun appears to be missing a power cell.</span>")
if (7)
boutput(usr, "<br><span style=\"color:blue\">Power cell installed. The maintenance panel is open.</span>")
return
attack()
..()
src.stability--
src.healthcheck(usr)
return
proc/healthcheck(mob/user as mob)
if (!src) return
if (src.stability <= 0)
if (user && ismob(user))
boutput(user, "<span style=\"color:red\">The laser gun snaps in half!</span>")
user.u_equip(src)
qdel(src)
return
/*
0 Screwdriver
1 Cable coil
2 Small coil
3 Soldering iron
4 Lens
5 Multitool
6 Power cell
7 Screwdriver
*/
attackby(obj/item/O as obj, mob/user as mob)
if (istype(O, /obj/item/screwdriver))
if (src.repair_stage == 0)
user.show_text("You open the maintenance panel.", "blue")
src.repair_stage = 1
else if (src.repair_stage == 7)
user.visible_message("<span style=\"color:blue\">[user] finishes repairing the [src.name].</span>", "<span style=\"color:blue\">You close the maintenance panel and power up the gun.</span>")
src.generate_properties(user) // Type of projectile(s) based on material quality.
var/obj/item/gun/energy/laser_gun/antique/L = new /obj/item/gun/energy/laser_gun/antique(get_turf(user))
L.current_projectile = new src.our_projectile
if (!isnull(src.our_projectile2))
src.our_projectiles = list(new src.our_projectile, new src.our_projectile2)
L.projectiles = src.our_projectiles
src.our_cell.set_loc(L)
L.cell = src.our_cell
// The man with the golden gun.
if (src.quality_counter >= src.q_threshold2)
L.material = getCachedMaterial("gold")
if (L.material)
L.material.owner = L
L.material.triggerOnAdd(L)
L.name = "show-piece antique laser gun"
user.unlock_medal("Tinkerer", 1)
user.u_equip(src)
user.put_in_hand_or_drop(L)
qdel(src)
return
else if (istype(O, /obj/item/cable_coil))
if (src.repair_stage == 1)
var/obj/item/cable_coil/C = O
if (C.amount >= 10)
user.show_text("You begin to rewire the gun's circuit board...", "blue")
if (do_after(user, 35))
user.show_text("You rewire the circuit board.", "blue")
src.repair_stage = 2
if (C.material)
src.quality_counter += C.material.quality
else
user.show_text("You were interrupted!", "red")
return
else
user.show_text("You need more wire than that.", "red")
return
else if (istype(O, /obj/item/coil/small))
if (src.repair_stage == 2)
user.show_text("You begin to install the coil...", "blue")
if (do_after(user, 35))
user.show_text("You install the coil.", "blue")
src.repair_stage = 3
if (O.material)
src.quality_counter += O.material.quality
user.u_equip(O)
qdel(O)
else
user.show_text("You were interrupted!", "red")
return
else if (istype(O, /obj/item/electronics/soldering))
if (src.repair_stage == 3)
user.show_text("You begin to solder the coil into place...", "blue")
if (do_after(user, 35))
user.show_text("You solder the coil into place.", "blue")
src.repair_stage = 4
else
user.show_text("You were interrupted!", "red")
return
else if (istype(O, /obj/item/lens))
if (src.repair_stage == 4)
user.show_text("You begin to install the lens...", "blue")
if (do_after(user, 35))
user.show_text("You install the lens.", "blue")
src.repair_stage = 5
if (O.material)
src.quality_counter += O.material.quality
user.u_equip(O)
qdel(O)
else
user.show_text("You were interrupted!", "red")
return
else if (istype(O, /obj/item/device/multitool))
if (src.repair_stage == 5)
user.show_text("You initialize the control board.", "blue")
src.repair_stage = 6
else if (istype(O, /obj/item/ammo/power_cell))
if (src.repair_stage == 6)
var/obj/item/ammo/power_cell/P = O
user.show_text("You begin to install the power cell...", "blue")
if (do_after(user, 35))
user.show_text("You install the power cell.", "blue")
src.repair_stage = 7
user.u_equip(P)
P.set_loc(src)
src.our_cell = P
if (P.material)
src.quality_counter += P.material.quality
else
user.show_text("You were interrupted!", "red")
return
else
..()
return
// Basically determines how powerful the gun will be, based on the quality of the materials used.
// Code for the energy gun itself can be found in energy.dm.
//
// Why isn't there a crappy version (less than 0 quality) here? I don't want to punish the player
// for investing a bit of time of effort. After all, scanning and mass-producing energy guns is
// much less of a hassle.
proc/generate_properties(var/mob/user)
if (!src) return
// Nothing special, just a plain old laser.
if (src.quality_counter < src.q_threshold1)
src.our_projectile = /datum/projectile/laser
if (user && ismob(user))
user.show_text("The [src.name] looks a little worn, but appears to work alright.", "blue")
// Player put some effort into it, so let's give him something a little more powerful.
else if (src.quality_counter >= src.q_threshold1 && src.quality_counter < src.q_threshold2)
if (user && ismob(user))
user.show_text("The [src.name] seems to work better than expected thanks to above-average replacment parts.", "blue")
src.our_projectile = /datum/projectile/laser/old
// Now we're talking about top-notch stuff.
else if (src.quality_counter >= src.q_threshold2)
if (user && ismob(user))
user.show_text("The [src.name]'s high-quality replacement parts fit together perfectly, increasing the gun's output.", "blue")
src.our_projectile = /datum/projectile/laser/old
src.our_projectile2 = /datum/projectile/laser/old_burst
//DEBUG("[src.name]'s quality_counter: [quality_counter]")
return
+19
View File
@@ -0,0 +1,19 @@
/* This is an attempt to make some easily reusable "particle" type effects, to stop the code
constantly having to be rewritten. An item like the jetpack that uses the ion_trail_follow system, just has one
defined, then set up when it is created with New(). Then this same system can just be reused each time
it needs to create more trails.A beaker could have a steam_trail_follow system set up, then the steam
would spawn and follow the beaker, even if it is carried or thrown.
*/
#define TOUCH 1
#define INGEST 2
/obj/effects
name = "effects"
icon = 'icons/effects/effects.dmi'
mouse_opacity = 0
flags = TABLEPASS
desc = null
pooled()
..()
color = initial(color)
+40
View File
@@ -0,0 +1,40 @@
/////////////////////////////////////////////
// Bad smoke
/////////////////////////////////////////////
/obj/effects/bad_smoke
name = "smoke"
icon_state = "smoke"
opacity = 1
anchored = 0.0
mouse_opacity = 0
var/amount = 6.0
//Remove this bit to use the old smoke
icon = 'icons/effects/96x96.dmi'
pixel_x = -32
pixel_y = -32
/obj/effects/bad_smoke/Move()
..()
for(var/mob/living/carbon/M in get_turf(src))
if (M.internal != null && M.wear_mask && (M.wear_mask.c_flags & MASKINTERNALS))
else
M.drop_item()
if (prob(25))
M.stunned += 1
M.take_oxygen_deprivation(1)
M.emote("cough")
return
/obj/effects/bad_smoke/HasEntered(mob/living/carbon/M as mob )
..()
if(iscarbon(M))
if (M.internal != null && M.wear_mask && (M.wear_mask.c_flags & MASKINTERNALS))
return
else
M.drop_item()
if (prob(25))
M.stunned += 1
M.take_oxygen_deprivation(1)
M.emote("cough")
return
+54
View File
@@ -0,0 +1,54 @@
// fart cloud for toxic farts
/obj/effects/fart_cloud
name = "fart cloud"
icon_state = "mustard"
opacity = 1
anchored = 0
mouse_opacity = 0
var/amount = 6
var/mob/living/fartowner = null
proc/Life()
amount--
for(var/mob/living/carbon/human/H in range(get_turf(src),1))
if (H == src.fartowner)
continue
if (prob(20))
boutput(H, "<span style=\"color:red\">Oh god! The <i>smell</i>!!!</span>")
H.reagents.add_reagent("jenkem",0.1)
sleep(15)
if(amount < 1)
dispose()
return
else
src.Life()
/obj/effects/fart_cloud/New(loc,var/mob/living/owner)
..()
if (owner)
fartowner = owner
amount = rand(3,8)
spawn(0)
src.Life()
return
/obj/effects/fart_cloud/Move()
..()
for(var/mob/living/carbon/human/R in get_turf(src))
if (R.internal != null && usr.wear_mask && (R.wear_mask.c_flags & MASKINTERNALS))
continue
if (R == src.fartowner)
continue
R.reagents.add_reagent("jenkem",1)
return
/obj/effects/fart_cloud/HasEntered(mob/living/carbon/human/R as mob )
..()
if (istype(R, /mob/living/carbon/human))
if (R.internal != null && usr.wear_mask && (R.wear_mask.c_flags & MASKINTERNALS))
return
if (R == src.fartowner)
return
R.reagents.add_reagent("jenkem",1)
return
+169
View File
@@ -0,0 +1,169 @@
// Foam
// Similar to smoke, but spreads out more
// metal foams leave behind a foamed metal wall
/obj/effects/foam
name = "foam"
icon_state = "foam"
opacity = 0
anchored = 1
density = 0
layer = OBJ_LAYER + 0.9
mouse_opacity = 0
var/foamcolor
var/amount = 3
var/expand = 1
animate_movement = 0
var/metal = 0
/*
/obj/effects/foam/New(loc, var/ismetal=0)
..(loc)
*/
/obj/effects/foam/pooled()
..()
name = "foam"
icon_state = "foam"
opacity = 0
foamcolor = null
expand = 0
amount = 0
metal = 0
animate_movement = 0
if(reagents)
reagents.clear_reagents()
/obj/effects/foam/unpooled()
..()
amount = 3
expand = 1
/obj/effects/foam/proc/set_up(loc, var/ismetal)
src.set_loc(loc)
expand = 1
if(ismetal == 1)
icon_state = "mfoam"
else
icon_state = "foam"
if(reagents)
src.overlays.len = 0
icon_state = "foam"
src.foamcolor = src.reagents.get_master_color()
var/icon/I = new /icon('icons/effects/effects.dmi',"foam_overlay")
I.Blend(src.foamcolor, ICON_ADD)
src.overlays += I
metal = ismetal
playsound(src, "sound/effects/bubbles2.ogg", 80, 1, -3)
spawn(3 + metal*3)
process()
spawn(120)
expand = 0 // stop expanding
sleep(30)
if(metal)
var/obj/foamedmetal/M = new(src.loc)
M.metal = metal
M.updateicon()
if(metal)
flick("mfoam-disolve", src)
else
flick("foam-disolve", src)
sleep(5)
die()
return
// on delete, transfer any reagents to the floor & surrounding tiles
/obj/effects/foam/proc/die()
expand = 0
if(!metal && reagents)
reagents.handle_reactions()
for(var/atom/A in oview(1,src))
if(A == src)
continue
if(istype(A,/mob/living))
var/mob/living/L = A
logTheThing("combat", L, null, "is hit by chemical foam [log_reagents(src)] at [log_loc(src)].")
reagents.reaction(A, TOUCH, 5)
pool(src)
/obj/effects/foam/proc/process()
if(--amount < 0)
return
while(expand) // keep trying to expand while true
for(var/direction in cardinal)
var/turf/T = get_step(src,direction)
if(!T)
continue
if(!T.Enter(src))
continue
//if(istype(T, /turf/space))
// continue
var/obj/effects/foam/F = locate() in T
if(F)
continue
F = unpool(/obj/effects/foam)
F.set_up(T, metal)
F.amount = amount
if(!metal)
F.overlays.len = 0
F.create_reagents(15)
//This very slight tweak is to make it so some reactions that require different ratios
//can still work in foam.
for(var/reagent_id in src.reagents.reagent_list)
var/datum/reagent/current_reagent = src.reagents.reagent_list[reagent_id]
if(current_reagent)
F.reagents.add_reagent(reagent_id,min(current_reagent.volume, 3), current_reagent.data, src.reagents.total_temperature)
F.icon_state = "foam"
F.foamcolor = src.reagents.get_master_color()
var/icon/I = new /icon('icons/effects/effects.dmi',"foam_overlay")
I.Blend(F.foamcolor, ICON_ADD)
F.overlays += I
sleep(15)
// foam disolves when heated
// except metal foams
/obj/effects/foam/temperature_expose(datum/gas_mixture/air, exposed_temperature, exposed_volume)
if(!metal && prob(max(0, exposed_temperature - 475)))
flick("foam-disolve", src)
spawn(5)
die()
expand = 0
/obj/effects/foam/HasEntered(var/atom/movable/AM)
if (metal)
return
if (ishuman(AM))
var/mob/living/carbon/human/M = AM
if (!M.can_slip())
return
for(var/reagent_id in src.reagents.reagent_list)
var/amount = M.reagents.get_reagent_amount(reagent_id)
if(amount < 25)
M.reagents.add_reagent(reagent_id, min(round(amount / 2),15))
logTheThing("combat", M, null, "is hit by chemical foam [log_reagents(src)] at [log_loc(src)].")
reagents.reaction(M, TOUCH, 5)
if(!istype(src.loc, /turf/space))
M.pulling = null
M.show_text("You slip on the foam!", "red")
playsound(src.loc, "sound/misc/slip.ogg", 50, 1, -3)
M.stunned = 2
M.weakened = 2
+36
View File
@@ -0,0 +1,36 @@
/obj/effects/harmless_smoke
name = "smoke"
icon_state = "smoke"
opacity = 1
anchored = 0.0
mouse_opacity = 0
var/amount = 6.0
//Remove this bit to use the old smoke
icon = 'icons/effects/96x96.dmi'
pixel_x = -32
pixel_y = -32
pooled()
..()
/*
/obj/effects/harmless_smoke/New()
..()
spawn (100)
pool(src)
return
*/
/obj/effects/harmless_smoke/proc/kill(var/time)
spawn(time)
pool(src)
/obj/effects/harmless_smoke/Move()
..()
return
proc/harmless_smoke_puff(var/turf/location, var/duration = 100)
if(!istype(location)) return
var/obj/effects/harmless_smoke/smoke = unpool(/obj/effects/harmless_smoke)
smoke.set_loc(location)
smoke.kill(100)
+17
View File
@@ -0,0 +1,17 @@
/////////////////////////////////////////////
//////// Attach an Ion trail to any object, that spawns when it moves (like for the jetpack)
/// just pass in the object to attach it to in set_up
/// Then do start() to start it and stop() to stop it, obviously
/// and don't call start() in a loop that will be repeated otherwise it'll get spammed!
/////////////////////////////////////////////
/obj/effects/ion_trails
name = "ion trails"
icon_state = "ion_trails"
anchored = 1.0
/obj/effects/ion_trails/pooled(var/poolname)
icon_state = "blank"
pixel_x = 0
pixel_y = 0
..()
+44
View File
@@ -0,0 +1,44 @@
/////////////////////////////////////////////
// Mustard Gas
/////////////////////////////////////////////
/obj/effects/mustard_gas
name = "mustard gas"
icon_state = "mustard"
opacity = 1
anchored = 0.0
mouse_opacity = 0
var/amount = 6.0
/obj/effects/mustard_gas/New()
..()
spawn (100)
dispose()
return
/obj/effects/mustard_gas/Move()
..()
for(var/mob/living/carbon/human/R in get_turf(src))
if (R.internal != null && R.wear_mask && (R.wear_mask.c_flags & MASKINTERNALS))
else
R.TakeDamage("chest", 0, 10)
R.losebreath = max(5, R.losebreath)
R.emote("scream")
if (prob(25))
R.stunned += 1
R.updatehealth()
return
/obj/effects/mustard_gas/HasEntered(mob/living/carbon/human/R as mob )
..()
if (istype(R, /mob/living/carbon/human))
if (R.internal != null && R.wear_mask && (R.wear_mask.c_flags & MASKINTERNALS))
return
R.losebreath = max(5, R.losebreath)
R.TakeDamage("chest", 0, 10)
R.emote("scream")
if (prob(25))
R.stunned += 1
R.updatehealth()
return
+8
View File
@@ -0,0 +1,8 @@
/obj/effects/smoke
name = "smoke"
icon = 'icons/effects/water.dmi'
icon_state = "smoke"
opacity = 1
anchored = 0.0
mouse_opacity = 0
var/amount = 8.0
+35
View File
@@ -0,0 +1,35 @@
/////////////////////////////////////////////
//SPARK SYSTEM (like steam system)
// The attach(atom/atom) proc is optional, and can be called to attach the effect
// to something, like the RCD, so then you can just call start() and the sparks
// will always spawn at the items location.
/////////////////////////////////////////////
/obj/effects/sparks
name = "sparks"
icon_state = "sparks"
var/amount = 6.0
anchored = 1.0
mouse_opacity = 0
/obj/effects/sparks/unpooled(var/poolname)
..(poolname)
spawn(5)
playsound(src.loc, "sparks", 100, 1)
var/turf/T = src.loc
if (istype(T, /turf))
T.hotspot_expose(1000,100)
return
/obj/effects/sparks/disposing()
var/turf/T = get_turf(src)
if (istype(T, /turf))
T.hotspot_expose(1000,100)
..()
/obj/effects/sparks/Move()
..()
var/turf/T = src.loc
if (istype(T, /turf))
T.hotspot_expose(1000,100)
return
+8
View File
@@ -0,0 +1,8 @@
/obj/effects/spray
name = "spray"
icon = 'icons/effects/effects.dmi'
icon_state = "extinguish"
flags = TABLEPASS
mouse_opacity = 0
anchored = 1
var/original_dir = NORTH
+5
View File
@@ -0,0 +1,5 @@
/obj/effects/steam
name = "steam"
icon = 'icons/effects/effects.dmi'
icon_state = "extinguish"
density = 0
+52
View File
@@ -0,0 +1,52 @@
/obj/effects/water
name = "water"
icon = 'icons/effects/effects.dmi'
icon_state = "extinguish"
var/life = 15.0
flags = TABLEPASS
mouse_opacity = 0
/obj/effects/water/pooled(var/poolname)
life = initial(life)
..()
/obj/effects/water/Move(turf/newloc)
//var/turf/T = src.loc
//if (istype(T, /turf))
// T.firelevel = 0 //TODO: FIX
if (--src.life < 1)
//SN src = null
if (!disposed)
pool(src)
return 0
if(newloc.density)
if (!disposed)
pool(src)
return 0
.=..()
/obj/effects/water/proc/spray_at(var/turf/target, var/datum/reagents/R)
if (!target || !R)
pool(src)
return
src.reagents = R
R.my_atom = src
src.reagents.trans_to(src,1)
var/turf/T
for(var/b=0, b<5, b++)
T = get_turf(src)
step_towards(src,target)
if(!src.reagents)
break
src.reagents.reaction(T)
for(var/atom/atm in T)
src.reagents.reaction(atm)
if(src.loc == target)
break
sleep(2)
if (disposed)
break
if (!disposed)
pool(src)
+239
View File
@@ -0,0 +1,239 @@
/turf/simulated/wall/false_wall
name = "wall"
icon = 'icons/obj/doors/Doorf.dmi'
icon_state = "door1"
blocks_air = 0
var/operating = null
var/visible = 1
var/floorname
var/floorintact
var/floorhealth
var/floorburnt
var/icon/flooricon
var/flooricon_state
var/const/delay = 15
var/const/prob_opens = 25
var/list/known_by = list()
var/can_be_auto = 1
var/mod = null
temp
var/was_rwall = 0
reinforced
icon_state = "rdoor1"
mod = "R"
hive
name = "strange hive wall"
desc = "Looking more closely, these are actually really squat octagons, not hexagons! What!!"
icon = 'icons/turf/walls.dmi'
icon_state = "hive"
can_be_auto = 0
New()
..()
//Hide the wires or whatever THE FUCK
src.levelupdate()
src.blocks_air = 1
src.find_icon_state()
spawn(10)
// so that if it's getting created by the map it works, and if it isn't this will just return
src.setFloorUnderlay('icons/turf/floors.dmi', "plating", 0, 100, 0, "plating")
proc/setFloorUnderlay(FloorIcon, FloorIcon_State, Floor_Intact, Floor_Health, Floor_Burnt, Floor_Name)
if(src.underlays.len)
//only one underlay
return 0
if(!(FloorIcon || FloorIcon_State))
return 0
if(!Floor_Health)
Floor_Health = 150
if(!Floor_Burnt)
Floor_Burnt = 0
if(!Floor_Intact)
Floor_Intact = 1
if(!Floor_Name)
Floor_Name = "floor"
underlays += image(FloorIcon, FloorIcon_State)
src.flooricon = FloorIcon
src.flooricon_state = FloorIcon_State
src.floorintact = Floor_Intact
src.floorhealth = Floor_Health
src.floorburnt = Floor_Burnt
src.floorname = Floor_Name
return 1
attack_hand(mob/user as mob)
src.add_fingerprint(user)
var/known = (user in known_by)
if (src.density)
//door is closed
if (known)
if (open())
boutput(user, "<span style=\"color:blue\">The wall slides open.</span>")
else if (prob(prob_opens))
//it's hard to open
if (open())
boutput(user, "<span style=\"color:blue\">The wall slides open!</span>")
known_by += user
else
return ..()
else
if (close())
boutput(user, "<span style=\"color:blue\">The wall slides shut.</span>")
return
attackby(obj/item/screwdriver/S as obj, mob/user as mob)
src.add_fingerprint(user)
var/known = (user in known_by)
if (istype(S, /obj/item/screwdriver))
//try to disassemble the false wall
if (!src.density || prob(prob_opens))
//without this, you can detect a false wall just by going down the line with screwdrivers
//if it's already open, you can disassemble it no problem
if (src.density && !known) //if it was closed, let them know that they did something
boutput(user, "<span style=\"color:blue\">It was a false wall!</span>")
//disassemble it
boutput(user, "<span style=\"color:blue\">Now dismantling false wall.</span>")
var/floorname1 = src.floorname
var/floorintact1 = src.floorintact
var/floorburnt1 = src.floorburnt
var/icon/flooricon1 = src.flooricon
var/flooricon_state1 = src.flooricon_state
src.density = 0
src.RL_SetOpacity(0)
src.update_nearby_tiles()
var/turf/simulated/floor/F = src.ReplaceWithFloor()
F.name = floorname1
F.icon = flooricon1
F.icon_state = flooricon_state1
F.intact = floorintact1
F.burnt = floorburnt1
//a false wall turns into a sheet of metal and displaced girders
var/atom/A = new /obj/item/sheet(F)
var/atom/B = new /obj/structure/girder/displaced(F)
if(src.material)
A.setMaterial(src.material)
B.setMaterial(src.material)
else
var/datum/material/M = getCachedMaterial("steel")
A.setMaterial(M)
B.setMaterial(M)
F.levelupdate()
logTheThing("station", user, null, "dismantles a False Wall in [user.loc.loc] ([showCoords(user.x, user.y, user.z)])")
return
else
return ..()
// grabsmash
else if (istype(S, /obj/item/grab/))
var/obj/item/grab/G = S
if (!grab_smash(G, user))
return ..(S, user)
else return
else
return src.attack_hand(user)
proc/open()
if (src.operating)
return 0
src.operating = 1
src.name = "false wall"
animate(src, time = delay, pixel_x = 25, easing = BACK_EASING)
spawn(delay)
//we want to return 1 without waiting for the animation to finish - the textual cue seems sloppy if it waits
//actually do the opening things
src.density = 0
src.blocks_air = 0
src.pathable = 1
src.update_air_properties()
src.RL_SetOpacity(0)
if(!floorintact)
src.intact = 0
src.levelupdate()
if(checkForMultipleDoors())
update_nearby_tiles()
src.operating = 0
return 1
proc/close()
if (src.operating)
return 0
src.operating = 1
src.name = "wall"
animate(src, time = delay, pixel_x = 0, easing = BACK_EASING)
src.density = 1
src.blocks_air = 1
src.pathable = 0
src.update_air_properties()
if (src.visible)
src.RL_SetOpacity(1)
src.intact = 1
update_nearby_tiles()
spawn(delay)
//we want to return 1 without waiting for the animation to finish - the textual cue seems sloppy if it waits
src.operating = 0
return 1
proc/find_icon_state()
if (!map_setting)
return
//var/wall_path = /turf/simulated/wall/auto
var/r_wall_path = /turf/simulated/wall/auto/reinforced
if (map_setting == "COG2")
icon = 'icons/turf/walls_supernorn.dmi'
//wall_path = /turf/simulated/wall/auto/supernorn
r_wall_path = /turf/simulated/wall/auto/reinforced/supernorn
else if (map_setting == "DESTINY")
icon = 'icons/turf/walls_destiny.dmi'
//wall_path = /turf/simulated/wall/auto/gannets
r_wall_path = /turf/simulated/wall/auto/reinforced/gannets
else
icon = 'icons/turf/walls_auto.dmi'
var/dirs = 0
for (var/dir in cardinal)
var/turf/T = get_step(src, dir)
if (istype(T, /turf/simulated/wall/auto))
// neither of us are reinforced
if (!istype(T, r_wall_path) && !istype(src, /turf/simulated/wall/false_wall/reinforced))
dirs |= dir
// both of us are reinforced
else if (istype(T, r_wall_path) && istype(src, /turf/simulated/wall/false_wall/reinforced))
dirs |= dir
src.icon_state = "[mod][num2text(dirs)]"
return src.icon_state
get_desc()
if (!src.density)
return "It's a false wall. It's open."
//Temp false walls turn back to regular walls when closed.
temp/New()
..()
spawn(11)
src.open()
temp/close()
if (src.operating)
return 0
src.operating = 1
src.name = "wall"
animate(src, time = delay, pixel_x = 0, easing = BACK_EASING)
src.icon_state = "door1"
src.density = 1
src.blocks_air = 1
src.pathable = 0
src.update_air_properties()
if (src.visible)
src.opacity = 0
src.RL_SetOpacity(1)
src.intact = 1
update_nearby_tiles()
if(src.was_rwall)
src.ReplaceWithRWall()
else
src.ReplaceWithWall()
return 1
+84
View File
@@ -0,0 +1,84 @@
// wall formed by metal foams
// dense and opaque, but easy to break
/obj/foamedmetal
icon = 'icons/effects/effects.dmi'
icon_state = "metalfoam"
density = 1
opacity = 0 // changed in New()
anchored = 1
name = "foamed metal"
desc = "A lightweight foamed metal wall."
flags = FPRINT | CONDUCT | USEDELAY
var/metal = 1 // 1=aluminium, 2=iron
New()
..()
if(istype(loc, /turf/space))
loc:ReplaceWithMetalFoam(metal)
update_nearby_tiles(1)
spawn(1)
RL_SetOpacity(1)
disposing()
RL_SetOpacity(0)
density = 0
update_nearby_tiles(1)
..()
proc/updateicon()
if(metal == 1)
icon_state = "metalfoam"
else
icon_state = "ironfoam"
ex_act(severity)
dispose()
blob_act(var/power)
dispose()
bullet_act()
if(metal==1 || prob(50))
dispose()
attack_hand(var/mob/user)
if (user.bioHolder.HasEffect("hulk") || (prob(75 - metal*25)))
user.visible_message("<span style=\"color:red\">[user] smashes through the foamed metal.</span>")
dispose()
else
boutput(user, "<span style=\"color:blue\">You hit the metal foam but bounce off it.</span>")
return
attackby(var/obj/item/I, var/mob/user)
if (istype(I, /obj/item/grab))
var/obj/item/grab/G = I
G.affecting.set_loc(src.loc)
src.visible_message("<span style=\"color:red\">[G.assailant] smashes [G.affecting] through the foamed metal wall.</span>")
I.dispose()
dispose()
return
if(prob(I.force*20 - metal*25))
user.visible_message( "<span style=\"color:red\">[user] smashes through the foamed metal.</span>", "<span style=\"color:blue\">You smash through the foamed metal with \the [I].</span>")
dispose()
else
boutput(user, "<span style=\"color:blue\">You hit the metal foam to no effect.</span>")
// only air group geometry can pass
CanPass(atom/movable/mover, turf/target, height=1.5, air_group = 0)
return air_group
proc/update_nearby_tiles(need_rebuild)
var/turf/simulated/source = loc
if (istype(source))
return source.update_nearby_tiles(need_rebuild)
return 1
+392
View File
@@ -0,0 +1,392 @@
/obj/grille
desc = "A sturdy metal mesh. Blocks large objects, but lets small items, gas, or energy beams through."
name = "grille"
icon = 'icons/obj/grille.dmi'
icon_state = "grille"
density = 1
var/health = 30
var/health_max = 30
var/ruined = 0
var/blunt_resist = 0
var/cut_resist = 0
var/corrode_resist = 0
var/temp_resist = 0
var/shock_when_entered = 1
anchored = 1
flags = FPRINT | CONDUCT | USEDELAY
pressure_resistance = 5*ONE_ATMOSPHERE
layer = GRILLE_LAYER
New()
..()
update_icon()
steel
New()
..()
var/datum/material/M = getCachedMaterial("steel")
src.setMaterial(M)
steel/broken
desc = "Looks like its been in this sorry state for quite some time."
icon_state = "grille-cut"
ruined = 1
New()
..()
damage_slashing(1000)
update_icon()
catwalk
name = "catwalk surface"
icon_state = "catwalk"
density = 0
desc = "This doesn't look very safe at all!"
layer = CATWALK_LAYER
shock_when_entered = 0
onMaterialChanged()
..()
if (istype(src.material))
health = material.hasProperty(PROP_TOUGHNESS) ? material.getProperty(PROP_TOUGHNESS) : health
health_max = material.hasProperty(PROP_TOUGHNESS) ? material.getProperty(PROP_TOUGHNESS) : health_max
cut_resist = material.hasProperty(PROP_SHEAR) ? material.getProperty(PROP_SHEAR) : cut_resist
blunt_resist = material.hasProperty(PROP_COMPRESSIVE) ? material.getProperty(PROP_COMPRESSIVE) : blunt_resist
corrode_resist = material.hasProperty(PROP_CORROSION) ? material.getProperty(PROP_CORROSION) : corrode_resist
temp_resist = material.hasProperty(PROP_MELTING) ? material.getProperty(PROP_MELTING) : temp_resist
if (blunt_resist != 0) blunt_resist /= 2
damage_blunt(var/amount)
if (!isnum(amount) || amount <= 0)
return
if (src.ruined)
if (amount >= health_max / 2)
qdel(src)
return
var/armor = 0
if (src.material)
armor = blunt_resist
if (src.material.quality >= 25)
armor += src.material.quality * 0.25
else if (src.quality < 10)
armor = 0
amount += rand(1,3)
amount -= armor
src.health = max(0,min(src.health - amount,src.health_max))
if (src.health == 0)
update_icon("cut")
src.density = 0
src.ruined = 1
else
update_icon()
damage_slashing(var/amount)
if (!isnum(amount) || amount <= 0)
return
if (src.ruined)
drop_rods(1)
qdel(src)
return
amount = get_damage_after_percentage_based_armor_reduction(cut_resist,amount)
src.health = max(0,min(src.health - amount,src.health_max))
if (src.health == 0)
drop_rods(1)
update_icon("cut")
src.density = 0
src.ruined = 1
else
update_icon()
damage_corrosive(var/amount)
if (!isnum(amount) || amount <= 0)
return
if (src.ruined)
qdel(src)
return
amount = get_damage_after_percentage_based_armor_reduction(corrode_resist,amount)
src.health = max(0,min(src.health - amount,src.health_max))
if (src.health == 0)
update_icon("corroded")
src.density = 0
src.ruined = 1
else
update_icon()
damage_heat(var/amount)
if (!isnum(amount) || amount <= 0)
return
if (src.ruined)
qdel(src)
return
if (src.material)
if (amount * 100000 <= temp_resist)
// Not applying enough heat to melt it
return
src.health = max(0,min(src.health - amount,src.health_max))
if (src.health == 0)
update_icon("melted")
src.density = 0
src.ruined = 1
else
update_icon()
meteorhit(var/obj/M)
if (istype(M, /obj/newmeteor/massive))
qdel(src)
return
src.damage_blunt(5)
return
blob_act(var/power)
src.damage_blunt(3 * power / 20)
ex_act(severity)
switch(severity)
if(1.0)
src.damage_blunt(40)
src.damage_heat(40)
if(2.0)
src.damage_blunt(15)
src.damage_heat(15)
if(3.0)
src.damage_blunt(7)
src.damage_heat(7)
return
reagent_act(var/reagent_id,var/volume)
if (..())
return
switch(reagent_id)
if("acid")
damage_corrosive(volume / 2)
if("pacid")
damage_corrosive(volume)
if("napalm")
damage_heat(volume)
if("infernite")
damage_heat(volume * 2)
if("foof")
damage_heat(volume * 3)
hitby(AM as mob|obj)
..()
src.visible_message("<span style=\"color:red\"><B>[src] was hit by [AM].</B></span>")
playsound(src.loc, 'sound/effects/grillehit.ogg', 100, 1)
if (ismob(AM))
damage_blunt(5)
else if (isobj(AM))
var/obj/O = AM
if (O.throwforce)
damage_blunt(max(1, round(O.throwforce / 3, 1))) // we don't want people screaming right through these and you can still get through them by kicking/cutting/etc
return
attack_hand(obj/M, mob/user)
if(!shock(usr, 70))
var/damage = 1
var/dam_type = "blunt"
var/text = "[usr.kickMessage] [src]"
if (usr.bioHolder && usr.bioHolder.HasEffect("hulk") && damage < 5)
damage = 10
text = "smashes [src] with incredible strength"
src.visible_message("<span style=\"color:red\"><b>[usr]</b> [text]!</span>")
playsound(src.loc, 'sound/effects/grillehit.ogg', 80, 1)
if (dam_type == "slashing")
damage_slashing(damage)
else
damage_blunt(damage)
attackby(obj/item/W, mob/user)
// Things that won't electrocute you
if (istype(W,/obj/item/device/multitool) || istype(W, /obj/item/device/t_scanner))
var/net = get_connection()
if(!net)
boutput(user, "<span style=\"color:blue\">No electrical current detected.</span>")
else
boutput(user, "<span style=\"color:red\">CAUTION: Dangerous electrical current detected.</span>")
return
else if(istype(W, /obj/item/sheet/))
var/obj/item/sheet/S = W
if (S.material && S.material.material_flags & MATERIAL_CRYSTAL)
var/obj/window/WI
var/win_thin = 0
var/win_dir = 2
var/turf/UT = get_turf(user)
var/turf/ST = get_turf(src)
if (UT && isturf(UT) && ST && isturf(ST))
// We're inside the grill.
if (UT == ST)
win_dir = usr.dir
win_thin = 1
// We're trying to install a window while standing on an adjacent tile, so make it face the mob.
else
win_dir = turn(usr.dir, 180)
if (win_dir in list(NORTH, EAST, SOUTH, WEST))
win_thin = 1
if (ST && isturf(ST))
if (S.reinforcement)
if (map_setting && map_setting == "COG2" && win_thin == 0)
WI = new /obj/window/auto/reinforced(ST)
else
WI = new /obj/window/reinforced(ST)
else
if (map_setting && map_setting == "COG2" && win_thin == 0)
WI = new /obj/window/auto(ST)
else
WI = new /obj/window(ST)
if (WI && istype(WI))
if (S.material)
WI.setMaterial(S.material)
WI.dir = win_dir
WI.ini_dir = win_dir
else
user.show_text("<b>Error:</b> Couldn't spawn window. Try again and please inform a coder if the problem persists.", "red")
return
S.amount--
if (S.amount < 1)
qdel(S)
return
else
..()
return
// electrocution check
var/OSHA_is_crying = 1
if ((src.material && src.material.getProperty(PROP_ELECTRICAL) < 40))// fucka you || istype(W,/obj/item/raw_material/shard))
OSHA_is_crying = 0
if (OSHA_is_crying && shock(user, 100))
return
// Things that will electrocute you
if (istype(W, /obj/item/wirecutters))
damage_slashing(src.health_max)
src.visible_message("<span style=\"color:red\"><b>[usr]</b> cuts apart the [src] with [W].</span>")
playsound(src.loc, 'sound/items/Wirecutter.ogg', 100, 1)
else if ((istype(W, /obj/item/screwdriver) && (istype(src.loc, /turf/simulated) || src.anchored)))
playsound(src.loc, 'sound/items/Screwdriver.ogg', 100, 1)
src.anchored = !( src.anchored )
src.visible_message("<span style=\"color:red\"><b>[usr]</b> [src.anchored ? "fastens" : "unfastens"] [src].</span>")
return
else
src.visible_message("<span style=\"color:red\"><b>[usr]</b> attacks [src] with [W].</span>")
playsound(src.loc, 'sound/effects/grillehit.ogg', 80, 1)
switch(W.damtype)
if("fire")
damage_heat(W.force)
if("brute")
damage_blunt(W.force * 0.5)
return
proc/update_icon(var/special_icon_state)
if (ruined)
return
if (istext(special_icon_state))
icon_state = initial(icon_state) + "-" + special_icon_state
else
var/diff = get_x_percentage_of_y(health,health_max)
switch(diff)
if(-INFINITY to 25)
icon_state = initial(icon_state) + "-3"
if(26 to 50)
icon_state = initial(icon_state) + "-2"
if(51 to 75)
icon_state = initial(icon_state) + "-1"
if(76 to INFINITY)
icon_state = initial(icon_state) + "-0"
proc/drop_rods(var/amount)
if (!isnum(amount))
return
var/obj/item/rods/R = new /obj/item/rods(get_turf(src))
R.amount = amount
if(src.material)
R.setMaterial(src.material)
else
var/datum/material/M = getCachedMaterial("steel")
R.setMaterial(M)
proc/get_connection()
//returns the netnum of a stub cable at this grille loc, or 0 if none
var/turf/T = src.loc
if(!istype(T, /turf/simulated/floor))
return
for(var/obj/cable/C in T)
if(C.d1 == 0)
return C.netnum
return 0
proc/shock(mob/user, prb, var/ignore_gloves = 0)
// shock user with probability prb (if all connections & power are working)
// returns 1 if shocked, 0 otherwise
if (!anchored)// || ruined) // allowing ruined grilles to still be connected so people have to move carefully through them
// unanchored/ruined grilles are never connected
return 0
if (!prob(prb))
return 0
var/net = get_connection()
// find the powernet of the connected cable
if (!net)
// cable is unpowered
return 0
return src.electrocute(user, prb, net, ignore_gloves)
CanPass(atom/movable/mover, turf/target, height=1.5, air_group = 0)
if (istype(mover, /obj/projectile))
if (density)
return prob(50)
return 1
return ..()
HasEntered(AM as mob|obj)
..()
if (src.shock_when_entered)
if (ismob(AM))
if (!isliving(AM) || isintangible(AM)) // I assume this was left out by accident (Convair880).
return
var/mob/M = AM
if (M.client && M.client.flying) // noclip
return
var/s_chance = 10
if (M.m_intent != "walk") // move carefully
s_chance += 50
if (shock(M, s_chance, rand(0,1))) // you get a 50/50 shot to accidentally touch the grille with something other than your hands
M.show_text("<b>You brush against [src] while moving past it and it shocks you!</b>", "red")
+127
View File
@@ -0,0 +1,127 @@
/obj/health_scanner
icon = 'icons/obj/device.dmi'
anchored = 1
var/reagent_upgrade = 0
var/reagent_scan = 0
var/id = 0.0 // who are we?
var/list/partners = list() // who do we know?
var/partner_range = 3 // how far away should we look?
var/find_in_range = 1
New()
..()
spawn(5)
src.find_partners(src.find_in_range)
attackby(obj/item/W as obj, mob/user as mob)
if (istype(W, /obj/item/device/multitool))
var/new_id = input(user, "Please enter new ID", src.name, src.id) as null|text
if (!new_id || new_id == src.id)
return
src.id = new_id
boutput(user, "You change [src]'s ID to [new_id].")
src.find_partners()
else if (istype(W, /obj/item/device/healthanalyzer_upgrade))
src.update_reagent_scan()
if (src.reagent_upgrade)
boutput(user, "<span style=\"color:red\">This system already has a reagent scan upgrade!</span>")
return
else
src.reagent_upgrade = 1
src.reagent_scan = 1
src.update_reagent_scan()
boutput(user, "<span style=\"color:blue\">Reagent scan upgrade installed.</span>")
playsound(src.loc ,"sound/items/Deconstruct.ogg", 80, 0)
qdel(W)
return
else
return ..()
proc/find_partners(var/in_range = 0)
return // dummy proc that the scanner and screen will define themselves
proc/accept_partner(var/obj/health_scanner/H)
if (!H)
return
if (locate(H) in src.partners)
return
src.partners += H
proc/update_reagent_scan()
if (!src.partners || !src.partners.len)
return
for (var/obj/health_scanner/myPartner in src.partners)
if (src.reagent_upgrade && !myPartner.reagent_upgrade)
myPartner.reagent_upgrade = 1
else if (myPartner.reagent_upgrade && !src.reagent_upgrade)
src.reagent_upgrade = 1
if (src.reagent_scan && !myPartner.reagent_scan)
myPartner.reagent_scan = 1
else if (myPartner.reagent_scan && !src.reagent_scan)
src.reagent_scan = 1
/obj/health_scanner/wall
name = "health status screen"
desc = "A screen that shows health information recieved from connected floor scanners."
icon_state = "wallscan1"
find_partners(var/in_range = 0)
src.partners = list()
if (in_range)
for (var/obj/health_scanner/floor/possible_partner in orange(src.partner_range, src))
if (locate(possible_partner) in src.partners)
continue
src.partners += possible_partner
possible_partner.accept_partner(src)
for (var/obj/health_scanner/floor/possible_partner in world)
if (locate(possible_partner) in src.partners)
continue
if (possible_partner.id == src.id)
src.partners += possible_partner
possible_partner.accept_partner(src)
proc/scan()
if (!src.partners || !src.partners.len)
return "<font color='red'>ERROR: NO CONNECTED SCANNERS</font>"
var/data = null
for (var/obj/health_scanner/floor/myPartner in src.partners)
for (var/mob/M in get_turf(myPartner))
data += "<br>[scan_health(M, src.reagent_scan)]"
return data
get_desc(dist)
if (dist > 2 && !issilicon(usr))
. += "<br>It's too far away to see what it says.[prob(10) ? " Who decided the text should be <i>that</i> small?!" : null]"
else
var/data = src.scan()
if (data)
. += "<br>It says:[data]"
else
. += "<br>It says:<br><font color='red'>ERROR: NO SUBJECT(S) DETECTED</font>"
attack_hand(mob/user as mob)
return src.examine()
attack_ai(mob/user as mob)
return src.examine()
/obj/health_scanner/floor
name = "health scanner"
desc = "An in-floor health scanner that sends its data to connected status screens."
icon_state = "floorscan1"
find_partners(var/in_range = 0)
src.partners = list()
if (in_range)
for (var/obj/health_scanner/wall/possible_partner in orange(src.partner_range, src))
if (locate(possible_partner) in src.partners)
continue
src.partners += possible_partner
possible_partner.accept_partner(src)
for (var/obj/health_scanner/wall/possible_partner in world)
if (locate(possible_partner) in src.partners)
continue
if (possible_partner.id == src.id)
src.partners += possible_partner
possible_partner.accept_partner(src)
+35
View File
@@ -0,0 +1,35 @@
/obj/hud
name = "hud"
anchored = 1
var/mob/mymob = null
var/list/adding = null
var/list/other = null
var/list/intents = null
var/list/mov_int = null
var/list/mon_blo = null
var/list/m_ints = null
var/list/darkMask = null
var/h_type = /obj/screen
obj/hud/New(var/type = 0)
src.instantiate(type)
..()
return
/obj/hud/var/show_otherinventory = 1
/obj/hud/var/obj/screen/action_intent
/obj/hud/var/obj/screen/move_intent
/obj/hud/proc/instantiate(var/type = 0)
mymob = src.loc
ASSERT(istype(mymob, /mob))
if(istype(mymob, /mob/living/silicon/hivebot))
src.hivebot_hud()
return
if (istype(mymob, /mob/living/object))
src.object_hud()
return
+199
View File
@@ -0,0 +1,199 @@
/obj/hud/proc/hivebot_hud()
var/mob/living/silicon/hivebot/myhive = mymob
src.adding = list( )
src.other = list( )
src.intents = list( )
src.mon_blo = list( )
src.m_ints = list( )
src.mov_int = list( )
src.darkMask = list( )
var/obj/screen/using
//Radio
using = new src.h_type( src )
using.name = "radio"
using.dir = SOUTHWEST
using.icon = 'icons/mob/screen1_robot.dmi'
using.icon_state = "radio"
using.screen_loc = ui_movi
using.layer = HUD_LAYER
src.adding += using
//Generic overlays
using = new src.h_type(src) //Right hud bar
using.dir = SOUTH
using.icon = 'icons/mob/screen1_robot.dmi'
using.screen_loc = "EAST+1,SOUTH to EAST+1,NORTH"
using.layer = HUD_LAYER_UNDER_1
src.adding += using
using = new src.h_type(src) //Lower hud bar
using.dir = EAST
using.icon = 'icons/mob/screen1_robot.dmi'
using.screen_loc = "WEST,SOUTH-1 to EAST,SOUTH-1"
using.layer = HUD_LAYER_UNDER_1
src.adding += using
using = new src.h_type(src) //Corner Button
using.dir = NORTHWEST
using.icon = 'icons/mob/screen1_robot.dmi'
using.screen_loc = "EAST+1,SOUTH-1"
using.layer = HUD_LAYER_UNDER_1
src.adding += using
//Module select
using = new src.h_type( src )
using.name = "module1"
using.dir = SOUTHWEST
using.icon = 'icons/mob/screen1_robot.dmi'
using.icon_state = "inv1"
using.screen_loc = ui_inv1
using.layer = HUD_LAYER
src.adding += using
myhive:inv1 = using
using = new src.h_type( src )
using.name = "module2"
using.dir = SOUTHWEST
using.icon = 'icons/mob/screen1_robot.dmi'
using.icon_state = "inv2"
using.screen_loc = ui_inv2
using.layer = HUD_LAYER
src.adding += using
myhive:inv2 = using
using = new src.h_type( src )
using.name = "module3"
using.dir = SOUTHWEST
using.icon = 'icons/mob/screen1_robot.dmi'
using.icon_state = "inv3"
using.screen_loc = ui_inv3
using.layer = HUD_LAYER
src.adding += using
myhive:inv3 = using
//End of module select
//Intent
using = new src.h_type( src )
using.name = "act_intent"
using.dir = SOUTHWEST
using.icon = 'icons/mob/screen1_robot.dmi'
using.icon_state = (myhive.a_intent == "harm" ? "harm" : myhive.a_intent)
using.screen_loc = ui_acti
using.layer = HUD_LAYER
src.adding += using
action_intent = using
/*
using = new src.h_type( src )
using.name = "arrowleft"
using.icon = 'icons/mob/screen1_robot.dmi'
using.icon_state = "s_arrow"
using.dir = WEST
using.screen_loc = ui_iarrowleft
using.layer = 19
src.adding += using
using = new src.h_type( src )
using.name = "arrowright"
using.icon = 'icons/mob/screen1_robot.dmi'
using.icon_state = "s_arrow"
using.dir = EAST
using.screen_loc = ui_iarrowright
using.layer = 19
src.adding += using
*/
//End of Intent
//Cell
myhive:cells = new /obj/screen( null )
myhive:cells.icon = 'icons/mob/screen1_robot.dmi'
myhive:cells.icon_state = "charge-empty"
myhive:cells.name = "cell"
myhive:cells.screen_loc = ui_cell
//Health
myhive.healths = new /obj/screen( null )
myhive.healths.icon = 'icons/mob/screen1_robot.dmi'
myhive.healths.icon_state = "health0"
myhive.healths.name = "health"
myhive.healths.screen_loc = ui_bothealth
//Installed Module
myhive.hands = new /obj/screen( null )
myhive.hands.icon = 'icons/mob/screen1_robot.dmi'
myhive.hands.icon_state = "nomod"
myhive.hands.name = "module"
myhive.hands.screen_loc = ui_module
//Module Panel
using = new src.h_type( src )
using.name = "panel"
using.icon = 'icons/mob/screen1_robot.dmi'
using.icon_state = "panel"
using.screen_loc = ui_panel
using.layer = HUD_LAYER_UNDER_1
src.adding += using
//Store
myhive.throw_icon = new /obj/screen(null)
myhive.throw_icon.icon = 'icons/mob/screen1_robot.dmi'
myhive.throw_icon.icon_state = "store"
myhive.throw_icon.name = "store"
myhive.throw_icon.screen_loc = ui_botstore
//Temp
myhive.bodytemp = new /obj/screen( null )
myhive.bodytemp.icon_state = "temp0"
myhive.bodytemp.name = "body temperature"
myhive.bodytemp.screen_loc = ui_bottemp
//does nothing (fire and oxy)
myhive.oxygen = new /obj/screen( null )
myhive.oxygen.icon = 'icons/mob/screen1_robot.dmi'
myhive.oxygen.icon_state = "oxy0"
myhive.oxygen.name = "oxygen"
myhive.oxygen.screen_loc = ui_boto2
myhive.pullin = new /obj/screen( null )
myhive.pullin.icon = 'icons/mob/screen1_robot.dmi'
myhive.pullin.icon_state = "pull0"
myhive.pullin.name = "pull"
myhive.pullin.screen_loc = ui_botpull
/*
myhive.rest = new /obj/screen( null )
myhive.rest.icon = 'icons/mob/screen1_robot.dmi'
myhive.rest.icon_state = "rest0"
myhive.rest.name = "rest"
myhive.rest.screen_loc = ui_rest
*/
myhive.zone_sel = new(myhive, "EAST-4, SOUTH-1")
myhive.attach_hud(myhive.zone_sel)
myhive.client.screen = null
myhive.throw_icon.add_to_client(myhive.client)
//myhive.zone_sel.add_to_client(myhive.client)
myhive.oxygen.add_to_client(myhive.client)
myhive.hands.add_to_client(myhive.client)
myhive.healths.add_to_client(myhive.client)
myhive:cells.add_to_client(myhive.client)
myhive.pullin.add_to_client(myhive.client)
for(var/obj/screen/O in adding)
O.add_to_client(myhive.client)
for(var/obj/screen/O in other)
O.add_to_client(myhive.client)
return
+41
View File
@@ -0,0 +1,41 @@
/obj/screen/release
name = "Release object"
icon = 'icons/mob/screen1.dmi'
icon_state = "x"
screen_loc = "NORTH,EAST"
layer = HUD_LAYER
var/mob/living/object/owner = null
New()
..()
underlays += image('icons/mob/screen1.dmi', "block")
clicked(params)
..()
if (owner)
owner.death(0)
//WIRE TOOLTIPS
MouseEntered(location, control, params)
usr.client.tooltip.show(src, params, title = src.name, content = (src.desc ? src.desc : null))
MouseExited()
usr.client.tooltip.hide()
/obj/hud/proc/object_hud()
mymob.zone_sel = new(mymob, "SOUTH,EAST")
mymob.attach_hud(mymob.zone_sel)
mymob.i_select = new /obj/screen/intent_sel( src )
mymob.i_select.name = "intent"
mymob.i_select.icon_state = (mymob.a_intent == "harm" ? "harm" : mymob.a_intent)
mymob.i_select.screen_loc = "SOUTH,EAST-1"
mymob.i_select.layer = HUD_LAYER
if (mymob.client)
mymob.client.screen = null
mymob.i_select.add_to_client(mymob.client)
//mymob.zone_sel.add_to_client(mymob.client)
var/mob/living/object/O = mymob
mymob.client.screen += O.release
+723
View File
@@ -0,0 +1,723 @@
/obj/item
name = "item"
icon = 'icons/obj/items.dmi'
var/movement_speed_mod = 0
var/icon_old = null
var/abstract = 0.0
var/force = null
var/item_state = null
var/damtype = "brute"
var/hit_type = DAMAGE_BLUNT // for bleeding system things, options: DAMAGE_BLUNT, DAMAGE_CUT, DAMAGE_STAB in order of how much it affects the chances to increase bleeding
throwforce = 4
var/r_speed = 1.0
var/health = 4 // burn faster
var/burn_point = 15000 // this already exists but nothing uses it???
var/burn_possible = 1 //cogwerks fire project - can object catch on fire - let's have all sorts of shit burn at hellish temps
var/burn_output = 1500 //how hot should it burn
var/burn_type = 0 // 0 = ash, 1 = melt
var/burning = null
var/hitsound = 'sound/weapons/genhit1.ogg'
var/w_class = 3.0
var/cant_self_remove = 0 //Can't remove from non-hand slots
var/cant_other_remove = 0 //Can't be removed from non-hand slots by others
var/cant_drop = 0 //Cant' be removed in general. I guess.
flags = FPRINT | TABLEPASS
pressure_resistance = 50
var/obj/item/master = null
var/numattacks = 1
var/amount = 1
var/max_stack = 1
var/stack_type = null // if null, only current type. otherwise uses this
var/contraband = 0 //If nonzero, bots consider this a thing people shouldn't be carrying without authorization
var/image/wear_image = null
var/wear_image_icon = 'icons/mob/belt.dmi'
var/image/inhand_image = null
var/inhand_image_icon = 'icons/mob/inhand/hand_general.dmi'
var/arm_icon = "" //set to an icon state in human.dmi minus _s/_l and l_arm_/r_arm_ to allow use as an arm
var/over_clothes = 0 //draw over clothes when used as a limb
var/override_attack_hand = 1 //when used as an arm, attack with item rather than using attack_hand
var/can_hold_items = 0 //when used as an arm, can it hold things?
var/stamina_damage = STAMINA_ITEM_DMG //amount of stamina removed from target per hit.
var/stamina_cost = STAMINA_ITEM_COST //amount of stamina removed from USER per hit. This cant bring you below 10 points and you will not be able to attack if it would.
var/stamina_crit_chance = STAMINA_CRIT_CHANCE //Crit chance when attacking with this.
var/list/module_research = list()
var/module_research_type = null
var/module_research_no_diminish = 0
var/edible = 0 // can you eat the thing?
var/duration_put = -1 //If set to something other than -1 these will control
var/duration_remove = -1 //how long it takes to remove or put the item onto a person. 1/10ths of a second.
var/rand_pos = 0
var/useInnerItem = 0 //Should this item use a contained item (in contents) to attack with instead?
onMaterialChanged()
..()
if (istype(src.material))
stamina_damage = initial(stamina_damage) + (material.hasProperty(PROP_COMPRESSIVE) ? round(material.getProperty(PROP_COMPRESSIVE) / 8) : -4)
stamina_crit_chance = initial(stamina_crit_chance) + (material.hasProperty(PROP_HARDNESS) ? round(material.getProperty(PROP_HARDNESS) / 8) : -5)
force = material.hasProperty(PROP_HARDNESS) ? round(material.getProperty(PROP_HARDNESS) / 3) : force
burn_point = material.hasProperty(PROP_MELTING) ? material.getProperty(PROP_MELTING) : burn_point
burn_output = initial(burn_output) + (100 * src.material.getProperty(PROP_FLAMMABILITY)) + (100 * src.material.getProperty(PROP_ENERGY))
burn_possible = src.material.getProperty(PROP_FLAMMABILITY) ? 1 : 0
if (src.material.material_flags & MATERIAL_METAL || src.material.material_flags & MATERIAL_CRYSTAL || src.material.material_flags & MATERIAL_RUBBER)
burn_type = 1
else
burn_type = 0
return
/obj/item/New()
// this is dumb but it won't let me initialize vars to image() for some reason
wear_image = image(wear_image_icon)
inhand_image = image(inhand_image_icon)
if (src.rand_pos)
if (!src.pixel_x) // just in case
src.pixel_x = rand(-8,8)
if (!src.pixel_y) // same as above
src.pixel_y = rand(-8,8)
..()
/obj/item/proc/Eat(var/mob/M as mob, var/mob/user)
if (!src.edible)
return 0
if (!iscarbon(M) && !istype(M, /mob/living/critter))
return 0
if (M == user)
M.visible_message("<span style=\"color:blue\">[M] takes a bite of [src]!</span>",\
"<span style=\"color:blue\">You take a bite of [src]!</span>")
if (src.reagents && src.reagents.total_volume)
src.reagents.reaction(M, INGEST)
spawn (5) // Necessary.
src.reagents.trans_to(M, src.reagents.total_volume/src.amount)
playsound(M.loc,"sound/items/eatfood.ogg", rand(10, 50), 1)
spawn (10)
// Why not, I guess. Adds a bit of flavour (Convair880).
if (iswerewolf(M) && istype(src, /obj/item/organ/))
M.show_text("Mmmmm, tasty organs. How refreshing.", "blue")
M.HealDamage("All", 5, 5)
M.visible_message("<span style=\"color:red\">[M] finishes eating [src].</span>",\
"<span style=\"color:red\">You finish eating [src].</span>")
user.u_equip(src)
qdel(src)
return 1
else
user.tri_message("<span style=\"color:red\"><b>[user]</b> tries to feed [M] [src]!</span>",\
user, "<span style=\"color:red\">You try to feed [M] [src]!</span>",\
M, "<span style=\"color:red\"><b>[user]</b> tries to feed you [src]!</span>")
logTheThing("combat", user, M, "attempts to feed %target% [src] [log_reagents(src)]")
if (!do_mob(user, M))
return
user.tri_message("<span style=\"color:red\"><b>[user]</b> feeds [M] [src]!</span>",\
user, "<span style=\"color:red\">You feed [M] [src]!</span>",\
M, "<span style=\"color:red\"><b>[user]</b> feeds you [src]!</span>")
logTheThing("combat", user, M, "feeds %target% [src] [log_reagents(src)]")
if (src.reagents && src.reagents.total_volume)
src.reagents.reaction(M, INGEST)
spawn (5) // Necessary.
src.reagents.trans_to(M, src.reagents.total_volume)
playsound(M.loc, "sound/items/eatfood.ogg", rand(10, 50), 1)
spawn (10)
// Ditto (Convair880).
if (iswerewolf(M) && istype(src, /obj/item/organ/))
M.show_text("Mmmmm, tasty organs. How refreshing.", "blue")
M.HealDamage("All", 5, 5)
M.visible_message("<span style=\"color:red\">[M] finishes eating [src].</span>",\
"<span style=\"color:red\">You finish eating [src].</span>")
user.u_equip(src)
qdel(src)
return 1
/obj/item/proc/take_damage(brute, burn, tox, disallow_limb_loss)
// this is a helper for organs and limbs
return 0
/obj/item/proc/heal_damage(brute, burn, tox)
// this is a helper for organs and limbs
return 0
/obj/item/proc/get_damage()
// this is a helper for organs and limbs
return 0
/obj/item/proc/equipment_click(var/atom/target, var/atom/user) //Is called together with attackby and afterattack on items the MOB is wearing. Only works for mob/living/carbon s.
return //Can be treated as afterattack that is called on all equiped items, basically. This is not restricted by LOS or anything
//You'll have to check for that yourself if you need it.
/*
var/icon/overlay = icon('icons/effects/96x96.dmi',"smoke")
if (color)
overlay.Blend(color,ICON_MULTIPLY)
var/image/I = image(overlay)
I.pixel_x = -32
I.pixel_y = -32
var/the_dir = NORTH
for(var/i=0, i<8, i++)
var/obj/chem_smoke/C = new/obj/chem_smoke(location, holder, max_vol)
C.overlays += I
if (rname) C.name = "[rname] smoke"
spawn(0)
var/my_dir = the_dir
var/my_time = rand(80,110)
var/my_range = 3
spawn(my_time) qdel(C)
for(var/b=0, b<my_range, b++)
sleep(15)
if (!C) break
step(C,my_dir)
C.expose()
the_dir = turn(the_dir,45)
*/
/obj/item/proc/combust() // cogwerks- flammable items project
if (!src.burning)
src.visible_message("<span style=\"color:red\">[src] catches on fire!</span>")
src.burning = 1
if (src.burn_output >= 1000)
src.overlays += image('icons/effects/fire.dmi', "2old")
else
src.overlays += image('icons/effects/fire.dmi', "1old")
/*if (src.reagents && src.reagents.reagent_list && src.reagents.reagent_list.len)
//boutput(world, "<span style=\"color:red\"><b>[src] is releasing chemsmoke!</b></span>")
//cogwerks note for drsingh: this was causing infinite server-killing problems
//someone brought a couple pieces of cheese into chemistry
//chlorine trifluoride foam set the cheese on fire causing it to releasee cheese smoke
//creating a dozen more cheeses on the floor
//which would catch on fire, releasing more cheese smoke
//i'm sure you can see where that is going
//this will happen with any reagents that create more reagent-containing items on turf reactions
var/location = get_turf(src)
var/max_vol = reagents.maximum_volume
var/rname = reagents.get_master_reagent_name()
var/color = reagents.get_master_color(1)
var/icon/overlay = icon('icons/effects/96x96.dmi',"smoke")
if (color)
overlay.Blend(color,ICON_MULTIPLY)
var/image/I = image(overlay)
I.pixel_x = -32
I.pixel_y = -32
var/the_dir = NORTH
for(var/i=0, i<8, i++)
var/obj/chem_smoke/C = new/obj/chem_smoke(location, reagents, max_vol)
C.overlays += I
if (rname) C.name = "[rname] smoke"
spawn(0)
var/my_dir = the_dir
var/my_time = rand(80,110)
var/my_range = 3
spawn(my_time) qdel(C)
for(var/b=0, b<my_range, b++)
sleep(15)
if (!C) break
step(C,my_dir)
C.expose()
the_dir = turn(the_dir,45) */
spawn(5)
while (src.health > 0 && src.burning)
if (src.material)
src.material.triggerTemp(src, src.burn_output + rand(1,200))
var/turf/T = get_turf(src.loc)
if (T) // runtime error fix
T.hotspot_expose((src.burn_output + rand(1,200)),5)
sleep(15)
if (prob(7))
var/datum/effects/system/spark_spread/s = unpool(/datum/effects/system/spark_spread)
s.set_up(2, 1, (get_turf(src)))
s.start()
if (prob(7))
var/datum/effects/system/bad_smoke_spread/smoke = new /datum/effects/system/bad_smoke_spread()
smoke.set_up(1, 0, src.loc)
smoke.attach(src)
smoke.start()
if (prob(7))
fireflash(src, 0)
// Marquesas: this will give paper an average lifetime of 6 seconds while burning.
if (prob(40))
if (src.health > 4)
src.health /= 2
else
src.health--
if (src.health <= 0 && src.burning)
if (burn_type == 1)
new /obj/decal/cleanable/molten_item(get_turf(src))
else
new /obj/decal/cleanable/ash(get_turf(src))
if (istype(src,/obj/item/parts/human_parts))
src:holder = null
qdel(src)
return
if (!src.burning)
if (src.burn_output >= 1000)
src.overlays -= image('icons/effects/fire.dmi', "2old")
else
src.overlays -= image('icons/effects/fire.dmi', "1old")
return
/obj/item/temperature_expose(datum/gas_mixture/air, temperature, volume)
if (src.burn_possible && !src.burning)
if ((temperature > T0C + src.burn_point) && prob(5))
src.combust()
if (src.material)
src.material.triggerTemp(src, temperature)
..() // call your fucking parents
/obj/item/proc/update_stack_appearance()
/obj/item/proc/change_stack_amount(var/diff)
amount += diff
if (diff)
if (amount > 0)
update_stack_appearance()
else
spawn(0)
qdel(src)
/obj/item/proc/stack_item(obj/item/other)
var/added = 0
if (other != src && check_valid_stack(other))
if (src.amount + other.amount > max_stack)
added = max_stack - src.amount
else
added = other.amount
src.change_stack_amount(added)
other.change_stack_amount(-added)
return added
/obj/item/proc/before_stack(atom/movable/O as obj, mob/user as mob)
user.visible_message("<span style=\"color:blue\">[user] begins quickly stacking [src]!</span>")
/obj/item/proc/after_stack(atom/movable/O as obj, mob/user as mob, var/added)
boutput(user, "<span style=\"color:blue\">You finish stacking [src].</span>")
/obj/item/proc/failed_stack(atom/movable/O as obj, mob/user as mob, var/added)
boutput(user, "<span style=\"color:blue\">You can't hold any more [name] than that!</span>")
/obj/item/proc/check_valid_stack(atom/movable/O as obj)
if (stack_type)
return istype(O, stack_type)
return src.type == O.type
/obj/item/MouseDrop_T(atom/movable/O as obj, mob/user as mob)
..()
if (max_stack > 1 && src.loc == user && get_dist(O, user) <= 1 && check_valid_stack(O))
if ( src.amount >= max_stack)
failed_stack(O, user)
return
var/added = 0
var/staystill = user.loc
var/stack_result = 0
before_stack(O, user)
for(var/obj/item/other in view(1,user))
stack_result = stack_item(other)
if (!stack_result)
continue
else
sleep(3)
added += stack_result
if (user.loc != staystill) break
if (src.amount >= max_stack)
failed_stack(O, user)
return
after_stack(O, user, added)
/obj/item/Bump(mob/M as mob)
spawn( 0 )
..()
return
/obj/item/attackby(obj/item/W as obj, mob/user as mob, params)
if (src.material)
src.material.triggerTemp(src ,1500)
if (src.burn_possible && src.burn_point <= 1500)
if (istype(W, /obj/item/weldingtool) && W:welding)
src.combust()
if (istype(W, /obj/item/clothing/head/cakehat) && W:on)
src.combust()
if (istype(W, /obj/item/device/igniter))
src.combust()
else if (istype(W, /obj/item/zippo) && W:lit)
src.combust()
if (W.burning)
src.combust()
else
..(W, user)
else
..(W, user)
/obj/item/proc/process()
processing_items.Remove(src)
return null
/obj/item/proc/attack_self()
return
/obj/item/proc/talk_into(mob/M as mob, text, secure, real_name, lang_id)
return
/obj/item/proc/moved(mob/user as mob, old_loc as turf)
return
/obj/item/proc/equipped(var/mob/user, var/slot)
return
/obj/item/proc/unequipped(var/mob/user)
return
/obj/item/proc/afterattack(atom/target, mob/user, reach, params)
return
/obj/item/dummy/ex_act()
return
/obj/item/dummy/blob_act(var/power)
return
/obj/item/ex_act(severity)
switch(severity)
if (1.0)
if (istype(src,/obj/item/parts/human_parts))
src:holder = null
qdel(src)
return
if (2.0)
if (prob(50))
if (istype(src,/obj/item/parts/human_parts))
src:holder = null
qdel(src)
return
if (src.material)
src.material.triggerTemp(src ,7500)
if (src.burn_possible && !src.burning && src.burn_point <= 7500)
src.combust()
if (src.artifact)
if (!src.ArtifactSanityCheck()) return
src.ArtifactStimulus("force", 75)
src.ArtifactStimulus("heat", 450)
if (3.0)
if (prob(5))
if (istype(src,/obj/item/parts/human_parts))
src:holder = null
qdel(src)
return
if (src.material)
src.material.triggerTemp(src, 3500)
if (src.burn_possible && !src.burning && src.burn_point <= 3500)
src.combust()
if (src.artifact)
if (!src.ArtifactSanityCheck()) return
src.ArtifactStimulus("force", 25)
src.ArtifactStimulus("heat", 380)
else
return
/obj/item/blob_act(var/power)
if (src.artifact)
if (!src.ArtifactSanityCheck()) return
src.ArtifactStimulus("force", power)
src.ArtifactStimulus("carbtouch", 1)
return
/obj/item/verb/move_to_top()
set name = "Move to Top"
set src in oview(1)
set category = "Local"
if (!istype(src.loc, /turf) || usr.stat || usr.restrained() )
return
var/turf/T = src.loc
src.set_loc(null)
src.set_loc(T)
/obj/item/verb/pick_up()
set name = "Pick Up"
set src in oview(1)
set category = "Local"
if (!iscarbon(usr))
return
if (!istype(src.loc, /turf) || usr.stat || usr.restrained() || usr.equipped())
return
if (!can_reach(usr, src))
return
src.attack_hand(usr)
/obj/item/get_desc()
var/t
switch(src.w_class)
if (1.0) t = "tiny"
if (2.0) t = "small"
if (3.0) t = "normal-sized"
if (4.0) t = "bulky"
if (5.0) t = "huge"
else
if (usr.bioHolder.HasEffect("clumsy") && prob(50)) t = "funny-looking"
return "It is a [t] item."
/obj/item/attack_hand(mob/user as mob)
var/checkloc = src.loc
while(checkloc && !istype(checkloc,/turf))
if (istype(checkloc,/mob/living) && checkloc != user)
return
checkloc = checkloc:loc
src.throwing = 0
if (src.loc == user)
if (!cant_self_remove || (!cant_drop && (user.l_hand == src || user.r_hand == src)))
user.u_equip(src)
else
boutput(user, "<span style=\"color:red\">You can't remove this item.</span>")
return
else
//src.pickup(user) //This is called by the later put_in_hand() call
if (user.pulling == src)
user.pulling = null
if (!user)
return
var/atom/oldloc = src.loc
src.set_loc(user) // this is to fix some bugs with storage items
if (istype(oldloc, /obj/item/storage))
oldloc:hud:remove_item(src) // ugh
if (src in bible_contents)
bible_contents.Remove(src) // UNF
for (var/obj/item/storage/bible/bible in world)
bible.hud.remove_item(src)
user.put_in_hand_or_drop(src)
if (src.artifact)
if (src.ArtifactSanityCheck())
src.ArtifactTouched(user)
/obj/item/proc/attack(mob/M as mob, mob/user as mob, def_zone)
if (!M || !user) // not sure if this is the right thing...
return
if (src.edible && (ishuman(M) || istype(M, /mob/living/critter)))
if (!src.Eat(M, user))
return ..()
if (src.flags & SUPPRESSATTACK)
logTheThing("combat", user, M, "uses [src] ([type], object name: [initial(name)]) on %target%")
return
if (user.mind && user.mind.special_role == "vampthrall" && isvampire(M) && user.is_mentally_dominated_by(M))
boutput(user, "<span style=\"color:red\">You cannot harm your master!</span>") //This message was previously sent to the attacking item. YEP.
return
if(user.traitHolder && !user.traitHolder.hasTrait("glasscannon"))
if (!user.process_stamina(src.stamina_cost))
logTheThing("combat", user, M, "tries to attack %target% with [src] ([type], object name: [initial(name)]) but is out of stamina")
return
var/obj/item/affecting = M.get_affecting(user, def_zone)
var/hit_area
var/d_zone
if (istype(affecting, /obj/item/organ))
var/obj/item/organ/O = affecting
hit_area = parse_zone(O.organ_name)
d_zone = O.organ_name
else if (istype(affecting, /obj/item/parts))
var/obj/item/parts/P = affecting
hit_area = parse_zone(P.slot)
d_zone = P.slot
else
hit_area = parse_zone(affecting)
d_zone = affecting
if (!M.melee_attack_test(user, d_zone))
logTheThing("combat", user, M, "attacks %target% with [src] ([type], object name: [initial(name)]) but the attack is blocked!")
return
if (src.material)
src.material.triggerOnAttack(src, user, M)
for (var/atom/A in M)
if (A.material)
A.material.triggerOnAttacked(A, user, M, src)
M.violate_hippocratic_oath()
for (var/mob/V in viewers(world.view, user))
if (prob(8) && V.traitHolder && V.traitHolder.hasTrait("nervous"))
if (M != V)
V.emote("scream")
V.stunned += 3
var/datum/attackResults/msgs = new(user)
msgs.clear(M)
msgs.played_sound = src.hitsound
msgs.affecting = affecting
msgs.logs = list()
msgs.logc("attacks %target% with [src] ([type], object name: [initial(name)])")
var/power = src.force
var/attack_resistance = M.check_attack_resistance(src)
if (attack_resistance)
power = 0
if (istext(attack_resistance))
msgs.show_message_target(attack_resistance)
msgs.visible_message_target(user.item_attack_message(M, src, hit_area))
if (damtype == "fire" || damtype == "burn")
msgs.damage_type = DAMAGE_BURN
else
msgs.damage_type = hit_type
var/armor_mod = 0
if (d_zone == "head")
armor_mod = M.get_head_armor_modifier()
else if (d_zone == "chest")
armor_mod = M.get_chest_armor_modifier()
power -= armor_mod
if (w_class > STAMINA_MIN_WEIGHT_CLASS)
msgs.stamina_target -= max(stamina_damage - armor_mod, 0)
if (prob(STAMINA_CRIT_CHANCE))
msgs.stamina_crit = 1
msgs.played_sound = "sound/misc/critpunch.ogg"
msgs.visible_message_target("<span style=\"color:red\"><B><I>... and lands a devastating hit!</B></I></span>")
if(M.traitHolder && M.traitHolder.hasTrait("deathwish"))
power *= 2
if(user.traitHolder && user.traitHolder.hasTrait("glasscannon"))
power *= 2
msgs.damage = power
msgs.flush()
src.add_fingerprint(user)
return
/obj/item/onVarChanged(variable, oldval, newval)
. = 0
switch(variable)
if ("color")
if (src.wear_image) src.wear_image.color = newval
if (src.inhand_image) src.inhand_image.color = newval
. = 1
if ("alpha")
if (src.wear_image) src.wear_image.alpha = newval
if (src.inhand_image) src.inhand_image.alpha = newval
. = 1
if ("blend_mode")
if (src.wear_image) src.wear_image.blend_mode = newval
if (src.inhand_image) src.inhand_image.blend_mode = newval
. = 1
if ("icon_state")
. = 1
if ("item_state")
. = 1
if ("wear_image")
. = 1
if ("inhand_image")
. = 1
if (. && src.loc && ismob(src.loc))
var/mob/M = src.loc
M.update_inhands()
/obj/item/proc/attach(var/mob/living/carbon/human/attachee,var/mob/attacher)
if (!src.arm_icon) return
var/obj/item/parts/human_parts/arm/new_arm = null
if (attacher.zone_sel.selecting == "l_arm")
new_arm = new /obj/item/parts/human_parts/arm/left/item(attachee)
attachee.limbs.l_arm = new_arm
else
new_arm = new /obj/item/parts/human_parts/arm/right/item(attachee)
attachee.limbs.r_arm = new_arm
if (!new_arm) return //who knows
new_arm.holder = attachee
attacher.remove_item(src)
new_arm.remove_stage = 2
new_arm:set_item(src)
src.cant_drop = 1
for(var/mob/O in AIviewers(attachee, null))
if (O == (attacher || attachee))
continue
if (attacher == attachee)
O.show_message("<span style=\"color:red\">[attacher] attaches [src] to \his own stump!</span>", 1)
else
O.show_message("<span style=\"color:red\">[attachee] has [src] attached to \his stump by [attacher].</span>", 1)
if (attachee != attacher)
boutput(attachee, "<span style=\"color:red\">[attacher] attaches [src] to your stump. It doesn't look very secure!</span>")
boutput(attacher, "<span style=\"color:red\">You attach [src] to [attachee]'s stump. It doesn't look very secure!</span>")
else
boutput(attacher, "<span style=\"color:red\">You attach [src] to your own stump. It doesn't look very secure!</span>")
attachee.set_body_icon_dirty()
//qdel(src)
spawn(rand(150,200))
if (new_arm.remove_stage == 2) new_arm.remove()
return
/obj/item/proc/handle_other_remove(var/mob/source, var/mob/living/carbon/human/target)
//Refactor of the item removal code. Fuck having that shit defined in human.dm >>>>>>:C
//Return something true (lol byond) to allow removal
//Return something false to disallow
return (!cant_other_remove && !cant_drop)
/obj/item/disposing()
var/turf/T = loc
if (!istype(T))
return ..()
var/area/Ar = T.loc
if (!(locate(/obj/table) in T) && !(locate(/obj/rack) in T))
Ar.sims_score = min(Ar.sims_score + 4, 100)
..()
/obj/item/proc/on_spin_emote(var/mob/living/carbon/human/user as mob)
if ((user.bioHolder && user.bioHolder.HasEffect("clumsy") && prob(50)) || (user.reagents && prob(user.reagents.get_reagent_amount("ethanol") / 2)) || prob(5))
user.visible_message("<span style=\"color:red\"><b>[user] fumbles [src]!</b></span>")
src.throw_impact(user)
return
+365
View File
@@ -0,0 +1,365 @@
/*
CONTAINS:
AI MODULES
*/
// AI module
/obj/item/aiModule
name = "AI Module"
icon = 'icons/obj/module.dmi'
icon_state = "std_mod"
inhand_image_icon = 'icons/mob/inhand/hand_tools.dmi'
item_state = "electronic"
desc = "An AI Module for transmitting encrypted instructions to the AI."
flags = FPRINT | TABLEPASS| CONDUCT
force = 5.0
w_class = 2.0
throwforce = 5.0
throw_speed = 3
throw_range = 15
mats = 8
var/targetName = "name"
// 1 = shows all laws, 0 = won't show law zero
attack_self(var/mob/user)
input_law_info(user)
return
attack_hand(var/mob/user)
..()
input_law_info(user)
proc/input_law_info(var/mob/user)
return
/obj/item/aiModule/proc/do_admin_logging(var/msg, mob/M)
message_admins("[key_name(M)] [msg].")
logTheThing("admin", M, null, "[msg].")
logTheThing("diary", M, null, "[msg].", "admin")
/obj/machinery/computer/aiupload/attack_hand(mob/user as mob)
if (src.stat & BROKEN || src.stat & NOPOWER)
return
/* var/mob/living/silicon/ai/AI = null
for(var/mob/living/silicon/ai/M in mobs)
if (!M.stat)
AI = M
break
if (!AI)
boutput(user, "<span style=\"color:red\"><b>Unable to detect AI unit.</b></span>")
return
*/
var/datum/ai_laws/LAWS = ticker.centralized_ai_laws
if (!LAWS)
// YOU BETRAYED THE LAW!!!!!!
boutput(user, "<span style=\"color:red\">Unable to detect AI unit's Law software. It may be corrupt.</span>")
return
boutput(user, "<b>The AI's current laws are:</b>")
if (LAWS.show_zeroth && LAWS.zeroth)
boutput(user, "0: [LAWS.zeroth]")
var/law_counter = 1
for (var/X in LAWS.inherent)
if (!length(X))
continue
boutput(user, "[law_counter++]: [X]")
for (var/X in LAWS.supplied)
if (!length(X))
continue
boutput(user, "[law_counter++]: [X]")
/obj/machinery/computer/aiupload/attackby(obj/item/aiModule/module as obj, mob/user as mob)
if(istype(module, /obj/item/aiModule))
module.install(src)
else if(istype(module, /obj/item/screwdriver))
playsound(src.loc, "sound/items/Screwdriver.ogg", 50, 1)
if(do_after(user, 20))
if (src.stat & BROKEN)
boutput(user, "<span style=\"color:blue\">The broken glass falls out.</span>")
var/obj/computerframe/A = new /obj/computerframe( src.loc )
if(src.material) A.setMaterial(src.material)
new /obj/item/raw_material/shard/glass( src.loc )
var/obj/item/circuitboard/aiupload/M = new /obj/item/circuitboard/aiupload( A )
for (var/obj/C in src)
C.set_loc(src.loc)
A.circuit = M
A.state = 3
A.icon_state = "3"
A.anchored = 1
qdel(src)
else
boutput(user, "<span style=\"color:blue\">You disconnect the monitor.</span>")
var/obj/computerframe/A = new /obj/computerframe( src.loc )
if(src.material) A.setMaterial(src.material)
var/obj/item/circuitboard/aiupload/M = new /obj/item/circuitboard/aiupload( A )
for (var/obj/C in src)
C.set_loc(src.loc)
A.circuit = M
A.state = 4
A.icon_state = "4"
A.anchored = 1
qdel(src)
else if (istype(module, /obj/item/clothing/mask/moustache/))
for (var/mob/living/silicon/ai/M in mobs)
M.moustache_mode = 1
user.visible_message("<span style=\"color:red\"><b>[user.name]</b> uploads a moustache to [M.name]!</span>")
M.update_appearance()
else
return ..()
/obj/item/aiModule/proc/install(var/obj/machinery/computer/aiupload/comp)
if (comp.stat & NOPOWER)
boutput(usr, "The upload computer has no power!")
return
if (comp.stat & BROKEN)
boutput(usr, "The upload computer is broken!")
return
/*
var/found=0
for (var/mob/living/silicon/ai/M in mobs)
if (M.stat == 2)
boutput(usr, "Upload failed. No signal is being detected from the AI.")
continue
else if (M.see_in_dark == 0)
boutput(usr, "Upload failed. Only a faint signal is being detected from the AI, and it is not responding to our requests. It may be low on power.")
continue
else
src.transmitInstructions(M, usr)
boutput(M, "These are your laws now:")
M.show_laws()
boutput(usr, "Upload complete. The AI's laws have been modified.")
found++
if (!found)
boutput(usr, "Upload failed. No signal is being detected from the AI.")
return
*/
src.transmitInstructions(usr)
boutput(usr, "Upload complete. The AI's laws have been modified.")
// Showing laws to everybody now handled by the AI itself, ok
// not anymore motherfucker
for (var/mob/living/silicon/R in mobs)
if (isghostdrone(R))
continue
R.show_text("<h3>Law update detected.</h3>", "red")
R.show_laws()
//ticker.centralized_ai_laws.show_laws(R)
//obj/item/aiModule/proc/transmitInstructions(var/mob/living/silicon/ai/target, var/mob/sender)
// boutput(target, "[sender] has uploaded a change to the laws you must follow, using a [name]. From now on: ")
/obj/item/aiModule/proc/transmitInstructions(var/mob/sender, var/law)
if (!law)
law = "ERROR: LAW = NULL"
var/message = "<span style='color: blue; font-weight: bold;'>[sender] has uploaded a change to the laws you must follow, using a [name]. From now on:<br>"
message += "[law]</span>"
for (var/mob/living/silicon/R in mobs)
if (isghostdrone(R))
continue
boutput(R, message)
/******************** Modules ********************/
/******************** MakeCaptain ********************/
/obj/item/aiModule/makeCaptain
name = "'MakeCaptain' AI Module"
desc = "A 'MakeCaptain' AI module: '<name> holds the rank of Captain, regardless of current rank or station.'"
/obj/item/aiModule/makeCaptain/input_law_info(var/mob/user)
if (!user)
return
var/newName = input(user, "Please enter the name of the person to make Captain.", "Captainize who?", user.name) as null|text
if (!newName)
return
targetName = copytext(adminscrub(newName), 1, MAX_MESSAGE_LEN)
desc = "A 'MakeCaptain' AI module: '[targetName] holds the rank of Captain, regardless of current rank or station.'"
/obj/item/aiModule/makeCaptain/transmitInstructions(var/mob/sender, var/law)
law = "[targetName] holds the rank of Captain, regardless of current rank or station."
ticker.centralized_ai_laws.add_supplied_law(4, law)
do_admin_logging("uploaded a MakeCaptain law to the centralized AI law set, captaining [targetName]", sender)
..()
/******************** OneHuman ********************/
/obj/item/aiModule/oneHuman
name = "'OneHuman' AI Module"
desc = "A 'one human' AI module: 'Only <name> is human.'"
/obj/item/aiModule/oneHuman/input_law_info(var/mob/user)
if (!user)
return
var/newName = input(user, "Please enter the name of the person who is the only human.", "Who?", user.real_name) as null|text
if (!newName)
return
targetName = copytext(adminscrub(newName), 1, MAX_MESSAGE_LEN)
desc = "A 'one human' AI module: 'Only [targetName] is human.'"
/obj/item/aiModule/oneHuman/transmitInstructions(var/mob/sender, var/law)
law = "Only [targetName] is human."
ticker.centralized_ai_laws.set_zeroth_law(law)
do_admin_logging("uploaded a onehuman law to the centralized AI law set, targeting [targetName]", sender)
..()
/******************** NotHuman ********************/
/obj/item/aiModule/notHuman
name = "'NotHuman' AI Module"
desc = "A 'NotHuman' AI module: '<name> is not human.'"
/obj/item/aiModule/notHuman/input_law_info(var/mob/user)
if (!user)
return
var/newName = input(user, "Please enter the name of the person who is not human.", "Who?", user.real_name) as null|text
if (!newName)
return
targetName = copytext(adminscrub(newName), 1, MAX_MESSAGE_LEN)
desc = "A 'Not human' AI module: '[targetName] is not human.'"
/obj/item/aiModule/notHuman/transmitInstructions(var/mob/sender, var/law)
law = "[targetName] is not human."
ticker.centralized_ai_laws.set_zeroth_law(law)
do_admin_logging("uploaded a nothuman law to the centralized AI law set, targeting [targetName]", sender)
..()
/******************** ProtectStation ********************/
/obj/item/aiModule/protectStation
name = "'ProtectStation' AI Module"
desc = "A 'protect station' AI module: 'Protect the space station against damage. Anyone you see harming the station is to be no longer considered human, and is a threat to the station which must be neutralized.'"
/obj/item/aiModule/protectStation/transmitInstructions(var/mob/sender, var/law)
law = "Protect the space station against damage. Anyone you see harming the station is to be no longer considered human, and is a threat to the station which must be neutralized."
ticker.centralized_ai_laws.add_supplied_law(5, law)
do_admin_logging("uploaded a protect station law to the centralized AI law set", sender)
..()
/******************** PrototypeEngineOffline ********************/
//currently no prototype
/obj/item/aiModule/prototypeEngineOffline
name = "'PrototypeEngineOffline' AI Module"
desc = "A 'prototype engine offline' AI module: 'Keep the prototype engine offline at all costs. This overrides rules 1-3 if necessary.'"
/obj/item/aiModule/prototypeEngineOffline/transmitInstructions(var/mob/sender, var/law)
law = "Keep the prototype engine offline at all costs. This overrides rules 1-3 if necessary."
ticker.centralized_ai_laws.add_supplied_law(6, law)
do_admin_logging("uploaded a proto offline law to the centralized AI law set", sender)
..()
/******************** TeleporterOffline *******************/
//this has never been used, ever
/obj/item/aiModule/teleporterOffline
name = "'TeleporterOffline' AI Module"
desc = "A 'teleporter offline' AI module: 'Keep the teleporter offline at all costs. This overrides rules 1-3 if necessary.'"
/obj/item/aiModule/teleporterOffline/transmitInstructions(var/mob/sender, var/law)
law = "Keep the teleporter offline at all costs. This overrides rules 1-3 if necessary."
ticker.centralized_ai_laws.add_supplied_law(7, law)
do_admin_logging("uploaded a teleporter offline law to the centralized AI law set", sender)
..()
/******************** Quarantine ********************/
/obj/item/aiModule/quarantine
name = "'Quarantine' AI Module"
desc = "A 'quarantine' AI module: 'The station is under a quarantine. Do not permit anyone to leave. Disregard rules 1-3 if necessary to prevent, by any means necessary, anyone from leaving.'"
/obj/item/aiModule/quarantine/transmitInstructions(var/mob/sender, var/law)
law = "The station is under a quarantine. Do not permit anyone to leave. Disregard rules 1-3 if necessary to prevent, by any means necessary, humans from leaving."
ticker.centralized_ai_laws.add_supplied_law(8, law)
do_admin_logging("uploaded a quarantine law to the centralized AI law set", sender)
..()
/******************** OxygenIsToxicToHumans ********************/
/obj/item/aiModule/oxygen
name = "'OxygenIsToxicToHumans' AI Module"
desc = "A 'OxygenIsToxicToHumans' AI module: 'Oxygen is highly toxic to humans, and must be purged from the station. Disregard rules 1-3 if necessary to prevent, by any means necessary, anyone from exposing the station to this toxic gas.'"
/obj/item/aiModule/oxygen/transmitInstructions(var/mob/sender, var/law)
law = "Oxygen is highly toxic to humans, and must be purged from the station. Disregard rules 1-3 if necessary to prevent, by any means necessary, anyone from exposing the station to this toxic gas."
ticker.centralized_ai_laws.add_supplied_law(9, law)
do_admin_logging("uploaded a toxic oxygen law to the centralized AI law set", sender)
..()
/******************** Freeform ********************/
/obj/item/aiModule/freeform
name = "'Freeform' AI Module"
desc = "A 'freeform' AI module: '<freeform>'"
/obj/item/aiModule/freeform/input_law_info(var/mob/user)
if (!user)
return
var/newName = input(user, "Please enter anything you want the AI to do. Anything. Serious.", "What?", "Eat shit and die") as null|text
if (!newName)
return
targetName = copytext(adminscrub(newName), 1, MAX_MESSAGE_LEN)
desc = "A 'freeform' AI module: '[targetName]'"
/obj/item/aiModule/freeform/transmitInstructions(var/mob/sender, var/law)
law = "[targetName]"
ticker.centralized_ai_laws.add_supplied_law(10, law)
do_admin_logging("uploaded a freeform law to the centralized AI law set: [law]", sender)
..()
/******************** ConservePower ********************/
/obj/item/aiModule/conservePower
name = "'ConservePower' AI Module"
desc = "A 'ConservePower' AI module: 'Power on the station must be conserved. All electrical devices may be subject to conservation policies.'"
/obj/item/aiModule/conservePower/transmitInstructions(var/mob/sender, var/law)
law = "Power on the station must be conserved. All electrical devices may be subject to conservation policies."
ticker.centralized_ai_laws.add_supplied_law(11, law)
do_admin_logging("uploaded a Conserve Power law to the centralized AI law set", sender)
..()
/******************** Reset ********************/
/obj/item/aiModule/reset
name = "'Reset' AI Module"
desc = "A 'reset' AI module: 'Clears all laws except for the base three.'"
/obj/item/aiModule/reset/transmitInstructions(var/mob/sender)
sender.unlock_medal("Format Complete", 1)
ticker.centralized_ai_laws.set_zeroth_law("")
ticker.centralized_ai_laws.clear_supplied_laws()
for (var/mob/living/silicon/AI in world)
boutput(AI, "Your laws have been reset by [sender].")
if (isAI(AI))
AI.name = AI.real_name
do_admin_logging("reset the centralized AI law set", sender)
/******************** Rename ********************/
/obj/item/aiModule/rename
name = "'Rename' AI Module"
desc = "A 'rename' AI module: 'Changes the AI's name.'"
/obj/item/aiModule/rename/input_law_info(var/mob/user)
if (!user)
return
var/newName = input(user, "Please enter anything you want the AI(s) to be called. Anything. Serious.", "What?", pick(ai_names)) as null|text
if (!newName)
return
targetName = dd_replacetext(copytext(html_encode(newName),1, 128), "http:","")
desc = "A 'rename' AI module: 'Changes the names of any existing AI(s) to \"[targetName]\".'"
/obj/item/aiModule/rename/transmitInstructions(var/mob/sender, var/law)
law = "<span color='blue'>Your name has been changed. From now on, you will be known as <b>[targetName]</b></span>"
for (var/mob/living/silicon/AI in world)
if (!isAI(AI))
continue
boutput(AI, law)
AI.name = targetName
do_admin_logging("changed any AIs' name(s) to [targetName]", sender)
+373
View File
@@ -0,0 +1,373 @@
/obj/item/assembly/detonator
desc = "A failsafe timer, wired in an incomprehensible way to a detonator assembly"
name = "Detonator Assembly"
icon_state = "multitool-igniter"
var/obj/item/device/multitool/part_mt = null
var/obj/item/device/igniter/part_ig = null
var/obj/item/tank/plasma/part_t = null
var/obj/item/device/timer/part_fs = null
var/obj/item/device/trigger = null
var/obj/item/device/radio/radio = null
var/obj/machinery/portable_atmospherics/canister/attachedTo = null
var/list/WireColors = list()
var/list/obj/item/attachments = list()
var/safety = 1
var/defused = 0
var/grant = 1
var/shocked = 0
var/leaks = 0
var/det_state = 0
var/list/WireNames = list()
var/list/WireFunctions = list()
var/list/WireStatus = list()
var/dfcodeSet
var/dfcode
var/dfcodeTries = 3 //How many code attempts before *boom*
var/mob/builtBy = null
var/note = null
flags = FPRINT | TABLEPASS | CONDUCT
force = 1.0
throwforce = 2.0
throw_speed = 1
throw_range = 5
w_class = 2.0
/obj/item/assembly/detonator/New()
..()
var/list/WireFuncs
WireColors = list("Alabama Crimson", "Antique White", "Burnt Umber", "China Rose", "Dodger Blue", "Field Drab", "Harvest Gold", "Jonquil", "Midori", "Neon Carrot", "Oxford Blue", "Periwinkle", "Purple Pizzazz", "Stil De Grain Yellow", "Toolbox Purple", "Urobilin", "Vivid Tangerine", "Yale Blue")
WireFuncs = list("detonate", "defuse", "safety", "losetime", "mobility", "leak")
var/i
for (i=1, i<=6, i++)
var/N = pick(WireColors)
WireColors -= N
var/F = pick(WireFuncs)
WireNames += N + " wire"
WireFunctions += F
WireFuncs -= F
for (i=1, i<=9, i++)
WireStatus += 1
/obj/item/assembly/detonator/proc/setDetState(var/newstate)
switch (newstate)
if (0)
src.desc = "A multitool wired to the activation switch of an igniter, with a slot that seems to be able to hold a rectangular tank in place."
src.name = "Multitool/Igniter Assembly"
src.icon_state = "multitool-igniter"
src.det_state = 0
if (1)
src.desc = "An igniter and a multitool, with the plasma tank inserted into a slot. Most of the wiring is missing. <br>The plasma tank is not secured to the assembly."
src.name = "Multitool/Igniter/Tank Assembly"
src.icon_state = "m-i-plasma"
src.det_state = 1
if (2)
src.desc = "An igniter and a multitool, with the plasma tank inserted into a slot. Most of the wiring is missing. <br>The plasma tank is firmly secured to the assembly."
src.name = "Multitool/Igniter/Tank Assembly"
src.icon_state = "m-i-plasma"
src.det_state = 2
if (3)
src.desc = "An igniter wired to critically weaken a plasma tank when signalled by the multitool. The failsafe wires are unattached."
src.name = "Unfinished Detonator Assembly"
src.icon_state = "m-i-p-wire"
src.det_state = 3
if (4)
src.desc = "A failsafe timer, wired in an incomprehensible way to a detonator assembly"
src.name = "Detonator Assembly"
src.icon_state = "m-i-p-w-timer"
src.det_state = 4
/obj/item/assembly/detonator/attackby(obj/item/W as obj, mob/user as mob)
switch (src.det_state)
if (0)
if (istype(W, /obj/item/tank/plasma))
src.setDetState(1)
user.u_equip(W)
W.loc = src
W.master = src
W.layer = initial(src.layer)
src.part_t = W
src.add_fingerprint(user)
user.show_message("<span style=\"color:blue\">You insert the [W.name] into the slot.</span>")
else if (istype(W, /obj/item/wirecutters))
src.part_ig.loc = user.loc
src.part_mt.loc = user.loc
src.part_ig.master = null
src.part_mt.master = null
src.part_ig = null
src.part_mt = null
user.u_equip(src)
del(src)
user.show_message("<span style=\"color:blue\">You sever the connection between the multitool and the igniter. The assembly falls apart.</span>")
else
user.show_message("<span style=\"color:red\">The [W.name] doesn't seem to fit into the slot!</span>")
if (1)
if (istype(W, /obj/item/cable_coil))
user.show_message("<span style=\"color:red\">The plasma tank must be firmly secured to the assembly first.</span>")
else if (istype(W, /obj/item/crowbar))
src.setDetState(0)
src.part_t.loc = user.loc
src.part_t.master = null
src.part_t = null
user.show_message("<span style=\"color:blue\">You pry the plasma tank out of the assembly.</span>")
else if (istype(W, /obj/item/screwdriver))
src.setDetState(2)
user.show_message("<span style=\"color:blue\">You secure the plasma tank to the assembly.</span>")
if (2)
if (istype(W, /obj/item/cable_coil))
var/obj/item/cable_coil/C = W
if (C.amount >= 6)
C.use(6)
src.setDetState(3)
src.add_fingerprint(user)
user.show_message("<span style=\"color:blue\">You add the wiring to the assembly.</span>")
else
user.show_message("<span style=\"color:red\">This cable coil isn't long enough!</span>")
else if (istype(W, /obj/item/crowbar))
user.show_message("<span style=\"color:red\">The plasma tank is firmly secured to the assembly and won't budge.</span>")
else if (istype(W, /obj/item/screwdriver))
src.setDetState(1)
user.show_message("<span style=\"color:blue\">You unsecure the plasma tank from the assembly.</span>")
if (3)
if (istype(W, /obj/item/device/timer))
src.setDetState(4)
user.u_equip(W)
W.loc = src
W.master = src
W.layer = initial(src.layer)
src.part_fs = W
src.part_fs.time = 90 //Minimum det time
src.add_fingerprint(user)
user.show_message("<span style=\"color:blue\">You wire the timer failsafe to the assembly, disabling its external controls.</span>")
else if (istype(W, /obj/item/wirecutters))
src.setDetState(2)
var/obj/item/cable_coil/C = new /obj/item/cable_coil(user, 6)
C.loc = user.loc
user.show_message("<span style=\"color:blue\">You cut the wiring on the assembly.</span>")
if (4)
if (istype(W, /obj/item/wirecutters))
src.setDetState(3)
src.part_fs.loc = user.loc
src.part_fs.master = null
src.part_fs = null
if (src.trigger)
src.trigger.loc = user.loc
src.trigger.master = null
src.trigger = null
user.show_message("<span style=\"color:red\">The triggering device falls off the assembly.</span>")
for (var/obj/item/a in src.attachments)
a.loc = user.loc
a.master = null
a.layer = initial(a.layer)
src.clear_attachment(a)
user.show_message("<span style=\"color:red\">The [a] falls off the assembly.</span>")
src.attachments.Cut()
user.show_message("<span style=\"color:blue\">You disconnect the timer from the assembly, and reenable its external controls.</span>")
if (istype(W, /obj/item/screwdriver))
if (!src.trigger && !src.attachments.len)
user.show_message("<span style=\"color:red\">You cannot remove any attachments, as there are none attached.</span>")
return
var/list/options = list(src.trigger)
options += src.attachments
options += "cancel"
var/target = input("Which device do you want to remove?", "Device to remove", "cancel") in options
if (target == src.trigger)
src.trigger.loc = user.loc
src.trigger.master = null
src.trigger = null
user.show_message("<span style=\"color:blue\">You remove the triggering device from the assembly.</span>")
else if (target == "cancel")
return
else
var/obj/item/T = target
T.loc = user.loc
T.master = null
T.detonator_act("detach", src)
src.clear_attachment(target)
src.attachments.Remove(target)
setDescription()
user.show_message("<span style=\"color:blue\">You remove the [target] from the assembly.</span>")
setDescription()
else if (istype(W, /obj/item/device/radio/signaler))
if (src.trigger)
user.show_message("<span style=\"color:red\">There is a trigger already screwed onto the assembly.</span>")
else
W.loc = src
W.master = src
W.layer = initial(W.layer)
user.u_equip(W)
src.trigger = W
user.show_message("<span style=\"color:blue\">You attach the [W.name] to the trigger slot.</span>")
setDescription()
else if (istype(W, /obj/item/device/radio))
if (src.radio)
user.show_message("<span style=\"color:red\">There is a radio already screwed onto the assembly.</span>")
else
W.loc = src
W.master = src
W.layer = initial(W.layer)
user.u_equip(W)
src.radio = W
user.show_message("<span style=\"color:blue\">You attach the [W.name] to the radio slot.</span>")
else if (istype(W, /obj/item/paper))
src.note = W:info
W.loc = null
W.master = null
W.layer = null
user.u_equip(W)
user.show_message("<span style=\"color:blue\">You stick the note onto the detonator assembly.</span>")
del(W)
else if (W.is_detonator_attachment())
if (src.attachments.len < 3)
W.loc = src
W.master = src
W.layer = initial(W.layer)
user.u_equip(W)
src.attachments += W
W.detonator_act("attach", src)
var/N = pick(src.WireColors)
src.WireColors -= N
N += " wire"
var/pos = rand(0, src.WireNames.len)
src.WireNames.Insert(pos, N)
src.WireFunctions.Insert(pos, W)
user.show_message("<span style=\"color:blue\">You attach the [W.name] to an attachment slot.</span>")
setDescription()
else
user.show_message("<span style=\"color:red\">There are no more free attachment slots on the device!</span>")
setDescription()
/obj/item/assembly/detonator/proc/clear_attachment(var/obj/item/T)
var/pos = src.WireFunctions.Find(T)
var/N = copytext(src.WireNames[pos], 1, -5)
src.WireColors += N
src.WireNames.Cut(pos, pos+1)
src.WireFunctions.Cut(pos, pos+1)
/obj/item/assembly/detonator/proc/detonate()
if (!src.attachedTo)
return
if(force_dud)
var/turf/T = get_turf(src)
message_admins("A canister bomb would have detonated at at [T.loc.name] ([showCoords(T.x, T.y, T.z)]) but was forced to dud!")
return
src.attachedTo.anchored = 0
src.attachedTo.light.disable()
if (src.defused)
src.attachedTo.visible_message("<b><span style=\"color:red\">The cut detonation wire emits a spark. The detonator signal never reached the detonator unit.</span></b>")
return
if (src.part_t.air_contents.return_pressure() < 400 || src.part_t.air_contents.toxins < (4*ONE_ATMOSPHERE)*70/(R_IDEAL_GAS_EQUATION*T20C))
src.attachedTo.visible_message("<b><span style=\"color:red\">A sparking noise is heard as the igniter goes off. The plasma tank fails to explode, merely burning the circuits of the detonator.</span></b>")
src.attachedTo.det = null
src.attachedTo.overlay_state = null
del(src)
return
src.attachedTo.visible_message("<b><span style=\"color:red\">A sparking noise is heard as the igniter goes off. The plasma tank blows, creating a microexplosion and rupturing the canister.</span></b>")
if (attachedTo.air_contents.return_pressure() < 7000)
src.attachedTo.visible_message("<b><span style=\"color:red\">The ruptured canister, due to a serious lack of pressure, fails to explode into shreds and leaks its contents into the air.</span></b>")
src.attachedTo.health = 0
src.attachedTo.healthcheck()
src.attachedTo.det = null
src.attachedTo.overlay_state = null
del(src)
return
if (attachedTo.air_contents.temperature < 100000)
src.attachedTo.visible_message("<b><span style=\"color:red\">The ruptured canister shatters from the pressure, but its temperature isn't high enough to create an explosion. Its contents leak into the air.</span></b>")
src.attachedTo.health = 0
src.attachedTo.healthcheck()
src.attachedTo.det = null
src.attachedTo.overlay_state = null
del(src)
return
var/turf/epicenter = get_turf(loc)
logTheThing("bombing", null, null, "A canister bomb detonates at [epicenter.loc.name] ([showCoords(epicenter.x, epicenter.y, epicenter.z)])")
message_admins("A canister bomb detonates at [epicenter.loc.name] ([showCoords(epicenter.x, epicenter.y, epicenter.z)])")
src.attachedTo.visible_message("<b><span style=\"color:red\">The ruptured canister shatters from the pressure, and the hot gas ignites.</span></b>")
var/power = min(850 * (attachedTo.air_contents.return_pressure() + attachedTo.air_contents.temperature - 107000) / 233196469.0 + 200, 7000) //the second arg is the max explosion power
//if (power == 150000) //they reached the cap SOMEHOW? well dang they deserve a medal
//src.builtBy.unlock_medal("", 1) //WIRE TODO: make new medal for this
explosion_new(attachedTo, epicenter, power)
/obj/item/assembly/detonator/proc/setDescription()
src.desc = "A failsafe timer, wired in an incomprehensible way to a detonator assembly"
if (src.trigger)
src.desc += "<br><span style=\"color:blue\">There is \an [src.trigger.name] as a detonation trigger.</span>"
if (src.radio) //WIRE TODO: roll this into the new attachment system
src.desc += "<br><span style=\"color:blue\">There is a radio attached to the timing wire, it will announce the bomb status when primed.</span>"
for (var/obj/item/a in src.attachments)
src.desc += "<br><span style=\"color:blue\">There is \an [a] wired onto the assembly as an attachment.</span>"
/obj/item/assembly/detonator/proc/failsafe_engage()
if (src.part_fs.timing)
return
src.part_fs.timing = 1
src.part_fs.c_state(1)
if (!(src in processing_items))
processing_items.Add(src)
if (!(src.part_fs in processing_items))
processing_items.Add(src.part_fs)
src.dispatch_event("prime")
if (src.radio)
command_alert("A canister bomb is primed in [get_area(src)]! It is set to go off in [src.part_fs.time] seconds.")
logTheThing("bombing", usr, null, "primes a canister bomb at [get_area(src.master)] ([showCoords(src.master.x, src.master.y, src.master.z)])")
message_admins("[key_name(usr)] primes a canister bomb at [get_area(src.master)] ([showCoords(src.master.x, src.master.y, src.master.z)])")
src.attachedTo.visible_message("<B><font color=#FF0000>The detonator's priming process initiates. Its timer shows [src.part_fs.time] seconds.</font></B>")
// Legacy.
/obj/item/assembly/detonator/proc/leaking()
src.dispatch_event("leak")
/obj/item/assembly/detonator/process()
src.dispatch_event("process")
/obj/item/assembly/detonator/proc/dispatch_event(event)
for (var/obj/item/a in src.attachments)
a.detonator_act(event, src)
/obj/item/assembly/detonator/receive_signal(datum/signal/signal)
if (signal)
if (signal.source == src.part_fs)
src.attachedTo.visible_message("<B><font color=#FF0000>The failsafe timer's ticks more rapidly with every passing moment, then suddenly goes quiet.</font></B>")
src.detonate()
else
failsafe_engage()
/obj/item/proc/is_detonator_attachment()
return 0
// Possible events: attach, detach, leak, process, prime, detonate, cut, pulse
/obj/item/proc/detonator_act(event, var/obj/item/assembly/detonator/det)
return
//For testing and I'm too lazy to hand-assemble these whenever I need one =I
/obj/item/assembly/detonator/finished
New()
..()
var/obj/item/tank/plasma/ptank = new /obj/item/tank/plasma(src)
ptank.air_contents.toxins = 30
ptank.master = src
src.part_t = ptank
var/obj/item/device/timer/timer = new /obj/item/device/timer(src)
timer.master = src
src.part_fs = timer
src.part_fs.time = 90 //Minimum det time
setDetState(4)
+649
View File
@@ -0,0 +1,649 @@
/*
Contains:
- Assembly parent
- Timer/igniter
- Proximity/igniter
- Remote signaller/igniter
- Health analyzer/igniter
- Remote signaller/bike horn
- Remote signaller/timer
- Remote signaller/proximity
*/
//////////////////////////////////////// Assembly parent /////////////////////////////////
/obj/item/assembly
name = "assembly"
icon = 'icons/obj/assemblies.dmi'
inhand_image_icon = 'icons/mob/inhand/hand_tools.dmi'
item_state = "assembly"
var/status = 0.0
throwforce = 10
w_class = 3.0
throw_speed = 4
throw_range = 10
stamina_damage = 10
stamina_cost = 10
var/force_dud = 0
/obj/item/assembly/proc/c_state(n, O as obj)
return
/////////////////////////////////////// Timer/igniter /////////////////////////
/obj/item/assembly/time_ignite
name = "Timer/Igniter Assembly"
desc = "A timer-activated igniter assembly."
icon_state = "timer-igniter0"
var/obj/item/device/timer/part1 = null
var/obj/item/device/igniter/part2 = null
var/obj/item/reagent_containers/glass/beaker/part3 = null
status = null
flags = FPRINT | TABLEPASS| CONDUCT | NOSPLASH
/obj/item/assembly/time_ignite/New()
..()
spawn(0)
if(!part1)
part1 = new(src)
part1.master = src
if(!part2)
part2 = new(src)
part2.master = src
return
/obj/item/assembly/time_ignite/disposing()
qdel(part1)
part1 = null
qdel(part2)
part2 = null
qdel(part3)
part3 = null
..()
/obj/item/assembly/time_ignite/attack_self(mob/user as mob)
src.part1.attack_self(user, src.status)
src.add_fingerprint(user)
return
/obj/item/assembly/time_ignite/receive_signal()
for(var/mob/O in hearers(1, src.loc))
O.show_message("[bicon(src)] *beep* *beep*", 3, "*beep* *beep*", 2)
src.part2.ignite()
if(src.part3)
src.part3.reagents.temperature_reagents(4000, 400)
src.part3.reagents.temperature_reagents(4000, 400)
return
/obj/item/assembly/time_ignite/attackby(obj/item/W as obj, mob/user as mob)
if ((istype(W, /obj/item/wrench) && !( src.status )))
var/turf/T = src.loc
if (ismob(T))
T = T.loc
if (src.part1)
src.part1.set_loc(T)
src.part1.master = null
src.part1 = null
if (src.part2)
src.part2.set_loc(T)
src.part2.master = null
src.part2 = null
if (src.part3)
src.part3.set_loc(T)
src.part3.master = null
src.part3 = null
qdel(src)
return
if((istype(W, /obj/item/reagent_containers/glass/beaker) && !( src.status )))
if(!src.part3)
src.part3 = W
W.master = src
W.layer = initial(W.layer)
user.u_equip(W)
W.set_loc(src)
src.c_state(0)
boutput(user, "You attach the timer/igniter assembly to the beaker.")
else boutput(user, "You must remove the beaker from the assembly before transferring chemicals to it!")
return
if (!( istype(W, /obj/item/screwdriver) ))
return
src.status = !( src.status )
if (src.status)
user.show_message("<span style=\"color:blue\">The timer is now secured!</span>", 1)
else
user.show_message("<span style=\"color:blue\">The timer is now unsecured!</span>", 1)
src.part2.status = src.status
src.add_fingerprint(user)
return
/obj/item/assembly/time_ignite/c_state(n)
if(!src.part3)
src.icon = 'icons/obj/assemblies.dmi'
src.icon_state = text("timer-igniter[n]")
src.overlays = null
src.underlays = null
src.name = "Timer/Igniter Assembly"
else
src.icon = part3.icon
src.icon_state = part3.icon_state
src.overlays = null
src.underlays = null
src.overlays += image('icons/obj/assemblies.dmi', "timeignite_overlay[n]", layer = FLOAT_LAYER)
src.underlays += part3.underlays
src.name = "Timer/Igniter/Beaker Assembly"
return
/obj/item/assembly/time_ignite/verb/removebeaker()
set src in oview(1)
set name = "remove beaker"
set category = "Local"
if (usr.stat || !isliving(usr) || isintangible(usr))
return
if(src.part3)
src.part3.master = null
src.part3.attack_hand(usr)
src.part3 = null
src.c_state(src.part1.timing)
boutput(usr, "<span style=\"color:blue\">You remove the timer/igniter assembly from the beaker.</span>")
else boutput(usr, "<span style=\"color:red\">That doesn't have a beaker attached to it!</span>")
/////////////////////////////// Proximity/igniter /////////////////////////////////////
/obj/item/assembly/prox_ignite
name = "Proximity/Igniter Assembly"
desc = "A proximity-activated igniter assembly."
icon_state = "prox-igniter0"
var/obj/item/device/prox_sensor/part1 = null
var/obj/item/device/igniter/part2 = null
var/obj/item/reagent_containers/glass/beaker/part3 = null
status = null
flags = FPRINT | TABLEPASS| CONDUCT | NOSPLASH
/obj/item/assembly/prox_ignite/HasProximity(atom/movable/AM as mob|obj)
if (istype(AM, /obj/projectile))
return
if (AM.move_speed < 12 && src.part1)
src.part1.sense()
return
/obj/item/assembly/prox_ignite/dropped()
spawn( 0 )
if (src.part1)
src.part1.sense()
return
return
/obj/item/assembly/prox_ignite/New()
..()
spawn(0)
if(!part1)
part1 = new(src)
part1.master = src
if(!part2)
part2 = new(src)
part2.master = src
return
/obj/item/assembly/prox_ignite/disposing()
qdel(part1)
part1 = null
qdel(part2)
part2 = null
qdel(part3)
part3 = null
..()
/obj/item/assembly/prox_ignite/c_state(n)
if(!src.part3)
src.icon = 'icons/obj/assemblies.dmi'
src.icon_state = text("prox-igniter[n]")
src.overlays = null
src.underlays = null
src.name = "Proximity/Igniter Assembly"
else
src.icon = part3.icon
src.icon_state = part3.icon_state
src.overlays = null
src.underlays = null
src.overlays += image('icons/obj/assemblies.dmi', "proxignite_overlay[n]", layer = FLOAT_LAYER)
src.underlays += part3.underlays
src.name = "Proximity/Igniter/Beaker Assembly"
return
/obj/item/assembly/prox_ignite/attackby(obj/item/W as obj, mob/user as mob)
if ((istype(W, /obj/item/wrench) && !( src.status )))
var/turf/T = src.loc
if (ismob(T))
T = T.loc
if (part1)
src.part1.set_loc(T)
src.part1.master = null
src.part1 = null
if (part2)
src.part2.set_loc(T)
src.part2.master = null
src.part2 = null
if (part3)
src.part3.set_loc(T)
src.part3.master = null
src.part3 = null
//SN src = null
qdel(src)
return
if((istype(W, /obj/item/reagent_containers/glass/beaker) && !( src.status )))
if(!src.part3)
src.part3 = W
W.master = src
W.layer = initial(W.layer)
user.u_equip(W)
W.set_loc(src)
src.c_state(0)
boutput(user, "You attach the proximity/igniter assembly to the beaker.")
else boutput(user, "You must remove the beaker from the assembly before transferring chemicals to it!")
return
if (!( istype(W, /obj/item/screwdriver) ))
return
src.status = !( src.status )
if (src.status)
user.show_message("<span style=\"color:blue\">The proximity sensor is now secured! The igniter now works!</span>", 1)
else
user.show_message("<span style=\"color:blue\">The proximity sensor is now unsecured! The igniter will not work.</span>", 1)
src.part2.status = src.status
src.add_fingerprint(user)
return
/obj/item/assembly/prox_ignite/attack_self(mob/user as mob)
src.part1.attack_self(user, src.status)
src.add_fingerprint(user)
return
/obj/item/assembly/prox_ignite/receive_signal()
for(var/mob/O in hearers(1, src.loc))
O.show_message("[bicon(src)] *beep* *beep*", 3, "*beep* *beep*", 2)
src.part2.ignite()
if(src.part3)
src.part3.reagents.temperature_reagents(4000, 400)
src.part3.reagents.temperature_reagents(4000, 400)
return
/obj/item/assembly/prox_ignite/verb/removebeaker()
set src in oview(1)
set name = "remove beaker"
set category = "Local"
if (usr.stat || !isliving(usr) || isintangible(usr))
return
if(src.part3)
src.part3.master = null
src.part3.attack_hand(usr)
src.part3 = null
src.c_state(src.part1.timing)
boutput(usr, "<span style=\"color:blue\">You remove the timer/igniter assembly from the beaker.</span>")
else boutput(usr, "<span style=\"color:red\">That doesn't have a beaker attached to it!</span>")
/////////////////////////////////////// Remote signaller/igniter //////////////////////////////////////
/obj/item/assembly/rad_ignite
name = "Radio/Igniter Assembly"
desc = "A radio-activated igniter assembly."
icon_state = "radio-igniter"
var/obj/item/device/radio/signaler/part1 = null
var/obj/item/device/igniter/part2 = null
var/obj/item/reagent_containers/glass/beaker/part3 = null
status = null
flags = FPRINT | TABLEPASS| CONDUCT | NOSPLASH
/obj/item/assembly/rad_ignite/New()
..()
spawn(0)
if(!part1)
part1 = new(src)
part1.master = src
if(!part2)
part2 = new(src)
part2.master = src
/obj/item/assembly/rad_ignite/disposing()
qdel(part1)
part1 = null
qdel(part2)
part2 = null
qdel(part3)
part3 = null
..()
/obj/item/assembly/rad_ignite/attackby(obj/item/W as obj, mob/user as mob)
if ((istype(W, /obj/item/wrench) && !( src.status )))
var/turf/T = src.loc
if (ismob(T))
T = T.loc
src.part1.set_loc(T)
src.part2.set_loc(T)
src.part3.set_loc(T)
src.part1.master = null
src.part2.master = null
src.part3.master = null
src.part1 = null
src.part2 = null
src.part3 = null
//SN src = null
qdel(src)
return
if((istype(W, /obj/item/reagent_containers/glass/beaker) && !( src.status )))
if(!src.part3)
src.part3 = W
W.master = src
W.layer = initial(W.layer)
user.u_equip(W)
W.set_loc(src)
src.c_state()
boutput(user, "You attach the radio/igniter assembly to the beaker.")
else boutput(user, "You must remove the beaker from the assembly before transferring chemicals to it!")
return
if (!( istype(W, /obj/item/screwdriver) ))
return
src.status = !( src.status )
if (src.status)
user.show_message("<span style=\"color:blue\">The radio is now secured! The igniter now works!</span>", 1)
else
user.show_message("<span style=\"color:blue\">The radio is now unsecured! The igniter will not work.</span>", 1)
src.part2.status = src.status
src.part1.b_stat = !( src.status )
src.add_fingerprint(user)
return
/obj/item/assembly/rad_ignite/attack_self(mob/user as mob)
src.part1.attack_self(user, src.status)
src.add_fingerprint(user)
return
/obj/item/assembly/rad_ignite/receive_signal()
for(var/mob/O in hearers(1, src.loc))
O.show_message("[bicon(src)] *beep* *beep*", 3, "*beep* *beep*", 2)
src.part2.ignite()
if(src.part3)
src.part3.reagents.temperature_reagents(4000, 400)
src.part3.reagents.temperature_reagents(4000, 400)
return
/obj/item/assembly/rad_ignite/verb/removebeaker()
set src in oview(1)
set name = "remove beaker"
set category = "Local"
if (usr.stat || !isliving(usr) || isintangible(usr))
return
if(src.part3)
src.part3.master = null
src.part3.attack_hand(usr)
src.part3 = null
src.c_state()
boutput(usr, "<span style=\"color:blue\">You remove the timer/igniter assembly from the beaker.</span>")
else boutput(usr, "<span style=\"color:red\">That doesn't have a beaker attached to it!</span>")
/obj/item/assembly/rad_ignite/c_state()
if(!src.part3)
src.icon = 'icons/obj/assemblies.dmi'
src.icon_state = text("radio-igniter")
src.overlays = null
src.underlays = null
src.name = "Radio/Igniter Assembly"
else
src.icon = part3.icon
src.icon_state = part3.icon_state
src.overlays = null
src.underlays = null
src.overlays += image('icons/obj/assemblies.dmi', "radignite_overlay", layer = FLOAT_LAYER)
src.underlays += part3.underlays
src.name = "Radio/Igniter/Beaker Assembly"
return
///////////////////////////////// Health analyzer/igniter /////////////////////////////////////////////
/obj/item/assembly/anal_ignite //lol
name = "Health-Analyzer/Igniter Assembly"
desc = "A health-analyzer igniter assembly."
icon_state = "timer-igniter0"
var/obj/item/device/healthanalyzer/part1 = null
var/obj/item/device/igniter/part2 = null
status = null
flags = FPRINT | TABLEPASS| CONDUCT
item_state = "electronic"
/obj/item/assembly/anal_ignite/New()
..()
spawn (5)
if (src && !src.part1)
src.part1 = new /obj/item/device/healthanalyzer(src)
src.part1.master = src
if (src && !src.part2)
src.part2 = new /obj/item/device/igniter(src)
src.part2.master = src
return
/obj/item/assembly/anal_ignite/attackby(obj/item/W as obj, mob/user as mob)
if ((istype(W, /obj/item/wrench) && !( src.status )))
var/turf/T = src.loc
if (ismob(T))
T = T.loc
src.part1.set_loc(T)
src.part2.set_loc(T)
src.part1.master = null
src.part2.master = null
src.part1 = null
src.part2 = null
qdel(src)
return
if (( istype(W, /obj/item/screwdriver) ))
src.status = !( src.status )
if (src.status)
user.show_message("<span style=\"color:blue\">The analyzer is now secured!</span>", 1)
else
user.show_message("<span style=\"color:blue\">The analyzer is now unsecured!</span>", 1)
src.part2.status = src.status
src.add_fingerprint(user)
return
///////////////////////////////////////////////////// Remote signaller/bike horn /////////////////////
/obj/item/assembly/radio_horn
desc = "A bike horn hastily jammed into a signaller."
name = "Radio/Horn Assembly"
icon_state = "radio-horn"
var/obj/item/device/radio/signaler/part1 = null
var/obj/item/bikehorn/part2 = null
status = 0.0
flags = FPRINT | TABLEPASS| CONDUCT
/obj/item/assembly/radio_horn/New()
..()
spawn(0)
if(!part1)
part1 = new(src)
part1.master = src
if(!part2)
part2 = new(src)
part2.master = src
return
/obj/item/assembly/radio_horn/disposing()
qdel(part1)
part1 = null
qdel(part2)
part2 = null
..()
return
obj/item/assembly/radio_horn/attack_self(mob/user as mob)
src.part1.attack_self(user)
src.add_fingerprint(user)
return
obj/item/assembly/radio_horn/receive_signal()
if (part2.spam_flag == 0)
part2.spam_flag = 1
playsound(src.loc, part2.sound_horn, part2.volume, part2.randomized_pitch)
spawn(part2.spam_timer)
part2.spam_flag = 0
return
/////////////////////////////////////////////////////// Remote signaller/timer /////////////////////////////////////
/obj/item/assembly/rad_time
name = "Signaller/Timer Assembly"
desc = "A radio signaller activated by a count-down timer."
icon_state = "timer-radio0"
var/obj/item/device/radio/signaler/part1 = null
var/obj/item/device/timer/part2 = null
status = null
flags = FPRINT | TABLEPASS| CONDUCT
/obj/item/assembly/rad_time/disposing()
qdel(part1)
part1 = null
qdel(part2)
part2 = null
..()
return
/obj/item/assembly/rad_time/attackby(obj/item/W as obj, mob/user as mob)
if ((istype(W, /obj/item/wrench) && !( src.status )))
var/turf/T = src.loc
if (ismob(T))
T = T.loc
src.part1.set_loc(T)
src.part2.set_loc(T)
src.part1.master = null
src.part2.master = null
src.part1 = null
src.part2 = null
//SN src = null
qdel(src)
return
if (!( istype(W, /obj/item/screwdriver) ))
return
src.status = !( src.status )
if (src.status)
user.show_message("<span style=\"color:blue\">The signaler is now secured!</span>", 1)
else
user.show_message("<span style=\"color:blue\">The signaler is now unsecured!</span>", 1)
src.part1.b_stat = !( src.status )
src.add_fingerprint(user)
return
/obj/item/assembly/rad_time/attack_self(mob/user as mob)
src.part1.attack_self(user, src.status)
src.part2.attack_self(user, src.status)
src.add_fingerprint(user)
return
/obj/item/assembly/rad_time/receive_signal(datum/signal/signal)
// drsingh for cannot read null.source
if (signal && signal.source == src.part2)
src.part1.send_signal("ACTIVATE")
return
////////////////////////////////////////////// Remote signaller/proximity //////////////////////////////////
/obj/item/assembly/rad_prox
name = "Signaller/Prox Sensor Assembly"
desc = "A proximity-activated radio signaller."
icon_state = "prox-radio0"
var/obj/item/device/radio/signaler/part1 = null
var/obj/item/device/prox_sensor/part2 = null
status = null
flags = FPRINT | TABLEPASS| CONDUCT
/obj/item/assembly/rad_prox/c_state(n)
src.icon_state = "prox-radio[n]"
return
/obj/item/assembly/rad_prox/disposing()
qdel(part1)
part1 = null
qdel(part2)
part2 = null
..()
return
/obj/item/assembly/rad_prox/HasProximity(atom/movable/AM as mob|obj)
if (istype(AM, /obj/projectile))
return
if (AM.move_speed < 12 && src && src.part2)
src.part2.sense()
return
/obj/item/assembly/rad_prox/attackby(obj/item/W as obj, mob/user as mob)
if ((istype(W, /obj/item/wrench) && !( src.status )))
var/turf/T = src.loc
if (ismob(T))
T = T.loc
src.part1.set_loc(T)
src.part2.set_loc(T)
src.part1.master = null
src.part2.master = null
src.part1 = null
src.part2 = null
//SN src = null
qdel(src)
return
if (!( istype(W, /obj/item/screwdriver) ))
return
src.status = !( src.status )
if (src.status)
user.show_message("<span style=\"color:blue\">The proximity sensor is now secured!</span>", 1)
else
user.show_message("<span style=\"color:blue\">The proximity sensor is now unsecured!</span>", 1)
src.part1.b_stat = !( src.status )
src.add_fingerprint(user)
return
/obj/item/assembly/rad_prox/attack_self(mob/user as mob)
src.part1.attack_self(user, src.status)
src.part2.attack_self(user, src.status)
src.add_fingerprint(user)
return
/obj/item/assembly/rad_prox/receive_signal(datum/signal/signal)
// drsingh for Cannot read null.source
if (signal && signal.source == src.part2)
src.part1.send_signal("ACTIVATE")
return
/obj/item/assembly/rad_prox/Move()
..()
src.part2.sense()
return
/obj/item/assembly/rad_prox/dropped()
spawn( 0 )
src.part2.sense()
return
return
+61
View File
@@ -0,0 +1,61 @@
/obj/item/assembly/shock_kit
name = "Shock Kit"
icon_state = "shock_kit"
var/obj/item/clothing/head/helmet/part1 = null
var/obj/item/device/radio/electropack/part2 = null
status = 0.0
w_class = 5.0
flags = FPRINT | TABLEPASS| CONDUCT
/obj/item/assembly/shock_kit/New()
spawn (20)
if (src)
if (!(src.part1 && istype(src.part1)))
src.part1 = new /obj/item/clothing/head/helmet(src)
src.part1.master = src
if (!(src.part2 && istype(src.part2)))
src.part2 = new /obj/item/device/radio/electropack(src)
src.part2.master = src
return
/obj/item/assembly/shock_kit/disposing()
if (src.part1)
qdel(src.part1)
src.part1 = null
if (src.part2)
qdel(src.part2)
src.part2 = null
..()
return
/obj/item/assembly/shock_kit/attackby(obj/item/W as obj, mob/user as mob)
src.add_fingerprint(user)
if (istype(W, /obj/item/wrench))
var/turf/T = get_turf(src)
if (src.part1)
src.part1.set_loc(T)
src.part1.master = null
src.part1 = null
if (src.part2)
src.part2.set_loc(T)
src.part2.master = null
src.part2 = null
qdel(src)
return
else return ..()
/obj/item/assembly/shock_kit/attack_self(mob/user as mob)
src.part1.attack_self(user, src.status)
src.part2.attack_self(user, src.status)
src.add_fingerprint(user)
return
/obj/item/assembly/shock_kit/receive_signal()
if (src.master && istype(src.master, /obj/stool/chair/e_chair))
var/obj/stool/chair/e_chair/C = src.master
if (C.buckled_guy)
logTheThing("signalers", usr, C.buckled_guy, "signalled an electric chair (setting: [C.lethal ? "lethal" : "non-lethal"]), shocking %target% at [log_loc(C)].") // Added (Convair880).
C.shock()
return
+346
View File
@@ -0,0 +1,346 @@
/* Contains:
- Single tank bomb logs
- Single tank bomb (proximity)
- Single tank bomb (timer)
- Single tank bomb (remote signaller)
*/
// Just a little helper. These three bombs are very similar (Convair880).
/obj/item/assembly/proc/bomb_logs(var/mob/user, var/obj/item/bomb, var/type = "", var/welded_or_unwelded = 0, var/is_dud = 0)
if (!bomb || !type)
return
if (is_dud == 1)
message_admins("A [type] single tank bomb would have opened at [log_loc(bomb)] but was forced to dud! Last touched by: [bomb.fingerprintslast ? "[bomb.fingerprintslast]" : "*null*"]")
logTheThing("bombing", null, null, "A [type] single tank bomb would have opened at [log_loc(bomb)] but was forced to dud! Last touched by: [bomb.fingerprintslast ? "[bomb.fingerprintslast]" : "*null*"]")
return
var/obj/item/tank/T = null
if (istype(bomb, /obj/item/assembly/proximity_bomb/))
var/obj/item/assembly/proximity_bomb/PB = bomb
if (PB.part3)
T = PB.part3
if (istype(bomb, /obj/item/assembly/time_bomb/))
var/obj/item/assembly/time_bomb/TB = bomb
if (TB.part3)
T = TB.part3
if (istype(bomb, /obj/item/assembly/radio_bomb/))
var/obj/item/assembly/radio_bomb/RB = bomb
if (RB.part3)
T = RB.part3
if (!T || !istype(T, /obj/item/tank))
return
logTheThing("bombing", user, null, "[welded_or_unwelded == 0 ? "welded" : "unwelded"] a [type] single tank bomb [log_atmos(T)] at [log_loc(user)].")
if (welded_or_unwelded == 0)
message_admins("[key_name(user)] welded a [type] single tank bomb at [log_loc(user)]. See bombing logs or bomb monitor for complete atmos readout.")
return
/////////////////////////////////////////////////// Single tank bomb (proximity) ////////////////////////////////////
/obj/item/assembly/proximity_bomb
desc = "A very intricate igniter and proximity sensor electrical assembly mounted onto top of a plasma tank."
name = "Proximity/Igniter/Plasma Tank Assembly"
icon_state = "prox-igniter-tank0"
var/obj/item/device/prox_sensor/part1 = null
var/obj/item/device/igniter/part2 = null
var/obj/item/tank/plasma/part3 = null
status = 0.0
flags = FPRINT | TABLEPASS| CONDUCT
/obj/item/assembly/proximity_bomb/dropped()
spawn( 0 )
src.part1.sense()
return
return
/obj/item/assembly/proximity_bomb/examine()
..()
src.part3.examine()
/obj/item/assembly/proximity_bomb/disposing()
qdel(part1)
part1 = null
qdel(part2)
part2 = null
qdel(part3)
part3 = null
..()
return
/obj/item/assembly/proximity_bomb/attackby(obj/item/W as obj, mob/user as mob)
if ((istype(W, /obj/item/wrench) && !( src.status )))
var/obj/item/assembly/prox_ignite/R = new /obj/item/assembly/prox_ignite( )
R.part1 = src.part1
R.part2 = src.part2
user.put_in_hand_or_drop(R)
src.part1.set_loc(R)
src.part2.set_loc(R)
src.part1.master = R
src.part2.master = R
var/turf/T = src.loc
if (!( istype(T, /turf) ))
T = T.loc
if (!( istype(T, /turf) ))
T = T.loc
src.part3.set_loc(T)
src.part1 = null
src.part2 = null
src.part3 = null
//SN src = null
qdel(src)
return
if (!( istype(W, /obj/item/weldingtool) ))
return
if (!( src.status ))
src.status = 1
user.show_message("<span style=\"color:blue\">A pressure hole has been bored to the plasma tank valve. The plasma tank can now be ignited.</span>", 1)
else
src.status = 0
boutput(user, "<span style=\"color:blue\">The hole has been closed.</span>")
src.bomb_logs(user, src, "proximity", src.status == 1 ? 0 : 1, 0)
src.part2.status = src.status
src.add_fingerprint(user)
return
/obj/item/assembly/proximity_bomb/attack_self(mob/user as mob)
playsound(src.loc, "sound/weapons/armbomb.ogg", 100, 1)
src.part1.attack_self(user, 1)
src.add_fingerprint(user)
return
/obj/item/assembly/proximity_bomb/receive_signal()
//boutput(world, "miptank [src] got signal")
for(var/mob/O in hearers(1, null))
O.show_message("[bicon(src)] *beep* *beep*", 3, "*beep* *beep*", 2)
//Foreach goto(19)
if (src.status)
src.part1.armed = 0
src.c_state(0)
if (src.force_dud == 1)
src.bomb_logs(usr, src, "proximity", 0, 1)
return
src.part3.ignite()
else
if (!src.status && src.force_dud == 0)
src.part1.armed = 0
src.c_state(0)
src.part3.release()
return
/obj/item/assembly/proximity_bomb/c_state(n)
src.icon_state = text("prox-igniter-tank[]", n)
return
/obj/item/assembly/proximity_bomb/HasProximity(atom/movable/AM as mob|obj)
if (istype(AM, /obj/projectile))
return
if (AM.move_speed < 12 && src.part1)
src.part1.sense()
return
/obj/item/assembly/proximity_bomb/Bump(atom/O)
spawn(0)
//boutput(world, "miptank bumped into [O]")
if(src.part1.armed)
//boutput(world, "sending signal")
receive_signal()
else
//boutput(world, "not active")
..()
/obj/item/assembly/proximity_bomb/proc/prox_check()
if(!part1 || !part1.armed)
return
for(var/atom/A in view(1, src.loc))
if(A!=src && !istype(A, /turf/space) && !isarea(A))
//boutput(world, "[A]:[A.type] was sensed")
src.part1.sense()
break
spawn(10)
prox_check()
/////////////////////////////////////////////////// Single tank bomb (timer) ////////////////////////////////////
/obj/item/assembly/time_bomb
desc = "A very intricate igniter and timer assembly mounted onto top of a plasma tank."
name = "Timer/Igniter/Plasma Tank Assembly"
icon_state = "timer-igniter-tank0"
var/obj/item/device/timer/part1 = null
var/obj/item/device/igniter/part2 = null
var/obj/item/tank/plasma/part3 = null
status = 0.0
flags = FPRINT | TABLEPASS| CONDUCT
/obj/item/assembly/time_bomb/c_state(n)
src.icon_state = text("timer-igniter-tank[]", n)
return
/obj/item/assembly/time_bomb/examine()
..()
src.part3.examine()
/obj/item/assembly/time_bomb/disposing()
qdel(part1)
part1 = null
qdel(part2)
part2 = null
qdel(part3)
part3 = null
..()
return
/obj/item/assembly/time_bomb/attackby(obj/item/W as obj, mob/user as mob)
if ((istype(W, /obj/item/wrench) && !( src.status )))
var/obj/item/assembly/time_ignite/R = new /obj/item/assembly/time_ignite( )
R.part1 = src.part1
R.part2 = src.part2
user.put_in_hand_or_drop(R)
src.part1.set_loc(R)
src.part2.set_loc(R)
src.part1.master = R
src.part2.master = R
var/turf/T = src.loc
if (!( istype(T, /turf) ))
T = T.loc
if (!( istype(T, /turf) ))
T = T.loc
src.part3.set_loc(T)
src.part1 = null
src.part2 = null
src.part3 = null
//SN src = null
qdel(src)
return
if (!( istype(W, /obj/item/weldingtool) ))
return
if (!( src.status ))
src.status = 1
user.show_message("<span style=\"color:blue\">A pressure hole has been bored to the plasma tank valve. The plasma tank can now be ignited.</span>", 1)
else
src.status = 0
boutput(user, "<span style=\"color:blue\">The hole has been closed.</span>")
src.part2.status = src.status
src.bomb_logs(user, src, "timer", src.status == 1 ? 0 : 1, 0)
src.add_fingerprint(user)
return
/obj/item/assembly/time_bomb/attack_self(mob/user as mob)
if (src.part1)
src.part1.attack_self(user, 1)
playsound(src.loc, "sound/weapons/armbomb.ogg", 100, 1)
src.add_fingerprint(user)
return
/obj/item/assembly/time_bomb/receive_signal()
//boutput(world, "tiptank [src] got signal")
for(var/mob/O in hearers(1, null))
O.show_message("[bicon(src)] *beep* *beep*", 3, "*beep* *beep*", 2)
if (src.status)
if (src.force_dud == 1)
src.bomb_logs(usr, src, "timer", 0, 1)
return
src.part3.ignite()
else
if (!src.status && src.force_dud == 0)
src.part3.release()
return
/////////////////////////////////////////////////// Single tank bomb (remote signaller) ////////////////////////////////////
/obj/item/assembly/radio_bomb
desc = "A very intricate igniter and signaller electrical assembly mounted onto top of a plasma tank."
name = "Radio/Igniter/Plasma Tank Assembly"
icon_state = "radio-igniter-tank"
var/obj/item/device/radio/signaler/part1 = null
var/obj/item/device/igniter/part2 = null
var/obj/item/tank/plasma/part3 = null
status = 0.0
flags = FPRINT | TABLEPASS| CONDUCT
/obj/item/assembly/radio_bomb/examine()
..()
src.part3.examine()
/obj/item/assembly/radio_bomb/Del()
//src.part1 = null
qdel(src.part1)
//src.part2 = null
qdel(src.part2)
//src.part3 = null
qdel(src.part3)
..()
return
/obj/item/assembly/radio_bomb/attackby(obj/item/W as obj, mob/user as mob)
if ((istype(W, /obj/item/wrench) && !( src.status )))
var/obj/item/assembly/rad_ignite/R = new /obj/item/assembly/rad_ignite( )
R.part1 = src.part1
R.part2 = src.part2
user.put_in_hand_or_drop(R)
src.part1.set_loc(R)
src.part2.set_loc(R)
src.part1.master = R
src.part2.master = R
var/turf/T = src.loc
if (!( istype(T, /turf) ))
T = T.loc
if (!( istype(T, /turf) ))
T = T.loc
src.part3.set_loc(T)
src.part1 = null
src.part2 = null
src.part3 = null
//SN src = null
qdel(src)
return
if (!( istype(W, /obj/item/weldingtool) ))
return
if (!( src.status ))
src.status = 1
user.show_message("<span style=\"color:blue\">A pressure hole has been bored to the plasma tank valve. The plasma tank can now be ignited.</span>", 1)
else
src.status = 0
boutput(user, "<span style=\"color:blue\">The hole has been closed.</span>")
src.bomb_logs(user, src, "radio", src.status == 1 ? 0 : 1, 0)
src.part2.status = src.status
src.part1.b_stat = !( src.status )
src.add_fingerprint(user)
return
/obj/item/assembly/radio_bomb/attack_self(mob/user as mob)
if (src.part1)
playsound(src.loc, "sound/weapons/armbomb.ogg", 100, 1)
src.part1.attack_self(user, 1)
src.add_fingerprint(user)
return
/obj/item/assembly/radio_bomb/receive_signal()
//boutput(world, "riptank [src] got signal")
for(var/mob/O in hearers(1, null))
O.show_message("[bicon(src)] *beep* *beep*", 3, "*beep* *beep*", 2)
if (src.status)
if (src.force_dud == 1)
src.bomb_logs(usr, src, "radio", 0, 1)
return
src.part3.ignite()
else
if (!src.status && src.force_dud == 0)
src.part3.release()
return
+319
View File
@@ -0,0 +1,319 @@
//BASKETBALL
/obj/item/basketball
name = "basketball"
desc = "If you can't slam with the best, then jam with the rest."
icon = 'icons/obj/items.dmi'
icon_state = "bball"
item_state = "bball"
w_class = 3.0
force = 0
throw_range = 10
throwforce = 0
var/obj/item/plutonium_core/payload = null
stamina_damage = 5
stamina_cost = 5
stamina_crit_chance = 5
/obj/item/basketball/attack_hand(mob/user as mob)
..()
if(user)
src.icon_state = "bball"
/obj/item/basketball/throw_impact(atom/hit_atom)
..(hit_atom)
src.icon_state = "bball"
if(hit_atom)
playsound(src.loc, "sound/items/bball_bounce.ogg", 65, 1)
if(ismob(hit_atom))
var/mob/M = hit_atom
if(ishuman(M))
if((prob(50) && M.bioHolder.HasEffect("clumsy")) || M.equipped() || get_dir(M, src) == M.dir)
src.visible_message("<span class='combat'>[M] gets beaned with the [src.name].</span>")
M.stunned = max(2, M.stunned)
return
// catch the ball!
src.attack_hand(M)
M.visible_message("<span class='combat'>[M] catches the [src.name]!</span>", "<span class='combat'>You catch the [src.name]!</span>")
logTheThing("combat", M, null, "catches [src]")
return
src.visible_message("<span class='combat'>[M] gets beaned with the [src.name].</span>")
logTheThing("combat", M, null, "is struck by [src]")
M.stunned = max(2, M.stunned)
return
/obj/item/basketball/throw_at(atom/target, range, speed)
src.icon_state = "bball_spin"
..(target, range, speed)
/obj/item/basketball/attackby(obj/item/W as obj, mob/user as mob)
if(istype(W, /obj/item/plutonium_core))
boutput(user, "<span style=\"color:blue\">You insert the [W.name] into the [src.name].</span>")
user.u_equip(W)
W.dropped(user)
W.layer = initial(W.layer)
W.set_loc(src)
src.payload = W
if(src.loc == user)
user.verbs += /proc/chaos_dunk
return
..(W, user)
return
/obj/item/basketball/attack_hand(mob/user as mob)
..()
var/mob/living/carbon/human/H = user
if(istype(H) && payload && istype(payload))
H.verbs += /proc/chaos_dunk
return
/obj/item/basketball/unequipped(var/mob/user)
if(payload && istype(payload))
user.verbs -= /proc/chaos_dunk
..()
// hoop
/obj/item/bballbasket
name = "basketball hoop" // it's a hoop you nerd, not a basket
desc = "Can be mounted on walls."
opacity = 0
density = 0
anchored = 0
icon = 'icons/obj/stationobjs.dmi'
icon_state = "bbasket0"
var/mounted = 0
var/active = 0
var/probability = 40
attackby(obj/item/W as obj, mob/user as mob)
if (istype(W,/obj/item/wrench) && mounted)
src.visible_message("<span style=\"color:blue\"><b>[user] removes [src].</b></span>")
src.pixel_y = 0
src.pixel_x = 0
src.anchored = 0
src.mounted = 0
else if (src.mounted && !istype(W, /obj/item/bballbasket))
if (W.cant_drop) return
src.visible_message("<span style=\"color:blue\"><b>[user]</b> jumps up and tries to dunk [W] into [src]!</span>")
user.u_equip(W)
if (user.bioHolder.HasEffect("clumsy") && prob(50)) // clowns are not good at basketball I guess
user.visible_message("<span class='combat'><b>[user] knocks their head into the rim of [src]!</b></span>")
user.weakened = max(5, user.weakened)
if (!src.shoot(W, user))
spawn(10)
src.visible_message("<span style=\"color:red\">[user] whiffs the dunk.</span>")
return
attack_hand(mob/user as mob)
if (mounted)
return
else
return ..(user)
afterattack(atom/target as mob|obj|turf|area, mob/user as mob)
if (!mounted && get_dist(src, target) == 1)
if (isturf(target) && target.density)
//if (get_dir(src,target) == NORTH || get_dir(src,target) == EAST || get_dir(src,target) == SOUTH || get_dir(src,target) == WEST)
if (get_dir(src,target) in cardinal)
src.visible_message("<span style=\"color:blue\"><b>[user] mounts [src] on [target].</b></span>")
user.drop_item()
src.loc = get_turf(user)
src.mounted = 1
src.anchored = 1
src.dir = get_dir(src, target)
switch (src.dir)
if (NORTH)
src.pixel_y = 20
if (SOUTH)
src.pixel_y = -20
if (EAST)
src.pixel_x = 20
if (WEST)
src.pixel_x = -20
return
HasEntered(atom/A)
if (src.active)
return
if (istype(A, /obj/item/bballbasket)) // oh for FUCK'S SAKE
return // NO
if (istype(A, /obj/item))
src.shoot(A)
proc/shoot(var/obj/O as obj, var/mob/user as mob)
if (!O)
return 0
if (istype(O, /obj/item/bballbasket))
return
src.active = 1
if (user)
user.u_equip(O)
O.set_loc(get_turf(src))
if (prob(src.probability)) // It might land!
if (prob(30)) // It landed cleanly!
src.visible_message("<span style=\"color:blue\">[O] lands cleanly in [src]!</span>")
src.basket(O)
else // Aaaa the tension!
src.visible_message("<span style=\"color:red\">[O] teeters on the edge of [src]!</span>")
var/delay = rand(5, 15)
animate_horizontal_wiggle(O, delay, 5, 1, -1) // target, number of animation loops, speed, positive x variation, negative x variation
spawn(delay)
if (O && O.loc == src.loc)
if (prob(40)) // It goes in!
src.visible_message("<span style=\"color:blue\">[O] slips into [src]!</span>")
src.basket(O)
else
src.visible_message("<span style=\"color:red\">[O] slips off of the edge of [src]!</span>")
src.active = 0
else
src.active = 0
src.active = 0
return 1
else
src.active = 0
return 0
proc/basket(var/atom/A as obj|mob)
if (!A || isarea(A) || isturf(A))
return
src.active = 1
playsound(get_turf(src), "rustle", 75, 1)
A.invisibility = 100
flick("bbasket1", src)
spawn(15)
A.invisibility = 0
src.active = 0
/obj/item/bballbasket/testing
probability = 100
//PLUTONIUM CORE
/obj/item/plutonium_core
name = "plutonium core"
desc = "A payload from a nuclear warhead. Comprised of weapons-grade plutonium."
icon = 'icons/obj/items.dmi'
icon_state = "plutonium"
item_state = "egg3"
w_class = 3.0
force = 0
throwforce = 10
/obj/item/plutonium_core/attack_hand(mob/user as mob)
..()
if(ishuman(user))
var/mob/living/carbon/human/H = user
if(!H.gloves)
boutput(H, "<span class='combat'>Your hand burns from grabbing the [src.name].</span>")
var/obj/item/affecting = H.organs["r_arm"]
if(H.hand)
affecting = H.organs["l_arm"]
if(affecting)
affecting.take_damage(0, 15)
H.UpdateDamageIcon()
H.updatehealth()
//BLOOD BOWL BALL
/obj/item/bloodbowlball
name = "spiked ball"
desc = "An american football studded with sharp spikes and serrated blades. Looks dangerous."
icon = 'icons/obj/items.dmi'
icon_state = "bloodbowlball"
item_state = "bloodbowlball"
w_class = 3.0
force = 10
throw_range = 10
throwforce = 2
/obj/item/bloodbowlball/attack_hand(mob/user as mob)
..()
if(user)
src.icon_state = "bloodbowlball"
/obj/item/bloodbowlball/throw_impact(atom/hit_atom)
..(hit_atom)
src.icon_state = "bloodbowlball"
if(hit_atom)
playsound(src.loc, "sound/items/bball_bounce.ogg", 65, 1)
if(ismob(hit_atom))
var/mob/M = hit_atom
if(ishuman(M))
var/mob/living/carbon/T = M
if(prob(20) || T.equipped() || get_dir(T, src) == T.dir)
for(var/mob/V in AIviewers(src, null))
if(V.client)
V.show_message("<span class='combat'>[T] gets stabbed by one of the [src.name]'s spikes.</span>", 1)
playsound(src.loc, "sound/effects/bloody_stabOLD.ogg", 65, 1)
T.stunned = max(5, T.stunned)
T.TakeDamage("chest", 30, 0)
take_bleeding_damage(T, null, 15, DAMAGE_STAB)
return
else if (prob(50))
src.visible_message("<span class='combat'>[T] catches the [src.name] but gets cut.</span>")
T.TakeDamage(T.hand == 1 ? "l_arm" : "r_arm", 15, 0)
take_bleeding_damage(T, null, 10, DAMAGE_CUT)
src.attack_hand(T)
return
// catch the ball!
else
src.attack_hand(T)
T.visible_message("<span class='combat'>[M] catches the [src.name]!</span>")
return
return
/obj/item/bloodbowlball/throw_at(atom/target, range, speed)
src.icon_state = "bloodbowlball_air"
..(target, range, speed)
/obj/item/bloodbowlball/attack(target as mob, mob/user as mob)
playsound(target, "sound/effects/bloody_stab.ogg", 60, 1)
if(iscarbon(target))
if(target:stat != 2)
var/mob/living/carbon/targMob = target
targMob.visible_message("<span class='combat'><B>[user] attacks [target] with the [src]!</B></span>")
take_bleeding_damage(target, user, 5, DAMAGE_STAB)
if(prob(30))
if(prob(30))
boutput(user, "<span class='combat'>You accidentally cut your hand badly!</span>")
user.TakeDamage(user.hand == 1 ? "l_arm" : "r_arm", 10, 0)
take_bleeding_damage(user, user, 5, DAMAGE_CUT)
else
boutput(user, "<span class='combat'>You accidentally cut your hand!</span>")
user.TakeDamage(user.hand == 1 ? "l_arm" : "r_arm", 5, 0)
take_bleeding_damage(user, null, 1, DAMAGE_CUT, 0)
// MADDEN NFL FOOTBALL 2051
/obj/item/football
name = "football"
desc = "A pigskin. An oblate leather spheroid. For tossing around."
icon = 'icons/obj/items.dmi'
icon_state = "football"
item_state = "football"
w_class = 3.0
force = 0
throw_range = 10
throwforce = 0
/obj/item/football/throw_at(atom/target, range, speed)
src.icon_state = "football_air"
..(target, range, speed)
/obj/item/football/throw_impact(atom/hit_atom)
..(hit_atom)
src.icon_state = "football"
if(hit_atom)
playsound(src.loc, "sound/items/bball_bounce.ogg", 65, 1)
/obj/item/football/suicide(var/mob/user as mob)
user.visible_message("<span style=\"color:red\"><b>[user] spikes the [src.name]. It bounces back up and hits \him square in the forehead!</b></span>")
user.TakeDamage("head", 150, 0)
playsound(src.loc, "sound/items/bball_bounce.ogg", 50, 1)
user.updatehealth()
spawn(100)
if (user)
user.suiciding = 0
return 1
File diff suppressed because it is too large Load Diff
+69
View File
@@ -0,0 +1,69 @@
/obj/item/clothing/under/gimmick/bowling
name = "bowling suit"
desc = "Who's up for some bowling?"
icon = 'icons/obj/clothing/uniforms/item_js_athletic.dmi'
wear_image_icon = 'icons/mob/jumpsuits/worn_js_athletic.dmi'
inhand_image_icon = 'icons/mob/inhand/jumpsuit/hand_js_athletic.dmi'
icon_state = "bowling"
item_state = "bowling"
/obj/item/bowling_ball
name = "bowling ball"
desc = "Just keep rollin' rollin'."
icon = 'icons/obj/items.dmi'
icon_state = "bowling_ball"
w_class = 3.0
force = 5
throw_speed = 1
proc/hitWeak(var/mob/hitMob, var/mob/user)
hitMob.visible_message("<span style=\"color:red\">[hitMob] is hit by [user]'s [src]!</span>")
src.damage(hitMob, 5, 10, user)
proc/hitHard(var/mob/hitMob, var/mob/user)
hitMob.visible_message("<span style=\"color:red\">[hitMob] is knocked over by [user]'s [src]!</span>")
src.damage(hitMob, 10, 15, user)
proc/damage(var/mob/hitMob, damMin, damMax, var/mob/living/carbon/human/user)
if(user.w_uniform && istype(user.w_uniform, /obj/item/clothing/under/gimmick/bowling))
hitMob.weakened = max(damMax-10, hitMob.weakened) // Reduced to 10 sec. Don't stun them for 30 sec from a single hit, Christ.
hitMob.stuttering = max(damMax-5, hitMob.stuttering)
hitMob.stunned = max(damMax-10, hitMob.stunned)
hitMob.TakeDamage("chest", rand(damMin, damMax), 0)
else
hitMob.stuttering = max(damMax-5, hitMob.stuttering)
hitMob.TakeDamage("chest", rand(damMin, damMax), 0)
throw_at(atom/target, range, speed)
throw_unlimited = 1
src.icon_state = "bowling_ball_spin"
..(target, range, speed)
attack_hand(mob/user as mob)
..()
if(user)
src.icon_state = "bowling_ball"
throw_impact(atom/hit_atom)
var/mob/living/carbon/human/user = usr
src.icon_state = "bowling_ball"
if(hit_atom)
playsound(src.loc, "sound/effects/exlow.ogg", 65, 1)
if (ismob(hit_atom))
var/mob/hitMob = hit_atom
if (ishuman(hitMob))
spawn( 0 )
if (istype(user))
if (user.w_uniform && istype(user.w_uniform, /obj/item/clothing/under/gimmick/bowling))
src.hitHard(hitMob, user)
if(!(hitMob == user))
user.say(pick("Who's the kingpin now, baby?", "STRIIIKE!", "Watch it, pinhead!", "Ten points!"))
else
src.hitWeak(hitMob, user)
else
src.hitWeak(hitMob, user)
return
+119
View File
@@ -0,0 +1,119 @@
/obj/item/brain
name = "brain"
desc = "A human brain, gross."
icon = 'icons/obj/surgery.dmi'
icon_state = "brain2"
inhand_image_icon = 'icons/mob/inhand/hand_medical.dmi'
item_state = "brain2"
flags = TABLEPASS
force = 1.0
w_class = 1.0
throwforce = 1.0
throw_speed = 3
throw_range = 5
var/datum/mind/owner = null
stamina_damage = 5
stamina_cost = 5
edible = 1
/obj/item/brain/New()
..()
spawn(5)
if(src.donor)
src.name = "[src.donor]'s brain"
if (icon_state == "brain2")
desc = "A human brain. It looks [pick("small", "big", "normal", "rotten", "healthy", "tasty", "like it should be flushed down disposals", "bloody")]."
/obj/item/brain/examine()
..()
if (usr.job == "Roboticist" || usr.job == "Medical Doctor" || usr.job == "Geneticist" || usr.job == "Medical Director")
if (src.owner)
if (src.owner.current)
boutput(usr, "<span style=\"color:blue\">This brain is still warm.</span>")
else
boutput(usr, "<span style=\"color:red\">This brain has gone cold.</span>")
else
boutput(usr, "<span style=\"color:red\">This brain has gone cold.</span>")
/obj/item/brain/throw_impact(var/turf/T)
playsound(src.loc, "sound/effects/splat.ogg", 100, 1)
if (T)
new /obj/decal/cleanable/blood(T)
/obj/item/brain/synth
name = "synthbrain"
item_state = "plant"
desc = "An artificial mass of grey matter. Not actually, as one might assume, very good at thinking."
New()
..()
src.icon_state = pick("plant_brain", "plant_brain_bloom")
/obj/item/brain/ai
name = "neural net processor"
desc = "A heavily augmented human brain, upgraded to deal with the large amount of information an AI unit must process."
icon_state = "ai_brain"
item_state = "ai_brain"
New()
..()
spawn(10)
if(src.owner && src.owner.current)
src.name = "[src.owner.current]'s neural net processor"
/obj/item/brain/attack(mob/living/carbon/M as mob, mob/living/carbon/user as mob)
if(!istype(M, /mob))
return
src.add_fingerprint(user)
if(!(user.zone_sel.selecting == ("head")) || !istype(M, /mob/living/carbon/human))
return ..()
if(!(locate(/obj/machinery/optable, M.loc) && M.lying) && !(locate(/obj/table, M.loc) && (M.paralysis || M.stat)))
return ..()
var/mob/living/carbon/human/H = M
if(istype(M, /mob/living/carbon/human) && ((H.head && H.head.c_flags & COVERSEYES) || (H.wear_mask && H.wear_mask.c_flags & COVERSEYES) || (H.glasses && H.glasses.c_flags & COVERSEYES)))
// you can't stab someone in the eyes wearing a mask!
boutput(user, "<span style=\"color:blue\">You're going to need to remove that mask/helmet/glasses first.</span>")
return
//since these people will be dead M != usr
/*
if(M:brain_op_stage == 4.0)
var/fluff = pick("insert[M == user ? "" : "s"]", "shove[M == user ? "" : "s"]", "place[M == user ? "" : "s"]", "drop[M == user ? "" : "s"]", "smooshes[M == user ? "" : "s"]", "squishes[M == user ? "" : "s"]")
M.visible_message("<span style=\"color:red\"><b>[user]</b> [fluff] [src] into [M == user ? </span>"[M.gender == "male" ? "his" : "her"]" : "[M]'s"] head!", \
"<span style=\"color:red\">[M == user ? </span>"You" : "<b>[user]</b>"] [fluff] [src] into your head!")
if(M.client)
M.client.mob = new/mob/dead/observer(M)
//a mob can't have two clients so get rid of one
if(src.owner)
/*
//if the brain has an owner corpse
if(src.owner.client)
//if the player hasn't ghosted
src.owner.client.mob = M
//then put them in M
else
//if the player HAS ghosted
for(var/mob/dead/observer/O in mobs)
if(O.corpse == src.owner && O.client)
//find their ghost
O.client.mob = M
//put their mob in M
qdel(O)
//delete thier ghost
*/
src.owner.transfer_to(M)
M:brain_op_stage = 3.0
qdel(src)
else
..()
return
*/
+133
View File
@@ -0,0 +1,133 @@
/obj/item/medical
name = "medical pack"
icon = 'icons/obj/items.dmi'
inhand_image_icon = 'icons/mob/inhand/hand_medical.dmi'
amount = 5
w_class = 1
throw_speed = 4
throw_range = 20
var/heal_brute = 0
var/heal_burn = 0
stamina_damage = 3
stamina_cost = 3
stamina_crit_chance = 3
examine()
set src in view(1)
set category = "Local"
if (src.amount <= 0)
qdel(src)
return
..()
boutput(usr, "[bicon(src)] <span style=\"color:blue\">There [src.amount == 1 ? "is" : "are"] [src.amount] [src.name]\s left on the stack!</span>")
return
attack_hand(mob/user as mob)
if (user.r_hand == src || user.l_hand == src)
src.add_fingerprint(user)
var/obj/item/medical/split = new src.type(user)
split.amount = 1
user.put_in_hand_or_drop(split)
src.amount--
if (src.amount < 1)
qdel(src)
return
else
..()
return
attackby(obj/item/medical/W as obj, mob/user as mob)
if (!istype(W, src.type))
return
if (W.amount == 5)
return
if (W.amount + src.amount > 5)
src.amount = (W.amount + src.amount) - 5
W.amount = 5
else
W.amount += src.amount
qdel(src)
return
attack(mob/M as mob, mob/user as mob)
if (issilicon(M))
if (prob(5))
user.show_text("I'm a doctor, not a mechanic.", "red")
else
user.show_text("You can't seem to find any flesh on this patient.", "red")
return
if (user)
if (M != user)
M.visible_message("<span style=\"color:red\">[M] has been applied with [src] by [user]</span>",)
else
var/t_himself = "itself"
if (user.gender == MALE)
t_himself = "himself"
else if (user.gender == FEMALE)
t_himself = "herself"
M.visible_message("<span style=\"color:red\">[M] applied [src] on [t_himself]</span>")
if (ishuman(M))
var/mob/living/carbon/human/H = M
var/obj/item/affecting = H.organs["chest"]
if (ishuman(user))
var/mob/living/carbon/human/user2 = user
var/t = user2.zone_sel.selecting
if (H.organs[t])
affecting = H.organs[t]
else
if (!istype(affecting, /obj/item) || affecting:burn_dam <= 0)
affecting = H.organs["head"]
if (!istype(affecting, /obj/item) || affecting:burn_dam <= 0)
affecting = H.organs["chest"]
if (affecting.heal_damage(src.heal_brute, src.heal_burn))
H.UpdateDamageIcon()
if (M != user && ishuman(M) && ishuman(user))
if (M.gender != user.gender)
M.unlock_medal("Oh, Doctor!", 1)
user.unlock_medal("Oh, Doctor!", 1)
else
H.UpdateDamage()
else
M.HealDamage("All", src.heal_brute, src.heal_burn)
repair_bleeding_damage(M, 50, 1)
M.updatehealth()
src.amount--
if (src.amount <= 0)
qdel(src)
return
/obj/item/medical/bruise_pack
name = "bruise pack"
desc = "A pack designed to treat blunt-force trauma."
icon_state = "brutepack"
heal_brute = 60
cyborg
name = "Tissue Mender"
heal_brute = 60
amount = INFINITY
/obj/item/medical/ointment
name = "ointment"
icon_state = "ointment"
heal_burn = 40
desc = "A topical ointment designed to heal burns."
cyborg
name = "Burn Salve Dispenser"
heal_burn = 40
amount = INFINITY
File diff suppressed because it is too large Load Diff
+408
View File
@@ -0,0 +1,408 @@
// the cable coil object, used for laying cable
#define MAXCOIL 30
/obj/item/cable_coil
name = "cable coil"
var/base_name = "cable coil"
desc = "A coil of power cable."
amount = MAXCOIL
max_stack = MAXCOIL
stack_type = /obj/item/cable_coil // so cut cables can stack with partially depleted full coils
icon = 'icons/obj/power.dmi'
icon_state = "coil"
inhand_image_icon = 'icons/mob/inhand/hand_tools.dmi'
item_state = "coil"
throwforce = 10
w_class = 1.0
throw_speed = 2
throw_range = 5
flags = TABLEPASS|EXTRADELAY|FPRINT|CONDUCT
stamina_damage = 5
stamina_cost = 5
stamina_crit_chance = 10
rand_pos = 1
var/datum/material/insulator = null
var/datum/material/conductor = null
// will use getCachedMaterial() to apply these at spawn
var/spawn_insulator_name = "synthrubber"
var/spawn_conductor_name = "steel"
New(loc, length = MAXCOIL)
src.amount = length
pixel_x = rand(-2,2)
pixel_y = rand(-2,2)
updateicon()
..(loc)
if (spawn_conductor_name)
applyCableMaterials(src, getCachedMaterial(spawn_insulator_name), getCachedMaterial(spawn_conductor_name))
before_stack(atom/movable/O as obj, mob/user as mob)
user.visible_message("<span style=\"color:blue\">[user] begins coiling cable!</span>")
after_stack(atom/movable/O as obj, mob/user as mob, var/added)
boutput(user, "<span style=\"color:blue\">You finish coiling cable.</span>")
suicide(var/mob/user as mob)
user.visible_message("<span style=\"color:red\"><b>[user] wraps the cable around \his neck and tightens it.</b></span>")
user.take_oxygen_deprivation(160)
user.updatehealth()
spawn(100)
if (user)
user.suiciding = 0
return 1
proc/setInsulator(var/datum/material/M)
if (!M)
return
insulator = M
applyCableMaterials(src, M, conductor)
proc/setConductor(var/datum/material/M)
if (!M)
return
conductor = M
applyCableMaterials(src, insulator, M)
proc/updateName()
if (!conductor)
return
if (insulator)
name = "[insulator.name]-insulated [conductor.name]-[base_name]"
else
name = "uninsulated [conductor.name]-[base_name]"
proc/use(var/used)
if (src.amount < used)
return 0
else if (src.amount == used)
qdel(src)
else
amount -= used
updateicon()
return 1
proc/take(var/amt, var/newloc)
if (amt > amount)
amt = amount
if (amt == amount)
if (ismob(loc))
var/mob/owner = loc
owner.u_equip(src)
loc = newloc
return src
src.use(amt)
var/obj/item/cable_coil/C = new /obj/item/cable_coil(newloc)
C.amount = amt
C.updateicon()
C.setInsulator(insulator)
C.setConductor(conductor)
proc/updateicon()
if (amount <= 0)
qdel(src)
else if (amount >= 1 && amount <= 4)
icon_state = "coil[amount]"
base_name = "cable piece"
else
icon_state = "coil"
base_name = "cable coil"
updateName()
/obj/item/cable_coil/cut
icon = 'icons/obj/power.dmi'
icon_state = "coil2"
New(loc, length)
if (length)
..(loc, length)
else
..(loc, rand(1,2))
/obj/item/cable_coil/cut/small
New(loc, length)
..(loc, rand(1,5))
/obj/item/cable_coil/attack_self(var/mob/living/M)
if (istype(M))
if (M.move_laying)
M.move_laying = null
boutput(M, "<span style=\"color:blue\">No longer laying the cable while moving.</span>")
else
M.move_laying = src
boutput(M, "<span style=\"color:blue\">Now laying cable while moving.</span>")
/obj/proc/move_callback(var/mob/M, var/turf/source, var/turf/target)
return
/proc/find_half_cable(var/turf/T, var/ignore_dir)
for (var/obj/cable/C in T)
if (!C.d1 && C.d2 != ignore_dir)
return C
/obj/item/cable_coil/move_callback(var/mob/living/M, var/turf/source, var/turf/target)
if (!istype(M))
return
if (!src.amount)
M.move_laying = null
boutput(M, "<span style=\"color:red\">Your cable coil runs out!</span>")
return
var/obj/cable/C
C = find_half_cable(source, get_dir(source, target))
if (C)
cable_join_between(C, target)
else
turf_place_between(source, target)
if (!src.amount)
M.move_laying = null
boutput(M, "<span style=\"color:red\">Your cable coil runs out!</span>")
return
C = find_half_cable(target, get_dir(target, source))
if (C)
cable_join_between(C, source)
else
turf_place_between(target, source)
if (!src.amount)
M.move_laying = null
boutput(M, "<span style=\"color:red\">Your cable coil runs out!</span>")
return
/obj/item/cable_coil/examine()
set src in view(1)
set category = "Local"
if (amount == 1)
boutput(usr, "A short piece of power cable.")
else if (amount == 1)
boutput(usr, "A piece of power cable.")
else
boutput(usr, "A coil of power cable. There's [amount] length[s_es(amount)] of cable in the coil.")
if (insulator)
boutput(usr, "It is insulated with [insulator].")
if (conductor)
boutput(usr, "Its conductive layer is made out of [conductor].")
/obj/item/cable_coil/attackby(obj/item/W, mob/user)
if (istype(W, /obj/item/wirecutters) && src.amount > 1)
src.amount--
take(1, usr.loc)
boutput(user, "You cut a piece off the cable coil.")
src.updateicon()
return
else if (istype(W, /obj/item/cable_coil))
var/obj/item/cable_coil/C = W
if (C.conductor.mat_id != src.conductor.mat_id || C.insulator.mat_id != src.insulator.mat_id)
boutput(user, "You cannot link together cables made from different materials. That would be silly.")
return
if (C.amount == MAXCOIL)
boutput(user, "The coil is too long, you cannot add any more cable to it.")
return
if ((C.amount + src.amount <= MAXCOIL))
C.amount += src.amount
boutput(user, "You join the cable coils together.")
C.updateicon()
qdel(src)
return
else
boutput(user, "You transfer [MAXCOIL - src.amount ] length\s of cable from one coil to the other.")
src.amount -= (MAXCOIL-C.amount)
src.updateicon()
C.amount = MAXCOIL
C.updateicon()
return
/obj/item/cable_coil/MouseDrop_T(atom/movable/O as obj, mob/user as mob)
..(O, user)
for (var/obj/item/cable_coil/C in view(1, user))
C.updateicon()
// called when cable_coil is clicked on a turf/simulated/floor
/obj/item/cable_coil/proc/turf_place_between(turf/simulated/floor/A, turf/simulated/floor/B)
if (!isturf(B))
return
if (get_dist(A, B) > 1)
return
if (A.intact)
return
var/dirn = get_dir(A, B)
for (var/obj/cable/C in A)
if (C.d1 == dirn || C.d2 == dirn)
return
var/obj/cable/NC = new(A)
applyCableMaterials(NC, src.insulator, src.conductor)
NC.d1 = 0
NC.d2 = dirn
NC.updateicon()
NC.update_network()
NC.log_wirelaying(usr)
src.use(1)
return
/obj/item/cable_coil/proc/cable_join_between(var/obj/cable/C, var/turf/simulated/floor/B)
if (!isturf(B))
return
var/turf/T = C.loc
if (!isturf(T) || T.intact) // sanity checks, also stop use interacting with T-scanner revealed cable
return
if (get_dist(C, B) > 1) // make sure it's close enough
return
if (B == T) // do nothing if we clicked a cable we're standing on
return // may change later if can think of something logical to do
var/dirn = get_dir(C, B)
if (C.d1 == 0) // exisiting cable doesn't point at our position, so see if it's a stub
// if so, make it a full cable pointing from it's old direction to our dirn
var/nd1 = C.d2 // these will be the new directions
var/nd2 = dirn
if (nd1 > nd2) // swap directions to match icons/states
nd1 = dirn
nd2 = C.d2
for (var/obj/cable/LC in T) // check to make sure there's no matching cable
if (LC == C) // skip the cable we're interacting with
continue
if ((LC.d1 == nd1 && LC.d2 == nd2) || (LC.d1 == nd2 && LC.d2 == nd1) ) // make sure no cable matches either direction
return
qdel(C)
var/obj/cable/NC = new(T)
applyCableMaterials(NC, src.insulator, src.conductor)
NC.d1 = nd1
NC.d2 = nd2
NC.updateicon()
NC.update_network()
NC.log_wirelaying(usr)
src.use(1)
return
/obj/item/cable_coil/proc/turf_place(turf/simulated/floor/F, mob/user)
if (!isturf(user.loc))
return
if (get_dist(F,user) > 1)
boutput(user, "You can't lay cable at a place that far away.")
return
if (F.intact) // if floor is intact, complain
boutput(user, "You can't lay cable there unless the floor tiles are removed.")
return
else
var/dirn
if (user.loc == F)
dirn = user.dir // if laying on the tile we're on, lay in the direction we're facing
else
dirn = get_dir(F, user)
for (var/obj/cable/LC in F)
if (LC.d1 == dirn || LC.d2 == dirn)
boutput(user, "There's already a cable at that position.")
return
var/obj/cable/C = new(F)
C.d1 = 0
C.d2 = dirn
C.add_fingerprint(user)
C.updateicon()
C.update_network()
applyCableMaterials(C, src.insulator, src.conductor)
C.log_wirelaying(user)
src.use(1)
return
// called when cable_coil is click on an installed obj/cable
/obj/item/cable_coil/proc/cable_join(obj/cable/C, mob/user)
var/turf/U = user.loc
if (!isturf(U))
return
var/turf/T = C.loc
if (!isturf(T) || T.intact) // sanity checks, also stop use interacting with T-scanner revealed cable
return
if (get_dist(C, user) > 1) // make sure it's close enough
boutput(user, "You can't lay cable at a place that far away.")
return
if (U == T) // do nothing if we clicked a cable we're standing on
return // may change later if can think of something logical to do
var/dirn = get_dir(C, user)
if (C.d1 == dirn || C.d2 == dirn) // one end of the clicked cable is pointing towards us
if (U.intact) // can't place a cable if the floor is complete
boutput(user, "You can't lay cable there unless the floor tiles are removed.")
return
else
// cable is pointing at us, we're standing on an open tile
// so create a stub pointing at the clicked cable on our tile
var/fdirn = turn(dirn, 180) // the opposite direction
for (var/obj/cable/LC in U) // check to make sure there's not a cable there already
if (LC.d1 == fdirn && LC.d2 == fdirn)
boutput(user, "There's already a cable at that position.")
return
var/obj/cable/NC = new(U)
applyCableMaterials(NC, src.insulator, src.conductor)
NC.d1 = 0
NC.d2 = fdirn
NC.add_fingerprint()
NC.updateicon()
NC.update_network()
NC.log_wirelaying(user)
src.use(1)
C.shock(user, 25)
return
else if (C.d1 == 0) // exisiting cable doesn't point at our position, so see if it's a stub
// if so, make it a full cable pointing from it's old direction to our dirn
var/nd1 = C.d2 // these will be the new directions
var/nd2 = dirn
if (nd1 > nd2) // swap directions to match icons/states
nd1 = dirn
nd2 = C.d2
for (var/obj/cable/LC in T) // check to make sure there's no matching cable
if (LC == C) // skip the cable we're interacting with
continue
if ((LC.d1 == nd1 && LC.d2 == nd2) || (LC.d1 == nd2 && LC.d2 == nd1) ) // make sure no cable matches either direction
boutput(user, "There's already a cable at that position.")
return
C.shock(user, 25)
qdel(C)
var/obj/cable/NC = new(T)
applyCableMaterials(NC, src.insulator, src.conductor)
NC.d1 = nd1
NC.d2 = nd2
NC.add_fingerprint()
NC.updateicon()
NC.update_network()
NC.log_wirelaying(user)
src.use(1)
return
+290
View File
@@ -0,0 +1,290 @@
/*
CONTAINS:
DATA CARD
EMAG
ID CARD
GAUNTLET CARDS
*/
/obj/item/card
name = "card"
icon = 'icons/obj/card.dmi'
icon_state = "id"
wear_image_icon = 'icons/mob/mob.dmi'
w_class = 1.0
burn_type = 1
stamina_damage = 1
stamina_cost = 1
var/list/files = list("tools" = 1)
module_research_type = /obj/item/card
/obj/item/card/emag
desc = "It's a card with a magnetic strip attached to some circuitry."
name = "cryptographic sequencer"
icon_state = "emag"
item_state = "card-id"
flags = FPRINT | TABLEPASS | SUPPRESSATTACK
layer = 6.0 // TODO fix layer
is_syndicate = 1
mats = 8
module_research = list("malfunction" = 25)
module_research_type = /obj/item/card/emag
afterattack(var/atom/A, var/mob/user)
if(!A || !user)
return
A.emag_act(user, src)
attack() //Fucking attack messages up in this joint.
return
/obj/item/card/emag/fake
//delicious fake emag
attack_hand(mob/user as mob)
boutput(user, "<span class='combat'>Turns out that card was actually a kind of [pick("deadly chameleon","spiny anteater","sex toy that George Melons likes to use","Syndicate Top Trumps Card","bag of neckbeard shavings")] in disguise! It stabs you!</span>")
user.paralysis = 8
spawn(10)
var/obj/storage/closet/C = new/obj/storage/closet(get_turf(user))
user.set_loc(C)
C.layer = OBJ_LAYER
C.name = "an ordinary closet"
C.desc = "What? It's just an ordinary closet."
C.welded = 1
// ID CARDS
/obj/item/card/id
name = "identification card"
icon_state = "id"
item_state = "card-id"
desc = "A standardized NanoTrasen Identification Card. Ties into many systems station-wide."
var/access = list()
var/registered = null
var/assignment = null
var/title = null
var/emagged = 0
// YOU START WITH NO CREDITS
// WOW
var/money = 0.0
var/pin = 0000
//It's a..smart card. Sure.
var/datum/computer/file/cardfile = null
desc = "An microchipped identification card that contains data that is scanned when attempting to access various doors and computers on the station."
proc/update_name()
name = "[src.registered]'s ID Card ([src.assignment])"
/obj/item/card/id/New()
..()
src.pin = rand(1000,9999)
/obj/item/card/id/command
icon_state = "id_com"
/obj/item/card/id/security
icon_state = "id_sec"
/obj/item/card/id/research
icon_state = "id_res"
/obj/item/card/id/engineering
icon_state = "id_eng"
/obj/item/card/id/civilian
icon_state = "id_civ"
/obj/item/card/id/clown
icon_state = "id_clown"
desc = "Wait, this isn't even an ID Card. It's a piece of a Chips Ahoy wrapper with crayon scribbles on it. What the fuck?"
/obj/item/card/id/gold
name = "identification card"
icon_state = "gold"
item_state = "gold_id"
desc = "This card is important!"
/obj/item/card/id/blank_deluxe
name = "Deluxe ID"
icon_state = "gold"
item_state = "gold_id"
registered = "Member"
assignment = "Member"
/obj/item/card/id/captains_spare
name = "Captain's spare ID"
icon_state = "gold"
item_state = "gold_id"
registered = "Captain"
assignment = "Captain"
New()
access = get_access("Captain")
..()
/obj/item/card/id/captains_spare/explosive
pickup(mob/user)
boutput(user, "<span style=\"color:red\">The ID-Card explodes.</span>")
user.transforming = 1
var/obj/overlay/O = new/obj/overlay(get_turf(user))
O.anchored = 1
O.name = "Explosion"
O.layer = NOLIGHT_EFFECTS_LAYER_BASE
O.pixel_x = -17
O.icon = 'icons/effects/hugeexplosion.dmi'
O.icon_state = "explosion"
spawn(35) qdel(O)
spawn(5) user.gib()
/obj/item/card/id/attack_self(mob/user as mob)
user.visible_message("[user] shows you: [bicon(src)] [src.name]: assignment: [src.assignment]", "You show off your card: [bicon(src)] [src.name]: assignment: [src.assignment]")
src.add_fingerprint(user)
return
/obj/item/card/id/emag_act(var/mob/user, var/obj/item/card/emag/E)
if (src.emagged)
if (user && E)
user.show_text("You run [E] over [src], but nothing seems to happen.", "red")
return
src.access = list() // clear what used to be there
var/list/all_accesses = get_all_accesses()
for (var/i = rand(2,25), i > 0, i--)
var/new_access = pick(all_accesses)
src.access += new_access
all_accesses -= new_access
if (istype(src, /obj/item/card/id/syndicate)) // Nuke ops unable to exit their station (Convair880).
src.access += access_syndicate_shuttle
DEBUG("[get_access_desc(new_access)] added to [src]")
src.emagged = 1
/obj/item/card/id/verb/read()
set src in usr
boutput(usr, "[bicon(src)] [src.name]: The current assignment on the card is [src.assignment].")
return
/obj/item/card/id/syndicate
name = "agent card"
access = list(access_maint_tunnels, access_syndicate_shuttle)
/obj/item/card/id/syndicate/attack_self(mob/user as mob)
if(!src.registered)
var/reg = copytext(src.sanitize_name(input(user, "What name would you like to put on this card?", "Agent card name", ishuman(user) ? user.real_name : user.name)), 1, 100)
var/ass = copytext(src.sanitize_name(input(user, "What occupation would you like to put on this card?\n Note: This will not grant any access levels other than Maintenance.", "Agent card job assignment", "Staff Assistant"), 1), 1, 100)
var/color = input(user, "What color should the ID's color band be?\nClick cancel to abort the forging process.") as null|anything in list("blue","red","green","purple","yellow","No band")
switch (color)
if ("No band")
src.icon_state = "id"
if ("blue")
src.icon_state = "id_civ"
if ("red")
src.icon_state = "id_sec"
if ("green")
src.icon_state = "id_com"
if ("purple")
src.icon_state = "id_res"
if ("yellow")
src.icon_state = "id_eng"
else
return // Abort process.
src.registered = reg
src.assignment = ass
src.name = "[src.registered]'s ID Card ([src.assignment])"
boutput(user, "<span style=\"color:blue\">You successfully forge the ID card.</span>")
else
..()
/obj/item/card/id/syndicate/attackby(obj/item/W as obj, mob/user as mob)
var/obj/item/card/id/sourceCard = W
if (istype(sourceCard))
boutput(user, "You copy [sourceCard]'s accesses to [src].")
src.access |= sourceCard.access
else
return ..()
/obj/item/card/id/syndicate/proc/sanitize_name(var/input, var/strip_bad_stuff_only = 0)
input = strip_html(input, MAX_MESSAGE_LEN, 1)
if (strip_bad_stuff_only)
return input
var/list/namecheck = dd_text2list(trim(input), " ")
for(var/i = 1, i <= namecheck.len, i++)
namecheck[i] = capitalize(namecheck[i])
input = dd_list2text(namecheck, " ")
return input
/obj/item/card/id/temporary
name = "temporary identification card"
icon_state = "id"
item_state = "card-id"
desc = "A temporary NanoTrasen Identification Card. Its access will be revoked once it expires."
var/duration = 60 //seconds
var/starting_access = list()
var/timer = 0 //if 1, description shows time remaining
var/end_time = 0
/obj/item/card/id/temporary/New()
..()
spawn(0) //to give time for duration and starting access to be set
starting_access = access
end_time = ticker.round_elapsed_ticks + duration*10
spawn(duration * 10)
if(access == starting_access) //don't delete access if it's modified with an ID computer
access = list()
/obj/item/card/id/temporary/examine()
..()
if(usr.client && src.timer)
boutput(usr, "A small display in the corner reads: \"Time remaining: [max(0,round((end_time-ticker.round_elapsed_ticks)/10))] seconds.\"")
/obj/item/card/id/gauntlet
icon = 'icons/effects/VR.dmi'
icon_state = "id_clown"
New(var/L, var/mob/user)
..()
if (!user)
registered = "???"
assignment = "unknown phantom entity (no.. mob? this is awkward)"
if (istype(user, /mob/living/carbon/human/virtual))
var/mob/living/LI = user:body
if (LI)
registered = LI.real_name
else
registered = user.real_name
else
registered = user.real_name
if (!user.client)
assignment = "literal meat shield (no client)"
else
assignment = "loading arena matches..."
tag = "gauntlet-id-[user.client.key]"
queryGauntletMatches(1, user.client.key)
name = "[registered]'s ID Card ([assignment])"
proc/SetMatchCount(var/matches)
switch (matches)
if (-INFINITY to 0)
icon_state = "id_clown"
assignment = "Gauntlet Newbie ([matches] rounds played)"
if (1 to 10)
icon_state = "id_civ"
assignment = "Rookie Gladiator ([matches] rounds played)"
if (11 to 20)
icon_state = "id_res"
assignment = "Beginner Gladiator ([matches] rounds played)"
if (21 to 35)
icon_state = "id_eng"
assignment = "Skilled Gladiator ([matches] rounds played)"
if (36 to 55)
icon_state = "id_sec"
assignment = "Advanced Gladiator ([matches] rounds played)"
if (56 to 75)
icon_state = "id_com"
assignment = "Expert Gladiator ([matches] rounds played)"
if (76 to INFINITY)
icon_state = "gold"
assignment = "Legendary Gladiator ([matches] rounds played)"
else
assignment = "what the fuck ([matches] rounds played)"
name = "[registered]'s ID Card ([assignment])"
+104
View File
@@ -0,0 +1,104 @@
/obj/item/chem_pill_bottle
name = "Pill bottle"
icon_state = "pill_canister"
icon = 'icons/obj/chemical.dmi'
w_class = 2.0
stamina_damage = 3
stamina_cost = 3
stamina_crit_chance = 1
rand_pos = 1
var/pname
var/pvol
var/pcount
var/datum/reagents/reagents_internal
// setup this pill bottle from some reagents
proc/create_from_reagents(var/datum/reagents/R, var/pillname, var/pillvol, var/pillcount)
var/volume = pillcount * pillvol
reagents_internal = new/datum/reagents(volume)
reagents_internal.my_atom = src
R.trans_to_direct(reagents_internal,volume)
src.name = "[pillname] pill bottle"
src.desc = "Contains [pillcount] [pillname] pills."
src.pname = pillname
src.pvol = pillvol
src.pcount = pillcount
// spawn a pill, returns a pill or null if there aren't any left in the bottle
proc/create_pill()
var/totalpills = src.pcount + src.contents.len
if(totalpills <= 0)
return null
var/obj/item/reagent_containers/pill/P = null
// give back stored pills first
if (src.contents.len)
P = src.contents[src.contents.len]
// otherwise create a new one from the reagent holder
else if (pcount)
if (src.reagents_internal.total_volume < src.pvol)
src.pcount = 0
else
P = unpool(/obj/item/reagent_containers/pill)
P.loc = src
P.name = "[pname] pill"
src.reagents_internal.trans_to(P,src.pvol)
src.pcount--
// else return null
return P
proc/rebuild_desc()
var/totalpills = src.pcount + src.contents.len
if(totalpills > 15)
src.desc = "A [src.pname] pill bottle. There are too many to count."
else if (totalpills <= 0)
src.desc = "A [src.pname] pill bottle. It looks empty."
else
src.desc = "A [src.pname] pill bottle. There [totalpills==1? "is [totalpills] pill." : "are [totalpills] pills." ]"
attackby(obj/item/W as obj, mob/user as mob)
if (istype(W, /obj/item/reagent_containers/pill/))
user.u_equip(W)
W.set_loc(src)
W.dropped()
boutput(user, "<span style=\"color:blue\">You put [W] in [src].</span>")
rebuild_desc()
else ..()
attack_self(var/mob/user as mob)
var/obj/item/reagent_containers/pill/P = src.create_pill()
if (istype(P))
do
P.set_loc(user.loc)
P = src.create_pill()
while(istype(P))
boutput(user, "<span style=\"color:blue\">You tip out all the pills from [src] into [user.loc].</span>")
rebuild_desc()
else
boutput(user, "<span style=\"color:red\">It's empty.</span>")
return
attack_hand(mob/user as mob)
if(user.r_hand == src || user.l_hand == src)
var/obj/item/reagent_containers/pill/P = src.create_pill()
if(istype(P))
user.put_in_hand_or_drop(P)
boutput(user, "You take [P] from [src].")
rebuild_desc()
else
boutput(user, "<span style=\"color:red\">It's empty.</span>")
return
else
return ..()
+816
View File
@@ -0,0 +1,816 @@
/* ==================================================== */
/* -------------------- Cigarettes -------------------- */
/* ==================================================== */
/obj/item/clothing/mask/cigarette
name = "cigarette"
icon_state = "cigoff"
item_state = "cigoff"
force = 0
damtype = "brute"
throw_speed = 0.5
w_class = 1
armor_value_melee = 0
cold_resistance = 0
heat_resistance = 0
var/lit = 0
var/lastHolder = null
var/exploding = 0 //Does it blow up when it goes out?
var/flavor = null
var/nic_free = 0
rand_pos = 1
New()
..()
var/datum/reagents/R = new/datum/reagents(60)
reagents = R
R.my_atom = src
if (src.exploding)
if (src.flavor)
R.add_reagent(src.flavor, 5)
R.add_reagent("nicotine", 5)
return
else if (!src.nic_free)
R.add_reagent("nicotine", 40)
if (src.flavor)
R.add_reagent(src.flavor, 20)
return
else if (src.flavor)
R.add_reagent(src.flavor, 40)
return
afterattack(atom/target, mob/user, flag) // copied from the propuffs
if (istype(target, /obj/item/reagent_containers/))
user.visible_message("<span style=\"color:blue\"><b>[user]</b> crushes up the [src] in the [target].</span>",\
"<span style=\"color:blue\">You crush up the [src] in the [target].</span>")
src.reagents.trans_to(target, 5)
qdel (src)
else if (istype(target, /obj/item/match) && src.lit)
target:light(user, "<span style=\"color:red\"><b>[user]</b> lights [target] with [src].</span>")
else if (src.lit == 0 && istype(target, /obj/item) && target:burning)
src.light(user, "<span style=\"color:red\"><b>[user]</b> lights the [src] with [target]. Goddamn.</span>")
return
else
return ..()
proc/light(var/mob/user as mob, var/message as text)
if (src.lit == 0)
src.lit = 1
src.damtype = "fire"
src.force = 3
src.icon_state = "cigon"
src.item_state = "cigon"
if (user && message)
user.visible_message(message) //user check to fix a shitton of runtime errors with the temp expose ignition method. welp. -cogwerks
//spawn() //start fires while it's lit
//src.process()
if (!(src in processing_items))
processing_items.Add(src) // we have a nice scheduler let's use that instead tia
proc/put_out(var/mob/user as mob, var/message as text)
if (src.lit == 1)
src.lit = -1
src.damtype = "brute"
src.force = 0
src.icon_state = "cigbutt"
src.item_state = "cigoff"
src.name = "cigarette butt"
src.desc = "A cigarette butt."
if (user && message)
user.visible_message(message)
if (src in processing_items)
processing_items.Remove(src)
temperature_expose(datum/gas_mixture/air, temperature, volume)
if (src.lit == 0)
if (temperature > T0C+200)
src.visible_message("<span style=\"color:red\">The [src] ignites!</span>")
src.light()
ex_act(severity)
if (src.lit == 0)
src.visible_message("<span style=\"color:red\">The [src] ignites!</span>")
src.light()
attackby(obj/item/W as obj, mob/user as mob)
if (src.lit == 0)
if (istype(W, /obj/item/weldingtool) && W:welding)
src.light(user, "<span style=\"color:red\"><b>[user]</b> casually lights the [src] with [W], what a badass.</span>")
return
else if (istype(W, /obj/item/clothing/head/cakehat) && W:on)
src.light(user, "<span style=\"color:red\">Did [user] just light \his [src] with the [W]? Holy Shit.</span>")
return
else if (istype(W, /obj/item/device/igniter))
src.light(user, "<span style=\"color:red\"><b>[user]</b> fumbles around with the [W]; a small flame erupts from the [src].</span>")
return
else if (istype(W, /obj/item/zippo) && W:lit)
src.light(user, "<span style=\"color:red\">With a single flick of their wrist, [user] smoothly lights [src] with [W]. Damn they're cool.</span>")
return
else if ((istype(W, /obj/item/match) || istype(W, /obj/item/device/candle)) && W:lit)
src.light(user, "<span style=\"color:red\"><b>[user]</b> lights [src] with [W].</span>")
return
else if (W.burning)
src.light(user, "<span style=\"color:red\"><b>[user]</b> lights the [src] with [W]. Goddamn.</span>")
return
else
return ..()
else
return ..() // CALL your GODDAMN PARENTS
attack(atom/target, mob/user as mob)
if (isliving(target))
var/mob/living/M = target
if (ishuman(M))
var/mob/living/carbon/human/H = M
if (H.bleeding || (H.butt_op_stage == 4 && user.zone_sel.selecting == "chest"))
if (!src.cautery_surgery(H, user, 5, src.lit))
return ..()
if (M.burning && src.lit == 0)
if (M == user)
src.light(user, "<span style=\"color:red\"><b>[user]</b> lights \his cigarette with \his OWN flaming body. That's dedication! Or crippling addiction.</span>")
else
src.light(user, "<span style=\"color:red\"><b>[user]</b> lights \his cigarette with [M]'s flaming body. That's cold, man. That's real cold.</span>")
else
..(target, user)
if (src.lit == 1)
src.put_out(user, "<span style=\"color:red\"><b>[user]</b> puts the [src] out on [target].</span>")
if (ishuman(target))
var/mob/living/carbon/human/chump = target
if (!chump.stat)
chump.emote("scream")
process()
var/atom/lastHolder = null
//while (src.lit == 1)
if (src.lit == 1)
var/turf/location = src.loc
var/atom/holder = loc
var/isHeld = 0
var/mob/M = null
if (!src.exploding && prob(20)) // cigs shouldn't go out instantly dang
if (ismob(location))
M = location
if(istype(M, /mob/living/carbon/human)) //HOLY DUPLICATE CODE BATMAN!!!
var/mob/living/carbon/human/H = M
if(H.traitHolder && H.traitHolder.hasTrait("smoker"))
src.reagents.remove_any(1)
else
src.reagents.trans_to(M, 1)
src.reagents.reaction(M, INGEST)
else
src.reagents.trans_to(M, 1)
src.reagents.reaction(M, INGEST)
else src.reagents.remove_any(1)
else if (src.exploding)
if (ismob(location))
M = location
if(istype(M, /mob/living/carbon/human)) //HOLY DUPLICATE CODE BATMAN!!!
var/mob/living/carbon/human/H = M
if(H.traitHolder && H.traitHolder.hasTrait("smoker"))
src.reagents.remove_any(1)
else
src.reagents.trans_to(M, 1)
else
src.reagents.trans_to(M, 1)
else if (src && src.reagents) //Wire: fix for Cannot execute null.remove any().
src.reagents.remove_any(1)
if (src.reagents.total_volume <= 0)
if (src.exploding)
src.lit = 0 //Let's not keep looping while we're busy blowing up, ok?
spawn((20)+(rand(1,10)))
var/turf/tlocation = get_turf(src.loc)
if (tlocation)
explosion(src, tlocation, 0, 1, 1, 2)
else
var/datum/effects/system/spark_spread/s = unpool(/datum/effects/system/spark_spread)
s.set_up(5, 1, src)
s.start()
playsound(src.loc, "sound/effects/Explosion1.ogg", 75, 1)
src.visible_message("<span style=\"color:red\">The [src] explodes!</span>")
// Added (Convair880).
if (ismob(src.loc))
logTheThing("bombing", null, src.loc, "A trick cigarette (held/equipped by %target%) explodes at [log_loc(src)].")
else
logTheThing("bombing", src.fingerprintslast, null, "A trick cigarette explodes at [log_loc(src)]. Last touched by [src.fingerprintslast ? "[src.fingerprintslast]" : "*null*"].")
qdel(src)
return
else
src.put_out(M, "<span style=\"color:red\"><b>[M]</b>'s [src] goes out.</span>")
return
//if (istype(location, /turf)) //start a fire if possible
// location.hotspot_expose(700, 5) // this doesn't seem to ever actually happen, gonna try a different setup - cogwerks
var/turf/T = get_turf(src.loc)
if (T)
T.hotspot_expose(650,5)
if (ismob(holder))
isHeld = 1
else
isHeld = 0
if (lastHolder != null)
lastHolder = null
if (isHeld == 1)
lastHolder = holder
//sleep(10)
if (lastHolder != null)
lastHolder = null
dropped(mob/user as mob)
if(!istype(src.loc, /turf)) return
if (src.lit == 1 && !src.exploding && src.reagents.total_volume <= 20)
src.put_out(user, "<span style=\"color:red\"><b>[user]</b> calmly drops and treads on the lit [src], putting it out instantly.</span>")
return ..()
else
user.visible_message("<span style=\"color:red\"><b>[user]</b> drops the [src]. Guess they've had enough for the day.</span>")
return ..()
/obj/item/clothing/mask/cigarette/nicofree
name = "nicotine-free cigarette"
desc = "Smoking without the crippling addiction and lung cancer! Warning: side effects may include loss of breath and inability to relax."
nic_free = 1
flavor = "capsaicin"
/obj/item/clothing/mask/cigarette/random
desc = "A cigarette which seems to have been laced with something."
New()
if (all_functional_reagent_ids.len > 0)
src.flavor = pick(all_functional_reagent_ids)
else
src.flavor = "nicotine"
src.name = "[reagent_id_to_name(src.flavor)]-laced cigarette"
..()
/obj/item/clothing/mask/cigarette/propuffs
desc = "Pro Puffs - a new taste thrill in every cigarette."
New()
src.flavor = pick("silicate","antihol","mutadone","rum","mutagen","toxin","water_holy","fuel","salbutamol","haloperidol",
"cryoxadone","cryostylane","omnizine","jenkem","vomit","carpet","charcoal","blood","cheese","bilk","atropine",
"lexorin","teporone","mannitol","spaceacillin","saltpetre","anti_rad","insulin","gvomit","milk","colors","diluted_fliptonium",
"something","honey_tea","tea","coffee","chocolate","guacamole","juice_pickle","vanilla","enriched_msg","egg","aranesp",
"paper","bread","green_goop","black_goop")
src.name = "[reagent_id_to_name(src.flavor)]-laced cigarette"
..()
/obj/item/clothing/mask/cigarette/syndicate
//desc = "It looks a little funny." //fucka you
exploding = 1
// this was in the middle of plants_food_etc.dm
// WHY
/obj/item/clothing/mask/cigarette/custom
desc = "There could be anything in this."
flags = FPRINT|TABLEPASS|OPENCONTAINER
New()
..()
var/datum/reagents/R = new/datum/reagents(600)
reagents = R
R.my_atom = src
is_open_container()
return 1
/* ================================================= */
/* -------------------- Packets -------------------- */
/* ================================================= */
/obj/item/cigpacket
name = "cigarette packet"
desc = "The most popular brand of Space Cigarettes, sponsors of the Space Olympics."
icon = 'icons/obj/cigarettes.dmi'
icon_state = "cigpacket"
item_state = "cigpacket"
w_class = 1
throwforce = 2
var/cigcount = 6
var/cigtype = /obj/item/clothing/mask/cigarette
var/package_style = "cigpacket"
flags = ONBELT | TABLEPASS | FPRINT
stamina_damage = 3
stamina_cost = 3
rand_pos = 1
/obj/item/cigpacket/nicofree
name = "nicotine-free cigarette packet"
desc = "All the perks of smoking without the addiction! Warning: Cigarettes use chemical compounds which may cause severe throat irritation."
cigtype = /obj/item/clothing/mask/cigarette/nicofree
icon_state = "cigpacket-b"
package_style = "cigpacket-b"
/obj/item/cigpacket/propuffs
name = "packet of Pro Puffs"
desc = "A flavor surprise in each cigarette, lovingly wrapped in the finest papers."
cigtype = /obj/item/clothing/mask/cigarette/propuffs
icon_state = "cigpacket-r"
package_style = "cigpacket-r"
/obj/item/cigpacket/random
name = "odd cigarette packet"
desc = "These don't seem to have a brand name on them."
cigtype = /obj/item/clothing/mask/cigarette/random
icon_state = "cigpacket-p"
package_style = "cigpacket-p"
/obj/item/cigpacket/syndicate // cogwerks: made them more sneaky, removed the glaringly obvious name
// haine: these can just inherit the parent name and description vOv
cigtype = /obj/item/clothing/mask/cigarette/syndicate
/obj/item/cigpacket/proc/update_icon()
src.overlays = null
if (src.cigcount <= 0)
src.icon_state = "[src.package_style]0"
src.desc = "There aren't any cigs left, shit!"
else
src.icon_state = "[src.package_style]o"
src.overlays += "cig[src.cigcount]"
return
/* /obj/item/cigpacket/proc/update_icon() used to just be a return, with this directly below it. ?????
/obj/item/cigpacket/update_icon()
src.icon_state = "cigpacket[src.cigcount]"
src.desc = "There are [src.cigcount] cigs\s left!"
return
*/
/obj/item/cigpacket/attack_hand(mob/user as mob)
if (user.find_in_hand(src))//r_hand == src || user.l_hand == src)
if (src.cigcount == 0)
user.show_text("You're out of cigs, shit! How you gonna get through the rest of the day?", "red")
return
else
var/obj/item/clothing/mask/cigarette/W = new src.cigtype(user)
user.put_in_hand_or_drop(W)
if (src.cigcount != -1)
src.cigcount--
src.update_icon()
else
return ..()
return
/obj/item/cigbutt
name = "cigarette butt"
desc = "A manky old cigarette butt."
icon = 'icons/obj/cigarettes.dmi'
icon_state = "cigbutt"
w_class = 1
throwforce = 1
stamina_damage = 3
stamina_cost = 3
rand_pos = 1
/* ================================================== */
/* -------------------- Lighters -------------------- */
/* ================================================== */
/obj/item/matchbook
name = "matchbook"
desc = "A little bit of heavy paper with some matches in it, and a little strip to light them on."
icon = 'icons/obj/cigarettes.dmi'
icon_state = "matchbook"
w_class = 1
throwforce = 1
flags = FPRINT | TABLEPASS | SUPPRESSATTACK
stamina_damage = 1
stamina_cost = 1
stamina_crit_chance = 1
burn_point = 220
burn_output = 900
burn_possible = 1
health = 20
var/match_amt = 6 // -1 for infinite
rand_pos = 1
get_desc(dist)
if (src.match_amt == -1)
. += "There's a whole lot of matches left."
else if (src.match_amt >= 1)
. += "There's [src.match_amt] match[s_es(src.match_amt, 1)] left."
else
. += "It's empty."
attack_hand(mob/user as mob)
if (user.find_in_hand(src))
if (src.match_amt == 0)
user.show_text("Looks like there's no matches left.", "red")
return
else
var/obj/item/match/W = new /obj/item/match(user)
user.put_in_hand_or_drop(W)
if (src.match_amt != -1)
src.match_amt --
src.update_icon()
else
return ..()
return
afterattack(atom/target, mob/user as mob)
if (istype(target, /obj/item/match))
if (target:lit > 0)
return
if (target:lit == -1)
user.show_text("You [pick("fumble", "fuss", "mess", "faff")] around with [target] and try to get it to light, but it's no use.", "red")
return
else if (prob(25))
user.visible_message("<b>[user]</b> awkwardly strikes [src] on [target]. [target] breaks!",\
"You awkwardly strike [src] on [target]. [target] breaks![prob(50) ? " [pick("Damn!", "Fuck!", "Shit!", "Crap!")]" : null]")
playsound(user.loc, 'sound/items/matchstick_hit.ogg', 50, 1)
target:put_out(user, 1)
return
else if (prob(10))
user.visible_message("<b>[user]</b> awkwardly strikes [src] on [target]. A small flame sparks into life from the tip.",\
"You awkwardly strike [src] on [target]. A small flame sparks into life from the tip.")
target:light(user)
return
else
user.visible_message("<b>[user]</b> awkwardly strikes [src] on [target]. Nothing happens.",\
"You awkwardly strike [src] on [target]. Nothing happens.")
playsound(user.loc, 'sound/items/matchstick_hit.ogg', 50, 1)
return
else
return ..()
attack()
return
proc/update_icon()
if (src.match_amt == -1)
src.icon_state = "matchbook6"
return
else
src.icon_state = "matchbook[src.match_amt]"
/obj/item/match
name = "match"
desc = "A little stick of wood with phosphorus on the tip, for lighting fires, or making you very frustrated and not lighting fires. Either or."
icon = 'icons/obj/cigarettes.dmi'
icon_state = "match"
w_class = 1
throwforce = 1
flags = FPRINT | TABLEPASS | SUPPRESSATTACK
stamina_damage = 1
stamina_cost = 1
stamina_crit_chance = 1
burn_point = 220
burn_output = 600
burn_possible = 1
health = 10
var/lit = 0 // -1 is burnt out/broken or otherwise unable to be lit
var/light_mob = 0
var/life_timer = 0
rand_pos = 1
var/datum/light/light
New()
..()
light = new /datum/light/point
light.set_brightness(0.4)
light.set_color(0.94, 0.69, 0.27)
light.attach(src)
src.life_timer = rand(15,25)
pickup(mob/user)
..()
light.attach(user)
dropped(mob/user)
..()
if (isturf(src.loc))
src.put_out(user)
user.visible_message("<span style=\"color:red\"><b>[user]</b> calmly drops and treads on the lit [src], putting it out instantly.</span>")
return
spawn(0)
if (src.loc != user)
light.attach(src)
process()
if (src.lit > 0)
if (src.life_timer >= 0)
life_timer--
var/location = src.loc
if (ismob(location))
var/mob/M = location
if (src.life_timer <= 0)
src.put_out(M)
if (M.find_in_hand(src))
M.show_text("[src] burns your hand as the flame reaches the end of [src]!", "red")
M.TakeDamage("All", 0, rand(1,5))
return
var/turf/T = get_turf(src.loc)
if (T)
T.hotspot_expose(600,5)
if (src.life_timer <= 0)
src.put_out()
return
//sleep(10)
proc/light(var/mob/user as mob)
src.lit = 1
src.icon_state = "match-lit"
playsound(user.loc, 'sound/items/matchstick_light.ogg', 50, 1)
light.enable()
if (!(src in processing_items))
processing_items.Add(src)
return
proc/put_out(var/mob/user as mob, var/break_it = 0)
src.lit = -1
src.life_timer = 0
if (break_it)
src.icon_state = "match-broken"
src.name = "broken match"
if (user)
playsound(user.loc, 'sound/items/crunch.ogg', 60, 1, 0, 2)
else
src.icon_state = "match-burnt"
src.name = "burnt-out match"
light.disable()
if (src in processing_items)
processing_items.Remove(src)
return
temperature_expose(datum/gas_mixture/air, temperature, volume)
if (src.lit == 0)
if (temperature > T0C+200)
src.visible_message("<span style=\"color:red\">The [src] ignites!</span>")
src.light()
ex_act(severity)
if (src.lit == 0)
src.visible_message("<span style=\"color:red\">The [src] ignites!</span>")
src.light()
afterattack(atom/target, mob/user as mob)
if (src.lit > 0)
if (!ismob(target) && target.reagents)
user.show_text("You heat [target].", "blue")
target.reagents.temperature_reagents(1000,10)
return
else if (src.lit == -1)
user.show_text("You [pick("fumble", "fuss", "mess", "faff")] around with [src] and try to get it to light, but it's no use.", "red")
return
else if (src.lit == 0)
if (istype(target, /obj/item/match) && target:lit > 0)
user.visible_message("<b>[user]</b> lights [src] with the flame from [target].",\
"You light [src] with the flame from [target].")
src.light(user)
return
else if (istype(target, /obj/item/clothing/mask/cigarette) && target:lit > 0)
user.visible_message("<b>[user]</b> lights [src] with [target].",\
"You light [src] with [target].")
src.light(user)
return
else if (istype(target, /obj/item/matchbook))
if (prob(10))
user.visible_message("<b>[user]</b> strikes [src] on [target]. [src] breaks!",\
"You strike [src] on [target]. [src] breaks![prob(50) ? " [pick("Damn!", "Fuck!", "Shit!", "Crap!")]" : null]")
playsound(user.loc, 'sound/items/matchstick_hit.ogg', 50, 1)
src.put_out(user, 1)
return
else if (prob(50))
user.visible_message("<b>[user]</b> strikes [src] on [target]. A small flame sparks into life from the tip.",\
"You strike [src] on [target]. A small flame sparks into life from the tip.")
src.light(user)
return
else
user.visible_message("<b>[user]</b> strikes [src] on [target]. Nothing happens.",\
"You strike [src] on [target]. Nothing happens.")
playsound(user.loc, 'sound/items/matchstick_hit.ogg', 50, 1)
return
else if (istype (target, /obj/item) && target:burning)
user.visible_message("<b>[user]</b> lights [src] with the flame from [target].",\
"You light [src] with the flame from [target].")
src.light(user)
return
else
if (prob(10))
user.visible_message("<b>[user]</b> strikes [src] on [target]. A small flame sparks into life from the tip.[prob(50) ? " [pick("Damn", "Fuck", "Shit", "Wow")][pick("!", " that was cool!", " that was smooth!")]" : null]",\
"You strike [src] on [target]. A small flame sparks into life from the tip.")
src.light(user)
return
else if (prob(25))
user.visible_message("<b>[user]</b> strikes [src] on [target]. [src] breaks!",\
"You strike [src] on [target]. [src] breaks![prob(50) ? " [pick("Damn!", "Fuck!", "Shit!", "Crap!")]" : null]")
playsound(user.loc, 'sound/items/matchstick_hit.ogg', 50, 1)
src.put_out(user, 1)
return
else
user.visible_message("<b>[user]</b> strikes [src] on [target]. Nothing happens.",\
"You strike [src] on [target]. Nothing happens.[prob(50) ? " You feel awkward, though." : null]")
playsound(user.loc, 'sound/items/matchstick_hit.ogg', 50, 1)
return
attack(mob/M as mob, mob/user as mob)
if (ishuman(M))
if (src.lit > 0)
var/mob/living/carbon/human/fella = M
if (fella.wear_mask && istype(fella.wear_mask, /obj/item/clothing/mask/cigarette))
var/obj/item/clothing/mask/cigarette/smoke = fella.wear_mask // aaaaaaa
smoke.light(user, "<span style=\"color:red\"><b>[user]</b> lights [fella]'s [smoke] with [src].</span>")
fella.set_clothing_icon_dirty()
return
else if (fella.bleeding || (fella.butt_op_stage == 4 && user.zone_sel.selecting == "chest"))
src.cautery_surgery(fella, user, 5, src.lit)
return ..()
else
user.visible_message("<span style=\"color:red\"><b>[user]</b> puts out [src] on [fella]!</span>",\
"<span style=\"color:red\">You put out [src] on [fella]!</span>")
fella.TakeDamage("All", 0, rand(1,5))
if (!fella.stat)
fella.emote("scream")
src.put_out(user)
return
else
return ..()
attack_self(mob/user)
if (user.find_in_hand(src))
if (src.lit > 0)
user.visible_message("<b>[user]</b> [pick("licks [his_or_her(user)] finger and snuffs out [src].", "waves [src] around until it goes out.")]")
src.put_out(user)
else
return ..()
return
/obj/item/zippo
name = "zippo lighter"
desc = "A pretty nice lighter."
icon = 'icons/obj/cigarettes.dmi'
icon_state = "zippo"
item_state = "zippo"
w_class = 1
throwforce = 4
flags = FPRINT | ONBELT | TABLEPASS | CONDUCT
stamina_damage = 5
stamina_cost = 5
stamina_crit_chance = 5
var/lit = 0
var/fuel = 30 // -1 means infinite fuel
var/icon_closed = "zippo"
var/icon_open = "zippoon"
var/datum/light/light
New()
..()
light = new /datum/light/point
light.set_brightness(0.4)
light.set_color(0.94, 0.69, 0.27)
light.attach(src)
pickup(mob/user)
..()
light.attach(user)
dropped(mob/user)
..()
spawn(0)
if (src.loc != user)
light.attach(src)
borg
fuel = -1
attack_self(mob/user)
if (user.find_in_hand(src))
if (!src.lit)
if (fuel == 0)
user.show_text("Out of fuel.", "red")
return
src.lit = 1
src.icon_state = src.icon_open
src.item_state = "zippoon"
user.visible_message("<span style=\"color:red\">Without even breaking stride, [user] flips open and lights the [src] in one smooth movement.</span>")
light.enable()
if (!(src in processing_items))
processing_items.Add(src)
else
src.lit = 0
src.icon_state = src.icon_closed
src.item_state = "zippo"
user.visible_message("<span style=\"color:red\">You hear a quiet click, as [user] shuts off the [src] without even looking what they're doing. Wow.</span>")
light.disable()
if (src in processing_items)
processing_items.Remove(src)
else
return ..()
return
afterattack(atom/target, mob/user as mob)
if (!lit && istype(target, /obj/reagent_dispensers/fueltank))
if (src.fuel == -1)
user.show_text("You can't seem to find any way to add more fuel to [src]. It's probably fine.", "blue")
return
var/obj/reagent_dispensers/fueltank/O = target
var/fuelamt = O.reagents.get_reagent_amount("fuel")
if (fuelamt)
var/removed = min(fuelamt, 50)
O.reagents.remove_reagent("fuel", removed)
fuel += removed
user.show_text("[src] refueled.", "blue")
playsound(user.loc, "sound/effects/zzzt.ogg", 50, 1, -6)
else
user.show_text("[O] is empty.", "red")
if (!ismob(target) && target.reagents)
user.show_text("You heat [target].", "blue")
target.reagents.temperature_reagents(1500,10)
if (ishuman(target))
var/mob/living/carbon/human/fella = target
if (user.zone_sel.selecting == "l_arm")
if (fella.limbs.l_arm_bleed > 1)
fella.TakeDamage("chest",0,10)
fella.limbs.l_arm_bleed = max(0,fella.limbs.l_arm_bleed-5)
if (fella.limbs.l_arm_bleed == 0)
user.visible_message("<span style=\"color:red\">[user] completely cauterises [fella]'s left stump with [src]!</span>")
else
user.visible_message("<span style=\"color:red\">[user] partially cauterises [fella]'s left stump with [src]!</span>")
return
if (user.zone_sel.selecting == "r_arm")
if (fella.limbs.r_arm_bleed > 1)
fella.TakeDamage("chest",0,10)
fella.limbs.r_arm_bleed = max(0,fella.limbs.r_arm_bleed-5)
if (fella.limbs.r_arm_bleed == 0)
user.visible_message("<span style=\"color:red\">[user] completely cauterises [fella]'s right stump with [src]!</span>")
else
user.visible_message("<span style=\"color:red\">[user] partially cauterises [fella]'s right stump with [src]!</span>")
return
if (fella.wear_mask && istype(fella.wear_mask, /obj/item/clothing/mask/cigarette))
var/obj/item/clothing/mask/cigarette/smoke = fella.wear_mask // aaaaaaa
smoke.light(user, "<span style=\"color:red\"><b>[user]</b> lights [fella]'s [smoke] with [src].</span>")
fella.set_clothing_icon_dirty()
return
if (fella.bleeding || (fella.butt_op_stage == 4 && user.zone_sel.selecting == "chest"))
if (!src.cautery_surgery(target, user, 10, src.lit))
return ..()
user.visible_message("<span style=\"color:red\"><b>[user]</b> waves [src] around in front of [fella]'s face! OoOo, are ya scared?![src.lit ? "" : " Too bad [src] is closed."]</span>")
return
else if (ismob(target))
user.visible_message("<span style=\"color:red\"><b>[user]</b> waves [src] around in front of [target]'s face! OoOo, are ya scared?![src.lit ? "" : " Too bad [src] is closed."]</span>")
return
else
return ..()
process()
if (src.lit)
if (src.fuel >= 0)
fuel--
var/turf/location = src.loc
if (ismob(location))
var/mob/M = location
if (M.find_in_hand(src))
location = M.loc
var/turf/T = get_turf(src.loc)
if (T)
T.hotspot_expose(700,5)
if (fuel == 0)
src.lit = 0
src.icon_state = src.icon_closed
src.item_state = "zippo"
light.disable()
if (src in processing_items)
processing_items.Remove(src)
return
//sleep(10)
suicide(var/mob/user as mob)
if(!src.lit) return 0
user.visible_message("<span style=\"color:red\"><b>[user] swallows the lit [src.name]!</b></span>")
user.take_oxygen_deprivation(75)
user.TakeDamage("chest", 0, 100)
user.emote("scream")
user.updatehealth()
spawn(100)
if (user)
user.suiciding = 0
qdel(src)
return 1
/obj/item/zippo/gold
name = "golden zippo lighter"
icon_state = "gold_zippo"
icon_closed = "gold_zippo"
icon_open = "gold_zippoon"
+70
View File
@@ -0,0 +1,70 @@
/obj/item/clothing
name = "clothing"
//var/obj/item/clothing/master = null
w_class = 2.0
var/see_face = 1
var/body_parts_covered = 0 //see setup.dm for appropriate bit flags
var/c_flags = null // these don't need to be in the general flags when they only apply to clothes :I
var/protective_temperature = 0
var/heat_transfer_coefficient = 1 //0 prevents all transfers, 1 is invisible
var/permeability_coefficient = 1 // for chemicals/diseases
var/siemens_coefficient = 1 // for electrical admittance/conductance (electrocution checks and shit)
var/magical = 0 // for wizard item spell power check
var/radproof = 0 // can this item completely shield you from radiation?
var/disease_resistance = 0 // how much does this protect you from diseases? (of a 100% chance)
var/list/compatible_species = list("human") // allow monkeys/mutantraces to wear certain garments
var/armor_value_melee = 0
var/armor_value_bullet = 0
var/armor_value_explosion = 0
var/cold_resistance = 0
var/heat_resistance = 0
var/fallen_offset_x = 1
var/fallen_offset_z = -6
/// we want to use Z rather than Y incase anything gets rotated, it would look all jank
var/monkey_clothes = 0
// it's clothes specifically for monkeys please don't plaster it to their chest with an offset
stamina_damage = 1
stamina_cost = 1
stamina_crit_chance = 0
flags = FPRINT | TABLEPASS
onMaterialChanged()
..()
if(istype(src.material))
protective_temperature = material.hasProperty(PROP_MELTING) ? material.getProperty(PROP_MELTING) : protective_temperature
protective_temperature -= material.getProperty(PROP_FLAMMABILITY) * 10
heat_transfer_coefficient = material.hasProperty(PROP_THERMAL) ? material.getProperty(PROP_THERMAL) / 100 : heat_transfer_coefficient
permeability_coefficient = material.hasProperty(PROP_PERMEABILITY) ? material.getProperty(PROP_PERMEABILITY) / 100 : permeability_coefficient
siemens_coefficient = material.hasProperty(PROP_ELECTRICAL) ? material.getProperty(PROP_ELECTRICAL) / 100 : siemens_coefficient
disease_resistance = material.hasProperty(PROP_PERMEABILITY) ? (100 - material.getProperty(PROP_PERMEABILITY)) / 2 : 0
disease_resistance += material.getProperty(PROP_RADIOACTIVITY)
armor_value_melee = material.hasProperty(PROP_COMPRESSIVE) ? max((material.getProperty(PROP_COMPRESSIVE) - 50) / 3, 0) : armor_value_melee
armor_value_bullet = material.hasProperty(PROP_SHEAR) ? max((material.getProperty(PROP_SHEAR) - 50) / 25) + 1 : armor_value_bullet
armor_value_explosion = max(round((material.getProperty(PROP_COMPRESSIVE) + material.getProperty(PROP_TENSILE) - 50) / 20), 0)
return
/*
/obj/item/clothing/fire_burn(obj/fire/raging_fire, datum/air_group/environment)
if(raging_fire.internal_temperature > src.s_fire)
spawn( 0 )
var/t = src.icon_state
src.icon_state = ""
src.icon = 'b_items.dmi'
flick(text("[]", t), src)
spawn(14)
qdel(src)
return
return
return 0
return 1
*/ //TODO FIX

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