Explorar el Código

* Added support for skill names to script commands:
- skill, addtoskill, guildskill, getskilllv, getgdskilllv, itemskill, petskillattack, petskillattack2, petskillsupport, skilleffect, npcskilleffect, unitskilluseid, unitskillusepos
- bonus/bonus2/bonus3/bonus4/bonus5 for bonuses bAutoSpell, bSkillAtk, bSkillHeal, bAutoSpellWhenHit, bAddSkillBlow, bCastrate

git-svn-id: https://svn.code.sf.net/p/rathena/svn/trunk@12814 54d463be-8e91-2dee-dedb-b68131a5f0ec

FlavioJS hace 17 años
padre
commit
625f9f62fd
Se han modificado 7 ficheros con 176 adiciones y 90 borrados
  1. 7 0
      Changelog-Trunk.txt
  2. 18 14
      doc/item_bonus.txt
  3. 23 5
      doc/script_commands.txt
  4. 1 0
      src/common/db.h
  5. 106 67
      src/map/script.c
  6. 19 4
      src/map/skill.c
  7. 2 0
      src/map/skill.h

+ 7 - 0
Changelog-Trunk.txt

@@ -4,6 +4,13 @@ AS OF SVN REV. 5091, WE ARE NOW USING TRUNK.  ALL UNTESTED BUGFIXES/FEATURES GO
 IF YOU HAVE A WORKING AND TESTED BUGFIX PUT IT INTO STABLE AS WELL AS TRUNK.
 
 
+2008/06/12
+	* Added support for skill names to script commands: [FlavioJS]
+	- skill, addtoskill, guildskill, getskilllv, getgdskilllv, itemskill, 
+	  petskillattack, petskillattack2, petskillsupport, skilleffect, 
+	  npcskilleffect, unitskilluseid, unitskillusepos
+	- bonus/bonus2/bonus3/bonus4/bonus5 for bonuses bAutoSpell, bSkillAtk, 
+	  bSkillHeal, bAutoSpellWhenHit, bAddSkillBlow, bCastrate
 2008/06/11
 	* Added partylock/guildlock checking for @changeleader/@changegm
 	  (bugreport:72) [ultramage]

+ 18 - 14
doc/item_bonus.txt

@@ -3,16 +3,20 @@
 //===== By ================================================
 //= Developers
 //===== Version ===========================================
-//= 1.0
+//= 1.1.20080612
 //=========================================================
 //= 1.0 - Standardized doc file
+//= 1.1.20080612 - skill command and bonuses (bAutoSpell, bSkillAtk, 
+//=   bSkillHeal, bAutoSpellWhenHit, bAddSkillBlow, bCastrate) accept 
+//=   skill names [FlavioJS]
+//= 
 //===== Description =======================================
 //= List of script instructions used in item bonuses,
 //= mainly bonus/bonus2/bonus3/bonus4/bonus5 arguments
 //=========================================================
 
 
-skill i,n;				Gives skill #i at level n
+skill i,n;				Gives skill #i at level n (supports skill names)
 
 bonus bStr,n;				STR + n
 bonus bAgi,n;				AGI + n
@@ -114,7 +118,7 @@ bonus2 bAddEff,e,x;			Adds a x/10000 chance to cause effect e to the target when
 							e: Eff_Blind, Eff_Sleep, Eff_Poison, Eff_Freeze, Eff_Silence, Eff_Stan, Eff_Curse, Eff_Confusion, Eff_Stone, Eff_Bleeding
 bonus2 bResEff,e,x;			Adds a x/10000 tolerance to effect e (e.g. x=100 makes 1% tolerance, x=10000 makes 100% tolerance, etc)
 							e: Eff_Blind, Eff_Sleep, Eff_Poison, Eff_Freeze, Eff_Silence, Eff_Stan, Eff_Curse, Eff_Confusion, Eff_Stone, Eff_Bleeding
-bonus2 bCastrate,n,x;			Adjust casting time of skill n by x%
+bonus2 bCastrate,n,x;			Adjust casting time of skill n by x% (supports skill names)
 bonus2 bAddSize,n,x;			+x% physical damage against size n.
 							n: 0=Small  1=Medium  2=Large
 bonus2 bMagicAddSize,n,x;		+x% magical damage against size n.
@@ -168,7 +172,7 @@ bonus3 bAddMonsterDropItem,n,x,y;	When killing monsters from race x with physica
 									10=Boss monster, 11=Other than (normal monster) boss monster
 									if 'x' is negative value, then it's a part of formula
 										chance = -x*(killed_mob_level/10)+1
-bonus3 bAutoSpell,n,x,y;		Auto Spell casting on attack of spell n at level x with y/10% chance.
+bonus3 bAutoSpell,n,x,y;		Auto Spell casting on attack of spell n at level x with y/10% chance. (supports skill names)
 								Skill is casted on target unless it is a self or support (inf = 4/16) skill.
 
 // bAddDamageClass, bAddMagicDamageClass and bAddMonsterDropItem it is setting possible up to 10. Those which exceed 10 are ignored.
