n0tttt

Members
  • Content Count

    296
  • Avg. Content Per Day

    0
  • Joined

  • Days Won

    11

Everything posted by n0tttt

  1. You could delete the bindatcmd line, but better use this one since I deleted it altogether: /* 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. */ // You can use this function with other scripts as well. function script dispell { while([email protected]++ < SC_SPL_MATK) { if( [email protected] != SC_WEIGHT50 && [email protected] != SC_WEIGHT90 && [email protected] != SC_NOCHAT && [email protected] != SC_BABY && /* [email protected] != SC_WEDDING && [email protected] != SC_XMAS && [email protected] != SC_SUMMER && [email protected] != SC_HANBOK && [email protected] != SC_OKTOBERFEST && */ [email protected] != SC_JAILED && [email protected] != SC_EXPBOOST && [email protected] != SC_ITEMBOOST ) sc_end [email protected]; } [email protected] = SC_FEAR; while([email protected]++ < SC_AKAITSUKI) sc_end [email protected]; } prontera,147,172,6 script PvP#0 4_M_SAKRAYROYAL,{ [email protected]$ = "^3227cd[PvP Room]^000000"; mes [email protected]$; 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: // 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 [email protected]$[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. [email protected] = 3; [email protected] = getarraysize([email protected]$); if(.map$ == "") { // You can edit the room mapflags here. setarray [email protected][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; [email protected] = getarraysize([email protected]); while([email protected]) { [email protected] = [email protected]; while([email protected]) setmapflag [email protected]$[[email protected]],[email protected][[email protected]]; } } [email protected]$ = .map$; [email protected] = rand([email protected]); .map$ = [email protected]$[[email protected]]; if([email protected] && .map$ == [email protected]$) { if(++.row >= [email protected]) { deletearray [email protected]$[[email protected]],1; .map$ = [email protected]$[rand([email protected] - 1)]; .row = 0; } } else if(.row) { .row = 0; } if(.map$ != [email protected]$ && [email protected]$ != "") { mapwarp [email protected]$,.map$,0,0; sleep 2500; mapannounce .map$,"The PvP Room has changed!",bc_npc,0xe53a12; } end; OnWaitingRoom: .waiting_room = true; while(true) { [email protected] = getmapusers(.map$); if([email protected] != [email protected]_count) { [email protected]_count = [email protected]; delwaitingroom; waitingroom F_InsertPlural([email protected],"player")+".",0; } sleep 2500; } end; }
  2. 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([email protected]++ < SC_SPL_MATK) { if( [email protected] != SC_WEIGHT50 && [email protected] != SC_WEIGHT90 && [email protected] != SC_NOCHAT && [email protected] != SC_BABY && /* [email protected] != SC_WEDDING && [email protected] != SC_XMAS && [email protected] != SC_SUMMER && [email protected] != SC_HANBOK && [email protected] != SC_OKTOBERFEST && */ [email protected] != SC_JAILED && [email protected] != SC_EXPBOOST && [email protected] != SC_ITEMBOOST ) sc_end [email protected]; } [email protected] = SC_FEAR; while([email protected]++ < SC_AKAITSUKI) sc_end [email protected]; } prontera,147,172,6 script PvP#0 4_M_SAKRAYROYAL,{ [email protected]$ = "^3227cd[PvP Room]^000000"; mes [email protected]$; 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 [email protected]$[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. [email protected] = 3; [email protected] = getarraysize([email protected]$); if(.map$ == "") { // You can edit the room mapflags here. setarray [email protected][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; [email protected] = getarraysize([email protected]); while([email protected]) { [email protected] = [email protected]; while([email protected]) setmapflag [email protected]$[[email protected]],[email protected][[email protected]]; } } [email protected]$ = .map$; [email protected] = rand([email protected]); .map$ = [email protected]$[[email protected]]; if([email protected] && .map$ == [email protected]$) { if(++.row >= [email protected]) { deletearray [email protected]$[[email protected]],1; .map$ = [email protected]$[rand([email protected] - 1)]; .row = 0; } } else if(.row) { .row = 0; } if(.map$ != [email protected]$ && [email protected]$ != "") { mapwarp [email protected]$,.map$,0,0; sleep 2500; mapannounce .map$,"The PvP Room has changed!",bc_npc,0xe53a12; } end; OnCommand: [email protected]_id = instance_id(); [email protected]$ = strcharinfo(3); if(([email protected]_id || instance_mapname([email protected]$,[email protected]_id) == "") && BaseLevel >= .min_lv) { if([email protected]$ != .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; } [email protected] = HP; sleep2 1400; while([email protected]++ < 5) { message strcharinfo(0),(6 - [email protected])+"..."; sleep2 990; if(HP < [email protected]) { 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([email protected]$ != .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) { [email protected] = getmapusers(.map$); if([email protected] != [email protected]_count) { [email protected]_count = [email protected]; delwaitingroom; waitingroom F_InsertPlural([email protected],"player")+".",0; } sleep 2500; } end; }
  3. You don't have the last version of rAthena. But you can change this line: getmapxy [email protected]$,[email protected],[email protected],BL_NPC; to: getmapxy [email protected]$,[email protected],[email protected],UNITTYPE_NPC;
  4. payon,147,229,4 script Test#HPbar 1_F_MARIA,{ if (.HP_Bar == false) { .HP_Bar = true; .mobGID = monster ("payon",148,226,"[T] HP Test",1031,1,strnpcinfo(0)+"::OnDie"); setunitdata .mobGID,UMOB_MAXHP,4000; setunitdata .mobGID,UMOB_HP,4000; [email protected] = getmapunits(BL_PC, "payon", [email protected]); for ([email protected] = 0; [email protected] < [email protected]; [email protected]++) { attachrid [email protected][[email protected]]; addtimer(0,strnpcinfo(0)+"::OnHPBar"); } } end; OnDie: .HP_Bar = false; end; OnHPBar: [email protected]_MAXHP = getunitdata (.mobGID,UMOB_MAXHP); while (.HP_Bar != false) { [email protected]_HP = getunitdata (.mobGID,UMOB_HP); [email protected]_HP = (@.U_HP*100)/[email protected]_MAXHP; cutin([email protected]_HP+"", 1); sleep2 100; } cutin("0_hpbar", 1); sleep2 5000; //Delay to hide HP Bar cutin("", 255); end; } This could be done for every MvP, but the way it's done (by adding a script and an attach every player on the map, adding new players on the map, and show them the HP every 100ms) would generate a lot of lag. I'd recommend using this for a special event mostly, and even that would be resource-intensive. Another way could be adding only the characters who attack the MvP with a custom label like OnAttack. I think there's such a label floating around boards.
  5. Something like this? - script Hourly_Rewards -1,{ OnAddMinute: #online_time++; if(#online_time % 5 == 0) { dispbottom "Time online: "+Time2Str(#online_time*60 + gettimetick(2))+"."; if(#online_time % 60 == 0) { [email protected]_points = #hourly_points; [email protected] = ((#online_time / 60) + 5)%6 + 1; switch([email protected]) { case 1: #hourly_points += 10; break; case 2: #hourly_points += 20; break; case 3: #hourly_points += 30; break; case 4: #hourly_points += 10; break; case 5: #hourly_points += 10; break; case 6: #hourly_points += 30; break } dispbottom "You won "+(#hourly_points - [email protected]_points)+" points. Current amount:"+F_InsertComma(#hourly_points)+"."; } } OnPCLoginEvent: addtimer 60000,"Hourly_Rewards::OnAddMinute"; end; }
  6. n0tttt

    R> Map Access

    I didn't read completely. In any case, he can disable every NPC, disable every outside player, and disable every item or skill which might warp players out of there. Something like this? - script Event_Novice -1,{ bindatcmd "startnovice","Event_Novice::OnStart"; bindatcmd "endnovice","Event_Novice::OnEnd"; end; OnStart: setmapflag "new_1-1",mf_noexp; setmapflag "new_1-1",mf_nowarp; setmapflag "new_1-1",mf_nowarpto; setmapflag "new_1-1",mf_noskill; setmapflag "new_1-1",mf_noitemconsumption; setmapflag "new_1-1",mf_loadevent; .size = getunits(BL_NPC,"new_1-1",.npc$); freeloop true; for([email protected] = 0;[email protected] < .size;[email protected]++) disablenpc .npc$[[email protected]]; /* [email protected] = getunits(BL_MOB,"new_1-1",[email protected]); for([email protected] = 0;[email protected] < [email protected];[email protected]++) unitkill [email protected][[email protected]]; */ [email protected] = getunits(BL_PC,"new_1-1",[email protected]$); for([email protected] = 0;[email protected] < [email protected];[email protected]++) { if(readparam(Class,[email protected]$[[email protected]]) != Job_Novice) warp "SavePoint",0,0,getcharid(0,[email protected]$[[email protected]]); } freeloop false; end; OnEnd: for([email protected] = 0;[email protected] < .size;[email protected]++) enablenpc .npc$[[email protected]]; deletearray .npc$; .size = 0; removemapflag "new_1-1",mf_noexp; removemapflag "new_1-1",mf_nowarp; removemapflag "new_1-1",mf_nowarpto; removemapflag "new_1-1",mf_noskill; removemapflag "new_1-1",mf_noitemconsumption; removemapflag "new_1-1",mf_loadevent; end; OnPCLoadMapEvent: if(strcharinfo(3) == "new_1-1" && Class != Job_Novice) warp "SavePoint",0,0; end; } I don't know what kind of event it is (GM-controlled?), but if he needs some NPCs, he can just add them with enablenpc. Forgot to mention why I added noexp. In case some people create party or guild. Actually don't remember how it works for guilds, but if it does like I think, player couldn't lvl up then couldn't join a guild and then escape by Emergency Recall or something like that. Anyways I don't know what kind of event is this (Zombie event?).
  7. n0tttt

    R> Map Access

    It also checks on warps. npc.cpp: switch(mapdata->npc[i]->subtype) { case NPCTYPE_WARP: if ((!mapdata->npc[i]->trigger_on_hidden && (pc_ishiding(sd) || (sd->sc.count && sd->sc.data[SC_CAMOUFLAGE]))) || pc_isdead(sd)) break; // hidden or dead chars cannot use warps if (!pc_job_can_entermap((enum e_job)sd->status.class_, map_mapindex2mapid(mapdata->npc[i]->u.warp.mapindex), sd->group_level)) break; if(sd->count_rewarp > 10){ ShowWarning("Prevented infinite warp loop for player (%d:%d). Please fix NPC: '%s', path: '%s'\n", sd->status.account_id, sd->status.char_id, mapdata->npc[i]->exname, mapdata->npc[i]->path); sd->count_rewarp=0; break; } pc_setpos(sd,mapdata->npc[i]->u.warp.mapindex,mapdata->npc[i]->u.warp.x,mapdata->npc[i]->u.warp.y,CLR_OUTSIGHT); break;
  8. - script Sample -1,{ OnPCLoginEvent: mes "[Points Viewer]"; mes "Hello "+strcharinfo(0); mes ""+#CASHPOINTS+" Cash and "+#KAFRAPOINTS+" Free Cash."; mes "-----------------------------------"; mes "Time VIP left"; mes Time2Str(vip_status(VIP_STATUS_REMAINING) + gettimetick(2)); mes "-----------------------------------"; close; } Or Time2Str(VIP_STATUS_EXPIRE)
  9. n0tttt

    R> Map Access

    db/import/job_noenter_map.txt JOB_NOVICE,1,100 Something like this?
  10. Like this? prontera,155,175,4 script TestScript 69,{ setarray [email protected]_id, 1002, 1004, 1005; setarray [email protected]_qt, 1, 3, 8; setarray [email protected]_req, 7, 8, 10; for(; [email protected] < getarraysize([email protected]_id); [email protected]++){ if([email protected]_qt[[email protected]] >= [email protected]_req[[email protected]]) { dispbottom "You hunted down all the monsters on that map."; } else { dispbottom "You still have to hunt down the following monsters:"; dispbottom "MonsterID: "[email protected]_id[[email protected]]+" Amount: "[email protected]_qt[[email protected]]+" Required quantity: "[email protected]_req[[email protected]]; [email protected] += ([email protected]_req[[email protected]] - [email protected]_qt[[email protected]]); } } if([email protected]) dispbottom "You still need to hunt "+F_InsertPlural([email protected],"monster")+"."; end; }
  11. - script Lucky_Draw -1,{ OnMinute00: [email protected]_id = 512; [email protected]_amt = 5; if(gettime(DT_HOUR) % 2 == 0) { [email protected] = getunits(BL_PC,[email protected]); [email protected] = [email protected][rand([email protected])]; attachrid [email protected]; announce strcharinfo(0)+" has won the Lucky Draw ("+F_InsertPlural([email protected]_amt,getitemname([email protected]_id))+").",bc_all; if(checkweight([email protected]_id,[email protected]_amt)) getitem [email protected]_id,[email protected]_amt; else mail getcharid(0),"Lucky Draw","Prize","Heres the Lucky Draw Prize",0,[email protected]_id,[email protected]_amt; } end; }
  12. Update to last version of rAthena (you need this commit https://github.com/rathena/rathena/commit/1f97beae277a95bf7ede02e582a108b8802bb46c), and also last version of the script.
  13. OnClock<hour><minute>: OnMinute<minute>: OnHour<hour>: On<weekday><hour><minute>: OnDay<month><day>: This will execute when the server clock hits the specified date or time. Hours and minutes are given in military time. ('0105' will mean 01:05 AM). Weekdays are Sun,Mon,Tue,Wed,Thu,Fri,Sat. Months are 01 to 12, days are 01 to 31. Remember the zero. OnWed1930:
  14. n0tttt

    Two questions.

    1) Edit db/pre-re or db/re achievement_db.yml 2) Test this: skill.cpp Change: /*========================================== * Does cast-time reductions based on dex, item bonuses and config setting *------------------------------------------*/ int skill_castfix(struct block_list *bl, uint16 skill_id, uint16 skill_lv) { double time = skill_get_cast(skill_id, skill_lv); nullpo_ret(bl); #ifndef RENEWAL_CAST { struct map_session_data *sd = BL_CAST(BL_PC, bl); struct status_change *sc = status_get_sc(bl); int reduce_cast_rate = 0; uint8 flag = skill_get_castnodex(skill_id); // Calculate base cast time (reduced by dex) if (!(flag&1)) { int scale = battle_config.castrate_dex_scale - status_get_dex(bl); if (scale > 0) // not instant cast time = time * (float)scale / battle_config.castrate_dex_scale; else return 0; // instant cast } // Calculate cast time reduced by item/card bonuses if (sd) { if (!(flag&4) && sd->castrate != 100) reduce_cast_rate += 100 - sd->castrate; // Skill-specific reductions work regardless of flag for (const auto &it : sd->skillcastrate) { if (it.id == skill_id) { time += time * it.val / 100; break; } } } // These cast time reductions are processed even if the skill fails if (sc && sc->count) { // Magic Strings stacks additively with item bonuses if (!(flag&2) && sc->data[SC_POEMBRAGI]) reduce_cast_rate += sc->data[SC_POEMBRAGI]->val2; // Foresight halves the cast time, it does not stack additively if (sc->data[SC_MEMORIZE]) { if(!(flag&2)) time -= time * 50 / 100; // Foresight counter gets reduced even if the skill is not affected by it if ((--sc->data[SC_MEMORIZE]->val2) <= 0) status_change_end(bl, SC_MEMORIZE, INVALID_TIMER); } } time = time * (1 - (float)reduce_cast_rate / 100); } #endif // config cast time multiplier if (battle_config.cast_rate != 100) time = time * battle_config.cast_rate / 100; // return final cast time time = max(time, 0); //ShowInfo("Castime castfix = %f\n",time); return (int)time; } to: /*========================================== * Does cast-time reductions based on dex, item bonuses and config setting *------------------------------------------*/ int skill_castfix(struct block_list *bl, uint16 skill_id, uint16 skill_lv) { double time = skill_get_cast(skill_id, skill_lv); nullpo_ret(bl); struct map_session_data *sd = BL_CAST(BL_PC, bl); struct status_change *sc = status_get_sc(bl); int reduce_cast_rate = 0; uint8 flag = skill_get_castnodex(skill_id); if(sd) { if(sd->class_ & ~MAPID_THIRDMASK) { // Calculate base cast time (reduced by dex) if (!(flag&1)) { int scale = battle_config.castrate_dex_scale - status_get_dex(bl); if (scale > 0) // not instant cast time = time * (float)scale / battle_config.castrate_dex_scale; else return 0; // instant cast } if (!(flag&4) && sd->castrate != 100) reduce_cast_rate += 100 - sd->castrate; // Skill-specific reductions work regardless of flag for (const auto &it : sd->skillcastrate) { if (it.id == skill_id) { time += time * it.val / 100; break; } } // These cast time reductions are processed even if the skill fails if (sc && sc->count) { // Magic Strings stacks additively with item bonuses if (!(flag&2) && sc->data[SC_POEMBRAGI]) reduce_cast_rate += sc->data[SC_POEMBRAGI]->val2; // Foresight halves the cast time, it does not stack additively if (sc->data[SC_MEMORIZE]) { if(!(flag&2)) time -= time * 50 / 100; // Foresight counter gets reduced even if the skill is not affected by it if ((--sc->data[SC_MEMORIZE]->val2) <= 0) status_change_end(bl, SC_MEMORIZE, INVALID_TIMER); } } time = time * (1 - (float)reduce_cast_rate / 100); } } // config cast time multiplier if (battle_config.cast_rate != 100) time = time * battle_config.cast_rate / 100; // return final cast time time = max(time, 0); //ShowInfo("Castime castfix = %f\n",time); return (int)time; }
  15. Could it be because this other NPC's (malangdo,218,123,1 script Namis#invest 545,4,4) OnTouch gets executed while you're on the other and sets the player current NPC id to 0 with its "end"? Test removing this for now: OnTouch: if (rand(2)) emotion ET_SLEEPY; else specialeffect EF_SLEEPATTACK; end;
  16. Script: // Here goes your view id to remove. [email protected]_id = 999; setarray [email protected][0],LOOK_HEAD_BOTTOM,LOOK_HEAD_TOP,LOOK_HEAD_MID; for([email protected] = EQI_HEAD_LOW;[email protected] <= EQI_HEAD_TOP;[email protected]++) { [email protected] = getiteminfo(getequipid([email protected]),11); if(getlook([email protected][[email protected] - 4]) == [email protected]_id) setlook [email protected][[email protected] - 4],[email protected]; } Or querys: UPDATE `char` SET `head_top` = '0' WHERE `head_top` = '999' UPDATE `char` SET `head_mid` = '0' WHERE `head_mid` = '999' UPDATE `char` SET `head_bottom` = '0' WHERE `head_bottom` = '999' I don't know how these might work, they may reset the view ids and players might have to relog (they could have no view id even if they have a poring hat, for example).
  17. //===== rAthena Script ======================================= //= Job Master //===== Description: ========================================= //= A fully functional job changer. //===== Additional Comments: ================================= //= 1.0 Initial script. [Euphy] //= 1.1 Fixed reset on Baby job change. //= 1.2 Added Expanded Super Novice support and initial Kagerou/Oboro support. //= 1.3 Kagerou/Oboro added. //= 1.4 Rebellion added. //= 1.5 Added option to disable RebirthClass. [mazvi] //= 1.6 Added option to get job related equipment on change. [Braniff] //= 1.7 Readability changes. Also added BabyExpanded and BabySummoner classes. [Jey] //= 1.8 Added option to disable Baby Novice Only but Baby Class can be Enabled [mazvi] //= 1.9 Migrate/Integrate to Global Functions Platinum Skills. [mazvi] //============================================================ prontera,153,193,6 script Job Master 123,{ function Get_Job_Equip; // Checks if the Player has the required level. // closes if not, returns if yes function Require_Level { if (BaseLevel < getarg(0) || JobLevel < getarg(1)) { [email protected] = getarg(0) - BaseLevel; [email protected] = getarg(1) - JobLevel; mes "Level requirement:"; mes ((getarg(0)>1)? "^bb0000"+getarg(0)+"^000000 (^bb0000Base^000000) / ":"")+"^00bb00"+ getarg(1)+"^000000 (^00bb00Job^000000)"; mes "You need " + (([email protected] > 0) ? "^bb0000"[email protected]+"^000000 more base levels " + (([email protected] > 0) ? "and " : "") : "") + (([email protected] > 0) ? "^00bb00"[email protected]+"^000000 more job levels " : "") + "to continue."; close; } return; } // Checks if the given eac is a baby class function Is_Baby { return ((getarg(0, eaclass())&EAJL_BABY)>0); } // Checks if the player can change to third class. // Note: This does not include the level checks. function Can_Change_Third { // To change to third class you either need to be: // * Second Class // * Transcendent Second Class // * Baby Second Class if( !.ThirdClass ) return false; // Third job change disabled if( !(eaclass()&EAJL_2) ) return false; // Not second Class if( eaclass()&EAJL_UPPER ) return false; // No Rebirth 3rd. if( eaclass()&EAJL_THIRD ) return false; // Already Third Class if( roclass(eaclass()|EAJL_THIRD) < 0 ) return false; // Job has no third Class if( (eaclass()&EAJ_UPPERMASK) == EAJ_SUPER_NOVICE ) return false; // Exp. Super Novice equals 3rd Cls, but has it's own case if( Is_Baby() && (!.BabyClass || !.BabyThird) ) return false; // No Baby (Third) change allowed return true; } function Can_Rebirth { // To rebirth, you need to be: // * Second Class if( !.RebirthClass ) return false; // Rebirth disabled if( !(eaclass()&EAJL_2) ) return false; // Not second Class if( eaclass()&EAJL_UPPER ) return false; // Already Rebirthed if( roclass(eaclass()|EAJL_UPPER) < 0 ) return false; // Job has no transcended class if( Is_Baby() && !.BabyClass ) return false; // No Baby changes allowed return true; } // Checks if the given eac is a first class function Is_First_Cls { return (getarg(0) <= EAJ_TAEKWON); } function Check_Riding { // Note: Why we should always check for Riding: // Mounts are considered as another class, which // would make this NPC bigger just to handle with // those special cases. if (checkfalcon() || checkcart() || checkriding() || ismounting()) { mes "Please remove your " + ((checkfalcon()) ? "falcon" : "") + ((checkcart()) ? "cart" : "") + ((checkriding()) ? "Peco" : "") + ((ismounting()) ? "mount" : "") + " before proceeding."; close; } return; } function Check_SkillPoints { if (.SkillPointCheck && SkillPoint) { mes "Please use all your skill points before proceeding."; close; } return; } // addJobOptions is essentially the same like // setarray [email protected][getarraysize([email protected])],opt1,opt2,...; // It's just easier to read, since we're using it very often function Job_Options { [email protected] = getargcount(); [email protected]_size = getarraysize(getarg(0)); for( [email protected] = 1; [email protected] < [email protected]; [email protected]++) { setarray getelementofarray(getarg(0), [email protected]_size++),getarg([email protected]); } } // Begin of the NPC mes .NPCName$; Check_Riding(); Check_SkillPoints(); // initialisation deletearray [email protected]_opt[0],getarraysize([email protected]_opt); [email protected] = eaclass(); [email protected]_possible = Can_Change_Third(); [email protected]_possible = Can_Rebirth(); [email protected]_eac = [email protected]&EAJ_BASEMASK; [email protected]_eac = [email protected]&EAJ_UPPERMASK; // Note: These are already set in pc.c // BaseClass = roclass([email protected]&EAJ_BASEMASK) which is the players First Class // BaseJob = roclass([email protected]&EAJ_UPPERMASK) which is the players Second Class //dispbottom "Debug: eac ("[email protected]+"), third ("[email protected]_possible+"), rebirth("[email protected]_possible+"), BaseClass ("+BaseClass+"), BaseJob ("+BaseJob+")"; // From here on the jobmaster checks the current class // and fills the the array `[email protected]_opt` with possible // job options for the player. if( [email protected]_possible ) { // Rebirth option (displayed on the top of the menu) Require_Level(.Req_Rebirth[0], .Req_Rebirth[1]); Job_Options([email protected]_opt, Job_Novice_High); } if( [email protected]_possible ) { // Third Job change (displayed below rebirth) Require_Level(.Req_Third[0], .Req_Third[1]); Job_Options([email protected]_opt, roclass([email protected]|EAJL_THIRD)); } if (.SecondExpanded && ([email protected]&EAJ_UPPERMASK) == EAJ_SUPER_NOVICE && // is Super Novice !(eaclass()&EAJL_THIRD) ) { // not already Expanded SN // (Baby) Super Novice to Expanded (Baby) Super Novice if( !Is_Baby([email protected]) || (.BabyClass && .BabyExpanded) ) { // .BabyClass & .BabyExpanded must be enabled if the is a baby Require_Level(.Req_Exp_SNOVI[0], .Req_Exp_SNOVI[1]); Job_Options([email protected]_opt,roclass([email protected]|EAJL_THIRD)); // Expanded SN is "third" cls } } if (.SecondExpanded && (([email protected]&(~EAJL_BABY)) == EAJ_NINJA || // is (Baby) Ninja ([email protected]&(~EAJL_BABY)) == EAJ_GUNSLINGER)) { // is (Baby) Gunslinger // (Baby) Ninja to (Baby) Kagerou / Oboro // (Baby) Gunslinger to (Baby) Rebellion if( !Is_Baby([email protected]) || (.BabyClass && .BabyExpanded) ) { // .BabyClass & .BabyExpanded must be enabled if the is a baby Require_Level(.Req_Exp_NJ_GS[0], .Req_Exp_NJ_GS[1]); // Kagerou, Oboro, Rebellion are considered as a 2-1 class Job_Options([email protected]_opt, roclass([email protected]|EAJL_2_1)); } } // Player is Job_Novice, Job_Novice_High or Job_Baby if ([email protected]_eac == EAJ_NOVICE && [email protected]_eac != EAJ_SUPER_NOVICE) { // MAPID_NOVICE, MAPID_SUPER_NOVICE, MAPID_NOVICE_HIGH, MAPID_BABY Require_Level(.Req_First[0], .Req_First[1]); switch(Class) { case Job_Novice: // First job change Job_Options([email protected]_opt,Job_Swordman, Job_Mage, Job_Archer, Job_Acolyte, Job_Merchant, Job_Thief, Job_Super_Novice, Job_Taekwon, Job_Gunslinger, Job_Ninja); if( .BabyNovice ) Job_Options([email protected]_opt, Job_Baby); break; case Job_Novice_High: // Job change after rebirth if( .LastJob && lastJob ) Job_Options([email protected]_opt, roclass((eaclass(lastJob)&EAJ_BASEMASK)|EAJL_UPPER)); else Job_Options([email protected]_opt, Job_Swordman_High, Job_Mage_High, Job_Archer_High, Job_Acolyte_High, Job_Merchant_High, Job_Thief_High); break; case Job_Baby: if( !.BabyClass ) break; // First job change as a baby Job_Options([email protected]_opt, Job_Baby_Swordman, Job_Baby_Mage, Job_Baby_Archer,Job_Baby_Acolyte, Job_Baby_Merchant, Job_Baby_Thief); if( .BabyExpanded ) Job_Options([email protected]_opt, Job_Super_Baby, Job_Baby_Taekwon, Job_Baby_Gunslinger, Job_Baby_Ninja); if( .BabySummoner ) Job_Options([email protected]_opt, Job_Baby_Summoner); break; default: mes "An error has occurred."; close; } } else if( Is_First_Cls([email protected]) || // First Class Is_First_Cls([email protected]&(~EAJL_UPPER)) || // Trans. First Cls (.BabyClass && Is_First_Cls([email protected]&(~EAJL_BABY))) ) { // Baby First Cls // Player is First Class (not Novice) // most jobs should have two options here (2-1 and 2-2) [email protected] = roclass([email protected]|EAJL_2_1); // 2-1 [email protected] = roclass([email protected]|EAJL_2_2); // 2-2 // dispbottom "Debug: Classes: class1 ("[email protected]+"), class2 ("[email protected]+")"; if(.LastJob && lastJob && ([email protected]&EAJL_UPPER)) { // Player is rebirth Cls and linear class changes are enforced Require_Level(.Req_Second[0], .Req_Second[1]); Job_Options([email protected]_opt, lastJob + Job_Novice_High); } else { // Class is not enforced, player can decide. if( [email protected] > 0 ) { // 2-1 Require_Level(.Req_Second[0], .Req_Second[1]); Job_Options([email protected]_opt, [email protected]); } if( [email protected] > 0 ) { // 2-2 Require_Level(.Req_Second[0], .Req_Second[1]); Job_Options([email protected]_opt, [email protected]); } } } // Displaying the Job Menu defined by [email protected]_opt. // [email protected]_opt should not be changed below this line. function Job_Menu; Job_Menu([email protected]_opt); close; // Displays the job menu function Job_Menu { // getarg(0) is the [email protected]_opt array holding all available job changes. function Confirm_Change; while(true) { [email protected]_cnt = getarraysize(getarg(0)); if( [email protected]_cnt <= 0 ) { mes "No more jobs are available."; close; } [email protected] = 0; // Just a single job class given, no select needed if ([email protected]_cnt > 1) { // Multiple job classes given. Select one and save it to [email protected] // After that confirm [email protected] mes "Select a job."; [email protected]$ = ""; for ([email protected] = 0; [email protected] < [email protected]_cnt; [email protected]++) { if( getelementofarray(getarg(0), [email protected]) == Job_Novice_High) [email protected]$ = "^0055FFRebirth^000000"; else [email protected]$ = jobname(getelementofarray(getarg(0), [email protected])); [email protected]$ = [email protected]$ + " ~ " + [email protected]$ + ":"; } [email protected]$ = [email protected]$+" ~ ^777777Cancel^000000"; [email protected] = select([email protected]$) - 1; if( [email protected] < 0 || [email protected] >= [email protected]_cnt ) close; next; mes .NPCName$; } [email protected] = getelementofarray(getarg(0), [email protected]); if (([email protected] == Job_Super_Novice || [email protected] == Job_Super_Baby) && BaseLevel < .SNovice) { // Special Level Requirement because Super Novice and // Super Baby can both be selected in one of the first class // changes. That's why the Level Requirement is after and not before // the selection. mes "A base level of " + .SNovice + " is required to turn into a " + jobname([email protected]) + "."; return; } // Confirm the Class Confirm_Change([email protected], [email protected]_cnt > 1); next; mes .NPCName$; } return; } // Executes the actual jobchange and closes. function Job_Change { [email protected]_cls = getarg(0); next; mes .NPCName$; mes "You are now " + callfunc("F_InsertArticle", jobname([email protected]_cls)) + "!"; if ([email protected]_cls == Job_Novice_High && .LastJob) lastJob = Class; // Saves the lastJob for rebirth jobchange [email protected]_cls; if ([email protected]_cls == Job_Novice_High) resetlvl(1); else if ([email protected]_cls == Job_Baby) { resetstatus; resetskill; set SkillPoint,0; } specialeffect2 EF_ANGEL2; specialeffect2 EF_ELECTRIC; if (.Platinum) callfunc "F_GetPlatinumSkills"; if (.GetJobEquip) Get_Job_Equip(); close; // Always closes after the change } function Confirm_Change { // Player confirms he want to change into [email protected] [email protected] = getarg(0, -1); [email protected] = getarg(1, false); if( [email protected] < 0 ) { mes "Unknown Class Error."; close; } mes "Do you want to change into ^0055FF"+jobname([email protected])+"^000000 class?"; [email protected]_option$ = " ~ Change into ^0055FF"+jobname([email protected])+"^000000 class"; if( [email protected] == Job_Novice_High) [email protected]_option$ = " ~ ^0055FFRebirth^000000"; if (select([email protected]_option$+": ~ ^777777" + (([email protected]) ?"Go back" : "Cancel") + "^000000") == 1) { Job_Change([email protected]); } if ([email protected]) close; // "Cancel" pressed return; } // Function which gives a job related item to the player // the items are the rewards from the original job change quests function Get_Job_Equip { // Note: The item is dropping, when the player can't hold it. // But that's better than not giving the item at all. [email protected] = eaclass(); if( [email protected]&EAJL_THIRD ) { // Third Class Items getitem 2795,1; // Green Apple Ring for every 3rd Class switch(BaseJob) { // BaseJob of Third Cls // For Normal Third, Baby Third and Transcended Third Cls case Job_Knight: getitem 5746,1; break; // Rune Circlet [1] case Job_Wizard: getitem 5753,1; break; // Magic Stone Hat [1] case Job_Hunter: getitem 5748,1; break; // Sniper Goggle [1] case Job_Priest: getitem 5747,1; break; // Mitra [1] case Job_Blacksmith: getitem 5749,1; break; // Driver Band [1] case Job_Assassin: getitem 5755,1; break; // Silent Executor [1] case Job_Crusader: getitem 5757,1; break; // Dip Schmidt Helm [1] case Job_Sage: getitem 5756,1; break; // Wind Whisper [1] case Job_Bard: getitem 5751,1; break; // Maestro Song's Hat [1] case Job_Dancer: getitem 5758,1; break; // Dying Swan [1] case Job_Monk: getitem 5754,1; break; // Blazing Soul [1] case Job_Alchemist: getitem 5752,1; break; // Midas Whisper[1] case Job_Rogue: getitem 5750,1; // Shadow Handicraft [1] getitem 6121,1; // Makeover Brush getitem 6122,1; break; // Paint Brush } } else if ([email protected]&EAJL_2) { // Second Class (And not Third Class) switch(BaseJob) { // Second Class case Job_Knight: getitem 1163,1; break; // Claymore [0] case Job_Priest: getitem 1522,1; break; // Stunner [0] case Job_Wizard: getitem 1617,1; break; // Survivor's Rod [0] case Job_Blacksmith: getitem 1360,1; break; // Two-Handed-Axe [1] case Job_Hunter: getitem 1718,1; break; // Hunter Bow [0] case Job_Assassin: getitem 1254,1; break; // Jamadhar [0] case Job_Crusader: getitem 1410,1; break; // Lance [0] case Job_Monk: getitem 1807,1; break; // Fist [0] case Job_Sage: getitem 1550,1; break; // Book [3] case Job_Rogue: getitem 1222,1; break; // Damascus [1] case Job_Alchemist: getitem 1126,1; break; // Saber [2] case Job_Bard: getitem 1907,1; break; // Guitar [0] case Job_Dancer: getitem 1960,1; break; // Whip [1] case Job_Super_Novice: getitem 1208,1; break; // Main Gauche [4] case Job_Gunslinger: getitem 13101,1; break; // Six Shooter [2] case Job_Ninja: getitem 13010,1; break; // Asura [2] case Job_Star_Gladiator: getitem 1550,1; break; // Book [3] case Job_Soul_Linker: getitem 1617,1; break; // Survivor's Rod [0] } } else { // Neither Second or Third Cls // => First Cls or not covered by the switch switch(BaseClass) { // First Class case Job_Swordman: getitem 1108,1; break; // Blade [4] case Job_Mage: getitem 1602,1; break; // Rod [4] case Job_Archer: getitem 1705,1; break; // Composite Bow [4] case Job_Acolyte: getitem 1505,1; break; // Mace [4] case Job_Merchant: getitem 1302,1; break; // Axe [4] case Job_Thief: getitem 1208,1; break; // Main Gauche [4] } } return; } OnInit: // Initialisation, do not edit these .NPCName$ = "[Job Master]"; // Settings .ThirdClass = true; // Enable third classes? .RebirthClass = true; // Enable rebirth classes? .SecondExpanded = true; // Enable new expanded second classes: Ex. Super Novice, Kagerou/Oboro, Rebellion? .BabyNovice = true; // Enable Baby novice classes? Disable it if you like player must have parent to get job baby. .BabyClass = true; // Enable Baby classes? .BabyThird = true; // Enable Baby third classes? .BabyExpanded = true; // Enable Baby Expanded classes: Ex. Baby Ninja, Baby Taekwon, etc. .BabySummoner = true; // Enable Baby Summoner? .LastJob = true; // Enforce linear class changes? .SkillPointCheck = true; // Force player to use up all skill points? .Platinum = true; // Get platinum skills automatically? .GetJobEquip = false; // Get job equipment (mostly weapons) on job change? // Level Requirements setarray .Req_First[0],1,10; // Minimum base level, job level to turn into 1st class setarray .Req_Second[0],1,40; // Minimum base level, job level to turn into 2nd class setarray .Req_Rebirth[0],99,50; // Minimum base level, job level to rebirth setarray .Req_Third[0],99,50; // Minimum base level, job level to change to third class setarray .Req_Exp_NJ_GS[0],99,70; // Minimum base level, job level to turn into Expanded Ninja and Gunslinger setarray .Req_Exp_SNOVI[0],99,99; // Minimum base level, job level to turn into Expanded Super Novice .SNovice = 45; // Minimum base level to turn into Super Novice // Setting adjustments by PACKETVER if( PACKETVER < 20161207 ) { if( .BabyExpanded ) debugmes "jobmaster: BabyExpanded is disabled due to outdated PACKETVER."; if( .BabySummoner ) debugmes "jobmaster: BabySummoner is disabled due to outdated PACKETVER."; .BabyExpanded = false; .BabySummoner = false; } end; }
  18. If you don't have a problem with the NPC moving anywhere and then other players unable to do the quest until the NPC arrives, then... if(.m$ == "") { getmapxy .m$,.x,.y,UNITTYPE_NPC; doevent strnpcinfo(0)+"::OnFollow"; } end; OnFollow: [email protected]_id = getnpcid(0); [email protected] = 10*60/2; while([email protected] < [email protected] && playerattached()) { getmapxy [email protected]$,[email protected],[email protected],UNITTYPE_PC; getmapxy [email protected]$,[email protected],[email protected],UNITTYPE_NPC; [email protected] = distance([email protected],[email protected],[email protected],[email protected]); getfreecell [email protected]$,[email protected],[email protected],[email protected],[email protected],2,2,1|4; if([email protected] > 14 || [email protected]$ != [email protected]$) unitwarp [email protected]_id,[email protected]$,[email protected],[email protected]; else npcwalkto [email protected],[email protected]; [email protected]++; sleep2 2000; } unitwarp [email protected]_id,.m$,.x,.y; .m$ = ""; .x = .y = 0; end;
  19. Test changing: [email protected] = getarg(1); [email protected]$ = getarg(2); [email protected] = getarg(3); [email protected]$ = getarg(4); to: [email protected] = getarg(1); [email protected]$ = getarg(0); [email protected] = getarg(3); [email protected]$ = getarg(2);
  20. //===== rAthena Script ======================================= //= Euphy's WOE Controller //===== By: ================================================== //= Euphy //===== Current Version: ===================================== //= 1.5 //===== Compatible With: ===================================== //= rAthena Project //===== Description: ========================================= //= A controller for War of Emperium designed for //= simplicity and ease of use. //= Many concepts taken from ToastOfDoom's script, //= and "rewards" function originally by Goddameit. //===== Additional Comments: ================================= //= Be sure to disable the default agit controllers! //== npc\guild\agit_controller.txt //== npc\guild2\agit_start_se.txt //============================================================ // Information NPC //============================================================ prontera,149,193,4 script WOE Information 835,{ doevent "WOE_CONTROL::OnMenu"; end; OnAgitStart: while(agitcheck()) { specialeffect EF_BEGINSPELL6; sleep 425; } end; } // Script Core //============================================================ - script WOE_CONTROL -1,{ function Disp_Owner; function Add_Zero; OnInit: // ----------------------------------------------------------- // Configuration settings. // ----------------------------------------------------------- set .CastleWarp,0; // 1: Always enable all castle warps. | 0: Warp only to active castles. set .AutoKick,1; // Automatically kick players from inactive castles during WOE? (1:yes / 0:no) set .NoOwner,0; // Automatically kick players from unconquered castles outside of WOE? (1:yes / 0:no) set .ExitWarp,0; // Warp all players from castles when WOE ends? (1:yes / 0:no) set .GMAccess,99; // GM level required to access Session Manager. // ----------------------------------------------------------- // Reward options. // ----------------------------------------------------------- // [1] Enable rewards. // [2] Mail all rewards. // - If not set, players receive items in their inventory. // - Only ONE item can be sent via mail, plus Zeny. // - Note that offline players do NOT receive rewards. // [4] Only reward Guild Masters. // - If not set, all guild members are rewarded. // - If mailing is enabled (option 2), offline Guild Masters WILL receive rewards. // [8] Duplicate IP check. // - Members in a guild with the same IP address are not rewarded. // - If Guild Masters is enabled (option 4), this feature is not used. // ----------------------------------------------------------- // Combine values as needed (e.g. 1|8 = 1+8 = 9). set .Options, 1|8; // Rewards per castle. // -- when given directly: <itemID>,<amount>{,<itemID>,<amount>,...} // -- via mail (option 2): <itemID>,<amount>,<Zeny> setarray .Reward[0],45001,1; setarray .Reward_Leader[0], 45000, 1; // ----------------------------------------------------------- // Constants (leave this section alone). // ----------------------------------------------------------- setarray .Castles$[0], "prtg_cas01","prtg_cas02","prtg_cas03","prtg_cas04","prtg_cas05", "payg_cas01","payg_cas02","payg_cas03","payg_cas04","payg_cas05", "gefg_cas01","gefg_cas02","gefg_cas03","gefg_cas04","gefg_cas05", "aldeg_cas01","aldeg_cas02","aldeg_cas03","aldeg_cas04","aldeg_cas05", "arug_cas01","arug_cas02","arug_cas03","arug_cas04","arug_cas05", "schg_cas01","schg_cas02","schg_cas03","schg_cas04","schg_cas05"; setarray .EndLabel$[0],"ar01","ar02","ar03","ar04","ar05","sc01","sc02","sc03","sc04","sc05"; setarray .Days$[0],"Sunday","Monday","Tuesday","Wednesday","Thursday","Friday","Saturday"; setarray .Regions$[0],"Prontera","Payon","Geffen","Aldebaran","Arunafeltz","Schwaltzvalt"; setarray .Map$[0],"prt_gld","pay_gld","gef_fild13","alde_gld","aru_gld","sch_gld"; setarray .MapX[0],134,240,153,111,208,121,295,317,140,204,214,308,143,193,305,48, 95,142,239,264,158,83, 68,299,292,293,288, 97,137, 71; setarray .MapY[0], 65,128,137,240,240,233,116,293,160,266, 75,240,240,278, 87,83,249, 85,242, 90,272,47,155,345,107,100,252,196, 90,315; // ----------------------------------------------------------- set .Size, getarraysize($WOE_CONTROL); if (.AutoKick || .NoOwner) for(set [email protected],0; [email protected]<30; set [email protected],[email protected]+1) { setmapflag .Castles$[[email protected]], mf_loadevent; setd "."+.Castles$[[email protected]], [email protected]; } if (!agitcheck() && !agitcheck2()) sleep 4000; set .Init,1; OnMinute00: freeloop(1); if (agitcheck() || agitcheck2()) { for(set [email protected],0; [email protected]<.Size; set [email protected],[email protected]+4) if (gettime(DT_DAYOFWEEK) == $WOE_CONTROL[[email protected]] && gettime(DT_HOUR) == $WOE_CONTROL[[email protected]+2]) { OnWOEEnd: announce "The War Of Emperium is over!",bc_all|bc_woe; AgitEnd; AgitEnd2; sleep 1000; for(set [email protected],0; [email protected]<30; set [email protected],[email protected]+1) { if (.Active[0]&(1<<[email protected])) Disp_Owner(.Castles$[[email protected]],1); if (.ExitWarp) maprespawnguildid .Castles$[[email protected]],0,3; } if ((.Options&1) && .Active[0] && .ForceEnd != 2) callsub OnReward, .Active[0]; deletearray .Active[0],2; if (.ForceEnd) { set .ForceEnd,0; end; } break; } } if ((!agitcheck() && !agitcheck2()) || .Init) { if (!agitcheck() && !agitcheck2()) set .Init,0; for(set [email protected],0; [email protected]<.Size; set [email protected],[email protected]+4) if (gettime(DT_DAYOFWEEK) == $WOE_CONTROL[[email protected]] && gettime(DT_HOUR) >= $WOE_CONTROL[[email protected]+1] && gettime(DT_HOUR) < $WOE_CONTROL[[email protected]+2]) { deletearray .Active[0],2; set .Active[0], $WOE_CONTROL[[email protected]+3]; if (.Init) { AgitEnd; AgitEnd2; } else announce "The War Of Emperium has begun!",bc_all|bc_woe; sleep 1000; AgitStart; AgitStart2; for(set [email protected],0; [email protected]<30; set [email protected],[email protected]+1) { if (.Active[0]&(1<<[email protected])) { if (!.Init) Disp_Owner(.Castles$[[email protected]],0); set .Active[1], .Active[1] | (1<<(([email protected]/5)+1)); } else { if ([email protected]<20) { donpcevent "Agit#"+.Castles$[[email protected]]+"::OnAgitEnd"; killmonster .Castles$[[email protected]], "Agit#"+.Castles$[[email protected]]+"::OnAgitBreak"; } else { donpcevent "Manager#"+.Castles$[[email protected]]+"::OnAgitEnd2"; killmonster .Castles$[[email protected]], "Steward#"+.EndLabel$[[email protected]]+"::OnStartArena"; } } } break; } } set .Init,0; end; function Disp_Owner { set [email protected], getcastledata(getarg(0),1); if ([email protected]) announce "The ["+getcastlename(getarg(0))+"] castle "+((getarg(1))?"has been conquered":"is currently held")+" by the ["+getguildname([email protected])+"] guild.",bc_all|bc_woe; else announce "The ["+getcastlename(getarg(0))+"] castle is currently unoccupied.",bc_all|bc_woe; return; } function Add_Zero { return ((getarg(0)<10)?"0":"")+getarg(0)+(getarg(1,0)?".":":")+"00"; } OnReward: set [email protected]$, ((.Options&4)?"position = 0":"online = 1"); if (.Options&2) set [email protected]$,gettimestr("%B %d, %Y",21); freeloop(1); for(set [email protected],0; [email protected]<30; set [email protected],[email protected]+1) if (getarg(0)&(1<<[email protected])) { set [email protected], getcastledata(.Castles$[[email protected]],1); if ([email protected]) continue; set [email protected], query_sql("SELECT account_id,char_id FROM `guild_member` WHERE guild_id = '"[email protected]+"' AND "[email protected]$,[email protected],[email protected]); set [email protected]_cid, getguildmasterid([email protected]); for(set [email protected],0; [email protected]<[email protected]; set [email protected],[email protected]+1) { if ((.Options&8) && !(.Options&4)) { set [email protected]$, replacestr(getcharip([email protected][[email protected]]),".","a"); if (getd("[email protected]_"[email protected]+"_"[email protected]$)) continue; setd "[email protected]_"[email protected]+"_"[email protected]$,1; } if (.Options&2) { if ([email protected][[email protected]] == [email protected]_cid) { [email protected]_id = .Reward[0]; [email protected]_amt = .Reward[1]; [email protected]_zeny = .Reward[2]; } else { [email protected]_id = .Reward_Leader[0]; [email protected]_amt = .Reward_Leader[1]; [email protected]_zeny = .Reward_Leader[2]; } query_sql("INSERT INTO `mail` (send_name,dest_id,title,message,nameid,amount,identify,zeny,time) VALUES ("+ "'no-reply',"[email protected][[email protected]]+",'** Siege Reward: "+getcastlename(.Castles$[[email protected]])+" **',"+ "'Brave one,% % Congratulations!% Your guild has successfully occupied% territory in the War of Emperium on% "[email protected]$+".% % % % % [ Your reward is attached. ]',"+ [email protected]_id+","[email protected]_amt+",0,"[email protected]_zeny+",UNIX_TIMESTAMP(NOW()))"); if (!getd("[email protected]_"[email protected][[email protected]]) && isloggedin([email protected][[email protected]],[email protected][[email protected]])) { setd "[email protected]_"[email protected][[email protected]],1; message rid2name([email protected][[email protected]]),"You've got mail! Please re-login to update your mailing list."; } } else if (isloggedin([email protected][[email protected]])) { deletearray [email protected]; if ([email protected][[email protected]] == [email protected]_cid) copyarray [email protected][0],.Reward_Leader[0],getarraysize(.Reward_Leader); else copyarray [email protected][0],.Reward[0],getarraysize(.Reward); [email protected] = getarraysize([email protected]); for(set [email protected],0; [email protected]<[email protected]; set [email protected],[email protected]+2) getitem [email protected][[email protected]], [email protected][[email protected]+1], [email protected]aid[[email protected]]; message rid2name([email protected][[email protected]]),"You have been rewarded for conquering "+getcastlename(.Castles$[[email protected]])+"."; } } } if (.Options&2) query_sql("UPDATE `mail` SET message = REPLACE(message,'%',CHAR(13)) WHERE send_name = 'no-reply'"); return; OnPCLoadMapEvent: if (!compare(strcharinfo(3),"g_cas")) end; if (((.AutoKick && .Active[0]) || (.NoOwner && !getcastledata(strcharinfo(3),1))) && !(.Active[0]&(1<<getd("."+strcharinfo(3))))) { if (getcharid(2) && getcastledata(strcharinfo(3),1) == getcharid(2)) end; sleep2 1000; message strcharinfo(0), getcastlename(strcharinfo(3))+" is currently inactive."; sleep2 5000; if (compare(strcharinfo(3),"g_cas")) warp "SavePoint",0,0; } end; OnMenu: while(1) { mes "[WOE Information]"; if (agitcheck() || agitcheck2()) { if (.Active[0]) { for(set [email protected],0; [email protected]<.Size; set [email protected],[email protected]+4) if (gettime(DT_DAYOFWEEK) == $WOE_CONTROL[[email protected]] && gettime(DT_HOUR) >= $WOE_CONTROL[[email protected]+1] && gettime(DT_HOUR) < $WOE_CONTROL[[email protected]+2]) { set [email protected], $WOE_CONTROL[[email protected]+2]; break; } mes "The War of Emperium is ^0055FFactive^000000 until ^FF0000"+Add_Zero([email protected])+"^000000 in the following regions:"; mes " "; for(set [email protected],0; [email protected]<6; set [email protected],[email protected]+1) if (.Active[1]&(1<<([email protected]+1))) mes " > ^777777"+.Regions$[[email protected]]+"^000000"; } else mes "The War of Emperium is ^0055FFactive^000000."; } else { for(set [email protected],0; [email protected]<.Size; set [email protected],[email protected]+4) if ((gettime(DT_DAYOFWEEK) == $WOE_CONTROL[[email protected]] && gettime(DT_HOUR) <= $WOE_CONTROL[[email protected]+1]) || gettime(DT_DAYOFWEEK) < $WOE_CONTROL[[email protected]]) { setarray [email protected][0],$WOE_CONTROL[[email protected]],$WOE_CONTROL[[email protected]+1]; break; } if (!getarraysize([email protected])) setarray [email protected][0],$WOE_CONTROL[0],$WOE_CONTROL[1]; mes "The War of Emperium is ^777777inactive^000000."; if (.Size) { mes " "; mes "The next session will begin"; mes "on ^0055FF"+.Days$[[email protected][0]]+"^000000 at "+Add_Zero([email protected][1])+"^000000."; } } next; switch(select(""+((.CastleWarp || .Active[1])?" ~ Warp to castles...":"")+": ~ Check schedule...: ~ View castle owners...:"+((getgmlevel()<.GMAccess || !getgmlevel())?"":" ~ Manage sessions...")+": ~ ^777777Cancel^000000")) { case 1: if (.CastleWarp) set [email protected]$,"^0055FF"; set [email protected]$,""; for(set [email protected],0; [email protected]<6; set [email protected],[email protected]+1) { if (.CastleWarp || .Active[1]&(1<<([email protected]+1))) set [email protected]$, [email protected]$+" ~ "+((.Active[1]&(1<<([email protected]+1)))[email protected]$:"^777777")+.Regions$[[email protected]]+" Castles^000000"; set [email protected]$, [email protected]$+":"; } set [email protected], select([email protected]$)-1; set [email protected]$,""; for(set [email protected],[email protected]*5; [email protected]<([email protected]*5)+5; set [email protected],[email protected]+1) { if (.CastleWarp || .Active[0]&(1<<[email protected])) set [email protected]$, [email protected]$+" ~ "+((.Active[0]&(1<<[email protected]))[email protected]$:"^777777")+getcastlename(.Castles$[[email protected]])+"^000000"; set [email protected]$, [email protected]$+":"; } set [email protected], select([email protected]$)-1; warp .Map$[[email protected]],.MapX[([email protected]*5)[email protected]],.MapY[([email protected]*5)[email protected]]; close; case 2: mes "[Schedule]"; if (.Size) { freeloop(1); for(set [email protected],0; [email protected]<.Size; set [email protected],[email protected]+4) { mes "> ^FF0000"+.Days$[$WOE_CONTROL[[email protected]]]+" ("+Add_Zero($WOE_CONTROL[[email protected]+1])+"-"+Add_Zero($WOE_CONTROL[[email protected]+2])+")^000000"; for(set [email protected],0; [email protected]<30; set [email protected],[email protected]+1) if ($WOE_CONTROL[[email protected]+3]&(1<<[email protected])) mes " ~ "+getcastlename(.Castles$[[email protected]])+" ^777777("+.Castles$[[email protected]]+")^000000"; if ([email protected]+4 < .Size) mes " "; } freeloop(0); } else mes "No times are configured."; next; break; case 3: mes "[Castle Ownership]"; for(set [email protected],0; [email protected]<6; set [email protected],[email protected]+1) { set [email protected], [email protected]*5; mes "> ^FF0000"+.Regions$[[email protected]]+"^000000"; for(set [email protected],[email protected]; [email protected]<([email protected]+5); set [email protected],[email protected]+1) { set [email protected], getcastledata(.Castles$[[email protected]],1); mes " ~ "+getcastlename(.Castles$[[email protected]])+": "+(([email protected])?"^0055FF"+getguildname([email protected]):"^777777unoccupied")+"^000000"; } if ([email protected] < 5) mes " "; } next; break; case 4: while(1) { mes "[Session Manager]"; mes "There are ^0055FF"+(.Size/4)+" session(s)^000000 configured."; mes "What would you like to do?"; next; switch(select(" ~ Add a session...: ~ Delete a session...: ~ Reload settings...:"+((agitcheck() || agitcheck2())?" ~ End WOE session...":"")+": ~ ^777777Go back^000000")) { case 1: mes "[New Session]"; if (.Size > 127) { mes "You have already reached the maximum of 32 sessions."; next; break; } mes "Select a day."; next; set [email protected], select(" ~ "+implode(.Days$,": ~ "))-1; mes "[New Session]"; mes "Select a start time for ^0055FF"+.Days$[[email protected]]+"^000000."; next; set [email protected]$,""; for(set [email protected],0; [email protected]<23; set [email protected],[email protected]+1) set [email protected]$, [email protected]$+" ~ "+Add_Zero([email protected],1)+":"; set [email protected], select([email protected]$)-1; mes "[New Session]"; mes "Select an end time for ^0055FF"+.Days$[[email protected]]+"^000000."; next; set [email protected]$,""; for(set [email protected],[email protected]+1; [email protected]<24; [email protected],[email protected]+1) set [email protected]$, [email protected]$+" ~ "+Add_Zero([email protected],1)+":"; set [email protected], select([email protected]$)[email protected]; for(set [email protected],0; [email protected]<.Size; set [email protected],[email protected]+4) if ([email protected] == $WOE_CONTROL[[email protected]] && (([email protected] >= $WOE_CONTROL[[email protected]+1] && [email protected] < $WOE_CONTROL[[email protected]+2]) || ([email protected] > $WOE_CONTROL[[email protected]+1] && [email protected] <= $WOE_CONTROL[[email protected]+2]) || ([email protected] <= $WOE_CONTROL[[email protected]+1] && [email protected] >= $WOE_CONTROL[[email protected]+2]))) { mes "[New Session]"; mes "The chosen times overlap with an existing session."; next; set [email protected],1; break; } if ([email protected]) { set [email protected],0; break; } set [email protected],0; while(1) { mes "[New Session]"; mes "^0055FF"+.Days$[[email protected]]+" ("+Add_Zero([email protected])+"-"+Add_Zero([email protected])+")^000000"; mes " > Castles:"; if ([email protected]) mes " ~ ^777777(none selected)^000000"; else for(set [email protected],0; [email protected]<30; set [email protected],[email protected]+1) if ([email protected]&(1<<[email protected])) mes " ~ "+getcastlename(.Castles$[[email protected]])+" ("+.Castles$[[email protected]]+")"; next; set [email protected]$,(([email protected])?" ~ ^FF0000Finished...^000000":"")+":"; for(set [email protected],0; [email protected]<30; set [email protected],[email protected]+1) set [email protected]$, [email protected]$+" ~ "+(([email protected]&(1<<[email protected]))?"^0055FF":"")+getcastlename(.Castles$[[email protected]])+" ("+.Castles$[[email protected]]+")^000000:"; set [email protected], select([email protected]$)-1; if ([email protected]) set [email protected], [email protected]^(1<<([email protected])); else { mes "[New Session]"; mes "Are you sure?"; next; switch(select(" ~ ^0055FFAdd session...^000000: ~ Continue selecting castles...: ~ ^777777Cancel^000000")) { case 1: for(set [email protected],0; [email protected]<.Size; set [email protected],[email protected]+4) if (([email protected] == $WOE_CONTROL[[email protected]] && [email protected] <= $WOE_CONTROL[[email protected]+1]) || [email protected] < $WOE_CONTROL[[email protected]]) { set [email protected],1; break; } if ([email protected]) { set [email protected],1; set [email protected],.Size; } copyarray $WOE_CONTROL[[email protected]+4], $WOE_CONTROL[[email protected]], [email protected]; setarray $WOE_CONTROL[[email protected]], [email protected], [email protected], [email protected], [email protected]; set .Size, getarraysize($WOE_CONTROL); case 3: mes "[New Session]"; mes (([email protected])?"Session added.":"cancelled."); next; set [email protected],1; case 2: break; } if ([email protected]) { set [email protected],0; break; } } } break; case 2: mes "[Remove Session]"; if (!.Size) { mes "There are no sessions configured."; next; break; } mes "Select a session to remove."; next; set [email protected]$,""; for(set [email protected],0; [email protected]<.Size; set [email protected],[email protected]+4) set [email protected]$, [email protected]$+" ~ "+.Days$[$WOE_CONTROL[[email protected]]]+" ("+Add_Zero($WOE_CONTROL[[email protected]+1],1)+"-"+Add_Zero($WOE_CONTROL[[email protected]+2],1)+"):"; set [email protected]$, [email protected]$+" ~ ^777777Cancel^000000"; set [email protected], select([email protected]$)-1; if ([email protected] == (.Size/4)) break; mes "[Remove Session]"; mes "Delete ^0055FF"+.Days$[$WOE_CONTROL[[email protected]*4]]+"'s^000000 session?"; mes "This action cannot be undone."; next; set [email protected], select(" ~ ^FF0000Delete session...^000000: ~ ^777777Cancel^000000"); mes "[Remove Session]"; if ([email protected] == 2) mes "cancelled."; else { deletearray $WOE_CONTROL[[email protected]*4],4; set .Size, getarraysize($WOE_CONTROL); mes "Session deleted."; } next; break; case 3: mes "[Reload Settings]"; mes "This will trigger all events related to new session configurations, if any."; if (agitcheck() || agitcheck2()) { mes " "; mes "Be aware that this will disrupt the current WOE session."; } next; set [email protected], select(" ~ ^0055FFReload settings...^000000: ~ ^777777Cancel^000000"); mes "[Reload Settings]"; if ([email protected] == 2) mes "cancelled."; else { set .Init,1; donpcevent "WOE_CONTROL::OnMinute00"; mes "Variables have been re-initialized."; } next; break; case 4: mes "[Force Agit End]"; if (!agitcheck() && !agitcheck2()) { mes "WOE has already ended."; next; break; } mes "This command will safely execute all AgitEnd events."; mes " "; mes "Kill the current WOE session?"; next; set [email protected], select(" ~ ^FF0000End session...^000000:"+((.Options&1)?" ~ ^FF0000End session without rewards...^000000":"")+": ~ ^777777Cancel^000000"); mes "[Force Agit End]"; if ([email protected] == 3) mes "cancelled."; else { set .ForceEnd, [email protected]; donpcevent "WOE_CONTROL::OnWOEEnd"; mes "WOE session terminated."; } next; break; case 5: set [email protected],1; break; } if ([email protected]) { set [email protected],0; break; } } break; case 5: close; } } } // Rewards per castle. // -- when given directly: <itemID>,<amount>{,<itemID>,<amount>,...} // -- via mail (option 2): <itemID>,<amount>,<Zeny> setarray .Reward[0],45001,1; setarray .Reward_Leader[0], 45000, 1;
  21. Might want to add agitcheck in there. Players could win points dueling.
  22. You could try creating a diff. Another option is to use Server Database Editor (http://www.mediafire.com/download/p0zhcc8ipa6cjt3). It has a feature to autogenerate clientside descriptions. You can test it yourself, it's pretty great.
  23. Didn't you you wanted that. prontera,150,150,4 script Stylist 4_F_NYDHOG,{ if(!(eaclass() & EAJ_SUMMONER)) { setarray [email protected][1], getbattleflag("max_hair_style"), getbattleflag("max_hair_color"), ((!getlook(LOOK_BODY2))? getbattleflag("max_cloth_color") : .max[4]); } else { copyarray [email protected][1],.max[1],3; } setarray [email protected][1], 1, // Hair style 0 crashed my client last time I tested. 0, 0; setarray [email protected][1], LOOK_HAIR, LOOK_HAIR_COLOR, LOOK_CLOTHES_COLOR; [email protected] = getarraysize(.blacklist$); [email protected]$ = "^3227cd[Stylist]^000000"; mes [email protected]$; mes "Hello "+strcharinfo(0)+"."; mes "Current hairstyle: ^00457f"+getlook(LOOK_HAIR)+"^000000."; mes "Current haircolor: ^215d90"+getlook(LOOK_HAIR_COLOR)+"^000000."; mes "Current clothcolor: ^4c9fe5"+getlook(LOOK_CLOTHES_COLOR)+"^000000."; mes "Do you want to change something?"; while(playerattached()) { next; [email protected] = select("^911b1bExit.^000000","Hairstyle.","Haircolor.","Clothes color.") - 1; mes [email protected]$; if([email protected]) { mes "Have a nice day."; close; } [email protected] = getlook([email protected][[email protected]]); mes "Where do you want to start from?"; next; [email protected] = select("From the beggining.","From my current style.","Specific style.","Random style."); mes [email protected]$; if([email protected] == 3) { mes "Input the number you'd like to start from."; mes "("[email protected][[email protected]]+" - "[email protected][[email protected]]+")"; mes "Your current style is: ^e83333"[email protected]+"^000000."; input [email protected]; if([email protected] > [email protected][[email protected]] || [email protected] < [email protected][[email protected]]) [email protected] = rand([email protected][[email protected]],[email protected][[email protected]]); } else { [email protected] = (([email protected] == 1)? [email protected][[email protected]] : (([email protected] == 2)? [email protected] : (([email protected] == 4)? rand([email protected][[email protected]],[email protected][[email protected]]) : [email protected][[email protected]]))); } if([email protected]) { stand; getmapxy [email protected]$,[email protected],[email protected],UNITTYPE_PC; unitwalk getcharid(3),[email protected],[email protected] - 1; } mes "Great, we can start now."; next; do { mes [email protected]$; if([email protected][[email protected]] == LOOK_CLOTHES_COLOR) { for([email protected] = 0;[email protected] < [email protected] && [email protected];[email protected]++) { if(compare(.blacklist$[[email protected]],"-")) { explode [email protected]$,.blacklist$[[email protected]],"-"; [email protected] = atoi([email protected]$[0]); [email protected] = atoi([email protected]$[1]); if([email protected] >= [email protected] && [email protected] <= [email protected]) { if([email protected]) [email protected] = [email protected] + 1; else [email protected] = [email protected] - 1; } } else { if([email protected] == atoi(.blacklist$[[email protected]])) [email protected]+= pow(-1,[email protected]); } } } mes "Style n°^e83333"[email protected]+"^000000."; setlook [email protected][[email protected]],[email protected]; if([email protected]) { [email protected]_1$ = (([email protected])? "Previous [^e83c00"+(([email protected] - 1 < [email protected][[email protected]])? [email protected][[email protected]] : [email protected] - 1)+"^000000]" : "Next [^e83c00"+(([email protected] + 1 > [email protected][[email protected]])? [email protected][[email protected]] : [email protected] + 1) +"^000000]"); [email protected]_2$ = (([email protected])? "Next [^e83c00"+(([email protected] + 1 > [email protected][[email protected]])[email protected][[email protected]] : [email protected] + 1)+"^000000]" : "Previous [^e83c00"+(([email protected] - 1 < [email protected][[email protected]])? [email protected][[email protected]] : [email protected] - 1) +"^000000]"); [email protected] = select([email protected]_1$,[email protected]_2$,"^911b1bI want this one.^000000","Jump to a number ("[email protected][[email protected]]+"-"[email protected][[email protected]]+").","Jump to a random number.","Revert changes.","^614c9cRandom mode^000000 [^e81600off^000000]"); if([email protected] + [email protected] == 2) [email protected]; else if([email protected] + [email protected] == 1) [email protected]++; if([email protected] < [email protected][[email protected]]) [email protected] = [email protected][[email protected]]; else if([email protected] > [email protected][[email protected]]) [email protected] = [email protected][[email protected]]; if([email protected] == 2) [email protected] = [email protected]; } else { [email protected] = select("Next.","^911b1bI want this one.^000000","Jump to a number ("[email protected][[email protected]]+"-"[email protected][[email protected]]+").","Revert changes.","^614c9cRandom mode^000000 [^50bf19on^000000]"); if([email protected] > 2) [email protected]++; if([email protected] > 4) [email protected]++; } if([email protected] == 4) { input [email protected]; if([email protected] > [email protected][[email protected]] || [email protected] < [email protected][[email protected]]) [email protected] = rand([email protected][[email protected]],[email protected][[email protected]]); } else if([email protected] == 5 || ([email protected] && [email protected] == 1)) { [email protected] = rand([email protected][[email protected]],[email protected][[email protected]]); } else if([email protected] == 6) { [email protected] = [email protected]; } else if([email protected] == 7) { [email protected] = [email protected]; } clear; } while([email protected] != (3 - [email protected])); next; mes [email protected]$; mes "Do you want to change something else?"; [email protected] = 0; [email protected] = false; [email protected] = false; } OnInit: //==============Settings:=============================================== setarray .max[1], 6, // Max summoner hairstyle. 10, // Max summoner hair color. 10, // Max summoner clothes color. 553; // Alternative outfist clothes color. setarray .blacklist$[0],"30-200","999"; // Blacklist for cloth color. //====================================================================== }
  24. Put it in codebox, not quote. And you can show a screenshot if there's an error. Anyways, I have an old stylist and added your change. Tell me how it goes: prontera,150,150,4 script Stylist 4_F_NYDHOG,{ if(!(eaclass() & EAJ_SUMMONER)) { setarray [email protected][1], getbattleflag("max_hair_style"), getbattleflag("max_hair_color"), ((!getlook(LOOK_BODY2))? getbattleflag("max_cloth_color") : .max[4]); } else { copyarray [email protected][1],.max[1],3; } setarray [email protected][1], 1, // Hair style 0 crashed my client last time I tested. 0, 0; setarray [email protected][1], LOOK_HAIR, LOOK_HAIR_COLOR, LOOK_CLOTHES_COLOR; [email protected] = getarraysize(.blacklist$); [email protected]$ = "^3227cd[Stylist]^000000"; mes [email protected]$; mes "Hello "+strcharinfo(0)+"."; mes "Current hairstyle: ^00457f"+getlook(LOOK_HAIR)+"^000000."; mes "Current haircolor: ^215d90"+getlook(LOOK_HAIR_COLOR)+"^000000."; mes "Current clothcolor: ^4c9fe5"+getlook(LOOK_CLOTHES_COLOR)+"^000000."; mes "Do you want to change something?"; while(playerattached()) { next; [email protected] = select("^911b1bExit.^000000","Hairstyle.","Haircolor.","Clothes color.") - 1; mes [email protected]$; if([email protected]) { mes "Have a nice day."; close; } [email protected] = getlook([email protected][[email protected]]); mes "Where do you want to start from?"; next; [email protected] = select("From the beggining.","From my current style.","Specific style.","Random style."); mes [email protected]$; if([email protected] == 3) { mes "Input the number you'd like to start from."; mes "("[email protected][[email protected]]+" - "[email protected][[email protected]]+")"; mes "Your current style is: ^e83333"[email protected]+"^000000."; input [email protected]; if([email protected] > [email protected][[email protected]] || [email protected] < [email protected][[email protected]]) [email protected] = rand([email protected][[email protected]],[email protected][[email protected]]); } else { [email protected] = (([email protected] == 1)? [email protected][[email protected]] : (([email protected] == 2)? [email protected] : (([email protected] == 4)? rand([email protected][[email protected]],[email protected][[email protected]]) : [email protected][[email protected]]))); } if([email protected]) { stand; getmapxy [email protected]$,[email protected],[email protected],UNITTYPE_PC; unitwalk getcharid(3),[email protected],[email protected] - 1; } mes "Great, we can start now."; next; do { mes [email protected]$; mes "Style n°^e83333"[email protected]+"^000000."; [email protected] = false; if([email protected][[email protected]] == LOOK_CLOTHES_COLOR) { for([email protected] = 0;[email protected] < [email protected] && [email protected];[email protected]++) { if(compare(.blacklist$[[email protected]],"-")) { explode [email protected]$,.blacklist$[[email protected]],"-"; [email protected] = atoi([email protected]$[0]); [email protected] = atoi([email protected]$[1]); if([email protected] >= [email protected] && [email protected] <= [email protected]) [email protected] = true; } else { if([email protected] == atoi(.blacklist$[[email protected]])) [email protected] = true; } } } if([email protected]) mes "^e20404Blacklisted^000000"; else setlook [email protected][[email protected]],[email protected]; if([email protected]) { [email protected]_1$ = (([email protected])? "Previous [^e83c00"+(([email protected] - 1 < [email protected][[email protected]])? [email protected][[email protected]] : [email protected] - 1)+"^000000]" : "Next [^e83c00"+(([email protected] + 1 > [email protected][[email protected]])? [email protected][[email protected]] : [email protected] + 1) +"^000000]"); [email protected]_2$ = (([email protected])? "Next [^e83c00"+(([email protected] + 1 > [email protected][[email protected]])[email protected][[email protected]] : [email protected] + 1)+"^000000]" : "Previous [^e83c00"+(([email protected] - 1 < [email protected][[email protected]])? [email protected][[email protected]] : [email protected] - 1) +"^000000]"); [email protected] = select([email protected]_1$,[email protected]_2$,"^911b1bI want this one.^000000","Jump to a number ("[email protected][[email protected]]+"-"[email protected][[email protected]]+").","Jump to a random number.","Revert changes.","^614c9cRandom mode^000000 [^e81600off^000000]"); if([email protected] + [email protected] == 2) [email protected]; else if([email protected] + [email protected] == 1) [email protected]++; if([email protected] < [email protected][[email protected]]) [email protected] = [email protected][[email protected]]; else if([email protected] > [email protected][[email protected]]) [email protected] = [email protected][[email protected]]; if([email protected] == 2) [email protected] = [email protected]; } else { [email protected] = select("Next.","^911b1bI want this one.^000000","Jump to a number ("[email protected][[email protected]]+"-"[email protected][[email protected]]+").","Revert changes.","^614c9cRandom mode^000000 [^50bf19on^000000]"); if([email protected] > 2) [email protected]++; if([email protected] > 4) [email protected]++; } if([email protected] == 4) { input [email protected]; if([email protected] > [email protected][[email protected]] || [email protected] < [email protected][[email protected]]) [email protected] = rand([email protected][[email protected]],[email protected][[email protected]]); } else if([email protected] == 5 || ([email protected] && [email protected] == 1)) { [email protected] = rand([email protected][[email protected]],[email protected][[email protected]]); } else if([email protected] == 6) { [email protected] = [email protected]; } else if([email protected] == 7) { [email protected] = [email protected]; } clear; } while([email protected] != (3 - [email protected])); next; mes [email protected]$; mes "Do you want to change something else?"; [email protected] = 0; [email protected] = false; [email protected] = false; } OnInit: //==============Settings:=============================================== setarray .max[1], 6, // Max summoner hairstyle. 10, // Max summoner hair color. 10, // Max summoner clothes color. 553; // Alternative outfist clothes color. setarray .blacklist$[0],"30-200","999"; // Blacklist for cloth color. //====================================================================== } You can add ranges in the blacklist, like "500-2000" (I only added it for clothes color), and single values.