// TMW2 Script // Author: // Jesusalva 006-7,44,50,0 script #OutOf0067 NPC_HIDDEN,0,0,{ end; OnTouch: if (!$@ICICLE_CHALLENGE) warp "006-6", 40, 36; end; OnRw: getexp 1000000, 0; Mobpt += 10000; dispbottom l("Der Schneemann has been defeated: %s Monster Points gained.", fnum(10000)); end; } 006-7,44,35,0 script Ice Lord NPC_YETIFLY,{ if ($@ICICLE_CHALLENGE) end; if (.ticks > gettimetick(2)) { mesn; mesq l("This challenge will be available in %s. Please wait until then.", FuzzyTime(.ticks)); close; } mesn; mesq l("With Magic and Blades, The Icicle shall break. Do you undertake the challenge?"); mesc l("Advised: 6+ players"), 1; mesc l("Advised: 1+ mage, 1+ tanker, 2+ healers"), 1; mesc l("Time Limit: 90 minutes"), 1; mesc l("Enter/Leave after start: %s", b(l("NO"))), 1; next; select l("Not yet."), l("Bring it on!"), rif(REBIRTH, l("Bring me, my worst nightmare.")); mes ""; if (@menu == 1) { closeclientdialog; close; } if (@menu == 2) .hard = false; else .hard = true; // Der Schneemann .ticks = gettimetick(2) + 5400; // 90 minutes .BOSS = monster("006-7", 44, 36, "The Icicle", SnowmanBoss, 1); .@mlt = (.hard ? 15 : 10); // Basic attributes setunitdata(.BOSS, UDT_MAXHP, 750000 * .@mlt / 10); // 750k ~ 1250k setunitdata(.BOSS, UDT_HP, 750000 * .@mlt / 10); setunitdata(.BOSS, UDT_ATKRANGE, (.hard ? 7 : 6)); // Reconfigure the AI .@opt=getunitdata(.BOSS, UDT_MODE); // Disable looting if (.@opt & MD_LOOTER) .@opt=.@opt^MD_LOOTER; // Add knockback immunity .@opt=.@opt|MD_NOKNOCKBACK; // Mark as boss .@opt=.@opt|MD_BOSS; // Mark as aggressive .@opt=.@opt|MD_AGGRESSIVE; .@opt=.@opt|MD_ANGRY; // Make it more op .@opt=.@opt|MD_DETECTOR; .@opt=.@opt|MD_CASTSENSOR_CHASE; .@opt=.@opt|MD_CASTSENSOR_IDLE; .@opt=.@opt|MD_CHANGECHASE; .@opt=.@opt|MD_CHANGETARGET_MELEE; .@opt=.@opt|MD_CHANGETARGET_CHASE; setunitdata(.BOSS, UDT_MODE, .@opt); // Nerf the damage, but never miss a hit setunitdata(.BOSS, UDT_ATKMIN, 60 * .@mlt / 10); // 60~90 dmg setunitdata(.BOSS, UDT_ATKMAX, 60 * .@mlt / 10); setunitdata(.BOSS, UDT_ADELAY, 2220 / .@mlt * 10); // 2220 or 1480ms setunitdata(.BOSS, UDT_HIT, 2400); // Boosting the defense is not necessary // It nerfs weapons to 40% (bows to 20%) // Then it resists 50% of Neutral element. // Note it is strong against Water (25% dmg) // And weak against Fire (snow) and Wind (100% dmg) // Otherwise, behave as Ghost element $@ICICLE_CHALLENGE = true; disablenpc .name$; initnpctimer; closeclientdialog; close; // Fail-safe Mechanism (will never happen) OnTimer25000: OnTimer15000: consolewarn("Warning, fail-safe mechanism triggered to Icicle."); // This is the boss' core OnTimer5000: /* Maybe the fight is over */ if (!mobcount("006-7", "all")) maptimer2("006-7", 10, "#OutOf0067::OnRw"); if (.ticks < gettimetick(2) || !mobcount("006-7", "all") || !getmapusers("006-7")) { killmonsterall("006-7"); enablenpc .name$; npctalk "The battle is over!"; .ticks = min(.ticks, gettimetick(2) + 1800); // Min. Cooldown: 30 min .beats = 0; .warn = 0; $@ICICLE_CHALLENGE = false; stopnpctimer; end; } /* Warn players when time is about to end */ if (.ticks - 1800 < gettimetick(2) && .warn < 1) { mapannounce("006-7", "Warning : ##1##BTime left: 30 minutes##b", 0); .warn = 1; } else if (.ticks - 900 < gettimetick(2) && .warn < 2) { mapannounce("006-7", "Warning : ##1##BTime left: 15 minutes##b", 0); .warn = 2; } else if (.ticks - 600 < gettimetick(2) && .warn < 3) { mapannounce("006-7", "Warning : ##1##BTime left: 10 minutes##b", 0); .warn = 3; } else if (.ticks - 300 < gettimetick(2) && .warn < 4) { mapannounce("006-7", "Warning : ##1##BTime left: 5 minutes##b", 0); .warn = 4; } /* Prepare some data */ .@hp = getunitdata(.BOSS, UDT_HP) * 10 / getunitdata(.BOSS, UDT_MAXHP); getmapxy(.@m$, .@x, .@y, UNITTYPE_MOB, .BOSS); .@c=getunits(BL_PC, .@pcs, MAX_CYCLE_PC, .@m$); .@mvp=0;.@rnd=0;.@def=-1; for (.@i = 0; .@i < .@c; .@i++) { if (!.@rnd || !rand2(.@c)) .@rnd=.@pcs[.@i]; if (readbattleparam(.@pcs[.@i], UDT_DEF) > .@def) { if (readparam(Hp, .@pcs[.@i]) < 1) continue; .@mvp=.@pcs[.@i]; .@def=readbattleparam(.@pcs[.@i], UDT_DEF); } } .beats += 1; /* Everyone is dead, get rid of them */ if (!.@mvp || !.@rnd) { mapwarp("006-7", "006-6", 40, 36); initnpctimer; end; } //debugmes "----------- Skill Loop, beat is %d", .beats % 18; /* Decide the skill to use based on ~5s beats over 3 minutes */ switch (.beats % 18) { // (1/6) Summon Reinforcements (every 60s) case 0: case 6: case 12: unittalk(.BOSS, "Come forth, ##Bsnow army##b, for the Icicle shall live forever!"); specialeffect(65, AREA, .BOSS); // Actually 64, but won't do well here sleep(1000); monster("006-7", 44, 22, strmobinfo(1, Snowman), Snowman, max(1, (11 - .@hp) / 10)); break; // (2/6) Tanker (~30s) case 1: case 4: case 7: case 10: case 13: case 16: specialeffect(702, AREA, .BOSS); sleep(1000); if (.@hp < 3) { // Third Attack Pattern: Judgment unittalk(.BOSS, sprintf("%s cannot stop me! ##BJudgment##b!", strcharinfo(0, "cursed player", .@mvp))); .@PW=250; .@SPW=60; .@RG=3; } else if (.@hp < 7) { // Second Attack Pattern: Holy Light unittalk(.BOSS, sprintf("%s, I'll show you no mercy! ##BHoly Light##b!", strcharinfo(0, "cursed player", .@mvp))); .@PW=125; .@SPW=25; .@RG=1; } else { // First Attack Pattern: Napalm Beat unittalk(.BOSS, sprintf("This battle is over, %s! ##BNapalm Beat##b!", strcharinfo(0, "cursed player", .@mvp))); .@PW=35; .@SPW=5; .@RG=2; } .@mtk = calcdmg(.BOSS, .@mvp, HARM_MAGI); .@dmg = .@mtk * .@PW / 100; .@dsb = .@mtk * .@SPW / 100; sleep(1000); areaharm(.@mvp, .@RG, .@dsb, HARM_MAGI, Ele_Holy, "filter_always", BL_PC|BL_MER|BL_HOM); harm(.@mvp, .@dmg, HARM_MAGI, Ele_Holy); break; // (3/6) Random Target (~60s) case 2: case 8: case 14: specialeffect(50, AREA, .BOSS); sleep(1000); .@time=rand2(18000, 36000) + 10000 - (.@hp * 1000); // Switch between curse and disable if (any(true,false)) { unittalk(.BOSS, sprintf("I hereby ##Bcurse##b you, %s!", strcharinfo(0, "cursed player", .@rnd))); sc_start(SC_CURSE, .@time, 1, 10000, SCFLAG_FIXEDRATE, .@rnd); } else { unittalk(.BOSS, sprintf("I shall ##Bdisable##b you, %s!", strcharinfo(0, "cursed player", .@rnd))); sc_start(SC_BLIND, .@time / 2, 1, 10000, SCFLAG_FIXEDRATE, .@rnd); sc_start(SC_SILENCE, .@time / 2, 1, 10000, SCFLAG_FIXEDRATE, .@rnd); } // Second pattern: Bleeding ON if (.@hp < 7) { sc_start(SC_BLOODING, 10000, 1, 9000-(.@hp*1000), SCFLAG_FIXEDRATE, .@rnd); } break; // (4/6) Traps (~60s) case 3: case 9: case 15: .@x1=rand2(31, 58); .@x2=rand2(31, 58); .@x3=rand2(31, 58); .@y1=rand2(23, 49); .@y2=rand2(23, 49); .@y3=rand2(23, 49); .@t1=monster("006-7", .@x1, .@y1, "", Dummy, 1); .@t2=monster("006-7", .@x2, .@y2, "", Dummy, 1); .@t3=monster("006-7", .@x3, .@y3, "", Dummy, 1); specialeffect(67, AREA, .@t1); specialeffect(67, AREA, .@t2); specialeffect(67, AREA, .@t3); immortal(.@t1); immortal(.@t2); immortal(.@t3); if (.@hp < 5 || .hard) { .@x4=rand2(31, 58); .@x5=rand2(31, 58); .@x6=rand2(31, 58); .@y4=rand2(23, 49); .@y5=rand2(23, 49); .@y6=rand2(23, 49); .@t4=monster("006-7", .@x1, .@y1, "", Dummy, 1); .@t5=monster("006-7", .@x2, .@y2, "", Dummy, 1); .@t6=monster("006-7", .@x3, .@y3, "", Dummy, 1); specialeffect(67, AREA, .@t4); specialeffect(67, AREA, .@t5); specialeffect(67, AREA, .@t6); immortal(.@t4); immortal(.@t5); immortal(.@t6); } sleep(2000); specialeffect(11, AREA, .@t1); specialeffect(11, AREA, .@t2); specialeffect(11, AREA, .@t3); if (.@hp < 5 || .hard) { specialeffect(11, AREA, .@t4); specialeffect(11, AREA, .@t5); specialeffect(11, AREA, .@t6); } areaharm(.@t1, 2, 450, HARM_MISC, Ele_Neutral, "filter_always", BL_PC|BL_MER|BL_HOM); areaharm(.@t2, 2, 450, HARM_MISC, Ele_Neutral, "filter_always", BL_PC|BL_MER|BL_HOM); areaharm(.@t3, 2, 450, HARM_MISC, Ele_Neutral, "filter_always", BL_PC|BL_MER|BL_HOM); if (.@hp < 5 || .hard) { areaharm(.@t4, 2, 450, HARM_MISC, Ele_Neutral, "filter_always", BL_PC|BL_MER|BL_HOM); areaharm(.@t5, 2, 450, HARM_MISC, Ele_Neutral, "filter_always", BL_PC|BL_MER|BL_HOM); areaharm(.@t6, 2, 450, HARM_MISC, Ele_Neutral, "filter_always", BL_PC|BL_MER|BL_HOM); } sleep(1000); // FIXME: M+ fails to remove them, need @refresh unitkill(.@t1); unitkill(.@t2); unitkill(.@t3); if (.@hp < 5 || .hard) { unitkill(.@t4); unitkill(.@t5); unitkill(.@t6); } break; // (5/6) Weak AOE (~60s) case 5: case 11: case 17: specialeffect(60, AREA, .BOSS); sleep(500); switch (rand2(3)) { case 1: unittalk(.BOSS, "I shall ##Bpoison##b you all!"); .@sc = (.@hp < 1 ? SC_DPOISON : SC_POISON); break; case 2: unittalk(.BOSS, "I shall ##Bhurt##b you all!"); .@sc = SC_BLOODING; break; case 3: unittalk(.BOSS, "I shall ##Bsilence##b you all!"); .@sc = SC_SILENCE; break; default: unittalk(.BOSS, "I shall ##Bcripple##b you all!"); .@sc = SC_BLIND; break; } areasc((.hard ? 7 : 6), 45000, .@sc, BL_PC|BL_HOM|BL_MER, 1, "filter_always", .BOSS, 95000); areaharm(.BOSS, (.hard ? 7 : 6), 100, HARM_MAGI, Ele_Water, "filter_always", BL_PC|BL_MER|BL_HOM); break; } // Strong AOE: Every 3 minutes (case = 0) // Stalls all other skills for a while if (.beats % 18 == 0) { specialeffect(66, AREA, .BOSS); unittalk(.BOSS, "I am the Icicle, the immortal."); sleep((.hard ? 1000 : 1500)); specialeffect(700, AREA, .BOSS); unittalk(.BOSS, "You're no match for me, so..."); sleep((.hard ? 1000 : 1500)); specialeffect(700, AREA, .BOSS); if (.@hp < 3) { unittalk(.BOSS, "Perish! ##BSnowstorm##b!"); .@dmg=rand2(900, 1100); areasc(3, 5000, SC_FREEZE, BL_PC|BL_HOM|BL_MER, 1, "filter_always", .BOSS, 2000); areasc(6, 10000, SC_BLIND, BL_PC|BL_HOM|BL_MER, 1, "filter_always", .BOSS, 2000); } else if (.@hp < 7) { unittalk(.BOSS, "Perish! ##BBlizzard##b!"); .@dmg=rand2(650, 900); areasc(3, 5000, SC_FREEZE, BL_PC|BL_HOM|BL_MER, 1, "filter_always", .BOSS, 1500); } else { unittalk(.BOSS, "Perish! ##BShattering Winds##b!"); .@dmg=rand2(400, 650); } /* Three blocks */ specialeffect(66, AREA, .BOSS); areaharm(.BOSS, (.hard ? 7 : 6), .@dmg, HARM_MAGI, Ele_Neutral, "filter_always", BL_PC|BL_MER|BL_HOM); sleep(500); specialeffect(66, AREA, .BOSS); areaharm(.BOSS, (.hard ? 18 : 12), .@dmg, HARM_MAGI, Ele_Water, "filter_always", BL_PC|BL_MER|BL_HOM); sleep(500); specialeffect(66, AREA, .BOSS); specialeffect(312, AREA, .BOSS); areaharm(.BOSS, (.hard ? 24 : 18), .@dmg, HARM_MAGI, Ele_Holy, "filter_always", BL_PC|BL_MER|BL_HOM); areasc((.hard ? 24 : 18), .@dmg*rand2(50, 100), SC_COLD, BL_PC|BL_HOM|BL_MER, 1, "filter_always", .BOSS, 10001 - (.@hp * 1000)); } initnpctimer; end; OnInit: .distance = 4; .ticks = gettimetick(2); .beats = 0; .hard = 0; .warn = 0; end; }