AnnieRuru 957 Posted November 29, 2015 (edited) After so many years of hearing rumor of this modification, finally today is the day I can release this to public Download : 1.5plugin original topic from eathena 1.0 rush releaseplugin 1.1 - plugin - now @reloadskilldb will also reload OnPCUseSkillEvent file - added clean_skillevent - credit to Ind's manner system - add self inf type skill, probably useful for mimic monster skill 1.2 - plugin - no need to clean too much LOL - now OnPCUseSkillEvent.conf can use more whitespace - unsupported inf type will now display which skill ID properly - fix a bug that inf type friend(16) when cast on self, will spam error message 1.3 - plugin - update to latest revision - fix server crash when parse the string in OnPCUseSkillEvent.txt - help clean the temporary player variable 1.4 - plugin - remove the 100 array limit by utilize VECTOR - drop CSV format and use Hercules standard libconfig format 1.5 - plugin - remove the OnPCUseSkillEvent.conf file Edited October 27, 2020 by AnnieRuru 6 Nebraskka, Easycore, Emistry and 3 others reacted to this Quote Share this post Link to post Share on other sites
AnnieRuru 957 Posted November 29, 2015 (edited) Tested with db/re/skill_db.conf { Id: 2991 Name: "CUSTOM_damage" Description: "CUSTOM_damage" MaxLevel: 1 Range: 15 SkillType: { Enemy: true } Event_Label: "qwer::Ontarget" }, { Id: 2992 Name: "CUSTOM_nodamage" Description: "CUSTOM_nodamage" MaxLevel: 1 Range: 15 SkillType: { Friend: true } Event_Label: "qwer::Ontarget" }, { Id: 2993 Name: "CUSTOM_setpos" Description: "CUSTOM_setpos" MaxLevel: 3 Range: 15 SkillType: { Place: true } Event_Label: "qwer::Onpos" }, { Id: 2994 Name: "CUSTOM_self" Description: "CUSTOM_self" MaxLevel: 1 Range: 15 SkillType: { Self: true } Event_Label: "qwer::Onself" }, data/luafiles514/lua files/skillinfoz/skillinfolist.lub [SKID.CUSTOM_damage] = { "CUSTOM_damage"; SkillName = "Get Target enemy", MaxLv = 1, Type = "Quest", SpAmount = { 0 }, bSeperateLv = true, AttackRange = { 15 }, }, [SKID.CUSTOM_nodamage] = { "CUSTOM_nodamage"; SkillName = "Get Target friend", MaxLv = 1, Type = "Quest", SpAmount = { 0 }, bSeperateLv = true, AttackRange = { 15 }, }, [SKID.CUSTOM_setpos] = { "CUSTOM_setpos"; SkillName = "Get Position", MaxLv = 3, Type = "Quest", SpAmount = { 0 }, bSeperateLv = true, AttackRange = { 15 }, }, [SKID.CUSTOM_self] = { "CUSTOM_self"; SkillName = "Self Cast", MaxLv = 1, Type = "Quest", SpAmount = { 0 }, bSeperateLv = true, AttackRange = { 1 }, }, data/luafiles514/lua files/skillinfoz/skillid.lub CUSTOM_damage = 2991, CUSTOM_nodamage = 2992, CUSTOM_setpos = 2993, CUSTOM_self = 2994, data/luafiles514/lua files/skillinfoz/skilldescript.lub [SKID.CUSTOM_damage] = { "Test Target Enemy", "MAX Lv : 1 ", "push these variables :-", "'@useskilllv' for the skill level.", "'@useskilltarget' for the GID.", }, [SKID.CUSTOM_nodamage] = { "Test Target Friend", "MAX Lv : 1 ", "push these variables :-", "'@useskilllv' for the skill level.", "'@useskilltarget' for the GID.", }, [SKID.CUSTOM_setpos] = { "Test Coordinate", "MAX Lv : 3 ", "push these variables :-", "'@useskilllv' for the skill level.", "'@useskillx' for the X coordinate.", "'@useskilly' for the Y coordinate.", }, [SKID.CUSTOM_self] = { "Test Self", "MAX Lv : 1 ", "push these variables :-", "'@useskilllv' for the skill level.", } and finally the npc script - script qwer FAKE_NPC,{ Ontarget: dispbottom "lv: "+ @useskilllv +" | target "+ @useskilltarget; unittalk @useskilltarget, "from "+ strcharinfo(PC_NAME); end; Onpos: dispbottom "lv: "+ @useskilllv +" | x: "+ @useskillx +" | y: "+ @useskilly; end; Onself: dispbottom "lv: "+ @useskilllv; end; OnPCStatCalcEvent: skill CUSTOM_damage, 1; skill CUSTOM_nodamage, 1; skill CUSTOM_setpos, 3; skill CUSTOM_self, 1; end; } fuh ! so, yes, this is basically making a new skill, so read this wiki on how to make a new skillhttp://herc.ws/wiki/Adding_new_skillsFrequently Asked QuestionWhy some skill ID doesn't work ? On 3/17/2014 at 5:45 AM, AnnieRuru said: the problem is because of http://herc.ws/board/topic/512-skill-id-processing-overhaul/ hercules implement the skill ID reading in such a way that its harder to add more skill ID ( to save memory ) so we have to use the skill ID that is within the range of the gap that gravity not using see this inside skill_get_index function //[Ind/Hercules] GO GO GO LESS! - http://herc.ws/board/topic/512-skill-id-processing-overhaul/ else if( skill_id > 1019 && skill_id < 8001 ) { if( skill_id < 2058 ) // 1020 - 2000 are empty skill_id = 1020 + skill_id - 2001; else if( skill_id < 2549 ) // 2058 - 2200 are empty - 1020+57 skill_id = (1077) + skill_id - 2201; else if ( skill_id < 3036 ) // 2549 - 3000 are empty - 1020+57+348 skill_id = (1425) + skill_id - 3001; else if ( skill_id < 5044 ) // 3036 - 5000 are empty - 1020+57+348+35 skill_id = (1460) + skill_id - 5001; else ShowWarning("skill_get_index: skill id '%d' is not being handled!\n",skill_id); } because eathena forum down, let me rephrase again what this modification does if the skill inf type is INF_ATTACK_SKILL (target enemy only) - Enemy: true - kill the unit with *unitkill - zap another player's health with *heal -1000, 0; - apply curse status with *sc_start - make the target *unittalk ... - etc etc etc... if the skill inf type is INF_SUPPORT_SKILL (target friends and enemy) - Friend: true - check if the player is party members, give buff by *sc_start - check if the player is guild members, give buff by *sc_start during events - make the player show emotion - warp the target player to somewhere else - give players item/stat/cashpoints .... by *getitem/*statusup ... *attachrid + #CASHPOINTS if the skill inf type is INF_GROUND_SKILL (target ground) - Place: true - use *monster script command to summon monsters - *makeitem to rain items ... skill level determine the item ID ... - create a temporary npc .... using duplicatenpc plugin - etc etc etc ... this is just things I can think of, basically you can do ANYTHING with any script commands available 2nd thing is, when the skill type is INF_SUPPORT_SKILL, (Friend: true) you have to hold shift to target players this is client side limitation, require client hexing ... which I dunno how to do History: Question: Why there is no OnPCUseSkillEvent label in the npc script, but using the title OnPCUseSkillEvent ? ... eathena forum down because the original modification made during eathena was something like this OnPCUseSkillEvent: switch ( @useskillid ) { case 2991: switch ( @useskilllv ) { case 1: case 2: case 3: ... } break; case 2992: switch ( @useskilllv ) { ... } break; ... default: end; } which runs this label every time a player use ANY skill and the original custom modification tax very heavily on server resources that's why now this (revamp) version only pick which skill ID to run, along with your configurable event label Edited March 26, 2019 by AnnieRuru 2 Angelmelody and Emistry reacted to this Quote Share this post Link to post Share on other sites
AnnieRuru 957 Posted December 14, 2015 1.2 plugin - no need to clean too much LOL - now OnPCUseSkillEvent.conf can use more whitespace - unsupported inf type will now display which skill ID properly - fix a bug that inf type friend(16) when cast on self, will spam error message Quote Share this post Link to post Share on other sites
Angelmelody 221 Posted December 14, 2015 1.2 plugin - no need to clean too much LOL - now OnPCUseSkillEvent.conf can use more whitespace - unsupported inf type will now display which skill ID properly - fix a bug that inf type friend(16) when cast on self, will spam error message wow~ nice, but you forgot herc emu dont have OnPCStatCalcEvent Quote Share this post Link to post Share on other sites
AnnieRuru 957 Posted December 14, 2015 you mean this ? http://herc.ws/board/topic/11292-onpcstatcalcevent/ 1 Angelmelody reacted to this Quote Share this post Link to post Share on other sites
tancejang 0 Posted April 10, 2016 Thank you @@AnnieRuru for the source.. I implemented this in my server.. no compiled error, no failed . but no file built in conf/import folder.. it said no file "conf/import/OnPCUseSkillEvent.txt" instead of "OnPCUseSkillEvent.conf" when in your post is conf formatted file. And i dunno what should i do with OnPCUseSkillEvent.txt or .conf .. can anyone help me? Thank you ^^ Quote Share this post Link to post Share on other sites
MikZ 5 Posted April 17, 2016 Hello @@AnnieRuruPlease help me with this, how to fixed this. thank you! CC OnPCUseSkillEvent.c OnPCUseSkillEvent.c: In function ‘read_skillevent’: OnPCUseSkillEvent.c:186: warning: format ‘%s’ expects type ‘char *’, but argument 3 has type ‘int’ PLUGIN OnPCUseSkillEvent Quote Share this post Link to post Share on other sites
AnnieRuru 957 Posted March 25, 2019 finally update this after 4 years.... 1.3 - plugin - update to latest revision - fix server crash when parse the string in OnPCUseSkillEvent.txt - help clean the temporary player variable 1.4 - plugin - remove the 100 array limit by utilize VECTOR - drop CSV format and use Hercules standard libconfig format 1 Emistry reacted to this Quote Share this post Link to post Share on other sites
Emistry 145 Posted March 26, 2019 I have been waiting for this soooooo loooonnnnggggg tiimmmmeeee... anyway, just curious, since its just adding a new field "event_label", why not consider alter the existing "skill_db" and add the field there? 1 AnnieRuru reacted to this Quote Share this post Link to post Share on other sites
AnnieRuru 957 Posted March 26, 2019 (edited) 1 hour ago, Emistry said: anyway, just curious, since its just adding a new field "event_label", why not consider alter the existing "skill_db" and add the field there? possible, but the event label can't throw error anymore during server start-up you see, the server has an order when loading stuffs [Status]: Done reading '64' command aliases in 'conf/atcommand.conf'. [Status]: Done reading '4' channels in 'conf/channels.conf'. [Status]: Done reading '10600' entries in 're/item_db.conf'. ... [Status]: Done reading '1128' entries in 'db/re/skill_db.conf'. // <--- HERE !!! [Status]: Done reading '264' entries in 'db/produce_db.txt'. [Status]: Done reading '136' entries in 'db/create_arrow_db.txt'. .... [Status]: Done reading '15' zones in 'db/re/map_zone_db.conf'. [Status]: Done reading '0' entries in 'db/mob_item_ratio.txt'. [Status]: Done reading '40' entries in 'mob_chat_db.txt'. [Status]: Done reading '1724' entries in 're/mob_db.conf'. ... [Status]: Done reading '3064' entries in 'quest_db.conf'. [Status]: Done reading '344' entries in 'db/re/achievement_db.conf'. [Status]: Done reading '11' entries in 'db/achievement_rank_db.conf'. [Info]: Done loading '8' NPCs: <-------------------------------------- HERE !!! -'0' Warps -'0' Shops -'8' Scripts -'0' Spawn sets -'0' Mobs Cached -'0' Mobs Not Cached [Status]: Done reading '56' entries in 'db/stylist_db.conf'. [Status]: Event 'OnInit' executed with '4' NPCs. [Info]: Hercules, Copyright (C) 2012-2018, Hercules Dev Team and others. [Info]: Licensed under the GNU General Public License, version 3 or later. [Status]: Server is 'ready' and listening on port '5121'. [Status]: Done reading '4' entries in 'conf/import/OnPCUseSkillEvent.conf'. <------ HERE !!! if I hook to the skill_validate_additional_fields, it will always say Event label NOT FOUND, because the npc wasn't loaded yet my plugin doesn't read the OnPCUseSkillEvent.conf file during [HPExport void plugin_init] function, but at [HPExport void server_online] function this is to make sure it runs AFTER the npc files are loaded yes, its possible to just hook to the skill_validate_additional_fields function, but it wont throw error on server start-up anymore the npc label check will be done when player is casting the skill instead, <-- which is already too late --> I want the error thrown during server start-up struct event_data *ev = (struct event_data*)strdb_get(npc->ev_db, event); if ( ev == NULL || ev->nd == NULL ) { ShowWarning( "OnPCUseSkillEvent: NPC label "CL_WHITE"%s"CL_RESET" does not found on skill "CL_WHITE"%s(%d)"CL_RESET" entry no."CL_WHITE"%d"CL_RESET" in '"CL_WHITE"%s"CL_RESET"'.\n", event, skillname, skillid, i, confpath ); continue; } EDIT: hmm ... yeah, why not just try hook both ... hook to the skill_validate_additional_fields function, then check the npc label again at [HPExport void server_online] function ... ... give it a try ... EDIT2: there is no addToSKILLDATA in HPMi.h !! Edited March 26, 2019 by AnnieRuru Quote Share this post Link to post Share on other sites
AnnieRuru 957 Posted March 26, 2019 1.5 - plugin - remove the OnPCUseSkillEvent.conf file Quote Share this post Link to post Share on other sites
rans 7 Posted May 10, 2019 Hi, Its broken on the lastest version of herc. it doesnt compile and showing error something about you cant declare struct on statement. Quote Share this post Link to post Share on other sites
Zero Human 0 Posted March 17, 2020 (edited) On 5/10/2019 at 10:50 AM, rans said: Hi, Its broken on the lastest version of herc. it doesnt compile and showing error something about you cant declare struct on statement. Here is the error message: Spoiler OnPCUseSkillEvent.c: In function ‘read_skillevent’: OnPCUseSkillEvent.c:161:4: error: a label can only be part of a statement and a declaration is not a statement struct enemyskilldata enemyskill_; ^~~~~~ OnPCUseSkillEvent.c:168:4: error: a label can only be part of a statement and a declaration is not a statement struct friendskilldata friendskill_; ^~~~~~ OnPCUseSkillEvent.c:175:4: error: a label can only be part of a statement and a declaration is not a statement struct placeskilldata placeskill_; ^~~~~~ OnPCUseSkillEvent.c:182:4: error: a label can only be part of a statement and a declaration is not a statement struct selfskilldata selfskill_; Edited March 17, 2020 by Zero Human Quote Share this post Link to post Share on other sites
Kenpachi 65 Posted March 19, 2020 Hi. For those errors replace: case INF_ATTACK_SKILL: struct enemyskilldata enemyskill_; enemyskill_.skill_id = skill_id; enemyskill_.event = aStrdup(VECTOR_INDEX(tempskill, i).event); VECTOR_ENSURE( enemyskill, 1, 1 ); VECTOR_PUSH( enemyskill, enemyskill_ ); break; case INF_SUPPORT_SKILL: struct friendskilldata friendskill_; friendskill_.skill_id = skill_id; friendskill_.event = aStrdup(VECTOR_INDEX(tempskill, i).event); VECTOR_ENSURE( friendskill, 1, 1 ); VECTOR_PUSH( friendskill, friendskill_ ); break; case INF_GROUND_SKILL: struct placeskilldata placeskill_; placeskill_.skill_id = skill_id; placeskill_.event = aStrdup(VECTOR_INDEX(tempskill, i).event); VECTOR_ENSURE( placeskill, 1, 1 ); VECTOR_PUSH( placeskill, placeskill_ ); break; case INF_SELF_SKILL: struct selfskilldata selfskill_; selfskill_.skill_id = skill_id; selfskill_.event = aStrdup(VECTOR_INDEX(tempskill, i).event); VECTOR_ENSURE( selfskill, 1, 1 ); VECTOR_PUSH( selfskill, selfskill_ ); break; with: case INF_ATTACK_SKILL: { struct enemyskilldata enemyskill_; enemyskill_.skill_id = skill_id; enemyskill_.event = aStrdup(VECTOR_INDEX(tempskill, i).event); VECTOR_ENSURE( enemyskill, 1, 1 ); VECTOR_PUSH( enemyskill, enemyskill_ ); break; } case INF_SUPPORT_SKILL: { struct friendskilldata friendskill_; friendskill_.skill_id = skill_id; friendskill_.event = aStrdup(VECTOR_INDEX(tempskill, i).event); VECTOR_ENSURE( friendskill, 1, 1 ); VECTOR_PUSH( friendskill, friendskill_ ); break; } case INF_GROUND_SKILL: { struct placeskilldata placeskill_; placeskill_.skill_id = skill_id; placeskill_.event = aStrdup(VECTOR_INDEX(tempskill, i).event); VECTOR_ENSURE( placeskill, 1, 1 ); VECTOR_PUSH( placeskill, placeskill_ ); break; } case INF_SELF_SKILL: { struct selfskilldata selfskill_; selfskill_.skill_id = skill_id; selfskill_.event = aStrdup(VECTOR_INDEX(tempskill, i).event); VECTOR_ENSURE( selfskill, 1, 1 ); VECTOR_PUSH( selfskill, selfskill_ ); break; } That's just a fix for the posted error messages. There may be more issues... ~Kenpachi Quote Share this post Link to post Share on other sites
Zero Human 0 Posted March 19, 2020 Thanks for fix the "first" error xD. And Yea, you're Right. The next error: OnPCUseSkillEvent.c: In function ‘read_skillevent’: OnPCUseSkillEvent.c:198:14: error: ‘struct enemyskilldata’ has no member named skill_id’; did you mean ‘skillid’? enemyskill_.skill_id = skill_id; ^ OnPCUseSkillEvent.c:198:26: error: ‘skill_id’ undeclared (first use in this function) enemyskill_.skill_id = skill_id; ^~~~~~~~ OnPCUseSkillEvent.c:198:26: note: each undeclared identifier is reported only once for each function it appears in In file included from OnPCUseSkillEvent.c:23:0: OnPCUseSkillEvent.c:199:44: error: ‘tempskill’ undeclared (first use in this function) enemyskill_.event = aStrdup(VECTOR_INDEX(tempskill, i).event); ^ ../common/memmgr.h:49:43: note: in definition of macro ‘aStrdup’ # define aStrdup(p) (iMalloc->astrdup((p),ALC_MARK)) ^ ../common/db.h:1160:4: note: in expansion of macro ‘VECTOR_DATA’ ( VECTOR_DATA(_vec)[_idx] ) ^~~~~~~~~~~ OnPCUseSkillEvent.c:199:31: note: in expansion of macro ‘VECTOR_INDEX’ enemyskill_.event = aStrdup(VECTOR_INDEX(tempskill, i).event); ^~~~~~~~~~~~ OnPCUseSkillEvent.c:206:15: error: ‘struct friendskilldata’ has no member named ‘skill_id’; did you mean ‘skillid’? friendskill_.skill_id = skill_id; ^ OnPCUseSkillEvent.c:214:14: error: ‘struct placeskilldata’ has no member named skill_id’; did you mean ‘skillid’? placeskill_.skill_id = skill_id; ^ OnPCUseSkillEvent.c:222:13: error: ‘struct selfskilldata’ has no member named ‘skill_id’; did you mean ‘skillid’? selfskill_.skill_id = skill_id; Quote Share this post Link to post Share on other sites
Kenpachi 65 Posted March 20, 2020 Hi. Compiles just fine for me, after adding those curly brackets. 😯 OnPCUseSkillEvent_1.5.c ~Kenpachi Quote Share this post Link to post Share on other sites
Zero Human 0 Posted March 20, 2020 Yea,... was my mistake. Works perfect now. Thank you. Quote Share this post Link to post Share on other sites
AnnieRuru 957 Posted September 16, 2020 @Zero Human can you please tell me which compiler you use to get that error ? I tested on latest hercules with Visual Studio 2019 and it doesn't throw any error and..... this plugin still works, but has to extra step by adding a diff after this commit src/common/mmo.h | 2 +- src/map/skill.c | 1 + 2 files changed, 2 insertions(+), 1 deletion(-) diff --git a/src/common/mmo.h b/src/common/mmo.h index e4b5a8bd5..6d029228a 100644 --- a/src/common/mmo.h +++ b/src/common/mmo.h @@ -234,7 +234,7 @@ #define MAX_CART 100 #endif #ifndef MAX_SKILL_DB -#define MAX_SKILL_DB 1314 ///< Maximum number of skills in the skill DB (compacted array size) +#define MAX_SKILL_DB 1318 ///< Maximum number of skills in the skill DB (compacted array size) #endif #ifndef MAX_SKILL_ID #define MAX_SKILL_ID 10015 // [Ind/Hercules] max used skill ID diff --git a/src/map/skill.c b/src/map/skill.c index c2a336d7e..f827eb21f 100644 --- a/src/map/skill.c +++ b/src/map/skill.c @@ -97,6 +97,7 @@ static const struct { { HLIF_HEAL, MH_VOLCANIC_ASH }, { MS_BASH, MER_INVINCIBLEOFF2 }, { EL_CIRCLE_OF_FIRE, EL_STONE_RAIN }, + { 2991, 2994 }, { GD_APPROVAL, GD_DEVELOPMENT }, CUSTOM_SKILL_RANGES }; blame 4144 and dastgir adding custom skills even harder now https://github.com/HerculesWS/Hercules/pull/2596 I dunno how to fix this just by plugin alone ... honestly someone please show me the way to add custom skill by just plugin alone ( example the extra *bonus can be added via plugin ) not like 4144 said need to add new custom project setting blah blah blah Quote Share this post Link to post Share on other sites
crdb5066 0 Posted March 17, 2021 Does this still work? I've compiled the one posted by Kenpachi and everything looks fine, but when I use my custom skill, nothing happens? When I try to add Event_Label to any skill, nothing happens. Is there another way to make a skill call an npc event or function? Like npc->script_event(sd, "NPCname::EventLabel"); in skill.c? Quote Share this post Link to post Share on other sites