@@ -198,15 +202,16 @@ bonus2 bCriticalAddRace,n,r;		Critical + n vs. enemies of race r
 bonus2 bHPRegenRate,n,x;		Gain n HP every x milliseconds
 bonus2 bHPLossRate,n,x;			Lose n HP every x milliseconds
 bonus2 bAddEffWhenHit,n,x;		x/100% chance to cause n state to the enemy when being hit by physical damage
-bonus2 bSkillAtk,n,x;			Increase damage of skill n by x%
-bonus2 bSkillHeal,n,x;			Increase heal amount of skill n by x%
+bonus2 bSkillAtk,n,x;			Increase damage of skill n by x% (supports skill names)
+bonus2 bSkillHeal,n,x;			Increase heal amount of skill n by x% (supports skill names)
 bonus2 bAddDamageByClass,n,x;		When being hit by monster of class n increase damage by x%
 bonus2 bAddRace2,n,x;			Increase damage by x% vs. enemies of race n
 							(Check db/mob_race2_db.txt)
 							y: 0=Don't show damage 1=Show damage
 bonus3 bAutoSpellWhenHit,x,y,n;		n/10% chance to cast skill x of level y on
 								attacker (unless it is a self or support skill) when being hit by a
-								direct attack. Target must be within spell's range to go off.
+								direct attack. (supports skill names)
+								Target must be within spell's range to go off.
 bonus3 bSPDrainRate,n,x,y;		When attacking there is a n% chance to either gain SP equivalent to x% of damage dealt,
 							OR drain the amount of sp from the enemy.
 							y: 0=gain sp  1:drain enemy sp
@@ -214,20 +219,20 @@ bonus3 bSPDrainValue,n,x,y;		When attacking there is a n% chance to either gain
 							OR drain the amount of sp from the enemy.
 							y:0=gain sp  1:drain enemy sp
 							(Note: setting x to -1 or below will reduce YOUR sp)
-bonus4 bAutoSpell,x,y,n,i;		n/10% chance to cast skill x of level y when attacking
+bonus4 bAutoSpell,x,y,n,i;		n/10% chance to cast skill x of level y when attacking (supports skill names)
 							i:
 								0=cast on self
 								1=cast on enemy, not on self
 								2=use random skill lv in [1..y]
 								3=1+2 (random lv on enemy)
-bonus4 bAutoSpellWhenHit,x,y,n,i;	n/10% chance to cast skill x of level y when being hit by a direct attack. 
+bonus4 bAutoSpellWhenHit,x,y,n,i;	n/10% chance to cast skill x of level y when being hit by a direct attack. (supports skill names)
 									Target must be within spell's range to go off.
 								i:
 									0=cast on self
 									1=cast on enemy, not on self
 									2=use random skill lv in [1..y]
 									3=1+2 (random lv on enemy)
-bonus5 bAutoSpell,x,y,n,t,i;		n/10% chance to cast skill x of level y when attacking
+bonus5 bAutoSpell,x,y,n,t,i;		n/10% chance to cast skill x of level y when attacking (supports skill names)
 					t: Trigger criteria:
 					   BF_SHORT: Trigger on melee attack
 					   BF_LONG: Trigger on ranged attack
@@ -249,9 +254,8 @@ bonus5 bAutoSpell,x,y,n,t,i;		n/10% chance to cast skill x of level y when attac
 					   2=use random skill lv in [1..y]
 					   3=1+2 (random lv on enemy)
 					   
-bonus5 bAutoSpellWhenHit,x,y,n,t,i;	n/10% chance to cast skill x of level y when being hit by a direct attack. 
-                    Target must be within spell's range to go
-					off.
+bonus5 bAutoSpellWhenHit,x,y,n,t,i;	n/10% chance to cast skill x of level y when being hit by a direct attack. (supports skill names)
+                    Target must be within spell's range to go off.
 					t: Trigger criteria:
 					   BF_SHORT: Trigger on melee attack
 					   BF_LONG: Trigger on ranged attack
@@ -324,4 +328,4 @@ bonus2 bWeaponComaRace,x,y;		y/100% chance to cause Coma when attacking a monste
 
 bAddStealRate,n;			n/100% increase to Steal skill success chance
 
-bonus2 bAddSkillBlow,x,y;	Pushback the target by y cells when using skill x
+bonus2 bAddSkillBlow,x,y;	Pushback the target by y cells when using skill x (supports skill names)

+ 23 - 5
doc/script_commands.txt

@@ -4,7 +4,7 @@
 //= A reference manual for the eAthena scripting language.
 //= Commands are sorted depending on their functionality.
 //===== Version ===========================================
-//= 3.19.20080407
+//= 3.21.20080612
 //=========================================================
 //= 1.0 - First release, filled will as much info as I could
 //=       remember or figure out, most likely there are errors,
@@ -111,8 +111,13 @@
 //= 3.19.20080407
 //=       Extended the behaviour of 'guardian'. [FlavioJS]
 //= 3.20.20080425
