Index: docs/plotdict.xml
===================================================================
--- docs/plotdict.xml	(revision 190)
+++ docs/plotdict.xml	(working copy)
@@ -488,6 +488,36 @@
 			<shortname>use door</shortname>
 			<description>Instantly uses the numbered door, just as if you had stepped into it. <note>An automatic <ref>wait</ref>(1) occurs immediately after this command.</note></description>
 		</command>
+		<command id="doorexists">
+			<canon>door exists (number)</canon>
+			<shortname>door exists</shortname>
+			<description>Returns <ref>true</ref> if there is a door with ID <p>number</p> on the current map. This command is useful for avoiding script errors due to invalid door IDs.</description>
+		</command>
+		<command id="getdoorx">
+			<canon>get door x (number)</canon>
+			<shortname>get door x</shortname>
+			<description>Returns the x coordinate (in tiles) of the numbered door.</description>
+		</command>
+		<command id="getdoory">
+			<canon>get door y (number)</canon>
+			<shortname>get door y</shortname>
+			<description>Returns the y coordinate (in tiles) of the numbered door.</description>
+		</command>
+		<command id="getdoordestinationid">
+			<canon>get door destination id (number)</canon>
+			<shortname>get door destination id</shortname>
+			<description>Returns the door id of the door linked to by the numbered door. To get the door's location, use <ref>getdoorx</ref> and <ref>getdoory</ref> when the player is on the destination map. If door <p>number</p> does not exist, or is not currently linked to any other door, then -1 is returned. <note>A door's destination can vary depending on the current game state. Check your doorlinks if you get unexpected results!</note></description>
+			<seealso>
+				<ref>getdoorx</ref>
+				<ref>getdoory</ref>
+				<ref>getdoordestinationmap</ref>
+			</seealso>
+		</command>
+		<command id="getdoordestinationmap">
+			<canon>get door destination map (number)</canon>
+			<shortname>get door destination map</shortname>
+			<description>Returns the map id of the door linked to by the numbered door. If door <p>number</p> does not exist, or is not currently linked to any other door, then -1 is returned. <note>A door's destination can vary depending on the current game state. Check your doorlinks if you get unexpected results!</note></description>
+		</command>
 		<command id="teleporttomap">
 			<canon>teleport to map (map, x, y)</canon>
 			<shortname>teleport to map</shortname>
@@ -1455,6 +1485,13 @@
 			<note>This command replaces the old <p>get attack name</p> which required you to use <p>atk:name -- 2</p> or the attack id number <p>-- 1</p></note>
 			</description>
 		</command>
+		<command id="getattackcaption">
+			<canon>get attack caption (ID, attack)</canon>
+			<shortname>get attack caption</shortname>
+			<description>This command will take the caption of <p>attack</p> and stick it in string #<p>ID</p>, overwriting its contents. Use the <p>atk:name</p> constants from your HSI file.
+			<note>If you want to use this command with attack ID numbers, you must add 1 to the ID number.</note>
+			</description>
+		</command>
 		<command id="getglobalstring">
 			<canon>get global string (ID, global)</canon>
 			<shortname>get global string</shortname>
@@ -4453,6 +4490,33 @@
 				<ref>readenemydata</ref>
 			</seealso>
 		</command>
+      <command id="readenemynormalattack">
+         <canon>read enemy normal attack (enemyid, index)</canon>
+         <shortname>read enemy normal attack</shortname>
+         <description>Reads an entry from an enemy's standard attack set. The <p>index</p> argument specifies which of the five attacks to read (from 0 to 4).</description>
+         <seealso>
+            <ref>readenemyaloneattack</ref>
+            <ref>readenemydesperationattack</ref>
+         </seealso>
+      </command>
+      <command id="readenemyaloneattack">
+         <canon>read enemy alone attack (enemyid, index)</canon>
+         <shortname>read enemy alone attack</shortname>
+         <description>Reads an entry from an enemy's Alone attack set. The <p>index</p> argument specifies which of the five attacks to read (from 0 to 4).</description>
+         <seealso>
+            <ref>readenemyattack</ref>
+            <ref>readenemydesperationattack</ref>
+         </seealso>
+      </command>
+		<command id="readenemynormalattack">
+			<canon>read enemy desperation attack (enemyid, index)</canon>
+			<shortname>read enemy desperation attack</shortname>
+			<description>Reads an entry from an enemy's Desperation attack set. The <p>index</p> argument specifies which of the five attacks to read (from 0 to 4).</description>
+			<seealso>
+				<ref>readenemyattack</ref>
+				<ref>readenemyaloneattack</ref>
+			</seealso>
+		</command>
 		<command id="addenemytoformation">
 			<canon>add enemy to formation (formation, enemy id, x, y, slot)</canon>
 			<shortname>add enemy to formation</shortname>
