Jump to content

Leaderboard

Popular Content

Showing content with the highest reputation on 03/24/19 in all areas

  1. Version 1.0.0

    538 downloads

    Hi, It's been a while.. I was bored and feels good today.. So I will release a free BG script I wrote months ago.. I updated some of its parts like UNITTYPE_ to BL_ to avoid any warning messages on latest rathena console.. but if your using an older ra version, Just search BL_ and replace with UNITTYPE_ .. Enough with the talking, here is how this works.. ( I was about to make a video but I got lazy ) I tested it and it is working (03-24-2019).. I don't think I would support this script further because I will be busy. Well, you are free to edit this as much as you need.. Just don't remove my signature and Don't resell this.. Enjoy and have a great day!
    Free
    3 points
  2. Heya, The following script commands replace addrid and they were initially implemented by Luxuri. The main advantage of these is that they do not attach the players on the current script, allowing an easier code flow. The commands: foreachinserver "<npc_label>" foreachinmap "<npc_label>", "<map_name>" foreachinparty "<npc_label>", <party_id> foreachinarea "<npc_label>", "<map_name>", <x1>, <y1>, <x2>, <y2> foreachinshootablerange "<npc_label>", "<map_name>", <x>, <y>, <range> foreachinguild "<npc_label>", <guild_id> prontera,155,185,3 script Test 77,{ foreachinserver("Test::OnEvent"); foreachinmap("Test::OnEvent", "prontera"); foreachinparty("Test::OnEvent", getcharid(1)); foreachinarea("Test::OnEvent", "this", 153, 182, 159, 177); foreachinshootablerange("Test::OnEvent", "this", 153, 182, 2); foreachinguild("Test::OnEvent", getcharid(2)); end; OnEvent: announce "Attached script to " + strcharinfo(0), 0; end; } For example, for making a script that kicks dead players without using OnPCDieEvent, you could use: prontera,155,185,3 script Test 77,{ initnpctimer; dispbottom "Kicking dead players."; end; OnTimer1000: .kicked = 0; foreachinmap("Test::OnKick", "prontera"); if (.kicked > 0) { announce .kicked + " player(s) have died!", 0; } initnpctimer; end; OnKick: if (HP <= 0) { .kicked++; getitem 501, 1; warp "alberta", 192, 147; percentheal 100, 100; } end; } You can easily make your own foreach methods (for BG, clans, etc). Diff file: diff --git a/src/map/npc.cpp b/src/map/npc.cpp index 647a765..c60a5d7 100644 --- a/src/map/npc.cpp +++ b/src/map/npc.cpp @@ -2224,6 +2224,20 @@ int npc_unload(struct npc_data* nd, bool single) { return 0; } +/// Returns the NPC associated with the specified event label. +struct npc_data* npc_event_label_nd(const char* labelname) +{ + struct event_data* ev = (struct event_data*)strdb_get(ev_db, labelname); + return (ev != NULL ? ev->nd : NULL); +} + +/// Returns the bytecode position that the specified event label refers to. +int npc_event_label_pos(const char* labelname) +{ + struct event_data* ev = (struct event_data*)strdb_get(ev_db, labelname); + return (ev != NULL ? ev->pos : -1); +} + // // NPC Source Files // diff --git a/src/map/npc.hpp b/src/map/npc.hpp index d6a9b97..3049651 100644 --- a/src/map/npc.hpp +++ b/src/map/npc.hpp @@ -1162,6 +1162,9 @@ bool npc_isnear(struct block_list * bl); int npc_get_new_npc_id(void); +struct npc_data* npc_event_label_nd(const char* labelname); +int npc_event_label_pos(const char* labelname); + int npc_addsrcfile(const char* name, bool loadscript); void npc_delsrcfile(const char* name); int npc_parsesrcfile(const char* filepath, bool runOnInit); diff --git a/src/map/script.cpp b/src/map/script.cpp index 180f9ba..5535094 100644 --- a/src/map/script.cpp +++ b/src/map/script.cpp @@ -12230,6 +12230,150 @@ BUILDIN_FUNC(isloggedin) return SCRIPT_CMD_SUCCESS; } +static int script_foreach_sub(TBL_PC* sd, const char* event) +{ + struct npc_data* nd; + int pos; + + if ((nd = npc_event_label_nd(event)) == NULL || (pos = npc_event_label_pos(event)) == -1) + return 0; + + run_script(nd->u.scr.script, pos, sd->bl.id, nd->bl.id); + return 1; +} + +static int script_foreach_sub_va_bl(struct block_list* bl, va_list args) { + const char* event = va_arg(args, const char*); + return script_foreach_sub((TBL_PC*)bl, event); +} + +static int script_foreach_sub_va_sd(TBL_PC* sd, va_list args) { + const char* event = va_arg(args, const char*); + return script_foreach_sub(sd, event); +} + +/// foreachinserver "<npc_label>" +BUILDIN_FUNC(foreachinserver) +{ + const char* event = script_getstr(st, 2); + map_foreachpc(script_foreach_sub_va_sd, event); + return SCRIPT_CMD_SUCCESS; +} + +/// foreachinmap "<npc_label>", "<map_name>" +BUILDIN_FUNC(foreachinmap) +{ + const char* event = script_getstr(st, 2); + const char* mapname = script_getstr(st, 3); + TBL_NPC* nd = map_id2nd(st->oid); + int16 m = (nd && strcmp(mapname, "this") == 0) ? nd->bl.m : map_mapname2mapid(mapname); + + if (m < 0) { + ShowWarning("buildin_foreachinmap: Invalid map name '%s'.\n", mapname); + return SCRIPT_CMD_SUCCESS; + } + + map_foreachinmap(script_foreach_sub_va_bl, m, BL_PC, event); + return SCRIPT_CMD_SUCCESS; +} + +/// foreachinparty "<npc_label>", <party_id> +BUILDIN_FUNC(foreachinparty) +{ + const char* event = script_getstr(st, 2); + int party_id = script_getnum(st, 3); + struct party_data* p; + int i; + + if ((p = party_search(party_id)) == NULL) { + ShowWarning("buildin_foreachinparty: Party id '%d' doesn't exist or is not loaded yet.\n", party_id); + return SCRIPT_CMD_SUCCESS; + } + + for (i = 0; i < MAX_PARTY; ++i) { + TBL_PC* sd; + int char_id = p->party.member[i].char_id; + + if (char_id == 0 || (sd = map_charid2sd(char_id)) == NULL) + continue; + + script_foreach_sub(sd, event); + } + + return SCRIPT_CMD_SUCCESS; +} + +/// foreachinarea "<npc_label>", "<map_name>", <x1>, <y1>, <x2>, <y2> +BUILDIN_FUNC(foreachinarea) +{ + const char* event = script_getstr(st, 2); + const char* mapname = script_getstr(st, 3); + int x1 = script_getnum(st, 4); + int y1 = script_getnum(st, 5); + int x2 = script_getnum(st, 6); + int y2 = script_getnum(st, 7); + TBL_NPC* nd = map_id2nd(st->oid); + int16 m = (nd && strcmp(mapname, "this") == 0) ? nd->bl.m : map_mapname2mapid(mapname); + + if (m < 0) { + ShowWarning("buildin_foreachinarea: Invalid map name '%s'.\n", mapname); + return SCRIPT_CMD_SUCCESS; + } + + map_foreachinarea(script_foreach_sub_va_bl, m, x1, y1, x2, y2, BL_PC, event); + return SCRIPT_CMD_SUCCESS; +} + +/// foreachinshootablerange "<npc_label>", "<map_name>", <x>, <y>, <range> +BUILDIN_FUNC(foreachinshootablerange) +{ + const char* event = script_getstr(st, 2); + const char* mapname = script_getstr(st, 3); + struct block_list bl; + int x1 = script_getnum(st, 4); + int y1 = script_getnum(st, 5); + int range = script_getnum(st, 6); + TBL_NPC* nd = map_id2nd(st->oid); + int16 m = (nd && strcmp(mapname, "this") == 0) ? nd->bl.m : map_mapname2mapid(mapname); + + if (m < 0) { + ShowWarning("buildin_foreachinarea: Invalid map name '%s'.\n", mapname); + return SCRIPT_CMD_SUCCESS; + } + + memset(&bl, 0, sizeof(struct block_list)); + bl.m = m; + bl.x = x1; + bl.y = y1; + + map_foreachinshootrange(script_foreach_sub_va_bl, &bl, range, BL_PC, event); + return SCRIPT_CMD_SUCCESS; +} + +/// foreachinguild "<npc_label>", <guild_id> +BUILDIN_FUNC(foreachinguild) +{ + const char* event = script_getstr(st, 2); + int guild_id = script_getnum(st, 3); + struct guild* g; + int i; + + if ((g = guild_search(guild_id)) == NULL) { + ShowWarning("buildin_foreachinguild: Guild id '%d' doesn't exist or is not loaded yet.\n", guild_id); + return SCRIPT_CMD_SUCCESS; + } + + for (i = 0; i < MAX_GUILD; ++i) { + TBL_PC* sd; + + if (!(sd = g->member[i].sd)) + continue; + + script_foreach_sub(sd, event); + } + + return SCRIPT_CMD_SUCCESS; +} /*========================================== * @@ -24642,6 +24786,13 @@ struct script_function buildin_func[] = { BUILDIN_DEF2(round, "floor", "i"), BUILDIN_DEF(getequiptradability, "i?"), BUILDIN_DEF(mail, "isss*"), + + BUILDIN_DEF(foreachinserver, "s"), + BUILDIN_DEF(foreachinmap, "ss"), + BUILDIN_DEF(foreachinparty, "si"), + BUILDIN_DEF(foreachinarea, "ssiiii"), + BUILDIN_DEF(foreachinshootablerange, "ssiii"), + BUILDIN_DEF(foreachinguild, "si"), #include "../custom/script_def.inc" {NULL,NULL,NULL}, foreach.diff
    1 point
  3. View File Usable Refinery Ores Description Players are able to click on the Ores items to refine the selected equipment. They can refine their Equipment at anywhere anytime they want. Based on requirement of Weapon Level and Type, different ores might be needed as well as Zeny. Preview Submitter Emistry Submitted 01/18/16 Category Utilities Content Author  
    1 point
  4. Probably the map you warped to didn't have the mf_loadevent mapflag. You can use this version anyways. I avoided doing it this way since it can cause a bit of lagging. /* Changelog: v1.1 Added option to debuff players when entering the room. Added command to rotate manually. Remove hiding when quitting room. Added lvl checking on command. v1.1a Removed right curly which made dispell function don't work. Sorry. Added color to the npc name in dialog. Added F_InsertPlural use. v1.2 Added waitingroom with player count. v1.3 Use of pcblock command. */ // You can use this function with other scripts as well. function script dispell { while(.@i++ < SC_SPL_MATK) { if( .@i != SC_WEIGHT50 && .@i != SC_WEIGHT90 && .@i != SC_NOCHAT && .@i != SC_BABY && /* .@i != SC_WEDDING && .@i != SC_XMAS && .@i != SC_SUMMER && .@i != SC_HANBOK && .@i != SC_OKTOBERFEST && */ .@i != SC_JAILED && .@i != SC_EXPBOOST && .@i != SC_ITEMBOOST ) sc_end .@i; } .@i = SC_FEAR; while(.@i++ < SC_AKAITSUKI) sc_end .@i; } prontera,147,172,6 script PvP#0 4_M_SAKRAYROYAL,{ .@n$ = "^3227cd[PvP Room]^000000"; mes .@n$; if(BaseLevel >= .min_lv) { mes "There are ^d40f00"+F_InsertPlural(getmapusers(.map$),"player")+"^000000 inside right now."; mes "Do you want to enter to the room?"; if(.debuff) mes "^8b0d1fBe careful, because every buff you have will be lost upon entering the room.^000000"; next; if(select("Yes.","No, thanks.") == 1) { specialeffect2 F_Rand(EF_STORMKICK1,EF_STORMKICK2,EF_STORMKICK3,EF_STORMKICK6,EF_STORMKICK7); sleep2 600; specialeffect2 F_Rand(EF_SPINMOVE,EF_CASTSPIN2); sleep2 550; if(.debuff) dispell(); warp .map$,0,0; mapannounce .map$,strcharinfo(0)+" has entered the room.",bc_map,0xb50505; if(!.waiting_room) donpcevent "PvP#0::OnWaitingRoom"; } } else { mes "You must be at least level "+.min_lv+" to be able to enter the room."; close; } end; OnInit: // This command can be used to enter the PvP Room. bindatcmd "pvp","PvP#0::OnCommand"; // Command to rotate the room maually. bindatcmd "rotatepvp","PvP#0::OnMinute00",60; // Min LvL to enter the room. .min_lv = 50; // Will players be dispelled upon entering the room? .debuff = false; OnMinute00: OnMinute30: // PvP maps go here. Change them as you wish. setarray .@maps$[0], "guild_vs2","guild_vs3","guild_vs5","pvp_y_1-1","guild_vs4","guild_vs1","arena_room"; // Max amount of times a map can be repeated. 0 = unlimited. .@row = 3; .@size = getarraysize(.@maps$); if(.map$ == "") { // You can edit the room mapflags here. setarray .@mapfl[0], mf_nosave, mf_nodrop, mf_novending, mf_noteleport, mf_noreturn, mf_nowarp, mf_nowarpto, mf_nomemo, mf_nopenalty, mf_nobranch, mf_hidemobhpbar, mf_pvp, mf_pvp_noguild, mf_pvp_noparty, mf_pvp_nocalcrank, mf_loadevent; .@i = getarraysize(.@mapfl); while(.@i--) { .@j = .@size; while(.@j--) setmapflag .@maps$[.@j],.@mapfl[.@i]; } } .@map$ = .map$; .@r = rand(.@size); .map$ = .@maps$[.@r]; if(.@row && .map$ == .@map$) { if(++.row >= .@row) { deletearray .@maps$[.@r],1; .map$ = .@maps$[rand(.@size - 1)]; .row = 0; } } else if(.row) { .row = 0; } if(.map$ != .@map$ && .@map$ != "") { mapwarp .@map$,.map$,0,0; sleep 2500; mapannounce .map$,"The PvP Room has changed!",bc_npc,0xe53a12; } end; OnCommand: .@ins_id = instance_id(); .@m$ = strcharinfo(3); if((!.@ins_id || instance_mapname(.@m$,.@ins_id) == "") && BaseLevel >= .min_lv) { if(.@m$ != .map$) { message strcharinfo(0),"Preparing to enter!"; } else { message strcharinfo(0),"Quitting the room..."; unitstopwalk getcharid(3); //pcblock PCBLOCK_MOVE|PCBLOCK_ATTACK|PCBLOCK_SKILL,true; pcblockmove getcharid(3),true; pcblockskill getcharid(3),true; setoption OPTION_HIDE|OPTION_CLOAK|OPTION_CHASEWALK,false; } .@hp = HP; sleep2 1400; while(.@i++ < 5) { message strcharinfo(0),(6 - .@i)+"..."; sleep2 990; if(HP < .@hp) { message strcharinfo(0),"You can't do this in the middle of a battle."; //pcblock PCBLOCK_MOVE|PCBLOCK_ATTACK|PCBLOCK_SKILL,false; pcblockmove getcharid(3),false; pcblockskill getcharid(3),false; end; } } specialeffect2 F_Rand(EF_STORMKICK1,EF_STORMKICK2,EF_STORMKICK3,EF_STORMKICK6,EF_STORMKICK7); sleep2 600; specialeffect2 F_Rand(EF_SPINMOVE,EF_CASTSPIN2); sleep2 550; if(.@m$ != .map$) { if(.debuff) dispell(); warp .map$,0,0; mapannounce .map$,strcharinfo(0)+" has entered the room.",bc_map,0xb50505; if(!.waiting_room) donpcevent "PvP#0::OnWaitingRoom"; } else { warp "SavePoint",0,0; //pcblock PCBLOCK_MOVE|PCBLOCK_ATTACK|PCBLOCK_SKILL,false; pcblockmove getcharid(3),false; pcblockskill getcharid(3),false; } } else if(BaseLevel < .min_lv) { message strcharinfo(0),"You must be at least level "+.min_lv+" to be able to enter the room."; } else { message strcharinfo(0),"You can't enter the room in the middle of an instance."; } end; OnWaitingRoom: .waiting_room = true; while(true) { .@count = getmapusers(.map$); if(.@count != .@old_count) { .@old_count = .@count; delwaitingroom; waitingroom F_InsertPlural(.@count,"player")+".",0; } sleep 2500; } end; }
    1 point
  5. I'm not sure if this works, but you could test it by making an NPC that sets a bonus2 bDropAddRace,RC_All,5; for the current chacter. bonus_script "<script code>",<duration>{,<flag>{,<type>{,<status_icon>{,<char_id>}}}};
    1 point
  6. Version 2.2.6

    7388 downloads

    !! UPDATE !! If there is still interst in this project, and you really would like a update with better performance. Write me a private message. I would like to renew this, but i dont have any server to test it. Also if no one want a new version, i dont see any reason to rewrite it. -- -- -- -- -- -- -- -- This application is made for windows servers, since it doesn't make much sense to have something like this on a linux system. Login-, Char- and Map-Server gets started without a window. All Output is redirected to this application so you can see all 3 windows in 1 application. Version 2.2.6 is really old, but still have some "nice" features like coloring of [info], [status], etc. Also it counts different messages. (Error, Warning, ...) [How-To] 1. Download the newest Version. 2. Unrar it & Place it where you want. 3. Start the Application and go to "Options". 4. Configurate the Path to your executables. 5. Click on Start. Have fun. [source] I'm sorry. This project is by the time i changed this, about 4,2 years old. After cleaning my github i deleted it without thinking about it. The only thing i can say is.. it was a horrible source code... I'm sorry for all the developers who looked at it. ^^ >> Please, no mirrors without asking. <<
    Free
    1 point
×
×
  • Create New...