-//=	      Corrected 'getitem', 'getitem2' & 'delitem2' (charid instead of accountid) [Toms]
-//=	      Modified 'delitem' (added optional accountid parameter) [Toms]
+//=       Corrected 'getitem', 'getitem2' & 'delitem2' (charid instead of accountid) [Toms]
+//=       Modified 'delitem' (added optional accountid parameter) [Toms]
+//= 3.21.20080612
+//=       Script commands extended to support skill names: [FlavioJS]
+//=       skill, addtoskill, guildskill, getskilllv, getgdskilllv, itemskill, 
+//=       petskillattack, petskillattack2, petskillsupport, skilleffect, npcskilleffect,
+//=       unitskilluseid, unitskillusepos, bonus/bonus2/bonus3/bonus4/bonus5
 //=========================================================
 
 This document is a reference manual for all the scripting commands and functions 
@@ -2734,6 +2739,7 @@ anything, obviously.
 ---------------------------------------
 
 *getgdskilllv(<guild id>,<skill id>)
+*getgdskilllv(<guild id>,"<skill name>")
 
 This function returns the level of the skill <skill id> of the guild <guild id>.
 If the guild does not have that skill, 0 is returned.
@@ -2769,6 +2775,7 @@ Example(s):
 ---------------------------------------
 
 *getskilllv(<skill id>)
+*getskilllv("<skill name>")
 
 This function returns the level of the specified skill that the invoking 
 character has. If they don't have the skill, 0 will be returned. The full list 
@@ -3936,6 +3943,7 @@ effect is still in effect).
 ---------------------------------------
 
 *itemskill <skill id>,<skill level>;
+*itemskill "<skill name>",<skill level>;
 
 This is a command meant for item scripts to replicate single-use skills. It will 
 not work properly in NPC scripts a lot of the time because casting a skill is 
@@ -4132,6 +4140,7 @@ any guild.
 ---------------------------------------
 
 *guildskill <skill id>,<level>
+*guildskill "<skill name>",<level>
 
 This command will bump up the specified guild skill by the specified number of 
 levels. This refers to the invoking character and will only work if the invoking 
@@ -4256,6 +4265,7 @@ should be rather obvious.
 ---------------------------------------
 
 *skilleffect <skill id>,<number>;
+*skilleffect "<skill name>",<number>;
 
 This command will display the visual and sound effects of a specified skill (see 
 'db/skill_db.txt' for a full list of skills) on the invoking character's sprite. 
@@ -4278,6 +4288,7 @@ effect displays a floating number, the number given will float up.
 ---------------------------------------
 
 *npcskilleffect <skill id>,<number>,<x>,<y>;
+*npcskilleffect "<skill name>",<number>,<x>,<y>;
 
 This command behaves identically to 'skilleffect', however, the effect will not 
 be centered on the invoking character's sprite, nor on the NPC sprite, if any, 
@@ -4383,7 +4394,9 @@ autoscript).
 ---------------------------------------
 
 *skill <skill id>,<level>{,<flag>};
-*addtoskill <skill id>,<level>{,<flag>}
+*skill "<skill name",<level>{,<flag>};
+*addtoskill <skill id>,<level>{,<flag>};
+*addtoskill "<skill name>",<level>{,<flag>};
 
 These commands will give the invoking character a specified skill. This is also 
 used for item scripts.
@@ -5830,8 +5843,10 @@ Example(s):
 
 ---------------------------------------
 
-*unitskilluseid <GID>,<skill id>,<skill lvl>;
+*unitskilluseid <GID>,<skill id>,<skill lvl>{,<target id>};
+*unitskilluseid <GID>,"<skill name>",<skill lvl>{,<target id>};
 *unitskillusepos <GID>,<skill id>,<skill lvl>,<x>,<y>;
+*unitskillusepos <GID>,"<skill name>",<skill lvl>,<x>,<y>;
 
 This is the replacement of the older commands, these use the same values for
 GID as the other unit* commands (See 'GID').
@@ -6064,6 +6079,7 @@ specified. Pet will store items and return them when the maximum is reached or
 when pet performance is activated.
 
 *petskillsupport <skill id>,<skill level>,<delay>,<percent hp>,<percent sp>;
+*petskillsupport "<skill name>",<skill level>,<delay>,<percent hp>,<percent sp>;
 *petheal <level>,<delay>,<percent hp>,<percent sp>;
 
 This will make the pet use a specified support skill on the owner whenever the 
@@ -6075,7 +6091,9 @@ It's not quite certain who's stats will be used for the skills cast, the
 character's or the pets. Probably, Skotlex can answer that question.
 
 *petskillattack <skill id>,<skill level>,<rate>,<bonusrate>;
+*petskillattack "<skill name>",<skill level>,<rate>,<bonusrate>;
 *petskillattack2 <skill id>,<damage>,<number of attacks>,<rate>,<bonusrate>;
+*petskillattack2 "<skill name>",<damage>,<number of attacks>,<rate>,<bonusrate>;
 
 These two commands will make the pet cast an attack skill on the enemy the pet's 
 owner is currently fighting. Skill IDs and levels are as per 'petskillsupport'. 

+ 1 - 0
src/common/db.h