@@ -5013,6 +5077,43 @@
 			<description>The case command is used to enclose a block of commands for one possible result of a <ref>switch</ref> command. See <ref>switch</ref> for more details.</description>
 		</command>
 	</section>
+	<section title="Attack Commands">
+		<command id="readattacktargetclass">
+			<canon>read attack target class (attackid)</canon>
+			<shortname>read attack target class</canon>
+			<description>Returns the target class of the given attack (one of <ref>targetclass:enemy</ref>, <ref>targetclass:ally</ref>, <ref>targetclass:self</ref>, <ref>targetclass:all</ref>, <ref>targetclass:allyincludingdead</ref>, <ref>targetclass:allyexcludingself</ref>, <ref>targetclass:revenge</ref>, <ref>targetclass:revengewholebattle</ref>, <ref>targetclass:previoustarget</ref>, <ref>targetclass:recordedtarget</ref>, <ref>targetclass:deadallies</ref>, <ref>targetclass:thankvenge</ref>, or <ref>targetclass:thankvengewholebattle</ref>).</description>
+		</command>
+		<command id="readattacktargetsetting">
+			<canon>read attack target setting (attackid)</canon>
+			<shortname>read attack target setting</canon>
+			<description>Returns the target setting of the given attack (one of <ref>targetsetting:focused</ref>, <ref>targetsetting:spread</ref>, <ref>targetsetting:optionalspread</ref>, <ref>targetsetting:random</ref>, or <ref>targetsetting:firsttarget</ref>).</description>
+		</command>
+		<command id="readattackdamageequation">
+			<canon>read attack damage equation (attackid)</canon>
+			<shortname>read attack damage equation</canon>
+			<description>Returns the damage equation of the given attack (one of <ref>damageequation:normal</ref>, <ref>damageequation:blunt</ref>, <ref>damageequation:sharp</ref>, <ref>damageequation:puredamage</ref>, <ref>damageequation:nodamage</ref>, <ref>damageequation:percentofmax</ref> or <ref>damageequation:percentofcurrent</ref>).</description>
+		</command>
+		<command id="readattackextradamage">
+			<canon>read attack extra damage (attackid)</canon>
+			<shortname>read attack extra damage</canon>
+			<description>Returns the extra damage percent of the given attack.</description>
+		</command>
+		<command id="readattackitem">
+			<canon>read attack item (attackid, slot)</canon>
+			<shortname>read attack item</canon>
+			<description>Returns the item ID + 1 of the given attack's chosen item cost slot (from 0 to 2).</description>
+			<seealso>
+				<ref>readattackitemquantity</ref>
+			</seealso>
+		</command>
+		<command id="readattackitemquantity">
+			<canon>read attack item quantity (attackid, slot)</canon>
+			<shortname>read attack item quantity</canon>
+			<description>Returns the quantity consumed of the given attack's chosen item cost slot (from 0 to 2).</description>
+			<seealso>
+				<ref>readattackitem</ref>
+			</seealso>
+		</command>
 	<section title="Advanced Commands">
 		<command id="setheropicture">
 			<canon>set hero picture (who,picture,type)</canon>
@@ -5368,6 +5469,11 @@
 				<ref>herobaseelementalresistasint</ref>
 			</seealso>
 		</command>
