Merge branch 'master' of https://github.com/ParadiseSS13/Paradise into EXTERMINATUSPARTONE

This commit is contained in:
Aurorablade
2019-01-29 17:42:39 -05:00
198 changed files with 5111 additions and 3030 deletions
+1 -1
View File
@@ -137,7 +137,7 @@ datum/admins/proc/DB_ban_record(var/bantype, var/mob/banned_mob, var/duration =
message_admins("[key_name_admin(usr)] has added a [bantype_str] for [ckey] [(job)?"([job])":""] [(duration > 0)?"([duration] minutes)":""] with the reason: \"[reason]\" to the ban database.",1)
if(announceinirc)
send2irc("BAN ALERT","[a_ckey] applied a [bantype_str] on [ckey]")
send2discord("message", config.discord_channel_admin,"BAN ALERT","[a_ckey] applied a [bantype_str] on [ckey]")
if(kickbannedckey)
if(banned_mob && banned_mob.client && banned_mob.client.ckey == banckey)
+2 -1
View File
@@ -2,7 +2,8 @@
var/list/admin_verbs_default = list(
/client/proc/deadmin_self, /*destroys our own admin datum so we can play as a regular player*/
/client/proc/hide_verbs, /*hides all our adminverbs*/
/client/proc/toggleadminhelpsound, /*toggles whether we hear bwoinks*/
/client/proc/toggleadminhelpsound,
/client/proc/togglementorhelpsound,
/client/proc/cmd_mentor_check_new_players,
/client/proc/cmd_mentor_check_player_exp /* shows players by playtime */
)
+7 -7
View File
@@ -108,7 +108,7 @@ var/list/adminhelp_ignored_words = list("unknown","the","a","an","of","monkey","
if("Mentorhelp")
msg = "<span class='mentorhelp'>[selected_type]: </span><span class='boldnotice'>[key_name(src, TRUE, selected_type)] ([ADMIN_QUE(mob,"?")]) ([ADMIN_PP(mob,"PP")]) ([ADMIN_VV(mob,"VV")]) ([ADMIN_SM(mob,"SM")]) ([admin_jump_link(mob)]) (<A HREF='?_src_=holder;check_antagonist=1'>CA</A>) (<A HREF='?_src_=holder;rejectadminhelp=[UID()]'>REJT</A>) [ai_found ? " (<A HREF='?_src_=holder;adminchecklaws=[mob.UID()]'>CL</A>)" : ""] (<A HREF='?_src_=holder;take_question=[mob.UID()];is_mhelp=1'>TAKE</A>) :</span> <span class='mentorhelp'>[msg]</span>"
for(var/client/X in mentorholders + modholders + adminholders)
if(X.prefs.sound & SOUND_ADMINHELP)
if(X.prefs.sound & SOUND_MENTORHELP)
X << 'sound/effects/adminhelp.ogg'
to_chat(X, msg)
if("Adminhelp")
@@ -136,15 +136,15 @@ var/list/adminhelp_ignored_words = list("unknown","the","a","an","of","monkey","
log_admin("[selected_type]: [key_name(src)]: [original_msg] - heard by [admin_number_present] non-AFK admins.")
if(admin_number_present <= 0)
if(!admin_number_afk)
send2adminirc("[selected_type] from [key_name(src)]: [original_msg] - !!No admins online!!")
send2admindiscord("[selected_type] from [key_name(src)]: [original_msg] - !!No admins online!!")
else
send2adminirc("[selected_type] from [key_name(src)]: [original_msg] - !!All admins AFK ([admin_number_afk])!!")
send2admindiscord("[selected_type] from [key_name(src)]: [original_msg] - !!All admins AFK ([admin_number_afk])!!")
else
send2adminirc("[selected_type] from [key_name(src)]: [original_msg]")
send2admindiscord("[selected_type] from [key_name(src)]: [original_msg]")
feedback_add_details("admin_verb","AH") //If you are copy-pasting this, ensure the 2nd parameter is unique to the new proc!
return
/proc/send2irc_adminless_only(source, msg, requiredflags = R_BAN)
/proc/send2discord_adminless_only(source, msg, requiredflags = R_BAN)
var/admin_number_total = 0 //Total number of admins
var/admin_number_afk = 0 //Holds the number of admins who are afk
var/admin_number_ignored = 0 //Holds the number of admins without +BAN (so admins who are not really admins)
@@ -166,7 +166,7 @@ var/list/adminhelp_ignored_words = list("unknown","the","a","an","of","monkey","
var/admin_number_present = admin_number_total - admin_number_decrease //Number of admins who are neither afk nor invalid
if(admin_number_present <= 0)
if(!admin_number_afk && !admin_number_ignored)
send2irc(source, "[msg] - No admins online")
send2discord("message", source, "[msg] - No admins online")
else
send2irc(source, "[msg] - All admins AFK ([admin_number_afk]/[admin_number_total]) or skipped ([admin_number_ignored]/[admin_number_total])")
send2discord("message", source, "[msg] - All admins AFK ([admin_number_afk]/[admin_number_total]) or skipped ([admin_number_ignored]/[admin_number_total])")
return admin_number_present
+3
View File
@@ -71,6 +71,9 @@
var/turf/T = locate(tx, ty, tz)
if(T)
admin_forcemove(usr, T)
if(isobserver(usr))
var/mob/dead/observer/O = usr
O.ManualFollow(T)
feedback_add_details("admin_verb","JC") //If you are copy-pasting this, ensure the 2nd parameter is unique to the new proc!
if(!isobserver(usr))
message_admins("[key_name_admin(usr)] jumped to coordinates [tx], [ty], [tz]")
+1 -1
View File
@@ -218,7 +218,7 @@
to_chat(src, "<span class='notice'>[msg]</span>")
return
send2adminirc("PlayerPM from [key_name(src)]: [html_decode(msg)]")
send2admindiscord("PlayerPM from [key_name(src)]: [html_decode(msg)]")
to_chat(src, "<font color='blue'>IRC PM to-<b>IRC-Admins</b>: [msg]</font>")
+1
View File
@@ -119,6 +119,7 @@ var/global/sent_honksquad = 0
equip_to_slot_or_del(new /obj/item/stamp/clown(src), slot_in_backpack)
equip_to_slot_or_del(new /obj/item/toy/crayon/rainbow(src), slot_in_backpack)
equip_to_slot_or_del(new /obj/item/reagent_containers/spray/waterflower(src), slot_in_backpack)
equip_to_slot_or_del(new /obj/item/reagent_containers/food/pill/patch/jestosterone(src), slot_r_store)
if(prob(50))
equip_to_slot_or_del(new /obj/item/gun/energy/clown(src), slot_in_backpack)
else
@@ -85,14 +85,13 @@ var/global/sent_syndicate_strike_team = 0
to_chat(new_syndicate_commando, "<span class='notice'>You are an Elite Syndicate [is_leader ? "<B>TEAM LEADER</B>" : "commando"] in the service of the Syndicate. \nYour current mission is: <span class='userdanger'>[input]</span></span>")
new_syndicate_commando.faction += "syndicate"
var/datum/atom_hud/antag/opshud = huds[ANTAG_HUD_OPS]
opshud.join_hud(new_syndicate_commando.mind.current)
set_antag_hud(new_syndicate_commando.mind.current, "hudoperative")
new_syndicate_commando.regenerate_icons()
is_leader = FALSE
syndicate_commando_number--
for(var/obj/effect/landmark/L in GLOB.landmarks_list)
if(L.name == "Syndicate-Commando-Bomb")
new /obj/effect/spawner/newbomb/timer/syndicate(L.loc)
qdel(L)
message_admins("<span class='notice'>[key_name_admin(usr)] has spawned a Syndicate strike squad.</span>", 1)
log_admin("[key_name(usr)] used Spawn Syndicate Squad.")
feedback_add_details("admin_verb","SDTHS") //If you are copy-pasting this, ensure the 2nd parameter is unique to the new proc!
@@ -122,49 +121,46 @@ var/global/sent_syndicate_strike_team = 0
qdel(spawn_location)
return new_syndicate_commando
/mob/living/carbon/human/proc/equip_syndicate_commando(is_leader = FALSE)
/mob/living/carbon/human/proc/equip_syndicate_commando(is_leader = FALSE, full_gear = FALSE)
var/obj/item/radio/R = new /obj/item/radio/headset/syndicate/alt/syndteam(src)
R.set_frequency(SYNDTEAM_FREQ)
equip_to_slot_or_del(R, slot_l_ear)
equip_to_slot_or_del(new /obj/item/clothing/under/syndicate(src), slot_w_uniform)
equip_to_slot_or_del(new /obj/item/clothing/shoes/magboots/syndie/advance(src), slot_shoes)
if(is_leader)
equip_to_slot_or_del(new /obj/item/clothing/suit/space/syndicate/black/red/strike(src), slot_wear_suit)
else
equip_to_slot_or_del(new /obj/item/clothing/suit/space/syndicate/black/strike(src), slot_wear_suit)
if(!full_gear)
equip_to_slot_or_del(new /obj/item/clothing/shoes/combat(src), slot_shoes)
equip_to_slot_or_del(new /obj/item/clothing/gloves/combat(src), slot_gloves)
if(is_leader)
equip_to_slot_or_del(new /obj/item/clothing/head/helmet/space/syndicate/black/red/strike(src), slot_head)
else
equip_to_slot_or_del(new /obj/item/clothing/head/helmet/space/syndicate/black/strike(src), slot_head)
equip_to_slot_or_del(new /obj/item/clothing/mask/gas/syndicate(src), slot_wear_mask)
equip_to_slot_or_del(new /obj/item/clothing/glasses/thermal(src), slot_glasses)
equip_to_slot_or_del(new /obj/item/storage/backpack/security(src), slot_back)
equip_to_slot_or_del(new /obj/item/ammo_box/magazine/mm556x45)
equip_to_slot_or_del(new /obj/item/storage/box/survival_syndi(src), slot_in_backpack)
equip_to_slot_or_del(new /obj/item/ammo_box/magazine/m45(src), slot_in_backpack)
equip_to_slot_or_del(new /obj/item/gun/projectile/revolver(src), slot_in_backpack)
equip_to_slot_or_del(new /obj/item/ammo_box/a357(src), slot_in_backpack)
equip_to_slot_or_del(new /obj/item/reagent_containers/hypospray/combat/nanites(src), slot_in_backpack)
equip_to_slot_or_del(new /obj/item/grenade/plastic/x4(src), slot_in_backpack)
equip_to_slot_or_del(new /obj/item/flashlight(src), slot_in_backpack)
if(is_leader)
equip_to_slot_or_del(new /obj/item/pinpointer(src), slot_in_backpack)
equip_to_slot_or_del(new /obj/item/disk/nuclear(src), slot_in_backpack)
else
equip_to_slot_or_del(new /obj/item/grenade/plastic/x4(src), slot_in_backpack)
equip_to_slot_or_del(new /obj/item/card/emag(src), slot_in_backpack)
equip_to_slot_or_del(new /obj/item/melee/energy/sword/saber(src), slot_l_store)
equip_to_slot_or_del(new /obj/item/grenade/empgrenade(src), slot_r_store)
equip_to_slot_or_del(new /obj/item/tank/emergency_oxygen/double/full(src), slot_s_store)
equip_to_slot_or_del(new /obj/item/gun/projectile/automatic/pistol/m1911(src), slot_belt)
equip_to_slot_or_del(new /obj/item/card/emag(src), slot_r_store)
equip_to_slot_or_del(new /obj/item/melee/energy/sword/saber/red(src), slot_l_store)
equip_to_slot_or_del(new /obj/item/gun/projectile/automatic/l6_saw(src), slot_r_hand)
if(full_gear)
equip_to_slot_or_del(new /obj/item/clothing/head/helmet/space/hardsuit/syndi/elite/sst(src), slot_head)
equip_to_slot_or_del(new /obj/item/clothing/mask/gas/syndicate(src), slot_wear_mask)
equip_to_slot_or_del(new /obj/item/clothing/suit/space/hardsuit/syndi/elite/sst(src), slot_wear_suit)
equip_to_slot_or_del(new /obj/item/clothing/glasses/thermal(src), slot_glasses)
equip_to_slot_or_del(new /obj/item/storage/belt/military/sst(src), slot_belt)
equip_to_slot_or_del(new /obj/item/tank/jetpack/oxygen/harness(src), slot_s_store)
equip_to_slot_or_del(new /obj/item/clothing/shoes/magboots/syndie/advance(src), slot_shoes)
equip_to_slot_or_del(new /obj/item/gun/projectile/automatic/l6_saw(src), slot_r_hand)
equip_to_slot_or_del(new /obj/item/ammo_box/magazine/mm556x45(src), slot_in_backpack)
var/obj/item/implant/dust/D = new /obj/item/implant/dust(src)
D.implant(src)
var/obj/item/card/id/syndicate/W = new(src) //Untrackable by AI
W.name = "[real_name]'s ID Card"
W.icon_state = "syndie"
W.access = get_all_accesses()//They get full station access because obviously the syndicate has HAAAX, and can make special IDs for their most elite members.
W.assignment = "Syndicate Commando"
W.access += get_syndicate_access(W.assignment)
W.registered_name = real_name
+3 -3
View File
@@ -471,7 +471,7 @@
var/watchreason = check_watchlist(ckey)
if(watchreason)
message_admins("<font color='red'><B>Notice: </B></font><font color='blue'>[key_name_admin(src)] is on the watchlist and has just connected - Reason: [watchreason]</font>")
send2irc(config.admin_notify_irc, "Watchlist - [key_name(src)] is on the watchlist and has just connected - Reason: [watchreason]")
send2discord("message", config.discord_channel_admin, "Watchlist - [key_name(src)] is on the watchlist and has just connected - Reason: [watchreason]")
//Just the standard check to see if it's actually a number
@@ -570,7 +570,7 @@
if(!cidcheck_failedckeys[ckey])
message_admins("<span class='adminnotice'>[key_name(src)] has been detected as using a CID randomizer. Connection rejected.</span>")
send2irc(config.cidrandomizer_irc, "[key_name(src)] has been detected as using a CID randomizer. Connection rejected.")
send2discord("message", config.discord_channel_cidrandomizer, "[key_name(src)] has been detected as using a CID randomizer. Connection rejected.")
cidcheck_failedckeys[ckey] = TRUE
note_randomizer_user()
@@ -583,7 +583,7 @@
if(cidcheck_failedckeys[ckey])
// Atonement
message_admins("<span class='adminnotice'>[key_name_admin(src)] has been allowed to connect after showing they removed their cid randomizer</span>")
send2irc(config.cidrandomizer_irc, "[key_name(src)] has been allowed to connect after showing they removed their cid randomizer.")
send2discord("message", config.discord_channel_cidrandomizer, "[key_name(src)] has been allowed to connect after showing they removed their cid randomizer.")
cidcheck_failedckeys -= ckey
if (cidcheck_spoofckeys[ckey])
message_admins("<span class='adminnotice'>[key_name_admin(src)] has been allowed to connect after appearing to have attempted to spoof a cid randomizer check because it <i>appears</i> they aren't spoofing one this time</span>")
@@ -46,6 +46,17 @@
to_chat(usr, "You will [(prefs.sound & SOUND_ADMINHELP) ? "now" : "no longer"] hear a sound when adminhelps arrive.")
feedback_add_details("admin_verb","AHS") //If you are copy-pasting this, ensure the 2nd parameter is unique to the new proc!
/client/proc/togglementorhelpsound()
set name = "Hear/Silence Mentorhelp Bwoinks"
set category = "Preferences"
set desc = "Toggle hearing a notification when mentorhelps are recieved"
if(!holder)
return
prefs.sound ^= SOUND_MENTORHELP
prefs.save_preferences(src)
to_chat(usr, "You will [(prefs.sound & SOUND_MENTORHELP) ? "now" : "no longer"] hear a sound when mentorhelps arrive.")
feedback_add_details("admin_verb","MHS") //If you are copy-pasting this, ensure the 2nd parameter is unique to the new proc!
/client/verb/deadchat() // Deadchat toggle is usable by anyone.
set name = "Show/Hide Deadchat"
set category = "Preferences"
@@ -462,6 +462,16 @@
name = "elite syndicate hardsuit (combat)"
desc = "An elite version of the syndicate hardsuit, with improved armour and fire shielding. It is in combat mode. Property of Gorlex Marauders."
//Strike team hardsuits
/obj/item/clothing/head/helmet/space/hardsuit/syndi/elite/sst
armor = list(melee = 70, bullet = 70, laser = 50, energy = 40, bomb = 80, bio = 100, rad = 100) //Almost as good as DS gear, but unlike DS can switch to combat for mobility
icon_state = "hardsuit0-sst"
item_color = "sst"
/obj/item/clothing/suit/space/hardsuit/syndi/elite/sst
armor = list(melee = 70, bullet = 70, laser = 50, energy = 40, bomb = 80, bio = 100, rad = 100)
icon_state = "hardsuit0-sst"
item_color = "sst"
/obj/item/clothing/suit/space/hardsuit/syndi/freedom
name = "eagle suit"
+15 -1
View File
@@ -6,7 +6,7 @@
var/time = 30 //time in deciseconds
var/parts[] = list() //type paths of items that will be placed in the result
var/chem_catalysts[] = list() //like tools but for reagents
var/category = CAT_MISC // Recipe category
var/category = CAT_NONE // Recipe category
var/roundstart_enabled = TRUE //Set to FALSE if you don't want a particular crafting recipe to be available all the time
/datum/crafting_recipe/proc/AdjustChems(var/obj/resultobj as obj)
@@ -90,6 +90,17 @@
time = 40
category = CAT_ROBOT
/datum/crafting_recipe/honkbot
name = "Honkbot"
result = /mob/living/simple_animal/bot/honkbot
reqs = list(/obj/item/robot_parts/r_arm = 1,
/obj/item/bikehorn = 1,
/obj/item/assembly/prox_sensor = 1,
/obj/item/storage/box/clown = 1,
/obj/item/instrument/trombone = 1)
time = 40
category = CAT_ROBOT
/datum/crafting_recipe/floorbot
name = "Floorbot"
result = /mob/living/simple_animal/bot/floorbot
@@ -240,6 +251,7 @@
reqs = list(/obj/item/camera = 1,
/datum/reagent/holywater = 10)
parts = list(/obj/item/camera = 1)
category = CAT_MISC
/datum/crafting_recipe/papersack
name = "Paper Sack"
@@ -262,6 +274,7 @@
time = 50
reqs = list(/obj/item/stack/tape_roll = 1,
/datum/reagent/liquidgibs = 10)
category = CAT_MISC
/datum/crafting_recipe/garrote
name = "Makeshift Garrote"
@@ -298,6 +311,7 @@
time = 15
reqs = list(/obj/item/clothing/gloves/color/latex = 1,
/obj/item/stack/cable_coil = 5)
category = CAT_MISC
/datum/crafting_recipe/gold_horn
name = "Golden bike horn"
+23
View File
@@ -900,6 +900,13 @@
body_parts_covered = UPPER_TORSO|LOWER_TORSO|LEGS|ARMS
icon_state = "dusty_jacket"
/obj/item/clothing/suit/fluff/cheeky_sov_coat //CheekyCrenando: Srusu Rskuzu
name = "Srusu's Greatcoat"
desc = "A heavy wool Soviet-style greatcoat. A name is written in fancy handwriting on the inside tag: Srusu Rskuzu"
icon = 'icons/obj/custom_items.dmi'
item_state = "cheeky_sov_coat"
icon_state = "cheeky_sov_coat"
/obj/item/clothing/suit/fluff/supplymaster_jacket //Denthamos: Henry Grandpa Gadow
name = "faded NT Supply Master's Coat"
desc = "A faded leather overcoat bearing a worn out badge from the NAS Crescent on the shoulder, and a designation tag of Supply Master on the front. A tarnished gold nameplate says H.Gadow on it."
@@ -984,6 +991,14 @@
species_fit = null
sprite_sheets = null
/obj/item/clothing/suit/storage/labcoat/fluff/ionward_labcoat // Ionward: Gemini
name = "Technocracy labcoat"
desc = "A thin, faded, carbon fiber labcoat. On the back, a Technocracy vessel's logo. Inside, the name 'Gemini' is printed on the collar."
icon = 'icons/obj/custom_items.dmi'
icon_state = "ionward_labcoat_open"
species_fit = null
sprite_sheets = null
/obj/item/clothing/suit/fluff/stobarico_greatcoat // Stobarico: F.U.R.R.Y
name = "\improper F.U.R.R.Y's Nanotrasen Greatcoat"
desc = "A greatcoat with Nanotrasen colors."
@@ -1604,3 +1619,11 @@
icon_state = "asmer_accordion"
item_state = "asmer_accordion"
/obj/item/clothing/head/rabbitears/fluff/pinesalad_bunny // Pineapple Salad : Dan Jello
name = "Bluespace rabbit ears"
desc = "A pair of sparkly bluespace rabbit ears, with a small tag on them that reads, 'Dan Jello~'. Yuck, \
there's some pink slime on the part that goes on your head!"
icon = 'icons/obj/custom_items.dmi'
icon_state = "ps_bunny"
@@ -21,6 +21,7 @@
can_be_placed_into = null
flags = NOBLUDGEON
container_type = OPENCONTAINER
has_lid = FALSE
var/wipespeed = 30
/obj/item/reagent_containers/glass/rag/attack(atom/target as obj|turf|area, mob/user as mob , flag)
+18
View File
@@ -0,0 +1,18 @@
/proc/send2discord(command, channel, message)
if (config.use_discord_bot && config.discord_host)
world.Export("http://[config.discord_host]/?command=[command]&channel=[channel]&message=[paranoid_sanitize(message)]")
/proc/send2maindiscord(message)
if(config.discord_channel_main)
send2discord("message", config.discord_channel_main, message)
return
/proc/send2admindiscord(message)
if(config.discord_channel_admin)
send2discord("message", config.discord_channel_admin, message)
return
/hook/startup/proc/discordNotify()
if(config.discord_channel_main)
send2discord("startup", config.discord_channel_main, "Server starting up on [station_name()]. Connect to: [config.server? "[config.server]" : "[world.address]:[world.port]"]")
return 1
-21
View File
@@ -1,21 +0,0 @@
/proc/send2irc(var/channel, var/msg)
if(config.use_irc_bot && config.irc_bot_host.len)
for(var/IP in config.irc_bot_host)
spawn(0)
// I have no means of trusting you, cmd
ext_python("ircbot_message.py", "[config.comms_password] [IP] [channel] [paranoid_sanitize(msg)]")
return
/proc/send2mainirc(var/msg)
if(config.main_irc)
send2irc(config.main_irc, msg)
return
/proc/send2adminirc(var/msg)
if(config.admin_irc)
send2irc(config.admin_irc, msg)
return
/hook/startup/proc/ircNotify()
send2mainirc("Server starting up on [station_name()]. Connect to: [config.server? "[config.server]" : "[world.address]:[world.port]"]")
return 1
+2 -2
View File
@@ -817,9 +817,9 @@ var/list/non_fakeattack_weapons = list(/obj/item/gun/projectile, /obj/item/ammo_
playsound_local(null, 'sound/voice/bfreeze.ogg', 35, 0)
if(9)
//To make it more realistic, I added two gunshots (enough to kill)
playsound_local(null, 'sound/weapons/gunshot.ogg', 25, 1)
playsound_local(null, 'sound/weapons/gunshots/gunshot.ogg', 25, 1)
var/timer_pause = rand(10,30)
addtimer(CALLBACK(GLOBAL_PROC, .proc/playsound_local, null, 'sound/weapons/gunshot.ogg', 25, 1), timer_pause)
addtimer(CALLBACK(GLOBAL_PROC, .proc/playsound_local, null, 'sound/weapons/gunshots/gunshot.ogg', 25, 1), timer_pause)
addtimer(CALLBACK(GLOBAL_PROC, .proc/playsound_local, null, sound(get_sfx("bodyfall"), 25), 25, 1), timer_pause+rand(5,10))
if(10)
playsound_local(null, 'sound/effects/pray_chaplain.ogg', 50)
@@ -345,7 +345,7 @@
/obj/item/reagent_containers/food/snacks/donut/sprinkles
name = "frosted donut"
icon_state = "donut2"
list_reagents = list("nutriment" = 3, "sugar" = 2, "spinkles" = 2)
list_reagents = list("nutriment" = 3, "sugar" = 2, "sprinkles" = 2)
filling_color = "#FF69B4"
randomized_sprinkles = 0
@@ -252,4 +252,23 @@
)
tools = list(/obj/item/kitchen/sushimat)
result = /obj/item/reagent_containers/food/snacks/sliceable/Tai_maki
category = CAT_FOOD
/datum/crafting_recipe/food
/datum/crafting_recipe/food/New()
parts |= reqs
/datum/crafting_recipe/food/cak
name = "Living cat/cake hybrid"
reqs = list(
/obj/item/organ/internal/brain = 1,
/obj/item/organ/internal/heart = 1,
/obj/item/reagent_containers/food/snacks/sliceable/birthdaycake = 1,
/obj/item/reagent_containers/food/snacks/meat = 3,
/datum/reagent/blood = 30,
/datum/reagent/consumable/sprinkles = 5,
/datum/reagent/teslium = 1,
)
result = /mob/living/simple_animal/pet/cat/cak
category = CAT_FOOD
+2
View File
@@ -219,6 +219,8 @@
var/mob/M = usr
if(M.incapacitated() || !Adjacent(M))
return
if(!ishuman(M))
return
if(over_object == M || istype(over_object, /obj/screen))
if(!remove_item_from_storage(M))
+10 -1
View File
@@ -167,8 +167,9 @@
icon_state ="book"
throw_speed = 1
throw_range = 5
force = 2
w_class = WEIGHT_CLASS_NORMAL //upped to three because books are, y'know, pretty big. (and you could hide them inside eachother recursively forever)
attack_verb = list("bashed", "whacked", "educated")
attack_verb = list("bashed", "whacked")
burn_state = FLAMMABLE
var/dat // Actual page content
@@ -283,6 +284,14 @@
else
return ..()
/obj/item/book/attack(mob/M, mob/living/user)
if(user.a_intent == INTENT_HELP)
force = 0
attack_verb = list("educated")
else
force = initial(force)
attack_verb = list("bashed", "whacked")
..()
/*
* Barcode Scanner
+1 -1
View File
@@ -34,7 +34,7 @@
ranged_message = "shoots"
ranged_cooldown_time = 30
projectiletype = /obj/item/projectile/kinetic
projectilesound = 'sound/weapons/gunshot4.ogg'
projectilesound = 'sound/weapons/gunshots/gunshot4.ogg'
speak_emote = list("states")
wanted_objects = list(/obj/item/stack/ore/diamond, /obj/item/stack/ore/gold, /obj/item/stack/ore/silver,
/obj/item/stack/ore/plasma, /obj/item/stack/ore/uranium, /obj/item/stack/ore/iron,
+12 -10
View File
@@ -70,7 +70,7 @@
sound_vol *= 0.5
if(sleeping || stat == UNCONSCIOUS)
hear_sleep(message_pieces)
hear_sleep(multilingual_to_message(message_pieces))
return 0
var/speaker_name = speaker.name
@@ -97,7 +97,7 @@
if(!can_hear())
// INNATE is the flag for audible-emote-language, so we don't want to show an "x talks but you cannot hear them" message if it's set
// if(!language || !(language.flags & INNATE))
// if(!language || !(language.flags & INNATE))
if(speaker == src)
to_chat(src, "<span class='warning'>You cannot hear yourself speak!</span>")
else
@@ -158,14 +158,16 @@
message = strip_html_properly(message)
var/list/punctuation = list(",", "!", ".", ";", "?")
var/list/messages = splittext(message, " ")
var/R = rand(1, messages.len)
var/heardword = messages[R]
if(copytext(heardword,1, 1) in punctuation)
heardword = copytext(heardword,2)
if(copytext(heardword,-1) in punctuation)
heardword = copytext(heardword,1,lentext(heardword))
heard = "<span class='game say'>...<i>You hear something about<i>... '[heardword]'...</span>"
if(messages.len > 0)
var/R = rand(1, messages.len)
var/heardword = messages[R]
if(copytext(heardword,1, 1) in punctuation)
heardword = copytext(heardword,2)
if(copytext(heardword,-1) in punctuation)
heardword = copytext(heardword,1,lentext(heardword))
heard = "<span class='game say'>...<i>You hear something about<i>... '[heardword]'...</span>"
else
heard = "<span class='game say'>...<i>You almost hear something...</i>...</span>"
else
heard = "<span class='game say'>...<i>You almost hear someone talking</i>...</span>"
@@ -92,6 +92,9 @@
return TRUE
/mob/living/carbon/human/death(gibbed)
if(can_die() && !gibbed && deathgasp_on_death)
emote("deathgasp") //let the world KNOW WE ARE DEAD
// Only execute the below if we successfully died
. = ..(gibbed)
if(!.)
+2 -4
View File
@@ -121,12 +121,10 @@
span = mind.speech_span
if((COMIC in mutations) \
|| (locate(/obj/item/organ/internal/cyberimp/brain/clown_voice) in internal_organs) \
|| istype(get_item_by_slot(slot_wear_mask), /obj/item/clothing/mask/gas/voice/clown))
|| istype(get_item_by_slot(slot_wear_mask), /obj/item/clothing/mask/gas/voice/clown) \
|| GetComponent(/datum/component/jestosterone))
span = "sans"
if(WINGDINGS in mutations)
span = "wingdings"
var/list/parent = ..()
verb = parent["verb"]
@@ -381,7 +381,6 @@
playsound(target.loc, attack.attack_sound, 25, 1, -1)
target.visible_message("<span class='danger'>[user] [pick(attack.attack_verb)]ed [target]!</span>")
target.apply_damage(damage, BRUTE, affecting, armor_block, sharp = attack.sharp) //moving this back here means Armalis are going to knock you down 70% of the time, but they're pure adminbus anyway.
if((target.stat != DEAD) && damage >= user.dna.species.punchstunthreshold)
target.visible_message("<span class='danger'>[user] has weakened [target]!</span>", \
@@ -390,6 +389,7 @@
target.forcesay(GLOB.hit_appends)
else if(target.lying)
target.forcesay(GLOB.hit_appends)
SEND_SIGNAL(target, COMSIG_PARENT_ATTACKBY)
/datum/species/proc/disarm(mob/living/carbon/human/user, mob/living/carbon/human/target, datum/martial_art/attacker_style)
if(target.check_block()) //cqc
@@ -10,7 +10,7 @@
"heart" = /obj/item/organ/internal/heart,
"liver" = /obj/item/organ/internal/liver,
"kidneys" = /obj/item/organ/internal/kidneys,
"brain" = /obj/item/organ/internal/brain,
"brain" = /obj/item/organ/internal/brain/abductor,
"appendix" = /obj/item/organ/internal/appendix,
"eyes" = /obj/item/organ/internal/eyes/abductor //3 darksight.
)
@@ -42,7 +42,7 @@
/datum/species/grey/after_equip_job(datum/job/J, mob/living/carbon/human/H)
var/translator_pref = H.client.prefs.speciesprefs
if(translator_pref || ((ismindshielded(H) || J.is_command) && (WINGDINGS in H.mutations)))
if(translator_pref || ((ismindshielded(H) || J.is_command || J.supervisors == "the captain") && (WINGDINGS in H.mutations)))
if(J.title == "Mime")
return
if(J.title == "Clown")
+2 -1
View File
@@ -508,6 +508,7 @@
var/turf/T = loc
. = ..()
if(.)
SEND_SIGNAL(src, COMSIG_MOVABLE_MOVED)
handle_footstep(loc)
step_count++
@@ -882,7 +883,7 @@
// If we're pulling something then drop what we're currently pulling and pull this instead.
AM.add_fingerprint(src)
if(pulling)
if(AM == pulling)// Are we trying to pull something we are already pulling? Then just stop here, no need to continue.
if(AM == pulling)// Are we trying to pull something we are already pulling? Then just stop here, no need to continue.
return
stop_pulling()
if(AM.pulledby)
+3 -2
View File
@@ -190,7 +190,7 @@ proc/get_radio_key_from_channel(var/channel)
message_range = 1
if(first_piece.speaking)
message_range = first_piece.speaking.get_talkinto_msg_range(message)
var/msg
if(!first_piece.speaking || !(first_piece.speaking.flags & NO_TALK_MSG))
msg = "<span class='notice'>[src] talks into [used_radios[1]]</span>"
@@ -343,6 +343,8 @@ proc/get_radio_key_from_channel(var/channel)
to_chat(src, "<span class='danger'>You're muzzled and cannot speak!</span>")
return
log_whisper(multilingual_to_message(message_pieces), src)
var/message_range = 1
var/eavesdropping_range = 2
var/watching_range = 5
@@ -445,7 +447,6 @@ proc/get_radio_key_from_channel(var/channel)
for(var/mob/M in watching)
M.show_message(rendered, 2)
log_whisper(multilingual_to_message(message_pieces), src)
return 1
/mob/living/speech_bubble(var/bubble_state = "",var/bubble_loc = src, var/list/bubble_recipients = list())
@@ -49,6 +49,9 @@
/mob/living/silicon/robot/death(gibbed)
if(can_die())
if(!gibbed && deathgasp_on_death)
emote("deathgasp")
if(module)
module.handle_death(gibbed)
@@ -408,6 +408,7 @@
..()
modules += new /obj/item/healthanalyzer/advanced(src)
modules += new /obj/item/reagent_scanner/adv(src)
modules += new /obj/item/bodyanalyzer/borg/syndicate(src)
modules += new /obj/item/borg_defib(src)
modules += new /obj/item/roller_holder(src)
modules += new /obj/item/reagent_containers/borghypo/syndicate(src)
@@ -13,7 +13,7 @@
if(INTENT_HARM, INTENT_DISARM)
M.do_attack_animation(src, ATTACK_EFFECT_PUNCH)
visible_message("<span class='danger'>[M] [response_harm] [src]!</span>")
playsound(loc, "punch", 25, 1, -1)
playsound(loc, attacked_sound, 25, 1, -1)
attack_threshold_check(harm_intent_damage)
add_attack_logs(M, src, "Melee attacked with fists")
updatehealth()
@@ -480,3 +480,56 @@
new /obj/item/robot_parts/l_arm(get_turf(src))
to_chat(user, "<span class='notice'>You remove the robot arm from [src].</span>")
build_step--
//Honkbot Assembly
/obj/item/storage/box/clown/attackby(obj/item/W, mob/user, params)
if(!istype(W, /obj/item/robot_parts/l_arm) && !istype(W, /obj/item/robot_parts/r_arm))
return ..()
if(contents.len)
to_chat(user, "<span class='warning'>You need to empty [src] out first!</span>")
return
var/obj/item/honkbot_arm_assembly/A = new /obj/item/honkbot_arm_assembly
qdel(W)
user.put_in_hands(A)
to_chat(user, "<span class='notice'>You add the robot arm to the honkbot.</span>")
user.unEquip(src, 1)
qdel(src)
/obj/item/honkbot_arm_assembly
name = "incomplete honkbot assembly."
desc = "A clown box with a robot arm permanently grafted to it."
icon = 'icons/obj/aibots.dmi'
icon_state = "honkbot_arm"
w_class = WEIGHT_CLASS_NORMAL
req_one_access = list(access_clown, access_robotics, access_mime)
var/build_step = 0
var/created_name = "Honkbot" //To preserve the name if it's a unique medbot I guess
/obj/item/honkbot_arm_assembly/attackby(obj/item/W, mob/user, params)
..()
if(build_step == 0)
if(istype(W, /obj/item/assembly/prox_sensor))
if(!user.unEquip(W))
return
build_step++
to_chat(user, "<span class='notice'>You add the proximity sensor to [src].</span>")
icon_state = "honkbot_proxy"
qdel(W)
else if(build_step == 1)
if(istype(W, /obj/item/bikehorn))
if(!user.unEquip(W))
return
build_step++
to_chat(user, "<span class='notice'>You add the bikehorn to [src]! Honk!</span>")
desc = "A clown box with a robot arm and a bikehorn permanently grafted to it. It needs a trombone to be finished"
qdel(W)
else if(build_step == 2)
if(istype(W, /obj/item/instrument/trombone))
if(!user.unEquip(W))
return
to_chat(user, "<span class='notice'>You add the trombone to [src]! Heeeenk! </span>")
qdel(W)
new /mob/living/simple_animal/bot/honkbot(get_turf(loc))
qdel(src)
@@ -0,0 +1,321 @@
/mob/living/simple_animal/bot/honkbot
name = "\improper honkbot"
desc = "A little robot. It looks happy with its bike horn."
icon = 'icons/obj/aibots.dmi'
icon_state = "honkbot"
density = FALSE
anchored = FALSE
health = 25
maxHealth = 25
damage_coeff = list(BRUTE = 0.5, BURN = 0.7, TOX = 0, CLONE = 0, STAMINA = 0, OXY = 0)
pass_flags = PASSMOB
radio_channel = "Service" //Service
bot_type = HONK_BOT
bot_filter = RADIO_HONKBOT
model = "Honkbot"
bot_core_type = /obj/machinery/bot_core/honkbot
window_id = "autohonk"
window_name = "Honkomatic Bike Horn Unit v1.0.7"
data_hud_type = DATA_HUD_SECURITY_BASIC // show jobs
path_image_color = "#FF69B4"
var/honksound = 'sound/items/bikehorn.ogg' //customizable sound
var/spam_flag = FALSE
var/cooldowntime = 30
var/cooldowntimehorn = 10
var/mob/living/carbon/target
var/oldtarget_name
var/target_lastloc = FALSE //Loc of target when arrested.
var/last_found = FALSE //There's a delay
var/threatlevel = FALSE
var/arrest_type = FALSE
/obj/machinery/bot_core/honkbot
req_one_access = list(access_clown, access_robotics, access_mime)
/mob/living/simple_animal/bot/honkbot/Initialize()
. = ..()
update_icon()
auto_patrol = TRUE
var/datum/job/clown/J = new/datum/job/clown
access_card.access += J.get_access()
prev_access = access_card.access
/mob/living/simple_animal/bot/honkbot/proc/spam_flag_false() //used for addtimer
spam_flag = FALSE
/mob/living/simple_animal/bot/honkbot/proc/sensor_blink()
icon_state = "honkbot-c"
addtimer(CALLBACK(src, .proc/update_icon), 5, TIMER_OVERRIDE|TIMER_UNIQUE)
//honkbots react with sounds.
/mob/living/simple_animal/bot/honkbot/proc/react_ping()
playsound(src, 'sound/machines/ping.ogg', 50, TRUE, -1) //the first sound upon creation!
spam_flag = TRUE
sensor_blink()
addtimer(CALLBACK(src, .proc/spam_flag_false), 18) // calibrates before starting the honk
/mob/living/simple_animal/bot/honkbot/proc/react_buzz()
playsound(src, 'sound/machines/buzz-sigh.ogg', 50, TRUE, -1)
sensor_blink()
/mob/living/simple_animal/bot/honkbot/bot_reset()
..()
target = null
oldtarget_name = null
anchored = FALSE
walk_to(src, 0)
last_found = world.time
spam_flag = FALSE
/mob/living/simple_animal/bot/honkbot/set_custom_texts()
text_hack = "You overload [name]'s sound control system"
text_dehack = "You reboot [name] and restore the sound control system."
text_dehack_fail = "[name] refuses to accept your authority!"
/mob/living/simple_animal/bot/honkbot/get_controls(mob/user)
var/dat
dat += hack(user)
dat += showpai(user)
dat += text({"
<TT><B>Honkomatic Bike Horn Unit v1.0.7 controls</B></TT><BR><BR>
Status: []<BR>
Behaviour controls are [locked ? "locked" : "unlocked"]<BR>
Maintenance panel is [open ? "opened" : "closed"]<BR>"},
"<A href='?src=[UID()];power=1'>[on ? "On" : "Off"]</A>")
if(!locked || issilicon(user) || user.can_admin_interact())
dat += "Auto Patrol <A href='?src=[UID()];operation=patrol'>[auto_patrol ? "On" : "Off"]</A><BR>"
return dat
/mob/living/simple_animal/bot/honkbot/proc/retaliate(mob/living/carbon/human/H)
threatlevel = H.assess_threat(src)
threatlevel += 6
if(threatlevel >= 4)
target = H
mode = BOT_HUNT
/mob/living/simple_animal/bot/honkbot/attack_hand(mob/living/carbon/human/H)
if(H.a_intent == INTENT_HARM)
retaliate(H)
addtimer(CALLBACK(src, .proc/react_buzz), 5)
return ..()
/mob/living/simple_animal/bot/honkbot/emag_act(mob/user)
..()
if(emagged == 2)
if(user)
to_chat(user, "<span class='warning'>You short out [src]'s target assessment circuits. It gives out an evil laugh!!</span>")
oldtarget_name = user.name
audible_message("<span class='danger'>[src] gives out an evil laugh!</span>")
playsound(src, 'sound/machines/honkbot_evil_laugh.ogg', 75, 1, -1) // evil laughter
update_icon()
/mob/living/simple_animal/bot/honkbot/bullet_act(obj/item/projectile/Proj)
if((istype(Proj,/obj/item/projectile/beam)) || (istype(Proj,/obj/item/projectile/bullet) && (Proj.damage_type == BURN))||(Proj.damage_type == BRUTE) && (!Proj.nodamage && Proj.damage < health && ishuman(Proj.firer)))
retaliate(Proj.firer)
..()
/mob/living/simple_animal/bot/honkbot/UnarmedAttack(atom/A)
if(!on)
return
if(iscarbon(A))
var/mob/living/carbon/C = A
if(emagged <= 1)
honk_attack(A)
else
if(!C.stunned || arrest_type) //originaly was paralisysed in tg ported as stun
stun_attack(A)
..()
else if(!spam_flag) //honking at the ground
bike_horn(A)
/mob/living/simple_animal/bot/honkbot/hitby(atom/movable/AM, skipcatch = FALSE, hitpush = TRUE, blocked = FALSE, datum/thrownthing/throwingdatum)
if(istype(AM, /obj/item))
playsound(src, honksound, 50, TRUE, -1)
var/obj/item/I = AM
if(I.throwforce < src.health && I.thrownby && ishuman(I.thrownby))
var/mob/living/carbon/human/H = I.thrownby
retaliate(H)
..()
/mob/living/simple_animal/bot/honkbot/proc/bike_horn() //use bike_horn
if(emagged <= 1)
if(!spam_flag)
playsound(src, honksound, 50, TRUE, -1)
spam_flag = TRUE //prevent spam
sensor_blink()
addtimer(CALLBACK(src, .proc/spam_flag_false), cooldowntimehorn)
else if(emagged == 2) //emagged honkbots will spam short and memorable sounds.
if(!spam_flag)
playsound(src, "honkbot_e", 50, 0)
spam_flag = TRUE // prevent spam
icon_state = "honkbot-e"
addtimer(CALLBACK(src, .proc/update_icon), 30, TIMER_OVERRIDE|TIMER_UNIQUE)
addtimer(CALLBACK(src, .proc/spam_flag_false), cooldowntimehorn)
/mob/living/simple_animal/bot/honkbot/proc/honk_attack(mob/living/carbon/C) // horn attack
if(!spam_flag)
playsound(loc, honksound, 50, TRUE, -1)
spam_flag = TRUE // prevent spam
sensor_blink()
addtimer(CALLBACK(src, .proc/spam_flag_false), cooldowntimehorn)
/mob/living/simple_animal/bot/honkbot/proc/stun_attack(mob/living/carbon/C) // airhorn stun
if(!spam_flag)
playsound(src, 'sound/items/AirHorn.ogg', 100, TRUE, -1) //HEEEEEEEEEEEENK!!
sensor_blink()
if(!spam_flag)
if(ishuman(C))
C.stuttering = 20 //stammer
C.MinimumDeafTicks(0, 5) //far less damage than the H.O.N.K.
C.Jitter(50)
C.Weaken(5)
C.Stun(5) // Paralysis from tg ported as stun
if(client) //prevent spam from players..
spam_flag = TRUE
if(emagged <= 1) //HONK once, then leave
threatlevel -= 6
target = oldtarget_name
else // you really don't want to hit an emagged honkbot
threatlevel = 6 // will never let you go
addtimer(CALLBACK(src, .proc/spam_flag_false), cooldowntime)
add_attack_logs(src, C, "honked by [src]")
C.visible_message("<span class='danger'>[src] has honked [C]!</span>",\
"<span class='userdanger'>[src] has honked you!</span>")
else
C.stuttering = 20
C.Stun(10)
addtimer(CALLBACK(src, .proc/spam_flag_false), cooldowntime)
/mob/living/simple_animal/bot/honkbot/handle_automated_action()
if(!..())
return
switch(mode)
if(BOT_IDLE) // idle
walk_to(src, 0)
look_for_perp()
if(!mode && auto_patrol)
mode = BOT_START_PATROL
if(BOT_HUNT)
// if can't reach perp for long enough, go idle
if(frustration >= 5) //gives up easier than beepsky
walk_to(src, 0)
back_to_idle()
return
if(target) // make sure target exists
if(Adjacent(target) && isturf(target.loc))
if(threatlevel <= 4)
honk_attack(target)
else
if(threatlevel >= 6)
set waitfor = 0
stun_attack(target)
anchored = FALSE
target_lastloc = target.loc
return
else // not next to perp
var/turf/olddist = get_dist(src, target)
walk_to(src, target, 1, 4)
if((get_dist(src, target)) >= (olddist))
frustration++
else
frustration = 0
else
back_to_idle()
if(BOT_START_PATROL)
look_for_perp()
start_patrol()
if(BOT_PATROL)
look_for_perp()
bot_patrol()
return
/mob/living/simple_animal/bot/honkbot/proc/back_to_idle()
anchored = FALSE
mode = BOT_IDLE
target = null
last_found = world.time
frustration = 0
INVOKE_ASYNC(src, .proc/handle_automated_action) //responds quickly
/mob/living/simple_animal/bot/honkbot/proc/back_to_hunt()
anchored = FALSE
frustration = 0
mode = BOT_HUNT
INVOKE_ASYNC(src, .proc/handle_automated_action) // responds quickly
/mob/living/simple_animal/bot/honkbot/proc/look_for_perp()
anchored = FALSE
for(var/mob/living/carbon/C in view(7, src))
if((C.stat) || (C.handcuffed))
continue
if((C.name == oldtarget_name) && (world.time < last_found + 100))
continue
if(threatlevel <= 3)
if(C in view(4, src)) //keep the range short for patrolling
if(!spam_flag)
bike_horn()
else if(threatlevel >= 10)
bike_horn() //just spam the shit outta this
else if(threatlevel >= 4)
if(!spam_flag)
target = C
oldtarget_name = C.name
bike_horn()
speak("Honk!")
visible_message("<b>[src]</b> starts chasing [C.name]!")
mode = BOT_HUNT
INVOKE_ASYNC(src, .proc/handle_automated_action)
break
else
continue
/mob/living/simple_animal/bot/honkbot/explode()
walk_to(src, 0)
visible_message("<span class='boldannounce'>[src] blows apart!</span>")
var/turf/Tsec = get_turf(src)
//doesn't drop cardboard nor its assembly, since its a very frail material.
if(prob(50))
new /obj/item/robot_parts/r_arm(Tsec)
new /obj/item/bikehorn(Tsec)
new /obj/item/assembly/prox_sensor(Tsec)
var/datum/effect_system/spark_spread/s = new
s.set_up(3, 1, src)
s.start()
..()
/mob/living/simple_animal/bot/honkbot/attack_alien(var/mob/living/carbon/alien/user as mob)
..()
if(!isalien(target))
target = user
mode = BOT_HUNT
/mob/living/simple_animal/bot/honkbot/Crossed(atom/movable/AM)
if(ismob(AM) && on) //only if its online
if(prob(30)) //you're far more likely to trip on a honkbot
var/mob/living/carbon/C = AM
if(!istype(C) || !C || in_range(src, target))
return
C.visible_message("<span class='warning'>[pick( \
"[C] dives out of [src]'s way!", \
"[C] stumbles over [src]!", \
"[C] jumps out of [src]'s path!", \
"[C] trips over [src] and falls!", \
"[C] topples over [src]!", \
"[C] leaps out of [src]'s way!")]</span>")
C.Weaken(5)
playsound(loc, 'sound/misc/sadtrombone.ogg', 50, 1, -1)
if(!client)
speak("Honk!")
sensor_blink()
return
..()
@@ -177,3 +177,57 @@
minbodytemp = 0
melee_damage_lower = 5
melee_damage_upper = 15
/mob/living/simple_animal/pet/cat/cak
name = "Keeki"
desc = "It's a cat made out of cake."
icon_state = "cak"
icon_living = "cak"
icon_resting = "cak_rest"
icon_dead = "cak_dead"
health = 50
maxHealth = 50
harm_intent_damage = 10
butcher_results = list(
/obj/item/organ/internal/brain = 1,
/obj/item/organ/internal/heart = 1,
/obj/item/reagent_containers/food/snacks/birthdaycakeslice = 3,
/obj/item/reagent_containers/food/snacks/meat/slab = 2
)
response_harm = "takes a bite out of"
attacked_sound = "sound/items/eatfood.ogg"
deathmessage = "loses its false life and collapses!"
death_sound = "bodyfall"
/mob/living/simple_animal/pet/cat/cak/Life()
..()
if(stat)
return
if(health < maxHealth)
adjustBruteLoss(-4)
for(var/obj/item/reagent_containers/food/snacks/donut/D in range(1, src))
if(D.icon_state != "donut2")
D.name = "frosted donut"
D.icon_state = "donut2"
D.reagents.add_reagent("sprinkles", 2)
D.filling_color = "#FF69B4"
/mob/living/simple_animal/pet/cat/cak/attack_hand(mob/living/L)
..()
if(L.a_intent == INTENT_HARM && L.reagents && !stat)
L.reagents.add_reagent("nutriment", 0.4)
L.reagents.add_reagent("vitamin", 0.4)
/mob/living/simple_animal/pet/cat/cak/CheckParts(list/parts)
..()
var/obj/item/organ/internal/brain/B = locate(/obj/item/organ/internal/brain) in contents
if(!B || !B.brainmob || !B.brainmob.mind)
return
B.brainmob.mind.transfer_to(src)
to_chat(src, "<span class='big bold'>You are a cak!</span><b> You're a harmless cat/cake hybrid that everyone loves. People can take bites out of you if they're hungry, but you regenerate health \
so quickly that it generally doesn't matter. You're remarkably resilient to any damage besides this and it's hard for you to really die at all. You should go around and bring happiness and \
free cake to the station!</b>")
var/new_name = stripped_input(src, "Enter your name, or press \"Cancel\" to stick with Keeki.", "Name Change")
if(new_name)
to_chat(src, "<span class='notice'>Your name is now <b>\"[new_name]\"</b>!</span>")
name = new_name
@@ -5,6 +5,7 @@
icon_state = "mouse_gray"
icon_living = "mouse_gray"
icon_dead = "mouse_gray_dead"
icon_resting = "mouse_gray_sleep"
speak = list("Squeek!","SQUEEK!","Squeek?")
speak_emote = list("squeeks","squeaks","squiks")
emote_hear = list("squeeks","squeaks","squiks")
@@ -69,6 +70,7 @@
icon_state = "mouse_[mouse_color]"
icon_living = "mouse_[mouse_color]"
icon_dead = "mouse_[mouse_color]_dead"
icon_resting = "mouse_[mouse_color]_sleep"
desc = "It's a small [mouse_color] rodent, often seen hiding in maintenance areas and making a nuisance of itself."
/mob/living/simple_animal/mouse/proc/splat()
@@ -121,7 +123,7 @@
if(on_CD == 1)
return
switch(act)
if("squeak")
message = "<B>\The [src]</B> squeaks!"
@@ -207,4 +209,16 @@
/mob/living/simple_animal/mouse/blobinfected/get_scooped(mob/living/carbon/grabber)
to_chat(grabber, "<span class='warning'>You try to pick up [src], but they slip out of your grasp!</span>")
to_chat(src, "<span class='warning'>[src] tries to pick you up, but you wriggle free of their grasp!</span>")
to_chat(src, "<span class='warning'>[src] tries to pick you up, but you wriggle free of their grasp!</span>")
/mob/living/simple_animal/mouse/fluff/clockwork
name = "Chip"
real_name = "Chip"
mouse_color = "clockwork"
icon_state = "mouse_clockwork"
response_help = "pets"
response_disarm = "gently pushes aside"
response_harm = "stamps on"
gold_core_spawnable = CHEM_MOB_SPAWN_INVALID
can_collar = 0
butcher_results = list(/obj/item/stack/sheet/metal = 1)
@@ -74,4 +74,5 @@
a_intent = INTENT_HARM
pass_flags = PASSTABLE
universal_speak = 1
universal_understand = 1
universal_understand = 1
gold_core_spawnable = CHEM_MOB_SPAWN_INVALID //badmin only
@@ -2,7 +2,7 @@
/mob/living/simple_animal/hostile/hellhound
// Sprites by FoS: http://nanotrasen.se/phpBB3/memberlist.php?mode=viewprofile&u=386
name = "Lesser Hellhound"
desc = "A horrifying, black canine monster, with glowing red eyes and vicious-looking teeth. A firey, lava-like substance drips from it."
desc = "A demonic-looking black canine monster with glowing red eyes and sharp teeth. A firey, lava-like substance drips from it."
icon_state = "hellhound"
icon_living = "hellhound"
icon_dead = "hellhound_dead"
@@ -97,7 +97,7 @@
/mob/living/simple_animal/hostile/hellhound/AttackingTarget()
. = ..()
if(ishuman(target))
if(ishuman(target) && (!client || a_intent == INTENT_HARM))
special_aoe()
/mob/living/simple_animal/hostile/hellhound/attackby(obj/item/C, mob/user, params)
@@ -117,6 +117,7 @@
/mob/living/simple_animal/hostile/hellhound/greater
name = "Greater Hellhound"
desc = "A demonic-looking black canine monster with glowing red eyes and sharp teeth. Greater hounds are far stronger than their lesser kin, and typically employed by powerful bluespace entities."
icon_state = "hellhoundgreater"
icon_living = "hellhoundgreater"
icon_resting = "hellhoundgreater_sit"
@@ -15,7 +15,7 @@
melee_damage_upper = 3
attacktext = "claws"
attack_sound = 'sound/weapons/bladeslice.ogg'
projectilesound = 'sound/weapons/gunshot.ogg'
projectilesound = 'sound/weapons/gunshots/gunshot.ogg'
projectiletype = /obj/item/projectile/hivebotbullet
faction = list("hivebot")
check_friendly_fire = 1
@@ -76,6 +76,7 @@
var/sentience_type = SENTIENCE_ORGANIC // Sentience type, for slime potions
var/list/loot = list() //list of things spawned at mob's loc when it dies
var/del_on_death = 0 //causes mob to be deleted on death, useful for mobs that spawn lootable corpses
var/attacked_sound = "punch"
var/deathmessage = ""
var/death_sound = null //The sound played on death
+1 -1
View File
@@ -13,7 +13,7 @@
message_admins("Admin logout: [key_name_admin(src)]")
var/list/admincounter = staff_countup(R_BAN)
if(admincounter[1] == 0) // No active admins
send2irc(config.admin_notify_irc, "[key_name(src)] logged out - No active admins, [admincounter[2]] non-admin staff, [admincounter[3]] inactive staff.")
send2admindiscord("[key_name(src)] logged out - No active admins, [admincounter[2]] non-admin staff, [admincounter[3]] inactive staff.")
..()
+2
View File
@@ -30,6 +30,8 @@
var/mob/M = usr
if(M.restrained() || M.stat || !Adjacent(M))
return
if(!ishuman(M))
return
if(over_object == M)
if(!remove_item_from_storage(M))
+3
View File
@@ -96,6 +96,9 @@
if(radio_controller)
radio_controller.add_object(src, control_freq, filter = bot_filter)
/obj/item/integrated_radio/honkbot
bot_filter = RADIO_HONKBOT
bot_type = HONK_BOT
/obj/item/integrated_radio/beepsky
bot_filter = RADIO_SECBOT
+1 -1
View File
@@ -1,5 +1,5 @@
/////SINGULARITY SPAWNER
/obj/machinery/the_singularitygen/
/obj/machinery/the_singularitygen
name = "Gravitational Singularity Generator"
desc = "An odd device which produces a Gravitational Singularity when set up."
icon = 'icons/obj/singularity.dmi'
@@ -126,7 +126,7 @@
if(!current_state)
log_and_message_admins(message)
if(send_to_irc)
send2adminirc(message)
send2admindiscord(message)
return TRUE
else
return FALSE
+6
View File
@@ -8,6 +8,7 @@
throwforce = 1
w_class = WEIGHT_CLASS_TINY
var/fire_sound = null //What sound should play when this ammo is fired
var/drop_sound = "casingdrop" //What sound should play when this ammo hits the ground
var/caliber = null //Which kind of guns it can be loaded into
var/projectile_type = null //The bullet type to create when New() is called
var/obj/item/projectile/BB = null //The loaded bullet
@@ -52,6 +53,7 @@
if(boolets > 0)
box.update_icon()
to_chat(user, "<span class='notice'>You collect [boolets] shell\s. [box] now contains [box.stored_ammo.len] shell\s.</span>")
playsound(src, 'sound/weapons/gun_interactions/bulletinsert.ogg', 50, 1)
else
to_chat(user, "<span class='warning'>You fail to collect anything!</span>")
else
@@ -129,6 +131,7 @@
if(stored_ammo.len < max_ammo)
stored_ammo += R
R.loc = src
playsound(src, 'sound/weapons/gun_interactions/bulletinsert.ogg', 50, 1)
update_mat_value()
return 1
//for accessibles magazines (e.g internal ones) when full, start replacing spent ammo
@@ -140,6 +143,7 @@
stored_ammo += R
R.loc = src
playsound(src, 'sound/weapons/gun_interactions/shotguninsert.ogg', 50, 1)
update_mat_value()
return 1
@@ -170,6 +174,7 @@
if(num_loaded)
if(!silent)
to_chat(user, "<span class='notice'>You load [num_loaded] shell\s into \the [src]!</span>")
playsound(src, 'sound/weapons/gun_interactions/shotguninsert.ogg', 50, 1)
A.update_icon()
update_icon()
@@ -179,6 +184,7 @@
var/obj/item/ammo_casing/A = get_round()
if(A)
user.put_in_hands(A)
playsound(src, 'sound/weapons/gun_interactions/remove_bullet.ogg', 50, 1)
to_chat(user, "<span class='notice'>You remove a round from \the [src]!</span>")
update_icon()
@@ -124,6 +124,7 @@
desc = "A 12 gauge lead slug."
icon_state = "blshell"
caliber = "shotgun"
drop_sound = 'sound/weapons/gun_interactions/shotgun_fall.ogg'
projectile_type = /obj/item/projectile/bullet
materials = list(MAT_METAL=4000)
@@ -87,7 +87,7 @@
delay = 15
/obj/item/ammo_casing/energy/electrode/gun
fire_sound = 'sound/weapons/gunshot.ogg'
fire_sound = 'sound/weapons/gunshots/gunshot.ogg'
e_cost = 100
/obj/item/ammo_casing/energy/electrode/hos //allows balancing of HoS and blueshit guns seperately from other energy weapons
@@ -218,7 +218,7 @@
/obj/item/ammo_casing/energy/clown
projectile_type = /obj/item/projectile/clown
fire_sound = 'sound/weapons/gunshot_smg.ogg'
fire_sound = 'sound/weapons/gunshots/gunshot_smg.ogg'
select_name = "clown"
/obj/item/ammo_casing/energy/sniper
@@ -48,5 +48,5 @@
/obj/item/ammo_casing/energy/c3dbullet
projectile_type = /obj/item/projectile/bullet/midbullet3
select_name = "spraydown"
fire_sound = 'sound/weapons/gunshot_smg.ogg'
fire_sound = 'sound/weapons/gunshots/gunshot_mg.ogg'
e_cost = 20
+2
View File
@@ -17,6 +17,8 @@
attack_verb = list("struck", "hit", "bashed")
var/fire_sound = "gunshot"
var/magin_sound = 'sound/weapons/gun_interactions/smg_magin.ogg'
var/magout_sound = 'sound/weapons/gun_interactions/smg_magout.ogg'
var/fire_sound_text = "gunshot" //the fire sound that shows in chat messages: laser blast, gunshot, etc.
var/suppressed = 0 //whether or not a message is displayed when fired
var/can_suppress = 0
@@ -1,3 +1,4 @@
// Ion Rifles //
/obj/item/gun/energy/ionrifle
name = "ion rifle"
desc = "A man portable anti-armor weapon designed to disable mechanical threats"
@@ -29,6 +30,7 @@
flight_x_offset = 18
flight_y_offset = 11
// Decloner //
/obj/item/gun/energy/decloner
name = "biological demolecularisor"
desc = "A gun that discharges high amounts of controlled radiation to slowly break a target into component elements."
@@ -44,6 +46,7 @@
if(power_supply.charge > shot.e_cost)
overlays += "decloner_spin"
// Flora Gun //
/obj/item/gun/energy/floragun
name = "floral somatoray"
desc = "A tool that discharges controlled radiation which induces mutation in plant cells."
@@ -56,12 +59,14 @@
ammo_x_offset = 1
selfcharge = 1
// Meteor Gun //
/obj/item/gun/energy/meteorgun
name = "meteor gun"
desc = "For the love of god, make sure you're aiming this the right way!"
icon = 'icons/obj/guns/projectile.dmi'
icon_state = "riotgun"
item_state = "c20r"
fire_sound = 'sound/weapons/gunshots/gunshot_shotgun.ogg'
w_class = WEIGHT_CLASS_BULKY
ammo_type = list(/obj/item/ammo_casing/energy/meteor)
cell_type = /obj/item/stock_parts/cell/potato
@@ -78,6 +83,7 @@
righthand_file = 'icons/mob/inhands/items_righthand.dmi'
w_class = WEIGHT_CLASS_TINY
// Mind Flayer //
/obj/item/gun/energy/mindflayer
name = "\improper Mind Flayer"
desc = "A prototype weapon recovered from the ruins of Research-Station Epsilon."
@@ -86,6 +92,7 @@
ammo_type = list(/obj/item/ammo_casing/energy/mindflayer)
ammo_x_offset = 2
// Energy Crossbows //
/obj/item/gun/energy/kinetic_accelerator/crossbow
name = "mini energy crossbow"
desc = "A weapon favored by syndicate stealth specialists."
@@ -132,6 +139,7 @@
shoot_live_shot()
return (OXYLOSS)
// Plasma Cutters //
/obj/item/gun/energy/plasmacutter
name = "plasma cutter"
desc = "A mining tool capable of expelling concentrated plasma bursts. You could use it to cut limbs off of xenos! Or, you know, mine stuff."
@@ -180,6 +188,7 @@
ammo_type = list(/obj/item/ammo_casing/energy/plasma/adv)
force = 15
// Wormhole Projectors //
/obj/item/gun/energy/wormhole_projector
name = "bluespace wormhole projector"
desc = "A projector that emits high density quantum-coupled bluespace beams."
@@ -227,7 +236,6 @@
orange.target = get_turf(blue)
/* 3d printer 'pseudo guns' for borgs */
/obj/item/gun/energy/printer
name = "cyborg lmg"
desc = "A machinegun that fires 3d-printed flachettes slowly regenerated using a cyborg's internal power source."
@@ -247,6 +255,7 @@
..()
robocharge()
// Instakill Lasers //
/obj/item/gun/energy/laser/instakill
name = "instakill rifle"
icon_state = "instagib"
@@ -271,6 +280,7 @@
item_state = "instagibblue"
ammo_type = list(/obj/item/ammo_casing/energy/instakill/blue)
// HONK Rifle //
/obj/item/gun/energy/clown
name = "HONK Rifle"
desc = "Clown Planet's finest."
@@ -291,6 +301,7 @@
ammo_type = list(/obj/item/ammo_casing/energy/toxplasma)
shaded_charge = 1
// Energy Sniper //
/obj/item/gun/energy/sniperrifle
name = "L.W.A.P. Sniper Rifle"
desc = "A rifle constructed of lightweight materials, fitted with a SMART aiming-system scope."
@@ -303,6 +314,7 @@
zoom_amt = 7 //Long range, enough to see in front of you, but no tiles behind you.
shaded_charge = 1
// Temperature Gun //
/obj/item/gun/energy/temperature
name = "temperature gun"
icon = 'icons/obj/guns/gun_temperature.dmi'
@@ -486,6 +498,7 @@
if(100 to 202) overlays += "100"
if(-INFINITY to 100) overlays += "0"
// Mimic Gun //
/obj/item/gun/energy/mimicgun
name = "mimic gun"
desc = "A self-defense weapon that exhausts organic targets, weakening them until they collapse. Why does this one have teeth?"
+36 -13
View File
@@ -8,6 +8,7 @@
var/mag_type = /obj/item/ammo_box/magazine/m10mm //Removes the need for max_ammo and caliber info
var/obj/item/ammo_box/magazine/magazine
var/can_tactical = FALSE //check to see if the gun can tactically reload
/obj/item/gun/projectile/New()
..()
@@ -32,7 +33,7 @@
if(eject_casing)
AC.loc = get_turf(src) //Eject casing onto ground.
AC.SpinAnimation(10, 1) //next gen special effects
playsound(src, chambered.drop_sound, 100, 1)
if(empty_chamber)
chambered = null
chamber_round()
@@ -51,21 +52,41 @@
return 0
return 1
/obj/item/gun/projectile/proc/can_reload()
return !magazine
/obj/item/gun/projectile/proc/reload(obj/item/ammo_box/magazine/AM, mob/user as mob)
user.remove_from_mob(AM)
magazine = AM
magazine.loc = src
playsound(src, magin_sound, 50, 1)
chamber_round()
AM.update_icon()
update_icon()
return
/obj/item/gun/projectile/attackby(var/obj/item/A as obj, mob/user as mob, params)
..()
if(istype(A, /obj/item/ammo_box/magazine))
var/obj/item/ammo_box/magazine/AM = A
if(!magazine && istype(AM, mag_type))
user.remove_from_mob(AM)
magazine = AM
magazine.loc = src
to_chat(user, "<span class='notice'>You load a new magazine into \the [src].</span>")
chamber_round()
A.update_icon()
update_icon()
return 1
else if(magazine)
to_chat(user, "<span class='notice'>There's already a magazine in \the [src].</span>")
if(istype(AM, mag_type))
if(can_reload())
reload(AM, user)
to_chat(user, "<span class='notice'>You load a new magazine into \the [src].</span>")
return TRUE
else if(!can_tactical)
to_chat(user, "<span class='notice'>There's already a magazine in \the [src].</span>")
return TRUE
else
to_chat(user, "<span class='notice'>You perform a tactical reload on \the [src], replacing the magazine.</span>")
magazine.loc = get_turf(loc)
magazine.update_icon()
magazine = null
reload(AM, user)
return TRUE
else
to_chat(user, "<span class='notice'>You can't put this type of ammo in \the [src].</span>")
return TRUE
if(istype(A, /obj/item/suppressor))
var/obj/item/suppressor/S = A
if(can_suppress)
@@ -76,7 +97,7 @@
suppressed = A
S.oldsound = fire_sound
S.initial_w_class = w_class
fire_sound = 'sound/weapons/gunshot_silenced.ogg'
fire_sound = 'sound/weapons/gunshots/gunshot_silenced.ogg'
w_class = WEIGHT_CLASS_NORMAL //so pistols do not fit in pockets when suppressed
A.loc = src
update_icon()
@@ -113,11 +134,13 @@
magazine.update_icon()
magazine = null
to_chat(user, "<span class='notice'>You pull the magazine out of \the [src]!</span>")
playsound(src, magout_sound, 50, 1)
else if(chambered)
AC.loc = get_turf(src)
AC.SpinAnimation(10, 1)
chambered = null
to_chat(user, "<span class='notice'>You unload the round from \the [src]'s chamber.</span>")
playsound(src, 'sound/weapons/gun_interactions/remove_bullet.ogg', 50, 1)
else
to_chat(user, "<span class='notice'>There's no magazine in \the [src].</span>")
update_icon()
@@ -2,6 +2,7 @@
w_class = WEIGHT_CLASS_NORMAL
var/alarmed = 0
var/select = 1
can_tactical = TRUE
can_suppress = 1
burst_size = 3
fire_delay = 2
@@ -60,7 +61,7 @@
fire_delay = initial(fire_delay)
to_chat(user, "<span class='notice'>You switch to [burst_size] round burst.</span>")
playsound(user, 'sound/weapons/empty.ogg', 100, 1)
playsound(user, 'sound/weapons/gun_interactions/selector.ogg', 100, 1)
update_icon()
for(var/X in actions)
var/datum/action/A = X
@@ -75,13 +76,16 @@
update_icon()
alarmed = 1
//Saber SMG//
/obj/item/gun/projectile/automatic/proto
name = "\improper Nanotrasen Saber SMG"
desc = "A prototype three-round burst 9mm submachine gun, designated 'SABR'. Has a threaded barrel for suppressors."
icon_state = "saber"
mag_type = /obj/item/ammo_box/magazine/smgm9mm
origin_tech = "combat=4;materials=2"
fire_sound = 'sound/weapons/gunshots/gunshot_pistol.ogg'
//C-20r SMG//
/obj/item/gun/projectile/automatic/c20r
name = "\improper C-20r SMG"
desc = "A two-round burst .45 SMG, designated 'C-20r'. Has a 'Scarborough Arms - Per falcis, per pravitas' buttstamp."
@@ -89,7 +93,7 @@
item_state = "c20r"
origin_tech = "combat=5;materials=2;syndicate=6"
mag_type = /obj/item/ammo_box/magazine/smgm45
fire_sound = 'sound/weapons/gunshot_smg.ogg'
fire_sound = 'sound/weapons/gunshots/gunshot_smg.ogg'
fire_delay = 2
burst_size = 2
@@ -105,12 +109,16 @@
..()
icon_state = "c20r[magazine ? "-[Ceiling(get_ammo(0)/4)*4]" : ""][chambered ? "" : "-e"][suppressed ? "-suppressed" : ""]"
//WT550//
/obj/item/gun/projectile/automatic/wt550
name = "security auto rifle"
desc = "An outdated personal defense weapon utilized by law enforcement. The WT-550 Automatic Rifle fires 4.6x30mm rounds."
icon_state = "wt550"
item_state = "arg"
mag_type = /obj/item/ammo_box/magazine/wt550m9
fire_sound = 'sound/weapons/gunshots/gunshot_rifle.ogg'
magin_sound = 'sound/weapons/gun_interactions/batrifle_magin.ogg'
magout_sound = 'sound/weapons/gun_interactions/batrifle_magout.ogg'
fire_delay = 2
can_suppress = 0
burst_size = 1
@@ -120,14 +128,17 @@
..()
icon_state = "wt550[magazine ? "-[Ceiling(get_ammo(0)/4)*4]" : ""]"
//Type-U3 Uzi//
/obj/item/gun/projectile/automatic/mini_uzi
name = "\improper 'Type U3' Uzi"
desc = "A lightweight, burst-fire submachine gun, for when you really want someone dead. Uses 9mm rounds."
icon_state = "mini-uzi"
origin_tech = "combat=4;materials=2;syndicate=4"
mag_type = /obj/item/ammo_box/magazine/uzim9mm
fire_sound = 'sound/weapons/gunshots/gunshot_pistol.ogg'
burst_size = 2
//M-90gl Carbine//
/obj/item/gun/projectile/automatic/m90
name = "\improper M-90gl Carbine"
desc = "A three-round burst 5.56 toploading carbine, designated 'M-90gl'. Has an attached underbarrel grenade launcher which can be toggled on and off."
@@ -135,7 +146,9 @@
item_state = "m90-4"
origin_tech = "combat=5;materials=2;syndicate=6"
mag_type = /obj/item/ammo_box/magazine/m556
fire_sound = 'sound/weapons/gunshot_smg.ogg'
fire_sound = 'sound/weapons/gunshots/gunshot_rifle.ogg'
magin_sound = 'sound/weapons/gun_interactions/batrifle_magin.ogg'
magout_sound = 'sound/weapons/gun_interactions/batrifle_magout.ogg'
can_suppress = 0
var/obj/item/gun/projectile/revolver/grenadelauncher/underbarrel
burst_size = 3
@@ -195,9 +208,10 @@
burst_size = 1
fire_delay = 0
to_chat(user, "<span class='notice'>You switch to semi-auto.</span>")
playsound(user, 'sound/weapons/empty.ogg', 100, 1)
playsound(user, 'sound/weapons/gun_interactions/selector.ogg', 100, 1)
update_icon()
//Tommy Gun//
/obj/item/gun/projectile/automatic/tommygun
name = "\improper Thompson SMG"
desc = "A genuine 'Chicago Typewriter'."
@@ -207,11 +221,12 @@
slot_flags = 0
origin_tech = "combat=5;materials=1;syndicate=3"
mag_type = /obj/item/ammo_box/magazine/tommygunm45
fire_sound = 'sound/weapons/gunshot_smg.ogg'
fire_sound = 'sound/weapons/gunshots/gunshot_smg.ogg'
can_suppress = 0
burst_size = 4
fire_delay = 1
//ARG Assault Rifle//
/obj/item/gun/projectile/automatic/ar
name = "ARG"
desc = "A robust assault rile used by Nanotrasen fighting forces."
@@ -220,7 +235,9 @@
slot_flags = 0
origin_tech = "combat=6;engineering=4"
mag_type = /obj/item/ammo_box/magazine/m556
fire_sound = 'sound/weapons/gunshot_smg.ogg'
fire_sound = 'sound/weapons/gunshots/gunshot_mg.ogg'
magin_sound = 'sound/weapons/gun_interactions/batrifle_magin.ogg'
magout_sound = 'sound/weapons/gun_interactions/batrifle_magout.ogg'
can_suppress = 0
burst_size = 3
fire_delay = 1
@@ -234,7 +251,9 @@
w_class = WEIGHT_CLASS_NORMAL
origin_tech = "combat=6;materials=4;syndicate=6"
mag_type = /obj/item/ammo_box/magazine/m12g
fire_sound = 'sound/weapons/gunshot4.ogg'
fire_sound = 'sound/weapons/gunshots/gunshot_shotgun.ogg'
magin_sound = 'sound/weapons/gun_interactions/batrifle_magin.ogg'
magout_sound = 'sound/weapons/gun_interactions/batrifle_magout.ogg'
can_suppress = 0
burst_size = 1
fire_delay = 0
@@ -259,6 +278,7 @@
..()
empty_alarm()
//Laser carbine//
/obj/item/gun/projectile/automatic/lasercarbine
name = "\improper IK-60 Laser Carbine"
desc = "A short, compact carbine like rifle, relying more on battery cartridges rather than a built in power cell. Utilized by the Nanotrasen Navy for combat operations."
@@ -267,7 +287,9 @@
w_class = WEIGHT_CLASS_NORMAL
origin_tech = "combat=4;materials=2"
mag_type = /obj/item/ammo_box/magazine/laser
fire_sound = 'sound/weapons/emitter2.ogg'
fire_sound = 'sound/weapons/gunshots/gunshot_lascarbine.ogg'
magin_sound = 'sound/weapons/gun_interactions/batrifle_magin.ogg'
magout_sound = 'sound/weapons/gun_interactions/batrifle_magout.ogg'
can_suppress = 0
burst_size = 2
@@ -1,3 +1,4 @@
//Stetchkin//
/obj/item/gun/projectile/automatic/pistol
name = "stechkin pistol"
desc = "A small, easily concealable 10mm handgun. Has a threaded barrel for suppressors."
@@ -5,6 +6,9 @@
w_class = WEIGHT_CLASS_SMALL
origin_tech = "combat=3;materials=2;syndicate=4"
mag_type = /obj/item/ammo_box/magazine/m10mm
fire_sound = 'sound/weapons/gunshots/gunshot_pistol.ogg'
magin_sound = 'sound/weapons/gun_interactions/pistol_magin.ogg'
magout_sound = 'sound/weapons/gun_interactions/pistol_magout.ogg'
can_suppress = 1
burst_size = 1
fire_delay = 0
@@ -18,6 +22,7 @@
icon_state = "[initial(icon_state)][chambered ? "" : "-e"][suppressed ? "-suppressed" : ""]"
return
//M1911//
/obj/item/gun/projectile/automatic/pistol/m1911
name = "\improper M1911"
desc = "A classic .45 handgun with a small magazine capacity."
@@ -26,6 +31,7 @@
mag_type = /obj/item/ammo_box/magazine/m45
can_suppress = 0
//Enforcer//
/obj/item/gun/projectile/automatic/pistol/enforcer
name = "Enforcer"
desc = "A pistol of modern design."
@@ -72,12 +78,16 @@
magazine = new/obj/item/ammo_box/magazine/enforcer/lethal
..()
//Desert Eagle//
/obj/item/gun/projectile/automatic/pistol/deagle
name = "desert eagle"
desc = "A robust .50 AE handgun."
icon_state = "deagle"
force = 14.0
mag_type = /obj/item/ammo_box/magazine/m50
fire_sound = 'sound/weapons/gunshots/gunshot_pistolH.ogg'
magin_sound = 'sound/weapons/gun_interactions/hpistol_magin.ogg'
magout_sound = 'sound/weapons/gun_interactions/hpistol_magout.ogg'
can_suppress = 0
/obj/item/gun/projectile/automatic/pistol/deagle/update_icon()
@@ -94,6 +104,7 @@
icon_state = "deaglecamo"
item_state = "deagleg"
//APS Pistol//
/obj/item/gun/projectile/automatic/pistol/APS
name = "stechkin APS pistol"
desc = "The original russian version of a widely used Syndicate sidearm. Uses 9mm ammo."
@@ -4,6 +4,7 @@
icon_state = "revolver"
mag_type = /obj/item/ammo_box/magazine/internal/cylinder
origin_tech = "combat=3;materials=2"
fire_sound = 'sound/weapons/gunshots/gunshot_strong.ogg'
/obj/item/gun/projectile/revolver/New()
..()
@@ -45,6 +46,7 @@
CB.loc = get_turf(loc)
CB.SpinAnimation(10, 1)
CB.update_icon()
playsound(get_turf(CB), "casingdrop", 60, 1)
num_unloaded++
if(num_unloaded)
to_chat(user, "<span class='notice'>You unload [num_unloaded] shell\s from [src].</span>")
@@ -251,6 +253,7 @@
chambered = null
CB.loc = get_turf(loc)
CB.update_icon()
playsound(get_turf(CB), "casingdrop", 60, 1)
num_unloaded++
if(num_unloaded)
to_chat(user, "<span class='notice'>You unload [num_unloaded] shell\s from [src].</span>")
@@ -316,6 +319,7 @@
flags = CONDUCT
slot_flags = SLOT_BACK
mag_type = /obj/item/ammo_box/magazine/internal/shot/dual
fire_sound = 'sound/weapons/gunshots/gunshot_shotgun.ogg'
sawn_desc = "Omar's coming!"
unique_rename = 1
unique_reskin = 1
@@ -348,7 +352,9 @@
CB = magazine.get_round(0)
chambered = null
CB.loc = get_turf(loc)
CB.SpinAnimation(10, 1)
CB.update_icon()
playsound(get_turf(CB), 'sound/weapons/gun_interactions/shotgun_fall.ogg', 70, 1)
num_unloaded++
if(num_unloaded)
to_chat(user, "<span class = 'notice'>You break open \the [src] and unload [num_unloaded] shell\s.</span>")
@@ -369,6 +375,7 @@
force = 10
slot_flags = null
mag_type = /obj/item/ammo_box/magazine/internal/shot/improvised
fire_sound = 'sound/weapons/gunshots/gunshot_shotgun.ogg'
sawn_desc = "I'm just here for the gasoline."
unique_rename = 0
unique_reskin = 0
@@ -420,7 +427,7 @@
mag_type = /obj/item/ammo_box/magazine/internal/shot/improvised/cane
sawn_desc = "I'm sorry, but why did you saw your cane in the first place?"
attack_verb = list("bludgeoned", "whacked", "disciplined", "thrashed")
fire_sound = 'sound/weapons/gunshot_silenced.ogg'
fire_sound = 'sound/weapons/gunshots/gunshot_silenced.ogg'
suppressed = 1
needs_permit = 0 //its just a cane beepsky.....
@@ -8,7 +8,9 @@
origin_tech = "combat=6;engineering=3;syndicate=6"
mag_type = /obj/item/ammo_box/magazine/mm556x45
weapon_weight = WEAPON_MEDIUM
fire_sound = 'sound/weapons/gunshot3.ogg'
fire_sound = 'sound/weapons/gunshots/gunshot_mg.ogg'
magin_sound = 'sound/weapons/gun_interactions/lmg_magin.ogg'
magout_sound = 'sound/weapons/gun_interactions/lmg_magout.ogg'
var/cover_open = 0
can_suppress = 0
burst_size = 3
@@ -17,6 +19,7 @@
/obj/item/gun/projectile/automatic/l6_saw/attack_self(mob/user)
cover_open = !cover_open
to_chat(user, "<span class='notice'>You [cover_open ? "open" : "close"] [src]'s cover.</span>")
playsound(src, cover_open ? 'sound/weapons/gun_interactions/sawopen.ogg' : 'sound/weapons/gun_interactions/sawclose.ogg', 50, 1)
update_icon()
/obj/item/gun/projectile/automatic/l6_saw/update_icon()
@@ -42,17 +45,18 @@
magazine.loc = get_turf(loc)
user.put_in_hands(magazine)
magazine = null
playsound(src, magout_sound, 50, 1)
update_icon()
to_chat(user, "<span class='notice'>You remove the magazine from [src].</span>")
/obj/item/gun/projectile/automatic/l6_saw/attackby(obj/item/A, mob/user, params)
. = ..()
if(.)
return
if(!cover_open)
to_chat(user, "<span class='warning'>[src]'s cover is closed! You can't insert a new mag.</span>")
return
/obj/item/gun/projectile/automatic/l6_saw/attackby(obj/item/A, mob/user, params)
if(istype(A, /obj/item/ammo_box/magazine))
var/obj/item/ammo_box/magazine/AM = A
if(istype(AM, mag_type))
if(!cover_open)
to_chat(user, "<span class='warning'>[src]'s cover is closed! You can't insert a new mag.</span>")
return
..()
//ammo//
@@ -9,6 +9,7 @@
slot_flags = SLOT_BACK
origin_tech = "combat=4;materials=2"
mag_type = /obj/item/ammo_box/magazine/internal/shot
fire_sound = 'sound/weapons/gunshots/gunshot_shotgun.ogg'
var/recentpump = 0 // to prevent spammage
/obj/item/gun/projectile/shotgun/attackby(obj/item/A, mob/user, params)
@@ -44,7 +45,7 @@
/obj/item/gun/projectile/shotgun/proc/pump(mob/M)
playsound(M, 'sound/weapons/shotgunpump.ogg', 60, 1)
playsound(M, 'sound/weapons/gun_interactions/shotgunpump.ogg', 60, 1)
pump_unload(M)
pump_reload(M)
update_icon() //I.E. fix the desc
@@ -54,6 +55,7 @@
if(chambered)//We have a shell in the chamber
chambered.loc = get_turf(src)//Eject casing
chambered.SpinAnimation(5, 1)
playsound(src, chambered.drop_sound, 60, 1)
chambered = null
/obj/item/gun/projectile/shotgun/proc/pump_reload(mob/M)
@@ -206,10 +208,11 @@
item_state = "moistnugget"
slot_flags = 0 //no SLOT_BACK sprite, alas
mag_type = /obj/item/ammo_box/magazine/internal/boltaction
fire_sound = 'sound/weapons/gunshots/gunshot_rifle.ogg'
var/bolt_open = 0
/obj/item/gun/projectile/shotgun/boltaction/pump(mob/M)
playsound(M, 'sound/weapons/shotgunpump.ogg', 60, 1)
playsound(M, 'sound/weapons/gun_interactions/rifle_load.ogg', 60, 1)
if(bolt_open)
pump_reload(M)
else
@@ -312,6 +315,7 @@
to_chat(user, "You switch to tube B.")
else
to_chat(user, "You switch to tube A.")
playsound(user, 'sound/weapons/gun_interactions/selector.ogg', 100, 1)
/obj/item/gun/projectile/shotgun/automatic/dual_tube/AltClick(mob/living/user)
if(user.incapacitated() || !Adjacent(user) || !istype(user))
@@ -6,6 +6,9 @@
recoil = 2
weapon_weight = WEAPON_MEDIUM
mag_type = /obj/item/ammo_box/magazine/sniper_rounds
fire_sound = 'sound/weapons/gunshots/gunshot_sniper.ogg'
magin_sound = 'sound/weapons/gun_interactions/batrifle_magin.ogg'
magout_sound = 'sound/weapons/gun_interactions/batrifle_magout.ogg'
fire_delay = 40
burst_size = 1
origin_tech = "combat=7"
@@ -5,7 +5,7 @@
icon_state = "saber"
item_state = "gun"
mag_type = /obj/item/ammo_box/magazine/toy/smg
fire_sound = 'sound/weapons/gunshot_smg.ogg'
fire_sound = 'sound/weapons/gunshots/gunshot_smg.ogg'
force = 0
throwforce = 0
burst_size = 3
@@ -22,7 +22,7 @@
icon_state = "pistol"
w_class = WEIGHT_CLASS_SMALL
mag_type = /obj/item/ammo_box/magazine/toy/pistol
fire_sound = 'sound/weapons/gunshot.ogg'
fire_sound = 'sound/weapons/gunshots/gunshot.ogg'
can_suppress = 0
burst_size = 1
fire_delay = 0
@@ -163,7 +163,7 @@
name = "makeshift bolt"
desc = "A sharpened metal rod that can be fired out of a crossbow."
icon_state = "metal-rod"
throwforce = 8
throwforce = 10
var/superheated = 0
/obj/item/arrow/rod/removed()
+5 -4
View File
@@ -577,9 +577,9 @@ var/const/INGEST = 2
reagent_list += R
R.holder = src
R.volume = amount
R.on_new(data)
if(data)
R.data = data
R.on_new(data)
update_total()
if(my_atom)
@@ -722,9 +722,10 @@ var/const/INGEST = 2
// that could possibly eat up a lot of memory needlessly
// if most data lists are read-only.
if(trans_data["viruses"])
var/list/v = trans_data["viruses"]
trans_data["viruses"] = v.Copy()
var/list/temp = list()
for(var/datum/disease/v in trans_data["viruses"])
temp.Add(v.Copy())
trans_data["viruses"] = temp
return trans_data
///////////////////////////////////////////////////////////////////////////////////
@@ -419,6 +419,70 @@
/datum/reagent/love/reaction_mob(mob/living/M, method=TOUCH, volume)
to_chat(M, "<span class='notice'>You feel loved!</span>")
/datum/reagent/jestosterone //Formerly known as Nitrogen tungstide hypochlorite before NT fired the chemists for trying to be funny
name = "Jestosterone"
id = "jestosterone"
description = "Jestosterone is an odd chemical compound that induces a variety of annoying side-effects in the average person. It also causes mild intoxication, and is toxic to mimes."
color = "#ff00ff" //Fuchsia, pity we can't do rainbow here
taste_message = "a funny flavour"
/datum/reagent/jestosterone/on_new()
..()
var/mob/living/carbon/C = holder.my_atom
if(!istype(C))
return
var/mind_type = FALSE
if(C.mind)
if(C.mind.assigned_role == "Clown" || C.mind.assigned_role == SPECIAL_ROLE_HONKSQUAD)
mind_type = "Clown"
to_chat(C, "<span class='notice'>Whatever that was, it feels great!</span>")
else if(C.mind.assigned_role == "Mime")
mind_type = "Mime"
to_chat(C, "<span class='warning'>You feel nauseous.</span>")
C.AdjustDizzy(volume)
else
to_chat(C, "<span class='warning'>Something doesn't feel right...</span>")
C.AdjustDizzy(volume)
C.AddComponent(/datum/component/jestosterone, mind_type)
C.AddComponent(/datum/component/squeak, null, null, null, null, null, TRUE)
/datum/reagent/jestosterone/on_mob_life(mob/living/carbon/M)
if(!istype(M))
return ..()
var/update_flags = STATUS_UPDATE_NONE
if(prob(10))
M.emote("giggle")
GET_COMPONENT_FROM(jestosterone_component, /datum/component/jestosterone, M)
if(jestosterone_component.mind_type == "Clown")
update_flags |= M.adjustBruteLoss(-1.5 * REAGENTS_EFFECT_MULTIPLIER) //Screw those pesky clown beatings!
else
M.AdjustDizzy(10, 0, 500)
M.Druggy(15)
if(prob(10))
M.EyeBlurry(5)
if(prob(6))
var/list/clown_message = list("You feel light-headed.",
"You can't see straight.",
"You feel about as funny as the station clown.",
"Bright colours and rainbows cloud your vision.",
"Your funny bone aches.",
"What was that?!",
"You can hear bike horns in the distance.",
"You feel like <em>SHOUTING</em>!",
"Sinister laughter echoes in your ears.",
"Your legs feel like jelly.",
"You feel like telling a pun.")
to_chat(M, "<span class='warning'>[pick(clown_message)]</span>")
if(jestosterone_component.mind_type == "Mime")
update_flags |= M.adjustToxLoss(1.5 * REAGENTS_EFFECT_MULTIPLIER)
return ..() | update_flags
/datum/reagent/jestosterone/on_mob_delete(mob/living/M)
..()
GET_COMPONENT_FROM(remove_fun, /datum/component/jestosterone, M)
GET_COMPONENT_FROM(squeaking, /datum/component/squeak, M)
remove_fun.Destroy()
squeaking.Destroy()
/datum/reagent/royal_bee_jelly
name = "royal bee jelly"
@@ -290,6 +290,18 @@
result_amount = 2
mix_message = "The substance gives off a lovely scent!"
/datum/chemical_reaction/jestosterone
name = "Jestosterone"
id = "jestosterone"
result = "jestosterone"
required_reagents = list("blood" = 1, "sodiumchloride" = 1, "banana" = 1, "lube" = 1, "space_drugs" = 1) //Or one freshly-squeezed clown
min_temp = 374
result_amount = 5
mix_message = "The substance quickly shifts colour, cycling from red, to yellow, to green, to blue, and finally settles at a vibrant fuchsia."
/datum/chemical_reaction/jestosterone/on_reaction(datum/reagents/holder, created_volume)
playsound(get_turf(holder.my_atom), 'sound/items/bikehorn.ogg', 50, 1)
/datum/chemical_reaction/royal_bee_jelly
name = "royal bee jelly"
id = "royal_bee_jelly"
@@ -10,6 +10,7 @@
var/list/list_reagents = null
var/spawned_disease = null
var/disease_amount = 20
var/has_lid = FALSE // Used for containers where we want to put lids on and off
/obj/item/reagent_containers/verb/set_APTFT() //set amount_per_transfer_from_this
set name = "Set transfer amount"
@@ -49,6 +50,14 @@
..()
/obj/item/reagent_containers/attack_self(mob/user)
if(has_lid)
if(is_open_container())
to_chat(usr, "<span class='notice'>You put the lid on [src].</span>")
container_type ^= REFILLABLE | DRAINABLE
else
to_chat(usr, "<span class='notice'>You take the lid off [src].</span>")
container_type |= REFILLABLE | DRAINABLE
update_icon()
return
// this prevented pills, food, and other things from being picked up by bags.
@@ -26,11 +26,11 @@
/obj/item/reagent_containers/borghypo/syndicate
name = "syndicate cyborg hypospray"
desc = "An experimental piece of Syndicate technology used to produce powerful restorative nanites used to very quickly restore injuries of all types. Also metabolizes potassium iodide, for radiation poisoning, and morphine, for offense."
desc = "An experimental piece of Syndicate technology used to produce powerful restorative nanites used to very quickly restore injuries of all types. Also metabolizes potassium iodide, for radiation poisoning, and hydrocodone, for field surgery and pain relief."
icon_state = "borghypo_s"
charge_cost = 20
recharge_time = 2
reagent_ids = list("syndicate_nanites", "potass_iodide", "ether")
reagent_ids = list("syndicate_nanites", "potass_iodide", "hydrocodone")
bypass_protection = 1
/obj/item/reagent_containers/borghypo/New()
@@ -12,6 +12,7 @@
possible_transfer_amounts = list(5,10,15,25,30,50)
volume = 50
container_type = OPENCONTAINER
has_lid = TRUE
var/label_text = ""
// the fucking asshole who designed this can go die in a fire - Iamgoofball
@@ -55,16 +56,6 @@
if(!is_open_container())
to_chat(user, "<span class='notice'>Airtight lid seals it completely.</span>")
/obj/item/reagent_containers/glass/attack_self()
..()
if(is_open_container())
to_chat(usr, "<span class='notice'>You put the lid on [src].</span>")
container_type ^= REFILLABLE | DRAINABLE
else
to_chat(usr, "<span class='notice'>You take the lid off [src].</span>")
container_type |= REFILLABLE | DRAINABLE
update_icon()
/obj/item/reagent_containers/glass/afterattack(obj/target, mob/user, proximity)
if(!proximity)
return
@@ -144,7 +144,7 @@
/obj/item/reagent_containers/hypospray/autoinjector/stimulants
name = "Stimulants autoinjector"
desc = "Rapidly stimulates and regernates the body's organ system."
desc = "Rapidly stimulates and regenerates the body's organ system."
icon_state = "stimpen"
amount_per_transfer_from_this = 50
possible_transfer_amounts = list(50)
@@ -37,4 +37,10 @@
/obj/item/reagent_containers/food/pill/patch/nicotine
name = "nicotine patch"
desc = "Helps temporarily curb the cravings of nicotine dependency."
list_reagents = list("nicotine" = 20)
list_reagents = list("nicotine" = 20)
/obj/item/reagent_containers/food/pill/patch/jestosterone
name = "jestosterone patch"
desc = "Helps with brute injuries if the affected person is a clown, otherwise inflicts various annoying effects."
icon_state = "bandaid_clown"
list_reagents = list("jestosterone" = 30)
+1 -1
View File
@@ -233,7 +233,7 @@
return
mode = SHUTTLE_DOCKED
timer = world.time
send2irc("Server", "The Emergency Shuttle has docked with the station.")
send2maindiscord("The Emergency Shuttle has docked with the station.")
emergency_shuttle_docked.Announce("The Emergency Shuttle has docked with the station. You have [timeLeft(600)] minutes to board the Emergency Shuttle.")
/*
+1 -1
View File
@@ -269,7 +269,7 @@
/obj/item/organ/internal/cyberimp/arm/surgery
name = "surgical toolset implant"
desc = "A set of surgical tools hidden behind a concealed panel on the user's arm"
contents = newlist(/obj/item/retractor/augment, /obj/item/hemostat/augment, /obj/item/cautery/augment, /obj/item/surgicaldrill/augment, /obj/item/scalpel/augment, /obj/item/circular_saw/augment, /obj/item/bonegel/augment, /obj/item/FixOVein/augment, /obj/item/bonesetter/augment)
contents = newlist(/obj/item/retractor/augment, /obj/item/hemostat/augment, /obj/item/cautery/augment, /obj/item/bonesetter/augment, /obj/item/scalpel/augment, /obj/item/circular_saw/augment, /obj/item/bonegel/augment, /obj/item/FixOVein/augment, /obj/item/surgicaldrill/augment)
origin_tech = "materials=3;engineering=3;biotech=3;programming=2;magnets=3"
action_icon = list(/datum/action/item_action/organ_action/toggle = 'icons/obj/storage.dmi')
action_icon_state = list(/datum/action/item_action/organ_action/toggle = "duffel-med")
@@ -1,3 +1,7 @@
/obj/item/organ/internal/brain/abductor
icon_state = "brain-x"
mmi_icon_state = "mmi_alien"
/obj/item/organ/internal/eyes/abductor
name = "abductor eyeballs"
dark_view = 3