diff --git a/code/__defines/xenoarcheaology.dm b/code/__defines/xenoarcheaology.dm
index 8a4988b78c..e4b0a3935a 100644
--- a/code/__defines/xenoarcheaology.dm
+++ b/code/__defines/xenoarcheaology.dm
@@ -37,7 +37,11 @@
#define ARCHAEO_ALIEN_BOAT 37
#define ARCHAEO_IMPERION_CIRCUIT 38
#define ARCHAEO_TELECUBE 39
-#define MAX_ARCHAEO 39
+#define ARCHAEO_BATTERY 40
+#define ARCHAEO_SYRINGE 41
+#define ARCHAEO_RING 42
+#define ARCHAEO_CLUB 43
+#define MAX_ARCHAEO 43
#define DIGSITE_GARDEN 1
#define DIGSITE_ANIMAL 2
diff --git a/code/game/gamemodes/technomancer/spells/aura/shock_aura.dm b/code/game/gamemodes/technomancer/spells/aura/shock_aura.dm
index 4135269219..b9bc8bc2c4 100644
--- a/code/game/gamemodes/technomancer/spells/aura/shock_aura.dm
+++ b/code/game/gamemodes/technomancer/spells/aura/shock_aura.dm
@@ -40,5 +40,4 @@
else
L.electrocute_act(power, src, 0.75, BP_TORSO)
-
- adjust_instability(3)
\ No newline at end of file
+ adjust_instability(3)
diff --git a/code/modules/mob/_modifiers/feysight.dm b/code/modules/mob/_modifiers/feysight.dm
new file mode 100644
index 0000000000..af391ed51c
--- /dev/null
+++ b/code/modules/mob/_modifiers/feysight.dm
@@ -0,0 +1,42 @@
+/datum/modifier/feysight
+ name = "feysight"
+ desc = "You are filled with an inner peace, and widened sight."
+ client_color = "#42e6ca"
+
+ on_created_text = "You feel an inner peace as your mind's eye expands!"
+ on_expired_text = "Your sight returns to what it once was."
+ stacks = MODIFIER_STACK_EXTEND
+
+ accuracy = -15
+ accuracy_dispersion = 1
+
+/datum/modifier/feysight/on_applied()
+ holder.see_invisible = 60
+ holder.see_invisible_default = 60
+
+/datum/modifier/feysight/on_expire()
+ holder.see_invisible_default = initial(holder.see_invisible_default)
+ holder.see_invisible = holder.see_invisible_default
+
+/datum/modifier/feysight/can_apply(var/mob/living/L)
+ if(L.stat)
+ to_chat(L, "You can't be unconscious or dead to experience tranquility.")
+ return FALSE
+
+ if(!L.is_sentient())
+ return FALSE // Drones don't feel anything.
+
+ if(ishuman(L))
+ var/mob/living/carbon/human/H = L
+ if(H.species.name == "Diona")
+ to_chat(L, "You feel strange for a moment, but it passes.")
+ return FALSE // Happy trees aren't affected by tranquility.
+
+ return ..()
+
+/datum/modifier/feysight/tick()
+ ..()
+
+ if(ishuman(holder))
+ var/mob/living/carbon/human/H = holder
+ H.druggy = min(15, H.druggy + 4)
diff --git a/code/modules/mob/living/simple_mob/subtypes/animal/space/bats.dm b/code/modules/mob/living/simple_mob/subtypes/animal/space/bats.dm
index 7397636686..7ca24f3174 100644
--- a/code/modules/mob/living/simple_mob/subtypes/animal/space/bats.dm
+++ b/code/modules/mob/living/simple_mob/subtypes/animal/space/bats.dm
@@ -50,3 +50,8 @@
/mob/living/simple_mob/animal/space/bats/cult/cultify()
return
+
+/mob/living/simple_mob/animal/space/bats/cult/strong
+ maxHealth = 60
+ health = 60
+ melee_damage_upper = 10
diff --git a/code/modules/shieldgen/energy_field.dm b/code/modules/shieldgen/energy_field.dm
index 5b7d7f2118..87d07cceaf 100644
--- a/code/modules/shieldgen/energy_field.dm
+++ b/code/modules/shieldgen/energy_field.dm
@@ -31,8 +31,14 @@
/obj/effect/energy_field/Destroy()
update_nearby_tiles()
- my_gen.field.Remove(src)
- my_gen = null
+ if(my_gen)
+ if(istype(my_gen))
+ my_gen.field.Remove(src)
+ my_gen = null
+ else if(istype(my_gen, /datum/artifact_effect/forcefield))
+ var/datum/artifact_effect/forcefield/AE = my_gen
+ AE.created_field.Remove(src)
+ my_gen = null
var/turf/current_loc = get_turf(src)
. = ..()
for(var/direction in cardinal)
diff --git a/code/modules/xenoarcheaology/artifacts/artifact.dm b/code/modules/xenoarcheaology/artifacts/artifact.dm
index 43ccbd9f3c..840c2096c5 100644
--- a/code/modules/xenoarcheaology/artifacts/artifact.dm
+++ b/code/modules/xenoarcheaology/artifacts/artifact.dm
@@ -271,7 +271,36 @@
warn = 1
if(warn)
- to_chat(M, "You accidentally touch [src].")
+ to_chat(M, "You accidentally touch \the [src].")
+ ..()
+
+/obj/machinery/artifact/Bump(var/atom/bumped)
+ if(istype(bumped,/obj))
+ if(bumped:throwforce >= 10)
+ if(my_effect.trigger == TRIGGER_FORCE)
+ my_effect.ToggleActivate()
+ if(secondary_effect && secondary_effect.trigger == TRIGGER_FORCE && prob(25))
+ secondary_effect.ToggleActivate(0)
+ else if(ishuman(bumped) && GetAnomalySusceptibility(bumped) >= 0.5)
+ var/warn = 0
+
+ if (my_effect.trigger == TRIGGER_TOUCH && prob(50))
+ my_effect.ToggleActivate()
+ warn = 1
+ if(secondary_effect && secondary_effect.trigger == TRIGGER_TOUCH && prob(25))
+ secondary_effect.ToggleActivate(0)
+ warn = 1
+
+ if (my_effect.effect == EFFECT_TOUCH && prob(50))
+ my_effect.DoEffectTouch(bumped)
+ warn = 1
+ if(secondary_effect && secondary_effect.effect == EFFECT_TOUCH && secondary_effect.activated && prob(50))
+ secondary_effect.DoEffectTouch(bumped)
+ warn = 1
+
+ if(warn)
+ to_chat(bumped, "You accidentally touch \the [src] as it hits you.")
+
..()
/obj/machinery/artifact/bullet_act(var/obj/item/projectile/P)
diff --git a/code/modules/xenoarcheaology/effects/animate_anomaly.dm b/code/modules/xenoarcheaology/effects/animate_anomaly.dm
new file mode 100644
index 0000000000..c0c17e4aaf
--- /dev/null
+++ b/code/modules/xenoarcheaology/effects/animate_anomaly.dm
@@ -0,0 +1,60 @@
+
+/datum/artifact_effect/animate_anomaly
+ name = "animate anomaly"
+ effect_type = EFFECT_PSIONIC
+ var/mob/living/target = null
+
+/datum/artifact_effect/animate_anomaly/ToggleActivate(var/reveal_toggle = 1)
+ ..()
+ find_target()
+
+/datum/artifact_effect/animate_anomaly/New()
+ ..()
+ effectrange = max(3, effectrange)
+
+/datum/artifact_effect/animate_anomaly/proc/find_target()
+ if(!target || target.z != holder.z || get_dist(target, holder) > effectrange)
+ var/mob/living/ClosestMob = null
+ for(var/mob/living/L in range(effectrange, holder))
+ if(!L.mind)
+ continue
+ if(!ClosestMob)
+ ClosestMob = L
+ continue
+ if(!L.stat)
+ if(get_dist(holder, L) < get_dist(holder, ClosestMob))
+ ClosestMob = L
+
+ target = ClosestMob
+
+/datum/artifact_effect/animate_anomaly/DoEffectTouch(var/mob/living/user)
+ var/obj/O = holder
+ var/turf/T = get_step_away(O, user)
+
+ if(target && istype(T) && istype(O.loc, /turf))
+ O.Move(T)
+ O.visible_message("\The [holder] lurches away from [user]")
+
+/datum/artifact_effect/animate_anomaly/DoEffectAura()
+ var/obj/O = holder
+ if(!target || target.z != O.z || get_dist(target, O) > effectrange)
+ target = null
+ find_target()
+ var/turf/T = get_step_to(O, target)
+
+ if(target && istype(T) && istype(O.loc, /turf))
+ if(get_dist(O, T) > 1)
+ O.Move(T)
+ O.visible_message("\The [holder] lurches toward [target]")
+
+/datum/artifact_effect/animate_anomaly/DoEffectPulse()
+ var/obj/O = holder
+ if(!target || target.z != O.z || get_dist(target, O) > effectrange)
+ target = null
+ find_target()
+ var/turf/T = get_step_to(O, target)
+
+ if(target && istype(T) && istype(O.loc, /turf))
+ if(get_dist(O, T) > 1)
+ O.Move(T)
+ O.visible_message("\The [holder] lurches toward [target]")
diff --git a/code/modules/xenoarcheaology/effects/cannibal.dm b/code/modules/xenoarcheaology/effects/cannibal.dm
new file mode 100644
index 0000000000..04a0b5a9e8
--- /dev/null
+++ b/code/modules/xenoarcheaology/effects/cannibal.dm
@@ -0,0 +1,75 @@
+/datum/artifact_effect/cannibalfeeling
+ name = "cannibalfeeling"
+ effect_type = EFFECT_PSIONIC
+ var/list/messages = list("You feel peckish.",
+ "Something doesn't feel right.",
+ "You get a strange feeling in your gut.",
+ "You feel particularly hungry.",
+ "You taste blood.",
+ "There's a strange feeling in the air.",
+ "There's a strange smell in the air.",
+ "The tips of your fingers feel tingly.",
+ "You feel twitchy.",
+ "You feel empty.",
+ "You've got a good feeling about this.",
+ "Your tongue prickles.",
+ "Are they clean?",
+ "You feel weak.",
+ "The ground is getting closer.",
+ "Something is missing.")
+
+ var/list/drastic_messages = list("They look delicious.",
+ "They'll take what's yours!",
+ "They're full of meat.",
+ "What's happening to you?",
+ "Butcher them!",
+ "Feast!")
+
+/datum/artifact_effect/cannibalfeeling/DoEffectTouch(var/mob/user)
+ if(user)
+ if (istype(user, /mob/living/carbon/human))
+ var/mob/living/carbon/human/H = user
+ if(H.is_sentient())
+ if(prob(50))
+ if(prob(75))
+ to_chat(H, "[pick(drastic_messages)]")
+ else
+ to_chat(H, "[pick(messages)]")
+
+ if(prob(50))
+ H.dizziness += rand(3,5)
+ H.nutrition = H.nutrition / 1.5
+
+/datum/artifact_effect/cannibalfeeling/DoEffectAura()
+ if(holder)
+ var/turf/T = get_turf(holder)
+ for (var/mob/living/carbon/human/H in range(src.effectrange,T))
+ if(H.is_sentient())
+ if(prob(5))
+ if(prob(75))
+ to_chat(H, "[pick(messages)]")
+ else
+ to_chat(H, "[pick(drastic_messages)]")
+
+ if(prob(10))
+ H.dizziness += rand(3,5)
+ H.nutrition = H.nutrition / 2
+ return 1
+
+/datum/artifact_effect/cannibalfeeling/DoEffectPulse()
+ if(holder)
+ var/turf/T = get_turf(holder)
+ for (var/mob/living/carbon/human/H in range(src.effectrange,T))
+ if(H.is_sentient())
+ if(prob(50))
+ if(prob(95))
+ to_chat(H, "[pick(drastic_messages)]")
+ else
+ to_chat(H, "[pick(messages)]")
+
+ if(prob(50))
+ H.dizziness += rand(3,5)
+ else if(prob(25))
+ H.dizziness += rand(5,15)
+ H.nutrition = H.nutrition / 4
+ return 1
diff --git a/code/modules/xenoarcheaology/effects/electric_field.dm b/code/modules/xenoarcheaology/effects/electric_field.dm
new file mode 100644
index 0000000000..3b27e8fe42
--- /dev/null
+++ b/code/modules/xenoarcheaology/effects/electric_field.dm
@@ -0,0 +1,69 @@
+
+/datum/artifact_effect/electric_field
+ name = "electric field"
+ effect_type = EFFECT_ENERGY
+
+/datum/artifact_effect/electric_field/DoEffectTouch(var/mob/user)
+ var/list/nearby_mobs = list()
+ for(var/mob/living/L in oview(effectrange, get_turf(holder)))
+ if(L == user) // You're "grounded" when you contact the artifact.
+ continue
+ if(!L.stat)
+ nearby_mobs |= L
+
+ for(var/obj/machinery/light/light in range(effectrange, get_turf(holder)))
+ light.flicker()
+
+ for(var/mob/living/L in nearby_mobs)
+ if(L.isSynthetic())
+ to_chat(L, "ERROR: Electrical fault detected!")
+ L.stuttering += 3
+
+ if(ishuman(L))
+ var/mob/living/carbon/human/H = L
+ var/obj/item/organ/external/affected = H.get_organ(check_zone(BP_TORSO))
+ H.electrocute_act(rand(25, 40), holder, H.get_siemens_coefficient_organ(affected), affected)
+ else
+ L.electrocute_act(rand(25, 40), holder, 0.75, BP_TORSO)
+
+/datum/artifact_effect/electric_field/DoEffectAura()
+ var/list/nearby_mobs = list()
+ for(var/mob/living/L in oview(effectrange, get_turf(holder)))
+ if(!L.stat)
+ nearby_mobs |= L
+
+ for(var/obj/machinery/light/light in range(effectrange, get_turf(holder)))
+ light.flicker()
+
+ for(var/mob/living/L in nearby_mobs)
+ if(L.isSynthetic())
+ to_chat(L, "ERROR: Electrical fault detected!")
+ L.stuttering += 3
+
+ if(ishuman(L))
+ var/mob/living/carbon/human/H = L
+ var/obj/item/organ/external/affected = H.get_organ(check_zone(BP_TORSO))
+ H.electrocute_act(rand(1, 10), holder, H.get_siemens_coefficient_organ(affected), affected)
+ else
+ L.electrocute_act(rand(1, 10), holder, 0.75, BP_TORSO)
+
+/datum/artifact_effect/electric_field/DoEffectPulse()
+ var/list/nearby_mobs = list()
+ for(var/mob/living/L in oview(effectrange, get_turf(holder)))
+ if(!L.stat)
+ nearby_mobs |= L
+
+ for(var/obj/machinery/light/light in range(effectrange, get_turf(holder)))
+ light.flicker()
+
+ for(var/mob/living/L in nearby_mobs)
+ if(L.isSynthetic())
+ to_chat(L, "ERROR: Electrical fault detected!")
+ L.stuttering += 3
+
+ if(ishuman(L))
+ var/mob/living/carbon/human/H = L
+ var/obj/item/organ/external/affected = H.get_organ(check_zone(BP_TORSO))
+ H.electrocute_act(rand(10, 30), holder, H.get_siemens_coefficient_organ(affected), affected)
+ else
+ L.electrocute_act(rand(10, 30), holder, 0.75, BP_TORSO)
diff --git a/code/modules/xenoarcheaology/effects/feysight.dm b/code/modules/xenoarcheaology/effects/feysight.dm
new file mode 100644
index 0000000000..379dc0cc54
--- /dev/null
+++ b/code/modules/xenoarcheaology/effects/feysight.dm
@@ -0,0 +1,43 @@
+/datum/artifact_effect/feysight
+ name = "feysight"
+ effect_type = EFFECT_PSIONIC
+
+/datum/artifact_effect/feysight/proc/apply_modifier(var/mob/living/L)
+ if(!istype(L))
+ return FALSE
+
+ if(!L.is_sentient())
+ return FALSE // Drons are presumably deaf to any psionic things.
+
+ if(L.add_modifier(/datum/modifier/feysight, 30 SECONDS))
+ to_chat(L, "An otherworldly feeling seems to enter your mind, and you feel at peace.")
+ L.adjustHalLoss(10)
+ to_chat(L, "The inside of your head hurts...")
+ return TRUE
+ else
+ if(L.has_modifier_of_type(/datum/modifier/feysight))
+ to_chat(L, "An otherworldly feeling seems to enter your mind again, and it holds the visions in place.")
+ else
+ to_chat(L, "An otherworldly feeling seems to enter your mind, and you briefly feel peace, but \
+ it quickly passes.")
+ return FALSE
+
+/datum/artifact_effect/feysight/DoEffectTouch(var/mob/toucher)
+ if(toucher && isliving(toucher))
+ apply_modifier(toucher)
+ return TRUE
+
+/datum/artifact_effect/feysight/DoEffectAura()
+ if(holder)
+ var/turf/T = get_turf(holder)
+ for(var/mob/living/L in range(src.effectrange,T))
+ if(prob(10))
+ apply_modifier(L)
+ return TRUE
+
+/datum/artifact_effect/feysight/DoEffectPulse()
+ if(holder)
+ var/turf/T = get_turf(holder)
+ for(var/mob/living/L in range(src.effectrange,T))
+ apply_modifier(L)
+ return TRUE
\ No newline at end of file
diff --git a/code/modules/xenoarcheaology/effects/gaia.dm b/code/modules/xenoarcheaology/effects/gaia.dm
new file mode 100644
index 0000000000..1a89149818
--- /dev/null
+++ b/code/modules/xenoarcheaology/effects/gaia.dm
@@ -0,0 +1,81 @@
+
+/datum/artifact_effect/gaia
+ name = "gaia"
+ effect_type = EFFECT_ORGANIC
+
+ var/list/my_glitterflies = list()
+
+/datum/artifact_effect/gaia/proc/age_plantlife(var/obj/machinery/portable_atmospherics/hydroponics/Tray = null)
+ if(istype(Tray) && Tray.seed)
+ Tray.health += rand(1,3) * HYDRO_SPEED_MULTIPLIER
+ Tray.age += 1
+
+ if(Tray.health > 0 && Tray.dead)
+ Tray.dead = FALSE
+
+ Tray.check_health()
+
+ if(!Tray.dead)
+ if((Tray.age > Tray.seed.get_trait(TRAIT_MATURATION)) && \
+ ((Tray.age - Tray.lastproduce) > Tray.seed.get_trait(TRAIT_PRODUCTION)) && \
+ (!Tray.harvest && !Tray.dead))
+ Tray.harvest = 1
+ Tray.lastproduce = Tray.age
+
+ else if(istype(Tray, /obj/effect/plant))
+ var/obj/effect/plant/P = Tray
+ Tray = P.plant
+ if(Tray)
+ age_plantlife(Tray)
+ P.update_icon()
+
+/datum/artifact_effect/gaia/DoEffectTouch(var/mob/user)
+ to_chat(user, "You feel the presence of something long forgotten.")
+ for(var/obj/machinery/portable_atmospherics/hydroponics/Tray in view(world.view,get_turf(holder)))
+ age_plantlife(Tray)
+ if(prob(30))
+ var/mob/living/simple_mob/animal/sif/glitterfly/G = new(get_turf(Tray))
+
+ my_glitterflies |= G
+
+ G.ai_holder.returns_home = TRUE
+
+ for(var/obj/effect/plant/P in view(world.view,get_turf(holder)))
+ age_plantlife(P)
+
+/datum/artifact_effect/gaia/DoEffectAura()
+ for(var/obj/machinery/portable_atmospherics/hydroponics/Tray in view(effectrange,holder))
+ age_plantlife(Tray)
+ if(prob(2))
+ var/mob/living/simple_mob/animal/sif/glitterfly/G = new(get_turf(Tray))
+
+ my_glitterflies |= G
+
+ G.ai_holder.returns_home = TRUE
+
+ for(var/obj/effect/plant/P in view(effectrange,get_turf(holder)))
+ age_plantlife(P)
+
+/datum/artifact_effect/gaia/DoEffectPulse()
+ for(var/obj/machinery/portable_atmospherics/hydroponics/Tray in view(effectrange,holder))
+ age_plantlife(Tray)
+ if(prob(10))
+ var/mob/living/simple_mob/animal/sif/glitterfly/G = new(get_turf(Tray))
+
+ my_glitterflies |= G
+
+ G.ai_holder.returns_home = TRUE
+
+ for(var/obj/effect/plant/P in view(effectrange,get_turf(holder)))
+ age_plantlife(P)
+
+/datum/artifact_effect/gaia/process()
+ ..()
+
+ listclearnulls(my_glitterflies)
+
+ for(var/mob/living/L in my_glitterflies)
+ if(L.stat == DEAD)
+ my_glitterflies -= L
+
+ L.ai_holder.home_turf = get_turf(holder)
diff --git a/code/modules/xenoarcheaology/effects/gravitational_waves.dm b/code/modules/xenoarcheaology/effects/gravitational_waves.dm
new file mode 100644
index 0000000000..8483d23d4b
--- /dev/null
+++ b/code/modules/xenoarcheaology/effects/gravitational_waves.dm
@@ -0,0 +1,25 @@
+
+/datum/artifact_effect/gravity_wave
+ name = "gravity wave"
+ effect_type = EFFECT_ENERGY
+
+ var/last_wave_pull = 0
+
+/datum/artifact_effect/gravity_wave/DoEffectTouch(var/mob/user)
+ gravwave(user, effectrange, STAGE_TWO)
+
+/datum/artifact_effect/gravity_wave/DoEffectAura()
+ var/seconds_since_last_pull = max(0, round((last_wave_pull - world.time) / 10))
+
+ if(prob(10 + seconds_since_last_pull))
+ holder.visible_message("\The [holder] distorts as local gravity intensifies, and shifts toward it.")
+ last_wave_pull = world.time
+ gravwave(get_turf(holder), effectrange, STAGE_TWO)
+
+/datum/artifact_effect/gravity_wave/DoEffectPulse()
+ holder.visible_message("\The [holder] distorts as local gravity intensifies, and shifts toward it.")
+ gravwave(get_turf(holder), effectrange, STAGE_TWO)
+
+proc/gravwave(var/atom/target, var/pull_range = 7, var/pull_power = STAGE_TWO)
+ for(var/atom/A in oview(pull_range, target))
+ A.singularity_pull(target, pull_power)
diff --git a/code/modules/xenoarcheaology/effects/poltergeist.dm b/code/modules/xenoarcheaology/effects/poltergeist.dm
new file mode 100644
index 0000000000..189c0ea4cd
--- /dev/null
+++ b/code/modules/xenoarcheaology/effects/poltergeist.dm
@@ -0,0 +1,47 @@
+
+/datum/artifact_effect/poltergeist
+ name = "poltergeist"
+ effect_type = EFFECT_ENERGY
+
+/datum/artifact_effect/poltergeist/proc/throw_at_mob(var/mob/living/target, var/damage = 20)
+ var/list/valid_targets = list()
+
+ for(var/obj/O in oview(world.view, target))
+ if(!O.anchored && isturf(O.loc))
+ valid_targets |= O
+
+ if(valid_targets.len)
+ var/obj/obj_to_throw = pick(valid_targets)
+ obj_to_throw.visible_message("\The [obj_to_throw] levitates, befure hurtling toward [target]!")
+ obj_to_throw.throw_at(target, world.view, min(40, damage * GetAnomalySusceptibility(target)))
+
+/datum/artifact_effect/poltergeist/DoEffectTouch(var/mob/user)
+ throw_at_mob(user, rand(10, 30))
+
+/datum/artifact_effect/poltergeist/DoEffectAura()
+ var/mob/living/target = null
+ for(var/mob/living/L in oview(get_turf(holder), effectrange))
+ if(L.stat || !L.mind)
+ continue
+
+ if(target && get_dist(get_turf(holder), L) > get_dist(get_turf(holder), target))
+ continue
+
+ target = L
+
+ if(target)
+ throw_at_mob(target, rand(15, 30))
+
+/datum/artifact_effect/poltergeist/DoEffectPulse()
+ var/mob/living/target = null
+ for(var/mob/living/L in oview(get_turf(holder), effectrange))
+ if(L.stat || !L.mind)
+ continue
+
+ if(target && get_dist(get_turf(holder), L) > get_dist(get_turf(holder), target))
+ continue
+
+ target = L
+
+ if(target)
+ throw_at_mob(target, chargelevelmax)
diff --git a/code/modules/xenoarcheaology/effects/resurrect.dm b/code/modules/xenoarcheaology/effects/resurrect.dm
new file mode 100644
index 0000000000..e54ca276ea
--- /dev/null
+++ b/code/modules/xenoarcheaology/effects/resurrect.dm
@@ -0,0 +1,100 @@
+/datum/artifact_effect/resurrect
+ name = "resurrect"
+ effect_type = EFFECT_ORGANIC
+
+ var/stored_life = 0
+
+/datum/artifact_effect/resurrect/proc/steal_life(var/mob/living/target = null)
+ if(!istype(target))
+ return 0
+
+ if(target.stat != DEAD && stored_life < 200)
+ holder.Beam(target, icon_state = "drain_life", time = 1 SECOND)
+ target.apply_damage(5, SEARING, BP_TORSO)
+ return 5
+
+ return 0
+
+/datum/artifact_effect/resurrect/proc/give_life(var/mob/living/target = null)
+ if(!istype(target))
+ return
+
+ if(target.stat == DEAD && stored_life)
+ holder.Beam(target, icon_state = "lichbeam", time = 1 SECOND)
+ target.adjustBruteLoss(-5)
+ target.adjustFireLoss(-5)
+ target.adjustCloneLoss(-5)
+ target.adjustOxyLoss(-5)
+ target.adjustHalLoss(-5)
+ target.adjustToxLoss(-5)
+ stored_life = max(0, stored_life - 5)
+
+ if(target.health > (target.maxHealth / 4))
+ attempt_revive(target)
+ stored_life = 0
+
+/datum/artifact_effect/resurrect/proc/attempt_revive(var/mob/living/L = null)
+ spawn()
+ if(istype(L, /mob/living/simple_mob))
+ var/mob/living/simple_mob/SM = L
+ SM.adjustBruteLoss(-40)
+ SM.adjustFireLoss(-40)
+ SM.health = SM.getMaxHealth() / 3
+ SM.stat = CONSCIOUS
+ dead_mob_list -= SM
+ living_mob_list += SM
+ SM.update_icon()
+ SM.revive()
+ holder.visible_message("\The [SM]'s eyes open in a flash of light!")
+ else if(ishuman(L))
+ var/mob/living/carbon/human/H = L
+
+ if(!H.client && H.mind)
+ for(var/mob/observer/dead/ghost in player_list)
+ if(ghost.mind == H.mind)
+ to_chat(ghost, "An artifact is trying to \
+ revive you. Return to your body if you want to be resurrected! \
+ (Verbs -> Ghost -> Re-enter corpse)")
+ break
+
+ H.adjustBruteLoss(-40)
+ H.adjustFireLoss(-40)
+
+ sleep(10 SECONDS)
+ if(H.client)
+ L.stat = CONSCIOUS
+ dead_mob_list -= H
+ living_mob_list += H
+ H.timeofdeath = null
+
+ holder.visible_message("\The [H]'s eyes open in a flash of light!")
+
+/datum/artifact_effect/resurrect/DoEffectTouch(var/mob/user)
+ for(var/mob/living/L in oview(effectrange, get_turf(holder)))
+ stored_life += 4 * steal_life(L)
+
+ var/turf/T = get_turf(holder)
+ for(var/mob/living/L in T)
+ if(L.stat == DEAD)
+ give_life(L)
+ break
+
+/datum/artifact_effect/resurrect/DoEffectAura()
+ for(var/mob/living/L in oview(effectrange, get_turf(holder)))
+ stored_life += steal_life(L)
+
+ var/turf/T = get_turf(holder)
+ for(var/mob/living/L in T)
+ if(L.stat == DEAD)
+ give_life(L)
+ break
+
+/datum/artifact_effect/resurrect/DoEffectPulse()
+ for(var/mob/living/L in oview(effectrange, get_turf(holder)))
+ stored_life += 2 * steal_life(L)
+
+ var/turf/T = get_turf(holder)
+ for(var/mob/living/L in T)
+ if(L.stat == DEAD)
+ give_life(L)
+ break
diff --git a/code/modules/xenoarcheaology/effects/vampire.dm b/code/modules/xenoarcheaology/effects/vampire.dm
new file mode 100644
index 0000000000..ee75ea5ba1
--- /dev/null
+++ b/code/modules/xenoarcheaology/effects/vampire.dm
@@ -0,0 +1,86 @@
+
+/datum/artifact_effect/vampire
+ name = "vampire"
+ effect_type = EFFECT_ORGANIC
+ var/last_bloodcall = 0
+ var/bloodcall_interval = 50
+ var/last_eat = 0
+ var/eat_interval = 100
+ var/charges = 0
+ var/list/nearby_mobs = list()
+
+/datum/artifact_effect/vampire/proc/bloodcall(var/mob/living/carbon/human/M)
+ last_bloodcall = world.time
+ if(istype(M))
+ playsound(holder.loc, pick('sound/hallucinations/wail.ogg','sound/hallucinations/veryfar_noise.ogg','sound/hallucinations/far_noise.ogg'), 50, 1, -3)
+
+ var/target = pick(M.organs_by_name)
+ M.apply_damage(rand(5, 10), SEARING, target)
+ to_chat(M, "The skin on your [parse_zone(target)] feels like it's ripping apart, and a stream of blood flies out.")
+ var/obj/effect/decal/cleanable/blood/splatter/animated/B = new(M.loc)
+ B.basecolor = M.species.get_blood_colour(M)
+ B.color = M.species.get_blood_colour(M)
+ B.target_turf = pick(range(1, get_turf(holder)))
+ B.blood_DNA = list()
+ B.blood_DNA[M.dna.unique_enzymes] = M.dna.b_type
+ M.vessel.remove_reagent("blood",rand(25,50))
+
+/datum/artifact_effect/vampire/DoEffectTouch(var/mob/user)
+ bloodcall(user)
+ DoEffectAura()
+
+/datum/artifact_effect/vampire/DoEffectAura()
+ nearby_mobs.Cut()
+
+ var/turf/T = get_turf(holder)
+
+ for(var/mob/living/L in oview(effectrange, T))
+ if(!L.stat && L.mind)
+ nearby_mobs |= L
+
+ if(world.time - last_bloodcall > bloodcall_interval && nearby_mobs.len)
+ var/mob/living/carbon/human/M = pick(nearby_mobs)
+ if(M in view(effectrange,holder) && M.health > 20)
+ if(prob(50))
+ bloodcall(M)
+ holder.Beam(M, icon_state = "drainbeam", time = 1 SECOND)
+
+ if(world.time - last_eat > eat_interval)
+ var/obj/effect/decal/cleanable/blood/B = locate() in range(2,holder)
+ if(B)
+ last_eat = world.time
+ B.loc = null
+ if(istype(B, /obj/effect/decal/cleanable/blood/drip))
+ charges += 0.25
+ else
+ charges += 1
+ playsound(holder.loc, 'sound/effects/splat.ogg', 50, 1, -3)
+
+ qdel(B)
+
+ if(charges >= 10)
+ charges -= 10
+ var/manifestation = pick(/obj/item/device/soulstone, /mob/living/simple_mob/faithless/cult/strong, /mob/living/simple_mob/creature/cult/strong, /mob/living/simple_mob/animal/space/bats/cult/strong)
+ new manifestation(get_turf(pick(view(1,T))))
+
+ if(charges >= 3)
+ if(prob(5))
+ charges -= 1
+ var/spawn_type = pick(/mob/living/simple_mob/animal/space/bats, /mob/living/simple_mob/creature, /mob/living/simple_mob/faithless)
+ new spawn_type(get_turf(pick(view(1,T))))
+ playsound(holder.loc, pick('sound/hallucinations/growl1.ogg','sound/hallucinations/growl2.ogg','sound/hallucinations/growl3.ogg'), 50, 1, -3)
+
+ if(charges >= 1 && nearby_mobs.len && prob(15 * nearby_mobs.len))
+ var/mob/living/L = pick(nearby_mobs)
+
+ holder.Beam(L, icon_state = "drainbeam", time = 1 SECOND)
+
+ L.add_modifier(/datum/modifier/agonize, 5 SECONDS)
+
+ if(charges >= 0.1)
+ if(prob(5))
+ holder.visible_message("\icon[holder] \The [holder] gleams a bloody red!")
+ charges -= 0.1
+
+/datum/artifact_effect/vampire/DoEffectPulse()
+ DoEffectAura()
diff --git a/code/modules/xenoarcheaology/finds/find_spawning.dm b/code/modules/xenoarcheaology/finds/find_spawning.dm
index 4c091200ca..20f10e91da 100644
--- a/code/modules/xenoarcheaology/finds/find_spawning.dm
+++ b/code/modules/xenoarcheaology/finds/find_spawning.dm
@@ -21,7 +21,7 @@
var/apply_prefix = 1
if(prob(40))
- material_descriptor = pick("rusted ","dusty ","archaic ","fragile ")
+ material_descriptor = pick("rusted ","dusty ","archaic ","fragile ", "damaged", "pristine")
source_material = pick("cordite","quadrinium",DEFAULT_WALL_MATERIAL,"titanium","aluminium","ferritic-alloy","plasteel","duranium")
var/talkative = 0
@@ -32,7 +32,7 @@
//icon_state
//item_state
switch(find_type)
- if(1)
+ if(ARCHAEO_BOWL)
item_type = "bowl"
if(prob(33))
new_item = new /obj/item/weapon/reagent_containers/glass/replenishing(src.loc)
@@ -46,7 +46,7 @@
new_item.color = rgb(rand(0,255),rand(0,255),rand(0,255))
if(prob(20))
additional_desc = "There appear to be [pick("dark","faintly glowing","pungent","bright")] [pick("red","purple","green","blue")] stains inside."
- if(2)
+ if(ARCHAEO_URN)
item_type = "urn"
if(prob(33))
new_item = new /obj/item/weapon/reagent_containers/glass/replenishing(src.loc)
@@ -58,7 +58,7 @@
apply_image_decorations = 1
if(prob(20))
additional_desc = "It [pick("whispers faintly","makes a quiet roaring sound","whistles softly","thrums quietly","throbs")] if you put it to your ear."
- if(3)
+ if(ARCHAEO_CUTLERY)
item_type = "[pick("fork","spoon","knife")]"
if(prob(25))
new_item = new /obj/item/weapon/material/kitchen/utensil/fork(src.loc)
@@ -71,7 +71,7 @@
additional_desc = "[pick("It's like no [item_type] you've ever seen before",\
"It's a mystery how anyone is supposed to eat with this",\
"You wonder what the creator's mouth was shaped like")]."
- if(4)
+ if(ARCHAEO_STATUETTE)
name = "statuette"
icon = 'icons/obj/xenoarchaeology.dmi'
item_type = "statuette"
@@ -82,7 +82,7 @@
if(prob(25))
new_item = new /obj/item/weapon/vampiric(src.loc)
LAZYSET(new_item.origin_tech, TECH_ARCANE, 1)
- if(5)
+ if(ARCHAEO_INSTRUMENT)
name = "instrument"
icon = 'icons/obj/xenoarchaeology.dmi'
item_type = "instrument"
@@ -93,13 +93,13 @@
"You wonder how many mouths the creator had",\
"You wonder what it sounds like",\
"You wonder what kind of music was made with it")]."
- if(6)
+ if(ARCHAEO_KNIFE)
item_type = "[pick("bladed knife","serrated blade","sharp cutting implement")]"
new_item = new /obj/item/weapon/material/knife(src.loc)
additional_desc = "[pick("It doesn't look safe.",\
"It looks wickedly jagged",\
"There appear to be [pick("dark red","dark purple","dark green","dark blue")] stains along the edges")]."
- if(7)
+ if(ARCHAEO_COIN)
//assuming there are 12 types of coins
var/chance = 8
for(var/type in typesof(/obj/item/weapon/coin))
@@ -112,11 +112,11 @@
apply_prefix = 0
apply_material_decorations = 0
apply_image_decorations = 1
- if(8)
+ if(ARCHAEO_HANDCUFFS)
item_type = "handcuffs"
new_item = new /obj/item/weapon/handcuffs(src.loc)
additional_desc = "[pick("They appear to be for securing two things together","Looks kinky","Doesn't seem like a children's toy")]."
- if(9)
+ if(ARCHAEO_BEARTRAP)
item_type = "[pick("wicked","evil","byzantine","dangerous")] looking [pick("device","contraption","thing","trap")]"
apply_prefix = 0
new_item = new /obj/item/weapon/beartrap(src.loc)
@@ -125,13 +125,13 @@
additional_desc = "[pick("It looks like it could take a limb off",\
"Could be some kind of animal trap",\
"There appear to be [pick("dark red","dark purple","dark green","dark blue")] stains along part of it")]."
- if(10)
+ if(ARCHAEO_LIGHTER)
item_type = "[pick("cylinder","tank","chamber")]"
new_item = new /obj/item/weapon/flame/lighter(src.loc)
additional_desc = "There is a tiny device attached."
if(prob(30))
apply_image_decorations = 1
- if(11)
+ if(ARCHAEO_BOX)
item_type = "box"
new_item = new /obj/item/weapon/storage/box(src.loc)
new_item.icon = 'icons/obj/xenoarchaeology.dmi'
@@ -143,7 +143,7 @@
if(prob(30))
LAZYSET(new_item.origin_tech, TECH_ARCANE, 1)
apply_image_decorations = 1
- if(12)
+ if(ARCHAEO_GASTANK)
item_type = "[pick("cylinder","tank","chamber")]"
if(prob(25))
new_item = new /obj/item/weapon/tank/air(src.loc)
@@ -153,7 +153,7 @@
new_item = new /obj/item/weapon/tank/phoron(src.loc)
icon_state = pick("oxygen","oxygen_fr","oxygen_f","phoron","anesthetic")
additional_desc = "It [pick("gloops","sloshes")] slightly when you shake it."
- if(13)
+ if(ARCHAEO_TOOL)
item_type = "tool"
if(prob(25))
new_item = new /obj/item/weapon/tool/wrench(src.loc)
@@ -167,7 +167,7 @@
additional_desc = "[pick("It doesn't look safe.",\
"You wonder what it was used for",\
"There appear to be [pick("dark red","dark purple","dark green","dark blue")] stains on it")]."
- if(14)
+ if(ARCHAEO_METAL)
apply_material_decorations = 0
var/list/possible_spawns = list()
possible_spawns += /obj/item/stack/material/steel
@@ -184,7 +184,7 @@
var/new_type = pick(possible_spawns)
new_item = new new_type(src.loc)
new_item:amount = rand(5,45)
- if(15)
+ if(ARCHAEO_PEN)
if(prob(75))
new_item = new /obj/item/weapon/pen(src.loc)
else
@@ -194,7 +194,7 @@
icon_state = "pen1"
LAZYSET(new_item.origin_tech, TECH_ARCANE, 1)
apply_image_decorations = 1
- if(16)
+ if(ARCHAEO_CRYSTAL)
apply_prefix = 0
if(prob(25))
icon = 'icons/obj/xenoarchaeology.dmi'
@@ -218,27 +218,28 @@
new_item.icon = 'icons/obj/xenoarchaeology.dmi'
new_item.icon_state = icon_state
LAZYSET(new_item.origin_tech, TECH_ARCANE, 2)
- if(17)
+ if(ARCHAEO_CULTBLADE)
//cultblade
apply_prefix = 0
new_item = new /obj/item/weapon/melee/cultblade(src.loc)
apply_material_decorations = 0
apply_image_decorations = 0
- if(18)
+ if(ARCHAEO_TELEBEACON)
new_item = new /obj/item/device/radio/beacon(src.loc)
talkative = 0
new_item.icon = 'icons/obj/xenoarchaeology.dmi'
new_item.icon_state = "unknown[rand(1,4)]"
new_item.desc = ""
- if(19)
+ if(ARCHAEO_CLAYMORE)
apply_prefix = 0
new_item = new /obj/item/weapon/material/sword(src.loc)
new_item.force = 10
+ new_item.name = pick("great-sword","claymore","longsword","broadsword","shortsword","gladius")
item_type = new_item.name
if(prob(30))
new_item.icon = 'icons/obj/xenoarchaeology.dmi'
new_item.icon_state = "blade1"
- if(20)
+ if(ARCHAEO_CULTROBES)
//arcane clothing
apply_prefix = 0
var/list/possible_spawns = list(/obj/item/clothing/head/culthood,
@@ -249,14 +250,14 @@
var/new_type = pick(possible_spawns)
new_item = new new_type(src.loc)
LAZYSET(new_item.origin_tech, TECH_ARCANE, 1)
- if(21)
+ if(ARCHAEO_SOULSTONE)
//soulstone
apply_prefix = 0
new_item = new /obj/item/device/soulstone(src.loc)
item_type = new_item.name
apply_material_decorations = 0
LAZYSET(new_item.origin_tech, TECH_ARCANE, 2)
- if(22)
+ if(ARCHAEO_SHARD)
if(prob(50))
new_item = new /obj/item/weapon/material/shard(src.loc)
else
@@ -264,12 +265,12 @@
apply_prefix = 0
apply_image_decorations = 0
apply_material_decorations = 0
- if(23)
+ if(ARCHAEO_RODS)
apply_prefix = 0
new_item = new /obj/item/stack/rods(src.loc)
apply_image_decorations = 0
apply_material_decorations = 0
- if(24)
+ if(ARCHAEO_STOCKPARTS)
var/list/possible_spawns = typesof(/obj/item/weapon/stock_parts)
possible_spawns -= /obj/item/weapon/stock_parts
possible_spawns -= /obj/item/weapon/stock_parts/subspace
@@ -278,12 +279,13 @@
new_item = new new_type(src.loc)
item_type = new_item.name
apply_material_decorations = 0
- if(25)
+ if(ARCHAEO_KATANA)
apply_prefix = 0
new_item = new /obj/item/weapon/material/sword/katana(src.loc)
new_item.force = 10
+ new_item.name = "katana"
item_type = new_item.name
- if(26)
+ if(ARCHAEO_LASER)
//energy gun
var/spawn_type = pick(\
/obj/item/weapon/gun/energy/laser/practice/xenoarch,\
@@ -311,7 +313,7 @@
new_gun.power_supply.charge = 0
item_type = "gun"
- if(27)
+ if(ARCHAEO_GUN)
//revolver
var/obj/item/weapon/gun/projectile/new_gun = new /obj/item/weapon/gun/projectile/revolver(src.loc)
new_item = new_gun
@@ -346,11 +348,11 @@
I.loc = null
item_type = "gun"
- if(28)
+ if(ARCHAEO_UNKNOWN)
//completely unknown alien device
if(prob(50))
apply_image_decorations = 0
- if(29)
+ if(ARCHAEO_FOSSIL)
//fossil bone/skull
//new_item = new /obj/item/weapon/fossil/base(src.loc)
@@ -364,7 +366,7 @@
additional_desc = "A fossilised part of an alien, long dead."
apply_image_decorations = 0
apply_material_decorations = 0
- if(30)
+ if(ARCHAEO_SHELL)
//fossil shell
new_item = new /obj/item/weapon/fossil/shell(src.loc)
apply_prefix = 0
@@ -373,7 +375,7 @@
apply_material_decorations = 0
if(prob(10))
apply_image_decorations = 1
- if(31)
+ if(ARCHAEO_PLANT)
//fossil plant
new_item = new /obj/item/weapon/fossil/plant(src.loc)
item_type = new_item.name
@@ -381,7 +383,7 @@
apply_image_decorations = 0
apply_material_decorations = 0
apply_prefix = 0
- if(32)
+ if(ARCHAEO_REMAINS_HUMANOID)
//humanoid remains
apply_prefix = 0
item_type = "humanoid [pick("remains","skeleton")]"
@@ -396,7 +398,7 @@
"The mouth is wide open in a death rictus, the victim would appear to have died screaming.")
apply_image_decorations = 0
apply_material_decorations = 0
- if(33)
+ if(ARCHAEO_REMAINS_ROBOT)
//robot remains
apply_prefix = 0
item_type = "[pick("mechanical","robotic","cyborg")] [pick("remains","chassis","debris")]"
@@ -411,7 +413,7 @@
"A pile of wires and crap metal that looks vaguely robotic.")
apply_image_decorations = 0
apply_material_decorations = 0
- if(34)
+ if(ARCHAEO_REMAINS_XENO)
//xenos remains
apply_prefix = 0
item_type = "alien [pick("remains","skeleton")]"
@@ -427,7 +429,7 @@
"It doesn't look human.")
apply_image_decorations = 0
apply_material_decorations = 0
- if(35)
+ if(ARCHAEO_GASMASK)
//gas mask
if(prob(25))
new_item = new /obj/item/clothing/mask/gas/poltergeist(src.loc)
@@ -436,7 +438,7 @@
new_item = new /obj/item/clothing/mask/gas(src.loc)
if(prob(40))
new_item.color = rgb(rand(0,255),rand(0,255),rand(0,255))
- if(36)
+ if(ARCHAEO_ALIEN_ITEM)
// Alien stuff.
apply_prefix = FALSE
apply_material_decorations = FALSE
@@ -469,7 +471,7 @@
LAZYSET(new_item.origin_tech, TECH_PRECURSOR, 1)
item_type = new_item.name
- if(37)
+ if(ARCHAEO_ALIEN_BOAT)
// Alien boats.
apply_prefix = FALSE
var/new_boat_mat = pickweight(list(
@@ -500,7 +502,7 @@
new_item = new new_type(src.loc, new_boat_mat)
item_type = new_item.name
- if(38)
+ if(ARCHAEO_IMPERION_CIRCUIT)
// Imperion circuit.
apply_prefix = FALSE
apply_image_decorations = FALSE
@@ -511,7 +513,7 @@
desc = new_item.desc
item_type = new_item.name
- if(39)
+ if(ARCHAEO_TELECUBE)
// Telecube.
if(prob(25))
apply_prefix = FALSE
@@ -520,6 +522,62 @@
if(prob(25))
apply_material_decorations = FALSE
new_item = new /obj/item/weapon/telecube/randomized(src.loc)
+ item_type = new_item.name
+
+ if(ARCHAEO_BATTERY)
+ // Battery!
+ var/new_path = pick(subtypesof(/obj/item/weapon/cell))
+ new_item = new new_path(src.loc)
+ new_item.name = pick("cell", "battery", "device")
+
+ if(prob(30))
+ apply_prefix = FALSE
+ if(prob(5))
+ apply_image_decorations = TRUE
+ if(prob(15))
+ apply_material_decorations = FALSE
+
+ item_type = new_item.name
+
+ if(ARCHAEO_SYRINGE)
+ // Syringe.
+ if(prob(25))
+ apply_prefix = FALSE
+ if(prob(75))
+ apply_image_decorations = TRUE
+ if(prob(25))
+ apply_material_decorations = FALSE
+ new_item = new /obj/item/weapon/reagent_containers/syringe(src.loc)
+ var/obj/item/weapon/reagent_containers/syringe/S = new_item
+
+ S.volume = 30
+ S.reagents.maximum_volume = 30
+
+ item_type = new_item.name
+
+ if(ARCHAEO_RING)
+ // Ring.
+ if(prob(15))
+ apply_prefix = FALSE
+ if(prob(40))
+ apply_image_decorations = TRUE
+ if(prob(25))
+ apply_material_decorations = FALSE
+ new_item = new /obj/item/clothing/gloves/ring/material(src.loc)
+ item_type = new_item.name
+
+ if(ARCHAEO_CLUB)
+ // Baseball Bat
+ if(prob(30))
+ apply_prefix = FALSE
+ if(prob(80))
+ apply_image_decorations = TRUE
+ if(prob(10))
+ apply_material_decorations = FALSE
+
+ new_item = new /obj/item/weapon/material/twohanded/baseballbat(src.loc)
+ new_item.name = pick("great-club","club","billyclub","mace","tenderizer","maul","bat")
+ item_type = new_item.name
if(istype(new_item, /obj/item/weapon/material))
var/new_item_mat = pickweight(list(
@@ -553,9 +611,13 @@
var/decorations = ""
if(apply_material_decorations)
source_material = pick("cordite","quadrinium",DEFAULT_WALL_MATERIAL,"titanium","aluminium","ferritic-alloy","plasteel","duranium")
+
if(istype(new_item, /obj/item/weapon/material))
var/obj/item/weapon/material/MW = new_item
source_material = MW.material.display_name
+ if(istype(new_item, /obj/vehicle/boat))
+ var/obj/vehicle/boat/B = new_item
+ source_material = B.material.display_name
desc = "A [material_descriptor ? "[material_descriptor] " : ""][item_type] made of [source_material], all craftsmanship is of [pick("the lowest","low","average","high","the highest")] quality."
var/list/descriptors = list()
diff --git a/code/modules/xenoarcheaology/tools/ano_device_battery.dm b/code/modules/xenoarcheaology/tools/ano_device_battery.dm
index 937f5f2927..5e0773e61e 100644
--- a/code/modules/xenoarcheaology/tools/ano_device_battery.dm
+++ b/code/modules/xenoarcheaology/tools/ano_device_battery.dm
@@ -3,12 +3,18 @@
icon = 'icons/obj/xenoarchaeology.dmi'
icon_state = "anobattery0"
var/datum/artifact_effect/battery_effect
- var/capacity = 300
+ var/capacity = 500
var/stored_charge = 0
var/effect_id = ""
+/obj/item/weapon/anobattery/advanced
+ name = "advanced anomaly battery"
+ capacity = 3000
+
+/*
/obj/item/weapon/anobattery/New()
battery_effect = new()
+*/
/obj/item/weapon/anobattery/proc/UpdateSprite()
var/p = (stored_charge/capacity)*100
@@ -105,7 +111,6 @@
to_chat(holder, "the \icon[src] [src] held by [holder] shudders in your grasp.")
else
src.loc.visible_message("the \icon[src] [src] shudders.")
- inserted_battery.battery_effect.DoEffectTouch(holder)
//consume power
inserted_battery.use_power(energy_consumed_on_touch)
@@ -113,11 +118,13 @@
//consume power equal to time passed
inserted_battery.use_power(world.time - last_process)
+ inserted_battery.battery_effect.DoEffectTouch(holder)
+
else if(inserted_battery.battery_effect.effect == EFFECT_PULSE)
inserted_battery.battery_effect.chargelevel = inserted_battery.battery_effect.chargelevelmax
//consume power relative to the time the artifact takes to charge and the effect range
- inserted_battery.use_power(inserted_battery.battery_effect.effectrange * inserted_battery.battery_effect.effectrange * inserted_battery.battery_effect.chargelevelmax)
+ inserted_battery.use_power((inserted_battery.battery_effect.effectrange * inserted_battery.battery_effect.chargelevelmax) / 2)
else
//consume power equal to time passed
@@ -167,6 +174,7 @@
if(!inserted_battery.battery_effect.activated)
inserted_battery.battery_effect.ToggleActivate(1)
time_end = world.time + duration
+ last_process = world.time
if(href_list["shutdown"])
activated = 0
if(href_list["ejectbattery"])
diff --git a/code/modules/xenoarcheaology/tools/artifact_harvester.dm b/code/modules/xenoarcheaology/tools/artifact_harvester.dm
index 6771db1b91..3d71aef155 100644
--- a/code/modules/xenoarcheaology/tools/artifact_harvester.dm
+++ b/code/modules/xenoarcheaology/tools/artifact_harvester.dm
@@ -156,6 +156,7 @@
//delete it when the ids match to account for duplicate ids having different effects
if(inserted_battery.battery_effect && inserted_battery.stored_charge <= 0)
qdel(inserted_battery.battery_effect)
+ inserted_battery.battery_effect = null
//
var/datum/artifact_effect/source_effect
diff --git a/html/changelogs/Mechoid - Xenoarch.yml b/html/changelogs/Mechoid - Xenoarch.yml
new file mode 100644
index 0000000000..b3df577d25
--- /dev/null
+++ b/html/changelogs/Mechoid - Xenoarch.yml
@@ -0,0 +1,40 @@
+################################
+# Example Changelog File
+#
+# Note: This file, and files beginning with ".", and files that don't end in ".yml" will not be read. If you change this file, you will look really dumb.
+#
+# Your changelog will be merged with a master changelog. (New stuff added only, and only on the date entry for the day it was merged.)
+# When it is, any changes listed below will disappear.
+#
+# Valid Prefixes:
+# bugfix
+# wip (For works in progress)
+# tweak
+# soundadd
+# sounddel
+# rscadd (general adding of nice things)
+# rscdel (general deleting of nice things)
+# imageadd
+# imagedel
+# maptweak
+# spellcheck (typo fixes)
+# experiment
+#################################
+
+# Your name.
+author: Mechoid
+
+# Optional: Remove this file after generating master changelog. Useful for PR changelogs that won't get used again.
+delete-after: True
+
+# Any changes you've made. See valid prefix list above.
+# INDENT WITH TWO SPACES. NOT TABS. SPACES.
+# SCREW THIS UP AND IT WON'T WORK.
+# Also, all entries are changed into a single [] after a master changelog generation. Just remove the brackets when you add new entries.
+# Please surround your changes in double quotes ("), as certain characters otherwise screws up compiling. The quotes will not show up in the changelog.
+changes:
+ - bugfix: "Artifact shields now function properly after fixing a runtime."
+ - bugfix: "Anomaly batteries function again."
+ - rscadd: "Archaeology sites can have unique batteries, syringes, rings, and 'clubs'."
+ - rscadd: "Multiple artifact effects added, in order to provide more spice, from naughty to nice."
+ - tweak: "Tweaks to normal artifact finds to be more unique."
diff --git a/icons/obj/xenoarchaeology.dmi b/icons/obj/xenoarchaeology.dmi
index e484762679..d500a48be0 100644
Binary files a/icons/obj/xenoarchaeology.dmi and b/icons/obj/xenoarchaeology.dmi differ
diff --git a/polaris.dme b/polaris.dme
index 0b5b3ac9e6..8b4969978a 100644
--- a/polaris.dme
+++ b/polaris.dme
@@ -1952,6 +1952,7 @@
#include "code\modules\mob\update_icons.dm"
#include "code\modules\mob\_modifiers\aura.dm"
#include "code\modules\mob\_modifiers\cloning.dm"
+#include "code\modules\mob\_modifiers\feysight.dm"
#include "code\modules\mob\_modifiers\fire.dm"
#include "code\modules\mob\_modifiers\medical.dm"
#include "code\modules\mob\_modifiers\modifiers.dm"
@@ -2791,29 +2792,38 @@
#include "code\modules\xenoarcheaology\artifacts\crystal.dm"
#include "code\modules\xenoarcheaology\artifacts\gigadrill.dm"
#include "code\modules\xenoarcheaology\artifacts\replicator.dm"
+#include "code\modules\xenoarcheaology\effects\animate_anomaly.dm"
#include "code\modules\xenoarcheaology\effects\badfeeling.dm"
#include "code\modules\xenoarcheaology\effects\berserk.dm"
+#include "code\modules\xenoarcheaology\effects\cannibal.dm"
#include "code\modules\xenoarcheaology\effects\cellcharge.dm"
#include "code\modules\xenoarcheaology\effects\celldrain.dm"
#include "code\modules\xenoarcheaology\effects\cold.dm"
#include "code\modules\xenoarcheaology\effects\dnaswitch.dm"
+#include "code\modules\xenoarcheaology\effects\electric_field.dm"
#include "code\modules\xenoarcheaology\effects\emp.dm"
+#include "code\modules\xenoarcheaology\effects\feysight.dm"
#include "code\modules\xenoarcheaology\effects\forcefield.dm"
+#include "code\modules\xenoarcheaology\effects\gaia.dm"
#include "code\modules\xenoarcheaology\effects\gasco2.dm"
#include "code\modules\xenoarcheaology\effects\gasnitro.dm"
#include "code\modules\xenoarcheaology\effects\gasoxy.dm"
#include "code\modules\xenoarcheaology\effects\gasphoron.dm"
#include "code\modules\xenoarcheaology\effects\gassleeping.dm"
#include "code\modules\xenoarcheaology\effects\goodfeeling.dm"
+#include "code\modules\xenoarcheaology\effects\gravitational_waves.dm"
#include "code\modules\xenoarcheaology\effects\heal.dm"
#include "code\modules\xenoarcheaology\effects\heat.dm"
#include "code\modules\xenoarcheaology\effects\hurt.dm"
+#include "code\modules\xenoarcheaology\effects\poltergeist.dm"
#include "code\modules\xenoarcheaology\effects\radiate.dm"
+#include "code\modules\xenoarcheaology\effects\resurrect.dm"
#include "code\modules\xenoarcheaology\effects\roboheal.dm"
#include "code\modules\xenoarcheaology\effects\robohurt.dm"
#include "code\modules\xenoarcheaology\effects\sleepy.dm"
#include "code\modules\xenoarcheaology\effects\stun.dm"
#include "code\modules\xenoarcheaology\effects\teleport.dm"
+#include "code\modules\xenoarcheaology\effects\vampire.dm"
#include "code\modules\xenoarcheaology\finds\eguns.dm"
#include "code\modules\xenoarcheaology\finds\find_spawning.dm"
#include "code\modules\xenoarcheaology\finds\finds.dm"