+		<command id="enemyelementalresistasint">
+			<canon>enemy elemental resist as int (id, element)</canon>
+			<shortname>enemy elemental resist as int</shortname>
+			<description>Gets the amount of damage that an enemy receives from attacks of a certain element, as a percentage of normal. The argument <p>id</p> is the enemy id. The argument <p>element</p> is a number from 0 to whatever the highest enabled element is. The result is rounded to the nearest integer. For example, if the enemy takes 2.5% damage (1/40 normal), then the result will be 3.<note>When floating point support is added to HamsterSpeak, an alternative to this command will be added.</note></description>
+		</command>
 		<command id="readglobal">
 			<canon>read global (id)</canon>
 			<shortname>read global</shortname>
@@ -5993,5 +6099,125 @@
 			<alias>song:sameaslastmap</alias>
 			<shortname>song: same as map</shortname>
 		</command>
+		<command id="targetclass:enemy">
+			<canon>targetclass: enemy</alias>
+			<shortname>targetclass: enemy</shortname>
+			<description>Used with <ref>readattacktargetclass</ref> to indicate an attack that targets enemies.</description>
+		</command>
+		<command id="targetclass:ally">
+			<canon>targetclass: ally</alias>
+			<shortname>targetclass: ally</shortname>
+			<description>Used with <ref>readattacktargetclass</ref> to indicate an attack that targets living allies.</description>
+		</command>
+		<command id="targetclass:self">
+			<canon>targetclass: self</alias>
+			<shortname>targetclass: self</shortname>
+			<description>Used with <ref>readattacktargetclass</ref> to indicate an attack that targets the caster.</description>
+		</command>
+		<command id="targetclass:allyincludingdead">
+			<canon>targetclass: ally including dead</alias>
+			<shortname>targetclass: ally including dead</shortname>
+			<description>Used with <ref>readattacktargetclass</ref> to indicate an attack that targets allies, living or dead.</description>
+		</command>
+		<command id="targetclass:allyexcludingself">
+			<canon>targetclass: ally excluding self</alias>
+			<shortname>targetclass: ally excluding self</shortname>
+			<description>Used with <ref>readattacktargetclass</ref> to indicate an attack that targets allies other than the caster.</description>
+		</command>
+		<command id="targetclass:revenge">
+			<canon>targetclass: revenge</alias>
+			<shortname>targetclass: enemy</shortname>
+			<description>Used with <ref>readattacktargetclass</ref> to indicate an attack that targets the last enemy to damage the caster.</description>
+		</command>
+		<command id="targetclass:revengewholebattle">
+			<canon>targetclass: revenge whole battle</alias>
+			<shortname>targetclass: revenge whole battle</shortname>
+			<description>Used with <ref>readattacktargetclass</ref> to indicate an attack that targets all enemies who have damaged the caster in this battle.</description>
+		</command>
+		<command id="targetclass:previoustarget">
+			<canon>targetclass: previous target</alias>
+			<shortname>targetclass: previous target</shortname>
+			<description>Used with <ref>readattacktargetclass</ref> to indicate an attack that targets the target of the previous attack.</description>
+		</command>
+		<command id="targetclass:recordedtarget">
+			<canon>targetclass: recorded target</alias>
+			<shortname>targetclass: recorded target</shortname>
+			<description>Used with <ref>readattacktargetclass</ref> to indicate an attack that targets the recorded target.</description>
+		</command>
+		<command id="targetclass:deadallies">
+			<canon>targetclass: dead allies</alias>
+			<shortname>targetclass: dead allies</shortname>
+			<description>Used with <ref>readattacktargetclass</ref> to indicate an attack that targets dead allies.</description>
+		</command>
+		<command id="targetclass:thankvenge">
+			<canon>targetclass: thankvenge</alias>
+			<shortname>targetclass: thankvenge</shortname>
+			<description>Used with <ref>readattacktargetclass</ref> to indicate an attack that targets the last ally to heal the caster.</description>
+		</command>
+		<command id="targetclass:thankvengewholebattle">
+			<canon>targetclass: thankvenge whole battle</alias>
+			<shortname>targetclass: thankvenge whole battle</shortname>
+			<description>Used with <ref>readattacktargetclass</ref> to indicate an attack that targets all allies who have healed the caster in this battle.</description>
+		</command>
+		<command id="targetsetting:focused">
+			<canon>targetsetting: focused</alias>
+			<shortname>targetsetting: focused</shortname>
+			<description>Used with <ref>readattacktargetsetting</ref> to indicate an attack that affects one target.</description>
+		</command>
+		<command id="targetsetting:spread">
+			<canon>targetsetting: spread</alias>
+			<shortname>targetsetting: spread</shortname>
+			<description>Used with <ref>readattacktargetsetting</ref> to indicate an attack that affects multiple targets.</description>
+		</command>
+		<command id="targetsetting:optionalspread">
+			<canon>targetsetting: optional spread</alias>
+			<shortname>targetsetting: optional spread</shortname>
+			<description>Used with <ref>readattacktargetsetting</ref> to indicate an attack that affects one or multiple targets.</description>
+		</command>
+		<command id="targetsetting:randomfocus">
+			<canon>targetsetting: random focus</alias>
+			<shortname>targetsetting: random focus</shortname>
+			<description>Used with <ref>readattacktargetsetting</ref> to indicate an attack that affects a single random target.</description>
+		</command>
+		<command id="targetsetting:firsttarget">
+			<canon>targetsetting: first target</alias>
+			<shortname>targetsetting: spread</shortname>
+			<description>Used with <ref>readattacktargetsetting</ref> to indicate an attack that affects the first available target.</description>
+		</command>
+		<command id="damageequation:normal">
+			<canon>damageequation: normal</alias>
+			<shortname>damageequation: normal</shortname>
+			<description>Used with <ref>readattackdamageequation</ref> to indicate an attack that uses the standard damage formula.</description>
+		</command>
+		<command id="damageequation:blunt">
+			<canon>damageequation: blunt</alias>
+			<shortname>damageequation: blunt</shortname>
+			<description>Used with <ref>readattackdamageequation</ref> to indicate an attack that uses the Blunt damage formula.</description>
+		</command>
+		<command id="damageequation:sharp">
+			<canon>damageequation: sharp</alias>
+			<shortname>damageequation: sharp</shortname>
+			<description>Used with <ref>readattackdamageequation</ref> to indicate an attack that uses the Sharp damage formula.</description>
+		</command>
+		<command id="damageequation:puredamage">
+			<canon>damageequation: pure damage</alias>
+			<shortname>damageequation: pure damage</shortname>
+			<description>Used with <ref>readattackdamageequation</ref> to indicate an attack that deals unmitigated damage.</description>
+		</command>
+		<command id="damageequation:nodamage">
+			<canon>damageequation: no damage</alias>
+			<shortname>damageequation: no damage</shortname>
+			<description>Used with <ref>readattackdamageequation</ref> to indicate an attack that deals no damage.</description>
+		</command>
+		<command id="damageequation:percentofmax">
+			<canon>damageequation: percent of max</alias>
+			<shortname>damageequation: percent of max</shortname>
+			<description>Used with <ref>readattackdamageequation</ref> to indicate an attack that sets the target stat to a percentage of its maximum value.</description>
+		</command>
+		<command id="damageequation:percentofcurrent">
+			<canon>damageequation: percent of current</alias>
+			<shortname>damageequation: percent of current</shortname>
+			<description>Used with <ref>readattackdamageequation</ref> to indicate an attack that sets the target stat to a percentage of its current value.</description>
+		</command>
 	</section>
