diff --git a/code/datums/spells/ethereal_jaunt.dm b/code/datums/spells/ethereal_jaunt.dm index cb164405a5b..a1ac834b367 100644 --- a/code/datums/spells/ethereal_jaunt.dm +++ b/code/datums/spells/ethereal_jaunt.dm @@ -95,7 +95,6 @@ var/canmove = 1 density = 0 anchored = 1 - invisibility = INVISIBILITY_OBSERVER /obj/effect/dummy/spell_jaunt/Destroy() // Eject contents if deleted somehow diff --git a/code/game/gamemodes/antag_spawner.dm b/code/game/gamemodes/antag_spawner.dm index 5de4666f647..abb9afb08a9 100644 --- a/code/game/gamemodes/antag_spawner.dm +++ b/code/game/gamemodes/antag_spawner.dm @@ -81,7 +81,7 @@ /obj/item/weapon/antag_spawner/slaughter_demon/attack_self(mob/user as mob) //var/list/demon_candidates = get_candidates(BE_ALIEN) - if(user.z != 1) + if(user.z != ZLEVEL_STATION)//this is to make sure the wizard does NOT summon a demon from the Den.. user << "You should probably wait until you reach the station." return if(!checking) @@ -108,7 +108,7 @@ possiblecandidates -= demon_candidates used = 1 checking = 0 - spawn_antag(demon_candidates, get_turf(src.loc), "Slaughter Demon") + spawn_antag(demon_candidates, get_turf(src.loc), "Slaughter Demon",user) user << "You shatter the bottle, no turning back now!" user << "You sense a dark presence lurking just beyond the veil..." playsound(user.loc, 'sound/effects/Glassbr1.ogg', 100, 1) @@ -126,24 +126,25 @@ return -/obj/item/weapon/antag_spawner/slaughter_demon/spawn_antag(var/client/C, var/turf/T, var/type = "") +/obj/item/weapon/antag_spawner/slaughter_demon/spawn_antag(var/client/C, var/turf/T, var/type = "", mob/user as mob) var /obj/effect/dummy/slaughter/holder = new /obj/effect/dummy/slaughter(T) var/mob/living/simple_animal/slaughter/S = new /mob/living/simple_animal/slaughter/(holder) S.vialspawned = TRUE S.phased = TRUE S.key = C.key - S.mind.assigned_role = "Slaughter Demon" - S.mind.special_role = "Slaughter Demon" - ticker.mode.traitors += S.mind - var/datum/objective/assassinate/KillDaWiz = new /datum/objective/assassinate - KillDaWiz.owner = S:mind - KillDaWiz:target = usr:mind - KillDaWiz.explanation_text = "Kill [usr.real_name], the one who was foolish enough to summon you." - S.mind.objectives += KillDaWiz - var/datum/objective/slaughter/objective = new - objective.owner = S:mind - //Paradise port:i changed ther verbage..might want to do so on the above kill objective. Maybe save the wizard for last... - S.mind.objectives += objective - S << "Objective #[1]: [KillDaWiz.explanation_text]" - S << "Objective #[2]: [objective.explanation_text]" \ No newline at end of file + if(S.mind) + S.mind.assigned_role = "Slaughter Demon" + S.mind.special_role = "Slaughter Demon" + ticker.mode.traitors += S.mind + var/datum/objective/assassinate/KillDaWiz = new /datum/objective/assassinate + KillDaWiz.owner = S.mind + KillDaWiz.target = user.mind + KillDaWiz.explanation_text = "Kill [user.real_name], the one who was foolish enough to summon you." + S.mind.objectives += KillDaWiz + var/datum/objective/slaughter/objective = new + objective.owner = S.mind + //Paradise port:i changed ther verbage..might want to do so on the above kill objective. Maybe save the wizard for last... + S.mind.objectives += objective + S << "Objective #[1]: [KillDaWiz.explanation_text]" + S << "Objective #[2]: [objective.explanation_text]" \ No newline at end of file diff --git a/code/game/gamemodes/wizard/artefact.dm b/code/game/gamemodes/wizard/artefact.dm index f33436f01c0..12c041d6aed 100644 --- a/code/game/gamemodes/wizard/artefact.dm +++ b/code/game/gamemodes/wizard/artefact.dm @@ -118,143 +118,82 @@ force = 15 throwforce = 10 w_class = 3 - var/charged = 1 hitsound = 'sound/weapons/bladeslice.ogg' + var/charged = 1 + var/spawn_type = /obj/singularity/narsie/wizard + var/spawn_amt = 1 + var/activate_descriptor = "reality" + var/rend_desc = "You should run now." + +/obj/item/weapon/veilrender/attack_self(mob/user as mob) + if(charged) + new /obj/effect/rend(get_turf(user), spawn_type, spawn_amt, rend_desc) + charged = 0 + user.visible_message("[src] hums with power as [user] deals a blow to [activate_descriptor] itself!") + else + user << "The unearthly energies that powered the blade are now dormant." + /obj/effect/rend name = "tear in the fabric of reality" - desc = "You should run now" + desc = "You should run now." icon = 'icons/obj/biomass.dmi' icon_state = "rift" density = 1 unacidable = 1 anchored = 1.0 + var/spawn_path = /mob/living/simple_animal/cow //defaulty cows to prevent unintentional narsies + var/spawn_amt_left = 20 -/obj/effect/rend/New() - spawn(50) - new /obj/singularity/narsie/wizard(get_turf(src)) +/obj/effect/rend/New(loc, var/spawn_type, var/spawn_amt, var/desc) + ..() + src.spawn_path = spawn_type + src.spawn_amt_left = spawn_amt + src.desc = desc + + processing_objects.Add(src) + //return + +/obj/effect/rend/process() + for(var/mob/M in loc) + return + new spawn_path(loc) + spawn_amt_left-- + if(spawn_amt_left <= 0) + qdel(src) + +/obj/effect/rend/attackby(obj/item/I as obj, mob/user as mob) + if(istype(I, /obj/item/weapon/nullrod)) + user.visible_message("[user] seals \the [src] with \the [I].") qdel(src) return - return - -/obj/item/weapon/veilrender/attack_self(mob/user as mob) - if(charged == 1) - new /obj/effect/rend(get_turf(usr)) - charged = 0 - visible_message("\red [src] hums with power as [usr] deals a blow to reality itself!") - else - user << "\red The unearthly energies that powered the blade are now dormant." - - + ..() /obj/item/weapon/veilrender/vealrender name = "veal render" desc = "A wicked curved blade of alien origin, recovered from the ruins of a vast farm." + spawn_type = /mob/living/simple_animal/cow + spawn_amt = 20 + activate_descriptor = "hunger" + rend_desc = "Reverberates with the sound of ten thousand moos." -/obj/item/weapon/veilrender/vealrender/attack_self(mob/user as mob) - if(charged) - new /obj/effect/rend/cow(get_turf(usr)) - charged = 0 - visible_message("\red [src] hums with power as [usr] deals a blow to hunger itself!") - else - user << "\red The unearthly energies that powered the blade are now dormant." - -/obj/effect/rend/cow - desc = "Reverberates with the sound of ten thousand moos." - var/cowsleft = 20 - -/obj/effect/rend/cow/New() - processing_objects.Add(src) - return - -/obj/effect/rend/cow/process() - if(locate(/mob) in loc) return - new /mob/living/simple_animal/cow(loc) - cowsleft-- - if(cowsleft <= 0) - qdel(src) - -/obj/effect/rend/cow/attackby(obj/item/I as obj, mob/user as mob, params) - if(istype(I, /obj/item/weapon/nullrod)) - visible_message("\red [I] strikes a blow against \the [src], banishing it!") - spawn(1) - qdel(src) - return - ..() -//Why did i add this....-Fethas -/obj/item/weapon/veilrender/honkrender //HONK!! +/obj/item/weapon/veilrender/honkrender name = "honk render" - desc = "A wicked curved 'blade' of honk origin, recovered from the ruins of a vast circus." + desc = "A wicked curved blade of alien origin, recovered from the ruins of a vast circus." + spawn_type = /mob/living/simple_animal/hostile/retaliate/clown + spawn_amt = 10 + activate_descriptor = "depression" + rend_desc = "Gently wafting with the sounds of endless laughter." icon_state = "clownrender" -/obj/item/weapon/veilrender/honkrender/attack_self(mob/user as mob) - if(charged) - new /obj/effect/rend/honk(get_turf(usr)) - charged = 0 - visible_message("\red [src] hums with power as [usr] deals a blow to depression itself!") - playsound(get_turf(usr),"sound/items/bikehorn.ogg",50,10,1) - else - user << "\red The honk energies that powered the blade are now dormant." -/obj/effect/rend/honk - desc = "Gently wafting with the sounds of endless laughter." - var/honkleft = 10 - -/obj/effect/rend/honk/New() - processing_objects.Add(src) - return - -/obj/effect/rend/honk/process() - if(locate(/mob) in loc) return - new /mob/living/simple_animal/hostile/retaliate/clown(loc) - honkleft-- - if(honkleft <= 0) - del src - -/obj/effect/rend/honk/attackby(obj/item/I as obj, mob/user as mob, params) - if(istype(I, /obj/item/weapon/nullrod)) - visible_message("\red [I] strikes a blow against \the [src], banishing it!") - spawn(1) - del src - return - ..() - -/obj/item/weapon/veilrender/crabrender //HONK!! +/obj/item/weapon/veilrender/crabrender name = "crab render" desc = "A wicked curved blade of alien origin, recovered from the ruins of a vast aquarium." - - -/obj/item/weapon/veilrender/crabrender/attack_self(mob/user as mob) - if(charged) - new /obj/effect/rend/crab(get_turf(usr)) - charged = 0 - visible_message("\red [src] hums with power as [usr] deals a blow to reality itself!") - else - user << "\red The energies that powered the blade are now dormant." - -/obj/effect/rend/crab - desc = "Gently wafting with the sounds of endless clacking." - var/crableft = 10 - -/obj/effect/rend/crab/New() - processing_objects.Add(src) - return - -/obj/effect/rend/crab/process() - if(locate(/mob) in loc) return - new /mob/living/simple_animal/crab(loc) - crableft-- - if(crableft <= 0) - del src - -///obj/effect/rend/crab/attackby(obj/item/I as obj, mob/user as mob, params) -// if(istype(I, /obj/item/weapon/nullrod)) -// visible_message("\red [I] strikes a blow against \the [src], banishing it!") -// spawn(1) -// del src -// return -// ..() - + spawn_type = /mob/living/simple_animal/crab + spawn_amt = 10 + activate_descriptor = "sea life" + rend_desc = "Gently wafting with the sounds of endless clacking." /////////////////////////////////////////Scrying/////////////////// @@ -272,5 +211,5 @@ /obj/item/weapon/scrying/attack_self(mob/user as mob) user << "\blue You can see...everything!" - visible_message("\red [usr] stares into [src], their eyes glazing over.") + visible_message("\red [user] stares into [src], their eyes glazing over.") user.ghostize(1) diff --git a/code/game/gamemodes/wizard/spellbook.dm b/code/game/gamemodes/wizard/spellbook.dm index c39231bf86e..f2abb066afe 100644 --- a/code/game/gamemodes/wizard/spellbook.dm +++ b/code/game/gamemodes/wizard/spellbook.dm @@ -267,7 +267,7 @@ user << "\blue The walls suddenly disappear." return 1 -/datum/spellbook_entry/item/scryingorb/CanBuy(var/mob/living/carbon/human/user,var/obj/item/weapon/spellbook/book) +/datum/spellbook_entry/item/bloodbottle/CanBuy(var/mob/living/carbon/human/user,var/obj/item/weapon/spellbook/book) return ..() && !limit /datum/spellbook_entry/item/soulstones diff --git a/code/modules/events/slaughterevent.dm b/code/modules/events/slaughterevent.dm index 34b2fe0b6d2..cc19fa80cff 100644 --- a/code/modules/events/slaughterevent.dm +++ b/code/modules/events/slaughterevent.dm @@ -66,5 +66,4 @@ log_game("[key_of_slaughter] was spawned as a Slaughter Demon by an event.") return 0 message_admins("Unfortunately, no candidates were available for becoming a Slaugter Demon. Shutting down.") - kill() - return \ No newline at end of file + kill() \ No newline at end of file diff --git a/code/modules/mob/living/simple_animal/slaughter/bloodnode.dm b/code/modules/mob/living/simple_animal/slaughter/bloodnode.dm index 1be13c8fa95..15825362eff 100644 --- a/code/modules/mob/living/simple_animal/slaughter/bloodnode.dm +++ b/code/modules/mob/living/simple_animal/slaughter/bloodnode.dm @@ -12,109 +12,106 @@ - New(loc, var/h = 100) - nodecount +=1 - processing_objects.Add(src) - NodeColor() - ..(loc, h) +/obj/effect/bloodnode/New(loc, var/h = 100) + nodecount +=1 + processing_objects.Add(src) + NodeColor() + ..(loc, h) - Destroy() - nodecount -= 1 - processing_objects.Remove(src) - ..() - return - process() - if(lastblood == 0 || (world.time - lastblood) > 600) - //src.visible_message("pulse!")//debug - var/obj/effect/decal/cleanable/blood/splatter/blooddecal = new (src.loc) - playsound(get_turf(src), 'sound/effects/splat.ogg', 50, 1) - //throw that then use a gibspawner - new /obj/effect/gibspawner/human(get_turf(src)) - var/atom/bloodtarget = get_edge_target_turf(src, get_dir(src, get_step_away(src, src))) - blooddecal.throw_at(get_edge_target_turf(bloodtarget,pick(alldirs)),rand(5,15),5) - lastblood += world.time - return +/obj/effect/bloodnode/Destroy() + nodecount -= 1 + processing_objects.Remove(src) + ..() - proc/NodeColor()//Stealing from NEW blob code... - overlays.Cut() - var/image/I = new('icons/mob/blob.dmi', "blob") - I.color = "#7F0000" - overlays += I - var/image/C = new('icons/mob/blob.dmi', "blob_node_overlay") - C.color = "#FF4C4C" - overlays += C +/obj/effect/bloodnode/process() + if(lastblood == 0 || (world.time - lastblood) > 600) + //src.visible_message("pulse!")//debug + var/obj/effect/decal/cleanable/blood/splatter/blooddecal = new (src.loc) + playsound(get_turf(src), 'sound/effects/splat.ogg', 50, 1) + //throw that then use a gibspawner + new /obj/effect/gibspawner/human(get_turf(src)) + var/atom/bloodtarget = get_edge_target_turf(src, get_dir(src, get_step_away(src, src))) + blooddecal.throw_at(get_edge_target_turf(bloodtarget,pick(alldirs)),rand(5,15),5) + lastblood += world.time - proc/Delete() +/obj/effect/bloodnode/proc/NodeColor()//Stealing from NEW blob code... + overlays.Cut() + var/image/I = new('icons/mob/blob.dmi', "blob") + I.color = "#7F0000" + overlays += I + var/image/C = new('icons/mob/blob.dmi', "blob_node_overlay") + C.color = "#FF4C4C" + overlays += C + + + +/obj/effect/bloodnode/update_icon() + //src.visible_message("[health]") + if(health <= 0) + playsound(get_turf(src), 'sound/effects/gib.ogg', 50, 1) + new /obj/effect/gibspawner/human(get_turf(src)) qdel(src) + +/obj/effect/bloodnode/ex_act(severity) + var/damage = 150 + health -= ((damage - (severity * 5))) update_icon() - //src.visible_message("[health]") - if(health <= 0) - playsound(get_turf(src), 'sound/effects/gib.ogg', 50, 1) - new /obj/effect/gibspawner/human(get_turf(src)) - Delete() - return + + +/obj/effect/bloodnode/bullet_act(var/obj/item/projectile/Proj) + ..() + health -= (Proj.damage) + update_icon() + return 0 + + +/obj/effect/bloodnode/attackby(var/obj/item/weapon/W, var/mob/living/user, params) + user.changeNext_move(CLICK_CD_MELEE) + user.do_attack_animation(src) + playsound(get_turf(src), 'sound/effects/attackblob.ogg', 50, 1) + src.visible_message("The [src.name] has been attacked with \the [W][(user ? " by [user]." : ".")]") + var/damage = 0 + switch(W.damtype) + if("fire") + damage = (W.force) + if(istype(W, /obj/item/weapon/weldingtool)) + playsound(get_turf(src), 'sound/items/Welder.ogg', 100, 1) + if("brute") + if(prob(25)) + paranoia.DoEffectTouch(user) + damage = (W.force) + + health -= damage + update_icon() + + +/obj/effect/bloodnode/attack_hand(var/mob/user) + user.changeNext_move(CLICK_CD_MELEE) + user.do_attack_animation(src) + if(prob(25)) + paranoia.DoEffectTouch(user) + playsound(src.loc, 'sound/effects/attackblob.ogg', 50, 1) + var/damage = rand(5,10) + if(!damage) // Avoid divide by zero errors return + src.visible_message("\The [src.name] has been punched by [user]!") + damage = max(damage) + health -= damage + update_icon() - ex_act(severity) - var/damage = 150 - health -= ((damage - (severity * 5))) - //update_icon() + + +/obj/effect/bloodnode/attack_animal(mob/living/simple_animal/M as mob) + M.changeNext_move(CLICK_CD_MELEE) + M.do_attack_animation(src) + playsound(src.loc, 'sound/effects/attackblob.ogg', 50, 1) + src.visible_message("\The [src.name] has been attacked by \the [M]!") + var/damage = rand(M.melee_damage_lower, M.melee_damage_upper) + if(!damage) // Avoid divide by zero errors return + damage = max(damage) + health -= damage + update_icon() - - bullet_act(var/obj/item/projectile/Proj) - ..() - health -= (Proj.damage) - //update_icon() - return 0 - - - attackby(var/obj/item/weapon/W, var/mob/living/user, params) - user.changeNext_move(CLICK_CD_MELEE) - user.do_attack_animation(src) - playsound(get_turf(src), 'sound/effects/attackblob.ogg', 50, 1) - src.visible_message("\red The [src.name] has been attacked with \the [W][(user ? " by [user]." : ".")]") - var/damage = 0 - switch(W.damtype) - if("fire") - damage = (W.force) - if(istype(W, /obj/item/weapon/weldingtool)) - playsound(get_turf(src), 'sound/items/Welder.ogg', 100, 1) - if("brute") - if(prob(25)) - paranoia.DoEffectTouch(user) - damage = (W.force) - - health -= damage - update_icon() - return - - attack_hand(var/mob/user) - user.changeNext_move(CLICK_CD_MELEE) - user.do_attack_animation(src) - if(prob(25)) - paranoia.DoEffectTouch(user) - playsound(src.loc, 'sound/effects/attackblob.ogg', 50, 1) - var/damage = rand(1,10) - if(!damage) // Avoid divide by zero errors - return - damage = max(damage) - health -= damage - update_icon() - return - - - attack_animal(mob/living/simple_animal/M as mob) - M.changeNext_move(CLICK_CD_MELEE) - M.do_attack_animation(src) - playsound(src.loc, 'sound/effects/attackblob.ogg', 50, 1) - src.visible_message("The [src.name] has been attacked by \the [M]!") - var/damage = rand(M.melee_damage_lower, M.melee_damage_upper) - if(!damage) // Avoid divide by zero errors - return - damage = max(damage) - health -= damage - update_icon() - return diff --git a/code/modules/mob/living/simple_animal/slaughter/slaughter.dm b/code/modules/mob/living/simple_animal/slaughter/slaughter.dm index 5912a72f7d7..19b47b5db8e 100644 --- a/code/modules/mob/living/simple_animal/slaughter/slaughter.dm +++ b/code/modules/mob/living/simple_animal/slaughter/slaughter.dm @@ -1,12 +1,3 @@ -///The following mini-antag was coded by KorPhaeron for TG Station -//Credits: Concept: KorPhaeron, Sprite:Ausops, Sounds:Cuboos -///Ported for paradise by Aurorablade/Fethas -///Things added for port: -//Various tweeks -//Blood... -/// Made the message tell you waht the demon is sinking into(gibs/blood etc) -///Alot of blood...Alot..Of blood.. - //////////////////The Monster /mob/living/simple_animal/slaughter @@ -27,20 +18,21 @@ status_flags = CANPUSH attack_sound = 'sound/misc/demon_attack1.ogg' min_oxy = 0 - max_oxy = 0 + max_oxy = INFINITY min_tox = 0 - max_tox = 0 + max_tox = INFINITY min_co2 = 0 - max_co2 = 0 + max_co2 = INFINITY min_n2 = 0 - max_n2 = 0 + max_n2 = INFINITY minbodytemp = 0 + maxbodytemp = INFINITY faction = list("slaughter") attacktext = "wildly tears into" maxHealth = 250 health = 250 environment_smash = 1 - universal_understand = 1 + //universal_understand = 1 melee_damage_lower = 30 melee_damage_upper = 30 see_in_dark = 8 @@ -93,10 +85,9 @@ visible_message("The [src] screams in anger as its form collapes into a pool of viscera.") ghostize() qdel(src) - return - - +/mob/living/simple_animal/slaughter/say(message) + return 0 ////////////////////The Powers /mob/living/simple_animal/slaughter/proc/phaseout(var/obj/effect/decal/cleanable/B) @@ -124,10 +115,10 @@ if(istype(src.pulling, /mob/living/)) var/mob/living/victim = src.pulling if(victim.stat == CONSCIOUS) - src.visible_message("[victim] kicks free of the [src] at the last second!") + src.visible_message("[victim] kicks free of \the [src] at the last second!") else victim.loc = holder///holder - src.visible_message("The [src] drags [victim] into [B]!") + src.visible_message("\The [src] drags [victim] into [B]!") src.kidnapped = victim flick("jaunt",animation) src.loc = holder @@ -161,12 +152,13 @@ if (src.devoured == 5) src.mind.current.verbs += /mob/living/simple_animal/slaughter/proc/goreThrow src.mind.current.verbs += /mob/living/simple_animal/slaughter/proc/bloodSac - src << " You have consumed enough to be able to summon Excess Gore." + src << " You have consumed enough to be able to summon Excess Gore." src.notransform = 0 if(!(src.eating)) new /obj/effect/gibspawner/human(get_turf(src))///Somewhere a janitor weeps.. sleep(6) - qdel(animation) + if(animation) + qdel(animation) /mob/living/simple_animal/slaughter/proc/phasein(var/obj/effect/decal/cleanable/B) var/atom/movable/overlay/animation = new /atom/movable/overlay( B.loc ) @@ -189,12 +181,14 @@ if (prob(25)) var/list/voice = list('sound/hallucinations/behind_you1.ogg','sound/hallucinations/im_here1.ogg','sound/hallucinations/turn_around1.ogg','sound/hallucinations/i_see_you1.ogg') playsound(get_turf(src), pick(voice),50, 1, -1) - src.visible_message("The [src] rises out of [B]!") + src.visible_message("\The [src] rises out of [B]!") new /obj/effect/gibspawner/human(get_turf(src)) playsound(get_turf(src), 'sound/misc/exit_blood.ogg', 100, 1, -1) sleep(6) - qdel(src.holder) - qdel(animation) + if(src.holder) + qdel(src.holder) + if(animation) + qdel(animation) /obj/effect/decal/cleanable/blood/CtrlClick(var/mob/user) ..() @@ -238,7 +232,7 @@ var/canmove = 1 density = 0 anchored = 1 - invisibility = INVISIBILITY_OBSERVER + //invisibility = INVISIBILITY_OBSERVER /obj/effect/dummy/slaughter/relaymove(var/mob/user, direction) if (!src.canmove || !direction) return @@ -268,7 +262,7 @@ var/list/choices = list() for(var/mob/living/carbon/C in living_mob_list) - if(C.stat != 2 && C.mind) + if(C.stat != 2 && C.client && C.stat != DEAD) choices += C var/mob/living/carbon/M = input(src,"Who do you wish to talk to?") in null|choices @@ -301,7 +295,7 @@ paranoia.DoEffectPulse() var/targetPart = pick("chest","groin","head","l_arm","r_arm","r_leg","l_leg","l_hand","r_hand","l_foot","r_foot") portal.apply_damage(rand(5, 10), BRUTE, targetPart) - portal << "\red The skin on your [parse_zone(targetPart)] feels like it's ripping apart, and a stream of blood flies out." + portal << "\The skin on your [parse_zone(targetPart)] feels like it's ripping apart, and a stream of blood flies out." var/obj/effect/decal/cleanable/blood/splatter/animated/aniBlood = new(portal.loc) aniBlood.target_turf = pick(range(1, src)) aniBlood.blood_DNA = list() @@ -309,7 +303,7 @@ portal.vessel.remove_reagent("blood",rand(25,50)) cooldown = world.time else - usr << "You cannot Exsanguinate mortals yet!" + usr << "You cannot Exsanguinate mortals yet!" /mob/living/simple_animal/slaughter/proc/goreThrow(mob/target as mob in oview()) set name = "Gore Throw"