@@ -609,6 +609,7 @@ struct DBMap {
 #define stridb_alloc(opt,maxlen)  db_alloc(__FILE__,__LINE__,DB_ISTRING,(opt),(maxlen))
 #define db_destroy(db)            ( (db)->destroy((db),NULL) )
 // Other macros
+#define db_clear(db)        ( (db)->clear(db,NULL) )
 #define db_iterator(db)     ( (db)->iterator(db) )
 #define dbi_first(dbi)      ( (dbi)->first(dbi,NULL) )
 #define dbi_last(dbi)       ( (dbi)->last(dbi,NULL) )

+ 106 - 67
src/map/script.c

@@ -90,6 +90,9 @@
 /// Pushes a copy of the data in the target index
 #define script_pushcopy(st,i) push_copy((st)->stack, (st)->start + (i))
 
+#define script_isstring(st,i) data_isstring(script_getdata(st,i))
+#define script_isint(st,i) data_isint(script_getdata(st,i))
+
 #define script_getnum(st,val) conv_num(st, script_getdata(st,val))
 #define script_getstr(st,val) conv_str(st, script_getdata(st,val))
 #define script_getref(st,val) ( script_getdata(st,val)->ref )
@@ -6581,11 +6584,11 @@ BUILDIN_FUNC(statusup2)
 BUILDIN_FUNC(bonus)
 {
 	int type;
-	int type2;
-	int type3;
-	int type4;
-	int type5;
-	int val;
+	int val1;
+	int val2 = 0;
+	int val3 = 0;
+	int val4 = 0;
+	int val5 = 0;
 	TBL_PC* sd;
 
 	sd = script_rid2sd(st);
@@ -6593,39 +6596,52 @@ BUILDIN_FUNC(bonus)
 		return 0; // no player attached
 
 	type = script_getnum(st,2);
-	switch( script_lastdata(st) ){
+	switch( type )
+	{
+	case SP_AUTOSPELL:
+	case SP_AUTOSPELL_WHENHIT:
+	case SP_SKILL_ATK:
+	case SP_SKILL_HEAL:
+	case SP_ADD_SKILL_BLOW:
+	case SP_CASTRATE:
+		// these bonuses support skill names
+		val1 = ( script_isstring(st,3) ? skill_name2id(script_getstr(st,3)) : script_getnum(st,3) );
+		break;
+	default:
+		val1 = script_getnum(st,3);
+		break;
+	}
+
+	switch( script_lastdata(st)-2 )
+	{
+	case 1:
+		pc_bonus(sd, type, val1);
+		break;
+	case 2:	
+		val2 = script_getnum(st,4);
+		pc_bonus2(sd, type, val1, val2);
+		break;
 	case 3:
-		val  = script_getnum(st,3);
-		pc_bonus(sd, type, val);
+		val2 = script_getnum(st,4);
+		val3 = script_getnum(st,5);
+		pc_bonus3(sd, type, val1, val2, val3);
 		break;
 	case 4:
-		type2 = script_getnum(st,3);
-		val   = script_getnum(st,4);
-		pc_bonus2(sd, type, type2, val);
+		val2 = script_getnum(st,4);
+		val3 = script_getnum(st,5);
+		val4 = script_getnum(st,6);
+		pc_bonus4(sd, type, val1, val2, val3, val4);
 		break;
 	case 5:
-		type2 = script_getnum(st,3);
-		type3 = script_getnum(st,4);
-		val   = script_getnum(st,5);
-		pc_bonus3(sd, type, type2, type3, val);
-		break;
-	case 6:
-		type2 = script_getnum(st,3);
-		type3 = script_getnum(st,4);
-		type4 = script_getnum(st,5);
-		val   = script_getnum(st,6);
-		pc_bonus4(sd, type, type2, type3, type4, val);
-		break;
-	case 7:
-		type2 = script_getnum(st,3);
-		type3 = script_getnum(st,4);
-		type4 = script_getnum(st,5);
-		type5 = script_getnum(st,6);
-		val   = script_getnum(st,7);
-		pc_bonus5(sd, type, type2, type3, type4, type5, val);
+		val2 = script_getnum(st,4);
+		val3 = script_getnum(st,5);
+		val4 = script_getnum(st,6);
+		val5 = script_getnum(st,7);
+		pc_bonus5(sd, type, val1, val2, val3, val4, val5);
 		break;
 	default:
-		ShowDebug("buildin_bonus: unexpected number of arguments (%d)\n", (script_lastdata(st) - 2));
+		ShowDebug("buildin_bonus: unexpected number of arguments (%d)\n", (script_lastdata(st) - 1));
+		break;
 	}
 
 	return 0;
@@ -6692,6 +6708,8 @@ BUILDIN_FUNC(bonusautoscript2)
 ///
 /// skill <skill id>,<level>,<flag>
 /// skill <skill id>,<level>
+/// skill "<skill name>",<level>,<flag>
+/// skill "<skill name>",<level>
 BUILDIN_FUNC(skill)
 {
 	int id;
@@ -6703,7 +6721,7 @@ BUILDIN_FUNC(skill)
 	if( sd == NULL )
 		return 0;// no player attached, report source
 
-	id    = script_getnum(st,2);
+	id = ( script_isstring(st,2) ? skill_name2id(script_getstr(st,2)) : script_getnum(st,2) );
 	level = script_getnum(st,3);
 	if( script_hasdata(st,4) )
 		flag = script_getnum(st,4);
@@ -6717,6 +6735,8 @@ BUILDIN_FUNC(skill)
 ///
 /// addtoskill <skill id>,<amount>,<flag>
 /// addtoskill <skill id>,<amount>
+/// addtoskill "<skill name>",<amount>,<flag>
+/// addtoskill "<skill name>",<amount>
 ///
 /// @see skill
 BUILDIN_FUNC(addtoskill)
@@ -6730,7 +6750,7 @@ BUILDIN_FUNC(addtoskill)
 	if( sd == NULL )
 		return 0;// no player attached, report source
 
-	id    = script_getnum(st,2);
+	id = ( script_isstring(st,2) ? skill_name2id(script_getstr(st,2)) : script_getnum(st,2) );
 	level = script_getnum(st,3);
 	if( script_hasdata(st,4) )
 		flag = script_getnum(st,4);
@@ -6742,6 +6762,7 @@ BUILDIN_FUNC(addtoskill)
 /// Increases the level of a guild skill.
 ///
 /// guildskill <skill id>,<amount>;
+/// guildskill "<skill name>",<amount>;
 BUILDIN_FUNC(guildskill)
 {
 	int id;
@@ -6753,7 +6774,7 @@ BUILDIN_FUNC(guildskill)
 	if( sd == NULL )
 		return 0;// no player attached, report source
 
-	id    = script_getnum(st,2);
+	id = ( script_isstring(st,2) ? skill_name2id(script_getstr(st,2)) : script_getnum(st,2) );
 	level = script_getnum(st,3);
 	for( i=0; i < level; i++ )
 		guild_skillup(sd, id);
@@ -6764,6 +6785,7 @@ BUILDIN_FUNC(guildskill)
 /// Returns the level of the player skill.
 ///
 /// getskilllv(<skill id>) -> <level>
+/// getskilllv("<skill name>") -> <level>
 BUILDIN_FUNC(getskilllv)
 {
 	int id;
@@ -6773,7 +6795,7 @@ BUILDIN_FUNC(getskilllv)
 	if( sd == NULL )
 		return 0;// no player attached, report source
 
-	id = script_getnum(st,2);
+	id = ( script_isstring(st,2) ? skill_name2id(script_getstr(st,2)) : script_getnum(st,2) );
 	script_pushint(st, pc_checkskill(sd,id));
 
 	return 0;
@@ -6782,6 +6804,7 @@ BUILDIN_FUNC(getskilllv)
 /// Returns the level of the guild skill.
 ///
 /// getgdskilllv(<guild id>,<skill id>) -> <level>
+/// getgdskilllv(<guild id>,"<skill name>") -> <level>
 BUILDIN_FUNC(getgdskilllv)
 {
 	int guild_id;
@@ -6789,7 +6812,7 @@ BUILDIN_FUNC(getgdskilllv)
 	struct guild* g;
 
 	guild_id = script_getnum(st,2);
-	skill_id = script_getnum(st,3);
+	skill_id = ( script_isstring(st,3) ? skill_name2id(script_getstr(st,3)) : script_getnum(st,3) );
 	g = guild_search(guild_id);
 	if( g == NULL )
 		script_pushint(st, -1);
@@ -7225,17 +7248,21 @@ BUILDIN_FUNC(guildopenstorage)
 /*==========================================
  * アイテムによるスキル発動
  *------------------------------------------*/
+/// itemskill <skill id>,<level>
+/// itemskill "<skill name>",<level>
 BUILDIN_FUNC(itemskill)
 {
-	int id,lv;
-	TBL_PC *sd=script_rid2sd(st);
-
-	id=script_getnum(st,2);
-	lv=script_getnum(st,3);
+	int id;
+	int lv;
+	TBL_PC* sd;
 
-	if(!sd || sd->ud.skilltimer != -1)
+	sd = script_rid2sd(st);
+	if( sd == NULL || sd->ud.skilltimer != INVALID_TIMER )
 		return 0;
 
+	id = ( script_isstring(st,2) ? skill_name2id(script_getstr(st,2)) : script_getnum(st,2) );
+	lv = script_getnum(st,3);
+
 	sd->skillitem=id;
 	sd->skillitemlv=lv;
 	clif_item_skill(sd,id,lv);
@@ -10489,6 +10516,8 @@ BUILDIN_FUNC(petheal)
 /*==========================================
  * pet attack skills [Valaris] //Rewritten by [Skotlex]
  *------------------------------------------*/
+/// petskillattack <skill id>,<level>,<rate>,<bonusrate>
+/// petskillattack "<skill name>",<level>,<rate>,<bonusrate>
 BUILDIN_FUNC(petskillattack)
 {
 	struct pet_data *pd;
@@ -10501,7 +10530,7 @@ BUILDIN_FUNC(petskillattack)
 	if (pd->a_skill == NULL)
 		pd->a_skill = (struct pet_skill_attack *)aMalloc(sizeof(struct pet_skill_attack));
 				
-	pd->a_skill->id=script_getnum(st,2);
+	pd->a_skill->id=( script_isstring(st,2) ? skill_name2id(script_getstr(st,2)) : script_getnum(st,2) );
 	pd->a_skill->lv=script_getnum(st,3);
 	pd->a_skill->div_ = 0;
 	pd->a_skill->rate=script_getnum(st,4);
@@ -10513,6 +10542,8 @@ BUILDIN_FUNC(petskillattack)
 /*==========================================
  * pet attack skills [Valaris]
  *------------------------------------------*/
+/// petskillattack2 <skill id>,<level>,<div>,<rate>,<bonusrate>
+/// petskillattack2 "<skill name>",<level>,<div>,<rate>,<bonusrate>
 BUILDIN_FUNC(petskillattack2)
 {
 	struct pet_data *pd;
@@ -10525,7 +10556,7 @@ BUILDIN_FUNC(petskillattack2)
 	if (pd->a_skill == NULL)
 		pd->a_skill = (struct pet_skill_attack *)aMalloc(sizeof(struct pet_skill_attack));
 				
-	pd->a_skill->id=script_getnum(st,2);
+	pd->a_skill->id=( script_isstring(st,2) ? skill_name2id(script_getstr(st,2)) : script_getnum(st,2) );
 	pd->a_skill->lv=script_getnum(st,3);
 	pd->a_skill->div_ = script_getnum(st,4);
 	pd->a_skill->rate=script_getnum(st,5);
@@ -10537,6 +10568,8 @@ BUILDIN_FUNC(petskillattack2)
 /*==========================================
  * pet support skills [Skotlex]
  *------------------------------------------*/
+/// petskillsupport <skill id>,<level>,<delay>,<hp>,<sp>
+/// petskillsupport "<skill name>",<level>,<delay>,<hp>,<sp>
 BUILDIN_FUNC(petskillsupport)
 {
 	struct pet_data *pd;
@@ -10558,7 +10591,7 @@ BUILDIN_FUNC(petskillsupport)
 	} else //init memory
 		pd->s_skill = (struct pet_skill_support *) aMalloc(sizeof(struct pet_skill_support)); 
 	
-	pd->s_skill->id=script_getnum(st,2);
+	pd->s_skill->id=( script_isstring(st,2) ? skill_name2id(script_getstr(st,2)) : script_getnum(st,2) );
 	pd->s_skill->lv=script_getnum(st,3);
 	pd->s_skill->delay=script_getnum(st,4);
 	pd->s_skill->hp=script_getnum(st,5);
@@ -10576,11 +10609,13 @@ BUILDIN_FUNC(petskillsupport)
 /*==========================================
  * Scripted skill effects [Celest]
  *------------------------------------------*/
+/// skilleffect <skill id>,<level>
+/// skilleffect "<skill name>",<level>
 BUILDIN_FUNC(skilleffect)
 {
 	TBL_PC *sd;
 
-	int skillid=script_getnum(st,2);
+	int skillid=( script_isstring(st,2) ? skill_name2id(script_getstr(st,2)) : script_getnum(st,2) );
 	int skilllv=script_getnum(st,3);
 	sd=script_rid2sd(st);
 
@@ -10592,11 +10627,13 @@ BUILDIN_FUNC(skilleffect)
 /*==========================================
  * NPC skill effects [Valaris]
  *------------------------------------------*/
+/// npcskilleffect <skill id>,<level>,<x>,<y>
+/// npcskilleffect "<skill name>",<level>,<x>,<y>
 BUILDIN_FUNC(npcskilleffect)
 {
 	struct block_list *bl= map_id2bl(st->oid);
 
-	int skillid=script_getnum(st,2);
+	int skillid=( script_isstring(st,2) ? skill_name2id(script_getstr(st,2)) : script_getnum(st,2) );
 	int skilllv=script_getnum(st,3);
 	int x=script_getnum(st,4);
 	int y=script_getnum(st,5);
@@ -12871,6 +12908,7 @@ BUILDIN_FUNC(unitemote)
 /// Makes the unit cast the skill on the target or self if no target is specified
 ///
 /// unitskilluseid <unit_id>,<skill_id>,<skill_lv>{,<target_id>};
+/// unitskilluseid <unit_id>,"<skill name>",<skill_lv>{,<target_id>};
 BUILDIN_FUNC(unitskilluseid)
 {
 	int unit_id;
@@ -12880,7 +12918,7 @@ BUILDIN_FUNC(unitskilluseid)
 	struct block_list* bl;
 
 	unit_id  = script_getnum(st,2);
-	skill_id = script_getnum(st,3);
+	skill_id = ( script_isstring(st,3) ? skill_name2id(script_getstr(st,3)) : script_getnum(st,3) );
 	skill_lv = script_getnum(st,4);
 	target_id = ( script_hasdata(st,5) ? script_getnum(st,5) : unit_id );
 
@@ -12894,6 +12932,7 @@ BUILDIN_FUNC(unitskilluseid)
 /// Makes the unit cast the skill on the target position.
 ///
 /// unitskillusepos <unit_id>,<skill_id>,<skill_lv>,<target_x>,<target_y>;
+/// unitskillusepos <unit_id>,"<skill name>",<skill_lv>,<target_x>,<target_y>;
 BUILDIN_FUNC(unitskillusepos)
 {
 	int unit_id;
@@ -12904,7 +12943,7 @@ BUILDIN_FUNC(unitskillusepos)
 	struct block_list* bl;
 
 	unit_id  = script_getnum(st,2);
-	skill_id = script_getnum(st,3);
+	skill_id = ( script_isstring(st,3) ? skill_name2id(script_getstr(st,3)) : script_getnum(st,3) );
 	skill_lv = script_getnum(st,4);
 	skill_x  = script_getnum(st,5);
 	skill_y  = script_getnum(st,6);
@@ -13344,18 +13383,18 @@ struct script_function buildin_func[] = {
 	BUILDIN_DEF(failedrefitem,"i"),
 	BUILDIN_DEF(statusup,"i"),
 	BUILDIN_DEF(statusup2,"ii"),
-	BUILDIN_DEF(bonus,"ii"),
-	BUILDIN_DEF2(bonus,"bonus2","iii"),
-	BUILDIN_DEF2(bonus,"bonus3","iiii"),
-	BUILDIN_DEF2(bonus,"bonus4","iiiii"),
-	BUILDIN_DEF2(bonus,"bonus5","iiiiii"),
+	BUILDIN_DEF(bonus,"iv"),
+	BUILDIN_DEF2(bonus,"bonus2","ivi"),
+	BUILDIN_DEF2(bonus,"bonus3","ivii"),
+	BUILDIN_DEF2(bonus,"bonus4","iviii"),
+	BUILDIN_DEF2(bonus,"bonus5","iviiii"),
 	BUILDIN_DEF(bonusautoscript,"si?"),
 	BUILDIN_DEF(bonusautoscript2,"si?"),
-	BUILDIN_DEF(skill,"ii?"),
-	BUILDIN_DEF(addtoskill,"ii?"), // [Valaris]
-	BUILDIN_DEF(guildskill,"ii"),
-	BUILDIN_DEF(getskilllv,"i"),
-	BUILDIN_DEF(getgdskilllv,"ii"),
+	BUILDIN_DEF(skill,"vi?"),
+	BUILDIN_DEF(addtoskill,"vi?"), // [Valaris]
+	BUILDIN_DEF(guildskill,"vi"),
+	BUILDIN_DEF(getskilllv,"v"),
+	BUILDIN_DEF(getgdskilllv,"iv"),
 	BUILDIN_DEF(basicskillcheck,""),
 	BUILDIN_DEF(getgmlevel,""),
 	BUILDIN_DEF(end,""),
@@ -13374,7 +13413,7 @@ struct script_function buildin_func[] = {
 	BUILDIN_DEF(gettimestr,"si"),
 	BUILDIN_DEF(openstorage,""),
 	BUILDIN_DEF(guildopenstorage,"*"),
-	BUILDIN_DEF(itemskill,"ii"),
+	BUILDIN_DEF(itemskill,"vi"),
 	BUILDIN_DEF(produce,"i"),
 	BUILDIN_DEF(monster,"siisii*"),
 	BUILDIN_DEF(areamonster,"siiiisii*"),
@@ -13481,11 +13520,11 @@ struct script_function buildin_func[] = {
 	BUILDIN_DEF(petrecovery,"ii"), // [Valaris]
 	BUILDIN_DEF(petloot,"i"), // [Valaris]
 	BUILDIN_DEF(petheal,"iiii"), // [Valaris]
-	BUILDIN_DEF(petskillattack,"iiii"), // [Skotlex]
-	BUILDIN_DEF(petskillattack2,"iiiii"), // [Valaris]
-	BUILDIN_DEF(petskillsupport,"iiiii"), // [Skotlex]
-	BUILDIN_DEF(skilleffect,"ii"), // skill effect [Celest]
-	BUILDIN_DEF(npcskilleffect,"iiii"), // npc skill effect [Valaris]
+	BUILDIN_DEF(petskillattack,"viii"), // [Skotlex]
+	BUILDIN_DEF(petskillattack2,"viiii"), // [Valaris]
+	BUILDIN_DEF(petskillsupport,"viiii"), // [Skotlex]
+	BUILDIN_DEF(skilleffect,"vi"), // skill effect [Celest]
+	BUILDIN_DEF(npcskilleffect,"viii"), // npc skill effect [Valaris]
 	BUILDIN_DEF(specialeffect,"i*"), // npc skill effect [Valaris]
 	BUILDIN_DEF(specialeffect2,"i*"), // skill effect on players[Valaris]
 	BUILDIN_DEF(nude,""), // nude command [Valaris]
@@ -13587,8 +13626,8 @@ struct script_function buildin_func[] = {
 	BUILDIN_DEF(unitstop,"i"),
 	BUILDIN_DEF(unittalk,"is"),
 	BUILDIN_DEF(unitemote,"ii"),
-	BUILDIN_DEF(unitskilluseid,"iii?"), // originally by Qamera [Celest]
-	BUILDIN_DEF(unitskillusepos,"iiiii"), // [Celest]
+	BUILDIN_DEF(unitskilluseid,"ivi?"), // originally by Qamera [Celest]
+	BUILDIN_DEF(unitskillusepos,"iviii"), // [Celest]
 // <--- [zBuffer] List of mob control commands
 	BUILDIN_DEF(sleep,"i"),
 	BUILDIN_DEF(sleep2,"i"),

+ 19 - 4
src/map/skill.c

@@ -47,6 +47,7 @@
 static struct eri *skill_unit_ers = NULL; //For handling skill_unit's [Skotlex]
 static struct eri *skill_timer_ers = NULL; //For handling skill_timerskills [Skotlex]
 
+DBMap* skilldb_name2id = NULL;
 struct s_skill_db skill_db[MAX_SKILL_DB];
 struct s_skill_produce_db skill_produce_db[MAX_SKILL_PRODUCE_DB];
 struct s_skill_arrow_db skill_arrow_db[MAX_SKILL_ARROW_DB];
@@ -59,6 +60,15 @@ int icewall_unit_pos;
 //Since only mob-casted splash skills can hit ice-walls
 #define splash_target(bl) (bl->type==BL_MOB?BL_SKILL|BL_CHAR:BL_CHAR)
 
+/// Returns the id of the skill, or 0 if not found.
+int skill_name2id(const char* name)
+{
+	if( name == NULL )
+		return 0;
+
+	return (int)strdb_get(skilldb_name2id, name);
+}
+
 /// Maps skill ids to skill db offsets.
 /// Returns the skill's array index, or 0 (Unknown Skill).
 int skill_get_index( int id )
@@ -10743,16 +10753,17 @@ void skill_init_unit_layout (void)
 
 static bool skill_parse_row_skilldb(char* split[], int columns, int current)
 {// id,range,hit,inf,element,nk,splash,max,list_num,castcancel,cast_defence_rate,inf2,maxcount,skill_type,blow_count,name,description
-	int i = atoi(split[0]);
-	if( i >= GD_SKILLRANGEMIN && i <= GD_SKILLRANGEMAX ) {
+	int id = atoi(split[0]);
+	int i;
+	if( id >= GD_SKILLRANGEMIN && id <= GD_SKILLRANGEMAX ) {
 		ShowWarning("skill_parse_row_skilldb: Skill id %d is forbidden (interferes with guild skill mapping)!\n");
 		return false;
 	}
-	if( i >= HM_SKILLRANGEMIN && i <= HM_SKILLRANGEMAX ) {
+	if( id >= HM_SKILLRANGEMIN && id <= HM_SKILLRANGEMAX ) {
 		ShowWarning("skill_parse_row_skilldb: Skill id %d is forbidden (interferes with homunculus skill mapping)!\n");
 		return false;
 	}
-	i = skill_get_index(i);
+	i = skill_get_index(id);
 	if( !i ) // invalid skill id
 		return false;
 
@@ -10783,6 +10794,7 @@ static bool skill_parse_row_skilldb(char* split[], int columns, int current)
 	skill_split_atoi(split[14],skill_db[i].blewcount);
 	safestrncpy(skill_db[i].name, trim(split[15]), sizeof(skill_db[i].name));
 	safestrncpy(skill_db[i].desc, trim(split[16]), sizeof(skill_db[i].desc));
+	strdb_put(skilldb_name2id, skill_db[i].name, (void*)id);
 
 	return true;
 }
@@ -11012,6 +11024,7 @@ static bool skill_parse_row_abradb(char* split[], int columns, int current)
 static void skill_readdb(void)
 {
 	// init skill db structures
+	db_clear(skilldb_name2id);
 	memset(skill_db,0,sizeof(skill_db));
 	memset(skill_produce_db,0,sizeof(skill_produce_db));
 	memset(skill_arrow_db,0,sizeof(skill_arrow_db));
@@ -11042,6 +11055,7 @@ void skill_reload (void)
  *------------------------------------------*/
 int do_init_skill (void)
 {
+	skilldb_name2id = strdb_alloc(DB_OPT_DUP_KEY, 0);
 	skill_readdb();
 	
 	skill_unit_ers = ers_new(sizeof(struct skill_unit_group));
@@ -11060,6 +11074,7 @@ int do_init_skill (void)
 
 int do_final_skill(void)
 {
+	db_destroy(skilldb_name2id);
 	ers_destroy(skill_unit_ers);
 	ers_destroy(skill_timer_ers);
 	return 0;

+ 2 - 0
src/map/skill.h

@@ -249,6 +249,8 @@ int	skill_tree_get_max( int id, int b_class );	// Celest
 const char*	skill_get_name( int id ); 	// [Skotlex]
 const char*	skill_get_desc( int id ); 	// [Skotlex]
 
+int skill_name2id(const char* name);
+
 int skill_isammotype(struct map_session_data *sd, int skill);
 int skill_castend_id(int tid, unsigned int tick, int id, intptr data);
 int skill_castend_pos(int tid, unsigned int tick, int id, intptr data);