-</plotscript>
+</plotscript>
\ No newline at end of file
Index: plotscr.hsd
===================================================================
--- plotscr.hsd	(revision 191)
+++ plotscr.hsd	(working copy)
@@ -535,6 +535,22 @@
 524,getdoordestinationmap,1,0    #map number of given door's exit
 525,doorexists,1,0               #returns true if the given door exists
 526,getattackcaption,2,0,0       #puts an attack's caption in a string (string id, attack id+1 / attack .hsi constant)
+527,enemyelementalresistasint,2,-1,0 # percentage damage taken from an element rounded to an int (enemy, element)
+528,readattacktargetclass,1,0    #returns the target class (ally, enemy, etc.) of the given attack
+529,readattacktargetsetting,1,0  #returns the target setting (focused, spread, etc.) of the given attack
+530,readattackdamageequation,1,0 #returns the damage equation (normal, sharp, etc.) of the given attack
+531,readattackextradamage,1,0    #returns the extra damage modifier of the given attack
+532,readattackitem,2,0,0         #returns item ID+1 of the given attack's nth item cost (attack, n [0..2])
+533,readattackitemquantity,2,0,0 #returns item quantity of the given attack's nth item cost (attack, n [0..2])
+534,readattackchain,2,0,0        #returns attack ID+1 of the given attack's chain (attack)
+535,readattackchainrate,2,0,0    #returns chain rate of the given attack's chain (attack)
+536,readattackelsechain,2,0,0    #returns attack ID+1 of the given attack's else chain (attack)
+537,readattackelsechainrate,2,0,0#returns chain rate of the given attack's else chain (attack)
+538,readattackinsteadchain,2,0,0     #returns attack ID+1 of the given attack's chain (attack)
+539,readattackinsteadchainrate,2,0,0 #returns chain rate of the given attack's chain (attack)
+540,readenemynormalattack,2,0,0  #returns the nth attack ID+1 of given enemy's normal attack set (id, n [0..4])
+541,readenemyaloneattack,2,0,0   #returns the nth attack ID+1 of given enemy's alone attack set (id, n [0..4])
+542,readenemydesperationattack,2,0,0 #returns the nth attack ID+1 of given enemy's desperation attack set (id, n [0..4])
 end
 
 #--------------------------------------------------------------------------
