cumbe11 1 Posted December 4, 2015 Here is this change? @partybuff (@spb) can display party member's special buffs in party list (Alt+Z)Buffs are:Quote B - BlessingA - Agility UpF - Full Chemical ProtectionS - Soul Link+ - Devotion Look like[BAFS+]Player name Quote Share this post Link to post Share on other sites
0 AnnieRuru 957 Posted December 4, 2015 (edited) even if this is possible, there is a client restriction which disallow to display player name longer than 23 characters ...and the color has to be client reverse engineer ... means, no, this also has to do client side modification but if not display in the Alt+Z, but with a message commandthen this can even done with scripting alone, with getstatus script command - script jsfkjsdf FAKE_NPC,{OnInit: bindatcmd "psc", strnpcinfo(0)+"::Onaaa"; end;Onaaa: .@pid = getcharid(1); if ( !.@pid ) { dispbottom "you don't have a party to use this command"; end; } getpartymember .@pid, 1; getpartymember .@pid, 2; .@origin = getcharid(3); for ( .@i = 0; .@i < $@partymembercount; ++.@i ) { if ( isloggedin( $@partymemberaid[.@i] , $@partymembercid[.@i] ) ) { attachrid $@partymemberaid[.@i]; .@buff$ = ""; if ( getstatus(SC_BLESSING) ) .@buff$ += "B"; if ( getstatus(SC_INC_AGI) ) .@buff$ += "A"; if ( getstatus(SC_PROTECTWEAPON) && getstatus(SC_PROTECTSHIELD) && getstatus(SC_PROTECTARMOR) && getstatus(SC_PROTECTHELM) ) .@buff$ += "F"; if ( getstatus(SC_SOULLINK) ) .@buff$ += "S"; if ( getstatus(SC_DEVOTION) ) .@buff$ += "+"; .@display$[.@c++] = "["+ .@buff$ +"] "+ strcharinfo(0); } } attachrid .@origin; for ( .@i = 0; .@i < .@c; ++.@i ) dispbottom .@display$[.@i]; end;} Edited December 4, 2015 by AnnieRuru 2 Legend and evilpuncker reacted to this Quote Share this post Link to post Share on other sites
0 REKT 10 Posted December 4, 2015 There's a mod like this from rAthena which is from Lilit's Mod. Quote Share this post Link to post Share on other sites
0 AnnieRuru 957 Posted December 4, 2015 (edited) @@Vlync now I'm very very interested, show meh ! EDIT: even a video is fine, I can guess how they did it Edited December 4, 2015 by AnnieRuru Quote Share this post Link to post Share on other sites
0 Dastgir 1246 Posted December 4, 2015 @@Vlync now I'm very very interested, show meh ! EDIT: even a video is fine, I can guess how they did it Name can be modified via clif.c, hooking appropriate functions..(And trimming names if they reach > 23 char, thats what they do) Quote Share this post Link to post Share on other sites
0 AnnieRuru 957 Posted December 4, 2015 ok, let's analyze the packet clif_party_member_info /// Adds new member to a party. /// 0104 <account id>.L <role>.L <x>.W <y>.W <state>.B <party name>.24B <char name>.24B <map name>.16B (ZC_ADD_MEMBER_TO_GROUP) 23 characters for name, 23 characters for map name hmm ... if we replace the map name with buff ... hehe ... sounds fun clif_party_info /// Sends party information (ZC_GROUP_LIST). /// 00fb <packet len>.W <party name>.24B { <account id>.L <nick>.24B <map name>.16B <role>.B <state>.B }* /// role: /// 0 = leader /// 1 = normal /// state: /// 0 = connected /// 1 = disconnected clif_party_xy /// Updates the position of a party member on the minimap (ZC_NOTIFY_POSITION_TO_GROUPM). /// 0107 <account id>.L <x>.W <y>.W clif_party_hp /// Updates HP bar of a party member. /// 0106 <account id>.L <hp>.W <max hp>.W (ZC_NOTIFY_HP_TO_GROUPM) so ... there is no packet to update the party member's status in Alt+Z bar clif_parse_LeaveParty /// Request to leave party (CZ_REQ_LEAVE_GROUP). clif_parse_RemovePartyMember /// Request to expel a party member (CZ_REQ_EXPEL_GROUP_MEMBER). the one trick that I can think off, is sending a packet to leave player's party and invite back with a fake name but I wonder doing this will have message on the chat log ? ... hmm ... ask a client translation team, maybe they know where is the english file at 1 Naruto reacted to this Quote Share this post Link to post Share on other sites
0 Dastgir 1246 Posted December 4, 2015 void clif_party_info -> memcpy(WBUFP(buf,28+c*46+4), m->name, NAME_LENGTH); Just modify m->name before using memcpy.. and that will show change in party window. Edit: In chat log, they will have normal name, just party window will be edited. 1 AnnieRuru reacted to this Quote Share this post Link to post Share on other sites
0 cumbe11 1 Posted December 4, 2015 1 AnnieRuru reacted to this Quote Share this post Link to post Share on other sites
0 Garr 117 Posted December 4, 2015 (edited) Hmm. But that will also need additional calls to this if status will get changed. Because iirc by default party info changes when player either logs off/on or changes map. Also, may change character name limit to 17 to avoid name cutting (most nicknames are under 12~15 characters anyway). Edited December 4, 2015 by Garr Quote Share this post Link to post Share on other sites
0 AnnieRuru 957 Posted December 4, 2015 (edited) #include "common/hercules.h"#include <stdio.h>#include <string.h>#include <stdlib.h>#include "map/pc.h"#include "map/clif.h"#include "map/party.h"#include "common/nullpo.h"#include "common/socket.h"#include "common/HPMDataCheck.h" // should always be the last file included! (if you don't make it last, it'll intentionally break compile time)HPExport struct hplugin_info pinfo = { "test123", // Plugin name SERVER_TYPE_MAP,// Which server types this plugin works with? "0.0", // Plugin version HPM_VERSION, // HPM Version (don't change, macro is automatically updated)};struct player_data { int buff;};int status_change_start_post( int retVal, struct block_list *src, struct block_list *bl, enum sc_type *type, int *rate, int *val1, int *val2, int *val3, int *val4, int *tick, int *flag) { if ( bl->type == BL_PC && retVal > 0 ) { ShowDebug( "PC" ); if ( *type == SC_BLESSING ) ShowDebug( "Yes" ); } return retVal;} void clif_party_info_pre(struct party_data* p, struct map_session_data *sd) { unsigned char buf[2+2+NAME_LENGTH+(4+NAME_LENGTH+MAP_NAME_LENGTH_EXT+1+1)*MAX_PARTY]; struct map_session_data* party_sd = NULL; int i, c; char aaa[NAME_LENGTH]; nullpo_retv(p); WBUFW(buf,0) = 0xfb; memcpy(WBUFP(buf,4), p->party.name, NAME_LENGTH); for (i = 0, c = 0; i < MAX_PARTY; i++) { struct party_member* m = &p->party.member[i]; if(!m->account_id) continue; if(party_sd == NULL) party_sd = p->data[i].sd; WBUFL(buf,28+c*46) = m->account_id; safesnprintf( aaa, NAME_LENGTH, "[ASDF]%s", m->name ); memcpy(WBUFP(buf,28+c*46+4), aaa, NAME_LENGTH); mapindex->getmapname_ext(mapindex_id2name(m->map), (char*)WBUFP(buf,28+c*46+28)); WBUFB(buf,28+c*46+44) = (m->leader) ? 0 : 1; WBUFB(buf,28+c*46+45) = (m->online) ? 0 : 1; c++; } WBUFW(buf,2) = 28+c*46; if(sd) clif->send(buf, WBUFW(buf,2), &sd->bl, SELF); else if (party_sd) clif->send(buf, WBUFW(buf,2), &party_sd->bl, PARTY); hookStop(); return;} HPExport void plugin_init (void) { addHookPre( "clif->party_info", clif_party_info_pre ); addHookPost( "status->change_start", status_change_start_post );}@@cumbe11is it normal to show [ASDF]<name> in the chat log like this ? EDIT: @@Garr I thought about that, but Dastgir said just have to put clif_party_info function in status_change_start and status_change_end, and it will update itself Edited December 4, 2015 by AnnieRuru Quote Share this post Link to post Share on other sites
0 cumbe11 1 Posted December 4, 2015 this is a plugin? Quote Share this post Link to post Share on other sites
0 AnnieRuru 957 Posted December 4, 2015 (edited) yup, currently look like this now #include "common/hercules.h" #include <stdio.h> #include <string.h> #include <stdlib.h> #include "map/pc.h" #include "map/clif.h" #include "map/party.h" #include "common/nullpo.h" #include "common/socket.h" #include "common/memmgr.h" #include "common/HPMDataCheck.h" // should always be the last file included! (if you don't make it last, it'll intentionally break compile time) HPExport struct hplugin_info pinfo = { "test123", // Plugin name SERVER_TYPE_MAP,// Which server types this plugin works with? "0.0", // Plugin version HPM_VERSION, // HPM Version (don't change, macro is automatically updated) }; struct player_data { int buff; }; int status_change_start_post( int retVal, struct block_list *src, struct block_list *bl, enum sc_type *type, int *rate, int *val1, int *val2, int *val3, int *val4, int *tick, int *flag) { if ( bl->type == BL_PC && retVal > 0 ) { TBL_PC *sd = BL_CAST(BL_PC, bl); struct party_data *p; if ( p = party->search(sd->status.party_id )) { struct player_data *ssd = getFromMSD( sd, 0 ); int before_buff = ssd->buff; if ( *type == SC_BLESSING ) ssd->buff |= 0x1; if ( *type == SC_INC_AGI ) ssd->buff |= 0x2; if ( *type == SC_PROTECTWEAPON || *type == SC_PROTECTSHIELD || *type == SC_PROTECTARMOR || *type == SC_PROTECTHELM ) if ( sd->sc.data[SC_PROTECTWEAPON] && sd->sc.data[SC_PROTECTSHIELD] && sd->sc.data[SC_PROTECTARMOR] && sd->sc.data[SC_PROTECTHELM] ) ssd->buff |= 0x4; if ( *type == SC_SOULLINK ) ssd->buff |= 0x8; if ( *type == SC_DEVOTION ) ssd->buff |= 0x10; if ( before_buff != ssd->buff ) // only send the packet if update the status is newly apply, no need to resend if just renew the status clif->party_info( p, NULL ); } } return retVal; } int status_change_end_post( int retVal, struct block_list *bl, enum sc_type *type, int *tid, const char *file, int *line ) { if ( bl->type == BL_PC && retVal > 0 ) { TBL_PC *sd = BL_CAST(BL_PC, bl); struct party_data *p; if ( sd->state.active == 1 ) { // fix map-server crash when player logout if (( p = party->search(sd->status.party_id ))) { struct player_data *ssd = getFromMSD( sd, 0 ); int before_buff = ssd->buff; if ( *type == SC_BLESSING ) ssd->buff &= ~0x1; if ( *type == SC_INC_AGI ) ssd->buff &= ~0x2; if ( *type == SC_PROTECTWEAPON || *type == SC_PROTECTSHIELD || *type == SC_PROTECTARMOR || *type == SC_PROTECTHELM ) if ( sd->sc.data[SC_PROTECTWEAPON] && sd->sc.data[SC_PROTECTSHIELD] && sd->sc.data[SC_PROTECTARMOR] && sd->sc.data[SC_PROTECTHELM] ) ssd->buff &= ~0x4; if ( *type == SC_SOULLINK ) ssd->buff &= ~0x8; if ( *type == SC_DEVOTION ) ssd->buff &= ~0x10; if ( before_buff != ssd->buff ) // only send the packet if update the status is newly apply, no need to resend if just renew the status clif->party_info( p, NULL ); } } } return retVal; } void clif_party_info_overload( struct party_data* p, struct map_session_data *sd ) { unsigned char buf[2+2+NAME_LENGTH+(4+NAME_LENGTH+MAP_NAME_LENGTH_EXT+1+1)*MAX_PARTY]; struct map_session_data* party_sd = NULL; int i, c; nullpo_retv(p); WBUFW(buf,0) = 0xfb; memcpy( WBUFP(buf,4), p->party.name, NAME_LENGTH ); for ( i = 0, c = 0; i < MAX_PARTY; i++ ) { struct party_member* m = &p->party.member[i]; if(!m->account_id) continue; if(party_sd == NULL) party_sd = p->data[i].sd; WBUFL(buf,28+c*46) = m->account_id; if ( m->online && p->data[i].sd != NULL ) { struct player_data *ssd = getFromMSD( p->data[i].sd, 0 ); char temp[NAME_LENGTH]; safesnprintf( temp, NAME_LENGTH, "[%s%s%s%s%s]%s", ( ssd->buff & 0x1 )? "B" : "_", ( ssd->buff & 0x2 )? "A" : "_", ( ssd->buff & 0x4 )? "F" : "_", ( ssd->buff & 0x8 )? "S" : "_", ( ssd->buff & 0x10 )? "+" : "_", m->name ); memcpy(WBUFP(buf,28+c*46+4), temp, NAME_LENGTH); } else memcpy(WBUFP(buf,28+c*46+4), m->name, NAME_LENGTH); mapindex->getmapname_ext(mapindex_id2name(m->map), (char*)WBUFP(buf,28+c*46+28)); WBUFB(buf,28+c*46+44) = (m->leader) ? 0 : 1; WBUFB(buf,28+c*46+45) = (m->online) ? 0 : 1; c++; } WBUFW(buf,2) = 28+c*46; if (sd) clif->send(buf, WBUFW(buf,2), &sd->bl, SELF); else if (party_sd) clif->send(buf, WBUFW(buf,2), &party_sd->bl, PARTY); return; } bool pc_authok_pre( struct map_session_data *sd, int *login_id2, time_t *expiration_time, int *group_id, struct mmo_charstatus *st, bool *changing_mapservers ) { struct player_data *ssd; CREATE( ssd, struct player_data, true ); ssd->buff = 0; addToMSD( sd, ssd, 0, true ); return 0; } int map_quit_post( int retVal, struct map_session_data *sd ) { struct player_data *ssd = getFromMSD( sd, 0 ); removeFromMSD( sd, 0 ); return retVal; } HPExport void plugin_init (void) { addHookPre( "pc->authok", pc_authok_pre ); addHookPost( "map->quit", map_quit_post ); clif->party_info = &clif_party_info_overload; addHookPost( "status->change_start", status_change_start_post ); addHookPost( "status->change_end_", status_change_end_post ); } there is a bug, when the player JUST login for the 1st time in that party ( party just loaded )your name will appear twice in the party windowbut will disappear when apply a buff ... or another party member loginand, when apply a buff, it really does show the [b____] for the party member nameI guess, have to do something like @showbuff atcommand, to make this bug disappearit also has the advantage to show it or not to show it... and this is harder to do than I thoughttry continue tomorrow, I have to sleep now =.= Edited January 28, 2016 by Dastgir Edited the plugin with newline 1 evilpuncker reacted to this Quote Share this post Link to post Share on other sites
0 cumbe11 1 Posted December 5, 2015 I can use this plugin in a eAthena emulator? Quote Share this post Link to post Share on other sites
0 evilpuncker 503 Posted December 5, 2015 I can use this plugin in a eAthena emulator? no, since eA doesn't support Hercules plugin system Quote Share this post Link to post Share on other sites
0 vBrenth 39 Posted January 31, 2016 (edited) @@Dastgir can you adapt this too on ur hercules plugin collection please? and check the bugs that annies talking about. Edit: In chat log, they will have normal name, just party window will be edited. and this Edited January 31, 2016 by vBrenth Quote Share this post Link to post Share on other sites
0 Functor 36 Posted March 15, 2016 (edited) there is a bug, when the player JUST login for the 1st time in that party ( party just loaded ) your name will appear twice in the party window Also we can see this bug, when someone enters to the party. It is caused by sending of 0x1E9 packet, which adds one specific party member to the list on the client side. To fix bug of this plugin, we can disable sending of this packet. Because in any case server always sends full list of party members in 0xFB packet. before: HPExport void plugin_init (void) { add: void clif_party_member_info_overload(struct party_data* p, struct map_session_data* sd) { return; } after: HPExport void plugin_init (void) { add: clif->party_member_info = &clif_party_member_info_overload; Edited March 16, 2016 by Functor 4 Kubix, Like it~*, gunnoy and 1 other reacted to this Quote Share this post Link to post Share on other sites
0 AnnieRuru 957 Posted June 4, 2018 (edited) http://upaste.me/aa5e49917485b4900 I need some people to comment on my script I just bam bam and google here and there and it works on VS2015, but not sure if it is work on others though 1. need help how to really optimize this code 2.not really sure about using this kind of function char *showing_buff( struct map_session_data *sd ) { @meko @4144 http://upaste.me/75d049918e2088402 no idea how I get this error message, only pop up once [Error]: --- nullpo info -------------------------------------------- [Error]: ..\src\plugins\showbuff.c:115: 'p' in function `unknown' [Error]: --- end nullpo info ---------------------------------------- @xVec Edited June 5, 2018 by AnnieRuru 1 xVec reacted to this Quote Share this post Link to post Share on other sites
0 4144 364 Posted June 5, 2018 in ACMD(showbuff) in line 275 you show error message and p is NULL, and after call clif->party_info(p), this call your overloaded function clif_party_info_overload, and here it validate parameter for NULL and show error message. 2 xVec and AnnieRuru reacted to this Quote Share this post Link to post Share on other sites
0 AnnieRuru 957 Posted June 5, 2018 0.4 http://upaste.me/75d049918e2088402 wow ~ thanks ... having an extra eye is different ... about turning the [BASF+] into player configured buff ... that will be done in another day ... 1 xVec reacted to this Quote Share this post Link to post Share on other sites
0 xVec 1 Posted July 4, 2018 On 6/5/2018 at 3:53 PM, AnnieRuru said: 0.4 http://upaste.me/75d049918e2088402 wow ~ thanks ... having an extra eye is different ... about turning the [BASF+] into player configured buff ... that will be done in another day ... I have an error when i make the plugins: CC showbuff.c showbuff.c: In function ‘status_change_start_post’: showbuff.c:50: warning: suggest parentheses around assignment used as truth value showbuff.c: In function ‘clif_party_info_overload’: showbuff.c:114: error: dereferencing pointer to incomplete type showbuff.c:114: error: invalid application of ‘sizeof’ to incomplete type ‘struct PACKET_ZC_GROUP_LIST_SUB’ showbuff.c:119: error: dereferencing pointer to incomplete type showbuff.c:119: error: ‘partyinfo’ undeclared (first use in this function) showbuff.c:119: error: (Each undeclared identifier is reported only once showbuff.c:119: error: for each function it appears in.) showbuff.c:120: error: dereferencing pointer to incomplete type showbuff.c:125: error: dereferencing pointer to incomplete type showbuff.c:129: error: dereferencing pointer to incomplete type showbuff.c:130: error: dereferencing pointer to incomplete type showbuff.c:131: error: dereferencing pointer to incomplete type showbuff.c:132: error: dereferencing pointer to incomplete type showbuff.c:139: error: dereferencing pointer to incomplete type showbuff.c:139: error: dereferencing pointer to incomplete type showbuff.c:139: error: invalid application of ‘sizeof’ to incomplete type ‘struct PACKET_ZC_GROUP_LIST_SUB’ showbuff.c:148: error: dereferencing pointer to incomplete type showbuff.c:152: error: dereferencing pointer to incomplete type showbuff.c:172: error: dereferencing pointer to incomplete type showbuff.c:182: error: dereferencing pointer to incomplete type showbuff.c:186: error: dereferencing pointer to incomplete type showbuff.c:114: warning: unused variable ‘buf’ make[1]: *** [../../plugins/showbuff.so] Error 1 make[1]: Leaving directory `/home/hercules1234/Hercules/src/plugins' make: *** [plugins] Error 2 Any ideas'? Thx in advance Quote Share this post Link to post Share on other sites
0 Dastgir 1246 Posted July 5, 2018 8 hours ago, xVec said: I have an error when i make the plugins: CC showbuff.c showbuff.c: In function ‘status_change_start_post’: showbuff.c:50: warning: suggest parentheses around assignment used as truth value showbuff.c: In function ‘clif_party_info_overload’: showbuff.c:114: error: dereferencing pointer to incomplete type showbuff.c:114: error: invalid application of ‘sizeof’ to incomplete type ‘struct PACKET_ZC_GROUP_LIST_SUB’ showbuff.c:119: error: dereferencing pointer to incomplete type showbuff.c:119: error: ‘partyinfo’ undeclared (first use in this function) showbuff.c:119: error: (Each undeclared identifier is reported only once showbuff.c:119: error: for each function it appears in.) showbuff.c:120: error: dereferencing pointer to incomplete type showbuff.c:125: error: dereferencing pointer to incomplete type showbuff.c:129: error: dereferencing pointer to incomplete type showbuff.c:130: error: dereferencing pointer to incomplete type showbuff.c:131: error: dereferencing pointer to incomplete type showbuff.c:132: error: dereferencing pointer to incomplete type showbuff.c:139: error: dereferencing pointer to incomplete type showbuff.c:139: error: dereferencing pointer to incomplete type showbuff.c:139: error: invalid application of ‘sizeof’ to incomplete type ‘struct PACKET_ZC_GROUP_LIST_SUB’ showbuff.c:148: error: dereferencing pointer to incomplete type showbuff.c:152: error: dereferencing pointer to incomplete type showbuff.c:172: error: dereferencing pointer to incomplete type showbuff.c:182: error: dereferencing pointer to incomplete type showbuff.c:186: error: dereferencing pointer to incomplete type showbuff.c:114: warning: unused variable ‘buf’ make[1]: *** [../../plugins/showbuff.so] Error 1 make[1]: Leaving directory `/home/hercules1234/Hercules/src/plugins' make: *** [plugins] Error 2 Any ideas'? Thx in advance Your hercules should be atleast updated till 2018.01.14 Quote Share this post Link to post Share on other sites
0 xVec 1 Posted July 5, 2018 9 hours ago, Dastgir said: Your hercules should be atleast updated till 2018.01.14 I see.. I have a very very dummy question. What if i don't want update my production herc and i just want add the PACKET_ZC_GROUP_LIST_SUB support? If I modify this files it should work? https://github.com/HerculesWS/Hercules/search?q=ZC_PROGRESS_ACTOR&unscoped_q=ZC_PROGRESS_ACTOR Quote Share this post Link to post Share on other sites
0 Dastgir 1246 Posted July 6, 2018 11 hours ago, xVec said: I see.. I have a very very dummy question. What if i don't want update my production herc and i just want add the PACKET_ZC_GROUP_LIST_SUB support? If I modify this files it should work? https://github.com/HerculesWS/Hercules/search?q=ZC_PROGRESS_ACTOR&unscoped_q=ZC_PROGRESS_ACTOR Wouldn't recommend that, but you need these changes: https://github.com/HerculesWS/Hercules/commit/499745c3eb6d79573e627433bd77881bd26afb7c Quote Share this post Link to post Share on other sites
0 xVec 1 Posted July 7, 2018 On 7/5/2018 at 9:18 PM, Dastgir said: Wouldn't recommend that, but you need these changes: https://github.com/HerculesWS/Hercules/commit/499745c3eb6d79573e627433bd77881bd26afb7c Thanks, I'll test in my testserver. Quote Share this post Link to post Share on other sites
0 Thinker 2 Posted August 24, 2018 Hi! Changed packets, how can you update @AnnieRuru? Quote Share this post Link to post Share on other sites
Here is this change?
@partybuff (@spb) can display party member's special buffs in party list (Alt+Z)
Buffs are:
Quote
Look like
[BAFS+]Player name
Share this post
Link to post
Share on other sites