From 8c7b9a0c4c09e73b8c71b7c3f480e8a6e963dbf2 Mon Sep 17 00:00:00 2001 From: Streusel Date: Sun, 2 Jun 2013 12:46:44 -0600 Subject: Update scripts.conf --- npc/re/scripts.conf | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) (limited to 'npc/re') diff --git a/npc/re/scripts.conf b/npc/re/scripts.conf index e4dcd94ac..c1e40dae6 100644 --- a/npc/re/scripts.conf +++ b/npc/re/scripts.conf @@ -57,6 +57,7 @@ npc: npc/re/merchants/refine.txt npc: npc/re/merchants/renters.txt npc: npc/re/merchants/shops.txt npc: npc/re/merchants/enchan_mal.txt +npc: npc/re/merchants/enchan_mora.txt npc: npc/re/merchants/coin_exchange.txt // --------------------------- Others --------------------------- @@ -89,4 +90,4 @@ npc: npc/re/quests/quests_malangdo.txt npc: npc/re/quests/quests_veins.txt npc: npc/re/quests/quests_mora.txt npc: npc/re/quests/monstertamers.txt -npc: npc/re/quests/quests_13_1.txt \ No newline at end of file +npc: npc/re/quests/quests_13_1.txt -- cgit v1.2.3-60-g2f50 From 7c31f8720d8bd47c5ef134fc8dbe3bee54424af7 Mon Sep 17 00:00:00 2001 From: malufett Date: Thu, 13 Jun 2013 01:56:21 +0800 Subject: Hercules Renewal Phase : Renewal Rename SC names to eagis standard. Implement SC Configuration.(see db/sc_config.txt) Skill updates and fixes. Some code optimization. Signed-off-by: malufett --- conf/battle/status.conf | 9 - conf/messages.conf | 3 - db/item_db2.txt | 8 +- db/item_delay.txt | 14 +- db/job_db2.txt | 9 +- db/pre-re/item_db.txt | 332 +- db/pre-re/skill_cast_db.txt | 140 +- db/pre-re/skill_db.txt | 145 +- db/pre-re/skill_require_db.txt | 20 + db/pre-re/skill_tree.txt | 99 + db/pre-re/skill_unit_db.txt | 11 +- db/re/item_combo_db.txt | 2 +- db/re/item_db.txt | 336 +- db/re/refine_db.txt | 7 +- db/re/skill_cast_db.txt | 91 +- db/re/skill_db.txt | 90 +- db/re/skill_require_db.txt | 24 +- db/re/skill_tree.txt | 99 + db/re/skill_unit_db.txt | 21 +- db/sc_config.txt | 407 ++ doc/script_commands.txt | 7 +- npc/cities/rachel.txt | 4 +- npc/custom/healer.txt | 2 +- npc/events/halloween_2009.txt | 42 +- npc/events/nguild/nguild_warper.txt | 6 +- npc/instances/NydhoggsNest.txt | 2 +- npc/mobs/citycleaners.txt | 2 + npc/quests/skills/assassin_skills.txt | 4 +- npc/re/cities/dewata.txt | 12 +- npc/re/jobs/3-1/rune_knight.txt | 4 +- npc/re/quests/quests_brasilis.txt | 22 +- src/char/char.c | 2 + src/common/mmo.h | 2 +- src/config/const.h | 4 +- src/map/atcommand.c | 8 +- src/map/battle.c | 7521 +++++++++++++------------- src/map/battle.h | 22 +- src/map/clif.c | 181 +- src/map/clif.h | 12 +- src/map/itemdb.h | 3 + src/map/map.c | 58 +- src/map/mercenary.c | 2 +- src/map/mob.c | 10 +- src/map/packets.h | 1 + src/map/party.c | 2 +- src/map/pc.c | 258 +- src/map/pc.h | 18 +- src/map/script.c | 4 +- src/map/skill.c | 9261 ++++++++++++++++----------------- src/map/skill.h | 25 +- src/map/status.c | 2787 +++++----- src/map/status.h | 770 +-- src/map/unit.c | 63 +- src/map/vending.c | 2 +- 54 files changed, 12206 insertions(+), 10784 deletions(-) create mode 100644 db/sc_config.txt (limited to 'npc/re') diff --git a/conf/battle/status.conf b/conf/battle/status.conf index 5341b606b..372619fd1 100644 --- a/conf/battle/status.conf +++ b/conf/battle/status.conf @@ -12,15 +12,6 @@ // Should skill casting be cancelled when inflicted by curse/stun/sleep/etc (includes silence) (Note 3)? status_cast_cancel: 0 -// Will certain skill status-changes be removed on logout? -// This mimics official servers, where Extremity Fist's no SP regen, -// Strip Equipment, and some other buffs are removed when you logout. Setting is: -// 0 = remove nothing. -// 1 = remove negative buffs (stripping, EF) -// 2 = remove positive buffs (maximize power, steel body...) -// 3 = remove both negative and positive buffs. -debuff_on_logout: 3 - // Adjustment for the natural rate of resistance from status changes. // If 50, status defense is halved, and you need twice as much stats to block // them (eg: 200 vit to completely block stun) diff --git a/conf/messages.conf b/conf/messages.conf index 5bff9a5af..e2886a57d 100644 --- a/conf/messages.conf +++ b/conf/messages.conf @@ -1505,8 +1505,5 @@ //src/map/pc.c::pc_isUseitem 1474: You cannot use this item while sitting -//src/map/clif.c::clif_parse_NpcClicked -1476: You cannot interact with NPCs while casting skills - //Custom translations import: conf/import/msg_conf.txt diff --git a/db/item_db2.txt b/db/item_db2.txt index 5ca7a825a..fe5a53d46 100644 --- a/db/item_db2.txt +++ b/db/item_db2.txt @@ -27,14 +27,14 @@ //5356,Pumpkin_Hat_H,Pumpkin Hat,5,20,,200,,2,,0,0xFFFFFFFF,7,2,256,,0,1,206,{ bonus bAllStats,2; bonus2 bSubRace,RC_Demon,5; bonus2 bMagicAddRace,RC_Demon,5; },{},{} //5811,Santa_Beard,Santa Beard,5,20,,100,,5,,0,0xFFFFFFFF,7,2,1,,0,0,25,{ bonus2 bSubRace,RC_Brute,5; },{},{} -//11702,Moon_Cookie,Moon Cookie,11,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_end SC_Poison; sc_end SC_Silence; sc_end SC_Blind; sc_end SC_Confusion; sc_end SC_Curse; sc_end SC_Hallucination; itemskill "AL_BLESSING",7; },{},{} -//12131,Lucky_Potion,Lucky Potion,0,2,,100,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_LUKFood,180000,15; },{},{} +//11702,Moon_Cookie,Moon Cookie,11,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_end SC_Poison; sc_end SC_Silence; sc_end SC_Blind; sc_end SC_Confusion; sc_end SC_Curse; sc_end SC_ILLUSION; itemskill "AL_BLESSING",7; },{},{} +//12131,Lucky_Potion,Lucky Potion,0,2,,100,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_LUK,180000,15; },{},{} //12143,Red_Can,Red Can,2,50000,,300,,,,,0xFFFFFFFF,7,2,,,,,,{ percentheal 25,25; },{},{} //Event effect: Summon monster? Probably Rice_Cake. x_x //12199,Rice_Scroll,Rice Scroll,2,0,,0,,,,,0xFFFFFFFF,7,2,,,,,,{},{},{} //12200,Event_Cake,Event Cake,2,20,,50,,,,,0xFFFFFFFF,7,2,,,,,,{ itemskill "PR_MAGNIFICAT",3; },{},{} -//12238,New_Year_Rice_Cake_1,New Year Rice Cake,0,20,,100,,,,,0xFFFFFFFF,7,2,,,,,,{ percentheal 20,15; sc_start SC_STRFood,1200000,3; sc_start SC_INTFood,1200000,3; sc_start SC_LUKFood,1200000,3; sc_start SC_SpeedUp1,5000,0; },{},{} -//12239,New_Year_Rice_Cake_2,New Year Rice Cake,0,20,,100,,,,,0xFFFFFFFF,7,2,,,,,,{ percentheal 20,15; sc_start SC_DEXFood,1200000,3; sc_start SC_AGIFood,1200000,3; sc_start SC_VITFood,1200000,3; sc_start SC_SpeedUp1,5000,0; },{},{} +//12238,New_Year_Rice_Cake_1,New Year Rice Cake,0,20,,100,,,,,0xFFFFFFFF,7,2,,,,,,{ percentheal 20,15; sc_start SC_FOOD_STR,1200000,3; sc_start SC_FOOD_INT,1200000,3; sc_start SC_FOOD_LUK,1200000,3; sc_start SC_MOVHASTE_INFINITY,5000,0; },{},{} +//12239,New_Year_Rice_Cake_2,New Year Rice Cake,0,20,,100,,,,,0xFFFFFFFF,7,2,,,,,,{ percentheal 20,15; sc_start SC_FOOD_DEX,1200000,3; sc_start SC_FOOD_AGI,1200000,3; sc_start SC_FOOD_VIT,1200000,3; sc_start SC_MOVHASTE_INFINITY,5000,0; },{},{} // iRO St. Patrick's Day Event 2008 //============================================================= diff --git a/db/item_delay.txt b/db/item_delay.txt index ec9d9c020..afcb56f9e 100644 --- a/db/item_delay.txt +++ b/db/item_delay.txt @@ -21,4 +21,16 @@ 11522,1000 // Red_Raffle_Sap 11523,2000 // Yellow_Raffle_Sap 11524,3000 // White_Raffle_Sap -11525,5000 // Mora_Hip_Tea \ No newline at end of file +11525,5000 // Mora_Hip_Tea + +12622,3000 // Reins_Of_Mount + +//12580,0 // Vending_Search_Scroll +//12581,0 // Vending_Search_Scroll2 +//12591,0 // Vending_Search_Scroll3 + +12725,120000 // Runstone_Nosiege,Nauthiz Rune +12726,30000 // Runstone_Rhydo,Raido Rune +12727,60000 // Runstone_Verkana,Berkana Rune +12732,1000 // Runstone_Pertz,Wyrd Rune + diff --git a/db/job_db2.txt b/db/job_db2.txt index 1880808fa..a36cc3d88 100644 --- a/db/job_db2.txt +++ b/db/job_db2.txt @@ -212,7 +212,7 @@ // Sura (Regular) 4070,2,5,0,1,1,0,0,0,1,2,5,0,0,3,3,1,0,0,3,1,0,0,2,2,5,0,0,4,4,1,3,0,0,0,2,5,5,0,0,0,4,3,2,2,0,0,0,4,5,5 // Genetic (Regular) -4071,4,4,5,0,0,5,4,2,0,0,0,4,5,3,0,0,0,3,5,2,0,0,4,3,3,0,0,5,2,0,6,0,0,1,4,4,0,0,5,2,4,0,0,4,4,0,2,0,0,4 +4071,4,4,5,0,0,5,4,2,0,0,0,4,5,0,0,0,0,3,5,2,0,0,4,3,3,0,0,5,2,0,6,0,0,0,4,4,1,0,5,2,4,0,0,4,4,0,2,0,0,4 // Shadow Chaser (Regular) 4072,6,1,0,0,1,0,6,2,5,4,0,0,4,6,0,0,2,0,3,3,4,5,0,0,3,6,0,0,3,0,1,1,3,6,0,0,4,4,0,0,0,3,3,1,1,0,0,5,2,0 // Royal Guard (Trans) @@ -226,7 +226,7 @@ // Sura (Trans) 4077,2,5,0,1,1,0,0,0,1,2,5,0,0,3,3,1,0,0,3,1,0,0,2,2,5,0,0,4,4,1,3,0,0,0,2,5,5,0,0,0,4,3,2,2,0,0,0,4,5,5 // Genetic (Trans) -4078,4,4,5,0,0,5,4,2,0,0,0,4,5,3,0,0,0,3,5,2,0,0,4,3,3,0,0,5,2,0,6,0,0,1,4,4,0,0,5,2,4,0,0,4,4,0,2,0,0,4 +4078,4,4,5,0,0,5,4,2,0,0,0,4,5,0,0,0,0,3,5,2,0,0,4,3,3,0,0,5,2,0,6,0,0,0,4,4,1,0,5,2,4,0,0,4,4,0,2,0,0,4 // Shadow Chaser (Trans) 4079,6,1,0,0,1,0,6,2,5,4,0,0,4,6,0,0,2,0,3,3,4,5,0,0,3,6,0,0,3,0,1,1,3,6,0,0,4,4,0,0,0,3,3,1,1,0,0,5,2,0 // Rune Knight (Dragon) (Regular) @@ -268,7 +268,7 @@ // Baby Sura 4106,2,5,0,1,1,0,0,0,1,2,5,0,0,3,3,1,0,0,3,1,0,0,2,2,5,0,0,4,4,1,3,0,0,0,2,5,5,0,0,0,4,3,2,2,0,0,0,4,5,5 // Baby Genetic -4107,4,4,5,0,0,5,4,2,0,0,0,4,5,3,0,0,0,3,5,2,0,0,4,3,3,0,0,5,2,0,6,0,0,1,4,4,0,0,5,2,4,0,0,4,4,0,2,0,0,4 +4107,4,4,5,0,0,5,4,2,0,0,0,4,5,0,0,0,0,3,5,2,0,0,4,3,3,0,0,5,2,0,6,0,0,0,4,4,1,0,5,2,4,0,0,4,4,0,2,0,0,4 // Baby Shadow Chaser 4108,6,1,0,0,1,0,6,2,5,4,0,0,4,6,0,0,2,0,3,3,4,5,0,0,3,6,0,0,3,0,1,1,3,6,0,0,4,4,0,0,0,3,3,1,1,0,0,5,2,0 // Baby Rune Knight (Dragon) @@ -283,8 +283,7 @@ 4190,1,2,0,3,0,4,5,0,6,0,1,2,0,3,0,4,5,0,6,0,1,2,0,3,0,4,5,0,6,0,1,2,0,3,0,4,5,0,6,0,1,2,0,3,0,4,5,0,6,0 // Super Baby (Expanded) 4191,1,2,0,3,0,4,5,0,6,0,1,2,0,3,0,4,5,0,6,0,1,2,0,3,0,4,5,0,6,0,1,2,0,3,0,4,5,0,6,0,1,2,0,3,0,4,5,0,6,0 -// Note: Kagerou and Oboro will temporarly use Ninja stat bonuses until official ones are known. // Kagerou 4211,5,0,4,0,2,3,0,1,6,0,5,1,2,0,4,6,3,0,1,5,2,0,6,3,4,0,5,0,2,0,1,4,0,5,4,0,3,5,1,0,2,4,1,0,5,6,2,1,0,5 // Oboro -4212,5,0,4,0,2,3,0,1,6,0,5,1,2,0,4,6,3,0,1,5,2,0,6,3,4,0,5,0,2,0,1,4,0,5,4,0,3,5,1,0,2,4,1,0,5,6,2,1,0,5 \ No newline at end of file +4212,5,0,4,0,2,3,0,1,6,0,5,1,2,0,4,6,3,0,1,5,2,0,6,3,4,0,5,0,2,0,1,4,0,5,4,0,3,5,1,0,2,4,1,0,5,6,2,1,0,5 diff --git a/db/pre-re/item_db.txt b/db/pre-re/item_db.txt index 501e657cc..f632e582a 100644 --- a/db/pre-re/item_db.txt +++ b/db/pre-re/item_db.txt @@ -28,8 +28,8 @@ 521,Leaflet_Of_Aloe,Aloe Leaflet,0,360,,20,,,,,0xFFFFFFFF,7,2,,,,,,{ itemheal rand(325,405),0; },{},{} 522,Fruit_Of_Mastela,Mastela Fruit,0,8500,,30,,,,,0xFFFFFFFF,7,2,,,,,,{ itemheal rand(400,600),0; },{},{} 523,Holy_Water,Holy Water,0,20,,30,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_end SC_Curse; },{},{} -525,Panacea,Panacea,0,500,,100,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_end SC_Poison; sc_end SC_Silence; sc_end SC_Blind; sc_end SC_Confusion; sc_end SC_Curse; sc_end SC_Hallucination; },{},{} -526,Royal_Jelly,Royal Jelly,0,7000,,150,,,,,0xFFFFFFFF,7,2,,,,,,{ itemheal rand(325,405),rand(40,60); sc_end SC_Poison; sc_end SC_Silence; sc_end SC_Blind; sc_end SC_Confusion; sc_end SC_Curse; sc_end SC_Hallucination; },{},{} +525,Panacea,Panacea,0,500,,100,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_end SC_Poison; sc_end SC_Silence; sc_end SC_Blind; sc_end SC_Confusion; sc_end SC_Curse; sc_end SC_ILLUSION; },{},{} +526,Royal_Jelly,Royal Jelly,0,7000,,150,,,,,0xFFFFFFFF,7,2,,,,,,{ itemheal rand(325,405),rand(40,60); sc_end SC_Poison; sc_end SC_Silence; sc_end SC_Blind; sc_end SC_Confusion; sc_end SC_Curse; sc_end SC_ILLUSION; },{},{} 528,Monster's_Feed,Monster's Feed,0,60,,150,,,,,0xFFFFFFFF,7,2,,,,,,{ itemheal rand(72,108),0; },{},{} 529,Candy,Candy,0,10,,30,,,,,0xFFFFFFFF,7,2,,,,,,{ itemheal rand(45,65),0; },{},{} 530,Candy_Striper,Candy Cane,0,20,,40,,,,,0xFFFFFFFF,7,2,,,,,,{ itemheal rand(105,145),0; },{},{} @@ -68,14 +68,14 @@ 563,Pizza_01,Doublecrust Swiss Fondue,0,1200,,150,,,,,0xFFFFFFFF,7,2,,,,,,{ itemheal rand(375,445),0; },{},{} 564,Rice_Ball,Rice Ball,0,1,,30,,,,,0xFFFFFFFF,7,2,,,,,,{ itemheal 200,0; },{},{} 565,Vita500_Bottle,Vita500,0,580,,100,,,,,0xFFFFFFFF,7,2,,,,,,{ itemheal rand(142,274),0; },{},{} -566,Tomyumkung,Tom Yum Goong,0,10000,,150,,,,,0xFFFFFFFF,7,2,,,,,,{ itemheal rand(244,350),rand(10,30); sc_end SC_Poison; sc_end SC_Silence; sc_end SC_Blind; sc_end SC_Confusion; sc_end SC_Curse; sc_end SC_Hallucination; },{},{} +566,Tomyumkung,Tom Yum Goong,0,10000,,150,,,,,0xFFFFFFFF,7,2,,,,,,{ itemheal rand(244,350),rand(10,30); sc_end SC_Poison; sc_end SC_Silence; sc_end SC_Blind; sc_end SC_Confusion; sc_end SC_Curse; sc_end SC_ILLUSION; },{},{} 567,Prawn,Shrimp,0,500,,40,,,,,0xFFFFFFFF,7,2,,,,,,{ itemheal rand(117,192),0; },{},{} 568,Lemon,Lemon,0,60,,40,,,,,0xFFFFFFFF,7,2,,,,,,{ itemheal 0,rand(10,20); },{},{} 569,Novice_Potion,Novice Potion,0,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ itemheal rand(22,33),0; },{},{} 570,Lucky_Candy,Lucky Candy,0,10,,30,,,,,0xFFFFFFFF,7,2,,,,,,{ itemheal rand(45,65),0; },{},{} 571,Lucky_Candy_Cane,Lucky Candy Cane,0,20,,40,,,,,0xFFFFFFFF,7,2,,,,,,{ itemheal rand(105,145),0; },{},{} 572,Lucky_Cookie,Lucky Cookie,0,1000,,30,,,,,0xFFFFFFFF,7,2,,,,,,{ itemheal rand(160,200),0; },{},{} -573,Chocolate_Drink,Chocolate Drink,0,7000,,150,,,,,0xFFFFFFFF,7,2,,,,,,{ itemheal rand(330,410),rand(45,65); sc_end SC_Poison; sc_end SC_Silence; sc_end SC_Blind; sc_end SC_Confusion; sc_end SC_Curse; sc_end SC_Hallucination; },{},{} +573,Chocolate_Drink,Chocolate Drink,0,7000,,150,,,,,0xFFFFFFFF,7,2,,,,,,{ itemheal rand(330,410),rand(45,65); sc_end SC_Poison; sc_end SC_Silence; sc_end SC_Blind; sc_end SC_Confusion; sc_end SC_Curse; sc_end SC_ILLUSION; },{},{} 574,Egg,Egg,0,20,,30,,,,,0xFFFFFFFF,7,2,,,,,,{ itemheal rand(33,42),0; },{},{} 575,Piece_Of_Cake_,2nd Anniversary Cake,0,10,,100,,,,,0xFFFFFFFF,7,2,,,,,,{ itemheal rand(270,330),0; },{},{} 576,Prickly_Fruit,Prickly Fruit,0,540,,60,,,,,0xFFFFFFFF,7,2,,,,,,{ itemheal rand(150,300),rand(20,30); },{},{} @@ -85,7 +85,7 @@ 580,Bread,Bread,0,150,,20,,,,,0xFFFFFFFF,7,2,,,,,,{ itemheal rand(50,90),0; },{},{} 581,Mushroom,Edible Mushroom,0,40,,20,,,,,0xFFFFFFFF,7,2,,,,,,{ itemheal rand(20,30),0; },{},{} 582,Orange,Orange,0,300,,20,,,,,0xFFFFFFFF,7,2,,,,,,{ itemheal rand(10,20),rand(10,20); },{},{} -583,KETUPAT_,Ketupat Sayur,0,7000,,150,,,,,0xFFFFFFFF,7,2,,,,,,{ itemheal rand(325,405),rand(40,60); sc_end SC_Poison; sc_end SC_Silence; sc_end SC_Blind; sc_end SC_Confusion; sc_end SC_Curse; sc_end SC_Hallucination; },{},{} +583,KETUPAT_,Ketupat Sayur,0,7000,,150,,,,,0xFFFFFFFF,7,2,,,,,,{ itemheal rand(325,405),rand(40,60); sc_end SC_Poison; sc_end SC_Silence; sc_end SC_Blind; sc_end SC_Confusion; sc_end SC_Curse; sc_end SC_ILLUSION; },{},{} 584,Fish_Ball_Soup,Fish Cake Soup,0,100,,60,,,,,0xFFFFFFFF,7,2,,,,,,{ itemheal rand(40,70),0; },{},{} 585,Wurst,Brusti,0,2,,40,,,,,0xFFFFFFFF,7,2,,,,,,{ itemheal rand(15,20),0; },{},{} 586,Mother's_Cake,Mother's Cake,0,20,,100,,,,,0xFFFFFFFF,7,2,,,,,,{ itemheal rand(325,405),0; },{},{} @@ -93,11 +93,11 @@ 588,Spaghetti,Spaghetti,0,100,,100,,,,,0xFFFFFFFF,7,2,,,,,,{ itemheal rand(40,70),0; },{},{} 589,Pizza_02,Pizza,0,1200,,150,,,,,0xFFFFFFFF,7,2,,,,,,{ itemheal rand(375,445),0; },{},{} 590,Brezel_,Pretzel,0,2,,20,,,,,0xFFFFFFFF,7,2,,,,,,{ itemheal rand(50,90),0; },{},{} -591,Caviar_Pancake,Caviar Pancake,0,0,,150,,,,,0xFFFFFFFF,7,2,,,,,,{ itemheal rand(325,405),rand(40,60); sc_end SC_Poison; sc_end SC_Silence; sc_end SC_Blind; sc_end SC_Confusion; sc_end SC_Curse; sc_end SC_Hallucination; },{},{} -592,Jam_Pancake,Jam Pancake,0,0,,150,,,,,0xFFFFFFFF,7,2,,,,,,{ itemheal rand(325,405),rand(40,60); sc_end SC_Poison; sc_end SC_Silence; sc_end SC_Blind; sc_end SC_Confusion; sc_end SC_Curse; sc_end SC_Hallucination; },{},{} -593,Honey_Pancake,Honey Pancake,0,0,,150,,,,,0xFFFFFFFF,7,2,,,,,,{ itemheal rand(325,405),rand(40,60); sc_end SC_Poison; sc_end SC_Silence; sc_end SC_Blind; sc_end SC_Confusion; sc_end SC_Curse; sc_end SC_Hallucination; },{},{} -594,Sour_Cream_Pancake,Sour-Cream Pancake,0,0,,150,,,,,0xFFFFFFFF,7,2,,,,,,{ itemheal rand(325,405),rand(40,60); sc_end SC_Poison; sc_end SC_Silence; sc_end SC_Blind; sc_end SC_Confusion; sc_end SC_Curse; sc_end SC_Hallucination; },{},{} -595,Mushroom_Pancake,Mushroom Pancake,0,0,,150,,,,,0xFFFFFFFF,7,2,,,,,,{ itemheal rand(325,405),rand(40,60); sc_end SC_Poison; sc_end SC_Silence; sc_end SC_Blind; sc_end SC_Confusion; sc_end SC_Curse; sc_end SC_Hallucination; },{},{} +591,Caviar_Pancake,Caviar Pancake,0,0,,150,,,,,0xFFFFFFFF,7,2,,,,,,{ itemheal rand(325,405),rand(40,60); sc_end SC_Poison; sc_end SC_Silence; sc_end SC_Blind; sc_end SC_Confusion; sc_end SC_Curse; sc_end SC_ILLUSION; },{},{} +592,Jam_Pancake,Jam Pancake,0,0,,150,,,,,0xFFFFFFFF,7,2,,,,,,{ itemheal rand(325,405),rand(40,60); sc_end SC_Poison; sc_end SC_Silence; sc_end SC_Blind; sc_end SC_Confusion; sc_end SC_Curse; sc_end SC_ILLUSION; },{},{} +593,Honey_Pancake,Honey Pancake,0,0,,150,,,,,0xFFFFFFFF,7,2,,,,,,{ itemheal rand(325,405),rand(40,60); sc_end SC_Poison; sc_end SC_Silence; sc_end SC_Blind; sc_end SC_Confusion; sc_end SC_Curse; sc_end SC_ILLUSION; },{},{} +594,Sour_Cream_Pancake,Sour-Cream Pancake,0,0,,150,,,,,0xFFFFFFFF,7,2,,,,,,{ itemheal rand(325,405),rand(40,60); sc_end SC_Poison; sc_end SC_Silence; sc_end SC_Blind; sc_end SC_Confusion; sc_end SC_Curse; sc_end SC_ILLUSION; },{},{} +595,Mushroom_Pancake,Mushroom Pancake,0,0,,150,,,,,0xFFFFFFFF,7,2,,,,,,{ itemheal rand(325,405),rand(40,60); sc_end SC_Poison; sc_end SC_Silence; sc_end SC_Blind; sc_end SC_Confusion; sc_end SC_Curse; sc_end SC_ILLUSION; },{},{} 596,Cute_Strawberry_Choco,Cute Strawberry-Choco,0,20,,100,,,,,0xFFFFFFFF,7,2,,,,,,{ itemheal 0,rand(1,100); },{},{} 597,Lovely_Choco_Tart,Lovely Choco-Tart,0,20,,100,,,,,0xFFFFFFFF,7,2,,,,,,{ itemheal rand(10,400),0; },{},{} 598,Light_Red_Pot,Light Red Potion,0,50,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ itemheal rand(45,65),0; },{},{} @@ -148,14 +148,14 @@ 642,Book_Of_Devil,Book of the Devil,2,1800,,50,,,,,0xFFFFFFFF,7,2,,,,,,{ pet 1101; },{},{} 643,Pet_Incubator,Pet Incubator,2,3000,,30,,,,,0xFFFFFFFF,7,2,,,,,,{ bpet; },{},{} 644,Gift_Box,Gift Box,2,1000,,200,,,,,0xFFFFFFFF,7,2,,,,,,{ getrandgroupitem(IG_GiftBox),1; },{},{} -645,Center_Potion,Concentration Potion,2,800,,100,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_ASPDPOTION0,1800000,0; },{},{} -656,Awakening_Potion,Awakening Potion,2,1500,,150,,,,,0xFFF7FEEF,7,2,,,40,,,{ sc_start SC_ASPDPOTION1,1800000,0; },{},{} -657,Berserk_Potion,Berserk Potion,2,3000,,200,,,,,0x01E646A6,7,2,,,85,,,{ sc_start SC_ASPDPOTION2,1800000,0; },{},{} +645,Center_Potion,Concentration Potion,2,800,,100,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_ATTHASTE_POTION1,1800000,0; },{},{} +656,Awakening_Potion,Awakening Potion,2,1500,,150,,,,,0xFFF7FEEF,7,2,,,40,,,{ sc_start SC_ATTHASTE_POTION2,1800000,0; },{},{} +657,Berserk_Potion,Berserk Potion,2,3000,,200,,,,,0x01E646A6,7,2,,,85,,,{ sc_start SC_ATTHASTE_POTION3,1800000,0; },{},{} 658,Union_Of_Tribe,Union of Tribe,2,2,,500,,,,,0xFFFFFFFF,7,2,,,,,,{ guildgetexp rand(600000,1200000); },{},{} 659,Heart_Of_Her,Her Heart,2,500,,50,,,,,0xFFFFFFFF,7,2,,,,,,{ pet 1188; },{},{} 660,Prohibition_Red_Candle,Forbidden Red Candle,2,20000,,50,,,,,0xFFFFFFFF,7,2,,,,,,{ pet 1200; },{},{} 661,Sway_Apron,Soft Apron,2,20000,,50,,,,,0xFFFFFFFF,7,2,,,,,,{ pet 1275; },{},{} -662,Inspector_Certificate,Authoritative Badge,2,1450,,30,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_SpeedUp0,180000,0; },{},{} +662,Inspector_Certificate,Authoritative Badge,2,1450,,30,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_MOVHASTE_HORSE,180000,0; },{},{} 663,Korea_Rice_Cake,Korean Rice Cake,0,1,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ percentheal 10,0; },{},{} 664,Gift_Box_1,Gift Box,2,1000,,200,,,,,0xFFFFFFFF,7,2,,,,,,{ getrandgroupitem(IG_GiftBox_1),1; },{},{} 665,Gift_Box_2,Gift Box,2,1000,,200,,,,,0xFFFFFFFF,7,2,,,,,,{ getrandgroupitem(IG_GiftBox_2),1; },{},{} @@ -171,13 +171,13 @@ 675,Silver_Coin,Silver Coin,3,5000,,40,,,,,0xFFFFFFFF,7,2,,,,,,{},{},{} 676,Silver_Coin_Moneybag,Bag of Silver Coins,3,50000,,400,,,,,0xFFFFFFFF,7,2,,,,,,{},{},{} 677,White_Gold_Coin,Platinum Coin,3,2000,,40,,,,,0xFFFFFFFF,7,2,,,,,,{},{},{} -678,Poison_Bottle,Poison Bottle,2,5000,,100,,,,,0xFFFFFFFF,7,2,,,,,,{ if(Class==Job_Assassin_Cross) { sc_start SC_DPoison,60000,0; sc_start SC_ASPDPOTION3,60000,0; } else percentheal -100,-100; },{},{} +678,Poison_Bottle,Poison Bottle,2,5000,,100,,,,,0xFFFFFFFF,7,2,,,,,,{ if(Class==Job_Assassin_Cross) { sc_start SC_DPoison,60000,0; sc_start SC_ATTHASTE_INFINITY,60000,0; } else percentheal -100,-100; },{},{} 679,Gold_Pill,Pilule,2,5000,,300,,,,,0xFFFFFFFF,7,2,,,,,,{ if(rand(1000)<100) sc_start SC_DPoison,10000,0; sc_start SC_Poison,50000,0; },{},{} 680,Magical_Carnation,Magic Carnation,0,0,,1000,,,,,0xFFFFFFFF,7,2,,,,,,{ percentheal 0,20; },{},{} 681,Memory_Of_Wedding,Sweet Memory of Marriage,2,50000,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ if(getpartnerid()) sc_start SC_WEDDING,600000,0; },{},{} -682,Realgar_Wine,Distilled Fighting Spirit,2,0,,100,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_ATKPOTION,60000,30; },{},{} -683,Exorcize_Herb,Herb of Incantation,2,0,,50,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_MATKPOTION,60000,30; },{},{} -684,Durian,Durian,2,15000,,300,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_ATKPOTION,60000,10; sc_start SC_MATKPOTION,60000,10; },{},{} +682,Realgar_Wine,Distilled Fighting Spirit,2,0,,100,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_PLUSATTACKPOWER,60000,30; },{},{} +683,Exorcize_Herb,Herb of Incantation,2,0,,50,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_PLUSMAGICPOWER,60000,30; },{},{} +684,Durian,Durian,2,15000,,300,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_PLUSATTACKPOWER,60000,10; sc_start SC_PLUSMAGICPOWER,60000,10; },{},{} 685,RAMADAN,Ramadan,0,5000,,300,,,,,0xFFFFFFFF,7,2,,,,,,{ percentheal 100,50; },{},{} 686,Earth_Scroll_1_3,Level 3 Earth Spike,11,1000,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ itemskill "WZ_EARTHSPIKE",3; },{},{} 687,Earth_Scroll_1_5,Level 5 Earth Spike,11,2000,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ itemskill "WZ_EARTHSPIKE",5; },{},{} @@ -4560,7 +4560,7 @@ 12013,Shadow_Arrow_Container,Shadow Arrow Quiver,2,2,,250,,,,,0xFFFFFFFF,7,2,,,,,,{ getitem 1767,500; },{},{} 12014,Imma_Arrow_Container,Immaterial Arrow Quiver,2,2,,250,,,,,0xFFFFFFFF,7,2,,,,,,{ getitem 1757,500; },{},{} 12015,Rusty_Arrow_Container,Rusty Arrow Quiver,2,2,,250,,,,,0xFFFFFFFF,7,2,,,,,,{ getitem 1762,500; },{},{} -12016,Speed_Up_Potion,Speed Potion,2,2,,100,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_SpeedUp1,5000,0; },{},{} +12016,Speed_Up_Potion,Speed Potion,2,2,,100,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_MOVHASTE_INFINITY,5000,0; },{},{} 12017,Slow_Down_Potion,Slow Potion,2,2,,100,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_SlowDown,5000,0; },{},{} 12018,Fire_Cracker,Firecracker,2,2,,20,,,,,0xFFFFFFFF,7,2,,,,,,{ end; },{},{} 12019,Holy_Egg,Holy Egg,11,2,,150,,,,,0xFFFFFFFF,7,2,,,,,,{ itemskill "ALL_RESURRECTION",2; },{},{} @@ -4572,10 +4572,10 @@ 12025,Egg_Boy,Dano Festival Egg,2,1000,,200,,,,,0xFFFFFFFF,7,2,,,,,,{ getrandgroupitem(IG_EggBoy),1; },{},{} 12026,Egg_Girl,Dano Festival Egg,2,1000,,200,,,,,0xFFFFFFFF,7,2,,,,,,{ getrandgroupitem(IG_EggGirl),1; },{},{} 12027,Giggling_Box,Giggling Box,2,1000,,200,,,,,0xFFFFFFFF,7,2,,,,,,{ percentheal 9,0; if(rand(1000)<300) sc_start SC_Curse,30000,0; },{},{} -12028,Box_Of_Thunder,Box of Thunder,2,1000,,200,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_SpeedUp0,20000,0; },{},{} +12028,Box_Of_Thunder,Box of Thunder,2,1000,,200,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_MOVHASTE_HORSE,20000,0; },{},{} 12029,Gloomy_Box,Box of Gloom,11,1000,,200,,,,,0xFFFFFFFF,7,2,,,,,,{ itemskill "AC_CONCENTRATION",1; },{},{} -12030,Box_Of_Grudge,Box of Resentment,2,1000,,200,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_ATKPOTION,60000,20; },{},{} -12031,Sleepy_Box,Box of Drowsiness,2,1000,,200,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_MATKPOTION,60000,20; },{},{} +12030,Box_Of_Grudge,Box of Resentment,2,1000,,200,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_PLUSATTACKPOWER,60000,20; },{},{} +12031,Sleepy_Box,Box of Drowsiness,2,1000,,200,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_PLUSMAGICPOWER,60000,20; },{},{} 12032,Box_Of_Storm,Box of Storms,11,1000,,200,,,,,0xFFFFFFFF,7,2,,,,,,{ itemskill "ITEM_ENCHANTARMS",2; },{},{} 12033,Box_Of_Sunlight,Box of Sunlight,2,1000,,200,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_Intravision,30000,0; },{},{} 12034,Painting_Box,Box of Panting,2,1000,,200,,,,,0xFFFFFFFF,7,2,,,,,,{ percentheal 0,9; if(rand(1000)<300) sc_start SC_Silence,30000,0; },{},{} @@ -4585,66 +4585,66 @@ 12038,Lotto_Box04,Lotto Box 04,2,0,,20,,,,,0xFFFFFFFF,7,2,,,,,,{ getrandgroupitem(IG_LottoBox),1; },{},{} 12039,Lotto_Box05,Lotto Box 05,2,0,,20,,,,,0xFFFFFFFF,7,2,,,,,,{ getitem rand(7542,7546),1; },{},{} 12040,Stone_Of_Intelligence_,Stone of Sage,2,100000,,300,,,,,0xFFFFFFFF,7,2,,,,,,{ homevolution; },{},{} -12041,Str_Dish01,Fried Grasshopper Legs,0,2000,,60,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_STRFOOD,1200000,1; percentheal 5,0; },{},{} -12042,Str_Dish02,Seasoned Sticky Webfoot,0,4000,,500,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_STRFOOD,1200000,2; percentheal 5,0; },{},{} -12043,Str_Dish03,Bomber Steak,0,6000,,500,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_STRFOOD,1200000,3; percentheal 5,0; },{},{} -12044,Str_Dish04,Herb Marinade Beef,0,8000,,500,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_STRFOOD,1200000,4; percentheal 5,0; },{},{} -12045,Str_Dish05,Lutie Lady's Pancake,0,10000,,500,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_STRFOOD,1200000,5; percentheal 10,0; },{},{} -12046,Int_Dish01,Grape Juice Herbal Tea,0,2000,,100,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_INTFOOD,1200000,1; percentheal 0,5; },{},{} -12047,Int_Dish02,Autumn Red Tea,0,4000,,500,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_INTFOOD,1200000,2; percentheal 0,5; },{},{} -12048,Int_Dish03,Honey Herbal Tea,0,6000,,500,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_INTFOOD,1200000,3; percentheal 0,5; },{},{} -12049,Int_Dish04,Morroc Fruit Wine,0,8000,,300,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_INTFOOD,1200000,4; percentheal 0,5; },{},{} -12050,Int_Dish05,Mastela Fruit Wine,0,10000,,400,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_INTFOOD,1200000,5; percentheal 0,10; },{},{} -12051,Vit_Dish01,Steamed Crab Nippers,0,2000,,100,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_VITFOOD,1200000,1; percentheal 5,0; },{},{} -12052,Vit_Dish02,Assorted Seafood,0,4000,,200,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_VITFOOD,1200000,2; percentheal 5,0; },{},{} -12053,Vit_Dish03,Clam Soup,0,6000,,300,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_VITFOOD,1200000,3; percentheal 5,0; },{},{} -12054,Vit_Dish04,Seasoned Jellyfish,0,8000,,500,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_VITFOOD,1200000,4; percentheal 5,0; },{},{} -12055,Vit_Dish05,Spicy Fried Bao,0,10000,,800,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_VITFOOD,1200000,5; percentheal 10,0; },{},{} -12056,Agi_Dish01,Frog Egg Squid Ink Soup,0,2000,,100,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_AGIFOOD,1200000,1; percentheal 3,1; },{},{} -12057,Agi_Dish02,Smooth Noodle,0,4000,,100,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_AGIFOOD,1200000,2; percentheal 3,1; },{},{} -12058,Agi_Dish03,Tentacle Cheese Gratin,0,6000,,500,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_AGIFOOD,1200000,3; percentheal 3,1; },{},{} -12059,Agi_Dish04,Lutie Cold Noodle,0,8000,,400,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_AGIFOOD,1200000,4; percentheal 3,1; },{},{} -12060,Agi_Dish05,Steamed Bat Wing in Pumpkin,0,10000,,500,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_AGIFOOD,1200000,5; percentheal 6,2; },{},{} -12061,Dex_Dish01,Honey Grape Juice,0,2000,,100,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_DEXFOOD,1200000,1; percentheal 2,2; },{},{} -12062,Dex_Dish02,Chocolate Mousse Cake,0,4000,,200,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_DEXFOOD,1200000,2; percentheal 2,2; },{},{} -12063,Dex_Dish03,Fruit Mix,0,6000,,200,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_DEXFOOD,1200000,3; percentheal 2,2; },{},{} -12064,Dex_Dish04,Cream Sandwich,0,8000,,500,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_DEXFOOD,1200000,4; percentheal 2,2; },{},{} -12065,Dex_Dish05,Green Salad,0,10000,,200,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_DEXFOOD,1200000,5; percentheal 5,5; },{},{} -12066,Luk_Dish01,Fried Monkey Tails,0,2000,,60,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_LUKFOOD,1200000,1; percentheal 3,2; },{},{} -12067,Luk_Dish02,Mixed Juice,0,4000,,200,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_LUKFOOD,1200000,2; percentheal 3,2; },{},{} -12068,Luk_Dish03,Fried Sweet Potato,0,6000,,500,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_LUKFOOD,1200000,3; percentheal 4,2; },{},{} -12069,Luk_Dish04,Steamed Ancient Lips,0,8000,,500,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_LUKFOOD,1200000,4; percentheal 4,2; },{},{} -12070,Luk_Dish05,Fried Scorpion Tails,0,10000,,400,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_LUKFOOD,1200000,5; percentheal 5,2; },{},{} -12071,Str_Dish06,Shiny Marinade Beef,0,20000,,800,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_STRFOOD,1200000,6; percentheal 10,2; },{},{} -12072,Str_Dish07,Whole Roast,0,40000,,1000,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_STRFOOD,1200000,7; percentheal 10,4; },{},{} -12073,Str_Dish08,Bearfoot Special,0,60000,,500,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_STRFOOD,1200000,8; percentheal 15,6; },{},{} -12074,Str_Dish09,Tendon Satay,0,80000,,1000,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_STRFOOD,1200000,9; percentheal 15,8; },{},{} -12075,Str_Dish10,Steamed Tongue,0,100000,,1000,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_STRFOOD,1200000,10; percentheal 20,20; },{},{} -12076,Int_Dish06,Red Mushroom Wine,0,20000,,300,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_INTFOOD,1200000,6; percentheal 2,10; },{},{} -12077,Int_Dish07,Special Royal Jelly Herbal Tea,0,40000,,800,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_INTFOOD,1200000,7; percentheal 4,10; },{},{} -12078,Int_Dish08,Royal Family Tea,0,60000,,1000,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_INTFOOD,1200000,8; percentheal 6,10; },{},{} -12079,Int_Dish09,Tristan XII,0,80000,,1000,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_INTFOOD,1200000,9; percentheal 8,15; },{},{} -12080,Int_Dish10,Dragon Breath Cocktail,0,100000,,1000,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_INTFOOD,1200000,10; percentheal 10,20; },{},{} -12081,Vit_Dish06,Awfully Bitter Bracer,0,20000,,500,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_VITFOOD,1200000,6; percentheal 13,0; },{},{} -12082,Vit_Dish07,Sumptuous Feast,0,40000,,400,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_VITFOOD,1200000,7; percentheal 16,0; },{},{} -12083,Vit_Dish08,Giant Burito,0,60000,,1000,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_VITFOOD,1200000,8; percentheal 19,0; },{},{} -12084,Vit_Dish09,Ascending Dragon Soup,0,80000,,1000,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_VITFOOD,1200000,9; percentheal 22,0; },{},{} -12085,Vit_Dish10,Immortal Stew,0,100000,,1000,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_VITFOOD,1200000,10; percentheal 25,0; },{},{} -12086,Agi_Dish06,Chile Shrimp Gratin,0,20000,,800,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_AGIFOOD,1200000,6; percentheal 7,2; },{},{} -12087,Agi_Dish07,Steamed Alligator with Vegetable,0,40000,,800,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_AGIFOOD,1200000,7; percentheal 8,2; },{},{} -12088,Agi_Dish08,Incredibly Spicy Curry,0,60000,,1000,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_AGIFOOD,1200000,8; percentheal 9,2; },{},{} -12089,Agi_Dish09,Special Meat Stew,0,80000,,1000,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_AGIFOOD,1200000,9; percentheal 10,2; },{},{} -12090,Agi_Dish10,Steamed Desert Scorpions,0,100000,,1000,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_AGIFOOD,1200000,10; percentheal 15,5; },{},{} -12091,Dex_Dish06,Peach Cake,0,20000,,800,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_DEXFOOD,1200000,6; percentheal 5,6; },{},{} -12092,Dex_Dish07,Soul Haunted Bread,0,40000,,800,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_DEXFOOD,1200000,7; percentheal 5,7; },{},{} -12093,Dex_Dish08,Special Toast,0,60000,,1000,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_DEXFOOD,1200000,8; percentheal 5,8; },{},{} -12094,Dex_Dish09,Heavenly Fruit Juice,0,80000,,500,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_DEXFOOD,1200000,9; percentheal 5,9; },{},{} -12095,Dex_Dish10,Hwergelmir's Tonic,0,100000,,1000,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_DEXFOOD,1200000,10; percentheal 10,10; },{},{} -12096,Luk_Dish06,Lucky Soup,0,20000,,300,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_LUKFOOD,1200000,6; percentheal 6,3; },{},{} -12097,Luk_Dish07,Assorted Shish Kebob,0,40000,,800,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_LUKFOOD,1200000,7; percentheal 7,3; },{},{} -12098,Luk_Dish08,Strawberry Flavored Rice Ball,0,60000,,400,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_LUKFOOD,1200000,8; percentheal 9,3; },{},{} -12099,Luk_Dish09,Blood Flavored Soda,0,80000,,1000,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_LUKFOOD,1200000,9; percentheal 10,4; },{},{} -12100,Luk_Dish10,Cooked Nine Tail's Tails,0,100000,,500,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_LUKFOOD,1200000,10; percentheal 14,8; },{},{} +12041,Str_Dish01,Fried Grasshopper Legs,0,2000,,60,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_STR,1200000,1; percentheal 5,0; },{},{} +12042,Str_Dish02,Seasoned Sticky Webfoot,0,4000,,500,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_STR,1200000,2; percentheal 5,0; },{},{} +12043,Str_Dish03,Bomber Steak,0,6000,,500,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_STR,1200000,3; percentheal 5,0; },{},{} +12044,Str_Dish04,Herb Marinade Beef,0,8000,,500,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_STR,1200000,4; percentheal 5,0; },{},{} +12045,Str_Dish05,Lutie Lady's Pancake,0,10000,,500,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_STR,1200000,5; percentheal 10,0; },{},{} +12046,Int_Dish01,Grape Juice Herbal Tea,0,2000,,100,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_INT,1200000,1; percentheal 0,5; },{},{} +12047,Int_Dish02,Autumn Red Tea,0,4000,,500,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_INT,1200000,2; percentheal 0,5; },{},{} +12048,Int_Dish03,Honey Herbal Tea,0,6000,,500,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_INT,1200000,3; percentheal 0,5; },{},{} +12049,Int_Dish04,Morroc Fruit Wine,0,8000,,300,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_INT,1200000,4; percentheal 0,5; },{},{} +12050,Int_Dish05,Mastela Fruit Wine,0,10000,,400,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_INT,1200000,5; percentheal 0,10; },{},{} +12051,Vit_Dish01,Steamed Crab Nippers,0,2000,,100,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_VIT,1200000,1; percentheal 5,0; },{},{} +12052,Vit_Dish02,Assorted Seafood,0,4000,,200,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_VIT,1200000,2; percentheal 5,0; },{},{} +12053,Vit_Dish03,Clam Soup,0,6000,,300,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_VIT,1200000,3; percentheal 5,0; },{},{} +12054,Vit_Dish04,Seasoned Jellyfish,0,8000,,500,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_VIT,1200000,4; percentheal 5,0; },{},{} +12055,Vit_Dish05,Spicy Fried Bao,0,10000,,800,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_VIT,1200000,5; percentheal 10,0; },{},{} +12056,Agi_Dish01,Frog Egg Squid Ink Soup,0,2000,,100,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_AGI,1200000,1; percentheal 3,1; },{},{} +12057,Agi_Dish02,Smooth Noodle,0,4000,,100,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_AGI,1200000,2; percentheal 3,1; },{},{} +12058,Agi_Dish03,Tentacle Cheese Gratin,0,6000,,500,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_AGI,1200000,3; percentheal 3,1; },{},{} +12059,Agi_Dish04,Lutie Cold Noodle,0,8000,,400,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_AGI,1200000,4; percentheal 3,1; },{},{} +12060,Agi_Dish05,Steamed Bat Wing in Pumpkin,0,10000,,500,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_AGI,1200000,5; percentheal 6,2; },{},{} +12061,Dex_Dish01,Honey Grape Juice,0,2000,,100,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_DEX,1200000,1; percentheal 2,2; },{},{} +12062,Dex_Dish02,Chocolate Mousse Cake,0,4000,,200,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_DEX,1200000,2; percentheal 2,2; },{},{} +12063,Dex_Dish03,Fruit Mix,0,6000,,200,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_DEX,1200000,3; percentheal 2,2; },{},{} +12064,Dex_Dish04,Cream Sandwich,0,8000,,500,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_DEX,1200000,4; percentheal 2,2; },{},{} +12065,Dex_Dish05,Green Salad,0,10000,,200,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_DEX,1200000,5; percentheal 5,5; },{},{} +12066,Luk_Dish01,Fried Monkey Tails,0,2000,,60,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_LUK,1200000,1; percentheal 3,2; },{},{} +12067,Luk_Dish02,Mixed Juice,0,4000,,200,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_LUK,1200000,2; percentheal 3,2; },{},{} +12068,Luk_Dish03,Fried Sweet Potato,0,6000,,500,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_LUK,1200000,3; percentheal 4,2; },{},{} +12069,Luk_Dish04,Steamed Ancient Lips,0,8000,,500,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_LUK,1200000,4; percentheal 4,2; },{},{} +12070,Luk_Dish05,Fried Scorpion Tails,0,10000,,400,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_LUK,1200000,5; percentheal 5,2; },{},{} +12071,Str_Dish06,Shiny Marinade Beef,0,20000,,800,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_STR,1200000,6; percentheal 10,2; },{},{} +12072,Str_Dish07,Whole Roast,0,40000,,1000,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_STR,1200000,7; percentheal 10,4; },{},{} +12073,Str_Dish08,Bearfoot Special,0,60000,,500,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_STR,1200000,8; percentheal 15,6; },{},{} +12074,Str_Dish09,Tendon Satay,0,80000,,1000,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_STR,1200000,9; percentheal 15,8; },{},{} +12075,Str_Dish10,Steamed Tongue,0,100000,,1000,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_STR,1200000,10; percentheal 20,20; },{},{} +12076,Int_Dish06,Red Mushroom Wine,0,20000,,300,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_INT,1200000,6; percentheal 2,10; },{},{} +12077,Int_Dish07,Special Royal Jelly Herbal Tea,0,40000,,800,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_INT,1200000,7; percentheal 4,10; },{},{} +12078,Int_Dish08,Royal Family Tea,0,60000,,1000,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_INT,1200000,8; percentheal 6,10; },{},{} +12079,Int_Dish09,Tristan XII,0,80000,,1000,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_INT,1200000,9; percentheal 8,15; },{},{} +12080,Int_Dish10,Dragon Breath Cocktail,0,100000,,1000,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_INT,1200000,10; percentheal 10,20; },{},{} +12081,Vit_Dish06,Awfully Bitter Bracer,0,20000,,500,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_VIT,1200000,6; percentheal 13,0; },{},{} +12082,Vit_Dish07,Sumptuous Feast,0,40000,,400,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_VIT,1200000,7; percentheal 16,0; },{},{} +12083,Vit_Dish08,Giant Burito,0,60000,,1000,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_VIT,1200000,8; percentheal 19,0; },{},{} +12084,Vit_Dish09,Ascending Dragon Soup,0,80000,,1000,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_VIT,1200000,9; percentheal 22,0; },{},{} +12085,Vit_Dish10,Immortal Stew,0,100000,,1000,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_VIT,1200000,10; percentheal 25,0; },{},{} +12086,Agi_Dish06,Chile Shrimp Gratin,0,20000,,800,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_AGI,1200000,6; percentheal 7,2; },{},{} +12087,Agi_Dish07,Steamed Alligator with Vegetable,0,40000,,800,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_AGI,1200000,7; percentheal 8,2; },{},{} +12088,Agi_Dish08,Incredibly Spicy Curry,0,60000,,1000,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_AGI,1200000,8; percentheal 9,2; },{},{} +12089,Agi_Dish09,Special Meat Stew,0,80000,,1000,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_AGI,1200000,9; percentheal 10,2; },{},{} +12090,Agi_Dish10,Steamed Desert Scorpions,0,100000,,1000,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_AGI,1200000,10; percentheal 15,5; },{},{} +12091,Dex_Dish06,Peach Cake,0,20000,,800,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_DEX,1200000,6; percentheal 5,6; },{},{} +12092,Dex_Dish07,Soul Haunted Bread,0,40000,,800,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_DEX,1200000,7; percentheal 5,7; },{},{} +12093,Dex_Dish08,Special Toast,0,60000,,1000,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_DEX,1200000,8; percentheal 5,8; },{},{} +12094,Dex_Dish09,Heavenly Fruit Juice,0,80000,,500,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_DEX,1200000,9; percentheal 5,9; },{},{} +12095,Dex_Dish10,Hwergelmir's Tonic,0,100000,,1000,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_DEX,1200000,10; percentheal 10,10; },{},{} +12096,Luk_Dish06,Lucky Soup,0,20000,,300,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_LUK,1200000,6; percentheal 6,3; },{},{} +12097,Luk_Dish07,Assorted Shish Kebob,0,40000,,800,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_LUK,1200000,7; percentheal 7,3; },{},{} +12098,Luk_Dish08,Strawberry Flavored Rice Ball,0,60000,,400,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_LUK,1200000,8; percentheal 9,3; },{},{} +12099,Luk_Dish09,Blood Flavored Soda,0,80000,,1000,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_LUK,1200000,9; percentheal 10,4; },{},{} +12100,Luk_Dish10,Cooked Nine Tail's Tails,0,100000,,500,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_LUK,1200000,10; percentheal 14,8; },{},{} 12101,Citron,Citron,0,20,,300,,,,,0xFFFFFFFF,7,2,,,,,,{},{},{} 12102,Meat_Skewer,Grilled Skewer,0,20,,300,,,,,0xFFFFFFFF,7,2,,,,,,{},{},{} 12103,Bloody_Dead_Branch,Bloody Branch,2,10000,,200,,,,,0xFFFFFFFF,7,2,,,,,,{ monster "this",-1,-1,"--ja--",-3,1,""; },{},{} @@ -4666,8 +4666,8 @@ 12119,Resist_Water,Coldproof Potion,2,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start4 SC_ARMOR_ELEMENT,1200000,20,0,0,-15; },{},{} 12120,Resist_Earth,Earthproof Potion,2,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start4 SC_ARMOR_ELEMENT,1200000,0,20,-15,0; },{},{} 12121,Resist_Wind,Thunderproof Potion,2,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start4 SC_ARMOR_ELEMENT,1200000,0,-15,0,20; },{},{} -12122,Sesame_Pastry,Sesame Pastry,2,2,,70,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_HITFOOD,1200000,30; },{},{} -12123,Honey_Pastry,Honey Pastry,2,2,,70,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FLEEFOOD,1200000,30; },{},{} +12122,Sesame_Pastry,Sesame Pastry,2,2,,70,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_BASICHIT,1200000,30; },{},{} +12123,Honey_Pastry,Honey Pastry,2,2,,70,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_BASICAVOIDANCE,1200000,30; },{},{} 12124,Rainbow_Cake,Rainbow Cake,2,2,,70,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_BATKFOOD,1200000,10; sc_start SC_MATKFOOD,120000,10; },{},{} 12125,Outdoor_Cooking_Kits,Outdoor Cooking Kit,2,500,,20,,,,,0xFFFFFFFF,7,2,,,,,,{ cooking 11; },{},{} 12126,Indoor_Cooking_Kits,Home Cooking Kit,2,1000,,30,,,,,0xFFFFFFFF,7,2,,,,,,{ cooking 12; },{},{} @@ -4686,7 +4686,7 @@ 12139,3rd_Stage_Prize,Third Stage Prize,2,0,,0,,,,,0xFFFFFFFF,7,2,,,,,,{},{},{} 12140,4th_Stage_Prize,Fourth Stage Prize,2,0,,0,,,,,0xFFFFFFFF,7,2,,,,,,{},{},{} 12141,5th_Stage_Prize,Fifth Stage Prize,2,0,,0,,,,,0xFFFFFFFF,7,2,,,,,,{},{},{} -12142,Magic_Book,Book of Magic,2,0,,100,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_AGIFOOD,1800000,10; },{},{} +12142,Magic_Book,Book of Magic,2,0,,100,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_AGI,1800000,10; },{},{} 12143,Red_Can,Red Can,2,50000,,300,,,,,0xFFFFFFFF,7,2,,,,,,{},{},{} 12144,Sphere_Case_Wind,Lightning Sphere Pack,2,2,,350,,,,,0xFFFFFFFF,7,2,,,,,,{ getitem 13204,500; },{},{} 12145,Sphere_Case_Darkness,Blind Sphere Pack,2,2,,350,,,,,0xFFFFFFFF,7,2,,,,,,{ getitem 13206,500; },{},{} @@ -4753,66 +4753,66 @@ 12205,Dex_Dish10_,Hwergelmir's Tonic,0,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_DEX_CASH,1800000,10; percentheal 15,5; },{},{} 12206,Luk_Dish10_,Cooked Nine Tail's Tails,0,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_LUK_CASH,1800000,10; percentheal 15,5; },{},{} 12207,Vit_Dish10_,Stew Of Immortality,0,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_VIT_CASH,1800000,10; percentheal 15,5; },{},{} -12208,Battle_Manual,Battle Manual,2,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_EXPBOOST,1800000,50; },{},{} -12209,Insurance,Life Insurance,2,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_LIFEINSURANCE,1800000,0; },{},{} -12210,Bubble_Gum,Bubble Gum,2,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_ITEMBOOST,1800000,200; },{},{} +12208,Battle_Manual,Battle Manual,2,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_CASH_PLUSEXP,1800000,50; },{},{} +12209,Insurance,Life Insurance,2,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_CASH_DEATHPENALTY,1800000,0; },{},{} +12210,Bubble_Gum,Bubble Gum,2,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_CASH_RECEIVEITEM,1800000,200; },{},{} 12211,Kafra_Card,Kafra Card,2,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ callfunc "F_CashStore"; },{},{} 12212,Giant_Fly_Wing,Giant Fly Wing,2,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ callfunc "F_CashPartyCall"; },{},{} 12213,Neuralizer,Neuralizer,11,2,,0,,,,,0xFFFFFFFF,7,2,,,,,,{ callfunc "F_CashReset"; },{},{} -12214,Convex_Mirror,Convex Mirror,2,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_BOSSMAPINFO,600000,0; },{},{} +12214,Convex_Mirror,Convex Mirror,2,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_CASH_BOSS_ALARM,600000,0; },{},{} 12215,Blessing_10_Scroll,LV10 Blessing Scroll,2,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ skilleffect "AL_BLESSING",0; sc_start SC_BLESSING,240000,10; },{},{} -12216,Inc_Agi_10_Scroll,LV10 Agil Scroll,2,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ if(Hp>15) { skilleffect "AL_INCAGI",0; sc_start SC_INCREASEAGI,240000,10; heal -15,0; } },{},{} +12216,Inc_Agi_10_Scroll,LV10 Agil Scroll,2,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ if(Hp>15) { skilleffect "AL_INCAGI",0; sc_start SC_INC_AGI,240000,10; heal -15,0; } },{},{} 12217,Aspersio_5_Scroll,LV5 Aspersio Scroll,2,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ if(countitem(523)>0) { skilleffect "PR_ASPERSIO",0; sc_start SC_ASPERSIO,180000,5; delitem 523,1; } },{},{} 12218,Assumptio_5_Scroll,LV5 Assumptio Scroll,2,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_ASSUMPTIO,100000,5; skilleffect "HP_ASSUMPTIO",0; },{},{} 12219,Wind_Walk_10_Scroll,LV10 Wind Walker Scroll,2,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ skilleffect "SN_WINDWALK",0; sc_start SC_WINDWALK,250000,5; },{},{} 12220,Adrenaline_Scroll,LV5 Adrenaline Scroll,2,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ set .@type,getiteminfo(getequipid(EQI_HAND_R),11); if (.@type==6||.@type==7||.@type==8) { skilleffect "BS_ADRENALINE",0; sc_start SC_ADRENALINE,150000,5; } },{},{} 12221,Megaphone_,Megaphone,2,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ input @megaphone$; announce strcharinfo(0) + ": " + @megaphone$,bc_all,0xFF0000; end; },{},{} 12225,Sweet_Candy_Striper,Sweet Candy Cane,2,20,,50,,,,,0xFFFFFFFF,7,2,,,,,,{ pet 1245; },{},{} -12226,Examination1,Examination 1,0,20,,50,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_SpeedUp0,5400000,0; percentheal 100,100; sc_start SC_STRFOOD,5400000,10; sc_start SC_DEXFOOD,5400000,5; sc_start SC_ATKPOTION,5400000,22; sc_start SC_MATKFOOD,5400000,15; },{},{} -12227,Examination2,Examination 2,0,20,,50,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_SpeedUp0,5400000,0; percentheal 100,100; sc_start SC_INTFOOD,5400000,8; sc_start SC_VITFOOD,5400000,7; sc_start SC_LUKFOOD,5400000,7; sc_start SC_ATKPOTION,5400000,10; },{},{} -12228,Examination3,Examination 3,0,20,,50,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_SpeedUp0,5400000,0; percentheal 100,100; sc_start SC_AGIFOOD,5400000,15; sc_start SC_ATKPOTION,5400000,52; sc_start SC_MATKFOOD,5400000,10; },{},{} -12229,Examination4,Examination 4,0,20,,50,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_SpeedUp0,5400000,0; percentheal 100,100; sc_start SC_STRFOOD,5400000,3; sc_start SC_AGIFOOD,5400000,5; sc_start SC_VITFOOD,5400000,10; sc_start SC_MATKFOOD,5400000,52; },{},{} -12230,Examination5,Examination 5,0,20,,50,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_SpeedUp0,5400000,0; percentheal 100,100; sc_start SC_INTFOOD,5400000,3; sc_start SC_DEXFOOD,5400000,12; sc_start SC_ATKPOTION,5400000,20; sc_start SC_MATKFOOD,5400000,20; },{},{} -12231,Examination6,Examination 6,0,20,,50,,,,,0xFFFFFFFF,7,2,,,,,,{ percentheal 100,100; sc_start SC_SpeedUp0,5400000,0; sc_start SC_STRFOOD,5400000,6; sc_start SC_DEXFOOD,5400000,6; sc_start SC_AGIFOOD,5400000,6; sc_start SC_INTFOOD,5400000,6; sc_start SC_VITFOOD,5400000,6; sc_start SC_LUKFOOD,5400000,6; sc_start SC_ATKPOTION,5400000,24; sc_start SC_MATKFOOD,5400000,24; },{},{} -12232,Gingerbread,Ginger Bread,2,20,,150,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_ASPDPOTION1,900000,0; sc_start SC_SpeedUp0,900000,0; },{},{} +12226,Examination1,Examination 1,0,20,,50,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_MOVHASTE_HORSE,5400000,0; percentheal 100,100; sc_start SC_FOOD_STR,5400000,10; sc_start SC_FOOD_DEX,5400000,5; sc_start SC_PLUSATTACKPOWER,5400000,22; sc_start SC_MATKFOOD,5400000,15; },{},{} +12227,Examination2,Examination 2,0,20,,50,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_MOVHASTE_HORSE,5400000,0; percentheal 100,100; sc_start SC_FOOD_INT,5400000,8; sc_start SC_FOOD_VIT,5400000,7; sc_start SC_FOOD_LUK,5400000,7; sc_start SC_PLUSATTACKPOWER,5400000,10; },{},{} +12228,Examination3,Examination 3,0,20,,50,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_MOVHASTE_HORSE,5400000,0; percentheal 100,100; sc_start SC_FOOD_AGI,5400000,15; sc_start SC_PLUSATTACKPOWER,5400000,52; sc_start SC_MATKFOOD,5400000,10; },{},{} +12229,Examination4,Examination 4,0,20,,50,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_MOVHASTE_HORSE,5400000,0; percentheal 100,100; sc_start SC_FOOD_STR,5400000,3; sc_start SC_FOOD_AGI,5400000,5; sc_start SC_FOOD_VIT,5400000,10; sc_start SC_MATKFOOD,5400000,52; },{},{} +12230,Examination5,Examination 5,0,20,,50,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_MOVHASTE_HORSE,5400000,0; percentheal 100,100; sc_start SC_FOOD_INT,5400000,3; sc_start SC_FOOD_DEX,5400000,12; sc_start SC_PLUSATTACKPOWER,5400000,20; sc_start SC_MATKFOOD,5400000,20; },{},{} +12231,Examination6,Examination 6,0,20,,50,,,,,0xFFFFFFFF,7,2,,,,,,{ percentheal 100,100; sc_start SC_MOVHASTE_HORSE,5400000,0; sc_start SC_FOOD_STR,5400000,6; sc_start SC_FOOD_DEX,5400000,6; sc_start SC_FOOD_AGI,5400000,6; sc_start SC_FOOD_INT,5400000,6; sc_start SC_FOOD_VIT,5400000,6; sc_start SC_FOOD_LUK,5400000,6; sc_start SC_PLUSATTACKPOWER,5400000,24; sc_start SC_MATKFOOD,5400000,24; },{},{} +12232,Gingerbread,Ginger Bread,2,20,,150,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_ATTHASTE_POTION2,900000,0; sc_start SC_MOVHASTE_HORSE,900000,0; },{},{} 12233,Kvass,Kvass,0,20,,200,,,,,0xFFFFFFFF,7,2,,,,,,{ percentheal 100,100; },{},{} 12234,Cacao99,Fierce Cacao 99%,0,20,,100,,,,,0xFFFFFFFF,7,2,,,,,,{ percentheal 25,0; },{},{} 12235,Strawberry_Choco,Chocolate Strawberry,2,20,,100,,,,,0xFFFFFFFF,7,2,,,,,,{ percentheal 0,5; skilleffect "AL_BLESSING",0; sc_start SC_BLESSING,240000,10; },{},{} 12236,Choco_Tart,Chocolate Tart,11,20,,100,,,,,0xFFFFFFFF,7,2,,,,,,{ percentheal 5,0; itemskill "AL_ANGELUS",5; },{},{} -12237,Choco_Lump,Junky Chocolate,2,0,,100,,,,,0xFFFFFFFF,7,2,,,,,,{ percentheal 0,5; sc_start SC_Poison,18000,0; sc_start SC_Bleeding,18000,0; },{},{} +12237,Choco_Lump,Junky Chocolate,2,0,,100,,,,,0xFFFFFFFF,7,2,,,,,,{ percentheal 0,5; sc_start SC_Poison,18000,0; sc_start SC_BLOODING,18000,0; },{},{} 12238,New_Year_Rice_Cake_1,New Year Rice Cake,2,20,,100,,,,,0xFFFFFFFF,7,2,,,,,,{ if(rand(1000)<100) sc_start SC_DPoison,10000,0; sc_start SC_Poison,50000,0; },{},{} 12239,New_Year_Rice_Cake_2,New Year Rice Cake,2,20,,100,,,,,0xFFFFFFFF,7,2,,,,,,{ if(rand(1000)<100) sc_start SC_DPoison,10000,0; sc_start SC_Poison,50000,0; },{},{} 12240,Old_Yellow_Box,Old Yellow Box,2,20,,200,,,,,0xFFFFFFFF,7,2,,,,,,{ getrandgroupitem(IG_YellowBox),1; },{},{} -12241,M_Center_Potion,Mercenary Concentration Potion,2,800,,100,,,,,0xFFFFFFFF,7,2,,,,,,{ mercenary_sc_start SC_ASPDPOTION0,1800000,0; },{},{} -12242,M_Awakening_Potion,Mercenary Awakening Potion,2,1500,,150,,,,,0xFFFFFFFF,7,2,,,,,,{ mercenary_sc_start SC_ASPDPOTION1,1800000,0; },{},{} -12243,M_Berserk_Potion,Mercenary Berserk Potion,2,3000,,200,,,,,0xFFFFFFFF,7,2,,,,,,{ mercenary_sc_start SC_ASPDPOTION2,1800000,0; },{},{} +12241,M_Center_Potion,Mercenary Concentration Potion,2,800,,100,,,,,0xFFFFFFFF,7,2,,,,,,{ mercenary_sc_start SC_ATTHASTE_POTION1,1800000,0; },{},{} +12242,M_Awakening_Potion,Mercenary Awakening Potion,2,1500,,150,,,,,0xFFFFFFFF,7,2,,,,,,{ mercenary_sc_start SC_ATTHASTE_POTION2,1800000,0; },{},{} +12243,M_Berserk_Potion,Mercenary Berserk Potion,2,3000,,200,,,,,0xFFFFFFFF,7,2,,,,,,{ mercenary_sc_start SC_ATTHASTE_POTION3,1800000,0; },{},{} 12244,Old_Gift_Box,Old Gift Box,2,20,,200,,,,,0xFFFFFFFF,7,2,,,,,,{ getrandgroupitem(IG_OldGiftBox),1; },{},{} 12245,Green_Ale_US,Green Ale,0,5000,,500,,,,,0xFFFFFFFF,7,2,,,,,,{ percentheal 100,0; },{},{} 12246,Magic_Card_Album,Mystical Card Album,2,10000,,50,,,,,0xFFFFFFFF,7,2,,,,,,{ getrandgroupitem(IG_MagicCardAlbum),1; },{},{} 12247,Halohalo,Halo-Halo,2,2,,100,,,,,0xFFFFFFFF,7,2,,,20,,,{ sc_start SC_INCALLSTATUS,600000,3; },{},{} 12248,Masquerade_Ball_Box,Fancy Ball Box,2,20,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ getrandgroupitem(IG_Masquerade),1; },{},{} 12249,Payroll_Of_Kafra_,Payment Statement for Kafra Employee,2,20,,10,,,,,0xFFFFFFFF,7,2,,,,,,{},{},{} -12250,Str_Dish10_M,Steamed Tongue,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_STRFOOD,3600000,10; percentheal 20,20; },{},{} -12251,Agi_Dish10_M,Steamed Desert Scorpions,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_AGIFOOD,3600000,10; percentheal 15,5; },{},{} -12252,Int_Dish10_M,Dragon Breath Cocktail,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_INTFOOD,3600000,10; percentheal 10,20; },{},{} -12253,Dex_Dish10_M,Hwergelmir's Tonic,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_DEXFOOD,3600000,10; percentheal 10,10; },{},{} -12254,Luk_Dish10_M,Cooked Nine Tail,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_LUKFOOD,3600000,10; percentheal 14,8; },{},{} -12255,Vit_Dish10_M,Immortal Stew,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_VITFOOD,3600000,10; percentheal 25,0; },{},{} +12250,Str_Dish10_M,Steamed Tongue,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_STR,3600000,10; percentheal 20,20; },{},{} +12251,Agi_Dish10_M,Steamed Desert Scorpions,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_AGI,3600000,10; percentheal 15,5; },{},{} +12252,Int_Dish10_M,Dragon Breath Cocktail,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_INT,3600000,10; percentheal 10,20; },{},{} +12253,Dex_Dish10_M,Hwergelmir's Tonic,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_DEX,3600000,10; percentheal 10,10; },{},{} +12254,Luk_Dish10_M,Cooked Nine Tail,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_LUK,3600000,10; percentheal 14,8; },{},{} +12255,Vit_Dish10_M,Immortal Stew,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_VIT,3600000,10; percentheal 25,0; },{},{} 12256,PRO_Gift_Box,PRO Gift Box,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{},{},{} 12257,Cold_Medicine,Cold Medicine,0,20,,100,,,,,0xFFFFFFFF,7,2,,,50,,,{ percentheal 25,25; },{},{} 12258,Bombring_Box,Bomb Poring Box,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ if(strcharinfo(3)=="job3_rang02") { monster "this",-1,-1,"--ja--",1904,1,""; } },{},{} 12259,Miracle_Medicine,Miracle Tonic,2,0,,0,,,,,0xFFFFFFFF,7,2,,,,,,{ getexp 3000000,1500000; },{},{} 12260,Cool_Summer_Outfit,Cool Summer Outfit,2,0,,100,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_Summer,600000,0; },{},{} 12261,Secret_Medicine,Leap of Fantasy,2,0,,0,,,,,0xFFFFFFFF,7,2,,,,,,{ getexp 2000000,1000000; },{},{} -12262,Inspector_Certificate_,Authoritative Badge,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_SpeedUp0,180000,0; },{},{} -12263,Comp_Battle_Manual,Field Manual,2,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_EXPBOOST,1800000,50; },{},{} -12264,Comp_Bubble_Gum,Bubble Gum,2,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_ITEMBOOST,1800000,200; },{},{} -12265,Comp_Insurance,Life Insurrance,2,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_LIFEINSURANCE,1800000,0; },{},{} -12266,Sesame_Pastry_,Sesame Pastry,2,2,,70,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_HITFOOD,1200000,30; },{},{} -12267,Honey_Pastry_,Honey Pastry,2,2,,70,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FLEEFOOD,1200000,30; },{},{} -12268,Rainbow_Cake_,Rainbow Cake,2,2,,70,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_ATKPOTION,60000,10; sc_start SC_MATKFOOD,120000,10; },{},{} -12269,Tasty_Colonel,Tasty Pink Ration,2,2,,70,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_ATKPOTION,600000,15; },{},{} -12270,Tasty_Major,Tasty White Ration,2,2,,70,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_MATKPOTION,600000,15; },{},{} +12262,Inspector_Certificate_,Authoritative Badge,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_MOVHASTE_HORSE,180000,0; },{},{} +12263,Comp_Battle_Manual,Field Manual,2,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_CASH_PLUSEXP,1800000,50; },{},{} +12264,Comp_Bubble_Gum,Bubble Gum,2,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_CASH_RECEIVEITEM,1800000,200; },{},{} +12265,Comp_Insurance,Life Insurrance,2,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_CASH_DEATHPENALTY,1800000,0; },{},{} +12266,Sesame_Pastry_,Sesame Pastry,2,2,,70,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_BASICHIT,1200000,30; },{},{} +12267,Honey_Pastry_,Honey Pastry,2,2,,70,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_BASICAVOIDANCE,1200000,30; },{},{} +12268,Rainbow_Cake_,Rainbow Cake,2,2,,70,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_PLUSATTACKPOWER,60000,10; sc_start SC_MATKFOOD,120000,10; },{},{} +12269,Tasty_Colonel,Tasty Pink Ration,2,2,,70,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_PLUSATTACKPOWER,600000,15; },{},{} +12270,Tasty_Major,Tasty White Ration,2,2,,70,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_PLUSMAGICPOWER,600000,15; },{},{} 12271,Mre_A,Military Ration A,0,2,,70,,,,,0xFFFFFFFF,7,2,,,,,,{ percentheal 5,0; },{},{} 12272,Mre_B,Military Ration B,2,2,,70,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_INCHIT,600000,33; },{},{} 12273,Mre_C,Military Ration C,2,2,,70,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_INCFLEE,600000,33; },{},{} @@ -4824,16 +4824,16 @@ 12279,Undead_Element_Scroll,Undead Elemental Scroll,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start4 SC_ARMOR_RESIST,300000,20,20,20,20; },{},{} 12280,Holy_Element_Scroll,Holy Elemental Scroll,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ specialeffect2 EF_BENEDICTIO; sc_start SC_BENEDICTIO,300000,1; },{},{} 12281,Tresure_Box_WoE,Event Treasure Box,2,20,,150,,,,,0xFFFFFFFF,7,2,,,,,,{ getrandgroupitem(IG_Tresure_Box_WoE),1; },{},{} -12282,Internet_Cafe1,Internet Cafe1,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_INCALLSTATUS,5400000,3; sc_start SC_ATKPOTION,5400000,15; sc_start SC_MATKPOTION,5400000,15; },{},{} -12283,Internet_Cafe2,Internet Cafe2,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_INCSTR,5400000,8; sc_start SC_INCDEX,5400000,4; sc_start SC_INCAGI,5400000,6; sc_start SC_ATKPOTION,5400000,32; sc_start SC_INCFLEE,5400000,5; },{},{} -12284,Internet_Cafe3,Internet Cafe3,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_INCINT,5400000,8; sc_start SC_INCVIT,5400000,4; sc_start SC_INCDEX,5400000,6; sc_start SC_MATKPOTION,5400000,40; },{},{} -12285,Internet_Cafe4,Internet Cafe4,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_INCDEX,5400000,8; sc_start SC_INCLUK,5400000,4; sc_start SC_INCAGI,5400000,6; sc_start SC_ATKPOTION,5400000,24; sc_start SC_MATKPOTION,5400000,24; },{},{} +12282,Internet_Cafe1,Internet Cafe1,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_INCALLSTATUS,5400000,3; sc_start SC_PLUSATTACKPOWER,5400000,15; sc_start SC_PLUSMAGICPOWER,5400000,15; },{},{} +12283,Internet_Cafe2,Internet Cafe2,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_INCSTR,5400000,8; sc_start SC_INCDEX,5400000,4; sc_start SC_INCAGI,5400000,6; sc_start SC_PLUSATTACKPOWER,5400000,32; sc_start SC_INCFLEE,5400000,5; },{},{} +12284,Internet_Cafe3,Internet Cafe3,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_INCINT,5400000,8; sc_start SC_INCVIT,5400000,4; sc_start SC_INCDEX,5400000,6; sc_start SC_PLUSMAGICPOWER,5400000,40; },{},{} +12285,Internet_Cafe4,Internet Cafe4,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_INCDEX,5400000,8; sc_start SC_INCLUK,5400000,4; sc_start SC_INCAGI,5400000,6; sc_start SC_PLUSATTACKPOWER,5400000,24; sc_start SC_PLUSMAGICPOWER,5400000,24; },{},{} 12286,Masquerade_Ball_Box2,Masquerade Ball Box2,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ getrandgroupitem(IG_Masquerade_2),1; },{},{} 12287,Love_Angel,Love Angel Magic Powder,2,0,,0,,,,,0xFFFFFFFF,7,2,,,,,,{ setfont 1; },{},{} 12288,Squirrel,Squirrel Magic Powder,2,0,,0,,,,,0xFFFFFFFF,7,2,,,,,,{ setfont 2; },{},{} 12289,Gogo,Gogo Magic Powder,2,0,,0,,,,,0xFFFFFFFF,7,2,,,,,,{ setfont 3; },{},{} 12290,Mysterious_Can,Mysterious Can Magic Powder,2,10,,100,,,,,0xFFFFFFFF,7,2,,,,,,{ percentheal 5,0; skilleffect "AL_BLESSING",0; sc_start SC_BLESSING,120000,5; },{},{} -12291,Mysterious_PET_Bottle,Mysterious PET Bottle,2,10,,100,,,,,0xFFFFFFFF,7,2,,,,,,{ percentheal 5,0; skilleffect "AL_INCAGI",0; sc_start SC_INCREASEAGI,120000,5; },{},{} +12291,Mysterious_PET_Bottle,Mysterious PET Bottle,2,10,,100,,,,,0xFFFFFFFF,7,2,,,,,,{ percentheal 5,0; skilleffect "AL_INCAGI",0; sc_start SC_INC_AGI,120000,5; },{},{} 12292,Unripe_Fruit,Unripe Fruit,0,500,,200,,,,,0xFFFFFFFF,7,2,,,,,,{ percentheal 20,0; },{},{} 12293,Dried_Yggdrasilberry,Dried Yggdrasilberry,0,500,,200,,,,,0xFFFFFFFF,7,2,,,,,,{ percentheal 0,20; },{},{} 12294,PC_Bang_Coin_Box1,PC-Room Coin Box,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ getitem 2740,1; },{},{} @@ -4854,7 +4854,7 @@ 12309,Bulging_Head,JJangu Magic Powder,2,0,,0,,,,,0xFFFFFFFF,7,2,,,,,,{ setfont 9; },{},{} 12310,Spray_Of_Flowers,Spray Of Flowers,2,0,,50,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_INCFLEE,600000,10; },{},{} 12311,Large_Spray_Of_Flowers,Huge Spray Of Flowers,11,0,,100,,,,,0xFFFFFFFF,7,2,,,,,,{ itemskill "ALL_PARTYFLEE",1; },{},{} -12312,Thick_Manual50,Thick Battle Manual,2,0,,0,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_EXPBOOST,3600000,50; },{},{} +12312,Thick_Manual50,Thick Battle Manual,2,0,,0,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_CASH_PLUSEXP,3600000,50; },{},{} 12313,Protection_Of_Angel,Guardian Angel,2,0,,0,,,,,0xFFFFFFFF,7,2,,,,,,{},{},{} 12314,Noive_Box,Noive Box,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{},{},{} 12315,Goddess_Bless,Goddess Of Blessing,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{},{},{} @@ -4863,7 +4863,7 @@ 12318,Little_Heart,Small Hearts,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{},{},{} 12319,Strawberry_Cake,Rune Strawberry Cake,2,0,,300,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_INCATKRATE,600000,5; sc_start SC_INCMATKRATE,600000,5; },{},{} 12320,Pineapple_Juice,Schwartzwald Pine Jubilee,2,0,,300,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_INCHIT,600000,10; sc_start SC_INCFLEE2,600000,20; },{},{} -12321,Spicy_Sandwich,Arunafeltz Desert Sandwich,2,0,,300,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_INCCRI,600000,7; },{},{} +12321,Spicy_Sandwich,Arunafeltz Desert Sandwich,2,0,,300,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_CRITICALPERCENT,600000,7; },{},{} 12322,Chocolate_Pie,Chocolate Pie,0,0,,50,,,,,0xFFFFFFFF,7,2,,,,,,{ percentheal 5,5; },{},{} 12323,N_Fly_Wing,Novice Fly Wing,11,0,,0,,,,,0xFFFFFFFF,7,2,,,,,,{ itemskill "AL_TELEPORT",1; },{},{} 12324,N_Butterfly_Wing,Novice Butterfly Wing,11,0,,0,,,,,0xFFFFFFFF,7,2,,,,,,{ itemskill "AL_TELEPORT",3; },{},{} @@ -4896,7 +4896,7 @@ 12351,Shout_Megaphone,Scream Megaphone,11,20,,50,,,,,0xFFFFFFFF,7,2,,,,,,{ itemskill "MC_LOUD",1; },{},{} 12352,Dun_Tele_Scroll3,Dungeon Teleport Scroll 3,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{},{},{} 12353,Tiny_Waterbottle,Small Bottle,2,800,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_WATERWEAPON,90000,1; },{},{} -12354,Buche_De_Noel,Buche De Noel,2,2,,50,,,,,0xFFFFFFFF,7,2,,,,,,{ specialeffect2 EF_ANGELUS; sc_start SC_INCMHPRATE,600000,3; sc_start SC_INCMSPRATE,600000,3; sc_start SC_INCHITRATE,600000,3; sc_start SC_INCCRI,600000,7; },{},{} +12354,Buche_De_Noel,Buche De Noel,2,2,,50,,,,,0xFFFFFFFF,7,2,,,,,,{ specialeffect2 EF_ANGELUS; sc_start SC_INCMHPRATE,600000,3; sc_start SC_INCMSPRATE,600000,3; sc_start SC_INCHITRATE,600000,3; sc_start SC_CRITICALPERCENT,600000,7; },{},{} 12355,Xmas_Gift,Xmas Gift,2,2,,100,,,,,0xFFFFFFFF,7,2,,,,,,{ getrandgroupitem(IG_Xmas_Gift),1; },{},{} 12356,Louise_Costume_Box,Louise Costume Box,2,2,,100,,,,,0xFFFFFFFF,7,2,,,,,,{ getrandgroupitem(IG_Louise_Costume_Box),1; },{},{} 12357,Shiny_Wing_Gown,Shiny Wing Gown,2,20,,50,,,,,0xFFFFFFFF,7,2,,,,,,{ pet 1630; },{},{} @@ -4953,10 +4953,10 @@ 12408,Leaf_Cat_Ball,Leaf Cat Ball,2,0,,0,,,,,0xFFFFFFFF,7,2,,,,,,{ pet 2081; },{},{} 12409,Pork_Belly_H,Pork Belly H,2,0,,0,,,,,0xFFFFFFFF,7,2,,,,,,{},{},{} 12410,Spareribs_H,Spareribs H,2,0,,0,,,,,0xFFFFFFFF,7,2,,,,,,{},{},{} -12411,HE_Battle_Manual,HE Battle Manual,2,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_EXPBOOST,900000,200; },{},{} -12412,HE_Bubble_Gum,HE Bubble Gum,2,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_ITEMBOOST,900000,300; },{},{} +12411,HE_Battle_Manual,HE Battle Manual,2,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_CASH_PLUSEXP,900000,200; },{},{} +12412,HE_Bubble_Gum,HE Bubble Gum,2,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_CASH_RECEIVEITEM,900000,300; },{},{} 12413,PCBang_Coupon_Box2,PCBang Coupon Box2,2,20,,10,,,,,0xFFFFFFFF,7,2,,,,,,{},{},{} -12414,Guarana_Candy,Guarana Candy,2,20,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_ASPDPOTION0,1800000,0; sc_start SC_INCREASEAGI,140000,5; skilleffect "AL_INCAGI",0; },{},{} +12414,Guarana_Candy,Guarana Candy,2,20,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_ATTHASTE_POTION1,1800000,0; sc_start SC_INC_AGI,140000,5; skilleffect "AL_INCAGI",0; },{},{} 12415,Siege_Teleport_Scroll2,Siege Teleport Scroll2,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{},{},{} 12416,Lucky_Egg_C3,Lucky Egg C3,2,20,,10,,,,,0xFFFFFFFF,7,2,,,,,,{},{},{} 12417,Boost500,Boost500,2,100,,50,,,,,0xFFFFFFFF,7,2,,,,,,{},{},{} @@ -5015,7 +5015,7 @@ 12472,F_Convex_Mirror,F Convex Mirror,2,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{},{},{} 12473,RWC_Parti_Box,RWC Parti Box,2,20,,10,,,,,0xFFFFFFFF,7,2,,,,,,{},{},{} 12474,RWC_Final_Comp_Box,RWC Final Comp Box,2,20,,10,,,,,0xFFFFFFFF,7,2,,,,,,{},{},{} -12475,Cure_Free,Cure Free,2,20,,50,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_end SC_SILENCE; sc_end SC_BLEEDING; sc_end SC_POISON; sc_end SC_CURSE; sc_end SC_ORCISH; sc_end SC_CHANGEUNDEAD; itemheal 500,0; },{},{} +12475,Cure_Free,Cure Free,2,20,,50,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_end SC_SILENCE; sc_end SC_BLOODING; sc_end SC_POISON; sc_end SC_CURSE; sc_end SC_ORCISH; sc_end SC_CHANGEUNDEAD; itemheal 500,0; },{},{} 12476,PCBang_Coupon_Box3,PCBang Coupon Box3,2,20,,10,,,,,0xFFFFFFFF,7,2,,,,,,{},{},{} 12477,Gift_Bundle,Gift Bundle,2,0,,0,,,,,0xFFFFFFFF,7,2,,,,,,{},{},{} 12478,Chance_Box,Chance Box,2,20,,10,,,,,0xFFFFFFFF,7,2,,,,,,{},{},{} @@ -5127,7 +5127,7 @@ 12702,Old_Bleu_Box,Old Navy Box,2,0,,200,,,,,0xFFFFFFFF,7,2,,,,,,{ getrandgroupitem(IG_BleuBox),1; getrandgroupitem(IG_BleuBox),1; },{},{} 12703,Holy_Egg_2,Holy Egg,11,0,,50,,,,,0xFFFFFFFF,7,2,,,,,,{},{},{} 12704,Elixir_Of_Life,Elixir of Life,0,0,,10,,,,,0xFFFFFFFF,7,2,,,85,,,{ percentheal 100,0; },{},{} -12705,Noble_Nameplate,Noble Nameplate,2,0,,100,,,,,0xFFFFFFFF,7,2,,,90,,,{ sc_start SC_EXPBOOST,1800000,100; },{},{} +12705,Noble_Nameplate,Noble Nameplate,2,0,,100,,,,,0xFFFFFFFF,7,2,,,90,,,{ sc_start SC_CASH_PLUSEXP,1800000,100; },{},{} 12706,Lucky_Cookie01,Lucky Cookie,11,0,,100,,,,,0xFFFFFFFF,7,2,,,,,,{ itemskill "PR_GLORIA",5; },{},{} 12707,Lucky_Cookie02,Lucky Cookie,11,0,,100,,,,,0xFFFFFFFF,7,2,,,,,,{ itemskill "PR_MAGNIFICAT",1; },{},{} 12708,Lucky_Cookie03,Lucky Cookie,11,0,,100,,,,,0xFFFFFFFF,7,2,,,,,,{ itemskill "PR_IMPOSITIO",3; },{},{} @@ -5436,7 +5436,7 @@ 13269,Boost500_To_Throw,Throwing Boost 500,10,100,,10,0,,,,0x00040000,8,2,32768,,99,,9,{ sc_start SC_BOOST500,500000,10; },{},{} 13270,Full_SwingK_To_Throw,Throwing Full Swing K,10,100,,50,0,,,,0x00040000,8,2,32768,,99,,9,{ sc_start SC_FULL_SWING_K,500000,50; },{},{} 13271,Mana_Plus_To_Throw,Throwing Mana Plus,10,100,,50,0,,,,0x00040000,8,2,32768,,99,,9,{ sc_start SC_MANA_PLUS,500000,50; },{},{} -13272,Cure_Free_To_Throw,Throwing Cure Free,10,100,,50,0,,,,0x00040000,8,2,32768,,99,,9,{ sc_end SC_Bleeding; sc_end SC_Curse; sc_end SC_Silence; itemheal rand(1000,1200),0; },{},{} +13272,Cure_Free_To_Throw,Throwing Cure Free,10,100,,50,0,,,,0x00040000,8,2,32768,,99,,9,{ sc_end SC_BLOODING; sc_end SC_Curse; sc_end SC_Silence; itemheal rand(1000,1200),0; },{},{} 13273,Stamina_Up_M_To_Throw,Throwing Muramura M,10,100,,10,0,,,,0x00040000,8,2,32768,,99,,9,{ sc_start SC_MUSTLE_M,500000,5; },{},{} 13274,Digestive_F_To_Throw,Throwing Falmons F,10,100,,10,0,,,,0x00040000,8,2,32768,,99,,9,{ sc_start SC_LIFE_FORCE_F,500000,5; },{},{} 13275,HP_Inc_PotS_To_Throw,Throwing Increase HP Potion (Small),10,100,,20,0,,,,0x00040000,8,2,32768,,99,,9,{ sc_start SC_INCMHPRATE,500000,1; percentheal 1,0; },{},{}//HP and SP pots need a recheck later to correct max increases. @@ -6319,11 +6319,11 @@ 14461,Asara_Fairy_Hat_Box,Ashura Fairy Hat Box,18,20,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ getitem 5505,1; },{},{} 14466,Valentine_Pledge_Box,Valentine's Emblem Box,2,0,,0,,,,,0xFFFFFFFF,7,2,,,,,,{},{},{} 14469,Ox_Tail_Scroll,Ox Tail Egg,2,20,,10,,,,,0xFFFFFFFF,7,2,,,,,,{},{},{} -14500,Insurance60,Life Insurrance Certificate,2,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_LIFEINSURANCE,3600000,0; },{},{} +14500,Insurance60,Life Insurrance Certificate,2,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_CASH_DEATHPENALTY,3600000,0; },{},{} 14508,Zeny_Scroll,Zeny Pet Egg Scroll,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{},{},{} -14509,Light_Center_Pot,Light Concentration Potion,2,800,,20,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_ASPDPOTION0,1800000,0; },{},{} -14510,Light_Awakening_Pot,Light Awakening Potion,2,1500,,20,,,,,0xFFF7FEEF,7,2,,,40,,,{ sc_start SC_ASPDPOTION1,1800000,0; },{},{} -14511,Light_Berserk_Pot,Light Berserk Potion,2,3000,,20,,,,,0x01E646A6,7,2,,,85,,,{ sc_start SC_ASPDPOTION2,1800000,0; },{},{} +14509,Light_Center_Pot,Light Concentration Potion,2,800,,20,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_ATTHASTE_POTION1,1800000,0; },{},{} +14510,Light_Awakening_Pot,Light Awakening Potion,2,1500,,20,,,,,0xFFF7FEEF,7,2,,,40,,,{ sc_start SC_ATTHASTE_POTION2,1800000,0; },{},{} +14511,Light_Berserk_Pot,Light Berserk Potion,2,3000,,20,,,,,0x01E646A6,7,2,,,85,,,{ sc_start SC_ATTHASTE_POTION3,1800000,0; },{},{} 14512,Meteor_10_Scroll,Meteor Storm Scroll,11,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ itemskill "WZ_METEOR",10; },{},{} 14513,Storm_10_Scroll,Storm Gust Scroll,11,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ itemskill "WZ_STORMGUST",10; },{},{} 14514,Vermilion_10_Scroll,Lord of Vermilion Scroll,11,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ itemskill "WZ_VERMILION",10; },{},{} @@ -6337,18 +6337,18 @@ 14522,Big_Bun,Big Bun,0,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ percentheal 100,0; },{},{} 14523,Pill_,Pill,0,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ percentheal 0,100; },{},{} 14524,Superb_Fish_Slice,Superb Fish Slice,0,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ percentheal 100,100; },{},{} -14525,Chewy_Ricecake,Chewy Ricecake,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_ATKPOTION,180000,10; },{},{} -14526,Oriental_Pastry,Oriental Pastry,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_MATKPOTION,180000,10; },{},{} +14525,Chewy_Ricecake,Chewy Ricecake,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_PLUSATTACKPOWER,180000,10; },{},{} +14526,Oriental_Pastry,Oriental Pastry,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_PLUSMAGICPOWER,180000,10; },{},{} 14527,Dun_Tele_Scroll1,Dungeon Teleport Scroll,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ callfunc "F_CashDungeon"; },{},{} 14528,PVP_Tele_Scroll,PVP Teleport Scroll,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{},{},{} 14529,Greed_Scroll,Greed Scroll,11,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ itemskill "BS_GREED",1; },{},{} 14530,Flee_30_Scroll,Evasion Scroll,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_INCFLEE,1800000,30; },{},{} 14531,Accuracy_30_Scroll,Concentration Scroll,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_INCHIT,1800000,30; },{},{} -14532,Battle_Manual25,Field Manual 25%,2,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_EXPBOOST,1800000,25; },{},{} -14533,Battle_Manual100,Field Manual 100%,2,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_EXPBOOST,1800000,100; },{},{} +14532,Battle_Manual25,Field Manual 25%,2,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_CASH_PLUSEXP,1800000,25; },{},{} +14533,Battle_Manual100,Field Manual 100%,2,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_CASH_PLUSEXP,1800000,100; },{},{} 14534,Small_Life_Potion,Small Life Potion,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ specialeffect2 320; sc_start4 SC_S_LIFEPOTION,600000,-5,5,0,0; },{},{} 14535,Med_Life_Potion,Medium Life Potion,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ specialeffect2 320; sc_start4 SC_L_LIFEPOTION,600000,-7,4,0,0; },{},{} -14536,Abrasive,Abrasive,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ specialeffect2 182; sc_start SC_INCCRI,300000,30; },{},{} +14536,Abrasive,Abrasive,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ specialeffect2 182; sc_start SC_CRITICALPERCENT,300000,30; },{},{} 14537,Regeneration_Potion,Regeneration Potion,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ specialeffect2 348; sc_start SC_INCHEALRATE,1800000,20; },{},{} 14538,Glass_Of_Illusion,Glass of Illusion,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ specialeffect2 EF_STEAL; sc_start SC_INCFLEE2,60000,20; },{},{} 14539,Shadow_Armor_S,Shadow Armor Scroll,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ specialeffect2 EF_CLOAKING; sc_start4 SC_ELEMENTALCHANGE,1800000,1,Ele_Dark,1,0; },{},{} @@ -6357,42 +6357,42 @@ 14542,B_Def_Potion,Big Defense Potion,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ specialeffect2 EF_GUARD; sc_start SC_DEF_RATE,180000,3; },{},{} 14543,S_Mdef_Potion,Small Magic Defense Potion,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ specialeffect2 EF_SPELLBREAKER; sc_start SC_MDEF_RATE,60000,3; },{},{} 14544,B_Mdef_Potion,Big Magic Defense Potion,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ specialeffect2 EF_SPELLBREAKER; sc_start SC_MDEF_RATE,180000,3; },{},{} -14545,Battle_Manual_X3,Field Manual 300%,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_EXPBOOST,1800000,300; },{},{} +14545,Battle_Manual_X3,Field Manual 300%,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_CASH_PLUSEXP,1800000,300; },{},{} 14546,Fire_Cracker_Love,I Love You Firecracker,2,2,,20,,,,,0xFFFFFFFF,7,2,,,,,,{ end; },{},{} 14547,Fire_Cracker_Wday,Whiteday Firecracker,2,2,,20,,,,,0xFFFFFFFF,7,2,,,,,,{ end; },{},{} 14548,Fire_Cracker_Valentine,Valentine's Day Firecracker,2,2,,20,,,,,0xFFFFFFFF,7,2,,,,,,{ end; },{},{} 14549,Fire_Cracker_Bday,Birthday Firecracker,2,2,,20,,,,,0xFFFFFFFF,7,2,,,,,,{ end; },{},{} 14550,Fire_Cracker_Xmas,Xmas Firecracker,2,2,,20,,,,,0xFFFFFFFF,7,2,,,,,,{ end; },{},{} -14551,Str_Dish01_,Fried Grasshopper Legs,0,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_STRFOOD,1200000,1; percentheal 5,0; },{},{} -14552,Str_Dish02_,Seasoned Sticky Webfoot,0,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_STRFOOD,1200000,2; percentheal 5,0; },{},{} -14553,Str_Dish03_,Bomber Steak,0,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_STRFOOD,1200000,3; percentheal 5,0; },{},{} -14554,Int_Dish01_,Grape Juice Herbal Tea,0,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_INTFOOD,1200000,1; percentheal 0,5; },{},{} -14555,Int_Dish02_,Autumn Red Tea,0,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_INTFOOD,1200000,2; percentheal 0,5; },{},{} -14556,Int_Dish03_,Honey Herbal Tea,0,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_INTFOOD,1200000,3; percentheal 0,5; },{},{} -14557,Vit_Dish01_,Steamed Crab Nippers,0,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_VITFOOD,1200000,1; percentheal 5,0; },{},{} -14558,Vit_Dish02_,Assorted Seafood,0,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_VITFOOD,1200000,2; percentheal 5,0; },{},{} -14559,Vit_Dish03_,Clam Soup,0,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_VITFOOD,1200000,3; percentheal 5,0; },{},{} -14560,Agi_Dish01_,Frog Egg Squid Ink Soup,0,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_AGIFOOD,1200000,1; percentheal 3,1; },{},{} -14561,Agi_Dish02_,Smooth Noodle,0,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_AGIFOOD,1200000,2; percentheal 3,1; },{},{} -14562,Agi_Dish03_,Tentacle Cheese Gratin,0,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_AGIFOOD,1200000,3; percentheal 3,1; },{},{} -14563,Dex_Dish01_,Honey Grape Juice,0,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_DEXFOOD,1200000,1; percentheal 2,2; },{},{} -14564,Dex_Dish02_,Chocolate Mousse Cake,0,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_DEXFOOD,1200000,2; percentheal 2,2; },{},{} -14565,Dex_Dish03_,Fruit Mix,0,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_DEXFOOD,1200000,3; percentheal 2,2; },{},{} -14566,Luk_Dish01_,Fried Monkey Tails,0,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_LUKFOOD,1200000,1; percentheal 3,2; },{},{} -14567,Luk_Dish02_,Mixed Juice,0,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_LUKFOOD,1200000,2; percentheal 3,2; },{},{} -14568,Luk_Dish03_,Fried Sweet Potato,0,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_LUKFOOD,1200000,3; percentheal 4,2; },{},{} +14551,Str_Dish01_,Fried Grasshopper Legs,0,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_STR,1200000,1; percentheal 5,0; },{},{} +14552,Str_Dish02_,Seasoned Sticky Webfoot,0,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_STR,1200000,2; percentheal 5,0; },{},{} +14553,Str_Dish03_,Bomber Steak,0,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_STR,1200000,3; percentheal 5,0; },{},{} +14554,Int_Dish01_,Grape Juice Herbal Tea,0,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_INT,1200000,1; percentheal 0,5; },{},{} +14555,Int_Dish02_,Autumn Red Tea,0,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_INT,1200000,2; percentheal 0,5; },{},{} +14556,Int_Dish03_,Honey Herbal Tea,0,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_INT,1200000,3; percentheal 0,5; },{},{} +14557,Vit_Dish01_,Steamed Crab Nippers,0,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_VIT,1200000,1; percentheal 5,0; },{},{} +14558,Vit_Dish02_,Assorted Seafood,0,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_VIT,1200000,2; percentheal 5,0; },{},{} +14559,Vit_Dish03_,Clam Soup,0,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_VIT,1200000,3; percentheal 5,0; },{},{} +14560,Agi_Dish01_,Frog Egg Squid Ink Soup,0,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_AGI,1200000,1; percentheal 3,1; },{},{} +14561,Agi_Dish02_,Smooth Noodle,0,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_AGI,1200000,2; percentheal 3,1; },{},{} +14562,Agi_Dish03_,Tentacle Cheese Gratin,0,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_AGI,1200000,3; percentheal 3,1; },{},{} +14563,Dex_Dish01_,Honey Grape Juice,0,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_DEX,1200000,1; percentheal 2,2; },{},{} +14564,Dex_Dish02_,Chocolate Mousse Cake,0,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_DEX,1200000,2; percentheal 2,2; },{},{} +14565,Dex_Dish03_,Fruit Mix,0,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_DEX,1200000,3; percentheal 2,2; },{},{} +14566,Luk_Dish01_,Fried Monkey Tails,0,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_LUK,1200000,1; percentheal 3,2; },{},{} +14567,Luk_Dish02_,Mixed Juice,0,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_LUK,1200000,2; percentheal 3,2; },{},{} +14568,Luk_Dish03_,Fried Sweet Potato,0,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_LUK,1200000,3; percentheal 4,2; },{},{} 14569,Knife_Goblin_Ring,Knife Goblin Ring,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ pet 1122; },{},{} 14570,Flail_Goblin_Ring,Flail Goblin Ring,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ pet 1123; },{},{} 14571,Hammer_Goblin_Ring,Hammer Goblin Ring,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ pet 1125; },{},{} 14572,Holy_Marble,Holy Marble,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ pet 1385; },{},{} 14573,Red_Burning_Stone,Red Burning Stone,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ pet 1382; },{},{} 14574,Skull_Of_Vagabond,Vagabond's Skull,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ pet 1208; },{},{} -14575,Str_Dish05_,Lutie Lady's Pancake,0,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_STRFOOD,1200000,5; percentheal 10,0; },{},{} -14576,Int_Dish05_,Mastela Fruit Wine,0,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_INTFOOD,1200000,5; percentheal 0,10; },{},{} -14577,Vit_Dish05_,Spicy Fried Bao,0,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_VITFOOD,1200000,5; percentheal 10,0; },{},{} -14578,Agi_Dish05_,Steamed Bat Wing in Pumpkin,0,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_AGIFOOD,1200000,5; percentheal 6,2; },{},{} -14579,Dex_Dish05_,Green Salad,0,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_DEXFOOD,1200000,5; percentheal 5,5; },{},{} -14580,Luk_Dish05_,Fried Scorpion Tails,0,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_LUKFOOD,1200000,5; percentheal 5,2; },{},{} +14575,Str_Dish05_,Lutie Lady's Pancake,0,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_STR,1200000,5; percentheal 10,0; },{},{} +14576,Int_Dish05_,Mastela Fruit Wine,0,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_INT,1200000,5; percentheal 0,10; },{},{} +14577,Vit_Dish05_,Spicy Fried Bao,0,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_VIT,1200000,5; percentheal 10,0; },{},{} +14578,Agi_Dish05_,Steamed Bat Wing in Pumpkin,0,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_AGI,1200000,5; percentheal 6,2; },{},{} +14579,Dex_Dish05_,Green Salad,0,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_DEX,1200000,5; percentheal 5,5; },{},{} +14580,Luk_Dish05_,Fried Scorpion Tails,0,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_LUK,1200000,5; percentheal 5,2; },{},{} 14581,Dun_Tele_Scroll2,Dungeon Teleport Scroll II,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ callfunc "F_CashDungeon"; },{},{} 14582,WOB_Rune,Yellow Butterfly Wing,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ callfunc "F_CashCity",1; },{},{} 14583,WOB_Schwaltz,Green Butterfly Wing,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ callfunc "F_CashCity",2; },{},{} @@ -6404,7 +6404,7 @@ 14589,Pty_Inc_Agi_Scroll,Party Increase Agi 10 Scroll,11,10,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ itemskill "CASH_INCAGI",10; },{},{} 14590,Pty_Assumptio_Scroll,Party Assumptio 5 Scroll,11,10,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ itemskill "CASH_ASSUMPTIO",5; },{},{} 14591,Siege_Teleport_Scroll,WoE Teleport Scroll,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ callfunc "F_CashSeigeTele"; },{},{} -14592,Job_Manual50,JOB Battle Manual,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_JEXPBOOST,1800000,50; },{},{} +14592,Job_Manual50,JOB Battle Manual,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_CASH_PLUSONLYJOBEXP,1800000,50; },{},{} 14593,Magic_Power_Scroll,Mystical Amplification Scroll,11,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ itemskill "HW_MAGICPOWER",10; },{},{} 14594,Quagmire_Scroll,Quagmire Scroll,11,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ itemskill "WZ_QUAGMIRE",5; },{},{} 14595,Unsealed_Magic_Spell,Unsealed Magic Spell,2,0,,0,,,,,0xFFFFFFFF,7,2,,,,,,{ warp "yuno_fild09",255,127; },{},{} @@ -6413,7 +6413,7 @@ 14598,GhostringS,Ghostring Scroll,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_ITEMSCRIPT,60000,4047; },{},{} 14599,Greed_Scroll_C,Greed Scroll,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{},{},{} 14600,Mental_Potion,Mental Potion,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{},{},{} -14601,Tyr's_Blessing,Tyr's Blessing,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_INCFLEE,300000,30; sc_start SC_INCHIT,300000,30; sc_start SC_ATKPOTION,300000,20; sc_start SC_MATKPOTION,300000,20; },{},{} +14601,Tyr's_Blessing,Tyr's Blessing,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_INCFLEE,300000,30; sc_start SC_INCHIT,300000,30; sc_start SC_PLUSATTACKPOWER,300000,20; sc_start SC_PLUSMAGICPOWER,300000,20; },{},{} 14602,TaogunkaS,Tao Gunka Scroll,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_ITEMSCRIPT,180000,4302; },{},{} 14603,MistressS,Mistress Scroll,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_ITEMSCRIPT,180000,4132; },{},{} 14604,Orc_HeroS,Orc Hero Scroll,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_ITEMSCRIPT,60000,4143; },{},{} diff --git a/db/pre-re/skill_cast_db.txt b/db/pre-re/skill_cast_db.txt index fcd2e8ceb..9a2c4bafb 100644 --- a/db/pre-re/skill_cast_db.txt +++ b/db/pre-re/skill_cast_db.txt @@ -1086,16 +1086,16 @@ 2006,1000,0,0,0,0,2000 //-- RK_DRAGONBREATH -2008,0:0:0:1000:1000:1000:1500:1500:2000:2000,2000,0,10000,0,0 +2008,0:0:0:1000:1000:1000:1500:1500:2000:2000,2000,0,42000,0,0 //-- RK_DRAGONHOWLING 2009,0,0,0,15000,0,10000 //-- RK_MILLENNIUMSHIELD -2011,0,1000,0,180000,0,60000 +2011,0,1000,0,180000,60000,0 //-- RK_CRUSHSTRIKE -2012,0,0,0,30000,0,30000 +2012,0,0,0,180000,30000,0 //-- RK_REFRESH -2013,0,0,0,60000,0,120000 +2013,0,0,0,60000,120000,0 //-- RK_GIANTGROWTH 2014,0,0,0,180000,0,0 //-- RK_STONEHARDSKIN @@ -1108,6 +1108,8 @@ 2018,0,0,0,180000,0,0 //-- RK_ABUNDANCE 2019,0,0,0,180000,0,0 +//-- RK_DRAGONBREATH_WATER +5004,0:0:0:1000:1000:1000:1500:1500:2000:2000,2000,0,40000,0,0 //========================================== //===== Gillotine Cross ==================== @@ -1144,6 +1146,8 @@ 2036,0,200,0,3000,0,0 //-- GC_CROSSRIPPERSLASHER 2037,0,1000,0,0,0,0 +//-- GC_DARKCROW +5001,0,1500,0,5000,0,0 //========================================== //===== Arch Bishop ======================== @@ -1183,6 +1187,8 @@ //-- AB_SILENTIUM 2057,4000,0,0,20000:30000:40000:50000:60000,0,15000 +//-- AB_OFFERTORIUM +5011,4000,0,0,90000,0,0,-1 //========================================== //===== Warlock ============================ @@ -1208,17 +1214,15 @@ //-- WL_CRIMSONROCK 2211,5000,2000,0,3000:4000:5000:6000:7000,0,5000 //-- WL_HELLINFERNO -2212,3000,1000,0,15000,0,0 +2212,3000,1000,0,42000,0,0 //-- WL_COMET -2213,10000:11000:12000:13000:14000,0,0,15000,0,60000 +2213,10000:11000:12000:13000:14000,0,0,100,42000,60000 //-- WL_CHAINLIGHTNING 2214,3500:4000:4500:5000:5500,0,0,100,0,3000 - //-- WL_EARTHSTRAIN -2216,2000:3000:4000:5000:6000,1000,0,150,75000:90000:105000:120000:135000,10000 -//-- WL_TETRAVORTEX -2217,5000:6000:7000:8000:9000,2000,0,20000,0,15000 - +2216,2000:3000:4000:5000:6000,1000,0,100,75000:90000:105000:120000:135000,10000 +//-- WL_TETRAVORTEX +2217,5000:6000:7000:8000:9000,2000,0,15000:120000:40000:5000,0,15000 //-- WL_SUMMONFB 2222,2000,0,0,120000:160000:200000:240000:280000,0,0 //-- WL_SUMMONBL @@ -1230,6 +1234,8 @@ //-- WL_READING_SB 2231,5000,500,0,0,0,0 +//-- WL_TELEKINESIS_INTENSE +5012,1000,0,0,180000,0,0 //========================================== //===== Ranger ============================= @@ -1271,6 +1277,8 @@ 2253,0,0,0,20000,15000,0 //-- RA_ICEBOUNDTRAP 2254,0,0,0,20000,15000,0 +//-- RA_UNLIMIT +5002,0,0,0,60000,0,0 //========================================== //===== Mechanic =========================== @@ -1326,6 +1334,8 @@ 2282,0,0,0,20000:30000:40000:50000:60000,0,0 //-- NC_DISJOINT 2283,2000,0,0,0,0,0 +//-- NC_MAGMA_ERUPTION +5006,1000,0,0,10000,42000,0 //========================================== //===== Shadow Chaser ====================== @@ -1411,6 +1421,8 @@ 2324,1000,3000,0,0,0,20000 //-- LG_INSPIRATION 2325,2000,2000,0,30000:45000:60000:75000:90000,0,540000:480000:420000:360000:300000 +//-- LG_KINGS_GRACE +5013,1000,0,0,5000,0,0 //========================================== //===== Sura Skills ======================== @@ -1457,6 +1469,8 @@ 2347,1000,1000,0,240000,0,200000:180000:160000:140000:120000 //-- SR_GENTLETOUCH_REVITALIZE 2348,1000,1000,0,240000,0,200000:180000:160000:140000:120000 +//-- SR_FLASHCOMBO +2348,0,4000,0,0,0,0 //========================================== //==== Wanderer skills ===================== @@ -1519,6 +1533,8 @@ 2433,1000,1000,0,20000:30000:40000:50000:60000,0,180000 //-- WM_UNLIMITED_HUMMING_VOICE 2434,1000,1000,0,60000:90000:120000:150000:180000,0,110000:120000:130000:140000:150000 +//-- WM_FRIGG_SONG +5007,0,0,0,60000,0,0 //========================================== //==== Sorcerer skills ===================== @@ -1639,60 +1655,62 @@ //========================================== //==== Kagerou & Oboro skills ============== -//-- KO_YAMIKUMO +//-- KO_YAMIKUMO 3001,0,0,0,60000,0,0 -//-- KO_JYUMONJIKIRI -3004,0,2500,0,5000,0,0 -//-- KO_SETSUDAN -3005,0,2000,0,0,0,0 -//-- KO_BAKURETSU -3006,1000:1500:2000:2500:3000,1000,0,100,0,3000 -//-- KO_HAPPOKUNAI -3007,0,1000,0,0,0,0 -//-- KO_MUCHANAGE -3008,0,0,0,100,0,10000 -//-- KO_HUUMARANKA -3009,0,3000,0,500,0,0 -//-- KO_MAKIBISHI -3010,0,0,0,12000:14000:16000:18000:20000,10000,0 -//-- KO_MEIKYOUSISUI -3011,3000,0,0,10000,0,0 -//-- KO_ZANZOU -3012,0,0,0,27000:24000:21000:18000:15000,0,0 -//-- KO_KYOUGAKU -3013,1000,0,0,12000:14000:16000:18000:20000,0,0 -//-- KO_JYUSATSU -3014,1000,0,0,8000:10000:12000:14000:16000,0,0 -//-- KO_KAHU_ENTEN -3015,500,0,0,300000,0,0 -//-- KO_HYOUHU_HUBUKI -3016,500,0,0,300000,0,0 -//-- KO_KAZEHU_SEIRAN -3017,500,0,0,300000,0,0 -//-- KO_DOHU_KOUKAI -3018,500,0,0,300000,0,0 -//-- KO_KAIHOU -3019,1000,0,0,0,0,0 -//-- KO_ZENKAI -3020,1000,0,0,10000,10000,0 -//-- KO_GENWAKU -3021,500,0,0,5000,0,0 -//-- KO_IZAYOI +//-- KO_JYUMONJIKIRI +3004,0,500,0,3000,0,5000 +//-- KO_SETSUDAN +3005,0,0,0,0,0,3000 +//-- KO_BAKURETSU +3006,1000:1400:1800:2200:2600,1000,0,100,0,3000 +//-- KO_HAPPOKUNAI +3007,0,500,0,0,0,0 +//-- KO_MUCHANAGE +3008,1000,0,0,100,0,10000 +//-- KO_HUUMARANKA +3009,1000:1200:1400:1600:1800,1000,0,500,0,3000 +//-- KO_MAKIBISHI +3010,0,0,0,12000:14000:16000:18000:20000,10000,10000 +//-- KO_MEIKYOUSISUI +3011,3000,0,0,10000,0 +//-- KO_ZANZOU +3012,0,1000,0,30000:27000:24000:21000:18000,0,0 +//-- KO_KYOUGAKU +3013,3000:2500:2000:1500:1000,1000,0,12000:14000:16000:18000:20000,0,0 +//-- KO_JYUSATSU +3014,3000:2500:2000:1500:1000,1000,0,8000:10000:12000:14000:16000,0,10000 +//-- KO_KAHU_ENTEN +3015,2000,0,0,300000,0,0 +//-- KO_HYOUHU_HUBUKI +3016,2000,0,0,300000,0,0 +//-- KO_KAZEHU_SEIRAN +3017,2000,0,0,300000,0,0 +//-- KO_DOHU_KOUKAI +3018,2000,0,0,300000,0,0 +//-- KO_ZENKAI +3020,0,1000,0,10000,10000,0 +//-- KO_GENWAKU +3021,3000:2500:2000:1500:1000,1000,0,5000,0,10000 +//-- KO_IZAYOI 3022,0,0,0,30000:45000:60000:75000:90000,0,60000 -//-- KG_KAGEHUMI -3023,0,0,0,5000,0,5000 -//-- KG_KYOMU -3024,0,0,0,10000:15000:20000:25000:30000,0,0 -//-- KG_KAGEMUSYA -3025,0,0,0,60000:90000:120000:15000:180000,0,0 -//-- OB_ZANGETSU -3026,0,0,0,60000:75000:90000:105000:120000,0,0 -//-- OB_OBOROGENSOU -3027,0,0,0,10000:15000:20000:25000:30000,0,0 -//-- OB_AKAITSUKI -3029,0,0,0,10000:15000:20000:25000:30000,0,0 +//-- KG_KAGEHUMI +3023,0,0,0,5000:6000:7000:8000:9000,0,0 +//-- KG_KYOMU +3024,0,1000,0,10000:15000:20000:25000:30000,0,20000 +//-- KG_KAGEMUSYA +3025,0,0,0,60000:90000:120000:150000:180000,0,0 + +//-- OB_ZANGETSU +3026,1000:1500:2000:2500:3000,1000,0,60000:75000:90000:105000:120000,0,30000 +//-- OB_OBOROGENSOU +3027,1000,0,0,10000:15000:20000:25000:30000,0,15000 +//-- OB_AKAITSUKI +3029,1000:1500:2000:2500:3000,1000,0,10000:15000:20000:25000:30000,0,30000 //========================================== +//-- ALL_FULL_THROTTLE +5014,0,0,0,10000:15000:20000:25000:30000,10000,20000:25000:30000:35000:40000 + //===== Homunculus Skills ================== //-- HLIF_HEAL 8001,0,2000,0,0,0,0 diff --git a/db/pre-re/skill_db.txt b/db/pre-re/skill_db.txt index 3635bca65..26030c867 100644 --- a/db/pre-re/skill_db.txt +++ b/db/pre-re/skill_db.txt @@ -660,7 +660,7 @@ 1003,0,0,0,0,0,0,1,0,no,0,0x1,0,weapon,0, AS_SONICACCEL,Sonic Acceleration 1004,9,8,1,0,0x8,0,1,1,no,0,0x1,0,weapon,0, AS_VENOMKNIFE,Throw Venom Knife 1005,1,6,1,0,0x1,0,1,1,no,0,0x1,0,weapon,0, RG_CLOSECONFINE,Close Confine -1006,0,6,4,3,0,2,1,1,yes,0,0x1,0,magic,3, WZ_SIGHTBLASTER,Sight Blaster +1006,0,6,4,3,0,1,1,1,yes,0,0x1,0,magic,3, WZ_SIGHTBLASTER,Sight Blaster 1007,0,6,4,0,0x1,0,1,0,no,0,0x1,0,none,0, SA_CREATECON,Create Elemental Converter 1008,9,6,1,1,0x1,0,1,1,yes,0,0x1,0,magic,0, SA_ELEMENTWATER,Elemental Change Water 1009,-9,6,1,0,0,0,1,1,no,0,0x1,0,weapon,3, HT_PHANTASMIC,Phantasmic Arrow @@ -680,15 +680,15 @@ //**** 2001,0,6,4,0,0x1,0,5,1,yes,0,0,0,none,0, RK_ENCHANTBLADE,Enchant Blade 2002,7:8:9:10:11,6,1,-1,0,0,5,1,no,0,0,0,weapon,0, RK_SONICWAVE,Sonic Wave -2003,0,6,4,0,0x1,0,10,1,no,0,0,0,weapon,0, RK_DEATHBOUND,Death Bound -2004,5,8,1,-1,0,0,10,-5,no,0,0,0,weapon,0, RK_HUNDREDSPEAR,Hundred Spear +2003,0,6,4,0,0x1,0,10,1,no,0,0,0,weapon,3, RK_DEATHBOUND,Death Bound +2004,1,8,1,-1,0,0,10,-5,no,0,0,0,weapon,0, RK_HUNDREDSPEAR,Hundred Spear 2005,1,6,2,4,0x2,2,5,1,no,0,0,0,weapon,3, RK_WINDCUTTER,Wind Cutter 2006,0,6,4,-1,0x2,5,5,1,no,0,0,0,weapon,0, RK_IGNITIONBREAK,Ignition Break 2007,0,0,0,0,0,0,5,0,no,0,0,0,weapon,0, RK_DRAGONTRAINING,Dragon Training 2008,9,6,2,3,0xC2,1:1:1:2:2:2:3:3:4:4,10,1,no,0,0,0,misc,0, RK_DRAGONBREATH,Dragon Breath -2009,0,6,4,0,0x3,3:4:5:6:7,5,1,no,0,0,0,none,0, RK_DRAGONHOWLING,Dragon Howling +2009,0,6,4,0,0x3,3:4:5:6:7,5,1,yes,0,0,0,none,0, RK_DRAGONHOWLING,Dragon Howling 2010,0,0,0,0,0,0,10,0,no,0,0,0,none,0, RK_RUNEMASTERY,Rune Mastery -2011,0,6,4,0,0x1,0,1,1,no,0,0,0,none,0, RK_MILLENNIUMSHIELD,Millenium Shield +2011,0,6,4,0,0x1,0,1,1,yes,0,0,0,none,0, RK_MILLENNIUMSHIELD,Millenium Shield 2012,1,6,4,-1,0,0x8,1,1,yes,0,0,0,weapon,0, RK_CRUSHSTRIKE,Crush Strike 2013,0,6,4,0,0x1,0,1,1,yes,0,0,0,none,0, RK_REFRESH,Refresh 2014,0,6,4,0,0x1,0,1,1,yes,0,0,0,none,0, RK_GIANTGROWTH,Giant Growth @@ -697,43 +697,7 @@ 2017,0,6,4,-1,0x2,3,1,1,no,0,0,0,weapon,7, RK_STORMBLAST,Storm Blast 2018,0,6,4,0,0x3,-1,1,1,yes,0,0,0,none,0, RK_FIGHTINGSPIRIT,Fighting Spirit //CHECK Is this splash needed? 2019,9,6,4,6,0x1,0,1,1,yes,0,0,0,none,0, RK_ABUNDANCE,Abundance -2020,5:6:7:8:9,6,16,-1,0,0,5,1,no,0,0,0,weapon,0, RK_PHANTOMTHRUST,Phantom Thrust - -//**** -// WL Warlock -//**** -2201,11,6,16,0,0,0,5,1,yes,0,0,0,magic,0, WL_WHITEIMPRISON,White Imprison -2202,11,8,1,8,0x2,1:1:1:2:2,5,-2,yes,0,0,0,magic,0, WL_SOULEXPANSION,Soul Expansion -2203,0,8,4,1,0x2,13,5,-3:-4:-5:-6:-7,yes,0,0,0,magic,0, WL_FROSTMISTY,Frosty Misty -2204,0,8,4,1,0x2,13,5,-5,yes,0,0,0,magic,0, WL_JACKFROST,Jack Frost -2205,11,6,1,0,0x1,0,5,1,yes,0,0,0,magic,0, WL_MARSHOFABYSS,Marsh of Abyss -2206,0,6,4,0,0x1,0,5,1,yes,0,0,0,magic,0, WL_RECOGNIZEDSPELL,Recognized Spell -2207,7,6,1,2,0x3,1:2:2:3:3,5,1,yes,0,0,0,magic,0, WL_SIENNAEXECRATE,Sienna Execrate -2208,0,0,0,0,0,0,3,0,no,0,0,0,none,0, WL_RADIUS,Radius -2209,0,6,4,0,0x3,9:10:11:12:13,5,1,yes,0,0,0,magic,0, WL_STASIS,Stasis -2210,11,6,1,0,0,0,5,1,yes,0,0,0,magic,0, WL_DRAINLIFE,Drain Life -2211,11,8,1,3,0x2,3,5,-7,yes,0,0,0,magic,3, WL_CRIMSONROCK,Crimson Rock -2212,11,6,1,3,0,0,5,1,yes,0,0,0,magic,0, WL_HELLINFERNO,Hell Inferno -2213,11,8,2,0,0x2,7,5,-20,yes,0,0,0,magic,2, WL_COMET,Comet -2214,11,6,1,0,0,3,5,1,yes,0,0,0,magic,0, WL_CHAINLIGHTNING,Chain Lightning //CHECK Is the splash being used for the target search? -2215,11,6,1,4,0,0,5,1,no,0,0,0,magic,0, WL_CHAINLIGHTNING_ATK,Chain Lightning Attack -2216,3,8,2,2,0,0,5,-6:-7:-8:-9:-10,yes,0,0,0,magic,0, WL_EARTHSTRAIN,Earth Strain -2217,11,6,1,0,0,0,5,1,yes,0,0,0,magic,0, WL_TETRAVORTEX,Tetra Vortex -2218,11,6,1,3,0,0,5,1,no,0,0,0,magic,0, WL_TETRAVORTEX_FIRE,Tetra Vortex Fire -2219,11,6,1,1,0,0,5,1,no,0,0,0,magic,0, WL_TETRAVORTEX_WATER,Tetra Vortex Water -2220,11,6,1,4,0,0,5,1,no,0,0,0,magic,0, WL_TETRAVORTEX_WIND,Tetra Vortex Wind -2221,11,6,1,2,0,0,5,1,no,0,0,0,magic,0, WL_TETRAVORTEX_GROUND,Tetra Vortex Earth -2222,0,6,4,3,0x1,0,5,1,yes,0,0,0,magic,0, WL_SUMMONFB,Summon Fire Ball -2223,0,6,4,4,0x1,0,5,1,yes,0,0,0,magic,0, WL_SUMMONBL,Summon Lightning Ball -2224,0,6,4,1,0x1,0,5,1,yes,0,0,0,magic,0, WL_SUMMONWB,Summon Water Ball -2225,11,6,1,3,0,0,5,1,no,0,0,1,magic,0, WL_SUMMON_ATK_FIRE,Summon Attack Fire //CHECK Summon attack ID's dont appear to have a range. -2226,11,6,1,4,0,0,5,1,no,0,0,1,magic,0, WL_SUMMON_ATK_WIND,Summon Attack Wind -2227,11,6,1,1,0,0,5,1,no,0,0,1,magic,0, WL_SUMMON_ATK_WATER,Summon Attack Water -2228,11,6,1,2,0,0,5,1,no,0,0,1,magic,0, WL_SUMMON_ATK_GROUND,Summon Attack Earth -2229,0,6,4,2,0x1,0,5,1,yes,0,0,0,magic,0, WL_SUMMONSTONE,Summon Stone -2230,11,8,1,0,0,0,2,1,yes,0,0,0,magic,0, WL_RELEASE,Release //CHECK Should it be left to do multi hit or single hit? -2231,0,6,4,0,0x1,0,1,1,yes,0,0,0,magic,0, WL_READING_SB,Reading Spellbook -2232,0,0,0,0,0,0,5,0,no,0,0,0,none,0, WL_FREEZE_SP,Freeze Spell +2020,5:6:7:8:9,6,1,-1,0,0,5,1,yes,0,0,0,weapon,0, RK_PHANTOMTHRUST,Phantom Thrust //**** // GC Guillotine Cross @@ -750,7 +714,7 @@ 2030,-2,6,4,-1,0x1,0,5,1,no,0,0x200,0,weapon,0, GC_WEAPONCRUSH,Weapon Crush //CHECK SHould this and the above skill have INF2 0x200? 2031,1,6,1,-1,0,0,5,1,no,0,0,0,weapon,0, GC_VENOMPRESSURE,Venom Pressure 2032,5,6,2,0,0x1,0,5,1,yes,0,0,1,none,0, GC_POISONSMOKE,Poison Smoke -2033,0,6,4,0,0x1,0,5,1,no,0,0,0,none,0, GC_CLOAKINGEXCEED,Cloaking Exceed +2033,0,6,4,0,0x1,0,5,1,no,0,0,0,weapon,0, GC_CLOAKINGEXCEED,Cloaking Exceed 2034,0,6,4,-1,0x2,3,1,1,no,0,0,0,weapon,0, GC_PHANTOMMENACE,Phantom Menace 2035,0,6,4,0,0x1,0,5,1,no,0,0,0,none,0, GC_HALLUCINATIONWALK,Hallucination Walk 2036,0,6,4,-1,0x2,1:1:1:1:2,5,1,no,0,0,0,weapon,0, GC_ROLLINGCUTTER,Rolling Cutter @@ -780,7 +744,41 @@ 2056,-1,6,1,0,0,0,10,1,no,0,0,0,magic,0, AB_DUPLELIGHT_MAGIC,Duple Light Magic 2057,0,6,4,6,0x3,4:5:6:7:8,5,1,yes,0,0,0,magic,0, AB_SILENTIUM,Silentium //CHECk Marked magic attack as well. Hmmmm.... -2515,11,6,16,0,0x1,0,5,1,yes,0,0,0,magic,0, AB_SECRAMENT,Secrament +//**** +// WL Warlock +//**** +2201,11,6,16,0,0,0,5,1,yes,0,0,0,magic,0, WL_WHITEIMPRISON,White Imprison +2202,11,8,1,8,0x2,1:1:1:2:2,5,-2,yes,0,0,0,magic,0, WL_SOULEXPANSION,Soul Expansion +2203,0,8,4,1,0x2,13,5,-3:-4:-5:-6:-7,yes,0,0,0,magic,0, WL_FROSTMISTY,Frosty Misty +2204,0,8,4,1,0x2,13,5,-5,yes,0,0,0,magic,0, WL_JACKFROST,Jack Frost +2205,11,6,1,0,0x1,0,5,1,yes,0,0,0,magic,0, WL_MARSHOFABYSS,Marsh of Abyss +2206,0,6,4,0,0x1,0,5,1,yes,0,0,0,magic,0, WL_RECOGNIZEDSPELL,Recognized Spell +2207,7,6,1,2,0x3,1:2:2:3:3,5,1,yes,0,0,0,magic,0, WL_SIENNAEXECRATE,Sienna Execrate +2208,0,0,0,0,0,0,3,0,no,0,0,0,none,0, WL_RADIUS,Radius +2209,0,6,4,0,0x3,9:10:11:12:13,5,1,yes,0,0,0,magic,0, WL_STASIS,Stasis +2210,11,6,1,0,0,0,5,1,yes,0,0,0,magic,0, WL_DRAINLIFE,Drain Life +2211,11,8,1,3,0x2,3,5,-7,yes,0,0,0,magic,3, WL_CRIMSONROCK,Crimson Rock +2212,11,6,1,3,0,0,5,1,yes,0,0,0,magic,0, WL_HELLINFERNO,Hell Inferno +2213,11,8,2,0,0,0,5,-20,yes,0,0,0,magic,2, WL_COMET,Comet +2214,11,6,1,0,0,3,5,1,yes,0,0,0,magic,0, WL_CHAINLIGHTNING,Chain Lightning +2215,11,6,1,4,0,0,5,1,no,0,0,0,magic,0, WL_CHAINLIGHTNING_ATK,Chain Lightning Attack +2216,3,8,2,2,0,0,5,-6:-7:-8:-9:-10,yes,0,0,0,magic,0, WL_EARTHSTRAIN,Earth Strain +2217,11,6,1,0,0,0,5,1,yes,0,0,0,magic,0, WL_TETRAVORTEX,Tetra Vortex +2218,11,6,1,3,0,0,5,1,no,0,0,0,magic,0, WL_TETRAVORTEX_FIRE,Tetra Vortex Fire +2219,11,6,1,1,0,0,5,1,no,0,0,0,magic,0, WL_TETRAVORTEX_WATER,Tetra Vortex Water +2220,11,6,1,4,0,0,5,1,no,0,0,0,magic,0, WL_TETRAVORTEX_WIND,Tetra Vortex Wind +2221,11,6,1,2,0,0,5,1,no,0,0,0,magic,0, WL_TETRAVORTEX_GROUND,Tetra Vortex Earth +2222,0,6,4,3,0x1,0,5,1,yes,0,0,0,magic,0, WL_SUMMONFB,Summon Fire Ball +2223,0,6,4,4,0x1,0,5,1,yes,0,0,0,magic,0, WL_SUMMONBL,Summon Lightning Ball +2224,0,6,4,1,0x1,0,5,1,yes,0,0,0,magic,0, WL_SUMMONWB,Summon Water Ball +2225,11,6,1,3,0,0,5,1,no,0,0,1,magic,0, WL_SUMMON_ATK_FIRE,Summon Attack Fire +2226,11,6,1,4,0,0,5,1,no,0,0,1,magic,0, WL_SUMMON_ATK_WIND,Summon Attack Wind +2227,11,6,1,1,0,0,5,1,no,0,0,1,magic,0, WL_SUMMON_ATK_WATER,Summon Attack Water +2228,11,6,1,2,0,0,5,1,no,0,0,1,magic,0, WL_SUMMON_ATK_GROUND,Summon Attack Earth +2229,0,6,4,2,0x1,0,5,1,yes,0,0,0,magic,0, WL_SUMMONSTONE,Summon Stone +2230,11,6,1,0,0,0,2,1,yes,0,0,0,magic,0, WL_RELEASE,Release +2231,0,6,4,0,0x1,0,1,1,yes,0,0,0,magic,0, WL_READING_SB,Reading Spellbook +2232,0,0,0,0,0,0,5,0,no,0,0,0,none,0, WL_FREEZE_SP,Freeze Spell //**** // RA Ranger @@ -911,9 +909,6 @@ 2346,0,6,4,0,0x1,0,5,1,yes,0,0,0,none,0, SR_GENTLETOUCH_ENERGYGAIN,Gentle Touch - Energy Gain 2347,2,6,16,0,0x1,0,5,1,yes,0,0,0,none,0, SR_GENTLETOUCH_CHANGE,Gentle Touch - Change 2348,2,6,16,0,0x1,0,5,1,yes,0,0,0,none,0, SR_GENTLETOUCH_REVITALIZE,Gentle Touch - Revitalize -//More from Sura but not following ID order -2517,0,6,4,-1,0x2,3:4:5:6:7,5,1,no,0,0,0,weapon,0, SR_HOWLINGOFLION,Howling of Lion -2518,11,6,2,-1,0x2,2:2:3:3:4,5,1,no,0,0,0,weapon,0, SR_RIDEINLIGHTNING,Ride In Lightening //**** // WA Wanderer @@ -931,7 +926,7 @@ // WM Wanderer/Minstrel 2412,0,0,0,0,0,0,10,0,no,0,0,0,none,0, WM_LESSON,Lesson 2413,9,8,1,-1,0,0,5,-2:-2:-3:-3:-4,yes,0,0,0,magic,0, WM_METALICSOUND,Metallic Sound -2414,9,6,2,-1,0x3,1,5,1,yes,0,0x80,3,none,0, WM_REVERBERATION,Reverberation +2414,9,6,2,-1,0x3,1,5,1,yes,0,0x80,3,none,0, WM_REVERBERATION,Reverberation 2415,0,6,1,-1,0x6,1,5,1,no,0,0,0,weapon,0, WM_REVERBERATION_MELEE,Reverberation Melee 2416,0,6,1,0,0x6,1,5,1,no,0,0,0,magic,0, WM_REVERBERATION_MAGIC,Reverberation Magic 2417,11,6,2,0,0x3,5,1,1,no,0,0,0,none,0, WM_DOMINION_IMPULSE,Dominion Impulse @@ -952,7 +947,6 @@ 2432,0,6,4,0,0x3,5,5,1,yes,0,0x4000,0,none,0, WM_MELODYOFSINK,Melody of Sink 2433,0,6,4,0,0x3,5,5,1,yes,0,0x4000,0,none,0, WM_BEYOND_OF_WARCRY,Warcry of Beyond 2434,0,6,4,0,0x3,5,5,1,yes,0,0x4000,0,none,0, WM_UNLIMITED_HUMMING_VOICE,Unlimited Humming Voice -2516,11,6,1,-1,0x2,5,5,1,no,0,0,0,weapon,0, WM_SEVERE_RAINSTORM_MELEE,Severe Rainstorm Melee //**** // SO Sorcerer @@ -1011,12 +1005,17 @@ 2497,0,6,4,0,0x1,0,10,1,no,0,0,0,none,0, GN_S_PHARMACY,Special Pharmacy 2498,11,6,1,0,0,0,1,1,no,0,0,0,weapon,0, GN_SLINGITEM_RANGEMELEEATK,Sling Item Attack +2515,11,6,16,0,0x1,0,5,1,yes,0,0,0,magic,0, AB_SECRAMENT,Secrament +2516,11,6,1,-1,0x2,5,5,1,no,0,0,0,weapon,0, WM_SEVERE_RAINSTORM_MELEE,Severe Rainstorm Melee +2517,0,6,4,-1,0x2,3:4:5:6:7,5,1,no,0,0,0,weapon,0, SR_HOWLINGOFLION,Howling of Lion +2518,11,6,2,-1,0x2,2:2:3:3:4,5,1,no,0,0,0,weapon,0, SR_RIDEINLIGHTNING,Ride In Lightening + // Episode 13.3 //2533,0,0,4,0,0x1,0,1,0,no,0,0,0,none,0, ALL_ODINS_RECALL,Odin's Recall -2534,0,0,4,0,0x1,0,1,0,no,0,0,0,none,0, RETURN_TO_ELDICASTES,Return To Eldicastes +2534,0,0,4,0,0x1,0,1,0,no,0,0,0,none,0, RETURN_TO_ELDICASTES,Return To Eldicastes 2535,0,0,4,0,0x1,0,1,0,no,0,0x1,0,none,0, ALL_BUYING_STORE,Open Buying Store -2536,0,0,4,0,0x1,0,1,0,no,0,0,0,none,0, ALL_GUARDIAN_RECALL,Guardian's Recall -//2537,9,6,16,0,0x1,0,2,1,yes,0,0,0,magic,0, ALL_ODINS_POWER,Odin's Power +2536,0,0,4,0,0x1,0,1,0,no,0,0,0,none,0, ALL_GUARDIAN_RECALL,Guardian's Recall +2537,9,6,16,0,0x1,0,2,1,yes,0,0,0,magic,0, ALL_ODINS_POWER,Odin's Power //2538,0,0,0,0,0,0,??,0,no,0,0,0,none,0, BEER_BOTTLE_CAP,Beer Bottle Cap //2539,0,0,0,0,0,0,??,0,no,0,0,0,none,0, NPC_ASSASSINCROSS,Assassin Cross of Sunset 2 //2540,0,0,0,0,0,0,??,0,no,0,0,0,none,0, NPC_DISSONANCE,Dissonance 2 @@ -1024,8 +1023,11 @@ //2542,0,0,0,0,0,0,??,0,no,0,0,0,none,0, ALL_TETANY,Tetany //2543,0,0,0,0,0,0,??,0,no,0,0,0,none,0, ALL_RAY_OF_PROTECTION,Ray of Protection //2544,0,0,0,0,0,0,??,0,no,0,0,0,none,0, MC_CARTDECORATE,Decorate Cart +//2545,0,0,1,0,0,0,99,0,0,none,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0 //GM_ITEM_ATKMAX#Maximum Attack# +//2546,0,0,1,0,0,0,99,0,0,none,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0 //GM_ITEM_ATKMIN#Minimal Attack# +//2547,0,0,1,0,0,0,99,0,0,none,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0 //GM_ITEM_MATKMAX#Maximum Magic Attack# +//2548,0,0,1,0,0,0,99,0,0,none,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0 //GM_ITEM_MATKMIN#Minimal Magic Attack# -//**** // Kagerou & Oboro 3001,0,6,4,0,0,0,1,1,no,0,0,0,none,0, KO_YAMIKUMO,Yamikumo 3002,0,0,0,0,0,0,5,0,no,0,0,0,weapon,0, KO_RIGHT,Right Hand Mastery @@ -1034,18 +1036,18 @@ 3005,2,6,1,-1,0,0,5,1,no,0,0,0,weapon,0, KO_SETSUDAN,Soul Sever 3006,7:8:9:10:11,6,2,0,0x2,2,5,0,no,0,0,0,weapon,0, KO_BAKURETSU,Bakuretsu Kunai 3007,0,6,4,-1,0x42,4:4:4:4:5,5,0,no,0,0,0,misc,0, KO_HAPPOKUNAI,Happo Kunai -3008,9,8,2,0,0x52,2,10,-10,no,0,0,0,misc,0, KO_MUCHANAGE,Mucha Nage +3008,9,8,2,0,0x12,2,10,-10,no,0,0,0,misc,0, KO_MUCHANAGE,Mucha Nage 3009,9:10:11:12:13,8,2,-1,0x2,3,5,2,no,0,0,0,weapon,0, KO_HUUMARANKA,Huuma Shuriken Ranka -3010,3,6,4,0,0x43,0,5,1,no,0,0x80,0,misc,0, KO_MAKIBISHI,Makibishi +3010,3,6,4,0,0x42,0,5,1,no,0,0x80,0,weapon,0, KO_MAKIBISHI,Makibishi 3011,0,6,4,0,0x1,0,5,0,yes,0,0,0,none,0, KO_MEIKYOUSISUI,Meikyo Shisui -3012,0,6,4,0,0x1,0,5,0,no,0,0,1,none,7, KO_ZANZOU,Zanzou +3012,0,6,4,0,0x1,0,5,0,no,0,0,1,none,3:4:5:6:7, KO_ZANZOU,Zanzou 3013,5,6,1,0,0x1,0,5,0,no,0,0,0,none,0, KO_KYOUGAKU,Kyougaku 3014,5,6,1,0,0x1,0,5,0,no,0,0,0,none,0, KO_JYUSATSU,Jyusatsu 3015,0,6,4,3,0x1,0,1,1,no,0,0,0,none,0, KO_KAHU_ENTEN,Kahu Enten 3016,0,6,4,1,0x1,0,1,1,no,0,0,0,none,0, KO_HYOUHU_HUBUKI,Hyouhu Hubuki 3017,0,6,4,4,0x1,0,1,1,no,0,0,0,none,0, KO_KAZEHU_SEIRAN,Kazehu Seiran 3018,0,6,4,2,0x1,0,1,1,no,0,0,0,none,0, KO_DOHU_KOUKAI,Dohu Koukai -3019,11,6,1,0,0,0,5,0,no,0,0,0,weapon,0, KO_KAIHOU,Technique Kaihou +3019,11,6,1,0,0,0,5,0,no,0,0,0,magic,0, KO_KAIHOU,Technique Kaihou 3020,7,6,2,0,0,0,1,3,yes,0,0,0,magic,0, KO_ZENKAI,Zenkai 3021,5:6:7:8:9,6,16,0,0x1,0,5,1,no,0,0,0,none,0, KO_GENWAKU,Genwaku 3022,0,6,4,0,0x1,0,5,0,no,0,0,0,none,0, KO_IZAYOI,Izayoi @@ -1054,9 +1056,36 @@ 3025,7,6,16,0,0x1,0,5,1,no,0,0,0,none,0, KG_KAGEMUSYA,Kagemusha 3026,7,6,16,0,0x1,0,5,1,no,0,0,0,none,0, OB_ZANGETSU,Zangetsu 3027,7,6,16,0,0x1,0,5,1,no,0,0,0,none,0, OB_OBOROGENSOU,Oboro Gensou -3028,1,6,4,0,0x2,3,1,1,no,0,0,0,weapon,0, OB_OBOROGENSOU_TRANSITION_ATK, +3028,1,6,4,0,0x2,3,1,1,no,0,0,0,weapon,0, OB_OBOROGENSOU_TRANSITION_ATK,Hazy Moonlight Illusion Transition Attack 3029,7,6,1,0,0x1,0,5,0,no,0,0,0,none,0, OB_AKAITSUKI,Akaitsuki +// Eclage Skills +3031,7,6,16,0,0x1,0,1,1,no,0,0,0,none,0, ECL_SNOWFLIP,Snow Flip +3032,7,6,16,0,0x1,0,1,1,no,0,0,0,none,0, ECL_PEONYMAMY,Peony Mamy +3033,7,6,16,0,0x1,0,1,1,no,0,0,0,none,0, ECL_SADAGUI,Sadagui +3034,7,6,16,0,0x1,0,1,1,no,0,0,0,none,0, ECL_SEQUOIADUST,Sequoia Dust +3035,0,6,4,0,0x1,0,1,1,no,0,0,0,none,0, ECLAGE_RECALL,Return To Eclage + +// EP 14.3 Part 2 3rd Job Skills +5001,1,6,1,-1,0,0,5,1,no,0,0,0,weapon,0, GC_DARKCROW,Dark Claw +5002,0,6,4,0,0x1,0,5,1,no,0,0,0,none,0, RA_UNLIMIT,Unlimited +//5003,7,6,1,-1,0x2,4:5:6:7:8,5,1,no,0,0,0,weapon,0, GN_ILLUSIONDOPING,Illusion Doping +5004,9,6,2,1,0x2,1:1:1:2:2:2:3:3:4:4,10,1,no,0,0,0,misc,0, RK_DRAGONBREATH_WATER,Dragon Breath - Water +//5005,0,6,4,0,0x3,3,1,1,no,0,0,0,none,0, RK_LUXANIMA,Lux Anima +5006,1,6,2,3,0,0,5,1,no,0,0,3,misc,0, NC_MAGMA_ERUPTION,Magma Eruption +5007,0,6,4,0,0x3,5:6:7:8:9,5,1,no,0,0,0,none,0, WM_FRIGG_SONG,Frigg's Song +//5008,0,6,4,0,0x3,15,5,1,no,0,0,0,none,0, SO_ELEMENTAL_SHIELD,Elemental Shield +5009,1,6,1,0,0x1,0,5,1,no,0,0,0,none,0, SR_FLASHCOMBO,Flash Combo +//5010,0,6,4,0,0x1,0,5,1,no,0,0,0,none,0, SC_ESCAPE,Emergency Escape +5011,0,6,4,0,0x1,0,5,1,no,0,0,0,none,0, AB_OFFERTORIUM,Offertorium +5012,0,6,4,0,0x1,0,5,1,no,0,0,0,none,0, WL_TELEKINESIS_INTENSE,Intense Telekinesis +5013,0,6,4,0,0x3,5,5,1,no,0,0,0,none,0, LG_KINGS_GRACE,King's Grace +5014,0,6,4,0,0x1,0,5,1,no,0,0,0,none,0, ALL_FULL_THROTTLE,Full Throttle +5015,0,6,4,0,0x1,0,5,1,no,0,0,0,none,0, SR_FLASHCOMBO_ATK_STEP1,Flash Combo Attack Step 1 +5016,0,6,4,0,0x1,0,5,1,no,0,0,0,none,0, SR_FLASHCOMBO_ATK_STEP2,Flash Combo Attack Step 2 +5017,0,6,4,0,0x1,0,5,1,no,0,0,0,none,0, SR_FLASHCOMBO_ATK_STEP3,Flash Combo Attack Step 3 +5018,0,6,4,0,0x1,0,5,1,no,0,0,0,none,0, SR_FLASHCOMBO_ATK_STEP4,Flash Combo Attack Step 4 + 8001,9,6,4,0,0x1,0,5,1,no,0,0,0,magic,0, HLIF_HEAL,Healing Touch 8002,0,6,4,0,0x3,-1,5,1,no,0,0,0,none,0, HLIF_AVOID,Avoid 8003,0,0,0,0,0,1,5,0,no,0,0,0,none,0, HLIF_BRAIN,Brain Surgery diff --git a/db/pre-re/skill_require_db.txt b/db/pre-re/skill_require_db.txt index b8e549b08..3eb00ff95 100644 --- a/db/pre-re/skill_require_db.txt +++ b/db/pre-re/skill_require_db.txt @@ -820,6 +820,26 @@ 3027,0,0,55:60:65:70:75 ,0,0,0,99,0,0,none,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0 //OB_OBOROGENSOU#Oboro Gensou# 3029,0,0,20:30:40:50:60,0,0,0,99,0,0,none,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0 //OB_AKAITSUKI#Akaitsuki# +// EP 14.3 Part 2 3rd Job Skills +5001,0,0,22:34:46:58:70,0,0,0,99,0,0,none,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0 //GC_DARKCROW#Dark Claw# +5002,0,0,100:120:140:160:180,0,0,0,99,0,0,none,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0 //RA_UNLIMIT#Unlimited# +5003,0,0,60:70:80:90:100,0,0,0,99,0,0,none,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0 //GN_ILLUSIONDOPING#Illusion Doping# +5004,0,0,30:35:40:45:50:55:60:65:70:75,0,0,0,99,0,0,dragon,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0 //RK_DRAGONBREATH_WATER#Dragon Breath - Water# +5005,0,0,1,0,0,0,99,0,0,none,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0 //RK_LUXANIMA#Lux Anima# +5006,0,0,60:70:80:90:100,0,0,0,99,0,0,none,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0 //NC_MAGMA_ERUPTION#Magma Eruption# +5007,0,0,200:230:260:290:320,0,0,0,99,0,0,none,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0 //WM_FRIGG_SONG#Frigg's Song# +5008,0,0,120:120:120:120:120,0,0,0,99,0,0,none,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0 //SO_ELEMENTAL_SHIELD#Elemental Shield# +5009,0,0,75:65:55:45:35,0,0,0,99,0,0,none,5:5:4:4:3,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0 //SR_FLASHCOMBO#Flash Combo# +5010,0,0,30:26:22:18:14,0,0,0,99,0,0,none,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0 //SC_ESCAPE#Emergency Escape# +5011,0,0,30:60:90:120:150,0,0,0,99,0,0,none,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0 //AB_OFFERTORIUM#Offertorium# +5012,0,0,100:150:200:250:300,0,0,0,99,0,0,none,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0 //WL_TELEKINESIS_INTENSE#Intense Telekinesis# +5013,0,0,200:180:160:140:120,0,0,0,99,0,0,none,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0 //LG_KINGS_GRACE#King's Grace# +5014,0,0,1:1:1:1:1,0,0,0,99,0,0,none,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0 //ALL_FULL_THROTTLE#Full Throttle# +5015,0,0,1,0,0,0,99,0,0,none,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0 //SR_FLASHCOMBO_ATK_STEP1#Flash Combo Attack Step 1#//All 4 steps are using temp req SP values for now. +5016,0,0,1,0,0,0,99,0,0,none,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0 //SR_FLASHCOMBO_ATK_STEP2#Flash Combo Attack Step 2# +5017,0,0,1,0,0,0,99,0,0,none,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0 //SR_FLASHCOMBO_ATK_STEP3#Flash Combo Attack Step 3# +5018,0,0,1,0,0,0,99,0,0,none,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0 //SR_FLASHCOMBO_ATK_STEP4#Flash Combo Attack Step 4# + 10010,0,0,1,0,0,0,99,0,0,none,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0 //GD_BATTLEORDER## 10011,0,0,1,0,0,0,99,0,0,none,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0 //GD_REGENERATION## 10012,0,0,1,0,0,0,99,0,0,none,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0 //GD_RESTORE## diff --git a/db/pre-re/skill_tree.txt b/db/pre-re/skill_tree.txt index f1954a2bc..f10c29dbb 100644 --- a/db/pre-re/skill_tree.txt +++ b/db/pre-re/skill_tree.txt @@ -2483,6 +2483,8 @@ 4054,2009,5,2007,2,0,0,0,0,0,0,0,0 //RK_DRAGONHOWLING#Dragon Howling# 4054,2010,10,0,0,0,0,0,0,0,0,0,0 //RK_RUNEMASTERY#Rune Mastery# 4054,2020,5,57,2,0,0,0,0,0,0,0,0 //RK_PHANTOMTHRUST#Phantom Thrust# +4054,5004,10,2007,2,0,0,0,0,0,0,0,0 //RK_DRAGONBREATH_WATER#Dragon Breath(Water)# +4054,5014,5,0,0,0,0,0,0,0,0,0,0 //ALL_FULL_THROTTLE#Full Throttle# //Warlock (Regular) 4055,1,9,0,0,0,0,0,0,0,0,0,0 //NV_BASIC#Basic Skill# 4055,142,1,0,0,0,0,0,0,0,0,0,0 //NV_FIRSTAID#First Aid# @@ -2539,6 +2541,8 @@ 4055,2230,2,0,0,0,0,0,0,0,0,0,0 //WL_RELEASE#Release# 4055,2231,1,0,0,0,0,0,0,0,0,0,0 //WL_READING_SB#Reading Spellbook# 4055,2232,5,0,0,0,0,0,0,0,0,0,0 //WL_FREEZE_SP#Freeze Spell# +4055,5012,5,2202,5,0,0,0,0,0,0,0,0 //WL_TELEKINESIS_INTENSE#Intense Telekinesis# +4055,5014,5,0,0,0,0,0,0,0,0,0,0 //ALL_FULL_THROTTLE#Full Throttle# //Ranger (Regular) 4056,1,9,0,0,0,0,0,0,0,0,0,0 //NV_BASIC#Basic Skill# 4056,142,1,0,0,0,0,0,0,0,0,0,0 //NV_FIRSTAID#First Aid# @@ -2592,6 +2596,8 @@ 4056,2252,1,2248,1,0,0,0,0,0,0,0,0 //RA_VERDURETRAP#Verdure Trap# 4056,2253,5,2237,1,0,0,0,0,0,0,0,0 //RA_FIRINGTRAP#Firing Trap# 4056,2254,5,2237,1,0,0,0,0,0,0,0,0 //RA_ICEBOUNDTRAP#Icebound Trap# +4056,5002,5,2234,5,0,0,0,0,0,0,0,0 //RA_UNLIMIT#Unlimit# +4056,5014,5,0,0,0,0,0,0,0,0,0,0 //ALL_FULL_THROTTLE#Full Throttle# //Arch Bishop (Regular) 4057,1,9,0,0,0,0,0,0,0,0,0,0 //NV_BASIC#Basic Skill# 4057,142,1,0,0,0,0,0,0,0,0,0,0 //NV_FIRSTAID#First Aid# @@ -2650,6 +2656,8 @@ 4057,2054,10,68,1,0,0,0,0,0,0,0,0 //AB_DUPLELIGHT#Duple Light# 4057,2057,5,2052,1,0,0,0,0,0,0,0,0 //AB_SILENTIUM#Silentium# 4057,2515,5,2044,1,2053,1,0,0,0,0,0,0 //AB_SECRAMENT#Secrament# +4057,5011,5,2051,2,0,0,0,0,0,0,0,0 //AB_OFFERTORIUM#Offertorium# +4057,5014,5,0,0,0,0,0,0,0,0,0,0 //ALL_FULL_THROTTLE#Full Throttle# //Mechanic (Regular) 4058,1,9,0,0,0,0,0,0,0,0,0,0 //NV_BASIC#Basic Skill# 4058,142,1,0,0,0,0,0,0,0,0,0,0 //NV_FIRSTAID#First Aid# @@ -2718,7 +2726,9 @@ 4058,2281,5,2277,2,0,0,0,0,0,0,0,0 //NC_SILVERSNIPER#FAW - Silver Sniper# 4058,2282,5,2277,2,0,0,0,0,0,0,0,0 //NC_MAGICDECOY#FAW - Magic Decoy# 4058,2283,1,2281,1,0,0,0,0,0,0,0,0 //NC_DISJOINT#FAW Removal# +4058,5006,5,0,0,0,0,0,0,0,0,0,0 //NC_MAGMA_ERUPTION#Magma Eruption# 4058,2535,1,41,1,0,0,0,0,0,0,0,0 //ALL_BUYING_STORE#Open Buying Store# +4058,5014,5,0,0,0,0,0,0,0,0,0,0 //ALL_FULL_THROTTLE#Full Throttle# //Guillotine Cross (Regular) 4059,1,9,0,0,0,0,0,0,0,0,0,0 //NV_BASIC#Basic Skill# 4059,142,1,0,0,0,0,0,0,0,0,0,0 //NV_FIRSTAID#First Aid# @@ -2763,6 +2773,8 @@ 4059,2035,5,2034,1,0,0,0,0,0,0,0,0 //GC_HALLUCINATIONWALK#Hallucination Walk# 4059,2036,5,136,10,0,0,0,0,0,0,0,0 //GC_ROLLINGCUTTER#Rolling Cutter# 4059,2037,5,2036,1,0,0,0,0,0,0,0,0 //GC_CROSSRIPPERSLASHER#Cross Ripper Slasher# +4059,5001,5,2023,5,0,0,0,0,0,0,0,0 //GC_DARKCROW#Dark Claw# +4059,5014,5,0,0,0,0,0,0,0,0,0,0 //ALL_FULL_THROTTLE#Full Throttle# //Rune Knight (Trans) 4060,1,9,0,0,0,0,0,0,0,0,0,0 //NV_BASIC#Basic Skill# 4060,142,1,0,0,0,0,0,0,0,0,0,0 //NV_FIRSTAID#First Aid# @@ -2809,6 +2821,8 @@ 4060,2009,5,2007,2,0,0,0,0,0,0,0,0 //RK_DRAGONHOWLING#Dragon Howling# 4060,2010,10,0,0,0,0,0,0,0,0,0,0 //RK_RUNEMASTERY#Rune Mastery# 4060,2020,5,57,2,0,0,0,0,0,0,0,0 //RK_PHANTOMTHRUST#Phantom Thrust# +4060,5004,10,2007,2,0,0,0,0,0,0,0,0 //RK_DRAGONBREATH_WATER#Dragon Breath(Water)# +4060,5014,5,0,0,0,0,0,0,0,0,0,0 //ALL_FULL_THROTTLE#Full Throttle# //Warlock (Trans) 4061,1,9,0,0,0,0,0,0,0,0,0,0 //NV_BASIC#Basic Skill# 4061,142,1,0,0,0,0,0,0,0,0,0,0 //NV_FIRSTAID#First Aid# @@ -2871,6 +2885,8 @@ 4061,2230,2,0,0,0,0,0,0,0,0,0,0 //WL_RELEASE#Release# 4061,2231,1,0,0,0,0,0,0,0,0,0,0 //WL_READING_SB#Reading Spellbook# 4061,2232,5,0,0,0,0,0,0,0,0,0,0 //WL_FREEZE_SP#Freeze Spell# +4061,5012,5,2202,5,0,0,0,0,0,0,0,0 //WL_TELEKINESIS_INTENSE#Intense Telekinesis# +4061,5014,5,0,0,0,0,0,0,0,0,0,0 //ALL_FULL_THROTTLE#Full Throttle# //Ranger (Trans) 4062,1,9,0,0,0,0,0,0,0,0,0,0 //NV_BASIC#Basic Skill# 4062,142,1,0,0,0,0,0,0,0,0,0,0 //NV_FIRSTAID#First Aid# @@ -2928,6 +2944,8 @@ 4062,2252,1,2248,1,0,0,0,0,0,0,0,0 //RA_VERDURETRAP#Verdure Trap# 4062,2253,5,2237,1,0,0,0,0,0,0,0,0 //RA_FIRINGTRAP#Firing Trap# 4062,2254,5,2237,1,0,0,0,0,0,0,0,0 //RA_ICEBOUNDTRAP#Icebound Trap# +4062,5002,5,2234,5,0,0,0,0,0,0,0,0 //RA_UNLIMIT#Unlimit# +4062,5014,5,0,0,0,0,0,0,0,0,0,0 //ALL_FULL_THROTTLE#Full Throttle# //Arch Bishop (Trans) 4063,1,9,0,0,0,0,0,0,0,0,0,0 //NV_BASIC#Basic Skill# 4063,142,1,0,0,0,0,0,0,0,0,0,0 //NV_FIRSTAID#First Aid# @@ -2990,6 +3008,8 @@ 4063,2054,10,68,1,0,0,0,0,0,0,0,0 //AB_DUPLELIGHT#Duple Light# 4063,2057,5,2052,1,0,0,0,0,0,0,0,0 //AB_SILENTIUM#Silentium# 4063,2515,5,2044,1,2053,1,0,0,0,0,0,0 //AB_SECRAMENT#Secrament# +4063,5011,5,2051,2,0,0,0,0,0,0,0,0 //AB_OFFERTORIUM#Offertorium# +4063,5014,5,0,0,0,0,0,0,0,0,0,0 //ALL_FULL_THROTTLE#Full Throttle# //Mechanic (Trans) 4064,1,9,0,0,0,0,0,0,0,0,0,0 //NV_BASIC#Basic Skill# 4064,142,1,0,0,0,0,0,0,0,0,0,0 //NV_FIRSTAID#First Aid# @@ -3063,7 +3083,9 @@ 4064,2281,5,2277,2,0,0,0,0,0,0,0,0 //NC_SILVERSNIPER#FAW - Silver Sniper# 4064,2282,5,2277,2,0,0,0,0,0,0,0,0 //NC_MAGICDECOY#FAW - Magic Decoy# 4064,2283,1,2281,1,0,0,0,0,0,0,0,0 //NC_DISJOINT#FAW Removal# +4064,5006,5,0,0,0,0,0,0,0,0,0,0 //NC_MAGMA_ERUPTION#Magma Eruption# 4064,2535,1,41,1,0,0,0,0,0,0,0,0 //ALL_BUYING_STORE#Open Buying Store# +4064,5014,5,0,0,0,0,0,0,0,0,0,0 //ALL_FULL_THROTTLE#Full Throttle# //Guillotine Cross (Trans) 4065,1,9,0,0,0,0,0,0,0,0,0,0 //NV_BASIC#Basic Skill# 4065,142,1,0,0,0,0,0,0,0,0,0,0 //NV_FIRSTAID#First Aid# @@ -3113,6 +3135,8 @@ 4065,2035,5,2034,1,0,0,0,0,0,0,0,0 //GC_HALLUCINATIONWALK#Hallucination Walk# 4065,2036,5,136,10,0,0,0,0,0,0,0,0 //GC_ROLLINGCUTTER#Rolling Cutter# 4065,2037,5,2036,1,0,0,0,0,0,0,0,0 //GC_CROSSRIPPERSLASHER#Cross Ripper Slasher# +4065,5001,5,2023,5,0,0,0,0,0,0,0,0 //GC_DARKCROW#Dark Claw# +4065,5014,5,0,0,0,0,0,0,0,0,0,0 //ALL_FULL_THROTTLE#Full Throttle# //Royal Guard (Regular) 4066,1,9,0,0,0,0,0,0,0,0,0,0 //NV_BASIC#Basic Skill# 4066,142,1,0,0,0,0,0,0,0,0,0,0 //NV_FIRSTAID#First Aid# @@ -3166,6 +3190,8 @@ 4066,2323,5,2311,3,0,0,0,0,0,0,0,0 //LG_EARTHDRIVE#Earth Drive# 4066,2324,5,2318,3,2319,3,0,0,0,0,0,0 //LG_HESPERUSLIT#Hesperus Lit# 4066,2325,5,2315,3,2321,4,2322,5,0,0,0,0 //LG_INSPIRATION#Inspiration# +4066,5013,5,2311,5,0,0,0,0,0,0,0,0 //LG_KINGS_GRACE#King's Grace# +4066,5014,5,0,0,0,0,0,0,0,0,0,0 //ALL_FULL_THROTTLE#Full Throttle# //Sorcerer (Regular) 4067,1,9,0,0,0,0,0,0,0,0,0,0 //NV_BASIC#Basic Skill# 4067,142,1,0,0,0,0,0,0,0,0,0,0 //NV_FIRSTAID#First Aid# @@ -3236,6 +3262,7 @@ 4067,2466,3,2458,3,0,0,0,0,0,0,0,0 //SO_WATER_INSIGNIA#Water Insignia# 4067,2467,3,2459,3,0,0,0,0,0,0,0,0 //SO_WIND_INSIGNIA#Wind Insignia# 4067,2468,3,2460,3,0,0,0,0,0,0,0,0 //SO_EARTH_INSIGNIA#Earth Insignia# +4067,5014,5,0,0,0,0,0,0,0,0,0,0 //ALL_FULL_THROTTLE#Full Throttle# //Minstrel (Regular) 4068,1,9,0,0,0,0,0,0,0,0,0,0 //NV_BASIC#Basic Skill# 4068,142,1,0,0,0,0,0,0,0,0,0,0 //NV_FIRSTAID#First Aid# @@ -3291,6 +3318,8 @@ 4068,2432,5,2427,1,0,0,0,0,0,0,0,0 //WM_MELODYOFSINK#Melody Of Sink# 4068,2433,5,2431,1,0,0,0,0,0,0,0,0 //WM_BEYOND_OF_WARCRY#Warcry Of Beyond# 4068,2434,5,2429,1,2433,1,0,0,0,0,0,0 //WM_UNLIMITED_HUMMING_VOICE#Unlimited Humming Voice# +4068,5007,5,2412,1,0,0,0,0,0,0,0,0 //WM_FRIGG_SONG# +4068,5014,5,0,0,0,0,0,0,0,0,0,0 //ALL_FULL_THROTTLE#Full Throttle# //Wanderer (Regular) 4069,1,9,0,0,0,0,0,0,0,0,0,0 //NV_BASIC#Basic Skill# 4069,142,1,0,0,0,0,0,0,0,0,0,0 //NV_FIRSTAID#First Aid# @@ -3346,6 +3375,8 @@ 4069,2432,5,2427,1,0,0,0,0,0,0,0,0 //WM_MELODYOFSINK#Melody Of Sink# 4069,2433,5,2431,1,0,0,0,0,0,0,0,0 //WM_BEYOND_OF_WARCRY#Warcry Of Beyond# 4069,2434,5,2429,1,2433,1,0,0,0,0,0,0 //WM_UNLIMITED_HUMMING_VOICE#Unlimited Humming Voice# +4069,5007,5,2412,1,0,0,0,0,0,0,0,0 //WM_FRIGG_SONG# +4069,5014,5,0,0,0,0,0,0,0,0,0,0 //ALL_FULL_THROTTLE#Full Throttle# //Sura (Regular) 4070,1,9,0,0,0,0,0,0,0,0,0,0 //NV_BASIC#Basic Skill# 4070,142,1,0,0,0,0,0,0,0,0,0,0 //NV_FIRSTAID#First Aid# @@ -3405,6 +3436,8 @@ 4070,2348,5,2347,5,0,0,0,0,0,0,0,0 //SR_GENTLETOUCH_REVITALIZE#Gentle Touch - Revitalize# 4070,2517,5,2340,1,2518,3,0,0,0,0,0,0 //SR_HOWLINGOFLION#Howling Of Lion# 4070,2518,5,267,3,0,0,0,0,0,0,0,0 //SR_RIDEINLIGHTNING#Ride In Lightening# +4070,5009,5,2326,3,2329,3,2330,1,2327,1,0,0 //SR_FLASHCOMBO#Flash Combo# +4070,5014,5,0,0,0,0,0,0,0,0,0,0 //ALL_FULL_THROTTLE#Full Throttle# //Genetic (Regular) 4071,1,9,0,0,0,0,0,0,0,0,0,0 //NV_BASIC#Basic Skill# 4071,142,1,0,0,0,0,0,0,0,0,0,0 //NV_FIRSTAID#First Aid# @@ -3459,7 +3492,9 @@ 4071,2495,2,2497,1,0,0,0,0,0,0,0,0 //GN_MIX_COOKING#Mix Cooking# 4071,2496,2,2495,1,0,0,0,0,0,0,0,0 //GN_MAKEBOMB#Create Bomb# 4071,2497,10,0,0,0,0,0,0,0,0,0,0 //GN_S_PHARMACY#Special Pharmacy# +4071,5003,5,2497,1,0,0,0,0,0,0,0,0 //GN_ILLUSIONDOOPING#Hallucination Drug# 4071,2535,1,41,1,0,0,0,0,0,0,0,0 //ALL_BUYING_STORE#Open Buying Store# +4071,5014,5,0,0,0,0,0,0,0,0,0,0 //ALL_FULL_THROTTLE#Full Throttle# //Shadow Chaser (Regular) 4072,1,9,0,0,0,0,0,0,0,0,0,0 //NV_BASIC#Basic Skill# 4072,142,1,0,0,0,0,0,0,0,0,0,0 //NV_FIRSTAID#First Aid# @@ -3517,6 +3552,8 @@ 4072,2302,3,2296,3,2301,3,0,0,0,0,0,0 //SC_MAELSTROM#Maelstrom# 4072,2303,3,2300,3,0,0,0,0,0,0,0,0 //SC_BLOODYLUST#Bloody Lust# 4072,2304,3,2300,3,0,0,0,0,0,0,0,0 //SC_FEINTBOMB#Feint Bomb# +4072,5010,5,2288,2,0,0,0,0,0,0,0,0 //SC_SCAPE#Scape# +4072,5014,5,0,0,0,0,0,0,0,0,0,0 //ALL_FULL_THROTTLE#Full Throttle# //Royal Guard (Trans) 4073,1,9,0,0,0,0,0,0,0,0,0,0 //NV_BASIC#Basic Skill# 4073,142,1,0,0,0,0,0,0,0,0,0,0 //NV_FIRSTAID#First Aid# @@ -3574,6 +3611,8 @@ 4073,2323,5,2311,3,0,0,0,0,0,0,0,0 //LG_EARTHDRIVE#Earth Drive# 4073,2324,5,2318,3,2319,3,0,0,0,0,0,0 //LG_HESPERUSLIT#Hesperus Lit# 4073,2325,5,2315,3,2321,4,2322,5,0,0,0,0 //LG_INSPIRATION#Inspiration# +4073,5013,5,2311,5,0,0,0,0,0,0,0,0 //LG_KINGS_GRACE#King's Grace# +4073,5014,5,0,0,0,0,0,0,0,0,0,0 //ALL_FULL_THROTTLE#Full Throttle# //Sorcerer (Trans) 4074,1,9,0,0,0,0,0,0,0,0,0,0 //NV_BASIC#Basic Skill# 4074,142,1,0,0,0,0,0,0,0,0,0,0 //NV_FIRSTAID#First Aid# @@ -3652,6 +3691,7 @@ 4074,2466,3,2458,3,0,0,0,0,0,0,0,0 //SO_WATER_INSIGNIA#Water Insignia# 4074,2467,3,2459,3,0,0,0,0,0,0,0,0 //SO_WIND_INSIGNIA#Wind Insignia# 4074,2468,3,2460,3,0,0,0,0,0,0,0,0 //SO_EARTH_INSIGNIA#Earth Insignia# +4074,5014,5,0,0,0,0,0,0,0,0,0,0 //ALL_FULL_THROTTLE#Full Throttle# //Minstrel (Trans) 4075,1,9,0,0,0,0,0,0,0,0,0,0 //NV_BASIC#Basic Skill# 4075,142,1,0,0,0,0,0,0,0,0,0,0 //NV_FIRSTAID#First Aid# @@ -3713,6 +3753,8 @@ 4075,2432,5,2427,1,0,0,0,0,0,0,0,0 //WM_MELODYOFSINK#Melody Of Sink# 4075,2433,5,2431,1,0,0,0,0,0,0,0,0 //WM_BEYOND_OF_WARCRY#Warcry Of Beyond# 4075,2434,5,2429,1,2433,1,0,0,0,0,0,0 //WM_UNLIMITED_HUMMING_VOICE#Unlimited Humming Voice# +4075,5007,5,2412,1,0,0,0,0,0,0,0,0 //WM_FRIGG_SONG# +4075,5014,5,0,0,0,0,0,0,0,0,0,0 //ALL_FULL_THROTTLE#Full Throttle# //Wanderer (Trans) 4076,1,9,0,0,0,0,0,0,0,0,0,0 //NV_BASIC#Basic Skill# 4076,142,1,0,0,0,0,0,0,0,0,0,0 //NV_FIRSTAID#First Aid# @@ -3774,6 +3816,8 @@ 4076,2432,5,2427,1,0,0,0,0,0,0,0,0 //WM_MELODYOFSINK#Melody Of Sink# 4076,2433,5,2431,1,0,0,0,0,0,0,0,0 //WM_BEYOND_OF_WARCRY#Warcry Of Beyond# 4076,2434,5,2429,1,2433,1,0,0,0,0,0,0 //WM_UNLIMITED_HUMMING_VOICE#Unlimited Humming Voice# +4076,5007,5,2412,1,0,0,0,0,0,0,0,0 //WM_FRIGG_SONG# +4076,5014,5,0,0,0,0,0,0,0,0,0,0 //ALL_FULL_THROTTLE#Full Throttle# //Sura (Trans) 4077,1,9,0,0,0,0,0,0,0,0,0,0 //NV_BASIC#Basic Skill# 4077,142,1,0,0,0,0,0,0,0,0,0,0 //NV_FIRSTAID#First Aid# @@ -3837,6 +3881,8 @@ 4077,2348,5,2347,5,0,0,0,0,0,0,0,0 //SR_GENTLETOUCH_REVITALIZE#Gentle Touch - Revitalize# 4077,2517,5,2340,1,2518,3,0,0,0,0,0,0 //SR_HOWLINGOFLION#Howling Of Lion# 4077,2518,5,267,3,0,0,0,0,0,0,0,0 //SR_RIDEINLIGHTNING#Ride In Lightening# +4077,5009,5,2326,3,2329,3,2330,1,2327,1,0,0 //SR_FLASHCOMBO#Flash Combo# +4077,5014,5,0,0,0,0,0,0,0,0,0,0 //ALL_FULL_THROTTLE#Full Throttle# //Genetic (Trans) 4078,1,9,0,0,0,0,0,0,0,0,0,0 //NV_BASIC#Basic Skill# 4078,142,1,0,0,0,0,0,0,0,0,0,0 //NV_FIRSTAID#First Aid# @@ -3895,7 +3941,9 @@ 4078,2495,2,2497,1,0,0,0,0,0,0,0,0 //GN_MIX_COOKING#Mix Cooking# 4078,2496,2,2495,1,0,0,0,0,0,0,0,0 //GN_MAKEBOMB#Create Bomb# 4078,2497,10,0,0,0,0,0,0,0,0,0,0 //GN_S_PHARMACY#Special Pharmacy# +4078,5003,5,2497,1,0,0,0,0,0,0,0,0 //GN_ILLUSIONDOOPING#Hallucination Drug# 4078,2535,1,41,1,0,0,0,0,0,0,0,0 //ALL_BUYING_STORE#Open Buying Store# +4078,5014,5,0,0,0,0,0,0,0,0,0,0 //ALL_FULL_THROTTLE#Full Throttle# //Shadow Chaser (Trans) 4079,1,9,0,0,0,0,0,0,0,0,0,0 //NV_BASIC#Basic Skill# 4079,142,1,0,0,0,0,0,0,0,0,0,0 //NV_FIRSTAID#First Aid# @@ -3941,6 +3989,7 @@ 4079,2286,10,2285,5,0,0,0,0,0,0,0,0 //SC_AUTOSHADOWSPELL#Auto Shadow Spell# 4079,2287,5,213,3,0,0,0,0,0,0,0,0 //SC_SHADOWFORM#Shadow Form# 4079,2288,10,46,7,0,0,0,0,0,0,0,0 //SC_TRIANGLESHOT#Triangle Shot# +4079,5010,5,2288,2,0,0,0,0,0,0,0,0 //SC_SCAPE#Scape# 4079,2289,5,0,0,0,0,0,0,0,0,0,0 //SC_BODYPAINT#Body Painting# 4079,2290,5,2286,7,2291,5,2296,3,0,0,0,0 //SC_INVISIBILITY#Invisibility# 4079,2291,5,2286,5,2287,3,0,0,0,0,0,0 //SC_DEADLYINFECT#Deadly Infect# @@ -3957,6 +4006,7 @@ 4079,2302,3,2296,3,2301,3,0,0,0,0,0,0 //SC_MAELSTROM#Maelstrom# 4079,2303,3,2300,3,0,0,0,0,0,0,0,0 //SC_BLOODYLUST#Bloody Lust# 4079,2304,3,2300,3,0,0,0,0,0,0,0,0 //SC_FEINTBOMB#Feint Bomb# +4079,5014,5,0,0,0,0,0,0,0,0,0,0 //ALL_FULL_THROTTLE#Full Throttle# //Rune Knight (Dragon) (Regular) 4080,1,9,0,0,0,0,0,0,0,0,0,0 //NV_BASIC#Basic Skill# 4080,142,1,0,0,0,0,0,0,0,0,0,0 //NV_FIRSTAID#First Aid# @@ -3995,6 +4045,8 @@ 4080,2009,5,2007,2,0,0,0,0,0,0,0,0 //RK_DRAGONHOWLING#Dragon Howling# 4080,2010,10,0,0,0,0,0,0,0,0,0,0 //RK_RUNEMASTERY#Rune Mastery# 4080,2020,5,57,2,0,0,0,0,0,0,0,0 //RK_PHANTOMTHRUST#Phantom Thrust# +4080,5004,10,2007,2,0,0,0,0,0,0,0,0 //RK_DRAGONBREATH_WATER#Dragon Breath(Water)# +4080,5014,5,0,0,0,0,0,0,0,0,0,0 //ALL_FULL_THROTTLE#Full Throttle# //Rune Knight (Dragon) (Trans) 4081,1,9,0,0,0,0,0,0,0,0,0,0 //NV_BASIC#Basic Skill# 4081,142,1,0,0,0,0,0,0,0,0,0,0 //NV_FIRSTAID#First Aid# @@ -4041,6 +4093,8 @@ 4081,2009,5,2007,2,0,0,0,0,0,0,0,0 //RK_DRAGONHOWLING#Dragon Howling# 4081,2010,10,0,0,0,0,0,0,0,0,0,0 //RK_RUNEMASTERY#Rune Mastery# 4081,2020,5,57,2,0,0,0,0,0,0,0,0 //RK_PHANTOMTHRUST#Phantom Thrust# +4081,5004,10,2007,2,0,0,0,0,0,0,0,0 //RK_DRAGONBREATH_WATER#Dragon Breath(Water)# +4081,5014,5,0,0,0,0,0,0,0,0,0,0 //ALL_FULL_THROTTLE#Full Throttle# //Royal Guard (Gryphon) (Regular) 4082,1,9,0,0,0,0,0,0,0,0,0,0 //NV_BASIC#Basic Skill# 4082,142,1,0,0,0,0,0,0,0,0,0,0 //NV_FIRSTAID#First Aid# @@ -4094,6 +4148,8 @@ 4082,2323,5,2311,3,0,0,0,0,0,0,0,0 //LG_EARTHDRIVE#Earth Drive# 4082,2324,5,2318,3,2319,3,0,0,0,0,0,0 //LG_HESPERUSLIT#Hesperus Lit# 4082,2325,5,2315,3,2321,4,2322,5,0,0,0,0 //LG_INSPIRATION#Inspiration# +4082,5013,5,2311,5,0,0,0,0,0,0,0,0 //LG_KINGS_GRACE#King's Grace# +4082,5014,5,0,0,0,0,0,0,0,0,0,0 //ALL_FULL_THROTTLE#Full Throttle# //Royal Guard (Gryphon) (Trans) 4083,1,9,0,0,0,0,0,0,0,0,0,0 //NV_BASIC#Basic Skill# 4083,142,1,0,0,0,0,0,0,0,0,0,0 //NV_FIRSTAID#First Aid# @@ -4151,6 +4207,8 @@ 4083,2323,5,2311,3,0,0,0,0,0,0,0,0 //LG_EARTHDRIVE#Earth Drive# 4083,2324,5,2318,3,2319,3,0,0,0,0,0,0 //LG_HESPERUSLIT#Hesperus Lit# 4083,2325,5,2315,3,2321,4,2322,5,0,0,0,0 //LG_INSPIRATION#Inspiration# +4083,5013,5,2311,5,0,0,0,0,0,0,0,0 //LG_KINGS_GRACE#King's Grace# +4083,5014,5,0,0,0,0,0,0,0,0,0,0 //ALL_FULL_THROTTLE#Full Throttle# //Ranger (Warg) (Regular) 4084,1,9,0,0,0,0,0,0,0,0,0,0 //NV_BASIC#Basic Skill# 4084,142,1,0,0,0,0,0,0,0,0,0,0 //NV_FIRSTAID#First Aid# @@ -4204,6 +4262,8 @@ 4084,2252,1,2248,1,0,0,0,0,0,0,0,0 //RA_VERDURETRAP#Verdure Trap# 4084,2253,5,2237,1,0,0,0,0,0,0,0,0 //RA_FIRINGTRAP#Firing Trap# 4084,2254,5,2237,1,0,0,0,0,0,0,0,0 //RA_ICEBOUNDTRAP#Icebound Trap# +4084,5002,5,2234,5,0,0,0,0,0,0,0,0 //RA_UNLIMIT#Unlimit# +4084,5014,5,0,0,0,0,0,0,0,0,0,0 //ALL_FULL_THROTTLE#Full Throttle# //Ranger (Warg) (Trans) 4085,1,9,0,0,0,0,0,0,0,0,0,0 //NV_BASIC#Basic Skill# 4085,142,1,0,0,0,0,0,0,0,0,0,0 //NV_FIRSTAID#First Aid# @@ -4261,6 +4321,8 @@ 4085,2252,1,2248,1,0,0,0,0,0,0,0,0 //RA_VERDURETRAP#Verdure Trap# 4085,2253,5,2237,1,0,0,0,0,0,0,0,0 //RA_FIRINGTRAP#Firing Trap# 4085,2254,5,2237,1,0,0,0,0,0,0,0,0 //RA_ICEBOUNDTRAP#Icebound Trap# +4085,5002,5,2234,5,0,0,0,0,0,0,0,0 //RA_UNLIMIT#Unlimit# +4085,5014,5,0,0,0,0,0,0,0,0,0,0 //ALL_FULL_THROTTLE#Full Throttle# //Mechanic (Mado) (Regular) 4086,1,9,0,0,0,0,0,0,0,0,0,0 //NV_BASIC#Basic Skill# 4086,142,1,0,0,0,0,0,0,0,0,0,0 //NV_FIRSTAID#First Aid# @@ -4329,7 +4391,9 @@ 4086,2281,5,2277,2,0,0,0,0,0,0,0,0 //NC_SILVERSNIPER#FAW - Silver Sniper# 4086,2282,5,2277,2,0,0,0,0,0,0,0,0 //NC_MAGICDECOY#FAW - Magic Decoy# 4086,2283,1,2281,1,0,0,0,0,0,0,0,0 //NC_DISJOINT#FAW Removal# +4086,5006,5,0,0,0,0,0,0,0,0,0,0 //NC_MAGMA_ERUPTION#Magma Eruption# 4086,2535,1,41,1,0,0,0,0,0,0,0,0 //ALL_BUYING_STORE#Open Buying Store# +4086,5014,5,0,0,0,0,0,0,0,0,0,0 //ALL_FULL_THROTTLE#Full Throttle# //Mechanic (Mado) (Trans) 4087,1,9,0,0,0,0,0,0,0,0,0,0 //NV_BASIC#Basic Skill# 4087,142,1,0,0,0,0,0,0,0,0,0,0 //NV_FIRSTAID#First Aid# @@ -4403,7 +4467,9 @@ 4087,2281,5,2277,2,0,0,0,0,0,0,0,0 //NC_SILVERSNIPER#FAW - Silver Sniper# 4087,2282,5,2277,2,0,0,0,0,0,0,0,0 //NC_MAGICDECOY#FAW - Magic Decoy# 4087,2283,1,2281,1,0,0,0,0,0,0,0,0 //NC_DISJOINT#FAW Removal# +4087,5006,5,0,0,0,0,0,0,0,0,0,0 //NC_MAGMA_ERUPTION#Magma Eruption# 4087,2535,1,41,1,0,0,0,0,0,0,0,0 //ALL_BUYING_STORE#Open Buying Store# +4087,5014,5,0,0,0,0,0,0,0,0,0,0 //ALL_FULL_THROTTLE#Full Throttle# //Baby Rune Knight 4096,1,9,0,0,0,0,0,0,0,0,0,0 //NV_BASIC#Basic Skill# 4096,142,1,0,0,0,0,0,0,0,0,0,0 //NV_FIRSTAID#First Aid# @@ -4443,6 +4509,8 @@ 4096,2009,5,2007,2,0,0,0,0,0,0,0,0 //RK_DRAGONHOWLING#Dragon Howling# 4096,2010,10,0,0,0,0,0,0,0,0,0,0 //RK_RUNEMASTERY#Rune Mastery# 4096,2020,5,57,2,0,0,0,0,0,0,0,0 //RK_PHANTOMTHRUST#Phantom Thrust# +4096,5004,10,2007,2,0,0,0,0,0,0,0,0 //RK_DRAGONBREATH_WATER#Dragon Breath(Water)# +4096,5014,5,0,0,0,0,0,0,0,0,0,0 //ALL_FULL_THROTTLE#Full Throttle# //Baby Warlock 4097,1,9,0,0,0,0,0,0,0,0,0,0 //NV_BASIC#Basic Skill# 4097,142,1,0,0,0,0,0,0,0,0,0,0 //NV_FIRSTAID#First Aid# @@ -4500,6 +4568,8 @@ 4097,2230,2,0,0,0,0,0,0,0,0,0,0 //WL_RELEASE#Release# 4097,2231,1,0,0,0,0,0,0,0,0,0,0 //WL_READING_SB#Reading Spellbook# 4097,2232,5,0,0,0,0,0,0,0,0,0,0 //WL_FREEZE_SP#Freeze Spell# +4097,5012,5,2202,5,0,0,0,0,0,0,0,0 //WL_TELEKINESIS_INTENSE#Intense Telekinesis# +4097,5014,5,0,0,0,0,0,0,0,0,0,0 //ALL_FULL_THROTTLE#Full Throttle# //Baby Ranger 4098,1,9,0,0,0,0,0,0,0,0,0,0 //NV_BASIC#Basic Skill# 4098,142,1,0,0,0,0,0,0,0,0,0,0 //NV_FIRSTAID#First Aid# @@ -4554,6 +4624,8 @@ 4098,2252,1,2248,1,0,0,0,0,0,0,0,0 //RA_VERDURETRAP#Verdure Trap# 4098,2253,5,2237,1,0,0,0,0,0,0,0,0 //RA_FIRINGTRAP#Firing Trap# 4098,2254,5,2237,1,0,0,0,0,0,0,0,0 //RA_ICEBOUNDTRAP#Icebound Trap# +4098,5002,5,2234,5,0,0,0,0,0,0,0,0 //RA_UNLIMIT#Unlimit# +4098,5014,5,0,0,0,0,0,0,0,0,0,0 //ALL_FULL_THROTTLE#Full Throttle# //Baby Arch Bishop 4099,1,9,0,0,0,0,0,0,0,0,0,0 //NV_BASIC#Basic Skill# 4099,142,1,0,0,0,0,0,0,0,0,0,0 //NV_FIRSTAID#First Aid# @@ -4613,6 +4685,8 @@ 4099,2054,10,68,1,0,0,0,0,0,0,0,0 //AB_DUPLELIGHT#Duple Light# 4099,2057,5,2052,1,0,0,0,0,0,0,0,0 //AB_SILENTIUM#Silentium# 4099,2515,5,2044,1,2053,1,0,0,0,0,0,0 //AB_SECRAMENT#Secrament# +4099,5011,5,2051,2,0,0,0,0,0,0,0,0 //AB_OFFERTORIUM#Offertorium# +4099,5014,5,0,0,0,0,0,0,0,0,0,0 //ALL_FULL_THROTTLE#Full Throttle# //Baby Mechanic 4100,1,9,0,0,0,0,0,0,0,0,0,0 //NV_BASIC#Basic Skill# 4100,142,1,0,0,0,0,0,0,0,0,0,0 //NV_FIRSTAID#First Aid# @@ -4682,7 +4756,9 @@ 4100,2281,5,2277,2,0,0,0,0,0,0,0,0 //NC_SILVERSNIPER#FAW - Silver Sniper# 4100,2282,5,2277,2,0,0,0,0,0,0,0,0 //NC_MAGICDECOY#FAW - Magic Decoy# 4100,2283,1,2281,1,0,0,0,0,0,0,0,0 //NC_DISJOINT#FAW Removal# +4100,5006,5,0,0,0,0,0,0,0,0,0,0 //NC_MAGMA_ERUPTION#Magma Eruption# 4100,2535,1,41,1,0,0,0,0,0,0,0,0 //ALL_BUYING_STORE#Open Buying Store# +4100,5014,5,0,0,0,0,0,0,0,0,0,0 //ALL_FULL_THROTTLE#Full Throttle# //Baby Guillotine Cross 4101,1,9,0,0,0,0,0,0,0,0,0,0 //NV_BASIC#Basic Skill# 4101,142,1,0,0,0,0,0,0,0,0,0,0 //NV_FIRSTAID#First Aid# @@ -4728,6 +4804,8 @@ 4101,2035,5,2034,1,0,0,0,0,0,0,0,0 //GC_HALLUCINATIONWALK#Hallucination Walk# 4101,2036,5,136,10,0,0,0,0,0,0,0,0 //GC_ROLLINGCUTTER#Rolling Cutter# 4101,2037,5,2036,1,0,0,0,0,0,0,0,0 //GC_CROSSRIPPERSLASHER#Cross Ripper Slasher# +4101,5001,5,2023,5,0,0,0,0,0,0,0,0 //GC_DARKCROW#Dark Claw# +4101,5014,5,0,0,0,0,0,0,0,0,0,0 //ALL_FULL_THROTTLE#Full Throttle# //Baby Royal Guard 4102,1,9,0,0,0,0,0,0,0,0,0,0 //NV_BASIC#Basic Skill# 4102,142,1,0,0,0,0,0,0,0,0,0,0 //NV_FIRSTAID#First Aid# @@ -4782,6 +4860,8 @@ 4102,2323,5,2311,3,0,0,0,0,0,0,0,0 //LG_EARTHDRIVE#Earth Drive# 4102,2324,5,2318,3,2319,3,0,0,0,0,0,0 //LG_HESPERUSLIT#Hesperus Lit# 4102,2325,5,2315,3,2321,4,2322,5,0,0,0,0 //LG_INSPIRATION#Inspiration# +4102,5013,5,2311,5,0,0,0,0,0,0,0,0 //LG_KINGS_GRACE#King's Grace# +4102,5014,5,0,0,0,0,0,0,0,0,0,0 //ALL_FULL_THROTTLE#Full Throttle# //Baby Sorcerer 4103,1,9,0,0,0,0,0,0,0,0,0,0 //NV_BASIC#Basic Skill# 4103,142,1,0,0,0,0,0,0,0,0,0,0 //NV_FIRSTAID#First Aid# @@ -4853,6 +4933,7 @@ 4103,2466,3,2458,3,0,0,0,0,0,0,0,0 //SO_WATER_INSIGNIA#Water Insignia# 4103,2467,3,2459,3,0,0,0,0,0,0,0,0 //SO_WIND_INSIGNIA#Wind Insignia# 4103,2468,3,2460,3,0,0,0,0,0,0,0,0 //SO_EARTH_INSIGNIA#Earth Insignia# +4103,5014,5,0,0,0,0,0,0,0,0,0,0 //ALL_FULL_THROTTLE#Full Throttle# //Baby Minstrel 4104,1,9,0,0,0,0,0,0,0,0,0,0 //NV_BASIC#Basic Skill# 4104,142,1,0,0,0,0,0,0,0,0,0,0 //NV_FIRSTAID#First Aid# @@ -4909,6 +4990,8 @@ 4104,2432,5,2427,1,0,0,0,0,0,0,0,0 //WM_MELODYOFSINK#Melody Of Sink# 4104,2433,5,2431,1,0,0,0,0,0,0,0,0 //WM_BEYOND_OF_WARCRY#Warcry Of Beyond# 4104,2434,5,2429,1,2433,1,0,0,0,0,0,0 //WM_UNLIMITED_HUMMING_VOICE#Unlimited Humming Voice# +4104,5007,5,2412,1,0,0,0,0,0,0,0,0 //WM_FRIGG_SONG# +4104,5014,5,0,0,0,0,0,0,0,0,0,0 //ALL_FULL_THROTTLE#Full Throttle# //Baby Wanderer 4105,1,9,0,0,0,0,0,0,0,0,0,0 //NV_BASIC#Basic Skill# 4105,142,1,0,0,0,0,0,0,0,0,0,0 //NV_FIRSTAID#First Aid# @@ -4965,6 +5048,8 @@ 4105,2432,5,2427,1,0,0,0,0,0,0,0,0 //WM_MELODYOFSINK#Melody Of Sink# 4105,2433,5,2431,1,0,0,0,0,0,0,0,0 //WM_BEYOND_OF_WARCRY#Warcry Of Beyond# 4105,2434,5,2429,1,2433,1,0,0,0,0,0,0 //WM_UNLIMITED_HUMMING_VOICE#Unlimited Humming Voice# +4105,5007,5,2412,1,0,0,0,0,0,0,0,0 //WM_FRIGG_SONG# +4105,5014,5,0,0,0,0,0,0,0,0,0,0 //ALL_FULL_THROTTLE#Full Throttle# //Baby Sura 4106,1,9,0,0,0,0,0,0,0,0,0,0 //NV_BASIC#Basic Skill# 4106,142,1,0,0,0,0,0,0,0,0,0,0 //NV_FIRSTAID#First Aid# @@ -5025,6 +5110,8 @@ 4106,2348,5,2347,5,0,0,0,0,0,0,0,0 //SR_GENTLETOUCH_REVITALIZE#Gentle Touch - Revitalize# 4106,2517,5,2340,1,2518,3,0,0,0,0,0,0 //SR_HOWLINGOFLION#Howling Of Lion# 4106,2518,5,267,3,0,0,0,0,0,0,0,0 //SR_RIDEINLIGHTNING#Ride In Lightening# +4106,5009,5,2326,3,2329,3,2330,1,2327,1,0,0 //SR_FLASHCOMBO#Flash Combo# +4106,5014,5,0,0,0,0,0,0,0,0,0,0 //ALL_FULL_THROTTLE#Full Throttle# //Baby Genetic 4107,1,9,0,0,0,0,0,0,0,0,0,0 //NV_BASIC#Basic Skill# 4107,142,1,0,0,0,0,0,0,0,0,0,0 //NV_FIRSTAID#First Aid# @@ -5080,7 +5167,9 @@ 4107,2495,2,2497,1,0,0,0,0,0,0,0,0 //GN_MIX_COOKING#Mix Cooking# 4107,2496,2,2495,1,0,0,0,0,0,0,0,0 //GN_MAKEBOMB#Create Bomb# 4107,2497,10,0,0,0,0,0,0,0,0,0,0 //GN_S_PHARMACY#Special Pharmacy# +4107,5003,5,2497,1,0,0,0,0,0,0,0,0 //GN_ILLUSIONDOOPING#Hallucination Drug# 4107,2535,1,41,1,0,0,0,0,0,0,0,0 //ALL_BUYING_STORE#Open Buying Store# +4107,5014,5,0,0,0,0,0,0,0,0,0,0 //ALL_FULL_THROTTLE#Full Throttle# //Baby Shadow Chaser 4108,1,9,0,0,0,0,0,0,0,0,0,0 //NV_BASIC#Basic Skill# 4108,142,1,0,0,0,0,0,0,0,0,0,0 //NV_FIRSTAID#First Aid# @@ -5139,6 +5228,8 @@ 4108,2302,3,2296,3,2301,3,0,0,0,0,0,0 //SC_MAELSTROM#Maelstrom# 4108,2303,3,2300,3,0,0,0,0,0,0,0,0 //SC_BLOODYLUST#Bloody Lust# 4108,2304,3,2300,3,0,0,0,0,0,0,0,0 //SC_FEINTBOMB#Feint Bomb# +4108,5010,5,2288,2,0,0,0,0,0,0,0,0 //SC_SCAPE#Scape# +4108,5014,5,0,0,0,0,0,0,0,0,0,0 //ALL_FULL_THROTTLE#Full Throttle# //Baby Rune Knight (Dragon) 4109,1,9,0,0,0,0,0,0,0,0,0,0 //NV_BASIC#Basic Skill# 4109,142,1,0,0,0,0,0,0,0,0,0,0 //NV_FIRSTAID#First Aid# @@ -5178,6 +5269,8 @@ 4109,2009,5,2007,2,0,0,0,0,0,0,0,0 //RK_DRAGONHOWLING#Dragon Howling# 4109,2010,10,0,0,0,0,0,0,0,0,0,0 //RK_RUNEMASTERY#Rune Mastery# 4109,2020,5,57,2,0,0,0,0,0,0,0,0 //RK_PHANTOMTHRUST#Phantom Thrust# +4009,5004,10,2007,2,0,0,0,0,0,0,0,0 //RK_DRAGONBREATH_WATER#Dragon Breath(Water)# +4109,5014,5,0,0,0,0,0,0,0,0,0,0 //ALL_FULL_THROTTLE#Full Throttle# //Baby Royal Guard (Gryphon) 4110,1,9,0,0,0,0,0,0,0,0,0,0 //NV_BASIC#Basic Skill# 4110,142,1,0,0,0,0,0,0,0,0,0,0 //NV_FIRSTAID#First Aid# @@ -5232,6 +5325,8 @@ 4110,2323,5,2311,3,0,0,0,0,0,0,0,0 //LG_EARTHDRIVE#Earth Drive# 4110,2324,5,2318,3,2319,3,0,0,0,0,0,0 //LG_HESPERUSLIT#Hesperus Lit# 4110,2325,5,2315,3,2321,4,2322,5,0,0,0,0 //LG_INSPIRATION#Inspiration# +4110,5013,5,2311,5,0,0,0,0,0,0,0,0 //LG_KINGS_GRACE#King's Grace# +4110,5014,5,0,0,0,0,0,0,0,0,0,0 //ALL_FULL_THROTTLE#Full Throttle# //Baby Ranger (Warg) 4111,1,9,0,0,0,0,0,0,0,0,0,0 //NV_BASIC#Basic Skill# 4111,142,1,0,0,0,0,0,0,0,0,0,0 //NV_FIRSTAID#First Aid# @@ -5286,6 +5381,8 @@ 4111,2252,1,2248,1,0,0,0,0,0,0,0,0 //RA_VERDURETRAP#Verdure Trap# 4111,2253,5,2237,1,0,0,0,0,0,0,0,0 //RA_FIRINGTRAP#Firing Trap# 4111,2254,5,2237,1,0,0,0,0,0,0,0,0 //RA_ICEBOUNDTRAP#Icebound Trap# +4111,5002,5,2234,5,0,0,0,0,0,0,0,0 //RA_UNLIMIT#Unlimit# +4111,5014,5,0,0,0,0,0,0,0,0,0,0 //ALL_FULL_THROTTLE#Full Throttle# //Baby Mechanic (Mado) 4112,1,9,0,0,0,0,0,0,0,0,0,0 //NV_BASIC#Basic Skill# 4112,142,1,0,0,0,0,0,0,0,0,0,0 //NV_FIRSTAID#First Aid# @@ -5355,7 +5452,9 @@ 4112,2281,5,2277,2,0,0,0,0,0,0,0,0 //NC_SILVERSNIPER#FAW - Silver Sniper# 4112,2282,5,2277,2,0,0,0,0,0,0,0,0 //NC_MAGICDECOY#FAW - Magic Decoy# 4112,2283,1,2281,1,0,0,0,0,0,0,0,0 //NC_DISJOINT#FAW Removal# +4112,5006,5,0,0,0,0,0,0,0,0,0,0 //NC_MAGMA_ERUPTION#Magma Eruption# 4112,2535,1,41,1,0,0,0,0,0,0,0,0 //ALL_BUYING_STORE#Open Buying Store# +4112,5014,5,0,0,0,0,0,0,0,0,0,0 //ALL_FULL_THROTTLE#Full Throttle# //Super Novice (Expanded) 4190,1,9,0,0,0,0,0,0,0,0,0,0 //NV_BASIC#Basic Skill# 4190,142,1,0,0,0,0,0,0,0,0,0,0 //NV_FIRSTAID#First Aid# diff --git a/db/pre-re/skill_unit_db.txt b/db/pre-re/skill_unit_db.txt index 388bfd341..f02c3c231 100644 --- a/db/pre-re/skill_unit_db.txt +++ b/db/pre-re/skill_unit_db.txt @@ -103,8 +103,8 @@ 2032,0xe1, , 2, 0,1000,enemy, 0x018 //GC_POISONSMOKE -2214,0x86, , 0, 5, 100,enemy, 0x080 //WL_CHAINLIGHTNING -2216,0xcb, , -1, 0, 150,enemy, 0x018 //WL_EARTHSTRAIN +2213,0x86, , 0, 8, 100,enemy, 0x018 //WL_COMET +2216,0xcb, , -1, 0, 100,enemy, 0x018 //WL_EARTHSTRAIN 2238,0xd8, , 0, 1,1000,enemy, 0x006 //RA_ELECTRICSHOCKER 2239,0xd9, , 0, 1,1000,enemy, 0x006 //RA_CLUSTERBOMB @@ -156,7 +156,10 @@ 3008,0x86, , 0, 2, 100,enemy, 0x018 //KO_MUCHANAGE 3009,0x86, , 0, 3, 500,enemy, 0x018 //KO_HUUMARANKA 3020,0xf8, , 0, 3, 100,all, 0x018 //KO_ZENKAI -3010,0xfc, , 0, 1,1000,enemy, 0x020 //KO_MAKIBISHI +3010,0xfc, , 0, 0,5000,enemy, 0x018 //KO_MAKIBISHI + +5006,0x101, , 0, 3,2000,enemy, 0x018 //NC_MAGMA_ERUPTION +5010,0xfe, , 0, 2, -1,enemy, 0x000 //SC_SCAPE 8020,0xf5, , 0, 3,2300:2100:1900:1700:1500,enemy, 0x018 //MH_POISON_MIST 8033,0x7e, , 0, 0, -1,all, 0x003 //MH_STEINWAND @@ -172,7 +175,7 @@ 8403,0xed, , -1, 1,1000,enemy, 0x018 //EL_FIRE_MANTLE 8406,0xee, , 0, 1, -1,friend,0x018 //EL_WATER_BARRIER -8409,0xef, , 0, 1, -1,friend,0x018 //EL_ZEPHYR +8409,0xef, , 0, 1,1000,friend,0x018 //EL_ZEPHYR 8412,0xf0, , 0, 1, -1,friend,0x018 //EL_POWER_OF_GAIA 10006,0xc1, , 2, 0, -1,sameguild, 0x040 //GD_LEADERSHIP diff --git a/db/re/item_combo_db.txt b/db/re/item_combo_db.txt index 26b955d9b..71e544107 100644 --- a/db/re/item_combo_db.txt +++ b/db/re/item_combo_db.txt @@ -115,7 +115,7 @@ 2472:2570:15030:16013,{ bonus2 bAddRace,RC_Undead,15; bonus2 bMagicAddRace,RC_Undead,15; bonus2 bSkillAtk,"AB_ADORAMUS",100; } 2472:2570:15030:16018,{ bonus2 bAddRace,RC_Undead,30; bonus2 bMagicAddRace,RC_Undead,30; bonus2 bSkillAtk,"AB_ADORAMUS",200; bonus bVariableCastrate,-50; } 2475:2574:2883:15036,{ bonus bMaxHPRate,14; bonus2 bSkillAtk,"RK_HUNDREDSPEAR",50; skill "CR_AUTOGUARD",1; } -2476:2575:2884:15037,{ bonus2 bAddRace,RC_NonBoss,10; bonus2 bAddRace,RC_Boss,10; bonus2 bSkillAtk,"RK_SONICWAVE",100; bonus2 bSkillAtk,"RK_WINDCUTTER",100; autobonus "{ sc_start SC_CONCENTRATION,10000,getskilllv(\"LK_CONCENTRATION\")?getskilllv(\"LK_CONCENTRATION\"):1; bonus bAspd,2; }",1,10000,BF_WEAPON,"{}"; } +2476:2575:2884:15037,{ bonus2 bAddRace,RC_NonBoss,10; bonus2 bAddRace,RC_Boss,10; bonus2 bSkillAtk,"RK_SONICWAVE",100; bonus2 bSkillAtk,"RK_WINDCUTTER",100; autobonus "{ sc_start SC_LKCONCENTRATION,10000,getskilllv(\"LK_CONCENTRATION\")?getskilllv(\"LK_CONCENTRATION\"):1; bonus bAspd,2; }",1,10000,BF_WEAPON,"{}"; } 2477:2577:2886:15038,{ bonus bCritical,15; bonus bFlee,10; bonus bCritAtkRate,40; bonus2 bSkillAtk,"GC_CROSSIMPACT",20; } 2478:2578:2887:15039,{ bonus2 bAddRace,RC_NonBoss,10; bonus2 bAddRace,RC_Boss,10; bonus bMatk,10; if(readparam(bStr)>119) { bonus bBaseAtk,30; } bonus3 bAutoSpell,"ASC_BREAKER",getskilllv("ASC_BREAKER"),10; bonus bCritical,-20; } 2479:2580:2890:15042,{ bonus bAspd,2; bonus bLongAtkRate,30; bonus3 bAutoSpell,"AC_DOUBLE",3,10; bonus2 bSkillAtk,"RA_ARROWSTORM",50; } diff --git a/db/re/item_db.txt b/db/re/item_db.txt index 5dccc5442..52b872afc 100644 --- a/db/re/item_db.txt +++ b/db/re/item_db.txt @@ -31,8 +31,8 @@ 521,Leaflet_Of_Aloe,Aloe Leaflet,0,360,,20,,,,,0xFFFFFFFF,7,2,,,,,,{ itemheal rand(325,405),0; },{},{} 522,Fruit_Of_Mastela,Mastela Fruit,0,8500,,30,,,,,0xFFFFFFFF,7,2,,,,,,{ itemheal rand(400,600),0; },{},{} 523,Holy_Water,Holy Water,0,20,,30,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_end SC_Curse; },{},{} -525,Panacea,Panacea,0,500,,100,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_end SC_Poison; sc_end SC_Silence; sc_end SC_Blind; sc_end SC_Confusion; sc_end SC_Curse; sc_end SC_Hallucination; },{},{} -526,Royal_Jelly,Royal Jelly,0,7000,,150,,,,,0xFFFFFFFF,7,2,,,,,,{ itemheal rand(325,405),rand(40,60); sc_end SC_Poison; sc_end SC_Silence; sc_end SC_Blind; sc_end SC_Confusion; sc_end SC_Curse; sc_end SC_Hallucination; },{},{} +525,Panacea,Panacea,0,500,,100,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_end SC_Poison; sc_end SC_Silence; sc_end SC_Blind; sc_end SC_Confusion; sc_end SC_Curse; sc_end SC_ILLUSION; },{},{} +526,Royal_Jelly,Royal Jelly,0,7000,,150,,,,,0xFFFFFFFF,7,2,,,,,,{ itemheal rand(325,405),rand(40,60); sc_end SC_Poison; sc_end SC_Silence; sc_end SC_Blind; sc_end SC_Confusion; sc_end SC_Curse; sc_end SC_ILLUSION; },{},{} 528,Monster's_Feed,Monster's Feed,0,60,,150,,,,,0xFFFFFFFF,7,2,,,,,,{ itemheal rand(72,108),0; },{},{} 529,Candy,Candy,0,10,,30,,,,,0xFFFFFFFF,7,2,,,,,,{ itemheal rand(45,65),0; },{},{} 530,Candy_Striper,Candy Cane,0,20,,40,,,,,0xFFFFFFFF,7,2,,,,,,{ itemheal rand(105,145),0; },{},{} @@ -71,14 +71,14 @@ 563,Pizza_01,Doublecrust Swiss Fondue,0,1200,,150,,,,,0xFFFFFFFF,7,2,,,,,,{ itemheal rand(375,445),0; },{},{} 564,Rice_Ball,Rice Ball,0,1,,30,,,,,0xFFFFFFFF,7,2,,,,,,{ itemheal 200,0; },{},{} 565,Vita500_Bottle,Vita500,0,580,,100,,,,,0xFFFFFFFF,7,2,,,,,,{ itemheal rand(142,274),0; },{},{} -566,Tomyumkung,Tom Yum Goong,0,10000,,150,,,,,0xFFFFFFFF,7,2,,,,,,{ itemheal rand(244,350),rand(10,30); sc_end SC_Poison; sc_end SC_Silence; sc_end SC_Blind; sc_end SC_Confusion; sc_end SC_Curse; sc_end SC_Hallucination; },{},{} +566,Tomyumkung,Tom Yum Goong,0,10000,,150,,,,,0xFFFFFFFF,7,2,,,,,,{ itemheal rand(244,350),rand(10,30); sc_end SC_Poison; sc_end SC_Silence; sc_end SC_Blind; sc_end SC_Confusion; sc_end SC_Curse; sc_end SC_ILLUSION; },{},{} 567,Prawn,Shrimp,0,500,,40,,,,,0xFFFFFFFF,7,2,,,,,,{ itemheal rand(117,192),0; },{},{} 568,Lemon,Lemon,0,60,,40,,,,,0xFFFFFFFF,7,2,,,,,,{ itemheal 0,rand(10,20); },{},{} 569,Novice_Potion,Novice Potion,0,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ itemheal rand(44,66),0; },{},{} 570,Lucky_Candy,Lucky Candy,0,10,,30,,,,,0xFFFFFFFF,7,2,,,,,,{ itemheal rand(45,65),0; },{},{} 571,Lucky_Candy_Cane,Lucky Candy Cane,0,20,,40,,,,,0xFFFFFFFF,7,2,,,,,,{ itemheal rand(105,145),0; },{},{} 572,Lucky_Cookie,Lucky Cookie,0,1000,,30,,,,,0xFFFFFFFF,7,2,,,,,,{ itemheal rand(160,200),0; },{},{} -573,Chocolate_Drink,Chocolate Drink,0,7000,,150,,,,,0xFFFFFFFF,7,2,,,,,,{ itemheal rand(330,410),rand(45,65); sc_end SC_Poison; sc_end SC_Silence; sc_end SC_Blind; sc_end SC_Confusion; sc_end SC_Curse; sc_end SC_Hallucination; },{},{} +573,Chocolate_Drink,Chocolate Drink,0,7000,,150,,,,,0xFFFFFFFF,7,2,,,,,,{ itemheal rand(330,410),rand(45,65); sc_end SC_Poison; sc_end SC_Silence; sc_end SC_Blind; sc_end SC_Confusion; sc_end SC_Curse; sc_end SC_ILLUSION; },{},{} 574,Egg,Egg,0,20,,30,,,,,0xFFFFFFFF,7,2,,,,,,{ itemheal rand(33,42),0; },{},{} 575,Piece_Of_Cake_,2nd Anniversary Cake,0,10,,100,,,,,0xFFFFFFFF,7,2,,,,,,{ itemheal rand(270,330),0; },{},{} 576,Prickly_Fruit,Prickly Fruit,0,540,,60,,,,,0xFFFFFFFF,7,2,,,,,,{ itemheal rand(150,300),rand(20,30); },{},{} @@ -88,7 +88,7 @@ 580,Bread,Bread,0,150,,20,,,,,0xFFFFFFFF,7,2,,,,,,{ itemheal rand(50,90),0; },{},{} 581,Mushroom,Edible Mushroom,0,40,,20,,,,,0xFFFFFFFF,7,2,,,,,,{ itemheal rand(20,30),0; },{},{} 582,Orange,Orange,0,300,,20,,,,,0xFFFFFFFF,7,2,,,,,,{ itemheal rand(10,20),rand(10,20); },{},{} -583,KETUPAT_,Ketupat Sayur,0,7000,,150,,,,,0xFFFFFFFF,7,2,,,,,,{ itemheal rand(325,405),rand(40,60); sc_end SC_Poison; sc_end SC_Silence; sc_end SC_Blind; sc_end SC_Confusion; sc_end SC_Curse; sc_end SC_Hallucination; },{},{} +583,KETUPAT_,Ketupat Sayur,0,7000,,150,,,,,0xFFFFFFFF,7,2,,,,,,{ itemheal rand(325,405),rand(40,60); sc_end SC_Poison; sc_end SC_Silence; sc_end SC_Blind; sc_end SC_Confusion; sc_end SC_Curse; sc_end SC_ILLUSION; },{},{} 584,Fish_Ball_Soup,Fish Cake Soup,0,100,,60,,,,,0xFFFFFFFF,7,2,,,,,,{ itemheal rand(40,70),0; },{},{} 585,Wurst,Brusti,0,2,,40,,,,,0xFFFFFFFF,7,2,,,,,,{ itemheal rand(15,20),0; },{},{} 586,Mother's_Cake,Mother's Cake,0,20,,100,,,,,0xFFFFFFFF,7,2,,,,,,{ itemheal rand(325,405),0; },{},{} @@ -96,11 +96,11 @@ 588,Spaghetti,Spaghetti,0,100,,100,,,,,0xFFFFFFFF,7,2,,,,,,{ itemheal rand(40,70),0; },{},{} 589,Pizza_02,Pizza,0,1200,,150,,,,,0xFFFFFFFF,7,2,,,,,,{ itemheal rand(375,445),0; },{},{} 590,Brezel_,Pretzel,0,2,,20,,,,,0xFFFFFFFF,7,2,,,,,,{ itemheal rand(50,90),0; },{},{} -591,Caviar_Pancake,Caviar Pancake,0,0,,150,,,,,0xFFFFFFFF,7,2,,,,,,{ itemheal rand(325,405),rand(40,60); sc_end SC_Poison; sc_end SC_Silence; sc_end SC_Blind; sc_end SC_Confusion; sc_end SC_Curse; sc_end SC_Hallucination; },{},{} -592,Jam_Pancake,Jam Pancake,0,0,,150,,,,,0xFFFFFFFF,7,2,,,,,,{ itemheal rand(325,405),rand(40,60); sc_end SC_Poison; sc_end SC_Silence; sc_end SC_Blind; sc_end SC_Confusion; sc_end SC_Curse; sc_end SC_Hallucination; },{},{} -593,Honey_Pancake,Honey Pancake,0,0,,150,,,,,0xFFFFFFFF,7,2,,,,,,{ itemheal rand(325,405),rand(40,60); sc_end SC_Poison; sc_end SC_Silence; sc_end SC_Blind; sc_end SC_Confusion; sc_end SC_Curse; sc_end SC_Hallucination; },{},{} -594,Sour_Cream_Pancake,Sour-Cream Pancake,0,0,,150,,,,,0xFFFFFFFF,7,2,,,,,,{ itemheal rand(325,405),rand(40,60); sc_end SC_Poison; sc_end SC_Silence; sc_end SC_Blind; sc_end SC_Confusion; sc_end SC_Curse; sc_end SC_Hallucination; },{},{} -595,Mushroom_Pancake,Mushroom Pancake,0,0,,150,,,,,0xFFFFFFFF,7,2,,,,,,{ itemheal rand(325,405),rand(40,60); sc_end SC_Poison; sc_end SC_Silence; sc_end SC_Blind; sc_end SC_Confusion; sc_end SC_Curse; sc_end SC_Hallucination; },{},{} +591,Caviar_Pancake,Caviar Pancake,0,0,,150,,,,,0xFFFFFFFF,7,2,,,,,,{ itemheal rand(325,405),rand(40,60); sc_end SC_Poison; sc_end SC_Silence; sc_end SC_Blind; sc_end SC_Confusion; sc_end SC_Curse; sc_end SC_ILLUSION; },{},{} +592,Jam_Pancake,Jam Pancake,0,0,,150,,,,,0xFFFFFFFF,7,2,,,,,,{ itemheal rand(325,405),rand(40,60); sc_end SC_Poison; sc_end SC_Silence; sc_end SC_Blind; sc_end SC_Confusion; sc_end SC_Curse; sc_end SC_ILLUSION; },{},{} +593,Honey_Pancake,Honey Pancake,0,0,,150,,,,,0xFFFFFFFF,7,2,,,,,,{ itemheal rand(325,405),rand(40,60); sc_end SC_Poison; sc_end SC_Silence; sc_end SC_Blind; sc_end SC_Confusion; sc_end SC_Curse; sc_end SC_ILLUSION; },{},{} +594,Sour_Cream_Pancake,Sour-Cream Pancake,0,0,,150,,,,,0xFFFFFFFF,7,2,,,,,,{ itemheal rand(325,405),rand(40,60); sc_end SC_Poison; sc_end SC_Silence; sc_end SC_Blind; sc_end SC_Confusion; sc_end SC_Curse; sc_end SC_ILLUSION; },{},{} +595,Mushroom_Pancake,Mushroom Pancake,0,0,,150,,,,,0xFFFFFFFF,7,2,,,,,,{ itemheal rand(325,405),rand(40,60); sc_end SC_Poison; sc_end SC_Silence; sc_end SC_Blind; sc_end SC_Confusion; sc_end SC_Curse; sc_end SC_ILLUSION; },{},{} 596,Cute_Strawberry_Choco,Cute Strawberry-Choco,0,20,,100,,,,,0xFFFFFFFF,7,2,,,,,,{ itemheal 0,rand(1,100); },{},{} 597,Lovely_Choco_Tart,Lovely Choco-Tart,0,20,,100,,,,,0xFFFFFFFF,7,2,,,,,,{ itemheal rand(10,400),0; },{},{} 598,Light_Red_Pot,Light Red Potion,0,50,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ itemheal rand(45,65),0; },{},{} @@ -153,15 +153,15 @@ 644,Gift_Box,Gift Box,2,1000,,200,,,,,0xFFFFFFFF,7,2,,,,,,{ getrandgroupitem(IG_GiftBox),1; },{},{} //ASPD in RE they give a fixed +4/+6/+9 ASPD -645,Center_Potion,Concentration Potion,2,800,,100,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_ASPDPOTION0,1800000,4; },{},{} -656,Awakening_Potion,Awakening Potion,2,1500,,150,,,,,0xFFF7FEEF,7,2,,,40,,,{ sc_start SC_ASPDPOTION1,1800000,6; },{},{} -657,Berserk_Potion,Berserk Potion,2,3000,,200,,,,,0x01E646A6,7,2,,,85,,,{ sc_start SC_ASPDPOTION2,1800000,9; },{},{} +645,Center_Potion,Concentration Potion,2,800,,100,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_ATTHASTE_POTION1,1800000,4; },{},{} +656,Awakening_Potion,Awakening Potion,2,1500,,150,,,,,0xFFF7FEEF,7,2,,,40,,,{ sc_start SC_ATTHASTE_POTION2,1800000,6; },{},{} +657,Berserk_Potion,Berserk Potion,2,3000,,200,,,,,0x01E646A6,7,2,,,85,,,{ sc_start SC_ATTHASTE_POTION3,1800000,9; },{},{} 658,Union_Of_Tribe,Union of Tribe,2,2,,500,,,,,0xFFFFFFFF,7,2,,,,,,{ guildgetexp rand(600000,1200000); },{},{} 659,Heart_Of_Her,Her Heart,2,500,,50,,,,,0xFFFFFFFF,7,2,,,,,,{ pet 1188; },{},{} 660,Prohibition_Red_Candle,Forbidden Red Candle,2,20000,,50,,,,,0xFFFFFFFF,7,2,,,,,,{ pet 1200; },{},{} 661,Sway_Apron,Soft Apron,2,20000,,50,,,,,0xFFFFFFFF,7,2,,,,,,{ pet 1275; },{},{} -662,Inspector_Certificate,Authoritative Badge,2,1450,,30,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_SpeedUp0,180000,0; },{},{} +662,Inspector_Certificate,Authoritative Badge,2,1450,,30,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_MOVHASTE_HORSE,180000,0; },{},{} 663,Korea_Rice_Cake,Korean Rice Cake,0,1,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ percentheal 10,0; },{},{} 664,Gift_Box_1,Gift Box,2,1000,,200,,,,,0xFFFFFFFF,7,2,,,,,,{ getrandgroupitem(IG_GiftBox_1),1; },{},{} 665,Gift_Box_2,Gift Box,2,1000,,200,,,,,0xFFFFFFFF,7,2,,,,,,{ getrandgroupitem(IG_GiftBox_2),1; },{},{} @@ -177,13 +177,13 @@ 675,Silver_Coin,Silver Coin,3,5000,,40,,,,,0xFFFFFFFF,7,2,,,,,,{},{},{} 676,Silver_Coin_Moneybag,Bag of Silver Coins,3,50000,,400,,,,,0xFFFFFFFF,7,2,,,,,,{},{},{} 677,White_Gold_Coin,Platinum Coin,3,2000,,40,,,,,0xFFFFFFFF,7,2,,,,,,{},{},{} -678,Poison_Bottle,Poison Bottle,2,5000,,100,,,,,0xFFFFFFFF,7,2,,,,,,{ if(Class == Job_Assassin_Cross || Class == Job_Guillotine_Cross || Class == Job_Guillotine_Cross_T) { sc_start SC_DPoison,60000,0; sc_start SC_ASPDPOTION3,60000,9; } else percentheal -100,-100; },{},{} +678,Poison_Bottle,Poison Bottle,2,5000,,100,,,,,0xFFFFFFFF,7,2,,,,,,{ if(Class == Job_Assassin_Cross || Class == Job_Guillotine_Cross || Class == Job_Guillotine_Cross_T) { sc_start SC_DPoison,60000,0; sc_start SC_ATTHASTE_INFINITY,60000,9; } else percentheal -100,-100; },{},{} 679,Gold_Pill,Pilule,2,5000,,300,,,,,0xFFFFFFFF,7,2,,,,,,{ if(rand(1000)<100) sc_start SC_DPoison,10000,0; sc_start SC_Poison,50000,0; },{},{} 680,Magical_Carnation,Magic Carnation,0,0,,1000,,,,,0xFFFFFFFF,7,2,,,,,,{ percentheal 0,20; },{},{} 681,Memory_Of_Wedding,Sweet Memory of Marriage,2,50000,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ if (getpartnerid()) sc_start SC_WEDDING,600000,0; },{},{} -682,Realgar_Wine,Distilled Fighting Spirit,2,0,,100,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_ATKPOTION,60000,30; },{},{} -683,Exorcize_Herb,Herb of Incantation,2,0,,50,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_MATKPOTION,60000,30; },{},{} -684,Durian,Durian,2,15000,,300,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_ATKPOTION,60000,10; sc_start SC_MATKPOTION,60000,10; },{},{} +682,Realgar_Wine,Distilled Fighting Spirit,2,0,,100,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_PLUSATTACKPOWER,60000,30; },{},{} +683,Exorcize_Herb,Herb of Incantation,2,0,,50,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_PLUSMAGICPOWER,60000,30; },{},{} +684,Durian,Durian,2,15000,,300,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_PLUSATTACKPOWER,60000,10; sc_start SC_PLUSMAGICPOWER,60000,10; },{},{} 685,RAMADAN,Ramadan,0,5000,,300,,,,,0xFFFFFFFF,7,2,,,,,,{ percentheal 100,50; },{},{} 686,Earth_Scroll_1_3,Level 3 Earth Spike,11,1000,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ itemskill "WZ_EARTHSPIKE",3; },{},{} 687,Earth_Scroll_1_5,Level 5 Earth Spike,11,2000,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ itemskill "WZ_EARTHSPIKE",5; },{},{} @@ -1638,7 +1638,7 @@ 2603,Necklace,Necklace,5,30000,,100,,0,,0,0xFFFFFFFE,7,2,136,,20,0,0,{ bonus bVit,2; },{},{} 2604,Glove,Glove,5,30000,,100,,0,,0,0xFFFFFFFE,7,2,136,,20,0,0,{ bonus bDex,2; },{},{} 2605,Brooch,Brooch,5,30000,,100,,0,,0,0xFFFFFFFE,7,2,136,,20,0,0,{ bonus bAgi,2; },{},{} -2607,Clip,Clip,5,30000,,100,,0,,1,0xFFFFFFFF,7,2,136,,0,0,0,{ bonus bMaxSP,10; },{},{} +2607,Clip,Clip,5,30000,,100,,0,,1,0xFFFFFFFF,7,2,136,,0,0,0,{ bonus bMaxSP,10; bonus bMaxHP,2; },{},{} 2608,Rosary,Rosary,5,15000,,100,,0,,0,0xFFFFFFFE,7,2,136,,20,0,0,{ bonus bMdef,5; bonus bLuk,2; },{},{} 2609,Skul_Ring,Skull Ring,5,10000,,100,,0,,0,0xFFFFFFFF,7,2,136,,0,0,0,{},{},{} 2610,Gold_Ring,Gold Ring,5,30000,,100,,0,,0,0xFFFFFFFF,7,2,136,,0,0,0,{},{},{} @@ -5312,7 +5312,7 @@ 12013,Shadow_Arrow_Container,Shadow Arrow Quiver,2,2,,250,,,,,0xFFFFFFFF,7,2,,,,,,{ getitem 1767,500; },{},{} 12014,Imma_Arrow_Container,Immaterial Arrow Quiver,2,2,,250,,,,,0xFFFFFFFF,7,2,,,,,,{ getitem 1757,500; },{},{} 12015,Rusty_Arrow_Container,Rusty Arrow Quiver,2,2,,250,,,,,0xFFFFFFFF,7,2,,,,,,{ getitem 1762,500; },{},{} -12016,Speed_Up_Potion,Speed Potion,2,2,,100,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_SpeedUp1,5000,0; },{},{} +12016,Speed_Up_Potion,Speed Potion,2,2,,100,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_MOVHASTE_INFINITY,5000,0; },{},{} 12017,Slow_Down_Potion,Slow Potion,2,2,,100,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_SlowDown,5000,0; },{},{} 12018,Fire_Cracker,Firecracker,2,2,,20,,,,,0xFFFFFFFF,7,2,,,,,,{ end; },{},{} 12019,Holy_Egg,Holy Egg,11,2,,150,,,,,0xFFFFFFFF,7,2,,,,,,{ itemskill "ALL_RESURRECTION",2; },{},{} @@ -5324,10 +5324,10 @@ 12025,Egg_Boy,Dano Festival Egg,2,1000,,200,,,,,0xFFFFFFFF,7,2,,,,,,{ getrandgroupitem(IG_EggBoy),1; },{},{} 12026,Egg_Girl,Dano Festival Egg,2,1000,,200,,,,,0xFFFFFFFF,7,2,,,,,,{ getrandgroupitem(IG_EggGirl),1; },{},{} 12027,Giggling_Box,Giggling Box,2,1000,,200,,,,,0xFFFFFFFF,7,2,,,,,,{ percentheal 9,0; if(rand(1000)<300) sc_start SC_Curse,30000,0; },{},{} -12028,Box_Of_Thunder,Box of Thunder,2,1000,,200,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_SpeedUp0,20000,0; },{},{} +12028,Box_Of_Thunder,Box of Thunder,2,1000,,200,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_MOVHASTE_HORSE,20000,0; },{},{} 12029,Gloomy_Box,Box of Gloom,11,1000,,200,,,,,0xFFFFFFFF,7,2,,,,,,{ itemskill "AC_CONCENTRATION",1; },{},{} -12030,Box_Of_Grudge,Box of Resentment,2,1000,,200,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_ATKPOTION,60000,20; },{},{} -12031,Sleepy_Box,Box of Drowsiness,2,1000,,200,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_MATKPOTION,60000,20; },{},{} +12030,Box_Of_Grudge,Box of Resentment,2,1000,,200,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_PLUSATTACKPOWER,60000,20; },{},{} +12031,Sleepy_Box,Box of Drowsiness,2,1000,,200,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_PLUSMAGICPOWER,60000,20; },{},{} 12032,Box_Of_Storm,Box of Storms,11,1000,,200,,,,,0xFFFFFFFF,7,2,,,,,,{ itemskill "ITEM_ENCHANTARMS",2; },{},{} 12033,Box_Of_Sunlight,Box of Sunlight,2,1000,,200,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_Intravision,30000,0; },{},{} 12034,Painting_Box,Box of Panting,2,1000,,200,,,,,0xFFFFFFFF,7,2,,,,,,{ percentheal 0,9; if(rand(1000)<300) sc_start SC_Silence,30000,0; },{},{} @@ -5337,66 +5337,66 @@ 12038,Lotto_Box04,Lotto Box 04,2,0,,20,,,,,0xFFFFFFFF,7,2,,,,,,{ getrandgroupitem(IG_LottoBox),1; },{},{} 12039,Lotto_Box05,Lotto Box 05,2,0,,20,,,,,0xFFFFFFFF,7,2,,,,,,{ getitem rand(7542,7546),1; },{},{} 12040,Stone_Of_Intelligence_,Stone of Sage,2,100000,,300,,,,,0xFFFFFFFF,7,2,,,,,,{ homevolution; },{},{} -12041,Str_Dish01,Fried Grasshopper Legs,0,2000,,60,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_STRFOOD,1200000,1; percentheal 5,0; },{},{} -12042,Str_Dish02,Seasoned Sticky Webfoot,0,4000,,500,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_STRFOOD,1200000,2; percentheal 5,0; },{},{} -12043,Str_Dish03,Bomber Steak,0,6000,,500,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_STRFOOD,1200000,3; percentheal 5,0; },{},{} -12044,Str_Dish04,Herb Marinade Beef,0,8000,,500,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_STRFOOD,1200000,4; percentheal 5,0; },{},{} -12045,Str_Dish05,Lutie Lady's Pancake,0,10000,,500,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_STRFOOD,1200000,5; percentheal 10,0; },{},{} -12046,Int_Dish01,Grape Juice Herbal Tea,0,2000,,100,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_INTFOOD,1200000,1; percentheal 0,5; },{},{} -12047,Int_Dish02,Autumn Red Tea,0,4000,,500,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_INTFOOD,1200000,2; percentheal 0,5; },{},{} -12048,Int_Dish03,Honey Herbal Tea,0,6000,,500,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_INTFOOD,1200000,3; percentheal 0,5; },{},{} -12049,Int_Dish04,Morroc Fruit Wine,0,8000,,300,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_INTFOOD,1200000,4; percentheal 0,5; },{},{} -12050,Int_Dish05,Mastela Fruit Wine,0,10000,,400,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_INTFOOD,1200000,5; percentheal 0,10; },{},{} -12051,Vit_Dish01,Steamed Crab Nippers,0,2000,,100,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_VITFOOD,1200000,1; percentheal 5,0; },{},{} -12052,Vit_Dish02,Assorted Seafood,0,4000,,200,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_VITFOOD,1200000,2; percentheal 5,0; },{},{} -12053,Vit_Dish03,Clam Soup,0,6000,,300,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_VITFOOD,1200000,3; percentheal 5,0; },{},{} -12054,Vit_Dish04,Seasoned Jellyfish,0,8000,,500,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_VITFOOD,1200000,4; percentheal 5,0; },{},{} -12055,Vit_Dish05,Spicy Fried Bao,0,10000,,800,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_VITFOOD,1200000,5; percentheal 10,0; },{},{} -12056,Agi_Dish01,Frog Egg Squid Ink Soup,0,2000,,100,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_AGIFOOD,1200000,1; percentheal 3,1; },{},{} -12057,Agi_Dish02,Smooth Noodle,0,4000,,100,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_AGIFOOD,1200000,2; percentheal 3,1; },{},{} -12058,Agi_Dish03,Tentacle Cheese Gratin,0,6000,,500,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_AGIFOOD,1200000,3; percentheal 3,1; },{},{} -12059,Agi_Dish04,Lutie Cold Noodle,0,8000,,400,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_AGIFOOD,1200000,4; percentheal 3,1; },{},{} -12060,Agi_Dish05,Steamed Bat Wing in Pumpkin,0,10000,,500,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_AGIFOOD,1200000,5; percentheal 6,2; },{},{} -12061,Dex_Dish01,Honey Grape Juice,0,2000,,100,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_DEXFOOD,1200000,1; percentheal 2,2; },{},{} -12062,Dex_Dish02,Chocolate Mousse Cake,0,4000,,200,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_DEXFOOD,1200000,2; percentheal 2,2; },{},{} -12063,Dex_Dish03,Fruit Mix,0,6000,,200,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_DEXFOOD,1200000,3; percentheal 2,2; },{},{} -12064,Dex_Dish04,Cream Sandwich,0,8000,,500,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_DEXFOOD,1200000,4; percentheal 2,2; },{},{} -12065,Dex_Dish05,Green Salad,0,10000,,200,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_DEXFOOD,1200000,5; percentheal 5,5; },{},{} -12066,Luk_Dish01,Fried Monkey Tails,0,2000,,60,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_LUKFOOD,1200000,1; percentheal 3,2; },{},{} -12067,Luk_Dish02,Mixed Juice,0,4000,,200,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_LUKFOOD,1200000,2; percentheal 3,2; },{},{} -12068,Luk_Dish03,Fried Sweet Potato,0,6000,,500,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_LUKFOOD,1200000,3; percentheal 4,2; },{},{} -12069,Luk_Dish04,Steamed Ancient Lips,0,8000,,500,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_LUKFOOD,1200000,4; percentheal 4,2; },{},{} -12070,Luk_Dish05,Fried Scorpion Tails,0,10000,,400,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_LUKFOOD,1200000,5; percentheal 5,2; },{},{} -12071,Str_Dish06,Shiny Marinade Beef,0,20000,,800,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_STRFOOD,1200000,6; percentheal 10,2; },{},{} -12072,Str_Dish07,Whole Roast,0,40000,,1000,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_STRFOOD,1200000,7; percentheal 10,4; },{},{} -12073,Str_Dish08,Bearfoot Special,0,60000,,500,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_STRFOOD,1200000,8; percentheal 15,6; },{},{} -12074,Str_Dish09,Tendon Satay,0,80000,,1000,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_STRFOOD,1200000,9; percentheal 15,8; },{},{} -12075,Str_Dish10,Steamed Tongue,0,100000,,1000,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_STRFOOD,1200000,10; percentheal 20,20; },{},{} -12076,Int_Dish06,Red Mushroom Wine,0,20000,,300,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_INTFOOD,1200000,6; percentheal 2,10; },{},{} -12077,Int_Dish07,Special Royal Jelly Herbal Tea,0,40000,,800,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_INTFOOD,1200000,7; percentheal 4,10; },{},{} -12078,Int_Dish08,Royal Family Tea,0,60000,,1000,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_INTFOOD,1200000,8; percentheal 6,10; },{},{} -12079,Int_Dish09,Tristan XII,0,80000,,1000,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_INTFOOD,1200000,9; percentheal 8,15; },{},{} -12080,Int_Dish10,Dragon Breath Cocktail,0,100000,,1000,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_INTFOOD,1200000,10; percentheal 10,20; },{},{} -12081,Vit_Dish06,Awfully Bitter Bracer,0,20000,,500,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_VITFOOD,1200000,6; percentheal 13,0; },{},{} -12082,Vit_Dish07,Sumptuous Feast,0,40000,,400,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_VITFOOD,1200000,7; percentheal 16,0; },{},{} -12083,Vit_Dish08,Giant Burito,0,60000,,1000,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_VITFOOD,1200000,8; percentheal 19,0; },{},{} -12084,Vit_Dish09,Ascending Dragon Soup,0,80000,,1000,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_VITFOOD,1200000,9; percentheal 22,0; },{},{} -12085,Vit_Dish10,Immortal Stew,0,100000,,1000,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_VITFOOD,1200000,10; percentheal 25,0; },{},{} -12086,Agi_Dish06,Chile Shrimp Gratin,0,20000,,800,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_AGIFOOD,1200000,6; percentheal 7,2; },{},{} -12087,Agi_Dish07,Steamed Alligator with Vegetable,0,40000,,800,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_AGIFOOD,1200000,7; percentheal 8,2; },{},{} -12088,Agi_Dish08,Incredibly Spicy Curry,0,60000,,1000,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_AGIFOOD,1200000,8; percentheal 9,2; },{},{} -12089,Agi_Dish09,Special Meat Stew,0,80000,,1000,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_AGIFOOD,1200000,9; percentheal 10,2; },{},{} -12090,Agi_Dish10,Steamed Desert Scorpions,0,100000,,1000,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_AGIFOOD,1200000,10; percentheal 15,5; },{},{} -12091,Dex_Dish06,Peach Cake,0,20000,,800,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_DEXFOOD,1200000,6; percentheal 5,6; },{},{} -12092,Dex_Dish07,Soul Haunted Bread,0,40000,,800,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_DEXFOOD,1200000,7; percentheal 5,7; },{},{} -12093,Dex_Dish08,Special Toast,0,60000,,1000,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_DEXFOOD,1200000,8; percentheal 5,8; },{},{} -12094,Dex_Dish09,Heavenly Fruit Juice,0,80000,,500,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_DEXFOOD,1200000,9; percentheal 5,9; },{},{} -12095,Dex_Dish10,Hwergelmir's Tonic,0,100000,,1000,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_DEXFOOD,1200000,10; percentheal 10,10; },{},{} -12096,Luk_Dish06,Lucky Soup,0,20000,,300,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_LUKFOOD,1200000,6; percentheal 6,3; },{},{} -12097,Luk_Dish07,Assorted Shish Kebob,0,40000,,800,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_LUKFOOD,1200000,7; percentheal 7,3; },{},{} -12098,Luk_Dish08,Strawberry Flavored Rice Ball,0,60000,,400,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_LUKFOOD,1200000,8; percentheal 9,3; },{},{} -12099,Luk_Dish09,Blood Flavored Soda,0,80000,,1000,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_LUKFOOD,1200000,9; percentheal 10,4; },{},{} -12100,Luk_Dish10,Cooked Nine Tail's Tails,0,100000,,500,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_LUKFOOD,1200000,10; percentheal 14,8; },{},{} +12041,Str_Dish01,Fried Grasshopper Legs,0,2000,,60,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_STR,1200000,1; percentheal 5,0; },{},{} +12042,Str_Dish02,Seasoned Sticky Webfoot,0,4000,,500,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_STR,1200000,2; percentheal 5,0; },{},{} +12043,Str_Dish03,Bomber Steak,0,6000,,500,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_STR,1200000,3; percentheal 5,0; },{},{} +12044,Str_Dish04,Herb Marinade Beef,0,8000,,500,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_STR,1200000,4; percentheal 5,0; },{},{} +12045,Str_Dish05,Lutie Lady's Pancake,0,10000,,500,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_STR,1200000,5; percentheal 10,0; },{},{} +12046,Int_Dish01,Grape Juice Herbal Tea,0,2000,,100,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_INT,1200000,1; percentheal 0,5; },{},{} +12047,Int_Dish02,Autumn Red Tea,0,4000,,500,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_INT,1200000,2; percentheal 0,5; },{},{} +12048,Int_Dish03,Honey Herbal Tea,0,6000,,500,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_INT,1200000,3; percentheal 0,5; },{},{} +12049,Int_Dish04,Morroc Fruit Wine,0,8000,,300,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_INT,1200000,4; percentheal 0,5; },{},{} +12050,Int_Dish05,Mastela Fruit Wine,0,10000,,400,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_INT,1200000,5; percentheal 0,10; },{},{} +12051,Vit_Dish01,Steamed Crab Nippers,0,2000,,100,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_VIT,1200000,1; percentheal 5,0; },{},{} +12052,Vit_Dish02,Assorted Seafood,0,4000,,200,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_VIT,1200000,2; percentheal 5,0; },{},{} +12053,Vit_Dish03,Clam Soup,0,6000,,300,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_VIT,1200000,3; percentheal 5,0; },{},{} +12054,Vit_Dish04,Seasoned Jellyfish,0,8000,,500,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_VIT,1200000,4; percentheal 5,0; },{},{} +12055,Vit_Dish05,Spicy Fried Bao,0,10000,,800,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_VIT,1200000,5; percentheal 10,0; },{},{} +12056,Agi_Dish01,Frog Egg Squid Ink Soup,0,2000,,100,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_AGI,1200000,1; percentheal 3,1; },{},{} +12057,Agi_Dish02,Smooth Noodle,0,4000,,100,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_AGI,1200000,2; percentheal 3,1; },{},{} +12058,Agi_Dish03,Tentacle Cheese Gratin,0,6000,,500,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_AGI,1200000,3; percentheal 3,1; },{},{} +12059,Agi_Dish04,Lutie Cold Noodle,0,8000,,400,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_AGI,1200000,4; percentheal 3,1; },{},{} +12060,Agi_Dish05,Steamed Bat Wing in Pumpkin,0,10000,,500,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_AGI,1200000,5; percentheal 6,2; },{},{} +12061,Dex_Dish01,Honey Grape Juice,0,2000,,100,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_DEX,1200000,1; percentheal 2,2; },{},{} +12062,Dex_Dish02,Chocolate Mousse Cake,0,4000,,200,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_DEX,1200000,2; percentheal 2,2; },{},{} +12063,Dex_Dish03,Fruit Mix,0,6000,,200,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_DEX,1200000,3; percentheal 2,2; },{},{} +12064,Dex_Dish04,Cream Sandwich,0,8000,,500,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_DEX,1200000,4; percentheal 2,2; },{},{} +12065,Dex_Dish05,Green Salad,0,10000,,200,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_DEX,1200000,5; percentheal 5,5; },{},{} +12066,Luk_Dish01,Fried Monkey Tails,0,2000,,60,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_LUK,1200000,1; percentheal 3,2; },{},{} +12067,Luk_Dish02,Mixed Juice,0,4000,,200,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_LUK,1200000,2; percentheal 3,2; },{},{} +12068,Luk_Dish03,Fried Sweet Potato,0,6000,,500,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_LUK,1200000,3; percentheal 4,2; },{},{} +12069,Luk_Dish04,Steamed Ancient Lips,0,8000,,500,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_LUK,1200000,4; percentheal 4,2; },{},{} +12070,Luk_Dish05,Fried Scorpion Tails,0,10000,,400,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_LUK,1200000,5; percentheal 5,2; },{},{} +12071,Str_Dish06,Shiny Marinade Beef,0,20000,,800,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_STR,1200000,6; percentheal 10,2; },{},{} +12072,Str_Dish07,Whole Roast,0,40000,,1000,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_STR,1200000,7; percentheal 10,4; },{},{} +12073,Str_Dish08,Bearfoot Special,0,60000,,500,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_STR,1200000,8; percentheal 15,6; },{},{} +12074,Str_Dish09,Tendon Satay,0,80000,,1000,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_STR,1200000,9; percentheal 15,8; },{},{} +12075,Str_Dish10,Steamed Tongue,0,100000,,1000,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_STR,1200000,10; percentheal 20,20; },{},{} +12076,Int_Dish06,Red Mushroom Wine,0,20000,,300,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_INT,1200000,6; percentheal 2,10; },{},{} +12077,Int_Dish07,Special Royal Jelly Herbal Tea,0,40000,,800,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_INT,1200000,7; percentheal 4,10; },{},{} +12078,Int_Dish08,Royal Family Tea,0,60000,,1000,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_INT,1200000,8; percentheal 6,10; },{},{} +12079,Int_Dish09,Tristan XII,0,80000,,1000,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_INT,1200000,9; percentheal 8,15; },{},{} +12080,Int_Dish10,Dragon Breath Cocktail,0,100000,,1000,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_INT,1200000,10; percentheal 10,20; },{},{} +12081,Vit_Dish06,Awfully Bitter Bracer,0,20000,,500,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_VIT,1200000,6; percentheal 13,0; },{},{} +12082,Vit_Dish07,Sumptuous Feast,0,40000,,400,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_VIT,1200000,7; percentheal 16,0; },{},{} +12083,Vit_Dish08,Giant Burito,0,60000,,1000,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_VIT,1200000,8; percentheal 19,0; },{},{} +12084,Vit_Dish09,Ascending Dragon Soup,0,80000,,1000,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_VIT,1200000,9; percentheal 22,0; },{},{} +12085,Vit_Dish10,Immortal Stew,0,100000,,1000,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_VIT,1200000,10; percentheal 25,0; },{},{} +12086,Agi_Dish06,Chile Shrimp Gratin,0,20000,,800,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_AGI,1200000,6; percentheal 7,2; },{},{} +12087,Agi_Dish07,Steamed Alligator with Vegetable,0,40000,,800,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_AGI,1200000,7; percentheal 8,2; },{},{} +12088,Agi_Dish08,Incredibly Spicy Curry,0,60000,,1000,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_AGI,1200000,8; percentheal 9,2; },{},{} +12089,Agi_Dish09,Special Meat Stew,0,80000,,1000,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_AGI,1200000,9; percentheal 10,2; },{},{} +12090,Agi_Dish10,Steamed Desert Scorpions,0,100000,,1000,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_AGI,1200000,10; percentheal 15,5; },{},{} +12091,Dex_Dish06,Peach Cake,0,20000,,800,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_DEX,1200000,6; percentheal 5,6; },{},{} +12092,Dex_Dish07,Soul Haunted Bread,0,40000,,800,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_DEX,1200000,7; percentheal 5,7; },{},{} +12093,Dex_Dish08,Special Toast,0,60000,,1000,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_DEX,1200000,8; percentheal 5,8; },{},{} +12094,Dex_Dish09,Heavenly Fruit Juice,0,80000,,500,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_DEX,1200000,9; percentheal 5,9; },{},{} +12095,Dex_Dish10,Hwergelmir's Tonic,0,100000,,1000,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_DEX,1200000,10; percentheal 10,10; },{},{} +12096,Luk_Dish06,Lucky Soup,0,20000,,300,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_LUK,1200000,6; percentheal 6,3; },{},{} +12097,Luk_Dish07,Assorted Shish Kebob,0,40000,,800,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_LUK,1200000,7; percentheal 7,3; },{},{} +12098,Luk_Dish08,Strawberry Flavored Rice Ball,0,60000,,400,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_LUK,1200000,8; percentheal 9,3; },{},{} +12099,Luk_Dish09,Blood Flavored Soda,0,80000,,1000,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_LUK,1200000,9; percentheal 10,4; },{},{} +12100,Luk_Dish10,Cooked Nine Tail's Tails,0,100000,,500,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_LUK,1200000,10; percentheal 14,8; },{},{} 12101,Citron,Citron,0,20,,300,,,,,0xFFFFFFFF,7,2,,,,,,{},{},{} 12102,Meat_Skewer,Grilled Skewer,0,20,,300,,,,,0xFFFFFFFF,7,2,,,,,,{},{},{} 12103,Bloody_Dead_Branch,Bloody Branch,2,10000,,200,,,,,0xFFFFFFFF,7,2,,,,,,{ monster "this",-1,-1,"--ja--",-3,1,""; },{},{} @@ -5418,8 +5418,8 @@ 12119,Resist_Water,Coldproof Potion,2,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start4 SC_ARMOR_ELEMENT,1200000,20,0,0,-15; },{},{} 12120,Resist_Earth,Earthproof Potion,2,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start4 SC_ARMOR_ELEMENT,1200000,0,20,-15,0; },{},{} 12121,Resist_Wind,Thunderproof Potion,2,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start4 SC_ARMOR_ELEMENT,1200000,0,-15,0,20; },{},{} -12122,Sesame_Pastry,Sesame Pastry,2,2,,70,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_HITFOOD,1200000,30; },{},{} -12123,Honey_Pastry,Honey Pastry,2,2,,70,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FLEEFOOD,1200000,30; },{},{} +12122,Sesame_Pastry,Sesame Pastry,2,2,,70,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_BASICHIT,1200000,30; },{},{} +12123,Honey_Pastry,Honey Pastry,2,2,,70,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_BASICAVOIDANCE,1200000,30; },{},{} 12124,Rainbow_Cake,Rainbow Cake,2,2,,70,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_BATKFOOD,1200000,10; sc_start SC_MATKFOOD,120000,10; },{},{} 12125,Outdoor_Cooking_Kits,Outdoor Cooking Kit,2,500,,20,,,,,0xFFFFFFFF,7,2,,,,,,{ cooking 11; },{},{} 12126,Indoor_Cooking_Kits,Home Cooking Kit,2,1000,,30,,,,,0xFFFFFFFF,7,2,,,,,,{ cooking 12; },{},{} @@ -5438,7 +5438,7 @@ 12139,3rd_Stage_Prize,Third Stage Prize,2,0,,0,,,,,0xFFFFFFFF,7,2,,,,,,{},{},{} 12140,4th_Stage_Prize,Fourth Stage Prize,2,0,,0,,,,,0xFFFFFFFF,7,2,,,,,,{},{},{} 12141,5th_Stage_Prize,Fifth Stage Prize,2,0,,0,,,,,0xFFFFFFFF,7,2,,,,,,{},{},{} -12142,Magic_Book,Book of Magic,2,0,,100,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_AGIFOOD,1800000,10; },{},{} +12142,Magic_Book,Book of Magic,2,0,,100,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_AGI,1800000,10; },{},{} 12143,Red_Can,Red Can,2,50000,,300,,,,,0xFFFFFFFF,7,2,,,,,,{},{},{} 12144,Sphere_Case_Wind,Lightning Sphere Pack,2,2,,350,,,,,0xFFFFFFFF,7,2,,,,,,{ getitem 13204,500; },{},{} 12145,Sphere_Case_Darkness,Blind Sphere Pack,2,2,,350,,,,,0xFFFFFFFF,7,2,,,,,,{ getitem 13206,500; },{},{} @@ -5505,66 +5505,66 @@ 12205,Dex_Dish10_,Hwergelmir's Tonic,0,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_DEX_CASH,1800000,10; percentheal 15,5; },{},{} 12206,Luk_Dish10_,Cooked Nine Tail's Tails,0,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_LUK_CASH,1800000,10; percentheal 15,5; },{},{} 12207,Vit_Dish10_,Stew Of Immortality,0,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_VIT_CASH,1800000,10; percentheal 15,5; },{},{} -12208,Battle_Manual,Battle Manual,2,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_EXPBOOST,1800000,50; },{},{} -12209,Insurance,Life Insurance,2,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_LIFEINSURANCE,1800000,0; },{},{} -12210,Bubble_Gum,Bubble Gum,2,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_ITEMBOOST,1800000,200; },{},{} +12208,Battle_Manual,Battle Manual,2,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_CASH_PLUSEXP,1800000,50; },{},{} +12209,Insurance,Life Insurance,2,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_CASH_DEATHPENALTY,1800000,0; },{},{} +12210,Bubble_Gum,Bubble Gum,2,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_CASH_RECEIVEITEM,1800000,200; },{},{} 12211,Kafra_Card,Kafra Card,2,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ callfunc "F_CashStore"; },{},{} 12212,Giant_Fly_Wing,Giant Fly Wing,2,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ callfunc "F_CashPartyCall"; },{},{} 12213,Neuralizer,Neuralizer,11,2,,0,,,,,0xFFFFFFFF,7,2,,,,,,{ callfunc "F_CashReset"; },{},{} -12214,Convex_Mirror,Convex Mirror,2,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_BOSSMAPINFO,600000,0; },{},{} +12214,Convex_Mirror,Convex Mirror,2,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_CASH_BOSS_ALARM,600000,0; },{},{} 12215,Blessing_10_Scroll,LV10 Blessing Scroll,2,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ skilleffect "AL_BLESSING",0; sc_start SC_BLESSING,240000,10; },{},{} -12216,Inc_Agi_10_Scroll,LV10 Agil Scroll,2,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ if(Hp>15) { skilleffect "AL_INCAGI",0; sc_start SC_INCREASEAGI,240000,10; heal -15,0; } },{},{} +12216,Inc_Agi_10_Scroll,LV10 Agil Scroll,2,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ if(Hp>15) { skilleffect "AL_INCAGI",0; sc_start SC_INC_AGI,240000,10; heal -15,0; } },{},{} 12217,Aspersio_5_Scroll,LV5 Aspersio Scroll,2,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ if(countitem(523)>0) { skilleffect "PR_ASPERSIO",0; sc_start SC_ASPERSIO,180000,5; delitem 523,1; } },{},{} 12218,Assumptio_5_Scroll,LV5 Assumptio Scroll,2,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_ASSUMPTIO,100000,5; skilleffect "HP_ASSUMPTIO",0; },{},{} 12219,Wind_Walk_10_Scroll,LV10 Wind Walker Scroll,2,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ skilleffect "SN_WINDWALK",0; sc_start SC_WINDWALK,250000,5; },{},{} 12220,Adrenaline_Scroll,LV5 Adrenaline Scroll,2,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ set .@type,getiteminfo(getequipid(EQI_HAND_R),11); if (.@type==6||.@type==7||.@type==8) { skilleffect "BS_ADRENALINE",0; sc_start SC_ADRENALINE,150000,5; } },{},{} 12221,Megaphone_,Megaphone,2,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ input @megaphone$; announce strcharinfo(0) + ": " + @megaphone$,bc_all,0xFF0000; end; },{},{} 12225,Sweet_Candy_Striper,Sweet Candy Cane,2,20,,50,,,,,0xFFFFFFFF,7,2,,,,,,{ pet 1245; },{},{} -12226,Examination1,Examination 1,0,20,,50,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_SpeedUp0,5400000,0; percentheal 100,100; sc_start SC_STRFOOD,5400000,10; sc_start SC_DEXFOOD,5400000,5; sc_start SC_ATKPOTION,5400000,22; sc_start SC_MATKFOOD,5400000,15; },{},{} -12227,Examination2,Examination 2,0,20,,50,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_SpeedUp0,5400000,0; percentheal 100,100; sc_start SC_INTFOOD,5400000,8; sc_start SC_VITFOOD,5400000,7; sc_start SC_LUKFOOD,5400000,7; sc_start SC_ATKPOTION,5400000,10; },{},{} -12228,Examination3,Examination 3,0,20,,50,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_SpeedUp0,5400000,0; percentheal 100,100; sc_start SC_AGIFOOD,5400000,15; sc_start SC_ATKPOTION,5400000,52; sc_start SC_MATKFOOD,5400000,10; },{},{} -12229,Examination4,Examination 4,0,20,,50,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_SpeedUp0,5400000,0; percentheal 100,100; sc_start SC_STRFOOD,5400000,3; sc_start SC_AGIFOOD,5400000,5; sc_start SC_VITFOOD,5400000,10; sc_start SC_MATKFOOD,5400000,52; },{},{} -12230,Examination5,Examination 5,0,20,,50,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_SpeedUp0,5400000,0; percentheal 100,100; sc_start SC_INTFOOD,5400000,3; sc_start SC_DEXFOOD,5400000,12; sc_start SC_ATKPOTION,5400000,20; sc_start SC_MATKFOOD,5400000,20; },{},{} -12231,Examination6,Examination 6,0,20,,50,,,,,0xFFFFFFFF,7,2,,,,,,{ percentheal 100,100; sc_start SC_SpeedUp0,5400000,0; sc_start SC_STRFOOD,5400000,6; sc_start SC_DEXFOOD,5400000,6; sc_start SC_AGIFOOD,5400000,6; sc_start SC_INTFOOD,5400000,6; sc_start SC_VITFOOD,5400000,6; sc_start SC_LUKFOOD,5400000,6; sc_start SC_ATKPOTION,5400000,24; sc_start SC_MATKFOOD,5400000,24; },{},{} -12232,Gingerbread,Ginger Bread,2,20,,150,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_ASPDPOTION1,900000,0; sc_start SC_SpeedUp0,900000,0; },{},{} +12226,Examination1,Examination 1,0,20,,50,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_MOVHASTE_HORSE,5400000,0; percentheal 100,100; sc_start SC_FOOD_STR,5400000,10; sc_start SC_FOOD_DEX,5400000,5; sc_start SC_PLUSATTACKPOWER,5400000,22; sc_start SC_MATKFOOD,5400000,15; },{},{} +12227,Examination2,Examination 2,0,20,,50,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_MOVHASTE_HORSE,5400000,0; percentheal 100,100; sc_start SC_FOOD_INT,5400000,8; sc_start SC_FOOD_VIT,5400000,7; sc_start SC_FOOD_LUK,5400000,7; sc_start SC_PLUSATTACKPOWER,5400000,10; },{},{} +12228,Examination3,Examination 3,0,20,,50,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_MOVHASTE_HORSE,5400000,0; percentheal 100,100; sc_start SC_FOOD_AGI,5400000,15; sc_start SC_PLUSATTACKPOWER,5400000,52; sc_start SC_MATKFOOD,5400000,10; },{},{} +12229,Examination4,Examination 4,0,20,,50,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_MOVHASTE_HORSE,5400000,0; percentheal 100,100; sc_start SC_FOOD_STR,5400000,3; sc_start SC_FOOD_AGI,5400000,5; sc_start SC_FOOD_VIT,5400000,10; sc_start SC_MATKFOOD,5400000,52; },{},{} +12230,Examination5,Examination 5,0,20,,50,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_MOVHASTE_HORSE,5400000,0; percentheal 100,100; sc_start SC_FOOD_INT,5400000,3; sc_start SC_FOOD_DEX,5400000,12; sc_start SC_PLUSATTACKPOWER,5400000,20; sc_start SC_MATKFOOD,5400000,20; },{},{} +12231,Examination6,Examination 6,0,20,,50,,,,,0xFFFFFFFF,7,2,,,,,,{ percentheal 100,100; sc_start SC_MOVHASTE_HORSE,5400000,0; sc_start SC_FOOD_STR,5400000,6; sc_start SC_FOOD_DEX,5400000,6; sc_start SC_FOOD_AGI,5400000,6; sc_start SC_FOOD_INT,5400000,6; sc_start SC_FOOD_VIT,5400000,6; sc_start SC_FOOD_LUK,5400000,6; sc_start SC_PLUSATTACKPOWER,5400000,24; sc_start SC_MATKFOOD,5400000,24; },{},{} +12232,Gingerbread,Ginger Bread,2,20,,150,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_ATTHASTE_POTION2,900000,0; sc_start SC_MOVHASTE_HORSE,900000,0; },{},{} 12233,Kvass,Kvass,0,20,,200,,,,,0xFFFFFFFF,7,2,,,,,,{ percentheal 100,100; },{},{} 12234,Cacao99,Fierce Cacao 99%,0,20,,100,,,,,0xFFFFFFFF,7,2,,,,,,{ percentheal 25,0; },{},{} 12235,Strawberry_Choco,Chocolate Strawberry,2,20,,100,,,,,0xFFFFFFFF,7,2,,,,,,{ percentheal 0,5; skilleffect "AL_BLESSING",0; sc_start SC_BLESSING,240000,10; },{},{} 12236,Choco_Tart,Chocolate Tart,11,20,,100,,,,,0xFFFFFFFF,7,2,,,,,,{ percentheal 5,0; itemskill "AL_ANGELUS",5; },{},{} -12237,Choco_Lump,Junky Chocolate,2,0,,100,,,,,0xFFFFFFFF,7,2,,,,,,{ percentheal 0,5; sc_start SC_Poison,18000,0; sc_start SC_Bleeding,18000,0; },{},{} +12237,Choco_Lump,Junky Chocolate,2,0,,100,,,,,0xFFFFFFFF,7,2,,,,,,{ percentheal 0,5; sc_start SC_Poison,18000,0; sc_start SC_BLOODING,18000,0; },{},{} 12238,New_Year_Rice_Cake_1,New Year Rice Cake,2,20,,100,,,,,0xFFFFFFFF,7,2,,,,,,{ if(rand(1000)<100) sc_start SC_DPoison,10000,0; sc_start SC_Poison,50000,0; },{},{} 12239,New_Year_Rice_Cake_2,New Year Rice Cake,2,20,,100,,,,,0xFFFFFFFF,7,2,,,,,,{ if(rand(1000)<100) sc_start SC_DPoison,10000,0; sc_start SC_Poison,50000,0; },{},{} 12240,Old_Yellow_Box,Old Yellow Box,2,20,,200,,,,,0xFFFFFFFF,7,2,,,,,,{ getrandgroupitem(IG_YellowBox),1; },{},{} -12241,M_Center_Potion,Mercenary Concentration Potion,2,800,,100,,,,,0xFFFFFFFF,7,2,,,,,,{ mercenary_sc_start SC_ASPDPOTION0,1800000,0; },{},{} -12242,M_Awakening_Potion,Mercenary Awakening Potion,2,1500,,150,,,,,0xFFFFFFFF,7,2,,,,,,{ mercenary_sc_start SC_ASPDPOTION1,1800000,0; },{},{} -12243,M_Berserk_Potion,Mercenary Berserk Potion,2,3000,,200,,,,,0xFFFFFFFF,7,2,,,,,,{ mercenary_sc_start SC_ASPDPOTION2,1800000,0; },{},{} +12241,M_Center_Potion,Mercenary Concentration Potion,2,800,,100,,,,,0xFFFFFFFF,7,2,,,,,,{ mercenary_sc_start SC_ATTHASTE_POTION1,1800000,0; },{},{} +12242,M_Awakening_Potion,Mercenary Awakening Potion,2,1500,,150,,,,,0xFFFFFFFF,7,2,,,,,,{ mercenary_sc_start SC_ATTHASTE_POTION2,1800000,0; },{},{} +12243,M_Berserk_Potion,Mercenary Berserk Potion,2,3000,,200,,,,,0xFFFFFFFF,7,2,,,,,,{ mercenary_sc_start SC_ATTHASTE_POTION3,1800000,0; },{},{} 12244,Old_Gift_Box,Old Gift Box,2,20,,200,,,,,0xFFFFFFFF,7,2,,,,,,{ getrandgroupitem(IG_OldGiftBox),1; },{},{} 12245,Green_Ale_US,Green Ale,0,5000,,500,,,,,0xFFFFFFFF,7,2,,,,,,{ percentheal 100,0; },{},{} 12246,Magic_Card_Album,Mystical Card Album,2,10000,,50,,,,,0xFFFFFFFF,7,2,,,,,,{ getrandgroupitem(IG_MagicCardAlbum),1; },{},{} 12247,Halohalo,Halo-Halo,2,2,,100,,,,,0xFFFFFFFF,7,2,,,20,,,{ sc_start SC_INCALLSTATUS,600000,3; },{},{} 12248,Masquerade_Ball_Box,Fancy Ball Box,2,20,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ getrandgroupitem(IG_Masquerade),1; },{},{} 12249,Payroll_Of_Kafra_,Payment Statement for Kafra Employee,2,20,,10,,,,,0xFFFFFFFF,7,2,,,,,,{},{},{} -12250,Str_Dish10_M,Steamed Tongue,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_STRFOOD,3600000,10; percentheal 20,20; },{},{} -12251,Agi_Dish10_M,Steamed Desert Scorpions,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_AGIFOOD,3600000,10; percentheal 15,5; },{},{} -12252,Int_Dish10_M,Dragon Breath Cocktail,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_INTFOOD,3600000,10; percentheal 10,20; },{},{} -12253,Dex_Dish10_M,Hwergelmir's Tonic,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_DEXFOOD,3600000,10; percentheal 10,10; },{},{} -12254,Luk_Dish10_M,Cooked Nine Tail,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_LUKFOOD,3600000,10; percentheal 14,8; },{},{} -12255,Vit_Dish10_M,Immortal Stew,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_VITFOOD,3600000,10; percentheal 25,0; },{},{} +12250,Str_Dish10_M,Steamed Tongue,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_STR,3600000,10; percentheal 20,20; },{},{} +12251,Agi_Dish10_M,Steamed Desert Scorpions,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_AGI,3600000,10; percentheal 15,5; },{},{} +12252,Int_Dish10_M,Dragon Breath Cocktail,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_INT,3600000,10; percentheal 10,20; },{},{} +12253,Dex_Dish10_M,Hwergelmir's Tonic,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_DEX,3600000,10; percentheal 10,10; },{},{} +12254,Luk_Dish10_M,Cooked Nine Tail,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_LUK,3600000,10; percentheal 14,8; },{},{} +12255,Vit_Dish10_M,Immortal Stew,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_VIT,3600000,10; percentheal 25,0; },{},{} 12256,PRO_Gift_Box,PRO Gift Box,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{},{},{} 12257,Cold_Medicine,Cold Medicine,0,20,,100,,,,,0xFFFFFFFF,7,2,,,50,,,{ percentheal 25,25; },{},{} 12258,Bombring_Box,Bomb Poring Box,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ if(strcharinfo(3)=="job3_rang02") { monster "this",-1,-1,"--ja--",1904,1,""; } },{},{} 12259,Miracle_Medicine,Miracle Tonic,2,0,,0,,,,,0xFFFFFFFF,7,2,,,,,,{ getexp 3000000,1500000; },{},{} 12260,Cool_Summer_Outfit,Cool Summer Outfit,2,0,,100,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_Summer,600000,0; },{},{} 12261,Secret_Medicine,Leap of Fantasy,2,0,,0,,,,,0xFFFFFFFF,7,2,,,,,,{ getexp 2000000,1000000; },{},{} -12262,Inspector_Certificate_,Authoritative Badge,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_SpeedUp0,180000,0; },{},{} -12263,Comp_Battle_Manual,Field Manual,2,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_EXPBOOST,1800000,50; },{},{} -12264,Comp_Bubble_Gum,Bubble Gum,2,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_ITEMBOOST,1800000,200; },{},{} -12265,Comp_Insurance,Life Insurrance,2,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_LIFEINSURANCE,1800000,0; },{},{} -12266,Sesame_Pastry_,Sesame Pastry,2,2,,70,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_HITFOOD,1200000,30; },{},{} -12267,Honey_Pastry_,Honey Pastry,2,2,,70,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FLEEFOOD,1200000,30; },{},{} -12268,Rainbow_Cake_,Rainbow Cake,2,2,,70,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_ATKPOTION,60000,10; sc_start SC_MATKFOOD,120000,10; },{},{} -12269,Tasty_Colonel,Tasty Pink Ration,2,2,,70,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_ATKPOTION,600000,15; },{},{} -12270,Tasty_Major,Tasty White Ration,2,2,,70,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_MATKPOTION,600000,15; },{},{} +12262,Inspector_Certificate_,Authoritative Badge,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_MOVHASTE_HORSE,180000,0; },{},{} +12263,Comp_Battle_Manual,Field Manual,2,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_CASH_PLUSEXP,1800000,50; },{},{} +12264,Comp_Bubble_Gum,Bubble Gum,2,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_CASH_RECEIVEITEM,1800000,200; },{},{} +12265,Comp_Insurance,Life Insurrance,2,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_CASH_DEATHPENALTY,1800000,0; },{},{} +12266,Sesame_Pastry_,Sesame Pastry,2,2,,70,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_BASICHIT,1200000,30; },{},{} +12267,Honey_Pastry_,Honey Pastry,2,2,,70,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_BASICAVOIDANCE,1200000,30; },{},{} +12268,Rainbow_Cake_,Rainbow Cake,2,2,,70,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_PLUSATTACKPOWER,60000,10; sc_start SC_MATKFOOD,120000,10; },{},{} +12269,Tasty_Colonel,Tasty Pink Ration,2,2,,70,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_PLUSATTACKPOWER,600000,15; },{},{} +12270,Tasty_Major,Tasty White Ration,2,2,,70,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_PLUSMAGICPOWER,600000,15; },{},{} 12271,Mre_A,Military Ration A,0,2,,70,,,,,0xFFFFFFFF,7,2,,,,,,{ percentheal 5,0; },{},{} 12272,Mre_B,Military Ration B,2,2,,70,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_INCHIT,600000,33; },{},{} 12273,Mre_C,Military Ration C,2,2,,70,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_INCFLEE,600000,33; },{},{} @@ -5576,16 +5576,16 @@ 12279,Undead_Element_Scroll,Undead Elemental Scroll,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start4 SC_ARMOR_RESIST,300000,20,20,20,20; },{},{} 12280,Holy_Element_Scroll,Holy Elemental Scroll,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ specialeffect2 EF_BENEDICTIO; sc_start SC_BENEDICTIO,300000,1; },{},{} 12281,Tresure_Box_WoE,Event Treasure Box,2,20,,150,,,,,0xFFFFFFFF,7,2,,,,,,{ getrandgroupitem(IG_Tresure_Box_WoE),1; },{},{} -12282,Internet_Cafe1,Internet Cafe1,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_INCALLSTATUS,5400000,3; sc_start SC_ATKPOTION,5400000,15; sc_start SC_MATKPOTION,5400000,15; },{},{} -12283,Internet_Cafe2,Internet Cafe2,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_INCSTR,5400000,8; sc_start SC_INCDEX,5400000,4; sc_start SC_INCAGI,5400000,6; sc_start SC_ATKPOTION,5400000,32; sc_start SC_INCFLEE,5400000,5; },{},{} -12284,Internet_Cafe3,Internet Cafe3,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_INCINT,5400000,8; sc_start SC_INCVIT,5400000,4; sc_start SC_INCDEX,5400000,6; sc_start SC_MATKPOTION,5400000,40; },{},{} -12285,Internet_Cafe4,Internet Cafe4,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_INCDEX,5400000,8; sc_start SC_INCLUK,5400000,4; sc_start SC_INCAGI,5400000,6; sc_start SC_ATKPOTION,5400000,24; sc_start SC_MATKPOTION,5400000,24; },{},{} +12282,Internet_Cafe1,Internet Cafe1,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_INCALLSTATUS,5400000,3; sc_start SC_PLUSATTACKPOWER,5400000,15; sc_start SC_PLUSMAGICPOWER,5400000,15; },{},{} +12283,Internet_Cafe2,Internet Cafe2,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_INCSTR,5400000,8; sc_start SC_INCDEX,5400000,4; sc_start SC_INCAGI,5400000,6; sc_start SC_PLUSATTACKPOWER,5400000,32; sc_start SC_INCFLEE,5400000,5; },{},{} +12284,Internet_Cafe3,Internet Cafe3,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_INCINT,5400000,8; sc_start SC_INCVIT,5400000,4; sc_start SC_INCDEX,5400000,6; sc_start SC_PLUSMAGICPOWER,5400000,40; },{},{} +12285,Internet_Cafe4,Internet Cafe4,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_INCDEX,5400000,8; sc_start SC_INCLUK,5400000,4; sc_start SC_INCAGI,5400000,6; sc_start SC_PLUSATTACKPOWER,5400000,24; sc_start SC_PLUSMAGICPOWER,5400000,24; },{},{} 12286,Masquerade_Ball_Box2,Masquerade Ball Box2,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ getrandgroupitem(IG_Masquerade_2),1; },{},{} 12287,Love_Angel,Love Angel Magic Powder,2,0,,0,,,,,0xFFFFFFFF,7,2,,,,,,{ setfont 1; },{},{} 12288,Squirrel,Squirrel Magic Powder,2,0,,0,,,,,0xFFFFFFFF,7,2,,,,,,{ setfont 2; },{},{} 12289,Gogo,Gogo Magic Powder,2,0,,0,,,,,0xFFFFFFFF,7,2,,,,,,{ setfont 3; },{},{} 12290,Mysterious_Can,Mysterious Can Magic Powder,2,10,,100,,,,,0xFFFFFFFF,7,2,,,,,,{ percentheal 5,0; skilleffect "AL_BLESSING",0; sc_start SC_BLESSING,120000,5; },{},{} -12291,Mysterious_PET_Bottle,Mysterious PET Bottle,2,10,,100,,,,,0xFFFFFFFF,7,2,,,,,,{ percentheal 5,0; skilleffect "AL_INCAGI",0; sc_start SC_INCREASEAGI,120000,5; },{},{} +12291,Mysterious_PET_Bottle,Mysterious PET Bottle,2,10,,100,,,,,0xFFFFFFFF,7,2,,,,,,{ percentheal 5,0; skilleffect "AL_INCAGI",0; sc_start SC_INC_AGI,120000,5; },{},{} 12292,Unripe_Fruit,Unripe Fruit,0,500,,200,,,,,0xFFFFFFFF,7,2,,,,,,{ percentheal 20,0; },{},{} 12293,Dried_Yggdrasilberry,Dried Yggdrasilberry,0,500,,200,,,,,0xFFFFFFFF,7,2,,,,,,{ percentheal 0,20; },{},{} 12294,PC_Bang_Coin_Box1,PC-Room Coin Box,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ getitem 2740,1; },{},{} @@ -5606,7 +5606,7 @@ 12309,Bulging_Head,JJangu Magic Powder,2,0,,0,,,,,0xFFFFFFFF,7,2,,,,,,{ setfont 9; },{},{} 12310,Spray_Of_Flowers,Spray Of Flowers,2,0,,50,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_INCFLEE,600000,10; },{},{} 12311,Large_Spray_Of_Flowers,Huge Spray Of Flowers,11,0,,100,,,,,0xFFFFFFFF,7,2,,,,,,{ itemskill "ALL_PARTYFLEE",1; },{},{} -12312,Thick_Manual50,Thick Battle Manual,2,0,,0,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_EXPBOOST,3600000,50; },{},{} +12312,Thick_Manual50,Thick Battle Manual,2,0,,0,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_CASH_PLUSEXP,3600000,50; },{},{} 12313,Protection_Of_Angel,Guardian Angel,2,0,,0,,,,,0xFFFFFFFF,7,2,,,,,,{},{},{} 12314,Noive_Box,Noive Box,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{},{},{} 12315,Goddess_Bless,Goddess Of Blessing,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{},{},{} @@ -5615,7 +5615,7 @@ 12318,Little_Heart,Small Hearts,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{},{},{} 12319,Strawberry_Cake,Rune Strawberry Cake,2,0,,300,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_INCATKRATE,600000,5; sc_start SC_INCMATKRATE,600000,5; },{},{} 12320,Pineapple_Juice,Schwartzwald Pine Jubilee,2,0,,300,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_INCHIT,600000,10; sc_start SC_INCFLEE2,600000,20; },{},{} -12321,Spicy_Sandwich,Arunafeltz Desert Sandwich,2,0,,300,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_INCCRI,600000,7; },{},{} +12321,Spicy_Sandwich,Arunafeltz Desert Sandwich,2,0,,300,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_CRITICALPERCENT,600000,7; },{},{} 12322,Chocolate_Pie,Chocolate Pie,0,0,,50,,,,,0xFFFFFFFF,7,2,,,,,,{ percentheal 5,5; },{},{} 12323,N_Fly_Wing,Novice Fly Wing,11,0,,0,,,,,0xFFFFFFFF,7,2,,,,,,{ itemskill "AL_TELEPORT",1; },{},{} 12324,N_Butterfly_Wing,Novice Butterfly Wing,11,0,,0,,,,,0xFFFFFFFF,7,2,,,,,,{ itemskill "AL_TELEPORT",3; },{},{} @@ -5648,7 +5648,7 @@ 12351,Shout_Megaphone,Scream Megaphone,11,20,,50,,,,,0xFFFFFFFF,7,2,,,,,,{ itemskill "MC_LOUD",1; },{},{} 12352,Dun_Tele_Scroll3,Dungeon Teleport Scroll 3,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{},{},{} 12353,Tiny_Waterbottle,Small Bottle,2,800,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_WATERWEAPON,90000,1; },{},{} -12354,Buche_De_Noel,Buche De Noel,2,2,,50,,,,,0xFFFFFFFF,7,2,,,,,,{ specialeffect2 EF_ANGELUS; sc_start SC_INCMHPRATE,600000,3; sc_start SC_INCMSPRATE,600000,3; sc_start SC_INCHITRATE,600000,3; sc_start SC_INCCRI,600000,7; },{},{} +12354,Buche_De_Noel,Buche De Noel,2,2,,50,,,,,0xFFFFFFFF,7,2,,,,,,{ specialeffect2 EF_ANGELUS; sc_start SC_INCMHPRATE,600000,3; sc_start SC_INCMSPRATE,600000,3; sc_start SC_INCHITRATE,600000,3; sc_start SC_CRITICALPERCENT,600000,7; },{},{} 12355,Xmas_Gift,Xmas Gift,2,2,,100,,,,,0xFFFFFFFF,7,2,,,,,,{ getrandgroupitem(IG_Xmas_Gift),1; },{},{} 12356,Louise_Costume_Box,Louise Costume Box,2,2,,100,,,,,0xFFFFFFFF,7,2,,,,,,{ getrandgroupitem(IG_Louise_Costume_Box),1; },{},{} 12357,Shiny_Wing_Gown,Shiny Wing Gown,2,20,,50,,,,,0xFFFFFFFF,7,2,,,,,,{ pet 1630; },{},{} @@ -5705,10 +5705,10 @@ 12408,Hydra_Ball,Hydra Ball,2,0,,0,,,,,0xFFFFFFFF,7,2,,,,,,{ pet 2081; },{},{} 12409,Pork_Belly_H,Pork Belly H,2,0,,0,,,,,0xFFFFFFFF,7,2,,,,,,{},{},{} 12410,Spareribs_H,Spareribs H,2,0,,0,,,,,0xFFFFFFFF,7,2,,,,,,{},{},{} -12411,HE_Battle_Manual,HE Battle Manual,2,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_EXPBOOST,900000,200; },{},{} -12412,HE_Bubble_Gum,HE Bubble Gum,2,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_ITEMBOOST,900000,300; },{},{} +12411,HE_Battle_Manual,HE Battle Manual,2,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_CASH_PLUSEXP,900000,200; },{},{} +12412,HE_Bubble_Gum,HE Bubble Gum,2,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_CASH_RECEIVEITEM,900000,300; },{},{} 12413,PCBang_Coupon_Box2,PCBang Coupon Box2,2,20,,10,,,,,0xFFFFFFFF,7,2,,,,,,{},{},{} -12414,Guarana_Candy,Guarana Candy,2,20,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_ASPDPOTION0,1800000,0; sc_start SC_INCREASEAGI,140000,5; skilleffect "AL_INCAGI",0; },{},{} +12414,Guarana_Candy,Guarana Candy,2,20,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_ATTHASTE_POTION1,1800000,0; sc_start SC_INC_AGI,140000,5; skilleffect "AL_INCAGI",0; },{},{} 12415,Siege_Teleport_Scroll2,Siege Teleport Scroll2,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{},{},{} 12416,Lucky_Egg_C3,Lucky Egg C3,2,20,,10,,,,,0xFFFFFFFF,7,2,,,,,,{},{},{} 12417,Boost500,Boost500,2,100,,50,,,,,0xFFFFFFFF,7,2,,,,,,{},{},{} @@ -5767,7 +5767,7 @@ 12472,F_Convex_Mirror,F Convex Mirror,2,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{},{},{} 12473,RWC_Parti_Box,RWC Parti Box,2,20,,10,,,,,0xFFFFFFFF,7,2,,,,,,{},{},{} 12474,RWC_Final_Comp_Box,RWC Final Comp Box,2,20,,10,,,,,0xFFFFFFFF,7,2,,,,,,{},{},{} -12475,Cure_Free,Cure Free,2,20,,50,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_end SC_SILENCE; sc_end SC_BLEEDING; sc_end SC_POISON; sc_end SC_CURSE; sc_end SC_ORCISH; sc_end SC_CHANGEUNDEAD; itemheal 500,0; },{},{} +12475,Cure_Free,Cure Free,2,20,,50,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_end SC_SILENCE; sc_end SC_BLOODING; sc_end SC_POISON; sc_end SC_CURSE; sc_end SC_ORCISH; sc_end SC_CHANGEUNDEAD; itemheal 500,0; },{},{} 12476,PCBang_Coupon_Box3,PCBang Coupon Box3,2,20,,10,,,,,0xFFFFFFFF,7,2,,,,,,{},{},{} 12477,Gift_Bundle,Gift Bundle,2,0,,0,,,,,0xFFFFFFFF,7,2,,,,,,{},{},{} 12478,Chance_Box,Chance Box,2,20,,10,,,,,0xFFFFFFFF,7,2,,,,,,{},{},{} @@ -5905,7 +5905,7 @@ 12702,Old_Bleu_Box,Old Navy Box,2,0,,200,,,,,0xFFFFFFFF,7,2,,,,,,{ getrandgroupitem(IG_BleuBox),1; getrandgroupitem(IG_BleuBox),1; },{},{} 12703,Holy_Egg_2,Holy Egg,11,0,,50,,,,,0xFFFFFFFF,7,2,,,,,,{},{},{} 12704,Elixir_Of_Life,Elixir of Life,0,0,,10,,,,,0xFFFFFFFF,7,2,,,85,,,{ percentheal 100,0; },{},{} -12705,Noble_Nameplate,Noble Nameplate,2,0,,100,,,,,0xFFFFFFFF,7,2,,,90,,,{ sc_start SC_EXPBOOST,1800000,100; },{},{} +12705,Noble_Nameplate,Noble Nameplate,2,0,,100,,,,,0xFFFFFFFF,7,2,,,90,,,{ sc_start SC_CASH_PLUSEXP,1800000,100; },{},{} 12706,Lucky_Cookie01,Lucky Cookie,11,0,,100,,,,,0xFFFFFFFF,7,2,,,,,,{ itemskill "PR_GLORIA",5; },{},{} 12707,Lucky_Cookie02,Lucky Cookie,11,0,,100,,,,,0xFFFFFFFF,7,2,,,,,,{ itemskill "PR_MAGNIFICAT",1; },{},{} 12708,Lucky_Cookie03,Lucky Cookie,11,0,,100,,,,,0xFFFFFFFF,7,2,,,,,,{ itemskill "PR_IMPOSITIO",3; },{},{} @@ -5984,7 +5984,7 @@ 12775,Ancient_Spirit_Amulet,Ancient Spirit Amulet,2,20,,600,,,,,0xFFFFFFFF,7,2,,,,,,{},{},{} // 12786,Change_Slot_Card,Character Position Change Coupon,2,,,,,,,,0xFFFFFFFF,7,2,,,,,,{ set SlotChange, SlotChange + 1; },{},{} -12790,Change_Name_Card,Name Change Coupon,2,,,,,,,,0xFFFFFFFF,7,2,,,,,,{ set CharRename, CharRename + 1; },{},{} +12790,Char_Rename_Card,Character Name Change Coupon,2,,,,,,,,0xFFFFFFFF,7,2,,,,,,{ set CharRename, CharRename + 1; },{},{} // 12848,Falcon_Flute,Falcon Flute,11,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ if(getskilllv("HT_FALCON")) { if(checkoption(Option_Wug)||checkoption(Option_Wugrider)) end; if(checkfalcon()==1) { setfalcon 0; } else { setfalcon 1; } } },{},{} 12900,Battle_Manual_Box,Battle Manual Box,18,20,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ getitem 12208,10; },{},{} @@ -6257,7 +6257,7 @@ 13269,Boost500_To_Throw,Throwing Boost 500,10,100,,10,0,,,,0x00040000,8,2,32768,,99,,9,{ sc_start SC_BOOST500,500000,10; },{},{} 13270,Full_SwingK_To_Throw,Throwing Full Swing K,10,100,,50,0,,,,0x00040000,8,2,32768,,99,,9,{ sc_start SC_FULL_SWING_K,500000,50; },{},{} 13271,Mana_Plus_To_Throw,Throwing Mana Plus,10,100,,50,0,,,,0x00040000,8,2,32768,,99,,9,{ sc_start SC_MANA_PLUS,500000,50; },{},{} -13272,Cure_Free_To_Throw,Throwing Cure Free,10,100,,50,0,,,,0x00040000,8,2,32768,,99,,9,{ sc_end SC_Bleeding; sc_end SC_Curse; sc_end SC_Silence; itemheal rand(1000,1200),0; },{},{} +13272,Cure_Free_To_Throw,Throwing Cure Free,10,100,,50,0,,,,0x00040000,8,2,32768,,99,,9,{ sc_end SC_BLOODING; sc_end SC_Curse; sc_end SC_Silence; itemheal rand(1000,1200),0; },{},{} 13273,Stamina_Up_M_To_Throw,Throwing Muramura M,10,100,,10,0,,,,0x00040000,8,2,32768,,99,,9,{ sc_start SC_MUSTLE_M,500000,5; },{},{} 13274,Digestive_F_To_Throw,Throwing Falmons F,10,100,,10,0,,,,0x00040000,8,2,32768,,99,,9,{ sc_start SC_LIFE_FORCE_F,500000,5; },{},{} 13275,HP_Inc_PotS_To_Throw,Throwing Increase HP Potion (Small),10,100,,20,0,,,,0x00040000,8,2,32768,,99,,9,{ sc_start SC_INCMHPRATE,500000,1; percentheal 1,0; },{},{}//HP and SP pots need a recheck later to correct max increases. @@ -7164,11 +7164,11 @@ 14461,Asara_Fairy_Hat_Box,Ashura Fairy Hat Box,18,20,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ getitem 5505,1; },{},{} 14466,Valentine_Pledge_Box,Valentine's Emblem Box,2,0,,0,,,,,0xFFFFFFFF,7,2,,,,,,{},{},{} 14469,Ox_Tail_Scroll,Ox Tail Egg,2,20,,10,,,,,0xFFFFFFFF,7,2,,,,,,{},{},{} -14500,Insurance60,Life Insurrance Certificate,2,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_LIFEINSURANCE,3600000,0; },{},{} +14500,Insurance60,Life Insurrance Certificate,2,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_CASH_DEATHPENALTY,3600000,0; },{},{} 14508,Zeny_Scroll,Zeny Pet Egg Scroll,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{},{},{} -14509,Light_Center_Pot,Light Concentration Potion,2,800,,20,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_ASPDPOTION0,1800000,0; },{},{} -14510,Light_Awakening_Pot,Light Awakening Potion,2,1500,,20,,,,,0xFFF7FEEF,7,2,,,40,,,{ sc_start SC_ASPDPOTION1,1800000,0; },{},{} -14511,Light_Berserk_Pot,Light Berserk Potion,2,3000,,20,,,,,0x01E646A6,7,2,,,85,,,{ sc_start SC_ASPDPOTION2,1800000,0; },{},{} +14509,Light_Center_Pot,Light Concentration Potion,2,800,,20,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_ATTHASTE_POTION1,1800000,0; },{},{} +14510,Light_Awakening_Pot,Light Awakening Potion,2,1500,,20,,,,,0xFFF7FEEF,7,2,,,40,,,{ sc_start SC_ATTHASTE_POTION2,1800000,0; },{},{} +14511,Light_Berserk_Pot,Light Berserk Potion,2,3000,,20,,,,,0x01E646A6,7,2,,,85,,,{ sc_start SC_ATTHASTE_POTION3,1800000,0; },{},{} 14512,Meteor_10_Scroll,Meteor Storm Scroll,11,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ itemskill "WZ_METEOR",10; },{},{} 14513,Storm_10_Scroll,Storm Gust Scroll,11,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ itemskill "WZ_STORMGUST",10; },{},{} 14514,Vermilion_10_Scroll,Lord of Vermilion Scroll,11,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ itemskill "WZ_VERMILION",10; },{},{} @@ -7182,18 +7182,18 @@ 14522,Big_Bun,Big Bun,0,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ percentheal 100,0; },{},{} 14523,Pill_,Pill,0,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ percentheal 0,100; },{},{} 14524,Superb_Fish_Slice,Superb Fish Slice,0,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ percentheal 100,100; },{},{} -14525,Chewy_Ricecake,Chewy Ricecake,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_ATKPOTION,180000,10; },{},{} -14526,Oriental_Pastry,Oriental Pastry,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_MATKPOTION,180000,10; },{},{} +14525,Chewy_Ricecake,Chewy Ricecake,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_PLUSATTACKPOWER,180000,10; },{},{} +14526,Oriental_Pastry,Oriental Pastry,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_PLUSMAGICPOWER,180000,10; },{},{} 14527,Dun_Tele_Scroll1,Dungeon Teleport Scroll,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ callfunc "F_CashDungeon"; },{},{} 14528,PVP_Tele_Scroll,PVP Teleport Scroll,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{},{},{} 14529,Greed_Scroll,Greed Scroll,11,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ itemskill "BS_GREED",1; },{},{} 14530,Flee_30_Scroll,Evasion Scroll,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_INCFLEE,1800000,30; },{},{} 14531,Accuracy_30_Scroll,Concentration Scroll,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_INCHIT,1800000,30; },{},{} -14532,Battle_Manual25,Field Manual 25%,2,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_EXPBOOST,1800000,25; },{},{} -14533,Battle_Manual100,Field Manual 100%,2,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_EXPBOOST,1800000,100; },{},{} +14532,Battle_Manual25,Field Manual 25%,2,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_CASH_PLUSEXP,1800000,25; },{},{} +14533,Battle_Manual100,Field Manual 100%,2,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_CASH_PLUSEXP,1800000,100; },{},{} 14534,Small_Life_Potion,Small Life Potion,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ specialeffect2 320; sc_start4 SC_S_LIFEPOTION,600000,-5,5,0,0; },{},{} 14535,Med_Life_Potion,Medium Life Potion,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ specialeffect2 320; sc_start4 SC_L_LIFEPOTION,600000,-7,4,0,0; },{},{} -14536,Abrasive,Abrasive,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ specialeffect2 182; sc_start SC_INCCRI,300000,30; },{},{} +14536,Abrasive,Abrasive,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ specialeffect2 182; sc_start SC_CRITICALPERCENT,300000,30; },{},{} 14537,Regeneration_Potion,Regeneration Potion,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ specialeffect2 348; sc_start SC_INCHEALRATE,1800000,20; },{},{} 14538,Glass_Of_Illusion,Glass of Illusion,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ specialeffect2 EF_STEAL; sc_start SC_INCFLEE2,60000,20; },{},{} 14539,Shadow_Armor_S,Shadow Armor Scroll,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ specialeffect2 EF_CLOAKING; sc_start4 SC_ELEMENTALCHANGE,1800000,1,Ele_Dark,1,0; },{},{} @@ -7202,42 +7202,42 @@ 14542,B_Def_Potion,Big Defense Potion,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ specialeffect2 EF_GUARD; sc_start SC_DEF_RATE,180000,3; },{},{} 14543,S_Mdef_Potion,Small Magic Defense Potion,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ specialeffect2 EF_SPELLBREAKER; sc_start SC_MDEF_RATE,60000,3; },{},{} 14544,B_Mdef_Potion,Big Magic Defense Potion,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ specialeffect2 EF_SPELLBREAKER; sc_start SC_MDEF_RATE,180000,3; },{},{} -14545,Battle_Manual_X3,Field Manual 300%,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_EXPBOOST,1800000,300; },{},{} +14545,Battle_Manual_X3,Field Manual 300%,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_CASH_PLUSEXP,1800000,300; },{},{} 14546,Fire_Cracker_Love,I Love You Firecracker,2,2,,20,,,,,0xFFFFFFFF,7,2,,,,,,{ end; },{},{} 14547,Fire_Cracker_Wday,Whiteday Firecracker,2,2,,20,,,,,0xFFFFFFFF,7,2,,,,,,{ end; },{},{} 14548,Fire_Cracker_Valentine,Valentine's Day Firecracker,2,2,,20,,,,,0xFFFFFFFF,7,2,,,,,,{ end; },{},{} 14549,Fire_Cracker_Bday,Birthday Firecracker,2,2,,20,,,,,0xFFFFFFFF,7,2,,,,,,{ end; },{},{} 14550,Fire_Cracker_Xmas,Xmas Firecracker,2,2,,20,,,,,0xFFFFFFFF,7,2,,,,,,{ end; },{},{} -14551,Str_Dish01_,Fried Grasshopper Legs,0,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_STRFOOD,1200000,1; percentheal 5,0; },{},{} -14552,Str_Dish02_,Seasoned Sticky Webfoot,0,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_STRFOOD,1200000,2; percentheal 5,0; },{},{} -14553,Str_Dish03_,Bomber Steak,0,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_STRFOOD,1200000,3; percentheal 5,0; },{},{} -14554,Int_Dish01_,Grape Juice Herbal Tea,0,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_INTFOOD,1200000,1; percentheal 0,5; },{},{} -14555,Int_Dish02_,Autumn Red Tea,0,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_INTFOOD,1200000,2; percentheal 0,5; },{},{} -14556,Int_Dish03_,Honey Herbal Tea,0,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_INTFOOD,1200000,3; percentheal 0,5; },{},{} -14557,Vit_Dish01_,Steamed Crab Nippers,0,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_VITFOOD,1200000,1; percentheal 5,0; },{},{} -14558,Vit_Dish02_,Assorted Seafood,0,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_VITFOOD,1200000,2; percentheal 5,0; },{},{} -14559,Vit_Dish03_,Clam Soup,0,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_VITFOOD,1200000,3; percentheal 5,0; },{},{} -14560,Agi_Dish01_,Frog Egg Squid Ink Soup,0,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_AGIFOOD,1200000,1; percentheal 3,1; },{},{} -14561,Agi_Dish02_,Smooth Noodle,0,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_AGIFOOD,1200000,2; percentheal 3,1; },{},{} -14562,Agi_Dish03_,Tentacle Cheese Gratin,0,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_AGIFOOD,1200000,3; percentheal 3,1; },{},{} -14563,Dex_Dish01_,Honey Grape Juice,0,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_DEXFOOD,1200000,1; percentheal 2,2; },{},{} -14564,Dex_Dish02_,Chocolate Mousse Cake,0,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_DEXFOOD,1200000,2; percentheal 2,2; },{},{} -14565,Dex_Dish03_,Fruit Mix,0,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_DEXFOOD,1200000,3; percentheal 2,2; },{},{} -14566,Luk_Dish01_,Fried Monkey Tails,0,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_LUKFOOD,1200000,1; percentheal 3,2; },{},{} -14567,Luk_Dish02_,Mixed Juice,0,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_LUKFOOD,1200000,2; percentheal 3,2; },{},{} -14568,Luk_Dish03_,Fried Sweet Potato,0,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_LUKFOOD,1200000,3; percentheal 4,2; },{},{} +14551,Str_Dish01_,Fried Grasshopper Legs,0,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_STR,1200000,1; percentheal 5,0; },{},{} +14552,Str_Dish02_,Seasoned Sticky Webfoot,0,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_STR,1200000,2; percentheal 5,0; },{},{} +14553,Str_Dish03_,Bomber Steak,0,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_STR,1200000,3; percentheal 5,0; },{},{} +14554,Int_Dish01_,Grape Juice Herbal Tea,0,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_INT,1200000,1; percentheal 0,5; },{},{} +14555,Int_Dish02_,Autumn Red Tea,0,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_INT,1200000,2; percentheal 0,5; },{},{} +14556,Int_Dish03_,Honey Herbal Tea,0,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_INT,1200000,3; percentheal 0,5; },{},{} +14557,Vit_Dish01_,Steamed Crab Nippers,0,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_VIT,1200000,1; percentheal 5,0; },{},{} +14558,Vit_Dish02_,Assorted Seafood,0,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_VIT,1200000,2; percentheal 5,0; },{},{} +14559,Vit_Dish03_,Clam Soup,0,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_VIT,1200000,3; percentheal 5,0; },{},{} +14560,Agi_Dish01_,Frog Egg Squid Ink Soup,0,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_AGI,1200000,1; percentheal 3,1; },{},{} +14561,Agi_Dish02_,Smooth Noodle,0,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_AGI,1200000,2; percentheal 3,1; },{},{} +14562,Agi_Dish03_,Tentacle Cheese Gratin,0,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_AGI,1200000,3; percentheal 3,1; },{},{} +14563,Dex_Dish01_,Honey Grape Juice,0,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_DEX,1200000,1; percentheal 2,2; },{},{} +14564,Dex_Dish02_,Chocolate Mousse Cake,0,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_DEX,1200000,2; percentheal 2,2; },{},{} +14565,Dex_Dish03_,Fruit Mix,0,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_DEX,1200000,3; percentheal 2,2; },{},{} +14566,Luk_Dish01_,Fried Monkey Tails,0,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_LUK,1200000,1; percentheal 3,2; },{},{} +14567,Luk_Dish02_,Mixed Juice,0,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_LUK,1200000,2; percentheal 3,2; },{},{} +14568,Luk_Dish03_,Fried Sweet Potato,0,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_LUK,1200000,3; percentheal 4,2; },{},{} 14569,Knife_Goblin_Ring,Knife Goblin Ring,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ pet 1122; },{},{} 14570,Flail_Goblin_Ring,Flail Goblin Ring,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ pet 1123; },{},{} 14571,Hammer_Goblin_Ring,Hammer Goblin Ring,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ pet 1125; },{},{} 14572,Holy_Marble,Holy Marble,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ pet 1385; },{},{} 14573,Red_Burning_Stone,Red Burning Stone,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ pet 1382; },{},{} 14574,Skull_Of_Vagabond,Vagabond's Skull,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ pet 1208; },{},{} -14575,Str_Dish05_,Lutie Lady's Pancake,0,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_STRFOOD,1200000,5; percentheal 10,0; },{},{} -14576,Int_Dish05_,Mastela Fruit Wine,0,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_INTFOOD,1200000,5; percentheal 0,10; },{},{} -14577,Vit_Dish05_,Spicy Fried Bao,0,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_VITFOOD,1200000,5; percentheal 10,0; },{},{} -14578,Agi_Dish05_,Steamed Bat Wing in Pumpkin,0,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_AGIFOOD,1200000,5; percentheal 6,2; },{},{} -14579,Dex_Dish05_,Green Salad,0,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_DEXFOOD,1200000,5; percentheal 5,5; },{},{} -14580,Luk_Dish05_,Fried Scorpion Tails,0,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_LUKFOOD,1200000,5; percentheal 5,2; },{},{} +14575,Str_Dish05_,Lutie Lady's Pancake,0,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_STR,1200000,5; percentheal 10,0; },{},{} +14576,Int_Dish05_,Mastela Fruit Wine,0,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_INT,1200000,5; percentheal 0,10; },{},{} +14577,Vit_Dish05_,Spicy Fried Bao,0,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_VIT,1200000,5; percentheal 10,0; },{},{} +14578,Agi_Dish05_,Steamed Bat Wing in Pumpkin,0,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_AGI,1200000,5; percentheal 6,2; },{},{} +14579,Dex_Dish05_,Green Salad,0,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_DEX,1200000,5; percentheal 5,5; },{},{} +14580,Luk_Dish05_,Fried Scorpion Tails,0,2,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_FOOD_LUK,1200000,5; percentheal 5,2; },{},{} 14581,Dun_Tele_Scroll2,Dungeon Teleport Scroll II,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ callfunc "F_CashDungeon"; },{},{} 14582,WOB_Rune,Yellow Butterfly Wing,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ callfunc "F_CashCity",1; },{},{} 14583,WOB_Schwaltz,Green Butterfly Wing,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ callfunc "F_CashCity",2; },{},{} @@ -7249,7 +7249,7 @@ 14589,Pty_Inc_Agi_Scroll,Party Increase Agi 10 Scroll,11,10,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ itemskill "CASH_INCAGI",10; },{},{} 14590,Pty_Assumptio_Scroll,Party Assumptio 5 Scroll,11,10,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ itemskill "CASH_ASSUMPTIO",5; },{},{} 14591,Siege_Teleport_Scroll,WoE Teleport Scroll,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ callfunc "F_CashSeigeTele"; },{},{} -14592,Job_Manual50,JOB Battle Manual,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_JEXPBOOST,1800000,50; },{},{} +14592,Job_Manual50,JOB Battle Manual,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_CASH_PLUSONLYJOBEXP,1800000,50; },{},{} 14593,Magic_Power_Scroll,Mystical Amplification Scroll,11,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ itemskill "HW_MAGICPOWER",10; },{},{} 14594,Quagmire_Scroll,Quagmire Scroll,11,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ itemskill "WZ_QUAGMIRE",5; },{},{} 14595,Unsealed_Magic_Spell,Unsealed Magic Spell,2,0,,0,,,,,0xFFFFFFFF,7,2,,,,,,{ warp "yuno_fild09",255,127; },{},{} @@ -7258,7 +7258,7 @@ 14598,GhostringS,Ghostring Scroll,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_ITEMSCRIPT,60000,4047; },{},{} 14599,Greed_Scroll_C,Greed Scroll,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{},{},{} 14600,Mental_Potion,Mental Potion,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{},{},{} -14601,Tyr's_Blessing,Tyr's Blessing,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_INCFLEE,300000,30; sc_start SC_INCHIT,300000,30; sc_start SC_ATKPOTION,300000,20; sc_start SC_MATKPOTION,300000,20; },{},{} +14601,Tyr's_Blessing,Tyr's Blessing,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_INCFLEE,300000,30; sc_start SC_INCHIT,300000,30; sc_start SC_PLUSATTACKPOWER,300000,20; sc_start SC_PLUSMAGICPOWER,300000,20; },{},{} 14602,TaogunkaS,Tao Gunka Scroll,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_ITEMSCRIPT,180000,4302; },{},{} 14603,MistressS,Mistress Scroll,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_ITEMSCRIPT,180000,4132; },{},{} 14604,Orc_HeroS,Orc Hero Scroll,2,0,,10,,,,,0xFFFFFFFF,7,2,,,,,,{ sc_start SC_ITEMSCRIPT,60000,4143; },{},{} diff --git a/db/re/refine_db.txt b/db/re/refine_db.txt index 421a1bdbc..3dad5be78 100644 --- a/db/re/refine_db.txt +++ b/db/re/refine_db.txt @@ -27,15 +27,14 @@ // Chance: // 100 = 100% // -// Note: Chances for +11 and higher are not verified - 10% is a rumor from iRO wiki. // A note about renewal Armors, there may or may not be another bonus, according to iRO wiki: Every upgrade gives floor[( 3 + current upgrade ) / 4] equipment DEF) 0,0,0,0,100:100,100:100,100:100,100:100,60:200,40:200,40:200,20:200,20:300,10:300,50:300,30:300,30:400,20:400,10:400,10:400,10:500,10:500,10:500,10:500 // Level 1 weapons -1,200,8,300,100:0,100:0,100:0,100:0,100:0,100:0,100:0,60:0,40:0,20:0,70:0,70:0,50:0,50:0,30:0,30:300,20:300,20:300,10:300,10:300 +1,200,8,300,100:0,100:0,100:0,100:0,100:0,100:0,100:0,60:0,40:0,20:0,90:0,80:0,80:0,70:0,70:0,60:300,60:300,40:300,20:300,20:300 // Level 2 weapons -2,300,7,500,100:0,100:0,100:0,100:0,100:0,100:0,60:0,40:0,20:0,20:0,70:0,50:0,50:0,30:0,30:0,20:600,20:600,10:600,10:600,10:600 +2,300,7,500,100:0,100:0,100:0,100:0,100:0,100:0,60:0,40:0,20:0,20:0,80:0,80:0,70:0,70:0,60:0,60:600,50:600,20:600,20:600,20:600 // Level 3 weapons -3,500,6,800,100:0,100:0,100:0,100:0,100:0,60:0,50:0,20:0,20:0,20:0,50:0,50:0,30:0,30:0,20:0,20:900,10:900,10:900,10:900,10:900 +3,500,6,800,100:0,100:0,100:0,100:0,100:0,60:0,50:0,20:0,20:0,20:0,80:0,70:0,70:0,60:0,60:0,40:900,40:900,20:900,20:900,10:900 // Level 4 weapons 4,700,5,1400,100:0,100:0,100:0,100:0,60:0,40:0,40:0,20:0,20:0,10:0,50:0,30:0,30:0,20:0,20:0,10:1200,10:1200,10:1200,10:1200,10:1200 diff --git a/db/re/skill_cast_db.txt b/db/re/skill_cast_db.txt index ef34d230a..5766f5217 100644 --- a/db/re/skill_cast_db.txt +++ b/db/re/skill_cast_db.txt @@ -1085,16 +1085,16 @@ 2006,1000,0,0,0,0,2000,-1 //-- RK_DRAGONBREATH -2008,0:0:0:1000:1000:1000:1500:1500:2000:2000,2000,0,10000,0,0,500 +2008,0:0:0:1000:1000:1000:1500:1500:2000:2000,2000,0,42000,0,0,500 //-- RK_DRAGONHOWLING 2009,0,0,0,15000,0,10000,-1 //-- RK_MILLENNIUMSHIELD -2011,0,1000,0,180000,0,60000,-1 +2011,0,1000,0,180000,60000,0,-1 //-- RK_CRUSHSTRIKE -2012,0,0,0,30000,0,30000,1000 +2012,0,0,0,180000,30000,0,1000 //-- RK_REFRESH -2013,0,0,0,60000,0,120000,1000 +2013,0,0,0,60000,120000,0,1000 //-- RK_GIANTGROWTH 2014,0,0,0,180000,0,0,1000 //-- RK_STONEHARDSKIN @@ -1107,6 +1107,8 @@ 2018,0,0,0,180000,0,0,-1 //-- RK_ABUNDANCE 2019,0,0,0,180000,0,0,-1 +//-- RK_DRAGONBREATH_WATER +5004,0:0:0:1000:1000:1000:1500:1500:2000:2000,2000,0,40000,0,0,500 //========================================== //===== Gillotine Cross ==================== @@ -1141,6 +1143,8 @@ 2036,0,200,0,3000,0,0,-1 //-- GC_CROSSRIPPERSLASHER 2037,0,1000,0,0,0,0,-1 +//-- GC_DARKCROW +5001,0,1500,0,5000,0,0,-1 //========================================== //===== Arch Bishop ======================== @@ -1180,6 +1184,8 @@ //-- AB_SILENTIUM 2057,4000,0,0,20000:30000:40000:50000:60000,0,15000,-1 +//-- AB_OFFERTORIUM +5011,4000,0,0,90000,0,0,-1 //========================================== //===== Warlock ============================ @@ -1197,7 +1203,6 @@ 2206,1000,1000,0,60000:90000:120000:150000:180000,0,50000:80000:110000:140000:170000,1000 //-- WL_SIENNAEXECRATE 2207,2000,2000,0,10000:12000:14000:16000:18000,0,0,-1 - //-- WL_STASIS 2209,3000,1000,0,10000:15000:20000:25000:30000,0,300000,1000 //-- WL_DRAINLIFE @@ -1205,17 +1210,15 @@ //-- WL_CRIMSONROCK 2211,5000,2000,0,3000:4000:5000:6000:7000,0,5000,2000 //-- WL_HELLINFERNO -2212,3000,1000,0,15000,0,0,1000 +2212,3000,1000,0,42000,0,0,1000 //-- WL_COMET -2213,10000:11000:12000:13000:14000,0,0,15000,0,60000,1000:1500:2000:2500:3000 +2213,10000:11000:12000:13000:14000,0,0,100,42000,60000,1000:1500:2000:2500:3000 //-- WL_CHAINLIGHTNING 2214,3500:4000:4500:5000:5500,0,0,100,0,3000,1000 - //-- WL_EARTHSTRAIN -2216,2000:3000:4000:5000:6000,1000,0,150,75000:90000:105000:120000:135000,10000,2000 +2216,2000:3000:4000:5000:6000,1000,0,100,75000:90000:105000:120000:135000,10000,2000 //-- WL_TETRAVORTEX -2217,5000:6000:7000:8000:9000,2000,0,20000,0,15000,2000 - +2217,5000:6000:7000:8000:9000,2000,0,15000:120000:40000:5000,0,15000,2000 //-- WL_SUMMONFB 2222,2000,0,0,120000:160000:200000:240000:280000,0,0,-1 //-- WL_SUMMONBL @@ -1224,9 +1227,10 @@ 2224,2000,0,0,120000:160000:200000:240000:280000,0,0,-1 //-- WL_SUMMONSTONE 2229,2000,0,0,120000:160000:200000:240000:280000,0,0,-1 - //-- WL_READING_SB 2231,5000,500,0,0,0,0,1000 +//-- WL_TELEKINESIS_INTENSE +5012,1000,0,0,180000,0,0,-1 //========================================== //===== Ranger ============================= @@ -1268,6 +1272,8 @@ 2253,0,0,0,20000,15000,0,-1 //-- RA_ICEBOUNDTRAP 2254,0,0,0,20000,15000,0,-1 +//-- RA_UNLIMIT +5002,0,0,0,60000,0,0,-1 //========================================== //===== Mechanic =========================== @@ -1323,6 +1329,8 @@ 2282,0,0,0,20000:30000:40000:50000:60000,0,0,1800:1600:1400:1200:1000 //-- NC_DISJOINT 2283,2000,0,0,0,0,0,-1 +//-- NC_MAGMA_ERUPTION +5006,1000,0,0,10000,42000,0,-1 //========================================== //===== Shadow Chaser ====================== @@ -1368,6 +1376,8 @@ 2303,2000,2000,0,10000:20000:30000,0,180000,-1 //-- SC_FEINTBOMB 2304,1000,0,0,1000,0,5000,-1 +//-- SC_SCAPE +5010,1000,0,0,1000,0,5000,-1 //========================================== //==== Royal Guard skills ================== @@ -1408,6 +1418,8 @@ 2324,1000,3000,0,0,0,20000,0 //-- LG_INSPIRATION 2325,2000,2000,0,30000:45000:60000:75000:90000,0,540000:480000:420000:360000:300000,1000 +//-- LG_KINGS_GRACE +5013,1000,0,0,5000,0,0,-1 //========================================== //===== Sura Skills ======================== @@ -1454,6 +1466,9 @@ 2347,1000,1000,0,240000,0,200000:180000:160000:140000:120000,1000 //-- SR_GENTLETOUCH_REVITALIZE 2348,1000,1000,0,240000,0,200000:180000:160000:140000:120000,1000 +//-- SR_FLASHCOMBO +2348,0,4000,0,0,0,0,-1 + //========================================== //==== Wanderer skills ===================== @@ -1516,6 +1531,8 @@ 2433,1000,1000,0,20000:30000:40000:50000:60000,0,180000,500 //-- WM_UNLIMITED_HUMMING_VOICE 2434,1000,1000,0,60000:90000:120000:150000:180000,0,110000:120000:130000:140000:150000,500 +//-- WM_FRIGG_SONG +5007,0,0,0,60000,0,0,0 //========================================== //==== Sorcerer skills ===================== @@ -1639,57 +1656,59 @@ //-- KO_YAMIKUMO 3001,0,0,0,60000,0,0,-1 //-- KO_JYUMONJIKIRI -3004,0,2500,0,5000,0,0,-1 +3004,0,500,0,3000,0,5000,-1 //-- KO_SETSUDAN -3005,0,2000,0,0,0,0,-1 +3005,0,0,0,0,0,3000,-1 //-- KO_BAKURETSU -3006,1000:1500:2000:2500:3000,1000,0,100,0,3000,0 +3006,1000:1400:1800:2200:2600,1000,0,100,0,3000,-1 //-- KO_HAPPOKUNAI -3007,0,1000,0,0,0,0,-1 +3007,0,500,0,0,0,0,-1 //-- KO_MUCHANAGE -3008,0,0,0,100,0,10000,-1 +3008,1000,0,0,100,0,10000,0 //-- KO_HUUMARANKA -3009,0,3000,0,500,0,0,-1 +3009,1000:1200:1400:1600:1800,1000,0,500,0,3000,-1 //-- KO_MAKIBISHI -3010,0,0,0,12000:14000:16000:18000:20000,10000,0,-1 +3010,0,0,0,12000:14000:16000:18000:20000,10000,10000,-1 //-- KO_MEIKYOUSISUI -3011,3000,0,0,10000,0,0,0 +3011,3000,0,0,10000,0,10000,-1 //-- KO_ZANZOU -3012,0,0,0,27000:24000:21000:18000:15000,0,0,-1 +3012,0,1000,0,30000:27000:24000:21000:18000,0,0,-1 //-- KO_KYOUGAKU -3013,1000,0,0,12000:14000:16000:18000:20000,0,0,0 +3013,3000:2500:2000:1500:1000,1000,0,12000:14000:16000:18000:20000,0,0,-1 //-- KO_JYUSATSU -3014,1000,0,0,8000:10000:12000:14000:16000,0,0,0 +3014,3000:2500:2000:1500:1000,1000,0,8000:10000:12000:14000:16000,0,10000,-1 //-- KO_KAHU_ENTEN -3015,500,0,0,300000,0,0,0 +3015,2000,0,0,300000,0,0,-1 //-- KO_HYOUHU_HUBUKI -3016,500,0,0,300000,0,0,0 +3016,2000,0,0,300000,0,0,-1 //-- KO_KAZEHU_SEIRAN -3017,500,0,0,300000,0,0,0 +3017,2000,0,0,300000,0,0,-1 //-- KO_DOHU_KOUKAI -3018,500,0,0,300000,0,0,0 -//-- KO_KAIHOU -3019,1000,0,0,0,0,0,0 +3018,2000,0,0,300000,0,0,-1 //-- KO_ZENKAI -3020,1000,0,0,10000,10000,0,0 +3020,0,1000,0,10000,10000,0,0 //-- KO_GENWAKU -3021,500,0,0,5000,0,0,0 +3021,3000:2500:2000:1500:1000,1000,0,5000,0,10000,-1 //-- KO_IZAYOI 3022,0,0,0,30000:45000:60000:75000:90000,0,60000,-1 //-- KG_KAGEHUMI -3023,0,0,0,5000,0,5000,-1 +3023,0,0,0,5000:6000:7000:8000:9000,0,0,-1 //-- KG_KYOMU -3024,0,0,0,10000:15000:20000:25000:30000,0,0,-1 +3024,0,1000,0,10000:15000:20000:25000:30000,0,20000,-1 //-- KG_KAGEMUSYA 3025,0,0,0,60000:90000:120000:150000:180000,0,0,-1 + //-- OB_ZANGETSU -3026,0,0,0,60000:75000:90000:105000:120000,0,0,-1 +3026,1000:1500:2000:2500:3000,1000,0,60000:75000:90000:105000:120000,0,30000,2000 //-- OB_OBOROGENSOU -3027,0,0,0,10000:15000:20000:25000:30000,0,0,-1 +3027,1000,0,0,10000:15000:20000:25000:30000,0,15000,0 //-- OB_AKAITSUKI -3029,0,0,0,10000:15000:20000:25000:30000,0,0,-1 +3029,1000:1500:2000:2500:3000,1000,0,10000:15000:20000:25000:30000,0,30000,2000 //========================================== +//-- ALL_FULL_THROTTLE +5014,0,0,0,10000:15000:20000:25000:30000,10000,20000:25000:30000:35000:40000,-1 + //===== Homunculus Skills ================== //-- HLIF_HEAL 8001,0,2000,0,0,0,0,-1 diff --git a/db/re/skill_db.txt b/db/re/skill_db.txt index f6da92528..e472626d4 100644 --- a/db/re/skill_db.txt +++ b/db/re/skill_db.txt @@ -9,8 +9,8 @@ // -2 - use endowed element, -3 - use random element.) // 06 nk (skill damage properties): // 0x01 - No damage skill -// 0x02 - Has splash area (requires source modification) -// 0x04 - Damage should be split among targets (requires 0x02 in order to work) +// 0x02 - Has splash area +// 0x04 - Damage should be split among targets // 0x08 - Skill ignores caster's % damage cards (misc type always ignores) // 0x10 - Skill ignores elemental adjustments // 0x20 - Skill ignores target's defense (misc type always ignores) @@ -91,7 +91,7 @@ 44,0,0,0,0,0,0,10,0,no,0,0,0,none,0, AC_VULTURE,Vulture's Eye 45,0,6,4,0,0x3,3,10,1,no,0,0,0,weapon,0, AC_CONCENTRATION,Improve Concentration 46,-9,8,1,-1,0,0,10,2,no,0,0,0,weapon,0, AC_DOUBLE,Double Strafe -47,-9,6,2,-1,0x2,2,10,1,no,0,0x2000,0,weapon,2, AC_SHOWER,Arrow Shower +47,-9,6,2,-1,0x2,2:2:2:2:2:3:3:3:3:3,10,1,no,0,0x2000,0,weapon,2, AC_SHOWER,Arrow Shower 48,-1,8,0,-1,0,0,10,2,no,0,0,0,weapon,0, TF_DOUBLE,Double Attack 49,0,0,0,0,0,0,10,0,no,0,0,0,weapon,0, TF_MISS,Improve Dodge 50,1,6,1,0,1,0,10,1,no,0,0,0,weapon,0, TF_STEAL,Steal @@ -422,7 +422,7 @@ 376,0,0,0,0,0x1,0,5,1,no,0,0,0,weapon,0, ASC_KATAR,Advanced Katar Mastery //377,0,0,4,0,0x1,0,10,1,no,0,0,0,misc,0, ASC_HALLUCINATION,Hallucination Walk 378,0,6,4,5,0x1,0,5,1,no,0,0,0,weapon,0, ASC_EDP,Enchant Deadly Poison -379,7,6,1,-1,0x8,0,10,1,yes,0,0,0,weapon,0, ASC_BREAKER,Soul Destroyer +379,7,6,1,-1,0x40,0,10,1,yes,0,0,0,misc,0, ASC_BREAKER,Soul Destroyer 380,0,6,4,0,0x1,0,10,1,no,0,0,0,weapon,0, SN_SIGHT,Falcon Eyes 381,5,8,1,0,0x40,0,5,1,yes,0,0,0,misc,0, SN_FALCONASSAULT,Falcon Assault 382,9,8,1,-1,0,2,5,1,yes,0,0,13,weapon,0, SN_SHARPSHOOTING,Focused Arrow Strike @@ -533,7 +533,7 @@ 487,0,6,4,0,0x1,0,5,1,no,0,0,0,none,0, CG_LONGINGFREEDOM,Longing for Freedom 488,0,6,4,0,0x1,1,5,1,no,0,0x40,0,misc,0, CG_HERMODE,Wand of Hermode 489,9,6,1,0,0x41,0,5,1,no,0,0,0,misc,0, CG_TAROTCARD,Tarot Card of Fate -490,9,8,1,0,0x40,0,10,1:2:3:4:5:6:7:8:9:10,yes,0,0,0,misc,0, CR_ACIDDEMONSTRATION,Acid Demonstration +490,9,8,1,0,0x40,0,10,-1:-2:-3:-4:-5:-6:-7:-8:-9:-10,yes,0,0,0,misc,0, CR_ACIDDEMONSTRATION,Acid Demonstration 491,1,6,2,0,0x1,0,2,1,no,0,0,0,none,0, CR_CULTIVATION,Plant Cultivation 492,0,6,4,0:1:2:3:4:5:6:7:8:9,0x1,0,10,1,no,0,0x2,0,none,0, ITEM_ENCHANTARMS,Weapon Enchantment 493,0,6,4,0,0x1,0,1,1,no,0,0,0,none,0, TK_MISSION,Taekwon Mission @@ -672,7 +672,7 @@ 1003,0,0,0,0,0,0,1,0,no,0,0x1,0,weapon,0, AS_SONICACCEL,Sonic Acceleration 1004,9,8,1,0,0x8,0,1,1,no,0,0x1,0,weapon,0, AS_VENOMKNIFE,Throw Venom Knife 1005,1,6,1,0,0x1,0,1,1,no,0,0x1,0,weapon,0, RG_CLOSECONFINE,Close Confine -1006,0,6,4,3,0,2,1,1,yes,0,0x1,0,magic,3, WZ_SIGHTBLASTER,Sight Blaster +1006,0,6,4,3,0,1,1,1,yes,0,0x1,0,magic,3, WZ_SIGHTBLASTER,Sight Blaster 1007,0,6,4,0,0x1,0,1,0,no,0,0x1,0,none,0, SA_CREATECON,Create Elemental Converter 1008,9,6,1,1,0x1,0,1,1,yes,0,0x1,0,magic,0, SA_ELEMENTWATER,Elemental Change Water 1009,-9,6,1,0,0,0,1,1,no,0,0x1,0,weapon,3, HT_PHANTASMIC,Phantasmic Arrow @@ -692,15 +692,15 @@ //**** 2001,0,6,4,0,0x1,0,5,1,yes,0,0,0,none,0, RK_ENCHANTBLADE,Enchant Blade 2002,7:8:9:10:11,6,1,-1,0,0,5,1,no,0,0,0,weapon,0, RK_SONICWAVE,Sonic Wave -2003,0,6,4,0,0x1,0,10,1,no,0,0,0,weapon,0, RK_DEATHBOUND,Death Bound +2003,0,6,4,0,0x1,0,10,1,no,0,0,0,weapon,3, RK_DEATHBOUND,Death Bound 2004,1,8,1,-1,0,0,10,-5,no,0,0,0,weapon,0, RK_HUNDREDSPEAR,Hundred Spear 2005,1,6,2,4,0x2,2,5,1,no,0,0,0,weapon,3, RK_WINDCUTTER,Wind Cutter 2006,0,6,4,-1,0x2,5,5,1,no,0,0,0,weapon,0, RK_IGNITIONBREAK,Ignition Break 2007,0,0,0,0,0,0,5,0,no,0,0,0,weapon,0, RK_DRAGONTRAINING,Dragon Training 2008,9,6,2,3,0xC2,1:1:1:2:2:2:3:3:4:4,10,1,no,0,0,0,misc,0, RK_DRAGONBREATH,Dragon Breath -2009,0,6,4,0,0x3,3:4:5:6:7,5,1,no,0,0,0,none,0, RK_DRAGONHOWLING,Dragon Howling +2009,0,6,4,0,0x3,3:4:5:6:7,5,1,yes,0,0,0,none,0, RK_DRAGONHOWLING,Dragon Howling 2010,0,0,0,0,0,0,10,0,no,0,0,0,none,0, RK_RUNEMASTERY,Rune Mastery -2011,0,6,4,0,0x1,0,1,1,no,0,0,0,none,0, RK_MILLENNIUMSHIELD,Millenium Shield +2011,0,6,4,0,0x1,0,1,1,yes,0,0,0,none,0, RK_MILLENNIUMSHIELD,Millenium Shield 2012,1,6,4,-1,0,0x8,1,1,yes,0,0,0,weapon,0, RK_CRUSHSTRIKE,Crush Strike 2013,0,6,4,0,0x1,0,1,1,yes,0,0,0,none,0, RK_REFRESH,Refresh 2014,0,6,4,0,0x1,0,1,1,yes,0,0,0,none,0, RK_GIANTGROWTH,Giant Growth @@ -709,7 +709,7 @@ 2017,0,6,4,-1,0x2,3,1,1,no,0,0,0,weapon,7, RK_STORMBLAST,Storm Blast 2018,0,6,4,0,0x3,-1,1,1,yes,0,0,0,none,0, RK_FIGHTINGSPIRIT,Fighting Spirit //CHECK Is this splash needed? 2019,9,6,4,6,0x1,0,1,1,yes,0,0,0,none,0, RK_ABUNDANCE,Abundance -2020,5:6:7:8:9,6,16,-1,0,0,5,1,no,0,0,0,weapon,0, RK_PHANTOMTHRUST,Phantom Thrust +2020,5:6:7:8:9,6,1,-1,0,0,5,1,yes,0,0,0,weapon,0, RK_PHANTOMTHRUST,Phantom Thrust //**** // GC Guillotine Cross @@ -771,8 +771,8 @@ 2210,11,6,1,0,0,0,5,1,yes,0,0,0,magic,0, WL_DRAINLIFE,Drain Life 2211,11,8,1,3,0x2,3,5,-7,yes,0,0,0,magic,3, WL_CRIMSONROCK,Crimson Rock 2212,11,6,1,3,0,0,5,1,yes,0,0,0,magic,0, WL_HELLINFERNO,Hell Inferno -2213,11,8,2,0,0x2,7,5,-20,yes,0,0,0,magic,2, WL_COMET,Comet -2214,11,6,1,0,0,3,5,1,yes,0,0,0,magic,0, WL_CHAINLIGHTNING,Chain Lightning //CHECK Is the splash being used for the target search? +2213,11,8,2,0,0,0,5,-20,yes,0,0,0,magic,2, WL_COMET,Comet +2214,11,6,1,0,0,3,5,1,yes,0,0,0,magic,0, WL_CHAINLIGHTNING,Chain Lightning 2215,11,6,1,4,0,0,5,1,no,0,0,0,magic,0, WL_CHAINLIGHTNING_ATK,Chain Lightning Attack 2216,3,8,2,2,0,0,5,-6:-7:-8:-9:-10,yes,0,0,0,magic,0, WL_EARTHSTRAIN,Earth Strain 2217,11,6,1,0,0,0,5,1,yes,0,0,0,magic,0, WL_TETRAVORTEX,Tetra Vortex @@ -783,12 +783,12 @@ 2222,0,6,4,3,0x1,0,5,1,yes,0,0,0,magic,0, WL_SUMMONFB,Summon Fire Ball 2223,0,6,4,4,0x1,0,5,1,yes,0,0,0,magic,0, WL_SUMMONBL,Summon Lightning Ball 2224,0,6,4,1,0x1,0,5,1,yes,0,0,0,magic,0, WL_SUMMONWB,Summon Water Ball -2225,11,6,1,3,0,0,5,1,no,0,0,1,magic,0, WL_SUMMON_ATK_FIRE,Summon Attack Fire //CHECK Summon attack ID's dont appear to have a range. +2225,11,6,1,3,0,0,5,1,no,0,0,1,magic,0, WL_SUMMON_ATK_FIRE,Summon Attack Fire 2226,11,6,1,4,0,0,5,1,no,0,0,1,magic,0, WL_SUMMON_ATK_WIND,Summon Attack Wind 2227,11,6,1,1,0,0,5,1,no,0,0,1,magic,0, WL_SUMMON_ATK_WATER,Summon Attack Water 2228,11,6,1,2,0,0,5,1,no,0,0,1,magic,0, WL_SUMMON_ATK_GROUND,Summon Attack Earth 2229,0,6,4,2,0x1,0,5,1,yes,0,0,0,magic,0, WL_SUMMONSTONE,Summon Stone -2230,11,8,1,0,0,0,2,1,yes,0,0,0,magic,0, WL_RELEASE,Release //CHECK Should it be left to do multi hit or single hit? +2230,11,6,1,0,0,0,2,1,yes,0,0,0,magic,0, WL_RELEASE,Release 2231,0,6,4,0,0x1,0,1,1,yes,0,0,0,magic,0, WL_READING_SB,Reading Spellbook 2232,0,0,0,0,0,0,5,0,no,0,0,0,none,0, WL_FREEZE_SP,Freeze Spell @@ -1048,18 +1048,18 @@ 3005,2,6,1,-1,0,0,5,1,no,0,0,0,weapon,0, KO_SETSUDAN,Soul Sever 3006,7:8:9:10:11,6,2,0,0x2,2,5,0,no,0,0,0,weapon,0, KO_BAKURETSU,Bakuretsu Kunai 3007,0,6,4,-1,0x42,4:4:4:4:5,5,0,no,0,0,0,misc,0, KO_HAPPOKUNAI,Happo Kunai -3008,9,8,2,0,0x52,2,10,-10,no,0,0,0,misc,0, KO_MUCHANAGE,Mucha Nage +3008,9,8,2,0,0x12,2,10,-10,no,0,0,0,misc,0, KO_MUCHANAGE,Mucha Nage 3009,9:10:11:12:13,8,2,-1,0x2,3,5,2,no,0,0,0,weapon,0, KO_HUUMARANKA,Huuma Shuriken Ranka -3010,3,6,4,0,0x43,0,5,1,no,0,0x80,0,misc,0, KO_MAKIBISHI,Makibishi +3010,3,6,4,0,0x42,0,5,1,no,0,0x80,0,weapon,0, KO_MAKIBISHI,Makibishi 3011,0,6,4,0,0x1,0,5,0,yes,0,0,0,none,0, KO_MEIKYOUSISUI,Meikyo Shisui -3012,0,6,4,0,0x1,0,5,0,no,0,0,1,none,7, KO_ZANZOU,Zanzou +3012,0,6,4,0,0x1,0,5,0,no,0,0,1,none,3:4:5:6:7, KO_ZANZOU,Zanzou 3013,5,6,1,0,0x1,0,5,0,no,0,0,0,none,0, KO_KYOUGAKU,Kyougaku 3014,5,6,1,0,0x1,0,5,0,no,0,0,0,none,0, KO_JYUSATSU,Jyusatsu 3015,0,6,4,3,0x1,0,1,1,no,0,0,0,none,0, KO_KAHU_ENTEN,Kahu Enten 3016,0,6,4,1,0x1,0,1,1,no,0,0,0,none,0, KO_HYOUHU_HUBUKI,Hyouhu Hubuki 3017,0,6,4,4,0x1,0,1,1,no,0,0,0,none,0, KO_KAZEHU_SEIRAN,Kazehu Seiran 3018,0,6,4,2,0x1,0,1,1,no,0,0,0,none,0, KO_DOHU_KOUKAI,Dohu Koukai -3019,11,6,1,0,0,0,5,0,no,0,0,0,weapon,0, KO_KAIHOU,Technique Kaihou +3019,11,6,1,0,0,0,5,0,no,0,0,0,magic,0, KO_KAIHOU,Technique Kaihou 3020,7,6,2,0,0,0,1,3,yes,0,0,0,magic,0, KO_ZENKAI,Zenkai 3021,5:6:7:8:9,6,16,0,0x1,0,5,1,no,0,0,0,none,0, KO_GENWAKU,Genwaku 3022,0,6,4,0,0x1,0,5,0,no,0,0,0,none,0, KO_IZAYOI,Izayoi @@ -1079,45 +1079,25 @@ 3035,0,6,4,0,0x1,0,1,1,no,0,0,0,none,0, ECLAGE_RECALL,Return To Eclage // EP 14.3 Part 2 3rd Job Skills -//5001,0,0,22:34:46:58:70,0,0,0,99,0,0,none,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0 //GC_DARKCROW#Dark Claw# -//5002,0,0,100:120:140:160:180,0,0,0,99,0,0,none,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0 //RA_UNLIMIT#Unlimited# -//5003,0,0,60:70:80:90:100,0,0,0,99,0,0,none,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0 //GN_ILLUSIONDOPING#Illusion Doping# -//5004,0,0,30:35:40:45:50:55:60:65:70:75,0,0,0,99,0,0,none,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0 //RK_DRAGONBREATH_WATER#Dragon Breath - Water# -//5005,0,0,1,0,0,0,99,0,0,none,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0 //RK_LUXANIMA#Lux Anima# -//5006,0,0,60:70:80:90:100,0,0,0,99,0,0,none,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0 //NC_MAGMA_ERUPTION#Magma Eruption# -//5007,0,0,200:230:260:290:320,0,0,0,99,0,0,none,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0 //WM_FRIGG_SONG#Frigg's Song# -//5008,0,0,120:120:120:120:120,0,0,0,99,0,0,none,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0 //SO_ELEMENTAL_SHIELD#Elemental Shield# -//5009,0,0,75:65:55:45:35,0,0,0,99,0,0,none,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0 //SR_FLASHCOMBO#Flash Combo# -//5010,0,0,30:26:22:18:14,0,0,0,99,0,0,none,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0 //SC_ESCAPE#Emergency Escape# -//5011,0,0,30:60:90:120:150,0,0,0,99,0,0,none,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0 //AB_OFFERTORIUM#Offertorium# -//5012,0,0,100:150:200:250:300,0,0,0,99,0,0,none,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0 //WL_TELEKINESIS_INTENSE#Intense Telekinesis# -//5013,0,0,200:180:160:140:120,0,0,0,99,0,0,none,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0 //LG_KINGS_GRACE#King's Grace# -//5014,0,0,1:1:1:1:1,0,0,0,99,0,0,none,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0 //ALL_FULL_THROTTLE#Full Throttle# -//5015,0,0,1,0,0,0,99,0,0,none,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0 //SR_FLASHCOMBO_ATK_STEP1#Flash Combo Attack Step 1#//All 4 steps are using temp req SP values for now. -//5016,0,0,1,0,0,0,99,0,0,none,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0 //SR_FLASHCOMBO_ATK_STEP2#Flash Combo Attack Step 2# -//5017,0,0,1,0,0,0,99,0,0,none,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0 //SR_FLASHCOMBO_ATK_STEP3#Flash Combo Attack Step 3# -//5018,0,0,1,0,0,0,99,0,0,none,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0 //SR_FLASHCOMBO_ATK_STEP4#Flash Combo Attack Step 4# - - -// EP 14.3 Part 2 3rd Job Skills -//5001,1,6,1,-1,0,0,5,1,no,0,0,0,weapon,0, GC_DARKCROW,Dark Claw -//5002,0,6,4,0,0x1,0,5,1,no,0,0,0,none,0, RA_UNLIMIT,Unlimited -//5003,7,6,1,-1,0x2,4:5:6:7:8,5,1,no,0,0,0,weapon,0,GN_ILLUSIONDOPING,Illusion Doping -//5004,9,6,2,1,0x2,1:1:1:2:2:2:3:3:4:4,10,1,no,0,0,0,weapon,0, RK_DRAGONBREATH_WATER,Dragon Breath - Water +5001,1,6,1,-1,0,0,5,1,no,0,0,0,weapon,0, GC_DARKCROW,Dark Claw +5002,0,6,4,0,0x1,0,5,1,no,0,0,0,none,0, RA_UNLIMIT,Unlimited +//5003,7,6,1,-1,0x2,4:5:6:7:8,5,1,no,0,0,0,weapon,0, GN_ILLUSIONDOPING,Illusion Doping +5004,9,6,2,1,0x2,1:1:1:2:2:2:3:3:4:4,10,1,no,0,0,0,misc,0, RK_DRAGONBREATH_WATER,Dragon Breath - Water //5005,0,6,4,0,0x3,3,1,1,no,0,0,0,none,0, RK_LUXANIMA,Lux Anima -//5006,1,6,2,3,0,0,5,1,no,0,0,3,misc,0, NC_MAGMA_ERUPTION,Magma Eruption -//5007,0,6,4,0,0x3,5:6:7:8:9,5,1,no,0,0,0,none,0, WM_FRIGG_SONG,Frigg's Song +5006,1,6,2,3,0,0,5,1,no,0,0,3,misc,0, NC_MAGMA_ERUPTION,Magma Eruption +5007,0,6,4,0,0x3,5:6:7:8:9,5,1,no,0,0,0,none,0, WM_FRIGG_SONG,Frigg's Song //5008,0,6,4,0,0x3,15,5,1,no,0,0,0,none,0, SO_ELEMENTAL_SHIELD,Elemental Shield -//5009,1,6,1,0,0x1,0,5,1,no,0,0,0,none,0, SR_FLASHCOMBO,Flash Combo//I can mark this as a no damage skill right? -//5010,0,6,4,0,0x1,0,5,1,no,0,0,0,none,0, SC_ESCAPE,Emergency Escape//Said places a ankle snare trap. Must confirm before I remove the no damage thing. -//5011,0,6,4,0,0x1,0,5,1,no,0,0,0,none,0, AB_OFFERTORIUM,Offertorium -//5012,0,6,4,0,0x1,0,5,1,no,0,0,0,none,0, WL_TELEKINESIS_INTENSE,Intense Telekinesis -//5013,0,6,4,0,0x3,5,5,1,no,0,0,0,none,0, LG_KINGS_GRACE,King's Grace//Need to know the splash AoE -//5014,0,6,4,0,0x1,0,5,1,no,0,0,0,none,0, ALL_FULL_THROTTLE,Full Throttle -//5015,-2,8,4,-1,0,0,10,-2,no,0,0x200,0,weapon,0, SR_FLASHCOMBO_ATK_STEP1,Flash Combo Attack Step 1//Dragon Combo -//5016,-2,8,4,-1,0,0,5,-2,no,0,0x200,0,weapon,0, SR_FLASHCOMBO_ATK_STEP2,Flash Combo Attack Step 2//Fallen Empire -//5017,-2,6,4,-1,0x42,1:1:1:1:1:2:2:2:2:2,10,1,no,0,0x200,0,weapon,0, SR_FLASHCOMBO_ATK_STEP3,Flash Combo Attack Step 3//Tiger Cannon -//5018,0,8,4,-1,0x2,2,5,-3,no,0,0,0,weapon,0, SR_FLASHCOMBO_ATK_STEP4,Flash Combo Attack Step 4//Skynet Blow +5009,1,6,1,0,0x1,0,5,1,no,0,0,0,none,0, SR_FLASHCOMBO,Flash Combo +//5010,0,6,4,0,0x1,0,5,1,no,0,0,0,none,0, SC_ESCAPE,Emergency Escape +5011,0,6,4,0,0x1,0,5,1,no,0,0,0,none,0, AB_OFFERTORIUM,Offertorium +5012,0,6,4,0,0x1,0,5,1,no,0,0,0,none,0, WL_TELEKINESIS_INTENSE,Intense Telekinesis +5013,0,6,4,0,0x3,5,5,1,no,0,0,0,none,0, LG_KINGS_GRACE,King's Grace +5014,0,6,4,0,0x1,0,5,1,no,0,0,0,none,0, ALL_FULL_THROTTLE,Full Throttle +5015,0,6,4,0,0x1,0,5,1,no,0,0,0,none,0, SR_FLASHCOMBO_ATK_STEP1,Flash Combo Attack Step 1 +5016,0,6,4,0,0x1,0,5,1,no,0,0,0,none,0, SR_FLASHCOMBO_ATK_STEP2,Flash Combo Attack Step 2 +5017,0,6,4,0,0x1,0,5,1,no,0,0,0,none,0, SR_FLASHCOMBO_ATK_STEP3,Flash Combo Attack Step 3 +5018,0,6,4,0,0x1,0,5,1,no,0,0,0,none,0, SR_FLASHCOMBO_ATK_STEP4,Flash Combo Attack Step 4 + 8001,9,6,4,0,0x1,0,5,1,no,0,0,0,magic,0, HLIF_HEAL,Healing Touch 8002,0,6,4,0,0x3,-1,5,1,no,0,0,0,none,0, HLIF_AVOID,Avoid diff --git a/db/re/skill_require_db.txt b/db/re/skill_require_db.txt index eccbbe456..6202ba94f 100644 --- a/db/re/skill_require_db.txt +++ b/db/re/skill_require_db.txt @@ -292,7 +292,7 @@ 374,0,0,5,0,0,0,99,0,0,none,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0 //PF_SOULCHANGE#ƒ\ƒEƒ‹ƒ`ƒFƒ“ƒW# 375,0,0,80:90:100:110:120,0,0,0,99,0,0,none,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0 //PF_SOULBURN#?ƒEƒ‹ƒo?ƒ“# -378,0,0,60:70:80:90:100,0,0,0,99,0,0,none,0,678,1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0 //ASC_EDP#ƒGƒ“ƒ`ƒƒƒ“ƒgƒfƒbƒhƒŠ?ƒ|ƒCƒYƒ“# +378,0,0,60:70:80:90:100,0,0,0,1:2:3:4:5:6:7:8:9:10:11:12:13:14:15:16:17:18:19:20:21:22,0,0,none,0,678,1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0 //ASC_EDP#ƒGƒ“ƒ`ƒƒƒ“ƒgƒfƒbƒhƒŠ?ƒ|ƒCƒYƒ“# 379,0,0,20:20:20:20:20:30:30:30:30:30,0,0,0,99,0,0,none,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0 //ASC_BREAKER#ƒ\ƒEƒ‹ƒuƒŒ?ƒJ?# 380,0,0,20:20:25:25:30:30:35:35:40:40,0,0,0,99,0,0,none,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0 //SN_SIGHT#ƒgƒDƒ‹?ƒTƒCƒg# 381,0,0,30:34:38:42:46,0,0,0,99,0,0,falcon,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0 //SN_FALCONASSAULT#ƒtƒ@ƒ‹ƒRƒ“ƒAƒTƒ‹ƒg# @@ -475,7 +475,7 @@ 2008,0,0,30:35:40:45:50:55:60:65:70:75,0,0,0,99,0,0,dragon,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0 //RK_DRAGONBREATH#Dragon Breath# 2009,0,0,70,0,0,0,99,0,0,dragon,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0 //RK_DRAGONHOWLING#Dragon Howling# 2011,0,0,1,0,0,0,99,0,0,none,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0 //RK_MILLENNIUMSHIELD#Millenium Shield# -2012,0,0,1,0,0,0,99,0,0,none,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0 //RK_CRUSHSTRIKE#Crush Strike# +2012,0,0,1,0,0,0,1:2:3:4:5:6:7:8,0,0,none,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0 //RK_CRUSHSTRIKE#Crush Strike# 2013,0,0,1,0,0,0,99,0,0,none,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0 //RK_REFRESH#Refresh# 2014,0,0,1,0,0,0,99,0,0,none,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0 //RK_GIANTGROWTH#Giant Growth# 2015,0,0,1,0,0,0,99,0,0,none,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0 //RK_STONEHARDSKIN#Stone Hard Skin# @@ -830,6 +830,26 @@ 3027,0,0,55:60:65:70:75 ,0,0,0,99,0,0,none,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0 //OB_OBOROGENSOU#Oboro Gensou# 3029,0,0,20:30:40:50:60,0,0,0,99,0,0,none,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0 //OB_AKAITSUKI#Akaitsuki# +// EP 14.3 Part 2 3rd Job Skills +5001,0,0,22:34:46:58:70,0,0,0,99,0,0,none,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0 //GC_DARKCROW#Dark Claw# +5002,0,0,100:120:140:160:180,0,0,0,99,0,0,none,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0 //RA_UNLIMIT#Unlimited# +5003,0,0,60:70:80:90:100,0,0,0,99,0,0,none,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0 //GN_ILLUSIONDOPING#Illusion Doping# +5004,0,0,30:35:40:45:50:55:60:65:70:75,0,0,0,99,0,0,dragon,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0 //RK_DRAGONBREATH_WATER#Dragon Breath - Water# +5005,0,0,1,0,0,0,99,0,0,none,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0 //RK_LUXANIMA#Lux Anima# +5006,0,0,60:70:80:90:100,0,0,0,99,0,0,none,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0 //NC_MAGMA_ERUPTION#Magma Eruption# +5007,0,0,200:230:260:290:320,0,0,0,99,0,0,none,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0 //WM_FRIGG_SONG#Frigg's Song# +5008,0,0,120:120:120:120:120,0,0,0,99,0,0,none,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0 //SO_ELEMENTAL_SHIELD#Elemental Shield# +5009,0,0,75:65:55:45:35,0,0,0,99,0,0,none,5:5:4:4:3,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0 //SR_FLASHCOMBO#Flash Combo# +5010,0,0,30:26:22:18:14,0,0,0,99,0,0,none,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0 //SC_ESCAPE#Emergency Escape# +5011,0,0,30:60:90:120:150,0,0,0,99,0,0,none,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0 //AB_OFFERTORIUM#Offertorium# +5012,0,0,100:150:200:250:300,0,0,0,99,0,0,none,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0 //WL_TELEKINESIS_INTENSE#Intense Telekinesis# +5013,0,0,200:180:160:140:120,0,0,0,99,0,0,none,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0 //LG_KINGS_GRACE#King's Grace# +5014,0,0,1:1:1:1:1,0,0,0,99,0,0,none,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0 //ALL_FULL_THROTTLE#Full Throttle# +5015,0,0,1,0,0,0,99,0,0,none,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0 //SR_FLASHCOMBO_ATK_STEP1#Flash Combo Attack Step 1#//All 4 steps are using temp req SP values for now. +5016,0,0,1,0,0,0,99,0,0,none,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0 //SR_FLASHCOMBO_ATK_STEP2#Flash Combo Attack Step 2# +5017,0,0,1,0,0,0,99,0,0,none,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0 //SR_FLASHCOMBO_ATK_STEP3#Flash Combo Attack Step 3# +5018,0,0,1,0,0,0,99,0,0,none,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0 //SR_FLASHCOMBO_ATK_STEP4#Flash Combo Attack Step 4# + 10010,0,0,1,0,0,0,99,0,0,none,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0 //GD_BATTLEORDER## 10011,0,0,1,0,0,0,99,0,0,none,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0 //GD_REGENERATION## 10012,0,0,1,0,0,0,99,0,0,none,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0 //GD_RESTORE## diff --git a/db/re/skill_tree.txt b/db/re/skill_tree.txt index b8b1cb86b..e7420dafe 100644 --- a/db/re/skill_tree.txt +++ b/db/re/skill_tree.txt @@ -2483,6 +2483,8 @@ 4054,2009,5,2007,2,0,0,0,0,0,0,0,0 //RK_DRAGONHOWLING#Dragon Howling# 4054,2010,10,0,0,0,0,0,0,0,0,0,0 //RK_RUNEMASTERY#Rune Mastery# 4054,2020,5,57,2,0,0,0,0,0,0,0,0 //RK_PHANTOMTHRUST#Phantom Thrust# +4054,5004,10,2007,2,0,0,0,0,0,0,0,0 //RK_DRAGONBREATH_WATER#Dragon Breath(Water)# +4054,5014,5,0,0,0,0,0,0,0,0,0,0 //ALL_FULL_THROTTLE#Full Throttle# //Warlock (Regular) 4055,1,9,0,0,0,0,0,0,0,0,0,0 //NV_BASIC#Basic Skill# 4055,142,1,0,0,0,0,0,0,0,0,0,0 //NV_FIRSTAID#First Aid# @@ -2539,6 +2541,8 @@ 4055,2230,2,0,0,0,0,0,0,0,0,0,0 //WL_RELEASE#Release# 4055,2231,1,0,0,0,0,0,0,0,0,0,0 //WL_READING_SB#Reading Spellbook# 4055,2232,5,0,0,0,0,0,0,0,0,0,0 //WL_FREEZE_SP#Freeze Spell# +4055,5012,5,2202,5,0,0,0,0,0,0,0,0 //WL_TELEKINESIS_INTENSE#Intense Telekinesis# +4055,5014,5,0,0,0,0,0,0,0,0,0,0 //ALL_FULL_THROTTLE#Full Throttle# //Ranger (Regular) 4056,1,9,0,0,0,0,0,0,0,0,0,0 //NV_BASIC#Basic Skill# 4056,142,1,0,0,0,0,0,0,0,0,0,0 //NV_FIRSTAID#First Aid# @@ -2592,6 +2596,8 @@ 4056,2252,1,2248,1,0,0,0,0,0,0,0,0 //RA_VERDURETRAP#Verdure Trap# 4056,2253,5,2237,1,0,0,0,0,0,0,0,0 //RA_FIRINGTRAP#Firing Trap# 4056,2254,5,2237,1,0,0,0,0,0,0,0,0 //RA_ICEBOUNDTRAP#Icebound Trap# +4056,5002,5,2234,5,0,0,0,0,0,0,0,0 //RA_UNLIMIT#Unlimit# +4056,5014,5,0,0,0,0,0,0,0,0,0,0 //ALL_FULL_THROTTLE#Full Throttle# //Arch Bishop (Regular) 4057,1,9,0,0,0,0,0,0,0,0,0,0 //NV_BASIC#Basic Skill# 4057,142,1,0,0,0,0,0,0,0,0,0,0 //NV_FIRSTAID#First Aid# @@ -2650,6 +2656,8 @@ 4057,2054,10,68,1,0,0,0,0,0,0,0,0 //AB_DUPLELIGHT#Duple Light# 4057,2057,5,2052,1,0,0,0,0,0,0,0,0 //AB_SILENTIUM#Silentium# 4057,2515,5,2044,1,2053,1,0,0,0,0,0,0 //AB_SECRAMENT#Secrament# +4057,5011,5,2051,2,0,0,0,0,0,0,0,0 //AB_OFFERTORIUM#Offertorium# +4057,5014,5,0,0,0,0,0,0,0,0,0,0 //ALL_FULL_THROTTLE#Full Throttle# //Mechanic (Regular) 4058,1,9,0,0,0,0,0,0,0,0,0,0 //NV_BASIC#Basic Skill# 4058,142,1,0,0,0,0,0,0,0,0,0,0 //NV_FIRSTAID#First Aid# @@ -2718,7 +2726,9 @@ 4058,2281,5,2277,2,0,0,0,0,0,0,0,0 //NC_SILVERSNIPER#FAW - Silver Sniper# 4058,2282,5,2277,2,0,0,0,0,0,0,0,0 //NC_MAGICDECOY#FAW - Magic Decoy# 4058,2283,1,2281,1,0,0,0,0,0,0,0,0 //NC_DISJOINT#FAW Removal# +4058,5006,5,0,0,0,0,0,0,0,0,0,0 //NC_MAGMA_ERUPTION#Magma Eruption# 4058,2535,1,41,1,0,0,0,0,0,0,0,0 //ALL_BUYING_STORE#Open Buying Store# +4058,5014,5,0,0,0,0,0,0,0,0,0,0 //ALL_FULL_THROTTLE#Full Throttle# //Guillotine Cross (Regular) 4059,1,9,0,0,0,0,0,0,0,0,0,0 //NV_BASIC#Basic Skill# 4059,142,1,0,0,0,0,0,0,0,0,0,0 //NV_FIRSTAID#First Aid# @@ -2763,6 +2773,8 @@ 4059,2035,5,2034,1,0,0,0,0,0,0,0,0 //GC_HALLUCINATIONWALK#Hallucination Walk# 4059,2036,5,136,10,0,0,0,0,0,0,0,0 //GC_ROLLINGCUTTER#Rolling Cutter# 4059,2037,5,2036,1,0,0,0,0,0,0,0,0 //GC_CROSSRIPPERSLASHER#Cross Ripper Slasher# +4059,5001,5,2023,5,0,0,0,0,0,0,0,0 //GC_DARKCROW#Dark Claw# +4059,5014,5,0,0,0,0,0,0,0,0,0,0 //ALL_FULL_THROTTLE#Full Throttle# //Rune Knight (Trans) 4060,1,9,0,0,0,0,0,0,0,0,0,0 //NV_BASIC#Basic Skill# 4060,142,1,0,0,0,0,0,0,0,0,0,0 //NV_FIRSTAID#First Aid# @@ -2809,6 +2821,8 @@ 4060,2009,5,2007,2,0,0,0,0,0,0,0,0 //RK_DRAGONHOWLING#Dragon Howling# 4060,2010,10,0,0,0,0,0,0,0,0,0,0 //RK_RUNEMASTERY#Rune Mastery# 4060,2020,5,57,2,0,0,0,0,0,0,0,0 //RK_PHANTOMTHRUST#Phantom Thrust# +4060,5004,10,2007,2,0,0,0,0,0,0,0,0 //RK_DRAGONBREATH_WATER#Dragon Breath(Water)# +4060,5014,5,0,0,0,0,0,0,0,0,0,0 //ALL_FULL_THROTTLE#Full Throttle# //Warlock (Trans) 4061,1,9,0,0,0,0,0,0,0,0,0,0 //NV_BASIC#Basic Skill# 4061,142,1,0,0,0,0,0,0,0,0,0,0 //NV_FIRSTAID#First Aid# @@ -2871,6 +2885,8 @@ 4061,2230,2,0,0,0,0,0,0,0,0,0,0 //WL_RELEASE#Release# 4061,2231,1,0,0,0,0,0,0,0,0,0,0 //WL_READING_SB#Reading Spellbook# 4061,2232,5,0,0,0,0,0,0,0,0,0,0 //WL_FREEZE_SP#Freeze Spell# +4061,5012,5,2202,5,0,0,0,0,0,0,0,0 //WL_TELEKINESIS_INTENSE#Intense Telekinesis# +4061,5014,5,0,0,0,0,0,0,0,0,0,0 //ALL_FULL_THROTTLE#Full Throttle# //Ranger (Trans) 4062,1,9,0,0,0,0,0,0,0,0,0,0 //NV_BASIC#Basic Skill# 4062,142,1,0,0,0,0,0,0,0,0,0,0 //NV_FIRSTAID#First Aid# @@ -2928,6 +2944,8 @@ 4062,2252,1,2248,1,0,0,0,0,0,0,0,0 //RA_VERDURETRAP#Verdure Trap# 4062,2253,5,2237,1,0,0,0,0,0,0,0,0 //RA_FIRINGTRAP#Firing Trap# 4062,2254,5,2237,1,0,0,0,0,0,0,0,0 //RA_ICEBOUNDTRAP#Icebound Trap# +4062,5002,5,2234,5,0,0,0,0,0,0,0,0 //RA_UNLIMIT#Unlimit# +4062,5014,5,0,0,0,0,0,0,0,0,0,0 //ALL_FULL_THROTTLE#Full Throttle# //Arch Bishop (Trans) 4063,1,9,0,0,0,0,0,0,0,0,0,0 //NV_BASIC#Basic Skill# 4063,142,1,0,0,0,0,0,0,0,0,0,0 //NV_FIRSTAID#First Aid# @@ -2990,6 +3008,8 @@ 4063,2054,10,68,1,0,0,0,0,0,0,0,0 //AB_DUPLELIGHT#Duple Light# 4063,2057,5,2052,1,0,0,0,0,0,0,0,0 //AB_SILENTIUM#Silentium# 4063,2515,5,2044,1,2053,1,0,0,0,0,0,0 //AB_SECRAMENT#Secrament# +4063,5011,5,2051,2,0,0,0,0,0,0,0,0 //AB_OFFERTORIUM#Offertorium# +4063,5014,5,0,0,0,0,0,0,0,0,0,0 //ALL_FULL_THROTTLE#Full Throttle# //Mechanic (Trans) 4064,1,9,0,0,0,0,0,0,0,0,0,0 //NV_BASIC#Basic Skill# 4064,142,1,0,0,0,0,0,0,0,0,0,0 //NV_FIRSTAID#First Aid# @@ -3063,7 +3083,9 @@ 4064,2281,5,2277,2,0,0,0,0,0,0,0,0 //NC_SILVERSNIPER#FAW - Silver Sniper# 4064,2282,5,2277,2,0,0,0,0,0,0,0,0 //NC_MAGICDECOY#FAW - Magic Decoy# 4064,2283,1,2281,1,0,0,0,0,0,0,0,0 //NC_DISJOINT#FAW Removal# +4064,5006,5,0,0,0,0,0,0,0,0,0,0 //NC_MAGMA_ERUPTION#Magma Eruption# 4064,2535,1,41,1,0,0,0,0,0,0,0,0 //ALL_BUYING_STORE#Open Buying Store# +4064,5014,5,0,0,0,0,0,0,0,0,0,0 //ALL_FULL_THROTTLE#Full Throttle# //Guillotine Cross (Trans) 4065,1,9,0,0,0,0,0,0,0,0,0,0 //NV_BASIC#Basic Skill# 4065,142,1,0,0,0,0,0,0,0,0,0,0 //NV_FIRSTAID#First Aid# @@ -3113,6 +3135,8 @@ 4065,2035,5,2034,1,0,0,0,0,0,0,0,0 //GC_HALLUCINATIONWALK#Hallucination Walk# 4065,2036,5,136,10,0,0,0,0,0,0,0,0 //GC_ROLLINGCUTTER#Rolling Cutter# 4065,2037,5,2036,1,0,0,0,0,0,0,0,0 //GC_CROSSRIPPERSLASHER#Cross Ripper Slasher# +4065,5001,5,2023,5,0,0,0,0,0,0,0,0 //GC_DARKCROW#Dark Claw# +4065,5014,5,0,0,0,0,0,0,0,0,0,0 //ALL_FULL_THROTTLE#Full Throttle# //Royal Guard (Regular) 4066,1,9,0,0,0,0,0,0,0,0,0,0 //NV_BASIC#Basic Skill# 4066,142,1,0,0,0,0,0,0,0,0,0,0 //NV_FIRSTAID#First Aid# @@ -3166,6 +3190,8 @@ 4066,2323,5,2311,3,0,0,0,0,0,0,0,0 //LG_EARTHDRIVE#Earth Drive# 4066,2324,5,2318,3,2319,3,0,0,0,0,0,0 //LG_HESPERUSLIT#Hesperus Lit# 4066,2325,5,2315,3,2321,4,2322,5,0,0,0,0 //LG_INSPIRATION#Inspiration# +4066,5013,5,2311,5,0,0,0,0,0,0,0,0 //LG_KINGS_GRACE#King's Grace# +4066,5014,5,0,0,0,0,0,0,0,0,0,0 //ALL_FULL_THROTTLE#Full Throttle# //Sorcerer (Regular) 4067,1,9,0,0,0,0,0,0,0,0,0,0 //NV_BASIC#Basic Skill# 4067,142,1,0,0,0,0,0,0,0,0,0,0 //NV_FIRSTAID#First Aid# @@ -3236,6 +3262,7 @@ 4067,2466,3,2458,3,0,0,0,0,0,0,0,0 //SO_WATER_INSIGNIA#Water Insignia# 4067,2467,3,2459,3,0,0,0,0,0,0,0,0 //SO_WIND_INSIGNIA#Wind Insignia# 4067,2468,3,2460,3,0,0,0,0,0,0,0,0 //SO_EARTH_INSIGNIA#Earth Insignia# +4067,5014,5,0,0,0,0,0,0,0,0,0,0 //ALL_FULL_THROTTLE#Full Throttle# //Minstrel (Regular) 4068,1,9,0,0,0,0,0,0,0,0,0,0 //NV_BASIC#Basic Skill# 4068,142,1,0,0,0,0,0,0,0,0,0,0 //NV_FIRSTAID#First Aid# @@ -3291,6 +3318,8 @@ 4068,2432,5,2427,1,0,0,0,0,0,0,0,0 //WM_MELODYOFSINK#Melody Of Sink# 4068,2433,5,2431,1,0,0,0,0,0,0,0,0 //WM_BEYOND_OF_WARCRY#Warcry Of Beyond# 4068,2434,5,2429,1,2433,1,0,0,0,0,0,0 //WM_UNLIMITED_HUMMING_VOICE#Unlimited Humming Voice# +4068,5007,5,2412,1,0,0,0,0,0,0,0,0 //WM_FRIGG_SONG# +4068,5014,5,0,0,0,0,0,0,0,0,0,0 //ALL_FULL_THROTTLE#Full Throttle# //Wanderer (Regular) 4069,1,9,0,0,0,0,0,0,0,0,0,0 //NV_BASIC#Basic Skill# 4069,142,1,0,0,0,0,0,0,0,0,0,0 //NV_FIRSTAID#First Aid# @@ -3346,6 +3375,8 @@ 4069,2432,5,2427,1,0,0,0,0,0,0,0,0 //WM_MELODYOFSINK#Melody Of Sink# 4069,2433,5,2431,1,0,0,0,0,0,0,0,0 //WM_BEYOND_OF_WARCRY#Warcry Of Beyond# 4069,2434,5,2429,1,2433,1,0,0,0,0,0,0 //WM_UNLIMITED_HUMMING_VOICE#Unlimited Humming Voice# +4069,5007,5,2412,1,0,0,0,0,0,0,0,0 //WM_FRIGG_SONG# +4069,5014,5,0,0,0,0,0,0,0,0,0,0 //ALL_FULL_THROTTLE#Full Throttle# //Sura (Regular) 4070,1,9,0,0,0,0,0,0,0,0,0,0 //NV_BASIC#Basic Skill# 4070,142,1,0,0,0,0,0,0,0,0,0,0 //NV_FIRSTAID#First Aid# @@ -3405,6 +3436,8 @@ 4070,2348,5,2347,5,0,0,0,0,0,0,0,0 //SR_GENTLETOUCH_REVITALIZE#Gentle Touch - Revitalize# 4070,2517,5,2340,1,2518,3,0,0,0,0,0,0 //SR_HOWLINGOFLION#Howling Of Lion# 4070,2518,5,267,3,0,0,0,0,0,0,0,0 //SR_RIDEINLIGHTNING#Ride In Lightening# +4070,5009,5,2326,3,2329,3,2330,1,2327,1,0,0 //SR_FLASHCOMBO#Flash Combo# +4070,5014,5,0,0,0,0,0,0,0,0,0,0 //ALL_FULL_THROTTLE#Full Throttle# //Genetic (Regular) 4071,1,9,0,0,0,0,0,0,0,0,0,0 //NV_BASIC#Basic Skill# 4071,142,1,0,0,0,0,0,0,0,0,0,0 //NV_FIRSTAID#First Aid# @@ -3459,7 +3492,9 @@ 4071,2495,2,2497,1,0,0,0,0,0,0,0,0 //GN_MIX_COOKING#Mix Cooking# 4071,2496,2,2495,1,0,0,0,0,0,0,0,0 //GN_MAKEBOMB#Create Bomb# 4071,2497,10,0,0,0,0,0,0,0,0,0,0 //GN_S_PHARMACY#Special Pharmacy# +4071,5003,5,2497,1,0,0,0,0,0,0,0,0 //GN_ILLUSIONDOOPING#Hallucination Drug# 4071,2535,1,41,1,0,0,0,0,0,0,0,0 //ALL_BUYING_STORE#Open Buying Store# +4071,5014,5,0,0,0,0,0,0,0,0,0,0 //ALL_FULL_THROTTLE#Full Throttle# //Shadow Chaser (Regular) 4072,1,9,0,0,0,0,0,0,0,0,0,0 //NV_BASIC#Basic Skill# 4072,142,1,0,0,0,0,0,0,0,0,0,0 //NV_FIRSTAID#First Aid# @@ -3517,6 +3552,8 @@ 4072,2302,3,2296,3,2301,3,0,0,0,0,0,0 //SC_MAELSTROM#Maelstrom# 4072,2303,3,2300,3,0,0,0,0,0,0,0,0 //SC_BLOODYLUST#Bloody Lust# 4072,2304,3,2300,3,0,0,0,0,0,0,0,0 //SC_FEINTBOMB#Feint Bomb# +4072,5010,5,2288,2,0,0,0,0,0,0,0,0 //SC_SCAPE#Scape# +4072,5014,5,0,0,0,0,0,0,0,0,0,0 //ALL_FULL_THROTTLE#Full Throttle# //Royal Guard (Trans) 4073,1,9,0,0,0,0,0,0,0,0,0,0 //NV_BASIC#Basic Skill# 4073,142,1,0,0,0,0,0,0,0,0,0,0 //NV_FIRSTAID#First Aid# @@ -3574,6 +3611,8 @@ 4073,2323,5,2311,3,0,0,0,0,0,0,0,0 //LG_EARTHDRIVE#Earth Drive# 4073,2324,5,2318,3,2319,3,0,0,0,0,0,0 //LG_HESPERUSLIT#Hesperus Lit# 4073,2325,5,2315,3,2321,4,2322,5,0,0,0,0 //LG_INSPIRATION#Inspiration# +4073,5013,5,2311,5,0,0,0,0,0,0,0,0 //LG_KINGS_GRACE#King's Grace# +4073,5014,5,0,0,0,0,0,0,0,0,0,0 //ALL_FULL_THROTTLE#Full Throttle# //Sorcerer (Trans) 4074,1,9,0,0,0,0,0,0,0,0,0,0 //NV_BASIC#Basic Skill# 4074,142,1,0,0,0,0,0,0,0,0,0,0 //NV_FIRSTAID#First Aid# @@ -3652,6 +3691,7 @@ 4074,2466,3,2458,3,0,0,0,0,0,0,0,0 //SO_WATER_INSIGNIA#Water Insignia# 4074,2467,3,2459,3,0,0,0,0,0,0,0,0 //SO_WIND_INSIGNIA#Wind Insignia# 4074,2468,3,2460,3,0,0,0,0,0,0,0,0 //SO_EARTH_INSIGNIA#Earth Insignia# +4074,5014,5,0,0,0,0,0,0,0,0,0,0 //ALL_FULL_THROTTLE#Full Throttle# //Minstrel (Trans) 4075,1,9,0,0,0,0,0,0,0,0,0,0 //NV_BASIC#Basic Skill# 4075,142,1,0,0,0,0,0,0,0,0,0,0 //NV_FIRSTAID#First Aid# @@ -3713,6 +3753,8 @@ 4075,2432,5,2427,1,0,0,0,0,0,0,0,0 //WM_MELODYOFSINK#Melody Of Sink# 4075,2433,5,2431,1,0,0,0,0,0,0,0,0 //WM_BEYOND_OF_WARCRY#Warcry Of Beyond# 4075,2434,5,2429,1,2433,1,0,0,0,0,0,0 //WM_UNLIMITED_HUMMING_VOICE#Unlimited Humming Voice# +4075,5007,5,2412,1,0,0,0,0,0,0,0,0 //WM_FRIGG_SONG# +4075,5014,5,0,0,0,0,0,0,0,0,0,0 //ALL_FULL_THROTTLE#Full Throttle# //Wanderer (Trans) 4076,1,9,0,0,0,0,0,0,0,0,0,0 //NV_BASIC#Basic Skill# 4076,142,1,0,0,0,0,0,0,0,0,0,0 //NV_FIRSTAID#First Aid# @@ -3774,6 +3816,8 @@ 4076,2432,5,2427,1,0,0,0,0,0,0,0,0 //WM_MELODYOFSINK#Melody Of Sink# 4076,2433,5,2431,1,0,0,0,0,0,0,0,0 //WM_BEYOND_OF_WARCRY#Warcry Of Beyond# 4076,2434,5,2429,1,2433,1,0,0,0,0,0,0 //WM_UNLIMITED_HUMMING_VOICE#Unlimited Humming Voice# +4076,5007,5,2412,1,0,0,0,0,0,0,0,0 //WM_FRIGG_SONG# +4076,5014,5,0,0,0,0,0,0,0,0,0,0 //ALL_FULL_THROTTLE#Full Throttle# //Sura (Trans) 4077,1,9,0,0,0,0,0,0,0,0,0,0 //NV_BASIC#Basic Skill# 4077,142,1,0,0,0,0,0,0,0,0,0,0 //NV_FIRSTAID#First Aid# @@ -3837,6 +3881,8 @@ 4077,2348,5,2347,5,0,0,0,0,0,0,0,0 //SR_GENTLETOUCH_REVITALIZE#Gentle Touch - Revitalize# 4077,2517,5,2340,1,2518,3,0,0,0,0,0,0 //SR_HOWLINGOFLION#Howling Of Lion# 4077,2518,5,267,3,0,0,0,0,0,0,0,0 //SR_RIDEINLIGHTNING#Ride In Lightening# +4077,5009,5,2326,3,2329,3,2330,1,2327,1,0,0 //SR_FLASHCOMBO#Flash Combo# +4077,5014,5,0,0,0,0,0,0,0,0,0,0 //ALL_FULL_THROTTLE#Full Throttle# //Genetic (Trans) 4078,1,9,0,0,0,0,0,0,0,0,0,0 //NV_BASIC#Basic Skill# 4078,142,1,0,0,0,0,0,0,0,0,0,0 //NV_FIRSTAID#First Aid# @@ -3895,7 +3941,9 @@ 4078,2495,2,2497,1,0,0,0,0,0,0,0,0 //GN_MIX_COOKING#Mix Cooking# 4078,2496,2,2495,1,0,0,0,0,0,0,0,0 //GN_MAKEBOMB#Create Bomb# 4078,2497,10,0,0,0,0,0,0,0,0,0,0 //GN_S_PHARMACY#Special Pharmacy# +4078,5003,5,2497,1,0,0,0,0,0,0,0,0 //GN_ILLUSIONDOOPING#Hallucination Drug# 4078,2535,1,41,1,0,0,0,0,0,0,0,0 //ALL_BUYING_STORE#Open Buying Store# +4078,5014,5,0,0,0,0,0,0,0,0,0,0 //ALL_FULL_THROTTLE#Full Throttle# //Shadow Chaser (Trans) 4079,1,9,0,0,0,0,0,0,0,0,0,0 //NV_BASIC#Basic Skill# 4079,142,1,0,0,0,0,0,0,0,0,0,0 //NV_FIRSTAID#First Aid# @@ -3941,6 +3989,7 @@ 4079,2286,10,2285,5,0,0,0,0,0,0,0,0 //SC_AUTOSHADOWSPELL#Auto Shadow Spell# 4079,2287,5,213,3,0,0,0,0,0,0,0,0 //SC_SHADOWFORM#Shadow Form# 4079,2288,10,46,7,0,0,0,0,0,0,0,0 //SC_TRIANGLESHOT#Triangle Shot# +4079,5010,5,2288,2,0,0,0,0,0,0,0,0 //SC_SCAPE#Scape# 4079,2289,5,0,0,0,0,0,0,0,0,0,0 //SC_BODYPAINT#Body Painting# 4079,2290,5,2286,7,2291,5,2296,3,0,0,0,0 //SC_INVISIBILITY#Invisibility# 4079,2291,5,2286,5,2287,3,0,0,0,0,0,0 //SC_DEADLYINFECT#Deadly Infect# @@ -3957,6 +4006,7 @@ 4079,2302,3,2296,3,2301,3,0,0,0,0,0,0 //SC_MAELSTROM#Maelstrom# 4079,2303,3,2300,3,0,0,0,0,0,0,0,0 //SC_BLOODYLUST#Bloody Lust# 4079,2304,3,2300,3,0,0,0,0,0,0,0,0 //SC_FEINTBOMB#Feint Bomb# +4079,5014,5,0,0,0,0,0,0,0,0,0,0 //ALL_FULL_THROTTLE#Full Throttle# //Rune Knight (Dragon) (Regular) 4080,1,9,0,0,0,0,0,0,0,0,0,0 //NV_BASIC#Basic Skill# 4080,142,1,0,0,0,0,0,0,0,0,0,0 //NV_FIRSTAID#First Aid# @@ -3995,6 +4045,8 @@ 4080,2009,5,2007,2,0,0,0,0,0,0,0,0 //RK_DRAGONHOWLING#Dragon Howling# 4080,2010,10,0,0,0,0,0,0,0,0,0,0 //RK_RUNEMASTERY#Rune Mastery# 4080,2020,5,57,2,0,0,0,0,0,0,0,0 //RK_PHANTOMTHRUST#Phantom Thrust# +4080,5004,10,2007,2,0,0,0,0,0,0,0,0 //RK_DRAGONBREATH_WATER#Dragon Breath(Water)# +4080,5014,5,0,0,0,0,0,0,0,0,0,0 //ALL_FULL_THROTTLE#Full Throttle# //Rune Knight (Dragon) (Trans) 4081,1,9,0,0,0,0,0,0,0,0,0,0 //NV_BASIC#Basic Skill# 4081,142,1,0,0,0,0,0,0,0,0,0,0 //NV_FIRSTAID#First Aid# @@ -4041,6 +4093,8 @@ 4081,2009,5,2007,2,0,0,0,0,0,0,0,0 //RK_DRAGONHOWLING#Dragon Howling# 4081,2010,10,0,0,0,0,0,0,0,0,0,0 //RK_RUNEMASTERY#Rune Mastery# 4081,2020,5,57,2,0,0,0,0,0,0,0,0 //RK_PHANTOMTHRUST#Phantom Thrust# +4081,5004,10,2007,2,0,0,0,0,0,0,0,0 //RK_DRAGONBREATH_WATER#Dragon Breath(Water)# +4081,5014,5,0,0,0,0,0,0,0,0,0,0 //ALL_FULL_THROTTLE#Full Throttle# //Royal Guard (Gryphon) (Regular) 4082,1,9,0,0,0,0,0,0,0,0,0,0 //NV_BASIC#Basic Skill# 4082,142,1,0,0,0,0,0,0,0,0,0,0 //NV_FIRSTAID#First Aid# @@ -4094,6 +4148,8 @@ 4082,2323,5,2311,3,0,0,0,0,0,0,0,0 //LG_EARTHDRIVE#Earth Drive# 4082,2324,5,2318,3,2319,3,0,0,0,0,0,0 //LG_HESPERUSLIT#Hesperus Lit# 4082,2325,5,2315,3,2321,4,2322,5,0,0,0,0 //LG_INSPIRATION#Inspiration# +4082,5013,5,2311,5,0,0,0,0,0,0,0,0 //LG_KINGS_GRACE#King's Grace# +4082,5014,5,0,0,0,0,0,0,0,0,0,0 //ALL_FULL_THROTTLE#Full Throttle# //Royal Guard (Gryphon) (Trans) 4083,1,9,0,0,0,0,0,0,0,0,0,0 //NV_BASIC#Basic Skill# 4083,142,1,0,0,0,0,0,0,0,0,0,0 //NV_FIRSTAID#First Aid# @@ -4151,6 +4207,8 @@ 4083,2323,5,2311,3,0,0,0,0,0,0,0,0 //LG_EARTHDRIVE#Earth Drive# 4083,2324,5,2318,3,2319,3,0,0,0,0,0,0 //LG_HESPERUSLIT#Hesperus Lit# 4083,2325,5,2315,3,2321,4,2322,5,0,0,0,0 //LG_INSPIRATION#Inspiration# +4083,5013,5,2311,5,0,0,0,0,0,0,0,0 //LG_KINGS_GRACE#King's Grace# +4083,5014,5,0,0,0,0,0,0,0,0,0,0 //ALL_FULL_THROTTLE#Full Throttle# //Ranger (Warg) (Regular) 4084,1,9,0,0,0,0,0,0,0,0,0,0 //NV_BASIC#Basic Skill# 4084,142,1,0,0,0,0,0,0,0,0,0,0 //NV_FIRSTAID#First Aid# @@ -4204,6 +4262,8 @@ 4084,2252,1,2248,1,0,0,0,0,0,0,0,0 //RA_VERDURETRAP#Verdure Trap# 4084,2253,5,2237,1,0,0,0,0,0,0,0,0 //RA_FIRINGTRAP#Firing Trap# 4084,2254,5,2237,1,0,0,0,0,0,0,0,0 //RA_ICEBOUNDTRAP#Icebound Trap# +4084,5002,5,2234,5,0,0,0,0,0,0,0,0 //RA_UNLIMIT#Unlimit# +4084,5014,5,0,0,0,0,0,0,0,0,0,0 //ALL_FULL_THROTTLE#Full Throttle# //Ranger (Warg) (Trans) 4085,1,9,0,0,0,0,0,0,0,0,0,0 //NV_BASIC#Basic Skill# 4085,142,1,0,0,0,0,0,0,0,0,0,0 //NV_FIRSTAID#First Aid# @@ -4261,6 +4321,8 @@ 4085,2252,1,2248,1,0,0,0,0,0,0,0,0 //RA_VERDURETRAP#Verdure Trap# 4085,2253,5,2237,1,0,0,0,0,0,0,0,0 //RA_FIRINGTRAP#Firing Trap# 4085,2254,5,2237,1,0,0,0,0,0,0,0,0 //RA_ICEBOUNDTRAP#Icebound Trap# +4085,5002,5,2234,5,0,0,0,0,0,0,0,0 //RA_UNLIMIT#Unlimit# +4085,5014,5,0,0,0,0,0,0,0,0,0,0 //ALL_FULL_THROTTLE#Full Throttle# //Mechanic (Mado) (Regular) 4086,1,9,0,0,0,0,0,0,0,0,0,0 //NV_BASIC#Basic Skill# 4086,142,1,0,0,0,0,0,0,0,0,0,0 //NV_FIRSTAID#First Aid# @@ -4329,7 +4391,9 @@ 4086,2281,5,2277,2,0,0,0,0,0,0,0,0 //NC_SILVERSNIPER#FAW - Silver Sniper# 4086,2282,5,2277,2,0,0,0,0,0,0,0,0 //NC_MAGICDECOY#FAW - Magic Decoy# 4086,2283,1,2281,1,0,0,0,0,0,0,0,0 //NC_DISJOINT#FAW Removal# +4086,5006,5,0,0,0,0,0,0,0,0,0,0 //NC_MAGMA_ERUPTION#Magma Eruption# 4086,2535,1,41,1,0,0,0,0,0,0,0,0 //ALL_BUYING_STORE#Open Buying Store# +4086,5014,5,0,0,0,0,0,0,0,0,0,0 //ALL_FULL_THROTTLE#Full Throttle# //Mechanic (Mado) (Trans) 4087,1,9,0,0,0,0,0,0,0,0,0,0 //NV_BASIC#Basic Skill# 4087,142,1,0,0,0,0,0,0,0,0,0,0 //NV_FIRSTAID#First Aid# @@ -4403,7 +4467,9 @@ 4087,2281,5,2277,2,0,0,0,0,0,0,0,0 //NC_SILVERSNIPER#FAW - Silver Sniper# 4087,2282,5,2277,2,0,0,0,0,0,0,0,0 //NC_MAGICDECOY#FAW - Magic Decoy# 4087,2283,1,2281,1,0,0,0,0,0,0,0,0 //NC_DISJOINT#FAW Removal# +4087,5006,5,0,0,0,0,0,0,0,0,0,0 //NC_MAGMA_ERUPTION#Magma Eruption# 4087,2535,1,41,1,0,0,0,0,0,0,0,0 //ALL_BUYING_STORE#Open Buying Store# +4087,5014,5,0,0,0,0,0,0,0,0,0,0 //ALL_FULL_THROTTLE#Full Throttle# //Baby Rune Knight 4096,1,9,0,0,0,0,0,0,0,0,0,0 //NV_BASIC#Basic Skill# 4096,142,1,0,0,0,0,0,0,0,0,0,0 //NV_FIRSTAID#First Aid# @@ -4443,6 +4509,8 @@ 4096,2009,5,2007,2,0,0,0,0,0,0,0,0 //RK_DRAGONHOWLING#Dragon Howling# 4096,2010,10,0,0,0,0,0,0,0,0,0,0 //RK_RUNEMASTERY#Rune Mastery# 4096,2020,5,57,2,0,0,0,0,0,0,0,0 //RK_PHANTOMTHRUST#Phantom Thrust# +4096,5004,10,2007,2,0,0,0,0,0,0,0,0 //RK_DRAGONBREATH_WATER#Dragon Breath(Water)# +4096,5014,5,0,0,0,0,0,0,0,0,0,0 //ALL_FULL_THROTTLE#Full Throttle# //Baby Warlock 4097,1,9,0,0,0,0,0,0,0,0,0,0 //NV_BASIC#Basic Skill# 4097,142,1,0,0,0,0,0,0,0,0,0,0 //NV_FIRSTAID#First Aid# @@ -4500,6 +4568,8 @@ 4097,2230,2,0,0,0,0,0,0,0,0,0,0 //WL_RELEASE#Release# 4097,2231,1,0,0,0,0,0,0,0,0,0,0 //WL_READING_SB#Reading Spellbook# 4097,2232,5,0,0,0,0,0,0,0,0,0,0 //WL_FREEZE_SP#Freeze Spell# +4097,5012,5,2202,5,0,0,0,0,0,0,0,0 //WL_TELEKINESIS_INTENSE#Intense Telekinesis# +4097,5014,5,0,0,0,0,0,0,0,0,0,0 //ALL_FULL_THROTTLE#Full Throttle# //Baby Ranger 4098,1,9,0,0,0,0,0,0,0,0,0,0 //NV_BASIC#Basic Skill# 4098,142,1,0,0,0,0,0,0,0,0,0,0 //NV_FIRSTAID#First Aid# @@ -4554,6 +4624,8 @@ 4098,2252,1,2248,1,0,0,0,0,0,0,0,0 //RA_VERDURETRAP#Verdure Trap# 4098,2253,5,2237,1,0,0,0,0,0,0,0,0 //RA_FIRINGTRAP#Firing Trap# 4098,2254,5,2237,1,0,0,0,0,0,0,0,0 //RA_ICEBOUNDTRAP#Icebound Trap# +4098,5002,5,2234,5,0,0,0,0,0,0,0,0 //RA_UNLIMIT#Unlimit# +4098,5014,5,0,0,0,0,0,0,0,0,0,0 //ALL_FULL_THROTTLE#Full Throttle# //Baby Arch Bishop 4099,1,9,0,0,0,0,0,0,0,0,0,0 //NV_BASIC#Basic Skill# 4099,142,1,0,0,0,0,0,0,0,0,0,0 //NV_FIRSTAID#First Aid# @@ -4613,6 +4685,8 @@ 4099,2054,10,68,1,0,0,0,0,0,0,0,0 //AB_DUPLELIGHT#Duple Light# 4099,2057,5,2052,1,0,0,0,0,0,0,0,0 //AB_SILENTIUM#Silentium# 4099,2515,5,2044,1,2053,1,0,0,0,0,0,0 //AB_SECRAMENT#Secrament# +4099,5011,5,2051,2,0,0,0,0,0,0,0,0 //AB_OFFERTORIUM#Offertorium# +4099,5014,5,0,0,0,0,0,0,0,0,0,0 //ALL_FULL_THROTTLE#Full Throttle# //Baby Mechanic 4100,1,9,0,0,0,0,0,0,0,0,0,0 //NV_BASIC#Basic Skill# 4100,142,1,0,0,0,0,0,0,0,0,0,0 //NV_FIRSTAID#First Aid# @@ -4682,7 +4756,9 @@ 4100,2281,5,2277,2,0,0,0,0,0,0,0,0 //NC_SILVERSNIPER#FAW - Silver Sniper# 4100,2282,5,2277,2,0,0,0,0,0,0,0,0 //NC_MAGICDECOY#FAW - Magic Decoy# 4100,2283,1,2281,1,0,0,0,0,0,0,0,0 //NC_DISJOINT#FAW Removal# +4100,5006,5,0,0,0,0,0,0,0,0,0,0 //NC_MAGMA_ERUPTION#Magma Eruption# 4100,2535,1,41,1,0,0,0,0,0,0,0,0 //ALL_BUYING_STORE#Open Buying Store# +4100,5014,5,0,0,0,0,0,0,0,0,0,0 //ALL_FULL_THROTTLE#Full Throttle# //Baby Guillotine Cross 4101,1,9,0,0,0,0,0,0,0,0,0,0 //NV_BASIC#Basic Skill# 4101,142,1,0,0,0,0,0,0,0,0,0,0 //NV_FIRSTAID#First Aid# @@ -4728,6 +4804,8 @@ 4101,2035,5,2034,1,0,0,0,0,0,0,0,0 //GC_HALLUCINATIONWALK#Hallucination Walk# 4101,2036,5,136,10,0,0,0,0,0,0,0,0 //GC_ROLLINGCUTTER#Rolling Cutter# 4101,2037,5,2036,1,0,0,0,0,0,0,0,0 //GC_CROSSRIPPERSLASHER#Cross Ripper Slasher# +4101,5001,5,2023,5,0,0,0,0,0,0,0,0 //GC_DARKCROW#Dark Claw# +4101,5014,5,0,0,0,0,0,0,0,0,0,0 //ALL_FULL_THROTTLE#Full Throttle# //Baby Royal Guard 4102,1,9,0,0,0,0,0,0,0,0,0,0 //NV_BASIC#Basic Skill# 4102,142,1,0,0,0,0,0,0,0,0,0,0 //NV_FIRSTAID#First Aid# @@ -4782,6 +4860,8 @@ 4102,2323,5,2311,3,0,0,0,0,0,0,0,0 //LG_EARTHDRIVE#Earth Drive# 4102,2324,5,2318,3,2319,3,0,0,0,0,0,0 //LG_HESPERUSLIT#Hesperus Lit# 4102,2325,5,2315,3,2321,4,2322,5,0,0,0,0 //LG_INSPIRATION#Inspiration# +4102,5013,5,2311,5,0,0,0,0,0,0,0,0 //LG_KINGS_GRACE#King's Grace# +4102,5014,5,0,0,0,0,0,0,0,0,0,0 //ALL_FULL_THROTTLE#Full Throttle# //Baby Sorcerer 4103,1,9,0,0,0,0,0,0,0,0,0,0 //NV_BASIC#Basic Skill# 4103,142,1,0,0,0,0,0,0,0,0,0,0 //NV_FIRSTAID#First Aid# @@ -4853,6 +4933,7 @@ 4103,2466,3,2458,3,0,0,0,0,0,0,0,0 //SO_WATER_INSIGNIA#Water Insignia# 4103,2467,3,2459,3,0,0,0,0,0,0,0,0 //SO_WIND_INSIGNIA#Wind Insignia# 4103,2468,3,2460,3,0,0,0,0,0,0,0,0 //SO_EARTH_INSIGNIA#Earth Insignia# +4103,5014,5,0,0,0,0,0,0,0,0,0,0 //ALL_FULL_THROTTLE#Full Throttle# //Baby Minstrel 4104,1,9,0,0,0,0,0,0,0,0,0,0 //NV_BASIC#Basic Skill# 4104,142,1,0,0,0,0,0,0,0,0,0,0 //NV_FIRSTAID#First Aid# @@ -4909,6 +4990,8 @@ 4104,2432,5,2427,1,0,0,0,0,0,0,0,0 //WM_MELODYOFSINK#Melody Of Sink# 4104,2433,5,2431,1,0,0,0,0,0,0,0,0 //WM_BEYOND_OF_WARCRY#Warcry Of Beyond# 4104,2434,5,2429,1,2433,1,0,0,0,0,0,0 //WM_UNLIMITED_HUMMING_VOICE#Unlimited Humming Voice# +4104,5007,5,2412,1,0,0,0,0,0,0,0,0 //WM_FRIGG_SONG# +4104,5014,5,0,0,0,0,0,0,0,0,0,0 //ALL_FULL_THROTTLE#Full Throttle# //Baby Wanderer 4105,1,9,0,0,0,0,0,0,0,0,0,0 //NV_BASIC#Basic Skill# 4105,142,1,0,0,0,0,0,0,0,0,0,0 //NV_FIRSTAID#First Aid# @@ -4965,6 +5048,8 @@ 4105,2432,5,2427,1,0,0,0,0,0,0,0,0 //WM_MELODYOFSINK#Melody Of Sink# 4105,2433,5,2431,1,0,0,0,0,0,0,0,0 //WM_BEYOND_OF_WARCRY#Warcry Of Beyond# 4105,2434,5,2429,1,2433,1,0,0,0,0,0,0 //WM_UNLIMITED_HUMMING_VOICE#Unlimited Humming Voice# +4105,5007,5,2412,1,0,0,0,0,0,0,0,0 //WM_FRIGG_SONG# +4105,5014,5,0,0,0,0,0,0,0,0,0,0 //ALL_FULL_THROTTLE#Full Throttle# //Baby Sura 4106,1,9,0,0,0,0,0,0,0,0,0,0 //NV_BASIC#Basic Skill# 4106,142,1,0,0,0,0,0,0,0,0,0,0 //NV_FIRSTAID#First Aid# @@ -5025,6 +5110,8 @@ 4106,2348,5,2347,5,0,0,0,0,0,0,0,0 //SR_GENTLETOUCH_REVITALIZE#Gentle Touch - Revitalize# 4106,2517,5,2340,1,2518,3,0,0,0,0,0,0 //SR_HOWLINGOFLION#Howling Of Lion# 4106,2518,5,267,3,0,0,0,0,0,0,0,0 //SR_RIDEINLIGHTNING#Ride In Lightening# +4106,5009,5,2326,3,2329,3,2330,1,2327,1,0,0 //SR_FLASHCOMBO#Flash Combo# +4106,5014,5,0,0,0,0,0,0,0,0,0,0 //ALL_FULL_THROTTLE#Full Throttle# //Baby Genetic 4107,1,9,0,0,0,0,0,0,0,0,0,0 //NV_BASIC#Basic Skill# 4107,142,1,0,0,0,0,0,0,0,0,0,0 //NV_FIRSTAID#First Aid# @@ -5080,7 +5167,9 @@ 4107,2495,2,2497,1,0,0,0,0,0,0,0,0 //GN_MIX_COOKING#Mix Cooking# 4107,2496,2,2495,1,0,0,0,0,0,0,0,0 //GN_MAKEBOMB#Create Bomb# 4107,2497,10,0,0,0,0,0,0,0,0,0,0 //GN_S_PHARMACY#Special Pharmacy# +4107,5003,5,2497,1,0,0,0,0,0,0,0,0 //GN_ILLUSIONDOOPING#Hallucination Drug# 4107,2535,1,41,1,0,0,0,0,0,0,0,0 //ALL_BUYING_STORE#Open Buying Store# +4107,5014,5,0,0,0,0,0,0,0,0,0,0 //ALL_FULL_THROTTLE#Full Throttle# //Baby Shadow Chaser 4108,1,9,0,0,0,0,0,0,0,0,0,0 //NV_BASIC#Basic Skill# 4108,142,1,0,0,0,0,0,0,0,0,0,0 //NV_FIRSTAID#First Aid# @@ -5139,6 +5228,8 @@ 4108,2302,3,2296,3,2301,3,0,0,0,0,0,0 //SC_MAELSTROM#Maelstrom# 4108,2303,3,2300,3,0,0,0,0,0,0,0,0 //SC_BLOODYLUST#Bloody Lust# 4108,2304,3,2300,3,0,0,0,0,0,0,0,0 //SC_FEINTBOMB#Feint Bomb# +4108,5010,5,2288,2,0,0,0,0,0,0,0,0 //SC_SCAPE#Scape# +4108,5014,5,0,0,0,0,0,0,0,0,0,0 //ALL_FULL_THROTTLE#Full Throttle# //Baby Rune Knight (Dragon) 4109,1,9,0,0,0,0,0,0,0,0,0,0 //NV_BASIC#Basic Skill# 4109,142,1,0,0,0,0,0,0,0,0,0,0 //NV_FIRSTAID#First Aid# @@ -5178,6 +5269,8 @@ 4109,2009,5,2007,2,0,0,0,0,0,0,0,0 //RK_DRAGONHOWLING#Dragon Howling# 4109,2010,10,0,0,0,0,0,0,0,0,0,0 //RK_RUNEMASTERY#Rune Mastery# 4109,2020,5,57,2,0,0,0,0,0,0,0,0 //RK_PHANTOMTHRUST#Phantom Thrust# +4009,5004,10,2007,2,0,0,0,0,0,0,0,0 //RK_DRAGONBREATH_WATER#Dragon Breath(Water)# +4109,5014,5,0,0,0,0,0,0,0,0,0,0 //ALL_FULL_THROTTLE#Full Throttle# //Baby Royal Guard (Gryphon) 4110,1,9,0,0,0,0,0,0,0,0,0,0 //NV_BASIC#Basic Skill# 4110,142,1,0,0,0,0,0,0,0,0,0,0 //NV_FIRSTAID#First Aid# @@ -5232,6 +5325,8 @@ 4110,2323,5,2311,3,0,0,0,0,0,0,0,0 //LG_EARTHDRIVE#Earth Drive# 4110,2324,5,2318,3,2319,3,0,0,0,0,0,0 //LG_HESPERUSLIT#Hesperus Lit# 4110,2325,5,2315,3,2321,4,2322,5,0,0,0,0 //LG_INSPIRATION#Inspiration# +4110,5013,5,2311,5,0,0,0,0,0,0,0,0 //LG_KINGS_GRACE#King's Grace# +4110,5014,5,0,0,0,0,0,0,0,0,0,0 //ALL_FULL_THROTTLE#Full Throttle# //Baby Ranger (Warg) 4111,1,9,0,0,0,0,0,0,0,0,0,0 //NV_BASIC#Basic Skill# 4111,142,1,0,0,0,0,0,0,0,0,0,0 //NV_FIRSTAID#First Aid# @@ -5286,6 +5381,8 @@ 4111,2252,1,2248,1,0,0,0,0,0,0,0,0 //RA_VERDURETRAP#Verdure Trap# 4111,2253,5,2237,1,0,0,0,0,0,0,0,0 //RA_FIRINGTRAP#Firing Trap# 4111,2254,5,2237,1,0,0,0,0,0,0,0,0 //RA_ICEBOUNDTRAP#Icebound Trap# +4111,5002,5,2234,5,0,0,0,0,0,0,0,0 //RA_UNLIMIT#Unlimit# +4111,5014,5,0,0,0,0,0,0,0,0,0,0 //ALL_FULL_THROTTLE#Full Throttle# //Baby Mechanic (Mado) 4112,1,9,0,0,0,0,0,0,0,0,0,0 //NV_BASIC#Basic Skill# 4112,142,1,0,0,0,0,0,0,0,0,0,0 //NV_FIRSTAID#First Aid# @@ -5355,7 +5452,9 @@ 4112,2281,5,2277,2,0,0,0,0,0,0,0,0 //NC_SILVERSNIPER#FAW - Silver Sniper# 4112,2282,5,2277,2,0,0,0,0,0,0,0,0 //NC_MAGICDECOY#FAW - Magic Decoy# 4112,2283,1,2281,1,0,0,0,0,0,0,0,0 //NC_DISJOINT#FAW Removal# +4112,5006,5,0,0,0,0,0,0,0,0,0,0 //NC_MAGMA_ERUPTION#Magma Eruption# 4112,2535,1,41,1,0,0,0,0,0,0,0,0 //ALL_BUYING_STORE#Open Buying Store# +4112,5014,5,0,0,0,0,0,0,0,0,0,0 //ALL_FULL_THROTTLE#Full Throttle# //Super Novice (Expanded) 4190,1,9,0,0,0,0,0,0,0,0,0,0 //NV_BASIC#Basic Skill# 4190,142,1,0,0,0,0,0,0,0,0,0,0 //NV_FIRSTAID#First Aid# diff --git a/db/re/skill_unit_db.txt b/db/re/skill_unit_db.txt index d8c19dbe9..7468c6cc3 100644 --- a/db/re/skill_unit_db.txt +++ b/db/re/skill_unit_db.txt @@ -2,7 +2,7 @@ // // layout = -1:special, 0:1*1, 1:3*3, 2:5*5, up to 5:11*11 // target = friend (party +guildmates +neutral players) / party / guild -// ally (party +guildmates) / all / sameguild (guild but no allies) / enemy +// ally (party +guildmates) / all / enemy // flag 0x001(UF_DEFNOTENEMY) If 'defunit_not_enemy' is set, the target is changed to 'friend' // 0x002(UF_NOREITERRATION) Spell cannot be stacked // 0x004(UF_NOFOOTSET) Spell cannot be cast near/on targets @@ -30,7 +30,7 @@ 21,0x86, , 0, 2,1000,enemy, 0x018 //MG_THUNDERSTORM 25,0x85, , 1, 0, -1,all, 0x003 //AL_PNEUMA 27,0x81,0x80, 0, 0, -1,all, 0x00E //AL_WARP - 47,0x86, , 0, 2,1000,enemy, 0x080 //AC_SHOWER + 47,0x86, , 0, 2:2:2:2:2:3:3:3:3:3,1000,enemy, 0x080 //AC_SHOWER 70,0x83, , -1, 1,1000,all, 0x018 //PR_SANCTUARY 79,0x84, , -1, 1,3000,enemy, 0x018 //PR_MAGNUS 80,0x87,0x88, 0, 1,2000,enemy, 0x006 //WZ_FIREPILLAR @@ -105,8 +105,8 @@ 2032,0xe1, , 2, 0,1000,enemy, 0x018 //GC_POISONSMOKE -2214,0x86, , 0, 5, 100,enemy, 0x080 //WL_CHAINLIGHTNING -2216,0xcb, , -1, 0, 150,enemy, 0x018 //WL_EARTHSTRAIN +2213,0x86, , 0, 8, 100,enemy, 0x018 //WL_COMET +2216,0xcb, , -1, 0, 100,enemy, 0x018 //WL_EARTHSTRAIN 2238,0xd8, , 0, 1,1000,enemy, 0x006 //RA_ELECTRICSHOCKER 2239,0xd9, , 0, 1,1000,enemy, 0x006 //RA_CLUSTERBOMB @@ -158,7 +158,10 @@ 3008,0x86, , 0, 2, 100,enemy, 0x018 //KO_MUCHANAGE 3009,0x86, , 0, 3, 500,enemy, 0x018 //KO_HUUMARANKA 3020,0xf8, , 0, 3, 100,all, 0x018 //KO_ZENKAI -3010,0xfc, , 0, 1,1000,enemy, 0x020 //KO_MAKIBISHI +3010,0xfc, , 0, 0,5000,enemy, 0x018 //KO_MAKIBISHI + +5006,0x101, , 0, 3,2000,enemy, 0x018 //NC_MAGMA_ERUPTION +5010,0xfe, , 0, 2, -1,enemy, 0x000 //SC_SCAPE 8020,0xf5, , 0, 3,2300:2100:1900:1700:1500,enemy, 0x018 //MH_POISON_MIST 8033,0x7e, , 0, 0, -1,all, 0x003 //MH_STEINWAND @@ -177,7 +180,7 @@ 8409,0xef, , 0, 1,1000,friend,0x018 //EL_ZEPHYR 8412,0xf0, , 0, 1, -1,friend,0x018 //EL_POWER_OF_GAIA -10006,0xc1, , 2, 0, -1,sameguild, 0x040 //GD_LEADERSHIP -10007,0xc2, , 2, 0, -1,sameguild, 0x040 //GD_GLORYWOUNDS -10008,0xc3, , 2, 0, -1,sameguild, 0x040 //GD_SOULCOLD -10009,0xc4, , 2, 0, -1,sameguild, 0x040 //GD_HAWKEYES +10006,0xc1, , 2, 0, -1,guild, 0x040 //GD_LEADERSHIP +10007,0xc2, , 2, 0, -1,guild, 0x040 //GD_GLORYWOUNDS +10008,0xc3, , 2, 0, -1,guild, 0x040 //GD_SOULCOLD +10009,0xc4, , 2, 0, -1,guild, 0x040 //GD_HAWKEYES diff --git a/db/sc_config.txt b/db/sc_config.txt new file mode 100644 index 000000000..2da6f3147 --- /dev/null +++ b/db/sc_config.txt @@ -0,0 +1,407 @@ +// Status Change configuration database +// +// Structure of Database: +// SC_NAME, flag +// +// flag 0x1 - SC cannot be removed by death. +// 0x2 - SC cannot be saved. +// 0x4 - SC cannot be reset by dispell. +// 0x8 - SC cannot be reset by clearance. +// 0x10 - SC considered as buff and be removed by Hermode and etc. +// 0x20 - SC considered as debuff and be removed by Gospel and etc. +// 0x40 - SC cannot be reset when MADO Gear is taken off. + +SC_PROVOKE, 0x20 +SC_ENDURE, 0x15 +SC_TWOHANDQUICKEN, 0x18 +SC_CONCENTRATION, 0x10 +SC_ENCHANTPOISON, 0x10 +SC_POISONREACT, 0x10 +SC_QUAGMIRE, 0x2A +SC_ANGELUS, 0x10 +SC_BLESSING, 0x50 +SC_INC_AGI, 0x50 +SC_DEC_AGI, 0x22 +SC_SLOWPOISON, 0x18 +SC_IMPOSITIO, 0x10 +SC_SUFFRAGIUM, 0x10 +SC_ASPERSIO, 0x50 +SC_BENEDICTIO, 0x1A +SC_KYRIE, 0x10 +SC_MAGNIFICAT, 0x12 +SC_GLORIA, 0x10 +SC_LEXAETERNA, 0x12 +SC_ADRENALINE, 0x10 +SC_WEAPONPERFECT, 0x10 +SC_OVERTHRUST, 0x10 +SC_MAXIMIZEPOWER, 0x10 +SC_TRICKDEAD, 0x1A +SC_SHOUT, 0x10 +SC_ENERGYCOAT, 0x10 +SC_ATTHASTE_POTION1, 0x18 +SC_ATTHASTE_POTION2, 0x18 +SC_ATTHASTE_POTION3, 0x10 +//SC_MOVHASTE_POTION, 0x1A +//SC_POSTDELAY, 0x1D +SC_BARRIER, 0x10 +SC_NOEQUIPWEAPON, 0x1E +SC_NOEQUIPSHIELD, 0x1E +SC_NOEQUIPARMOR, 0x1E +SC_NOEQUIPHELM, 0x1E +SC_PROTECTWEAPON, 0x1C +SC_PROTECTSHIELD, 0x1C +SC_PROTECTARMOR, 0x1C +SC_PROTECTHELM, 0x1C +SC_AUTOGUARD, 0x18 +SC_REFLECTSHIELD, 0x18 +SC_DEVOTION, 0x12 +SC_PROVIDENCE, 0x12 +SC_DEFENDER, 0x10 +SC_MAGICROD, 0x1A +//SC_WEAPONPROPERTY, 0x18 +SC_AUTOSPELL, 0x15 +//SC_SPECIALZONE, 0x1A +//SC_MASK, 0x1A +SC_SPEARQUICKEN, 0x10 +SC_BLADESTOP, 0x1A +SC_EXPLOSIONSPIRITS, 0x1A +SC_STEELBODY, 0x12 +SC_PROPERTYFIRE, 0x1D +SC_PROPERTYWATER, 0x1D +SC_PROPERTYWIND, 0x1D +SC_PROPERTYGROUND, 0x1D +SC_STOP, 0x1A +SC_PROPERTYUNDEAD, 0x1A +//SC_STATUSONE, 0x1A +SC_AURABLADE, 0x12 +SC_PARRYING, 0x1A +SC_LKCONCENTRATION, 0x12 +SC_TENSIONRELAX, 0x1A +SC_BERSERK, 0x12 +SC_SACRIFICE, 0x1A +SC_GOSPEL, 0x22 +SC_ASSUMPTIO, 0x10 +SC_BASILICA, 0x1A +//SC_GROUNDMAGIC, 0x1A //is divided to SC_VOLCANO, 0xSC_DELUGE, 0xSC_VIOLENTGALE +SC_VOLCANO, 0x1A +SC_DELUGE, 0x1A +SC_VIOLENTGALE, 0x1A +SC_MAGICPOWER, 0x12 +SC_EDP, 0x17 +SC_TRUESIGHT, 0x12 +SC_WINDWALK, 0x12 +SC_MELTDOWN, 0x17 +SC_CARTBOOST, 0x17 +SC_BLOODING, 0x1A +SC_JOINTBEAT, 0x2A +SC_MINDBREAKER, 0x12 +SC_MEMORIZE, 0x12 +SC_FOGWALL, 0x1A +SC_SPIDERWEB, 0x2F +//SC_SUB_WEAPONPROPERTY, 0x17 +SC_RUN, 0x1A +SC_STRUP, 0x1A +SC_PROPERTYDARK, 0x1A +SC_ADRENALINE2, 0x12 +SC_PROPERTYTELEKINESIS, 0x1A +SC_SOULLINK, 0x1A +SC_PLUSATTACKPOWER, 0x58 +SC_PLUSMAGICPOWER, 0x58 +SC_KAITE, 0x1A +SC_KAAHI, 0x1A +SC_KAUPE, 0x1A +SC_ONEHANDQUICKEN, 0x1A +//SC_GDSKILL_POSTDELAY, 0x1D +SC_PRESERVE, 0x12 +SC_CHASEWALK2, 0x1A +//SC_MOVESLOW_POTION, 0x1A +SC_DOUBLECASTING, 0x1A +SC_GRAVITATION, 0x1A +SC_OVERTHRUSTMAX, 0x12 +SC_TAROTCARD, 0x2A +SC_CR_SHRINK, 0x17 +SC_WZ_SIGHTBLASTER, 0x17 +SC_RG_CCONFINE_M, 0x1F +SC_RG_CCONFINE_S, 0x1F +SC_NJ_UTSUSEMI, 0x1A +SC_NJ_BUNSINJYUTSU, 0x1A +SC_NJ_SUITON, 0x2F +//SC_MENTAL, 0x1A +//SC_EXPMEMORY, 0x1A +//SC_PERFORMANCE, 0x1A +//SC_GAIN, 0x1A +//SC_DRIFT, 0x1A +//SC_WALLSHIFT, 0x1A +//SC_REINCARNATION, 0x1A +//SC_DENERGY, 0x1A +//SC_DAURA, 0x1A +//SC_DFREEZER, 0x1A +//SC_DPUNISH, 0x1A +//SC_DBARRIER, 0x1A +//SC_DWARNING, 0x1A +//SC_MOUSEWHEEL, 0x1E +//SC_DACCEL, 0x1A +//SC_DBLOCK, 0x1A +SC_FOOD_STR, 0x1C +SC_FOOD_AGI, 0x1C +SC_FOOD_VIT, 0x1C +SC_FOOD_DEX, 0x1C +SC_FOOD_INT, 0x1C +SC_FOOD_LUK, 0x1C +SC_FOOD_BASICAVOIDANCE, 0x58 +SC_FOOD_BASICHIT, 0x58 +//SC_FOOD_CRITICALSUCCESSVALUE, 0x18 +SC_CASH_PLUSEXP, 0x1D +SC_CASH_DEATHPENALTY, 0x1D +SC_CASH_RECEIVEITEM, 0x1D +SC_CASH_BOSS_ALARM, 0x1E +//SC_DA_ENERGY, 0x1A +//SC_DA_FIRSTSLOT, 0x1A +//SC_DA_HEADDEF, 0x1A +//SC_DA_SPACE, 0x1E +//SC_DA_ITEMREBUILD, 0x1E +//SC_DA_ILLUSION, 0x1A +//SC_DA_EARPLUG, 0x1E +//SC_DA_CONTRACT, 0x1D +//SC_DA_BLACK, 0x1E +//SC_DA_MAGICCART, 0x1A +//SC_CRYSTAL, 0x1E +//SC_DA_REBUILD, 0x1D +//SC_DA_EDARKNESS, 0x1A +//SC_DA_EGUARDIAN, 0x1A +//SC_DA_TIMEOUT, 0x1A +SC_FOOD_STR_CASH, 0x1D +SC_FOOD_AGI_CASH, 0x1D +SC_FOOD_VIT_CASH, 0x1D +SC_FOOD_DEX_CASH, 0x1D +SC_FOOD_INT_CASH, 0x1D +SC_FOOD_LUK_CASH, 0x1D +SC_MER_FLEE, 0x1C +SC_MER_ATK, 0x1C +SC_MER_HP, 0x1C +SC_MER_SP, 0x1C +SC_MER_HIT, 0x1C +SC_SLOWCAST, 0x1F +SC_CRITICALWOUND, 0x17 +SC_MOVHASTE_HORSE, 0x1F +SC_PROTECT_DEF, 0x1C +SC_PROTECT_MDEF, 0x1C +SC_HEALPLUS, 0x5C +SC_S_LIFEPOTION, 0x5C +SC_L_LIFEPOTION, 0x5C +SC_CRITICALPERCENT, 0x5C +SC_PLUSAVOIDVALUE, 0x5C +//SC_ATKER_ASPD, 0x1C +//SC_TARGET_ASPD, 0x5C +//SC_ATKER_MOVESPEED, 0x1C +SC_ATKER_BLOOD, 0x1C +SC_TARGET_BLOOD, 0x1E +SC_ARMOR_PROPERTY, 0x1D +//SC_REUSE_LIMIT_A, 0x1D +SC_HELLPOWER, 0x1D +//SC_STEAMPACK, 0x5C +//SC_REUSE_LIMIT_B, 0x1D +//SC_REUSE_LIMIT_C, 0x1D +//SC_REUSE_LIMIT_D, 0x1D +//SC_REUSE_LIMIT_E, 0x1D +//SC_REUSE_LIMIT_F, 0x1D +SC_CASH_PLUSONLYJOBEXP, 0x1D +SC_PARTYFLEE, 0x18 +//SC_ANGEL_PROTECT, 0x18 +//SC_ENDURE_MDEF, 0x15 +SC_ENCHANTBLADE, 0x10 +SC_DEATHBOUND, 0x1E +SC_REFRESH, 0x16 +SC_GIANTGROWTH, 0x14 +SC_STONEHARDSKIN, 0x17 +SC_VITALITYACTIVATION, 0x14 +SC_FIGHTINGSPIRIT, 0x14 +SC_ABUNDANCE, 0x14 +//SC_REUSE_MILLENNIUMSHIELD, 0x1D +//SC_REUSE_CRUSHSTRIKE, 0x1D +//SC_REUSE_REFRESH, 0x1D +//SC_REUSE_STORMBLAST, 0x1D +SC_EPICLESIS, 0x1D +SC_ORATIO, 0x14 +SC_LAUDAAGNUS, 0x14 +SC_LAUDARAMUS, 0x14 +SC_CLOAKINGEXCEED, 0x1E +SC_HALLUCINATIONWALK, 0x1C +SC_HALLUCINATIONWALK_POSTDELAY, 0x1F +SC_RENOVATIO, 0x14 +SC_WEAPONBLOCKING, 0x1C +//SC_WEAPONBLOCKING_POSTDELAY, 0x1F +SC_ROLLINGCUTTER, 0x1E +SC_EXPIATIO, 0x14 +SC_POISONINGWEAPON, 0x1C +SC_TOXIN, 0x14 +SC_PARALYSE, 0x14 +SC_VENOMBLEED, 0x14 +SC_MAGICMUSHROOM, 0x14 +SC_DEATHHURT, 0x14 +SC_PYREXIA, 0x14 +SC_OBLIVIONCURSE, 0x14 +SC_LEECHESEND, 0x14 +SC_DUPLELIGHT, 0x14 +SC_FEARBREEZE, 0x1C +SC_ELECTRICSHOCKER, 0x1E +SC_MARSHOFABYSS, 0x14 +SC_RECOGNIZEDSPELL, 0x14 +//SC_WUGRIDER, 0x1D +SC_WUGDASH, 0x1E +SC_WUGBITE, 0x1E +SC_CAMOUFLAGE, 0x1E +SC_ACCELERATION, 0x1C +SC_HOVERING, 0x1C +SC_SUMMON1, 0x18 +SC_SUMMON2, 0x18 +SC_SUMMON3, 0x18 +SC_SUMMON4, 0x18 +SC_SUMMON5, 0x18 +//SC_MVPCARD_TAOGUNKA, 0x1C +//SC_MVPCARD_MISTRESS, 0x1C +//SC_MVPCARD_ORCHERO, 0x1C +//SC_MVPCARD_ORCLORD, 0x1C +SC_OVERHEAT_LIMITPOINT, 0x1C +SC_OVERHEAT, 0x1C +SC_SHAPESHIFT, 0x1C +SC_INFRAREDSCAN, 0x1C +SC_MAGNETICFIELD, 0x1E +SC_NEUTRALBARRIER, 0x1E +SC_NEUTRALBARRIER_MASTER, 0x1E +SC_STEALTHFIELD_MASTER, 0x1E +SC_MANU_ATK, 0x1C +SC_MANU_DEF, 0x1C +SC_SPL_ATK, 0x1C +SC_SPL_DEF, 0x1C +SC__REPRODUCE, 0x1C +SC_MANU_MATK, 0x1C +SC_SPL_MATK, 0x1C +//SC_STR_SCROLL, 0x1D +//SC_INT_SCROLL, 0x1D +SC_FORCEOFVANGUARD, 0x1C +//SC_BUCHEDENOEL, 0x1C +SC__AUTOSHADOWSPELL, 0x10 +SC__SHADOWFORM, 0x1E +SC_RAID, 0x1C +SC_SHIELDSPELL_DEF, 0x10 +SC_SHIELDSPELL_MDEF, 0x10 +SC_SHIELDSPELL_REF, 0x10 +SC__BODYPAINT, 0x14 +SC_EXEEDBREAK, 0x1C +SC_ADORAMUS, 0x10 +SC_PRESTIGE, 0x10 +SC__INVISIBILITY, 0x1E +SC__DEADLYINFECT, 0x14 +SC_BANDING, 0x1C +SC_BANDING_DEFENCE, 0x1C +SC_EARTHDRIVE, 0x14 +SC_INSPIRATION, 0x1C +SC__ENERVATION, 0x10 +SC__GROOMY, 0x10 +SC_RAISINGDRAGON, 0x1E +SC__IGNORANCE, 0x10 +SC__LAZINESS, 0x10 +SC_LIGHTNINGWALK, 0x1C +//SC_ACARAJE, 0x18 +SC__UNLUCKY, 0x10 +SC_CURSEDCIRCLE_ATKER, 0x1C +SC_CURSEDCIRCLE_TARGET, 0x1C +SC__WEAKNESS, 0x10 +SC_CRESCENTELBOW, 0x1C +//SC_NOEQUIPACCESSARY, 0x1E +SC__STRIPACCESSARY, 0x1C +SC__MANHOLE, 0x5E +//SC_POPECOOKIE, 0x1C +SC__BLOODYLUST, 0x20 +SC_SWING, 0x1C +SC_SYMPHONY_LOVE, 0x1C +SC_PROPERTYWALK, 0x12 +SC_SPELLFIST, 0x10 +SC_NETHERWORLD, 0x10 +SC_SIREN, 0x10 +SC_DEEP_SLEEP, 0x22 +SC_SIRCLEOFNATURE, 0x10 +SC_GLOOMYDAY, 0x10 +SC_GLOOMYDAY_SK, 0x10 +SC_SONG_OF_MANA, 0x10 +SC_DANCE_WITH_WUG, 0x10 +SC_RUSH_WINDMILL, 0x1C +SC_ECHOSONG, 0x1C +SC_HARMONIZE, 0x10 +SC_MOONLIT_SERENADE, 0x1C +SC_SATURDAY_NIGHT_FEVER, 0x10 +SC_SITDOWN_FORCE, 0x1C +SC_ANALYZE, 0x1C +SC_LERADS_DEW, 0x1C +SC_MELODYOFSINK, 0x1C +SC_BEYOND_OF_WARCRY, 0x1C +SC_UNLIMITED_HUMMING_VOICE, 0x1C +SC_WARMER, 0x2 +SC_VENOMIMPRESS, 0x4 +SC_FROSTMISTY, 0x20 +//SC_ASSUMPTIO2, 0x10 +//SC_GN_TRAINING_SWORD, 0x1F +//SC_GN_REMODELING_CART, 0x1F +SC_STOMACHACHE, 0x20 +SC_MYSTERIOUS_POWDER, 0x20 +//SC_ELEMENTAL_AGGRESSIVE, 0x2 +//SC_ELEMENTAL_WAIT, 0x2 +//SC_ELEMENTAL_PASSIVE, 0x2 +//SC_ELEMENTAL_DEFENSIVE, 0x2 +SC_WATER_BARRIER, 0x2 +SC_ZEPHYR, 0x2 +SC_POWER_OF_GAIA, 0x2 +SC_FIRE_INSIGNIA, 0x2 +SC_WATER_INSIGNIA, 0x2 +SC_WIND_INSIGNIA, 0x2 +SC_EARTH_INSIGNIA, 0x2 +//SC_MORA_BUFF, 0x2 +//SC_REUSE_LIMIT_G, 0x1D +//SC_REUSE_LIMIT_H, 0x1D +SC_NEEDLE_OF_PARALYZE, 0x1 +SC_PAIN_KILLER, 0x1 +//SC_G_LIFEPOTION, 0x44 +//SC_VITALIZE_POTION, 0x4 +SC_LIGHT_OF_REGENE, 0x1 +//SC_SONIC_CLAW_POSTDELAY, 0x2 +//SC_SILVERVEIN_RUSH_POSTDELAY, 0x2 +//SC_MIDNIGHT_FRENZY_POSTDELAY, 0x2 +//SC_TINDER_BREAKER, 0x2 +//SC_TINDER_BREAKER_POSTDELAY, 0x2 +//SC_CBC, 0x2 +//SC_CBC_POSTDELAY, 0x2 +//SC_EQC, 0x2 +//SC_MAGIC_CANDY, 0x5C +//SC_ALL_RIDING_REUSE_LIMIT, 0x1 +//SC_HANDICAPSTATE_DEEP_SLEEP, 0x50 + +SC_FULL_THROTTLE, 0x12 +SC_REBOUND, 0x12 +SC_TELEKINESIS_INTENSE, 0x12 + +// Unremovable +SC_WEIGHTOVER50, 0x4F +SC_WEIGHTOVER90, 0x4F +SC_XMAS, 0x4D +SC_SUMMER, 0x4D +SC_NOCHAT, 0x4D +SC_FUSION, 0x4D +SC_EARTHSCROLL, 0x4D +SC_STORMKICK_READY, 0x4D +SC_DOWNKICK_READY, 0x4D +SC_COUNTERKICK_READY, 0x4D +SC_TURNKICK_READY, 0x4D +SC_DODGE_READY, 0x4D +SC_JAILED, 0x4D +SC_AUTOTRADE, 0x4D +SC_WHISTLE, 0x4F +SC_ASSNCROS, 0x4F +SC_POEMBRAGI, 0x4F +SC_APPLEIDUN, 0x4F +SC_HUMMING, 0x4F +SC_DONTFORGETME, 0x4F +SC_FORTUNE, 0x4F +SC_SERVICEFORYOU, 0x4F +SC_INCHIT, 0x4D +SC_PUSH_CART, 0x4D \ No newline at end of file diff --git a/doc/script_commands.txt b/doc/script_commands.txt index 3bac278bb..0441d385a 100644 --- a/doc/script_commands.txt +++ b/doc/script_commands.txt @@ -1,4 +1,4 @@ -//===== Hercules Documentation =============================== +//===== Hercules Documentation =============================== //= Hercules Script Commands //===== By: ================================================== //= Hercules Dev Team @@ -183,9 +183,8 @@ There are two optional fields for monster size and AI. Size can be 0 (medium), 1 (small), or 2 (big). AI can be 0 (default), 1 (attack/friendly), 2 (sphere), 3 (flora), or 4 (zanzou). -Alternately, a monster spawned using 'boss_monster' instead of 'monster' -is able to be detected on the map with the SC_BOSSMAPINFO status (used by -Convex Mirror, item ID# 12214). +Alternately, a monster spawned using 'boss_monster' instead of 'monster' is able +to be detected on the map with the SC_CASH_BOSS_ALARM status (used by Convex Mirror, item ID# 12214). ** NPC names diff --git a/npc/cities/rachel.txt b/npc/cities/rachel.txt index db3c6816e..88eb359f1 100644 --- a/npc/cities/rachel.txt +++ b/npc/cities/rachel.txt @@ -308,8 +308,8 @@ rachel,206,30,3 script Freya's Priest#play 920,{ set .@play,rand(1,10); if (.@play == 1) warp "Random",0,0; else if (.@play == 2) warp "Random",0,0; - else if (.@play == 3) sc_start SC_SpeedUp1,5000,0; - else if (.@play == 4) sc_start SC_SpeedUp1,5000,0; + else if (.@play == 3) sc_start SC_MOVHASTE_INFINITY,5000,0; + else if (.@play == 4) sc_start SC_MOVHASTE_INFINITY,5000,0; else sc_start SC_SlowDown,5000,0; end; } diff --git a/npc/custom/healer.txt b/npc/custom/healer.txt index 31f247695..a6f028e8a 100644 --- a/npc/custom/healer.txt +++ b/npc/custom/healer.txt @@ -26,7 +26,7 @@ } specialeffect2 313; percentheal 100,100; if (.@Buffs) { - specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,240000,10; + specialeffect2 EF_INCAGILITY; sc_start SC_INC_AGI,240000,10; specialeffect2 EF_BLESSING; sc_start SC_BLESSING,240000,10; } if (.@Delay) set @HD, gettimetick(2)+.@Delay; diff --git a/npc/events/halloween_2009.txt b/npc/events/halloween_2009.txt index 9dee31807..a5faf713e 100644 --- a/npc/events/halloween_2009.txt +++ b/npc/events/halloween_2009.txt @@ -118,13 +118,13 @@ OnTouch: mes "[Trick or Treater]"; mes "Yay thank you!"; mes "Here, take this for being so nice!"; - sc_start SC_STRFood, 1800000, 5; - sc_start SC_INTFood, 1800000, 5; - sc_start SC_VITFood, 1800000, 5; - sc_start SC_AGIFood, 1800000, 5; - sc_start SC_DEXFood, 1800000, 5; - sc_start SC_LUKFood, 1800000, 5; - sc_start SC_FLEEFOOD, 1800000, 15; + sc_start SC_FOOD_STR, 1800000, 5; + sc_start SC_FOOD_INT, 1800000, 5; + sc_start SC_FOOD_VIT, 1800000, 5; + sc_start SC_FOOD_AGI, 1800000, 5; + sc_start SC_FOOD_DEX, 1800000, 5; + sc_start SC_FOOD_LUK, 1800000, 5; + sc_start SC_FOOD_BASICAVOIDANCE, 1800000, 15; delitem 529,1; // Candy close; }else{ @@ -139,13 +139,13 @@ OnTouch: mes "[Trick or Treater]"; mes "Yay thank you!"; mes "Here, take this for being so nice!"; - sc_start SC_STRFood, 1800000, 5; - sc_start SC_INTFood, 1800000, 5; - sc_start SC_VITFood, 1800000, 5; - sc_start SC_AGIFood, 1800000, 5; - sc_start SC_DEXFood, 1800000, 5; - sc_start SC_LUKFood, 1800000, 5; - sc_start SC_FLEEFOOD, 1800000, 15; + sc_start SC_FOOD_STR, 1800000, 5; + sc_start SC_FOOD_INT, 1800000, 5; + sc_start SC_FOOD_VIT, 1800000, 5; + sc_start SC_FOOD_AGI, 1800000, 5; + sc_start SC_FOOD_DEX, 1800000, 5; + sc_start SC_FOOD_LUK, 1800000, 5; + sc_start SC_FOOD_BASICAVOIDANCE, 1800000, 15; delitem 530,1; // Candy Cane close; }else{ @@ -160,13 +160,13 @@ OnTouch: mes "[Trick or Treater]"; mes "Yay thank you!"; mes "Here, take this for being so nice!"; - sc_start SC_STRFood, 1800000, 5; - sc_start SC_INTFood, 1800000, 5; - sc_start SC_VITFood, 1800000, 5; - sc_start SC_AGIFood, 1800000, 5; - sc_start SC_DEXFood, 1800000, 5; - sc_start SC_LUKFood, 1800000, 5; - sc_start SC_FLEEFOOD, 1800000, 15; + sc_start SC_FOOD_STR, 1800000, 5; + sc_start SC_FOOD_INT, 1800000, 5; + sc_start SC_FOOD_VIT, 1800000, 5; + sc_start SC_FOOD_AGI, 1800000, 5; + sc_start SC_FOOD_DEX, 1800000, 5; + sc_start SC_FOOD_LUK, 1800000, 5; + sc_start SC_FOOD_BASICAVOIDANCE, 1800000, 15; delitem 538,1; // Well-baked Cookie close; }else{ diff --git a/npc/events/nguild/nguild_warper.txt b/npc/events/nguild/nguild_warper.txt index 57f5bc827..ac54c0716 100644 --- a/npc/events/nguild/nguild_warper.txt +++ b/npc/events/nguild/nguild_warper.txt @@ -64,7 +64,7 @@ prontera,146,163,6 script Novice Castles 729,{ sc_end SC_IMPOSITIO; sc_end SC_SUFFRAGIUM; sc_end SC_MAGNIFICAT; - sc_end SC_WEAPONPERFECTION; + sc_end SC_WEAPONPERFECT; sc_end SC_GOSPEL; sc_end SC_BASILICA; sc_end SC_MAGICPOWER; @@ -72,8 +72,8 @@ prontera,146,163,6 script Novice Castles 729,{ sc_end SC_MARIONETTE2; sc_end SC_DEVOTION; sc_end SC_SACRIFICE; - sc_end SC_MAXOVERTHRUST; - sc_end SC_SPIRIT; + sc_end SC_OVERTHRUSTMAX; + sc_end SC_SOULLINK; warp "n_castle",102,93+rand(14); } } diff --git a/npc/instances/NydhoggsNest.txt b/npc/instances/NydhoggsNest.txt index 2d48d0341..f2fe3fc68 100644 --- a/npc/instances/NydhoggsNest.txt +++ b/npc/instances/NydhoggsNest.txt @@ -2182,7 +2182,7 @@ OnDisable: OnTouch: percentheal -50,0; percentheal -30,0; - sc_start SC_BLEEDING,60000,0; + sc_start SC_BLOODING,60000,0; end; OnTimer10000: diff --git a/npc/mobs/citycleaners.txt b/npc/mobs/citycleaners.txt index 0e810ac5b..876017fd4 100644 --- a/npc/mobs/citycleaners.txt +++ b/npc/mobs/citycleaners.txt @@ -46,3 +46,5 @@ einbech,0,0,0,0 monster Tarou 1175,5,1800000,1500000,0 // payon_in02 - Inside Payon //================================================== payon_in02,23,68,5,5 monster Thief Bug Egg 1048,7,1200000,600000,0 + +job3_war01,19,33,5,5 monster Thief Bug Egg 1213,1,12,60,0 diff --git a/npc/quests/skills/assassin_skills.txt b/npc/quests/skills/assassin_skills.txt index 109d699d3..4fddf6b12 100644 --- a/npc/quests/skills/assassin_skills.txt +++ b/npc/quests/skills/assassin_skills.txt @@ -758,7 +758,7 @@ OnTouch: mes "the coffin bit your"; mes "hand really hard!^000000"; sc_start SC_Poison,30000,0; - sc_start SC_Bleeding,10000,0; + sc_start SC_BLOODING,10000,0; Emotion e_omg,1; close; case 2: @@ -830,7 +830,7 @@ OnTouch: mes "the coffin bit your"; mes "hand really hard!^000000"; sc_start SC_Poison,30000,0; - sc_start SC_Bleeding,10000,0; + sc_start SC_BLOODING,10000,0; Emotion e_omg,1; close; } diff --git a/npc/re/cities/dewata.txt b/npc/re/cities/dewata.txt index 6bbbfeb4e..3c5953adf 100644 --- a/npc/re/cities/dewata.txt +++ b/npc/re/cities/dewata.txt @@ -457,32 +457,32 @@ dewata,89,191,6 script Small Shrine#dew1 844,{ callsub L_Wish; set Zeny, Zeny - .@input; if (.@stat & 1 && .@bonus){ - sc_start SC_STRFOOD,1200000,3; + sc_start SC_FOOD_STR,1200000,3; percentheal 5,0; //consumeitem 12043; //Str_Dish03 } else if (.@stat & 2 && .@bonus){ - sc_start SC_AGIFOOD,1200000,3; + sc_start SC_FOOD_AGI,1200000,3; percentheal 5,0; //consumeitem 12058; //Agi_Dish03 } else if (.@stat & 4 && .@bonus){ - sc_start SC_DEXFOOD,1200000,3; + sc_start SC_FOOD_DEX,1200000,3; percentheal 5,0; //consumeitem 12063; //Dex_Dish03 } else if (.@stat & 8 && .@bonus){ - sc_start SC_VITFOOD,1200000,3; + sc_start SC_FOOD_VIT,1200000,3; percentheal 5,0; //consumeitem 12053; //Vit_Dish03 } else if (.@stat & 16 && .@bonus){ - sc_start SC_INTFOOD,1200000,3; + sc_start SC_FOOD_INT,1200000,3; percentheal 5,0; //consumeitem 12048; //Int_Dish03 } else if (.@stat & 32 && .@bonus){ - sc_start SC_LUKFOOD,1200000,3; + sc_start SC_FOOD_LUK,1200000,3; percentheal 5,0; //consumeitem 12068; //Luk_Dish03 } diff --git a/npc/re/jobs/3-1/rune_knight.txt b/npc/re/jobs/3-1/rune_knight.txt index 6dbfdaa3a..1255c355e 100644 --- a/npc/re/jobs/3-1/rune_knight.txt +++ b/npc/re/jobs/3-1/rune_knight.txt @@ -1826,7 +1826,7 @@ job3_rune02,34,46,5 script Captain Tigris#jrt1 470,2,2,{ break; case 5: mapannounce "job3_rune02","Captain Tigris : For a Rune Knight, this kind of ordeal is nothing!",bc_map,"0xFFFF00"; //FW_NORMAL 12 0 0 - sc_start SC_BLEEDING,10000,0; + sc_start SC_BLOODING,10000,0; break; } set $@job_rune_test2,1; @@ -2161,4 +2161,4 @@ sec_in02,34,167,3 script R.Knight Job Manager 470,1,1,{ close; } job3_rune01,1,1,3 duplicate(R.Knight Job Manager) #renshucheck 844 -*/ \ No newline at end of file +*/ diff --git a/npc/re/quests/quests_brasilis.txt b/npc/re/quests/quests_brasilis.txt index 2e1cbe75a..e9256047f 100644 --- a/npc/re/quests/quests_brasilis.txt +++ b/npc/re/quests/quests_brasilis.txt @@ -227,9 +227,9 @@ brasilis,192,133,6 script Lucia#brasilis 478,{ if (.@nQState2 > -1) erasequest 9029; setquest 9029; percentheal 100,100; - sc_start SC_LUKFOOD, 1200000, 5; percentheal 5,2; - sc_start SC_VITFOOD, 1200000, 5; percentheal 10,0; - sc_start SC_DEXFOOD, 1200000, 5; percentheal 5,5; + sc_start SC_FOOD_LUK, 1200000, 5; percentheal 5,2; + sc_start SC_FOOD_VIT, 1200000, 5; percentheal 10,0; + sc_start SC_FOOD_DEX, 1200000, 5; percentheal 5,5; getitem 11502,3; //Light_Blue_Pot close; } @@ -971,7 +971,7 @@ OnTouch_: set brazil_gua,8; changequest 2197,2198; close2; - sc_start SC_SpeedUp1,5000,0; + sc_start SC_MOVHASTE_INFINITY,5000,0; end; } else { @@ -3071,13 +3071,13 @@ bra_dun02,157,74,5 script Iara#nk 478,2,2,{ delitem 11517,1; //Puri_Potion percentheal 100,100; sc_start SC_INCFLEE,3600000,20; - sc_start SC_INCCRI,3600000,10; - sc_start SC_STRFOOD,1200000,3; - sc_start SC_DEXFOOD,1200000,3; - sc_start SC_AGIFOOD,1200000,3; - sc_start SC_VITFOOD,1200000,3; - sc_start SC_INTFOOD,1200000,3; - sc_start SC_LUKFOOD,1200000,3; + sc_start SC_CRITICALPERCENT,3600000,10; + sc_start SC_FOOD_STR,1200000,3; + sc_start SC_FOOD_DEX,1200000,3; + sc_start SC_FOOD_AGI,1200000,3; + sc_start SC_FOOD_VIT,1200000,3; + sc_start SC_FOOD_INT,1200000,3; + sc_start SC_FOOD_LUK,1200000,3; next; mes "[Iara]"; mes "Ahhh~..."; diff --git a/src/char/char.c b/src/char/char.c index f889c1a25..7dfb6861c 100644 --- a/src/char/char.c +++ b/src/char/char.c @@ -2027,6 +2027,8 @@ static void char_auth_ok(int fd, struct char_session_data *sd) mapif_disconnectplayer(server[character->server].fd, character->account_id, character->char_id, 2); if (character->waiting_disconnect == INVALID_TIMER) character->waiting_disconnect = iTimer->add_timer(iTimer->gettick()+20000, chardb_waiting_disconnect, character->account_id, 0); + if (character) + character->pincode_enable = -1; WFIFOHEAD(fd,3); WFIFOW(fd,0) = 0x81; WFIFOB(fd,2) = 8; diff --git a/src/common/mmo.h b/src/common/mmo.h index c2fdfe43a..eaffdf7df 100644 --- a/src/common/mmo.h +++ b/src/common/mmo.h @@ -83,7 +83,7 @@ #define MAX_ZENY 1000000000 #define MAX_FAME 1000000000 #define MAX_CART 100 -#define MAX_SKILL 1477 +#define MAX_SKILL 1478 #define MAX_SKILL_ID 10015 // [Ind/Hercules] max used skill ID #define GLOBAL_REG_NUM 256 // Max permanent character variables per char #define ACCOUNT_REG_NUM 64 // Max permanent local account variables per account diff --git a/src/config/const.h b/src/config/const.h index 756c681c1..7acdea688 100644 --- a/src/config/const.h +++ b/src/config/const.h @@ -60,8 +60,8 @@ /* ATCMD_FUNC(mobinfo) HIT and FLEE calculations */ #ifdef RENEWAL - #define MOB_FLEE(mob) ( mob->lv + mob->status.agi + mob->status.luk/5 + 100 ) - #define MOB_HIT(mob) ( mob->lv + mob->status.dex + mob->status.luk/3 + 175 ) + #define MOB_FLEE(mob) ( mob->lv + mob->status.agi + 100 ) + #define MOB_HIT(mob) ( mob->lv + mob->status.dex + 150 ) #else #define MOB_FLEE(mob) ( mob->lv + mob->status.agi ) #define MOB_HIT(mob) ( mob->lv + mob->status.dex ) diff --git a/src/map/atcommand.c b/src/map/atcommand.c index f96c7920a..d9810e77c 100644 --- a/src/map/atcommand.c +++ b/src/map/atcommand.c @@ -6148,7 +6148,7 @@ ACMD(npctalk) unsigned long color=0; if (sd->sc.count && //no "chatting" while muted. - (sd->sc.data[SC_BERSERK] || sd->sc.data[SC_DEEPSLEEP] || sd->sc.data[SC__BLOODYLUST] || + (sd->sc.data[SC_BERSERK] || sd->sc.data[SC_DEEP_SLEEP] || sd->sc.data[SC__BLOODYLUST] || (sd->sc.data[SC_NOCHAT] && sd->sc.data[SC_NOCHAT]->val1&MANNER_NOCHAT))) return false; @@ -6199,7 +6199,7 @@ ACMD(pettalk) } if (sd->sc.count && //no "chatting" while muted. - (sd->sc.data[SC_BERSERK] || sd->sc.data[SC_DEEPSLEEP] || sd->sc.data[SC__BLOODYLUST] || + (sd->sc.data[SC_BERSERK] || sd->sc.data[SC_DEEP_SLEEP] || sd->sc.data[SC__BLOODYLUST] || (sd->sc.data[SC_NOCHAT] && sd->sc.data[SC_NOCHAT]->val1&MANNER_NOCHAT))) return false; @@ -6965,7 +6965,7 @@ ACMD(homtalk) } if (sd->sc.count && //no "chatting" while muted. - (sd->sc.data[SC_BERSERK] || sd->sc.data[SC_DEEPSLEEP] || sd->sc.data[SC__BLOODYLUST] || + (sd->sc.data[SC_BERSERK] || sd->sc.data[SC_DEEP_SLEEP] || sd->sc.data[SC__BLOODYLUST] || (sd->sc.data[SC_NOCHAT] && sd->sc.data[SC_NOCHAT]->val1&MANNER_NOCHAT))) return false; @@ -7348,7 +7348,7 @@ ACMD(me) memset(atcmd_output, '\0', sizeof(atcmd_output)); if (sd->sc.count && //no "chatting" while muted. - (sd->sc.data[SC_BERSERK] || sd->sc.data[SC_DEEPSLEEP] || sd->sc.data[SC__BLOODYLUST] || + (sd->sc.data[SC_BERSERK] || sd->sc.data[SC_DEEP_SLEEP] || sd->sc.data[SC__BLOODYLUST] || (sd->sc.data[SC_NOCHAT] && sd->sc.data[SC_NOCHAT]->val1&MANNER_NOCHAT))) return false; diff --git a/src/map/battle.c b/src/map/battle.c index a2cc7692c..a4908982c 100644 --- a/src/map/battle.c +++ b/src/map/battle.c @@ -363,14 +363,14 @@ int battle_attr_fix(struct block_list *src, struct block_list *target, int damag if( tsc->data[SC_SPIDERWEB]->val2 == 0 ) status_change_end(target, SC_SPIDERWEB, INVALID_TIMER); } - if( tsc->data[SC_THORNSTRAP]) - status_change_end(target, SC_THORNSTRAP, INVALID_TIMER); + if( tsc->data[SC_THORNS_TRAP]) + status_change_end(target, SC_THORNS_TRAP, INVALID_TIMER); if( tsc->data[SC_FIRE_CLOAK_OPTION]) damage -= damage * tsc->data[SC_FIRE_CLOAK_OPTION]->val2 / 100; if( tsc->data[SC_CRYSTALIZE] && target->type != BL_MOB) status_change_end(target, SC_CRYSTALIZE, INVALID_TIMER); if( tsc->data[SC_EARTH_INSIGNIA]) damage += damage/2; - if( tsc->data[SC_ASH]) damage += damage/2; //150% + if( tsc->data[SC_VOLCANIC_ASH]) damage += damage/2; //150% break; case ELE_HOLY: if( tsc->data[SC_ORATIO]) ratio += tsc->data[SC_ORATIO]->val1 * 2; @@ -394,1833 +394,1365 @@ int battle_attr_fix(struct block_list *src, struct block_list *target, int damag struct map_session_data *sd = BL_CAST(BL_PC, src); int s; - ARR_FIND(1, 6, s, sd->talisman[s] > 0); + ARR_FIND(1, 6, s, sd->charm[s] > 0); if( s < 5 && atk_elem == s ) - ratio += sd->talisman[s] * 2; // +2% custom value + ratio += sd->charm[s] * 2; // +2% custom value } if( target && target->type == BL_PC ) { struct map_session_data *tsd = BL_CAST(BL_PC, target); int t; - ARR_FIND(1, 6, t, tsd->talisman[t] > 0); + ARR_FIND(1, 6, t, tsd->charm[t] > 0); if( t < 5 && atk_elem == t ) - damage -= damage * ( tsd->talisman[t] * 3 ) / 100;// -3% custom value + damage -= damage * ( tsd->charm[t] * 3 ) / 100;// -3% custom value } return damage*ratio/100; } -/*========================================== - * Calculates card bonuses damage adjustments. - *------------------------------------------*/ -int battle_calc_cardfix(int attack_type, struct block_list *src, struct block_list *target, int nk, int s_ele, int s_ele_, int damage, int left, int flag){ - struct map_session_data *sd, *tsd; - short cardfix = 1000, t_class, s_class, s_race2, t_race2; - struct status_data *sstatus, *tstatus; - int i; +int battle_calc_weapon_damage(struct block_list *src, struct block_list *bl, uint16 skill_id, uint16 skill_lv, struct weapon_atk *watk, int nk, bool n_ele, short s_ele, short s_ele_, int size, int type, int flag, int flag2){ // [malufett] + int damage, eatk = 0; + struct status_change *sc; + struct map_session_data *sd; - if( !damage ) + if( !src || !bl ) return 0; + sc = status_get_sc(src); sd = BL_CAST(BL_PC, src); - tsd = BL_CAST(BL_PC, target); - t_class = status_get_class(target); - s_class = status_get_class(src); - sstatus = status_get_status_data(src); - tstatus = status_get_status_data(target); - s_race2 = status_get_race2(src); - switch(attack_type){ - case BF_MAGIC: - if ( sd && !(nk&NK_NO_CARDFIX_ATK) ) { - cardfix=cardfix*(100+sd->magic_addrace[tstatus->race])/100; - if (!(nk&NK_NO_ELEFIX)) - cardfix=cardfix*(100+sd->magic_addele[tstatus->def_ele])/100; - cardfix=cardfix*(100+sd->magic_addsize[tstatus->size])/100; - cardfix=cardfix*(100+sd->magic_addrace[is_boss(target)?RC_BOSS:RC_NONBOSS])/100; - cardfix=cardfix*(100+sd->magic_atk_ele[s_ele])/100; - for(i=0; i< ARRAYLENGTH(sd->add_mdmg) && sd->add_mdmg[i].rate;i++) { - if(sd->add_mdmg[i].class_ == t_class) { - cardfix=cardfix*(100+sd->add_mdmg[i].rate)/100; - break; - } - } - if (cardfix != 1000) - damage = damage * cardfix / 1000; - } + damage = status_get_weapon_atk(src, watk, flag); + + if( sd ){ + if( type == EQI_HAND_R ) + damage = battle->calc_sizefix(sd, damage, EQI_HAND_R, size, flag&8); + else + damage = battle->calc_sizefix(sd, damage, EQI_HAND_L, size, flag&8); - if( tsd && !(nk&NK_NO_CARDFIX_DEF) ) - { // Target cards. - if (!(nk&NK_NO_ELEFIX)) - { - int ele_fix = tsd->subele[s_ele]; - for (i = 0; ARRAYLENGTH(tsd->subele2) > i && tsd->subele2[i].rate != 0; i++) - { - if(tsd->subele2[i].ele != s_ele) continue; - if(!(tsd->subele2[i].flag&flag&BF_WEAPONMASK && - tsd->subele2[i].flag&flag&BF_RANGEMASK && - tsd->subele2[i].flag&flag&BF_SKILLMASK)) - continue; - ele_fix += tsd->subele2[i].rate; - } - cardfix=cardfix*(100-ele_fix)/100; - } - cardfix=cardfix*(100-tsd->subsize[sstatus->size])/100; - cardfix=cardfix*(100-tsd->subrace2[s_race2])/100; - cardfix=cardfix*(100-tsd->subrace[sstatus->race])/100; - cardfix=cardfix*(100-tsd->subrace[is_boss(src)?RC_BOSS:RC_NONBOSS])/100; - if( sstatus->race != RC_DEMIHUMAN ) - cardfix=cardfix*(100-tsd->subrace[RC_NONDEMIHUMAN])/100; + if( sd->bonus.eatk > 0 ) + eatk = sd->bonus.eatk; + if( flag&2 && sd->bonus.arrow_atk ) + eatk += sd->bonus.arrow_atk; + } + + if( sc && sc->count ){ + if( sc->data[SC_ZENKAI] && watk->ele == sc->data[SC_ZENKAI]->val2 ) + eatk += 200; + #ifdef RENEWAL_EDP + if( sc->data[SC_EDP] && skill_id != AS_GRIMTOOTH && skill_id != AS_VENOMKNIFE ){ + eatk = eatk * sc->data[SC_EDP]->val3 / 100; // 400% + damage = damage * sc->data[SC_EDP]->val4 / 100; // 500% + damage--; // temporary until we find the correct formula [malufett] + } + #endif + } - for(i=0; i < ARRAYLENGTH(tsd->add_mdef) && tsd->add_mdef[i].rate;i++) { - if(tsd->add_mdef[i].class_ == s_class) { - cardfix=cardfix*(100-tsd->add_mdef[i].rate)/100; - break; - } - } - //It was discovered that ranged defense also counts vs magic! [Skotlex] - if ( flag&BF_SHORT ) - cardfix = cardfix * ( 100 - tsd->bonus.near_attack_def_rate ) / 100; - else - cardfix = cardfix * ( 100 - tsd->bonus.long_attack_def_rate ) / 100; + /* [malufett] + some unknown factors that needs to be discovered. PS: it's something related with ranged attacks + if( eatk ){ + eatk += unknown value; + eatk = eatk * (unknown value) / 100; + } + */ - cardfix = cardfix * ( 100 - tsd->bonus.magic_def_rate ) / 100; + if( sc && sc->data[SC_WATK_ELEMENT] ) + damage = damage + eatk; + else + damage = battle->calc_elefix(src, bl, skill_id, skill_lv, damage + eatk, nk, n_ele, s_ele, s_ele_, false, flag); + + /** + * In RE Shield Bommerang takes weapon element only for damage calculation, + * - resist calculation is always against neutral + **/ + if ( skill_id == CR_SHIELDBOOMERANG ) + s_ele = s_ele_ = ELE_NEUTRAL; + + if( type == EQI_HAND_R ) + damage = battle->calc_cardfix(BF_WEAPON, src, bl, nk, s_ele, s_ele_, damage, 2, flag2); + else + damage = battle->calc_cardfix(BF_WEAPON, src, bl, nk, s_ele, s_ele_, damage, 3, flag2); + + return damage; +} +/*========================================== + * Calculates the standard damage of a normal attack assuming it hits, + * it calculates nothing extra fancy, is needed for magnum break's WATK_ELEMENT bonus. [Skotlex] + *------------------------------------------ + * Pass damage2 as NULL to not calc it. + * Flag values: + * &1: Critical hit + * &2: Arrow attack + * &4: Skill is Magic Crasher + * &8: Skip target size adjustment (Extremity Fist?) + *&16: Arrow attack but BOW, REVOLVER, RIFLE, SHOTGUN, GATLING or GRENADE type weapon not equipped (i.e. shuriken, kunai and venom knives not affected by DEX) + */ - if( tsd->sc.data[SC_MDEF_RATE] ) - cardfix = cardfix * ( 100 - tsd->sc.data[SC_MDEF_RATE]->val1 ) / 100; +#ifdef RENEWAL +int battle_calc_base_damage(struct block_list *src, struct block_list *bl, uint16 skill_id, uint16 skill_lv, int nk, bool n_ele, short s_ele, short s_ele_, int type, int flag, int flag2) +{ + int damage, batk; + struct status_change *sc = status_get_sc(src); + struct status_data *status = status_get_status_data(src); + + if( sc && sc->data[SC_TK_SEVENWIND] && !sc->data[SC_WATK_ELEMENT] ) + batk = battle->calc_elefix(src, bl, skill_id, skill_lv, status->batk, nk, n_ele, s_ele, s_ele_, false, flag); + else + batk = status->batk; - if (cardfix != 1000) - damage = damage * cardfix / 1000; - } - break; - case BF_WEAPON: - t_race2 = status_get_race2(target); - if( sd && !(nk&NK_NO_CARDFIX_ATK) && (left&2) ) - { - short cardfix_ = 1000; - if(sd->state.arrow_atk) - { - cardfix=cardfix*(100+sd->right_weapon.addrace[tstatus->race]+sd->arrow_addrace[tstatus->race])/100; - if (!(nk&NK_NO_ELEFIX)) - { - int ele_fix = sd->right_weapon.addele[tstatus->def_ele] + sd->arrow_addele[tstatus->def_ele]; - for (i = 0; ARRAYLENGTH(sd->right_weapon.addele2) > i && sd->right_weapon.addele2[i].rate != 0; i++) { - if (sd->right_weapon.addele2[i].ele != tstatus->def_ele) continue; - if(!(sd->right_weapon.addele2[i].flag&flag&BF_WEAPONMASK && - sd->right_weapon.addele2[i].flag&flag&BF_RANGEMASK && - sd->right_weapon.addele2[i].flag&flag&BF_SKILLMASK)) - continue; - ele_fix += sd->right_weapon.addele2[i].rate; - } - cardfix=cardfix*(100+ele_fix)/100; - } - cardfix=cardfix*(100+sd->right_weapon.addsize[tstatus->size]+sd->arrow_addsize[tstatus->size])/100; - cardfix=cardfix*(100+sd->right_weapon.addrace2[t_race2])/100; - cardfix=cardfix*(100+sd->right_weapon.addrace[is_boss(target)?RC_BOSS:RC_NONBOSS]+sd->arrow_addrace[is_boss(target)?RC_BOSS:RC_NONBOSS])/100; - if( tstatus->race != RC_DEMIHUMAN ) - cardfix=cardfix*(100+sd->right_weapon.addrace[RC_NONDEMIHUMAN]+sd->arrow_addrace[RC_NONDEMIHUMAN])/100; - } - else - { // Melee attack - if( !battle_config.left_cardfix_to_right ) - { - cardfix=cardfix*(100+sd->right_weapon.addrace[tstatus->race])/100; - if (!(nk&NK_NO_ELEFIX)) { - int ele_fix = sd->right_weapon.addele[tstatus->def_ele]; - for (i = 0; ARRAYLENGTH(sd->right_weapon.addele2) > i && sd->right_weapon.addele2[i].rate != 0; i++) { - if (sd->right_weapon.addele2[i].ele != tstatus->def_ele) continue; - if(!(sd->right_weapon.addele2[i].flag&flag&BF_WEAPONMASK && - sd->right_weapon.addele2[i].flag&flag&BF_RANGEMASK && - sd->right_weapon.addele2[i].flag&flag&BF_SKILLMASK)) - continue; - ele_fix += sd->right_weapon.addele2[i].rate; - } - cardfix=cardfix*(100+ele_fix)/100; - } - cardfix=cardfix*(100+sd->right_weapon.addsize[tstatus->size])/100; - cardfix=cardfix*(100+sd->right_weapon.addrace2[t_race2])/100; - cardfix=cardfix*(100+sd->right_weapon.addrace[is_boss(target)?RC_BOSS:RC_NONBOSS])/100; - if( tstatus->race != RC_DEMIHUMAN ) - cardfix=cardfix*(100+sd->right_weapon.addrace[RC_NONDEMIHUMAN])/100; + if( type == EQI_HAND_L ) + damage = batk + 3 * battle->calc_weapon_damage(src, bl, skill_id, skill_lv, &status->lhw, nk, n_ele, s_ele, s_ele_, status_get_size(bl), type, flag, flag2) / 4; + else + damage = (batk << 1) + battle->calc_weapon_damage(src, bl, skill_id, skill_lv, &status->rhw, nk, n_ele, s_ele, s_ele_, status_get_size(bl), type, flag, flag2); +#else +static int battle_calc_base_damage(struct status_data *status, struct weapon_atk *wa, struct status_change *sc, unsigned short t_size, struct map_session_data *sd, int flag) +{ + unsigned int atkmin=0, atkmax=0; + short type = 0; + int damage = 0; - if( left&1 ) - { - cardfix_=cardfix_*(100+sd->left_weapon.addrace[tstatus->race])/100; - if (!(nk&NK_NO_ELEFIX)) { - int ele_fix_lh = sd->left_weapon.addele[tstatus->def_ele]; - for (i = 0; ARRAYLENGTH(sd->left_weapon.addele2) > i && sd->left_weapon.addele2[i].rate != 0; i++) { - if (sd->left_weapon.addele2[i].ele != tstatus->def_ele) continue; - if(!(sd->left_weapon.addele2[i].flag&flag&BF_WEAPONMASK && - sd->left_weapon.addele2[i].flag&flag&BF_RANGEMASK && - sd->left_weapon.addele2[i].flag&flag&BF_SKILLMASK)) - continue; - ele_fix_lh += sd->left_weapon.addele2[i].rate; - } - cardfix=cardfix*(100+ele_fix_lh)/100; - } - cardfix_=cardfix_*(100+sd->left_weapon.addsize[tstatus->size])/100; - cardfix_=cardfix_*(100+sd->left_weapon.addrace2[t_race2])/100; - cardfix_=cardfix_*(100+sd->left_weapon.addrace[is_boss(target)?RC_BOSS:RC_NONBOSS])/100; - if( tstatus->race != RC_DEMIHUMAN ) - cardfix_=cardfix_*(100+sd->left_weapon.addrace[RC_NONDEMIHUMAN])/100; - } - } - else - { - int ele_fix = sd->right_weapon.addele[tstatus->def_ele] + sd->left_weapon.addele[tstatus->def_ele]; - for (i = 0; ARRAYLENGTH(sd->right_weapon.addele2) > i && sd->right_weapon.addele2[i].rate != 0; i++) { - if (sd->right_weapon.addele2[i].ele != tstatus->def_ele) continue; - if(!(sd->right_weapon.addele2[i].flag&flag&BF_WEAPONMASK && - sd->right_weapon.addele2[i].flag&flag&BF_RANGEMASK && - sd->right_weapon.addele2[i].flag&flag&BF_SKILLMASK)) - continue; - ele_fix += sd->right_weapon.addele2[i].rate; - } - for (i = 0; ARRAYLENGTH(sd->left_weapon.addele2) > i && sd->left_weapon.addele2[i].rate != 0; i++) { - if (sd->left_weapon.addele2[i].ele != tstatus->def_ele) continue; - if(!(sd->left_weapon.addele2[i].flag&flag&BF_WEAPONMASK && - sd->left_weapon.addele2[i].flag&flag&BF_RANGEMASK && - sd->left_weapon.addele2[i].flag&flag&BF_SKILLMASK)) - continue; - ele_fix += sd->left_weapon.addele2[i].rate; - } + if (!sd) { //Mobs/Pets + if(flag&4) { + atkmin = status->matk_min; + atkmax = status->matk_max; + } else { + atkmin = wa->atk; + atkmax = wa->atk2; + } + if (atkmin > atkmax) + atkmin = atkmax; + } else { //PCs + atkmax = wa->atk; + type = (wa == &status->lhw)?EQI_HAND_L:EQI_HAND_R; - cardfix=cardfix*(100+sd->right_weapon.addrace[tstatus->race]+sd->left_weapon.addrace[tstatus->race])/100; - cardfix=cardfix*(100+ele_fix)/100; - cardfix=cardfix*(100+sd->right_weapon.addsize[tstatus->size]+sd->left_weapon.addsize[tstatus->size])/100; - cardfix=cardfix*(100+sd->right_weapon.addrace2[t_race2]+sd->left_weapon.addrace2[t_race2])/100; - cardfix=cardfix*(100+sd->right_weapon.addrace[is_boss(target)?RC_BOSS:RC_NONBOSS]+sd->left_weapon.addrace[is_boss(target)?RC_BOSS:RC_NONBOSS])/100; - if( tstatus->race != RC_DEMIHUMAN ) - cardfix=cardfix*(100+sd->right_weapon.addrace[RC_NONDEMIHUMAN]+sd->left_weapon.addrace[RC_NONDEMIHUMAN])/100; - } - } - for( i = 0; i < ARRAYLENGTH(sd->right_weapon.add_dmg) && sd->right_weapon.add_dmg[i].rate; i++ ) - { - if( sd->right_weapon.add_dmg[i].class_ == t_class ) - { - cardfix=cardfix*(100+sd->right_weapon.add_dmg[i].rate)/100; - break; - } - } + if (!(flag&1) || (flag&2)) { //Normal attacks + atkmin = status->dex; - if( left&1 ) - { - for( i = 0; i < ARRAYLENGTH(sd->left_weapon.add_dmg) && sd->left_weapon.add_dmg[i].rate; i++ ) - { - if( sd->left_weapon.add_dmg[i].class_ == t_class ) - { - cardfix_=cardfix_*(100+sd->left_weapon.add_dmg[i].rate)/100; - break; - } - } - } + if (sd->equip_index[type] >= 0 && sd->inventory_data[sd->equip_index[type]]) + atkmin = atkmin*(80 + sd->inventory_data[sd->equip_index[type]]->wlv*20)/100; - if( flag&BF_LONG ) - cardfix = cardfix * ( 100 + sd->bonus.long_attack_atk_rate ) / 100; -#ifdef RENEWAL_EDP - if( sd->sc.data[SC_EDP] ){ - cardfix = cardfix * (100 + sd->sc.data[SC_EDP]->val1 * 60 ) / 100; - cardfix_ = cardfix_ * (100 + sd->sc.data[SC_EDP]->val1 * 60 ) / 100; - } -#endif - if( (left&1) && cardfix_ != 1000 ) - damage = damage * cardfix_ / 1000; - else if( cardfix != 1000 ) - damage = damage * cardfix / 1000; + if (atkmin > atkmax) + atkmin = atkmax; - }else if( tsd && !(nk&NK_NO_CARDFIX_DEF) ){ - if( !(nk&NK_NO_ELEFIX) ) - { - int ele_fix = tsd->subele[s_ele]; - for (i = 0; ARRAYLENGTH(tsd->subele2) > i && tsd->subele2[i].rate != 0; i++) - { - if(tsd->subele2[i].ele != s_ele) continue; - if(!(tsd->subele2[i].flag&flag&BF_WEAPONMASK && - tsd->subele2[i].flag&flag&BF_RANGEMASK && - tsd->subele2[i].flag&flag&BF_SKILLMASK)) - continue; - ele_fix += tsd->subele2[i].rate; - } - cardfix=cardfix*(100-ele_fix)/100; - if( left&1 && s_ele_ != s_ele ) - { - int ele_fix_lh = tsd->subele[s_ele_]; - for (i = 0; ARRAYLENGTH(tsd->subele2) > i && tsd->subele2[i].rate != 0; i++) - { - if(tsd->subele2[i].ele != s_ele_) continue; - if(!(tsd->subele2[i].flag&flag&BF_WEAPONMASK && - tsd->subele2[i].flag&flag&BF_RANGEMASK && - tsd->subele2[i].flag&flag&BF_SKILLMASK)) - continue; - ele_fix_lh += tsd->subele2[i].rate; - } - cardfix=cardfix*(100-ele_fix_lh)/100; - } + if(flag&2 && !(flag&16)) { //Bows + atkmin = atkmin*atkmax/100; + if (atkmin > atkmax) + atkmax = atkmin; } - cardfix=cardfix*(100-tsd->subsize[sstatus->size])/100; - cardfix=cardfix*(100-tsd->subrace2[s_race2])/100; - cardfix=cardfix*(100-tsd->subrace[sstatus->race])/100; - cardfix=cardfix*(100-tsd->subrace[is_boss(src)?RC_BOSS:RC_NONBOSS])/100; - if( sstatus->race != RC_DEMIHUMAN ) - cardfix=cardfix*(100-tsd->subrace[RC_NONDEMIHUMAN])/100; + } + } - for( i = 0; i < ARRAYLENGTH(tsd->add_def) && tsd->add_def[i].rate;i++ ) { - if( tsd->add_def[i].class_ == s_class ) { - cardfix=cardfix*(100-tsd->add_def[i].rate)/100; - break; - } - } + if (sc && sc->data[SC_MAXIMIZEPOWER]) + atkmin = atkmax; - if( flag&BF_SHORT ) - cardfix = cardfix * ( 100 - tsd->bonus.near_attack_def_rate ) / 100; - else // BF_LONG (there's no other choice) - cardfix = cardfix * ( 100 - tsd->bonus.long_attack_def_rate ) / 100; + //Weapon Damage calculation + if (!(flag&1)) + damage = (atkmax>atkmin? rnd()%(atkmax-atkmin):0)+atkmin; + else + damage = atkmax; + + if (sd) { + //rodatazone says the range is 0~arrow_atk-1 for non crit + if (flag&2 && sd->bonus.arrow_atk) + damage += ( (flag&1) ? sd->bonus.arrow_atk : rnd()%sd->bonus.arrow_atk ); - if( tsd->sc.data[SC_DEF_RATE] ) - cardfix = cardfix * ( 100 - tsd->sc.data[SC_DEF_RATE]->val1 ) / 100; + //SizeFix only for players + if (!(sd->special_state.no_sizefix || (flag&8))) + DAMAGE_RATE(type==EQI_HAND_L? + sd->left_weapon.atkmods[t_size]: + sd->right_weapon.atkmods[t_size]) + } - if( cardfix != 1000 ) - damage = damage * cardfix / 1000; + //Finally, add baseatk + if(flag&4) + damage += status->matk_min; + else + damage += status->batk; + + //rodatazone says that Overrefine bonuses are part of baseatk + //Here we also apply the weapon_atk_rate bonus so it is correctly applied on left/right hands. + if(sd) { + if (type == EQI_HAND_L) { + if(sd->left_weapon.overrefine) + damage += rnd()%sd->left_weapon.overrefine+1; + if (sd->weapon_atk_rate[sd->weapontype2]) + DAMAGE_ADDRATE(sd->weapon_atk_rate[sd->weapontype2]) + } else { //Right hand + if(sd->right_weapon.overrefine) + damage += rnd()%sd->right_weapon.overrefine+1; + if (sd->weapon_atk_rate[sd->weapontype1]) + DAMAGE_ADDRATE(sd->weapon_atk_rate[sd->weapontype1]) } - break; - case BF_MISC: - if( tsd && !(nk&NK_NO_CARDFIX_DEF) ){ - // misc damage reduction from equipment - if (!(nk&NK_NO_ELEFIX)) - { - int ele_fix = tsd->subele[s_ele]; - for (i = 0; ARRAYLENGTH(tsd->subele2) > i && tsd->subele2[i].rate != 0; i++) - { - if(tsd->subele2[i].ele != s_ele) continue; - if(!(tsd->subele2[i].flag&flag&BF_WEAPONMASK && - tsd->subele2[i].flag&flag&BF_RANGEMASK && - tsd->subele2[i].flag&flag&BF_SKILLMASK)) - continue; - ele_fix += tsd->subele2[i].rate; - } - cardfix=cardfix*(100-ele_fix)/100; - } - cardfix=cardfix*(100-tsd->subsize[sstatus->size])/100; - cardfix=cardfix*(100-tsd->subrace2[s_race2])/100; - cardfix=cardfix*(100-tsd->subrace[sstatus->race])/100; - cardfix=cardfix*(100-tsd->subrace[is_boss(src)?RC_BOSS:RC_NONBOSS])/100; - if( sstatus->race != RC_DEMIHUMAN ) - cardfix=cardfix*(100-tsd->subrace[RC_NONDEMIHUMAN])/100; + } +#endif + return damage; +} - cardfix = cardfix * ( 100 - tsd->bonus.misc_def_rate ) / 100; - if( flag&BF_SHORT ) - cardfix = cardfix * ( 100 - tsd->bonus.near_attack_def_rate ) / 100; - else // BF_LONG (there's no other choice) - cardfix = cardfix * ( 100 - tsd->bonus.long_attack_def_rate ) / 100; +int battle_calc_sizefix(struct map_session_data *sd, int damage, int type, int size, bool ignore){ + //SizeFix only for players + if (!(sd->special_state.no_sizefix || (ignore))) + damage = damage * ( type == EQI_HAND_L ? sd->left_weapon.atkmods[size] : sd->right_weapon.atkmods[size] ) / 100; + return damage; +} - if (cardfix != 10000) - damage = damage * cardfix / 1000; +/*========================================== + * Passive skill damages increases + *------------------------------------------*/ +int battle_addmastery(struct map_session_data *sd,struct block_list *target,int dmg,int type) +{ + int damage,skill; + struct status_data *status = status_get_status_data(target); + int weapon; + damage = dmg; + + nullpo_ret(sd); + + if((skill = pc->checkskill(sd,AL_DEMONBANE)) > 0 && + target->type == BL_MOB && //This bonus doesnt work against players. + (battle->check_undead(status->race,status->def_ele) || status->race==RC_DEMON) ) + damage += (int)(skill*(3+sd->status.base_level/20.0)); + //damage += (skill * 3); + if( (skill = pc->checkskill(sd, RA_RANGERMAIN)) > 0 && (status->race == RC_BRUTE || status->race == RC_PLANT || status->race == RC_FISH) ) + damage += (skill * 5); + if( (skill = pc->checkskill(sd,NC_RESEARCHFE)) > 0 && (status->def_ele == ELE_FIRE || status->def_ele == ELE_EARTH) ) + damage += (skill * 10); + if( pc_ismadogear(sd) ) + damage += 20 + 20 * pc->checkskill(sd, NC_MADOLICENCE); +#ifdef RENEWAL + if( (skill = pc->checkskill(sd,BS_WEAPONRESEARCH)) > 0 ) + damage += (skill * 2); +#endif + if((skill = pc->checkskill(sd,HT_BEASTBANE)) > 0 && (status->race==RC_BRUTE || status->race==RC_INSECT) ) { + damage += (skill * 4); + if (sd->sc.data[SC_SOULLINK] && sd->sc.data[SC_SOULLINK]->val2 == SL_HUNTER) + damage += sd->status.str; + } + + if(type == 0) + weapon = sd->weapontype1; + else + weapon = sd->weapontype2; + switch(weapon) + { + case W_1HSWORD: + #ifdef RENEWAL + if((skill = pc->checkskill(sd,AM_AXEMASTERY)) > 0) + damage += (skill * 3); + #endif + case W_DAGGER: + if((skill = pc->checkskill(sd,SM_SWORD)) > 0) + damage += (skill * 4); + if((skill = pc->checkskill(sd,GN_TRAINING_SWORD)) > 0) + damage += skill * 10; + break; + case W_2HSWORD: + #ifdef RENEWAL + if((skill = pc->checkskill(sd,AM_AXEMASTERY)) > 0) + damage += (skill * 3); + #endif + if((skill = pc->checkskill(sd,SM_TWOHAND)) > 0) + damage += (skill * 4); + break; + case W_1HSPEAR: + case W_2HSPEAR: + if((skill = pc->checkskill(sd,KN_SPEARMASTERY)) > 0) { + + if(!pc_isriding(sd)) + damage += (skill * 4); + else if(pc_isridingdragon(sd)) + damage += (skill * 10); + else + damage += (skill * 5); } break; + case W_1HAXE: + case W_2HAXE: + if((skill = pc->checkskill(sd,AM_AXEMASTERY)) > 0) + damage += (skill * 3); + if((skill = pc->checkskill(sd,NC_TRAININGAXE)) > 0) + damage += (skill * 5); + break; + case W_MACE: + case W_2HMACE: + if((skill = pc->checkskill(sd,PR_MACEMASTERY)) > 0) + damage += (skill * 3); + if((skill = pc->checkskill(sd,NC_TRAININGAXE)) > 0) + damage += (skill * 5); + break; + case W_FIST: + if((skill = pc->checkskill(sd,TK_RUN)) > 0) + damage += (skill * 10); + // No break, fallthrough to Knuckles + case W_KNUCKLE: + if((skill = pc->checkskill(sd,MO_IRONHAND)) > 0) + damage += (skill * 3); + break; + case W_MUSICAL: + if((skill = pc->checkskill(sd,BA_MUSICALLESSON)) > 0) + damage += (skill * 3); + break; + case W_WHIP: + if((skill = pc->checkskill(sd,DC_DANCINGLESSON)) > 0) + damage += (skill * 3); + break; + case W_BOOK: + if((skill = pc->checkskill(sd,SA_ADVANCEDBOOK)) > 0) + damage += (skill * 3); + break; + case W_KATAR: + if((skill = pc->checkskill(sd,AS_KATAR)) > 0) + damage += (skill * 3); + break; } return damage; } /*========================================== - * Check dammage trough status. - * ATK may be MISS, BLOCKED FAIL, reduc, increase, end status... - * After this we apply bg/gvg reduction + * Calculates ATK masteries. *------------------------------------------*/ -int battle_calc_damage(struct block_list *src,struct block_list *bl,struct Damage *d,int damage,uint16 skill_id,uint16 skill_lv) -{ - struct map_session_data *sd = NULL; +int battle_calc_masteryfix(struct block_list *src, struct block_list *target, uint16 skill_id, uint16 skill_lv, int damage, int div, bool left, bool weapon){ + int skill, i; + struct map_session_data *sd; struct status_change *sc; - struct status_change_entry *sce; - int div_ = d->div_, flag = d->flag; - - nullpo_ret(bl); - if( !damage ) - return 0; - if( battle_config.ksprotection && mob_ksprotected(src, bl) ) - return 0; + nullpo_ret(src); + nullpo_ret(target); - if (bl->type == BL_PC) { - sd=(struct map_session_data *)bl; - //Special no damage states - if(flag&BF_WEAPON && sd->special_state.no_weapon_damage) - damage -= damage * sd->special_state.no_weapon_damage / 100; + sd = BL_CAST(BL_PC, src); + sc = status_get_sc(src); - if(flag&BF_MAGIC && sd->special_state.no_magic_damage) - damage -= damage * sd->special_state.no_magic_damage / 100; + if ( !sd ) + return damage; - if(flag&BF_MISC && sd->special_state.no_misc_damage) - damage -= damage * sd->special_state.no_misc_damage / 100; + switch( skill_id ){ // specific skill masteries + case MO_INVESTIGATE: + case MO_EXTREMITYFIST: + case CR_GRANDCROSS: + case NJ_ISSEN: + case CR_ACIDDEMONSTRATION: + return damage; + case NJ_SYURIKEN: + if( (skill = pc->checkskill(sd,NJ_TOBIDOUGU)) > 0 && weapon ) + damage += 3 * skill; + break; + case NJ_KUNAI: + if( weapon ) + damage += 60; + break; + case RA_WUGDASH: + case RA_WUGSTRIKE: + case RA_WUGBITE: + damage += 30*pc->checkskill(sd, RA_TOOTHOFWUG); + break; + } - if(!damage) return 0; + if ( sc && sc->data[SC_MIRACLE] ) i = 2; //Star anger + else + ARR_FIND(0, MAX_PC_FEELHATE, i, status_get_class(target) == sd->hate_mob[i]); + if ( i < MAX_PC_FEELHATE && (skill=pc->checkskill(sd,sg_info[i].anger_id)) && weapon ){ + int ratio = sd->status.base_level + status_get_dex(src) + status_get_luk(src); + if ( i == 2 ) ratio += status_get_str(src); //Star Anger + if (skill < 4 ) + ratio /= 12 - 3 * skill; + damage += damage * ratio; + } + + if( sc ){ + if(sc->data[SC_GN_CARTBOOST]) + damage += 10 * sc->data[SC_GN_CARTBOOST]->val1; + if(sc->data[SC_CAMOUFLAGE]) + damage += 30 * ( 10 - sc->data[SC_CAMOUFLAGE]->val4 ); } - sc = status_get_sc(bl); + // general skill masteries +#ifdef RENEWAL + if( skill_id == MO_FINGEROFFENSIVE )//The finger offensive spheres on moment of attack do count. [Skotlex] + damage += div * sd->spiritball_old * 3; + else + damage += div * sd->spiritball * 3; + if( skill_id != CR_SHIELDBOOMERANG ) // Only Shield boomerang doesn't takes the Star Crumbs bonus. + damage += div * (left ? sd->left_weapon.star : sd->right_weapon.star); +#else + if( skill_id != ASC_BREAKER && weapon ) // Adv Katar Mastery is does not applies to ASC_BREAKER, but other masteries DO apply >_> + if( sd->status.weapon == W_KATAR && (skill=pc->checkskill(sd,ASC_KATAR)) > 0 ) + damage += damage * (10 + 2 * skill) / 100; +#endif - if( sc && sc->data[SC_INVINCIBLE] && !sc->data[SC_INVINCIBLEOFF] ) - return 1; - if (skill_id == PA_PRESSURE) - return damage; //This skill bypass everything else. - - if( sc && sc->count ) - { - //First, sc_*'s that reduce damage to 0. - if( sc->data[SC_BASILICA] && !(status_get_mode(src)&MD_BOSS) ) - { - d->dmg_lv = ATK_BLOCK; - return 0; - } - if( sc->data[SC_WHITEIMPRISON] && skill_id != HW_GRAVITATION ) { // Gravitation and Pressure do damage without removing the effect - if( skill_id == MG_NAPALMBEAT || - skill_id == MG_SOULSTRIKE || - skill_id == WL_SOULEXPANSION || - (skill_id && skill->get_ele(skill_id, skill_lv) == ELE_GHOST) || - (!skill_id && (status_get_status_data(src))->rhw.ele == ELE_GHOST) - ){ - if( skill_id == WL_SOULEXPANSION ) - damage <<= 1; // If used against a player in White Imprison, the skill deals double damage. - status_change_end(bl,SC_WHITEIMPRISON,INVALID_TIMER); // Those skills do damage and removes effect - }else{ - d->dmg_lv = ATK_BLOCK; - return 0; - } - } - - if(sc->data[SC_ZEPHYR] && - flag&(BF_LONG|BF_SHORT)){ - d->dmg_lv = ATK_BLOCK; - return 0; - } - - if( sc->data[SC_SAFETYWALL] && (flag&(BF_SHORT|BF_MAGIC))==BF_SHORT ) - { - struct skill_unit_group* group = skill->id2group(sc->data[SC_SAFETYWALL]->val3); - uint16 skill_id = sc->data[SC_SAFETYWALL]->val2; - if (group) { - if(skill_id == MH_STEINWAND){ - if (--group->val2<=0) - skill->del_unitgroup(group,ALC_MARK); - d->dmg_lv = ATK_BLOCK; - return 0; - } - /** - * in RE, SW possesses a lifetime equal to 3 times the caster's health - **/ - #ifdef RENEWAL - d->dmg_lv = ATK_BLOCK; - if ( ( group->val2 - damage) > 0 ) { - group->val2 -= damage; - } else - skill->del_unitgroup(group,ALC_MARK); - return 0; - #else - if (--group->val2<=0) - skill->del_unitgroup(group,ALC_MARK); - d->dmg_lv = ATK_BLOCK; - return 0; - #endif - } - status_change_end(bl, SC_SAFETYWALL, INVALID_TIMER); - } - - if( ( sc->data[SC_PNEUMA] && (flag&(BF_MAGIC|BF_LONG)) == BF_LONG ) || sc->data[SC__MANHOLE] ) { - d->dmg_lv = ATK_BLOCK; - return 0; - } - if( sc->data[SC_WEAPONBLOCKING] && flag&(BF_SHORT|BF_WEAPON) && rnd()%100 < sc->data[SC_WEAPONBLOCKING]->val2 ) - { - clif->skill_nodamage(bl,src,GC_WEAPONBLOCKING,1,1); - d->dmg_lv = ATK_BLOCK; - sc_start2(bl,SC_COMBO,100,GC_WEAPONBLOCKING,src->id,2000); - return 0; - } - if( (sce=sc->data[SC_AUTOGUARD]) && flag&BF_WEAPON && !(skill->get_nk(skill_id)&NK_NO_CARDFIX_ATK) && rnd()%100 < sce->val2 ) - { - int delay; - clif->skill_nodamage(bl,bl,CR_AUTOGUARD,sce->val1,1); - // different delay depending on skill level [celest] - if (sce->val1 <= 5) - delay = 300; - else if (sce->val1 > 5 && sce->val1 <= 9) - delay = 200; - else - delay = 100; - unit_set_walkdelay(bl, iTimer->gettick(), delay, 1); - - if(sc->data[SC_SHRINK] && rnd()%100<5*sce->val1) - skill->blown(bl,src,skill->get_blewcount(CR_SHRINK,1),-1,0); - return 0; - } - - if( (sce = sc->data[SC_MILLENNIUMSHIELD]) && sce->val2 > 0 && damage > 0 ) { - clif->skill_nodamage(bl, bl, RK_MILLENNIUMSHIELD, 1, 1); - sce->val3 -= damage; // absorb damage - d->dmg_lv = ATK_BLOCK; - sc_start(bl,SC_STUN,15,0,skill->get_time2(RK_MILLENNIUMSHIELD,sce->val1)); // There is a chance to be stuned when one shield is broken. - if( sce->val3 <= 0 ) { // Shield Down - sce->val2--; - if( sce->val2 > 0 ) { - if( sd ) - clif->millenniumshield(sd,sce->val2); - sce->val3 = 1000; // Next Shield - } else - status_change_end(bl,SC_MILLENNIUMSHIELD,INVALID_TIMER); // All shields down - } - return 0; - } + damage = battle->add_mastery(sd, target, damage, left); + if((skill = pc->checkskill(sd,AB_EUCHARISTICA)) > 0 && + (status_get_status_data(target)->race == RC_DEMON || status_get_status_data(target)->def_ele == ELE_DARK) ) + damage += damage * skill / 100; - if( (sce=sc->data[SC_PARRYING]) && flag&BF_WEAPON && skill_id != WS_CARTTERMINATION && rnd()%100 < sce->val2 ) - { // attack blocked by Parrying - clif->skill_nodamage(bl, bl, LK_PARRYING, sce->val1,1); - return 0; - } + return damage; +} +/*========================================== + * Elemental attribute fix. + *------------------------------------------*/ +int battle_calc_elefix(struct block_list *src, struct block_list *target, uint16 skill_id, uint16 skill_lv, int damage, int nk, int n_ele, int s_ele, int s_ele_, bool left, int flag){ + struct status_data *sstatus, *tstatus; + struct status_change *sc; - if(sc->data[SC_DODGE] && ( !sc->opt1 || sc->opt1 == OPT1_BURNING ) && - (flag&BF_LONG || sc->data[SC_SPURT]) - && rnd()%100 < 20) { - if (sd && pc_issit(sd)) pc->setstand(sd); //Stand it to dodge. - clif->skill_nodamage(bl,bl,TK_DODGE,1,1); - if (!sc->data[SC_COMBO]) - sc_start4(bl, SC_COMBO, 100, TK_JUMPKICK, src->id, 1, 0, 2000); - return 0; - } + nullpo_ret(src); + nullpo_ret(target); - if(sc->data[SC_HERMODE] && flag&BF_MAGIC) - return 0; + sstatus = status_get_status_data(src); + tstatus = status_get_status_data(target); + sc = status_get_sc(src); - if(sc->data[SC_TATAMIGAESHI] && (flag&(BF_MAGIC|BF_LONG)) == BF_LONG) - return 0; + if( (nk&NK_NO_ELEFIX) && n_ele ) + return damage; - if( sc->data[SC_NEUTRALBARRIER] && (flag&(BF_MAGIC|BF_LONG)) == (BF_MAGIC|BF_LONG) ) { - d->dmg_lv = ATK_MISS; - return 0; + if( damage > 0 ) + { + if( left ) + damage = battle->attr_fix(src, target, damage, s_ele_, tstatus->def_ele, tstatus->ele_lv); + else{ + damage=battle->attr_fix(src, target, damage, s_ele, tstatus->def_ele, tstatus->ele_lv); + if( skill_id == MC_CARTREVOLUTION ) //Cart Revolution applies the element fix once more with neutral element + damage = battle->attr_fix(src,target,damage,ELE_NEUTRAL,tstatus->def_ele, tstatus->ele_lv); + if( skill_id == GS_GROUNDDRIFT ) //Additional 50*lv Neutral damage. + damage += battle_attr_fix(src,target,50*skill_lv,ELE_NEUTRAL,tstatus->def_ele, tstatus->ele_lv); } + } + if( sc && sc->data[SC_WATK_ELEMENT] ) + { // Descriptions indicate this means adding a percent of a normal attack in another element. [Skotlex] + damage = +#ifndef RENEWAL + battle->calc_base_damage(sstatus, &sstatus->rhw, sc, tstatus->size, ((TBL_PC*)src), (flag?2:0)) +#else + battle->calc_base_damage(src, target, skill_id, skill_lv, nk, n_ele, s_ele, s_ele_, EQI_HAND_R, (flag?2:0)|(sc && sc->data[SC_MAXIMIZEPOWER]?1:0)|(sc && sc->data[SC_WEAPONPERFECT]?8:0), 0) +#endif + * sc->data[SC_WATK_ELEMENT]->val2 / 100; + + damage += battle->attr_fix(src, target, damage, sc->data[SC_WATK_ELEMENT]->val1, tstatus->def_ele, tstatus->ele_lv); + if( left ){ + damage = +#ifndef RENEWAL + battle->calc_base_damage(sstatus, &sstatus->lhw, sc, tstatus->size, ((TBL_PC*)src), (flag?2:0)) +#else + battle->calc_base_damage(src, target, skill_id, skill_lv, nk, n_ele, s_ele, s_ele_, EQI_HAND_L, (flag?2:0)|(sc && sc->data[SC_MAXIMIZEPOWER]?1:0)|(sc && sc->data[SC_WEAPONPERFECT]?8:0), 0) +#endif + * sc->data[SC_WATK_ELEMENT]->val2 / 100; + damage += battle->attr_fix(src, target, damage, sc->data[SC_WATK_ELEMENT]->val1, tstatus->def_ele, tstatus->ele_lv); + } + } - if((sce=sc->data[SC_KAUPE]) && rnd()%100 < sce->val2) - { //Kaupe blocks damage (skill or otherwise) from players, mobs, homuns, mercenaries. - clif->specialeffect(bl, 462, AREA); - //Shouldn't end until Breaker's non-weapon part connects. - if (skill_id != ASC_BREAKER || !(flag&BF_WEAPON)) - if (--(sce->val3) <= 0) //We make it work like Safety Wall, even though it only blocks 1 time. - status_change_end(bl, SC_KAUPE, INVALID_TIMER); - return 0; - } + return damage; +} +/*========================================== + * Calculates card bonuses damage adjustments. + *------------------------------------------*/ +int battle_calc_cardfix(int attack_type, struct block_list *src, struct block_list *target, int nk, int s_ele, int s_ele_, int damage, int left, int flag){ + struct map_session_data *sd, *tsd; + short cardfix = 1000, t_class, s_class, s_race2, t_race2; + struct status_data *sstatus, *tstatus; + int i; - if( flag&BF_MAGIC && (sce=sc->data[SC_PRESTIGE]) && rnd()%100 < sce->val2) { - clif->specialeffect(bl, 462, AREA); // Still need confirm it. - return 0; - } + if( !damage ) + return 0; + + nullpo_ret(src); + nullpo_ret(target); - if (((sce=sc->data[SC_UTSUSEMI]) || sc->data[SC_BUNSINJYUTSU]) - && flag&BF_WEAPON && !(skill->get_nk(skill_id)&NK_NO_CARDFIX_ATK)) { + sd = BL_CAST(BL_PC, src); + tsd = BL_CAST(BL_PC, target); + t_class = status_get_class(target); + s_class = status_get_class(src); + sstatus = status_get_status_data(src); + tstatus = status_get_status_data(target); + s_race2 = status_get_race2(src); - skill->additional_effect (src, bl, skill_id, skill_lv, flag, ATK_BLOCK, iTimer->gettick() ); - if( !status_isdead(src) ) - skill->counter_additional_effect( src, bl, skill_id, skill_lv, flag, iTimer->gettick() ); - if (sce) { - clif->specialeffect(bl, 462, AREA); - skill->blown(src,bl,sce->val3,-1,0); + switch(attack_type){ + case BF_MAGIC: + if ( sd && !(nk&NK_NO_CARDFIX_ATK) ) { + cardfix=cardfix*(100+sd->magic_addrace[tstatus->race])/100; + if (!(nk&NK_NO_ELEFIX)) + cardfix=cardfix*(100+sd->magic_addele[tstatus->def_ele])/100; + cardfix=cardfix*(100+sd->magic_addsize[tstatus->size])/100; + cardfix=cardfix*(100+sd->magic_addrace[is_boss(target)?RC_BOSS:RC_NONBOSS])/100; + cardfix=cardfix*(100+sd->magic_atk_ele[s_ele])/100; + for(i=0; i< ARRAYLENGTH(sd->add_mdmg) && sd->add_mdmg[i].rate;i++) { + if(sd->add_mdmg[i].class_ == t_class) { + cardfix=cardfix*(100+sd->add_mdmg[i].rate)/100; + break; + } + } + if (cardfix != 1000) + damage = damage * cardfix / 1000; } - //Both need to be consumed if they are active. - if (sce && --(sce->val2) <= 0) - status_change_end(bl, SC_UTSUSEMI, INVALID_TIMER); - if ((sce=sc->data[SC_BUNSINJYUTSU]) && --(sce->val2) <= 0) - status_change_end(bl, SC_BUNSINJYUTSU, INVALID_TIMER); - return 0; - } + if( tsd && !(nk&NK_NO_CARDFIX_DEF) ) + { // Target cards. + if (!(nk&NK_NO_ELEFIX)) + { + int ele_fix = tsd->subele[s_ele]; + for (i = 0; ARRAYLENGTH(tsd->subele2) > i && tsd->subele2[i].rate != 0; i++) + { + if(tsd->subele2[i].ele != s_ele) continue; + if(!(tsd->subele2[i].flag&flag&BF_WEAPONMASK && + tsd->subele2[i].flag&flag&BF_RANGEMASK && + tsd->subele2[i].flag&flag&BF_SKILLMASK)) + continue; + ele_fix += tsd->subele2[i].rate; + } + cardfix=cardfix*(100-ele_fix)/100; + } + cardfix=cardfix*(100-tsd->subsize[sstatus->size])/100; + cardfix=cardfix*(100-tsd->subrace2[s_race2])/100; + cardfix=cardfix*(100-tsd->subrace[sstatus->race])/100; + cardfix=cardfix*(100-tsd->subrace[is_boss(src)?RC_BOSS:RC_NONBOSS])/100; + if( sstatus->race != RC_DEMIHUMAN ) + cardfix=cardfix*(100-tsd->subrace[RC_NONDEMIHUMAN])/100; - //Now damage increasing effects - if( sc->data[SC_AETERNA] && skill_id != PF_SOULBURN ) - { - if( src->type != BL_MER || skill_id == 0 ) - damage <<= 1; // Lex Aeterna only doubles damage of regular attacks from mercenaries + for(i=0; i < ARRAYLENGTH(tsd->add_mdef) && tsd->add_mdef[i].rate;i++) { + if(tsd->add_mdef[i].class_ == s_class) { + cardfix=cardfix*(100-tsd->add_mdef[i].rate)/100; + break; + } + } + //It was discovered that ranged defense also counts vs magic! [Skotlex] + if ( flag&BF_SHORT ) + cardfix = cardfix * ( 100 - tsd->bonus.near_attack_def_rate ) / 100; + else + cardfix = cardfix * ( 100 - tsd->bonus.long_attack_def_rate ) / 100; - if( skill_id != ASC_BREAKER || !(flag&BF_WEAPON) ) - status_change_end(bl, SC_AETERNA, INVALID_TIMER); //Shouldn't end until Breaker's non-weapon part connects. - } + cardfix = cardfix * ( 100 - tsd->bonus.magic_def_rate ) / 100; -#ifdef RENEWAL - if( sc->data[SC_RAID] ) { - damage += damage * 20 / 100; + if( tsd->sc.data[SC_PROTECT_MDEF] ) + cardfix = cardfix * ( 100 - tsd->sc.data[SC_PROTECT_MDEF]->val1 ) / 100; - if (--sc->data[SC_RAID]->val1 == 0) - status_change_end(bl, SC_RAID, INVALID_TIMER); - } -#endif - - if( damage ) { - struct map_session_data *tsd = BL_CAST(BL_PC, src); - if( sc->data[SC_DEEPSLEEP] ) { - damage += damage / 2; // 1.5 times more damage while in Deep Sleep. - status_change_end(bl,SC_DEEPSLEEP,INVALID_TIMER); + if (cardfix != 1000) + damage = damage * cardfix / 1000; } - if( tsd && sd && sc->data[SC_CRYSTALIZE] && flag&BF_WEAPON ){ - switch(tsd->status.weapon){ - case W_MACE: - case W_2HMACE: - case W_1HAXE: - case W_2HAXE: - damage = damage * 150/100; - break; - case W_MUSICAL: - case W_WHIP: - if(!sd->state.arrow_atk) - break; - case W_BOW: - case W_REVOLVER: - case W_RIFLE: - case W_GATLING: - case W_SHOTGUN: - case W_GRENADE: - case W_DAGGER: - case W_1HSWORD: - case W_2HSWORD: - damage = damage * 50/100; - break; + break; + case BF_WEAPON: + t_race2 = status_get_race2(target); + if( sd && !(nk&NK_NO_CARDFIX_ATK) && (left&2) ) + { + short cardfix_ = 1000; + if(sd->state.arrow_atk) + { + cardfix=cardfix*(100+sd->right_weapon.addrace[tstatus->race]+sd->arrow_addrace[tstatus->race])/100; + if (!(nk&NK_NO_ELEFIX)) + { + int ele_fix = sd->right_weapon.addele[tstatus->def_ele] + sd->arrow_addele[tstatus->def_ele]; + for (i = 0; ARRAYLENGTH(sd->right_weapon.addele2) > i && sd->right_weapon.addele2[i].rate != 0; i++) { + if (sd->right_weapon.addele2[i].ele != tstatus->def_ele) continue; + if(!(sd->right_weapon.addele2[i].flag&flag&BF_WEAPONMASK && + sd->right_weapon.addele2[i].flag&flag&BF_RANGEMASK && + sd->right_weapon.addele2[i].flag&flag&BF_SKILLMASK)) + continue; + ele_fix += sd->right_weapon.addele2[i].rate; + } + cardfix=cardfix*(100+ele_fix)/100; + } + cardfix=cardfix*(100+sd->right_weapon.addsize[tstatus->size]+sd->arrow_addsize[tstatus->size])/100; + cardfix=cardfix*(100+sd->right_weapon.addrace2[t_race2])/100; + cardfix=cardfix*(100+sd->right_weapon.addrace[is_boss(target)?RC_BOSS:RC_NONBOSS]+sd->arrow_addrace[is_boss(target)?RC_BOSS:RC_NONBOSS])/100; + if( tstatus->race != RC_DEMIHUMAN ) + cardfix=cardfix*(100+sd->right_weapon.addrace[RC_NONDEMIHUMAN]+sd->arrow_addrace[RC_NONDEMIHUMAN])/100; } - } - if( sc->data[SC_VOICEOFSIREN] ) - status_change_end(bl,SC_VOICEOFSIREN,INVALID_TIMER); - } + else + { // Melee attack + if( !battle_config.left_cardfix_to_right ) + { + cardfix=cardfix*(100+sd->right_weapon.addrace[tstatus->race])/100; + if (!(nk&NK_NO_ELEFIX)) { + int ele_fix = sd->right_weapon.addele[tstatus->def_ele]; + for (i = 0; ARRAYLENGTH(sd->right_weapon.addele2) > i && sd->right_weapon.addele2[i].rate != 0; i++) { + if (sd->right_weapon.addele2[i].ele != tstatus->def_ele) continue; + if(!(sd->right_weapon.addele2[i].flag&flag&BF_WEAPONMASK && + sd->right_weapon.addele2[i].flag&flag&BF_RANGEMASK && + sd->right_weapon.addele2[i].flag&flag&BF_SKILLMASK)) + continue; + ele_fix += sd->right_weapon.addele2[i].rate; + } + cardfix=cardfix*(100+ele_fix)/100; + } + cardfix=cardfix*(100+sd->right_weapon.addsize[tstatus->size])/100; + cardfix=cardfix*(100+sd->right_weapon.addrace2[t_race2])/100; + cardfix=cardfix*(100+sd->right_weapon.addrace[is_boss(target)?RC_BOSS:RC_NONBOSS])/100; + if( tstatus->race != RC_DEMIHUMAN ) + cardfix=cardfix*(100+sd->right_weapon.addrace[RC_NONDEMIHUMAN])/100; - //Finally damage reductions.... - // Assumptio doubles the def & mdef on RE mode, otherwise gives a reduction on the final damage. [Igniz] -#ifndef RENEWAL - if( sc->data[SC_ASSUMPTIO] ) { - if( map_flag_vs(bl->m) ) - damage = damage*2/3; //Receive 66% damage - else - damage >>= 1; //Receive 50% damage - } -#endif + if( left&1 ) + { + cardfix_=cardfix_*(100+sd->left_weapon.addrace[tstatus->race])/100; + if (!(nk&NK_NO_ELEFIX)) { + int ele_fix_lh = sd->left_weapon.addele[tstatus->def_ele]; + for (i = 0; ARRAYLENGTH(sd->left_weapon.addele2) > i && sd->left_weapon.addele2[i].rate != 0; i++) { + if (sd->left_weapon.addele2[i].ele != tstatus->def_ele) continue; + if(!(sd->left_weapon.addele2[i].flag&flag&BF_WEAPONMASK && + sd->left_weapon.addele2[i].flag&flag&BF_RANGEMASK && + sd->left_weapon.addele2[i].flag&flag&BF_SKILLMASK)) + continue; + ele_fix_lh += sd->left_weapon.addele2[i].rate; + } + cardfix=cardfix*(100+ele_fix_lh)/100; + } + cardfix_=cardfix_*(100+sd->left_weapon.addsize[tstatus->size])/100; + cardfix_=cardfix_*(100+sd->left_weapon.addrace2[t_race2])/100; + cardfix_=cardfix_*(100+sd->left_weapon.addrace[is_boss(target)?RC_BOSS:RC_NONBOSS])/100; + if( tstatus->race != RC_DEMIHUMAN ) + cardfix_=cardfix_*(100+sd->left_weapon.addrace[RC_NONDEMIHUMAN])/100; + } + } + else + { + int ele_fix = sd->right_weapon.addele[tstatus->def_ele] + sd->left_weapon.addele[tstatus->def_ele]; + for (i = 0; ARRAYLENGTH(sd->right_weapon.addele2) > i && sd->right_weapon.addele2[i].rate != 0; i++) { + if (sd->right_weapon.addele2[i].ele != tstatus->def_ele) continue; + if(!(sd->right_weapon.addele2[i].flag&flag&BF_WEAPONMASK && + sd->right_weapon.addele2[i].flag&flag&BF_RANGEMASK && + sd->right_weapon.addele2[i].flag&flag&BF_SKILLMASK)) + continue; + ele_fix += sd->right_weapon.addele2[i].rate; + } + for (i = 0; ARRAYLENGTH(sd->left_weapon.addele2) > i && sd->left_weapon.addele2[i].rate != 0; i++) { + if (sd->left_weapon.addele2[i].ele != tstatus->def_ele) continue; + if(!(sd->left_weapon.addele2[i].flag&flag&BF_WEAPONMASK && + sd->left_weapon.addele2[i].flag&flag&BF_RANGEMASK && + sd->left_weapon.addele2[i].flag&flag&BF_SKILLMASK)) + continue; + ele_fix += sd->left_weapon.addele2[i].rate; + } - if(sc->data[SC_DEFENDER] && - (flag&(BF_LONG|BF_WEAPON)) == (BF_LONG|BF_WEAPON)) - damage = damage * ( 100 - sc->data[SC_DEFENDER]->val2 ) / 100; + cardfix=cardfix*(100+sd->right_weapon.addrace[tstatus->race]+sd->left_weapon.addrace[tstatus->race])/100; + cardfix=cardfix*(100+ele_fix)/100; + cardfix=cardfix*(100+sd->right_weapon.addsize[tstatus->size]+sd->left_weapon.addsize[tstatus->size])/100; + cardfix=cardfix*(100+sd->right_weapon.addrace2[t_race2]+sd->left_weapon.addrace2[t_race2])/100; + cardfix=cardfix*(100+sd->right_weapon.addrace[is_boss(target)?RC_BOSS:RC_NONBOSS]+sd->left_weapon.addrace[is_boss(target)?RC_BOSS:RC_NONBOSS])/100; + if( tstatus->race != RC_DEMIHUMAN ) + cardfix=cardfix*(100+sd->right_weapon.addrace[RC_NONDEMIHUMAN]+sd->left_weapon.addrace[RC_NONDEMIHUMAN])/100; + } + } + for( i = 0; i < ARRAYLENGTH(sd->right_weapon.add_dmg) && sd->right_weapon.add_dmg[i].rate; i++ ) + { + if( sd->right_weapon.add_dmg[i].class_ == t_class ) + { + cardfix=cardfix*(100+sd->right_weapon.add_dmg[i].rate)/100; + break; + } + } - if(sc->data[SC_ADJUSTMENT] && - (flag&(BF_LONG|BF_WEAPON)) == (BF_LONG|BF_WEAPON)) - damage -= damage * 20 / 100; + if( left&1 ) + { + for( i = 0; i < ARRAYLENGTH(sd->left_weapon.add_dmg) && sd->left_weapon.add_dmg[i].rate; i++ ) + { + if( sd->left_weapon.add_dmg[i].class_ == t_class ) + { + cardfix_=cardfix_*(100+sd->left_weapon.add_dmg[i].rate)/100; + break; + } + } + } - if(sc->data[SC_FOGWALL] && skill_id != RK_DRAGONBREATH) { - if(flag&BF_SKILL) //25% reduction - damage -= damage * 25 / 100; - else if ((flag&(BF_LONG|BF_WEAPON)) == (BF_LONG|BF_WEAPON)) - damage >>= 2; //75% reduction - } + if( flag&BF_LONG ) + cardfix = cardfix * ( 100 + sd->bonus.long_attack_atk_rate ) / 100; + if( (left&1) && cardfix_ != 1000 ) + damage = damage * cardfix_ / 1000; + else if( cardfix != 1000 ) + damage = damage * cardfix / 1000; - // Compressed code, fixed by map.h [Epoque] - if (src->type == BL_MOB) { - int i; - if (sc->data[SC_MANU_DEF]) - for (i=0;ARRAYLENGTH(mob_manuk)>i;i++) - if (mob_manuk[i]==((TBL_MOB*)src)->class_) { - damage -= damage * sc->data[SC_MANU_DEF]->val1 / 100; - break; - } - if (sc->data[SC_SPL_DEF]) - for (i=0;ARRAYLENGTH(mob_splendide)>i;i++) - if (mob_splendide[i]==((TBL_MOB*)src)->class_) { - damage -= damage * sc->data[SC_SPL_DEF]->val1 / 100; - break; + }else if( tsd && !(nk&NK_NO_CARDFIX_DEF) ){ + if( !(nk&NK_NO_ELEFIX) ) + { + int ele_fix = tsd->subele[s_ele]; + for (i = 0; ARRAYLENGTH(tsd->subele2) > i && tsd->subele2[i].rate != 0; i++) + { + if(tsd->subele2[i].ele != s_ele) continue; + if(!(tsd->subele2[i].flag&flag&BF_WEAPONMASK && + tsd->subele2[i].flag&flag&BF_RANGEMASK && + tsd->subele2[i].flag&flag&BF_SKILLMASK)) + continue; + ele_fix += tsd->subele2[i].rate; + } + cardfix=cardfix*(100-ele_fix)/100; + if( left&1 && s_ele_ != s_ele ) + { + int ele_fix_lh = tsd->subele[s_ele_]; + for (i = 0; ARRAYLENGTH(tsd->subele2) > i && tsd->subele2[i].rate != 0; i++) + { + if(tsd->subele2[i].ele != s_ele_) continue; + if(!(tsd->subele2[i].flag&flag&BF_WEAPONMASK && + tsd->subele2[i].flag&flag&BF_RANGEMASK && + tsd->subele2[i].flag&flag&BF_SKILLMASK)) + continue; + ele_fix_lh += tsd->subele2[i].rate; } - } + cardfix=cardfix*(100-ele_fix_lh)/100; + } + } + cardfix=cardfix*(100-tsd->subsize[sstatus->size])/100; + cardfix=cardfix*(100-tsd->subrace2[s_race2])/100; + cardfix=cardfix*(100-tsd->subrace[sstatus->race])/100; + cardfix=cardfix*(100-tsd->subrace[is_boss(src)?RC_BOSS:RC_NONBOSS])/100; + if( sstatus->race != RC_DEMIHUMAN ) + cardfix=cardfix*(100-tsd->subrace[RC_NONDEMIHUMAN])/100; - if((sce=sc->data[SC_ARMOR]) && //NPC_DEFENDER - sce->val3&flag && sce->val4&flag) - damage -= damage * sc->data[SC_ARMOR]->val2 / 100; + for( i = 0; i < ARRAYLENGTH(tsd->add_def) && tsd->add_def[i].rate;i++ ) { + if( tsd->add_def[i].class_ == s_class ) { + cardfix=cardfix*(100-tsd->add_def[i].rate)/100; + break; + } + } -#ifdef RENEWAL - if(sc->data[SC_ENERGYCOAT] && (flag&BF_WEAPON || flag&BF_MAGIC) && skill_id != WS_CARTTERMINATION) -#else - if(sc->data[SC_ENERGYCOAT] && (flag&BF_WEAPON && skill_id != WS_CARTTERMINATION)) -#endif - { - struct status_data *status = status_get_status_data(bl); - int per = 100*status->sp / status->max_sp -1; //100% should be counted as the 80~99% interval - per /=20; //Uses 20% SP intervals. - //SP Cost: 1% + 0.5% per every 20% SP - if (!status_charge(bl, 0, (10+5*per)*status->max_sp/1000)) - status_change_end(bl, SC_ENERGYCOAT, INVALID_TIMER); - //Reduction: 6% + 6% every 20% - damage -= damage * (6 * (1+per)) / 100; - } - if(sc->data[SC_GRANITIC_ARMOR]){ - damage -= damage * sc->data[SC_GRANITIC_ARMOR]->val2 / 100; - } - if(sc->data[SC_PAIN_KILLER]){ - damage -= damage * sc->data[SC_PAIN_KILLER]->val3 / 100; - } - if((sce=sc->data[SC_MAGMA_FLOW]) && (rnd()%100 <= sce->val2) ){ - skill->castend_damage_id(bl,src,MH_MAGMA_FLOW,sce->val1,iTimer->gettick(),0); + if( flag&BF_SHORT ) + cardfix = cardfix * ( 100 - tsd->bonus.near_attack_def_rate ) / 100; + else // BF_LONG (there's no other choice) + cardfix = cardfix * ( 100 - tsd->bonus.long_attack_def_rate ) / 100; + + if( tsd->sc.data[SC_PROTECT_DEF] ) + cardfix = cardfix * ( 100 - tsd->sc.data[SC_PROTECT_DEF]->val1 ) / 100; + + if( cardfix != 1000 ) + damage = damage * cardfix / 1000; } + break; + case BF_MISC: + if( tsd && !(nk&NK_NO_CARDFIX_DEF) ){ + // misc damage reduction from equipment + if (!(nk&NK_NO_ELEFIX)) + { + int ele_fix = tsd->subele[s_ele]; + for (i = 0; ARRAYLENGTH(tsd->subele2) > i && tsd->subele2[i].rate != 0; i++) + { + if(tsd->subele2[i].ele != s_ele) continue; + if(!(tsd->subele2[i].flag&flag&BF_WEAPONMASK && + tsd->subele2[i].flag&flag&BF_RANGEMASK && + tsd->subele2[i].flag&flag&BF_SKILLMASK)) + continue; + ele_fix += tsd->subele2[i].rate; + } + cardfix=cardfix*(100-ele_fix)/100; + } + cardfix=cardfix*(100-tsd->subsize[sstatus->size])/100; + cardfix=cardfix*(100-tsd->subrace2[s_race2])/100; + cardfix=cardfix*(100-tsd->subrace[sstatus->race])/100; + cardfix=cardfix*(100-tsd->subrace[is_boss(src)?RC_BOSS:RC_NONBOSS])/100; + if( sstatus->race != RC_DEMIHUMAN ) + cardfix=cardfix*(100-tsd->subrace[RC_NONDEMIHUMAN])/100; - if( (sce = sc->data[SC_STONEHARDSKIN]) && flag&BF_WEAPON && damage > 0 ) { - sce->val2 -= damage; - if( src->type == BL_PC ) { - TBL_PC *ssd = BL_CAST(BL_PC, src); - if (ssd && ssd->status.weapon != W_BOW) - skill->break_equip(src, EQP_WEAPON, 3000, BCT_SELF); - } else - skill->break_equip(src, EQP_WEAPON, 3000, BCT_SELF); - // 30% chance to reduce monster's ATK by 25% for 10 seconds. - if( src->type == BL_MOB ) - sc_start(src, SC_STRIPWEAPON, 30, 0, skill->get_time2(RK_STONEHARDSKIN, sce->val1)); - if( sce->val2 <= 0 ) - status_change_end(bl, SC_STONEHARDSKIN, INVALID_TIMER); - } + cardfix = cardfix * ( 100 - tsd->bonus.misc_def_rate ) / 100; + if( flag&BF_SHORT ) + cardfix = cardfix * ( 100 - tsd->bonus.near_attack_def_rate ) / 100; + else // BF_LONG (there's no other choice) + cardfix = cardfix * ( 100 - tsd->bonus.long_attack_def_rate ) / 100; -/** - * In renewal steel body reduces all incoming damage by 1/10 - **/ -#ifdef RENEWAL - if( sc->data[SC_STEELBODY] ) { - damage = damage > 10 ? damage / 10 : 1; - } -#endif + if (cardfix != 1000) + damage = damage * cardfix / 1000; + } + break; + } - //Finally added to remove the status of immobile when aimedbolt is used. [Jobbie] - if( skill_id == RA_AIMEDBOLT && (sc->data[SC_BITE] || sc->data[SC_ANKLE] || sc->data[SC_ELECTRICSHOCKER]) ) - { - status_change_end(bl, SC_BITE, INVALID_TIMER); - status_change_end(bl, SC_ANKLE, INVALID_TIMER); - status_change_end(bl, SC_ELECTRICSHOCKER, INVALID_TIMER); - } + return damage; +} - //Finally Kyrie because it may, or not, reduce damage to 0. - if((sce = sc->data[SC_KYRIE]) && damage > 0){ - sce->val2-=damage; - if(flag&BF_WEAPON || skill_id == TF_THROWSTONE){ - if(sce->val2>=0) - damage=0; - else - damage=-sce->val2; +/*========================================== + * Calculates defense reduction. [malufett] + * flag: + * &1 - idef/imdef(Ignore defense) + * &2 - pdef(Pierce defense) + * &4 - tdef(Total defense reduction) + *------------------------------------------*/ +int battle_calc_defense(int attack_type, struct block_list *src, struct block_list *target, uint16 skill_id, uint16 skill_lv, int damage, int flag, int pdef){ + struct status_data *sstatus, *tstatus; + struct map_session_data *sd, *tsd; + struct status_change *sc, *tsc; + int i; + + if( !damage ) + return 0; + + nullpo_ret(src); + nullpo_ret(target); + + sd = BL_CAST(BL_PC, src); + tsd = BL_CAST(BL_PC, target); + sstatus = status_get_status_data(src); + tstatus = status_get_status_data(target); + sc = status_get_sc(src); + tsc = status_get_sc(target); + + switch(attack_type){ + case BF_WEAPON: + { + /** Take note in RE + * def1 = equip def + * def2 = status def + **/ + defType def1 = status_get_def(target); //Don't use tstatus->def1 due to skill timer reductions. + short def2 = tstatus->def2, vit_def; + + def1 = status_calc_def2(target, tsc, def1, false); // equip def(RE) + def2 = status_calc_def(target, tsc, def2, false); // status def(RE) + + if( sd ){ + i = sd->ignore_def[is_boss(target)?RC_BOSS:RC_NONBOSS]; + i += sd->ignore_def[tstatus->race]; + if( i ){ + if( i > 100 ) i = 100; + def1 -= def1 * i / 100; + def2 -= def2 * i / 100; + } } - if((--sce->val3)<=0 || (sce->val2<=0) || skill_id == AL_HOLYLIGHT) - status_change_end(bl, SC_KYRIE, INVALID_TIMER); - } - if( sc->data[SC_MEIKYOUSISUI] && rand()%100 < 40 ) // custom value - damage = 0; + if( sc && sc->data[SC_EXPIATIO] ){ + i = 5 * sc->data[SC_EXPIATIO]->val1; // 5% per level + def1 -= def1 * i / 100; + def2 -= def2 * i / 100; + } + + if( battle_config.vit_penalty_type && battle_config.vit_penalty_target&target->type ) { + unsigned char target_count; //256 max targets should be a sane max + target_count = unit_counttargeted(target); + if(target_count >= battle_config.vit_penalty_count) { + if(battle_config.vit_penalty_type == 1) { + if( !tsc || !tsc->data[SC_STEELBODY] ) + def1 = (def1 * (100 - (target_count - (battle_config.vit_penalty_count - 1))*battle_config.vit_penalty_num))/100; + def2 = (def2 * (100 - (target_count - (battle_config.vit_penalty_count - 1))*battle_config.vit_penalty_num))/100; + } else { //Assume type 2 + if( !tsc || !tsc->data[SC_STEELBODY] ) + def1 -= (target_count - (battle_config.vit_penalty_count - 1))*battle_config.vit_penalty_num; + def2 -= (target_count - (battle_config.vit_penalty_count - 1))*battle_config.vit_penalty_num; + } + } + if(skill_id == AM_ACIDTERROR) def1 = 0; //Acid Terror ignores only armor defense. [Skotlex] + if(def2 < 1) def2 = 1; + } + //Vitality reduction from rodatazone: http://rodatazone.simgaming.net/mechanics/substats.php#def + if (tsd) //Sd vit-eq + { +#ifndef RENEWAL + //[VIT*0.5] + rnd([VIT*0.3], max([VIT*0.3],[VIT^2/150]-1)) + vit_def = def2*(def2-15)/150; + vit_def = def2/2 + (vit_def>0?rnd()%vit_def:0); +#else + vit_def = def2; +#endif + if((battle->check_undead(sstatus->race,sstatus->def_ele) || sstatus->race==RC_DEMON) && //This bonus already doesnt work vs players + src->type == BL_MOB && (i=pc->checkskill(tsd,AL_DP)) > 0) + vit_def += i*(int)(3 +(tsd->status.base_level+1)*0.04); // submitted by orn + if( src->type == BL_MOB && (i=pc->checkskill(tsd,RA_RANGERMAIN))>0 && + (sstatus->race == RC_BRUTE || sstatus->race == RC_FISH || sstatus->race == RC_PLANT) ) + vit_def += i*5; + } + else { //Mob-Pet vit-eq +#ifndef RENEWAL + //VIT + rnd(0,[VIT/20]^2-1) + vit_def = (def2/20)*(def2/20); + vit_def = def2 + (vit_def>0?rnd()%vit_def:0); +#else + vit_def = def2; +#endif + } + + if (battle_config.weapon_defense_type) { + vit_def += def1*battle_config.weapon_defense_type; + def1 = 0; + } + #ifdef RENEWAL + /** + * RE DEF Reduction + * Damage = Attack * (4000+eDEF)/(4000+eDEF*10) - sDEF + * Pierce defence gains 1 atk per def/2 + **/ + if( def1 == -400 ) /* being hit by a gazillion units, you hit the jackpot and got -400 which creates a division by 0 and subsequently crashes */ + def1 = -399; - if (!damage) return 0; + if( flag&2 ) + damage += def1 >> 1; - if( (sce = sc->data[SC_LIGHTNINGWALK]) && flag&BF_LONG && rnd()%100 < sce->val1 ) { - int dx[8]={0,-1,-1,-1,0,1,1,1}; - int dy[8]={1,1,0,-1,-1,-1,0,1}; - uint8 dir = iMap->calc_dir(bl, src->x, src->y); - if( unit_movepos(bl, src->x-dx[dir], src->y-dy[dir], 1, 1) ) { - clif->slide(bl,src->x-dx[dir],src->y-dy[dir]); - unit_setdir(bl, dir); + if( !(flag&1) && !(flag&2) ) + if( flag&4 ) + damage -= (def1 + vit_def); + else + damage = damage * (4000+def1) / (4000+10*def1) - vit_def; + + #else + if( def1 > 100 ) def1 = 100; + if( !(flag&1) ){ + if( flag&2 ) + damage = damage * pdef * (def1+vit_def) / 100; + else + damage = damage * (100-def1) / 100; + } + if( !(flag&1 || flag&2) ) + damage -= vit_def; + #endif } - d->dmg_lv = ATK_DEF; - status_change_end(bl, SC_LIGHTNINGWALK, INVALID_TIMER); - return 0; - } + break; - //Probably not the most correct place, but it'll do here - //(since battle_drain is strictly for players currently) - if ((sce=sc->data[SC_BLOODLUST]) && flag&BF_WEAPON && damage > 0 && - rnd()%100 < sce->val3) - status_heal(src, damage*sce->val4/100, 0, 3); + case BF_MAGIC: + { + defType mdef = tstatus->mdef; + short mdef2= tstatus->mdef2; - if( sd && (sce = sc->data[SC_FORCEOFVANGUARD]) && flag&BF_WEAPON && rnd()%100 < sce->val2 ) - pc->addspiritball(sd,skill->get_time(LG_FORCEOFVANGUARD,sce->val1),sce->val3); - if (sc->data[SC_STYLE_CHANGE] && rnd()%2) { - TBL_HOM *hd = BL_CAST(BL_HOM,bl); - if (hd) homun->addspiritball(hd, 10); //add a sphere - } + mdef2 = status_calc_mdef(target, tsc, mdef2, false); // status mdef(RE) + mdef = status_calc_mdef2(target, tsc, mdef, false); // equip mde(RE) - if( sc->data[SC__DEADLYINFECT] && damage > 0 && rnd()%100 < 65 + 5 * sc->data[SC__DEADLYINFECT]->val1 ) - status_change_spread(bl, src); // Deadly infect attacked side + if( flag&1 ) + mdef = 0; - if( sc && sc->data[SC__SHADOWFORM] ) { - struct block_list *s_bl = iMap->id2bl(sc->data[SC__SHADOWFORM]->val2); - if( !s_bl || s_bl->m != bl->m ) { // If the shadow form target is not present remove the sc. - status_change_end(bl, SC__SHADOWFORM, INVALID_TIMER); - } else if( status_isdead(s_bl) || !battle->check_target(src,s_bl,BCT_ENEMY)) { // If the shadow form target is dead or not your enemy remove the sc in both. - status_change_end(bl, SC__SHADOWFORM, INVALID_TIMER); - if( s_bl->type == BL_PC ) - ((TBL_PC*)s_bl)->shadowform_id = 0; - } else { - if( (--sc->data[SC__SHADOWFORM]->val3) < 0 ) { // If you have exceded max hits supported, remove the sc in both. - status_change_end(bl, SC__SHADOWFORM, INVALID_TIMER); - if( s_bl->type == BL_PC ) - ((TBL_PC*)s_bl)->shadowform_id = 0; - } else { - status_damage(bl, s_bl, damage, 0, clif->damage(s_bl, s_bl, iTimer->gettick(), 500, 500, damage, -1, 0, 0), 0); - return ATK_NONE; + if(sd) { + i = sd->ignore_mdef[is_boss(target)?RC_BOSS:RC_NONBOSS]; + i += sd->ignore_mdef[tstatus->race]; + if (i) + { + if (i > 100) i = 100; + mdef -= mdef * i/100; + //mdef2-= mdef2* i/100; } } - } - + #ifdef RENEWAL + /** + * RE MDEF Reduction + * Damage = Magic Attack * (1000+eMDEF)/(1000+eMDEF) - sMDEF + **/ + damage = damage * (1000 + mdef) / (1000 + mdef * 10) - mdef2; + #else + if(battle_config.magic_defense_type) + damage = damage - mdef*battle_config.magic_defense_type - mdef2; + else + damage = damage * (100-mdef)/100 - mdef2; + #endif + } + break; } + return damage; +} - //SC effects from caster side. - sc = status_get_sc(src); +int battle_calc_skillratio(int attack_type, struct block_list *src, struct block_list *target, uint16 skill_id, uint16 skill_lv, int skillratio, int flag){ + int i, addedratio; + struct status_change *sc, *tsc; + struct map_session_data *sd, *tsd; + struct status_data *status, *tstatus; - if (sc && sc->count) { - if( sc->data[SC_INVINCIBLE] && !sc->data[SC_INVINCIBLEOFF] ) - damage += damage * 75 / 100; - // [Epoque] - if (bl->type == BL_MOB) { - int i; + nullpo_ret(src); + nullpo_ret(target); - if ( ((sce=sc->data[SC_MANU_ATK]) && (flag&BF_WEAPON)) || - ((sce=sc->data[SC_MANU_MATK]) && (flag&BF_MAGIC)) - ) - for (i=0;ARRAYLENGTH(mob_manuk)>i;i++) - if (((TBL_MOB*)bl)->class_==mob_manuk[i]) { - damage += damage * sce->val1 / 100; - break; + sd = BL_CAST(BL_PC, src); + tsd = BL_CAST(BL_PC, target); + sc = status_get_sc(src); + tsc = status_get_sc(target); + status = status_get_status_data(src); + tstatus = status_get_status_data(target); + + addedratio = skillratio - 100; + + switch(attack_type){ + case BF_MAGIC: + switch(skill_id){ + case MG_NAPALMBEAT: + skillratio += skill_lv * 10 - 30; + break; + case MG_FIREBALL: + #ifdef RENEWAL + skillratio += 20 * skill_lv; + #else + skillratio += skill_lv * 10 - 30; + #endif + break; + case MG_SOULSTRIKE: + if (battle->check_undead(tstatus->race,tstatus->def_ele)) + skillratio += 5*skill_lv; + break; + case MG_FIREWALL: + skillratio -= 50; + break; + case MG_THUNDERSTORM: + /** + * in Renewal Thunder Storm boost is 100% (in pre-re, 80%) + **/ + #ifndef RENEWAL + skillratio -= 20; + #endif + break; + case MG_FROSTDIVER: + skillratio += 10 * skill_lv; + break; + case AL_HOLYLIGHT: + skillratio += 25; + if (sc && sc->data[SC_SOULLINK] && sc->data[SC_SOULLINK]->val2 == SL_PRIEST) + skillratio *= 5; //Does 5x damage include bonuses from other skills? + break; + case AL_RUWACH: + skillratio += 45; + break; + case WZ_FROSTNOVA: + skillratio += (100+skill_lv*10) * 2 / 3 - 100; + break; + case WZ_FIREPILLAR: + if (skill_lv > 10) + skillratio += 100; + else + skillratio -= 80; + break; + case WZ_SIGHTRASHER: + skillratio += 20 * skill_lv; + break; + case WZ_WATERBALL: + skillratio += 30 * skill_lv; + break; + case WZ_STORMGUST: + skillratio += 40 * skill_lv; + break; + case HW_NAPALMVULCAN: + skillratio += 10 * skill_lv - 30; + break; + case SL_STIN: + skillratio += (tstatus->size!=SZ_SMALL?-99:10*skill_lv); //target size must be small (0) for full damage. + break; + case SL_STUN: + skillratio += (tstatus->size!=SZ_BIG?5*skill_lv:-99); //Full damage is dealt on small/medium targets + break; + case SL_SMA: + skillratio += -60 + status_get_lv(src); //Base damage is 40% + lv% + break; + case NJ_KOUENKA: + skillratio -= 10; + break; + case NJ_KAENSIN: + skillratio -= 50; + break; + case NJ_BAKUENRYU: + skillratio += 50 * (skill_lv-1); + break; + case NJ_HYOUSYOURAKU: + skillratio += 50 * skill_lv; + break; + case NJ_RAIGEKISAI: + skillratio += 60 + 40 * skill_lv; + break; + case NJ_KAMAITACHI: + case NPC_ENERGYDRAIN: + skillratio += 100 * skill_lv; + break; + case NPC_EARTHQUAKE: + skillratio += 100 + 100 * skill_lv + 100 * (skill_lv/2); + break; + #ifdef RENEWAL + case WZ_HEAVENDRIVE: + case WZ_METEOR: + skillratio += 25; + break; + case WZ_VERMILION: + { + int interval = 0, per = interval, ratio = per; + while( (per++) < skill_lv ){ + ratio += interval; + if(per%3==0) interval += 20; + } + if( skill_lv > 9 ) + ratio -= 10; + skillratio += ratio; } - if ( ((sce=sc->data[SC_SPL_ATK]) && (flag&BF_WEAPON)) || - ((sce=sc->data[SC_SPL_MATK]) && (flag&BF_MAGIC)) - ) - for (i=0;ARRAYLENGTH(mob_splendide)>i;i++) - if (((TBL_MOB*)bl)->class_==mob_splendide[i]) { - damage += damage * sce->val1 / 100; - break; + break; + case NJ_HUUJIN: + skillratio += 50; + break; + #else + case WZ_VERMILION: + skillratio += 20*skill_lv-20; + break; + #endif + /** + * Arch Bishop + **/ + case AB_JUDEX: + skillratio += 180 + 20 * skill_lv; + if (skill_lv > 4) skillratio += 20; + RE_LVL_DMOD(100); + break; + case AB_ADORAMUS: + skillratio += 400 + 100 * skill_lv; + RE_LVL_DMOD(100); + break; + case AB_DUPLELIGHT_MAGIC: + skillratio += 100 + 20 * skill_lv; + break; + /** + * Warlock + **/ + case WL_SOULEXPANSION: // MATK [{( Skill Level + 4 ) x 100 ) + ( Caster?s INT )} x ( Caster?s Base Level / 100 )] % + skillratio += 300 + 100 * skill_lv + status_get_int(src); + RE_LVL_DMOD(100); + break; + case WL_FROSTMISTY: // MATK [{( Skill Level x 100 ) + 200 } x ( Caster’s Base Level / 100 )] % + skillratio += 100 + 100 * skill_lv; + RE_LVL_DMOD(100); + break; + case WL_JACKFROST: + if( tsc && tsc->data[SC_FROSTMISTY] ){ + skillratio += 900 + 300 * skill_lv; + RE_LVL_DMOD(100); + }else{ + skillratio += 400 + 100 * skill_lv; + RE_LVL_DMOD(150); } - } - if( sc->data[SC_POISONINGWEAPON] && skill_id != GC_VENOMPRESSURE && (flag&BF_WEAPON) && damage > 0 && rnd()%100 < sc->data[SC_POISONINGWEAPON]->val3 ) - sc_start(bl,sc->data[SC_POISONINGWEAPON]->val2,100,sc->data[SC_POISONINGWEAPON]->val1,skill->get_time2(GC_POISONINGWEAPON, 1)); - if( sc->data[SC__DEADLYINFECT] && damage > 0 && rnd()%100 < 65 + 5 * sc->data[SC__DEADLYINFECT]->val1 ) - status_change_spread(src, bl); - if (sc->data[SC_STYLE_CHANGE] && rnd()%2) { - TBL_HOM *hd = BL_CAST(BL_HOM,bl); - if (hd) homun->addspiritball(hd, 10); - } - } - /* no data claims these settings affect anything other than players */ - if( damage && sd && bl->type == BL_PC ) { - switch( skill_id ) { - //case PA_PRESSURE: /* pressure also belongs to this list but it doesn't reach this area -- so dont worry about it */ - case HW_GRAVITATION: - case NJ_ZENYNAGE: - case KO_MUCHANAGE: - break; - default: - if (flag & BF_SKILL) { //Skills get a different reduction than non-skills. [Skotlex] - if (flag&BF_WEAPON) - damage = damage * map[bl->m].weapon_damage_rate / 100; - if (flag&BF_MAGIC) - damage = damage * map[bl->m].magic_damage_rate / 100; - if (flag&BF_MISC) - damage = damage * map[bl->m].misc_damage_rate / 100; - } else { //Normal attacks get reductions based on range. - if (flag & BF_SHORT) - damage = damage * map[bl->m].short_damage_rate / 100; - if (flag & BF_LONG) - damage = damage * map[bl->m].long_damage_rate / 100; + break; + case WL_DRAINLIFE: + skillratio = 200 * skill_lv + status_get_int(src); + RE_LVL_DMOD(100); + break; + case WL_CRIMSONROCK: + skillratio = 300 * skill_lv; + RE_LVL_DMOD(100); + skillratio += 1300; + break; + case WL_HELLINFERNO: + skillratio = 300 * skill_lv; + RE_LVL_DMOD(100); + // Shadow: MATK [{( Skill Level x 300 ) x ( Caster Base Level / 100 ) x 4/5 }] % + // Fire : MATK [{( Skill Level x 300 ) x ( Caster Base Level / 100 ) /5 }] % + if( flag&ELE_DARK ) + skillratio *= 4; + skillratio /= 5; + break; + case WL_COMET: + i = ( sc ? distance_xy(target->x, target->y, sc->comet_x, sc->comet_y) : 8 ); + if( i <= 3 ) skillratio += 2400 + 500 * skill_lv; // 7 x 7 cell + else + if( i <= 5 ) skillratio += 1900 + 500 * skill_lv; // 11 x 11 cell + else + if( i <= 7 ) skillratio += 1400 + 500 * skill_lv; // 15 x 15 cell + else + skillratio += 900 + 500 * skill_lv; // 19 x 19 cell + + if( sd && sd->status.party_id ){ + struct map_session_data* psd; + int static p_sd[5] = {0, 0, 0, 0, 0}, c; // just limit it to 5 + + c = 0; + memset (p_sd, 0, sizeof(p_sd)); + party_foreachsamemap(skill->check_condition_char_sub, sd, 3, &sd->bl, &c, &p_sd, skill_id); + c = ( c > 1 ? rand()%c : 0 ); + + if( (psd = iMap->id2sd(p_sd[c])) && pc->checkskill(psd,WL_COMET) > 0 ){ + skillratio = skill_lv * 400; //MATK [{( Skill Level x 400 ) x ( Caster's Base Level / 120 )} + 2500 ] % + RE_LVL_DMOD(120); + skillratio += 2500; + status_zap(&psd->bl, 0, skill->get_sp(skill_id, skill_lv) / 2); + } + } + break; + case WL_CHAINLIGHTNING_ATK: + skillratio += 400 + 100 * skill_lv; + RE_LVL_DMOD(100); + if(flag > 0) + skillratio += 100 * flag; + break; + case WL_EARTHSTRAIN: + skillratio += 1900 + 100 * skill_lv; + RE_LVL_DMOD(100); + break; + case WL_TETRAVORTEX_FIRE: + case WL_TETRAVORTEX_WATER: + case WL_TETRAVORTEX_WIND: + case WL_TETRAVORTEX_GROUND: + skillratio += 400 + 500 * skill_lv; + break; + case WL_SUMMON_ATK_FIRE: + case WL_SUMMON_ATK_WATER: + case WL_SUMMON_ATK_WIND: + case WL_SUMMON_ATK_GROUND: + skillratio = skill_lv * (status_get_lv(src) + ( sd ? sd->status.job_level : 50 ));// This is close to official, but lacking a little info to finalize. [Rytech] + RE_LVL_DMOD(100); + break; + case LG_RAYOFGENESIS: + { + int16 lv = skill_lv; + int bandingBonus = 0; + if( sc && sc->data[SC_BANDING] ) + bandingBonus = 200 * (sd ? skill->check_pc_partner(sd,skill_id,&lv,skill->get_splash(skill_id,skill_lv),0) : 1); + skillratio = ((300 * skill_lv) + bandingBonus) * (sd ? sd->status.job_level : 1) / 25; } - if(!damage) damage = 1; break; - } - } - - if(battle_config.skill_min_damage && damage > 0 && damage < div_) - { - if ((flag&BF_WEAPON && battle_config.skill_min_damage&1) - || (flag&BF_MAGIC && battle_config.skill_min_damage&2) - || (flag&BF_MISC && battle_config.skill_min_damage&4) - ) - damage = div_; - } + case LG_SHIELDSPELL:// [(Casters Base Level x 4) + (Shield MDEF x 100) + (Casters INT x 2)] % + if( sd ) { + skillratio = status_get_lv(src) * 4 + sd->bonus.shieldmdef * 100 + status_get_int(src) * 2; + } else + skillratio += 1900; //2000% + break; + case WM_METALICSOUND: + skillratio += 120 * skill_lv + 60 * ( sd? pc->checkskill(sd, WM_LESSON) : 10 ) - 100; + break; + /*case WM_SEVERE_RAINSTORM: + skillratio += 50 * skill_lv; + break; - if( bl->type == BL_MOB && !status_isdead(bl) && src != bl) { - if (damage > 0 ) - mobskill_event((TBL_MOB*)bl,src,iTimer->gettick(),flag); - if (skill_id) - mobskill_event((TBL_MOB*)bl,src,iTimer->gettick(),MSC_SKILLUSED|(skill_id<<16)); - } - if( sd ) { - if( pc_ismadogear(sd) && rnd()%100 < 50 ) { - short element = skill->get_ele(skill_id, skill_lv); - if( !skill_id || element == -1 ) { //Take weapon's element - struct status_data *sstatus = NULL; - if( src->type == BL_PC && ((TBL_PC*)src)->bonus.arrow_ele ) - element = ((TBL_PC*)src)->bonus.arrow_ele; - else if( (sstatus = status_get_status_data(src)) ) { - element = sstatus->rhw.ele; - } + WM_SEVERE_RAINSTORM just set a unit place, + refer to WM_SEVERE_RAINSTORM_MELEE to set the formula. + */ + case WM_REVERBERATION_MAGIC: + // MATK [{(Skill Level x 100) + 100} x Casters Base Level / 100] % + skillratio += 100 * (sd ? pc->checkskill(sd, WM_REVERBERATION) : 1); + RE_LVL_DMOD(100); + break; + case SO_FIREWALK: + skillratio = 300; + RE_LVL_DMOD(100); + if( sc && sc->data[SC_HEATER_OPTION] ) + skillratio += sc->data[SC_HEATER_OPTION]->val3; + break; + case SO_ELECTRICWALK: + skillratio = 300; + RE_LVL_DMOD(100); + if( sc && sc->data[SC_BLAST_OPTION] ) + skillratio += sd ? sd->status.job_level / 2 : 0; + break; + case SO_EARTHGRAVE: + skillratio = ( 200 * ( sd ? pc->checkskill(sd, SA_SEISMICWEAPON) : 10 ) + status_get_int(src) * skill_lv ); + RE_LVL_DMOD(100); + if( sc && sc->data[SC_CURSED_SOIL_OPTION] ) + skillratio += sc->data[SC_CURSED_SOIL_OPTION]->val2; + break; + case SO_DIAMONDDUST: + skillratio = ( 200 * ( sd ? pc->checkskill(sd, SA_FROSTWEAPON) : 10 ) + status_get_int(src) * skill_lv ); + RE_LVL_DMOD(100); + if( sc && sc->data[SC_COOLER_OPTION] ) + skillratio += sc->data[SC_COOLER_OPTION]->val3; + break; + case SO_POISON_BUSTER: + skillratio += 1100 + 300 * skill_lv; + if( sc && sc->data[SC_CURSED_SOIL_OPTION] ) + skillratio += sc->data[SC_CURSED_SOIL_OPTION]->val2; + break; + case SO_PSYCHIC_WAVE: + skillratio += -100 + skill_lv * 70 + (status_get_int(src) * 3); + RE_LVL_DMOD(100); + if( sc ){ + if( sc->data[SC_HEATER_OPTION] ) + skillratio += sc->data[SC_HEATER_OPTION]->val3; + else if(sc->data[SC_COOLER_OPTION] ) + skillratio += sc->data[SC_COOLER_OPTION]->val3; + else if(sc->data[SC_BLAST_OPTION] ) + skillratio += sc->data[SC_BLAST_OPTION]->val2; + else if(sc->data[SC_CURSED_SOIL_OPTION] ) + skillratio += sc->data[SC_CURSED_SOIL_OPTION]->val3; + } + break; + case SO_VARETYR_SPEAR: //MATK [{( Endow Tornado skill level x 50 ) + ( Caster INT x Varetyr Spear Skill level )} x Caster Base Level / 100 ] % + skillratio = status_get_int(src) * skill_lv + ( sd ? pc->checkskill(sd, SA_LIGHTNINGLOADER) * 50 : 0 ); + RE_LVL_DMOD(100); + if( sc && sc->data[SC_BLAST_OPTION] ) + skillratio += sd ? sd->status.job_level * 5 : 0; + break; + case SO_CLOUD_KILL: + skillratio += -100 + skill_lv * 40; + RE_LVL_DMOD(100); + if( sc && sc->data[SC_CURSED_SOIL_OPTION] ) + skillratio += sc->data[SC_CURSED_SOIL_OPTION]->val2; + break; + case GN_DEMONIC_FIRE: + if( skill_lv > 20) + { // Fire expansion Lv.2 + skillratio += 110 + 20 * (skill_lv - 20) + status_get_int(src) * 3; // Need official INT bonus. [LimitLine] + } + else if( skill_lv > 10 ) + { // Fire expansion Lv.1 + skillratio += 110 + 20 * (skill_lv - 10) / 2; + } + else + skillratio += 110 + 20 * skill_lv; + break; + // Magical Elemental Spirits Attack Skills + case EL_FIRE_MANTLE: + case EL_WATER_SCREW: + skillratio += 900; + break; + case EL_FIRE_ARROW: + case EL_ROCK_CRUSHER_ATK: + skillratio += 200; + break; + case EL_FIRE_BOMB: + case EL_ICE_NEEDLE: + case EL_HURRICANE_ATK: + skillratio += 400; + break; + case EL_FIRE_WAVE: + case EL_TYPOON_MIS_ATK: + skillratio += 1100; + break; + case MH_ERASER_CUTTER: + if(skill_lv%2) skillratio += 400; //600:800:1000 + else skillratio += 700; //1000:1200 + skillratio += 100 * skill_lv; + break; + case MH_XENO_SLASHER: + if(skill_lv%2) skillratio += 350 + 50 * skill_lv; //500:600:700 + else skillratio += 400 + 100 * skill_lv; //700:900 + break; + case MH_HEILIGE_STANGE: + skillratio += 400 + 250 * skill_lv; + break; + case MH_POISON_MIST: + skillratio += 100 * skill_lv; + break; + case KO_KAIHOU: + if( sd ){ + ARR_FIND(1, 6, i, sd->charm[i] > 0); + if( i < 5 ){ + skillratio += -100 + 200 * sd->charm[i]; + RE_LVL_DMOD(100); + pc->del_charm(sd, sd->charm[i], i); + } + } + break; } - else if( element == -2 ) //Use enchantment's element - element = status_get_attack_sc_element(src,status_get_sc(src)); - else if( element == -3 ) //Use random element - element = rnd()%ELE_MAX; - if( element == ELE_FIRE || element == ELE_WATER ) - pc->overheat(sd,element == ELE_FIRE ? 1 : -1); - } - } - - return damage; -} - -/*========================================== - * Calculates BG related damage adjustments. - *------------------------------------------*/ -int battle_calc_bg_damage(struct block_list *src, struct block_list *bl, int damage, int div_, uint16 skill_id, uint16 skill_lv, int flag) -{ - if( !damage ) - return 0; - - if( bl->type == BL_MOB ) { - struct mob_data* md = BL_CAST(BL_MOB, bl); - - if( flag&BF_SKILL && (md->class_ == MOBID_BLUE_CRYST || md->class_ == MOBID_PINK_CRYST) ) - return 0; // Crystal cannot receive skill damage on battlegrounds - } - - return damage; -} - -/*========================================== - * Calculates GVG related damage adjustments. - *------------------------------------------*/ -int battle_calc_gvg_damage(struct block_list *src,struct block_list *bl,int damage,int div_,uint16 skill_id,uint16 skill_lv,int flag) -{ - struct mob_data* md = BL_CAST(BL_MOB, bl); - int class_ = status_get_class(bl); - - if (!damage) //No reductions to make. - return 0; - - if(md && md->guardian_data) { - if(class_ == MOBID_EMPERIUM && flag&BF_SKILL) { - //Skill immunity. - switch (skill_id) { -#ifndef RENEWAL - case MO_TRIPLEATTACK: -#endif - case HW_GRAVITATION: - break; - default: - return 0; - } - } - if(src->type != BL_MOB) { - struct guild *g = src->type == BL_PC ? ((TBL_PC *)src)->guild : guild->search(status_get_guild_id(src)); - - if (class_ == MOBID_EMPERIUM && (!g || guild->checkskill(g,GD_APPROVAL) <= 0 )) - return 0; - - if (g && battle_config.guild_max_castles && guild->checkcastles(g)>=battle_config.guild_max_castles) - return 0; // [MouseJstr] - } - } - - switch (skill_id) { - case PA_PRESSURE: - case HW_GRAVITATION: - case NJ_ZENYNAGE: - case KO_MUCHANAGE: - break; - default: - /* Uncomment if you want god-mode Emperiums at 100 defense. [Kisuka] - if (md && md->guardian_data) { - damage -= damage * (md->guardian_data->castle->defense/100) * battle_config.castle_defense_rate/100; - } - */ - break; - } - - return damage; -} - -/*========================================== - * HP/SP drain calculation - *------------------------------------------*/ -int battle_calc_drain(int damage, int rate, int per) { - int diff = 0; - - if (per && rnd()%1000 < rate) { - diff = (damage * per) / 100; - if (diff == 0) { - if (per > 0) - diff = 1; - else - diff = -1; - } - } - return diff; -} - -/*========================================== - * Passif skill dammages increases - *------------------------------------------*/ -int battle_addmastery(struct map_session_data *sd,struct block_list *target,int dmg,int type) { - int damage,skill; - struct status_data *status = status_get_status_data(target); - int weapon; - damage = dmg; - - nullpo_ret(sd); - - if((skill = pc->checkskill(sd,AL_DEMONBANE)) > 0 && - target->type == BL_MOB && //This bonus doesnt work against players. - (battle->check_undead(status->race,status->def_ele) || status->race==RC_DEMON) ) - damage += (skill*(int)(3+(sd->status.base_level+1)*0.05)); // submitted by orn - //damage += (skill * 3); - if( (skill = pc->checkskill(sd, RA_RANGERMAIN)) > 0 && (status->race == RC_BRUTE || status->race == RC_PLANT || status->race == RC_FISH) ) - damage += (skill * 5); - if( (skill = pc->checkskill(sd,NC_RESEARCHFE)) > 0 && (status->def_ele == ELE_FIRE || status->def_ele == ELE_EARTH) ) - damage += (skill * 10); - if( pc_ismadogear(sd) ) - damage += 20 + 20 * pc->checkskill(sd, NC_MADOLICENCE); - - if((skill = pc->checkskill(sd,HT_BEASTBANE)) > 0 && (status->race==RC_BRUTE || status->race==RC_INSECT) ) { - damage += (skill * 4); - if (sd->sc.data[SC_SPIRIT] && sd->sc.data[SC_SPIRIT]->val2 == SL_HUNTER) - damage += sd->status.str; - } - - if(type == 0) - weapon = sd->weapontype1; - else - weapon = sd->weapontype2; - switch(weapon) - { - case W_1HSWORD: - #ifdef RENEWAL - if((skill = pc->checkskill(sd,AM_AXEMASTERY)) > 0) - damage += (skill * 3); - #endif - case W_DAGGER: - if((skill = pc->checkskill(sd,SM_SWORD)) > 0) - damage += (skill * 4); - if((skill = pc->checkskill(sd,GN_TRAINING_SWORD)) > 0) - damage += skill * 10; - break; - case W_2HSWORD: - #ifdef RENEWAL - if((skill = pc->checkskill(sd,AM_AXEMASTERY)) > 0) - damage += (skill * 3); - #endif - if((skill = pc->checkskill(sd,SM_TWOHAND)) > 0) - damage += (skill * 4); - break; - case W_1HSPEAR: - case W_2HSPEAR: - if((skill = pc->checkskill(sd,KN_SPEARMASTERY)) > 0) { - if(!pc_isriding(sd)) - damage += (skill * 4); - else - damage += (skill * 5); - } - break; - case W_1HAXE: - case W_2HAXE: - if((skill = pc->checkskill(sd,AM_AXEMASTERY)) > 0) - damage += (skill * 3); - if((skill = pc->checkskill(sd,NC_TRAININGAXE)) > 0) - damage += (skill * 5); - break; - case W_MACE: - case W_2HMACE: - if((skill = pc->checkskill(sd,PR_MACEMASTERY)) > 0) - damage += (skill * 3); - if((skill = pc->checkskill(sd,NC_TRAININGAXE)) > 0) - damage += (skill * 5); - break; - case W_FIST: - if((skill = pc->checkskill(sd,TK_RUN)) > 0) - damage += (skill * 10); - // No break, fallthrough to Knuckles - case W_KNUCKLE: - if((skill = pc->checkskill(sd,MO_IRONHAND)) > 0) - damage += (skill * 3); - break; - case W_MUSICAL: - if((skill = pc->checkskill(sd,BA_MUSICALLESSON)) > 0) - damage += (skill * 3); - break; - case W_WHIP: - if((skill = pc->checkskill(sd,DC_DANCINGLESSON)) > 0) - damage += (skill * 3); - break; - case W_BOOK: - if((skill = pc->checkskill(sd,SA_ADVANCEDBOOK)) > 0) - damage += (skill * 3); - break; - case W_KATAR: - if((skill = pc->checkskill(sd,AS_KATAR)) > 0) - damage += (skill * 3); - break; - } - - return damage; -} -/*========================================== - * Calculates the standard damage of a normal attack assuming it hits, - * it calculates nothing extra fancy, is needed for magnum break's WATK_ELEMENT bonus. [Skotlex] - *------------------------------------------ - * Pass damage2 as NULL to not calc it. - * Flag values: - * &1: Critical hit - * &2: Arrow attack - * &4: Skill is Magic Crasher - * &8: Skip target size adjustment (Extremity Fist?) - *&16: Arrow attack but BOW, REVOLVER, RIFLE, SHOTGUN, GATLING or GRENADE type weapon not equipped (i.e. shuriken, kunai and venom knives not affected by DEX) - */ -int battle_calc_base_damage(struct status_data *status, struct weapon_atk *wa, struct status_change *sc, unsigned short t_size, struct map_session_data *sd, int flag) { - unsigned int atkmin=0, atkmax=0; - short type = 0; - int damage = 0; - - if (!sd) - { //Mobs/Pets - if(flag&4) - { - atkmin = status->matk_min; - atkmax = status->matk_max; - } else { - atkmin = wa->atk; - atkmax = wa->atk2; - } - if (atkmin > atkmax) - atkmin = atkmax; - } else { //PCs - atkmax = wa->atk; - type = (wa == &status->lhw)?EQI_HAND_L:EQI_HAND_R; - - if (!(flag&1) || (flag&2)) - { //Normal attacks - atkmin = status->dex; - - if (sd->equip_index[type] >= 0 && sd->inventory_data[sd->equip_index[type]]) - atkmin = atkmin*(80 + sd->inventory_data[sd->equip_index[type]]->wlv*20)/100; - - if (atkmin > atkmax) - atkmin = atkmax; - - if(flag&2 && !(flag&16)) - { //Bows - atkmin = atkmin*atkmax/100; - if (atkmin > atkmax) - atkmax = atkmin; - } - } - } - - if (sc && sc->data[SC_MAXIMIZEPOWER]) - atkmin = atkmax; - - //Weapon Damage calculation - if (!(flag&1)) - damage = (atkmax>atkmin? rnd()%(atkmax-atkmin):0)+atkmin; - else - damage = atkmax; - - if (sd) - { - //rodatazone says the range is 0~arrow_atk-1 for non crit - if (flag&2 && sd->bonus.arrow_atk) - damage += ( (flag&1) ? sd->bonus.arrow_atk : rnd()%sd->bonus.arrow_atk ); - - //SizeFix only for players - if (!(sd->special_state.no_sizefix || (flag&8))) - damage = damage * ( type == EQI_HAND_L ? sd->left_weapon.atkmods[t_size] : sd->right_weapon.atkmods[t_size] ) / 100; - } - - //Finally, add baseatk - if(flag&4) - damage += status->matk_min; - else - damage += status->batk; - - //rodatazone says that Overrefine bonuses are part of baseatk - //Here we also apply the weapon_atk_rate bonus so it is correctly applied on left/right hands. - if(sd) { - if (type == EQI_HAND_L) { - if(sd->left_weapon.overrefine) - damage += rnd()%sd->left_weapon.overrefine+1; - if (sd->weapon_atk_rate[sd->weapontype2]) - damage += damage * sd->weapon_atk_rate[sd->weapontype2] / 100; - } else { //Right hand - if(sd->right_weapon.overrefine) - damage += rnd()%sd->right_weapon.overrefine+1; - if (sd->weapon_atk_rate[sd->weapontype1]) - damage += damage * sd->weapon_atk_rate[sd->weapontype1] / 100; - } - } - return damage; -} - -/*========================================== - * Consumes ammo for the given skill. - *------------------------------------------*/ -void battle_consume_ammo(TBL_PC*sd, int skill_id, int lv) { - int qty=1; - if (!battle_config.arrow_decrement) - return; - - if (skill) { - qty = skill->get_ammo_qty(skill_id, lv); - if (!qty) qty = 1; - } - - if(sd->equip_index[EQI_AMMO]>=0) //Qty check should have been done in skill_check_condition - pc->delitem(sd,sd->equip_index[EQI_AMMO],qty,0,1,LOG_TYPE_CONSUME); - - sd->state.arrow_atk = 0; -} -//Skill Range Criteria -int battle_range_type(struct block_list *src, struct block_list *target, uint16 skill_id, uint16 skill_lv) { - if (battle_config.skillrange_by_distance && - (src->type&battle_config.skillrange_by_distance) - ) { //based on distance between src/target [Skotlex] - if (check_distance_bl(src, target, 5)) - return BF_SHORT; - return BF_LONG; - } - //based on used skill's range - if (skill->get_range2(src, skill_id, skill_lv) < 5) - return BF_SHORT; - return BF_LONG; -} -int battle_adjust_skill_damage(int m, unsigned short skill_id) { - - if( map[m].skill_count ) { - int i; - ARR_FIND(0, map[m].skill_count, i, map[m].skills[i]->skill_id == skill_id ); - - if( i < map[m].skill_count ) { - return map[m].skills[i]->modifier; - } - - } - - return 0; -} -int battle_blewcount_bonus(struct map_session_data *sd, uint16 skill_id) { - int i; - if (!sd->skillblown[0].id) - return 0; - //Apply the bonus blewcount. [Skotlex] - for (i = 0; i < ARRAYLENGTH(sd->skillblown) && sd->skillblown[i].id; i++) { - if (sd->skillblown[i].id == skill_id) - return sd->skillblown[i].val; - } - return 0; -} - -//For quick div adjustment. -#define damage_div_fix(dmg, div) { if (div > 1) (dmg)*=div; else if (div < 0) (div)*=-1; } -/*========================================== - * battle_calc_weapon_attack (by Skotlex) - *------------------------------------------*/ -struct Damage battle_calc_weapon_attack(struct block_list *src,struct block_list *target,uint16 skill_id,uint16 skill_lv,int wflag) -{ - unsigned int skillratio = 100; //Skill dmg modifiers. - short temp=0; - short s_ele, s_ele_, t_class; - int i, nk; - bool n_ele = false; // non-elemental - - struct map_session_data *sd, *tsd; - struct Damage wd; - struct status_change *sc = status_get_sc(src); - struct status_change *tsc = status_get_sc(target); - struct status_data *sstatus = status_get_status_data(src); - struct status_data *tstatus = status_get_status_data(target); - struct { - unsigned hit : 1; //the attack Hit? (not a miss) - unsigned cri : 1; //Critical hit - unsigned idef : 1; //Ignore defense - unsigned idef2 : 1; //Ignore defense (left weapon) - unsigned pdef : 2; //Pierces defense (Investigate/Ice Pick) - unsigned pdef2 : 2; //1: Use def+def2/100, 2: Use def+def2/50 - unsigned infdef : 1; //Infinite defense (plants) - unsigned arrow : 1; //Attack is arrow-based - unsigned rh : 1; //Attack considers right hand (wd.damage) - unsigned lh : 1; //Attack considers left hand (wd.damage2) - unsigned weapon : 1; //It's a weapon attack (consider VVS, and all that) - } flag; - - memset(&wd,0,sizeof(wd)); - memset(&flag,0,sizeof(flag)); - - if(src==NULL || target==NULL) - { - nullpo_info(NLP_MARK); - return wd; - } - //Initial flag - flag.rh=1; - flag.weapon=1; - flag.infdef=(tstatus->mode&MD_PLANT && skill_id != RA_CLUSTERBOMB -#ifdef RENEWAL - && skill_id != HT_FREEZINGTRAP -#endif - ?1:0); - if( target->type == BL_SKILL){ - TBL_SKILL *su = (TBL_SKILL*)target; - if( su->group && (su->group->skill_id == WM_REVERBERATION || su->group->skill_id == WM_POEMOFNETHERWORLD) ) - flag.infdef = 1; - } - - //Initial Values - wd.type=0; //Normal attack - wd.div_=skill_id?skill->get_num(skill_id,skill_lv):1; - wd.amotion=(skill_id && skill->get_inf(skill_id)&INF_GROUND_SKILL)?0:sstatus->amotion; //Amotion should be 0 for ground skills. - if(skill_id == KN_AUTOCOUNTER) - wd.amotion >>= 1; - wd.dmotion=tstatus->dmotion; - wd.blewcount=skill->get_blewcount(skill_id,skill_lv); - wd.flag = BF_WEAPON; //Initial Flag - wd.flag |= (skill_id||wflag)?BF_SKILL:BF_NORMAL; // Baphomet card's splash damage is counted as a skill. [Inkfish] - wd.dmg_lv=ATK_DEF; //This assumption simplifies the assignation later - nk = skill->get_nk(skill_id); - if( !skill_id && wflag ) //If flag, this is splash damage from Baphomet Card and it always hits. - nk |= NK_NO_CARDFIX_ATK|NK_IGNORE_FLEE; - flag.hit = nk&NK_IGNORE_FLEE?1:0; - flag.idef = flag.idef2 = nk&NK_IGNORE_DEF?1:0; - - if (sc && !sc->count) - sc = NULL; //Skip checking as there are no status changes active. - if (tsc && !tsc->count) - tsc = NULL; //Skip checking as there are no status changes active. - - sd = BL_CAST(BL_PC, src); - tsd = BL_CAST(BL_PC, target); - - if(sd) - wd.blewcount += battle->blewcount_bonus(sd, skill_id); - - //Set miscellaneous data that needs be filled regardless of hit/miss - if( - (sd && sd->state.arrow_atk) || - (!sd && ((skill_id && skill->get_ammotype(skill_id)) || sstatus->rhw.range>3)) - ) - flag.arrow = 1; - - if(skill_id) { - wd.flag |= battle->range_type(src, target, skill_id, skill_lv); - switch(skill_id) { - case MO_FINGEROFFENSIVE: - if(sd) { - if (battle_config.finger_offensive_type) - wd.div_ = 1; - else - wd.div_ = sd->spiritball_old; - } - break; - case HT_PHANTASMIC: - //Since these do not consume ammo, they need to be explicitly set as arrow attacks. - flag.arrow = 1; - break; -#ifndef RENEWAL - case PA_SHIELDCHAIN: - case CR_SHIELDBOOMERANG: -#endif - case LG_SHIELDPRESS: - case LG_EARTHDRIVE: - flag.weapon = 0; - break; - - case KN_PIERCE: - case ML_PIERCE: - wd.div_= (wd.div_>0?tstatus->size+1:-(tstatus->size+1)); - break; - - case TF_DOUBLE: //For NPC used skill. - case GS_CHAINACTION: - wd.type = 0x08; - break; - - case GS_GROUNDDRIFT: - case KN_SPEARSTAB: - case KN_BOWLINGBASH: - case MS_BOWLINGBASH: - case MO_BALKYOUNG: - case TK_TURNKICK: - wd.blewcount=0; - break; - - case KN_AUTOCOUNTER: - wd.flag=(wd.flag&~BF_SKILLMASK)|BF_NORMAL; - break; - - case NPC_CRITICALSLASH: - case LG_PINPOINTATTACK: - flag.cri = 1; //Always critical skill. - break; - - case LK_SPIRALPIERCE: - if (!sd) wd.flag=(wd.flag&~(BF_RANGEMASK|BF_WEAPONMASK))|BF_LONG|BF_MISC; - break; - } - } else //Range for normal attacks. - wd.flag |= flag.arrow?BF_LONG:BF_SHORT; - - if ( (!skill_id || skill_id == PA_SACRIFICE) && tstatus->flee2 && rnd()%1000 < tstatus->flee2 ) - { //Check for Lucky Dodge - wd.type=0x0b; - wd.dmg_lv=ATK_LUCKY; - if (wd.div_ < 0) wd.div_*=-1; - return wd; - } - - t_class = status_get_class(target); - s_ele = s_ele_ = skill->get_ele(skill_id, skill_lv); - if( !skill_id || s_ele == -1 ) - { //Take weapon's element - s_ele = sstatus->rhw.ele; - s_ele_ = sstatus->lhw.ele; - if( sd ){ //Summoning 10 talisman will endow your weapon. - ARR_FIND(1, 6, i, sd->talisman[i] >= 10); - if( i < 5 ) s_ele = s_ele_ = i; - } - if( flag.arrow && sd && sd->bonus.arrow_ele ) - s_ele = sd->bonus.arrow_ele; - if( battle_config.attack_attr_none&src->type ) - n_ele = true; //Weapon's element is "not elemental" - } - else if( s_ele == -2 ) //Use enchantment's element - s_ele = s_ele_ = status_get_attack_sc_element(src,sc); - else if( s_ele == -3 ) //Use random element - s_ele = s_ele_ = rnd()%ELE_MAX; - switch( skill_id ) - { - case GS_GROUNDDRIFT: - s_ele = s_ele_ = wflag; //element comes in flag. - break; - case LK_SPIRALPIERCE: - if (!sd) n_ele = false; //forced neutral for monsters - break; - } - - if (!(nk & NK_NO_ELEFIX) && !n_ele) - if (src->type == BL_HOM) - n_ele = true; //skill is "not elemental" - if (sc && sc->data[SC_GOLDENE_FERSE] && ((!skill_id && (rnd() % 100 < sc->data[SC_GOLDENE_FERSE]->val4)) || skill_id == MH_STAHL_HORN)) { - s_ele = s_ele_ = ELE_HOLY; - n_ele = false; - } - - if(!skill_id) - { //Skills ALWAYS use ONLY your right-hand weapon (tested on Aegis 10.2) - if (sd && sd->weapontype1 == 0 && sd->weapontype2 > 0) - { - flag.rh=0; - flag.lh=1; - } - if (sstatus->lhw.atk) - flag.lh=1; - } - - if( sd && !skill_id ) { //Check for double attack. - if( ( ( skill_lv = pc->checkskill(sd,TF_DOUBLE) ) > 0 && sd->weapontype1 == W_DAGGER ) - || ( sd->bonus.double_rate > 0 && sd->weapontype1 != W_FIST ) //Will fail bare-handed - || ( sc && sc->data[SC_KAGEMUSYA] && sd->weapontype1 != W_FIST )) // Need confirmation - { //Success chance is not added, the higher one is used [Skotlex] - if( rnd()%100 < ( 5*skill_lv > sd->bonus.double_rate ? 5*skill_lv : sc && sc->data[SC_KAGEMUSYA]?sc->data[SC_KAGEMUSYA]->val1*3:sd->bonus.double_rate ) ) - { - wd.div_ = skill->get_num(TF_DOUBLE,skill_lv?skill_lv:1); - wd.type = 0x08; - } - } - else if( sd->weapontype1 == W_REVOLVER && (skill_lv = pc->checkskill(sd,GS_CHAINACTION)) > 0 && rnd()%100 < 5*skill_lv ) - { - wd.div_ = skill->get_num(GS_CHAINACTION,skill_lv); - wd.type = 0x08; - } - else if(sc && sc->data[SC_FEARBREEZE] && sd->weapontype1==W_BOW - && (i = sd->equip_index[EQI_AMMO]) >= 0 && sd->inventory_data[i] && sd->status.inventory[i].amount > 1){ - int chance = rand()%100; - wd.type = 0x08; - switch(sc->data[SC_FEARBREEZE]->val1){ - case 5: - if( chance < 3){// 3 % chance to attack 5 times. - wd.div_ = 5; - break; - } - case 4: - if( chance < 7){// 6 % chance to attack 4 times. - wd.div_ = 4; - break; - } - case 3: - if( chance < 10){// 9 % chance to attack 3 times. - wd.div_ = 3; - break; - } - case 2: - case 1: - if( chance < 13){// 12 % chance to attack 2 times. - wd.div_ = 2; - break; - } - } - wd.div_ = min(wd.div_,sd->status.inventory[i].amount); - sc->data[SC_FEARBREEZE]->val4 = wd.div_-1; - } - } - - //Check for critical - if( !flag.cri && !(wd.type&0x08) && sstatus->cri && - (!skill_id || - skill_id == KN_AUTOCOUNTER || - skill_id == SN_SHARPSHOOTING || skill_id == MA_SHARPSHOOTING || - skill_id == NJ_KIRIKAGE)) - { - short cri = sstatus->cri; - if (sd) - { - cri+= sd->critaddrace[tstatus->race]; - if(flag.arrow) - cri += sd->bonus.arrow_cri; - } - if( sc && sc->data[SC_CAMOUFLAGE] ) - cri += 10 * (10-sc->data[SC_CAMOUFLAGE]->val4); - //The official equation is *2, but that only applies when sd's do critical. - //Therefore, we use the old value 3 on cases when an sd gets attacked by a mob - cri -= tstatus->luk*(!sd&&tsd?3:2); - - if( tsc && tsc->data[SC_SLEEP] ) { - cri <<= 1; - } - switch (skill_id) { - case KN_AUTOCOUNTER: - if(battle_config.auto_counter_type && - (battle_config.auto_counter_type&src->type)) - flag.cri = 1; - else - cri <<= 1; - break; - case SN_SHARPSHOOTING: - case MA_SHARPSHOOTING: - cri += 200; - break; - case NJ_KIRIKAGE: - cri += 250 + 50*skill_lv; - break; - } - if(tsd && tsd->bonus.critical_def) - cri = cri * ( 100 - tsd->bonus.critical_def ) / 100; - if (rnd()%1000 < cri) - flag.cri = 1; - } - if (flag.cri) { - wd.type = 0x0a; -#ifdef RENEWAL - flag.hit = 1; -#else - flag.idef = flag.idef2 = flag.hit = 1; -#endif - } else { //Check for Perfect Hit - if(sd && sd->bonus.perfect_hit > 0 && rnd()%100 < sd->bonus.perfect_hit) - flag.hit = 1; - if (sc && sc->data[SC_FUSION]) { - flag.hit = 1; //SG_FUSION always hit [Komurka] - flag.idef = flag.idef2 = 1; //def ignore [Komurka] - } - if( !flag.hit ) - switch(skill_id) - { - case AS_SPLASHER: - if( !wflag ) // Always hits the one exploding. - flag.hit = 1; - break; - case CR_SHIELDBOOMERANG: - if( sc && sc->data[SC_SPIRIT] && sc->data[SC_SPIRIT]->val2 == SL_CRUSADER ) - flag.hit = 1; - break; - } - if (tsc && !flag.hit && tsc->opt1 && tsc->opt1 != OPT1_STONEWAIT && tsc->opt1 != OPT1_BURNING) - flag.hit = 1; - } - - if (!flag.hit) - { //Hit/Flee calculation - short - flee = tstatus->flee, -#ifdef RENEWAL - hitrate = 0; //Default hitrate -#else - hitrate = 80; //Default hitrate -#endif - - if(battle_config.agi_penalty_type && battle_config.agi_penalty_target&target->type) { - unsigned char attacker_count; //256 max targets should be a sane max - attacker_count = unit_counttargeted(target); - if(attacker_count >= battle_config.agi_penalty_count) { - if (battle_config.agi_penalty_type == 1) - flee = (flee * (100 - (attacker_count - (battle_config.agi_penalty_count - 1))*battle_config.agi_penalty_num))/100; - else //asume type 2: absolute reduction - flee -= (attacker_count - (battle_config.agi_penalty_count - 1))*battle_config.agi_penalty_num; - if(flee < 1) flee = 1; - } - } - - hitrate+= sstatus->hit - flee; - - if(wd.flag&BF_LONG && !skill_id && //Fogwall's hit penalty is only for normal ranged attacks. - tsc && tsc->data[SC_FOGWALL]) - hitrate -= 50; - - if(sd && flag.arrow) - hitrate += sd->bonus.arrow_hit; -#ifdef RENEWAL - if( sd ) //in Renewal hit bonus from Vultures Eye is not anymore shown in status window - hitrate += pc->checkskill(sd,AC_VULTURE); -#endif - if(skill_id) - switch(skill_id) - { //Hit skill modifiers - //It is proven that bonus is applied on final hitrate, not hit. - case SM_BASH: - case MS_BASH: - hitrate += hitrate * 5 * skill_lv / 100; - break; - case MS_MAGNUM: - case SM_MAGNUM: - hitrate += hitrate * 10 * skill_lv / 100; - break; - case KN_AUTOCOUNTER: - case PA_SHIELDCHAIN: - case NPC_WATERATTACK: - case NPC_GROUNDATTACK: - case NPC_FIREATTACK: - case NPC_WINDATTACK: - case NPC_POISONATTACK: - case NPC_HOLYATTACK: - case NPC_DARKNESSATTACK: - case NPC_UNDEADATTACK: - case NPC_TELEKINESISATTACK: - case NPC_BLEEDING: - hitrate += hitrate * 20 / 100; - break; - case KN_PIERCE: - case ML_PIERCE: - hitrate += hitrate * 5 * skill_lv / 100; - break; - case AS_SONICBLOW: - if(sd && pc->checkskill(sd,AS_SONICACCEL)>0) - hitrate += hitrate * 50 / 100; - break; - case MC_CARTREVOLUTION: - case GN_CART_TORNADO: - case GN_CARTCANNON: - if( sd && pc->checkskill(sd, GN_REMODELING_CART) ) - hitrate += pc->checkskill(sd, GN_REMODELING_CART) * 4; - break; - case GC_VENOMPRESSURE: - hitrate += 10 + 4 * skill_lv; - break; - } - - if( sd ) { - // Weaponry Research hidden bonus - if ((temp = pc->checkskill(sd,BS_WEAPONRESEARCH)) > 0) - hitrate += hitrate * ( 2 * temp ) / 100; - - if( (sd->status.weapon == W_1HSWORD || sd->status.weapon == W_DAGGER) && - (temp = pc->checkskill(sd, GN_TRAINING_SWORD))>0 ) - hitrate += 3 * temp; - } - - hitrate = cap_value(hitrate, battle_config.min_hitrate, battle_config.max_hitrate); - - if(rnd()%100 >= hitrate) - wd.dmg_lv = ATK_FLEE; - else - flag.hit = 1; - } //End hit/miss calculation - - if (flag.hit && !flag.infdef) //No need to do the math for plants - { //Hitting attack - -//Assuming that 99% of the cases we will not need to check for the flag.rh... we don't. -//ATK_RATE scales the damage. 100 = no change. 50 is halved, 200 is doubled, etc -#define ATK_RATE( a ) { wd.damage= wd.damage*(a)/100 ; if(flag.lh) wd.damage2= wd.damage2*(a)/100; } -#define ATK_RATE2( a , b ) { wd.damage= wd.damage*(a)/100 ; if(flag.lh) wd.damage2= wd.damage2*(b)/100; } -#define ATK_RATER(a){ wd.damage = wd.damage*(a)/100;} -#define ATK_RATEL(a){ wd.damage2 = wd.damage2*(a)/100;} -//Adds dmg%. 100 = +100% (double) damage. 10 = +10% damage -#define ATK_ADDRATE( a ) { wd.damage+= wd.damage*(a)/100 ; if(flag.lh) wd.damage2+= wd.damage2*(a)/100; } -#define ATK_ADDRATE2( a , b ) { wd.damage+= wd.damage*(a)/100 ; if(flag.lh) wd.damage2+= wd.damage2*(b)/100; } -//Adds an absolute value to damage. 100 = +100 damage -#define ATK_ADD( a ) { wd.damage+= a; if (flag.lh) wd.damage2+= a; } -#define ATK_ADD2( a , b ) { wd.damage+= a; if (flag.lh) wd.damage2+= b; } - - switch (skill_id) - { //Calc base damage according to skill - case PA_SACRIFICE: - wd.damage = sstatus->max_hp* 9/100; - wd.damage2 = 0; - break; -#ifndef RENEWAL - case NJ_ISSEN: - wd.damage = 40*sstatus->str +skill_lv*(sstatus->hp/10 + 35); - wd.damage2 = 0; - break; - case LK_SPIRALPIERCE: - case ML_SPIRALPIERCE: - if (sd) { - short index = sd->equip_index[EQI_HAND_R]; - - if (index >= 0 && - sd->inventory_data[index] && - sd->inventory_data[index]->type == IT_WEAPON) - wd.damage = sd->inventory_data[index]->weight*8/100; //80% of weight - } else - wd.damage = sstatus->rhw.atk2*8/10; //Else use Atk2 - - ATK_ADDRATE(50*skill_lv); //Skill modifier applies to weight only. - i = sstatus->str/10; - i*=i; - ATK_ADD(i); //Add str bonus. - switch (tstatus->size) { //Size-fix. Is this modified by weapon perfection? - case SZ_SMALL: //Small: 125% - ATK_RATE(125); - break; - //case SZ_MEDIUM: //Medium: 100% - case SZ_BIG: //Large: 75% - ATK_RATE(75); - break; - } - break; -#endif - case CR_SHIELDBOOMERANG: - case PA_SHIELDCHAIN: - case LG_SHIELDPRESS: - case LG_EARTHDRIVE: - wd.damage = sstatus->batk; - if (sd) { - short index = sd->equip_index[EQI_HAND_L]; - - if (index >= 0 && - sd->inventory_data[index] && - sd->inventory_data[index]->type == IT_ARMOR) - ATK_ADD(sd->inventory_data[index]->weight/10); - } else - ATK_ADD(sstatus->rhw.atk2); //Else use Atk2 - break; - case HFLI_SBR44: //[orn] - if(src->type == BL_HOM) { - wd.damage = ((TBL_HOM*)src)->homunculus.intimacy ; - break; - } - default: - { - i = (flag.cri?1:0)| - (flag.arrow?2:0)| - (skill_id == HW_MAGICCRASHER?4:0)| - (!skill_id && sc && sc->data[SC_CHANGE]?4:0)| - (skill_id == MO_EXTREMITYFIST?8:0)| - (sc && sc->data[SC_WEAPONPERFECTION]?8:0); - if (flag.arrow && sd) - switch(sd->status.weapon) { - case W_BOW: - case W_REVOLVER: - case W_GATLING: - case W_SHOTGUN: - case W_GRENADE: - break; - default: - i |= 16; // for ex. shuriken must not be influenced by DEX - } - wd.damage = battle->calc_base_damage(sstatus, &sstatus->rhw, sc, tstatus->size, sd, i); - if (flag.lh) - wd.damage2 = battle->calc_base_damage(sstatus, &sstatus->lhw, sc, tstatus->size, sd, i); - - if (nk&NK_SPLASHSPLIT){ // Divide ATK among targets - if(wflag>0) - wd.damage/= wflag; - else - ShowError("0 enemies targeted by %d:%s, divide per 0 avoided!\n", skill_id, skill->get_name(skill_id)); - } - - //Add any bonuses that modify the base baseatk+watk (pre-skills) - if(sd) { - if (sd->bonus.atk_rate) - ATK_ADDRATE(sd->bonus.atk_rate); - - if(flag.cri && sd->bonus.crit_atk_rate) - ATK_ADDRATE(sd->bonus.crit_atk_rate); - - if(sd->status.party_id && (temp=pc->checkskill(sd,TK_POWER)) > 0){ - if( (i = party_foreachsamemap(party->sub_count, sd, 0)) > 1 ) // exclude the player himself [Inkfish] - ATK_ADDRATE(2*temp*i); - } - } - break; - } //End default case - } //End switch(skill_id) - - //Skill damage modifiers that stack linearly - if(sc && skill_id != PA_SACRIFICE) - { - if(sc->data[SC_OVERTHRUST]) - skillratio += sc->data[SC_OVERTHRUST]->val3; - if(sc->data[SC_MAXOVERTHRUST]) - skillratio += sc->data[SC_MAXOVERTHRUST]->val2; - if (sc->data[SC_BERSERK] || sc->data[SC_SATURDAYNIGHTFEVER] || sc->data[SC__BLOODYLUST]) - skillratio += 100; - if(sc->data[SC_ZENKAI] && sstatus->rhw.ele == sc->data[SC_ZENKAI]->val2 ) - skillratio += sc->data[SC_ZENKAI]->val1 * 2; - } - if( !skill_id ) - { - ATK_RATE(skillratio); - } - else - { + break; + case BF_WEAPON: switch( skill_id ) { case SM_BASH: case MS_BASH: - skillratio += 30*skill_lv; + skillratio += 30 * skill_lv; break; case SM_MAGNUM: case MS_MAGNUM: - skillratio += 20*skill_lv; + skillratio += 20 * skill_lv; break; case MC_MAMMONITE: - skillratio += 50*skill_lv; + skillratio += 50 * skill_lv; break; case HT_POWER: - skillratio += -50+8*sstatus->str; + skillratio += -50 + 8 * status_get_str(src); break; case AC_DOUBLE: case MA_DOUBLE: - skillratio += 10*(skill_lv-1); + skillratio += 10 * (skill_lv-1); break; case AC_SHOWER: case MA_SHOWER: #ifdef RENEWAL - skillratio += 50+10*skill_lv; + skillratio += 50 + 10 * skill_lv; #else - skillratio += -25+5*skill_lv; + skillratio += -25 + 5 * skill_lv; #endif break; case AC_CHARGEARROW: case MA_CHARGEARROW: skillratio += 50; break; -#ifndef RENEWAL + #ifndef RENEWAL case HT_FREEZINGTRAP: case MA_FREEZINGTRAP: - skillratio += -50+10*skill_lv; + skillratio += -50 + 10 * skill_lv; break; -#endif + #endif case KN_PIERCE: case ML_PIERCE: - skillratio += 10*skill_lv; + skillratio += 10 * skill_lv; break; case MER_CRASH: - skillratio += 10*skill_lv; + skillratio += 10 * skill_lv; break; case KN_SPEARSTAB: - skillratio += 15*skill_lv; + skillratio += 15 * skill_lv; break; case KN_SPEARBOOMERANG: skillratio += 50*skill_lv; @@ -2228,41 +1760,41 @@ struct Damage battle_calc_weapon_attack(struct block_list *src,struct block_list case KN_BRANDISHSPEAR: case ML_BRANDISH: { - int ratio = 100+20*skill_lv; - skillratio += ratio-100; - if(skill_lv>3 && wflag==1) skillratio += ratio/2; - if(skill_lv>6 && wflag==1) skillratio += ratio/4; - if(skill_lv>9 && wflag==1) skillratio += ratio/8; - if(skill_lv>6 && wflag==2) skillratio += ratio/2; - if(skill_lv>9 && wflag==2) skillratio += ratio/4; - if(skill_lv>9 && wflag==3) skillratio += ratio/2; + int ratio = 100 + 20 * skill_lv; + skillratio += ratio - 100; + if(skill_lv>3 && flag==1) skillratio += ratio / 2; + if(skill_lv>6 && flag==1) skillratio += ratio / 4; + if(skill_lv>9 && flag==1) skillratio += ratio / 8; + if(skill_lv>6 && flag==2) skillratio += ratio / 2; + if(skill_lv>9 && flag==2) skillratio += ratio / 4; + if(skill_lv>9 && flag==3) skillratio += ratio / 2; break; } case KN_BOWLINGBASH: case MS_BOWLINGBASH: - skillratio+= 40*skill_lv; + skillratio+= 40 * skill_lv; break; case AS_GRIMTOOTH: - skillratio += 20*skill_lv; + skillratio += 20 * skill_lv; break; case AS_POISONREACT: - skillratio += 30*skill_lv; + skillratio += 30 * skill_lv; break; case AS_SONICBLOW: - skillratio += -50+5*skill_lv; + skillratio += -50 + 5 * skill_lv; break; case TF_SPRINKLESAND: skillratio += 30; break; case MC_CARTREVOLUTION: skillratio += 50; - if(sd && sd->cart_weight) - skillratio += 100*sd->cart_weight/sd->cart_weight_max; // +1% every 1% weight + if( sd && sd->cart_weight ) + skillratio += 100 * sd->cart_weight / sd->cart_weight_max; // +1% every 1% weight else if (!sd) skillratio += 100; //Max damage for non players. break; case NPC_RANDOMATTACK: - skillratio += 100*skill_lv; + skillratio += 100 * skill_lv; break; case NPC_WATERATTACK: case NPC_GROUNDATTACK: @@ -2281,30 +1813,30 @@ struct Damage battle_calc_weapon_attack(struct block_list *src,struct block_list case NPC_THUNDERBREATH: case NPC_HELLJUDGEMENT: case NPC_PULSESTRIKE: - skillratio += 100*(skill_lv-1); + skillratio += 100 * (skill_lv-1); break; case RG_BACKSTAP: - if(sd && sd->status.weapon == W_BOW && battle_config.backstab_bow_penalty) - skillratio += (200+40*skill_lv)/2; + if( sd && sd->status.weapon == W_BOW && battle_config.backstab_bow_penalty ) + skillratio += (200 + 40 * skill_lv) / 2; else - skillratio += 200+40*skill_lv; + skillratio += 200 + 40 * skill_lv; break; case RG_RAID: - skillratio += 40*skill_lv; + skillratio += 40 * skill_lv; break; case RG_INTIMIDATE: - skillratio += 30*skill_lv; + skillratio += 30 * skill_lv; break; case CR_SHIELDCHARGE: - skillratio += 20*skill_lv; + skillratio += 20 * skill_lv; break; case CR_SHIELDBOOMERANG: - skillratio += 30*skill_lv; + skillratio += 30 * skill_lv; break; case NPC_DARKCROSS: case CR_HOLYCROSS: { - int ratio = 35*skill_lv; + int ratio = 35 * skill_lv; #ifdef RENEWAL if(sd && sd->status.weapon == W_2HSPEAR) ratio *= 2; @@ -2313,18 +1845,18 @@ struct Damage battle_calc_weapon_attack(struct block_list *src,struct block_list break; } case AM_DEMONSTRATION: - skillratio += 20*skill_lv; + skillratio += 20 * skill_lv; break; case AM_ACIDTERROR: - skillratio += 40*skill_lv; + skillratio += 40 * skill_lv; break; case MO_FINGEROFFENSIVE: skillratio+= 50 * skill_lv; break; case MO_INVESTIGATE: - skillratio += 75*skill_lv; - flag.pdef = flag.pdef2 = 2; + skillratio += 75 * skill_lv; break; + #ifndef RENEWAL case MO_EXTREMITYFIST: { //Overflow check. [Skotlex] unsigned int ratio = skillratio + 100*(8 + sstatus->sp/10); @@ -2333,76 +1865,63 @@ struct Damage battle_calc_weapon_attack(struct block_list *src,struct block_list skillratio = (unsigned short)ratio; } break; + #endif case MO_TRIPLEATTACK: - skillratio += 20*skill_lv; + skillratio += 20 * skill_lv; break; case MO_CHAINCOMBO: - skillratio += 50+50*skill_lv; + skillratio += 50 + 50 * skill_lv; break; case MO_COMBOFINISH: - skillratio += 140+60*skill_lv; + skillratio += 140 + 60 * skill_lv; break; case BA_MUSICALSTRIKE: case DC_THROWARROW: - skillratio += 25+25*skill_lv; + skillratio += 25 + 25 * skill_lv; break; case CH_TIGERFIST: - skillratio += 100*skill_lv-60; + skillratio += 100 * skill_lv - 60; break; case CH_CHAINCRUSH: - skillratio += 300+100*skill_lv; + skillratio += 300 + 100 * skill_lv; break; case CH_PALMSTRIKE: - skillratio += 100+100*skill_lv; + skillratio += 100 + 100 * skill_lv; break; case LK_HEADCRUSH: - skillratio += 40*skill_lv; + skillratio += 40 * skill_lv; break; case LK_JOINTBEAT: - i = 10*skill_lv-50; + i = 10 * skill_lv - 50; // Although not clear, it's being assumed that the 2x damage is only for the break neck ailment. - if (wflag&BREAK_NECK) i*=2; + if (flag&BREAK_NECK) i*=2; skillratio += i; break; -#ifdef RENEWAL - case LK_SPIRALPIERCE: - case ML_SPIRALPIERCE: - {// Formula: Floor[Floor(Weapon Weight/2)*skill level + ATK ]*(100%+50%*s.lvl) * 5 multi-hits - short index = sd?sd->equip_index[EQI_HAND_R]:0; - int weight = 0; - - if (sd && index >= 0 && - sd->inventory_data[index] && - sd->inventory_data[index]->type == IT_WEAPON) - weight = sd->inventory_data[index]->weight/20; - ATK_ADD(weight * skill_lv) - skillratio += 50*skill_lv; - } - break; -#endif case ASC_METEORASSAULT: - skillratio += 40*skill_lv-60; + skillratio += 40 * skill_lv - 60; break; case SN_SHARPSHOOTING: case MA_SHARPSHOOTING: - skillratio += 100+50*skill_lv; + skillratio += 100 + 50 * skill_lv; break; case CG_ARROWVULCAN: - skillratio += 100+100*skill_lv; + skillratio += 100 + 100 * skill_lv; break; case AS_SPLASHER: - skillratio += 400+50*skill_lv; + skillratio += 400 + 50 * skill_lv; if(sd) skillratio += 20 * pc->checkskill(sd,AS_POISONREACT); break; + #ifndef RENEWAL case ASC_BREAKER: skillratio += 100*skill_lv-100; break; + #endif case PA_SACRIFICE: - skillratio += 10*skill_lv-10; + skillratio += 10 * skill_lv - 10; break; case PA_SHIELDCHAIN: - skillratio += 30*skill_lv; + skillratio += 30 * skill_lv; break; case WS_CARTTERMINATION: i = 10 * (16 - skill_lv); @@ -2414,30 +1933,30 @@ struct Damage battle_calc_weapon_attack(struct block_list *src,struct block_list skillratio += 80000 / i - 100; break; case TK_DOWNKICK: - skillratio += 60 + 20*skill_lv; + skillratio += 60 + 20 * skill_lv; break; case TK_STORMKICK: - skillratio += 60 + 20*skill_lv; + skillratio += 60 + 20 * skill_lv; break; case TK_TURNKICK: - skillratio += 90 + 30*skill_lv; + skillratio += 90 + 30 * skill_lv; break; case TK_COUNTER: - skillratio += 90 + 30*skill_lv; + skillratio += 90 + 30 * skill_lv; break; case TK_JUMPKICK: skillratio += -70 + 10*skill_lv; - if (sc && sc->data[SC_COMBO] && sc->data[SC_COMBO]->val1 == skill_id) - skillratio += 10*status_get_lv(src)/3; //Tumble bonus - if (wflag) + if (sc && sc->data[SC_COMBOATTACK] && sc->data[SC_COMBOATTACK]->val1 == skill_id) + skillratio += 10 * status_get_lv(src) / 3; //Tumble bonus + if (flag) { - skillratio += 10*status_get_lv(src)/3; //Running bonus (TODO: What is the real bonus?) - if( sc && sc->data[SC_SPURT] ) // Spurt bonus + skillratio += 10 * status_get_lv(src) / 3; //Running bonus (TODO: What is the real bonus?) + if( sc && sc->data[SC_STRUP] ) // Spurt bonus skillratio *= 2; } break; case GS_TRIPLEACTION: - skillratio += 50*skill_lv; + skillratio += 50 * skill_lv; break; case GS_BULLSEYE: //Only works well against brute/demihumans non bosses. @@ -2446,55 +1965,47 @@ struct Damage battle_calc_weapon_attack(struct block_list *src,struct block_list skillratio += 400; break; case GS_TRACKING: - skillratio += 100 *(skill_lv+1); + skillratio += 100 * (skill_lv+1); break; case GS_PIERCINGSHOT: - skillratio += 20*skill_lv; + skillratio += 20 * skill_lv; break; case GS_RAPIDSHOWER: - skillratio += 10*skill_lv; + skillratio += 10 * skill_lv; break; case GS_DESPERADO: - skillratio += 50*(skill_lv-1); + skillratio += 50 * (skill_lv-1); break; case GS_DUST: - skillratio += 50*skill_lv; + skillratio += 50 * skill_lv; break; case GS_FULLBUSTER: - skillratio += 100*(skill_lv+2); + skillratio += 100 * (skill_lv+2); break; case GS_SPREADATTACK: #ifdef RENEWAL - skillratio += 20*(skill_lv); + skillratio += 20 * (skill_lv); #else - skillratio += 20*(skill_lv-1); + skillratio += 20 * (skill_lv-1); #endif break; -#ifdef RENEWAL - case NJ_ISSEN: - skillratio += 100 * (skill_lv-1); - break; -#endif case NJ_HUUMA: - skillratio += 50 + 150*skill_lv; + skillratio += 50 + 150 * skill_lv; break; case NJ_TATAMIGAESHI: -#ifdef RENEWAL - ATK_RATE(200); -#endif - skillratio += 10*skill_lv; + skillratio += 10 * skill_lv; break; case NJ_KASUMIKIRI: - skillratio += 10*skill_lv; + skillratio += 10 * skill_lv; break; case NJ_KIRIKAGE: - skillratio += 100*(skill_lv-1); + skillratio += 100 * (skill_lv-1); break; case KN_CHARGEATK: { - int k = (wflag-1)/3; //+100% every 3 cells of distance - if( k > 2 ) k = 2; // ...but hard-limited to 300%. - skillratio += 100 * k; + int k = (flag-1)/3; //+100% every 3 cells of distance + if( k > 2 ) k = 2; // ...but hard-limited to 300%. + skillratio += 100 * k; } break; case HT_PHANTASMIC: @@ -2504,66 +2015,63 @@ struct Damage battle_calc_weapon_attack(struct block_list *src,struct block_list skillratio += 200; break; case HFLI_MOON: //[orn] - skillratio += 10+110*skill_lv; + skillratio += 10 + 110 * skill_lv; break; case HFLI_SBR44: //[orn] - skillratio += 100 *(skill_lv-1); + skillratio += 100 * (skill_lv-1); break; case NPC_VAMPIRE_GIFT: - skillratio += ((skill_lv-1)%5+1)*100; + skillratio += ((skill_lv-1)%5+1) * 100; break; case RK_SONICWAVE: - skillratio += 400 + 100 * skill_lv; - RE_LVL_DMOD(100); + skillratio += -100 + 100 * (skill_lv + 5); + skillratio = skillratio * (100 + (status_get_lv(src)-100) / 2) / 100; break; case RK_HUNDREDSPEAR: skillratio += 500 + (80 * skill_lv); - if( sd ) - { + if( sd ){ short index = sd->equip_index[EQI_HAND_R]; if( index >= 0 && sd->inventory_data[index] && sd->inventory_data[index]->type == IT_WEAPON ) - skillratio += max(10000 - sd->inventory_data[index]->weight, 0) / 10; - skillratio += 50 * pc->checkskill(sd,LK_SPIRALPIERCE); - } // (1 + [(Casters Base Level - 100) / 200]) - skillratio = skillratio * (100 + (status_get_lv(src)-100) / 2) / 100; + skillratio += (10000 - min(10000, sd->inventory_data[index]->weight)) / 10; + skillratio = skillratio * (100 + (status_get_lv(src)-100) / 2) / 100 + 50 * pc->checkskill(sd,LK_SPIRALPIERCE); + } break; case RK_WINDCUTTER: - skillratio += 50 * skill_lv; + skillratio += -100 + 50 * (skill_lv + 2); RE_LVL_DMOD(100); break; case RK_IGNITIONBREAK: i = distance_bl(src,target); if( i < 2 ) - skillratio = 200 + 200 * skill_lv; + skillratio += 300 * skill_lv; else if( i < 4 ) - skillratio = 100 + 200 * skill_lv; + skillratio += 250 * skill_lv; else - skillratio = 100 + 100 * skill_lv; - RE_LVL_DMOD(100); - if( sstatus->rhw.ele == ELE_FIRE ) - skillratio += skillratio / 2; + skillratio += 200 * skill_lv; + skillratio = (skillratio - 100) * (100 + (status_get_lv(src)-100)) / 100; + if( status->rhw.ele == ELE_FIRE ) + skillratio += 100 * skill_lv; break; case RK_CRUSHSTRIKE: if( sd ) {//ATK [{Weapon Level * (Weapon Upgrade Level + 6) * 100} + (Weapon ATK) + (Weapon Weight)]% short index = sd->equip_index[EQI_HAND_R]; if( index >= 0 && sd->inventory_data[index] && sd->inventory_data[index]->type == IT_WEAPON ) - skillratio = sd->inventory_data[index]->weight/10 + sstatus->rhw.atk + + skillratio += -100 + sd->inventory_data[index]->weight/10 + status->rhw.atk + 100 * sd->inventory_data[index]->wlv * (sd->status.inventory[index].refine + 6); } break; case RK_STORMBLAST: - skillratio = 100 * (sd ? pc->checkskill(sd,RK_RUNEMASTERY) : 1) + 100 * (sstatus->int_ / 4); + skillratio += -100 + 100 * (sd ? pc->checkskill(sd,RK_RUNEMASTERY) : 1) + 100 * (status_get_int(src) / 4); break; case RK_PHANTOMTHRUST: - skillratio = 50 * skill_lv + 10 * ( sd ? pc->checkskill(sd,KN_SPEARMASTERY) : 10); - //if( s_level > 100 ) skillratio += skillratio * s_level / 150; // Base level bonus. This is official, but is disabled until I can confirm something with was changed or not. [Rytech] - //if( s_level > 100 ) skillratio += skillratio * (s_level - 100) / 200; // Base level bonus. + skillratio += -100 + 50 * skill_lv + 10 * ( sd ? pc->checkskill(sd,KN_SPEARMASTERY) : 10); + RE_LVL_DMOD(150); break; /** - * GC Guilotine Cross - **/ + * GC Guilotine Cross + **/ case GC_CROSSIMPACT: skillratio += 900 + 100 * skill_lv; RE_LVL_DMOD(120); @@ -2575,7 +2083,7 @@ struct Damage battle_calc_weapon_attack(struct block_list *src,struct block_list //ATK [{(Skill Level x 100) + 300} x Caster's Base Level / 120]% + ATK [(AGI x 2) + (Caster's Job Level x 4)]% skillratio += 200 + (100 * skill_lv); RE_LVL_DMOD(120); - skillratio += sstatus->agi + (sd?sd->status.job_level:0) * 4; + skillratio += status_get_agi(src) * 2 + (sd?sd->status.job_level:0) * 4; break; case GC_ROLLINGCUTTER: skillratio += -50 + 50 * skill_lv; @@ -2585,17 +2093,20 @@ struct Damage battle_calc_weapon_attack(struct block_list *src,struct block_list skillratio += 300 + 80 * skill_lv; RE_LVL_DMOD(100); if( sc && sc->data[SC_ROLLINGCUTTER] ) - skillratio += sc->data[SC_ROLLINGCUTTER]->val1 * sstatus->agi; + skillratio += sc->data[SC_ROLLINGCUTTER]->val1 * status_get_agi(src); + break; + case GC_DARKCROW: + skillratio += 100 * (skill_lv - 1); break; /** - * Arch Bishop - **/ + * Arch Bishop + **/ case AB_DUPLELIGHT_MELEE: skillratio += 10 * skill_lv; break; /** - * Ranger - **/ + * Ranger + **/ case RA_ARROWSTORM: skillratio += 900 + 80 * skill_lv; RE_LVL_DMOD(100); @@ -2603,8 +2114,6 @@ struct Damage battle_calc_weapon_attack(struct block_list *src,struct block_list case RA_AIMEDBOLT: skillratio += 400 + 50 * skill_lv; RE_LVL_DMOD(100); - if( tsc && (tsc->data[SC_BITE] || tsc->data[SC_ANKLE] || tsc->data[SC_ELECTRICSHOCKER]) ) - wd.div_ = tstatus->size + 2 + ( (rnd()%100 < 50-tstatus->size*10) ? 1 : 0 ); break; case RA_CLUSTERBOMB: skillratio += 100 + 100 * skill_lv; @@ -2613,7 +2122,7 @@ struct Damage battle_calc_weapon_attack(struct block_list *src,struct block_list skillratio += 200; break; case RA_WUGSTRIKE: - skillratio = 200 * skill_lv; + skillratio += -100 + 200 * skill_lv; break; case RA_WUGBITE: skillratio += 300 + 200 * skill_lv; @@ -2623,18 +2132,18 @@ struct Damage battle_calc_weapon_attack(struct block_list *src,struct block_list skillratio += 50 * skill_lv; break; /** - * Mechanic - **/ + * Mechanic + **/ case NC_BOOSTKNUCKLE: - skillratio += 100 + 100 * skill_lv + sstatus->dex; + skillratio += 100 + 100 * skill_lv + status_get_dex(src); RE_LVL_DMOD(100); break; case NC_PILEBUNKER: - skillratio += 200 + 100 * skill_lv + sstatus->str; + skillratio += 200 + 100 * skill_lv + status_get_str(src); RE_LVL_DMOD(100); break; case NC_VULCANARM: - skillratio = 70 * skill_lv + sstatus->dex; + skillratio += -100 + 70 * skill_lv + status_get_dex(src); RE_LVL_DMOD(100); break; case NC_FLAMELAUNCHER: @@ -2661,11 +2170,11 @@ struct Damage battle_calc_weapon_attack(struct block_list *src,struct block_list RE_LVL_DMOD(100); break; case NC_POWERSWING: - skillratio += 80 + 20 * skill_lv + sstatus->str + sstatus->dex; + skillratio += 80 + 20 * skill_lv + status_get_str(src) + status_get_dex(src); RE_LVL_DMOD(100); break; case NC_AXETORNADO: - skillratio += 100 + 100 * skill_lv + sstatus->vit; + skillratio += 100 + 100 * skill_lv + status_get_vit(src); RE_LVL_DMOD(100); break; case SC_FATALMENACE: @@ -2678,7 +2187,7 @@ struct Damage battle_calc_weapon_attack(struct block_list *src,struct block_list skillratio += 100 + 100 * skill_lv; break; case LG_CANNONSPEAR:// Stimated formula. Still need confirm it. - skillratio += -100 + (50 + sstatus->str) * skill_lv; + skillratio += -100 + (50 + status_get_str(src)) * skill_lv; RE_LVL_DMOD(100); break; case LG_BANISHINGPOINT: @@ -2690,7 +2199,7 @@ struct Damage battle_calc_weapon_attack(struct block_list *src,struct block_list RE_LVL_DMOD(100); break; case LG_PINPOINTATTACK: - skillratio = ((100 * skill_lv) + (10 * status_get_agi(src)) ); + skillratio += -100 + ((100 * skill_lv) + (10 * status_get_agi(src)) ); RE_LVL_DMOD(100); break; case LG_RAGEBURST: @@ -2703,7 +2212,7 @@ struct Damage battle_calc_weapon_attack(struct block_list *src,struct block_list case LG_SHIELDSPELL:// [(Casters Base Level x 4) + (Shield DEF x 10) + (Casters VIT x 2)] % if( sd ) { struct item_data *shield_data = sd->inventory_data[sd->equip_index[EQI_HAND_L]]; - skillratio = status_get_lv(src) * 4 + status_get_vit(src) * 2; + skillratio += -100 + status_get_lv(src) * 4 + status_get_vit(src) * 2; if( shield_data ) skillratio += shield_data->def * 10; } else @@ -2714,668 +2223,1563 @@ struct Damage battle_calc_weapon_attack(struct block_list *src,struct block_list RE_LVL_DMOD(100); break; case LG_OVERBRAND: - skillratio = 400 * skill_lv + (pc->checkskill(sd,CR_SPEARQUICKEN) * 30); + skillratio += -100 + 400 * skill_lv + (pc->checkskill(sd,CR_SPEARQUICKEN) * 30); RE_LVL_DMOD(100); break; case LG_OVERBRAND_BRANDISH: - skillratio = 300 * skill_lv + (2 * (sstatus->str + sstatus->dex) / 3); + skillratio += -100 + 300 * skill_lv + (2 * (status_get_str(src) + status_get_dex(src)) / 3); RE_LVL_DMOD(100); break; case LG_OVERBRAND_PLUSATK: - skillratio = 150 * skill_lv; + skillratio += -100 + 150 * skill_lv; + RE_LVL_DMOD(100); + break; + case LG_RAYOFGENESIS: + skillratio += 200 + 300 * skill_lv; + RE_LVL_DMOD(100); + break; + case LG_EARTHDRIVE: + skillratio = (skillratio + 100) * skill_lv; + RE_LVL_DMOD(100); + break; + case LG_HESPERUSLIT: + skillratio += 120 * skill_lv - 100; + break; + case SR_DRAGONCOMBO: + skillratio += 40 * skill_lv; + RE_LVL_DMOD(100); + break; + case SR_SKYNETBLOW: + if( sc && sc->data[SC_COMBOATTACK] && sc->data[SC_COMBOATTACK]->val1 == SR_DRAGONCOMBO )//ATK [{(Skill Level x 100) + (Caster AGI) + 150} x Caster Base Level / 100] % + skillratio += 100 * skill_lv + status_get_agi(src) + 50; + else //ATK [{(Skill Level x 80) + (Caster AGI)} x Caster Base Level / 100] % + skillratio += -100 + 80 * skill_lv + status_get_agi(src); + RE_LVL_DMOD(100); + break; + case SR_EARTHSHAKER: + if( tsc && (tsc->data[SC_HIDING] || tsc->data[SC_CLOAKING] || // [(Skill Level x 150) x (Caster Base Level / 100) + (Caster INT x 3)] % + tsc->data[SC_CHASEWALK] || tsc->data[SC_CLOAKINGEXCEED] || tsc->data[SC__INVISIBILITY]) ){ + skillratio += -100 + 150 * skill_lv; + RE_LVL_DMOD(100); + skillratio += status_get_int(src) * 3; + }else{ //[(Skill Level x 50) x (Caster Base Level / 100) + (Caster INT x 2)] % + skillratio += 50 * (skill_lv-2); + RE_LVL_DMOD(100); + skillratio += status_get_int(src) * 2; + } + break; + case SR_FALLENEMPIRE:// ATK [(Skill Level x 150 + 100) x Caster Base Level / 150] % + skillratio += 150 *skill_lv; + RE_LVL_DMOD(150); + break; + case SR_TIGERCANNON:// ATK [((Caster consumed HP + SP) / 4) x Caster Base Level / 100] % + { + int hp = status_get_max_hp(src) * (10 + 2 * skill_lv) / 100, + sp = status_get_max_sp(src) * (6 + skill_lv) / 100; + if( sc && sc->data[SC_COMBOATTACK] && sc->data[SC_COMBOATTACK]->val1 == SR_FALLENEMPIRE ) // ATK [((Caster consumed HP + SP) / 2) x Caster Base Level / 100] % + skillratio += -100 + hp+sp / 2; + else + skillratio += -100 + (hp+sp) / 4; + RE_LVL_DMOD(100); + } + break; + case SR_RAMPAGEBLASTER: + skillratio += 20 * skill_lv * (sd?sd->spiritball_old:5) - 100; + if( sc && sc->data[SC_EXPLOSIONSPIRITS] ){ + skillratio += sc->data[SC_EXPLOSIONSPIRITS]->val1 * 20; + RE_LVL_DMOD(120); + }else + RE_LVL_DMOD(150); + break; + case SR_KNUCKLEARROW: + if( flag&4 ){ // ATK [(Skill Level x 150) + (1000 x Target current weight / Maximum weight) + (Target Base Level x 5) x (Caster Base Level / 150)] % + skillratio += -100 + 150 * skill_lv + status_get_lv(target) * 5 * (status_get_lv(src) / 100) ; + if( tsd && tsd->weight ) + skillratio += 100 * (tsd->weight / tsd->max_weight); + }else // ATK [(Skill Level x 100 + 500) x Caster Base Level / 100] % + skillratio += 400 + (100 * skill_lv); + RE_LVL_DMOD(100); + break; + case SR_WINDMILL: // ATK [(Caster Base Level + Caster DEX) x Caster Base Level / 100] % + skillratio += -100 + status_get_lv(src) + status_get_dex(src); + RE_LVL_DMOD(100); + break; + case SR_GATEOFHELL: + if( sc && sc->data[SC_COMBOATTACK] + && sc->data[SC_COMBOATTACK]->val1 == SR_FALLENEMPIRE ) + skillratio += 800 * skill_lv -100; + else + skillratio += 500 * skill_lv -100; + RE_LVL_DMOD(100); + break; + case SR_GENTLETOUCH_QUIET: + skillratio += 100 * skill_lv - 100 + status_get_dex(src); + RE_LVL_DMOD(100); + break; + case SR_HOWLINGOFLION: + skillratio += 300 * skill_lv - 100; + RE_LVL_DMOD(150); + break; + case SR_RIDEINLIGHTNING: // ATK [{(Skill Level x 200) + Additional Damage} x Caster Base Level / 100] % + if( (status->rhw.ele) == ELE_WIND || (status->lhw.ele) == ELE_WIND ) + skillratio += skill_lv * 50; + skillratio += -100 + 200 * skill_lv; + RE_LVL_DMOD(100); + break; + case WM_REVERBERATION_MELEE: + // ATK [{(Skill Level x 100) + 300} x Caster Base Level / 100] + skillratio += 200 + 100 * pc->checkskill(sd, WM_REVERBERATION); RE_LVL_DMOD(100); break; - case LG_RAYOFGENESIS: - skillratio = 300 + 300 * skill_lv; + case WM_SEVERE_RAINSTORM_MELEE: + //ATK [{(Caster DEX + AGI) x (Skill Level / 5)} x Caster Base Level / 100] % + skillratio += -100 + (status_get_dex(src) + status_get_agi(src)) * (skill_lv * 2); + RE_LVL_DMOD(100); + skillratio /= 10; + break; + case WM_GREAT_ECHO: + skillratio += 800 + 100 * skill_lv; + if( sd ) { // Still need official value [pakpil] + short lv = (short)skill_lv; + skillratio += 100 * skill->check_pc_partner(sd,skill_id,&lv,skill->get_splash(skill_id,skill_lv),0); + } + break; + case WM_SOUND_OF_DESTRUCTION: + skillratio += 400; + break; + case GN_CART_TORNADO: + // ATK [( Skill Level x 50 ) + ( Cart Weight / ( 150 - Caster Base STR ))] + ( Cart Remodeling Skill Level x 50 )] % + skillratio += -100 + 50 * skill_lv; + if( sd && sd->cart_weight) + skillratio += sd->cart_weight/10 / max(150-status_get_str(src),1) + pc->checkskill(sd, GN_REMODELING_CART) * 50; + break; + case GN_CARTCANNON: + // ATK [{( Cart Remodeling Skill Level x 50 ) x ( INT / 40 )} + ( Cart Cannon Skill Level x 60 )] % + skillratio += -100 + 60 * skill_lv; + if( sd ) skillratio += pc->checkskill(sd, GN_REMODELING_CART) * 50 * (status_get_int(src) / 40); + break; + case GN_SPORE_EXPLOSION: + skillratio += 200 + 100 * skill_lv; + break; + case GN_CRAZYWEED_ATK: + skillratio += 400 + 100 * skill_lv; + break; + case GN_SLINGITEM_RANGEMELEEATK: + if( sd ) { + switch( sd->itemid ) { + case 13260: // Apple Bomob + case 13261: // Coconut Bomb + case 13262: // Melon Bomb + case 13263: // Pinapple Bomb + skillratio += 400; // Unconfirded + break; + case 13264: // Banana Bomb 2000% + skillratio += 1900; + break; + case 13265: skillratio -= 75; break; // Black Lump 25% + case 13266: skillratio -= 25; break; // Hard Black Lump 75% + case 13267: skillratio += 100; break; // Extremely Hard Black Lump 200% + } + } else + skillratio += 300; // Bombs + break; + case SO_VARETYR_SPEAR://ATK [{( Striking Level x 50 ) + ( Varetyr Spear Skill Level x 50 )} x Caster Base Level / 100 ] % + skillratio += -100 + 50 * skill_lv + ( sd ? pc->checkskill(sd, SO_STRIKING) * 50 : 0 ); + if( sc && sc->data[SC_BLAST_OPTION] ) + skillratio += sd ? sd->status.job_level * 5 : 0; + break; + // Physical Elemantal Spirits Attack Skills + case EL_CIRCLE_OF_FIRE: + case EL_FIRE_BOMB_ATK: + case EL_STONE_RAIN: + skillratio += 200; + break; + case EL_FIRE_WAVE_ATK: + skillratio += 500; + break; + case EL_TIDAL_WEAPON: + skillratio += 1400; + break; + case EL_WIND_SLASH: + skillratio += 100; + break; + case EL_HURRICANE: + skillratio += 600; + break; + case EL_TYPOON_MIS: + case EL_WATER_SCREW_ATK: + skillratio += 900; + break; + case EL_STONE_HAMMER: + skillratio += 400; + break; + case EL_ROCK_CRUSHER: + skillratio += 700; + break; + case KO_JYUMONJIKIRI: + skillratio += -100 + 150 * skill_lv; + RE_LVL_DMOD(120); + if( tsc && tsc->data[SC_KO_JYUMONJIKIRI] ) + skillratio += status_get_lv(src) * skill_lv; + case KO_HUUMARANKA: + skillratio += -100 + 150 * skill_lv + status_get_agi(src) + status_get_dex(src) + 100 * (sd ? pc->checkskill(sd, NJ_HUUMA) : 0); + break; + case KO_SETSUDAN: + skillratio += -100 + 100 * skill_lv; RE_LVL_DMOD(100); break; - case LG_EARTHDRIVE: - skillratio = (skillratio + 100) * skill_lv; - RE_LVL_DMOD(100); + case KO_BAKURETSU: + skillratio += -100 + (50 + status_get_dex(src) / 4) * skill_lv * (sd?pc->checkskill(sd,NJ_TOBIDOUGU):10) * 4 / 100; + RE_LVL_DMOD(120); + skillratio += 10 * (sd ? sd->status.job_level : 0); break; - case LG_HESPERUSLIT: - skillratio += 120 * skill_lv - 100; + case MH_NEEDLE_OF_PARALYZE: + skillratio += 600 + 100 * skill_lv; break; - case SR_DRAGONCOMBO: - skillratio += 40 * skill_lv; - RE_LVL_DMOD(100); + case MH_STAHL_HORN: + skillratio += 400 + 100 * skill_lv; break; - case SR_SKYNETBLOW: - //ATK [{(Skill Level x 80) + (Caster AGI)} x Caster Base Level / 100] % - skillratio = 80 * skill_lv + sstatus->agi; - if( sc && sc->data[SC_COMBO] && sc->data[SC_COMBO]->val1 == SR_DRAGONCOMBO )//ATK [{(Skill Level x 100) + (Caster AGI) + 150} x Caster Base Level / 100] % - skillratio = 100 * skill_lv + sstatus->agi + 150; - RE_LVL_DMOD(100); + case MH_LAVA_SLIDE: + skillratio += -100 + 70 * skill_lv; break; - case SR_EARTHSHAKER: - if( tsc && (tsc->data[SC_HIDING] || tsc->data[SC_CLOAKING] || // [(Skill Level x 150) x (Caster Base Level / 100) + (Caster INT x 3)] % - tsc->data[SC_CHASEWALK] || tsc->data[SC_CLOAKINGEXCEED] || tsc->data[SC__INVISIBILITY]) ){ - skillratio = 150 * skill_lv; - RE_LVL_DMOD(100); - skillratio += sstatus->int_ * 3; - }else{ //[(Skill Level x 50) x (Caster Base Level / 100) + (Caster INT x 2)] % - skillratio += 50 * (skill_lv-2); - RE_LVL_DMOD(100); - skillratio += sstatus->int_ * 2; - } + case MH_TINDER_BREAKER: + case MH_MAGMA_FLOW: + skillratio += -100 + 100 * skill_lv; break; - case SR_FALLENEMPIRE:// ATK [(Skill Level x 150 + 100) x Caster Base Level / 150] % - skillratio += 150 *skill_lv; - RE_LVL_DMOD(150); - break; - case SR_TIGERCANNON:// ATK [((Caster consumed HP + SP) / 4) x Caster Base Level / 100] % - { - int hp = sstatus->max_hp * (10 + 2 * skill_lv) / 100, - sp = sstatus->max_sp * (6 + skill_lv) / 100; - skillratio = (hp+sp) / 4; - if( sc && sc->data[SC_COMBO] && sc->data[SC_COMBO]->val1 == SR_FALLENEMPIRE ) // ATK [((Caster consumed HP + SP) / 2) x Caster Base Level / 100] % - skillratio = hp+sp / 2; - RE_LVL_DMOD(100); + } + if( sc && sc->data[SC_EDP] ){ + skillratio -= addedratio; + if( skill_id == AS_SONICBLOW || + skill_id == GC_COUNTERSLASH || + skill_id == GC_CROSSIMPACT ) + skillratio >>= 1; + skillratio += addedratio; + } + } + if( skillratio < 1 ) + return 0; + return skillratio; +} +/*========================================== + * Check dammage trough status. + * ATK may be MISS, BLOCKED FAIL, reduc, increase, end status... + * After this we apply bg/gvg reduction + *------------------------------------------*/ +int battle_calc_damage(struct block_list *src,struct block_list *bl,struct Damage *d,int damage,uint16 skill_id,uint16 skill_lv) +{ + struct map_session_data *sd = NULL; + struct status_change *sc; + struct status_change_entry *sce; + int div_ = d->div_, flag = d->flag; + + nullpo_ret(bl); + + if( !damage ) + return 0; + if( battle_config.ksprotection && mob_ksprotected(src, bl) ) + return 0; + + if (bl->type == BL_PC) { + sd=(struct map_session_data *)bl; + //Special no damage states + if(flag&BF_WEAPON && sd->special_state.no_weapon_damage) + damage -= damage * sd->special_state.no_weapon_damage / 100; + + if(flag&BF_MAGIC && sd->special_state.no_magic_damage) + damage -= damage * sd->special_state.no_magic_damage / 100; + + if(flag&BF_MISC && sd->special_state.no_misc_damage) + damage -= damage * sd->special_state.no_misc_damage / 100; + + if(!damage) return 0; + } + + sc = status_get_sc(bl); + + if( sc && sc->data[SC_INVINCIBLE] && !sc->data[SC_INVINCIBLEOFF] ) + return 1; + + if (skill_id == PA_PRESSURE) + return damage; //This skill bypass everything else. + + if( sc && sc->count ) + { + //First, sc_*'s that reduce damage to 0. + if( sc->data[SC_BASILICA] && !(status_get_mode(src)&MD_BOSS) ) + { + d->dmg_lv = ATK_BLOCK; + return 0; + } + if( sc->data[SC_WHITEIMPRISON] && skill_id != HW_GRAVITATION ) { // Gravitation and Pressure do damage without removing the effect + if( skill_id == MG_NAPALMBEAT || + skill_id == MG_SOULSTRIKE || + skill_id == WL_SOULEXPANSION || + (skill_id && skill->get_ele(skill_id, skill_lv) == ELE_GHOST) || + (!skill_id && (status_get_status_data(src))->rhw.ele == ELE_GHOST) + ){ + if( skill_id == WL_SOULEXPANSION ) + damage <<= 1; // If used against a player in White Imprison, the skill deals double damage. + status_change_end(bl,SC_WHITEIMPRISON,INVALID_TIMER); // Those skills do damage and removes effect + }else{ + d->dmg_lv = ATK_BLOCK; + return 0; + } + } + + if(sc->data[SC_ZEPHYR] && + flag&(BF_LONG|BF_SHORT)){ + d->dmg_lv = ATK_BLOCK; + return 0; + } + + if( sc->data[SC_SAFETYWALL] && (flag&(BF_SHORT|BF_MAGIC))==BF_SHORT ) + { + struct skill_unit_group* group = skill->id2group(sc->data[SC_SAFETYWALL]->val3); + uint16 skill_id = sc->data[SC_SAFETYWALL]->val2; + if (group) { + if(skill_id == MH_STEINWAND){ + if (--group->val2<=0) + skill->del_unitgroup(group,ALC_MARK); + d->dmg_lv = ATK_BLOCK; + return 0; + } + /** + * in RE, SW possesses a lifetime equal to 3 times the caster's health + **/ + #ifdef RENEWAL + d->dmg_lv = ATK_BLOCK; + if ( ( group->val2 - damage) > 0 ) { + group->val2 -= damage; + } else + skill->del_unitgroup(group,ALC_MARK); + return 0; + #else + if (--group->val2<=0) + skill->del_unitgroup(group,ALC_MARK); + d->dmg_lv = ATK_BLOCK; + return 0; + #endif + } + status_change_end(bl, SC_SAFETYWALL, INVALID_TIMER); + } + + if( ( sc->data[SC_PNEUMA] && (flag&(BF_MAGIC|BF_LONG)) == BF_LONG ) || sc->data[SC__MANHOLE] ) { + d->dmg_lv = ATK_BLOCK; + return 0; + } + if( sc->data[SC_WEAPONBLOCKING] && flag&(BF_SHORT|BF_WEAPON) && rnd()%100 < sc->data[SC_WEAPONBLOCKING]->val2 ) + { + clif->skill_nodamage(bl,src,GC_WEAPONBLOCKING,1,1); + d->dmg_lv = ATK_BLOCK; + sc_start2(bl,SC_COMBOATTACK,100,GC_WEAPONBLOCKING,src->id,2000); + return 0; + } + if( (sce=sc->data[SC_AUTOGUARD]) && flag&BF_WEAPON && !(skill->get_nk(skill_id)&NK_NO_CARDFIX_ATK) && rnd()%100 < sce->val2 ) + { + int delay; + clif->skill_nodamage(bl,bl,CR_AUTOGUARD,sce->val1,1); + // different delay depending on skill level [celest] + if (sce->val1 <= 5) + delay = 300; + else if (sce->val1 > 5 && sce->val1 <= 9) + delay = 200; + else + delay = 100; + unit_set_walkdelay(bl, iTimer->gettick(), delay, 1); + + if(sc->data[SC_CR_SHRINK] && rnd()%100<5*sce->val1) + skill->blown(bl,src,skill->get_blewcount(CR_SHRINK,1),-1,0); + return 0; + } + + if( (sce = sc->data[SC_MILLENNIUMSHIELD]) && sce->val2 > 0 && damage > 0 ) { + clif->skill_nodamage(bl, bl, RK_MILLENNIUMSHIELD, 1, 1); + sce->val3 -= damage; // absorb damage + d->dmg_lv = ATK_BLOCK; + sc_start(bl,SC_STUN,15,0,skill->get_time2(RK_MILLENNIUMSHIELD,sce->val1)); // There is a chance to be stuned when one shield is broken. + if( sce->val3 <= 0 ) { // Shield Down + sce->val2--; + if( sce->val2 > 0 ) { + if( sd ) + clif->millenniumshield(sd,sce->val2); + sce->val3 = 1000; // Next Shield + } else + status_change_end(bl,SC_MILLENNIUMSHIELD,INVALID_TIMER); // All shields down + } + return 0; + } + + + if( (sce=sc->data[SC_PARRYING]) && flag&BF_WEAPON && skill_id != WS_CARTTERMINATION && rnd()%100 < sce->val2 ) + { // attack blocked by Parrying + clif->skill_nodamage(bl, bl, LK_PARRYING, sce->val1,1); + return 0; + } + + if(sc->data[SC_DODGE_READY] && ( !sc->opt1 || sc->opt1 == OPT1_BURNING ) && + (flag&BF_LONG || sc->data[SC_STRUP]) + && rnd()%100 < 20) { + if (sd && pc_issit(sd)) pc->setstand(sd); //Stand it to dodge. + clif->skill_nodamage(bl,bl,TK_DODGE,1,1); + if (!sc->data[SC_COMBOATTACK]) + sc_start4(bl, SC_COMBOATTACK, 100, TK_JUMPKICK, src->id, 1, 0, 2000); + return 0; + } + + if(sc->data[SC_HERMODE] && flag&BF_MAGIC) + return 0; + + if(sc->data[SC_NJ_TATAMIGAESHI] && (flag&(BF_MAGIC|BF_LONG)) == BF_LONG) + return 0; + + if( sc->data[SC_NEUTRALBARRIER] && (flag&(BF_MAGIC|BF_LONG)) == (BF_MAGIC|BF_LONG) ) { + d->dmg_lv = ATK_MISS; + return 0; + } + + if((sce=sc->data[SC_KAUPE]) && rnd()%100 < sce->val2) + { //Kaupe blocks damage (skill or otherwise) from players, mobs, homuns, mercenaries. + clif->specialeffect(bl, 462, AREA); + //Shouldn't end until Breaker's non-weapon part connects. + if (skill_id != ASC_BREAKER || !(flag&BF_WEAPON)) + if (--(sce->val3) <= 0) //We make it work like Safety Wall, even though it only blocks 1 time. + status_change_end(bl, SC_KAUPE, INVALID_TIMER); + return 0; + } + + if( flag&BF_MAGIC && (sce=sc->data[SC_PRESTIGE]) && rnd()%100 < sce->val2) { + clif->specialeffect(bl, 462, AREA); // Still need confirm it. + return 0; + } + + if (((sce=sc->data[SC_NJ_UTSUSEMI]) || sc->data[SC_NJ_BUNSINJYUTSU]) + && flag&BF_WEAPON && !(skill->get_nk(skill_id)&NK_NO_CARDFIX_ATK)) { + + skill->additional_effect (src, bl, skill_id, skill_lv, flag, ATK_BLOCK, iTimer->gettick() ); + if( !status_isdead(src) ) + skill->counter_additional_effect( src, bl, skill_id, skill_lv, flag, iTimer->gettick() ); + if (sce) { + clif->specialeffect(bl, 462, AREA); + skill->blown(src,bl,sce->val3,-1,0); + } + //Both need to be consumed if they are active. + if (sce && --(sce->val2) <= 0) + status_change_end(bl, SC_NJ_UTSUSEMI, INVALID_TIMER); + if ((sce=sc->data[SC_NJ_BUNSINJYUTSU]) && --(sce->val2) <= 0) + status_change_end(bl, SC_NJ_BUNSINJYUTSU, INVALID_TIMER); + + return 0; + } + + //Now damage increasing effects + if( sc->data[SC_LEXAETERNA] && skill_id != PF_SOULBURN ) + { + if( src->type != BL_MER || skill_id == 0 ) + damage <<= 1; // Lex Aeterna only doubles damage of regular attacks from mercenaries + + if( skill_id != ASC_BREAKER || !(flag&BF_WEAPON) ) + status_change_end(bl, SC_LEXAETERNA, INVALID_TIMER); //Shouldn't end until Breaker's non-weapon part connects. + } + +#ifdef RENEWAL + if( sc->data[SC_RAID] ) { + damage += damage * 20 / 100; + + if (--sc->data[SC_RAID]->val1 == 0) + status_change_end(bl, SC_RAID, INVALID_TIMER); + } +#endif + + if( damage ) { + struct map_session_data *tsd = BL_CAST(BL_PC, src); + if( sc->data[SC_DEEP_SLEEP] ) { + damage += damage / 2; // 1.5 times more damage while in Deep Sleep. + status_change_end(bl,SC_DEEP_SLEEP,INVALID_TIMER); + } + if( tsd && sd && sc->data[SC_CRYSTALIZE] && flag&BF_WEAPON ){ + switch(tsd->status.weapon){ + case W_MACE: + case W_2HMACE: + case W_1HAXE: + case W_2HAXE: + damage = damage * 150/100; + break; + case W_MUSICAL: + case W_WHIP: + if(!sd->state.arrow_atk) + break; + case W_BOW: + case W_REVOLVER: + case W_RIFLE: + case W_GATLING: + case W_SHOTGUN: + case W_GRENADE: + case W_DAGGER: + case W_1HSWORD: + case W_2HSWORD: + damage = damage * 50/100; + break; + } + } + if( sc->data[SC_SIREN] ) + status_change_end(bl,SC_SIREN,INVALID_TIMER); + } + + //Finally damage reductions.... + // Assumptio doubles the def & mdef on RE mode, otherwise gives a reduction on the final damage. [Igniz] +#ifndef RENEWAL + if( sc->data[SC_ASSUMPTIO] ) { + if( map_flag_vs(bl->m) ) + damage = damage*2/3; //Receive 66% damage + else + damage >>= 1; //Receive 50% damage + } +#endif + + if(sc->data[SC_DEFENDER] && + (flag&(BF_LONG|BF_WEAPON)) == (BF_LONG|BF_WEAPON)) + damage = damage * ( 100 - sc->data[SC_DEFENDER]->val2 ) / 100; + + if(sc->data[SC_GS_ADJUSTMENT] && + (flag&(BF_LONG|BF_WEAPON)) == (BF_LONG|BF_WEAPON)) + damage -= damage * 20 / 100; + + if(sc->data[SC_FOGWALL] && skill_id != RK_DRAGONBREATH && skill_id != RK_DRAGONBREATH_WATER) { + if(flag&BF_SKILL) //25% reduction + damage -= damage * 25 / 100; + else if ((flag&(BF_LONG|BF_WEAPON)) == (BF_LONG|BF_WEAPON)) + damage >>= 2; //75% reduction + } + + // Compressed code, fixed by map.h [Epoque] + if (src->type == BL_MOB) { + int i; + if (sc->data[SC_MANU_DEF]) + for (i=0;ARRAYLENGTH(mob_manuk)>i;i++) + if (mob_manuk[i]==((TBL_MOB*)src)->class_) { + damage -= damage * sc->data[SC_MANU_DEF]->val1 / 100; + break; } + if (sc->data[SC_SPL_DEF]) + for (i=0;ARRAYLENGTH(mob_splendide)>i;i++) + if (mob_splendide[i]==((TBL_MOB*)src)->class_) { + damage -= damage * sc->data[SC_SPL_DEF]->val1 / 100; + break; + } + } + + if((sce=sc->data[SC_ARMOR]) && //NPC_DEFENDER + sce->val3&flag && sce->val4&flag) + damage -= damage * sc->data[SC_ARMOR]->val2 / 100; + +#ifdef RENEWAL + if(sc->data[SC_ENERGYCOAT] && (flag&BF_WEAPON || flag&BF_MAGIC) && skill_id != WS_CARTTERMINATION) +#else + if(sc->data[SC_ENERGYCOAT] && (flag&BF_WEAPON && skill_id != WS_CARTTERMINATION)) +#endif + { + struct status_data *status = status_get_status_data(bl); + int per = 100*status->sp / status->max_sp -1; //100% should be counted as the 80~99% interval + per /=20; //Uses 20% SP intervals. + //SP Cost: 1% + 0.5% per every 20% SP + if (!status_charge(bl, 0, (10+5*per)*status->max_sp/1000)) + status_change_end(bl, SC_ENERGYCOAT, INVALID_TIMER); + //Reduction: 6% + 6% every 20% + damage -= damage * (6 * (1+per)) / 100; + } + if(sc->data[SC_GRANITIC_ARMOR]){ + damage -= damage * sc->data[SC_GRANITIC_ARMOR]->val2 / 100; + } + if(sc->data[SC_PAIN_KILLER]){ + damage -= damage * sc->data[SC_PAIN_KILLER]->val3 / 100; + } + if((sce=sc->data[SC_MAGMA_FLOW]) && (rnd()%100 <= sce->val2) ){ + skill->castend_damage_id(bl,src,MH_MAGMA_FLOW,sce->val1,iTimer->gettick(),0); + } + + if( (sce = sc->data[SC_STONEHARDSKIN]) && flag&(BF_SHORT|BF_WEAPON) && damage > 0 ) { + sce->val2 -= damage; + if( src->type == BL_PC ) { + TBL_PC *ssd = BL_CAST(BL_PC, src); + if (ssd && ssd->status.weapon != W_BOW) + skill->break_equip(src, EQP_WEAPON, 3000, BCT_SELF); + } else + skill->break_equip(src, EQP_WEAPON, 3000, BCT_SELF); + // 30% chance to reduce monster's ATK by 25% for 10 seconds. + if( src->type == BL_MOB ) + sc_start(src, SC_NOEQUIPWEAPON, 30, 0, skill->get_time2(RK_STONEHARDSKIN, sce->val1)); + if( sce->val2 <= 0 ) + status_change_end(bl, SC_STONEHARDSKIN, INVALID_TIMER); + } + +/** + * In renewal steel body reduces all incoming damage by 1/10 + **/ +#ifdef RENEWAL + if( sc->data[SC_STEELBODY] ) { + damage = damage > 10 ? damage / 10 : 1; + } +#endif + + //Finally added to remove the status of immobile when aimedbolt is used. [Jobbie] + if( skill_id == RA_AIMEDBOLT && (sc->data[SC_WUGBITE] || sc->data[SC_ANKLESNARE] || sc->data[SC_ELECTRICSHOCKER]) ) + { + status_change_end(bl, SC_WUGBITE, INVALID_TIMER); + status_change_end(bl, SC_ANKLESNARE, INVALID_TIMER); + status_change_end(bl, SC_ELECTRICSHOCKER, INVALID_TIMER); + } + + //Finally Kyrie because it may, or not, reduce damage to 0. + if((sce = sc->data[SC_KYRIE]) && damage > 0){ + sce->val2-=damage; + if(flag&BF_WEAPON || skill_id == TF_THROWSTONE){ + if(sce->val2>=0) + damage=0; + else + damage=-sce->val2; + } + if((--sce->val3)<=0 || (sce->val2<=0) || skill_id == AL_HOLYLIGHT) + status_change_end(bl, SC_KYRIE, INVALID_TIMER); + } + + if( sc->data[SC_MEIKYOUSISUI] && rand()%100 < 40 ) // custom value + damage = 0; + + + if (!damage) return 0; + + if( (sce = sc->data[SC_LIGHTNINGWALK]) && flag&BF_LONG && rnd()%100 < sce->val1 ) { + int dx[8]={0,-1,-1,-1,0,1,1,1}; + int dy[8]={1,1,0,-1,-1,-1,0,1}; + uint8 dir = iMap->calc_dir(bl, src->x, src->y); + if( unit_movepos(bl, src->x-dx[dir], src->y-dy[dir], 1, 1) ) { + clif->slide(bl,src->x-dx[dir],src->y-dy[dir]); + unit_setdir(bl, dir); + } + d->dmg_lv = ATK_DEF; + status_change_end(bl, SC_LIGHTNINGWALK, INVALID_TIMER); + return 0; + } + + //Probably not the most correct place, but it'll do here + //(since battle_drain is strictly for players currently) + if ((sce=sc->data[SC_HAMI_BLOODLUST]) && flag&BF_WEAPON && damage > 0 && + rnd()%100 < sce->val3) + status_heal(src, damage*sce->val4/100, 0, 3); + + if( sd && (sce = sc->data[SC_FORCEOFVANGUARD]) && flag&BF_WEAPON && rnd()%100 < sce->val2 ) + pc->addspiritball(sd,skill->get_time(LG_FORCEOFVANGUARD,sce->val1),sce->val3); + if (sc->data[SC_STYLE_CHANGE] && rnd()%2) { + TBL_HOM *hd = BL_CAST(BL_HOM,bl); + if (hd) homun->addspiritball(hd, 10); //add a sphere + } + + if( sc->data[SC__DEADLYINFECT] && damage > 0 && rnd()%100 < 65 + 5 * sc->data[SC__DEADLYINFECT]->val1 ) + status_change_spread(bl, src); // Deadly infect attacked side + + if( sc && sc->data[SC__SHADOWFORM] ) { + struct block_list *s_bl = iMap->id2bl(sc->data[SC__SHADOWFORM]->val2); + if( !s_bl || s_bl->m != bl->m ) { // If the shadow form target is not present remove the sc. + status_change_end(bl, SC__SHADOWFORM, INVALID_TIMER); + } else if( status_isdead(s_bl) || !battle->check_target(src,s_bl,BCT_ENEMY)) { // If the shadow form target is dead or not your enemy remove the sc in both. + status_change_end(bl, SC__SHADOWFORM, INVALID_TIMER); + if( s_bl->type == BL_PC ) + ((TBL_PC*)s_bl)->shadowform_id = 0; + } else { + if( (--sc->data[SC__SHADOWFORM]->val3) < 0 ) { // If you have exceded max hits supported, remove the sc in both. + status_change_end(bl, SC__SHADOWFORM, INVALID_TIMER); + if( s_bl->type == BL_PC ) + ((TBL_PC*)s_bl)->shadowform_id = 0; + } else { + status_damage(bl, s_bl, damage, 0, clif->damage(s_bl, s_bl, iTimer->gettick(), 500, 500, damage, -1, 0, 0), 0); + return ATK_NONE; + } + } + } + + } + + //SC effects from caster side. + sc = status_get_sc(src); + + if (sc && sc->count) { + if( sc->data[SC_INVINCIBLE] && !sc->data[SC_INVINCIBLEOFF] ) + damage += damage * 75 / 100; + // [Epoque] + if (bl->type == BL_MOB) { + int i; + + if ( ((sce=sc->data[SC_MANU_ATK]) && (flag&BF_WEAPON)) || + ((sce=sc->data[SC_MANU_MATK]) && (flag&BF_MAGIC)) + ) + for (i=0;ARRAYLENGTH(mob_manuk)>i;i++) + if (((TBL_MOB*)bl)->class_==mob_manuk[i]) { + damage += damage * sce->val1 / 100; break; - case SR_RAMPAGEBLASTER: - skillratio += 20 * skill_lv * (sd?sd->spiritball_old:5) - 100; - if( sc && sc->data[SC_EXPLOSIONSPIRITS] ){ - skillratio += sc->data[SC_EXPLOSIONSPIRITS]->val1 * 20; - RE_LVL_DMOD(120); - }else - RE_LVL_DMOD(150); - break; - case SR_KNUCKLEARROW: - if( wflag&4 ){ // ATK [(Skill Level x 150) + (1000 x Target current weight / Maximum weight) + (Target Base Level x 5) x (Caster Base Level / 150)] % - skillratio = 150 * skill_lv + status_get_lv(target) * 5 * (status_get_lv(src) / 100) ; - if( tsd && tsd->weight ) - skillratio += 100 * (tsd->weight / tsd->max_weight); - }else // ATK [(Skill Level x 100 + 500) x Caster Base Level / 100] % - skillratio += 400 + (100 * skill_lv); - RE_LVL_DMOD(100); - break; - case SR_WINDMILL: // ATK [(Caster Base Level + Caster DEX) x Caster Base Level / 100] % - skillratio = status_get_lv(src) + sstatus->dex; - RE_LVL_DMOD(100); - break; - case SR_GATEOFHELL: - if( sc && sc->data[SC_COMBO] - && sc->data[SC_COMBO]->val1 == SR_FALLENEMPIRE ) - skillratio += 800 * skill_lv -100; - else - skillratio += 500 * skill_lv -100; - RE_LVL_DMOD(100); - break; - case SR_GENTLETOUCH_QUIET: - skillratio += 100 * skill_lv - 100 + sstatus->dex; - RE_LVL_DMOD(100); - break; - case SR_HOWLINGOFLION: - skillratio += 300 * skill_lv - 100; - RE_LVL_DMOD(150); - break; - case SR_RIDEINLIGHTNING: // ATK [{(Skill Level x 200) + Additional Damage} x Caster Base Level / 100] % - if( (sstatus->rhw.ele) == ELE_WIND || (sstatus->lhw.ele) == ELE_WIND ) - skillratio += skill_lv * 50; - skillratio += -100 + 200 * skill_lv; - RE_LVL_DMOD(100); - break; - case WM_REVERBERATION_MELEE: - // ATK [{(Skill Level x 100) + 300} x Caster Base Level / 100] - skillratio += 200 + 100 * pc->checkskill(sd, WM_REVERBERATION); - RE_LVL_DMOD(100); - break; - case WM_SEVERE_RAINSTORM_MELEE: - //ATK [{(Caster DEX + AGI) x (Skill Level / 5)} x Caster Base Level / 100] % - skillratio = (sstatus->dex + sstatus->agi) * (skill_lv * 2); - RE_LVL_DMOD(100); - skillratio /= 10; - break; - case WM_GREAT_ECHO: - skillratio += 800 + 100 * skill_lv; - if( sd ) { // Still need official value [pakpil] - short lv = (short)skill_lv; - skillratio += 100 * skill->check_pc_partner(sd,skill_id,&lv,skill->get_splash(skill_id,skill_lv),0); } - break; - case WM_SOUND_OF_DESTRUCTION: - skillratio += 400; - break; - case GN_CART_TORNADO: - // ATK [( Skill Level x 50 ) + ( Cart Weight / ( 150 - Caster Base STR ))] + ( Cart Remodeling Skill Level x 50 )] % - skillratio = 50 * skill_lv; - if( sd && sd->cart_weight) - skillratio += sd->cart_weight/10 / max(150-sstatus->str,1) + pc->checkskill(sd, GN_REMODELING_CART) * 50; - break; - case GN_CARTCANNON: - // ATK [{( Cart Remodeling Skill Level x 50 ) x ( INT / 40 )} + ( Cart Cannon Skill Level x 60 )] % - skillratio = 60 * skill_lv; - if( sd ) skillratio += pc->checkskill(sd, GN_REMODELING_CART) * 50 * (sstatus->int_ / 40); - break; - case GN_SPORE_EXPLOSION: - skillratio += 200 + 100 * skill_lv; - break; - case GN_CRAZYWEED_ATK: - skillratio += 400 + 100 * skill_lv; - break; - case GN_SLINGITEM_RANGEMELEEATK: - if( sd ) { - switch( sd->itemid ) { - case 13260: // Apple Bomob - case 13261: // Coconut Bomb - case 13262: // Melon Bomb - case 13263: // Pinapple Bomb - skillratio += 400; // Unconfirded - break; - case 13264: // Banana Bomb 2000% - skillratio += 1900; - break; - case 13265: skillratio -= 75; break; // Black Lump 25% - case 13266: skillratio -= 25; break; // Hard Black Lump 75% - case 13267: skillratio += 100; break; // Extremely Hard Black Lump 200% - } - } else - skillratio += 300; // Bombs - break; - case SO_VARETYR_SPEAR://ATK [{( Striking Level x 50 ) + ( Varetyr Spear Skill Level x 50 )} x Caster Base Level / 100 ] % - skillratio = 50 * skill_lv + ( sd ? pc->checkskill(sd, SO_STRIKING) * 50 : 0 ); - if( sc && sc->data[SC_BLAST_OPTION] ) - skillratio += sd ? sd->status.job_level * 5 : 0; - break; - // Physical Elemantal Spirits Attack Skills - case EL_CIRCLE_OF_FIRE: - case EL_FIRE_BOMB_ATK: - case EL_STONE_RAIN: - skillratio += 200; - break; - case EL_FIRE_WAVE_ATK: - skillratio += 500; - break; - case EL_TIDAL_WEAPON: - skillratio += 1400; - break; - case EL_WIND_SLASH: - skillratio += 100; - break; - case EL_HURRICANE: - skillratio += 600; - break; - case EL_TYPOON_MIS: - case EL_WATER_SCREW_ATK: - skillratio += 900; - break; - case EL_STONE_HAMMER: - skillratio += 400; - break; - case EL_ROCK_CRUSHER: - skillratio += 700; - break; - case KO_JYUMONJIKIRI: - if( tsc && tsc->data[SC_JYUMONJIKIRI] ) - wd.div_ = wd.div_ * -1;// needs more info - skillratio += -100 + 150 * skill_lv; - case KO_HUUMARANKA: - skillratio += -100 + 150 * skill_lv + sstatus->dex/2 + sstatus->agi/2; // needs more info - break; - case KO_SETSUDAN: - skillratio += 100 * (skill_lv-1); - break; - case KO_BAKURETSU: - skillratio = 50 * skill_lv * (sd?pc->checkskill(sd,NJ_TOBIDOUGU):10); - break; - case MH_NEEDLE_OF_PARALYZE: - skillratio += 600 + 100 * skill_lv; - break; - case MH_STAHL_HORN: - skillratio += 400 + 100 * skill_lv; - break; - case MH_LAVA_SLIDE: - skillratio = 70 * skill_lv; - break; - case MH_TINDER_BREAKER: - case MH_MAGMA_FLOW: - skillratio += -100 + 100 * skill_lv; - break; + if ( ((sce=sc->data[SC_SPL_ATK]) && (flag&BF_WEAPON)) || + ((sce=sc->data[SC_SPL_MATK]) && (flag&BF_MAGIC)) + ) + for (i=0;ARRAYLENGTH(mob_splendide)>i;i++) + if (((TBL_MOB*)bl)->class_==mob_splendide[i]) { + damage += damage * sce->val1 / 100; + break; + } + } + if( sc->data[SC_POISONINGWEAPON] && skill_id != GC_VENOMPRESSURE && (flag&BF_WEAPON) && damage > 0 && rnd()%100 < sc->data[SC_POISONINGWEAPON]->val3 ) + sc_start(bl,sc->data[SC_POISONINGWEAPON]->val2,100,sc->data[SC_POISONINGWEAPON]->val1,skill->get_time2(GC_POISONINGWEAPON, 1)); + if( sc->data[SC__DEADLYINFECT] && damage > 0 && rnd()%100 < 65 + 5 * sc->data[SC__DEADLYINFECT]->val1 ) + status_change_spread(src, bl); + if (sc->data[SC_STYLE_CHANGE] && rnd()%2) { + TBL_HOM *hd = BL_CAST(BL_HOM,bl); + if (hd) homun->addspiritball(hd, 10); + } + } + /* no data claims these settings affect anything other than players */ + if( damage && sd && bl->type == BL_PC ) { + switch( skill_id ) { + //case PA_PRESSURE: /* pressure also belongs to this list but it doesn't reach this area -- so dont worry about it */ + case HW_GRAVITATION: + case NJ_ZENYNAGE: + case KO_MUCHANAGE: + break; + default: + if (flag & BF_SKILL) { //Skills get a different reduction than non-skills. [Skotlex] + if (flag&BF_WEAPON) + damage = damage * map[bl->m].weapon_damage_rate / 100; + if (flag&BF_MAGIC) + damage = damage * map[bl->m].magic_damage_rate / 100; + if (flag&BF_MISC) + damage = damage * map[bl->m].misc_damage_rate / 100; + } else { //Normal attacks get reductions based on range. + if (flag & BF_SHORT) + damage = damage * map[bl->m].short_damage_rate / 100; + if (flag & BF_LONG) + damage = damage * map[bl->m].long_damage_rate / 100; + } + if(!damage) damage = 1; + break; + } + } + + if(battle_config.skill_min_damage && damage > 0 && damage < div_) + { + if ((flag&BF_WEAPON && battle_config.skill_min_damage&1) + || (flag&BF_MAGIC && battle_config.skill_min_damage&2) + || (flag&BF_MISC && battle_config.skill_min_damage&4) + ) + damage = div_; + } + + if( bl->type == BL_MOB && !status_isdead(bl) && src != bl) { + if (damage > 0 ) + mobskill_event((TBL_MOB*)bl,src,iTimer->gettick(),flag); + if (skill_id) + mobskill_event((TBL_MOB*)bl,src,iTimer->gettick(),MSC_SKILLUSED|(skill_id<<16)); + } + if( sd ) { + if( pc_ismadogear(sd) && rnd()%100 < 50 ) { + short element = skill->get_ele(skill_id, skill_lv); + if( !skill_id || element == -1 ) { //Take weapon's element + struct status_data *sstatus = NULL; + if( src->type == BL_PC && ((TBL_PC*)src)->bonus.arrow_ele ) + element = ((TBL_PC*)src)->bonus.arrow_ele; + else if( (sstatus = status_get_status_data(src)) ) { + element = sstatus->rhw.ele; + } + } + else if( element == -2 ) //Use enchantment's element + element = status_get_attack_sc_element(src,status_get_sc(src)); + else if( element == -3 ) //Use random element + element = rnd()%ELE_MAX; + if( element == ELE_FIRE || element == ELE_WATER ) + pc->overheat(sd,element == ELE_FIRE ? 1 : -1); + } + } + + return damage; +} + +/*========================================== + * Calculates BG related damage adjustments. + *------------------------------------------*/ +int battle_calc_bg_damage(struct block_list *src, struct block_list *bl, int damage, int div_, uint16 skill_id, uint16 skill_lv, int flag) +{ + if( !damage ) + return 0; + + if( bl->type == BL_MOB ) { + struct mob_data* md = BL_CAST(BL_MOB, bl); + + if( flag&BF_SKILL && (md->class_ == MOBID_BLUE_CRYST || md->class_ == MOBID_PINK_CRYST) ) + return 0; // Crystal cannot receive skill damage on battlegrounds + } + + return damage; +} + +/*========================================== + * Calculates GVG related damage adjustments. + *------------------------------------------*/ +int battle_calc_gvg_damage(struct block_list *src,struct block_list *bl,int damage,int div_,uint16 skill_id,uint16 skill_lv,int flag) +{ + struct mob_data* md = BL_CAST(BL_MOB, bl); + int class_ = status_get_class(bl); + + if (!damage) //No reductions to make. + return 0; + + if(md && md->guardian_data) { + if(class_ == MOBID_EMPERIUM && flag&BF_SKILL) { + //Skill immunity. + switch (skill_id) { +#ifndef RENEWAL + case MO_TRIPLEATTACK: +#endif + case HW_GRAVITATION: + break; + default: + return 0; + } + } + if(src->type != BL_MOB) { + struct guild *g = src->type == BL_PC ? ((TBL_PC *)src)->guild : guild->search(status_get_guild_id(src)); + + if (class_ == MOBID_EMPERIUM && (!g || guild->checkskill(g,GD_APPROVAL) <= 0 )) + return 0; + + if (g && battle_config.guild_max_castles && guild->checkcastles(g)>=battle_config.guild_max_castles) + return 0; // [MouseJstr] + } + } + + switch (skill_id) { + case PA_PRESSURE: + case HW_GRAVITATION: + case NJ_ZENYNAGE: + case KO_MUCHANAGE: + break; + default: + /* Uncomment if you want god-mode Emperiums at 100 defense. [Kisuka] + if (md && md->guardian_data) { + damage -= damage * (md->guardian_data->castle->defense/100) * battle_config.castle_defense_rate/100; + } + */ + break; + } + + return damage; +} + +/*========================================== + * HP/SP drain calculation + *------------------------------------------*/ +int battle_calc_drain(int damage, int rate, int per) { + int diff = 0; + + if (per && rnd()%1000 < rate) { + diff = (damage * per) / 100; + if (diff == 0) { + if (per > 0) + diff = 1; + else + diff = -1; + } + } + return diff; +} + +/*========================================== + * Consumes ammo for the given skill. + *------------------------------------------*/ +void battle_consume_ammo(TBL_PC*sd, int skill_id, int lv) { + int qty=1; + if (!battle_config.arrow_decrement) + return; + + if (skill) { + qty = skill->get_ammo_qty(skill_id, lv); + if (!qty) qty = 1; + } + + if(sd->equip_index[EQI_AMMO]>=0) //Qty check should have been done in skill_check_condition + pc->delitem(sd,sd->equip_index[EQI_AMMO],qty,0,1,LOG_TYPE_CONSUME); + + sd->state.arrow_atk = 0; +} +//Skill Range Criteria +int battle_range_type(struct block_list *src, struct block_list *target, uint16 skill_id, uint16 skill_lv) { + if (battle_config.skillrange_by_distance && + (src->type&battle_config.skillrange_by_distance) + ) { //based on distance between src/target [Skotlex] + if (check_distance_bl(src, target, 5)) + return BF_SHORT; + return BF_LONG; + } + //based on used skill's range + if (skill->get_range2(src, skill_id, skill_lv) < 5) + return BF_SHORT; + return BF_LONG; +} +int battle_adjust_skill_damage(int m, unsigned short skill_id) { + + if( map[m].skill_count ) { + int i; + ARR_FIND(0, map[m].skill_count, i, map[m].skills[i]->skill_id == skill_id ); + + if( i < map[m].skill_count ) { + return map[m].skills[i]->modifier; + } + + } + + return 0; +} +int battle_blewcount_bonus(struct map_session_data *sd, uint16 skill_id) { + int i; + if (!sd->skillblown[0].id) + return 0; + //Apply the bonus blewcount. [Skotlex] + for (i = 0; i < ARRAYLENGTH(sd->skillblown) && sd->skillblown[i].id; i++) { + if (sd->skillblown[i].id == skill_id) + return sd->skillblown[i].val; + } + return 0; +} +//For quick div adjustment. +#define damage_div_fix(dmg, div) { if (div > 1) (dmg)*=div; else if (div < 0) (div)*=-1; } +/*========================================== + * battle_calc_magic_attack [DracoRPG] + *------------------------------------------*/ +struct Damage battle_calc_magic_attack(struct block_list *src,struct block_list *target,uint16 skill_id,uint16 skill_lv,int mflag) { + int i, nk; + short s_ele = 0; + unsigned int skillratio = 100; //Skill dmg modifiers. + + TBL_PC *sd; +// TBL_PC *tsd; + struct status_change *sc, *tsc; + struct Damage ad; + struct status_data *sstatus = status_get_status_data(src); + struct status_data *tstatus = status_get_status_data(target); + struct { + unsigned imdef : 1; + unsigned infdef : 1; + } flag; + + memset(&ad,0,sizeof(ad)); + memset(&flag,0,sizeof(flag)); + + if(src==NULL || target==NULL) + { + nullpo_info(NLP_MARK); + return ad; + } + //Initial Values + ad.damage = 1; + ad.div_=skill->get_num(skill_id,skill_lv); + ad.amotion=skill->get_inf(skill_id)&INF_GROUND_SKILL?0:sstatus->amotion; //Amotion should be 0 for ground skills. + ad.dmotion=tstatus->dmotion; + ad.blewcount = skill->get_blewcount(skill_id,skill_lv); + ad.flag=BF_MAGIC|BF_SKILL; + ad.dmg_lv=ATK_DEF; + nk = skill->get_nk(skill_id); + flag.imdef = nk&NK_IGNORE_DEF?1:0; + + sd = BL_CAST(BL_PC, src); +// tsd = BL_CAST(BL_PC, target); + sc = status_get_sc(src); + tsc = status_get_sc(target); + + //Initialize variables that will be used afterwards + s_ele = skill->get_ele(skill_id, skill_lv); + + if (s_ele == -1){ // pl=-1 : the skill takes the weapon's element + s_ele = sstatus->rhw.ele; + if( sd ){ //Summoning 10 charm will endow your weapon + ARR_FIND(1, 6, i, sd->charm[i] >= 10); + if( i < 5 ) s_ele = i; + } + }else if (s_ele == -2) //Use status element + s_ele = status_get_attack_sc_element(src,status_get_sc(src)); + else if( s_ele == -3 ) //Use random element + s_ele = rnd()%ELE_MAX; + + if( skill_id == SO_PSYCHIC_WAVE ) { + if( sc && sc->count ) { + if( sc->data[SC_HEATER_OPTION] ) s_ele = sc->data[SC_HEATER_OPTION]->val4; + else if( sc->data[SC_COOLER_OPTION] ) s_ele = sc->data[SC_COOLER_OPTION]->val4; + else if( sc->data[SC_BLAST_OPTION] ) s_ele = sc->data[SC_BLAST_OPTION]->val3; + else if( sc->data[SC_CURSED_SOIL_OPTION] ) s_ele = sc->data[SC_CURSED_SOIL_OPTION]->val4; + } + } + + //Set miscellaneous data that needs be filled + if(sd) { + sd->state.arrow_atk = 0; + ad.blewcount += battle->blewcount_bonus(sd, skill_id); + } + + //Skill Range Criteria + ad.flag |= battle->range_type(src, target, skill_id, skill_lv); + flag.infdef=(tstatus->mode&MD_PLANT?1:0); + if( target->type == BL_SKILL){ + TBL_SKILL *su = (TBL_SKILL*)target; + if( su->group && (su->group->skill_id == WM_REVERBERATION || su->group->skill_id == WM_POEMOFNETHERWORLD) ) + flag.infdef = 1; + } + + switch(skill_id) { + case MG_FIREWALL: + case NJ_KAENSIN: + ad.dmotion = 0; //No flinch animation. + if ( tstatus->def_ele == ELE_FIRE || battle->check_undead(tstatus->race, tstatus->def_ele) ) + ad.blewcount = 0; //No knockback + break; + case PR_SANCTUARY: + ad.dmotion = 0; //No flinch animation. + break; + case WL_HELLINFERNO: + if( mflag&ELE_DARK ) + s_ele = ELE_DARK; + break; + case KO_KAIHOU: + if( sd ){ + ARR_FIND(1, 6, i, sd->charm[i] > 0); + if( i < 5 ) + s_ele = i; } + break; #ifdef RENEWAL - if( sc && sc->data[SC_TRUESIGHT] ) - skillratio += 2*sc->data[SC_TRUESIGHT]->val1; + case CR_ACIDDEMONSTRATION: + case ASC_BREAKER: + case HW_MAGICCRASHER: + flag.imdef = 1; + break; #endif - ATK_RATE(skillratio); + } - //Constant/misc additions from skills - switch (skill_id) { - case MO_EXTREMITYFIST: - ATK_ADD(250 + 150*skill_lv); - break; - case TK_DOWNKICK: - case TK_STORMKICK: - case TK_TURNKICK: - case TK_COUNTER: - case TK_JUMPKICK: - //TK_RUN kick damage bonus. - if(sd && sd->weapontype1 == W_FIST && sd->weapontype2 == W_FIST) - ATK_ADD(10*pc->checkskill(sd, TK_RUN)); - break; - case GS_MAGICALBULLET: - if(sstatus->matk_max>sstatus->matk_min) { - ATK_ADD(sstatus->matk_min+rnd()%(sstatus->matk_max-sstatus->matk_min)); - } else { - ATK_ADD(sstatus->matk_min); - } - break; - case NJ_SYURIKEN: - ATK_ADD(4*skill_lv); - break; + if (!flag.infdef) //No need to do the math for plants + { #ifdef RENEWAL - case NJ_ISSEN: - // Damage = (current HP + atk * skill_lv) - (sdef+edef) - ATK_ADD(sstatus->hp); - wd.damage2 = 0;// needs more info if this really 0 for dual weilding KG/OB. [malufett] - if( sc && sc->data[SC_BUNSINJYUTSU] && (i=sc->data[SC_BUNSINJYUTSU]->val2) > 0){ - wd.div_ = -( i + 2 ); // mirror image number of hits + 2 - ATK_ADDRATE(20 + i*20); // (20 + 20 * mirror image) % - } - break; + ad.damage = 0; //reinitialize.. #endif - case HT_FREEZINGTRAP: - if(sd) - ATK_ADD( 40 * pc->checkskill(sd, RA_RESEARCHTRAP) ); - break; - case RA_WUGDASH ://(Caster Current Weight x 10 / 8) - if( sd && sd->weight ) - ATK_ADD( sd->weight / 8 ); - case RA_WUGSTRIKE: - case RA_WUGBITE: - if(sd) - ATK_ADD(30*pc->checkskill(sd, RA_TOOTHOFWUG)); - break; - case SR_GATEOFHELL: - ATK_ADD (sstatus->max_hp - status_get_hp(src)); - if(sc && sc->data[SC_COMBO] && sc->data[SC_COMBO]->val1 == SR_FALLENEMPIRE){ - ATK_ADD ( (sstatus->max_sp * (1 + skill_lv * 2 / 10)) + 40 * status_get_lv(src) ); - }else{ - ATK_ADD ( (sstatus->sp * (1 + skill_lv * 2 / 10)) + 10 * status_get_lv(src) ); - } - break; - case SR_TIGERCANNON: // (Tiger Cannon skill level x 240) + (Target Base Level x 40) - ATK_ADD( skill_lv * 240 + status_get_lv(target) * 40 ); - if( sc && sc->data[SC_COMBO] - && sc->data[SC_COMBO]->val1 == SR_FALLENEMPIRE ) // (Tiger Cannon skill level x 500) + (Target Base Level x 40) - ATK_ADD( skill_lv * 500 + status_get_lv(target) * 40 ); - break; - case SR_FALLENEMPIRE:// [(Target Size value + Skill Level - 1) x Caster STR] + [(Target current weight x Caster DEX / 120)] - ATK_ADD( ((tstatus->size+1)*2 + skill_lv - 1) * sstatus->str); - if( tsd && tsd->weight ){ - ATK_ADD( (tsd->weight/10) * sstatus->dex / 120 ); - }else{ - ATK_ADD( status_get_lv(target) * 50 ); //mobs - } - break; - case KO_SETSUDAN: - if( tsc && tsc->data[SC_SPIRIT] ){ - ATK_ADDRATE(10*tsc->data[SC_SPIRIT]->val1);// +10% custom value. - status_change_end(target,SC_SPIRIT,INVALID_TIMER); - } - break; - case KO_KAIHOU: - if( sd ){ - ARR_FIND(1, 6, i, sd->talisman[i] > 0); - if( i < 5 ){ - s_ele = i; - ATK_ADDRATE(100 * sd->talisman[i]);// +100% custom value. - pc->del_talisman(sd, sd->talisman[i], i); +//MATK_RATE scales the damage. 100 = no change. 50 is halved, 200 is doubled, etc +#define MATK_RATE( a ) { ad.damage= ad.damage*(a)/100; } +//Adds dmg%. 100 = +100% (double) damage. 10 = +10% damage +#define MATK_ADDRATE( a ) { ad.damage+= ad.damage*(a)/100; } +//Adds an absolute value to damage. 100 = +100 damage +#define MATK_ADD( a ) { ad.damage+= a; } + + switch (skill_id) + { //Calc base damage according to skill + case AL_HEAL: + case PR_BENEDICTIO: + case PR_SANCTUARY: + /** + * Arch Bishop + **/ + case AB_HIGHNESSHEAL: + ad.damage = skill->calc_heal(src, target, skill_id, skill_lv, false); + break; + case PR_ASPERSIO: + ad.damage = 40; + break; + case ALL_RESURRECTION: + case PR_TURNUNDEAD: + //Undead check is on skill_castend_damageid code. + i = 20*skill_lv + sstatus->luk + sstatus->int_ + status_get_lv(src) + + 200 - 200*tstatus->hp/tstatus->max_hp; // there is no changed in success chance in renewal. [malufett] + if(i > 700) i = 700; + if(rnd()%1000 < i && !(tstatus->mode&MD_BOSS)) + ad.damage = tstatus->hp; + else { + #ifdef RENEWAL + MATK_ADD(status_get_matk(src, 2)); + #else + ad.damage = status_get_lv(src) + sstatus->int_ + skill_lv * 10; + #endif + } + break; + case PF_SOULBURN: + ad.damage = tstatus->sp * 2; + break; + /** + * Arch Bishop + **/ + case AB_RENOVATIO: + //Damage calculation from iRO wiki. [Jobbie] + ad.damage = (int)((15 * status_get_lv(src)) + (1.5 * sstatus->int_)); + break; + default: { + MATK_ADD( status_get_matk(src, 2) ); + + if (nk&NK_SPLASHSPLIT) { // Divide MATK in case of multiple targets skill + if(mflag>0) + ad.damage/= mflag; + else + ShowError("0 enemies targeted by %d:%s, divide per 0 avoided!\n", skill_id, skill->get_name(skill_id)); + } + + if (sc){ + if( sc->data[SC_TELEKINESIS_INTENSE] && s_ele == ELE_GHOST ) + skillratio += sc->data[SC_TELEKINESIS_INTENSE]->val3; + } + switch(skill_id){ + case MG_FIREBOLT: + case MG_COLDBOLT: + case MG_LIGHTNINGBOLT: + if ( sc && sc->data[SC_SPELLFIST] && mflag&BF_SHORT ) { + skillratio += (sc->data[SC_SPELLFIST]->val4 * 100) + (sc->data[SC_SPELLFIST]->val2 * 100) - 100;// val4 = used bolt level, val2 = used spellfist level. [Rytech] + ad.div_ = 1;// ad mods, to make it work similar to regular hits [Xazax] + ad.flag = BF_WEAPON|BF_SHORT; + ad.type = 0; } + break; + default: + MATK_RATE(battle->calc_skillratio(BF_MAGIC, src, target, skill_id, skill_lv, skillratio, mflag)); + } + //Constant/misc additions from skills + if (skill_id == WZ_FIREPILLAR) + MATK_ADD(50); + if( sd && (i=pc->checkskill(sd,AB_EUCHARISTICA)) > 0 && + (tstatus->race == RC_DEMON || tstatus->def_ele == ELE_DARK) ) + MATK_ADDRATE(i); + } + } +#ifndef HMAP_ZONE_DAMAGE_CAP_TYPE + if( target && skill_id ) { + for(i = 0; i < map[target->m].zone->capped_skills_count; i++) { + if( skill_id == map[target->m].zone->capped_skills[i]->nameid && (map[target->m].zone->capped_skills[i]->type & target->type) ) { + if( target->type == BL_MOB && map[target->m].zone->capped_skills[i]->subtype != MZS_NONE ) { + if( (((TBL_MOB*)target)->status.mode&MD_BOSS) && !(map[target->m].zone->disabled_skills[i]->subtype&MZS_BOSS) ) + continue; + if( ((TBL_MOB*)target)->special_state.clone && !(map[target->m].zone->disabled_skills[i]->subtype&MZS_CLONE) ) + continue; } + if( ad.damage > map[target->m].zone->capped_skills[i]->cap ) + ad.damage = map[target->m].zone->capped_skills[i]->cap; + if( ad.damage2 > map[target->m].zone->capped_skills[i]->cap ) + ad.damage2 = map[target->m].zone->capped_skills[i]->cap; break; + } } } - //Div fix. - damage_div_fix(wd.damage, wd.div_); - - //The following are applied on top of current damage and are stackable. - if ( sc ) { -#ifndef RENEWAL - if( sc->data[SC_TRUESIGHT] ) - ATK_ADDRATE(2*sc->data[SC_TRUESIGHT]->val1); #endif - if( sc->data[SC_GLOOMYDAY_SK] && - ( skill_id == LK_SPIRALPIERCE || skill_id == KN_BRANDISHSPEAR || - skill_id == CR_SHIELDBOOMERANG || skill_id == PA_SHIELDCHAIN || - skill_id == LG_SHIELDPRESS ) ) - ATK_ADDRATE(sc->data[SC_GLOOMYDAY_SK]->val2); - if( sc->data[SC_EDP] ){ - switch(skill_id){ - case AS_SPLASHER: case AS_VENOMKNIFE: -#ifndef RENEWAL_EDP - case AS_GRIMTOOTH: +#ifdef RENEWAL + ad.damage = battle->calc_cardfix(BF_MAGIC, src, target, nk, s_ele, 0, ad.damage, 0, ad.flag); #endif + if(sd) { + //Damage bonuses + if ((i = pc->skillatk_bonus(sd, skill_id))) + ad.damage += ad.damage*i/100; + + if( (i = battle->adjust_skill_damage(src->m,skill_id)) ) + MATK_RATE(i); + + //Ignore Defense? + if (!flag.imdef && ( + sd->bonus.ignore_mdef_ele & ( 1 << tstatus->def_ele ) || + sd->bonus.ignore_mdef_race & ( 1 << tstatus->race ) || + sd->bonus.ignore_mdef_race & ( is_boss(target) ? 1 << RC_BOSS : 1 << RC_NONBOSS ) + )) + flag.imdef = 1; + } + + ad.damage = battle->calc_defense(BF_MAGIC, src, target, skill_id, skill_lv, ad.damage, (flag.imdef?1:0), 0); + + if (skill_id == NPC_EARTHQUAKE) + { //Adds atk2 to the damage, should be influenced by number of hits and skill-ratio, but not mdef reductions. [Skotlex] + //Also divide the extra bonuses from atk2 based on the number in range [Kevin] + if(mflag>0) + ad.damage+= (sstatus->rhw.atk2*skillratio/100)/mflag; + else + ShowError("Zero range by %d:%s, divide per 0 avoided!\n", skill_id, skill->get_name(skill_id)); + } + + if(ad.damage<1) + ad.damage=1; + else if(sc){//only applies when hit + // TODO: there is another factor that contribute with the damage and need to be formulated. [malufett] + switch(skill_id){ + case MG_LIGHTNINGBOLT: + case MG_THUNDERSTORM: + case MG_FIREBOLT: + case MG_FIREWALL: + case MG_COLDBOLT: + case MG_FROSTDIVER: + case WZ_EARTHSPIKE: + case WZ_HEAVENDRIVE: + if(sc->data[SC_GUST_OPTION] || sc->data[SC_PETROLOGY_OPTION] + || sc->data[SC_PYROTECHNIC_OPTION] || sc->data[SC_AQUAPLAY_OPTION]) + ad.damage += (6 + sstatus->int_/4) + max(sstatus->dex-10,0)/30; break; -#ifndef RENEWAL_EDP - case ASC_BREAKER: case ASC_METEORASSAULT: break; -#else - case AS_SONICBLOW: - case ASC_BREAKER: - case GC_COUNTERSLASH: - case GC_CROSSIMPACT: - ATK_RATE(50); // only modifier is halved but still benefit with the damage bonus -#endif - default: - ATK_ADDRATE(sc->data[SC_EDP]->val3); - } } - if(sc->data[SC_STYLE_CHANGE]){ - TBL_HOM *hd = BL_CAST(BL_HOM,src); - if (hd) ATK_ADD(hd->homunculus.spiritball * 3); - } } - switch (skill_id) { - case AS_SONICBLOW: - if (sc && sc->data[SC_SPIRIT] && - sc->data[SC_SPIRIT]->val2 == SL_ASSASIN) - ATK_ADDRATE(map_flag_gvg(src->m)?25:100); //+25% dmg on woe/+100% dmg on nonwoe + if (!(nk&NK_NO_ELEFIX)) + ad.damage=battle->attr_fix(src, target, ad.damage, s_ele, tstatus->def_ele, tstatus->ele_lv); - if(sd && pc->checkskill(sd,AS_SONICACCEL)>0) - ATK_ADDRATE(10); - break; - case CR_SHIELDBOOMERANG: - if(sc && sc->data[SC_SPIRIT] && - sc->data[SC_SPIRIT]->val2 == SL_CRUSADER) - ATK_ADDRATE(100); - break; - case NC_AXETORNADO: - if( (sstatus->rhw.ele) == ELE_WIND || (sstatus->lhw.ele) == ELE_WIND ) - ATK_ADDRATE(50); - break; + if( skill_id == CR_GRANDCROSS || skill_id == NPC_GRANDDARKNESS ) + { //Apply the physical part of the skill's damage. [Skotlex] + struct Damage wd = battle->calc_weapon_attack(src,target,skill_id,skill_lv,mflag); + ad.damage = battle->attr_fix(src, target, wd.damage + ad.damage, s_ele, tstatus->def_ele, tstatus->ele_lv) * (100 + 40*skill_lv)/100; + if( src == target ) + { + if( src->type == BL_PC ) + ad.damage = ad.damage/2; + else + ad.damage = 0; + } } - if( (i = battle->adjust_skill_damage(src->m,skill_id)) ) - ATK_RATE(i); - - if( sd ) { - if (skill_id && (i = pc->skillatk_bonus(sd, skill_id))) - ATK_ADDRATE(i); - - if( skill_id != PA_SACRIFICE && skill_id != MO_INVESTIGATE && skill_id != CR_GRANDCROSS && skill_id != NPC_GRANDDARKNESS && skill_id != PA_SHIELDCHAIN && !flag.cri ) - { //Elemental/Racial adjustments - if( sd->right_weapon.def_ratio_atk_ele & (1<def_ele) || - sd->right_weapon.def_ratio_atk_race & (1<race) || - sd->right_weapon.def_ratio_atk_race & (1<<(is_boss(target)?RC_BOSS:RC_NONBOSS)) - ) - flag.pdef = 1; +#ifndef RENEWAL + ad.damage = battle->calc_cardfix(BF_MAGIC, src, target, nk, s_ele, 0, ad.damage, 0, ad.flag); +#endif + } - if( sd->left_weapon.def_ratio_atk_ele & (1<def_ele) || - sd->left_weapon.def_ratio_atk_race & (1<race) || - sd->left_weapon.def_ratio_atk_race & (1<<(is_boss(target)?RC_BOSS:RC_NONBOSS)) - ) - { //Pass effect onto right hand if configured so. [Skotlex] - if (battle_config.left_cardfix_to_right && flag.rh) - flag.pdef = 1; - else - flag.pdef2 = 1; - } - } + damage_div_fix(ad.damage, ad.div_); - if (skill_id != CR_GRANDCROSS && skill_id != NPC_GRANDDARKNESS) - { //Ignore Defense? - if (!flag.idef && ( - sd->right_weapon.ignore_def_ele & (1<def_ele) || - sd->right_weapon.ignore_def_race & (1<race) || - sd->right_weapon.ignore_def_race & (is_boss(target)?1<0?1:-1; - if (!flag.idef2 && ( - sd->left_weapon.ignore_def_ele & (1<def_ele) || - sd->left_weapon.ignore_def_race & (1<race) || - sd->left_weapon.ignore_def_race & (is_boss(target)?1<calc_damage(src,target,&ad,ad.damage,skill_id,skill_lv); + if( map_flag_gvg2(target->m) ) + ad.damage=battle->calc_gvg_damage(src,target,ad.damage,ad.div_,skill_id,skill_lv,ad.flag); + else if( map[target->m].flag.battleground ) + ad.damage=battle->calc_bg_damage(src,target,ad.damage,ad.div_,skill_id,skill_lv,ad.flag); + + switch( skill_id ) { /* post-calc modifiers */ + case SO_VARETYR_SPEAR: { // Physical damage. + struct Damage wd = battle->calc_weapon_attack(src,target,skill_id,skill_lv,mflag); + if(!flag.infdef && ad.damage > 1) + ad.damage += wd.damage; + break; } + //case HM_ERASER_CUTTER: + } + + return ad; +} + +/*========================================== + * Calculate Misc dammage for skill_id + *------------------------------------------*/ +struct Damage battle_calc_misc_attack(struct block_list *src,struct block_list *target,uint16 skill_id,uint16 skill_lv,int mflag) { + int temp; + short i, nk; + short s_ele; + + struct map_session_data *sd, *tsd; + struct Damage md; //DO NOT CONFUSE with md of mob_data! + struct status_data *sstatus = status_get_status_data(src); + struct status_data *tstatus = status_get_status_data(target); + struct status_change *tsc = status_get_sc(target); + struct status_change *sc = status_get_sc(src); + + memset(&md,0,sizeof(md)); + + if( src == NULL || target == NULL ){ + nullpo_info(NLP_MARK); + return md; + } + + //Some initial values + md.amotion=skill->get_inf(skill_id)&INF_GROUND_SKILL?0:sstatus->amotion; + md.dmotion=tstatus->dmotion; + md.div_=skill->get_num( skill_id,skill_lv ); + md.blewcount=skill->get_blewcount(skill_id,skill_lv); + md.dmg_lv=ATK_DEF; + md.flag=BF_MISC|BF_SKILL; + + nk = skill->get_nk(skill_id); - if (!flag.idef || !flag.idef2) - { //Defense reduction - short vit_def; - defType def1 = status_get_def(target); //Don't use tstatus->def1 due to skill timer reductions. - short def2 = tstatus->def2; -#ifdef RENEWAL - if( tsc && tsc->data[SC_ASSUMPTIO] ) - def1 <<= 1; // only eDEF is doubled -#endif - if( sd ) - { - i = sd->ignore_def[is_boss(target)?RC_BOSS:RC_NONBOSS]; - i += sd->ignore_def[tstatus->race]; - if( i ) - { - if( i > 100 ) i = 100; - def1 -= def1 * i / 100; - def2 -= def2 * i / 100; - } - } + sd = BL_CAST(BL_PC, src); + tsd = BL_CAST(BL_PC, target); - if( sc && sc->data[SC_EXPIATIO] ){ - i = 5 * sc->data[SC_EXPIATIO]->val1; // 5% per level - def1 -= def1 * i / 100; - def2 -= def2 * i / 100; - } + if(sd) { + sd->state.arrow_atk = 0; + md.blewcount += battle->blewcount_bonus(sd, skill_id); + } - if( tsc && tsc->data[SC_GT_REVITALIZE] && tsc->data[SC_GT_REVITALIZE]->val4 ) - def2 += 2 * tsc->data[SC_GT_REVITALIZE]->val4; + s_ele = skill->get_ele(skill_id, skill_lv); + if (s_ele < 0 && s_ele != -3) //Attack that takes weapon's element for misc attacks? Make it neutral [Skotlex] + s_ele = ELE_NEUTRAL; + else if (s_ele == -3) //Use random element + s_ele = rnd()%ELE_MAX; - if( tsc && tsc->data[SC_CAMOUFLAGE] ){ - i = 5 * (10-tsc->data[SC_CAMOUFLAGE]->val4); - def1 -= def1 * i / 100; - def2 -= def2 * i / 100; - } + //Skill Range Criteria + md.flag |= battle->range_type(src, target, skill_id, skill_lv); - if( battle_config.vit_penalty_type && battle_config.vit_penalty_target&target->type ) { - unsigned char target_count; //256 max targets should be a sane max - target_count = unit_counttargeted(target); - if(target_count >= battle_config.vit_penalty_count) { - if(battle_config.vit_penalty_type == 1) { - if( !tsc || !tsc->data[SC_STEELBODY] ) - def1 = (def1 * (100 - (target_count - (battle_config.vit_penalty_count - 1))*battle_config.vit_penalty_num))/100; - def2 = (def2 * (100 - (target_count - (battle_config.vit_penalty_count - 1))*battle_config.vit_penalty_num))/100; - } else { //Assume type 2 - if( !tsc || !tsc->data[SC_STEELBODY] ) - def1 -= (target_count - (battle_config.vit_penalty_count - 1))*battle_config.vit_penalty_num; - def2 -= (target_count - (battle_config.vit_penalty_count - 1))*battle_config.vit_penalty_num; - } - } - if(skill_id == AM_ACIDTERROR) def1 = 0; //Acid Terror ignores only armor defense. [Skotlex] - if(def2 < 1) def2 = 1; - } - //Vitality reduction from rodatazone: http://rodatazone.simgaming.net/mechanics/substats.php#def - if (tsd) //Sd vit-eq - { -#ifndef RENEWAL - //[VIT*0.5] + rnd([VIT*0.3], max([VIT*0.3],[VIT^2/150]-1)) - vit_def = def2*(def2-15)/150; - vit_def = def2/2 + (vit_def>0?rnd()%vit_def:0); -#else - vit_def = def2; -#endif - if((battle->check_undead(sstatus->race,sstatus->def_ele) || sstatus->race==RC_DEMON) && //This bonus already doesnt work vs players - src->type == BL_MOB && (temp=pc->checkskill(tsd,AL_DP)) > 0) - vit_def += temp*(int)(3 +(tsd->status.base_level+1)*0.04); // submitted by orn - if( src->type == BL_MOB && (temp=pc->checkskill(tsd,RA_RANGERMAIN))>0 && - (sstatus->race == RC_BRUTE || sstatus->race == RC_FISH || sstatus->race == RC_PLANT) ) - vit_def += temp*5; + switch( skill_id ) + { #ifdef RENEWAL - if( temp == NJ_ISSEN ){//TODO: do better implementation if other skills(same func) are found [malufett] - vit_def += def1; - def1 = 0; - } -#endif - } - else { //Mob-Pet vit-eq -#ifndef RENEWAL - //VIT + rnd(0,[VIT/20]^2-1) - vit_def = (def2/20)*(def2/20); - vit_def = def2 + (vit_def>0?rnd()%vit_def:0); + case HT_LANDMINE: + case MA_LANDMINE: + case HT_BLASTMINE: + case HT_CLAYMORETRAP: + md.damage = skill_lv * sstatus->dex * (3+status_get_lv(src)/100) * (1+sstatus->int_/35); + md.damage += md.damage * (rnd()%20-10) / 100; + md.damage += 40 * (sd?pc->checkskill(sd,RA_RESEARCHTRAP):0); + break; #else - vit_def = def2; + case HT_LANDMINE: + case MA_LANDMINE: + md.damage=skill_lv*(sstatus->dex+75)*(100+sstatus->int_)/100; + break; + case HT_BLASTMINE: + md.damage=skill_lv*(sstatus->dex/2+50)*(100+sstatus->int_)/100; + break; + case HT_CLAYMORETRAP: + md.damage=skill_lv*(sstatus->dex/2+75)*(100+sstatus->int_)/100; + break; #endif - } + case HT_BLITZBEAT: + case SN_FALCONASSAULT: + //Blitz-beat Damage. + if(!sd || (temp = pc->checkskill(sd,HT_STEELCROW)) <= 0) + temp=0; + md.damage=(sstatus->dex/10+sstatus->int_/2+temp*3+40)*2; + if(mflag > 1) //Autocasted Blitz. + nk|=NK_SPLASHSPLIT; + if (skill_id == SN_FALCONASSAULT) { + //Div fix of Blitzbeat + temp = skill->get_num(HT_BLITZBEAT, 5); + damage_div_fix(md.damage, temp); - if (battle_config.weapon_defense_type) { - vit_def += def1*battle_config.weapon_defense_type; - def1 = 0; + //Falcon Assault Modifier + md.damage=md.damage*(150+70*skill_lv)/100; + } + break; + case TF_THROWSTONE: + md.damage=50; + break; + case BA_DISSONANCE: + md.damage=30+skill_lv*10; + if (sd) + md.damage+= 3*pc->checkskill(sd,BA_MUSICALLESSON); + break; + case NPC_SELFDESTRUCTION: + md.damage = sstatus->hp; + break; + case NPC_SMOKING: + md.damage=3; + break; + case NPC_DARKBREATH: + md.damage = 500 + (skill_lv-1)*1000 + rnd()%1000; + if(md.damage > 9999) md.damage = 9999; + break; + case PA_PRESSURE: + md.damage=500+300*skill_lv; + break; + case PA_GOSPEL: + md.damage = 1+rnd()%9999; + break; + case CR_ACIDDEMONSTRATION: +#ifdef RENEWAL + {// [malufett] + int matk=0, atk; + short tdef = status_get_total_def(target); + short tmdef = status_get_total_mdef(target); + int targetVit = min(120, status_get_vit(target)); + short totaldef = (tmdef + tdef - ((unsigned _int64)(tmdef + tdef) >> 32)) >> 1; + + matk = battle->calc_magic_attack(src, target, skill_id, skill_lv, mflag).damage; + atk = battle->calc_base_damage(src, target, skill_id, skill_lv, nk, false, s_ele, ELE_NEUTRAL, EQI_HAND_R, (sc && sc->data[SC_MAXIMIZEPOWER]?1:0)|(sc && sc->data[SC_WEAPONPERFECT]?8:0), md.flag); + md.damage = matk + atk; + if( src->type == BL_MOB ){ + totaldef = (tdef + tmdef) >> 1; + md.damage = 7 * targetVit * skill_lv * (atk + matk) / 100; + /* + // Pending [malufett] + if( unknown condition ) + md.damage >>= 1; + if( unknown condition ){ + md.damage = 7 * md.damage % 20; + md.damage = 7 * md.damage / 20; + }*/ + }else{ + float vitfactor = 0.0f, temp; + + if( (vitfactor=(status_get_vit(target)-120.0f)) > 0) + vitfactor = (vitfactor * (matk + atk) / 10) / status_get_vit(target); + temp = max(0, vitfactor) + (targetVit * (matk + atk)) / 10; + md.damage = (int)(temp * 70 * skill_lv / 100); } - #ifdef RENEWAL - /** - * RE DEF Reduction - * Damage = Attack * (4000+eDEF)/(4000+eDEF) - sDEF - * Pierce defence gains 1 atk per def/2 - **/ - - if( def1 == -400 ) /* being hit by a gazillion units, you hit the jackpot and got -400 which creates a division by 0 and subsequently crashes */ - def1 = -399; - - ATK_ADD2( - flag.pdef ?(def1/2):0, - flag.pdef2?(def1/2):0 - ); - if( !flag.idef && !flag.pdef ) - wd.damage = wd.damage * (4000+def1) / (4000+10*def1) - vit_def; - if( flag.lh && !flag.idef2 && !flag.pdef2 ) - wd.damage2 = wd.damage2 * (4000+def1) / (4000+10*def1) - vit_def; - - #else - if (def1 > 100) def1 = 100; - ATK_RATE2( - flag.idef ?100:(flag.pdef ? flag.pdef*(def1+vit_def) : (100-def1)), - flag.idef2?100:(flag.pdef2? flag.pdef2*(def1+vit_def) : (100-def1)) - ); - ATK_ADD2( - flag.idef ||flag.pdef ?0:-vit_def, - flag.idef2||flag.pdef2?0:-vit_def - ); - #endif + md.damage -= totaldef; } +#else + // updated the formula based on a Japanese formula found to be exact [Reddozen] + if(tstatus->vit+sstatus->int_) //crash fix + md.damage = (int)(7*tstatus->vit*sstatus->int_*sstatus->int_ / (10*(tstatus->vit+sstatus->int_))); + else + md.damage = 0; + if (tsd) md.damage>>=1; +#endif + if (md.damage < 0 || md.damage > INT_MAX>>1) + //Overflow prevention, will anyone whine if I cap it to a few billion? + //Not capped to INT_MAX to give some room for further damage increase. + md.damage = INT_MAX>>1; + break; - //Post skill/vit reduction damage increases - if( sc ) - { //SC skill damages - if(sc->data[SC_AURABLADE] + case KO_MUCHANAGE: + md.damage = skill->get_zeny(skill_id ,skill_lv); + md.damage = md.damage * (50 + rand()%50) / 100; + if ( is_boss(target) || (sd && !pc->checkskill(sd,NJ_TOBIDOUGU)) ) + md.damage >>= 1; + break; + case NJ_ZENYNAGE: + md.damage = skill->get_zeny(skill_id ,skill_lv); + if (!md.damage) md.damage = 2; + md.damage = rand()%md.damage + md.damage; + if (is_boss(target)) + md.damage=md.damage / 3; + else if (tsd) + md.damage=md.damage / 2; + break; + case GS_FLING: + md.damage = sd?sd->status.job_level:status_get_lv(src); + break; + case HVAN_EXPLOSION: //[orn] + md.damage = sstatus->max_hp * (50 + 50 * skill_lv) / 100; + break ; + case ASC_BREAKER: + { #ifndef RENEWAL - && skill_id != LK_SPIRALPIERCE && skill_id != ML_SPIRALPIERCE -#endif - ){ - int lv = sc->data[SC_AURABLADE]->val1; -#ifdef RENEWAL - lv *= ((skill_id == LK_SPIRALPIERCE || skill_id == ML_SPIRALPIERCE)?wd.div_:1); // +100 per hit in lv 5 + md.damage = 500+rnd()%500 + 5*skill_lv * sstatus->int_; + nk|=NK_IGNORE_FLEE|NK_NO_ELEFIX; //These two are not properties of the weapon based part. +#else + int ratio = 300 + 50 * skill_lv; + int matk = battle->calc_magic_attack(src, target, skill_id, skill_lv, mflag).damage; + short totaldef = status_get_total_def(target) + status_get_total_mdef(target); + int atk = battle->calc_base_damage(src, target, skill_id, skill_lv, nk, false, s_ele, ELE_NEUTRAL, EQI_HAND_R, (sc && sc->data[SC_MAXIMIZEPOWER]?1:0)|(sc && sc->data[SC_WEAPONPERFECT]?8:0), md.flag); + + if( sc && sc->data[SC_EDP] ) + ratio >>= 1; + md.damage = (matk + atk) * ratio / 100; + md.damage -= totaldef; #endif - ATK_ADD(20*lv); - } - - if(sc->data[SC_GN_CARTBOOST]) - ATK_ADD(10*sc->data[SC_GN_CARTBOOST]->val1); - - if(sc->data[SC_GT_CHANGE] && sc->data[SC_GT_CHANGE]->val2){ - struct block_list *bl; // ATK increase: ATK [{(Caster DEX / 4) + (Caster STR / 2)} x Skill Level / 5] - if( (bl = iMap->id2bl(sc->data[SC_GT_CHANGE]->val2)) ) - ATK_ADD( ( status_get_dex(bl)/4 + status_get_str(bl)/2 ) * sc->data[SC_GT_CHANGE]->val1 / 5 ); - } - - if(sc->data[SC_CAMOUFLAGE]) - ATK_ADD(30 * (10-sc->data[SC_CAMOUFLAGE]->val4) ); } + break; + case HW_GRAVITATION: + md.damage = 200+200*skill_lv; + md.dmotion = 0; //No flinch animation. + break; + case NPC_EVILLAND: + md.damage = skill->calc_heal(src,target,skill_id,skill_lv,false); + break; + case RK_DRAGONBREATH: + case RK_DRAGONBREATH_WATER: + md.damage = ((status_get_hp(src) / 50) + (status_get_max_sp(src) / 4)) * skill_lv; + RE_LVL_MDMOD(150); + if (sd) md.damage = md.damage * (100 + 5 * (pc->checkskill(sd,RK_DRAGONTRAINING) - 1)) / 100; + md.flag |= BF_LONG|BF_WEAPON; + break; + /** + * Ranger + **/ + case RA_CLUSTERBOMB: + case RA_FIRINGTRAP: + case RA_ICEBOUNDTRAP: + md.damage = skill_lv * sstatus->dex + sstatus->int_ * 5 ; + RE_LVL_TMDMOD(); + if(sd) + { + int researchskill_lv = pc->checkskill(sd,RA_RESEARCHTRAP); + if(researchskill_lv) + md.damage = md.damage * 20 * researchskill_lv / (skill_id == RA_CLUSTERBOMB?50:100); + else + md.damage = 0; + }else + md.damage = md.damage * 200 / (skill_id == RA_CLUSTERBOMB?50:100); - //Refine bonus - if( sd && flag.weapon && skill_id != MO_INVESTIGATE && skill_id != MO_EXTREMITYFIST ) - { // Counts refine bonus multiple times - if( skill_id == MO_FINGEROFFENSIVE ) - { - ATK_ADD2(wd.div_*sstatus->rhw.atk2, wd.div_*sstatus->lhw.atk2); - } else { - ATK_ADD2(sstatus->rhw.atk2, sstatus->lhw.atk2); - } + break; + /** + * Mechanic + **/ + case NC_SELFDESTRUCTION: + { + short totaldef = status_get_total_def(target); + md.damage = ( (sd?pc->checkskill(sd,NC_MAINFRAME):10) + 8 ) * ( skill_lv + 1 ) * ( status_get_sp(src) + sstatus->vit ); + RE_LVL_MDMOD(100); + md.damage += status_get_hp(src) - totaldef; + } + break; + case NC_MAGMA_ERUPTION: + md.damage = 1200 + 400 * skill_lv; + break; + case GN_THORNS_TRAP: + md.damage = 100 + 200 * skill_lv + sstatus->int_; + break; + case GN_HELLS_PLANT_ATK: + //[{( Hell Plant Skill Level x Casters Base Level ) x 10 } + {( Casters INT x 7 ) / 2 } x { 18 + ( Casters Job Level / 4 )] x ( 5 / ( 10 - Summon Flora Skill Level )) + md.damage = ( skill_lv * status_get_lv(src) * 10 ) + ( sstatus->int_ * 7 / 2 ) * ( 18 + (sd?sd->status.job_level:0) / 4 ) * ( 5 / (10 - (sd?pc->checkskill(sd,AM_CANNIBALIZE):0)) ); + break; + case KO_HAPPOKUNAI: + { + struct Damage wd = battle->calc_weapon_attack(src,target,skill_id,skill_lv,mflag); + short totaldef = status_get_total_def(target); + md.damage = 3 * wd.damage * (5 + skill_lv) / 5; + md.damage -= totaldef; } + break; + } - //Set to min of 1 - if (flag.rh && wd.damage < 1) wd.damage = 1; - if (flag.lh && wd.damage2 < 1) wd.damage2 = 1; + if (nk&NK_SPLASHSPLIT){ // Divide ATK among targets + if(mflag>0) + md.damage/= mflag; + else + ShowError("0 enemies targeted by %d:%s, divide per 0 avoided!\n", skill_id, skill->get_name(skill_id)); + } - if (sd && flag.weapon && - skill_id != MO_INVESTIGATE && - skill_id != MO_EXTREMITYFIST && - skill_id != CR_GRANDCROSS) - { //Add mastery damage - if(skill_id != ASC_BREAKER && sd->status.weapon == W_KATAR && - (temp=pc->checkskill(sd,ASC_KATAR)) > 0) - { //Adv Katar Mastery is does not applies to ASC_BREAKER, - // but other masteries DO apply >_> - ATK_ADDRATE(10+ 2*temp); - } + damage_div_fix(md.damage, md.div_); - wd.damage = battle->add_mastery(sd,target,wd.damage,0); - if (flag.lh) - wd.damage2 = battle->add_mastery(sd,target,wd.damage2,1); + if (!(nk&NK_IGNORE_FLEE)) + { + i = 0; //Temp for "hit or no hit" + if(tsc && tsc->opt1 && tsc->opt1 != OPT1_STONEWAIT && tsc->opt1 != OPT1_BURNING) + i = 1; + else { + short + flee = tstatus->flee, +#ifdef RENEWAL + hitrate = 0; //Default hitrate +#else + hitrate = 80; //Default hitrate +#endif - if (sc && sc->data[SC_MIRACLE]) i = 2; //Star anger - else - ARR_FIND(0, MAX_PC_FEELHATE, i, t_class == sd->hate_mob[i]); - if (i < MAX_PC_FEELHATE && (temp=pc->checkskill(sd,sg_info[i].anger_id))) { - skillratio = sd->status.base_level + sstatus->dex + sstatus->luk; - if (i == 2) skillratio += sstatus->str; //Star Anger - if (temp<4) - skillratio /= 12-3*temp; - ATK_ADDRATE(skillratio); + if(battle_config.agi_penalty_type && battle_config.agi_penalty_target&target->type) { + unsigned char attacker_count; //256 max targets should be a sane max + attacker_count = unit_counttargeted(target); + if(attacker_count >= battle_config.agi_penalty_count) + { + if (battle_config.agi_penalty_type == 1) + flee = (flee * (100 - (attacker_count - (battle_config.agi_penalty_count - 1))*battle_config.agi_penalty_num))/100; + else //asume type 2: absolute reduction + flee -= (attacker_count - (battle_config.agi_penalty_count - 1))*battle_config.agi_penalty_num; + if(flee < 1) flee = 1; + } } - if (skill_id == NJ_SYURIKEN && (temp = pc->checkskill(sd,NJ_TOBIDOUGU)) > 0) { - ATK_ADD(3*temp); - } else if (skill_id == NJ_KUNAI) - ATK_ADD(60); - } - } //Here ends flag.hit section, the rest of the function applies to both hitting and missing attacks - else if(wd.div_ < 0) //Since the attack missed... - wd.div_ *= -1; - - if(sd && (temp=pc->checkskill(sd,BS_WEAPONRESEARCH)) > 0) - ATK_ADD(temp*2); - if(skill_id==TF_POISON) - ATK_ADD(15*skill_lv); + hitrate+= sstatus->hit - flee; +#ifdef RENEWAL + if( sd ) //in Renewal hit bonus from Vultures Eye is not anymore shown in status window + hitrate += pc->checkskill(sd,AC_VULTURE); +#endif + if( skill_id == KO_MUCHANAGE ) + hitrate = (int)((10 - ((float)1 / (status_get_dex(src) + status_get_luk(src))) * 500) * ((float)skill_lv / 2 + 5)); + + hitrate = cap_value(hitrate, battle_config.min_hitrate, battle_config.max_hitrate); - if( !(nk&NK_NO_ELEFIX) && !n_ele ) - { //Elemental attribute fix - if( wd.damage > 0 ) - { - wd.damage=battle->attr_fix(src,target,wd.damage,s_ele,tstatus->def_ele, tstatus->ele_lv); - if( skill_id == MC_CARTREVOLUTION ) //Cart Revolution applies the element fix once more with neutral element - wd.damage = battle->attr_fix(src,target,wd.damage,ELE_NEUTRAL,tstatus->def_ele, tstatus->ele_lv); - if( skill_id== GS_GROUNDDRIFT ) //Additional 50*lv Neutral damage. - wd.damage += battle->attr_fix(src,target,50*skill_lv,ELE_NEUTRAL,tstatus->def_ele, tstatus->ele_lv); - } - if( flag.lh && wd.damage2 > 0 ) - wd.damage2 = battle->attr_fix(src,target,wd.damage2,s_ele_,tstatus->def_ele, tstatus->ele_lv); - if( sc && sc->data[SC_WATK_ELEMENT] ) - { // Descriptions indicate this means adding a percent of a normal attack in another element. [Skotlex] - int damage = battle->calc_base_damage(sstatus, &sstatus->rhw, sc, tstatus->size, sd, (flag.arrow?2:0)) * sc->data[SC_WATK_ELEMENT]->val2 / 100; - wd.damage += battle->attr_fix(src, target, damage, sc->data[SC_WATK_ELEMENT]->val1, tstatus->def_ele, tstatus->ele_lv); - - if( flag.lh ) { - damage = battle->calc_base_damage(sstatus, &sstatus->lhw, sc, tstatus->size, sd, (flag.arrow?2:0)) * sc->data[SC_WATK_ELEMENT]->val2 / 100; - wd.damage2 += battle->attr_fix(src, target, damage, sc->data[SC_WATK_ELEMENT]->val1, tstatus->def_ele, tstatus->ele_lv); - } + if(rnd()%100 < hitrate) + i = 1; + } + if (!i) { + md.damage = 0; + md.dmg_lv=ATK_FLEE; } - #ifdef RENEWAL - /** - * In RE Shield Bommerang takes weapon element only for damage calculation, - * - resist calculation is always against neutral - **/ - if ( skill_id == CR_SHIELDBOOMERANG ) - s_ele = s_ele_ = ELE_NEUTRAL; - #endif } - - if(skill_id == CR_GRANDCROSS || skill_id == NPC_GRANDDARKNESS) - return wd; //Enough, rest is not needed. #ifndef HMAP_ZONE_DAMAGE_CAP_TYPE if( target && skill_id ) { for(i = 0; i < map[target->m].zone->capped_skills_count; i++) { @@ -3386,1107 +3790,970 @@ struct Damage battle_calc_weapon_attack(struct block_list *src,struct block_list if( ((TBL_MOB*)target)->special_state.clone && !(map[target->m].zone->disabled_skills[i]->subtype&MZS_CLONE) ) continue; } - if( wd.damage > map[target->m].zone->capped_skills[i]->cap ) - wd.damage = map[target->m].zone->capped_skills[i]->cap; - if( wd.damage2 > map[target->m].zone->capped_skills[i]->cap ) - wd.damage2 = map[target->m].zone->capped_skills[i]->cap; + if( md.damage > map[target->m].zone->capped_skills[i]->cap ) + md.damage = map[target->m].zone->capped_skills[i]->cap; + if( md.damage2 > map[target->m].zone->capped_skills[i]->cap ) + md.damage2 = map[target->m].zone->capped_skills[i]->cap; break; } } } #endif - if (sd) { - if (skill_id != CR_SHIELDBOOMERANG) //Only Shield boomerang doesn't takes the Star Crumbs bonus. - ATK_ADD2(wd.div_*sd->right_weapon.star, wd.div_*sd->left_weapon.star); - if (skill_id==MO_FINGEROFFENSIVE) { //The finger offensive spheres on moment of attack do count. [Skotlex] - ATK_ADD(wd.div_*sd->spiritball_old*3); - } else { - ATK_ADD(wd.div_*sd->spiritball*3); - } + md.damage = battle->calc_cardfix(BF_MISC, src, target, nk, s_ele, 0, md.damage, 0, md.flag); - //Card Fix, sd side - wd.damage = battle->calc_cardfix(BF_WEAPON, src, target, nk, s_ele, s_ele_, wd.damage, 2, wd.flag); - if( flag.lh ) - wd.damage2 = battle->calc_cardfix(BF_WEAPON, src, target, nk, s_ele, s_ele_, wd.damage2, 3, wd.flag); + if (sd && (i = pc->skillatk_bonus(sd, skill_id))) + md.damage += md.damage*i/100; + + if( (i = battle->adjust_skill_damage(src->m,skill_id)) ) + md.damage = md.damage * i / 100; + + if(md.damage < 0) + md.damage = 0; + else if(md.damage && tstatus->mode&MD_PLANT){ + switch(skill_id){ + case HT_LANDMINE: + case MA_LANDMINE: + case HT_BLASTMINE: + case HT_CLAYMORETRAP: + case RA_CLUSTERBOMB: #ifdef RENEWAL - if( flag.cri ) - ATK_ADDRATE(sd->bonus.crit_atk_rate>=100?sd->bonus.crit_atk_rate-60:40); + break; #endif - if( skill_id == CR_SHIELDBOOMERANG || skill_id == PA_SHIELDCHAIN ) - { //Refine bonus applies after cards and elements. - short index= sd->equip_index[EQI_HAND_L]; - if( index >= 0 && sd->inventory_data[index] && sd->inventory_data[index]->type == IT_ARMOR ) - ATK_ADD(10*sd->status.inventory[index].refine); + default: + md.damage = 1; } + }else if( target->type == BL_SKILL ){ + TBL_SKILL *su = (TBL_SKILL*)target; + if( su->group && (su->group->skill_id == WM_REVERBERATION || su->group->skill_id == WM_POEMOFNETHERWORLD) ) + md.damage = 1; } - //Card Fix, tsd side - if(tsd) //if player on player then it was already measured above - wd.damage = battle->calc_cardfix(BF_WEAPON, src, target, nk, s_ele, s_ele_, wd.damage, flag.lh, wd.flag); + if(!(nk&NK_NO_ELEFIX)) + md.damage=battle->attr_fix(src, target, md.damage, s_ele, tstatus->def_ele, tstatus->ele_lv); - if( flag.infdef ) { //Plants receive 1 damage when hit - short class_ = status_get_class(target); - if( flag.hit || wd.damage > 0 ) - wd.damage = wd.div_; // In some cases, right hand no need to have a weapon to increase damage - if( flag.lh && (flag.hit || wd.damage2 > 0) ) - wd.damage2 = wd.div_; - if( flag.hit && class_ == MOBID_EMPERIUM ) { - if(wd.damage2 > 0) { - wd.damage2 = battle->attr_fix(src,target,wd.damage2,s_ele_,tstatus->def_ele, tstatus->ele_lv); - wd.damage2 = battle->calc_gvg_damage(src,target,wd.damage2,wd.div_,skill_id,skill_lv,wd.flag); - } - else if(wd.damage > 0) { - wd.damage = battle->attr_fix(src,target,wd.damage,s_ele_,tstatus->def_ele, tstatus->ele_lv); - wd.damage = battle->calc_gvg_damage(src,target,wd.damage,wd.div_,skill_id,skill_lv,wd.flag); - } - return wd; - } - if( !(battle_config.skill_min_damage&1) ) - //Do not return if you are supposed to deal greater damage to plants than 1. [Skotlex] - return wd; - } + md.damage=battle->calc_damage(src,target,&md,md.damage,skill_id,skill_lv); + if( map_flag_gvg2(target->m) ) + md.damage=battle->calc_gvg_damage(src,target,md.damage,md.div_,skill_id,skill_lv,md.flag); + else if( map[target->m].flag.battleground ) + md.damage=battle->calc_bg_damage(src,target,md.damage,md.div_,skill_id,skill_lv,md.flag); - if (sd) { - if (!flag.rh && flag.lh) { //Move lh damage to the rh - wd.damage = wd.damage2; - wd.damage2 = 0; - flag.rh=1; - flag.lh=0; - } else if(flag.rh && flag.lh) { //Dual-wield - if (wd.damage) { - if( (temp = pc->checkskill(sd,AS_RIGHT)) ) - ATK_RATER(50 + (temp * 10)) - else if( (temp = pc->checkskill(sd,KO_RIGHT)) ) - ATK_RATER(70 + (temp * 10)) - if(wd.damage < 1) wd.damage = 1; - } - if (wd.damage2) { - if( (temp = pc->checkskill(sd,AS_LEFT)) ) - ATK_RATEL(30 + (temp * 10)) - else if( (temp = pc->checkskill(sd,KO_LEFT)) ) - ATK_RATEL(50 + (temp * 10)) - if(wd.damage2 < 1) wd.damage2 = 1; + switch( skill_id ) { + case RA_FIRINGTRAP: + case RA_ICEBOUNDTRAP: + if( md.damage == 1 ) break; + case RA_CLUSTERBOMB: + { + struct Damage wd; + wd = battle->calc_weapon_attack(src,target,skill_id,skill_lv,mflag); + md.damage += wd.damage; } - } else if(sd->status.weapon == W_KATAR && !skill_id) { //Katars (offhand damage only applies to normal attacks, tested on Aegis 10.2) - temp = pc->checkskill(sd,TF_DOUBLE); - wd.damage2 = wd.damage * (1 + (temp * 2))/100; - - if(wd.damage && !wd.damage2) wd.damage2 = 1; - flag.lh = 1; - } - } - - if(!flag.rh && wd.damage) - wd.damage=0; - - if(!flag.lh && wd.damage2) - wd.damage2=0; - - if( wd.damage + wd.damage2 ) - { //There is a total damage value - if(!wd.damage2) - { - wd.damage = battle->calc_damage(src,target,&wd,wd.damage,skill_id,skill_lv); - if( map_flag_gvg2(target->m) ) - wd.damage=battle->calc_gvg_damage(src,target,wd.damage,wd.div_,skill_id,skill_lv,wd.flag); - else if( map[target->m].flag.battleground ) - wd.damage=battle->calc_bg_damage(src,target,wd.damage,wd.div_,skill_id,skill_lv,wd.flag); - } - else if(!wd.damage) - { - wd.damage2 = battle->calc_damage(src,target,&wd,wd.damage2,skill_id,skill_lv); - if( map_flag_gvg2(target->m) ) - wd.damage2 = battle->calc_gvg_damage(src,target,wd.damage2,wd.div_,skill_id,skill_lv,wd.flag); - else if( map[target->m].flag.battleground ) - wd.damage = battle->calc_bg_damage(src,target,wd.damage2,wd.div_,skill_id,skill_lv,wd.flag); - } - else - { - int d1 = wd.damage + wd.damage2,d2 = wd.damage2; - wd.damage = battle->calc_damage(src,target,&wd,d1,skill_id,skill_lv); - if( map_flag_gvg2(target->m) ) - wd.damage = battle->calc_gvg_damage(src,target,wd.damage,wd.div_,skill_id,skill_lv,wd.flag); - else if( map[target->m].flag.battleground ) - wd.damage = battle->calc_bg_damage(src,target,wd.damage,wd.div_,skill_id,skill_lv,wd.flag); - wd.damage2 = d2*100/d1 * wd.damage/100; - if(wd.damage > 1 && wd.damage2 < 1) wd.damage2 = 1; - wd.damage-=wd.damage2; - } - } - //Reject Sword bugreport:4493 by Daegaladh - if(wd.damage && tsc && tsc->data[SC_REJECTSWORD] && - (src->type!=BL_PC || ( - ((TBL_PC *)src)->weapontype1 == W_DAGGER || - ((TBL_PC *)src)->weapontype1 == W_1HSWORD || - ((TBL_PC *)src)->status.weapon == W_2HSWORD - )) && - rnd()%100 < tsc->data[SC_REJECTSWORD]->val2 - ) { - ATK_RATER(50) - status_fix_damage(target,src,wd.damage,clif->damage(target,src,iTimer->gettick(),0,0,wd.damage,0,0,0)); - clif->skill_nodamage(target,target,ST_REJECTSWORD,tsc->data[SC_REJECTSWORD]->val1,1); - if( --(tsc->data[SC_REJECTSWORD]->val3) <= 0 ) - status_change_end(target, SC_REJECTSWORD, INVALID_TIMER); - } - if(skill_id == ASC_BREAKER) { //Breaker's int-based damage (a misc attack?) - struct Damage md = battle->calc_misc_attack(src, target, skill_id, skill_lv, wflag); - wd.damage += md.damage; - } - if( sc ) { - //SG_FUSION hp penalty [Komurka] - if (sc->data[SC_FUSION]) { - int hp= sstatus->max_hp; - if (sd && tsd) { - hp = 8*hp/100; - if ((sstatus->hp * 100) <= (sstatus->max_hp * 20)) - hp = sstatus->hp; - } else - hp = 2*hp/100; //2% hp loss per hit - status_zap(src, hp, 0); - } - /** - * affecting non-skills - **/ - if( !skill_id ) { - /** - * RK Enchant Blade - **/ - if( sc->data[SC_ENCHANTBLADE] && sd && ( (flag.rh && sd->weapontype1) || (flag.lh && sd->weapontype2) ) ) { - //[( ( Skill Lv x 20 ) + 100 ) x ( casterBaseLevel / 150 )] + casterInt - ATK_ADD( ( sc->data[SC_ENCHANTBLADE]->val1*20+100 ) * status_get_lv(src) / 150 + status_get_int(src) ); + break; + case NJ_ZENYNAGE: + if( sd ) { + if ( md.damage > sd->status.zeny ) + md.damage = sd->status.zeny; + pc->payzeny(sd, md.damage,LOG_TYPE_STEAL,NULL); } - } - status_change_end(src,SC_CAMOUFLAGE, INVALID_TIMER); - } - if( skill_id == LG_RAYOFGENESIS ) { - struct Damage md = battle->calc_magic_attack(src, target, skill_id, skill_lv, wflag); - wd.damage += md.damage; + break; } - return wd; + return md; } /*========================================== - * battle_calc_magic_attack [DracoRPG] + * battle_calc_weapon_attack (by Skotlex) *------------------------------------------*/ -struct Damage battle_calc_magic_attack(struct block_list *src,struct block_list *target,uint16 skill_id,uint16 skill_lv,int mflag) { - int i, nk; - short s_ele = 0; +struct Damage battle_calc_weapon_attack(struct block_list *src,struct block_list *target,uint16 skill_id,uint16 skill_lv,int wflag) +{ unsigned int skillratio = 100; //Skill dmg modifiers. + short temp=0; + short s_ele, s_ele_, t_class; + int i, nk; + bool n_ele = false; // non-elemental - TBL_PC *sd; -// TBL_PC *tsd; - struct status_change *sc, *tsc; - struct Damage ad; + struct map_session_data *sd, *tsd; + struct Damage wd; + struct status_change *sc = status_get_sc(src); + struct status_change *tsc = status_get_sc(target); struct status_data *sstatus = status_get_status_data(src); struct status_data *tstatus = status_get_status_data(target); struct { - unsigned imdef : 1; - unsigned infdef : 1; + unsigned hit : 1; //the attack Hit? (not a miss) + unsigned cri : 1; //Critical hit + unsigned idef : 1; //Ignore defense + unsigned idef2 : 1; //Ignore defense (left weapon) + unsigned pdef : 2; //Pierces defense (Investigate/Ice Pick) + unsigned pdef2 : 2; //1: Use def+def2/100, 2: Use def+def2/50 + unsigned infdef : 1; //Infinite defense (plants) + unsigned arrow : 1; //Attack is arrow-based + unsigned rh : 1; //Attack considers right hand (wd.damage) + unsigned lh : 1; //Attack considers left hand (wd.damage2) + unsigned weapon : 1; //It's a weapon attack (consider VVS, and all that) +#ifdef RENEWAL + unsigned tdef : 1; //Total defence reduction +#endif } flag; - memset(&ad,0,sizeof(ad)); + memset(&wd,0,sizeof(wd)); memset(&flag,0,sizeof(flag)); if(src==NULL || target==NULL) { nullpo_info(NLP_MARK); - return ad; - } - //Initial Values - ad.damage = 1; - ad.div_=skill->get_num(skill_id,skill_lv); - ad.amotion=skill->get_inf(skill_id)&INF_GROUND_SKILL?0:sstatus->amotion; //Amotion should be 0 for ground skills. - ad.dmotion=tstatus->dmotion; - ad.blewcount = skill->get_blewcount(skill_id,skill_lv); - ad.flag=BF_MAGIC|BF_SKILL; - ad.dmg_lv=ATK_DEF; - nk = skill->get_nk(skill_id); - flag.imdef = nk&NK_IGNORE_DEF?1:0; - - sd = BL_CAST(BL_PC, src); -// tsd = BL_CAST(BL_PC, target); - sc = status_get_sc(src); - tsc = status_get_sc(target); - - //Initialize variables that will be used afterwards - s_ele = skill->get_ele(skill_id, skill_lv); - - if (s_ele == -1){ // pl=-1 : the skill takes the weapon's element - s_ele = sstatus->rhw.ele; - if( sd ){ //Summoning 10 talisman will endow your weapon - ARR_FIND(1, 6, i, sd->talisman[i] >= 10); - if( i < 5 ) s_ele = i; - } - }else if (s_ele == -2) //Use status element - s_ele = status_get_attack_sc_element(src,status_get_sc(src)); - else if( s_ele == -3 ) //Use random element - s_ele = rnd()%ELE_MAX; - - if( skill_id == SO_PSYCHIC_WAVE ) { - if( sc && sc->count ) { - if( sc->data[SC_HEATER_OPTION] ) s_ele = sc->data[SC_HEATER_OPTION]->val4; - else if( sc->data[SC_COOLER_OPTION] ) s_ele = sc->data[SC_COOLER_OPTION]->val4; - else if( sc->data[SC_BLAST_OPTION] ) s_ele = sc->data[SC_BLAST_OPTION]->val3; - else if( sc->data[SC_CURSED_SOIL_OPTION] ) s_ele = sc->data[SC_CURSED_SOIL_OPTION]->val4; - } - } - - //Set miscellaneous data that needs be filled - if(sd) { - sd->state.arrow_atk = 0; - ad.blewcount += battle->blewcount_bonus(sd, skill_id); - } - - //Skill Range Criteria - ad.flag |= battle->range_type(src, target, skill_id, skill_lv); - flag.infdef=(tstatus->mode&MD_PLANT?1:0); - if( target->type == BL_SKILL){ - TBL_SKILL *su = (TBL_SKILL*)target; - if( su->group && (su->group->skill_id == WM_REVERBERATION || su->group->skill_id == WM_POEMOFNETHERWORLD) ) - flag.infdef = 1; - } - - switch(skill_id) { - case MG_FIREWALL: - case NJ_KAENSIN: - ad.dmotion = 0; //No flinch animation. - if ( tstatus->def_ele == ELE_FIRE || battle->check_undead(tstatus->race, tstatus->def_ele) ) - ad.blewcount = 0; //No knockback - break; - case PR_SANCTUARY: - ad.dmotion = 0; //No flinch animation. - break; + return wd; + } + //Initial flag + flag.rh=1; + flag.weapon=1; + flag.infdef=(tstatus->mode&MD_PLANT && skill_id != RA_CLUSTERBOMB +#ifdef RENEWAL + && skill_id != HT_FREEZINGTRAP +#endif + ?1:0); + if( target->type == BL_SKILL){ + TBL_SKILL *su = (TBL_SKILL*)target; + if( su->group && (su->group->skill_id == WM_REVERBERATION || su->group->skill_id == WM_POEMOFNETHERWORLD) ) + flag.infdef = 1; } - if (!flag.infdef) //No need to do the math for plants - { -#ifdef RENEWAL - ad.damage = 0; //reinitialize.. -#endif -//MATK_RATE scales the damage. 100 = no change. 50 is halved, 200 is doubled, etc -#define MATK_RATE( a ) { ad.damage= ad.damage*(a)/100; } -//Adds dmg%. 100 = +100% (double) damage. 10 = +10% damage -#define MATK_ADDRATE( a ) { ad.damage+= ad.damage*(a)/100; } -//Adds an absolute value to damage. 100 = +100 damage -#define MATK_ADD( a ) { ad.damage+= a; } - - switch (skill_id) - { //Calc base damage according to skill - case AL_HEAL: - case PR_BENEDICTIO: - case PR_SANCTUARY: - /** - * Arch Bishop - **/ - case AB_HIGHNESSHEAL: - ad.damage = skill->calc_heal(src, target, skill_id, skill_lv, false); - break; - case PR_ASPERSIO: - ad.damage = 40; - break; - case ALL_RESURRECTION: - case PR_TURNUNDEAD: - //Undead check is on skill_castend_damageid code. - #ifdef RENEWAL - i = 10*skill_lv + sstatus->luk + sstatus->int_ + status_get_lv(src) - + 300 - 300*tstatus->hp/tstatus->max_hp; - #else - i = 20*skill_lv + sstatus->luk + sstatus->int_ + status_get_lv(src) - + 200 - 200*tstatus->hp/tstatus->max_hp; - #endif - if(i > 700) i = 700; - if(rnd()%1000 < i && !(tstatus->mode&MD_BOSS)) - ad.damage = tstatus->hp; - else { - #ifdef RENEWAL - if (sstatus->matk_max > sstatus->matk_min) { - MATK_ADD(sstatus->matk_min+rnd()%(sstatus->matk_max-sstatus->matk_min)); - } else { - MATK_ADD(sstatus->matk_min); - } - MATK_RATE(skill_lv); - #else - ad.damage = status_get_lv(src) + sstatus->int_ + skill_lv * 10; - #endif - } - break; - case PF_SOULBURN: - ad.damage = tstatus->sp * 2; - break; - /** - * Arch Bishop - **/ - case AB_RENOVATIO: - //Damage calculation from iRO wiki. [Jobbie] - ad.damage = (int)((15 * status_get_lv(src)) + (1.5 * sstatus->int_)); - break; - default: { - if (sstatus->matk_max > sstatus->matk_min) { - MATK_ADD(sstatus->matk_min+rnd()%(sstatus->matk_max-sstatus->matk_min)); - } else { - MATK_ADD(sstatus->matk_min); - } - - if (nk&NK_SPLASHSPLIT) { // Divide MATK in case of multiple targets skill - if(mflag>0) - ad.damage/= mflag; - else - ShowError("0 enemies targeted by %d:%s, divide per 0 avoided!\n", skill_id, skill->get_name(skill_id)); - } - - switch(skill_id){ - case MG_NAPALMBEAT: - skillratio += skill_lv*10-30; - break; - case MG_FIREBALL: - #ifdef RENEWAL - skillratio += 20*skill_lv; - #else - skillratio += skill_lv*10-30; - #endif - break; - case MG_SOULSTRIKE: - if (battle->check_undead(tstatus->race,tstatus->def_ele)) - skillratio += 5*skill_lv; - break; - case MG_FIREWALL: - skillratio -= 50; - break; - case MG_FIREBOLT: - case MG_COLDBOLT: - case MG_LIGHTNINGBOLT: - if ( sc && sc->data[SC_SPELLFIST] && mflag&BF_SHORT ) { - skillratio += (sc->data[SC_SPELLFIST]->val4 * 100) + (sc->data[SC_SPELLFIST]->val2 * 100) - 100;// val4 = used bolt level, val2 = used spellfist level. [Rytech] - ad.div_ = 1;// ad mods, to make it work similar to regular hits [Xazax] - ad.flag = BF_WEAPON|BF_SHORT; - ad.type = 0; - } - break; - case MG_THUNDERSTORM: - /** - * in Renewal Thunder Storm boost is 100% (in pre-re, 80%) - **/ - #ifndef RENEWAL - skillratio -= 20; - #endif - break; - case MG_FROSTDIVER: - skillratio += 10*skill_lv; - break; - case AL_HOLYLIGHT: - skillratio += 25; - if (sd && sd->sc.data[SC_SPIRIT] && sd->sc.data[SC_SPIRIT]->val2 == SL_PRIEST) - skillratio *= 5; //Does 5x damage include bonuses from other skills? - break; - case AL_RUWACH: - skillratio += 45; - break; - case WZ_FROSTNOVA: - skillratio += (100+skill_lv*10)*2/3-100; - break; - case WZ_FIREPILLAR: - if (skill_lv > 10) - skillratio += 100; - else - skillratio -= 80; - break; - case WZ_SIGHTRASHER: - skillratio += 20*skill_lv; - break; - case WZ_WATERBALL: - skillratio += 30*skill_lv; - break; - case WZ_STORMGUST: - skillratio += 40*skill_lv; - break; - case HW_NAPALMVULCAN: - skillratio += 10*skill_lv-30; - break; - case SL_STIN: - skillratio += (tstatus->size!=SZ_SMALL?-99:10*skill_lv); //target size must be small (0) for full damage. - break; - case SL_STUN: - skillratio += (tstatus->size!=SZ_BIG?5*skill_lv:-99); //Full damage is dealt on small/medium targets - break; - case SL_SMA: - skillratio += -60 + status_get_lv(src); //Base damage is 40% + lv% - break; - case NJ_KOUENKA: - skillratio -= 10; - break; - case NJ_KAENSIN: - skillratio -= 50; - break; - case NJ_BAKUENRYU: - skillratio += 50*(skill_lv-1); - break; - case NJ_HYOUSYOURAKU: - skillratio += 50*skill_lv; - break; - case NJ_RAIGEKISAI: - skillratio += 60 + 40*skill_lv; - break; - case NJ_KAMAITACHI: - case NPC_ENERGYDRAIN: - skillratio += 100*skill_lv; - break; - case NPC_EARTHQUAKE: - skillratio += 100 +100*skill_lv +100*(skill_lv/2); - break; - #ifdef RENEWAL - case WZ_HEAVENDRIVE: - case WZ_METEOR: - skillratio += 25; - break; - case WZ_VERMILION: - { - int interval = 0, per = interval, ratio = per; - while( (per++) < skill_lv ){ - ratio += interval; - if(per%3==0) interval += 20; - } - if( skill_lv > 9 ) - ratio -= 10; - skillratio += ratio; - } - break; - case NJ_HUUJIN: - skillratio += 50; - break; - #else - case WZ_VERMILION: - skillratio += 20*skill_lv-20; - break; - #endif - /** - * Arch Bishop - **/ - case AB_JUDEX: - skillratio += 180 + 20 * skill_lv; - if (skill_lv > 4) skillratio += 20; - RE_LVL_DMOD(100); - break; - case AB_ADORAMUS: - skillratio += 400 + 100 * skill_lv; - RE_LVL_DMOD(100); - break; - case AB_DUPLELIGHT_MAGIC: - skillratio += 100 + 20 * skill_lv; - break; - /** - * Warlock - **/ - case WL_SOULEXPANSION: - skillratio += 300 + 100 * skill_lv + sstatus->int_; - RE_LVL_DMOD(100); - break; - case WL_FROSTMISTY: - skillratio += 100 + 100 * skill_lv; - RE_LVL_DMOD(100); - break; - case WL_JACKFROST: - if( tsc && tsc->data[SC_FREEZING] ){ - skillratio += 900 + 300 * skill_lv; - RE_LVL_DMOD(100); - }else{ - skillratio += 400 + 100 * skill_lv; - RE_LVL_DMOD(150); - } - break; - case WL_DRAINLIFE: - skillratio = 200 * skill_lv + sstatus->int_; - RE_LVL_DMOD(100); - break; - case WL_CRIMSONROCK: - skillratio += 1200 + 300 * skill_lv; - RE_LVL_DMOD(100); - break; - case WL_HELLINFERNO: - skillratio = 300 * skill_lv; - RE_LVL_DMOD(100); - // Shadow: MATK [{( Skill Level x 300 ) x ( Caster Base Level / 100 ) x 4/5 }] % - // Fire : MATK [{( Skill Level x 300 ) x ( Caster Base Level / 100 ) /5 }] % - if( mflag&ELE_DARK ){ skillratio *= 4; s_ele = ELE_DARK; } - skillratio /= 5; - break; - case WL_COMET: { - struct status_change * sc = status_get_sc(src); - if( sc ) - i = distance_xy(target->x, target->y, sc->comet_x, sc->comet_y); - else - i = 8; - if( i < 2 ) skillratio = 2500 + 500 * skill_lv; - else - if( i < 4 ) skillratio = 1600 + 400 * skill_lv; - else - if( i < 6 ) skillratio = 1200 + 300 * skill_lv; - else - skillratio = 800 + 200 * skill_lv; - } - break; - case WL_CHAINLIGHTNING_ATK: - skillratio += 100 + 300 * skill_lv; - RE_LVL_DMOD(100); - break; - case WL_EARTHSTRAIN: - skillratio += 1900 + 100 * skill_lv; - RE_LVL_DMOD(100); - break; - case WL_TETRAVORTEX_FIRE: - case WL_TETRAVORTEX_WATER: - case WL_TETRAVORTEX_WIND: - case WL_TETRAVORTEX_GROUND: - skillratio += 400 + 500 * skill_lv; - break; - case WL_SUMMON_ATK_FIRE: - case WL_SUMMON_ATK_WATER: - case WL_SUMMON_ATK_WIND: - case WL_SUMMON_ATK_GROUND: - skillratio = skill_lv * (status_get_lv(src) + ( sd ? sd->status.job_level : 50 ));// This is close to official, but lacking a little info to finalize. [Rytech] - RE_LVL_DMOD(100); - break; - case LG_RAYOFGENESIS: - { - int16 lv = skill_lv; - int bandingBonus = 0; - if( sc && sc->data[SC_BANDING] ) - bandingBonus = 200 * (sd ? skill->check_pc_partner(sd,skill_id,&lv,skill->get_splash(skill_id,skill_lv),0) : 1); - skillratio = ((300 * skill_lv) + bandingBonus) * (sd ? sd->status.job_level : 1) / 25; - } - break; - case LG_SHIELDSPELL:// [(Casters Base Level x 4) + (Shield MDEF x 100) + (Casters INT x 2)] % - if( sd ) { - skillratio = status_get_lv(src) * 4 + sd->bonus.shieldmdef * 100 + status_get_int(src) * 2; - } else - skillratio += 1900; //2000% - break; - case WM_METALICSOUND: - skillratio += 120 * skill_lv + 60 * ( sd? pc->checkskill(sd, WM_LESSON) : 10 ) - 100; - break; - /*case WM_SEVERE_RAINSTORM: - skillratio += 50 * skill_lv; - break; - - WM_SEVERE_RAINSTORM just set a unit place, - refer to WM_SEVERE_RAINSTORM_MELEE to set the formula. - */ - case WM_REVERBERATION_MAGIC: - // MATK [{(Skill Level x 100) + 100} x Casters Base Level / 100] % - skillratio += 100 * (sd ? pc->checkskill(sd, WM_REVERBERATION) : 1); - RE_LVL_DMOD(100); - break; - case SO_FIREWALK: - skillratio = 300; - RE_LVL_DMOD(100); - if( sc && sc->data[SC_HEATER_OPTION] ) - skillratio += sc->data[SC_HEATER_OPTION]->val3; - break; - case SO_ELECTRICWALK: - skillratio = 300; - RE_LVL_DMOD(100); - if( sc && sc->data[SC_BLAST_OPTION] ) - skillratio += sd ? sd->status.job_level / 2 : 0; - break; - case SO_EARTHGRAVE: - skillratio = ( 200 * ( sd ? pc->checkskill(sd, SA_SEISMICWEAPON) : 10 ) + sstatus->int_ * skill_lv ); - RE_LVL_DMOD(100); - if( sc && sc->data[SC_CURSED_SOIL_OPTION] ) - skillratio += sc->data[SC_CURSED_SOIL_OPTION]->val2; - break; - case SO_DIAMONDDUST: - skillratio = ( 200 * ( sd ? pc->checkskill(sd, SA_FROSTWEAPON) : 10 ) + sstatus->int_ * skill_lv ); - RE_LVL_DMOD(100); - if( sc && sc->data[SC_COOLER_OPTION] ) - skillratio += sc->data[SC_COOLER_OPTION]->val3; - break; - case SO_POISON_BUSTER: - skillratio += 1100 + 300 * skill_lv; - if( sc && sc->data[SC_CURSED_SOIL_OPTION] ) - skillratio += sc->data[SC_CURSED_SOIL_OPTION]->val2; - break; - case SO_PSYCHIC_WAVE: - skillratio += -100 + skill_lv * 70 + (sstatus->int_ * 3); - RE_LVL_DMOD(100); - if( sc ){ - if( sc->data[SC_HEATER_OPTION] ) - skillratio += sc->data[SC_HEATER_OPTION]->val3; - else if(sc->data[SC_COOLER_OPTION] ) - skillratio += sc->data[SC_COOLER_OPTION]->val3; - else if(sc->data[SC_BLAST_OPTION] ) - skillratio += sc->data[SC_BLAST_OPTION]->val2; - else if(sc->data[SC_CURSED_SOIL_OPTION] ) - skillratio += sc->data[SC_CURSED_SOIL_OPTION]->val3; - } - break; - case SO_VARETYR_SPEAR: //MATK [{( Endow Tornado skill level x 50 ) + ( Caster INT x Varetyr Spear Skill level )} x Caster Base Level / 100 ] % - skillratio = status_get_int(src) * skill_lv + ( sd ? pc->checkskill(sd, SA_LIGHTNINGLOADER) * 50 : 0 ); - RE_LVL_DMOD(100); - if( sc && sc->data[SC_BLAST_OPTION] ) - skillratio += sd ? sd->status.job_level * 5 : 0; - break; - case SO_CLOUD_KILL: - skillratio += -100 + skill_lv * 40; - RE_LVL_DMOD(100); - if( sc && sc->data[SC_CURSED_SOIL_OPTION] ) - skillratio += sc->data[SC_CURSED_SOIL_OPTION]->val2; - break; - case GN_DEMONIC_FIRE: - if( skill_lv > 20) - { // Fire expansion Lv.2 - skillratio += 110 + 20 * (skill_lv - 20) + status_get_int(src) * 3; // Need official INT bonus. [LimitLine] - } - else if( skill_lv > 10 ) - { // Fire expansion Lv.1 - skillratio += 110 + 20 * (skill_lv - 10) / 2; - } - else - skillratio += 110 + 20 * skill_lv; - break; - // Magical Elemental Spirits Attack Skills - case EL_FIRE_MANTLE: - case EL_WATER_SCREW: - skillratio += 900; - break; - case EL_FIRE_ARROW: - case EL_ROCK_CRUSHER_ATK: - skillratio += 200; - break; - case EL_FIRE_BOMB: - case EL_ICE_NEEDLE: - case EL_HURRICANE_ATK: - skillratio += 400; - break; - case EL_FIRE_WAVE: - case EL_TYPOON_MIS_ATK: - skillratio += 1100; - break; - case MH_ERASER_CUTTER: - if(skill_lv%2) skillratio += 400; //600:800:1000 - else skillratio += 700; //1000:1200 - skillratio += 100 * skill_lv; - break; - case MH_XENO_SLASHER: - if(skill_lv%2) skillratio += 350 + 50 * skill_lv; //500:600:700 - else skillratio += 400 + 100 * skill_lv; //700:900 - break; - case MH_HEILIGE_STANGE: - skillratio += 400 + 250 * skill_lv; - break; - case MH_POISON_MIST: - skillratio += 100 * skill_lv; - break; - } + //Initial Values + wd.type=0; //Normal attack + wd.div_=skill_id?skill->get_num(skill_id,skill_lv):1; + wd.amotion=(skill_id && skill->get_inf(skill_id)&INF_GROUND_SKILL)?0:sstatus->amotion; //Amotion should be 0 for ground skills. + if(skill_id == KN_AUTOCOUNTER) + wd.amotion >>= 1; + wd.dmotion=tstatus->dmotion; + wd.blewcount=skill->get_blewcount(skill_id,skill_lv); + wd.flag = BF_WEAPON; //Initial Flag + wd.flag |= (skill_id||wflag)?BF_SKILL:BF_NORMAL; // Baphomet card's splash damage is counted as a skill. [Inkfish] + wd.dmg_lv=ATK_DEF; //This assumption simplifies the assignation later + nk = skill->get_nk(skill_id); + if( !skill_id && wflag ) //If flag, this is splash damage from Baphomet Card and it always hits. + nk |= NK_NO_CARDFIX_ATK|NK_IGNORE_FLEE; + flag.hit = nk&NK_IGNORE_FLEE?1:0; + flag.idef = flag.idef2 = nk&NK_IGNORE_DEF?1:0; + flag.tdef = 0; - MATK_RATE(skillratio); + if (sc && !sc->count) + sc = NULL; //Skip checking as there are no status changes active. + if (tsc && !tsc->count) + tsc = NULL; //Skip checking as there are no status changes active. - //Constant/misc additions from skills - if (skill_id == WZ_FIREPILLAR) - MATK_ADD(50); - } - } -#ifndef HMAP_ZONE_DAMAGE_CAP_TYPE - if( target && skill_id ) { - for(i = 0; i < map[target->m].zone->capped_skills_count; i++) { - if( skill_id == map[target->m].zone->capped_skills[i]->nameid && (map[target->m].zone->capped_skills[i]->type & target->type) ) { - if( target->type == BL_MOB && map[target->m].zone->capped_skills[i]->subtype != MZS_NONE ) { - if( (((TBL_MOB*)target)->status.mode&MD_BOSS) && !(map[target->m].zone->disabled_skills[i]->subtype&MZS_BOSS) ) - continue; - if( ((TBL_MOB*)target)->special_state.clone && !(map[target->m].zone->disabled_skills[i]->subtype&MZS_CLONE) ) - continue; - } - if( ad.damage > map[target->m].zone->capped_skills[i]->cap ) - ad.damage = map[target->m].zone->capped_skills[i]->cap; - if( ad.damage2 > map[target->m].zone->capped_skills[i]->cap ) - ad.damage2 = map[target->m].zone->capped_skills[i]->cap; - break; + sd = BL_CAST(BL_PC, src); + tsd = BL_CAST(BL_PC, target); + + if(sd) + wd.blewcount += battle->blewcount_bonus(sd, skill_id); + + //Set miscellaneous data that needs be filled regardless of hit/miss + if( + (sd && sd->state.arrow_atk) || + (!sd && ((skill_id && skill->get_ammotype(skill_id)) || sstatus->rhw.range>3)) + ) + flag.arrow = 1; + + if(skill_id) { + wd.flag |= battle->range_type(src, target, skill_id, skill_lv); + switch(skill_id) { + case MO_FINGEROFFENSIVE: + if(sd) { + if (battle_config.finger_offensive_type) + wd.div_ = 1; + else + wd.div_ = sd->spiritball_old; } - } - } + break; + case HT_PHANTASMIC: + //Since these do not consume ammo, they need to be explicitly set as arrow attacks. + flag.arrow = 1; + break; +#ifndef RENEWAL + case PA_SHIELDCHAIN: + case CR_SHIELDBOOMERANG: #endif + case LG_SHIELDPRESS: + case LG_EARTHDRIVE: + flag.weapon = 0; + break; + + case KN_PIERCE: + case ML_PIERCE: + wd.div_= (wd.div_>0?tstatus->size+1:-(tstatus->size+1)); + break; + + case TF_DOUBLE: //For NPC used skill. + case GS_CHAINACTION: + wd.type = 0x08; + break; + + case GS_GROUNDDRIFT: + case KN_SPEARSTAB: + case KN_BOWLINGBASH: + case MS_BOWLINGBASH: + case MO_BALKYOUNG: + case TK_TURNKICK: + wd.blewcount=0; + break; + + case KN_AUTOCOUNTER: + wd.flag=(wd.flag&~BF_SKILLMASK)|BF_NORMAL; + break; + + case NPC_CRITICALSLASH: + case LG_PINPOINTATTACK: + flag.cri = 1; //Always critical skill. + break; + + case LK_SPIRALPIERCE: + if (!sd) wd.flag=(wd.flag&~(BF_RANGEMASK|BF_WEAPONMASK))|BF_LONG|BF_MISC; + break; + + case MO_INVESTIGATE: + flag.pdef = flag.pdef2 = 2; + break; + + case RA_AIMEDBOLT: + if( tsc && (tsc->data[SC_WUGBITE] || tsc->data[SC_ANKLESNARE] || tsc->data[SC_ELECTRICSHOCKER]) ) + wd.div_ = tstatus->size + 2 + ( (rnd()%100 < 50-tstatus->size*10) ? 1 : 0 ); + break; #ifdef RENEWAL - ad.damage = battle->calc_cardfix(BF_MAGIC, src, target, nk, s_ele, 0, ad.damage, 0, ad.flag); + case HW_MAGICCRASHER: + flag.tdef = 1; + break; #endif - if(sd) { - //Damage bonuses - if ((i = pc->skillatk_bonus(sd, skill_id))) - ad.damage += ad.damage*i/100; - - if( (i = battle->adjust_skill_damage(src->m,skill_id)) ) - MATK_RATE(i); + } + } else //Range for normal attacks. + wd.flag |= flag.arrow?BF_LONG:BF_SHORT; + if ( (!skill_id || skill_id == PA_SACRIFICE) && tstatus->flee2 && rnd()%1000 < tstatus->flee2 ) + { //Check for Lucky Dodge + wd.type=0x0b; + wd.dmg_lv=ATK_LUCKY; + if (wd.div_ < 0) wd.div_*=-1; + return wd; + } - //Ignore Defense? - if (!flag.imdef && ( - sd->bonus.ignore_mdef_ele & ( 1 << tstatus->def_ele ) || - sd->bonus.ignore_mdef_race & ( 1 << tstatus->race ) || - sd->bonus.ignore_mdef_race & ( is_boss(target) ? 1 << RC_BOSS : 1 << RC_NONBOSS ) - )) - flag.imdef = 1; + t_class = status_get_class(target); + s_ele = s_ele_ = skill->get_ele(skill_id, skill_lv); + if( !skill_id || s_ele == -1 ) + { //Take weapon's element + s_ele = sstatus->rhw.ele; + s_ele_ = sstatus->lhw.ele; + if( sd ){ //Summoning 10 charm will endow your weapon. + ARR_FIND(1, 6, i, sd->charm[i] >= 10); + if( i < 5 ) s_ele = s_ele_ = i; + } + if( flag.arrow && sd && sd->bonus.arrow_ele ) + s_ele = sd->bonus.arrow_ele; + if( battle_config.attack_attr_none&src->type ) + n_ele = true; //Weapon's element is "not elemental" + } + else if( s_ele == -2 ) //Use enchantment's element + s_ele = s_ele_ = status_get_attack_sc_element(src,sc); + else if( s_ele == -3 ) //Use random element + s_ele = s_ele_ = rnd()%ELE_MAX; + switch( skill_id ) + { + case GS_GROUNDDRIFT: + s_ele = s_ele_ = wflag; //element comes in flag. + break; + case LK_SPIRALPIERCE: + if (!sd) n_ele = false; //forced neutral for monsters + break; + } + + if (!(nk & NK_NO_ELEFIX) && !n_ele) + if (src->type == BL_HOM) + n_ele = true; //skill is "not elemental" + if (sc && sc->data[SC_GOLDENE_FERSE] && ((!skill_id && (rnd() % 100 < sc->data[SC_GOLDENE_FERSE]->val4)) || skill_id == MH_STAHL_HORN)) { + s_ele = s_ele_ = ELE_HOLY; + n_ele = false; + } + + if(!skill_id) + { //Skills ALWAYS use ONLY your right-hand weapon (tested on Aegis 10.2) + if (sd && sd->weapontype1 == 0 && sd->weapontype2 > 0) + { + flag.rh=0; + flag.lh=1; } + if (sstatus->lhw.atk) + flag.lh=1; + } - if(!flag.imdef){ - defType mdef = tstatus->mdef; - int mdef2= tstatus->mdef2; -#ifdef RENEWAL - if(tsc && tsc->data[SC_ASSUMPTIO]) - mdef <<= 1; // only eMDEF is doubled -#endif - if(sd) { - i = sd->ignore_mdef[is_boss(target)?RC_BOSS:RC_NONBOSS]; - i+= sd->ignore_mdef[tstatus->race]; - if (i) - { - if (i > 100) i = 100; - mdef -= mdef * i/100; - //mdef2-= mdef2* i/100; + if( sd && !skill_id ) { //Check for double attack. + if( ( ( skill_lv = pc->checkskill(sd,TF_DOUBLE) ) > 0 && sd->weapontype1 == W_DAGGER ) + || ( sd->bonus.double_rate > 0 && sd->weapontype1 != W_FIST ) //Will fail bare-handed + || ( sc && sc->data[SC_KAGEMUSYA] && sd->weapontype1 != W_FIST )) // Need confirmation + { //Success chance is not added, the higher one is used [Skotlex] + if( rnd()%100 < ( 5*skill_lv > sd->bonus.double_rate ? 5*skill_lv : sc && sc->data[SC_KAGEMUSYA]?sc->data[SC_KAGEMUSYA]->val1*3:sd->bonus.double_rate ) ) + { + wd.div_ = skill->get_num(TF_DOUBLE,skill_lv?skill_lv:1); + wd.type = 0x08; + } + } + else if( sd->weapontype1 == W_REVOLVER && (skill_lv = pc->checkskill(sd,GS_CHAINACTION)) > 0 && rnd()%100 < 5*skill_lv ) + { + wd.div_ = skill->get_num(GS_CHAINACTION,skill_lv); + wd.type = 0x08; + } + else if(sc && sc->data[SC_FEARBREEZE] && sd->weapontype1==W_BOW + && (i = sd->equip_index[EQI_AMMO]) >= 0 && sd->inventory_data[i] && sd->status.inventory[i].amount > 1){ + int chance = rand()%100; + wd.type = 0x08; + switch(sc->data[SC_FEARBREEZE]->val1){ + case 5: + if( chance < 3){// 3 % chance to attack 5 times. + wd.div_ = 5; + break; + } + case 4: + if( chance < 7){// 6 % chance to attack 4 times. + wd.div_ = 4; + break; + } + case 3: + if( chance < 10){// 9 % chance to attack 3 times. + wd.div_ = 3; + break; + } + case 2: + case 1: + if( chance < 13){// 12 % chance to attack 2 times. + wd.div_ = 2; + break; + } } - } - #ifdef RENEWAL - /** - * RE MDEF Reduction - * Damage = Magic Attack * (1000+eMDEF)/(1000+eMDEF) - sMDEF - **/ - ad.damage = ad.damage * (1000 + mdef) / (1000 + mdef * 10) - mdef2; - #else - if(battle_config.magic_defense_type) - ad.damage = ad.damage - mdef*battle_config.magic_defense_type - mdef2; - else - ad.damage = ad.damage * (100-mdef)/100 - mdef2; - #endif + wd.div_ = min(wd.div_,sd->status.inventory[i].amount); + sc->data[SC_FEARBREEZE]->val4 = wd.div_-1; } + } - if (skill_id == NPC_EARTHQUAKE) - { //Adds atk2 to the damage, should be influenced by number of hits and skill-ratio, but not mdef reductions. [Skotlex] - //Also divide the extra bonuses from atk2 based on the number in range [Kevin] - if(mflag>0) - ad.damage+= (sstatus->rhw.atk2*skillratio/100)/mflag; - else - ShowError("Zero range by %d:%s, divide per 0 avoided!\n", skill_id, skill->get_name(skill_id)); + //Check for critical + if( !flag.cri && !(wd.type&0x08) && sstatus->cri && + (!skill_id || + skill_id == KN_AUTOCOUNTER || + skill_id == SN_SHARPSHOOTING || skill_id == MA_SHARPSHOOTING || + skill_id == NJ_KIRIKAGE)) + { + short cri = sstatus->cri; + if (sd) + { + cri+= sd->critaddrace[tstatus->race]; + if(flag.arrow) + cri += sd->bonus.arrow_cri; } + if( sc && sc->data[SC_CAMOUFLAGE] ) + cri += 10 * (10-sc->data[SC_CAMOUFLAGE]->val4); +#ifndef RENEWAL + //The official equation is *2, but that only applies when sd's do critical. + //Therefore, we use the old value 3 on cases when an sd gets attacked by a mob + cri -= tstatus->luk*(!sd&&tsd?3:2); +#else + cri -= status_get_lv(target) / 15 + 2 * status_get_luk(target); +#endif - if(ad.damage<1) - ad.damage=1; - else if(sc){//only applies when hit - // TODO: there is another factor that contribute with the damage and need to be formulated. [malufett] - switch(skill_id){ - case MG_LIGHTNINGBOLT: - case MG_THUNDERSTORM: - case MG_FIREBOLT: - case MG_FIREWALL: - case MG_COLDBOLT: - case MG_FROSTDIVER: - case WZ_EARTHSPIKE: - case WZ_HEAVENDRIVE: - if(sc->data[SC_GUST_OPTION] || sc->data[SC_PETROLOGY_OPTION] - || sc->data[SC_PYROTECHNIC_OPTION] || sc->data[SC_AQUAPLAY_OPTION]) - ad.damage += (6 + sstatus->int_/4) + max(sstatus->dex-10,0)/30; - break; - } + if( tsc && tsc->data[SC_SLEEP] ) { + cri <<= 1; } - - if (!(nk&NK_NO_ELEFIX)) - ad.damage=battle->attr_fix(src, target, ad.damage, s_ele, tstatus->def_ele, tstatus->ele_lv); - - if( skill_id == CR_GRANDCROSS || skill_id == NPC_GRANDDARKNESS ) - { //Apply the physical part of the skill's damage. [Skotlex] - struct Damage wd = battle->calc_weapon_attack(src,target,skill_id,skill_lv,mflag); - ad.damage = battle->attr_fix(src, target, wd.damage + ad.damage, s_ele, tstatus->def_ele, tstatus->ele_lv) * (100 + 40*skill_lv)/100; - if( src == target ) - { - if( src->type == BL_PC ) - ad.damage = ad.damage/2; + switch (skill_id) { + case KN_AUTOCOUNTER: + if(battle_config.auto_counter_type && + (battle_config.auto_counter_type&src->type)) + flag.cri = 1; else - ad.damage = 0; - } + cri <<= 1; + break; + case SN_SHARPSHOOTING: + case MA_SHARPSHOOTING: + cri += 200; + break; + case NJ_KIRIKAGE: + cri += 250 + 50*skill_lv; + break; } - + if(tsd && tsd->bonus.critical_def) + cri = cri * ( 100 - tsd->bonus.critical_def ) / 100; + if (rnd()%1000 < cri) + flag.cri = 1; + } + if (flag.cri) { + wd.type = 0x0a; #ifndef RENEWAL - ad.damage = battle->calc_cardfix(BF_MAGIC, src, target, nk, s_ele, 0, ad.damage, 0, ad.flag); + flag.idef = flag.idef2 = #endif + flag.hit = 1; + } else { //Check for Perfect Hit + if(sd && sd->bonus.perfect_hit > 0 && rnd()%100 < sd->bonus.perfect_hit) + flag.hit = 1; + if (sc && sc->data[SC_FUSION]) { + flag.hit = 1; //SG_FUSION always hit [Komurka] + flag.idef = flag.idef2 = 1; //def ignore [Komurka] + } + if( !flag.hit ) + switch(skill_id) + { + case AS_SPLASHER: + if( !wflag ) // Always hits the one exploding. + flag.hit = 1; + break; + case CR_SHIELDBOOMERANG: + if( sc && sc->data[SC_SOULLINK] && sc->data[SC_SOULLINK]->val2 == SL_CRUSADER ) + flag.hit = 1; + break; + } + if (tsc && !flag.hit && tsc->opt1 && tsc->opt1 != OPT1_STONEWAIT && tsc->opt1 != OPT1_BURNING) + flag.hit = 1; } - damage_div_fix(ad.damage, ad.div_); - - if (flag.infdef && ad.damage) - ad.damage = ad.damage>0?1:-1; - - ad.damage=battle->calc_damage(src,target,&ad,ad.damage,skill_id,skill_lv); - if( map_flag_gvg2(target->m) ) - ad.damage=battle->calc_gvg_damage(src,target,ad.damage,ad.div_,skill_id,skill_lv,ad.flag); - else if( map[target->m].flag.battleground ) - ad.damage=battle->calc_bg_damage(src,target,ad.damage,ad.div_,skill_id,skill_lv,ad.flag); + if (!flag.hit) + { //Hit/Flee calculation + short + flee = tstatus->flee, +#ifdef RENEWAL + hitrate = 0; //Default hitrate +#else + hitrate = 80; //Default hitrate +#endif - switch( skill_id ) { /* post-calc modifiers */ - case SO_VARETYR_SPEAR: { // Physical damage. - struct Damage wd = battle->calc_weapon_attack(src,target,skill_id,skill_lv,mflag); - if(!flag.infdef && ad.damage > 1) - ad.damage += wd.damage; - break; + if(battle_config.agi_penalty_type && battle_config.agi_penalty_target&target->type) { + unsigned char attacker_count; //256 max targets should be a sane max + attacker_count = unit_counttargeted(target); + if(attacker_count >= battle_config.agi_penalty_count) { + if (battle_config.agi_penalty_type == 1) + flee = (flee * (100 - (attacker_count - (battle_config.agi_penalty_count - 1))*battle_config.agi_penalty_num))/100; + else //asume type 2: absolute reduction + flee -= (attacker_count - (battle_config.agi_penalty_count - 1))*battle_config.agi_penalty_num; + if(flee < 1) flee = 1; + } } - //case HM_ERASER_CUTTER: - } - return ad; -} - -/*========================================== - * Calculate Misc dammage for skill_id - *------------------------------------------*/ -struct Damage battle_calc_misc_attack(struct block_list *src,struct block_list *target,uint16 skill_id,uint16 skill_lv,int mflag) { - int temp; - short i, nk; - short s_ele; + hitrate+= sstatus->hit - flee; - struct map_session_data *sd, *tsd; - struct Damage md; //DO NOT CONFUSE with md of mob_data! - struct status_data *sstatus = status_get_status_data(src); - struct status_data *tstatus = status_get_status_data(target); + if(wd.flag&BF_LONG && !skill_id && //Fogwall's hit penalty is only for normal ranged attacks. + tsc && tsc->data[SC_FOGWALL]) + hitrate -= 50; - memset(&md,0,sizeof(md)); + if(sd && flag.arrow) + hitrate += sd->bonus.arrow_hit; +#ifdef RENEWAL + if( sd ) //in Renewal hit bonus from Vultures Eye is not anymore shown in status window + hitrate += pc->checkskill(sd,AC_VULTURE); +#endif + if(skill_id) + switch(skill_id) + { //Hit skill modifiers + //It is proven that bonus is applied on final hitrate, not hit. + case SM_BASH: + case MS_BASH: + hitrate += hitrate * 5 * skill_lv / 100; + break; + case MS_MAGNUM: + case SM_MAGNUM: + hitrate += hitrate * 10 * skill_lv / 100; + break; + case KN_AUTOCOUNTER: + case PA_SHIELDCHAIN: + case NPC_WATERATTACK: + case NPC_GROUNDATTACK: + case NPC_FIREATTACK: + case NPC_WINDATTACK: + case NPC_POISONATTACK: + case NPC_HOLYATTACK: + case NPC_DARKNESSATTACK: + case NPC_UNDEADATTACK: + case NPC_TELEKINESISATTACK: + case NPC_BLEEDING: + hitrate += hitrate * 20 / 100; + break; + case KN_PIERCE: + case ML_PIERCE: + hitrate += hitrate * 5 * skill_lv / 100; + break; + case AS_SONICBLOW: + if(sd && pc->checkskill(sd,AS_SONICACCEL)>0) + hitrate += hitrate * 50 / 100; + break; + case MC_CARTREVOLUTION: + case GN_CART_TORNADO: + case GN_CARTCANNON: + if( sd && pc->checkskill(sd, GN_REMODELING_CART) ) + hitrate += pc->checkskill(sd, GN_REMODELING_CART) * 4; + break; + case GC_VENOMPRESSURE: + hitrate += 10 + 4 * skill_lv; + break; + } - if( src == NULL || target == NULL ){ - nullpo_info(NLP_MARK); - return md; - } + if( sd ) { + // Weaponry Research hidden bonus + if ((temp = pc->checkskill(sd,BS_WEAPONRESEARCH)) > 0) + hitrate += hitrate * ( 2 * temp ) / 100; - //Some initial values - md.amotion=skill->get_inf(skill_id)&INF_GROUND_SKILL?0:sstatus->amotion; - md.dmotion=tstatus->dmotion; - md.div_=skill->get_num( skill_id,skill_lv ); - md.blewcount=skill->get_blewcount(skill_id,skill_lv); - md.dmg_lv=ATK_DEF; - md.flag=BF_MISC|BF_SKILL; + if( (sd->status.weapon == W_1HSWORD || sd->status.weapon == W_DAGGER) && + (temp = pc->checkskill(sd, GN_TRAINING_SWORD))>0 ) + hitrate += 3 * temp; + } - nk = skill->get_nk(skill_id); + hitrate = cap_value(hitrate, battle_config.min_hitrate, battle_config.max_hitrate); +#ifdef RENEWAL + if( !sd ) + hitrate = cap_value(hitrate, 5, 95); +#endif + if(rnd()%100 >= hitrate) + wd.dmg_lv = ATK_FLEE; + else + flag.hit = 1; + } //End hit/miss calculation - sd = BL_CAST(BL_PC, src); - tsd = BL_CAST(BL_PC, target); + if (flag.hit && !flag.infdef) //No need to do the math for plants + { //Hitting attack - if(sd) { - sd->state.arrow_atk = 0; - md.blewcount += battle->blewcount_bonus(sd, skill_id); - } +//Assuming that 99% of the cases we will not need to check for the flag.rh... we don't. +//ATK_RATE scales the damage. 100 = no change. 50 is halved, 200 is doubled, etc +#define ATK_RATE( a ) { wd.damage= wd.damage*(a)/100 ; if(flag.lh) wd.damage2= wd.damage2*(a)/100; } +#define ATK_RATE2( a , b ) { wd.damage= wd.damage*(a)/100 ; if(flag.lh) wd.damage2= wd.damage2*(b)/100; } +#define ATK_RATER(a){ wd.damage = wd.damage*(a)/100;} +#define ATK_RATEL(a){ wd.damage2 = wd.damage2*(a)/100;} +//Adds dmg%. 100 = +100% (double) damage. 10 = +10% damage +#define ATK_ADDRATE( a ) { wd.damage+= wd.damage*(a)/100 ; if(flag.lh) wd.damage2+= wd.damage2*(a)/100; } +#define ATK_ADDRATE2( a , b ) { wd.damage+= wd.damage*(a)/100 ; if(flag.lh) wd.damage2+= wd.damage2*(b)/100; } +//Adds an absolute value to damage. 100 = +100 damage +#define ATK_ADD( a ) { wd.damage+= a; if (flag.lh) wd.damage2+= a; } +#define ATK_ADD2( a , b ) { wd.damage+= a; if (flag.lh) wd.damage2+= b; } - s_ele = skill->get_ele(skill_id, skill_lv); - if (s_ele < 0 && s_ele != -3) //Attack that takes weapon's element for misc attacks? Make it neutral [Skotlex] - s_ele = ELE_NEUTRAL; - else if (s_ele == -3) //Use random element - s_ele = rnd()%ELE_MAX; + switch (skill_id) + { //Calc base damage according to skill + case PA_SACRIFICE: + wd.damage = sstatus->max_hp* 9/100; + wd.damage2 = 0; + break; + +#ifdef RENEWAL + case MO_EXTREMITYFIST: // [malufett] + wd.damage = battle->calc_base_damage(src, target, skill_id, skill_lv, nk, n_ele, s_ele, s_ele_, EQI_HAND_R, (sc && sc->data[SC_MAXIMIZEPOWER]?1:0)|8, wd.flag); + // first value is still not confirm. + wd.damage = status_get_sp(src) + 10 * status_get_sp(src) * wd.damage / 100 + 8 * wd.damage; + flag.tdef = 1; + break; + case NJ_ISSEN: // [malufett] + { + short totaldef = status_get_total_def(target); + i = 0; + wd.damage = battle->calc_base_damage(src, target, skill_id, skill_lv, nk, n_ele, s_ele, s_ele_, EQI_HAND_R, (sc && sc->data[SC_MAXIMIZEPOWER]?1:0)|(sc && sc->data[SC_WEAPONPERFECT]?8:0), wd.flag); + if( sc && sc->data[SC_NJ_BUNSINJYUTSU] && (i=sc->data[SC_NJ_BUNSINJYUTSU]->val2) > 0 ) + wd.div_ = ~( i++ + 2 ) + 1; + wd.damage *= sstatus->hp * skill_lv; + wd.damage = wd.damage / sstatus->max_hp + sstatus->hp + i * (wd.damage / sstatus->max_hp + sstatus->hp) / 5; + ATK_ADD(-totaldef); + if( is_boss(target) ) + ATK_RATE(50); + flag.idef = 1; + } +#else + + wd.damage = 40*sstatus->str +skill_lv*(sstatus->hp/10 + 35); + wd.damage2 = 0; +#endif + break; +#ifndef RENEWAL + case LK_SPIRALPIERCE: + case ML_SPIRALPIERCE: + if (sd) { + short index = sd->equip_index[EQI_HAND_R]; - //Skill Range Criteria - md.flag |= battle->range_type(src, target, skill_id, skill_lv); + if (index >= 0 && + sd->inventory_data[index] && + sd->inventory_data[index]->type == IT_WEAPON) + wd.damage = sd->inventory_data[index]->weight*8/100; //80% of weight + } else + wd.damage = sstatus->rhw.atk2*8/10; //Else use Atk2 - switch( skill_id ) - { + ATK_ADDRATE(50*skill_lv); //Skill modifier applies to weight only. + i = sstatus->str/10; + i*=i; + ATK_ADD(i); //Add str bonus. + switch (tstatus->size) { //Size-fix. Is this modified by weapon perfection? + case SZ_SMALL: //Small: 125% + ATK_RATE(125); + break; + //case SZ_MEDIUM: //Medium: 100% + case SZ_BIG: //Large: 75% + ATK_RATE(75); + break; + } + break; +#endif + case CR_SHIELDBOOMERANG: + case PA_SHIELDCHAIN: + case LG_SHIELDPRESS: + case LG_EARTHDRIVE: + wd.damage = sstatus->batk; + if (sd) { + short index = sd->equip_index[EQI_HAND_L]; + + if (index >= 0 && + sd->inventory_data[index] && + sd->inventory_data[index]->type == IT_ARMOR) + ATK_ADD(sd->inventory_data[index]->weight/10); + } else + ATK_ADD(sstatus->rhw.atk2); //Else use Atk2 + break; + case HFLI_SBR44: //[orn] + if(src->type == BL_HOM) { + wd.damage = ((TBL_HOM*)src)->homunculus.intimacy ; + break; + } + default: + { + i = (flag.cri #ifdef RENEWAL - case HT_LANDMINE: - case MA_LANDMINE: - case HT_BLASTMINE: - case HT_CLAYMORETRAP: - md.damage = skill_lv * sstatus->dex * (3+status_get_lv(src)/100) * (1+sstatus->int_/35); - md.damage += md.damage * (rnd()%20-10) / 100; - md.damage += 40 * (sd?pc->checkskill(sd,RA_RESEARCHTRAP):0); - break; + || (sc && sc->data[SC_MAXIMIZEPOWER]) +#endif + ?1:0)| + (flag.arrow?2:0)| +#ifndef RENEWAL + (skill_id == HW_MAGICCRASHER?4:0)| + (skill_id == MO_EXTREMITYFIST?8:0)| +#endif + (!skill_id && sc && sc->data[SC_HLIF_CHANGE]?4:0)| + (sc && sc->data[SC_WEAPONPERFECT]?8:0); + if (flag.arrow && sd) + switch(sd->status.weapon) { + case W_BOW: + case W_REVOLVER: + case W_GATLING: + case W_SHOTGUN: + case W_GRENADE: + break; + default: + i |= 16; // for ex. shuriken must not be influenced by DEX + } +#ifdef RENEWAL + wd.damage = battle->calc_base_damage(src, target, skill_id, skill_lv, nk, n_ele, s_ele, s_ele_, EQI_HAND_R, i, wd.flag); + wd.damage = battle->calc_masteryfix(src, target, skill_id, skill_lv, wd.damage, wd.div_, 0, flag.weapon); + if (flag.lh){ + wd.damage2 = battle->calc_base_damage(src, target, skill_id, skill_lv, nk, n_ele, s_ele, s_ele_, EQI_HAND_L, i, wd.flag); + wd.damage2 = battle->calc_masteryfix(src, target, skill_id, skill_lv, wd.damage2, wd.div_, 1, flag.weapon); + } #else - case HT_LANDMINE: - case MA_LANDMINE: - md.damage=skill_lv*(sstatus->dex+75)*(100+sstatus->int_)/100; - break; - case HT_BLASTMINE: - md.damage=skill_lv*(sstatus->dex/2+50)*(100+sstatus->int_)/100; - break; - case HT_CLAYMORETRAP: - md.damage=skill_lv*(sstatus->dex/2+75)*(100+sstatus->int_)/100; - break; + wd.damage = battle->calc_base_damage(sstatus, &sstatus->rhw, sc, tstatus->size, sd, i); + if (flag.lh) + wd.damage2 = battle->calc_base_damage(sstatus, &sstatus->lhw, sc, tstatus->size, sd, i); #endif - case HT_BLITZBEAT: - case SN_FALCONASSAULT: - //Blitz-beat Damage. - if(!sd || (temp = pc->checkskill(sd,HT_STEELCROW)) <= 0) - temp=0; - md.damage=(sstatus->dex/10+sstatus->int_/2+temp*3+40)*2; - if(mflag > 1) //Autocasted Blitz. - nk|=NK_SPLASHSPLIT; + if (nk&NK_SPLASHSPLIT){ // Divide ATK among targets + if(wflag>0) + wd.damage/= wflag; + else + ShowError("0 enemies targeted by %d:%s, divide per 0 avoided!\n", skill_id, skill->get_name(skill_id)); + } - if (skill_id == SN_FALCONASSAULT) { - //Div fix of Blitzbeat - temp = skill->get_num(HT_BLITZBEAT, 5); - damage_div_fix(md.damage, temp); + //Add any bonuses that modify the base baseatk+watk (pre-skills) + if(sd) { + if (sd->bonus.atk_rate) + ATK_ADDRATE(sd->bonus.atk_rate); - //Falcon Assault Modifier - md.damage=md.damage*(150+70*skill_lv)/100; - } - break; - case TF_THROWSTONE: - md.damage=50; - break; - case BA_DISSONANCE: - md.damage=30+skill_lv*10; - if (sd) - md.damage+= 3*pc->checkskill(sd,BA_MUSICALLESSON); - break; - case NPC_SELFDESTRUCTION: - md.damage = sstatus->hp; - break; - case NPC_SMOKING: - md.damage=3; - break; - case NPC_DARKBREATH: - md.damage = 500 + (skill_lv-1)*1000 + rnd()%1000; - if(md.damage > 9999) md.damage = 9999; - break; - case PA_PRESSURE: - md.damage=500+300*skill_lv; - break; - case PA_GOSPEL: - md.damage = 1+rnd()%9999; - break; - case CR_ACIDDEMONSTRATION: // updated the formula based on a Japanese formula found to be exact [Reddozen] - if(tstatus->vit+sstatus->int_) //crash fix - md.damage = (int)(7*tstatus->vit*sstatus->int_*sstatus->int_ / (10*(tstatus->vit+sstatus->int_))); - else - md.damage = 0; - if (tsd) md.damage>>=1; - if (md.damage < 0 || md.damage > INT_MAX>>1) - //Overflow prevention, will anyone whine if I cap it to a few billion? - //Not capped to INT_MAX to give some room for further damage increase. - md.damage = INT_MAX>>1; - break; - case NJ_ZENYNAGE: - case KO_MUCHANAGE: - md.damage = skill->get_zeny(skill_id ,skill_lv); - if (!md.damage) md.damage = 2; - md.damage = rand()%md.damage + md.damage / (skill_id==NJ_ZENYNAGE?1:2) ; - if (is_boss(target)) - md.damage=md.damage / (skill_id==NJ_ZENYNAGE?3:2); - else if (tsd) // need confirmation for KO_MUCHANAGE - md.damage=md.damage/2; - break; - case GS_FLING: - md.damage = sd?sd->status.job_level:status_get_lv(src); - break; - case HVAN_EXPLOSION: //[orn] - md.damage = sstatus->max_hp * (50 + 50 * skill_lv) / 100; - break ; - case ASC_BREAKER: - md.damage = 500+rnd()%500 + 5*skill_lv * sstatus->int_; - nk|=NK_IGNORE_FLEE|NK_NO_ELEFIX; //These two are not properties of the weapon based part. - break; - case HW_GRAVITATION: - md.damage = 200+200*skill_lv; - md.dmotion = 0; //No flinch animation. - break; - case NPC_EVILLAND: - md.damage = skill->calc_heal(src,target,skill_id,skill_lv,false); - break; - case RK_DRAGONBREATH: - md.damage = ((status_get_hp(src) / 50) + (status_get_max_sp(src) / 4)) * skill_lv; - RE_LVL_MDMOD(150); - if (sd) md.damage = md.damage * (100 + 5 * (pc->checkskill(sd,RK_DRAGONTRAINING) - 1)) / 100; - md.flag |= BF_LONG|BF_WEAPON; - break; - /** - * Ranger - **/ - case RA_CLUSTERBOMB: - case RA_FIRINGTRAP: - case RA_ICEBOUNDTRAP: - md.damage = skill_lv * sstatus->dex + sstatus->int_ * 5 ; - RE_LVL_TMDMOD(); - if(sd) - { - int researchskill_lv = pc->checkskill(sd,RA_RESEARCHTRAP); - if(researchskill_lv) - md.damage = md.damage * 20 * researchskill_lv / (skill_id == RA_CLUSTERBOMB?50:100); - else - md.damage = 0; - }else - md.damage = md.damage * 200 / (skill_id == RA_CLUSTERBOMB?50:100); + if(flag.cri && sd->bonus.crit_atk_rate) + ATK_ADDRATE(sd->bonus.crit_atk_rate); + + if(sd->status.party_id && (temp=pc->checkskill(sd,TK_POWER)) > 0){ + if( (i = party_foreachsamemap(party->sub_count, sd, 0)) > 1 ) // exclude the player himself [Inkfish] + ATK_ADDRATE(2*temp*i); + } + } + break; + } //End default case + } //End switch(skill_id) - break; - /** - * Mechanic - **/ - case NC_SELFDESTRUCTION: + //Skill damage modifiers that stack linearly + if( sd && sd->status.weapon == W_KATAR && (i=pc->checkskill(sd,ASC_KATAR)) > 0 ) + skillratio += skillratio * (13 + 2 * i) / 100; + if(sc && skill_id != PA_SACRIFICE) { - short totaldef = tstatus->def2 + (short)status_get_def(target); - md.damage = ( (sd?pc->checkskill(sd,NC_MAINFRAME):10) + 8 ) * ( skill_lv + 1 ) * ( status_get_sp(src) + sstatus->vit ); - RE_LVL_MDMOD(100); - md.damage += status_get_hp(src) - totaldef; + if(sc->data[SC_OVERTHRUST]) + skillratio += sc->data[SC_OVERTHRUST]->val3; + if(sc->data[SC_OVERTHRUSTMAX]) + skillratio += sc->data[SC_OVERTHRUSTMAX]->val2; + if (sc->data[SC_BERSERK] || sc->data[SC_SATURDAY_NIGHT_FEVER] || sc->data[SC__BLOODYLUST]) + skillratio += 100; +#ifdef RENEWAL + if( sc->data[SC_TRUESIGHT] ) + skillratio += 2*sc->data[SC_TRUESIGHT]->val1; + if( sc->data[SC_LKCONCENTRATION] ) + skillratio += sc->data[SC_LKCONCENTRATION]->val2; +#endif + if( sc->data[SC_UNLIMIT] && wd.flag&BF_LONG ) + ATK_ADD( 50 * sc->data[SC_UNLIMIT]->val1 ); } - break; - case GN_THORNS_TRAP: - md.damage = 100 + 200 * skill_lv + sstatus->int_; - break; - case GN_HELLS_PLANT_ATK: - //[{( Hell Plant Skill Level x Casters Base Level ) x 10 } + {( Casters INT x 7 ) / 2 } x { 18 + ( Casters Job Level / 4 )] x ( 5 / ( 10 - Summon Flora Skill Level )) - md.damage = ( skill_lv * status_get_lv(src) * 10 ) + ( sstatus->int_ * 7 / 2 ) * ( 18 + (sd?sd->status.job_level:0) / 4 ) * ( 5 / (10 - (sd?pc->checkskill(sd,AM_CANNIBALIZE):0)) ); - break; - case KO_HAPPOKUNAI: - { - struct Damage wd = battle->calc_weapon_attack(src,target,skill_id,skill_lv,mflag); - short totaldef = tstatus->def2 + (short)status_get_def(target); - md.damage = wd.damage * 60 * (5 + skill_lv) / 100; - md.damage -= totaldef; + if( tsc && skill_id != PA_SACRIFICE ){ + if( tsc->data[SC_DARKCROW] && wd.flag&BF_SHORT ) + ATK_ADD( 30 * tsc->data[SC_DARKCROW]->val1 ); } - break; - case KO_MAKIBISHI: - md.damage = 20 * skill_lv; - break; - } - if (nk&NK_SPLASHSPLIT){ // Divide ATK among targets - if(mflag>0) - md.damage/= mflag; + if( !skill_id ) + { + ATK_RATE(skillratio); + } else - ShowError("0 enemies targeted by %d:%s, divide per 0 avoided!\n", skill_id, skill->get_name(skill_id)); - } + { + switch(skill_id){ + #ifdef RENEWAL + case LK_SPIRALPIERCE: + case ML_SPIRALPIERCE: + {// Formula: Floor[Floor(Weapon Weight/2)*skill level + ATK ]*(100%+50%*s.lvl) * 5 multi-hits + short index = sd?sd->equip_index[EQI_HAND_R]:0; + int weight = 0; - damage_div_fix(md.damage, md.div_); + if (sd && index >= 0 && + sd->inventory_data[index] && + sd->inventory_data[index]->type == IT_WEAPON) + weight = sd->inventory_data[index]->weight/20; + ATK_ADD(weight * skill_lv); + } + case NJ_TATAMIGAESHI: + if( skill_id != LK_SPIRALPIERCE && skill_id != ML_SPIRALPIERCE ) + ATK_RATE(200); + #endif + default: + ATK_RATE(battle->calc_skillratio(BF_WEAPON, src, target, skill_id, skill_lv, skillratio, wflag)); + } - if (!(nk&NK_IGNORE_FLEE)) - { - struct status_change *sc = status_get_sc(target); - i = 0; //Temp for "hit or no hit" - if(sc && sc->opt1 && sc->opt1 != OPT1_STONEWAIT && sc->opt1 != OPT1_BURNING) - i = 1; - else { - short - flee = tstatus->flee, + //Constant/misc additions from skills + switch (skill_id) { + case MO_EXTREMITYFIST: + ATK_ADD(250 + 150*skill_lv); + break; #ifdef RENEWAL - hitrate = 0; //Default hitrate + case HW_MAGICCRASHER: + ATK_ADD(battle->calc_magic_attack(src, target, skill_id, skill_lv, wflag).damage / 5); + break; +#endif + case TK_DOWNKICK: + case TK_STORMKICK: + case TK_TURNKICK: + case TK_COUNTER: + case TK_JUMPKICK: + //TK_RUN kick damage bonus. + if(sd && sd->weapontype1 == W_FIST && sd->weapontype2 == W_FIST) + ATK_ADD(10*pc->checkskill(sd, TK_RUN)); + break; + case GS_MAGICALBULLET: +#ifndef RENEWAL + ATK_ADD( status_get_matk(src, 2) ); #else - hitrate = 80; //Default hitrate + ATK_ADD( battle->calc_magic_attack(src, target, skill_id, skill_lv, wflag).damage ); + flag.tdef = 1; +#endif + case NJ_SYURIKEN: + ATK_ADD(4*skill_lv); + break; + case HT_FREEZINGTRAP: + if(sd) + ATK_ADD( 40 * pc->checkskill(sd, RA_RESEARCHTRAP) ); + break; + case RA_WUGDASH ://(Caster Current Weight x 10 / 8) + if( sd && sd->weight ) + ATK_ADD( sd->weight / 8 ); + break; + case SR_TIGERCANNON: // (Tiger Cannon skill level x 240) + (Target Base Level x 40) + ATK_ADD( skill_lv * 240 + status_get_lv(target) * 40 ); + if( sc && sc->data[SC_COMBOATTACK] + && sc->data[SC_COMBOATTACK]->val1 == SR_FALLENEMPIRE ) // (Tiger Cannon skill level x 500) + (Target Base Level x 40) + ATK_ADD( skill_lv * 500 + status_get_lv(target) * 40 ); + break; + case SR_FALLENEMPIRE:// [(Target Size value + Skill Level - 1) x Caster STR] + [(Target current weight x Caster DEX / 120)] + ATK_ADD( ((tstatus->size+1)*2 + skill_lv - 1) * sstatus->str); + if( tsd && tsd->weight ){ + ATK_ADD( (tsd->weight/10) * sstatus->dex / 120 ); + }else{ + ATK_ADD( status_get_lv(target) * 50 ); //mobs + } + break; + case KO_SETSUDAN: + if( tsc && tsc->data[SC_SOULLINK] ){ + ATK_ADDRATE(200*tsc->data[SC_SOULLINK]->val1); + status_change_end(target,SC_SOULLINK,INVALID_TIMER); + } + break; + case KO_MAKIBISHI: + wd.damage = 20 * skill_lv; + break; + } + } +#ifndef RENEWAL + //Div fix. + damage_div_fix(wd.damage, wd.div_); +#endif + //The following are applied on top of current damage and are stackable. + if ( sc ) { +#ifndef RENEWAL + if( sc->data[SC_TRUESIGHT] ) + ATK_ADDRATE(2*sc->data[SC_TRUESIGHT]->val1); +#endif + if( sc->data[SC_GLOOMYDAY_SK] && + ( skill_id == LK_SPIRALPIERCE || skill_id == KN_BRANDISHSPEAR || + skill_id == CR_SHIELDBOOMERANG || skill_id == PA_SHIELDCHAIN || + skill_id == LG_SHIELDPRESS || skill_id == RK_HUNDREDSPEAR || + skill_id == CR_SHIELDCHARGE ) ) + ATK_ADDRATE(sc->data[SC_GLOOMYDAY_SK]->val2); + if( sc->data[SC_EDP] ){ + switch(skill_id){ +#ifndef RENEWAL_EDP + case AS_SPLASHER: case AS_VENOMKNIFE: + case AS_GRIMTOOTH: + break; + case ASC_METEORASSAULT: break; + default: + ATK_ADDRATE(sc->data[SC_EDP]->val3); #endif + } + } + if(sc->data[SC_STYLE_CHANGE]){ + TBL_HOM *hd = BL_CAST(BL_HOM,src); + if (hd) ATK_ADD(hd->homunculus.spiritball * 3); + } + } - if(battle_config.agi_penalty_type && battle_config.agi_penalty_target&target->type) { - unsigned char attacker_count; //256 max targets should be a sane max - attacker_count = unit_counttargeted(target); - if(attacker_count >= battle_config.agi_penalty_count) - { - if (battle_config.agi_penalty_type == 1) - flee = (flee * (100 - (attacker_count - (battle_config.agi_penalty_count - 1))*battle_config.agi_penalty_num))/100; - else //asume type 2: absolute reduction - flee -= (attacker_count - (battle_config.agi_penalty_count - 1))*battle_config.agi_penalty_num; - if(flee < 1) flee = 1; + switch (skill_id) { + case AS_SONICBLOW: + if (sc && sc->data[SC_SOULLINK] && + sc->data[SC_SOULLINK]->val2 == SL_ASSASIN) + ATK_ADDRATE(map_flag_gvg(src->m)?25:100); //+25% dmg on woe/+100% dmg on nonwoe + + if(sd && pc->checkskill(sd,AS_SONICACCEL)>0) + ATK_ADDRATE(10); + break; + case CR_SHIELDBOOMERANG: + if(sc && sc->data[SC_SOULLINK] && + sc->data[SC_SOULLINK]->val2 == SL_CRUSADER) + ATK_ADDRATE(100); + break; + case NC_AXETORNADO: + if( (sstatus->rhw.ele) == ELE_WIND || (sstatus->lhw.ele) == ELE_WIND ) + ATK_ADDRATE(50); + break; + } + + if( (i = battle->adjust_skill_damage(src->m,skill_id)) ) + ATK_RATE(i); + + if( sd ) { + if (skill_id && (i = pc->skillatk_bonus(sd, skill_id))) + ATK_ADDRATE(i); + if( (i=pc->checkskill(sd,AB_EUCHARISTICA)) > 0 && + (tstatus->race == RC_DEMON || tstatus->def_ele == ELE_DARK) ) + ATK_ADDRATE(-i); + if( skill_id != PA_SACRIFICE && skill_id != MO_INVESTIGATE && skill_id != CR_GRANDCROSS && skill_id != NPC_GRANDDARKNESS && skill_id != PA_SHIELDCHAIN && !flag.cri ) + { //Elemental/Racial adjustments + if( sd->right_weapon.def_ratio_atk_ele & (1<def_ele) || + sd->right_weapon.def_ratio_atk_race & (1<race) || + sd->right_weapon.def_ratio_atk_race & (1<<(is_boss(target)?RC_BOSS:RC_NONBOSS)) + ) + flag.pdef = 1; + + if( sd->left_weapon.def_ratio_atk_ele & (1<def_ele) || + sd->left_weapon.def_ratio_atk_race & (1<race) || + sd->left_weapon.def_ratio_atk_race & (1<<(is_boss(target)?RC_BOSS:RC_NONBOSS)) + ) + { //Pass effect onto right hand if configured so. [Skotlex] + if (battle_config.left_cardfix_to_right && flag.rh) + flag.pdef = 1; + else + flag.pdef2 = 1; + } + } + + if (skill_id != CR_GRANDCROSS && skill_id != NPC_GRANDDARKNESS) + { //Ignore Defense? + if (!flag.idef && ( + sd->right_weapon.ignore_def_ele & (1<def_ele) || + sd->right_weapon.ignore_def_race & (1<race) || + sd->right_weapon.ignore_def_race & (is_boss(target)?1<left_weapon.ignore_def_ele & (1<def_ele) || + sd->left_weapon.ignore_def_race & (1<race) || + sd->left_weapon.ignore_def_race & (is_boss(target)?1<calc_defense(BF_WEAPON, src, target, skill_id, skill_lv, wd.damage, (flag.idef?1:0)|(flag.pdef?2:0)|(flag.tdef?4:0), flag.pdef); + if( wd.damage2 ) + wd.damage2 = battle->calc_defense(BF_WEAPON, src, target, skill_id, skill_lv, wd.damage2, (flag.idef2?1:0)|(flag.pdef2?2:0)|(flag.tdef?4:0), flag.pdef2); + } + +#ifdef RENEWAL + //Div fix. + damage_div_fix(wd.damage, wd.div_); +#endif + //Post skill/vit reduction damage increases + if( sc ) + { //SC skill damages + if(sc->data[SC_AURABLADE] +#ifndef RENEWAL + && skill_id != LK_SPIRALPIERCE && skill_id != ML_SPIRALPIERCE +#endif + ){ + int lv = sc->data[SC_AURABLADE]->val1; +#ifdef RENEWAL + lv *= ((skill_id == LK_SPIRALPIERCE || skill_id == ML_SPIRALPIERCE)?wd.div_:1); // +100 per hit in lv 5 +#endif + ATK_ADD(20*lv); + } + } +#ifndef RENEWAL + //Refine bonus + if( sd && flag.weapon && skill_id != MO_INVESTIGATE && skill_id != MO_EXTREMITYFIST ) + { // Counts refine bonus multiple times + if( skill_id == MO_FINGEROFFENSIVE ) + { + ATK_ADD2(wd.div_*sstatus->rhw.atk2, wd.div_*sstatus->lhw.atk2); + } else { + ATK_ADD2(sstatus->rhw.atk2, sstatus->lhw.atk2); + } + } + //Set to min of 1 + if (flag.rh && wd.damage < 1) wd.damage = 1; + if (flag.lh && wd.damage2 < 1) wd.damage2 = 1; +#else + if (flag.rh && wd.damage < 1) wd.damage = 0; + if (flag.lh && wd.damage2 < 1) wd.damage2 = 0; +#endif + +#ifndef RENEWAL + wd.damage = battle->calc_masteryfix(src, target, skill_id, skill_lv, wd.damage, wd.div_, 0, flag.weapon); + if( flag.lh) + wd.damage2 = battle->calc_masteryfix(src, target, skill_id, skill_lv, wd.damage2, wd.div_, 1, flag.weapon); +#else + if( flag.cri ) + ATK_ADDRATE(40); +#endif + } //Here ends flag.hit section, the rest of the function applies to both hitting and missing attacks + else if(wd.div_ < 0) //Since the attack missed... + wd.div_ *= -1; +#ifndef RENEWAL + if(sd && (temp=pc->checkskill(sd,BS_WEAPONRESEARCH)) > 0) + ATK_ADD(temp*2); +#endif + if(skill_id==TF_POISON) + ATK_ADD(15*skill_lv); - hitrate+= sstatus->hit - flee; -#ifdef RENEWAL - if( sd ) //in Renewal hit bonus from Vultures Eye is not anymore shown in status window - hitrate += pc->checkskill(sd,AC_VULTURE); +#ifndef RENEWAL + wd.damage = battle->calc_elefix(src, target, skill_id, skill_lv, wd.damage, nk, n_ele, s_ele, s_ele_, false, flag.arrow); + if( flag.lh ) + wd.damage2 = battle->calc_elefix(src, target, skill_id, skill_lv, wd.damage2, nk, n_ele, s_ele, s_ele_, true, flag.arrow); #endif - hitrate = cap_value(hitrate, battle_config.min_hitrate, battle_config.max_hitrate); - if(rnd()%100 < hitrate) - i = 1; - } - if (!i) { - md.damage = 0; - md.dmg_lv=ATK_FLEE; - } - } + if(skill_id == CR_GRANDCROSS || skill_id == NPC_GRANDDARKNESS) + return wd; //Enough, rest is not needed. #ifndef HMAP_ZONE_DAMAGE_CAP_TYPE if( target && skill_id ) { for(i = 0; i < map[target->m].zone->capped_skills_count; i++) { @@ -4497,75 +4764,251 @@ struct Damage battle_calc_misc_attack(struct block_list *src,struct block_list * if( ((TBL_MOB*)target)->special_state.clone && !(map[target->m].zone->disabled_skills[i]->subtype&MZS_CLONE) ) continue; } - if( md.damage > map[target->m].zone->capped_skills[i]->cap ) - md.damage = map[target->m].zone->capped_skills[i]->cap; - if( md.damage2 > map[target->m].zone->capped_skills[i]->cap ) - md.damage2 = map[target->m].zone->capped_skills[i]->cap; + if( wd.damage > map[target->m].zone->capped_skills[i]->cap ) + wd.damage = map[target->m].zone->capped_skills[i]->cap; + if( wd.damage2 > map[target->m].zone->capped_skills[i]->cap ) + wd.damage2 = map[target->m].zone->capped_skills[i]->cap; break; } } } #endif - md.damage = battle->calc_cardfix(BF_MISC, src, target, nk, s_ele, 0, md.damage, 0, md.flag); - - if (sd && (i = pc->skillatk_bonus(sd, skill_id))) - md.damage += md.damage*i/100; +#ifndef RENEWAL + if (sd) { + if (skill_id != CR_SHIELDBOOMERANG) //Only Shield boomerang doesn't takes the Star Crumbs bonus. + ATK_ADD2(wd.div_*sd->right_weapon.star, wd.div_*sd->left_weapon.star); + if (skill_id==MO_FINGEROFFENSIVE) { //The finger offensive spheres on moment of attack do count. [Skotlex] + ATK_ADD(wd.div_*sd->spiritball_old*3); + } else { + ATK_ADD(wd.div_*sd->spiritball*3); + } + //Card Fix, sd side + wd.damage = battle->calc_cardfix(BF_WEAPON, src, target, nk, s_ele, s_ele_, wd.damage, 2, wd.flag); + if( flag.lh ) + wd.damage2 = battle->calc_cardfix(BF_WEAPON, src, target, nk, s_ele, s_ele_, wd.damage2, 3, wd.flag); +#ifdef RENEWAL + if( flag.cri ) + ATK_ADDRATE(sd->bonus.crit_atk_rate>=100?sd->bonus.crit_atk_rate-60:40); +#endif + if( skill_id == CR_SHIELDBOOMERANG || skill_id == PA_SHIELDCHAIN ) + { //Refine bonus applies after cards and elements. + short index= sd->equip_index[EQI_HAND_L]; + if( index >= 0 && sd->inventory_data[index] && sd->inventory_data[index]->type == IT_ARMOR ) + ATK_ADD(10*sd->status.inventory[index].refine); + } + } + //Card Fix, tsd side + if(tsd){ //if player on player then it was already measured above + wd.damage = battle->calc_cardfix(BF_WEAPON, src, target, nk, s_ele, s_ele_, wd.damage, 2, wd.flag); + if( flag.lh ) + wd.damage2 = battle->calc_cardfix(BF_WEAPON, src, target, nk, s_ele, s_ele_, wd.damage2, 3, wd.flag); + } +#endif + if( flag.infdef ) { //Plants receive 1 damage when hit + short class_ = status_get_class(target); + if( flag.hit || wd.damage > 0 ) + wd.damage = wd.div_; // In some cases, right hand no need to have a weapon to increase damage + if( flag.lh && (flag.hit || wd.damage2 > 0) ) + wd.damage2 = wd.div_; + if( flag.hit && class_ == MOBID_EMPERIUM ) { + if(wd.damage2 > 0) { + wd.damage2 = battle->attr_fix(src,target,wd.damage2,s_ele_,tstatus->def_ele, tstatus->ele_lv); + wd.damage2 = battle->calc_gvg_damage(src,target,wd.damage2,wd.div_,skill_id,skill_lv,wd.flag); + } + else if(wd.damage > 0) { + wd.damage = battle->attr_fix(src,target,wd.damage,s_ele_,tstatus->def_ele, tstatus->ele_lv); + wd.damage = battle->calc_gvg_damage(src,target,wd.damage,wd.div_,skill_id,skill_lv,wd.flag); + } + return wd; + } + if( !(battle_config.skill_min_damage&1) ) + //Do not return if you are supposed to deal greater damage to plants than 1. [Skotlex] + return wd; + } - if( (i = battle->adjust_skill_damage(src->m,skill_id)) ) - md.damage = md.damage * i / 100; + if (sd) { + if (!flag.rh && flag.lh) { //Move lh damage to the rh + wd.damage = wd.damage2; + wd.damage2 = 0; + flag.rh=1; + flag.lh=0; + } else if(flag.rh && flag.lh) { //Dual-wield + if (wd.damage) { + temp = pc->checkskill(sd,AS_RIGHT) * 10; + if( (sd->class_&MAPID_UPPERMASK) == MAPID_KAGEROUOBORO ) + temp = pc->checkskill(sd,KO_RIGHT) * 10 + 20; + ATK_RATER( 50 + temp ); + } + if (wd.damage2) { + temp = pc->checkskill(sd,AS_LEFT) * 10; + if( (sd->class_&MAPID_UPPERMASK) == MAPID_KAGEROUOBORO ) + temp = pc->checkskill(sd,KO_LEFT) * 10 + 20; + ATK_RATEL( 30 + temp ); + } +#ifdef RENEWAL + if(wd.damage < 0) wd.damage = 0; + if(wd.damage2 < 0) wd.damage2 = 0; +#else + if(wd.damage < 1) wd.damage = 1; + if(wd.damage2 < 1) wd.damage2 = 1; +#endif + } else if(sd->status.weapon == W_KATAR && !skill_id) { //Katars (offhand damage only applies to normal attacks, tested on Aegis 10.2) + temp = pc->checkskill(sd,TF_DOUBLE); + wd.damage2 = wd.damage * (1 + (temp * 2))/100; - if(md.damage < 0) - md.damage = 0; - else if(md.damage && tstatus->mode&MD_PLANT){ - switch(skill_id){ - case HT_LANDMINE: - case MA_LANDMINE: - case HT_BLASTMINE: - case HT_CLAYMORETRAP: - case RA_CLUSTERBOMB: + if(wd.damage && !wd.damage2) wd.damage2 = #ifdef RENEWAL - break; + 0; +#else + 1; #endif - default: - md.damage = 1; + flag.lh = 1; } - }else if( target->type == BL_SKILL ){ - TBL_SKILL *su = (TBL_SKILL*)target; - if( su->group && (su->group->skill_id == WM_REVERBERATION || su->group->skill_id == WM_POEMOFNETHERWORLD) ) - md.damage = 1; } - if(!(nk&NK_NO_ELEFIX)) - md.damage=battle->attr_fix(src, target, md.damage, s_ele, tstatus->def_ele, tstatus->ele_lv); + if(!flag.rh && wd.damage) + wd.damage=0; - md.damage=battle->calc_damage(src,target,&md,md.damage,skill_id,skill_lv); - if( map_flag_gvg2(target->m) ) - md.damage=battle->calc_gvg_damage(src,target,md.damage,md.div_,skill_id,skill_lv,md.flag); - else if( map[target->m].flag.battleground ) - md.damage=battle->calc_bg_damage(src,target,md.damage,md.div_,skill_id,skill_lv,md.flag); + if(!flag.lh && wd.damage2) + wd.damage2=0; - switch( skill_id ) { - case RA_FIRINGTRAP: - case RA_ICEBOUNDTRAP: - if( md.damage == 1 ) break; - case RA_CLUSTERBOMB: - { - struct Damage wd; - wd = battle->calc_weapon_attack(src,target,skill_id,skill_lv,mflag); - md.damage += wd.damage; + if( sc ) { + //SG_FUSION hp penalty [Komurka] + if (sc->data[SC_FUSION]) { + int hp= sstatus->max_hp; + if (sd && tsd) { + hp = 8*hp/100; + if ((sstatus->hp * 100) <= (sstatus->max_hp * 20)) + hp = sstatus->hp; + } else + hp = 2*hp/100; //2% hp loss per hit + status_zap(src, hp, 0); + } + if( !skill_id ) { + if( sc->data[SC_ENCHANTBLADE] ) { // it also works with bear hands..intended in official + //[( ( Skill Lv x 20 ) + 100 ) x ( casterBaseLevel / 150 )] + casterInt + ATK_ADD(( sc->data[SC_ENCHANTBLADE]->val1 * 20 + 100 ) * status_get_lv(src) / 150 + status_get_int(src)); } + } + status_change_end(src,SC_CAMOUFLAGE, INVALID_TIMER); + } + + switch(skill_id){ + case LG_RAYOFGENESIS: + { + struct Damage md = battle->calc_magic_attack(src, target, skill_id, skill_lv, wflag); + wd.damage += md.damage; break; - case NJ_ZENYNAGE: - if( sd ) { - if ( md.damage > sd->status.zeny ) - md.damage = sd->status.zeny; - pc->payzeny(sd, md.damage,LOG_TYPE_STEAL,NULL); } - break; + case SR_GATEOFHELL: + ATK_ADD (sstatus->max_hp - status_get_hp(src)); + if(sc && sc->data[SC_COMBOATTACK] && sc->data[SC_COMBOATTACK]->val1 == SR_FALLENEMPIRE){ + ATK_ADD ( (sstatus->max_sp * (1 + skill_lv * 2 / 10)) + 40 * status_get_lv(src) ); + }else{ + ATK_ADD ( (sstatus->sp * (1 + skill_lv * 2 / 10)) + 10 * status_get_lv(src) ); + } + break; } - return md; + if( wd.damage + wd.damage2 ) + { //There is a total damage value + int damage = wd.damage + wd.damage2, rdamage = 0, rdelay = 0; + + if( src != target && + (!skill_id || skill_id || + ( src->type == BL_SKILL && ( skill_id == SG_SUN_WARM || skill_id == SG_MOON_WARM || skill_id == SG_STAR_WARM ) )) ){ + + rdamage = battle->calc_return_damage(target, src, &damage, wd.flag, 0, &rdelay); + + if( tsc && tsc->count ) { + if( tsc && tsc->data[SC_DEATHBOUND] ){ + wd.damage = damage; + wd.damage2 = 0; + status_change_end(target,SC_DEATHBOUND,INVALID_TIMER); + } + } + if( rdamage > 0 ) { + if( tsc && tsc->data[SC_LG_REFLECTDAMAGE] ) { + if( src != target ) {// Don't reflect your own damage (Grand Cross) + bool change = false; + if( sd && !sd->state.autocast ) + change = true; + if( change ) + sd->state.autocast = 1; + iMap->foreachinshootrange(battle->damage_area,target,skill->get_splash(LG_REFLECTDAMAGE,1),BL_CHAR,iTimer->gettick(),target,wd.amotion,sstatus->dmotion,rdamage,tstatus->race); + if( change ) + sd->state.autocast = 0; + } + } else { + //Use Reflect Shield to signal this kind of skill trigger. [Skotlex] + if( tsd && src != target ) + battle->drain(tsd, src, rdamage, rdamage, sstatus->race, is_boss(src)); + battle->delay_damage(iTimer->gettick(), wd.amotion,target,src,0,CR_REFLECTSHIELD,0,rdamage,ATK_DEF,rdelay,true); + skill->additional_effect(target, src, CR_REFLECTSHIELD, 1, BF_WEAPON|BF_SHORT|BF_NORMAL,ATK_DEF,iTimer->gettick()); + } + } + } + if(!wd.damage2) + { + wd.damage = battle->calc_damage(src,target,&wd,wd.damage,skill_id,skill_lv); + if( map_flag_gvg2(target->m) ) + wd.damage=battle->calc_gvg_damage(src,target,wd.damage,wd.div_,skill_id,skill_lv,wd.flag); + else if( map[target->m].flag.battleground ) + wd.damage=battle->calc_bg_damage(src,target,wd.damage,wd.div_,skill_id,skill_lv,wd.flag); + } + else if(!wd.damage) + { + wd.damage2 = battle->calc_damage(src,target,&wd,wd.damage2,skill_id,skill_lv); + if( map_flag_gvg2(target->m) ) + wd.damage2 = battle->calc_gvg_damage(src,target,wd.damage2,wd.div_,skill_id,skill_lv,wd.flag); + else if( map[target->m].flag.battleground ) + wd.damage = battle->calc_bg_damage(src,target,wd.damage2,wd.div_,skill_id,skill_lv,wd.flag); + } + else + { +#ifdef RENEWAL + wd.damage = battle->calc_damage(src,target,&wd,wd.damage,skill_id,skill_lv); + wd.damage2 = battle->calc_damage(src,target,&wd,wd.damage2,skill_id,skill_lv); +#else + int d1 = wd.damage + wd.damage2,d2 = wd.damage2; + wd.damage = battle->calc_damage(src,target,&wd,d1,skill_id,skill_lv); +#endif + if( map_flag_gvg2(target->m) ) + wd.damage = battle->calc_gvg_damage(src,target,wd.damage,wd.div_,skill_id,skill_lv,wd.flag); + else if( map[target->m].flag.battleground ) + wd.damage = battle->calc_bg_damage(src,target,wd.damage,wd.div_,skill_id,skill_lv,wd.flag); +#ifndef RENEWAL + wd.damage2 = d2*100/d1 * wd.damage/100; + if(wd.damage > 1 && wd.damage2 < 1) wd.damage2 = 1; + wd.damage-=wd.damage2; +#endif + } + } + //Reject Sword bugreport:4493 by Daegaladh + if(wd.damage && tsc && tsc->data[SC_SWORDREJECT] && + (src->type!=BL_PC || ( + ((TBL_PC *)src)->weapontype1 == W_DAGGER || + ((TBL_PC *)src)->weapontype1 == W_1HSWORD || + ((TBL_PC *)src)->status.weapon == W_2HSWORD + )) && + rnd()%100 < tsc->data[SC_SWORDREJECT]->val2 + ) { + ATK_RATER(50) + status_fix_damage(target,src,wd.damage,clif->damage(target,src,iTimer->gettick(),0,0,wd.damage,0,0,0)); + clif->skill_nodamage(target,target,ST_REJECTSWORD,tsc->data[SC_SWORDREJECT]->val1,1); + if( --(tsc->data[SC_SWORDREJECT]->val3) <= 0 ) + status_change_end(target, SC_SWORDREJECT, INVALID_TIMER); + } +#ifndef RENEWAL + if(skill_id == ASC_BREAKER) { //Breaker's int-based damage (a misc attack?) + struct Damage md = battle->calc_misc_attack(src, target, skill_id, skill_lv, wflag); + wd.damage += md.damage; + } +#endif + + return wd; } + /*========================================== * Battle main entry, from skill->attack *------------------------------------------*/ @@ -4614,19 +5057,19 @@ struct Damage battle_calc_attack(int attack_type,struct block_list *bl,struct bl } //Calculates BF_WEAPON returned damage. -int battle_calc_return_damage(struct block_list* bl, struct block_list *src, int *dmg, int flag, uint16 skill_id){ +int battle_calc_return_damage(struct block_list* bl, struct block_list *src, int *dmg, int flag, uint16 skill_id, int *delay){ + int rdamage = 0, damage = *dmg, rdelay = *delay, trdamage = 0; struct map_session_data* sd; - int rdamage = 0, damage = *dmg; struct status_change* sc; + int max_reflect_damage; sd = BL_CAST(BL_PC, bl); sc = status_get_sc(bl); + max_reflect_damage = max(status_get_max_hp(bl), status_get_max_hp(bl) * status_get_lv(bl) / 100); - if( sc && sc->data[SC_REFLECTDAMAGE] ) { - int max_damage = status_get_max_hp(bl) * status_get_lv(bl) / 100; - rdamage = (*dmg) * sc->data[SC_REFLECTDAMAGE]->val2 / 100; - if( rdamage > max_damage ) rdamage = max_damage; - }else if( sc && sc->data[SC_CRESCENTELBOW] && !is_boss(src) && rnd()%100 < sc->data[SC_CRESCENTELBOW]->val2 ){ +#define NORMALIZE_RDAMAGE(d){ trdamage += rdamage = max(1, min(max_reflect_damage, d)); } + + if( sc && sc->data[SC_CRESCENTELBOW] && !is_boss(src) && rnd()%100 < sc->data[SC_CRESCENTELBOW]->val2 ){ //ATK [{(Target HP / 100) x Skill Level} x Caster Base Level / 125] % + [Received damage x {1 + (Skill Level x 0.2)}] int ratio = (status_get_hp(src) / 100) * sc->data[SC_CRESCENTELBOW]->val1 * status_get_lv(bl) / 125; if (ratio > 5000) ratio = 5000; // Maximum of 5000% ATK @@ -4638,42 +5081,56 @@ int battle_calc_return_damage(struct block_list* bl, struct block_list *src, int status_damage(src, bl, status_damage(bl, src, rdamage, 0, 0, 1)/10, 0, 0, 1); status_change_end(bl, SC_CRESCENTELBOW, INVALID_TIMER); return 0; // Just put here to minimize redundancy - }else if (flag & BF_SHORT) {//Bounces back part of the damage. - if ( sd && sd->bonus.short_weapon_damage_return ) { - rdamage += damage * sd->bonus.short_weapon_damage_return / 100; - if(rdamage < 1) rdamage = 1; + } + if( flag & BF_SHORT) {//Bounces back part of the damage. + if ( sd && sd->bonus.short_weapon_damage_return ){ + NORMALIZE_RDAMAGE(damage * sd->bonus.short_weapon_damage_return / 100); + rdelay = clif->damage(src, src, iTimer->gettick(), status_get_amotion(src), status_get_dmotion(src), rdamage, 1, 4, 0); } if( sc && sc->count ) { - if ( sc->data[SC_REFLECTSHIELD] && skill_id != WS_CARTTERMINATION ) { - rdamage += damage * sc->data[SC_REFLECTSHIELD]->val2 / 100; - if (rdamage < 1) rdamage = 1; + if( sc->data[SC_REFLECTSHIELD] && skill_id != WS_CARTTERMINATION ){ + NORMALIZE_RDAMAGE(damage * sc->data[SC_REFLECTSHIELD]->val2 / 100); + rdelay = clif->skill_damage(src, src, iTimer->gettick(), status_get_amotion(src), status_get_dmotion(src), rdamage, 1, CR_REFLECTSHIELD, 1, 4); + } + if( sc->data[SC_LG_REFLECTDAMAGE] && rand()%100 < (30 + 10*sc->data[SC_LG_REFLECTDAMAGE]->val1) ) { + if( skill_id != HT_LANDMINE && skill_id != HT_CLAYMORETRAP + && skill_id != RA_CLUSTERBOMB && (skill_id <= RA_VERDURETRAP || skill_id > RA_ICEBOUNDTRAP && skill_id != MA_LANDMINE) ){ + NORMALIZE_RDAMAGE((*dmg) * sc->data[SC_LG_REFLECTDAMAGE]->val2 / 100); + rdelay = clif->damage(src, src, iTimer->gettick(), status_get_amotion(src), status_get_dmotion(src), rdamage, 1, 4, 0); + } } - if(sc->data[SC_DEATHBOUND] && skill_id != WS_CARTTERMINATION && !(src->type == BL_MOB && is_boss(src)) ) { + if( sc->data[SC_DEATHBOUND] && skill_id != WS_CARTTERMINATION && !is_boss(src) ) { uint8 dir = iMap->calc_dir(bl,src->x,src->y), - t_dir = unit_getdir(bl); - - if( distance_bl(src,bl) <= 0 || !iMap->check_dir(dir,t_dir) ) { - int rd1 = 0; - rd1 = min(damage,status_get_max_hp(bl)) * sc->data[SC_DEATHBOUND]->val2 / 100; // Amplify damage. - *dmg = rd1 * 30 / 100; // Received damage = 30% of amplifly damage. - clif->skill_damage(src,bl,iTimer->gettick(), status_get_amotion(src), 0, -30000, 1, RK_DEATHBOUND, sc->data[SC_DEATHBOUND]->val1,6); - status_change_end(bl,SC_DEATHBOUND,INVALID_TIMER); - rdamage += rd1; - if (rdamage < 1) rdamage = 1; + t_dir = unit_getdir(bl); + + if( !iMap->check_dir(dir,t_dir) ) { + int rd1 = damage * sc->data[SC_DEATHBOUND]->val2 / 100; // Amplify damage. + trdamage += rdamage = rd1 - (*dmg = rd1 * 30 / 100); // not normalized as intended. + clif->skill_damage(src, bl, iTimer->gettick(), status_get_amotion(src), 0, -3000, 1, RK_DEATHBOUND, sc->data[SC_DEATHBOUND]->val1, 6); + skill->blown(bl, src, skill->get_blewcount(RK_DEATHBOUND, sc->data[SC_DEATHBOUND]->val1), unit_getdir(src), 0); + if( skill_id ) + status_change_end(bl, SC_DEATHBOUND, INVALID_TIMER); + rdelay = clif->damage(src, src, iTimer->gettick(), status_get_amotion(src), status_get_dmotion(src), rdamage, 1, 4, 0); } } } + if( sc->data[SC_SHIELDSPELL_DEF] && sc->data[SC_SHIELDSPELL_DEF]->val1 == 2 && !is_boss(src) ){ + NORMALIZE_RDAMAGE(damage * sc->data[SC_SHIELDSPELL_DEF]->val2 / 100); + rdelay = clif->damage(src, src, iTimer->gettick(), status_get_amotion(src), status_get_dmotion(src), rdamage, 1, 4, 0); + } } else { - if (sd && sd->bonus.long_weapon_damage_return) { - rdamage += damage * sd->bonus.long_weapon_damage_return / 100; - if (rdamage < 1) rdamage = 1; + if (sd && sd->bonus.long_weapon_damage_return){ + NORMALIZE_RDAMAGE(damage * sd->bonus.long_weapon_damage_return / 100); + rdelay = clif->damage(src, src, iTimer->gettick(), status_get_amotion(src), status_get_dmotion(src), rdamage, 1, 4, 0); } } + + if( !(sc && sc->data[SC_DEATHBOUND]) ){ + if( sc && sc->data[SC_KYOMU] ) // Nullify reflecting ability + return 0; + } - if( sc && sc->data[SC_KYOMU] ) // Nullify reflecting ability - rdamage = 0; - - return rdamage; + return max(0, trdamage); } void battle_drain(TBL_PC *sd, struct block_list *tbl, int rdamage, int ldamage, int race, int boss) @@ -4898,17 +5355,17 @@ enum damage_lv battle_weapon_attack(struct block_list* src, struct block_list* t return ATK_DEF; return ATK_MISS; } - if( sc->data[SC_GT_ENERGYGAIN] ) { - if( sd && rnd()%100 < 10 + 5 * sc->data[SC_GT_ENERGYGAIN]->val1) + if( sc->data[SC_GENTLETOUCH_ENERGYGAIN] ) { + if( sd && rnd()%100 < 10 + 5 * sc->data[SC_GENTLETOUCH_ENERGYGAIN]->val1) pc->addspiritball(sd, - skill->get_time(MO_CALLSPIRITS, sc->data[SC_GT_ENERGYGAIN]->val1), - sc->data[SC_GT_ENERGYGAIN]->val1); + skill->get_time(MO_CALLSPIRITS, sc->data[SC_GENTLETOUCH_ENERGYGAIN]->val1), + sc->data[SC_GENTLETOUCH_ENERGYGAIN]->val1); } - if( tsc && tsc->data[SC_GT_ENERGYGAIN] ) { - if( tsd && rnd()%100 < 10 + 5 * tsc->data[SC_GT_ENERGYGAIN]->val1) + if( tsc && tsc->data[SC_GENTLETOUCH_ENERGYGAIN] ) { + if( tsd && rnd()%100 < 10 + 5 * tsc->data[SC_GENTLETOUCH_ENERGYGAIN]->val1) pc->addspiritball(tsd, - skill->get_time(MO_CALLSPIRITS, tsc->data[SC_GT_ENERGYGAIN]->val1), - tsc->data[SC_GT_ENERGYGAIN]->val1); + skill->get_time(MO_CALLSPIRITS, tsc->data[SC_GENTLETOUCH_ENERGYGAIN]->val1), + tsc->data[SC_GENTLETOUCH_ENERGYGAIN]->val1); } if( sc && sc->data[SC_CRUSHSTRIKE] ){ uint16 skill_lv = sc->data[SC_CRUSHSTRIKE]->val1; @@ -4958,19 +5415,6 @@ enum damage_lv battle_weapon_attack(struct block_list* src, struct block_list* t skill_id = AB_DUPLELIGHT_MAGIC; skill->attack(skill->get_type(skill_id), src, src, target, skill_id, sc->data[SC_DUPLELIGHT]->val1, tick, SD_LEVEL); } - - rdamage = battle->calc_return_damage(target,src, &damage, wd.flag, 0); - if( rdamage > 0 ) { - if( tsc && tsc->data[SC_REFLECTDAMAGE] ) { - if( src != target ) {// Don't reflect your own damage (Grand Cross) - iMap->foreachinshootrange(battle->damage_area,target,skill->get_splash(LG_REFLECTDAMAGE,1),BL_CHAR,tick,target,wd.amotion,wd.dmotion,rdamage,tstatus->race); - } - } else { - rdelay = clif->damage(src, src, tick, wd.amotion, sstatus->dmotion, rdamage, 1, 4, 0); - //Use Reflect Shield to signal this kind of skill trigger. [Skotlex] - skill->additional_effect(target,src,CR_REFLECTSHIELD,1,BF_WEAPON|BF_SHORT|BF_NORMAL,ATK_DEF,tick); - } - } } wd.dmotion = clif->damage(src, target, tick, wd.amotion, wd.dmotion, wd.damage, wd.div_ , wd.type, wd.damage2); @@ -5023,7 +5467,7 @@ enum damage_lv battle_weapon_attack(struct block_list* src, struct block_list* t uint16 skill_id = sc->data[SC_AUTOSPELL]->val2; uint16 skill_lv = sc->data[SC_AUTOSPELL]->val3; int i = rnd()%100; - if (sc->data[SC_SPIRIT] && sc->data[SC_SPIRIT]->val2 == SL_SAGE) + if (sc->data[SC_SOULLINK] && sc->data[SC_SOULLINK]->val2 == SL_SAGE) i = 0; //Max chance, no skill_lv reduction. [Skotlex] if (i >= 50) skill_lv -= 2; else if (i >= 15) skill_lv--; @@ -5099,7 +5543,7 @@ enum damage_lv battle_weapon_attack(struct block_list* src, struct block_list* t sd->state.autocast = 0; sd->ud.canact_tick = tick + skill->delay_fix(src, r_skill, r_lv); - clif->status_change(src, SI_ACTIONDELAY, 1, skill->delay_fix(src, r_skill, r_lv), 0, 0, 1); + clif->status_change(src, SI_POSTDELAY, 1, skill->delay_fix(src, r_skill, r_lv), 0, 0, 1); } } @@ -5110,11 +5554,6 @@ enum damage_lv battle_weapon_attack(struct block_list* src, struct block_list* t battle->drain(sd, target, wd.damage, wd.damage2, tstatus->race, is_boss(target)); } } - if (rdamage > 0 && !(tsc && tsc->data[SC_REFLECTDAMAGE])) { //By sending attack type "none" skill->additional_effect won't be invoked. [Skotlex] - if(tsd && src != target) - battle->drain(tsd, src, rdamage, rdamage, sstatus->race, is_boss(src)); - battle->delay_damage(tick, wd.amotion, target, src, 0, CR_REFLECTSHIELD, 0, rdamage, ATK_DEF, rdelay, true); - } if (tsc) { if (tsc->data[SC_POISONREACT] && @@ -5243,7 +5682,7 @@ int battle_check_target( struct block_list *src, struct block_list *target,int f if (((TBL_PC*)target)->invincible_timer != INVALID_TIMER || pc_isinvisible((TBL_PC*)target)) return -1; //Cannot be targeted yet. if( sc && sc->count ) { - if( sc->data[SC_VOICEOFSIREN] && sc->data[SC_VOICEOFSIREN]->val2 == target->id ) + if( sc->data[SC_SIREN] && sc->data[SC_SIREN]->val2 == target->id ) return -1; } } @@ -5265,6 +5704,7 @@ int battle_check_target( struct block_list *src, struct block_list *target,int f if( skill->get_inf2(su->group->skill_id)&INF2_TRAP ) { //Only a few skills can target traps... switch( battle->get_current_skill(src) ) { case RK_DRAGONBREATH:// it can only hit traps in pvp/gvg maps + case RK_DRAGONBREATH_WATER: if( !map[m].flag.pvp && !map[m].flag.gvg ) break; case 0://you can hit them without skills @@ -5838,7 +6278,6 @@ static const struct _battle_data { { "ignore_items_gender", &battle_config.ignore_items_gender, 1, 0, 1, }, { "copyskill_restrict", &battle_config.copyskill_restrict, 2, 0, 2, }, { "berserk_cancels_buffs", &battle_config.berserk_cancels_buffs, 0, 0, 1, }, - { "debuff_on_logout", &battle_config.debuff_on_logout, 1|2, 0, 1|2, }, { "monster_ai", &battle_config.mob_ai, 0x000, 0x000, 0x77F, }, { "hom_setting", &battle_config.hom_setting, 0xFFFF, 0x0000, 0xFFFF, }, { "dynamic_mobs", &battle_config.dynamic_mobs, 1, 0, 1, }, @@ -6239,9 +6678,15 @@ void battle_defaults(void) { battle->drain = battle_drain; battle->calc_return_damage = battle_calc_return_damage; battle->calc_weapon_attack = battle_calc_weapon_attack; + battle->calc_weapon_damage = battle_calc_weapon_damage; + battle->calc_defense = battle_calc_defense; battle->attr_ratio = battle_attr_ratio; battle->attr_fix = battle_attr_fix; battle->calc_cardfix = battle_calc_cardfix; + battle->calc_elefix = battle_calc_elefix; + battle->calc_masteryfix = battle_calc_masteryfix; + battle->calc_skillratio = battle_calc_skillratio; + battle->calc_sizefix = battle_calc_sizefix; battle->get_master = battle_get_master; battle->get_targeted = battle_gettargeted; battle->get_enemy = battle_getenemy; diff --git a/src/map/battle.h b/src/map/battle.h index f2d870032..bbe723f36 100644 --- a/src/map/battle.h +++ b/src/map/battle.h @@ -348,7 +348,6 @@ struct Battle_Config { int copyskill_restrict; // [Aru] int berserk_cancels_buffs; // [Aru] - int debuff_on_logout; // Removes a few "official" negative Scs on logout. [Skotlex] int mob_ai; //Configures various mob_ai settings to make them smarter or dumber(official). [Skotlex] int hom_setting; //Configures various homunc settings which make them behave unlike normal characters.. [Skotlex] int dynamic_mobs; // Dynamic Mobs [Wizputer] - battle.conf flag implemented by [random] @@ -489,13 +488,25 @@ struct battle_interface { /* drain damage */ void (*drain) (struct map_session_data *sd, struct block_list *tbl, int rdamage, int ldamage, int race, int boss); /* damage return/reflect */ - int (*calc_return_damage) (struct block_list *bl, struct block_list *src, int *, int flag, uint16 skill_id); + int (*calc_return_damage) (struct block_list *bl, struct block_list *src, int *, int flag, uint16 skill_id, int*); /* attribute rate */ int (*attr_ratio) (int atk_elem, int def_type, int def_lv); /* applies attribute modifiers */ int (*attr_fix) (struct block_list *src, struct block_list *target, int damage, int atk_elem, int def_type, int def_lv); /* applies card modifiers */ int (*calc_cardfix) (int attack_type, struct block_list *src, struct block_list *target, int nk, int s_ele, int s_ele_, int damage, int left, int flag); + /* applies element modifiers */ + int (*calc_elefix) (struct block_list *src, struct block_list *target, uint16 skill_id, uint16 skill_lv, int damage, int nk, int n_ele, int s_ele, int s_ele_, bool left, int flag); + /* applies mastery modifiers */ + int (*calc_masteryfix) (struct block_list *src, struct block_list *target, uint16 skill_id, uint16 skill_lv, int damage, int div, bool left, bool weapon); + /* applies skill modifiers */ + int (*calc_skillratio) (int attack_type, struct block_list *src, struct block_list *target, uint16 skill_id, uint16 skill_lv, int skillratio, int flag); + /* applies size modifiers */ + int (*calc_sizefix) (struct map_session_data *sd, int damage, int type, int size, bool ignore); + /* get weapon damage */ + int (*calc_weapon_damage) (struct block_list *src, struct block_list *bl, uint16 skill_id, uint16 skill_lv, struct weapon_atk *watk, int nk, bool n_ele, short s_ele, short s_ele_, int size, int type, int flag, int flag2); + /* applies defense reductions */ + int (*calc_defense) (int attack_type, struct block_list *src, struct block_list *target, uint16 skill_id, uint16 skill_lv, int damage, int flag, int pdef); /* get master (who does this unit respond to?) */ struct block_list *(*get_master) (struct block_list *src); /* returns a random unit who is targeting this unit */ @@ -521,7 +532,12 @@ struct battle_interface { int (*blewcount_bonus) (struct map_session_data *sd, uint16 skill_id); /* skill range criteria */ int (*range_type) (struct block_list *src, struct block_list *target, uint16 skill_id, uint16 skill_lv); - int (*calc_base_damage) (struct status_data *status, struct weapon_atk *wa, struct status_change *sc, unsigned short t_size, struct map_session_data *sd, int flag); + int (*calc_base_damage) +#ifdef RENEWAL + (struct block_list *src, struct block_list *bl, uint16 skill_id, uint16 skill_lv, int nk, bool n_ele, short s_ele, short s_ele_, int type, int flag, int flag2); +#else + (struct status_data *status, struct weapon_atk *wa, struct status_change *sc, unsigned short t_size, struct map_session_data *sd, int flag); +#endif struct Damage (*calc_misc_attack) (struct block_list *src,struct block_list *target,uint16 skill_id,uint16 skill_lv,int mflag); struct Damage (*calc_magic_attack) (struct block_list *src,struct block_list *target,uint16 skill_id,uint16 skill_lv,int mflag); int (*adjust_skill_damage) (int m, unsigned short skill_id); diff --git a/src/map/clif.c b/src/map/clif.c index 202469605..2f8ecd6a4 100644 --- a/src/map/clif.c +++ b/src/map/clif.c @@ -1259,12 +1259,12 @@ void clif_spiritball_single(int fd, struct map_session_data *sd) { /*========================================== * Kagerou/Oboro amulet spirit *------------------------------------------*/ -void clif_talisman_single(int fd, struct map_session_data *sd, short type) { +void clif_charm_single(int fd, struct map_session_data *sd, short type) { WFIFOHEAD(fd, packet_len(0x08cf)); WFIFOW(fd,0)=0x08cf; WFIFOL(fd,2)=sd->bl.id; WFIFOW(fd,6)=type; - WFIFOW(fd,8)=sd->talisman[type]; + WFIFOW(fd,8)=sd->charm[type]; WFIFOSET(fd, packet_len(0x08cf)); } @@ -1358,8 +1358,8 @@ int clif_spawn(struct block_list *bl) clif->sc_load(&sd->bl, sd->bl.id,AREA,StatusIconChangeTable[sd->sc_display[i]->type],sd->sc_display[i]->val1,sd->sc_display[i]->val2,sd->sc_display[i]->val3); } for(i = 1; i < 5; i++){ - if( sd->talisman[i] > 0 ) - clif->talisman(sd, i); + if( sd->charm[i] > 0 ) + clif->charm(sd, i); } if (sd->status.robe) clif->refreshlook(bl,bl->id,LOOK_ROBE,sd->status.robe,AREA); @@ -3461,7 +3461,9 @@ void clif_arrowequip(struct map_session_data *sd,int val) nullpo_retv(sd); pc_stop_attack(sd); // [Valaris] - +#if PACKETVER >= 20121128 + clif->status_change(&sd->bl, SI_CLIENT_ONLY_EQUIP_ARROW, 1, INVALID_TIMER, 0, 0, 0); +#endif fd=sd->fd; WFIFOHEAD(fd, packet_len(0x013c)); WFIFOW(fd,0)=0x013c; @@ -4309,8 +4311,8 @@ void clif_getareachar_pc(struct map_session_data* sd,struct map_session_data* ds if(dstsd->spiritball > 0) clif->spiritball_single(sd->fd, dstsd); for(i = 1; i < 5; i++){ - if( dstsd->talisman[i] > 0 ) - clif->talisman_single(sd->fd, dstsd, i); + if( dstsd->charm[i] > 0 ) + clif->charm_single(sd->fd, dstsd, i); } for( i = 0; i < dstsd->sc_display_count; i++ ) { clif->sc_load(&sd->bl,dstsd->bl.id,SELF,StatusIconChangeTable[dstsd->sc_display[i]->type],dstsd->sc_display[i]->val1,dstsd->sc_display[i]->val2,dstsd->sc_display[i]->val3); @@ -4471,9 +4473,9 @@ int clif_damage(struct block_list* src, struct block_list* dst, unsigned int tic type = clif_calc_delay(type,div,damage+damage2,ddelay); sc = status_get_sc(dst); if(sc && sc->count) { - if(sc->data[SC_HALLUCINATION]) { - if(damage) damage = damage*(sc->data[SC_HALLUCINATION]->val2) + rnd()%100; - if(damage2) damage2 = damage2*(sc->data[SC_HALLUCINATION]->val2) + rnd()%100; + if(sc->data[SC_ILLUSION]) { + if(damage) damage = damage*(sc->data[SC_ILLUSION]->val2) + rnd()%100; + if(damage2) damage2 = damage2*(sc->data[SC_ILLUSION]->val2) + rnd()%100; } } @@ -4643,12 +4645,21 @@ void clif_getareachar_item(struct map_session_data* sd,struct flooritem_data* fi /// Notifies the client of a skill unit. /// 011f .L .L .W .W .B .B (ZC_SKILL_ENTRY) /// 01c9 .L .L .W .W .B .B .B .80B (ZC_SKILL_ENTRY2) +/// 08c7 .W L .L .W .W .B .W .B (ZC_SKILL_ENTRY3) +/// 099f .W L .L .W .W .L .W .B (ZC_SKILL_ENTRY4) void clif_getareachar_skillunit(struct map_session_data *sd, struct skill_unit *unit) { - int fd = sd->fd; + int fd = sd->fd, header = 0x11f, pos=0; if( unit->group->state.guildaura ) return; +#if PACKETVER >= 20130320 + if(unit->group->unit_id > UCHAR_MAX){ + header = 0x99f; + pos = 2; + } +#endif + #if PACKETVER >= 3 if(unit->group->unit_id==UNT_GRAFFITI) { // Graffiti [Valaris] WFIFOHEAD(fd,packet_len(0x1c9)); @@ -4665,20 +4676,26 @@ void clif_getareachar_skillunit(struct map_session_data *sd, struct skill_unit * return; } #endif - WFIFOHEAD(fd,packet_len(0x11f)); - WFIFOW(fd, 0)=0x11f; - WFIFOL(fd, 2)=unit->bl.id; - WFIFOL(fd, 6)=unit->group->src_id; - WFIFOW(fd,10)=unit->bl.x; - WFIFOW(fd,12)=unit->bl.y; + WFIFOHEAD(fd,packet_len(header)); + WFIFOW(fd, 0)=header; + if(pos > 0) + WFIFOL(fd, pos)=packet_len(header); + WFIFOL(fd, 2 + pos)=unit->bl.id; + WFIFOL(fd, 6 + pos)=unit->group->src_id; + WFIFOW(fd,10 + pos)=unit->bl.x; + WFIFOW(fd,12 + pos)=unit->bl.y; if (battle_config.traps_setting&1 && skill->get_inf2(unit->group->skill_id)&INF2_TRAP) WFIFOB(fd,14)=UNT_DUMMYSKILL; //Use invisible unit id for traps. else if (skill->get_unit_flag(unit->group->skill_id) & UF_RANGEDSINGLEUNIT && !(unit->val2 & UF_RANGEDSINGLEUNIT)) WFIFOB(fd,14)=UNT_DUMMYSKILL; //Use invisible unit id for traps. - else + else if(pos > 0){ + WFIFOL(fd,16)=unit->group->unit_id; + WFIFOW(fd,20)=unit->range; + pos += 5; + }else WFIFOB(fd,14)=unit->group->unit_id; - WFIFOB(fd,15)=1; // ignored by client (always gets set to 1) - WFIFOSET(fd,packet_len(0x11f)); + WFIFOB(fd,15 + pos)=1; // ignored by client (always gets set to 1) + WFIFOSET(fd,packet_len(header)); if(unit->group->skill_id == WZ_ICEWALL) clif->changemapcell(fd,unit->bl.m,unit->bl.x,unit->bl.y,5,SELF); @@ -5134,8 +5151,8 @@ int clif_skill_damage(struct block_list *src,struct block_list *dst,unsigned int type = clif_calc_delay(type,div,damage,ddelay); sc = status_get_sc(dst); if(sc && sc->count) { - if(sc->data[SC_HALLUCINATION] && damage) - damage = damage*(sc->data[SC_HALLUCINATION]->val2) + rnd()%100; + if(sc->data[SC_ILLUSION] && damage) + damage = damage*(sc->data[SC_ILLUSION]->val2) + rnd()%100; } #if PACKETVER < 3 @@ -5223,8 +5240,8 @@ int clif_skill_damage2(struct block_list *src,struct block_list *dst,unsigned in sc = status_get_sc(dst); if(sc && sc->count) { - if(sc->data[SC_HALLUCINATION] && damage) - damage = damage*(sc->data[SC_HALLUCINATION]->val2) + rnd()%100; + if(sc->data[SC_ILLUSION] && damage) + damage = damage*(sc->data[SC_ILLUSION]->val2) + rnd()%100; } WBUFW(buf,0)=0x115; @@ -5330,12 +5347,20 @@ void clif_skill_poseffect(struct block_list *src,uint16 skill_id,int val,int x,i void clif_skill_setunit(struct skill_unit *unit) { unsigned char buf[128]; + int header = 0x11f, pos = 0; nullpo_retv(unit); if( unit->group->state.guildaura ) return; +#if PACKETVER >= 20130320 + if(unit->group->unit_id > UCHAR_MAX){ + header = 0x99f; + pos = 2; + } +#endif + #if PACKETVER >= 3 if(unit->group->unit_id==UNT_GRAFFITI) { // Graffiti [Valaris] WBUFW(buf, 0)=0x1c9; @@ -5351,19 +5376,25 @@ void clif_skill_setunit(struct skill_unit *unit) return; } #endif - WBUFW(buf, 0)=0x11f; - WBUFL(buf, 2)=unit->bl.id; - WBUFL(buf, 6)=unit->group->src_id; - WBUFW(buf,10)=unit->bl.x; - WBUFW(buf,12)=unit->bl.y; + WBUFW(buf, 0)=header; + if(pos > 0) + WBUFW(buf, pos)=packet_len(header); + WBUFL(buf, 2 + pos)=unit->bl.id; + WBUFL(buf, 6 + pos)=unit->group->src_id; + WBUFW(buf,10 + pos)=unit->bl.x; + WBUFW(buf,12 + pos)=unit->bl.y; if (unit->group->state.song_dance&0x1 && unit->val2&UF_ENSEMBLE) WBUFB(buf,14)=unit->val2&UF_SONG?UNT_DISSONANCE:UNT_UGLYDANCE; else if (skill->get_unit_flag(unit->group->skill_id) & UF_RANGEDSINGLEUNIT && !(unit->val2 & UF_RANGEDSINGLEUNIT)) WBUFB(buf, 14) = UNT_DUMMYSKILL; // Only display the unit at center. - else + else if(pos > 0){ + WBUFL(buf,16)=unit->group->unit_id; + WBUFW(buf,20)=unit->range; + pos += 5; + }else WBUFB(buf,14)=unit->group->unit_id; - WBUFB(buf,15)=1; // ignored by client (always gets set to 1) - clif->send(buf,packet_len(0x11f),&unit->bl,AREA); + WBUFB(buf,15 + pos)=1; // ignored by client (always gets set to 1) + clif->send(buf,packet_len(header),&unit->bl,AREA); } @@ -5388,9 +5419,10 @@ void clif_skill_warppoint(struct map_session_data* sd, uint16 skill_id, uint16 s WFIFOSET(fd,packet_len(0x11c)); sd->menuskill_id = skill_id; - if (skill_id == AL_WARP) + if (skill_id == AL_WARP){ sd->menuskill_val = (sd->ud.skillx<<16)|sd->ud.skilly; //Store warp position here. - else + sd->state.workinprogress = 3; + }else sd->menuskill_val = skill_lv; } @@ -5423,10 +5455,11 @@ void clif_skill_memomessage(struct map_session_data* sd, int type) /// type: /// 0 = "Unable to Teleport in this area" in color 0xFFFF00 (cyan) /// 1 = "Saved point cannot be memorized." in color 0x0000FF (red) +/// 2 = "This skill cannot be used within this area." in color 0xFFFF00 (cyan) /// /// @param sd Who receives the message /// @param type What message -void clif_skill_teleportmessage(struct map_session_data *sd, int type) +void clif_skill_mapinfomessage(struct map_session_data *sd, int type) { int fd; @@ -5621,6 +5654,9 @@ void clif_status_change(struct block_list *bl,int type,int flag,int tick,int val if (!(status_type2relevant_bl_types(type)&bl->type)) // only send status changes that actually matter to the client return; + if ( tick < 0 ) + tick = 9999; + sd = BL_CAST(BL_PC, bl); p.PacketType = status_changeType; @@ -6061,6 +6097,7 @@ void clif_item_identify_list(struct map_session_data *sd) WFIFOSET(fd,WFIFOW(fd,2)); sd->menuskill_id = MC_IDENTIFY; sd->menuskill_val = c; + sd->state.workinprogress = 3; } } @@ -6163,25 +6200,20 @@ void clif_item_refine_list(struct map_session_data *sd) int fd; uint16 skill_lv; int wlv; - int refine_item[5]; nullpo_retv(sd); skill_lv = pc->checkskill(sd,WS_WEAPONREFINE); fd=sd->fd; - - refine_item[0] = -1; - refine_item[1] = pc->search_inventory(sd,1010); - refine_item[2] = pc->search_inventory(sd,1011); - refine_item[3] = refine_item[4] = pc->search_inventory(sd,984); - + WFIFOHEAD(fd, MAX_INVENTORY * 13 + 4); WFIFOW(fd,0)=0x221; for(i=c=0;istatus.inventory[i].nameid > 0 && sd->status.inventory[i].refine < skill_lv && - sd->status.inventory[i].identify && (wlv=itemdb_wlv(sd->status.inventory[i].nameid)) >=1 && - refine_item[wlv]!=-1 && !(sd->status.inventory[i].equip&EQP_ARMS)){ + if(sd->status.inventory[i].nameid > 0 && sd->status.inventory[i].identify + && (wlv=itemdb_wlv(sd->status.inventory[i].nameid)) >=1 + && !sd->inventory_data[i]->flag.no_refine + && !(sd->status.inventory[i].equip&EQP_ARMS)){ WFIFOW(fd,c*13+ 4)=i+2; WFIFOW(fd,c*13+ 6)=sd->status.inventory[i].nameid; WFIFOB(fd,c*13+ 8)=sd->status.inventory[i].refine; @@ -8498,8 +8530,8 @@ void clif_refresh(struct map_session_data *sd) if (sd->spiritball) clif->spiritball_single(sd->fd, sd); for(i = 1; i < 5; i++){ - if( sd->talisman[i] > 0 ) - clif->talisman_single(sd->fd, sd, i); + if( sd->charm[i] > 0 ) + clif->charm_single(sd->fd, sd, i); } if (sd->vd.cloth_color) clif->refreshlook(&sd->bl,sd->bl.id,LOOK_CLOTHES_COLOR,sd->vd.cloth_color,SELF); @@ -9499,7 +9531,7 @@ void clif_parse_LoadEndAck(int fd,struct map_session_data *sd) if (iMap->night_flag && map[sd->bl.m].flag.nightenabled) { sd->state.night = 1; - clif->status_change(&sd->bl, SI_NIGHT, 1, 0, 0, 0, 0); + clif->status_change(&sd->bl, SI_SKE, 1, 0, 0, 0, 0); } // Notify everyone that this char logged in [Skotlex]. @@ -9537,11 +9569,11 @@ void clif_parse_LoadEndAck(int fd,struct map_session_data *sd) if( iMap->night_flag && map[sd->bl.m].flag.nightenabled ) { //Display night. if( !sd->state.night ) { sd->state.night = 1; - clif->sc_end(&sd->bl, sd->bl.id, SELF, SI_NIGHT); + clif->sc_end(&sd->bl, sd->bl.id, SELF, SI_SKE); } } else if( sd->state.night ) { //Clear night display. sd->state.night = 0; - clif->sc_end(&sd->bl, sd->bl.id, SELF, SI_NIGHT); + clif->sc_end(&sd->bl, sd->bl.id, SELF, SI_SKE); } if( map[sd->bl.m].flag.battleground ) { @@ -9586,7 +9618,7 @@ void clif_parse_LoadEndAck(int fd,struct map_session_data *sd) npc_script_event(sd, NPCE_LOADMAP); if (pc->checkskill(sd, SG_DEVIL) && !pc->nextjobexp(sd)) //blindness [Komurka] - clif->sc_end(&sd->bl, sd->bl.id, SELF, SI_DEVIL); + clif->sc_end(&sd->bl, sd->bl.id, SELF, SI_DEVIL1); if (sd->sc.opt2) //Client loses these on warp. clif->changeoption(&sd->bl); @@ -9862,7 +9894,7 @@ void clif_parse_GlobalMessage(int fd, struct map_session_data* sd) if( atcommand->parse(fd, sd, message, 1) ) return; - if( sd->sc.data[SC_BERSERK] || sd->sc.data[SC_DEEPSLEEP] || sd->sc.data[SC__BLOODYLUST] || (sd->sc.data[SC_NOCHAT] && sd->sc.data[SC_NOCHAT]->val1&MANNER_NOCHAT) ) + if( sd->sc.data[SC_BERSERK] || sd->sc.data[SC__BLOODYLUST] || sd->sc.data[SC_DEEP_SLEEP] || (sd->sc.data[SC_NOCHAT] && sd->sc.data[SC_NOCHAT]->val1&MANNER_NOCHAT) ) return; if( battle_config.min_chat_delay ) { //[Skotlex] @@ -10321,7 +10353,7 @@ void clif_parse_WisMessage(int fd, struct map_session_data* sd) if ( atcommand->parse(fd, sd, message, 1) ) return; - if (sd->sc.data[SC_BERSERK] || sd->sc.data[SC_DEEPSLEEP] || sd->sc.data[SC__BLOODYLUST] || (sd->sc.data[SC_NOCHAT] && sd->sc.data[SC_NOCHAT]->val1&MANNER_NOCHAT)) + if (sd->sc.data[SC_BERSERK] || sd->sc.data[SC__BLOODYLUST] || sd->sc.data[SC_DEEP_SLEEP] || (sd->sc.data[SC_NOCHAT] && sd->sc.data[SC_NOCHAT]->val1&MANNER_NOCHAT)) return; if (battle_config.min_chat_delay) { //[Skotlex] @@ -10602,7 +10634,7 @@ void clif_parse_EquipItem(int fd,struct map_session_data *sd) return; } else if ( sd->state.storage_flag || sd->sc.opt1 ) ; //You can equip/unequip stuff while storage is open/under status changes - else if ( pc_cant_act2(sd) ) + else if ( pc_cant_act2(sd) || sd->state.prerefining ) return; if(!sd->status.inventory[index].identify) { @@ -10730,7 +10762,7 @@ void clif_parse_UnequipItem(int fd,struct map_session_data *sd) return; } else if ( sd->state.storage_flag || sd->sc.opt1 ) ; //You can equip/unequip stuff while storage is open/under status changes - else if ( pc_cant_act2(sd) ) + else if ( pc_cant_act2(sd) || sd->state.prerefining ) return; index = RFIFOW(fd,2)-2; @@ -10751,7 +10783,12 @@ void clif_parse_NpcClicked(int fd,struct map_session_data *sd) clif_clearunit_area(&sd->bl,CLR_DEAD); return; } - + if( sd->npc_id || sd->state.workinprogress&2 ){ +#ifdef RENEWAL + clif->msg(sd, 0x783); // TODO look for the client date that has this message. +#endif + return; + } if ( pc_cant_act2(sd) || !(bl = iMap->id2bl(RFIFOL(fd,2))) ) return; @@ -10761,8 +10798,10 @@ void clif_parse_NpcClicked(int fd,struct map_session_data *sd) clif->pActionRequest_sub(sd, 0x07, bl->id, iTimer->gettick()); break; case BL_NPC: - if( sd->ud.skilltimer != INVALID_TIMER ) { - clif->colormes(fd,COLOR_WHITE,msg_txt(1476)); + if( sd->ud.skill_id < RK_ENCHANTBLADE && sd->ud.skilltimer != INVALID_TIMER ) {// TODO: should only work with none 3rd job skills +#ifdef RENEWAL + clif->msg(sd, 0x783); +#endif break; } if( bl->m != -1 )// the user can't click floating npcs directly (hack attempt) @@ -11270,7 +11309,7 @@ void clif_parse_UseSkillToId(int fd, struct map_session_data *sd) // Whether skill fails or not is irrelevant, the char ain't idle. [Skotlex] sd->idletime = last_tick; - if( sd->npc_id ){ + if( sd->npc_id || sd->state.workinprogress&1 ){ #ifdef RENEWAL clif->msg(sd, 0x783); // TODO look for the client date that has this message. #endif @@ -11563,6 +11602,8 @@ void clif_parse_WeaponRefine(int fd, struct map_session_data *sd) { int idx; + sd->state.prerefining = 0; + if (sd->menuskill_id != WS_WEAPONREFINE) //Packet exploit? return; if (pc_istrading(sd)) { @@ -11664,6 +11705,8 @@ void clif_parse_ItemIdentify(int fd,struct map_session_data *sd) if (sd->menuskill_id != MC_IDENTIFY) return; if( idx == -1 ) {// cancel pressed + sd->state.workinprogress = 0; + clif->item_identified(sd,idx-2,1); clif_menuskill_clear(sd); return; } @@ -12096,7 +12139,7 @@ void clif_parse_PartyMessage(int fd, struct map_session_data* sd) if( atcommand->parse(fd, sd, message, 1) ) return; - if( sd->sc.data[SC_BERSERK] || sd->sc.data[SC_DEEPSLEEP] || sd->sc.data[SC__BLOODYLUST] || (sd->sc.data[SC_NOCHAT] && sd->sc.data[SC_NOCHAT]->val1&MANNER_NOCHAT) ) + if( sd->sc.data[SC_BERSERK] || sd->sc.data[SC__BLOODYLUST] || sd->sc.data[SC_DEEP_SLEEP] || (sd->sc.data[SC_NOCHAT] && sd->sc.data[SC_NOCHAT]->val1&MANNER_NOCHAT) ) return; if( battle_config.min_chat_delay ) @@ -12658,7 +12701,7 @@ void clif_parse_OpenVending(int fd, struct map_session_data* sd) const uint8* data = (uint8*)RFIFOP(fd,85); if( !flag ) - sd->state.prevend = 0; + sd->state.prevend = sd->state.workinprogress = 0; if( sd->sc.data[SC_NOCHAT] && sd->sc.data[SC_NOCHAT]->val1&MANNER_NOROOM ) return; @@ -12937,7 +12980,7 @@ void clif_parse_GuildMessage(int fd, struct map_session_data* sd) if( atcommand->parse(fd, sd, message, 1) ) return; - if( sd->sc.data[SC_BERSERK] || sd->sc.data[SC_DEEPSLEEP] || sd->sc.data[SC__BLOODYLUST] || (sd->sc.data[SC_NOCHAT] && sd->sc.data[SC_NOCHAT]->val1&MANNER_NOCHAT) ) + if( sd->sc.data[SC_BERSERK] || sd->sc.data[SC__BLOODYLUST] || sd->sc.data[SC_DEEP_SLEEP] || (sd->sc.data[SC_NOCHAT] && sd->sc.data[SC_NOCHAT]->val1&MANNER_NOCHAT) ) return; if( battle_config.min_chat_delay ) @@ -15790,7 +15833,7 @@ void clif_parse_BattleChat(int fd, struct map_session_data* sd) if( atcommand->parse(fd, sd, message, 1) ) return; - if( sd->sc.data[SC_BERSERK] || sd->sc.data[SC_DEEPSLEEP] || sd->sc.data[SC__BLOODYLUST] || (sd->sc.data[SC_NOCHAT] && sd->sc.data[SC_NOCHAT]->val1&MANNER_NOCHAT) ) + if( sd->sc.data[SC_BERSERK] || sd->sc.data[SC__BLOODYLUST] || sd->sc.data[SC_DEEP_SLEEP] || (sd->sc.data[SC_NOCHAT] && sd->sc.data[SC_NOCHAT]->val1&MANNER_NOCHAT) ) return; if( battle_config.min_chat_delay ) { @@ -16735,7 +16778,7 @@ int clif_spellbook_list(struct map_session_data *sd) if( itemdb_is_spellbook(sd->status.inventory[i].nameid) ) { WFIFOW(fd, c * 2 + 4) = sd->status.inventory[i].nameid; - c ++; + c++; } } @@ -16926,7 +16969,7 @@ void clif_parse_SkillSelectMenu(int fd, struct map_session_data *sd) { /*========================================== * Kagerou/Oboro amulet spirit *------------------------------------------*/ -void clif_talisman(struct map_session_data *sd,short type) +void clif_charm(struct map_session_data *sd,short type) { unsigned char buf[10]; @@ -16935,7 +16978,7 @@ void clif_talisman(struct map_session_data *sd,short type) WBUFW(buf,0)=0x08cf; WBUFL(buf,2)=sd->bl.id; WBUFW(buf,6)=type; - WBUFW(buf,8)=sd->talisman[type]; + WBUFW(buf,8)=sd->charm[type]; clif->send(buf,packet_len(0x08cf),&sd->bl,AREA); } /// Move Item from or to Personal Tab (CZ_WHATSOEVER) [FE] @@ -17744,7 +17787,7 @@ void clif_defaults(void) { clif->skill_fail = clif_skill_fail; clif->skill_cooldown = clif_skill_cooldown; clif->skill_memomessage = clif_skill_memomessage; - clif->skill_teleportmessage = clif_skill_teleportmessage; + clif->skill_mapinfomessage = clif_skill_mapinfomessage; clif->skill_produce_mix_list = clif_skill_produce_mix_list; clif->cooking_list = clif_cooking_list; clif->autospell = clif_autospell; @@ -17845,8 +17888,8 @@ void clif_defaults(void) { clif->specialeffect_single = clif_specialeffect_single; clif->specialeffect_value = clif_specialeffect_value; clif->millenniumshield = clif_millenniumshield; - clif->talisman = clif_talisman; - clif->talisman_single = clif_talisman_single; + clif->charm = clif_charm; + clif->charm_single = clif_charm_single; clif->snap = clif_snap; clif->weather_check = clif_weather_check; /* sound effects client-side */ diff --git a/src/map/clif.h b/src/map/clif.h index 5393ef5b7..b447687ea 100644 --- a/src/map/clif.h +++ b/src/map/clif.h @@ -231,7 +231,7 @@ enum map_type { // clif_map_type MAPTYPE_UNUSED = 29, }; -enum useskill_fail_cause { // clif_skill_fail +typedef enum useskill_fail_cause { // clif_skill_fail USESKILL_FAIL_LEVEL = 0, USESKILL_FAIL_SP_INSUFFICIENT = 1, USESKILL_FAIL_HP_INSUFFICIENT = 2, @@ -272,7 +272,7 @@ enum useskill_fail_cause { // clif_skill_fail USESKILL_FAIL_CANONBALL = 37, //XXX_USESKILL_FAIL_II_MADOGEAR_ACCELERATION = 38, //XXX_USESKILL_FAIL_II_MADOGEAR_HOVERING_BOOSTER = 39, - USESKILL_FAIL_MADOGEAR_HOVERING = 40, + //XXX_USESKILL_FAIL_MADOGEAR_HOVERING = 40, //XXX_USESKILL_FAIL_II_MADOGEAR_SELFDESTRUCTION_DEVICE = 41, //XXX_USESKILL_FAIL_II_MADOGEAR_SHAPESHIFTER = 42, USESKILL_FAIL_GUILLONTINE_POISON = 43, @@ -316,7 +316,7 @@ enum useskill_fail_cause { // clif_skill_fail USESKILL_FAIL_STYLE_CHANGE_FIGHTER = 81, USESKILL_FAIL_STYLE_CHANGE_GRAPPLER = 82, USESKILL_FAIL_THERE_ARE_NPC_AROUND = 83, -}; +}useskill_fail_cause; enum clif_messages { SKILL_CANT_USE_AREA = 0x536, @@ -571,7 +571,7 @@ struct clif_interface { void (*skill_fail) (struct map_session_data *sd,uint16 skill_id,enum useskill_fail_cause cause,int btype); void (*skill_cooldown) (struct map_session_data *sd, uint16 skill_id, unsigned int tick); void (*skill_memomessage) (struct map_session_data* sd, int type); - void (*skill_teleportmessage) (struct map_session_data *sd, int type); + void (*skill_mapinfomessage) (struct map_session_data *sd, int type); void (*skill_produce_mix_list) (struct map_session_data *sd, int skill_id, int trigger); void (*cooking_list) (struct map_session_data *sd, int trigger, uint16 skill_id, int qty, int list_type); void (*autospell) (struct map_session_data *sd,uint16 skill_lv); @@ -672,8 +672,8 @@ struct clif_interface { void (*specialeffect_single) (struct block_list* bl, int type, int fd); void (*specialeffect_value) (struct block_list* bl, int effect_id, int num, send_target target); void (*millenniumshield) (struct map_session_data *sd, short shields ); - void (*talisman) (struct map_session_data *sd, short type); - void (*talisman_single) (int fd, struct map_session_data *sd, short type); + void (*charm) (struct map_session_data *sd, short type); + void (*charm_single) (int fd, struct map_session_data *sd, short type); void (*snap) ( struct block_list *bl, short x, short y ); void (*weather_check) (struct map_session_data *sd); /* sound effects client-side */ diff --git a/src/map/itemdb.h b/src/map/itemdb.h index c441de26a..ea478d135 100644 --- a/src/map/itemdb.h +++ b/src/map/itemdb.h @@ -22,11 +22,13 @@ #define MAX_ITEMS_PER_COMBO 6 enum item_itemid { + ITEMID_HOLY_WATER = 523, ITEMID_EMPERIUM = 714, ITEMID_YELLOW_GEMSTONE = 715, ITEMID_RED_GEMSTONE = 716, ITEMID_BLUE_GEMSTONE = 717, ITEMID_TRAP = 1065, + ITEMID_FACE_PAINT = 6120, ITEMID_STONE = 7049, ITEMID_SKULL_ = 7420, ITEMID_TOKEN_OF_SIEGFRIED = 7621, @@ -66,6 +68,7 @@ enum { ITEMID_CAMOUFLAGE_GENERATOR, ITEMID_HIGH_QUALITY_COOLER, ITEMID_SPECIAL_COOLER, + ITEMID_MONKEY_SPANNER = 6186, } mecha_item_list; enum { diff --git a/src/map/map.c b/src/map/map.c index 0dab56d21..510f36109 100644 --- a/src/map/map.c +++ b/src/map/map.c @@ -358,10 +358,10 @@ int map_moveblock(struct block_list *bl, int x1, int y1, unsigned int tick) sc = status_get_sc(bl); skill->unit_move(bl,tick,2); - status_change_end(bl, SC_CLOSECONFINE, INVALID_TIMER); - status_change_end(bl, SC_CLOSECONFINE2, INVALID_TIMER); + status_change_end(bl, SC_RG_CCONFINE_M, INVALID_TIMER); + status_change_end(bl, SC_RG_CCONFINE_S, INVALID_TIMER); // status_change_end(bl, SC_BLADESTOP, INVALID_TIMER); //Won't stop when you are knocked away, go figure... - status_change_end(bl, SC_TATAMIGAESHI, INVALID_TIMER); + status_change_end(bl, SC_NJ_TATAMIGAESHI, INVALID_TIMER); status_change_end(bl, SC_MAGICROD, INVALID_TIMER); if (sc->data[SC_PROPERTYWALK] && sc->data[SC_PROPERTYWALK]->val3 >= skill->get_maxcount(sc->data[SC_PROPERTYWALK]->val1,sc->data[SC_PROPERTYWALK]->val2) ) @@ -1667,45 +1667,19 @@ int map_quit(struct map_session_data *sd) { //(changing map-servers invokes unit_free but bypasses iMap->quit) if( sd->sc.count ) { //Status that are not saved... - status_change_end(&sd->bl, SC_BOSSMAPINFO, INVALID_TIMER); - status_change_end(&sd->bl, SC_AUTOTRADE, INVALID_TIMER); - status_change_end(&sd->bl, SC_SPURT, INVALID_TIMER); - status_change_end(&sd->bl, SC_BERSERK, INVALID_TIMER); - status_change_end(&sd->bl, SC__BLOODYLUST, INVALID_TIMER); - status_change_end(&sd->bl, SC_TRICKDEAD, INVALID_TIMER); - status_change_end(&sd->bl, SC_LEADERSHIP, INVALID_TIMER); - status_change_end(&sd->bl, SC_GLORYWOUNDS, INVALID_TIMER); - status_change_end(&sd->bl, SC_SOULCOLD, INVALID_TIMER); - status_change_end(&sd->bl, SC_HAWKEYES, INVALID_TIMER); - if(sd->sc.data[SC_ENDURE] && sd->sc.data[SC_ENDURE]->val4) - status_change_end(&sd->bl, SC_ENDURE, INVALID_TIMER); //No need to save infinite endure. - status_change_end(&sd->bl, SC_WEIGHT50, INVALID_TIMER); - status_change_end(&sd->bl, SC_WEIGHT90, INVALID_TIMER); - status_change_end(&sd->bl, SC_SATURDAYNIGHTFEVER, INVALID_TIMER); - status_change_end(&sd->bl, SC_KYOUGAKU, INVALID_TIMER); - if (battle_config.debuff_on_logout&1) { - status_change_end(&sd->bl, SC_ORCISH, INVALID_TIMER); - status_change_end(&sd->bl, SC_STRIPWEAPON, INVALID_TIMER); - status_change_end(&sd->bl, SC_STRIPARMOR, INVALID_TIMER); - status_change_end(&sd->bl, SC_STRIPSHIELD, INVALID_TIMER); - status_change_end(&sd->bl, SC_STRIPHELM, INVALID_TIMER); - status_change_end(&sd->bl, SC_EXTREMITYFIST, INVALID_TIMER); - status_change_end(&sd->bl, SC_EXPLOSIONSPIRITS, INVALID_TIMER); - if(sd->sc.data[SC_REGENERATION] && sd->sc.data[SC_REGENERATION]->val4) - status_change_end(&sd->bl, SC_REGENERATION, INVALID_TIMER); - //TO-DO Probably there are way more NPC_type negative status that are removed - status_change_end(&sd->bl, SC_CHANGEUNDEAD, INVALID_TIMER); - // Both these statuses are removed on logout. [L0ne_W0lf] - status_change_end(&sd->bl, SC_SLOWCAST, INVALID_TIMER); - status_change_end(&sd->bl, SC_CRITICALWOUND, INVALID_TIMER); - } - if (battle_config.debuff_on_logout&2) { - status_change_end(&sd->bl, SC_MAXIMIZEPOWER, INVALID_TIMER); - status_change_end(&sd->bl, SC_MAXOVERTHRUST, INVALID_TIMER); - status_change_end(&sd->bl, SC_STEELBODY, INVALID_TIMER); - status_change_end(&sd->bl, SC_PRESERVE, INVALID_TIMER); - status_change_end(&sd->bl, SC_KAAHI, INVALID_TIMER); - status_change_end(&sd->bl, SC_SPIRIT, INVALID_TIMER); + for(i=0; i < SC_MAX; i++){ + if ( status_get_sc_type(i)&SC_NO_SAVE ){ + if ( !sd->sc.data[i] ) + continue; + switch( i ){ + case SC_ENDURE: + case SC_GDSKILL_REGENERATION: + if( !sd->sc.data[i]->val4 ) + break; + default: + status_change_end(&sd->bl, (sc_type)i, INVALID_TIMER); + } + } } } diff --git a/src/map/mercenary.c b/src/map/mercenary.c index 91d685a49..566f68409 100644 --- a/src/map/mercenary.c +++ b/src/map/mercenary.c @@ -361,7 +361,7 @@ int mercenary_dead(struct mercenary_data *md) int mercenary_killbonus(struct mercenary_data *md) { - const enum sc_type scs[] = { SC_MERC_FLEEUP, SC_MERC_ATKUP, SC_MERC_HPUP, SC_MERC_SPUP, SC_MERC_HITUP }; + const enum sc_type scs[] = { SC_MER_FLEE, SC_MER_ATK, SC_MER_HP, SC_MER_SP, SC_MER_HIT }; int index = rnd() % ARRAYLENGTH(scs); sc_start(&md->bl, scs[index], 100, rnd() % 5, 600000); diff --git a/src/map/mob.c b/src/map/mob.c index 04c4bba38..6bb40478f 100644 --- a/src/map/mob.c +++ b/src/map/mob.c @@ -1461,7 +1461,7 @@ static bool mob_ai_sub_hard(struct mob_data *md, unsigned int tick) if( !battle->check_range(&md->bl, tbl, md->status.rhw.range) && ( //Can't attack back and can't reach back. (!can_move && DIFF_TICK(tick, md->ud.canmove_tick) > 0 && (battle_config.mob_ai&0x2 || (md->sc.data[SC_SPIDERWEB] && md->sc.data[SC_SPIDERWEB]->val1) - || md->sc.data[SC_BITE] || md->sc.data[SC_VACUUM_EXTREME] || md->sc.data[SC_THORNSTRAP] + || md->sc.data[SC_WUGBITE] || md->sc.data[SC_VACUUM_EXTREME] || md->sc.data[SC_THORNS_TRAP] || md->sc.data[SC__MANHOLE])) // Not yet confirmed if boss will teleport once it can't reach target. || !mob_can_reach(md, tbl, md->min_chase, MSS_RUSH) ) @@ -1484,7 +1484,7 @@ static bool mob_ai_sub_hard(struct mob_data *md, unsigned int tick) || (!battle->check_range(&md->bl, abl, md->status.rhw.range) // Not on Melee Range and ... && ( // Reach check (!can_move && DIFF_TICK(tick, md->ud.canmove_tick) > 0 && (battle_config.mob_ai&0x2 || (md->sc.data[SC_SPIDERWEB] && md->sc.data[SC_SPIDERWEB]->val1) - || md->sc.data[SC_BITE] || md->sc.data[SC_VACUUM_EXTREME] || md->sc.data[SC_THORNSTRAP] + || md->sc.data[SC_WUGBITE] || md->sc.data[SC_VACUUM_EXTREME] || md->sc.data[SC_THORNS_TRAP] || md->sc.data[SC__MANHOLE])) // Not yet confirmed if boss will teleport once it can't reach target. || !mob_can_reach(md, abl, dist+md->db->range3, MSS_RUSH) ) @@ -2360,9 +2360,9 @@ int mob_dead(struct mob_data *md, struct block_list *src, int type) (int)(md->level - sd->status.base_level) >= 20) drop_rate = (int)(drop_rate*1.25); // pk_mode increase drops if 20 level difference [Valaris] - // Increase drop rate if user has SC_ITEMBOOST - if (sd && sd->sc.data[SC_ITEMBOOST]) // now rig the drop rate to never be over 90% unless it is originally >90%. - drop_rate = max(drop_rate,cap_value((int)(0.5+drop_rate*(sd->sc.data[SC_ITEMBOOST]->val1)/100.),0,9000)); + // Increase drop rate if user has SC_CASH_RECEIVEITEM + if (sd && sd->sc.data[SC_CASH_RECEIVEITEM]) // now rig the drop rate to never be over 90% unless it is originally >90%. + drop_rate = max(drop_rate,cap_value((int)(0.5+drop_rate*(sd->sc.data[SC_CASH_RECEIVEITEM]->val1)/100.),0,9000)); #ifdef RENEWAL_DROP if( drop_modifier != 100 ) { drop_rate = drop_rate * drop_modifier / 100; diff --git a/src/map/packets.h b/src/map/packets.h index 4f2b119fb..bcce36040 100644 --- a/src/map/packets.h +++ b/src/map/packets.h @@ -2091,6 +2091,7 @@ packet(0x020d,-1); // New Packets packet(0x0998,8,clif->pEquipItem,2,4); packet(0x0447,2); // PACKET_CZ_BLOCKING_PLAY_CANCEL + packet(0x099f,24); // New Packets End #endif diff --git a/src/map/party.c b/src/map/party.c index e30d16c07..adcb35c5a 100644 --- a/src/map/party.c +++ b/src/map/party.c @@ -840,7 +840,7 @@ int party_skill_check(struct map_session_data *sd, int party_id, uint16 skill_id break; case MO_COMBOFINISH: //Increase Counter rate of Star Gladiators if((p_sd->class_&MAPID_UPPERMASK) == MAPID_STAR_GLADIATOR - && sd->sc.data[SC_READYCOUNTER] + && sd->sc.data[SC_COUNTERKICK_READY] && pc->checkskill(p_sd,SG_FRIEND)) { sc_start4(&p_sd->bl,SC_SKILLRATE_UP,100,TK_COUNTER, 50+50*pc->checkskill(p_sd,SG_FRIEND), //+100/150/200% rate diff --git a/src/map/pc.c b/src/map/pc.c index 170de63ff..155812836 100644 --- a/src/map/pc.c +++ b/src/map/pc.c @@ -868,20 +868,20 @@ int pc_isequip(struct map_session_data *sd,int n) if (sd->sc.count) { - if(item->equip & EQP_ARMS && item->type == IT_WEAPON && sd->sc.data[SC_STRIPWEAPON]) // Also works with left-hand weapons [DracoRPG] + if(item->equip & EQP_ARMS && item->type == IT_WEAPON && sd->sc.data[SC_NOEQUIPWEAPON]) // Also works with left-hand weapons [DracoRPG] return 0; - if(item->equip & EQP_SHIELD && item->type == IT_ARMOR && sd->sc.data[SC_STRIPSHIELD]) + if(item->equip & EQP_SHIELD && item->type == IT_ARMOR && sd->sc.data[SC_NOEQUIPSHIELD]) return 0; - if(item->equip & EQP_ARMOR && sd->sc.data[SC_STRIPARMOR]) + if(item->equip & EQP_ARMOR && sd->sc.data[SC_NOEQUIPARMOR]) return 0; - if(item->equip & EQP_HEAD_TOP && sd->sc.data[SC_STRIPHELM]) + if(item->equip & EQP_HEAD_TOP && sd->sc.data[SC_NOEQUIPHELM]) return 0; - if(item->equip & EQP_ACC && sd->sc.data[SC__STRIPACCESSORY]) + if(item->equip & EQP_ACC && sd->sc.data[SC__STRIPACCESSARY]) return 0; if(item->equip && sd->sc.data[SC_KYOUGAKU]) return 0; - if (sd->sc.data[SC_SPIRIT] && sd->sc.data[SC_SPIRIT]->val2 == SL_SUPERNOVICE) { + if (sd->sc.data[SC_SOULLINK] && sd->sc.data[SC_SOULLINK]->val2 == SL_SUPERNOVICE) { //Spirit of Super Novice equip bonuses. [Skotlex] if (sd->status.base_level > 90 && item->equip & EQP_HELM) return 1; //Can equip all helms @@ -1338,7 +1338,7 @@ int pc_calc_skilltree(struct map_session_data *sd) sd->status.skill[i].flag = SKILL_FLAG_PERMANENT; } - if( sd->sc.count && sd->sc.data[SC_SPIRIT] && sd->sc.data[SC_SPIRIT]->val2 == SL_BARDDANCER && skill_db[i].nameid >= DC_HUMMING && skill_db[i].nameid <= DC_SERVICEFORYOU ) + if( sd->sc.count && sd->sc.data[SC_SOULLINK] && sd->sc.data[SC_SOULLINK]->val2 == SL_BARDDANCER && skill_db[i].nameid >= DC_HUMMING && skill_db[i].nameid <= DC_SERVICEFORYOU ) { //Enable Bard/Dancer spirit linked skills. if( sd->status.sex ) { //Link dancer skills to bard. @@ -1427,7 +1427,7 @@ int pc_calc_skilltree(struct map_session_data *sd) if(!sd->status.skill[idx].lv && ( (inf2&INF2_QUEST_SKILL && !battle_config.quest_skill_learn) || inf2&INF2_WEDDING_SKILL || - (inf2&INF2_SPIRIT_SKILL && !sd->sc.data[SC_SPIRIT]) + (inf2&INF2_SPIRIT_SKILL && !sd->sc.data[SC_SOULLINK]) )) continue; //Cannot be learned via normal means. Note this check DOES allows raising already known skills. @@ -1459,7 +1459,7 @@ int pc_calc_skilltree(struct map_session_data *sd) if( sd->status.skill[idx].id == 0 ) { sd->status.skill[idx].id = id; sd->status.skill[idx].flag = SKILL_FLAG_TEMPORARY; // So it is not saved, and tagged as a "bonus" skill. - } else if( id != NV_BASIC) { + } else if( id != NV_BASIC ) { sd->status.skill[idx].flag = SKILL_FLAG_REPLACED_LV_0 + sd->status.skill[idx].lv; // Remember original level } @@ -1518,7 +1518,7 @@ static void pc_check_skilltree(struct map_session_data *sd, int skill_id) if( !sd->status.skill[idx].lv && ( (j&INF2_QUEST_SKILL && !battle_config.quest_skill_learn) || j&INF2_WEDDING_SKILL || - (j&INF2_SPIRIT_SKILL && !sd->sc.data[SC_SPIRIT]) + (j&INF2_SPIRIT_SKILL && !sd->sc.data[SC_SOULLINK]) ) ) continue; //Cannot be learned via normal means. @@ -1620,7 +1620,7 @@ int pc_calc_skilltree_normalize_job(struct map_session_data *sd) *------------------------------------------ * 1: overweight 50% * 2: overweight 90% - * It's assumed that SC_WEIGHT50 and SC_WEIGHT90 are only started/stopped here. + * It's assumed that SC_WEIGHTOVER50 and SC_WEIGHTOVER90 are only started/stopped here. */ int pc_updateweightstatus(struct map_session_data *sd) { @@ -1629,7 +1629,7 @@ int pc_updateweightstatus(struct map_session_data *sd) nullpo_retr(1, sd); - old_overweight = (sd->sc.data[SC_WEIGHT90]) ? 2 : (sd->sc.data[SC_WEIGHT50]) ? 1 : 0; + old_overweight = (sd->sc.data[SC_WEIGHTOVER90]) ? 2 : (sd->sc.data[SC_WEIGHTOVER50]) ? 1 : 0; new_overweight = (pc_is90overweight(sd)) ? 2 : (pc_is50overweight(sd)) ? 1 : 0; if( old_overweight == new_overweight ) @@ -1637,15 +1637,15 @@ int pc_updateweightstatus(struct map_session_data *sd) // stop old status change if( old_overweight == 1 ) - status_change_end(&sd->bl, SC_WEIGHT50, INVALID_TIMER); + status_change_end(&sd->bl, SC_WEIGHTOVER50, INVALID_TIMER); else if( old_overweight == 2 ) - status_change_end(&sd->bl, SC_WEIGHT90, INVALID_TIMER); + status_change_end(&sd->bl, SC_WEIGHTOVER90, INVALID_TIMER); // start new status change if( new_overweight == 1 ) - sc_start(&sd->bl, SC_WEIGHT50, 100, 0, 0); + sc_start(&sd->bl, SC_WEIGHTOVER50, 100, 0, 0); else if( new_overweight == 2 ) - sc_start(&sd->bl, SC_WEIGHT90, 100, 0, 0); + sc_start(&sd->bl, SC_WEIGHTOVER90, 100, 0, 0); // update overweight status sd->regen.state.overweight = new_overweight; @@ -2070,12 +2070,13 @@ int pc_bonus(struct map_session_data *sd,int type,int val) break; case SP_BASE_ATK: if(sd->state.lr_flag != 2) { - //#ifdef RENEWAL - // sd->bonus.eatk += val; - //#else +#ifdef RENEWAL + sd->bonus.eatk += val; + clif->updatestatus(sd,SP_ATK2); +#else bonus = status->batk + val; status->batk = cap_value(bonus, 0, USHRT_MAX); - //#endif +#endif } break; case SP_DEF1: @@ -2431,7 +2432,7 @@ int pc_bonus(struct map_session_data *sd,int type,int val) case SP_INTRAVISION: // Maya Purple Card effect allowing to see Hiding/Cloaking people [DracoRPG] if(sd->state.lr_flag != 2) { sd->special_state.intravision = 1; - clif->status_change(&sd->bl, SI_INTRAVISION, 1, 0, 0, 0, 0); + clif->status_change(&sd->bl, SI_CLAIRVOYANCE, 1, 0, 0, 0, 0); } break; case SP_NO_KNOCKBACK: @@ -4122,7 +4123,7 @@ int pc_isUseitem(struct map_session_data *sd,int n) case 12212: // Giant Fly Wing if( map[sd->bl.m].flag.noteleport || map_flag_gvg(sd->bl.m) ) { - clif->skill_teleportmessage(sd,0); + clif->skill_mapinfomessage(sd,0); return 0; } case 602: // ButterFly Wing @@ -4150,7 +4151,7 @@ int pc_isUseitem(struct map_session_data *sd,int n) break; case 12210: // Bubble Gum case 12264: // Comp Bubble Gum - if( sd->sc.data[SC_ITEMBOOST] ) + if( sd->sc.data[SC_CASH_RECEIVEITEM] ) return 0; break; case 12208: // Battle Manual @@ -4160,11 +4161,11 @@ int pc_isUseitem(struct map_session_data *sd,int n) case 14532: // Battle_Manual25 case 14533: // Battle_Manual100 case 14545: // Battle_Manual300 - if( sd->sc.data[SC_EXPBOOST] ) + if( sd->sc.data[SC_CASH_PLUSEXP] ) return 0; break; case 14592: // JOB_Battle_Manual - if( sd->sc.data[SC_JEXPBOOST] ) + if( sd->sc.data[SC_CASH_PLUSONLYJOBEXP] ) return 0; break; @@ -4177,7 +4178,7 @@ int pc_isUseitem(struct map_session_data *sd,int n) case 12243: // Mercenary's Berserk Potion if( sd->md == NULL || sd->md->db == NULL ) return 0; - if (sd->md->sc.data[SC_BERSERK] || sd->md->sc.data[SC_SATURDAYNIGHTFEVER] || sd->md->sc.data[SC__BLOODYLUST]) + if (sd->md->sc.data[SC_BERSERK] || sd->md->sc.data[SC_SATURDAY_NIGHT_FEVER] || sd->md->sc.data[SC__BLOODYLUST]) return 0; if( nameid == 12242 && sd->md->db->lv < 40 ) return 0; @@ -4281,7 +4282,8 @@ int pc_useitem(struct map_session_data *sd,int n) sd->sc.data[SC_HIDING] || sd->sc.data[SC__SHADOWFORM] || sd->sc.data[SC__MANHOLE] || - sd->sc.data[SC_KAGEHUMI] || + sd->sc.data[SC_KG_KAGEHUMI] || + sd->sc.data[SC_WHITEIMPRISON] || (sd->sc.data[SC_NOCHAT] && sd->sc.data[SC_NOCHAT]->val1&MANNER_NOITEM) )) return 0; @@ -4315,16 +4317,7 @@ int pc_useitem(struct map_session_data *sd,int n) if( sd->item_delay[i].nameid ) {// found if( DIFF_TICK(sd->item_delay[i].tick, tick) > 0 ) { int e_tick = DIFF_TICK(sd->item_delay[i].tick, tick)/1000; - char e_msg[100]; - if( e_tick > 99 ) - sprintf(e_msg,"Item Failed. [%s] is cooling down. wait %.1f minutes.", - itemdb_jname(sd->status.inventory[n].nameid), - (double)e_tick / 60); - else - sprintf(e_msg,"Item Failed. [%s] is cooling down. wait %d seconds.", - itemdb_jname(sd->status.inventory[n].nameid), - e_tick+1); - clif->colormes(sd->fd,COLOR_RED,e_msg); + clif->msgtable_num(sd->fd, 0x746, e_tick + 1); // [%d] seconds left until you can use return 0; // Delay has not expired yet } } else {// not yet used item (all slots are initially empty) @@ -4375,7 +4368,7 @@ int pc_useitem(struct map_session_data *sd,int n) pc->famerank(MakeDWord(sd->status.inventory[n].card[2],sd->status.inventory[n].card[3]), MAPID_ALCHEMIST)) { potion_flag = 2; // Famous player's potions have 50% more efficiency - if (sd->sc.data[SC_SPIRIT] && sd->sc.data[SC_SPIRIT]->val2 == SL_ROGUE) + if (sd->sc.data[SC_SOULLINK] && sd->sc.data[SC_SOULLINK]->val2 == SL_ROGUE) potion_flag = 3; //Even more effective potions. } @@ -4781,7 +4774,7 @@ int pc_setpos(struct map_session_data* sd, unsigned short mapindex, int x, int y if (sd->sc.count) { // Cancel some map related stuff. if (sd->sc.data[SC_JAILED]) return 1; //You may not get out! - status_change_end(&sd->bl, SC_BOSSMAPINFO, INVALID_TIMER); + status_change_end(&sd->bl, SC_CASH_BOSS_ALARM, INVALID_TIMER); status_change_end(&sd->bl, SC_WARM, INVALID_TIMER); status_change_end(&sd->bl, SC_SUN_COMFORT, INVALID_TIMER); status_change_end(&sd->bl, SC_MOON_COMFORT, INVALID_TIMER); @@ -4947,7 +4940,7 @@ int pc_memo(struct map_session_data* sd, int pos) // check mapflags if( sd->bl.m >= 0 && (map[sd->bl.m].flag.nomemo || map[sd->bl.m].flag.nowarpto) && !pc_has_permission(sd, PC_PERM_WARP_ANYWHERE) ) { - clif->skill_teleportmessage(sd, 1); // "Saved point cannot be memorized." + clif->skill_mapinfomessage(sd, 1); // "Saved point cannot be memorized." return 0; } @@ -5038,21 +5031,24 @@ int pc_checkallowskill(struct map_session_data *sd) { const enum sc_type scw_list[] = { SC_TWOHANDQUICKEN, - SC_ONEHAND, + SC_ONEHANDQUICKEN, SC_AURABLADE, SC_PARRYING, SC_SPEARQUICKEN, SC_ADRENALINE, SC_ADRENALINE2, SC_DANCING, - SC_GATLINGFEVER, + SC_GS_GATLINGFEVER, +#ifdef RENEWAL + SC_EDP, +#endif SC_FEARBREEZE }; const enum sc_type scs_list[] = { SC_AUTOGUARD, SC_DEFENDER, SC_REFLECTSHIELD, - SC_REFLECTDAMAGE + SC_LG_REFLECTDAMAGE }; int i; nullpo_ret(sd); @@ -5069,9 +5065,9 @@ int pc_checkallowskill(struct map_session_data *sd) status_change_end(&sd->bl, scw_list[i], INVALID_TIMER); } - if(sd->sc.data[SC_SPURT] && sd->status.weapon) + if(sd->sc.data[SC_STRUP] && sd->status.weapon) // Spurt requires bare hands (feet, in fact xD) - status_change_end(&sd->bl, SC_SPURT, INVALID_TIMER); + status_change_end(&sd->bl, SC_STRUP, INVALID_TIMER); if(sd->status.shield <= 0) { // Skills requiring a shield for (i = 0; i < ARRAYLENGTH(scs_list); i++) @@ -5755,7 +5751,7 @@ int pc_checkjoblevelup(struct map_session_data *sd) status_calc_pc(sd,0); clif->misceffect(&sd->bl,1); if (pc->checkskill(sd, SG_DEVIL) && !pc->nextjobexp(sd)) - clif->status_change(&sd->bl,SI_DEVIL, 1, 0, 0, 0, 1); //Permanent blind effect from SG_DEVIL. + clif->status_change(&sd->bl,SI_DEVIL1, 1, 0, 0, 0, 1); //Permanent blind effect from SG_DEVIL. npc_script_event(sd, NPCE_JOBLVUP); return 1; @@ -5777,13 +5773,13 @@ static void pc_calcexp(struct map_session_data *sd, unsigned int *base_exp, unsi (int)(status_get_lv(src) - sd->status.base_level) >= 20) bonus += 15; // pk_mode additional exp if monster >20 levels [Valaris] - if (sd->sc.data[SC_EXPBOOST]) - bonus += sd->sc.data[SC_EXPBOOST]->val1; + if (sd->sc.data[SC_CASH_PLUSEXP]) + bonus += sd->sc.data[SC_CASH_PLUSEXP]->val1; *base_exp = (unsigned int) cap_value(*base_exp + (double)*base_exp * bonus/100., 1, UINT_MAX); - if (sd->sc.data[SC_JEXPBOOST]) - bonus += sd->sc.data[SC_JEXPBOOST]->val1; + if (sd->sc.data[SC_CASH_PLUSONLYJOBEXP]) + bonus += sd->sc.data[SC_CASH_PLUSONLYJOBEXP]->val1; *job_exp = (unsigned int) cap_value(*job_exp + (double)*job_exp * bonus/100., 1, UINT_MAX); @@ -6134,6 +6130,19 @@ int pc_skillup(struct map_session_data *sd,uint16 skill_id) { clif->updatestatus(sd,SP_CARTINFO); if (!pc_has_permission(sd, PC_PERM_ALL_SKILL)) // may skill everything at any time anyways, and this would cause a huge slowdown clif->skillinfoblock(sd); + }else if( battle_config.skillup_limit ){ + int pts = 0, i, id; + for(i = 0; i < MAX_SKILL_TREE && (id=skill_tree[pc_class2idx(sd->status.class_)][i].id) > 0 ; i++){ + int inf2 = skill->get_inf2(id); + if ( inf2&INF2_QUEST_SKILL || (inf2&(INF2_WEDDING_SKILL|INF2_SPIRIT_SKILL)) || id == NV_BASIC ) + continue; + if( sd->status.skill[id].id && sd->status.skill[id].flag == SKILL_FLAG_PERMANENT ) + pts += pc_checkskill(sd, id); + } + if( pts < sd->change_level_2nd ) + clif->msg_value(sd, 0x61E, sd->change_level_2nd-pts); + else if( pts < (sd->change_level_3rd + sd->change_level_2nd) ) + clif->msg_value(sd, 0x61F, sd->change_level_3rd - (pts - sd->change_level_2nd)); } return 0; @@ -6370,7 +6379,7 @@ int pc_resetskill(struct map_session_data* sd, int flag) return 0; if( pc->checkskill(sd, SG_DEVIL) && !pc->nextjobexp(sd) ) //Remove perma blindness due to skill-reset. [Skotlex] - clif->sc_end(&sd->bl, sd->bl.id, SELF, SI_DEVIL); + clif->sc_end(&sd->bl, sd->bl.id, SELF, SI_DEVIL1); i = sd->sc.option; if( i&OPTION_RIDING && (!pc->checkskill(sd, KN_RIDING) || (sd->class_&MAPID_THIRDMASK) == MAPID_RUNE_KNIGHT) ) i &= ~OPTION_RIDING; @@ -6691,7 +6700,7 @@ int pc_dead(struct map_session_data *sd,struct block_list *src) { pc->delspiritball(sd,sd->spiritball,0); for(i = 1; i < 5; i++) - pc->del_talisman(sd, sd->talisman[i], i); + pc->del_charm(sd, sd->charm[i], i); if (src) { switch (src->type) { @@ -6801,7 +6810,7 @@ int pc_dead(struct map_session_data *sd,struct block_list *src) { if(battle_config.death_penalty_type && (sd->class_&MAPID_UPPERMASK) != MAPID_NOVICE // only novices will receive no penalty && !map[sd->bl.m].flag.noexppenalty && !map_flag_gvg(sd->bl.m) - && !sd->sc.data[SC_BABY] && !sd->sc.data[SC_LIFEINSURANCE]) + && !sd->sc.data[SC_BABY] && !sd->sc.data[SC_CASH_DEATHPENALTY]) { unsigned int base_penalty =0; if (battle_config.death_penalty_base > 0) { @@ -7304,8 +7313,8 @@ int pc_itemheal(struct map_session_data *sd,int itemid, int hp,int sp) hp = hp * bonus / 100; // Recovery Potion - if( sd->sc.data[SC_INCHEALRATE] ) - hp += (int)(hp * sd->sc.data[SC_INCHEALRATE]->val1/100.); + if( sd->sc.data[SC_HEALPLUS] ) + hp += (int)(hp * sd->sc.data[SC_HEALPLUS]->val1/100.); } if(sp) { bonus = 100 + (sd->battle_status.int_<<1) @@ -7529,7 +7538,7 @@ int pc_jobchange(struct map_session_data *sd,int job, int upper) //Remove peco/cart/falcon i = sd->sc.option; - if( i&OPTION_RIDING && !pc->checkskill(sd, KN_RIDING) ) + if( i&OPTION_RIDING && (!pc->checkskill(sd, KN_RIDING) || (sd->class_&MAPID_THIRDMASK) == MAPID_RUNE_KNIGHT) ) i&=~OPTION_RIDING; if( i&OPTION_FALCON && !pc->checkskill(sd, HT_FALCON) ) i&=~OPTION_FALCON; @@ -7715,22 +7724,23 @@ int pc_setoption(struct map_session_data *sd,int type) } } if( (sd->class_&MAPID_THIRDMASK) == MAPID_MECHANIC ) { - if( type&OPTION_MADOGEAR && !(p_type&OPTION_MADOGEAR) ) { + int i; + if( type&OPTION_MADOGEAR && !(p_type&OPTION_MADOGEAR) ) status_calc_pc(sd, 0); - status_change_end(&sd->bl,SC_MAXIMIZEPOWER,INVALID_TIMER); - status_change_end(&sd->bl,SC_OVERTHRUST,INVALID_TIMER); - status_change_end(&sd->bl,SC_WEAPONPERFECTION,INVALID_TIMER); - status_change_end(&sd->bl,SC_ADRENALINE,INVALID_TIMER); - status_change_end(&sd->bl,SC_CARTBOOST,INVALID_TIMER); - status_change_end(&sd->bl,SC_MELTDOWN,INVALID_TIMER); - status_change_end(&sd->bl,SC_MAXOVERTHRUST,INVALID_TIMER); - } else if( !(type&OPTION_MADOGEAR) && p_type&OPTION_MADOGEAR ) { + else if( !(type&OPTION_MADOGEAR) && p_type&OPTION_MADOGEAR ) status_calc_pc(sd, 0); - status_change_end(&sd->bl,SC_SHAPESHIFT,INVALID_TIMER); - status_change_end(&sd->bl,SC_HOVERING,INVALID_TIMER); - status_change_end(&sd->bl,SC_ACCELERATION,INVALID_TIMER); - status_change_end(&sd->bl,SC_OVERHEAT_LIMITPOINT,INVALID_TIMER); - status_change_end(&sd->bl,SC_OVERHEAT,INVALID_TIMER); + for( i = 0; i < SC_MAX; i++ ){ + if ( !sd->sc.data[i] || !status_get_sc_type(i) ) + continue; + if ( status_get_sc_type(i)&SC_MADO_NO_RESET ) + continue; + switch (i) { + case SC_BERSERK: + case SC_SATURDAY_NIGHT_FEVER: + sd->sc.data[i]->val2 = 0; + break; + } + status_change_end(&sd->bl, (sc_type)i, INVALID_TIMER); } } @@ -8503,7 +8513,7 @@ int pc_equipitem(struct map_session_data *sd,int n,int req_pos) return 0; } - if (sd->sc.data[SC_BERSERK] || sd->sc.data[SC_SATURDAYNIGHTFEVER] || sd->sc.data[SC__BLOODYLUST]) + if (sd->sc.data[SC_BERSERK] || sd->sc.data[SC_SATURDAY_NIGHT_FEVER] || sd->sc.data[SC__BLOODYLUST]) { clif->equipitemack(sd,n,0,0); // fail return 0; @@ -8699,7 +8709,7 @@ int pc_unequipitem(struct map_session_data *sd,int n,int flag) { } // if player is berserk then cannot unequip - if (!(flag & 2) && sd->sc.count && (sd->sc.data[SC_BERSERK] || sd->sc.data[SC_SATURDAYNIGHTFEVER] || sd->sc.data[SC__BLOODYLUST])) + if (!(flag & 2) && sd->sc.count && (sd->sc.data[SC_BERSERK] || sd->sc.data[SC_SATURDAY_NIGHT_FEVER] || sd->sc.data[SC__BLOODYLUST])) { clif->unequipitemack(sd,n,0,0); return 0; @@ -8780,7 +8790,7 @@ int pc_unequipitem(struct map_session_data *sd,int n,int flag) { clif->unequipitemack(sd,n,sd->status.inventory[n].equip,1); if((sd->status.inventory[n].equip & EQP_ARMS) && - sd->weapontype1 == 0 && sd->weapontype2 == 0 && (!sd->sc.data[SC_SEVENWIND] || sd->sc.data[SC_ASPERSIO])) //Check for seven wind (but not level seven!) + sd->weapontype1 == 0 && sd->weapontype2 == 0 && (!sd->sc.data[SC_TK_SEVENWIND] || sd->sc.data[SC_ASPERSIO])) //Check for seven wind (but not level seven!) skill->enchant_elemental_end(&sd->bl,-1); if(sd->status.inventory[n].equip & EQP_ARMOR) { @@ -8822,8 +8832,8 @@ int pc_unequipitem(struct map_session_data *sd,int n,int flag) { status_calc_pc(sd,0); } - if(sd->sc.data[SC_SIGNUMCRUCIS] && !battle->check_undead(sd->battle_status.race,sd->battle_status.def_ele)) - status_change_end(&sd->bl, SC_SIGNUMCRUCIS, INVALID_TIMER); + if(sd->sc.data[SC_CRUCIS] && !battle->check_undead(sd->battle_status.race,sd->battle_status.def_ele)) + status_change_end(&sd->bl, SC_CRUCIS, INVALID_TIMER); //OnUnEquip script [Skotlex] if (sd->inventory_data[n]) { @@ -9209,7 +9219,7 @@ int pc_autosave(int tid, unsigned int tick, int id, intptr_t data) static int pc_daynight_timer_sub(struct map_session_data *sd,va_list ap) { if (sd->state.night != iMap->night_flag && map[sd->bl.m].flag.nightenabled) { //Night/day state does not match. - clif->status_change(&sd->bl, SI_NIGHT, iMap->night_flag, 0, 0, 0, 0); //New night effect by dynamix [Skotlex] + clif->status_change(&sd->bl, SI_SKE, iMap->night_flag, 0, 0, 0, 0); //New night effect by dynamix [Skotlex] sd->state.night = iMap->night_flag; return 1; } @@ -9313,7 +9323,7 @@ bool pc_can_use_command(struct map_session_data *sd, const char *command) { return atcommand->can_use(sd,command); } -static int pc_talisman_timer(int tid, unsigned int tick, int id, intptr_t data) +static int pc_charm_timer(int tid, unsigned int tick, int id, intptr_t data) { struct map_session_data *sd; int i, type; @@ -9321,33 +9331,33 @@ static int pc_talisman_timer(int tid, unsigned int tick, int id, intptr_t data) if( (sd=(struct map_session_data *)iMap->id2sd(id)) == NULL || sd->bl.type!=BL_PC ) return 1; - ARR_FIND(1, 5, type, sd->talisman[type] > 0); + ARR_FIND(1, 5, type, sd->charm[type] > 0); - if( sd->talisman[type] <= 0 ) + if( sd->charm[type] <= 0 ) { - ShowError("pc_talisman_timer: %d talisman's available. (aid=%d cid=%d tid=%d)\n", sd->talisman[type], sd->status.account_id, sd->status.char_id, tid); - sd->talisman[type] = 0; + ShowError("pc_charm_timer: %d charm's available. (aid=%d cid=%d tid=%d)\n", sd->charm[type], sd->status.account_id, sd->status.char_id, tid); + sd->charm[type] = 0; return 0; } - ARR_FIND(0, sd->talisman[type], i, sd->talisman_timer[type][i] == tid); - if( i == sd->talisman[type] ) + ARR_FIND(0, sd->charm[type], i, sd->charm_timer[type][i] == tid); + if( i == sd->charm[type] ) { - ShowError("pc_talisman_timer: timer not found (aid=%d cid=%d tid=%d)\n", sd->status.account_id, sd->status.char_id, tid); + ShowError("pc_charm_timer: timer not found (aid=%d cid=%d tid=%d)\n", sd->status.account_id, sd->status.char_id, tid); return 0; } - sd->talisman[type]--; - if( i != sd->talisman[type] ) - memmove(sd->talisman_timer[type]+i, sd->talisman_timer[type]+i+1, (sd->talisman[type]-i)*sizeof(int)); - sd->talisman_timer[type][sd->talisman[type]] = INVALID_TIMER; + sd->charm[type]--; + if( i != sd->charm[type] ) + memmove(sd->charm_timer[type]+i, sd->charm_timer[type]+i+1, (sd->charm[type]-i)*sizeof(int)); + sd->charm_timer[type][sd->charm[type]] = INVALID_TIMER; - clif->talisman(sd, type); + clif->charm(sd, type); return 0; } -int pc_add_talisman(struct map_session_data *sd,int interval,int max,int type) +int pc_add_charm(struct map_session_data *sd,int interval,int max,int type) { int tid, i; @@ -9355,61 +9365,61 @@ int pc_add_talisman(struct map_session_data *sd,int interval,int max,int type) if(max > 10) max = 10; - if(sd->talisman[type] < 0) - sd->talisman[type] = 0; + if(sd->charm[type] < 0) + sd->charm[type] = 0; - if( sd->talisman[type] && sd->talisman[type] >= max ) + if( sd->charm[type] && sd->charm[type] >= max ) { - if(sd->talisman_timer[type][0] != INVALID_TIMER) - iTimer->delete_timer(sd->talisman_timer[type][0],pc_talisman_timer); - sd->talisman[type]--; - if( sd->talisman[type] != 0 ) - memmove(sd->talisman_timer[type]+0, sd->talisman_timer[type]+1, (sd->talisman[type])*sizeof(int)); - sd->talisman_timer[type][sd->talisman[type]] = INVALID_TIMER; - } - - tid = iTimer->add_timer(iTimer->gettick()+interval, pc_talisman_timer, sd->bl.id, 0); - ARR_FIND(0, sd->talisman[type], i, sd->talisman_timer[type][i] == INVALID_TIMER || DIFF_TICK(iTimer->get_timer(tid)->tick,iTimer->get_timer(sd->talisman_timer[type][i])->tick) < 0); - if( i != sd->talisman[type] ) - memmove(sd->talisman_timer[type]+i+1, sd->talisman_timer[type]+i, (sd->talisman[type]-i)*sizeof(int)); - sd->talisman_timer[type][i] = tid; - sd->talisman[type]++; - - clif->talisman(sd, type); + if(sd->charm_timer[type][0] != INVALID_TIMER) + iTimer->delete_timer(sd->charm_timer[type][0],pc_charm_timer); + sd->charm[type]--; + if( sd->charm[type] != 0 ) + memmove(sd->charm_timer[type]+0, sd->charm_timer[type]+1, (sd->charm[type])*sizeof(int)); + sd->charm_timer[type][sd->charm[type]] = INVALID_TIMER; + } + + tid = iTimer->add_timer(iTimer->gettick()+interval, pc_charm_timer, sd->bl.id, 0); + ARR_FIND(0, sd->charm[type], i, sd->charm_timer[type][i] == INVALID_TIMER || DIFF_TICK(iTimer->get_timer(tid)->tick, iTimer->get_timer(sd->charm_timer[type][i])->tick) < 0); + if( i != sd->charm[type] ) + memmove(sd->charm_timer[type]+i+1, sd->charm_timer[type]+i, (sd->charm[type]-i)*sizeof(int)); + sd->charm_timer[type][i] = tid; + sd->charm[type]++; + + clif->charm(sd, type); return 0; } -int pc_del_talisman(struct map_session_data *sd,int count,int type) +int pc_del_charm(struct map_session_data *sd,int count,int type) { int i; nullpo_ret(sd); - if( sd->talisman[type] <= 0 ) { - sd->talisman[type] = 0; + if( sd->charm[type] <= 0 ) { + sd->charm[type] = 0; return 0; } if( count <= 0 ) return 0; - if( count > sd->talisman[type] ) - count = sd->talisman[type]; - sd->talisman[type] -= count; + if( count > sd->charm[type] ) + count = sd->charm[type]; + sd->charm[type] -= count; if( count > 10 ) count = 10; for(i = 0; i < count; i++) { - if(sd->talisman_timer[type][i] != INVALID_TIMER) { - iTimer->delete_timer(sd->talisman_timer[type][i],pc_talisman_timer); - sd->talisman_timer[type][i] = INVALID_TIMER; + if(sd->charm_timer[type][i] != INVALID_TIMER) { + iTimer->delete_timer(sd->charm_timer[type][i],pc_charm_timer); + sd->charm_timer[type][i] = INVALID_TIMER; } } for(i = count; i < 10; i++) { - sd->talisman_timer[type][i-count] = sd->talisman_timer[type][i]; - sd->talisman_timer[type][i] = INVALID_TIMER; + sd->charm_timer[type][i-count] = sd->charm_timer[type][i]; + sd->charm_timer[type][i] = INVALID_TIMER; } - clif->talisman(sd, type); + clif->charm(sd, type); return 0; } #if defined(RENEWAL_DROP) || defined(RENEWAL_EXP) @@ -9854,7 +9864,7 @@ int do_init_pc(void) { iTimer->add_timer_func_list(pc_spiritball_timer, "pc_spiritball_timer"); iTimer->add_timer_func_list(pc_follow_timer, "pc_follow_timer"); iTimer->add_timer_func_list(pc->endautobonus, "pc->endautobonus"); - iTimer->add_timer_func_list(pc_talisman_timer, "pc_talisman_timer"); + iTimer->add_timer_func_list(pc_charm_timer, "pc_charm_timer"); iTimer->add_timer(iTimer->gettick() + iMap->autosave_interval, pc_autosave, 0, 0); @@ -10087,8 +10097,8 @@ void pc_defaults(void) { pc->load_combo = pc_load_combo; - pc->add_talisman = pc_add_talisman; - pc->del_talisman = pc_del_talisman; + pc->add_charm = pc_add_charm; + pc->del_charm = pc_del_charm; pc->baselevelchanged = pc_baselevelchanged; #if defined(RENEWAL_DROP) || defined(RENEWAL_EXP) diff --git a/src/map/pc.h b/src/map/pc.h index ebf474823..cd2a45a6b 100644 --- a/src/map/pc.h +++ b/src/map/pc.h @@ -160,6 +160,8 @@ struct map_session_data { unsigned int warping : 1;//states whether you're in the middle of a warp processing unsigned int permanent_speed : 1; // When 1, speed cannot be changed through status_calc_pc(). unsigned int dialog : 1; + unsigned int prerefining : 1; + unsigned int workinprogress : 3; // 1 = disable skill/item, 2 = disable npc interaction, 3 = disable both } state; struct { unsigned char no_weapon_damage, no_magic_damage, no_misc_damage; @@ -190,7 +192,7 @@ struct map_session_data { unsigned char head_dir; //0: Look forward. 1: Look right, 2: Look left. unsigned int client_tick; int npc_id,areanpc_id,npc_shopid,touching_id; //for script follow scriptoid; ,npcid - int npc_item_flag; //Marks the npc_id with which you can use items during interactions with said npc (see script command enable_itemuse) + int npc_item_flag; //Marks the npc_id with which you can change equipments during interactions with said npc (see script command enable_itemuse) int npc_menu; // internal variable, used in npc menu handling int npc_amount; struct script_state *st; @@ -324,7 +326,7 @@ struct map_session_data { int fixcastrate,varcastrate; int add_fixcast,add_varcast; int ematk; // matk bonus from equipment -// int eatk; // atk bonus from equipment + int eatk; // atk bonus from equipment } bonus; // zeroed vars end here. int castrate,delayrate,hprate,sprate,dsprate; @@ -336,8 +338,8 @@ struct map_session_data { short catch_target_class; // pet catching, stores a pet class to catch (short now) [zzo] short spiritball, spiritball_old; int spirit_timer[MAX_SPIRITBALL]; - short talisman[ELE_POISON+1]; // There are actually 5 talisman Fire, Ice, Wind, Earth & Poison maybe because its color violet. - int talisman_timer[ELE_POISON+1][10]; + short charm[ELE_POISON+1]; // There are actually 5 charm Fire, Ice, Wind, Earth & Poison maybe because its color violet. + int charm_timer[ELE_POISON+1][10]; unsigned char potion_success_counter; //Potion successes in row counter unsigned char mission_count; //Stores the bounty kill count for TK_MISSION short mission_mobid; //Stores the target mob_id for TK_MISSION @@ -650,13 +652,13 @@ enum equip_pos { // clientside display macros (values to the left/right of the "+") #ifdef RENEWAL #define pc_leftside_atk(sd) ((sd)->battle_status.batk) - #define pc_rightside_atk(sd) ((sd)->battle_status.rhw.atk + (sd)->battle_status.lhw.atk + (sd)->battle_status.rhw.atk2 + (sd)->battle_status.lhw.atk2) + #define pc_rightside_atk(sd) ((sd)->battle_status.rhw.atk + (sd)->battle_status.lhw.atk + (sd)->battle_status.rhw.atk2 + (sd)->battle_status.lhw.atk2 + (sd)->bonus.eatk ) #define pc_leftside_def(sd) ((sd)->battle_status.def2) #define pc_rightside_def(sd) ((sd)->battle_status.def) #define pc_leftside_mdef(sd) ((sd)->battle_status.mdef2) #define pc_rightside_mdef(sd) ((sd)->battle_status.mdef) #define pc_leftside_matk(sd) (status_base_matk(status_get_status_data(&(sd)->bl), (sd)->status.base_level)) -#define pc_rightside_matk(sd) ((sd)->battle_status.rhw.matk+(sd)->bonus.ematk) +#define pc_rightside_matk(sd) ((sd)->battle_status.rhw.matk+(sd)->battle_status.lhw.matk+(sd)->bonus.ematk) #else #define pc_leftside_atk(sd) ((sd)->battle_status.batk + (sd)->battle_status.rhw.atk + (sd)->battle_status.lhw.atk) #define pc_rightside_atk(sd) ((sd)->battle_status.rhw.atk2 + (sd)->battle_status.lhw.atk2) @@ -940,8 +942,8 @@ struct pc_interface { int (*load_combo) (struct map_session_data *sd); - int (*add_talisman) (struct map_session_data *sd,int interval,int max,int type); - int (*del_talisman) (struct map_session_data *sd,int count,int type); + int (*add_charm) (struct map_session_data *sd,int interval,int max,int type); + int (*del_charm) (struct map_session_data *sd,int count,int type); void (*baselevelchanged) (struct map_session_data *sd); #if defined(RENEWAL_DROP) || defined(RENEWAL_EXP) diff --git a/src/map/script.c b/src/map/script.c index e1015a718..a01372385 100644 --- a/src/map/script.c +++ b/src/map/script.c @@ -9581,8 +9581,8 @@ BUILDIN(sc_end) switch (type) { - case SC_WEIGHT50: - case SC_WEIGHT90: + case SC_WEIGHTOVER50: + case SC_WEIGHTOVER90: case SC_NOCHAT: case SC_PUSH_CART: return true; diff --git a/src/map/skill.c b/src/map/skill.c index 15c133dc1..dcc422da5 100644 --- a/src/map/skill.c +++ b/src/map/skill.c @@ -346,7 +346,6 @@ int skill_get_range2 (struct block_list *bl, uint16 skill_id, uint16 skill_lv) { **/ case WL_WHITEIMPRISON: case WL_SOULEXPANSION: - case WL_FROSTMISTY: case WL_MARSHOFABYSS: case WL_SIENNAEXECRATE: case WL_DRAINLIFE: @@ -355,6 +354,7 @@ int skill_get_range2 (struct block_list *bl, uint16 skill_id, uint16 skill_lv) { case WL_COMET: case WL_CHAINLIGHTNING: case WL_TETRAVORTEX: + case WL_EARTHSTRAIN: case WL_RELEASE: if( bl->type == BL_PC ) range += pc->checkskill((TBL_PC*)bl, WL_RADIUS); @@ -385,13 +385,13 @@ int skill_calc_heal(struct block_list *src, struct block_list *target, uint16 sk struct status_change* sc; switch( skill_id ) { - case BA_APPLEIDUN: + case BA_APPLEIDUN: #ifdef RENEWAL - hp = 100+5*skill_lv+5*(status_get_vit(src)/10); // HP recovery + hp = 100+5*skill_lv+5*(status_get_vit(src)/10); // HP recovery #else - hp = 30+5*skill_lv+5*(status_get_vit(src)/10); // HP recovery + hp = 30+5*skill_lv+5*(status_get_vit(src)/10); // HP recovery #endif - if( sd ) + if( sd ) hp += 5*pc->checkskill(sd,BA_MUSICALLESSON); break; case PR_SANCTUARY: @@ -406,7 +406,7 @@ int skill_calc_heal(struct block_list *src, struct block_list *target, uint16 sk #ifdef RENEWAL /** * Renewal Heal Formula - * Formula: ( [(Base Level + INT) / 5] � 30 ) � (Heal Level / 10) � (Modifiers) + MATK + * Formula: ( [(Base Level + INT) / 5] ? 30 ) ? (Heal Level / 10) ? (Modifiers) + MATK **/ hp = (status_get_lv(src) + status_get_int(src)) / 5 * 30 * skill_lv / 10; #else @@ -434,10 +434,12 @@ int skill_calc_heal(struct block_list *src, struct block_list *target, uint16 sk hp -= hp * sc->data[SC_CRITICALWOUND]->val2/100; if( sc->data[SC_DEATHHURT] && heal ) hp -= hp * 20/100; - if( sc->data[SC_INCHEALRATE] && skill_id != NPC_EVILLAND && skill_id != BA_APPLEIDUN ) - hp += hp * sc->data[SC_INCHEALRATE]->val1/100; // Only affects Heal, Sanctuary and PotionPitcher.(like bHealPower) [Inkfish] + if( sc->data[SC_HEALPLUS] && skill_id != NPC_EVILLAND && skill_id != BA_APPLEIDUN ) + hp += hp * sc->data[SC_HEALPLUS]->val1/100; // Only affects Heal, Sanctuary and PotionPitcher.(like bHealPower) [Inkfish] if( sc->data[SC_WATER_INSIGNIA] && sc->data[SC_WATER_INSIGNIA]->val1 == 2) hp += hp / 10; + if( sc->data[SC_OFFERTORIUM] && (skill_id == AB_HIGHNESSHEAL || skill_id == AB_CHEAL || skill_id == PR_SANCTUARY || skill_id == AL_HEAL) ) + hp += hp * sc->data[SC_OFFERTORIUM]->val2 / 100; } #ifdef RENEWAL @@ -447,32 +449,7 @@ int skill_calc_heal(struct block_list *src, struct block_list *target, uint16 sk case BA_APPLEIDUN: case PR_SANCTUARY: case NPC_EVILLAND: break; default: - { - struct status_data *status = status_get_status_data(src); - int min, max; - - min = max = status_base_matk(status, status_get_lv(src)); - if( status->rhw.matk > 0 ){ - int wMatk, variance; - wMatk = status->rhw.matk; - variance = wMatk * status->rhw.wlv / 10; - min += wMatk - variance; - max += wMatk + variance; - } - - if( sc && sc->data[SC_RECOGNIZEDSPELL] ) - min = max; - - if( sd && sd->right_weapon.overrefine > 0 ){ - min++; - max += sd->right_weapon.overrefine - 1; - } - - if(max > min) - hp += min+rnd()%(max-min); - else - hp += min; - } + hp += status_get_matk(src, 3); } #endif return hp; @@ -557,7 +534,7 @@ int skillnotok (uint16 skill_id, struct map_session_data *sd) case RETURN_TO_ELDICASTES: case ALL_GUARDIAN_RECALL: if(map[m].flag.nowarp) { - clif->skill_teleportmessage(sd,0); + clif->skill_mapinfomessage(sd,0); return 1; } return 0; @@ -565,7 +542,7 @@ int skillnotok (uint16 skill_id, struct map_session_data *sd) case SC_FATALMENACE: case SC_DIMENSIONDOOR: if(map[m].flag.noteleport) { - clif->skill_teleportmessage(sd,0); + clif->skill_mapinfomessage(sd,0); return 1; } return 0; // gonna be checked in 'skill->castend_nodamage_id' @@ -573,7 +550,7 @@ int skillnotok (uint16 skill_id, struct map_session_data *sd) case WE_CALLPARENT: case WE_CALLBABY: if (map[m].flag.nomemo) { - clif->skill_teleportmessage(sd,1); + clif->skill_mapinfomessage(sd,1); return 1; } break; @@ -625,7 +602,7 @@ int skillnotok (uint16 skill_id, struct map_session_data *sd) * These skills cannot be used while in mado gear (credits to Xantara) **/ if( pc_ismadogear(sd) ) { - clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); + clif->skill_fail(sd,skill_id,USESKILL_FAIL_MADOGEAR_RIDE,0); return 1; } break; @@ -636,7 +613,7 @@ int skillnotok (uint16 skill_id, struct map_session_data *sd) case WM_LULLABY_DEEPSLEEP: case WM_SATURDAY_NIGHT_FEVER: if( !map_flag_vs(m) ) { - clif->skill_teleportmessage(sd,2); // This skill uses this msg instead of skill fails. + clif->skill_mapinfomessage(sd,2); // This skill uses this msg instead of skill fails. return 1; } break; @@ -815,12 +792,12 @@ int skill_additional_effect (struct block_list* src, struct block_list *bl, uint if(sd) { // Automatic trigger of Blitz Beat if (pc_isfalcon(sd) && sd->status.weapon == W_BOW && (temp=pc->checkskill(sd,HT_BLITZBEAT))>0 && - rnd()%1000 <= sstatus->luk*10/3+1 ) { - rate=(sd->status.job_level+9)/10; + rnd()%1000 <= sstatus->luk*3 ) { + rate = sd->status.job_level / 10 + 1; skill->castend_damage_id(src,bl,HT_BLITZBEAT,(tempstatus.weapon == W_BOW || sd->status.weapon == W_FIST) && (temp=pc->checkskill(sd,RA_WUGSTRIKE)) > 0 && rnd()%1000 <= sstatus->luk*10/3+1 ) + if( pc_iswug(sd) && (temp=pc->checkskill(sd,RA_WUGSTRIKE)) > 0 && rnd()%1000 <= sstatus->luk*3 ) skill->castend_damage_id(src,bl,RA_WUGSTRIKE,temp,tick,0); // Gank if(dstmd && sd->status.weapon != W_BOW && @@ -832,26 +809,26 @@ int skill_additional_effect (struct block_list* src, struct block_list *bl, uint clif->skill_fail(sd,RG_SNATCHER,USESKILL_FAIL_LEVEL,0); } // Chance to trigger Taekwon kicks [Dralnu] - if(sc && !sc->data[SC_COMBO]) { - if(sc->data[SC_READYSTORM] && - sc_start(src,SC_COMBO, 15, TK_STORMKICK, + if(sc && !sc->data[SC_COMBOATTACK]) { + if(sc->data[SC_STORMKICK_READY] && + sc_start(src,SC_COMBOATTACK, 15, TK_STORMKICK, (2000 - 4*sstatus->agi - 2*sstatus->dex))) ; //Stance triggered - else if(sc->data[SC_READYDOWN] && - sc_start(src,SC_COMBO, 15, TK_DOWNKICK, + else if(sc->data[SC_DOWNKICK_READY] && + sc_start(src,SC_COMBOATTACK, 15, TK_DOWNKICK, (2000 - 4*sstatus->agi - 2*sstatus->dex))) ; //Stance triggered - else if(sc->data[SC_READYTURN] && - sc_start(src,SC_COMBO, 15, TK_TURNKICK, + else if(sc->data[SC_TURNKICK_READY] && + sc_start(src,SC_COMBOATTACK, 15, TK_TURNKICK, (2000 - 4*sstatus->agi - 2*sstatus->dex))) ; //Stance triggered - else if (sc->data[SC_READYCOUNTER]) { //additional chance from SG_FRIEND [Komurka] + else if (sc->data[SC_COUNTERKICK_READY]) { //additional chance from SG_FRIEND [Komurka] rate = 20; if (sc->data[SC_SKILLRATE_UP] && sc->data[SC_SKILLRATE_UP]->val1 == TK_COUNTER) { rate += rate*sc->data[SC_SKILLRATE_UP]->val2/100; status_change_end(src, SC_SKILLRATE_UP, INVALID_TIMER); } - sc_start2(src, SC_COMBO, rate, TK_COUNTER, bl->id, + sc_start2(src, SC_COMBOATTACK, rate, TK_COUNTER, bl->id, (2000 - 4*sstatus->agi - 2*sstatus->dex)); } } @@ -862,7 +839,7 @@ int skill_additional_effect (struct block_list* src, struct block_list *bl, uint if (sc) { struct status_change_entry *sce; // Enchant Poison gives a chance to poison attacked enemies - if((sce=sc->data[SC_ENCPOISON])) //Don't use sc_start since chance comes in 1/10000 rate. + if((sce=sc->data[SC_ENCHANTPOISON])) //Don't use sc_start since chance comes in 1/10000 rate. status_change_start(bl,SC_POISON,sce->val2, sce->val1,src->id,0,0, skill->get_time2(AS_ENCHANTPOISON,sce->val1),0); // Enchant Deadly Poison gives a chance to deadly poison attacked enemies @@ -871,7 +848,7 @@ int skill_additional_effect (struct block_list* src, struct block_list *bl, uint skill->get_time2(ASC_EDP,sce->val1)); } } - break; + break; case SM_BASH: if( sd && skill_lv > 5 && pc->checkskill(sd,SM_FATALBLOW)>0 ){ @@ -990,7 +967,7 @@ int skill_additional_effect (struct block_list* src, struct block_list *bl, uint break; case AM_ACIDTERROR: - sc_start2(bl,SC_BLEEDING,(skill_lv*3),skill_lv,src->id,skill->get_time2(skill_id,skill_lv)); + sc_start2(bl,SC_BLOODING,(skill_lv*3),skill_lv,src->id,skill->get_time2(skill_id,skill_lv)); if (skill->break_equip(bl, EQP_ARMOR, 100*skill->get_time(skill_id,skill_lv), BCT_ENEMY)) clif->emotion(bl,E_OMG); break; @@ -1062,14 +1039,12 @@ int skill_additional_effect (struct block_list* src, struct block_list *bl, uint sc_start(bl,status_skill2sc(skill_id),70,skill_lv,skill->get_time2(skill_id,skill_lv)); break; case NPC_BLEEDING: - sc_start2(bl,SC_BLEEDING,(20*skill_lv),skill_lv,src->id,skill->get_time2(skill_id,skill_lv)); + sc_start2(bl,SC_BLOODING,(20*skill_lv),skill_lv,src->id,skill->get_time2(skill_id,skill_lv)); break; case NPC_MENTALBREAKER: { //Based on observations by Tharis, Mental Breaker should do SP damage - //equal to Matk*skLevel. - rate = sstatus->matk_min; - if (rate < sstatus->matk_max) - rate += rnd()%(sstatus->matk_max - sstatus->matk_min); + //equal to Matk*skLevel. + rate = status_get_matk(src, 2); rate*=skill_lv; status_zap(bl, 0, rate); break; @@ -1108,7 +1083,7 @@ int skill_additional_effect (struct block_list* src, struct block_list *bl, uint case LK_HEADCRUSH: //Headcrush has chance of causing Bleeding status, except on demon and undead element if (!(battle->check_undead(tstatus->race, tstatus->def_ele) || tstatus->race == RC_DEMON)) - sc_start2(bl, SC_BLEEDING,50, skill_lv, src->id, skill->get_time2(skill_id,skill_lv)); + sc_start2(bl, SC_BLOODING,50, skill_lv, src->id, skill->get_time2(skill_id,skill_lv)); break; case LK_JOINTBEAT: @@ -1128,8 +1103,8 @@ int skill_additional_effect (struct block_list* src, struct block_list *bl, uint sc_start(bl,SC_STUN,(5+skill_lv*5),skill_lv,skill->get_time2(skill_id,2)); break; default: - sc_start2(bl,SC_BLEEDING,(5+skill_lv*5),skill_lv,src->id,skill->get_time2(skill_id,3)); - } + sc_start2(bl,SC_BLOODING,(5+skill_lv*5),skill_lv,src->id,skill->get_time2(skill_id,3)); + } break; case HW_NAPALMVULCAN: @@ -1151,12 +1126,12 @@ int skill_additional_effect (struct block_list* src, struct block_list *bl, uint case TK_JUMPKICK: if( dstsd && dstsd->class_ != MAPID_SOUL_LINKER && !tsc->data[SC_PRESERVE] ) {// debuff the following statuses - status_change_end(bl, SC_SPIRIT, INVALID_TIMER); + status_change_end(bl, SC_SOULLINK, INVALID_TIMER); status_change_end(bl, SC_ADRENALINE2, INVALID_TIMER); status_change_end(bl, SC_KAITE, INVALID_TIMER); status_change_end(bl, SC_KAAHI, INVALID_TIMER); - status_change_end(bl, SC_ONEHAND, INVALID_TIMER); - status_change_end(bl, SC_ASPDPOTION2, INVALID_TIMER); + status_change_end(bl, SC_ONEHANDQUICKEN, INVALID_TIMER); + status_change_end(bl, SC_ATTHASTE_POTION3, INVALID_TIMER); } break; case TK_TURNKICK: @@ -1169,7 +1144,7 @@ int skill_additional_effect (struct block_list* src, struct block_list *bl, uint status_change_start(bl,SC_COMA,10,skill_lv,0,src->id,0,0,0); break; case GS_PIERCINGSHOT: - sc_start2(bl,SC_BLEEDING,(skill_lv*3),skill_lv,src->id,skill->get_time2(skill_id,skill_lv)); + sc_start2(bl,SC_BLOODING,(skill_lv*3),skill_lv,src->id,skill->get_time2(skill_id,skill_lv)); break; case NJ_HYOUSYOURAKU: sc_start(bl,SC_FREEZE,(10+10*skill_lv),skill_lv,skill->get_time2(skill_id,skill_lv)); @@ -1204,34 +1179,37 @@ int skill_additional_effect (struct block_list* src, struct block_list *bl, uint sc_start(bl,SC_FEAR,3+2*skill_lv,skill_lv,skill->get_time(skill_id,skill_lv)); break; case RK_DRAGONBREATH: - sc_start4(bl,SC_BURNING,5+5*skill_lv,skill_lv,1000,src->id,0,skill->get_time(skill_id,skill_lv)); + sc_start4(bl,SC_BURNING,5+5*skill_lv,skill_lv,0,src->id,0,skill->get_time(skill_id,skill_lv)); + break; + case RK_DRAGONBREATH_WATER: + sc_start4(bl,SC_FROSTMISTY,5+5*skill_lv,skill_lv,0,src->id,0,skill->get_time(skill_id,skill_lv)); break; case AB_ADORAMUS: - if( tsc && !tsc->data[SC_DECREASEAGI] ) //Prevent duplicate agi-down effect. + if( tsc && !tsc->data[SC_DEC_AGI] ) //Prevent duplicate agi-down effect. sc_start(bl, SC_ADORAMUS, 100, skill_lv, skill->get_time(skill_id, skill_lv)); break; case WL_CRIMSONROCK: sc_start(bl, SC_STUN, 40, skill_lv, skill->get_time(skill_id, skill_lv)); break; case WL_COMET: - sc_start4(bl,SC_BURNING,100,skill_lv,1000,src->id,0,skill->get_time(skill_id,skill_lv)); + sc_start4(bl,SC_BURNING,100,skill_lv,0,src->id,0,skill->get_time2(skill_id,skill_lv)); break; case WL_EARTHSTRAIN: { - int rate = 0, i; - const int pos[5] = { EQP_WEAPON, EQP_HELM, EQP_SHIELD, EQP_ARMOR, EQP_ACC }; - rate = 6 * skill_lv + sstatus->dex / 10 + (sd? sd->status.job_level / 4 : 0) - tstatus->dex /5;// The tstatus->dex / 5 part is unofficial, but players gotta have some kind of way to have resistance. [Rytech] - //rate -= rate * tstatus->dex / 200; // Disabled until official resistance is found. - - for( i = 0; i < skill_lv; i++ ) - skill->strip_equip(bl,pos[i],rate,skill_lv,skill->get_time2(skill_id,skill_lv)); + // lv 1 & 2 = Strip Helm, lv 3 = Strip Armor, lv 4 = Strip Weapon and lv 5 = Strip Accessory. [malufett] + const int pos[5] = { EQP_HELM, EQP_HELM, EQP_ARMOR, EQP_WEAPON, EQP_ACC }; + skill->strip_equip(bl, pos[skill_lv], 6 * skill_lv + status_get_lv(src) / 4 + status_get_dex(src) / 10, + skill_lv, skill->get_time2(skill_id,skill_lv)); } break; case WL_JACKFROST: sc_start(bl,SC_FREEZE,100,skill_lv,skill->get_time(skill_id,skill_lv)); break; + case WL_FROSTMISTY: + sc_start(bl,SC_FROSTMISTY,25 + 5 * skill_lv,skill_lv,skill->get_time(skill_id,skill_lv)); + break; case RA_WUGBITE: - sc_start(bl, SC_BITE, (sd ? pc->checkskill(sd,RA_TOOTHOFWUG)*2 : 0), skill_lv, (skill->get_time(skill_id,skill_lv) + (sd ? pc->checkskill(sd,RA_TOOTHOFWUG)*500 : 0)) ); + sc_start(bl, SC_WUGBITE, (sd ? pc->checkskill(sd,RA_TOOTHOFWUG)*2 : 0), skill_lv, (skill->get_time(skill_id,skill_lv) + (sd ? pc->checkskill(sd,RA_TOOTHOFWUG)*500 : 0)) ); break; case RA_SENSITIVEKEEN: if( rnd()%100 < 8 * skill_lv ) @@ -1239,7 +1217,7 @@ int skill_additional_effect (struct block_list* src, struct block_list *bl, uint break; case RA_FIRINGTRAP: case RA_ICEBOUNDTRAP: - sc_start(bl, (skill_id == RA_FIRINGTRAP) ? SC_BURNING:SC_FREEZING, 40 + 10 * skill_lv, skill_lv, skill->get_time2(skill_id, skill_lv)); + sc_start4(bl, (skill_id == RA_FIRINGTRAP) ? SC_BURNING:SC_FROSTMISTY, 40 + 10 * skill_lv, skill_lv, 0, src->id, 0, skill->get_time2(skill_id, skill_lv)); break; case NC_PILEBUNKER: if( rnd()%100 < 5 + 15*skill_lv ) @@ -1252,20 +1230,27 @@ int skill_additional_effect (struct block_list* src, struct block_list *bl, uint } break; case NC_FLAMELAUNCHER: - sc_start4(bl, SC_BURNING, 50 + 10 * skill_lv, skill_lv, 1000, src->id, 0, skill->get_time2(skill_id, skill_lv)); + sc_start4(bl, SC_BURNING, 50 + 10 * skill_lv, skill_lv, 0, src->id, 0, skill->get_time2(skill_id, skill_lv)); break; case NC_COLDSLOWER: sc_start(bl, SC_FREEZE, 10 * skill_lv, skill_lv, skill->get_time(skill_id, skill_lv)); - sc_start(bl, SC_FREEZING, 20 + 10 * skill_lv, skill_lv, skill->get_time(skill_id, skill_lv)); + sc_start(bl, SC_FROSTMISTY, 20 + 10 * skill_lv, skill_lv, skill->get_time(skill_id, skill_lv)); break; case NC_POWERSWING: sc_start(bl, SC_STUN, 5*skill_lv, skill_lv, skill->get_time(skill_id, skill_lv)); if( rnd()%100 < 5*skill_lv ) skill->castend_damage_id(src, bl, NC_AXEBOOMERANG, pc->checkskill(sd, NC_AXEBOOMERANG), tick, 1); break; + case NC_MAGMA_ERUPTION: + sc_start4(bl, SC_BURNING, 10 * skill_lv, skill_lv, 0, src->id, 0, skill->get_time2(skill_id, skill_lv)); + sc_start(bl, SC_STUN, 10 * skill_lv, skill_lv, skill->get_time(skill_id, skill_lv)); + break; case GC_WEAPONCRUSH: skill->castend_nodamage_id(src,bl,skill_id,skill_lv,tick,BCT_ENEMY); break; + case GC_DARKCROW: + sc_start(bl, SC_DARKCROW, 10 * skill_lv, skill_lv, skill->get_time(skill_id, skill_lv)); + break; case LG_SHIELDPRESS: sc_start(bl, SC_STUN, 30 + 8 * skill_lv, skill_lv, skill->get_time(skill_id,skill_lv)); break; @@ -1273,7 +1258,7 @@ int skill_additional_effect (struct block_list* src, struct block_list *bl, uint rate = 30 + (((5 * (sd?pc->checkskill(sd,LG_PINPOINTATTACK):skill_lv)) + (sstatus->agi + status_get_lv(src))) / 10); switch( skill_lv ) { case 1: - sc_start2(bl,SC_BLEEDING,rate,skill_lv,src->id,skill->get_time(skill_id,skill_lv)); + sc_start2(bl,SC_BLOODING,rate,skill_lv,src->id,skill->get_time(skill_id,skill_lv)); break; case 2: if( dstsd && dstsd->spiritball && rnd()%100 < rate ) @@ -1335,25 +1320,25 @@ int skill_additional_effect (struct block_list* src, struct block_list *bl, uint status_change_end(bl, SC_APPLEIDUN, INVALID_TIMER); status_change_end(bl, SC_HUMMING, INVALID_TIMER); status_change_end(bl, SC_FORTUNE, INVALID_TIMER); - status_change_end(bl, SC_SERVICE4U, INVALID_TIMER); + status_change_end(bl, SC_SERVICEFORYOU, INVALID_TIMER); status_change_end(bl, SC_LONGING, INVALID_TIMER); - status_change_end(bl, SC_SWINGDANCE, INVALID_TIMER); - status_change_end(bl, SC_SYMPHONYOFLOVER, INVALID_TIMER); - status_change_end(bl, SC_MOONLITSERENADE, INVALID_TIMER); - status_change_end(bl, SC_RUSHWINDMILL, INVALID_TIMER); + status_change_end(bl, SC_SWING, INVALID_TIMER); + status_change_end(bl, SC_SYMPHONY_LOVE, INVALID_TIMER); + status_change_end(bl, SC_MOONLIT_SERENADE, INVALID_TIMER); + status_change_end(bl, SC_RUSH_WINDMILL, INVALID_TIMER); status_change_end(bl, SC_ECHOSONG, INVALID_TIMER); status_change_end(bl, SC_HARMONIZE, INVALID_TIMER); - status_change_end(bl, SC_WINKCHARM, INVALID_TIMER); - status_change_end(bl, SC_SONGOFMANA, INVALID_TIMER); - status_change_end(bl, SC_DANCEWITHWUG, INVALID_TIMER); - status_change_end(bl, SC_LERADSDEW, INVALID_TIMER); + status_change_end(bl, SC_DC_WINKCHARM, INVALID_TIMER); + status_change_end(bl, SC_SONG_OF_MANA, INVALID_TIMER); + status_change_end(bl, SC_DANCE_WITH_WUG, INVALID_TIMER); + status_change_end(bl, SC_LERADS_DEW, INVALID_TIMER); status_change_end(bl, SC_MELODYOFSINK, INVALID_TIMER); - status_change_end(bl, SC_BEYONDOFWARCRY, INVALID_TIMER); - status_change_end(bl, SC_UNLIMITEDHUMMINGVOICE, INVALID_TIMER); + status_change_end(bl, SC_BEYOND_OF_WARCRY, INVALID_TIMER); + status_change_end(bl, SC_UNLIMITED_HUMMING_VOICE, INVALID_TIMER); } break; case SO_EARTHGRAVE: - sc_start2(bl, SC_BLEEDING, 5 * skill_lv, skill_lv, src->id, skill->get_time2(skill_id, skill_lv)); // Need official rate. [LimitLine] + sc_start2(bl, SC_BLOODING, 5 * skill_lv, skill_lv, src->id, skill->get_time2(skill_id, skill_lv)); // Need official rate. [LimitLine] break; case SO_DIAMONDDUST: rate = 5 + 5 * skill_lv; @@ -1369,14 +1354,14 @@ int skill_additional_effect (struct block_list* src, struct block_list *bl, uint switch( sd->itemid ) { // Starting SCs here instead of do it in skill->additional_effect to simplify the code. case 13261: sc_start(bl, SC_STUN, 100, skill_lv, skill->get_time2(GN_SLINGITEM, skill_lv)); - sc_start2(bl, SC_BLEEDING, 100, skill_lv, src->id, skill->get_time2(GN_SLINGITEM, skill_lv)); + sc_start2(bl, SC_BLOODING, 100, skill_lv, src->id, skill->get_time2(GN_SLINGITEM, skill_lv)); break; case 13262: sc_start(bl, SC_MELON_BOMB, 100, skill_lv, skill->get_time(GN_SLINGITEM, skill_lv)); // Reduces ASPD and moviment speed break; case 13264: sc_start(bl, SC_BANANA_BOMB, 100, skill_lv, skill->get_time(GN_SLINGITEM, skill_lv)); // Reduces LUK ??Needed confirm it, may be it's bugged in kRORE? - sc_start(bl, SC_BANANA_BOMB_SITDOWN, 75, skill_lv, skill->get_time(GN_SLINGITEM_RANGEMELEEATK,skill_lv)); // Sitdown for 3 seconds. + sc_start(bl, SC_BANANA_BOMB_SITDOWN_POSTDELAY, 75, skill_lv, skill->get_time(GN_SLINGITEM_RANGEMELEEATK,skill_lv)); // Sitdown for 3 seconds. break; } sd->itemid = -1; @@ -1384,10 +1369,10 @@ int skill_additional_effect (struct block_list* src, struct block_list *bl, uint break; case GN_HELLS_PLANT_ATK: sc_start(bl, SC_STUN, 5 + 5 * skill_lv, skill_lv, skill->get_time2(skill_id, skill_lv)); - sc_start2(bl, SC_BLEEDING, 20 + 10 * skill_lv, skill_lv, src->id,skill->get_time2(skill_id, skill_lv)); + sc_start2(bl, SC_BLOODING, 20 + 10 * skill_lv, skill_lv, src->id,skill->get_time2(skill_id, skill_lv)); break; case EL_WIND_SLASH: // Non confirmed rate. - sc_start2(bl, SC_BLEEDING, 25, skill_lv, src->id, skill->get_time(skill_id,skill_lv)); + sc_start2(bl, SC_BLOODING, 25, skill_lv, src->id, skill->get_time(skill_id,skill_lv)); break; case EL_STONE_HAMMER: rate = 10 * skill_lv; @@ -1400,20 +1385,20 @@ int skill_additional_effect (struct block_list* src, struct block_list *bl, uint case EL_TYPOON_MIS: sc_start(bl,SC_SILENCE,10*skill_lv,skill_lv,skill->get_time(skill_id,skill_lv)); break; - case KO_JYUMONJIKIRI: // needs more info - sc_start(bl,SC_JYUMONJIKIRI,25,skill_lv,skill->get_time(skill_id,skill_lv)); + case KO_JYUMONJIKIRI: + sc_start(bl,SC_KO_JYUMONJIKIRI,90,skill_lv,skill->get_time(skill_id,skill_lv)); break; case KO_MAKIBISHI: - sc_start(bl, SC_STUN, 100, skill_lv, skill->get_time2(skill_id,skill_lv)); + sc_start(bl, SC_STUN, 10 * skill_lv, skill_lv, 1000 * (skill_lv / 2 + 2)); break; case MH_LAVA_SLIDE: - if (tsc && !tsc->data[SC_BURNING]) sc_start4(bl, SC_BURNING, 10 * skill_lv, skill_lv, 1000, src->id, 0, skill->get_time(skill_id, skill_lv)); + if (tsc && !tsc->data[SC_BURNING]) sc_start4(bl, SC_BURNING, 10 * skill_lv, skill_lv, 0, src->id, 0, skill->get_time(skill_id, skill_lv)); break; case MH_STAHL_HORN: sc_start(bl, SC_STUN, (20 + 4 * (skill_lv-1)), skill_lv, skill->get_time(skill_id, skill_lv)); break; case MH_NEEDLE_OF_PARALYZE: - sc_start(bl, SC_PARALYSIS, 40 + (5*skill_lv), skill_lv, skill->get_time(skill_id, skill_lv)); + sc_start(bl, SC_NEEDLE_OF_PARALYZE, 40 + (5*skill_lv), skill_lv, skill->get_time(skill_id, skill_lv)); break; } @@ -1442,7 +1427,7 @@ int skill_additional_effect (struct block_list* src, struct block_list *bl, uint rate += 10; if(sc->data[SC_OVERTHRUST]) rate += 10; - if(sc->data[SC_MAXOVERTHRUST]) + if(sc->data[SC_OVERTHRUSTMAX]) rate += 10; } if( rate ) @@ -1492,7 +1477,7 @@ int skill_additional_effect (struct block_list* src, struct block_list *bl, uint if (DIFF_TICK(ud->canact_tick, tick + rate) < 0){ ud->canact_tick = tick+rate; if ( battle_config.display_status_timers ) - clif->status_change(src, SI_ACTIONDELAY, 1, rate, 0, 0, 0); + clif->status_change(src, SI_POSTDELAY, 1, rate, 0, 0, 0); } } } @@ -1589,7 +1574,7 @@ int skill_additional_effect (struct block_list* src, struct block_list *bl, uint if (DIFF_TICK(ud->canact_tick, tick + rate) < 0){ ud->canact_tick = tick+rate; if ( battle_config.display_status_timers && sd ) - clif->status_change(src, SI_ACTIONDELAY, 1, rate, 0, 0, 0); + clif->status_change(src, SI_POSTDELAY, 1, rate, 0, 0, 0); } } } @@ -1828,10 +1813,10 @@ int skill_counter_additional_effect (struct block_list* src, struct block_list * if( skill_id == WZ_WATERBALL ) {//(bugreport:5303) struct status_change *sc = NULL; if( ( sc = status_get_sc(src) ) ) { - if(sc->data[SC_SPIRIT] && - sc->data[SC_SPIRIT]->val2 == SL_WIZARD && - sc->data[SC_SPIRIT]->val3 == WZ_WATERBALL) - sc->data[SC_SPIRIT]->val3 = 0; //Clear bounced spell check. + if(sc->data[SC_SOULLINK] && + sc->data[SC_SOULLINK]->val2 == SL_WIZARD && + sc->data[SC_SOULLINK]->val3 == WZ_WATERBALL) + sc->data[SC_SOULLINK]->val3 = 0; //Clear bounced spell check. } } } @@ -1925,7 +1910,7 @@ int skill_counter_additional_effect (struct block_list* src, struct block_list * if (DIFF_TICK(ud->canact_tick, tick + rate) < 0){ ud->canact_tick = tick+rate; if ( battle_config.display_status_timers && dstsd ) - clif->status_change(bl, SI_ACTIONDELAY, 1, rate, 0, 0, 0); + clif->status_change(bl, SI_POSTDELAY, 1, rate, 0, 0, 0); } } } @@ -1957,8 +1942,8 @@ int skill_counter_additional_effect (struct block_list* src, struct block_list * --------------------------------------------------------------------------*/ int skill_break_equip (struct block_list *bl, unsigned short where, int rate, int flag) { const int where_list[4] = {EQP_WEAPON, EQP_ARMOR, EQP_SHIELD, EQP_HELM}; - const enum sc_type scatk[4] = {SC_STRIPWEAPON, SC_STRIPARMOR, SC_STRIPSHIELD, SC_STRIPHELM}; - const enum sc_type scdef[4] = {SC_CP_WEAPON, SC_CP_ARMOR, SC_CP_SHIELD, SC_CP_HELM}; + const enum sc_type scatk[4] = {SC_NOEQUIPWEAPON, SC_NOEQUIPARMOR, SC_NOEQUIPSHIELD, SC_NOEQUIPHELM}; + const enum sc_type scdef[4] = {SC_PROTECTWEAPON, SC_PROTECTARMOR, SC_PROTECTSHIELD, SC_PROTECTHELM}; struct status_change *sc = status_get_sc(bl); int i,j; TBL_PC *sd; @@ -2048,8 +2033,8 @@ int skill_break_equip (struct block_list *bl, unsigned short where, int rate, in int skill_strip_equip(struct block_list *bl, unsigned short where, int rate, int lv, int time) { struct status_change *sc; const int pos[5] = {EQP_WEAPON, EQP_SHIELD, EQP_ARMOR, EQP_HELM, EQP_ACC}; - const enum sc_type sc_atk[5] = {SC_STRIPWEAPON, SC_STRIPSHIELD, SC_STRIPARMOR, SC_STRIPHELM, SC__STRIPACCESSORY}; - const enum sc_type sc_def[5] = {SC_CP_WEAPON, SC_CP_SHIELD, SC_CP_ARMOR, SC_CP_HELM, 0}; + const enum sc_type sc_atk[5] = {SC_NOEQUIPWEAPON, SC_NOEQUIPSHIELD, SC_NOEQUIPARMOR, SC_NOEQUIPHELM, SC__STRIPACCESSARY}; + const enum sc_type sc_def[5] = {SC_PROTECTWEAPON, SC_PROTECTSHIELD, SC_PROTECTARMOR, SC_PROTECTHELM, 0}; int i; if (rnd()%100 >= rate) @@ -2182,7 +2167,7 @@ int skill_attack (int attack_type, struct block_list* src, struct block_list *ds struct status_data *sstatus, *tstatus; struct status_change *sc; struct map_session_data *sd, *tsd; - int type,damage,rdamage=0; + int type,damage; int8 rmdamage=0;//magic reflected bool additional_effects = true; @@ -2253,15 +2238,15 @@ int skill_attack (int attack_type, struct block_list* src, struct block_list *ds flag |= 2; //Spirit of Wizard blocks Kaite's reflection - if( type == 2 && sc && sc->data[SC_SPIRIT] && sc->data[SC_SPIRIT]->val2 == SL_WIZARD ) + if( type == 2 && sc && sc->data[SC_SOULLINK] && sc->data[SC_SOULLINK]->val2 == SL_WIZARD ) { //Consume one Fragment per hit of the casted skill? [Skotlex] type = tsd?pc->search_inventory (tsd, 7321):0; if (type >= 0) { if ( tsd ) pc->delitem(tsd, type, 1, 0, 1, LOG_TYPE_CONSUME); dmg.damage = dmg.damage2 = 0; dmg.dmg_lv = ATK_MISS; - sc->data[SC_SPIRIT]->val3 = skill_id; - sc->data[SC_SPIRIT]->val4 = dsrc->id; + sc->data[SC_SOULLINK]->val3 = skill_id; + sc->data[SC_SOULLINK]->val4 = dsrc->id; } } else if( type != 2 ) /* Kaite bypasses */ additional_effects = false; @@ -2311,19 +2296,15 @@ int skill_attack (int attack_type, struct block_list* src, struct block_list *ds if( (skill_id == AL_INCAGI || skill_id == AL_BLESSING || skill_id == CASH_BLESSING || skill_id == CASH_INCAGI || - skill_id == MER_INCAGI || skill_id == MER_BLESSING) && tsd->sc.data[SC_CHANGEUNDEAD] ) + skill_id == MER_INCAGI || skill_id == MER_BLESSING) && tsd->sc.data[SC_PROPERTYUNDEAD] ) damage = 1; - if( damage > 0 && (( dmg.flag&BF_WEAPON && src != bl && ( src == dsrc || ( dsrc->type == BL_SKILL && ( skill_id == SG_SUN_WARM || skill_id == SG_MOON_WARM || skill_id == SG_STAR_WARM ) ) )) - || (sc && sc->data[SC_REFLECTDAMAGE])) ) - rdamage = battle->calc_return_damage(bl,src, &damage, dmg.flag, skill_id); - if( damage && sc && sc->data[SC_GENSOU] && dmg.flag&BF_MAGIC ){ struct block_list *nbl; nbl = battle->get_enemy_area(bl,bl->x,bl->y,2,BL_CHAR,bl->id); if( nbl ){ // Only one target is chosen. - damage = damage / 2; // Deflect half of the damage to a target nearby - clif->skill_damage(bl, nbl, tick, status_get_amotion(src), 0, status_fix_damage(bl,nbl,damage,0), dmg.div_, OB_OBOROGENSOU_TRANSITION_ATK, -1, 6); + int temp = (int)(damage / (float)(10 / skill_lv)); + clif->skill_damage(bl, nbl, tick, status_get_amotion(src), 0, status_fix_damage(bl,nbl,temp,0), 1, OB_OBOROGENSOU_TRANSITION_ATK, -1, 6); } } @@ -2348,7 +2329,7 @@ int skill_attack (int attack_type, struct block_list* src, struct block_list *ds if(sd) { int flag = 0; //Used to signal if this skill can be combo'ed later on. struct status_change_entry *sce; - if ((sce = sd->sc.data[SC_COMBO])) {//End combo state after skill is invoked. [Skotlex] + if ((sce = sd->sc.data[SC_COMBOATTACK])) {//End combo state after skill is invoked. [Skotlex] switch (skill_id) { case TK_TURNKICK: case TK_STORMKICK: @@ -2359,14 +2340,14 @@ int skill_attack (int attack_type, struct block_list* src, struct block_list *ds sce->val3 = skill_id; if( sce->timer != INVALID_TIMER ) iTimer->delete_timer(sce->timer, status_change_timer); - sce->timer = iTimer->add_timer(tick+sce->val4, status_change_timer, src->id, SC_COMBO); + sce->timer = iTimer->add_timer(tick+sce->val4, status_change_timer, src->id, SC_COMBOATTACK); break; } unit_cancel_combo(src); // Cancel combo wait break; default: if( src == dsrc ) // Ground skills are exceptions. [Inkfish] - status_change_end(src, SC_COMBO, INVALID_TIMER); + status_change_end(src, SC_COMBOATTACK, INVALID_TIMER); } } switch(skill_id) { @@ -2394,7 +2375,7 @@ int skill_attack (int attack_type, struct block_list* src, struct block_list *ds if( (tstatus->race == RC_BRUTE || tstatus->race == RC_INSECT) && pc->checkskill(sd, HT_POWER)) { //TODO: This code was taken from Triple Blows, is this even how it should be? [Skotlex] - sc_start2(src,SC_COMBO,100,HT_POWER,bl->id,2000); + sc_start2(src,SC_COMBOATTACK,100,HT_POWER,bl->id,2000); clif->combo_delay(src,2000); } break; @@ -2407,8 +2388,8 @@ int skill_attack (int attack_type, struct block_list* src, struct block_list *ds break; case SL_STIN: case SL_STUN: - if (skill_lv >= 7 && !sd->sc.data[SC_SMA]) - sc_start(src,SC_SMA,100,skill_lv,skill->get_time(SL_SMA, skill_lv)); + if (skill_lv >= 7 && !sd->sc.data[SC_SMA_READY]) + sc_start(src,SC_SMA_READY,100,skill_lv,skill->get_time(SL_SMA, skill_lv)); break; case GS_FULLBUSTER: //Can't attack nor use items until skill's delay expires. [Skotlex] @@ -2425,7 +2406,7 @@ int skill_attack (int attack_type, struct block_list* src, struct block_list *ds } //Switch End if (flag) { //Possible to chain if ( (flag = DIFF_TICK(sd->ud.canact_tick, tick)) < 50 ) flag = 50;/* less is a waste. */ - sc_start2(src,SC_COMBO,100,skill_id,bl->id,flag); + sc_start2(src,SC_COMBOATTACK,100,skill_id,bl->id,flag); clif->combo_delay(src, flag); } } @@ -2459,9 +2440,11 @@ int skill_attack (int attack_type, struct block_list* src, struct block_list *ds case SR_EARTHSHAKER: dmg.dmotion = clif->skill_damage(src,bl,tick,dmg.amotion,dmg.dmotion,damage,1,skill_id,-2,6); break; + case KO_MUCHANAGE: + if( dmg.dmg_lv == ATK_FLEE ) + break; case WL_SOULEXPANSION: case WL_COMET: - case KO_MUCHANAGE: case NJ_HUUMA: dmg.dmotion = clif->skill_damage(src,bl,tick,dmg.amotion,dmg.dmotion,damage,dmg.div_,skill_id,skill_lv,8); break; @@ -2488,6 +2471,7 @@ int skill_attack (int attack_type, struct block_list* src, struct block_list *ds case EL_HURRICANE_ATK: case KO_BAKURETSU: case GN_CRAZYWEED_ATK: + case NC_MAGMA_ERUPTION: dmg.dmotion = clif->skill_damage(src,bl,tick,dmg.amotion,dmg.dmotion,damage,dmg.div_,skill_id,-1,5); break; case GN_SLINGITEM_RANGEMELEEATK: @@ -2503,6 +2487,12 @@ int skill_attack (int attack_type, struct block_list* src, struct block_list *ds case WM_REVERBERATION_MAGIC: dmg.dmotion = clif->skill_damage(src,bl,tick,dmg.amotion,dmg.dmotion,damage,dmg.div_,WM_REVERBERATION,-2,6); break; + case WL_TETRAVORTEX_FIRE: + case WL_TETRAVORTEX_WATER: + case WL_TETRAVORTEX_WIND: + case WL_TETRAVORTEX_GROUND: + dmg.dmotion = clif->skill_damage(src,bl,tick,dmg.amotion,dmg.dmotion,damage,dmg.div_, WL_TETRAVORTEX,-1,5); + break; case HT_CLAYMORETRAP: case HT_BLASTMINE: case HT_FLASHER: @@ -2518,7 +2508,7 @@ int skill_attack (int attack_type, struct block_list* src, struct block_list *ds break; case WZ_SIGHTBLASTER: dmg.dmotion = clif->skill_damage(src,bl,tick, dmg.amotion, dmg.dmotion, damage, dmg.div_, skill_id, flag&SD_LEVEL?-1:skill_lv, 5); - break; + break; case AB_DUPLELIGHT_MELEE: case AB_DUPLELIGHT_MAGIC: dmg.amotion = 300;/* makes the damage value not overlap with previous damage (when displayed by the client) */ @@ -2643,8 +2633,8 @@ int skill_attack (int attack_type, struct block_list* src, struct block_list *ds skill->counter_additional_effect(src,bl,skill_id,skill_lv,dmg.flag,tick); } // Hell Inferno burning status only starts if Fire part hits. - if( skill_id == WL_HELLINFERNO && dmg.damage > 0 ) - sc_start4(bl,SC_BURNING,55+5*skill_lv,skill_lv,1000,src->id,0,skill->get_time(skill_id,skill_lv)); + if( skill_id == WL_HELLINFERNO && dmg.damage > 0 && !(flag&ELE_DARK) ) + sc_start4(bl,SC_BURNING,55+5*skill_lv,skill_lv,0,src->id,0,skill->get_time(skill_id,skill_lv)); // Apply knock back chance in SC_TRIANGLESHOT skill. else if( skill_id == SC_TRIANGLESHOT && rnd()%100 > (1 + skill_lv) ) dmg.blewcount = 0; @@ -2753,7 +2743,7 @@ int skill_attack (int attack_type, struct block_list* src, struct block_list *ds dmg.flag |= BF_WEAPON; if( sd && src != bl && damage > 0 && ( dmg.flag&BF_WEAPON || - (dmg.flag&BF_MISC && (skill_id == RA_CLUSTERBOMB || skill_id == RA_FIRINGTRAP || skill_id == RA_ICEBOUNDTRAP || skill_id == RK_DRAGONBREATH)) ) ) + (dmg.flag&BF_MISC && (skill_id == RA_CLUSTERBOMB || skill_id == RA_FIRINGTRAP || skill_id == RA_ICEBOUNDTRAP || skill_id == RK_DRAGONBREATH || skill_id == RK_DRAGONBREATH_WATER)) ) ) { if (battle_config.left_cardfix_to_right) battle->drain(sd, bl, dmg.damage, dmg.damage, tstatus->race, tstatus->mode&MD_BOSS); @@ -2761,30 +2751,7 @@ int skill_attack (int attack_type, struct block_list* src, struct block_list *ds battle->drain(sd, bl, dmg.damage, dmg.damage2, tstatus->race, tstatus->mode&MD_BOSS); } - if( rdamage > 0 ) { - if( sc && sc->data[SC_REFLECTDAMAGE] ) { - if( src != bl ) {// Don't reflect your own damage (Grand Cross) - bool change = false; - if( sd && !sd->state.autocast ) - change = true; - if( change ) - sd->state.autocast = 1; - iMap->foreachinshootrange(battle->damage_area,bl,skill->get_splash(LG_REFLECTDAMAGE,1),BL_CHAR,tick,bl,dmg.amotion,sstatus->dmotion,rdamage,tstatus->race); - if( change ) - sd->state.autocast = 0; - } - } else { - if( dmg.amotion ) - battle->delay_damage(tick, dmg.amotion,bl,src,0,CR_REFLECTSHIELD,0,rdamage,ATK_DEF,0,additional_effects); - else - status_fix_damage(bl,src,rdamage,0); - clif->damage(src,src,tick, dmg.amotion,0,rdamage,1,4,0); // in aegis damage reflected is shown in single hit. - //Use Reflect Shield to signal this kind of skill trigger. [Skotlex] - if( tsd && src != bl ) - battle->drain(tsd, src, rdamage, rdamage, sstatus->race, is_boss(src)); - skill->additional_effect(bl, src, CR_REFLECTSHIELD, 1, BF_WEAPON|BF_SHORT|BF_NORMAL,ATK_DEF,tick); - } - } + if( damage > 0 ) { /** * Post-damage effects @@ -2818,8 +2785,8 @@ int skill_attack (int attack_type, struct block_list* src, struct block_list *ds skill_id == MG_COLDBOLT || skill_id == MG_FIREBOLT || skill_id == MG_LIGHTNINGBOLT ) && (sc = status_get_sc(src)) && - sc->data[SC_DOUBLECAST] && - rnd() % 100 < sc->data[SC_DOUBLECAST]->val2) + sc->data[SC_DOUBLECASTING] && + rnd() % 100 < sc->data[SC_DOUBLECASTING]->val2) { // skill->addtimerskill(src, tick + dmg.div_*dmg.amotion, bl->id, 0, 0, skill_id, skill_lv, BF_MAGIC, flag|2); skill->addtimerskill(src, tick + dmg.amotion, bl->id, 0, 0, skill_id, skill_lv, BF_MAGIC, flag|2); @@ -3101,7 +3068,7 @@ int skill_check_condition_mercenary(struct block_list *bl, int skill_id, int lv, index[i] = pc->search_inventory(sd, itemid[i]); if( index[i] < 0 || sd->status.inventory[index[i]].amount < amount[i] ) { - clif->skill_fail(sd, skill_id, USESKILL_FAIL_LEVEL, 0); + clif->skill_fail(sd, skill_id, USESKILL_FAIL_NEED_ITEM, amount[i]|(itemid[i] << 16)); return 0; } } @@ -3193,10 +3160,10 @@ int skill_timerskill(int tid, unsigned int tick, int id, intptr_t data) { } else { struct status_change *sc = status_get_sc(src); if(sc) { - if(sc->data[SC_SPIRIT] && - sc->data[SC_SPIRIT]->val2 == SL_WIZARD && - sc->data[SC_SPIRIT]->val3 == skl->skill_id) - sc->data[SC_SPIRIT]->val3 = 0; //Clear bounced spell check. + if(sc->data[SC_SOULLINK] && + sc->data[SC_SOULLINK]->val2 == SL_WIZARD && + sc->data[SC_SOULLINK]->val3 == skl->skill_id) + sc->data[SC_SOULLINK]->val3 = 0; //Clear bounced spell check. } } break; @@ -3205,48 +3172,33 @@ int skill_timerskill(int tid, unsigned int tick, int id, intptr_t data) { **/ case WL_CHAINLIGHTNING_ATK: { struct block_list *nbl = NULL; // Next Target of Chain - skill->attack(BF_MAGIC,src,src,target,skl->skill_id,skl->skill_lv,tick,skl->flag); // Hit a Lightning on the current Target + skill->attack(BF_MAGIC, src, src, target, skl->skill_id, skl->skill_lv, tick, (9-skl->type)); // Hit a Lightning on the current Target skill->toggle_magicpower(src, skl->skill_id); // only the first hit will be amplify - if( skl->type > 1 ) { // Remaining Chains Hit - nbl = battle->get_enemy_area(src,target->x,target->y,2,BL_CHAR|BL_SKILL,target->id); // Search for a new Target around current one... - if( nbl == NULL && skl->x > 1 ) { - nbl = target; - skl->x--; - } else - skl->x = 3; + + if( skl->type < (4 + skl->skill_lv - 1) && skl->x < 3 ) + { // Remaining Chains Hit + nbl = battle->get_enemy_area(src, target->x, target->y, (skl->type>2)?2:3, // After 2 bounces, it will bounce to other targets in 7x7 range. + BL_CHAR|BL_SKILL, target->id); // Search for a new Target around current one... + if( nbl == NULL) + skl->x++; + else + skl->x = 0; + + skill->addtimerskill(src, tick + 651, (nbl?nbl:target)->id, skl->x, 0, WL_CHAINLIGHTNING_ATK, skl->skill_lv, skl->type + 1, skl->flag); } - - if( nbl ) - skill->addtimerskill(src,tick+status_get_adelay(src),nbl->id,skl->x,0,WL_CHAINLIGHTNING_ATK,skl->skill_lv,skl->type-1,skl->flag); } break; case WL_TETRAVORTEX_FIRE: case WL_TETRAVORTEX_WATER: case WL_TETRAVORTEX_WIND: case WL_TETRAVORTEX_GROUND: - skill->attack(BF_MAGIC,src,src,target,skl->skill_id,skl->skill_lv,tick,skl->flag|SD_ANIMATION); + clif->skill_nodamage(src, target, skl->skill_id, skl->skill_lv, 1); + skill_attack(BF_MAGIC, src, src, target, skl->skill_id, skl->skill_lv, tick, skl->flag); skill->toggle_magicpower(src, skl->skill_id); // only the first hit will be amplify - if( skl->type >= 3 ) { // Final Hit - if( !status_isdead(target) ) { // Final Status Effect - int effects[4] = { SC_BURNING, SC_FREEZING, SC_BLEEDING, SC_STUN }, - applyeffects[4] = { 0, 0, 0, 0 }, - i, j = 0, k = 0; - for( i = 1; i <= 8; i = i + i ) { - if( skl->x&i ) - { - applyeffects[j] = effects[k]; - j++; - } - k++; - } - if( j ) { - i = applyeffects[rnd()%j]; - status_change_start(target, i, 10000, skl->skill_lv, - (i == SC_BURNING ? 1000 : (i == SC_BLEEDING ? src->id : 0)), - (i == SC_BURNING ? src->id : 0), - 0, skill->get_time(WL_TETRAVORTEX,skl->skill_lv), 0); - } - } + if( skl->type == 4 ){ + const enum sc_type scs[] = { SC_BURNING, SC_BLOODING, SC_FROSTMISTY, SC_STUN }; // status inflicts are depend on what summoned element is used. + int rate = skl->y, index = skl->x-1; + sc_start2(target, scs[index], rate, skl->skill_lv, src->id, skill->get_time(WL_TETRAVORTEX,index)); } break; case WM_REVERBERATION_MELEE: @@ -3282,6 +3234,19 @@ int skill_timerskill(int tid, unsigned int tick, int id, intptr_t data) { iMap->foreachinrange(skill->area_sub, target, skill->get_splash(skl->skill_id, skl->skill_lv), BL_CHAR, src, skl->skill_id, skl->skill_lv, 0, skl->flag|1|BCT_ENEMY, skill->castend_damage_id); break; + case SR_FLASHCOMBO_ATK_STEP1: + case SR_FLASHCOMBO_ATK_STEP2: + case SR_FLASHCOMBO_ATK_STEP3: + case SR_FLASHCOMBO_ATK_STEP4: + if( src->type == BL_PC ) { + struct map_session_data *sd = NULL; + const enum e_skill combos[] = {SR_DRAGONCOMBO, SR_FALLENEMPIRE, SR_TIGERCANNON, SR_SKYNETBLOW}; + if( (sd = ((TBL_PC*)src)) ){ + uint16 cid = combos[skl->skill_id-SR_FLASHCOMBO_ATK_STEP1]; + skill->castend_damage_id(src, target, cid, pc->checkskill(sd, cid), tick, 0); + } + } + break; case CH_PALMSTRIKE: { struct status_change* tsc = status_get_sc(target); @@ -3525,7 +3490,9 @@ int skill_castend_damage_id (struct block_list* src, struct block_list *bl, uint case GS_FULLBUSTER: case NJ_SYURIKEN: case NJ_KUNAI: +#ifndef RENEWAL case ASC_BREAKER: +#endif case HFLI_MOON: //[orn] case HFLI_SBR44: //[orn] case NPC_BLEEDING: @@ -3533,6 +3500,8 @@ int skill_castend_damage_id (struct block_list* src, struct block_list *bl, uint case NPC_HELLPOWER: case RK_SONICWAVE: case RK_HUNDREDSPEAR: + case RK_STORMBLAST: + case RK_CRUSHSTRIKE: case AB_DUPLELIGHT_MELEE: case RA_AIMEDBOLT: case NC_AXEBOOMERANG: @@ -3555,7 +3524,7 @@ int skill_castend_damage_id (struct block_list* src, struct block_list *bl, uint case GN_SLINGITEM_RANGEMELEEATK: case KO_JYUMONJIKIRI: case KO_SETSUDAN: - case KO_KAIHOU: + case GC_DARKCROW: skill->attack(BF_WEAPON,src,src,bl,skill_id,skill_lv,tick,flag); break; @@ -3588,7 +3557,7 @@ int skill_castend_damage_id (struct block_list* src, struct block_list *bl, uint break; case MO_COMBOFINISH: - if (!(flag&1) && sc && sc->data[SC_SPIRIT] && sc->data[SC_SPIRIT]->val2 == SL_MONK) + if (!(flag&1) && sc && sc->data[SC_SOULLINK] && sc->data[SC_SOULLINK]->val2 == SL_MONK) { //Becomes a splash attack when Soul Linked. iMap->foreachinrange(skill->area_sub, bl, skill->get_splash(skill_id, skill_lv),splash_target(src), @@ -3687,9 +3656,6 @@ int skill_castend_damage_id (struct block_list* src, struct block_list *bl, uint break; case NJ_ISSEN: - status_change_end(src, SC_NEN, INVALID_TIMER); - status_change_end(src, SC_HIDING, INVALID_TIMER); - // fall through case MO_EXTREMITYFIST: { short x, y, i = 2; // Move 2 cells for Issen(from target) @@ -3708,7 +3674,9 @@ int skill_castend_damage_id (struct block_list* src, struct block_list *bl, uint #ifdef RENEWAL sc_start(src,SC_EXTREMITYFIST2,100,skill_lv,skill->get_time(skill_id,skill_lv)); #endif - }else + }else{ + status_change_end(src, SC_NJ_NEN, INVALID_TIMER); + status_change_end(src, SC_HIDING, INVALID_TIMER); status_set_hp(src, #ifdef RENEWAL max(status_get_max_hp(src)/100, 1) @@ -3716,7 +3684,7 @@ int skill_castend_damage_id (struct block_list* src, struct block_list *bl, uint 1 #endif , 0); - + } dir = iMap->calc_dir(src,bl->x,bl->y); if( dir > 0 && dir < 4) x = -i; else if( dir > 4 ) x = i; @@ -3945,6 +3913,7 @@ int skill_castend_damage_id (struct block_list* src, struct block_list *bl, uint case AB_DUPLELIGHT_MAGIC: case WM_METALICSOUND: case MH_ERASER_CUTTER: + case KO_KAIHOU: skill->attack(BF_MAGIC,src,src,bl,skill_id,skill_lv,tick,flag); break; @@ -4011,7 +3980,7 @@ int skill_castend_damage_id (struct block_list* src, struct block_list *bl, uint break; case SL_SMA: - status_change_end(src, SC_SMA, INVALID_TIMER); + status_change_end(src, SC_SMA_READY, INVALID_TIMER); case SL_STIN: case SL_STUN: if (sd && !battle_config.allow_es_magic_pc && bl->type != BL_MOB) { @@ -4033,11 +4002,15 @@ int skill_castend_damage_id (struct block_list* src, struct block_list *bl, uint case NJ_ZENYNAGE: case GN_THORNS_TRAP: case GN_HELLS_PLANT_ATK: +#ifdef RENEWAL + case ASC_BREAKER: +#endif skill->attack(BF_MISC,src,src,bl,skill_id,skill_lv,tick,flag); break; /** * Rune Knight **/ + case RK_DRAGONBREATH_WATER: case RK_DRAGONBREATH: { struct status_change *tsc = NULL; if( (tsc = status_get_sc(bl)) && (tsc->data[SC_HIDING] )) { @@ -4112,16 +4085,6 @@ int skill_castend_damage_id (struct block_list* src, struct block_list *bl, uint skill->attack(BF_WEAPON,src,src,bl,skill_id,skill_lv,tick,flag); break; - case RK_STORMBLAST: - case RK_CRUSHSTRIKE: - if( sd ) { - if( pc->checkskill(sd,RK_RUNEMASTERY) >= ( skill_id == RK_CRUSHSTRIKE ? 7 : 3 ) ) - skill->attack(BF_WEAPON,src,src,bl,skill_id,skill_lv,tick,flag); - else - clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); - } else //non-sd support - skill->attack(BF_WEAPON,src,src,bl,skill_id,skill_lv,tick,flag); - break; case GC_DARKILLUSION: { short x, y; @@ -4145,9 +4108,8 @@ int skill_castend_damage_id (struct block_list* src, struct block_list *bl, uint } break; - case GC_WEAPONCRUSH: - if( sc && sc->data[SC_COMBO] && sc->data[SC_COMBO]->val1 == GC_WEAPONBLOCKING ) + if( sc && sc->data[SC_COMBOATTACK] && sc->data[SC_COMBOATTACK]->val1 == GC_WEAPONBLOCKING ) skill->attack(BF_WEAPON,src,src,bl,skill_id,skill_lv,tick,flag); else if( sd ) clif->skill_fail(sd,skill_id,USESKILL_FAIL_GC_WEAPONBLOCKING,0); @@ -4173,7 +4135,7 @@ int skill_castend_damage_id (struct block_list* src, struct block_list *bl, uint break; case WL_CHAINLIGHTNING: clif->skill_nodamage(src,bl,skill_id,skill_lv,1); - skill->addtimerskill(src,tick + 150,bl->id,3,0,WL_CHAINLIGHTNING_ATK,skill_lv,4+skill_lv,flag); + skill->addtimerskill(src,tick+status_get_amotion(src),bl->id,0,0,WL_CHAINLIGHTNING_ATK,skill_lv,0,flag); break; case WL_DRAINLIFE: { @@ -4182,7 +4144,7 @@ int skill_castend_damage_id (struct block_list* src, struct block_list *bl, uint heal = heal * (5 + 5 * skill_lv) / 100; - if( bl->type == BL_SKILL ) + if( bl->type == BL_SKILL || status_get_hp(src) == status_get_max_hp(src)) // Don't absorb when caster was in full HP heal = 0; // Don't absorb heal from Ice Walls or other skill units. if( heal && rnd()%100 < rate ) @@ -4194,61 +4156,43 @@ int skill_castend_damage_id (struct block_list* src, struct block_list *bl, uint break; case WL_TETRAVORTEX: - if( sd ) { - int spheres[5] = { 0, 0, 0, 0, 0 }, - positions[5] = {-1,-1,-1,-1,-1 }, - i, j = 0, k, subskill = 0; - - for( i = SC_SPHERE_1; i <= SC_SPHERE_5; i++ ) - if( sc && sc->data[i] ) - { - spheres[j] = i; - positions[j] = sc->data[i]->val2; - j++; // - } - - if( j < 4 ) - { // Need 4 spheres minimum - clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); - break; - } - - // Sphere Sort, this time from new to old - for( i = 0; i <= j - 2; i++ ) - for( k = i + 1; k <= j - 1; k++ ) - if( positions[i] < positions[k] ) - { - swap(positions[i],positions[k]); - swap(spheres[i],spheres[k]); + if( sc ){ + int i = SC_SUMMON5, x = 0; + int types[][2] = {{0, 0}, {0, 0}, {0, 0}, {0, 0}}; + for(; i >= SC_SUMMON1; i--){ + if( sc->data[i] ){ + int skillid = WL_TETRAVORTEX_FIRE + (sc->data[i]->val1 - WLS_FIRE) + (sc->data[i]->val1 == WLS_WIND) - (sc->data[i]->val1 == WLS_WATER), sc_index = 0, rate = 0; + if( x < 4 ){ + types[x][0] = (sc->data[i]->val1 - WLS_FIRE) + 1; + types[x][1] = 25; // 25% each for equal sharing + if( x == 3 ){ + x = 0; + sc_index = types[rand()%4][0]; + for(; x < 4; x++) + if(types[x][0] == sc_index) + rate += types[x][1]; + } + skill->addtimerskill(src, tick + (SC_SUMMON5-i) * 206, bl->id, sc_index, rate, skillid, skill_lv, x, flag); } - - k = 0; - for( i = 0; i < 4; i++ ) - { - switch( sc->data[spheres[i]]->val1 ) - { - case WLS_FIRE: subskill = WL_TETRAVORTEX_FIRE; k |= 1; break; - case WLS_WIND: subskill = WL_TETRAVORTEX_WIND; k |= 4; break; - case WLS_WATER: subskill = WL_TETRAVORTEX_WATER; k |= 2; break; - case WLS_STONE: subskill = WL_TETRAVORTEX_GROUND; k |= 8; break; + status_change_end(src, (sc_type)i, INVALID_TIMER); + x++; } - skill->addtimerskill(src, tick + i * 200, bl->id, k, 0, subskill, skill_lv, i, flag); - clif->skill_nodamage(src, bl, subskill, skill_lv, 1); - status_change_end(src, spheres[i], INVALID_TIMER); } } break; case WL_RELEASE: if( sd ) { - int i; + int i, cooldown; + clif->skill_nodamage(src, bl, skill_id, skill_lv, 1); + skill->toggle_magicpower(src, skill_id); // Priority is to release SpellBook if( sc && sc->data[SC_READING_SB] ) { // SpellBook uint16 skill_id, skill_lv, point, s = 0; - int spell[SC_MAXSPELLBOOK-SC_SPELLBOOK1 + 1]; + int spell[SC_SPELLBOOK7-SC_SPELLBOOK1 + 1]; - for(i = SC_MAXSPELLBOOK; i >= SC_SPELLBOOK1; i--) // List all available spell to be released - if( sc->data[i] ) spell[s++] = i; + for(i = SC_SPELLBOOK7; i >= SC_SPELLBOOK1; i--) // List all available spell to be released + if( sc->data[i] ) spell[s++] = i; if ( s == 0 ) break; @@ -4261,13 +4205,12 @@ int skill_castend_damage_id (struct block_list* src, struct block_list *bl, uint status_change_end(src, (sc_type)i, INVALID_TIMER); }else //something went wrong :( break; - + if( sc->data[SC_READING_SB]->val2 > point ) sc->data[SC_READING_SB]->val2 -= point; else // Last spell to be released status_change_end(src, SC_READING_SB, INVALID_TIMER); - if( bl->type != BL_SKILL ) /* skill types will crash the client */ - clif->skill_nodamage(src, bl, skill_id, skill_lv, 1); + if( !skill->check_condition_castbegin(sd, skill_id, skill_lv) ) break; @@ -4284,47 +4227,32 @@ int skill_castend_damage_id (struct block_list* src, struct block_list *bl, uint } sd->ud.canact_tick = tick + skill->delay_fix(src, skill_id, skill_lv); - clif->status_change(src, SI_ACTIONDELAY, 1, skill->delay_fix(src, skill_id, skill_lv), 0, 0, 0); - } else { // Summon Balls - int j = 0, k, skele; - int spheres[5] = { 0, 0, 0, 0, 0 }, - positions[5] = {-1,-1,-1,-1,-1 }; - - for( i = SC_SPHERE_1; i <= SC_SPHERE_5; i++ ) - if( sc && sc->data[i] ) { - spheres[j] = i; - positions[j] = sc->data[i]->val2; - sc->data[i]->val2--; // Prepares for next position - j++; - } + clif->status_change(src, SI_POSTDELAY, 1, skill->delay_fix(src, skill_id, skill_lv), 0, 0, 0); - if( j == 0 ) { // No Spheres - clif->skill_fail(sd,skill_id,USESKILL_FAIL_SUMMON_NONE,0); - break; + cooldown = skill_get_cooldown(skill_id, skill_lv); + for (i = 0; i < ARRAYLENGTH(sd->skillcooldown) && sd->skillcooldown[i].id; i++) { + if (sd->skillcooldown[i].id == skill_id){ + cooldown += sd->skillcooldown[i].val; + break; + } } - - // Sphere Sort - for( i = 0; i <= j - 2; i++ ) - for( k = i + 1; k <= j - 1; k++ ) - if( positions[i] > positions[k] ) { - swap(positions[i],positions[k]); - swap(spheres[i],spheres[k]); - } - - if( skill_lv == 1 ) j = 1; // Limit only to one ball - for( i = 0; i < j; i++ ) { - skele = WL_RELEASE - 5 + sc->data[spheres[i]]->val1 - WLS_FIRE; // Convert Ball Element into Skill ATK for balls - // WL_SUMMON_ATK_FIRE, WL_SUMMON_ATK_WIND, WL_SUMMON_ATK_WATER, WL_SUMMON_ATK_GROUND - skill->addtimerskill(src,tick+status_get_adelay(src)*i,bl->id,0,0,skele,sc->data[spheres[i]]->val3,BF_MAGIC,flag|SD_LEVEL); - status_change_end(src, spheres[i], INVALID_TIMER); // Eliminate ball + if(cooldown) + skill->blockpc_start(sd, skill_id, cooldown, false); + }else if( sc ){ // Summon Balls + int i = SC_SUMMON5; + for(; i >= SC_SUMMON1; i--){ + if( sc->data[i] ){ + int skillid = WL_SUMMON_ATK_FIRE + (sc->data[i]->val1 - WLS_FIRE); + skill->addtimerskill(src, tick + status_get_adelay(src) * (SC_SUMMON5 - i), bl->id, 0, 0, skillid, skill_lv, BF_MAGIC, flag); + status_change_end(src, (sc_type)i, INVALID_TIMER); + if(skill_lv == 1) + break; + } } - clif->skill_nodamage(src,bl,skill_id,0,1); } } break; case WL_FROSTMISTY: - // Causes Freezing status through walls. - sc_start(bl,status_skill2sc(skill_id),20+12*skill_lv+(sd ? sd->status.job_level : 50)/5,skill_lv,skill->get_time(skill_id,skill_lv)); // Doesn't deal damage through non-shootable walls. if( path_search(NULL,src->m,src->x,src->y,bl->x,bl->y,1,CELL_CHKWALL) ) skill->attack(BF_MAGIC,src,src,bl,skill_id,skill_lv,tick,flag|SD_ANIMATION); @@ -4453,19 +4381,19 @@ int skill_castend_damage_id (struct block_list* src, struct block_list *bl, uint break; case SR_HOWLINGOFLION: - status_change_end(bl, SC_SWINGDANCE, INVALID_TIMER); - status_change_end(bl, SC_SYMPHONYOFLOVER, INVALID_TIMER); - status_change_end(bl, SC_MOONLITSERENADE, INVALID_TIMER); - status_change_end(bl, SC_RUSHWINDMILL, INVALID_TIMER); + status_change_end(bl, SC_SWING, INVALID_TIMER); + status_change_end(bl, SC_SYMPHONY_LOVE, INVALID_TIMER); + status_change_end(bl, SC_MOONLIT_SERENADE, INVALID_TIMER); + status_change_end(bl, SC_RUSH_WINDMILL, INVALID_TIMER); status_change_end(bl, SC_ECHOSONG, INVALID_TIMER); status_change_end(bl, SC_HARMONIZE, INVALID_TIMER); status_change_end(bl, SC_SIRCLEOFNATURE, INVALID_TIMER); - status_change_end(bl, SC_SATURDAYNIGHTFEVER, INVALID_TIMER); - status_change_end(bl, SC_DANCEWITHWUG, INVALID_TIMER); - status_change_end(bl, SC_LERADSDEW, INVALID_TIMER); + status_change_end(bl, SC_SATURDAY_NIGHT_FEVER, INVALID_TIMER); + status_change_end(bl, SC_DANCE_WITH_WUG, INVALID_TIMER); + status_change_end(bl, SC_LERADS_DEW, INVALID_TIMER); status_change_end(bl, SC_MELODYOFSINK, INVALID_TIMER); - status_change_end(bl, SC_BEYONDOFWARCRY, INVALID_TIMER); - status_change_end(bl, SC_UNLIMITEDHUMMINGVOICE, INVALID_TIMER); + status_change_end(bl, SC_BEYOND_OF_WARCRY, INVALID_TIMER); + status_change_end(bl, SC_UNLIMITED_HUMMING_VOICE, INVALID_TIMER); skill->attack(BF_WEAPON, src, src, bl, skill_id, skill_lv, tick, flag|SD_ANIMATION); break; @@ -4573,7 +4501,6 @@ int skill_castend_damage_id (struct block_list* src, struct block_list *bl, uint } break; - //recursive homon skill case MH_MAGMA_FLOW: case MH_XENO_SLASHER: @@ -4589,8 +4516,8 @@ int skill_castend_damage_id (struct block_list* src, struct block_list *bl, uint case MH_NEEDLE_OF_PARALYZE: skill->attack(BF_WEAPON, src, src, bl, skill_id, skill_lv, tick, flag); break; - case MH_TINDER_BREAKER: - if (unit_movepos(src, bl->x, bl->y, 1, 1)) { + case MH_TINDER_BREAKER: + if (unit_movepos(src, bl->x, bl->y, 1, 1)) { #if PACKETVER >= 20111005 clif->snap(src, bl->x, bl->y); #else @@ -4598,7 +4525,7 @@ int skill_castend_damage_id (struct block_list* src, struct block_list *bl, uint #endif } clif->skill_nodamage(src,bl,skill_id,skill_lv, - sc_start4(bl,SC_CLOSECONFINE2,100,skill_lv,src->id,0,0,skill->get_time(skill_id,skill_lv))); + sc_start4(bl,SC_RG_CCONFINE_S,100,skill_lv,src->id,0,0,skill->get_time(skill_id,skill_lv))); skill->attack(BF_WEAPON, src, src, bl, skill_id, skill_lv, tick, flag); break; @@ -4651,4760 +4578,4697 @@ int skill_castend_damage_id (struct block_list* src, struct block_list *bl, uint /*========================================== * *------------------------------------------*/ -int skill_castend_nodamage_id (struct block_list *src, struct block_list *bl, uint16 skill_id, uint16 skill_lv, unsigned int tick, int flag) +int skill_castend_id(int tid, unsigned int tick, int id, intptr_t data) { - struct map_session_data *sd, *dstsd; - struct mob_data *md, *dstmd; - struct homun_data *hd; - struct mercenary_data *mer; - struct status_data *sstatus, *tstatus; - struct status_change *tsc; - struct status_change_entry *tsce; - - int i = 0; - enum sc_type type; - - if(skill_id > 0 && !skill_lv) return 0; // celest + struct block_list *target, *src; + struct map_session_data *sd; + struct mob_data *md; + struct unit_data *ud; + struct status_change *sc = NULL; + int inf,inf2,flag = 0; - nullpo_retr(1, src); - nullpo_retr(1, bl); + src = iMap->id2bl(id); + if( src == NULL ) + { + ShowDebug("skill_castend_id: src == NULL (tid=%d, id=%d)\n", tid, id); + return 0;// not found + } - if (src->m != bl->m) - return 1; + ud = unit_bl2ud(src); + if( ud == NULL ) + { + ShowDebug("skill_castend_id: ud == NULL (tid=%d, id=%d)\n", tid, id); + return 0;// ??? + } - sd = BL_CAST(BL_PC, src); - hd = BL_CAST(BL_HOM, src); + sd = BL_CAST(BL_PC, src); md = BL_CAST(BL_MOB, src); - mer = BL_CAST(BL_MER, src); - - dstsd = BL_CAST(BL_PC, bl); - dstmd = BL_CAST(BL_MOB, bl); - if(bl->prev == NULL) - return 1; - if(status_isdead(src)) - return 1; + if( src->prev == NULL ) { + ud->skilltimer = INVALID_TIMER; + return 0; + } - if( src != bl && status_isdead(bl) ) { - /** - * Skills that may be cast on dead targets - **/ - switch( skill_id ) { - case NPC_WIDESOULDRAIN: - case PR_REDEMPTIO: - case ALL_RESURRECTION: - case WM_DEADHILLHERE: - break; - default: - return 1; + if(ud->skill_id != SA_CASTCANCEL && ud->skill_id != SO_SPELLFIST) {// otherwise handled in unit_skillcastcancel() + if( ud->skilltimer != tid ) { + ShowError("skill_castend_id: Timer mismatch %d!=%d!\n", ud->skilltimer, tid); + ud->skilltimer = INVALID_TIMER; + return 0; } - } - tstatus = status_get_status_data(bl); - sstatus = status_get_status_data(src); + if( sd && ud->skilltimer != INVALID_TIMER && (pc->checkskill(sd,SA_FREECAST) > 0 || ud->skill_id == LG_EXEEDBREAK) ) + {// restore original walk speed + ud->skilltimer = INVALID_TIMER; + status_calc_bl(&sd->bl, SCB_SPEED); + } - //Check for undead skills that convert a no-damage skill into a damage one. [Skotlex] - switch (skill_id) { - case HLIF_HEAL: //[orn] - if (bl->type != BL_HOM) { - if (sd) clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0) ; - break ; - } - case AL_HEAL: - case ALL_RESURRECTION: - case PR_ASPERSIO: - /** - * Arch Bishop - **/ - case AB_RENOVATIO: - case AB_HIGHNESSHEAL: - //Apparently only player casted skills can be offensive like this. - if (sd && battle->check_undead(tstatus->race,tstatus->def_ele)) { - if (battle->check_target(src, bl, BCT_ENEMY) < 1) { - //Offensive heal does not works on non-enemies. [Skotlex] - clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); - return 0; - } - return skill->castend_damage_id (src, bl, skill_id, skill_lv, tick, flag); - } - break; - case NPC_SMOKING: //Since it is a self skill, this one ends here rather than in damage_id. [Skotlex] - return skill->castend_damage_id (src, bl, skill_id, skill_lv, tick, flag); - case MH_STEINWAND: { - struct block_list *s_src = battle->get_master(src); - short ret = 0; - if(!skill->check_unit_range(src, src->x, src->y, skill_id, skill_lv)) //prevent reiteration - ret = skill->castend_pos2(src,src->x,src->y,skill_id,skill_lv,tick,flag); //cast on homon - if(s_src && !skill->check_unit_range(s_src, s_src->x, s_src->y, skill_id, skill_lv)) - ret |= skill->castend_pos2(s_src,s_src->x,s_src->y,skill_id,skill_lv,tick,flag); //cast on master - if (hd) - skill->blockhomun_start(hd, skill_id, skill->get_cooldown(skill_id, skill_lv)); - return ret; - } - break; - default: - //Skill is actually ground placed. - if (src == bl && skill->get_unit_id(skill_id,0)) - return skill->castend_pos2(src,bl->x,bl->y,skill_id,skill_lv,tick,0); + ud->skilltimer = INVALID_TIMER; } - type = status_skill2sc(skill_id); - tsc = status_get_sc(bl); - tsce = (tsc && type != -1)?tsc->data[type]:NULL; + if (ud->skilltarget == id) + target = src; + else + target = iMap->id2bl(ud->skilltarget); - if (src!=bl && type > -1 && - (i = skill->get_ele(skill_id, skill_lv)) > ELE_NEUTRAL && - skill->get_inf(skill_id) != INF_SUPPORT_SKILL && - battle->attr_fix(NULL, NULL, 100, i, tstatus->def_ele, tstatus->ele_lv) <= 0) - return 1; //Skills that cause an status should be blocked if the target element blocks its element. + // Use a do so that you can break out of it when the skill fails. + do { + if(!target || target->prev==NULL) break; - iMap->freeblock_lock(); - switch(skill_id) { - case HLIF_HEAL: //[orn] - case AL_HEAL: - /** - * Arch Bishop - **/ - case AB_HIGHNESSHEAL: - { - int heal = skill->calc_heal(src, bl, (skill_id == AB_HIGHNESSHEAL)?AL_HEAL:skill_id, (skill_id == AB_HIGHNESSHEAL)?10:skill_lv, true); - int heal_get_jobexp; - //Highness Heal: starts at 1.5 boost + 0.5 for each level - if( skill_id == AB_HIGHNESSHEAL ) { - heal = heal * ( 15 + 5 * skill_lv ) / 10; - } - if( status_isimmune(bl) || - (dstmd && (dstmd->class_ == MOBID_EMPERIUM || mob_is_battleground(dstmd))) || - (dstsd && pc_ismadogear(dstsd)) )//Mado is immune to heal - heal=0; + if(src->m != target->m || status_isdead(src)) break; - if( sd && dstsd && sd->status.partner_id == dstsd->status.char_id && (sd->class_&MAPID_UPPERMASK) == MAPID_SUPER_NOVICE && sd->status.sex == 0 ) - heal = heal*2; - - if( tsc && tsc->count ) - { - if( tsc->data[SC_KAITE] && !(sstatus->mode&MD_BOSS) ) - { //Bounce back heal - if (--tsc->data[SC_KAITE]->val2 <= 0) - status_change_end(bl, SC_KAITE, INVALID_TIMER); - if (src == bl) - heal=0; //When you try to heal yourself under Kaite, the heal is voided. - else { - bl = src; - dstsd = sd; - } - } - else if (tsc->data[SC_BERSERK] || tsc->data[SC_SATURDAYNIGHTFEVER] || tsc->data[SC__BLOODYLUST]) - heal = 0; //Needed so that it actually displays 0 when healing. + switch (ud->skill_id) { + //These should become skill_castend_pos + case WE_CALLPARTNER: + if(sd) clif->callpartner(sd); + case WE_CALLPARENT: + case WE_CALLBABY: + case AM_RESURRECTHOMUN: + case PF_SPIDERWEB: + //Find a random spot to place the skill. [Skotlex] + inf2 = skill->get_splash(ud->skill_id, ud->skill_lv); + ud->skillx = target->x + inf2; + ud->skilly = target->y + inf2; + if (inf2 && !iMap->random_dir(target, &ud->skillx, &ud->skilly)) { + ud->skillx = target->x; + ud->skilly = target->y; } - clif->skill_nodamage (src, bl, skill_id, heal, 1); - if( tsc && tsc->data[SC_AKAITSUKI] && heal && skill_id != HLIF_HEAL ) - heal = ~heal + 1; - heal_get_jobexp = status_heal(bl,heal,0,0); + ud->skilltimer=tid; + return skill->castend_pos(tid,tick,id,data); + case GN_WALLOFTHORN: + ud->skillx = target->x; + ud->skilly = target->y; + ud->skilltimer = tid; + return skill->castend_pos(tid,tick,id,data); + } - if(sd && dstsd && heal > 0 && sd != dstsd && battle_config.heal_exp > 0){ - heal_get_jobexp = heal_get_jobexp * battle_config.heal_exp / 100; - if (heal_get_jobexp <= 0) - heal_get_jobexp = 1; - pc->gainexp (sd, bl, 0, heal_get_jobexp, false); - } + if(ud->skill_id == RG_BACKSTAP) { + uint8 dir = iMap->calc_dir(src,target->x,target->y),t_dir = unit_getdir(target); + if(check_distance_bl(src, target, 0) || iMap->check_dir(dir,t_dir)) { + break; } - break; + } - case PR_REDEMPTIO: - if (sd && !(flag&1)) { - if (sd->status.party_id == 0) { - clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); - break; - } - skill_area_temp[0] = 0; - party_foreachsamemap(skill->area_sub, - sd,skill->get_splash(skill_id, skill_lv), - src,skill_id,skill_lv,tick, flag|BCT_PARTY|1, - skill->castend_nodamage_id); - if (skill_area_temp[0] == 0) { - clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); - break; - } - skill_area_temp[0] = 5 - skill_area_temp[0]; // The actual penalty... - if (skill_area_temp[0] > 0 && !map[src->m].flag.noexppenalty) { //Apply penalty - sd->status.base_exp -= min(sd->status.base_exp, pc->nextbaseexp(sd) * skill_area_temp[0] * 2/1000); //0.2% penalty per each. - sd->status.job_exp -= min(sd->status.job_exp, pc->nextjobexp(sd) * skill_area_temp[0] * 2/1000); - clif->updatestatus(sd,SP_BASEEXP); - clif->updatestatus(sd,SP_JOBEXP); - } - status_set_hp(src, 1, 0); - status_set_sp(src, 0, 0); + if( ud->skill_id == PR_TURNUNDEAD ) { + struct status_data *tstatus = status_get_status_data(target); + if( !battle->check_undead(tstatus->race, tstatus->def_ele) ) break; - } else if (status_isdead(bl) && flag&1) { //Revive - skill_area_temp[0]++; //Count it in, then fall-through to the Resurrection code. - skill_lv = 3; //Resurrection level 3 is used - } else //Invalid target, skip resurrection. + } + + if( ud->skill_id == RA_WUGSTRIKE ){ + if( !path_search(NULL,src->m,src->x,src->y,target->x,target->y,1,CELL_CHKNOREACH)) break; + } - case ALL_RESURRECTION: - if(sd && (map_flag_gvg(bl->m) || map[bl->m].flag.battleground)) - { //No reviving in WoE grounds! - clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); + if( ud->skill_id == PR_LEXDIVINA || ud->skill_id == MER_LEXDIVINA ) + { + sc = status_get_sc(target); + if( battle->check_target(src,target, BCT_ENEMY) <= 0 && (!sc || !sc->data[SC_SILENCE]) ) + { //If it's not an enemy, and not silenced, you can't use the skill on them. [Skotlex] + clif->skill_nodamage (src, target, ud->skill_id, ud->skill_lv, 0); break; } - if (!status_isdead(bl)) - break; + } + else + { // Check target validity. + inf = skill->get_inf(ud->skill_id); + inf2 = skill->get_inf2(ud->skill_id); + + if(inf&INF_ATTACK_SKILL || + (inf&INF_SELF_SKILL && inf2&INF2_NO_TARGET_SELF) //Combo skills + ) // Casted through combo. + inf = BCT_ENEMY; //Offensive skill. + else if(inf2&INF2_NO_ENEMY) + inf = BCT_NOENEMY; + else + inf = 0; + + if(inf2 & (INF2_PARTY_ONLY|INF2_GUILD_ONLY) && src != target) { - int per = 0, sper = 0; - if (tsc && tsc->data[SC_HELLPOWER]) - break; + inf |= + (inf2&INF2_PARTY_ONLY?BCT_PARTY:0)| + (inf2&INF2_GUILD_ONLY?BCT_GUILD:0); + //Remove neutral targets (but allow enemy if skill is designed to be so) + inf &= ~BCT_NEUTRAL; + } - if (map[bl->m].flag.pvp && dstsd && dstsd->pvp_point < 0) + if( sd && (inf2&INF2_CHORUS_SKILL) && skill->check_pc_partner(sd, ud->skill_id, &ud->skill_lv, 1, 0) < 1 ) { + clif->skill_fail(sd, ud->skill_id, USESKILL_FAIL_NEED_HELPER, 0); + break; + } + + if( ud->skill_id >= SL_SKE && ud->skill_id <= SL_SKA && target->type == BL_MOB ) + { + if( ((TBL_MOB*)target)->class_ == MOBID_EMPERIUM ) break; + } + else if (inf && battle->check_target(src, target, inf) <= 0){ + if (sd) clif->skill_fail(sd,ud->skill_id,USESKILL_FAIL_LEVEL,0); + break; + } - switch(skill_lv){ - case 1: per=10; break; - case 2: per=30; break; - case 3: per=50; break; - case 4: per=80; break; - } - if(dstsd && dstsd->special_state.restart_full_recover) - per = sper = 100; - if (status_revive(bl, per, sper)) - { - clif->skill_nodamage(src,bl,ALL_RESURRECTION,skill_lv,1); //Both Redemptio and Res show this skill-animation. - if(sd && dstsd && battle_config.resurrection_exp > 0) - { - int exp = 0,jexp = 0; - int lv = dstsd->status.base_level - sd->status.base_level, jlv = dstsd->status.job_level - sd->status.job_level; - if(lv > 0 && pc->nextbaseexp(dstsd)) { - exp = (int)((double)dstsd->status.base_exp * (double)lv * (double)battle_config.resurrection_exp / 1000000.); - if (exp < 1) exp = 1; - } - if(jlv > 0 && pc->nextjobexp(dstsd)) { - jexp = (int)((double)dstsd->status.job_exp * (double)lv * (double)battle_config.resurrection_exp / 1000000.); - if (jexp < 1) jexp = 1; - } - if(exp > 0 || jexp > 0) - pc->gainexp (sd, bl, exp, jexp, false); - } - } + if(inf&BCT_ENEMY && (sc = status_get_sc(target)) && + sc->data[SC_FOGWALL] && + rnd() % 100 < 75) { //Fogwall makes all offensive-type targetted skills fail at 75% + if (sd) clif->skill_fail(sd, ud->skill_id, USESKILL_FAIL_LEVEL, 0); + break; } - break; + } - case AL_DECAGI: - case MER_DECAGI: - clif->skill_nodamage (src, bl, skill_id, skill_lv, - sc_start(bl, type, (40 + skill_lv * 2 + (status_get_lv(src) + sstatus->int_)/5), skill_lv, skill->get_time(skill_id,skill_lv))); + //Avoid doing double checks for instant-cast skills. + if (tid != INVALID_TIMER && !status_check_skilluse(src, target, ud->skill_id, 1)) break; - case AL_CRUCIS: - if (flag&1) - sc_start(bl,type, 23+skill_lv*4 +status_get_lv(src) -status_get_lv(bl), skill_lv,skill->get_time(skill_id,skill_lv)); - else { - iMap->foreachinrange(skill->area_sub, src, skill->get_splash(skill_id, skill_lv), BL_CHAR, - src, skill_id, skill_lv, tick, flag|BCT_ENEMY|1, skill->castend_nodamage_id); - clif->skill_nodamage(src, bl, skill_id, skill_lv, 1); + if(md) { + md->last_thinktime=tick +MIN_MOBTHINKTIME; + if(md->skill_idx >= 0 && md->db->skill[md->skill_idx].emotion >= 0) + clif->emotion(src, md->db->skill[md->skill_idx].emotion); + } + + if(src != target && battle_config.skill_add_range && + !check_distance_bl(src, target, skill->get_range2(src,ud->skill_id,ud->skill_lv)+battle_config.skill_add_range)) + { + if (sd) { + clif->skill_fail(sd,ud->skill_id,USESKILL_FAIL_LEVEL,0); + if(battle_config.skill_out_range_consume) //Consume items anyway. [Skotlex] + skill->consume_requirement(sd,ud->skill_id,ud->skill_lv,3); } break; + } - case PR_LEXDIVINA: - case MER_LEXDIVINA: - if( tsce ) - status_change_end(bl,type, INVALID_TIMER); + if( sd ) + { + if( !skill->check_condition_castend(sd, ud->skill_id, ud->skill_lv) ) + break; else - sc_start(bl,type,100,skill_lv,skill->get_time(skill_id,skill_lv)); - clif->skill_nodamage (src, bl, skill_id, skill_lv, 1); + skill->consume_requirement(sd,ud->skill_id,ud->skill_lv,1); + } +#ifdef OFFICIAL_WALKPATH + if( !path_search_long(NULL, src->m, src->x, src->y, target->x, target->y, CELL_CHKWALL) ) + break; +#endif + if( (src->type == BL_MER || src->type == BL_HOM) && !skill->check_condition_mercenary(src, ud->skill_id, ud->skill_lv, 1) ) break; - case SA_ABRACADABRA: - { - int abra_skill_id = 0, abra_skill_lv; - do { - i = rnd() % MAX_SKILL_ABRA_DB; - abra_skill_id = skill_abra_db[i].skill_id; - } while (abra_skill_id == 0 || - skill_abra_db[i].req_lv > skill_lv || //Required lv for it to appear - rnd()%10000 >= skill_abra_db[i].per - ); - abra_skill_lv = min(skill_lv, skill->get_max(abra_skill_id)); - clif->skill_nodamage (src, bl, skill_id, skill_lv, 1); + if (ud->state.running && ud->skill_id == TK_JUMPKICK) { + ud->state.running = 0; + status_change_end(src, SC_RUN, INVALID_TIMER); + flag = 1; + } - if( sd ) - {// player-casted - sd->state.abra_flag = 1; - sd->skillitem = abra_skill_id; - sd->skillitemlv = abra_skill_lv; - clif->item_skill(sd, abra_skill_id, abra_skill_lv); - } - else - {// mob-casted - struct unit_data *ud = unit_bl2ud(src); - int inf = skill->get_inf(abra_skill_id); - if (!ud) break; - if (inf&INF_SELF_SKILL || inf&INF_SUPPORT_SKILL) { - if (src->type == BL_PET) - bl = (struct block_list*)((TBL_PET*)src)->msd; - if (!bl) bl = src; - unit_skilluse_id(src, bl->id, abra_skill_id, abra_skill_lv); - } else { //Assume offensive skills - int target_id = 0; - if (ud->target) - target_id = ud->target; - else switch (src->type) { - case BL_MOB: target_id = ((TBL_MOB*)src)->target_id; break; - case BL_PET: target_id = ((TBL_PET*)src)->target_id; break; - } - if (!target_id) - break; - if (skill->get_casttype(abra_skill_id) == CAST_GROUND) { - bl = iMap->id2bl(target_id); - if (!bl) bl = src; - unit_skilluse_pos(src, bl->x, bl->y, abra_skill_id, abra_skill_lv); - } else - unit_skilluse_id(src, target_id, abra_skill_id, abra_skill_lv); - } - } - } - break; - - case SA_COMA: - clif->skill_nodamage(src,bl,skill_id,skill_lv, - sc_start(bl,type,100,skill_lv,skill->get_time2(skill_id,skill_lv))); - break; - case SA_FULLRECOVERY: - clif->skill_nodamage(src,bl,skill_id,skill_lv,1); - if (status_isimmune(bl)) - break; - status_percent_heal(bl, 100, 100); - break; - case NPC_ALLHEAL: - { - int heal; - if( status_isimmune(bl) ) - break; - heal = status_percent_heal(bl, 100, 0); - clif->skill_nodamage(NULL, bl, AL_HEAL, heal, 1); - if( dstmd ) - { // Reset Damage Logs - memset(dstmd->dmglog, 0, sizeof(dstmd->dmglog)); - dstmd->tdmg = 0; + if (ud->walktimer != INVALID_TIMER && ud->skill_id != TK_RUN && ud->skill_id != RA_WUGDASH) + unit_stop_walking(src,1); + + if( !sd || sd->skillitem != ud->skill_id || skill->get_delay(ud->skill_id,ud->skill_lv) ) + ud->canact_tick = tick + skill->delay_fix(src, ud->skill_id, ud->skill_lv); //Tests show wings don't overwrite the delay but skill scrolls do. [Inkfish] + if (sd) { //Cooldown application + int i, cooldown = skill->get_cooldown(ud->skill_id, ud->skill_lv); + for (i = 0; i < ARRAYLENGTH(sd->skillcooldown) && sd->skillcooldown[i].id; i++) { // Increases/Decreases cooldown of a skill by item/card bonuses. + if (sd->skillcooldown[i].id == ud->skill_id){ + cooldown += sd->skillcooldown[i].val; + break; } } - break; - case SA_SUMMONMONSTER: - clif->skill_nodamage(src,bl,skill_id,skill_lv,1); - if (sd) mob_once_spawn(sd, src->m, src->x, src->y," --ja--", -1, 1, "", SZ_SMALL, AI_NONE); - break; - case SA_LEVELUP: - clif->skill_nodamage(src,bl,skill_id,skill_lv,1); - if (sd && pc->nextbaseexp(sd)) pc->gainexp(sd, NULL, pc->nextbaseexp(sd) * 10 / 100, 0, false); - break; - case SA_INSTANTDEATH: - clif->skill_nodamage(src,bl,skill_id,skill_lv,1); - status_set_hp(bl,1,0); - break; - case SA_QUESTION: - case SA_GRAVITY: - clif->skill_nodamage(src,bl,skill_id,skill_lv,1); - break; - case SA_CLASSCHANGE: - case SA_MONOCELL: - if (dstmd) + if(cooldown) + skill->blockpc_start(sd, ud->skill_id, cooldown, false); + } + if( battle_config.display_status_timers && sd ) + clif->status_change(src, SI_POSTDELAY, 1, skill->delay_fix(src, ud->skill_id, ud->skill_lv), 0, 0, 0); + if( sd ) + { + switch( ud->skill_id ) { - int class_; - if ( sd && dstmd->status.mode&MD_BOSS ) - { - clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); - break; - } - class_ = skill_id==SA_MONOCELL?1002:mob_get_random_id(4, 1, 0); - clif->skill_nodamage(src,bl,skill_id,skill_lv,1); - mob_class_change(dstmd,class_); - if( tsc && dstmd->status.mode&MD_BOSS ) + case GS_DESPERADO: + sd->canequip_tick = tick + skill->get_time(ud->skill_id, ud->skill_lv); + break; + case CR_GRANDCROSS: + case NPC_GRANDDARKNESS: + if( (sc = status_get_sc(src)) && sc->data[SC_NOEQUIPSHIELD] ) { - const enum sc_type scs[] = { SC_QUAGMIRE, SC_PROVOKE, SC_ROKISWEIL, SC_GRAVITATION, SC_SUITON, SC_STRIPWEAPON, SC_STRIPSHIELD, SC_STRIPARMOR, SC_STRIPHELM, SC_BLADESTOP }; - for (i = SC_COMMON_MIN; i <= SC_COMMON_MAX; i++) - if (tsc->data[i]) status_change_end(bl, (sc_type)i, INVALID_TIMER); - for (i = 0; i < ARRAYLENGTH(scs); i++) - if (tsc->data[scs[i]]) status_change_end(bl, scs[i], INVALID_TIMER); + const struct TimerData *timer = iTimer->get_timer(sc->data[SC_NOEQUIPSHIELD]->timer); + if( timer && timer->func == status_change_timer && DIFF_TICK(timer->tick,iTimer->gettick()+skill->get_time(ud->skill_id, ud->skill_lv)) > 0 ) + break; } - } - break; - case SA_DEATH: - if ( sd && dstmd && dstmd->status.mode&MD_BOSS ) - { - clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); + sc_start2(src, SC_NOEQUIPSHIELD, 100, 0, 1, skill->get_time(ud->skill_id, ud->skill_lv)); break; } - clif->skill_nodamage(src,bl,skill_id,skill_lv,1); - status_kill(bl); - break; - case SA_REVERSEORCISH: - clif->skill_nodamage(src,bl,skill_id,skill_lv, - sc_start(bl,type,100,skill_lv,skill->get_time(skill_id, skill_lv))); - break; - case SA_FORTUNE: - clif->skill_nodamage(src,bl,skill_id,skill_lv,1); - if(sd) pc->getzeny(sd,status_get_lv(bl)*100,LOG_TYPE_STEAL,NULL); - break; - case SA_TAMINGMONSTER: - clif->skill_nodamage(src,bl,skill_id,skill_lv,1); - if (sd && dstmd) { - ARR_FIND( 0, MAX_PET_DB, i, dstmd->class_ == pet_db[i].class_ ); - if( i < MAX_PET_DB ) - pet_catch_process1(sd, dstmd->class_); - } - break; - - case CR_PROVIDENCE: - if(sd && dstsd){ //Check they are not another crusader [Skotlex] - if ((dstsd->class_&MAPID_UPPERMASK) == MAPID_CRUSADER) { - clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); - iMap->freeblock_unlock(); - return 1; - } - } - clif->skill_nodamage(src,bl,skill_id,skill_lv, - sc_start(bl,type,100,skill_lv,skill->get_time(skill_id,skill_lv))); - break; - - case CG_MARIONETTE: - { - struct status_change* sc = status_get_sc(src); - - if( sd && dstsd && (dstsd->class_&MAPID_UPPERMASK) == MAPID_BARDDANCER && dstsd->status.sex == sd->status.sex ) - {// Cannot cast on another bard/dancer-type class of the same gender as caster - clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); - iMap->freeblock_unlock(); - return 1; - } + } + if (skill->get_state(ud->skill_id) != ST_MOVE_ENABLE) + unit_set_walkdelay(src, tick, battle_config.default_walk_delay+skill->get_walkdelay(ud->skill_id, ud->skill_lv), 1); - if( sc && tsc ) - { - if( !sc->data[SC_MARIONETTE] && !tsc->data[SC_MARIONETTE2] ) - { - sc_start(src,SC_MARIONETTE,100,bl->id,skill->get_time(skill_id,skill_lv)); - sc_start(bl,SC_MARIONETTE2,100,src->id,skill->get_time(skill_id,skill_lv)); - clif->skill_nodamage(src,bl,skill_id,skill_lv,1); - } - else - if( sc->data[SC_MARIONETTE ] && sc->data[SC_MARIONETTE ]->val1 == bl->id && - tsc->data[SC_MARIONETTE2] && tsc->data[SC_MARIONETTE2]->val1 == src->id ) - { - status_change_end(src, SC_MARIONETTE, INVALID_TIMER); - status_change_end(bl, SC_MARIONETTE2, INVALID_TIMER); - } - else - { - if( sd ) - clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); + if(battle_config.skill_log && battle_config.skill_log&src->type) + ShowInfo("Type %d, ID %d skill castend id [id =%d, lv=%d, target ID %d]\n", + src->type, src->id, ud->skill_id, ud->skill_lv, target->id); - iMap->freeblock_unlock(); - return 1; - } - } - } - break; + iMap->freeblock_lock(); - case RG_CLOSECONFINE: - clif->skill_nodamage(src,bl,skill_id,skill_lv, - sc_start4(bl,type,100,skill_lv,src->id,0,0,skill->get_time(skill_id,skill_lv))); - break; - case SA_FLAMELAUNCHER: // added failure chance and chance to break weapon if turned on [Valaris] - case SA_FROSTWEAPON: - case SA_LIGHTNINGLOADER: - case SA_SEISMICWEAPON: - if (dstsd) { - if(dstsd->status.weapon == W_FIST || - (dstsd->sc.count && !dstsd->sc.data[type] && - ( //Allow re-enchanting to lenghten time. [Skotlex] - dstsd->sc.data[SC_FIREWEAPON] || - dstsd->sc.data[SC_WATERWEAPON] || - dstsd->sc.data[SC_WINDWEAPON] || - dstsd->sc.data[SC_EARTHWEAPON] || - dstsd->sc.data[SC_SHADOWWEAPON] || - dstsd->sc.data[SC_GHOSTWEAPON] || - dstsd->sc.data[SC_ENCPOISON] - )) - ) { - if (sd) clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); - clif->skill_nodamage(src,bl,skill_id,skill_lv,0); - break; - } - } - // 100% success rate at lv4 & 5, but lasts longer at lv5 - if(!clif->skill_nodamage(src,bl,skill_id,skill_lv, sc_start(bl,type,(60+skill_lv*10),skill_lv, skill->get_time(skill_id,skill_lv)))) { - if (sd) - clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); - if (skill->break_equip(bl, EQP_WEAPON, 10000, BCT_PARTY) && sd && sd != dstsd) - clif->message(sd->fd, msg_txt(669)); - } - break; + // SC_MAGICPOWER needs to switch states before any damage is actually dealt + skill->toggle_magicpower(src, ud->skill_id); + if( ud->skill_id != RA_CAMOUFLAGE ) // only normal attack and auto cast skills benefit from its bonuses + status_change_end(src,SC_CAMOUFLAGE, INVALID_TIMER); - case PR_ASPERSIO: - if (sd && dstmd) { - clif->skill_nodamage(src,bl,skill_id,skill_lv,0); - break; - } - clif->skill_nodamage(src,bl,skill_id,skill_lv, - sc_start(bl,type,100,skill_lv,skill->get_time(skill_id,skill_lv))); - break; + if (skill->get_casttype(ud->skill_id) == CAST_NODAMAGE) + skill->castend_nodamage_id(src,target,ud->skill_id,ud->skill_lv,tick,flag); + else + skill->castend_damage_id(src,target,ud->skill_id,ud->skill_lv,tick,flag); - case ITEM_ENCHANTARMS: - clif->skill_nodamage(src,bl,skill_id,skill_lv, - sc_start2(bl,type,100,skill_lv, - skill->get_ele(skill_id,skill_lv), skill->get_time(skill_id,skill_lv))); - break; + sc = status_get_sc(src); + if(sc && sc->count) { + if(sc->data[SC_SOULLINK] && + sc->data[SC_SOULLINK]->val2 == SL_WIZARD && + sc->data[SC_SOULLINK]->val3 == ud->skill_id && + ud->skill_id != WZ_WATERBALL) + sc->data[SC_SOULLINK]->val3 = 0; //Clear bounced spell check. - case TK_SEVENWIND: - switch(skill->get_ele(skill_id,skill_lv)) { - case ELE_EARTH : type = SC_EARTHWEAPON; break; - case ELE_WIND : type = SC_WINDWEAPON; break; - case ELE_WATER : type = SC_WATERWEAPON; break; - case ELE_FIRE : type = SC_FIREWEAPON; break; - case ELE_GHOST : type = SC_GHOSTWEAPON; break; - case ELE_DARK : type = SC_SHADOWWEAPON; break; - case ELE_HOLY : type = SC_ASPERSIO; break; - } - clif->skill_nodamage(src,bl,skill_id,skill_lv, - sc_start(bl,type,100,skill_lv,skill->get_time(skill_id,skill_lv))); + if( sc->data[SC_DANCING] && skill->get_inf2(ud->skill_id)&INF2_SONG_DANCE && sd ) + skill->blockpc_start(sd,BD_ADAPTATION,3000, false); + } - sc_start(bl,SC_SEVENWIND,100,skill_lv,skill->get_time(skill_id,skill_lv)); + if( sd && ud->skill_id != SA_ABRACADABRA && ud->skill_id != WM_RANDOMIZESPELL ) // they just set the data so leave it as it is.[Inkfish] + sd->skillitem = sd->skillitemlv = 0; - break; + if (ud->skilltimer == INVALID_TIMER) { + if(md) md->skill_idx = -1; + else ud->skill_id = 0; //mobs can't clear this one as it is used for skill condition 'afterskill' + ud->skill_lv = ud->skilltarget = 0; + } + iMap->freeblock_unlock(); + return 1; + } while(0); - case PR_KYRIE: - case MER_KYRIE: - clif->skill_nodamage(bl,bl,skill_id,skill_lv, - sc_start(bl,type,100,skill_lv,skill->get_time(skill_id,skill_lv))); - break; - //Passive Magnum, should had been casted on yourself. - case SM_MAGNUM: - case MS_MAGNUM: - skill_area_temp[1] = 0; - iMap->foreachinrange(skill->area_sub, src, skill->get_splash(skill_id, skill_lv), BL_SKILL|BL_CHAR, - src,skill_id,skill_lv,tick, flag|BCT_ENEMY|1, skill->castend_damage_id); - clif->skill_nodamage (src,src,skill_id,skill_lv,1); - // Initiate 10% of your damage becomes fire element. - sc_start4(src,SC_WATK_ELEMENT,100,3,20,0,0,skill->get_time2(skill_id, skill_lv)); - if( sd ) - skill->blockpc_start(sd, skill_id, skill->get_time(skill_id, skill_lv), false); - else if( bl->type == BL_MER ) - skill->blockmerc_start((TBL_MER*)bl, skill_id, skill->get_time(skill_id, skill_lv)); + //Skill failed. + if (ud->skill_id == MO_EXTREMITYFIST && sd && !(sc && sc->data[SC_FOGWALL])) + { //When Asura fails... (except when it fails from Fog of Wall) + //Consume SP/spheres + skill->consume_requirement(sd,ud->skill_id, ud->skill_lv,1); + status_set_sp(src, 0, 0); + sc = &sd->sc; + if (sc->count) + { //End states + status_change_end(src, SC_EXPLOSIONSPIRITS, INVALID_TIMER); + status_change_end(src, SC_BLADESTOP, INVALID_TIMER); +#ifdef RENEWAL + sc_start(src, SC_EXTREMITYFIST2, 100, ud->skill_lv, skill->get_time(ud->skill_id, ud->skill_lv)); +#endif + } + if (target && target->m == src->m) + { //Move character to target anyway. + int dir, x, y; + dir = iMap->calc_dir(src,target->x,target->y); + if( dir > 0 && dir < 4) x = -2; + else if( dir > 4 ) x = 2; + else x = 0; + if( dir > 2 && dir < 6 ) y = -2; + else if( dir == 7 || dir < 2 ) y = 2; + else y = 0; + if (unit_movepos(src, src->x+x, src->y+y, 1, 1)) + { //Display movement + animation. + clif->slide(src,src->x,src->y); + clif->skill_damage(src,target,tick,sd->battle_status.amotion,0,0,1,ud->skill_id, ud->skill_lv, 5); + } + clif->skill_fail(sd,ud->skill_id,USESKILL_FAIL_LEVEL,0); + } + } + + ud->skill_id = ud->skill_lv = ud->skilltarget = 0; + if( !sd || sd->skillitem != ud->skill_id || skill->get_delay(ud->skill_id,ud->skill_lv) ) + ud->canact_tick = tick; + //You can't place a skill failed packet here because it would be + //sent in ALL cases, even cases where skill_check_condition fails + //which would lead to double 'skill failed' messages u.u [Skotlex] + if(sd) + sd->skillitem = sd->skillitemlv = 0; + else if(md) + md->skill_idx = -1; + return 0; +} + +/*========================================== + * + *------------------------------------------*/ +int skill_castend_nodamage_id (struct block_list *src, struct block_list *bl, uint16 skill_id, uint16 skill_lv, unsigned int tick, int flag) +{ + struct map_session_data *sd, *dstsd; + struct mob_data *md, *dstmd; + struct homun_data *hd; + struct mercenary_data *mer; + struct status_data *sstatus, *tstatus; + struct status_change *tsc; + struct status_change_entry *tsce; + + int i = 0; + enum sc_type type; + + if(skill_id > 0 && !skill_lv) return 0; // celest + + nullpo_retr(1, src); + nullpo_retr(1, bl); + + if (src->m != bl->m) + return 1; + + sd = BL_CAST(BL_PC, src); + hd = BL_CAST(BL_HOM, src); + md = BL_CAST(BL_MOB, src); + mer = BL_CAST(BL_MER, src); + + dstsd = BL_CAST(BL_PC, bl); + dstmd = BL_CAST(BL_MOB, bl); + + if(bl->prev == NULL) + return 1; + if(status_isdead(src)) + return 1; + + if( src != bl && status_isdead(bl) ) { + /** + * Skills that may be cast on dead targets + **/ + switch( skill_id ) { + case NPC_WIDESOULDRAIN: + case PR_REDEMPTIO: + case ALL_RESURRECTION: + case WM_DEADHILLHERE: + break; + default: + return 1; + } + } + + tstatus = status_get_status_data(bl); + sstatus = status_get_status_data(src); + + //Check for undead skills that convert a no-damage skill into a damage one. [Skotlex] + switch (skill_id) { + case HLIF_HEAL: //[orn] + if (bl->type != BL_HOM) { + if (sd) clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0) ; + break ; + } + case AL_HEAL: + case ALL_RESURRECTION: + case PR_ASPERSIO: + /** + * Arch Bishop + **/ + case AB_RENOVATIO: + case AB_HIGHNESSHEAL: + //Apparently only player casted skills can be offensive like this. + if (sd && battle->check_undead(tstatus->race,tstatus->def_ele)) { + if (battle->check_target(src, bl, BCT_ENEMY) < 1) { + //Offensive heal does not works on non-enemies. [Skotlex] + clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); + return 0; + } + return skill->castend_damage_id (src, bl, skill_id, skill_lv, tick, flag); + } break; + case NPC_SMOKING: //Since it is a self skill, this one ends here rather than in damage_id. [Skotlex] + return skill->castend_damage_id (src, bl, skill_id, skill_lv, tick, flag); + case MH_STEINWAND: { + struct block_list *s_src = battle->get_master(src); + short ret = 0; + if(!skill->check_unit_range(src, src->x, src->y, skill_id, skill_lv)) //prevent reiteration + ret = skill->castend_pos2(src,src->x,src->y,skill_id,skill_lv,tick,flag); //cast on homon + if(s_src && !skill->check_unit_range(s_src, s_src->x, s_src->y, skill_id, skill_lv)) + ret |= skill->castend_pos2(s_src,s_src->x,s_src->y,skill_id,skill_lv,tick,flag); //cast on master + if (hd) + skill->blockhomun_start(hd, skill_id, skill->get_cooldown(skill_id, skill_lv)); + return ret; + } + break; + case RK_MILLENNIUMSHIELD: + case RK_CRUSHSTRIKE: + case RK_REFRESH: + case RK_GIANTGROWTH: + case RK_STONEHARDSKIN: + case RK_VITALITYACTIVATION: + case RK_STORMBLAST: + case RK_FIGHTINGSPIRIT: + case RK_ABUNDANCE: + if( sd && !pc->checkskill(sd, RK_RUNEMASTERY) ){ + if( status_change_start(&sd->bl, (sc_type)(rnd()%SC_CONFUSION), 1000, 1, 0, 0, 0, skill->get_time2(skill_id,skill_lv),8) ){ + skill->consume_requirement(sd,skill_id,skill_lv,2); + iMap->freeblock_unlock(); + return 0; + } + } + break; + default: + //Skill is actually ground placed. + if (src == bl && skill->get_unit_id(skill_id,0)) + return skill->castend_pos2(src,bl->x,bl->y,skill_id,skill_lv,tick,0); + } - case TK_JUMPKICK: - /* Check if the target is an enemy; if not, skill should fail so the character doesn't unit_movepos (exploitable) */ - if( battle->check_target(src, bl, BCT_ENEMY) > 0 ) + type = status_skill2sc(skill_id); + tsc = status_get_sc(bl); + tsce = (tsc && type != -1)?tsc->data[type]:NULL; + + if (src!=bl && type > -1 && + (i = skill->get_ele(skill_id, skill_lv)) > ELE_NEUTRAL && + skill->get_inf(skill_id) != INF_SUPPORT_SKILL && + battle->attr_fix(NULL, NULL, 100, i, tstatus->def_ele, tstatus->ele_lv) <= 0) + return 1; //Skills that cause an status should be blocked if the target element blocks its element. + + iMap->freeblock_lock(); + switch(skill_id) { + case HLIF_HEAL: //[orn] + case AL_HEAL: + /** + * Arch Bishop + **/ + case AB_HIGHNESSHEAL: { - if( unit_movepos(src, bl->x, bl->y, 1, 1) ) + int heal = skill->calc_heal(src, bl, (skill_id == AB_HIGHNESSHEAL)?AL_HEAL:skill_id, (skill_id == AB_HIGHNESSHEAL)?10:skill_lv, true); + int heal_get_jobexp; + //Highness Heal: starts at 1.5 boost + 0.5 for each level + if( skill_id == AB_HIGHNESSHEAL ) { + heal = heal * ( 15 + 5 * skill_lv ) / 10; + } + if( status_isimmune(bl) || + (dstmd && (dstmd->class_ == MOBID_EMPERIUM || mob_is_battleground(dstmd))) || + (dstsd && pc_ismadogear(dstsd)) )//Mado is immune to heal + heal=0; + + if( sd && dstsd && sd->status.partner_id == dstsd->status.char_id && (sd->class_&MAPID_UPPERMASK) == MAPID_SUPER_NOVICE && sd->status.sex == 0 ) + heal = heal*2; + + if( tsc && tsc->count ) { - skill->attack(BF_WEAPON,src,src,bl,skill_id,skill_lv,tick,flag); - clif->slide(src,bl->x,bl->y); + if( tsc->data[SC_KAITE] && !(sstatus->mode&MD_BOSS) ) + { //Bounce back heal + if (--tsc->data[SC_KAITE]->val2 <= 0) + status_change_end(bl, SC_KAITE, INVALID_TIMER); + if (src == bl) + heal=0; //When you try to heal yourself under Kaite, the heal is voided. + else { + bl = src; + dstsd = sd; + } + } + else if (tsc->data[SC_BERSERK] || tsc->data[SC_SATURDAY_NIGHT_FEVER] || tsc->data[SC__BLOODYLUST]) + heal = 0; //Needed so that it actually displays 0 when healing. + } + clif->skill_nodamage (src, bl, skill_id, heal, 1); + if( tsc && tsc->data[SC_AKAITSUKI] && heal && skill_id != HLIF_HEAL ) + heal = ~heal + 1; + heal_get_jobexp = status_heal(bl,heal,0,0); + + if(sd && dstsd && heal > 0 && sd != dstsd && battle_config.heal_exp > 0){ + heal_get_jobexp = heal_get_jobexp * battle_config.heal_exp / 100; + if (heal_get_jobexp <= 0) + heal_get_jobexp = 1; + pc->gainexp (sd, bl, 0, heal_get_jobexp, false); } } - else - clif->skill_fail(sd,skill_id,USESKILL_FAIL,0); break; - case AL_INCAGI: - case AL_BLESSING: - case MER_INCAGI: - case MER_BLESSING: - if (dstsd != NULL && tsc->data[SC_CHANGEUNDEAD]) { - skill->attack(BF_MISC,src,src,bl,skill_id,skill_lv,tick,flag); + case PR_REDEMPTIO: + if (sd && !(flag&1)) { + if (sd->status.party_id == 0) { + clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); + break; + } + skill_area_temp[0] = 0; + party_foreachsamemap(skill->area_sub, + sd,skill->get_splash(skill_id, skill_lv), + src,skill_id,skill_lv,tick, flag|BCT_PARTY|1, + skill->castend_nodamage_id); + if (skill_area_temp[0] == 0) { + clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); + break; + } + skill_area_temp[0] = 5 - skill_area_temp[0]; // The actual penalty... + if (skill_area_temp[0] > 0 && !map[src->m].flag.noexppenalty) { //Apply penalty + sd->status.base_exp -= min(sd->status.base_exp, pc->nextbaseexp(sd) * skill_area_temp[0] * 2/1000); //0.2% penalty per each. + sd->status.job_exp -= min(sd->status.job_exp, pc->nextjobexp(sd) * skill_area_temp[0] * 2/1000); + clif->updatestatus(sd,SP_BASEEXP); + clif->updatestatus(sd,SP_JOBEXP); + } + status_set_hp(src, 1, 0); + status_set_sp(src, 0, 0); + break; + } else if (status_isdead(bl) && flag&1) { //Revive + skill_area_temp[0]++; //Count it in, then fall-through to the Resurrection code. + skill_lv = 3; //Resurrection level 3 is used + } else //Invalid target, skip resurrection. break; - } - case PR_SLOWPOISON: - case PR_IMPOSITIO: - case PR_LEXAETERNA: - case PR_SUFFRAGIUM: - case PR_BENEDICTIO: - case LK_BERSERK: - case MS_BERSERK: - case KN_AUTOCOUNTER: - case KN_TWOHANDQUICKEN: - case KN_ONEHAND: - case MER_QUICKEN: - case CR_SPEARQUICKEN: - case CR_REFLECTSHIELD: - case MS_REFLECTSHIELD: - case AS_POISONREACT: - case MC_LOUD: - case MG_ENERGYCOAT: - case MO_EXPLOSIONSPIRITS: - case MO_STEELBODY: - case MO_BLADESTOP: - case LK_AURABLADE: - case LK_PARRYING: - case MS_PARRYING: - case LK_CONCENTRATION: - case WS_CARTBOOST: - case SN_SIGHT: - case WS_MELTDOWN: - case WS_OVERTHRUSTMAX: - case ST_REJECTSWORD: - case HW_MAGICPOWER: - case PF_MEMORIZE: - case PA_SACRIFICE: - case ASC_EDP: - case PF_DOUBLECASTING: - case SG_SUN_COMFORT: - case SG_MOON_COMFORT: - case SG_STAR_COMFORT: - case NPC_HALLUCINATION: - case GS_MADNESSCANCEL: - case GS_ADJUSTMENT: - case GS_INCREASING: - case NJ_KASUMIKIRI: - case NJ_UTSUSEMI: - case NJ_NEN: - case NPC_DEFENDER: - case NPC_MAGICMIRROR: - case ST_PRESERVE: - case NPC_INVINCIBLE: - case NPC_INVINCIBLEOFF: - case RK_DEATHBOUND: - case AB_RENOVATIO: - case AB_EXPIATIO: - case AB_DUPLELIGHT: - case AB_SECRAMENT: - case NC_ACCELERATION: - case NC_HOVERING: - case NC_SHAPESHIFT: - case WL_RECOGNIZEDSPELL: - case GC_VENOMIMPRESS: - case SC_DEADLYINFECT: - case LG_EXEEDBREAK: - case LG_PRESTIGE: - case SR_CRESCENTELBOW: - case SR_LIGHTNINGWALK: - case SR_GENTLETOUCH_ENERGYGAIN: - case GN_CARTBOOST: - case KO_MEIKYOUSISUI: - clif->skill_nodamage(src,bl,skill_id,skill_lv, - sc_start(bl,type,100,skill_lv,skill->get_time(skill_id,skill_lv))); - break; - case SO_STRIKING: - if (sd) { - int bonus = 25 + 10 * skill_lv; - bonus += (pc->checkskill(sd, SA_FLAMELAUNCHER)+pc->checkskill(sd, SA_FROSTWEAPON)+pc->checkskill(sd, SA_LIGHTNINGLOADER)+pc->checkskill(sd, SA_SEISMICWEAPON))*5; - clif->skill_nodamage( src, bl, skill_id, skill_lv, - battle->check_target(src,bl,BCT_PARTY) > 0 ? - sc_start2(bl, type, 100, skill_lv, bonus, skill->get_time(skill_id,skill_lv)) : - 0 - ); + case ALL_RESURRECTION: + if(sd && (map_flag_gvg(bl->m) || map[bl->m].flag.battleground)) + { //No reviving in WoE grounds! + clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); + break; } - break; + if (!status_isdead(bl)) + break; + { + int per = 0, sper = 0; + if (tsc && tsc->data[SC_HELLPOWER]) + break; - case NPC_STOP: - if( clif->skill_nodamage(src,bl,skill_id,skill_lv, - sc_start2(bl,type,100,skill_lv,src->id,skill->get_time(skill_id,skill_lv)) ) ) - sc_start2(src,type,100,skill_lv,bl->id,skill->get_time(skill_id,skill_lv)); - break; - case HP_ASSUMPTIO: - if( sd && dstmd ) - clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); - else - clif->skill_nodamage(src,bl,skill_id,skill_lv, - sc_start(bl,type,100,skill_lv,skill->get_time(skill_id,skill_lv))); - break; - case MG_SIGHT: - case MER_SIGHT: - case AL_RUWACH: - case WZ_SIGHTBLASTER: - case NPC_WIDESIGHT: - case NPC_STONESKIN: - case NPC_ANTIMAGIC: - clif->skill_nodamage(src,bl,skill_id,skill_lv, - sc_start2(bl,type,100,skill_lv,skill_id,skill->get_time(skill_id,skill_lv))); - break; - case HLIF_AVOID: - case HAMI_DEFENCE: - i = skill->get_time(skill_id,skill_lv); - clif->skill_nodamage(bl,bl,skill_id,skill_lv,sc_start(bl,type,100,skill_lv,i)); // Master - clif->skill_nodamage(src,src,skill_id,skill_lv,sc_start(src,type,100,skill_lv,i)); // Homunc + if (map[bl->m].flag.pvp && dstsd && dstsd->pvp_point < 0) + break; + + switch(skill_lv){ + case 1: per=10; break; + case 2: per=30; break; + case 3: per=50; break; + case 4: per=80; break; + } + if(dstsd && dstsd->special_state.restart_full_recover) + per = sper = 100; + if (status_revive(bl, per, sper)) + { + clif->skill_nodamage(src,bl,ALL_RESURRECTION,skill_lv,1); //Both Redemptio and Res show this skill-animation. + if(sd && dstsd && battle_config.resurrection_exp > 0) + { + int exp = 0,jexp = 0; + int lv = dstsd->status.base_level - sd->status.base_level, jlv = dstsd->status.job_level - sd->status.job_level; + if(lv > 0 && pc->nextbaseexp(dstsd)) { + exp = (int)((double)dstsd->status.base_exp * (double)lv * (double)battle_config.resurrection_exp / 1000000.); + if (exp < 1) exp = 1; + } + if(jlv > 0 && pc->nextjobexp(dstsd)) { + jexp = (int)((double)dstsd->status.job_exp * (double)lv * (double)battle_config.resurrection_exp / 1000000.); + if (jexp < 1) jexp = 1; + } + if(exp > 0 || jexp > 0) + pc->gainexp (sd, bl, exp, jexp, false); + } + } + } break; - case NJ_BUNSINJYUTSU: - clif->skill_nodamage(src,bl,skill_id,skill_lv, - sc_start(bl,type,100,skill_lv,skill->get_time(skill_id,skill_lv))); - status_change_end(bl, SC_NEN, INVALID_TIMER); + + case AL_DECAGI: + case MER_DECAGI: + clif->skill_nodamage (src, bl, skill_id, skill_lv, + sc_start(bl, type, (40 + skill_lv * 2 + (status_get_lv(src) + sstatus->int_)/5), skill_lv, skill->get_time(skill_id,skill_lv))); break; - /* Was modified to only affect targetted char. [Skotlex] - case HP_ASSUMPTIO: + + case AL_CRUCIS: if (flag&1) - sc_start(bl,type,100,skill_lv,skill->get_time(skill_id,skill_lv)); - else - { - iMap->foreachinrange(skill->area_sub, bl, - skill->get_splash(skill_id, skill_lv), BL_PC, - src, skill_id, skill_lv, tick, flag|BCT_ALL|1, - skill->castend_nodamage_id); - clif->skill_nodamage(src,bl,skill_id,skill_lv,1); + sc_start(bl,type, 23+skill_lv*4 +status_get_lv(src) -status_get_lv(bl), skill_lv,skill->get_time(skill_id,skill_lv)); + else { + iMap->foreachinrange(skill->area_sub, src, skill->get_splash(skill_id, skill_lv), BL_CHAR, + src, skill_id, skill_lv, tick, flag|BCT_ENEMY|1, skill->castend_nodamage_id); + clif->skill_nodamage(src, bl, skill_id, skill_lv, 1); } break; - */ - case SM_ENDURE: - clif->skill_nodamage(src,bl,skill_id,skill_lv, - sc_start(bl,type,100,skill_lv,skill->get_time(skill_id,skill_lv))); - if (sd) - skill->blockpc_start (sd, skill_id, skill->get_time2(skill_id,skill_lv), false); + + case PR_LEXDIVINA: + case MER_LEXDIVINA: + if( tsce ) + status_change_end(bl,type, INVALID_TIMER); + else + sc_start(bl,type,100,skill_lv,skill->get_time(skill_id,skill_lv)); + clif->skill_nodamage (src, bl, skill_id, skill_lv, 1); break; - case AS_ENCHANTPOISON: // Prevent spamming [Valaris] - if (sd && dstsd && dstsd->sc.count) { - if (dstsd->sc.data[SC_FIREWEAPON] || - dstsd->sc.data[SC_WATERWEAPON] || - dstsd->sc.data[SC_WINDWEAPON] || - dstsd->sc.data[SC_EARTHWEAPON] || - dstsd->sc.data[SC_SHADOWWEAPON] || - dstsd->sc.data[SC_GHOSTWEAPON] - // dstsd->sc.data[SC_ENCPOISON] //People say you should be able to recast to lengthen the timer. [Skotlex] - ) { - clif->skill_nodamage(src,bl,skill_id,skill_lv,0); - clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); - break; + case SA_ABRACADABRA: + { + int abra_skill_id = 0, abra_skill_lv; + do { + i = rnd() % MAX_SKILL_ABRA_DB; + abra_skill_id = skill_abra_db[i].skill_id; + } while (abra_skill_id == 0 || + skill_abra_db[i].req_lv > skill_lv || //Required lv for it to appear + rnd()%10000 >= skill_abra_db[i].per + ); + abra_skill_lv = min(skill_lv, skill->get_max(abra_skill_id)); + clif->skill_nodamage (src, bl, skill_id, skill_lv, 1); + + if( sd ) + {// player-casted + sd->state.abra_flag = 1; + sd->skillitem = abra_skill_id; + sd->skillitemlv = abra_skill_lv; + clif->item_skill(sd, abra_skill_id, abra_skill_lv); + } + else + {// mob-casted + struct unit_data *ud = unit_bl2ud(src); + int inf = skill->get_inf(abra_skill_id); + if (!ud) break; + if (inf&INF_SELF_SKILL || inf&INF_SUPPORT_SKILL) { + if (src->type == BL_PET) + bl = (struct block_list*)((TBL_PET*)src)->msd; + if (!bl) bl = src; + unit_skilluse_id(src, bl->id, abra_skill_id, abra_skill_lv); + } else { //Assume offensive skills + int target_id = 0; + if (ud->target) + target_id = ud->target; + else switch (src->type) { + case BL_MOB: target_id = ((TBL_MOB*)src)->target_id; break; + case BL_PET: target_id = ((TBL_PET*)src)->target_id; break; + } + if (!target_id) + break; + if (skill->get_casttype(abra_skill_id) == CAST_GROUND) { + bl = iMap->id2bl(target_id); + if (!bl) bl = src; + unit_skilluse_pos(src, bl->x, bl->y, abra_skill_id, abra_skill_lv); + } else + unit_skilluse_id(src, target_id, abra_skill_id, abra_skill_lv); + } } } - clif->skill_nodamage(src,bl,skill_id,skill_lv, - sc_start(bl,type,100,skill_lv,skill->get_time(skill_id,skill_lv))); break; - case LK_TENSIONRELAX: + case SA_COMA: clif->skill_nodamage(src,bl,skill_id,skill_lv, - sc_start4(bl,type,100,skill_lv,0,0,skill->get_time2(skill_id,skill_lv), - skill->get_time(skill_id,skill_lv))); + sc_start(bl,type,100,skill_lv,skill->get_time2(skill_id,skill_lv))); break; - - case MC_CHANGECART: + case SA_FULLRECOVERY: clif->skill_nodamage(src,bl,skill_id,skill_lv,1); + if (status_isimmune(bl)) + break; + status_percent_heal(bl, 100, 100); break; - - case TK_MISSION: - if (sd) { - int id; - if (sd->mission_mobid && (sd->mission_count || rnd()%100)) { //Cannot change target when already have one - clif->mission_info(sd, sd->mission_mobid, sd->mission_count); - clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); + case NPC_ALLHEAL: + { + int heal; + if( status_isimmune(bl) ) break; + heal = status_percent_heal(bl, 100, 0); + clif->skill_nodamage(NULL, bl, AL_HEAL, heal, 1); + if( dstmd ) + { // Reset Damage Logs + memset(dstmd->dmglog, 0, sizeof(dstmd->dmglog)); + dstmd->tdmg = 0; } - id = mob_get_random_id(0,0xF, sd->status.base_level); - if (!id) { + } + break; + case SA_SUMMONMONSTER: + clif->skill_nodamage(src,bl,skill_id,skill_lv,1); + if (sd) mob_once_spawn(sd, src->m, src->x, src->y," --ja--", -1, 1, "", SZ_SMALL, AI_NONE); + break; + case SA_LEVELUP: + clif->skill_nodamage(src,bl,skill_id,skill_lv,1); + if (sd && pc->nextbaseexp(sd)) pc->gainexp(sd, NULL, pc->nextbaseexp(sd) * 10 / 100, 0, false); + break; + case SA_INSTANTDEATH: + clif->skill_nodamage(src,bl,skill_id,skill_lv,1); + status_set_hp(bl,1,0); + break; + case SA_QUESTION: + case SA_GRAVITY: + clif->skill_nodamage(src,bl,skill_id,skill_lv,1); + break; + case SA_CLASSCHANGE: + case SA_MONOCELL: + if (dstmd) + { + int class_; + if ( sd && dstmd->status.mode&MD_BOSS ) + { clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); break; } - sd->mission_mobid = id; - sd->mission_count = 0; - pc_setglobalreg(sd,"TK_MISSION_ID", id); - clif->mission_info(sd, id, 0); + class_ = skill_id==SA_MONOCELL?1002:mob_get_random_id(4, 1, 0); clif->skill_nodamage(src,bl,skill_id,skill_lv,1); + mob_class_change(dstmd,class_); + if( tsc && dstmd->status.mode&MD_BOSS ) + { + const enum sc_type scs[] = { SC_QUAGMIRE, SC_PROVOKE, SC_ROKISWEIL, SC_GRAVITATION, SC_NJ_SUITON, SC_NOEQUIPWEAPON, SC_NOEQUIPSHIELD, SC_NOEQUIPARMOR, SC_NOEQUIPHELM, SC_BLADESTOP }; + for (i = SC_COMMON_MIN; i <= SC_COMMON_MAX; i++) + if (tsc->data[i]) status_change_end(bl, (sc_type)i, INVALID_TIMER); + for (i = 0; i < ARRAYLENGTH(scs); i++) + if (tsc->data[scs[i]]) status_change_end(bl, scs[i], INVALID_TIMER); + } } break; - - case AC_CONCENTRATION: + case SA_DEATH: + if ( sd && dstmd && dstmd->status.mode&MD_BOSS ) { - clif->skill_nodamage(src,bl,skill_id,skill_lv, - sc_start(bl,type,100,skill_lv,skill->get_time(skill_id,skill_lv))); - iMap->foreachinrange( status_change_timer_sub, src, - skill->get_splash(skill_id, skill_lv), BL_CHAR, - src,NULL,type,tick); + clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); + break; } + clif->skill_nodamage(src,bl,skill_id,skill_lv,1); + status_kill(bl); break; - - case SM_PROVOKE: - case SM_SELFPROVOKE: - case MER_PROVOKE: - if( (tstatus->mode&MD_BOSS) || battle->check_undead(tstatus->race,tstatus->def_ele) ) - { - iMap->freeblock_unlock(); - return 1; - } - //TODO: How much does base level affects? Dummy value of 1% per level difference used. [Skotlex] - clif->skill_nodamage(src,bl,skill_id == SM_SELFPROVOKE ? SM_PROVOKE : skill_id,skill_lv, - (i = sc_start(bl,type, skill_id == SM_SELFPROVOKE ? 100:( 50 + 3*skill_lv + status_get_lv(src) - status_get_lv(bl)), skill_lv, skill->get_time(skill_id,skill_lv)))); - if( !i ) - { - if( sd ) - clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); - iMap->freeblock_unlock(); - return 0; - } - unit_skillcastcancel(bl, 2); - - if( tsc && tsc->count ) - { - status_change_end(bl, SC_FREEZE, INVALID_TIMER); - if( tsc->data[SC_STONE] && tsc->opt1 == OPT1_STONE ) - status_change_end(bl, SC_STONE, INVALID_TIMER); - status_change_end(bl, SC_SLEEP, INVALID_TIMER); - status_change_end(bl, SC_TRICKDEAD, INVALID_TIMER); + case SA_REVERSEORCISH: + clif->skill_nodamage(src,bl,skill_id,skill_lv, + sc_start(bl,type,100,skill_lv,skill->get_time(skill_id, skill_lv))); + break; + case SA_FORTUNE: + clif->skill_nodamage(src,bl,skill_id,skill_lv,1); + if(sd) pc->getzeny(sd,status_get_lv(bl)*100,LOG_TYPE_STEAL,NULL); + break; + case SA_TAMINGMONSTER: + clif->skill_nodamage(src,bl,skill_id,skill_lv,1); + if (sd && dstmd) { + ARR_FIND( 0, MAX_PET_DB, i, dstmd->class_ == pet_db[i].class_ ); + if( i < MAX_PET_DB ) + pet_catch_process1(sd, dstmd->class_); } + break; - if( dstmd ) - { - dstmd->state.provoke_flag = src->id; - mob_target(dstmd, src, skill->get_range2(src,skill_id,skill_lv)); + case CR_PROVIDENCE: + if(sd && dstsd){ //Check they are not another crusader [Skotlex] + if ((dstsd->class_&MAPID_UPPERMASK) == MAPID_CRUSADER) { + clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); + iMap->freeblock_unlock(); + return 1; + } } + clif->skill_nodamage(src,bl,skill_id,skill_lv, + sc_start(bl,type,100,skill_lv,skill->get_time(skill_id,skill_lv))); break; - case ML_DEVOTION: - case CR_DEVOTION: - { - int count, lv; - if( !dstsd || (!sd && !mer) ) - { // Only players can be devoted - if( sd ) - clif->skill_fail(sd, skill_id, USESKILL_FAIL_LEVEL, 0); - break; - } + case CG_MARIONETTE: + { + struct status_change* sc = status_get_sc(src); - if( (lv = status_get_lv(src) - dstsd->status.base_level) < 0 ) - lv = -lv; - if( lv > battle_config.devotion_level_difference || // Level difference requeriments - (dstsd->sc.data[type] && dstsd->sc.data[type]->val1 != src->id) || // Cannot Devote a player devoted from another source - (skill_id == ML_DEVOTION && (!mer || mer != dstsd->md)) || // Mercenary only can devote owner - (dstsd->class_&MAPID_UPPERMASK) == MAPID_CRUSADER || // Crusader Cannot be devoted - (dstsd->sc.data[SC_HELLPOWER])) // Players affected by SC_HELLPOWERR cannot be devoted. - { - if( sd ) - clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); + if( sd && dstsd && (dstsd->class_&MAPID_UPPERMASK) == MAPID_BARDDANCER && dstsd->status.sex == sd->status.sex ) + {// Cannot cast on another bard/dancer-type class of the same gender as caster + clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); iMap->freeblock_unlock(); return 1; } - i = 0; - count = (sd)? min(skill_lv,5) : 1; // Mercenary only can Devote owner - if( sd ) - { // Player Devoting Player - ARR_FIND(0, count, i, sd->devotion[i] == bl->id ); - if( i == count ) + if( sc && tsc ) + { + if( !sc->data[SC_MARIONETTE_MASTER] && !tsc->data[SC_MARIONETTE] ) { - ARR_FIND(0, count, i, sd->devotion[i] == 0 ); - if( i == count ) - { // No free slots, skill Fail - clif->skill_fail(sd, skill_id, USESKILL_FAIL_LEVEL, 0); - iMap->freeblock_unlock(); - return 1; - } + sc_start(src,SC_MARIONETTE_MASTER,100,bl->id,skill->get_time(skill_id,skill_lv)); + sc_start(bl,SC_MARIONETTE,100,src->id,skill->get_time(skill_id,skill_lv)); + clif->skill_nodamage(src,bl,skill_id,skill_lv,1); + } + else + if( sc->data[SC_MARIONETTE_MASTER ] && sc->data[SC_MARIONETTE_MASTER ]->val1 == bl->id && + tsc->data[SC_MARIONETTE] && tsc->data[SC_MARIONETTE]->val1 == src->id ) + { + status_change_end(src, SC_MARIONETTE_MASTER, INVALID_TIMER); + status_change_end(bl, SC_MARIONETTE, INVALID_TIMER); } + else + { + if( sd ) + clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); - sd->devotion[i] = bl->id; + iMap->freeblock_unlock(); + return 1; + } } - else - mer->devotion_flag = 1; // Mercenary Devoting Owner - - clif->skill_nodamage(src, bl, skill_id, skill_lv, - sc_start4(bl, type, 100, src->id, i, skill->get_range2(src,skill_id,skill_lv),0, skill->get_time2(skill_id, skill_lv))); - clif->devotion(src, NULL); - } - break; - - case MO_CALLSPIRITS: - if(sd) { - int limit = skill_lv; - if( sd->sc.data[SC_RAISINGDRAGON] ) - limit += sd->sc.data[SC_RAISINGDRAGON]->val1; - clif->skill_nodamage(src,bl,skill_id,skill_lv,1); - pc->addspiritball(sd,skill->get_time(skill_id,skill_lv),limit); - } - break; - - case CH_SOULCOLLECT: - if(sd) { - int limit = 5; - if( sd->sc.data[SC_RAISINGDRAGON] ) - limit += sd->sc.data[SC_RAISINGDRAGON]->val1; - clif->skill_nodamage(src,bl,skill_id,skill_lv,1); - for (i = 0; i < limit; i++) - pc->addspiritball(sd,skill->get_time(skill_id,skill_lv),limit); } break; - case MO_KITRANSLATION: - if(dstsd && (dstsd->class_&MAPID_BASEMASK)!=MAPID_GUNSLINGER) { - pc->addspiritball(dstsd,skill->get_time(skill_id,skill_lv),5); - } + case RG_CLOSECONFINE: + clif->skill_nodamage(src,bl,skill_id,skill_lv, + sc_start4(bl,type,100,skill_lv,src->id,0,0,skill->get_time(skill_id,skill_lv))); break; - - case TK_TURNKICK: - case MO_BALKYOUNG: //Passive part of the attack. Splash knock-back+stun. [Skotlex] - if (skill_area_temp[1] != bl->id) { - skill->blown(src,bl,skill->get_blewcount(skill_id,skill_lv),-1,0); - skill->additional_effect(src,bl,skill_id,skill_lv,BF_MISC,ATK_DEF,tick); //Use Misc rather than weapon to signal passive pushback + case SA_FLAMELAUNCHER: // added failure chance and chance to break weapon if turned on [Valaris] + case SA_FROSTWEAPON: + case SA_LIGHTNINGLOADER: + case SA_SEISMICWEAPON: + if (dstsd) { + if(dstsd->status.weapon == W_FIST || + (dstsd->sc.count && !dstsd->sc.data[type] && + ( //Allow re-enchanting to lenghten time. [Skotlex] + dstsd->sc.data[SC_PROPERTYFIRE] || + dstsd->sc.data[SC_PROPERTYWATER] || + dstsd->sc.data[SC_PROPERTYWIND] || + dstsd->sc.data[SC_PROPERTYGROUND] || + dstsd->sc.data[SC_PROPERTYDARK] || + dstsd->sc.data[SC_PROPERTYTELEKINESIS] || + dstsd->sc.data[SC_ENCHANTPOISON] + )) + ) { + if (sd) clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); + clif->skill_nodamage(src,bl,skill_id,skill_lv,0); + break; + } } - break; - - case MO_ABSORBSPIRITS: - i = 0; - if (dstsd && dstsd->spiritball && (sd == dstsd || map_flag_vs(src->m)) && (dstsd->class_&MAPID_BASEMASK)!=MAPID_GUNSLINGER) - { // split the if for readability, and included gunslingers in the check so that their coins cannot be removed [Reddozen] - i = dstsd->spiritball * 7; - pc->delspiritball(dstsd,dstsd->spiritball,0); - } else if (dstmd && !(tstatus->mode&MD_BOSS) && rnd() % 100 < 20) - { // check if target is a monster and not a Boss, for the 20% chance to absorb 2 SP per monster's level [Reddozen] - i = 2 * dstmd->level; - mob_target(dstmd,src,0); + // 100% success rate at lv4 & 5, but lasts longer at lv5 + if(!clif->skill_nodamage(src,bl,skill_id,skill_lv, sc_start(bl,type,(60+skill_lv*10),skill_lv, skill->get_time(skill_id,skill_lv)))) { + if (sd) + clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); + if (skill->break_equip(bl, EQP_WEAPON, 10000, BCT_PARTY) && sd && sd != dstsd) + clif->message(sd->fd, msg_txt(669)); } - if (i) status_heal(src, 0, i, 3); - clif->skill_nodamage(src,bl,skill_id,skill_lv,i?1:0); break; - case AC_MAKINGARROW: - if(sd) { - clif->arrow_create_list(sd); - clif->skill_nodamage(src,bl,skill_id,skill_lv,1); + case PR_ASPERSIO: + if (sd && dstmd) { + clif->skill_nodamage(src,bl,skill_id,skill_lv,0); + break; } + clif->skill_nodamage(src,bl,skill_id,skill_lv, + sc_start(bl,type,100,skill_lv,skill->get_time(skill_id,skill_lv))); break; - case AM_PHARMACY: - if(sd) { - clif->skill_produce_mix_list(sd,skill_id,22); - clif->skill_nodamage(src,bl,skill_id,skill_lv,1); - } + case ITEM_ENCHANTARMS: + clif->skill_nodamage(src,bl,skill_id,skill_lv, + sc_start2(bl,type,100,skill_lv, + skill->get_ele(skill_id,skill_lv), skill->get_time(skill_id,skill_lv))); break; - case SA_CREATECON: - if(sd) { - clif->elementalconverter_list(sd); - clif->skill_nodamage(src,bl,skill_id,skill_lv,1); + case TK_SEVENWIND: + switch(skill->get_ele(skill_id,skill_lv)) { + case ELE_EARTH : type = SC_PROPERTYGROUND; break; + case ELE_WIND : type = SC_PROPERTYWIND; break; + case ELE_WATER : type = SC_PROPERTYWATER; break; + case ELE_FIRE : type = SC_PROPERTYFIRE; break; + case ELE_GHOST : type = SC_PROPERTYTELEKINESIS; break; + case ELE_DARK : type = SC_PROPERTYDARK; break; + case ELE_HOLY : type = SC_ASPERSIO; break; } - break; - - case BS_HAMMERFALL: clif->skill_nodamage(src,bl,skill_id,skill_lv, - sc_start(bl,SC_STUN,(20 + 10 * skill_lv),skill_lv,skill->get_time2(skill_id,skill_lv))); - break; - case RG_RAID: - skill_area_temp[1] = 0; - clif->skill_nodamage(src,bl,skill_id,skill_lv,1); - iMap->foreachinrange(skill->area_sub, bl, - skill->get_splash(skill_id, skill_lv), splash_target(src), - src,skill_id,skill_lv,tick, flag|BCT_ENEMY|1, - skill->castend_damage_id); - status_change_end(src, SC_HIDING, INVALID_TIMER); - break; - - case ASC_METEORASSAULT: - case GS_SPREADATTACK: - case RK_STORMBLAST: - case NC_AXETORNADO: - case GC_COUNTERSLASH: - case SR_SKYNETBLOW: - case SR_RAMPAGEBLASTER: - case SR_HOWLINGOFLION: - case KO_HAPPOKUNAI: - skill_area_temp[1] = 0; - clif->skill_nodamage(src,bl,skill_id,skill_lv,1); - i = iMap->foreachinrange(skill->area_sub, bl, skill->get_splash(skill_id, skill_lv), splash_target(src), - src, skill_id, skill_lv, tick, flag|BCT_ENEMY|SD_SPLASH|1, skill->castend_damage_id); - if( !i && ( skill_id == NC_AXETORNADO || skill_id == SR_SKYNETBLOW || skill_id == KO_HAPPOKUNAI ) ) - clif->skill_damage(src,src,tick, status_get_amotion(src), 0, -30000, 1, skill_id, skill_lv, 6); - break; + sc_start(bl,type,100,skill_lv,skill->get_time(skill_id,skill_lv))); - case NC_EMERGENCYCOOL: - clif->skill_nodamage(src,bl,skill_id,skill_lv,1); - status_change_end(src,SC_OVERHEAT_LIMITPOINT,INVALID_TIMER); - status_change_end(src,SC_OVERHEAT,INVALID_TIMER); - break; - case SR_WINDMILL: - case GN_CART_TORNADO: - clif->skill_nodamage(src,bl,skill_id,skill_lv,1); - case SR_EARTHSHAKER: - case NC_INFRAREDSCAN: - case NPC_EARTHQUAKE: - case NPC_VAMPIRE_GIFT: - case NPC_HELLJUDGEMENT: - case NPC_PULSESTRIKE: - case LG_MOONSLASHER: - skill->castend_damage_id(src, src, skill_id, skill_lv, tick, flag); - break; + sc_start2(bl,SC_TK_SEVENWIND,100,skill_lv,skill->get_ele(skill_id,skill_lv),skill->get_time(skill_id,skill_lv)); - case KN_BRANDISHSPEAR: - case ML_BRANDISH: - skill->brandishspear(src, bl, skill_id, skill_lv, tick, flag); break; - case WZ_SIGHTRASHER: - //Passive side of the attack. - status_change_end(src, SC_SIGHT, INVALID_TIMER); - clif->skill_nodamage(src,bl,skill_id,skill_lv,1); - iMap->foreachinrange(skill->area_sub,src, - skill->get_splash(skill_id, skill_lv),BL_CHAR|BL_SKILL, - src,skill_id,skill_lv,tick, flag|BCT_ENEMY|1, - skill->castend_damage_id); + case PR_KYRIE: + case MER_KYRIE: + clif->skill_nodamage(bl,bl,skill_id,skill_lv, + sc_start(bl,type,100,skill_lv,skill->get_time(skill_id,skill_lv))); break; - - case NJ_HYOUSYOURAKU: - case NJ_RAIGEKISAI: - case WZ_FROSTNOVA: - clif->skill_nodamage(src,bl,skill_id,skill_lv,1); + //Passive Magnum, should had been casted on yourself. + case SM_MAGNUM: + case MS_MAGNUM: skill_area_temp[1] = 0; - iMap->foreachinrange(skill->attack_area, src, - skill->get_splash(skill_id, skill_lv), splash_target(src), - BF_MAGIC, src, src, skill_id, skill_lv, tick, flag, BCT_ENEMY); - break; - - case HVAN_EXPLOSION: //[orn] - case NPC_SELFDESTRUCTION: - //Self Destruction hits everyone in range (allies+enemies) - //Except for Summoned Marine spheres on non-versus maps, where it's just enemy. - i = ((!md || md->special_state.ai == 2) && !map_flag_vs(src->m))? - BCT_ENEMY:BCT_ALL; - clif->skill_nodamage(src, src, skill_id, -1, 1); - iMap->delblock(src); //Required to prevent chain-self-destructions hitting back. - iMap->foreachinrange(skill->area_sub, bl, - skill->get_splash(skill_id, skill_lv), splash_target(src), - src, skill_id, skill_lv, tick, flag|i, - skill->castend_damage_id); - iMap->addblock(src); - status_damage(src, src, sstatus->max_hp,0,0,1); - break; - - case AL_ANGELUS: - case PR_MAGNIFICAT: - case PR_GLORIA: - case SN_WINDWALK: - case CASH_BLESSING: - case CASH_INCAGI: - case CASH_ASSUMPTIO: - if( sd == NULL || sd->status.party_id == 0 || (flag & 1) ) - clif->skill_nodamage(bl, bl, skill_id, skill_lv, sc_start(bl,type,100,skill_lv,skill->get_time(skill_id,skill_lv))); - else if( sd ) - party_foreachsamemap(skill->area_sub, sd, skill->get_splash(skill_id, skill_lv), src, skill_id, skill_lv, tick, flag|BCT_PARTY|1, skill->castend_nodamage_id); + iMap->foreachinrange(skill->area_sub, src, skill->get_splash(skill_id, skill_lv), BL_SKILL|BL_CHAR, + src,skill_id,skill_lv,tick, flag|BCT_ENEMY|1, skill->castend_damage_id); + clif->skill_nodamage (src,src,skill_id,skill_lv,1); + // Initiate 10% of your damage becomes fire element. + sc_start4(src,SC_WATK_ELEMENT,100,3,20,0,0,skill->get_time2(skill_id, skill_lv)); + if( sd ) + skill->blockpc_start(sd, skill_id, skill->get_time(skill_id, skill_lv), false); + else if( bl->type == BL_MER ) + skill->blockmerc_start((TBL_MER*)bl, skill_id, skill->get_time(skill_id, skill_lv)); break; - case MER_MAGNIFICAT: - if( mer != NULL ) + + case TK_JUMPKICK: + /* Check if the target is an enemy; if not, skill should fail so the character doesn't unit_movepos (exploitable) */ + if( battle->check_target(src, bl, BCT_ENEMY) > 0 ) { - clif->skill_nodamage(bl, bl, skill_id, skill_lv, sc_start(bl,type,100,skill_lv,skill->get_time(skill_id,skill_lv))); - if( mer->master && mer->master->status.party_id != 0 && !(flag&1) ) - party_foreachsamemap(skill->area_sub, mer->master, skill->get_splash(skill_id, skill_lv), src, skill_id, skill_lv, tick, flag|BCT_PARTY|1, skill->castend_nodamage_id); - else if( mer->master && !(flag&1) ) - clif->skill_nodamage(src, &mer->master->bl, skill_id, skill_lv, sc_start(bl,type,100,skill_lv,skill->get_time(skill_id,skill_lv))); + if( unit_movepos(src, bl->x, bl->y, 1, 1) ) + { + skill->attack(BF_WEAPON,src,src,bl,skill_id,skill_lv,tick,flag); + clif->slide(src,bl->x,bl->y); + } } + else + clif->skill_fail(sd,skill_id,USESKILL_FAIL,0); break; - case BS_ADRENALINE: - case BS_ADRENALINE2: - case BS_WEAPONPERFECT: - case BS_OVERTHRUST: - if (sd == NULL || sd->status.party_id == 0 || (flag & 1)) { - clif->skill_nodamage(bl,bl,skill_id,skill_lv, - sc_start2(bl,type,100,skill_lv,(src == bl)? 1:0,skill->get_time(skill_id,skill_lv))); - } else if (sd) { - party_foreachsamemap(skill->area_sub, - sd,skill->get_splash(skill_id, skill_lv), - src,skill_id,skill_lv,tick, flag|BCT_PARTY|1, - skill->castend_nodamage_id); + case AL_INCAGI: + case AL_BLESSING: + case MER_INCAGI: + case MER_BLESSING: + if (dstsd != NULL && tsc->data[SC_PROPERTYUNDEAD]) { + skill->attack(BF_MISC,src,src,bl,skill_id,skill_lv,tick,flag); + break; } + case PR_SLOWPOISON: + case PR_IMPOSITIO: + case PR_LEXAETERNA: + case PR_SUFFRAGIUM: + case PR_BENEDICTIO: + case LK_BERSERK: + case MS_BERSERK: + case KN_AUTOCOUNTER: + case KN_TWOHANDQUICKEN: + case KN_ONEHAND: + case MER_QUICKEN: + case CR_SPEARQUICKEN: + case CR_REFLECTSHIELD: + case MS_REFLECTSHIELD: + case AS_POISONREACT: + case MC_LOUD: + case MG_ENERGYCOAT: + case MO_EXPLOSIONSPIRITS: + case MO_STEELBODY: + case MO_BLADESTOP: + case LK_AURABLADE: + case LK_PARRYING: + case MS_PARRYING: + case LK_CONCENTRATION: + case WS_CARTBOOST: + case SN_SIGHT: + case WS_MELTDOWN: + case WS_OVERTHRUSTMAX: + case ST_REJECTSWORD: + case HW_MAGICPOWER: + case PF_MEMORIZE: + case PA_SACRIFICE: + case ASC_EDP: + case PF_DOUBLECASTING: + case SG_SUN_COMFORT: + case SG_MOON_COMFORT: + case SG_STAR_COMFORT: + case NPC_HALLUCINATION: + case GS_MADNESSCANCEL: + case GS_ADJUSTMENT: + case GS_INCREASING: + case NJ_KASUMIKIRI: + case NJ_UTSUSEMI: + case NJ_NEN: + case NPC_DEFENDER: + case NPC_MAGICMIRROR: + case ST_PRESERVE: + case NPC_INVINCIBLE: + case NPC_INVINCIBLEOFF: + case RK_DEATHBOUND: + case AB_RENOVATIO: + case AB_EXPIATIO: + case AB_DUPLELIGHT: + case AB_SECRAMENT: + case NC_ACCELERATION: + case NC_HOVERING: + case NC_SHAPESHIFT: + case WL_RECOGNIZEDSPELL: + case GC_VENOMIMPRESS: + case SC_DEADLYINFECT: + case LG_EXEEDBREAK: + case LG_PRESTIGE: + case SR_CRESCENTELBOW: + case SR_LIGHTNINGWALK: + case SR_GENTLETOUCH_ENERGYGAIN: + case GN_CARTBOOST: + case KO_MEIKYOUSISUI: + case ALL_FULL_THROTTLE: + case RA_UNLIMIT: + case WL_TELEKINESIS_INTENSE: + case AB_OFFERTORIUM: + case RK_GIANTGROWTH: + case RK_VITALITYACTIVATION: + case RK_ABUNDANCE: + case RK_CRUSHSTRIKE: + clif->skill_nodamage(src,bl,skill_id,skill_lv, + sc_start(bl,type,100,skill_lv,skill->get_time(skill_id,skill_lv))); break; - case BS_MAXIMIZE: - case NV_TRICKDEAD: - case CR_DEFENDER: - case ML_DEFENDER: - case CR_AUTOGUARD: - case ML_AUTOGUARD: - case TK_READYSTORM: - case TK_READYDOWN: - case TK_READYTURN: - case TK_READYCOUNTER: - case TK_DODGE: - case CR_SHRINK: - case SG_FUSION: - case GS_GATLINGFEVER: - if( tsce ) - { - clif->skill_nodamage(src,bl,skill_id,skill_lv,status_change_end(bl, type, INVALID_TIMER)); - iMap->freeblock_unlock(); - return 0; - } - clif->skill_nodamage(src,bl,skill_id,skill_lv,sc_start(bl,type,100,skill_lv,skill->get_time(skill_id,skill_lv))); - break; - case SL_KAITE: - case SL_KAAHI: - case SL_KAIZEL: - case SL_KAUPE: + case SO_STRIKING: if (sd) { - if (!dstsd || !( - (sd->sc.data[SC_SPIRIT] && sd->sc.data[SC_SPIRIT]->val2 == SL_SOULLINKER) || - (dstsd->class_&MAPID_UPPERMASK) == MAPID_SOUL_LINKER || - dstsd->status.char_id == sd->status.char_id || - dstsd->status.char_id == sd->status.partner_id || - dstsd->status.char_id == sd->status.child - )) { - status_change_start(src,SC_STUN,10000,skill_lv,0,0,0,500,8); - clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); - break; - } + int bonus = 25 + 10 * skill_lv; + bonus += (pc->checkskill(sd, SA_FLAMELAUNCHER)+pc->checkskill(sd, SA_FROSTWEAPON)+pc->checkskill(sd, SA_LIGHTNINGLOADER)+pc->checkskill(sd, SA_SEISMICWEAPON))*5; + clif->skill_nodamage( src, bl, skill_id, skill_lv, + battle->check_target(src,bl,BCT_PARTY) > 0 ? + sc_start2(bl, type, 100, skill_lv, bonus, skill->get_time(skill_id,skill_lv)) : + 0 + ); } - clif->skill_nodamage(src,bl,skill_id,skill_lv, - sc_start(bl,type,100,skill_lv,skill->get_time(skill_id, skill_lv))); break; - case SM_AUTOBERSERK: - case MER_AUTOBERSERK: - if( tsce ) - i = status_change_end(bl, type, INVALID_TIMER); + + case NPC_STOP: + if( clif->skill_nodamage(src,bl,skill_id,skill_lv, + sc_start2(bl,type,100,skill_lv,src->id,skill->get_time(skill_id,skill_lv)) ) ) + sc_start2(src,type,100,skill_lv,bl->id,skill->get_time(skill_id,skill_lv)); + break; + case HP_ASSUMPTIO: + if( sd && dstmd ) + clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); else - i = sc_start(bl,type,100,skill_lv,60000); - clif->skill_nodamage(src,bl,skill_id,skill_lv,i); + clif->skill_nodamage(src,bl,skill_id,skill_lv, + sc_start(bl,type,100,skill_lv,skill->get_time(skill_id,skill_lv))); break; - case TF_HIDING: - case ST_CHASEWALK: - case KO_YAMIKUMO: - if (tsce) - { - clif->skill_nodamage(src,bl,skill_id,-1,status_change_end(bl, type, INVALID_TIMER)); //Hide skill-scream animation. - iMap->freeblock_unlock(); - return 0; - } else if( tsc && tsc->option&OPTION_MADOGEAR ) { - //Mado Gear cannot hide - if( sd ) clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); - iMap->freeblock_unlock(); - return 0; - } - clif->skill_nodamage(src,bl,skill_id,-1,sc_start(bl,type,100,skill_lv,skill->get_time(skill_id,skill_lv))); + case MG_SIGHT: + case MER_SIGHT: + case AL_RUWACH: + case WZ_SIGHTBLASTER: + case NPC_WIDESIGHT: + case NPC_STONESKIN: + case NPC_ANTIMAGIC: + clif->skill_nodamage(src,bl,skill_id,skill_lv, + sc_start2(bl,type,100,skill_lv,skill_id,skill->get_time(skill_id,skill_lv))); break; - case TK_RUN: - if (tsce) + case HLIF_AVOID: + case HAMI_DEFENCE: + i = skill->get_time(skill_id,skill_lv); + clif->skill_nodamage(bl,bl,skill_id,skill_lv,sc_start(bl,type,100,skill_lv,i)); // Master + clif->skill_nodamage(src,src,skill_id,skill_lv,sc_start(src,type,100,skill_lv,i)); // Homunc + break; + case NJ_BUNSINJYUTSU: + clif->skill_nodamage(src,bl,skill_id,skill_lv, + sc_start(bl,type,100,skill_lv,skill->get_time(skill_id,skill_lv))); + status_change_end(bl, SC_NJ_NEN, INVALID_TIMER); + break; + /* Was modified to only affect targetted char. [Skotlex] + case HP_ASSUMPTIO: + if (flag&1) + sc_start(bl,type,100,skill_lv,skill->get_time(skill_id,skill_lv)); + else { - clif->skill_nodamage(src,bl,skill_id,skill_lv,status_change_end(bl, type, INVALID_TIMER)); - iMap->freeblock_unlock(); - return 0; + iMap->foreachinrange(skill->area_sub, bl, + skill->get_splash(skill_id, skill_lv), BL_PC, + src, skill_id, skill_lv, tick, flag|BCT_ALL|1, + skill->castend_nodamage_id); + clif->skill_nodamage(src,bl,skill_id,skill_lv,1); } - clif->skill_nodamage(src,bl,skill_id,skill_lv,sc_start4(bl,type,100,skill_lv,unit_getdir(bl),0,0,0)); - if (sd) // If the client receives a skill-use packet inmediately before a walkok packet, it will discard the walk packet! [Skotlex] - clif->walkok(sd); // So aegis has to resend the walk ok. break; - case AS_CLOAKING: - case GC_CLOAKINGEXCEED: - case LG_FORCEOFVANGUARD: - case SC_REPRODUCE: - case SC_INVISIBILITY: - if (tsce) { - i = status_change_end(bl, type, INVALID_TIMER); - if( i ) - clif->skill_nodamage(src,bl,skill_id,( skill_id == LG_FORCEOFVANGUARD ) ? skill_lv : -1,i); - else if( sd ) - clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); - iMap->freeblock_unlock(); - return 0; - } - case RA_CAMOUFLAGE: - i = sc_start(bl,type,100,skill_lv,skill->get_time(skill_id,skill_lv)); - if( i ) - clif->skill_nodamage(src,bl,skill_id,( skill_id == LG_FORCEOFVANGUARD ) ? skill_lv : -1,i); - else if( sd ) - clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); + */ + case SM_ENDURE: + clif->skill_nodamage(src,bl,skill_id,skill_lv, + sc_start(bl,type,100,skill_lv,skill->get_time(skill_id,skill_lv))); + if (sd) + skill->blockpc_start (sd, skill_id, skill->get_time2(skill_id,skill_lv), false); + break; + + case AS_ENCHANTPOISON: // Prevent spamming [Valaris] + if (sd && dstsd && dstsd->sc.count) { + if (dstsd->sc.data[SC_PROPERTYFIRE] || + dstsd->sc.data[SC_PROPERTYWATER] || + dstsd->sc.data[SC_PROPERTYWIND] || + dstsd->sc.data[SC_PROPERTYGROUND] || + dstsd->sc.data[SC_PROPERTYDARK] || + dstsd->sc.data[SC_PROPERTYTELEKINESIS] + // dstsd->sc.data[SC_ENCHANTPOISON] //People say you should be able to recast to lengthen the timer. [Skotlex] + ) { + clif->skill_nodamage(src,bl,skill_id,skill_lv,0); + clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); + break; + } + } + clif->skill_nodamage(src,bl,skill_id,skill_lv, + sc_start(bl,type,100,skill_lv,skill->get_time(skill_id,skill_lv))); break; - case BD_ADAPTATION: - if(tsc && tsc->data[SC_DANCING]){ - clif->skill_nodamage(src,bl,skill_id,skill_lv,1); - status_change_end(bl, SC_DANCING, INVALID_TIMER); - } + case LK_TENSIONRELAX: + clif->skill_nodamage(src,bl,skill_id,skill_lv, + sc_start4(bl,type,100,skill_lv,0,0,skill->get_time2(skill_id,skill_lv), + skill->get_time(skill_id,skill_lv))); break; - case BA_FROSTJOKER: - case DC_SCREAM: + case MC_CHANGECART: clif->skill_nodamage(src,bl,skill_id,skill_lv,1); - skill->addtimerskill(src,tick+2000,bl->id,src->x,src->y,skill_id,skill_lv,0,flag); - - if (md) { - // custom hack to make the mob display the skill, because these skills don't show the skill use text themselves - //NOTE: mobs don't have the sprite animation that is used when performing this skill (will cause glitches) - char temp[70]; - snprintf(temp, sizeof(temp), "%s : %s !!",md->name,skill_db[skill_id].desc); - clif->disp_overhead(&md->bl,temp); - } break; - case BA_PANGVOICE: - clif->skill_nodamage(src,bl,skill_id,skill_lv, sc_start(bl,SC_CONFUSION,50,7,skill->get_time(skill_id,skill_lv))); + case TK_MISSION: + if (sd) { + int id; + if (sd->mission_mobid && (sd->mission_count || rnd()%100)) { //Cannot change target when already have one + clif->mission_info(sd, sd->mission_mobid, sd->mission_count); + clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); + break; + } + id = mob_get_random_id(0,0xF, sd->status.base_level); + if (!id) { + clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); + break; + } + sd->mission_mobid = id; + sd->mission_count = 0; + pc_setglobalreg(sd,"TK_MISSION_ID", id); + clif->mission_info(sd, id, 0); + clif->skill_nodamage(src,bl,skill_id,skill_lv,1); + } break; - case DC_WINKCHARM: - if( dstsd ) - clif->skill_nodamage(src,bl,skill_id,skill_lv, sc_start(bl,SC_CONFUSION,30,7,skill->get_time2(skill_id,skill_lv))); - else - if( dstmd ) + case AC_CONCENTRATION: { - if( status_get_lv(src) > status_get_lv(bl) - && (tstatus->race == RC_DEMON || tstatus->race == RC_DEMIHUMAN || tstatus->race == RC_ANGEL) - && !(tstatus->mode&MD_BOSS) ) - clif->skill_nodamage(src,bl,skill_id,skill_lv, sc_start2(bl,type,70,skill_lv,src->id,skill->get_time(skill_id,skill_lv))); - else - { - clif->skill_nodamage(src,bl,skill_id,skill_lv,0); - if(sd) clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); - } + clif->skill_nodamage(src,bl,skill_id,skill_lv, + sc_start(bl,type,100,skill_lv,skill->get_time(skill_id,skill_lv))); + iMap->foreachinrange( status_change_timer_sub, src, + skill->get_splash(skill_id, skill_lv), BL_CHAR, + src,NULL,type,tick); } break; - case TF_STEAL: - if(sd) { - if(pc->steal_item(sd,bl,skill_lv)) - clif->skill_nodamage(src,bl,skill_id,skill_lv,1); - else - clif->skill_fail(sd,skill_id,USESKILL_FAIL,0); + case SM_PROVOKE: + case SM_SELFPROVOKE: + case MER_PROVOKE: + if( (tstatus->mode&MD_BOSS) || battle->check_undead(tstatus->race,tstatus->def_ele) ) + { + iMap->freeblock_unlock(); + return 1; } - break; + //TODO: How much does base level affects? Dummy value of 1% per level difference used. [Skotlex] + clif->skill_nodamage(src,bl,skill_id == SM_SELFPROVOKE ? SM_PROVOKE : skill_id,skill_lv, + (i = sc_start(bl,type, skill_id == SM_SELFPROVOKE ? 100:( 50 + 3*skill_lv + status_get_lv(src) - status_get_lv(bl)), skill_lv, skill->get_time(skill_id,skill_lv)))); + if( !i ) + { + if( sd ) + clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); + iMap->freeblock_unlock(); + return 0; + } + unit_skillcastcancel(bl, 2); - case RG_STEALCOIN: - if(sd) { - if(pc->steal_coin(sd,bl)) - { - dstmd->state.provoke_flag = src->id; - mob_target(dstmd, src, skill->get_range2(src,skill_id,skill_lv)); - clif->skill_nodamage(src,bl,skill_id,skill_lv,1); + if( tsc && tsc->count ) + { + status_change_end(bl, SC_FREEZE, INVALID_TIMER); + if( tsc->data[SC_STONE] && tsc->opt1 == OPT1_STONE ) + status_change_end(bl, SC_STONE, INVALID_TIMER); + status_change_end(bl, SC_SLEEP, INVALID_TIMER); + status_change_end(bl, SC_TRICKDEAD, INVALID_TIMER); + } - } - else - clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); + if( dstmd ) + { + dstmd->state.provoke_flag = src->id; + mob_target(dstmd, src, skill->get_range2(src,skill_id,skill_lv)); } break; - case MG_STONECURSE: + case ML_DEVOTION: + case CR_DEVOTION: { - int brate = 0; - if (tstatus->mode&MD_BOSS) { - if (sd) clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); + int count, lv; + if( !dstsd || (!sd && !mer) ) + { // Only players can be devoted + if( sd ) + clif->skill_fail(sd, skill_id, USESKILL_FAIL_LEVEL, 0); break; } - if(status_isimmune(bl) || !tsc) - break; - if (sd && sd->sc.data[SC_PETROLOGY_OPTION]) - brate = sd->sc.data[SC_PETROLOGY_OPTION]->val3; - - if (tsc->data[SC_STONE]) { - status_change_end(bl, SC_STONE, INVALID_TIMER); - if (sd) clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); - break; + if( (lv = status_get_lv(src) - dstsd->status.base_level) < 0 ) + lv = -lv; + if( lv > battle_config.devotion_level_difference || // Level difference requeriments + (dstsd->sc.data[type] && dstsd->sc.data[type]->val1 != src->id) || // Cannot Devote a player devoted from another source + (skill_id == ML_DEVOTION && (!mer || mer != dstsd->md)) || // Mercenary only can devote owner + (dstsd->class_&MAPID_UPPERMASK) == MAPID_CRUSADER || // Crusader Cannot be devoted + (dstsd->sc.data[SC_HELLPOWER])) // Players affected by SC_HELLPOWERR cannot be devoted. + { + if( sd ) + clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); + iMap->freeblock_unlock(); + return 1; } - if (sc_start4(bl,SC_STONE,(skill_lv*4+20)+brate, - skill_lv, 0, 0, skill->get_time(skill_id, skill_lv), - skill->get_time2(skill_id,skill_lv))) - clif->skill_nodamage(src,bl,skill_id,skill_lv,1); - else if(sd) { - clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); - // Level 6-10 doesn't consume a red gem if it fails [celest] - if (skill_lv > 5) - { // not to consume items - iMap->freeblock_unlock(); - return 0; + + i = 0; + count = (sd)? min(skill_lv,5) : 1; // Mercenary only can Devote owner + if( sd ) + { // Player Devoting Player + ARR_FIND(0, count, i, sd->devotion[i] == bl->id ); + if( i == count ) + { + ARR_FIND(0, count, i, sd->devotion[i] == 0 ); + if( i == count ) + { // No free slots, skill Fail + clif->skill_fail(sd, skill_id, USESKILL_FAIL_LEVEL, 0); + iMap->freeblock_unlock(); + return 1; + } } + + sd->devotion[i] = bl->id; } + else + mer->devotion_flag = 1; // Mercenary Devoting Owner + + clif->skill_nodamage(src, bl, skill_id, skill_lv, + sc_start4(bl, type, 100, src->id, i, skill->get_range2(src,skill_id,skill_lv),0, skill->get_time2(skill_id, skill_lv))); + clif->devotion(src, NULL); } break; - case NV_FIRSTAID: - clif->skill_nodamage(src,bl,skill_id,5,1); - status_heal(bl,5,0,0); + case MO_CALLSPIRITS: + if(sd) { + int limit = skill_lv; + if( sd->sc.data[SC_RAISINGDRAGON] ) + limit += sd->sc.data[SC_RAISINGDRAGON]->val1; + clif->skill_nodamage(src,bl,skill_id,skill_lv,1); + pc->addspiritball(sd,skill->get_time(skill_id,skill_lv),limit); + } break; - case AL_CURE: - if(status_isimmune(bl)) { - clif->skill_nodamage(src,bl,skill_id,skill_lv,0); - break; + case CH_SOULCOLLECT: + if(sd) { + int limit = 5; + if( sd->sc.data[SC_RAISINGDRAGON] ) + limit += sd->sc.data[SC_RAISINGDRAGON]->val1; + clif->skill_nodamage(src,bl,skill_id,skill_lv,1); + for (i = 0; i < limit; i++) + pc->addspiritball(sd,skill->get_time(skill_id,skill_lv),limit); } - status_change_end(bl, SC_SILENCE, INVALID_TIMER); - status_change_end(bl, SC_BLIND, INVALID_TIMER); - status_change_end(bl, SC_CONFUSION, INVALID_TIMER); - clif->skill_nodamage(src,bl,skill_id,skill_lv,1); break; - case TF_DETOXIFY: - clif->skill_nodamage(src,bl,skill_id,skill_lv,1); - status_change_end(bl, SC_POISON, INVALID_TIMER); - status_change_end(bl, SC_DPOISON, INVALID_TIMER); + case MO_KITRANSLATION: + if(dstsd && (dstsd->class_&MAPID_BASEMASK)!=MAPID_GUNSLINGER) { + pc->addspiritball(dstsd,skill->get_time(skill_id,skill_lv),5); + } break; - case PR_STRECOVERY: - if(status_isimmune(bl)) { - clif->skill_nodamage(src,bl,skill_id,skill_lv,0); - break; + case TK_TURNKICK: + case MO_BALKYOUNG: //Passive part of the attack. Splash knock-back+stun. [Skotlex] + if (skill_area_temp[1] != bl->id) { + skill->blown(src,bl,skill->get_blewcount(skill_id,skill_lv),-1,0); + skill->additional_effect(src,bl,skill_id,skill_lv,BF_MISC,ATK_DEF,tick); //Use Misc rather than weapon to signal passive pushback } - if (tsc && tsc->opt1) { - status_change_end(bl, SC_FREEZE, INVALID_TIMER); - status_change_end(bl, SC_STONE, INVALID_TIMER); - status_change_end(bl, SC_SLEEP, INVALID_TIMER); - status_change_end(bl, SC_STUN, INVALID_TIMER); - status_change_end(bl, SC_WHITEIMPRISON, INVALID_TIMER); + break; + + case MO_ABSORBSPIRITS: + i = 0; + if (dstsd && dstsd->spiritball && (sd == dstsd || map_flag_vs(src->m)) && (dstsd->class_&MAPID_BASEMASK)!=MAPID_GUNSLINGER) + { // split the if for readability, and included gunslingers in the check so that their coins cannot be removed [Reddozen] + i = dstsd->spiritball * 7; + pc->delspiritball(dstsd,dstsd->spiritball,0); + } else if (dstmd && !(tstatus->mode&MD_BOSS) && rnd() % 100 < 20) + { // check if target is a monster and not a Boss, for the 20% chance to absorb 2 SP per monster's level [Reddozen] + i = 2 * dstmd->level; + mob_target(dstmd,src,0); } - //Is this equation really right? It looks so... special. - if( battle->check_undead(tstatus->race,tstatus->def_ele) ) { - status_change_start(bl, SC_BLIND, - 100*(100-(tstatus->int_/2+tstatus->vit/3+tstatus->luk/10)), - 1,0,0,0, - skill->get_time2(skill_id, skill_lv) * (100-(tstatus->int_+tstatus->vit)/2)/100,0); + if (i) status_heal(src, 0, i, 3); + clif->skill_nodamage(src,bl,skill_id,skill_lv,i?1:0); + break; + + case AC_MAKINGARROW: + if(sd) { + clif->arrow_create_list(sd); + clif->skill_nodamage(src,bl,skill_id,skill_lv,1); } - clif->skill_nodamage(src,bl,skill_id,skill_lv,1); - if(dstmd) - mob_unlocktarget(dstmd,tick); break; - // Mercenary Supportive Skills - case MER_BENEDICTION: - status_change_end(bl, SC_CURSE, INVALID_TIMER); - status_change_end(bl, SC_BLIND, INVALID_TIMER); - clif->skill_nodamage(src,bl,skill_id,skill_lv,1); + case AM_PHARMACY: + if(sd) { + clif->skill_produce_mix_list(sd,skill_id,22); + clif->skill_nodamage(src,bl,skill_id,skill_lv,1); + } break; - case MER_COMPRESS: - status_change_end(bl, SC_BLEEDING, INVALID_TIMER); - clif->skill_nodamage(src,bl,skill_id,skill_lv,1); + + case SA_CREATECON: + if(sd) { + clif->elementalconverter_list(sd); + clif->skill_nodamage(src,bl,skill_id,skill_lv,1); + } break; - case MER_MENTALCURE: - status_change_end(bl, SC_CONFUSION, INVALID_TIMER); + + case BS_HAMMERFALL: + clif->skill_nodamage(src,bl,skill_id,skill_lv, + sc_start(bl,SC_STUN,(20 + 10 * skill_lv),skill_lv,skill->get_time2(skill_id,skill_lv))); + break; + case RG_RAID: + skill_area_temp[1] = 0; clif->skill_nodamage(src,bl,skill_id,skill_lv,1); + iMap->foreachinrange(skill->area_sub, bl, + skill->get_splash(skill_id, skill_lv), splash_target(src), + src,skill_id,skill_lv,tick, flag|BCT_ENEMY|1, + skill->castend_damage_id); + status_change_end(src, SC_HIDING, INVALID_TIMER); break; - case MER_RECUPERATE: - status_change_end(bl, SC_POISON, INVALID_TIMER); - status_change_end(bl, SC_SILENCE, INVALID_TIMER); + + case ASC_METEORASSAULT: + case GS_SPREADATTACK: + case RK_STORMBLAST: + case NC_AXETORNADO: + case GC_COUNTERSLASH: + case SR_SKYNETBLOW: + case SR_RAMPAGEBLASTER: + case SR_HOWLINGOFLION: + case KO_HAPPOKUNAI: + skill_area_temp[1] = 0; clif->skill_nodamage(src,bl,skill_id,skill_lv,1); + i = iMap->foreachinrange(skill->area_sub, bl, skill->get_splash(skill_id, skill_lv), splash_target(src), + src, skill_id, skill_lv, tick, flag|BCT_ENEMY|SD_SPLASH|1, skill->castend_damage_id); + if( !i && ( skill_id == NC_AXETORNADO || skill_id == SR_SKYNETBLOW || skill_id == KO_HAPPOKUNAI ) ) + clif->skill_damage(src,src,tick, status_get_amotion(src), 0, -30000, 1, skill_id, skill_lv, 6); break; - case MER_REGAIN: - status_change_end(bl, SC_SLEEP, INVALID_TIMER); - status_change_end(bl, SC_STUN, INVALID_TIMER); + + case NC_EMERGENCYCOOL: clif->skill_nodamage(src,bl,skill_id,skill_lv,1); + status_change_end(src,SC_OVERHEAT_LIMITPOINT,INVALID_TIMER); + status_change_end(src,SC_OVERHEAT,INVALID_TIMER); break; - case MER_TENDER: - status_change_end(bl, SC_FREEZE, INVALID_TIMER); - status_change_end(bl, SC_STONE, INVALID_TIMER); + case SR_WINDMILL: + case GN_CART_TORNADO: clif->skill_nodamage(src,bl,skill_id,skill_lv,1); + case SR_EARTHSHAKER: + case NC_INFRAREDSCAN: + case NPC_EARTHQUAKE: + case NPC_VAMPIRE_GIFT: + case NPC_HELLJUDGEMENT: + case NPC_PULSESTRIKE: + case LG_MOONSLASHER: + skill->castend_damage_id(src, src, skill_id, skill_lv, tick, flag); break; - case MER_SCAPEGOAT: - if( mer && mer->master ) - { - status_heal(&mer->master->bl, mer->battle_status.hp, 0, 2); - status_damage(src, src, mer->battle_status.max_hp, 0, 0, 1); - } + case KN_BRANDISHSPEAR: + case ML_BRANDISH: + skill->brandishspear(src, bl, skill_id, skill_lv, tick, flag); break; - case MER_ESTIMATION: - if( !mer ) - break; - sd = mer->master; - case WZ_ESTIMATION: - if( sd == NULL ) - break; - if( dstsd ) - { // Fail on Players - clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); - break; - } - if( dstmd && dstmd->class_ == MOBID_EMPERIUM ) - break; // Cannot be Used on Emperium - - clif->skill_nodamage(src, bl, skill_id, skill_lv, 1); - clif->skill_estimation(sd, bl); - if( skill_id == MER_ESTIMATION ) - sd = NULL; + case WZ_SIGHTRASHER: + //Passive side of the attack. + status_change_end(src, SC_SIGHT, INVALID_TIMER); + clif->skill_nodamage(src,bl,skill_id,skill_lv,1); + iMap->foreachinrange(skill->area_sub,src, + skill->get_splash(skill_id, skill_lv),BL_CHAR|BL_SKILL, + src,skill_id,skill_lv,tick, flag|BCT_ENEMY|1, + skill->castend_damage_id); break; - case BS_REPAIRWEAPON: - if(sd && dstsd) - clif->item_repair_list(sd,dstsd,skill_lv); + case NJ_HYOUSYOURAKU: + case NJ_RAIGEKISAI: + case WZ_FROSTNOVA: + clif->skill_nodamage(src,bl,skill_id,skill_lv,1); + skill_area_temp[1] = 0; + iMap->foreachinrange(skill->attack_area, src, + skill->get_splash(skill_id, skill_lv), splash_target(src), + BF_MAGIC, src, src, skill_id, skill_lv, tick, flag, BCT_ENEMY); break; - case MC_IDENTIFY: - if(sd) { - clif->item_identify_list(sd); - if( sd->menuskill_id != MC_IDENTIFY ) {/* failed, dont consume anything, return */ - clif->skill_nodamage(src,bl,skill_id,skill_lv,1); - iMap->freeblock_unlock(); - return 1; - } - status_zap(src,0,skill_db[skill->get_index(skill_id)].sp[skill_lv]); // consume sp only if succeeded - } + case HVAN_EXPLOSION: //[orn] + case NPC_SELFDESTRUCTION: + //Self Destruction hits everyone in range (allies+enemies) + //Except for Summoned Marine spheres on non-versus maps, where it's just enemy. + i = ((!md || md->special_state.ai == 2) && !map_flag_vs(src->m))? + BCT_ENEMY:BCT_ALL; + clif->skill_nodamage(src, src, skill_id, -1, 1); + iMap->delblock(src); //Required to prevent chain-self-destructions hitting back. + iMap->foreachinrange(skill->area_sub, bl, + skill->get_splash(skill_id, skill_lv), splash_target(src), + src, skill_id, skill_lv, tick, flag|i, + skill->castend_damage_id); + iMap->addblock(src); + status_damage(src, src, sstatus->max_hp,0,0,1); break; - // Weapon Refining [Celest] - case WS_WEAPONREFINE: - if(sd) - clif->item_refine_list(sd); + case AL_ANGELUS: + case PR_MAGNIFICAT: + case PR_GLORIA: + case SN_WINDWALK: + case CASH_BLESSING: + case CASH_INCAGI: + case CASH_ASSUMPTIO: + case WM_FRIGG_SONG: + if( sd == NULL || sd->status.party_id == 0 || (flag & 1) ) + clif->skill_nodamage(bl, bl, skill_id, skill_lv, sc_start(bl,type,100,skill_lv,skill->get_time(skill_id,skill_lv))); + else if( sd ) + party_foreachsamemap(skill->area_sub, sd, skill->get_splash(skill_id, skill_lv), src, skill_id, skill_lv, tick, flag|BCT_PARTY|1, skill->castend_nodamage_id); break; - - case MC_VENDING: - if(sd) - { //Prevent vending of GMs with unnecessary Level to trade/drop. [Skotlex] - if ( !pc->can_give_items(sd) ) - clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); - else { - sd->state.prevend = 1; - clif->openvendingreq(sd,2+skill_lv); - } + case MER_MAGNIFICAT: + if( mer != NULL ) + { + clif->skill_nodamage(bl, bl, skill_id, skill_lv, sc_start(bl,type,100,skill_lv,skill->get_time(skill_id,skill_lv))); + if( mer->master && mer->master->status.party_id != 0 && !(flag&1) ) + party_foreachsamemap(skill->area_sub, mer->master, skill->get_splash(skill_id, skill_lv), src, skill_id, skill_lv, tick, flag|BCT_PARTY|1, skill->castend_nodamage_id); + else if( mer->master && !(flag&1) ) + clif->skill_nodamage(src, &mer->master->bl, skill_id, skill_lv, sc_start(bl,type,100,skill_lv,skill->get_time(skill_id,skill_lv))); } break; - case AL_TELEPORT: - if(sd) - { - if (map[bl->m].flag.noteleport && skill_lv <= 2) { - clif->skill_teleportmessage(sd,0); - break; - } - if(!battle_config.duel_allow_teleport && sd->duel_group && skill_lv <= 2) { // duel restriction [LuzZza] - char output[128]; sprintf(output, msg_txt(365), skill->get_name(AL_TELEPORT)); - clif->message(sd->fd, output); //"Duel: Can't use %s in duel." - break; - } - - if( sd->state.autocast || ( (sd->skillitem == AL_TELEPORT || battle_config.skip_teleport_lv1_menu) && skill_lv == 1 ) || skill_lv == 3 ) - { - if( skill_lv == 1 ) - pc->randomwarp(sd,CLR_TELEPORT); - else - pc->setpos(sd,sd->status.save_point.map,sd->status.save_point.x,sd->status.save_point.y,CLR_TELEPORT); - break; - } - - clif->skill_nodamage(src,bl,skill_id,skill_lv,1); - if( skill_lv == 1 ) - clif->skill_warppoint(sd,skill_id,skill_lv, (unsigned short)-1,0,0,0); - else - clif->skill_warppoint(sd,skill_id,skill_lv, (unsigned short)-1,sd->status.save_point.map,0,0); - } else - unit_warp(bl,-1,-1,-1,CLR_TELEPORT); + case BS_ADRENALINE: + case BS_ADRENALINE2: + case BS_WEAPONPERFECT: + case BS_OVERTHRUST: + if (sd == NULL || sd->status.party_id == 0 || (flag & 1)) { + clif->skill_nodamage(bl,bl,skill_id,skill_lv, + sc_start2(bl,type,100,skill_lv,(src == bl)? 1:0,skill->get_time(skill_id,skill_lv))); + } else if (sd) { + party_foreachsamemap(skill->area_sub, + sd,skill->get_splash(skill_id, skill_lv), + src,skill_id,skill_lv,tick, flag|BCT_PARTY|1, + skill->castend_nodamage_id); + } break; - case NPC_EXPULSION: - clif->skill_nodamage(src,bl,skill_id,skill_lv,1); - unit_warp(bl,-1,-1,-1,CLR_TELEPORT); + case BS_MAXIMIZE: + case NV_TRICKDEAD: + case CR_DEFENDER: + case ML_DEFENDER: + case CR_AUTOGUARD: + case ML_AUTOGUARD: + case TK_READYSTORM: + case TK_READYDOWN: + case TK_READYTURN: + case TK_READYCOUNTER: + case TK_DODGE: + case CR_SHRINK: + case SG_FUSION: + case GS_GATLINGFEVER: + if( tsce ) + { + clif->skill_nodamage(src,bl,skill_id,skill_lv,status_change_end(bl, type, INVALID_TIMER)); + iMap->freeblock_unlock(); + return 0; + } + clif->skill_nodamage(src,bl,skill_id,skill_lv,sc_start(bl,type,100,skill_lv,skill->get_time(skill_id,skill_lv))); break; - - case AL_HOLYWATER: - if(sd) { - if (skill->produce_mix(sd, skill_id, 523, 0, 0, 0, 1)) - clif->skill_nodamage(src,bl,skill_id,skill_lv,1); - else + case SL_KAITE: + case SL_KAAHI: + case SL_KAIZEL: + case SL_KAUPE: + if (sd) { + if (!dstsd || !( + (sd->sc.data[SC_SOULLINK] && sd->sc.data[SC_SOULLINK]->val2 == SL_SOULLINKER) || + (dstsd->class_&MAPID_UPPERMASK) == MAPID_SOUL_LINKER || + dstsd->status.char_id == sd->status.char_id || + dstsd->status.char_id == sd->status.partner_id || + dstsd->status.char_id == sd->status.child + )) { + status_change_start(src,SC_STUN,10000,skill_lv,0,0,0,500,8); clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); - } - break; - - case TF_PICKSTONE: - if(sd) { - int eflag; - struct item item_tmp; - struct block_list tbl; - clif->skill_nodamage(src,bl,skill_id,skill_lv,1); - memset(&item_tmp,0,sizeof(item_tmp)); - memset(&tbl,0,sizeof(tbl)); // [MouseJstr] - item_tmp.nameid = ITEMID_STONE; - item_tmp.identify = 1; - tbl.id = 0; - clif->takeitem(&sd->bl,&tbl); - eflag = pc->additem(sd,&item_tmp,1,LOG_TYPE_PRODUCE); - if(eflag) { - clif->additem(sd,0,0,eflag); - iMap->addflooritem(&item_tmp,1,sd->bl.m,sd->bl.x,sd->bl.y,0,0,0,0); + break; } } + clif->skill_nodamage(src,bl,skill_id,skill_lv, + sc_start(bl,type,100,skill_lv,skill->get_time(skill_id, skill_lv))); break; - case ASC_CDP: - if(sd) { - clif->skill_nodamage(src,bl,skill_id,skill_lv,1); - skill->produce_mix(sd, skill_id, 678, 0, 0, 0, 1); //Produce a Deadly Poison Bottle. - } + case SM_AUTOBERSERK: + case MER_AUTOBERSERK: + if( tsce ) + i = status_change_end(bl, type, INVALID_TIMER); + else + i = sc_start(bl,type,100,skill_lv,60000); + clif->skill_nodamage(src,bl,skill_id,skill_lv,i); break; - - case RG_STRIPWEAPON: - case RG_STRIPSHIELD: - case RG_STRIPARMOR: - case RG_STRIPHELM: - case ST_FULLSTRIP: - case GC_WEAPONCRUSH: - case SC_STRIPACCESSARY: { - unsigned short location = 0; - int d = 0; - - //Rate in percent - if ( skill_id == ST_FULLSTRIP ) { - i = 5 + 2*skill_lv + (sstatus->dex - tstatus->dex)/5; - } else if( skill_id == SC_STRIPACCESSARY ) { - i = 12 + 2 * skill_lv + (sstatus->dex - tstatus->dex)/5; - } else { - i = 5 + 5*skill_lv + (sstatus->dex - tstatus->dex)/5; - } - - if (i < 5) i = 5; //Minimum rate 5% - - //Duration in ms - if( skill_id == GC_WEAPONCRUSH){ - d = skill->get_time(skill_id,skill_lv); - if(bl->type == BL_PC) - d += skill_lv * 15 + (sstatus->dex - tstatus->dex); - else - d += skill_lv * 30 + (sstatus->dex - tstatus->dex) / 2; - }else - d = skill->get_time(skill_id,skill_lv) + (sstatus->dex - tstatus->dex)*500; - - if (d < 0) d = 0; //Minimum duration 0ms - - switch (skill_id) { - case RG_STRIPWEAPON: - case GC_WEAPONCRUSH: - location = EQP_WEAPON; - break; - case RG_STRIPSHIELD: - location = EQP_SHIELD; - break; - case RG_STRIPARMOR: - location = EQP_ARMOR; - break; - case RG_STRIPHELM: - location = EQP_HELM; - break; - case ST_FULLSTRIP: - location = EQP_WEAPON|EQP_SHIELD|EQP_ARMOR|EQP_HELM; - break; - case SC_STRIPACCESSARY: - location = EQP_ACC; - break; + case TF_HIDING: + case ST_CHASEWALK: + case KO_YAMIKUMO: + if (tsce) + { + clif->skill_nodamage(src,bl,skill_id,-1,status_change_end(bl, type, INVALID_TIMER)); //Hide skill-scream animation. + iMap->freeblock_unlock(); + return 0; + } else if( tsc && tsc->option&OPTION_MADOGEAR ) { + //Mado Gear cannot hide + if( sd ) clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); + iMap->freeblock_unlock(); + return 0; } - - //Special message when trying to use strip on FCP [Jobbie] - if( sd && skill_id == ST_FULLSTRIP && tsc && tsc->data[SC_CP_WEAPON] && tsc->data[SC_CP_HELM] && tsc->data[SC_CP_ARMOR] && tsc->data[SC_CP_SHIELD]) + clif->skill_nodamage(src,bl,skill_id,-1,sc_start(bl,type,100,skill_lv,skill->get_time(skill_id,skill_lv))); + break; + case TK_RUN: + if (tsce) { - clif->gospel_info(sd, 0x28); - break; + clif->skill_nodamage(src,bl,skill_id,skill_lv,status_change_end(bl, type, INVALID_TIMER)); + iMap->freeblock_unlock(); + return 0; } - - //Attempts to strip at rate i and duration d - if( (i = skill->strip_equip(bl, location, i, skill_lv, d)) || (skill_id != ST_FULLSTRIP && skill_id != GC_WEAPONCRUSH ) ) - clif->skill_nodamage(src,bl,skill_id,skill_lv,i); - - //Nothing stripped. - if( sd && !i ) + clif->skill_nodamage(src,bl,skill_id,skill_lv,sc_start4(bl,type,100,skill_lv,unit_getdir(bl),0,0,0)); + if (sd) // If the client receives a skill-use packet inmediately before a walkok packet, it will discard the walk packet! [Skotlex] + clif->walkok(sd); // So aegis has to resend the walk ok. + break; + case AS_CLOAKING: + case GC_CLOAKINGEXCEED: + case LG_FORCEOFVANGUARD: + case SC_REPRODUCE: + case SC_INVISIBILITY: + if (tsce) { + i = status_change_end(bl, type, INVALID_TIMER); + if( i ) + clif->skill_nodamage(src,bl,skill_id,( skill_id == LG_FORCEOFVANGUARD ) ? skill_lv : -1,i); + else if( sd ) + clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); + iMap->freeblock_unlock(); + return 0; + } + case RA_CAMOUFLAGE: + i = sc_start(bl,type,100,skill_lv,skill->get_time(skill_id,skill_lv)); + if( i ) + clif->skill_nodamage(src,bl,skill_id,( skill_id == LG_FORCEOFVANGUARD ) ? skill_lv : -1,i); + else if( sd ) clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); break; - } - - case AM_BERSERKPITCHER: - case AM_POTIONPITCHER: { - int i,sp = 0; - int64 hp = 0; - if( dstmd && dstmd->class_ == MOBID_EMPERIUM ) { - iMap->freeblock_unlock(); - return 1; - } - if( sd ) { - int x,bonus=100; - x = skill_lv%11 - 1; - i = pc->search_inventory(sd,skill_db[skill_id].itemid[x]); - if( i < 0 || skill_db[skill_id].itemid[x] <= 0 ) { - clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); - iMap->freeblock_unlock(); - return 1; - } - if(sd->inventory_data[i] == NULL || sd->status.inventory[i].amount < skill_db[skill_id].amount[x]) { - clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); - iMap->freeblock_unlock(); - return 1; - } - if( skill_id == AM_BERSERKPITCHER ) { - if( dstsd && dstsd->status.base_level < (unsigned int)sd->inventory_data[i]->elv ) { - clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); - iMap->freeblock_unlock(); - return 1; - } - } - potion_flag = 1; - potion_hp = potion_sp = potion_per_hp = potion_per_sp = 0; - potion_target = bl->id; - run_script(sd->inventory_data[i]->script,0,sd->bl.id,0); - potion_flag = potion_target = 0; - if( sd->sc.data[SC_SPIRIT] && sd->sc.data[SC_SPIRIT]->val2 == SL_ALCHEMIST ) - bonus += sd->status.base_level; - if( potion_per_hp > 0 || potion_per_sp > 0 ) { - hp = tstatus->max_hp * potion_per_hp / 100; - hp = hp * (100 + pc->checkskill(sd,AM_POTIONPITCHER)*10 + pc->checkskill(sd,AM_LEARNINGPOTION)*5)*bonus/10000; - if( dstsd ) { - sp = dstsd->status.max_sp * potion_per_sp / 100; - sp = sp * (100 + pc->checkskill(sd,AM_POTIONPITCHER)*10 + pc->checkskill(sd,AM_LEARNINGPOTION)*5)*bonus/10000; - } - } else { - if( potion_hp > 0 ) { - hp = potion_hp * (100 + pc->checkskill(sd,AM_POTIONPITCHER)*10 + pc->checkskill(sd,AM_LEARNINGPOTION)*5)*bonus/10000; - hp = hp * (100 + (tstatus->vit<<1)) / 100; - if( dstsd ) - hp = hp * (100 + pc->checkskill(dstsd,SM_RECOVERY)*10) / 100; - } - if( potion_sp > 0 ) { - sp = potion_sp * (100 + pc->checkskill(sd,AM_POTIONPITCHER)*10 + pc->checkskill(sd,AM_LEARNINGPOTION)*5)*bonus/10000; - sp = sp * (100 + (tstatus->int_<<1)) / 100; - if( dstsd ) - sp = sp * (100 + pc->checkskill(dstsd,MG_SRECOVERY)*10) / 100; - } - } - - if (sd->itemgrouphealrate[IG_POTION]>0) { - hp += hp * sd->itemgrouphealrate[IG_POTION] / 100; - sp += sp * sd->itemgrouphealrate[IG_POTION] / 100; - } - if( (i = pc->skillheal_bonus(sd, skill_id)) ) { - hp += hp * i / 100; - sp += sp * i / 100; - } - } else { - hp = (1 + rnd()%400) * (100 + skill_lv*10) / 100; - hp = hp * (100 + (tstatus->vit<<1)) / 100; - if( dstsd ) - hp = hp * (100 + pc->checkskill(dstsd,SM_RECOVERY)*10) / 100; - } - if( dstsd && (i = pc->skillheal2_bonus(dstsd, skill_id)) ) { - hp += hp * i / 100; - sp += sp * i / 100; - } - if( tsc && tsc->count ) { - if( tsc->data[SC_CRITICALWOUND] ) { - hp -= hp * tsc->data[SC_CRITICALWOUND]->val2 / 100; - sp -= sp * tsc->data[SC_CRITICALWOUND]->val2 / 100; - } - if( tsc->data[SC_DEATHHURT] ) { - hp -= hp * 20 / 100; - sp -= sp * 20 / 100; - } - if( tsc->data[SC_WATER_INSIGNIA] && tsc->data[SC_WATER_INSIGNIA]->val1 == 2 ) { - hp += hp / 10; - sp += sp / 10; - } - } + case BD_ADAPTATION: + if(tsc && tsc->data[SC_DANCING]){ clif->skill_nodamage(src,bl,skill_id,skill_lv,1); - if( hp > 0 || (skill_id == AM_POTIONPITCHER && sp <= 0) ) - clif->skill_nodamage(NULL,bl,AL_HEAL,(int)hp,1); - if( sp > 0 ) - clif->skill_nodamage(NULL,bl,MG_SRECOVERY,sp,1); - #ifdef RENEWAL - if( tsc && tsc->data[SC_EXTREMITYFIST2] ) - sp = 0; - #endif - status_heal(bl,(int)hp,sp,0); + status_change_end(bl, SC_DANCING, INVALID_TIMER); } - break; - case AM_CP_WEAPON: - case AM_CP_SHIELD: - case AM_CP_ARMOR: - case AM_CP_HELM: - { - unsigned int equip[] = {EQP_WEAPON, EQP_SHIELD, EQP_ARMOR, EQP_HEAD_TOP}; + break; - if( sd && ( bl->type != BL_PC || ( dstsd && pc->checkequip(dstsd,equip[skill_id - AM_CP_WEAPON]) < 0 ) ) ){ - clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); - iMap->freeblock_unlock(); // Don't consume item requirements - return 0; - } + case BA_FROSTJOKER: + case DC_SCREAM: + clif->skill_nodamage(src,bl,skill_id,skill_lv,1); + skill->addtimerskill(src,tick+2000,bl->id,src->x,src->y,skill_id,skill_lv,0,flag); - clif->skill_nodamage(src,bl,skill_id,skill_lv, - sc_start(bl,type,100,skill_lv,skill->get_time(skill_id,skill_lv))); + if (md) { + // custom hack to make the mob display the skill, because these skills don't show the skill use text themselves + //NOTE: mobs don't have the sprite animation that is used when performing this skill (will cause glitches) + char temp[70]; + snprintf(temp, sizeof(temp), "%s : %s !!",md->name,skill_db[skill_id].desc); + clif->disp_overhead(&md->bl,temp); } break; - case AM_TWILIGHT1: - if (sd) { - clif->skill_nodamage(src,bl,skill_id,skill_lv,1); - //Prepare 200 White Potions. - if (!skill->produce_mix(sd, skill_id, 504, 0, 0, 0, 200)) - clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); + + case BA_PANGVOICE: + clif->skill_nodamage(src,bl,skill_id,skill_lv, sc_start(bl,SC_CONFUSION,50,7,skill->get_time(skill_id,skill_lv))); + break; + + case DC_WINKCHARM: + if( dstsd ) + clif->skill_nodamage(src,bl,skill_id,skill_lv, sc_start(bl,SC_CONFUSION,30,7,skill->get_time2(skill_id,skill_lv))); + else + if( dstmd ) + { + if( status_get_lv(src) > status_get_lv(bl) + && (tstatus->race == RC_DEMON || tstatus->race == RC_DEMIHUMAN || tstatus->race == RC_ANGEL) + && !(tstatus->mode&MD_BOSS) ) + clif->skill_nodamage(src,bl,skill_id,skill_lv, sc_start2(bl,type,70,skill_lv,src->id,skill->get_time(skill_id,skill_lv))); + else + { + clif->skill_nodamage(src,bl,skill_id,skill_lv,0); + if(sd) clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); + } } break; - case AM_TWILIGHT2: - if (sd) { - clif->skill_nodamage(src,bl,skill_id,skill_lv,1); - //Prepare 200 Slim White Potions. - if (!skill->produce_mix(sd, skill_id, 547, 0, 0, 0, 200)) - clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); + + case TF_STEAL: + if(sd) { + if(pc->steal_item(sd,bl,skill_lv)) + clif->skill_nodamage(src,bl,skill_id,skill_lv,1); + else + clif->skill_fail(sd,skill_id,USESKILL_FAIL,0); } break; - case AM_TWILIGHT3: - if (sd) { - int ebottle = pc->search_inventory(sd,713); - if( ebottle >= 0 ) - ebottle = sd->status.inventory[ebottle].amount; - //check if you can produce all three, if not, then fail: - if (!skill->can_produce_mix(sd,970,-1, 100) //100 Alcohol - || !skill->can_produce_mix(sd,7136,-1, 50) //50 Acid Bottle - || !skill->can_produce_mix(sd,7135,-1, 50) //50 Flame Bottle - || ebottle < 200 //200 empty bottle are required at total. - ) { - clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); - break; + + case RG_STEALCOIN: + if(sd) { + if(pc->steal_coin(sd,bl)) + { + dstmd->state.provoke_flag = src->id; + mob_target(dstmd, src, skill->get_range2(src,skill_id,skill_lv)); + clif->skill_nodamage(src,bl,skill_id,skill_lv,1); + } - clif->skill_nodamage(src,bl,skill_id,skill_lv,1); - skill->produce_mix(sd, skill_id, 970, 0, 0, 0, 100); - skill->produce_mix(sd, skill_id, 7136, 0, 0, 0, 50); - skill->produce_mix(sd, skill_id, 7135, 0, 0, 0, 50); + else + clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); } break; - case SA_DISPELL: - if (flag&1 || (i = skill->get_splash(skill_id, skill_lv)) < 1) + + case MG_STONECURSE: { - clif->skill_nodamage(src,bl,skill_id,skill_lv,1); - if((dstsd && (dstsd->class_&MAPID_UPPERMASK) == MAPID_SOUL_LINKER) - || (tsc && tsc->data[SC_SPIRIT] && tsc->data[SC_SPIRIT]->val2 == SL_ROGUE) //Rogue's spirit defends againt dispel. - || rnd()%100 >= 50+10*skill_lv - || ( tsc && tsc->option&OPTION_MADOGEAR ) )//Mado Gear is immune to dispell according to bug report 49 [Ind] - { - if (sd) - clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); + int brate = 0; + if (tstatus->mode&MD_BOSS) { + if (sd) clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); break; } - if(status_isimmune(bl) || !tsc || !tsc->count) + if(status_isimmune(bl) || !tsc) break; - - if( sd && dstsd && !map_flag_vs(sd->bl.m) && sd->status.guild_id == dstsd->status.guild_id ) { - clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); + + if (sd && sd->sc.data[SC_PETROLOGY_OPTION]) + brate = sd->sc.data[SC_PETROLOGY_OPTION]->val3; + + if (tsc->data[SC_STONE]) { + status_change_end(bl, SC_STONE, INVALID_TIMER); + if (sd) clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); break; } - - for(i=0;idata[i]) - continue; - switch (i) { - case SC_WEIGHT50: case SC_WEIGHT90: case SC_HALLUCINATION: - case SC_STRIPWEAPON: case SC_STRIPSHIELD: case SC_STRIPARMOR: - case SC_STRIPHELM: case SC_CP_WEAPON: case SC_CP_SHIELD: - case SC_CP_ARMOR: case SC_CP_HELM: case SC_COMBO: - case SC_STRFOOD: case SC_AGIFOOD: case SC_VITFOOD: - case SC_INTFOOD: case SC_DEXFOOD: case SC_LUKFOOD: - case SC_HITFOOD: case SC_FLEEFOOD: case SC_BATKFOOD: - case SC_WATKFOOD: case SC_MATKFOOD: case SC_DANCING: - case SC_EDP: case SC_AUTOBERSERK: - case SC_CARTBOOST: case SC_MELTDOWN: case SC_SAFETYWALL: - case SC_SMA: case SC_SPEEDUP0: case SC_NOCHAT: - case SC_ANKLE: case SC_SPIDERWEB: case SC_JAILED: - case SC_ITEMBOOST: case SC_EXPBOOST: case SC_LIFEINSURANCE: - case SC_BOSSMAPINFO: case SC_PNEUMA: case SC_AUTOSPELL: - case SC_INCHITRATE: case SC_INCATKRATE: case SC_NEN: - case SC_READYSTORM: case SC_READYDOWN: case SC_READYTURN: - case SC_READYCOUNTER: case SC_DODGE: case SC_WARM: - case SC_SPEEDUP1: case SC_AUTOTRADE: case SC_CRITICALWOUND: - case SC_JEXPBOOST: case SC_INVINCIBLE: case SC_INVINCIBLEOFF: - case SC_HELLPOWER: case SC_MANU_ATK: case SC_MANU_DEF: - case SC_SPL_ATK: case SC_SPL_DEF: case SC_MANU_MATK: - case SC_SPL_MATK: case SC_RICHMANKIM: case SC_ETERNALCHAOS: - case SC_DRUMBATTLE: case SC_NIBELUNGEN: case SC_ROKISWEIL: - case SC_INTOABYSS: case SC_SIEGFRIED: case SC_FOOD_STR_CASH: - case SC_FOOD_AGI_CASH: case SC_FOOD_VIT_CASH: case SC_FOOD_DEX_CASH: - case SC_FOOD_INT_CASH: case SC_FOOD_LUK_CASH: case SC_SEVENWIND: - case SC_MIRACLE: case SC_S_LIFEPOTION: case SC_L_LIFEPOTION: - case SC_INCHEALRATE: case SC_ELECTRICSHOCKER: case SC__STRIPACCESSORY: - //case SC_SAVAGE_STEAK: case SC_COCKTAIL_WARG_BLOOD: case SC_MINOR_BBQ: - //case SC_SIROMA_ICE_TEA: case SC_DROCERA_HERB_STEAMED: case SC_PUTTI_TAILS_NOODLES: - case SC_NEUTRALBARRIER_MASTER: case SC_NEUTRALBARRIER: case SC_STEALTHFIELD_MASTER: - case SC_STEALTHFIELD: case SC_GIANTGROWTH: case SC_MILLENNIUMSHIELD: - case SC_REFRESH: case SC_STONEHARDSKIN: case SC_VITALITYACTIVATION: - case SC_FIGHTINGSPIRIT: case SC_ABUNDANCE: case SC__SHADOWFORM: - case SC_LEADERSHIP: case SC_GLORYWOUNDS: case SC_SOULCOLD: - case SC_HAWKEYES: case SC_GUILDAURA: case SC_PUSH_CART: - case SC_RAISINGDRAGON: case SC_GT_ENERGYGAIN: case SC_GT_CHANGE: - case SC_GT_REVITALIZE: case SC_REFLECTDAMAGE: case SC_INSPIRATION: - case SC_EXEEDBREAK: case SC_FORCEOFVANGUARD: case SC_BANDING: - case SC_DUPLELIGHT: case SC_EXPIATIO: case SC_LAUDAAGNUS: - case SC_LAUDARAMUS: case SC_GATLINGFEVER: case SC_INCREASING: - case SC_ADJUSTMENT: case SC_MADNESSCANCEL: case SC_ALL_RIDING: - #ifdef RENEWAL - case SC_EXTREMITYFIST2: - #endif - continue; - /** - * bugreport:4888 these songs may only be dispelled if you're not in their song area anymore - **/ - case SC_WHISTLE: - case SC_ASSNCROS: - case SC_POEMBRAGI: - case SC_APPLEIDUN: - case SC_HUMMING: - case SC_DONTFORGETME: - case SC_FORTUNE: - case SC_SERVICE4U: - if( !tsc->data[i]->val4 ) //val4 = out-of-song-area - continue; - break; - case SC_ASSUMPTIO: - if( bl->type == BL_MOB ) - continue; - break; + if (sc_start4(bl,SC_STONE,(skill_lv*4+20)+brate, + skill_lv, 0, 0, skill->get_time(skill_id, skill_lv), + skill->get_time2(skill_id,skill_lv))) + clif->skill_nodamage(src,bl,skill_id,skill_lv,1); + else if(sd) { + clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); + // Level 6-10 doesn't consume a red gem if it fails [celest] + if (skill_lv > 5) + { // not to consume items + iMap->freeblock_unlock(); + return 0; } - if(i==SC_BERSERK || i==SC_SATURDAYNIGHTFEVER) tsc->data[i]->val2=0; //Mark a dispelled berserk to avoid setting hp to 100 by setting hp penalty to 0. - status_change_end(bl, (sc_type)i, INVALID_TIMER); } + } + break; + + case NV_FIRSTAID: + clif->skill_nodamage(src,bl,skill_id,5,1); + status_heal(bl,5,0,0); + break; + + case AL_CURE: + if(status_isimmune(bl)) { + clif->skill_nodamage(src,bl,skill_id,skill_lv,0); + break; + } + status_change_end(bl, SC_SILENCE, INVALID_TIMER); + status_change_end(bl, SC_BLIND, INVALID_TIMER); + status_change_end(bl, SC_CONFUSION, INVALID_TIMER); + clif->skill_nodamage(src,bl,skill_id,skill_lv,1); + break; + + case TF_DETOXIFY: + clif->skill_nodamage(src,bl,skill_id,skill_lv,1); + status_change_end(bl, SC_POISON, INVALID_TIMER); + status_change_end(bl, SC_DPOISON, INVALID_TIMER); + break; + + case PR_STRECOVERY: + if(status_isimmune(bl)) { + clif->skill_nodamage(src,bl,skill_id,skill_lv,0); + break; + } + if (tsc && tsc->opt1) { + status_change_end(bl, SC_FREEZE, INVALID_TIMER); + status_change_end(bl, SC_STONE, INVALID_TIMER); + status_change_end(bl, SC_SLEEP, INVALID_TIMER); + status_change_end(bl, SC_STUN, INVALID_TIMER); + status_change_end(bl, SC_WHITEIMPRISON, INVALID_TIMER); + } + //Is this equation really right? It looks so... special. + if( battle->check_undead(tstatus->race,tstatus->def_ele) ) { + status_change_start(bl, SC_BLIND, + 100*(100-(tstatus->int_/2+tstatus->vit/3+tstatus->luk/10)), + 1,0,0,0, + skill->get_time2(skill_id, skill_lv) * (100-(tstatus->int_+tstatus->vit)/2)/100,0); + } + clif->skill_nodamage(src,bl,skill_id,skill_lv,1); + if(dstmd) + mob_unlocktarget(dstmd,tick); + break; + + // Mercenary Supportive Skills + case MER_BENEDICTION: + status_change_end(bl, SC_CURSE, INVALID_TIMER); + status_change_end(bl, SC_BLIND, INVALID_TIMER); + clif->skill_nodamage(src,bl,skill_id,skill_lv,1); + break; + case MER_COMPRESS: + status_change_end(bl, SC_BLOODING, INVALID_TIMER); + clif->skill_nodamage(src,bl,skill_id,skill_lv,1); + break; + case MER_MENTALCURE: + status_change_end(bl, SC_CONFUSION, INVALID_TIMER); + clif->skill_nodamage(src,bl,skill_id,skill_lv,1); + break; + case MER_RECUPERATE: + status_change_end(bl, SC_POISON, INVALID_TIMER); + status_change_end(bl, SC_SILENCE, INVALID_TIMER); + clif->skill_nodamage(src,bl,skill_id,skill_lv,1); + break; + case MER_REGAIN: + status_change_end(bl, SC_SLEEP, INVALID_TIMER); + status_change_end(bl, SC_STUN, INVALID_TIMER); + clif->skill_nodamage(src,bl,skill_id,skill_lv,1); + break; + case MER_TENDER: + status_change_end(bl, SC_FREEZE, INVALID_TIMER); + status_change_end(bl, SC_STONE, INVALID_TIMER); + clif->skill_nodamage(src,bl,skill_id,skill_lv,1); + break; + + case MER_SCAPEGOAT: + if( mer && mer->master ) + { + status_heal(&mer->master->bl, mer->battle_status.hp, 0, 2); + status_damage(src, src, mer->battle_status.max_hp, 0, 0, 1); + } + break; + + case MER_ESTIMATION: + if( !mer ) + break; + sd = mer->master; + case WZ_ESTIMATION: + if( sd == NULL ) + break; + if( dstsd ) + { // Fail on Players + clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); break; } - //Affect all targets on splash area. - iMap->foreachinrange(skill->area_sub, bl, i, BL_CHAR, - src, skill_id, skill_lv, tick, flag|1, - skill->castend_damage_id); + if( dstmd && dstmd->class_ == MOBID_EMPERIUM ) + break; // Cannot be Used on Emperium + + clif->skill_nodamage(src, bl, skill_id, skill_lv, 1); + clif->skill_estimation(sd, bl); + if( skill_id == MER_ESTIMATION ) + sd = NULL; + break; + + case BS_REPAIRWEAPON: + if(sd && dstsd) + clif->item_repair_list(sd,dstsd,skill_lv); + break; + + case MC_IDENTIFY: + if(sd) { + clif->item_identify_list(sd); + if( sd->menuskill_id != MC_IDENTIFY ) {/* failed, dont consume anything, return */ + clif->skill_nodamage(src,bl,skill_id,skill_lv,1); + iMap->freeblock_unlock(); + return 1; + } + status_zap(src,0,skill_db[skill->get_index(skill_id)].sp[skill_lv]); // consume sp only if succeeded + } + break; + + // Weapon Refining [Celest] + case WS_WEAPONREFINE: + if(sd){ + sd->state.prerefining = 1; + clif->item_refine_list(sd); + } break; - case TF_BACKSLIDING: //This is the correct implementation as per packet logging information. [Skotlex] - clif->skill_nodamage(src,bl,skill_id,skill_lv,1); - skill->blown(src,bl,skill->get_blewcount(skill_id,skill_lv),unit_getdir(bl),0); + case MC_VENDING: + if(sd) + { //Prevent vending of GMs with unnecessary Level to trade/drop. [Skotlex] + if ( !pc->can_give_items(sd) ) + clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); + else { + sd->state.prevend = sd->state.workinprogress = 3; + clif->openvendingreq(sd,2+skill_lv); + } + } break; - case TK_HIGHJUMP: + case AL_TELEPORT: + if(sd) { - int x,y, dir = unit_getdir(src); - - //Fails on noteleport maps, except for GvG and BG maps [Skotlex] - if( map[src->m].flag.noteleport && - !(map[src->m].flag.battleground || map_flag_gvg2(src->m) ) - ) { - x = src->x; - y = src->y; - } else { - x = src->x + dirx[dir]*skill_lv*2; - y = src->y + diry[dir]*skill_lv*2; + if (map[bl->m].flag.noteleport && skill_lv <= 2) { + clif->skill_mapinfomessage(sd,0); + break; + } + if(!battle_config.duel_allow_teleport && sd->duel_group && skill_lv <= 2) { // duel restriction [LuzZza] + char output[128]; sprintf(output, msg_txt(365), skill->get_name(AL_TELEPORT)); + clif->message(sd->fd, output); //"Duel: Can't use %s in duel." + break; } - clif->skill_nodamage(src,bl,TK_HIGHJUMP,skill_lv,1); - if(!iMap->count_oncell(src->m,x,y,BL_PC|BL_NPC|BL_MOB) && iMap->getcell(src->m,x,y,CELL_CHKREACH)) { - clif->slide(src,x,y); - unit_movepos(src, x, y, 1, 0); + if( sd->state.autocast || ( (sd->skillitem == AL_TELEPORT || battle_config.skip_teleport_lv1_menu) && skill_lv == 1 ) || skill_lv == 3 ) + { + if( skill_lv == 1 ) + pc->randomwarp(sd,CLR_TELEPORT); + else + pc->setpos(sd,sd->status.save_point.map,sd->status.save_point.x,sd->status.save_point.y,CLR_TELEPORT); + break; } - } + + clif->skill_nodamage(src,bl,skill_id,skill_lv,1); + if( skill_lv == 1 ) + clif->skill_warppoint(sd,skill_id,skill_lv, (unsigned short)-1,0,0,0); + else + clif->skill_warppoint(sd,skill_id,skill_lv, (unsigned short)-1,sd->status.save_point.map,0,0); + } else + unit_warp(bl,-1,-1,-1,CLR_TELEPORT); break; - case SA_CASTCANCEL: - case SO_SPELLFIST: + case NPC_EXPULSION: clif->skill_nodamage(src,bl,skill_id,skill_lv,1); - unit_skillcastcancel(src,1); - if(sd) { - int sp = skill->get_sp(sd->skill_id_old,sd->skill_lv_old); - if( skill_id == SO_SPELLFIST ){ - sc_start4(src,type,100,skill_lv+1,skill_lv,sd->skill_id_old,sd->skill_lv_old,skill->get_time(skill_id,skill_lv)); - sd->skill_id_old = sd->skill_lv_old = 0; - break; - } - sp = sp * (90 - (skill_lv-1)*20) / 100; - if(sp < 0) sp = 0; - status_zap(src, 0, sp); - } + unit_warp(bl,-1,-1,-1,CLR_TELEPORT); break; - case SA_SPELLBREAKER: - { - int sp; - if(tsc && tsc->data[SC_MAGICROD]) { - sp = skill->get_sp(skill_id,skill_lv); - sp = sp * tsc->data[SC_MAGICROD]->val2 / 100; - if(sp < 1) sp = 1; - status_heal(bl,0,sp,2); - status_percent_damage(bl, src, 0, -20, false); //20% max SP damage. - } else { - struct unit_data *ud = unit_bl2ud(bl); - int bl_skill_id=0,bl_skill_lv=0,hp = 0; - if (!ud || ud->skilltimer == INVALID_TIMER) - break; //Nothing to cancel. - bl_skill_id = ud->skill_id; - bl_skill_lv = ud->skill_lv; - if (tstatus->mode & MD_BOSS) - { //Only 10% success chance against bosses. [Skotlex] - if (rnd()%100 < 90) - { - if (sd) clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); - break; - } - } else if (!dstsd || map_flag_vs(bl->m)) //HP damage only on pvp-maps when against players. - hp = tstatus->max_hp/50; //Recover 2% HP [Skotlex] + case AL_HOLYWATER: + if(sd) { + if (skill->produce_mix(sd, skill_id, 523, 0, 0, 0, 1)) clif->skill_nodamage(src,bl,skill_id,skill_lv,1); - unit_skillcastcancel(bl,0); - sp = skill->get_sp(bl_skill_id,bl_skill_lv); - status_zap(bl, hp, sp); - - if (hp && skill_lv >= 5) - hp>>=1; //Recover half damaged HP at level 5 [Skotlex] - else - hp = 0; - - if (sp) //Recover some of the SP used - sp = sp*(25*(skill_lv-1))/100; - - if(hp || sp) - status_heal(src, hp, sp, 2); - } + else + clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); } break; - case SA_MAGICROD: - clif->skill_nodamage(src,src,SA_MAGICROD,skill_lv,1); - sc_start(bl,type,100,skill_lv,skill->get_time(skill_id,skill_lv)); - break; - case SA_AUTOSPELL: - clif->skill_nodamage(src,bl,skill_id,skill_lv,1); - if(sd) - clif->autospell(sd,skill_lv); - else { - int maxlv=1,spellid=0; - static const int spellarray[3] = { MG_COLDBOLT,MG_FIREBOLT,MG_LIGHTNINGBOLT }; - if(skill_lv >= 10) { - spellid = MG_FROSTDIVER; - // if (tsc && tsc->data[SC_SPIRIT] && tsc->data[SC_SPIRIT]->val2 == SA_SAGE) - // maxlv = 10; - // else - maxlv = skill_lv - 9; - } - else if(skill_lv >=8) { - spellid = MG_FIREBALL; - maxlv = skill_lv - 7; - } - else if(skill_lv >=5) { - spellid = MG_SOULSTRIKE; - maxlv = skill_lv - 4; - } - else if(skill_lv >=2) { - int i = rnd()%3; - spellid = spellarray[i]; - maxlv = skill_lv - 1; - } - else if(skill_lv > 0) { - spellid = MG_NAPALMBEAT; - maxlv = 3; + + case TF_PICKSTONE: + if(sd) { + int eflag; + struct item item_tmp; + struct block_list tbl; + clif->skill_nodamage(src,bl,skill_id,skill_lv,1); + memset(&item_tmp,0,sizeof(item_tmp)); + memset(&tbl,0,sizeof(tbl)); // [MouseJstr] + item_tmp.nameid = ITEMID_STONE; + item_tmp.identify = 1; + tbl.id = 0; + clif->takeitem(&sd->bl,&tbl); + eflag = pc->additem(sd,&item_tmp,1,LOG_TYPE_PRODUCE); + if(eflag) { + clif->additem(sd,0,0,eflag); + iMap->addflooritem(&item_tmp,1,sd->bl.m,sd->bl.x,sd->bl.y,0,0,0,0); } - if(spellid > 0) - sc_start4(src,SC_AUTOSPELL,100,skill_lv,spellid,maxlv,0, - skill->get_time(SA_AUTOSPELL,skill_lv)); } break; - - case BS_GREED: - if(sd){ + case ASC_CDP: + if(sd) { clif->skill_nodamage(src,bl,skill_id,skill_lv,1); - iMap->foreachinrange(skill->greed,bl, - skill->get_splash(skill_id, skill_lv),BL_ITEM,bl); + skill->produce_mix(sd, skill_id, 678, 0, 0, 0, 1); //Produce a Deadly Poison Bottle. } break; - case SA_ELEMENTWATER: - case SA_ELEMENTFIRE: - case SA_ELEMENTGROUND: - case SA_ELEMENTWIND: - if(sd && !dstmd) //Only works on monsters. + case RG_STRIPWEAPON: + case RG_STRIPSHIELD: + case RG_STRIPARMOR: + case RG_STRIPHELM: + case ST_FULLSTRIP: + case GC_WEAPONCRUSH: + case SC_STRIPACCESSARY: { + unsigned short location = 0; + int d = 0; + + //Rate in percent + if ( skill_id == ST_FULLSTRIP ) { + i = 5 + 2*skill_lv + (sstatus->dex - tstatus->dex)/5; + } else if( skill_id == SC_STRIPACCESSARY ) { + i = 12 + 2 * skill_lv + (sstatus->dex - tstatus->dex)/5; + } else { + i = 5 + 5*skill_lv + (sstatus->dex - tstatus->dex)/5; + } + + if (i < 5) i = 5; //Minimum rate 5% + + //Duration in ms + if( skill_id == GC_WEAPONCRUSH){ + d = skill->get_time(skill_id,skill_lv); + if(bl->type == BL_PC) + d += skill_lv * 15 + (sstatus->dex - tstatus->dex); + else + d += skill_lv * 30 + (sstatus->dex - tstatus->dex) / 2; + }else + d = skill->get_time(skill_id,skill_lv) + (sstatus->dex - tstatus->dex)*500; + + if (d < 0) d = 0; //Minimum duration 0ms + + switch (skill_id) { + case RG_STRIPWEAPON: + case GC_WEAPONCRUSH: + location = EQP_WEAPON; break; - if(tstatus->mode&MD_BOSS) + case RG_STRIPSHIELD: + location = EQP_SHIELD; break; - case NPC_ATTRICHANGE: - case NPC_CHANGEWATER: - case NPC_CHANGEGROUND: - case NPC_CHANGEFIRE: - case NPC_CHANGEWIND: - case NPC_CHANGEPOISON: - case NPC_CHANGEHOLY: - case NPC_CHANGEDARKNESS: - case NPC_CHANGETELEKINESIS: - clif->skill_nodamage(src,bl,skill_id,skill_lv, - sc_start2(bl, type, 100, skill_lv, skill->get_ele(skill_id,skill_lv), - skill->get_time(skill_id, skill_lv))); - break; - case NPC_CHANGEUNDEAD: - //This skill should fail if target is wearing bathory/evil druid card [Brainstorm] - //TO-DO This is ugly, fix it - if(tstatus->def_ele==ELE_UNDEAD || tstatus->def_ele==ELE_DARK) break; - clif->skill_nodamage(src,bl,skill_id,skill_lv, - sc_start2(bl, type, 100, skill_lv, skill->get_ele(skill_id,skill_lv), - skill->get_time(skill_id, skill_lv))); - break; - - case NPC_PROVOCATION: - clif->skill_nodamage(src,bl,skill_id,skill_lv,1); - if (md) mob_unlocktarget(md, tick); - break; + case RG_STRIPARMOR: + location = EQP_ARMOR; + break; + case RG_STRIPHELM: + location = EQP_HELM; + break; + case ST_FULLSTRIP: + location = EQP_WEAPON|EQP_SHIELD|EQP_ARMOR|EQP_HELM; + break; + case SC_STRIPACCESSARY: + location = EQP_ACC; + break; + } - case NPC_KEEPING: - case NPC_BARRIER: + //Special message when trying to use strip on FCP [Jobbie] + if( sd && skill_id == ST_FULLSTRIP && tsc && tsc->data[SC_PROTECTWEAPON] && tsc->data[SC_PROTECTHELM] && tsc->data[SC_PROTECTARMOR] && tsc->data[SC_PROTECTSHIELD]) { - int skill_time = skill->get_time(skill_id,skill_lv); - struct unit_data *ud = unit_bl2ud(bl); - if (clif->skill_nodamage(src,bl,skill_id,skill_lv, - sc_start(bl,type,100,skill_lv,skill_time)) - && ud) { //Disable attacking/acting/moving for skill's duration. - ud->attackabletime = - ud->canact_tick = - ud->canmove_tick = tick + skill_time; - } + clif->gospel_info(sd, 0x28); + break; } - break; - case NPC_REBIRTH: - if( md && md->state.rebirth ) - break; // only works once - sc_start(bl,type,100,skill_lv,-1); - break; + //Attempts to strip at rate i and duration d + if( (i = skill->strip_equip(bl, location, i, skill_lv, d)) || (skill_id != ST_FULLSTRIP && skill_id != GC_WEAPONCRUSH ) ) + clif->skill_nodamage(src,bl,skill_id,skill_lv,i); - case NPC_DARKBLESSING: - clif->skill_nodamage(src,bl,skill_id,skill_lv, - sc_start2(bl,type,(50+skill_lv*5),skill_lv,skill_lv,skill->get_time2(skill_id,skill_lv))); + //Nothing stripped. + if( sd && !i ) + clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); break; + } - case NPC_LICK: - status_zap(bl, 0, 100); - clif->skill_nodamage(src,bl,skill_id,skill_lv, - sc_start(bl,type,(skill_lv*5),skill_lv,skill->get_time2(skill_id,skill_lv))); - break; + case AM_BERSERKPITCHER: + case AM_POTIONPITCHER: { + int i,sp = 0; + int64 hp = 0; + if( dstmd && dstmd->class_ == MOBID_EMPERIUM ) { + iMap->freeblock_unlock(); + return 1; + } + if( sd ) { + int x,bonus=100; + x = skill_lv%11 - 1; + i = pc->search_inventory(sd,skill_db[skill_id].itemid[x]); + if( i < 0 || skill_db[skill_id].itemid[x] <= 0 ) { + clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); + iMap->freeblock_unlock(); + return 1; + } + if(sd->inventory_data[i] == NULL || sd->status.inventory[i].amount < skill_db[skill_id].amount[x]) { + clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); + iMap->freeblock_unlock(); + return 1; + } + if( skill_id == AM_BERSERKPITCHER ) { + if( dstsd && dstsd->status.base_level < (unsigned int)sd->inventory_data[i]->elv ) { + clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); + iMap->freeblock_unlock(); + return 1; + } + } + potion_flag = 1; + potion_hp = potion_sp = potion_per_hp = potion_per_sp = 0; + potion_target = bl->id; + run_script(sd->inventory_data[i]->script,0,sd->bl.id,0); + potion_flag = potion_target = 0; + if( sd->sc.data[SC_SOULLINK] && sd->sc.data[SC_SOULLINK]->val2 == SL_ALCHEMIST ) + bonus += sd->status.base_level; + if( potion_per_hp > 0 || potion_per_sp > 0 ) { + hp = tstatus->max_hp * potion_per_hp / 100; + hp = hp * (100 + pc->checkskill(sd,AM_POTIONPITCHER)*10 + pc->checkskill(sd,AM_LEARNINGPOTION)*5)*bonus/10000; + if( dstsd ) { + sp = dstsd->status.max_sp * potion_per_sp / 100; + sp = sp * (100 + pc->checkskill(sd,AM_POTIONPITCHER)*10 + pc->checkskill(sd,AM_LEARNINGPOTION)*5)*bonus/10000; + } + } else { + if( potion_hp > 0 ) { + hp = potion_hp * (100 + pc->checkskill(sd,AM_POTIONPITCHER)*10 + pc->checkskill(sd,AM_LEARNINGPOTION)*5)*bonus/10000; + hp = hp * (100 + (tstatus->vit<<1)) / 100; + if( dstsd ) + hp = hp * (100 + pc->checkskill(dstsd,SM_RECOVERY)*10) / 100; + } + if( potion_sp > 0 ) { + sp = potion_sp * (100 + pc->checkskill(sd,AM_POTIONPITCHER)*10 + pc->checkskill(sd,AM_LEARNINGPOTION)*5)*bonus/10000; + sp = sp * (100 + (tstatus->int_<<1)) / 100; + if( dstsd ) + sp = sp * (100 + pc->checkskill(dstsd,MG_SRECOVERY)*10) / 100; + } + } - case NPC_SUICIDE: - clif->skill_nodamage(src,bl,skill_id,skill_lv,1); - status_kill(src); //When suiciding, neither exp nor drops is given. - break; + if (sd->itemgrouphealrate[IG_POTION]>0) { + hp += hp * sd->itemgrouphealrate[IG_POTION] / 100; + sp += sp * sd->itemgrouphealrate[IG_POTION] / 100; + } - case NPC_SUMMONSLAVE: - case NPC_SUMMONMONSTER: - if(md && md->skill_idx >= 0) - mob_summonslave(md,md->db->skill[md->skill_idx].val,skill_lv,skill_id); + if( (i = pc->skillheal_bonus(sd, skill_id)) ) { + hp += hp * i / 100; + sp += sp * i / 100; + } + } else { + hp = (1 + rnd()%400) * (100 + skill_lv*10) / 100; + hp = hp * (100 + (tstatus->vit<<1)) / 100; + if( dstsd ) + hp = hp * (100 + pc->checkskill(dstsd,SM_RECOVERY)*10) / 100; + } + if( dstsd && (i = pc->skillheal2_bonus(dstsd, skill_id)) ) { + hp += hp * i / 100; + sp += sp * i / 100; + } + if( tsc && tsc->count ) { + if( tsc->data[SC_CRITICALWOUND] ) { + hp -= hp * tsc->data[SC_CRITICALWOUND]->val2 / 100; + sp -= sp * tsc->data[SC_CRITICALWOUND]->val2 / 100; + } + if( tsc->data[SC_DEATHHURT] ) { + hp -= hp * 20 / 100; + sp -= sp * 20 / 100; + } + if( tsc->data[SC_WATER_INSIGNIA] && tsc->data[SC_WATER_INSIGNIA]->val1 == 2 ) { + hp += hp / 10; + sp += sp / 10; + } + } + clif->skill_nodamage(src,bl,skill_id,skill_lv,1); + if( hp > 0 || (skill_id == AM_POTIONPITCHER && sp <= 0) ) + clif->skill_nodamage(NULL,bl,AL_HEAL,(int)hp,1); + if( sp > 0 ) + clif->skill_nodamage(NULL,bl,MG_SRECOVERY,sp,1); + #ifdef RENEWAL + if( tsc && tsc->data[SC_EXTREMITYFIST2] ) + sp = 0; + #endif + status_heal(bl,(int)hp,sp,0); + } break; + case AM_CP_WEAPON: + case AM_CP_SHIELD: + case AM_CP_ARMOR: + case AM_CP_HELM: + { + unsigned int equip[] = {EQP_WEAPON, EQP_SHIELD, EQP_ARMOR, EQP_HEAD_TOP}; - case NPC_CALLSLAVE: - mob_warpslave(src,MOB_SLAVEDISTANCE); - break; + if( sd && ( bl->type != BL_PC || ( dstsd && pc->checkequip(dstsd,equip[skill_id - AM_CP_WEAPON]) < 0 ) ) ){ + clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); + iMap->freeblock_unlock(); // Don't consume item requirements + return 0; + } - case NPC_RANDOMMOVE: - if (md) { - md->next_walktime = tick - 1; - mob_randomwalk(md,tick); + clif->skill_nodamage(src,bl,skill_id,skill_lv, + sc_start(bl,type,100,skill_lv,skill->get_time(skill_id,skill_lv))); } break; - - case NPC_SPEEDUP: - { - // or does it increase casting rate? just a guess xD - int i = SC_ASPDPOTION0 + skill_lv - 1; - if (i > SC_ASPDPOTION3) - i = SC_ASPDPOTION3; - clif->skill_nodamage(src,bl,skill_id,skill_lv, - sc_start(bl,(sc_type)i,100,skill_lv,skill_lv * 60000)); + case AM_TWILIGHT1: + if (sd) { + clif->skill_nodamage(src,bl,skill_id,skill_lv,1); + //Prepare 200 White Potions. + if (!skill->produce_mix(sd, skill_id, 504, 0, 0, 0, 200)) + clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); } break; - - case NPC_REVENGE: - // not really needed... but adding here anyway ^^ - if (md && md->master_id > 0) { - struct block_list *mbl, *tbl; - if ((mbl = iMap->id2bl(md->master_id)) == NULL || - (tbl = battle->get_targeted(mbl)) == NULL) + case AM_TWILIGHT2: + if (sd) { + clif->skill_nodamage(src,bl,skill_id,skill_lv,1); + //Prepare 200 Slim White Potions. + if (!skill->produce_mix(sd, skill_id, 547, 0, 0, 0, 200)) + clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); + } + break; + case AM_TWILIGHT3: + if (sd) { + int ebottle = pc->search_inventory(sd,713); + if( ebottle >= 0 ) + ebottle = sd->status.inventory[ebottle].amount; + //check if you can produce all three, if not, then fail: + if (!skill->can_produce_mix(sd,970,-1, 100) //100 Alcohol + || !skill->can_produce_mix(sd,7136,-1, 50) //50 Acid Bottle + || !skill->can_produce_mix(sd,7135,-1, 50) //50 Flame Bottle + || ebottle < 200 //200 empty bottle are required at total. + ) { + clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); break; - md->state.provoke_flag = tbl->id; - mob_target(md, tbl, sstatus->rhw.range); + } + clif->skill_nodamage(src,bl,skill_id,skill_lv,1); + skill->produce_mix(sd, skill_id, 970, 0, 0, 0, 100); + skill->produce_mix(sd, skill_id, 7136, 0, 0, 0, 50); + skill->produce_mix(sd, skill_id, 7135, 0, 0, 0, 50); } break; - - case NPC_RUN: + case SA_DISPELL: + if (flag&1 || (i = skill->get_splash(skill_id, skill_lv)) < 1) { - const int mask[8][2] = {{0,-1},{1,-1},{1,0},{1,1},{0,1},{-1,1},{-1,0},{-1,-1}}; - uint8 dir = (bl == src)?unit_getdir(src):iMap->calc_dir(src,bl->x,bl->y); //If cast on self, run forward, else run away. - unit_stop_attack(src); - //Run skillv tiles overriding the can-move check. - if (unit_walktoxy(src, src->x + skill_lv * mask[dir][0], src->y + skill_lv * mask[dir][1], 2) && md) - md->state.skillstate = MSS_WALK; //Otherwise it isn't updated in the ai. + clif->skill_nodamage(src,bl,skill_id,skill_lv,1); + if((dstsd && (dstsd->class_&MAPID_UPPERMASK) == MAPID_SOUL_LINKER) + || (tsc && tsc->data[SC_SOULLINK] && tsc->data[SC_SOULLINK]->val2 == SL_ROGUE) //Rogue's spirit defends againt dispel. + || rnd()%100 >= 50+10*skill_lv ) + { + if (sd) + clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); + break; + } + if(status_isimmune(bl) || !tsc || !tsc->count) + break; + + if( sd && dstsd && !map_flag_vs(sd->bl.m) && sd->status.guild_id == dstsd->status.guild_id ) { + clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); + break; + } + + for(i = 0; i < SC_MAX; i++) + { + if ( !tsc->data[i] ) + continue; + if( SC_COMMON_MAX < i ){ + if ( status_get_sc_type(i)&SC_NO_DISPELL ) + continue; + } + switch (i) { + /** + * bugreport:4888 these songs may only be dispelled if you're not in their song area anymore + **/ + case SC_WHISTLE: + case SC_ASSNCROS: + case SC_POEMBRAGI: + case SC_APPLEIDUN: + case SC_HUMMING: + case SC_DONTFORGETME: + case SC_FORTUNE: + case SC_SERVICEFORYOU: + if( tsc->data[i]->val4 ) //val4 = out-of-song-area + continue; + break; + case SC_ASSUMPTIO: + if( bl->type == BL_MOB ) + continue; + break; + case SC_BERSERK: + case SC_SATURDAY_NIGHT_FEVER: + tsc->data[i]->val2=0; //Mark a dispelled berserk to avoid setting hp to 100 by setting hp penalty to 0. + break; + } + status_change_end(bl, (sc_type)i, INVALID_TIMER); + } + break; } + //Affect all targets on splash area. + iMap->foreachinrange(skill->area_sub, bl, i, BL_CHAR, + src, skill_id, skill_lv, tick, flag|1, + skill->castend_damage_id); break; - case NPC_TRANSFORMATION: - case NPC_METAMORPHOSIS: - if(md && md->skill_idx >= 0) { - int class_ = mob_random_class (md->db->skill[md->skill_idx].val,0); - if (skill_lv > 1) //Multiply the rest of mobs. [Skotlex] - mob_summonslave(md,md->db->skill[md->skill_idx].val,skill_lv-1,skill_id); - if (class_) mob_class_change(md, class_); - } + case TF_BACKSLIDING: //This is the correct implementation as per packet logging information. [Skotlex] + clif->skill_nodamage(src,bl,skill_id,skill_lv,1); + skill->blown(src,bl,skill->get_blewcount(skill_id,skill_lv),unit_getdir(bl),0); break; - case NPC_EMOTION_ON: - case NPC_EMOTION: - //val[0] is the emotion to use. - //NPC_EMOTION & NPC_EMOTION_ON can change a mob's mode 'permanently' [Skotlex] - //val[1] 'sets' the mode - //val[2] adds to the current mode - //val[3] removes from the current mode - //val[4] if set, asks to delete the previous mode change. - if(md && md->skill_idx >= 0 && tsc) { - clif->emotion(bl, md->db->skill[md->skill_idx].val[0]); - if(md->db->skill[md->skill_idx].val[4] && tsce) - status_change_end(bl, type, INVALID_TIMER); + case TK_HIGHJUMP: + { + int x,y, dir = unit_getdir(src); - //If mode gets set by NPC_EMOTION then the target should be reset [Playtester] - if(skill_id == NPC_EMOTION && md->db->skill[md->skill_idx].val[1]) - mob_unlocktarget(md,tick); - - if(md->db->skill[md->skill_idx].val[1] || md->db->skill[md->skill_idx].val[2]) - sc_start4(src, type, 100, skill_lv, - md->db->skill[md->skill_idx].val[1], - md->db->skill[md->skill_idx].val[2], - md->db->skill[md->skill_idx].val[3], - skill->get_time(skill_id, skill_lv)); + //Fails on noteleport maps, except for GvG and BG maps [Skotlex] + if( map[src->m].flag.noteleport && + !(map[src->m].flag.battleground || map_flag_gvg2(src->m) ) + ) { + x = src->x; + y = src->y; + } else { + x = src->x + dirx[dir]*skill_lv*2; + y = src->y + diry[dir]*skill_lv*2; + } + + clif->skill_nodamage(src,bl,TK_HIGHJUMP,skill_lv,1); + if(!iMap->count_oncell(src->m,x,y,BL_PC|BL_NPC|BL_MOB) && iMap->getcell(src->m,x,y,CELL_CHKREACH)) { + clif->slide(src,x,y); + unit_movepos(src, x, y, 1, 0); + } } break; - case NPC_POWERUP: - sc_start(bl,SC_INCATKRATE,100,200,skill->get_time(skill_id, skill_lv)); - clif->skill_nodamage(src,bl,skill_id,skill_lv, - sc_start(bl,type,100,100,skill->get_time(skill_id, skill_lv))); + case SA_CASTCANCEL: + case SO_SPELLFIST: + clif->skill_nodamage(src,bl,skill_id,skill_lv,1); + unit_skillcastcancel(src,1); + if(sd) { + int sp = skill->get_sp(sd->skill_id_old,sd->skill_lv_old); + if( skill_id == SO_SPELLFIST ){ + sc_start4(src,type,100,skill_lv+1,skill_lv,sd->skill_id_old,sd->skill_lv_old,skill->get_time(skill_id,skill_lv)); + sd->skill_id_old = sd->skill_lv_old = 0; + break; + } + sp = sp * (90 - (skill_lv-1)*20) / 100; + if(sp < 0) sp = 0; + status_zap(src, 0, sp); + } break; + case SA_SPELLBREAKER: + { + int sp; + if(tsc && tsc->data[SC_MAGICROD]) { + sp = skill->get_sp(skill_id,skill_lv); + sp = sp * tsc->data[SC_MAGICROD]->val2 / 100; + if(sp < 1) sp = 1; + status_heal(bl,0,sp,2); + status_percent_damage(bl, src, 0, -20, false); //20% max SP damage. + } else { + struct unit_data *ud = unit_bl2ud(bl); + int bl_skill_id=0,bl_skill_lv=0,hp = 0; + if (!ud || ud->skilltimer == INVALID_TIMER) + break; //Nothing to cancel. + bl_skill_id = ud->skill_id; + bl_skill_lv = ud->skill_lv; + if (tstatus->mode & MD_BOSS) + { //Only 10% success chance against bosses. [Skotlex] + if (rnd()%100 < 90) + { + if (sd) clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); + break; + } + } else if (!dstsd || map_flag_vs(bl->m)) //HP damage only on pvp-maps when against players. + hp = tstatus->max_hp/50; //Recover 2% HP [Skotlex] - case NPC_AGIUP: - sc_start(bl,SC_SPEEDUP1,100,skill_lv,skill->get_time(skill_id, skill_lv)); - clif->skill_nodamage(src,bl,skill_id,skill_lv, - sc_start(bl,type,100,100,skill->get_time(skill_id, skill_lv))); - break; + clif->skill_nodamage(src,bl,skill_id,skill_lv,1); + unit_skillcastcancel(bl,0); + sp = skill->get_sp(bl_skill_id,bl_skill_lv); + status_zap(bl, hp, sp); - case NPC_INVISIBLE: - //Have val4 passed as 6 is for "infinite cloak" (do not end on attack/skill use). - clif->skill_nodamage(src,bl,skill_id,skill_lv, - sc_start4(bl,type,100,skill_lv,0,0,6,skill->get_time(skill_id,skill_lv))); - break; + if (hp && skill_lv >= 5) + hp>>=1; //Recover half damaged HP at level 5 [Skotlex] + else + hp = 0; - case NPC_SIEGEMODE: - // not sure what it does - clif->skill_nodamage(src,bl,skill_id,skill_lv,1); - break; + if (sp) //Recover some of the SP used + sp = sp*(25*(skill_lv-1))/100; - case WE_MALE: - { - int hp_rate=(!skill_lv)? 0:skill_db[skill_id].hp_rate[skill_lv-1]; - int gain_hp= tstatus->max_hp*abs(hp_rate)/100; // The earned is the same % of the target HP than it costed the caster. [Skotlex] - clif->skill_nodamage(src,bl,skill_id,status_heal(bl, gain_hp, 0, 0),1); + if(hp || sp) + status_heal(src, hp, sp, 2); + } } break; - case WE_FEMALE: - { - int sp_rate=(!skill_lv)? 0:skill_db[skill_id].sp_rate[skill_lv-1]; - int gain_sp=tstatus->max_sp*abs(sp_rate)/100;// The earned is the same % of the target SP than it costed the caster. [Skotlex] - clif->skill_nodamage(src,bl,skill_id,status_heal(bl, 0, gain_sp, 0),1); - } + case SA_MAGICROD: + clif->skill_nodamage(src,src,SA_MAGICROD,skill_lv,1); + sc_start(bl,type,100,skill_lv,skill->get_time(skill_id,skill_lv)); break; - - // parent-baby skills - case WE_BABY: - if(sd){ - struct map_session_data *f_sd = pc->get_father(sd); - struct map_session_data *m_sd = pc->get_mother(sd); - // if neither was found - if(!f_sd && !m_sd){ - clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); - iMap->freeblock_unlock(); - return 0; + case SA_AUTOSPELL: + clif->skill_nodamage(src,bl,skill_id,skill_lv,1); + if(sd) + clif->autospell(sd,skill_lv); + else { + int maxlv=1,spellid=0; + static const int spellarray[3] = { MG_COLDBOLT,MG_FIREBOLT,MG_LIGHTNINGBOLT }; + if(skill_lv >= 10) { + spellid = MG_FROSTDIVER; + // if (tsc && tsc->data[SC_SOULLINK] && tsc->data[SC_SOULLINK]->val2 == SA_SAGE) + // maxlv = 10; + // else + maxlv = skill_lv - 9; } - status_change_start(bl,SC_STUN,10000,skill_lv,0,0,0,skill->get_time2(skill_id,skill_lv),8); - if (f_sd) sc_start(&f_sd->bl,type,100,skill_lv,skill->get_time(skill_id,skill_lv)); - if (m_sd) sc_start(&m_sd->bl,type,100,skill_lv,skill->get_time(skill_id,skill_lv)); - } - break; - - case PF_HPCONVERSION: - { - int hp, sp; - hp = sstatus->max_hp/10; - sp = hp * 10 * skill_lv / 100; - if (!status_charge(src,hp,0)) { - if (sd) clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); - break; + else if(skill_lv >=8) { + spellid = MG_FIREBALL; + maxlv = skill_lv - 7; } - clif->skill_nodamage(src, bl, skill_id, skill_lv, 1); - status_heal(bl,0,sp,2); + else if(skill_lv >=5) { + spellid = MG_SOULSTRIKE; + maxlv = skill_lv - 4; + } + else if(skill_lv >=2) { + int i = rnd()%3; + spellid = spellarray[i]; + maxlv = skill_lv - 1; + } + else if(skill_lv > 0) { + spellid = MG_NAPALMBEAT; + maxlv = 3; + } + if(spellid > 0) + sc_start4(src,SC_AUTOSPELL,100,skill_lv,spellid,maxlv,0, + skill->get_time(SA_AUTOSPELL,skill_lv)); } break; - case MA_REMOVETRAP: - case HT_REMOVETRAP: - { - struct skill_unit* su; - struct skill_unit_group* sg; - su = BL_CAST(BL_SKILL, bl); - - // Mercenaries can remove any trap - // Players can only remove their own traps or traps on Vs maps. - if( su && (sg = su->group) && (src->type == BL_MER || sg->src_id == src->id || map_flag_vs(bl->m)) && (skill->get_inf2(sg->skill_id)&INF2_TRAP) ) - { - clif->skill_nodamage(src, bl, skill_id, skill_lv, 1); - if( sd && !(sg->unit_id == UNT_USED_TRAPS || (sg->unit_id == UNT_ANKLESNARE && sg->val2 != 0 )) ) - { // prevent picking up expired traps - if( battle_config.skill_removetrap_type ) - { // get back all items used to deploy the trap - for( i = 0; i < 10; i++ ) - { - if( skill_db[su->group->skill_id].itemid[i] > 0 ) - { - int flag; - struct item item_tmp; - memset(&item_tmp,0,sizeof(item_tmp)); - item_tmp.nameid = skill_db[su->group->skill_id].itemid[i]; - item_tmp.identify = 1; - if( item_tmp.nameid && (flag=pc->additem(sd,&item_tmp,skill_db[su->group->skill_id].amount[i],LOG_TYPE_OTHER)) ) - { - clif->additem(sd,0,0,flag); - iMap->addflooritem(&item_tmp,skill_db[su->group->skill_id].amount[i],sd->bl.m,sd->bl.x,sd->bl.y,0,0,0,0); - } - } - } - } - else - { // get back 1 trap - struct item item_tmp; - memset(&item_tmp,0,sizeof(item_tmp)); - item_tmp.nameid = su->group->item_id?su->group->item_id:ITEMID_TRAP; - item_tmp.identify = 1; - if( item_tmp.nameid && (flag=pc->additem(sd,&item_tmp,1,LOG_TYPE_OTHER)) ) - { - clif->additem(sd,0,0,flag); - iMap->addflooritem(&item_tmp,1,sd->bl.m,sd->bl.x,sd->bl.y,0,0,0,0); - } - } - } - skill->delunit(su); - }else if(sd) - clif->skill_fail(sd, skill_id, USESKILL_FAIL_LEVEL, 0); - + case BS_GREED: + if(sd){ + clif->skill_nodamage(src,bl,skill_id,skill_lv,1); + iMap->foreachinrange(skill->greed,bl, + skill->get_splash(skill_id, skill_lv),BL_ITEM,bl); } break; - case HT_SPRINGTRAP: + + case SA_ELEMENTWATER: + case SA_ELEMENTFIRE: + case SA_ELEMENTGROUND: + case SA_ELEMENTWIND: + if(sd && !dstmd) //Only works on monsters. + break; + if(tstatus->mode&MD_BOSS) + break; + case NPC_ATTRICHANGE: + case NPC_CHANGEWATER: + case NPC_CHANGEGROUND: + case NPC_CHANGEFIRE: + case NPC_CHANGEWIND: + case NPC_CHANGEPOISON: + case NPC_CHANGEHOLY: + case NPC_CHANGEDARKNESS: + case NPC_CHANGETELEKINESIS: + clif->skill_nodamage(src,bl,skill_id,skill_lv, + sc_start2(bl, type, 100, skill_lv, skill->get_ele(skill_id,skill_lv), + skill->get_time(skill_id, skill_lv))); + break; + case NPC_CHANGEUNDEAD: + //This skill should fail if target is wearing bathory/evil druid card [Brainstorm] + //TO-DO This is ugly, fix it + if(tstatus->def_ele==ELE_UNDEAD || tstatus->def_ele==ELE_DARK) break; + clif->skill_nodamage(src,bl,skill_id,skill_lv, + sc_start2(bl, type, 100, skill_lv, skill->get_ele(skill_id,skill_lv), + skill->get_time(skill_id, skill_lv))); + break; + + case NPC_PROVOCATION: clif->skill_nodamage(src,bl,skill_id,skill_lv,1); + if (md) mob_unlocktarget(md, tick); + break; + + case NPC_KEEPING: + case NPC_BARRIER: { - struct skill_unit *su=NULL; - if((bl->type==BL_SKILL) && (su=(struct skill_unit *)bl) && (su->group) ){ - switch(su->group->unit_id){ - case UNT_ANKLESNARE: // ankle snare - if (su->group->val2 != 0) - // if it is already trapping something don't spring it, - // remove trap should be used instead - break; - // otherwise fallthrough to below - case UNT_BLASTMINE: - case UNT_SKIDTRAP: - case UNT_LANDMINE: - case UNT_SHOCKWAVE: - case UNT_SANDMAN: - case UNT_FLASHER: - case UNT_FREEZINGTRAP: - case UNT_CLAYMORETRAP: - case UNT_TALKIEBOX: - su->group->unit_id = UNT_USED_TRAPS; - clif->changetraplook(bl, UNT_USED_TRAPS); - su->group->limit=DIFF_TICK(tick+1500,su->group->tick); - su->limit=DIFF_TICK(tick+1500,su->group->tick); - } + int skill_time = skill->get_time(skill_id,skill_lv); + struct unit_data *ud = unit_bl2ud(bl); + if (clif->skill_nodamage(src,bl,skill_id,skill_lv, + sc_start(bl,type,100,skill_lv,skill_time)) + && ud) { //Disable attacking/acting/moving for skill's duration. + ud->attackabletime = + ud->canact_tick = + ud->canmove_tick = tick + skill_time; } } break; - case BD_ENCORE: - clif->skill_nodamage(src,bl,skill_id,skill_lv,1); - if(sd) - unit_skilluse_id(src,src->id,sd->skill_id_dance,sd->skill_lv_dance); + + case NPC_REBIRTH: + if( md && md->state.rebirth ) + break; // only works once + sc_start(bl,type,100,skill_lv,-1); break; - case AS_SPLASHER: - if(tstatus->mode&MD_BOSS - /** - * Renewal dropped the 3/4 hp requirement - **/ - #ifndef RENEWAL - || tstatus-> hp > tstatus->max_hp*3/4 - #endif - ) { - if (sd) clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); - iMap->freeblock_unlock(); - return 1; - } + case NPC_DARKBLESSING: clif->skill_nodamage(src,bl,skill_id,skill_lv, - sc_start4(bl,type,100,skill_lv,skill_id,src->id,skill->get_time(skill_id,skill_lv),1000)); - #ifndef RENEWAL - if (sd) skill->blockpc_start (sd, skill_id, skill->get_time(skill_id, skill_lv)+3000, false); - #endif + sc_start2(bl,type,(50+skill_lv*5),skill_lv,skill_lv,skill->get_time2(skill_id,skill_lv))); break; - case PF_MINDBREAKER: - { - if(tstatus->mode&MD_BOSS || battle->check_undead(tstatus->race,tstatus->def_ele) ) { - iMap->freeblock_unlock(); - return 1; - } - - if (tsce) - { //HelloKitty2 (?) explained that this silently fails when target is - //already inflicted. [Skotlex] - iMap->freeblock_unlock(); - return 1; - } + case NPC_LICK: + status_zap(bl, 0, 100); + clif->skill_nodamage(src,bl,skill_id,skill_lv, + sc_start(bl,type,(skill_lv*5),skill_lv,skill->get_time2(skill_id,skill_lv))); + break; - //Has a 55% + skill_lv*5% success chance. - if (!clif->skill_nodamage(src,bl,skill_id,skill_lv, - sc_start(bl,type,55+5*skill_lv,skill_lv,skill->get_time(skill_id,skill_lv)))) - { - if (sd) clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); - iMap->freeblock_unlock(); - return 0; - } + case NPC_SUICIDE: + clif->skill_nodamage(src,bl,skill_id,skill_lv,1); + status_kill(src); //When suiciding, neither exp nor drops is given. + break; - unit_skillcastcancel(bl,0); + case NPC_SUMMONSLAVE: + case NPC_SUMMONMONSTER: + if(md && md->skill_idx >= 0) + mob_summonslave(md,md->db->skill[md->skill_idx].val,skill_lv,skill_id); + break; - if(tsc && tsc->count){ - status_change_end(bl, SC_FREEZE, INVALID_TIMER); - if(tsc->data[SC_STONE] && tsc->opt1 == OPT1_STONE) - status_change_end(bl, SC_STONE, INVALID_TIMER); - status_change_end(bl, SC_SLEEP, INVALID_TIMER); - } + case NPC_CALLSLAVE: + mob_warpslave(src,MOB_SLAVEDISTANCE); + break; - if(dstmd) - mob_target(dstmd,src,skill->get_range2(src,skill_id,skill_lv)); + case NPC_RANDOMMOVE: + if (md) { + md->next_walktime = tick - 1; + mob_randomwalk(md,tick); } break; - case PF_SOULCHANGE: + case NPC_SPEEDUP: { - unsigned int sp1 = 0, sp2 = 0; - if (dstmd) { - if (dstmd->state.soul_change_flag) { - if(sd) clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); - break; - } - dstmd->state.soul_change_flag = 1; - sp2 = sstatus->max_sp * 3 /100; - status_heal(src, 0, sp2, 2); - clif->skill_nodamage(src,bl,skill_id,skill_lv,1); - break; - } - sp1 = sstatus->sp; - sp2 = tstatus->sp; - #ifdef RENEWAL - sp1 = sp1 / 2; - sp2 = sp2 / 2; - if( tsc && tsc->data[SC_EXTREMITYFIST2] ) - sp1 = tstatus->sp; - #endif - status_set_sp(src, sp2, 3); - status_set_sp(bl, sp1, 3); - clif->skill_nodamage(src,bl,skill_id,skill_lv,1); + // or does it increase casting rate? just a guess xD + int i = SC_ATTHASTE_POTION1 + skill_lv - 1; + if (i > SC_ATTHASTE_INFINITY) + i = SC_ATTHASTE_INFINITY; + clif->skill_nodamage(src,bl,skill_id,skill_lv, + sc_start(bl,(sc_type)i,100,skill_lv,skill_lv * 60000)); } break; - // Slim Pitcher - case CR_SLIMPITCHER: - // Updated to block Slim Pitcher from working on barricades and guardian stones. - if( dstmd && (dstmd->class_ == MOBID_EMPERIUM || (dstmd->class_ >= MOBID_BARRICADE1 && dstmd->class_ <= MOBID_GUARIDAN_STONE2)) ) - break; - if (potion_hp || potion_sp) { - int hp = potion_hp, sp = potion_sp; - hp = hp * (100 + (tstatus->vit<<1))/100; - sp = sp * (100 + (tstatus->int_<<1))/100; - if (dstsd) { - if (hp) - hp = hp * (100 + pc->checkskill(dstsd,SM_RECOVERY)*10 + pc->skillheal2_bonus(dstsd, skill_id))/100; - if (sp) - sp = sp * (100 + pc->checkskill(dstsd,MG_SRECOVERY)*10 + pc->skillheal2_bonus(dstsd, skill_id))/100; - } - if( tsc && tsc->count ) { - if (tsc->data[SC_CRITICALWOUND]) { - hp -= hp * tsc->data[SC_CRITICALWOUND]->val2 / 100; - sp -= sp * tsc->data[SC_CRITICALWOUND]->val2 / 100; - } - if (tsc->data[SC_DEATHHURT]) { - hp -= hp * 20 / 100; - sp -= sp * 20 / 100; - } - if( tsc->data[SC_WATER_INSIGNIA] && tsc->data[SC_WATER_INSIGNIA]->val1 == 2) { - hp += hp / 10; - sp += sp / 10; - } - } - if(hp > 0) - clif->skill_nodamage(NULL,bl,AL_HEAL,hp,1); - if(sp > 0) - clif->skill_nodamage(NULL,bl,MG_SRECOVERY,sp,1); - status_heal(bl,hp,sp,0); + case NPC_REVENGE: + // not really needed... but adding here anyway ^^ + if (md && md->master_id > 0) { + struct block_list *mbl, *tbl; + if ((mbl = iMap->id2bl(md->master_id)) == NULL || + (tbl = battle->get_targeted(mbl)) == NULL) + break; + md->state.provoke_flag = tbl->id; + mob_target(md, tbl, sstatus->rhw.range); } break; - // Full Chemical Protection - case CR_FULLPROTECTION: - { - unsigned int equip[] = {EQP_WEAPON, EQP_SHIELD, EQP_ARMOR, EQP_HEAD_TOP}; - int i, s = 0, skilltime = skill->get_time(skill_id,skill_lv); - for (i=0 ; i<4; i++) { - if( bl->type != BL_PC || ( dstsd && pc->checkequip(dstsd,equip[i]) < 0 ) ) - continue; - sc_start(bl,(sc_type)(SC_CP_WEAPON + i),100,skill_lv,skilltime); - s++; - } - if( sd && !s ){ - clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); - iMap->freeblock_unlock(); // Don't consume item requirements - return 0; - } - clif->skill_nodamage(src,bl,skill_id,skill_lv,1); + case NPC_RUN: + { + const int mask[8][2] = {{0,-1},{1,-1},{1,0},{1,1},{0,1},{-1,1},{-1,0},{-1,-1}}; + uint8 dir = (bl == src)?unit_getdir(src):iMap->calc_dir(src,bl->x,bl->y); //If cast on self, run forward, else run away. + unit_stop_attack(src); + //Run skillv tiles overriding the can-move check. + if (unit_walktoxy(src, src->x + skill_lv * mask[dir][0], src->y + skill_lv * mask[dir][1], 2) && md) + md->state.skillstate = MSS_WALK; //Otherwise it isn't updated in the ai. } break; - case RG_CLEANER: //AppleGirl - clif->skill_nodamage(src,bl,skill_id,skill_lv,1); - break; - - case CG_LONGINGFREEDOM: - { - if (tsc && !tsce && (tsce=tsc->data[SC_DANCING]) && tsce->val4 - && (tsce->val1&0xFFFF) != CG_MOONLIT) //Can't use Longing for Freedom while under Moonlight Petals. [Skotlex] - { - clif->skill_nodamage(src,bl,skill_id,skill_lv, - sc_start(bl,type,100,skill_lv,skill->get_time(skill_id,skill_lv))); - } + case NPC_TRANSFORMATION: + case NPC_METAMORPHOSIS: + if(md && md->skill_idx >= 0) { + int class_ = mob_random_class (md->db->skill[md->skill_idx].val,0); + if (skill_lv > 1) //Multiply the rest of mobs. [Skotlex] + mob_summonslave(md,md->db->skill[md->skill_idx].val,skill_lv-1,skill_id); + if (class_) mob_class_change(md, class_); } break; - case CG_TAROTCARD: - { - int eff, count = -1; - if( rnd() % 100 > skill_lv * 8 || (dstmd && ((dstmd->guardian_data && dstmd->class_ == MOBID_EMPERIUM) || mob_is_battleground(dstmd))) ) - { - if( sd ) - clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); + case NPC_EMOTION_ON: + case NPC_EMOTION: + //val[0] is the emotion to use. + //NPC_EMOTION & NPC_EMOTION_ON can change a mob's mode 'permanently' [Skotlex] + //val[1] 'sets' the mode + //val[2] adds to the current mode + //val[3] removes from the current mode + //val[4] if set, asks to delete the previous mode change. + if(md && md->skill_idx >= 0 && tsc) { + clif->emotion(bl, md->db->skill[md->skill_idx].val[0]); + if(md->db->skill[md->skill_idx].val[4] && tsce) + status_change_end(bl, type, INVALID_TIMER); - iMap->freeblock_unlock(); - return 0; - } - status_zap(src,0,skill_db[skill->get_index(skill_id)].sp[skill_lv]); // consume sp only if succeeded [Inkfish] - do { - eff = rnd() % 14; - clif->specialeffect(bl, 523 + eff, AREA); - switch (eff) - { - case 0: // heals SP to 0 - status_percent_damage(src, bl, 0, 100, false); - break; - case 1: // matk halved - sc_start(bl,SC_INCMATKRATE,100,-50,skill->get_time2(skill_id,skill_lv)); - break; - case 2: // all buffs removed - status_change_clear_buffs(bl,1); - break; - case 3: // 1000 damage, random armor destroyed - { - status_fix_damage(src, bl, 1000, 0); - clif->damage(src,bl,tick,0,0,1000,0,0,0); - if( !status_isdead(bl) ) { - int where[] = { EQP_ARMOR, EQP_SHIELD, EQP_HELM, EQP_SHOES, EQP_GARMENT }; - skill->break_equip(bl, where[rnd()%5], 10000, BCT_ENEMY); - } - } - break; - case 4: // atk halved - sc_start(bl,SC_INCATKRATE,100,-50,skill->get_time2(skill_id,skill_lv)); - break; - case 5: // 2000HP heal, random teleported - status_heal(src, 2000, 0, 0); - if( !map_flag_vs(bl->m) ) - unit_warp(bl, -1,-1,-1, CLR_TELEPORT); - break; - case 6: // random 2 other effects - if (count == -1) - count = 3; - else - count++; //Should not retrigger this one. - break; - case 7: // stop freeze or stoned - { - enum sc_type sc[] = { SC_STOP, SC_FREEZE, SC_STONE }; - sc_start(bl,sc[rnd()%3],100,skill_lv,skill->get_time2(skill_id,skill_lv)); - } - break; - case 8: // curse coma and poison - sc_start(bl,SC_COMA,100,skill_lv,skill->get_time2(skill_id,skill_lv)); - sc_start(bl,SC_CURSE,100,skill_lv,skill->get_time2(skill_id,skill_lv)); - sc_start(bl,SC_POISON,100,skill_lv,skill->get_time2(skill_id,skill_lv)); - break; - case 9: // confusion - sc_start(bl,SC_CONFUSION,100,skill_lv,skill->get_time2(skill_id,skill_lv)); - break; - case 10: // 6666 damage, atk matk halved, cursed - status_fix_damage(src, bl, 6666, 0); - clif->damage(src,bl,tick,0,0,6666,0,0,0); - sc_start(bl,SC_INCATKRATE,100,-50,skill->get_time2(skill_id,skill_lv)); - sc_start(bl,SC_INCMATKRATE,100,-50,skill->get_time2(skill_id,skill_lv)); - sc_start(bl,SC_CURSE,skill_lv,100,skill->get_time2(skill_id,skill_lv)); - break; - case 11: // 4444 damage - status_fix_damage(src, bl, 4444, 0); - clif->damage(src,bl,tick,0,0,4444,0,0,0); - break; - case 12: // stun - sc_start(bl,SC_STUN,100,skill_lv,5000); - break; - case 13: // atk,matk,hit,flee,def reduced - sc_start(bl,SC_INCATKRATE,100,-20,skill->get_time2(skill_id,skill_lv)); - sc_start(bl,SC_INCMATKRATE,100,-20,skill->get_time2(skill_id,skill_lv)); - sc_start(bl,SC_INCHITRATE,100,-20,skill->get_time2(skill_id,skill_lv)); - sc_start(bl,SC_INCFLEERATE,100,-20,skill->get_time2(skill_id,skill_lv)); - sc_start(bl,SC_INCDEFRATE,100,-20,skill->get_time2(skill_id,skill_lv)); - break; - default: - break; - } - } while ((--count) > 0); - clif->skill_nodamage(src,bl,skill_id,skill_lv,1); + //If mode gets set by NPC_EMOTION then the target should be reset [Playtester] + if(skill_id == NPC_EMOTION && md->db->skill[md->skill_idx].val[1]) + mob_unlocktarget(md,tick); + + if(md->db->skill[md->skill_idx].val[1] || md->db->skill[md->skill_idx].val[2]) + sc_start4(src, type, 100, skill_lv, + md->db->skill[md->skill_idx].val[1], + md->db->skill[md->skill_idx].val[2], + md->db->skill[md->skill_idx].val[3], + skill->get_time(skill_id, skill_lv)); } break; - case SL_ALCHEMIST: - case SL_ASSASIN: - case SL_BARDDANCER: - case SL_BLACKSMITH: - case SL_CRUSADER: - case SL_HUNTER: - case SL_KNIGHT: - case SL_MONK: - case SL_PRIEST: - case SL_ROGUE: - case SL_SAGE: - case SL_SOULLINKER: - case SL_STAR: - case SL_SUPERNOVICE: - case SL_WIZARD: - //NOTE: here, 'type' has the value of the associated MAPID, not of the SC_SPIRIT constant. - if (sd && !(dstsd && (dstsd->class_&MAPID_UPPERMASK) == type)) { - clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); - break; - } - if (skill_id == SL_SUPERNOVICE && dstsd && dstsd->die_counter && !(rnd()%100)) - { //Erase death count 1% of the casts - dstsd->die_counter = 0; - pc_setglobalreg(dstsd,"PC_DIE_COUNTER", 0); - clif->specialeffect(bl, 0x152, AREA); - //SC_SPIRIT invokes status_calc_pc for us. - } + case NPC_POWERUP: + sc_start(bl,SC_INCATKRATE,100,200,skill->get_time(skill_id, skill_lv)); clif->skill_nodamage(src,bl,skill_id,skill_lv, - sc_start4(bl,SC_SPIRIT,100,skill_lv,skill_id,0,0,skill->get_time(skill_id,skill_lv))); - sc_start(src,SC_SMA,100,skill_lv,skill->get_time(SL_SMA,skill_lv)); + sc_start(bl,type,100,100,skill->get_time(skill_id, skill_lv))); break; - case SL_HIGH: - if (sd && !(dstsd && (dstsd->class_&JOBL_UPPER) && !(dstsd->class_&JOBL_2) && dstsd->status.base_level < 70)) { - clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); - break; - } + + case NPC_AGIUP: + sc_start(bl,SC_MOVHASTE_INFINITY,100,skill_lv,skill->get_time(skill_id, skill_lv)); clif->skill_nodamage(src,bl,skill_id,skill_lv, - sc_start4(bl,type,100,skill_lv,skill_id,0,0,skill->get_time(skill_id,skill_lv))); - sc_start(src,SC_SMA,100,skill_lv,skill->get_time(SL_SMA,skill_lv)); + sc_start(bl,type,100,100,skill->get_time(skill_id, skill_lv))); break; - case SL_SWOO: - if (tsce) { - if(sd) - clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); - status_change_start(src,SC_STUN,10000,skill_lv,0,0,0,10000,8); - status_change_end(bl, SC_SWOO, INVALID_TIMER); - break; - } - case SL_SKA: // [marquis007] - case SL_SKE: - if (sd && !battle_config.allow_es_magic_pc && bl->type != BL_MOB) { - clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); - status_change_start(src,SC_STUN,10000,skill_lv,0,0,0,500,10); - break; - } - clif->skill_nodamage(src,bl,skill_id,skill_lv,sc_start(bl,type,100,skill_lv,skill->get_time(skill_id,skill_lv))); - if (skill_id == SL_SKE) - sc_start(src,SC_SMA,100,skill_lv,skill->get_time(SL_SMA,skill_lv)); + case NPC_INVISIBLE: + //Have val4 passed as 6 is for "infinite cloak" (do not end on attack/skill use). + clif->skill_nodamage(src,bl,skill_id,skill_lv, + sc_start4(bl,type,100,skill_lv,0,0,6,skill->get_time(skill_id,skill_lv))); break; - // New guild skills [Celest] - case GD_BATTLEORDER: - if(flag&1) { - if (status_get_guild_id(src) == status_get_guild_id(bl)) - sc_start(bl,type,100,skill_lv,skill->get_time(skill_id, skill_lv)); - } else if (status_get_guild_id(src)) { - clif->skill_nodamage(src,bl,skill_id,skill_lv,1); - iMap->foreachinrange(skill->area_sub, src, - skill->get_splash(skill_id, skill_lv), BL_PC, - src,skill_id,skill_lv,tick, flag|BCT_GUILD|1, - skill->castend_nodamage_id); - if (sd) - guild->block_skill(sd,skill->get_time2(skill_id,skill_lv)); + case NPC_SIEGEMODE: + // not sure what it does + clif->skill_nodamage(src,bl,skill_id,skill_lv,1); + break; + + case WE_MALE: + { + int hp_rate=(!skill_lv)? 0:skill_db[skill_id].hp_rate[skill_lv-1]; + int gain_hp= tstatus->max_hp*abs(hp_rate)/100; // The earned is the same % of the target HP than it costed the caster. [Skotlex] + clif->skill_nodamage(src,bl,skill_id,status_heal(bl, gain_hp, 0, 0),1); } break; - case GD_REGENERATION: - if(flag&1) { - if (status_get_guild_id(src) == status_get_guild_id(bl)) - sc_start(bl,type,100,skill_lv,skill->get_time(skill_id, skill_lv)); - } else if (status_get_guild_id(src)) { - clif->skill_nodamage(src,bl,skill_id,skill_lv,1); - iMap->foreachinrange(skill->area_sub, src, - skill->get_splash(skill_id, skill_lv), BL_PC, - src,skill_id,skill_lv,tick, flag|BCT_GUILD|1, - skill->castend_nodamage_id); - if (sd) - guild->block_skill(sd,skill->get_time2(skill_id,skill_lv)); + case WE_FEMALE: + { + int sp_rate=(!skill_lv)? 0:skill_db[skill_id].sp_rate[skill_lv-1]; + int gain_sp=tstatus->max_sp*abs(sp_rate)/100;// The earned is the same % of the target SP than it costed the caster. [Skotlex] + clif->skill_nodamage(src,bl,skill_id,status_heal(bl, 0, gain_sp, 0),1); } break; - case GD_RESTORE: - if(flag&1) { - if (status_get_guild_id(src) == status_get_guild_id(bl)) - clif->skill_nodamage(src,bl,AL_HEAL,status_percent_heal(bl,90,90),1); - } else if (status_get_guild_id(src)) { - clif->skill_nodamage(src,bl,skill_id,skill_lv,1); - iMap->foreachinrange(skill->area_sub, src, - skill->get_splash(skill_id, skill_lv), BL_PC, - src,skill_id,skill_lv,tick, flag|BCT_GUILD|1, - skill->castend_nodamage_id); - if (sd) - guild->block_skill(sd,skill->get_time2(skill_id,skill_lv)); + + // parent-baby skills + case WE_BABY: + if(sd){ + struct map_session_data *f_sd = pc->get_father(sd); + struct map_session_data *m_sd = pc->get_mother(sd); + // if neither was found + if(!f_sd && !m_sd){ + clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); + iMap->freeblock_unlock(); + return 0; + } + status_change_start(bl,SC_STUN,10000,skill_lv,0,0,0,skill->get_time2(skill_id,skill_lv),8); + if (f_sd) sc_start(&f_sd->bl,type,100,skill_lv,skill->get_time(skill_id,skill_lv)); + if (m_sd) sc_start(&m_sd->bl,type,100,skill_lv,skill->get_time(skill_id,skill_lv)); } break; - case GD_EMERGENCYCALL: + + case PF_HPCONVERSION: { - int dx[9]={-1, 1, 0, 0,-1, 1,-1, 1, 0}; - int dy[9]={ 0, 0, 1,-1, 1,-1,-1, 1, 0}; - int j = 0; - struct guild *g; - // i don't know if it actually summons in a circle, but oh well. ;P - g = sd?sd->state.gmaster_flag:guild->search(status_get_guild_id(src)); - if (!g) + int hp, sp; + hp = sstatus->max_hp/10; + sp = hp * 10 * skill_lv / 100; + if (!status_charge(src,hp,0)) { + if (sd) clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); break; - clif->skill_nodamage(src,bl,skill_id,skill_lv,1); - for(i = 0; i < g->max_member; i++, j++) { - if (j>8) j=0; - if ((dstsd = g->member[i].sd) != NULL && sd != dstsd && !dstsd->state.autotrade && !pc_isdead(dstsd)) { - if (map[dstsd->bl.m].flag.nowarp && !map_flag_gvg2(dstsd->bl.m)) - continue; - if(iMap->getcell(src->m,src->x+dx[j],src->y+dy[j],CELL_CHKNOREACH)) - dx[j] = dy[j] = 0; - pc->setpos(dstsd, map_id2index(src->m), src->x+dx[j], src->y+dy[j], CLR_RESPAWN); - } } - if (sd) - guild->block_skill(sd,skill->get_time2(skill_id,skill_lv)); + clif->skill_nodamage(src, bl, skill_id, skill_lv, 1); + status_heal(bl,0,sp,2); } break; - case SG_FEEL: - //AuronX reported you CAN memorize the same map as all three. [Skotlex] - if (sd) { - if(!sd->feel_map[skill_lv-1].index) - clif->feel_req(sd->fd,sd, skill_lv); - else - clif->feel_info(sd, skill_lv-1, 1); + case MA_REMOVETRAP: + case HT_REMOVETRAP: + { + struct skill_unit* su; + struct skill_unit_group* sg; + su = BL_CAST(BL_SKILL, bl); + + // Mercenaries can remove any trap + // Players can only remove their own traps or traps on Vs maps. + if( su && (sg = su->group) && (src->type == BL_MER || sg->src_id == src->id || map_flag_vs(bl->m)) && (skill->get_inf2(sg->skill_id)&INF2_TRAP) ) + { + clif->skill_nodamage(src, bl, skill_id, skill_lv, 1); + if( sd && !(sg->unit_id == UNT_USED_TRAPS || (sg->unit_id == UNT_ANKLESNARE && sg->val2 != 0 )) ) + { // prevent picking up expired traps + if( battle_config.skill_removetrap_type ) + { // get back all items used to deploy the trap + for( i = 0; i < 10; i++ ) + { + if( skill_db[su->group->skill_id].itemid[i] > 0 ) + { + int flag; + struct item item_tmp; + memset(&item_tmp,0,sizeof(item_tmp)); + item_tmp.nameid = skill_db[su->group->skill_id].itemid[i]; + item_tmp.identify = 1; + if( item_tmp.nameid && (flag=pc->additem(sd,&item_tmp,skill_db[su->group->skill_id].amount[i],LOG_TYPE_OTHER)) ) + { + clif->additem(sd,0,0,flag); + iMap->addflooritem(&item_tmp,skill_db[su->group->skill_id].amount[i],sd->bl.m,sd->bl.x,sd->bl.y,0,0,0,0); + } + } + } + } + else + { // get back 1 trap + struct item item_tmp; + memset(&item_tmp,0,sizeof(item_tmp)); + item_tmp.nameid = su->group->item_id?su->group->item_id:ITEMID_TRAP; + item_tmp.identify = 1; + if( item_tmp.nameid && (flag=pc->additem(sd,&item_tmp,1,LOG_TYPE_OTHER)) ) + { + clif->additem(sd,0,0,flag); + iMap->addflooritem(&item_tmp,1,sd->bl.m,sd->bl.x,sd->bl.y,0,0,0,0); + } + } + } + skill->delunit(su); + }else if(sd) + clif->skill_fail(sd, skill_id, USESKILL_FAIL_LEVEL, 0); + } break; - - case SG_HATE: - if (sd) { - clif->skill_nodamage(src,bl,skill_id,skill_lv,1); - if (!pc->set_hate_mob(sd, skill_lv-1, bl)) - clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); + case HT_SPRINGTRAP: + clif->skill_nodamage(src,bl,skill_id,skill_lv,1); + { + struct skill_unit *su=NULL; + if((bl->type==BL_SKILL) && (su=(struct skill_unit *)bl) && (su->group) ){ + switch(su->group->unit_id){ + case UNT_ANKLESNARE: // ankle snare + if (su->group->val2 != 0) + // if it is already trapping something don't spring it, + // remove trap should be used instead + break; + // otherwise fallthrough to below + case UNT_BLASTMINE: + case UNT_SKIDTRAP: + case UNT_LANDMINE: + case UNT_SHOCKWAVE: + case UNT_SANDMAN: + case UNT_FLASHER: + case UNT_FREEZINGTRAP: + case UNT_CLAYMORETRAP: + case UNT_TALKIEBOX: + su->group->unit_id = UNT_USED_TRAPS; + clif->changetraplook(bl, UNT_USED_TRAPS); + su->group->limit=DIFF_TICK(tick+1500,su->group->tick); + su->limit=DIFF_TICK(tick+1500,su->group->tick); + } + } } break; + case BD_ENCORE: + clif->skill_nodamage(src,bl,skill_id,skill_lv,1); + if(sd) + unit_skilluse_id(src,src->id,sd->skill_id_dance,sd->skill_lv_dance); + break; - case GS_GLITTERING: - if(sd) { - clif->skill_nodamage(src,bl,skill_id,skill_lv,1); - if(rnd()%100 < (20+10*skill_lv)) - pc->addspiritball(sd,skill->get_time(skill_id,skill_lv),10); - else if(sd->spiritball > 0) - pc->delspiritball(sd,1,0); + case AS_SPLASHER: + if(tstatus->mode&MD_BOSS + /** + * Renewal dropped the 3/4 hp requirement + **/ + #ifndef RENEWAL + || tstatus-> hp > tstatus->max_hp*3/4 + #endif + ) { + if (sd) clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); + iMap->freeblock_unlock(); + return 1; } + clif->skill_nodamage(src,bl,skill_id,skill_lv, + sc_start4(bl,type,100,skill_lv,skill_id,src->id,skill->get_time(skill_id,skill_lv),1000)); + #ifndef RENEWAL + if (sd) skill->blockpc_start (sd, skill_id, skill->get_time(skill_id, skill_lv)+3000, false); + #endif break; - case GS_CRACKER: - /* per official standards, this skill works on players and mobs. */ - if (sd && (dstsd || dstmd)) + case PF_MINDBREAKER: { - i =65 -5*distance_bl(src,bl); //Base rate - if (i < 30) i = 30; - clif->skill_nodamage(src,bl,skill_id,skill_lv,1); - sc_start(bl,SC_STUN, i,skill_lv,skill->get_time2(skill_id,skill_lv)); - } - break; + if(tstatus->mode&MD_BOSS || battle->check_undead(tstatus->race,tstatus->def_ele) ) { + iMap->freeblock_unlock(); + return 1; + } - case AM_CALLHOMUN: //[orn] - if (sd && homun->call(sd)) - clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); - break; + if (tsce) + { //HelloKitty2 (?) explained that this silently fails when target is + //already inflicted. [Skotlex] + iMap->freeblock_unlock(); + return 1; + } - case AM_REST: - if (sd) { - if (homun->vaporize(sd,1)) - clif->skill_nodamage(src, bl, skill_id, skill_lv, 1); - else - clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); + //Has a 55% + skill_lv*5% success chance. + if (!clif->skill_nodamage(src,bl,skill_id,skill_lv, + sc_start(bl,type,55+5*skill_lv,skill_lv,skill->get_time(skill_id,skill_lv)))) + { + if (sd) clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); + iMap->freeblock_unlock(); + return 0; + } + + unit_skillcastcancel(bl,0); + + if(tsc && tsc->count){ + status_change_end(bl, SC_FREEZE, INVALID_TIMER); + if(tsc->data[SC_STONE] && tsc->opt1 == OPT1_STONE) + status_change_end(bl, SC_STONE, INVALID_TIMER); + status_change_end(bl, SC_SLEEP, INVALID_TIMER); + } + + if(dstmd) + mob_target(dstmd,src,skill->get_range2(src,skill_id,skill_lv)); } break; - case HAMI_CASTLE: //[orn] - if(rnd()%100 < 20*skill_lv && src != bl) + case PF_SOULCHANGE: { - int x,y; - x = src->x; - y = src->y; - if (hd) - skill->blockhomun_start(hd, skill_id, skill->get_time2(skill_id,skill_lv)); - - if (unit_movepos(src,bl->x,bl->y,0,0)) { - clif->skill_nodamage(src,src,skill_id,skill_lv,1); // Homunc - clif->slide(src,bl->x,bl->y) ; - if (unit_movepos(bl,x,y,0,0)) - { - clif->skill_nodamage(bl,bl,skill_id,skill_lv,1); // Master - clif->slide(bl,x,y) ; + unsigned int sp1 = 0, sp2 = 0; + if (dstmd) { + if (dstmd->state.soul_change_flag) { + if(sd) clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); + break; } + dstmd->state.soul_change_flag = 1; + sp2 = sstatus->max_sp * 3 /100; + status_heal(src, 0, sp2, 2); + clif->skill_nodamage(src,bl,skill_id,skill_lv,1); + break; + } + sp1 = sstatus->sp; + sp2 = tstatus->sp; + #ifdef RENEWAL + sp1 = sp1 / 2; + sp2 = sp2 / 2; + if( tsc && tsc->data[SC_EXTREMITYFIST2] ) + sp1 = tstatus->sp; + #endif + status_set_sp(src, sp2, 3); + status_set_sp(bl, sp1, 3); + clif->skill_nodamage(src,bl,skill_id,skill_lv,1); + } + break; - //TODO: Shouldn't also players and the like switch targets? - iMap->foreachinrange(skill->chastle_mob_changetarget,src, - AREA_SIZE, BL_MOB, bl, src); + // Slim Pitcher + case CR_SLIMPITCHER: + // Updated to block Slim Pitcher from working on barricades and guardian stones. + if( dstmd && (dstmd->class_ == MOBID_EMPERIUM || (dstmd->class_ >= MOBID_BARRICADE1 && dstmd->class_ <= MOBID_GUARIDAN_STONE2)) ) + break; + if (potion_hp || potion_sp) { + int hp = potion_hp, sp = potion_sp; + hp = hp * (100 + (tstatus->vit<<1))/100; + sp = sp * (100 + (tstatus->int_<<1))/100; + if (dstsd) { + if (hp) + hp = hp * (100 + pc->checkskill(dstsd,SM_RECOVERY)*10 + pc->skillheal2_bonus(dstsd, skill_id))/100; + if (sp) + sp = sp * (100 + pc->checkskill(dstsd,MG_SRECOVERY)*10 + pc->skillheal2_bonus(dstsd, skill_id))/100; + } + if( tsc && tsc->count ) { + if (tsc->data[SC_CRITICALWOUND]) { + hp -= hp * tsc->data[SC_CRITICALWOUND]->val2 / 100; + sp -= sp * tsc->data[SC_CRITICALWOUND]->val2 / 100; + } + if (tsc->data[SC_DEATHHURT]) { + hp -= hp * 20 / 100; + sp -= sp * 20 / 100; + } + if( tsc->data[SC_WATER_INSIGNIA] && tsc->data[SC_WATER_INSIGNIA]->val1 == 2) { + hp += hp / 10; + sp += sp / 10; + } } + if(hp > 0) + clif->skill_nodamage(NULL,bl,AL_HEAL,hp,1); + if(sp > 0) + clif->skill_nodamage(NULL,bl,MG_SRECOVERY,sp,1); + status_heal(bl,hp,sp,0); } - // Failed - else if (hd && hd->master) - clif->skill_fail(hd->master, skill_id, USESKILL_FAIL_LEVEL, 0); - else if (sd) - clif->skill_fail(sd, skill_id, USESKILL_FAIL_LEVEL, 0); break; - case HVAN_CHAOTIC: //[orn] + // Full Chemical Protection + case CR_FULLPROTECTION: { - static const int per[5][2]={{20,50},{50,60},{25,75},{60,64},{34,67}}; - int r = rnd()%100; - i = (skill_lv-1)%5; - if(rget_master(src); - else //Enemy - bl = iMap->id2bl(battle->get_target(src)); + unsigned int equip[] = {EQP_WEAPON, EQP_SHIELD, EQP_ARMOR, EQP_HEAD_TOP}; + int i, s = 0, skilltime = skill->get_time(skill_id,skill_lv); - if (!bl) bl = src; - i = skill->calc_heal(src, bl, skill_id, 1+rnd()%skill_lv, true); - //Eh? why double skill packet? - clif->skill_nodamage(src,bl,AL_HEAL,i,1); - clif->skill_nodamage(src,bl,skill_id,i,1); - status_heal(bl, i, 0, 0); + for (i=0 ; i<4; i++) { + if( bl->type != BL_PC || ( dstsd && pc->checkequip(dstsd,equip[i]) < 0 ) ) + continue; + sc_start(bl,(sc_type)(SC_PROTECTWEAPON + i),100,skill_lv,skilltime); + s++; + } + if( sd && !s ){ + clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); + iMap->freeblock_unlock(); // Don't consume item requirements + return 0; + } + clif->skill_nodamage(src,bl,skill_id,skill_lv,1); } break; - //Homun single-target support skills [orn] - case HAMI_BLOODLUST: - case HFLI_FLEET: - case HFLI_SPEED: - case HLIF_CHANGE: - case MH_ANGRIFFS_MODUS: - case MH_GOLDENE_FERSE: - clif->skill_nodamage(src,bl,skill_id,skill_lv, - sc_start(bl,type,100,skill_lv,skill->get_time(skill_id,skill_lv))); - if (hd) - skill->blockhomun_start(hd, skill_id, skill->get_time2(skill_id,skill_lv)); + + case RG_CLEANER: //AppleGirl + clif->skill_nodamage(src,bl,skill_id,skill_lv,1); break; - case NPC_DRAGONFEAR: - if (flag&1) { - const enum sc_type sc[] = { SC_STUN, SC_SILENCE, SC_CONFUSION, SC_BLEEDING }; - int j; - j = i = rnd()%ARRAYLENGTH(sc); - while ( !sc_start2(bl,sc[i],100,skill_lv,src->id,skill->get_time2(skill_id,i+1)) ) { - i++; - if ( i == ARRAYLENGTH(sc) ) - i = 0; - if (i == j) - break; + case CG_LONGINGFREEDOM: + { + if (tsc && !tsce && (tsce=tsc->data[SC_DANCING]) && tsce->val4 + && (tsce->val1&0xFFFF) != CG_MOONLIT) //Can't use Longing for Freedom while under Moonlight Petals. [Skotlex] + { + clif->skill_nodamage(src,bl,skill_id,skill_lv, + sc_start(bl,type,100,skill_lv,skill->get_time(skill_id,skill_lv))); } - break; - } - case NPC_WIDEBLEEDING: - case NPC_WIDECONFUSE: - case NPC_WIDECURSE: - case NPC_WIDEFREEZE: - case NPC_WIDESLEEP: - case NPC_WIDESILENCE: - case NPC_WIDESTONE: - case NPC_WIDESTUN: - case NPC_SLOWCAST: - case NPC_WIDEHELLDIGNITY: - if (flag&1) - sc_start2(bl,type,100,skill_lv,src->id,skill->get_time2(skill_id,skill_lv)); - else { - skill_area_temp[2] = 0; //For SD_PREAMBLE - clif->skill_nodamage(src,bl,skill_id,skill_lv,1); - iMap->foreachinrange(skill->area_sub, bl, - skill->get_splash(skill_id, skill_lv),BL_CHAR, - src,skill_id,skill_lv,tick, flag|BCT_ENEMY|SD_PREAMBLE|1, - skill->castend_nodamage_id); - } - break; - case NPC_WIDESOULDRAIN: - if (flag&1) - status_percent_damage(src,bl,0,((skill_lv-1)%5+1)*20,false); - else { - skill_area_temp[2] = 0; //For SD_PREAMBLE - clif->skill_nodamage(src,bl,skill_id,skill_lv,1); - iMap->foreachinrange(skill->area_sub, bl, - skill->get_splash(skill_id, skill_lv),BL_CHAR, - src,skill_id,skill_lv,tick, flag|BCT_ENEMY|SD_PREAMBLE|1, - skill->castend_nodamage_id); } break; - case ALL_PARTYFLEE: - if( sd && !(flag&1) ) + + case CG_TAROTCARD: { - if( !sd->status.party_id ) + int eff, count = -1; + if( tsc && tsc->data[type] ){ + iMap->freeblock_unlock(); + return 0; + } + if( rnd() % 100 > skill_lv * 8 || (dstmd && ((dstmd->guardian_data && dstmd->class_ == MOBID_EMPERIUM) || mob_is_battleground(dstmd))) ) { - clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); - break; + if( sd ) + clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); + + iMap->freeblock_unlock(); + return 0; } - party_foreachsamemap(skill->area_sub, sd, skill->get_splash(skill_id, skill_lv), src, skill_id, skill_lv, tick, flag|BCT_PARTY|1, skill->castend_nodamage_id); + status_zap(src,0,skill_db[skill->get_index(skill_id)].sp[skill_lv]); // consume sp only if succeeded [Inkfish] + do { + eff = rnd() % 14; + if( eff == 5 ) + clif->specialeffect(src, 528, AREA); + else + clif->specialeffect(bl, 523 + eff, AREA); + switch (eff) + { + case 0: // heals SP to 0 + status_percent_damage(src, bl, 0, 100, false); + break; + case 1: // matk halved + sc_start(bl,SC_INCMATKRATE,100,-50,skill->get_time2(skill_id,skill_lv)); + break; + case 2: // all buffs removed + status_change_clear_buffs(bl,1); + break; + case 3: // 1000 damage, random armor destroyed + { + status_fix_damage(src, bl, 1000, 0); + clif->damage(src,bl,tick,0,0,1000,0,0,0); + if( !status_isdead(bl) ) { + int where[] = { EQP_ARMOR, EQP_SHIELD, EQP_HELM, EQP_SHOES, EQP_GARMENT }; + skill->break_equip(bl, where[rnd()%5], 10000, BCT_ENEMY); + } + } + break; + case 4: // atk halved + sc_start(bl,SC_INCATKRATE,100,-50,skill->get_time2(skill_id,skill_lv)); + break; + case 5: // 2000HP heal, random teleported + status_heal(src, 2000, 0, 0); + if( !map_flag_vs(bl->m) ) + unit_warp(bl, -1,-1,-1, CLR_TELEPORT); + break; + case 6: // random 2 other effects + if (count == -1) + count = 3; + else + count++; //Should not retrigger this one. + break; + case 7: // stop freeze or stoned + { + enum sc_type sc[] = { SC_STOP, SC_FREEZE, SC_STONE }; + sc_start(bl,sc[rnd()%3],100,skill_lv,skill->get_time2(skill_id,skill_lv)); + } + break; + case 8: // curse coma and poison + sc_start(bl,SC_COMA,100,skill_lv,skill->get_time2(skill_id,skill_lv)); + sc_start(bl,SC_CURSE,100,skill_lv,skill->get_time2(skill_id,skill_lv)); + sc_start(bl,SC_POISON,100,skill_lv,skill->get_time2(skill_id,skill_lv)); + break; + case 9: // confusion + sc_start(bl,SC_CONFUSION,100,skill_lv,skill->get_time2(skill_id,skill_lv)); + break; + case 10: // 6666 damage, atk matk halved, cursed + status_fix_damage(src, bl, 6666, 0); + clif->damage(src,bl,tick,0,0,6666,0,0,0); + sc_start(bl,SC_INCATKRATE,100,-50,skill->get_time2(skill_id,skill_lv)); + sc_start(bl,SC_INCMATKRATE,100,-50,skill->get_time2(skill_id,skill_lv)); + sc_start(bl,SC_CURSE,skill_lv,100,skill->get_time2(skill_id,skill_lv)); + break; + case 11: // 4444 damage + status_fix_damage(src, bl, 4444, 0); + clif->damage(src,bl,tick,0,0,4444,0,0,0); + break; + case 12: // stun + sc_start(bl,SC_STUN,100,skill_lv,5000); + break; + case 13: // atk,matk,hit,flee,def reduced + sc_start(bl,SC_INCATKRATE,100,-20,skill->get_time2(skill_id,skill_lv)); + sc_start(bl,SC_INCMATKRATE,100,-20,skill->get_time2(skill_id,skill_lv)); + sc_start(bl,SC_INCHITRATE,100,-20,skill->get_time2(skill_id,skill_lv)); + sc_start(bl,SC_INCFLEERATE,100,-20,skill->get_time2(skill_id,skill_lv)); + sc_start(bl,SC_INCDEFRATE,100,-20,skill->get_time2(skill_id,skill_lv)); + sc_start(bl,type,100,skill_lv,skill->get_time2(skill_id,skill_lv)); + break; + default: + break; + } + } while ((--count) > 0); + clif->skill_nodamage(src,bl,skill_id,skill_lv,1); } - else - clif->skill_nodamage(src,bl,skill_id,skill_lv,sc_start(bl,type,100,skill_lv,skill->get_time(skill_id,skill_lv))); - break; - case NPC_TALK: - case ALL_WEWISH: - clif->skill_nodamage(src,bl,skill_id,skill_lv,1); break; - case ALL_BUYING_STORE: - if( sd ) - {// players only, skill allows 5 buying slots - clif->skill_nodamage(src, bl, skill_id, skill_lv, buyingstore->setup(sd, MAX_BUYINGSTORE_SLOTS)); + + case SL_ALCHEMIST: + case SL_ASSASIN: + case SL_BARDDANCER: + case SL_BLACKSMITH: + case SL_CRUSADER: + case SL_HUNTER: + case SL_KNIGHT: + case SL_MONK: + case SL_PRIEST: + case SL_ROGUE: + case SL_SAGE: + case SL_SOULLINKER: + case SL_STAR: + case SL_SUPERNOVICE: + case SL_WIZARD: + //NOTE: here, 'type' has the value of the associated MAPID, not of the SC_SOULLINK constant. + if (sd && !(dstsd && (dstsd->class_&MAPID_UPPERMASK) == type)) { + clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); + break; } + if (skill_id == SL_SUPERNOVICE && dstsd && dstsd->die_counter && !(rnd()%100)) + { //Erase death count 1% of the casts + dstsd->die_counter = 0; + pc_setglobalreg(dstsd,"PC_DIE_COUNTER", 0); + clif->specialeffect(bl, 0x152, AREA); + //SC_SOULLINK invokes status_calc_pc for us. + } + clif->skill_nodamage(src,bl,skill_id,skill_lv, + sc_start4(bl,SC_SOULLINK,100,skill_lv,skill_id,0,0,skill->get_time(skill_id,skill_lv))); + sc_start(src,SC_SMA_READY,100,skill_lv,skill->get_time(SL_SMA,skill_lv)); break; - case RK_ENCHANTBLADE: - clif->skill_nodamage(src,bl,skill_id,skill_lv,// formula not confirmed - sc_start2(bl,type,100,skill_lv,100+20*skill_lv/*+sstatus->int_/2+status_get_lv(bl)/10*/,skill->get_time(skill_id,skill_lv))); - break; - case RK_DRAGONHOWLING: - if( flag&1) - sc_start(bl,type,50 + 6 * skill_lv,skill_lv,skill->get_time(skill_id,skill_lv)); - else - { - skill_area_temp[2] = 0; - clif->skill_nodamage(src,bl,skill_id,skill_lv,1); - iMap->foreachinrange(skill->area_sub, src, - skill->get_splash(skill_id,skill_lv),BL_CHAR, - src,skill_id,skill_lv,tick,flag|BCT_ENEMY|SD_PREAMBLE|1, - skill->castend_nodamage_id); + case SL_HIGH: + if (sd && !(dstsd && (dstsd->class_&JOBL_UPPER) && !(dstsd->class_&JOBL_2) && dstsd->status.base_level < 70)) { + clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); + break; } + clif->skill_nodamage(src,bl,skill_id,skill_lv, + sc_start4(bl,type,100,skill_lv,skill_id,0,0,skill->get_time(skill_id,skill_lv))); + sc_start(src,SC_SMA_READY,100,skill_lv,skill->get_time(SL_SMA,skill_lv)); break; - case RK_IGNITIONBREAK: - case LG_EARTHDRIVE: - clif->skill_damage(src,bl,tick, status_get_amotion(src), 0, -30000, 1, skill_id, skill_lv, 6); - i = skill->get_splash(skill_id,skill_lv); - if( skill_id == LG_EARTHDRIVE ) { - int dummy = 1; - iMap->foreachinarea(skill->cell_overlap, src->m, src->x-i, src->y-i, src->x+i, src->y+i, BL_SKILL, LG_EARTHDRIVE, &dummy, src); - } - iMap->foreachinrange(skill->area_sub, bl,i,BL_CHAR, - src,skill_id,skill_lv,tick,flag|BCT_ENEMY|1,skill->castend_damage_id); - break; - case RK_STONEHARDSKIN: - if( sd && pc->checkskill(sd,RK_RUNEMASTERY) >= 4 ) - { - int heal = sstatus->hp / 4; // 25% HP - if( status_charge(bl,heal,0) ) - clif->skill_nodamage(src,bl,skill_id,skill_lv,sc_start2(bl,type,100,skill_lv,heal,skill->get_time(skill_id,skill_lv))); - else + + case SL_SWOO: + if (tsce) { + if(sd) clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); + status_change_start(src,SC_STUN,10000,skill_lv,0,0,0,10000,8); + status_change_end(bl, SC_SWOO, INVALID_TIMER); + break; } - break; - case RK_REFRESH: - if( sd && pc->checkskill(sd,RK_RUNEMASTERY) >= 8 ) - { - int heal = status_get_max_hp(bl) * 25 / 100; - clif->skill_nodamage(src,bl,skill_id,skill_lv, - sc_start(bl,type,100,skill_lv,skill->get_time(skill_id,skill_lv))); - status_heal(bl,heal,0,1); - status_change_clear_buffs(bl,4); + case SL_SKA: // [marquis007] + case SL_SKE: + if (sd && !battle_config.allow_es_magic_pc && bl->type != BL_MOB) { + clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); + status_change_start(src,SC_STUN,10000,skill_lv,0,0,0,500,10); + break; } + clif->skill_nodamage(src,bl,skill_id,skill_lv,sc_start(bl,type,100,skill_lv,skill->get_time(skill_id,skill_lv))); + if (skill_id == SL_SKE) + sc_start(src,SC_SMA_READY,100,skill_lv,skill->get_time(SL_SMA,skill_lv)); break; - case RK_MILLENNIUMSHIELD: - if( sd && pc->checkskill(sd,RK_RUNEMASTERY) >= 9 ) - { - short shields = (rnd()%100<50) ? 4 : ((rnd()%100<80) ? 3 : 2); - sc_start4(bl,type,100,skill_lv,shields,1000,0,skill->get_time(skill_id,skill_lv)); - clif->millenniumshield(sd,shields); - clif->skill_nodamage(src,bl,skill_id,1,1); + // New guild skills [Celest] + case GD_BATTLEORDER: + if(flag&1) { + if (status_get_guild_id(src) == status_get_guild_id(bl)) + sc_start(bl,type,100,skill_lv,skill->get_time(skill_id, skill_lv)); + } else if (status_get_guild_id(src)) { + clif->skill_nodamage(src,bl,skill_id,skill_lv,1); + iMap->foreachinrange(skill->area_sub, src, + skill->get_splash(skill_id, skill_lv), BL_PC, + src,skill_id,skill_lv,tick, flag|BCT_GUILD|1, + skill->castend_nodamage_id); + if (sd) + guild->block_skill(sd,skill->get_time2(skill_id,skill_lv)); } break; - - case RK_GIANTGROWTH: - case RK_VITALITYACTIVATION: - case RK_ABUNDANCE: - case RK_CRUSHSTRIKE: - if( sd ) - { - int lv = 1; // RK_GIANTGROWTH - if( skill_id == RK_VITALITYACTIVATION ) - lv = 2; - else if( skill_id == RK_ABUNDANCE ) - lv = 6; - else if( skill_id == RK_CRUSHSTRIKE ) - lv = 7; - if( pc->checkskill(sd,RK_RUNEMASTERY) >= lv ) - clif->skill_nodamage(src,bl,skill_id,skill_lv,sc_start(bl,type,100,skill_lv,skill->get_time(skill_id,skill_lv))); + case GD_REGENERATION: + if(flag&1) { + if (status_get_guild_id(src) == status_get_guild_id(bl)) + sc_start(bl,type,100,skill_lv,skill->get_time(skill_id, skill_lv)); + } else if (status_get_guild_id(src)) { + clif->skill_nodamage(src,bl,skill_id,skill_lv,1); + iMap->foreachinrange(skill->area_sub, src, + skill->get_splash(skill_id, skill_lv), BL_PC, + src,skill_id,skill_lv,tick, flag|BCT_GUILD|1, + skill->castend_nodamage_id); + if (sd) + guild->block_skill(sd,skill->get_time2(skill_id,skill_lv)); } break; - - case RK_FIGHTINGSPIRIT: - if( flag&1 ) { - if( src == bl ) - sc_start2(bl,type,100,skill_area_temp[5],10*(sd?pc->checkskill(sd,RK_RUNEMASTERY):10),skill->get_time(skill_id,skill_lv)); - else - sc_start(bl,type,100,skill_area_temp[5]/4,skill->get_time(skill_id,skill_lv)); - } else if( sd && pc->checkskill(sd,RK_RUNEMASTERY) >= 5 ) { - if( sd->status.party_id ) { - i = party_foreachsamemap(skill->area_sub,sd,skill->get_splash(skill_id,skill_lv),src,skill_id,skill_lv,tick,BCT_PARTY,skill->area_sub_count); - skill_area_temp[5] = 7 * i; // ATK - party_foreachsamemap(skill->area_sub,sd,skill->get_splash(skill_id,skill_lv),src,skill_id,skill_lv,tick,flag|BCT_PARTY|1,skill->castend_nodamage_id); - } else - sc_start2(bl,type,100,7,5,skill->get_time(skill_id,skill_lv)); + case GD_RESTORE: + if(flag&1) { + if (status_get_guild_id(src) == status_get_guild_id(bl)) + clif->skill_nodamage(src,bl,AL_HEAL,status_percent_heal(bl,90,90),1); + } else if (status_get_guild_id(src)) { + clif->skill_nodamage(src,bl,skill_id,skill_lv,1); + iMap->foreachinrange(skill->area_sub, src, + skill->get_splash(skill_id, skill_lv), BL_PC, + src,skill_id,skill_lv,tick, flag|BCT_GUILD|1, + skill->castend_nodamage_id); + if (sd) + guild->block_skill(sd,skill->get_time2(skill_id,skill_lv)); } - clif->skill_nodamage(src,bl,skill_id,1,1); break; - /** - * Guilotine Cross - **/ - case GC_ROLLINGCUTTER: + case GD_EMERGENCYCALL: { - short count = 1; - skill_area_temp[2] = 0; - iMap->foreachinrange(skill->area_sub,src,skill->get_splash(skill_id,skill_lv),BL_CHAR,src,skill_id,skill_lv,tick,flag|BCT_ENEMY|SD_PREAMBLE|SD_SPLASH|1,skill->castend_damage_id); - if( tsc && tsc->data[SC_ROLLINGCUTTER] ) - { // Every time the skill is casted the status change is reseted adding a counter. - count += (short)tsc->data[SC_ROLLINGCUTTER]->val1; - if( count > 10 ) - count = 10; // Max coounter - status_change_end(bl, SC_ROLLINGCUTTER, INVALID_TIMER); + int dx[9]={-1, 1, 0, 0,-1, 1,-1, 1, 0}; + int dy[9]={ 0, 0, 1,-1, 1,-1,-1, 1, 0}; + int j = 0; + struct guild *g; + // i don't know if it actually summons in a circle, but oh well. ;P + g = sd?sd->state.gmaster_flag:guild->search(status_get_guild_id(src)); + if (!g) + break; + clif->skill_nodamage(src,bl,skill_id,skill_lv,1); + for(i = 0; i < g->max_member; i++, j++) { + if (j>8) j=0; + if ((dstsd = g->member[i].sd) != NULL && sd != dstsd && !dstsd->state.autotrade && !pc_isdead(dstsd)) { + if (map[dstsd->bl.m].flag.nowarp && !map_flag_gvg2(dstsd->bl.m)) + continue; + if(iMap->getcell(src->m,src->x+dx[j],src->y+dy[j],CELL_CHKNOREACH)) + dx[j] = dy[j] = 0; + pc->setpos(dstsd, map_id2index(src->m), src->x+dx[j], src->y+dy[j], CLR_RESPAWN); + } } - sc_start(bl,SC_ROLLINGCUTTER,100,count,skill->get_time(skill_id,skill_lv)); - clif->skill_nodamage(src,src,skill_id,skill_lv,1); + if (sd) + guild->block_skill(sd,skill->get_time2(skill_id,skill_lv)); } break; - case GC_WEAPONBLOCKING: - if( tsc && tsc->data[SC_WEAPONBLOCKING] ) - status_change_end(bl, SC_WEAPONBLOCKING, INVALID_TIMER); - else - sc_start(bl,SC_WEAPONBLOCKING,100,skill_lv,skill->get_time(skill_id,skill_lv)); - clif->skill_nodamage(src,bl,skill_id,skill_lv,1); - break; - - case GC_CREATENEWPOISON: - if( sd ) - { - clif->skill_produce_mix_list(sd,skill_id,25); - clif->skill_nodamage(src, bl, skill_id, skill_lv, 1); + case SG_FEEL: + //AuronX reported you CAN memorize the same map as all three. [Skotlex] + if (sd) { + if(!sd->feel_map[skill_lv-1].index) + clif->feel_req(sd->fd,sd, skill_lv); + else + clif->feel_info(sd, skill_lv-1, 1); } break; - case GC_POISONINGWEAPON: - if( sd ) { - clif->poison_list(sd,skill_lv); + case SG_HATE: + if (sd) { clif->skill_nodamage(src,bl,skill_id,skill_lv,1); + if (!pc->set_hate_mob(sd, skill_lv-1, bl)) + clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); } break; - case GC_ANTIDOTE: - clif->skill_nodamage(src,bl,skill_id,skill_lv,1); - if( tsc ) - { - status_change_end(bl, SC_PARALYSE, INVALID_TIMER); - status_change_end(bl, SC_PYREXIA, INVALID_TIMER); - status_change_end(bl, SC_DEATHHURT, INVALID_TIMER); - status_change_end(bl, SC_LEECHESEND, INVALID_TIMER); - status_change_end(bl, SC_VENOMBLEED, INVALID_TIMER); - status_change_end(bl, SC_MAGICMUSHROOM, INVALID_TIMER); - status_change_end(bl, SC_TOXIN, INVALID_TIMER); - status_change_end(bl, SC_OBLIVIONCURSE, INVALID_TIMER); - } - break; - - case GC_PHANTOMMENACE: - clif->skill_damage(src,bl,tick, status_get_amotion(src), 0, -30000, 1, skill_id, skill_lv, 6); - clif->skill_nodamage(src,bl,skill_id,skill_lv,1); - iMap->foreachinrange(skill->area_sub,src,skill->get_splash(skill_id,skill_lv),BL_CHAR, - src,skill_id,skill_lv,tick,flag|BCT_ENEMY|1,skill->castend_damage_id); - break; - - case GC_HALLUCINATIONWALK: - { - int heal = status_get_max_hp(bl) / 10; - if( status_get_hp(bl) < heal ) { // if you haven't enough HP skill fails. - if( sd ) clif->skill_fail(sd,skill_id,USESKILL_FAIL_HP_INSUFFICIENT,0); - break; - } - if( !status_charge(bl,heal,0) ) - { - if( sd ) clif->skill_fail(sd,skill_id,USESKILL_FAIL_HP_INSUFFICIENT,0); - break; - } - clif->skill_nodamage(src,bl,skill_id,skill_lv,sc_start(bl,type,100,skill_lv,skill->get_time(skill_id,skill_lv))); - } - break; - /** - * Arch Bishop - **/ - case AB_ANCILLA: - if( sd ) { + case GS_GLITTERING: + if(sd) { clif->skill_nodamage(src,bl,skill_id,skill_lv,1); - skill->produce_mix(sd, skill_id, ITEMID_ANCILLA, 0, 0, 0, 1); + if(rnd()%100 < (20+10*skill_lv)) + pc->addspiritball(sd,skill->get_time(skill_id,skill_lv),10); + else if(sd->spiritball > 0) + pc->delspiritball(sd,1,0); } break; - case AB_CLEMENTIA: - case AB_CANTO: + case GS_CRACKER: + /* per official standards, this skill works on players and mobs. */ + if (sd && (dstsd || dstmd)) { - int bless_lv = pc->checkskill(sd,AL_BLESSING) + (sd->status.job_level / 10); - int agi_lv = pc->checkskill(sd,AL_INCAGI) + (sd->status.job_level / 10); - if( sd == NULL || sd->status.party_id == 0 || flag&1 ) - clif->skill_nodamage(bl, bl, skill_id, skill_lv, sc_start(bl,type,100, - (skill_id == AB_CLEMENTIA)? bless_lv : (skill_id == AB_CANTO)? agi_lv : skill_lv, skill->get_time(skill_id,skill_lv))); - else if( sd ) - party_foreachsamemap(skill->area_sub, sd, skill->get_splash(skill_id, skill_lv), src, skill_id, skill_lv, tick, flag|BCT_PARTY|1, skill->castend_nodamage_id); + i =65 -5*distance_bl(src,bl); //Base rate + if (i < 30) i = 30; + clif->skill_nodamage(src,bl,skill_id,skill_lv,1); + sc_start(bl,SC_STUN, i,skill_lv,skill->get_time2(skill_id,skill_lv)); } break; - case AB_PRAEFATIO: - if( sd == NULL || sd->status.party_id == 0 || flag&1 ) - clif->skill_nodamage(bl, bl, skill_id, skill_lv, sc_start4(bl, type, 100, skill_lv, 0, 0, 1, skill->get_time(skill_id, skill_lv))); - else if( sd ) - party_foreachsamemap(skill->area_sub, sd, skill->get_splash(skill_id, skill_lv), src, skill_id, skill_lv, tick, flag|BCT_PARTY|1, skill->castend_nodamage_id); + case AM_CALLHOMUN: //[orn] + if (sd && homun->call(sd)) + clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); break; - - case AB_CHEAL: - if( sd == NULL || sd->status.party_id == 0 || flag&1 ) { - if( sd && tstatus && !battle->check_undead(tstatus->race, tstatus->def_ele) ) { - i = skill->calc_heal(src, bl, AL_HEAL, pc->checkskill(sd, AL_HEAL), true); - - if( (dstsd && pc_ismadogear(dstsd)) || status_isimmune(bl)) - i = 0; // Should heal by 0 or won't do anything?? in iRO it breaks the healing to members.. [malufett] - - clif->skill_nodamage(bl, bl, skill_id, i, 1); - if( tsc && tsc->data[SC_AKAITSUKI] && i ) - i = ~i + 1; - status_heal(bl, i, 0, 0); - } + + case AM_REST: + if (sd) { + if (homun->vaporize(sd,1)) + clif->skill_nodamage(src, bl, skill_id, skill_lv, 1); + else + clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); } - else if( sd ) - party_foreachsamemap(skill->area_sub, sd, skill->get_splash(skill_id, skill_lv), src, skill_id, skill_lv, tick, flag|BCT_PARTY|1, skill->castend_nodamage_id); break; - case AB_ORATIO: - if( flag&1 ) - sc_start(bl, type, 40 + 5 * skill_lv, skill_lv, skill->get_time(skill_id, skill_lv)); - else + case HAMI_CASTLE: //[orn] + if(rnd()%100 < 20*skill_lv && src != bl) { - iMap->foreachinrange(skill->area_sub, src, skill->get_splash(skill_id, skill_lv), BL_CHAR, - src, skill_id, skill_lv, tick, flag|BCT_ENEMY|1, skill->castend_nodamage_id); - clif->skill_nodamage(src, bl, skill_id, skill_lv, 1); + int x,y; + x = src->x; + y = src->y; + if (hd) + skill->blockhomun_start(hd, skill_id, skill->get_time2(skill_id,skill_lv)); + + if (unit_movepos(src,bl->x,bl->y,0,0)) { + clif->skill_nodamage(src,src,skill_id,skill_lv,1); // Homunc + clif->slide(src,bl->x,bl->y) ; + if (unit_movepos(bl,x,y,0,0)) + { + clif->skill_nodamage(bl,bl,skill_id,skill_lv,1); // Master + clif->slide(bl,x,y) ; + } + + //TODO: Shouldn't also players and the like switch targets? + iMap->foreachinrange(skill->chastle_mob_changetarget,src, + AREA_SIZE, BL_MOB, bl, src); + } } + // Failed + else if (hd && hd->master) + clif->skill_fail(hd->master, skill_id, USESKILL_FAIL_LEVEL, 0); + else if (sd) + clif->skill_fail(sd, skill_id, USESKILL_FAIL_LEVEL, 0); break; + case HVAN_CHAOTIC: //[orn] + { + static const int per[5][2]={{20,50},{50,60},{25,75},{60,64},{34,67}}; + int r = rnd()%100; + i = (skill_lv-1)%5; + if(rget_master(src); + else //Enemy + bl = iMap->id2bl(battle->get_target(src)); - case AB_LAUDAAGNUS: - if( flag&1 || sd == NULL ) { - if( tsc && (tsc->data[SC_FREEZE] || tsc->data[SC_STONE] || tsc->data[SC_BLIND] || - tsc->data[SC_BURNING] || tsc->data[SC_FREEZING] || tsc->data[SC_CRYSTALIZE])) { - // Success Chance: (40 + 10 * Skill Level) % - if( rnd()%100 > 40+10*skill_lv ) break; - status_change_end(bl, SC_FREEZE, INVALID_TIMER); - status_change_end(bl, SC_STONE, INVALID_TIMER); - status_change_end(bl, SC_BLIND, INVALID_TIMER); - status_change_end(bl, SC_BURNING, INVALID_TIMER); - status_change_end(bl, SC_FREEZING, INVALID_TIMER); - status_change_end(bl, SC_CRYSTALIZE, INVALID_TIMER); - }else //Success rate only applies to the curing effect and not stat bonus. Bonus status only applies to non infected targets - clif->skill_nodamage(bl, bl, skill_id, skill_lv, - sc_start(bl, type, 100, skill_lv, skill->get_time(skill_id, skill_lv))); - } else if( sd ) - party_foreachsamemap(skill->area_sub, sd, skill->get_splash(skill_id, skill_lv), - src, skill_id, skill_lv, tick, flag|BCT_PARTY|1, skill->castend_nodamage_id); + if (!bl) bl = src; + i = skill->calc_heal(src, bl, skill_id, 1+rnd()%skill_lv, true); + //Eh? why double skill packet? + clif->skill_nodamage(src,bl,AL_HEAL,i,1); + clif->skill_nodamage(src,bl,skill_id,i,1); + status_heal(bl, i, 0, 0); + } break; - - case AB_LAUDARAMUS: - if( flag&1 || sd == NULL ) { - if( tsc && (tsc->data[SC_SLEEP] || tsc->data[SC_STUN] || tsc->data[SC_MANDRAGORA] || tsc->data[SC_SILENCE]) ){ - // Success Chance: (40 + 10 * Skill Level) % - if( rnd()%100 > 40+10*skill_lv ) break; - status_change_end(bl, SC_SLEEP, INVALID_TIMER); - status_change_end(bl, SC_STUN, INVALID_TIMER); - status_change_end(bl, SC_MANDRAGORA, INVALID_TIMER); - status_change_end(bl, SC_SILENCE, INVALID_TIMER); - }else // Success rate only applies to the curing effect and not stat bonus. Bonus status only applies to non infected targets - clif->skill_nodamage(bl, bl, skill_id, skill_lv, - sc_start(bl, type, 100, skill_lv, skill->get_time(skill_id, skill_lv))); - } else if( sd ) - party_foreachsamemap(skill->area_sub, sd, skill->get_splash(skill_id, skill_lv), - src, skill_id, skill_lv, tick, flag|BCT_PARTY|1, skill->castend_nodamage_id); + //Homun single-target support skills [orn] + case HAMI_BLOODLUST: + case HFLI_FLEET: + case HFLI_SPEED: + case HLIF_CHANGE: + case MH_ANGRIFFS_MODUS: + case MH_GOLDENE_FERSE: + clif->skill_nodamage(src,bl,skill_id,skill_lv, + sc_start(bl,type,100,skill_lv,skill->get_time(skill_id,skill_lv))); + if (hd) + skill->blockhomun_start(hd, skill_id, skill->get_time2(skill_id,skill_lv)); break; - case AB_CLEARANCE: - if( flag&1 || (i = skill->get_splash(skill_id, skill_lv)) < 1 ) - { //As of the behavior in official server Clearance is just a super version of Dispell skill. [Jobbie] - clif->skill_nodamage(src,bl,skill_id,skill_lv,1); - if((dstsd && (dstsd->class_&MAPID_UPPERMASK) == MAPID_SOUL_LINKER) || rnd()%100 >= 30 + 10 * skill_lv) - { - if (sd) - clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); - break; - } - if(status_isimmune(bl) || !tsc || !tsc->count) - break; - for(i=0;idata[i]) - continue; - switch (i) { - case SC_WEIGHT50: case SC_WEIGHT90: case SC_HALLUCINATION: - case SC_STRIPWEAPON: case SC_STRIPSHIELD: case SC_STRIPARMOR: - case SC_STRIPHELM: case SC_CP_WEAPON: case SC_CP_SHIELD: - case SC_CP_ARMOR: case SC_CP_HELM: case SC_COMBO: - case SC_STRFOOD: case SC_AGIFOOD: case SC_VITFOOD: - case SC_INTFOOD: case SC_DEXFOOD: case SC_LUKFOOD: - case SC_HITFOOD: case SC_FLEEFOOD: case SC_BATKFOOD: - case SC_WATKFOOD: case SC_MATKFOOD: case SC_DANCING: - case SC_SPIRIT: case SC_AUTOBERSERK: - case SC_CARTBOOST: case SC_MELTDOWN: case SC_SAFETYWALL: - case SC_SMA: case SC_SPEEDUP0: case SC_NOCHAT: - case SC_ANKLE: case SC_SPIDERWEB: case SC_JAILED: - case SC_ITEMBOOST: case SC_EXPBOOST: case SC_LIFEINSURANCE: - case SC_BOSSMAPINFO: case SC_PNEUMA: case SC_AUTOSPELL: - case SC_INCHITRATE: case SC_INCATKRATE: case SC_NEN: - case SC_READYSTORM: case SC_READYDOWN: case SC_READYTURN: - case SC_READYCOUNTER:case SC_DODGE: case SC_WARM: - case SC_SPEEDUP1: case SC_AUTOTRADE: case SC_CRITICALWOUND: - case SC_JEXPBOOST: case SC_INVINCIBLE: case SC_INVINCIBLEOFF: - case SC_HELLPOWER: case SC_MANU_ATK: case SC_MANU_DEF: - case SC_SPL_ATK: case SC_SPL_DEF: case SC_MANU_MATK: - case SC_SPL_MATK: case SC_RICHMANKIM: case SC_ETERNALCHAOS: - case SC_DRUMBATTLE: case SC_NIBELUNGEN: case SC_ROKISWEIL: - case SC_INTOABYSS: case SC_SIEGFRIED: case SC_WHISTLE: - case SC_ASSNCROS: case SC_POEMBRAGI: case SC_APPLEIDUN: - case SC_HUMMING: case SC_DONTFORGETME: case SC_FORTUNE: - case SC_SERVICE4U: case SC_FOOD_STR_CASH: case SC_FOOD_AGI_CASH: - case SC_FOOD_VIT_CASH: case SC_FOOD_DEX_CASH: case SC_FOOD_INT_CASH: - case SC_FOOD_LUK_CASH: case SC_ELECTRICSHOCKER: case SC_BITE: - case SC__STRIPACCESSORY: case SC__ENERVATION: case SC__GROOMY: - case SC__IGNORANCE: case SC__LAZINESS: case SC__UNLUCKY: - case SC__WEAKNESS: //case SC_SAVAGE_STEAK: case SC_COCKTAIL_WARG_BLOOD: - case SC_MAGNETICFIELD://case SC_MINOR_BBQ: case SC_SIROMA_ICE_TEA: - //case SC_DROCERA_HERB_STEAMED: case SC_PUTTI_TAILS_NOODLES: - case SC_NEUTRALBARRIER_MASTER: case SC_NEUTRALBARRIER: - case SC_STEALTHFIELD_MASTER: case SC_STEALTHFIELD: - case SC_LEADERSHIP: case SC_GLORYWOUNDS: case SC_SOULCOLD: - case SC_HAWKEYES: case SC_GUILDAURA: case SC_PUSH_CART: - case SC_PARTYFLEE: case SC_GT_REVITALIZE: - case SC_RAISINGDRAGON: case SC_GT_ENERGYGAIN: case SC_GT_CHANGE: - #ifdef RENEWAL - case SC_EXTREMITYFIST2: - #endif - continue; - case SC_ASSUMPTIO: - if( bl->type == BL_MOB ) - continue; + case NPC_DRAGONFEAR: + if (flag&1) { + const enum sc_type sc[] = { SC_STUN, SC_SILENCE, SC_CONFUSION, SC_BLOODING }; + int j; + j = i = rnd()%ARRAYLENGTH(sc); + while ( !sc_start2(bl,sc[i],100,skill_lv,src->id,skill->get_time2(skill_id,i+1)) ) { + i++; + if ( i == ARRAYLENGTH(sc) ) + i = 0; + if (i == j) break; - } - if(i==SC_BERSERK || i==SC_SATURDAYNIGHTFEVER) tsc->data[i]->val2=0; //Mark a dispelled berserk to avoid setting hp to 100 by setting hp penalty to 0. - status_change_end(bl,(sc_type)i,INVALID_TIMER); } break; } - iMap->foreachinrange(skill->area_sub, bl, i, BL_CHAR, src, skill_id, skill_lv, tick, flag|1, skill->castend_damage_id); - break; - - case AB_SILENTIUM: - // Should the level of Lex Divina be equivalent to the level of Silentium or should the highest level learned be used? [LimitLine] - iMap->foreachinrange(skill->area_sub, src, skill->get_splash(skill_id, skill_lv), BL_CHAR, - src, PR_LEXDIVINA, skill_lv, tick, flag|BCT_ENEMY|1, skill->castend_nodamage_id); - clif->skill_nodamage(src, bl, skill_id, skill_lv, 1); + case NPC_WIDEBLEEDING: + case NPC_WIDECONFUSE: + case NPC_WIDECURSE: + case NPC_WIDEFREEZE: + case NPC_WIDESLEEP: + case NPC_WIDESILENCE: + case NPC_WIDESTONE: + case NPC_WIDESTUN: + case NPC_SLOWCAST: + case NPC_WIDEHELLDIGNITY: + if (flag&1) + sc_start2(bl,type,100,skill_lv,src->id,skill->get_time2(skill_id,skill_lv)); + else { + skill_area_temp[2] = 0; //For SD_PREAMBLE + clif->skill_nodamage(src,bl,skill_id,skill_lv,1); + iMap->foreachinrange(skill->area_sub, bl, + skill->get_splash(skill_id, skill_lv),BL_CHAR, + src,skill_id,skill_lv,tick, flag|BCT_ENEMY|SD_PREAMBLE|1, + skill->castend_nodamage_id); + } break; - /** - * Warlock - **/ - case WL_STASIS: - if( flag&1 ) - sc_start(bl,type,100,skill_lv,skill->get_time(skill_id,skill_lv)); - else - { - iMap->foreachinrange(skill->area_sub,src,skill->get_splash(skill_id, skill_lv),BL_CHAR,src,skill_id,skill_lv,tick,(map_flag_vs(src->m)?BCT_ALL:BCT_ENEMY|BCT_SELF)|flag|1,skill->castend_nodamage_id); - clif->skill_nodamage(src, bl, skill_id, skill_lv, 1); + case NPC_WIDESOULDRAIN: + if (flag&1) + status_percent_damage(src,bl,0,((skill_lv-1)%5+1)*20,false); + else { + skill_area_temp[2] = 0; //For SD_PREAMBLE + clif->skill_nodamage(src,bl,skill_id,skill_lv,1); + iMap->foreachinrange(skill->area_sub, bl, + skill->get_splash(skill_id, skill_lv),BL_CHAR, + src,skill_id,skill_lv,tick, flag|BCT_ENEMY|SD_PREAMBLE|1, + skill->castend_nodamage_id); } break; - - case WL_WHITEIMPRISON: - if( (src == bl || battle->check_target(src, bl, BCT_ENEMY) > 0 ) && !is_boss(bl) )// Should not work with bosses. + case ALL_PARTYFLEE: + if( sd && !(flag&1) ) { - int rate = ( sd? sd->status.job_level : 50 ) / 4; - - if( src == bl ) rate = 100; // Success Chance: On self, 100% - else if(bl->type == BL_PC) rate += 20 + 10 * skill_lv; // On Players, (20 + 10 * Skill Level) % - else rate += 40 + 10 * skill_lv; // On Monsters, (40 + 10 * Skill Level) % - - if( sd ) - skill->blockpc_start(sd,skill_id,4000, false); - - if( !(tsc && tsc->data[type]) ){ - i = sc_start2(bl,type,rate,skill_lv,src->id,(src == bl)?5000:(bl->type == BL_PC)?skill->get_time(skill_id,skill_lv):skill->get_time2(skill_id, skill_lv)); - clif->skill_nodamage(src,bl,skill_id,skill_lv,i); - if( !i ) - clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); + if( !sd->status.party_id ) + { + clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); + break; } - }else - if( sd ) - clif->skill_fail(sd,skill_id,USESKILL_FAIL_TOTARGET,0); + party_foreachsamemap(skill->area_sub, sd, skill->get_splash(skill_id, skill_lv), src, skill_id, skill_lv, tick, flag|BCT_PARTY|1, skill->castend_nodamage_id); + } + else + clif->skill_nodamage(src,bl,skill_id,skill_lv,sc_start(bl,type,100,skill_lv,skill->get_time(skill_id,skill_lv))); break; - - case WL_FROSTMISTY: + case NPC_TALK: + case ALL_WEWISH: clif->skill_nodamage(src,bl,skill_id,skill_lv,1); - iMap->foreachinrange(skill->area_sub,bl,skill->get_splash(skill_id,skill_lv),BL_CHAR|BL_SKILL,src,skill_id,skill_lv,tick,flag|BCT_ENEMY,skill->castend_damage_id); break; - - case WL_JACKFROST: - clif->skill_nodamage(src,bl,skill_id,skill_lv,1); - iMap->foreachinshootrange(skill->area_sub,bl,skill->get_splash(skill_id,skill_lv),BL_CHAR|BL_SKILL,src,skill_id,skill_lv,tick,flag|BCT_ENEMY|1,skill->castend_damage_id); + case ALL_BUYING_STORE: + if( sd ) + {// players only, skill allows 5 buying slots + clif->skill_nodamage(src, bl, skill_id, skill_lv, buyingstore->setup(sd, MAX_BUYINGSTORE_SLOTS)); + } break; - - case WL_MARSHOFABYSS: - // Should marsh of abyss still apply half reduction to players after the 28/10 patch? [LimitLine] - clif->skill_nodamage(src, bl, skill_id, skill_lv, - sc_start4(bl, type, 100, skill_lv, status_get_int(src), sd ? sd->status.job_level : 50, 0, - skill->get_time(skill_id, skill_lv))); + case RK_ENCHANTBLADE: + clif->skill_nodamage(src,bl,skill_id,skill_lv,// formula not confirmed + sc_start2(bl,type,100,skill_lv,100+20*skill_lv/*+sstatus->int_/2+status_get_lv(bl)/10*/,skill->get_time(skill_id,skill_lv))); break; - - case WL_SIENNAEXECRATE: - if( status_isimmune(bl) || !tsc ) - break; - - if( flag&1 ) { - if( bl->id == skill_area_temp[1] ) - break; // Already work on this target - - if( tsc && tsc->data[SC_STONE] ) - status_change_end(bl,SC_STONE,INVALID_TIMER); - else - status_change_start(bl,SC_STONE,10000,skill_lv,0,0,1000,skill->get_time(skill_id, skill_lv),2); - } else { - int rate = 40 + 8 * skill_lv + ( sd? sd->status.job_level : 50 ) / 4; - // IroWiki says Rate should be reduced by target stats, but currently unknown - if( rnd()%100 < rate ) { // Success on First Target - if( !tsc->data[SC_STONE] ) - rate = status_change_start(bl,SC_STONE,10000,skill_lv,0,0,1000,skill->get_time(skill_id, skill_lv),2); - else { - rate = 1; - status_change_end(bl,SC_STONE,INVALID_TIMER); - } - - if( rate ) { - skill_area_temp[1] = bl->id; - iMap->foreachinrange(skill->area_sub,bl,skill->get_splash(skill_id,skill_lv),BL_CHAR,src,skill_id,skill_lv,tick,flag|BCT_ENEMY|1,skill->castend_nodamage_id); - } - // Doesn't send failure packet if it fails on defense. + case RK_DRAGONHOWLING: + if( flag&1) + sc_start(bl,type,50 + 6 * skill_lv,skill_lv,skill->get_time(skill_id,skill_lv)); + else + { + skill_area_temp[2] = 0; + clif->skill_nodamage(src,bl,skill_id,skill_lv,1); + iMap->foreachinrange(skill->area_sub, src, + skill->get_splash(skill_id,skill_lv),BL_CHAR, + src,skill_id,skill_lv,tick,flag|BCT_ENEMY|SD_PREAMBLE|1, + skill->castend_nodamage_id); + } + break; + case RK_IGNITIONBREAK: + case LG_EARTHDRIVE: + clif->skill_damage(src,bl,tick, status_get_amotion(src), 0, -30000, 1, skill_id, skill_lv, 6); + i = skill->get_splash(skill_id,skill_lv); + if( skill_id == LG_EARTHDRIVE ) { + int dummy = 1; + iMap->foreachinarea(skill->cell_overlap, src->m, src->x-i, src->y-i, src->x+i, src->y+i, BL_SKILL, LG_EARTHDRIVE, &dummy, src); } - else if( sd ) // Failure on Rate + iMap->foreachinrange(skill->area_sub, bl,i,BL_CHAR, + src,skill_id,skill_lv,tick,flag|BCT_ENEMY|1,skill->castend_damage_id); + break; + case RK_STONEHARDSKIN: + if( sd ) + { + int heal = sstatus->hp / 4; // 25% HP + if( status_charge(bl,heal,0) ) + clif->skill_nodamage(src,bl,skill_id,skill_lv,sc_start2(bl,type,100,skill_lv,heal,skill->get_time(skill_id,skill_lv))); + else clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); } break; - - case WL_SUMMONFB: - case WL_SUMMONBL: - case WL_SUMMONWB: - case WL_SUMMONSTONE: + case RK_REFRESH: { - short element = 0, sctype = 0, pos = -1; - struct status_change *sc = status_get_sc(src); - if( !sc ) break; - - for( i = SC_SPHERE_1; i <= SC_SPHERE_5; i++ ) - { - if( !sctype && !sc->data[i] ) - sctype = i; // Take the free SC - if( sc->data[i] ) - pos = max(sc->data[i]->val2,pos); - } - - if( !sctype ) - { - if( sd ) // No free slots to put SC - clif->skill_fail(sd,skill_id,USESKILL_FAIL_SUMMON,0); - break; - } - - pos++; // Used in val2 for SC. Indicates the order of this ball - switch( skill_id ) { // Set val1. The SC element for this ball - case WL_SUMMONFB: element = WLS_FIRE; break; - case WL_SUMMONBL: element = WLS_WIND; break; - case WL_SUMMONWB: element = WLS_WATER; break; - case WL_SUMMONSTONE: element = WLS_STONE; break; - } - - sc_start4(src,sctype,100,element,pos,skill_lv,0,skill->get_time(skill_id,skill_lv)); - clif->skill_nodamage(src,bl,skill_id,0,0); + int heal = status_get_max_hp(bl) * 25 / 100; + clif->skill_nodamage(src,bl,skill_id,skill_lv, + sc_start(bl,type,100,skill_lv,skill->get_time(skill_id,skill_lv))); + status_heal(bl,heal,0,1); + status_change_clear_buffs(bl,4); } break; - case WL_READING_SB: - if( sd ) { - struct status_change *sc = status_get_sc(bl); - - for( i = SC_SPELLBOOK1; i <= SC_MAXSPELLBOOK; i++) - if( sc && !sc->data[i] ) - break; - if( i == SC_MAXSPELLBOOK ) { - clif->skill_fail(sd, WL_READING_SB, USESKILL_FAIL_SPELLBOOK_READING, 0); - break; - } - - sc_start(bl, SC_STOP, 100, skill_lv, INVALID_TIMER); //Can't move while selecting a spellbook. - clif->spellbook_list(sd); - clif->skill_nodamage(src, bl, skill_id, skill_lv, 1); + case RK_MILLENNIUMSHIELD: + if( sd ){ + short shields = (rnd()%100<50) ? 4 : ((rnd()%100<80) ? 3 : 2); + sc_start4(bl,type,100,skill_lv,shields,1000,0,skill->get_time(skill_id,skill_lv)); + clif->millenniumshield(sd,shields); + clif->skill_nodamage(src,bl,skill_id,1,1); } break; - /** - * Ranger - **/ - case RA_FEARBREEZE: - clif->skill_damage(src, src, tick, status_get_amotion(src), 0, -30000, 1, skill_id, skill_lv, 6); - clif->skill_nodamage(src, bl, skill_id, skill_lv, sc_start(bl, type, 100, skill_lv, skill->get_time(skill_id, skill_lv))); - break; - case RA_WUGMASTERY: - if( sd ) { - if( !pc_iswug(sd) ) - pc->setoption(sd,sd->sc.option|OPTION_WUG); + case RK_FIGHTINGSPIRIT: + if( flag&1 ) { + if( src == bl ) + sc_start2(bl,type,100,skill_area_temp[5],10*(sd?pc->checkskill(sd,RK_RUNEMASTERY):10),skill->get_time(skill_id,skill_lv)); else - pc->setoption(sd,sd->sc.option&~OPTION_WUG); - clif->skill_nodamage(src,bl,skill_id,skill_lv,1); + sc_start(bl,type,100,skill_area_temp[5]/4,skill->get_time(skill_id,skill_lv)); + } else if( sd ) { + if( sd->status.party_id ) { + i = party_foreachsamemap(skill->area_sub,sd,skill->get_splash(skill_id,skill_lv),src,skill_id,skill_lv,tick,BCT_PARTY,skill->area_sub_count); + skill_area_temp[5] = 7 * i; // ATK + party_foreachsamemap(skill->area_sub,sd,skill->get_splash(skill_id,skill_lv),src,skill_id,skill_lv,tick,flag|BCT_PARTY|1,skill->castend_nodamage_id); + } else + sc_start2(bl,type,100,7,5,skill->get_time(skill_id,skill_lv)); } + clif->skill_nodamage(src,bl,skill_id,1,1); break; - - case RA_WUGRIDER: - if( sd ) { - if( !pc_isridingwug(sd) && pc_iswug(sd) ) { - pc->setoption(sd,sd->sc.option&~OPTION_WUG); - pc->setoption(sd,sd->sc.option|OPTION_WUGRIDER); - } else if( pc_isridingwug(sd) ) { - pc->setoption(sd,sd->sc.option&~OPTION_WUGRIDER); - pc->setoption(sd,sd->sc.option|OPTION_WUG); + /** + * Guilotine Cross + **/ + case GC_ROLLINGCUTTER: + { + short count = 1; + skill_area_temp[2] = 0; + iMap->foreachinrange(skill->area_sub,src,skill->get_splash(skill_id,skill_lv),BL_CHAR,src,skill_id,skill_lv,tick,flag|BCT_ENEMY|SD_PREAMBLE|SD_SPLASH|1,skill->castend_damage_id); + if( tsc && tsc->data[SC_ROLLINGCUTTER] ) + { // Every time the skill is casted the status change is reseted adding a counter. + count += (short)tsc->data[SC_ROLLINGCUTTER]->val1; + if( count > 10 ) + count = 10; // Max coounter + status_change_end(bl, SC_ROLLINGCUTTER, INVALID_TIMER); } - clif->skill_nodamage(src,bl,skill_id,skill_lv,1); - } - break; - - case RA_WUGDASH: - if( tsce ) { - clif->skill_nodamage(src,bl,skill_id,skill_lv,status_change_end(bl, type, INVALID_TIMER)); - iMap->freeblock_unlock(); - return 0; - } - if( sd && pc_isridingwug(sd) ) { - clif->skill_nodamage(src,bl,skill_id,skill_lv,sc_start4(bl,type,100,skill_lv,unit_getdir(bl),0,0,1)); - clif->walkok(sd); + sc_start(bl,SC_ROLLINGCUTTER,100,count,skill->get_time(skill_id,skill_lv)); + clif->skill_nodamage(src,src,skill_id,skill_lv,1); } break; - case RA_SENSITIVEKEEN: + case GC_WEAPONBLOCKING: + if( tsc && tsc->data[SC_WEAPONBLOCKING] ) + status_change_end(bl, SC_WEAPONBLOCKING, INVALID_TIMER); + else + sc_start(bl,SC_WEAPONBLOCKING,100,skill_lv,skill->get_time(skill_id,skill_lv)); clif->skill_nodamage(src,bl,skill_id,skill_lv,1); - clif->skill_damage(src,src,tick, status_get_amotion(src), 0, -30000, 1, skill_id, skill_lv, 6); - iMap->foreachinrange(skill->area_sub,src,skill->get_splash(skill_id,skill_lv),BL_CHAR|BL_SKILL,src,skill_id,skill_lv,tick,flag|BCT_ENEMY,skill->castend_damage_id); break; - /** - * Mechanic - **/ - case NC_F_SIDESLIDE: - case NC_B_SIDESLIDE: + + case GC_CREATENEWPOISON: + if( sd ) { - uint8 dir = (skill_id == NC_F_SIDESLIDE) ? (unit_getdir(src)+4)%8 : unit_getdir(src); - skill->blown(src,bl,skill->get_blewcount(skill_id,skill_lv),dir,0x1); - clif->slide(src,src->x,src->y); - clif->fixpos(src); //Aegis sent this packet - clif->skill_nodamage(src,bl,skill_id,skill_lv,1); + clif->skill_produce_mix_list(sd,skill_id,25); + clif->skill_nodamage(src, bl, skill_id, skill_lv, 1); } break; - case NC_SELFDESTRUCTION: + case GC_POISONINGWEAPON: if( sd ) { - if( pc_ismadogear(sd) ) - pc->setmadogear(sd, 0); - clif->skill_nodamage(src, bl, skill_id, skill_lv, 1); - skill->castend_damage_id(src, src, skill_id, skill_lv, tick, flag); - status_set_sp(src, 0, 0); + clif->poison_list(sd,skill_lv); + clif->skill_nodamage(src,bl,skill_id,skill_lv,1); } break; - case NC_ANALYZE: - clif->skill_damage(src, bl, tick, status_get_amotion(src), 0, -30000, 1, skill_id, skill_lv, 6); - clif->skill_nodamage(src, bl, skill_id, skill_lv, - sc_start(bl,type, 30 + 12 * skill_lv,skill_lv,skill->get_time(skill_id,skill_lv))); - if( sd ) pc->overheat(sd,1); - break; - - case NC_MAGNETICFIELD: - if( (i = sc_start2(bl,type,100,skill_lv,src->id,skill->get_time(skill_id,skill_lv))) ) + case GC_ANTIDOTE: + clif->skill_nodamage(src,bl,skill_id,skill_lv,1); + if( tsc ) { - iMap->foreachinrange(skill->area_sub,src,skill->get_splash(skill_id,skill_lv),splash_target(src),src,skill_id,skill_lv,tick,flag|BCT_ENEMY|SD_SPLASH|1,skill->castend_damage_id);; - clif->skill_damage(src,src,tick,status_get_amotion(src),0,-30000,1,skill_id,skill_lv,6); - if (sd) pc->overheat(sd,1); + status_change_end(bl, SC_PARALYSE, INVALID_TIMER); + status_change_end(bl, SC_PYREXIA, INVALID_TIMER); + status_change_end(bl, SC_DEATHHURT, INVALID_TIMER); + status_change_end(bl, SC_LEECHESEND, INVALID_TIMER); + status_change_end(bl, SC_VENOMBLEED, INVALID_TIMER); + status_change_end(bl, SC_MAGICMUSHROOM, INVALID_TIMER); + status_change_end(bl, SC_TOXIN, INVALID_TIMER); + status_change_end(bl, SC_OBLIVIONCURSE, INVALID_TIMER); } - clif->skill_nodamage(src,src,skill_id,skill_lv,i); break; - case NC_REPAIR: - if( sd ) + case GC_PHANTOMMENACE: + clif->skill_damage(src,bl,tick, status_get_amotion(src), 0, -30000, 1, skill_id, skill_lv, 6); + clif->skill_nodamage(src,bl,skill_id,skill_lv,1); + iMap->foreachinrange(skill->area_sub,src,skill->get_splash(skill_id,skill_lv),BL_CHAR, + src,skill_id,skill_lv,tick,flag|BCT_ENEMY|1,skill->castend_damage_id); + break; + + case GC_HALLUCINATIONWALK: { - int heal; - if( dstsd && pc_ismadogear(dstsd) ) + int heal = status_get_max_hp(bl) / 10; + if( status_get_hp(bl) < heal ) { // if you haven't enough HP skill fails. + if( sd ) clif->skill_fail(sd,skill_id,USESKILL_FAIL_HP_INSUFFICIENT,0); + break; + } + if( !status_charge(bl,heal,0) ) { - heal = dstsd->status.max_hp * (3+3*skill_lv) / 100; - status_heal(bl,heal,0,2); - } else { - heal = sd->status.max_hp * (3+3*skill_lv) / 100; - status_heal(src,heal,0,2); + if( sd ) clif->skill_fail(sd,skill_id,USESKILL_FAIL_HP_INSUFFICIENT,0); + break; } - - clif->skill_damage(src, src, tick, status_get_amotion(src), 0, -30000, 1, skill_id, skill_lv, 6); - clif->skill_nodamage(src, bl, skill_id, skill_lv, heal); + clif->skill_nodamage(src,bl,skill_id,skill_lv,sc_start(bl,type,100,skill_lv,skill->get_time(skill_id,skill_lv))); + } + break; + /** + * Arch Bishop + **/ + case AB_ANCILLA: + if( sd ) { + clif->skill_nodamage(src,bl,skill_id,skill_lv,1); + skill->produce_mix(sd, skill_id, ITEMID_ANCILLA, 0, 0, 0, 1); } break; - case NC_DISJOINT: + case AB_CLEMENTIA: + case AB_CANTO: { - if( bl->type != BL_MOB ) break; - md = iMap->id2md(bl->id); - if( md && md->class_ >= MOBID_SILVERSNIPER && md->class_ <= MOBID_MAGICDECOY_WIND ) - status_kill(bl); - clif->skill_nodamage(src, bl, skill_id, skill_lv, 1); + int bless_lv = pc->checkskill(sd,AL_BLESSING) + (sd->status.job_level / 10); + int agi_lv = pc->checkskill(sd,AL_INCAGI) + (sd->status.job_level / 10); + if( sd == NULL || sd->status.party_id == 0 || flag&1 ) + clif->skill_nodamage(bl, bl, skill_id, skill_lv, sc_start(bl,type,100, + (skill_id == AB_CLEMENTIA)? bless_lv : (skill_id == AB_CANTO)? agi_lv : skill_lv, skill->get_time(skill_id,skill_lv))); + else if( sd ) + party_foreachsamemap(skill->area_sub, sd, skill->get_splash(skill_id, skill_lv), src, skill_id, skill_lv, tick, flag|BCT_PARTY|1, skill->castend_nodamage_id); } break; - case SC_AUTOSHADOWSPELL: - if( sd ) { - int idx1 = skill->get_index(sd->reproduceskill_id), idx2 = skill->get_index(sd->cloneskill_id); - if( sd->status.skill[idx1].id || sd->status.skill[idx2].id ) { - sc_start(src,SC_STOP,100,skill_lv,-1);// The skill_lv is stored in val1 used in skill_select_menu to determine the used skill lvl [Xazax] - clif->autoshadowspell_list(sd); - clif->skill_nodamage(src,bl,skill_id,1,1); - } - else - clif->skill_fail(sd,skill_id,USESKILL_FAIL_IMITATION_SKILL_NONE,0); - } + + case AB_PRAEFATIO: + if( sd == NULL || sd->status.party_id == 0 || flag&1 ) + clif->skill_nodamage(bl, bl, skill_id, skill_lv, sc_start4(bl, type, 100, skill_lv, 0, 0, 1, skill->get_time(skill_id, skill_lv))); + else if( sd ) + party_foreachsamemap(skill->area_sub, sd, skill->get_splash(skill_id, skill_lv), src, skill_id, skill_lv, tick, flag|BCT_PARTY|1, skill->castend_nodamage_id); break; - case SC_SHADOWFORM: - if( sd && dstsd && src != bl && !dstsd->shadowform_id ) { - if( clif->skill_nodamage(src,bl,skill_id,skill_lv,sc_start4(src,type,100,skill_lv,bl->id,4+skill_lv,0,skill->get_time(skill_id, skill_lv))) ) - dstsd->shadowform_id = src->id; + case AB_CHEAL: + if( sd == NULL || sd->status.party_id == 0 || flag&1 ) { + if( sd && tstatus && !battle->check_undead(tstatus->race, tstatus->def_ele) ) { + i = skill->calc_heal(src, bl, AL_HEAL, pc->checkskill(sd, AL_HEAL), true); + + if( (dstsd && pc_ismadogear(dstsd)) || status_isimmune(bl)) + i = 0; // Should heal by 0 or won't do anything?? in iRO it breaks the healing to members.. [malufett] + + clif->skill_nodamage(bl, bl, skill_id, i, 1); + if( tsc && tsc->data[SC_AKAITSUKI] && i ) + i = ~i + 1; + status_heal(bl, i, 0, 0); + } } else if( sd ) - clif->skill_fail(sd, skill_id, USESKILL_FAIL_LEVEL, 0); + party_foreachsamemap(skill->area_sub, sd, skill->get_splash(skill_id, skill_lv), src, skill_id, skill_lv, tick, flag|BCT_PARTY|1, skill->castend_nodamage_id); break; - case SC_BODYPAINT: - if( flag&1 ) { - if( tsc && (tsc->data[SC_HIDING] || tsc->data[SC_CLOAKING] || - tsc->data[SC_CHASEWALK] || tsc->data[SC_CLOAKINGEXCEED] || - tsc->data[SC__INVISIBILITY]) ) { - status_change_end(bl, SC_HIDING, INVALID_TIMER); - status_change_end(bl, SC_CLOAKING, INVALID_TIMER); - status_change_end(bl, SC_CHASEWALK, INVALID_TIMER); - status_change_end(bl, SC_CLOAKINGEXCEED, INVALID_TIMER); - status_change_end(bl, SC__INVISIBILITY, INVALID_TIMER); - - sc_start(bl,type,100,skill_lv,skill->get_time(skill_id,skill_lv)); - sc_start(bl,SC_BLIND,53 + 2 * skill_lv,skill_lv,skill->get_time(skill_id,skill_lv)); - } - } else { - clif->skill_nodamage(src, bl, skill_id, 0, 1); - iMap->foreachinrange(skill->area_sub, bl, skill->get_splash(skill_id, skill_lv), BL_CHAR, + case AB_ORATIO: + if( flag&1 ) + sc_start(bl, type, 40 + 5 * skill_lv, skill_lv, skill->get_time(skill_id, skill_lv)); + else + { + iMap->foreachinrange(skill->area_sub, src, skill->get_splash(skill_id, skill_lv), BL_CHAR, src, skill_id, skill_lv, tick, flag|BCT_ENEMY|1, skill->castend_nodamage_id); + clif->skill_nodamage(src, bl, skill_id, skill_lv, 1); } break; - case SC_ENERVATION: - case SC_GROOMY: - case SC_LAZINESS: - case SC_UNLUCKY: - case SC_WEAKNESS: - if( !(tsc && tsc->data[type]) ) { - //((rand(myDEX / 12, myDEX / 4) + myJobLevel + 10 * skLevel) + myLevel / 10) - (targetLevel / 10 + targetLUK / 10 + (targetMaxWeight - targetWeight) / 1000 + rand(targetAGI / 6, targetAGI / 3)) - int rate = rnd_value(sstatus->dex/12,sstatus->dex/4) + 10*skill_lv + (sd?sd->status.job_level:0) + status_get_lv(src)/10 - - status_get_lv(bl)/10 - tstatus->luk/10 - (dstsd?(dstsd->max_weight-dstsd->weight)/10000:0) - rnd_value(tstatus->agi/6,tstatus->agi/3); - rate = cap_value(rate, skill_lv+sstatus->dex/20, 100); - clif->skill_nodamage(src,bl,skill_id,0,sc_start(bl,type,rate,skill_lv,skill->get_time(skill_id,skill_lv))); + case AB_LAUDAAGNUS: + if( flag&1 || sd == NULL ) { + if( tsc && (tsc->data[SC_FREEZE] || tsc->data[SC_STONE] || tsc->data[SC_BLIND] || + tsc->data[SC_BURNING] || tsc->data[SC_FROSTMISTY] || tsc->data[SC_CRYSTALIZE])) { + // Success Chance: (40 + 10 * Skill Level) % + if( rnd()%100 > 40+10*skill_lv ) break; + status_change_end(bl, SC_FREEZE, INVALID_TIMER); + status_change_end(bl, SC_STONE, INVALID_TIMER); + status_change_end(bl, SC_BLIND, INVALID_TIMER); + status_change_end(bl, SC_BURNING, INVALID_TIMER); + status_change_end(bl, SC_FROSTMISTY, INVALID_TIMER); + status_change_end(bl, SC_CRYSTALIZE, INVALID_TIMER); + }else //Success rate only applies to the curing effect and not stat bonus. Bonus status only applies to non infected targets + clif->skill_nodamage(bl, bl, skill_id, skill_lv, + sc_start(bl, type, 100, skill_lv, skill->get_time(skill_id, skill_lv))); } else if( sd ) - clif->skill_fail(sd,skill_id,0,0); + party_foreachsamemap(skill->area_sub, sd, skill->get_splash(skill_id, skill_lv), + src, skill_id, skill_lv, tick, flag|BCT_PARTY|1, skill->castend_nodamage_id); break; - case SC_IGNORANCE: - if( !(tsc && tsc->data[type]) ) { - int rate = rnd_value(sstatus->dex/12,sstatus->dex/4) + 10*skill_lv + (sd?sd->status.job_level:0) + status_get_lv(src)/10 - - status_get_lv(bl)/10 - tstatus->luk/10 - (dstsd?(dstsd->max_weight-dstsd->weight)/10000:0) - rnd_value(tstatus->agi/6,tstatus->agi/3); - rate = cap_value(rate, skill_lv+sstatus->dex/20, 100); - if (clif->skill_nodamage(src,bl,skill_id,0,sc_start(bl,type,rate,skill_lv,skill->get_time(skill_id,skill_lv)))) { - int sp = 200 * skill_lv; - if( dstmd ) sp = dstmd->level * 2; - if( status_zap(bl,0,sp) ) - status_heal(src,0,sp/2,3); - } - else if( sd ) clif->skill_fail(sd,skill_id,0,0); + case AB_LAUDARAMUS: + if( flag&1 || sd == NULL ) { + if( tsc && (tsc->data[SC_SLEEP] || tsc->data[SC_STUN] || tsc->data[SC_MANDRAGORA] || tsc->data[SC_SILENCE]) ){ + // Success Chance: (40 + 10 * Skill Level) % + if( rnd()%100 > 40+10*skill_lv ) break; + status_change_end(bl, SC_SLEEP, INVALID_TIMER); + status_change_end(bl, SC_STUN, INVALID_TIMER); + status_change_end(bl, SC_MANDRAGORA, INVALID_TIMER); + status_change_end(bl, SC_SILENCE, INVALID_TIMER); + }else // Success rate only applies to the curing effect and not stat bonus. Bonus status only applies to non infected targets + clif->skill_nodamage(bl, bl, skill_id, skill_lv, + sc_start(bl, type, 100, skill_lv, skill->get_time(skill_id, skill_lv))); } else if( sd ) - clif->skill_fail(sd,skill_id,0,0); + party_foreachsamemap(skill->area_sub, sd, skill->get_splash(skill_id, skill_lv), + src, skill_id, skill_lv, tick, flag|BCT_PARTY|1, skill->castend_nodamage_id); break; - case LG_TRAMPLE: - clif->skill_damage(src,bl,tick, status_get_amotion(src), 0, -30000, 1, skill_id, skill_lv, 6); - iMap->foreachinrange(skill->destroy_trap,bl,skill->get_splash(skill_id,skill_lv),BL_SKILL,tick); + case AB_CLEARANCE: + if( flag&1 || (i = skill->get_splash(skill_id, skill_lv)) < 1 ) + { //As of the behavior in official server Clearance is just a super version of Dispell skill. [Jobbie] + clif->skill_nodamage(src,bl,skill_id,skill_lv,1); + if((dstsd && (dstsd->class_&MAPID_UPPERMASK) == MAPID_SOUL_LINKER) || rnd()%100 >= 30 + 10 * skill_lv) + { + if (sd) + clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); + break; + } + if(status_isimmune(bl) || !tsc || !tsc->count) + break; + for(i = 0; i < SC_MAX; i++) + { + if( SC_COMMON_MAX > i ){ + if ( !tsc->data[i] || !status_get_sc_type(i) ) + continue; + if ( status_get_sc_type(i)&SC_NO_CLEARANCE ) + continue; + } + switch (i) { + case SC_ASSUMPTIO: + if( bl->type == BL_MOB ) + continue; + break; + case SC_BERSERK: + case SC_SATURDAY_NIGHT_FEVER: + tsc->data[i]->val2=0; //Mark a dispelled berserk to avoid setting hp to 100 by setting hp penalty to 0. + break; + } + status_change_end(bl,(sc_type)i,INVALID_TIMER); + } + break; + } + iMap->foreachinrange(skill->area_sub, bl, i, BL_CHAR, src, skill_id, skill_lv, tick, flag|1, skill->castend_damage_id); break; - case LG_REFLECTDAMAGE: - if( tsc && tsc->data[type] ) - status_change_end(bl,type,INVALID_TIMER); - else + case AB_SILENTIUM: + // Should the level of Lex Divina be equivalent to the level of Silentium or should the highest level learned be used? [LimitLine] + iMap->foreachinrange(skill->area_sub, src, skill->get_splash(skill_id, skill_lv), BL_CHAR, + src, PR_LEXDIVINA, skill_lv, tick, flag|BCT_ENEMY|1, skill->castend_nodamage_id); + clif->skill_nodamage(src, bl, skill_id, skill_lv, 1); + break; + /** + * Warlock + **/ + case WL_STASIS: + if( flag&1 ) sc_start(bl,type,100,skill_lv,skill->get_time(skill_id,skill_lv)); - clif->skill_nodamage(src,bl,skill_id,skill_lv,1); + else + { + iMap->foreachinrange(skill->area_sub,src,skill->get_splash(skill_id, skill_lv),BL_CHAR,src,skill_id,skill_lv,tick,(map_flag_vs(src->m)?BCT_ALL:BCT_ENEMY|BCT_SELF)|flag|1,skill->castend_nodamage_id); + clif->skill_nodamage(src, bl, skill_id, skill_lv, 1); + } break; - case LG_SHIELDSPELL: - if( flag&1 ) { - int duration = (sd) ? sd->bonus.shieldmdef * 2000 : 10000; - sc_start(bl,SC_SILENCE,100,skill_lv,duration); - } else if( sd ) { - int opt = skill_lv; - int rate = rnd()%100; - int val, brate; - switch( skill_lv ) { - case 1: - { - struct item_data *shield_data = sd->inventory_data[sd->equip_index[EQI_HAND_L]]; - if( !shield_data || shield_data->type != IT_ARMOR ) { // No shield? - clif->skill_fail(sd, skill_id, USESKILL_FAIL_LEVEL, 0); - break; - } - brate = shield_data->def * 10; - if( rate < 50 ) - opt = 1; - else if( rate < 75 ) - opt = 2; - else - opt = 3; + case WL_WHITEIMPRISON: + if( (src == bl || battle->check_target(src, bl, BCT_ENEMY) > 0 ) && !is_boss(bl) )// Should not work with bosses. + { + int rate = ( sd? sd->status.job_level : 50 ) / 4; - switch( opt ) { - case 1: - sc_start(bl,SC_SHIELDSPELL_DEF,100,opt,-1); - clif->skill_damage(src,bl,tick, status_get_amotion(src), 0, -30000, 1, skill_id, skill_lv, 6); - if( rate < brate ) - iMap->foreachinrange(skill->area_sub,src,skill->get_splash(skill_id,skill_lv),BL_CHAR,src,skill_id,skill_lv,tick,flag|BCT_ENEMY|1,skill->castend_damage_id); - status_change_end(bl,SC_SHIELDSPELL_DEF,INVALID_TIMER); - break; - case 2: - val = shield_data->def / 10; // % Reflected damage. - sc_start2(bl,SC_SHIELDSPELL_DEF,brate,opt,val,shield_data->def * 1000); - break; - case 3: - val = shield_data->def; // Attack increase. - sc_start2(bl,SC_SHIELDSPELL_DEF,brate,opt,val,shield_data->def * 3000); - break; - } - } - break; + if( src == bl ) rate = 100; // Success Chance: On self, 100% + else if(bl->type == BL_PC) rate += 20 + 10 * skill_lv; // On Players, (20 + 10 * Skill Level) % + else rate += 40 + 10 * skill_lv; // On Monsters, (40 + 10 * Skill Level) % - case 2: - brate = sd->bonus.shieldmdef * 20; - if( rate < 30 ) - opt = 1; - else if( rate < 60 ) - opt = 2; - else - opt = 3; - switch( opt ) { - case 1: - sc_start(bl,SC_SHIELDSPELL_MDEF,100,opt,-1); - clif->skill_damage(src,bl,tick, status_get_amotion(src), 0, -30000, 1, skill_id, skill_lv, 6); - if( rate < brate ) - iMap->foreachinrange(skill->area_sub,src,skill->get_splash(skill_id,skill_lv),BL_CHAR,src,skill_id,skill_lv,tick,flag|BCT_ENEMY|2,skill->castend_damage_id); - status_change_end(bl,SC_SHIELDSPELL_MDEF,INVALID_TIMER); - break; - case 2: - sc_start(bl,SC_SHIELDSPELL_MDEF,100,opt,-1); - clif->skill_damage(src,bl,tick, status_get_amotion(src), 0, -30000, 1, skill_id, skill_lv, 6); - if( rate < brate ) - iMap->foreachinrange(skill->area_sub,src,skill->get_splash(skill_id,skill_lv),BL_CHAR,src,skill_id,skill_lv,tick,flag|BCT_ENEMY|1,skill->castend_nodamage_id); - break; - case 3: - if( sc_start(bl,SC_SHIELDSPELL_MDEF,brate,opt,sd->bonus.shieldmdef * 30000) ) - clif->skill_nodamage(src,bl,PR_MAGNIFICAT,skill_lv, - sc_start(bl,SC_MAGNIFICAT,100,1,sd->bonus.shieldmdef * 30000)); - break; - } - break; + if( sd ) + skill->blockpc_start(sd,skill_id,4000, false); - case 3: - { - struct item *it = &sd->status.inventory[sd->equip_index[EQI_HAND_L]]; - if( !it ) { // No shield? - clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); - break; - } - brate = it->refine * 5; - if( rate < 25 ) - opt = 1; - else if( rate < 50 ) - opt = 2; - else - opt = 3; - switch( opt ) { - case 1: - val = 105 * it->refine / 10; - sc_start2(bl,SC_SHIELDSPELL_REF,brate,opt,val,skill->get_time(skill_id,skill_lv)); - break; - case 2: case 3: - if( rate < brate ) - { - val = sstatus->max_hp * (11 + it->refine) / 100; - status_heal(bl, val, 0, 3); - } - break; - /*case 3: - // Full protection. I need confirm what effect should be here. Moved to case 2 to until we got it. - break;*/ - } - } - break; + if( !(tsc && tsc->data[type]) ){ + i = sc_start2(bl,type,rate,skill_lv,src->id,(src == bl)?5000:(bl->type == BL_PC)?skill->get_time(skill_id,skill_lv):skill->get_time2(skill_id, skill_lv)); + clif->skill_nodamage(src,bl,skill_id,skill_lv,i); + if( sd && !i ) + clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); } - clif->skill_nodamage(src,bl,skill_id,skill_lv,1); - } + }else + if( sd ) + clif->skill_fail(sd,skill_id,USESKILL_FAIL_TOTARGET,0); break; - case LG_PIETY: - if( flag&1 ) - sc_start(bl,type,100,skill_lv,skill->get_time(skill_id,skill_lv)); - else { - skill_area_temp[2] = 0; - iMap->foreachinrange(skill->area_sub,bl,skill->get_splash(skill_id,skill_lv),BL_PC,src,skill_id,skill_lv,tick,flag|SD_PREAMBLE|BCT_PARTY|BCT_SELF|1,skill->castend_nodamage_id); - clif->skill_nodamage(src,bl,skill_id,skill_lv,1); - } + case WL_FROSTMISTY: + clif->skill_nodamage(src,bl,skill_id,skill_lv,1); + iMap->foreachinrange(skill->area_sub,bl,skill->get_splash(skill_id,skill_lv),BL_CHAR|BL_SKILL,src,skill_id,skill_lv,tick,flag|BCT_ENEMY,skill->castend_damage_id); break; - case LG_INSPIRATION: - if( sd && !map[sd->bl.m].flag.noexppenalty && sd->status.base_level != MAX_LEVEL ) { - sd->status.base_exp -= min(sd->status.base_exp, pc->nextbaseexp(sd) * 1 / 100); // 1% penalty. - sd->status.job_exp -= min(sd->status.job_exp, pc->nextjobexp(sd) * 1 / 100); - clif->updatestatus(sd,SP_BASEEXP); - clif->updatestatus(sd,SP_JOBEXP); - } - clif->skill_nodamage(bl,src,skill_id,skill_lv, - sc_start(bl, type, 100, skill_lv, skill->get_time(skill_id, skill_lv))); - break; - case SR_CURSEDCIRCLE: - if( flag&1 ) { - if( is_boss(bl) ) break; - if( sc_start2(bl, type, 100, skill_lv, src->id, skill->get_time(skill_id, skill_lv))) { - if( bl->type == BL_MOB ) - mob_unlocktarget((TBL_MOB*)bl,iTimer->gettick()); - unit_stop_attack(bl); - clif->bladestop(src, bl->id, 1); - iMap->freeblock_unlock(); - return 1; - } - } else { - int count = 0; - clif->skill_damage(src, bl, tick, status_get_amotion(src), 0, -30000, 1, skill_id, skill_lv, 6); - count = iMap->forcountinrange(skill->area_sub, src, skill->get_splash(skill_id,skill_lv), (sd)?sd->spiritball_old:15, // Assume 15 spiritballs in non-charactors - BL_CHAR, src, skill_id, skill_lv, tick, flag|BCT_ENEMY|1, skill->castend_nodamage_id); - if( sd ) pc->delspiritball(sd, count, 0); - clif->skill_nodamage(src, src, skill_id, skill_lv, - sc_start2(src, SC_CURSEDCIRCLE_ATKER, 100, skill_lv, count, skill->get_time(skill_id,skill_lv))); - } + case WL_JACKFROST: + clif->skill_nodamage(src,bl,skill_id,skill_lv,1); + iMap->foreachinshootrange(skill->area_sub,bl,skill->get_splash(skill_id,skill_lv),BL_CHAR|BL_SKILL,src,skill_id,skill_lv,tick,flag|BCT_ENEMY|1,skill->castend_damage_id); break; - case SR_RAISINGDRAGON: - if( sd ) { - short max = 5 + skill_lv; - sc_start(bl, SC_EXPLOSIONSPIRITS, 100, skill_lv, skill->get_time(skill_id, skill_lv)); - for( i = 0; i < max; i++ ) // Don't call more than max available spheres. - pc->addspiritball(sd, skill->get_time(skill_id, skill_lv), max); - clif->skill_nodamage(src, bl, skill_id, skill_lv, sc_start(bl, type, 100, skill_lv,skill->get_time(skill_id, skill_lv))); - } + case WL_MARSHOFABYSS: + clif->skill_nodamage(src, bl, skill_id, skill_lv, + sc_start(bl, type, 100, skill_lv, skill->get_time(skill_id, skill_lv))); break; - case SR_ASSIMILATEPOWER: + case WL_SIENNAEXECRATE: if( flag&1 ) { - i = 0; - if( dstsd && dstsd->spiritball && (sd == dstsd || map_flag_vs(src->m)) && (dstsd->class_&MAPID_BASEMASK)!=MAPID_GUNSLINGER ) - { - i = dstsd->spiritball; //1%sp per spiritball. - pc->delspiritball(dstsd, dstsd->spiritball, 0); - } - if( i ) status_percent_heal(src, 0, i); - clif->skill_nodamage(src, bl, skill_id, skill_lv, i ? 1:0); + if( status_isimmune(bl) || !tsc ) + break; + if( tsc && tsc->data[SC_STONE] ) + status_change_end(bl,SC_STONE,INVALID_TIMER); + else + status_change_start(bl,SC_STONE,10000,skill_lv,0,0,500,skill->get_time(skill_id, skill_lv),2); } else { - clif->skill_damage(src,bl,tick, status_get_amotion(src), 0, -30000, 1, skill_id, skill_lv, 6); - iMap->foreachinrange(skill->area_sub, bl, skill->get_splash(skill_id, skill_lv), splash_target(src), src, skill_id, skill_lv, tick, flag|BCT_ENEMY|BCT_SELF|SD_SPLASH|1, skill->castend_nodamage_id); + int rate = 45 + 5 * skill_lv; + if( rnd()%100 < rate ){ + clif->skill_nodamage(src, bl, skill_id, skill_lv, 1); + iMap->foreachinrange(skill_area_sub,bl,skill->get_splash(skill_id,skill_lv),BL_CHAR,src,skill_id,skill_lv,tick,flag|BCT_ENEMY|1,skill_castend_nodamage_id); + }else if( sd ) // Failure on Rate + clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); } break; - case SR_POWERVELOCITY: - if( !dstsd ) - break; - if( sd && dstsd->spiritball <= 5 ) { - for(i = 0; i <= 5; i++) { - pc->addspiritball(dstsd, skill->get_time(MO_CALLSPIRITS, pc->checkskill(sd,MO_CALLSPIRITS)), i); - pc->delspiritball(sd, sd->spiritball, 0); + case WL_SUMMONFB: + case WL_SUMMONBL: + case WL_SUMMONWB: + case WL_SUMMONSTONE: + for( i = SC_SUMMON1; i <= SC_SUMMON5; i++ ){ + if( tsc && !tsc->data[i] ){ // officially it doesn't work like a stack + int ele = WLS_FIRE + (skill_id - WL_SUMMONFB) - (skill_id == WL_SUMMONSTONE ? 4 : 0); + clif->skill_nodamage(src, bl, skill_id, skill_lv, + sc_start(bl, (sc_type)i, 100, ele, skill->get_time(skill_id, skill_lv))); + break; } } - clif->skill_nodamage(src, bl, skill_id, skill_lv, 1); break; - case SR_GENTLETOUCH_CURE: - { - int heal; + case WL_READING_SB: + if( sd ) { + struct status_change *sc = status_get_sc(bl); - if( status_isimmune(bl) ) - { - clif->skill_nodamage(src,bl,skill_id,skill_lv,0); + for( i = SC_SPELLBOOK1; i <= SC_SPELLBOOK7; i++) + if( sc && !sc->data[i] ) + break; + if( i == SC_SPELLBOOK7 ) { + clif->skill_fail(sd, WL_READING_SB, USESKILL_FAIL_SPELLBOOK_READING, 0); break; } - heal = 120 * skill_lv + status_get_max_hp(bl) * (2 + skill_lv) / 100; - status_heal(bl, heal, 0, 0); + sc_start(bl, SC_STOP, 100, skill_lv, INVALID_TIMER); //Can't move while selecting a spellbook. + clif->spellbook_list(sd); + clif->skill_nodamage(src, bl, skill_id, skill_lv, 1); + } + break; + /** + * Ranger + **/ + case RA_FEARBREEZE: + clif->skill_damage(src, src, tick, status_get_amotion(src), 0, -30000, 1, skill_id, skill_lv, 6); + clif->skill_nodamage(src, bl, skill_id, skill_lv, sc_start(bl, type, 100, skill_lv, skill->get_time(skill_id, skill_lv))); + break; - if( (tsc && tsc->opt1) && (rnd()%100 < ((skill_lv * 5) + (status_get_dex(src) + status_get_lv(src)) / 4) - (1 + (rnd() % 10))) ) - { - status_change_end(bl, SC_STONE, INVALID_TIMER); - status_change_end(bl, SC_FREEZE, INVALID_TIMER); - status_change_end(bl, SC_STUN, INVALID_TIMER); - status_change_end(bl, SC_POISON, INVALID_TIMER); - status_change_end(bl, SC_SILENCE, INVALID_TIMER); - status_change_end(bl, SC_BLIND, INVALID_TIMER); - status_change_end(bl, SC_HALLUCINATION, INVALID_TIMER); - status_change_end(bl, SC_BURNING, INVALID_TIMER); - status_change_end(bl, SC_FREEZING, INVALID_TIMER); - } + case RA_WUGMASTERY: + if( sd ) { + if( !pc_iswug(sd) ) + pc->setoption(sd,sd->sc.option|OPTION_WUG); + else + pc->setoption(sd,sd->sc.option&~OPTION_WUG); + clif->skill_nodamage(src,bl,skill_id,skill_lv,1); + } + break; + case RA_WUGRIDER: + if( sd ) { + if( !pc_isridingwug(sd) && pc_iswug(sd) ) { + pc->setoption(sd,sd->sc.option&~OPTION_WUG); + pc->setoption(sd,sd->sc.option|OPTION_WUGRIDER); + } else if( pc_isridingwug(sd) ) { + pc->setoption(sd,sd->sc.option&~OPTION_WUGRIDER); + pc->setoption(sd,sd->sc.option|OPTION_WUG); + } clif->skill_nodamage(src,bl,skill_id,skill_lv,1); } break; - case SR_GENTLETOUCH_CHANGE: - case SR_GENTLETOUCH_REVITALIZE: - clif->skill_nodamage(src,bl,skill_id,skill_lv, - sc_start2(bl,type,100,skill_lv,src->id,skill->get_time(skill_id,skill_lv))); + + case RA_WUGDASH: + if( tsce ) { + clif->skill_nodamage(src,bl,skill_id,skill_lv,status_change_end(bl, type, INVALID_TIMER)); + iMap->freeblock_unlock(); + return 0; + } + if( sd && pc_isridingwug(sd) ) { + clif->skill_nodamage(src,bl,skill_id,skill_lv,sc_start4(bl,type,100,skill_lv,unit_getdir(bl),0,0,1)); + clif->walkok(sd); + } break; - case WA_SWING_DANCE: - case WA_MOONLIT_SERENADE: - if( sd == NULL || sd->status.party_id == 0 || (flag & 1) ) - sc_start(bl,type,100,skill_lv,skill->get_time(skill_id,skill_lv)); - else if( sd ) { // Only shows effects on caster. + + case RA_SENSITIVEKEEN: + clif->skill_nodamage(src,bl,skill_id,skill_lv,1); + clif->skill_damage(src,src,tick, status_get_amotion(src), 0, -30000, 1, skill_id, skill_lv, 6); + iMap->foreachinrange(skill->area_sub,src,skill->get_splash(skill_id,skill_lv),BL_CHAR|BL_SKILL,src,skill_id,skill_lv,tick,flag|BCT_ENEMY,skill->castend_damage_id); + break; + /** + * Mechanic + **/ + case NC_F_SIDESLIDE: + case NC_B_SIDESLIDE: + { + uint8 dir = (skill_id == NC_F_SIDESLIDE) ? (unit_getdir(src)+4)%8 : unit_getdir(src); + skill->blown(src,bl,skill->get_blewcount(skill_id,skill_lv),dir,0); + clif->slide(src,src->x,src->y); clif->skill_nodamage(src,bl,skill_id,skill_lv,1); - party_foreachsamemap(skill->area_sub, sd, skill->get_splash(skill_id, skill_lv), src, skill_id, skill_lv, tick, flag|BCT_PARTY|1, skill->castend_nodamage_id); } break; - case WA_SYMPHONY_OF_LOVER: - case MI_RUSH_WINDMILL: - case MI_ECHOSONG: - if( sd == NULL || sd->status.party_id == 0 || (flag & 1) ) - sc_start4(bl,type,100,skill_lv,6*skill_lv,(sd?pc->checkskill(sd,WM_LESSON):0),(sd?sd->status.job_level:0),skill->get_time(skill_id,skill_lv)); - else if( sd ) { // Only shows effects on caster. - clif->skill_nodamage(src,bl,skill_id,skill_lv,1); - party_foreachsamemap(skill->area_sub, sd, skill->get_splash(skill_id, skill_lv), src, skill_id, skill_lv, tick, flag|BCT_PARTY|1, skill->castend_nodamage_id); + case NC_SELFDESTRUCTION: + if( sd ) { + if( pc_ismadogear(sd) ) + pc->setmadogear(sd, 0); + clif->skill_nodamage(src, bl, skill_id, skill_lv, 1); + skill->castend_damage_id(src, src, skill_id, skill_lv, tick, flag); + status_set_sp(src, 0, 0); } break; - case MI_HARMONIZE: - if( src != bl ) - clif->skill_nodamage(src, src, skill_id, skill_lv, sc_start(src, type, 100, skill_lv, skill->get_time(skill_id,skill_lv))); - clif->skill_nodamage(src, bl, skill_id, skill_lv, sc_start(bl, type, 100, skill_lv, skill->get_time(skill_id,skill_lv))); + case NC_ANALYZE: + clif->skill_damage(src, bl, tick, status_get_amotion(src), 0, -30000, 1, skill_id, skill_lv, 6); + clif->skill_nodamage(src, bl, skill_id, skill_lv, + sc_start(bl,type, 30 + 12 * skill_lv,skill_lv,skill->get_time(skill_id,skill_lv))); + if( sd ) pc->overheat(sd,1); break; - case WM_DEADHILLHERE: - if( bl->type == BL_PC ) { - if( !status_isdead(bl) ) - break; + case NC_MAGNETICFIELD: + if( (i = sc_start2(bl,type,100,skill_lv,src->id,skill->get_time(skill_id,skill_lv))) ) + { + iMap->foreachinrange(skill->area_sub,src,skill->get_splash(skill_id,skill_lv),splash_target(src),src,skill_id,skill_lv,tick,flag|BCT_ENEMY|SD_SPLASH|1,skill->castend_damage_id);; + clif->skill_damage(src,src,tick,status_get_amotion(src),0,-30000,1,skill_id,skill_lv,6); + if (sd) pc->overheat(sd,1); + } + clif->skill_nodamage(src,src,skill_id,skill_lv,i); + break; - if( rnd()%100 < 88 + 2 * skill_lv ) { - int heal = tstatus->sp; - if( heal <= 0 ) - heal = 1; - tstatus->hp = heal; - tstatus->sp -= tstatus->sp * ( 120 - 20 * skill_lv ) / 100; - clif->skill_nodamage(src,bl,skill_id,skill_lv,1); - pc->revive((TBL_PC*)bl,heal,0); - clif->resurrection(bl,1); + case NC_REPAIR: + if( sd ) + { + int heal; + if( dstsd && pc_ismadogear(dstsd) ) + { + heal = dstsd->status.max_hp * (3+3*skill_lv) / 100; + status_heal(bl,heal,0,2); + } else { + heal = sd->status.max_hp * (3+3*skill_lv) / 100; + status_heal(src,heal,0,2); + } + + clif->skill_damage(src, src, tick, status_get_amotion(src), 0, -30000, 1, skill_id, skill_lv, 6); + clif->skill_nodamage(src, bl, skill_id, skill_lv, heal); + } + break; + + case NC_DISJOINT: + { + if( bl->type != BL_MOB ) break; + md = iMap->id2md(bl->id); + if( md && md->class_ >= MOBID_SILVERSNIPER && md->class_ <= MOBID_MAGICDECOY_WIND ) + status_kill(bl); + clif->skill_nodamage(src, bl, skill_id, skill_lv, 1); + } + break; + case SC_AUTOSHADOWSPELL: + if( sd ) { + int idx1 = skill->get_index(sd->reproduceskill_id), idx2 = skill->get_index(sd->cloneskill_id); + if( sd->status.skill[idx1].id || sd->status.skill[idx2].id ) { + sc_start(src,SC_STOP,100,skill_lv,-1);// The skill_lv is stored in val1 used in skill_select_menu to determine the used skill lvl [Xazax] + clif->autoshadowspell_list(sd); + clif->skill_nodamage(src,bl,skill_id,1,1); } + else + clif->skill_fail(sd,skill_id,USESKILL_FAIL_IMITATION_SKILL_NONE,0); } break; - case WM_SIRCLEOFNATURE: - flag |= BCT_SELF|BCT_PARTY|BCT_GUILD; - case WM_VOICEOFSIREN: - if( skill_id != WM_SIRCLEOFNATURE ) - flag &= ~BCT_SELF; + case SC_SHADOWFORM: + if( sd && dstsd && src != bl && !dstsd->shadowform_id ) { + if( clif->skill_nodamage(src,bl,skill_id,skill_lv,sc_start4(src,type,100,skill_lv,bl->id,4+skill_lv,0,skill->get_time(skill_id, skill_lv))) ) + dstsd->shadowform_id = src->id; + } + else if( sd ) + clif->skill_fail(sd, skill_id, USESKILL_FAIL_LEVEL, 0); + break; + + case SC_BODYPAINT: if( flag&1 ) { - sc_start2(bl,type,(skill_id==WM_VOICEOFSIREN)?20+10*skill_lv:100,skill_lv,(skill_id==WM_VOICEOFSIREN)?src->id:0,skill->get_time(skill_id,skill_lv)); + if( tsc && (tsc->data[SC_HIDING] || tsc->data[SC_CLOAKING] || + tsc->data[SC_CHASEWALK] || tsc->data[SC_CLOAKINGEXCEED] || + tsc->data[SC__INVISIBILITY]) ) { + status_change_end(bl, SC_HIDING, INVALID_TIMER); + status_change_end(bl, SC_CLOAKING, INVALID_TIMER); + status_change_end(bl, SC_CHASEWALK, INVALID_TIMER); + status_change_end(bl, SC_CLOAKINGEXCEED, INVALID_TIMER); + status_change_end(bl, SC__INVISIBILITY, INVALID_TIMER); + + sc_start(bl,type,100,skill_lv,skill->get_time(skill_id,skill_lv)); + sc_start(bl,SC_BLIND,53 + 2 * skill_lv,skill_lv,skill->get_time(skill_id,skill_lv)); + } } else { - iMap->foreachinrange(skill->area_sub, src, skill->get_splash(skill_id,skill_lv),(skill_id==WM_VOICEOFSIREN)?BL_CHAR|BL_SKILL:BL_PC, src, skill_id, skill_lv, tick, flag|BCT_ENEMY|1, skill->castend_nodamage_id); - clif->skill_nodamage(src,bl,skill_id,skill_lv,1); + clif->skill_nodamage(src, bl, skill_id, 0, 1); + iMap->foreachinrange(skill->area_sub, bl, skill->get_splash(skill_id, skill_lv), BL_CHAR, + src, skill_id, skill_lv, tick, flag|BCT_ENEMY|1, skill->castend_nodamage_id); } break; - case WM_GLOOMYDAY: - clif->skill_nodamage(src,bl,skill_id,skill_lv,1); - if( dstsd && ( pc->checkskill(dstsd,KN_BRANDISHSPEAR) || pc->checkskill(dstsd,LK_SPIRALPIERCE) || - pc->checkskill(dstsd,CR_SHIELDCHARGE) || pc->checkskill(dstsd,CR_SHIELDBOOMERANG) || - pc->checkskill(dstsd,PA_SHIELDCHAIN) || pc->checkskill(dstsd,LG_SHIELDPRESS) ) ) - { - sc_start(bl,SC_GLOOMYDAY_SK,100,skill_lv,skill->get_time(skill_id,skill_lv)); - break; - } - sc_start(bl,type,100,skill_lv,skill->get_time(skill_id,skill_lv)); + case SC_ENERVATION: + case SC_GROOMY: + case SC_LAZINESS: + case SC_UNLUCKY: + case SC_WEAKNESS: + if( !(tsc && tsc->data[type]) ) { + //((rand(myDEX / 12, myDEX / 4) + myJobLevel + 10 * skLevel) + myLevel / 10) - (targetLevel / 10 + targetLUK / 10 + (targetMaxWeight - targetWeight) / 1000 + rand(targetAGI / 6, targetAGI / 3)) + int rate = rnd_value(sstatus->dex/12,sstatus->dex/4) + 10*skill_lv + (sd?sd->status.job_level:0) + status_get_lv(src)/10 + - status_get_lv(bl)/10 - tstatus->luk/10 - (dstsd?(dstsd->max_weight-dstsd->weight)/10000:0) - rnd_value(tstatus->agi/6,tstatus->agi/3); + rate = cap_value(rate, skill_lv+sstatus->dex/20, 100); + clif->skill_nodamage(src,bl,skill_id,0,sc_start(bl,type,rate,skill_lv,skill->get_time(skill_id,skill_lv))); + } else if( sd ) + clif->skill_fail(sd,skill_id,0,0); break; - case WM_SATURDAY_NIGHT_FEVER: - if( flag&1 ) { // Affect to all targets arround the caster and caster too. - if( !(tsc && tsc->data[type]) ) - sc_start(bl, type, 100, skill_lv,skill->get_time(skill_id, skill_lv)); - } else if( flag&2 ) { - if( src->id != bl->id && battle->check_target(src,bl,BCT_ENEMY) > 0 ) - status_fix_damage(src,bl,9999,clif->damage(src,bl,tick,0,0,9999,0,0,0)); - } else if( sd ) { - short chance = sstatus->int_/6 + sd->status.job_level/5 + skill_lv*4; - if( !sd->status.party_id || (rnd()%100 > chance)) { - clif->skill_fail(sd,skill_id,USESKILL_FAIL_NEED_HELPER,0); - break; + case SC_IGNORANCE: + if( !(tsc && tsc->data[type]) ) { + int rate = rnd_value(sstatus->dex/12,sstatus->dex/4) + 10*skill_lv + (sd?sd->status.job_level:0) + status_get_lv(src)/10 + - status_get_lv(bl)/10 - tstatus->luk/10 - (dstsd?(dstsd->max_weight-dstsd->weight)/10000:0) - rnd_value(tstatus->agi/6,tstatus->agi/3); + rate = cap_value(rate, skill_lv+sstatus->dex/20, 100); + if (clif->skill_nodamage(src,bl,skill_id,0,sc_start(bl,type,rate,skill_lv,skill->get_time(skill_id,skill_lv)))) { + int sp = 200 * skill_lv; + if( dstmd ) sp = dstmd->level * 2; + if( status_zap(bl,0,sp) ) + status_heal(src,0,sp/2,3); } - if( iMap->foreachinrange(skill->area_sub, bl, skill->get_splash(skill_id,skill_lv), - BL_PC, src, skill_id, skill_lv, tick, BCT_ENEMY, skill->area_sub_count) > 7 ) - flag |= 2; - else - flag |= 1; - iMap->foreachinrange(skill->area_sub, src, skill->get_splash(skill_id,skill_lv),BL_PC, src, skill_id, skill_lv, tick, flag|BCT_ENEMY|BCT_SELF, skill->castend_nodamage_id); - clif->skill_nodamage(src, bl, skill_id, skill_lv, - sc_start(src,SC_STOP,100,skill_lv,skill->get_time2(skill_id,skill_lv))); - if( flag&2 ) // Dealed here to prevent conflicts - status_fix_damage(src,bl,9999,clif->damage(src,bl,tick,0,0,9999,0,0,0)); - } + else if( sd ) clif->skill_fail(sd,skill_id,0,0); + } else if( sd ) + clif->skill_fail(sd,skill_id,0,0); break; - case WM_SONG_OF_MANA: - case WM_DANCE_WITH_WUG: - case WM_LERADS_DEW: - if( flag&1 ) { // These affect to to all party members near the caster. - struct status_change *sc = status_get_sc(src); - if( sc && sc->data[type] ) { - sc_start2(bl,type,100,skill_lv,sc->data[type]->val2,skill->get_time(skill_id,skill_lv)); - } - } else if( sd ) { - short lv = (short)skill_lv; - int count = skill->check_pc_partner(sd,skill_id,&lv,skill->get_splash(skill_id,skill_lv),1); - if( sc_start2(bl,type,100,skill_lv,count,skill->get_time(skill_id,skill_lv)) ) - party_foreachsamemap(skill->area_sub,sd,skill->get_splash(skill_id,skill_lv),src,skill_id,skill_lv,tick,flag|BCT_PARTY|1,skill->castend_nodamage_id); - clif->skill_nodamage(src,bl,skill_id,skill_lv,1); + case LG_TRAMPLE: + clif->skill_damage(src,bl,tick, status_get_amotion(src), 0, -30000, 1, skill_id, skill_lv, 6); + iMap->foreachinrange(skill->destroy_trap,bl,skill->get_splash(skill_id,skill_lv),BL_SKILL,tick); + break; - } + case LG_REFLECTDAMAGE: + if( tsc && tsc->data[type] ) + status_change_end(bl,type,INVALID_TIMER); + else + sc_start(bl,type,100,skill_lv,skill->get_time(skill_id,skill_lv)); + clif->skill_nodamage(src,bl,skill_id,skill_lv,1); break; - case WM_MELODYOFSINK: - case WM_BEYOND_OF_WARCRY: - case WM_UNLIMITED_HUMMING_VOICE: + case LG_SHIELDSPELL: if( flag&1 ) { - sc_start2(bl,type,100,skill_lv,skill_area_temp[0],skill->get_time(skill_id,skill_lv)); - } else { // These affect to all targets arround the caster. - short lv = (short)skill_lv; - skill_area_temp[0] = (sd) ? skill->check_pc_partner(sd,skill_id,&lv,skill->get_splash(skill_id,skill_lv),1) : 50; // 50% chance in non BL_PC (clones). - iMap->foreachinrange(skill->area_sub, src, skill->get_splash(skill_id,skill_lv),BL_PC, src, skill_id, skill_lv, tick, flag|BCT_ENEMY|1, skill->castend_nodamage_id); - clif->skill_nodamage(src,bl,skill_id,skill_lv,1); - } - break; + int duration = (sd) ? sd->bonus.shieldmdef * 2000 : 10000; + sc_start(bl,SC_SILENCE,100,skill_lv,duration); + } else if( sd ) { + int opt = skill_lv; + int rate = rnd()%100; + int val, brate; + switch( skill_lv ) { + case 1: + { + struct item_data *shield_data = sd->inventory_data[sd->equip_index[EQI_HAND_L]]; + if( !shield_data || shield_data->type != IT_ARMOR ) { // No shield? + clif->skill_fail(sd, skill_id, USESKILL_FAIL_LEVEL, 0); + break; + } + brate = shield_data->def * 10; + if( rate < 50 ) + opt = 1; + else if( rate < 75 ) + opt = 2; + else + opt = 3; - case WM_RANDOMIZESPELL: { - int improv_skill_id = 0, improv_skill_lv; - do { - i = rnd() % MAX_SKILL_IMPROVISE_DB; - improv_skill_id = skill_improvise_db[i].skill_id; - } while( improv_skill_id == 0 || rnd()%10000 >= skill_improvise_db[i].per ); - improv_skill_lv = 4 + skill_lv; - clif->skill_nodamage (src, bl, skill_id, skill_lv, 1); + switch( opt ) { + case 1: + sc_start(bl,SC_SHIELDSPELL_DEF,100,opt,-1); + clif->skill_damage(src,bl,tick, status_get_amotion(src), 0, -30000, 1, skill_id, skill_lv, 6); + if( rate < brate ) + iMap->foreachinrange(skill->area_sub,src,skill->get_splash(skill_id,skill_lv),BL_CHAR,src,skill_id,skill_lv,tick,flag|BCT_ENEMY|1,skill->castend_damage_id); + status_change_end(bl,SC_SHIELDSPELL_DEF,INVALID_TIMER); + break; + case 2: + val = shield_data->def / 10; // % Reflected damage. + sc_start2(bl,SC_SHIELDSPELL_DEF,brate,opt,val,shield_data->def * 1000); + break; + case 3: + val = shield_data->def; // Attack increase. + sc_start2(bl,SC_SHIELDSPELL_DEF,brate,opt,val,shield_data->def * 3000); + break; + } + } + break; - if( sd ) { - sd->state.abra_flag = 2; - sd->skillitem = improv_skill_id; - sd->skillitemlv = improv_skill_lv; - clif->item_skill(sd, improv_skill_id, improv_skill_lv); - } else { - struct unit_data *ud = unit_bl2ud(src); - int inf = skill->get_inf(improv_skill_id); - if (!ud) break; - if (inf&INF_SELF_SKILL || inf&INF_SUPPORT_SKILL) { - if (src->type == BL_PET) - bl = (struct block_list*)((TBL_PET*)src)->msd; - if (!bl) bl = src; - unit_skilluse_id(src, bl->id, improv_skill_id, improv_skill_lv); - } else { - int target_id = 0; - if (ud->target) - target_id = ud->target; - else switch (src->type) { - case BL_MOB: target_id = ((TBL_MOB*)src)->target_id; break; - case BL_PET: target_id = ((TBL_PET*)src)->target_id; break; + case 2: + brate = sd->bonus.shieldmdef * 20; + if( rate < 30 ) + opt = 1; + else if( rate < 60 ) + opt = 2; + else + opt = 3; + switch( opt ) { + case 1: + sc_start(bl,SC_SHIELDSPELL_MDEF,100,opt,-1); + clif->skill_damage(src,bl,tick, status_get_amotion(src), 0, -30000, 1, skill_id, skill_lv, 6); + if( rate < brate ) + iMap->foreachinrange(skill->area_sub,src,skill->get_splash(skill_id,skill_lv),BL_CHAR,src,skill_id,skill_lv,tick,flag|BCT_ENEMY|2,skill->castend_damage_id); + status_change_end(bl,SC_SHIELDSPELL_MDEF,INVALID_TIMER); + break; + case 2: + sc_start(bl,SC_SHIELDSPELL_MDEF,100,opt,-1); + clif->skill_damage(src,bl,tick, status_get_amotion(src), 0, -30000, 1, skill_id, skill_lv, 6); + if( rate < brate ) + iMap->foreachinrange(skill->area_sub,src,skill->get_splash(skill_id,skill_lv),BL_CHAR,src,skill_id,skill_lv,tick,flag|BCT_ENEMY|1,skill->castend_nodamage_id); + break; + case 3: + if( sc_start(bl,SC_SHIELDSPELL_MDEF,brate,opt,sd->bonus.shieldmdef * 30000) ) + clif->skill_nodamage(src,bl,PR_MAGNIFICAT,skill_lv, + sc_start(bl,SC_MAGNIFICAT,100,1,sd->bonus.shieldmdef * 30000)); + break; + } + break; + + case 3: + { + struct item *it = &sd->status.inventory[sd->equip_index[EQI_HAND_L]]; + if( !it ) { // No shield? + clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); + break; + } + brate = it->refine * 5; + if( rate < 25 ) + opt = 1; + else if( rate < 50 ) + opt = 2; + else + opt = 3; + switch( opt ) { + case 1: + val = 105 * it->refine / 10; + sc_start2(bl,SC_SHIELDSPELL_REF,brate,opt,val,skill->get_time(skill_id,skill_lv)); + break; + case 2: case 3: + if( rate < brate ) + { + val = sstatus->max_hp * (11 + it->refine) / 100; + status_heal(bl, val, 0, 3); + } + break; + /*case 3: + // Full protection. I need confirm what effect should be here. Moved to case 2 to until we got it. + break;*/ } - if (!target_id) - break; - if (skill->get_casttype(improv_skill_id) == CAST_GROUND) { - bl = iMap->id2bl(target_id); - if (!bl) bl = src; - unit_skilluse_pos(src, bl->x, bl->y, improv_skill_id, improv_skill_lv); - } else - unit_skilluse_id(src, target_id, improv_skill_id, improv_skill_lv); } + break; } + clif->skill_nodamage(src,bl,skill_id,skill_lv,1); } break; - - case RETURN_TO_ELDICASTES: - case ALL_GUARDIAN_RECALL: - if( sd ) - { - short x, y; // Destiny position. - unsigned short mapindex; - - if( skill_id == RETURN_TO_ELDICASTES) - { - x = 198; - y = 187; - mapindex = mapindex_name2id(MAP_DICASTES); - } - else + case LG_PIETY: + if( flag&1 ) + sc_start(bl,type,100,skill_lv,skill->get_time(skill_id,skill_lv)); + else { + skill_area_temp[2] = 0; + iMap->foreachinrange(skill->area_sub,bl,skill->get_splash(skill_id,skill_lv),BL_PC,src,skill_id,skill_lv,tick,flag|SD_PREAMBLE|BCT_PARTY|BCT_SELF|1,skill->castend_nodamage_id); + clif->skill_nodamage(src,bl,skill_id,skill_lv,1); + } + break; + case LG_KINGS_GRACE: + if( flag&1 ){ + sc_start(bl,type,100,skill_lv,skill->get_time(skill_id,skill_lv)); + for(i=0; idata[i]) + continue; + switch(i){ + case SC_POISON: case SC_BLIND: + case SC_FREEZE: case SC_STONE: + case SC_STUN: case SC_SLEEP: + case SC_BLOODING: case SC_CURSE: + case SC_CONFUSION: case SC_ILLUSION: + case SC_SILENCE: case SC_BURNING: + case SC_CRYSTALIZE: case SC_FROSTMISTY: + case SC_DEEP_SLEEP: case SC_FEAR: + case SC_MANDRAGORA: + status_change_end(bl, (sc_type)i, INVALID_TIMER); + } } - - if(!mapindex) - { //Given map not found? - clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); + }else { + skill_area_temp[2] = 0; + if( !map_flag_vs(src->m) && !map_flag_gvg(src->m) ) + flag |= BCT_GUILD; + iMap->foreachinrange(skill->area_sub,bl,skill->get_splash(skill_id,skill_lv),BL_PC,src,skill_id,skill_lv,tick,flag|SD_PREAMBLE|BCT_PARTY|BCT_SELF|1,skill->castend_nodamage_id); + clif->skill_nodamage(src,bl,skill_id,skill_lv,1); + } + break; + case LG_INSPIRATION: + if( sd && !map[sd->bl.m].flag.noexppenalty && sd->status.base_level != MAX_LEVEL ) { + sd->status.base_exp -= min(sd->status.base_exp, pc->nextbaseexp(sd) * 1 / 100); // 1% penalty. + sd->status.job_exp -= min(sd->status.job_exp, pc->nextjobexp(sd) * 1 / 100); + clif->updatestatus(sd,SP_BASEEXP); + clif->updatestatus(sd,SP_JOBEXP); + } + clif->skill_nodamage(bl,src,skill_id,skill_lv, + sc_start(bl, type, 100, skill_lv, skill->get_time(skill_id, skill_lv))); + break; + case SR_CURSEDCIRCLE: + if( flag&1 ) { + if( is_boss(bl) ) break; + if( sc_start2(bl, type, 100, skill_lv, src->id, skill->get_time(skill_id, skill_lv))) { + if( bl->type == BL_MOB ) + mob_unlocktarget((TBL_MOB*)bl,iTimer->gettick()); + unit_stop_attack(bl); + clif->bladestop(src, bl->id, 1); iMap->freeblock_unlock(); - return 0; + return 1; } - pc->setpos(sd, mapindex, x, y, CLR_TELEPORT); + } else { + int count = 0; + clif->skill_damage(src, bl, tick, status_get_amotion(src), 0, -30000, 1, skill_id, skill_lv, 6); + count = iMap->forcountinrange(skill->area_sub, src, skill->get_splash(skill_id,skill_lv), (sd)?sd->spiritball_old:15, // Assume 15 spiritballs in non-charactors + BL_CHAR, src, skill_id, skill_lv, tick, flag|BCT_ENEMY|1, skill->castend_nodamage_id); + if( sd ) pc->delspiritball(sd, count, 0); + clif->skill_nodamage(src, src, skill_id, skill_lv, + sc_start2(src, SC_CURSEDCIRCLE_ATKER, 100, skill_lv, count, skill->get_time(skill_id,skill_lv))); } break; - case GM_SANDMAN: - if( tsc ) { - if( tsc->opt1 == OPT1_SLEEP ) - tsc->opt1 = 0; - else - tsc->opt1 = OPT1_SLEEP; - clif->changeoption(bl); - clif->skill_nodamage (src, bl, skill_id, skill_lv, 1); + case SR_RAISINGDRAGON: + if( sd ) { + short max = 5 + skill_lv; + sc_start(bl, SC_EXPLOSIONSPIRITS, 100, skill_lv, skill->get_time(skill_id, skill_lv)); + for( i = 0; i < max; i++ ) // Don't call more than max available spheres. + pc->addspiritball(sd, skill->get_time(skill_id, skill_lv), max); + clif->skill_nodamage(src, bl, skill_id, skill_lv, sc_start(bl, type, 100, skill_lv,skill->get_time(skill_id, skill_lv))); } break; - case SO_ARRULLO: - { - // [(15 + 5 * Skill Level) + ( Caster�s INT / 5 ) + ( Caster�s Job Level / 5 ) - ( Target�s INT / 6 ) - ( Target�s LUK / 10 )] % - int rate = (15 + 5 * skill_lv) + status_get_int(src)/5 + (sd ? sd->status.job_level : 0); - rate -= status_get_int(bl)/6 - status_get_luk(bl)/10; - clif->skill_nodamage(src, bl, skill_id, skill_lv, 1); - sc_start2(bl, type, rate, skill_lv, 1, skill->get_time(skill_id, skill_lv)); + case SR_ASSIMILATEPOWER: + if( flag&1 ) { + i = 0; + if( dstsd && dstsd->spiritball && (sd == dstsd || map_flag_vs(src->m)) && (dstsd->class_&MAPID_BASEMASK)!=MAPID_GUNSLINGER ) + { + i = dstsd->spiritball; //1%sp per spiritball. + pc->delspiritball(dstsd, dstsd->spiritball, 0); + } + if( i ) status_percent_heal(src, 0, i); + clif->skill_nodamage(src, bl, skill_id, skill_lv, i ? 1:0); + } else { + clif->skill_damage(src,bl,tick, status_get_amotion(src), 0, -30000, 1, skill_id, skill_lv, 6); + iMap->foreachinrange(skill->area_sub, bl, skill->get_splash(skill_id, skill_lv), splash_target(src), src, skill_id, skill_lv, tick, flag|BCT_ENEMY|BCT_SELF|SD_SPLASH|1, skill->castend_nodamage_id); } break; - case WM_LULLABY_DEEPSLEEP: - if( flag&1 ){ - //[(Skill Level x 4) + (Voice Lessons Skill Level x 2) + (Caster�s Base Level / 15) + (Caster�s Job Level / 5)] % - int rate = (4 * skill_lv) + ( (sd) ? pc->checkskill(sd,WM_LESSON)*2 + sd->status.job_level/5 : 0 ) + status_get_lv(src) / 15; - if( bl != src ) - sc_start(bl,type,rate,skill_lv,skill->get_time(skill_id,skill_lv)); - }else { - clif->skill_nodamage(src, bl, skill_id, skill_lv, 1); - iMap->foreachinrange(skill->area_sub, bl, skill->get_splash(skill_id, skill_lv), BL_CHAR, - src, skill_id, skill_lv, tick, flag|BCT_ALL|1, skill->castend_nodamage_id); + case SR_POWERVELOCITY: + if( !dstsd ) + break; + if( sd && dstsd->spiritball <= 5 ) { + for(i = 0; i <= 5; i++) { + pc->addspiritball(dstsd, skill->get_time(MO_CALLSPIRITS, pc->checkskill(sd,MO_CALLSPIRITS)), i); + pc->delspiritball(sd, sd->spiritball, 0); + } } + clif->skill_nodamage(src, bl, skill_id, skill_lv, 1); break; - case SO_SUMMON_AGNI: - case SO_SUMMON_AQUA: - case SO_SUMMON_VENTUS: - case SO_SUMMON_TERA: - if( sd ) { - int elemental_class = skill->get_elemental_type(skill_id,skill_lv); - - // Remove previous elemental fisrt. - if( sd->ed ) - elemental_delete(sd->ed,0); + case SR_GENTLETOUCH_CURE: + { + int heal; - // Summoning the new one. - if( !elemental_create(sd,elemental_class,skill->get_time(skill_id,skill_lv)) ) { - clif->skill_fail(sd,skill_id,0,0); + if( status_isimmune(bl) ) + { + clif->skill_nodamage(src,bl,skill_id,skill_lv,0); break; } - clif->skill_nodamage(src,bl,skill_id,skill_lv,1); - } - break; - - case SO_EL_CONTROL: - if( sd ) { - int mode = EL_MODE_PASSIVE; // Standard mode. - if( !sd->ed ) break; + heal = 120 * skill_lv + status_get_max_hp(bl) * (2 + skill_lv) / 100; + status_heal(bl, heal, 0, 0); - if( skill_lv == 4 ) {// At level 4 delete elementals. - elemental_delete(sd->ed, 0); - break; - } - switch( skill_lv ) {// Select mode bassed on skill level used. - case 2: mode = EL_MODE_ASSIST; break; - case 3: mode = EL_MODE_AGGRESSIVE; break; - } - if( !elemental_change_mode(sd->ed,mode) ) { - clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); - break; + if( (tsc && tsc->opt1) && (rnd()%100 < ((skill_lv * 5) + (status_get_dex(src) + status_get_lv(src)) / 4) - (1 + (rnd() % 10))) ) + { + status_change_end(bl, SC_STONE, INVALID_TIMER); + status_change_end(bl, SC_FREEZE, INVALID_TIMER); + status_change_end(bl, SC_STUN, INVALID_TIMER); + status_change_end(bl, SC_POISON, INVALID_TIMER); + status_change_end(bl, SC_SILENCE, INVALID_TIMER); + status_change_end(bl, SC_BLIND, INVALID_TIMER); + status_change_end(bl, SC_ILLUSION, INVALID_TIMER); + status_change_end(bl, SC_BURNING, INVALID_TIMER); + status_change_end(bl, SC_FROSTMISTY, INVALID_TIMER); } - clif->skill_nodamage(src,bl,skill_id,skill_lv,1); - } - break; - case SO_EL_ACTION: - if( sd ) { - int duration = 3000; - if( !sd->ed ) break; - sd->skill_id_old = skill_id; - elemental_action(sd->ed, bl, tick); clif->skill_nodamage(src,bl,skill_id,skill_lv,1); - switch(sd->ed->db->class_){ - case 2115:case 2124: - case 2118:case 2121: - duration = 6000; - break; - case 2116:case 2119: - case 2122:case 2125: - duration = 9000; - break; - } - skill->blockpc_start(sd, skill_id, duration, false); } break; - - case SO_EL_CURE: - if( sd ) { - struct elemental_data *ed = sd->ed; - int s_hp = sd->battle_status.hp * 10 / 100, s_sp = sd->battle_status.sp * 10 / 100; - int e_hp, e_sp; - - if( !ed ) break; - if( !status_charge(&sd->bl,s_hp,s_sp) ) { - clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); - break; - } - e_hp = ed->battle_status.max_hp * 10 / 100; - e_sp = ed->battle_status.max_sp * 10 / 100; - status_heal(&ed->bl,e_hp,e_sp,3); - clif->skill_nodamage(src,&ed->bl,skill_id,skill_lv,1); - } + case SR_GENTLETOUCH_CHANGE: + case SR_GENTLETOUCH_REVITALIZE: + clif->skill_nodamage(src,bl,skill_id,skill_lv, + sc_start2(bl,type,100,skill_lv,src->id,skill->get_time(skill_id,skill_lv))); break; - - case GN_CHANGEMATERIAL: - case SO_EL_ANALYSIS: - if( sd ) { - clif->skill_nodamage(src,bl,skill_id,skill_lv,1); - clif->skill_itemlistwindow(sd,skill_id,skill_lv); - } + case SR_FLASHCOMBO: + clif->skill_nodamage(src,bl,skill_id,skill_lv,1); + for(i = SR_FLASHCOMBO_ATK_STEP1; i <= SR_FLASHCOMBO_ATK_STEP4; i++) + skill->addtimerskill(src, tick + 600 * (i - SR_FLASHCOMBO_ATK_STEP1), bl->id, 0, 0, i, skill_lv, BF_WEAPON, flag|SD_LEVEL); break; - - case GN_BLOOD_SUCKER: - { - struct status_change *sc = status_get_sc(src); - - if( sc && sc->bs_counter < skill->get_maxcount( skill_id , skill_lv) ) { - if( tsc && tsc->data[type] ){ - (sc->bs_counter)--; - status_change_end(src, type, INVALID_TIMER); // the first one cancels and the last one will take effect resetting the timer - } - clif->skill_nodamage(src, bl, skill_id, skill_lv, 1); - sc_start2(bl, type, 100, skill_lv, src->id, skill->get_time(skill_id,skill_lv)); - (sc->bs_counter)++; - } else if( sd ) { - clif->skill_fail(sd, skill_id, USESKILL_FAIL_LEVEL, 0); - break; - } + case WA_SWING_DANCE: + case WA_MOONLIT_SERENADE: + if( sd == NULL || sd->status.party_id == 0 || (flag & 1) ) + sc_start(bl,type,100,skill_lv,skill->get_time(skill_id,skill_lv)); + else if( sd ) { // Only shows effects on caster. + clif->skill_nodamage(src,bl,skill_id,skill_lv,1); + party_foreachsamemap(skill->area_sub, sd, skill->get_splash(skill_id, skill_lv), src, skill_id, skill_lv, tick, flag|BCT_PARTY|1, skill->castend_nodamage_id); } break; - case GN_MANDRAGORA: - if( flag&1 ) { - if ( clif->skill_nodamage(bl, src, skill_id, skill_lv, - sc_start(bl, type, 25 + 10 * skill_lv, skill_lv, skill->get_time(skill_id, skill_lv))) ) - status_zap(bl, 0, status_get_max_sp(bl) * (25 + 5 * skill_lv) / 100); - } else - iMap->foreachinrange(skill->area_sub, bl, skill->get_splash(skill_id, skill_lv), BL_CHAR, - src, skill_id, skill_lv, tick, flag|BCT_ENEMY|1, skill->castend_nodamage_id); + case WA_SYMPHONY_OF_LOVER: + case MI_RUSH_WINDMILL: + case MI_ECHOSONG: + if( sd == NULL || sd->status.party_id == 0 || (flag & 1) ) + sc_start4(bl,type,100,skill_lv,6*skill_lv,(sd?pc->checkskill(sd,WM_LESSON):0),(sd?sd->status.job_level:0),skill->get_time(skill_id,skill_lv)); + else if( sd ) { // Only shows effects on caster. + clif->skill_nodamage(src,bl,skill_id,skill_lv,1); + party_foreachsamemap(skill->area_sub, sd, skill->get_splash(skill_id, skill_lv), src, skill_id, skill_lv, tick, flag|BCT_PARTY|1, skill->castend_nodamage_id); + } break; - case GN_SLINGITEM: - if( sd ) { - short ammo_id; - i = sd->equip_index[EQI_AMMO]; - if( i <= 0 ) - break; // No ammo. - ammo_id = sd->inventory_data[i]->nameid; - if( ammo_id <= 0 ) + case MI_HARMONIZE: + if( src != bl ) + clif->skill_nodamage(src, src, skill_id, skill_lv, sc_start(src, type, 100, skill_lv, skill->get_time(skill_id,skill_lv))); + clif->skill_nodamage(src, bl, skill_id, skill_lv, sc_start(bl, type, 100, skill_lv, skill->get_time(skill_id,skill_lv))); + break; + + case WM_DEADHILLHERE: + if( bl->type == BL_PC ) { + if( !status_isdead(bl) ) break; - sd->itemid = ammo_id; - if( itemdb_is_GNbomb(ammo_id) ) { - if(battle->check_target(src,bl,BCT_ENEMY) > 0) {// Only attack if the target is an enemy. - if( ammo_id == 13263 ) - iMap->foreachincell(skill->area_sub,bl->m,bl->x,bl->y,BL_CHAR,src,GN_SLINGITEM_RANGEMELEEATK,skill_lv,tick,flag|BCT_ENEMY|1,skill->castend_damage_id); - else - skill->attack(BF_WEAPON,src,src,bl,GN_SLINGITEM_RANGEMELEEATK,skill_lv,tick,flag); - } else //Otherwise, it fails, shows animation and removes items. - clif->skill_fail(sd,GN_SLINGITEM_RANGEMELEEATK,0xa,0); - } else if( itemdb_is_GNthrowable(ammo_id) ){ - struct script_code *script = sd->inventory_data[i]->script; - if( !script ) - break; - if( dstsd ) - run_script(script,0,dstsd->bl.id,fake_nd->bl.id); - else - run_script(script,0,src->id,0); + + if( rnd()%100 < 88 + 2 * skill_lv ) { + int heal = tstatus->sp; + if( heal <= 0 ) + heal = 1; + tstatus->hp = heal; + tstatus->sp -= tstatus->sp * ( 120 - 20 * skill_lv ) / 100; + clif->skill_nodamage(src,bl,skill_id,skill_lv,1); + pc->revive((TBL_PC*)bl,heal,0); + clif->resurrection(bl,1); } } - clif->skill_nodamage(src,bl,skill_id,skill_lv,1); - clif->skill_nodamage(src,bl,skill_id,skill_lv,1);// This packet is received twice actually, I think it is to show the animation. break; - case GN_MIX_COOKING: - case GN_MAKEBOMB: - case GN_S_PHARMACY: - if( sd ) { - int qty = 1; - sd->skill_id_old = skill_id; - sd->skill_lv_old = skill_lv; - if( skill_id != GN_S_PHARMACY && skill_lv > 1 ) - qty = 10; - clif->cooking_list(sd,(skill_id - GN_MIX_COOKING) + 27,skill_id,qty,skill_id==GN_MAKEBOMB?5:6); + case WM_SIRCLEOFNATURE: + flag |= BCT_SELF|BCT_PARTY|BCT_GUILD; + case WM_VOICEOFSIREN: + if( skill_id != WM_SIRCLEOFNATURE ) + flag &= ~BCT_SELF; + if( flag&1 ) { + sc_start2(bl,type,(skill_id==WM_VOICEOFSIREN)?20+10*skill_lv:100,skill_lv,(skill_id==WM_VOICEOFSIREN)?src->id:0,skill->get_time(skill_id,skill_lv)); + } else { + iMap->foreachinrange(skill->area_sub, src, skill->get_splash(skill_id,skill_lv),(skill_id==WM_VOICEOFSIREN)?BL_CHAR|BL_SKILL:BL_PC, src, skill_id, skill_lv, tick, flag|BCT_ENEMY|1, skill->castend_nodamage_id); clif->skill_nodamage(src,bl,skill_id,skill_lv,1); } break; - case EL_CIRCLE_OF_FIRE: - case EL_PYROTECHNIC: - case EL_HEATER: - case EL_TROPIC: - case EL_AQUAPLAY: - case EL_COOLER: - case EL_CHILLY_AIR: - case EL_GUST: - case EL_BLAST: - case EL_WILD_STORM: - case EL_PETROLOGY: - case EL_CURSED_SOIL: - case EL_UPHEAVAL: - case EL_FIRE_CLOAK: - case EL_WATER_DROP: - case EL_WIND_CURTAIN: - case EL_SOLID_SKIN: - case EL_STONE_SHIELD: - case EL_WIND_STEP: { - struct elemental_data *ele = BL_CAST(BL_ELEM, src); - if( ele ) { - sc_type type2 = type-1; - struct status_change *sc = status_get_sc(&ele->bl); - if( (sc && sc->data[type2]) || (tsc && tsc->data[type]) ) { - elemental_clean_single_effect(ele, skill_id); - } else { - clif->skill_nodamage(src,src,skill_id,skill_lv,1); - clif->skill_damage(src, ( skill_id == EL_GUST || skill_id == EL_BLAST || skill_id == EL_WILD_STORM )?src:bl, tick, status_get_amotion(src), 0, -30000, 1, skill_id, skill_lv, 6); - if( skill_id == EL_WIND_STEP ) // There aren't teleport, just push the master away. - skill->blown(src,bl,(rnd()%skill->get_blewcount(skill_id,skill_lv))+1,rand()%8,0); - sc_start(src,type2,100,skill_lv,skill->get_time(skill_id,skill_lv)); - sc_start(bl,type,100,skill_lv,skill->get_time(skill_id,skill_lv)); - } + case WM_GLOOMYDAY: + clif->skill_nodamage(src,bl,skill_id,skill_lv,1); + if( dstsd && ( pc->checkskill(dstsd,KN_BRANDISHSPEAR) || pc->checkskill(dstsd,LK_SPIRALPIERCE) || + pc->checkskill(dstsd,CR_SHIELDCHARGE) || pc->checkskill(dstsd,CR_SHIELDBOOMERANG) || + pc->checkskill(dstsd,PA_SHIELDCHAIN) || pc->checkskill(dstsd,LG_SHIELDPRESS) ) ) + { + sc_start(bl,SC_GLOOMYDAY_SK,100,skill_lv,skill->get_time(skill_id,skill_lv)); + break; } - } + sc_start(bl,type,100,skill_lv,skill->get_time(skill_id,skill_lv)); break; - case EL_FIRE_MANTLE: - case EL_WATER_BARRIER: - case EL_ZEPHYR: - case EL_POWER_OF_GAIA: - clif->skill_nodamage(src,src,skill_id,skill_lv,1); - clif->skill_damage(src, bl, tick, status_get_amotion(src), 0, -30000, 1, skill_id, skill_lv, 6); - skill->unitsetting(src,skill_id,skill_lv,bl->x,bl->y,0); + case WM_SATURDAY_NIGHT_FEVER: + if( flag&1 ) { // Affect to all targets arround the caster and caster too. + if( !(tsc && tsc->data[type]) ) + sc_start(bl, type, 100, skill_lv,skill->get_time(skill_id, skill_lv)); + } else if( flag&2 ) { + if( src->id != bl->id && battle->check_target(src,bl,BCT_ENEMY) > 0 ) + status_fix_damage(src,bl,9999,clif->damage(src,bl,tick,0,0,9999,0,0,0)); + } else if( sd ) { + short chance = sstatus->int_/6 + sd->status.job_level/5 + skill_lv*4; + if( !sd->status.party_id || (rnd()%100 > chance)) { + clif->skill_fail(sd,skill_id,USESKILL_FAIL_NEED_HELPER,0); + break; + } + if( iMap->foreachinrange(skill->area_sub, bl, skill->get_splash(skill_id,skill_lv), + BL_PC, src, skill_id, skill_lv, tick, BCT_ENEMY, skill->area_sub_count) > 7 ) + flag |= 2; + else + flag |= 1; + iMap->foreachinrange(skill->area_sub, src, skill->get_splash(skill_id,skill_lv),BL_PC, src, skill_id, skill_lv, tick, flag|BCT_ENEMY|BCT_SELF, skill->castend_nodamage_id); + clif->skill_nodamage(src, bl, skill_id, skill_lv, + sc_start(src,SC_STOP,100,skill_lv,skill->get_time2(skill_id,skill_lv))); + if( flag&2 ) // Dealed here to prevent conflicts + status_fix_damage(src,bl,9999,clif->damage(src,bl,tick,0,0,9999,0,0,0)); + } break; - case EL_WATER_SCREEN: { - struct elemental_data *ele = BL_CAST(BL_ELEM, src); - if( ele ) { - struct status_change *sc = status_get_sc(&ele->bl); - sc_type type2 = type-1; - - clif->skill_nodamage(src,src,skill_id,skill_lv,1); - if( (sc && sc->data[type2]) || (tsc && tsc->data[type]) ) { - elemental_clean_single_effect(ele, skill_id); - } else { - // This not heals at the end. - clif->skill_damage(src, src, tick, status_get_amotion(src), 0, -30000, 1, skill_id, skill_lv, 6); - sc_start(src,type2,100,skill_lv,skill->get_time(skill_id,skill_lv)); - sc_start(bl,type,100,src->id,skill->get_time(skill_id,skill_lv)); - } + case WM_SONG_OF_MANA: + case WM_DANCE_WITH_WUG: + case WM_LERADS_DEW: + if( flag&1 ) { // These affect to to all party members near the caster. + struct status_change *sc = status_get_sc(src); + if( sc && sc->data[type] ) { + sc_start2(bl,type,100,skill_lv,sc->data[type]->val2,skill->get_time(skill_id,skill_lv)); } + } else if( sd ) { + short lv = (short)skill_lv; + int count = skill->check_pc_partner(sd,skill_id,&lv,skill->get_splash(skill_id,skill_lv),1); + if( sc_start2(bl,type,100,skill_lv,count,skill->get_time(skill_id,skill_lv)) ) + party_foreachsamemap(skill->area_sub,sd,skill->get_splash(skill_id,skill_lv),src,skill_id,skill_lv,tick,flag|BCT_PARTY|1,skill->castend_nodamage_id); + clif->skill_nodamage(src,bl,skill_id,skill_lv,1); + } break; - case KO_KAHU_ENTEN: - case KO_HYOUHU_HUBUKI: - case KO_KAZEHU_SEIRAN: - case KO_DOHU_KOUKAI: - if(sd) { - int ttype = skill->get_ele(skill_id, skill_lv); - clif->skill_nodamage(src, bl, skill_id, skill_lv, 1); - pc->add_talisman(sd, skill->get_time(skill_id, skill_lv), 10, ttype); + case WM_MELODYOFSINK: + case WM_BEYOND_OF_WARCRY: + case WM_UNLIMITED_HUMMING_VOICE: + if( flag&1 ) { + sc_start2(bl,type,100,skill_lv,skill_area_temp[0],skill->get_time(skill_id,skill_lv)); + } else { // These affect to all targets arround the caster. + short lv = (short)skill_lv; + skill_area_temp[0] = (sd) ? skill->check_pc_partner(sd,skill_id,&lv,skill->get_splash(skill_id,skill_lv),1) : 50; // 50% chance in non BL_PC (clones). + iMap->foreachinrange(skill->area_sub, src, skill->get_splash(skill_id,skill_lv),BL_PC, src, skill_id, skill_lv, tick, flag|BCT_ENEMY|1, skill->castend_nodamage_id); + clif->skill_nodamage(src,bl,skill_id,skill_lv,1); } break; - case KO_ZANZOU: - if(sd){ - struct mob_data *md; + case WM_RANDOMIZESPELL: { + int improv_skill_id = 0, improv_skill_lv; + do { + i = rnd() % MAX_SKILL_IMPROVISE_DB; + improv_skill_id = skill_improvise_db[i].skill_id; + } while( improv_skill_id == 0 || rnd()%10000 >= skill_improvise_db[i].per ); + improv_skill_lv = 4 + skill_lv; + clif->skill_nodamage (src, bl, skill_id, skill_lv, 1); - md = mob_once_spawn_sub(src, src->m, src->x, src->y, status_get_name(src), 2308, "", SZ_SMALL, AI_NONE); - if( md ) - { - md->master_id = src->id; - md->special_state.ai = AI_ZANZOU; - if( md->deletetimer != INVALID_TIMER ) - iTimer->delete_timer(md->deletetimer, mob_timer_delete); - md->deletetimer = iTimer->add_timer (iTimer->gettick() + skill->get_time(skill_id, skill_lv), mob_timer_delete, md->bl.id, 0); - mob_spawn( md ); - pc->setinvincibletimer(sd,500);// unlock target lock - clif->skill_nodamage(src,bl,skill_id,skill_lv,1); - skill->blown(src,bl,skill->get_blewcount(skill_id,skill_lv),unit_getdir(bl),0); + if( sd ) { + sd->state.abra_flag = 2; + sd->skillitem = improv_skill_id; + sd->skillitemlv = improv_skill_lv; + clif->item_skill(sd, improv_skill_id, improv_skill_lv); + } else { + struct unit_data *ud = unit_bl2ud(src); + int inf = skill->get_inf(improv_skill_id); + if (!ud) break; + if (inf&INF_SELF_SKILL || inf&INF_SUPPORT_SKILL) { + if (src->type == BL_PET) + bl = (struct block_list*)((TBL_PET*)src)->msd; + if (!bl) bl = src; + unit_skilluse_id(src, bl->id, improv_skill_id, improv_skill_lv); + } else { + int target_id = 0; + if (ud->target) + target_id = ud->target; + else switch (src->type) { + case BL_MOB: target_id = ((TBL_MOB*)src)->target_id; break; + case BL_PET: target_id = ((TBL_PET*)src)->target_id; break; + } + if (!target_id) + break; + if (skill->get_casttype(improv_skill_id) == CAST_GROUND) { + bl = iMap->id2bl(target_id); + if (!bl) bl = src; + unit_skilluse_pos(src, bl->x, bl->y, improv_skill_id, improv_skill_lv); + } else + unit_skilluse_id(src, target_id, improv_skill_id, improv_skill_lv); + } } } break; - case KO_KYOUGAKU: - if( dstsd && tsc && !tsc->data[type] && rand()%100 < tstatus->int_/2 ){ - clif->skill_nodamage(src,bl,skill_id,skill_lv, - sc_start(bl,type,100,skill_lv,skill->get_time(skill_id,skill_lv))); - }else if( sd ) - clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); - break; - - case KO_JYUSATSU: - if( dstsd && tsc && !tsc->data[type] && - rand()%100 < ((45+5*skill_lv) + skill_lv*5 - status_get_int(bl)/2) ){//[(Base chance of success) + (Skill Level x 5) - (int / 2)]%. - clif->skill_nodamage(src,bl,skill_id,skill_lv, - status_change_start(bl,type,10000,skill_lv,0,0,0,skill->get_time(skill_id,skill_lv),1)); - status_zap(bl, tstatus->max_hp*skill_lv*5/100 , 0); - if( status_get_lv(bl) <= status_get_lv(src) ) - status_change_start(bl,SC_COMA,10,skill_lv,0,src->id,0,0,0); - }else if( sd ) - clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); - break; - case KO_GENWAKU: - if ( !map_flag_gvg(src->m) && ( dstsd || dstmd ) && battle->check_target(src,bl,BCT_ENEMY) > 0 ) { - int x = src->x, y = src->y; + case RETURN_TO_ELDICASTES: + case ALL_GUARDIAN_RECALL: + if( sd ) + { + short x, y; // Destiny position. + unsigned short mapindex; - if( sd && rnd()%100 > ((45+5*skill_lv) - status_get_int(bl)/10) ){//[(Base chance of success) - (Intelligence Objectives / 10)]%. - clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); - break; + if( skill_id == RETURN_TO_ELDICASTES) + { + x = 198; + y = 187; + mapindex = mapindex_name2id(MAP_DICASTES); + } + else + { + x = 44; + y = 151; + mapindex = mapindex_name2id(MAP_MORA); } - if (unit_movepos(src,bl->x,bl->y,0,0)) { - clif->skill_nodamage(src,src,skill_id,skill_lv,1); - clif->slide(src,bl->x,bl->y) ; - sc_start(src,SC_CONFUSION,80,skill_lv,skill->get_time(skill_id,skill_lv)); - if (unit_movepos(bl,x,y,0,0)) - { - clif->skill_damage(bl,bl,tick, status_get_amotion(src), 0, -30000, 1, skill_id, -1, 6); - if( bl->type == BL_PC && pc_issit((TBL_PC*)bl)) - clif->sitting(bl); //Avoid sitting sync problem - clif->slide(bl,x,y) ; - sc_start(bl,SC_CONFUSION,80,skill_lv,skill->get_time(skill_id,skill_lv)); - } + if(!mapindex) + { //Given map not found? + clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); + iMap->freeblock_unlock(); + return 0; } + pc->setpos(sd, mapindex, x, y, CLR_TELEPORT); } break; - case OB_AKAITSUKI: - case OB_OBOROGENSOU: - if( sd && ( (skill_id == OB_OBOROGENSOU && bl->type == BL_MOB) // This skill does not work on monsters. - || is_boss(bl) ) ){ // Does not work on Boss monsters. - clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); - break; + case GM_SANDMAN: + if( tsc ) { + if( tsc->opt1 == OPT1_SLEEP ) + tsc->opt1 = 0; + else + tsc->opt1 = OPT1_SLEEP; + clif->changeoption(bl); + clif->skill_nodamage (src, bl, skill_id, skill_lv, 1); } - case KO_IZAYOI: - case OB_ZANGETSU: - case KG_KYOMU: - case KG_KAGEMUSYA: - clif->skill_nodamage(src,bl,skill_id,skill_lv, - sc_start(bl,type,100,skill_lv,skill->get_time(skill_id,skill_lv))); - clif->skill_damage(src,bl,tick, status_get_amotion(src), 0, -30000, 1, skill_id, skill_lv, 6); break; - case KG_KAGEHUMI: - if( flag&1 ){ - if(tsc && ( tsc->option&(OPTION_CLOAK|OPTION_HIDE) || - tsc->data[SC_CAMOUFLAGE] || tsc->data[SC__SHADOWFORM] || - tsc->data[SC_MARIONETTE] || tsc->data[SC_HARMONIZE])){ - sc_start(src, type, 100, skill_lv, skill->get_time(skill_id, skill_lv)); - sc_start(bl, type, 100, skill_lv, skill->get_time(skill_id, skill_lv)); - status_change_end(bl, SC_HIDING, INVALID_TIMER); - status_change_end(bl, SC_CLOAKING, INVALID_TIMER); - status_change_end(bl, SC_CLOAKINGEXCEED, INVALID_TIMER); - status_change_end(bl, SC_CAMOUFLAGE, INVALID_TIMER); - status_change_end(bl, SC__SHADOWFORM, INVALID_TIMER); - status_change_end(bl, SC_MARIONETTE, INVALID_TIMER); - status_change_end(bl, SC_HARMONIZE, INVALID_TIMER); - } - if( skill_area_temp[2] == 1 ){ - clif->skill_damage(src,src,tick, status_get_amotion(src), 0, -30000, 1, skill_id, skill_lv, 6); - sc_start(src, SC_STOP, 100, skill_lv, skill->get_time(skill_id, skill_lv)); - } - }else{ - skill_area_temp[2] = 0; - iMap->foreachinrange(skill->area_sub, bl, skill->get_splash(skill_id, skill_lv), splash_target(src), src, skill_id, skill_lv, tick, flag|BCT_ENEMY|SD_SPLASH|1, skill->castend_nodamage_id); + case SO_ARRULLO: + { + // [(15 + 5 * Skill Level) + ( Caster?s INT / 5 ) + ( Caster?s Job Level / 5 ) - ( Target?s INT / 6 ) - ( Target?s LUK / 10 )] % + int rate = (15 + 5 * skill_lv) + status_get_int(src)/5 + (sd ? sd->status.job_level : 0); + rate -= status_get_int(bl)/6 - status_get_luk(bl)/10; + clif->skill_nodamage(src, bl, skill_id, skill_lv, 1); + sc_start2(bl, type, rate, skill_lv, 1, skill->get_time(skill_id, skill_lv)); } break; - case MH_SILENT_BREEZE: { - struct status_change *ssc = status_get_sc(src); - struct block_list *m_bl = battle->get_master(src); - const enum sc_type scs[] = { - SC_MANDRAGORA, SC_HARMONIZE, SC_DEEPSLEEP, SC_VOICEOFSIREN, SC_SLEEP, SC_CONFUSION, SC_HALLUCINATION - }; - int heal; - if(tsc){ - for (i = 0; i < ARRAYLENGTH(scs); i++) { - if (tsc->data[scs[i]]) status_change_end(bl, scs[i], INVALID_TIMER); - } - if (!tsc->data[SC_SILENCE]) //put inavoidable silence on target - status_change_start(bl, SC_SILENCE, 100, skill_lv, 0,0,0, skill->get_time(skill_id, skill_lv),1|2|8); - } - heal = status_get_matk_min(src)*4; - status_heal(bl, heal, 0, 7); - - //now inflict silence on everyone - if(ssc && !ssc->data[SC_SILENCE]) //put inavoidable silence on homun - status_change_start(src, SC_SILENCE, 100, skill_lv, 0,0,0, skill->get_time(skill_id, skill_lv),1|2|8); - if(m_bl){ - struct status_change *msc = status_get_sc(m_bl); - if(msc && !msc->data[SC_SILENCE]) //put inavoidable silence on master - status_change_start(m_bl, SC_SILENCE, 100, skill_lv, 0,0,0, skill->get_time(skill_id, skill_lv),1|2|8); - } - if (hd) - skill->blockhomun_start(hd, skill_id, skill->get_cooldown(skill_id, skill_lv)); - } - break; - case MH_OVERED_BOOST: - if (hd){ - struct block_list *s_bl = battle->get_master(src); - if(hd->homunculus.hunger>50) //reduce hunger - hd->homunculus.hunger = hd->homunculus.hunger/2; - else - hd->homunculus.hunger = min(1,hd->homunculus.hunger); - if(s_bl && s_bl->type==BL_PC){ - status_set_sp(s_bl,status_get_max_sp(s_bl)/2,0); //master drain 50% sp - clif->send_homdata(((TBL_PC *)s_bl), SP_HUNGRY, hd->homunculus.hunger); //refresh hunger info - sc_start(s_bl, type, 100, skill_lv, skill->get_time(skill_id, skill_lv)); //gene bonus - } - sc_start(bl, type, 100, skill_lv, skill->get_time(skill_id, skill_lv)); - skill->blockhomun_start(hd, skill_id, skill->get_cooldown(skill_id, skill_lv)); - } - break; - case MH_GRANITIC_ARMOR: - case MH_PYROCLASTIC: { - struct block_list *s_bl = battle->get_master(src); - if(s_bl) - sc_start2(s_bl, type, 100, skill_lv, hd->homunculus.level, skill->get_time(skill_id, skill_lv)); //start on master - sc_start2(bl, type, 100, skill_lv, hd->homunculus.level, skill->get_time(skill_id, skill_lv)); - if (hd) - skill->blockhomun_start(hd, skill_id, skill->get_cooldown(skill_id, skill_lv)); - } - break; - - case MH_LIGHT_OF_REGENE: - if(hd){ - hd->homunculus.intimacy = 251; //change to neutral (can't be cast if < 750) - if(sd) clif->send_homdata(sd, SP_INTIMATE, hd->homunculus.intimacy); //refresh intimacy info + case WM_LULLABY_DEEPSLEEP: + if( flag&1 ){ + //[(Skill Level x 4) + (Voice Lessons Skill Level x 2) + (Caster?s Base Level / 15) + (Caster?s Job Level / 5)] % + int rate = (4 * skill_lv) + ( (sd) ? pc->checkskill(sd,WM_LESSON)*2 + sd->status.job_level/5 : 0 ) + status_get_lv(src) / 15; + if( bl != src ) + sc_start(bl,type,rate,skill_lv,skill->get_time(skill_id,skill_lv)); + }else { + clif->skill_nodamage(src, bl, skill_id, skill_lv, 1); + iMap->foreachinrange(skill->area_sub, bl, skill->get_splash(skill_id, skill_lv), BL_CHAR, + src, skill_id, skill_lv, tick, flag|BCT_ALL|1, skill->castend_nodamage_id); } - //don't break need to start status and start block timer - case MH_STYLE_CHANGE: - case MH_MAGMA_FLOW: - case MH_PAIN_KILLER: - sc_start(bl, type, 100, skill_lv, skill->get_time(skill_id, skill_lv)); - if (hd) - skill->blockhomun_start(hd, skill_id, skill->get_cooldown(skill_id, skill_lv)); - break; - case MH_SUMMON_LEGION: - { - int summons[5] = {1004, 1303, 1303, 1994, 1994}; - int qty[5] = {3 , 3 , 4 , 4 , 5}; - struct mob_data *md; - int i, dummy = 0; - - i = iMap->foreachinmap(skill->check_condition_mob_master_sub ,hd->bl.m, BL_MOB, hd->bl.id, summons[skill_lv-1], skill_id, &dummy); - if(i >= qty[skill_lv-1]) - break; - - for(i=0; im, src->x, src->y, status_get_name(src), summons[skill_lv - 1], "", SZ_SMALL, AI_ATTACK); - if (md) { - md->master_id = src->id; - if (md->deletetimer != INVALID_TIMER) - iTimer->delete_timer(md->deletetimer, mob_timer_delete); - md->deletetimer = iTimer->add_timer(iTimer->gettick() + skill->get_time(skill_id, skill_lv), mob_timer_delete, md->bl.id, 0); - mob_spawn(md); //Now it is ready for spawning. - sc_start4(&md->bl, SC_MODECHANGE, 100, 1, 0, MD_CANATTACK|MD_AGGRESSIVE, 0, 60000); - } - } - if (hd) - skill->blockhomun_start(hd, skill_id, skill->get_cooldown(skill_id, skill_lv)); - } - break; - default: - ShowWarning("skill_castend_nodamage_id: Unknown skill used:%d\n",skill_id); - clif->skill_nodamage(src,bl,skill_id,skill_lv,1); - iMap->freeblock_unlock(); - return 1; - } - - if(skill_id != SR_CURSEDCIRCLE){ - struct status_change *sc = status_get_sc(src); - if( sc && sc->data[SC_CURSEDCIRCLE_ATKER] )//Should only remove after the skill had been casted. - status_change_end(src,SC_CURSEDCIRCLE_ATKER,INVALID_TIMER); - } - - if (dstmd) { //Mob skill event for no damage skills (damage ones are handled in battle_calc_damage) [Skotlex] - mob_log_damage(dstmd, src, 0); //Log interaction (counts as 'attacker' for the exp bonus) - mobskill_event(dstmd, src, tick, MSC_SKILLUSED|(skill_id<<16)); - } - - if( sd && !(flag&1) ) { // ensure that the skill last-cast tick is recorded - sd->canskill_tick = iTimer->gettick(); + break; - if( sd->state.arrow_atk ) { // consume arrow on last invocation to this skill. - battle->consume_ammo(sd, skill_id, skill_lv); - } - skill->onskillusage(sd, bl, skill_id, tick); - // perform skill requirement consumption - skill->consume_requirement(sd,skill_id,skill_lv,2); - } + case SO_SUMMON_AGNI: + case SO_SUMMON_AQUA: + case SO_SUMMON_VENTUS: + case SO_SUMMON_TERA: + if( sd ) { + int elemental_class = skill->get_elemental_type(skill_id,skill_lv); - iMap->freeblock_unlock(); - return 0; -} + // Remove previous elemental fisrt. + if( sd->ed ) + elemental_delete(sd->ed,0); -/*========================================== - * - *------------------------------------------*/ -int skill_castend_id(int tid, unsigned int tick, int id, intptr_t data) -{ - struct block_list *target, *src; - struct map_session_data *sd; - struct mob_data *md; - struct unit_data *ud; - struct status_change *sc = NULL; - int inf,inf2,flag = 0; + // Summoning the new one. + if( !elemental_create(sd,elemental_class,skill->get_time(skill_id,skill_lv)) ) { + clif->skill_fail(sd,skill_id,0,0); + break; + } + clif->skill_nodamage(src,bl,skill_id,skill_lv,1); + } + break; - src = iMap->id2bl(id); - if( src == NULL ) - { - ShowDebug("skill_castend_id: src == NULL (tid=%d, id=%d)\n", tid, id); - return 0;// not found - } + case SO_EL_CONTROL: + if( sd ) { + int mode = EL_MODE_PASSIVE; // Standard mode. - ud = unit_bl2ud(src); - if( ud == NULL ) - { - ShowDebug("skill_castend_id: ud == NULL (tid=%d, id=%d)\n", tid, id); - return 0;// ??? - } + if( !sd->ed ) break; - sd = BL_CAST(BL_PC, src); - md = BL_CAST(BL_MOB, src); + if( skill_lv == 4 ) {// At level 4 delete elementals. + elemental_delete(sd->ed, 0); + break; + } + switch( skill_lv ) {// Select mode bassed on skill level used. + case 2: mode = EL_MODE_ASSIST; break; + case 3: mode = EL_MODE_AGGRESSIVE; break; + } + if( !elemental_change_mode(sd->ed,mode) ) { + clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); + break; + } + clif->skill_nodamage(src,bl,skill_id,skill_lv,1); + } + break; - if( src->prev == NULL ) { - ud->skilltimer = INVALID_TIMER; - return 0; - } + case SO_EL_ACTION: + if( sd ) { + int duration = 3000; + if( !sd->ed ) break; + sd->skill_id_old = skill_id; + elemental_action(sd->ed, bl, tick); + clif->skill_nodamage(src,bl,skill_id,skill_lv,1); + switch(sd->ed->db->class_){ + case 2115:case 2124: + case 2118:case 2121: + duration = 6000; + break; + case 2116:case 2119: + case 2122:case 2125: + duration = 9000; + break; + } + skill->blockpc_start(sd, skill_id, duration, false); + } + break; - if(ud->skill_id != SA_CASTCANCEL && ud->skill_id != SO_SPELLFIST) {// otherwise handled in unit_skillcastcancel() - if( ud->skilltimer != tid ) { - ShowError("skill_castend_id: Timer mismatch %d!=%d!\n", ud->skilltimer, tid); - ud->skilltimer = INVALID_TIMER; - return 0; - } + case SO_EL_CURE: + if( sd ) { + struct elemental_data *ed = sd->ed; + int s_hp = sd->battle_status.hp * 10 / 100, s_sp = sd->battle_status.sp * 10 / 100; + int e_hp, e_sp; - if( sd && ud->skilltimer != INVALID_TIMER && (pc->checkskill(sd,SA_FREECAST) > 0 || ud->skill_id == LG_EXEEDBREAK) ) - {// restore original walk speed - ud->skilltimer = INVALID_TIMER; - status_calc_bl(&sd->bl, SCB_SPEED); - } + if( !ed ) break; + if( !status_charge(&sd->bl,s_hp,s_sp) ) { + clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); + break; + } + e_hp = ed->battle_status.max_hp * 10 / 100; + e_sp = ed->battle_status.max_sp * 10 / 100; + status_heal(&ed->bl,e_hp,e_sp,3); + clif->skill_nodamage(src,&ed->bl,skill_id,skill_lv,1); + } + break; - ud->skilltimer = INVALID_TIMER; - } + case GN_CHANGEMATERIAL: + case SO_EL_ANALYSIS: + if( sd ) { + clif->skill_nodamage(src,bl,skill_id,skill_lv,1); + clif->skill_itemlistwindow(sd,skill_id,skill_lv); + } + break; - if (ud->skilltarget == id) - target = src; - else - target = iMap->id2bl(ud->skilltarget); + case GN_BLOOD_SUCKER: + { + struct status_change *sc = status_get_sc(src); - // Use a do so that you can break out of it when the skill fails. - do { - if(!target || target->prev==NULL) break; + if( sc && sc->bs_counter < skill->get_maxcount( skill_id , skill_lv) ) { + if( tsc && tsc->data[type] ){ + (sc->bs_counter)--; + status_change_end(src, type, INVALID_TIMER); // the first one cancels and the last one will take effect resetting the timer + } + clif->skill_nodamage(src, bl, skill_id, skill_lv, 1); + sc_start2(bl, type, 100, skill_lv, src->id, skill->get_time(skill_id,skill_lv)); + (sc->bs_counter)++; + } else if( sd ) { + clif->skill_fail(sd, skill_id, USESKILL_FAIL_LEVEL, 0); + break; + } + } + break; - if(src->m != target->m || status_isdead(src)) break; + case GN_MANDRAGORA: + if( flag&1 ) { + if ( clif->skill_nodamage(bl, src, skill_id, skill_lv, + sc_start(bl, type, 25 + 10 * skill_lv, skill_lv, skill->get_time(skill_id, skill_lv))) ) + status_zap(bl, 0, status_get_max_sp(bl) * (25 + 5 * skill_lv) / 100); + } else + iMap->foreachinrange(skill->area_sub, bl, skill->get_splash(skill_id, skill_lv), BL_CHAR, + src, skill_id, skill_lv, tick, flag|BCT_ENEMY|1, skill->castend_nodamage_id); + break; - switch (ud->skill_id) { - //These should become skill_castend_pos - case WE_CALLPARTNER: - if(sd) clif->callpartner(sd); - case WE_CALLPARENT: - case WE_CALLBABY: - case AM_RESURRECTHOMUN: - case PF_SPIDERWEB: - //Find a random spot to place the skill. [Skotlex] - inf2 = skill->get_splash(ud->skill_id, ud->skill_lv); - ud->skillx = target->x + inf2; - ud->skilly = target->y + inf2; - if (inf2 && !iMap->random_dir(target, &ud->skillx, &ud->skilly)) { - ud->skillx = target->x; - ud->skilly = target->y; + case GN_SLINGITEM: + if( sd ) { + short ammo_id; + i = sd->equip_index[EQI_AMMO]; + if( i <= 0 ) + break; // No ammo. + ammo_id = sd->inventory_data[i]->nameid; + if( ammo_id <= 0 ) + break; + sd->itemid = ammo_id; + if( itemdb_is_GNbomb(ammo_id) ) { + if(battle->check_target(src,bl,BCT_ENEMY) > 0) {// Only attack if the target is an enemy. + if( ammo_id == 13263 ) + iMap->foreachincell(skill->area_sub,bl->m,bl->x,bl->y,BL_CHAR,src,GN_SLINGITEM_RANGEMELEEATK,skill_lv,tick,flag|BCT_ENEMY|1,skill->castend_damage_id); + else + skill->attack(BF_WEAPON,src,src,bl,GN_SLINGITEM_RANGEMELEEATK,skill_lv,tick,flag); + } else //Otherwise, it fails, shows animation and removes items. + clif->skill_fail(sd,GN_SLINGITEM_RANGEMELEEATK,0xa,0); + } else if( itemdb_is_GNthrowable(ammo_id) ){ + struct script_code *script = sd->inventory_data[i]->script; + if( !script ) + break; + if( dstsd ) + run_script(script,0,dstsd->bl.id,fake_nd->bl.id); + else + run_script(script,0,src->id,0); } - ud->skilltimer=tid; - return skill->castend_pos(tid,tick,id,data); - case GN_WALLOFTHORN: - ud->skillx = target->x; - ud->skilly = target->y; - ud->skilltimer = tid; - return skill->castend_pos(tid,tick,id,data); - } + } + clif->skill_nodamage(src,bl,skill_id,skill_lv,1); + clif->skill_nodamage(src,bl,skill_id,skill_lv,1);// This packet is received twice actually, I think it is to show the animation. + break; - if(ud->skill_id == RG_BACKSTAP) { - uint8 dir = iMap->calc_dir(src,target->x,target->y),t_dir = unit_getdir(target); - if(check_distance_bl(src, target, 0) || iMap->check_dir(dir,t_dir)) { - break; + case GN_MIX_COOKING: + case GN_MAKEBOMB: + case GN_S_PHARMACY: + if( sd ) { + int qty = 1; + sd->skill_id_old = skill_id; + sd->skill_lv_old = skill_lv; + if( skill_id != GN_S_PHARMACY && skill_lv > 1 ) + qty = 10; + clif->cooking_list(sd,(skill_id - GN_MIX_COOKING) + 27,skill_id,qty,skill_id==GN_MAKEBOMB?5:6); + clif->skill_nodamage(src,bl,skill_id,skill_lv,1); } - } + break; + case EL_CIRCLE_OF_FIRE: + case EL_PYROTECHNIC: + case EL_HEATER: + case EL_TROPIC: + case EL_AQUAPLAY: + case EL_COOLER: + case EL_CHILLY_AIR: + case EL_GUST: + case EL_BLAST: + case EL_WILD_STORM: + case EL_PETROLOGY: + case EL_CURSED_SOIL: + case EL_UPHEAVAL: + case EL_FIRE_CLOAK: + case EL_WATER_DROP: + case EL_WIND_CURTAIN: + case EL_SOLID_SKIN: + case EL_STONE_SHIELD: + case EL_WIND_STEP: { + struct elemental_data *ele = BL_CAST(BL_ELEM, src); + if( ele ) { + sc_type type2 = type-1; + struct status_change *sc = status_get_sc(&ele->bl); - if( ud->skill_id == PR_TURNUNDEAD ) { - struct status_data *tstatus = status_get_status_data(target); - if( !battle->check_undead(tstatus->race, tstatus->def_ele) ) - break; - } + if( (sc && sc->data[type2]) || (tsc && tsc->data[type]) ) { + elemental_clean_single_effect(ele, skill_id); + } else { + clif->skill_nodamage(src,src,skill_id,skill_lv,1); + clif->skill_damage(src, ( skill_id == EL_GUST || skill_id == EL_BLAST || skill_id == EL_WILD_STORM )?src:bl, tick, status_get_amotion(src), 0, -30000, 1, skill_id, skill_lv, 6); + if( skill_id == EL_WIND_STEP ) // There aren't teleport, just push the master away. + skill->blown(src,bl,(rnd()%skill->get_blewcount(skill_id,skill_lv))+1,rand()%8,0); + sc_start(src,type2,100,skill_lv,skill->get_time(skill_id,skill_lv)); + sc_start(bl,type,100,skill_lv,skill->get_time(skill_id,skill_lv)); + } + } + } + break; - if( ud->skill_id == RA_WUGSTRIKE ){ - if( !path_search(NULL,src->m,src->x,src->y,target->x,target->y,1,CELL_CHKNOREACH)) - break; - } + case EL_FIRE_MANTLE: + case EL_WATER_BARRIER: + case EL_ZEPHYR: + case EL_POWER_OF_GAIA: + clif->skill_nodamage(src,src,skill_id,skill_lv,1); + clif->skill_damage(src, bl, tick, status_get_amotion(src), 0, -30000, 1, skill_id, skill_lv, 6); + skill->unitsetting(src,skill_id,skill_lv,bl->x,bl->y,0); + break; + + case EL_WATER_SCREEN: { + struct elemental_data *ele = BL_CAST(BL_ELEM, src); + if( ele ) { + struct status_change *sc = status_get_sc(&ele->bl); + sc_type type2 = type-1; - if( ud->skill_id == PR_LEXDIVINA || ud->skill_id == MER_LEXDIVINA ) - { - sc = status_get_sc(target); - if( battle->check_target(src,target, BCT_ENEMY) <= 0 && (!sc || !sc->data[SC_SILENCE]) ) - { //If it's not an enemy, and not silenced, you can't use the skill on them. [Skotlex] - clif->skill_nodamage (src, target, ud->skill_id, ud->skill_lv, 0); - break; + clif->skill_nodamage(src,src,skill_id,skill_lv,1); + if( (sc && sc->data[type2]) || (tsc && tsc->data[type]) ) { + elemental_clean_single_effect(ele, skill_id); + } else { + // This not heals at the end. + clif->skill_damage(src, src, tick, status_get_amotion(src), 0, -30000, 1, skill_id, skill_lv, 6); + sc_start(src,type2,100,skill_lv,skill->get_time(skill_id,skill_lv)); + sc_start(bl,type,100,src->id,skill->get_time(skill_id,skill_lv)); + } + } } - } - else - { // Check target validity. - inf = skill->get_inf(ud->skill_id); - inf2 = skill->get_inf2(ud->skill_id); - - if(inf&INF_ATTACK_SKILL || - (inf&INF_SELF_SKILL && inf2&INF2_NO_TARGET_SELF) //Combo skills - ) // Casted through combo. - inf = BCT_ENEMY; //Offensive skill. - else if(inf2&INF2_NO_ENEMY) - inf = BCT_NOENEMY; - else - inf = 0; + break; - if(inf2 & (INF2_PARTY_ONLY|INF2_GUILD_ONLY) && src != target) - { - inf |= - (inf2&INF2_PARTY_ONLY?BCT_PARTY:0)| - (inf2&INF2_GUILD_ONLY?BCT_GUILD:0); - //Remove neutral targets (but allow enemy if skill is designed to be so) - inf &= ~BCT_NEUTRAL; + case KO_KAHU_ENTEN: + case KO_HYOUHU_HUBUKI: + case KO_KAZEHU_SEIRAN: + case KO_DOHU_KOUKAI: + if(sd) { + int ttype = skill->get_ele(skill_id, skill_lv); + clif->skill_nodamage(src, bl, skill_id, skill_lv, 1); + ARR_FIND(1, 6, i, sd->charm[i] > 0 && ttype != i); + if( i < 6 ) + pc->del_charm(sd, sd->charm[i], i); // replace with a new one. + pc->add_charm(sd, skill->get_time(skill_id, skill_lv), 10, ttype); } + break; - if( sd && (inf2&INF2_CHORUS_SKILL) && skill->check_pc_partner(sd, ud->skill_id, &ud->skill_lv, 1, 0) < 1 ) { - clif->skill_fail(sd, ud->skill_id, USESKILL_FAIL_NEED_HELPER, 0); - break; - } + case KO_ZANZOU: + if(sd){ + struct mob_data *md; - if( ud->skill_id >= SL_SKE && ud->skill_id <= SL_SKA && target->type == BL_MOB ) - { - if( ((TBL_MOB*)target)->class_ == MOBID_EMPERIUM ) - break; - } - else if (inf && battle->check_target(src, target, inf) <= 0){ - if (sd) clif->skill_fail(sd,ud->skill_id,USESKILL_FAIL_LEVEL,0); - break; + md = mob_once_spawn_sub(src, src->m, src->x, src->y, status_get_name(src), 2308, "", SZ_SMALL, AI_NONE); + if( md ) + { + md->master_id = src->id; + md->special_state.ai = AI_ZANZOU; + if( md->deletetimer != INVALID_TIMER ) + iTimer->delete_timer(md->deletetimer, mob_timer_delete); + md->deletetimer = iTimer->add_timer (iTimer->gettick() + skill->get_time(skill_id, skill_lv), mob_timer_delete, md->bl.id, 0); + mob_spawn( md ); + pc->setinvincibletimer(sd,500);// unlock target lock + clif->skill_nodamage(src,bl,skill_id,skill_lv,1); + skill->blown(src,bl,skill->get_blewcount(skill_id,skill_lv),unit_getdir(bl),0); + } } + break; - if(inf&BCT_ENEMY && (sc = status_get_sc(target)) && - sc->data[SC_FOGWALL] && - rnd() % 100 < 75) { //Fogwall makes all offensive-type targetted skills fail at 75% - if (sd) clif->skill_fail(sd, ud->skill_id, USESKILL_FAIL_LEVEL, 0); + case KO_KYOUGAKU: + { + int rate = max(5, (45 + 5 * skill_lv - status_get_int(bl) / 10)); + if( sd && !map_flag_gvg(src->m) ){ + clif->skill_fail(sd, skill_id, USESKILL_FAIL_SIZE, 0); break; + } + if( dstsd && tsc && !tsc->data[type] && rand()%100 < rate ){ + clif->skill_nodamage(src, bl, skill_id, skill_lv, + sc_start(bl, type, 100, skill_lv, skill->get_time(skill_id, skill_lv))); + }else if( sd ) + clif->skill_fail(sd, skill_id, USESKILL_FAIL_LEVEL, 0); } - } + break; - //Avoid doing double checks for instant-cast skills. - if (tid != INVALID_TIMER && !status_check_skilluse(src, target, ud->skill_id, 1)) + case KO_JYUSATSU: + if( dstsd && tsc && !tsc->data[type] && + rand()%100 < (10 * (5 * skill_lv - status_get_int(bl) / 2 + 45 + 5 * skill_lv)) ){ + clif->skill_nodamage(src, bl, skill_id, skill_lv, + status_change_start(bl, type, 10000, skill_lv, 0, 0, 0, skill->get_time(skill_id, skill_lv), 1)); + status_zap(bl, tstatus->max_hp * skill_lv * 5 / 100 , 0); + if( status_get_lv(bl) <= status_get_lv(src) ) + status_change_start(bl, SC_COMA, skill_lv, skill_lv, 0, src->id, 0, 0, 0); + }else if( sd ) + clif->skill_fail(sd, skill_id, USESKILL_FAIL_LEVEL, 0); break; - if(md) { - md->last_thinktime=tick +MIN_MOBTHINKTIME; - if(md->skill_idx >= 0 && md->db->skill[md->skill_idx].emotion >= 0) - clif->emotion(src, md->db->skill[md->skill_idx].emotion); - } + case KO_GENWAKU: + if ( !map_flag_gvg(src->m) && ( dstsd || dstmd ) && !(tstatus->mode&MD_PLANT) && battle->check_target(src,bl,BCT_ENEMY) > 0 ) { + int x = src->x, y = src->y; + if( sd && rnd()%100 > max(5, (45 + 5 * skill_lv) - status_get_int(bl) / 10) ){//[(Base chance of success) - ( target's int / 10)]%. + clif->skill_fail(sd, skill_id, USESKILL_FAIL_LEVEL, 0); + break; + } - if(src != target && battle_config.skill_add_range && - !check_distance_bl(src, target, skill->get_range2(src,ud->skill_id,ud->skill_lv)+battle_config.skill_add_range)) - { - if (sd) { - clif->skill_fail(sd,ud->skill_id,USESKILL_FAIL_LEVEL,0); - if(battle_config.skill_out_range_consume) //Consume items anyway. [Skotlex] - skill->consume_requirement(sd,ud->skill_id,ud->skill_lv,3); + if (unit_movepos(src, bl->x, bl->y, 0, 0)) { + clif->skill_nodamage(src, src, skill_id, skill_lv, 1); + clif->slide(src, bl->x, bl->y) ; + sc_start(src, SC_CONFUSION, 25, skill_lv, skill->get_time(skill_id, skill_lv)); + if ( !is_boss(bl) && unit_stop_walking(&sd->bl, 1) && unit_movepos(bl, x, y, 0, 0) ) + { + if( dstsd && pc_issit(dstsd) ) + pc->setstand(dstsd); + clif->slide(bl, x, y) ; + sc_start(bl, SC_CONFUSION, 75, skill_lv, skill->get_time(skill_id, skill_lv)); + } + } } break; - } - if( sd ) - { - if( !skill->check_condition_castend(sd, ud->skill_id, ud->skill_lv) ) + case OB_AKAITSUKI: + case OB_OBOROGENSOU: + if( sd && ( (skill_id == OB_OBOROGENSOU && bl->type == BL_MOB) // This skill does not work on monsters. + || is_boss(bl) ) ){ // Does not work on Boss monsters. + clif->skill_fail(sd, skill_id, USESKILL_FAIL_TOTARGET_PLAYER, 0); break; - else - skill->consume_requirement(sd,ud->skill_id,ud->skill_lv,1); - } -#ifdef OFFICIAL_WALKPATH - if( !path_search_long(NULL, src->m, src->x, src->y, target->x, target->y, CELL_CHKWALL) ) - break; -#endif - if( (src->type == BL_MER || src->type == BL_HOM) && !skill->check_condition_mercenary(src, ud->skill_id, ud->skill_lv, 1) ) + } + case KO_IZAYOI: + case OB_ZANGETSU: + case KG_KYOMU: + case KG_KAGEMUSYA: + clif->skill_nodamage(src,bl,skill_id,skill_lv, + sc_start(bl,type,100,skill_lv,skill->get_time(skill_id,skill_lv))); + clif->skill_damage(src,bl,tick, status_get_amotion(src), 0, -30000, 1, skill_id, skill_lv, 6); break; - if (ud->state.running && ud->skill_id == TK_JUMPKICK) { - ud->state.running = 0; - status_change_end(src, SC_RUN, INVALID_TIMER); - flag = 1; - } + case KG_KAGEHUMI: + if( flag&1 ){ + if(tsc && ( tsc->option&(OPTION_CLOAK|OPTION_HIDE) || + tsc->data[SC_CAMOUFLAGE] || tsc->data[SC__SHADOWFORM] || + tsc->data[SC_MARIONETTE_MASTER] || tsc->data[SC_HARMONIZE])){ + sc_start(src, type, 100, skill_lv, skill->get_time(skill_id, skill_lv)); + sc_start(bl, type, 100, skill_lv, skill->get_time(skill_id, skill_lv)); + status_change_end(bl, SC_HIDING, INVALID_TIMER); + status_change_end(bl, SC_CLOAKING, INVALID_TIMER); + status_change_end(bl, SC_CLOAKINGEXCEED, INVALID_TIMER); + status_change_end(bl, SC_CAMOUFLAGE, INVALID_TIMER); + status_change_end(bl, SC__SHADOWFORM, INVALID_TIMER); + status_change_end(bl, SC_MARIONETTE_MASTER, INVALID_TIMER); + status_change_end(bl, SC_HARMONIZE, INVALID_TIMER); + } + if( skill_area_temp[2] == 1 ){ + clif->skill_damage(src,src,tick, status_get_amotion(src), 0, -30000, 1, skill_id, skill_lv, 6); + sc_start(src, SC_STOP, 100, skill_lv, skill->get_time(skill_id, skill_lv)); + } + }else{ + skill_area_temp[2] = 0; + iMap->foreachinrange(skill->area_sub, bl, skill->get_splash(skill_id, skill_lv), splash_target(src), src, skill_id, skill_lv, tick, flag|BCT_ENEMY|SD_SPLASH|1, skill->castend_nodamage_id); + } + break; - if (ud->walktimer != INVALID_TIMER && ud->skill_id != TK_RUN && ud->skill_id != RA_WUGDASH) - unit_stop_walking(src,1); + case MH_SILENT_BREEZE: { + struct status_change *ssc = status_get_sc(src); + struct block_list *m_bl = battle->get_master(src); + const enum sc_type scs[] = { + SC_MANDRAGORA, SC_HARMONIZE, SC_DEEP_SLEEP, SC_SIREN, SC_SLEEP, SC_CONFUSION, SC_ILLUSION + }; + int heal; + if(tsc){ + for (i = 0; i < ARRAYLENGTH(scs); i++) { + if (tsc->data[scs[i]]) status_change_end(bl, scs[i], INVALID_TIMER); + } + if (!tsc->data[SC_SILENCE]) //put inavoidable silence on target + status_change_start(bl, SC_SILENCE, 100, skill_lv, 0,0,0, skill->get_time(skill_id, skill_lv),1|2|8); + } + heal = status_get_matk_min(src)*4; + status_heal(bl, heal, 0, 7); - if( !sd || sd->skillitem != ud->skill_id || skill->get_delay(ud->skill_id,ud->skill_lv) ) - ud->canact_tick = tick + skill->delay_fix(src, ud->skill_id, ud->skill_lv); //Tests show wings don't overwrite the delay but skill scrolls do. [Inkfish] - if (sd) { //Cooldown application - int i, cooldown = skill->get_cooldown(ud->skill_id, ud->skill_lv); - for (i = 0; i < ARRAYLENGTH(sd->skillcooldown) && sd->skillcooldown[i].id; i++) { // Increases/Decreases cooldown of a skill by item/card bonuses. - if (sd->skillcooldown[i].id == ud->skill_id){ - cooldown += sd->skillcooldown[i].val; - break; - } + //now inflict silence on everyone + if(ssc && !ssc->data[SC_SILENCE]) //put inavoidable silence on homun + status_change_start(src, SC_SILENCE, 100, skill_lv, 0,0,0, skill->get_time(skill_id, skill_lv),1|2|8); + if(m_bl){ + struct status_change *msc = status_get_sc(m_bl); + if(msc && !msc->data[SC_SILENCE]) //put inavoidable silence on master + status_change_start(m_bl, SC_SILENCE, 100, skill_lv, 0,0,0, skill->get_time(skill_id, skill_lv),1|2|8); } - if(cooldown) - skill->blockpc_start(sd, ud->skill_id, cooldown, false); - } - if( battle_config.display_status_timers && sd ) - clif->status_change(src, SI_ACTIONDELAY, 1, skill->delay_fix(src, ud->skill_id, ud->skill_lv), 0, 0, 0); - if( sd ) - { - switch( ud->skill_id ) - { - case GS_DESPERADO: - sd->canequip_tick = tick + skill->get_time(ud->skill_id, ud->skill_lv); + if (hd) + skill->blockhomun_start(hd, skill_id, skill->get_cooldown(skill_id, skill_lv)); + } + break; + case MH_OVERED_BOOST: + if (hd){ + struct block_list *s_bl = battle->get_master(src); + if(hd->homunculus.hunger>50) //reduce hunger + hd->homunculus.hunger = hd->homunculus.hunger/2; + else + hd->homunculus.hunger = min(1,hd->homunculus.hunger); + if(s_bl && s_bl->type==BL_PC){ + status_set_sp(s_bl,status_get_max_sp(s_bl)/2,0); //master drain 50% sp + clif->send_homdata(((TBL_PC *)s_bl), SP_HUNGRY, hd->homunculus.hunger); //refresh hunger info + sc_start(s_bl, type, 100, skill_lv, skill->get_time(skill_id, skill_lv)); //gene bonus + } + sc_start(bl, type, 100, skill_lv, skill->get_time(skill_id, skill_lv)); + skill->blockhomun_start(hd, skill_id, skill->get_cooldown(skill_id, skill_lv)); + } break; - case CR_GRANDCROSS: - case NPC_GRANDDARKNESS: - if( (sc = status_get_sc(src)) && sc->data[SC_STRIPSHIELD] ) + case MH_GRANITIC_ARMOR: + case MH_PYROCLASTIC: { + struct block_list *s_bl = battle->get_master(src); + if(s_bl) + sc_start2(s_bl, type, 100, skill_lv, hd->homunculus.level, skill->get_time(skill_id, skill_lv)); //start on master + sc_start2(bl, type, 100, skill_lv, hd->homunculus.level, skill->get_time(skill_id, skill_lv)); + if (hd) + skill->blockhomun_start(hd, skill_id, skill->get_cooldown(skill_id, skill_lv)); + } + break; + + case MH_LIGHT_OF_REGENE: + if(hd){ + hd->homunculus.intimacy = 251; //change to neutral (can't be cast if < 750) + if(sd) clif->send_homdata(sd, SP_INTIMATE, hd->homunculus.intimacy); //refresh intimacy info + } + //don't break need to start status and start block timer + case MH_STYLE_CHANGE: + case MH_MAGMA_FLOW: + case MH_PAIN_KILLER: + sc_start(bl, type, 100, skill_lv, skill->get_time(skill_id, skill_lv)); + if (hd) + skill->blockhomun_start(hd, skill_id, skill->get_cooldown(skill_id, skill_lv)); + break; + case MH_SUMMON_LEGION: { - const struct TimerData *timer = iTimer->get_timer(sc->data[SC_STRIPSHIELD]->timer); - if( timer && timer->func == status_change_timer && DIFF_TICK(timer->tick,iTimer->gettick()+skill->get_time(ud->skill_id, ud->skill_lv)) > 0 ) + int summons[5] = {1004, 1303, 1303, 1994, 1994}; + int qty[5] = {3 , 3 , 4 , 4 , 5}; + struct mob_data *md; + int i, dummy = 0; + + i = iMap->foreachinmap(skill->check_condition_mob_master_sub ,hd->bl.m, BL_MOB, hd->bl.id, summons[skill_lv-1], skill_id, &dummy); + if(i >= qty[skill_lv-1]) break; + + for(i=0; im, src->x, src->y, status_get_name(src), summons[skill_lv - 1], "", SZ_SMALL, AI_ATTACK); + if (md) { + md->master_id = src->id; + if (md->deletetimer != INVALID_TIMER) + iTimer->delete_timer(md->deletetimer, mob_timer_delete); + md->deletetimer = iTimer->add_timer(iTimer->gettick() + skill->get_time(skill_id, skill_lv), mob_timer_delete, md->bl.id, 0); + mob_spawn(md); //Now it is ready for spawning. + sc_start4(&md->bl, SC_MODECHANGE, 100, 1, 0, MD_CANATTACK|MD_AGGRESSIVE, 0, 60000); + } + } + if (hd) + skill->blockhomun_start(hd, skill_id, skill->get_cooldown(skill_id, skill_lv)); } - sc_start2(src, SC_STRIPSHIELD, 100, 0, 1, skill->get_time(ud->skill_id, ud->skill_lv)); break; - } - } - if (skill->get_state(ud->skill_id) != ST_MOVE_ENABLE) - unit_set_walkdelay(src, tick, battle_config.default_walk_delay+skill->get_walkdelay(ud->skill_id, ud->skill_lv), 1); - - if(battle_config.skill_log && battle_config.skill_log&src->type) - ShowInfo("Type %d, ID %d skill castend id [id =%d, lv=%d, target ID %d]\n", - src->type, src->id, ud->skill_id, ud->skill_lv, target->id); - - iMap->freeblock_lock(); - - // SC_MAGICPOWER needs to switch states before any damage is actually dealt - skill->toggle_magicpower(src, ud->skill_id); - if( ud->skill_id != RA_CAMOUFLAGE ) // only normal attack and auto cast skills benefit from its bonuses - status_change_end(src,SC_CAMOUFLAGE, INVALID_TIMER); - - if (skill->get_casttype(ud->skill_id) == CAST_NODAMAGE) - skill->castend_nodamage_id(src,target,ud->skill_id,ud->skill_lv,tick,flag); - else - skill->castend_damage_id(src,target,ud->skill_id,ud->skill_lv,tick,flag); - - sc = status_get_sc(src); - if(sc && sc->count) { - if(sc->data[SC_SPIRIT] && - sc->data[SC_SPIRIT]->val2 == SL_WIZARD && - sc->data[SC_SPIRIT]->val3 == ud->skill_id && - ud->skill_id != WZ_WATERBALL) - sc->data[SC_SPIRIT]->val3 = 0; //Clear bounced spell check. + default: + ShowWarning("skill_castend_nodamage_id: Unknown skill used:%d\n",skill_id); + clif->skill_nodamage(src,bl,skill_id,skill_lv,1); + iMap->freeblock_unlock(); + return 1; + } - if( sc->data[SC_DANCING] && skill->get_inf2(ud->skill_id)&INF2_SONG_DANCE && sd ) - skill->blockpc_start(sd,BD_ADAPTATION,3000, false); - } + if(skill_id != SR_CURSEDCIRCLE){ + struct status_change *sc = status_get_sc(src); + if( sc && sc->data[SC_CURSEDCIRCLE_ATKER] )//Should only remove after the skill had been casted. + status_change_end(src,SC_CURSEDCIRCLE_ATKER,INVALID_TIMER); + } - if( sd && ud->skill_id != SA_ABRACADABRA && ud->skill_id != WM_RANDOMIZESPELL ) // they just set the data so leave it as it is.[Inkfish] - sd->skillitem = sd->skillitemlv = 0; + if (dstmd) { //Mob skill event for no damage skills (damage ones are handled in battle_calc_damage) [Skotlex] + mob_log_damage(dstmd, src, 0); //Log interaction (counts as 'attacker' for the exp bonus) + mobskill_event(dstmd, src, tick, MSC_SKILLUSED|(skill_id<<16)); + } - if (ud->skilltimer == INVALID_TIMER) { - if(md) md->skill_idx = -1; - else ud->skill_id = 0; //mobs can't clear this one as it is used for skill condition 'afterskill' - ud->skill_lv = ud->skilltarget = 0; - } - iMap->freeblock_unlock(); - return 1; - } while(0); + if( sd && !(flag&1) ) { // ensure that the skill last-cast tick is recorded + sd->canskill_tick = iTimer->gettick(); - //Skill failed. - if (ud->skill_id == MO_EXTREMITYFIST && sd && !(sc && sc->data[SC_FOGWALL])) - { //When Asura fails... (except when it fails from Fog of Wall) - //Consume SP/spheres - skill->consume_requirement(sd,ud->skill_id, ud->skill_lv,1); - status_set_sp(src, 0, 0); - sc = &sd->sc; - if (sc->count) - { //End states - status_change_end(src, SC_EXPLOSIONSPIRITS, INVALID_TIMER); - status_change_end(src, SC_BLADESTOP, INVALID_TIMER); -#ifdef RENEWAL - sc_start(src, SC_EXTREMITYFIST2, 100, ud->skill_lv, skill->get_time(ud->skill_id, ud->skill_lv)); -#endif - } - if (target && target->m == src->m) - { //Move character to target anyway. - int dir, x, y; - dir = iMap->calc_dir(src,target->x,target->y); - if( dir > 0 && dir < 4) x = -2; - else if( dir > 4 ) x = 2; - else x = 0; - if( dir > 2 && dir < 6 ) y = -2; - else if( dir == 7 || dir < 2 ) y = 2; - else y = 0; - if (unit_movepos(src, src->x+x, src->y+y, 1, 1)) - { //Display movement + animation. - clif->slide(src,src->x,src->y); - clif->skill_damage(src,target,tick,sd->battle_status.amotion,0,0,1,ud->skill_id, ud->skill_lv, 5); - } - clif->skill_fail(sd,ud->skill_id,USESKILL_FAIL_LEVEL,0); + if( sd->state.arrow_atk ) { // consume arrow on last invocation to this skill. + battle->consume_ammo(sd, skill_id, skill_lv); } + skill->onskillusage(sd, bl, skill_id, tick); + // perform skill requirement consumption + skill->consume_requirement(sd,skill_id,skill_lv,2); } - ud->skill_id = ud->skill_lv = ud->skilltarget = 0; - if( !sd || sd->skillitem != ud->skill_id || skill->get_delay(ud->skill_id,ud->skill_lv) ) - ud->canact_tick = tick; - //You can't place a skill failed packet here because it would be - //sent in ALL cases, even cases where skill_check_condition fails - //which would lead to double 'skill failed' messages u.u [Skotlex] - if(sd) - sd->skillitem = sd->skillitemlv = 0; - else if(md) - md->skill_idx = -1; + iMap->freeblock_unlock(); return 0; } @@ -9528,7 +9392,7 @@ int skill_castend_pos(int tid, unsigned int tick, int id, intptr_t data) skill->blockpc_start(sd, ud->skill_id, cooldown, false); } if( battle_config.display_status_timers && sd ) - clif->status_change(src, SI_ACTIONDELAY, 1, skill->delay_fix(src, ud->skill_id, ud->skill_lv), 0, 0, 0); + clif->status_change(src, SI_POSTDELAY, 1, skill->delay_fix(src, ud->skill_id, ud->skill_lv), 0, 0, 0); // if( sd ) // { // switch( ud->skill_id ) @@ -9574,6 +9438,143 @@ static int skill_count_wos(struct block_list *bl,va_list ap) { } return 0; } + +/*========================================== + * + *------------------------------------------*/ +int skill_castend_map (struct map_session_data *sd, uint16 skill_id, const char *map) +{ + nullpo_ret(sd); + +//Simplify skill_failed code. +#define skill_failed(sd) { sd->menuskill_id = sd->menuskill_val = 0; } + if(skill_id != sd->menuskill_id) + return 0; + + if( sd->bl.prev == NULL || pc_isdead(sd) ) { + skill_failed(sd); + return 0; + } + + if( ( sd->sc.opt1 && sd->sc.opt1 != OPT1_BURNING ) || sd->sc.option&OPTION_HIDE ) { + skill_failed(sd); + return 0; + } + if(sd->sc.count && ( + sd->sc.data[SC_SILENCE] || + sd->sc.data[SC_ROKISWEIL] || + sd->sc.data[SC_AUTOCOUNTER] || + sd->sc.data[SC_STEELBODY] || + (sd->sc.data[SC_DANCING] && skill_id < RK_ENCHANTBLADE && !pc->checkskill(sd, WM_LESSON)) || + sd->sc.data[SC_BERSERK] || sd->sc.data[SC__BLOODYLUST] || + sd->sc.data[SC_BASILICA] || + sd->sc.data[SC_MARIONETTE_MASTER] || + sd->sc.data[SC_WHITEIMPRISON] || + (sd->sc.data[SC_STASIS] && skill->block_check(&sd->bl, SC_STASIS, skill_id)) || + (sd->sc.data[SC_KG_KAGEHUMI] && skill->block_check(&sd->bl, SC_KG_KAGEHUMI, skill_id)) || + sd->sc.data[SC_OBLIVIONCURSE] || + sd->sc.data[SC__MANHOLE] || + (sd->sc.data[SC_VOLCANIC_ASH] && rnd()%2) //50% fail chance under ASH + )) { + skill_failed(sd); + return 0; + } + + pc_stop_attack(sd); + pc_stop_walking(sd,0); + + if(battle_config.skill_log && battle_config.skill_log&BL_PC) + ShowInfo("PC %d skill castend skill =%d map=%s\n",sd->bl.id,skill_id,map); + + if(strcmp(map,"cancel")==0) { + skill_failed(sd); + return 0; + } + + switch(skill_id) { + case AL_TELEPORT: + if(strcmp(map,"Random")==0) + pc->randomwarp(sd,CLR_TELEPORT); + else if (sd->menuskill_val > 1) //Need lv2 to be able to warp here. + pc->setpos(sd,sd->status.save_point.map,sd->status.save_point.x,sd->status.save_point.y,CLR_TELEPORT); + break; + + case AL_WARP: + { + const struct point *p[4]; + struct skill_unit_group *group; + int i, lv, wx, wy; + int maxcount=0; + int x,y; + unsigned short mapindex; + + mapindex = mapindex_name2id((char*)map); + sd->state.workinprogress = 0; + if(!mapindex) { //Given map not found? + clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); + skill_failed(sd); + return 0; + } + p[0] = &sd->status.save_point; + p[1] = &sd->status.memo_point[0]; + p[2] = &sd->status.memo_point[1]; + p[3] = &sd->status.memo_point[2]; + + if((maxcount = skill->get_maxcount(skill_id, sd->menuskill_val)) > 0) { + for(i=0;iud.skillunit[i] && maxcount;i++) { + if(sd->ud.skillunit[i]->skill_id == skill_id) + maxcount--; + } + if(!maxcount) { + clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); + skill_failed(sd); + return 0; + } + } + + lv = sd->skillitem==skill_id?sd->skillitemlv:pc->checkskill(sd,skill_id); + wx = sd->menuskill_val>>16; + wy = sd->menuskill_val&0xffff; + + if( lv <= 0 ) return 0; + if( lv > 4 ) lv = 4; // crash prevention + + // check if the chosen map exists in the memo list + ARR_FIND( 0, lv, i, mapindex == p[i]->map ); + if( i < lv ) { + x=p[i]->x; + y=p[i]->y; + } else { + skill_failed(sd); + return 0; + } + + if(!skill->check_condition_castend(sd, sd->menuskill_id, lv)) { // This checks versus skill_id/skill_lv... + skill_failed(sd); + return 0; + } + + skill->consume_requirement(sd,sd->menuskill_id,lv,2); + sd->skillitem = sd->skillitemlv = 0; // Clear data that's skipped in 'skill_castend_pos' [Inkfish] + + if((group=skill->unitsetting(&sd->bl,skill_id,lv,wx,wy,0))==NULL) { + skill_failed(sd); + return 0; + } + + group->val1 = (group->val1<<16)|(short)0; + // record the destination coordinates + group->val2 = (x<<16)|y; + group->val3 = mapindex; + } + break; + } + + sd->menuskill_id = sd->menuskill_val = 0; + return 0; +#undef skill_failed +} + /*========================================== * *------------------------------------------*/ @@ -9740,6 +9741,7 @@ int skill_castend_pos2(struct block_list* src, int x, int y, uint16 skill_id, ui case NJ_HUUMA: #endif case NPC_EVILLAND: + case WL_COMET: case RA_ELECTRICSHOCKER: case RA_CLUSTERBOMB: case RA_MAGENTATRAP: @@ -9776,6 +9778,7 @@ int skill_castend_pos2(struct block_list* src, int x, int y, uint16 skill_id, ui case MH_POISON_MIST: case MH_STEINWAND: case MH_XENO_SLASHER: + case NC_MAGMA_ERUPTION: flag|=1;//Set flag to 1 to prevent deleting ammo (it will be deleted on group-delete). case GS_GROUNDDRIFT: //Ammo should be deleted right away. skill->unitsetting(src,skill_id,skill_lv,x,y,0); @@ -10038,6 +10041,7 @@ int skill_castend_pos2(struct block_list* src, int x, int y, uint16 skill_id, ui case NC_COLDSLOWER: case NC_ARMSCANNON: case RK_DRAGONBREATH: + case RK_DRAGONBREATH_WATER: i = skill->get_splash(skill_id,skill_lv); iMap->foreachinarea(skill->area_sub,src->m,x-i,y-i,x+i,y+i,splash_target(src), src,skill_id,skill_lv,tick,flag|BCT_ENEMY|1,skill->castend_damage_id); @@ -10070,17 +10074,6 @@ int skill_castend_pos2(struct block_list* src, int x, int y, uint16 skill_id, ui iMap->foreachinarea(skill->area_sub, src->m, x - i, y - i, x + i, y + i, BL_CHAR, src, ALL_RESURRECTION, 1, tick, flag|BCT_NOENEMY|1,skill->castend_nodamage_id); } break; - /** - * Warlock - **/ - case WL_COMET: - if( sc ) { - sc->comet_x = x; - sc->comet_y = y; - } - i = skill->get_splash(skill_id,skill_lv); - iMap->foreachinarea(skill->area_sub,src->m,x-i,y-i,x+i,y+i,splash_target(src),src,skill_id,skill_lv,tick,flag|BCT_ENEMY|1,skill->castend_damage_id); - break; case WL_EARTHSTRAIN: { @@ -10095,7 +10088,7 @@ int skill_castend_pos2(struct block_list* src, int x, int y, uint16 skill_id, ui case 2: sx = x - i; break; case 6: sx = x + i; break; } - skill->addtimerskill(src,iTimer->gettick() + (150 * i),0,sx,sy,skill_id,skill_lv,dir,flag&2); + skill->addtimerskill(src,iTimer->gettick() + (50 * i),0,sx,sy,skill_id,skill_lv,dir,flag&2); } } break; @@ -10142,10 +10135,10 @@ int skill_castend_pos2(struct block_list* src, int x, int y, uint16 skill_id, ui break; case SC_FEINTBOMB: - clif->skill_nodamage(src,src,skill_id,skill_lv,1); skill->unitsetting(src,skill_id,skill_lv,x,y,0); // Set bomb on current Position + clif->skill_nodamage(src,src,skill_id,skill_lv,1); if( skill->blown(src,src,6,unit_getdir(src),0) ) - skill->castend_nodamage_id(src,src,TF_HIDING,1,tick,0); + skill->castend_nodamage_id(src,src,TF_HIDING,1,tick,0x2); break; case LG_OVERBRAND: @@ -10279,141 +10272,6 @@ int skill_castend_pos2(struct block_list* src, int x, int y, uint16 skill_id, ui return 0; } -/*========================================== - * - *------------------------------------------*/ -int skill_castend_map (struct map_session_data *sd, uint16 skill_id, const char *map) -{ - nullpo_ret(sd); - -//Simplify skill_failed code. -#define skill_failed(sd) { sd->menuskill_id = sd->menuskill_val = 0; } - if(skill_id != sd->menuskill_id) - return 0; - - if( sd->bl.prev == NULL || pc_isdead(sd) ) { - skill_failed(sd); - return 0; - } - - if( ( sd->sc.opt1 && sd->sc.opt1 != OPT1_BURNING ) || sd->sc.option&OPTION_HIDE ) { - skill_failed(sd); - return 0; - } - if(sd->sc.count && ( - sd->sc.data[SC_SILENCE] || - sd->sc.data[SC_ROKISWEIL] || - sd->sc.data[SC_AUTOCOUNTER] || - sd->sc.data[SC_STEELBODY] || - (sd->sc.data[SC_DANCING] && skill_id < RK_ENCHANTBLADE && !pc->checkskill(sd, WM_LESSON)) || - sd->sc.data[SC_BERSERK] || sd->sc.data[SC__BLOODYLUST] || - sd->sc.data[SC_BASILICA] || - sd->sc.data[SC_MARIONETTE] || - sd->sc.data[SC_WHITEIMPRISON] || - (sd->sc.data[SC_STASIS] && skill->block_check(&sd->bl, SC_STASIS, skill_id)) || - (sd->sc.data[SC_KAGEHUMI] && skill->block_check(&sd->bl, SC_KAGEHUMI, skill_id)) || - sd->sc.data[SC_OBLIVIONCURSE] || - sd->sc.data[SC__MANHOLE] || - (sd->sc.data[SC_ASH] && rnd()%2) //50% fail chance under ASH - )) { - skill_failed(sd); - return 0; - } - - pc_stop_attack(sd); - pc_stop_walking(sd,0); - - if(battle_config.skill_log && battle_config.skill_log&BL_PC) - ShowInfo("PC %d skill castend skill =%d map=%s\n",sd->bl.id,skill_id,map); - - if(strcmp(map,"cancel")==0) { - skill_failed(sd); - return 0; - } - - switch(skill_id) { - case AL_TELEPORT: - if(strcmp(map,"Random")==0) - pc->randomwarp(sd,CLR_TELEPORT); - else if (sd->menuskill_val > 1) //Need lv2 to be able to warp here. - pc->setpos(sd,sd->status.save_point.map,sd->status.save_point.x,sd->status.save_point.y,CLR_TELEPORT); - break; - - case AL_WARP: - { - const struct point *p[4]; - struct skill_unit_group *group; - int i, lv, wx, wy; - int maxcount=0; - int x,y; - unsigned short mapindex; - - mapindex = mapindex_name2id((char*)map); - if(!mapindex) { //Given map not found? - clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); - skill_failed(sd); - return 0; - } - p[0] = &sd->status.save_point; - p[1] = &sd->status.memo_point[0]; - p[2] = &sd->status.memo_point[1]; - p[3] = &sd->status.memo_point[2]; - - if((maxcount = skill->get_maxcount(skill_id, sd->menuskill_val)) > 0) { - for(i=0;iud.skillunit[i] && maxcount;i++) { - if(sd->ud.skillunit[i]->skill_id == skill_id) - maxcount--; - } - if(!maxcount) { - clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); - skill_failed(sd); - return 0; - } - } - - lv = sd->skillitem==skill_id?sd->skillitemlv:pc->checkskill(sd,skill_id); - wx = sd->menuskill_val>>16; - wy = sd->menuskill_val&0xffff; - - if( lv <= 0 ) return 0; - if( lv > 4 ) lv = 4; // crash prevention - - // check if the chosen map exists in the memo list - ARR_FIND( 0, lv, i, mapindex == p[i]->map ); - if( i < lv ) { - x=p[i]->x; - y=p[i]->y; - } else { - skill_failed(sd); - return 0; - } - - if(!skill->check_condition_castend(sd, sd->menuskill_id, lv)) { // This checks versus skill_id/skill_lv... - skill_failed(sd); - return 0; - } - - skill->consume_requirement(sd,sd->menuskill_id,lv,2); - sd->skillitem = sd->skillitemlv = 0; // Clear data that's skipped in 'skill_castend_pos' [Inkfish] - - if((group=skill->unitsetting(&sd->bl,skill_id,lv,wx,wy,0))==NULL) { - skill_failed(sd); - return 0; - } - - group->val1 = (group->val1<<16)|(short)0; - // record the destination coordinates - group->val2 = (x<<16)|y; - group->val3 = mapindex; - } - break; - } - - sd->menuskill_id = sd->menuskill_val = 0; - return 0; -#undef skill_failed -} - /// transforms 'target' skill unit into dissonance (if conditions are met) int skill_dance_overlap_sub(struct block_list* bl, va_list ap) { struct skill_unit* target = (struct skill_unit*)bl; @@ -10713,8 +10571,13 @@ struct skill_unit_group* skill_unitsetting (struct block_list *src, uint16 skill } break; case DC_DONTFORGETME: +#ifdef RENEWAL + val1 = status->dex/10 + 3*skill_lv; // ASPD decrease + val2 = status->agi/10 + 2*skill_lv; // Movement speed adjustment. +#else val1 = status->dex/10 + 3*skill_lv + 5; // ASPD decrease val2 = status->agi/10 + 3*skill_lv + 5; // Movement speed adjustment. +#endif if(sd){ val1 += pc->checkskill(sd,DC_DANCINGLESSON); val2 += pc->checkskill(sd,DC_DANCINGLESSON); @@ -10734,9 +10597,15 @@ struct skill_unit_group* skill_unitsetting (struct block_list *src, uint16 skill } break; case BA_ASSASSINCROSS: +#ifdef RENEWAL + val1 = 10 + skill_lv + (status->agi/10); // ASPD increase + if(sd) + val1 += 4*pc->checkskill(sd,BA_MUSICALLESSON); +#else val1 = 100+(10*skill_lv)+(status->agi/10); // ASPD increase if(sd) val1 += 5*pc->checkskill(sd,BA_MUSICALLESSON); +#endif break; case DC_FORTUNEKISS: val1 = 10+skill_lv+(status->luk/10); // Critical increase @@ -10823,6 +10692,12 @@ struct skill_unit_group* skill_unitsetting (struct block_list *src, uint16 skill case GD_HAWKEYES: limit = 1000000;//it doesn't matter break; + case WL_COMET: + if( sc ) { + sc->comet_x = x; + sc->comet_y = y; + } + break; case LG_BANDING: limit = -1; break; @@ -10841,7 +10716,6 @@ struct skill_unit_group* skill_unitsetting (struct block_list *src, uint16 skill break; case SO_VACUUM_EXTREME: range++; - break; case SC_BLOODYLUST: skill->clear_group(src, 32); @@ -10853,13 +10727,13 @@ struct skill_unit_group* skill_unitsetting (struct block_list *src, uint16 skill break; case KO_ZENKAI: if( sd ){ - ARR_FIND(1, 6, i, sd->talisman[i] > 0); + ARR_FIND(1, 6, i, sd->charm[i] > 0); if( i < 5 ){ - val1 = sd->talisman[i]; // no. of aura + val1 = sd->charm[i]; // no. of aura val2 = i; // aura type limit += val1 * 1000; subunt = i - 1; - pc->del_talisman(sd, sd->talisman[i], i); + pc->del_charm(sd, sd->charm[i], i); } } break; @@ -11151,7 +11025,7 @@ int skill_unit_onplace (struct skill_unit *src, struct block_list *bl, unsigned case UNT_INTOABYSS: case UNT_SIEGFRIED: //Needed to check when a dancer/bard leaves their ensemble area. - if (sg->src_id==bl->id && !(sc && sc->data[SC_SPIRIT] && sc->data[SC_SPIRIT]->val2 == SL_BARDDANCER)) + if (sg->src_id==bl->id && !(sc && sc->data[SC_SOULLINK] && sc->data[SC_SOULLINK]->val2 == SL_BARDDANCER)) return skill_id; if (!sce) sc_start4(bl,type,100,sg->skill_lv,sg->val1,sg->val2,0,sg->limit); @@ -11164,7 +11038,7 @@ int skill_unit_onplace (struct skill_unit *src, struct block_list *bl, unsigned case UNT_DONTFORGETME: case UNT_FORTUNEKISS: case UNT_SERVICEFORYOU: - if (sg->src_id==bl->id && !(sc && sc->data[SC_SPIRIT] && sc->data[SC_SPIRIT]->val2 == SL_BARDDANCER)) + if (sg->src_id==bl->id && !(sc && sc->data[SC_SOULLINK] && sc->data[SC_SOULLINK]->val2 == SL_BARDDANCER)) return 0; if (!sc) return 0; @@ -11217,7 +11091,7 @@ int skill_unit_onplace (struct skill_unit *src, struct block_list *bl, unsigned case UNT_VOLCANIC_ASH: if (!sce) - sc_start(bl, SC_ASH, 100, sg->skill_lv, skill->get_time(MH_VOLCANIC_ASH, sg->skill_lv)); + sc_start(bl, SC_VOLCANIC_ASH, 100, sg->skill_lv, skill->get_time(MH_VOLCANIC_ASH, sg->skill_lv)); break; case UNT_GD_LEADERSHIP: @@ -11543,7 +11417,7 @@ int skill_unit_onplace_timer (struct skill_unit *src, struct block_list *bl, uns if( md && md->class_ == MOBID_EMPERIUM ) break; #endif - if( sg->src_id == bl->id && !(tsc && tsc->data[SC_SPIRIT] && tsc->data[SC_SPIRIT]->val2 == SL_BARDDANCER) ) + if( sg->src_id == bl->id && !(tsc && tsc->data[SC_SOULLINK] && tsc->data[SC_SOULLINK]->val2 == SL_BARDDANCER) ) break; // affects self only when soullinked heal = skill->calc_heal(ss,bl,sg->skill_id, sg->skill_lv, true); if( tsc->data[SC_AKAITSUKI] && heal ) @@ -11574,7 +11448,7 @@ int skill_unit_onplace_timer (struct skill_unit *src, struct block_list *bl, uns status_heal(bl,heal,0,0); break; case 1: // End all negative status - status_change_clear_buffs(bl,6); + status_change_clear_buffs(bl,2); if (tsd) clif->gospel_info(tsd, 0x15); break; case 2: // Immunity to all status @@ -11597,7 +11471,7 @@ int skill_unit_onplace_timer (struct skill_unit *src, struct block_list *bl, uns sc_start(bl,SC_BLESSING,100,10,time); break; case 7: // Level 10 Increase AGI - sc_start(bl,SC_INCREASEAGI,100,10,time); + sc_start(bl,SC_INC_AGI,100,10,time); break; case 8: // Enchant weapon with Holy element sc_start(bl,SC_ASPERSIO,100,1,time); @@ -11678,6 +11552,8 @@ int skill_unit_onplace_timer (struct skill_unit *src, struct block_list *bl, uns case UNT_FIREWALK: case UNT_ELECTRICWALK: case UNT_PSYCHIC_WAVE: + case UNT_MAGMA_ERUPTION: + case UNT_MAKIBISHI: skill->attack(skill->get_type(sg->skill_id),ss,&src->bl,bl,sg->skill_id,sg->skill_lv,tick,0); break; @@ -11723,7 +11599,7 @@ int skill_unit_onplace_timer (struct skill_unit *src, struct block_list *bl, uns } } /* Enable this if kRO fix the current skill. Currently no damage on undead and demon monster. [Jobbie] - else if( battle->check_target(ss, bl, BCT_ENEMY) > 0 && battle_check_undead(tstatus->race, tstatus->def_ele) ) + else if( battle->check_target(ss, bl, BCT_ENEMY) > 0 && battle->check_undead(tstatus->race, tstatus->def_ele) ) skill->castend_damage_id(&src->bl, bl, sg->skill_id, sg->skill_lv, 0, 0);*/ break; @@ -11775,7 +11651,7 @@ int skill_unit_onplace_timer (struct skill_unit *src, struct block_list *bl, uns } else sec = 3000; // Couldn't trap it? sg->limit = DIFF_TICK(tick, sg->tick) + sec; - } else if( tsc->data[SC_THORNSTRAP] && bl->id == sg->val2 ) + } else if( tsc->data[SC_THORNS_TRAP] && bl->id == sg->val2 ) skill->attack(skill->get_type(GN_THORNS_TRAP), ss, ss, bl, sg->skill_id, sg->skill_lv, tick, SD_LEVEL|SD_ANIMATION); } break; @@ -11786,7 +11662,7 @@ int skill_unit_onplace_timer (struct skill_unit *src, struct block_list *bl, uns case 1: case 2: default: - sc_start(bl, SC_BURNING, 4 + 4 * sg->skill_lv, sg->skill_lv, + sc_start4(bl, SC_BURNING, 4 + 4 * sg->skill_lv, sg->skill_lv, 0, ss->id, 0, skill->get_time2(sg->skill_id, sg->skill_lv)); skill->attack(skill->get_type(sg->skill_id), ss, &src->bl, bl, sg->skill_id, sg->skill_lv + 10 * sg->val2, tick, 0); @@ -11903,36 +11779,31 @@ int skill_unit_onplace_timer (struct skill_unit *src, struct block_list *bl, uns case UNT_ZENKAI_WATER: sc_start(bl, SC_CRYSTALIZE, sg->val1*5, sg->skill_lv, skill->get_time2(sg->skill_id, sg->skill_lv)); sc_start(bl, SC_FREEZE, sg->val1*5, sg->skill_lv, skill->get_time2(sg->skill_id, sg->skill_lv)); - sc_start(bl, SC_FREEZING, sg->val1*5, sg->skill_lv, skill->get_time2(sg->skill_id, sg->skill_lv)); + sc_start(bl, SC_FROSTMISTY, sg->val1*5, sg->skill_lv, skill->get_time2(sg->skill_id, sg->skill_lv)); break; case UNT_ZENKAI_LAND: sc_start(bl, SC_STONE, sg->val1*5, sg->skill_lv, skill->get_time2(sg->skill_id, sg->skill_lv)); sc_start(bl, SC_POISON, sg->val1*5, sg->skill_lv, skill->get_time2(sg->skill_id, sg->skill_lv)); break; case UNT_ZENKAI_FIRE: - sc_start(bl, SC_BURNING, sg->val1*5, sg->skill_lv, skill->get_time2(sg->skill_id, sg->skill_lv)); + sc_start4(bl, SC_BURNING, sg->val1*5, sg->skill_lv, 0, ss->id, 0, skill->get_time2(sg->skill_id, sg->skill_lv)); break; case UNT_ZENKAI_WIND: sc_start(bl, SC_SILENCE, sg->val1*5, sg->skill_lv, skill->get_time2(sg->skill_id, sg->skill_lv)); sc_start(bl, SC_SLEEP, sg->val1*5, sg->skill_lv, skill->get_time2(sg->skill_id, sg->skill_lv)); - sc_start(bl, SC_DEEPSLEEP, sg->val1*5, sg->skill_lv, skill->get_time2(sg->skill_id, sg->skill_lv)); + sc_start(bl, SC_DEEP_SLEEP, sg->val1*5, sg->skill_lv, skill->get_time2(sg->skill_id, sg->skill_lv)); break; } }else sc_start2(bl,type,100,sg->val1,sg->val2,skill->get_time2(sg->skill_id, sg->skill_lv)); break; - case UNT_MAKIBISHI: - skill->attack(BF_MISC, ss, &src->bl, bl, sg->skill_id, sg->skill_lv, tick, 0); - sg->limit = DIFF_TICK(tick, sg->tick); - sg->unit_id = UNT_USED_TRAPS; - break; - case UNT_LAVA_SLIDE: skill->attack(BF_WEAPON, ss, &src->bl, bl, sg->skill_id, sg->skill_lv, tick, 0); if(++sg->val1 > 4) //after 5 stop hit and destroy me sg->limit = DIFF_TICK(tick, sg->tick); break; + case UNT_POISON_MIST: skill->attack(BF_MAGIC, ss, &src->bl, bl, sg->skill_id, sg->skill_lv, tick, 0); status_change_start(bl, SC_BLIND, rnd() % 100 > sg->skill_lv * 10, sg->skill_lv, sg->skill_id, 0, 0, skill->get_time2(sg->skill_id, sg->skill_lv), 2|8); @@ -12234,7 +12105,7 @@ int skill_check_condition_char_sub (struct block_list *bl, va_list ap) { return 1; case WL_COMET: // Comet does not consume Red Gemstones when there is at least 1 Warlock class next to the caster - if( ( sd->class_&MAPID_THIRDMASK ) == MAPID_WARLOCK ) + if( ( tsd->class_&MAPID_THIRDMASK ) == MAPID_WARLOCK ) p_sd[(*c)++] = tsd->bl.id; return 1; case LG_RAYOFGENESIS: @@ -12469,11 +12340,11 @@ int skill_check_condition_castbegin(struct map_session_data* sd, uint16 skill_id case BS_ADRENALINE: case WS_WEAPONREFINE: case BS_WEAPONPERFECT: case WS_CARTTERMINATION: case BS_OVERTHRUST: case WS_OVERTHRUSTMAX: - case BS_MAXIMIZE: case NC_AXEBOOMERANG: - case BS_ADRENALINE2: case NC_POWERSWING: - case BS_UNFAIRLYTRICK: case NC_AXETORNADO: + case BS_MAXIMIZE: + case BS_ADRENALINE2: + case BS_UNFAIRLYTRICK: case BS_GREED: - clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); + clif->skill_fail(sd,skill_id,USESKILL_FAIL_MADOGEAR,0); return 0; default: //Only Mechanic exlcusive skill can be used. break; @@ -12529,30 +12400,43 @@ int skill_check_condition_castbegin(struct map_session_data* sd, uint16 skill_id return 0; if(sc->data[SC_BLADESTOP]) break; - if(sc->data[SC_COMBO] && sc->data[SC_COMBO]->val1 == MO_TRIPLEATTACK) + if( (i=(sc && sc->data[SC_COMBOATTACK])) && sc->data[SC_COMBOATTACK]->val1 == MO_TRIPLEATTACK ) break; + if( i ) + clif->skill_fail(sd, skill_id, USESKILL_FAIL_COMBOSKILL, MO_TRIPLEATTACK); return 0; case MO_COMBOFINISH: - if(!(sc && sc->data[SC_COMBO] && sc->data[SC_COMBO]->val1 == MO_CHAINCOMBO)) + if(!sc) return 0; - break; + if( (i=(sc && sc->data[SC_COMBOATTACK])) && sc->data[SC_COMBOATTACK]->val1 == MO_CHAINCOMBO ) + break; + if( i ) + clif->skill_fail(sd, skill_id, USESKILL_FAIL_COMBOSKILL, MO_CHAINCOMBO); + return 0; case CH_TIGERFIST: - if(!(sc && sc->data[SC_COMBO] && sc->data[SC_COMBO]->val1 == MO_COMBOFINISH)) + if(!sc) return 0; - break; + if( (i=(sc && sc->data[SC_COMBOATTACK])) && sc->data[SC_COMBOATTACK]->val1 == MO_COMBOFINISH ) + break; + if( i ) + clif->skill_fail(sd, skill_id, USESKILL_FAIL_COMBOSKILL, MO_COMBOFINISH); + return 0; case CH_CHAINCRUSH: - if(!(sc && sc->data[SC_COMBO])) - return 0; - if(sc->data[SC_COMBO]->val1 != MO_COMBOFINISH && sc->data[SC_COMBO]->val1 != CH_TIGERFIST) + if(!sc) return 0; - break; + if( (i=(sc && sc->data[SC_COMBOATTACK])) && sc->data[SC_COMBOATTACK]->val1 == CH_TIGERFIST ) + break; + if( i ) + clif->skill_fail(sd, skill_id, USESKILL_FAIL_COMBOSKILL, CH_TIGERFIST); + return 0; case MO_EXTREMITYFIST: // if(sc && sc->data[SC_EXTREMITYFIST]) //To disable Asura during the 5 min skill block uncomment this... // return 0; if( sc && (sc->data[SC_BLADESTOP] || sc->data[SC_CURSEDCIRCLE_ATKER]) ) break; - if( sc && sc->data[SC_COMBO] ) { - switch(sc->data[SC_COMBO]->val1) { + if( sc && sc->data[SC_COMBOATTACK] ) + { + switch(sc->data[SC_COMBOATTACK]->val1) { case MO_COMBOFINISH: case CH_TIGERFIST: case CH_CHAINCRUSH: @@ -12594,17 +12478,17 @@ int skill_check_condition_castbegin(struct map_session_data* sd, uint16 skill_id case TK_COUNTER: if ((sd->class_&MAPID_UPPERMASK) == MAPID_SOUL_LINKER) return 0; //Anti-Soul Linker check in case you job-changed with Stances active. - if(!(sc && sc->data[SC_COMBO]) || sc->data[SC_COMBO]->val1 == TK_JUMPKICK) + if(!(sc && sc->data[SC_COMBOATTACK]) || sc->data[SC_COMBOATTACK]->val1 == TK_JUMPKICK) return 0; //Combo needs to be ready - if (sc->data[SC_COMBO]->val3) { //Kick chain + if (sc->data[SC_COMBOATTACK]->val3) { //Kick chain //Do not repeat a kick. - if (sc->data[SC_COMBO]->val3 != skill_id) + if (sc->data[SC_COMBOATTACK]->val3 != skill_id) break; - status_change_end(&sd->bl, SC_COMBO, INVALID_TIMER); + status_change_end(&sd->bl, SC_COMBOATTACK, INVALID_TIMER); return 0; } - if(sc->data[SC_COMBO]->val1 != skill_id && !( sd && sd->status.base_level >= 90 && pc->famerank(sd->status.char_id, MAPID_TAEKWON) )) { //Cancel combo wait. + if(sc->data[SC_COMBOATTACK]->val1 != skill_id && !( sd && sd->status.base_level >= 90 && pc->famerank(sd->status.char_id, MAPID_TAEKWON) )) { //Cancel combo wait. unit_cancel_combo(&sd->bl); return 0; } @@ -12638,12 +12522,12 @@ int skill_check_condition_castbegin(struct map_session_data* sd, uint16 skill_id break; case SL_SMA: - if(!(sc && sc->data[SC_SMA])) + if(!(sc && sc->data[SC_SMA_READY])) return 0; break; case HT_POWER: - if(!(sc && sc->data[SC_COMBO] && sc->data[SC_COMBO]->val1 == skill_id)) + if(!(sc && sc->data[SC_COMBOATTACK] && sc->data[SC_COMBOATTACK]->val1 == skill_id)) return 0; break; @@ -12709,7 +12593,7 @@ int skill_check_condition_castbegin(struct map_session_data* sd, uint16 skill_id clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); return 0; case SG_FUSION: - if (sc && sc->data[SC_SPIRIT] && sc->data[SC_SPIRIT]->val2 == SL_STAR) + if (sc && sc->data[SC_SOULLINK] && sc->data[SC_SOULLINK]->val2 == SL_STAR) break; //Auron insists we should implement SP consumption when you are not Soul Linked. [Skotlex] //Only invoke on skill begin cast (instant cast skill). [Kevin] @@ -12751,7 +12635,7 @@ int skill_check_condition_castbegin(struct map_session_data* sd, uint16 skill_id return 0; } case NJ_BUNSINJYUTSU: - if (!(sc && sc->data[SC_NEN])) { + if (!(sc && sc->data[SC_NJ_NEN])) { clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); return 0; } @@ -12824,13 +12708,36 @@ int skill_check_condition_castbegin(struct map_session_data* sd, uint16 skill_id case WL_SUMMONBL: case WL_SUMMONWB: case WL_SUMMONSTONE: - if( sc ) + case WL_TETRAVORTEX: + case WL_RELEASE: { - ARR_FIND(SC_SPHERE_1,SC_SPHERE_5+1,i,!sc->data[i]); - if( i == SC_SPHERE_5+1 ) - { // No more free slots - clif->skill_fail(sd,skill_id,USESKILL_FAIL_SUMMON,0); - return 0; + int x = SC_SUMMON1; + i = 0; + for(; x <= SC_SUMMON5; x++) + if( sc && sc->data[x] ) + i++; + + switch(skill_id){ + case WL_TETRAVORTEX: + if( i < 4 ){ + clif->skill_fail(sd,skill_id,USESKILL_FAIL_CONDITION,0); + return 0; + } + break; + case WL_RELEASE: + for(x = SC_SPELLBOOK7; x >= SC_SPELLBOOK1; x--) + if( sc && sc->data[x] ) + i++; + if( i == 0 ){ + clif->skill_fail(sd,skill_id,USESKILL_FAIL_SUMMON_NONE,0); + return 0; + } + break; + default: + if( i == 5 ){ + clif->skill_fail(sd,skill_id,USESKILL_FAIL_SUMMON,0); + return 0; + } } } break; @@ -12845,7 +12752,7 @@ int skill_check_condition_castbegin(struct map_session_data* sd, uint16 skill_id break; case GC_COUNTERSLASH: case GC_WEAPONCRUSH: - if( !(sc && sc->data[SC_COMBO] && sc->data[SC_COMBO]->val1 == GC_WEAPONBLOCKING) ) { + if( !(sc && sc->data[SC_COMBOATTACK] && sc->data[SC_COMBOATTACK]->val1 == GC_WEAPONBLOCKING) ) { clif->skill_fail(sd, skill_id, USESKILL_FAIL_GC_WEAPONBLOCKING, 0); return 0; } @@ -12854,26 +12761,26 @@ int skill_check_condition_castbegin(struct map_session_data* sd, uint16 skill_id * Ranger **/ case RA_WUGMASTERY: - if( pc_isfalcon(sd) || pc_isridingwug(sd) || sd->sc.data[SC__GROOMY]) { - clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); + if( pc_isfalcon(sd) || pc_isridingwug(sd) || sd->sc.data[SC__GROOMY] ) { + clif->skill_fail(sd,skill_id,sd->sc.data[SC__GROOMY]?USESKILL_FAIL_MANUAL_NOTIFY:USESKILL_FAIL_CONDITION,0); return 0; } break; case RA_WUGSTRIKE: if( !pc_iswug(sd) && !pc_isridingwug(sd) ) { - clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); + clif->skill_fail(sd,skill_id,USESKILL_FAIL_CONDITION,0); return 0; } break; case RA_WUGRIDER: if( pc_isfalcon(sd) || ( !pc_isridingwug(sd) && !pc_iswug(sd) ) ) { - clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); + clif->skill_fail(sd,skill_id,USESKILL_FAIL_CONDITION,0); return 0; } break; case RA_WUGDASH: if(!pc_isridingwug(sd)) { - clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); + clif->skill_fail(sd,skill_id,USESKILL_FAIL_CONDITION,0); return 0; } break; @@ -12915,10 +12822,13 @@ int skill_check_condition_castbegin(struct map_session_data* sd, uint16 skill_id } break; case SR_FALLENEMPIRE: - if( !(sc && sc->data[SC_COMBO] && sc->data[SC_COMBO]->val1 == SR_DRAGONCOMBO) ) + if( !sc ) return 0; - break; - + if( (i=(sc && sc->data[SC_COMBOATTACK])) && sc->data[SC_COMBOATTACK]->val1 == SR_DRAGONCOMBO ) + break; + if( i ) + clif->skill_fail(sd, skill_id, USESKILL_FAIL_COMBOSKILL, SR_DRAGONCOMBO); + return 0; case SR_CRESCENTELBOW: if( sc && sc->data[SC_CRESCENTELBOW] ) { clif->skill_fail(sd, skill_id, USESKILL_FAIL_DUPLICATE, 0); @@ -12973,7 +12883,7 @@ int skill_check_condition_castbegin(struct map_session_data* sd, uint16 skill_id break; case SO_EL_CONTROL: if( !sd->status.ele_id || !sd->ed ) { - clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); + clif->skill_fail(sd,skill_id,USESKILL_FAIL_EL_SUMMON,0); return 0; } break; @@ -12985,7 +12895,7 @@ int skill_check_condition_castbegin(struct map_session_data* sd, uint16 skill_id break; case LG_REFLECTDAMAGE: case CR_REFLECTSHIELD: - if( sc && sc->data[SC_KYOMU] && rand()%100 < 30){ + if( sc && sc->data[SC_KYOMU] && rand()%100 < 5 * sc->data[SC_KYOMU]->val1 ){ clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); return 0; } @@ -12996,18 +12906,17 @@ int skill_check_condition_castbegin(struct map_session_data* sd, uint16 skill_id case KO_DOHU_KOUKAI: { int ttype = skill->get_ele(skill_id, skill_lv); - ARR_FIND(1, 5, i, sd->talisman[i] > 0 && i != ttype); - if( (i < 5 && i != ttype) || sd->talisman[ttype] >= 10 ){ - clif->skill_fail(sd, skill_id, USESKILL_FAIL_LEVEL, 0); + if( sd->charm[ttype] >= 10 ){ + clif->skill_fail(sd, skill_id, USESKILL_FAIL_SUMMON, 0); return 0; } } break; case KO_KAIHOU: case KO_ZENKAI: - ARR_FIND(1, 6, i, sd->talisman[i] > 0); + ARR_FIND(1, 6, i, sd->charm[i] > 0); if( i > 4 ) { - clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); + clif->skill_fail(sd,skill_id,USESKILL_FAIL_SUMMON,0); return 0; } break; @@ -13051,7 +12960,7 @@ int skill_check_condition_castbegin(struct map_session_data* sd, uint16 skill_id } case ST_CART: if(!pc_iscarton(sd)) { - clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); + clif->skill_fail(sd,skill_id,USESKILL_FAIL_CART,0); return 0; } break; @@ -13069,7 +12978,7 @@ int skill_check_condition_castbegin(struct map_session_data* sd, uint16 skill_id break; case ST_EXPLOSIONSPIRITS: if(!(sc && sc->data[SC_EXPLOSIONSPIRITS])) { - clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); + clif->skill_fail(sd,skill_id,USESKILL_FAIL_EXPLOSIONSPIRITS,0); return 0; } break; @@ -13080,7 +12989,7 @@ int skill_check_condition_castbegin(struct map_session_data* sd, uint16 skill_id } break; case ST_MOVE_ENABLE: - if (sc && sc->data[SC_COMBO] && sc->data[SC_COMBO]->val1 == skill_id) + if (sc && sc->data[SC_COMBOATTACK] && sc->data[SC_COMBOATTACK]->val1 == skill_id) sd->ud.canmove_tick = iTimer->gettick(); //When using a combo, cancel the can't move delay to enable the skill. [Skotlex] if (!unit_can_move(&sd->bl)) { @@ -13089,7 +12998,7 @@ int skill_check_condition_castbegin(struct map_session_data* sd, uint16 skill_id } break; case ST_WATER: - if (sc && (sc->data[SC_DELUGE] || sc->data[SC_SUITON])) + if (sc && (sc->data[SC_DELUGE] || sc->data[SC_NJ_SUITON])) break; if (iMap->getcell(sd->bl.m,sd->bl.x,sd->bl.y,CELL_CHKWATER)) break; @@ -13097,7 +13006,7 @@ int skill_check_condition_castbegin(struct map_session_data* sd, uint16 skill_id return 0; case ST_RIDINGDRAGON: if( !pc_isridingdragon(sd) ) { - clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); + clif->skill_fail(sd,skill_id,USESKILL_FAIL_DRAGON,0); return 0; } break; @@ -13115,7 +13024,7 @@ int skill_check_condition_castbegin(struct map_session_data* sd, uint16 skill_id break; case ST_MADO: if( !pc_ismadogear(sd) ) { - clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); + clif->skill_fail(sd,skill_id,USESKILL_FAIL_MADOGEAR,0); return 0; } break; @@ -13182,7 +13091,7 @@ int skill_check_condition_castbegin(struct map_session_data* sd, uint16 skill_id return 0; } - if( sd->sc.data[SC_COMBO] ) { + if( sd->sc.data[SC_COMBOATTACK] ) { switch( skill_id ) { case MO_CHAINCOMBO: case MO_COMBOFINISH: @@ -13329,7 +13238,10 @@ int skill_check_condition_castend(struct map_session_data* sd, uint16 skill_id, if( require.ammo ) { //Skill requires stuff equipped in the arrow slot. if((i=sd->equip_index[EQI_AMMO]) < 0 || !sd->inventory_data[i] ) { - clif->arrow_fail(sd,0); + if( require.ammo&1<<8 ) + clif->skill_fail(sd,skill_id,USESKILL_FAIL_CANONBALL,0); + else + clif->arrow_fail(sd,0); return 0; } else if( sd->status.inventory[i].amount < require.ammo_qty ) { char e_msg[100]; @@ -13353,12 +13265,39 @@ int skill_check_condition_castend(struct map_session_data* sd, uint16 skill_id, continue; index[i] = pc->search_inventory(sd,require.itemid[i]); if( index[i] < 0 || sd->status.inventory[index[i]].amount < require.amount[i] ) { - if( require.itemid[i] == ITEMID_RED_GEMSTONE ) - clif->skill_fail(sd,skill_id,USESKILL_FAIL_REDJAMSTONE,0);// red gemstone required - else if( require.itemid[i] == ITEMID_BLUE_GEMSTONE ) - clif->skill_fail(sd,skill_id,USESKILL_FAIL_BLUEJAMSTONE,0);// blue gemstone required - else - clif->skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0); + useskill_fail_cause cause = USESKILL_FAIL_NEED_ITEM; + switch( skill_id ){ + case NC_SILVERSNIPER: + case NC_MAGICDECOY: + cause = USESKILL_FAIL_STUFF_INSUFFICIENT; + break; + default: + switch(require.itemid[i]){ + case ITEMID_RED_GEMSTONE: + cause = USESKILL_FAIL_REDJAMSTONE; break; + case ITEMID_BLUE_GEMSTONE: + cause = USESKILL_FAIL_BLUEJAMSTONE; break; + case ITEMID_HOLY_WATER: + cause = USESKILL_FAIL_HOLYWATER; break; + case ITEMID_ANCILLA: + cause = USESKILL_FAIL_ANCILLA; break; + case ITEMID_ACCELERATOR: + case ITEMID_HOVERING_BOOSTER: + case ITEMID_SUICIDAL_DEVICE: + case ITEMID_SHAPE_SHIFTER: + case ITEMID_COOLING_DEVICE: + case ITEMID_MAGNETIC_FIELD_GENERATOR: + case ITEMID_BARRIER_BUILDER: + case ITEMID_CAMOUFLAGE_GENERATOR: + case ITEMID_REPAIR_KIT: + case ITEMID_MONKEY_SPANNER: + cause = USESKILL_FAIL_NEED_EQUIPMENT; + default: + clif->skill_fail(sd, skill_id, cause, max(1,require.amount[i])|(require.itemid[i] << 16)); + return 0; + } + } + clif->skill_fail(sd, skill_id, cause, 0); return 0; } } @@ -13417,7 +13356,7 @@ int skill_consume_requirement( struct map_session_data *sd, uint16 skill_id, uin if( !req.itemid[i] ) continue; - if( itemid_isgemstone(req.itemid[i]) && skill_id != HW_GANBANTEIN && sc && sc->data[SC_SPIRIT] && sc->data[SC_SPIRIT]->val2 == SL_WIZARD ) + if( itemid_isgemstone(req.itemid[i]) && skill_id != HW_GANBANTEIN && sc && sc->data[SC_SOULLINK] && sc->data[SC_SOULLINK]->val2 == SL_WIZARD ) continue; //Gemstones are checked, but not substracted from inventory. switch( skill_id ){ @@ -13521,10 +13460,12 @@ struct skill_condition skill_get_requirement(struct map_session_data* sd, uint16 if( sc ) { if( sc->data[SC__LAZINESS] ) req.sp += req.sp + sc->data[SC__LAZINESS]->val1 * 10; - if (sc->data[SC_UNLIMITEDHUMMINGVOICE]) - req.sp += req.sp * sc->data[SC_UNLIMITEDHUMMINGVOICE]->val2 / 100; + if( sc->data[SC_UNLIMITED_HUMMING_VOICE] ) + req.sp += req.sp * sc->data[SC_UNLIMITED_HUMMING_VOICE]->val2 / 100; if( sc->data[SC_RECOGNIZEDSPELL] ) req.sp += req.sp / 4; + if( sc->data[SC_TELEKINESIS_INTENSE] && skill->get_ele(skill_id, skill_lv) == ELE_GHOST) + req.sp -= req.sp * sc->data[SC_TELEKINESIS_INTENSE]->val2 / 100; } req.zeny = skill_db[idx].zeny[skill_lv-1]; @@ -13644,7 +13585,7 @@ struct skill_condition skill_get_requirement(struct map_session_data* sd, uint16 req.zeny -= req.zeny*10/100; break; case AL_HOLYLIGHT: - if(sc && sc->data[SC_SPIRIT] && sc->data[SC_SPIRIT]->val2 == SL_PRIEST) + if(sc && sc->data[SC_SOULLINK] && sc->data[SC_SOULLINK]->val2 == SL_PRIEST) req.sp *= 5; break; case SL_SMA: @@ -13668,7 +13609,7 @@ struct skill_condition skill_get_requirement(struct map_session_data* sd, uint16 case MO_COMBOFINISH: case CH_TIGERFIST: case CH_CHAINCRUSH: - if(sc && sc->data[SC_SPIRIT] && sc->data[SC_SPIRIT]->val2 == SL_MONK) + if(sc && sc->data[SC_SOULLINK] && sc->data[SC_SOULLINK]->val2 == SL_MONK) req.sp -= req.sp*25/100; //FIXME: Need real data. this is a custom value. break; case MO_BODYRELOCATION: @@ -13680,9 +13621,9 @@ struct skill_condition skill_get_requirement(struct map_session_data* sd, uint16 { if( sc->data[SC_BLADESTOP] ) req.spiritball--; - else if( sc->data[SC_COMBO] ) + else if( sc->data[SC_COMBOATTACK] ) { - switch( sc->data[SC_COMBO]->val1 ) + switch( sc->data[SC_COMBOATTACK]->val1 ) { case MO_COMBOFINISH: req.spiritball = 4; @@ -13702,7 +13643,7 @@ struct skill_condition skill_get_requirement(struct map_session_data* sd, uint16 req.spiritball = sd->spiritball?sd->spiritball:15; break; case SR_GATEOFHELL: - if( sc && sc->data[SC_COMBO] && sc->data[SC_COMBO]->val1 == SR_FALLENEMPIRE ) + if( sc && sc->data[SC_COMBOATTACK] && sc->data[SC_COMBOATTACK]->val1 == SR_FALLENEMPIRE ) req.sp -= req.sp * 10 / 100; break; case SO_SUMMON_AGNI: @@ -13779,15 +13720,15 @@ int skill_castfix_sc (struct block_list *bl, int time) if( time < 0 ) return 0; - + if( bl->type == BL_MOB ) // mobs casttime is fixed nothing to alter. return time; if (sc && sc->count) { if (sc->data[SC_SLOWCAST]) time += time * sc->data[SC_SLOWCAST]->val2 / 100; - if (sc->data[SC_PARALYSIS]) - time += sc->data[SC_PARALYSIS]->val3; + if (sc->data[SC_NEEDLE_OF_PARALYZE]) + time += sc->data[SC_NEEDLE_OF_PARALYZE]->val3; if (sc->data[SC_SUFFRAGIUM]) { time -= time * sc->data[SC_SUFFRAGIUM]->val2 / 100; status_change_end(bl, SC_SUFFRAGIUM, INVALID_TIMER); @@ -13859,8 +13800,12 @@ int skill_vfcastfix (struct block_list *bl, double time, uint16 skill_id, uint16 if (sc && sc->count && !(skill->get_castnodex(skill_id, skill_lv)&2) ) { // All variable cast additive bonuses must come first + if (sc->data[SC_MAGICPOWER] ) + time += 700; if (sc->data[SC_SLOWCAST]) VARCAST_REDUCTION(-sc->data[SC_SLOWCAST]->val2); + if (sc->data[SC_FROSTMISTY]) + VARCAST_REDUCTION(-15); // Variable cast reduction bonuses if (sc->data[SC_SUFFRAGIUM]) { @@ -13878,17 +13823,33 @@ int skill_vfcastfix (struct block_list *bl, double time, uint16 skill_id, uint16 VARCAST_REDUCTION(50); if (sc->data[SC_WATER_INSIGNIA] && sc->data[SC_WATER_INSIGNIA]->val1 == 3 && (skill->get_ele(skill_id, skill_lv) == ELE_WATER)) VARCAST_REDUCTION(30); //Reduces 30% Variable Cast Time of Water spells. + if (sc->data[SC_TELEKINESIS_INTENSE]) + VARCAST_REDUCTION(sc->data[SC_TELEKINESIS_INTENSE]->val2); + if (sc->data[SC_SOULLINK]){ + if(sc->data[SC_SOULLINK]->val2 == SL_WIZARD || sc->data[SC_SOULLINK]->val2 == SL_BARDDANCER) + switch(skill_id){ + case WZ_FIREPILLAR: + if(skill_lv < 5) + break; + case HW_GRAVITATION: + case MG_SAFETYWALL: + case MG_STONECURSE: + case BA_MUSICALSTRIKE: + case DC_THROWARROW: + VARCAST_REDUCTION(50); + } + } // Fixed cast reduction bonuses if( sc->data[SC__LAZINESS] ) fixcast_r = max(fixcast_r, sc->data[SC__LAZINESS]->val2); if( sc->data[SC_SECRAMENT] ) fixcast_r = max(fixcast_r, sc->data[SC_SECRAMENT]->val2); - if( sd && ( skill_lv = pc->checkskill(sd, WL_RADIUS) ) && skill_id >= WL_WHITEIMPRISON && skill_id <= WL_FREEZE_SP ) - fixcast_r = max(fixcast_r, 5 + skill_lv * 5); + if( sd && ( skill_lv = pc->checkskill(sd, WL_RADIUS) ) && (skill_id >= WL_WHITEIMPRISON && skill_id < WL_FREEZE_SP) ) + fixcast_r = max(fixcast_r, (status_get_int(bl) + status_get_lv(bl)) / 15 + skill_lv * 5); // [{(Caster?s INT / 15) + (Caster?s Base Level / 15) + (Radius Skill Level x 5)}] % // Fixed cast non percentage bonuses if( sc->data[SC_MANDRAGORA] ) fixed += sc->data[SC_MANDRAGORA]->val1 * 1000 / 2; - if (sc->data[SC_IZAYOI] && (skill_id >= NJ_TOBIDOUGU && skill_id <= NJ_ISSEN)) + if( sc->data[SC_IZAYOI] ) fixed = 0; if( sc->data[SC_GUST_OPTION] || sc->data[SC_BLAST_OPTION] || sc->data[SC_WILD_STORM_OPTION] ) fixed -= 1000; @@ -13966,14 +13927,14 @@ int skill_delay_fix (struct block_list *bl, uint16 skill_id, uint16 skill_lv) } } - if ( sc && sc->data[SC_SPIRIT] ) { + if ( sc && sc->data[SC_SOULLINK] ) { switch (skill_id) { case CR_SHIELDBOOMERANG: - if (sc->data[SC_SPIRIT]->val2 == SL_CRUSADER) + if (sc->data[SC_SOULLINK]->val2 == SL_CRUSADER) time /= 2; break; case AS_SONICBLOW: - if (!map_flag_gvg(bl->m) && !map[bl->m].flag.battleground && sc->data[SC_SPIRIT]->val2 == SL_ASSASIN) + if (!map_flag_gvg(bl->m) && !map[bl->m].flag.battleground && sc->data[SC_SOULLINK]->val2 == SL_ASSASIN) time /= 2; break; } @@ -14231,7 +14192,7 @@ void skill_identify (struct map_session_data *sd, int idx) int flag=1; nullpo_retv(sd); - + sd->state.workinprogress = 0; if(idx >= 0 && idx < MAX_INVENTORY) { if(sd->status.inventory[idx].nameid > 0 && sd->status.inventory[idx].identify == 0 ){ flag=0; @@ -14258,20 +14219,29 @@ void skill_weaponrefine (struct map_session_data *sd, int idx) if(item->nameid > 0 && ditem->type == IT_WEAPON) { - if( item->refine >= sd->menuskill_val - || item->refine >= 10 // if it's no longer refineable - || ditem->flag.no_refine // if the item isn't refinable - || (i = pc->search_inventory(sd, material [ditem->wlv])) < 0 ) - { + if( ditem->flag.no_refine ){ // if the item isn't refinable clif->skill_fail(sd,sd->menuskill_id,USESKILL_FAIL_LEVEL,0); return; } + if( item->refine >= sd->menuskill_val || item->refine >= 10 ){ + clif->upgrademessage(sd->fd, 2, item->nameid); + return; + } + if( (i = pc->search_inventory(sd, material [ditem->wlv])) < 0 ){ + clif->upgrademessage(sd->fd, 3, material [ditem->wlv]); + return; + } - per = status_get_refine_chance(ditem->wlv, (int)item->refine); - per += (((signed int)sd->status.job_level)-50)/2; //Updated per the new kro descriptions. [Skotlex] - + per = status_get_refine_chance(ditem->wlv, (int)item->refine) * 10; + + // Aegis leaked formula. [malufett] + if( sd->status.class_ == JOB_MECHANIC_T ) + per += 100; + else + per += 5 * ((signed int)sd->status.job_level - 50); + pc->delitem(sd, i, 1, 0, 0, LOG_TYPE_OTHER); - if (per > rnd() % 100) { + if (per > rnd() % 1000) { logs->pick_pc(sd, LOG_TYPE_OTHER, -1, item, ditem); item->refine++; logs->pick_pc(sd, LOG_TYPE_OTHER, 1, item, ditem); @@ -14279,9 +14249,10 @@ void skill_weaponrefine (struct map_session_data *sd, int idx) ep = item->equip; pc->unequipitem(sd,idx,3); } + clif->delitem(sd,idx,1,0); + clif->upgrademessage(sd->fd, 0,item->nameid); + clif->inventorylist(sd); clif->refine(sd->fd,0,idx,item->refine); - clif->delitem(sd,idx,1,3); - clif->additem(sd,idx,1,0); if (ep) pc->equipitem(sd,idx,ep); clif->misceffect(&sd->bl,3); @@ -14306,7 +14277,7 @@ void skill_weaponrefine (struct map_session_data *sd, int idx) if(item->equip) pc->unequipitem(sd,idx,3); clif->refine(sd->fd,1,idx,item->refine); - pc->delitem(sd,idx,1,0,2, LOG_TYPE_OTHER); + pc->delitem(sd,idx,1,0,0, LOG_TYPE_OTHER); clif->misceffect(&sd->bl,2); clif->emotion(&sd->bl, E_OMG); } @@ -14331,7 +14302,7 @@ int skill_autospell (struct map_session_data *sd, uint16 skill_id) if(skill_id==MG_NAPALMBEAT) maxlv=3; else if(skill_id==MG_COLDBOLT || skill_id==MG_FIREBOLT || skill_id==MG_LIGHTNINGBOLT){ - if (sd->sc.data[SC_SPIRIT] && sd->sc.data[SC_SPIRIT]->val2 == SL_SAGE) + if (sd->sc.data[SC_SOULLINK] && sd->sc.data[SC_SOULLINK]->val2 == SL_SAGE) maxlv =10; //Soul Linker bonus. [Skotlex] else if(skill_lv==2) maxlv=1; else if(skill_lv==3) maxlv=2; @@ -14862,7 +14833,7 @@ int skill_trap_splash (struct block_list *bl, va_list ap) { case UNT_MAIZETRAP: case UNT_VERDURETRAP: if( bl->type != BL_PC && !is_boss(bl) ) - sc_start2(bl,SC_ELEMENTALCHANGE,100,sg->skill_lv,skill->get_ele(sg->skill_id,sg->skill_lv),skill->get_time2(sg->skill_id,sg->skill_lv)); + sc_start2(bl,SC_ARMOR_PROPERTY,100,sg->skill_lv,skill->get_ele(sg->skill_id,sg->skill_lv),skill->get_time2(sg->skill_id,sg->skill_lv)); break; case UNT_REVERBERATION: skill->addtimerskill(ss,tick+50,bl->id,0,0,WM_REVERBERATION_MELEE,sg->skill_lv,BF_WEAPON,0); // for proper skill delay animation when use with Dominion Impulse @@ -14881,7 +14852,7 @@ int skill_trap_splash (struct block_list *bl, va_list ap) { int skill_enchant_elemental_end (struct block_list *bl, int type) { struct status_change *sc; - const enum sc_type scs[] = { SC_ENCPOISON, SC_ASPERSIO, SC_FIREWEAPON, SC_WATERWEAPON, SC_WINDWEAPON, SC_EARTHWEAPON, SC_SHADOWWEAPON, SC_GHOSTWEAPON, SC_ENCHANTARMS, SC_EXEEDBREAK }; + const enum sc_type scs[] = { SC_ENCHANTPOISON, SC_ASPERSIO, SC_PROPERTYFIRE, SC_PROPERTYWATER, SC_PROPERTYWIND, SC_PROPERTYGROUND, SC_PROPERTYDARK, SC_PROPERTYTELEKINESIS, SC_ENCHANTARMS, SC_EXEEDBREAK }; int i; nullpo_ret(bl); nullpo_ret(sc= status_get_sc(bl)); @@ -15036,7 +15007,7 @@ int skill_delunit (struct skill_unit* unit) { case HT_ANKLESNARE: { struct block_list* target = iMap->id2bl(group->val2); if( target ) - status_change_end(target, SC_ANKLE, INVALID_TIMER); + status_change_end(target, SC_ANKLESNARE, INVALID_TIMER); } break; case WZ_ICEWALL: @@ -16083,40 +16054,39 @@ int skill_produce_mix (struct map_session_data *sd, uint16 skill_id, int nameid, **/ case RK_RUNEMASTERY: { - int A = 100 * (51 + 2 * pc->checkskill(sd, skill_id)); - int B = 100 * status->dex / 30 + 10 * (status->luk + sd->status.job_level); + int A = 5100 + 200 * pc->checkskill(sd, skill_id); + int B = 10 * status->dex / 3 + (status->luk + sd->status.job_level); int C = 100 * cap_value(sd->itemid,0,100); //itemid depend on makerune() - int D = 0; + int D = 2500; switch (nameid) { //rune rank it_diff 9 craftable rune - case ITEMID_BERKANA: - D = -2000; - break; //Rank S - case ITEMID_NAUTHIZ: - case ITEMID_URUZ: - D = -1500; - break; //Rank A - case ITEMID_ISA: - case ITEMID_WYRD: - D = -1000; - break; //Rank B case ITEMID_RAIDO: case ITEMID_THURISAZ: case ITEMID_HAGALAZ: case ITEMID_OTHILA: - D = -500; - break; //Rank C - default: D = -1500; - break; //not specified =-15% + D -= 500; //Rank C + case ITEMID_ISA: + case ITEMID_WYRD: + D -= 500; //Rank B + case ITEMID_NAUTHIZ: + case ITEMID_URUZ: + D -= 500; //Rank A + case ITEMID_BERKANA: + D -= 500; //Rank S } - make_per = A + B + C + D; + make_per = A + B + C - D; break; } /** * Guilotine Cross **/ case GC_CREATENEWPOISON: - make_per = 3000 + 500 * pc->checkskill(sd,GC_RESEARCHNEWPOISON); - qty = 1+rnd()%pc->checkskill(sd,GC_RESEARCHNEWPOISON); + { + const int min[] = {2, 2, 3, 3, 4, 4, 5, 5, 6, 6}; + const int max[] = {4, 5, 5, 6, 6, 7, 7, 8, 8, 9}; + uint16 lv = pc->checkskill(sd,GC_RESEARCHNEWPOISON); + make_per = 3000 + 500 * lv ; + qty = min[lv] + rand()%(max[lv] - min[lv]); + } break; case GN_CHANGEMATERIAL: for(i=0; ibl); status_change_end(&sd->bl, SC_STOP, INVALID_TIMER); - for(i=SC_SPELLBOOK1; i <= SC_MAXSPELLBOOK; i++) if( sc && !sc->data[i] ) break; - if( i > SC_MAXSPELLBOOK ) + for(i=SC_SPELLBOOK1; i <= SC_SPELLBOOK7; i++) if( sc && !sc->data[i] ) break; + if( i > SC_SPELLBOOK7 ) { clif->skill_fail(sd, WL_READING_SB, USESKILL_FAIL_SPELLBOOK_READING, 0); return 0; @@ -16637,7 +16607,7 @@ int skill_spellbook (struct map_session_data *sd, int nameid) { return 0; } - max_preserve = 4 * pc->checkskill(sd, WL_FREEZE_SP) + status_get_int(&sd->bl) / 10 + sd->status.base_level / 10; + max_preserve = 4 * pc->checkskill(sd, WL_FREEZE_SP) + (status_get_int(&sd->bl) + sd->status.base_level) / 10; point = skill_spellbook_db[i].point; if( sc && sc->data[SC_READING_SB] ) { @@ -16645,7 +16615,7 @@ int skill_spellbook (struct map_session_data *sd, int nameid) { clif->skill_fail(sd, WL_READING_SB, USESKILL_FAIL_SPELLBOOK_PRESERVATION_POINT, 0); return 0; } - for(i = SC_MAXSPELLBOOK; i >= SC_SPELLBOOK1; i--){ // This is how official saves spellbook. [malufett] + for(i = SC_SPELLBOOK7; i >= SC_SPELLBOOK1; i--){ // This is how official saves spellbook. [malufett] if( !sc->data[i] ){ sc->data[SC_READING_SB]->val2 += point; // increase points sc_start4(&sd->bl, (sc_type)i, 100, skill_id, pc->checkskill(sd,skill_id), point, 0, INVALID_TIMER); @@ -16654,7 +16624,7 @@ int skill_spellbook (struct map_session_data *sd, int nameid) { } }else{ sc_start2(&sd->bl, SC_READING_SB, 100, 0, point, INVALID_TIMER); - sc_start4(&sd->bl, SC_MAXSPELLBOOK, 100, skill_id, pc->checkskill(sd,skill_id), point, 0, INVALID_TIMER); + sc_start4(&sd->bl, SC_SPELLBOOK7, 100, skill_id, pc->checkskill(sd,skill_id), point, 0, INVALID_TIMER); } return 1; @@ -17365,7 +17335,7 @@ int skill_block_check(struct block_list *bl, sc_type type , uint16 skill_id) { return 1; // Can't do it. } break; - case SC_KAGEHUMI: + case SC_KG_KAGEHUMI: switch(skill_id) { case TF_HIDING: case AS_CLOAKING: case GC_CLOAKINGEXCEED: case SC_SHADOWFORM: case MI_HARMONIZE: case CG_MARIONETTE: case AL_TELEPORT: case TF_BACKSLIDING: @@ -17995,6 +17965,7 @@ void skill_defaults(void) { skill->delay_fix = skill_delay_fix; skill->check_condition_castbegin = skill_check_condition_castbegin; skill->check_condition_castend = skill_check_condition_castend; + skill->check_condition_char_sub = skill_check_condition_char_sub; skill->get_requirement = skill_get_requirement; skill->check_pc_partner = skill_check_pc_partner; skill->consume_requirement = skill_consume_requirement; diff --git a/src/map/skill.h b/src/map/skill.h index c585bbb3a..cc9ac4bfc 100644 --- a/src/map/skill.h +++ b/src/map/skill.h @@ -1281,7 +1281,26 @@ enum e_skill { ECL_SADAGUI, ECL_SEQUOIADUST, ECLAGE_RECALL, - + + GC_DARKCROW = 5001, + RA_UNLIMIT, + GN_ILLUSIONDOPING, + RK_DRAGONBREATH_WATER, + RK_LUXANIMA, + NC_MAGMA_ERUPTION, + WM_FRIGG_SONG, + SO_ELEMENTAL_SHIELD, + SR_FLASHCOMBO, + SC_ESCAPE, + AB_OFFERTORIUM, + WL_TELEKINESIS_INTENSE, + LG_KINGS_GRACE, + ALL_FULL_THROTTLE, + SR_FLASHCOMBO_ATK_STEP1, + SR_FLASHCOMBO_ATK_STEP2, + SR_FLASHCOMBO_ATK_STEP3, + SR_FLASHCOMBO_ATK_STEP4, + HLIF_HEAL = 8001, HLIF_AVOID, HLIF_BRAIN, @@ -1541,6 +1560,10 @@ enum { UNT_ZENKAI_WIND, UNT_MAKIBISHI, UNT_VENOMFOG, + UNT_ICEMINE, + UNT_FLAMECROSS, + UNT_HELLBURNING, + UNT_MAGMA_ERUPTION, /** * Guild Auras diff --git a/src/map/status.c b/src/map/status.c index c163135d8..0e1661728 100644 --- a/src/map/status.c +++ b/src/map/status.c @@ -69,6 +69,7 @@ static struct { static int atkmods[3][MAX_WEAPON_TYPE]; //ATK weapon modification for size (size_fix.txt) static char job_bonus[CLASS_COUNT][MAX_LEVEL]; +static sc_conf_type sc_conf[SC_MAX]; static struct eri *sc_data_ers; //For sc_data entries static struct status_data dummy_status; @@ -189,7 +190,7 @@ void initChangeTables(void) { set_sc( NPC_SILENCEATTACK , SC_SILENCE , SI_BLANK , SCB_NONE ); set_sc( NPC_WIDECONFUSE , SC_CONFUSION , SI_BLANK , SCB_NONE ); set_sc( NPC_BLINDATTACK , SC_BLIND , SI_BLANK , SCB_HIT|SCB_FLEE ); - set_sc( NPC_BLEEDING , SC_BLEEDING , SI_BLEEDING , SCB_REGEN ); + set_sc( NPC_BLEEDING , SC_BLOODING , SI_BLOODING , SCB_REGEN ); set_sc( NPC_POISON , SC_DPOISON , SI_BLANK , SCB_DEF2|SCB_REGEN ); //The main status definitions @@ -203,12 +204,12 @@ void initChangeTables(void) { add_sc( MG_STONECURSE , SC_STONE ); add_sc( AL_RUWACH , SC_RUWACH ); add_sc( AL_PNEUMA , SC_PNEUMA ); - set_sc( AL_INCAGI , SC_INCREASEAGI , SI_INCREASEAGI , SCB_AGI|SCB_SPEED ); - set_sc( AL_DECAGI , SC_DECREASEAGI , SI_DECREASEAGI , SCB_AGI|SCB_SPEED ); - set_sc( AL_CRUCIS , SC_SIGNUMCRUCIS , SI_SIGNUMCRUCIS , SCB_DEF ); + set_sc( AL_INCAGI , SC_INC_AGI , SI_INC_AGI , SCB_AGI|SCB_SPEED ); + set_sc( AL_DECAGI , SC_DEC_AGI , SI_DEC_AGI , SCB_AGI|SCB_SPEED ); + set_sc( AL_CRUCIS , SC_CRUCIS , SI_CRUCIS , SCB_DEF ); set_sc( AL_ANGELUS , SC_ANGELUS , SI_ANGELUS , SCB_DEF2 ); set_sc( AL_BLESSING , SC_BLESSING , SI_BLESSING , SCB_STR|SCB_INT|SCB_DEX ); - set_sc( AC_CONCENTRATION , SC_CONCENTRATE , SI_CONCENTRATE , SCB_AGI|SCB_DEX ); + set_sc( AC_CONCENTRATION , SC_CONCENTRATION , SI_CONCENTRATION , SCB_AGI|SCB_DEX ); set_sc( TF_HIDING , SC_HIDING , SI_HIDING , SCB_SPEED ); add_sc( TF_POISON , SC_POISON ); set_sc( KN_TWOHANDQUICKEN , SC_TWOHANDQUICKEN , SI_TWOHANDQUICKEN , SCB_ASPD ); @@ -222,44 +223,44 @@ void initChangeTables(void) { set_sc( PR_MAGNIFICAT , SC_MAGNIFICAT , SI_MAGNIFICAT , SCB_REGEN ); set_sc( PR_GLORIA , SC_GLORIA , SI_GLORIA , SCB_LUK ); add_sc( PR_LEXDIVINA , SC_SILENCE ); - set_sc( PR_LEXAETERNA , SC_AETERNA , SI_AETERNA , SCB_NONE ); + set_sc( PR_LEXAETERNA , SC_LEXAETERNA , SI_LEXAETERNA , SCB_NONE ); add_sc( WZ_METEOR , SC_STUN ); add_sc( WZ_VERMILION , SC_BLIND ); add_sc( WZ_FROSTNOVA , SC_FREEZE ); add_sc( WZ_STORMGUST , SC_FREEZE ); - set_sc( WZ_QUAGMIRE , SC_QUAGMIRE , SI_QUAGMIRE , SCB_AGI|SCB_DEX|SCB_ASPD|SCB_SPEED ); - set_sc( BS_ADRENALINE , SC_ADRENALINE , SI_ADRENALINE , SCB_ASPD ); - set_sc( BS_WEAPONPERFECT , SC_WEAPONPERFECTION, SI_WEAPONPERFECTION, SCB_NONE ); - set_sc( BS_OVERTHRUST , SC_OVERTHRUST , SI_OVERTHRUST , SCB_NONE ); - set_sc( BS_MAXIMIZE , SC_MAXIMIZEPOWER , SI_MAXIMIZEPOWER , SCB_REGEN ); - add_sc( HT_LANDMINE , SC_STUN ); - add_sc( HT_ANKLESNARE , SC_ANKLE ); + set_sc( WZ_QUAGMIRE , SC_QUAGMIRE , SI_QUAGMIRE , SCB_AGI|SCB_DEX|SCB_ASPD|SCB_SPEED ); + set_sc( BS_ADRENALINE , SC_ADRENALINE , SI_ADRENALINE , SCB_ASPD ); + set_sc( BS_WEAPONPERFECT , SC_WEAPONPERFECT , SI_WEAPONPERFECT, SCB_NONE ); + set_sc( BS_OVERTHRUST , SC_OVERTHRUST , SI_OVERTHRUST , SCB_NONE ); + set_sc( BS_MAXIMIZE , SC_MAXIMIZEPOWER , SI_MAXIMIZE , SCB_REGEN ); + add_sc( HT_LANDMINE , SC_STUN ); + set_sc( HT_ANKLESNARE , SC_ANKLESNARE , SI_ANKLESNARE , SCB_NONE ); add_sc( HT_SANDMAN , SC_SLEEP ); add_sc( HT_FLASHER , SC_BLIND ); add_sc( HT_FREEZINGTRAP , SC_FREEZE ); - set_sc( AS_CLOAKING , SC_CLOAKING , SI_CLOAKING , SCB_CRI|SCB_SPEED ); + set_sc( AS_CLOAKING , SC_CLOAKING , SI_CLOAKING , SCB_CRI|SCB_SPEED ); add_sc( AS_SONICBLOW , SC_STUN ); - set_sc( AS_ENCHANTPOISON , SC_ENCPOISON , SI_ENCPOISON , SCB_ATK_ELE ); - set_sc( AS_POISONREACT , SC_POISONREACT , SI_POISONREACT , SCB_NONE ); + set_sc( AS_ENCHANTPOISON , SC_ENCHANTPOISON , SI_ENCHANTPOISON, SCB_ATK_ELE ); + set_sc( AS_POISONREACT , SC_POISONREACT , SI_POISONREACT , SCB_NONE ); add_sc( AS_VENOMDUST , SC_POISON ); add_sc( AS_SPLASHER , SC_SPLASHER ); - set_sc( NV_TRICKDEAD , SC_TRICKDEAD , SI_TRICKDEAD , SCB_REGEN ); - set_sc( SM_AUTOBERSERK , SC_AUTOBERSERK , SI_AUTOBERSERK , SCB_NONE ); + set_sc( NV_TRICKDEAD , SC_TRICKDEAD , SI_TRICKDEAD , SCB_REGEN ); + set_sc( SM_AUTOBERSERK , SC_AUTOBERSERK , SI_AUTOBERSERK , SCB_NONE ); add_sc( TF_SPRINKLESAND , SC_BLIND ); add_sc( TF_THROWSTONE , SC_STUN ); - set_sc( MC_LOUD , SC_LOUD , SI_LOUD , SCB_STR ); - set_sc( MG_ENERGYCOAT , SC_ENERGYCOAT , SI_ENERGYCOAT , SCB_NONE ); - set_sc( NPC_EMOTION , SC_MODECHANGE , SI_BLANK , SCB_MODE ); - add_sc( NPC_EMOTION_ON , SC_MODECHANGE ); - set_sc( NPC_ATTRICHANGE , SC_ELEMENTALCHANGE , SI_ARMOR_PROPERTY , SCB_DEF_ELE ); - add_sc( NPC_CHANGEWATER , SC_ELEMENTALCHANGE ); - add_sc( NPC_CHANGEGROUND , SC_ELEMENTALCHANGE ); - add_sc( NPC_CHANGEFIRE , SC_ELEMENTALCHANGE ); - add_sc( NPC_CHANGEWIND , SC_ELEMENTALCHANGE ); - add_sc( NPC_CHANGEPOISON , SC_ELEMENTALCHANGE ); - add_sc( NPC_CHANGEHOLY , SC_ELEMENTALCHANGE ); - add_sc( NPC_CHANGEDARKNESS , SC_ELEMENTALCHANGE ); - add_sc( NPC_CHANGETELEKINESIS, SC_ELEMENTALCHANGE ); + set_sc( MC_LOUD , SC_SHOUT , SI_SHOUT , SCB_STR ); + set_sc( MG_ENERGYCOAT , SC_ENERGYCOAT , SI_ENERGYCOAT , SCB_NONE ); + set_sc( NPC_EMOTION , SC_MODECHANGE , SI_BLANK , SCB_MODE ); + add_sc( NPC_EMOTION_ON , SC_MODECHANGE ); + set_sc( NPC_ATTRICHANGE , SC_ARMOR_PROPERTY , SI_ARMOR_PROPERTY , SCB_DEF_ELE ); + add_sc( NPC_CHANGEWATER , SC_ARMOR_PROPERTY ); + add_sc( NPC_CHANGEGROUND , SC_ARMOR_PROPERTY ); + add_sc( NPC_CHANGEFIRE , SC_ARMOR_PROPERTY ); + add_sc( NPC_CHANGEWIND , SC_ARMOR_PROPERTY ); + add_sc( NPC_CHANGEPOISON , SC_ARMOR_PROPERTY ); + add_sc( NPC_CHANGEHOLY , SC_ARMOR_PROPERTY ); + add_sc( NPC_CHANGEDARKNESS , SC_ARMOR_PROPERTY ); + add_sc( NPC_CHANGETELEKINESIS, SC_ARMOR_PROPERTY ); add_sc( NPC_POISON , SC_POISON ); add_sc( NPC_BLINDATTACK , SC_BLIND ); add_sc( NPC_SILENCEATTACK , SC_SILENCE ); @@ -273,25 +274,25 @@ void initChangeTables(void) { set_sc( NPC_BARRIER , SC_BARRIER , SI_BLANK , SCB_MDEF|SCB_DEF ); add_sc( NPC_DEFENDER , SC_ARMOR ); add_sc( NPC_LICK , SC_STUN ); - set_sc( NPC_HALLUCINATION , SC_HALLUCINATION , SI_HALLUCINATION , SCB_NONE ); + set_sc( NPC_HALLUCINATION , SC_ILLUSION , SI_ILLUSION , SCB_NONE ); add_sc( NPC_REBIRTH , SC_REBIRTH ); add_sc( RG_RAID , SC_STUN ); #ifdef RENEWAL add_sc( RG_RAID , SC_RAID ); add_sc( RG_BACKSTAP , SC_STUN ); #endif - set_sc( RG_STRIPWEAPON , SC_STRIPWEAPON , SI_STRIPWEAPON , SCB_WATK ); - set_sc( RG_STRIPSHIELD , SC_STRIPSHIELD , SI_STRIPSHIELD , SCB_DEF ); - set_sc( RG_STRIPARMOR , SC_STRIPARMOR , SI_STRIPARMOR , SCB_VIT ); - set_sc( RG_STRIPHELM , SC_STRIPHELM , SI_STRIPHELM , SCB_INT ); - add_sc( AM_ACIDTERROR , SC_BLEEDING ); - set_sc( AM_CP_WEAPON , SC_CP_WEAPON , SI_CP_WEAPON , SCB_NONE ); - set_sc( AM_CP_SHIELD , SC_CP_SHIELD , SI_CP_SHIELD , SCB_NONE ); - set_sc( AM_CP_ARMOR , SC_CP_ARMOR , SI_CP_ARMOR , SCB_NONE ); - set_sc( AM_CP_HELM , SC_CP_HELM , SI_CP_HELM , SCB_NONE ); - set_sc( CR_AUTOGUARD , SC_AUTOGUARD , SI_AUTOGUARD , SCB_NONE ); + set_sc( RG_STRIPWEAPON , SC_NOEQUIPWEAPON , SI_NOEQUIPWEAPON , SCB_WATK ); + set_sc( RG_STRIPSHIELD , SC_NOEQUIPSHIELD , SI_NOEQUIPSHIELD , SCB_DEF ); + set_sc( RG_STRIPARMOR , SC_NOEQUIPARMOR , SI_NOEQUIPARMOR , SCB_VIT ); + set_sc( RG_STRIPHELM , SC_NOEQUIPHELM , SI_NOEQUIPHELM , SCB_INT ); + add_sc( AM_ACIDTERROR , SC_BLOODING ); + set_sc( AM_CP_WEAPON , SC_PROTECTWEAPON , SI_PROTECTWEAPON , SCB_NONE ); + set_sc( AM_CP_SHIELD , SC_PROTECTSHIELD , SI_PROTECTSHIELD , SCB_NONE ); + set_sc( AM_CP_ARMOR , SC_PROTECTARMOR , SI_PROTECTARMOR , SCB_NONE ); + set_sc( AM_CP_HELM , SC_PROTECTHELM , SI_PROTECTHELM , SCB_NONE ); + set_sc( CR_AUTOGUARD , SC_AUTOGUARD , SI_AUTOGUARD , SCB_NONE ); add_sc( CR_SHIELDCHARGE , SC_STUN ); - set_sc( CR_REFLECTSHIELD , SC_REFLECTSHIELD , SI_REFLECTSHIELD , SCB_NONE ); + set_sc( CR_REFLECTSHIELD , SC_REFLECTSHIELD , SI_REFLECTSHIELD , SCB_NONE ); add_sc( CR_HOLYCROSS , SC_BLIND ); add_sc( CR_GRANDCROSS , SC_BLIND ); add_sc( CR_DEVOTION , SC_DEVOTION ); @@ -304,17 +305,17 @@ void initChangeTables(void) { set_sc( MO_EXPLOSIONSPIRITS , SC_EXPLOSIONSPIRITS, SI_EXPLOSIONSPIRITS, SCB_CRI|SCB_REGEN ); set_sc( MO_EXTREMITYFIST , SC_EXTREMITYFIST , SI_BLANK , SCB_REGEN ); #ifdef RENEWAL - set_sc( MO_EXTREMITYFIST , SC_EXTREMITYFIST2 , SI_EXTREMITYFIST , SCB_NONE ); + set_sc( MO_EXTREMITYFIST , SC_EXTREMITYFIST2 , SI_EXTREMITYFIST , SCB_NONE ); #endif add_sc( SA_MAGICROD , SC_MAGICROD ); set_sc( SA_AUTOSPELL , SC_AUTOSPELL , SI_AUTOSPELL , SCB_NONE ); - set_sc( SA_FLAMELAUNCHER , SC_FIREWEAPON , SI_FIREWEAPON , SCB_ATK_ELE ); - set_sc( SA_FROSTWEAPON , SC_WATERWEAPON , SI_WATERWEAPON , SCB_ATK_ELE ); - set_sc( SA_LIGHTNINGLOADER , SC_WINDWEAPON , SI_WINDWEAPON , SCB_ATK_ELE ); - set_sc( SA_SEISMICWEAPON , SC_EARTHWEAPON , SI_EARTHWEAPON , SCB_ATK_ELE ); - set_sc( SA_VOLCANO , SC_VOLCANO , SI_LANDENDOW , SCB_WATK ); - set_sc( SA_DELUGE , SC_DELUGE , SI_LANDENDOW , SCB_MAXHP ); - set_sc( SA_VIOLENTGALE , SC_VIOLENTGALE , SI_LANDENDOW , SCB_FLEE ); + set_sc( SA_FLAMELAUNCHER , SC_PROPERTYFIRE , SI_PROPERTYFIRE , SCB_ATK_ELE ); + set_sc( SA_FROSTWEAPON , SC_PROPERTYWATER , SI_PROPERTYWATER , SCB_ATK_ELE ); + set_sc( SA_LIGHTNINGLOADER , SC_PROPERTYWIND , SI_PROPERTYWIND , SCB_ATK_ELE ); + set_sc( SA_SEISMICWEAPON , SC_PROPERTYGROUND , SI_PROPERTYGROUND , SCB_ATK_ELE ); + set_sc( SA_VOLCANO , SC_VOLCANO , SI_GROUNDMAGIC , SCB_WATK ); + set_sc( SA_DELUGE , SC_DELUGE , SI_GROUNDMAGIC , SCB_MAXHP ); + set_sc( SA_VIOLENTGALE , SC_VIOLENTGALE , SI_GROUNDMAGIC , SCB_FLEE ); add_sc( SA_REVERSEORCISH , SC_ORCISH ); add_sc( SA_COMA , SC_COMA ); set_sc( BD_ENCORE , SC_DANCING , SI_BLANK , SCB_SPEED|SCB_REGEN ); @@ -334,19 +335,23 @@ void initChangeTables(void) { set_sc( DC_HUMMING , SC_HUMMING , SI_BLANK , SCB_HIT ); set_sc( DC_DONTFORGETME , SC_DONTFORGETME , SI_BLANK , SCB_SPEED|SCB_ASPD ); set_sc( DC_FORTUNEKISS , SC_FORTUNE , SI_BLANK , SCB_CRI ); - set_sc( DC_SERVICEFORYOU , SC_SERVICE4U , SI_BLANK , SCB_ALL ); + set_sc( DC_SERVICEFORYOU , SC_SERVICEFORYOU , SI_BLANK , SCB_ALL ); add_sc( NPC_DARKCROSS , SC_BLIND ); add_sc( NPC_GRANDDARKNESS , SC_BLIND ); set_sc( NPC_STOP , SC_STOP , SI_STOP , SCB_NONE ); set_sc( NPC_WEAPONBRAKER , SC_BROKENWEAPON , SI_BROKENWEAPON , SCB_NONE ); set_sc( NPC_ARMORBRAKE , SC_BROKENARMOR , SI_BROKENARMOR , SCB_NONE ); - set_sc( NPC_CHANGEUNDEAD , SC_CHANGEUNDEAD , SI_UNDEAD , SCB_DEF_ELE ); + set_sc( NPC_CHANGEUNDEAD , SC_PROPERTYUNDEAD , SI_PROPERTYUNDEAD , SCB_DEF_ELE ); set_sc( NPC_POWERUP , SC_INCHITRATE , SI_BLANK , SCB_HIT ); set_sc( NPC_AGIUP , SC_INCFLEERATE , SI_BLANK , SCB_FLEE ); add_sc( NPC_INVISIBLE , SC_CLOAKING ); set_sc( LK_AURABLADE , SC_AURABLADE , SI_AURABLADE , SCB_NONE ); set_sc( LK_PARRYING , SC_PARRYING , SI_PARRYING , SCB_NONE ); - set_sc( LK_CONCENTRATION , SC_CONCENTRATION , SI_CONCENTRATION , SCB_BATK|SCB_WATK|SCB_HIT|SCB_DEF|SCB_DEF2|SCB_MDEF|SCB_DSPD ); +#ifndef RENEWAL + set_sc( LK_CONCENTRATION , SC_LKCONCENTRATION , SI_CONCENTRATION , SCB_BATK|SCB_WATK|SCB_HIT|SCB_DEF|SCB_DEF2); +#else + set_sc( LK_CONCENTRATION , SC_LKCONCENTRATION , SI_CONCENTRATION , SCB_HIT|SCB_DEF); +#endif set_sc( LK_TENSIONRELAX , SC_TENSIONRELAX , SI_TENSIONRELAX , SCB_REGEN ); set_sc( LK_BERSERK , SC_BERSERK , SI_BERSERK , SCB_DEF|SCB_DEF2|SCB_MDEF|SCB_MDEF2|SCB_FLEE|SCB_SPEED|SCB_ASPD|SCB_MAXHP|SCB_REGEN ); set_sc( HP_ASSUMPTIO , SC_ASSUMPTIO , SI_ASSUMPTIO , SCB_NONE ); @@ -362,32 +367,32 @@ void initChangeTables(void) { set_sc( WS_MELTDOWN , SC_MELTDOWN , SI_MELTDOWN , SCB_NONE ); set_sc( WS_CARTBOOST , SC_CARTBOOST , SI_CARTBOOST , SCB_SPEED ); set_sc( ST_CHASEWALK , SC_CHASEWALK , SI_BLANK , SCB_SPEED ); - set_sc( ST_REJECTSWORD , SC_REJECTSWORD , SI_REJECTSWORD , SCB_NONE ); + set_sc( ST_REJECTSWORD , SC_SWORDREJECT , SI_SWORDREJECT , SCB_NONE ); add_sc( ST_REJECTSWORD , SC_AUTOCOUNTER ); - set_sc( CG_MARIONETTE , SC_MARIONETTE , SI_MARIONETTE , SCB_STR|SCB_AGI|SCB_VIT|SCB_INT|SCB_DEX|SCB_LUK ); - set_sc( CG_MARIONETTE , SC_MARIONETTE2 , SI_MARIONETTE2 , SCB_STR|SCB_AGI|SCB_VIT|SCB_INT|SCB_DEX|SCB_LUK ); + set_sc( CG_MARIONETTE , SC_MARIONETTE_MASTER , SI_MARIONETTE_MASTER , SCB_STR|SCB_AGI|SCB_VIT|SCB_INT|SCB_DEX|SCB_LUK ); + set_sc( CG_MARIONETTE , SC_MARIONETTE , SI_MARIONETTE , SCB_STR|SCB_AGI|SCB_VIT|SCB_INT|SCB_DEX|SCB_LUK ); add_sc( LK_SPIRALPIERCE , SC_STOP ); - add_sc( LK_HEADCRUSH , SC_BLEEDING ); + add_sc( LK_HEADCRUSH , SC_BLOODING ); set_sc( LK_JOINTBEAT , SC_JOINTBEAT , SI_JOINTBEAT , SCB_BATK|SCB_DEF2|SCB_SPEED|SCB_ASPD ); add_sc( HW_NAPALMVULCAN , SC_CURSE ); set_sc( PF_MINDBREAKER , SC_MINDBREAKER , SI_BLANK , SCB_MATK|SCB_MDEF2 ); add_sc( PF_MEMORIZE , SC_MEMORIZE ); add_sc( PF_FOGWALL , SC_FOGWALL ); set_sc( PF_SPIDERWEB , SC_SPIDERWEB , SI_BLANK , SCB_FLEE ); - set_sc( WE_BABY , SC_BABY , SI_BABY , SCB_NONE ); + set_sc( WE_BABY , SC_BABY , SI_PROTECTEXP , SCB_NONE ); set_sc( TK_RUN , SC_RUN , SI_RUN , SCB_SPEED|SCB_DSPD ); - set_sc( TK_RUN , SC_SPURT , SI_SPURT , SCB_STR ); - set_sc( TK_READYSTORM , SC_READYSTORM , SI_READYSTORM , SCB_NONE ); - set_sc( TK_READYDOWN , SC_READYDOWN , SI_READYDOWN , SCB_NONE ); + set_sc( TK_RUN , SC_STRUP , SI_STRUP , SCB_STR ); + set_sc( TK_READYSTORM , SC_STORMKICK_READY , SI_STORMKICK_ON , SCB_NONE ); + set_sc( TK_READYDOWN , SC_DOWNKICK_READY , SI_DOWNKICK_ON , SCB_NONE ); add_sc( TK_DOWNKICK , SC_STUN ); - set_sc( TK_READYTURN , SC_READYTURN , SI_READYTURN , SCB_NONE ); - set_sc( TK_READYCOUNTER , SC_READYCOUNTER , SI_READYCOUNTER , SCB_NONE ); - set_sc( TK_DODGE , SC_DODGE , SI_DODGE , SCB_NONE ); + set_sc( TK_READYTURN , SC_TURNKICK_READY , SI_TURNKICK_ON , SCB_NONE ); + set_sc( TK_READYCOUNTER , SC_COUNTERKICK_READY , SI_COUNTER_ON , SCB_NONE ); + set_sc( TK_DODGE , SC_DODGE_READY , SI_DODGE_ON , SCB_NONE ); set_sc( TK_SPTIME , SC_EARTHSCROLL , SI_EARTHSCROLL , SCB_NONE ); - add_sc( TK_SEVENWIND , SC_SEVENWIND ); - set_sc( TK_SEVENWIND , SC_GHOSTWEAPON , SI_GHOSTWEAPON , SCB_ATK_ELE ); - set_sc( TK_SEVENWIND , SC_SHADOWWEAPON , SI_SHADOWWEAPON , SCB_ATK_ELE ); - set_sc( SG_SUN_WARM , SC_WARM , SI_WARM , SCB_NONE ); + add_sc( TK_SEVENWIND , SC_TK_SEVENWIND ); + set_sc( TK_SEVENWIND , SC_PROPERTYTELEKINESIS , SI_PROPERTYTELEKINESIS , SCB_ATK_ELE ); + set_sc( TK_SEVENWIND , SC_PROPERTYDARK , SI_PROPERTYDARK , SCB_ATK_ELE ); + set_sc( SG_SUN_WARM , SC_WARM , SI_SG_SUN_WARM , SCB_NONE ); add_sc( SG_MOON_WARM , SC_WARM ); add_sc( SG_STAR_WARM , SC_WARM ); set_sc( SG_SUN_COMFORT , SC_SUN_COMFORT , SI_SUN_COMFORT , SCB_DEF2 ); @@ -405,39 +410,40 @@ void initChangeTables(void) { set_sc( SL_SWOO , SC_SWOO , SI_BLANK , SCB_SPEED ); set_sc( SL_SKE , SC_SKE , SI_BLANK , SCB_BATK|SCB_WATK|SCB_DEF|SCB_DEF2 ); set_sc( SL_SKA , SC_SKA , SI_BLANK , SCB_DEF|SCB_MDEF|SCB_ASPD ); - set_sc( SL_SMA , SC_SMA , SI_SMA , SCB_NONE ); + set_sc( SL_SMA , SC_SMA_READY , SI_SMA_READY , SCB_NONE ); set_sc( SM_SELFPROVOKE , SC_PROVOKE , SI_PROVOKE , SCB_DEF|SCB_DEF2|SCB_BATK|SCB_WATK ); set_sc( ST_PRESERVE , SC_PRESERVE , SI_PRESERVE , SCB_NONE ); - set_sc( PF_DOUBLECASTING , SC_DOUBLECAST , SI_DOUBLECAST , SCB_NONE ); + set_sc( PF_DOUBLECASTING , SC_DOUBLECASTING , SI_DOUBLECASTING , SCB_NONE ); set_sc( HW_GRAVITATION , SC_GRAVITATION , SI_BLANK , SCB_ASPD ); add_sc( WS_CARTTERMINATION , SC_STUN ); - set_sc( WS_OVERTHRUSTMAX , SC_MAXOVERTHRUST , SI_MAXOVERTHRUST , SCB_NONE ); + set_sc( WS_OVERTHRUSTMAX , SC_OVERTHRUSTMAX , SI_OVERTHRUSTMAX , SCB_NONE ); set_sc( CG_LONGINGFREEDOM , SC_LONGING , SI_BLANK , SCB_SPEED|SCB_ASPD ); add_sc( CG_HERMODE , SC_HERMODE ); + set_sc( CG_TAROTCARD , SC_TAROTCARD , SI_TAROTCARD , SCB_NONE ); set_sc( ITEM_ENCHANTARMS , SC_ENCHANTARMS , SI_BLANK , SCB_ATK_ELE ); - set_sc( SL_HIGH , SC_SPIRIT , SI_SPIRIT , SCB_ALL ); - set_sc( KN_ONEHAND , SC_ONEHAND , SI_ONEHAND , SCB_ASPD ); + set_sc( SL_HIGH , SC_SOULLINK , SI_SOULLINK , SCB_ALL ); + set_sc( KN_ONEHAND , SC_ONEHANDQUICKEN , SI_ONEHANDQUICKEN , SCB_ASPD ); set_sc( GS_FLING , SC_FLING , SI_BLANK , SCB_DEF|SCB_DEF2 ); add_sc( GS_CRACKER , SC_STUN ); - add_sc( GS_DISARM , SC_STRIPWEAPON ); - add_sc( GS_PIERCINGSHOT , SC_BLEEDING ); - set_sc( GS_MADNESSCANCEL , SC_MADNESSCANCEL , SI_MADNESSCANCEL , SCB_BATK|SCB_ASPD ); - set_sc( GS_ADJUSTMENT , SC_ADJUSTMENT , SI_ADJUSTMENT , SCB_HIT|SCB_FLEE ); - set_sc( GS_INCREASING , SC_INCREASING , SI_ACCURACY , SCB_AGI|SCB_DEX|SCB_HIT ); - set_sc( GS_GATLINGFEVER , SC_GATLINGFEVER , SI_GATLINGFEVER , SCB_BATK|SCB_FLEE|SCB_SPEED|SCB_ASPD ); - set_sc( NJ_TATAMIGAESHI , SC_TATAMIGAESHI , SI_BLANK , SCB_NONE ); - set_sc( NJ_SUITON , SC_SUITON , SI_BLANK , SCB_AGI|SCB_SPEED ); + add_sc( GS_DISARM , SC_NOEQUIPWEAPON ); + add_sc( GS_PIERCINGSHOT , SC_BLOODING ); + set_sc( GS_MADNESSCANCEL , SC_GS_MADNESSCANCEL , SI_GS_MADNESSCANCEL , SCB_BATK|SCB_ASPD ); + set_sc( GS_ADJUSTMENT , SC_GS_ADJUSTMENT , SI_GS_ADJUSTMENT , SCB_HIT|SCB_FLEE ); + set_sc( GS_INCREASING , SC_GS_ACCURACY , SI_GS_ACCURACY , SCB_AGI|SCB_DEX|SCB_HIT ); + set_sc( GS_GATLINGFEVER , SC_GS_GATLINGFEVER , SI_GS_GATLINGFEVER , SCB_BATK|SCB_FLEE|SCB_SPEED|SCB_ASPD ); + set_sc( NJ_TATAMIGAESHI , SC_NJ_TATAMIGAESHI , SI_BLANK , SCB_NONE ); + set_sc( NJ_SUITON , SC_NJ_SUITON , SI_NJ_SUITON , SCB_AGI|SCB_SPEED ); add_sc( NJ_HYOUSYOURAKU , SC_FREEZE ); - set_sc( NJ_NEN , SC_NEN , SI_NEN , SCB_STR|SCB_INT ); - set_sc( NJ_UTSUSEMI , SC_UTSUSEMI , SI_UTSUSEMI , SCB_NONE ); - set_sc( NJ_BUNSINJYUTSU , SC_BUNSINJYUTSU , SI_BUNSINJYUTSU , SCB_DYE ); + set_sc( NJ_NEN , SC_NJ_NEN , SI_NJ_NEN , SCB_STR|SCB_INT ); + set_sc( NJ_UTSUSEMI , SC_NJ_UTSUSEMI , SI_NJ_UTSUSEMI , SCB_NONE ); + set_sc( NJ_BUNSINJYUTSU , SC_NJ_BUNSINJYUTSU , SI_NJ_BUNSINJYUTSU , SCB_DYE ); add_sc( NPC_ICEBREATH , SC_FREEZE ); add_sc( NPC_ACIDBREATH , SC_POISON ); add_sc( NPC_HELLJUDGEMENT , SC_CURSE ); add_sc( NPC_WIDESILENCE , SC_SILENCE ); add_sc( NPC_WIDEFREEZE , SC_FREEZE ); - add_sc( NPC_WIDEBLEEDING , SC_BLEEDING ); + add_sc( NPC_WIDEBLEEDING , SC_BLOODING ); add_sc( NPC_WIDESTONE , SC_STONE ); add_sc( NPC_WIDECONFUSE , SC_CONFUSION ); add_sc( NPC_WIDESLEEP , SC_SLEEP ); @@ -446,8 +452,8 @@ void initChangeTables(void) { add_sc( NPC_MAGICMIRROR , SC_MAGICMIRROR ); set_sc( NPC_SLOWCAST , SC_SLOWCAST , SI_SLOWCAST , SCB_NONE ); set_sc( NPC_CRITICALWOUND , SC_CRITICALWOUND , SI_CRITICALWOUND , SCB_NONE ); - set_sc( NPC_STONESKIN , SC_ARMORCHANGE , SI_BLANK , SCB_DEF|SCB_MDEF ); - add_sc( NPC_ANTIMAGIC , SC_ARMORCHANGE ); + set_sc( NPC_STONESKIN , SC_STONESKIN , SI_BLANK , SCB_DEF|SCB_MDEF ); + add_sc( NPC_ANTIMAGIC , SC_STONESKIN ); add_sc( NPC_WIDECURSE , SC_CURSE ); add_sc( NPC_WIDESTUN , SC_STUN ); @@ -457,29 +463,29 @@ void initChangeTables(void) { set_sc( NPC_INVINCIBLEOFF , SC_INVINCIBLEOFF , SI_BLANK , SCB_SPEED ); set_sc( CASH_BLESSING , SC_BLESSING , SI_BLESSING , SCB_STR|SCB_INT|SCB_DEX ); - set_sc( CASH_INCAGI , SC_INCREASEAGI , SI_INCREASEAGI , SCB_AGI|SCB_SPEED ); + set_sc( CASH_INCAGI , SC_INC_AGI , SI_INC_AGI , SCB_AGI|SCB_SPEED ); set_sc( CASH_ASSUMPTIO , SC_ASSUMPTIO , SI_ASSUMPTIO , SCB_NONE ); set_sc( ALL_PARTYFLEE , SC_PARTYFLEE , SI_PARTYFLEE , SCB_NONE ); set_sc( ALL_ODINS_POWER , SC_ODINS_POWER , SI_ODINS_POWER , SCB_MATK|SCB_BATK|SCB_MDEF|SCB_DEF ); - set_sc( CR_SHRINK , SC_SHRINK , SI_SHRINK , SCB_NONE ); - set_sc( RG_CLOSECONFINE , SC_CLOSECONFINE2 , SI_CLOSECONFINE2 , SCB_NONE ); - set_sc( RG_CLOSECONFINE , SC_CLOSECONFINE , SI_CLOSECONFINE , SCB_FLEE ); - set_sc( WZ_SIGHTBLASTER , SC_SIGHTBLASTER , SI_SIGHTBLASTER , SCB_NONE ); - set_sc( DC_WINKCHARM , SC_WINKCHARM , SI_WINKCHARM , SCB_NONE ); + set_sc( CR_SHRINK , SC_CR_SHRINK , SI_CR_SHRINK , SCB_NONE ); + set_sc( RG_CLOSECONFINE , SC_RG_CCONFINE_S , SI_RG_CCONFINE_S , SCB_NONE ); + set_sc( RG_CLOSECONFINE , SC_RG_CCONFINE_M , SI_RG_CCONFINE_M , SCB_FLEE ); + set_sc( WZ_SIGHTBLASTER , SC_WZ_SIGHTBLASTER , SI_WZ_SIGHTBLASTER , SCB_NONE ); + set_sc( DC_WINKCHARM , SC_DC_WINKCHARM , SI_DC_WINKCHARM , SCB_NONE ); add_sc( MO_BALKYOUNG , SC_STUN ); - add_sc( SA_ELEMENTWATER , SC_ELEMENTALCHANGE ); - add_sc( SA_ELEMENTFIRE , SC_ELEMENTALCHANGE ); - add_sc( SA_ELEMENTGROUND , SC_ELEMENTALCHANGE ); - add_sc( SA_ELEMENTWIND , SC_ELEMENTALCHANGE ); - - set_sc( HLIF_AVOID , SC_AVOID , SI_BLANK , SCB_SPEED ); - set_sc( HLIF_CHANGE , SC_CHANGE , SI_BLANK , SCB_VIT|SCB_INT ); - set_sc( HFLI_FLEET , SC_FLEET , SI_BLANK , SCB_ASPD|SCB_BATK|SCB_WATK ); - set_sc( HFLI_SPEED , SC_SPEED , SI_BLANK , SCB_FLEE ); - set_sc( HAMI_DEFENCE , SC_DEFENCE , SI_BLANK , SCB_DEF ); - set_sc( HAMI_BLOODLUST , SC_BLOODLUST , SI_BLANK , SCB_BATK|SCB_WATK ); + add_sc( SA_ELEMENTWATER , SC_ARMOR_PROPERTY ); + add_sc( SA_ELEMENTFIRE , SC_ARMOR_PROPERTY ); + add_sc( SA_ELEMENTGROUND , SC_ARMOR_PROPERTY ); + add_sc( SA_ELEMENTWIND , SC_ARMOR_PROPERTY ); + + set_sc( HLIF_AVOID , SC_HLIF_AVOID , SI_BLANK , SCB_SPEED ); + set_sc( HLIF_CHANGE , SC_HLIF_CHANGE , SI_BLANK , SCB_VIT|SCB_INT ); + set_sc( HFLI_FLEET , SC_HLIF_FLEET , SI_BLANK , SCB_ASPD|SCB_BATK|SCB_WATK ); + set_sc( HFLI_SPEED , SC_HLIF_SPEED , SI_BLANK , SCB_FLEE ); + set_sc( HAMI_DEFENCE , SC_HAMI_DEFENCE , SI_BLANK , SCB_DEF ); + set_sc( HAMI_BLOODLUST , SC_HAMI_BLOODLUST , SI_BLANK , SCB_BATK|SCB_WATK ); // Homunculus S add_sc(MH_STAHL_HORN, SC_STUN); @@ -489,25 +495,25 @@ void initChangeTables(void) { add_sc(MH_ERASER_CUTTER, SC_ERASER_CUTTER); set_sc(MH_OVERED_BOOST, SC_OVERED_BOOST, SI_BLANK, SCB_FLEE|SCB_ASPD); add_sc(MH_LIGHT_OF_REGENE, SC_LIGHT_OF_REGENE); - set_sc(MH_VOLCANIC_ASH, SC_ASH, SI_VOLCANIC_ASH, SCB_DEF|SCB_DEF2|SCB_HIT|SCB_BATK|SCB_FLEE); + set_sc(MH_VOLCANIC_ASH, SC_VOLCANIC_ASH, SI_VOLCANIC_ASH, SCB_DEF|SCB_DEF2|SCB_HIT|SCB_BATK|SCB_FLEE); set_sc(MH_GRANITIC_ARMOR, SC_GRANITIC_ARMOR, SI_GRANITIC_ARMOR, SCB_NONE); set_sc(MH_MAGMA_FLOW, SC_MAGMA_FLOW, SI_MAGMA_FLOW, SCB_NONE); set_sc(MH_PYROCLASTIC, SC_PYROCLASTIC, SI_PYROCLASTIC, SCB_BATK|SCB_ATK_ELE); add_sc(MH_LAVA_SLIDE, SC_BURNING); - set_sc(MH_NEEDLE_OF_PARALYZE, SC_PARALYSIS, SI_NEEDLE_OF_PARALYZE, SCB_DEF2); + set_sc(MH_NEEDLE_OF_PARALYZE, SC_NEEDLE_OF_PARALYZE, SI_NEEDLE_OF_PARALYZE, SCB_DEF2); add_sc(MH_POISON_MIST, SC_BLIND); set_sc(MH_PAIN_KILLER, SC_PAIN_KILLER, SI_PAIN_KILLER, SCB_ASPD); add_sc(MH_STYLE_CHANGE, SC_STYLE_CHANGE); - set_sc( MH_TINDER_BREAKER , SC_CLOSECONFINE2 , SI_CLOSECONFINE2 , SCB_NONE ); - set_sc( MH_TINDER_BREAKER , SC_CLOSECONFINE , SI_CLOSECONFINE , SCB_FLEE ); + set_sc( MH_TINDER_BREAKER , SC_RG_CCONFINE_S , SI_RG_CCONFINE_S , SCB_NONE ); + set_sc( MH_TINDER_BREAKER , SC_RG_CCONFINE_M , SI_RG_CCONFINE_M , SCB_FLEE ); add_sc( MER_CRASH , SC_STUN ); set_sc( MER_PROVOKE , SC_PROVOKE , SI_PROVOKE , SCB_DEF|SCB_DEF2|SCB_BATK|SCB_WATK ); add_sc( MS_MAGNUM , SC_WATK_ELEMENT ); add_sc( MER_SIGHT , SC_SIGHT ); - set_sc( MER_DECAGI , SC_DECREASEAGI , SI_DECREASEAGI , SCB_AGI|SCB_SPEED ); + set_sc( MER_DECAGI , SC_DEC_AGI , SI_DEC_AGI , SCB_AGI|SCB_SPEED ); set_sc( MER_MAGNIFICAT , SC_MAGNIFICAT , SI_MAGNIFICAT , SCB_REGEN ); add_sc( MER_LEXDIVINA , SC_SILENCE ); add_sc( MA_LANDMINE , SC_STUN ); @@ -520,19 +526,19 @@ void initChangeTables(void) { set_sc( MS_PARRYING , SC_PARRYING , SI_PARRYING , SCB_NONE ); set_sc( MS_BERSERK , SC_BERSERK , SI_BERSERK , SCB_DEF|SCB_DEF2|SCB_MDEF|SCB_MDEF2|SCB_FLEE|SCB_SPEED|SCB_ASPD|SCB_MAXHP|SCB_REGEN ); add_sc( ML_SPIRALPIERCE , SC_STOP ); - set_sc( MER_QUICKEN , SC_MERC_QUICKEN , SI_BLANK , SCB_ASPD ); + set_sc( MER_QUICKEN , SC_MER_QUICKEN , SI_BLANK , SCB_ASPD ); add_sc( ML_DEVOTION , SC_DEVOTION ); set_sc( MER_KYRIE , SC_KYRIE , SI_KYRIE , SCB_NONE ); set_sc( MER_BLESSING , SC_BLESSING , SI_BLESSING , SCB_STR|SCB_INT|SCB_DEX ); - set_sc( MER_INCAGI , SC_INCREASEAGI , SI_INCREASEAGI , SCB_AGI|SCB_SPEED ); + set_sc( MER_INCAGI , SC_INC_AGI , SI_INC_AGI , SCB_AGI|SCB_SPEED ); set_sc( GD_LEADERSHIP , SC_LEADERSHIP , SI_BLANK , SCB_STR ); set_sc( GD_GLORYWOUNDS , SC_GLORYWOUNDS , SI_BLANK , SCB_VIT ); set_sc( GD_SOULCOLD , SC_SOULCOLD , SI_BLANK , SCB_AGI ); set_sc( GD_HAWKEYES , SC_HAWKEYES , SI_BLANK , SCB_DEX ); - set_sc( GD_BATTLEORDER , SC_BATTLEORDERS , SI_BLANK , SCB_STR|SCB_INT|SCB_DEX ); - set_sc( GD_REGENERATION , SC_REGENERATION , SI_BLANK , SCB_REGEN ); + set_sc( GD_BATTLEORDER , SC_GDSKILL_BATTLEORDER , SI_BLANK , SCB_STR|SCB_INT|SCB_DEX ); + set_sc( GD_REGENERATION , SC_GDSKILL_REGENERATION , SI_BLANK , SCB_REGEN ); /** * Rune Knight @@ -541,15 +547,16 @@ void initChangeTables(void) { set_sc( RK_DRAGONHOWLING , SC_FEAR , SI_BLANK , SCB_FLEE|SCB_HIT ); set_sc( RK_DEATHBOUND , SC_DEATHBOUND , SI_DEATHBOUND , SCB_NONE ); set_sc( RK_WINDCUTTER , SC_FEAR , SI_BLANK , SCB_FLEE|SCB_HIT ); - add_sc( RK_DRAGONBREATH , SC_BURNING ); - set_sc( RK_MILLENNIUMSHIELD , SC_MILLENNIUMSHIELD , SI_REUSE_MILLENNIUMSHIELD , SCB_NONE ); + set_sc( RK_DRAGONBREATH , SC_BURNING , SI_BLANK , SCB_MDEF ); + set_sc( RK_MILLENNIUMSHIELD , SC_MILLENNIUMSHIELD , SI_BLANK , SCB_NONE ); set_sc( RK_REFRESH , SC_REFRESH , SI_REFRESH , SCB_NONE ); set_sc( RK_GIANTGROWTH , SC_GIANTGROWTH , SI_GIANTGROWTH , SCB_STR ); - set_sc( RK_STONEHARDSKIN , SC_STONEHARDSKIN , SI_STONEHARDSKIN , SCB_DEF|SCB_MDEF ); + set_sc( RK_STONEHARDSKIN , SC_STONEHARDSKIN , SI_STONEHARDSKIN , SCB_NONE ); set_sc( RK_VITALITYACTIVATION, SC_VITALITYACTIVATION, SI_VITALITYACTIVATION, SCB_REGEN ); set_sc( RK_FIGHTINGSPIRIT , SC_FIGHTINGSPIRIT , SI_FIGHTINGSPIRIT , SCB_WATK|SCB_ASPD ); set_sc( RK_ABUNDANCE , SC_ABUNDANCE , SI_ABUNDANCE , SCB_NONE ); set_sc( RK_CRUSHSTRIKE , SC_CRUSHSTRIKE , SI_CRUSHSTRIKE , SCB_NONE ); + add_sc( RK_DRAGONBREATH_WATER, SC_FROSTMISTY ); /** * GC Guillotine Cross **/ @@ -559,12 +566,13 @@ void initChangeTables(void) { set_sc( GC_CLOAKINGEXCEED , SC_CLOAKINGEXCEED , SI_CLOAKINGEXCEED , SCB_SPEED ); set_sc( GC_HALLUCINATIONWALK , SC_HALLUCINATIONWALK, SI_HALLUCINATIONWALK, SCB_FLEE ); set_sc( GC_ROLLINGCUTTER , SC_ROLLINGCUTTER , SI_ROLLINGCUTTER , SCB_NONE ); + set_sc_with_vfx( GC_DARKCROW , SC_DARKCROW , SI_DARKCROW , SCB_NONE ); /** * Arch Bishop **/ set_sc( AB_ADORAMUS , SC_ADORAMUS , SI_ADORAMUS , SCB_AGI|SCB_SPEED ); add_sc( AB_CLEMENTIA , SC_BLESSING ); - add_sc( AB_CANTO , SC_INCREASEAGI ); + add_sc( AB_CANTO , SC_INC_AGI ); set_sc( AB_EPICLESIS , SC_EPICLESIS , SI_EPICLESIS , SCB_MAXHP ); add_sc( AB_PRAEFATIO , SC_KYRIE ); set_sc_with_vfx( AB_ORATIO , SC_ORATIO , SI_ORATIO , SCB_NONE ); @@ -574,14 +582,16 @@ void initChangeTables(void) { set_sc( AB_EXPIATIO , SC_EXPIATIO , SI_EXPIATIO , SCB_ATK_ELE ); set_sc( AB_DUPLELIGHT , SC_DUPLELIGHT , SI_DUPLELIGHT , SCB_NONE ); set_sc( AB_SECRAMENT , SC_SECRAMENT , SI_SECRAMENT , SCB_NONE ); + set_sc( AB_OFFERTORIUM , SC_OFFERTORIUM , SI_OFFERTORIUM , SCB_NONE ); /** * Warlock **/ add_sc( WL_WHITEIMPRISON , SC_WHITEIMPRISON ); - set_sc_with_vfx( WL_FROSTMISTY , SC_FREEZING , SI_FROSTMISTY , SCB_ASPD|SCB_SPEED|SCB_DEF|SCB_DEF2 ); - set_sc( WL_MARSHOFABYSS , SC_MARSHOFABYSS , SI_MARSHOFABYSS , SCB_SPEED|SCB_FLEE|SCB_DEF|SCB_MDEF ); + set_sc_with_vfx( WL_FROSTMISTY , SC_FROSTMISTY , SI_FROSTMISTY , SCB_ASPD|SCB_SPEED|SCB_DEF ); + set_sc( WL_MARSHOFABYSS , SC_MARSHOFABYSS , SI_MARSHOFABYSS , SCB_SPEED|SCB_FLEE|SCB_AGI|SCB_DEX ); set_sc(WL_RECOGNIZEDSPELL , SC_RECOGNIZEDSPELL , SI_RECOGNIZEDSPELL , SCB_MATK); set_sc( WL_STASIS , SC_STASIS , SI_STASIS , SCB_NONE ); + set_sc( WL_TELEKINESIS_INTENSE, SC_TELEKINESIS_INTENSE , SI_TELEKINESIS_INTENSE , SCB_MATK ); /** * Ranger **/ @@ -589,12 +599,13 @@ void initChangeTables(void) { set_sc( RA_ELECTRICSHOCKER , SC_ELECTRICSHOCKER , SI_ELECTRICSHOCKER , SCB_NONE ); set_sc( RA_WUGDASH , SC_WUGDASH , SI_WUGDASH , SCB_SPEED ); set_sc( RA_CAMOUFLAGE , SC_CAMOUFLAGE , SI_CAMOUFLAGE , SCB_SPEED ); - add_sc( RA_MAGENTATRAP , SC_ELEMENTALCHANGE ); - add_sc( RA_COBALTTRAP , SC_ELEMENTALCHANGE ); - add_sc( RA_MAIZETRAP , SC_ELEMENTALCHANGE ); - add_sc( RA_VERDURETRAP , SC_ELEMENTALCHANGE ); - add_sc( RA_FIRINGTRAP , SC_BURNING ); - set_sc_with_vfx( RA_ICEBOUNDTRAP , SC_FREEZING , SI_FROSTMISTY , SCB_NONE ); + add_sc( RA_MAGENTATRAP , SC_ARMOR_PROPERTY ); + add_sc( RA_COBALTTRAP , SC_ARMOR_PROPERTY ); + add_sc( RA_MAIZETRAP , SC_ARMOR_PROPERTY ); + add_sc( RA_VERDURETRAP , SC_ARMOR_PROPERTY ); + add_sc( RA_FIRINGTRAP , SC_BURNING ); + add_sc( RA_ICEBOUNDTRAP , SC_FROSTMISTY ); + set_sc( RA_UNLIMIT , SC_UNLIMIT , SI_UNLIMIT , SCB_NONE ); /** * Mechanic **/ @@ -609,7 +620,7 @@ void initChangeTables(void) { /** * Royal Guard **/ - set_sc( LG_REFLECTDAMAGE , SC_REFLECTDAMAGE , SI_LG_REFLECTDAMAGE, SCB_NONE ); + set_sc( LG_REFLECTDAMAGE , SC_LG_REFLECTDAMAGE , SI_LG_REFLECTDAMAGE, SCB_NONE ); set_sc( LG_FORCEOFVANGUARD , SC_FORCEOFVANGUARD , SI_FORCEOFVANGUARD , SCB_MAXHP|SCB_DEF ); set_sc( LG_EXEEDBREAK , SC_EXEEDBREAK , SI_EXEEDBREAK , SCB_NONE ); set_sc( LG_PRESTIGE , SC_PRESTIGE , SI_PRESTIGE , SCB_DEF ); @@ -619,6 +630,7 @@ void initChangeTables(void) { set_sc( LG_INSPIRATION , SC_INSPIRATION , SI_INSPIRATION , SCB_MAXHP|SCB_WATK|SCB_HIT|SCB_VIT|SCB_AGI|SCB_STR|SCB_DEX|SCB_INT|SCB_LUK); set_sc( LG_SHIELDSPELL , SC_SHIELDSPELL_DEF , SI_SHIELDSPELL_DEF , SCB_WATK ); set_sc( LG_SHIELDSPELL , SC_SHIELDSPELL_REF , SI_SHIELDSPELL_REF , SCB_DEF ); + set_sc( LG_KINGS_GRACE , SC_KINGS_GRACE , SI_KINGS_GRACE , SCB_NONE ); /** * Shadow Chaser **/ @@ -634,7 +646,7 @@ void initChangeTables(void) { set_sc( SC_LAZINESS , SC__LAZINESS , SI_LAZINESS , SCB_FLEE ); set_sc( SC_UNLUCKY , SC__UNLUCKY , SI_UNLUCKY , SCB_CRI|SCB_FLEE2 ); set_sc( SC_WEAKNESS , SC__WEAKNESS , SI_WEAKNESS , SCB_FLEE2|SCB_MAXHP ); - set_sc( SC_STRIPACCESSARY , SC__STRIPACCESSORY , SI_STRIPACCESSARY , SCB_DEX|SCB_INT|SCB_LUK ); + set_sc( SC_STRIPACCESSARY , SC__STRIPACCESSARY , SI_STRIPACCESSARY , SCB_DEX|SCB_INT|SCB_LUK ); set_sc_with_vfx( SC_MANHOLE , SC__MANHOLE , SI_MANHOLE , SCB_NONE ); add_sc( SC_CHAOSPANIC , SC_CONFUSION ); set_sc_with_vfx( SC_BLOODYLUST , SC__BLOODYLUST , SI_BLOODYLUST , SCB_DEF | SCB_DEF2 | SCB_MDEF | SCB_MDEF2 | SCB_FLEE | SCB_SPEED | SCB_ASPD | SCB_MAXHP | SCB_REGEN ); @@ -647,30 +659,32 @@ void initChangeTables(void) { set_sc_with_vfx( SR_CURSEDCIRCLE , SC_CURSEDCIRCLE_TARGET, SI_CURSEDCIRCLE_TARGET , SCB_NONE ); set_sc( SR_LIGHTNINGWALK , SC_LIGHTNINGWALK , SI_LIGHTNINGWALK , SCB_NONE ); set_sc( SR_RAISINGDRAGON , SC_RAISINGDRAGON , SI_RAISINGDRAGON , SCB_REGEN|SCB_MAXHP|SCB_MAXSP ); - set_sc( SR_GENTLETOUCH_ENERGYGAIN, SC_GT_ENERGYGAIN , SI_GENTLETOUCH_ENERGYGAIN, SCB_NONE ); - set_sc( SR_GENTLETOUCH_CHANGE , SC_GT_CHANGE , SI_GENTLETOUCH_CHANGE , SCB_ASPD|SCB_MDEF|SCB_MAXHP ); - set_sc( SR_GENTLETOUCH_REVITALIZE, SC_GT_REVITALIZE , SI_GENTLETOUCH_REVITALIZE, SCB_MAXHP|SCB_REGEN ); + set_sc( SR_GENTLETOUCH_ENERGYGAIN, SC_GENTLETOUCH_ENERGYGAIN , SI_GENTLETOUCH_ENERGYGAIN, SCB_NONE ); + set_sc( SR_GENTLETOUCH_CHANGE , SC_GENTLETOUCH_CHANGE , SI_GENTLETOUCH_CHANGE , SCB_ASPD|SCB_MDEF|SCB_MAXHP ); + set_sc( SR_GENTLETOUCH_REVITALIZE, SC_GENTLETOUCH_REVITALIZE , SI_GENTLETOUCH_REVITALIZE, SCB_MAXHP|SCB_REGEN ); /** * Wanderer / Minstrel **/ - set_sc( WA_SWING_DANCE , SC_SWINGDANCE , SI_SWINGDANCE , SCB_SPEED|SCB_ASPD ); - set_sc( WA_SYMPHONY_OF_LOVER , SC_SYMPHONYOFLOVER , SI_SYMPHONYOFLOVERS , SCB_MDEF ); - set_sc( WA_MOONLIT_SERENADE , SC_MOONLITSERENADE , SI_MOONLITSERENADE , SCB_MATK ); - set_sc( MI_RUSH_WINDMILL , SC_RUSHWINDMILL , SI_RUSHWINDMILL , SCB_BATK ); - set_sc( MI_ECHOSONG , SC_ECHOSONG , SI_ECHOSONG , SCB_DEF2 ); - set_sc( MI_HARMONIZE , SC_HARMONIZE , SI_HARMONIZE , SCB_STR|SCB_AGI|SCB_VIT|SCB_INT|SCB_DEX|SCB_LUK ); - set_sc_with_vfx( WM_POEMOFNETHERWORLD , SC_NETHERWORLD , SI_NETHERWORLD , SCB_NONE ); - set_sc_with_vfx( WM_VOICEOFSIREN , SC_VOICEOFSIREN , SI_VOICEOFSIREN , SCB_NONE ); - set_sc_with_vfx( WM_LULLABY_DEEPSLEEP , SC_DEEPSLEEP , SI_DEEPSLEEP , SCB_NONE ); - set_sc( WM_SIRCLEOFNATURE , SC_SIRCLEOFNATURE , SI_SIRCLEOFNATURE , SCB_NONE ); - set_sc( WM_GLOOMYDAY , SC_GLOOMYDAY , SI_GLOOMYDAY , SCB_FLEE|SCB_ASPD ); - set_sc( WM_SONG_OF_MANA , SC_SONGOFMANA , SI_SONGOFMANA , SCB_NONE ); - set_sc( WM_DANCE_WITH_WUG , SC_DANCEWITHWUG , SI_DANCEWITHWUG , SCB_ASPD ); - set_sc( WM_SATURDAY_NIGHT_FEVER , SC_SATURDAYNIGHTFEVER , SI_SATURDAYNIGHTFEVER , SCB_BATK|SCB_DEF|SCB_FLEE|SCB_REGEN ); - set_sc( WM_LERADS_DEW , SC_LERADSDEW , SI_LERADSDEW , SCB_MAXHP ); - set_sc( WM_MELODYOFSINK , SC_MELODYOFSINK , SI_MELODYOFSINK , SCB_BATK|SCB_MATK ); - set_sc( WM_BEYOND_OF_WARCRY , SC_BEYONDOFWARCRY , SI_WARCRYOFBEYOND , SCB_BATK|SCB_MATK ); - set_sc( WM_UNLIMITED_HUMMING_VOICE, SC_UNLIMITEDHUMMINGVOICE, SI_UNLIMITEDHUMMINGVOICE, SCB_NONE ); + set_sc( WA_SWING_DANCE , SC_SWING , SI_SWINGDANCE , SCB_SPEED|SCB_ASPD ); + set_sc( WA_SYMPHONY_OF_LOVER , SC_SYMPHONY_LOVE , SI_SYMPHONYOFLOVERS , SCB_MDEF ); + set_sc( WA_MOONLIT_SERENADE , SC_MOONLIT_SERENADE , SI_MOONLITSERENADE , SCB_MATK ); + set_sc( MI_RUSH_WINDMILL , SC_RUSH_WINDMILL , SI_RUSHWINDMILL , SCB_BATK ); + set_sc( MI_ECHOSONG , SC_ECHOSONG , SI_ECHOSONG , SCB_DEF2 ); + set_sc( MI_HARMONIZE , SC_HARMONIZE , SI_HARMONIZE , SCB_STR|SCB_AGI|SCB_VIT|SCB_INT|SCB_DEX|SCB_LUK ); + set_sc_with_vfx( WM_POEMOFNETHERWORLD , SC_NETHERWORLD , SI_NETHERWORLD , SCB_NONE ); + set_sc_with_vfx( WM_VOICEOFSIREN , SC_SIREN , SI_SIREN , SCB_NONE ); + set_sc_with_vfx( WM_LULLABY_DEEPSLEEP , SC_DEEP_SLEEP , SI_DEEPSLEEP , SCB_NONE ); + set_sc( WM_SIRCLEOFNATURE , SC_SIRCLEOFNATURE , SI_SIRCLEOFNATURE , SCB_NONE ); + set_sc( WM_GLOOMYDAY , SC_GLOOMYDAY , SI_GLOOMYDAY , SCB_FLEE|SCB_ASPD ); + set_sc( WM_SONG_OF_MANA , SC_SONG_OF_MANA , SI_SONG_OF_MANA , SCB_NONE ); + set_sc( WM_DANCE_WITH_WUG , SC_DANCE_WITH_WUG , SI_DANCEWITHWUG , SCB_ASPD ); + set_sc( WM_SATURDAY_NIGHT_FEVER , SC_SATURDAY_NIGHT_FEVER , SI_SATURDAYNIGHTFEVER , SCB_BATK|SCB_DEF|SCB_FLEE|SCB_REGEN ); + set_sc( WM_LERADS_DEW , SC_LERADS_DEW , SI_LERADSDEW , SCB_MAXHP ); + set_sc( WM_MELODYOFSINK , SC_MELODYOFSINK , SI_MELODYOFSINK , SCB_BATK|SCB_MATK ); + set_sc( WM_BEYOND_OF_WARCRY , SC_BEYOND_OF_WARCRY , SI_WARCRYOFBEYOND , SCB_BATK|SCB_MATK ); + set_sc( WM_UNLIMITED_HUMMING_VOICE, SC_UNLIMITED_HUMMING_VOICE, SI_UNLIMITEDHUMMINGVOICE, SCB_NONE ); + set_sc( WM_FRIGG_SONG , SC_FRIGG_SONG , SI_FRIGG_SONG , SCB_MAXHP ); + /** * Sorcerer **/ @@ -682,7 +696,7 @@ void initChangeTables(void) { set_sc( SO_STRIKING , SC_STRIKING , SI_STRIKING , SCB_WATK|SCB_CRI ); set_sc( SO_WARMER , SC_WARMER , SI_WARMER , SCB_NONE ); set_sc( SO_VACUUM_EXTREME , SC_VACUUM_EXTREME , SI_VACUUM_EXTREME , SCB_NONE ); - set_sc( SO_ARRULLO , SC_DEEPSLEEP , SI_DEEPSLEEP , SCB_NONE ); + set_sc( SO_ARRULLO , SC_DEEP_SLEEP , SI_DEEPSLEEP , SCB_NONE ); set_sc( SO_FIRE_INSIGNIA , SC_FIRE_INSIGNIA , SI_FIRE_INSIGNIA , SCB_MATK | SCB_BATK | SCB_WATK | SCB_ATK_ELE | SCB_REGEN ); set_sc( SO_WATER_INSIGNIA , SC_WATER_INSIGNIA , SI_WATER_INSIGNIA , SCB_WATK | SCB_ATK_ELE | SCB_REGEN ); set_sc( SO_WIND_INSIGNIA , SC_WIND_INSIGNIA , SI_WIND_INSIGNIA , SCB_WATK | SCB_ATK_ELE | SCB_REGEN ); @@ -691,11 +705,11 @@ void initChangeTables(void) { * Genetic **/ set_sc( GN_CARTBOOST , SC_GN_CARTBOOST, SI_CARTSBOOST , SCB_SPEED ); - set_sc( GN_THORNS_TRAP , SC_THORNSTRAP , SI_THORNTRAP , SCB_NONE ); - set_sc_with_vfx( GN_BLOOD_SUCKER , SC_BLOODSUCKER , SI_BLOODSUCKER , SCB_NONE ); + set_sc( GN_THORNS_TRAP , SC_THORNS_TRAP , SI_THORNTRAP , SCB_NONE ); + set_sc_with_vfx( GN_BLOOD_SUCKER , SC_BLOOD_SUCKER , SI_BLOODSUCKER , SCB_NONE ); set_sc( GN_WALLOFTHORN , SC_STOP , SI_BLANK , SCB_NONE ); - set_sc( GN_FIRE_EXPANSION_SMOKE_POWDER, SC_SMOKEPOWDER , SI_FIRE_EXPANSION_SMOKE_POWDER, SCB_NONE ); - set_sc( GN_FIRE_EXPANSION_TEAR_GAS , SC_TEARGAS , SI_FIRE_EXPANSION_TEAR_GAS , SCB_NONE ); + set_sc( GN_FIRE_EXPANSION_SMOKE_POWDER, SC_FIRE_EXPANSION_SMOKE_POWDER , SI_FIRE_EXPANSION_SMOKE_POWDER, SCB_NONE ); + set_sc( GN_FIRE_EXPANSION_TEAR_GAS , SC_FIRE_EXPANSION_TEAR_GAS , SI_FIRE_EXPANSION_TEAR_GAS , SCB_NONE ); set_sc( GN_MANDRAGORA , SC_MANDRAGORA , SI_MANDRAGORA , SCB_INT ); // Elemental Spirit summoner's 'side' status changes. @@ -727,7 +741,7 @@ void initChangeTables(void) { set_sc( EL_ROCK_CRUSHER_ATK, SC_ROCK_CRUSHER_ATK , SI_ROCK_CRUSHER_ATK , SCB_SPEED ); add_sc( KO_YAMIKUMO , SC_HIDING ); - set_sc_with_vfx( KO_JYUMONJIKIRI , SC_JYUMONJIKIRI , SI_KO_JYUMONJIKIRI , SCB_NONE ); + set_sc_with_vfx( KO_JYUMONJIKIRI , SC_KO_JYUMONJIKIRI , SI_KO_JYUMONJIKIRI , SCB_NONE ); add_sc( KO_MAKIBISHI , SC_STUN ); set_sc( KO_MEIKYOUSISUI , SC_MEIKYOUSISUI , SI_MEIKYOUSISUI , SCB_NONE ); set_sc( KO_KYOUGAKU , SC_KYOUGAKU , SI_KYOUGAKU , SCB_STR|SCB_AGI|SCB_VIT|SCB_INT|SCB_DEX|SCB_LUK ); @@ -736,12 +750,14 @@ void initChangeTables(void) { set_sc( KO_IZAYOI , SC_IZAYOI , SI_IZAYOI , SCB_MATK ); set_sc( KG_KYOMU , SC_KYOMU , SI_KYOMU , SCB_NONE ); set_sc( KG_KAGEMUSYA , SC_KAGEMUSYA , SI_KAGEMUSYA , SCB_NONE ); - set_sc( KG_KAGEHUMI , SC_KAGEHUMI , SI_KG_KAGEHUMI , SCB_NONE ); + set_sc( KG_KAGEHUMI , SC_KG_KAGEHUMI , SI_KG_KAGEHUMI , SCB_NONE ); set_sc( OB_ZANGETSU , SC_ZANGETSU , SI_ZANGETSU , SCB_MATK|SCB_BATK ); set_sc_with_vfx( OB_AKAITSUKI , SC_AKAITSUKI , SI_AKAITSUKI , SCB_NONE ); set_sc( OB_OBOROGENSOU , SC_GENSOU , SI_GENSOU , SCB_NONE ); - // Storing the target job rather than simply SC_SPIRIT simplifies code later on. + set_sc( ALL_FULL_THROTTLE , SC_FULL_THROTTLE , SI_FULL_THROTTLE , SCB_SPEED|SCB_STR|SCB_AGI|SCB_VIT|SCB_INT|SCB_DEX|SCB_LUK ); + + // Storing the target job rather than simply SC_SOULLINK simplifies code later on. SkillStatusChangeTable[SL_ALCHEMIST] = (sc_type)MAPID_ALCHEMIST, SkillStatusChangeTable[SL_MONK] = (sc_type)MAPID_MONK, SkillStatusChangeTable[SL_STAR] = (sc_type)MAPID_STAR_GLADIATOR, @@ -759,33 +775,33 @@ void initChangeTables(void) { SkillStatusChangeTable[SL_SOULLINKER] = (sc_type)MAPID_SOUL_LINKER, //Status that don't have a skill associated. - StatusIconChangeTable[SC_WEIGHT50] = SI_WEIGHT50; - StatusIconChangeTable[SC_WEIGHT90] = SI_WEIGHT90; - StatusIconChangeTable[SC_ASPDPOTION0] = SI_ASPDPOTION0; - StatusIconChangeTable[SC_ASPDPOTION1] = SI_ASPDPOTION1; - StatusIconChangeTable[SC_ASPDPOTION2] = SI_ASPDPOTION2; - StatusIconChangeTable[SC_ASPDPOTION3] = SI_ASPDPOTIONINFINITY; - StatusIconChangeTable[SC_SPEEDUP0] = SI_MOVHASTE_HORSE; - StatusIconChangeTable[SC_SPEEDUP1] = SI_SPEEDPOTION1; - StatusIconChangeTable[SC_INCSTR] = SI_INCSTR; - StatusIconChangeTable[SC_MIRACLE] = SI_SPIRIT; - StatusIconChangeTable[SC_INTRAVISION] = SI_INTRAVISION; - StatusIconChangeTable[SC_STRFOOD] = SI_FOODSTR; - StatusIconChangeTable[SC_AGIFOOD] = SI_FOODAGI; - StatusIconChangeTable[SC_VITFOOD] = SI_FOODVIT; - StatusIconChangeTable[SC_INTFOOD] = SI_FOODINT; - StatusIconChangeTable[SC_DEXFOOD] = SI_FOODDEX; - StatusIconChangeTable[SC_LUKFOOD] = SI_FOODLUK; - StatusIconChangeTable[SC_FLEEFOOD]= SI_FOODFLEE; - StatusIconChangeTable[SC_HITFOOD] = SI_FOODHIT; + StatusIconChangeTable[SC_WEIGHTOVER50] = SI_WEIGHTOVER50; + StatusIconChangeTable[SC_WEIGHTOVER90] = SI_WEIGHTOVER90; + StatusIconChangeTable[SC_ATTHASTE_POTION1] = SI_ATTHASTE_POTION1; + StatusIconChangeTable[SC_ATTHASTE_POTION2] = SI_ATTHASTE_POTION2; + StatusIconChangeTable[SC_ATTHASTE_POTION3] = SI_ATTHASTE_POTION3; + StatusIconChangeTable[SC_ATTHASTE_INFINITY] = SI_ATTHASTE_INFINITY; + StatusIconChangeTable[SC_MOVHASTE_HORSE] = SI_MOVHASTE_HORSE; + StatusIconChangeTable[SC_MOVHASTE_INFINITY] = SI_MOVHASTE_INFINITY; + StatusIconChangeTable[SC_CHASEWALK2] = SI_INCSTR; + StatusIconChangeTable[SC_MIRACLE] = SI_SOULLINK; + StatusIconChangeTable[SC_CLAIRVOYANCE] = SI_CLAIRVOYANCE; + StatusIconChangeTable[SC_FOOD_STR] = SI_FOOD_STR; + StatusIconChangeTable[SC_FOOD_AGI] = SI_FOOD_AGI; + StatusIconChangeTable[SC_FOOD_VIT] = SI_FOOD_VIT; + StatusIconChangeTable[SC_FOOD_INT] = SI_FOOD_INT; + StatusIconChangeTable[SC_FOOD_DEX] = SI_FOOD_DEX; + StatusIconChangeTable[SC_FOOD_LUK] = SI_FOOD_LUK; + StatusIconChangeTable[SC_FOOD_BASICAVOIDANCE]= SI_FOOD_BASICAVOIDANCE; + StatusIconChangeTable[SC_FOOD_BASICHIT] = SI_FOOD_BASICHIT; StatusIconChangeTable[SC_MANU_ATK] = SI_MANU_ATK; StatusIconChangeTable[SC_MANU_DEF] = SI_MANU_DEF; StatusIconChangeTable[SC_SPL_ATK] = SI_SPL_ATK; StatusIconChangeTable[SC_SPL_DEF] = SI_SPL_DEF; StatusIconChangeTable[SC_MANU_MATK] = SI_MANU_MATK; StatusIconChangeTable[SC_SPL_MATK] = SI_SPL_MATK; - StatusIconChangeTable[SC_ATKPOTION] = SI_PLUSATTACKPOWER; - StatusIconChangeTable[SC_MATKPOTION] = SI_PLUSMAGICPOWER; + StatusIconChangeTable[SC_PLUSATTACKPOWER] = SI_PLUSATTACKPOWER; + StatusIconChangeTable[SC_PLUSMAGICPOWER] = SI_PLUSMAGICPOWER; //Cash Items StatusIconChangeTable[SC_FOOD_STR_CASH] = SI_FOOD_STR_CASH; StatusIconChangeTable[SC_FOOD_AGI_CASH] = SI_FOOD_AGI_CASH; @@ -793,32 +809,32 @@ void initChangeTables(void) { StatusIconChangeTable[SC_FOOD_DEX_CASH] = SI_FOOD_DEX_CASH; StatusIconChangeTable[SC_FOOD_INT_CASH] = SI_FOOD_INT_CASH; StatusIconChangeTable[SC_FOOD_LUK_CASH] = SI_FOOD_LUK_CASH; - StatusIconChangeTable[SC_EXPBOOST] = SI_EXPBOOST; - StatusIconChangeTable[SC_ITEMBOOST] = SI_ITEMBOOST; - StatusIconChangeTable[SC_JEXPBOOST] = SI_CASH_PLUSONLYJOBEXP; - StatusIconChangeTable[SC_LIFEINSURANCE] = SI_LIFEINSURANCE; - StatusIconChangeTable[SC_BOSSMAPINFO] = SI_BOSSMAPINFO; - StatusIconChangeTable[SC_DEF_RATE] = SI_DEF_RATE; - StatusIconChangeTable[SC_MDEF_RATE] = SI_MDEF_RATE; - StatusIconChangeTable[SC_INCCRI] = SI_INCCRI; - StatusIconChangeTable[SC_INCFLEE2] = SI_PLUSAVOIDVALUE; - StatusIconChangeTable[SC_INCHEALRATE] = SI_INCHEALRATE; + StatusIconChangeTable[SC_CASH_PLUSEXP] = SI_CASH_PLUSEXP; + StatusIconChangeTable[SC_CASH_RECEIVEITEM] = SI_CASH_RECEIVEITEM; + StatusIconChangeTable[SC_CASH_PLUSONLYJOBEXP] = SI_CASH_PLUSONLYJOBEXP; + StatusIconChangeTable[SC_CASH_DEATHPENALTY] = SI_CASH_DEATHPENALTY; + StatusIconChangeTable[SC_CASH_BOSS_ALARM] = SI_CASH_BOSS_ALARM; + StatusIconChangeTable[SC_PROTECT_DEF] = SI_PROTECT_DEF; + StatusIconChangeTable[SC_PROTECT_MDEF] = SI_PROTECT_MDEF; + StatusIconChangeTable[SC_CRITICALPERCENT] = SI_CRITICALPERCENT; + StatusIconChangeTable[SC_PLUSAVOIDVALUE] = SI_PLUSAVOIDVALUE; + StatusIconChangeTable[SC_HEALPLUS] = SI_HEALPLUS; StatusIconChangeTable[SC_S_LIFEPOTION] = SI_S_LIFEPOTION; StatusIconChangeTable[SC_L_LIFEPOTION] = SI_L_LIFEPOTION; - StatusIconChangeTable[SC_SPCOST_RATE] = SI_ATKER_BLOOD; - StatusIconChangeTable[SC_COMMONSC_RESIST] = SI_TARGET_BLOOD; + StatusIconChangeTable[SC_ATKER_BLOOD] = SI_ATKER_BLOOD; + StatusIconChangeTable[SC_TARGET_BLOOD] = SI_TARGET_BLOOD; // Mercenary Bonus Effects - StatusIconChangeTable[SC_MERC_FLEEUP] = SI_MERC_FLEEUP; - StatusIconChangeTable[SC_MERC_ATKUP] = SI_MERC_ATKUP; - StatusIconChangeTable[SC_MERC_HPUP] = SI_MERC_HPUP; - StatusIconChangeTable[SC_MERC_SPUP] = SI_MERC_SPUP; - StatusIconChangeTable[SC_MERC_HITUP] = SI_MERC_HITUP; + StatusIconChangeTable[SC_MER_FLEE] = SI_MER_FLEE; + StatusIconChangeTable[SC_MER_ATK] = SI_MER_ATK; + StatusIconChangeTable[SC_MER_HP] = SI_MER_HP; + StatusIconChangeTable[SC_MER_SP] = SI_MER_SP; + StatusIconChangeTable[SC_MER_HIT] = SI_MER_HIT; // Warlock Spheres - StatusIconChangeTable[SC_SPHERE_1] = SI_SPHERE_1; - StatusIconChangeTable[SC_SPHERE_2] = SI_SPHERE_2; - StatusIconChangeTable[SC_SPHERE_3] = SI_SPHERE_3; - StatusIconChangeTable[SC_SPHERE_4] = SI_SPHERE_4; - StatusIconChangeTable[SC_SPHERE_5] = SI_SPHERE_5; + StatusIconChangeTable[SC_SUMMON1] = SI_SPHERE_1; + StatusIconChangeTable[SC_SUMMON2] = SI_SPHERE_2; + StatusIconChangeTable[SC_SUMMON3] = SI_SPHERE_3; + StatusIconChangeTable[SC_SUMMON4] = SI_SPHERE_4; + StatusIconChangeTable[SC_SUMMON5] = SI_SPHERE_5; // Warlock Preserved spells StatusIconChangeTable[SC_SPELLBOOK1] = SI_SPELLBOOK1; StatusIconChangeTable[SC_SPELLBOOK2] = SI_SPELLBOOK2; @@ -826,7 +842,7 @@ void initChangeTables(void) { StatusIconChangeTable[SC_SPELLBOOK4] = SI_SPELLBOOK4; StatusIconChangeTable[SC_SPELLBOOK5] = SI_SPELLBOOK5; StatusIconChangeTable[SC_SPELLBOOK6] = SI_SPELLBOOK6; - StatusIconChangeTable[SC_MAXSPELLBOOK] = SI_SPELLBOOK7; + StatusIconChangeTable[SC_SPELLBOOK7] = SI_SPELLBOOK7; StatusIconChangeTable[SC_NEUTRALBARRIER_MASTER] = SI_NEUTRALBARRIER_MASTER; StatusIconChangeTable[SC_STEALTHFIELD_MASTER] = SI_STEALTHFIELD_MASTER; @@ -856,7 +872,7 @@ void initChangeTables(void) { StatusIconChangeTable[SC_MYSTERIOUS_POWDER] = SI_MYSTERIOUS_POWDER; StatusIconChangeTable[SC_MELON_BOMB] = SI_MELON_BOMB; StatusIconChangeTable[SC_BANANA_BOMB] = SI_BANANA_BOMB; - StatusIconChangeTable[SC_BANANA_BOMB_SITDOWN] = SI_BANANA_BOMB_SITDOWN_POSTDELAY; + StatusIconChangeTable[SC_BANANA_BOMB_SITDOWN_POSTDELAY] = SI_BANANA_BOMB_SITDOWN_POSTDELAY; //Genetics New Food Items Status Icons StatusIconChangeTable[SC_SAVAGE_STEAK] = SI_SAVAGE_STEAK; @@ -897,19 +913,20 @@ void initChangeTables(void) { StatusIconChangeTable[SC_CURSED_SOIL] = SI_CURSED_SOIL; StatusIconChangeTable[SC_UPHEAVAL] = SI_UPHEAVAL; StatusIconChangeTable[SC_PUSH_CART] = SI_ON_PUSH_CART; + StatusIconChangeTable[SC_REBOUND] = SI_REBOUND; StatusIconChangeTable[SC_ALL_RIDING] = SI_ALL_RIDING; //Other SC which are not necessarily associated to skills. - StatusChangeFlagTable[SC_ASPDPOTION0] = SCB_ASPD; - StatusChangeFlagTable[SC_ASPDPOTION1] = SCB_ASPD; - StatusChangeFlagTable[SC_ASPDPOTION2] = SCB_ASPD; - StatusChangeFlagTable[SC_ASPDPOTION3] = SCB_ASPD; - StatusChangeFlagTable[SC_SPEEDUP0] = SCB_SPEED; - StatusChangeFlagTable[SC_SPEEDUP1] = SCB_SPEED; - StatusChangeFlagTable[SC_ATKPOTION] = SCB_BATK; - StatusChangeFlagTable[SC_MATKPOTION] = SCB_MATK; + StatusChangeFlagTable[SC_ATTHASTE_POTION1] = SCB_ASPD; + StatusChangeFlagTable[SC_ATTHASTE_POTION2] = SCB_ASPD; + StatusChangeFlagTable[SC_ATTHASTE_POTION3] = SCB_ASPD; + StatusChangeFlagTable[SC_ATTHASTE_INFINITY] = SCB_ASPD; + StatusChangeFlagTable[SC_MOVHASTE_HORSE] = SCB_SPEED; + StatusChangeFlagTable[SC_MOVHASTE_INFINITY] = SCB_SPEED; + StatusChangeFlagTable[SC_PLUSATTACKPOWER] = SCB_BATK; + StatusChangeFlagTable[SC_PLUSMAGICPOWER] = SCB_MATK; StatusChangeFlagTable[SC_INCALLSTATUS] |= SCB_STR|SCB_AGI|SCB_VIT|SCB_INT|SCB_DEX|SCB_LUK; - StatusChangeFlagTable[SC_INCSTR] |= SCB_STR; + StatusChangeFlagTable[SC_CHASEWALK2] |= SCB_STR; StatusChangeFlagTable[SC_INCAGI] |= SCB_AGI; StatusChangeFlagTable[SC_INCVIT] |= SCB_VIT; StatusChangeFlagTable[SC_INCINT] |= SCB_INT; @@ -919,9 +936,9 @@ void initChangeTables(void) { StatusChangeFlagTable[SC_INCHITRATE] |= SCB_HIT; StatusChangeFlagTable[SC_INCFLEE] |= SCB_FLEE; StatusChangeFlagTable[SC_INCFLEERATE] |= SCB_FLEE; - StatusChangeFlagTable[SC_INCCRI] |= SCB_CRI; + StatusChangeFlagTable[SC_CRITICALPERCENT] |= SCB_CRI; StatusChangeFlagTable[SC_INCASPDRATE] |= SCB_ASPD; - StatusChangeFlagTable[SC_INCFLEE2] |= SCB_FLEE2; + StatusChangeFlagTable[SC_PLUSAVOIDVALUE] |= SCB_FLEE2; StatusChangeFlagTable[SC_INCMHPRATE] |= SCB_MAXHP; StatusChangeFlagTable[SC_INCMSPRATE] |= SCB_MAXSP; StatusChangeFlagTable[SC_INCMHP] |= SCB_MAXHP; @@ -929,20 +946,20 @@ void initChangeTables(void) { StatusChangeFlagTable[SC_INCATKRATE] |= SCB_BATK|SCB_WATK; StatusChangeFlagTable[SC_INCMATKRATE] |= SCB_MATK; StatusChangeFlagTable[SC_INCDEFRATE] |= SCB_DEF; - StatusChangeFlagTable[SC_STRFOOD] |= SCB_STR; - StatusChangeFlagTable[SC_AGIFOOD] |= SCB_AGI; - StatusChangeFlagTable[SC_VITFOOD] |= SCB_VIT; - StatusChangeFlagTable[SC_INTFOOD] |= SCB_INT; - StatusChangeFlagTable[SC_DEXFOOD] |= SCB_DEX; - StatusChangeFlagTable[SC_LUKFOOD] |= SCB_LUK; - StatusChangeFlagTable[SC_HITFOOD] |= SCB_HIT; - StatusChangeFlagTable[SC_FLEEFOOD] |= SCB_FLEE; + StatusChangeFlagTable[SC_FOOD_STR] |= SCB_STR; + StatusChangeFlagTable[SC_FOOD_AGI] |= SCB_AGI; + StatusChangeFlagTable[SC_FOOD_VIT] |= SCB_VIT; + StatusChangeFlagTable[SC_FOOD_INT] |= SCB_INT; + StatusChangeFlagTable[SC_FOOD_DEX] |= SCB_DEX; + StatusChangeFlagTable[SC_FOOD_LUK] |= SCB_LUK; + StatusChangeFlagTable[SC_FOOD_BASICHIT] |= SCB_HIT; + StatusChangeFlagTable[SC_FOOD_BASICAVOIDANCE] |= SCB_FLEE; StatusChangeFlagTable[SC_BATKFOOD] |= SCB_BATK; StatusChangeFlagTable[SC_WATKFOOD] |= SCB_WATK; StatusChangeFlagTable[SC_MATKFOOD] |= SCB_MATK; - StatusChangeFlagTable[SC_ARMOR_ELEMENT] |= SCB_ALL; + StatusChangeFlagTable[SC_ARMORPROPERTY] |= SCB_ALL; StatusChangeFlagTable[SC_ARMOR_RESIST] |= SCB_ALL; - StatusChangeFlagTable[SC_SPCOST_RATE] |= SCB_ALL; + StatusChangeFlagTable[SC_ATKER_BLOOD] |= SCB_ALL; StatusChangeFlagTable[SC_WALKSPEED] |= SCB_SPEED; StatusChangeFlagTable[SC_ITEMSCRIPT] |= SCB_ALL; // Cash Items @@ -953,11 +970,11 @@ void initChangeTables(void) { StatusChangeFlagTable[SC_FOOD_INT_CASH] = SCB_INT; StatusChangeFlagTable[SC_FOOD_LUK_CASH] = SCB_LUK; // Mercenary Bonus Effects - StatusChangeFlagTable[SC_MERC_FLEEUP] |= SCB_FLEE; - StatusChangeFlagTable[SC_MERC_ATKUP] |= SCB_WATK; - StatusChangeFlagTable[SC_MERC_HPUP] |= SCB_MAXHP; - StatusChangeFlagTable[SC_MERC_SPUP] |= SCB_MAXSP; - StatusChangeFlagTable[SC_MERC_HITUP] |= SCB_HIT; + StatusChangeFlagTable[SC_MER_FLEE] |= SCB_FLEE; + StatusChangeFlagTable[SC_MER_ATK] |= SCB_WATK; + StatusChangeFlagTable[SC_MER_HP] |= SCB_MAXHP; + StatusChangeFlagTable[SC_MER_SP] |= SCB_MAXSP; + StatusChangeFlagTable[SC_MER_HIT] |= SCB_HIT; // Guillotine Cross Poison Effects StatusChangeFlagTable[SC_PARALYSE] |= SCB_ASPD|SCB_FLEE|SCB_SPEED; StatusChangeFlagTable[SC_DEATHHURT] |= SCB_REGEN; @@ -978,30 +995,31 @@ void initChangeTables(void) { StatusChangeFlagTable[SC_EXTRACT_WHITE_POTION_Z] |= SCB_REGEN; StatusChangeFlagTable[SC_VITATA_500] |= SCB_REGEN; StatusChangeFlagTable[SC_EXTRACT_SALAMINE_JUICE] |= SCB_ASPD; + StatusChangeFlagTable[SC_REBOUND] |= SCB_SPEED|SCB_REGEN; StatusChangeFlagTable[SC_ALL_RIDING] = SCB_SPEED; /* StatusDisplayType Table [Ind/Hercules] */ StatusDisplayType[SC_ALL_RIDING] = true; StatusDisplayType[SC_PUSH_CART] = true; - StatusDisplayType[SC_SPHERE_1] = true; - StatusDisplayType[SC_SPHERE_2] = true; - StatusDisplayType[SC_SPHERE_3] = true; - StatusDisplayType[SC_SPHERE_4] = true; - StatusDisplayType[SC_SPHERE_5] = true; + StatusDisplayType[SC_SUMMON1] = true; + StatusDisplayType[SC_SUMMON2] = true; + StatusDisplayType[SC_SUMMON3] = true; + StatusDisplayType[SC_SUMMON4] = true; + StatusDisplayType[SC_SUMMON5] = true; StatusDisplayType[SC_CAMOUFLAGE] = true; StatusDisplayType[SC_DUPLELIGHT] = true; StatusDisplayType[SC_ORATIO] = true; - StatusDisplayType[SC_FREEZING] = true; + StatusDisplayType[SC_FROSTMISTY] = true; StatusDisplayType[SC_VENOMIMPRESS] = true; StatusDisplayType[SC_HALLUCINATIONWALK] = true; StatusDisplayType[SC_ROLLINGCUTTER] = true; StatusDisplayType[SC_BANDING] = true; StatusDisplayType[SC_CRYSTALIZE] = true; - StatusDisplayType[SC_DEEPSLEEP] = true; + StatusDisplayType[SC_DEEP_SLEEP] = true; StatusDisplayType[SC_CURSEDCIRCLE_ATKER]= true; StatusDisplayType[SC_CURSEDCIRCLE_TARGET]= true; - StatusDisplayType[SC_BLOODSUCKER] = true; + StatusDisplayType[SC_BLOOD_SUCKER] = true; StatusDisplayType[SC__SHADOWFORM] = true; StatusDisplayType[SC__MANHOLE] = true; @@ -1011,7 +1029,7 @@ void initChangeTables(void) { #endif if( !battle_config.display_hallucination ) //Disable Hallucination. - StatusIconChangeTable[SC_HALLUCINATION] = SI_BLANK; + StatusIconChangeTable[SC_ILLUSION] = SI_BLANK; } static void initDummyData(void) @@ -1147,7 +1165,7 @@ int status_damage(struct block_list *src,struct block_list *target,int hp, int s status_change_end(target, SC_STONE, INVALID_TIMER); status_change_end(target, SC_FREEZE, INVALID_TIMER); status_change_end(target, SC_SLEEP, INVALID_TIMER); - status_change_end(target, SC_WINKCHARM, INVALID_TIMER); + status_change_end(target, SC_DC_WINKCHARM, INVALID_TIMER); status_change_end(target, SC_CONFUSION, INVALID_TIMER); status_change_end(target, SC_TRICKDEAD, INVALID_TIMER); status_change_end(target, SC_HIDING, INVALID_TIMER); @@ -1155,8 +1173,8 @@ int status_damage(struct block_list *src,struct block_list *target,int hp, int s status_change_end(target, SC_CHASEWALK, INVALID_TIMER); status_change_end(target, SC_CAMOUFLAGE, INVALID_TIMER); status_change_end(target, SC__INVISIBILITY, INVALID_TIMER); - status_change_end(target, SC_DEEPSLEEP, INVALID_TIMER); - if ((sce=sc->data[SC_ENDURE]) && !sce->val4) { + status_change_end(target, SC_DEEP_SLEEP, INVALID_TIMER); + if ((sce=sc->data[SC_ENDURE]) && !sce->val4 && !sc->data[SC_LKCONCENTRATION]) { //Endure count is only reduced by non-players on non-gvg maps. //val4 signals infinite endure. [Skotlex] if (src && src->type != BL_PC && !map_flag_gvg(target->m) && !map[target->m].flag.battleground && --(sce->val2) < 0) @@ -1192,8 +1210,8 @@ int status_damage(struct block_list *src,struct block_list *target,int hp, int s status_change_end(target, SC_BERSERK, INVALID_TIMER); if( sc->data[SC_RAISINGDRAGON] && status->hp <= 1000 ) status_change_end(target, SC_RAISINGDRAGON, INVALID_TIMER); - if (sc->data[SC_SATURDAYNIGHTFEVER] && status->hp <= 100) - status_change_end(target, SC_SATURDAYNIGHTFEVER, INVALID_TIMER); + if (sc->data[SC_SATURDAY_NIGHT_FEVER] && status->hp <= 100) + status_change_end(target, SC_SATURDAY_NIGHT_FEVER, INVALID_TIMER); if (sc->data[SC__BLOODYLUST] && status->hp <= 100) status_change_end(target, SC__BLOODYLUST, INVALID_TIMER); } @@ -1576,9 +1594,9 @@ int status_check_skilluse(struct block_list *src, struct block_list *target, uin ) return 0; - if (sc->data[SC_WINKCHARM] && target && !flag) { //Prevents skill usage + if (sc->data[SC_DC_WINKCHARM] && target && !flag) { //Prevents skill usage if( unit_bl2ud(src) && (unit_bl2ud(src))->walktimer == INVALID_TIMER ) - unit_walktobl(src, iMap->id2bl(sc->data[SC_WINKCHARM]->val2), 3, 1); + unit_walktobl(src, iMap->id2bl(sc->data[SC_DC_WINKCHARM]->val2), 3, 1); clif->emotion(src, E_LV); return 0; } @@ -1632,13 +1650,13 @@ int status_check_skilluse(struct block_list *src, struct block_list *target, uin sc->data[SC__INVISIBILITY] || (sc->data[SC_CRYSTALIZE] && src->type != BL_MOB) || sc->data[SC__IGNORANCE] || - sc->data[SC_DEEPSLEEP] || - sc->data[SC_SATURDAYNIGHTFEVER] || + sc->data[SC_DEEP_SLEEP] || + sc->data[SC_SATURDAY_NIGHT_FEVER] || sc->data[SC_CURSEDCIRCLE_TARGET] || - (sc->data[SC_MARIONETTE] && skill_id != CG_MARIONETTE) || //Only skill you can use is marionette again to cancel it - (sc->data[SC_MARIONETTE2] && skill_id == CG_MARIONETTE) || //Cannot use marionette if you are being buffed by another + (sc->data[SC_MARIONETTE_MASTER] && skill_id != CG_MARIONETTE) || //Only skill you can use is marionette again to cancel it + (sc->data[SC_MARIONETTE] && skill_id == CG_MARIONETTE) || //Cannot use marionette if you are being buffed by another (sc->data[SC_STASIS] && skill->block_check(src, SC_STASIS, skill_id)) || - (sc->data[SC_KAGEHUMI] && skill->block_check(src, SC_KAGEHUMI, skill_id)) + (sc->data[SC_KG_KAGEHUMI] && skill->block_check(src, SC_KG_KAGEHUMI, skill_id)) )) return 0; @@ -1882,17 +1900,18 @@ static unsigned short status_base_atk(const struct block_list *bl, const struct str += dstr*dstr; if (bl->type == BL_PC) #ifdef RENEWAL - str = (rstr*10 + dex*10/5 + status->luk*10/3 + ((TBL_PC*)bl)->status.base_level*10/4)/10; + str = (int)(rstr + (float)dex/5 + (float)status->luk/3 + (float)((TBL_PC*)bl)->status.base_level/4); + else if(bl->type == BL_MOB) + str = rstr + ((TBL_MOB*)bl)->level; #else str+= dex/5 + status->luk/5; #endif return cap_value(str, 0, USHRT_MAX); } -#ifndef RENEWAL static inline unsigned short status_base_matk_min(const struct status_data* status){ return status->int_+(status->int_/7)*(status->int_/7); } static inline unsigned short status_base_matk_max(const struct status_data* status){ return status->int_+(status->int_/5)*(status->int_/5); } -#else +#ifdef RENEWAL unsigned short status_base_matk(const struct status_data* status, int level){ return status->int_+(status->int_/2)+(status->dex/5)+(status->luk/3)+(level/4); } #endif @@ -1907,11 +1926,11 @@ void status_calc_misc(struct block_list *bl, struct status_data *status, int lev status->cri = status->flee2 = 0; #ifdef RENEWAL // renewal formulas - status->matk_min = status->matk_max = status_base_matk(status, level); - status->hit += level + status->dex + status->luk/3 + 175; //base level + ( every 1 dex = +1 hit ) + (every 3 luk = +1 hit) + 175 - status->flee += level + status->agi + status->luk/5 + 100; //base level + ( every 1 agi = +1 flee ) + (every 5 luk = +1 flee) + 100 - status->def2 += (int)(((float)level + status->vit)/2 + ((float)status->agi/5)); //base level + (every 2 vit = +1 def) + (every 5 agi = +1 def) - status->mdef2 += (int)(status->int_ + ((float)level/4) + ((float)status->dex/5) + ((float)status->vit/5)); //(every 4 base level = +1 mdef) + (every 1 int = +1 mdef) + (every 5 dex = +1 mdef) + (every 5 vit = +1 mdef) + status->matk_min = status->matk_max = bl->type == BL_PC ? status_base_matk(status, level) : level + status->int_; + status->hit += level + status->dex + (bl->type == BL_PC ? status->luk/3 + 175 : 150); //base level + ( every 1 dex = +1 hit ) + (every 3 luk = +1 hit) + 175 + status->flee += level + status->agi + (bl->type == BL_PC ? status->luk/5 : 0) + 100; //base level + ( every 1 agi = +1 flee ) + (every 5 luk = +1 flee) + 100 + status->def2 += (int)(((float)level + status->vit)/2 + ( bl->type == BL_PC ? ((float)status->agi/5) : 0 )); //base level + (every 2 vit = +1 def) + (every 5 agi = +1 def) + status->mdef2 += (int)( bl->type == BL_PC ?(status->int_ + ((float)level/4) + ((float)(status->dex+status->vit)/5)):((float)(status->int_ + level)/4)); //(every 4 base level = +1 mdef) + (every 1 int = +1 mdef) + (every 5 dex = +1 mdef) + (every 5 vit = +1 mdef) #else status->matk_min = status_base_matk_min(status); status->matk_max = status_base_matk_max(status); @@ -1947,6 +1966,13 @@ void status_calc_misc(struct block_list *bl, struct status_data *status, int lev case BL_PC: //Players don't have a critical adjustment setting as of yet. break; + case BL_MER: +#ifdef RENEWAL + status->matk_min = status->matk_max = status_base_matk_max(status); + status->def2 = status->vit + level / 10 + status->vit / 5; + status->mdef2 = level / 10 + status->int_ / 5; +#endif + break; default: if(battle_config.critical_rate != 100) status->cri = status->cri*battle_config.critical_rate/100; @@ -2030,7 +2056,7 @@ int status_calc_mob_(struct mob_data* md, bool first) if (ud->skill_id == AM_SPHEREMINE) { status->max_hp = 2000 + 400*ud->skill_lv; } else if(ud->skill_id == KO_ZANZOU){ - status->max_hp = 3000 + 3000 * ud->skill_lv; + status->max_hp = 3000 + 3000 * ud->skill_lv + status_get_max_sp(battle->get_master(mbl)); } else { //AM_CANNIBALIZE status->max_hp = 1500 + 200*ud->skill_lv + 10*status_get_lv(mbl); status->mode|= MD_CANATTACK|MD_AGGRESSIVE; @@ -2352,8 +2378,8 @@ int status_calc_pc_(struct map_session_data* sd, bool first) memset (&sd->right_weapon.overrefine, 0, sizeof(sd->right_weapon) - sizeof(sd->right_weapon.atkmods)); memset (&sd->left_weapon.overrefine, 0, sizeof(sd->left_weapon) - sizeof(sd->left_weapon.atkmods)); - if (sd->special_state.intravision && !sd->sc.data[SC_INTRAVISION]) //Clear intravision as long as nothing else is using it - clif->sc_end(&sd->bl,sd->bl.id,SELF,SI_INTRAVISION); + if (sd->special_state.intravision && !sd->sc.data[SC_CLAIRVOYANCE]) //Clear intravision as long as nothing else is using it + clif->sc_end(&sd->bl,sd->bl.id,SELF,SI_CLAIRVOYANCE); memset(&sd->special_state,0,sizeof(sd->special_state)); memset(&status->max_hp, 0, sizeof(struct status_data)-(sizeof(status->hp)+sizeof(status->sp))); @@ -2365,7 +2391,7 @@ int status_calc_pc_(struct map_session_data* sd, bool first) status->mode = MD_MASK&~(MD_BOSS|MD_PLANT|MD_DETECTOR|MD_ANGRY|MD_TARGETWEAK); status->size = (sd->class_&JOBL_BABY)?SZ_SMALL:SZ_MEDIUM; - if (battle_config.character_size && pc_isriding(sd)) { //[Lupus] + if (battle_config.character_size && (pc_isriding(sd) || pc_isridingdragon(sd)) ) { //[Lupus] if (sd->class_&JOBL_BABY) { if (battle_config.character_size&SZ_BIG) status->size++; @@ -2638,7 +2664,7 @@ int status_calc_pc_(struct map_session_data* sd, bool first) sd->left_weapon.atkmods[1] = atkmods[1][sd->weapontype2]; sd->left_weapon.atkmods[2] = atkmods[2][sd->weapontype2]; - if(pc_isriding(sd) && + if( (pc_isriding(sd) || pc_isridingdragon(sd)) && (sd->status.weapon==W_1HSPEAR || sd->status.weapon==W_2HSPEAR)) { //When Riding with spear, damage modifier to mid-class becomes //same as versus large size. @@ -2704,8 +2730,10 @@ int status_calc_pc_(struct map_session_data* sd, bool first) if (sd->status.weapon < MAX_WEAPON_TYPE && sd->weapon_atk[sd->status.weapon]) status->batk += sd->weapon_atk[sd->status.weapon]; // Absolute modifiers from passive skills - if((skill=pc->checkskill(sd,BS_HILTBINDING))>0) +#ifndef RENEWAL + if((skill=pc->checkskill(sd,BS_HILTBINDING))>0) // it doesn't work in RE. status->batk += 4; +#endif // ----- HP MAX CALCULATION ----- @@ -2964,11 +2992,11 @@ int status_calc_pc_(struct map_session_data* sd, bool first) if((skill=pc->checkskill(sd,HP_MANARECHARGE))>0 ) sd->dsprate -= 4*skill; - if(sc->data[SC_SERVICE4U]) - sd->dsprate -= sc->data[SC_SERVICE4U]->val3; + if(sc->data[SC_SERVICEFORYOU]) + sd->dsprate -= sc->data[SC_SERVICEFORYOU]->val3; - if(sc->data[SC_SPCOST_RATE]) - sd->dsprate -= sc->data[SC_SPCOST_RATE]->val1; + if(sc->data[SC_ATKER_BLOOD]) + sd->dsprate -= sc->data[SC_ATKER_BLOOD]->val1; //Underflow protections. if(sd->dsprate < 0) @@ -3002,9 +3030,9 @@ int status_calc_pc_(struct map_session_data* sd, bool first) } if(sc->count){ - if(sc->data[SC_CONCENTRATE]) { //Update the card-bonus data - sc->data[SC_CONCENTRATE]->val3 = sd->param_bonus[1]; //Agi - sc->data[SC_CONCENTRATE]->val4 = sd->param_bonus[4]; //Dex + if(sc->data[SC_CONCENTRATION]) { //Update the card-bonus data + sc->data[SC_CONCENTRATION]->val3 = sd->param_bonus[1]; //Agi + sc->data[SC_CONCENTRATION]->val4 = sd->param_bonus[4]; //Dex } if(sc->data[SC_SIEGFRIED]){ i = sc->data[SC_SIEGFRIED]->val2; @@ -3022,11 +3050,11 @@ int status_calc_pc_(struct map_session_data* sd, bool first) sd->subele[ELE_HOLY] += sc->data[SC_PROVIDENCE]->val2; sd->subrace[RC_DEMON] += sc->data[SC_PROVIDENCE]->val2; } - if(sc->data[SC_ARMOR_ELEMENT]) { //This status change should grant card-type elemental resist. - sd->subele[ELE_WATER] += sc->data[SC_ARMOR_ELEMENT]->val1; - sd->subele[ELE_EARTH] += sc->data[SC_ARMOR_ELEMENT]->val2; - sd->subele[ELE_FIRE] += sc->data[SC_ARMOR_ELEMENT]->val3; - sd->subele[ELE_WIND] += sc->data[SC_ARMOR_ELEMENT]->val4; + if(sc->data[SC_ARMORPROPERTY]) { //This status change should grant card-type elemental resist. + sd->subele[ELE_WATER] += sc->data[SC_ARMORPROPERTY]->val1; + sd->subele[ELE_EARTH] += sc->data[SC_ARMORPROPERTY]->val2; + sd->subele[ELE_FIRE] += sc->data[SC_ARMORPROPERTY]->val3; + sd->subele[ELE_WIND] += sc->data[SC_ARMORPROPERTY]->val4; } if(sc->data[SC_ARMOR_RESIST]) { // Undead Scroll sd->subele[ELE_WATER] += sc->data[SC_ARMOR_RESIST]->val1; @@ -3266,17 +3294,13 @@ static unsigned short status_calc_vit(struct block_list *,struct status_change * static unsigned short status_calc_int(struct block_list *,struct status_change *,int); static unsigned short status_calc_dex(struct block_list *,struct status_change *,int); static unsigned short status_calc_luk(struct block_list *,struct status_change *,int); -static unsigned short status_calc_batk(struct block_list *,struct status_change *,int); -static unsigned short status_calc_watk(struct block_list *,struct status_change *,int); -static unsigned short status_calc_matk(struct block_list *,struct status_change *,int); -static signed short status_calc_hit(struct block_list *,struct status_change *,int); -static signed short status_calc_critical(struct block_list *,struct status_change *,int); -static signed short status_calc_flee(struct block_list *,struct status_change *,int); -static signed short status_calc_flee2(struct block_list *,struct status_change *,int); -static defType status_calc_def(struct block_list *bl, struct status_change *sc, int); -static signed short status_calc_def2(struct block_list *,struct status_change *,int); -static defType status_calc_mdef(struct block_list *bl, struct status_change *sc, int); -static signed short status_calc_mdef2(struct block_list *,struct status_change *,int); +static unsigned short status_calc_batk(struct block_list *,struct status_change *,int,bool); +static unsigned short status_calc_watk(struct block_list *,struct status_change *,int,bool); +static unsigned short status_calc_matk(struct block_list *,struct status_change *,int,bool); +static signed short status_calc_hit(struct block_list *,struct status_change *,int,bool); +static signed short status_calc_critical(struct block_list *,struct status_change *,int,bool); +static signed short status_calc_flee(struct block_list *,struct status_change *,int,bool); +static signed short status_calc_flee2(struct block_list *,struct status_change *,int,bool); static unsigned short status_calc_speed(struct block_list *,struct status_change *,int); static short status_calc_aspd_rate(struct block_list *,struct status_change *,int); static unsigned short status_calc_dmotion(struct block_list *bl, struct status_change *sc, int dmotion); @@ -3430,18 +3454,18 @@ void status_calc_regen_rate(struct block_list *bl, struct regen_data *regen, str || (sc->data[SC_DPOISON] && !sc->data[SC_SLOWPOISON]) || sc->data[SC_BERSERK] || sc->data[SC__BLOODYLUST] || sc->data[SC_TRICKDEAD] - || sc->data[SC_BLEEDING] + || sc->data[SC_BLOODING] || sc->data[SC_MAGICMUSHROOM] || sc->data[SC_RAISINGDRAGON] - || sc->data[SC_SATURDAYNIGHTFEVER] + || sc->data[SC_SATURDAY_NIGHT_FEVER] ) //No regen regen->flag = 0; if ( - sc->data[SC_DANCING] || sc->data[SC_OBLIVIONCURSE] || sc->data[SC_MAXIMIZEPOWER] + sc->data[SC_DANCING] || sc->data[SC_OBLIVIONCURSE] || sc->data[SC_MAXIMIZEPOWER] || sc->data[SC_REBOUND] || ( (bl->type == BL_PC && ((TBL_PC*)bl)->class_&MAPID_UPPERMASK) == MAPID_MONK && - (sc->data[SC_EXTREMITYFIST] || (sc->data[SC_EXPLOSIONSPIRITS] && (!sc->data[SC_SPIRIT] || sc->data[SC_SPIRIT]->val2 != SL_MONK))) + (sc->data[SC_EXTREMITYFIST] || (sc->data[SC_EXPLOSIONSPIRITS] && (!sc->data[SC_SOULLINK] || sc->data[SC_SOULLINK]->val2 != SL_MONK))) ) ) //No natural SP regen regen->flag &=~RGN_SP; @@ -3458,9 +3482,9 @@ void status_calc_regen_rate(struct block_list *bl, struct regen_data *regen, str regen->rate.hp += 1; regen->rate.sp += 1; } - if (sc->data[SC_REGENERATION]) + if (sc->data[SC_GDSKILL_REGENERATION]) { - const struct status_change_entry *sce = sc->data[SC_REGENERATION]; + const struct status_change_entry *sce = sc->data[SC_GDSKILL_REGENERATION]; if (!sce->val4) { regen->rate.hp += sce->val2; @@ -3468,8 +3492,8 @@ void status_calc_regen_rate(struct block_list *bl, struct regen_data *regen, str } else regen->flag&=~sce->val4; //Remove regen as specified by val4 } - if(sc->data[SC_GT_REVITALIZE]){ - regen->hp = cap_value(regen->hp*sc->data[SC_GT_REVITALIZE]->val3/100, 1, SHRT_MAX); + if(sc->data[SC_GENTLETOUCH_REVITALIZE]){ + regen->hp = cap_value(regen->hp*sc->data[SC_GENTLETOUCH_REVITALIZE]->val3/100, 1, SHRT_MAX); regen->state.walk= 1; } if ((sc->data[SC_FIRE_INSIGNIA] && sc->data[SC_FIRE_INSIGNIA]->val1 == 1) //if insignia lvl 1 @@ -3563,23 +3587,22 @@ void status_calc_bl_main(struct block_list *bl, /*enum scb_flag*/int flag) temp += status->batk; status->batk = cap_value(temp, 0, USHRT_MAX); } - status->batk = status_calc_batk(bl, sc, status->batk); + status->batk = status_calc_batk(bl, sc, status->batk, true); } - if(flag&SCB_WATK) { - - status->rhw.atk = status_calc_watk(bl, sc, b_status->rhw.atk); + if(flag&SCB_WATK) { + status->rhw.atk = status_calc_watk(bl, sc, b_status->rhw.atk, true); if (!sd) //Should not affect weapon refine bonus - status->rhw.atk2 = status_calc_watk(bl, sc, b_status->rhw.atk2); + status->rhw.atk2 = status_calc_watk(bl, sc, b_status->rhw.atk2, true); if(b_status->lhw.atk) { if (sd) { sd->state.lr_flag = 1; - status->lhw.atk = status_calc_watk(bl, sc, b_status->lhw.atk); + status->lhw.atk = status_calc_watk(bl, sc, b_status->lhw.atk, true); sd->state.lr_flag = 0; } else { - status->lhw.atk = status_calc_watk(bl, sc, b_status->lhw.atk); - status->lhw.atk2= status_calc_watk(bl, sc, b_status->lhw.atk2); + status->lhw.atk = status_calc_watk(bl, sc, b_status->lhw.atk, true); + status->lhw.atk2 = status_calc_watk(bl, sc, b_status->lhw.atk2, true); } } @@ -3598,13 +3621,13 @@ void status_calc_bl_main(struct block_list *bl, /*enum scb_flag*/int flag) && status->luk == b_status->luk #endif ) - status->hit = status_calc_hit(bl, sc, b_status->hit); + status->hit = status_calc_hit(bl, sc, b_status->hit, true); else status->hit = status_calc_hit(bl, sc, b_status->hit + (status->dex - b_status->dex) #ifdef RENEWAL + (status->luk/3 - b_status->luk/3) #endif - ); + , true); } if(flag&SCB_FLEE) { @@ -3613,18 +3636,18 @@ void status_calc_bl_main(struct block_list *bl, /*enum scb_flag*/int flag) && status->luk == b_status->luk #endif ) - status->flee = status_calc_flee(bl, sc, b_status->flee); + status->flee = status_calc_flee(bl, sc, b_status->flee, true); else status->flee = status_calc_flee(bl, sc, b_status->flee +(status->agi - b_status->agi) #ifdef RENEWAL + (status->luk/5 - b_status->luk/5) #endif - ); + , true); } if(flag&SCB_DEF) { - status->def = status_calc_def(bl, sc, b_status->def); + status->def = status_calc_def(bl, sc, b_status->def, true); if( bl->type&BL_HOM ) status->def += (status->vit/5 - b_status->vit/5); @@ -3636,7 +3659,7 @@ void status_calc_bl_main(struct block_list *bl, /*enum scb_flag*/int flag) && status->agi == b_status->agi #endif ) - status->def2 = status_calc_def2(bl, sc, b_status->def2); + status->def2 = status_calc_def2(bl, sc, b_status->def2, true); else status->def2 = status_calc_def2(bl, sc, b_status->def2 #ifdef RENEWAL @@ -3644,12 +3667,12 @@ void status_calc_bl_main(struct block_list *bl, /*enum scb_flag*/int flag) #else + (status->vit - b_status->vit) #endif - ); + , true); } if(flag&SCB_MDEF) { - status->mdef = status_calc_mdef(bl, sc, b_status->mdef); + status->mdef = status_calc_mdef(bl, sc, b_status->mdef, true); if( bl->type&BL_HOM ) status->mdef += (status->int_/5 - b_status->int_/5); @@ -3661,7 +3684,7 @@ void status_calc_bl_main(struct block_list *bl, /*enum scb_flag*/int flag) && status->dex == b_status->dex #endif ) - status->mdef2 = status_calc_mdef2(bl, sc, b_status->mdef2); + status->mdef2 = status_calc_mdef2(bl, sc, b_status->mdef2, true); else status->mdef2 = status_calc_mdef2(bl, sc, b_status->mdef2 +(status->int_ - b_status->int_) #ifdef RENEWAL @@ -3669,7 +3692,7 @@ void status_calc_bl_main(struct block_list *bl, /*enum scb_flag*/int flag) #else + ((status->vit - b_status->vit)>>1) #endif - ); + , true); } if(flag&SCB_SPEED) { @@ -3693,9 +3716,9 @@ void status_calc_bl_main(struct block_list *bl, /*enum scb_flag*/int flag) if(flag&SCB_CRI && b_status->cri) { if (status->luk == b_status->luk) - status->cri = status_calc_critical(bl, sc, b_status->cri); + status->cri = status_calc_critical(bl, sc, b_status->cri, true); else - status->cri = status_calc_critical(bl, sc, b_status->cri + 3*(status->luk - b_status->luk)); + status->cri = status_calc_critical(bl, sc, b_status->cri + 3*(status->luk - b_status->luk), true); /** * after status_calc_critical so the bonus is applied despite if you have or not a sc bugreport:5240 **/ @@ -3706,9 +3729,9 @@ void status_calc_bl_main(struct block_list *bl, /*enum scb_flag*/int flag) if(flag&SCB_FLEE2 && b_status->flee2) { if (status->luk == b_status->luk) - status->flee2 = status_calc_flee2(bl, sc, b_status->flee2); + status->flee2 = status_calc_flee2(bl, sc, b_status->flee2, true); else - status->flee2 = status_calc_flee2(bl, sc, b_status->flee2 +(status->luk - b_status->luk)); + status->flee2 = status_calc_flee2(bl, sc, b_status->flee2 +(status->luk - b_status->luk), true); } if(flag&SCB_ATK_ELE) { @@ -3784,52 +3807,8 @@ void status_calc_bl_main(struct block_list *bl, /*enum scb_flag*/int flag) } } - if(flag&SCB_MATK) { -#ifndef RENEWAL - status->matk_min = status_base_matk_min(status) + (sd?sd->bonus.ematk:0); - status->matk_max = status_base_matk_max(status) + (sd?sd->bonus.ematk:0); -#else - /** - * RE MATK Formula (from irowiki:http://irowiki.org/wiki/MATK) - * MATK = (sMATK + wMATK + eMATK) * Multiplicative Modifiers - **/ - status->matk_min = status->matk_max = status_base_matk(status, status_get_lv(bl)); - if( bl->type&BL_PC ){ - // Any +MATK you get from skills and cards, including cards in weapon, is added here. - if( sd->bonus.ematk > 0 ){ - status->matk_max += sd->bonus.ematk; - status->matk_min += sd->bonus.ematk; - } - status->matk_min = status_calc_ematk(bl, sc, status->matk_min); - status->matk_max = status_calc_ematk(bl, sc, status->matk_max); - //This is the only portion in MATK that varies depending on the weapon level and refinement rate. - if( status->rhw.matk > 0 ){ - int wMatk = status->rhw.matk; - int variance = wMatk * status->rhw.wlv / 10; - status->matk_min += wMatk - variance; - status->matk_max += wMatk + variance; - } - } -#endif - if (bl->type&BL_PC && sd->matk_rate != 100) { - status->matk_max = status->matk_max * sd->matk_rate/100; - status->matk_min = status->matk_min * sd->matk_rate/100; - } - - status->matk_min = status_calc_matk(bl, sc, status->matk_min); - status->matk_max = status_calc_matk(bl, sc, status->matk_max); - - if ((bl->type&BL_HOM && battle_config.hom_setting&0x20) //Hom Min Matk is always the same as Max Matk - || sc->data[SC_RECOGNIZEDSPELL]) - status->matk_min = status->matk_max; - -#ifdef RENEWAL - if( sd && sd->right_weapon.overrefine > 0){ - status->matk_min++; - status->matk_max += sd->right_weapon.overrefine - 1; - } -#endif - + if(flag&SCB_MATK) { + status_get_matk(bl, 0); } if(flag&SCB_ASPD) { @@ -3844,11 +3823,11 @@ void status_calc_bl_main(struct block_list *bl, /*enum scb_flag*/int flag) amotion = amotion*status->aspd_rate/1000; #else // aspd = baseaspd + floor(sqrt((agi^2/2) + (dex^2/5))/4 + (potskillbonus*agi/200)) - amotion -= (int)(sqrt( (pow(status->agi, 2) / 2) + (pow(status->dex, 2) / 5) ) / 4 + (status_calc_aspd(bl, sc, 1) * status->agi / 200)) * 10; + amotion -= (int)(sqrt( (pow(status->agi, 2) / 2) + (pow(status->dex, 2) / 5) ) / 4 + ((float)status_calc_aspd(bl, sc, 1) * status->agi / 200)) * 10; if( (status_calc_aspd(bl, sc, 2) + status->aspd_rate2) != 0 ) // RE ASPD percertage modifier - amotion -= ( amotion - ((sd->class_&JOBL_THIRD) ? battle_config.max_third_aspd : battle_config.max_aspd) ) - * (status_calc_aspd(bl, sc, 2) + status->aspd_rate2) / 100; + amotion -= (( amotion - ((sd->class_&JOBL_THIRD) ? battle_config.max_third_aspd : battle_config.max_aspd) ) + * (status_calc_aspd(bl, sc, 2) + status->aspd_rate2) / 10 + 5) / 10; if(status->aspd_rate != 1000) // absolute percentage modifier amotion = ( 200 - (200-amotion/10) * status->aspd_rate / 1000 ) * 10; @@ -4102,38 +4081,38 @@ static unsigned short status_calc_str(struct block_list *bl, struct status_chang str -= sc->data[SC_HARMONIZE]->val2; return (unsigned short)cap_value(str,0,USHRT_MAX); } - if(sc->data[SC_SPIRIT] && sc->data[SC_SPIRIT]->val2 == SL_HIGH && str < 50) + if(sc->data[SC_SOULLINK] && sc->data[SC_SOULLINK]->val2 == SL_HIGH && str < 50) return 50; if(sc->data[SC_INCALLSTATUS]) str += sc->data[SC_INCALLSTATUS]->val1; - if(sc->data[SC_INCSTR]) - str += sc->data[SC_INCSTR]->val1; - if(sc->data[SC_STRFOOD]) - str += sc->data[SC_STRFOOD]->val1; + if(sc->data[SC_CHASEWALK2]) + str += sc->data[SC_CHASEWALK2]->val1; + if(sc->data[SC_FOOD_STR]) + str += sc->data[SC_FOOD_STR]->val1; if(sc->data[SC_FOOD_STR_CASH]) str += sc->data[SC_FOOD_STR_CASH]->val1; - if(sc->data[SC_BATTLEORDERS]) + if(sc->data[SC_GDSKILL_BATTLEORDER]) str += 5; if(sc->data[SC_LEADERSHIP]) str += sc->data[SC_LEADERSHIP]->val1; - if(sc->data[SC_LOUD]) + if(sc->data[SC_SHOUT]) str += 4; if(sc->data[SC_TRUESIGHT]) str += 5; - if(sc->data[SC_SPURT]) + if(sc->data[SC_STRUP]) str += 10; - if(sc->data[SC_NEN]) - str += sc->data[SC_NEN]->val1; + if(sc->data[SC_NJ_NEN]) + str += sc->data[SC_NJ_NEN]->val1; if(sc->data[SC_BLESSING]){ if(sc->data[SC_BLESSING]->val2) str += sc->data[SC_BLESSING]->val2; else str >>= 1; } + if(sc->data[SC_MARIONETTE_MASTER]) + str -= ((sc->data[SC_MARIONETTE_MASTER]->val3)>>16)&0xFF; if(sc->data[SC_MARIONETTE]) - str -= ((sc->data[SC_MARIONETTE]->val3)>>16)&0xFF; - if(sc->data[SC_MARIONETTE2]) - str += ((sc->data[SC_MARIONETTE2]->val3)>>16)&0xFF; + str += ((sc->data[SC_MARIONETTE]->val3)>>16)&0xFF; if(sc->data[SC_GIANTGROWTH]) str += 30; if(sc->data[SC_SAVAGE_STEAK]) @@ -4144,6 +4123,8 @@ static unsigned short status_calc_str(struct block_list *bl, struct status_chang str -= sc->data[SC_STOMACHACHE]->val1; if(sc->data[SC_KYOUGAKU]) str -= sc->data[SC_KYOUGAKU]->val2; + if(sc->data[SC_FULL_THROTTLE]) + str += str * 20 / 100; return (unsigned short)cap_value(str,0,USHRT_MAX); } @@ -4157,36 +4138,36 @@ static unsigned short status_calc_agi(struct block_list *bl, struct status_chang agi -= sc->data[SC_HARMONIZE]->val2; return (unsigned short)cap_value(agi,0,USHRT_MAX); } - if(sc->data[SC_SPIRIT] && sc->data[SC_SPIRIT]->val2 == SL_HIGH && agi < 50) + if(sc->data[SC_SOULLINK] && sc->data[SC_SOULLINK]->val2 == SL_HIGH && agi < 50) return 50; - if(sc->data[SC_CONCENTRATE] && !sc->data[SC_QUAGMIRE]) - agi += (agi-sc->data[SC_CONCENTRATE]->val3)*sc->data[SC_CONCENTRATE]->val2/100; + if(sc->data[SC_CONCENTRATION] && !sc->data[SC_QUAGMIRE]) + agi += (agi-sc->data[SC_CONCENTRATION]->val3)*sc->data[SC_CONCENTRATION]->val2/100; if(sc->data[SC_INCALLSTATUS]) agi += sc->data[SC_INCALLSTATUS]->val1; if(sc->data[SC_INCAGI]) agi += sc->data[SC_INCAGI]->val1; - if(sc->data[SC_AGIFOOD]) - agi += sc->data[SC_AGIFOOD]->val1; + if(sc->data[SC_FOOD_AGI]) + agi += sc->data[SC_FOOD_AGI]->val1; if(sc->data[SC_FOOD_AGI_CASH]) agi += sc->data[SC_FOOD_AGI_CASH]->val1; if(sc->data[SC_SOULCOLD]) agi += sc->data[SC_SOULCOLD]->val1; if(sc->data[SC_TRUESIGHT]) agi += 5; - if(sc->data[SC_INCREASEAGI]) - agi += sc->data[SC_INCREASEAGI]->val2; - if(sc->data[SC_INCREASING]) + if(sc->data[SC_INC_AGI]) + agi += sc->data[SC_INC_AGI]->val2; + if(sc->data[SC_GS_ACCURACY]) agi += 4; // added based on skill updates [Reddozen] - if(sc->data[SC_DECREASEAGI]) - agi -= sc->data[SC_DECREASEAGI]->val2; + if(sc->data[SC_DEC_AGI]) + agi -= sc->data[SC_DEC_AGI]->val2; if(sc->data[SC_QUAGMIRE]) agi -= sc->data[SC_QUAGMIRE]->val2; - if(sc->data[SC_SUITON] && sc->data[SC_SUITON]->val3) - agi -= sc->data[SC_SUITON]->val2; + if(sc->data[SC_NJ_SUITON] && sc->data[SC_NJ_SUITON]->val3) + agi -= sc->data[SC_NJ_SUITON]->val2; + if(sc->data[SC_MARIONETTE_MASTER]) + agi -= ((sc->data[SC_MARIONETTE_MASTER]->val3)>>8)&0xFF; if(sc->data[SC_MARIONETTE]) - agi -= ((sc->data[SC_MARIONETTE]->val3)>>8)&0xFF; - if(sc->data[SC_MARIONETTE2]) - agi += ((sc->data[SC_MARIONETTE2]->val3)>>8)&0xFF; + agi += ((sc->data[SC_MARIONETTE]->val3)>>8)&0xFF; if(sc->data[SC_ADORAMUS]) agi -= sc->data[SC_ADORAMUS]->val2; if(sc->data[SC_DROCERA_HERB_STEAMED]) @@ -4198,6 +4179,11 @@ static unsigned short status_calc_agi(struct block_list *bl, struct status_chang if(sc->data[SC_KYOUGAKU]) agi -= sc->data[SC_KYOUGAKU]->val2; + if(sc->data[SC_MARSHOFABYSS]) + agi -= agi * sc->data[SC_MARSHOFABYSS]->val2 / 100; + if(sc->data[SC_FULL_THROTTLE]) + agi += agi * 20 / 100; + return (unsigned short)cap_value(agi,0,USHRT_MAX); } @@ -4210,26 +4196,26 @@ static unsigned short status_calc_vit(struct block_list *bl, struct status_chang vit -= sc->data[SC_HARMONIZE]->val2; return (unsigned short)cap_value(vit,0,USHRT_MAX); } - if(sc->data[SC_SPIRIT] && sc->data[SC_SPIRIT]->val2 == SL_HIGH && vit < 50) + if(sc->data[SC_SOULLINK] && sc->data[SC_SOULLINK]->val2 == SL_HIGH && vit < 50) return 50; if(sc->data[SC_INCALLSTATUS]) vit += sc->data[SC_INCALLSTATUS]->val1; if(sc->data[SC_INCVIT]) vit += sc->data[SC_INCVIT]->val1; - if(sc->data[SC_VITFOOD]) - vit += sc->data[SC_VITFOOD]->val1; + if(sc->data[SC_FOOD_VIT]) + vit += sc->data[SC_FOOD_VIT]->val1; if(sc->data[SC_FOOD_VIT_CASH]) vit += sc->data[SC_FOOD_VIT_CASH]->val1; - if(sc->data[SC_CHANGE]) - vit += sc->data[SC_CHANGE]->val2; + if(sc->data[SC_HLIF_CHANGE]) + vit += sc->data[SC_HLIF_CHANGE]->val2; if(sc->data[SC_GLORYWOUNDS]) vit += sc->data[SC_GLORYWOUNDS]->val1; if(sc->data[SC_TRUESIGHT]) vit += 5; + if(sc->data[SC_MARIONETTE_MASTER]) + vit -= sc->data[SC_MARIONETTE_MASTER]->val3&0xFF; if(sc->data[SC_MARIONETTE]) - vit -= sc->data[SC_MARIONETTE]->val3&0xFF; - if(sc->data[SC_MARIONETTE2]) - vit += sc->data[SC_MARIONETTE2]->val3&0xFF; + vit += sc->data[SC_MARIONETTE]->val3&0xFF; if(sc->data[SC_LAUDAAGNUS]) vit += 4 + sc->data[SC_LAUDAAGNUS]->val1; if(sc->data[SC_MINOR_BBQ]) @@ -4241,8 +4227,10 @@ static unsigned short status_calc_vit(struct block_list *bl, struct status_chang if(sc->data[SC_KYOUGAKU]) vit -= sc->data[SC_KYOUGAKU]->val2; - if(sc->data[SC_STRIPARMOR]) - vit -= vit * sc->data[SC_STRIPARMOR]->val2/100; + if(sc->data[SC_NOEQUIPARMOR]) + vit -= vit * sc->data[SC_NOEQUIPARMOR]->val2/100; + if(sc->data[SC_FULL_THROTTLE]) + vit += vit * 20 / 100; return (unsigned short)cap_value(vit,0,USHRT_MAX); } @@ -4256,19 +4244,19 @@ static unsigned short status_calc_int(struct block_list *bl, struct status_chang int_ -= sc->data[SC_HARMONIZE]->val2; return (unsigned short)cap_value(int_,0,USHRT_MAX); } - if(sc->data[SC_SPIRIT] && sc->data[SC_SPIRIT]->val2 == SL_HIGH && int_ < 50) + if(sc->data[SC_SOULLINK] && sc->data[SC_SOULLINK]->val2 == SL_HIGH && int_ < 50) return 50; if(sc->data[SC_INCALLSTATUS]) int_ += sc->data[SC_INCALLSTATUS]->val1; if(sc->data[SC_INCINT]) int_ += sc->data[SC_INCINT]->val1; - if(sc->data[SC_INTFOOD]) - int_ += sc->data[SC_INTFOOD]->val1; + if(sc->data[SC_FOOD_INT]) + int_ += sc->data[SC_FOOD_INT]->val1; if(sc->data[SC_FOOD_INT_CASH]) int_ += sc->data[SC_FOOD_INT_CASH]->val1; - if(sc->data[SC_CHANGE]) - int_ += sc->data[SC_CHANGE]->val3; - if(sc->data[SC_BATTLEORDERS]) + if(sc->data[SC_HLIF_CHANGE]) + int_ += sc->data[SC_HLIF_CHANGE]->val3; + if(sc->data[SC_GDSKILL_BATTLEORDER]) int_ += 5; if(sc->data[SC_TRUESIGHT]) int_ += 5; @@ -4278,12 +4266,12 @@ static unsigned short status_calc_int(struct block_list *bl, struct status_chang else int_ >>= 1; } - if(sc->data[SC_NEN]) - int_ += sc->data[SC_NEN]->val1; + if(sc->data[SC_NJ_NEN]) + int_ += sc->data[SC_NJ_NEN]->val1; + if(sc->data[SC_MARIONETTE_MASTER]) + int_ -= ((sc->data[SC_MARIONETTE_MASTER]->val4)>>16)&0xFF; if(sc->data[SC_MARIONETTE]) - int_ -= ((sc->data[SC_MARIONETTE]->val4)>>16)&0xFF; - if(sc->data[SC_MARIONETTE2]) - int_ += ((sc->data[SC_MARIONETTE2]->val4)>>16)&0xFF; + int_ += ((sc->data[SC_MARIONETTE]->val4)>>16)&0xFF; if(sc->data[SC_MANDRAGORA]) int_ -= 5 + 5 * sc->data[SC_MANDRAGORA]->val1; if(sc->data[SC_COCKTAIL_WARG_BLOOD]) @@ -4295,10 +4283,12 @@ static unsigned short status_calc_int(struct block_list *bl, struct status_chang if(sc->data[SC_KYOUGAKU]) int_ -= sc->data[SC_KYOUGAKU]->val2; - if(sc->data[SC_STRIPHELM]) - int_ -= int_ * sc->data[SC_STRIPHELM]->val2/100; - if(sc->data[SC__STRIPACCESSORY]) - int_ -= int_ * sc->data[SC__STRIPACCESSORY]->val2 / 100; + if(sc->data[SC_NOEQUIPHELM]) + int_ -= int_ * sc->data[SC_NOEQUIPHELM]->val2/100; + if(sc->data[SC__STRIPACCESSARY]) + int_ -= int_ * sc->data[SC__STRIPACCESSARY]->val2 / 100; + if(sc->data[SC_FULL_THROTTLE]) + int_ += int_ * 20 / 100; return (unsigned short)cap_value(int_,0,USHRT_MAX); } @@ -4312,19 +4302,19 @@ static unsigned short status_calc_dex(struct block_list *bl, struct status_chang dex -= sc->data[SC_HARMONIZE]->val2; return (unsigned short)cap_value(dex,0,USHRT_MAX); } - if(sc->data[SC_SPIRIT] && sc->data[SC_SPIRIT]->val2 == SL_HIGH && dex < 50) + if(sc->data[SC_SOULLINK] && sc->data[SC_SOULLINK]->val2 == SL_HIGH && dex < 50) return 50; - if(sc->data[SC_CONCENTRATE] && !sc->data[SC_QUAGMIRE]) - dex += (dex-sc->data[SC_CONCENTRATE]->val4)*sc->data[SC_CONCENTRATE]->val2/100; + if(sc->data[SC_CONCENTRATION] && !sc->data[SC_QUAGMIRE]) + dex += (dex-sc->data[SC_CONCENTRATION]->val4)*sc->data[SC_CONCENTRATION]->val2/100; if(sc->data[SC_INCALLSTATUS]) dex += sc->data[SC_INCALLSTATUS]->val1; if(sc->data[SC_INCDEX]) dex += sc->data[SC_INCDEX]->val1; - if(sc->data[SC_DEXFOOD]) - dex += sc->data[SC_DEXFOOD]->val1; + if(sc->data[SC_FOOD_DEX]) + dex += sc->data[SC_FOOD_DEX]->val1; if(sc->data[SC_FOOD_DEX_CASH]) dex += sc->data[SC_FOOD_DEX_CASH]->val1; - if(sc->data[SC_BATTLEORDERS]) + if(sc->data[SC_GDSKILL_BATTLEORDER]) dex += 5; if(sc->data[SC_HAWKEYES]) dex += sc->data[SC_HAWKEYES]->val1; @@ -4338,12 +4328,12 @@ static unsigned short status_calc_dex(struct block_list *bl, struct status_chang else dex >>= 1; } - if(sc->data[SC_INCREASING]) + if(sc->data[SC_GS_ACCURACY]) dex += 4; // added based on skill updates [Reddozen] + if(sc->data[SC_MARIONETTE_MASTER]) + dex -= ((sc->data[SC_MARIONETTE_MASTER]->val4)>>8)&0xFF; if(sc->data[SC_MARIONETTE]) - dex -= ((sc->data[SC_MARIONETTE]->val4)>>8)&0xFF; - if(sc->data[SC_MARIONETTE2]) - dex += ((sc->data[SC_MARIONETTE2]->val4)>>8)&0xFF; + dex += ((sc->data[SC_MARIONETTE]->val4)>>8)&0xFF; if(sc->data[SC_SIROMA_ICE_TEA]) dex += sc->data[SC_SIROMA_ICE_TEA]->val1; if(sc->data[SC_INSPIRATION]) @@ -4353,8 +4343,12 @@ static unsigned short status_calc_dex(struct block_list *bl, struct status_chang if(sc->data[SC_KYOUGAKU]) dex -= sc->data[SC_KYOUGAKU]->val2; - if(sc->data[SC__STRIPACCESSORY]) - dex -= dex * sc->data[SC__STRIPACCESSORY]->val2 / 100; + if(sc->data[SC_MARSHOFABYSS]) + dex -= dex * sc->data[SC_MARSHOFABYSS]->val2 / 100; + if(sc->data[SC__STRIPACCESSARY]) + dex -= dex * sc->data[SC__STRIPACCESSARY]->val2 / 100; + if(sc->data[SC_FULL_THROTTLE]) + dex += dex * 20 / 100; return (unsigned short)cap_value(dex,0,USHRT_MAX); } @@ -4370,24 +4364,24 @@ static unsigned short status_calc_luk(struct block_list *bl, struct status_chang } if(sc->data[SC_CURSE]) return 0; - if(sc->data[SC_SPIRIT] && sc->data[SC_SPIRIT]->val2 == SL_HIGH && luk < 50) + if(sc->data[SC_SOULLINK] && sc->data[SC_SOULLINK]->val2 == SL_HIGH && luk < 50) return 50; if(sc->data[SC_INCALLSTATUS]) luk += sc->data[SC_INCALLSTATUS]->val1; if(sc->data[SC_INCLUK]) luk += sc->data[SC_INCLUK]->val1; - if(sc->data[SC_LUKFOOD]) - luk += sc->data[SC_LUKFOOD]->val1; + if(sc->data[SC_FOOD_LUK]) + luk += sc->data[SC_FOOD_LUK]->val1; if(sc->data[SC_FOOD_LUK_CASH]) luk += sc->data[SC_FOOD_LUK_CASH]->val1; if(sc->data[SC_TRUESIGHT]) luk += 5; if(sc->data[SC_GLORIA]) luk += 30; + if(sc->data[SC_MARIONETTE_MASTER]) + luk -= sc->data[SC_MARIONETTE_MASTER]->val4&0xFF; if(sc->data[SC_MARIONETTE]) - luk -= sc->data[SC_MARIONETTE]->val4&0xFF; - if(sc->data[SC_MARIONETTE2]) - luk += sc->data[SC_MARIONETTE2]->val4&0xFF; + luk += sc->data[SC_MARIONETTE]->val4&0xFF; if(sc->data[SC_PUTTI_TAILS_NOODLES]) luk += sc->data[SC_PUTTI_TAILS_NOODLES]->val1; if(sc->data[SC_INSPIRATION]) @@ -4399,26 +4393,33 @@ static unsigned short status_calc_luk(struct block_list *bl, struct status_chang if(sc->data[SC_LAUDARAMUS]) luk += 4 + sc->data[SC_LAUDARAMUS]->val1; - if(sc->data[SC__STRIPACCESSORY]) - luk -= luk * sc->data[SC__STRIPACCESSORY]->val2 / 100; + if(sc->data[SC__STRIPACCESSARY]) + luk -= luk * sc->data[SC__STRIPACCESSARY]->val2 / 100; if(sc->data[SC_BANANA_BOMB]) luk -= luk * sc->data[SC_BANANA_BOMB]->val1 / 100; + if(sc->data[SC_FULL_THROTTLE]) + luk += luk * 20 / 100; return (unsigned short)cap_value(luk,0,USHRT_MAX); } -static unsigned short status_calc_batk(struct block_list *bl, struct status_change *sc, int batk) +static unsigned short status_calc_batk(struct block_list *bl, struct status_change *sc, int batk, bool viewable) { if(!sc || !sc->count) return cap_value(batk,0,USHRT_MAX); + + if( !viewable ){ + /* some statuses that are hidden in the status window */ + return (unsigned short)cap_value(batk,0,USHRT_MAX); + } - if(sc->data[SC_ATKPOTION]) - batk += sc->data[SC_ATKPOTION]->val1; + if(sc->data[SC_PLUSATTACKPOWER]) + batk += sc->data[SC_PLUSATTACKPOWER]->val1; if(sc->data[SC_BATKFOOD]) batk += sc->data[SC_BATKFOOD]->val1; - if(sc->data[SC_GATLINGFEVER]) - batk += sc->data[SC_GATLINGFEVER]->val3; - if(sc->data[SC_MADNESSCANCEL]) + if(sc->data[SC_GS_GATLINGFEVER]) + batk += sc->data[SC_GS_GATLINGFEVER]->val3; + if(sc->data[SC_GS_MADNESSCANCEL]) batk += 100; if(sc->data[SC_FIRE_INSIGNIA] && sc->data[SC_FIRE_INSIGNIA]->val1 == 2) batk += 50; @@ -4433,7 +4434,7 @@ static unsigned short status_calc_batk(struct block_list *bl, struct status_chan batk += sc->data[SC_FULL_SWING_K]->val1; if(sc->data[SC_ODINS_POWER]) batk += 70; - if(sc->data[SC_ASH] && (bl->type==BL_MOB)){ + if(sc->data[SC_VOLCANIC_ASH] && (bl->type==BL_MOB)){ if(status_get_element(bl) == ELE_WATER) //water type batk /= 2; } @@ -4446,42 +4447,53 @@ static unsigned short status_calc_batk(struct block_list *bl, struct status_chan batk += batk * sc->data[SC_INCATKRATE]->val1/100; if(sc->data[SC_PROVOKE]) batk += batk * sc->data[SC_PROVOKE]->val3/100; - if(sc->data[SC_CONCENTRATION]) - batk += batk * sc->data[SC_CONCENTRATION]->val2/100; +#ifndef RENEWAL + if(sc->data[SC_LKCONCENTRATION]) + batk += batk * sc->data[SC_LKCONCENTRATION]->val2/100; +#endif if(sc->data[SC_SKE]) batk += batk * 3; - if(sc->data[SC_BLOODLUST]) - batk += batk * sc->data[SC_BLOODLUST]->val2/100; + if(sc->data[SC_HAMI_BLOODLUST]) + batk += batk * sc->data[SC_HAMI_BLOODLUST]->val2/100; if(sc->data[SC_JOINTBEAT] && sc->data[SC_JOINTBEAT]->val2&BREAK_WAIST) batk -= batk * 25/100; if(sc->data[SC_CURSE]) batk -= batk * 25/100; + if( sc->data[SC_ZANGETSU] ) + batk += sc->data[SC_ZANGETSU]->val2; //Curse shouldn't effect on this? <- Curse OR Bleeding?? -// if(sc->data[SC_BLEEDING]) +// if(sc->data[SC_BLOODING]) // batk -= batk * 25/100; - if(sc->data[SC_FLEET]) - batk += batk * sc->data[SC_FLEET]->val3/100; + if(sc->data[SC_HLIF_FLEET]) + batk += batk * sc->data[SC_HLIF_FLEET]->val3/100; if(sc->data[SC__ENERVATION]) batk -= batk * sc->data[SC__ENERVATION]->val2 / 100; - if(sc->data[SC_RUSHWINDMILL]) - batk += batk * sc->data[SC_RUSHWINDMILL]->val2/100; - if(sc->data[SC_SATURDAYNIGHTFEVER]) - batk += 100 * sc->data[SC_SATURDAYNIGHTFEVER]->val1; + if(sc->data[SC_RUSH_WINDMILL]) + batk += batk * sc->data[SC_RUSH_WINDMILL]->val2/100; + if(sc->data[SC_SATURDAY_NIGHT_FEVER]) + batk += 100 * sc->data[SC_SATURDAY_NIGHT_FEVER]->val1; if(sc->data[SC_MELODYOFSINK]) batk -= batk * sc->data[SC_MELODYOFSINK]->val3/100; - if(sc->data[SC_BEYONDOFWARCRY]) - batk += batk * sc->data[SC_BEYONDOFWARCRY]->val3/100; - if( sc->data[SC_ZANGETSU] ) - batk += batk * sc->data[SC_ZANGETSU]->val2 / 100; + if(sc->data[SC_BEYOND_OF_WARCRY]) + batk += batk * sc->data[SC_BEYOND_OF_WARCRY]->val3/100; return (unsigned short)cap_value(batk,0,USHRT_MAX); } -static unsigned short status_calc_watk(struct block_list *bl, struct status_change *sc, int watk) +static unsigned short status_calc_watk(struct block_list *bl, struct status_change *sc, int watk, bool viewable) { if(!sc || !sc->count) return cap_value(watk,0,USHRT_MAX); + if( !viewable ){ + /* some statuses that are hidden in the status window */ + if(sc->data[SC_STRIKING]) + watk += sc->data[SC_STRIKING]->val2; + if(sc->data[SC_GENTLETOUCH_CHANGE] && sc->data[SC_GENTLETOUCH_CHANGE]->val2) + watk += sc->data[SC_GENTLETOUCH_CHANGE]->val2; + return (unsigned short)cap_value(watk,0,USHRT_MAX); + } + if(sc->data[SC_IMPOSITIO]) watk += sc->data[SC_IMPOSITIO]->val2; if(sc->data[SC_WATKFOOD]) @@ -4490,12 +4502,10 @@ static unsigned short status_calc_watk(struct block_list *bl, struct status_chan watk += sc->data[SC_DRUMBATTLE]->val2; if(sc->data[SC_VOLCANO]) watk += sc->data[SC_VOLCANO]->val2; - if(sc->data[SC_MERC_ATKUP]) - watk += sc->data[SC_MERC_ATKUP]->val2; + if(sc->data[SC_MER_ATK]) + watk += sc->data[SC_MER_ATK]->val2; if(sc->data[SC_FIGHTINGSPIRIT]) watk += sc->data[SC_FIGHTINGSPIRIT]->val1; - if(sc->data[SC_STRIKING]) - watk += sc->data[SC_STRIKING]->val2; if(sc->data[SC_SHIELDSPELL_DEF] && sc->data[SC_SHIELDSPELL_DEF]->val1 == 3) watk += sc->data[SC_SHIELDSPELL_DEF]->val2; if(sc->data[SC_INSPIRATION]) @@ -4522,23 +4532,28 @@ static unsigned short status_calc_watk(struct block_list *bl, struct status_chan watk += sc->data[SC_NIBELUNGEN]->val2; } } - +#ifndef RENEWAL + if(sc->data[SC_STRIKING]) + watk += sc->data[SC_STRIKING]->val2; + if(sc->data[SC_GENTLETOUCH_CHANGE] && sc->data[SC_GENTLETOUCH_CHANGE]->val2) + watk += sc->data[SC_GENTLETOUCH_CHANGE]->val2; + if(sc->data[SC_LKCONCENTRATION]) + watk += watk * sc->data[SC_LKCONCENTRATION]->val2/100; +#endif if(sc->data[SC_INCATKRATE]) watk += watk * sc->data[SC_INCATKRATE]->val1/100; if(sc->data[SC_PROVOKE]) watk += watk * sc->data[SC_PROVOKE]->val3/100; - if(sc->data[SC_CONCENTRATION]) - watk += watk * sc->data[SC_CONCENTRATION]->val2/100; if(sc->data[SC_SKE]) watk += watk * 3; if(sc->data[SC__ENERVATION]) watk -= watk * sc->data[SC__ENERVATION]->val2 / 100; - if(sc->data[SC_FLEET]) - watk += watk * sc->data[SC_FLEET]->val3/100; + if(sc->data[SC_HLIF_FLEET]) + watk += watk * sc->data[SC_HLIF_FLEET]->val3/100; if(sc->data[SC_CURSE]) watk -= watk * 25/100; - if(sc->data[SC_STRIPWEAPON]) - watk -= watk * sc->data[SC_STRIPWEAPON]->val2/100; + if(sc->data[SC_NOEQUIPWEAPON]) + watk -= watk * sc->data[SC_NOEQUIPWEAPON]->val2/100; if(sc->data[SC__ENERVATION]) watk -= watk * sc->data[SC__ENERVATION]->val2 / 100; if((sc->data[SC_FIRE_INSIGNIA] && sc->data[SC_FIRE_INSIGNIA]->val1 == 2) @@ -4551,10 +4566,6 @@ static unsigned short status_calc_watk(struct block_list *bl, struct status_chan watk += watk * sc->data[SC_TIDAL_WEAPON]->val2 / 100; if(sc->data[SC_ANGRIFFS_MODUS]) watk += watk * sc->data[SC_ANGRIFFS_MODUS]->val2/100; -#ifdef RENEWAL_EDP - if( sc->data[SC_EDP] ) - watk = watk * (100 + sc->data[SC_EDP]->val1 * 80) / 100; -#endif return (unsigned short)cap_value(watk,0,USHRT_MAX); } @@ -4564,8 +4575,8 @@ static unsigned short status_calc_ematk(struct block_list *bl, struct status_cha if (!sc || !sc->count) return cap_value(matk,0,USHRT_MAX); - if (sc->data[SC_MATKPOTION]) - matk += sc->data[SC_MATKPOTION]->val1; + if (sc->data[SC_PLUSMAGICPOWER]) + matk += sc->data[SC_PLUSMAGICPOWER]->val1; if (sc->data[SC_MATKFOOD]) matk += sc->data[SC_MATKFOOD]->val1; if(sc->data[SC_MANA_PLUS]) @@ -4581,18 +4592,24 @@ static unsigned short status_calc_ematk(struct block_list *bl, struct status_cha if(sc->data[SC_ODINS_POWER]) matk += 40 + 30 * sc->data[SC_ODINS_POWER]->val1; //70 lvl1, 100lvl2 if(sc->data[SC_IZAYOI]) - matk += 50 * sc->data[SC_IZAYOI]->val1; + matk += 25 * sc->data[SC_IZAYOI]->val1; return (unsigned short)cap_value(matk,0,USHRT_MAX); } #endif -static unsigned short status_calc_matk(struct block_list *bl, struct status_change *sc, int matk) +static unsigned short status_calc_matk(struct block_list *bl, struct status_change *sc, int matk, bool viewable) { if(!sc || !sc->count) return cap_value(matk,0,USHRT_MAX); + + if( !viewable ){ + /* some statuses that are hidden in the status window */ + return (unsigned short)cap_value(matk,0,USHRT_MAX); + } + #ifndef RENEWAL // take note fixed value first before % modifiers - if (sc->data[SC_MATKPOTION]) - matk += sc->data[SC_MATKPOTION]->val1; + if (sc->data[SC_PLUSMAGICPOWER]) + matk += sc->data[SC_PLUSMAGICPOWER]->val1; if (sc->data[SC_MATKFOOD]) matk += sc->data[SC_MATKFOOD]->val1; if (sc->data[SC_MANA_PLUS]) @@ -4608,33 +4625,38 @@ static unsigned short status_calc_matk(struct block_list *bl, struct status_chan if (sc->data[SC_ODINS_POWER]) matk += 40 + 30 * sc->data[SC_ODINS_POWER]->val1; //70 lvl1, 100lvl2 if (sc->data[SC_IZAYOI]) - matk += 50 * sc->data[SC_IZAYOI]->val1; + matk += 25 * sc->data[SC_IZAYOI]->val1; #endif + if( sc->data[SC_ZANGETSU] ) + matk += sc->data[SC_ZANGETSU]->val3; if (sc->data[SC_MAGICPOWER] && sc->data[SC_MAGICPOWER]->val4) matk += matk * sc->data[SC_MAGICPOWER]->val3/100; if (sc->data[SC_MINDBREAKER]) matk += matk * sc->data[SC_MINDBREAKER]->val2/100; if (sc->data[SC_INCMATKRATE]) matk += matk * sc->data[SC_INCMATKRATE]->val1/100; - if (sc->data[SC_MOONLITSERENADE]) - matk += matk * sc->data[SC_MOONLITSERENADE]->val2/100; + if (sc->data[SC_MOONLIT_SERENADE]) + matk += matk * sc->data[SC_MOONLIT_SERENADE]->val2/100; if (sc->data[SC_MELODYOFSINK]) matk += matk * sc->data[SC_MELODYOFSINK]->val3/100; - if (sc->data[SC_BEYONDOFWARCRY]) - matk -= matk * sc->data[SC_BEYONDOFWARCRY]->val3/100; - if( sc->data[SC_ZANGETSU] ) - matk += matk * sc->data[SC_ZANGETSU]->val2 / 100; + if (sc->data[SC_BEYOND_OF_WARCRY]) + matk -= matk * sc->data[SC_BEYOND_OF_WARCRY]->val3/100; return (unsigned short)cap_value(matk,0,USHRT_MAX); } -static signed short status_calc_critical(struct block_list *bl, struct status_change *sc, int critical) { +static signed short status_calc_critical(struct block_list *bl, struct status_change *sc, int critical, bool viewable) { if(!sc || !sc->count) return cap_value(critical,10,SHRT_MAX); - if (sc->data[SC_INCCRI]) - critical += sc->data[SC_INCCRI]->val2; + if( !viewable ){ + /* some statuses that are hidden in the status window */ + return (short)cap_value(critical,10,SHRT_MAX); + } + + if (sc->data[SC_CRITICALPERCENT]) + critical += sc->data[SC_CRITICALPERCENT]->val2; if (sc->data[SC_EXPLOSIONSPIRITS]) critical += sc->data[SC_EXPLOSIONSPIRITS]->val2; if (sc->data[SC_FORTUNE]) @@ -4658,30 +4680,35 @@ static signed short status_calc_critical(struct block_list *bl, struct status_ch return (short)cap_value(critical,10,SHRT_MAX); } -static signed short status_calc_hit(struct block_list *bl, struct status_change *sc, int hit) +static signed short status_calc_hit(struct block_list *bl, struct status_change *sc, int hit, bool viewable) { if(!sc || !sc->count) return cap_value(hit,1,SHRT_MAX); + if( !viewable ){ + /* some statuses that are hidden in the status window */ + return (short)cap_value(hit,1,SHRT_MAX); + } + if(sc->data[SC_INCHIT]) hit += sc->data[SC_INCHIT]->val1; - if(sc->data[SC_HITFOOD]) - hit += sc->data[SC_HITFOOD]->val1; + if(sc->data[SC_FOOD_BASICHIT]) + hit += sc->data[SC_FOOD_BASICHIT]->val1; if(sc->data[SC_TRUESIGHT]) hit += sc->data[SC_TRUESIGHT]->val3; if(sc->data[SC_HUMMING]) hit += sc->data[SC_HUMMING]->val2; - if(sc->data[SC_CONCENTRATION]) - hit += sc->data[SC_CONCENTRATION]->val3; + if(sc->data[SC_LKCONCENTRATION]) + hit += sc->data[SC_LKCONCENTRATION]->val3; if(sc->data[SC_INSPIRATION]) hit += 5 * sc->data[SC_INSPIRATION]->val1; - if(sc->data[SC_ADJUSTMENT]) + if(sc->data[SC_GS_ADJUSTMENT]) hit -= 30; - if(sc->data[SC_INCREASING]) + if(sc->data[SC_GS_ACCURACY]) hit += 20; // RockmanEXE; changed based on updated [Reddozen] - if(sc->data[SC_MERC_HITUP]) - hit += sc->data[SC_MERC_HITUP]->val2; + if(sc->data[SC_MER_HIT]) + hit += sc->data[SC_MER_HIT]->val2; if(sc->data[SC_INCHITRATE]) hit += hit * sc->data[SC_INCHITRATE]->val1/100; @@ -4691,13 +4718,13 @@ static signed short status_calc_hit(struct block_list *bl, struct status_change hit -= hit * sc->data[SC__GROOMY]->val3 / 100; if(sc->data[SC_FEAR]) hit -= hit * 20 / 100; - if (sc->data[SC_ASH]) + if (sc->data[SC_VOLCANIC_ASH]) hit /= 2; return (short)cap_value(hit,1,SHRT_MAX); } -static signed short status_calc_flee(struct block_list *bl, struct status_change *sc, int flee) +static signed short status_calc_flee(struct block_list *bl, struct status_change *sc, int flee, bool viewable) { if( bl->type == BL_PC ) { @@ -4710,10 +4737,15 @@ static signed short status_calc_flee(struct block_list *bl, struct status_change if(!sc || !sc->count) return cap_value(flee,1,SHRT_MAX); + if( !viewable ){ + /* some statuses that are hidden in the status window */ + return (short)cap_value(flee,1,SHRT_MAX); + } + if(sc->data[SC_INCFLEE]) flee += sc->data[SC_INCFLEE]->val1; - if(sc->data[SC_FLEEFOOD]) - flee += sc->data[SC_FLEEFOOD]->val1; + if(sc->data[SC_FOOD_BASICAVOIDANCE]) + flee += sc->data[SC_FOOD_BASICAVOIDANCE]->val1; if(sc->data[SC_WHISTLE]) flee += sc->data[SC_WHISTLE]->val2; if(sc->data[SC_WINDWALK]) @@ -4722,28 +4754,26 @@ static signed short status_calc_flee(struct block_list *bl, struct status_change flee += sc->data[SC_VIOLENTGALE]->val2; if(sc->data[SC_MOON_COMFORT]) //SG skill [Komurka] flee += sc->data[SC_MOON_COMFORT]->val2; - if(sc->data[SC_CLOSECONFINE]) + if(sc->data[SC_RG_CCONFINE_M]) flee += 10; if (sc->data[SC_ANGRIFFS_MODUS]) flee -= sc->data[SC_ANGRIFFS_MODUS]->val3; if (sc->data[SC_OVERED_BOOST]) flee = max(flee,sc->data[SC_OVERED_BOOST]->val2); - if(sc->data[SC_ADJUSTMENT]) + if(sc->data[SC_GS_ADJUSTMENT]) flee += 30; - if(sc->data[SC_SPEED]) - flee += 10 + sc->data[SC_SPEED]->val1 * 10; - if(sc->data[SC_GATLINGFEVER]) - flee -= sc->data[SC_GATLINGFEVER]->val4; + if(sc->data[SC_HLIF_SPEED]) + flee += 10 + sc->data[SC_HLIF_SPEED]->val1 * 10; + if(sc->data[SC_GS_GATLINGFEVER]) + flee -= sc->data[SC_GS_GATLINGFEVER]->val4; if(sc->data[SC_PARTYFLEE]) flee += sc->data[SC_PARTYFLEE]->val1 * 10; - if(sc->data[SC_MERC_FLEEUP]) - flee += sc->data[SC_MERC_FLEEUP]->val2; + if(sc->data[SC_MER_FLEE]) + flee += sc->data[SC_MER_FLEE]->val2; if( sc->data[SC_HALLUCINATIONWALK] ) flee += sc->data[SC_HALLUCINATIONWALK]->val2; if( sc->data[SC_WATER_BARRIER] ) flee -= sc->data[SC_WATER_BARRIER]->val3; - if( sc->data[SC_MARSHOFABYSS] ) - flee -= (9 * sc->data[SC_MARSHOFABYSS]->val3 / 10 + sc->data[SC_MARSHOFABYSS]->val2 / 10) * (bl->type == BL_MOB ? 2 : 1); #ifdef RENEWAL if( sc->data[SC_SPEARQUICKEN] ) flee += 2 * sc->data[SC_SPEARQUICKEN]->val1; @@ -4767,13 +4797,13 @@ static signed short status_calc_flee(struct block_list *bl, struct status_change flee -= flee * sc->data[SC__LAZINESS]->val3 / 100; if( sc->data[SC_GLOOMYDAY] ) flee -= flee * sc->data[SC_GLOOMYDAY]->val2 / 100; - if( sc->data[SC_SATURDAYNIGHTFEVER] ) - flee -= flee * (40 + 10 * sc->data[SC_SATURDAYNIGHTFEVER]->val1) / 100; + if( sc->data[SC_SATURDAY_NIGHT_FEVER] ) + flee -= flee * (40 + 10 * sc->data[SC_SATURDAY_NIGHT_FEVER]->val1) / 100; if( sc->data[SC_WIND_STEP_OPTION] ) flee += flee * sc->data[SC_WIND_STEP_OPTION]->val2 / 100; if( sc->data[SC_ZEPHYR] ) flee += flee * sc->data[SC_ZEPHYR]->val2 / 100; - if(sc->data[SC_ASH] && (bl->type==BL_MOB)){ //mob + if(sc->data[SC_VOLCANIC_ASH] && (bl->type==BL_MOB)){ //mob if(status_get_element(bl) == ELE_WATER) //water type flee /= 2; } @@ -4781,13 +4811,18 @@ static signed short status_calc_flee(struct block_list *bl, struct status_change return (short)cap_value(flee,1,SHRT_MAX); } -static signed short status_calc_flee2(struct block_list *bl, struct status_change *sc, int flee2) +static signed short status_calc_flee2(struct block_list *bl, struct status_change *sc, int flee2, bool viewable) { if(!sc || !sc->count) return cap_value(flee2,10,SHRT_MAX); - if(sc->data[SC_INCFLEE2]) - flee2 += sc->data[SC_INCFLEE2]->val2; + if( !viewable ){ + /* some statuses that are hidden in the status window */ + return (short)cap_value(flee2,10,SHRT_MAX); + } + + if(sc->data[SC_PLUSAVOIDVALUE]) + flee2 += sc->data[SC_PLUSAVOIDVALUE]->val2; if(sc->data[SC_WHISTLE]) flee2 += sc->data[SC_WHISTLE]->val3*10; if(sc->data[SC__UNLUCKY]) @@ -4795,11 +4830,20 @@ static signed short status_calc_flee2(struct block_list *bl, struct status_chang return (short)cap_value(flee2,10,SHRT_MAX); } -static defType status_calc_def(struct block_list *bl, struct status_change *sc, int def) { +defType status_calc_def(struct block_list *bl, struct status_change *sc, int def, bool viewable) { if(!sc || !sc->count) return (defType)cap_value(def,DEFTYPE_MIN,DEFTYPE_MAX); + if( !viewable ){ + /* some statuses that are hidden in the status window */ + if( sc && sc->data[SC_CAMOUFLAGE] ) + def -= def * 5 * (10-sc->data[SC_CAMOUFLAGE]->val4) / 100; + if( sc && sc->data[SC_GENTLETOUCH_REVITALIZE] && sc->data[SC_GENTLETOUCH_REVITALIZE]->val4 ) + def += 2 * sc->data[SC_GENTLETOUCH_REVITALIZE]->val4; + return (defType)cap_value(def,DEFTYPE_MIN,DEFTYPE_MAX); + } + if (sc->data[SC_BERSERK] || sc->data[SC__BLOODYLUST]) return 0; if(sc->data[SC_SKA]) @@ -4813,12 +4857,12 @@ static defType status_calc_def(struct block_list *bl, struct status_change *sc, return 90; #endif - if(sc->data[SC_ARMORCHANGE]) - def += sc->data[SC_ARMORCHANGE]->val2; + if(sc->data[SC_STONESKIN]) + def += sc->data[SC_STONESKIN]->val2; if(sc->data[SC_DRUMBATTLE]) def += sc->data[SC_DRUMBATTLE]->val3; - if(sc->data[SC_DEFENCE]) //[orn] - def += sc->data[SC_DEFENCE]->val2 ; + if(sc->data[SC_HAMI_DEFENCE]) //[orn] + def += sc->data[SC_HAMI_DEFENCE]->val2 ; if(sc->data[SC_INCDEFRATE]) def += def * sc->data[SC_INCDEFRATE]->val1/100; if(sc->data[SC_EARTH_INSIGNIA] && sc->data[SC_EARTH_INSIGNIA]->val1 == 2) @@ -4833,28 +4877,24 @@ static defType status_calc_def(struct block_list *bl, struct status_change *sc, def >>=1; if(sc->data[SC_FREEZE]) def >>=1; - if(sc->data[SC_SIGNUMCRUCIS]) - def -= def * sc->data[SC_SIGNUMCRUCIS]->val2/100; - if(sc->data[SC_CONCENTRATION]) - def -= def * sc->data[SC_CONCENTRATION]->val4/100; + if(sc->data[SC_CRUCIS]) + def -= def * sc->data[SC_CRUCIS]->val2/100; + if(sc->data[SC_LKCONCENTRATION]) + def -= def * sc->data[SC_LKCONCENTRATION]->val4/100; if(sc->data[SC_SKE]) def >>=1; if(sc->data[SC_PROVOKE] && bl->type != BL_PC) // Provoke doesn't alter player defense-> def -= def * sc->data[SC_PROVOKE]->val4/100; - if(sc->data[SC_STRIPSHIELD]) - def -= def * sc->data[SC_STRIPSHIELD]->val2/100; + if(sc->data[SC_NOEQUIPSHIELD]) + def -= def * sc->data[SC_NOEQUIPSHIELD]->val2/100; if (sc->data[SC_FLING]) def -= def * (sc->data[SC_FLING]->val2)/100; - if( sc->data[SC_FREEZING] ) - def -= def * 10 / 100; - if( sc->data[SC_MARSHOFABYSS] ) - def -= def * ( 6 + 6 * sc->data[SC_MARSHOFABYSS]->val3/10 + (bl->type == BL_MOB ? 5 : 3) * sc->data[SC_MARSHOFABYSS]->val2/36 ) / 100; if( sc->data[SC_ANALYZE] ) def -= def * ( 14 * sc->data[SC_ANALYZE]->val1 ) / 100; if( sc->data[SC_FORCEOFVANGUARD] ) def += def * 2 * sc->data[SC_FORCEOFVANGUARD]->val1 / 100; - if(sc->data[SC_SATURDAYNIGHTFEVER]) - def -= def * (10 + 10 * sc->data[SC_SATURDAYNIGHTFEVER]->val1) / 100; + if(sc->data[SC_SATURDAY_NIGHT_FEVER]) + def -= def * (10 + 10 * sc->data[SC_SATURDAY_NIGHT_FEVER]->val1) / 100; if(sc->data[SC_EARTHDRIVE]) def -= def * 25 / 100; if( sc->data[SC_ROCK_CRUSHER] ) @@ -4863,15 +4903,17 @@ static defType status_calc_def(struct block_list *bl, struct status_change *sc, def += def * sc->data[SC_POWER_OF_GAIA]->val2 / 100; if( sc->data[SC_PRESTIGE] ) def += def * sc->data[SC_PRESTIGE]->val1 / 100; - if(sc->data[SC_ASH] && (bl->type==BL_MOB)){ + if( sc->data[SC_FROSTMISTY] ) + def -= def * 10 / 100; + if(sc->data[SC_VOLCANIC_ASH] && (bl->type==BL_MOB)){ if(status_get_race(bl)==RC_PLANT) def /= 2; } - return (defType)cap_value(def,DEFTYPE_MIN,DEFTYPE_MAX);; + return (defType)cap_value(def,DEFTYPE_MIN,DEFTYPE_MAX); } -static signed short status_calc_def2(struct block_list *bl, struct status_change *sc, int def2) +signed short status_calc_def2(struct block_list *bl, struct status_change *sc, int def2, bool viewable) { if(!sc || !sc->count) #ifdef RENEWAL @@ -4880,6 +4922,21 @@ static signed short status_calc_def2(struct block_list *bl, struct status_change return (short)cap_value(def2,1,SHRT_MAX); #endif + if( !viewable ){ + /* some statuses that are hidden in the status window */ +#ifdef RENEWAL + if( sc && sc->data[SC_ASSUMPTIO] ) + def2 <<= 1; +#endif + if( sc && sc->data[SC_CAMOUFLAGE] ) + def2 -= def2 * 5 * (10-sc->data[SC_CAMOUFLAGE]->val4) / 100; +#ifdef RENEWAL + return (short)cap_value(def2,SHRT_MIN,SHRT_MAX); +#else + return (short)cap_value(def2,1,SHRT_MAX); +#endif + } + if (sc->data[SC_BERSERK] || sc->data[SC__BLOODYLUST]) return 0; if(sc->data[SC_ETERNALCHAOS]) @@ -4896,9 +4953,9 @@ static signed short status_calc_def2(struct block_list *bl, struct status_change def2 += status_get_vit(bl) / 2 * sc->data[SC_ANGELUS]->val2/100; #else def2 += def2 * sc->data[SC_ANGELUS]->val2/100; + if(sc->data[SC_LKCONCENTRATION]) + def2 -= def2 * sc->data[SC_LKCONCENTRATION]->val4/100; #endif - if(sc->data[SC_CONCENTRATION]) - def2 -= def2 * sc->data[SC_CONCENTRATION]->val4/100; if(sc->data[SC_POISON]) def2 -= def2 * 25/100; if(sc->data[SC_DPOISON]) @@ -4912,18 +4969,16 @@ static signed short status_calc_def2(struct block_list *bl, struct status_change + def2 * ( sc->data[SC_JOINTBEAT]->val2&BREAK_WAIST ? 25 : 0 ) / 100; if(sc->data[SC_FLING]) def2 -= def2 * (sc->data[SC_FLING]->val3)/100; - if( sc->data[SC_FREEZING] ) - def2 -= def2 * 3 / 10; if(sc->data[SC_ANALYZE]) def2 -= def2 * ( 14 * sc->data[SC_ANALYZE]->val1 ) / 100; if( sc->data[SC_ECHOSONG] ) def2 += def2 * sc->data[SC_ECHOSONG]->val2/100; - if(sc->data[SC_ASH] && (bl->type==BL_MOB)){ + if(sc->data[SC_VOLCANIC_ASH] && (bl->type==BL_MOB)){ if(status_get_race(bl)==RC_PLANT) def2 /= 2; } - if (sc->data[SC_PARALYSIS]) - def2 -= def2 * sc->data[SC_PARALYSIS]->val2 / 100; + if (sc->data[SC_NEEDLE_OF_PARALYZE]) + def2 -= def2 * sc->data[SC_NEEDLE_OF_PARALYZE]->val2 / 100; #ifdef RENEWAL return (short)cap_value(def2,SHRT_MIN,SHRT_MAX); @@ -4933,11 +4988,16 @@ static signed short status_calc_def2(struct block_list *bl, struct status_change } -static defType status_calc_mdef(struct block_list *bl, struct status_change *sc, int mdef) { +defType status_calc_mdef(struct block_list *bl, struct status_change *sc, int mdef, bool viewable) { if(!sc || !sc->count) return (defType)cap_value(mdef,DEFTYPE_MIN,DEFTYPE_MAX); + if( !viewable ){ + /* some statuses that are hidden in the status window */ + return (defType)cap_value(mdef,DEFTYPE_MIN,DEFTYPE_MAX); + } + if (sc->data[SC_BERSERK] || sc->data[SC__BLOODYLUST]) return 0; if(sc->data[SC_BARRIER]) @@ -4948,15 +5008,13 @@ static defType status_calc_mdef(struct block_list *bl, struct status_change *sc, return 90; #endif - if(sc->data[SC_ARMORCHANGE]) - mdef += sc->data[SC_ARMORCHANGE]->val3; + if(sc->data[SC_STONESKIN]) + mdef += sc->data[SC_STONESKIN]->val3; if(sc->data[SC_EARTH_INSIGNIA] && sc->data[SC_EARTH_INSIGNIA]->val1 == 3) mdef += 50; if(sc->data[SC_ENDURE])// It has been confirmed that eddga card grants 1 MDEF, not 0, not 10, but 1. mdef += (sc->data[SC_ENDURE]->val4 == 0) ? sc->data[SC_ENDURE]->val1 : 1; - if(sc->data[SC_CONCENTRATION]) - mdef += 1; //Skill info says it adds a fixed 1 Mdef point. - if(sc->data[SC_STONEHARDSKIN]) + if(sc->data[SC_STONEHARDSKIN])// Final MDEF increase divided by 10 since were using classic (pre-renewal) mechanics. [Rytech] mdef += sc->data[SC_STONEHARDSKIN]->val1; if(sc->data[SC_WATER_BARRIER]) mdef += sc->data[SC_WATER_BARRIER]->val2; @@ -4964,21 +5022,21 @@ static defType status_calc_mdef(struct block_list *bl, struct status_change *sc, mdef += 25*mdef/100; if(sc->data[SC_FREEZE]) mdef += 25*mdef/100; - if( sc->data[SC_MARSHOFABYSS] ) - mdef -= mdef * ( 6 + 6 * sc->data[SC_MARSHOFABYSS]->val3/10 + (bl->type == BL_MOB ? 5 : 3) * sc->data[SC_MARSHOFABYSS]->val2/36 ) / 100; if(sc->data[SC_ANALYZE]) mdef -= mdef * ( 14 * sc->data[SC_ANALYZE]->val1 ) / 100; - if(sc->data[SC_SYMPHONYOFLOVER]) - mdef += mdef * sc->data[SC_SYMPHONYOFLOVER]->val2 / 100; - if(sc->data[SC_GT_CHANGE] && sc->data[SC_GT_CHANGE]->val4) - mdef -= mdef * sc->data[SC_GT_CHANGE]->val4 / 100; + if(sc->data[SC_SYMPHONY_LOVE]) + mdef += mdef * sc->data[SC_SYMPHONY_LOVE]->val2 / 100; + if(sc->data[SC_GENTLETOUCH_CHANGE] && sc->data[SC_GENTLETOUCH_CHANGE]->val4) + mdef -= mdef * sc->data[SC_GENTLETOUCH_CHANGE]->val4 / 100; if (sc->data[SC_ODINS_POWER]) mdef -= 20 * sc->data[SC_ODINS_POWER]->val1; + if(sc->data[SC_BURNING]) + mdef -= mdef *25 / 100; return (defType)cap_value(mdef,DEFTYPE_MIN,DEFTYPE_MAX); } -static signed short status_calc_mdef2(struct block_list *bl, struct status_change *sc, int mdef2) +signed short status_calc_mdef2(struct block_list *bl, struct status_change *sc, int mdef2, bool viewable) { if(!sc || !sc->count) #ifdef RENEWAL @@ -4987,6 +5045,16 @@ static signed short status_calc_mdef2(struct block_list *bl, struct status_chang return (short)cap_value(mdef2,1,SHRT_MAX); #endif + if( !viewable ){ + /* some statuses that are hidden in the status window */ +#ifdef RENEWAL + if(sc && sc->data[SC_ASSUMPTIO]) + mdef2 <<= 1; + return (short)cap_value(mdef2,SHRT_MIN,SHRT_MAX); +#else + return (short)cap_value(mdef2,1,SHRT_MAX); +#endif + } if (sc->data[SC_BERSERK] || sc->data[SC__BLOODYLUST]) return 0; @@ -5063,9 +5131,9 @@ static unsigned short status_calc_speed(struct block_list *bl, struct status_cha val = max( val, 50 - 10 * sc->data[SC_LONGING]->val1 ); else if( sd && sc->data[SC_DANCING] ) - val = max( val, 500 - (40 + 10 * (sc->data[SC_SPIRIT] && sc->data[SC_SPIRIT]->val2 == SL_BARDDANCER)) * pc->checkskill(sd,(sd->status.sex?BA_MUSICALLESSON:DC_DANCINGLESSON)) ); + val = max( val, 500 - (40 + 10 * (sc->data[SC_SOULLINK] && sc->data[SC_SOULLINK]->val2 == SL_BARDDANCER)) * pc->checkskill(sd,(sd->status.sex?BA_MUSICALLESSON:DC_DANCINGLESSON)) ); - if( sc->data[SC_DECREASEAGI] ) + if( sc->data[SC_DEC_AGI] ) val = max( val, 25 ); if( sc->data[SC_QUAGMIRE] || sc->data[SC_HALLUCINATIONWALK_POSTDELAY] || (sc->data[SC_GLOOMYDAY] && sc->data[SC_GLOOMYDAY]->val4) ) val = max( val, 50 ); @@ -5085,16 +5153,14 @@ static unsigned short status_calc_speed(struct block_list *bl, struct status_cha val = max( val, 75 ); if( sc->data[SC_SLOWDOWN] ) // Slow Potion val = max( val, 100 ); - if( sc->data[SC_GATLINGFEVER] ) + if( sc->data[SC_GS_GATLINGFEVER] ) val = max( val, 100 ); - if( sc->data[SC_SUITON] ) - val = max( val, sc->data[SC_SUITON]->val3 ); + if( sc->data[SC_NJ_SUITON] ) + val = max( val, sc->data[SC_NJ_SUITON]->val3 ); if( sc->data[SC_SWOO] ) val = max( val, 300 ); - if( sc->data[SC_FREEZING] ) - val = max( val, 70 ); - if( sc->data[SC_MARSHOFABYSS] ) - val = max( val, 40 + 10 * sc->data[SC_MARSHOFABYSS]->val1 ); + if( sc->data[SC_FROSTMISTY] ) + val = max( val, 50 ); if( sc->data[SC_CAMOUFLAGE] && (sc->data[SC_CAMOUFLAGE]->val3&1) == 0 ) val = max( val, sc->data[SC_CAMOUFLAGE]->val1 < 3 ? 0 : 25 * (5 - sc->data[SC_CAMOUFLAGE]->val1) ); if( sc->data[SC__GROOMY] ) @@ -5109,6 +5175,9 @@ static unsigned short status_calc_speed(struct block_list *bl, struct status_cha val = max( val, sc->data[SC_POWER_OF_GAIA]->val2 ); if( sc->data[SC_MELON_BOMB] ) val = max( val, sc->data[SC_MELON_BOMB]->val1 ); + + if( sc->data[SC_MARSHOFABYSS] ) // It stacks to other statuses so always put this at the end. + val = max( 50, val + 10 * sc->data[SC_MARSHOFABYSS]->val1 ); if( sd && sd->bonus.speed_rate + sd->bonus.speed_add_rate > 0 ) // permanent item-based speedup val = max( val, sd->bonus.speed_rate + sd->bonus.speed_add_rate ); @@ -5121,9 +5190,9 @@ static unsigned short status_calc_speed(struct block_list *bl, struct status_cha { int val = 0; - if( sc->data[SC_SPEEDUP1] ) //FIXME: used both by NPC_AGIUP and Speed Potion script + if( sc->data[SC_MOVHASTE_INFINITY] ) //FIXME: used both by NPC_AGIUP and Speed Potion script val = max( val, 50 ); - if( sc->data[SC_INCREASEAGI] ) + if( sc->data[SC_INC_AGI] ) val = max( val, 25 ); if( sc->data[SC_WINDWALK] ) val = max( val, 2 * sc->data[SC_WINDWALK]->val1 ); @@ -5137,8 +5206,8 @@ static unsigned short status_calc_speed(struct block_list *bl, struct status_cha val = max( val, 25 ); if( sc->data[SC_RUN] ) val = max( val, 55 ); - if( sc->data[SC_AVOID] ) - val = max( val, 10 * sc->data[SC_AVOID]->val1 ); + if( sc->data[SC_HLIF_AVOID] ) + val = max( val, 10 * sc->data[SC_HLIF_AVOID]->val1 ); if( sc->data[SC_INVINCIBLE] && !sc->data[SC_INVINCIBLEOFF] ) val = max( val, 75 ); if( sc->data[SC_CLOAKINGEXCEED] ) @@ -5147,13 +5216,14 @@ static unsigned short status_calc_speed(struct block_list *bl, struct status_cha val = max( val, 10 ); if( sc->data[SC_GN_CARTBOOST] ) val = max( val, sc->data[SC_GN_CARTBOOST]->val2 ); - if( sc->data[SC_SWINGDANCE] ) - val = max( val, sc->data[SC_SWINGDANCE]->val2 ); + if( sc->data[SC_SWING] ) + val = max( val, sc->data[SC_SWING]->val2 ); if( sc->data[SC_WIND_STEP_OPTION] ) val = max( val, sc->data[SC_WIND_STEP_OPTION]->val2 ); - + if( sc->data[SC_FULL_THROTTLE] ) + val = max( val, 30); //FIXME: official items use a single bonus for this [ultramage] - if( sc->data[SC_SPEEDUP0] ) // temporary item-based speedup + if( sc->data[SC_MOVHASTE_HORSE] ) // temporary item-based speedup val = max( val, 25 ); if( sd && sd->bonus.speed_rate + sd->bonus.speed_add_rate < 0 ) // permanent item-based speedup val = max( val, -(sd->bonus.speed_rate + sd->bonus.speed_add_rate) ); @@ -5171,6 +5241,8 @@ static unsigned short status_calc_speed(struct block_list *bl, struct status_cha speed += speed * (50 - 5 * pc->checkskill(sd,MC_PUSHCART)) / 100; if( sc->data[SC_PARALYSE] ) speed += speed * 50 / 100; + if( sc->data[SC_REBOUND] ) + speed += max(speed, 100); if( speed_rate != 100 ) speed = speed * speed_rate / 100; if( sc->data[SC_STEELBODY] ) @@ -5179,6 +5251,7 @@ static unsigned short status_calc_speed(struct block_list *bl, struct status_cha speed = max(speed, 200); if( sc->data[SC_WALKSPEED] && sc->data[SC_WALKSPEED]->val1 > 0 ) // ChangeSpeed speed = speed * 100 / sc->data[SC_WALKSPEED]->val1; + } return (short)cap_value(speed,10,USHRT_MAX); @@ -5194,22 +5267,19 @@ static short status_calc_aspd(struct block_list *bl, struct status_change *sc, s if(!sc || !sc->count) return 0; - if(sc->data[i=SC_ASPDPOTION3] || - sc->data[i=SC_ASPDPOTION2] || - sc->data[i=SC_ASPDPOTION1] || - sc->data[i=SC_ASPDPOTION0]) + if(sc->data[i=SC_ATTHASTE_INFINITY] || + sc->data[i=SC_ATTHASTE_POTION3] || + sc->data[i=SC_ATTHASTE_POTION2] || + sc->data[i=SC_ATTHASTE_POTION1]) pots += sc->data[i]->val1; if( !sc->data[SC_QUAGMIRE] ){ - if(sc->data[SC_STAR_COMFORT]) - skills1 = 5; // needs more info - if(sc->data[SC_TWOHANDQUICKEN] && skills1 < 7) skills1 = 7; - if(sc->data[SC_ONEHAND] && skills1 < 7) skills1 = 7; + if(sc->data[SC_ONEHANDQUICKEN] && skills1 < 7) skills1 = 7; - if(sc->data[SC_MERC_QUICKEN] && skills1 < 7) // needs more info + if(sc->data[SC_MER_QUICKEN] && skills1 < 7) // needs more info skills1 = 7; if(sc->data[SC_ADRENALINE2] && skills1 < 6) @@ -5221,48 +5291,25 @@ static short status_calc_aspd(struct block_list *bl, struct status_change *sc, s if(sc->data[SC_SPEARQUICKEN] && skills1 < 7) skills1 = 7; - if(sc->data[SC_GATLINGFEVER] && skills1 < 9) // needs more info - skills1 = 9; - - if(sc->data[SC_FLEET] && skills1 < 5) + if(sc->data[SC_HLIF_FLEET] && skills1 < 5) skills1 = 5; - - if(sc->data[SC_ASSNCROS] && - skills1 < 5+1*sc->data[SC_ASSNCROS]->val1) // needs more info - { - if (bl->type!=BL_PC) - skills1 = 4+1*sc->data[SC_ASSNCROS]->val1; - else - switch(((TBL_PC*)bl)->status.weapon) - { - case W_BOW: - case W_REVOLVER: - case W_RIFLE: - case W_GATLING: - case W_SHOTGUN: - case W_GRENADE: - break; - default: - skills1 = 5+1*sc->data[SC_ASSNCROS]->val1; - } - } } if((sc->data[SC_BERSERK] || sc->data[SC__BLOODYLUST]) && skills1 < 15) skills1 = 15; - else if(sc->data[SC_MADNESSCANCEL] && skills1 < 15) // needs more info - skills1 = 15; + else if(sc->data[SC_GS_MADNESSCANCEL] && skills1 < 20) + skills1 = 20; if(sc->data[SC_DONTFORGETME]) - skills2 -= sc->data[SC_DONTFORGETME]->val2; // needs more info + skills2 -= sc->data[SC_DONTFORGETME]->val2; if(sc->data[SC_LONGING]) - skills2 -= sc->data[SC_LONGING]->val2; // needs more info + skills2 -= sc->data[SC_LONGING]->val2; if(sc->data[SC_STEELBODY]) skills2 -= 25; if(sc->data[SC_SKA]) skills2 -= 25; if(sc->data[SC_DEFENDER]) - skills2 -= sc->data[SC_DEFENDER]->val4; // needs more info + skills2 -= sc->data[SC_DEFENDER]->val4 / 10; if(sc->data[SC_GOSPEL] && sc->data[SC_GOSPEL]->val4 == BCT_ENEMY) // needs more info skills2 -= 25; if(sc->data[SC_GRAVITATION]) @@ -5273,8 +5320,8 @@ static short status_calc_aspd(struct block_list *bl, struct status_change *sc, s if( sc->data[SC_JOINTBEAT]->val2&BREAK_KNEE ) skills2 -= 10; } - if( sc->data[SC_FREEZING] ) - skills2 -= 30; + if( sc->data[SC_FROSTMISTY] ) + skills2 -= 15; if( sc->data[SC_HALLUCINATIONWALK_POSTDELAY] ) skills2 -= 50; if( sc->data[SC_PARALYSE] ) @@ -5285,25 +5332,46 @@ static short status_calc_aspd(struct block_list *bl, struct status_change *sc, s skills2 -= sc->data[SC__INVISIBILITY]->val2 ; if( sc->data[SC__GROOMY] ) skills2 -= sc->data[SC__GROOMY]->val2; - if( sc->data[SC_SWINGDANCE] ) - skills2 += sc->data[SC_SWINGDANCE]->val2; - if( sc->data[SC_DANCEWITHWUG] ) - skills2 += sc->data[SC_DANCEWITHWUG]->val3; if( sc->data[SC_GLOOMYDAY] ) skills2 -= sc->data[SC_GLOOMYDAY]->val3; if( sc->data[SC_EARTHDRIVE] ) skills2 -= 25; - if( sc->data[SC_GT_CHANGE] ) - skills2 += sc->data[SC_GT_CHANGE]->val3; if( sc->data[SC_MELON_BOMB] ) skills2 -= sc->data[SC_MELON_BOMB]->val1; + + if( sc->data[SC_SWING] ) + skills2 += sc->data[SC_SWING]->val2; + if( sc->data[SC_DANCE_WITH_WUG] ) + skills2 += sc->data[SC_DANCE_WITH_WUG]->val3; + if( sc->data[SC_GENTLETOUCH_CHANGE] ) + skills2 += sc->data[SC_GENTLETOUCH_CHANGE]->val3; if( sc->data[SC_BOOST500] ) skills2 += sc->data[SC_BOOST500]->val1; if( sc->data[SC_EXTRACT_SALAMINE_JUICE] ) skills2 += sc->data[SC_EXTRACT_SALAMINE_JUICE]->val1; if( sc->data[SC_INCASPDRATE] ) skills2 += sc->data[SC_INCASPDRATE]->val1; - + if( sc->data[SC_GS_GATLINGFEVER] ) + skills2 += sc->data[SC_GS_GATLINGFEVER]->val1; + if( sc->data[SC_STAR_COMFORT] ) + skills2 += 3 * sc->data[SC_STAR_COMFORT]->val1; + if( sc->data[SC_ASSNCROS] && !skills1){ + if (bl->type!=BL_PC) + skills2 += sc->data[SC_ASSNCROS]->val2; + else + switch(((TBL_PC*)bl)->status.weapon) + { + case W_BOW: + case W_REVOLVER: + case W_RIFLE: + case W_GATLING: + case W_SHOTGUN: + case W_GRENADE: + break; + default: + skills2 += sc->data[SC_ASSNCROS]->val2; + } + } return ( flag&1? (skills1 + pots) : skills2 ); } #endif @@ -5344,13 +5412,13 @@ static short status_calc_aspd_rate(struct block_list *bl, struct status_change * max < sc->data[SC_TWOHANDQUICKEN]->val2) max = sc->data[SC_TWOHANDQUICKEN]->val2; - if(sc->data[SC_ONEHAND] && - max < sc->data[SC_ONEHAND]->val2) - max = sc->data[SC_ONEHAND]->val2; + if(sc->data[SC_ONEHANDQUICKEN] && + max < sc->data[SC_ONEHANDQUICKEN]->val2) + max = sc->data[SC_ONEHANDQUICKEN]->val2; - if(sc->data[SC_MERC_QUICKEN] && - max < sc->data[SC_MERC_QUICKEN]->val2) - max = sc->data[SC_MERC_QUICKEN]->val2; + if(sc->data[SC_MER_QUICKEN] && + max < sc->data[SC_MER_QUICKEN]->val2) + max = sc->data[SC_MER_QUICKEN]->val2; if(sc->data[SC_ADRENALINE2] && max < sc->data[SC_ADRENALINE2]->val3) @@ -5364,13 +5432,13 @@ static short status_calc_aspd_rate(struct block_list *bl, struct status_change * max < sc->data[SC_SPEARQUICKEN]->val2) max = sc->data[SC_SPEARQUICKEN]->val2; - if(sc->data[SC_GATLINGFEVER] && - max < sc->data[SC_GATLINGFEVER]->val2) - max = sc->data[SC_GATLINGFEVER]->val2; + if(sc->data[SC_GS_GATLINGFEVER] && + max < sc->data[SC_GS_GATLINGFEVER]->val2) + max = sc->data[SC_GS_GATLINGFEVER]->val2; - if(sc->data[SC_FLEET] && - max < sc->data[SC_FLEET]->val2) - max = sc->data[SC_FLEET]->val2; + if(sc->data[SC_HLIF_FLEET] && + max < sc->data[SC_HLIF_FLEET]->val2) + max = sc->data[SC_HLIF_FLEET]->val2; if(sc->data[SC_ASSNCROS] && max < sc->data[SC_ASSNCROS]->val2) @@ -5395,14 +5463,14 @@ static short status_calc_aspd_rate(struct block_list *bl, struct status_change * if((sc->data[SC_BERSERK] || sc->data[SC__BLOODYLUST])) aspd_rate -= 300; - else if(sc->data[SC_MADNESSCANCEL]) + else if(sc->data[SC_GS_MADNESSCANCEL]) aspd_rate -= 200; } - if( sc->data[i=SC_ASPDPOTION3] || - sc->data[i=SC_ASPDPOTION2] || - sc->data[i=SC_ASPDPOTION1] || - sc->data[i=SC_ASPDPOTION0] ) + if( sc->data[i=SC_ATTHASTE_INFINITY] || + sc->data[i=SC_ATTHASTE_POTION3] || + sc->data[i=SC_ATTHASTE_POTION2] || + sc->data[i=SC_ATTHASTE_POTION1] ) aspd_rate -= sc->data[i]->val2; if(sc->data[SC_DONTFORGETME]) @@ -5425,8 +5493,8 @@ static short status_calc_aspd_rate(struct block_list *bl, struct status_change * if( sc->data[SC_JOINTBEAT]->val2&BREAK_KNEE ) aspd_rate += 100; } - if( sc->data[SC_FREEZING] ) - aspd_rate += 300; + if( sc->data[SC_FROSTMISTY] ) + aspd_rate += 150; if( sc->data[SC_HALLUCINATIONWALK_POSTDELAY] ) aspd_rate += 500; if( sc->data[SC_FIGHTINGSPIRIT] && sc->data[SC_FIGHTINGSPIRIT]->val2 ) @@ -5439,16 +5507,16 @@ static short status_calc_aspd_rate(struct block_list *bl, struct status_change * aspd_rate += sc->data[SC__INVISIBILITY]->val2 * 10 ; if( sc->data[SC__GROOMY] ) aspd_rate += sc->data[SC__GROOMY]->val2 * 10; - if( sc->data[SC_SWINGDANCE] ) - aspd_rate -= sc->data[SC_SWINGDANCE]->val2 * 10; - if( sc->data[SC_DANCEWITHWUG] ) - aspd_rate -= sc->data[SC_DANCEWITHWUG]->val3 * 10; + if( sc->data[SC_SWING] ) + aspd_rate -= sc->data[SC_SWING]->val2 * 10; + if( sc->data[SC_DANCE_WITH_WUG] ) + aspd_rate -= sc->data[SC_DANCE_WITH_WUG]->val3 * 10; if( sc->data[SC_GLOOMYDAY] ) aspd_rate += sc->data[SC_GLOOMYDAY]->val3 * 10; if( sc->data[SC_EARTHDRIVE] ) aspd_rate += 250; - if( sc->data[SC_GT_CHANGE] ) - aspd_rate -= sc->data[SC_GT_CHANGE]->val3 * 10; + if( sc->data[SC_GENTLETOUCH_CHANGE] ) + aspd_rate -= sc->data[SC_GENTLETOUCH_CHANGE]->val3 * 10; if( sc->data[SC_MELON_BOMB] ) aspd_rate += sc->data[SC_MELON_BOMB]->val1 * 10; if( sc->data[SC_BOOST500] ) @@ -5474,8 +5542,6 @@ static unsigned short status_calc_dmotion(struct block_list *bl, struct status_c **/ if( sc->data[SC_ENDURE] || ( bl->type == BL_MOB && (((TBL_MOB*)bl)->status.mode&MD_BOSS) ) ) return 0; - if( sc->data[SC_CONCENTRATION] ) - return 0; if( sc->data[SC_RUN] || sc->data[SC_WUGDASH] ) return 0; @@ -5497,7 +5563,7 @@ static unsigned int status_calc_maxhp(struct block_list *bl, struct status_chang maxhp += maxhp * sc->data[SC_DELUGE]->val2/100; if (sc->data[SC_BERSERK] || sc->data[SC__BLOODYLUST]) maxhp += maxhp * 2; - if(sc->data[SC_MARIONETTE]) + if(sc->data[SC_MARIONETTE_MASTER]) maxhp -= 1000; if(sc->data[SC_SOLID_SKIN_OPTION]) maxhp += 2000;// Fix amount. @@ -5506,8 +5572,8 @@ static unsigned int status_calc_maxhp(struct block_list *bl, struct status_chang if(sc->data[SC_EARTH_INSIGNIA] && sc->data[SC_EARTH_INSIGNIA]->val1 == 2) maxhp += 500; - if(sc->data[SC_MERC_HPUP]) - maxhp += maxhp * sc->data[SC_MERC_HPUP]->val2/100; + if(sc->data[SC_MER_HP]) + maxhp += maxhp * sc->data[SC_MER_HP]->val2/100; if(sc->data[SC_EPICLESIS]) maxhp += maxhp * 5 * sc->data[SC_EPICLESIS]->val1 / 100; @@ -5515,18 +5581,18 @@ static unsigned int status_calc_maxhp(struct block_list *bl, struct status_chang maxhp -= maxhp * 15 / 100; if(sc->data[SC__WEAKNESS]) maxhp -= maxhp * sc->data[SC__WEAKNESS]->val2 / 100; - if(sc->data[SC_LERADSDEW]) - maxhp += maxhp * sc->data[SC_LERADSDEW]->val3 / 100; + if(sc->data[SC_LERADS_DEW]) + maxhp += maxhp * sc->data[SC_LERADS_DEW]->val3 / 100; if(sc->data[SC_FORCEOFVANGUARD]) maxhp += maxhp * 3 * sc->data[SC_FORCEOFVANGUARD]->val1 / 100; if(sc->data[SC_INSPIRATION]) //Custom value. maxhp += maxhp * 3 * sc->data[SC_INSPIRATION]->val1 / 100; if(sc->data[SC_RAISINGDRAGON]) maxhp += maxhp * (2 + sc->data[SC_RAISINGDRAGON]->val1) / 100; - if(sc->data[SC_GT_CHANGE]) // Max HP decrease: [Skill Level x 4] % - maxhp -= maxhp * (4 * sc->data[SC_GT_CHANGE]->val1) / 100; - if(sc->data[SC_GT_REVITALIZE])// Max HP increase: [Skill Level x 2] % - maxhp += maxhp * (2 * sc->data[SC_GT_REVITALIZE]->val1) / 100; + if(sc->data[SC_GENTLETOUCH_CHANGE]) // Max HP decrease: [Skill Level x 4] % + maxhp -= maxhp * (4 * sc->data[SC_GENTLETOUCH_CHANGE]->val1) / 100; + if(sc->data[SC_GENTLETOUCH_REVITALIZE])// Max HP increase: [Skill Level x 2] % + maxhp += maxhp * (2 * sc->data[SC_GENTLETOUCH_REVITALIZE]->val1) / 100; if(sc->data[SC_MUSTLE_M]) maxhp += maxhp * sc->data[SC_MUSTLE_M]->val1/100; if(sc->data[SC_MYSTERIOUS_POWDER]) @@ -5537,6 +5603,8 @@ static unsigned int status_calc_maxhp(struct block_list *bl, struct status_chang maxhp += maxhp * 5 * sc->data[SC_ANGRIFFS_MODUS]->val1 /100; if (sc->data[SC_GOLDENE_FERSE]) maxhp += maxhp * sc->data[SC_GOLDENE_FERSE]->val2 / 100; + if(sc->data[SC_FRIGG_SONG]) + maxhp += maxhp * sc->data[SC_FRIGG_SONG]->val2 / 100; return (unsigned int)cap_value(maxhp,1,UINT_MAX); } @@ -5550,10 +5618,10 @@ static unsigned int status_calc_maxsp(struct block_list *bl, struct status_chang maxsp += maxsp * sc->data[SC_INCMSPRATE]->val1/100; if(sc->data[SC_INCMSP]) maxsp += (sc->data[SC_INCMSP]->val1); - if(sc->data[SC_SERVICE4U]) - maxsp += maxsp * sc->data[SC_SERVICE4U]->val2/100; - if(sc->data[SC_MERC_SPUP]) - maxsp += maxsp * sc->data[SC_MERC_SPUP]->val2/100; + if(sc->data[SC_SERVICEFORYOU]) + maxsp += maxsp * sc->data[SC_SERVICEFORYOU]->val2/100; + if(sc->data[SC_MER_SP]) + maxsp += maxsp * sc->data[SC_MER_SP]->val2/100; if(sc->data[SC_RAISINGDRAGON]) maxsp += maxsp * (2 + sc->data[SC_RAISINGDRAGON]->val1) / 100; if(sc->data[SC_LIFE_FORCE_F]) @@ -5575,10 +5643,10 @@ static unsigned char status_calc_element(struct block_list *bl, struct status_ch return ELE_EARTH; if(sc->data[SC_BENEDICTIO]) return ELE_HOLY; - if(sc->data[SC_CHANGEUNDEAD]) + if(sc->data[SC_PROPERTYUNDEAD]) return ELE_UNDEAD; - if(sc->data[SC_ELEMENTALCHANGE]) - return sc->data[SC_ELEMENTALCHANGE]->val2; + if(sc->data[SC_ARMOR_PROPERTY]) + return sc->data[SC_ARMOR_PROPERTY]->val2; if(sc->data[SC_SHAPESHIFT]) return sc->data[SC_SHAPESHIFT]->val2; @@ -5596,10 +5664,10 @@ static unsigned char status_calc_element_lv(struct block_list *bl, struct status return 1; if(sc->data[SC_BENEDICTIO]) return 1; - if(sc->data[SC_CHANGEUNDEAD]) + if(sc->data[SC_PROPERTYUNDEAD]) return 1; - if(sc->data[SC_ELEMENTALCHANGE]) - return sc->data[SC_ELEMENTALCHANGE]->val1; + if(sc->data[SC_ARMOR_PROPERTY]) + return sc->data[SC_ARMOR_PROPERTY]->val1; if(sc->data[SC_SHAPESHIFT]) return 1; if(sc->data[SC__INVISIBILITY]) @@ -5615,25 +5683,25 @@ unsigned char status_calc_attack_element(struct block_list *bl, struct status_ch return element; if(sc->data[SC_ENCHANTARMS]) return sc->data[SC_ENCHANTARMS]->val2; - if(sc->data[SC_WATERWEAPON] + if(sc->data[SC_PROPERTYWATER] || (sc->data[SC_WATER_INSIGNIA] && sc->data[SC_WATER_INSIGNIA]->val1 == 2) ) return ELE_WATER; - if(sc->data[SC_EARTHWEAPON] + if(sc->data[SC_PROPERTYGROUND] || (sc->data[SC_EARTH_INSIGNIA] && sc->data[SC_EARTH_INSIGNIA]->val1 == 2) ) return ELE_EARTH; - if(sc->data[SC_FIREWEAPON] + if(sc->data[SC_PROPERTYFIRE] || (sc->data[SC_FIRE_INSIGNIA] && sc->data[SC_FIRE_INSIGNIA]->val1 == 2) ) return ELE_FIRE; - if(sc->data[SC_WINDWEAPON] + if(sc->data[SC_PROPERTYWIND] || (sc->data[SC_WIND_INSIGNIA] && sc->data[SC_WIND_INSIGNIA]->val1 == 2) ) return ELE_WIND; - if(sc->data[SC_ENCPOISON]) + if(sc->data[SC_ENCHANTPOISON]) return ELE_POISON; if(sc->data[SC_ASPERSIO]) return ELE_HOLY; - if(sc->data[SC_SHADOWWEAPON]) + if(sc->data[SC_PROPERTYDARK]) return ELE_DARK; - if(sc->data[SC_GHOSTWEAPON] || sc->data[SC__INVISIBILITY]) + if(sc->data[SC_PROPERTYTELEKINESIS] || sc->data[SC__INVISIBILITY]) return ELE_GHOST; if(sc->data[SC_TIDAL_WEAPON_OPTION] || sc->data[SC_TIDAL_WEAPON] ) return ELE_WATER; @@ -6119,14 +6187,14 @@ int status_get_sc_def(struct block_list *bl, enum sc_type type, int rate, int ti //Status that are blocked by Golden Thief Bug card or Wand of Hermod if (status_isimmune(bl)) switch (type) { - case SC_DECREASEAGI: + case SC_DEC_AGI: case SC_SILENCE: case SC_COMA: - case SC_INCREASEAGI: + case SC_INC_AGI: case SC_BLESSING: case SC_SLOWPOISON: case SC_IMPOSITIO: - case SC_AETERNA: + case SC_LEXAETERNA: case SC_SUFFRAGIUM: case SC_BENEDICTIO: case SC_PROVIDENCE: @@ -6137,11 +6205,11 @@ int status_get_sc_def(struct block_list *bl, enum sc_type type, int rate, int ti case SC_GLORIA: case SC_WINDWALK: case SC_MAGICROD: - case SC_HALLUCINATION: + case SC_ILLUSION: case SC_STONE: case SC_QUAGMIRE: - case SC_SUITON: - case SC_SWINGDANCE: + case SC_NJ_SUITON: + case SC_SWING: case SC__ENERVATION: case SC__GROOMY: case SC__IGNORANCE: @@ -6164,7 +6232,7 @@ int status_get_sc_def(struct block_list *bl, enum sc_type type, int rate, int ti return tick; case SC_DPOISON: case SC_SILENCE: - case SC_BLEEDING: + case SC_BLOODING: sc_def = status->vit*100; sc_def2 = status->luk*10; break; @@ -6172,11 +6240,11 @@ int status_get_sc_def(struct block_list *bl, enum sc_type type, int rate, int ti sc_def = status->int_*100; sc_def2 = status->luk*10; break; - case SC_DEEPSLEEP: + case SC_DEEP_SLEEP: sc_def = status->int_*50; tick_def = status->int_*10 + status_get_lv(bl) * 65 / 10; //Seems to be -1 sec every 10 int and -5% chance every 10 int. break; - case SC_DECREASEAGI: + case SC_DEC_AGI: case SC_ADORAMUS: //Arch Bishop if (sd) tick>>=1; //Half duration for players. case SC_STONE: @@ -6205,13 +6273,13 @@ int status_get_sc_def(struct block_list *bl, enum sc_type type, int rate, int ti sc_def = (status->str + status->int_)*50; sc_def2 = status->luk*10; break; - case SC_ANKLE: + case SC_ANKLESNARE: if(status->mode&MD_BOSS) // Lasts 5 times less on bosses tick /= 5; sc_def = status->agi*50; break; case SC_MAGICMIRROR: - case SC_ARMORCHANGE: + case SC_STONESKIN: if (sd) //Duration greatly reduced for players. tick /= 15; sc_def2 = status_get_lv(bl)*20 + status->vit*25 + status->agi*10; // Lineal Reduction of Rate @@ -6231,21 +6299,20 @@ int status_get_sc_def(struct block_list *bl, enum sc_type type, int rate, int ti tick -= (status->vit + status->luk) / 20 * 1000; break; case SC_BURNING: - // From iROwiki : http://forums.irowiki.org/showpost.php?p=577240&postcount=583 - tick -= 50*status->luk + 60*status->int_ + 170*status->vit; - tick = max(tick,10000); // Minimum Duration 10s. + tick -= 75 * status->luk + 125 * status->agi; + tick = max(tick,5000); // Minimum Duration 5s. break; - case SC_FREEZING: + case SC_FROSTMISTY: tick -= 1000 * ((status->vit + status->dex) / 20); - tick = max(tick,10000); // Minimum Duration 10s. + tick = max(tick,6000); // Minimum Duration 10s. break; case SC_OBLIVIONCURSE: // 100% - (100 - 0.8 x INT) sc_def = 100 - ( 100 - status->int_* 8 / 10 ); sc_def = max(sc_def, 5); // minimum of 5% break; - case SC_BITE: // {(Base Success chance) - (Target's AGI / 4)} - rate -= status->agi*1000/4; - rate = max(rate,50000); // minimum of 50% + case SC_WUGBITE: // {(Base Success chance) - (Target's AGI / 4)} + rate -= status->agi*100/4; + rate = max(rate,5000); // minimum of 50% break; case SC_ELECTRICSHOCKER: if( bl->type == BL_MOB ) @@ -6258,11 +6325,11 @@ int status_get_sc_def(struct block_list *bl, enum sc_type type, int rate, int ti sc_def = (status->vit+status->luk)/5; break; case SC_KYOUGAKU: - tick -= 30*status->int_; + tick -= 1000 * status_get_int(bl) / 20; break; - case SC_PARALYSIS: - tick -= 50 * (status->vit + status->luk); //(1000/20); - break; + case SC_NEEDLE_OF_PARALYZE: + tick -= 50 * (status->vit + status->luk); //(1000/20); + break; default: //Effect that cannot be reduced? Likely a buff. if (!(rnd()%10000 < rate)) @@ -6320,7 +6387,7 @@ int status_get_sc_def(struct block_list *bl, enum sc_type type, int rate, int ti //Minimum chances switch (type) { - case SC_BITE: + case SC_WUGBITE: rate = max(rate, 5000); //Minimum of 50% break; } @@ -6330,8 +6397,8 @@ int status_get_sc_def(struct block_list *bl, enum sc_type type, int rate, int ti { if( sd->reseff[type-SC_COMMON_MIN] > 0 ) rate -= rate*sd->reseff[type-SC_COMMON_MIN]/10000; - if( sd->sc.data[SC_COMMONSC_RESIST] ) - rate -= rate*sd->sc.data[SC_COMMONSC_RESIST]->val1/100; + if( sd->sc.data[SC_TARGET_BLOOD] ) + rate -= rate*sd->sc.data[SC_TARGET_BLOOD]->val1/100; } } @@ -6350,13 +6417,13 @@ int status_get_sc_def(struct block_list *bl, enum sc_type type, int rate, int ti //Minimum durations switch (type) { - case SC_ANKLE: + case SC_ANKLESNARE: case SC_MARSHOFABYSS: case SC_STASIS: tick = max(tick, 5000); //Minimum duration 5s break; case SC_BURNING: - case SC_FREEZING: + case SC_FROSTMISTY: tick = max(tick, 10000); //Minimum duration 10s break; default: @@ -6460,9 +6527,9 @@ int status_change_start(struct block_list* bl,enum sc_type type,int rate,int val return 0; // Immune to status ailements switch( type ) { case SC_QUAGMIRE://Tester said it protects against this and decrease agi. - case SC_DECREASEAGI: + case SC_DEC_AGI: case SC_BURNING: - case SC_FREEZING: + case SC_FROSTMISTY: //case SC_WHITEIMPRISON://Need confirm. Protected against this in the past. [Rytech] case SC_MARSHOFABYSS: case SC_TOXIN: @@ -6474,7 +6541,7 @@ int status_change_start(struct block_list* bl,enum sc_type type,int rate,int val case SC_OBLIVIONCURSE: case SC_LEECHESEND: case SC_CRYSTALIZE: ////08/31/2011 - Class Balance Changes - case SC_DEEPSLEEP: + case SC_DEEP_SLEEP: case SC_MANDRAGORA: return 0; } @@ -6483,8 +6550,8 @@ int status_change_start(struct block_list* bl,enum sc_type type,int rate,int val if( type >= SC_COMMON_MIN && type <= SC_COMMON_MAX ) return 0; // Immune to status ailements switch( type ) { - case SC_DEEPSLEEP: - case SC_SATURDAYNIGHTFEVER: + case SC_DEEP_SLEEP: + case SC_SATURDAY_NIGHT_FEVER: case SC_PYREXIA: case SC_DEATHHURT: case SC_MAGICMUSHROOM: @@ -6528,14 +6595,14 @@ int status_change_start(struct block_list* bl,enum sc_type type,int rate,int val //Undead are immune to Freeze/Stone if (undead_flag && !(flag&1)) return 0; - case SC_DEEPSLEEP: + case SC_DEEP_SLEEP: case SC_SLEEP: case SC_STUN: - case SC_FREEZING: + case SC_FROSTMISTY: case SC_CRYSTALIZE: if (sc->opt1) return 0; //Cannot override other opt1 status changes. [Skotlex] - if((type == SC_FREEZE || type == SC_FREEZING || type == SC_CRYSTALIZE) && sc->data[SC_WARMER]) + if((type == SC_FREEZE || type == SC_FROSTMISTY || type == SC_CRYSTALIZE) && sc->data[SC_WARMER]) return 0; //Immune to Frozen and Freezing status if under Warmer status. [Jobbie] break; @@ -6543,23 +6610,23 @@ int status_change_start(struct block_list* bl,enum sc_type type,int rate,int val case SC__BLOODYLUST: if(!sd) return 0; //should only affect player case SC_BERSERK: - if (((type == SC_BERSERK) && (sc->data[SC_SATURDAYNIGHTFEVER] || sc->data[SC__BLOODYLUST])) - || ((type == SC__BLOODYLUST) && (sc->data[SC_SATURDAYNIGHTFEVER] || sc->data[SC_BERSERK])) + if (((type == SC_BERSERK) && (sc->data[SC_SATURDAY_NIGHT_FEVER] || sc->data[SC__BLOODYLUST])) + || ((type == SC__BLOODYLUST) && (sc->data[SC_SATURDAY_NIGHT_FEVER] || sc->data[SC_BERSERK])) ) return 0; break; case SC_BURNING: - if(sc->opt1 || sc->data[SC_FREEZING]) + if(sc->opt1 || sc->data[SC_FROSTMISTY]) return 0; break; - case SC_SIGNUMCRUCIS: + case SC_CRUCIS: //Only affects demons and undead element (but not players) if((!undead_flag && status->race!=RC_DEMON) || bl->type == BL_PC) return 0; break; - case SC_AETERNA: + case SC_LEXAETERNA: if( (sc->data[SC_STONE] && sc->opt1 == OPT1_STONE) || sc->data[SC_FREEZE] ) return 0; break; @@ -6568,9 +6635,9 @@ int status_change_start(struct block_list* bl,enum sc_type type,int rate,int val return 0; break; case SC_OVERTHRUST: - if (sc->data[SC_MAXOVERTHRUST]) + if (sc->data[SC_OVERTHRUSTMAX]) return 0; //Overthrust can't take effect if under Max Overthrust. [Skotlex] - case SC_MAXOVERTHRUST: + case SC_OVERTHRUSTMAX: if( sc->option&OPTION_MADOGEAR ) return 0;//Overthrust and Overthrust Max cannot be used on Mado Gear [Ind] break; @@ -6578,7 +6645,7 @@ int status_change_start(struct block_list* bl,enum sc_type type,int rate,int val if(sd && !pc_check_weapontype(sd,skill->get_weapontype(BS_ADRENALINE))) return 0; if (sc->data[SC_QUAGMIRE] || - sc->data[SC_DECREASEAGI] || + sc->data[SC_DEC_AGI] || sc->option&OPTION_MADOGEAR //Adrenaline doesn't affect Mado Gear [Ind] ) return 0; @@ -6587,27 +6654,27 @@ int status_change_start(struct block_list* bl,enum sc_type type,int rate,int val if(sd && !pc_check_weapontype(sd,skill->get_weapontype(BS_ADRENALINE2))) return 0; if (sc->data[SC_QUAGMIRE] || - sc->data[SC_DECREASEAGI] + sc->data[SC_DEC_AGI] ) return 0; break; case SC_MAGNIFICAT: - if( sc->option&OPTION_MADOGEAR ) //Mado is immune to magnificat + if( sc->data[SC_OFFERTORIUM] || sc->option&OPTION_MADOGEAR ) //Mado is immune to magnificat return 0; break; - case SC_ONEHAND: - case SC_MERC_QUICKEN: + case SC_ONEHANDQUICKEN: + case SC_MER_QUICKEN: case SC_TWOHANDQUICKEN: - if(sc->data[SC_DECREASEAGI]) + if(sc->data[SC_DEC_AGI]) return 0; - case SC_INCREASEAGI: + case SC_INC_AGI: if(sd && pc_issit(sd)){ pc->setstand(sd); clif->standing(&sd->bl); } - case SC_CONCENTRATE: + case SC_CONCENTRATION: case SC_SPEARQUICKEN: case SC_TRUESIGHT: case SC_WINDWALK: @@ -6648,7 +6715,7 @@ int status_change_start(struct block_list* bl,enum sc_type type,int rate,int val } break; //Strip skills, need to divest something or it fails. - case SC_STRIPWEAPON: + case SC_NOEQUIPWEAPON: if (sd && !(flag&4)) { //apply sc anyway if loading saved sc_data int i; opt_flag = 0; //Reuse to check success condition. @@ -6664,7 +6731,7 @@ int status_change_start(struct block_list* bl,enum sc_type type,int rate,int val } if (tick == 1) return 1; //Minimal duration: Only strip without causing the SC break; - case SC_STRIPSHIELD: + case SC_NOEQUIPSHIELD: if( val2 == 1 ) val2 = 0; //GX effect. Do not take shield off.. else if (sd && !(flag&4)) { @@ -6678,7 +6745,7 @@ int status_change_start(struct block_list* bl,enum sc_type type,int rate,int val } if (tick == 1) return 1; //Minimal duration: Only strip without causing the SC break; - case SC_STRIPARMOR: + case SC_NOEQUIPARMOR: if (sd && !(flag&4)) { int i; if(sd->bonus.unstripable_equip&EQP_ARMOR) @@ -6690,7 +6757,7 @@ int status_change_start(struct block_list* bl,enum sc_type type,int rate,int val } if (tick == 1) return 1; //Minimal duration: Only strip without causing the SC break; - case SC_STRIPHELM: + case SC_NOEQUIPHELM: if (sd && !(flag&4)) { int i; if(sd->bonus.unstripable_equip&EQP_HELM) @@ -6702,67 +6769,67 @@ int status_change_start(struct block_list* bl,enum sc_type type,int rate,int val } if (tick == 1) return 1; //Minimal duration: Only strip without causing the SC break; - case SC_MERC_FLEEUP: - case SC_MERC_ATKUP: - case SC_MERC_HPUP: - case SC_MERC_SPUP: - case SC_MERC_HITUP: + case SC_MER_FLEE: + case SC_MER_ATK: + case SC_MER_HP: + case SC_MER_SP: + case SC_MER_HIT: if( bl->type != BL_MER ) return 0; // Stats only for Mercenaries break; - case SC_STRFOOD: + case SC_FOOD_STR: if (sc->data[SC_FOOD_STR_CASH] && sc->data[SC_FOOD_STR_CASH]->val1 > val1) return 0; break; - case SC_AGIFOOD: + case SC_FOOD_AGI: if (sc->data[SC_FOOD_AGI_CASH] && sc->data[SC_FOOD_AGI_CASH]->val1 > val1) return 0; break; - case SC_VITFOOD: + case SC_FOOD_VIT: if (sc->data[SC_FOOD_VIT_CASH] && sc->data[SC_FOOD_VIT_CASH]->val1 > val1) return 0; break; - case SC_INTFOOD: + case SC_FOOD_INT: if (sc->data[SC_FOOD_INT_CASH] && sc->data[SC_FOOD_INT_CASH]->val1 > val1) return 0; break; - case SC_DEXFOOD: + case SC_FOOD_DEX: if (sc->data[SC_FOOD_DEX_CASH] && sc->data[SC_FOOD_DEX_CASH]->val1 > val1) return 0; break; - case SC_LUKFOOD: + case SC_FOOD_LUK: if (sc->data[SC_FOOD_LUK_CASH] && sc->data[SC_FOOD_LUK_CASH]->val1 > val1) return 0; break; case SC_FOOD_STR_CASH: - if (sc->data[SC_STRFOOD] && sc->data[SC_STRFOOD]->val1 > val1) + if (sc->data[SC_FOOD_STR] && sc->data[SC_FOOD_STR]->val1 > val1) return 0; break; case SC_FOOD_AGI_CASH: - if (sc->data[SC_AGIFOOD] && sc->data[SC_AGIFOOD]->val1 > val1) + if (sc->data[SC_FOOD_AGI] && sc->data[SC_FOOD_AGI]->val1 > val1) return 0; break; case SC_FOOD_VIT_CASH: - if (sc->data[SC_VITFOOD] && sc->data[SC_VITFOOD]->val1 > val1) + if (sc->data[SC_FOOD_VIT] && sc->data[SC_FOOD_VIT]->val1 > val1) return 0; break; case SC_FOOD_INT_CASH: - if (sc->data[SC_INTFOOD] && sc->data[SC_INTFOOD]->val1 > val1) + if (sc->data[SC_FOOD_INT] && sc->data[SC_FOOD_INT]->val1 > val1) return 0; break; case SC_FOOD_DEX_CASH: - if (sc->data[SC_DEXFOOD] && sc->data[SC_DEXFOOD]->val1 > val1) + if (sc->data[SC_FOOD_DEX] && sc->data[SC_FOOD_DEX]->val1 > val1) return 0; break; case SC_FOOD_LUK_CASH: - if (sc->data[SC_LUKFOOD] && sc->data[SC_LUKFOOD]->val1 > val1) + if (sc->data[SC_FOOD_LUK] && sc->data[SC_FOOD_LUK]->val1 > val1) return 0; break; case SC_CAMOUFLAGE: if( sd && pc->checkskill(sd, RA_CAMOUFLAGE) < 3 && !skill->check_camouflage(bl,NULL) ) return 0; break; - case SC__STRIPACCESSORY: + case SC__STRIPACCESSARY: if( sd ) { int i = -1; if( !(sd->bonus.unstripable_equip&EQI_ACC_L) ) { @@ -6793,10 +6860,14 @@ int status_change_start(struct block_list* bl,enum sc_type type,int rate,int val if(sc->data[i]) return 0; } break; - case SC_SATURDAYNIGHTFEVER: + case SC_SATURDAY_NIGHT_FEVER: if (sc->data[SC_BERSERK] || sc->data[SC_INSPIRATION] || sc->data[SC__BLOODYLUST]) return 0; break; + case SC_OFFERTORIUM: + if (sc->data[SC_MAGNIFICAT]) + return 0; + break; } //Check for BOSS resistances @@ -6805,20 +6876,20 @@ int status_change_start(struct block_list* bl,enum sc_type type,int rate,int val return 0; switch (type) { case SC_BLESSING: - case SC_DECREASEAGI: + case SC_DEC_AGI: case SC_PROVOKE: case SC_COMA: case SC_GRAVITATION: - case SC_SUITON: + case SC_NJ_SUITON: case SC_RICHMANKIM: case SC_ROKISWEIL: case SC_FOGWALL: - case SC_FREEZING: + case SC_FROSTMISTY: case SC_BURNING: case SC_MARSHOFABYSS: case SC_ADORAMUS: - case SC_PARALYSIS: - case SC_DEEPSLEEP: + case SC_NEEDLE_OF_PARALYZE: + case SC_DEEP_SLEEP: case SC_CRYSTALIZE: // Exploit prevention - kRO Fix @@ -6832,7 +6903,7 @@ int status_change_start(struct block_list* bl,enum sc_type type,int rate,int val case SC_LEECHESEND: // Ranger Effects - case SC_BITE: + case SC_WUGBITE: case SC_ELECTRICSHOCKER: case SC_MAGNETICFIELD: @@ -6851,35 +6922,35 @@ int status_change_start(struct block_list* bl,enum sc_type type,int rate,int val status_change_end(bl, SC_STONE, INVALID_TIMER); } break; - case SC_INCREASEAGI: - status_change_end(bl, SC_DECREASEAGI, INVALID_TIMER); + case SC_INC_AGI: + status_change_end(bl, SC_DEC_AGI, INVALID_TIMER); break; case SC_QUAGMIRE: - status_change_end(bl, SC_CONCENTRATE, INVALID_TIMER); + status_change_end(bl, SC_CONCENTRATION, INVALID_TIMER); status_change_end(bl, SC_TRUESIGHT, INVALID_TIMER); status_change_end(bl, SC_WINDWALK, INVALID_TIMER); //Also blocks the ones below... - case SC_DECREASEAGI: + case SC_DEC_AGI: status_change_end(bl, SC_CARTBOOST, INVALID_TIMER); //Also blocks the ones below... case SC_DONTFORGETME: - status_change_end(bl, SC_INCREASEAGI, INVALID_TIMER); + status_change_end(bl, SC_INC_AGI, INVALID_TIMER); status_change_end(bl, SC_ADRENALINE, INVALID_TIMER); status_change_end(bl, SC_ADRENALINE2, INVALID_TIMER); status_change_end(bl, SC_SPEARQUICKEN, INVALID_TIMER); status_change_end(bl, SC_TWOHANDQUICKEN, INVALID_TIMER); - status_change_end(bl, SC_ONEHAND, INVALID_TIMER); - status_change_end(bl, SC_MERC_QUICKEN, INVALID_TIMER); + status_change_end(bl, SC_ONEHANDQUICKEN, INVALID_TIMER); + status_change_end(bl, SC_MER_QUICKEN, INVALID_TIMER); status_change_end(bl, SC_ACCELERATION, INVALID_TIMER); break; - case SC_ONEHAND: + case SC_ONEHANDQUICKEN: //Removes the Aspd potion effect, as reported by Vicious. [Skotlex] - status_change_end(bl, SC_ASPDPOTION0, INVALID_TIMER); - status_change_end(bl, SC_ASPDPOTION1, INVALID_TIMER); - status_change_end(bl, SC_ASPDPOTION2, INVALID_TIMER); - status_change_end(bl, SC_ASPDPOTION3, INVALID_TIMER); + status_change_end(bl, SC_ATTHASTE_POTION1, INVALID_TIMER); + status_change_end(bl, SC_ATTHASTE_POTION2, INVALID_TIMER); + status_change_end(bl, SC_ATTHASTE_POTION3, INVALID_TIMER); + status_change_end(bl, SC_ATTHASTE_INFINITY, INVALID_TIMER); break; - case SC_MAXOVERTHRUST: + case SC_OVERTHRUSTMAX: //Cancels Normal Overthrust. [Skotlex] status_change_end(bl, SC_OVERTHRUST, INVALID_TIMER); break; @@ -6896,18 +6967,18 @@ int status_change_start(struct block_list* bl,enum sc_type type,int rate,int val status_change_end(bl, SC_GOSPEL, INVALID_TIMER); break; case SC_HIDING: - status_change_end(bl, SC_CLOSECONFINE, INVALID_TIMER); - status_change_end(bl, SC_CLOSECONFINE2, INVALID_TIMER); + status_change_end(bl, SC_RG_CCONFINE_M, INVALID_TIMER); + status_change_end(bl, SC_RG_CCONFINE_S, INVALID_TIMER); break; case SC__BLOODYLUST: case SC_BERSERK: if(battle_config.berserk_cancels_buffs) { - status_change_end(bl, SC_ONEHAND, INVALID_TIMER); + status_change_end(bl, SC_ONEHANDQUICKEN, INVALID_TIMER); status_change_end(bl, SC_TWOHANDQUICKEN, INVALID_TIMER); - status_change_end(bl, SC_CONCENTRATION, INVALID_TIMER); + status_change_end(bl, SC_LKCONCENTRATION, INVALID_TIMER); status_change_end(bl, SC_PARRYING, INVALID_TIMER); status_change_end(bl, SC_AURABLADE, INVALID_TIMER); - status_change_end(bl, SC_MERC_QUICKEN, INVALID_TIMER); + status_change_end(bl, SC_MER_QUICKEN, INVALID_TIMER); } #ifdef RENEWAL else { @@ -6923,61 +6994,65 @@ int status_change_start(struct block_list* bl,enum sc_type type,int rate,int val status_change_end(bl, SC_ASSUMPTIO, INVALID_TIMER); break; case SC_CARTBOOST: - if(sc->data[SC_DECREASEAGI]) + if(sc->data[SC_DEC_AGI]) { //Cancel Decrease Agi, but take no further effect [Skotlex] - status_change_end(bl, SC_DECREASEAGI, INVALID_TIMER); + status_change_end(bl, SC_DEC_AGI, INVALID_TIMER); return 0; } break; case SC_FUSION: - status_change_end(bl, SC_SPIRIT, INVALID_TIMER); + status_change_end(bl, SC_SOULLINK, INVALID_TIMER); break; - case SC_ADJUSTMENT: - status_change_end(bl, SC_MADNESSCANCEL, INVALID_TIMER); + case SC_GS_ADJUSTMENT: + status_change_end(bl, SC_GS_MADNESSCANCEL, INVALID_TIMER); break; - case SC_MADNESSCANCEL: - status_change_end(bl, SC_ADJUSTMENT, INVALID_TIMER); + case SC_GS_MADNESSCANCEL: + status_change_end(bl, SC_GS_ADJUSTMENT, INVALID_TIMER); break; //NPC_CHANGEUNDEAD will debuff Blessing and Agi Up - case SC_CHANGEUNDEAD: + case SC_PROPERTYUNDEAD: status_change_end(bl, SC_BLESSING, INVALID_TIMER); - status_change_end(bl, SC_INCREASEAGI, INVALID_TIMER); + status_change_end(bl, SC_INC_AGI, INVALID_TIMER); break; - case SC_STRFOOD: + case SC_FOOD_STR: status_change_end(bl, SC_FOOD_STR_CASH, INVALID_TIMER); break; - case SC_AGIFOOD: + case SC_FOOD_AGI: status_change_end(bl, SC_FOOD_AGI_CASH, INVALID_TIMER); break; - case SC_VITFOOD: + case SC_FOOD_VIT: status_change_end(bl, SC_FOOD_VIT_CASH, INVALID_TIMER); break; - case SC_INTFOOD: + case SC_FOOD_INT: status_change_end(bl, SC_FOOD_INT_CASH, INVALID_TIMER); break; - case SC_DEXFOOD: + case SC_FOOD_DEX: status_change_end(bl, SC_FOOD_DEX_CASH, INVALID_TIMER); break; - case SC_LUKFOOD: + case SC_FOOD_LUK: status_change_end(bl, SC_FOOD_LUK_CASH, INVALID_TIMER); break; case SC_FOOD_STR_CASH: - status_change_end(bl, SC_STRFOOD, INVALID_TIMER); + status_change_end(bl, SC_FOOD_STR, INVALID_TIMER); break; case SC_FOOD_AGI_CASH: - status_change_end(bl, SC_AGIFOOD, INVALID_TIMER); + status_change_end(bl, SC_FOOD_AGI, INVALID_TIMER); break; case SC_FOOD_VIT_CASH: - status_change_end(bl, SC_VITFOOD, INVALID_TIMER); + status_change_end(bl, SC_FOOD_VIT, INVALID_TIMER); break; case SC_FOOD_INT_CASH: - status_change_end(bl, SC_INTFOOD, INVALID_TIMER); + status_change_end(bl, SC_FOOD_INT, INVALID_TIMER); break; case SC_FOOD_DEX_CASH: - status_change_end(bl, SC_DEXFOOD, INVALID_TIMER); + status_change_end(bl, SC_FOOD_DEX, INVALID_TIMER); break; case SC_FOOD_LUK_CASH: - status_change_end(bl, SC_LUKFOOD, INVALID_TIMER); + status_change_end(bl, SC_FOOD_LUK, INVALID_TIMER); + break; + case SC_ENDURE: + if( val4 ) + status_change_end(bl, SC_LKCONCENTRATION, INVALID_TIMER); break; case SC_FIGHTINGSPIRIT: status_change_end(bl, type, INVALID_TIMER); // Remove previous one. @@ -6985,57 +7060,57 @@ int status_change_start(struct block_list* bl,enum sc_type type,int rate,int val case SC_MARSHOFABYSS: status_change_end(bl, SC_INCAGI, INVALID_TIMER); status_change_end(bl, SC_WINDWALK, INVALID_TIMER); - status_change_end(bl, SC_ASPDPOTION0, INVALID_TIMER); - status_change_end(bl, SC_ASPDPOTION1, INVALID_TIMER); - status_change_end(bl, SC_ASPDPOTION2, INVALID_TIMER); - status_change_end(bl, SC_ASPDPOTION3, INVALID_TIMER); + status_change_end(bl, SC_ATTHASTE_POTION1, INVALID_TIMER); + status_change_end(bl, SC_ATTHASTE_POTION2, INVALID_TIMER); + status_change_end(bl, SC_ATTHASTE_POTION3, INVALID_TIMER); + status_change_end(bl, SC_ATTHASTE_INFINITY, INVALID_TIMER); break; - case SC_SWINGDANCE: - case SC_SYMPHONYOFLOVER: - case SC_MOONLITSERENADE: - case SC_RUSHWINDMILL: + case SC_SWING: + case SC_SYMPHONY_LOVE: + case SC_MOONLIT_SERENADE: + case SC_RUSH_WINDMILL: case SC_ECHOSONG: case SC_HARMONIZE: //group A doesn't overlap - if (type != SC_SWINGDANCE) status_change_end(bl, SC_SWINGDANCE, INVALID_TIMER); - if (type != SC_SYMPHONYOFLOVER) status_change_end(bl, SC_SYMPHONYOFLOVER, INVALID_TIMER); - if (type != SC_MOONLITSERENADE) status_change_end(bl, SC_MOONLITSERENADE, INVALID_TIMER); - if (type != SC_RUSHWINDMILL) status_change_end(bl, SC_RUSHWINDMILL, INVALID_TIMER); + if (type != SC_SWING) status_change_end(bl, SC_SWING, INVALID_TIMER); + if (type != SC_SYMPHONY_LOVE) status_change_end(bl, SC_SYMPHONY_LOVE, INVALID_TIMER); + if (type != SC_MOONLIT_SERENADE) status_change_end(bl, SC_MOONLIT_SERENADE, INVALID_TIMER); + if (type != SC_RUSH_WINDMILL) status_change_end(bl, SC_RUSH_WINDMILL, INVALID_TIMER); if (type != SC_ECHOSONG) status_change_end(bl, SC_ECHOSONG, INVALID_TIMER); if (type != SC_HARMONIZE) status_change_end(bl, SC_HARMONIZE, INVALID_TIMER); break; - case SC_VOICEOFSIREN: - case SC_DEEPSLEEP: + case SC_SIREN: + case SC_DEEP_SLEEP: case SC_GLOOMYDAY: - case SC_SONGOFMANA: - case SC_DANCEWITHWUG: - case SC_SATURDAYNIGHTFEVER: - case SC_LERADSDEW: + case SC_SONG_OF_MANA: + case SC_DANCE_WITH_WUG: + case SC_SATURDAY_NIGHT_FEVER: + case SC_LERADS_DEW: case SC_MELODYOFSINK: - case SC_BEYONDOFWARCRY: - case SC_UNLIMITEDHUMMINGVOICE: //group B - if (type != SC_VOICEOFSIREN) status_change_end(bl, SC_VOICEOFSIREN, INVALID_TIMER); - if (type != SC_DEEPSLEEP) status_change_end(bl, SC_DEEPSLEEP, INVALID_TIMER); - if (type != SC_LERADSDEW) status_change_end(bl, SC_LERADSDEW, INVALID_TIMER); + case SC_BEYOND_OF_WARCRY: + case SC_UNLIMITED_HUMMING_VOICE: //group B + if (type != SC_SIREN) status_change_end(bl, SC_SIREN, INVALID_TIMER); + if (type != SC_DEEP_SLEEP) status_change_end(bl, SC_DEEP_SLEEP, INVALID_TIMER); + if (type != SC_LERADS_DEW) status_change_end(bl, SC_LERADS_DEW, INVALID_TIMER); if (type != SC_MELODYOFSINK) status_change_end(bl, SC_MELODYOFSINK, INVALID_TIMER); - if (type != SC_BEYONDOFWARCRY) status_change_end(bl, SC_BEYONDOFWARCRY, INVALID_TIMER); - if (type != SC_UNLIMITEDHUMMINGVOICE) status_change_end(bl, SC_UNLIMITEDHUMMINGVOICE, INVALID_TIMER); + if (type != SC_BEYOND_OF_WARCRY) status_change_end(bl, SC_BEYOND_OF_WARCRY, INVALID_TIMER); + if (type != SC_UNLIMITED_HUMMING_VOICE) status_change_end(bl, SC_UNLIMITED_HUMMING_VOICE, INVALID_TIMER); if (type != SC_GLOOMYDAY) { status_change_end(bl, SC_GLOOMYDAY, INVALID_TIMER); status_change_end(bl, SC_GLOOMYDAY_SK, INVALID_TIMER); } - if (type != SC_SONGOFMANA) status_change_end(bl, SC_SONGOFMANA, INVALID_TIMER); - if (type != SC_DANCEWITHWUG) status_change_end(bl, SC_DANCEWITHWUG, INVALID_TIMER); - if (type != SC_SATURDAYNIGHTFEVER) { - if (sc->data[SC_SATURDAYNIGHTFEVER]) { - sc->data[SC_SATURDAYNIGHTFEVER]->val2 = 0; //mark to not lose hp - status_change_end(bl, SC_SATURDAYNIGHTFEVER, INVALID_TIMER); + if (type != SC_SONG_OF_MANA) status_change_end(bl, SC_SONG_OF_MANA, INVALID_TIMER); + if (type != SC_DANCE_WITH_WUG) status_change_end(bl, SC_DANCE_WITH_WUG, INVALID_TIMER); + if (type != SC_SATURDAY_NIGHT_FEVER) { + if (sc->data[SC_SATURDAY_NIGHT_FEVER]) { + sc->data[SC_SATURDAY_NIGHT_FEVER]->val2 = 0; //mark to not lose hp + status_change_end(bl, SC_SATURDAY_NIGHT_FEVER, INVALID_TIMER); } } break; case SC_REFLECTSHIELD: - status_change_end(bl, SC_REFLECTDAMAGE, INVALID_TIMER); + status_change_end(bl, SC_LG_REFLECTDAMAGE, INVALID_TIMER); break; - case SC_REFLECTDAMAGE: + case SC_LG_REFLECTDAMAGE: status_change_end(bl, SC_REFLECTSHIELD, INVALID_TIMER); break; case SC_SHIELDSPELL_DEF: @@ -7049,15 +7124,15 @@ int status_change_start(struct block_list* bl,enum sc_type type,int rate,int val if( type != SC_SHIELDSPELL_REF ) status_change_end(bl, SC_SHIELDSPELL_REF, INVALID_TIMER); break; - case SC_GT_ENERGYGAIN: - case SC_GT_CHANGE: - case SC_GT_REVITALIZE: - if( type != SC_GT_REVITALIZE ) - status_change_end(bl, SC_GT_REVITALIZE, INVALID_TIMER); - if( type != SC_GT_ENERGYGAIN ) - status_change_end(bl, SC_GT_ENERGYGAIN, INVALID_TIMER); - if( type != SC_GT_CHANGE ) - status_change_end(bl, SC_GT_CHANGE, INVALID_TIMER); + case SC_GENTLETOUCH_ENERGYGAIN: + case SC_GENTLETOUCH_CHANGE: + case SC_GENTLETOUCH_REVITALIZE: + if( type != SC_GENTLETOUCH_REVITALIZE ) + status_change_end(bl, SC_GENTLETOUCH_REVITALIZE, INVALID_TIMER); + if( type != SC_GENTLETOUCH_ENERGYGAIN ) + status_change_end(bl, SC_GENTLETOUCH_ENERGYGAIN, INVALID_TIMER); + if( type != SC_GENTLETOUCH_CHANGE ) + status_change_end(bl, SC_GENTLETOUCH_CHANGE, INVALID_TIMER); break; case SC_INVINCIBLE: status_change_end(bl, SC_INVINCIBLEOFF, INVALID_TIMER); @@ -7073,24 +7148,24 @@ int status_change_start(struct block_list* bl,enum sc_type type,int rate,int val //Check for overlapping fails if( (sce = sc->data[type]) ) { switch( type ) { - case SC_MERC_FLEEUP: - case SC_MERC_ATKUP: - case SC_MERC_HPUP: - case SC_MERC_SPUP: - case SC_MERC_HITUP: + case SC_MER_FLEE: + case SC_MER_ATK: + case SC_MER_HP: + case SC_MER_SP: + case SC_MER_HIT: if( sce->val1 > val1 ) val1 = sce->val1; break; case SC_ADRENALINE: case SC_ADRENALINE2: - case SC_WEAPONPERFECTION: + case SC_WEAPONPERFECT: case SC_OVERTHRUST: if (sce->val2 > val2) return 0; break; case SC_S_LIFEPOTION: case SC_L_LIFEPOTION: - case SC_BOSSMAPINFO: + case SC_CASH_BOSS_ALARM: case SC_STUN: case SC_SLEEP: case SC_POISON: @@ -7098,13 +7173,13 @@ int status_change_start(struct block_list* bl,enum sc_type type,int rate,int val case SC_SILENCE: case SC_CONFUSION: case SC_BLIND: - case SC_BLEEDING: + case SC_BLOODING: case SC_DPOISON: - case SC_CLOSECONFINE2: //Can't be re-closed in. + case SC_RG_CCONFINE_S: //Can't be re-closed in. + case SC_MARIONETTE_MASTER: case SC_MARIONETTE: - case SC_MARIONETTE2: case SC_NOCHAT: - case SC_CHANGE: //Otherwise your Hp/Sp would get refilled while still within effect of the last invocation. + case SC_HLIF_CHANGE: //Otherwise your Hp/Sp would get refilled while still within effect of the last invocation. case SC__INVISIBILITY: case SC__ENERVATION: case SC__GROOMY: @@ -7113,17 +7188,17 @@ int status_change_start(struct block_list* bl,enum sc_type type,int rate,int val case SC__WEAKNESS: case SC__UNLUCKY: return 0; - case SC_COMBO: + case SC_COMBOATTACK: case SC_DANCING: case SC_DEVOTION: - case SC_ASPDPOTION0: - case SC_ASPDPOTION1: - case SC_ASPDPOTION2: - case SC_ASPDPOTION3: - case SC_ATKPOTION: - case SC_MATKPOTION: + case SC_ATTHASTE_POTION1: + case SC_ATTHASTE_POTION2: + case SC_ATTHASTE_POTION3: + case SC_ATTHASTE_INFINITY: + case SC_PLUSATTACKPOWER: + case SC_PLUSMAGICPOWER: case SC_ENCHANTARMS: - case SC_ARMOR_ELEMENT: + case SC_ARMORPROPERTY: case SC_ARMOR_RESIST: break; case SC_GOSPEL: @@ -7153,7 +7228,7 @@ int status_change_start(struct block_list* bl,enum sc_type type,int rate,int val val3 = sce->val3; val4 = sce->val4; break; - case SC_LERADSDEW: + case SC_LERADS_DEW: if (sc && (sc->data[SC_BERSERK] || sc->data[SC__BLOODYLUST])) return 0; case SC_SHAPESHIFT: @@ -7178,8 +7253,8 @@ int status_change_start(struct block_list* bl,enum sc_type type,int rate,int val calc_flag = StatusChangeFlagTable[type]; if(!(flag&4)) { //&4 - Do not parse val settings when loading SCs switch(type) { - case SC_DECREASEAGI: - case SC_INCREASEAGI: + case SC_DEC_AGI: + case SC_INC_AGI: val2 = 2 + val1; //Agi change break; case SC_ENDURE: @@ -7209,7 +7284,7 @@ int status_change_start(struct block_list* bl,enum sc_type type,int rate,int val sc_start4(bl,SC_PROVOKE,100,10,1,0,0,60000); tick = -1; break; - case SC_SIGNUMCRUCIS: + case SC_CRUCIS: val2 = 10 + 4*val1; //Def reduction tick = -1; clif->emotion(bl,E_SWT); @@ -7220,7 +7295,10 @@ int status_change_start(struct block_list* bl,enum sc_type type,int rate,int val break; case SC_EDP: // [Celest] val2 = val1 + 2; //Chance to Poison enemies. - #ifndef RENEWAL_EDP + #ifdef RENEWAL_EDP + val3 = 50*(val1+3); + val4 = 100 * ((val1 + 1)/2 + 2); + #else val3 = 50*(val1+1); //Damage increase (+50 +50*lv%) #endif if( sd )//[Ind] - iROwiki says each level increases its duration by 3 seconds @@ -7247,18 +7325,18 @@ int status_change_start(struct block_list* bl,enum sc_type type,int rate,int val val2 = 5; //Lasts 5 hits tick = -1; break; - case SC_ENCPOISON: + case SC_ENCHANTPOISON: val2= 250+50*val1; //Poisoning Chance (2.5+0.5%) in 1/10000 rate case SC_ASPERSIO: - case SC_FIREWEAPON: - case SC_WATERWEAPON: - case SC_WINDWEAPON: - case SC_EARTHWEAPON: - case SC_SHADOWWEAPON: - case SC_GHOSTWEAPON: + case SC_PROPERTYFIRE: + case SC_PROPERTYWATER: + case SC_PROPERTYWIND: + case SC_PROPERTYGROUND: + case SC_PROPERTYDARK: + case SC_PROPERTYTELEKINESIS: skill->enchant_elemental_end(bl,type); break; - case SC_ELEMENTALCHANGE: + case SC_ARMOR_PROPERTY: // val1 : Element Lvl (if called by skill lvl 1, takes random value between 1 and 4) // val2 : Element (When no element, random one is picked) // val3 : 0 = called by skill 1 = called by script (fixed level) @@ -7291,19 +7369,19 @@ int status_change_start(struct block_list* bl,enum sc_type type,int rate,int val status_change_start(&tsd->bl, type, 10000, val1, val2, 0, 0, tick, 1); } break; - case SC_STRIPWEAPON: + case SC_NOEQUIPWEAPON: if (!sd) //Watk reduction val2 = 25; break; - case SC_STRIPSHIELD: + case SC_NOEQUIPSHIELD: if (!sd) //Def reduction val2 = 15; break; - case SC_STRIPARMOR: + case SC_NOEQUIPARMOR: if (!sd) //Vit reduction val2 = 40; break; - case SC_STRIPHELM: + case SC_NOEQUIPHELM: if (!sd) //Int reduction val2 = 40; break; @@ -7334,7 +7412,7 @@ int status_change_start(struct block_list* bl,enum sc_type type,int rate,int val val2 = 0; #endif break; - case SC_SUITON: + case SC_NJ_SUITON: if (!val2 || (sd && (sd->class_&MAPID_BASEMASK) == MAPID_NINJA)) { //No penalties. val2 = 0; //Agi penalty @@ -7345,13 +7423,13 @@ int status_change_start(struct block_list* bl,enum sc_type type,int rate,int val val2 = 3*((val1+1)/3); if (val1 > 4) val2--; break; - case SC_ONEHAND: + case SC_ONEHANDQUICKEN: case SC_TWOHANDQUICKEN: val2 = 300; if (val1 > 10) //For boss casted skills [Skotlex] val2 += 20*(val1-10); break; - case SC_MERC_QUICKEN: + case SC_MER_QUICKEN: val2 = 300; break; #ifndef RENEWAL_ASPD @@ -7365,24 +7443,28 @@ int status_change_start(struct block_list* bl,enum sc_type type,int rate,int val //val3 : Brings the skill_lv (merged into val1 here) //val4 : Partner if (val1 == CG_MOONLIT) - clif->status_change(bl,SI_MOONLIT,1,tick,0, 0, 0); + clif->status_change(bl,SI_MOON,1,tick,0, 0, 0); val1|= (val3<<16); val3 = tick/1000; //Tick duration tick_time = 1000; // [GodLesZ] tick time break; case SC_LONGING: + #ifdef RENEWAL + val2 = 50 + 10 * val1; + #else val2 = 500-100*val1; //Aspd penalty. + #endif break; case SC_EXPLOSIONSPIRITS: val2 = 75 + 25*val1; //Cri bonus break; - case SC_ASPDPOTION0: - case SC_ASPDPOTION1: - case SC_ASPDPOTION2: - case SC_ASPDPOTION3: - val2 = 50*(2+type-SC_ASPDPOTION0); - break; + case SC_ATTHASTE_POTION1: + case SC_ATTHASTE_POTION2: + case SC_ATTHASTE_POTION3: + case SC_ATTHASTE_INFINITY: + val2 = 50*(2+type-SC_ATTHASTE_POTION1); + break; case SC_WEDDING: case SC_XMAS: @@ -7407,7 +7489,8 @@ int status_change_start(struct block_list* bl,enum sc_type type,int rate,int val val3 = tick/1000; //Petrified HP-damage iterations. if(val3 < 1) val3 = 1; tick = val4; //Petrifying time. - tick = max(tick, 1000); //Min time + if(val4 > 500) // not with WL_SIENNAEXECRATE + tick = max(tick, 1000); //Min time calc_flag = 0; //Actual status changes take effect on petrified state. break; @@ -7439,7 +7522,7 @@ int status_change_start(struct block_list* bl,enum sc_type type,int rate,int val case SC_CONFUSION: clif->emotion(bl,E_WHAT); break; - case SC_BLEEDING: + case SC_BLOODING: val4 = tick/10000; if (!val4) val4 = 1; tick_time = 10000; // [GodLesZ] tick time @@ -7455,7 +7538,7 @@ int status_change_start(struct block_list* bl,enum sc_type type,int rate,int val val4 = 1; tick_time = val2 * 1000; // [GodLesZ] tick time break; - case SC_BOSSMAPINFO: + case SC_CASH_BOSS_ALARM: if( sd != NULL ) { struct mob_data *boss_md = iMap->getmob_boss(bl->m); // Search for Boss on this Map @@ -7479,7 +7562,7 @@ int status_change_start(struct block_list* bl,enum sc_type type,int rate,int val case SC_CHASEWALK: val2 = tick>0?tick:10000; //Interval at which SP is drained. val3 = 35 - 5 * val1; //Speed adjustment. - if (sc->data[SC_SPIRIT] && sc->data[SC_SPIRIT]->val2 == SL_ROGUE) + if (sc->data[SC_SOULLINK] && sc->data[SC_SOULLINK]->val2 == SL_ROGUE) val3 -= 40; val4 = 10+val1*2; //SP cost. if (map_flag_gvg(bl->m) || map[bl->m].flag.battleground) val4 *= 5; @@ -7500,24 +7583,24 @@ int status_change_start(struct block_list* bl,enum sc_type type,int rate,int val break; case SC_SIGHT: /* splash status */ case SC_RUWACH: - case SC_SIGHTBLASTER: + case SC_WZ_SIGHTBLASTER: val3 = skill->get_splash(val2, val1); //Val2 should bring the skill-id. val2 = tick/250; tick_time = 10; // [GodLesZ] tick time break; //Permanent effects. - case SC_AETERNA: + case SC_LEXAETERNA: case SC_MODECHANGE: - case SC_WEIGHT50: - case SC_WEIGHT90: + case SC_WEIGHTOVER50: + case SC_WEIGHTOVER90: case SC_BROKENWEAPON: case SC_BROKENARMOR: - case SC_READYSTORM: - case SC_READYDOWN: - case SC_READYCOUNTER: - case SC_READYTURN: - case SC_DODGE: + case SC_STORMKICK_READY: + case SC_DOWNKICK_READY: + case SC_COUNTERKICK_READY: + case SC_TURNKICK_READY: + case SC_DODGE_READY: case SC_PUSH_CART: case SC_ALL_RIDING: tick = -1; @@ -7591,7 +7674,7 @@ int status_change_start(struct block_list* bl,enum sc_type type,int rate,int val case SC_JOINTBEAT: if( val2&BREAK_NECK ) - sc_start2(bl,SC_BLEEDING,100,val1,val3,skill->get_time2(status_sc2skill(type),val1)); + sc_start2(bl,SC_BLOODING,100,val1,val3,skill->get_time2(status_sc2skill(type),val1)); break; case SC_BERSERK: @@ -7614,7 +7697,7 @@ int status_change_start(struct block_list* bl,enum sc_type type,int rate,int val } break; - case SC_MARIONETTE: + case SC_MARIONETTE_MASTER: { int stat; @@ -7628,13 +7711,13 @@ int status_change_start(struct block_list* bl,enum sc_type type,int rate,int val stat = ( sd ? sd->status.luk : status_get_base_status(bl)->luk ) / 2; val4 |= cap_value(stat,0,0xFF); break; } - case SC_MARIONETTE2: + case SC_MARIONETTE: { int stat,max_stat; // fetch caster information struct block_list *pbl = iMap->id2bl(val1); struct status_change *psc = pbl?status_get_sc(pbl):NULL; - struct status_change_entry *psce = psc?psc->data[SC_MARIONETTE]:NULL; + struct status_change_entry *psce = psc?psc->data[SC_MARIONETTE_MASTER]:NULL; // fetch target's stats struct status_data* status = status_get_status_data(bl); // battle status @@ -7652,7 +7735,7 @@ int status_change_start(struct block_list* bl,enum sc_type type,int rate,int val stat = (psce->val4 >> 0)&0xFF; stat = min(stat, max_stat - status->luk ); val4 |= cap_value(stat,0,0xFF); break; } - case SC_REJECTSWORD: + case SC_SWORDREJECT: val2 = 15*val1; //Reflect chance val3 = 3; //Reflections tick = -1; @@ -7667,7 +7750,7 @@ int status_change_start(struct block_list* bl,enum sc_type type,int rate,int val val2 = 50*val1; //aspd reduction break; - case SC_REGENERATION: + case SC_GDSKILL_REGENERATION: if (val1 == 1) val2 = 2; else @@ -7706,18 +7789,18 @@ int status_change_start(struct block_list* bl,enum sc_type type,int rate,int val status_zap(bl, status->hp-1, val2?0:status->sp); return 1; break; - case SC_CLOSECONFINE2: + case SC_RG_CCONFINE_S: { struct block_list *src = val2?iMap->id2bl(val2):NULL; struct status_change *sc2 = src?status_get_sc(src):NULL; - struct status_change_entry *sce2 = sc2?sc2->data[SC_CLOSECONFINE]:NULL; + struct status_change_entry *sce2 = sc2?sc2->data[SC_RG_CCONFINE_M]:NULL; if (src && sc2) { if (!sce2) //Start lock on caster. - sc_start4(src,SC_CLOSECONFINE,100,val1,1,0,0,tick+1000); + sc_start4(src,SC_RG_CCONFINE_M,100,val1,1,0,0,tick+1000); else { //Increase count of locked enemies and refresh time. (sce2->val2)++; iTimer->delete_timer(sce2->timer, status_change_timer); - sce2->timer = iTimer->add_timer(iTimer->gettick()+tick+1000, status_change_timer, src->id, SC_CLOSECONFINE); + sce2->timer = iTimer->add_timer(iTimer->gettick()+tick+1000, status_change_timer, src->id, SC_RG_CCONFINE_M); } } else //Status failed. return 0; @@ -7742,7 +7825,7 @@ int status_change_start(struct block_list* bl,enum sc_type type,int rate,int val } break; - case SC_COMBO: { + case SC_COMBOATTACK: { //val1: Skill ID //val2: When given, target (for autotargetting skills) //val3: When set, this combo time should NOT delay attack/movement @@ -7780,7 +7863,7 @@ int status_change_start(struct block_list* bl,enum sc_type type,int rate,int val if (vd) vd->dead_sit = 1; tick = -1; break; - case SC_CONCENTRATE: + case SC_CONCENTRATION: val2 = 2 + val1; if (sd) { //Store the card-bonus data that should not count in the % val3 = sd->param_bonus[1]; //Agi @@ -7789,7 +7872,7 @@ int status_change_start(struct block_list* bl,enum sc_type type,int rate,int val val3 = val4 = 0; } break; - case SC_MAXOVERTHRUST: + case SC_OVERTHRUSTMAX: val2 = 20*val1; //Power increase break; case SC_OVERTHRUST: @@ -7801,14 +7884,15 @@ int status_change_start(struct block_list* bl,enum sc_type type,int rate,int val case SC_ADRENALINE2: case SC_ADRENALINE: val3 = (val2) ? 300 : 200; // aspd increase - case SC_WEAPONPERFECTION: + case SC_WEAPONPERFECT: if(sd && pc->checkskill(sd,BS_HILTBINDING)>0) tick += tick / 10; break; - case SC_CONCENTRATION: + case SC_LKCONCENTRATION: val2 = 5*val1; //Batk/Watk Increase val3 = 10*val1; //Hit Increase val4 = 5*val1; //Def reduction + sc_start(bl, SC_ENDURE, 100, 1, tick); //Endure effect break; case SC_ANGELUS: val2 = 5*val1; //def increase @@ -7838,7 +7922,7 @@ int status_change_start(struct block_list* bl,enum sc_type type,int rate,int val break; // gs_something1 [Vicious] - case SC_GATLINGFEVER: + case SC_GS_GATLINGFEVER: val2 = 20*val1; //Aspd increase val3 = 20+10*val1; //Batk increase val4 = 5*val1; //Flee decrease @@ -7856,18 +7940,18 @@ int status_change_start(struct block_list* bl,enum sc_type type,int rate,int val val3 = 2+3*val1; //Atk increase val4 = 5+5*val1; //Def reduction. break; - case SC_AVOID: + case SC_HLIF_AVOID: //val2 = 10*val1; //Speed change rate. break; - case SC_DEFENCE: + case SC_HAMI_DEFENCE: val2 = 2*val1; //Def bonus break; - case SC_BLOODLUST: + case SC_HAMI_BLOODLUST: val2 = 20+10*val1; //Atk rate change. val3 = 3*val1; //Leech chance val4 = 20; //Leech percent break; - case SC_FLEET: + case SC_HLIF_FLEET: val2 = 30*val1; //Aspd change val3 = 5+5*val1; //bAtk/wAtk rate change break; @@ -7901,14 +7985,14 @@ int status_change_start(struct block_list* bl,enum sc_type type,int rate,int val } } break; - case SC_UTSUSEMI: + case SC_NJ_UTSUSEMI: val2=(val1+1)/2; // number of hits blocked val3=skill->get_blewcount(NJ_UTSUSEMI, val1); //knockback value. break; - case SC_BUNSINJYUTSU: + case SC_NJ_BUNSINJYUTSU: val2=(val1+1)/2; // number of hits blocked break; - case SC_CHANGE: + case SC_HLIF_CHANGE: val2= 30*val1; //Vit increase val3= 20*val1; //Int increase break; @@ -7944,7 +8028,7 @@ int status_change_start(struct block_list* bl,enum sc_type type,int rate,int val val2 = 20*val1; //Magic reflection/cast rate break; - case SC_ARMORCHANGE: + case SC_STONESKIN: if (val2 == NPC_ANTIMAGIC) { //Boost mdef val2 =-20; @@ -7956,32 +8040,32 @@ int status_change_start(struct block_list* bl,enum sc_type type,int rate,int val val2*=val1; //20% per level val3*=val1; break; - case SC_EXPBOOST: - case SC_JEXPBOOST: + case SC_CASH_PLUSEXP: + case SC_CASH_PLUSONLYJOBEXP: if (val1 < 0) val1 = 0; break; - case SC_INCFLEE2: - case SC_INCCRI: + case SC_PLUSAVOIDVALUE: + case SC_CRITICALPERCENT: val2 = val1*10; //Actual boost (since 100% = 1000) break; case SC_SUFFRAGIUM: val2 = 15 * val1; //Speed cast decrease break; - case SC_INCHEALRATE: + case SC_HEALPLUS: if (val1 < 1) val1 = 1; break; - case SC_HALLUCINATION: + case SC_ILLUSION: val2 = 5+val1; //Factor by which displayed damage is increased by break; - case SC_DOUBLECAST: + case SC_DOUBLECASTING: val2 = 30+10*val1; //Trigger rate break; case SC_KAIZEL: val2 = 10*val1; //% of life to be revived with break; - // case SC_ARMOR_ELEMENT: + // case SC_ARMORPROPERTY: // case SC_ARMOR_RESIST: // Mod your resistance against elements: // val1 = water | val2 = earth | val3 = fire | val4 = wind @@ -7991,13 +8075,13 @@ int status_change_start(struct block_list* bl,enum sc_type type,int rate,int val //associated, and yet are not wrong/unknown. [Skotlex] //break; - case SC_MERC_FLEEUP: - case SC_MERC_ATKUP: - case SC_MERC_HITUP: + case SC_MER_FLEE: + case SC_MER_ATK: + case SC_MER_HIT: val2 = 15 * val1; break; - case SC_MERC_HPUP: - case SC_MERC_SPUP: + case SC_MER_HP: + case SC_MER_SP: val2 = 5 * val1; break; case SC_REBIRTH: @@ -8023,8 +8107,8 @@ int status_change_start(struct block_list* bl,enum sc_type type,int rate,int val tick_time = 1000; // [GodLesZ] tick time break; case SC_BURNING: - val4 = tick / 2000; // Total Ticks to Burn!! - tick_time = 2000; // [GodLesZ] tick time + val4 = tick / 3000; // Total Ticks to Burn!! + tick_time = 3000; // [GodLesZ] tick time break; /** * Rune Knight @@ -8110,24 +8194,27 @@ int status_change_start(struct block_list* bl,enum sc_type type,int rate,int val break; case SC_WHITEIMPRISON: status_change_end(bl, SC_BURNING, INVALID_TIMER); - status_change_end(bl, SC_FREEZING, INVALID_TIMER); + status_change_end(bl, SC_FROSTMISTY, INVALID_TIMER); status_change_end(bl, SC_FREEZE, INVALID_TIMER); status_change_end(bl, SC_STONE, INVALID_TIMER); break; - case SC_FREEZING: + case SC_MARSHOFABYSS: + val2 = 6 * val1; + if( sd ) // half on players + val2 >>= 1; + break; + case SC_FROSTMISTY: status_change_end(bl, SC_BURNING, INVALID_TIMER); break; case SC_READING_SB: // val2 = sp reduction per second tick_time = 5000; // [GodLesZ] tick time break; - case SC_SPHERE_1: - case SC_SPHERE_2: - case SC_SPHERE_3: - case SC_SPHERE_4: - case SC_SPHERE_5: - if( !sd ) - return 0; // Should only work on players. + case SC_SUMMON1: + case SC_SUMMON2: + case SC_SUMMON3: + case SC_SUMMON4: + case SC_SUMMON5: val4 = tick / 1000; if( val4 < 1 ) val4 = 1; @@ -8168,7 +8255,7 @@ int status_change_start(struct block_list* bl,enum sc_type type,int rate,int val tick_time = 1000; // [GodLesZ] tick time } break; - case SC__STRIPACCESSORY: + case SC__STRIPACCESSARY: if (!sd) val2 = 20; break; @@ -8212,8 +8299,8 @@ int status_change_start(struct block_list* bl,enum sc_type type,int rate,int val val2 = 10 * val1; val_flag |= 1|2; // bypasses coating protection and MADO - sc_start(bl,SC_STRIPWEAPON,100,val1,tick); - sc_start(bl,SC_STRIPSHIELD,100,val1,tick); + sc_start(bl,SC_NOEQUIPWEAPON,100,val1,tick); + sc_start(bl,SC_NOEQUIPSHIELD,100,val1,tick); break; break; case SC_GN_CARTBOOST: @@ -8230,7 +8317,7 @@ int status_change_start(struct block_list* bl,enum sc_type type,int rate,int val break; case SC_WARMER: status_change_end(bl, SC_FREEZE, INVALID_TIMER); - status_change_end(bl, SC_FREEZING, INVALID_TIMER); + status_change_end(bl, SC_FROSTMISTY, INVALID_TIMER); status_change_end(bl, SC_CRYSTALIZE, INVALID_TIMER); break; case SC_STRIKING: @@ -8238,36 +8325,42 @@ int status_change_start(struct block_list* bl,enum sc_type type,int rate,int val val4 = tick / 1000; tick_time = 1000; // [GodLesZ] tick time break; - case SC_BLOODSUCKER: - val4 = tick / 1000; - tick_time = 1000; // [GodLesZ] tick time + case SC_BLOOD_SUCKER: + { + struct block_list *src = iMap->id2bl(sce->val2); + val3 = 1; + if(src) + val3 = 200 + 100 * sce->val1 + status_get_int(src); + val4 = tick / 1000; + tick_time = 1000; // [GodLesZ] tick time + } break; case SC_VACUUM_EXTREME: tick -= (status->str / 20) * 1000; val4 = val3 = tick / 100; tick_time = 100; // [GodLesZ] tick time break; - case SC_SWINGDANCE: + case SC_SWING: val2 = 4 * val1; // Walk speed and aspd reduction. break; - case SC_SYMPHONYOFLOVER: - case SC_RUSHWINDMILL: + case SC_SYMPHONY_LOVE: + case SC_RUSH_WINDMILL: case SC_ECHOSONG: val2 = 6 * val1; val2 += val3; //Adding 1% * Lesson Bonus val2 += (int)(val4*2/10); //Adding 0.2% per JobLevel break; - case SC_MOONLITSERENADE: + case SC_MOONLIT_SERENADE: val2 = 10 * val1; break; case SC_HARMONIZE: val2 = 5 + 5 * val1; break; - case SC_VOICEOFSIREN: + case SC_SIREN: val4 = tick / 2000; tick_time = 2000; // [GodLesZ] tick time break; - case SC_DEEPSLEEP: + case SC_DEEP_SLEEP: val4 = tick / 2000; tick_time = 2000; // [GodLesZ] tick time break; @@ -8277,12 +8370,12 @@ int status_change_start(struct block_list* bl,enum sc_type type,int rate,int val val4 = tick / 1000; tick_time = 1000; // [GodLesZ] tick time break; - case SC_SONGOFMANA: + case SC_SONG_OF_MANA: val3 = 10 + (2 * val2); val4 = tick/3000; tick_time = 3000; // [GodLesZ] tick time break; - case SC_SATURDAYNIGHTFEVER: + case SC_SATURDAY_NIGHT_FEVER: if (!val4) val4 = skill->get_time2(status_sc2skill(type),val1); if (!val4) val4 = 3000; val3 = tick/val4; @@ -8302,7 +8395,7 @@ int status_change_start(struct block_list* bl,enum sc_type type,int rate,int val val2 = 15 + rand()%( (sd?pc->checkskill(sd, WM_LESSON)*5:0) + val1*10 ); break; case SC_SITDOWN_FORCE: - case SC_BANANA_BOMB_SITDOWN: + case SC_BANANA_BOMB_SITDOWN_POSTDELAY: if( sd && !pc_issit(sd) ) { pc_setsit(sd); @@ -8310,19 +8403,19 @@ int status_change_start(struct block_list* bl,enum sc_type type,int rate,int val clif->sitting(bl); } break; - case SC_DANCEWITHWUG: + case SC_DANCE_WITH_WUG: val3 = (5 * val1) + (1 * val2); //Still need official value. break; - case SC_LERADSDEW: + case SC_LERADS_DEW: val3 = (5 * val1) + (1 * val2); break; case SC_MELODYOFSINK: val3 = (5 * val1) + (1 * val2); break; - case SC_BEYONDOFWARCRY: + case SC_BEYOND_OF_WARCRY: val3 = (5 * val1) + (1 * val2); break; - case SC_UNLIMITEDHUMMINGVOICE: + case SC_UNLIMITED_HUMMING_VOICE: { struct unit_data *ud = unit_bl2ud(bl); if( ud == NULL ) return 0; @@ -8330,7 +8423,7 @@ int status_change_start(struct block_list* bl,enum sc_type type,int rate,int val val3 = 15 - (2 * val2); } break; - case SC_REFLECTDAMAGE: + case SC_LG_REFLECTDAMAGE: val2 = 15 + 5 * val1; val3 = (val1==5)?20:(val1+4)*2; // SP consumption val4 = tick/10000; @@ -8398,15 +8491,17 @@ int status_change_start(struct block_list* bl,enum sc_type type,int rate,int val val3 = tick / 5000; tick_time = 5000; // [GodLesZ] tick time break; - case SC_GT_CHANGE: + case SC_GENTLETOUCH_CHANGE: {// take note there is no def increase as skill desc says. [malufett] struct block_list * src; val3 = status->agi * val1 / 60; // ASPD increase: [(Target AGI x Skill Level) / 60] % - if( (src = iMap->id2bl(val2)) ) + if( (src = iMap->id2bl(val2)) ){ val4 = ( 200/status_get_int(src) ) * val1;// MDEF decrease: MDEF [(200 / Caster INT) x Skill Level] + val2 = ( status_get_dex(src)/4 + status_get_str(src)/2 ) * val1 / 5; // ATK increase: ATK [{(Caster DEX / 4) + (Caster STR / 2)} x Skill Level / 5] + } } break; - case SC_GT_REVITALIZE: + case SC_GENTLETOUCH_REVITALIZE: {// take note there is no vit,aspd,speed increase as skill desc says. [malufett] struct block_list * src; val3 = val1 * 30 + 150; // Natural HP recovery increase: [(Skill Level x 30) + 50] % @@ -8519,8 +8614,8 @@ int status_change_start(struct block_list* bl,enum sc_type type,int rate,int val tick_time = 10000; // [GodLesZ] tick time break; case SC_KYOUGAKU: - val2 = 2*val1 + rand()%val1; - clif->status_change(bl,SI_ACTIVE_MONSTER_TRANSFORM,1,0,1002,0,0); + val2 = 2*val1 + rand()%(3 * val1); + clif->status_change(bl, SI_ACTIVE_MONSTER_TRANSFORM, 1, 0, 1002, 0, 0); // Poring in disguise break; case SC_KAGEMUSYA: val3 = val1 * 2; @@ -8529,80 +8624,100 @@ int status_change_start(struct block_list* bl,enum sc_type type,int rate,int val tick_time = 1000; break; case SC_ZANGETSU: - if( (status_get_hp(bl)+status_get_sp(bl)) % 2 == 0) - val2 = status_get_lv(bl) / 2 + 50; - else - val2 -= 50; + val2 = status_get_lv(bl) / 3 + 20 * val1; + val3 = status_get_lv(bl) / 2 + 30 * val1; + val2 = (!(status_get_hp(bl)%2) ? val2 : -val3); + val3 = (!(status_get_sp(bl)%2) ? val2 : -val3); break; case SC_GENSOU: { - int hp = status_get_hp(bl), lv = 5; - short per = 100 / (status_get_max_hp(bl) / hp); - - if( per <= 15 ) - lv = 1; - else if( per <= 30 ) - lv = 2; - else if( per <= 50 ) - lv = 3; - else if( per <= 75 ) - lv = 4; - if( hp % 2 == 0) - status_heal(bl, hp * (6-lv) * 4 / 100, status_get_sp(bl) * (6-lv) * 3 / 100, 1); - else - status_zap(bl, hp * (lv*4) / 100, status_get_sp(bl) * (lv*3) / 100); + int hp = status_get_hp(bl), sp = status_get_sp(bl), lv = 5; + #define PER( a ) { if( a <= 15 )lv = 1;else if( a <= 30 )lv = 2;else if( a <= 50 )lv = 3;else if( a <= 75 )lv = 4;} + + if( rand()%100 > (25 + 10 * val1) - status_get_int(bl) / 2) + return 0; + + PER( 100 / (status_get_max_hp(bl) / hp) ); + status_heal(bl, (!(hp%2) ? (6-lv) *4 / 100 : -(lv*4) / 100), 0, 1); + + PER( 100 / (status_get_max_sp(bl) / sp) ); + status_heal(bl, 0,(!(sp%2) ? (6-lv) *3 / 100 : -(lv*3) / 100), 1); } break; - case SC_ANGRIFFS_MODUS: - val2 = 50 + 20 * val1; //atk bonus - val3 = 40 + 20 * val1; // Flee reduction. - val4 = tick/1000; // hp/sp reduction timer - tick_time = 1000; - break; - case SC_NEUTRALBARRIER: - tick_time = tick; - tick = -1; - break; - case SC_GOLDENE_FERSE: - val2 = 10 + 10*val1; //max hp bonus - val3 = 6 + 4 * val1; // Aspd Bonus - val4 = 2 + 2 * val1; // Chance of holy attack - break; - case SC_OVERED_BOOST: - val2 = 300 + 40*val1; //flee bonus - val3 = 179 + 2*val1; //aspd bonus - break; - case SC_GRANITIC_ARMOR: - val2 = 2*val1; //dmg reduction - val3 = 6*val1; //dmg on status end - break; - case SC_MAGMA_FLOW: - val2 = 3*val1; //activation chance - break; - case SC_PYROCLASTIC: - val2 += 10*val1; //atk bonus - break; - case SC_PARALYSIS: //[Lighta] need real info - val2 = 2*val1; //def reduction - val3 = 500*val1; //varcast augmentation - break; - case SC_PAIN_KILLER: //[Lighta] need real info - val2 = 2*val1; //aspd reduction % - val3 = 2*val1; //dmg reduction % - if(sc->data[SC_PARALYSIS]) - sc_start(bl, SC_ENDURE, 100, val1, tick); //start endure for same duration - break; - case SC_STYLE_CHANGE: //[Lighta] need real info - tick = -1; - if(val2 == MH_MD_FIGHTING) val2 = MH_MD_GRAPPLING; - else val2 = MH_MD_FIGHTING; - break; - default: - if( calc_flag == SCB_NONE && StatusSkillChangeTable[type] == 0 && StatusIconChangeTable[type] == 0 ) - { //Status change with no calc, no icon, and no skill associated...? - ShowError("UnknownStatusChange [%d]\n", type); - return 0; - } + case SC_ANGRIFFS_MODUS: + val2 = 50 + 20 * val1; //atk bonus + val3 = 40 + 20 * val1; // Flee reduction. + val4 = tick/1000; // hp/sp reduction timer + tick_time = 1000; + break; + case SC_NEUTRALBARRIER: + tick_time = tick; + tick = -1; + break; + case SC_GOLDENE_FERSE: + val2 = 10 + 10*val1; //max hp bonus + val3 = 6 + 4 * val1; // Aspd Bonus + val4 = 2 + 2 * val1; // Chance of holy attack + break; + case SC_OVERED_BOOST: + val2 = 300 + 40*val1; //flee bonus + val3 = 179 + 2*val1; //aspd bonus + break; + case SC_GRANITIC_ARMOR: + val2 = 2*val1; //dmg reduction + val3 = 6*val1; //dmg on status end + break; + case SC_MAGMA_FLOW: + val2 = 3*val1; //activation chance + break; + case SC_PYROCLASTIC: + val2 += 10*val1; //atk bonus + break; + case SC_NEEDLE_OF_PARALYZE: //[Lighta] need real info + val2 = 2*val1; //def reduction + val3 = 500*val1; //varcast augmentation + break; + case SC_PAIN_KILLER: //[Lighta] need real info + val2 = 2*val1; //aspd reduction % + val3 = 2*val1; //dmg reduction % + if(sc->data[SC_NEEDLE_OF_PARALYZE]) + sc_start(bl, SC_ENDURE, 100, val1, tick); //start endure for same duration + break; + case SC_STYLE_CHANGE: //[Lighta] need real info + tick = -1; + if(val2 == MH_MD_FIGHTING) val2 = MH_MD_GRAPPLING; + else val2 = MH_MD_FIGHTING; + break; + case SC_FULL_THROTTLE: + status_percent_heal(bl,100,0); + val2 = 7 - val1; + tick_time = 1000; + val4 = tick / tick_time; + break; + case SC_KINGS_GRACE: + val2 = 3 + val1; + tick_time = 1000; + val4 = tick / tick_time; + break; + case SC_TELEKINESIS_INTENSE: + val2 = 10 * val1; + val3 = 40 * val1; + break; + case SC_OFFERTORIUM: + val2 = 30 * val1; + break; + case SC_FRIGG_SONG: + val2 = 5 * val1; + val3 = 1000 + 100 * val1; + tick_time = 10000; + val4 = tick / tick_time; + break; + default: + if( calc_flag == SCB_NONE && StatusSkillChangeTable[type] == 0 && StatusIconChangeTable[type] == 0 ) + { //Status change with no calc, no icon, and no skill associated...? + ShowError("UnknownStatusChange [%d]\n", type); + return 0; + } } } else { //Special considerations when loading SC data. switch( type ) { @@ -8619,6 +8734,13 @@ int status_change_start(struct block_list* bl,enum sc_type type,int rate,int val case SC_KAAHI: val4 = INVALID_TIMER; break; + case SC_SUMMON1: + case SC_SUMMON2: + case SC_SUMMON3: + case SC_SUMMON4: + case SC_SUMMON5: + val_flag |= 1; + break; } } @@ -8642,7 +8764,7 @@ int status_change_start(struct block_list* bl,enum sc_type type,int rate,int val case SC_STUN: case SC_SLEEP: case SC_STONE: - case SC_DEEPSLEEP: + case SC_DEEP_SLEEP: if (sd && pc_issit(sd)) //Avoid sprite sync problems. pc->setstand(sd); case SC_TRICKDEAD: @@ -8654,12 +8776,12 @@ int status_change_start(struct block_list* bl,enum sc_type type,int rate,int val unit_stop_attack(bl); case SC_STOP: case SC_CONFUSION: - case SC_CLOSECONFINE: - case SC_CLOSECONFINE2: + case SC_RG_CCONFINE_M: + case SC_RG_CCONFINE_S: case SC_SPIDERWEB: case SC_ELECTRICSHOCKER: - case SC_BITE: - case SC_THORNSTRAP: + case SC_WUGBITE: + case SC_THORNS_TRAP: case SC__MANHOLE: case SC_CRYSTALIZE: case SC_CURSEDCIRCLE_ATKER: @@ -8668,10 +8790,11 @@ int status_change_start(struct block_list* bl,enum sc_type type,int rate,int val case SC_NETHERWORLD: case SC_MEIKYOUSISUI: case SC_KYOUGAKU: - case SC_PARALYSIS: + case SC_NEEDLE_OF_PARALYZE: + case SC_DEATHBOUND: unit_stop_walking(bl,1); break; - case SC_ANKLE: + case SC_ANKLESNARE: if( battle_config.skill_trap_type || !map_flag_gvg(bl->m) ) unit_stop_walking(bl,1); break; @@ -8679,9 +8802,9 @@ int status_change_start(struct block_list* bl,enum sc_type type,int rate,int val case SC_CLOAKING: case SC_CLOAKINGEXCEED: case SC_CHASEWALK: - case SC_WEIGHT90: + case SC_WEIGHTOVER90: case SC_CAMOUFLAGE: - case SC_VOICEOFSIREN: + case SC_SIREN: unit_stop_attack(bl); break; case SC_SILENCE: @@ -8697,7 +8820,7 @@ int status_change_start(struct block_list* bl,enum sc_type type,int rate,int val case SC_STONE: sc->opt1 = OPT1_STONEWAIT; break; case SC_FREEZE: sc->opt1 = OPT1_FREEZE; break; case SC_STUN: sc->opt1 = OPT1_STUN; break; - case SC_DEEPSLEEP: opt_flag = 0; + case SC_DEEP_SLEEP: opt_flag = 0; case SC_SLEEP: sc->opt1 = OPT1_SLEEP; break; case SC_BURNING: sc->opt1 = OPT1_BURNING; break; // Burning need this to be showed correctly. [pakpil] case SC_WHITEIMPRISON: sc->opt1 = OPT1_IMPRISON; break; @@ -8707,24 +8830,24 @@ int status_change_start(struct block_list* bl,enum sc_type type,int rate,int val case SC_CURSE: sc->opt2 |= OPT2_CURSE; break; case SC_SILENCE: sc->opt2 |= OPT2_SILENCE; break; - case SC_SIGNUMCRUCIS: + case SC_CRUCIS: sc->opt2 |= OPT2_SIGNUMCRUCIS; break; case SC_BLIND: sc->opt2 |= OPT2_BLIND; break; case SC_ANGELUS: sc->opt2 |= OPT2_ANGELUS; break; - case SC_BLEEDING: sc->opt2 |= OPT2_BLEEDING; break; + case SC_BLOODING: sc->opt2 |= OPT2_BLEEDING; break; case SC_DPOISON: sc->opt2 |= OPT2_DPOISON; break; //OPT3 case SC_TWOHANDQUICKEN: - case SC_ONEHAND: + case SC_ONEHANDQUICKEN: case SC_SPEARQUICKEN: - case SC_CONCENTRATION: - case SC_MERC_QUICKEN: + case SC_LKCONCENTRATION: + case SC_MER_QUICKEN: sc->opt3 |= OPT3_QUICKEN; opt_flag = 0; break; - case SC_MAXOVERTHRUST: + case SC_OVERTHRUSTMAX: case SC_OVERTHRUST: case SC_SWOO: //Why does it shares the same opt as Overthrust? Perhaps we'll never know... sc->opt3 |= OPT3_OVERTHRUST; @@ -8772,8 +8895,8 @@ int status_change_start(struct block_list* bl,enum sc_type type,int rate,int val sc->opt3 |= OPT3_MOONLIT; opt_flag = 0; break; + case SC_MARIONETTE_MASTER: case SC_MARIONETTE: - case SC_MARIONETTE2: sc->opt3 |= OPT3_MARIONETTE; opt_flag = 0; break; @@ -8789,15 +8912,15 @@ int status_change_start(struct block_list* bl,enum sc_type type,int rate,int val sc->opt3 |= OPT3_KAITE; opt_flag = 0; break; - case SC_BUNSINJYUTSU: + case SC_NJ_BUNSINJYUTSU: sc->opt3 |= OPT3_BUNSIN; opt_flag = 0; break; - case SC_SPIRIT: + case SC_SOULLINK: sc->opt3 |= OPT3_SOULLINK; opt_flag = 0; break; - case SC_CHANGEUNDEAD: + case SC_PROPERTYUNDEAD: sc->opt3 |= OPT3_UNDEAD; opt_flag = 0; break; @@ -8911,7 +9034,7 @@ int status_change_start(struct block_list* bl,enum sc_type type,int rate,int val } sce->val2 = 5 * status->max_hp / 100; break; - case SC_CHANGE: + case SC_HLIF_CHANGE: status_percent_heal(bl, 100, 100); break; case SC_RUN: @@ -8921,13 +9044,13 @@ int status_change_start(struct block_list* bl,enum sc_type type,int rate,int val ud->state.running = unit_run(bl); } break; - case SC_BOSSMAPINFO: + case SC_CASH_BOSS_ALARM: clif->bossmapinfo(sd->fd, iMap->id2boss(sce->val1), 0); // First Message break; - case SC_MERC_HPUP: + case SC_MER_HP: status_percent_heal(bl, 100, 0); // Recover Full HP break; - case SC_MERC_SPUP: + case SC_MER_SP: status_percent_heal(bl, 0, 100); // Recover Full SP break; /** @@ -8940,7 +9063,7 @@ int status_change_start(struct block_list* bl,enum sc_type type,int rate,int val ud->state.running = unit_wugdash(bl, sd); } break; - case SC_COMBO: + case SC_COMBOATTACK: switch (sce->val1) { case TK_STORMKICK: clif->skill_nodamage(bl,bl,TK_READYSTORM,1,1); @@ -9008,68 +9131,25 @@ int status_change_clear(struct block_list* bl, int type) { for(i = 0; i < SC_MAX; i++) { if(!sc->data[i]) continue; - - if(type == 0) { - switch (i) { //Type 0: PC killed -> Place here statuses that do not dispel on death. - case SC_ELEMENTALCHANGE://Only when its Holy or Dark that it doesn't dispell on death - if( sc->data[i]->val2 != ELE_HOLY && sc->data[i]->val2 != ELE_DARK ) - break; - case SC_WEIGHT50: - case SC_WEIGHT90: - case SC_EDP: - case SC_MELTDOWN: - case SC_XMAS: - case SC_SUMMER: - case SC_HANBOK: - case SC_NOCHAT: - case SC_FUSION: - case SC_EARTHSCROLL: - case SC_READYSTORM: - case SC_READYDOWN: - case SC_READYCOUNTER: - case SC_READYTURN: - case SC_DODGE: - case SC_JAILED: - case SC_EXPBOOST: - case SC_ITEMBOOST: - case SC_HELLPOWER: - case SC_JEXPBOOST: - case SC_AUTOTRADE: - case SC_WHISTLE: - case SC_ASSNCROS: - case SC_POEMBRAGI: - case SC_APPLEIDUN: - case SC_HUMMING: - case SC_DONTFORGETME: - case SC_FORTUNE: - case SC_SERVICE4U: - case SC_FOOD_STR_CASH: - case SC_FOOD_AGI_CASH: - case SC_FOOD_VIT_CASH: - case SC_FOOD_DEX_CASH: - case SC_FOOD_INT_CASH: - case SC_FOOD_LUK_CASH: - case SC_DEF_RATE: - case SC_MDEF_RATE: - case SC_INCHEALRATE: - case SC_INCFLEE2: - case SC_INCHIT: - case SC_ATKPOTION: - case SC_MATKPOTION: - case SC_S_LIFEPOTION: - case SC_L_LIFEPOTION: - case SC_PUSH_CART: - case SC_ALL_RIDING: - continue; + + if(type == 0){ + if( status_get_sc_type(i)&SC_NO_REM_DEATH ){ + switch (i) { + case SC_ARMOR_PROPERTY://Only when its Holy or Dark that it doesn't dispell on death + if( sc->data[i]->val2 != ELE_HOLY && sc->data[i]->val2 != ELE_DARK ) + break; + default: + continue; + } } } - if( type == 3 ) { switch (i) {// TODO: This list may be incomplete - case SC_WEIGHT50: - case SC_WEIGHT90: + case SC_WEIGHTOVER50: + case SC_WEIGHTOVER90: case SC_NOCHAT: case SC_PUSH_CART: + case SC_JAILED: case SC_ALL_RIDING: continue; } @@ -9094,6 +9174,7 @@ int status_change_clear(struct block_list* bl, int type) { #ifndef RENEWAL sc->sg_counter = 0; #endif + if( type == 0 || type == 2 ) clif->changeoption(bl); @@ -9188,7 +9269,7 @@ int status_change_end_(struct block_list* bl, enum sc_type type, int tid, const DIFF_TICK(iTimer->gettick(), sce->val4) <= 1000 && (!sd || (sd->weapontype1 == 0 && sd->weapontype2 == 0)) ) - sc_start(bl,SC_SPURT,100,sce->val1,skill->get_time2(status_sc2skill(type), sce->val1)); + sc_start(bl,SC_STRUP,100,sce->val1,skill->get_time2(status_sc2skill(type), sce->val1)); } break; case SC_AUTOBERSERK: @@ -9307,7 +9388,7 @@ int status_change_end_(struct block_list* bl, enum sc_type type, int tid, const } if((sce->val1&0xFFFF) == CG_MOONLIT) - clif->sc_end(bl,bl->id,AREA,SI_MOONLIT); + clif->sc_end(bl,bl->id,AREA,SI_MOON); status_change_end(bl, SC_LONGING, INVALID_TIMER); } @@ -9328,18 +9409,18 @@ int status_change_end_(struct block_list* bl, enum sc_type type, int tid, const skill->castend_damage_id(src, bl, sce->val2, sce->val1, iTimer->gettick(), SD_LEVEL ); } break; - case SC_CLOSECONFINE2: + case SC_RG_CCONFINE_S: { struct block_list *src = sce->val2?iMap->id2bl(sce->val2):NULL; struct status_change *sc2 = src?status_get_sc(src):NULL; - if (src && sc2 && sc2->data[SC_CLOSECONFINE]) { + if (src && sc2 && sc2->data[SC_RG_CCONFINE_M]) { //If status was already ended, do nothing. //Decrease count - if (--(sc2->data[SC_CLOSECONFINE]->val1) <= 0) //No more holds, free him up. - status_change_end(src, SC_CLOSECONFINE, INVALID_TIMER); + if (--(sc2->data[SC_RG_CCONFINE_M]->val1) <= 0) //No more holds, free him up. + status_change_end(src, SC_RG_CCONFINE_M, INVALID_TIMER); } } - case SC_CLOSECONFINE: + case SC_RG_CCONFINE_M: if (sce->val2 > 0) { //Caster has been unlocked... nearby chars need to be unlocked. int range = 1 @@ -9349,7 +9430,7 @@ int status_change_end_(struct block_list* bl, enum sc_type type, int tid, const bl->m, bl->x-range, bl->y-range, bl->x+range,bl->y+range,BL_CHAR,bl,sce,type,iTimer->gettick()); } break; - case SC_COMBO: + case SC_COMBOATTACK: if( sd ) switch (sce->val1) { case MO_COMBOFINISH: @@ -9371,11 +9452,11 @@ int status_change_end_(struct block_list* bl, enum sc_type type, int tid, const } break; - case SC_MARIONETTE: - case SC_MARIONETTE2: /// Marionette target + case SC_MARIONETTE_MASTER: + case SC_MARIONETTE: /// Marionette target if (sce->val1) { // check for partner and end their marionette status as well - enum sc_type type2 = (type == SC_MARIONETTE) ? SC_MARIONETTE2 : SC_MARIONETTE; + enum sc_type type2 = (type == SC_MARIONETTE_MASTER) ? SC_MARIONETTE : SC_MARIONETTE_MASTER; struct block_list *pbl = iMap->id2bl(sce->val1); struct status_change* sc2 = pbl?status_get_sc(pbl):NULL; @@ -9388,7 +9469,7 @@ int status_change_end_(struct block_list* bl, enum sc_type type, int tid, const break; case SC_BERSERK: - case SC_SATURDAYNIGHTFEVER: + case SC_SATURDAY_NIGHT_FEVER: //If val2 is removed, no HP penalty (dispelled?) [Skotlex] if (status->hp > 100 && sce->val2) status_set_hp(bl, 100, 0); @@ -9398,8 +9479,8 @@ int status_change_end_(struct block_list* bl, enum sc_type type, int tid, const status_change_end(bl, SC_ENDURE, INVALID_TIMER); } case SC__BLOODYLUST: - sc_start4(bl, SC_REGENERATION, 100, 10,0,0,(RGN_HP|RGN_SP), skill->get_time(LK_BERSERK, sce->val1)); - if( type == SC_SATURDAYNIGHTFEVER ) //Sit down force of Saturday Night Fever has the duration of only 3 seconds. + sc_start4(bl, SC_GDSKILL_REGENERATION, 100, 10,0,0,(RGN_HP|RGN_SP), skill->get_time(LK_BERSERK, sce->val1)); + if( type == SC_SATURDAY_NIGHT_FEVER ) //Sit down force of Saturday Night Fever has the duration of only 3 seconds. sc_start(bl,SC_SITDOWN_FORCE,100,sce->val1,skill->get_time2(WM_SATURDAY_NIGHT_FEVER,sce->val1)); break; case SC_GOSPEL: @@ -9440,7 +9521,7 @@ int status_change_end_(struct block_list* bl, enum sc_type type, int tid, const if(sd && sd->mapindex == sce->val2) pc->setpos(sd,(unsigned short)sce->val3,sce->val4&0xFFFF, sce->val4>>16, CLR_TELEPORT); break; //guess hes not in jail :P - case SC_CHANGE: + case SC_HLIF_CHANGE: if (tid == INVALID_TIMER) break; // "lose almost all their HP and SP" on natural expiration. @@ -9466,6 +9547,9 @@ int status_change_end_(struct block_list* bl, enum sc_type type, int tid, const status_change_end(tbl, SC_STOP, INVALID_TIMER); } break; + case SC_LKCONCENTRATION: + status_change_end(bl, SC_ENDURE, INVALID_TIMER); + break; /** * 3rd Stuff **/ @@ -9552,7 +9636,7 @@ int status_change_end_(struct block_list* bl, enum sc_type type, int tid, const } } break; - case SC_BLOODSUCKER: + case SC_BLOOD_SUCKER: if( sce->val2 ){ struct block_list *src = iMap->id2bl(sce->val2); if(src){ @@ -9565,10 +9649,13 @@ int status_change_end_(struct block_list* bl, enum sc_type type, int tid, const clif->sc_end(&sd->bl,sd->bl.id,AREA,SI_KYOUGAKU); clif->sc_end(&sd->bl,sd->bl.id,AREA,SI_ACTIVE_MONSTER_TRANSFORM); break; - case SC_INTRAVISION: + case SC_CLAIRVOYANCE: calc_flag = SCB_ALL;/* required for overlapping */ break; - } + case SC_FULL_THROTTLE: + sc_start(bl,SC_REBOUND,100,sce->val1,skill->get_time2(ALL_FULL_THROTTLE,sce->val1)); + break; + } opt_flag = 1; switch(type){ @@ -9576,7 +9663,7 @@ int status_change_end_(struct block_list* bl, enum sc_type type, int tid, const case SC_FREEZE: case SC_STUN: case SC_SLEEP: - case SC_DEEPSLEEP: + case SC_DEEP_SLEEP: case SC_BURNING: case SC_WHITEIMPRISON: case SC_CRYSTALIZE: @@ -9592,7 +9679,7 @@ int status_change_end_(struct block_list* bl, enum sc_type type, int tid, const case SC_DPOISON: sc->opt2 &= ~OPT2_DPOISON; break; - case SC_SIGNUMCRUCIS: + case SC_CRUCIS: sc->opt2 &= ~OPT2_SIGNUMCRUCIS; break; @@ -9641,15 +9728,15 @@ int status_change_end_(struct block_list* bl, enum sc_type type, int tid, const break; //opt3 case SC_TWOHANDQUICKEN: - case SC_ONEHAND: + case SC_ONEHANDQUICKEN: case SC_SPEARQUICKEN: case SC_CONCENTRATION: - case SC_MERC_QUICKEN: + case SC_MER_QUICKEN: sc->opt3 &= ~OPT3_QUICKEN; opt_flag = 0; break; case SC_OVERTHRUST: - case SC_MAXOVERTHRUST: + case SC_OVERTHRUSTMAX: case SC_SWOO: sc->opt3 &= ~OPT3_OVERTHRUST; if( type == SC_SWOO ) @@ -9700,7 +9787,7 @@ int status_change_end_(struct block_list* bl, enum sc_type type, int tid, const opt_flag = 0; break; case SC_MARIONETTE: - case SC_MARIONETTE2: + case SC_MARIONETTE_MASTER: sc->opt3 &= ~OPT3_MARIONETTE; opt_flag = 0; break; @@ -9716,15 +9803,15 @@ int status_change_end_(struct block_list* bl, enum sc_type type, int tid, const sc->opt3 &= ~OPT3_KAITE; opt_flag = 0; break; - case SC_BUNSINJYUTSU: + case SC_NJ_BUNSINJYUTSU: sc->opt3 &= ~OPT3_BUNSIN; opt_flag = 0; break; - case SC_SPIRIT: + case SC_SOULLINK: sc->opt3 &= ~OPT3_SOULLINK; opt_flag = 0; break; - case SC_CHANGEUNDEAD: + case SC_PROPERTYUNDEAD: sc->opt3 &= ~OPT3_UNDEAD; opt_flag = 0; break; @@ -9861,9 +9948,9 @@ int status_change_timer(int tid, unsigned int tick, int id, intptr_t data) if(!status_charge(bl, 0, sce->val4)) break; //Not enough SP to continue. - if (!sc->data[SC_INCSTR]) { - sc_start(bl, SC_INCSTR,100,1<<(sce->val1-1), - (sc->data[SC_SPIRIT] && sc->data[SC_SPIRIT]->val2 == SL_ROGUE?10:1) //SL bonus -> x10 duration + if (!sc->data[SC_CHASEWALK2]) { + sc_start(bl, SC_CHASEWALK2,100,1<<(sce->val1-1), + (sc->data[SC_SOULLINK] && sc->data[SC_SOULLINK]->val2 == SL_ROGUE?10:1) //SL bonus -> x10 duration *skill->get_time2(status_sc2skill(type),sce->val1)); } sc_timer_next(sce->val2+tick, status_change_timer, bl->id, data); @@ -9891,8 +9978,8 @@ int status_change_timer(int tid, unsigned int tick, int id, intptr_t data) case SC_SIGHT: case SC_RUWACH: - case SC_SIGHTBLASTER: - if(type == SC_SIGHTBLASTER) + case SC_WZ_SIGHTBLASTER: + if(type == SC_WZ_SIGHTBLASTER) iMap->foreachinrange( status_change_timer_sub, bl, sce->val3, BL_CHAR|BL_SKILL, bl, sce, type, tick); else iMap->foreachinrange( status_change_timer_sub, bl, sce->val3, BL_CHAR, bl, sce, type, tick); @@ -9970,7 +10057,7 @@ int status_change_timer(int tid, unsigned int tick, int id, intptr_t data) } break; - case SC_BLEEDING: + case SC_BLOODING: if (--(sce->val4) >= 0) { int hp = rnd()%600 + 200; struct block_list* src = iMap->id2bl(sce->val2); @@ -10005,7 +10092,7 @@ int status_change_timer(int tid, unsigned int tick, int id, intptr_t data) } break; - case SC_BOSSMAPINFO: + case SC_CASH_BOSS_ALARM: if( sd && --(sce->val4) >= 0 ) { struct mob_data *boss_md = iMap->id2boss(sce->val1); @@ -10112,8 +10199,8 @@ int status_change_timer(int tid, unsigned int tick, int id, intptr_t data) } break; + case SC_MARIONETTE_MASTER: case SC_MARIONETTE: - case SC_MARIONETTE2: { struct block_list *pbl = iMap->id2bl(sce->val1); if( pbl && check_distance_bl(bl, pbl, 7) ) @@ -10160,7 +10247,7 @@ int status_change_timer(int tid, unsigned int tick, int id, intptr_t data) break; case SC_PYREXIA: - if( --(sce->val4) >= 0 ) { + if( --(sce->val4) > 0 ) { iMap->freeblock_lock(); clif->damage(bl,bl,tick,status_get_amotion(bl),status_get_dmotion(bl)+500,100,0,0,0); status_fix_damage(NULL,bl,100,0); @@ -10173,7 +10260,7 @@ int status_change_timer(int tid, unsigned int tick, int id, intptr_t data) break; case SC_LEECHESEND: - if( --(sce->val4) >= 0 ) { + if( --(sce->val4) > 0 ) { int damage = status->max_hp/100; // {Target VIT x (New Poison Research Skill Level - 3)} + (Target HP/100) damage += status->vit * (sce->val1 - 3); unit_skillcastcancel(bl,2); @@ -10188,7 +10275,7 @@ int status_change_timer(int tid, unsigned int tick, int id, intptr_t data) break; case SC_MAGICMUSHROOM: - if( --(sce->val4) >= 0 ) { + if( --(sce->val4) > 0 ) { bool flag = 0; int damage = status->max_hp * 3 / 100; if( status->hp <= damage ) @@ -10233,7 +10320,7 @@ int status_change_timer(int tid, unsigned int tick, int id, intptr_t data) break; case SC_TOXIN: - if( --(sce->val4) >= 0 ) + if( --(sce->val4) > 0 ) { //Damage is every 10 seconds including 3%sp drain. iMap->freeblock_lock(); clif->damage(bl,bl,tick,status_get_amotion(bl),1,1,0,0,0); @@ -10247,7 +10334,7 @@ int status_change_timer(int tid, unsigned int tick, int id, intptr_t data) break; case SC_OBLIVIONCURSE: - if( --(sce->val4) >= 0 ) + if( --(sce->val4) > 0 ) { clif->emotion(bl,E_WHAT); sc_timer_next(3000 + tick, status_change_timer, bl->id, data ); @@ -10256,7 +10343,7 @@ int status_change_timer(int tid, unsigned int tick, int id, intptr_t data) break; case SC_WEAPONBLOCKING: - if( --(sce->val4) >= 0 ) + if( --(sce->val4) > 0 ) { if( !status_charge(bl,0,3) ) break; @@ -10272,7 +10359,7 @@ int status_change_timer(int tid, unsigned int tick, int id, intptr_t data) return 0; case SC_RENOVATIO: - if( --(sce->val4) >= 0 ) + if( --(sce->val4) > 0 ) { int heal = status->max_hp * 3 / 100; if( sc && sc->data[SC_AKAITSUKI] && heal ) @@ -10284,7 +10371,7 @@ int status_change_timer(int tid, unsigned int tick, int id, intptr_t data) break; case SC_BURNING: - if( --(sce->val4) >= 0 ) + if( --(sce->val4) > 0 ) { struct block_list *src = iMap->id2bl(sce->val3); int damage = 1000 + 3 * status_get_max_hp(bl) / 100; // Deals fixed (1000 + 3%*MaxHP) @@ -10294,7 +10381,7 @@ int status_change_timer(int tid, unsigned int tick, int id, intptr_t data) status_damage(src, bl, damage, 0, 0, 1); if( sc->data[type]){ // Target still lives. [LimitLine] - sc_timer_next(2000 + tick, status_change_timer, bl->id, data); + sc_timer_next(3000 + tick, status_change_timer, bl->id, data); } iMap->freeblock_unlock(); return 0; @@ -10302,7 +10389,7 @@ int status_change_timer(int tid, unsigned int tick, int id, intptr_t data) break; case SC_FEAR: - if( --(sce->val4) >= 0 ) + if( --(sce->val4) > 0 ) { if( sce->val2 > 0 ) sce->val2--; @@ -10311,12 +10398,12 @@ int status_change_timer(int tid, unsigned int tick, int id, intptr_t data) } break; - case SC_SPHERE_1: - case SC_SPHERE_2: - case SC_SPHERE_3: - case SC_SPHERE_4: - case SC_SPHERE_5: - if( --(sce->val4) >= 0 ) + case SC_SUMMON1: + case SC_SUMMON2: + case SC_SUMMON3: + case SC_SUMMON4: + case SC_SUMMON5: + if( --(sce->val4) > 0 ) { if( !status_charge(bl, 0, 1) ) break; @@ -10328,7 +10415,7 @@ int status_change_timer(int tid, unsigned int tick, int id, intptr_t data) case SC_READING_SB: if( !status_charge(bl, 0, sce->val2) ){ int i; - for(i = SC_SPELLBOOK1; i <= SC_MAXSPELLBOOK; i++) // Also remove stored spell as well. + for(i = SC_SPELLBOOK1; i <= SC_SPELLBOOK7; i++) // Also remove stored spell as well. status_change_end(bl, (sc_type)i, INVALID_TIMER); break; } @@ -10336,7 +10423,7 @@ int status_change_timer(int tid, unsigned int tick, int id, intptr_t data) return 0; case SC_ELECTRICSHOCKER: - if( --(sce->val4) >= 0 ) + if( --(sce->val4) > 0 ) { status_charge(bl, 0, status->max_sp / 100 * sce->val1 ); sc_timer_next(1000 + tick, status_change_timer, bl->id, data); @@ -10359,7 +10446,7 @@ int status_change_timer(int tid, unsigned int tick, int id, intptr_t data) return 0; case SC__SHADOWFORM: - if( --(sce->val4) >= 0 ) + if( --(sce->val4) > 0 ) { if( !status_charge(bl, 0, sce->val1 - (sce->val1 - 1)) ) break; @@ -10369,7 +10456,7 @@ int status_change_timer(int tid, unsigned int tick, int id, intptr_t data) break; case SC__INVISIBILITY: - if( --(sce->val4) >= 0 ) + if( --(sce->val4) > 0 ) { if( !status_charge(bl, 0, (status->sp * 6 - sce->val1) / 100) )// 6% - skill_lv. break; @@ -10379,7 +10466,7 @@ int status_change_timer(int tid, unsigned int tick, int id, intptr_t data) break; case SC_STRIKING: - if( --(sce->val4) >= 0 ) + if( --(sce->val4) > 0 ) { if( !status_charge(bl,0, sce->val1 ) ) break; @@ -10388,19 +10475,19 @@ int status_change_timer(int tid, unsigned int tick, int id, intptr_t data) } break; case SC_VACUUM_EXTREME: - if( --(sce->val4) >= 0 ){ + if( --(sce->val4) > 0 ){ sc_timer_next(100 + tick, status_change_timer, bl->id, data); return 0; } break; - case SC_BLOODSUCKER: - if( --(sce->val4) >= 0 ) { + case SC_BLOOD_SUCKER: + if( --(sce->val4) > 0 ) { struct block_list *src = iMap->id2bl(sce->val2); int damage; if( !src || (src && (status_isdead(src) || src->m != bl->m || distance_bl(src, bl) >= 12)) ) break; iMap->freeblock_lock(); - damage = 200 + 100 * sce->val1 + status_get_int(src); + damage = sce->val3; status_damage(src, bl, damage, 0, clif->damage(bl,bl,tick,status->amotion,status->dmotion+200,damage,1,0,0), 1); unit_skillcastcancel(bl,1); if ( sc->data[type] ) { @@ -10412,8 +10499,8 @@ int status_change_timer(int tid, unsigned int tick, int id, intptr_t data) } break; - case SC_VOICEOFSIREN: - if( --(sce->val4) >= 0 ) + case SC_SIREN: + if( --(sce->val4) > 0 ) { clif->emotion(bl,E_LV); sc_timer_next(2000 + tick, status_change_timer, bl->id, data); @@ -10421,8 +10508,8 @@ int status_change_timer(int tid, unsigned int tick, int id, intptr_t data) } break; - case SC_DEEPSLEEP: - if( --(sce->val4) >= 0 ) + case SC_DEEP_SLEEP: + if( --(sce->val4) > 0 ) { // Recovers 1% HP/SP every 2 seconds. status_heal(bl, status->max_hp / 100, status->max_sp / 100, 2); sc_timer_next(2000 + tick, status_change_timer, bl->id, data); @@ -10431,7 +10518,7 @@ int status_change_timer(int tid, unsigned int tick, int id, intptr_t data) break; case SC_SIRCLEOFNATURE: - if( --(sce->val4) >= 0 ) + if( --(sce->val4) > 0 ) { if( !status_charge(bl,0,sce->val2) ) break; @@ -10441,8 +10528,8 @@ int status_change_timer(int tid, unsigned int tick, int id, intptr_t data) } break; - case SC_SONGOFMANA: - if( --(sce->val4) >= 0 ) + case SC_SONG_OF_MANA: + if( --(sce->val4) > 0 ) { status_heal(bl,0,sce->val3,3); sc_timer_next(3000 + tick, status_change_timer, bl->id, data); @@ -10451,9 +10538,9 @@ int status_change_timer(int tid, unsigned int tick, int id, intptr_t data) break; - case SC_SATURDAYNIGHTFEVER: + case SC_SATURDAY_NIGHT_FEVER: // 1% HP/SP drain every val4 seconds [Jobbie] - if( --(sce->val3) >= 0 ) + if( --(sce->val3) > 0 ) { int hp = status->hp / 100; int sp = status->sp / 100; @@ -10465,7 +10552,7 @@ int status_change_timer(int tid, unsigned int tick, int id, intptr_t data) break; case SC_CRYSTALIZE: - if( --(sce->val4) >= 0 ) + if( --(sce->val4) > 0 ) { // Drains 2% of HP and 1% of SP every seconds. if( bl->type != BL_MOB) // doesn't work on mobs status_charge(bl, status->max_hp * 2 / 100, status->max_sp / 100); @@ -10489,8 +10576,8 @@ int status_change_timer(int tid, unsigned int tick, int id, intptr_t data) } break; - case SC_REFLECTDAMAGE: - if( --(sce->val4) >= 0 ) { + case SC_LG_REFLECTDAMAGE: + if( --(sce->val4) > 0 ) { if( !status_charge(bl,0,sce->val3) ) break; sc_timer_next(10000 + tick, status_change_timer, bl->id, data); @@ -10538,7 +10625,7 @@ int status_change_timer(int tid, unsigned int tick, int id, intptr_t data) break; case SC_INSPIRATION: - if(--(sce->val4) >= 0) + if(--(sce->val4) > 0) { int hp = status->max_hp * (7-sce->val1) / 100; int sp = status->max_sp * (9-sce->val1) / 100; @@ -10615,12 +10702,36 @@ int status_change_timer(int tid, unsigned int tick, int id, intptr_t data) } break; case SC_ANGRIFFS_MODUS: - if(--(sce->val4) >= 0) { //drain hp/sp + if(--(sce->val4) > 0) { //drain hp/sp if( !status_charge(bl,100,20) ) break; sc_timer_next(1000+tick,status_change_timer,bl->id, data); return 0; } break; + case SC_FULL_THROTTLE: + if( --(sce->val4) > 0 ) + { + status_percent_damage(bl, bl, sce->val2, 0, false); + sc_timer_next(1000 + tick, status_change_timer, bl->id, data); + return 0; + } + break; + case SC_KINGS_GRACE: + if( --(sce->val4) > 0 ) + { + status_percent_heal(bl, sce->val2, 0); + sc_timer_next(1000 + tick, status_change_timer, bl->id, data); + return 0; + } + break; + case SC_FRIGG_SONG: + if( --(sce->val4) > 0 ) + { + status_heal(bl, sce->val3, 0, 0); + sc_timer_next(10000 + tick, status_change_timer, bl->id, data); + return 0; + } + break; } // default for all non-handled control paths is to end the status @@ -10650,7 +10761,7 @@ int status_change_timer_sub(struct block_list* bl, va_list ap) if( tsc && tsc->data[SC__SHADOWFORM] && (sce && sce->val4 >0 && sce->val4%2000 == 0) && // for every 2 seconds do the checking rnd()%100 < 100-tsc->data[SC__SHADOWFORM]->val1*10 ) // [100 - (Skill Level x 10)] % status_change_end(bl, SC__SHADOWFORM, INVALID_TIMER); - case SC_CONCENTRATE: + case SC_CONCENTRATION: status_change_end(bl, SC_HIDING, INVALID_TIMER); status_change_end(bl, SC_CLOAKING, INVALID_TIMER); status_change_end(bl, SC_CLOAKINGEXCEED, INVALID_TIMER); @@ -10673,7 +10784,7 @@ int status_change_timer_sub(struct block_list* bl, va_list ap) rnd()%100 < 100-tsc->data[SC__SHADOWFORM]->val1*10 ) // [100 - (Skill Level x 10)] % status_change_end(bl, SC__SHADOWFORM, INVALID_TIMER); break; - case SC_SIGHTBLASTER: + case SC_WZ_SIGHTBLASTER: if (battle->check_target( src, bl, BCT_ENEMY ) > 0 && status_check_skilluse(src, bl, WZ_SIGHTBLASTER, 2)) { @@ -10683,11 +10794,11 @@ int status_change_timer_sub(struct block_list* bl, va_list ap) } } break; - case SC_CLOSECONFINE: + case SC_RG_CCONFINE_M: //Lock char has released the hold on everyone... - if (tsc && tsc->data[SC_CLOSECONFINE2] && tsc->data[SC_CLOSECONFINE2]->val2 == src->id) { - tsc->data[SC_CLOSECONFINE2]->val2 = 0; - status_change_end(bl, SC_CLOSECONFINE2, INVALID_TIMER); + if (tsc && tsc->data[SC_RG_CCONFINE_S] && tsc->data[SC_RG_CCONFINE_S]->val2 == src->id) { + tsc->data[SC_RG_CCONFINE_S]->val2 = 0; + status_change_end(bl, SC_RG_CCONFINE_S, INVALID_TIMER); } break; case SC_CURSEDCIRCLE_TARGET: @@ -10700,6 +10811,131 @@ int status_change_timer_sub(struct block_list* bl, va_list ap) return 0; } +#ifdef RENEWAL +int status_get_total_def(struct block_list *src){ return status_get_status_data(src)->def2 + (short)status_get_def(src); } +int status_get_total_mdef(struct block_list *src){ return status_get_status_data(src)->mdef2 + (short)status_get_mdef(src); } +int status_get_weapon_atk(struct block_list *bl, struct weapon_atk *watk, int flag){ + int min = 0, max = 0, dstr; + float strdex_bonus, variance; + struct status_change *sc = status_get_sc(bl); + struct status_data *status = status_get_status_data(bl); + + if ( bl->type == BL_PC && watk->atk ){ + if ( flag&16 ) + dstr = status_get_dex(bl); + else + dstr = status_get_str(bl); + + variance = 5.0f * watk->atk * watk->wlv / 100.0f; + strdex_bonus = watk->atk * dstr / 200.0f; + + min = (watk->atk - (int)(variance + strdex_bonus)) + watk->atk2; + max = (watk->atk + (int)(variance + strdex_bonus)) + watk->atk2; + }else if( watk->atk ){ + min = watk->atk * 80 / 100; + max = watk->atk * 120 / 100; + } + + if( !(flag&1) ){ + if( max > min ) + max = min + rnd()%(max - min); + else + max = min; + } + + if( bl->type == BL_PC && ((TBL_PC*)bl)->right_weapon.overrefine > 0) + max += rnd()%((TBL_PC*)bl)->right_weapon.overrefine + 1; + + max = status_calc_watk(bl, sc, max, false); + + return max; +} +#endif + +#define GETRANDMATK(){\ + if( status->matk_max > status->matk_min )\ + return status->matk_min + rnd()%(status->matk_max - status->matk_min);\ + else\ + return status->matk_min;\ +} + +/*========================================== + * flag [malufett] + * 0 - update matk values + * 1 - get matk w/o SC bonuses + * 2 - get modified matk + * 3 - get matk w/o eatk & SC bonuses + *------------------------------------------*/ +int status_get_matk(struct block_list *bl, int flag){ + struct status_data *status; + struct status_change *sc; + struct map_session_data *sd; + + if( bl == NULL ) + return 1; + + status = status_get_status_data(bl); + sc = status_get_sc(bl); + sd = BL_CAST(BL_PC, bl); + + if( flag == 2 ) // just get matk + GETRANDMATK(); + +#ifndef RENEWAL + status->matk_min = status_base_matk_min(status) + (sd?sd->bonus.ematk:0); + status->matk_max = status_base_matk_max(status) + (sd?sd->bonus.ematk:0); +#else + /** + * RE MATK Formula (from irowiki:http://irowiki.org/wiki/MATK) + * MATK = (sMATK + wMATK + eMATK) * Multiplicative Modifiers + **/ + status->matk_min = status_base_matk(status, status_get_lv(bl)); + + // Any +MATK you get from skills and cards, including cards in weapon, is added here. + if( sd && sd->bonus.ematk > 0 && flag != 3 ) + status->matk_min += sd->bonus.ematk; + if( flag != 3 ) + status->matk_min = status_calc_ematk(bl, sc, status->matk_min); + + status->matk_max = status->matk_min; + + //This is the only portion in MATK that varies depending on the weapon level and refinement rate. + if( bl->type&BL_PC && (status->rhw.matk + status->lhw.matk) > 0 ){ + int wMatk = status->rhw.matk + status->lhw.matk; // Left and right matk stacks + int variance = wMatk * status->rhw.wlv / 10; // Only use right hand weapon level + status->matk_min += wMatk - variance; + status->matk_max += wMatk + variance; + }else if( bl->type&BL_MOB ){ + status->matk_min = status->matk_max = status_get_int(bl) + status_get_lv(bl); + status->matk_min += 70 * ((TBL_MOB*)bl)->status.rhw.atk2 / 100; + status->matk_max += 130 * ((TBL_MOB*)bl)->status.rhw.atk2 / 100; + } +#endif + if (bl->type&BL_PC && sd->matk_rate != 100) { + status->matk_max = status->matk_max * sd->matk_rate/100; + status->matk_min = status->matk_min * sd->matk_rate/100; + } + + if ((bl->type&BL_HOM && battle_config.hom_setting&0x20) //Hom Min Matk is always the same as Max Matk + || sc->data[SC_RECOGNIZEDSPELL]) + status->matk_min = status->matk_max; + +#ifdef RENEWAL + if( sd && sd->right_weapon.overrefine > 0){ + status->matk_min++; + status->matk_max += sd->right_weapon.overrefine - 1; + } +#endif + + if( flag ) // get unmodified from sc matk + GETRANDMATK(); + + status->matk_min = status_calc_matk(bl, sc, status->matk_min, true); + status->matk_max = status_calc_matk(bl, sc, status->matk_max, true); + + return 0; +} + /*========================================== * Clears buffs/debuffs of a character. * type&1 -> buffs, type&2 -> debuffs @@ -10719,70 +10955,18 @@ int status_change_clear_buffs (struct block_list* bl, int type) for( i = SC_COMMON_MAX+1; i < SC_MAX; i++ ) { - if(!sc->data[i]) + if( !sc->data[i] || !status_get_sc_type(i) ) continue; - switch (i) { - //Stuff that cannot be removed - case SC_WEIGHT50: - case SC_WEIGHT90: - case SC_COMBO: - case SC_SMA: - case SC_DANCING: - case SC_LEADERSHIP: - case SC_GLORYWOUNDS: - case SC_SOULCOLD: - case SC_HAWKEYES: - case SC_GUILDAURA: - case SC_SAFETYWALL: - case SC_PNEUMA: - case SC_NOCHAT: - case SC_JAILED: - case SC_ANKLE: - case SC_BLADESTOP: - case SC_CP_WEAPON: - case SC_CP_SHIELD: - case SC_CP_ARMOR: - case SC_CP_HELM: - case SC_STRFOOD: - case SC_AGIFOOD: - case SC_VITFOOD: - case SC_INTFOOD: - case SC_DEXFOOD: - case SC_LUKFOOD: - case SC_HITFOOD: - case SC_FLEEFOOD: - case SC_BATKFOOD: - case SC_WATKFOOD: - case SC_MATKFOOD: - case SC_FOOD_STR_CASH: - case SC_FOOD_AGI_CASH: - case SC_FOOD_VIT_CASH: - case SC_FOOD_DEX_CASH: - case SC_FOOD_INT_CASH: - case SC_FOOD_LUK_CASH: - case SC_EXPBOOST: - case SC_JEXPBOOST: - case SC_ITEMBOOST: - case SC_ELECTRICSHOCKER: - case SC__MANHOLE: - case SC_GIANTGROWTH: - case SC_MILLENNIUMSHIELD: - case SC_REFRESH: - case SC_STONEHARDSKIN: - case SC_VITALITYACTIVATION: - case SC_FIGHTINGSPIRIT: - case SC_ABUNDANCE: - case SC_CURSEDCIRCLE_ATKER: - case SC_CURSEDCIRCLE_TARGET: - case SC_PUSH_CART: - case SC_ALL_RIDING: - continue; + if( type&1 && !(status_get_sc_type(i)&SC_BUFF) ) + continue; - //Debuffs that can be removed. - case SC_DEEPSLEEP: - case SC_BURNING: - case SC_FREEZING: + if( type&2 && !(status_get_sc_type(i)&SC_DEBUFF) ) + continue; + + switch (i) { + case SC_DEEP_SLEEP: + case SC_FROSTMISTY: case SC_CRYSTALIZE: case SC_TOXIN: case SC_PARALYSE: @@ -10797,40 +10981,13 @@ int status_change_clear_buffs (struct block_list* bl, int type) if(!(type&4)) continue; break; - case SC_HALLUCINATION: - case SC_QUAGMIRE: - case SC_SIGNUMCRUCIS: - case SC_DECREASEAGI: - case SC_SLOWDOWN: - case SC_MINDBREAKER: - case SC_WINKCHARM: - case SC_STOP: - case SC_ORCISH: - case SC_STRIPWEAPON: - case SC_STRIPSHIELD: - case SC_STRIPARMOR: - case SC_STRIPHELM: - case SC_BITE: - case SC_ADORAMUS: - case SC_VACUUM_EXTREME: - case SC_FEAR: - case SC_MAGNETICFIELD: - case SC_NETHERWORLD: - if (!(type&2)) - continue; - break; - //The rest are buffs that can be removed. case SC__BLOODYLUST: case SC_BERSERK: - case SC_SATURDAYNIGHTFEVER: - if (!(type&1)) + case SC_SATURDAY_NIGHT_FEVER: + if(type&4) continue; sc->data[i]->val2 = 0; break; - default: - if (!(type&1)) - continue; - break; } status_change_end(bl, (sc_type)i, INVALID_TIMER); } @@ -10861,21 +11018,21 @@ int status_change_spread( struct block_list *src, struct block_list *bl ) { case SC_CONFUSION: case SC_BLIND: case SC_NOCHAT: - case SC_HALLUCINATION: - case SC_SIGNUMCRUCIS: - case SC_DECREASEAGI: + case SC_ILLUSION: + case SC_CRUCIS: + case SC_DEC_AGI: case SC_SLOWDOWN: case SC_MINDBREAKER: - case SC_WINKCHARM: + case SC_DC_WINKCHARM: case SC_STOP: case SC_ORCISH: - //case SC_STRIPWEAPON://Omg I got infected and had the urge to strip myself physically. - //case SC_STRIPSHIELD://No this is stupid and shouldnt be spreadable at all. - //case SC_STRIPARMOR:// Disabled until I can confirm if it does or not. [Rytech] - //case SC_STRIPHELM: - //case SC__STRIPACCESSORY: - case SC_BITE: - case SC_FREEZING: + //case SC_NOEQUIPWEAPON://Omg I got infected and had the urge to strip myself physically. + //case SC_NOEQUIPSHIELD://No this is stupid and shouldnt be spreadable at all. + //case SC_NOEQUIPARMOR:// Disabled until I can confirm if it does or not. [Rytech] + //case SC_NOEQUIPHELM: + //case SC__STRIPACCESSARY: + case SC_WUGBITE: + case SC_FROSTMISTY: case SC_VENOMBLEED: case SC_DEATHHURT: case SC_PARALYSE: @@ -10907,7 +11064,7 @@ int status_change_spread( struct block_list *src, struct block_list *bl ) { data.tick = sc->data[i]->val4 * 4000; break; case SC_TOXIN: - case SC_BLEEDING: + case SC_BLOODING: data.tick = sc->data[i]->val4 * 10000; break; default: @@ -11142,6 +11299,13 @@ int status_get_refine_chance(enum refine_type wlv, int refine) { return refine_info[wlv].chance[refine]; } +int status_get_sc_type(sc_type type) { + + if( type <= SC_NONE || type >= SC_MAX ) + return 0; + + return sc_conf[type]; +} /*------------------------------------------ * DB reading. @@ -11244,6 +11408,20 @@ static bool status_readdb_refine(char* fields[], int columns, int current) return true; } +static bool status_readdb_scconfig(char* fields[], int columns, int current) +{ + int val = 0; + char* type = fields[0]; + + if( !script_get_constant(type, &val) ){ + ShowWarning("status_readdb_sc_conf: Invalid status type %s specified.\n", type); + return false; + } + + sc_conf[val] = (int)strtol(fields[1], NULL, 0); + + return true; +} /* * Read status db * job1.txt @@ -11295,6 +11473,7 @@ int status_readdb(void) sv->readdb(iMap->db_path, "job_db2.txt", ',', 1, 1+MAX_LEVEL, -1, &status_readdb_job2); sv->readdb(iMap->db_path, "size_fix.txt", ',', MAX_WEAPON_TYPE, MAX_WEAPON_TYPE, ARRAYLENGTH(atkmods), &status_readdb_sizefix); sv->readdb(iMap->db_path, DBPATH"refine_db.txt", ',', 4+MAX_REFINE, 4+MAX_REFINE, ARRAYLENGTH(refine_info), &status_readdb_refine); + sv->readdb(iMap->db_path, "sc_config.txt", ',', 2, 2, SC_MAX, &status_readdb_scconfig); return 0; } diff --git a/src/map/status.h b/src/map/status.h index 4a7af884e..617cd9572 100644 --- a/src/map/status.h +++ b/src/map/status.h @@ -31,6 +31,16 @@ enum refine_type { REFINE_TYPE_MAX = 5 }; +typedef enum sc_conf_type { + SC_NO_REM_DEATH = 0x1, + SC_NO_SAVE = 0x2, + SC_NO_DISPELL = 0x4, + SC_NO_CLEARANCE = 0x8, + SC_BUFF = 0x10, + SC_DEBUFF = 0x20, + SC_MADO_NO_RESET = 0x40 +} sc_conf_type; + int status_get_refine_chance(enum refine_type wlv, int refine); // Status changes listing. These code are for use by the server. @@ -48,25 +58,26 @@ typedef enum sc_type { SC_SILENCE, SC_CONFUSION, SC_BLIND, - SC_BLEEDING, - SC_DPOISON, //10 - SC_COMMON_MAX = 10, // end + SC_BLOODING, + SC_DPOISON, + SC_BURNING, //11 + SC_COMMON_MAX = 11, // end //Next up, we continue on 20, to leave enough room for additional "common" ailments in the future. SC_PROVOKE = 20, SC_ENDURE, SC_TWOHANDQUICKEN, - SC_CONCENTRATE, + SC_CONCENTRATION, SC_HIDING, SC_CLOAKING, - SC_ENCPOISON, + SC_ENCHANTPOISON, SC_POISONREACT, SC_QUAGMIRE, SC_ANGELUS, SC_BLESSING, //30 - SC_SIGNUMCRUCIS, - SC_INCREASEAGI, - SC_DECREASEAGI, + SC_CRUCIS, + SC_INC_AGI, + SC_DEC_AGI, SC_SLOWPOISON, SC_IMPOSITIO , SC_SUFFRAGIUM, @@ -75,40 +86,40 @@ typedef enum sc_type { SC_KYRIE, SC_MAGNIFICAT, //40 SC_GLORIA, - SC_AETERNA, + SC_LEXAETERNA, SC_ADRENALINE, - SC_WEAPONPERFECTION, + SC_WEAPONPERFECT, SC_OVERTHRUST, SC_MAXIMIZEPOWER, SC_TRICKDEAD, - SC_LOUD, + SC_SHOUT, SC_ENERGYCOAT, SC_BROKENARMOR, //50 - NOTE: These two aren't used anywhere, and they have an icon... SC_BROKENWEAPON, - SC_HALLUCINATION, - SC_WEIGHT50, - SC_WEIGHT90, - SC_ASPDPOTION0, - SC_ASPDPOTION1, - SC_ASPDPOTION2, - SC_ASPDPOTION3, - SC_SPEEDUP0, - SC_SPEEDUP1, //60 - SC_ATKPOTION, - SC_MATKPOTION, + SC_ILLUSION, + SC_WEIGHTOVER50, + SC_WEIGHTOVER90, + SC_ATTHASTE_POTION1, + SC_ATTHASTE_POTION2, + SC_ATTHASTE_POTION3, + SC_ATTHASTE_INFINITY, + SC_MOVHASTE_HORSE, + SC_MOVHASTE_INFINITY, //60 + SC_PLUSATTACKPOWER, + SC_PLUSMAGICPOWER, SC_WEDDING, SC_SLOWDOWN, - SC_ANKLE, + SC_ANKLESNARE, SC_KEEPING, SC_BARRIER, - SC_STRIPWEAPON, - SC_STRIPSHIELD, - SC_STRIPARMOR, //70 - SC_STRIPHELM, - SC_CP_WEAPON, - SC_CP_SHIELD, - SC_CP_ARMOR, - SC_CP_HELM, + SC_NOEQUIPWEAPON, + SC_NOEQUIPSHIELD, + SC_NOEQUIPARMOR, //70 + SC_NOEQUIPHELM, + SC_PROTECTWEAPON, + SC_PROTECTSHIELD, + SC_PROTECTARMOR, + SC_PROTECTHELM, SC_AUTOGUARD, SC_REFLECTSHIELD, SC_SPLASHER, @@ -126,24 +137,24 @@ typedef enum sc_type { SC_RUWACH, //90 SC_EXTREMITYFIST, SC_EXPLOSIONSPIRITS, - SC_COMBO, + SC_COMBOATTACK, SC_BLADESTOP_WAIT, SC_BLADESTOP, - SC_FIREWEAPON, - SC_WATERWEAPON, - SC_WINDWEAPON, - SC_EARTHWEAPON, + SC_PROPERTYFIRE, + SC_PROPERTYWATER, + SC_PROPERTYWIND, + SC_PROPERTYGROUND, SC_VOLCANO, //100, SC_DELUGE, SC_VIOLENTGALE, SC_WATK_ELEMENT, SC_ARMOR, - SC_ARMOR_ELEMENT, + SC_ARMORPROPERTY, SC_NOCHAT, SC_BABY, SC_AURABLADE, SC_PARRYING, - SC_CONCENTRATION, //110 + SC_LKCONCENTRATION, //110 SC_TENSIONRELAX, SC_BERSERK, SC_FURY, @@ -158,10 +169,10 @@ typedef enum sc_type { SC_MELTDOWN, SC_CARTBOOST, SC_CHASEWALK, - SC_REJECTSWORD, + SC_SWORDREJECT, + SC_MARIONETTE_MASTER, SC_MARIONETTE, - SC_MARIONETTE2, - SC_CHANGEUNDEAD, + SC_PROPERTYUNDEAD, SC_JOINTBEAT, SC_MINDBREAKER, //130 SC_MEMORIZE, @@ -171,39 +182,40 @@ typedef enum sc_type { SC_SACRIFICE, SC_STEELBODY, SC_ORCISH, - SC_READYSTORM, - SC_READYDOWN, - SC_READYTURN, //140 - SC_READYCOUNTER, - SC_DODGE, + SC_STORMKICK_READY, + SC_DOWNKICK_READY, + SC_TURNKICK_READY, //140 + SC_COUNTERKICK_READY, + SC_DODGE_READY, SC_RUN, - SC_SHADOWWEAPON, + SC_PROPERTYDARK, SC_ADRENALINE2, - SC_GHOSTWEAPON, + SC_PROPERTYTELEKINESIS, SC_KAIZEL, SC_KAAHI, SC_KAUPE, - SC_ONEHAND, //150 + SC_ONEHANDQUICKEN, //150 SC_PRESERVE, - SC_BATTLEORDERS, - SC_REGENERATION, - SC_DOUBLECAST, + SC_GDSKILL_BATTLEORDER, + SC_GDSKILL_REGENERATION, + SC_DOUBLECASTING, SC_GRAVITATION, - SC_MAXOVERTHRUST, + SC_OVERTHRUSTMAX, SC_LONGING, SC_HERMODE, - SC_SHRINK, - SC_SIGHTBLASTER, //160 - SC_WINKCHARM, - SC_CLOSECONFINE, - SC_CLOSECONFINE2, + SC_TAROTCARD, + SC_CR_SHRINK, //160 + SC_WZ_SIGHTBLASTER, + SC_DC_WINKCHARM, + SC_RG_CCONFINE_M, + SC_RG_CCONFINE_S, SC_DANCING, - SC_ELEMENTALCHANGE, + SC_ARMOR_PROPERTY, SC_RICHMANKIM, SC_ETERNALCHAOS, SC_DRUMBATTLE, - SC_NIBELUNGEN, - SC_ROKISWEIL, //170 + SC_NIBELUNGEN, //170 + SC_ROKISWEIL, SC_INTOABYSS, SC_SIEGFRIED, SC_WHISTLE, @@ -212,18 +224,18 @@ typedef enum sc_type { SC_APPLEIDUN, SC_MODECHANGE, SC_HUMMING, - SC_DONTFORGETME, - SC_FORTUNE, //180 - SC_SERVICE4U, + SC_DONTFORGETME, //180 + SC_FORTUNE, + SC_SERVICEFORYOU, SC_STOP, //Prevents inflicted chars from walking. [Skotlex] - SC_SPURT, - SC_SPIRIT, + SC_STRUP, + SC_SOULLINK, SC_COMA, //Not a real SC_, it makes a char's HP/SP hit 1. - SC_INTRAVISION, + SC_CLAIRVOYANCE, SC_INCALLSTATUS, - SC_INCSTR, - SC_INCAGI, - SC_INCVIT, //190 + SC_CHASEWALK2, + SC_INCAGI, //190 + SC_INCVIT, SC_INCINT, SC_INCDEX, SC_INCLUK, @@ -232,18 +244,18 @@ typedef enum sc_type { SC_INCFLEE, SC_INCFLEERATE, SC_INCMHPRATE, - SC_INCMSPRATE, - SC_INCATKRATE, //200 + SC_INCMSPRATE, //200 + SC_INCATKRATE, SC_INCMATKRATE, SC_INCDEFRATE, - SC_STRFOOD, - SC_AGIFOOD, - SC_VITFOOD, - SC_INTFOOD, - SC_DEXFOOD, - SC_LUKFOOD, - SC_HITFOOD, - SC_FLEEFOOD, //210 + SC_FOOD_STR, + SC_FOOD_AGI, + SC_FOOD_VIT, + SC_FOOD_INT, + SC_FOOD_DEX, + SC_FOOD_LUK, + SC_FOOD_BASICHIT, //210 + SC_FOOD_BASICAVOIDANCE, SC_BATKFOOD, SC_WATKFOOD, SC_MATKFOOD, @@ -252,8 +264,8 @@ typedef enum sc_type { SC_WARM, //SG skills [Komurka] SC_SUN_COMFORT, SC_MOON_COMFORT, - SC_STAR_COMFORT, - SC_FUSION, //220 + SC_STAR_COMFORT, //220 + SC_FUSION, SC_SKILLRATE_UP, SC_SKE, SC_KAITE, @@ -261,82 +273,82 @@ typedef enum sc_type { SC_SKA, // [marquis007] SC_EARTHSCROLL, SC_MIRACLE, //SG 'hidden' skill [Komurka] - SC_MADNESSCANCEL, - SC_ADJUSTMENT, - SC_INCREASING, //230 - SC_GATLINGFEVER, - SC_TATAMIGAESHI, - SC_UTSUSEMI, - SC_BUNSINJYUTSU, - SC_KAENSIN, - SC_SUITON, - SC_NEN, + SC_GS_MADNESSCANCEL, + SC_GS_ADJUSTMENT, //230 + SC_GS_ACCURACY, + SC_GS_GATLINGFEVER, + SC_NJ_TATAMIGAESHI, + SC_NJ_UTSUSEMI, + SC_NJ_BUNSINJYUTSU, + SC_NJ_KAENSIN, + SC_NJ_SUITON, + SC_NJ_NEN, SC_KNOWLEDGE, - SC_SMA, - SC_FLING, //240 - SC_AVOID, - SC_CHANGE, - SC_BLOODLUST, - SC_FLEET, - SC_SPEED, - SC_DEFENCE, + SC_SMA_READY, //240 + SC_FLING, + SC_HLIF_AVOID, + SC_HLIF_CHANGE, + SC_HAMI_BLOODLUST, + SC_HLIF_FLEET, + SC_HLIF_SPEED, + SC_HAMI_DEFENCE, SC_INCASPDRATE, - SC_INCFLEE2 = 248, - SC_JAILED, - SC_ENCHANTARMS, //250 + SC_PLUSAVOIDVALUE, + SC_JAILED, //250 + SC_ENCHANTARMS, SC_MAGICALATTACK, - SC_ARMORCHANGE, + SC_STONESKIN, SC_CRITICALWOUND, SC_MAGICMIRROR, SC_SLOWCAST, SC_SUMMER, - SC_EXPBOOST, - SC_ITEMBOOST, - SC_BOSSMAPINFO, - SC_LIFEINSURANCE, //260 - SC_INCCRI, + SC_CASH_PLUSEXP, + SC_CASH_RECEIVEITEM, + SC_CASH_BOSS_ALARM, //260 + SC_CASH_DEATHPENALTY, + SC_CRITICALPERCENT, //SC_INCDEF, - //SC_INCBASEATK = 263, + //SC_INCBASEATK = 264, //SC_FASTCAST, - SC_MDEF_RATE = 265, + SC_PROTECT_MDEF = 266, //SC_HPREGEN, - SC_INCHEALRATE = 267, + SC_HEALPLUS = 268, SC_PNEUMA, - SC_AUTOTRADE, - SC_KSPROTECTED, //270 - SC_ARMOR_RESIST = 271, - SC_SPCOST_RATE, - SC_COMMONSC_RESIST, - SC_SEVENWIND, - SC_DEF_RATE, + SC_AUTOTRADE, //270 + SC_KSPROTECTED, + SC_ARMOR_RESIST, + SC_ATKER_BLOOD, + SC_TARGET_BLOOD, + SC_TK_SEVENWIND, + SC_PROTECT_DEF, //SC_SPREGEN, - SC_WALKSPEED = 277, + SC_WALKSPEED = 278, // Mercenary Only Bonus Effects - SC_MERC_FLEEUP, - SC_MERC_ATKUP, - SC_MERC_HPUP, //280 - SC_MERC_SPUP, - SC_MERC_HITUP, - SC_MERC_QUICKEN, + SC_MER_FLEE, + SC_MER_ATK, //280 + SC_MER_HP, + SC_MER_SP, + SC_MER_HIT, + SC_MER_QUICKEN, SC_REBIRTH, - //SC_SKILLCASTRATE, //285 + //SC_SKILLCASTRATE, //286 //SC_DEFRATIOATK, //SC_HPDRAIN, //SC_SKILLATKBONUS, - SC_ITEMSCRIPT = 289, - SC_S_LIFEPOTION, //290 + SC_ITEMSCRIPT = 290, + SC_S_LIFEPOTION, SC_L_LIFEPOTION, - SC_JEXPBOOST, + SC_CASH_PLUSONLYJOBEXP, //SC_IGNOREDEF, - SC_HELLPOWER = 294, - SC_INVINCIBLE, //295 + SC_HELLPOWER = 295, + SC_INVINCIBLE, SC_INVINCIBLEOFF, SC_MANU_ATK, SC_MANU_DEF, - SC_SPL_ATK, - SC_SPL_DEF, //300 + SC_SPL_ATK, //300 + SC_SPL_DEF, SC_MANU_MATK, SC_SPL_MATK, SC_FOOD_STR_CASH, @@ -344,25 +356,24 @@ typedef enum sc_type { SC_FOOD_VIT_CASH, SC_FOOD_DEX_CASH, SC_FOOD_INT_CASH, - SC_FOOD_LUK_CASH,//308 + SC_FOOD_LUK_CASH, /** * 3rd **/ - SC_FEAR,//309 - SC_BURNING,//310 - SC_FREEZING,//311 + SC_FEAR, + SC_FROSTMISTY, /** * Rune Knight **/ - SC_ENCHANTBLADE,//312 - SC_DEATHBOUND,//313 + SC_ENCHANTBLADE, + SC_DEATHBOUND, SC_MILLENNIUMSHIELD, - SC_CRUSHSTRIKE,//315 + SC_CRUSHSTRIKE, SC_REFRESH, SC_REUSE_REFRESH, SC_GIANTGROWTH, SC_STONEHARDSKIN, - SC_VITALITYACTIVATION,//320 + SC_VITALITYACTIVATION, SC_STORMBLAST, SC_FIGHTINGSPIRIT, SC_ABUNDANCE, @@ -370,12 +381,12 @@ typedef enum sc_type { * Arch Bishop **/ SC_ADORAMUS, - SC_EPICLESIS,//325 + SC_EPICLESIS, SC_ORATIO, SC_LAUDAAGNUS, SC_LAUDARAMUS, SC_RENOVATIO, - SC_EXPIATIO,//330 + SC_EXPIATIO, SC_DUPLELIGHT, SC_SECRAMENT, /** @@ -383,38 +394,38 @@ typedef enum sc_type { **/ SC_WHITEIMPRISON, SC_MARSHOFABYSS, - SC_RECOGNIZEDSPELL,//335 + SC_RECOGNIZEDSPELL, SC_STASIS, - SC_SPHERE_1, - SC_SPHERE_2, - SC_SPHERE_3, - SC_SPHERE_4,//340 - SC_SPHERE_5, + SC_SUMMON1, + SC_SUMMON2, + SC_SUMMON3, + SC_SUMMON4, + SC_SUMMON5, SC_READING_SB, - SC_FREEZINGSPELL, + SC_FREEZINGSP, /** * Ranger **/ SC_FEARBREEZE, - SC_ELECTRICSHOCKER,//345 + SC_ELECTRICSHOCKER, SC_WUGDASH, - SC_BITE, + SC_WUGBITE, SC_CAMOUFLAGE, /** * Mechanic **/ SC_ACCELERATION, - SC_HOVERING,//350 + SC_HOVERING, SC_SHAPESHIFT, SC_INFRAREDSCAN, SC_ANALYZE, SC_MAGNETICFIELD, - SC_NEUTRALBARRIER,//355 + SC_NEUTRALBARRIER, SC_NEUTRALBARRIER_MASTER, SC_STEALTHFIELD, SC_STEALTHFIELD_MASTER, SC_OVERHEAT, - SC_OVERHEAT_LIMITPOINT,//360 + SC_OVERHEAT_LIMITPOINT, /** * Guillotine Cross **/ @@ -422,30 +433,30 @@ typedef enum sc_type { SC_POISONINGWEAPON, SC_WEAPONBLOCKING, SC_CLOAKINGEXCEED, - SC_HALLUCINATIONWALK,//365 + SC_HALLUCINATIONWALK, SC_HALLUCINATIONWALK_POSTDELAY, SC_ROLLINGCUTTER, SC_TOXIN, SC_PARALYSE, - SC_VENOMBLEED,//370 + SC_VENOMBLEED, SC_MAGICMUSHROOM, SC_DEATHHURT, SC_PYREXIA, SC_OBLIVIONCURSE, - SC_LEECHESEND,//375 + SC_LEECHESEND, /** * Royal Guard **/ - SC_REFLECTDAMAGE, + SC_LG_REFLECTDAMAGE, SC_FORCEOFVANGUARD, SC_SHIELDSPELL_DEF, SC_SHIELDSPELL_MDEF, - SC_SHIELDSPELL_REF,//380 + SC_SHIELDSPELL_REF, SC_EXEEDBREAK, SC_PRESTIGE, SC_BANDING, SC_BANDING_DEFENCE, - SC_EARTHDRIVE,//385 + SC_EARTHDRIVE, SC_INSPIRATION, /** * Sorcerer @@ -453,30 +464,30 @@ typedef enum sc_type { SC_SPELLFIST, SC_CRYSTALIZE, SC_STRIKING, - SC_WARMER,//390 + SC_WARMER, SC_VACUUM_EXTREME, SC_PROPERTYWALK, /** * Minstrel / Wanderer **/ - SC_SWINGDANCE, - SC_SYMPHONYOFLOVER, - SC_MOONLITSERENADE,//395 - SC_RUSHWINDMILL, + SC_SWING, + SC_SYMPHONY_LOVE, + SC_MOONLIT_SERENADE, + SC_RUSH_WINDMILL, SC_ECHOSONG, SC_HARMONIZE, - SC_VOICEOFSIREN, - SC_DEEPSLEEP,//400 + SC_SIREN, + SC_DEEP_SLEEP, SC_SIRCLEOFNATURE, SC_GLOOMYDAY, SC_GLOOMYDAY_SK, - SC_SONGOFMANA, - SC_DANCEWITHWUG,//405 - SC_SATURDAYNIGHTFEVER, - SC_LERADSDEW, + SC_SONG_OF_MANA, + SC_DANCE_WITH_WUG, + SC_SATURDAY_NIGHT_FEVER, + SC_LERADS_DEW, SC_MELODYOFSINK, - SC_BEYONDOFWARCRY, - SC_UNLIMITEDHUMMINGVOICE,//410 + SC_BEYOND_OF_WARCRY, + SC_UNLIMITED_HUMMING_VOICE, SC_SITDOWN_FORCE, SC_NETHERWORLD, /** @@ -485,35 +496,35 @@ typedef enum sc_type { SC_CRESCENTELBOW, SC_CURSEDCIRCLE_ATKER, SC_CURSEDCIRCLE_TARGET, - SC_LIGHTNINGWALK,//416 + SC_LIGHTNINGWALK, SC_RAISINGDRAGON, - SC_GT_ENERGYGAIN, - SC_GT_CHANGE, - SC_GT_REVITALIZE, + SC_GENTLETOUCH_ENERGYGAIN, + SC_GENTLETOUCH_CHANGE, + SC_GENTLETOUCH_REVITALIZE, /** * Genetic **/ - SC_GN_CARTBOOST,//427 - SC_THORNSTRAP, - SC_BLOODSUCKER, - SC_SMOKEPOWDER, - SC_TEARGAS, - SC_MANDRAGORA,//426 + SC_GN_CARTBOOST, + SC_THORNS_TRAP, + SC_BLOOD_SUCKER, + SC_FIRE_EXPANSION_SMOKE_POWDER, + SC_FIRE_EXPANSION_TEAR_GAS, + SC_MANDRAGORA, SC_STOMACHACHE, SC_MYSTERIOUS_POWDER, SC_MELON_BOMB, SC_BANANA_BOMB, - SC_BANANA_BOMB_SITDOWN,//431 + SC_BANANA_BOMB_SITDOWN_POSTDELAY, SC_SAVAGE_STEAK, SC_COCKTAIL_WARG_BLOOD, SC_MINOR_BBQ, SC_SIROMA_ICE_TEA, - SC_DROCERA_HERB_STEAMED,//436 + SC_DROCERA_HERB_STEAMED, SC_PUTTI_TAILS_NOODLES, SC_BOOST500, SC_FULL_SWING_K, SC_MANA_PLUS, - SC_MUSTLE_M,//441 + SC_MUSTLE_M, SC_LIFE_FORCE_F, SC_EXTRACT_WHITE_POTION_Z, SC_VITATA_500, @@ -521,21 +532,21 @@ typedef enum sc_type { /** * Shadow Chaser **/ - SC__REPRODUCE,//446 + SC__REPRODUCE, SC__AUTOSHADOWSPELL, SC__SHADOWFORM, SC__BODYPAINT, SC__INVISIBILITY, - SC__DEADLYINFECT,//451 + SC__DEADLYINFECT, SC__ENERVATION, SC__GROOMY, SC__IGNORANCE, SC__LAZINESS, - SC__UNLUCKY,//456 + SC__UNLUCKY, SC__WEAKNESS, - SC__STRIPACCESSORY, + SC__STRIPACCESSARY, SC__MANHOLE, - SC__BLOODYLUST,//460 + SC__BLOODYLUST, /** * Elemental Spirits **/ @@ -543,61 +554,60 @@ typedef enum sc_type { SC_CIRCLE_OF_FIRE_OPTION, SC_FIRE_CLOAK, SC_FIRE_CLOAK_OPTION, - SC_WATER_SCREEN,//465 + SC_WATER_SCREEN, SC_WATER_SCREEN_OPTION, SC_WATER_DROP, SC_WATER_DROP_OPTION, SC_WATER_BARRIER, - SC_WIND_STEP,//470 + SC_WIND_STEP, SC_WIND_STEP_OPTION, SC_WIND_CURTAIN, SC_WIND_CURTAIN_OPTION, SC_ZEPHYR, - SC_SOLID_SKIN,//475 + SC_SOLID_SKIN, SC_SOLID_SKIN_OPTION, SC_STONE_SHIELD, SC_STONE_SHIELD_OPTION, SC_POWER_OF_GAIA, - SC_PYROTECHNIC,//480 + SC_PYROTECHNIC, SC_PYROTECHNIC_OPTION, SC_HEATER, SC_HEATER_OPTION, SC_TROPIC, - SC_TROPIC_OPTION,//485 + SC_TROPIC_OPTION, SC_AQUAPLAY, SC_AQUAPLAY_OPTION, SC_COOLER, SC_COOLER_OPTION, - SC_CHILLY_AIR,//490 + SC_CHILLY_AIR, SC_CHILLY_AIR_OPTION, SC_GUST, SC_GUST_OPTION, SC_BLAST, - SC_BLAST_OPTION,//495 + SC_BLAST_OPTION, SC_WILD_STORM, SC_WILD_STORM_OPTION, SC_PETROLOGY, SC_PETROLOGY_OPTION, - SC_CURSED_SOIL,//500 + SC_CURSED_SOIL, SC_CURSED_SOIL_OPTION, SC_UPHEAVAL, SC_UPHEAVAL_OPTION, SC_TIDAL_WEAPON, - SC_TIDAL_WEAPON_OPTION,//505 + SC_TIDAL_WEAPON_OPTION, SC_ROCK_CRUSHER, SC_ROCK_CRUSHER_ATK, /* Guild Aura */ SC_LEADERSHIP, SC_GLORYWOUNDS, - SC_SOULCOLD, //508 + SC_SOULCOLD, SC_HAWKEYES, /* ... */ SC_ODINS_POWER, - SC_RAID, /* Sorcerer .extra */ SC_FIRE_INSIGNIA, SC_WATER_INSIGNIA, - SC_WIND_INSIGNIA, //516 + SC_WIND_INSIGNIA, SC_EARTH_INSIGNIA, /* new pushcart */ SC_PUSH_CART, @@ -610,22 +620,22 @@ typedef enum sc_type { SC_SPELLBOOK6, /** * In official server there are only 7 maximum number of spell books that can be memorized - * To increase the maximum value just add another status type before SC_MAXSPELLBOOK (ex. SC_SPELLBOOK7, SC_SPELLBOOK8 and so on) + * To increase the maximum value just add another status type before SC_SPELLBOOK7 (ex. SC_SPELLBOOK8, SC_SPELLBOOK9 and so on) **/ - SC_MAXSPELLBOOK, + SC_SPELLBOOK7, /* Max HP & SP */ SC_INCMHP, SC_INCMSP, - SC_PARTYFLEE, // 531 + SC_PARTYFLEE, /** * Kagerou & Oboro [malufett] **/ SC_MEIKYOUSISUI, - SC_JYUMONJIKIRI, + SC_KO_JYUMONJIKIRI, SC_KYOUGAKU, SC_IZAYOI, SC_ZENKAI, - SC_KAGEHUMI, + SC_KG_KAGEHUMI, SC_KYOMU, SC_KAGEMUSYA, SC_ZANGETSU, @@ -639,17 +649,24 @@ typedef enum sc_type { SC_ERASER_CUTTER, SC_OVERED_BOOST, SC_LIGHT_OF_REGENE, - SC_ASH, + SC_VOLCANIC_ASH, SC_GRANITIC_ARMOR, SC_MAGMA_FLOW, SC_PYROCLASTIC, - SC_PARALYSIS, + SC_NEEDLE_OF_PARALYZE, SC_PAIN_KILLER, - - #ifdef RENEWAL SC_EXTREMITYFIST2, + SC_RAID, #endif + SC_DARKCROW = 553, + SC_FULL_THROTTLE, + SC_REBOUND, + SC_UNLIMIT, + SC_KINGS_GRACE, + SC_TELEKINESIS_INTENSE, + SC_OFFERTORIUM, + SC_FRIGG_SONG, SC_ALL_RIDING, SC_HANBOK, @@ -660,66 +677,66 @@ typedef enum sc_type { // Official status change ids, used to display status icons on the client. enum si_type { SI_BLANK = -1, - SI_PROVOKE = 0, - SI_ENDURE = 1, - SI_TWOHANDQUICKEN = 2, - SI_CONCENTRATE = 3, - SI_HIDING = 4, - SI_CLOAKING = 5, - SI_ENCPOISON = 6, - SI_POISONREACT = 7, - SI_QUAGMIRE = 8, - SI_ANGELUS = 9, - SI_BLESSING = 10, - SI_SIGNUMCRUCIS = 11, - SI_INCREASEAGI = 12, - SI_DECREASEAGI = 13, - SI_SLOWPOISON = 14, - SI_IMPOSITIO = 15, - SI_SUFFRAGIUM = 16, - SI_ASPERSIO = 17, - SI_BENEDICTIO = 18, - SI_KYRIE = 19, - SI_MAGNIFICAT = 20, - SI_GLORIA = 21, - SI_AETERNA = 22, - SI_ADRENALINE = 23, - SI_WEAPONPERFECTION = 24, - SI_OVERTHRUST = 25, - SI_MAXIMIZEPOWER = 26, - SI_RIDING = 27, - SI_FALCON = 28, - SI_TRICKDEAD = 29, - SI_LOUD = 30, - SI_ENERGYCOAT = 31, - SI_BROKENARMOR = 32, - SI_BROKENWEAPON = 33, - SI_HALLUCINATION = 34, - SI_WEIGHT50 = 35, - SI_WEIGHT90 = 36, - SI_ASPDPOTION0 = 37, - SI_ASPDPOTION1 = 38, - SI_ASPDPOTION2 = 39, - SI_ASPDPOTIONINFINITY = 40, - SI_SPEEDPOTION1 = 41, -// SI_MOVHASTE_INFINITY = 42, + SI_PROVOKE = 0, + SI_ENDURE = 1, + SI_TWOHANDQUICKEN = 2, + SI_CONCENTRATION = 3, + SI_HIDING = 4, + SI_CLOAKING = 5, + SI_ENCHANTPOISON = 6, + SI_POISONREACT = 7, + SI_QUAGMIRE = 8, + SI_ANGELUS = 9, + SI_BLESSING = 10, + SI_CRUCIS = 11, + SI_INC_AGI = 12, + SI_DEC_AGI = 13, + SI_SLOWPOISON = 14, + SI_IMPOSITIO = 15, + SI_SUFFRAGIUM = 16, + SI_ASPERSIO = 17, + SI_BENEDICTIO = 18, + SI_KYRIE = 19, + SI_MAGNIFICAT = 20, + SI_GLORIA = 21, + SI_LEXAETERNA = 22, + SI_ADRENALINE = 23, + SI_WEAPONPERFECT = 24, + SI_OVERTHRUST = 25, + SI_MAXIMIZE = 26, + SI_RIDING = 27, + SI_FALCON = 28, + SI_TRICKDEAD = 29, + SI_SHOUT = 30, + SI_ENERGYCOAT = 31, + SI_BROKENARMOR = 32, + SI_BROKENWEAPON = 33, + SI_ILLUSION = 34, + SI_WEIGHTOVER50 = 35, + SI_WEIGHTOVER90 = 36, + SI_ATTHASTE_POTION1 = 37, + SI_ATTHASTE_POTION2 = 38, + SI_ATTHASTE_POTION3 = 39, + SI_ATTHASTE_INFINITY = 40, + SI_MOVHASTE_POTION = 41, + SI_MOVHASTE_INFINITY = 42, // SI_AUTOCOUNTER = 43, // SI_SPLASHER = 44, -// SI_ANKLESNARE = 45, - SI_ACTIONDELAY = 46, + SI_ANKLESNARE = 45, + SI_POSTDELAY = 46, // SI_NOACTION = 47, // SI_IMPOSSIBLEPICKUP = 48, // SI_BARRIER = 49, - SI_STRIPWEAPON = 50, - SI_STRIPSHIELD = 51, - SI_STRIPARMOR = 52, - SI_STRIPHELM = 53, - SI_CP_WEAPON = 54, - SI_CP_SHIELD = 55, - SI_CP_ARMOR = 56, - SI_CP_HELM = 57, - SI_AUTOGUARD = 58, - SI_REFLECTSHIELD = 59, + SI_NOEQUIPWEAPON = 50, + SI_NOEQUIPSHIELD = 51, + SI_NOEQUIPARMOR = 52, + SI_NOEQUIPHELM = 53, + SI_PROTECTWEAPON = 54, + SI_PROTECTSHIELD = 55, + SI_PROTECTARMOR = 56, + SI_PROTECTHELM = 57, + SI_AUTOGUARD = 58, + SI_REFLECTSHIELD = 59, // SI_DEVOTION = 60, SI_PROVIDENCE = 61, SI_DEFENDER = 62, @@ -750,29 +767,29 @@ enum si_type { SI_STEELBODY = 87, SI_EXTREMITYFIST = 88, // SI_COMBOATTACK = 89, - SI_FIREWEAPON = 90, - SI_WATERWEAPON = 91, - SI_WINDWEAPON = 92, - SI_EARTHWEAPON = 93, + SI_PROPERTYFIRE = 90, + SI_PROPERTYWATER = 91, + SI_PROPERTYWIND = 92, + SI_PROPERTYGROUND = 93, // SI_MAGICATTACK = 94, SI_STOP = 95, // SI_WEAPONBRAKER = 96, - SI_UNDEAD = 97, + SI_PROPERTYUNDEAD = 97, // SI_POWERUP = 98, // SI_AGIUP = 99, // SI_SIEGEMODE = 100, // SI_INVISIBLE = 101, // SI_STATUSONE = 102, - SI_AURABLADE = 103, - SI_PARRYING = 104, - SI_CONCENTRATION = 105, - SI_TENSIONRELAX = 106, + SI_AURABLADE = 103, + SI_PARRYING = 104, + SI_LKCONCENTRATION = 105, + SI_TENSIONRELAX = 106, SI_BERSERK = 107, // SI_SACRIFICE = 108, // SI_GOSPEL = 109, SI_ASSUMPTIO = 110, // SI_BASILICA = 111, - SI_LANDENDOW = 112, + SI_GROUNDMAGIC = 112, SI_MAGICPOWER = 113, SI_EDP = 114, SI_TRUESIGHT = 115, @@ -780,52 +797,52 @@ enum si_type { SI_MELTDOWN = 117, SI_CARTBOOST = 118, // SI_CHASEWALK = 119, - SI_REJECTSWORD = 120, - SI_MARIONETTE = 121, - SI_MARIONETTE2 = 122, - SI_MOONLIT = 123, - SI_BLEEDING = 124, + SI_SWORDREJECT = 120, + SI_MARIONETTE_MASTER = 121, + SI_MARIONETTE = 122, + SI_MOON = 123, + SI_BLOODING = 124, SI_JOINTBEAT = 125, // SI_MINDBREAKER = 126, // SI_MEMORIZE = 127, // SI_FOGWALL = 128, // SI_SPIDERWEB = 129, - SI_BABY = 130, + SI_PROTECTEXP = 130, // SI_SUB_WEAPONPROPERTY = 131, SI_AUTOBERSERK = 132, SI_RUN = 133, - SI_BUMP = 134, - SI_READYSTORM = 135, -// SI_STORMKICK_READY = 136, - SI_READYDOWN = 137, -// SI_DOWNKICK_READY = 138, - SI_READYTURN = 139, -// SI_TURNKICK_READY = 140, - SI_READYCOUNTER = 141, -// SI_COUNTER_READY = 142, - SI_DODGE = 143, -// SI_DODGE_READY = 144, - SI_SPURT = 145, - SI_SHADOWWEAPON = 146, - SI_ADRENALINE2 = 147, - SI_GHOSTWEAPON = 148, - SI_SPIRIT = 149, - SI_PLUSATTACKPOWER = 150, - SI_PLUSMAGICPOWER = 151, - SI_DEVIL = 152, + SI_TING = 134, + SI_STORMKICK_ON = 135, + SI_STORMKICK_READY = 136, + SI_DOWNKICK_ON = 137, + SI_DOWNKICK_READY = 138, + SI_TURNKICK_ON = 139, + SI_TURNKICK_READY = 140, + SI_COUNTER_ON = 141, + SI_COUNTER_READY = 142, + SI_DODGE_ON = 143, + SI_DODGE_READY = 144, + SI_STRUP = 145, + SI_PROPERTYDARK = 146, + SI_ADRENALINE2 = 147, + SI_PROPERTYTELEKINESIS = 148, + SI_SOULLINK = 149, + SI_PLUSATTACKPOWER = 150, + SI_PLUSMAGICPOWER = 151, + SI_DEVIL1 = 152, SI_KAITE = 153, // SI_SWOO = 154, // SI_STAR2 = 155, SI_KAIZEL = 156, SI_KAAHI = 157, SI_KAUPE = 158, - SI_SMA = 159, - SI_NIGHT = 160, - SI_ONEHAND = 161, + SI_SMA_READY = 159, + SI_SKE = 160, + SI_ONEHANDQUICKEN = 161, // SI_FRIEND = 162, // SI_FRIENDUP = 163, // SI_SG_WARM = 164, - SI_WARM = 165, + SI_SG_SUN_WARM = 165, // 166 | The three show the exact same display: ultra red character (165, 166, 167) // 167 | Their names would be SI_SG_SUN_WARM, SI_SG_MOON_WARM, SI_SG_STAR_WARM // SI_EMOTION = 168, @@ -844,34 +861,34 @@ enum si_type { SI_PRESERVE = 181, SI_INCSTR = 182, // SI_NOT_EXTREMITYFIST = 183, - SI_INTRAVISION = 184, + SI_CLAIRVOYANCE = 184, // SI_MOVESLOW_POTION = 185, - SI_DOUBLECAST = 186, + SI_DOUBLECASTING = 186, // SI_GRAVITATION = 187, - SI_MAXOVERTHRUST = 188, + SI_OVERTHRUSTMAX = 188, // SI_LONGING = 189, // SI_HERMODE = 190, - SI_TAROT = 191, // the icon allows no doubt... but what is it really used for ?? [DracoRPG] + SI_TAROTCARD = 191, // the icon allows no doubt... but what is it really used for ?? [DracoRPG] // SI_HLIF_AVOID = 192, // SI_HFLI_FLEET = 193, // SI_HFLI_SPEED = 194, // SI_HLIF_CHANGE = 195, // SI_HAMI_BLOODLUST = 196, - SI_SHRINK = 197, - SI_SIGHTBLASTER = 198, - SI_WINKCHARM = 199, - SI_CLOSECONFINE = 200, - SI_CLOSECONFINE2 = 201, + SI_CR_SHRINK = 197, + SI_WZ_SIGHTBLASTER = 198, + SI_DC_WINKCHARM = 199, + SI_RG_CCONFINE_M = 200, + SI_RG_CCONFINE_S = 201, // SI_DISABLEMOVE = 202, - SI_MADNESSCANCEL = 203, //[blackhole89] - SI_GATLINGFEVER = 204, - SI_EARTHSCROLL = 205, - SI_UTSUSEMI = 206, - SI_BUNSINJYUTSU = 207, - SI_NEN = 208, - SI_ADJUSTMENT = 209, - SI_ACCURACY = 210, -// SI_NJ_SUITON = 211, + SI_GS_MADNESSCANCEL = 203, //[blackhole89] + SI_GS_GATLINGFEVER = 204, + SI_EARTHSCROLL = 205, + SI_NJ_UTSUSEMI = 206, + SI_NJ_BUNSINJYUTSU = 207, + SI_NJ_NEN = 208, + SI_GS_ADJUSTMENT = 209, + SI_GS_ACCURACY = 210, + SI_NJ_SUITON = 211, // SI_PET = 212, // SI_MENTAL = 213, // SI_EXPMEMORY = 214, @@ -901,19 +918,19 @@ enum si_type { // SI_DGAUGE = 238, // SI_DACCEL = 239, // SI_DBLOCK = 240, - SI_FOODSTR = 241, - SI_FOODAGI = 242, - SI_FOODVIT = 243, - SI_FOODDEX = 244, - SI_FOODINT = 245, - SI_FOODLUK = 246, - SI_FOODFLEE = 247, - SI_FOODHIT = 248, - SI_FOODCRI = 249, - SI_EXPBOOST = 250, - SI_LIFEINSURANCE = 251, - SI_ITEMBOOST = 252, - SI_BOSSMAPINFO = 253, + SI_FOOD_STR = 241, + SI_FOOD_AGI = 242, + SI_FOOD_VIT = 243, + SI_FOOD_DEX = 244, + SI_FOOD_INT = 245, + SI_FOOD_LUK = 246, + SI_FOOD_BASICAVOIDANCE = 247, + SI_FOOD_BASICHIT = 248, + SI_FOOD_CRITICALSUCCESSVALUE = 249, + SI_CASH_PLUSEXP = 250, + SI_CASH_DEATHPENALTY = 251, + SI_CASH_RECEIVEITEM = 252, + SI_CASH_BOSS_ALARM = 253, // SI_DA_ENERGY = 254, // SI_DA_FIRSTSLOT = 255, // SI_DA_HEADDEF = 256, @@ -937,11 +954,11 @@ enum si_type { SI_FOOD_DEX_CASH = 274, SI_FOOD_INT_CASH = 275, SI_FOOD_LUK_CASH = 276, - SI_MERC_FLEEUP = 277, - SI_MERC_ATKUP = 278, - SI_MERC_HPUP = 279, - SI_MERC_SPUP = 280, - SI_MERC_HITUP = 281, + SI_MER_FLEE = 277, + SI_MER_ATK = 278, + SI_MER_HP = 279, + SI_MER_SP = 280, + SI_MER_HIT = 281, SI_SLOWCAST = 282, // SI_MAGICMIRROR = 283, // SI_STONESKIN = 284, @@ -949,14 +966,14 @@ enum si_type { SI_CRITICALWOUND = 286, // SI_NPC_DEFENDER = 287, // SI_NOACTION_WAIT = 288, - SI_MOVHASTE_HORSE = 289, - SI_DEF_RATE = 290, - SI_MDEF_RATE = 291, - SI_INCHEALRATE = 292, - SI_S_LIFEPOTION = 293, - SI_L_LIFEPOTION = 294, - SI_INCCRI = 295, - SI_PLUSAVOIDVALUE = 296, + SI_MOVHASTE_HORSE = 289, + SI_PROTECT_DEF = 290, + SI_PROTECT_MDEF = 291, + SI_HEALPLUS = 292, + SI_S_LIFEPOTION = 293, + SI_L_LIFEPOTION = 294, + SI_CRITICALPERCENT = 295, + SI_PLUSAVOIDVALUE = 296, // SI_ATKER_ASPD = 297, // SI_TARGET_ASPD = 298, // SI_ATKER_MOVESPEED = 299, @@ -975,7 +992,7 @@ enum si_type { SI_CASH_PLUSONLYJOBEXP = 312, SI_PARTYFLEE = 313, // SI_ANGEL_PROTECT = 314, - SI_ENDURE_MDEF = 315, +// SI_ENDURE_MDEF = 315, SI_ENCHANTBLADE = 316, SI_DEATHBOUND = 317, SI_REFRESH = 318, @@ -1094,12 +1111,12 @@ enum si_type { SI_PROPERTYWALK = 431, SI_SPELLFIST = 432, SI_NETHERWORLD = 433, - SI_VOICEOFSIREN = 434, + SI_SIREN = 434, SI_DEEPSLEEP = 435, SI_SIRCLEOFNATURE = 436, SI_COLD = 437, SI_GLOOMYDAY = 438, - SI_SONGOFMANA = 439, + SI_SONG_OF_MANA = 439, SI_CLOUDKILL = 440, SI_DANCEWITHWUG = 441, SI_RUSHWINDMILL = 442, @@ -1361,6 +1378,34 @@ enum si_type { SI_QUEST_BUFF3 = 707, SI_REUSE_LIMIT_RECALL = 708, SI_SAVEPOSITION = 709, + SI_HANDICAPSTATE_ICEEXPLO = 710, + SI_FENRIR_CARD = 711, + SI_REUSE_LIMIT_ASPD_POTION = 712, + SI_MAXPAIN = 713, + SI_PC_STOP = 714, + SI_FRIGG_SONG = 715, + SI_OFFERTORIUM = 716, + SI_TELEKINESIS_INTENSE = 717, + SI_MOONSTAR = 718, + SI_STRANGELIGHTS = 719, + SI_FULL_THROTTLE = 720, + SI_REBOUND = 721, + SI_UNLIMIT = 722, + SI_KINGS_GRACE = 723, + SI_ITEM_ATKMAX = 724, + SI_ITEM_ATKMIN = 725, + SI_ITEM_MATKMAX = 726, + SI_ITEM_MATKMIN = 727, + SI_SUPER_STAR = 728, + SI_HIGH_RANKER = 729, + SI_DARKCROW = 730, + SI_2013_VALENTINE1 = 731, + SI_2013_VALENTINE2 = 732, + SI_2013_VALENTINE3 = 733, + //SI_ = 734, + //SI_ = 735, + SI_CHILL = 736, + SI_BURNT = 737, SI_MAX, }; @@ -1553,7 +1598,7 @@ enum scb_flag //Basic damage info of a weapon //Required because players have two of these, one in status_data //and another for their left hand weapon. -struct weapon_atk { +typedef struct weapon_atk { unsigned short atk, atk2; unsigned short range; unsigned char ele; @@ -1561,7 +1606,7 @@ struct weapon_atk { unsigned short matk; unsigned char wlv; #endif -}; +}weapon_atk; sc_type SkillStatusChangeTable[MAX_SKILL]; // skill -> status int StatusIconChangeTable[SC_MAX]; // status -> "icon" (icon is a bit of a misnomer, since there exist values with no icon associated) @@ -1681,6 +1726,7 @@ sc_type status_skill2sc(int skill); int status_sc2skill(sc_type sc); unsigned int status_sc2scb_flag(sc_type sc); int status_type2relevant_bl_types(int type); +int status_get_sc_type(sc_type idx); int status_damage(struct block_list *src,struct block_list *target,int hp,int sp, int walkdelay, int flag); //Define for standard HP damage attacks. @@ -1801,10 +1847,20 @@ int status_check_visibility(struct block_list *src, struct block_list *target); int status_change_spread( struct block_list *src, struct block_list *bl ); +defType status_calc_def(struct block_list *bl, struct status_change *sc, int, bool); +signed short status_calc_def2(struct block_list *,struct status_change *, int, bool); +defType status_calc_mdef(struct block_list *bl, struct status_change *sc, int, bool); +signed short status_calc_mdef2(struct block_list *,struct status_change *, int, bool); + #ifdef RENEWAL unsigned short status_base_matk(const struct status_data* status, int level); +int status_get_weapon_atk(struct block_list *src, struct weapon_atk *watk, int flag); +int status_get_total_mdef(struct block_list *src); +int status_get_total_def(struct block_list *src); #endif +int status_get_matk(struct block_list *src, int flag); + int status_readdb(void); int do_init_status(void); void do_final_status(void); diff --git a/src/map/unit.c b/src/map/unit.c index 153ef5eda..371a75ac7 100644 --- a/src/map/unit.c +++ b/src/map/unit.c @@ -491,7 +491,7 @@ int unit_run(struct block_list *bl) if( (to_x == bl->x && to_y == bl->y ) || (to_x == (bl->x+1) || to_y == (bl->y+1)) || (to_x == (bl->x-1) || to_y == (bl->y-1))) { //If you can't run forward, you must be next to a wall, so bounce back. [Skotlex] - clif->sc_load(bl,bl->id,AREA,SI_BUMP,0,0,0); + clif->sc_load(bl,bl->id,AREA,SI_TING,0,0,0); //Set running to 0 beforehand so status_change_end knows not to enable spurt [Kevin] unit_bl2ud(bl)->state.running = 0; @@ -499,7 +499,7 @@ int unit_run(struct block_list *bl) skill->blown(bl,bl,skill->get_blewcount(TK_RUN,lv),unit_getdir(bl),0); clif->fixpos(bl); //Why is a clif->slide (skill->blown) AND a fixpos needed? Ask Aegis. - clif->sc_end(bl,bl->id,AREA,SI_BUMP); + clif->sc_end(bl,bl->id,AREA,SI_TING); return 0; } if (unit_walktoxy(bl, to_x, to_y, 1)) @@ -511,7 +511,7 @@ int unit_run(struct block_list *bl) } while (--i > 0 && !unit_walktoxy(bl, to_x, to_y, 1)); if ( i == 0 ) { // copy-paste from above - clif->sc_load(bl,bl->id,AREA,SI_BUMP,0,0,0); + clif->sc_load(bl,bl->id,AREA,SI_TING,0,0,0); //Set running to 0 beforehand so status_change_end knows not to enable spurt [Kevin] unit_bl2ud(bl)->state.running = 0; @@ -519,7 +519,7 @@ int unit_run(struct block_list *bl) skill->blown(bl,bl,skill->get_blewcount(TK_RUN,lv),unit_getdir(bl),0); clif->fixpos(bl); - clif->sc_end(bl,bl->id,AREA,SI_BUMP); + clif->sc_end(bl,bl->id,AREA,SI_TING); return 0; } return 1; @@ -924,7 +924,7 @@ int unit_can_move(struct block_list *bl) { if (sc) { if( sc->count && ( - sc->data[SC_ANKLE] + sc->data[SC_ANKLESNARE] || sc->data[SC_AUTOCOUNTER] || sc->data[SC_TRICKDEAD] || sc->data[SC_BLADESTOP] @@ -932,14 +932,14 @@ int unit_can_move(struct block_list *bl) { || (sc->data[SC_GOSPEL] && sc->data[SC_GOSPEL]->val4 == BCT_SELF) // cannot move while gospel is in effect || (sc->data[SC_BASILICA] && sc->data[SC_BASILICA]->val4 == bl->id) // Basilica caster cannot move || sc->data[SC_STOP] - || sc->data[SC_CLOSECONFINE] - || sc->data[SC_CLOSECONFINE2] - || sc->data[SC_MADNESSCANCEL] + || sc->data[SC_RG_CCONFINE_M] + || sc->data[SC_RG_CCONFINE_S] + || sc->data[SC_GS_MADNESSCANCEL] || (sc->data[SC_GRAVITATION] && sc->data[SC_GRAVITATION]->val3 == BCT_SELF) || sc->data[SC_WHITEIMPRISON] || sc->data[SC_ELECTRICSHOCKER] - || sc->data[SC_BITE] - || sc->data[SC_THORNSTRAP] + || sc->data[SC_WUGBITE] + || sc->data[SC_THORNS_TRAP] || sc->data[SC_MAGNETICFIELD] || sc->data[SC__MANHOLE] || sc->data[SC_CURSEDCIRCLE_ATKER] @@ -948,9 +948,9 @@ int unit_can_move(struct block_list *bl) { || sc->data[SC_NETHERWORLD] || (sc->data[SC_CAMOUFLAGE] && sc->data[SC_CAMOUFLAGE]->val1 < 3 && !(sc->data[SC_CAMOUFLAGE]->val3&1)) || sc->data[SC_MEIKYOUSISUI] - || sc->data[SC_KAGEHUMI] + || sc->data[SC_KG_KAGEHUMI] || sc->data[SC_KYOUGAKU] - || sc->data[SC_PARALYSIS] + || sc->data[SC_NEEDLE_OF_PARALYZE] || sc->data[SC_VACUUM_EXTREME] || (sc->data[SC_FEAR] && sc->data[SC_FEAR]->val2 > 0) || (sc->data[SC_SPIDERWEB] && sc->data[SC_SPIDERWEB]->val1) @@ -1069,10 +1069,10 @@ int unit_skilluse_id2(struct block_list *src, int target_id, uint16 skill_id, ui sc = NULL; //Unneeded //temp: used to signal combo-skills right now. - if (sc && sc->data[SC_COMBO] && (sc->data[SC_COMBO]->val1 == skill_id || + if (sc && sc->data[SC_COMBOATTACK] && (sc->data[SC_COMBOATTACK]->val1 == skill_id || (sd?skill->check_condition_castbegin(sd,skill_id,skill_lv):0) )) { - if (sc->data[SC_COMBO]->val2) - target_id = sc->data[SC_COMBO]->val2; + if (sc->data[SC_COMBOATTACK]->val2) + target_id = sc->data[SC_COMBOATTACK]->val2; else target_id = ud->target; @@ -1240,17 +1240,17 @@ int unit_skilluse_id2(struct block_list *src, int target_id, uint16 skill_id, ui casttime += casttime * min(skill_lv, sd->spiritball); break; case MO_EXTREMITYFIST: - if (sc && sc->data[SC_COMBO] && - (sc->data[SC_COMBO]->val1 == MO_COMBOFINISH || - sc->data[SC_COMBO]->val1 == CH_TIGERFIST || - sc->data[SC_COMBO]->val1 == CH_CHAINCRUSH)) + if (sc && sc->data[SC_COMBOATTACK] && + (sc->data[SC_COMBOATTACK]->val1 == MO_COMBOFINISH || + sc->data[SC_COMBOATTACK]->val1 == CH_TIGERFIST || + sc->data[SC_COMBOATTACK]->val1 == CH_CHAINCRUSH)) casttime = -1; temp = 1; break; case SR_GATEOFHELL: case SR_TIGERCANNON: - if (sc && sc->data[SC_COMBO] && - sc->data[SC_COMBO]->val1 == SR_FALLENEMPIRE) + if (sc && sc->data[SC_COMBOATTACK] && + sc->data[SC_COMBOATTACK]->val1 == SR_FALLENEMPIRE) casttime = -1; temp = 1; break; @@ -1317,10 +1317,11 @@ int unit_skilluse_id2(struct block_list *src, int target_id, uint16 skill_id, ui if(!ud->state.running) //need TK_RUN or WUGDASH handler to be done before that, see bugreport:6026 unit_stop_walking(src,1);// eventhough this is not how official works but this will do the trick. bugreport:6829 + // in official this is triggered even if no cast time. clif->skillcasting(src, src->id, target_id, 0,0, skill_id, skill->get_ele(skill_id, skill_lv), casttime); if( casttime > 0 || temp ) - { + { if (sd && target->type == BL_MOB) { TBL_MOB *md = (TBL_MOB*)target; @@ -1518,7 +1519,7 @@ int unit_skilluse_pos2( struct block_list *src, short skill_x, short skill_y, ui if( casttime > 0 ) { ud->skilltimer = iTimer->add_timer( tick+casttime, skill->castend_pos, src->id, 0 ); if( (sd && pc->checkskill(sd,SA_FREECAST) > 0) || skill_id == LG_EXEEDBREAK) - status_calc_bl(&sd->bl, SCB_SPEED); + status_calc_bl(&sd->bl, SCB_SPEED); } else { ud->skilltimer = INVALID_TIMER; skill->castend_pos(ud->skilltimer,tick,src->id,0); @@ -1638,7 +1639,7 @@ int unit_cancel_combo(struct block_list *bl) { struct unit_data *ud; - if (!status_change_end(bl, SC_COMBO, INVALID_TIMER)) + if (!status_change_end(bl, SC_COMBOATTACK, INVALID_TIMER)) return 0; //Combo wasn't active. ud = unit_bl2ud(bl); @@ -1925,7 +1926,7 @@ int unit_skillcastcancel(struct block_list *bl,int type) return 0; if (sd && (sd->special_state.no_castcancel2 || - ((sd->sc.data[SC_UNLIMITEDHUMMINGVOICE] || sd->special_state.no_castcancel) && !map_flag_gvg(bl->m) && !map[bl->m].flag.battleground))) //fixed flags being read the wrong way around [blackhole89] + ((sd->sc.data[SC_UNLIMITED_HUMMING_VOICE] || sd->special_state.no_castcancel) && !map_flag_gvg(bl->m) && !map[bl->m].flag.battleground))) //fixed flags being read the wrong way around [blackhole89] return 0; } @@ -2053,17 +2054,17 @@ int unit_remove_map_(struct block_list *bl, clr_type clrtype, const char* file, if(sc && sc->count ) { //map-change/warp dispells. status_change_end(bl, SC_BLADESTOP, INVALID_TIMER); status_change_end(bl, SC_BASILICA, INVALID_TIMER); - status_change_end(bl, SC_ANKLE, INVALID_TIMER); + status_change_end(bl, SC_ANKLESNARE, INVALID_TIMER); status_change_end(bl, SC_TRICKDEAD, INVALID_TIMER); status_change_end(bl, SC_BLADESTOP_WAIT, INVALID_TIMER); status_change_end(bl, SC_RUN, INVALID_TIMER); status_change_end(bl, SC_DANCING, INVALID_TIMER); status_change_end(bl, SC_WARM, INVALID_TIMER); status_change_end(bl, SC_DEVOTION, INVALID_TIMER); + status_change_end(bl, SC_MARIONETTE_MASTER, INVALID_TIMER); status_change_end(bl, SC_MARIONETTE, INVALID_TIMER); - status_change_end(bl, SC_MARIONETTE2, INVALID_TIMER); - status_change_end(bl, SC_CLOSECONFINE, INVALID_TIMER); - status_change_end(bl, SC_CLOSECONFINE2, INVALID_TIMER); + status_change_end(bl, SC_RG_CCONFINE_M, INVALID_TIMER); + status_change_end(bl, SC_RG_CCONFINE_S, INVALID_TIMER); status_change_end(bl, SC_HIDING, INVALID_TIMER); // Ensure the bl is a PC; if so, we'll handle the removal of cloaking and cloaking exceed later if ( bl->type != BL_PC ) @@ -2074,7 +2075,7 @@ int unit_remove_map_(struct block_list *bl, clr_type clrtype, const char* file, status_change_end(bl, SC_CHASEWALK, INVALID_TIMER); if (sc->data[SC_GOSPEL] && sc->data[SC_GOSPEL]->val4 == BCT_SELF) status_change_end(bl, SC_GOSPEL, INVALID_TIMER); - status_change_end(bl, SC_CHANGE, INVALID_TIMER); + status_change_end(bl, SC_HLIF_CHANGE, INVALID_TIMER); status_change_end(bl, SC_STOP, INVALID_TIMER); status_change_end(bl, SC_WUGDASH, INVALID_TIMER); status_change_end(bl, SC_CAMOUFLAGE, INVALID_TIMER); @@ -2322,7 +2323,7 @@ int unit_free(struct block_list *bl, clr_type clrtype) pc->inventory_rental_clear(sd); pc->delspiritball(sd,sd->spiritball,1); for(i = 1; i < 5; i++) - pc->del_talisman(sd, sd->talisman[i], i); + pc->del_charm(sd, sd->charm[i], i); if( sd->reg ) { //Double logout already freed pointer fix... [Skotlex] aFree(sd->reg); diff --git a/src/map/vending.c b/src/map/vending.c index e0dd844e1..b9575c8dd 100644 --- a/src/map/vending.c +++ b/src/map/vending.c @@ -272,7 +272,7 @@ void vending_openvending(struct map_session_data* sd, const char* message, const clif->skill_fail(sd, MC_VENDING, USESKILL_FAIL_LEVEL, 0); // custom reply packet return; } - sd->state.prevend = 0; + sd->state.prevend = sd->state.workinprogress = 0; sd->state.vending = true; sd->vender_id = getid(); sd->vend_num = i; -- cgit v1.2.3-60-g2f50 From c23b6e354a20046a864e6d0a42e178c9c641055b Mon Sep 17 00:00:00 2001 From: Euphy Date: Thu, 20 Jun 2013 19:32:11 -0400 Subject: Implemented Eden Tutorial. --- npc/re/quests/eden/eden_tutorial.txt | 1561 ++++++++++++++++++++++++++++++++++ 1 file changed, 1561 insertions(+) create mode 100644 npc/re/quests/eden/eden_tutorial.txt (limited to 'npc/re') diff --git a/npc/re/quests/eden/eden_tutorial.txt b/npc/re/quests/eden/eden_tutorial.txt new file mode 100644 index 000000000..0c1519d0a --- /dev/null +++ b/npc/re/quests/eden/eden_tutorial.txt @@ -0,0 +1,1561 @@ +//===== rAthena Script ======================================= +//= Eden Tutorial +//===== By: ================================================== +//= Euphy +//===== Current Version: ===================================== +//= 1.0 +//===== Compatible With: ===================================== +//= rAthena SVN +//===== Description: ========================================= +//= A series of quests introducing the major features of +//= Ragnarok Online. +//===== Additional Comments: ================================= +//= 1.0 First Version. [Euphy] +//============================================================ + +moc_para01,34,178,3 script Tutorial Instructor 904,{ + if (Class == Job_Novice) { + // Fall through + } else if (checkquest(9167) == -1) { + OnStartQuest: + if (@tutorial_restart) { + set .@tutorial_restart,1; + set @tutorial_restart,0; + } + mes "[Tutorial Instructor]"; + mes "Lately, it has been said that"; + mes "they are developing ways to add options"; + mes "to put in sockets or add statuses"; + mes "on equipment that normally don't have it."; + mes "They call that ^006400Enchant^000000."; + next; + mes "[Tutorial Instructor]"; + mes "After seeing that being developed,"; + mes "I was so inspired by it"; + mes "that I worked hard to discover"; + mes "a way to do it and I finally"; + mes "made my own way to ^006400Enchant^000000!"; + next; + mes "[Tutorial Instructor]"; + mes "But in order do to this"; + mes "I need some special materials."; + mes "If you're okay with it..."; + mes "Do you think you can"; + mes "help me out by gathering them?"; + next; + switch(select("Sure, I can help out!:I'm a little busy right now...")) { + case 1: + mes "[Tutorial Instructor]"; + mes "However, looking at you"; + mes "in your current state makes me"; + mes "doubt your ability to gather"; + mes "the items I need..."; + next; + mes "[Tutorial Instructor]"; + mes "Well, I guess if you employ"; + mes "a ^006400Mercenary^000000 for this"; + mes "then I think I can entrust you"; + mes "with my requests... right?"; + next; + mes "[Tutorial Instructor]"; + mes "In order to employ a Mercenary,"; + mes "go find the ^006400Mercenary Guild^000000"; + mes "which is by the front door of ^8B4513Prontera^000000."; + mes "Go to the ^006400Information Agent^000000"; + mes "and ask them where the ^006400Mercenary Guild Official^000000"; + mes "is located and they will let you know."; + next; + if (.@tutorial_restart) { + erasequest 9167; + erasequest 9168; + erasequest 9169; + erasequest 9170; + erasequest 9171; + erasequest 9172; + completequest 9173; + erasequest 9173; + } + mes "[Tutorial Instructor]"; + mes "Now... Hurry and employ"; + mes "a ^006400Mercenary^000000 and come back to me!"; + setquest 9167; + close; + case 2: + mes "[Tutorial Instructor]"; + mes "Well since you said you're busy"; + mes "I can't be helped..."; + mes "When you're not so busy, come find me again."; + close; + } + } else if (checkquest(9167) == 0 || checkquest(9167) == 1) { + if (!getmercinfo(1)) { + mes "[Tutorial Instructor]"; + mes "You haven't gotten a mercenary yet."; + next; + mes "[Tutorial Instructor]"; + mes "In order to employ a Mercenary,"; + mes "go find the ^006400Mercenary Guild^000000"; + mes "which is by the front door of ^8B4513Prontera^000000."; + mes "Go to the ^006400Information Agent^000000"; + mes "and ask them where the ^006400Mercenary Guild Official^000000"; + mes "is located and they will let you know."; + next; + mes "[Tutorial Instructor]"; + mes "Now... Hurry and employ"; + mes "a ^006400Mercenary^000000 and come back to me!"; + } + mes "[Tutorial Instructor]"; + mes "Seeing you with a ^006400Mercenary^000000 definitely makes me trust you more."; + next; + mes "[Tutorial Instructor]"; + mes "If a 006400Mercenary^000000 gives you direct effect"; + mes "by fighting for you"; + mes "then a ^006400Pet^000000 helps you indirectly with their"; + mes "abilities and varied appearances,"; + mes "and it captures your heart."; + mes "Try raising a ^006400Pet^000000 in the future as well."; + next; + mes "[Tutorial Instructor]"; + mes "Now, let's see... In order to"; + mes "get this ^006400Enchant^000000 to succeed"; + mes "you have to go gather some materials for me..."; + mes "What I need is..."; + mes ".............."; + next; + select("I don't think I heard you clearly..."); + mes "[Tutorial Instructor]"; + mes "I really don't like to repeat myself.."; + mes "If you ask me again like that"; + mes "does it just make your mouth tired?"; + mes "In these situations, open your ^006400Quest Window^000000"; + mes "and you can see what is requested of you"; + mes "and the details of my request."; + next; + mes "[Tutorial Instructor]"; + mes "If you look at the top left"; + mes "in the area with the information,"; + mes "it says ^006400QUEST^000000"; + mes "and if you click that"; + mes "it'll show all information"; + mes "that pertains to the request."; + next; + mes "[Tutorial Instructor]"; + mes "Once you verify what materials"; + mes "you need go gather from"; + mes "the ^006400Quest Window^000000,"; + mes "come find and talk to me again."; + completequest 9167; + setquest 9168; + close; + } else if (checkquest(9168) == 0 || checkquest(9168) == 1) { + if (checkweight(607,1) == 0) { + if (MaxWeight - Weight < getiteminfo(607,6)) { + mes "[Tutorial Instructor]"; + mes "You seemed to be sluggish with a lot of items"; + mes "in your inventory making you heavy..."; + mes "It'll be hard to do my request"; + mes "when you're heavy with all that junk!"; + mes "Go empty out your inventory and come back to me."; + close; + } else { + mes "[Tutorial Instructor]"; + mes "It seems that you have"; + mes "one too many items on you..."; + mes "If you want to help me out"; + mes "then you're gonna have to put some"; + mes "stuff away then come back."; + close; + } + } + mes "[Tutorial Instructor]"; + mes "Did you open your ^006400Quest Window^000000"; + mes "to verify the materials?"; + next; + switch(select("Yup!:No...:Where is the Quest Window...")) { + case 1: + mes "[Tutorial Instructor]"; + mes "Oh yeah? Then shall I test you to see"; + mes "if you really checked it?"; + mes "Write down what material I asked you to get."; + next; + input .@inputstr$; + if (.@inputstr$ == "10 Jellopy") { + mes "[Tutorial Instructor]"; + mes "Good, you know."; + mes "Now, are you feeling pretty familiar"; + mes "about the ^006400Quest Window^000000?"; + mes "But there is an issue..."; + mes "You know what material to collect,"; + mes "but gathering that won't be easy."; + next; + mes "[Tutorial Instructor]"; + mes "Also, there is one thing"; + mes "I absolutely think you need to try."; + mes "And that is..."; + mes "the ^006400Universal Silver Catalog^000000."; + next; + mes "[Tutorial Instructor]"; + mes "The ^006400Universal Silver Catalog^000000"; + mes "can be obtained from"; + mes "the ^0000FFCatalogue Wizard^000000"; + mes "that is located in South Prontera."; + next; + mes "[Tutorial Instructor]"; + mes "Now, go and obtain"; + mes "a ^006400Universal Silver Catalog^000000"; + mes "then come back and talk to me."; + completequest 9168; + setquest 9169; + close; + } + mes "[Tutorial Instructor]"; + mes "You... still don't seem"; + mes "to know much about the"; + mes "^006400Quest Window^000000."; + mes "I will inform you again."; + next; + break; + case 2: + mes "[Tutorial Instructor]"; + mes "Hurry and check to see"; + mes "what materials are required in"; + mes "your ^006400Quest Window^000000."; + close; + case 3: + break; + } + mes "[Tutorial Instructor]"; + mes "If you look at the top left"; + mes "in the area with the information,"; + mes "it says ^006400QUEST^000000"; + mes "and if you click that"; + mes "it'll show all information"; + mes "that pertains to the request."; + next; + mes "[Tutorial Instructor]"; + mes "Once you verify what materials"; + mes "you need go gather from"; + mes "the ^006400Quest Window^000000,"; + mes "come find and talk to me again."; + close; + } else if (checkquest(9169) == 0 || checkquest(9169) == 1) { + if (countitem(12580) == 0) { + mes "[Tutorial Instructor]"; + mes "Hmm? So I noticed that"; + mes "you haven't gone and picked up a"; + mes "^006400Universal Silver Catalog^000000 yet!"; + next; + mes "[Tutorial Instructor]"; + mes "You can get the"; + mes "^006400Universal Silver Catalog^000000"; + mes "from the ^0000FFCatalogue Wizard^000000"; + mes "who is located in Prontera."; + next; + mes "[Tutorial Instructor]"; + mes "So, go and get the"; + mes "^006400Universal Silver Catalog^000000"; + mes "then come back to me."; + close; + } + mes "[Tutorial Instructor]"; + mes "Oh! You managed to get a"; + mes "^006400Universal Silver Catalog^000000!"; + next; + mes "[Tutorial Instructor]"; + mes "This lets you browse and search"; + mes "through all the various stores"; + mes "that are on the same map and"; + mes "are open for vending."; + next; + mes "[Tutorial Instructor]"; + mes "It only costs 200 zeny for one"; + mes "of these and with it you can"; + mes "search up to 10 times."; + mes "You can say that it's a necessity."; + next; + mes "[Tutorial Instructor]"; + mes "So, go to the area you want"; + mes "and try out the ^006400Universal Silver Catalog^000000"; + mes "then come and find me"; + mes "after you've done this."; + completequest 9169; + setquest 9170; + close; + } else if (checkquest(9170) == 0 || checkquest(9170) == 1) { + if (countitem(12580)) { + mes "[Tutorial Instructor]"; + mes "Hmm... It seems that you still have"; + mes "the ^006400Universal Silver Catalog^000000 in your inventory."; + mes "Since you're saying you forgot how to use it"; + mes "I'll explain it to you again."; + next; + mes "[Tutorial Instructor]"; + mes "You see... the ^006400Universal Silver Catalog^000000"; + mes "lets you browse and search"; + mes "through all the various stores"; + mes "that are on the same map and"; + mes "are open for vending."; + next; + mes "[Tutorial Instructor]"; + mes "So, go to the area you want"; + mes "and try out the ^006400Universal Silver Catalog^000000"; + mes "them come and find me"; + mes "after you've done this."; + close; + } + mes "[Tutorial Instructor]"; + mes "How do you feel after trying out"; + mes "the ^006400Universal Silver Catalog^000000?"; + mes "It feels a lot easier than"; + mes "going through each individual"; + mes "vendor and finding the item"; + mes "you need, right?"; + next; + mes "[Tutorial Instructor]"; + mes "Now, go out and gather"; + mes "the materials I need and"; + mes "I will make sure to give you"; + mes "a fantastic ^006400enchant^000000!"; + mes "I'll be waiting!"; + completequest 9170; + setquest 9171; + close; + } else if (checkquest(9171) == 0 || checkquest(9171) == 1) { + if (countitem(909) < 10) { + mes "[Tutorial Instructor]"; + mes "It seems you didn't bring"; + mes "enough materials. Did you forget"; + mes "what you needed to gather?"; + next; + switch(select("Yeah...:Nope!")) { + case 1: + mes "[Tutorial Instructor]"; + mes "I've been told that if you click the"; + mes "thing on the top left that says"; + mes "^006400QUEST^000000, it'll show you all"; + mes "the information that you need"; + mes "that pertains to your requests."; + next; + mes "[Tutorial Instructor]"; + mes "Once you gather all the materials"; + mes "that are listed in your ^006400Quest Window^000000"; + mes "come and talk to me."; + close; + case 2: + mes "[Tutorial Instructor]"; + mes "When you gather the items"; + mes "come to me and I will show you"; + mes "an awesome ^006400ENCHANT^000000."; + mes "I'll be waiting!"; + close; + } + } + if (checkweight(607,6) == 0) { + if (MaxWeight - Weight < getiteminfo(607,6)) { + mes "[Tutorial Instructor]"; + mes "Your inventory seems to be really full"; + mes "with various stuff... Do you think"; + mes "you can get anything done when you're so"; + mes "weighed down? Go put some stuff away"; + mes "then come back to me."; + close; + } else { + mes "[Tutorial Instructor]"; + mes "You seem to have too much stuff"; + mes "in your inventory... Go put some"; + mes "stuff away then come back to me"; + mes "when you have less suff on you."; + close; + } + } + mes "[Tutorial Instructor]"; + mes "You got everything I asked for!"; + mes "So~ Shall we start on the awesome"; + mes "Enchant that I found and developed?"; + next; + specialeffect EF_BASH3D2; + mes "[Tutorial Instructor]"; + mes "Okay! Now for the first skill!!"; + mes "To add a new ability to your armor..."; + mes "^006400HIDDEN SOCKET ENCHANT^000000!!"; + next; + specialeffect EF_BASH3D2; + mes "[Tutorial Instructor]"; + mes "And for the second skill!!"; + mes "To add a new socket into your"; + mes "weapon and shield..."; + mes "^006400SOCKET ENCHANT^000000!!"; + next; + mes "[Tutorial Instructor]"; + mes "There. The Enchant is done. You can't understand the the process by just watching me, so I'll let you look at the items themselves."; + delitem 909,10; //Jellopy + completequest 9171; + setquest 9172; + getitem2 15033,1,1,0,0,0,0,0,4702; //Tutorial_Mattle[Strength3] + getitem 15033,1; //Tutorial_Mattle + getitem 15034,1; //Tutorial_Mattle_ + next; + mes "[Tutorial Instructor]"; + mes "Those items cannot be"; + mes "worn or traded so don't even"; + mes "think about running away with them."; + mes "When you're done looking at them,"; + mes "give them back to me."; + close; + } else if (checkquest(9172) == 0 || checkquest(9172) == 1) { + if (countitem(15033) == 0 || countitem(15034) == 0) { + mes "[Tutorial Instructor]"; + mes "What did you do with the Enchanted"; + mes "items I lent to you to look at?"; + mes "Until you bring back the fruits of"; + mes "my labor, I don't want to talk to you,"; + mes "let alone see your face."; + close; + } + mes "[Tutorial Instructor]"; + mes "Are you done looking over"; + mes "the items I Enchanted?"; + next; + switch(select("Yes, thank you.:I haven't looked at them yet.")) { + case 1: + mes "[Tutorial Instructor]"; + mes "So what did you think after inspecting it? Now that you've looked at an actual Enchanted item, do you understand it?"; + // Item deletions moved below to prevent errors. + next; + mes "[Tutorial Instructor]"; + mes "Thanks to you I was able to see great results of my research and study."; + next; + mes "[Tutorial Instructor]"; + mes "If you have any questions about anything that I discussed with you, I will tell you everything! Thanks for your hard work!"; + delitem 15033,2; + delitem 15034,1; + completequest 9172; + setquest 9173; + getexp 5000,2500; + close; + case 2: + mes "[Tutorial Instructor]"; + mes "Take your time to look them over"; + mes "then bring them back to me."; + close; + } + } else if (checkquest(9173) == 0 || checkquest(9173) == 1) { + mes "[Tutorial Instructor]"; + mes "Do you have any questions?"; + next; + switch(select("Can I do the same quest again?:About the Quest Window...:About ENCHANT...:About Searching Vends...:About Mercenary and Pets...:End Conversation.")) { + case 1: + if (checkquest(9173,PLAYTIME) == 0 || checkquest(9173,PLAYTIME) == 1) { + mes "[Tutorial Instructor]"; + mes "The one method to do the same quests repeatdedly is to do the ^006400Daily Quests^000000."; + next; + mes "[Tutorial Instructor]"; + mes "Once you complete a ^006400Daily Quest^000000 and turn it in, wait about a day then come back to get the request and do it all over again!"; + mes "[Tutorial Instructor]"; + mes "If you received a daily quest, look at bottom right of the ^006400Quest Window^000000. There is a section that is called ^006400LIMITED^000000. In that section, it'll tell you how much time needs to pass before you can pick up another daily quest."; + next; + mes "[Tutorial Instructor]"; + mes "It seems you still have some time left to wait out after finishing my quest. Wait it out a bit more, then come find me and you can get the same quest again."; + close; + } + mes "[Tutorial Instructor]"; + mes "It seems that about a day has passed since you've finished my quest. Alright, so like the ^006400Daily Quests^000000, you can get a quest from me. Did you want to proceed?"; + next; + switch(select("Yes:No")) { + case 1: + set @tutorial_restart,1; + goto OnStartQuest; + case 2: + mes "[Tutorial Instructor]"; + mes "Okay. But if you change your mind and want to receive a quest, come find me."; + close; + } + case 2: + mes "[Tutorial Instructor]"; + mes "They say that the ^006400Quest Window^000000 details out everything you need to know about your quests."; + next; + mes "[Tutorial Instructor]"; + mes "If you look at the top left"; + mes "in the area with the information,"; + mes "it says ^006400QUEST^000000"; + mes "and if you click that"; + mes "it'll show all information"; + mes "that pertains to the request."; + next; + mes "[Tutorial Instructor]"; + mes "Using the ^006400Quest Window^000000 will make your life easier. It'll tell you where to go, what items to get or who to find and etc."; + close; + case 3: + mes "[Tutorial Instructor]"; + mes "006400ENCHANT^000000, in general, is divided into two parts: ^006400SOCKET ENCHANT^000000 and ^006400HIDDEN SOCKET ENCHANT^000000."; + next; + mes "[Tutorial Instructor]"; + mes "^006400SOCKET ENCHANT^000000 is used to add a SOCKET into equipments and ^006400HIDDEN SOCKET ENCHANT^000000 is used to put in stats into a socket of an armor."; + next; + mes "[Tutorial Instructor]"; + mes "Of course, in order to do this we are in need of some materials and there is a chance that it may fail, but that's the risk you're taking."; + next; + mes "[Tutorial Instructor]"; + mes "The people who do the ^006400SOCKET ENCHANT^000000 can be found in ^8B4513Prontera, Morroc, Payon,^000000. ^8B4513Rhitalzen^000000 is in the Refinery and ^0000FFSeiyablem^000000 and ^0000FFReiablem^000000 can be found near the entrance."; + next; + mes "[Tutorial Instructor]"; + mes "The one who does ^006400HIDDEN SOCKET ENCHANT^000000 is found at the 6 o'clock location of ^8B4513Prontera^000000. Look for the ^0000FFCraftman Apprentice^000000."; + next; + mes "[Tutorial Instructor]"; + mes "Do you think you understand a little bit more about ^006400ENCHANT^000000?"; + close; + case 4: + mes "[Tutorial Instructor]"; + mes "^006400Vend Search^000000 can be utilized by the ^006400Universal Silver Catalog^000000 item. Since you search through as vends on that map, it'll make it easier for you to find the item that you're looking for."; + next; + mes "[Tutorial Instructor]"; + mes "The ^006400Universal Silver Catalog^000000"; + mes "can be obtained from "; + mes "the ^0000FFCatalogue Wizard^000000"; + mes "that is located in South Prontera;"; + next; + mes "[Tutorial Instructor]"; + mes "It only costs 200 zeny for one"; + mes "of these and with it you can"; + mes "search up to 10 times."; + mes "You can say that it's a necessity."; + next; + mes "[Tutorial Instructor]"; + mes "So, are you getting familiar with ^006400Vend Search^000000? Don't just stand there and listen to me. Go ahead and try it for yourself!"; + close; + case 5: + mes "[Tutorial Instructor]"; + mes "Depending on what you need, ^006400Mercenary^000000 and ^006400Pet^000000 can be used in various ways."; + next; + mes "[Tutorial Instructor]"; + mes "If a 006400Mercenary^000000 gives you direct effect"; + mes "by fighting for you"; + mes "then a ^006400Pet^000000 helps you indirectly with their"; + mes "abilities and varied appearances,"; + mes "and it captures your heart."; + next; + mes "[Tutorial Instructor]"; + mes "In order to employ a Mercenary"; + mes "Go find the ^006400Mercenary Guild^000000"; + mes "which is by the front door of ^8B4513Prontera^000000."; + mes "Go to the ^006400Information Agent^000000"; + mes "and ask them where the ^006400Mercenary Guild Official^000000"; + mes "is located and they will let you know."; + next; + mes "[Tutorial Instructor]"; + mes "In order to get a ^006400Pet^000000, while hunting you will obtain taming items. Use the tame on the monster it's for and you can get a pet."; + next; + mes "[Tutorial Instructor]"; + mes "Because there is a chance for failure, please use the taming item with great care."; + next; + mes "[Tutorial Instructor]"; + mes "That aside... you can get a ^006400Mercenary^000000 from the Mercenary Guild and you can get a ^006400Pet^000000 by trading or buying it from another player."; + next; + mes "[Tutorial Instructor]"; + mes "Now, do you understand a bit more about using a ^006400Mercenary^000000 and a ^006400Pet^000000? I hope you get a chance to use them in the future."; + close; + case 6: + mes "[Tutorial Instructor]"; + mes "If you have any questions, come find me again."; + close; + } + } + mes "[Tutorial Instructor]"; + mes "Lately, it has been said that"; + mes "they are developing ways to add options"; + mes "to put in sockets or add statuses"; + mes "on equipment that normally don't have it."; + close; +} + +moc_para01,32,179,4 script Tutorial Goal 895,{ + if (checkweight(608,7) == 0) { + if (MaxWeight - Weight < getiteminfo(608,7)) { + mes "[Tutorial Goal]"; + mes "You seem to be overweight with items. Go put some stuff away then come back."; + close; + } else { + mes "[Tutorial Goal]"; + mes "You have too many items on you. Go put some stuff away then come back."; + close; + } + } + if (checkquest(4161) == 0 || checkquest(4161) == 1) { + mes "[Tutorial Goal]"; + mes "Well~ We gotta go challenge the experts right?"; + mes "Let's start off by finding the ^006400Siege Expert^000000!"; + close; + } else if (checkquest(4162) == 0 || checkquest(4162) == 1) { + mes "[Tutorial Goal]"; + mes "You've passed the ^006400Siege Expert^000000's test! Congrats!"; + mes "Now, go find the ^006400Party Recruiting Expert^000000!"; + close; + } else if (checkquest(4163) == 0 || checkquest(4163) == 1) { + mes "[Tutorial Goal]"; + mes "Oh! You've passed the ^006400Party Recruiting Expert^000000's test! Congrats!"; + mes "Now, go find the ^006400Battleground Expert^000000!"; + close; + } else if (checkquest(4164) == 0 || checkquest(4164) == 1) { + mes "[Tutorial Goal]"; + mes "Yay! You passed the test from the ^006400Battleground Expert^000000! Congrats!"; + mes "Next, go and find the ^006400Memorial Dungeon Expert^000000!"; + close; + } else if (checkquest(4165) == 0 || checkquest(4165) == 1) { + mes "[Tutorial Goal]"; + mes "You passed the test from ^006400Memorial Dungeon Expert^000000! That's great!"; + mes "Try finding the ^006400Map Expert^000000!"; + close; + } else if (checkquest(4166) == 0 || checkquest(4166) == 1) { + mes "[Tutorial Goal]"; + mes "You passed ^006400Map Expert^000000's test! Congrats!"; + mes "I'm so glad that you were to pass all the Experts' tests! You're better than I expected!!"; + next; + mes "[Tutorial Goal]"; + mes "Now, even you are an ^006400Expert^000000!! Such a fitting nick name for you!"; + mes "Thank you so much for your hard work. As promised, here is a small little reward for you."; + next; + mes "[Tutorial Goal]"; + mes "I think it'll be useful to you during your adventures. I wish you luck on your future adventures~"; + completequest 4166; + getitem 510,5; //Blue_Herb + getitem 511,5; //Green_Herb + getitem 504,5; //White_Potion + getitem 608,1; //Seed_Of_Yggdrasil + close; + } else if (checkquest(4166) == 2) { + mes "[Tutorial Goal]"; + mes "Now, even you are an ^006400Expert^000000!! Such a fitting nick name for you!"; + mes "Thank you so much for your hard work."; + mes "I hope that your future adventures are filled with good luck."; + close; + } + if (Class == Job_Novice) { + mes "[Tutorial Goal]"; + mes "Hmm, I wonder if there is any adventurer that is smart enough to challenge our Experts..."; + close; + } + mes "[Tutorial Goal]"; + mes "Hey you! You look like an adventurer... Though you look a little dull..."; + next; + if(select("What'd you say? I'm smart!:Yeah... I'm dull.") == 1) { + mes "[Tutorial Goal]"; + mes "Serious? Though I don't know if I can believe that. Look at the expert who is in front of me! He took up only one area of study for 16 years and now he is as dignified as can be!"; + next; + mes "[Tutorial Goal]"; + mes "Well, if you manage to pass all their tests then I will believe in your abilities."; + next; + mes "[Tutorial Goal]"; + mes "And I will apologize for calling you dull. How about it, Dull Expert?! Do you want to challenge them?"; + next; + if(select("Ch... Challenge!!:Um... I think I'll just give up now...") == 1) { + mes "[Tutorial Goal]"; + mes "You're braver than you look. You can't go back now that you've decided to challenge!"; + next; + mes "[Tutorial Goal]"; + mes "Okay~ Start by talking to the ^006400Siege Expert^000000 who's right there in front."; + setquest 4161; + close; + } + } + mes "[Tutorial Goal]"; + mes "Well, don't get discouraged... If you change your mind and want to do the challenge, come find me."; + close; +} + +moc_para01,24,175,4 script Siege Master 734,{ + set .@checkquest, checkquest(4161); + if (.@checkquest == 2) { + mes "[Siege Expert]"; + mes "Since you've come again, I assume you're curious about ^006400Siege^000000?"; + next; + switch(select("Listen about Siege.:End Conversation.")) { + case 1: + callsub L_Info; + mes "[Siege Expert]"; + mes "Now that you've gone through all of this with an expert, isn't it easy to understand? If you want to go over anything, just come talk to me."; + close; + case 2: + mes "[Siege Expert]"; + mes "If you want to go over anything, just come talk to me."; + close; + } + } else if (.@checkquest == 0 || .@checkquest == 1) { + mes "[Siege Expert]"; + mes "I am someone who has studied War of Emperium for 16 years! So that makes me an expert! Since you came to find me, I assume you want to learn more about ^006400Siege^000000."; + next; + mes "[Siege Expert]"; + mes "You have great desire and enthusiasm. As the Expert of ^006400Siege^000000, you have motivated me! All the other Experts are waiting for you! Go get'em!"; + next; + mes "[Siege Expert]"; + mes "If I told you that there was a great prize for being able to pass all the Experts' tests~ would you go for the challenge?"; + next; + mes "[Siege Expert]"; + mes "As the first Expert, I can teach you about ^006400Siege^000000. How about it? Did you wanna learn about ^006400Siege^000000s?"; + next; + switch(select("Listen about Siege.:End Conversation.")) { + case 1: + callsub L_Info; + mes "[Siege Expert]"; + mes "Now that you've gone through all of this with an expert, isn't it easy to understand?"; + mes "Now I'll give you 3 questions~ get those right and you've passed! Do you want a challenge?"; + while(1) { + set .@correct,0; + next; + switch(select("Challenge me!:Listen Again:Quit")) { + case 1: + switch(rand(1,3)) { + case 1: + mes "[Siege Expert]"; + mes "A Siege is done in order to take over a []."; + mes "It's a war that happens between a [] and another []."; + mes "What words go in the empty spaces of []?"; + next; + if(select("Castle, User, Guild:Castle, Guild, Guild:Town, Guild, Guild:Town, User, User") == 2) + set .@correct, .@correct+10; + mes "[Siege Expert]"; + mes "What is the wrong Siege time?"; + next; + if(select("WoE 1 Tues 9-11:WoE 1 Sat 4-6:WoE 1 Thurs 8-10") == 3) + set .@correct, .@correct+10; + mes "[Siege Expert]"; + mes "When you get a castle, you must raise [] in order to get better benefits."; + mes "What words go in the empty spaces of []?"; + next; + if(select("Commerce Development:Industrial Development:Guild Development:Town Development") == 1) + set .@correct, .@correct+10; + break; + case 2: + mes "[Siege Expert]"; + mes "There are 2 types of Siege."; + mes "There is the normal War of Emperium"; + mes "and then there is []."; + mes "What words go in the empty spaces of []?"; + next; + if(select("War of Emperium MO:War of Emperium NE:War of Emperium SK:War of Emperium SE") == 4) + set .@correct, .@correct+10; + mes "[Siege Expert]"; + mes "As the guild that owns a castle, you must protect the []."; + mes "What words go in the empty spaces of []?"; + next; + if(select("Emperial:Emperium:Emperiom:Imperial") == 2) + set .@correct, .@correct+10; + mes "[Siege Expert]"; + mes "What benefits does the guild get for winning the Siege?"; + next; + if(select("30% off all items when purchasing:Increase experience gained by 20%:Access to Guild Dungeon:Getting Weapons everyday at midnight.") == 3) + set .@correct, .@correct+10; + break; + case 3: + mes "[Siege Expert]"; + mes "What benefits does the guild get for winning the Siege?"; + next; + if(select("Increase experience gained by 20%:30% off all items when purchasing:Access to Guild Field:Treasure Box daily at midnight") == 4) + set .@correct, .@correct+10; + mes "[Siege Expert]"; + mes "How many hours does a siege last?"; + next; + if(select("1 Hour:2 Hours:3 Hours:4 Hours") == 2) + set .@correct, .@correct+10; + mes "[Siege Expert]"; + mes "When you get a castle, you must raise [] in order to get better benefits."; + mes "What words go in the empty spaces of []?"; + next; + if(select("Town Development:Industry Development:Guild Development:Commerce Development") == 4) + set .@correct, .@correct+10; + break; + } + if (.@correct == 30) { + mes "[Siege Expert]"; + mes "Wow! You got all 3 questions correct! So, you feel pretty good about ^006400Siege^000000s? Right?"; + next; + mes "[Siege Expert]"; + mes "If you ever want to learn about ^006400Siege^000000, come find me."; + next; + mes "[Siege Expert]"; + mes "Now, go and find the ^0000FFParty Recruiting Expert^000000. He's waiting for you."; + completequest 4161; + setquest 4162; + getexp 2000,1000; + close; + } + mes "[Siege Expert]"; + mes "There's only 3 questions and you didn't get them all right! At this rate, you'll fail all the Experts' tests."; + next; + mes "[Siege Expert]"; + mes "But when I look at you I know you have potential. Did you want to try to tackle it again?"; + break; + case 2: + callsub L_Info; + mes "[Siege Expert]"; + mes "Now that you've gone through all of this with an expert, isn't it easy to understand?"; + mes "Now I'll give you 3 questions~ get those right and you've passed! Do you want a challenge?"; + break; + case 3: + mes "[Siege Expert]"; + mes "Bah! You're no fun... you give up too easy! If you change your mind, come find me."; + close; + } + } + close; + case 2: + mes "[Siege Expert]"; + mes "Are you giving up? If you change your mind, come find me."; + close; + } + } + mes "[Siege Expert]"; + mes "If you want to learn something from me, go meet ^006400Tutorial Goal^000000 first."; + close; + +L_Info: + mes "[Siege Expert]"; + mes "A ^006400Siege^000000 is a ^0000FFGuild vs. Guild^000000 war in hope to occupy a castle!"; + next; + mes "[Siege Expert]"; + mes "There are 2 different types of ^006400Siege^000000."; + mes "There is the standard ^006400War of Emperium^000000 and one that is slightly different which is known as ^006400War of Emperium 2^000000."; + next; + mes "[Siege Expert]"; + mes "So during this time, there are two sides of the war."; + mes "The ^0000FFGuild That Owns a Castle^000000 tries to protect the ^006400Emperium^000000 and the ^0000FFGuild That Attacks a Castle^000000 tries to break the ^006400Emperium^000000."; + next; + mes "[Siege Expert]"; + mes "You can find ^006400Siege^000000 times on our website."; + mes "And guilds that win also get a special something-something."; + next; + mes "[Siege Expert]"; + mes "Guilds that win during the Siege"; + mes "get access to a ^006400Guild Dungeon^000000"; + mes "and the Guild Master gets to open ^006400Treasure Box^000000es at ^0000FFMidnight each day^000000."; + mes "Isn't that a great benefit?"; + next; + mes "[Siege Expert]"; + mes "Another thing you have to do when you win a castle is called ^006400Commerce Development^000000. The more you do it, the better the benefits."; + next; + return; +} + +moc_para01,21,172,4 script Party Recruiting Expert 878,{ + set .@checkquest, checkquest(4162); + if (.@checkquest == 2) { + mes "[Party Recruiting Expert]"; + mes "Since you've come and found me, it seems you're curious about ^006400Party Recruiting^000000?"; + next; + switch(select("Listen about Party Recruiting.:End Conversation.")) { + case 1: + callsub L_Info; + mes "[Party Recruiting Expert]"; + mes "This expert's explanation was pretty great, huh? If you need a refresher, come find me again."; + close; + case 2: + mes "[Party Recruiting Expert]"; + mes "Well, if you have any questions, come find me."; + close; + } + } else if (.@checkquest == 0 || .@checkquest == 1) { + mes "[Party Recruiting Expert]"; + mes "I am the ^006400Party Recruiting^000000 expert because I did research about Party Recruting for 16 years! It seems that the ^006400Siege Expert^000000 sent you my way since you passed his tests, hmm?"; + next; + mes "[Party Recruiting Expert]"; + mes "You may have already heard but if you pass all the Experts' quizzes, you'll get an awesome prize!"; + next; + mes "[Party Recruiting Expert]"; + mes "As the 2nd expert, I'll tell you all about ^006400Party Recruiting^000000! How about it?"; + next; + switch(select("Listen about Party Recruiting.:End Conversation.")) { + case 1: + callsub L_Info; + mes "[Party Recruiting Expert]"; + mes "Now~ my explanations were smoother than a smooth criminal, right? Now I'm gonna give you a quiz with 3 questions. Get them all right and you've passed. Wanna take the challenge?"; + while(1) { + set .@correct,0; + next; + switch(select("On to the quiz!:Explain again please?:Give up.")) { + case 1: + switch(rand(1,3)) { + case 1: + mes "[Party Recruiting Expert]"; + mes "Party Recruiting is used to help"; + mes "users that are looking for []"; + mes "and those looking for a []."; + mes "What words go in the empty spaces of []?"; + next; + if(select("Guild, Guildmate:Club, Club Members:Paris, Party Members:Party, Party Members") == 4) + set .@correct, .@correct+10; + mes "[Party Recruiting Expert]"; + mes "The window that is used to help users look and search for a party is called a []."; + mes "What words go in the empty spaces of []?"; + next; + if(select("Party List:Party Wanted List:Party Recruiting List:Costume Party List") == 3) + set .@correct, .@correct+10; + mes "[Party Recruiting Expert]"; + mes "Which of the choices are not listed as a choice to pick when making a party recruit notice?"; + next; + if(select("LEVEL:SKILL:JOB:MAP") == 2) + set .@correct, .@correct+10; + break; + case 2: + mes "[Party Recruiting Expert]"; + mes "There are 2 types of Party Recruiting."; + mes "Registering Party Recruiting is one"; + mes "and the 2nd one is []."; + mes "What words go in the empty spaces of []?"; + next; + if(select("Search for Parties that are Recruiting:Parties that are starting to hunt:Party Recruit and Item Distribution:Party Stuff") == 1) + set .@correct, .@correct+10; + mes "[Party Recruiting Expert]"; + mes "In order to start Party Recruiting, you have to click the [] button which is located in the info section of the upper left hand side."; + mes "What words go in the empty spaces of []?"; + next; + if(select("party:guild:booking:skill") == 3) + set .@correct, .@correct+10; + mes "[Party Recruiting Expert]"; + mes "If you want to know more about commands for Party Recruiting, you have to press the [] button on the Party Recruting List window."; + mes "What words go in the empty spaces of []?"; + next; + if(select("Basic Information:Help:Party:Confirm") == 2) + set .@correct, .@correct+10; + break; + case 3: + mes "[Party Recruiting Expert]"; + mes "For Party Recruiting, in order to make the"; + mes "Party Recruiting Window pop up,"; + mes "You type in this command []."; + mes "What words go in the empty spaces of []?"; + next; + if(select("/Party Collection Window:/Party Collection:/Party Recruitment Window:/Party Recruitment") == 4) + set .@correct, .@correct+10; + mes "[Party Recruiting Expert]"; + mes "When recruiting for a party, you can set 3 parameters. Those 3 are"; + mes "LEVEL, JOB, and []."; + mes "What words go in the empty spaces of []?"; + next; + if(select("SKILL:GUILD:MAP:OPTION") == 3) + set .@correct, .@correct+10; + mes "[Party Recruiting Expert]"; + mes "Party Recruiting is used to help"; + mes "users that are looking for []"; + mes "and those looking for a []."; + mes "What words go in the empty spaces of []?"; + next; + if(select("Parry, Party Members:Club, Club Members:Party, Party Members:Guild, Guild Members") == 3) + set .@correct, .@correct+10; + break; + } + if (.@correct == 30) { + mes "[Party Recruiting Expert]"; + mes "Nice! You got all 3 correct! Now do you feel more confident about ^006400Party Recruiting^000000?"; + next; + mes "[Party Recruiting Expert]"; + mes "If you ever want to hear more about ^006400Party Recruiting^000000, come find me anytime."; + next; + mes "[Party Recruiting Expert]"; + mes "Well, off you go to the ^0000FFBattleground Expert^000000! He is probably waiting for you."; + completequest 4162; + setquest 4163; + getexp 2000,1000; + close; + } + mes "[Party Recruiting Expert]"; + mes "There's only 3 questions and you didn't get them all right! At this rate, you'll fail all the Experts' tests."; + next; + mes "[Party Recruiting Expert]"; + mes "But if you want to retake the quiz! Go for it! I think you have potential! Wanna take the quiz again?"; + break; + case 2: + callsub L_Info; + mes "[Party Recruiting Expert]"; + mes "Now~ my explanations were smoother than a smooth criminal, right? Now I'm gonna give you a quiz with 3 questions. Get them all right and you've passed. Wanna take the challenge?"; + break; + case 3: + mes "[Party Recruiting Expert]"; + mes "Don't give up! You can do it! If you change your mind, come talk to me again!"; + close; + } + } + close; + case 2: + mes "[Party Recruiting Expert]"; + mes "You're gonna give up without even listening to me? If you change your mind, come talk to me again!"; + close; + } + } + mes "[Party Recruiting Expert]"; + mes "If you want to learn something from me, talk to the ^006400Siege Master^000000 first."; + close; + +L_Info: + mes "[Party Recruiting Expert]"; + mes "^006400Party Recruiting^000000 is pretty self explanatory. It helps people find party members and it helps people find parties."; + next; + mes "[Party Recruiting Expert]"; + mes "There are 2 parts to Party Recruiting."; + mes "1st step is ^0000FRegistering Party Recruiting^000000,"; + mes "and the 2nd step is ^0000FFParty Search^000000."; + next; + mes "[Party Recruiting Expert]"; + mes "In order to look up Party Recruiting, in the info window on the upper left, click the button that says ^006400booking^000000. Then the ^006400Party Recruiting List^000000 will come up."; + next; + mes "[Party Recruiting Expert]"; + mes "^006400Party Recruiting List^000000 window shows you the parties that are looking for members that was listed by other users. You can search through it."; + next; + mes "[Party Recruiting Expert]"; + mes "In the case that you don't want to join a party, but you want to recruit for one, type in the ^0000FF/Party Recruit^000000 command then in the ^006400Party Recruiting^000000 window, you can do some recruiting!"; + next; + mes "[Party Recruiting Expert]"; + mes "Once you register your party recruit notice in the ^006400Party Recruiting^000000 window, the users can search out your ^006400Party Recruiting List^000000"; + next; + mes "[Party Recruiting Expert]"; + mes "In the ^006400Party Recruiting List^000000 and"; + mes "^006400Party Recruiting^000000 you can put in basic information of what you're going to be doing, or what you're looking for like "; + mes "^006400LEVEL^000000, ^006400MAP^000000, ^006400JOB^000000."; + mes "Then the users can search using those parameters and utilizing the ^006400Party Recruitment^000000 system."; + next; + mes "[Party Recruiting Expert]"; + mes "If you want to learn more commands about ^006400Party Recruiting^000000, click on the ^006400Help^000000 button on the bottom right of the ^006400Party Recruiting list^000000."; + next; + return; +} + +moc_para01,12,179,6 script Battleground Master 419,{ + set .@checkquest, checkquest(4163); + if (.@checkquest == 2) { + mes "[Battleground Expert]"; + mes "Seeing that you sought me out, I guess you want to learn about ^006400Battleground^000000s, eh?"; + next; + switch(select("Learn about Battlegrounds.:End Conversation.")) { + case 1: + callsub L_Info; + mes "[Battleground Expert]"; + mes "There's nothing better than hearing it straight from the expert! If you want to go over it again, just talk to me."; + close; + case 2: + mes "[Battleground Expert]"; + mes "If you want to go over anything, let me know."; + close; + } + } else if (.@checkquest == 0 || .@checkquest == 1) { + mes "[Battleground Expert]"; + mes "For 16 years, I experienced the intense heat of battle on the ^006400Battleground^000000s... I am the ^006400Battleground^000000 Expert!"; + mes "It seems that the ^006400Party Recruiting Expert^000000 sent you to me since you passed his quiz."; + next; + mes "[Battleground Expert]"; + mes "You may already know but if you get pass all the quizzes from the Experts, you'll get a prize!"; + next; + mes "[Battleground Expert]"; + mes "I will tell you about the ^006400Battleground^000000s! I will tell you everything I know! How about it? Wanna hear about it?"; + next; + switch(select("Learn about Battlegrounds.:End Conversation.")) { + case 1: + callsub L_Info; + mes "[Battleground Expert]"; + mes "There's nothing better than hearing it straight from the expert! Now, do you wanna take my 3-question quiz? You have to answer all 3 correctly to pass!"; + while(1) { + set .@correct,0; + next; + switch(select("On to the quiz!:Explain again please?:Give up.")) { + case 1: + switch(rand(1,3)) { + case 1: + mes "[Battleground Expert]"; + mes "For starters, you have to pick either the side of [] Camp or [] Camp in order to to participate in Battleground."; + mes "What words go in the empty spaces of []?"; + next; + if(select("Guillaume, Tierra:Rachel, KVM:Guillaume, Croix:Maroll, KVM") == 3) + set .@correct, .@correct+10; + mes "[Battleground Expert]"; + mes "[] can do either 10vs10 and you have to attack the crystals of the opposing team while protecting yours."; + mes "What words go in the empty spaces of []?"; + next; + if(select("Tierra:Flavius:KVM:Maroll") == 2) + set .@correct, .@correct+10; + mes "[Battleground Expert]"; + mes "When you complete a battle, you may get a reward! From a KVM battle, you get []."; + mes "What words go in the empty spaces of []?"; + next; + if(select("KVM Badge:Valor Badge:Bravery Badge:Honor Badge") == 1) + set .@correct, .@correct+10; + break; + case 2: + mes "[Battleground Expert]"; + mes "For [], it's 10vs10. You also need to attack the enemies supply depot while protecting your own."; + mes "What words go in the empty spaces of []?"; + next; + if(select("Maroll:KVM:Flavius:Tierra") == 4) + set .@correct, .@correct+10; + mes "[Battleground Expert]"; + mes "In order to get into the battlegrounds, which one is not the recruiter you need to find?"; + next; + if(select("Maroll Mercenary Recruiter:KVM Mercenary Recruiter:Tierra Mercenary Recruiter:Flavius Mercenary Recruiter") == 1) + set .@correct, .@correct+10; + mes "[Battleground Expert]"; + mes "You can get [] from participating in the Battlegrounds of Tierra."; + mes "What words go in the empty spaces of []?"; + next; + if(select("KVM Badge:Valor Badge:Bravery Badge:Honor Badge") == 2) + set .@correct, .@correct+10; + break; + case 3: + mes "[Battleground Expert]"; + mes "In every major city, you can find [] to enter the Battlegrounds."; + mes "What words go in the empty spaces of []?"; + next; + if(select("Maroll Battleground Recruiter:Tierra Battleground Recruiter:Flavius Battleground Recruiter:KVM Battleground Recruiter") == 1) + set .@correct, .@correct+10; + mes "[Battleground Expert]"; + mes "For [], you go in 5vs5 with the intention of trying to reduce the number of enemies on the opposite side."; + mes "What words go in the empty spaces of []?"; + next; + if(select("Maroll:Flavius:KVM:Tierra") == 3) + set .@correct, .@correct+10; + mes "[Battleground Expert]"; + mes "When you complete a battle, you get a prize. The prize from Flavius is called []."; + mes "What words go in the empty spaces of []?"; + next; + if(select("KVM Badge:Valor Badge:Bravery Badge:Honor Badge") == 3) + set .@correct, .@correct+10; + break; + } + if (.@correct == 30) { + mes "[Battleground Expert]"; + mes "You got all 3 correct! I think you got a pretty good head on your shoulders. You know a thing or two about ^006400Battleground^000000s."; + next; + mes "[Battleground Expert]"; + mes "If you ever want to go over anything about ^006400Battleground^000000s, feel free to come talk to me!"; + next; + mes "[Battleground Expert]"; + mes "Go on and find and talk to the 0000FFMemorial Dungeon Expert^000000!"; + completequest 4163; + setquest 4164; + getexp 2000,1000; + close; + } + mes "[Battleground Expert]"; + mes "There's only 3 questions and you didn't get them all right! At this rate, you'll fail all the Experts' tests."; + next; + mes "[Battleground Expert]"; + mes "But if you want to take it on again, you should."; + break; + case 2: + callsub L_Info; + mes "[Battleground Expert]"; + mes "There's nothing better than hearing it straight from the expert! Now, do you wanna take my 3-question quiz? You have to answer all 3 correctly to pass!"; + break; + case 3: + mes "[Battleground Expert]"; + mes "Don't disappoint me by giving up. If you change your mind, come find me again."; + close; + } + } + close; + case 2: + mes "[Battleground Expert]"; + mes "You're a coward if you give up even before starting. If you change your mind, come find me again."; + close; + } + close; + } + mes "[Battleground Expert]"; + mes "If you want to learn something from me, go get acknowledged by the ^006400Party Recruiting Expert^000000 first."; + close; + +L_Info: + mes "[Battleground Expert]"; + mes "To explain ^006400Battleground^000000 easily..."; + mes "You pick either Camp ^006400Guillaume^000000 or Camp ^006400Croix^000000 then you fight each other."; + next; + mes "[Battleground Expert]"; + mes "There are 3 types of ^006400Battleground^000000s."; + mes "First is ^006400KVM^000000. It is a 5vs5 battle with the goal of reducing the number of people on either side."; + next; + mes "[Battleground Expert]"; + mes "The second one is 10vs10. You attack the supply depots of your opponents and in turn, you protect your supply depots. This is called ^006400Tierra^000000."; + next; + mes "[Battleground Expert]"; + mes "The third and final one is called ^006400Flavius^000000. This one is also 10vs10. For this one, you attack the crystals of your opponents while trying to protect your own."; + next; + mes "[Battleground Expert]"; + mes "To get to ^006400Battleground^000000s, find ^006400Maroll, the Recruiter^000000 who can be found in all major towns."; + next; + mes "[Battleground Expert]"; + mes "After you enter, pick if you want to side with Guillaume or Croix, then on their side, pick either..."; + mes "^006400KVM Mercenary Recruiter^000000,"; + mes "^006400Tierra Mercenary Recruiter^000000, or"; + mes "^006400Flavius Mercenary Recruiter^000000,"; + mes "then you can join the ^006400Battleground^000000s."; + next; + mes "[Battleground Expert]"; + mes "Depending on the outcome of the ^006400Battleground^000000 you can get a prize too."; + mes "You get KVM Badges from ^006400KVM^000000,"; + mes "from ^006400Tierra^000000 you obtain Bravery Badges and"; + mes "you receive Valor Badges ^006400Flavius^000000."; + next; + mes "[Battleground Expert]"; + mes "With the rewards from ^006400Battleground^000000s, you can get items that you can't normally get elsewhere."; + mes "Each ^006400Battleground^000000 reward you can obtain is different so you'll have to check on it."; + next; + return; +} + +moc_para01,28,167,3 script Memorial Dungeon Expert 868,{ + set .@checkquest, checkquest(4164); + if (.@checkquest == 2) { + mes "[Memorial Dungeon Expert]"; + mes "Since you've come here, it seems you want to learn about the ^006400Memorial Dungeon^000000."; + next; + switch(select("Listen about Memorial Dungeon.:End Conversation.")) { + case 1: + callsub L_Info; + mes "[Memorial Dungeon Expert]"; + mes "Now that you've listend to an expert, it's easy to understand, right? If you want to hear about it again, come find me."; + close; + case 2: + mes "[Memorial Dungeon Expert]"; + mes " If you want to hear about it again, come find me."; + close; + } + } else if (.@checkquest == 0 || .@checkquest == 1) { + mes "[Memorial Dungeon Expert]"; + mes "I am the ^006400Memorial Dungeon^000000 Expert! I studied the ^006400Memorial Dungeon^000000 for 16 years!"; + mes "Since you've sought me out, I assume that you've passed the ^006400Battleground Expert^000000's quiz."; + next; + mes "[Memorial Dungeon Expert]"; + mes "As you already know, if you pass all the Experts' quiz you'll get a prize."; + next; + mes "[Memorial Dungeon Expert]"; + mes "As the 4th Expert, I will explain everything to you about ^006400Memorial Dungeon^000000."; + mes "Want to hear about ^006400Memorial Dungeon^000000?"; + next; + switch(select("Listen about Memorial Dungeon.:End Conversation.")) { + case 1: + callsub L_Info; + mes "[Memorial Dungeon Expert]"; + mes "Now that you've listend to an expert, it's easy to understand, right? If you want to hear about it again, come find me."; + mes "Okay, now I'm gonna give you a quiz. You have to get all the questions right to pass. Ready?"; + while(1) { + set .@correct,0; + next; + switch(select("On to the quiz!:Explain again please?:Give up.")) { + case 1: + switch(rand(1,3)) { + case 1: + mes "[Memorial Dungeon Expert]"; + mes "^006400Memorial Dungeon^000000 isn't a dungeon that is open to all users. It's only available to you and your []."; + mes "What words go in the empty spaces of []?"; + next; + if(select("Party Members:Guildmates:Friends:Family") == 1) + set .@correct, .@correct+10; + mes "[Memorial Dungeon Expert]"; + mes "If you go to [] and find [], he will give you information about Endless Tower- which is a huge and tall dungeon."; + mes "What words go in the empty spaces of []?"; + next; + if(select("Prontera, Seiyablem:Alberta, Leyablem:Alberta, Captain Jansen:Prontera, Captin Jansen") == 3) + set .@correct, .@correct+10; + mes "[Memorial Dungeon Expert]"; + mes "In order to enter Memorial Dungeon the [] must apply and then be on stand-by to enter. You will enter in the order the application was put in."; + mes "What words go in the empty spaces of []?"; + next; + if(select("Guild Member:Guild Leader:Party Leader:Party Member") == 3) + set .@correct, .@correct+10; + break; + case 2: + mes "[Memorial Dungeon Expert]"; + mes "When you're done with the [], you cannot re-enter the same dungeon for a certain period of time."; + mes "What words go in the empty spaces of []?"; + next; + if(select("Buff:Ritual:Exploration:Inspection") == 3) + set .@correct, .@correct+10; + mes "[Memorial Dungeon Expert]"; + mes "If you go to the Orc Map where all the orcs live, you will be able to find []. He will probably be able to give you information about the Orc's Memory dungeon."; + mes "What words go in the empty spaces of []?"; + next; + if(select("Insane Scientist:Crazy Scientist:Insane Alchemist:Crazy Alchemist") == 1) + set .@correct, .@correct+10; + mes "[Memorial Dungeon Expert]"; + mes "In order to enter Memorial Dungeon, the [] must apply- then you'll be able to enter in order of when your application was turned in."; + mes "You have to be on stand-by for this."; + mes "What words go in the empty spaces of []?"; + next; + if(select("Guild Leader:Guildmate:Party Member:Party Leader") == 4) + set .@correct, .@correct+10; + break; + case 3: + mes "[Memorial Dungeon Expert]"; + mes "If you go to the place where you can become a monk, the Capitolina Monastery, you can meet []. He will tell you about the dungeon with the Sealed Baphomet."; + mes "What words go in the empty spaces of []?"; + next; + if(select("Agent Patrick:Patrolman Patrick:Drunken Patrick:Detective Patrick") == 4) + set .@correct, .@correct+10; + mes "[Memorial Dungeon Expert]"; + mes "When you're done with the [], you cannot re-enter the same dungeon for a certain period of time."; + mes "What words go in the empty spaces of []?"; + next; + if(select("Exploration:Inspection:Buff:Ritual") == 1) + set .@correct, .@correct+10; + mes "[Memorial Dungeon Expert]"; + mes "^006400Memorial Dungeon^000000 is not just open to all users. It is open available for you and your []."; + mes "What words go in the empty spaces of []?"; + next; + if(select("Friends:Family:Party Members:Guildmates") == 3) + set .@correct, .@correct+10; + break; + } + if (.@correct == 30) { + mes "[Memorial Dungeon Expert]"; + mes "You're pretty bright~ seeing that you got all 3 correct. Now do you understand about ^006400Memorial Dungeon^000000?"; + next; + mes "[Memorial Dungeon Expert]"; + mes "If you ever want to go over things about ^006400Memorial Dungeon^000000, come talk to me any time."; + next; + mes "[Memorial Dungeon Expert]"; + mes "Now, off you go to the the ^0000FFMap Expert^000000!"; + completequest 4164; + setquest 4165; + getexp 2000,1000; + close; + } + mes "[Memorial Dungeon Expert]"; + mes "The quiz wasn't that hard..."; + next; + mes "[Memorial Dungeon Expert]"; + mes "You look like you have potential... you should try again."; + break; + case 2: + callsub L_Info; + mes "[Memorial Dungeon Expert]"; + mes "It's easy to understand since it's coming from an expert like me. Now it's quiz time. You have to get all the answers correct to pass. Are you ready?"; + break; + case 3: + mes "[Memorial Dungeon Expert]"; + mes "Giving up is lame. If you change your mind, come talk to me."; + close; + } + } + close; + case 2: + mes "[Memorial Dungeon Expert]"; + mes "Giving up without even trying is lame. If you change your mind, come talk to me."; + close; + } + close; + } + mes "[Memorial Dungeon Expert]"; + mes "If you want to learn anything from me, talk to the ^006400Battleground Master^000000 first and get acknowledged by him."; + close; + +L_Info: + mes "[Memorial Dungeon Expert]"; + mes "The ^006400Memorial Dungeon^000000is not a dungeon that is open to everyone. It only opens to ^0000FFYou and your Party Members^000000."; + next; + mes "[Memorial Dungeon Expert]"; + mes "Therefore, in order to enter ^006400Memorial Dungeon^000000, the Party Leader must apply to enter. Since you enter in the order you apply, you must be on stand-by to enter."; + next; + mes "[Memorial Dungeon Expert]"; + mes "Also, after you explore Memorial Dungeon, you cannot re-enter the same ^006400Memorial Dungeon^000000 for a certain period of time."; + next; + mes "[Memorial Dungeon Expert]"; + mes "Many ^006400Memorial Dungeon^000000s exist, but we will give you hints to help you find Memorial Dungeon in the world of Rune Midgard."; + next; + mes "[Memorial Dungeon Expert]"; + mes "First, go to ^8B4513Alberta^000000 and find ^006400Captain Jansen^000000."; + mes "He will give you information about the really huge and tall dungeon known as ^006400Endless Tower^000000."; + next; + mes "[Memorial Dungeon Expert]"; + mes "Second, go to the ^8B4513Orc Map^000000 where all the orcs live and find the ^006400Insane Scientist^000000."; + mes "You might be able to get some information about a dungeon that has to do with ^006400Orc's Memory^000000."; + next; + mes "[Memorial Dungeon Expert]"; + mes "Third and last, seek out the place where you can become a monk, which is the ^8B4513Capitolina Monastery^000000 and seek out ^006400Detective Patrick^000000."; + mes "He will be able to give you information about the dungeon with the ^006400Sealed Baphomet^000000+."; + next; + mes "[Memorial Dungeon Expert]"; + mes "Of course there are other locations for Memorial Dungeon but it's best to start where you can find it easily."; + mes "As you continue to go on your adventures you will be able to find them more easily."; + next; + return; +} + +moc_para01,14,168,6 script Map Expert 743,{ + set .@checkquest, checkquest(4165); + if (.@checkquest == 2) { + mes "[Map Expert]"; + mes "Seeing that you came to me, I assume you have some questions about ^006400MAP^000000s?"; + next; + switch(select("List about the Map.:End Conversation.")) { + case 1: + callsub L_Info; + mes "[Map Expert]"; + mes "If you end up in those areas while you're adventuring, be sure to tell me all about it!"; + mes "And now, since you've passed all the Expert's quizzes, go on and talk to ^006400Tutorial Goal^000000."; + close; + case 2: + mes "[Map Expert]"; + mes "If you have any more questions, come find me."; + close; + } + } else if (.@checkquest == 0 || .@checkquest == 1) { + mes "[Map Expert]"; + mes "I have been researching and studying ^006400MAP^000000s for 16 years and so now I am the ^006400MAP^000000 Expert!"; + mes "Since you've sought me out, it seems you've passed ^006400Memorial Dungeon Expert^000000's quiz."; + next; + mes "[Map Expert]"; + mes "As you already know, if you pass all the Experts' quiz you'll get a prize."; + next; + mes "[Map Expert]"; + mes "As the last Expert, I will try to explain everything about ^006400MAP^000000s to make it easy on you. Ready to start?"; + next; + switch(select("Listen about Maps.:End Conversation.")) { + case 1: + callsub L_Info; + mes "[Map Expert]"; + mes "How was my explanation? Now I am gonna give you a quick quiz! You have to get all the answers correct in order to pass. Ready?"; + while(1) { + set .@correct,0; + next; + switch(select("On to the quiz!:Explain again please?:Give up.")) { + case 1: + switch(rand(1,3)) { + case 1: + mes "[Map Expert]"; + mes "You can view the map by clicking on the [] button that is located in the upper left hand side."; + mes "What words go in the empty spaces of []?"; + next; + if(select("SKILL:GUILD:MAP:BOOKING") == 3) + set .@correct, .@correct+10; + mes "[Map Expert]"; + mes "When looking at the map, each area offers the [] and [] information about the monsters. That will take all the guess work out of where you should hunt."; + mes "What words go in the empty spaces of []?"; + next; + if(select("Name, Age:Attributes, Level:Attributes, Tribe:Name, Level") == 4) + set .@correct, .@correct+10; + mes "[Map Expert]"; + mes "If you want to stop looking at the map, simple press the shortcut key of [] or ESC and it will close the map for you."; + mes "What words go in the empty spaces of []?"; + next; + if(select("ALT + F4:CTRL + %:CTRL + M:ALT + ESC") == 2) + set .@correct, .@correct+10; + break; + case 2: + mes "[Map Expert]"; + mes "After you open your map and you"; + mes "hover your mouse over specific areas"; + mes "you can see the [] and [] of the region."; + mes "What words go in the empty spaces of []?"; + next; + if(select("Name, Area Details:Name, Monster Attributes:Specialties, Area Details:Specialties, Name") == 1) + set .@correct, .@correct+10; + mes "[Map Expert]"; + mes "If you look to the bottom right of the map, you will see a drawing of []. Click on that or press the TAB shortcut key and you can find out various information."; + mes "What words go in the empty spaces of []?"; + next; + if(select("Desert Wolf:Mimic:Siroma:Poring") == 4) + set .@correct, .@correct+10; + mes "[Map Expert]"; + mes "While looking at the map, when you press the TAB shortcut key, you will be able to find and locate various dungeons and their Entrance Locations."; + mes "You can also find the [] of the monsters in that area."; + mes "What words go in the empty spaces of []?"; + next; + if(select("Name:Level:Attribute:Size") == 2) + set .@correct, .@correct+10; + break; + case 3: + mes "[Map Expert]"; + mes "If you want to stop looking at the map, all you need to do is press the [] to go back to your normal screen."; + mes "What words go in the empty spaces of []?"; + next; + if(select("O:X:EXIT:ALT") == 2) + set .@correct, .@correct+10; + mes "[Map Expert]"; + mes "While looking at the map, when you press the TAB shortcut key, you will be able to find and locate various dungeons and their Entrance Locations."; + mes "You can also find the [] of the monsters in that area."; + mes "What words go in the empty spaces of []?"; + next; + if(select("Level:Name:Size:Attribute") == 1) + set .@correct, .@correct+10; + mes "[Map Expert]"; + mes "You can view the map by clicking on the [] button that is located in the upper left hand side."; + mes "What words go in the empty spaces of []?"; + next; + if(select("GUILD:SKILL:BOOKING:MAP") == 4) + set .@correct, .@correct+10; + break; + } + if (.@correct == 30) { + mes "[Map Expert]"; + mes "Bingo! You got all 3 answers correct! Now, do you feel like you understand stuff about ^006400MAP^000000s more?"; + next; + mes "[Map Expert]"; + mes "If you ever feel like you want to learn more about ^006400MAP^000000s, come talk to me anytime."; + next; + mes "[Map Expert]"; + mes "Congrats on passing all the Experts' quizzes! Now, go find and talk to the ^006400Tutorial Goal^000000!"; + completequest 4165; + setquest 4166; + getexp 2000,1000; + close; + } + mes "[Map Expert]"; + mes "The 3 questions shouldn't have been that hard..."; + next; + mes "[Map Expert]"; + mes "Well, you seem to be pretty smart so why not try the quiz again?"; + break; + case 2: + callsub L_Info; + mes "[Map Expert]"; + mes "How is this Expert's explanations? Now I am gonna give you a quick quiz. You have to get all the answers correct to pass. Want to try it?"; + break; + case 3: + mes "[Map Expert]"; + mes "I'm the last Expert! Dont' give up! Come find me again when you're ready!"; + close; + } + } + close; + case 2: + mes "[Map Expert]"; + mes "You're gonna give up without even trying? But I'm the last Expert! Dont' give up! Come find me again when you're ready!"; + close; + } + close; + } + mes "[Map Expert]"; + mes "If you want to learn from me, go get acknowledged by the ^006400Memorial Dungeon^000000 first."; + close; + +L_Info: + mes "[Map Expert]"; + mes "A ^006400MAP^000000 shows you things that is much needed for travelling around the world; such as the lay of the land, major towns and fields and such. It's a very important tool!"; + next; + mes "[Map Expert]"; + mes "Because of this, it's more important than everything else that you know about ^006400MAP^000000s."; + next; + mes "[Map Expert]"; + mes "The map can be accessed by clicking on the button that says ^006400MAP^000000 on the upper left side of your screen."; + next; + mes "[Map Expert]"; + mes "When you click on the ^006400MAP^000000 button, a full sized map of Rune Midgards will take up your screen."; + mes "When you ^0000FFHover your mouse over specific areas^000000, you can find out more things such as ^006400NAME^000000 and Area Details."; + next; + mes "[Map Expert]"; + mes "If you look to the lower right side of your map, there is a ^006400Poring drawing^000000."; + mes "If you click on it or press the ^006400TAB^000000 shortcut key, you will be able to various information."; + next; + mes "[Map Expert]"; + mes "Firstly, you can find out the ^006400NAME^000000 and ^006400LEVEL^000000 of the monsters in each area. That will take a lot of the guess work out of where you want to go hunt."; + next; + mes "[Map Expert]"; + mes "Secondly, You can locate various ^006400DUNGEON^000000s and their"; + mes "^006400Entrance Location^000000. Plus, it'll also tell you monsters that reside in that area"; + mes "along with their ^006400LEVEL^000000. It's displayed in red so it's easy to find."; + next; + mes "[Map Expert]"; + mes "If you want to stop looking at the map, there are 2 ways to do this."; + mes "You can press the shortcut keys which are ^006400CTRL + %^000000 or ^006400ESC^000000"; + mes "Or at the top right of the map, there is a ^006400X^000000 button. Click that and you will return to your normal game screen."; + next; + mes "[Map Expert]"; + mes "Currently, we cannot see places that are beyond Rune Midgards but it has been said that there are a lot of unknown worlds that exist in the beyond."; + next; + return; +} -- cgit v1.2.3-60-g2f50 From 061951753e2ba556d9afd0cff5f1bfada0b14232 Mon Sep 17 00:00:00 2001 From: Euphy Date: Thu, 20 Jun 2013 19:33:49 -0400 Subject: Follow-up. --- npc/re/quests/eden/eden_tutorial.txt | 1 + 1 file changed, 1 insertion(+) (limited to 'npc/re') diff --git a/npc/re/quests/eden/eden_tutorial.txt b/npc/re/quests/eden/eden_tutorial.txt index 0c1519d0a..5a3d6751b 100644 --- a/npc/re/quests/eden/eden_tutorial.txt +++ b/npc/re/quests/eden/eden_tutorial.txt @@ -103,6 +103,7 @@ moc_para01,34,178,3 script Tutorial Instructor 904,{ mes "[Tutorial Instructor]"; mes "Now... Hurry and employ"; mes "a ^006400Mercenary^000000 and come back to me!"; + close; } mes "[Tutorial Instructor]"; mes "Seeing you with a ^006400Mercenary^000000 definitely makes me trust you more."; -- cgit v1.2.3-60-g2f50 From caa8a41b40a5ce3c96eb793619ff75f191ca558b Mon Sep 17 00:00:00 2001 From: Euphy Date: Thu, 20 Jun 2013 19:54:10 -0400 Subject: Follow-up. --- npc/re/quests/eden/eden_tutorial.txt | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'npc/re') diff --git a/npc/re/quests/eden/eden_tutorial.txt b/npc/re/quests/eden/eden_tutorial.txt index 5a3d6751b..c9ecd6f17 100644 --- a/npc/re/quests/eden/eden_tutorial.txt +++ b/npc/re/quests/eden/eden_tutorial.txt @@ -991,7 +991,7 @@ L_Info: next; mes "[Party Recruiting Expert]"; mes "There are 2 parts to Party Recruiting."; - mes "1st step is ^0000FRegistering Party Recruiting^000000,"; + mes "1st step is ^0000FFRegistering Party Recruiting^000000,"; mes "and the 2nd step is ^0000FFParty Search^000000."; next; mes "[Party Recruiting Expert]"; -- cgit v1.2.3-60-g2f50 From 4bf9ae53f5a95a959621a6bf79b1b958e491f283 Mon Sep 17 00:00:00 2001 From: Euphy Date: Sat, 22 Jun 2013 11:35:07 -0400 Subject: Port Malaya Jeepneys [by DeadlySilence] --- npc/re/cities/malaya.txt | 248 ++++++++++++++++++++++++++++++++++++++++++++++- 1 file changed, 247 insertions(+), 1 deletion(-) (limited to 'npc/re') diff --git a/npc/re/cities/malaya.txt b/npc/re/cities/malaya.txt index 3daff8526..b56186af0 100644 --- a/npc/re/cities/malaya.txt +++ b/npc/re/cities/malaya.txt @@ -3,13 +3,14 @@ //===== By: ================================================== //= Masao //===== Current Version: ===================================== -//= 1.0 +//= 1.1 //===== Compatible With: ===================================== //= Hercules //===== Description: ========================================= //= Many Port Malaya NPC's & Quests. //===== Additional Comments: ================================= //= 1.0 First Version. +//= 1.1 Added Jeepney script. [DeadlySilence] //============================================================ malaya,276,55,4 script Optamara Crew#malaya 100,{ @@ -1517,4 +1518,249 @@ malaya,63,185,4 script Woman#ma08 583,{ mes "[Woman]"; mes "there is rumor that the monster came from the soul of a baby that never been born. So sad."; close; +} + +function script F_Malaya_Jeepney { + .@mapName$ = getarg(0); + .@passengers = getarg(1); + + // set the other messages of varying amount) + for (.@i = 5; .@i < getargcount(); .@i++) { + setd(".@msgJeepneyInfo$[" + (.@i - 5) + "]", getarg(.@i)); + } + + if (malaya_hi < 10) { + mes "[Jeepney Driver]"; + mes getarg(2); + close; + } else if ((malaya_hi >= 10) && (malaya_hi < 20)) { + mes "[Jeepney Driver]"; + mes getarg(3); + close; + } else { + mes "[Jeepney Driver]"; + mes getarg(4); + next; + } + switch (select("Board [Passenger " + getmapusers(.@mapName$) + "/" + .@passengers +"]:Jeepney?:Are there any other Jeepneys?:Ah... Yes...")) { + case 1: + if (getmapusers(.@mapName$) >= .@passengers) { + mes "[Jeepney Driver]"; + mes "I'm afraid the Jeepney is full."; + mes "I'm sorry but how about some other Jeepney?"; + close; + } else { + mes "[Jeepney Driver]"; + mes "Have a nice day."; + close2; + warp .@mapName$,29,24; + end; + } + case 2: + // iterate through all the jeepney information for this specific NPC + for (.@i = 0; .@i < getarraysize(.@msgJeepneyInfo$); .@i++) { + // write the name as well as the individual message + mes "[Jeepney Driver]"; + mes getd(".@msgJeepneyInfo$[" + .@i + "]"); + + if (.@i < (getarraysize(.@msgJeepneyInfo$) - 1)) { + next; + } + } + close; + case 3: + mes "[Jeepney Driver]"; + mes "Oh! Other Jeepneys are in operation, of course."; + next; + mes "[Jeepney Driver]"; + mes "In Port Malaya there are 12, 30 and 60 passenger Jeepneys with 3 each operating."; + next; + mes "[Jeepney Driver]"; + mes "Would you like to know the location of other cars?"; + next; + switch (select("I'd like to know where the 12 passenger car is.:I'd like to know where the 30 passenger car is.:I'd like to know where the 60 passenger car is.")) { + case 1: + viewpoint 1, 237, 240, 1, 0xF7E009; + viewpoint 1, 67 , 44 , 2, 0xF7E009; + viewpoint 1, 282, 129, 3, 0xF7E009; + set .@zif_in, 12; + break; + case 2: + viewpoint 1, 134, 250, 4, 0xF7E009; + viewpoint 1, 341, 153, 5, 0xF7E009; + viewpoint 1, 293, 290, 6, 0xF7E009; + set .@zif_in, 30; + break; + case 3: + viewpoint 1, 242, 221, 7, 0xF7E009; + viewpoint 1, 62 , 245, 8, 0xF7E009; + viewpoint 1, 257, 58 , 9, 0xF7E009; + set .@zif_in, 60; + break; + } + mes "[Jeepney Driver]"; + mes .@zif_in+" passenger Jeepney's location has been marked on your map."; + next; + break; + } + mes "[Jeepney Driver]"; + mes "Have a nice trip."; + close; +} + +malaya,237,240,4 script Jeepney Driver#01 582,{ + callfunc( + "F_Malaya_Jeepney", // function to call + "ma_zif01", // name of the map to warp to + 12, // amount of possible jeepney passengers + + "UUrgghhhh.... I'm scared... so scared... what happened to this place?", // message for 10 > malaya_hi + "The place is still a mess... I wonder if I can operate a jeepney here...", // message for 10 >= malaya_hi < 20 + "Ha ha ha Welcome. I am ^1561EAVol^000000, operating the 12 man Jeepney here.", // message for 20 < malaya_hi + + "Is this your first time in Port Malaya?", // first entry for the monologue of variable length + "Jeepney drivers here also promote Jeepneys, so let me explain them to you.", + "Jeepneys were first developed to transport goods quickly, but are now used as public transport.", + "Since everybody has different tastes, you can see those with cool and elaborate decorations.", + "Of course you don't need to drive them yourselves, but you can ride them so please feel free to do so." + ); +} + +malaya,67,44,4 script Jeepney Driver#02 582,{ + callfunc( + "F_Malaya_Jeepney", // function to call + "ma_zif02", // name of the map to warp to + 12, // amount of possible jeepney passengers + + "Wha... What's... Going on in that hospital...", // message for 10 > malaya_hi + "I think the moaning coming from the hospital has lessened...", // message for 10 >= malaya_hi < 20 + "I'm ^1561EAChui^000000, operating a 12 man Jeepney. Hi there~", // message for 20 < malaya_hi + + "Is this your first time in Port Malaya?", // first entry for the monologue of variable length + "Jeepney drivers here also promote Jeepneys, so let me explain them to you.", + "Jeepneys were first developed to transport goods quickly, but are now used as public transport.", + "I modified my Jeepney myself...", + "For safety reasons there's a limit to the number of passengers, and it's safe so no worries..." + ); +} + +malaya,282,129,4 script Jeepney Driver#03 582,{ + callfunc( + "F_Malaya_Jeepney", // function to call + "ma_zif03", // name of the map to warp to + 12, // amount of possible jeepney passengers + + "It's not good for outsiders to have a chat... Perhaps the Mumbaki Leader may have the solution for this.", // message for 10 > malaya_hi + "Are you the adventurer who recently met Mumbaki? No wait... Then you shouldn't be here... Yes it's a ghost... Arghhhh...", // message for 10 >= malaya_hi < 20 + "The name's ^1561EATop^000000, operating one of the 3 12 man Jeepneys in town.", // message for 20 < malaya_hi + + "First time in town?", // first entry for the monologue of variable length + "Jeepney drivers here also promote Jeepneys, so let me explain them to you.", + "Jeepneys were first developed to transport goods quickly, but are now used as public transport.", + "They all look different depending on their drivers...", + "Now it is the fame of Port Malaya." + ); +} + +malaya,134,250,6 script Jeepney Driver#04 582,{ + callfunc( + "F_Malaya_Jeepney", // function to call + "ma_zif04", // name of the map to warp to + 30, // amount of possible jeepney passengers + + "G...Go... Go away...", // message for 10 > malaya_hi + "Arghh... Scared the devil out of me... Go away... Shoo...", // message for 10 >= malaya_hi < 20 + "^1561EABrav^000000, 30 man Jeepney driver at your service, driving as safely as I can since I get scared easily.", // message for 20 < malaya_hi + + "Is this your first time in Port Malaya?", // first entry for the monologue of variable length + "Jeepneys were first developed to transport goods quickly, but are now used as public transport.", + "The modified cars are decorated by their operators.", + "You come to Port Malaya, you must ride a Jeepney.", + "Ha ha ha, of course you can't drive it yourself." + ); +} + +malaya,341,153,4 script Jeepney Driver#05 582,{ + callfunc( + "F_Malaya_Jeepney", // function to call + "ma_zif05", // name of the map to warp to + 30, // amount of possible jeepney passengers + + "G... Ghosts in town... Hey... Do you have one on you?", // message for 10 > malaya_hi + "I think there are fewer ghosts now... The town is slightly quieter...", // message for 10 >= malaya_hi < 20 + "Hi I'm ^1561EALivil^000000 operator for the 30 man Jeepney. Safety is my priority.", // message for 20 < malaya_hi + + "First time in town?", // first entry for the monologue of variable length + "I'll give you a quick guide as a service.", + "Jeepneys were first developed to transport goods quickly, but are now used as public transport.", + "For safety reasons, Jeepneys have a limit on the number of passengers.", + "Some carried 180 people, but there aren't any of those in Port Malaya today." + ); +} + +malaya,293,290,6 script Jeepney Driver#06 582,{ + callfunc( + "F_Malaya_Jeepney", // function to call + "ma_zif06", // name of the map to warp to + 30, // amount of possible jeepney passengers + + "Gu... Guards... What are the guards doing...", // message for 10 > malaya_hi + "Did the guards finally do something? Phew... What a rush...", // message for 10 >= malaya_hi < 20 + "I'm ^1561EAGad^000000, the trustworthy 30 man Jeepney driver.", // message for 20 < malaya_hi + + "I see you're new to this town.", // first entry for the monologue of variable length + "To guide travelers is also my task!! Let me explain.", + "Jeepneys were goods transport vehicles, now decorated and modified with Port Malaya's new technology!!", + "This Jeepney is my very own handiwork. Ha ha ha... It's cool right? Ha ha ha", + "Even though the customer is king, I can't let you drive it... Ha ha ha" + ); +} + +malaya,242,221,4 script Jeepney Driver#07 582,{ + callfunc( + "F_Malaya_Jeepney", // function to call + "ma_zif07", // name of the map to warp to + 60, // amount of possible jeepney passengers + + "Oh no... I think the whole village is bewitched by ghosts... Maybe... I should give the Mumbaki Leader a visit...", // message for 10 > malaya_hi + "Ghost... I'm sure the Mumbaki Leader knows how to get rid of these ghosts...", // message for 10 >= malaya_hi < 20 + "^1561EAHott^000000, at your service, the safest 60 man Jeepney Operator.", // message for 20 < malaya_hi + + "Jeepney is the public transportation of Port Malaya.", // first entry for the monologue of variable length + "Therefore they are everywhere. And it's free! I know they all have different passenger limits, but that's no problem because they're everywhere." + ); +} + +malaya,62,245,6 script Jeepney Driver#08 582,{ + callfunc( + "F_Malaya_Jeepney", // function to call + "ma_zif08", // name of the map to warp to + 60, // amount of possible jeepney passengers + + "Shoo~ Be gone if you're a ghost, and go away even if you're human~ Shoo~", // message for 10 > malaya_hi + "Hey... You... Are human right? Right? Huh? Say you are... Please...", // message for 10 >= malaya_hi < 20 + "Hullo, I'm ^1561EAMuyan^000000, operator of this 60 man Jeepney. Nice to meet you.", // message for 20 < malaya_hi + + "Jeepneys are public transport, so safety is our priority.", // first entry for the monologue of variable length + "My Jeepney received the best class of Port Malaya, a '60 man Jeepney' certificate.", + "Meaning!! That it is perfectly safe!! Don't you worry about the ride." + ); +} + +malaya,257,58,6 script Jeepney Driver#09 582,{ + callfunc( + "F_Malaya_Jeepney", // function to call + "ma_zif09", // name of the map to warp to + 60, // amount of possible jeepney passengers + + "...You're an outsider... Don't go touching anything and be careful in town...", // message for 10 > malaya_hi + "The town is still quite dangerous. Best not touch anything until it is safe.", // message for 10 >= malaya_hi < 20 + "Hi there. I'm ^1561EAGramma^000000, Operator of the 60 man Jeepney of Port Malaya.", // message for 20 < malaya_hi + + "Is this your first time in Port Malaya?", // first entry for the monologue of variable length + "We Jeepney drivers here also promote Jeepneys, so let me explain them to you.", + "Jeepneys were first developed to transport goods quickly, but are now used as public transport.", + "Since everybody have different tastes, you can see those with cool and elaborate decorations.", + "Of course you don't need to drive them yourselves, but you can ride them so please feel free to do so." + ); } \ No newline at end of file -- cgit v1.2.3-60-g2f50 From 294067e15bf2d85fe9ef848c472979be637223f7 Mon Sep 17 00:00:00 2001 From: Euphy Date: Sat, 22 Jun 2013 21:46:36 -0400 Subject: Port Malay MVP Armors [by DeadlySilence] --- npc/re/quests/quests_malaya.txt | 507 ++++++++++++++++++++++++++++++++++++++++ 1 file changed, 507 insertions(+) create mode 100644 npc/re/quests/quests_malaya.txt (limited to 'npc/re') diff --git a/npc/re/quests/quests_malaya.txt b/npc/re/quests/quests_malaya.txt new file mode 100644 index 000000000..9bab65bea --- /dev/null +++ b/npc/re/quests/quests_malaya.txt @@ -0,0 +1,507 @@ +//===== rAthena Script ======================================= +//= Port Malaya Quest NPCs +//===== By: ================================================== +//= Euphy +//===== Current Version: ===================================== +//= 0.2 +//===== Compatible With: ===================================== +//= rAthena SVN +//===== Description: ========================================= +//= [Official Conversion] +//= Quest NPCs related to Port Malaya. +//===== Additional Comments: ================================= +//= 0.1 Traders only. Adapted from Masao's conversion. [Euphy] +//= 0.2 Added Tribe Blacksmith [DeadlySilence] +//============================================================ + +// Traders +//============================================================ +ma_fild01,166,214,6 script Old Man in Dilemma#GA 575,{ + if (MaxWeight - Weight < 600 || checkweight(1201,1) == 0) { + mes "Cannot proceed because you have too many items in your possession."; + close; + } + mes "[Old Man in Dilemma]"; + mes "Oh! Demons are gaining more and more power in this world."; + next; + switch(select("We need to gather items to fight them off.:Ignore.")) { + case 1: + if (countitem(6497) >= 3 && Zeny >= 1000) { + mes "[Old Man in Dilemma]"; + mes "You don't seem to be strong enough to fight off demons."; + next; + mes "[Old Man in Dilemma]"; + mes "Will you create a Greater Agimat of Ancient Spirit with 3 Lesser Agimats and 1,000 Zeny?"; + next; + if(select("Create.:No, thank you.") == 1) { + if (countitem(6497) >= 3 && Zeny >= 1000) { + specialeffect2 EF_CONE; + specialeffect EF_FORESTLIGHT2; + set Zeny, Zeny-1000; + getitem 12775,1; //Ancient_Spirit_Agimat + } else { + mes "[Old Man in Dilemma]"; + mes "Short on materials."; + close; + } + } + mes "[Old Man in Dilemma]"; + mes "Hope you win the fight with the demon."; + close; + } + mes "[Old Man in Dilemma]"; + mes "Can't make it now but there is an old way of making it handed down by generations."; + next; + mes "[Old Man in Dilemma]"; + mes "You need to call upon the power of Ancient Spirits. But you'll need several important materials first."; + next; + select("What are they?"); + mes "[Old Man in Dilemma]"; + mes "3 Lesser Agimats to hold the power of Ancient Spirits here and another special material handed down for generations."; + next; + mes "[Old Man in Dilemma]"; + mes "But nobody can get this special item anymore."; + next; + select("Something money cannot buy?"); + mes "[Old Man in Dilemma]"; + mes "No, no... It's this round little thing, you see?"; + next; + select("Are you talking about Zeny?"); + mes "[Old Man in Dilemma]"; + mes "Looks similar to the special items handed down from generations."; + next; + mes "[Old Man in Dilemma]"; + mes "As long as we have enough of that, we could make the Greater Agimat of Ancient Spirit to fight against the demons."; + next; + select("Sounds good."); + mes "[Old Man in Dilemma]"; + mes "In case you are too weary to take on the demons..."; + next; + mes "[Old Man in Dilemma]"; + mes "Come by with 3 Lesser Agimats and 1,000 of those so-called Zeny."; + next; + mes "[Old Man in Dilemma]"; + mes "I will make a Greater Agimat of Ancient Spirit that will increase your attacks against demons by 10% for 20 min."; + close; + case 2: + mes "[Old Man in Dilemma]"; + mes "Hope you win the fight with the demon."; + close; + } +} + +ma_fild01,238,198,4 script Tikbalang Expert#malaya 582,{ + if (MaxWeight - Weight < 50 || checkweight(1201,1) == 0) { + mes "Cannot proceed because you have too many items in your possession."; + close; + } + mes "[Tikbalang Expert]"; + mes "I spent 90% of my life studying Tikbalang."; + next; + switch(select("But you look young?:What is Tikbalang?:Teach me how to catch a Tikbalang.")) { + case 1: + mes "[Tikbalang Expert]"; + mes "What! I might be imagining things."; + next; + mes "[Tikbalang Expert]"; + mes "I look younger than I am because of my baby face. Ha ha ha~"; + next; + select("... ... ..."); + mes "[Tikbalang Expert]"; + mes "Trust!! They say faith will bring you luck."; + close; + case 2: + mes "[Tikbalang Expert]"; + mes "Ha ha... You ask the right question."; + mes "I'm a specialist in that field. Ask me anything."; + next; + select("Why won't you answer me?"); + mes "[Tikbalang Expert]"; + mes "Have you... ever been fooled by anyone around you? Why can't you believe someone's word for it? Really, ask me anything."; + next; + while(1) { + switch(select("I don't have any questions.:Characteristics?:Features?:Rumors?:Habitat?")) { + case 1: + mes "[Tikbalang Expert]"; + mes "I think this is enough explanation for now. You wouldn't understand other highly sophisticated topics with specific terminology and all anyway."; + next; + mes "[Tikbalang Expert]"; + mes "Oh! Do you have any other questions?"; + next; + mes "[Tikbalang Expert]"; + mes "What do you think? Impressed at how much I know? Come by anytime when you have any more questions."; + close; + case 2: + mes "[Tikbalang Expert]"; + mes "Tikbalangs have a way to confuse travelers when they meet them by making them turn in circles regardless of wherever and how far they travel."; + next; + mes "[Tikbalang Expert]"; + mes "They are mischievous creatures."; + next; + mes "[Tikbalang Expert]"; + mes "But of course there is a way to stop their pranks. You know about the Inside-out Shirt? You can either wear your top inside-out."; + next; + mes "[Tikbalang Expert]"; + mes "Or go on your way quietly without disrupting the Tikbalangs."; + next; + mes "[Tikbalang Expert]"; + mes "Ha ha ha ha~ But everyone knows adventurers are never quiet while they travel, right?"; + next; + mes "[Tikbalang Expert]"; + mes "Never..."; + break; + case 3: + mes "[Tikbalang Expert]"; + mes "They say Tikbalangs have several distinctions."; + next; + mes "[Tikbalang Expert]"; + mes "First, they are very tall ^AAAAAA(tsk... wish I were tall)^000000 and have skinny, imbalanced legs and arms. Looks almost like a human but their knees are higher than their upper body when they sit down."; + next; + mes "[Tikbalang Expert]"; + mes "Second, is the standard characteristics acknowledged by the association. They have heads and feet like a horse."; + next; + mes "[Tikbalang Expert]"; + mes "So with all these appearance traits, Tikbalang is sometimes called the creature from hell."; + break; + case 4: + mes "[Tikbalang Expert]"; + mes "There are several fun rumors about Tikbalangs."; + next; + mes "[Tikbalang Expert]"; + mes "One of them is about Tikbalangs being the guardians of some kingdom that worships nature."; + next; + mes "[Tikbalang Expert]"; + mes "So the Tikbalangs will trick travelers who come with bad intentions to the kingdom by making them travel in circles."; + next; + mes "[Tikbalang Expert]"; + mes "Another rumor is that people around here say that 'if it rains on a clear day, then it must be Tikbalang's wedding day'."; + next; + mes "[Tikbalang Expert]"; + mes "The association speculates that sayings like 'it rains on Bathory's wedding day' or 'it rains on Moonlight Flower's wedding day' might have derived from the Tikbalang's saying."; + next; + mes "[Tikbalang Expert]"; + mes "Lastly, ancient fairy tales say that Tikbalangs can transform into human form or even make themselves transparen't but nobody has verified this yet."; + break; + case 5: + mes "[Tikbalang Expert]"; + mes "Tikbalangs usually live in dark, busy places where there aren't many people around."; + next; + mes "[Tikbalang Expert]"; + mes "Hmm... For example, they are known to live beneath bridges, in banana and bamboo forests and beneath large trees."; + next; + mes "[Tikbalang Expert]"; + mes "And this is just my opinion but wouldn't you agree that they are living in dark places because it is easier to play pranks on people?"; + break; + } + next; + } + case 3: + mes "[Tikbalang Expert]"; + mes "Ha ha ha. Do you now know how great I am?"; + next; + if (countitem(6496) >= 3 && countitem(6497) >= 5) { + mes "[Tikbalang Expert]"; + mes "Oh! Isn't this material to make 'Tikbalang Belt' used to tame Tikbalangs?"; + next; + mes "[Tikbalang Expert]"; + mes "The '^F80835Tikbalang Belt^000000' is used to capture Tikbalangs without the hassle. But that doesn't mean it's 100% successful. Interested? Do you want me to make one for you?"; + next; + switch(select("Yes, Im interested.:No, I can capture one myself.")) { + case 1: + delitem 6496,3; //Tikbalang_Thick_Spine + getitem 12699,1; //Tikbalang_Belt + mes "[Tikbalang Expert]"; + mes "Yiiiiiiiiiiii! Yap!"; + next; + specialeffect EF_SONICBLOW2; + select("Huh?"); + mes "[Tikbalang Expert]"; + mes "The '^F80835Tikbalang Belt^000000' is already created."; + close; + case 2: + mes "[Tikbalang Expert]"; + mes "You? Ha... You can try if you want to."; + close; + } + } + mes "[Tikbalang Expert]"; + mes "There is the easy way and the hard way to capture Tikbalangs. Which one do you prefer?"; + next; + switch(select("Easy way.:Hard way.")) { + case 1: + mes "[Tikbalang Expert]"; + mes "Ha ha. I've come up with the easy way myself."; + next; + mes "[Tikbalang Expert]"; + mes "Bring me 3 Tikbalang's Thick Spines and 5 Lesser Agimats to make a '^F80835Tikbalang Belt^000000' to help you easily capture Tikbalangs."; + next; + mes "[Tikbalang Expert]"; + mes "Ha ha ha ha ha!"; + mes "I will say it again."; + mes "It's 3 Tikbalang's Thick Spines and 5 Lesser Agimats. Understood?"; + close; + case 2: + mes "[Tikbalang Expert]"; + mes "It's easy for me but I don't know about you."; + next; + mes "[Tikbalang Expert]"; + mes "Tikbalangs have a sharp, pointy mane behind their neck."; + next; + mes "[Tikbalang Expert]"; + mes "Of course! There are several of them but you must get the three thickest ones."; + next; + mes "[Tikbalang Expert]"; + mes "These three manes are the weak point. You can tame a Tikbalang by pulling the manes out."; + next; + mes "[Tikbalang Expert]"; + mes "Now let me explain how to pull these manes out."; + next; + mes "[Tikbalang Expert]"; + mes "You must fly like a butterfly and land like a bee on the back of a Tikbalang."; + next; + mes "[Tikbalang Expert]"; + mes "Of course! The Tikbalang will get mad and try to shake you off with all its might."; + next; + mes "[Tikbalang Expert]"; + mes "All you have to do is hold on until the Tikbalang gets exhausted."; + next; + mes "[Tikbalang Expert]"; + mes "Then again, itll take 4 days and 3 nights for Tikbalangs to get tired since they are strong creatures. But let's not focus on too much details."; + next; + mes "[Tikbalang Expert]"; + mes "Which means!! The Tikbalang is already tamed."; + close; + } + } +} + +// MVP Armors :: mvpitem +// ============================================================ +ma_fild01,158,243,6 script Tribe Blacksmith#malaya 582,{ + + mes "[Bayani]"; + mes "I will upgrade your armor if you bring one that holds enormous power."; + next; + switch (select("What kind of equipment do upgrade?:What are the required materials?:What will it become after an upgrade?:Please upgrade this.")) { + case 1: + mes "[Bayani]"; + mes "Your questions are too simple, but!"; + next; + mes "[Bayani]"; + mes "Are also important."; + next; + mes "[Bayani]"; + mes "^7B4772Bakonawa Scale Armor^000000 made from the scales of the Bakonawa monster known to swallow the moon."; + next; + mes "[Bayani]"; + mes "Light but sturdy ^7B4772Kalasag^000000 made from rattan that grows wild around Port Malaya."; + next; + mes "[Bayani]"; + mes "^7B4772Buwaya Sack Cloth^000000 made from the sack of the man-eating alligator Buwaya."; + next; + mes "[Bayani]"; + mes "^7B4772Bangungot Boots of Nightmare^000000 imbued with the hatred and vengeance of the monster Bangungot."; + next; + mes "[Bayani]"; + mes "As just mentioned."; + next; + mes "[Bayani]"; + mes "I will make powerful armor out of ONLY the strongest armor dropped from fearful monsters."; + close; + case 2: + mes "[Bayani]"; + mes "Learned well."; + mes "Seems you learned that there is no such thing as free in life."; + next; + mes "[Bayani]"; + mes "First thing to remember is that the object to upgrade must be strong itself. At least strong enough to endure ^FF0000+9 Refinement^000000."; + next; + mes "[Bayani]"; + mes "Next is true strength that only comes out of power obtained naturally. I need ^FF000020 Ancient Grudges^000000 for protection from evil while Im refining."; + next; + mes "[Bayani]"; + mes "When a ^FF0000+9 Refined Strong armor^000000 is combined with ^FF000020 Ancient Grudges^000000 for protection!!"; + next; + mes "[Bayani]"; + mes "You get a completely new and improved armor from old scraps."; + next; + mes "[Bayani]"; + mes "Always look forward to this."; + close; + case 3: + mes "[Bayani]"; + mes "Listen, because this is a very important question."; + next; + mes "[Bayani]"; + mes "It won't matter if I say it more than a 100 times that upgraded armor is powerful."; + next; + mes "[Bayani]"; + mes "Unless the one that holds it doesn't believe it is! Ask about what has changed and decide for yourself!"; + next; + while (1) { + switch (select("There is no more.:Bakonawa Scale Armor:Kalasag:Buwaya Sack Cloth:Bangungot Boots of Nightmare")) { + case 1: + mes "[Bayani]"; + mes "Looks like you ran out of questions."; + mes "Don't forget. You'll have to give up something to gain something."; + close; + case 2: + mes "[Bayani]"; + mes "The Bakonawa Scale Armor adds +1 to all stats for all jobs which is overall great armor for everyone."; + next; + mes "[Bayani]"; + mes "But I'm sure the inner you thinks this isn't enough."; + next; + mes "[Bayani]"; + mes "That is why +2 can be added to all stats and an extra slot for a card to your socket if upgraded."; + next; + break; + case 3: + mes "[Bayani]"; + mes "Kalasag is a good shield to reduce damage from boss monsters by 1% per 3 refinements."; + next; + mes "[Bayani]"; + mes "But not enough. Can't believe that a shield doesnt have a place to equip a card."; + next; + mes "[Bayani]"; + mes "That is why I can add an extra slot for a card to your socket if upgraded."; + next; + break; + case 4: + mes "[Bayani]"; + mes "The Buwaya Sack Cloth offers healing capacity and healing item effect increase by 1% per 3 refinements. Not to mention it reduces 10% damage from Water, Earth, Fire, and Wind elemental monsters."; + next; + mes "[Bayani]"; + mes "But not enough. Can't believe that these clothes don't come with a place to equip a card. Everyone knows that clothes should have Raydric on them!"; + next; + mes "[Bayani]"; + mes "Don't worry! I can add an extra slot for a card to your socket if upgraded."; + next; + break; + case 5: + mes "[Bayani]"; + mes "The Bangungot Boots of Nightmare increases +1 MDEF per 1 refinement and speed increases starting at 14 refinement and above."; + next; + mes "[Bayani]"; + mes "The speed increase effect from shoes like Moonlight Flower Shoes and Sleipnir items are out of reach for ordinary people."; + next; + mes "[Bayani]"; + mes "But of course, +14 refinement isn't easy but there is an easy way to get it."; + next; + mes "[Bayani]"; + mes "By upgrading your shoes, you can get speed increase starting from +12 refinement!"; + next; + mes "[Bayani]"; + mes "And it doesn't end there!!"; + mes "I will also put in an extra slot in your socket to add a card."; + next; + break; + } + mes "[Bayani]"; + mes "However, you'll have to give up something to gain something."; + next; + mes "[Bayani]"; + mes "^0000FFEquipping the Kalasag, Buwaya Sack Cloth, Bakonawa Scale Armor, and Bangungot Boots of Nightmare all at once will lose the ^FF0000Set Effects^0000FF.^000000"; + next; + mes "[Bayani]"; + mes "Think it through. Next question?"; + next; + } + } + mes "[Bayani]"; + mes "Ha ha ha ha ha ha ha! Good!"; + mes "You've brought the materials, right?"; + next; + if (select("Oh... sorry...:Preparations are complete!!") == 1) { + mes "[Bayani]"; + mes "Oh no!!"; + mes "I will need an light but sturdy armor with an refinement of +9 or greater and 20 Ancient Grudges!!"; + close; + } + if (countitem(6499) < 20) { + mes "[Bayani]"; + mes "You said all preparations are done and you give me this?! I need at least 20 Ancient Grudges to refine your item."; + close; + } + mes "[Bayani]"; + mes "So what armor will it be?"; + next; + switch (select("Bakonawa Scale Armor:Kalasag:Buwaya Sack Cloth:Bangungot Boots of Nightmare")) { + case 1: + .@part = EQI_ARMOR; + .@item = 15051; + .@newItem = 15052; + break; + case 2: + .@part = EQI_HAND_L; + .@item = 2169; + .@newItem = 2170; + break; + case 3: + .@part = EQI_GARMENT; + .@item = 2590; + .@newItem = 2591; + break; + case 4: + .@part = EQI_SHOES; + .@item = 2491; + .@newItem = 2492; + break; + } + + if (!(.@item)) { + mes "[Bayani]"; + mes "You should wear the equipment to upgrade and not come without it on you."; + close; + } else if (getequipid(.@part) != .@item) { + mes "[Bayani]"; + mes "What is this! You said you wanted to upgrade " + getitemname(.@item) + " but why are you giving me this? You should be wearing " + getitemname(.@item) + "."; + close; + } else if (getequiprefinerycnt(.@part) < 9) { + mes "[Bayani]"; + mes "No, the sturdiness of this item has not been tested yet. It'll have to be at least +9 refined for me to say, 'Oh this is pretty sturdy armor."; + close; + } + + mes "[Bayani]"; + mes "Looks like you did your homework! Don't see a flaw! Then I have one question to ask before I start refinement."; + next; + mes "[Bayani]"; + mes "^0000FFOnce your item is refined, the refinement level will be ^FF00000^0000FF and the item will be upgraded.^000000 You get this part?"; + next; + if (select("No.:Yes.") == 1) { + mes "[Bayani]"; + mes "What? You didn't know this? Then, read through my instructions and come back again."; + close; + } + mes "[Bayani]"; + mes "Good. Next question. Once refinement is done,"; + mes "^0000FFEquipping the Kalasag, Buwaya Sack Cloth, Bakonawa Scale Armor, and Bangungot Boots of Nightmare all at once will lose the ^FF0000Set Effects^0000FF.^000000"; + mes "Do you understand this point?"; + next; + if (select("No.:Yes.") == 1) { + mes "[Bayani]"; + mes "What? You didn't know this? Then, read through my instructions and come back again."; + close; + } + mes "[Bayani]"; + mes "Awesome! Then let's start refining " + getitemname(.@item) + "."; + next; + specialeffect EF_SONICBLOW; + mes "[Bayani]"; + mes "Pow!! Wow!! Flip... flop!"; + next; + specialeffect2 EF_TRIPLEATTACK; + mes "[Bayani]"; + mes "BAM!!"; + next; + + delitem 6499,20; //Ancient_Grudge + delequip .@part; + getitem .@newItem, 1; + + mes "[Bayani]"; + mes "Ha ha. Perfect."; + mes "Congratulations. Your armor is better than ever."; + close; +} \ No newline at end of file -- cgit v1.2.3-60-g2f50 From 28a9fec0916db3d92629ae6e6cd62b5777b09e73 Mon Sep 17 00:00:00 2001 From: j-tkay Date: Thu, 4 Jul 2013 05:15:48 +0800 Subject: Merged/Updated/Added scripts from rAthena. - Fixed Bug #7400 Signed-off-by: j-tkay --- db/quest_db.txt | 327 +++++- db/re/refine_db.txt | 11 +- npc/cities/louyang.txt | 6 +- npc/custom/healer.txt | 54 +- npc/custom/quests/hunting_missions.txt | 30 +- npc/custom/quests/quest_shop.txt | 30 +- npc/custom/warper.txt | 512 +++++---- npc/events/RWC_2011.txt | 535 ++++++++++ npc/events/RWC_2012.txt | 328 ++++++ npc/merchants/advanced_refiner.txt | 15 +- npc/merchants/refine.txt | 12 +- npc/quests/quests_13_1.txt | 3 +- npc/quests/quests_morocc.txt | 2 +- npc/quests/seals/mjolnir_seal.txt | 10 - npc/quests/the_sign_quest.txt | 7 +- npc/re/cities/eclage.txt | 487 +++++++++ npc/re/cities/malaya.txt | 2 +- npc/re/cities/mora.txt | 1351 ++++++++++++++++++----- npc/re/guides/guides_eclage.txt | 51 + npc/re/instances/MalangdoCulvert.txt | 1084 +++++++++++++++++++ npc/re/instances/OctopusCave.txt | 721 +++++++++++++ npc/re/merchants/blessed_refiner.txt | 173 +++ npc/re/merchants/coin_exchange.txt | 352 +++++- npc/re/merchants/enchan_mora.txt | 751 ++----------- npc/re/merchants/hd_refiner.txt | 308 ++++++ npc/re/merchants/refine.txt | 420 ++++---- npc/re/merchants/ticket_refiner.txt | 162 +++ npc/re/quests/eden/86-90.txt | 231 ++-- npc/re/quests/eden/91-99.txt | 249 +++-- npc/re/quests/eden/eden_quests.txt | 483 +++++---- npc/re/quests/pile_bunker.txt | 29 +- npc/re/quests/quests_dicastes.txt | 27 +- npc/re/quests/quests_eclage.txt | 1839 ++++++++++++++++++++++++++++++++ npc/re/quests/quests_malangdo.txt | 8 +- npc/re/quests/quests_malaya.txt | 982 ++++++++++++++++- npc/re/quests/quests_mora.txt | 1 + npc/re/quests/quests_morocc.txt | 213 ++++ npc/re/scripts.conf | 13 + npc/re/scripts_guild.conf | 8 + npc/re/scripts_main.conf | 1 + npc/re/scripts_warps.conf | 1 + npc/re/warps/dungeons/moc_pryd.txt | 16 + npc/re/warps/fields/bra_fild.txt | 3 +- npc/scripts.conf | 5 +- npc/warps/dungeons/tha_t.txt | 4 +- 45 files changed, 10018 insertions(+), 1839 deletions(-) create mode 100644 npc/events/RWC_2011.txt create mode 100644 npc/events/RWC_2012.txt create mode 100644 npc/re/cities/eclage.txt create mode 100644 npc/re/guides/guides_eclage.txt create mode 100644 npc/re/instances/MalangdoCulvert.txt create mode 100644 npc/re/instances/OctopusCave.txt create mode 100644 npc/re/merchants/blessed_refiner.txt create mode 100644 npc/re/merchants/hd_refiner.txt create mode 100644 npc/re/merchants/ticket_refiner.txt create mode 100644 npc/re/quests/quests_eclage.txt create mode 100644 npc/re/quests/quests_morocc.txt create mode 100644 npc/re/scripts_guild.conf create mode 100644 npc/re/warps/dungeons/moc_pryd.txt (limited to 'npc/re') diff --git a/db/quest_db.txt b/db/quest_db.txt index 6b4108ad6..c6c306070 100644 --- a/db/quest_db.txt +++ b/db/quest_db.txt @@ -31,7 +31,6 @@ 1115,0,0,0,0,0,0,0,"Ropewa & Yuridi - Song of the Abyss" 1116,0,0,0,0,0,0,0,"Ropewa & Yuridi - Dead Man's Song" 1117,0,0,0,0,0,0,0,"Ropewa & Yuridi - Eternal Promise, Broken Ring" -// Ropewa Clue Quest 1118,0,0,0,0,0,0,0,"Neighborhood Knight - I Need Clues" 1119,82800,0,0,0,0,0,0,"Neighborhood Knight - Cooldown" @@ -46,7 +45,6 @@ 1153,0,0,0,0,0,0,0,"Help the poor cat" 1154,0,2197,20,0,0,0,0,"Help the poor cat" 1155,0,0,0,0,0,0,0,"Help the poor cat" - 1174,0,0,0,0,0,0,0,"Rumor, Time and Legend" 1175,0,0,0,0,0,0,0,"Rumor, Time and Legend" 1176,0,0,0,0,0,0,0,"Rumor, Time and Legend" @@ -68,6 +66,23 @@ 1192,0,0,0,0,0,0,0,"Get Rid of Bakonawa" 1193,0,0,0,0,0,0,0,"Get Rid of Bakonawa" +// Find Professor Worm's Memory +1214,0,0,0,0,0,0,0,"Getting back Professor Worm's memory" +1215,0,0,0,0,0,0,0,"Getting back Professor Worm's memory" +1216,0,0,0,0,0,0,0,"Getting back Professor Worm's memory" +1217,0,0,0,0,0,0,0,"Getting back Professor Worm's memory" +1218,0,0,0,0,0,0,0,"Getting back Professor Worm's memory" +1219,0,0,0,0,0,0,0,"Getting back Professor Worm's memory" +1220,0,0,0,0,0,0,0,"Getting back Professor Worm's memory" +1221,0,0,0,0,0,0,0,"Getting back Professor Worm's memory" +1222,0,0,0,0,0,0,0,"Getting back Professor Worm's memory" +1223,0,0,0,0,0,0,0,"Getting back Professor Worm's memory" +1224,0,0,0,0,0,0,0,"Getting back Professor Worm's memory" +1225,0,2367,15,0,0,0,0,"Getting back Professor Worm's memory" +1226,0,0,0,0,0,0,0,"Getting back Professor Worm's memory" +1227,0,0,0,0,0,0,0,"Getting back Professor Worm's memory" +1228,0,0,0,0,0,0,0,"Getting back Professor Worm's memory" + 2000,0,0,0,0,0,0,0,"Job Change to Blacksmith" 2001,0,0,0,0,0,0,0,"Job Change to Blacksmith" 2002,0,0,0,0,0,0,0,"Job Change to Blacksmith" @@ -263,6 +278,25 @@ 2222,0,0,0,0,0,0,0,"Wanderer Job Change Quest" 2223,0,1428,100,0,0,0,0,"Generic Job Change Quest" +// Secret in the Woods +2271,0,0,0,0,0,0,0,"Secret in the Woods" +2272,0,0,0,0,0,0,0,"Secret in the Woods" +2273,0,0,0,0,0,0,0,"Secret in the Woods" +2274,0,0,0,0,0,0,0,"Secret in the Woods" +2275,0,0,0,0,0,0,0,"Secret in the Woods" +2276,0,0,0,0,0,0,0,"Secret in the Woods" +2277,0,0,0,0,0,0,0,"Secret in the Woods" +2278,0,0,0,0,0,0,0,"Secret in the Woods" +2279,0,0,0,0,0,0,0,"Secret in the Woods" +2280,0,0,0,0,0,0,0,"Secret in the Woods" +2281,0,2319,1,0,0,0,0,"Get Rid of Buwaya" + +// Pyramid (Nightmare) +2289,0,2355,20,0,0,0,0,"Verit Hunting (Nightmare)" +2290,82800,0,0,0,0,0,0,"Verit Hunting - Cooldown" +2291,82800,0,0,0,0,0,0,"Mummy Hunting - Cooldown" +2292,0,2354,20,0,0,0,0,"Mummy Hunting (Nightmare)" + // New Novice Ground 2299,0,0,0,0,0,0,0,"Training Center: Talk to Lisa" 2300,0,0,0,0,0,0,0,"Training Center: Talk to General Reindeer" @@ -474,6 +508,13 @@ 4159,0,0,0,0,0,0,0,"Homunculus S Mutation Mission - 5" 4160,0,0,0,0,0,0,0,"Homunculus S Mutation Mission - 6" +4161,0,0,0,0,0,0,0,"Siege Expert" +4162,0,0,0,0,0,0,0,"Party Recruiting Expert" +4163,0,0,0,0,0,0,0,"Battleground Expert" +4164,0,0,0,0,0,0,0,"Memorial Dungeon Expert" +4165,0,0,0,0,0,0,0,"Map Expert" +4166,0,0,0,0,0,0,0,"Passing Grades" + // Paradise 86 - 90 [Chilly] 4167,0,1321,30,0,0,0,0,"Paradise: Dragon Tail Handling" 4168,0,1322,30,0,0,0,0,"Paradise: Spring Rabbit Handling" @@ -508,7 +549,54 @@ 4195,0,1255,30,0,0,0,0,"Paradise: Neraid Handling" 4196,0,1506,30,0,0,0,0,"Paradise: Disguise Handling" -4229,0,0,0,0,0,0,0,"Devil in the Cave" +4197,10800,0,0,0,0,0,0,"Octopus" + +// Paradise Cooldowns +4198,10800,0,0,0,0,0,0,"86-90 Mission Board Timer" +4199,10800,0,0,0,0,0,0,"86-90 Mission Board Timer" +4200,10800,0,0,0,0,0,0,"86-90 Mission Board Timer" +4201,10800,0,0,0,0,0,0,"86-90 Mission Board Timer" +4202,10800,0,0,0,0,0,0,"86-90 Mission Board Timer" +4203,10800,0,0,0,0,0,0,"86-90 Mission Board Timer" +4204,10800,0,0,0,0,0,0,"86-90 Mission Board Timer" +4205,10800,0,0,0,0,0,0,"86-90 Mission Board Timer" +4206,10800,0,0,0,0,0,0,"86-90 Mission Board Timer" +4207,10800,0,0,0,0,0,0,"86-90 Mission Board Timer" +4208,10800,0,0,0,0,0,0,"86-90 Mission Board Timer" +4209,10800,0,0,0,0,0,0,"86-90 Mission Board Timer" +4210,10800,0,0,0,0,0,0,"86-90 Mission Board Timer" +4211,10800,0,0,0,0,0,0,"86-90 Mission Board Timer" +4212,10800,0,0,0,0,0,0,"91-99 Mission Board Timer" +4213,10800,0,0,0,0,0,0,"91-99 Mission Board Timer" +4214,10800,0,0,0,0,0,0,"91-99 Mission Board Timer" +4215,10800,0,0,0,0,0,0,"91-99 Mission Board Timer" +4216,10800,0,0,0,0,0,0,"91-99 Mission Board Timer" +4217,10800,0,0,0,0,0,0,"91-99 Mission Board Timer" +4218,10800,0,0,0,0,0,0,"91-99 Mission Board Timer" +4219,10800,0,0,0,0,0,0,"91-99 Mission Board Timer" +4220,10800,0,0,0,0,0,0,"91-99 Mission Board Timer" +4221,10800,0,0,0,0,0,0,"91-99 Mission Board Timer" +4222,10800,0,0,0,0,0,0,"91-99 Mission Board Timer" +4223,10800,0,0,0,0,0,0,"91-99 Mission Board Timer" +4224,10800,0,0,0,0,0,0,"91-99 Mission Board Timer" +4225,10800,0,0,0,0,0,0,"91-99 Mission Board Timer" +4226,10800,0,0,0,0,0,0,"91-99 Mission Board Timer" +4227,10800,0,0,0,0,0,0,"91-99 Mission Board Timer" + +4229,86400,0,0,0,0,0,0,"Devil in the Cave" + +4254,0,0,0,0,0,0,0,"Fairy with a stomache" +4255,0,0,0,0,0,0,0,"Revenge!" +4256,0,0,0,0,0,0,0,"An accomplice?" +4257,0,0,0,0,0,0,0,"Conspiracy" +4258,0,0,0,0,0,0,0,"Eirinn" +4259,0,0,0,0,0,0,0,"Bourbon" +4260,0,0,0,0,0,0,0,"Bee" +4261,0,0,0,0,0,0,0,"Counterattack (1)" +4262,0,0,0,0,0,0,0,"Counterattack (2)" +4263,0,0,0,0,0,0,0,"Counteroffensive (1)" +4264,0,0,0,0,0,0,0,"Counteroffensive (2)" +4265,0,0,0,0,0,0,0,"Bookshelf use" 5000,0,0,0,0,0,0,0,"The Crow of the Fate - 7" @@ -527,7 +615,6 @@ 5027,0,0,0,0,0,0,0,"Northern Pool Research" 5028,43200,0,0,0,0,0,0,"Inspection of the Sample" 5029,3600,0,0,0,0,0,0,"Unidentified Creature" - 5030,0,0,0,0,0,0,0,"The creature's family" 5031,0,0,0,0,0,0,0,"The creature's family" 5032,0,0,0,0,0,0,0,"The creature's family" @@ -617,7 +704,7 @@ 5124,0,0,0,0,0,0,0,"[Rest] Clown" 5125,0,0,0,0,0,0,0,"[Rest] Gypsy" -// Kagerou/Oboro Job Quests +// Kagerou/Oboro Job Quest 5131,0,0,0,0,0,0,0,"Strange Conversation" 5132,0,0,0,0,0,0,0,"Family Business-(1)" 5133,0,0,0,0,0,0,0,"Family Business-(2)" @@ -833,8 +920,10 @@ 7178,0,0,0,0,0,0,0,"Destination of Deception, Delusion and Gaiety" 7179,0,0,0,0,0,0,0,"Vicente, you dare!" 7180,0,0,0,0,0,0,0,"Message from Doomk" + 7181,0,0,0,0,0,0,0,"Karakas's ring" -// El Dicastes [Euphy] + +// El Dicastes 7182,0,0,0,0,0,0,0,"Sapha's Visit" 7183,0,0,0,0,0,0,0,"Invitation from Sapha" 7184,0,0,0,0,0,0,0,"To El Dicastes!" @@ -857,7 +946,6 @@ 7201,0,0,0,0,0,0,0,"Removing traces" 7202,0,0,0,0,0,0,0,"Secret order from Doha - Collect proof" 7203,0,0,0,0,0,0,0,"Secret order from Doha - Final Report" -// New Sapha's Honor Quest 7206,0,0,0,0,0,0,0,"New Day for Cheshire" 7207,0,0,0,0,0,0,0,"Cheshire's Box" 7208,86400,0,0,0,0,0,0,"Wait for Cheshire?" @@ -866,6 +954,7 @@ 7211,9000,0,0,0,0,0,0,"Misty Forest Labyrinth Exploration" 7212,0,0,0,0,0,0,0,"Loki's Search" 7213,0,0,0,0,0,0,0,"Wandering Protector" + // Paradise Gear Advanced Quests [Chilly] 7214,0,0,0,0,0,0,0,"Paradise Advanced: Romeo Training" 7215,0,1278,3,0,0,0,0,"Paradise Advanced: Romeo Hunt 1" @@ -1016,7 +1105,6 @@ 7362,0,0,0,0,0,0,0,"Deliver Holy Item to Merchant" 7363,0,0,0,0,0,0,0,"Deliver Holy Item to Little Kid" 7364,0,0,0,0,0,0,0,"Deliver Holy Item to Middle-aged Man" -// Hunting Quests 7365,0,0,0,0,0,0,0,"Better than My Old Button-2" 7366,0,0,0,0,0,0,0,"Traditional Spiritual Protection and Impudent Girl-1" 7367,0,0,0,0,0,0,0,"Traditional Spiritual Protection and Impudent Girl-2" @@ -1064,6 +1152,55 @@ 7409,0,0,0,0,0,0,0,"Cannot Meet Eyes with Him!" 7410,0,0,0,0,0,0,0,"Teach Another Lesson Tomorrow!" +// Eclage +7411,0,0,0,0,0,0,0,"The traveler, Fome's story" +7412,0,0,0,0,0,0,0,"The traveler, Litrip's story" +7413,0,0,0,0,0,0,0,"The traveler, Chiba's story" +7414,0,0,0,0,0,0,0,"Eclage guard's message" +7415,0,0,0,0,0,0,0,"Laphine's Chief of Staff" +7416,600,0,0,0,0,0,0,"Waiting to meet" +7417,0,0,0,0,0,0,0,"Kardui's request" +7418,0,0,0,0,0,0,0,"For Eclage 1" +7419,0,0,0,0,0,0,0,"For Eclage 2" +7420,0,0,0,0,0,0,0,"For Eclage 3" +7421,0,0,0,0,0,0,0,"That's enough" +7422,0,0,0,0,0,0,0,"Kardui's gift" +7423,0,0,0,0,0,0,0,"A rumor about the King 1" +7424,0,0,0,0,0,0,0,"A rumor about the King 2" +7425,0,0,0,0,0,0,0,"A rumor about the King 3" +7426,0,0,0,0,0,0,0,"A rumor about the King 4" +7427,0,0,0,0,0,0,0,"At times like this, face it straight on!" +7428,0,0,0,0,0,0,0,"Yai of the wild" +7429,0,0,0,0,0,0,0,"Wild recent trend!" +7430,0,0,0,0,0,0,0,"Deliveryman that runs through space" +7431,0,0,0,0,0,0,0,"A mailman never rests!" +7432,0,0,0,0,0,0,0,"The troublemakers in the land of blooming flowers" +7433,0,0,0,0,0,0,0,"Need constant guidance" + +// Twins and Scholar of Magics +7434,0,0,0,0,0,0,0,"Kardui's big brother" +7435,0,0,0,0,0,0,0,"Time for reading the letter" +7436,0,0,0,0,0,0,0,"Avant the Scholar of Magics" +7437,0,0,0,0,0,0,0,"Shenime's favor" +7438,0,0,0,0,0,0,0,"Secret sponsorship" +7439,0,0,0,0,0,0,0,"The scholar of magics sponsored by Shenime" +7440,0,0,0,0,0,0,0,"Minuel's witness" +7441,0,0,0,0,0,0,0,"Mail is here!" +7442,0,0,0,0,0,0,0,"The identity of the scholar of magics" +7443,0,0,0,0,0,0,0,"Interfere with the research!" +7444,0,0,0,0,0,0,0,"What Avant was researching" + +// Orb +7445,0,0,0,0,0,0,0,"Avant's back" +7446,0,0,0,0,0,0,0,"Unfruitful conversation" +7447,0,0,0,0,0,0,0,"Dilemma surrounding the Orb" +7448,0,0,0,0,0,0,0,"Something's not right" +7449,0,0,0,0,0,0,0,"Temptation toward the Orb" +7450,0,0,0,0,0,0,0,"Orb's lighting room" +7451,0,0,0,0,0,0,0,"Betrayal" +7452,0,0,0,0,0,0,0,"Find the chief of staff!" +7453,0,0,0,0,0,0,0,"The last of the chief of staff" + 8000,0,0,0,0,0,0,0,"Quitting Job Change" 8001,0,0,0,0,0,0,0,"Job Change to Assassin" 8002,0,0,0,0,0,0,0,"Job Change to Assassin" @@ -1389,10 +1526,56 @@ 9164,0,0,0,0,0,0,0,"Delivery of Good News(4)" 9165,0,0,0,0,0,0,0,"Reward from Paiko for success of Jaty Crown" +9167,0,0,0,0,0,0,0,"Tutorial - Mercenary for Hire" +9168,0,0,0,0,0,0,0,"Quest Window Check" +9169,0,0,0,0,0,0,0,"Window Shopper Catalogue" +9170,0,0,0,0,0,0,0,"Window Shopper Catalogue" +9171,0,0,0,0,0,0,0,"Enchanting Items" +9172,0,0,0,0,0,0,0,"Enchanted Items" +9173,72000,0,0,0,0,0,0,"Tutorial Timer Cooldown" + 9222,0,0,0,0,0,0,0,"Get Rid of Bangungot from Hospital 2F" 9223,0,0,0,0,0,0,0,"Will there be Peace at the Hospital?" 9224,0,0,0,0,0,0,0,"Explore Hospital 2F" +9225,0,0,0,0,0,0,0,"Mystery Robbery Incident 1" +9226,0,0,0,0,0,0,0,"Mystery Robbery Incident 2" +9227,0,0,0,0,0,0,0,"Mystery Robbery Incident 3" +9228,0,0,0,0,0,0,0,"Mystery Robbery Incident 4" +9229,0,0,0,0,0,0,0,"Mystery Robbery Incident 5" +9230,0,0,0,0,0,0,0,"Mystery Robbery Incident 6" +9231,0,0,0,0,0,0,0,"Mystery Robbery Incident 7" +9232,0,0,0,0,0,0,0,"Mystery Robbery Incident 8" +9233,0,0,0,0,0,0,0,"Mystery Robbery Incident 9" +9234,0,0,0,0,0,0,0,"Mystery Robbery Incident 10" +9235,0,0,0,0,0,0,0,"Mystery Robbery Incident 11" +9236,0,0,0,0,0,0,0,"Mystery Robbery Incident 12" +9237,0,0,0,0,0,0,0,"Mystery Robbery Incident 13" +9238,0,0,0,0,0,0,0,"Mystery Robbery Incident 14" +9239,0,0,0,0,0,0,0,"Mystery Robbery Incident 15" +9240,0,0,0,0,0,0,0,"Luen's statement notes" +9241,0,0,0,0,0,0,0,"Luen's statement notes" +9242,0,0,0,0,0,0,0,"Luen's statement notes" +9243,0,0,0,0,0,0,0,"Luen's statement notes" +9244,0,0,0,0,0,0,0,"Dames's statement notes" +9245,0,0,0,0,0,0,0,"Dames's statement notes" +9246,0,0,0,0,0,0,0,"Dames's statement notes" +9247,0,0,0,0,0,0,0,"Dames's statement notes" +9248,0,0,0,0,0,0,0,"Rosa's statement notes" +9249,0,0,0,0,0,0,0,"Rosa's statement notes" +9250,0,0,0,0,0,0,0,"Rosa's statement notes" +9251,0,0,0,0,0,0,0,"Rosa's statement notes" +9252,0,0,0,0,0,0,0,"Observing Poppy" +9253,0,0,0,0,0,0,0,"Examining a messy bookshelf" +9254,0,0,0,0,0,0,0,"Examining a damaged book" +9255,0,0,0,0,0,0,0,"Examining a container for soda cans" +9256,0,0,0,0,0,0,0,"Examining a messed up table" +9257,0,0,0,0,0,0,0,"Examining a foreign object" +9258,0,0,0,0,0,0,0,"Field examination results" +9259,0,0,0,0,0,0,0,"Confirming Cruyan's statements" +9260,0,0,0,0,0,0,0,"Survey investigation notes" +9262,0,0,0,0,0,0,0,"Mystery Robbery Incident 16" + 10000,0,0,0,0,0,0,0,"To the Prontera Royal Court" 10001,0,0,0,0,0,0,0,"Qualification Test" 10002,0,0,0,0,0,0,0,"Qualification Review" @@ -1513,7 +1696,7 @@ 10115,0,1386,20,0,0,0,0,"Juno - sleeper" 10116,0,1372,20,0,0,0,0,"Juno - Goat" 10117,0,1376,20,0,0,0,0,"Juno - Harpy" -10118,0,1269,10,0,0,0,0,"clock tower - Clock" +10118,0,1269,15,0,0,0,0,"clock tower - Clock" 10119,0,1199,15,0,0,0,0,"clock tower - Punk" 10120,0,1195,15,0,0,0,0,"clock tower - Rideword" 10121,0,1883,15,0,0,0,0,"Localizing - Uzhas" @@ -1677,12 +1860,12 @@ 11162,0,0,0,0,0,0,0,"Story of Rose" 11163,0,0,0,0,0,0,0,"Story of Bain" 11164,0,0,0,0,0,0,0,"Story of Lash" -11165,0,0,0,0,0,0,0,"Delivered to Brian" -11166,0,0,0,0,0,0,0,"Delivered to John" -11167,0,0,0,0,0,0,0,"Delivered to Tyler" -11168,0,0,0,0,0,0,0,"Delivered to Rose" -11169,0,0,0,0,0,0,0,"Delivered to Bain" -11170,0,0,0,0,0,0,0,"Delivered to Lash" +11165,0,0,0,0,0,0,0,"Delivery to Brian" +11166,0,0,0,0,0,0,0,"Delivery to John" +11167,0,0,0,0,0,0,0,"Delivery to Tyler" +11168,0,0,0,0,0,0,0,"Delivery to Rose" +11169,0,0,0,0,0,0,0,"Delivery to Bain" +11170,0,0,0,0,0,0,0,"Delivery to Lash" 11171,0,0,0,0,0,0,0,"Request from Frede" 11172,0,0,0,0,0,0,0,"Request from Frede" 11173,0,0,0,0,0,0,0,"Request from Frede" @@ -1690,11 +1873,9 @@ 11175,7200,0,0,0,0,0,0,"Supply Shortage" 11176,0,0,0,0,0,0,0,"For my friends" -//Mora Quests -// == Roast Beef Quest +// Mora 11182,60,0,0,0,0,0,0,"Theore's Report" 11183,0,0,0,0,0,0,0,"Theore's Favor" -// == Theo 11184,0,0,0,0,0,0,0,"Runaway Laphine" 11185,0,0,0,0,0,0,0,"Pouch" 11186,0,0,0,0,0,0,0,"Pouch" @@ -1703,28 +1884,23 @@ 11189,0,0,0,0,0,0,0,"Roast Beef" 11190,0,0,0,0,0,0,0,"Roast Beef" 11191,0,0,0,0,0,0,0,"Shortage of Roast Beef" - -11198,0,0,0,0,0,0,0,"Mora Village..." -11199,0,0,0,0,0,0,0,"Theo's Friend" -// == Sonya 11192,0,0,0,0,0,0,0,"Mora Village..." 11193,0,0,0,0,0,0,0,"Sonya's Friend" - 11194,0,0,0,0,0,0,0,"Runaway Laphine" 11195,0,0,0,0,0,0,0,"Pouch" 11196,0,0,0,0,0,0,0,"Pouch" 11197,0,0,0,0,0,0,0,"Pouch" -// +11198,0,0,0,0,0,0,0,"Mora Village..." +11199,0,0,0,0,0,0,0,"Theo's Friend" 11200,0,0,0,0,0,0,0,"Pouch" 11201,0,0,0,0,0,0,0,"Roast Beef" 11202,0,0,0,0,0,0,0,"Roast Beef" 11203,0,0,0,0,0,0,0,"Shortage of Roast Beef" - 11206,0,0,0,0,0,0,0,"Quick Delivery Yoneseu" 11207,0,0,0,0,0,0,0,"A Very Heavy Burden" 11208,0,0,0,0,0,0,0,"Daphne" -//Malangdo Quests +// Malangdo 11209,0,0,0,0,0,0,0,"Hardships of Thomas" 11210,0,0,0,0,0,0,0,"Malangdo Reunion" 11211,0,0,0,0,0,0,0,"Malangdo Reunion" @@ -1790,6 +1966,35 @@ 11308,0,0,0,0,0,0,0,"Nurse at Port Malaya-25" 11309,0,0,0,0,0,0,0,"Nurse at Port Malaya-26" +11310,0,0,0,0,0,0,0,"Eclage's Entrance" +11311,0,0,0,0,0,0,0,"Eclage's Entrance" +11312,0,0,0,0,0,0,0,"Goliath" +11313,0,0,0,0,0,0,0,"Goliath" +11314,0,0,0,0,0,0,0,"Goliath" +11315,0,0,0,0,0,0,0,"And time keeps on flowing" +11316,0,0,0,0,0,0,0,"And time keeps on flowing" +11317,0,0,0,0,0,0,0,"And time keeps on flowing" +11318,0,0,0,0,0,0,0,"And time keeps on flowing" +11319,0,0,0,0,0,0,0,"And time keeps on flowing" +11320,0,0,0,0,0,0,0,"And time keeps on flowing" +11321,0,0,0,0,0,0,0,"And time keeps on flowing" +11322,0,0,0,0,0,0,0,"And time keeps on flowing" +11323,0,0,0,0,0,0,0,"And time keeps on flowing" +11324,0,0,0,0,0,0,0,"And time keeps on flowing" +11325,0,0,0,0,0,0,0,"The chicken or the egg" +11326,0,0,0,0,0,0,0,"The chicken or the egg" +11327,0,0,0,0,0,0,0,"The chicken or the egg" +11328,0,0,0,0,0,0,0,"The chicken or the egg" +11329,0,0,0,0,0,0,0,"The chicken or the egg" +11330,0,0,0,0,0,0,0,"The chicken or the egg" +11331,0,0,0,0,0,0,0,"The chicken or the egg" +11332,0,0,0,0,0,0,0,"The chicken or the egg" +11333,0,0,0,0,0,0,0,"Red seed and green seed" +11334,0,0,0,0,0,0,0,"Red seed and green seed" +11335,0,0,0,0,0,0,0,"Dreaming boy" +11336,0,0,0,0,0,0,0,"Dreaming boy" +11337,0,0,0,0,0,0,0,"Dreaming boy" + 12000,0,0,0,0,0,0,0,"An old friend" 12001,0,0,0,0,0,0,0,"Digotz, Maku's old friend" 12002,0,0,0,0,0,0,0,"Messenger of Friendship" @@ -2020,6 +2225,7 @@ 12240,0,0,0,0,0,0,0,"Sticky Mucus Collecting" 12241,82800,0,0,0,0,0,0,"Mora Item Request 1" 12242,82800,0,0,0,0,0,0,"Mora Item Request 2" + // Missing Person Quests 12243,0,0,0,0,0,0,0,"Missing Information on Tajareu" 12244,0,0,0,0,0,0,0,"Missing Information on Tokenizer" @@ -2056,8 +2262,73 @@ 12273,579600,0,0,0,0,0,0,"In progress general culvert weekly service" 12274,579600,0,0,0,0,0,0,"In progress hard culvert weekly service" -12278,0,0,0,0,0,0,0,"Towards Bakonawa Lake..." -12279,0,0,0,0,0,0,0,"Get Rid of Bakonawa" +12278,604800,0,0,0,0,0,0,"Towards Bakonawa Lake..." +12279,0,2322,1,0,0,0,0,"Get Rid of Bakonawa" + +12280,0,0,0,0,0,0,0,"A suspicious prisoner" +12281,0,0,0,0,0,0,0,"An unwanted favor" +12282,0,0,0,0,0,0,0,"Gossip king Clever" +12283,0,0,0,0,0,0,0,"The rift researcher" +12284,0,0,0,0,0,0,0,"A cat merchant's source of information" +12285,0,0,0,0,0,0,0,"A way to calm down a cat" +12286,0,0,0,0,0,0,0,"Information traded for some canned foods" +12287,0,0,0,0,0,0,0,"A weird experience" +12288,0,0,0,0,0,0,0,"A successful experience" +12289,0,0,0,0,0,0,0,"Another visitation" +12290,0,0,0,0,0,0,0,"Clever's historical documents" +12291,0,0,0,0,0,0,0,"Hidden historical documents (?)" +12292,0,0,0,0,0,0,0,"The unknown ones" +12293,0,0,0,0,0,0,0,"Figures in history" +12294,0,0,0,0,0,0,0,"Tour of Eclage" +12295,0,0,0,0,0,0,0,"Error" +12296,0,0,0,0,0,0,0,"Fun times with the reactor" +12297,0,0,0,0,0,0,0,"Encountering Etran" +12298,0,0,0,0,0,0,0,"Two wishes" +12299,0,0,0,0,0,0,0,"Revisiting Robert" +12300,0,0,0,0,0,0,0,"Revisiting Etran" +12301,0,0,0,0,0,0,0,"Two remaining friends" + +13000,0,0,0,0,0,0,0,"RWC2011Card Gathering" +13001,82800,0,0,0,0,0,0,"RWC2011Card Gathering - Hold" + +13050,0,0,0,0,0,0,0,"The Laphine that loves the land" +13051,0,0,0,0,0,0,0,"The singing Laphine" +13052,0,0,0,0,0,0,0,"The watering Laphine" +13053,0,0,0,0,0,0,0,"The dancing Laphine" +13054,0,0,0,0,0,0,0,"The smiling Laphine" +13055,0,0,0,0,0,0,0,"See if all the adventurers are safe" +13056,0,0,0,0,0,0,0,"Reporter Rossi" +13057,0,0,0,0,0,0,0,"Adventurer Euncheong" +13058,0,0,0,0,0,0,0,"Troublemaker New Oz" +13059,86400,0,0,0,0,0,0,"End of project" +13060,86400,0,0,0,0,0,0,"Safety confirmation complete!" +13061,0,0,0,0,0,0,0,"Food support" +13062,86400,0,0,0,0,0,0,"Food support - complete" +13063,0,0,0,0,0,0,0,"Dusting off" +13064,86400,0,0,0,0,0,0,"Dusting off - complete" +13065,0,0,0,0,0,0,0,"Collecting a souvenir" +13066,86400,0,0,0,0,0,0,"This is enough for souvenirs" + +14118,0,0,0,0,0,0,0,"Wuhari's concern" +14119,0,0,0,0,0,0,0,"Test of patience" +14120,0,0,0,0,0,0,0,"Test of patience 2" +14121,0,0,0,0,0,0,0,"Test of patience 3" +14122,0,0,0,0,0,0,0,"Time for two" +14123,0,0,0,0,0,0,0,"Wuharu's favor" +14125,0,0,0,0,0,0,0,"Surveying the area" +14126,0,0,0,0,0,0,0,"Searching for Ms. Goatie" +14127,0,0,0,0,0,0,0,"Searching for Ms. Goatie's husband" +14128,0,0,0,0,0,0,0,"Obtaining the research report" +14131,0,0,0,0,0,0,0,"Analysis time" +14133,0,0,0,0,0,0,0,"Another favor" +14134,0,0,0,0,0,0,0,"Sharp Ms. Goatie" +14135,0,0,0,0,0,0,0,"Searching for Mr. Pompe" +14136,0,0,0,0,0,0,0,"A terrible scene in the field" +14137,0,0,0,0,0,0,0,"An interesting proposition" +14138,0,0,0,0,0,0,0,"The big corpse" +14139,0,0,0,0,0,0,0,"To Wuhuru" +14140,0,0,0,0,0,0,0,"To Wuhari" +14141,0,0,0,0,0,0,0,"Ingredients for research" 16000,0,0,0,0,0,0,0,"Metz Brayde's Notice" 16001,0,0,0,0,0,0,0,"First examination" diff --git a/db/re/refine_db.txt b/db/re/refine_db.txt index 3dad5be78..a9b7fedd1 100644 --- a/db/re/refine_db.txt +++ b/db/re/refine_db.txt @@ -27,14 +27,15 @@ // Chance: // 100 = 100% // +// Note: Chances for +11 and higher are not verified - 10% is a rumor from iRO wiki. // A note about renewal Armors, there may or may not be another bonus, according to iRO wiki: Every upgrade gives floor[( 3 + current upgrade ) / 4] equipment DEF) -0,0,0,0,100:100,100:100,100:100,100:100,60:200,40:200,40:200,20:200,20:300,10:300,50:300,30:300,30:400,20:400,10:400,10:400,10:500,10:500,10:500,10:500 +0,0,0,0,100:100,100:100,100:100,100:100,60:200,40:200,40:200,20:200,20:300,10:300,100:300,100:300,100:400,100:400,90:400,60:400,60:500,30:500,30:500,10:500 // Level 1 weapons -1,200,8,300,100:0,100:0,100:0,100:0,100:0,100:0,100:0,60:0,40:0,20:0,90:0,80:0,80:0,70:0,70:0,60:300,60:300,40:300,20:300,20:300 +1,200,8,300,100:0,100:0,100:0,100:0,100:0,100:0,100:0,60:0,40:0,20:0,100:0,100:0,100:0,100:0,100:0,100:300,100:300,90:300,60:300,20:300 // Level 2 weapons -2,300,7,500,100:0,100:0,100:0,100:0,100:0,100:0,60:0,40:0,20:0,20:0,80:0,80:0,70:0,70:0,60:0,60:600,50:600,20:600,20:600,20:600 +2,300,7,500,100:0,100:0,100:0,100:0,100:0,100:0,60:0,40:0,20:0,20:0,100:0,100:0,100:0,100:0,100:0,100:600,90:600,60:600,30:600,20:600 // Level 3 weapons -3,500,6,800,100:0,100:0,100:0,100:0,100:0,60:0,50:0,20:0,20:0,20:0,80:0,70:0,70:0,60:0,60:0,40:900,40:900,20:900,20:900,10:900 +3,500,6,800,100:0,100:0,100:0,100:0,100:0,60:0,50:0,20:0,20:0,20:0,100:0,100:0,100:0,100:0,100:0,90:900,75:900,30:900,30:900,20:900 // Level 4 weapons -4,700,5,1400,100:0,100:0,100:0,100:0,60:0,40:0,40:0,20:0,20:0,10:0,50:0,30:0,30:0,20:0,20:0,10:1200,10:1200,10:1200,10:1200,10:1200 +4,700,5,1400,100:0,100:0,100:0,100:0,60:0,40:0,40:0,20:0,20:0,10:0,100:0,100:0,100:0,100:0,90:0,60:1200,60:1200,30:1200,30:1200,10:1200 diff --git a/npc/cities/louyang.txt b/npc/cities/louyang.txt index 9f4b41f80..ac6d92307 100644 --- a/npc/cities/louyang.txt +++ b/npc/cities/louyang.txt @@ -1,5 +1,5 @@ //===== Hercules Script ====================================== -//= Louyang City NPC's +//= Louyang City NPCs //===== By: ================================================== //= Vidar (1.0) //= Mass Zero (1.1) @@ -10,14 +10,14 @@ //===== Current Version: ===================================== //= 3.0 //===== Description: ========================================= -//= [Aegis Conversion] +//= [Official Conversion] //= Louyang Town Script //===== Additional Comments: ================================= //= 2.9 Rescripted to Aegis 10.3 Standards. [L0ne_W0lf] //= 3.0 Moved Alberta NPC to pre-re/re paths. [Euphy] //============================================================ -// Louyang Transportaion +// Louyang Transportation //============================================================ - script ::Girl_louyang -1,{ mes "[Girl]"; diff --git a/npc/custom/healer.txt b/npc/custom/healer.txt index a6f028e8a..7bd9119b2 100644 --- a/npc/custom/healer.txt +++ b/npc/custom/healer.txt @@ -3,67 +3,77 @@ //===== By: ================================================== //= Euphy //===== Current Version: ===================================== -//= 1.0 +//= 1.1 //===== Compatible With: ===================================== //= Hercules //===== Description: ========================================= //= Basic healer script. +//===== Additional Comments: ================================= +//= 1.0 Initial script. +//= 1.1 Aligned coordinates with @go. //============================================================ - script Healer -1,{ - + set .@Price,0; // Zeny required for heal set .@Buffs,0; // Also buff players? (1: yes / 0: no) set .@Delay,0; // Heal delay, in seconds - callfunc "F_ClearGarbage",0; if (@HD > gettimetick(2)) end; if (.@Price) { message strcharinfo(0),"Healing costs "+.@Price+" Zeny."; if (Zeny < .@Price) end; - if(select("^0055FFHeal^000000:^777777Cancel^000000") == 2) close; + if(select("^0055FFHeal^000000:^777777Cancel^000000") == 2) end; set Zeny, Zeny-.@Price; } - specialeffect2 313; percentheal 100,100; + specialeffect2 EF_HEAL2; percentheal 100,100; if (.@Buffs) { - specialeffect2 EF_INCAGILITY; sc_start SC_INC_AGI,240000,10; + specialeffect2 EF_INCAGILITY; sc_start SC_INCREASEAGI,240000,10; specialeffect2 EF_BLESSING; sc_start SC_BLESSING,240000,10; } if (.@Delay) set @HD, gettimetick(2)+.@Delay; end; } + +// Duplicates +//============================================================ alberta,25,240,6 duplicate(Healer) Healer#alb 909 aldebaran,135,118,6 duplicate(Healer) Healer#alde 909 amatsu,200,79,4 duplicate(Healer) Healer#ama 909 ayothaya,207,169,6 duplicate(Healer) Healer#ayo 909 -brasilis,194,221,6 duplicate(Healer) Healer#bra 909 comodo,184,158,6 duplicate(Healer) Healer#com 909 -dewata,193,175,6 duplicate(Healer) Healer#dew 909 -eclage,105,35,4 duplicate(Healer) Healer#ecl 909 -einbech,142,244,4 duplicate(Healer) Healer#einbe 909 +einbech,57,36,6 duplicate(Healer) Healer#einbe 909 einbroch,57,202,6 duplicate(Healer) Healer#einbr 909 -dicastes01,201,194,4 duplicate(Healer) Healer#dic 909 geffen,115,72,6 duplicate(Healer) Healer#gef 909 gonryun,156,122,6 duplicate(Healer) Healer#gon 909 hugel,89,150,6 duplicate(Healer) Healer#hug 909 izlude,125,118,5 duplicate(Healer) Healer#izl 909 -lighthalzen,149,103,6 duplicate(Healer) Healer#li 909 -louyang,225,103,4 duplicate(Healer) Healer#lou 909 -malangdo,226,188,4 duplicate(Healer) Healer#mal 909 -malaya,205,205,6 duplicate(Healer) Healer#malay 909 -manuk,256,176,6 duplicate(Healer) Healer#man 909 +jawaii,250,139,4 duplicate(Healer) Healer#jaw 909 +lighthalzen,152,100,6 duplicate(Healer) Healer#lhz 909 +louyang,226,103,4 duplicate(Healer) Healer#lou 909 +manuk,272,144,6 duplicate(Healer) Healer#man 909 mid_camp,203,289,6 duplicate(Healer) Healer#mid 909 -mora,106,100,6 duplicate(Healer) Healer#mora 909 +moc_ruins,72,164,4 duplicate(Healer) Healer#moc 909 morocc,153,97,6 duplicate(Healer) Healer#mor 909 -moscovia,215,194,6 duplicate(Healer) Healer#mos 909 -niflheim,188,180,5 duplicate(Healer) Healer#nif 909 +moscovia,220,191,4 duplicate(Healer) Healer#mos 909 +niflheim,212,182,5 duplicate(Healer) Healer#nif 909 payon,179,106,4 duplicate(Healer) Healer#pay 909 -prontera,162,193,4 duplicate(Healer) Healer#pront 909 +prontera,162,193,4 duplicate(Healer) Healer#prt 909 rachel,125,116,6 duplicate(Healer) Healer#rac 909 splendide,201,153,4 duplicate(Healer) Healer#spl 909 thor_camp,249,74,4 duplicate(Healer) Healer#thor 909 -umbala,129,132,4 duplicate(Healer) Healer#umb 909 +umbala,105,148,3 duplicate(Healer) Healer#umb 909 veins,217,121,4 duplicate(Healer) Healer#ve 909 -xmas,143,136,6 duplicate(Healer) Healer#xmas 909 +xmas,143,136,4 duplicate(Healer) Healer#xmas 909 yuno,164,45,4 duplicate(Healer) Healer#yuno 909 + +// Duplicates (Renewal) +//============================================================ +brasilis,194,221,6 duplicate(Healer) Healer#bra 909 +dewata,195,187,4 duplicate(Healer) Healer#dew 909 +dicastes01,201,194,4 duplicate(Healer) Healer#dic 909 +ecl_in01,45,60,4 duplicate(Healer) Healer#ecl 909 +malangdo,132,114,6 duplicate(Healer) Healer#mal 909 +malaya,205,205,6 duplicate(Healer) Healer#ma 909 +mora,55,152,4 duplicate(Healer) Healer#mora 909 diff --git a/npc/custom/quests/hunting_missions.txt b/npc/custom/quests/hunting_missions.txt index fd07b8de6..8ce85bc7a 100644 --- a/npc/custom/quests/hunting_missions.txt +++ b/npc/custom/quests/hunting_missions.txt @@ -3,12 +3,19 @@ //===== By: ================================================== //= Euphy //===== Current Version: ===================================== -//= 1.3 +//= 1.3a //===== Compatible With: ===================================== //= Hercules //===== Description: ========================================= //= Random hunting missions. //= Rewards are based on quest difficulty. +//===== Additional Comments: ================================= +//= 1.0 Initial script. +//= 1.1 Small improvements and fixes. +//= 1.2 Added party support and replaced blacklists with an +//= SQL query, both thanks to AnnieRuru. +//= 1.3 Re-added a blacklist adapted for the SQL query. +//= 1.3a Added mission reset options. //============================================================ prontera,152,187,6 script Hunting Missions 951,{ @@ -72,10 +79,24 @@ function Chk; function Cm; mes "[Hunting Missions]"; mes "Do you really want to"; mes "abandon your mission?"; - if (.Delay) mes "Your delay time will not be reset."; + if (.Reset < 0 && .Delay) + mes "Your delay time will not be reset."; + else if (.Reset > 0) + mes "It will cost "+Cm(.Reset)+" Zeny."; next; switch(select(" ~ Abandon...: ~ ^777777Cancel^000000")) { case 1: + if (.Reset > 0) { + if (Zeny < .Reset) { + mes "[Hunting Missions]"; + mes "You don't have enough"; + mes "Zeny to drop this mission."; + emotion e_sry; + close; + } + set Zeny, Zeny-.Reset; + emotion e_cash; + } mes "[Hunting Missions]"; mes "Alright, I've dropped"; mes "your current mission."; @@ -85,7 +106,7 @@ function Chk; function Cm; setd "Mission"+.@i+"_",0; } set #Mission_Count,0; - if (.Delay) set #Mission_Delay, gettimetick(2)+(.Delay*3600); + if (.Reset < 0 && .Delay) set #Mission_Delay, gettimetick(2)+(.Delay*3600); close; case 2: mes "[Hunting Missions]"; @@ -262,6 +283,7 @@ OnInit: set .Delay,12; // Quest delay, in hours (0 to disable). set .Quests,4; // Number of subquests per mission (increases rewards). set .Party,3; // Party options: 0 (exclude party kills), 1 (include party kills), 2 (same map only), 3 (screen area only) + set .Reset,-1; // Reset options: -1 (abandoning mission sets delay time), 0 (no delay time), [Zeny] (cost to abandon mission, no delay time) setarray .Count[0], // Min and max monsters per subquest (increases rewards). 40,70; setarray .Modifier[0], // Multipliers for Base Exp, Job Exp, and Zeny rewards. @@ -280,4 +302,4 @@ OnInit: npcshopadditem "mission_shop", .Shop[.@i], .Shop[.@i+1]; end; } -- shop mission_shop -1,512:-1 \ No newline at end of file +- shop mission_shop -1,512:-1 diff --git a/npc/custom/quests/quest_shop.txt b/npc/custom/quests/quest_shop.txt index 3f69c73ef..3395ac102 100644 --- a/npc/custom/quests/quest_shop.txt +++ b/npc/custom/quests/quest_shop.txt @@ -3,13 +3,21 @@ //===== By: ================================================== //= Euphy //===== Current Version: ===================================== -//= 1.6 +//= 1.6a //===== Compatible With: ===================================== //= Hercules //===== Description: ========================================= //= A dynamic quest shop based on Lunar's, with easier config. //= Includes support for multiple shops & cashpoints. //= Item Preview script by ToastOfDoom. +//===== Additional Comments: ================================= +//= 1.0 Initial script. +//= 1.2 Added category support. +//= 1.3 More options and fixes. +//= 1.4 Added debug settings. +//= 1.5 Replaced categories with shop IDs. +//= 1.6 Added support for purchasing stackables. +//= 1.6a Added support for previewing costumes and robes. //============================================================ // Shop NPCs -- supplying no argument displays entire menu. @@ -116,11 +124,11 @@ OnBuyItem: mes " > "+Chk(countitem(.@q[.@i]),.@q[.@i+1]*.@q[1])+((.ShowID)?"{"+.@q[.@i]+"} ":"")+Slot(.@q[.@i])+" ("+countitem(.@q[.@i])+"/"+(.@q[.@i+1]*.@q[1])+")^000000"; next; setarray @qe[1], getiteminfo(.@q[0],5), getiteminfo(.@q[0],11); - if (((@qe[1] & 1) || (@qe[1] & 256) || (@qe[1] & 512)) && @qe[2] > 0) + if (@qe[2] > 0 && ((@qe[1] & 1) || (@qe[1] & 256) || (@qe[1] & 512) || (@qe[1] & 1024) || (@qe[1] & 2048) || (@qe[1] & 4096) || (@qe[1] & 4) || (@qe[1] & 8192))) set .@preview,1; addtimer 1000, strnpcinfo(0)+"::OnEnd"; while(1) { - switch(select(" ~ Purchase ^0055FF"+getitemname(.@q[0])+"^000000:"+((.@preview && !@qe[6])?" ~ Preview...":"")+": ~ ^777777Cancel^000000")) { + switch(select(" ~ Purchase ^0055FF"+getitemname(.@q[0])+"^000000:"+((.@preview && !@qe[7])?" ~ Preview...":"")+": ~ ^777777Cancel^000000")) { case 1: if (@qe[0]) { mes "[Quest Shop]"; @@ -138,13 +146,14 @@ OnBuyItem: delitem .@q[.@i],.@q[.@i+1]*.@q[1]; getitem .@q[0],.@q[2]; if (.Announce) announce strcharinfo(0)+" has created "+((.@q[2] > 1)?.@q[2]+"x "+getitemname(.@q[0]):A_An(getitemname(.@q[0])))+"!",0; - specialeffect2 699; + specialeffect2 EF_FLOWERLEAF; close; case 2: - setarray @qe[3], getlook(LOOK_HEAD_BOTTOM), getlook(LOOK_HEAD_TOP), getlook(LOOK_HEAD_MID), 1; - if (@qe[1] & 1) changelook LOOK_HEAD_BOTTOM, @qe[2]; - if (@qe[1] & 256) changelook LOOK_HEAD_TOP, @qe[2]; - if (@qe[1] & 512) changelook LOOK_HEAD_MID, @qe[2]; + setarray @qe[3], getlook(LOOK_HEAD_BOTTOM), getlook(LOOK_HEAD_TOP), getlook(LOOK_HEAD_MID), getlook(LOOK_ROBE), 1; + if ((@qe[1] & 1) || (@qe[1] & 4096)) changelook LOOK_HEAD_BOTTOM, @qe[2]; + else if ((@qe[1] & 256) || (@qe[1] & 1024)) changelook LOOK_HEAD_TOP, @qe[2]; + else if ((@qe[1] & 512) || (@qe[1] & 2048)) changelook LOOK_HEAD_MID, @qe[2]; + else if ((@qe[1] & 4) || (@qe[1] & 8192)) changelook LOOK_ROBE, @qe[2]; break; case 3: close; @@ -152,12 +161,13 @@ OnBuyItem: } OnEnd: - if (@qe[6]) { + if (@qe[7]) { changelook LOOK_HEAD_BOTTOM, @qe[3]; changelook LOOK_HEAD_TOP, @qe[4]; changelook LOOK_HEAD_MID, @qe[5]; + changelook LOOK_ROBE, @qe[6]; } - deletearray @qe[0],7; + deletearray @qe[0],8; end; function Add { diff --git a/npc/custom/warper.txt b/npc/custom/warper.txt index 14dcfebf0..72d3bafac 100644 --- a/npc/custom/warper.txt +++ b/npc/custom/warper.txt @@ -3,16 +3,23 @@ //===== By: ================================================== //= Euphy //===== Current Version: ===================================== -//= 1.2 +//= 1.4 //===== Compatible With: ===================================== //= Hercules //===== Description: ========================================= //= A complete - but very condensed - warper script. -//= Coordinates written largely by Tekno-Kanix and ToastOfDoom. +//= Some coordinates written by Tekno-Kanix and ToastOfDoom. +//===== Additional Comments: ================================= +//= 1.0 Initial script. +//= 1.1 Added missing duplicates and fixed coordinates. +//= 1.2 Added new episodes and simplified functions. +//= 1.3 Added Renewal checks and Instances menu. +//= Aligned coordinates with @go. +//= 1.4 Added new Guild Dungeons. //============================================================ - script Warper -1,{ -function Go; function Disp; function Pick; +function Go; function Disp; function Pick; function Restrict; // -------------------------------------------------- // Main Menu: @@ -20,21 +27,31 @@ function Go; function Disp; function Pick; menu "Last Warp ^777777["+lastwarp$+"]^000000",-, " ~ Towns",Towns, " ~ Fields",Fields, " ~ Dungeons",Dungeons, - " ~ Guild Castles",Castles, " ~ Special Areas",Special; + " ~ Guild Castles",Castles, " ~ Guild Dungeons",Guild_Dungeons, + " ~ Instances",Instances, " ~ Special Areas",Special; - if (lastwarp$ == "") dispbottom "You have not warped anywhere yet."; - else warp lastwarp$,lastwarpx,lastwarpy; - close; + if (lastwarp$ == "") + message strcharinfo(0),"You haven't warped anywhere yet."; + else + warp lastwarp$,lastwarpx,lastwarpy; + end; // ------------------- Functions ------------------- // * Go("",,); // ~ Warps directly to a map. +// // * Disp("",,); // * Pick(""{,}); -// ~ Dynamic menu and map selection. -// * Disp("","