@@ -1583,6 +1599,31 @@
 0,trans:solid
 1,trans:fuzzy
 2,trans:hollow
+0,targetclass:enemy
+1,targetclass:ally
+2,targetclass:self
+3,targetclass:all
+4,targetclass:ally including dead
+5,targetclass:ally excluding self
+6,targetclass:revenge
+7,targetclass:revenge whole battle
+8,targetclass:previous target
+9,targetclass:recorded target
+10,targetclass:dead allies
+11,targetclass:thankvenge
+12,targetclass:thankvenge whole battle
+0,targetsetting:focused
+1,targetsetting:spread
+2,targetsetting:optional spread
+3,targetsetting:random
+4,targetsetting:first target
+0,damageequation:normal
+1,damageequation:blunt
+2,damageequation:sharp
+3,damageequation:pure damage
+4,damageequation:no damage
+5,damageequation:percent of max
+6,damageequation:percent of current
 end
 
 #<SLICE LOOKUP CODES>
Index: yetmore.bas
===================================================================
--- yetmore.bas	(revision 191)
+++ yetmore.bas	(working copy)
@@ -2914,7 +2914,103 @@
  IF valid_plotstr(retvals(0), 5) AND bound_arg(retvals(1), 1, gen(genMaxAttack)+1, "attack ID", , , 5) THEN
    plotstr(retvals(0)).s = readattackcaption(retvals(1) - 1)
    scriptret = 1
+ END IF
+ CASE 527 '--enemy elemental resist as int
+  IF in_bound(retvals(0), 0, gen(genMaxEnemy)) AND bound_arg(retvals(1), 0, gen(genNumElements) - 1, "element number") THEN
+   DIM enemy as EnemyDef
+   loadenemydata enemy, retvals(0)
+   scriptret = 100 * enemy.elementals(retvals(1))
   END IF
