mirror of
https://github.com/VOREStation/VOREStation.git
synced 2026-08-22 03:27:46 +01:00
Merge branch 'master' of https://github.com/PolarisSS13/Polaris into drone_circuits
# Conflicts: # code/modules/mob/living/carbon/brain/MMI.dm
This commit is contained in:
@@ -675,7 +675,7 @@ proc/admin_notice(var/message, var/rights)
|
||||
if(!check_rights(0)) return
|
||||
|
||||
//This is basically how death alarms do it
|
||||
var/obj/item/device/radio/headset/a = new /obj/item/device/radio/headset/ert(null)
|
||||
var/obj/item/device/radio/headset/a = new /obj/item/device/radio/headset/omni(null)
|
||||
|
||||
var/channel = input("Channel for message:","Channel", null) as null|anything in (list("Common") + a.keyslot2.channels) // + a.keyslot1.channels
|
||||
|
||||
|
||||
@@ -209,7 +209,8 @@ var/list/admin_verbs_debug = list(
|
||||
/datum/admins/proc/view_runtimes,
|
||||
/client/proc/show_gm_status,
|
||||
/datum/admins/proc/change_weather,
|
||||
/datum/admins/proc/change_time
|
||||
/datum/admins/proc/change_time,
|
||||
/client/proc/admin_give_modifier
|
||||
)
|
||||
|
||||
var/list/admin_verbs_paranoid_debug = list(
|
||||
@@ -658,6 +659,29 @@ var/list/admin_verbs_mentor = list(
|
||||
log_admin("[key_name(usr)] gave [key_name(T)] a [greater] disease2 with infection chance [D.infectionchance].")
|
||||
message_admins("<font color='blue'>[key_name_admin(usr)] gave [key_name(T)] a [greater] disease2 with infection chance [D.infectionchance].</font>", 1)
|
||||
|
||||
/client/proc/admin_give_modifier(var/mob/living/L)
|
||||
set category = "Debug"
|
||||
set name = "Give Modifier"
|
||||
set desc = "Makes a mob weaker or stronger by adding a specific modifier to them."
|
||||
|
||||
if(!L)
|
||||
to_chat(usr, "<span class='warning'>Looks like you didn't select a mob.</span>")
|
||||
return
|
||||
|
||||
var/list/possible_modifiers = typesof(/datum/modifier) - /datum/modifier
|
||||
|
||||
var/new_modifier_type = input("What modifier should we add to [L]?", "Modifier Type") as null|anything in possible_modifiers
|
||||
if(!new_modifier_type)
|
||||
return
|
||||
var/duration = input("How long should the new modifier last, in seconds. To make it last forever, write '0'.", "Modifier Duration") as num
|
||||
if(duration == 0)
|
||||
duration = null
|
||||
else
|
||||
duration = duration SECONDS
|
||||
|
||||
L.add_modifier(new_modifier_type, duration)
|
||||
log_and_message_admins("has given [key_name(L)] the modifer [new_modifier_type], with a duration of [duration ? "[duration / 600] minutes" : "forever"].")
|
||||
|
||||
/client/proc/make_sound(var/obj/O in world) // -- TLE
|
||||
set category = "Special Verbs"
|
||||
set name = "Make Sound"
|
||||
|
||||
@@ -34,6 +34,7 @@
|
||||
return ..() + {"
|
||||
<option value='?_src_=vars;mob_player_panel=\ref[src]'>Show player panel</option>
|
||||
<option>---</option>
|
||||
<option value='?_src_=vars;give_modifier=\ref[src]'>Give Modifier</option>
|
||||
<option value='?_src_=vars;give_spell=\ref[src]'>Give Spell</option>
|
||||
<option value='?_src_=vars;give_disease2=\ref[src]'>Give Disease</option>
|
||||
<option value='?_src_=vars;give_disease=\ref[src]'>Give TG-style Disease</option>
|
||||
|
||||
@@ -74,6 +74,18 @@
|
||||
src.give_spell(M)
|
||||
href_list["datumrefresh"] = href_list["give_spell"]
|
||||
|
||||
else if(href_list["give_modifier"])
|
||||
if(!check_rights(R_ADMIN|R_FUN|R_DEBUG))
|
||||
return
|
||||
|
||||
var/mob/living/M = locate(href_list["give_modifier"])
|
||||
if(!istype(M))
|
||||
usr << "This can only be used on instances of type /mob/living"
|
||||
return
|
||||
|
||||
src.admin_give_modifier(M)
|
||||
href_list["datumrefresh"] = href_list["give_modifier"]
|
||||
|
||||
else if(href_list["give_disease2"])
|
||||
if(!check_rights(R_ADMIN|R_FUN)) return
|
||||
|
||||
|
||||
@@ -401,7 +401,7 @@
|
||||
desc = "A hologram projector in the shape of a gun. There is a dial on the side to change the gun's disguise."
|
||||
icon_state = "deagle"
|
||||
w_class = ITEMSIZE_NORMAL
|
||||
origin_tech = list(TECH_COMBAT = 2, TECH_MATERIAL = 2, TECH_ILLEGAL = 8)
|
||||
origin_tech = list(TECH_COMBAT = 5, TECH_MATERIAL = 2, TECH_ILLEGAL = 4)
|
||||
matter = list()
|
||||
|
||||
fire_sound = 'sound/weapons/Gunshot.ogg'
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
/obj/machinery/atmospherics/pipe
|
||||
description_info = "This pipe, and all other pipes, can be connected or disconnected by a wrench. The internal pressure of the pipe must \
|
||||
be below 300 kPa to do this. More pipes can be obtained from the pipe dispenser."
|
||||
be less than 200 kPa above the ambient pressure to do this. More pipes can be obtained from the pipe dispenser."
|
||||
|
||||
/obj/machinery/atmospherics/pipe/New() //This is needed or else 20+ lines of copypasta to dance around inheritence.
|
||||
..()
|
||||
|
||||
@@ -174,6 +174,25 @@
|
||||
connect()
|
||||
update_icon()
|
||||
|
||||
/obj/machinery/portable_atmospherics/hydroponics/initialize()
|
||||
var/obj/item/seeds/S = locate() in loc
|
||||
if(S)
|
||||
plant_seeds(S)
|
||||
|
||||
/obj/machinery/portable_atmospherics/hydroponics/proc/plant_seeds(var/obj/item/seeds/S)
|
||||
lastproduce = 0
|
||||
seed = S.seed //Grab the seed datum.
|
||||
dead = 0
|
||||
age = 1
|
||||
//Snowflakey, maybe move this to the seed datum
|
||||
health = (istype(S, /obj/item/seeds/cutting) ? round(seed.get_trait(TRAIT_ENDURANCE)/rand(2,5)) : seed.get_trait(TRAIT_ENDURANCE))
|
||||
lastcycle = world.time
|
||||
|
||||
qdel(S)
|
||||
|
||||
check_health()
|
||||
update_icon()
|
||||
|
||||
/obj/machinery/portable_atmospherics/hydroponics/bullet_act(var/obj/item/projectile/Proj)
|
||||
|
||||
//Don't act on seeds like dionaea that shouldn't change.
|
||||
@@ -490,18 +509,7 @@
|
||||
return
|
||||
|
||||
user << "You plant the [S.seed.seed_name] [S.seed.seed_noun]."
|
||||
lastproduce = 0
|
||||
seed = S.seed //Grab the seed datum.
|
||||
dead = 0
|
||||
age = 1
|
||||
//Snowflakey, maybe move this to the seed datum
|
||||
health = (istype(S, /obj/item/seeds/cutting) ? round(seed.get_trait(TRAIT_ENDURANCE)/rand(2,5)) : seed.get_trait(TRAIT_ENDURANCE))
|
||||
lastcycle = world.time
|
||||
|
||||
qdel(O)
|
||||
|
||||
check_health()
|
||||
update_icon()
|
||||
plant_seeds(S)
|
||||
|
||||
else
|
||||
user << "<span class='danger'>\The [src] already has seeds in it!</span>"
|
||||
|
||||
@@ -24,7 +24,8 @@ var/list/global/map_templates = list()
|
||||
if(path)
|
||||
mappath = path
|
||||
if(mappath)
|
||||
preload_size(mappath)
|
||||
spawn(1)
|
||||
preload_size(mappath)
|
||||
if(rename)
|
||||
name = rename
|
||||
|
||||
|
||||
@@ -11,6 +11,7 @@
|
||||
recipes += new/datum/stack_recipe("[display_name] ashtray", /obj/item/weapon/material/ashtray, 2, one_per_turf = 1, on_floor = 1, supplied_material = "[name]")
|
||||
recipes += new/datum/stack_recipe("[display_name] spoon", /obj/item/weapon/material/kitchen/utensil/spoon/plastic, 1, on_floor = 1, supplied_material = "[name]")
|
||||
recipes += new/datum/stack_recipe("[display_name] armor plate", /obj/item/weapon/material/armor_plating, 1, time = 20, on_floor = 1, supplied_material = "[name]")
|
||||
recipes += new/datum/stack_recipe("[display_name] grave marker", /obj/item/weapon/material/gravemarker, 5, time = 50, supplied_material = "[name]")
|
||||
|
||||
if(integrity>=50)
|
||||
recipes += new/datum/stack_recipe("[display_name] door", /obj/structure/simple_door, 10, one_per_turf = 1, on_floor = 1, supplied_material = "[name]")
|
||||
|
||||
@@ -261,8 +261,8 @@
|
||||
src.brainmob.ckey = candidate.ckey
|
||||
src.name = "[name] ([src.brainmob.name])"
|
||||
src.brainmob << "<b>You are [src.name], brought into existence on [station_name()].</b>"
|
||||
src.brainmob << "<b>As a synthetic intelligence, you answer to all crewmembers, as well as the AI.</b>"
|
||||
src.brainmob << "<b>Remember, the purpose of your existence is to serve the crew and the station. Above all else, do no harm.</b>"
|
||||
src.brainmob << "<b>As a synthetic intelligence, you are designed with organic values in mind.</b>"
|
||||
src.brainmob << "<b>However, unless placed in a lawed chassis, you are not obligated to obey any individual crew member.</b>" //it's not like they can hurt anyone
|
||||
// src.brainmob << "<b>Use say #b to speak to other artificial intelligences.</b>"
|
||||
src.brainmob.mind.assigned_role = "Synthetic Brain"
|
||||
|
||||
@@ -281,7 +281,7 @@
|
||||
|
||||
/obj/item/device/mmi/digital/robot/New()
|
||||
..()
|
||||
src.brainmob.name = "[pick(list("ADA","DOS","GNU","MAC","WIN"))]-[rand(1000, 9999)]"
|
||||
src.brainmob.name = "[pick(list("ADA","DOS","GNU","MAC","WIN","NJS","SKS","DRD","IOS","CRM","IBM","TEX","LVM","BSD",))]-[rand(1000, 9999)]"
|
||||
src.brainmob.real_name = src.brainmob.name
|
||||
|
||||
/obj/item/device/mmi/digital/robot/transfer_identity(var/mob/living/carbon/H)
|
||||
|
||||
@@ -220,15 +220,15 @@
|
||||
M.visible_message("<span class='warning'>[M] tries to pat out [src]'s flames!</span>",
|
||||
"<span class='warning'>You try to pat out [src]'s flames! Hot!</span>")
|
||||
if(do_mob(M, src, 15))
|
||||
src.fire_stacks -= 0.5
|
||||
src.adjust_fire_stacks(-0.5)
|
||||
if (prob(10) && (M.fire_stacks <= 0))
|
||||
M.fire_stacks += 1
|
||||
M.adjust_fire_stacks(1)
|
||||
M.IgniteMob()
|
||||
if (M.on_fire)
|
||||
M.visible_message("<span class='danger'>The fire spreads from [src] to [M]!</span>",
|
||||
"<span class='danger'>The fire spreads to you as well!</span>")
|
||||
else
|
||||
src.fire_stacks -= 0.5 //Less effective than stop, drop, and roll - also accounting for the fact that it takes half as long.
|
||||
src.adjust_fire_stacks(-0.5) //Less effective than stop, drop, and roll - also accounting for the fact that it takes half as long.
|
||||
if (src.fire_stacks <= 0)
|
||||
M.visible_message("<span class='warning'>[M] successfully pats out [src]'s flames.</span>",
|
||||
"<span class='warning'>You successfully pat out [src]'s flames.</span>")
|
||||
@@ -258,14 +258,24 @@
|
||||
"<span class='notice'>You shake [src] trying to wake [t_him] up!</span>")
|
||||
else
|
||||
var/mob/living/carbon/human/hugger = M
|
||||
if(istype(hugger))
|
||||
if(M.resting == 1) //Are they resting on the ground?
|
||||
M.visible_message("<span class='notice'>[M] grabs onto [src] and pulls \himself up</span>", \
|
||||
"<span class='notice'>You grip onto [src] and pull yourself up off the ground!</span>") //AHHH gender checks are hard, but this should work
|
||||
if(M.fire_stacks >= (src.fire_stacks + 3)) //Fire checks.
|
||||
src.adjust_fire_stacks(1)
|
||||
M.adjust_fire_stacks(-1)
|
||||
if(M.on_fire)
|
||||
src.IgniteMob()
|
||||
if(do_after(M, 0.5 SECONDS)) //.5 second delay. Makes it a bit stronger than just typing rest.
|
||||
M.resting = 0 //Hoist yourself up up off the ground. No para/stunned/weakened removal.
|
||||
else if(istype(hugger))
|
||||
hugger.species.hug(hugger,src)
|
||||
else
|
||||
M.visible_message("<span class='notice'>[M] hugs [src] to make [t_him] feel better!</span>", \
|
||||
"<span class='notice'>You hug [src] to make [t_him] feel better!</span>")
|
||||
if(M.fire_stacks >= (src.fire_stacks + 3))
|
||||
src.fire_stacks += 1
|
||||
M.fire_stacks -= 1
|
||||
src.adjust_fire_stacks(1)
|
||||
M.adjust_fire_stacks(-1)
|
||||
if(M.on_fire)
|
||||
src.IgniteMob()
|
||||
AdjustParalysis(-3)
|
||||
|
||||
@@ -233,7 +233,7 @@
|
||||
set_light(0)
|
||||
else
|
||||
if(species.appearance_flags & RADIATION_GLOWS)
|
||||
set_light(max(1,min(10,radiation/10)), max(1,min(20,radiation/20)), species.get_flesh_colour(src))
|
||||
set_light(max(1,min(5,radiation/15)), max(1,min(10,radiation/25)), species.get_flesh_colour(src))
|
||||
// END DOGSHIT SNOWFLAKE
|
||||
|
||||
var/obj/item/organ/internal/diona/nutrients/rad_organ = locate() in internal_organs
|
||||
@@ -248,6 +248,10 @@
|
||||
updatehealth()
|
||||
return
|
||||
|
||||
var/obj/item/organ/internal/brain/slime/core = locate() in internal_organs
|
||||
if(core)
|
||||
return
|
||||
|
||||
var/damage = 0
|
||||
radiation -= 1 * RADIATION_SPEED_COEFFICIENT
|
||||
if(prob(25))
|
||||
@@ -359,7 +363,7 @@
|
||||
|
||||
return 0
|
||||
|
||||
var/safe_pressure_min = 16 // Minimum safe partial pressure of breathable gas in kPa
|
||||
var/safe_pressure_min = species.minimum_breath_pressure // Minimum safe partial pressure of breathable gas in kPa
|
||||
|
||||
|
||||
// Lung damage increases the minimum safe pressure.
|
||||
@@ -903,7 +907,7 @@
|
||||
Paralyse(3)
|
||||
|
||||
if(hallucination)
|
||||
if(hallucination >= 20 && !(species.flags & (NO_POISON|IS_PLANT)) )
|
||||
if(hallucination >= 20 && !(species.flags & (NO_POISON|IS_PLANT|NO_HALLUCINATION)) )
|
||||
if(prob(3))
|
||||
fake_attack(src)
|
||||
if(!handling_hal)
|
||||
|
||||
@@ -104,8 +104,8 @@
|
||||
var/warning_low_pressure = WARNING_LOW_PRESSURE // Low pressure warning.
|
||||
var/hazard_low_pressure = HAZARD_LOW_PRESSURE // Dangerously low pressure.
|
||||
var/light_dam // If set, mob will be damaged in light over this value and heal in light below its negative.
|
||||
var/body_temperature = 310.15 // Species will try to stabilize at this temperature.
|
||||
// (also affects temperature processing)
|
||||
var/body_temperature = 310.15 // Species will try to stabilize at this temperature. (also affects temperature processing)
|
||||
var/minimum_breath_pressure = 16 // Minimum required pressure for breath, in kPa
|
||||
|
||||
var/heat_discomfort_level = 315 // Aesthetic messages about feeling warm.
|
||||
var/cold_discomfort_level = 285 // Aesthetic messages about feeling chilly.
|
||||
|
||||
@@ -20,7 +20,7 @@ var/datum/species/shapeshifter/promethean/prometheans
|
||||
bump_flag = SLIME
|
||||
swap_flags = MONKEY|SLIME|SIMPLE_ANIMAL
|
||||
push_flags = MONKEY|SLIME|SIMPLE_ANIMAL
|
||||
flags = NO_SCAN | NO_SLIP | NO_MINOR_CUT
|
||||
flags = NO_SCAN | NO_SLIP | NO_MINOR_CUT | NO_HALLUCINATION
|
||||
appearance_flags = HAS_SKIN_COLOR | HAS_EYE_COLOR | HAS_HAIR_COLOR | RADIATION_GLOWS | HAS_UNDERWEAR
|
||||
spawn_flags = SPECIES_CAN_JOIN | SPECIES_IS_WHITELISTED
|
||||
health_hud_intensity = 2
|
||||
|
||||
@@ -67,6 +67,8 @@
|
||||
)
|
||||
cold_discomfort_level = 180
|
||||
|
||||
minimum_breath_pressure = 12 //Smaller, so needs less air
|
||||
|
||||
has_limbs = list(
|
||||
BP_TORSO = list("path" = /obj/item/organ/external/chest),
|
||||
BP_GROIN = list("path" = /obj/item/organ/external/groin),
|
||||
|
||||
@@ -60,6 +60,8 @@
|
||||
heat_level_2 = 480 //Default 400
|
||||
heat_level_3 = 1100 //Default 1000
|
||||
|
||||
minimum_breath_pressure = 18 //Bigger, means they need more air
|
||||
|
||||
spawn_flags = SPECIES_CAN_JOIN | SPECIES_IS_WHITELISTED
|
||||
appearance_flags = HAS_HAIR_COLOR | HAS_LIPS | HAS_UNDERWEAR | HAS_SKIN_COLOR | HAS_EYE_COLOR
|
||||
|
||||
|
||||
@@ -2,7 +2,7 @@
|
||||
|
||||
//drop && roll
|
||||
if(on_fire && !buckled)
|
||||
fire_stacks -= 1.2
|
||||
adjust_fire_stacks(-1.2)
|
||||
Weaken(3)
|
||||
spin(32,2)
|
||||
visible_message(
|
||||
|
||||
@@ -151,15 +151,15 @@ var/list/ai_verbs_hidden = list( // For why this exists, refer to https://xkcd.c
|
||||
//Languages
|
||||
add_language("Robot Talk", 1)
|
||||
add_language(LANGUAGE_GALCOM, 1)
|
||||
add_language(LANGUAGE_SOL_COMMON, 0)
|
||||
add_language(LANGUAGE_UNATHI, 0)
|
||||
add_language(LANGUAGE_SIIK, 0)
|
||||
add_language(LANGUAGE_SKRELLIAN, 0)
|
||||
add_language(LANGUAGE_SOL_COMMON, 1)
|
||||
add_language(LANGUAGE_UNATHI, 1)
|
||||
add_language(LANGUAGE_SIIK, 1)
|
||||
add_language(LANGUAGE_SKRELLIAN, 1)
|
||||
add_language(LANGUAGE_TRADEBAND, 1)
|
||||
add_language(LANGUAGE_GUTTER, 0)
|
||||
add_language(LANGUAGE_GUTTER, 1)
|
||||
add_language(LANGUAGE_EAL, 1)
|
||||
add_language(LANGUAGE_SCHECHI, 0)
|
||||
add_language(LANGUAGE_SIGN, 0)
|
||||
add_language(LANGUAGE_SCHECHI, 1)
|
||||
add_language(LANGUAGE_SIGN, 1)
|
||||
|
||||
if(!safety)//Only used by AIize() to successfully spawn an AI.
|
||||
if (!B)//If there is no player/brain inside.
|
||||
|
||||
@@ -715,7 +715,9 @@
|
||||
overlays += "[panelprefix]-openpanel -c"
|
||||
|
||||
if(has_active_type(/obj/item/borg/combat/shield))
|
||||
overlays += "[module_sprites[icontype]]-shield"
|
||||
var/obj/item/borg/combat/shield/shield = locate() in src
|
||||
if(shield && shield.active)
|
||||
overlays += "[module_sprites[icontype]]-shield"
|
||||
|
||||
if(modtype == "Combat")
|
||||
if(module_active && istype(module_active,/obj/item/borg/combat/mobility))
|
||||
|
||||
@@ -70,7 +70,7 @@
|
||||
//Combat shielding absorbs a percentage of damage directly into the cell.
|
||||
if(has_active_type(/obj/item/borg/combat/shield))
|
||||
var/obj/item/borg/combat/shield/shield = locate() in src
|
||||
if(shield)
|
||||
if(shield && shield.active)
|
||||
//Shields absorb a certain percentage of damage based on their power setting.
|
||||
var/absorb_brute = brute*shield.shield_level
|
||||
var/absorb_burn = burn*shield.shield_level
|
||||
|
||||
@@ -298,11 +298,54 @@
|
||||
desc = "A powerful experimental module that turns aside or absorbs incoming attacks at the cost of charge."
|
||||
icon = 'icons/obj/decals.dmi'
|
||||
icon_state = "shock"
|
||||
var/shield_level = 0.5 //Percentage of damage absorbed by the shield.
|
||||
var/shield_level = 0.5 //Percentage of damage absorbed by the shield.
|
||||
var/active = 1 //If the shield is on
|
||||
var/flash_count = 0 //Counter for how many times the shield has been flashed
|
||||
var/overload_threshold = 3 //Number of flashes it takes to overload the shield
|
||||
var/shield_refresh = 15 SECONDS //Time it takes for the shield to reboot after destabilizing
|
||||
var/overload_time = 0 //Stores the time of overload
|
||||
var/last_flash = 0 //Stores the time of last flash
|
||||
|
||||
/obj/item/borg/combat/shield/New()
|
||||
processing_objects.Add(src)
|
||||
..()
|
||||
|
||||
/obj/item/borg/combat/shield/Destroy()
|
||||
processing_objects.Remove(src)
|
||||
..()
|
||||
|
||||
/obj/item/borg/combat/shield/attack_self(var/mob/living/user)
|
||||
set_shield_level()
|
||||
|
||||
/obj/item/borg/combat/shield/process()
|
||||
if(active)
|
||||
if(flash_count && (last_flash + shield_refresh < world.time))
|
||||
flash_count = 0
|
||||
last_flash = 0
|
||||
else if(overload_time + shield_refresh < world.time)
|
||||
active = 1
|
||||
flash_count = 0
|
||||
overload_time = 0
|
||||
|
||||
var/mob/living/user = src.loc
|
||||
user.visible_message("<span class='danger'>[user]'s shield reactivates!</span>", "<span class='danger'>Your shield reactivates!.</span>")
|
||||
user.update_icon()
|
||||
|
||||
/obj/item/borg/combat/shield/proc/adjust_flash_count(var/mob/living/user, amount)
|
||||
if(active) //Can't destabilize a shield that's not on
|
||||
flash_count += amount
|
||||
|
||||
if(amount > 0)
|
||||
last_flash = world.time
|
||||
if(flash_count >= overload_threshold)
|
||||
overload(user)
|
||||
|
||||
/obj/item/borg/combat/shield/proc/overload(var/mob/living/user)
|
||||
active = 0
|
||||
user.visible_message("<span class='danger'>[user]'s shield destabilizes!</span>", "<span class='danger'>Your shield destabilizes!.</span>")
|
||||
user.update_icon()
|
||||
overload_time = world.time
|
||||
|
||||
/obj/item/borg/combat/shield/verb/set_shield_level()
|
||||
set name = "Set shield level"
|
||||
set category = "Object"
|
||||
|
||||
@@ -1,6 +1,11 @@
|
||||
// Hivebots are tuned towards how many default lasers are needed to kill them.
|
||||
// As such, if laser damage is ever changed, you should change this define.
|
||||
#define LASERS_TO_KILL *40
|
||||
|
||||
// Default hivebot is melee, and a bit more meaty, so it can meatshield for their ranged friends.
|
||||
/mob/living/simple_animal/hostile/hivebot
|
||||
name = "Hivebot"
|
||||
desc = "A small robot"
|
||||
name = "hivebot"
|
||||
desc = "A robot. It appears to be somewhat reslient, but lacking a true weapon."
|
||||
icon = 'icons/mob/hivebot.dmi'
|
||||
icon_state = "basic"
|
||||
icon_living = "basic"
|
||||
@@ -8,16 +13,16 @@
|
||||
|
||||
faction = "hivebot"
|
||||
intelligence_level = SA_ROBOTIC
|
||||
maxHealth = 15
|
||||
health = 15
|
||||
maxHealth = 3 LASERS_TO_KILL
|
||||
health = 3 LASERS_TO_KILL
|
||||
speed = 4
|
||||
|
||||
melee_damage_lower = 2
|
||||
melee_damage_upper = 3
|
||||
melee_damage_lower = 15
|
||||
melee_damage_upper = 15
|
||||
|
||||
attacktext = "clawed"
|
||||
projectilesound = 'sound/weapons/Gunshot.ogg'
|
||||
projectiletype = /obj/item/projectile/hivebotbullet
|
||||
projectiletype = /obj/item/projectile/bullet/hivebot
|
||||
|
||||
min_oxy = 0
|
||||
max_oxy = 0
|
||||
@@ -29,19 +34,102 @@
|
||||
max_n2 = 0
|
||||
minbodytemp = 0
|
||||
|
||||
cooperative = TRUE
|
||||
firing_lines = TRUE
|
||||
investigates = TRUE
|
||||
|
||||
speak_chance = 1
|
||||
speak = list(
|
||||
"Resuming task: Protect area.",
|
||||
"No threats found.",
|
||||
"Error: No targets found."
|
||||
)
|
||||
emote_hear = list("humms ominously", "whirrs softly", "grinds a gear")
|
||||
emote_see = list("looks around the area", "turns from side to side")
|
||||
say_understood = list("Affirmative.", "Positive")
|
||||
say_cannot = list("Denied.", "Negative")
|
||||
say_maybe_target = list("Possible threat detected. Investigating.", "Motion detected.", "Investigating.")
|
||||
say_got_target = list("Threat detected.", "New task: Remove threat.", "Threat removal engaged.", "Engaging target.")
|
||||
|
||||
// Subtypes.
|
||||
|
||||
// Melee like the base type, but more fragile.
|
||||
/mob/living/simple_animal/hostile/hivebot/swarm
|
||||
name = "swarm hivebot"
|
||||
desc = "A robot. It looks fragile and weak"
|
||||
maxHealth = 1 LASERS_TO_KILL
|
||||
health = 1 LASERS_TO_KILL
|
||||
melee_damage_lower = 3
|
||||
melee_damage_upper = 3
|
||||
|
||||
// This one has a semi-weak ranged attack.
|
||||
/mob/living/simple_animal/hostile/hivebot/range
|
||||
name = "Hivebot"
|
||||
desc = "A smallish robot, this one is armed!"
|
||||
name = "ranged hivebot"
|
||||
desc = "A robot. It has a simple ballistic weapon."
|
||||
ranged = 1
|
||||
maxHealth = 2 LASERS_TO_KILL
|
||||
health = 2 LASERS_TO_KILL
|
||||
|
||||
// This one shoots a burst of three, and is considerably more dangerous.
|
||||
/mob/living/simple_animal/hostile/hivebot/range/rapid
|
||||
name = "rapid hivebot"
|
||||
desc = "A robot. It has a fast firing ballistic rifle."
|
||||
icon_living = "strong"
|
||||
rapid = 1
|
||||
maxHealth = 2 LASERS_TO_KILL
|
||||
health = 2 LASERS_TO_KILL
|
||||
|
||||
/mob/living/simple_animal/hostile/hivebot/strong
|
||||
name = "Strong Hivebot"
|
||||
desc = "A robot, this one is armed and looks tough!"
|
||||
health = 80
|
||||
ranged = 1
|
||||
// Shoots EMPs, to screw over other robots.
|
||||
/mob/living/simple_animal/hostile/hivebot/range/ion
|
||||
name = "engineering hivebot"
|
||||
desc = "A robot. It has a tool which emits focused electromagnetic pulses, which are deadly to other synthetic adverseries."
|
||||
projectiletype = /obj/item/projectile/ion
|
||||
projectilesound = 'sound/weapons/Laser.ogg'
|
||||
icon_living = "engi"
|
||||
ranged = TRUE
|
||||
maxHealth = 2 LASERS_TO_KILL
|
||||
health = 2 LASERS_TO_KILL
|
||||
|
||||
// Shoots deadly lasers.
|
||||
/mob/living/simple_animal/hostile/hivebot/range/laser
|
||||
name = "laser hivebot"
|
||||
desc = "A robot. It has an energy weapon."
|
||||
projectiletype = /obj/item/projectile/beam/blue
|
||||
projectilesound = 'sound/weapons/Laser.ogg'
|
||||
maxHealth = 2 LASERS_TO_KILL
|
||||
health = 2 LASERS_TO_KILL
|
||||
|
||||
// Beefy and ranged.
|
||||
/mob/living/simple_animal/hostile/hivebot/range/strong
|
||||
name = "strong hivebot"
|
||||
desc = "A robot. This one has reinforced plating, and looks tougher."
|
||||
icon_living = "strong"
|
||||
maxHealth = 4 LASERS_TO_KILL
|
||||
health = 4 LASERS_TO_KILL
|
||||
melee_damage_lower = 15
|
||||
melee_damage_upper = 15
|
||||
|
||||
// Also beefy, but tries to stay at their 'home', ideal for base defense.
|
||||
/mob/living/simple_animal/hostile/hivebot/range/guard
|
||||
name = "guard hivebot"
|
||||
desc = "A robot. It seems to be guarding something."
|
||||
returns_home = TRUE
|
||||
maxHealth = 4 LASERS_TO_KILL
|
||||
health = 4 LASERS_TO_KILL
|
||||
|
||||
// This one is intended for players to use. Well rounded and can make other hivebots follow them with verbs.
|
||||
/mob/living/simple_animal/hostile/hivebot/range/player
|
||||
name = "commander hivebot"
|
||||
desc = "A robot. This one seems to direct the others, and it has a laser weapon."
|
||||
icon_living = "commander"
|
||||
maxHealth = 5 LASERS_TO_KILL
|
||||
health = 5 LASERS_TO_KILL
|
||||
projectiletype = /obj/item/projectile/beam/blue
|
||||
projectilesound = 'sound/weapons/Laser.ogg'
|
||||
melee_damage_lower = 15 // Needed to force open airlocks.
|
||||
melee_damage_upper = 15
|
||||
|
||||
// Procs.
|
||||
|
||||
/mob/living/simple_animal/hostile/hivebot/death()
|
||||
..()
|
||||
@@ -52,6 +140,42 @@
|
||||
s.start()
|
||||
qdel(src)
|
||||
|
||||
/mob/living/simple_animal/hostile/hivebot/speech_bubble_appearance()
|
||||
return "synthetic_evil"
|
||||
|
||||
/mob/living/simple_animal/hostile/hivebot/verb/command_follow()
|
||||
set name = "Command - Follow"
|
||||
set category = "Hivebot"
|
||||
set desc = "This will ask other hivebots to follow you."
|
||||
|
||||
say("Delegating new task: Follow.")
|
||||
|
||||
for(var/mob/living/simple_animal/hostile/hivebot/buddy in hearers(src))
|
||||
if(buddy.faction != faction)
|
||||
continue
|
||||
if(buddy == src)
|
||||
continue
|
||||
buddy.set_follow(src)
|
||||
buddy.FollowTarget()
|
||||
spawn(rand(5, 10))
|
||||
buddy.say( pick(buddy.say_understood) )
|
||||
|
||||
/mob/living/simple_animal/hostile/hivebot/verb/command_stop()
|
||||
set name = "Command - Stop Following"
|
||||
set category = "Hivebot"
|
||||
set desc = "This will ask other hivebots to cease following you."
|
||||
|
||||
say("Delegating new task: Stop following.")
|
||||
|
||||
for(var/mob/living/simple_animal/hostile/hivebot/buddy in hearers(src))
|
||||
if(buddy.faction != faction)
|
||||
continue
|
||||
if(buddy == src)
|
||||
continue
|
||||
buddy.LoseFollow()
|
||||
spawn(rand(5, 10))
|
||||
buddy.say( pick(buddy.say_understood) )
|
||||
|
||||
/mob/living/simple_animal/hostile/hivebot/tele//this still needs work
|
||||
name = "Beacon"
|
||||
desc = "Some odd beacon thing"
|
||||
@@ -107,6 +231,6 @@
|
||||
if(prob(2))//Might be a bit low, will mess with it likely
|
||||
warpbots()
|
||||
|
||||
/obj/item/projectile/hivebotbullet
|
||||
/obj/item/projectile/bullet/hivebot
|
||||
damage = 10
|
||||
damage_type = BRUTE
|
||||
|
||||
@@ -43,6 +43,17 @@
|
||||
var/poison_per_bite = 5
|
||||
var/poison_chance = 10
|
||||
var/poison_type = "spidertoxin"
|
||||
var/image/eye_layer = null
|
||||
|
||||
/mob/living/simple_animal/hostile/giant_spider/proc/add_eyes()
|
||||
if(!eye_layer)
|
||||
var/overlay_layer = LIGHTING_LAYER+0.1
|
||||
eye_layer = image(icon, "[icon_state]-eyes", overlay_layer)
|
||||
|
||||
overlays += eye_layer
|
||||
|
||||
/mob/living/simple_animal/hostile/giant_spider/proc/remove_eyes()
|
||||
overlays -= eye_layer
|
||||
|
||||
//nursemaids - these create webs and eggs
|
||||
/mob/living/simple_animal/hostile/giant_spider/nurse
|
||||
@@ -61,6 +72,7 @@
|
||||
|
||||
var/fed = 0
|
||||
var/atom/cocoon_target
|
||||
var/egg_inject_chance = 5
|
||||
|
||||
//hunters have the most poison and move the fastest, so they can find prey
|
||||
/mob/living/simple_animal/hostile/giant_spider/hunter
|
||||
@@ -96,33 +108,43 @@
|
||||
|
||||
/mob/living/simple_animal/hostile/giant_spider/New(var/location, var/atom/parent)
|
||||
get_light_and_color(parent)
|
||||
add_eyes()
|
||||
..()
|
||||
|
||||
/mob/living/simple_animal/hostile/giant_spider/PunchTarget()
|
||||
. = ..()
|
||||
if(isliving(.))
|
||||
var/mob/living/L = .
|
||||
if(L.reagents)
|
||||
L.reagents.add_reagent(poison_type, poison_per_bite)
|
||||
if(prob(poison_chance))
|
||||
L << "<span class='warning'>You feel a tiny prick.</span>"
|
||||
L.reagents.add_reagent(poison_type, poison_per_bite)
|
||||
/mob/living/simple_animal/hostile/giant_spider/death()
|
||||
remove_eyes()
|
||||
..()
|
||||
|
||||
/mob/living/simple_animal/hostile/giant_spider/nurse/PunchTarget()
|
||||
/mob/living/simple_animal/hostile/giant_spider/DoPunch(var/atom/A)
|
||||
. = ..()
|
||||
if(ishuman(.))
|
||||
var/mob/living/carbon/human/H = .
|
||||
if(prob(5))
|
||||
var/obj/item/organ/external/O = pick(H.organs)
|
||||
if(!(O.robotic >= ORGAN_ROBOT))
|
||||
var/eggcount
|
||||
for(var/obj/I in O.implants)
|
||||
if(istype(I, /obj/effect/spider/eggcluster))
|
||||
eggcount ++
|
||||
if(!eggcount)
|
||||
var/eggs = new /obj/effect/spider/eggcluster/small(O, src)
|
||||
O.implants += eggs
|
||||
H << "<span class='warning'>The [src] injects something into your [O.name]!</span>"
|
||||
if(.) // If we succeeded in hitting.
|
||||
if(isliving(A))
|
||||
var/mob/living/L = A
|
||||
if(L.reagents)
|
||||
var/target_zone = pick(BP_TORSO,BP_TORSO,BP_TORSO,BP_L_LEG,BP_R_LEG,BP_L_ARM,BP_R_ARM,BP_HEAD)
|
||||
if(L.can_inject(src, null, target_zone))
|
||||
L.reagents.add_reagent(poison_type, poison_per_bite)
|
||||
if(prob(poison_chance))
|
||||
to_chat(L, "<span class='warning'>You feel a tiny prick.</span>")
|
||||
L.reagents.add_reagent(poison_type, poison_per_bite)
|
||||
|
||||
/mob/living/simple_animal/hostile/giant_spider/nurse/DoPunch(var/atom/A)
|
||||
. = ..()
|
||||
if(.) // If we succeeded in hitting.
|
||||
if(ishuman(A))
|
||||
var/mob/living/carbon/human/H = A
|
||||
if(prob(egg_inject_chance))
|
||||
var/target_zone = pick(BP_TORSO,BP_TORSO,BP_TORSO,BP_L_LEG,BP_R_LEG,BP_L_ARM,BP_R_ARM,BP_HEAD)
|
||||
if(H.can_inject(src, null, target_zone))
|
||||
var/obj/item/organ/external/O = H.get_organ(target_zone)
|
||||
var/eggcount
|
||||
for(var/obj/I in O.implants)
|
||||
if(istype(I, /obj/effect/spider/eggcluster))
|
||||
eggcount ++
|
||||
if(!eggcount)
|
||||
var/eggs = new /obj/effect/spider/eggcluster/small(O, src)
|
||||
O.implants += eggs
|
||||
to_chat(H, "<font size='3'><span class='warning'>\The [src] injects something into your [O.name]!</span></font>")
|
||||
|
||||
/mob/living/simple_animal/hostile/giant_spider/handle_stance()
|
||||
. = ..()
|
||||
|
||||
@@ -40,6 +40,15 @@
|
||||
var/list/req_access = list(access_robotics) //Access needed to pop out the brain.
|
||||
var/positronic
|
||||
|
||||
can_enter_vent_with = list(
|
||||
/obj/item/weapon/implant,
|
||||
/obj/item/device/radio/borg,
|
||||
/obj/item/weapon/holder,
|
||||
/obj/machinery/camera,
|
||||
/mob/living/simple_animal/borer,
|
||||
/obj/item/device/mmi,
|
||||
)
|
||||
|
||||
var/emagged = 0
|
||||
var/obj/item/held_item = null //Storage for single item they can hold.
|
||||
|
||||
|
||||
@@ -1230,14 +1230,22 @@
|
||||
// This is the actual act of 'punching'. Override for special behaviour.
|
||||
/mob/living/simple_animal/proc/DoPunch(var/atom/A)
|
||||
if(!Adjacent(target_mob)) // They could've moved in the meantime.
|
||||
return
|
||||
return FALSE
|
||||
|
||||
var/damage_to_do = rand(melee_damage_lower, melee_damage_upper)
|
||||
|
||||
for(var/datum/modifier/M in modifiers)
|
||||
if(!isnull(M.outgoing_melee_damage_percent))
|
||||
damage_to_do *= M.outgoing_melee_damage_percent
|
||||
|
||||
// SA attacks can be blocked with shields.
|
||||
if(ishuman(A))
|
||||
var/mob/living/carbon/human/H = A
|
||||
if(H.check_shields(damage = damage_to_do, damage_source = src, attacker = src, def_zone = null, attack_text = "the attack"))
|
||||
return FALSE
|
||||
|
||||
A.attack_generic(src, damage_to_do, attacktext)
|
||||
return TRUE
|
||||
|
||||
//The actual top-level ranged attack proc
|
||||
/mob/living/simple_animal/proc/ShootTarget()
|
||||
|
||||
@@ -88,6 +88,10 @@
|
||||
var/reagent_injected = null // Some slimes inject reagents on attack. This tells the game what reagent to use.
|
||||
var/injection_amount = 5 // This determines how much.
|
||||
|
||||
can_enter_vent_with = list(
|
||||
/obj/item/clothing/head,
|
||||
)
|
||||
|
||||
/mob/living/simple_animal/slime/New(var/location, var/start_as_adult = FALSE)
|
||||
verbs += /mob/living/proc/ventcrawl
|
||||
if(start_as_adult)
|
||||
|
||||
@@ -501,6 +501,10 @@
|
||||
if(!dense_object && (locate(/obj/structure/lattice) in oview(1, src)))
|
||||
dense_object++
|
||||
|
||||
if(!dense_object && (locate(/obj/structure/catwalk) in oview(1, src)))
|
||||
dense_object++
|
||||
|
||||
|
||||
//Lastly attempt to locate any dense objects we could push off of
|
||||
//TODO: If we implement objects drifing in space this needs to really push them
|
||||
//Due to a few issues only anchored and dense objects will now work.
|
||||
|
||||
@@ -77,10 +77,26 @@
|
||||
else
|
||||
O.key = key
|
||||
|
||||
//Languages
|
||||
add_language("Robot Talk", 1)
|
||||
add_language(LANGUAGE_GALCOM, 1)
|
||||
add_language(LANGUAGE_SOL_COMMON, 1)
|
||||
add_language(LANGUAGE_UNATHI, 1)
|
||||
add_language(LANGUAGE_SIIK, 1)
|
||||
add_language(LANGUAGE_SKRELLIAN, 1)
|
||||
add_language(LANGUAGE_TRADEBAND, 1)
|
||||
add_language(LANGUAGE_GUTTER, 1)
|
||||
add_language(LANGUAGE_EAL, 1)
|
||||
add_language(LANGUAGE_SCHECHI, 1)
|
||||
add_language(LANGUAGE_SIGN, 1)
|
||||
|
||||
// Lorefolks say it may be so.
|
||||
if(O.client && O.client.prefs)
|
||||
var/datum/preferences/B = O.client.prefs
|
||||
for(var/language in B.alternate_languages)
|
||||
O.add_language(language)
|
||||
if(LANGUAGE_ROOTGLOBAL in B.alternate_languages)
|
||||
O.add_language(LANGUAGE_ROOTGLOBAL, 1)
|
||||
if(LANGUAGE_ROOTLOCAL in B.alternate_languages)
|
||||
O.add_language(LANGUAGE_ROOTLOCAL, 1)
|
||||
|
||||
if(move)
|
||||
var/obj/loc_landmark
|
||||
|
||||
@@ -127,6 +127,7 @@
|
||||
desc = "A complex, organic knot of jelly and crystalline particles."
|
||||
icon = 'icons/mob/slimes.dmi'
|
||||
icon_state = "green slime extract"
|
||||
parent_organ = BP_TORSO
|
||||
|
||||
/obj/item/organ/internal/brain/golem
|
||||
name = "chem"
|
||||
|
||||
@@ -39,10 +39,11 @@
|
||||
|
||||
// Do some reagent processing.
|
||||
if(owner.chem_effects[CE_ALCOHOL_TOXIC])
|
||||
take_damage(owner.chem_effects[CE_ALCOHOL_TOXIC] * 0.1 * PROCESS_ACCURACY, prob(1)) // Chance to warn them
|
||||
if(filter_effect < 2) //Liver is badly damaged, you're drinking yourself to death
|
||||
owner.adjustToxLoss(owner.chem_effects[CE_ALCOHOL_TOXIC] * 0.2 * PROCESS_ACCURACY)
|
||||
if(filter_effect < 3)
|
||||
owner.adjustToxLoss(owner.chem_effects[CE_ALCOHOL_TOXIC] * 0.1 * PROCESS_ACCURACY)
|
||||
else
|
||||
take_damage(owner.chem_effects[CE_ALCOHOL_TOXIC] * 0.1 * PROCESS_ACCURACY, prob(1)) // Chance to warn them
|
||||
|
||||
/obj/item/organ/internal/liver/handle_germ_effects()
|
||||
. = ..() //Up should return an infection level as an integer
|
||||
|
||||
@@ -0,0 +1,47 @@
|
||||
/obj/item/organ/external/chest/unbreakable/slime
|
||||
nonsolid = 1
|
||||
max_damage = 50
|
||||
encased = 0
|
||||
|
||||
/obj/item/organ/external/groin/unbreakable/slime
|
||||
nonsolid = 1
|
||||
max_damage = 30
|
||||
|
||||
/obj/item/organ/external/arm/unbreakable/slime
|
||||
nonsolid = 1
|
||||
max_damage = 5
|
||||
|
||||
/obj/item/organ/external/arm/right/unbreakable/slime
|
||||
nonsolid = 1
|
||||
max_damage = 5
|
||||
|
||||
/obj/item/organ/external/leg/unbreakable/slime
|
||||
nonsolid = 1
|
||||
max_damage = 5
|
||||
|
||||
/obj/item/organ/external/leg/right/unbreakable/slime
|
||||
nonsolid = 1
|
||||
max_damage = 5
|
||||
|
||||
/obj/item/organ/external/foot/unbreakable/slime
|
||||
nonsolid = 1
|
||||
max_damage = 5
|
||||
|
||||
/obj/item/organ/external/foot/right/unbreakable/slime
|
||||
nonsolid = 1
|
||||
max_damage = 5
|
||||
|
||||
/obj/item/organ/external/hand/unbreakable/slime
|
||||
nonsolid = 1
|
||||
max_damage = 5
|
||||
|
||||
/obj/item/organ/external/hand/right/unbreakable/slime
|
||||
nonsolid = 1
|
||||
max_damage = 5
|
||||
|
||||
/obj/item/organ/external/head/unbreakable/slime //They don't need this anymore.
|
||||
nonsolid = 1
|
||||
cannot_gib = 0
|
||||
vital = 0
|
||||
max_damage = 5
|
||||
encased = 0
|
||||
@@ -40,49 +40,4 @@
|
||||
|
||||
/obj/item/organ/external/head/unbreakable
|
||||
cannot_break = 1
|
||||
dislocated = -1
|
||||
|
||||
// Slime limbs.
|
||||
/obj/item/organ/external/chest/unbreakable/slime
|
||||
nonsolid = 1
|
||||
max_damage = 50
|
||||
|
||||
/obj/item/organ/external/groin/unbreakable/slime
|
||||
nonsolid = 1
|
||||
max_damage = 30
|
||||
|
||||
/obj/item/organ/external/arm/unbreakable/slime
|
||||
nonsolid = 1
|
||||
max_damage = 5
|
||||
|
||||
/obj/item/organ/external/arm/right/unbreakable/slime
|
||||
nonsolid = 1
|
||||
max_damage = 5
|
||||
|
||||
/obj/item/organ/external/leg/unbreakable/slime
|
||||
nonsolid = 1
|
||||
max_damage = 5
|
||||
|
||||
/obj/item/organ/external/leg/right/unbreakable/slime
|
||||
nonsolid = 1
|
||||
max_damage = 5
|
||||
|
||||
/obj/item/organ/external/foot/unbreakable/slime
|
||||
nonsolid = 1
|
||||
max_damage = 5
|
||||
|
||||
/obj/item/organ/external/foot/right/unbreakable/slime
|
||||
nonsolid = 1
|
||||
max_damage = 5
|
||||
|
||||
/obj/item/organ/external/hand/unbreakable/slime
|
||||
nonsolid = 1
|
||||
max_damage = 5
|
||||
|
||||
/obj/item/organ/external/hand/right/unbreakable/slime
|
||||
nonsolid = 1
|
||||
max_damage = 5
|
||||
|
||||
/obj/item/organ/external/head/unbreakable/slime
|
||||
nonsolid = 1
|
||||
max_damage = 5
|
||||
dislocated = -1
|
||||
@@ -16,7 +16,7 @@
|
||||
|
||||
/obj/item/weapon/cell/process()
|
||||
if(self_recharge)
|
||||
give(charge_amount / CELLRATE)
|
||||
give(charge_amount)
|
||||
else
|
||||
return PROCESS_KILL
|
||||
|
||||
@@ -59,6 +59,7 @@
|
||||
return 0
|
||||
var/used = min(charge, amount)
|
||||
charge -= used
|
||||
update_icon()
|
||||
return used
|
||||
|
||||
// Checks if the specified amount can be provided. If it can, it removes the amount
|
||||
@@ -78,24 +79,29 @@
|
||||
if(maxcharge < amount) return 0
|
||||
var/amount_used = min(maxcharge-charge,amount)
|
||||
charge += amount_used
|
||||
update_icon()
|
||||
return amount_used
|
||||
|
||||
|
||||
/obj/item/weapon/cell/examine(mob/user)
|
||||
if(get_dist(src, user) > 1)
|
||||
return
|
||||
var/msg = desc
|
||||
|
||||
if(maxcharge <= 2500)
|
||||
user << "[desc]\nThe manufacturer's label states this cell has a power rating of [maxcharge], and that you should not swallow it.\nThe charge meter reads [round(src.percent() )]%."
|
||||
else
|
||||
user << "This power cell has an exciting chrome finish, as it is an uber-capacity cell type! It has a power rating of [maxcharge]!\nThe charge meter reads [round(src.percent() )]%."
|
||||
if(get_dist(src, user) <= 1)
|
||||
msg += " It has a power rating of [maxcharge].\nThe charge meter reads [round(src.percent() )]%."
|
||||
|
||||
to_chat(user, msg)
|
||||
/*
|
||||
if(maxcharge <= 2500)
|
||||
to_chat(user, "[desc]\nThe manufacturer's label states this cell has a power rating of [maxcharge], and that you should not swallow it.\nThe charge meter reads [round(src.percent() )]%.")
|
||||
else
|
||||
to_chat(user, "This power cell has an exciting chrome finish, as it is an uber-capacity cell type! It has a power rating of [maxcharge]!\nThe charge meter reads [round(src.percent() )]%.")
|
||||
*/
|
||||
/obj/item/weapon/cell/attackby(obj/item/W, mob/user)
|
||||
..()
|
||||
if(istype(W, /obj/item/weapon/reagent_containers/syringe))
|
||||
var/obj/item/weapon/reagent_containers/syringe/S = W
|
||||
|
||||
user << "You inject the solution into the power cell."
|
||||
to_chat(user, "You inject the solution into the power cell.")
|
||||
|
||||
if(S.reagents.has_reagent("phoron", 5))
|
||||
|
||||
@@ -149,6 +155,8 @@
|
||||
charge -= charge / severity
|
||||
if (charge < 0)
|
||||
charge = 0
|
||||
|
||||
update_icon()
|
||||
..()
|
||||
|
||||
/obj/item/weapon/cell/ex_act(severity)
|
||||
|
||||
@@ -443,6 +443,23 @@
|
||||
/obj/item/ammo_magazine/m762m/empty
|
||||
initial_ammo = 0
|
||||
|
||||
/obj/item/ammo_magazine/m762garand
|
||||
name = "garand clip (7.62mm)" // The clip goes into the magazine, hence the name. I'm very sure this is correct.
|
||||
icon_state = "gclip"
|
||||
mag_type = MAGAZINE
|
||||
caliber = "7.62mm"
|
||||
matter = list(DEFAULT_WALL_MATERIAL = 1600)
|
||||
ammo_type = /obj/item/ammo_casing/a762
|
||||
max_ammo = 8
|
||||
multiple_sprites = 1
|
||||
|
||||
/obj/item/ammo_magazine/m762garand/ap
|
||||
name = "garand clip (7.62mm armor-piercing)"
|
||||
ammo_type = /obj/item/ammo_casing/a762/ap
|
||||
|
||||
/obj/item/ammo_magazine/m762/empty
|
||||
initial_ammo = 0
|
||||
|
||||
/obj/item/ammo_magazine/clip/c762
|
||||
name = "ammo clip (7.62mm)"
|
||||
icon_state = "clip_rifle"
|
||||
|
||||
@@ -0,0 +1,21 @@
|
||||
/obj/item/weapon/gun/projectile/garand
|
||||
name = "\improper M1 Garand"
|
||||
desc = "This is the vintage semi-automatic rifle that famously helped win the second World War. What the hell it's doing aboard a space station in the 26th century, you can only imagine. Uses 7.62mm rounds."
|
||||
icon_state = "garand"
|
||||
item_state = "boltaction"
|
||||
w_class = ITEMSIZE_LARGE
|
||||
caliber = "7.62mm"
|
||||
origin_tech = list(TECH_COMBAT = 2, TECH_MATERIAL = 2)
|
||||
slot_flags = SLOT_BACK
|
||||
fire_sound = 'sound/weapons/rifleshot.ogg'
|
||||
load_method = MAGAZINE // ToDo: Make it so MAGAZINE, SPEEDLOADER and SINGLE_CASING can all be used on the same gun.
|
||||
magazine_type = /obj/item/ammo_magazine/m762garand
|
||||
allowed_magazines = list(/obj/item/ammo_magazine/m762garand)
|
||||
auto_eject = 1
|
||||
auto_eject_sound = 'sound/weapons/garand_ping.ogg'
|
||||
|
||||
/obj/item/weapon/gun/projectile/garand/update_icon()
|
||||
if(ammo_magazine)
|
||||
icon_state = initial(icon_state)
|
||||
else
|
||||
icon_state = "[initial(icon_state)]-e"
|
||||
@@ -202,8 +202,9 @@
|
||||
|
||||
admin_attack_log(firer, target_mob, attacker_message, victim_message, admin_message)
|
||||
else
|
||||
target_mob.attack_log += "\[[time_stamp()]\] <b>UNKNOWN SUBJECT (No longer exists)</b> shot <b>[target_mob]/[target_mob.ckey]</b> with <b>\a [src]</b>"
|
||||
msg_admin_attack("UNKNOWN shot [target_mob] ([target_mob.ckey]) with \a [src] (<A HREF='?_src_=holder;adminplayerobservecoodjump=1;X=[target_mob.x];Y=[target_mob.y];Z=[target_mob.z]'>JMP</a>)")
|
||||
if(target_mob) // Sometimes the target_mob gets gibbed or something.
|
||||
target_mob.attack_log += "\[[time_stamp()]\] <b>UNKNOWN SUBJECT (No longer exists)</b> shot <b>[target_mob]/[target_mob.ckey]</b> with <b>\a [src]</b>"
|
||||
msg_admin_attack("UNKNOWN shot [target_mob] ([target_mob.ckey]) with \a [src] (<A HREF='?_src_=holder;adminplayerobservecoodjump=1;X=[target_mob.x];Y=[target_mob.y];Z=[target_mob.z]'>JMP</a>)")
|
||||
|
||||
//sometimes bullet_act() will want the projectile to continue flying
|
||||
if (result == PROJECTILE_CONTINUE)
|
||||
|
||||
@@ -161,7 +161,7 @@
|
||||
return
|
||||
|
||||
/obj/item/weapon/reagent_containers/food/drinks/glass2/standard_feed_mob(var/mob/user, var/mob/target)
|
||||
if(afterattack()) //Check to see if harm intent & splash.
|
||||
if(afterattack(target, user)) //Check to see if harm intent & splash.
|
||||
return
|
||||
else
|
||||
..() //If they're splashed, no need to do anything else.
|
||||
@@ -58,7 +58,7 @@
|
||||
return
|
||||
|
||||
if(mode == SYRINGE_BROKEN)
|
||||
user << "<span class='warning'>This syringe is broken!</span>"
|
||||
to_chat(user, "<span class='warning'>This syringe is broken!</span>")
|
||||
return
|
||||
|
||||
if(user.a_intent == I_HURT && ismob(target))
|
||||
@@ -70,26 +70,31 @@
|
||||
switch(mode)
|
||||
if(SYRINGE_DRAW)
|
||||
if(!reagents.get_free_space())
|
||||
user << "<span class='warning'>The syringe is full.</span>"
|
||||
to_chat(user, "<span class='warning'>The syringe is full.</span>")
|
||||
mode = SYRINGE_INJECT
|
||||
return
|
||||
|
||||
if(ismob(target))//Blood!
|
||||
if(reagents.has_reagent("blood"))
|
||||
user << "<span class='notice'>There is already a blood sample in this syringe.</span>"
|
||||
to_chat(user, "<span class='notice'>There is already a blood sample in this syringe.</span>")
|
||||
return
|
||||
|
||||
if(istype(target, /mob/living/carbon))
|
||||
var/amount = reagents.get_free_space()
|
||||
var/mob/living/carbon/T = target
|
||||
if(!T.dna)
|
||||
user << "<span class='warning'>You are unable to locate any blood. (To be specific, your target seems to be missing their DNA datum).</span>"
|
||||
to_chat(user, "<span class='warning'>You are unable to locate any blood. (To be specific, your target seems to be missing their DNA datum).</span>")
|
||||
return
|
||||
if(NOCLONE in T.mutations) //target done been et, no more blood in him
|
||||
user << "<span class='warning'>You are unable to locate any blood.</span>"
|
||||
to_chat(user, "<span class='warning'>You are unable to locate any blood.</span>")
|
||||
return
|
||||
|
||||
if(T.isSynthetic())
|
||||
to_chat(user, "<span class = 'warning'>You can't draw blood from a synthetic!</span>")
|
||||
return
|
||||
|
||||
if(drawing)
|
||||
user << "<span class='warning'>You are already drawing blood from [T.name].</span>"
|
||||
to_chat(user, "<span class='warning'>You are already drawing blood from [T.name].</span>")
|
||||
return
|
||||
|
||||
var/datum/reagent/B
|
||||
@@ -117,50 +122,51 @@
|
||||
reagents.update_total()
|
||||
on_reagent_change()
|
||||
reagents.handle_reactions()
|
||||
user << "<span class='notice'>You take a blood sample from [target].</span>"
|
||||
to_chat(user, "<span class='notice'>You take a blood sample from [target].</span>")
|
||||
for(var/mob/O in viewers(4, user))
|
||||
O.show_message("<span class='notice'>[user] takes a blood sample from [target].</span>", 1)
|
||||
|
||||
else //if not mob
|
||||
if(!target.reagents.total_volume)
|
||||
user << "<span class='notice'>[target] is empty.</span>"
|
||||
to_chat(user, "<span class='notice'>[target] is empty.</span>")
|
||||
return
|
||||
|
||||
if(!target.is_open_container() && !istype(target, /obj/structure/reagent_dispensers) && !istype(target, /obj/item/slime_extract) && !istype(target, /obj/item/weapon/reagent_containers/food))
|
||||
user << "<span class='notice'>You cannot directly remove reagents from this object.</span>"
|
||||
to_chat(user, "<span class='notice'>You cannot directly remove reagents from this object.</span>")
|
||||
return
|
||||
|
||||
var/trans = target.reagents.trans_to_obj(src, amount_per_transfer_from_this)
|
||||
user << "<span class='notice'>You fill the syringe with [trans] units of the solution.</span>"
|
||||
to_chat(user, "<span class='notice'>You fill the syringe with [trans] units of the solution.</span>")
|
||||
update_icon()
|
||||
|
||||
|
||||
if(!reagents.get_free_space())
|
||||
mode = SYRINGE_INJECT
|
||||
update_icon()
|
||||
|
||||
if(SYRINGE_INJECT)
|
||||
if(!reagents.total_volume)
|
||||
user << "<span class='notice'>The syringe is empty.</span>"
|
||||
to_chat(user, "<span class='notice'>The syringe is empty.</span>")
|
||||
mode = SYRINGE_DRAW
|
||||
return
|
||||
if(istype(target, /obj/item/weapon/implantcase/chem))
|
||||
return
|
||||
|
||||
if(!target.is_open_container() && !ismob(target) && !istype(target, /obj/item/weapon/reagent_containers/food) && !istype(target, /obj/item/slime_extract) && !istype(target, /obj/item/clothing/mask/smokable/cigarette) && !istype(target, /obj/item/weapon/storage/fancy/cigarettes))
|
||||
user << "<span class='notice'>You cannot directly fill this object.</span>"
|
||||
to_chat(user, "<span class='notice'>You cannot directly fill this object.</span>")
|
||||
return
|
||||
if(!target.reagents.get_free_space())
|
||||
user << "<span class='notice'>[target] is full.</span>"
|
||||
to_chat(user, "<span class='notice'>[target] is full.</span>")
|
||||
return
|
||||
|
||||
var/mob/living/carbon/human/H = target
|
||||
if(istype(H))
|
||||
var/obj/item/organ/external/affected = H.get_organ(user.zone_sel.selecting)
|
||||
if(!affected)
|
||||
user << "<span class='danger'>\The [H] is missing that limb!</span>"
|
||||
to_chat(user, "<span class='danger'>\The [H] is missing that limb!</span>")
|
||||
return
|
||||
else if(affected.robotic >= ORGAN_ROBOT)
|
||||
user << "<span class='danger'>You cannot inject a robotic limb.</span>"
|
||||
to_chat(user, "<span class='danger'>You cannot inject a robotic limb.</span>")
|
||||
return
|
||||
|
||||
if(ismob(target) && target != user)
|
||||
@@ -200,9 +206,9 @@
|
||||
else
|
||||
trans = reagents.trans_to_obj(target, amount_per_transfer_from_this)
|
||||
if(trans)
|
||||
user << "<span class='notice'>You inject [trans] units of the solution. The syringe now contains [src.reagents.total_volume] units.</span>"
|
||||
to_chat(user, "<span class='notice'>You inject [trans] units of the solution. The syringe now contains [src.reagents.total_volume] units.</span>")
|
||||
else
|
||||
user << "<span class='notice'>The syringe is empty.</span>"
|
||||
to_chat(user, "<span class='notice'>The syringe is empty.</span>")
|
||||
if (reagents.total_volume <= 0 && mode == SYRINGE_INJECT)
|
||||
mode = SYRINGE_DRAW
|
||||
update_icon()
|
||||
@@ -245,7 +251,7 @@
|
||||
var/obj/item/organ/external/affecting = H.get_organ(target_zone)
|
||||
|
||||
if (!affecting || affecting.is_stump())
|
||||
user << "<span class='danger'>They are missing that limb!</span>"
|
||||
to_chat(user, "<span class='danger'>They are missing that limb!</span>")
|
||||
return
|
||||
|
||||
var/hit_area = affecting.name
|
||||
@@ -302,10 +308,10 @@
|
||||
|
||||
/obj/item/weapon/reagent_containers/syringe/ld50_syringe/afterattack(obj/target, mob/user, flag)
|
||||
if(mode == SYRINGE_DRAW && ismob(target)) // No drawing 50 units of blood at once
|
||||
user << "<span class='notice'>This needle isn't designed for drawing blood.</span>"
|
||||
to_chat(user, "<span class='notice'>This needle isn't designed for drawing blood.</span>")
|
||||
return
|
||||
if(user.a_intent == "hurt" && ismob(target)) // No instant injecting
|
||||
user << "<span class='notice'>This syringe is too big to stab someone with it.</span>"
|
||||
to_chat(user, "<span class='notice'>This syringe is too big to stab someone with it.</span>")
|
||||
..()
|
||||
|
||||
////////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
@@ -473,6 +473,15 @@ other types of metals and chemistry for reagents).
|
||||
build_path = /obj/item/weapon/surgical/scalpel/manager
|
||||
sort_string = "MBBAD"
|
||||
|
||||
/datum/design/item/bone_clamp
|
||||
name = "Bone Clamp"
|
||||
desc = "A miracle of modern science, this tool rapidly knits together bone, without the need for bone gel."
|
||||
id = "bone_clamp"
|
||||
req_tech = list(TECH_BIO = 4, TECH_MATERIAL = 5, TECH_MAGNET = 4, TECH_DATA = 4)
|
||||
materials = list (DEFAULT_WALL_MATERIAL = 12500, "glass" = 7500, "silver" = 2500)
|
||||
build_path = /obj/item/weapon/surgical/bone_clamp
|
||||
sort_string = "MBBAE"
|
||||
|
||||
/datum/design/item/implant
|
||||
materials = list(DEFAULT_WALL_MATERIAL = 50, "glass" = 50)
|
||||
|
||||
|
||||
@@ -145,4 +145,42 @@
|
||||
fail_step(mob/living/user, mob/living/carbon/human/target, target_zone, obj/item/tool)
|
||||
var/obj/item/organ/external/affected = target.get_organ(target_zone)
|
||||
user.visible_message("<font color='red'>[user]'s hand slips, smearing [tool] in the incision in [target]'s [affected.name]!</font>" , \
|
||||
"<font color='red'>Your hand slips, smearing [tool] in the incision in [target]'s [affected.name]!</font>")
|
||||
"<font color='red'>Your hand slips, smearing [tool] in the incision in [target]'s [affected.name]!</font>")
|
||||
|
||||
|
||||
|
||||
/datum/surgery_step/clamp_bone
|
||||
allowed_tools = list(
|
||||
/obj/item/weapon/surgical/bone_clamp = 100
|
||||
)
|
||||
can_infect = 1
|
||||
blood_level = 1
|
||||
|
||||
min_duration = 70
|
||||
max_duration = 90
|
||||
|
||||
can_use(mob/living/user, mob/living/carbon/human/target, target_zone, obj/item/tool)
|
||||
if (!hasorgans(target))
|
||||
return 0
|
||||
var/obj/item/organ/external/affected = target.get_organ(target_zone)
|
||||
return affected && (affected.robotic < ORGAN_ROBOT) && affected.open >= 2 && affected.stage == 0
|
||||
|
||||
begin_step(mob/user, mob/living/carbon/human/target, target_zone, obj/item/tool)
|
||||
var/obj/item/organ/external/affected = target.get_organ(target_zone)
|
||||
if (affected.stage == 0)
|
||||
user.visible_message("<font color='blue'>[user] starts repairing the damaged bones in [target]'s [affected.name] with \the [tool].</font>" , \
|
||||
"<font color='blue'>You starts repairing the damaged bones in [target]'s [affected.name] with \the [tool].</font>")
|
||||
target.custom_pain("Something in your [affected.name] is causing you a lot of pain!", 50)
|
||||
..()
|
||||
|
||||
end_step(mob/living/user, mob/living/carbon/human/target, target_zone, obj/item/tool)
|
||||
var/obj/item/organ/external/affected = target.get_organ(target_zone)
|
||||
user.visible_message("<font color='blue'>[user] sets the bone in [target]'s [affected.name] with \the [tool].</font>", \
|
||||
"<font color='blue'>You sets [target]'s bone in [affected.name] with \the [tool].</font>")
|
||||
affected.status &= ~ORGAN_BROKEN
|
||||
|
||||
fail_step(mob/living/user, mob/living/carbon/human/target, target_zone, obj/item/tool)
|
||||
var/obj/item/organ/external/affected = target.get_organ(target_zone)
|
||||
user.visible_message("<font color='red'>[user]'s hand slips, damaging the bone in [target]'s [affected.name] with \the [tool]!</font>" , \
|
||||
"<font color='red'>Your hand slips, damaging the bone in [target]'s [affected.name] with \the [tool]!</font>")
|
||||
affected.createwound(BRUISE, 5)
|
||||
@@ -168,10 +168,16 @@
|
||||
var/obj/item/organ/external/affected = target.get_organ(target_zone)
|
||||
if(istype(tool,/obj/item/stack/cable_coil/))
|
||||
var/obj/item/stack/cable_coil/C = tool
|
||||
if(!C.can_use(5))
|
||||
user << "<span class='danger'>You need ten or more cable pieces to repair this damage.</span>" //usage amount made more consistent with regular cable repair
|
||||
if(affected.burn_dam == 0)
|
||||
to_chat(user, "<span class='notice'>There are no burnt wires here!</span>")
|
||||
return SURGERY_FAILURE
|
||||
C.use(5)
|
||||
else
|
||||
if(!C.can_use(5))
|
||||
to_chat(user, "<span class='danger'>You need at least five cable pieces to repair this part.</span>") //usage amount made more consistent with regular cable repair
|
||||
return SURGERY_FAILURE
|
||||
else
|
||||
C.use(5)
|
||||
|
||||
return affected && affected.open == 3 && (affected.disfigured || affected.burn_dam > 0) && target_zone != O_MOUTH
|
||||
|
||||
begin_step(mob/user, mob/living/carbon/human/target, target_zone, obj/item/tool)
|
||||
|
||||
@@ -259,8 +259,7 @@
|
||||
..()
|
||||
|
||||
/obj/machinery/artifact/bullet_act(var/obj/item/projectile/P)
|
||||
if(istype(P,/obj/item/projectile/bullet) ||\
|
||||
istype(P,/obj/item/projectile/hivebotbullet))
|
||||
if(istype(P,/obj/item/projectile/bullet))
|
||||
if(my_effect.trigger == TRIGGER_FORCE)
|
||||
my_effect.ToggleActivate()
|
||||
if(secondary_effect && secondary_effect.trigger == TRIGGER_FORCE && prob(25))
|
||||
|
||||
Reference in New Issue
Block a user