+ CASE 528 '--read attack target class
+  IF bound_arg(retvals(0), 1, gen(genMaxAttack)+1, "attack ID", , , 5) THEN
+   DIM attack as AttackData
+   loadattackdata attack, retvals(0)
+   scriptret = attack.targ_class
+  END IF
+ CASE 529 '--read attack target setting
+  IF bound_arg(retvals(0), 1, gen(genMaxAttack)+1, "attack ID", , , 5) THEN
+   DIM attack as AttackData
+   loadattackdata attack, retvals(0)
+   scriptret = attack.targ_set
+  END IF
+ CASE 530 '--read attack damage equation
+  IF bound_arg(retvals(0), 1, gen(genMaxAttack)+1, "attack ID", , , 5) THEN
+   DIM attack as AttackData
+   loadattackdata attack, retvals(0)
+   scriptret = attack.damage_math
+  END IF
+ CASE 531 '--read attack extra damage
+  IF bound_arg(retvals(0), 1, gen(genMaxAttack)+1, "attack ID", , , 5) THEN
+   DIM attack as AttackData
+   loadattackdata attack, retvals(0)
+   scriptret = attack.extra_damage
+  END IF
+ CASE 532 '--read attack item
+  IF bound_arg(retvals(0), 1, gen(genMaxAttack)+1, "attack ID", , , 5) AND in_bound(retvals(1), 0, 2) THEN
+   DIM attack as AttackData
+   loadattackdata attack, retvals(0)
+   scriptret = attack.item(retvals(1)).id
+  END IF
+ CASE 533 '--read attack item quantity
+  IF bound_arg(retvals(0), 1, gen(genMaxAttack)+1, "attack ID", , , 5) AND in_bound(retvals(1), 0, 2) THEN
+   DIM attack as AttackData
+   loadattackdata attack, retvals(0)
+   scriptret = attack.item(retvals(1)).number
+  END IF
+ CASE 534 '--read attack chain
+  IF bound_arg(retvals(0), 1, gen(genMaxAttack)+1, "attack ID", , , 5) THEN
+   DIM attack as AttackData
+   loadattackdata attack, retvals(0)
+   scriptret = attack.chain.atk_id
+  END IF
+ CASE 535 '--read attack chain rate
+  IF bound_arg(retvals(0), 1, gen(genMaxAttack)+1, "attack ID", , , 5) THEN
+   DIM attack as AttackData
+   loadattackdata attack, retvals(0)
+   scriptret = attack.chain.rate
+  END IF
+ CASE 536 '--read attack else chain
+  IF bound_arg(retvals(0), 1, gen(genMaxAttack)+1, "attack ID", , , 5) THEN
+   DIM attack as AttackData
+   loadattackdata attack, retvals(0)
+   scriptret = attack.elsechain.atk_id
+  END IF
+ CASE 537 '--read attack else chain rate
+  IF bound_arg(retvals(0), 1, gen(genMaxAttack)+1, "attack ID", , , 5) THEN
+   DIM attack as AttackData
+   loadattackdata attack, retvals(0)
+   scriptret = attack.elsechain.rate
+  END IF
+ CASE 538 '--read attack instead chain
+  IF bound_arg(retvals(0), 1, gen(genMaxAttack)+1, "attack ID", , , 5) THEN
+   DIM attack as AttackData
+   loadattackdata attack, retvals(0)
+   scriptret = attack.instead.atk_id
+  END IF
+ CASE 539 '--read attack instead chain rate
+  IF bound_arg(retvals(0), 1, gen(genMaxAttack)+1, "attack ID", , , 5) THEN
+   DIM attack as AttackData
+   loadattackdata attack, retvals(0)
+   scriptret = attack.instead.rate
+  END IF
+ CASE 540 '--read enemy normal attack
+  IF in_bound(retvals(0), 0, gen(genMaxEnemy)) AND in_bound(retvals(1), 0, 4) THEN
+   DIM enemy as EnemyDef
+   loadenemydata enemy, retvals(0)
+   scriptret = enemy.regular_ai(retvals(1))
+  END IF
+ CASE 541 '--read enemy alone attack
+  IF in_bound(retvals(0), 0, gen(genMaxEnemy)) AND in_bound(retvals(1), 0, 4) THEN
+   DIM enemy as EnemyDef
+   loadenemydata enemy, retvals(0)
+   scriptret = enemy.alone_ai(retvals(1))
+  END IF
+ CASE 542 '--read enemy desperation attack
+  IF in_bound(retvals(0), 0, gen(genMaxEnemy)) AND in_bound(retvals(1), 0, 4) THEN
+   DIM enemy as EnemyDef
+   loadenemydata enemy, retvals(0)
+   scriptret = enemy.desperation_ai(retvals(1))
+  END IF
 END SELECT
 
 END SUB
