Merge branch 'master' into refactor/cmake
This commit is contained in:
commit
b01e7da68d
@ -30,10 +30,6 @@ emblem_transparency_limit: 80
|
|||||||
// "Can't connect to local MySQL server through socket '/tmp/mysql.sock' (2)"
|
// "Can't connect to local MySQL server through socket '/tmp/mysql.sock' (2)"
|
||||||
// and you have localhost, switch it to 127.0.0.1
|
// and you have localhost, switch it to 127.0.0.1
|
||||||
|
|
||||||
// Global SQL settings
|
|
||||||
// overridden by local settings when the hostname is defined there
|
|
||||||
// (currently only the login-server reads/obeys these settings)
|
|
||||||
|
|
||||||
// MySQL Login server
|
// MySQL Login server
|
||||||
login_server_ip: 127.0.0.1
|
login_server_ip: 127.0.0.1
|
||||||
login_server_port: 3306
|
login_server_port: 3306
|
||||||
|
|||||||
@ -532,3 +532,23 @@ Body:
|
|||||||
Points: 4545
|
Points: 4545
|
||||||
- Level: 250
|
- Level: 250
|
||||||
Points: 4545
|
Points: 4545
|
||||||
|
- Level: 251
|
||||||
|
Points: 4545
|
||||||
|
- Level: 252
|
||||||
|
Points: 4545
|
||||||
|
- Level: 253
|
||||||
|
Points: 4545
|
||||||
|
- Level: 254
|
||||||
|
Points: 4545
|
||||||
|
- Level: 255
|
||||||
|
Points: 4545
|
||||||
|
- Level: 256
|
||||||
|
Points: 4545
|
||||||
|
- Level: 257
|
||||||
|
Points: 4545
|
||||||
|
- Level: 258
|
||||||
|
Points: 4545
|
||||||
|
- Level: 259
|
||||||
|
Points: 4545
|
||||||
|
- Level: 260
|
||||||
|
Points: 4545
|
||||||
|
|||||||
@ -10518,7 +10518,7 @@ Body:
|
|||||||
- Shoes_Of_Punishment # 22120
|
- Shoes_Of_Punishment # 22120
|
||||||
- Holy_Stick # 1631
|
- Holy_Stick # 1631
|
||||||
- Combo:
|
- Combo:
|
||||||
- Shoes_Of_Punishment # 22225
|
- Shoes_Of_Punishment_ # 22225
|
||||||
- Holy_Stick # 1631
|
- Holy_Stick # 1631
|
||||||
Script: |
|
Script: |
|
||||||
.@r = getequiprefinerycnt(EQI_HAND_R);
|
.@r = getequiprefinerycnt(EQI_HAND_R);
|
||||||
@ -47267,7 +47267,7 @@ Body:
|
|||||||
- Combos:
|
- Combos:
|
||||||
- Combo:
|
- Combo:
|
||||||
- Hero # 29509
|
- Hero # 29509
|
||||||
- aegis_312300 # 312300
|
- aegis_312301 # 312301
|
||||||
Script: |
|
Script: |
|
||||||
bonus2 bSkillCooldown,"BO_ACIDIFIED_ZONE_FIRE",-200;
|
bonus2 bSkillCooldown,"BO_ACIDIFIED_ZONE_FIRE",-200;
|
||||||
bonus2 bSkillCooldown,"BO_ACIDIFIED_ZONE_WATER",-200;
|
bonus2 bSkillCooldown,"BO_ACIDIFIED_ZONE_WATER",-200;
|
||||||
@ -47454,21 +47454,6 @@ Body:
|
|||||||
bonus bMaxHPrate,10;
|
bonus bMaxHPrate,10;
|
||||||
bonus bMaxSPrate,10;
|
bonus bMaxSPrate,10;
|
||||||
bonus2 bSubEle,Ele_Earth,15;
|
bonus2 bSubEle,Ele_Earth,15;
|
||||||
- Combos:
|
|
||||||
- Combo:
|
|
||||||
- Goddess_of_Abundance # 311073
|
|
||||||
- aegis_450286 # 450286
|
|
||||||
Script: |
|
|
||||||
bonus2 bAddSize,Size_All,30;
|
|
||||||
bonus2 bMagicAddSize,Size_All,30;
|
|
||||||
- Combos:
|
|
||||||
- Combo:
|
|
||||||
- Goddess_of_Abundance # 311073
|
|
||||||
- aegis_420223 # 420223
|
|
||||||
Script: |
|
|
||||||
bonus2 bSubRace,RC_Player_Human,3;
|
|
||||||
bonus2 bSubRace,RC_Player_Doram,3;
|
|
||||||
bonus bNoCastCancel;
|
|
||||||
- Combos:
|
- Combos:
|
||||||
- Combo:
|
- Combo:
|
||||||
- Bakonawa_Tattoo # 2910
|
- Bakonawa_Tattoo # 2910
|
||||||
|
|||||||
@ -40827,7 +40827,7 @@ Body:
|
|||||||
Assassin: true
|
Assassin: true
|
||||||
Priest: true
|
Priest: true
|
||||||
Locations:
|
Locations:
|
||||||
Head_Low: true
|
Head_Top: true
|
||||||
ArmorLevel: 1
|
ArmorLevel: 1
|
||||||
EquipLevelMin: 70
|
EquipLevelMin: 70
|
||||||
View: 180
|
View: 180
|
||||||
@ -48957,6 +48957,7 @@ Body:
|
|||||||
Weight: 500
|
Weight: 500
|
||||||
Defense: 5
|
Defense: 5
|
||||||
Locations:
|
Locations:
|
||||||
|
Head_Low: true
|
||||||
Head_Mid: true
|
Head_Mid: true
|
||||||
Head_Top: true
|
Head_Top: true
|
||||||
ArmorLevel: 1
|
ArmorLevel: 1
|
||||||
@ -49901,7 +49902,6 @@ Body:
|
|||||||
Weight: 500
|
Weight: 500
|
||||||
Defense: 5
|
Defense: 5
|
||||||
Locations:
|
Locations:
|
||||||
Head_Low: true
|
|
||||||
Head_Mid: true
|
Head_Mid: true
|
||||||
Head_Top: true
|
Head_Top: true
|
||||||
ArmorLevel: 1
|
ArmorLevel: 1
|
||||||
@ -49959,6 +49959,7 @@ Body:
|
|||||||
Type: Armor
|
Type: Armor
|
||||||
Defense: 5
|
Defense: 5
|
||||||
Locations:
|
Locations:
|
||||||
|
Head_Mid: true
|
||||||
Head_Top: true
|
Head_Top: true
|
||||||
ArmorLevel: 1
|
ArmorLevel: 1
|
||||||
Refineable: true
|
Refineable: true
|
||||||
@ -64053,7 +64054,7 @@ Body:
|
|||||||
KagerouOboro: true
|
KagerouOboro: true
|
||||||
Ninja: true
|
Ninja: true
|
||||||
Locations:
|
Locations:
|
||||||
Right_Hand: true
|
Both_Hand: true
|
||||||
WeaponLevel: 3
|
WeaponLevel: 3
|
||||||
EquipLevelMin: 40
|
EquipLevelMin: 40
|
||||||
Refineable: true
|
Refineable: true
|
||||||
@ -78196,7 +78197,7 @@ Body:
|
|||||||
.@d = readparam(bInt)/18;
|
.@d = readparam(bInt)/18;
|
||||||
.@e = readparam(bDex)/18;
|
.@e = readparam(bDex)/18;
|
||||||
.@f = readparam(bLuk)/18;
|
.@f = readparam(bLuk)/18;
|
||||||
skill "MC_IDENTIFY",1,0;
|
skill "MC_IDENTIFY",1;
|
||||||
bonus bHit,2*.@a;
|
bonus bHit,2*.@a;
|
||||||
bonus bMaxHPrate,2*.@a;
|
bonus bMaxHPrate,2*.@a;
|
||||||
bonus bFlee,2*.@b;
|
bonus bFlee,2*.@b;
|
||||||
@ -84118,6 +84119,7 @@ Body:
|
|||||||
Defense: 10
|
Defense: 10
|
||||||
Slots: 1
|
Slots: 1
|
||||||
Locations:
|
Locations:
|
||||||
|
Head_Mid: true
|
||||||
Head_Top: true
|
Head_Top: true
|
||||||
ArmorLevel: 1
|
ArmorLevel: 1
|
||||||
EquipLevelMin: 70
|
EquipLevelMin: 70
|
||||||
@ -96939,7 +96941,7 @@ Body:
|
|||||||
EquipLevelMin: 100
|
EquipLevelMin: 100
|
||||||
View: 1093
|
View: 1093
|
||||||
Script: |
|
Script: |
|
||||||
skill "MC_IDENTIFY",1,0;
|
skill "MC_IDENTIFY",1;
|
||||||
.@a = readparam(bStr);
|
.@a = readparam(bStr);
|
||||||
.@b = readparam(bAgi);
|
.@b = readparam(bAgi);
|
||||||
.@c = readparam(bVit);
|
.@c = readparam(bVit);
|
||||||
@ -96971,7 +96973,7 @@ Body:
|
|||||||
ArmorLevel: 1
|
ArmorLevel: 1
|
||||||
EquipLevelMin: 100
|
EquipLevelMin: 100
|
||||||
Script: |
|
Script: |
|
||||||
skill "MC_IDENTIFY",1,0;
|
skill "MC_IDENTIFY",1;
|
||||||
.@a = readparam(bStr);
|
.@a = readparam(bStr);
|
||||||
.@b = readparam(bAgi);
|
.@b = readparam(bAgi);
|
||||||
.@c = readparam(bVit);
|
.@c = readparam(bVit);
|
||||||
@ -98820,6 +98822,7 @@ Body:
|
|||||||
Type: Armor
|
Type: Armor
|
||||||
Locations:
|
Locations:
|
||||||
Costume_Head_Top: true
|
Costume_Head_Top: true
|
||||||
|
Costume_Head_Mid: true
|
||||||
ArmorLevel: 1
|
ArmorLevel: 1
|
||||||
EquipLevelMin: 1
|
EquipLevelMin: 1
|
||||||
View: 528
|
View: 528
|
||||||
@ -100887,6 +100890,14 @@ Body:
|
|||||||
NoAuction: true
|
NoAuction: true
|
||||||
Script: |
|
Script: |
|
||||||
bonus2 bExpAddRace,RC_All,10;
|
bonus2 bExpAddRace,RC_All,10;
|
||||||
|
- Id: 19766
|
||||||
|
AegisName: C_Yggdrasil_Hat
|
||||||
|
Name: Costume Yggdrasil Hat
|
||||||
|
Type: Armor
|
||||||
|
Locations:
|
||||||
|
Costume_Head_Top: true
|
||||||
|
ArmorLevel: 1
|
||||||
|
View: 997
|
||||||
- Id: 19767
|
- Id: 19767
|
||||||
AegisName: C_Home_Cherry_Blossom
|
AegisName: C_Home_Cherry_Blossom
|
||||||
Name: Costume Home Cherry Blossom
|
Name: Costume Home Cherry Blossom
|
||||||
@ -100896,14 +100907,6 @@ Body:
|
|||||||
ArmorLevel: 1
|
ArmorLevel: 1
|
||||||
EquipLevelMin: 1
|
EquipLevelMin: 1
|
||||||
View: 602
|
View: 602
|
||||||
- Id: 19766
|
|
||||||
AegisName: C_Yggdrasil_Hat
|
|
||||||
Name: Costume Yggdrasil Hat
|
|
||||||
Type: Armor
|
|
||||||
Locations:
|
|
||||||
Costume_Head_Top: true
|
|
||||||
ArmorLevel: 1
|
|
||||||
View: 997
|
|
||||||
- Id: 19768
|
- Id: 19768
|
||||||
AegisName: C_Sakura_Coronet
|
AegisName: C_Sakura_Coronet
|
||||||
Name: Costume Sakura Coronet
|
Name: Costume Sakura Coronet
|
||||||
@ -102407,8 +102410,6 @@ Body:
|
|||||||
Type: Armor
|
Type: Armor
|
||||||
Locations:
|
Locations:
|
||||||
Costume_Head_Top: true
|
Costume_Head_Top: true
|
||||||
Costume_Head_Mid: true
|
|
||||||
Costume_Head_Low: true
|
|
||||||
ArmorLevel: 1
|
ArmorLevel: 1
|
||||||
EquipLevelMin: 1
|
EquipLevelMin: 1
|
||||||
View: 636
|
View: 636
|
||||||
@ -103236,6 +103237,7 @@ Body:
|
|||||||
Type: Armor
|
Type: Armor
|
||||||
Locations:
|
Locations:
|
||||||
Costume_Head_Top: true
|
Costume_Head_Top: true
|
||||||
|
Costume_Head_Mid: true
|
||||||
ArmorLevel: 1
|
ArmorLevel: 1
|
||||||
EquipLevelMin: 1
|
EquipLevelMin: 1
|
||||||
View: 175
|
View: 175
|
||||||
@ -103669,7 +103671,7 @@ Body:
|
|||||||
Name: Costume Prayer Cherry Blossom
|
Name: Costume Prayer Cherry Blossom
|
||||||
Type: Armor
|
Type: Armor
|
||||||
Locations:
|
Locations:
|
||||||
Costume_Head_Top: true
|
Costume_Head_Mid: true
|
||||||
ArmorLevel: 1
|
ArmorLevel: 1
|
||||||
EquipLevelMin: 1
|
EquipLevelMin: 1
|
||||||
View: 1223
|
View: 1223
|
||||||
@ -107006,6 +107008,7 @@ Body:
|
|||||||
Type: Armor
|
Type: Armor
|
||||||
Locations:
|
Locations:
|
||||||
Costume_Head_Top: true
|
Costume_Head_Top: true
|
||||||
|
Costume_Head_Mid: true
|
||||||
ArmorLevel: 1
|
ArmorLevel: 1
|
||||||
EquipLevelMin: 1
|
EquipLevelMin: 1
|
||||||
View: 634
|
View: 634
|
||||||
@ -107903,7 +107906,7 @@ Body:
|
|||||||
Name: Costume Unidentified Flying Poring
|
Name: Costume Unidentified Flying Poring
|
||||||
Type: Armor
|
Type: Armor
|
||||||
Locations:
|
Locations:
|
||||||
Costume_Head_Top: true
|
Costume_Head_Low: true
|
||||||
ArmorLevel: 1
|
ArmorLevel: 1
|
||||||
EquipLevelMin: 1
|
EquipLevelMin: 1
|
||||||
View: 1017
|
View: 1017
|
||||||
@ -108180,7 +108183,7 @@ Body:
|
|||||||
Name: Costume Blessings Of Soul
|
Name: Costume Blessings Of Soul
|
||||||
Type: Armor
|
Type: Armor
|
||||||
Locations:
|
Locations:
|
||||||
Costume_Head_Low: true
|
Costume_Garment: true
|
||||||
ArmorLevel: 1
|
ArmorLevel: 1
|
||||||
EquipLevelMin: 1
|
EquipLevelMin: 1
|
||||||
Script: |
|
Script: |
|
||||||
@ -147592,7 +147595,6 @@ Body:
|
|||||||
Type: Armor
|
Type: Armor
|
||||||
Locations:
|
Locations:
|
||||||
Costume_Head_Top: true
|
Costume_Head_Top: true
|
||||||
Costume_Head_Mid: true
|
|
||||||
Costume_Head_Low: true
|
Costume_Head_Low: true
|
||||||
ArmorLevel: 1
|
ArmorLevel: 1
|
||||||
EquipLevelMin: 1
|
EquipLevelMin: 1
|
||||||
@ -148489,6 +148491,7 @@ Body:
|
|||||||
Type: Armor
|
Type: Armor
|
||||||
Locations:
|
Locations:
|
||||||
Costume_Head_Top: true
|
Costume_Head_Top: true
|
||||||
|
Costume_Head_Mid: true
|
||||||
ArmorLevel: 1
|
ArmorLevel: 1
|
||||||
EquipLevelMin: 1
|
EquipLevelMin: 1
|
||||||
View: 223
|
View: 223
|
||||||
@ -149039,7 +149042,7 @@ Body:
|
|||||||
Name: Costume War Princess Ribbon
|
Name: Costume War Princess Ribbon
|
||||||
Type: Armor
|
Type: Armor
|
||||||
Locations:
|
Locations:
|
||||||
Costume_Head_Top: true
|
Costume_Head_Mid: true
|
||||||
ArmorLevel: 1
|
ArmorLevel: 1
|
||||||
EquipLevelMin: 1
|
EquipLevelMin: 1
|
||||||
View: 1583
|
View: 1583
|
||||||
@ -154559,7 +154562,7 @@ Body:
|
|||||||
Name: Costume Savage Shoulder Bebe
|
Name: Costume Savage Shoulder Bebe
|
||||||
Type: Armor
|
Type: Armor
|
||||||
Locations:
|
Locations:
|
||||||
Costume_Head_Top: true
|
Costume_Head_Mid: true
|
||||||
ArmorLevel: 1
|
ArmorLevel: 1
|
||||||
EquipLevelMin: 1
|
EquipLevelMin: 1
|
||||||
View: 1915
|
View: 1915
|
||||||
@ -169223,6 +169226,14 @@ Body:
|
|||||||
Costume_Head_Top: true
|
Costume_Head_Top: true
|
||||||
ArmorLevel: 1
|
ArmorLevel: 1
|
||||||
View: 1001
|
View: 1001
|
||||||
|
- Id: 400558
|
||||||
|
AegisName: aegis_400558
|
||||||
|
Name: Costume Snowman Experience # !todo check english name
|
||||||
|
Type: Armor
|
||||||
|
Locations:
|
||||||
|
Costume_Head_Top: true
|
||||||
|
ArmorLevel: 1
|
||||||
|
View: 2486
|
||||||
- Id: 400574
|
- Id: 400574
|
||||||
AegisName: ROZ_Bijou_Hat_Str
|
AegisName: ROZ_Bijou_Hat_Str
|
||||||
Name: Bijou's Hat (Strength)
|
Name: Bijou's Hat (Strength)
|
||||||
@ -169397,6 +169408,14 @@ Body:
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
- Id: 400585
|
||||||
|
AegisName: aegis_400585
|
||||||
|
Name: Costume Snowman Hat # !todo check english name
|
||||||
|
Type: Armor
|
||||||
|
Locations:
|
||||||
|
Costume_Head_Top: true
|
||||||
|
ArmorLevel: 1
|
||||||
|
View: 2488
|
||||||
- Id: 410000
|
- Id: 410000
|
||||||
AegisName: Resonate_Taego_J
|
AegisName: Resonate_Taego_J
|
||||||
Name: Ancient Resonance
|
Name: Ancient Resonance
|
||||||
@ -169741,8 +169760,7 @@ Body:
|
|||||||
View: 876
|
View: 876
|
||||||
Slots: 1
|
Slots: 1
|
||||||
Locations:
|
Locations:
|
||||||
Head_Top: true
|
Head_Mid: true
|
||||||
Head_Low: true
|
|
||||||
ArmorLevel: 1
|
ArmorLevel: 1
|
||||||
EquipLevelMin: 130
|
EquipLevelMin: 130
|
||||||
Trade:
|
Trade:
|
||||||
@ -169762,8 +169780,7 @@ Body:
|
|||||||
View: 917
|
View: 917
|
||||||
Slots: 1
|
Slots: 1
|
||||||
Locations:
|
Locations:
|
||||||
Head_Top: true
|
Head_Mid: true
|
||||||
Head_Low: true
|
|
||||||
ArmorLevel: 1
|
ArmorLevel: 1
|
||||||
EquipLevelMin: 130
|
EquipLevelMin: 130
|
||||||
Trade:
|
Trade:
|
||||||
@ -169783,8 +169800,7 @@ Body:
|
|||||||
View: 906
|
View: 906
|
||||||
Slots: 1
|
Slots: 1
|
||||||
Locations:
|
Locations:
|
||||||
Head_Top: true
|
Head_Mid: true
|
||||||
Head_Low: true
|
|
||||||
ArmorLevel: 1
|
ArmorLevel: 1
|
||||||
EquipLevelMin: 130
|
EquipLevelMin: 130
|
||||||
Trade:
|
Trade:
|
||||||
@ -172200,8 +172216,8 @@ Body:
|
|||||||
Trade:
|
Trade:
|
||||||
NoDrop: true
|
NoDrop: true
|
||||||
NoTrade: true
|
NoTrade: true
|
||||||
|
NoSell: true
|
||||||
NoCart: true
|
NoCart: true
|
||||||
NoStorage: true
|
|
||||||
NoGuildStorage: true
|
NoGuildStorage: true
|
||||||
NoMail: true
|
NoMail: true
|
||||||
NoAuction: true
|
NoAuction: true
|
||||||
@ -172216,8 +172232,8 @@ Body:
|
|||||||
Trade:
|
Trade:
|
||||||
NoDrop: true
|
NoDrop: true
|
||||||
NoTrade: true
|
NoTrade: true
|
||||||
|
NoSell: true
|
||||||
NoCart: true
|
NoCart: true
|
||||||
NoStorage: true
|
|
||||||
NoGuildStorage: true
|
NoGuildStorage: true
|
||||||
NoMail: true
|
NoMail: true
|
||||||
NoAuction: true
|
NoAuction: true
|
||||||
@ -172422,6 +172438,13 @@ Body:
|
|||||||
Costume_Head_Top: true
|
Costume_Head_Top: true
|
||||||
ArmorLevel: 1
|
ArmorLevel: 1
|
||||||
View: 1463
|
View: 1463
|
||||||
|
- Id: 410295
|
||||||
|
AegisName: aegis_410295
|
||||||
|
Name: Costume Bells on a Winter Night # !todo check english name
|
||||||
|
Type: Armor
|
||||||
|
Locations:
|
||||||
|
Costume_Head_Mid: true
|
||||||
|
ArmorLevel: 1
|
||||||
- Id: 420000
|
- Id: 420000
|
||||||
AegisName: Isabella_Carrot
|
AegisName: Isabella_Carrot
|
||||||
Name: Isabella Carrot
|
Name: Isabella Carrot
|
||||||
@ -174724,6 +174747,13 @@ Body:
|
|||||||
ArmorLevel: 1
|
ArmorLevel: 1
|
||||||
EquipLevelMin: 150
|
EquipLevelMin: 150
|
||||||
View: 2448
|
View: 2448
|
||||||
|
- Id: 420304
|
||||||
|
AegisName: aegis_420304
|
||||||
|
Name: Costume Routier’s Night Sky # !todo check english name
|
||||||
|
Type: Armor
|
||||||
|
Locations:
|
||||||
|
Costume_Head_Low: true
|
||||||
|
ArmorLevel: 1
|
||||||
- Id: 430001
|
- Id: 430001
|
||||||
AegisName: C_Helm_Of_Ra
|
AegisName: C_Helm_Of_Ra
|
||||||
Name: Costume Hat of the Sun God
|
Name: Costume Hat of the Sun God
|
||||||
@ -174902,7 +174932,7 @@ Body:
|
|||||||
View: 666
|
View: 666
|
||||||
Weight: 100
|
Weight: 100
|
||||||
Locations:
|
Locations:
|
||||||
Head_Top: true
|
Head_Low: true
|
||||||
Head_Mid: true
|
Head_Mid: true
|
||||||
ArmorLevel: 1
|
ArmorLevel: 1
|
||||||
EquipLevelMin: 99
|
EquipLevelMin: 99
|
||||||
@ -174917,7 +174947,7 @@ Body:
|
|||||||
View: 693
|
View: 693
|
||||||
Weight: 100
|
Weight: 100
|
||||||
Locations:
|
Locations:
|
||||||
Head_Top: true
|
Head_Low: true
|
||||||
Head_Mid: true
|
Head_Mid: true
|
||||||
ArmorLevel: 1
|
ArmorLevel: 1
|
||||||
EquipLevelMin: 99
|
EquipLevelMin: 99
|
||||||
@ -174933,7 +174963,7 @@ Body:
|
|||||||
Weight: 100
|
Weight: 100
|
||||||
Defense: 3
|
Defense: 3
|
||||||
Locations:
|
Locations:
|
||||||
Head_Top: true
|
Head_Low: true
|
||||||
Head_Mid: true
|
Head_Mid: true
|
||||||
ArmorLevel: 1
|
ArmorLevel: 1
|
||||||
EquipLevelMin: 99
|
EquipLevelMin: 99
|
||||||
@ -174950,7 +174980,7 @@ Body:
|
|||||||
Defense: 3
|
Defense: 3
|
||||||
Slots: 1
|
Slots: 1
|
||||||
Locations:
|
Locations:
|
||||||
Head_Top: true
|
Head_Low: true
|
||||||
Head_Mid: true
|
Head_Mid: true
|
||||||
ArmorLevel: 1
|
ArmorLevel: 1
|
||||||
EquipLevelMin: 99
|
EquipLevelMin: 99
|
||||||
@ -174966,7 +174996,7 @@ Body:
|
|||||||
Weight: 100
|
Weight: 100
|
||||||
Slots: 1
|
Slots: 1
|
||||||
Locations:
|
Locations:
|
||||||
Head_Top: true
|
Head_Low: true
|
||||||
Head_Mid: true
|
Head_Mid: true
|
||||||
ArmorLevel: 1
|
ArmorLevel: 1
|
||||||
EquipLevelMin: 99
|
EquipLevelMin: 99
|
||||||
@ -174982,7 +175012,7 @@ Body:
|
|||||||
Weight: 100
|
Weight: 100
|
||||||
Slots: 1
|
Slots: 1
|
||||||
Locations:
|
Locations:
|
||||||
Head_Top: true
|
Head_Low: true
|
||||||
Head_Mid: true
|
Head_Mid: true
|
||||||
ArmorLevel: 1
|
ArmorLevel: 1
|
||||||
EquipLevelMin: 99
|
EquipLevelMin: 99
|
||||||
@ -188348,6 +188378,7 @@ Body:
|
|||||||
bonus bAtkRate,7;
|
bonus bAtkRate,7;
|
||||||
if (.@r>=9) {
|
if (.@r>=9) {
|
||||||
bonus bShortAtkRate,10;
|
bonus bShortAtkRate,10;
|
||||||
|
bonus bLongAtkRate,10;
|
||||||
if (.@r>=11) {
|
if (.@r>=11) {
|
||||||
bonus bFixedCast,-500;
|
bonus bFixedCast,-500;
|
||||||
}
|
}
|
||||||
@ -195089,6 +195120,14 @@ Body:
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
- Id: 480405
|
||||||
|
AegisName: aegis_480405
|
||||||
|
Name: Costume Santa Teddy Bear Doll Bag # !todo check english name
|
||||||
|
Type: Armor
|
||||||
|
Locations:
|
||||||
|
Costume_Garment: true
|
||||||
|
ArmorLevel: 1
|
||||||
|
View: 202
|
||||||
- Id: 490004
|
- Id: 490004
|
||||||
AegisName: Atker_Ring
|
AegisName: Atker_Ring
|
||||||
Name: Attacker Booster Ring
|
Name: Attacker Booster Ring
|
||||||
@ -203309,7 +203348,7 @@ Body:
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
if (.@g>=ENCHANTGRADE_D) {
|
if (.@g>=ENCHANTGRADE_D) {
|
||||||
bonus bShortAtkRate,5;
|
bonus bShortAtkRate,10;
|
||||||
if (.@g>=ENCHANTGRADE_C) {
|
if (.@g>=ENCHANTGRADE_C) {
|
||||||
bonus2 bAddSize,Size_All,10;
|
bonus2 bAddSize,Size_All,10;
|
||||||
if (.@g>=ENCHANTGRADE_B) {
|
if (.@g>=ENCHANTGRADE_B) {
|
||||||
@ -225854,7 +225893,7 @@ Body:
|
|||||||
All_Third: true
|
All_Third: true
|
||||||
Fourth: true
|
Fourth: true
|
||||||
Locations:
|
Locations:
|
||||||
Right_Hand: true
|
Both_Hand: true
|
||||||
WeaponLevel: 4
|
WeaponLevel: 4
|
||||||
EquipLevelMin: 150
|
EquipLevelMin: 150
|
||||||
Refineable: true
|
Refineable: true
|
||||||
|
|||||||
@ -41749,6 +41749,7 @@ Body:
|
|||||||
Buy: 20
|
Buy: 20
|
||||||
Weight: 10
|
Weight: 10
|
||||||
Locations:
|
Locations:
|
||||||
|
Head_Low: true
|
||||||
Head_Mid: true
|
Head_Mid: true
|
||||||
Head_Top: true
|
Head_Top: true
|
||||||
Flags:
|
Flags:
|
||||||
@ -41763,6 +41764,7 @@ Body:
|
|||||||
Buy: 20
|
Buy: 20
|
||||||
Weight: 10
|
Weight: 10
|
||||||
Locations:
|
Locations:
|
||||||
|
Head_Low: true
|
||||||
Head_Mid: true
|
Head_Mid: true
|
||||||
Head_Top: true
|
Head_Top: true
|
||||||
Flags:
|
Flags:
|
||||||
@ -51300,6 +51302,8 @@ Body:
|
|||||||
Type: Card
|
Type: Card
|
||||||
Weight: 10
|
Weight: 10
|
||||||
Locations:
|
Locations:
|
||||||
|
Head_Low: true
|
||||||
|
Head_Mid: true
|
||||||
Head_Top: true
|
Head_Top: true
|
||||||
Flags:
|
Flags:
|
||||||
BuyingStore: true
|
BuyingStore: true
|
||||||
@ -63337,42 +63341,42 @@ Body:
|
|||||||
Type: Card
|
Type: Card
|
||||||
SubType: Enchant
|
SubType: Enchant
|
||||||
Script: |
|
Script: |
|
||||||
autobonus "{ bonus bAtkRate,25; bonus bVit,50; }",30,10000,BF_WEAPON;
|
autobonus "{ bonus bAtkRate,25; bonus bVit,50; }",30,10000,BF_WEAPON,"{ specialeffect2 EF_POTION_BERSERK; }";
|
||||||
- Id: 311121
|
- Id: 311121
|
||||||
AegisName: Ice_F_Orb_Sp_Int
|
AegisName: Ice_F_Orb_Sp_Int
|
||||||
Name: Ice Magic Orb (Spell Buster)
|
Name: Ice Magic Orb (Spell Buster)
|
||||||
Type: Card
|
Type: Card
|
||||||
SubType: Enchant
|
SubType: Enchant
|
||||||
Script: |
|
Script: |
|
||||||
autobonus "{ bonus bMatkRate,25; bonus bInt,50; }",30,10000,BF_MAGIC;
|
autobonus "{ bonus bMatkRate,25; bonus bInt,50; }",30,10000,BF_MAGIC,"{ specialeffect2 EF_POTION_BERSERK; }";
|
||||||
- Id: 311122
|
- Id: 311122
|
||||||
AegisName: Ice_F_Orb_Fi_Dex
|
AegisName: Ice_F_Orb_Fi_Dex
|
||||||
Name: Ice Magic Orb (Firing Shot)
|
Name: Ice Magic Orb (Firing Shot)
|
||||||
Type: Card
|
Type: Card
|
||||||
SubType: Enchant
|
SubType: Enchant
|
||||||
Script: |
|
Script: |
|
||||||
autobonus "{ bonus bLongAtkRate,15; bonus bDex,50; }",30,10000,BF_WEAPON;
|
autobonus "{ bonus bLongAtkRate,15; bonus bDex,50; }",30,10000,BF_WEAPON,"{ specialeffect2 EF_POTION_BERSERK; }";
|
||||||
- Id: 311123
|
- Id: 311123
|
||||||
AegisName: Ice_F_Orb_Ov_Str
|
AegisName: Ice_F_Orb_Ov_Str
|
||||||
Name: Ice Magic Orb (Overpower)
|
Name: Ice Magic Orb (Overpower)
|
||||||
Type: Card
|
Type: Card
|
||||||
SubType: Enchant
|
SubType: Enchant
|
||||||
Script: |
|
Script: |
|
||||||
autobonus "{ bonus bShortAtkRate,15; bonus bStr,50; }",30,10000,BF_WEAPON;
|
autobonus "{ bonus bShortAtkRate,15; bonus bStr,50; }",30,10000,BF_WEAPON,"{ specialeffect2 EF_POTION_BERSERK; }";
|
||||||
- Id: 311124
|
- Id: 311124
|
||||||
AegisName: Ice_F_Orb_Fa_Agi
|
AegisName: Ice_F_Orb_Fa_Agi
|
||||||
Name: Ice Magic Orb (Fatal Flash)
|
Name: Ice Magic Orb (Fatal Flash)
|
||||||
Type: Card
|
Type: Card
|
||||||
SubType: Enchant
|
SubType: Enchant
|
||||||
Script: |
|
Script: |
|
||||||
autobonus "{ bonus bCritAtkRate,25; bonus bAgi,50; }",30,10000,BF_WEAPON;
|
autobonus "{ bonus bCritAtkRate,25; bonus bAgi,50; }",30,10000,BF_WEAPON,"{ specialeffect2 EF_POTION_BERSERK; }";
|
||||||
- Id: 311125
|
- Id: 311125
|
||||||
AegisName: Ice_F_Orb_Lu_Luk
|
AegisName: Ice_F_Orb_Lu_Luk
|
||||||
Name: Ice Magic Orb (Lucky Strike)
|
Name: Ice Magic Orb (Lucky Strike)
|
||||||
Type: Card
|
Type: Card
|
||||||
SubType: Enchant
|
SubType: Enchant
|
||||||
Script: |
|
Script: |
|
||||||
autobonus "{ bonus2 bMagicAtkEle,Ele_All,15; bonus bLuk,50; }",30,10000,BF_MAGIC;
|
autobonus "{ bonus2 bMagicAtkEle,Ele_All,15; bonus bLuk,50; }",30,10000,BF_MAGIC,"{ specialeffect2 EF_POTION_BERSERK; }";
|
||||||
- Id: 311126
|
- Id: 311126
|
||||||
AegisName: Ice_F_Orb_A_Delay
|
AegisName: Ice_F_Orb_A_Delay
|
||||||
Name: Ice Magic Orb (Delay After Attack)
|
Name: Ice Magic Orb (Delay After Attack)
|
||||||
@ -70935,7 +70939,7 @@ Body:
|
|||||||
.@g = getenchantgrade();
|
.@g = getenchantgrade();
|
||||||
bonus bMaxHPrate,-5;
|
bonus bMaxHPrate,-5;
|
||||||
bonus bMaxSPrate,-5;
|
bonus bMaxSPrate,-5;
|
||||||
autobonus "{ bonus bStr,50; bonus bPow,15; bonus bSta,15; }",30,10000,BF_WEAPON;
|
autobonus "{ bonus bStr,50; bonus bPow,15; bonus bSta,15; }",30,10000,BF_WEAPON,"{ specialeffect2 EF_POTION_BERSERK; }";
|
||||||
if (.@g>=ENCHANTGRADE_D) {
|
if (.@g>=ENCHANTGRADE_D) {
|
||||||
bonus bLongAtkRate,5;
|
bonus bLongAtkRate,5;
|
||||||
bonus bShortAtkRate,5;
|
bonus bShortAtkRate,5;
|
||||||
@ -70953,7 +70957,7 @@ Body:
|
|||||||
.@g = getenchantgrade();
|
.@g = getenchantgrade();
|
||||||
bonus bMaxHPrate,-5;
|
bonus bMaxHPrate,-5;
|
||||||
bonus bMaxSPrate,-5;
|
bonus bMaxSPrate,-5;
|
||||||
autobonus "{ bonus bInt,50; bonus bWis,15; bonus bSpl,15; }",30,10000,BF_MAGIC;
|
autobonus "{ bonus bInt,50; bonus bWis,15; bonus bSpl,15; }",30,10000,BF_MAGIC,"{ specialeffect2 EF_POTION_BERSERK; }";
|
||||||
if (.@g>=ENCHANTGRADE_D) {
|
if (.@g>=ENCHANTGRADE_D) {
|
||||||
bonus2 bMagicAtkEle,Ele_All,5;
|
bonus2 bMagicAtkEle,Ele_All,5;
|
||||||
if (.@g>=ENCHANTGRADE_C) {
|
if (.@g>=ENCHANTGRADE_C) {
|
||||||
@ -70969,7 +70973,7 @@ Body:
|
|||||||
.@g = getenchantgrade();
|
.@g = getenchantgrade();
|
||||||
bonus bMaxHPrate,-5;
|
bonus bMaxHPrate,-5;
|
||||||
bonus bMaxSPrate,-5;
|
bonus bMaxSPrate,-5;
|
||||||
autobonus "{ bonus bDex,50; bonus bCon,15; bonus bCrt,15; }",30,10000,BF_WEAPON;
|
autobonus "{ bonus bDex,50; bonus bCon,15; bonus bCrt,15; }",30,10000,BF_WEAPON,"{ specialeffect2 EF_POTION_BERSERK; }";
|
||||||
if (.@g>=ENCHANTGRADE_D) {
|
if (.@g>=ENCHANTGRADE_D) {
|
||||||
bonus bLongAtkRate,5;
|
bonus bLongAtkRate,5;
|
||||||
bonus bShortAtkRate,5;
|
bonus bShortAtkRate,5;
|
||||||
@ -78734,6 +78738,7 @@ Body:
|
|||||||
Trade:
|
Trade:
|
||||||
NoDrop: true
|
NoDrop: true
|
||||||
NoTrade: true
|
NoTrade: true
|
||||||
|
NoSell: true
|
||||||
NoCart: true
|
NoCart: true
|
||||||
NoStorage: true
|
NoStorage: true
|
||||||
NoGuildStorage: true
|
NoGuildStorage: true
|
||||||
@ -78746,6 +78751,7 @@ Body:
|
|||||||
Trade:
|
Trade:
|
||||||
NoDrop: true
|
NoDrop: true
|
||||||
NoTrade: true
|
NoTrade: true
|
||||||
|
NoSell: true
|
||||||
NoCart: true
|
NoCart: true
|
||||||
NoStorage: true
|
NoStorage: true
|
||||||
NoGuildStorage: true
|
NoGuildStorage: true
|
||||||
@ -84763,6 +84769,30 @@ Body:
|
|||||||
Flags:
|
Flags:
|
||||||
BuyingStore: true
|
BuyingStore: true
|
||||||
DropEffect: CLIENT
|
DropEffect: CLIENT
|
||||||
|
- Id: 1001581
|
||||||
|
AegisName: aegis_1001581
|
||||||
|
Name: Coffin of Good and Evil Coupon # !todo check english name
|
||||||
|
Type: Etc
|
||||||
|
Flags:
|
||||||
|
BuyingStore: true
|
||||||
|
- Id: 1001583
|
||||||
|
AegisName: aegis_1001583
|
||||||
|
Name: Good and Evil Boots Coupon # !todo check english name
|
||||||
|
Type: Etc
|
||||||
|
Flags:
|
||||||
|
BuyingStore: true
|
||||||
|
- Id: 1001584
|
||||||
|
AegisName: aegis_1001584
|
||||||
|
Name: Good Weapon Coupon # !todo check english name
|
||||||
|
Type: Etc
|
||||||
|
Flags:
|
||||||
|
BuyingStore: true
|
||||||
|
- Id: 1001588
|
||||||
|
AegisName: aegis_1001588
|
||||||
|
Name: Weapon of Evil Coupon # !todo check english name
|
||||||
|
Type: Etc
|
||||||
|
Flags:
|
||||||
|
BuyingStore: true
|
||||||
- Id: 1220001
|
- Id: 1220001
|
||||||
AegisName: Kunai
|
AegisName: Kunai
|
||||||
Name: Kunai
|
Name: Kunai
|
||||||
|
|||||||
@ -62882,7 +62882,6 @@ Body:
|
|||||||
NoDrop: true
|
NoDrop: true
|
||||||
NoTrade: true
|
NoTrade: true
|
||||||
NoCart: true
|
NoCart: true
|
||||||
NoStorage: true
|
|
||||||
NoGuildStorage: true
|
NoGuildStorage: true
|
||||||
NoMail: true
|
NoMail: true
|
||||||
NoAuction: true
|
NoAuction: true
|
||||||
|
|||||||
File diff suppressed because it is too large
Load Diff
1962
db/re/job_exp.yml
1962
db/re/job_exp.yml
File diff suppressed because it is too large
Load Diff
@ -8884,6 +8884,15 @@ Body:
|
|||||||
- Level: 50
|
- Level: 50
|
||||||
Vit: 1
|
Vit: 1
|
||||||
Pow: 1
|
Pow: 1
|
||||||
|
- Level: 51
|
||||||
|
Crt: 1
|
||||||
|
- Level: 52
|
||||||
|
Pow: 1
|
||||||
|
- Level: 54
|
||||||
|
Pow: 1
|
||||||
|
Crt: 1
|
||||||
|
- Level: 55
|
||||||
|
Sta: 1
|
||||||
- Jobs:
|
- Jobs:
|
||||||
Meister: true
|
Meister: true
|
||||||
Meister2: true
|
Meister2: true
|
||||||
@ -9017,6 +9026,15 @@ Body:
|
|||||||
- Level: 50
|
- Level: 50
|
||||||
Pow: 1
|
Pow: 1
|
||||||
Wis: 1
|
Wis: 1
|
||||||
|
- Level: 51
|
||||||
|
Pow: 1
|
||||||
|
- Level: 52
|
||||||
|
Con: 1
|
||||||
|
- Level: 53
|
||||||
|
Sta: 1
|
||||||
|
Wis: 1
|
||||||
|
- Level: 55
|
||||||
|
Pow: 1
|
||||||
- Jobs:
|
- Jobs:
|
||||||
Shadow_Cross: true
|
Shadow_Cross: true
|
||||||
MaxWeight: 32000
|
MaxWeight: 32000
|
||||||
@ -9149,6 +9167,15 @@ Body:
|
|||||||
- Level: 50
|
- Level: 50
|
||||||
Pow: 1
|
Pow: 1
|
||||||
Crt: 1
|
Crt: 1
|
||||||
|
- Level: 51
|
||||||
|
Pow: 1
|
||||||
|
- Level: 53
|
||||||
|
Con: 1
|
||||||
|
- Level: 54
|
||||||
|
Sta: 1
|
||||||
|
Crt: 1
|
||||||
|
- Level: 55
|
||||||
|
Crt: 1
|
||||||
- Jobs:
|
- Jobs:
|
||||||
Arch_Mage: true
|
Arch_Mage: true
|
||||||
MaxWeight: 30000
|
MaxWeight: 30000
|
||||||
@ -9281,6 +9308,15 @@ Body:
|
|||||||
- Level: 50
|
- Level: 50
|
||||||
Sta: 1
|
Sta: 1
|
||||||
Wis: 1
|
Wis: 1
|
||||||
|
- Level: 52
|
||||||
|
Spl: 1
|
||||||
|
- Level: 53
|
||||||
|
Con: 1
|
||||||
|
- Level: 54
|
||||||
|
Sta: 1
|
||||||
|
Wis: 1
|
||||||
|
- Level: 55
|
||||||
|
Spl: 1
|
||||||
- Jobs:
|
- Jobs:
|
||||||
Cardinal: true
|
Cardinal: true
|
||||||
MaxWeight: 30000
|
MaxWeight: 30000
|
||||||
@ -9413,6 +9449,16 @@ Body:
|
|||||||
- Level: 50
|
- Level: 50
|
||||||
Spl: 1
|
Spl: 1
|
||||||
Crt: 1
|
Crt: 1
|
||||||
|
- Level: 51
|
||||||
|
Spl: 1
|
||||||
|
- Level: 52
|
||||||
|
Pow: 1
|
||||||
|
- Level: 53
|
||||||
|
Sta: 1
|
||||||
|
- Level: 54
|
||||||
|
Wis: 1
|
||||||
|
- Level: 55
|
||||||
|
Crt: 1
|
||||||
- Jobs:
|
- Jobs:
|
||||||
Windhawk: true
|
Windhawk: true
|
||||||
Windhawk2: true
|
Windhawk2: true
|
||||||
@ -9546,6 +9592,15 @@ Body:
|
|||||||
- Level: 50
|
- Level: 50
|
||||||
Dex: 1
|
Dex: 1
|
||||||
Con: 1
|
Con: 1
|
||||||
|
- Level: 51
|
||||||
|
Con: 1
|
||||||
|
- Level: 52
|
||||||
|
Pow: 1
|
||||||
|
Con: 1
|
||||||
|
- Level: 53
|
||||||
|
Sta: 1
|
||||||
|
- Level: 55
|
||||||
|
Pow: 1
|
||||||
- Jobs:
|
- Jobs:
|
||||||
Imperial_Guard: true
|
Imperial_Guard: true
|
||||||
Imperial_Guard2: true
|
Imperial_Guard2: true
|
||||||
@ -9680,6 +9735,15 @@ Body:
|
|||||||
- Level: 50
|
- Level: 50
|
||||||
Pow: 1
|
Pow: 1
|
||||||
Sta: 1
|
Sta: 1
|
||||||
|
- Level: 51
|
||||||
|
Pow: 1
|
||||||
|
- Level: 52
|
||||||
|
Sta: 1
|
||||||
|
- Level: 53
|
||||||
|
Sta: 1
|
||||||
|
- Level: 55
|
||||||
|
Wis: 1
|
||||||
|
Con: 1
|
||||||
- Jobs:
|
- Jobs:
|
||||||
Biolo: true
|
Biolo: true
|
||||||
MaxWeight: 32000
|
MaxWeight: 32000
|
||||||
@ -9812,6 +9876,15 @@ Body:
|
|||||||
- Level: 50
|
- Level: 50
|
||||||
Str: 1
|
Str: 1
|
||||||
Crt: 1
|
Crt: 1
|
||||||
|
- Level: 51
|
||||||
|
Crt: 1
|
||||||
|
- Level: 52
|
||||||
|
Sta: 1
|
||||||
|
- Level: 53
|
||||||
|
Pow: 1
|
||||||
|
Crt: 1
|
||||||
|
- Level: 55
|
||||||
|
Con: 1
|
||||||
- Jobs:
|
- Jobs:
|
||||||
Abyss_Chaser: true
|
Abyss_Chaser: true
|
||||||
MaxWeight: 28000
|
MaxWeight: 28000
|
||||||
@ -9944,6 +10017,15 @@ Body:
|
|||||||
- Level: 50
|
- Level: 50
|
||||||
Pow: 1
|
Pow: 1
|
||||||
Spl: 1
|
Spl: 1
|
||||||
|
- Level: 51
|
||||||
|
Pow: 1
|
||||||
|
- Level: 52
|
||||||
|
Crt: 1
|
||||||
|
- Level: 54
|
||||||
|
Sta: 1
|
||||||
|
- Level: 55
|
||||||
|
Sta: 1
|
||||||
|
Con: 1
|
||||||
- Jobs:
|
- Jobs:
|
||||||
Elemental_Master: true
|
Elemental_Master: true
|
||||||
MaxWeight: 30000
|
MaxWeight: 30000
|
||||||
@ -10076,6 +10158,16 @@ Body:
|
|||||||
- Level: 50
|
- Level: 50
|
||||||
Wis: 1
|
Wis: 1
|
||||||
Spl: 1
|
Spl: 1
|
||||||
|
- Level: 51
|
||||||
|
Spl: 1
|
||||||
|
- Level: 52
|
||||||
|
Sta: 1
|
||||||
|
- Level: 53
|
||||||
|
Sta: 1
|
||||||
|
- Level: 54
|
||||||
|
Wis: 1
|
||||||
|
- Level: 55
|
||||||
|
Spl: 1
|
||||||
- Jobs:
|
- Jobs:
|
||||||
Inquisitor: true
|
Inquisitor: true
|
||||||
MaxWeight: 30000
|
MaxWeight: 30000
|
||||||
@ -10208,6 +10300,15 @@ Body:
|
|||||||
- Level: 50
|
- Level: 50
|
||||||
Pow: 1
|
Pow: 1
|
||||||
Wis: 1
|
Wis: 1
|
||||||
|
- Level: 51
|
||||||
|
Pow: 1
|
||||||
|
- Level: 52
|
||||||
|
Sta: 1
|
||||||
|
- Level: 53
|
||||||
|
Sta: 1
|
||||||
|
- Level: 55
|
||||||
|
Pow: 1
|
||||||
|
Wis: 1
|
||||||
- Jobs:
|
- Jobs:
|
||||||
Troubadour: true
|
Troubadour: true
|
||||||
MaxWeight: 32000
|
MaxWeight: 32000
|
||||||
@ -10340,6 +10441,15 @@ Body:
|
|||||||
Con: 1
|
Con: 1
|
||||||
- Level: 50
|
- Level: 50
|
||||||
Dex: 1
|
Dex: 1
|
||||||
|
- Level: 51
|
||||||
|
Con: 1
|
||||||
|
- Level: 52
|
||||||
|
Spl: 1
|
||||||
|
- Level: 53
|
||||||
|
Sta: 1
|
||||||
|
- Level: 55
|
||||||
|
Pow: 1
|
||||||
|
Con: 1
|
||||||
- Jobs:
|
- Jobs:
|
||||||
Trouvere: true
|
Trouvere: true
|
||||||
MaxWeight: 32000
|
MaxWeight: 32000
|
||||||
@ -10473,6 +10583,15 @@ Body:
|
|||||||
Con: 1
|
Con: 1
|
||||||
- Level: 50
|
- Level: 50
|
||||||
Agi: 1
|
Agi: 1
|
||||||
|
- Level: 51
|
||||||
|
Con: 1
|
||||||
|
- Level: 52
|
||||||
|
Sta: 1
|
||||||
|
- Level: 53
|
||||||
|
Spl: 1
|
||||||
|
- Level: 55
|
||||||
|
Pow: 1
|
||||||
|
Con: 1
|
||||||
- Jobs:
|
- Jobs:
|
||||||
Sky_Emperor: true
|
Sky_Emperor: true
|
||||||
MaxWeight: 42000
|
MaxWeight: 42000
|
||||||
@ -10607,6 +10726,14 @@ Body:
|
|||||||
- Level: 50
|
- Level: 50
|
||||||
Pow: 1
|
Pow: 1
|
||||||
Crt: 1
|
Crt: 1
|
||||||
|
- Level: 51
|
||||||
|
Sta: 1
|
||||||
|
Con: 1
|
||||||
|
- Level: 53
|
||||||
|
Sta: 1
|
||||||
|
- Level: 55
|
||||||
|
Pow: 1
|
||||||
|
Con: 1
|
||||||
- Jobs:
|
- Jobs:
|
||||||
Soul_Ascetic: true
|
Soul_Ascetic: true
|
||||||
MaxWeight: 42000
|
MaxWeight: 42000
|
||||||
@ -10730,6 +10857,16 @@ Body:
|
|||||||
- Level: 50
|
- Level: 50
|
||||||
Wis: 1
|
Wis: 1
|
||||||
Spl: 1
|
Spl: 1
|
||||||
|
- Level: 51
|
||||||
|
Spl: 1
|
||||||
|
- Level: 52
|
||||||
|
Con: 1
|
||||||
|
- Level: 53
|
||||||
|
Wis: 1
|
||||||
|
- Level: 54
|
||||||
|
Sta: 1
|
||||||
|
- Level: 55
|
||||||
|
Spl: 1
|
||||||
- Jobs:
|
- Jobs:
|
||||||
Shinkiro: true
|
Shinkiro: true
|
||||||
MaxWeight: 45000
|
MaxWeight: 45000
|
||||||
@ -10863,6 +11000,16 @@ Body:
|
|||||||
- Level: 50
|
- Level: 50
|
||||||
Pow: 1
|
Pow: 1
|
||||||
Crt: 1
|
Crt: 1
|
||||||
|
- Level: 51
|
||||||
|
Crt: 1
|
||||||
|
- Level: 52
|
||||||
|
Con: 1
|
||||||
|
- Level: 53
|
||||||
|
Wis: 1
|
||||||
|
- Level: 54
|
||||||
|
Sta: 1
|
||||||
|
- Level: 55
|
||||||
|
Sta: 1
|
||||||
- Jobs:
|
- Jobs:
|
||||||
Shiranui: true
|
Shiranui: true
|
||||||
MaxWeight: 45000
|
MaxWeight: 45000
|
||||||
@ -10985,6 +11132,15 @@ Body:
|
|||||||
- Level: 50
|
- Level: 50
|
||||||
Wis: 1
|
Wis: 1
|
||||||
Spl: 1
|
Spl: 1
|
||||||
|
- Level: 51
|
||||||
|
Pow: 1
|
||||||
|
- Level: 52
|
||||||
|
Spl: 1
|
||||||
|
- Level: 54
|
||||||
|
Spl: 1
|
||||||
|
- Level: 55
|
||||||
|
Spl: 1
|
||||||
|
Con: 1
|
||||||
- Jobs:
|
- Jobs:
|
||||||
Night_Watch: true
|
Night_Watch: true
|
||||||
MaxWeight: 48000
|
MaxWeight: 48000
|
||||||
@ -11112,6 +11268,15 @@ Body:
|
|||||||
Con: 1
|
Con: 1
|
||||||
- Level: 50
|
- Level: 50
|
||||||
Pow: 1
|
Pow: 1
|
||||||
|
- Level: 51
|
||||||
|
Con: 1
|
||||||
|
- Level: 53
|
||||||
|
Pow: 1
|
||||||
|
Con: 1
|
||||||
|
- Level: 54
|
||||||
|
Wis: 1
|
||||||
|
- Level: 55
|
||||||
|
Pow: 1
|
||||||
- Jobs:
|
- Jobs:
|
||||||
Hyper_Novice: true
|
Hyper_Novice: true
|
||||||
MaxWeight: 40000
|
MaxWeight: 40000
|
||||||
@ -11248,6 +11413,15 @@ Body:
|
|||||||
- Level: 50
|
- Level: 50
|
||||||
Agi: 1
|
Agi: 1
|
||||||
Dex: 1
|
Dex: 1
|
||||||
|
- Level: 51
|
||||||
|
Con: 1
|
||||||
|
- Level: 52
|
||||||
|
Pow: 1
|
||||||
|
Con: 1
|
||||||
|
- Level: 53
|
||||||
|
Sta: 1
|
||||||
|
- Level: 55
|
||||||
|
Spl: 1
|
||||||
- Jobs:
|
- Jobs:
|
||||||
Spirit_Handler: true
|
Spirit_Handler: true
|
||||||
MaxWeight: 42000
|
MaxWeight: 42000
|
||||||
@ -11379,3 +11553,13 @@ Body:
|
|||||||
Crt: 1
|
Crt: 1
|
||||||
- Level: 50
|
- Level: 50
|
||||||
Pow: 1
|
Pow: 1
|
||||||
|
- Level: 51
|
||||||
|
Con: 1
|
||||||
|
- Level: 52
|
||||||
|
Pow: 1
|
||||||
|
- Level: 53
|
||||||
|
Spl: 1
|
||||||
|
- Level: 54
|
||||||
|
Wis: 1
|
||||||
|
- Level: 55
|
||||||
|
Sta: 1
|
||||||
|
|||||||
1262
db/re/skill_db.yml
1262
db/re/skill_db.yml
File diff suppressed because it is too large
Load Diff
@ -7864,3 +7864,89 @@ Body:
|
|||||||
Royal_Guard: true
|
Royal_Guard: true
|
||||||
Royal_Guard_T: true
|
Royal_Guard_T: true
|
||||||
Imperial_Guard: true
|
Imperial_Guard: true
|
||||||
|
- Job: Hyper_Novice
|
||||||
|
Inherit:
|
||||||
|
Novice: true
|
||||||
|
Supernovice: true
|
||||||
|
Super_Novice_E: true
|
||||||
|
Tree:
|
||||||
|
- Name: HN_SELFSTUDY_TATICS
|
||||||
|
MaxLevel: 10
|
||||||
|
- Name: HN_SELFSTUDY_SOCERY
|
||||||
|
MaxLevel: 10
|
||||||
|
- Name: HN_DOUBLEBOWLINGBASH
|
||||||
|
MaxLevel: 10
|
||||||
|
Requires:
|
||||||
|
- Name: HN_SELFSTUDY_TATICS
|
||||||
|
Level: 5
|
||||||
|
- Name: HN_SHIELD_CHAIN_RUSH
|
||||||
|
MaxLevel: 10
|
||||||
|
Requires:
|
||||||
|
- Name: HN_SELFSTUDY_TATICS
|
||||||
|
Level: 5
|
||||||
|
- Name: HN_METEOR_STORM_BUSTER
|
||||||
|
MaxLevel: 10
|
||||||
|
Requires:
|
||||||
|
- Name: HN_SELFSTUDY_SOCERY
|
||||||
|
Level: 5
|
||||||
|
- Name: HN_JUPITEL_THUNDER_STORM
|
||||||
|
MaxLevel: 10
|
||||||
|
Requires:
|
||||||
|
- Name: HN_SELFSTUDY_SOCERY
|
||||||
|
Level: 5
|
||||||
|
- Name: HN_JACK_FROST_NOVA
|
||||||
|
MaxLevel: 10
|
||||||
|
Requires:
|
||||||
|
- Name: HN_SELFSTUDY_SOCERY
|
||||||
|
Level: 5
|
||||||
|
- Name: HN_HELLS_DRIVE
|
||||||
|
MaxLevel: 10
|
||||||
|
Requires:
|
||||||
|
- Name: HN_SELFSTUDY_SOCERY
|
||||||
|
Level: 5
|
||||||
|
- Name: HN_MEGA_SONIC_BLOW
|
||||||
|
MaxLevel: 10
|
||||||
|
Requires:
|
||||||
|
- Name: HN_DOUBLEBOWLINGBASH
|
||||||
|
Level: 7
|
||||||
|
- Name: HN_SPIRAL_PIERCE_MAX
|
||||||
|
MaxLevel: 10
|
||||||
|
Requires:
|
||||||
|
- Name: HN_SHIELD_CHAIN_RUSH
|
||||||
|
Level: 7
|
||||||
|
- Name: HN_GROUND_GRAVITATION
|
||||||
|
MaxLevel: 10
|
||||||
|
Requires:
|
||||||
|
- Name: HN_SELFSTUDY_SOCERY
|
||||||
|
Level: 5
|
||||||
|
- Name: HN_NAPALM_VULCAN_STRIKE
|
||||||
|
MaxLevel: 10
|
||||||
|
Requires:
|
||||||
|
- Name: HN_SELFSTUDY_SOCERY
|
||||||
|
Level: 5
|
||||||
|
- Name: HN_BREAKINGLIMIT
|
||||||
|
MaxLevel: 1
|
||||||
|
Requires:
|
||||||
|
- Name: HN_DOUBLEBOWLINGBASH
|
||||||
|
Level: 7
|
||||||
|
- Name: HN_MEGA_SONIC_BLOW
|
||||||
|
Level: 7
|
||||||
|
- Name: HN_SHIELD_CHAIN_RUSH
|
||||||
|
Level: 7
|
||||||
|
- Name: HN_SPIRAL_PIERCE_MAX
|
||||||
|
Level: 7
|
||||||
|
- Name: HN_RULEBREAK
|
||||||
|
MaxLevel: 1
|
||||||
|
Requires:
|
||||||
|
- Name: HN_METEOR_STORM_BUSTER
|
||||||
|
Level: 5
|
||||||
|
- Name: HN_JUPITEL_THUNDER_STORM
|
||||||
|
Level: 5
|
||||||
|
- Name: HN_JACK_FROST_NOVA
|
||||||
|
Level: 5
|
||||||
|
- Name: HN_HELLS_DRIVE
|
||||||
|
Level: 5
|
||||||
|
- Name: HN_GROUND_GRAVITATION
|
||||||
|
Level: 5
|
||||||
|
- Name: HN_NAPALM_VULCAN_STRIKE
|
||||||
|
Level: 5
|
||||||
|
|||||||
@ -582,3 +582,33 @@ Body:
|
|||||||
- Level: 250
|
- Level: 250
|
||||||
Points: 4099
|
Points: 4099
|
||||||
TraitPoints: 190
|
TraitPoints: 190
|
||||||
|
- Level: 251
|
||||||
|
Points: 4099
|
||||||
|
TraitPoints: 193
|
||||||
|
- Level: 252
|
||||||
|
Points: 4099
|
||||||
|
TraitPoints: 196
|
||||||
|
- Level: 253
|
||||||
|
Points: 4099
|
||||||
|
TraitPoints: 199
|
||||||
|
- Level: 254
|
||||||
|
Points: 4099
|
||||||
|
TraitPoints: 202
|
||||||
|
- Level: 255
|
||||||
|
Points: 4099
|
||||||
|
TraitPoints: 209
|
||||||
|
- Level: 256
|
||||||
|
Points: 4099
|
||||||
|
TraitPoints: 212
|
||||||
|
- Level: 257
|
||||||
|
Points: 4099
|
||||||
|
TraitPoints: 215
|
||||||
|
- Level: 258
|
||||||
|
Points: 4099
|
||||||
|
TraitPoints: 218
|
||||||
|
- Level: 259
|
||||||
|
Points: 4099
|
||||||
|
TraitPoints: 221
|
||||||
|
- Level: 260
|
||||||
|
Points: 4099
|
||||||
|
TraitPoints: 228
|
||||||
|
|||||||
@ -5732,6 +5732,8 @@ Body:
|
|||||||
DurationLookup: RA_UNLIMIT
|
DurationLookup: RA_UNLIMIT
|
||||||
Flags:
|
Flags:
|
||||||
DisplayPc: true
|
DisplayPc: true
|
||||||
|
NoDispell: true
|
||||||
|
NoClearance: true
|
||||||
- Status: Kings_Grace
|
- Status: Kings_Grace
|
||||||
Icon: EFST_KINGS_GRACE
|
Icon: EFST_KINGS_GRACE
|
||||||
DurationLookup: LG_KINGS_GRACE
|
DurationLookup: LG_KINGS_GRACE
|
||||||
@ -7633,7 +7635,7 @@ Body:
|
|||||||
RemoveOnDamaged: true
|
RemoveOnDamaged: true
|
||||||
- Status: Handicapstate_Lightningstrike
|
- Status: Handicapstate_Lightningstrike
|
||||||
Icon: EFST_HANDICAPSTATE_LIGHTNINGSTRIKE
|
Icon: EFST_HANDICAPSTATE_LIGHTNINGSTRIKE
|
||||||
DurationLookup: WH_SWIFTTRAP
|
DurationLookup: EM_LIGHTNING_LAND
|
||||||
States:
|
States:
|
||||||
#NoMove: true
|
#NoMove: true
|
||||||
#NoCast: true
|
#NoCast: true
|
||||||
@ -7646,7 +7648,7 @@ Body:
|
|||||||
RemoveOnDamaged: true
|
RemoveOnDamaged: true
|
||||||
- Status: Handicapstate_Crystallization
|
- Status: Handicapstate_Crystallization
|
||||||
Icon: EFST_HANDICAPSTATE_CRYSTALLIZATION
|
Icon: EFST_HANDICAPSTATE_CRYSTALLIZATION
|
||||||
DurationLookup: WH_SOLIDTRAP
|
DurationLookup: EM_TERRA_DRIVE
|
||||||
States:
|
States:
|
||||||
#NoMove: true
|
#NoMove: true
|
||||||
#NoCast: true
|
#NoCast: true
|
||||||
@ -7660,7 +7662,7 @@ Body:
|
|||||||
RemoveOnDamaged: true
|
RemoveOnDamaged: true
|
||||||
- Status: Handicapstate_Conflagration
|
- Status: Handicapstate_Conflagration
|
||||||
Icon: EFST_HANDICAPSTATE_CONFLAGRATION
|
Icon: EFST_HANDICAPSTATE_CONFLAGRATION
|
||||||
DurationLookup: WH_FLAMETRAP
|
DurationLookup: EM_CONFLAGRATION
|
||||||
Flags:
|
Flags:
|
||||||
BlEffect: true
|
BlEffect: true
|
||||||
DisplayPc: true
|
DisplayPc: true
|
||||||
@ -8751,3 +8753,31 @@ Body:
|
|||||||
NoDispell: true
|
NoDispell: true
|
||||||
NoBanishingBuster: true
|
NoBanishingBuster: true
|
||||||
NoClearance: true
|
NoClearance: true
|
||||||
|
- Status: Hnnoweapon
|
||||||
|
Icon: EFST_NOEQUIPWEAPON
|
||||||
|
DurationLookup: HN_DOUBLEBOWLINGBASH
|
||||||
|
- Status: Shieldchainrush
|
||||||
|
Icon: EFST_SHIELDCHAINRUSH
|
||||||
|
DurationLookup: HN_SHIELD_CHAIN_RUSH
|
||||||
|
CalcFlags:
|
||||||
|
Speed: true
|
||||||
|
Flags:
|
||||||
|
BossResist: true
|
||||||
|
- Status: Mistyfrost
|
||||||
|
Icon: EFST_MISTYFROST
|
||||||
|
DurationLookup: HN_JACK_FROST_NOVA
|
||||||
|
Flags:
|
||||||
|
BossResist: true
|
||||||
|
- Status: Groundgravity
|
||||||
|
Icon: EFST_GROUNDGRAVITY
|
||||||
|
DurationLookup: HN_GROUND_GRAVITATION
|
||||||
|
CalcFlags:
|
||||||
|
Speed: true
|
||||||
|
Flags:
|
||||||
|
BossResist: true
|
||||||
|
- Status: Breakinglimit
|
||||||
|
Icon: EFST_BREAKINGLIMIT
|
||||||
|
DurationLookup: HN_BREAKINGLIMIT
|
||||||
|
- Status: Rulebreak
|
||||||
|
Icon: EFST_RULEBREAK
|
||||||
|
DurationLookup: HN_RULEBREAK
|
||||||
|
|||||||
@ -7481,10 +7481,10 @@ This command lets you override the contents of an existing NPC shop or cashshop.
|
|||||||
current sell list will be wiped, and only the items specified with the price
|
current sell list will be wiped, and only the items specified with the price
|
||||||
specified will be for sale.
|
specified will be for sale.
|
||||||
|
|
||||||
The function returns 1 if shop was updated successfully, or 0 if not found.
|
The function returns 1 if shop was updated successfully, or 0 on failure.
|
||||||
|
|
||||||
NOTES:
|
NOTES:
|
||||||
- That you cannot use -1 to specify default selling price!
|
- That you cannot use -1 to specify default selling price for cashshops, pointshops, or itemshops.
|
||||||
- If the attached shop type is a market shop, notice that there is an extra parameter after price, <stock>. Make sure to not add duplicate items! For unlimited stock use -1.
|
- If the attached shop type is a market shop, notice that there is an extra parameter after price, <stock>. Make sure to not add duplicate items! For unlimited stock use -1.
|
||||||
|
|
||||||
---------------------------------------
|
---------------------------------------
|
||||||
@ -7496,10 +7496,10 @@ This command will add more items at the end of the selling list for the
|
|||||||
specified NPC shop or cashshop. If you specify an item already for sell, that item will
|
specified NPC shop or cashshop. If you specify an item already for sell, that item will
|
||||||
appear twice on the sell list.
|
appear twice on the sell list.
|
||||||
|
|
||||||
The function returns 1 if shop was updated successfully, or 0 if not found.
|
The function returns 1 if shop was updated successfully, or 0 on failure.
|
||||||
|
|
||||||
NOTES:
|
NOTES:
|
||||||
- That you cannot use -1 to specify default selling price!
|
- That you cannot use -1 to specify default selling price for cashshops, pointshops, or itemshops.
|
||||||
- If attached shop type is market shop, need an extra param after price, it's <stock>
|
- If attached shop type is market shop, need an extra param after price, it's <stock>
|
||||||
and make sure don't add duplication item! For unlimited stock use -1.
|
and make sure don't add duplication item! For unlimited stock use -1.
|
||||||
|
|
||||||
@ -7543,6 +7543,13 @@ Update an entry from a shop. If the price is 0 it won't be changed. May also be
|
|||||||
marketshop to update the stock quantity. For unlimited stock, use -1.
|
marketshop to update the stock quantity. For unlimited stock, use -1.
|
||||||
For other shop types, the stock value has no effect.
|
For other shop types, the stock value has no effect.
|
||||||
|
|
||||||
|
If the price is -1, it sets it to the default buy price.
|
||||||
|
|
||||||
|
The function returns 1 if shop was updated successfully, or 0 on failure.
|
||||||
|
|
||||||
|
NOTES:
|
||||||
|
- That you cannot use -1 to specify default selling price for cashshops, pointshops, or itemshops.
|
||||||
|
|
||||||
---------------------------------------
|
---------------------------------------
|
||||||
|
|
||||||
*waitingroom "<chatroom name>",<limit>{,"<event label>"{,<trigger>{,<required zeny>{,<min lvl>{,<max lvl>}}}}};
|
*waitingroom "<chatroom name>",<limit>{,"<event label>"{,<trigger>{,<required zeny>{,<min lvl>{,<max lvl>}}}}};
|
||||||
|
|||||||
@ -10,6 +10,7 @@
|
|||||||
//= 1.0 Initial release [crazyarashi]
|
//= 1.0 Initial release [crazyarashi]
|
||||||
//= 1.1 Optimizations and cleanup [Everade]
|
//= 1.1 Optimizations and cleanup [Everade]
|
||||||
//= 1.2 Cleanup [Capuche]
|
//= 1.2 Cleanup [Capuche]
|
||||||
|
//= 1.3 Updated monsters spawn times (significantly reduced). [Atemo]
|
||||||
//============================================================
|
//============================================================
|
||||||
|
|
||||||
ba_maison,120,320,0 script #herbs_chk HIDDEN_WARP_NPC,3,3,{
|
ba_maison,120,320,0 script #herbs_chk HIDDEN_WARP_NPC,3,3,{
|
||||||
@ -1623,36 +1624,36 @@ OnSummon:
|
|||||||
'total_mobs = 16;
|
'total_mobs = 16;
|
||||||
monster 'map_herbs$,77,197,"Flower Garden Watcher",20622,1, .@event$;
|
monster 'map_herbs$,77,197,"Flower Garden Watcher",20622,1, .@event$;
|
||||||
monster 'map_herbs$,51,196,"Flower Garden Watcher",20622,1, .@event$;
|
monster 'map_herbs$,51,196,"Flower Garden Watcher",20622,1, .@event$;
|
||||||
sleep 6000;
|
sleep 100;
|
||||||
monster 'map_herbs$,63,217,"Flower Garden Watcher",20622,1, .@event$;
|
monster 'map_herbs$,63,217,"Flower Garden Watcher",20622,1, .@event$;
|
||||||
sleep 3000;
|
sleep 100;
|
||||||
monster 'map_herbs$,81,195,"Flower Garden Watcher",20624,1, .@event$;
|
monster 'map_herbs$,81,195,"Flower Garden Watcher",20624,1, .@event$;
|
||||||
monster 'map_herbs$,61,217,"Flower Garden Watcher",20622,1, .@event$;
|
monster 'map_herbs$,61,217,"Flower Garden Watcher",20622,1, .@event$;
|
||||||
sleep 3000;
|
sleep 100;
|
||||||
monster 'map_herbs$,57,193,"Flower Garden Watcher",20622,1, .@event$;
|
monster 'map_herbs$,57,193,"Flower Garden Watcher",20622,1, .@event$;
|
||||||
sleep 6000;
|
sleep 100;
|
||||||
monster 'map_herbs$,56,191,"Flower Garden Watcher",20626,1, .@event$;
|
monster 'map_herbs$,56,191,"Flower Garden Watcher",20626,1, .@event$;
|
||||||
sleep 3000;
|
sleep 100;
|
||||||
monster 'map_herbs$,59,193,"Flower Garden Watcher",20626,1, .@event$;
|
monster 'map_herbs$,59,193,"Flower Garden Watcher",20626,1, .@event$;
|
||||||
sleep 6000;
|
sleep 100;
|
||||||
monster 'map_herbs$,59,192,"Flower Garden Watcher",20622,1, .@event$;
|
monster 'map_herbs$,59,192,"Flower Garden Watcher",20622,1, .@event$;
|
||||||
monster 'map_herbs$,60,222,"Flower Garden Watcher",20622,1, .@event$;
|
monster 'map_herbs$,60,222,"Flower Garden Watcher",20622,1, .@event$;
|
||||||
monster 'map_herbs$,58,191,"Flower Garden Watcher",20622,1, .@event$;
|
monster 'map_herbs$,58,191,"Flower Garden Watcher",20622,1, .@event$;
|
||||||
sleep 6000;
|
sleep 100;
|
||||||
monster 'map_herbs$,78,199,"Flower Garden Watcher",20622,1, .@event$;
|
monster 'map_herbs$,78,199,"Flower Garden Watcher",20622,1, .@event$;
|
||||||
sleep 3000;
|
sleep 100;
|
||||||
monster 'map_herbs$,54,192,"Flower Garden Watcher",20626,1, .@event$;
|
monster 'map_herbs$,54,192,"Flower Garden Watcher",20626,1, .@event$;
|
||||||
monster 'map_herbs$,79,195,"Flower Garden Watcher",20622,1, .@event$;
|
monster 'map_herbs$,79,195,"Flower Garden Watcher",20622,1, .@event$;
|
||||||
sleep 9000;
|
sleep 100;
|
||||||
monster 'map_herbs$,76,192,"Flower Garden Watcher",20626,1, .@event$;
|
monster 'map_herbs$,76,192,"Flower Garden Watcher",20626,1, .@event$;
|
||||||
monster 'map_herbs$,51,196,"Flower Garden Watcher",20624,1, .@event$;
|
monster 'map_herbs$,51,196,"Flower Garden Watcher",20624,1, .@event$;
|
||||||
}
|
}
|
||||||
else {
|
else {
|
||||||
'total_mobs = 16;
|
'total_mobs = 16;
|
||||||
monster 'map_herbs$,53,197,"Flower Garden Watcher",20623,1, .@event$;
|
monster 'map_herbs$,53,197,"Flower Garden Watcher",20623,1, .@event$;
|
||||||
sleep 3000;
|
sleep 100;
|
||||||
monster 'map_herbs$,62,217,"Flower Garden Watcher",20623,1, .@event$;
|
monster 'map_herbs$,62,217,"Flower Garden Watcher",20623,1, .@event$;
|
||||||
sleep 3000;
|
sleep 100;
|
||||||
monster 'map_herbs$,57,219,"Flower Garden Watcher",20627,1, .@event$;
|
monster 'map_herbs$,57,219,"Flower Garden Watcher",20627,1, .@event$;
|
||||||
monster 'map_herbs$,62,222,"Flower Garden Watcher",20623,1, .@event$;
|
monster 'map_herbs$,62,222,"Flower Garden Watcher",20623,1, .@event$;
|
||||||
monster 'map_herbs$,79,200,"Flower Garden Watcher",20623,1, .@event$;
|
monster 'map_herbs$,79,200,"Flower Garden Watcher",20623,1, .@event$;
|
||||||
@ -1660,14 +1661,14 @@ OnSummon:
|
|||||||
monster 'map_herbs$,80,199,"Flower Garden Watcher",20623,1, .@event$;
|
monster 'map_herbs$,80,199,"Flower Garden Watcher",20623,1, .@event$;
|
||||||
monster 'map_herbs$,58,193,"Flower Garden Watcher",20623,1, .@event$;
|
monster 'map_herbs$,58,193,"Flower Garden Watcher",20623,1, .@event$;
|
||||||
monster 'map_herbs$,56,192,"Flower Garden Watcher",20625,1, .@event$;
|
monster 'map_herbs$,56,192,"Flower Garden Watcher",20625,1, .@event$;
|
||||||
sleep 3000;
|
sleep 100;
|
||||||
monster 'map_herbs$,51,191,"Flower Garden Watcher",20623,1, .@event$;
|
monster 'map_herbs$,51,191,"Flower Garden Watcher",20623,1, .@event$;
|
||||||
monster 'map_herbs$,51,192,"Flower Garden Watcher",20623,1, .@event$;
|
monster 'map_herbs$,51,192,"Flower Garden Watcher",20623,1, .@event$;
|
||||||
monster 'map_herbs$,83,199,"Flower Garden Watcher",20625,1, .@event$;
|
monster 'map_herbs$,83,199,"Flower Garden Watcher",20625,1, .@event$;
|
||||||
monster 'map_herbs$,83,191,"Flower Garden Watcher",20623,1, .@event$;
|
monster 'map_herbs$,83,191,"Flower Garden Watcher",20623,1, .@event$;
|
||||||
sleep 3000;
|
sleep 100;
|
||||||
monster 'map_herbs$,83,196,"Flower Garden Watcher",20623,1, .@event$;
|
monster 'map_herbs$,83,196,"Flower Garden Watcher",20623,1, .@event$;
|
||||||
sleep 6000;
|
sleep 100;
|
||||||
monster 'map_herbs$,57,193,"Flower Garden Watcher",20623,1, .@event$;
|
monster 'map_herbs$,57,193,"Flower Garden Watcher",20623,1, .@event$;
|
||||||
monster 'map_herbs$,62,222,"Flower Garden Watcher",20623,1, .@event$;
|
monster 'map_herbs$,62,222,"Flower Garden Watcher",20623,1, .@event$;
|
||||||
}
|
}
|
||||||
@ -1678,15 +1679,15 @@ OnSummon:
|
|||||||
monster 'map_herbs$,114,226,"Flower Garden Watcher",20622,1, .@event$;
|
monster 'map_herbs$,114,226,"Flower Garden Watcher",20622,1, .@event$;
|
||||||
monster 'map_herbs$,114,227,"Flower Garden Watcher",20622,1, .@event$;
|
monster 'map_herbs$,114,227,"Flower Garden Watcher",20622,1, .@event$;
|
||||||
monster 'map_herbs$,119,217,"Flower Garden Watcher",20624,1, .@event$;
|
monster 'map_herbs$,119,217,"Flower Garden Watcher",20624,1, .@event$;
|
||||||
sleep 6000;
|
sleep 100;
|
||||||
monster 'map_herbs$,118,227,"Flower Garden Watcher",20622,1, .@event$;
|
monster 'map_herbs$,118,227,"Flower Garden Watcher",20622,1, .@event$;
|
||||||
sleep 3000;
|
sleep 100;
|
||||||
monster 'map_herbs$,116,216,"Flower Garden Watcher",20626,1, .@event$;
|
monster 'map_herbs$,116,216,"Flower Garden Watcher",20626,1, .@event$;
|
||||||
sleep 6000;
|
sleep 100;
|
||||||
monster 'map_herbs$,114,215,"Flower Garden Watcher",20626,1, .@event$;
|
monster 'map_herbs$,114,215,"Flower Garden Watcher",20626,1, .@event$;
|
||||||
sleep 3000;
|
sleep 100;
|
||||||
monster 'map_herbs$,114,225,"Flower Garden Watcher",20622,1, .@event$;
|
monster 'map_herbs$,114,225,"Flower Garden Watcher",20622,1, .@event$;
|
||||||
sleep 6000;
|
sleep 100;
|
||||||
monster 'map_herbs$,114,224,"Flower Garden Watcher",20622,1, .@event$;
|
monster 'map_herbs$,114,224,"Flower Garden Watcher",20622,1, .@event$;
|
||||||
monster 'map_herbs$,139,205,"Flower Garden Watcher",20622,1, .@event$;
|
monster 'map_herbs$,139,205,"Flower Garden Watcher",20622,1, .@event$;
|
||||||
monster 'map_herbs$,140,202,"Flower Garden Watcher",20622,1, .@event$;
|
monster 'map_herbs$,140,202,"Flower Garden Watcher",20622,1, .@event$;
|
||||||
@ -1708,30 +1709,30 @@ OnSummon:
|
|||||||
monster 'map_herbs$,142,205,"Flower Garden Watcher",20627,1, .@event$;
|
monster 'map_herbs$,142,205,"Flower Garden Watcher",20627,1, .@event$;
|
||||||
monster 'map_herbs$,145,200,"Flower Garden Watcher",20623,1, .@event$;
|
monster 'map_herbs$,145,200,"Flower Garden Watcher",20623,1, .@event$;
|
||||||
monster 'map_herbs$,146,201,"Flower Garden Watcher",20625,1, .@event$;
|
monster 'map_herbs$,146,201,"Flower Garden Watcher",20625,1, .@event$;
|
||||||
sleep 6000;
|
sleep 100;
|
||||||
monster 'map_herbs$,147,201,"Flower Garden Watcher",20623,1, .@event$;
|
monster 'map_herbs$,147,201,"Flower Garden Watcher",20623,1, .@event$;
|
||||||
sleep 3000;
|
sleep 100;
|
||||||
monster 'map_herbs$,141,208,"Flower Garden Watcher",20627,1, .@event$;
|
monster 'map_herbs$,141,208,"Flower Garden Watcher",20627,1, .@event$;
|
||||||
monster 'map_herbs$,166,224,"Flower Garden Watcher",20625,1, .@event$;
|
monster 'map_herbs$,166,224,"Flower Garden Watcher",20625,1, .@event$;
|
||||||
sleep 6000;
|
sleep 100;
|
||||||
monster 'map_herbs$,171,217,"Flower Garden Watcher",20627,1, .@event$;
|
monster 'map_herbs$,171,217,"Flower Garden Watcher",20627,1, .@event$;
|
||||||
sleep 3000;
|
sleep 100;
|
||||||
monster 'map_herbs$,172,225,"Flower Garden Watcher",20627,1, .@event$;
|
monster 'map_herbs$,172,225,"Flower Garden Watcher",20627,1, .@event$;
|
||||||
monster 'map_herbs$,173,214,"Flower Garden Watcher",20623,1, .@event$;
|
monster 'map_herbs$,173,214,"Flower Garden Watcher",20623,1, .@event$;
|
||||||
monster 'map_herbs$,174,225,"Flower Garden Watcher",20627,1, .@event$;
|
monster 'map_herbs$,174,225,"Flower Garden Watcher",20627,1, .@event$;
|
||||||
monster 'map_herbs$,174,223,"Flower Garden Watcher",20627,1, .@event$;
|
monster 'map_herbs$,174,223,"Flower Garden Watcher",20627,1, .@event$;
|
||||||
sleep 6000;
|
sleep 100;
|
||||||
monster 'map_herbs$,170,213,"Flower Garden Watcher",20623,1, .@event$;
|
monster 'map_herbs$,170,213,"Flower Garden Watcher",20623,1, .@event$;
|
||||||
sleep 3000;
|
sleep 100;
|
||||||
monster 'map_herbs$,169,219,"Flower Garden Watcher",20623,1, .@event$;
|
monster 'map_herbs$,169,219,"Flower Garden Watcher",20623,1, .@event$;
|
||||||
sleep 6000;
|
sleep 100;
|
||||||
monster 'map_herbs$,136,205,"Flower Garden Watcher",20623,1, .@event$;
|
monster 'map_herbs$,136,205,"Flower Garden Watcher",20623,1, .@event$;
|
||||||
monster 'map_herbs$,136,210,"Flower Garden Watcher",20623,1, .@event$;
|
monster 'map_herbs$,136,210,"Flower Garden Watcher",20623,1, .@event$;
|
||||||
monster 'map_herbs$,120,224,"Flower Garden Watcher",20623,1, .@event$;
|
monster 'map_herbs$,120,224,"Flower Garden Watcher",20623,1, .@event$;
|
||||||
monster 'map_herbs$,118,223,"Flower Garden Watcher",20623,1, .@event$;
|
monster 'map_herbs$,118,223,"Flower Garden Watcher",20623,1, .@event$;
|
||||||
monster 'map_herbs$,117,219,"Flower Garden Watcher",20623,1, .@event$;
|
monster 'map_herbs$,117,219,"Flower Garden Watcher",20623,1, .@event$;
|
||||||
monster 'map_herbs$,115,214,"Flower Garden Watcher",20623,1, .@event$;
|
monster 'map_herbs$,115,214,"Flower Garden Watcher",20623,1, .@event$;
|
||||||
sleep 3000;
|
sleep 100;
|
||||||
monster 'map_herbs$,115,233,"Flower Garden Watcher",20623,1, .@event$;
|
monster 'map_herbs$,115,233,"Flower Garden Watcher",20623,1, .@event$;
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
@ -1740,45 +1741,45 @@ OnSummon:
|
|||||||
'total_mobs = 28;
|
'total_mobs = 28;
|
||||||
monster 'map_herbs$,213,205,"Flower Garden Watcher",20622,1, .@event$;
|
monster 'map_herbs$,213,205,"Flower Garden Watcher",20622,1, .@event$;
|
||||||
monster 'map_herbs$,202,214,"Flower Garden Watcher",20626,1, .@event$;
|
monster 'map_herbs$,202,214,"Flower Garden Watcher",20626,1, .@event$;
|
||||||
sleep 3000;
|
sleep 100;
|
||||||
monster 'map_herbs$,202,213,"Flower Garden Watcher",20626,1, .@event$;
|
monster 'map_herbs$,202,213,"Flower Garden Watcher",20626,1, .@event$;
|
||||||
sleep 3000;
|
sleep 100;
|
||||||
monster 'map_herbs$,210,212,"Flower Garden Watcher",20626,1, .@event$;
|
monster 'map_herbs$,210,212,"Flower Garden Watcher",20626,1, .@event$;
|
||||||
sleep 6000;
|
sleep 100;
|
||||||
monster 'map_herbs$,211,207,"Flower Garden Watcher",20624,1, .@event$;
|
monster 'map_herbs$,211,207,"Flower Garden Watcher",20624,1, .@event$;
|
||||||
sleep 3000;
|
sleep 100;
|
||||||
monster 'map_herbs$,209,214,"Flower Garden Watcher",20624,1, .@event$;
|
monster 'map_herbs$,209,214,"Flower Garden Watcher",20624,1, .@event$;
|
||||||
sleep 3000;
|
sleep 100;
|
||||||
monster 'map_herbs$,203,212,"Flower Garden Watcher",20622,1, .@event$;
|
monster 'map_herbs$,203,212,"Flower Garden Watcher",20622,1, .@event$;
|
||||||
monster 'map_herbs$,218,194,"Flower Garden Watcher",20622,1, .@event$;
|
monster 'map_herbs$,218,194,"Flower Garden Watcher",20622,1, .@event$;
|
||||||
sleep 6000;
|
sleep 100;
|
||||||
monster 'map_herbs$,203,196,"Flower Garden Watcher",20622,1, .@event$;
|
monster 'map_herbs$,203,196,"Flower Garden Watcher",20622,1, .@event$;
|
||||||
sleep 3000;
|
sleep 100;
|
||||||
monster 'map_herbs$,204,193,"Flower Garden Watcher",20626,1, .@event$;
|
monster 'map_herbs$,204,193,"Flower Garden Watcher",20626,1, .@event$;
|
||||||
sleep 3000;
|
sleep 100;
|
||||||
monster 'map_herbs$,215,201,"Flower Garden Watcher",20624,1, .@event$;
|
monster 'map_herbs$,215,201,"Flower Garden Watcher",20624,1, .@event$;
|
||||||
monster 'map_herbs$,204,193,"Flower Garden Watcher",20626,1, .@event$;
|
monster 'map_herbs$,204,193,"Flower Garden Watcher",20626,1, .@event$;
|
||||||
sleep 3000;
|
sleep 100;
|
||||||
monster 'map_herbs$,205,213,"Flower Garden Watcher",20626,1, .@event$;
|
monster 'map_herbs$,205,213,"Flower Garden Watcher",20626,1, .@event$;
|
||||||
sleep 3000;
|
sleep 100;
|
||||||
monster 'map_herbs$,218,208,"Flower Garden Watcher",20622,1, .@event$;
|
monster 'map_herbs$,218,208,"Flower Garden Watcher",20622,1, .@event$;
|
||||||
sleep 6000;
|
sleep 100;
|
||||||
monster 'map_herbs$,210,210,"Flower Garden Watcher",20622,1, .@event$;
|
monster 'map_herbs$,210,210,"Flower Garden Watcher",20622,1, .@event$;
|
||||||
monster 'map_herbs$,245,214,"Flower Garden Watcher",20626,1, .@event$;
|
monster 'map_herbs$,245,214,"Flower Garden Watcher",20626,1, .@event$;
|
||||||
sleep 6000;
|
sleep 100;
|
||||||
monster 'map_herbs$,220,192,"Flower Garden Watcher",20622,1, .@event$;
|
monster 'map_herbs$,220,192,"Flower Garden Watcher",20622,1, .@event$;
|
||||||
monster 'map_herbs$,248,208,"Flower Garden Watcher",20622,1, .@event$;
|
monster 'map_herbs$,248,208,"Flower Garden Watcher",20622,1, .@event$;
|
||||||
monster 'map_herbs$,253,208,"Flower Garden Watcher",20622,1, .@event$;
|
monster 'map_herbs$,253,208,"Flower Garden Watcher",20622,1, .@event$;
|
||||||
monster 'map_herbs$,253,208,"Flower Garden Watcher",20626,1, .@event$;
|
monster 'map_herbs$,253,208,"Flower Garden Watcher",20626,1, .@event$;
|
||||||
sleep 6000;
|
sleep 100;
|
||||||
monster 'map_herbs$,246,212,"Flower Garden Watcher",20624,1, .@event$;
|
monster 'map_herbs$,246,212,"Flower Garden Watcher",20624,1, .@event$;
|
||||||
sleep 6000;
|
sleep 100;
|
||||||
monster 'map_herbs$,251,210,"Flower Garden Watcher",20622,1, .@event$;
|
monster 'map_herbs$,251,210,"Flower Garden Watcher",20622,1, .@event$;
|
||||||
sleep 3000;
|
sleep 100;
|
||||||
monster 'map_herbs$,245,209,"Flower Garden Watcher",20626,1, .@event$;
|
monster 'map_herbs$,245,209,"Flower Garden Watcher",20626,1, .@event$;
|
||||||
monster 'map_herbs$,222,195,"Flower Garden Watcher",20624,1, .@event$;
|
monster 'map_herbs$,222,195,"Flower Garden Watcher",20624,1, .@event$;
|
||||||
monster 'map_herbs$,203,212,"Flower Garden Watcher",20624,1, .@event$;
|
monster 'map_herbs$,203,212,"Flower Garden Watcher",20624,1, .@event$;
|
||||||
sleep 6000;
|
sleep 100;
|
||||||
monster 'map_herbs$,208,213,"Flower Garden Watcher",20622,1, .@event$;
|
monster 'map_herbs$,208,213,"Flower Garden Watcher",20622,1, .@event$;
|
||||||
monster 'map_herbs$,219,192,"Flower Garden Watcher",20622,1, .@event$;
|
monster 'map_herbs$,219,192,"Flower Garden Watcher",20622,1, .@event$;
|
||||||
monster 'map_herbs$,245,209,"Flower Garden Watcher",20626,1, .@event$;
|
monster 'map_herbs$,245,209,"Flower Garden Watcher",20626,1, .@event$;
|
||||||
@ -1787,35 +1788,35 @@ OnSummon:
|
|||||||
'total_mobs = 27;
|
'total_mobs = 27;
|
||||||
monster 'map_herbs$,207,194,"Flower Garden Watcher",20625,1, .@event$;
|
monster 'map_herbs$,207,194,"Flower Garden Watcher",20625,1, .@event$;
|
||||||
monster 'map_herbs$,217,204,"Flower Garden Watcher",20623,1, .@event$;
|
monster 'map_herbs$,217,204,"Flower Garden Watcher",20623,1, .@event$;
|
||||||
sleep 3000;
|
sleep 100;
|
||||||
monster 'map_herbs$,210,210,"Flower Garden Watcher",20627,1, .@event$;
|
monster 'map_herbs$,210,210,"Flower Garden Watcher",20627,1, .@event$;
|
||||||
sleep 3000;
|
sleep 100;
|
||||||
monster 'map_herbs$,218,195,"Flower Garden Watcher",20623,1, .@event$;
|
monster 'map_herbs$,218,195,"Flower Garden Watcher",20623,1, .@event$;
|
||||||
sleep 3000;
|
sleep 100;
|
||||||
monster 'map_herbs$,211,209,"Flower Garden Watcher",20627,1, .@event$;
|
monster 'map_herbs$,211,209,"Flower Garden Watcher",20627,1, .@event$;
|
||||||
sleep 3000;
|
sleep 100;
|
||||||
monster 'map_herbs$,210,211,"Flower Garden Watcher",20625,1, .@event$;
|
monster 'map_herbs$,210,211,"Flower Garden Watcher",20625,1, .@event$;
|
||||||
sleep 3000;
|
sleep 100;
|
||||||
monster 'map_herbs$,207,194,"Flower Garden Watcher",20625,1, .@event$;
|
monster 'map_herbs$,207,194,"Flower Garden Watcher",20625,1, .@event$;
|
||||||
sleep 3000;
|
sleep 100;
|
||||||
monster 'map_herbs$,209,214,"Flower Garden Watcher",20623,1, .@event$;
|
monster 'map_herbs$,209,214,"Flower Garden Watcher",20623,1, .@event$;
|
||||||
sleep 3000;
|
sleep 100;
|
||||||
monster 'map_herbs$,216,192,"Flower Garden Watcher",20623,1, .@event$;
|
monster 'map_herbs$,216,192,"Flower Garden Watcher",20623,1, .@event$;
|
||||||
sleep 3000;
|
sleep 100;
|
||||||
monster 'map_herbs$,208,211,"Flower Garden Watcher",20623,1, .@event$;
|
monster 'map_herbs$,208,211,"Flower Garden Watcher",20623,1, .@event$;
|
||||||
sleep 3000;
|
sleep 100;
|
||||||
monster 'map_herbs$,214,208,"Flower Garden Watcher",20623,1, .@event$;
|
monster 'map_herbs$,214,208,"Flower Garden Watcher",20623,1, .@event$;
|
||||||
sleep 6000;
|
sleep 100;
|
||||||
monster 'map_herbs$,209,214,"Flower Garden Watcher",20623,1, .@event$;
|
monster 'map_herbs$,209,214,"Flower Garden Watcher",20623,1, .@event$;
|
||||||
monster 'map_herbs$,215,201,"Flower Garden Watcher",20627,1, .@event$;
|
monster 'map_herbs$,215,201,"Flower Garden Watcher",20627,1, .@event$;
|
||||||
monster 'map_herbs$,205,214,"Flower Garden Watcher",20623,1, .@event$;
|
monster 'map_herbs$,205,214,"Flower Garden Watcher",20623,1, .@event$;
|
||||||
monster 'map_herbs$,205,214,"Flower Garden Watcher",20625,1, .@event$;
|
monster 'map_herbs$,205,214,"Flower Garden Watcher",20625,1, .@event$;
|
||||||
sleep 6000;
|
sleep 100;
|
||||||
monster 'map_herbs$,220,207,"Flower Garden Watcher",20625,1, .@event$;
|
monster 'map_herbs$,220,207,"Flower Garden Watcher",20625,1, .@event$;
|
||||||
sleep 3000;
|
sleep 100;
|
||||||
monster 'map_herbs$,208,213,"Flower Garden Watcher",20623,1, .@event$;
|
monster 'map_herbs$,208,213,"Flower Garden Watcher",20623,1, .@event$;
|
||||||
monster 'map_herbs$,202,212,"Flower Garden Watcher",20623,1, .@event$;
|
monster 'map_herbs$,202,212,"Flower Garden Watcher",20623,1, .@event$;
|
||||||
sleep 3000;
|
sleep 100;
|
||||||
monster 'map_herbs$,202,193,"Flower Garden Watcher",20623,1, .@event$;
|
monster 'map_herbs$,202,193,"Flower Garden Watcher",20623,1, .@event$;
|
||||||
monster 'map_herbs$,206,214,"Flower Garden Watcher",20623,1, .@event$;
|
monster 'map_herbs$,206,214,"Flower Garden Watcher",20623,1, .@event$;
|
||||||
monster 'map_herbs$,245,212,"Flower Garden Watcher",20627,1, .@event$;
|
monster 'map_herbs$,245,212,"Flower Garden Watcher",20627,1, .@event$;
|
||||||
@ -1849,15 +1850,15 @@ OnSummon:
|
|||||||
monster 'map_herbs$,285,210,"Flower Garden Watcher",20624,1, .@event$;
|
monster 'map_herbs$,285,210,"Flower Garden Watcher",20624,1, .@event$;
|
||||||
monster 'map_herbs$,283,228,"Flower Garden Watcher",20624,1, .@event$;
|
monster 'map_herbs$,283,228,"Flower Garden Watcher",20624,1, .@event$;
|
||||||
monster 'map_herbs$,294,252,"Flower Garden Watcher",20624,1, .@event$;
|
monster 'map_herbs$,294,252,"Flower Garden Watcher",20624,1, .@event$;
|
||||||
sleep 3000;
|
sleep 100;
|
||||||
monster 'map_herbs$,295,247,"Flower Garden Watcher",20626,1, .@event$;
|
monster 'map_herbs$,295,247,"Flower Garden Watcher",20626,1, .@event$;
|
||||||
sleep 6000;
|
sleep 100;
|
||||||
monster 'map_herbs$,294,245,"Flower Garden Watcher",20624,1, .@event$;
|
monster 'map_herbs$,294,245,"Flower Garden Watcher",20624,1, .@event$;
|
||||||
sleep 3000;
|
sleep 100;
|
||||||
monster 'map_herbs$,281,232,"Flower Garden Watcher",20622,1, .@event$;
|
monster 'map_herbs$,281,232,"Flower Garden Watcher",20622,1, .@event$;
|
||||||
monster 'map_herbs$,287,219,"Flower Garden Watcher",20626,1, .@event$;
|
monster 'map_herbs$,287,219,"Flower Garden Watcher",20626,1, .@event$;
|
||||||
monster 'map_herbs$,302,239,"Flower Garden Watcher",20626,1, .@event$;
|
monster 'map_herbs$,302,239,"Flower Garden Watcher",20626,1, .@event$;
|
||||||
sleep 3000;
|
sleep 100;
|
||||||
monster 'map_herbs$,307,217,"Flower Garden Watcher",20622,1, .@event$;
|
monster 'map_herbs$,307,217,"Flower Garden Watcher",20622,1, .@event$;
|
||||||
monster 'map_herbs$,300,235,"Flower Garden Watcher",20624,1, .@event$;
|
monster 'map_herbs$,300,235,"Flower Garden Watcher",20624,1, .@event$;
|
||||||
monster 'map_herbs$,295,249,"Flower Garden Watcher",20624,1, .@event$;
|
monster 'map_herbs$,295,249,"Flower Garden Watcher",20624,1, .@event$;
|
||||||
@ -1873,18 +1874,18 @@ OnSummon:
|
|||||||
monster 'map_herbs$,284,236,"Flower Garden Watcher",20625,1, .@event$;
|
monster 'map_herbs$,284,236,"Flower Garden Watcher",20625,1, .@event$;
|
||||||
monster 'map_herbs$,283,235,"Flower Garden Watcher",20625,1, .@event$;
|
monster 'map_herbs$,283,235,"Flower Garden Watcher",20625,1, .@event$;
|
||||||
monster 'map_herbs$,304,240,"Flower Garden Watcher",20627,1, .@event$;
|
monster 'map_herbs$,304,240,"Flower Garden Watcher",20627,1, .@event$;
|
||||||
sleep 3000;
|
sleep 100;
|
||||||
monster 'map_herbs$,298,246,"Flower Garden Watcher",20625,1, .@event$;
|
monster 'map_herbs$,298,246,"Flower Garden Watcher",20625,1, .@event$;
|
||||||
monster 'map_herbs$,305,224,"Flower Garden Watcher",20627,1, .@event$;
|
monster 'map_herbs$,305,224,"Flower Garden Watcher",20627,1, .@event$;
|
||||||
monster 'map_herbs$,310,225,"Flower Garden Watcher",20627,1, .@event$;
|
monster 'map_herbs$,310,225,"Flower Garden Watcher",20627,1, .@event$;
|
||||||
sleep 9000;
|
sleep 100;
|
||||||
monster 'map_herbs$,284,218,"Flower Garden Watcher",20623,1, .@event$;
|
monster 'map_herbs$,284,218,"Flower Garden Watcher",20623,1, .@event$;
|
||||||
monster 'map_herbs$,298,213,"Flower Garden Watcher",20625,1, .@event$;
|
monster 'map_herbs$,298,213,"Flower Garden Watcher",20625,1, .@event$;
|
||||||
sleep 3000;
|
sleep 100;
|
||||||
monster 'map_herbs$,308,224,"Flower Garden Watcher",20625,1, .@event$;
|
monster 'map_herbs$,308,224,"Flower Garden Watcher",20625,1, .@event$;
|
||||||
monster 'map_herbs$,290,210,"Flower Garden Watcher",20625,1, .@event$;
|
monster 'map_herbs$,290,210,"Flower Garden Watcher",20625,1, .@event$;
|
||||||
monster 'map_herbs$,310,224,"Flower Garden Watcher",20627,1, .@event$;
|
monster 'map_herbs$,310,224,"Flower Garden Watcher",20627,1, .@event$;
|
||||||
sleep 3000;
|
sleep 100;
|
||||||
monster 'map_herbs$,308,220,"Flower Garden Watcher",20627,1, .@event$;
|
monster 'map_herbs$,308,220,"Flower Garden Watcher",20627,1, .@event$;
|
||||||
monster 'map_herbs$,284,211,"Flower Garden Watcher",20625,1, .@event$;
|
monster 'map_herbs$,284,211,"Flower Garden Watcher",20625,1, .@event$;
|
||||||
monster 'map_herbs$,284,218,"Flower Garden Watcher",20623,1, .@event$;
|
monster 'map_herbs$,284,218,"Flower Garden Watcher",20623,1, .@event$;
|
||||||
@ -1892,22 +1893,22 @@ OnSummon:
|
|||||||
monster 'map_herbs$,281,231,"Flower Garden Watcher",20625,1, .@event$;
|
monster 'map_herbs$,281,231,"Flower Garden Watcher",20625,1, .@event$;
|
||||||
monster 'map_herbs$,280,226,"Flower Garden Watcher",20625,1, .@event$;
|
monster 'map_herbs$,280,226,"Flower Garden Watcher",20625,1, .@event$;
|
||||||
monster 'map_herbs$,285,210,"Flower Garden Watcher",20625,1, .@event$;
|
monster 'map_herbs$,285,210,"Flower Garden Watcher",20625,1, .@event$;
|
||||||
sleep 6000;
|
sleep 100;
|
||||||
monster 'map_herbs$,280,227,"Flower Garden Watcher",20623,1, .@event$;
|
monster 'map_herbs$,280,227,"Flower Garden Watcher",20623,1, .@event$;
|
||||||
monster 'map_herbs$,285,234,"Flower Garden Watcher",20627,1, .@event$;
|
monster 'map_herbs$,285,234,"Flower Garden Watcher",20627,1, .@event$;
|
||||||
monster 'map_herbs$,283,236,"Flower Garden Watcher",20627,1, .@event$;
|
monster 'map_herbs$,283,236,"Flower Garden Watcher",20627,1, .@event$;
|
||||||
monster 'map_herbs$,284,233,"Flower Garden Watcher",20625,1, .@event$;
|
monster 'map_herbs$,284,233,"Flower Garden Watcher",20625,1, .@event$;
|
||||||
sleep 3000;
|
sleep 100;
|
||||||
monster 'map_herbs$,284,237,"Flower Garden Watcher",20625,1, .@event$;
|
monster 'map_herbs$,284,237,"Flower Garden Watcher",20625,1, .@event$;
|
||||||
monster 'map_herbs$,284,239,"Flower Garden Watcher",20627,1, .@event$;
|
monster 'map_herbs$,284,239,"Flower Garden Watcher",20627,1, .@event$;
|
||||||
monster 'map_herbs$,293,246,"Flower Garden Watcher",20627,1, .@event$;
|
monster 'map_herbs$,293,246,"Flower Garden Watcher",20627,1, .@event$;
|
||||||
monster 'map_herbs$,300,247,"Flower Garden Watcher",20627,1, .@event$;
|
monster 'map_herbs$,300,247,"Flower Garden Watcher",20627,1, .@event$;
|
||||||
sleep 3000;
|
sleep 100;
|
||||||
monster 'map_herbs$,294,253,"Flower Garden Watcher",20627,1, .@event$;
|
monster 'map_herbs$,294,253,"Flower Garden Watcher",20627,1, .@event$;
|
||||||
monster 'map_herbs$,302,240,"Flower Garden Watcher",20625,1, .@event$;
|
monster 'map_herbs$,302,240,"Flower Garden Watcher",20625,1, .@event$;
|
||||||
monster 'map_herbs$,299,255,"Flower Garden Watcher",20625,1, .@event$;
|
monster 'map_herbs$,299,255,"Flower Garden Watcher",20625,1, .@event$;
|
||||||
monster 'map_herbs$,295,256,"Flower Garden Watcher",20625,1, .@event$;
|
monster 'map_herbs$,295,256,"Flower Garden Watcher",20625,1, .@event$;
|
||||||
sleep 3000;
|
sleep 100;
|
||||||
monster 'map_herbs$,310,218,"Flower Garden Watcher",20623,1, .@event$;
|
monster 'map_herbs$,310,218,"Flower Garden Watcher",20623,1, .@event$;
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
|
|||||||
@ -412,6 +412,20 @@ Body:
|
|||||||
- Index: 3
|
- Index: 3
|
||||||
Item: IllusionStone
|
Item: IllusionStone
|
||||||
Amount: 120
|
Amount: 120
|
||||||
|
- Name: resonance_stone_barter
|
||||||
|
Items:
|
||||||
|
- Index: 0
|
||||||
|
Item: ILL_Piece_A
|
||||||
|
RequiredItems:
|
||||||
|
- Index: 0
|
||||||
|
Item: IllusionStone
|
||||||
|
Amount: 10
|
||||||
|
- Index: 1
|
||||||
|
Item: ILL_Piece_B
|
||||||
|
RequiredItems:
|
||||||
|
- Index: 0
|
||||||
|
Item: IllusionStone
|
||||||
|
Amount: 10
|
||||||
- Name: barter_ill_moonlight
|
- Name: barter_ill_moonlight
|
||||||
Items:
|
Items:
|
||||||
- Index: 0
|
- Index: 0
|
||||||
|
|||||||
@ -14,6 +14,7 @@
|
|||||||
//= 1.5 Added Illusion of Luanda enchanter [Capuche]
|
//= 1.5 Added Illusion of Luanda enchanter [Capuche]
|
||||||
//= 1.6 Added Illusion of Underwater exchange [Capuche]
|
//= 1.6 Added Illusion of Underwater exchange [Capuche]
|
||||||
//= 1.7 Added Illusion of Twins enchanter [Capuche]
|
//= 1.7 Added Illusion of Twins enchanter [Capuche]
|
||||||
|
//= 1.8 Added Illusion Merchant [Haydrich]
|
||||||
//============================================================
|
//============================================================
|
||||||
|
|
||||||
//============================================================
|
//============================================================
|
||||||
@ -846,3 +847,40 @@ OnInit:
|
|||||||
setunitdata .@npc_id, UNPC_HAIRCOLOR, 6;
|
setunitdata .@npc_id, UNPC_HAIRCOLOR, 6;
|
||||||
end;
|
end;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
//============================================================
|
||||||
|
//= Illusion Merchant
|
||||||
|
//============================================================
|
||||||
|
- marketshop market_resonance_stone -1,100003:2000000:99999,100004:2000000:99999
|
||||||
|
prontera,88,113,5 script Illusion Merchant#0829 HIDDEN_NPC,{
|
||||||
|
mes "[Illusion Merchant]";
|
||||||
|
mes "I'm selling two random optional weapon grant scrolls that I made myself. You can choose the payment method you like.";
|
||||||
|
next;
|
||||||
|
switch( select( "Purchase with Zeny.", "Purchase with Illusion Stones" )) {
|
||||||
|
case 1:
|
||||||
|
mes "[Illusion Merchant]";
|
||||||
|
mes "I hope you like it.";
|
||||||
|
close2;
|
||||||
|
callshop "market_resonance_stone";
|
||||||
|
end;
|
||||||
|
case 2:
|
||||||
|
mes "[Illusion Merchant]";
|
||||||
|
mes "I hope you like it.";
|
||||||
|
close2;
|
||||||
|
callshop "resonance_stone_barter";
|
||||||
|
end;
|
||||||
|
}
|
||||||
|
OnInit:
|
||||||
|
.@npc_id = getnpcid(0);
|
||||||
|
setunitdata .@npc_id,UNPC_CLASS, JOB_MAGE_HIGH;
|
||||||
|
setunitdata .@npc_id,UNPC_SEX,SEX_FEMALE;
|
||||||
|
setunitdata .@npc_id,UNPC_HEADTOP,142;
|
||||||
|
setunitdata .@npc_id,UNPC_HEADMIDDLE,92;
|
||||||
|
setunitdata .@npc_id,UNPC_HAIRSTYLE,2;
|
||||||
|
setunitdata .@npc_id,UNPC_HAIRCOLOR,2;
|
||||||
|
|
||||||
|
// Restock
|
||||||
|
npcshopupdate "market_resonance_stone",100003,2000000,99999;
|
||||||
|
npcshopupdate "market_resonance_stone",100004,2000000,99999;
|
||||||
|
end;
|
||||||
|
}
|
||||||
|
|||||||
@ -9,35 +9,66 @@
|
|||||||
// monsters killed. [Capuche]
|
// monsters killed. [Capuche]
|
||||||
//============================================================
|
//============================================================
|
||||||
|
|
||||||
lhz_dun_n,0,0 monster Eremes Guille 3208,20,5000,0,"lhz_dun_n::OnRegularDead"
|
lhz_dun_n,0,0 monster Eremes Guille 3208,20,5000,0,"lhz_dun_n::OnRegularDead3208"
|
||||||
lhz_dun_n,0,0 monster Magaleta Sorin 3209,10,5000,0,"lhz_dun_n::OnRegularDead"
|
lhz_dun_n,0,0 monster Magaleta Sorin 3209,10,5000,0,"lhz_dun_n::OnRegularDead3209"
|
||||||
lhz_dun_n,0,0 monster Catherine Cheiron 3210,15,5000,0,"lhz_dun_n::OnRegularDead"
|
lhz_dun_n,0,0 monster Catherine Cheiron 3210,15,5000,0,"lhz_dun_n::OnRegularDead3210"
|
||||||
lhz_dun_n,0,0 monster Shecil Damon 3211,20,5000,0,"lhz_dun_n::OnRegularDead"
|
lhz_dun_n,0,0 monster Shecil Damon 3211,20,5000,0,"lhz_dun_n::OnRegularDead3211"
|
||||||
lhz_dun_n,0,0 monster Harword Alt-Eisen 3212,10,5000,0,"lhz_dun_n::OnRegularDead"
|
lhz_dun_n,0,0 monster Harword Alt-Eisen 3212,10,5000,0,"lhz_dun_n::OnRegularDead3212"
|
||||||
lhz_dun_n,0,0 monster Seyren Windsor 3213,10,5000,0,"lhz_dun_n::OnRegularDead"
|
lhz_dun_n,0,0 monster Seyren Windsor 3213,10,5000,0,"lhz_dun_n::OnRegularDead3213"
|
||||||
|
|
||||||
lhz_dun_n,0,0 monster Randel Lawrence 3226,10,5000,0,"lhz_dun_n::OnRegularDead"
|
lhz_dun_n,0,0 monster Randel Lawrence 3226,10,5000,0,"lhz_dun_n::OnRegularDead3226"
|
||||||
lhz_dun_n,0,0 monster Flamel Emule 3227,10,5000,0,"lhz_dun_n::OnRegularDead"
|
lhz_dun_n,0,0 monster Flamel Emule 3227,10,5000,0,"lhz_dun_n::OnRegularDead3227"
|
||||||
lhz_dun_n,0,0 monster Celia Alde 3228,15,5000,0,"lhz_dun_n::OnRegularDead"
|
lhz_dun_n,0,0 monster Celia Alde 3228,15,5000,0,"lhz_dun_n::OnRegularDead3228"
|
||||||
lhz_dun_n,0,0 monster Chen Liu 3229,15,5000,0,"lhz_dun_n::OnRegularDead"
|
lhz_dun_n,0,0 monster Chen Liu 3229,15,5000,0,"lhz_dun_n::OnRegularDead3229"
|
||||||
lhz_dun_n,0,0 monster Gertie Wie 3230,15,5000,0,"lhz_dun_n::OnRegularDead"
|
lhz_dun_n,0,0 monster Gertie Wie 3230,15,5000,0,"lhz_dun_n::OnRegularDead3230"
|
||||||
lhz_dun_n,0,0 monster Alphoccio Basil 3231,10,5000,0,"lhz_dun_n::OnRegularDead"
|
lhz_dun_n,0,0 monster Alphoccio Basil 3231,10,5000,0,"lhz_dun_n::OnRegularDead3231"
|
||||||
lhz_dun_n,0,0 monster Trentini 3232,10,5000,0,"lhz_dun_n::OnRegularDead"
|
lhz_dun_n,0,0 monster Trentini 3232,10,5000,0,"lhz_dun_n::OnRegularDead3232"
|
||||||
|
|
||||||
lhz_dun_n,0,0,0 script lhz_dun_n -1,{
|
lhz_dun_n,0,0,0 script lhz_dun_n -1,{
|
||||||
end;
|
end;
|
||||||
OnRegularDead:
|
OnRegularDead3208: callsub( S_Regular, 3208 );
|
||||||
.@mob_id = killedrid;
|
OnRegularDead3209: callsub( S_Regular, 3209 );
|
||||||
|
OnRegularDead3210: callsub( S_Regular, 3210 );
|
||||||
|
OnRegularDead3211: callsub( S_Regular, 3211 );
|
||||||
|
OnRegularDead3212: callsub( S_Regular, 3212 );
|
||||||
|
OnRegularDead3213: callsub( S_Regular, 3213 );
|
||||||
|
|
||||||
|
OnRegularDead3226: callsub( S_Regular, 3226 );
|
||||||
|
OnRegularDead3227: callsub( S_Regular, 3227 );
|
||||||
|
OnRegularDead3228: callsub( S_Regular, 3228 );
|
||||||
|
OnRegularDead3229: callsub( S_Regular, 3229 );
|
||||||
|
OnRegularDead3230: callsub( S_Regular, 3230 );
|
||||||
|
OnRegularDead3231: callsub( S_Regular, 3231 );
|
||||||
|
OnRegularDead3232: callsub( S_Regular, 3232 );
|
||||||
|
|
||||||
|
S_Regular:
|
||||||
|
.@mob_id = getarg(0);
|
||||||
if (.lhz_dun_n[.@mob_id] < 110 && .lhz_dun_n_boss == 0) {
|
if (.lhz_dun_n[.@mob_id] < 110 && .lhz_dun_n_boss == 0) {
|
||||||
.lhz_dun_n[.@mob_id]++;
|
.lhz_dun_n[.@mob_id]++;
|
||||||
if (.lhz_dun_n[.@mob_id] == 110) {
|
if (.lhz_dun_n[.@mob_id] == 110) {
|
||||||
.@mini_boss = .@mob_id + 6 + (.@mob_id > 3213); // mini boss version ID: regular ID +6 for non-transcendent, +7 for others
|
.@mini_boss = .@mob_id + 6 + (.@mob_id > 3219); // mini boss version ID: regular ID +6 for non-transcendent, +7 for others
|
||||||
monster "lhz_dun_n",0,0,"--en--",.@mini_boss,1, "lhz_dun_n::OnMiniDead";
|
monster "lhz_dun_n",0,0,"--en--",.@mini_boss,1, "lhz_dun_n::OnMiniDead" + .@mini_boss;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
end;
|
end;
|
||||||
OnMiniDead:
|
|
||||||
.@mob_id = killedrid;
|
OnMiniDead3214: callsub( S_Mini, 3214 );
|
||||||
|
OnMiniDead3215: callsub( S_Mini, 3215 );
|
||||||
|
OnMiniDead3216: callsub( S_Mini, 3216 );
|
||||||
|
OnMiniDead3217: callsub( S_Mini, 3217 );
|
||||||
|
OnMiniDead3218: callsub( S_Mini, 3218 );
|
||||||
|
OnMiniDead3219: callsub( S_Mini, 3219 );
|
||||||
|
|
||||||
|
OnMiniDead3233: callsub( S_Mini, 3233 );
|
||||||
|
OnMiniDead3234: callsub( S_Mini, 3234 );
|
||||||
|
OnMiniDead3235: callsub( S_Mini, 3235 );
|
||||||
|
OnMiniDead3236: callsub( S_Mini, 3236 );
|
||||||
|
OnMiniDead3237: callsub( S_Mini, 3237 );
|
||||||
|
OnMiniDead3238: callsub( S_Mini, 3238 );
|
||||||
|
OnMiniDead3239: callsub( S_Mini, 3239 );
|
||||||
|
|
||||||
|
S_Mini:
|
||||||
|
.@mob_id = getarg(0);
|
||||||
if (.lhz_dun_n[.@mob_id] < 4 && .lhz_dun_n_boss == 0) {
|
if (.lhz_dun_n[.@mob_id] < 4 && .lhz_dun_n_boss == 0) {
|
||||||
.lhz_dun_n[.@mob_id]++;
|
.lhz_dun_n[.@mob_id]++;
|
||||||
.@regular = .@mob_id - 6 - (.@mob_id > 3219);
|
.@regular = .@mob_id - 6 - (.@mob_id > 3219);
|
||||||
@ -53,11 +84,7 @@ OnMiniDead:
|
|||||||
monster "lhz_dun_n",140,230,"--en--", F_Rand(3220,3221,3222,3223,3224,3225,3240,3241,3242,3243,3244,3245,3246),1, "lhz_dun_n::OnMyMVPDead";
|
monster "lhz_dun_n",140,230,"--en--", F_Rand(3220,3221,3222,3223,3224,3225,3240,3241,3242,3243,3244,3245,3246),1, "lhz_dun_n::OnMyMVPDead";
|
||||||
mapannounce "lhz_dun_n", "Voice of Reaper: It's been a while.", bc_map; // unknown message
|
mapannounce "lhz_dun_n", "Voice of Reaper: It's been a while.", bc_map; // unknown message
|
||||||
.lhz_dun_n_boss = 1;
|
.lhz_dun_n_boss = 1;
|
||||||
for ( .@i = 0; .@i < 13; ++.@i ) {
|
deletearray .lhz_dun_n;
|
||||||
.@regular = .@mini_boss_list[.@i] - 6 - (.@mini_boss_list[.@i] > 3219);
|
|
||||||
.lhz_dun_n[.@regular] = 0;
|
|
||||||
.lhz_dun_n[.@mini_boss_list[.@i]] = 0;
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
end;
|
end;
|
||||||
|
|||||||
@ -30,10 +30,6 @@
|
|||||||
|
|
||||||
using namespace rathena;
|
using namespace rathena;
|
||||||
|
|
||||||
// Reuseable global packet buffer to prevent too many allocations
|
|
||||||
// Take socket.cpp::socket_max_client_packet into consideration
|
|
||||||
static int8 packet_buffer[UINT16_MAX];
|
|
||||||
|
|
||||||
std::vector<struct s_point_str> accessible_maps{
|
std::vector<struct s_point_str> accessible_maps{
|
||||||
s_point_str{ MAP_PRONTERA, 273, 354 },
|
s_point_str{ MAP_PRONTERA, 273, 354 },
|
||||||
s_point_str{ MAP_GEFFEN, 120, 100 },
|
s_point_str{ MAP_GEFFEN, 120, 100 },
|
||||||
|
|||||||
@ -548,7 +548,7 @@ void mapif_Mail_return( int fd, uint32 char_id, int mail_id, uint32 account_id_r
|
|||||||
char temp_[MAIL_TITLE_LENGTH + 3];
|
char temp_[MAIL_TITLE_LENGTH + 3];
|
||||||
|
|
||||||
// swap sender and receiver
|
// swap sender and receiver
|
||||||
SWAP( msg.send_id, msg.dest_id );
|
std::swap( msg.send_id, msg.dest_id );
|
||||||
safestrncpy( temp_, msg.send_name, NAME_LENGTH );
|
safestrncpy( temp_, msg.send_name, NAME_LENGTH );
|
||||||
safestrncpy( msg.send_name, msg.dest_name, NAME_LENGTH );
|
safestrncpy( msg.send_name, msg.dest_name, NAME_LENGTH );
|
||||||
safestrncpy( msg.dest_name, temp_, NAME_LENGTH );
|
safestrncpy( msg.dest_name, temp_, NAME_LENGTH );
|
||||||
|
|||||||
@ -266,18 +266,6 @@ typedef char bool;
|
|||||||
//////////////////////////////////////////////////////////////////////////
|
//////////////////////////////////////////////////////////////////////////
|
||||||
// macro tools
|
// macro tools
|
||||||
|
|
||||||
#ifdef SWAP // just to be sure
|
|
||||||
#undef SWAP
|
|
||||||
#endif
|
|
||||||
// hmm only ints?
|
|
||||||
//#define SWAP(a,b) { int temp=a; a=b; b=temp;}
|
|
||||||
// if using macros then something that is type independent
|
|
||||||
//#define SWAP(a,b) ((a == b) || ((a ^= b), (b ^= a), (a ^= b)))
|
|
||||||
// Avoid "value computed is not used" warning and generates the same assembly code
|
|
||||||
#define SWAP(a,b) if (a != b) ((a ^= b), (b ^= a), (a ^= b))
|
|
||||||
#define swap_ptrcast(c,a,b) if ((a) != (b)) ((a) = static_cast<c>((void*)((intptr_t)(a) ^ (intptr_t)(b))), (b) = static_cast<c>((void*)((intptr_t)(a) ^ (intptr_t)(b))), (a) = static_cast<c>((void*)((intptr_t)(a) ^ (intptr_t)(b))) )
|
|
||||||
#define swap_ptr(a,b) swap_ptrcast(void*,a,b)
|
|
||||||
|
|
||||||
//////////////////////////////////////////////////////////////////////////
|
//////////////////////////////////////////////////////////////////////////
|
||||||
// should not happen
|
// should not happen
|
||||||
#ifndef NULL
|
#ifndef NULL
|
||||||
|
|||||||
@ -34,6 +34,7 @@
|
|||||||
<ClInclude Include="mmo.hpp" />
|
<ClInclude Include="mmo.hpp" />
|
||||||
<ClInclude Include="msg_conf.hpp" />
|
<ClInclude Include="msg_conf.hpp" />
|
||||||
<ClInclude Include="nullpo.hpp" />
|
<ClInclude Include="nullpo.hpp" />
|
||||||
|
<ClInclude Include="packets.hpp" />
|
||||||
<ClInclude Include="random.hpp" />
|
<ClInclude Include="random.hpp" />
|
||||||
<ClInclude Include="showmsg.hpp" />
|
<ClInclude Include="showmsg.hpp" />
|
||||||
<ClInclude Include="socket.hpp" />
|
<ClInclude Include="socket.hpp" />
|
||||||
|
|||||||
@ -56,6 +56,9 @@
|
|||||||
<ClInclude Include="nullpo.hpp">
|
<ClInclude Include="nullpo.hpp">
|
||||||
<Filter>Header Files</Filter>
|
<Filter>Header Files</Filter>
|
||||||
</ClInclude>
|
</ClInclude>
|
||||||
|
<ClInclude Include="packets.hpp">
|
||||||
|
<Filter>Header Files</Filter>
|
||||||
|
</ClInclude>
|
||||||
<ClInclude Include="random.hpp">
|
<ClInclude Include="random.hpp">
|
||||||
<Filter>Header Files</Filter>
|
<Filter>Header Files</Filter>
|
||||||
</ClInclude>
|
</ClInclude>
|
||||||
|
|||||||
@ -2386,6 +2386,7 @@ DBOptions db_fix_options(DBType type, DBOptions options)
|
|||||||
|
|
||||||
default:
|
default:
|
||||||
ShowError("db_fix_options: Unknown database type %u with options %x\n", type, options);
|
ShowError("db_fix_options: Unknown database type %u with options %x\n", type, options);
|
||||||
|
[[fallthrough]];
|
||||||
case DB_STRING:
|
case DB_STRING:
|
||||||
case DB_ISTRING: // String databases, no fix required
|
case DB_ISTRING: // String databases, no fix required
|
||||||
return options;
|
return options;
|
||||||
|
|||||||
@ -42,6 +42,8 @@
|
|||||||
#ifndef DB_HPP
|
#ifndef DB_HPP
|
||||||
#define DB_HPP
|
#define DB_HPP
|
||||||
|
|
||||||
|
#include <utility>
|
||||||
|
|
||||||
#include <stdarg.h>
|
#include <stdarg.h>
|
||||||
|
|
||||||
#include "cbasetypes.hpp"
|
#include "cbasetypes.hpp"
|
||||||
@ -1483,8 +1485,7 @@ void linkdb_foreach (struct linkdb_node** head, LinkDBFunc func, ...);
|
|||||||
/// @param __heap Binary heap
|
/// @param __heap Binary heap
|
||||||
/// @param __val Value
|
/// @param __val Value
|
||||||
/// @param __topcmp Comparator
|
/// @param __topcmp Comparator
|
||||||
/// @param __swp Swapper
|
#define BHEAP_PUSH(__heap,__val,__topcmp) \
|
||||||
#define BHEAP_PUSH(__heap,__val,__topcmp,__swp) \
|
|
||||||
do{ \
|
do{ \
|
||||||
size_t _i_ = VECTOR_LENGTH(__heap); \
|
size_t _i_ = VECTOR_LENGTH(__heap); \
|
||||||
VECTOR_PUSH(__heap,__val); /* insert at end */ \
|
VECTOR_PUSH(__heap,__val); /* insert at end */ \
|
||||||
@ -1493,7 +1494,7 @@ void linkdb_foreach (struct linkdb_node** head, LinkDBFunc func, ...);
|
|||||||
size_t _parent_ = (_i_-1)/2; \
|
size_t _parent_ = (_i_-1)/2; \
|
||||||
if( __topcmp(VECTOR_INDEX(__heap,_parent_),VECTOR_INDEX(__heap,_i_)) < 0 ) \
|
if( __topcmp(VECTOR_INDEX(__heap,_parent_),VECTOR_INDEX(__heap,_i_)) < 0 ) \
|
||||||
break; /* done */ \
|
break; /* done */ \
|
||||||
__swp(VECTOR_INDEX(__heap,_parent_),VECTOR_INDEX(__heap,_i_)); \
|
std::swap(VECTOR_INDEX(__heap,_parent_),VECTOR_INDEX(__heap,_i_)); \
|
||||||
_i_ = _parent_; \
|
_i_ = _parent_; \
|
||||||
} \
|
} \
|
||||||
}while(0)
|
}while(0)
|
||||||
@ -1505,12 +1506,11 @@ void linkdb_foreach (struct linkdb_node** head, LinkDBFunc func, ...);
|
|||||||
/// @param __heap Binary heap
|
/// @param __heap Binary heap
|
||||||
/// @param __val Value
|
/// @param __val Value
|
||||||
/// @param __topcmp Comparator
|
/// @param __topcmp Comparator
|
||||||
/// @param __swp Swapper
|
#define BHEAP_PUSH2(__heap,__val,__topcmp) \
|
||||||
#define BHEAP_PUSH2(__heap,__val,__topcmp,__swp) \
|
|
||||||
do{ \
|
do{ \
|
||||||
size_t _i_ = VECTOR_LENGTH(__heap); \
|
size_t _i_ = VECTOR_LENGTH(__heap); \
|
||||||
VECTOR_PUSH(__heap,__val); /* insert at end */ \
|
VECTOR_PUSH(__heap,__val); /* insert at end */ \
|
||||||
BHEAP_SIFTDOWN(__heap,0,_i_,__topcmp,__swp); \
|
BHEAP_SIFTDOWN(__heap,0,_i_,__topcmp); \
|
||||||
}while(0)
|
}while(0)
|
||||||
|
|
||||||
|
|
||||||
@ -1525,8 +1525,7 @@ void linkdb_foreach (struct linkdb_node** head, LinkDBFunc func, ...);
|
|||||||
///
|
///
|
||||||
/// @param __heap Binary heap
|
/// @param __heap Binary heap
|
||||||
/// @param __topcmp Comparator
|
/// @param __topcmp Comparator
|
||||||
/// @param __swp Swapper
|
#define BHEAP_POP(__heap,__topcmp) BHEAP_POPINDEX(__heap,0,__topcmp)
|
||||||
#define BHEAP_POP(__heap,__topcmp,__swp) BHEAP_POPINDEX(__heap,0,__topcmp,__swp)
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
@ -1534,13 +1533,12 @@ void linkdb_foreach (struct linkdb_node** head, LinkDBFunc func, ...);
|
|||||||
///
|
///
|
||||||
/// @param __heap Binary heap
|
/// @param __heap Binary heap
|
||||||
/// @param __topcmp Comparator
|
/// @param __topcmp Comparator
|
||||||
/// @param __swp Swapper
|
#define BHEAP_POP2(__heap,__topcmp) \
|
||||||
#define BHEAP_POP2(__heap,__topcmp,__swp) \
|
|
||||||
do{ \
|
do{ \
|
||||||
VECTOR_INDEX(__heap,0) = VECTOR_POP(__heap); /* put last at index */ \
|
VECTOR_INDEX(__heap,0) = VECTOR_POP(__heap); /* put last at index */ \
|
||||||
if( !VECTOR_LENGTH(__heap) ) /* removed last, nothing to do */ \
|
if( !VECTOR_LENGTH(__heap) ) /* removed last, nothing to do */ \
|
||||||
break; \
|
break; \
|
||||||
BHEAP_SIFTUP(__heap,0,__topcmp,__swp); \
|
BHEAP_SIFTUP(__heap,0,__topcmp); \
|
||||||
}while(0)
|
}while(0)
|
||||||
|
|
||||||
|
|
||||||
@ -1556,8 +1554,7 @@ void linkdb_foreach (struct linkdb_node** head, LinkDBFunc func, ...);
|
|||||||
/// @param __heap Binary heap
|
/// @param __heap Binary heap
|
||||||
/// @param __idx Index
|
/// @param __idx Index
|
||||||
/// @param __topcmp Comparator
|
/// @param __topcmp Comparator
|
||||||
/// @param __swp Swapper
|
#define BHEAP_POPINDEX(__heap,__idx,__topcmp) \
|
||||||
#define BHEAP_POPINDEX(__heap,__idx,__topcmp,__swp) \
|
|
||||||
do{ \
|
do{ \
|
||||||
size_t _i_ = __idx; \
|
size_t _i_ = __idx; \
|
||||||
VECTOR_INDEX(__heap,__idx) = VECTOR_POP(__heap); /* put last at index */ \
|
VECTOR_INDEX(__heap,__idx) = VECTOR_POP(__heap); /* put last at index */ \
|
||||||
@ -1568,7 +1565,7 @@ void linkdb_foreach (struct linkdb_node** head, LinkDBFunc func, ...);
|
|||||||
size_t _parent_ = (_i_-1)/2; \
|
size_t _parent_ = (_i_-1)/2; \
|
||||||
if( __topcmp(VECTOR_INDEX(__heap,_parent_),VECTOR_INDEX(__heap,_i_)) < 0 ) \
|
if( __topcmp(VECTOR_INDEX(__heap,_parent_),VECTOR_INDEX(__heap,_i_)) < 0 ) \
|
||||||
break; /* done */ \
|
break; /* done */ \
|
||||||
__swp(VECTOR_INDEX(__heap,_parent_),VECTOR_INDEX(__heap,_i_)); \
|
std::swap(VECTOR_INDEX(__heap,_parent_),VECTOR_INDEX(__heap,_i_)); \
|
||||||
_i_ = _parent_; \
|
_i_ = _parent_; \
|
||||||
} \
|
} \
|
||||||
while( _i_ < VECTOR_LENGTH(__heap) ) \
|
while( _i_ < VECTOR_LENGTH(__heap) ) \
|
||||||
@ -1580,12 +1577,12 @@ void linkdb_foreach (struct linkdb_node** head, LinkDBFunc func, ...);
|
|||||||
break; /* done */ \
|
break; /* done */ \
|
||||||
else if( _rchild_ >= VECTOR_LENGTH(__heap) || __topcmp(VECTOR_INDEX(__heap,_lchild_),VECTOR_INDEX(__heap,_rchild_)) <= 0 ) \
|
else if( _rchild_ >= VECTOR_LENGTH(__heap) || __topcmp(VECTOR_INDEX(__heap,_lchild_),VECTOR_INDEX(__heap,_rchild_)) <= 0 ) \
|
||||||
{ /* left child */ \
|
{ /* left child */ \
|
||||||
__swp(VECTOR_INDEX(__heap,_i_),VECTOR_INDEX(__heap,_lchild_)); \
|
std::swap(VECTOR_INDEX(__heap,_i_),VECTOR_INDEX(__heap,_lchild_)); \
|
||||||
_i_ = _lchild_; \
|
_i_ = _lchild_; \
|
||||||
} \
|
} \
|
||||||
else \
|
else \
|
||||||
{ /* right child */ \
|
{ /* right child */ \
|
||||||
__swp(VECTOR_INDEX(__heap,_i_),VECTOR_INDEX(__heap,_rchild_)); \
|
std::swap(VECTOR_INDEX(__heap,_i_),VECTOR_INDEX(__heap,_rchild_)); \
|
||||||
_i_ = _rchild_; \
|
_i_ = _rchild_; \
|
||||||
} \
|
} \
|
||||||
} \
|
} \
|
||||||
@ -1601,8 +1598,7 @@ void linkdb_foreach (struct linkdb_node** head, LinkDBFunc func, ...);
|
|||||||
/// @param __startidx Index of an ancestor of __idx
|
/// @param __startidx Index of an ancestor of __idx
|
||||||
/// @param __idx Index of an inserted element
|
/// @param __idx Index of an inserted element
|
||||||
/// @param __topcmp Comparator
|
/// @param __topcmp Comparator
|
||||||
/// @param __swp Swapper
|
#define BHEAP_SIFTDOWN(__heap,__startidx,__idx,__topcmp) \
|
||||||
#define BHEAP_SIFTDOWN(__heap,__startidx,__idx,__topcmp,__swp) \
|
|
||||||
do{ \
|
do{ \
|
||||||
size_t _i2_ = __idx; \
|
size_t _i2_ = __idx; \
|
||||||
while( _i2_ > __startidx ) \
|
while( _i2_ > __startidx ) \
|
||||||
@ -1610,7 +1606,7 @@ void linkdb_foreach (struct linkdb_node** head, LinkDBFunc func, ...);
|
|||||||
size_t _parent_ = (_i2_-1)/2; \
|
size_t _parent_ = (_i2_-1)/2; \
|
||||||
if( __topcmp(VECTOR_INDEX(__heap,_parent_),VECTOR_INDEX(__heap,_i2_)) <= 0 ) \
|
if( __topcmp(VECTOR_INDEX(__heap,_parent_),VECTOR_INDEX(__heap,_i2_)) <= 0 ) \
|
||||||
break; /* done */ \
|
break; /* done */ \
|
||||||
__swp(VECTOR_INDEX(__heap,_parent_),VECTOR_INDEX(__heap,_i2_)); \
|
std::swap(VECTOR_INDEX(__heap,_parent_),VECTOR_INDEX(__heap,_i2_)); \
|
||||||
_i2_ = _parent_; \
|
_i2_ = _parent_; \
|
||||||
} \
|
} \
|
||||||
}while(0)
|
}while(0)
|
||||||
@ -1622,8 +1618,7 @@ void linkdb_foreach (struct linkdb_node** head, LinkDBFunc func, ...);
|
|||||||
/// @param __heap Binary heap
|
/// @param __heap Binary heap
|
||||||
/// @param __idx Index of an inserted element
|
/// @param __idx Index of an inserted element
|
||||||
/// @param __topcmp Comparator
|
/// @param __topcmp Comparator
|
||||||
/// @param __swp Swapper
|
#define BHEAP_SIFTUP(__heap,__idx,__topcmp) \
|
||||||
#define BHEAP_SIFTUP(__heap,__idx,__topcmp,__swp) \
|
|
||||||
do{ \
|
do{ \
|
||||||
size_t _i_ = __idx; \
|
size_t _i_ = __idx; \
|
||||||
size_t _lchild_ = _i_*2 + 1; \
|
size_t _lchild_ = _i_*2 + 1; \
|
||||||
@ -1632,17 +1627,17 @@ void linkdb_foreach (struct linkdb_node** head, LinkDBFunc func, ...);
|
|||||||
size_t _rchild_ = _i_*2 + 2; \
|
size_t _rchild_ = _i_*2 + 2; \
|
||||||
if( _rchild_ >= VECTOR_LENGTH(__heap) || __topcmp(VECTOR_INDEX(__heap,_lchild_),VECTOR_INDEX(__heap,_rchild_)) < 0 ) \
|
if( _rchild_ >= VECTOR_LENGTH(__heap) || __topcmp(VECTOR_INDEX(__heap,_lchild_),VECTOR_INDEX(__heap,_rchild_)) < 0 ) \
|
||||||
{ /* left child */ \
|
{ /* left child */ \
|
||||||
__swp(VECTOR_INDEX(__heap,_i_),VECTOR_INDEX(__heap,_lchild_)); \
|
std::swap(VECTOR_INDEX(__heap,_i_),VECTOR_INDEX(__heap,_lchild_)); \
|
||||||
_i_ = _lchild_; \
|
_i_ = _lchild_; \
|
||||||
} \
|
} \
|
||||||
else \
|
else \
|
||||||
{ /* right child */ \
|
{ /* right child */ \
|
||||||
__swp(VECTOR_INDEX(__heap,_i_),VECTOR_INDEX(__heap,_rchild_)); \
|
std::swap(VECTOR_INDEX(__heap,_i_),VECTOR_INDEX(__heap,_rchild_)); \
|
||||||
_i_ = _rchild_; \
|
_i_ = _rchild_; \
|
||||||
} \
|
} \
|
||||||
_lchild_ = _i_*2 + 1; \
|
_lchild_ = _i_*2 + 1; \
|
||||||
} \
|
} \
|
||||||
BHEAP_SIFTDOWN(__heap,__idx,_i_,__topcmp,__swp); \
|
BHEAP_SIFTDOWN(__heap,__idx,_i_,__topcmp); \
|
||||||
}while(0)
|
}while(0)
|
||||||
|
|
||||||
|
|
||||||
@ -1652,11 +1647,10 @@ void linkdb_foreach (struct linkdb_node** head, LinkDBFunc func, ...);
|
|||||||
/// @param __heap Binary heap
|
/// @param __heap Binary heap
|
||||||
/// @param __idx Index
|
/// @param __idx Index
|
||||||
/// @param __topcmp Comparator
|
/// @param __topcmp Comparator
|
||||||
/// @param __swp Swapper
|
#define BHEAP_UPDATE(__heap,__idx,__topcmp) \
|
||||||
#define BHEAP_UPDATE(__heap,__idx,__topcmp,__swp) \
|
|
||||||
do{ \
|
do{ \
|
||||||
BHEAP_SIFTDOWN(__heap,0,__idx,__topcmp,__swp); \
|
BHEAP_SIFTDOWN(__heap,0,__idx,__topcmp); \
|
||||||
BHEAP_SIFTUP(__heap,__idx,__topcmp,__swp); \
|
BHEAP_SIFTUP(__heap,__idx,__topcmp); \
|
||||||
}while(0)
|
}while(0)
|
||||||
|
|
||||||
|
|
||||||
|
|||||||
@ -164,6 +164,7 @@ void mapindex_init(void) {
|
|||||||
switch (sscanf(line, "%11s\t%d", map_name, &index)) {
|
switch (sscanf(line, "%11s\t%d", map_name, &index)) {
|
||||||
case 1: //Map with no ID given, auto-assign
|
case 1: //Map with no ID given, auto-assign
|
||||||
index = last_index+1;
|
index = last_index+1;
|
||||||
|
[[fallthrough]];
|
||||||
case 2: //Map with ID given
|
case 2: //Map with ID given
|
||||||
mapindex_addmap(index,map_name);
|
mapindex_addmap(index,map_name);
|
||||||
break;
|
break;
|
||||||
|
|||||||
@ -235,10 +235,8 @@ void MD5_String(const char * string, char * output)
|
|||||||
}
|
}
|
||||||
|
|
||||||
/** output is a sequence of non-zero characters to be used as password salt. */
|
/** output is a sequence of non-zero characters to be used as password salt. */
|
||||||
void MD5_Salt(unsigned int len, char * output)
|
void MD5_Salt( size_t len, char* output ){
|
||||||
{
|
for( size_t i = 0; i < len; ++i ){
|
||||||
unsigned int i;
|
output[i] = static_cast<char>( rnd_value( 1, 255 ) );
|
||||||
for( i = 0; i < len; ++i )
|
}
|
||||||
output[i] = (char)(1 + rnd() % 255);
|
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|||||||
@ -4,8 +4,10 @@
|
|||||||
#ifndef MD5CALC_HPP
|
#ifndef MD5CALC_HPP
|
||||||
#define MD5CALC_HPP
|
#define MD5CALC_HPP
|
||||||
|
|
||||||
|
#include "cbasetypes.hpp"
|
||||||
|
|
||||||
void MD5_String(const char * string, char * output);
|
void MD5_String(const char * string, char * output);
|
||||||
void MD5_Binary(const char * string, unsigned char * output);
|
void MD5_Binary(const char * string, unsigned char * output);
|
||||||
void MD5_Salt(unsigned int len, char * output);
|
void MD5_Salt(size_t len, char * output);
|
||||||
|
|
||||||
#endif /* MD5CALC_HPP */
|
#endif /* MD5CALC_HPP */
|
||||||
|
|||||||
@ -116,6 +116,9 @@ typedef uint32 t_itemid;
|
|||||||
#ifndef MAX_BARTER_REQUIREMENTS
|
#ifndef MAX_BARTER_REQUIREMENTS
|
||||||
#define MAX_BARTER_REQUIREMENTS 5
|
#define MAX_BARTER_REQUIREMENTS 5
|
||||||
#endif
|
#endif
|
||||||
|
#ifndef WEB_AUTH_TOKEN_LENGTH
|
||||||
|
#define WEB_AUTH_TOKEN_LENGTH 16+1
|
||||||
|
#endif
|
||||||
|
|
||||||
enum e_enchantgrade : uint16{
|
enum e_enchantgrade : uint16{
|
||||||
ENCHANTGRADE_NONE = 0,
|
ENCHANTGRADE_NONE = 0,
|
||||||
|
|||||||
212
src/common/packets.hpp
Normal file
212
src/common/packets.hpp
Normal file
@ -0,0 +1,212 @@
|
|||||||
|
// Copyright (c) rAthena Dev Teams - Licensed under GNU GPL
|
||||||
|
// For more information, see LICENCE in the main folder
|
||||||
|
|
||||||
|
#ifndef PACKETS_HPP
|
||||||
|
#define PACKETS_HPP
|
||||||
|
|
||||||
|
#include <common/cbasetypes.hpp>
|
||||||
|
#include <common/mmo.hpp>
|
||||||
|
|
||||||
|
#pragma warning( push )
|
||||||
|
#pragma warning( disable : 4200 )
|
||||||
|
|
||||||
|
#define DEFINE_PACKET_HEADER( name, id ) const int16 HEADER_##name = id
|
||||||
|
#define DEFINE_PACKET_ID( name, id ) DEFINE_PACKET_HEADER( name, id )
|
||||||
|
|
||||||
|
// NetBSD 5 and Solaris don't like pragma pack but accept the packed attribute
|
||||||
|
#if !defined( sun ) && ( !defined( __NETBSD__ ) || __NetBSD_Version__ >= 600000000 )
|
||||||
|
#pragma pack( push, 1 )
|
||||||
|
#endif
|
||||||
|
|
||||||
|
struct PACKET_CA_LOGIN{
|
||||||
|
int16 packetType;
|
||||||
|
uint32 version;
|
||||||
|
char username[NAME_LENGTH];
|
||||||
|
char password[NAME_LENGTH];
|
||||||
|
uint8 clienttype;
|
||||||
|
} __attribute__((packed));
|
||||||
|
DEFINE_PACKET_HEADER( CA_LOGIN, 0x64 );
|
||||||
|
|
||||||
|
#if PACKETVER >= 20170315
|
||||||
|
struct PACKET_AC_ACCEPT_LOGIN_sub{
|
||||||
|
uint32 ip;
|
||||||
|
uint16 port;
|
||||||
|
char name[20];
|
||||||
|
uint16 users;
|
||||||
|
uint16 type;
|
||||||
|
uint16 new_;
|
||||||
|
uint8 unknown[128];
|
||||||
|
} __attribute__((packed));
|
||||||
|
|
||||||
|
struct PACKET_AC_ACCEPT_LOGIN{
|
||||||
|
int16 packetType;
|
||||||
|
int16 packetLength;
|
||||||
|
uint32 login_id1;
|
||||||
|
uint32 AID;
|
||||||
|
uint32 login_id2;
|
||||||
|
uint32 last_ip;
|
||||||
|
char last_login[26];
|
||||||
|
uint8 sex;
|
||||||
|
char token[WEB_AUTH_TOKEN_LENGTH];
|
||||||
|
PACKET_AC_ACCEPT_LOGIN_sub char_servers[];
|
||||||
|
} __attribute__((packed));
|
||||||
|
DEFINE_PACKET_HEADER( AC_ACCEPT_LOGIN, 0xac4 );
|
||||||
|
#else
|
||||||
|
struct PACKET_AC_ACCEPT_LOGIN_sub{
|
||||||
|
uint32 ip;
|
||||||
|
uint16 port;
|
||||||
|
char name[20];
|
||||||
|
uint16 users;
|
||||||
|
uint16 type;
|
||||||
|
uint16 new_;
|
||||||
|
} __attribute__((packed));
|
||||||
|
|
||||||
|
struct PACKET_AC_ACCEPT_LOGIN{
|
||||||
|
int16 packetType;
|
||||||
|
int16 packetLength;
|
||||||
|
uint32 login_id1;
|
||||||
|
uint32 AID;
|
||||||
|
uint32 login_id2;
|
||||||
|
uint32 last_ip;
|
||||||
|
char last_login[26];
|
||||||
|
uint8 sex;
|
||||||
|
PACKET_AC_ACCEPT_LOGIN_sub char_servers[];
|
||||||
|
} __attribute__((packed));
|
||||||
|
DEFINE_PACKET_HEADER( AC_ACCEPT_LOGIN, 0x69 );
|
||||||
|
#endif
|
||||||
|
|
||||||
|
// not sure when this started
|
||||||
|
#if PACKETVER >= 20120000
|
||||||
|
struct PACKET_AC_REFUSE_LOGIN{
|
||||||
|
int16 packetType;
|
||||||
|
uint32 error;
|
||||||
|
char unblock_time[20];
|
||||||
|
} __attribute__((packed));
|
||||||
|
DEFINE_PACKET_HEADER( AC_REFUSE_LOGIN, 0x83e );
|
||||||
|
#else
|
||||||
|
struct PACKET_AC_REFUSE_LOGIN{
|
||||||
|
int16 packetType;
|
||||||
|
uint8 error;
|
||||||
|
char unblock_time[20];
|
||||||
|
} __attribute__((packed));
|
||||||
|
DEFINE_PACKET_HEADER( AC_REFUSE_LOGIN, 0x6a );
|
||||||
|
#endif
|
||||||
|
|
||||||
|
struct PACKET_SC_NOTIFY_BAN{
|
||||||
|
int16 packetType;
|
||||||
|
uint8 result;
|
||||||
|
} __attribute__((packed));
|
||||||
|
DEFINE_PACKET_HEADER( SC_NOTIFY_BAN, 0x81 );
|
||||||
|
|
||||||
|
struct PACKET_CA_REQ_HASH{
|
||||||
|
int16 packetType;
|
||||||
|
} __attribute__((packed));
|
||||||
|
DEFINE_PACKET_HEADER( CA_REQ_HASH, 0x1db );
|
||||||
|
|
||||||
|
struct PACKET_AC_ACK_HASH{
|
||||||
|
int16 packetType;
|
||||||
|
int16 packetLength;
|
||||||
|
char salt[];
|
||||||
|
} __attribute__((packed));
|
||||||
|
DEFINE_PACKET_HEADER( AC_ACK_HASH, 0x1dc );
|
||||||
|
|
||||||
|
struct PACKET_CA_LOGIN2{
|
||||||
|
int16 packetType;
|
||||||
|
uint32 version;
|
||||||
|
char username[NAME_LENGTH];
|
||||||
|
uint8 passwordMD5[16];
|
||||||
|
uint8 clienttype;
|
||||||
|
} __attribute__((packed));
|
||||||
|
DEFINE_PACKET_HEADER( CA_LOGIN2, 0x1dd );
|
||||||
|
|
||||||
|
struct PACKET_CA_LOGIN3{
|
||||||
|
int16 packetType;
|
||||||
|
uint32 version;
|
||||||
|
char username[NAME_LENGTH];
|
||||||
|
uint8 passwordMD5[16];
|
||||||
|
uint8 clienttype;
|
||||||
|
uint8 clientinfo;
|
||||||
|
} __attribute__((packed));
|
||||||
|
DEFINE_PACKET_HEADER( CA_LOGIN3, 0x1fa );
|
||||||
|
|
||||||
|
struct PACKET_CA_CONNECT_INFO_CHANGED{
|
||||||
|
int16 packetType;
|
||||||
|
char name[NAME_LENGTH];
|
||||||
|
} __attribute__((packed));
|
||||||
|
DEFINE_PACKET_HEADER( CA_CONNECT_INFO_CHANGED, 0x200 );
|
||||||
|
|
||||||
|
struct PACKET_CA_EXE_HASHCHECK{
|
||||||
|
int16 packetType;
|
||||||
|
char hash[16];
|
||||||
|
} __attribute__((packed));
|
||||||
|
DEFINE_PACKET_HEADER( CA_EXE_HASHCHECK, 0x204 );
|
||||||
|
|
||||||
|
struct PACKET_CA_LOGIN_PCBANG{
|
||||||
|
int16 packetType;
|
||||||
|
uint32 version;
|
||||||
|
char username[NAME_LENGTH];
|
||||||
|
char password[NAME_LENGTH];
|
||||||
|
uint8 clienttype;
|
||||||
|
char ip[16];
|
||||||
|
char mac[13];
|
||||||
|
} __attribute__((packed));
|
||||||
|
DEFINE_PACKET_HEADER( CA_LOGIN_PCBANG, 0x277 );
|
||||||
|
|
||||||
|
struct PACKET_CA_LOGIN4{
|
||||||
|
int16 packetType;
|
||||||
|
uint32 version;
|
||||||
|
char username[NAME_LENGTH];
|
||||||
|
uint8 passwordMD5[16];
|
||||||
|
uint8 clienttype;
|
||||||
|
char mac[13];
|
||||||
|
} __attribute__((packed));
|
||||||
|
DEFINE_PACKET_HEADER( CA_LOGIN4, 0x27c );
|
||||||
|
|
||||||
|
struct PACKET_CA_LOGIN_CHANNEL{
|
||||||
|
int16 packetType;
|
||||||
|
uint32 version;
|
||||||
|
char username[NAME_LENGTH];
|
||||||
|
char password[NAME_LENGTH];
|
||||||
|
uint8 clienttype;
|
||||||
|
char ip[16];
|
||||||
|
char mac[13];
|
||||||
|
uint8 is_gravity;
|
||||||
|
} __attribute__((packed));
|
||||||
|
DEFINE_PACKET_HEADER( CA_LOGIN_CHANNEL, 0x2b0 );
|
||||||
|
|
||||||
|
struct PACKET_CA_SSO_LOGIN_REQ{
|
||||||
|
int16 packetType;
|
||||||
|
int16 packetLength;
|
||||||
|
uint32 version;
|
||||||
|
uint8 clienttype;
|
||||||
|
char username[NAME_LENGTH];
|
||||||
|
char password[27];
|
||||||
|
char mac[17];
|
||||||
|
char ip[15];
|
||||||
|
char token[];
|
||||||
|
} __attribute__((packed));
|
||||||
|
DEFINE_PACKET_HEADER( CA_SSO_LOGIN_REQ, 0x825 );
|
||||||
|
|
||||||
|
struct PACKET_CT_AUTH{
|
||||||
|
int16 packetType;
|
||||||
|
uint8 unknown[66];
|
||||||
|
} __attribute__((packed));
|
||||||
|
DEFINE_PACKET_HEADER( CT_AUTH, 0xacf );
|
||||||
|
|
||||||
|
struct PACKET_TC_RESULT{
|
||||||
|
int16 packetType;
|
||||||
|
int16 packetLength;
|
||||||
|
uint32 type;
|
||||||
|
char unknown1[20];
|
||||||
|
char unknown2[6];
|
||||||
|
} __attribute__((packed));
|
||||||
|
DEFINE_PACKET_HEADER( TC_RESULT, 0xae3 );
|
||||||
|
|
||||||
|
// NetBSD 5 and Solaris don't like pragma pack but accept the packed attribute
|
||||||
|
#if !defined( sun ) && ( !defined( __NETBSD__ ) || __NetBSD_Version__ >= 600000000 )
|
||||||
|
#pragma pack( pop )
|
||||||
|
#endif
|
||||||
|
|
||||||
|
#pragma warning( pop )
|
||||||
|
|
||||||
|
#endif /* PACKETS_HPP */
|
||||||
@ -20,6 +20,9 @@ int32 rnd(void);// [0, SINT32_MAX]
|
|||||||
*/
|
*/
|
||||||
template <typename T>
|
template <typename T>
|
||||||
typename std::enable_if<std::is_integral<T>::value, T>::type rnd_value(T min, T max) {
|
typename std::enable_if<std::is_integral<T>::value, T>::type rnd_value(T min, T max) {
|
||||||
|
if (min > max) {
|
||||||
|
std::swap(min, max);
|
||||||
|
}
|
||||||
std::uniform_int_distribution<T> dist(min, max);
|
std::uniform_int_distribution<T> dist(min, max);
|
||||||
return dist(generator);
|
return dist(generator);
|
||||||
}
|
}
|
||||||
|
|||||||
@ -47,6 +47,10 @@
|
|||||||
#include "strlib.hpp"
|
#include "strlib.hpp"
|
||||||
#include "timer.hpp"
|
#include "timer.hpp"
|
||||||
|
|
||||||
|
// Reuseable global packet buffer to prevent too many allocations
|
||||||
|
// Take socket.cpp::socket_max_client_packet into consideration
|
||||||
|
int8 packet_buffer[UINT16_MAX];
|
||||||
|
|
||||||
/////////////////////////////////////////////////////////////////////
|
/////////////////////////////////////////////////////////////////////
|
||||||
#if defined(WIN32)
|
#if defined(WIN32)
|
||||||
/////////////////////////////////////////////////////////////////////
|
/////////////////////////////////////////////////////////////////////
|
||||||
|
|||||||
@ -199,4 +199,34 @@ void send_shortlist_add_fd(int fd);
|
|||||||
void send_shortlist_do_sends();
|
void send_shortlist_do_sends();
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
// Reuseable global packet buffer to prevent too many allocations
|
||||||
|
// Take socket.cpp::socket_max_client_packet into consideration
|
||||||
|
extern int8 packet_buffer[UINT16_MAX];
|
||||||
|
|
||||||
|
template <typename P>
|
||||||
|
bool socket_send( int fd, P& packet ){
|
||||||
|
if( !session_isActive( fd ) ){
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
WFIFOHEAD( fd, sizeof( P ) );
|
||||||
|
memcpy( WFIFOP( fd, 0 ), &packet, sizeof( P ) );
|
||||||
|
WFIFOSET( fd, sizeof( P ) );
|
||||||
|
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
template <typename P>
|
||||||
|
bool socket_send( int fd, P* packet ){
|
||||||
|
if( !session_isActive( fd ) ){
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
WFIFOHEAD( fd, packet->packetLength );
|
||||||
|
memcpy( WFIFOP( fd, 0 ), packet, packet->packetLength );
|
||||||
|
WFIFOSET( fd, packet->packetLength );
|
||||||
|
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
#endif /* SOCKET_HPP */
|
#endif /* SOCKET_HPP */
|
||||||
|
|||||||
@ -511,59 +511,91 @@ static int Sql_P_BindSqlDataType(MYSQL_BIND* bind, enum SqlDataType buffer_type,
|
|||||||
memset(bind, 0, sizeof(MYSQL_BIND));
|
memset(bind, 0, sizeof(MYSQL_BIND));
|
||||||
switch( buffer_type )
|
switch( buffer_type )
|
||||||
{
|
{
|
||||||
case SQLDT_NULL: bind->buffer_type = MYSQL_TYPE_NULL;
|
case SQLDT_NULL:
|
||||||
|
bind->buffer_type = MYSQL_TYPE_NULL;
|
||||||
buffer_len = 0;// FIXME length = ? [FlavioJS]
|
buffer_len = 0;// FIXME length = ? [FlavioJS]
|
||||||
break;
|
break;
|
||||||
// fixed size
|
// fixed size
|
||||||
case SQLDT_UINT8: bind->is_unsigned = 1;
|
case SQLDT_UINT8:
|
||||||
case SQLDT_INT8: bind->buffer_type = MYSQL_TYPE_TINY;
|
bind->is_unsigned = 1;
|
||||||
|
[[fallthrough]];
|
||||||
|
case SQLDT_INT8:
|
||||||
|
bind->buffer_type = MYSQL_TYPE_TINY;
|
||||||
buffer_len = 1;
|
buffer_len = 1;
|
||||||
break;
|
break;
|
||||||
case SQLDT_UINT16: bind->is_unsigned = 1;
|
case SQLDT_UINT16:
|
||||||
case SQLDT_INT16: bind->buffer_type = MYSQL_TYPE_SHORT;
|
bind->is_unsigned = 1;
|
||||||
|
[[fallthrough]];
|
||||||
|
case SQLDT_INT16:
|
||||||
|
bind->buffer_type = MYSQL_TYPE_SHORT;
|
||||||
buffer_len = 2;
|
buffer_len = 2;
|
||||||
break;
|
break;
|
||||||
case SQLDT_UINT32: bind->is_unsigned = 1;
|
case SQLDT_UINT32:
|
||||||
case SQLDT_INT32: bind->buffer_type = MYSQL_TYPE_LONG;
|
bind->is_unsigned = 1;
|
||||||
|
[[fallthrough]];
|
||||||
|
case SQLDT_INT32:
|
||||||
|
bind->buffer_type = MYSQL_TYPE_LONG;
|
||||||
buffer_len = 4;
|
buffer_len = 4;
|
||||||
break;
|
break;
|
||||||
case SQLDT_UINT64: bind->is_unsigned = 1;
|
case SQLDT_UINT64:
|
||||||
case SQLDT_INT64: bind->buffer_type = MYSQL_TYPE_LONGLONG;
|
bind->is_unsigned = 1;
|
||||||
|
[[fallthrough]];
|
||||||
|
case SQLDT_INT64:
|
||||||
|
bind->buffer_type = MYSQL_TYPE_LONGLONG;
|
||||||
buffer_len = 8;
|
buffer_len = 8;
|
||||||
break;
|
break;
|
||||||
// platform dependent size
|
// platform dependent size
|
||||||
case SQLDT_UCHAR: bind->is_unsigned = 1;
|
case SQLDT_UCHAR:
|
||||||
case SQLDT_CHAR: bind->buffer_type = Sql_P_SizeToMysqlIntType(sizeof(char));
|
bind->is_unsigned = 1;
|
||||||
|
[[fallthrough]];
|
||||||
|
case SQLDT_CHAR:
|
||||||
|
bind->buffer_type = Sql_P_SizeToMysqlIntType(sizeof(char));
|
||||||
buffer_len = sizeof(char);
|
buffer_len = sizeof(char);
|
||||||
break;
|
break;
|
||||||
case SQLDT_USHORT: bind->is_unsigned = 1;
|
case SQLDT_USHORT:
|
||||||
case SQLDT_SHORT: bind->buffer_type = Sql_P_SizeToMysqlIntType(sizeof(short));
|
bind->is_unsigned = 1;
|
||||||
|
[[fallthrough]];
|
||||||
|
case SQLDT_SHORT:
|
||||||
|
bind->buffer_type = Sql_P_SizeToMysqlIntType(sizeof(short));
|
||||||
buffer_len = sizeof(short);
|
buffer_len = sizeof(short);
|
||||||
break;
|
break;
|
||||||
case SQLDT_UINT: bind->is_unsigned = 1;
|
case SQLDT_UINT:
|
||||||
case SQLDT_INT: bind->buffer_type = Sql_P_SizeToMysqlIntType(sizeof(int));
|
bind->is_unsigned = 1;
|
||||||
|
[[fallthrough]];
|
||||||
|
case SQLDT_INT:
|
||||||
|
bind->buffer_type = Sql_P_SizeToMysqlIntType(sizeof(int));
|
||||||
buffer_len = sizeof(int);
|
buffer_len = sizeof(int);
|
||||||
break;
|
break;
|
||||||
case SQLDT_ULONG: bind->is_unsigned = 1;
|
case SQLDT_ULONG:
|
||||||
case SQLDT_LONG: bind->buffer_type = Sql_P_SizeToMysqlIntType(sizeof(long));
|
bind->is_unsigned = 1;
|
||||||
|
[[fallthrough]];
|
||||||
|
case SQLDT_LONG:
|
||||||
|
bind->buffer_type = Sql_P_SizeToMysqlIntType(sizeof(long));
|
||||||
buffer_len = sizeof(long);
|
buffer_len = sizeof(long);
|
||||||
break;
|
break;
|
||||||
case SQLDT_ULONGLONG: bind->is_unsigned = 1;
|
case SQLDT_ULONGLONG:
|
||||||
case SQLDT_LONGLONG: bind->buffer_type = Sql_P_SizeToMysqlIntType(sizeof(int64));
|
bind->is_unsigned = 1;
|
||||||
|
[[fallthrough]];
|
||||||
|
case SQLDT_LONGLONG:
|
||||||
|
bind->buffer_type = Sql_P_SizeToMysqlIntType(sizeof(int64));
|
||||||
buffer_len = sizeof(int64);
|
buffer_len = sizeof(int64);
|
||||||
break;
|
break;
|
||||||
// floating point
|
// floating point
|
||||||
case SQLDT_FLOAT: bind->buffer_type = MYSQL_TYPE_FLOAT;
|
case SQLDT_FLOAT:
|
||||||
|
bind->buffer_type = MYSQL_TYPE_FLOAT;
|
||||||
buffer_len = 4;
|
buffer_len = 4;
|
||||||
break;
|
break;
|
||||||
case SQLDT_DOUBLE: bind->buffer_type = MYSQL_TYPE_DOUBLE;
|
case SQLDT_DOUBLE:
|
||||||
|
bind->buffer_type = MYSQL_TYPE_DOUBLE;
|
||||||
buffer_len = 8;
|
buffer_len = 8;
|
||||||
break;
|
break;
|
||||||
// other
|
// other
|
||||||
case SQLDT_STRING:
|
case SQLDT_STRING:
|
||||||
case SQLDT_ENUM: bind->buffer_type = MYSQL_TYPE_STRING;
|
case SQLDT_ENUM:
|
||||||
|
bind->buffer_type = MYSQL_TYPE_STRING;
|
||||||
break;
|
break;
|
||||||
case SQLDT_BLOB: bind->buffer_type = MYSQL_TYPE_BLOB;
|
case SQLDT_BLOB:
|
||||||
|
bind->buffer_type = MYSQL_TYPE_BLOB;
|
||||||
break;
|
break;
|
||||||
default:
|
default:
|
||||||
ShowDebug("Sql_P_BindSqlDataType: unsupported buffer type (%d)\n", buffer_type);
|
ShowDebug("Sql_P_BindSqlDataType: unsupported buffer type (%d)\n", buffer_type);
|
||||||
|
|||||||
@ -3,6 +3,8 @@
|
|||||||
|
|
||||||
#include "timer.hpp"
|
#include "timer.hpp"
|
||||||
|
|
||||||
|
#include <utility>
|
||||||
|
|
||||||
#include <stdlib.h>
|
#include <stdlib.h>
|
||||||
#include <string.h>
|
#include <string.h>
|
||||||
|
|
||||||
@ -203,7 +205,7 @@ t_tick gettick(void)
|
|||||||
static void push_timer_heap(int tid)
|
static void push_timer_heap(int tid)
|
||||||
{
|
{
|
||||||
BHEAP_ENSURE(timer_heap, 1, 256);
|
BHEAP_ENSURE(timer_heap, 1, 256);
|
||||||
BHEAP_PUSH(timer_heap, tid, DIFFTICK_MINTOPCMP, SWAP);
|
BHEAP_PUSH(timer_heap, tid, DIFFTICK_MINTOPCMP);
|
||||||
}
|
}
|
||||||
|
|
||||||
/*==========================
|
/*==========================
|
||||||
@ -340,9 +342,9 @@ t_tick settick_timer(int tid, t_tick tick)
|
|||||||
return tick;// nothing to do, already in propper position
|
return tick;// nothing to do, already in propper position
|
||||||
|
|
||||||
// pop and push adjusted timer
|
// pop and push adjusted timer
|
||||||
BHEAP_POPINDEX(timer_heap, i, DIFFTICK_MINTOPCMP, SWAP);
|
BHEAP_POPINDEX(timer_heap, i, DIFFTICK_MINTOPCMP);
|
||||||
timer_data[tid].tick = tick;
|
timer_data[tid].tick = tick;
|
||||||
BHEAP_PUSH(timer_heap, tid, DIFFTICK_MINTOPCMP, SWAP);
|
BHEAP_PUSH(timer_heap, tid, DIFFTICK_MINTOPCMP);
|
||||||
return tick;
|
return tick;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -362,7 +364,7 @@ t_tick do_timer(t_tick tick)
|
|||||||
break; // no more expired timers to process
|
break; // no more expired timers to process
|
||||||
|
|
||||||
// remove timer
|
// remove timer
|
||||||
BHEAP_POP(timer_heap, DIFFTICK_MINTOPCMP, SWAP);
|
BHEAP_POP(timer_heap, DIFFTICK_MINTOPCMP);
|
||||||
timer_data[tid].type |= TIMER_REMOVE_HEAP;
|
timer_data[tid].type |= TIMER_REMOVE_HEAP;
|
||||||
|
|
||||||
if( timer_data[tid].func )
|
if( timer_data[tid].func )
|
||||||
|
|||||||
@ -22,12 +22,12 @@
|
|||||||
typedef struct AccountDB_SQL {
|
typedef struct AccountDB_SQL {
|
||||||
AccountDB vtable; // public interface
|
AccountDB vtable; // public interface
|
||||||
Sql* accounts; // SQL handle accounts storage
|
Sql* accounts; // SQL handle accounts storage
|
||||||
char db_hostname[1024]; // Doubled for long hostnames (bugreport:8003)
|
std::string db_hostname = "127.0.0.1";
|
||||||
uint16 db_port;
|
uint16 db_port = 3306;
|
||||||
char db_username[1024];
|
std::string db_username = "ragnarok";
|
||||||
char db_password[1024];
|
std::string db_password = "";
|
||||||
char db_database[1024];
|
std::string db_database = "ragnarok";
|
||||||
char codepage[1024];
|
std::string codepage = "";
|
||||||
// other settings
|
// other settings
|
||||||
bool case_sensitive;
|
bool case_sensitive;
|
||||||
//table name
|
//table name
|
||||||
@ -67,6 +67,7 @@ static bool mmo_auth_tosql(AccountDB_SQL* db, const struct mmo_account* acc, boo
|
|||||||
/// public constructor
|
/// public constructor
|
||||||
AccountDB* account_db_sql(void) {
|
AccountDB* account_db_sql(void) {
|
||||||
AccountDB_SQL* db = (AccountDB_SQL*)aCalloc(1, sizeof(AccountDB_SQL));
|
AccountDB_SQL* db = (AccountDB_SQL*)aCalloc(1, sizeof(AccountDB_SQL));
|
||||||
|
new(db) AccountDB_SQL();
|
||||||
|
|
||||||
// set up the vtable
|
// set up the vtable
|
||||||
db->vtable.init = &account_db_sql_init;
|
db->vtable.init = &account_db_sql_init;
|
||||||
@ -85,13 +86,6 @@ AccountDB* account_db_sql(void) {
|
|||||||
|
|
||||||
// initialize to default values
|
// initialize to default values
|
||||||
db->accounts = NULL;
|
db->accounts = NULL;
|
||||||
// local sql settings
|
|
||||||
safestrncpy(db->db_hostname, "127.0.0.1", sizeof(db->db_hostname));
|
|
||||||
db->db_port = 3306;
|
|
||||||
safestrncpy(db->db_username, "ragnarok", sizeof(db->db_username));
|
|
||||||
safestrncpy(db->db_password, "", sizeof(db->db_password));
|
|
||||||
safestrncpy(db->db_database, "ragnarok", sizeof(db->db_database));
|
|
||||||
safestrncpy(db->codepage, "", sizeof(db->codepage));
|
|
||||||
// other settings
|
// other settings
|
||||||
db->case_sensitive = false;
|
db->case_sensitive = false;
|
||||||
safestrncpy(db->account_db, "login", sizeof(db->account_db));
|
safestrncpy(db->account_db, "login", sizeof(db->account_db));
|
||||||
@ -112,34 +106,21 @@ AccountDB* account_db_sql(void) {
|
|||||||
static bool account_db_sql_init(AccountDB* self) {
|
static bool account_db_sql_init(AccountDB* self) {
|
||||||
AccountDB_SQL* db = (AccountDB_SQL*)self;
|
AccountDB_SQL* db = (AccountDB_SQL*)self;
|
||||||
Sql* sql_handle;
|
Sql* sql_handle;
|
||||||
const char* username = "ragnarok";
|
|
||||||
const char* password = "";
|
|
||||||
const char* hostname = "127.0.0.1";
|
|
||||||
uint16 port = 3306;
|
|
||||||
const char* database = "ragnarok";
|
|
||||||
const char* codepage = "";
|
|
||||||
|
|
||||||
db->accounts = Sql_Malloc();
|
db->accounts = Sql_Malloc();
|
||||||
sql_handle = db->accounts;
|
sql_handle = db->accounts;
|
||||||
|
|
||||||
username = db->db_username;
|
if( SQL_ERROR == Sql_Connect(sql_handle, db->db_username.c_str(), db->db_password.c_str(), db->db_hostname.c_str(), db->db_port, db->db_database.c_str()) )
|
||||||
password = db->db_password;
|
|
||||||
hostname = db->db_hostname;
|
|
||||||
port = db->db_port;
|
|
||||||
database = db->db_database;
|
|
||||||
codepage = db->codepage;
|
|
||||||
|
|
||||||
if( SQL_ERROR == Sql_Connect(sql_handle, username, password, hostname, port, database) )
|
|
||||||
{
|
{
|
||||||
ShowError("Couldn't connect with uname='%s',host='%s',port='%d',database='%s'\n",
|
ShowError("Couldn't connect with uname='%s',host='%s',port='%hu',database='%s'\n",
|
||||||
username, hostname, port, database);
|
db->db_username.c_str(), db->db_hostname.c_str(), db->db_port, db->db_database.c_str());
|
||||||
Sql_ShowDebug(sql_handle);
|
Sql_ShowDebug(sql_handle);
|
||||||
Sql_Free(db->accounts);
|
Sql_Free(db->accounts);
|
||||||
db->accounts = NULL;
|
db->accounts = NULL;
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
if( codepage[0] != '\0' && SQL_ERROR == Sql_SetEncoding(sql_handle, codepage) )
|
if( !db->codepage.empty() && SQL_ERROR == Sql_SetEncoding(sql_handle, db->codepage.c_str()) )
|
||||||
Sql_ShowDebug(sql_handle);
|
Sql_ShowDebug(sql_handle);
|
||||||
|
|
||||||
self->remove_webtokens( self );
|
self->remove_webtokens( self );
|
||||||
@ -160,6 +141,8 @@ static void account_db_sql_destroy(AccountDB* self){
|
|||||||
|
|
||||||
Sql_Free(db->accounts);
|
Sql_Free(db->accounts);
|
||||||
db->accounts = NULL;
|
db->accounts = NULL;
|
||||||
|
|
||||||
|
db->~AccountDB_SQL();
|
||||||
aFree(db);
|
aFree(db);
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -181,19 +164,19 @@ static bool account_db_sql_get_property(AccountDB* self, const char* key, char*
|
|||||||
if( strncmpi(key, signature, strlen(signature)) == 0 ) {
|
if( strncmpi(key, signature, strlen(signature)) == 0 ) {
|
||||||
key += strlen(signature);
|
key += strlen(signature);
|
||||||
if( strcmpi(key, "ip") == 0 )
|
if( strcmpi(key, "ip") == 0 )
|
||||||
safesnprintf(buf, buflen, "%s", db->db_hostname);
|
safesnprintf(buf, buflen, "%s", db->db_hostname.c_str());
|
||||||
else
|
else
|
||||||
if( strcmpi(key, "port") == 0 )
|
if( strcmpi(key, "port") == 0 )
|
||||||
safesnprintf(buf, buflen, "%d", db->db_port);
|
safesnprintf(buf, buflen, "%hu", db->db_port);
|
||||||
else
|
else
|
||||||
if( strcmpi(key, "id") == 0 )
|
if( strcmpi(key, "id") == 0 )
|
||||||
safesnprintf(buf, buflen, "%s", db->db_username);
|
safesnprintf(buf, buflen, "%s", db->db_username.c_str());
|
||||||
else
|
else
|
||||||
if( strcmpi(key, "pw") == 0 )
|
if( strcmpi(key, "pw") == 0 )
|
||||||
safesnprintf(buf, buflen, "%s", db->db_password);
|
safesnprintf(buf, buflen, "%s", db->db_password.c_str());
|
||||||
else
|
else
|
||||||
if( strcmpi(key, "db") == 0 )
|
if( strcmpi(key, "db") == 0 )
|
||||||
safesnprintf(buf, buflen, "%s", db->db_database);
|
safesnprintf(buf, buflen, "%s", db->db_database.c_str());
|
||||||
else
|
else
|
||||||
if( strcmpi(key, "account_db") == 0 )
|
if( strcmpi(key, "account_db") == 0 )
|
||||||
safesnprintf(buf, buflen, "%s", db->account_db);
|
safesnprintf(buf, buflen, "%s", db->account_db);
|
||||||
@ -212,7 +195,7 @@ static bool account_db_sql_get_property(AccountDB* self, const char* key, char*
|
|||||||
if( strncmpi(key, signature, strlen(signature)) == 0 ) {
|
if( strncmpi(key, signature, strlen(signature)) == 0 ) {
|
||||||
key += strlen(signature);
|
key += strlen(signature);
|
||||||
if( strcmpi(key, "codepage") == 0 )
|
if( strcmpi(key, "codepage") == 0 )
|
||||||
safesnprintf(buf, buflen, "%s", db->codepage);
|
safesnprintf(buf, buflen, "%s", db->codepage.c_str());
|
||||||
else
|
else
|
||||||
if( strcmpi(key, "case_sensitive") == 0 )
|
if( strcmpi(key, "case_sensitive") == 0 )
|
||||||
safesnprintf(buf, buflen, "%d", (db->case_sensitive ? 1 : 0));
|
safesnprintf(buf, buflen, "%d", (db->case_sensitive ? 1 : 0));
|
||||||
@ -240,19 +223,19 @@ static bool account_db_sql_set_property(AccountDB* self, const char* key, const
|
|||||||
if( strncmp(key, signature, strlen(signature)) == 0 ) {
|
if( strncmp(key, signature, strlen(signature)) == 0 ) {
|
||||||
key += strlen(signature);
|
key += strlen(signature);
|
||||||
if( strcmpi(key, "ip") == 0 )
|
if( strcmpi(key, "ip") == 0 )
|
||||||
safestrncpy(db->db_hostname, value, sizeof(db->db_hostname));
|
db->db_hostname = value;
|
||||||
else
|
else
|
||||||
if( strcmpi(key, "port") == 0 )
|
if( strcmpi(key, "port") == 0 )
|
||||||
db->db_port = (uint16)strtoul(value, NULL, 10);
|
db->db_port = (uint16)strtoul( value, nullptr, 10 );
|
||||||
else
|
else
|
||||||
if( strcmpi(key, "id") == 0 )
|
if( strcmpi(key, "id") == 0 )
|
||||||
safestrncpy(db->db_username, value, sizeof(db->db_username));
|
db->db_username = value;
|
||||||
else
|
else
|
||||||
if( strcmpi(key, "pw") == 0 )
|
if( strcmpi(key, "pw") == 0 )
|
||||||
safestrncpy(db->db_password, value, sizeof(db->db_password));
|
db->db_password = value;
|
||||||
else
|
else
|
||||||
if( strcmpi(key, "db") == 0 )
|
if( strcmpi(key, "db") == 0 )
|
||||||
safestrncpy(db->db_database, value, sizeof(db->db_database));
|
db->db_database = value;
|
||||||
else
|
else
|
||||||
if( strcmpi(key, "account_db") == 0 )
|
if( strcmpi(key, "account_db") == 0 )
|
||||||
safestrncpy(db->account_db, value, sizeof(db->account_db));
|
safestrncpy(db->account_db, value, sizeof(db->account_db));
|
||||||
@ -271,7 +254,7 @@ static bool account_db_sql_set_property(AccountDB* self, const char* key, const
|
|||||||
if( strncmpi(key, signature, strlen(signature)) == 0 ) {
|
if( strncmpi(key, signature, strlen(signature)) == 0 ) {
|
||||||
key += strlen(signature);
|
key += strlen(signature);
|
||||||
if( strcmpi(key, "codepage") == 0 )
|
if( strcmpi(key, "codepage") == 0 )
|
||||||
safestrncpy(db->codepage, value, sizeof(db->codepage));
|
db->codepage = value;
|
||||||
else
|
else
|
||||||
if( strcmpi(key, "case_sensitive") == 0 )
|
if( strcmpi(key, "case_sensitive") == 0 )
|
||||||
db->case_sensitive = (config_switch(value)==1);
|
db->case_sensitive = (config_switch(value)==1);
|
||||||
|
|||||||
@ -5,13 +5,9 @@
|
|||||||
#define ACCOUNT_HPP
|
#define ACCOUNT_HPP
|
||||||
|
|
||||||
#include <common/cbasetypes.hpp>
|
#include <common/cbasetypes.hpp>
|
||||||
#include <common/mmo.hpp> // ACCOUNT_REG2_NUM
|
#include <common/mmo.hpp> // ACCOUNT_REG2_NUM, WEB_AUTH_TOKEN_LENGTH
|
||||||
#include <config/core.hpp>
|
#include <config/core.hpp>
|
||||||
|
|
||||||
#ifndef WEB_AUTH_TOKEN_LENGTH
|
|
||||||
#define WEB_AUTH_TOKEN_LENGTH 16+1
|
|
||||||
#endif
|
|
||||||
|
|
||||||
typedef struct AccountDB AccountDB;
|
typedef struct AccountDB AccountDB;
|
||||||
typedef struct AccountDBIterator AccountDBIterator;
|
typedef struct AccountDBIterator AccountDBIterator;
|
||||||
|
|
||||||
|
|||||||
@ -15,14 +15,14 @@
|
|||||||
#include "login.hpp"
|
#include "login.hpp"
|
||||||
#include "loginlog.hpp"
|
#include "loginlog.hpp"
|
||||||
|
|
||||||
// login sql settings
|
|
||||||
static char ipban_db_hostname[64] = "127.0.0.1";
|
std::string ipban_db_hostname = "127.0.0.1";
|
||||||
static uint16 ipban_db_port = 3306;
|
uint16 ipban_db_port = 3306;
|
||||||
static char ipban_db_username[32] = "ragnarok";
|
std::string ipban_db_username = "ragnarok";
|
||||||
static char ipban_db_password[32] = "";
|
std::string ipban_db_password = "";
|
||||||
static char ipban_db_database[32] = "ragnarok";
|
std::string ipban_db_database = "ragnarok";
|
||||||
static char ipban_codepage[32] = "";
|
std::string ipban_codepage = "";
|
||||||
static char ipban_table[32] = "ipbanlist";
|
std::string ipban_table = "ipbanlist";
|
||||||
|
|
||||||
// globals
|
// globals
|
||||||
static Sql* sql_handle = NULL;
|
static Sql* sql_handle = NULL;
|
||||||
@ -46,7 +46,7 @@ bool ipban_check(uint32 ip) {
|
|||||||
return false;// ipban disabled
|
return false;// ipban disabled
|
||||||
|
|
||||||
if( SQL_ERROR == Sql_Query(sql_handle, "SELECT count(*) FROM `%s` WHERE `rtime` > NOW() AND (`list` = '%u.*.*.*' OR `list` = '%u.%u.*.*' OR `list` = '%u.%u.%u.*' OR `list` = '%u.%u.%u.%u')",
|
if( SQL_ERROR == Sql_Query(sql_handle, "SELECT count(*) FROM `%s` WHERE `rtime` > NOW() AND (`list` = '%u.*.*.*' OR `list` = '%u.%u.*.*' OR `list` = '%u.%u.%u.*' OR `list` = '%u.%u.%u.%u')",
|
||||||
ipban_table, p[3], p[3], p[2], p[3], p[2], p[1], p[3], p[2], p[1], p[0]) )
|
ipban_table.c_str(), p[3], p[3], p[2], p[3], p[2], p[1], p[3], p[2], p[1], p[0]) )
|
||||||
{
|
{
|
||||||
Sql_ShowDebug(sql_handle);
|
Sql_ShowDebug(sql_handle);
|
||||||
// close connection because we can't verify their connectivity.
|
// close connection because we can't verify their connectivity.
|
||||||
@ -81,7 +81,7 @@ void ipban_log(uint32 ip) {
|
|||||||
{
|
{
|
||||||
uint8* p = (uint8*)&ip;
|
uint8* p = (uint8*)&ip;
|
||||||
if( SQL_ERROR == Sql_Query(sql_handle, "INSERT INTO `%s`(`list`,`btime`,`rtime`,`reason`) VALUES ('%u.%u.%u.*', NOW() , NOW() + INTERVAL %d MINUTE ,'Password error ban')",
|
if( SQL_ERROR == Sql_Query(sql_handle, "INSERT INTO `%s`(`list`,`btime`,`rtime`,`reason`) VALUES ('%u.%u.%u.*', NOW() , NOW() + INTERVAL %d MINUTE ,'Password error ban')",
|
||||||
ipban_table, p[3], p[2], p[1], login_config.dynamic_pass_failure_ban_duration) )
|
ipban_table.c_str(), p[3], p[2], p[1], login_config.dynamic_pass_failure_ban_duration) )
|
||||||
Sql_ShowDebug(sql_handle);
|
Sql_ShowDebug(sql_handle);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -100,7 +100,7 @@ TIMER_FUNC(ipban_cleanup){
|
|||||||
if( !login_config.ipban )
|
if( !login_config.ipban )
|
||||||
return 0;// ipban disabled
|
return 0;// ipban disabled
|
||||||
|
|
||||||
if( SQL_ERROR == Sql_Query(sql_handle, "DELETE FROM `%s` WHERE `rtime` <= NOW()", ipban_table) )
|
if( SQL_ERROR == Sql_Query(sql_handle, "DELETE FROM `%s` WHERE `rtime` <= NOW()", ipban_table.c_str()) )
|
||||||
Sql_ShowDebug(sql_handle);
|
Sql_ShowDebug(sql_handle);
|
||||||
|
|
||||||
return 0;
|
return 0;
|
||||||
@ -123,19 +123,19 @@ bool ipban_config_read(const char* key, const char* value) {
|
|||||||
{
|
{
|
||||||
key += strlen(signature);
|
key += strlen(signature);
|
||||||
if( strcmpi(key, "ip") == 0 )
|
if( strcmpi(key, "ip") == 0 )
|
||||||
safestrncpy(ipban_db_hostname, value, sizeof(ipban_db_hostname));
|
ipban_db_hostname = value;
|
||||||
else
|
else
|
||||||
if( strcmpi(key, "port") == 0 )
|
if( strcmpi(key, "port") == 0 )
|
||||||
ipban_db_port = (uint16)strtoul(value, NULL, 10);
|
ipban_db_port = (uint16)strtoul( value, nullptr, 10 );
|
||||||
else
|
else
|
||||||
if( strcmpi(key, "id") == 0 )
|
if( strcmpi(key, "id") == 0 )
|
||||||
safestrncpy(ipban_db_username, value, sizeof(ipban_db_username));
|
ipban_db_username = value;
|
||||||
else
|
else
|
||||||
if( strcmpi(key, "pw") == 0 )
|
if( strcmpi(key, "pw") == 0 )
|
||||||
safestrncpy(ipban_db_password, value, sizeof(ipban_db_password));
|
ipban_db_password = value;
|
||||||
else
|
else
|
||||||
if( strcmpi(key, "db") == 0 )
|
if( strcmpi(key, "db") == 0 )
|
||||||
safestrncpy(ipban_db_database, value, sizeof(ipban_db_database));
|
ipban_db_database = value;
|
||||||
else
|
else
|
||||||
return false;// not found
|
return false;// not found
|
||||||
return true;
|
return true;
|
||||||
@ -146,10 +146,10 @@ bool ipban_config_read(const char* key, const char* value) {
|
|||||||
{
|
{
|
||||||
key += strlen(signature);
|
key += strlen(signature);
|
||||||
if( strcmpi(key, "codepage") == 0 )
|
if( strcmpi(key, "codepage") == 0 )
|
||||||
safestrncpy(ipban_codepage, value, sizeof(ipban_codepage));
|
ipban_codepage = value;
|
||||||
else
|
else
|
||||||
if( strcmpi(key, "ipban_table") == 0 )
|
if( strcmpi(key, "ipban_table") == 0 )
|
||||||
safestrncpy(ipban_table, value, sizeof(ipban_table));
|
ipban_table = value;
|
||||||
else
|
else
|
||||||
if( strcmpi(key, "enable") == 0 )
|
if( strcmpi(key, "enable") == 0 )
|
||||||
login_config.ipban = (config_switch(value) != 0);
|
login_config.ipban = (config_switch(value) != 0);
|
||||||
@ -181,41 +181,25 @@ bool ipban_config_read(const char* key, const char* value) {
|
|||||||
* Launched at login-serv start, create db or other long scope variable here.
|
* Launched at login-serv start, create db or other long scope variable here.
|
||||||
*/
|
*/
|
||||||
void ipban_init(void) {
|
void ipban_init(void) {
|
||||||
const char* username = ipban_db_username;
|
|
||||||
const char* password = ipban_db_password;
|
|
||||||
const char* hostname = ipban_db_hostname;
|
|
||||||
uint16 port = ipban_db_port;
|
|
||||||
const char* database = ipban_db_database;
|
|
||||||
const char* codepage = ipban_codepage;
|
|
||||||
|
|
||||||
ipban_inited = true;
|
ipban_inited = true;
|
||||||
|
|
||||||
if( !login_config.ipban )
|
if( !login_config.ipban )
|
||||||
return;// ipban disabled
|
return;// ipban disabled
|
||||||
|
|
||||||
if( ipban_db_hostname[0] != '\0' )
|
|
||||||
{// local settings
|
|
||||||
username = ipban_db_username;
|
|
||||||
password = ipban_db_password;
|
|
||||||
hostname = ipban_db_hostname;
|
|
||||||
port = ipban_db_port;
|
|
||||||
database = ipban_db_database;
|
|
||||||
codepage = ipban_codepage;
|
|
||||||
}
|
|
||||||
|
|
||||||
// establish connections
|
// establish connections
|
||||||
sql_handle = Sql_Malloc();
|
sql_handle = Sql_Malloc();
|
||||||
if( SQL_ERROR == Sql_Connect(sql_handle, username, password, hostname, port, database) )
|
if( SQL_ERROR == Sql_Connect(sql_handle, ipban_db_username.c_str(), ipban_db_password.c_str(), ipban_db_hostname.c_str(), ipban_db_port, ipban_db_database.c_str()) )
|
||||||
{
|
{
|
||||||
ShowError("Couldn't connect with uname='%s',passwd='%s',host='%s',port='%d',database='%s'\n",
|
ShowError("Couldn't connect with uname='%s',host='%s',port='%hu',database='%s'\n",
|
||||||
username, password, hostname, port, database);
|
ipban_db_username.c_str(), ipban_db_hostname.c_str(), ipban_db_port, ipban_db_database.c_str());
|
||||||
Sql_ShowDebug(sql_handle);
|
Sql_ShowDebug(sql_handle);
|
||||||
Sql_Free(sql_handle);
|
Sql_Free(sql_handle);
|
||||||
exit(EXIT_FAILURE);
|
exit(EXIT_FAILURE);
|
||||||
}
|
}
|
||||||
ShowInfo("Ipban connection made.\n");
|
|
||||||
|
|
||||||
if( codepage[0] != '\0' && SQL_ERROR == Sql_SetEncoding(sql_handle, codepage) )
|
ShowInfo("Ipban connection made.\n");
|
||||||
|
|
||||||
|
if( !ipban_codepage.empty() && SQL_ERROR == Sql_SetEncoding(sql_handle, ipban_codepage.c_str()) )
|
||||||
Sql_ShowDebug(sql_handle);
|
Sql_ShowDebug(sql_handle);
|
||||||
|
|
||||||
if( login_config.ipban_cleanup_interval > 0 )
|
if( login_config.ipban_cleanup_interval > 0 )
|
||||||
|
|||||||
@ -56,7 +56,7 @@ int subnet_count = 0; //number of subnet config
|
|||||||
int login_fd; // login server file descriptor socket
|
int login_fd; // login server file descriptor socket
|
||||||
|
|
||||||
//early declaration
|
//early declaration
|
||||||
bool login_check_password(const char* md5key, int passwdenc, const char* passwd, const char* refpass);
|
bool login_check_password( struct login_session_data& sd, struct mmo_account& acc );
|
||||||
|
|
||||||
///Accessors
|
///Accessors
|
||||||
AccountDB* login_get_accounts_db(void){
|
AccountDB* login_get_accounts_db(void){
|
||||||
@ -345,7 +345,12 @@ int login_mmo_auth(struct login_session_data* sd, bool isServer) {
|
|||||||
return 0; // 0 = Unregistered ID
|
return 0; // 0 = Unregistered ID
|
||||||
}
|
}
|
||||||
|
|
||||||
if( !login_check_password(sd->md5key, sd->passwdenc, sd->passwd, acc.pass) ) {
|
if( !isServer && sex_str2num( acc.sex ) == SEX_SERVER ){
|
||||||
|
ShowWarning( "Connection refused: ip %s tried to log into server account '%s'\n", ip, sd->userid );
|
||||||
|
return 0; // 0 = Unregistered ID
|
||||||
|
}
|
||||||
|
|
||||||
|
if( !login_check_password( *sd, acc ) ) {
|
||||||
ShowNotice("Invalid password (account: '%s', ip: %s)\n", sd->userid, ip);
|
ShowNotice("Invalid password (account: '%s', ip: %s)\n", sd->userid, ip);
|
||||||
return 1; // 1 = Incorrect Password
|
return 1; // 1 = Incorrect Password
|
||||||
}
|
}
|
||||||
@ -426,24 +431,6 @@ int login_mmo_auth(struct login_session_data* sd, bool isServer) {
|
|||||||
return -1; // account OK
|
return -1; // account OK
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
|
||||||
* Sub function of login_check_password.
|
|
||||||
* Checking if password matches the one in db hashed with client md5key.
|
|
||||||
* Test if(md5(str1+str2)==passwd).
|
|
||||||
* @param str1: string (atm:md5key or dbpass)
|
|
||||||
* @param str2: string (atm:md5key or dbpass)
|
|
||||||
* @param passwd: pass to check
|
|
||||||
* @return true if matching else false
|
|
||||||
*/
|
|
||||||
bool login_check_encrypted(const char* str1, const char* str2, const char* passwd) {
|
|
||||||
char tmpstr[64+1], md5str[32+1];
|
|
||||||
|
|
||||||
safesnprintf(tmpstr, sizeof(tmpstr), "%s%s", str1, str2);
|
|
||||||
MD5_String(tmpstr, md5str);
|
|
||||||
|
|
||||||
return (0==strcmp(passwd, md5str));
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Verify if a password is correct.
|
* Verify if a password is correct.
|
||||||
* @param md5key: md5key of client
|
* @param md5key: md5key of client
|
||||||
@ -452,16 +439,44 @@ bool login_check_encrypted(const char* str1, const char* str2, const char* passw
|
|||||||
* @param refpass: pass register in db
|
* @param refpass: pass register in db
|
||||||
* @return true if matching else false
|
* @return true if matching else false
|
||||||
*/
|
*/
|
||||||
bool login_check_password(const char* md5key, int passwdenc, const char* passwd, const char* refpass) {
|
bool login_check_password( struct login_session_data& sd, struct mmo_account& acc ){
|
||||||
if(passwdenc == 0){
|
if( sd.passwdenc == 0 ){
|
||||||
return (0==strcmp(passwd, refpass));
|
return 0 == strcmp( sd.passwd, acc.pass );
|
||||||
}
|
}
|
||||||
else {
|
|
||||||
// password mode set to 1 -> md5(md5key, refpass) enable with <passwordencrypt></passwordencrypt>
|
// password mode set to 1 -> md5(md5key, refpass) enable with <passwordencrypt></passwordencrypt>
|
||||||
// password mode set to 2 -> md5(refpass, md5key) enable with <passwordencrypt2></passwordencrypt2>
|
if( sd.passwdenc & 0x01 ){
|
||||||
return ((passwdenc&0x01) && login_check_encrypted(md5key, refpass, passwd)) ||
|
std::string pwd;
|
||||||
((passwdenc&0x02) && login_check_encrypted(refpass, md5key, passwd));
|
|
||||||
|
pwd.append( sd.md5key, sd.md5keylen );
|
||||||
|
pwd.append( acc.pass );
|
||||||
|
|
||||||
|
char md5str[32 + 1];
|
||||||
|
|
||||||
|
MD5_String( pwd.c_str(), md5str );
|
||||||
|
|
||||||
|
if( 0 == strcmp( sd.passwd, md5str ) ){
|
||||||
|
return true;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// password mode set to 2 -> md5(refpass, md5key) enable with <passwordencrypt2></passwordencrypt2>
|
||||||
|
if( sd.passwdenc & 0x02 ){
|
||||||
|
std::string pwd;
|
||||||
|
|
||||||
|
pwd.append( acc.pass );
|
||||||
|
pwd.append( sd.md5key, sd.md5keylen );
|
||||||
|
|
||||||
|
char md5str[32 + 1];
|
||||||
|
|
||||||
|
MD5_String( pwd.c_str(), md5str );
|
||||||
|
|
||||||
|
if( 0 == strcmp( sd.passwd, md5str ) ){
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
int login_get_usercount( int users ){
|
int login_get_usercount( int users ){
|
||||||
|
|||||||
@ -8,6 +8,7 @@
|
|||||||
|
|
||||||
#include <common/malloc.hpp>
|
#include <common/malloc.hpp>
|
||||||
#include <common/md5calc.hpp>
|
#include <common/md5calc.hpp>
|
||||||
|
#include <common/packets.hpp>
|
||||||
#include <common/random.hpp>
|
#include <common/random.hpp>
|
||||||
#include <common/showmsg.hpp> //show notice
|
#include <common/showmsg.hpp> //show notice
|
||||||
#include <common/socket.hpp> //wfifo session
|
#include <common/socket.hpp> //wfifo session
|
||||||
@ -31,10 +32,12 @@
|
|||||||
* <result>.B (SC_NOTIFY_BAN)
|
* <result>.B (SC_NOTIFY_BAN)
|
||||||
*/
|
*/
|
||||||
static void logclif_sent_auth_result(int fd,char result){
|
static void logclif_sent_auth_result(int fd,char result){
|
||||||
WFIFOHEAD(fd,3);
|
PACKET_SC_NOTIFY_BAN p = {};
|
||||||
WFIFOW(fd,0) = 0x81;
|
|
||||||
WFIFOB(fd,2) = result;
|
p.packetType = HEADER_SC_NOTIFY_BAN;
|
||||||
WFIFOSET(fd,3);
|
p.result = result;
|
||||||
|
|
||||||
|
socket_send( fd, p );
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@ -49,16 +52,6 @@ static void logclif_auth_ok(struct login_session_data* sd) {
|
|||||||
uint32 subnet_char_ip;
|
uint32 subnet_char_ip;
|
||||||
int i;
|
int i;
|
||||||
|
|
||||||
#if PACKETVER < 20170315
|
|
||||||
int cmd = 0x69; // AC_ACCEPT_LOGIN
|
|
||||||
int header = 47;
|
|
||||||
int size = 32;
|
|
||||||
#else
|
|
||||||
int cmd = 0xac4; // AC_ACCEPT_LOGIN3
|
|
||||||
int header = 64;
|
|
||||||
int size = 160;
|
|
||||||
#endif
|
|
||||||
|
|
||||||
if( !global_core->is_running() ){
|
if( !global_core->is_running() ){
|
||||||
// players can only login while running
|
// players can only login while running
|
||||||
logclif_sent_auth_result(fd,1); // server closed
|
logclif_sent_auth_result(fd,1); // server closed
|
||||||
@ -118,33 +111,39 @@ static void logclif_auth_ok(struct login_session_data* sd) {
|
|||||||
login_log(ip, sd->userid, 100, "login ok");
|
login_log(ip, sd->userid, 100, "login ok");
|
||||||
ShowStatus("Connection of the account '%s' accepted.\n", sd->userid);
|
ShowStatus("Connection of the account '%s' accepted.\n", sd->userid);
|
||||||
|
|
||||||
WFIFOHEAD(fd,header+size*server_num);
|
PACKET_AC_ACCEPT_LOGIN* p = (PACKET_AC_ACCEPT_LOGIN*)packet_buffer;
|
||||||
WFIFOW(fd,0) = cmd;
|
|
||||||
WFIFOW(fd,2) = header+size*server_num;
|
p->packetType = HEADER_AC_ACCEPT_LOGIN;
|
||||||
WFIFOL(fd,4) = sd->login_id1;
|
p->packetLength = sizeof( *p );
|
||||||
WFIFOL(fd,8) = sd->account_id;
|
p->login_id1 = sd->login_id1;
|
||||||
WFIFOL(fd,12) = sd->login_id2;
|
p->AID = sd->account_id;
|
||||||
WFIFOL(fd,16) = 0; // in old version, that was for ip (not more used)
|
p->login_id2 = sd->login_id2;
|
||||||
//memcpy(WFIFOP(fd,20), sd->lastlogin, 24); // in old version, that was for name (not more used)
|
// in old version, that was for ip (not more used)
|
||||||
memset(WFIFOP(fd,20), 0, 24);
|
p->last_ip = 0;
|
||||||
WFIFOW(fd,44) = 0; // unknown
|
// in old version, that was for last login time (not more used)
|
||||||
WFIFOB(fd,46) = sex_str2num(sd->sex);
|
safestrncpy( p->last_login, "", sizeof( p->last_login ) );
|
||||||
|
p->sex = sex_str2num( sd->sex );
|
||||||
#if PACKETVER >= 20170315
|
#if PACKETVER >= 20170315
|
||||||
safestrncpy( WFIFOCP( fd, 47 ), sd->web_auth_token, WEB_AUTH_TOKEN_LENGTH ); // web authentication token
|
safestrncpy( p->token, sd->web_auth_token, WEB_AUTH_TOKEN_LENGTH ); // web authentication token
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
for( i = 0, n = 0; i < ARRAYLENGTH(ch_server); ++i ) {
|
for( i = 0, n = 0; i < ARRAYLENGTH(ch_server); ++i ) {
|
||||||
if( !session_isValid(ch_server[i].fd) )
|
if( !session_isValid(ch_server[i].fd) )
|
||||||
continue;
|
continue;
|
||||||
subnet_char_ip = lan_subnetcheck(ip); // Advanced subnet check [LuzZza]
|
subnet_char_ip = lan_subnetcheck(ip); // Advanced subnet check [LuzZza]
|
||||||
WFIFOL(fd,header+n*size) = htonl((subnet_char_ip) ? subnet_char_ip : ch_server[i].ip);
|
|
||||||
WFIFOW(fd,header+n*size+4) = ntows(htons(ch_server[i].port)); // [!] LE byte order here [!]
|
PACKET_AC_ACCEPT_LOGIN_sub& char_server = p->char_servers[n];
|
||||||
memcpy(WFIFOP(fd,header+n*size+6), ch_server[i].name, 20);
|
|
||||||
WFIFOW(fd,header+n*size+26) = login_get_usercount( ch_server[i].users );
|
char_server.ip = htonl( ( subnet_char_ip ) ? subnet_char_ip : ch_server[i].ip );
|
||||||
WFIFOW(fd,header+n*size+28) = ch_server[i].type;
|
char_server.port = ntows( htons( ch_server[i].port ) ); // [!] LE byte order here [!]
|
||||||
WFIFOW(fd,header+n*size+30) = ch_server[i].new_;
|
safestrncpy( char_server.name, ch_server[i].name, sizeof( char_server.name ) );
|
||||||
|
char_server.users = login_get_usercount( ch_server[i].users );
|
||||||
|
char_server.type = ch_server[i].type;
|
||||||
|
char_server.new_ = ch_server[i].new_;
|
||||||
#if PACKETVER >= 20170315
|
#if PACKETVER >= 20170315
|
||||||
memset(WFIFOP(fd, header+n*size+32), 0, 128); // Unknown
|
memset( &char_server.unknown, 0, sizeof( char_server.unknown ) );
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
#ifdef DEBUG
|
#ifdef DEBUG
|
||||||
ShowDebug(
|
ShowDebug(
|
||||||
"Sending the client (%d %d.%d.%d.%d) to char-server %s with ip %d.%d.%d.%d and port "
|
"Sending the client (%d %d.%d.%d.%d) to char-server %s with ip %d.%d.%d.%d and port "
|
||||||
@ -152,9 +151,12 @@ static void logclif_auth_ok(struct login_session_data* sd) {
|
|||||||
sd->account_id, CONVIP(ip), ch_server[i].name,
|
sd->account_id, CONVIP(ip), ch_server[i].name,
|
||||||
CONVIP((subnet_char_ip) ? subnet_char_ip : ch_server[i].ip), ch_server[i].port);
|
CONVIP((subnet_char_ip) ? subnet_char_ip : ch_server[i].ip), ch_server[i].port);
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
n++;
|
n++;
|
||||||
|
p->packetLength += sizeof( char_server );
|
||||||
}
|
}
|
||||||
WFIFOSET(fd,header+size*server_num);
|
|
||||||
|
socket_send( fd, p );
|
||||||
|
|
||||||
// create temporary auth entry
|
// create temporary auth entry
|
||||||
login_add_auth_node( sd, ip );
|
login_add_auth_node( sd, ip );
|
||||||
@ -165,6 +167,16 @@ static void logclif_auth_ok(struct login_session_data* sd) {
|
|||||||
data->waiting_disconnect = add_timer(gettick()+AUTH_TIMEOUT, login_waiting_disconnect_timer, sd->account_id, 0);
|
data->waiting_disconnect = add_timer(gettick()+AUTH_TIMEOUT, login_waiting_disconnect_timer, sd->account_id, 0);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static void logclif_auth_failed( int fd, int result, const char* unblock_time = "" ){
|
||||||
|
PACKET_AC_REFUSE_LOGIN p = {};
|
||||||
|
|
||||||
|
p.packetType = HEADER_AC_REFUSE_LOGIN;
|
||||||
|
p.error = result;
|
||||||
|
safestrncpy( p.unblock_time, "", sizeof( p.unblock_time ) );
|
||||||
|
|
||||||
|
socket_send( fd, p );
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Inform client that auth has failed.
|
* Inform client that auth has failed.
|
||||||
* @param sd: player session
|
* @param sd: player session
|
||||||
@ -210,33 +222,18 @@ static void logclif_auth_failed(struct login_session_data* sd, int result) {
|
|||||||
if( (result == 0 || result == 1) && login_config.dynamic_pass_failure_ban )
|
if( (result == 0 || result == 1) && login_config.dynamic_pass_failure_ban )
|
||||||
ipban_log(ip); // log failed password attempt
|
ipban_log(ip); // log failed password attempt
|
||||||
|
|
||||||
#if PACKETVER >= 20120000 /* not sure when this started */
|
// 6 = You are prohibited to log in until %s
|
||||||
WFIFOHEAD(fd,26);
|
if( result == 6 ){
|
||||||
WFIFOW(fd,0) = 0x83e;
|
char unblock_time[20];
|
||||||
WFIFOL(fd,2) = result;
|
|
||||||
if( result != 6 )
|
|
||||||
memset(WFIFOP(fd,6), '\0', 20);
|
|
||||||
else { // 6 = You are prohibited to log in until %s
|
|
||||||
struct mmo_account acc;
|
struct mmo_account acc;
|
||||||
AccountDB* accounts = login_get_accounts_db();
|
AccountDB* accounts = login_get_accounts_db();
|
||||||
time_t unban_time = ( accounts->load_str(accounts, &acc, sd->userid) ) ? acc.unban_time : 0;
|
time_t unban_time = ( accounts->load_str( accounts, &acc, sd->userid ) ) ? acc.unban_time : 0;
|
||||||
timestamp2string(WFIFOCP(fd,6), 20, unban_time, login_config.date_format);
|
timestamp2string( unblock_time, sizeof( unblock_time ), unban_time, login_config.date_format );
|
||||||
|
|
||||||
|
logclif_auth_failed( fd, result, unblock_time );
|
||||||
|
}else{
|
||||||
|
logclif_auth_failed( fd, result );
|
||||||
}
|
}
|
||||||
WFIFOSET(fd,26);
|
|
||||||
#else
|
|
||||||
WFIFOHEAD(fd,23);
|
|
||||||
WFIFOW(fd,0) = 0x6a;
|
|
||||||
WFIFOB(fd,2) = (uint8)result;
|
|
||||||
if( result != 6 )
|
|
||||||
memset(WFIFOP(fd,3), '\0', 20);
|
|
||||||
else { // 6 = You are prohibited to log in until %s
|
|
||||||
struct mmo_account acc;
|
|
||||||
AccountDB* accounts = login_get_accounts_db();
|
|
||||||
time_t unban_time = ( accounts->load_str(accounts, &acc, sd->userid) ) ? acc.unban_time : 0;
|
|
||||||
timestamp2string(WFIFOCP(fd,3), 20, unban_time, login_config.date_format);
|
|
||||||
}
|
|
||||||
WFIFOSET(fd,23);
|
|
||||||
#endif
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@ -246,9 +243,14 @@ static void logclif_auth_failed(struct login_session_data* sd, int result) {
|
|||||||
* @return 0 not enough info transmitted, 1 success
|
* @return 0 not enough info transmitted, 1 success
|
||||||
*/
|
*/
|
||||||
static int logclif_parse_keepalive(int fd){
|
static int logclif_parse_keepalive(int fd){
|
||||||
if (RFIFOREST(fd) < 26)
|
PACKET_CA_CONNECT_INFO_CHANGED* p = (PACKET_CA_CONNECT_INFO_CHANGED*)RFIFOP( fd, 0 );
|
||||||
|
|
||||||
|
if( RFIFOREST( fd ) < sizeof( *p ) ){
|
||||||
return 0;
|
return 0;
|
||||||
RFIFOSKIP(fd,26);
|
}
|
||||||
|
|
||||||
|
RFIFOSKIP( fd, sizeof( *p ) );
|
||||||
|
|
||||||
return 1;
|
return 1;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -259,112 +261,124 @@ static int logclif_parse_keepalive(int fd){
|
|||||||
* @return 0 not enough info transmitted, 1 success
|
* @return 0 not enough info transmitted, 1 success
|
||||||
*/
|
*/
|
||||||
static int logclif_parse_updclhash(int fd, struct login_session_data *sd){
|
static int logclif_parse_updclhash(int fd, struct login_session_data *sd){
|
||||||
if (RFIFOREST(fd) < 18)
|
PACKET_CA_EXE_HASHCHECK* p = (PACKET_CA_EXE_HASHCHECK*)RFIFOP( fd, 0 );
|
||||||
|
|
||||||
|
if( RFIFOREST( fd ) < sizeof( *p ) ){
|
||||||
return 0;
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
sd->has_client_hash = 1;
|
sd->has_client_hash = 1;
|
||||||
memcpy(sd->client_hash, RFIFOP(fd, 2), 16);
|
memcpy( sd->client_hash, p->hash, sizeof( sd->client_hash ) );
|
||||||
RFIFOSKIP(fd,18);
|
|
||||||
|
RFIFOSKIP( fd, sizeof( *p ) );
|
||||||
|
|
||||||
return 1;
|
return 1;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
template <typename P>
|
||||||
* Received a connection request.
|
int logclif_parse_reqauth_raw( int fd, login_session_data& sd, char* ip ){
|
||||||
* @param fd: file descriptor to parse from (client)
|
P* p = (P*)RFIFOP( fd, 0 );
|
||||||
* @param sd: client session
|
|
||||||
* @param command: packet type sent
|
|
||||||
* @param ip: ipv4 address (client)
|
|
||||||
* S 0064 <version>.L <username>.24B <password>.24B <clienttype>.B
|
|
||||||
* S 0277 <version>.L <username>.24B <password>.24B <clienttype>.B <ip address>.16B <adapter address>.13B
|
|
||||||
* S 02b0 <version>.L <username>.24B <password>.24B <clienttype>.B <ip address>.16B <adapter address>.13B <g_isGravityID>.B
|
|
||||||
* S 01dd <version>.L <username>.24B <password hash>.16B <clienttype>.B
|
|
||||||
* S 01fa <version>.L <username>.24B <password hash>.16B <clienttype>.B <?>.B(index of the connection in the clientinfo file (+10 if the command-line contains "pc"))
|
|
||||||
* S 027c <version>.L <username>.24B <password hash>.16B <clienttype>.B <?>.13B(junk)
|
|
||||||
* S 0825 <packetsize>.W <version>.L <clienttype>.B <userid>.24B <password>.27B <mac>.17B <ip>.15B <token>.(packetsize - 0x5C)B
|
|
||||||
* @param fd: fd to parse from (client fd)
|
|
||||||
* @return 0 failure, 1 success
|
|
||||||
*/
|
|
||||||
static int logclif_parse_reqauth(int fd, struct login_session_data *sd, int command, char* ip){
|
|
||||||
size_t packet_len = RFIFOREST(fd);
|
|
||||||
|
|
||||||
if( (command == 0x0064 && packet_len < 55)
|
if( RFIFOREST( fd ) < sizeof( *p ) ){
|
||||||
|| (command == 0x0277 && packet_len < 84)
|
|
||||||
|| (command == 0x02b0 && packet_len < 85)
|
|
||||||
|| (command == 0x01dd && packet_len < 47)
|
|
||||||
|| (command == 0x01fa && packet_len < 48)
|
|
||||||
|| (command == 0x027c && packet_len < 60)
|
|
||||||
|| (command == 0x0825 && (packet_len < 4 || packet_len < RFIFOW(fd, 2))) )
|
|
||||||
return 0;
|
return 0;
|
||||||
else {
|
|
||||||
int result;
|
|
||||||
char username[NAME_LENGTH];
|
|
||||||
char password[PASSWD_LENGTH];
|
|
||||||
unsigned char passhash[16];
|
|
||||||
uint8 clienttype;
|
|
||||||
bool israwpass = (command==0x0064 || command==0x0277 || command==0x02b0 || command == 0x0825);
|
|
||||||
|
|
||||||
// Shinryo: For the time being, just use token as password.
|
|
||||||
if(command == 0x0825) {
|
|
||||||
char *accname = RFIFOCP(fd, 9);
|
|
||||||
char *token = RFIFOCP(fd, 0x5C);
|
|
||||||
size_t uAccLen = strlen(accname);
|
|
||||||
size_t uTokenLen = RFIFOREST(fd) - 0x5C;
|
|
||||||
|
|
||||||
if(uAccLen > NAME_LENGTH - 1 || uAccLen == 0 || uTokenLen > NAME_LENGTH - 1 || uTokenLen == 0)
|
|
||||||
{
|
|
||||||
logclif_auth_failed(sd, 3);
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
safestrncpy(username, accname, uAccLen + 1);
|
|
||||||
safestrncpy(password, token, uTokenLen + 1);
|
|
||||||
clienttype = RFIFOB(fd, 8);
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
safestrncpy(username, RFIFOCP(fd,6), NAME_LENGTH);
|
|
||||||
if( israwpass )
|
|
||||||
{
|
|
||||||
safestrncpy(password, RFIFOCP(fd,30), PASSWD_LENGTH);
|
|
||||||
clienttype = RFIFOB(fd,54);
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
memcpy(passhash, RFIFOP(fd,30), 16);
|
|
||||||
clienttype = RFIFOB(fd,46);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
RFIFOSKIP(fd,RFIFOREST(fd)); // assume no other packet was sent
|
|
||||||
|
|
||||||
sd->clienttype = clienttype;
|
|
||||||
safestrncpy(sd->userid, username, NAME_LENGTH);
|
|
||||||
if( israwpass )
|
|
||||||
{
|
|
||||||
ShowStatus("Request for connection of %s (ip: %s)\n", sd->userid, ip);
|
|
||||||
safestrncpy(sd->passwd, password, PASSWD_LENGTH);
|
|
||||||
if( login_config.use_md5_passwds )
|
|
||||||
MD5_String(sd->passwd, sd->passwd);
|
|
||||||
sd->passwdenc = 0;
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
ShowStatus("Request for connection (passwdenc mode) of %s (ip: %s)\n", sd->userid, ip);
|
|
||||||
bin2hex(sd->passwd, passhash, 16); // raw binary data here!
|
|
||||||
sd->passwdenc = PASSWORDENC;
|
|
||||||
}
|
|
||||||
|
|
||||||
if( sd->passwdenc != 0 && login_config.use_md5_passwds )
|
|
||||||
{
|
|
||||||
logclif_auth_failed(sd, 3); // send "rejected from server"
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
result = login_mmo_auth(sd, false);
|
|
||||||
|
|
||||||
if( result == -1 )
|
|
||||||
logclif_auth_ok(sd);
|
|
||||||
else
|
|
||||||
logclif_auth_failed(sd, result);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
safestrncpy( sd.userid, p->username, sizeof( sd.userid ) );
|
||||||
|
sd.clienttype = p->clienttype;
|
||||||
|
|
||||||
|
ShowStatus( "Request for connection of %s (ip: %s)\n", sd.userid, ip );
|
||||||
|
safestrncpy( sd.passwd, p->password, PASSWD_LENGTH );
|
||||||
|
|
||||||
|
if( login_config.use_md5_passwds ){
|
||||||
|
MD5_String( sd.passwd, sd.passwd );
|
||||||
|
}
|
||||||
|
|
||||||
|
sd.passwdenc = 0;
|
||||||
|
|
||||||
|
RFIFOSKIP( fd, sizeof( *p ) );
|
||||||
|
|
||||||
|
int result = login_mmo_auth( &sd, false );
|
||||||
|
|
||||||
|
if( result == -1 ){
|
||||||
|
logclif_auth_ok( &sd );
|
||||||
|
}else{
|
||||||
|
logclif_auth_failed( &sd, result );
|
||||||
|
}
|
||||||
|
|
||||||
|
return 1;
|
||||||
|
}
|
||||||
|
|
||||||
|
template <typename P>
|
||||||
|
int logclif_parse_reqauth_md5( int fd, login_session_data& sd, char* ip ){
|
||||||
|
P* p = (P*)RFIFOP( fd, 0 );
|
||||||
|
|
||||||
|
if( RFIFOREST( fd ) < sizeof( *p ) ){
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
safestrncpy( sd.userid, p->username, sizeof( sd.userid ) );
|
||||||
|
sd.clienttype = p->clienttype;
|
||||||
|
|
||||||
|
ShowStatus( "Request for connection (passwdenc mode) of %s (ip: %s)\n", sd.userid, ip );
|
||||||
|
bin2hex( sd.passwd, p->passwordMD5, sizeof( p->passwordMD5 ) ); // raw binary data here!
|
||||||
|
|
||||||
|
sd.passwdenc = PASSWORDENC;
|
||||||
|
|
||||||
|
RFIFOSKIP( fd, sizeof( *p ) );
|
||||||
|
|
||||||
|
if( login_config.use_md5_passwds ){
|
||||||
|
logclif_auth_failed( &sd, 3 ); // send "rejected from server"
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
int result = login_mmo_auth( &sd, false );
|
||||||
|
|
||||||
|
if( result == -1 ){
|
||||||
|
logclif_auth_ok( &sd );
|
||||||
|
}else{
|
||||||
|
logclif_auth_failed( &sd, result );
|
||||||
|
}
|
||||||
|
|
||||||
|
return 1;
|
||||||
|
}
|
||||||
|
|
||||||
|
template <typename P>
|
||||||
|
int logclif_parse_reqauth_sso( int fd, login_session_data& sd, char* ip ){
|
||||||
|
P* p = (P*)RFIFOP( fd, 0 );
|
||||||
|
|
||||||
|
if( RFIFOREST( fd ) < sizeof( *p ) ){
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
if( RFIFOREST( fd ) < p->packetLength ){
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
size_t token_length = p->packetLength - sizeof( *p );
|
||||||
|
|
||||||
|
safestrncpy( sd.userid, p->username, sizeof( sd.userid ) );
|
||||||
|
sd.clienttype = p->clienttype;
|
||||||
|
|
||||||
|
ShowStatus( "Request for connection (SSO mode) of %s (ip: %s)\n", sd.userid, ip );
|
||||||
|
// Shinryo: For the time being, just use token as password.
|
||||||
|
safestrncpy( sd.passwd, p->token, token_length + 1 );
|
||||||
|
|
||||||
|
if( login_config.use_md5_passwds ){
|
||||||
|
MD5_String( sd.passwd, sd.passwd );
|
||||||
|
}
|
||||||
|
|
||||||
|
sd.passwdenc = 0;
|
||||||
|
|
||||||
|
RFIFOSKIP( fd, p->packetLength );
|
||||||
|
|
||||||
|
int result = login_mmo_auth( &sd, false );
|
||||||
|
|
||||||
|
if( result == -1 ){
|
||||||
|
logclif_auth_ok( &sd );
|
||||||
|
}else{
|
||||||
|
logclif_auth_failed( &sd, result );
|
||||||
|
}
|
||||||
|
|
||||||
return 1;
|
return 1;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -375,17 +389,25 @@ static int logclif_parse_reqauth(int fd, struct login_session_data *sd, int comm
|
|||||||
* @return 1 success
|
* @return 1 success
|
||||||
*/
|
*/
|
||||||
static int logclif_parse_reqkey(int fd, struct login_session_data *sd){
|
static int logclif_parse_reqkey(int fd, struct login_session_data *sd){
|
||||||
RFIFOSKIP(fd,2);
|
PACKET_CA_REQ_HASH* p_in = (PACKET_CA_REQ_HASH*)RFIFOP( fd, 0 );
|
||||||
{
|
|
||||||
sd->md5keylen = sizeof( sd->md5key );
|
|
||||||
MD5_Salt(sd->md5keylen, sd->md5key);
|
|
||||||
|
|
||||||
WFIFOHEAD(fd,4 + sd->md5keylen);
|
if( RFIFOREST( fd ) < sizeof( *p_in ) ){
|
||||||
WFIFOW(fd,0) = 0x01dc;
|
return 0;
|
||||||
WFIFOW(fd,2) = 4 + sd->md5keylen;
|
|
||||||
memcpy(WFIFOP(fd,4), sd->md5key, sd->md5keylen);
|
|
||||||
WFIFOSET(fd,WFIFOW(fd,2));
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
RFIFOSKIP( fd, sizeof( *p_in ) );
|
||||||
|
|
||||||
|
sd->md5keylen = sizeof( sd->md5key );
|
||||||
|
MD5_Salt( sd->md5keylen, sd->md5key );
|
||||||
|
|
||||||
|
PACKET_AC_ACK_HASH* p_out = (PACKET_AC_ACK_HASH*)packet_buffer;
|
||||||
|
|
||||||
|
p_out->packetType = HEADER_AC_ACK_HASH;
|
||||||
|
p_out->packetLength = sizeof( *p_out ) + sd->md5keylen;
|
||||||
|
strncpy( p_out->salt, sd->md5key, sd->md5keylen );
|
||||||
|
|
||||||
|
socket_send( fd, p_out );
|
||||||
|
|
||||||
return 1;
|
return 1;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -464,15 +486,23 @@ static int logclif_parse_reqcharconnec(int fd, struct login_session_data *sd, ch
|
|||||||
}
|
}
|
||||||
|
|
||||||
int logclif_parse_otp_login( int fd, struct login_session_data* sd ){
|
int logclif_parse_otp_login( int fd, struct login_session_data* sd ){
|
||||||
RFIFOSKIP( fd, 68 );
|
PACKET_CT_AUTH* p_in = (PACKET_CT_AUTH*)RFIFOP( fd, 0 );
|
||||||
|
|
||||||
WFIFOHEAD( fd, 34 );
|
if( RFIFOREST( fd ) < sizeof( *p_in ) ){
|
||||||
WFIFOW( fd, 0 ) = 0xae3;
|
return 0;
|
||||||
WFIFOW( fd, 2 ) = 34;
|
}
|
||||||
WFIFOL( fd, 4 ) = 0; // normal login
|
|
||||||
safestrncpy( WFIFOCP( fd, 8 ), "S1000", 6 );
|
RFIFOSKIP( fd, sizeof( *p_in ) );
|
||||||
safestrncpy( WFIFOCP( fd, 28 ), "token", 6 );
|
|
||||||
WFIFOSET( fd, 34 );
|
PACKET_TC_RESULT p_out = {};
|
||||||
|
|
||||||
|
p_out.packetType = HEADER_TC_RESULT;
|
||||||
|
p_out.packetLength = sizeof( p_out );
|
||||||
|
p_out.type = 0; // normal login
|
||||||
|
safestrncpy( p_out.unknown1, "S1000", sizeof( p_out.unknown1 ) );
|
||||||
|
safestrncpy( p_out.unknown2, "token", sizeof( p_out.unknown2 ) );
|
||||||
|
|
||||||
|
socket_send( fd, p_out );
|
||||||
|
|
||||||
return 1;
|
return 1;
|
||||||
}
|
}
|
||||||
@ -497,17 +527,15 @@ int logclif_parse(int fd) {
|
|||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
if( sd == NULL )
|
if( sd == nullptr ){
|
||||||
{
|
|
||||||
// Perform ip-ban check
|
// Perform ip-ban check
|
||||||
if( login_config.ipban && ipban_check(ipl) )
|
if( login_config.ipban && ipban_check(ipl) )
|
||||||
{
|
{
|
||||||
ShowStatus("Connection refused: IP isn't authorised (deny/allow, ip: %s).\n", ip);
|
ShowStatus("Connection refused: IP isn't authorised (deny/allow, ip: %s).\n", ip);
|
||||||
login_log(ipl, "unknown", -3, "ip banned");
|
login_log(ipl, "unknown", -3, "ip banned");
|
||||||
WFIFOHEAD(fd,23);
|
|
||||||
WFIFOW(fd,0) = 0x6a;
|
logclif_auth_failed( fd, 3 ); // 3 = Rejected from Server
|
||||||
WFIFOB(fd,2) = 3; // 3 = Rejected from Server
|
|
||||||
WFIFOSET(fd,23);
|
|
||||||
set_eof(fd);
|
set_eof(fd);
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
@ -522,35 +550,59 @@ int logclif_parse(int fd) {
|
|||||||
uint16 command = RFIFOW(fd,0);
|
uint16 command = RFIFOW(fd,0);
|
||||||
int next=1;
|
int next=1;
|
||||||
|
|
||||||
switch( command )
|
switch( command ){
|
||||||
{
|
// New alive packet: used to verify if client is always alive.
|
||||||
// New alive packet: used to verify if client is always alive.
|
case HEADER_CA_CONNECT_INFO_CHANGED:
|
||||||
case 0x0200: next = logclif_parse_keepalive(fd); break;
|
next = logclif_parse_keepalive( fd );
|
||||||
// client md5 hash (binary)
|
break;
|
||||||
case 0x0204: next = logclif_parse_updclhash(fd,sd); break;
|
// client md5 hash (binary)
|
||||||
// request client login (raw password)
|
case HEADER_CA_EXE_HASHCHECK:
|
||||||
case 0x0064: // S 0064 <version>.L <username>.24B <password>.24B <clienttype>.B
|
next = logclif_parse_updclhash( fd, sd );
|
||||||
case 0x0277: // S 0277 <version>.L <username>.24B <password>.24B <clienttype>.B <ip address>.16B <adapter address>.13B
|
break;
|
||||||
case 0x02b0: // S 02b0 <version>.L <username>.24B <password>.24B <clienttype>.B <ip address>.16B <adapter address>.13B <g_isGravityID>.B
|
// request client login (raw password)
|
||||||
// request client login (md5-hashed password)
|
case HEADER_CA_LOGIN:
|
||||||
case 0x01dd: // S 01dd <version>.L <username>.24B <password hash>.16B <clienttype>.B
|
// S 0064 <version>.L <username>.24B <password>.24B <clienttype>.B
|
||||||
case 0x01fa: // S 01fa <version>.L <username>.24B <password hash>.16B <clienttype>.B <?>.B(index of the connection in the clientinfo file (+10 if the command-line contains "pc"))
|
next = logclif_parse_reqauth_raw<PACKET_CA_LOGIN>( fd, *sd, ip );
|
||||||
case 0x027c: // S 027c <version>.L <username>.24B <password hash>.16B <clienttype>.B <?>.13B(junk)
|
break;
|
||||||
case 0x0825: // S 0825 <packetsize>.W <version>.L <clienttype>.B <userid>.24B <password>.27B <mac>.17B <ip>.15B <token>.(packetsize - 0x5C)B
|
case HEADER_CA_LOGIN_PCBANG:
|
||||||
next = logclif_parse_reqauth(fd, sd, command, ip);
|
// S 0277 <version>.L <username>.24B <password>.24B <clienttype>.B <ip address>.16B <adapter address>.13B
|
||||||
break;
|
next = logclif_parse_reqauth_raw<PACKET_CA_LOGIN_PCBANG>( fd, *sd, ip );
|
||||||
// Sending request of the coding key
|
break;
|
||||||
case 0x01db: next = logclif_parse_reqkey(fd, sd); break;
|
case HEADER_CA_LOGIN_CHANNEL:
|
||||||
// OTP token login
|
// S 02b0 <version>.L <username>.24B <password>.24B <clienttype>.B <ip address>.16B <adapter address>.13B <g_isGravityID>.B
|
||||||
case 0x0acf:
|
next = logclif_parse_reqauth_raw<PACKET_CA_LOGIN_CHANNEL>( fd, *sd, ip );
|
||||||
next = logclif_parse_otp_login( fd, sd );
|
break;
|
||||||
break;
|
// request client login (md5-hashed password)
|
||||||
// Connection request of a char-server
|
case HEADER_CA_LOGIN2:
|
||||||
case 0x2710: logclif_parse_reqcharconnec(fd,sd, ip); return 0; // processing will continue elsewhere
|
// S 01dd <version>.L <username>.24B <password hash>.16B <clienttype>.B
|
||||||
default:
|
next = logclif_parse_reqauth_md5<PACKET_CA_LOGIN2>( fd, *sd, ip );
|
||||||
ShowNotice("Abnormal end of connection (ip: %s): Unknown packet 0x%x\n", ip, command);
|
break;
|
||||||
set_eof(fd);
|
case HEADER_CA_LOGIN3:
|
||||||
return 0;
|
// S 01fa <version>.L <username>.24B <password hash>.16B <clienttype>.B <?>.B(index of the connection in the clientinfo file (+10 if the command-line contains "pc"))
|
||||||
|
next = logclif_parse_reqauth_md5<PACKET_CA_LOGIN3>( fd, *sd, ip );
|
||||||
|
break;
|
||||||
|
case HEADER_CA_LOGIN4:
|
||||||
|
// S 027c <version>.L <username>.24B <password hash>.16B <clienttype>.B <adapter address>.13B
|
||||||
|
next = logclif_parse_reqauth_md5<PACKET_CA_LOGIN4>( fd, *sd, ip );
|
||||||
|
break;
|
||||||
|
case HEADER_CA_SSO_LOGIN_REQ:
|
||||||
|
// S 0825 <packetsize>.W <version>.L <clienttype>.B <userid>.24B <password>.27B <mac>.17B <ip>.15B <token>.?B
|
||||||
|
next = logclif_parse_reqauth_sso<PACKET_CA_SSO_LOGIN_REQ>( fd, *sd, ip );
|
||||||
|
break;
|
||||||
|
// Sending request of the coding key
|
||||||
|
case HEADER_CA_REQ_HASH:
|
||||||
|
next = logclif_parse_reqkey( fd, sd );
|
||||||
|
break;
|
||||||
|
// OTP token login
|
||||||
|
case HEADER_CT_AUTH:
|
||||||
|
next = logclif_parse_otp_login( fd, sd );
|
||||||
|
break;
|
||||||
|
// Connection request of a char-server
|
||||||
|
case 0x2710: logclif_parse_reqcharconnec(fd,sd, ip); return 0; // processing will continue elsewhere
|
||||||
|
default:
|
||||||
|
ShowNotice("Abnormal end of connection (ip: %s): Unknown packet 0x%x\n", ip, command);
|
||||||
|
set_eof(fd);
|
||||||
|
return 0;
|
||||||
}
|
}
|
||||||
if(next==0) return 0; // avoid processing of followup packets (prev was probably incomplete)
|
if(next==0) return 0; // avoid processing of followup packets (prev was probably incomplete)
|
||||||
}
|
}
|
||||||
|
|||||||
@ -3,8 +3,9 @@
|
|||||||
|
|
||||||
#include "loginlog.hpp"
|
#include "loginlog.hpp"
|
||||||
|
|
||||||
|
#include <string>
|
||||||
|
|
||||||
#include <stdlib.h> // exit
|
#include <stdlib.h> // exit
|
||||||
#include <string.h>
|
|
||||||
|
|
||||||
#include <common/cbasetypes.hpp>
|
#include <common/cbasetypes.hpp>
|
||||||
#include <common/mmo.hpp>
|
#include <common/mmo.hpp>
|
||||||
@ -13,21 +14,14 @@
|
|||||||
#include <common/sql.hpp>
|
#include <common/sql.hpp>
|
||||||
#include <common/strlib.hpp>
|
#include <common/strlib.hpp>
|
||||||
|
|
||||||
// global sql settings (in ipban_sql.cpp)
|
|
||||||
static char global_db_hostname[64] = "127.0.0.1"; // Doubled to reflect the change on commit #0f2dd7f
|
std::string log_db_hostname = "127.0.0.1";
|
||||||
static uint16 global_db_port = 3306;
|
uint16 log_db_port = 3306;
|
||||||
static char global_db_username[32] = "ragnarok";
|
std::string log_db_username = "ragnarok";
|
||||||
static char global_db_password[32] = ""; //empty by default since mysql is empty by default as well
|
std::string log_db_password = "";
|
||||||
static char global_db_database[32] = "ragnarok";
|
std::string log_db_database = "ragnarok";
|
||||||
static char global_codepage[32] = "";
|
std::string log_login_db = "loginlog";
|
||||||
// local sql settings
|
std::string log_codepage = "";
|
||||||
static char log_db_hostname[64] = ""; // Doubled to reflect the change on commit #0f2dd7f
|
|
||||||
static uint16 log_db_port = 0;
|
|
||||||
static char log_db_username[32] = "";
|
|
||||||
static char log_db_password[32] = "";
|
|
||||||
static char log_db_database[32] = "";
|
|
||||||
static char log_codepage[32] = "";
|
|
||||||
static char log_login_db[256] = "loginlog";
|
|
||||||
|
|
||||||
static Sql* sql_handle = NULL;
|
static Sql* sql_handle = NULL;
|
||||||
static bool enabled = false;
|
static bool enabled = false;
|
||||||
@ -46,7 +40,7 @@ unsigned long loginlog_failedattempts(uint32 ip, unsigned int minutes) {
|
|||||||
return 0;
|
return 0;
|
||||||
|
|
||||||
if( SQL_ERROR == Sql_Query(sql_handle, "SELECT count(*) FROM `%s` WHERE `ip` = '%s' AND (`rcode` = '0' OR `rcode` = '1') AND `time` > NOW() - INTERVAL %d MINUTE",
|
if( SQL_ERROR == Sql_Query(sql_handle, "SELECT count(*) FROM `%s` WHERE `ip` = '%s' AND (`rcode` = '0' OR `rcode` = '1') AND `time` > NOW() - INTERVAL %d MINUTE",
|
||||||
log_login_db, ip2str(ip,NULL), minutes) )// how many times failed account? in one ip.
|
log_login_db.c_str(), ip2str(ip,NULL), minutes) )// how many times failed account? in one ip.
|
||||||
Sql_ShowDebug(sql_handle);
|
Sql_ShowDebug(sql_handle);
|
||||||
|
|
||||||
if( SQL_SUCCESS == Sql_NextRow(sql_handle) )
|
if( SQL_SUCCESS == Sql_NextRow(sql_handle) )
|
||||||
@ -80,7 +74,7 @@ void login_log(uint32 ip, const char* username, int rcode, const char* message)
|
|||||||
|
|
||||||
retcode = Sql_Query(sql_handle,
|
retcode = Sql_Query(sql_handle,
|
||||||
"INSERT INTO `%s`(`time`,`ip`,`user`,`rcode`,`log`) VALUES (NOW(), '%s', '%s', '%d', '%s')",
|
"INSERT INTO `%s`(`time`,`ip`,`user`,`rcode`,`log`) VALUES (NOW(), '%s', '%s', '%d', '%s')",
|
||||||
log_login_db, ip2str(ip,NULL), esc_username, rcode, esc_message);
|
log_login_db.c_str(), ip2str(ip,NULL), esc_username, rcode, esc_message);
|
||||||
|
|
||||||
if( retcode != SQL_SUCCESS )
|
if( retcode != SQL_SUCCESS )
|
||||||
Sql_ShowDebug(sql_handle);
|
Sql_ShowDebug(sql_handle);
|
||||||
@ -93,54 +87,26 @@ void login_log(uint32 ip, const char* username, int rcode, const char* message)
|
|||||||
* @return true if successful, false if config not complete or server already running
|
* @return true if successful, false if config not complete or server already running
|
||||||
*/
|
*/
|
||||||
bool loginlog_config_read(const char* key, const char* value) {
|
bool loginlog_config_read(const char* key, const char* value) {
|
||||||
const char* signature;
|
|
||||||
|
|
||||||
signature = "sql.";
|
|
||||||
if( strncmpi(key, signature, strlen(signature)) == 0 )
|
|
||||||
{
|
|
||||||
key += strlen(signature);
|
|
||||||
if( strcmpi(key, "db_hostname") == 0 )
|
|
||||||
safestrncpy(global_db_hostname, value, sizeof(global_db_hostname));
|
|
||||||
else
|
|
||||||
if( strcmpi(key, "db_port") == 0 )
|
|
||||||
global_db_port = (uint16)strtoul(value, NULL, 10);
|
|
||||||
else
|
|
||||||
if( strcmpi(key, "db_username") == 0 )
|
|
||||||
safestrncpy(global_db_username, value, sizeof(global_db_username));
|
|
||||||
else
|
|
||||||
if( strcmpi(key, "db_password") == 0 )
|
|
||||||
safestrncpy(global_db_password, value, sizeof(global_db_password));
|
|
||||||
else
|
|
||||||
if( strcmpi(key, "db_database") == 0 )
|
|
||||||
safestrncpy(global_db_database, value, sizeof(global_db_database));
|
|
||||||
else
|
|
||||||
if( strcmpi(key, "codepage") == 0 )
|
|
||||||
safestrncpy(global_codepage, value, sizeof(global_codepage));
|
|
||||||
else
|
|
||||||
return false;// not found
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
|
|
||||||
if( strcmpi(key, "log_db_ip") == 0 )
|
if( strcmpi(key, "log_db_ip") == 0 )
|
||||||
safestrncpy(log_db_hostname, value, sizeof(log_db_hostname));
|
log_db_hostname = value;
|
||||||
else
|
else
|
||||||
if( strcmpi(key, "log_db_port") == 0 )
|
if( strcmpi(key, "log_db_port") == 0 )
|
||||||
log_db_port = (uint16)strtoul(value, NULL, 10);
|
log_db_port = (uint16)strtoul(value, NULL, 10);
|
||||||
else
|
else
|
||||||
if( strcmpi(key, "log_db_id") == 0 )
|
if( strcmpi(key, "log_db_id") == 0 )
|
||||||
safestrncpy(log_db_username, value, sizeof(log_db_username));
|
log_db_username = value;
|
||||||
else
|
else
|
||||||
if( strcmpi(key, "log_db_pw") == 0 )
|
if( strcmpi(key, "log_db_pw") == 0 )
|
||||||
safestrncpy(log_db_password, value, sizeof(log_db_password));
|
log_db_password = value;
|
||||||
else
|
else
|
||||||
if( strcmpi(key, "log_db_db") == 0 )
|
if( strcmpi(key, "log_db_db") == 0 )
|
||||||
safestrncpy(log_db_database, value, sizeof(log_db_database));
|
log_db_database = value;
|
||||||
else
|
else
|
||||||
if( strcmpi(key, "log_codepage") == 0 )
|
if( strcmpi(key, "log_codepage") == 0 )
|
||||||
safestrncpy(log_codepage, value, sizeof(log_codepage));
|
log_codepage = value;
|
||||||
else
|
else
|
||||||
if( strcmpi(key, "log_login_db") == 0 )
|
if( strcmpi(key, "log_login_db") == 0 )
|
||||||
safestrncpy(log_login_db, value, sizeof(log_login_db));
|
log_login_db = value;
|
||||||
else
|
else
|
||||||
return false;
|
return false;
|
||||||
|
|
||||||
@ -156,44 +122,18 @@ bool loginlog_config_read(const char* key, const char* value) {
|
|||||||
* @return true if success else exit execution
|
* @return true if success else exit execution
|
||||||
*/
|
*/
|
||||||
bool loginlog_init(void) {
|
bool loginlog_init(void) {
|
||||||
const char* username;
|
|
||||||
const char* password;
|
|
||||||
const char* hostname;
|
|
||||||
uint16 port;
|
|
||||||
const char* database;
|
|
||||||
const char* codepage;
|
|
||||||
|
|
||||||
if( log_db_hostname[0] != '\0' )
|
|
||||||
{// local settings
|
|
||||||
username = log_db_username;
|
|
||||||
password = log_db_password;
|
|
||||||
hostname = log_db_hostname;
|
|
||||||
port = log_db_port;
|
|
||||||
database = log_db_database;
|
|
||||||
codepage = log_codepage;
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{// global settings
|
|
||||||
username = global_db_username;
|
|
||||||
password = global_db_password;
|
|
||||||
hostname = global_db_hostname;
|
|
||||||
port = global_db_port;
|
|
||||||
database = global_db_database;
|
|
||||||
codepage = global_codepage;
|
|
||||||
}
|
|
||||||
|
|
||||||
sql_handle = Sql_Malloc();
|
sql_handle = Sql_Malloc();
|
||||||
|
|
||||||
if( SQL_ERROR == Sql_Connect(sql_handle, username, password, hostname, port, database) )
|
if( SQL_ERROR == Sql_Connect(sql_handle, log_db_username.c_str(), log_db_password.c_str(), log_db_hostname.c_str(), log_db_port, log_db_database.c_str()) )
|
||||||
{
|
{
|
||||||
ShowError("Couldn't connect with uname='%s',passwd='%s',host='%s',port='%d',database='%s'\n",
|
ShowError("Couldn't connect with uname='%s',host='%s',port='%hu',database='%s'\n",
|
||||||
username, password, hostname, port, database);
|
log_db_username.c_str(), log_db_hostname.c_str(), log_db_port, log_db_database.c_str());
|
||||||
Sql_ShowDebug(sql_handle);
|
Sql_ShowDebug(sql_handle);
|
||||||
Sql_Free(sql_handle);
|
Sql_Free(sql_handle);
|
||||||
exit(EXIT_FAILURE);
|
exit(EXIT_FAILURE);
|
||||||
}
|
}
|
||||||
|
|
||||||
if( codepage[0] != '\0' && SQL_ERROR == Sql_SetEncoding(sql_handle, codepage) )
|
if( !log_codepage.empty() && SQL_ERROR == Sql_SetEncoding(sql_handle, log_codepage.c_str()) )
|
||||||
Sql_ShowDebug(sql_handle);
|
Sql_ShowDebug(sql_handle);
|
||||||
|
|
||||||
enabled = true;
|
enabled = true;
|
||||||
|
|||||||
@ -580,6 +580,12 @@ int64 battle_attr_fix(struct block_list *src, struct block_list *target, int64 d
|
|||||||
ratio += 50;
|
ratio += 50;
|
||||||
#else
|
#else
|
||||||
damage += (int64)(damage * 50 / 100);
|
damage += (int64)(damage * 50 / 100);
|
||||||
|
#endif
|
||||||
|
if (tsc->getSCE(SC_MISTYFROST))
|
||||||
|
#ifdef RENEWAL
|
||||||
|
ratio += 15;
|
||||||
|
#else
|
||||||
|
damage += (int64)(damage * 15 / 100);
|
||||||
#endif
|
#endif
|
||||||
break;
|
break;
|
||||||
case ELE_EARTH:
|
case ELE_EARTH:
|
||||||
@ -1377,7 +1383,7 @@ bool battle_status_block_damage(struct block_list *src, struct block_list *targe
|
|||||||
unit_set_walkdelay(target, gettick(), delay, 1);
|
unit_set_walkdelay(target, gettick(), delay, 1);
|
||||||
#ifdef RENEWAL
|
#ifdef RENEWAL
|
||||||
if (sc->getSCE(SC_SHRINK))
|
if (sc->getSCE(SC_SHRINK))
|
||||||
sc_start(src, target, SC_STUN, 50, skill_lv, skill_get_time2(skill_id, skill_lv));
|
sc_start(target, src, SC_STUN, 50, skill_lv, skill_get_time2(skill_id, skill_lv));
|
||||||
#else
|
#else
|
||||||
if (sc->getSCE(SC_SHRINK) && rnd() % 100 < 5 * sce->val1)
|
if (sc->getSCE(SC_SHRINK) && rnd() % 100 < 5 * sce->val1)
|
||||||
skill_blown(target, src, skill_get_blewcount(CR_SHRINK, 1), -1, BLOWN_NONE);
|
skill_blown(target, src, skill_get_blewcount(CR_SHRINK, 1), -1, BLOWN_NONE);
|
||||||
@ -1569,6 +1575,11 @@ int64 battle_calc_damage(struct block_list *src,struct block_list *bl,struct Dam
|
|||||||
damage *= 4;
|
damage *= 4;
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
if (tsc->getSCE(SC_GROUNDGRAVITY) && flag&(BF_MAGIC|BF_WEAPON))
|
||||||
|
damage += damage * 15 / 100;
|
||||||
|
if (tsc->getSCE(SC_SHIELDCHAINRUSH))
|
||||||
|
damage += damage / 10;
|
||||||
|
|
||||||
if (tsc->getSCE(SC_AETERNA) && skill_id != PF_SOULBURN) {
|
if (tsc->getSCE(SC_AETERNA) && skill_id != PF_SOULBURN) {
|
||||||
if (src->type != BL_MER || !skill_id)
|
if (src->type != BL_MER || !skill_id)
|
||||||
damage *= 2; // Lex Aeterna only doubles damage of regular attacks from mercenaries
|
damage *= 2; // Lex Aeterna only doubles damage of regular attacks from mercenaries
|
||||||
@ -1605,6 +1616,7 @@ int64 battle_calc_damage(struct block_list *src,struct block_list *bl,struct Dam
|
|||||||
case W_WHIP:
|
case W_WHIP:
|
||||||
if(!tsd->state.arrow_atk)
|
if(!tsd->state.arrow_atk)
|
||||||
break;
|
break;
|
||||||
|
[[fallthrough]];
|
||||||
case W_BOW:
|
case W_BOW:
|
||||||
case W_REVOLVER:
|
case W_REVOLVER:
|
||||||
case W_RIFLE:
|
case W_RIFLE:
|
||||||
@ -1830,6 +1842,36 @@ int64 battle_calc_damage(struct block_list *src,struct block_list *bl,struct Dam
|
|||||||
status_change* sc = status_get_sc(src);
|
status_change* sc = status_get_sc(src);
|
||||||
|
|
||||||
if (sc && sc->count) {
|
if (sc && sc->count) {
|
||||||
|
if (sc->getSCE(SC_BREAKINGLIMIT)) {
|
||||||
|
switch (skill_id) {
|
||||||
|
case HN_SHIELD_CHAIN_RUSH:
|
||||||
|
case HN_DOUBLEBOWLINGBASH:
|
||||||
|
damage += damage * 70 / 100;
|
||||||
|
break;
|
||||||
|
case HN_MEGA_SONIC_BLOW:
|
||||||
|
case HN_SPIRAL_PIERCE_MAX:
|
||||||
|
damage *= 2;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if (sc->getSCE(SC_RULEBREAK)) {
|
||||||
|
switch (skill_id) {
|
||||||
|
case HN_METEOR_STORM_BUSTER:
|
||||||
|
case HN_GROUND_GRAVITATION:
|
||||||
|
damage += damage / 2;
|
||||||
|
break;
|
||||||
|
case HN_JUPITEL_THUNDER_STORM:
|
||||||
|
case HN_JACK_FROST_NOVA:
|
||||||
|
case HN_HELLS_DRIVE:
|
||||||
|
damage += damage * 70 / 100;
|
||||||
|
break;
|
||||||
|
case HN_NAPALM_VULCAN_STRIKE:
|
||||||
|
damage += damage * 40 / 100;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
if( sc->getSCE(SC_INVINCIBLE) && !sc->getSCE(SC_INVINCIBLEOFF) )
|
if( sc->getSCE(SC_INVINCIBLE) && !sc->getSCE(SC_INVINCIBLEOFF) )
|
||||||
damage += damage * 75 / 100;
|
damage += damage * 75 / 100;
|
||||||
|
|
||||||
@ -2263,7 +2305,7 @@ int64 battle_addmastery(map_session_data *sd,struct block_list *target,int64 dmg
|
|||||||
case W_FIST:
|
case W_FIST:
|
||||||
if((skill = pc_checkskill(sd,TK_RUN)) > 0)
|
if((skill = pc_checkskill(sd,TK_RUN)) > 0)
|
||||||
damage += (skill * 10);
|
damage += (skill * 10);
|
||||||
// No break, fallthrough to Knuckles
|
[[fallthrough]];
|
||||||
case W_KNUCKLE:
|
case W_KNUCKLE:
|
||||||
if((skill = pc_checkskill(sd,MO_IRONHAND)) > 0)
|
if((skill = pc_checkskill(sd,MO_IRONHAND)) > 0)
|
||||||
damage += (skill * 3);
|
damage += (skill * 3);
|
||||||
@ -2924,6 +2966,7 @@ static bool is_attack_critical(struct Damage* wd, struct block_list *src, struct
|
|||||||
break;
|
break;
|
||||||
clif_specialeffect(src, EF_AUTOCOUNTER, AREA);
|
clif_specialeffect(src, EF_AUTOCOUNTER, AREA);
|
||||||
status_change_end(src, SC_AUTOCOUNTER);
|
status_change_end(src, SC_AUTOCOUNTER);
|
||||||
|
[[fallthrough]];
|
||||||
case KN_AUTOCOUNTER:
|
case KN_AUTOCOUNTER:
|
||||||
if(battle_config.auto_counter_type &&
|
if(battle_config.auto_counter_type &&
|
||||||
(battle_config.auto_counter_type&src->type))
|
(battle_config.auto_counter_type&src->type))
|
||||||
@ -3238,7 +3281,11 @@ static bool attack_ignores_def(struct Damage* wd, struct block_list *src, struct
|
|||||||
#endif
|
#endif
|
||||||
if (sc && sc->getSCE(SC_FUSION))
|
if (sc && sc->getSCE(SC_FUSION))
|
||||||
return true;
|
return true;
|
||||||
else if (skill_id != CR_GRANDCROSS && skill_id != NPC_GRANDDARKNESS)
|
|
||||||
|
if (skill_id == RK_WINDCUTTER && sd && sd->status.weapon == W_2HSWORD)
|
||||||
|
return true;
|
||||||
|
|
||||||
|
if (skill_id != CR_GRANDCROSS && skill_id != NPC_GRANDDARKNESS)
|
||||||
{ //Ignore Defense?
|
{ //Ignore Defense?
|
||||||
if (sd && (sd->right_weapon.ignore_def_ele & (1<<tstatus->def_ele) || sd->right_weapon.ignore_def_ele & (1<<ELE_ALL) ||
|
if (sd && (sd->right_weapon.ignore_def_ele & (1<<tstatus->def_ele) || sd->right_weapon.ignore_def_ele & (1<<ELE_ALL) ||
|
||||||
sd->right_weapon.ignore_def_race & (1<<tstatus->race) || sd->right_weapon.ignore_def_race & (1<<RC_ALL) ||
|
sd->right_weapon.ignore_def_race & (1<<tstatus->race) || sd->right_weapon.ignore_def_race & (1<<RC_ALL) ||
|
||||||
@ -3256,8 +3303,7 @@ static bool attack_ignores_def(struct Damage* wd, struct block_list *src, struct
|
|||||||
} else if (weapon_position == EQI_HAND_L)
|
} else if (weapon_position == EQI_HAND_L)
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
} else if (skill_id == RK_WINDCUTTER && sd && sd->status.weapon == W_2HSWORD)
|
}
|
||||||
return true;
|
|
||||||
|
|
||||||
return nk[NK_IGNOREDEFENSE] != 0;
|
return nk[NK_IGNOREDEFENSE] != 0;
|
||||||
}
|
}
|
||||||
@ -4036,11 +4082,30 @@ static void battle_calc_multi_attack(struct Damage* wd, struct block_list *src,s
|
|||||||
{
|
{
|
||||||
int chance = rnd()%100;
|
int chance = rnd()%100;
|
||||||
switch(sc->getSCE(SC_FEARBREEZE)->val1) {
|
switch(sc->getSCE(SC_FEARBREEZE)->val1) {
|
||||||
case 5: if( chance < 4) { wd->div_ = 5; break; } // 3 % chance to attack 5 times.
|
case 5:
|
||||||
case 4: if( chance < 7) { wd->div_ = 4; break; } // 6 % chance to attack 4 times.
|
if (chance < 4) {
|
||||||
case 3: if( chance < 10) { wd->div_ = 3; break; } // 9 % chance to attack 3 times.
|
wd->div_ = 5;
|
||||||
|
break;
|
||||||
|
} // 3 % chance to attack 5 times.
|
||||||
|
[[fallthrough]];
|
||||||
|
case 4:
|
||||||
|
if (chance < 7) {
|
||||||
|
wd->div_ = 4;
|
||||||
|
break;
|
||||||
|
} // 6 % chance to attack 4 times.
|
||||||
|
[[fallthrough]];
|
||||||
|
case 3:
|
||||||
|
if (chance < 10) {
|
||||||
|
wd->div_ = 3;
|
||||||
|
break;
|
||||||
|
} // 9 % chance to attack 3 times.
|
||||||
|
[[fallthrough]];
|
||||||
case 2:
|
case 2:
|
||||||
case 1: if( chance < 13) { wd->div_ = 2; break; } // 12 % chance to attack 2 times.
|
case 1:
|
||||||
|
if (chance < 13) {
|
||||||
|
wd->div_ = 2;
|
||||||
|
break;
|
||||||
|
} // 12 % chance to attack 2 times.
|
||||||
}
|
}
|
||||||
wd->div_ = min(wd->div_,sd->inventory.u.items_inventory[i].amount);
|
wd->div_ = min(wd->div_,sd->inventory.u.items_inventory[i].amount);
|
||||||
sc->getSCE(SC_FEARBREEZE)->val4 = wd->div_-1;
|
sc->getSCE(SC_FEARBREEZE)->val4 = wd->div_-1;
|
||||||
@ -4491,7 +4556,7 @@ static int battle_calc_attack_skill_ratio(struct Damage* wd, struct block_list *
|
|||||||
skillratio += 100 + 50 * skill_lv;
|
skillratio += 100 + 50 * skill_lv;
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
// Fall through
|
[[fallthrough]];
|
||||||
case MA_SHARPSHOOTING:
|
case MA_SHARPSHOOTING:
|
||||||
#ifdef RENEWAL
|
#ifdef RENEWAL
|
||||||
skillratio += -100 + 300 + 300 * skill_lv;
|
skillratio += -100 + 300 + 300 * skill_lv;
|
||||||
@ -5380,7 +5445,7 @@ static int battle_calc_attack_skill_ratio(struct Damage* wd, struct block_list *
|
|||||||
break;
|
break;
|
||||||
case DK_HACKANDSLASHER:
|
case DK_HACKANDSLASHER:
|
||||||
case DK_HACKANDSLASHER_ATK:
|
case DK_HACKANDSLASHER_ATK:
|
||||||
skillratio += -100 + 300 + 700 * skill_lv;
|
skillratio += -100 + 200 + 750 * skill_lv;
|
||||||
skillratio += 7 * sstatus->pow;
|
skillratio += 7 * sstatus->pow;
|
||||||
RE_LVL_DMOD(100);
|
RE_LVL_DMOD(100);
|
||||||
break;
|
break;
|
||||||
@ -5391,7 +5456,7 @@ static int battle_calc_attack_skill_ratio(struct Damage* wd, struct block_list *
|
|||||||
RE_LVL_DMOD(100);
|
RE_LVL_DMOD(100);
|
||||||
break;
|
break;
|
||||||
case DK_MADNESS_CRUSHER:
|
case DK_MADNESS_CRUSHER:
|
||||||
skillratio += -100 + 400 + 800 * skill_lv + 7 * sstatus->pow;
|
skillratio += -100 + 350 + 1600 * skill_lv + 10 * sstatus->pow;
|
||||||
if( sd != nullptr ){
|
if( sd != nullptr ){
|
||||||
int16 index = sd->equip_index[EQI_HAND_R];
|
int16 index = sd->equip_index[EQI_HAND_R];
|
||||||
|
|
||||||
@ -5404,9 +5469,9 @@ static int battle_calc_attack_skill_ratio(struct Damage* wd, struct block_list *
|
|||||||
skillratio *= 2;
|
skillratio *= 2;
|
||||||
break;
|
break;
|
||||||
case DK_STORMSLASH:
|
case DK_STORMSLASH:
|
||||||
skillratio += -100 + 100 + 170 * skill_lv + 5 * sstatus->pow;
|
skillratio += -100 + 200 + 400 * skill_lv + 5 * sstatus->pow;
|
||||||
RE_LVL_DMOD(100);
|
RE_LVL_DMOD(100);
|
||||||
if (sc && sc->getSCE(SC_GIANTGROWTH) && rnd()%100 < 30)
|
if (sc && sc->getSCE(SC_GIANTGROWTH) && rnd_chance(60, 100))
|
||||||
skillratio *= 2;
|
skillratio *= 2;
|
||||||
break;
|
break;
|
||||||
case DK_DRAGONIC_BREATH:
|
case DK_DRAGONIC_BREATH:
|
||||||
@ -5423,16 +5488,16 @@ static int battle_calc_attack_skill_ratio(struct Damage* wd, struct block_list *
|
|||||||
RE_LVL_DMOD(100);
|
RE_LVL_DMOD(100);
|
||||||
break;
|
break;
|
||||||
case IQ_MASSIVE_F_BLASTER:
|
case IQ_MASSIVE_F_BLASTER:
|
||||||
skillratio += -100 + 2150 * skill_lv + 15 * sstatus->pow;
|
skillratio += -100 + 2300 * skill_lv + 15 * sstatus->pow;
|
||||||
if (tstatus->race == RC_BRUTE || tstatus->race == RC_DEMON)
|
if (tstatus->race == RC_BRUTE || tstatus->race == RC_DEMON)
|
||||||
skillratio += 150 * skill_lv;
|
skillratio += 150 * skill_lv;
|
||||||
RE_LVL_DMOD(100);
|
RE_LVL_DMOD(100);
|
||||||
break;
|
break;
|
||||||
case IQ_EXPOSION_BLASTER:
|
case IQ_EXPOSION_BLASTER:
|
||||||
skillratio += -100 + 2800 * skill_lv + 15 * sstatus->pow;
|
skillratio += -100 + 2400 * skill_lv + 10 * sstatus->pow;
|
||||||
|
|
||||||
if( tsc != nullptr && tsc->getSCE( SC_HOLY_OIL ) ){
|
if( tsc != nullptr && tsc->getSCE( SC_HOLY_OIL ) ){
|
||||||
skillratio += 400 * skill_lv;
|
skillratio += 350 + 1050 * skill_lv;
|
||||||
}
|
}
|
||||||
|
|
||||||
RE_LVL_DMOD(100);
|
RE_LVL_DMOD(100);
|
||||||
@ -5475,20 +5540,23 @@ static int battle_calc_attack_skill_ratio(struct Damage* wd, struct block_list *
|
|||||||
skillratio += skillratio * i / 100;
|
skillratio += skillratio * i / 100;
|
||||||
break;
|
break;
|
||||||
case IG_SHIELD_SHOOTING:
|
case IG_SHIELD_SHOOTING:
|
||||||
skillratio += -100 + 1400 + 2100 * skill_lv + 5 * sstatus->pow;
|
skillratio += -100 + 650 + 2850 * skill_lv;
|
||||||
skillratio += skill_lv * 15 * pc_checkskill( sd, IG_SHIELD_MASTERY );
|
skillratio += 7 * sstatus->pow;
|
||||||
|
skillratio += skill_lv * 50 * pc_checkskill( sd, IG_SHIELD_MASTERY );
|
||||||
if (sd) { // Damage affected by the shield's weight and refine. Need official formula. [Rytech]
|
if (sd) { // Damage affected by the shield's weight and refine. Need official formula. [Rytech]
|
||||||
short index = sd->equip_index[EQI_HAND_L];
|
short index = sd->equip_index[EQI_HAND_L];
|
||||||
|
|
||||||
if (index >= 0 && sd->inventory_data[index] && sd->inventory_data[index]->type == IT_ARMOR) {
|
if (index >= 0 && sd->inventory_data[index] && sd->inventory_data[index]->type == IT_ARMOR) {
|
||||||
skillratio += (sd->inventory_data[index]->weight * 7 / 6) / 10;
|
skillratio += (sd->inventory_data[index]->weight * 7 / 6) / 10;
|
||||||
skillratio += sd->inventory.u.items_inventory[index].refine * 4;
|
skillratio += sd->inventory.u.items_inventory[index].refine * 25;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
RE_LVL_DMOD(100);
|
RE_LVL_DMOD(100);
|
||||||
break;
|
break;
|
||||||
case IG_OVERSLASH:
|
case IG_OVERSLASH:
|
||||||
skillratio += -100 + (120 + pc_checkskill(sd, IG_SPEAR_SWORD_M) * 10) * skill_lv + 5 * sstatus->pow;
|
skillratio += -100 + 160 * skill_lv;
|
||||||
|
skillratio += pc_checkskill(sd, IG_SPEAR_SWORD_M) * 25 * skill_lv;
|
||||||
|
skillratio += 7 * sstatus->pow;
|
||||||
RE_LVL_DMOD(100);
|
RE_LVL_DMOD(100);
|
||||||
if ((i = pc_checkskill_imperial_guard(sd, 3)) > 0)
|
if ((i = pc_checkskill_imperial_guard(sd, 3)) > 0)
|
||||||
skillratio += skillratio * i / 100;
|
skillratio += skillratio * i / 100;
|
||||||
@ -5503,7 +5571,7 @@ static int battle_calc_attack_skill_ratio(struct Damage* wd, struct block_list *
|
|||||||
RE_LVL_DMOD(100);
|
RE_LVL_DMOD(100);
|
||||||
break;
|
break;
|
||||||
case CD_PETITIO:
|
case CD_PETITIO:
|
||||||
skillratio += -100 + (1050 + pc_checkskill(sd,CD_MACE_BOOK_M) * 10) * skill_lv + 5 * sstatus->pow;
|
skillratio += -100 + (1050 + pc_checkskill(sd,CD_MACE_BOOK_M) * 50) * skill_lv + 5 * sstatus->pow;
|
||||||
RE_LVL_DMOD(100);
|
RE_LVL_DMOD(100);
|
||||||
break;
|
break;
|
||||||
case SHC_DANCING_KNIFE:
|
case SHC_DANCING_KNIFE:
|
||||||
@ -5529,7 +5597,12 @@ static int battle_calc_attack_skill_ratio(struct Damage* wd, struct block_list *
|
|||||||
RE_LVL_DMOD(100);
|
RE_LVL_DMOD(100);
|
||||||
break;
|
break;
|
||||||
case SHC_SHADOW_STAB:
|
case SHC_SHADOW_STAB:
|
||||||
skillratio += -100 + 300 * skill_lv + 5 * sstatus->pow;
|
skillratio += -100 + 350 * skill_lv + 5 * sstatus->pow;
|
||||||
|
|
||||||
|
if( sc && sc->getSCE( SC_CLOAKINGEXCEED ) ){
|
||||||
|
skillratio += 50 * skill_lv + 2 * sstatus->pow;
|
||||||
|
}
|
||||||
|
|
||||||
RE_LVL_DMOD(100);
|
RE_LVL_DMOD(100);
|
||||||
break;
|
break;
|
||||||
case SHC_IMPACT_CRATER:
|
case SHC_IMPACT_CRATER:
|
||||||
@ -5543,7 +5616,7 @@ static int battle_calc_attack_skill_ratio(struct Damage* wd, struct block_list *
|
|||||||
RE_LVL_DMOD(100);
|
RE_LVL_DMOD(100);
|
||||||
break;
|
break;
|
||||||
case MT_AXE_STOMP:
|
case MT_AXE_STOMP:
|
||||||
skillratio += -100 + 350 + 850 * skill_lv + 5 * sstatus->pow;
|
skillratio += -100 + 400 + 950 * skill_lv + 5 * sstatus->pow;
|
||||||
RE_LVL_DMOD(100);
|
RE_LVL_DMOD(100);
|
||||||
break;
|
break;
|
||||||
case MT_MIGHTY_SMASH:
|
case MT_MIGHTY_SMASH:
|
||||||
@ -5576,7 +5649,8 @@ static int battle_calc_attack_skill_ratio(struct Damage* wd, struct block_list *
|
|||||||
RE_LVL_DMOD(100);
|
RE_LVL_DMOD(100);
|
||||||
break;
|
break;
|
||||||
case ABC_ABYSS_DAGGER:
|
case ABC_ABYSS_DAGGER:
|
||||||
skillratio += -100 + 100 + 500 * skill_lv + 5 * sstatus->pow;
|
skillratio += -100 + 100 + 900 * skill_lv;
|
||||||
|
skillratio += 5 * sstatus->pow;
|
||||||
RE_LVL_DMOD(100);
|
RE_LVL_DMOD(100);
|
||||||
break;
|
break;
|
||||||
case ABC_UNLUCKY_RUSH:
|
case ABC_UNLUCKY_RUSH:
|
||||||
@ -5592,31 +5666,37 @@ static int battle_calc_attack_skill_ratio(struct Damage* wd, struct block_list *
|
|||||||
RE_LVL_DMOD(100);
|
RE_LVL_DMOD(100);
|
||||||
break;
|
break;
|
||||||
case ABC_DEFT_STAB:
|
case ABC_DEFT_STAB:
|
||||||
skillratio += -100 + 350 + 550 * skill_lv + 5 * sstatus->pow;
|
skillratio += -100 + 250 + 350 * skill_lv;
|
||||||
|
skillratio += 5 * sstatus->pow;
|
||||||
RE_LVL_DMOD(100);
|
RE_LVL_DMOD(100);
|
||||||
break;
|
break;
|
||||||
case ABC_FRENZY_SHOT:
|
case ABC_FRENZY_SHOT:
|
||||||
skillratio += -100 + 400 * skill_lv + 5 * sstatus->con;
|
skillratio += -100 + 150 + 600 * skill_lv;
|
||||||
|
skillratio += 15 * sstatus->con;
|
||||||
RE_LVL_DMOD(100);
|
RE_LVL_DMOD(100);
|
||||||
break;
|
break;
|
||||||
case WH_HAWKRUSH:
|
case WH_HAWKRUSH:
|
||||||
skillratio += -100 + 500 * skill_lv + 5 * sstatus->con;
|
skillratio += -100 + 500 * skill_lv + 5 * sstatus->con;
|
||||||
|
if (sd)
|
||||||
|
skillratio += skillratio * pc_checkskill(sd, WH_NATUREFRIENDLY) / 10;
|
||||||
RE_LVL_DMOD(100);
|
RE_LVL_DMOD(100);
|
||||||
break;
|
break;
|
||||||
case WH_HAWKBOOMERANG:// Affected by trait stats??? CON for sure but the other one unknown. Likely POW. [Rytech]
|
case WH_HAWKBOOMERANG:
|
||||||
skillratio += -100 + 600 * skill_lv + 10 * sstatus->pow + 10 * sstatus->con;
|
skillratio += -100 + 600 * skill_lv + 10 * sstatus->con;
|
||||||
|
if (sd)
|
||||||
|
skillratio += skillratio * pc_checkskill(sd, WH_NATUREFRIENDLY) / 10;
|
||||||
if (tstatus->race == RC_BRUTE || tstatus->race == RC_FISH)
|
if (tstatus->race == RC_BRUTE || tstatus->race == RC_FISH)
|
||||||
skillratio += skillratio * 50 / 100;
|
skillratio += skillratio * 50 / 100;
|
||||||
RE_LVL_DMOD(100);
|
RE_LVL_DMOD(100);
|
||||||
break;
|
break;
|
||||||
case WH_GALESTORM:
|
case WH_GALESTORM:
|
||||||
skillratio += -100 + 950 * skill_lv + 10 * sstatus->con;
|
skillratio += -100 + 1000 * skill_lv + 10 * sstatus->con;
|
||||||
RE_LVL_DMOD(100);
|
RE_LVL_DMOD(100);
|
||||||
if (sc && sc->getSCE(SC_CALAMITYGALE) && (tstatus->race == RC_BRUTE || tstatus->race == RC_FISH))
|
if (sc && sc->getSCE(SC_CALAMITYGALE) && (tstatus->race == RC_BRUTE || tstatus->race == RC_FISH))
|
||||||
skillratio += skillratio * 50 / 100;
|
skillratio += skillratio * 50 / 100;
|
||||||
break;
|
break;
|
||||||
case WH_CRESCIVE_BOLT:
|
case WH_CRESCIVE_BOLT:
|
||||||
skillratio += -100 + 340 * skill_lv + 5 * sstatus->con;
|
skillratio += -100 + 400 + 900 * skill_lv + 5 * sstatus->con;
|
||||||
RE_LVL_DMOD(100);
|
RE_LVL_DMOD(100);
|
||||||
if (sc) {
|
if (sc) {
|
||||||
if (sc->getSCE(SC_CRESCIVEBOLT))
|
if (sc->getSCE(SC_CRESCIVEBOLT))
|
||||||
@ -5708,13 +5788,18 @@ static int battle_calc_attack_skill_ratio(struct Damage* wd, struct block_list *
|
|||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
case TR_RHYTHMSHOOTING:
|
case TR_RHYTHMSHOOTING:
|
||||||
skillratio += -100 + 200 + 120 * skill_lv;
|
skillratio += -100 + 450 + 650 * skill_lv;
|
||||||
|
|
||||||
if (sd && pc_checkskill(sd, TR_STAGE_MANNER) > 0)
|
if (sd && pc_checkskill(sd, TR_STAGE_MANNER) > 0)
|
||||||
skillratio += 3 * sstatus->con;
|
skillratio += 5 * sstatus->con;
|
||||||
|
|
||||||
if (tsc && tsc->getSCE(SC_SOUNDBLEND))
|
if (tsc && tsc->getSCE(SC_SOUNDBLEND)) {
|
||||||
skillratio += 100 + 100 * skill_lv;
|
if (skill_lv == 4)
|
||||||
|
skillratio += 830; // Typo in skill description ?
|
||||||
|
else
|
||||||
|
skillratio += 350 + 100 * skill_lv;
|
||||||
|
skillratio += 2 * sstatus->con;
|
||||||
|
}
|
||||||
|
|
||||||
RE_LVL_DMOD(100);
|
RE_LVL_DMOD(100);
|
||||||
if (sc && sc->getSCE(SC_MYSTIC_SYMPHONY)) {
|
if (sc && sc->getSCE(SC_MYSTIC_SYMPHONY)) {
|
||||||
@ -5731,6 +5816,43 @@ static int battle_calc_attack_skill_ratio(struct Damage* wd, struct block_list *
|
|||||||
case ABR_INFINITY_BUSTER:// Need official formula.
|
case ABR_INFINITY_BUSTER:// Need official formula.
|
||||||
skillratio += -100 + 50000;
|
skillratio += -100 + 50000;
|
||||||
break;
|
break;
|
||||||
|
case HN_SPIRAL_PIERCE_MAX:
|
||||||
|
skillratio += -100 + 700 + 800 * skill_lv;
|
||||||
|
skillratio += pc_checkskill(sd, HN_SELFSTUDY_TATICS) * 3 * skill_lv;
|
||||||
|
skillratio += 5 * sstatus->pow;
|
||||||
|
switch (status_get_size(target)){
|
||||||
|
case SZ_SMALL:
|
||||||
|
skillratio = skillratio * 150 / 100;
|
||||||
|
break;
|
||||||
|
case SZ_MEDIUM:
|
||||||
|
skillratio = skillratio * 130 / 100;
|
||||||
|
break;
|
||||||
|
case SZ_BIG:
|
||||||
|
skillratio = skillratio * 120 / 100;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
RE_LVL_DMOD(100);
|
||||||
|
break;
|
||||||
|
case HN_SHIELD_CHAIN_RUSH:
|
||||||
|
skillratio += -100 + 700 + 500 * skill_lv;
|
||||||
|
skillratio += pc_checkskill(sd, HN_SELFSTUDY_TATICS) * 3 * skill_lv;
|
||||||
|
skillratio += 5 * sstatus->pow;
|
||||||
|
RE_LVL_DMOD(100);
|
||||||
|
break;
|
||||||
|
case HN_MEGA_SONIC_BLOW:
|
||||||
|
skillratio += -100 + 900 + 750 * skill_lv;
|
||||||
|
skillratio += pc_checkskill(sd, HN_SELFSTUDY_TATICS) * 5 * skill_lv;
|
||||||
|
skillratio += 5 * sstatus->pow;
|
||||||
|
if (status_get_hp(target) < status_get_max_hp(target) / 2)
|
||||||
|
skillratio *= 2;
|
||||||
|
RE_LVL_DMOD(100);
|
||||||
|
break;
|
||||||
|
case HN_DOUBLEBOWLINGBASH:
|
||||||
|
skillratio += -100 + 200 + 300 * skill_lv;
|
||||||
|
skillratio += pc_checkskill(sd, HN_SELFSTUDY_TATICS) * 3 * skill_lv;
|
||||||
|
skillratio += 5 * sstatus->pow;
|
||||||
|
RE_LVL_DMOD(100);
|
||||||
|
break;
|
||||||
}
|
}
|
||||||
return skillratio;
|
return skillratio;
|
||||||
}
|
}
|
||||||
@ -6608,7 +6730,7 @@ static struct Damage initialize_weapon_data(struct block_list *src, struct block
|
|||||||
|
|
||||||
case GS_GROUNDDRIFT:
|
case GS_GROUNDDRIFT:
|
||||||
wd.amotion = sstatus->amotion;
|
wd.amotion = sstatus->amotion;
|
||||||
//Fall through
|
[[fallthrough]];
|
||||||
case KN_SPEARSTAB:
|
case KN_SPEARSTAB:
|
||||||
#ifndef RENEWAL
|
#ifndef RENEWAL
|
||||||
case KN_BOWLINGBASH:
|
case KN_BOWLINGBASH:
|
||||||
@ -6673,7 +6795,7 @@ static struct Damage initialize_weapon_data(struct block_list *src, struct block
|
|||||||
break;
|
break;
|
||||||
case SHC_SHADOW_STAB:
|
case SHC_SHADOW_STAB:
|
||||||
if (wd.miscflag == 2)
|
if (wd.miscflag == 2)
|
||||||
wd.div_ = 2;
|
wd.div_ = 3;
|
||||||
break;
|
break;
|
||||||
case SHC_IMPACT_CRATER:
|
case SHC_IMPACT_CRATER:
|
||||||
if (sc && sc->getSCE(SC_ROLLINGCUTTER))
|
if (sc && sc->getSCE(SC_ROLLINGCUTTER))
|
||||||
@ -6698,6 +6820,10 @@ static struct Damage initialize_weapon_data(struct block_list *src, struct block
|
|||||||
if (sc && sc->getSCE(SC_RESEARCHREPORT))
|
if (sc && sc->getSCE(SC_RESEARCHREPORT))
|
||||||
wd.div_ = 4;
|
wd.div_ = 4;
|
||||||
break;
|
break;
|
||||||
|
case HN_DOUBLEBOWLINGBASH:
|
||||||
|
if (wd.miscflag > 1)
|
||||||
|
wd.div_ += min(4, wd.miscflag);
|
||||||
|
break;
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
bool is_long = false;
|
bool is_long = false;
|
||||||
@ -6903,11 +7029,27 @@ static struct Damage battle_calc_weapon_attack(struct block_list *src, struct bl
|
|||||||
battle_attack_sc_bonus(&wd, src, target, skill_id, skill_lv);
|
battle_attack_sc_bonus(&wd, src, target, skill_id, skill_lv);
|
||||||
|
|
||||||
if (sd) { //monsters, homuns and pets have their damage computed directly
|
if (sd) { //monsters, homuns and pets have their damage computed directly
|
||||||
//PATK mod applies to Dragonbreaths if Dragonic Aura is skilled only - [munkrej]
|
wd.damage = wd.statusAtk + wd.weaponAtk + wd.equipAtk + wd.percentAtk;
|
||||||
if (!((skill_id == RK_DRAGONBREATH || skill_id == RK_DRAGONBREATH_WATER) && pc_checkskill( sd, DK_DRAGONIC_AURA ) == 0)) {
|
if( is_attack_left_handed( src, skill_id ) ){
|
||||||
wd.damage = (int64)floor((float)((wd.statusAtk + wd.weaponAtk + wd.equipAtk + wd.percentAtk) * (100 + sstatus->patk) / 100 + wd.masteryAtk + bonus_damage));
|
wd.damage2 = wd.statusAtk2 + wd.weaponAtk2 + wd.equipAtk2 + wd.percentAtk2;
|
||||||
if (is_attack_left_handed(src, skill_id))
|
}
|
||||||
wd.damage2 = (int64)floor((float)((wd.statusAtk2 + wd.weaponAtk2 + wd.equipAtk2 + wd.percentAtk2) * (100 + sstatus->patk) / 100 + wd.masteryAtk2 + bonus_damage));
|
// Apply PATK mod
|
||||||
|
// But for Dragonbreaths it only applies if Dragonic Aura is skilled
|
||||||
|
if( ( skill_id != RK_DRAGONBREATH && skill_id != RK_DRAGONBREATH_WATER ) || pc_checkskill( sd, DK_DRAGONIC_AURA ) > 0 ){
|
||||||
|
wd.damage = (int64)floor( (float)( wd.damage * ( 100 + sstatus->patk ) / 100 ) );
|
||||||
|
if( is_attack_left_handed( src, skill_id ) ){
|
||||||
|
wd.damage2 = (int64)floor( (float)( wd.damage2 * ( 100 + sstatus->patk ) / 100 ) );
|
||||||
|
}
|
||||||
|
}
|
||||||
|
// Apply MasteryATK
|
||||||
|
wd.damage += wd.masteryAtk;
|
||||||
|
if( is_attack_left_handed( src, skill_id ) ){
|
||||||
|
wd.damage2 += wd.masteryAtk2;
|
||||||
|
}
|
||||||
|
// Apply bonus damage
|
||||||
|
wd.damage += bonus_damage;
|
||||||
|
if( is_attack_left_handed( src, skill_id ) ){
|
||||||
|
wd.damage2 += bonus_damage;
|
||||||
}
|
}
|
||||||
|
|
||||||
// CritAtkRate modifier
|
// CritAtkRate modifier
|
||||||
@ -7267,7 +7409,7 @@ struct Damage battle_calc_magic_attack(struct block_list *src,struct block_list
|
|||||||
case MG_FIREWALL:
|
case MG_FIREWALL:
|
||||||
if ( tstatus->def_ele == ELE_FIRE || battle_check_undead(tstatus->race, tstatus->def_ele) )
|
if ( tstatus->def_ele == ELE_FIRE || battle_check_undead(tstatus->race, tstatus->def_ele) )
|
||||||
ad.blewcount = 0; //No knockback
|
ad.blewcount = 0; //No knockback
|
||||||
//Fall through
|
[[fallthrough]];
|
||||||
case NJ_KAENSIN:
|
case NJ_KAENSIN:
|
||||||
case PR_SANCTUARY:
|
case PR_SANCTUARY:
|
||||||
ad.dmotion = 1; //No flinch animation.
|
ad.dmotion = 1; //No flinch animation.
|
||||||
@ -7833,14 +7975,14 @@ struct Damage battle_calc_magic_attack(struct block_list *src,struct block_list
|
|||||||
RE_LVL_DMOD(100);
|
RE_LVL_DMOD(100);
|
||||||
break;
|
break;
|
||||||
case AG_DESTRUCTIVE_HURRICANE:
|
case AG_DESTRUCTIVE_HURRICANE:
|
||||||
skillratio += -100 + 250 + 2800 * skill_lv + 5 * sstatus->spl;
|
skillratio += -100 + 600 + 2850 * skill_lv + 5 * sstatus->spl;
|
||||||
RE_LVL_DMOD(100);
|
RE_LVL_DMOD(100);
|
||||||
if (sc && sc->getSCE(SC_CLIMAX))
|
if (sc && sc->getSCE(SC_CLIMAX))
|
||||||
{
|
{
|
||||||
if (sc->getSCE(SC_CLIMAX)->val1 == 3)
|
if (sc->getSCE(SC_CLIMAX)->val1 == 3)
|
||||||
skillratio *= 3;
|
skillratio += skillratio * 150 / 100;
|
||||||
else if (sc->getSCE(SC_CLIMAX)->val1 == 5)
|
else if (sc->getSCE(SC_CLIMAX)->val1 == 5)
|
||||||
skillratio += skillratio * 50 / 100;
|
skillratio -= skillratio * 20 / 100;
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
case AG_RAIN_OF_CRYSTAL:
|
case AG_RAIN_OF_CRYSTAL:
|
||||||
@ -7921,7 +8063,7 @@ struct Damage battle_calc_magic_attack(struct block_list *src,struct block_list
|
|||||||
RE_LVL_DMOD(100);
|
RE_LVL_DMOD(100);
|
||||||
break;
|
break;
|
||||||
case AG_ROCK_DOWN:
|
case AG_ROCK_DOWN:
|
||||||
skillratio += -100 + 950 * skill_lv + 5 * sstatus->spl;
|
skillratio += -100 + 1200 * skill_lv + 5 * sstatus->spl;
|
||||||
|
|
||||||
if( sc != nullptr && sc->getSCE( SC_CLIMAX ) ){
|
if( sc != nullptr && sc->getSCE( SC_CLIMAX ) ){
|
||||||
skillratio += 300 * skill_lv;
|
skillratio += 300 * skill_lv;
|
||||||
@ -7930,7 +8072,7 @@ struct Damage battle_calc_magic_attack(struct block_list *src,struct block_list
|
|||||||
RE_LVL_DMOD(100);
|
RE_LVL_DMOD(100);
|
||||||
break;
|
break;
|
||||||
case AG_STORM_CANNON:
|
case AG_STORM_CANNON:
|
||||||
skillratio += -100 + 950 * skill_lv + 5 * sstatus->spl;
|
skillratio += -100 + 1200 * skill_lv + 5 * sstatus->spl;
|
||||||
|
|
||||||
if( sc != nullptr && sc->getSCE( SC_CLIMAX ) ){
|
if( sc != nullptr && sc->getSCE( SC_CLIMAX ) ){
|
||||||
skillratio += 300 * skill_lv;
|
skillratio += 300 * skill_lv;
|
||||||
@ -7939,15 +8081,15 @@ struct Damage battle_calc_magic_attack(struct block_list *src,struct block_list
|
|||||||
RE_LVL_DMOD(100);
|
RE_LVL_DMOD(100);
|
||||||
break;
|
break;
|
||||||
case AG_CRIMSON_ARROW:
|
case AG_CRIMSON_ARROW:
|
||||||
skillratio += -100 + 300 * skill_lv + 5 * sstatus->spl;
|
skillratio += -100 + 350 * skill_lv + 5 * sstatus->spl;
|
||||||
RE_LVL_DMOD(100);
|
RE_LVL_DMOD(100);
|
||||||
break;
|
break;
|
||||||
case AG_CRIMSON_ARROW_ATK:
|
case AG_CRIMSON_ARROW_ATK:
|
||||||
skillratio += -100 + 600 * skill_lv + 5 * sstatus->spl;
|
skillratio += -100 + 700 * skill_lv + 5 * sstatus->spl;
|
||||||
RE_LVL_DMOD(100);
|
RE_LVL_DMOD(100);
|
||||||
break;
|
break;
|
||||||
case AG_FROZEN_SLASH:
|
case AG_FROZEN_SLASH:
|
||||||
skillratio += -100 + 250 + 900 * skill_lv + 5 * sstatus->spl;
|
skillratio += -100 + 400 + 900 * skill_lv + 5 * sstatus->spl;
|
||||||
|
|
||||||
if( sc != nullptr && sc->getSCE( SC_CLIMAX ) ){
|
if( sc != nullptr && sc->getSCE( SC_CLIMAX ) ){
|
||||||
skillratio += 150 + 350 * skill_lv;
|
skillratio += 150 + 350 * skill_lv;
|
||||||
@ -7965,21 +8107,21 @@ struct Damage battle_calc_magic_attack(struct block_list *src,struct block_list
|
|||||||
break;
|
break;
|
||||||
case IG_CROSS_RAIN:
|
case IG_CROSS_RAIN:
|
||||||
if( sc && sc->getSCE( SC_HOLY_S ) ){
|
if( sc && sc->getSCE( SC_HOLY_S ) ){
|
||||||
skillratio += -100 + ( 450 + 10 * pc_checkskill( sd, IG_SPEAR_SWORD_M ) ) * skill_lv;
|
skillratio += -100 + ( 450 + 15 * pc_checkskill( sd, IG_SPEAR_SWORD_M ) ) * skill_lv;
|
||||||
}else{
|
}else{
|
||||||
skillratio += -100 + ( 320 + 5 * pc_checkskill( sd, IG_SPEAR_SWORD_M ) ) * skill_lv;
|
skillratio += -100 + ( 320 + 10 * pc_checkskill( sd, IG_SPEAR_SWORD_M ) ) * skill_lv;
|
||||||
}
|
}
|
||||||
skillratio += 5 * sstatus->spl;
|
skillratio += 7 * sstatus->spl;
|
||||||
RE_LVL_DMOD(100);
|
RE_LVL_DMOD(100);
|
||||||
break;
|
break;
|
||||||
case CD_ARBITRIUM:
|
case CD_ARBITRIUM:
|
||||||
skillratio += -100 + 1000 * skill_lv + 7 * sstatus->spl;
|
skillratio += -100 + 1000 * skill_lv + 10 * sstatus->spl;
|
||||||
skillratio += 10 * pc_checkskill( sd, CD_FIDUS_ANIMUS ) * skill_lv;
|
skillratio += 10 * pc_checkskill( sd, CD_FIDUS_ANIMUS ) * skill_lv;
|
||||||
RE_LVL_DMOD(100);
|
RE_LVL_DMOD(100);
|
||||||
break;
|
break;
|
||||||
case CD_ARBITRIUM_ATK:
|
case CD_ARBITRIUM_ATK:
|
||||||
skillratio += -100 + 1250 * skill_lv + 7 * sstatus->spl;
|
skillratio += -100 + 1750 * skill_lv + 10 * sstatus->spl;
|
||||||
skillratio += 10 * pc_checkskill( sd, CD_FIDUS_ANIMUS ) * skill_lv;
|
skillratio += 50 * pc_checkskill( sd, CD_FIDUS_ANIMUS ) * skill_lv;
|
||||||
RE_LVL_DMOD(100);
|
RE_LVL_DMOD(100);
|
||||||
break;
|
break;
|
||||||
case CD_PNEUMATICUS_PROCELLA:
|
case CD_PNEUMATICUS_PROCELLA:
|
||||||
@ -7992,7 +8134,7 @@ struct Damage battle_calc_magic_attack(struct block_list *src,struct block_list
|
|||||||
RE_LVL_DMOD(100);
|
RE_LVL_DMOD(100);
|
||||||
break;
|
break;
|
||||||
case CD_FRAMEN:
|
case CD_FRAMEN:
|
||||||
skillratio += -100 + (800 + 5 * pc_checkskill(sd,CD_FIDUS_ANIMUS)) * skill_lv + 5 * sstatus->spl;
|
skillratio += -100 + (950 + 5 * pc_checkskill(sd,CD_FIDUS_ANIMUS)) * skill_lv + 5 * sstatus->spl;
|
||||||
if (tstatus->race == RC_UNDEAD || tstatus->race == RC_DEMON)
|
if (tstatus->race == RC_UNDEAD || tstatus->race == RC_DEMON)
|
||||||
skillratio += 100 * skill_lv;
|
skillratio += 100 * skill_lv;
|
||||||
RE_LVL_DMOD(100);
|
RE_LVL_DMOD(100);
|
||||||
@ -8011,12 +8153,14 @@ struct Damage battle_calc_magic_attack(struct block_list *src,struct block_list
|
|||||||
skillratio += -100 + ( 570 + 20 * pc_checkskill( sd, ABC_MAGIC_SWORD_M ) ) * skill_lv + 5 * sstatus->spl;
|
skillratio += -100 + ( 570 + 20 * pc_checkskill( sd, ABC_MAGIC_SWORD_M ) ) * skill_lv + 5 * sstatus->spl;
|
||||||
RE_LVL_DMOD(100);
|
RE_LVL_DMOD(100);
|
||||||
break;
|
break;
|
||||||
case TR_METALIC_FURY: {
|
case TR_METALIC_FURY:
|
||||||
int area = skill_get_splash(skill_id, skill_lv);
|
skillratio += -100 + 2600 * skill_lv;
|
||||||
int count = map_forcountinarea(skill_check_bl_sc,target->m,target->x - area,target->y - area,target->x + area,target->y + area,5,BL_MOB,SC_SOUNDBLEND);
|
// !Todo: skill affected by SPL (without SC_SOUNDBLEND) as well?
|
||||||
skillratio += -100 + (2200 + 300 * count) * skill_lv + 5 * sstatus->spl;
|
if (tsc && tsc->getSCE(SC_SOUNDBLEND)) {
|
||||||
RE_LVL_DMOD(100);
|
skillratio += 1000 * skill_lv;
|
||||||
|
skillratio += 2 * pc_checkskill(sd, TR_STAGE_MANNER) * sstatus->spl;
|
||||||
}
|
}
|
||||||
|
RE_LVL_DMOD(100);
|
||||||
break;
|
break;
|
||||||
case TR_SOUNDBLEND:
|
case TR_SOUNDBLEND:
|
||||||
skillratio += -100 + 120 * skill_lv + 5 * sstatus->spl;
|
skillratio += -100 + 120 * skill_lv + 5 * sstatus->spl;
|
||||||
@ -8115,6 +8259,57 @@ struct Damage battle_calc_magic_attack(struct block_list *src,struct block_list
|
|||||||
case NPC_RAINOFMETEOR:
|
case NPC_RAINOFMETEOR:
|
||||||
skillratio += 350; // unknown ratio
|
skillratio += 350; // unknown ratio
|
||||||
break;
|
break;
|
||||||
|
case HN_NAPALM_VULCAN_STRIKE:
|
||||||
|
skillratio += -100 + 350 + 650 * skill_lv;
|
||||||
|
skillratio += pc_checkskill(sd, HN_SELFSTUDY_SOCERY) * 4 * skill_lv;
|
||||||
|
skillratio += 5 * sstatus->spl;
|
||||||
|
RE_LVL_DMOD(100);
|
||||||
|
break;
|
||||||
|
case HN_JUPITEL_THUNDER_STORM:
|
||||||
|
skillratio += -100 + 1800 * skill_lv;
|
||||||
|
skillratio += pc_checkskill(sd, HN_SELFSTUDY_SOCERY) * 3 * skill_lv;
|
||||||
|
skillratio += 5 * sstatus->spl;
|
||||||
|
RE_LVL_DMOD(100);
|
||||||
|
break;
|
||||||
|
case HN_HELLS_DRIVE:
|
||||||
|
skillratio += -100 + 1500 + 700 * skill_lv;
|
||||||
|
skillratio += pc_checkskill(sd, HN_SELFSTUDY_SOCERY) * 4 * skill_lv;
|
||||||
|
skillratio += 5 * sstatus->spl;
|
||||||
|
RE_LVL_DMOD(100);
|
||||||
|
break;
|
||||||
|
case HN_GROUND_GRAVITATION:
|
||||||
|
if (mflag & SKILL_ALTDMG_FLAG) {
|
||||||
|
skillratio += -100 + 3000 + 1500 * skill_lv;
|
||||||
|
skillratio += pc_checkskill(sd, HN_SELFSTUDY_SOCERY) * 4 * skill_lv;
|
||||||
|
ad.div_ = -2;
|
||||||
|
} else {
|
||||||
|
skillratio += -100 + 800 + 700 * skill_lv;
|
||||||
|
skillratio += pc_checkskill(sd, HN_SELFSTUDY_SOCERY) * 2 * skill_lv;
|
||||||
|
}
|
||||||
|
skillratio += 5 * sstatus->spl;
|
||||||
|
RE_LVL_DMOD(100);
|
||||||
|
break;
|
||||||
|
case HN_JACK_FROST_NOVA:
|
||||||
|
if (mflag & SKILL_ALTDMG_FLAG) {
|
||||||
|
skillratio += -100 + 200 * skill_lv;
|
||||||
|
} else {
|
||||||
|
skillratio += -100 + 400 + 500 * skill_lv;
|
||||||
|
}
|
||||||
|
skillratio += pc_checkskill(sd, HN_SELFSTUDY_SOCERY) * 3 * skill_lv;
|
||||||
|
skillratio += 5 * sstatus->spl;
|
||||||
|
RE_LVL_DMOD(100);
|
||||||
|
break;
|
||||||
|
case HN_METEOR_STORM_BUSTER:
|
||||||
|
if (mflag & SKILL_ALTDMG_FLAG) {
|
||||||
|
skillratio += -100 + 300 + 160 * skill_lv * 2;
|
||||||
|
ad.div_ = -3;
|
||||||
|
} else {
|
||||||
|
skillratio += -100 + 450 + 160 * skill_lv;
|
||||||
|
}
|
||||||
|
skillratio += pc_checkskill(sd, HN_SELFSTUDY_SOCERY) * 5 * skill_lv;
|
||||||
|
skillratio += 5 * sstatus->spl;
|
||||||
|
RE_LVL_DMOD(100);
|
||||||
|
break;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (sc) {// Insignia's increases the damage of offensive magic by a fixed percentage depending on the element.
|
if (sc) {// Insignia's increases the damage of offensive magic by a fixed percentage depending on the element.
|
||||||
@ -8649,6 +8844,7 @@ struct Damage battle_calc_misc_attack(struct block_list *src,struct block_list *
|
|||||||
case RA_ICEBOUNDTRAP:
|
case RA_ICEBOUNDTRAP:
|
||||||
if (md.damage == 1)
|
if (md.damage == 1)
|
||||||
break;
|
break;
|
||||||
|
[[fallthrough]];
|
||||||
case RA_CLUSTERBOMB:
|
case RA_CLUSTERBOMB:
|
||||||
{
|
{
|
||||||
struct Damage wd = battle_calc_weapon_attack(src,target,skill_id,skill_lv,mflag);
|
struct Damage wd = battle_calc_weapon_attack(src,target,skill_id,skill_lv,mflag);
|
||||||
|
|||||||
@ -66,6 +66,7 @@ struct Channel* channel_create(struct Channel *tmp_chan) {
|
|||||||
break;
|
break;
|
||||||
case CHAN_TYPE_PRIVATE:
|
case CHAN_TYPE_PRIVATE:
|
||||||
channel->char_id = tmp_chan->char_id;
|
channel->char_id = tmp_chan->char_id;
|
||||||
|
[[fallthrough]];
|
||||||
default:
|
default:
|
||||||
strdb_put(channel_db, channel->name, channel);
|
strdb_put(channel_db, channel->name, channel);
|
||||||
break;
|
break;
|
||||||
|
|||||||
@ -915,6 +915,7 @@ static void chrif_ack_login_req(int aid, const char* player_name, uint16 type, u
|
|||||||
case CHRIF_OP_LOGIN_CHANGESEX:
|
case CHRIF_OP_LOGIN_CHANGESEX:
|
||||||
case CHRIF_OP_CHANGECHARSEX:
|
case CHRIF_OP_CHANGECHARSEX:
|
||||||
type = CHRIF_OP_LOGIN_CHANGESEX; // So we don't have to create a new msgstring.
|
type = CHRIF_OP_LOGIN_CHANGESEX; // So we don't have to create a new msgstring.
|
||||||
|
[[fallthrough]];
|
||||||
case CHRIF_OP_LOGIN_BLOCK:
|
case CHRIF_OP_LOGIN_BLOCK:
|
||||||
case CHRIF_OP_LOGIN_BAN:
|
case CHRIF_OP_LOGIN_BAN:
|
||||||
case CHRIF_OP_LOGIN_UNBLOCK:
|
case CHRIF_OP_LOGIN_UNBLOCK:
|
||||||
|
|||||||
144
src/map/clif.cpp
144
src/map/clif.cpp
@ -81,9 +81,6 @@ static inline int32 client_exp(t_exp exp) {
|
|||||||
static struct eri *delay_clearunit_ers;
|
static struct eri *delay_clearunit_ers;
|
||||||
|
|
||||||
struct s_packet_db packet_db[MAX_PACKET_DB + 1];
|
struct s_packet_db packet_db[MAX_PACKET_DB + 1];
|
||||||
// Reuseable global packet buffer to prevent too many allocations
|
|
||||||
// Take socket.cpp::socket_max_client_packet into consideration
|
|
||||||
static int8 packet_buffer[UINT16_MAX];
|
|
||||||
unsigned long color_table[COLOR_MAX];
|
unsigned long color_table[COLOR_MAX];
|
||||||
|
|
||||||
#include "clif_obfuscation.hpp"
|
#include "clif_obfuscation.hpp"
|
||||||
@ -529,6 +526,7 @@ int clif_send(const void* buf, int len, struct block_list* bl, enum send_target
|
|||||||
case AREA_WOSC:
|
case AREA_WOSC:
|
||||||
if (sd && bl->prev == NULL) //Otherwise source misses the packet.[Skotlex]
|
if (sd && bl->prev == NULL) //Otherwise source misses the packet.[Skotlex]
|
||||||
clif_send (buf, len, bl, SELF);
|
clif_send (buf, len, bl, SELF);
|
||||||
|
[[fallthrough]];
|
||||||
case AREA_WOC:
|
case AREA_WOC:
|
||||||
case AREA_WOS:
|
case AREA_WOS:
|
||||||
map_foreachinallarea(clif_send_sub, bl->m, bl->x-AREA_SIZE, bl->y-AREA_SIZE, bl->x+AREA_SIZE, bl->y+AREA_SIZE,
|
map_foreachinallarea(clif_send_sub, bl->m, bl->x-AREA_SIZE, bl->y-AREA_SIZE, bl->x+AREA_SIZE, bl->y+AREA_SIZE,
|
||||||
@ -568,6 +566,7 @@ int clif_send(const void* buf, int len, struct block_list* bl, enum send_target
|
|||||||
y0 = bl->y - AREA_SIZE;
|
y0 = bl->y - AREA_SIZE;
|
||||||
x1 = bl->x + AREA_SIZE;
|
x1 = bl->x + AREA_SIZE;
|
||||||
y1 = bl->y + AREA_SIZE;
|
y1 = bl->y + AREA_SIZE;
|
||||||
|
[[fallthrough]];
|
||||||
case PARTY:
|
case PARTY:
|
||||||
case PARTY_WOS:
|
case PARTY_WOS:
|
||||||
case PARTY_SAMEMAP:
|
case PARTY_SAMEMAP:
|
||||||
@ -644,6 +643,7 @@ int clif_send(const void* buf, int len, struct block_list* bl, enum send_target
|
|||||||
y0 = bl->y - AREA_SIZE;
|
y0 = bl->y - AREA_SIZE;
|
||||||
x1 = bl->x + AREA_SIZE;
|
x1 = bl->x + AREA_SIZE;
|
||||||
y1 = bl->y + AREA_SIZE;
|
y1 = bl->y + AREA_SIZE;
|
||||||
|
[[fallthrough]];
|
||||||
case GUILD_SAMEMAP:
|
case GUILD_SAMEMAP:
|
||||||
case GUILD_SAMEMAP_WOS:
|
case GUILD_SAMEMAP_WOS:
|
||||||
case GUILD:
|
case GUILD:
|
||||||
@ -695,6 +695,7 @@ int clif_send(const void* buf, int len, struct block_list* bl, enum send_target
|
|||||||
y0 = bl->y - AREA_SIZE;
|
y0 = bl->y - AREA_SIZE;
|
||||||
x1 = bl->x + AREA_SIZE;
|
x1 = bl->x + AREA_SIZE;
|
||||||
y1 = bl->y + AREA_SIZE;
|
y1 = bl->y + AREA_SIZE;
|
||||||
|
[[fallthrough]];
|
||||||
case BG_SAMEMAP:
|
case BG_SAMEMAP:
|
||||||
case BG_SAMEMAP_WOS:
|
case BG_SAMEMAP_WOS:
|
||||||
case BG:
|
case BG:
|
||||||
@ -2928,7 +2929,7 @@ static void clif_item_equip( short idx, struct EQUIPITEM_INFO *p, struct item *i
|
|||||||
#endif
|
#endif
|
||||||
|
|
||||||
#if PACKETVER_MAIN_NUM >= 20200916 || PACKETVER_RE_NUM >= 20200724
|
#if PACKETVER_MAIN_NUM >= 20200916 || PACKETVER_RE_NUM >= 20200724
|
||||||
p->enchantgrade = it->enchantgrade;
|
p->grade = it->enchantgrade;
|
||||||
#endif
|
#endif
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -4940,10 +4941,10 @@ void clif_storageitemadded( map_session_data* sd, struct item* i, int index, int
|
|||||||
p.damaged = i->attribute; // attribute
|
p.damaged = i->attribute; // attribute
|
||||||
p.refine = i->refine; //refine
|
p.refine = i->refine; //refine
|
||||||
clif_addcards( &p.slot, i );
|
clif_addcards( &p.slot, i );
|
||||||
#if PACKETVER >= 20150226
|
#if PACKETVER_MAIN_NUM >= 20140813 || PACKETVER_RE_NUM >= 20140402 || defined(PACKETVER_ZERO)
|
||||||
clif_add_random_options( p.option_data, *i );
|
clif_add_random_options( p.option_data, *i );
|
||||||
#if PACKETVER_MAIN_NUM >= 20200916 || PACKETVER_RE_NUM >= 20200724
|
#if PACKETVER_MAIN_NUM >= 20200916 || PACKETVER_RE_NUM >= 20200723 || PACKETVER_ZERO_NUM >= 20221024
|
||||||
p.enchantgrade = i->enchantgrade;
|
p.grade = i->enchantgrade;
|
||||||
#endif
|
#endif
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
@ -9156,12 +9157,7 @@ void clif_guild_emblem_area(struct block_list* bl)
|
|||||||
p.packetType = HEADER_ZC_CHANGE_GUILD;
|
p.packetType = HEADER_ZC_CHANGE_GUILD;
|
||||||
p.guild_id = status_get_guild_id(bl);
|
p.guild_id = status_get_guild_id(bl);
|
||||||
p.emblem_id = status_get_emblem_id(bl);
|
p.emblem_id = status_get_emblem_id(bl);
|
||||||
|
p.AID = bl->id;
|
||||||
#if PACKETVER < 20190724
|
|
||||||
p.aid = bl->id;
|
|
||||||
#else
|
|
||||||
p.unknown = 0;
|
|
||||||
#endif
|
|
||||||
|
|
||||||
clif_send(&p, sizeof(p), bl, AREA_WOS);
|
clif_send(&p, sizeof(p), bl, AREA_WOS);
|
||||||
}
|
}
|
||||||
@ -15170,6 +15166,7 @@ void clif_parse_NoviceDoriDori(int fd, map_session_data *sd)
|
|||||||
case MAPID_TAEKWON:
|
case MAPID_TAEKWON:
|
||||||
if (!sd->state.rest)
|
if (!sd->state.rest)
|
||||||
break;
|
break;
|
||||||
|
[[fallthrough]];
|
||||||
case MAPID_SUPER_NOVICE:
|
case MAPID_SUPER_NOVICE:
|
||||||
case MAPID_SUPER_BABY:
|
case MAPID_SUPER_BABY:
|
||||||
case MAPID_SUPER_NOVICE_E:
|
case MAPID_SUPER_NOVICE_E:
|
||||||
@ -17514,40 +17511,31 @@ void clif_parse_Adopt_reply(int fd, map_session_data *sd){
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
/// Convex Mirror (ZC_BOSS_INFO).
|
/// Convex Mirror
|
||||||
/// 0293 <infoType>.B <x>.L <y>.L <minHours>.W <minMinutes>.W <maxHours>.W <maxMinutes>.W <monster name>.51B
|
/// 0293 <infoType>.B <x>.L <y>.L <minHours>.W <minMinutes>.W <maxHours>.W <maxMinutes>.W <monster name>.51B (ZC_BOSS_INFO)
|
||||||
/// infoType:
|
/// infoType:
|
||||||
/// BOSS_INFO_NOT = No boss on this map.
|
/// BOSS_INFO_NOT = No boss on this map.
|
||||||
/// BOSS_INFO_ALIVE = Boss is alive (position update).
|
/// BOSS_INFO_ALIVE = Boss is alive (position update).
|
||||||
/// BOSS_INFO_ALIVE_WITHMSG = Boss is alive (initial announce).
|
/// BOSS_INFO_ALIVE_WITHMSG = Boss is alive (initial announce).
|
||||||
/// BOSS_INFO_DEAD = Boss is dead.
|
/// BOSS_INFO_DEAD = Boss is dead.
|
||||||
void clif_bossmapinfo(map_session_data *sd, struct mob_data *md, enum e_bossmap_info flag)
|
void clif_bossmapinfo( map_session_data& sd, mob_data* md, e_bossmap_info flag ){
|
||||||
{
|
PACKET_ZC_BOSS_INFO p = {};
|
||||||
int fd = sd->fd;
|
|
||||||
|
|
||||||
WFIFOHEAD(fd,70);
|
p.packetType = HEADER_ZC_BOSS_INFO;
|
||||||
memset(WFIFOP(fd,0),0,70);
|
p.type = flag;
|
||||||
WFIFOW(fd,0) = 0x293;
|
|
||||||
|
|
||||||
switch (flag) {
|
switch (flag) {
|
||||||
case BOSS_INFO_NOT:
|
case BOSS_INFO_NOT:
|
||||||
WFIFOB(fd,2) = BOSS_INFO_NOT;
|
|
||||||
// No data required
|
// No data required
|
||||||
break;
|
break;
|
||||||
case BOSS_INFO_ALIVE:
|
|
||||||
WFIFOB(fd,2) = BOSS_INFO_ALIVE;
|
|
||||||
// Update X/Y
|
|
||||||
WFIFOL(fd,3) = md->bl.x;
|
|
||||||
WFIFOL(fd,7) = md->bl.y;
|
|
||||||
break;
|
|
||||||
case BOSS_INFO_ALIVE_WITHMSG:
|
case BOSS_INFO_ALIVE_WITHMSG:
|
||||||
WFIFOB(fd,2) = BOSS_INFO_ALIVE_WITHMSG;
|
[[fallthrough]];
|
||||||
// Current X/Y
|
case BOSS_INFO_ALIVE:
|
||||||
WFIFOL(fd,3) = md->bl.x;
|
|
||||||
WFIFOL(fd,7) = md->bl.y;
|
p.x = md->bl.x;
|
||||||
|
p.y = md->bl.y;
|
||||||
break;
|
break;
|
||||||
case BOSS_INFO_DEAD:
|
case BOSS_INFO_DEAD: {
|
||||||
{
|
|
||||||
const struct TimerData * timer_data = get_timer(md->spawn_timer);
|
const struct TimerData * timer_data = get_timer(md->spawn_timer);
|
||||||
unsigned int seconds;
|
unsigned int seconds;
|
||||||
int hours, minutes;
|
int hours, minutes;
|
||||||
@ -17557,18 +17545,18 @@ void clif_bossmapinfo(map_session_data *sd, struct mob_data *md, enum e_bossmap_
|
|||||||
seconds = seconds - (60 * 60 * hours);
|
seconds = seconds - (60 * 60 * hours);
|
||||||
minutes = seconds / 60;
|
minutes = seconds / 60;
|
||||||
|
|
||||||
WFIFOB(fd,2) = BOSS_INFO_DEAD;
|
|
||||||
// Add respawn info
|
p.minHours = hours;
|
||||||
WFIFOW(fd,11) = hours; // Hours
|
p.minMinutes = minutes;
|
||||||
WFIFOW(fd,13) = minutes; // Minutes
|
|
||||||
}
|
|
||||||
break;
|
break;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if (md != NULL)
|
if( md != nullptr ){
|
||||||
safestrncpy(WFIFOCP(fd,19), md->db->jname.c_str(), NAME_LENGTH);
|
safestrncpy( p.name, md->db->jname.c_str(), sizeof( p.name ) );
|
||||||
|
}
|
||||||
|
|
||||||
WFIFOSET(fd,70);
|
clif_send( &p, sizeof( p ), &sd.bl, SELF );
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
@ -17677,7 +17665,7 @@ std::string clif_quest_string( std::shared_ptr<s_quest_objective> objective ){
|
|||||||
case RC_DRAGON: race_name = "Dragon"; break;
|
case RC_DRAGON: race_name = "Dragon"; break;
|
||||||
default:
|
default:
|
||||||
ShowWarning( "clif_quest_string: Unsupported race %d - using empty string...\n", objective->race );
|
ShowWarning( "clif_quest_string: Unsupported race %d - using empty string...\n", objective->race );
|
||||||
// Fallthrough
|
[[fallthrough]];
|
||||||
case RC_ALL: race_name = ""; break;
|
case RC_ALL: race_name = ""; break;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -17689,7 +17677,7 @@ std::string clif_quest_string( std::shared_ptr<s_quest_objective> objective ){
|
|||||||
case SZ_BIG: size_name = "Large"; break;
|
case SZ_BIG: size_name = "Large"; break;
|
||||||
default:
|
default:
|
||||||
ShowWarning( "clif_quest_string: Unsupported size %d - using empty string...\n", objective->size );
|
ShowWarning( "clif_quest_string: Unsupported size %d - using empty string...\n", objective->size );
|
||||||
// Fallthrough
|
[[fallthrough]];
|
||||||
case SZ_ALL: size_name = ""; break;
|
case SZ_ALL: size_name = ""; break;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -17708,7 +17696,7 @@ std::string clif_quest_string( std::shared_ptr<s_quest_objective> objective ){
|
|||||||
case ELE_UNDEAD: ele_name = "Undead Element"; break;
|
case ELE_UNDEAD: ele_name = "Undead Element"; break;
|
||||||
default:
|
default:
|
||||||
ShowWarning( "clif_quest_string: Unsupported element %d - using empty string...\n", objective->element );
|
ShowWarning( "clif_quest_string: Unsupported element %d - using empty string...\n", objective->element );
|
||||||
// Fallthrough
|
[[fallthrough]];
|
||||||
case ELE_ALL: ele_name = ""; break;
|
case ELE_ALL: ele_name = ""; break;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -23586,14 +23574,14 @@ void clif_parse_laphine_upgrade( int fd, map_session_data* sd ){
|
|||||||
}else if( upgrade->resultRefineMaximum > 0 ){
|
}else if( upgrade->resultRefineMaximum > 0 ){
|
||||||
// If a minimum is specified it can also downgrade
|
// If a minimum is specified it can also downgrade
|
||||||
if( upgrade->resultRefineMinimum ){
|
if( upgrade->resultRefineMinimum ){
|
||||||
item->refine = rnd_value( upgrade->resultRefineMinimum, upgrade->resultRefineMaximum );
|
item->refine = static_cast<uint8>( rnd_value<uint16>( upgrade->resultRefineMinimum, upgrade->resultRefineMaximum ) );
|
||||||
}else{
|
}else{
|
||||||
// Otherwise it can only be upgraded until the maximum, but not downgraded
|
// Otherwise it can only be upgraded until the maximum, but not downgraded
|
||||||
item->refine = rnd_value<uint16>( item->refine, upgrade->resultRefineMaximum );
|
item->refine = static_cast<uint8>( rnd_value<uint16>( item->refine, upgrade->resultRefineMaximum ) );
|
||||||
}
|
}
|
||||||
}else if( upgrade->resultRefineMinimum > 0 ){
|
}else if( upgrade->resultRefineMinimum > 0 ){
|
||||||
// No maximum has been specified, so it can be anything between minimum and MAX_REFINE
|
// No maximum has been specified, so it can be anything between minimum and MAX_REFINE
|
||||||
item->refine = rnd_value<uint16>( upgrade->resultRefineMinimum, MAX_REFINE );
|
item->refine = static_cast<uint8>( rnd_value<uint16>( upgrade->resultRefineMinimum, MAX_REFINE ) );
|
||||||
}
|
}
|
||||||
|
|
||||||
// Log retrieving the item again -> with the new options
|
// Log retrieving the item again -> with the new options
|
||||||
@ -23987,11 +23975,11 @@ void clif_reputation_list( map_session_data& sd ){
|
|||||||
}
|
}
|
||||||
|
|
||||||
void clif_item_reform_open( map_session_data& sd, t_itemid item ){
|
void clif_item_reform_open( map_session_data& sd, t_itemid item ){
|
||||||
#if PACKETVER_RE_NUM >= 20211103 || PACKETVER_MAIN_NUM >= 20220330
|
#if PACKETVER_MAIN_NUM >= 20201118 || PACKETVER_RE_NUM >= 20211103 || PACKETVER_ZERO_NUM >= 20221024
|
||||||
struct PACKET_ZC_OPEN_REFORM_UI p = {};
|
struct PACKET_ZC_OPEN_REFORM_UI p = {};
|
||||||
|
|
||||||
p.packetType = HEADER_ZC_OPEN_REFORM_UI;
|
p.PacketType = HEADER_ZC_OPEN_REFORM_UI;
|
||||||
p.itemId = item;
|
p.ITID = item;
|
||||||
|
|
||||||
clif_send( &p, sizeof( p ), &sd.bl, SELF );
|
clif_send( &p, sizeof( p ), &sd.bl, SELF );
|
||||||
|
|
||||||
@ -24000,16 +23988,16 @@ void clif_item_reform_open( map_session_data& sd, t_itemid item ){
|
|||||||
}
|
}
|
||||||
|
|
||||||
void clif_parse_item_reform_close( int fd, map_session_data* sd ){
|
void clif_parse_item_reform_close( int fd, map_session_data* sd ){
|
||||||
#if PACKETVER_RE_NUM >= 20211103 || PACKETVER_MAIN_NUM >= 20220330
|
#if PACKETVER_MAIN_NUM >= 20200916 || PACKETVER_RE_NUM >= 20211103 || PACKETVER_ZERO_NUM >= 20221024
|
||||||
sd->state.item_reform = 0;
|
sd->state.item_reform = 0;
|
||||||
#endif
|
#endif
|
||||||
}
|
}
|
||||||
|
|
||||||
void clif_item_reform_result( map_session_data& sd, uint16 index, uint8 result ){
|
void clif_item_reform_result( map_session_data& sd, uint16 index, uint8 result ){
|
||||||
#if PACKETVER_RE_NUM >= 20211103 || PACKETVER_MAIN_NUM >= 20220330
|
#if PACKETVER_MAIN_NUM >= 20201118 || PACKETVER_RE_NUM >= 20211103 || PACKETVER_ZERO_NUM >= 20221024
|
||||||
struct PACKET_ZC_ITEM_REFORM_ACK p = {};
|
struct PACKET_ZC_ITEM_REFORM_ACK p = {};
|
||||||
|
|
||||||
p.packetType = HEADER_ZC_ITEM_REFORM_ACK;
|
p.PacketType = HEADER_ZC_ITEM_REFORM_ACK;
|
||||||
p.index = client_index( index );
|
p.index = client_index( index );
|
||||||
p.result = result;
|
p.result = result;
|
||||||
|
|
||||||
@ -24023,7 +24011,7 @@ void clif_item_reform_result( map_session_data& sd, uint16 index, uint8 result )
|
|||||||
}
|
}
|
||||||
|
|
||||||
void clif_parse_item_reform_start( int fd, map_session_data* sd ){
|
void clif_parse_item_reform_start( int fd, map_session_data* sd ){
|
||||||
#if PACKETVER_RE_NUM >= 20211103 || PACKETVER_MAIN_NUM >= 20220330
|
#if PACKETVER_MAIN_NUM >= 20200916 || PACKETVER_RE_NUM >= 20211103 || PACKETVER_ZERO_NUM >= 20221024
|
||||||
// Not opened
|
// Not opened
|
||||||
if( sd->state.item_reform == 0 ){
|
if( sd->state.item_reform == 0 ){
|
||||||
return;
|
return;
|
||||||
@ -24032,7 +24020,7 @@ void clif_parse_item_reform_start( int fd, map_session_data* sd ){
|
|||||||
struct PACKET_CZ_ITEM_REFORM *p = (struct PACKET_CZ_ITEM_REFORM*)RFIFOP( fd, 0 );
|
struct PACKET_CZ_ITEM_REFORM *p = (struct PACKET_CZ_ITEM_REFORM*)RFIFOP( fd, 0 );
|
||||||
|
|
||||||
// Item mismatch
|
// Item mismatch
|
||||||
if( p->itemId != sd->state.item_reform ){
|
if( p->ITID != sd->state.item_reform ){
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -24202,13 +24190,13 @@ void clif_enchantwindow_result( map_session_data& sd, bool success, t_itemid enc
|
|||||||
#if PACKETVER_RE_NUM >= 20211103 || PACKETVER_MAIN_NUM >= 20220330
|
#if PACKETVER_RE_NUM >= 20211103 || PACKETVER_MAIN_NUM >= 20220330
|
||||||
struct PACKET_ZC_RESPONSE_ENCHANT p = {};
|
struct PACKET_ZC_RESPONSE_ENCHANT p = {};
|
||||||
|
|
||||||
p.packetType = HEADER_ZC_RESPONSE_ENCHANT;
|
p.PacketType = HEADER_ZC_RESPONSE_ENCHANT;
|
||||||
if( success ){
|
if( success ){
|
||||||
p.messageId = C_ENCHANT_SUCCESS;
|
p.msgId = C_ENCHANT_SUCCESS;
|
||||||
}else{
|
}else{
|
||||||
p.messageId = C_ENCHANT_FAILURE;
|
p.msgId = C_ENCHANT_FAILURE;
|
||||||
}
|
}
|
||||||
p.enchantItemId = enchant;
|
p.ITID = enchant;
|
||||||
|
|
||||||
clif_send( &p, sizeof( p ), &sd.bl, SELF );
|
clif_send( &p, sizeof( p ), &sd.bl, SELF );
|
||||||
|
|
||||||
@ -24253,10 +24241,10 @@ bool clif_parse_enchant_basecheck( struct item& selected_item, std::shared_ptr<s
|
|||||||
}
|
}
|
||||||
|
|
||||||
void clif_parse_enchantwindow_general( int fd, map_session_data* sd ){
|
void clif_parse_enchantwindow_general( int fd, map_session_data* sd ){
|
||||||
#if PACKETVER_RE_NUM >= 20211103 || PACKETVER_MAIN_NUM >= 20220330
|
#if PACKETVER_MAIN_NUM >= 20201118 || PACKETVER_RE_NUM >= 20211103 || PACKETVER_ZERO_NUM >= 20221024
|
||||||
struct PACKET_CZ_REQUEST_RANDOM_ENCHANT *p = (struct PACKET_CZ_REQUEST_RANDOM_ENCHANT*)RFIFOP( fd, 0 );
|
struct PACKET_CZ_REQUEST_RANDOM_ENCHANT *p = (struct PACKET_CZ_REQUEST_RANDOM_ENCHANT*)RFIFOP( fd, 0 );
|
||||||
|
|
||||||
if( sd->state.item_enchant_index != p->clientLuaIndex ){
|
if( sd->state.item_enchant_index != p->enchant_group ){
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -24271,7 +24259,7 @@ void clif_parse_enchantwindow_general( int fd, map_session_data* sd ){
|
|||||||
}
|
}
|
||||||
|
|
||||||
struct item& selected_item = sd->inventory.u.items_inventory[index];
|
struct item& selected_item = sd->inventory.u.items_inventory[index];
|
||||||
std::shared_ptr<s_item_enchant> enchant = item_enchant_db.find( p->clientLuaIndex );
|
std::shared_ptr<s_item_enchant> enchant = item_enchant_db.find( p->enchant_group );
|
||||||
|
|
||||||
if( enchant == nullptr ){
|
if( enchant == nullptr ){
|
||||||
return;
|
return;
|
||||||
@ -24382,10 +24370,10 @@ void clif_parse_enchantwindow_general( int fd, map_session_data* sd ){
|
|||||||
}
|
}
|
||||||
|
|
||||||
void clif_parse_enchantwindow_perfect( int fd, map_session_data* sd ){
|
void clif_parse_enchantwindow_perfect( int fd, map_session_data* sd ){
|
||||||
#if PACKETVER_RE_NUM >= 20211103 || PACKETVER_MAIN_NUM >= 20220330
|
#if PACKETVER_MAIN_NUM >= 20201118 || PACKETVER_RE_NUM >= 20211103 || PACKETVER_ZERO_NUM >= 20221024
|
||||||
struct PACKET_CZ_REQUEST_PERFECT_ENCHANT *p = (struct PACKET_CZ_REQUEST_PERFECT_ENCHANT*)RFIFOP( fd, 0 );
|
struct PACKET_CZ_REQUEST_PERFECT_ENCHANT *p = (struct PACKET_CZ_REQUEST_PERFECT_ENCHANT*)RFIFOP( fd, 0 );
|
||||||
|
|
||||||
if( sd->state.item_enchant_index != p->clientLuaIndex ){
|
if( sd->state.item_enchant_index != p->enchant_group ){
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -24400,7 +24388,7 @@ void clif_parse_enchantwindow_perfect( int fd, map_session_data* sd ){
|
|||||||
}
|
}
|
||||||
|
|
||||||
struct item& selected_item = sd->inventory.u.items_inventory[index];
|
struct item& selected_item = sd->inventory.u.items_inventory[index];
|
||||||
std::shared_ptr<s_item_enchant> enchant = item_enchant_db.find( p->clientLuaIndex );
|
std::shared_ptr<s_item_enchant> enchant = item_enchant_db.find( p->enchant_group );
|
||||||
|
|
||||||
if( enchant == nullptr ){
|
if( enchant == nullptr ){
|
||||||
return;
|
return;
|
||||||
@ -24433,7 +24421,7 @@ void clif_parse_enchantwindow_perfect( int fd, map_session_data* sd ){
|
|||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
std::shared_ptr<s_item_enchant_perfect> perfect_enchant = util::umap_find( enchant_slot->perfect.enchants, p->itemId );
|
std::shared_ptr<s_item_enchant_perfect> perfect_enchant = util::umap_find( enchant_slot->perfect.enchants, p->ITID );
|
||||||
|
|
||||||
if( perfect_enchant == nullptr ){
|
if( perfect_enchant == nullptr ){
|
||||||
return;
|
return;
|
||||||
@ -24482,10 +24470,10 @@ void clif_parse_enchantwindow_perfect( int fd, map_session_data* sd ){
|
|||||||
}
|
}
|
||||||
|
|
||||||
void clif_parse_enchantwindow_upgrade( int fd, map_session_data* sd ){
|
void clif_parse_enchantwindow_upgrade( int fd, map_session_data* sd ){
|
||||||
#if PACKETVER_RE_NUM >= 20211103 || PACKETVER_MAIN_NUM >= 20220330
|
#if PACKETVER_MAIN_NUM >= 20201118 || PACKETVER_RE_NUM >= 20211103 || PACKETVER_ZERO_NUM >= 20221024
|
||||||
struct PACKET_CZ_REQUEST_UPGRADE_ENCHANT *p = (struct PACKET_CZ_REQUEST_UPGRADE_ENCHANT*)RFIFOP( fd, 0 );
|
struct PACKET_CZ_REQUEST_UPGRADE_ENCHANT *p = (struct PACKET_CZ_REQUEST_UPGRADE_ENCHANT*)RFIFOP( fd, 0 );
|
||||||
|
|
||||||
if( sd->state.item_enchant_index != p->clientLuaIndex ){
|
if( sd->state.item_enchant_index != p->enchant_group ){
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -24500,7 +24488,7 @@ void clif_parse_enchantwindow_upgrade( int fd, map_session_data* sd ){
|
|||||||
}
|
}
|
||||||
|
|
||||||
struct item& selected_item = sd->inventory.u.items_inventory[index];
|
struct item& selected_item = sd->inventory.u.items_inventory[index];
|
||||||
std::shared_ptr<s_item_enchant> enchant = item_enchant_db.find( p->clientLuaIndex );
|
std::shared_ptr<s_item_enchant> enchant = item_enchant_db.find( p->enchant_group );
|
||||||
|
|
||||||
if( enchant == nullptr ){
|
if( enchant == nullptr ){
|
||||||
return;
|
return;
|
||||||
@ -24579,10 +24567,10 @@ void clif_parse_enchantwindow_upgrade( int fd, map_session_data* sd ){
|
|||||||
}
|
}
|
||||||
|
|
||||||
void clif_parse_enchantwindow_reset( int fd, map_session_data* sd ){
|
void clif_parse_enchantwindow_reset( int fd, map_session_data* sd ){
|
||||||
#if PACKETVER_RE_NUM >= 20211103 || PACKETVER_MAIN_NUM >= 20220330
|
#if PACKETVER_MAIN_NUM >= 20201118 || PACKETVER_RE_NUM >= 20211103 || PACKETVER_ZERO_NUM >= 20221024
|
||||||
struct PACKET_CZ_REQUEST_RESET_ENCHANT *p = (struct PACKET_CZ_REQUEST_RESET_ENCHANT*)RFIFOP( fd, 0 );
|
struct PACKET_CZ_REQUEST_RESET_ENCHANT *p = (struct PACKET_CZ_REQUEST_RESET_ENCHANT*)RFIFOP( fd, 0 );
|
||||||
|
|
||||||
if( sd->state.item_enchant_index != p->clientLuaIndex ){
|
if( sd->state.item_enchant_index != p->enchant_group ){
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -24610,7 +24598,7 @@ void clif_parse_enchantwindow_reset( int fd, map_session_data* sd ){
|
|||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
std::shared_ptr<s_item_enchant> enchant = item_enchant_db.find( p->clientLuaIndex );
|
std::shared_ptr<s_item_enchant> enchant = item_enchant_db.find( p->enchant_group );
|
||||||
|
|
||||||
if( enchant == nullptr ){
|
if( enchant == nullptr ){
|
||||||
return;
|
return;
|
||||||
@ -24697,7 +24685,7 @@ void clif_parse_enchantwindow_reset( int fd, map_session_data* sd ){
|
|||||||
}
|
}
|
||||||
|
|
||||||
void clif_parse_enchantwindow_close( int fd, map_session_data* sd ){
|
void clif_parse_enchantwindow_close( int fd, map_session_data* sd ){
|
||||||
#if PACKETVER_RE_NUM >= 20211103 || PACKETVER_MAIN_NUM >= 20220330
|
#if PACKETVER_MAIN_NUM >= 20201118 || PACKETVER_RE_NUM >= 20211103 || PACKETVER_ZERO_NUM >= 20221024
|
||||||
sd->state.item_enchant_index = 0;
|
sd->state.item_enchant_index = 0;
|
||||||
#endif
|
#endif
|
||||||
}
|
}
|
||||||
@ -25066,7 +25054,7 @@ void clif_dynamicnpc_result( map_session_data& sd, e_dynamicnpc_result result ){
|
|||||||
#if PACKETVER_MAIN_NUM >= 20140430 || PACKETVER_RE_NUM >= 20140430 || defined(PACKETVER_ZERO)
|
#if PACKETVER_MAIN_NUM >= 20140430 || PACKETVER_RE_NUM >= 20140430 || defined(PACKETVER_ZERO)
|
||||||
struct PACKET_ZC_DYNAMICNPC_CREATE_RESULT p = {};
|
struct PACKET_ZC_DYNAMICNPC_CREATE_RESULT p = {};
|
||||||
|
|
||||||
p.packetType = HEADER_ZC_DYNAMICNPC_CREATE_RESULT;
|
p.PacketType = HEADER_ZC_DYNAMICNPC_CREATE_RESULT;
|
||||||
p.result = result;
|
p.result = result;
|
||||||
|
|
||||||
clif_send( &p, sizeof( p ), &sd.bl, SELF );
|
clif_send( &p, sizeof( p ), &sd.bl, SELF );
|
||||||
@ -25193,6 +25181,12 @@ void clif_parse_partybooking_reply( int fd, map_session_data* sd ){
|
|||||||
#endif
|
#endif
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void clif_parse_reset_skill( int fd, map_session_data* sd ){
|
||||||
|
#if PACKETVER_MAIN_NUM >= 20220216 || PACKETVER_ZERO_NUM >= 20220203
|
||||||
|
PACKET_CZ_RESET_SKILL* p = (PACKET_CZ_RESET_SKILL*)RFIFOP( fd, 0 );
|
||||||
|
#endif
|
||||||
|
}
|
||||||
|
|
||||||
/*==========================================
|
/*==========================================
|
||||||
* Main client packet processing function
|
* Main client packet processing function
|
||||||
*------------------------------------------*/
|
*------------------------------------------*/
|
||||||
|
|||||||
@ -1015,7 +1015,7 @@ void clif_Auction_message(int fd, unsigned char flag);
|
|||||||
void clif_Auction_close(int fd, unsigned char flag);
|
void clif_Auction_close(int fd, unsigned char flag);
|
||||||
void clif_parse_Auction_cancelreg(int fd, map_session_data *sd);
|
void clif_parse_Auction_cancelreg(int fd, map_session_data *sd);
|
||||||
|
|
||||||
void clif_bossmapinfo(map_session_data *sd, struct mob_data *md, enum e_bossmap_info flag);
|
void clif_bossmapinfo( map_session_data& sd, mob_data* md, e_bossmap_info flag );
|
||||||
void clif_cashshop_show(map_session_data *sd, struct npc_data *nd);
|
void clif_cashshop_show(map_session_data *sd, struct npc_data *nd);
|
||||||
|
|
||||||
// ADOPTION
|
// ADOPTION
|
||||||
|
|||||||
@ -2425,13 +2425,8 @@
|
|||||||
parseable_packet( HEADER_CZ_GRADE_ENCHANT_CLOSE_UI, sizeof( struct PACKET_CZ_GRADE_ENCHANT_CLOSE_UI ), clif_parse_enchantgrade_close, 0 );
|
parseable_packet( HEADER_CZ_GRADE_ENCHANT_CLOSE_UI, sizeof( struct PACKET_CZ_GRADE_ENCHANT_CLOSE_UI ), clif_parse_enchantgrade_close, 0 );
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
#if PACKETVER_RE_NUM >= 20211103 || PACKETVER_ZERO_NUM >= 20210818 || PACKETVER_MAIN_NUM >= 20220330
|
|
||||||
parseable_packet( HEADER_CZ_CHECKNAME2, sizeof( struct PACKET_CZ_CHECKNAME2 ), clif_parse_Mail_Receiver_Check, 0 );
|
#if PACKETVER_MAIN_NUM >= 20201118 || PACKETVER_RE_NUM >= 20211103 || PACKETVER_ZERO_NUM >= 20221024
|
||||||
parseable_packet( HEADER_CZ_UNCONFIRMED_RODEX_RETURN, sizeof( struct PACKET_CZ_UNCONFIRMED_RODEX_RETURN ), clif_parse_Mail_return, 0 );
|
|
||||||
parseable_packet( HEADER_CZ_REQ_TAKEOFF_EQUIP_ALL, sizeof( struct PACKET_CZ_REQ_TAKEOFF_EQUIP_ALL ), clif_parse_unequipall, 0 );
|
|
||||||
parseable_packet( 0xb93, 12, clif_parse_dull, 0 );
|
|
||||||
parseable_packet( HEADER_CZ_CLOSE_REFORM_UI, sizeof( struct PACKET_CZ_CLOSE_REFORM_UI ), clif_parse_item_reform_close, 0 );
|
|
||||||
parseable_packet( HEADER_CZ_ITEM_REFORM, sizeof( struct PACKET_CZ_ITEM_REFORM ), clif_parse_item_reform_start, 0 );
|
|
||||||
parseable_packet( HEADER_CZ_REQUEST_RANDOM_ENCHANT, sizeof( struct PACKET_CZ_REQUEST_RANDOM_ENCHANT ), clif_parse_enchantwindow_general, 0 );
|
parseable_packet( HEADER_CZ_REQUEST_RANDOM_ENCHANT, sizeof( struct PACKET_CZ_REQUEST_RANDOM_ENCHANT ), clif_parse_enchantwindow_general, 0 );
|
||||||
parseable_packet( HEADER_CZ_REQUEST_PERFECT_ENCHANT, sizeof( struct PACKET_CZ_REQUEST_PERFECT_ENCHANT ), clif_parse_enchantwindow_perfect, 0 );
|
parseable_packet( HEADER_CZ_REQUEST_PERFECT_ENCHANT, sizeof( struct PACKET_CZ_REQUEST_PERFECT_ENCHANT ), clif_parse_enchantwindow_perfect, 0 );
|
||||||
parseable_packet( HEADER_CZ_REQUEST_UPGRADE_ENCHANT, sizeof( struct PACKET_CZ_REQUEST_UPGRADE_ENCHANT ), clif_parse_enchantwindow_upgrade, 0 );
|
parseable_packet( HEADER_CZ_REQUEST_UPGRADE_ENCHANT, sizeof( struct PACKET_CZ_REQUEST_UPGRADE_ENCHANT ), clif_parse_enchantwindow_upgrade, 0 );
|
||||||
@ -2439,6 +2434,18 @@
|
|||||||
parseable_packet( HEADER_CZ_CLOSE_UI_ENCHANT, sizeof( struct PACKET_CZ_CLOSE_UI_ENCHANT ), clif_parse_enchantwindow_close, 0 );
|
parseable_packet( HEADER_CZ_CLOSE_UI_ENCHANT, sizeof( struct PACKET_CZ_CLOSE_UI_ENCHANT ), clif_parse_enchantwindow_close, 0 );
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
#if PACKETVER_RE_NUM >= 20211103 || PACKETVER_ZERO_NUM >= 20210818 || PACKETVER_MAIN_NUM >= 20220330
|
||||||
|
parseable_packet( HEADER_CZ_CHECKNAME2, sizeof( struct PACKET_CZ_CHECKNAME2 ), clif_parse_Mail_Receiver_Check, 0 );
|
||||||
|
parseable_packet( HEADER_CZ_UNCONFIRMED_RODEX_RETURN, sizeof( struct PACKET_CZ_UNCONFIRMED_RODEX_RETURN ), clif_parse_Mail_return, 0 );
|
||||||
|
parseable_packet( HEADER_CZ_REQ_TAKEOFF_EQUIP_ALL, sizeof( struct PACKET_CZ_REQ_TAKEOFF_EQUIP_ALL ), clif_parse_unequipall, 0 );
|
||||||
|
parseable_packet( 0xb93, 12, clif_parse_dull, 0 );
|
||||||
|
#endif
|
||||||
|
|
||||||
|
#if PACKETVER_MAIN_NUM >= 20200916 || PACKETVER_RE_NUM >= 20211103 || PACKETVER_ZERO_NUM >= 20221024
|
||||||
|
parseable_packet( HEADER_CZ_CLOSE_REFORM_UI, sizeof( struct PACKET_CZ_CLOSE_REFORM_UI ), clif_parse_item_reform_close, 0 );
|
||||||
|
parseable_packet( HEADER_CZ_ITEM_REFORM, sizeof( struct PACKET_CZ_ITEM_REFORM ), clif_parse_item_reform_start, 0 );
|
||||||
|
#endif
|
||||||
|
|
||||||
#if PACKETVER_MAIN_NUM >= 20220216
|
#if PACKETVER_MAIN_NUM >= 20220216
|
||||||
parseable_packet( HEADER_CZ_APPROXIMATE_ACTOR, sizeof( struct PACKET_CZ_APPROXIMATE_ACTOR ), clif_parse_dull, 0 );
|
parseable_packet( HEADER_CZ_APPROXIMATE_ACTOR, sizeof( struct PACKET_CZ_APPROXIMATE_ACTOR ), clif_parse_dull, 0 );
|
||||||
#endif
|
#endif
|
||||||
@ -2447,4 +2454,8 @@
|
|||||||
parseable_packet( HEADER_CZ_USE_PACKAGEITEM, sizeof( struct PACKET_CZ_USE_PACKAGEITEM ), clif_parse_itempackage_select, 0 );
|
parseable_packet( HEADER_CZ_USE_PACKAGEITEM, sizeof( struct PACKET_CZ_USE_PACKAGEITEM ), clif_parse_itempackage_select, 0 );
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
#if PACKETVER_MAIN_NUM >= 20220216 || PACKETVER_ZERO_NUM >= 20220203
|
||||||
|
parseable_packet( HEADER_CZ_RESET_SKILL, sizeof( struct PACKET_CZ_RESET_SKILL ), clif_parse_reset_skill, 0 );
|
||||||
|
#endif
|
||||||
|
|
||||||
#endif /* CLIF_PACKETDB_HPP */
|
#endif /* CLIF_PACKETDB_HPP */
|
||||||
|
|||||||
@ -514,23 +514,16 @@ static int elemental_ai_sub_timer_activesearch(block_list *bl, va_list ap) {
|
|||||||
if( battle_check_target(&ed->bl,bl,BCT_ENEMY) <= 0 )
|
if( battle_check_target(&ed->bl,bl,BCT_ENEMY) <= 0 )
|
||||||
return 0;
|
return 0;
|
||||||
|
|
||||||
int dist;
|
if (bl->type == BL_PC && !map_flag_vs(ed->bl.m))
|
||||||
|
return 0;
|
||||||
switch( bl->type ) {
|
int dist = distance_bl(&ed->bl, bl);
|
||||||
case BL_PC:
|
if( ((*target) == nullptr || !check_distance_bl(&ed->bl, *target, dist)) && battle_check_range(&ed->bl,bl,ed->db->range2) ) { //Pick closest target?
|
||||||
if( !map_flag_vs(ed->bl.m) )
|
(*target) = bl;
|
||||||
return 0;
|
ed->target_id = bl->id;
|
||||||
default:
|
ed->min_chase = dist + ed->db->range3;
|
||||||
dist = distance_bl(&ed->bl, bl);
|
if( ed->min_chase > AREA_SIZE )
|
||||||
if( ((*target) == NULL || !check_distance_bl(&ed->bl, *target, dist)) && battle_check_range(&ed->bl,bl,ed->db->range2) ) { //Pick closest target?
|
ed->min_chase = AREA_SIZE;
|
||||||
(*target) = bl;
|
return 1;
|
||||||
ed->target_id = bl->id;
|
|
||||||
ed->min_chase = dist + ed->db->range3;
|
|
||||||
if( ed->min_chase > AREA_SIZE )
|
|
||||||
ed->min_chase = AREA_SIZE;
|
|
||||||
return 1;
|
|
||||||
}
|
|
||||||
break;
|
|
||||||
}
|
}
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|||||||
@ -2954,11 +2954,11 @@ static void itemdb_pc_get_itemgroup_sub(map_session_data *sd, bool identify, std
|
|||||||
|
|
||||||
if( itemdb_isequip( data->nameid ) ){
|
if( itemdb_isequip( data->nameid ) ){
|
||||||
if( data->refineMinimum > 0 && data->refineMaximum > 0 ){
|
if( data->refineMinimum > 0 && data->refineMaximum > 0 ){
|
||||||
tmp.refine = rnd_value( data->refineMinimum, data->refineMaximum );
|
tmp.refine = static_cast<uint8>( rnd_value<uint16>( data->refineMinimum, data->refineMaximum ) );
|
||||||
}else if( data->refineMinimum > 0 ){
|
}else if( data->refineMinimum > 0 ){
|
||||||
tmp.refine = rnd_value<uint16>( data->refineMinimum, MAX_REFINE );
|
tmp.refine = static_cast<uint8>( rnd_value<uint16>( data->refineMinimum, MAX_REFINE ) );
|
||||||
}else if( data->refineMaximum > 0 ){
|
}else if( data->refineMaximum > 0 ){
|
||||||
tmp.refine = rnd_value<uint16>( 1, data->refineMaximum );
|
tmp.refine = static_cast<uint8>( rnd_value<uint16>( 1, data->refineMaximum ) );
|
||||||
}else{
|
}else{
|
||||||
tmp.refine = 0;
|
tmp.refine = 0;
|
||||||
}
|
}
|
||||||
@ -4290,7 +4290,7 @@ uint64 RandomOptionDatabase::parseBodyNode(const ryml::NodeRef& node) {
|
|||||||
return 0;
|
return 0;
|
||||||
|
|
||||||
if (randopt->script) {
|
if (randopt->script) {
|
||||||
aFree(randopt->script);
|
script_free_code( randopt->script );
|
||||||
randopt->script = nullptr;
|
randopt->script = nullptr;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@ -95,7 +95,7 @@ char guild_storage_log_table[32] = "guild_storage_log";
|
|||||||
|
|
||||||
// log database
|
// log database
|
||||||
std::string log_db_ip = "127.0.0.1";
|
std::string log_db_ip = "127.0.0.1";
|
||||||
int log_db_port = 3306;
|
uint16 log_db_port = 3306;
|
||||||
std::string log_db_id = "ragnarok";
|
std::string log_db_id = "ragnarok";
|
||||||
std::string log_db_pw = "";
|
std::string log_db_pw = "";
|
||||||
std::string log_db_db = "log";
|
std::string log_db_db = "log";
|
||||||
@ -349,7 +349,7 @@ int map_addblock(struct block_list* bl)
|
|||||||
|
|
||||||
struct map_data *mapdata = map_getmapdata(m);
|
struct map_data *mapdata = map_getmapdata(m);
|
||||||
|
|
||||||
if (mapdata->cell == nullptr) // Player warped to a freed map. Stop them!
|
if (mapdata == nullptr || mapdata->cell == nullptr) // Player warped to a freed map. Stop them!
|
||||||
return 1;
|
return 1;
|
||||||
|
|
||||||
if( x < 0 || x >= mapdata->xs || y < 0 || y >= mapdata->ys )
|
if( x < 0 || x >= mapdata->xs || y < 0 || y >= mapdata->ys )
|
||||||
@ -402,6 +402,8 @@ int map_delblock(struct block_list* bl)
|
|||||||
|
|
||||||
struct map_data *mapdata = map_getmapdata(bl->m);
|
struct map_data *mapdata = map_getmapdata(bl->m);
|
||||||
|
|
||||||
|
nullpo_ret(mapdata);
|
||||||
|
|
||||||
pos = bl->x/BLOCK_SIZE+(bl->y/BLOCK_SIZE)*mapdata->bxs;
|
pos = bl->x/BLOCK_SIZE+(bl->y/BLOCK_SIZE)*mapdata->bxs;
|
||||||
|
|
||||||
if (bl->next)
|
if (bl->next)
|
||||||
@ -409,8 +411,10 @@ int map_delblock(struct block_list* bl)
|
|||||||
if (bl->prev == &bl_head) {
|
if (bl->prev == &bl_head) {
|
||||||
//Since the head of the list, update the block_list map of []
|
//Since the head of the list, update the block_list map of []
|
||||||
if (bl->type == BL_MOB) {
|
if (bl->type == BL_MOB) {
|
||||||
|
nullpo_ret(mapdata->block_mob);
|
||||||
mapdata->block_mob[pos] = bl->next;
|
mapdata->block_mob[pos] = bl->next;
|
||||||
} else {
|
} else {
|
||||||
|
nullpo_ret(mapdata->block);
|
||||||
mapdata->block[pos] = bl->next;
|
mapdata->block[pos] = bl->next;
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
@ -434,6 +438,8 @@ int map_delblock(struct block_list* bl)
|
|||||||
*/
|
*/
|
||||||
int map_moveblock(struct block_list *bl, int x1, int y1, t_tick tick)
|
int map_moveblock(struct block_list *bl, int x1, int y1, t_tick tick)
|
||||||
{
|
{
|
||||||
|
nullpo_ret(bl);
|
||||||
|
|
||||||
int x0 = bl->x, y0 = bl->y;
|
int x0 = bl->x, y0 = bl->y;
|
||||||
status_change *sc = NULL;
|
status_change *sc = NULL;
|
||||||
int moveblock = ( x0/BLOCK_SIZE != x1/BLOCK_SIZE || y0/BLOCK_SIZE != y1/BLOCK_SIZE);
|
int moveblock = ( x0/BLOCK_SIZE != x1/BLOCK_SIZE || y0/BLOCK_SIZE != y1/BLOCK_SIZE);
|
||||||
@ -763,9 +769,9 @@ int map_foreachinareaV(int(*func)(struct block_list*, va_list), int16 m, int16 x
|
|||||||
return 0;
|
return 0;
|
||||||
|
|
||||||
if (x1 < x0)
|
if (x1 < x0)
|
||||||
SWAP(x0, x1);
|
std::swap(x0, x1);
|
||||||
if (y1 < y0)
|
if (y1 < y0)
|
||||||
SWAP(y0, y1);
|
std::swap(y0, y1);
|
||||||
|
|
||||||
struct map_data *mapdata = map_getmapdata(m);
|
struct map_data *mapdata = map_getmapdata(m);
|
||||||
|
|
||||||
@ -942,9 +948,9 @@ int map_forcountinarea(int (*func)(struct block_list*,va_list), int16 m, int16 x
|
|||||||
return 0;
|
return 0;
|
||||||
|
|
||||||
if ( x1 < x0 )
|
if ( x1 < x0 )
|
||||||
SWAP(x0, x1);
|
std::swap(x0, x1);
|
||||||
if ( y1 < y0 )
|
if ( y1 < y0 )
|
||||||
SWAP(y0, y1);
|
std::swap(y0, y1);
|
||||||
|
|
||||||
struct map_data *mapdata = map_getmapdata(m);
|
struct map_data *mapdata = map_getmapdata(m);
|
||||||
|
|
||||||
@ -1021,9 +1027,9 @@ int map_foreachinmovearea(int (*func)(struct block_list*,va_list), struct block_
|
|||||||
y1 = center->y + range;
|
y1 = center->y + range;
|
||||||
|
|
||||||
if ( x1 < x0 )
|
if ( x1 < x0 )
|
||||||
SWAP(x0, x1);
|
std::swap(x0, x1);
|
||||||
if ( y1 < y0 )
|
if ( y1 < y0 )
|
||||||
SWAP(y0, y1);
|
std::swap(y0, y1);
|
||||||
|
|
||||||
if( dx == 0 || dy == 0 ) {
|
if( dx == 0 || dy == 0 ) {
|
||||||
//Movement along one axis only.
|
//Movement along one axis only.
|
||||||
@ -1254,9 +1260,9 @@ int map_foreachinpath(int (*func)(struct block_list*,va_list),int16 m,int16 x0,i
|
|||||||
|
|
||||||
//The two fors assume mx0 < mx1 && my0 < my1
|
//The two fors assume mx0 < mx1 && my0 < my1
|
||||||
if ( mx0 > mx1 )
|
if ( mx0 > mx1 )
|
||||||
SWAP(mx0, mx1);
|
std::swap(mx0, mx1);
|
||||||
if ( my0 > my1 )
|
if ( my0 > my1 )
|
||||||
SWAP(my0, my1);
|
std::swap(my0, my1);
|
||||||
|
|
||||||
struct map_data *mapdata = map_getmapdata(m);
|
struct map_data *mapdata = map_getmapdata(m);
|
||||||
|
|
||||||
@ -1416,9 +1422,9 @@ int map_foreachindir(int(*func)(struct block_list*, va_list), int16 m, int16 x0,
|
|||||||
|
|
||||||
//The following assumes mx0 < mx1 && my0 < my1
|
//The following assumes mx0 < mx1 && my0 < my1
|
||||||
if (mx0 > mx1)
|
if (mx0 > mx1)
|
||||||
SWAP(mx0, mx1);
|
std::swap(mx0, mx1);
|
||||||
if (my0 > my1)
|
if (my0 > my1)
|
||||||
SWAP(my0, my1);
|
std::swap(my0, my1);
|
||||||
|
|
||||||
//Apply width to the path by turning 90 degrees
|
//Apply width to the path by turning 90 degrees
|
||||||
mx0 -= abs( range * dirx[( dir + 2 ) % DIR_MAX] );
|
mx0 -= abs( range * dirx[( dir + 2 ) % DIR_MAX] );
|
||||||
@ -4189,7 +4195,7 @@ int inter_config_read(const char *cfgName)
|
|||||||
log_db_pw = w2;
|
log_db_pw = w2;
|
||||||
else
|
else
|
||||||
if(strcmpi(w1,"log_db_port")==0)
|
if(strcmpi(w1,"log_db_port")==0)
|
||||||
log_db_port = atoi(w2);
|
log_db_port = (uint16)strtoul( w2, nullptr, 10 );
|
||||||
else
|
else
|
||||||
if(strcmpi(w1,"log_db_db")==0)
|
if(strcmpi(w1,"log_db_db")==0)
|
||||||
log_db_db = w2;
|
log_db_db = w2;
|
||||||
@ -4274,7 +4280,7 @@ int log_sql_init(void)
|
|||||||
|
|
||||||
ShowInfo("" CL_WHITE "[SQL]" CL_RESET ": Connecting to the Log Database " CL_WHITE "%s" CL_RESET " At " CL_WHITE "%s" CL_RESET "...\n",log_db_db.c_str(), log_db_ip.c_str());
|
ShowInfo("" CL_WHITE "[SQL]" CL_RESET ": Connecting to the Log Database " CL_WHITE "%s" CL_RESET " At " CL_WHITE "%s" CL_RESET "...\n",log_db_db.c_str(), log_db_ip.c_str());
|
||||||
if ( SQL_ERROR == Sql_Connect(logmysql_handle, log_db_id.c_str(), log_db_pw.c_str(), log_db_ip.c_str(), log_db_port, log_db_db.c_str()) ){
|
if ( SQL_ERROR == Sql_Connect(logmysql_handle, log_db_id.c_str(), log_db_pw.c_str(), log_db_ip.c_str(), log_db_port, log_db_db.c_str()) ){
|
||||||
ShowError("Couldn't connect with uname='%s',host='%s',port='%d',database='%s'\n",
|
ShowError("Couldn't connect with uname='%s',host='%s',port='%hu',database='%s'\n",
|
||||||
log_db_id.c_str(), log_db_ip.c_str(), log_db_port, log_db_db.c_str());
|
log_db_id.c_str(), log_db_ip.c_str(), log_db_port, log_db_db.c_str());
|
||||||
Sql_ShowDebug(logmysql_handle);
|
Sql_ShowDebug(logmysql_handle);
|
||||||
Sql_Free(logmysql_handle);
|
Sql_Free(logmysql_handle);
|
||||||
|
|||||||
@ -66,7 +66,7 @@ void map_msg_reload(void);
|
|||||||
#define NATURAL_HEAL_INTERVAL 500
|
#define NATURAL_HEAL_INTERVAL 500
|
||||||
#define MIN_FLOORITEM 2
|
#define MIN_FLOORITEM 2
|
||||||
#define MAX_FLOORITEM START_ACCOUNT_NUM
|
#define MAX_FLOORITEM START_ACCOUNT_NUM
|
||||||
#define MAX_LEVEL 250
|
#define MAX_LEVEL 260
|
||||||
#define MAX_DROP_PER_MAP 48
|
#define MAX_DROP_PER_MAP 48
|
||||||
#define MAX_IGNORE_LIST 20 // official is 14
|
#define MAX_IGNORE_LIST 20 // official is 14
|
||||||
#define MAX_VENDING 12
|
#define MAX_VENDING 12
|
||||||
|
|||||||
@ -726,9 +726,9 @@ int mob_once_spawn_area(map_session_data* sd, int16 m, int16 x0, int16 y0, int16
|
|||||||
|
|
||||||
// normalize x/y coordinates
|
// normalize x/y coordinates
|
||||||
if (x0 > x1)
|
if (x0 > x1)
|
||||||
SWAP(x0, x1);
|
std::swap(x0, x1);
|
||||||
if (y0 > y1)
|
if (y0 > y1)
|
||||||
SWAP(y0, y1);
|
std::swap(y0, y1);
|
||||||
|
|
||||||
// choose a suitable max. number of attempts
|
// choose a suitable max. number of attempts
|
||||||
max = (y1 - y0 + 1)*(x1 - x0 + 1)*3;
|
max = (y1 - y0 + 1)*(x1 - x0 + 1)*3;
|
||||||
@ -1281,37 +1281,33 @@ static int mob_ai_sub_hard_activesearch(struct block_list *bl,va_list ap)
|
|||||||
if(battle_check_target(&md->bl,bl,BCT_ENEMY)<=0)
|
if(battle_check_target(&md->bl,bl,BCT_ENEMY)<=0)
|
||||||
return 0;
|
return 0;
|
||||||
|
|
||||||
switch (bl->type)
|
if (bl->type == BL_PC && BL_CAST(BL_PC, bl)->state.gangsterparadise &&
|
||||||
{
|
!status_has_mode(&md->status,MD_STATUSIMMUNE))
|
||||||
case BL_PC:
|
return 0; //Gangster paradise protection.
|
||||||
if (((TBL_PC*)bl)->state.gangsterparadise &&
|
|
||||||
!status_has_mode(&md->status,MD_STATUSIMMUNE))
|
|
||||||
return 0; //Gangster paradise protection.
|
|
||||||
default:
|
|
||||||
if (battle_config.hom_setting&HOMSET_FIRST_TARGET &&
|
|
||||||
(*target) && (*target)->type == BL_HOM && bl->type != BL_HOM)
|
|
||||||
return 0; //For some reason Homun targets are never overriden.
|
|
||||||
|
|
||||||
dist = distance_bl(&md->bl, bl);
|
if (battle_config.hom_setting&HOMSET_FIRST_TARGET &&
|
||||||
if(
|
(*target) != nullptr && (*target)->type == BL_HOM && bl->type != BL_HOM)
|
||||||
((*target) == NULL || !check_distance_bl(&md->bl, *target, dist)) &&
|
return 0; //For some reason Homun targets are never overriden.
|
||||||
battle_check_range(&md->bl,bl,md->db->range2)
|
|
||||||
) { //Pick closest target?
|
dist = distance_bl(&md->bl, bl);
|
||||||
|
if(
|
||||||
|
((*target) == nullptr || !check_distance_bl(&md->bl, *target, dist)) &&
|
||||||
|
battle_check_range(&md->bl,bl,md->db->range2)
|
||||||
|
) { //Pick closest target?
|
||||||
#ifdef ACTIVEPATHSEARCH
|
#ifdef ACTIVEPATHSEARCH
|
||||||
struct walkpath_data wpd;
|
struct walkpath_data wpd;
|
||||||
if (!path_search(&wpd, md->bl.m, md->bl.x, md->bl.y, bl->x, bl->y, 0, CELL_CHKWALL)) // Count walk path cells
|
if (!path_search(&wpd, md->bl.m, md->bl.x, md->bl.y, bl->x, bl->y, 0, CELL_CHKWALL)) // Count walk path cells
|
||||||
return 0;
|
return 0;
|
||||||
//Standing monsters use range2, walking monsters use range3
|
//Standing monsters use range2, walking monsters use range3
|
||||||
if ((md->ud.walktimer == INVALID_TIMER && wpd.path_len > md->db->range2)
|
if ((md->ud.walktimer == INVALID_TIMER && wpd.path_len > md->db->range2)
|
||||||
|| (md->ud.walktimer != INVALID_TIMER && wpd.path_len > md->db->range3))
|
|| (md->ud.walktimer != INVALID_TIMER && wpd.path_len > md->db->range3))
|
||||||
return 0;
|
return 0;
|
||||||
#endif
|
#endif
|
||||||
(*target) = bl;
|
(*target) = bl;
|
||||||
md->target_id=bl->id;
|
md->target_id=bl->id;
|
||||||
md->min_chase = cap_value(dist + md->db->range3 - md->status.rhw.range, md->db->range3, MAX_MINCHASE);
|
md->min_chase = cap_value(dist + md->db->range3 - md->status.rhw.range, md->db->range3, MAX_MINCHASE);
|
||||||
return 1;
|
return 1;
|
||||||
}
|
|
||||||
break;
|
|
||||||
}
|
}
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
@ -1518,6 +1514,7 @@ int mob_unlocktarget(struct mob_data *md, t_tick tick)
|
|||||||
break;
|
break;
|
||||||
//Because it is not unset when the mob finishes walking.
|
//Because it is not unset when the mob finishes walking.
|
||||||
md->state.skillstate = MSS_IDLE;
|
md->state.skillstate = MSS_IDLE;
|
||||||
|
[[fallthrough]];
|
||||||
case MSS_IDLE:
|
case MSS_IDLE:
|
||||||
if( md->ud.walktimer == INVALID_TIMER && md->idle_event[0] && npc_event_do_id( md->idle_event, md->bl.id ) > 0 ){
|
if( md->ud.walktimer == INVALID_TIMER && md->idle_event[0] && npc_event_do_id( md->idle_event, md->bl.id ) > 0 ){
|
||||||
md->idle_event[0] = 0;
|
md->idle_event[0] = 0;
|
||||||
@ -3857,8 +3854,9 @@ int mobskill_use(struct mob_data *md, t_tick tick, int event, int64 damage)
|
|||||||
bl = &md->bl;
|
bl = &md->bl;
|
||||||
if (md->master_id)
|
if (md->master_id)
|
||||||
bl = map_id2bl(md->master_id);
|
bl = map_id2bl(md->master_id);
|
||||||
if (bl) //Otherwise, fall through.
|
if (bl)
|
||||||
break;
|
break;
|
||||||
|
[[fallthrough]];
|
||||||
case MST_FRIEND:
|
case MST_FRIEND:
|
||||||
bl = fbl?fbl:(fmd?&fmd->bl:&md->bl);
|
bl = fbl?fbl:(fmd?&fmd->bl:&md->bl);
|
||||||
break;
|
break;
|
||||||
@ -3907,8 +3905,9 @@ int mobskill_use(struct mob_data *md, t_tick tick, int event, int64 damage)
|
|||||||
bl = &md->bl;
|
bl = &md->bl;
|
||||||
if (md->master_id)
|
if (md->master_id)
|
||||||
bl = map_id2bl(md->master_id);
|
bl = map_id2bl(md->master_id);
|
||||||
if (bl) //Otherwise, fall through.
|
if (bl)
|
||||||
break;
|
break;
|
||||||
|
[[fallthrough]];
|
||||||
case MST_FRIEND:
|
case MST_FRIEND:
|
||||||
if (fbl) {
|
if (fbl) {
|
||||||
bl = fbl;
|
bl = fbl;
|
||||||
@ -3916,7 +3915,8 @@ int mobskill_use(struct mob_data *md, t_tick tick, int event, int64 damage)
|
|||||||
} else if (fmd) {
|
} else if (fmd) {
|
||||||
bl = &fmd->bl;
|
bl = &fmd->bl;
|
||||||
break;
|
break;
|
||||||
} // else fall through
|
}
|
||||||
|
[[fallthrough]];
|
||||||
default:
|
default:
|
||||||
bl = &md->bl;
|
bl = &md->bl;
|
||||||
break;
|
break;
|
||||||
|
|||||||
@ -78,13 +78,11 @@ static enum directions walk_choices [3][3] =
|
|||||||
/// Pushes path_node to the binary node_heap.
|
/// Pushes path_node to the binary node_heap.
|
||||||
/// Ensures there is enough space in array to store new element.
|
/// Ensures there is enough space in array to store new element.
|
||||||
|
|
||||||
#define swap_ptrcast_pathnode(a, b) swap_ptrcast(struct path_node *, a, b)
|
|
||||||
|
|
||||||
static void heap_push_node(struct node_heap *heap, struct path_node *node)
|
static void heap_push_node(struct node_heap *heap, struct path_node *node)
|
||||||
{
|
{
|
||||||
#ifndef __clang_analyzer__ // TODO: Figure out why clang's static analyzer doesn't like this
|
#ifndef __clang_analyzer__ // TODO: Figure out why clang's static analyzer doesn't like this
|
||||||
BHEAP_ENSURE2(*heap, 1, 256, struct path_node **);
|
BHEAP_ENSURE2(*heap, 1, 256, struct path_node **);
|
||||||
BHEAP_PUSH2(*heap, node, NODE_MINTOPCMP, swap_ptrcast_pathnode);
|
BHEAP_PUSH2(*heap, node, NODE_MINTOPCMP);
|
||||||
#endif // __clang_analyzer__
|
#endif // __clang_analyzer__
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -97,7 +95,7 @@ static int heap_update_node(struct node_heap *heap, struct path_node *node)
|
|||||||
ShowError("heap_update_node: node not found\n");
|
ShowError("heap_update_node: node not found\n");
|
||||||
return 1;
|
return 1;
|
||||||
}
|
}
|
||||||
BHEAP_UPDATE(*heap, i, NODE_MINTOPCMP, swap_ptrcast_pathnode);
|
BHEAP_UPDATE(*heap, i, NODE_MINTOPCMP);
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
// end 1:1 copy of definitions from path.cpp
|
// end 1:1 copy of definitions from path.cpp
|
||||||
@ -225,7 +223,7 @@ bool navi_path_search(struct navi_walkpath_data *wpd, const struct navi_pos *fro
|
|||||||
}
|
}
|
||||||
|
|
||||||
current = BHEAP_PEEK(g_open_set); // Look for the lowest f_cost node in the 'open' set
|
current = BHEAP_PEEK(g_open_set); // Look for the lowest f_cost node in the 'open' set
|
||||||
BHEAP_POP2(g_open_set, NODE_MINTOPCMP, swap_ptrcast_pathnode); // Remove it from 'open' set
|
BHEAP_POP2(g_open_set, NODE_MINTOPCMP); // Remove it from 'open' set
|
||||||
|
|
||||||
x = current->x;
|
x = current->x;
|
||||||
y = current->y;
|
y = current->y;
|
||||||
|
|||||||
@ -5159,10 +5159,7 @@ static const char* npc_parse_function(char* w1, char* w2, char* w3, char* w4, co
|
|||||||
struct script_code *oldscript = (struct script_code*)db_data2ptr(&old_data);
|
struct script_code *oldscript = (struct script_code*)db_data2ptr(&old_data);
|
||||||
|
|
||||||
ShowInfo("npc_parse_function: Overwriting user function [%s] (%s:%d)\n", w3, filepath, strline(buffer,start-buffer));
|
ShowInfo("npc_parse_function: Overwriting user function [%s] (%s:%d)\n", w3, filepath, strline(buffer,start-buffer));
|
||||||
script_stop_scriptinstances(oldscript);
|
script_free_code( oldscript );
|
||||||
script_free_vars(oldscript->local.vars);
|
|
||||||
aFree(oldscript->script_buf);
|
|
||||||
aFree(oldscript);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
return end;
|
return end;
|
||||||
|
|||||||
@ -177,19 +177,6 @@ struct PACKET_CZ_GUILD_EMBLEM_CHANGE2 {
|
|||||||
uint32 version;
|
uint32 version;
|
||||||
} __attribute__((packed));
|
} __attribute__((packed));
|
||||||
|
|
||||||
struct PACKET_ZC_CHANGE_GUILD {
|
|
||||||
int16 packetType;
|
|
||||||
#if PACKETVER < 20190724
|
|
||||||
uint32 aid;
|
|
||||||
uint32 guild_id;
|
|
||||||
uint16 emblem_id;
|
|
||||||
#else
|
|
||||||
uint32 guild_id;
|
|
||||||
uint32 emblem_id;
|
|
||||||
uint32 unknown;
|
|
||||||
#endif
|
|
||||||
} __attribute__((packed));
|
|
||||||
|
|
||||||
struct PACKET_ZC_BROADCAST{
|
struct PACKET_ZC_BROADCAST{
|
||||||
int16 packetType;
|
int16 packetType;
|
||||||
int16 PacketLength;
|
int16 PacketLength;
|
||||||
@ -252,69 +239,12 @@ struct PACKET_ZC_REPUTE_INFO{
|
|||||||
struct PACKET_ZC_REPUTE_INFO_sub list[];
|
struct PACKET_ZC_REPUTE_INFO_sub list[];
|
||||||
} __attribute__((packed));
|
} __attribute__((packed));
|
||||||
|
|
||||||
struct PACKET_ZC_OPEN_REFORM_UI{
|
|
||||||
int16 packetType;
|
|
||||||
uint32 itemId;
|
|
||||||
} __attribute__((packed));
|
|
||||||
|
|
||||||
struct PACKET_CZ_CLOSE_REFORM_UI{
|
|
||||||
int16 packetType;
|
|
||||||
} __attribute__((packed));
|
|
||||||
|
|
||||||
struct PACKET_CZ_ITEM_REFORM{
|
|
||||||
int16 packetType;
|
|
||||||
uint32 itemId;
|
|
||||||
uint16 index;
|
|
||||||
} __attribute__((packed));
|
|
||||||
|
|
||||||
struct PACKET_ZC_ITEM_REFORM_ACK{
|
|
||||||
int16 packetType;
|
|
||||||
uint16 index;
|
|
||||||
uint8 result;
|
|
||||||
} __attribute__((packed));
|
|
||||||
|
|
||||||
struct PACKET_ZC_UI_OPEN_V3{
|
struct PACKET_ZC_UI_OPEN_V3{
|
||||||
int16 packetType;
|
int16 packetType;
|
||||||
uint8 type;
|
uint8 type;
|
||||||
uint64 data;
|
uint64 data;
|
||||||
} __attribute__((packed));
|
} __attribute__((packed));
|
||||||
|
|
||||||
struct PACKET_CZ_REQUEST_RANDOM_ENCHANT{
|
|
||||||
int16 packetType;
|
|
||||||
uint64 clientLuaIndex;
|
|
||||||
uint16 index;
|
|
||||||
} __attribute__((packed));
|
|
||||||
|
|
||||||
struct PACKET_CZ_REQUEST_PERFECT_ENCHANT{
|
|
||||||
int16 packetType;
|
|
||||||
uint64 clientLuaIndex;
|
|
||||||
uint16 index;
|
|
||||||
uint32 itemId;
|
|
||||||
} __attribute__((packed));
|
|
||||||
|
|
||||||
struct PACKET_CZ_REQUEST_UPGRADE_ENCHANT{
|
|
||||||
int16 packetType;
|
|
||||||
uint64 clientLuaIndex;
|
|
||||||
uint16 index;
|
|
||||||
uint16 slot;
|
|
||||||
} __attribute__((packed));
|
|
||||||
|
|
||||||
struct PACKET_CZ_REQUEST_RESET_ENCHANT{
|
|
||||||
int16 packetType;
|
|
||||||
uint64 clientLuaIndex;
|
|
||||||
uint16 index;
|
|
||||||
} __attribute__((packed));
|
|
||||||
|
|
||||||
struct PACKET_ZC_RESPONSE_ENCHANT{
|
|
||||||
int16 packetType;
|
|
||||||
uint32 messageId;
|
|
||||||
uint32 enchantItemId;
|
|
||||||
} __attribute__((packed));
|
|
||||||
|
|
||||||
struct PACKET_CZ_CLOSE_UI_ENCHANT{
|
|
||||||
int16 packetType;
|
|
||||||
} __attribute__((packed));
|
|
||||||
|
|
||||||
struct PACKET_ZC_TARGET_SPIRITS {
|
struct PACKET_ZC_TARGET_SPIRITS {
|
||||||
int16 packetType;
|
int16 packetType;
|
||||||
uint32 GID;
|
uint32 GID;
|
||||||
@ -322,14 +252,6 @@ struct PACKET_ZC_TARGET_SPIRITS {
|
|||||||
uint16 amount;
|
uint16 amount;
|
||||||
} __attribute__((packed));
|
} __attribute__((packed));
|
||||||
|
|
||||||
struct PACKET_CZ_USE_PACKAGEITEM{
|
|
||||||
int16 PacketType;
|
|
||||||
uint16 index;
|
|
||||||
uint32 AID;
|
|
||||||
uint32 itemID;
|
|
||||||
uint32 BoxIndex;
|
|
||||||
} __attribute__((packed));
|
|
||||||
|
|
||||||
struct PACKET_ZC_FRIENDS_LIST_sub{
|
struct PACKET_ZC_FRIENDS_LIST_sub{
|
||||||
uint32 AID;
|
uint32 AID;
|
||||||
uint32 CID;
|
uint32 CID;
|
||||||
@ -418,11 +340,6 @@ struct PACKET_ZC_COUPLENAME {
|
|||||||
char name[NAME_LENGTH];
|
char name[NAME_LENGTH];
|
||||||
} __attribute__((packed));
|
} __attribute__((packed));
|
||||||
|
|
||||||
struct PACKET_ZC_DYNAMICNPC_CREATE_RESULT{
|
|
||||||
int16 packetType;
|
|
||||||
int32 result;
|
|
||||||
} __attribute__((packed));
|
|
||||||
|
|
||||||
struct PACKET_CZ_PARTY_REQ_MASTER_TO_JOIN{
|
struct PACKET_CZ_PARTY_REQ_MASTER_TO_JOIN{
|
||||||
int16 packetType;
|
int16 packetType;
|
||||||
uint32 CID;
|
uint32 CID;
|
||||||
@ -481,6 +398,23 @@ struct PACKET_CZ_REQ_MERGE_ITEM{
|
|||||||
uint16 indices[];
|
uint16 indices[];
|
||||||
} __attribute__((packed));
|
} __attribute__((packed));
|
||||||
|
|
||||||
|
struct PACKET_CZ_RESET_SKILL{
|
||||||
|
int16 packetType;
|
||||||
|
uint8 unknown;
|
||||||
|
} __attribute__((packed));
|
||||||
|
|
||||||
|
struct PACKET_ZC_BOSS_INFO{
|
||||||
|
int16 packetType;
|
||||||
|
uint8 type;
|
||||||
|
uint32 x;
|
||||||
|
uint32 y;
|
||||||
|
uint16 minHours;
|
||||||
|
uint16 minMinutes;
|
||||||
|
uint16 maxHours;
|
||||||
|
uint16 maxMinutes;
|
||||||
|
char name[51];
|
||||||
|
} __attribute__((packed));
|
||||||
|
|
||||||
// NetBSD 5 and Solaris don't like pragma pack but accept the packed attribute
|
// NetBSD 5 and Solaris don't like pragma pack but accept the packed attribute
|
||||||
#if !defined( sun ) && ( !defined( __NETBSD__ ) || __NetBSD_Version__ >= 600000000 )
|
#if !defined( sun ) && ( !defined( __NETBSD__ ) || __NetBSD_Version__ >= 600000000 )
|
||||||
#pragma pack( pop )
|
#pragma pack( pop )
|
||||||
@ -502,17 +436,13 @@ DEFINE_PACKET_HEADER(ZC_BROADCAST2, 0x1c3)
|
|||||||
#else
|
#else
|
||||||
DEFINE_PACKET_HEADER(CZ_REQ_ITEMREPAIR, 0x1fd)
|
DEFINE_PACKET_HEADER(CZ_REQ_ITEMREPAIR, 0x1fd)
|
||||||
#endif
|
#endif
|
||||||
#if PACKETVER >= 20190724
|
|
||||||
DEFINE_PACKET_HEADER(ZC_CHANGE_GUILD, 0x0b47)
|
|
||||||
#else
|
|
||||||
DEFINE_PACKET_HEADER(ZC_CHANGE_GUILD, 0x1b4)
|
|
||||||
#endif
|
|
||||||
DEFINE_PACKET_HEADER(ZC_COUPLENAME, 0x1e6);
|
DEFINE_PACKET_HEADER(ZC_COUPLENAME, 0x1e6);
|
||||||
DEFINE_PACKET_HEADER(ZC_FRIENDS_LIST, 0x201)
|
DEFINE_PACKET_HEADER(ZC_FRIENDS_LIST, 0x201)
|
||||||
DEFINE_PACKET_HEADER(ZC_NOTIFY_WEAPONITEMLIST, 0x221)
|
DEFINE_PACKET_HEADER(ZC_NOTIFY_WEAPONITEMLIST, 0x221)
|
||||||
DEFINE_PACKET_HEADER(ZC_ACK_WEAPONREFINE, 0x223)
|
DEFINE_PACKET_HEADER(ZC_ACK_WEAPONREFINE, 0x223)
|
||||||
DEFINE_PACKET_HEADER(CZ_REQ_MAKINGITEM, 0x25b)
|
DEFINE_PACKET_HEADER(CZ_REQ_MAKINGITEM, 0x25b)
|
||||||
DEFINE_PACKET_HEADER(ZC_PC_CASH_POINT_ITEMLIST, 0x287)
|
DEFINE_PACKET_HEADER(ZC_PC_CASH_POINT_ITEMLIST, 0x287)
|
||||||
|
DEFINE_PACKET_HEADER(ZC_BOSS_INFO, 0x293)
|
||||||
DEFINE_PACKET_HEADER(ZC_CASH_TIME_COUNTER, 0x298)
|
DEFINE_PACKET_HEADER(ZC_CASH_TIME_COUNTER, 0x298)
|
||||||
DEFINE_PACKET_HEADER(ZC_CASH_ITEM_DELETE, 0x299)
|
DEFINE_PACKET_HEADER(ZC_CASH_ITEM_DELETE, 0x299)
|
||||||
DEFINE_PACKET_HEADER(ZC_NOTIFY_BIND_ON_EQUIP, 0x2d3)
|
DEFINE_PACKET_HEADER(ZC_NOTIFY_BIND_ON_EQUIP, 0x2d3)
|
||||||
@ -537,7 +467,6 @@ DEFINE_PACKET_HEADER(ZC_ACK_OPEN_BANKING, 0x9b7)
|
|||||||
DEFINE_PACKET_HEADER(ZC_ACK_CLOSE_BANKING, 0x9b9)
|
DEFINE_PACKET_HEADER(ZC_ACK_CLOSE_BANKING, 0x9b9)
|
||||||
DEFINE_PACKET_HEADER(ZC_ACK_COUNT_BARGAIN_SALE_ITEM, 0x9c4)
|
DEFINE_PACKET_HEADER(ZC_ACK_COUNT_BARGAIN_SALE_ITEM, 0x9c4)
|
||||||
DEFINE_PACKET_HEADER(ZC_ACK_GUILDSTORAGE_LOG, 0x9da)
|
DEFINE_PACKET_HEADER(ZC_ACK_GUILDSTORAGE_LOG, 0x9da)
|
||||||
DEFINE_PACKET_HEADER(ZC_DYNAMICNPC_CREATE_RESULT, 0xa17)
|
|
||||||
DEFINE_PACKET_HEADER(CZ_REQ_APPLY_BARGAIN_SALE_ITEM2, 0xa3d)
|
DEFINE_PACKET_HEADER(CZ_REQ_APPLY_BARGAIN_SALE_ITEM2, 0xa3d)
|
||||||
DEFINE_PACKET_HEADER(CZ_REQ_STYLE_CHANGE, 0xa46)
|
DEFINE_PACKET_HEADER(CZ_REQ_STYLE_CHANGE, 0xa46)
|
||||||
DEFINE_PACKET_HEADER(ZC_STYLE_CHANGE_RES, 0xa47)
|
DEFINE_PACKET_HEADER(ZC_STYLE_CHANGE_RES, 0xa47)
|
||||||
@ -557,18 +486,8 @@ DEFINE_PACKET_HEADER(CZ_UNCONFIRMED_RODEX_RETURN, 0xb98)
|
|||||||
DEFINE_PACKET_HEADER(ZC_SUMMON_HP_INIT, 0xb6b)
|
DEFINE_PACKET_HEADER(ZC_SUMMON_HP_INIT, 0xb6b)
|
||||||
DEFINE_PACKET_HEADER(ZC_SUMMON_HP_UPDATE, 0xb6c)
|
DEFINE_PACKET_HEADER(ZC_SUMMON_HP_UPDATE, 0xb6c)
|
||||||
DEFINE_PACKET_HEADER(ZC_REPUTE_INFO, 0x0b8d)
|
DEFINE_PACKET_HEADER(ZC_REPUTE_INFO, 0x0b8d)
|
||||||
DEFINE_PACKET_HEADER(ZC_OPEN_REFORM_UI, 0x0b8f)
|
|
||||||
DEFINE_PACKET_HEADER(CZ_CLOSE_REFORM_UI, 0x0b90)
|
|
||||||
DEFINE_PACKET_HEADER(CZ_ITEM_REFORM, 0x0b91)
|
|
||||||
DEFINE_PACKET_HEADER(ZC_ITEM_REFORM_ACK, 0x0b92)
|
|
||||||
DEFINE_PACKET_HEADER(ZC_UI_OPEN_V3, 0x0b9a)
|
DEFINE_PACKET_HEADER(ZC_UI_OPEN_V3, 0x0b9a)
|
||||||
DEFINE_PACKET_HEADER(CZ_REQUEST_RANDOM_ENCHANT, 0x0b9b)
|
DEFINE_PACKET_HEADER(CZ_RESET_SKILL, 0x0bb1)
|
||||||
DEFINE_PACKET_HEADER(CZ_REQUEST_PERFECT_ENCHANT, 0x0b9c)
|
|
||||||
DEFINE_PACKET_HEADER(CZ_REQUEST_UPGRADE_ENCHANT, 0x0b9d)
|
|
||||||
DEFINE_PACKET_HEADER(CZ_REQUEST_RESET_ENCHANT, 0x0b9e)
|
|
||||||
DEFINE_PACKET_HEADER(ZC_RESPONSE_ENCHANT, 0x0b9f)
|
|
||||||
DEFINE_PACKET_HEADER(CZ_CLOSE_UI_ENCHANT, 0x0ba0)
|
|
||||||
DEFINE_PACKET_HEADER(CZ_USE_PACKAGEITEM, 0x0baf)
|
|
||||||
DEFINE_PACKET_HEADER(CZ_PC_SELL_ITEMLIST, 0x00c9)
|
DEFINE_PACKET_HEADER(CZ_PC_SELL_ITEMLIST, 0x00c9)
|
||||||
|
|
||||||
const int16 MAX_INVENTORY_ITEM_PACKET_NORMAL = ( ( INT16_MAX - ( sizeof( struct packet_itemlist_normal ) - ( sizeof( struct NORMALITEM_INFO ) * MAX_ITEMLIST) ) ) / sizeof( struct NORMALITEM_INFO ) );
|
const int16 MAX_INVENTORY_ITEM_PACKET_NORMAL = ( ( INT16_MAX - ( sizeof( struct packet_itemlist_normal ) - ( sizeof( struct NORMALITEM_INFO ) * MAX_ITEMLIST) ) ) / sizeof( struct NORMALITEM_INFO ) );
|
||||||
|
|||||||
@ -145,7 +145,7 @@ enum packet_headers {
|
|||||||
#else
|
#else
|
||||||
inventorylistnormalType = 0xa3,
|
inventorylistnormalType = 0xa3,
|
||||||
#endif
|
#endif
|
||||||
#if PACKETVER_MAIN_NUM >= 20200916 || PACKETVER_RE_NUM >= 20200723
|
#if PACKETVER_MAIN_NUM >= 20200916 || PACKETVER_RE_NUM >= 20200723 || PACKETVER_ZERO_NUM >= 20221024
|
||||||
inventorylistequipType = 0xb39,
|
inventorylistequipType = 0xb39,
|
||||||
#elif PACKETVER_MAIN_NUM >= 20181002 || PACKETVER_RE_NUM >= 20180912 || PACKETVER_ZERO_NUM >= 20180919
|
#elif PACKETVER_MAIN_NUM >= 20181002 || PACKETVER_RE_NUM >= 20180912 || PACKETVER_ZERO_NUM >= 20180919
|
||||||
inventorylistequipType = 0xb0a,
|
inventorylistequipType = 0xb0a,
|
||||||
@ -171,7 +171,7 @@ enum packet_headers {
|
|||||||
#else
|
#else
|
||||||
storageListNormalType = 0xa5,
|
storageListNormalType = 0xa5,
|
||||||
#endif
|
#endif
|
||||||
#if PACKETVER_MAIN_NUM >= 20200916 || PACKETVER_RE_NUM >= 20200723
|
#if PACKETVER_MAIN_NUM >= 20200916 || PACKETVER_RE_NUM >= 20200723 || PACKETVER_ZERO_NUM >= 20221024
|
||||||
storageListEquipType = 0xb39,
|
storageListEquipType = 0xb39,
|
||||||
#elif PACKETVER_MAIN_NUM >= 20181002 || PACKETVER_RE_NUM >= 20180829 || PACKETVER_ZERO_NUM >= 20180919
|
#elif PACKETVER_MAIN_NUM >= 20181002 || PACKETVER_RE_NUM >= 20180829 || PACKETVER_ZERO_NUM >= 20180919
|
||||||
storageListEquipType = 0xb0a,
|
storageListEquipType = 0xb0a,
|
||||||
@ -197,7 +197,7 @@ enum packet_headers {
|
|||||||
#else
|
#else
|
||||||
cartlistnormalType = 0x123,
|
cartlistnormalType = 0x123,
|
||||||
#endif
|
#endif
|
||||||
#if PACKETVER_MAIN_NUM >= 20200916 || PACKETVER_RE_NUM >= 20200723
|
#if PACKETVER_MAIN_NUM >= 20200916 || PACKETVER_RE_NUM >= 20200723 || PACKETVER_ZERO_NUM >= 20221024
|
||||||
cartlistequipType = 0xb39,
|
cartlistequipType = 0xb39,
|
||||||
#elif PACKETVER_MAIN_NUM >= 20181002 || PACKETVER_RE_NUM >= 20180829 || PACKETVER_ZERO_NUM >= 20180919
|
#elif PACKETVER_MAIN_NUM >= 20181002 || PACKETVER_RE_NUM >= 20180829 || PACKETVER_ZERO_NUM >= 20180919
|
||||||
cartlistequipType = 0xb0a,
|
cartlistequipType = 0xb0a,
|
||||||
@ -211,13 +211,6 @@ enum packet_headers {
|
|||||||
cartlistequipType = 0x297,
|
cartlistequipType = 0x297,
|
||||||
#else
|
#else
|
||||||
cartlistequipType = 0x122,
|
cartlistequipType = 0x122,
|
||||||
#endif
|
|
||||||
#if PACKETVER < 20100105
|
|
||||||
vendinglistType = 0x133,
|
|
||||||
#elif !(PACKETVER_MAIN_NUM >= 20200916 || PACKETVER_RE_NUM >= 20200723)
|
|
||||||
vendinglistType = 0x800,
|
|
||||||
#else
|
|
||||||
vendinglistType = 0xb3d,
|
|
||||||
#endif
|
#endif
|
||||||
openvendingType = 0x136,
|
openvendingType = 0x136,
|
||||||
#if PACKETVER >= 20120925
|
#if PACKETVER >= 20120925
|
||||||
@ -350,9 +343,9 @@ enum packet_headers {
|
|||||||
#endif
|
#endif
|
||||||
};
|
};
|
||||||
|
|
||||||
#if PACKETVER_MAIN_NUM >= 20200916 || PACKETVER_RE_NUM >= 20200723
|
#if PACKETVER_MAIN_NUM >= 20200916 || PACKETVER_RE_NUM >= 20200723 || PACKETVER_ZERO_NUM >= 20221024
|
||||||
DEFINE_PACKET_ID(ZC_PAR_4JOB_CHANGE, 0x0b25);
|
DEFINE_PACKET_ID(ZC_PAR_4JOB_CHANGE, 0x0b25);
|
||||||
#endif // PACKETVER_MAIN_NUM >= 20200916 || PACKETVER_RE_NUM >= 20200723
|
#endif // PACKETVER_MAIN_NUM >= 20200916 || PACKETVER_RE_NUM >= 20200723 || PACKETVER_ZERO_NUM >= 20221024
|
||||||
|
|
||||||
#if !defined(sun) && (!defined(__NETBSD__) || __NetBSD_Version__ >= 600000000) // NetBSD 5 and Solaris don't like pragma pack but accept the packed attribute
|
#if !defined(sun) && (!defined(__NETBSD__) || __NetBSD_Version__ >= 600000000) // NetBSD 5 and Solaris don't like pragma pack but accept the packed attribute
|
||||||
#pragma pack(push, 1)
|
#pragma pack(push, 1)
|
||||||
@ -482,9 +475,9 @@ struct EQUIPITEM_INFO {
|
|||||||
#if PACKETVER < 20120925
|
#if PACKETVER < 20120925
|
||||||
uint8 IsDamaged;
|
uint8 IsDamaged;
|
||||||
#endif
|
#endif
|
||||||
#if !(PACKETVER_MAIN_NUM >= 20200916 || PACKETVER_RE_NUM >= 20200723)
|
#if !(PACKETVER_MAIN_NUM >= 20200916 || PACKETVER_RE_NUM >= 20200723 || PACKETVER_ZERO_NUM >= 20221024)
|
||||||
uint8 RefiningLevel;
|
uint8 RefiningLevel;
|
||||||
#endif // !(PACKETVER_MAIN_NUM >= 20200916 || PACKETVER_RE_NUM >= 20200723)
|
#endif // !(PACKETVER_MAIN_NUM >= 20200916 || PACKETVER_RE_NUM >= 20200723 || PACKETVER_ZERO_NUM >= 20221024)
|
||||||
struct EQUIPSLOTINFO slot;
|
struct EQUIPSLOTINFO slot;
|
||||||
#if PACKETVER >= 20071002
|
#if PACKETVER >= 20071002
|
||||||
int32 HireExpireDate;
|
int32 HireExpireDate;
|
||||||
@ -499,10 +492,10 @@ struct EQUIPITEM_INFO {
|
|||||||
uint8 option_count;
|
uint8 option_count;
|
||||||
struct ItemOptions option_data[MAX_ITEM_OPTIONS];
|
struct ItemOptions option_data[MAX_ITEM_OPTIONS];
|
||||||
#endif
|
#endif
|
||||||
#if PACKETVER_MAIN_NUM >= 20200916 || PACKETVER_RE_NUM >= 20200723
|
#if PACKETVER_MAIN_NUM >= 20200916 || PACKETVER_RE_NUM >= 20200723 || PACKETVER_ZERO_NUM >= 20221024
|
||||||
uint8 RefiningLevel;
|
uint8 RefiningLevel;
|
||||||
uint8 enchantgrade;
|
uint8 grade;
|
||||||
#endif // PACKETVER_MAIN_NUM >= 20200916 || PACKETVER_RE_NUM >= 20200723
|
#endif // PACKETVER_MAIN_NUM >= 20200916 || PACKETVER_RE_NUM >= 20200723 || PACKETVER_ZERO_NUM >= 20221024
|
||||||
#if PACKETVER >= 20120925
|
#if PACKETVER >= 20120925
|
||||||
struct {
|
struct {
|
||||||
uint8 IsIdentified : 1;
|
uint8 IsIdentified : 1;
|
||||||
@ -555,9 +548,9 @@ struct PACKET_ZC_ITEM_PICKUP_ACK {
|
|||||||
#endif
|
#endif
|
||||||
uint8 IsIdentified;
|
uint8 IsIdentified;
|
||||||
uint8 IsDamaged;
|
uint8 IsDamaged;
|
||||||
#if !(PACKETVER_MAIN_NUM >= 20200916 || PACKETVER_RE_NUM >= 20200723)
|
#if !(PACKETVER_MAIN_NUM >= 20200916 || PACKETVER_RE_NUM >= 20200723 || PACKETVER_ZERO_NUM >= 20221024)
|
||||||
uint8 refiningLevel;
|
uint8 refiningLevel;
|
||||||
#endif // !(PACKETVER_MAIN_NUM >= 20200916 || PACKETVER_RE_NUM >= 20200723)
|
#endif // !(PACKETVER_MAIN_NUM >= 20200916 || PACKETVER_RE_NUM >= 20200723 || PACKETVER_ZERO_NUM >= 20221024)
|
||||||
struct EQUIPSLOTINFO slot;
|
struct EQUIPSLOTINFO slot;
|
||||||
#if PACKETVER >= 20120925
|
#if PACKETVER >= 20120925
|
||||||
uint32 location;
|
uint32 location;
|
||||||
@ -579,13 +572,13 @@ struct PACKET_ZC_ITEM_PICKUP_ACK {
|
|||||||
uint8 favorite;
|
uint8 favorite;
|
||||||
uint16 look;
|
uint16 look;
|
||||||
#endif
|
#endif
|
||||||
#if PACKETVER_MAIN_NUM >= 20200916 || PACKETVER_RE_NUM >= 20200723
|
#if PACKETVER_MAIN_NUM >= 20200916 || PACKETVER_RE_NUM >= 20200723 || PACKETVER_ZERO_NUM >= 20221024
|
||||||
uint8 refiningLevel;
|
uint8 refiningLevel;
|
||||||
uint8 grade;
|
uint8 grade;
|
||||||
#endif // PACKETVER_MAIN_NUM >= 20200916 || PACKETVER_RE_NUM >= 20200723
|
#endif // PACKETVER_MAIN_NUM >= 20200916 || PACKETVER_RE_NUM >= 20200723 || PACKETVER_ZERO_NUM >= 20221024
|
||||||
} __attribute__((packed));
|
} __attribute__((packed));
|
||||||
|
|
||||||
#if PACKETVER_MAIN_NUM >= 20200916 || PACKETVER_RE_NUM >= 20200723
|
#if PACKETVER_MAIN_NUM >= 20200916 || PACKETVER_RE_NUM >= 20200723 || PACKETVER_ZERO_NUM >= 20221024
|
||||||
DEFINE_PACKET_HEADER(ZC_ITEM_PICKUP_ACK, 0x0b41);
|
DEFINE_PACKET_HEADER(ZC_ITEM_PICKUP_ACK, 0x0b41);
|
||||||
#elif PACKETVER >= 20160921
|
#elif PACKETVER >= 20160921
|
||||||
DEFINE_PACKET_HEADER(ZC_ITEM_PICKUP_ACK, 0x0a37);
|
DEFINE_PACKET_HEADER(ZC_ITEM_PICKUP_ACK, 0x0a37);
|
||||||
@ -1311,7 +1304,7 @@ struct packet_unequipitem_ack {
|
|||||||
uint8 result;
|
uint8 result;
|
||||||
} __attribute__((packed));
|
} __attribute__((packed));
|
||||||
|
|
||||||
#if PACKETVER_MAIN_NUM >= 20200916 || PACKETVER_RE_NUM >= 20200723
|
#if PACKETVER_MAIN_NUM >= 20200916 || PACKETVER_RE_NUM >= 20200723 || PACKETVER_ZERO_NUM >= 20221024
|
||||||
struct PACKET_ZC_EQUIPWIN_MICROSCOPE {
|
struct PACKET_ZC_EQUIPWIN_MICROSCOPE {
|
||||||
int16 PacketType;
|
int16 PacketType;
|
||||||
int16 PacketLength;
|
int16 PacketLength;
|
||||||
@ -1524,7 +1517,7 @@ struct PACKET_CZ_NPC_MARKET_PURCHASE {
|
|||||||
DEFINE_PACKET_HEADER(CZ_NPC_MARKET_PURCHASE, 0x09d6)
|
DEFINE_PACKET_HEADER(CZ_NPC_MARKET_PURCHASE, 0x09d6)
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
#if PACKETVER_MAIN_NUM >= 20210203 || PACKETVER_RE_NUM >= 20211103
|
#if PACKETVER_MAIN_NUM >= 20210203 || PACKETVER_RE_NUM >= 20211103 || PACKETVER_ZERO_NUM >= 20221024
|
||||||
struct PACKET_ZC_NPC_MARKET_OPEN_sub {
|
struct PACKET_ZC_NPC_MARKET_OPEN_sub {
|
||||||
#if PACKETVER_MAIN_NUM >= 20181121 || PACKETVER_RE_NUM >= 20180704 || PACKETVER_ZERO_NUM >= 20181114
|
#if PACKETVER_MAIN_NUM >= 20181121 || PACKETVER_RE_NUM >= 20180704 || PACKETVER_ZERO_NUM >= 20181114
|
||||||
uint32 nameid;
|
uint32 nameid;
|
||||||
@ -1741,7 +1734,7 @@ struct PACKET_CZ_ADD_ITEM_TO_MAIL {
|
|||||||
// [4144] this packet exists from
|
// [4144] this packet exists from
|
||||||
// PACKETVER_MAIN_NUM >= 20141112 || PACKETVER_RE_NUM >= 20140924 || defined(PACKETVER_ZERO)
|
// PACKETVER_MAIN_NUM >= 20141112 || PACKETVER_RE_NUM >= 20140924 || defined(PACKETVER_ZERO)
|
||||||
// but used only packet versions with known struct
|
// but used only packet versions with known struct
|
||||||
#if PACKETVER_MAIN_NUM >= 20200916 || PACKETVER_RE_NUM >= 20200723
|
#if PACKETVER_MAIN_NUM >= 20200916 || PACKETVER_RE_NUM >= 20200723 || PACKETVER_ZERO_NUM >= 20221024
|
||||||
struct PACKET_ZC_ACK_ADD_ITEM_RODEX {
|
struct PACKET_ZC_ACK_ADD_ITEM_RODEX {
|
||||||
int16 PacketType;
|
int16 PacketType;
|
||||||
int8 result;
|
int8 result;
|
||||||
@ -1924,7 +1917,7 @@ struct PACKET_CZ_REQ_READ_MAIL {
|
|||||||
int64 MailID;
|
int64 MailID;
|
||||||
} __attribute__((packed));
|
} __attribute__((packed));
|
||||||
|
|
||||||
#if PACKETVER_MAIN_NUM >= 20200916 || PACKETVER_RE_NUM >= 20200723
|
#if PACKETVER_MAIN_NUM >= 20200916 || PACKETVER_RE_NUM >= 20200723 || PACKETVER_ZERO_NUM >= 20221024
|
||||||
struct PACKET_ZC_ACK_READ_RODEX_SUB {
|
struct PACKET_ZC_ACK_READ_RODEX_SUB {
|
||||||
int16 count;
|
int16 count;
|
||||||
#if PACKETVER_MAIN_NUM >= 20181121 || PACKETVER_RE_NUM >= 20180704 || PACKETVER_ZERO_NUM >= 20181114
|
#if PACKETVER_MAIN_NUM >= 20181121 || PACKETVER_RE_NUM >= 20180704 || PACKETVER_ZERO_NUM >= 20181114
|
||||||
@ -2259,14 +2252,14 @@ struct PACKET_ZC_UI_OPEN {
|
|||||||
DEFINE_PACKET_HEADER(ZC_UI_OPEN, 0x0a38);
|
DEFINE_PACKET_HEADER(ZC_UI_OPEN, 0x0a38);
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
#if PACKETVER_MAIN_NUM >= 20210203 || PACKETVER_RE_NUM >= 20211103
|
#if PACKETVER_MAIN_NUM >= 20210203 || PACKETVER_RE_NUM >= 20211103 || PACKETVER_ZERO_NUM >= 20221024
|
||||||
struct PACKET_ZC_UI_OPEN2 {
|
struct PACKET_ZC_UI_OPEN2 {
|
||||||
int16 PacketType;
|
int16 PacketType;
|
||||||
int8 UIType;
|
int8 UIType;
|
||||||
int64 data;
|
int64 data;
|
||||||
} __attribute__((packed));
|
} __attribute__((packed));
|
||||||
DEFINE_PACKET_HEADER(ZC_UI_OPEN2, 0x0b9a);
|
DEFINE_PACKET_HEADER(ZC_UI_OPEN2, 0x0b9a);
|
||||||
#endif // PACKETVER_MAIN_NUM >= 20210203 || PACKETVER_RE_NUM >= 20211103
|
#endif // PACKETVER_MAIN_NUM >= 20210203 || PACKETVER_RE_NUM >= 20211103 || PACKETVER_ZERO_NUM >= 20221024
|
||||||
|
|
||||||
struct PACKET_ZC_UI_ACTION {
|
struct PACKET_ZC_UI_ACTION {
|
||||||
int16 PacketType;
|
int16 PacketType;
|
||||||
@ -2370,7 +2363,7 @@ struct PACKET_ZC_ITEM_ENTRY {
|
|||||||
uint8 subY;
|
uint8 subY;
|
||||||
} __attribute__((packed));
|
} __attribute__((packed));
|
||||||
|
|
||||||
#if PACKETVER_MAIN_NUM >= 20200916 || PACKETVER_RE_NUM >= 20200723
|
#if PACKETVER_MAIN_NUM >= 20200916 || PACKETVER_RE_NUM >= 20200723 || PACKETVER_ZERO_NUM >= 20221024
|
||||||
struct PACKET_ZC_ADD_ITEM_TO_STORE {
|
struct PACKET_ZC_ADD_ITEM_TO_STORE {
|
||||||
int16 packetType;
|
int16 packetType;
|
||||||
int16 index;
|
int16 index;
|
||||||
@ -2386,7 +2379,7 @@ struct PACKET_ZC_ADD_ITEM_TO_STORE {
|
|||||||
struct EQUIPSLOTINFO slot;
|
struct EQUIPSLOTINFO slot;
|
||||||
struct ItemOptions option_data[MAX_ITEM_OPTIONS];
|
struct ItemOptions option_data[MAX_ITEM_OPTIONS];
|
||||||
uint8 refine;
|
uint8 refine;
|
||||||
uint8 enchantgrade;
|
uint8 grade;
|
||||||
} __attribute__((packed));
|
} __attribute__((packed));
|
||||||
DEFINE_PACKET_HEADER(ZC_ADD_ITEM_TO_STORE, 0x0b44)
|
DEFINE_PACKET_HEADER(ZC_ADD_ITEM_TO_STORE, 0x0b44)
|
||||||
#elif PACKETVER_MAIN_NUM >= 20140813 || PACKETVER_RE_NUM >= 20140402 || defined(PACKETVER_ZERO)
|
#elif PACKETVER_MAIN_NUM >= 20140813 || PACKETVER_RE_NUM >= 20140402 || defined(PACKETVER_ZERO)
|
||||||
@ -2467,7 +2460,7 @@ struct PACKET_ZC_ACK_TOUSESKILL {
|
|||||||
} __attribute__((packed));
|
} __attribute__((packed));
|
||||||
DEFINE_PACKET_HEADER(ZC_ACK_TOUSESKILL, 0x0110)
|
DEFINE_PACKET_HEADER(ZC_ACK_TOUSESKILL, 0x0110)
|
||||||
|
|
||||||
#if PACKETVER_MAIN_NUM >= 20200916 || PACKETVER_RE_NUM >= 20200723
|
#if PACKETVER_MAIN_NUM >= 20200916 || PACKETVER_RE_NUM >= 20200723 || PACKETVER_ZERO_NUM >= 20221024
|
||||||
struct PACKET_ZC_ADD_ITEM_TO_CART {
|
struct PACKET_ZC_ADD_ITEM_TO_CART {
|
||||||
int16 packetType;
|
int16 packetType;
|
||||||
int16 index;
|
int16 index;
|
||||||
@ -2628,9 +2621,9 @@ struct PACKET_ZC_ADD_EXCHANGE_ITEM {
|
|||||||
#endif
|
#endif
|
||||||
uint8 identified;
|
uint8 identified;
|
||||||
uint8 damaged;
|
uint8 damaged;
|
||||||
#if !(PACKETVER_MAIN_NUM >= 20200916 || PACKETVER_RE_NUM >= 20200723)
|
#if !(PACKETVER_MAIN_NUM >= 20200916 || PACKETVER_RE_NUM >= 20200723 || PACKETVER_ZERO_NUM >= 20221024)
|
||||||
uint8 refine;
|
uint8 refine;
|
||||||
#endif // !(PACKETVER_MAIN_NUM >= 20200916 || PACKETVER_RE_NUM >= 20200723)
|
#endif // !(PACKETVER_MAIN_NUM >= 20200916 || PACKETVER_RE_NUM >= 20200723 || PACKETVER_ZERO_NUM >= 20221024)
|
||||||
struct EQUIPSLOTINFO slot;
|
struct EQUIPSLOTINFO slot;
|
||||||
#if PACKETVER >= 20150226
|
#if PACKETVER >= 20150226
|
||||||
struct ItemOptions option_data[MAX_ITEM_OPTIONS];
|
struct ItemOptions option_data[MAX_ITEM_OPTIONS];
|
||||||
@ -2639,13 +2632,13 @@ struct PACKET_ZC_ADD_EXCHANGE_ITEM {
|
|||||||
uint32 location;
|
uint32 location;
|
||||||
uint16 look;
|
uint16 look;
|
||||||
#endif // PACKETVER_MAIN_NUM >= 20161102 || PACKETVER_RE_NUM >= 20161026 || defined(PACKETVER_ZERO)
|
#endif // PACKETVER_MAIN_NUM >= 20161102 || PACKETVER_RE_NUM >= 20161026 || defined(PACKETVER_ZERO)
|
||||||
#if PACKETVER_MAIN_NUM >= 20200916 || PACKETVER_RE_NUM >= 20200723
|
#if PACKETVER_MAIN_NUM >= 20200916 || PACKETVER_RE_NUM >= 20200723 || PACKETVER_ZERO_NUM >= 20221024
|
||||||
uint8 refine;
|
uint8 refine;
|
||||||
uint8 grade;
|
uint8 grade;
|
||||||
#endif // PACKETVER_MAIN_NUM >= 20200916 || PACKETVER_RE_NUM >= 20200723
|
#endif // PACKETVER_MAIN_NUM >= 20200916 || PACKETVER_RE_NUM >= 20200723 || PACKETVER_ZERO_NUM >= 20221024
|
||||||
} __attribute__((packed));
|
} __attribute__((packed));
|
||||||
|
|
||||||
#if PACKETVER_MAIN_NUM >= 20200916 || PACKETVER_RE_NUM >= 20200723
|
#if PACKETVER_MAIN_NUM >= 20200916 || PACKETVER_RE_NUM >= 20200723 || PACKETVER_ZERO_NUM >= 20221024
|
||||||
DEFINE_PACKET_HEADER(ZC_ADD_EXCHANGE_ITEM, 0x0b42);
|
DEFINE_PACKET_HEADER(ZC_ADD_EXCHANGE_ITEM, 0x0b42);
|
||||||
#elif PACKETVER_MAIN_NUM >= 20161102 || PACKETVER_RE_NUM >= 20161026 || defined(PACKETVER_ZERO)
|
#elif PACKETVER_MAIN_NUM >= 20161102 || PACKETVER_RE_NUM >= 20161026 || defined(PACKETVER_ZERO)
|
||||||
DEFINE_PACKET_HEADER(ZC_ADD_EXCHANGE_ITEM, 0x0a96);
|
DEFINE_PACKET_HEADER(ZC_ADD_EXCHANGE_ITEM, 0x0a96);
|
||||||
@ -2677,7 +2670,7 @@ struct PACKET_ZC_CASH_ITEM_DELETE {
|
|||||||
#endif
|
#endif
|
||||||
} __attribute__((packed));
|
} __attribute__((packed));
|
||||||
|
|
||||||
#if PACKETVER_MAIN_NUM >= 20200916 || PACKETVER_RE_NUM >= 20200723
|
#if PACKETVER_MAIN_NUM >= 20200916 || PACKETVER_RE_NUM >= 20200723 || PACKETVER_ZERO_NUM >= 20221024
|
||||||
struct PACKET_ZC_ITEM_PICKUP_PARTY {
|
struct PACKET_ZC_ITEM_PICKUP_PARTY {
|
||||||
int16 packetType;
|
int16 packetType;
|
||||||
uint32 AID;
|
uint32 AID;
|
||||||
@ -2742,7 +2735,7 @@ struct PACKET_ZC_ACK_WEAPONREFINE {
|
|||||||
#endif
|
#endif
|
||||||
} __attribute__((packed));
|
} __attribute__((packed));
|
||||||
|
|
||||||
#if PACKETVER_MAIN_NUM >= 20210303 || PACKETVER_RE_NUM >= 20211103
|
#if PACKETVER_MAIN_NUM >= 20210303 || PACKETVER_RE_NUM >= 20211103 || PACKETVER_ZERO_NUM >= 20221024
|
||||||
// PACKET_ZC_PROPERTY_HOMUN4
|
// PACKET_ZC_PROPERTY_HOMUN4
|
||||||
struct PACKET_ZC_PROPERTY_HOMUN {
|
struct PACKET_ZC_PROPERTY_HOMUN {
|
||||||
int16 packetType;
|
int16 packetType;
|
||||||
@ -2927,7 +2920,7 @@ struct REPAIRITEM_INFO2 {
|
|||||||
uint8 refine; // unused?
|
uint8 refine; // unused?
|
||||||
struct EQUIPSLOTINFO slot; // unused?
|
struct EQUIPSLOTINFO slot; // unused?
|
||||||
} __attribute__((packed));
|
} __attribute__((packed));
|
||||||
#endif // PACKETVER_MAIN_NUM >= 20200916 || PACKETVER_RE_NUM >= 20200723
|
#endif // PACKETVER_MAIN_NUM >= 20200916 || PACKETVER_RE_NUM >= 20200723 || PACKETVER_ZERO_NUM >= 20221024
|
||||||
|
|
||||||
struct REPAIRITEM_INFO1 {
|
struct REPAIRITEM_INFO1 {
|
||||||
int16 index;
|
int16 index;
|
||||||
@ -2996,7 +2989,7 @@ struct PACKET_ZC_ACK_SCHEDULER_CASHITEM {
|
|||||||
struct PACKET_ZC_ACK_SCHEDULER_CASHITEM_sub items[];
|
struct PACKET_ZC_ACK_SCHEDULER_CASHITEM_sub items[];
|
||||||
} __attribute__((packed));
|
} __attribute__((packed));
|
||||||
|
|
||||||
#if PACKETVER_MAIN_NUM >= 20200916 || PACKETVER_RE_NUM >= 20200723
|
#if PACKETVER_MAIN_NUM >= 20200916 || PACKETVER_RE_NUM >= 20200723 || PACKETVER_ZERO_NUM >= 20221024
|
||||||
struct PACKET_ZC_PC_PURCHASE_MYITEMLIST_sub {
|
struct PACKET_ZC_PC_PURCHASE_MYITEMLIST_sub {
|
||||||
uint32 price;
|
uint32 price;
|
||||||
int16 index;
|
int16 index;
|
||||||
@ -3021,7 +3014,7 @@ struct PACKET_ZC_PC_PURCHASE_MYITEMLIST {
|
|||||||
struct PACKET_ZC_PC_PURCHASE_MYITEMLIST_sub items[];
|
struct PACKET_ZC_PC_PURCHASE_MYITEMLIST_sub items[];
|
||||||
} __attribute__((packed));
|
} __attribute__((packed));
|
||||||
DEFINE_PACKET_HEADER(ZC_PC_PURCHASE_MYITEMLIST, 0x0b40);
|
DEFINE_PACKET_HEADER(ZC_PC_PURCHASE_MYITEMLIST, 0x0b40);
|
||||||
#else // PACKETVER_MAIN_NUM >= 20200916 || PACKETVER_RE_NUM >= 20200723
|
#else // PACKETVER_MAIN_NUM >= 20200916 || PACKETVER_RE_NUM >= 20200723 || PACKETVER_ZERO_NUM >= 20221024
|
||||||
struct PACKET_ZC_PC_PURCHASE_MYITEMLIST_sub {
|
struct PACKET_ZC_PC_PURCHASE_MYITEMLIST_sub {
|
||||||
uint32 price;
|
uint32 price;
|
||||||
int16 index;
|
int16 index;
|
||||||
@ -3047,9 +3040,9 @@ struct PACKET_ZC_PC_PURCHASE_MYITEMLIST {
|
|||||||
struct PACKET_ZC_PC_PURCHASE_MYITEMLIST_sub items[];
|
struct PACKET_ZC_PC_PURCHASE_MYITEMLIST_sub items[];
|
||||||
} __attribute__((packed));
|
} __attribute__((packed));
|
||||||
DEFINE_PACKET_HEADER(ZC_PC_PURCHASE_MYITEMLIST, 0x0136);
|
DEFINE_PACKET_HEADER(ZC_PC_PURCHASE_MYITEMLIST, 0x0136);
|
||||||
#endif // PACKETVER_MAIN_NUM >= 20200916 || PACKETVER_RE_NUM >= 20200723
|
#endif // PACKETVER_MAIN_NUM >= 20200916 || PACKETVER_RE_NUM >= 20200723 || PACKETVER_ZERO_NUM >= 20221024
|
||||||
|
|
||||||
#if PACKETVER_MAIN_NUM >= 20210203 || PACKETVER_RE_NUM >= 20211103
|
#if PACKETVER_MAIN_NUM >= 20210203 || PACKETVER_RE_NUM >= 20211103 || PACKETVER_ZERO_NUM >= 20221024
|
||||||
struct PACKET_ZC_PC_PURCHASE_ITEMLIST_sub {
|
struct PACKET_ZC_PC_PURCHASE_ITEMLIST_sub {
|
||||||
#if PACKETVER_MAIN_NUM >= 20181121 || PACKETVER_RE_NUM >= 20180704 || PACKETVER_ZERO_NUM >= 20181114
|
#if PACKETVER_MAIN_NUM >= 20181121 || PACKETVER_RE_NUM >= 20180704 || PACKETVER_ZERO_NUM >= 20181114
|
||||||
uint32 itemId;
|
uint32 itemId;
|
||||||
@ -3140,7 +3133,7 @@ struct PACKET_ZC_MYITEMLIST_BUYING_STORE {
|
|||||||
struct PACKET_ZC_MYITEMLIST_BUYING_STORE_sub items[];
|
struct PACKET_ZC_MYITEMLIST_BUYING_STORE_sub items[];
|
||||||
} __attribute__((packed));
|
} __attribute__((packed));
|
||||||
|
|
||||||
#if PACKETVER_MAIN_NUM >= 20200916 || PACKETVER_RE_NUM >= 20200723
|
#if PACKETVER_MAIN_NUM >= 20200916 || PACKETVER_RE_NUM >= 20200723 || PACKETVER_ZERO_NUM >= 20221024
|
||||||
struct PACKET_ZC_PC_PURCHASE_ITEMLIST_FROMMC_sub {
|
struct PACKET_ZC_PC_PURCHASE_ITEMLIST_FROMMC_sub {
|
||||||
uint32 price;
|
uint32 price;
|
||||||
uint16 amount;
|
uint16 amount;
|
||||||
@ -3182,7 +3175,7 @@ struct PACKET_ZC_PC_PURCHASE_ITEMLIST_FROMMC_sub {
|
|||||||
#endif
|
#endif
|
||||||
uint8 identified;
|
uint8 identified;
|
||||||
uint8 damaged;
|
uint8 damaged;
|
||||||
#if !(PACKETVER_MAIN_NUM >= 20200916 || PACKETVER_RE_NUM >= 20200723)
|
#if !(PACKETVER_MAIN_NUM >= 20200916 || PACKETVER_RE_NUM >= 20200723 || PACKETVER_ZERO_NUM >= 20221024)
|
||||||
uint8 refine;
|
uint8 refine;
|
||||||
#endif
|
#endif
|
||||||
struct EQUIPSLOTINFO slot;
|
struct EQUIPSLOTINFO slot;
|
||||||
@ -3194,7 +3187,7 @@ struct PACKET_ZC_PC_PURCHASE_ITEMLIST_FROMMC_sub {
|
|||||||
uint32 location;
|
uint32 location;
|
||||||
uint16 viewSprite;
|
uint16 viewSprite;
|
||||||
#endif
|
#endif
|
||||||
#if PACKETVER_MAIN_NUM >= 20200916 || PACKETVER_RE_NUM >= 20200723
|
#if PACKETVER_MAIN_NUM >= 20200916 || PACKETVER_RE_NUM >= 20200723 || PACKETVER_ZERO_NUM >= 20221024
|
||||||
uint8 refine;
|
uint8 refine;
|
||||||
uint8 grade;
|
uint8 grade;
|
||||||
#endif
|
#endif
|
||||||
@ -3304,7 +3297,7 @@ struct PACKET_ZC_MAKINGARROW_LIST {
|
|||||||
} __attribute__((packed));
|
} __attribute__((packed));
|
||||||
DEFINE_PACKET_HEADER(ZC_MAKINGARROW_LIST, 0x01ad);
|
DEFINE_PACKET_HEADER(ZC_MAKINGARROW_LIST, 0x01ad);
|
||||||
|
|
||||||
#if PACKETVER_MAIN_NUM >= 20200916 || PACKETVER_RE_NUM >= 20200723
|
#if PACKETVER_MAIN_NUM >= 20200916 || PACKETVER_RE_NUM >= 20200723 || PACKETVER_ZERO_NUM >= 20221024
|
||||||
#define REPAIRITEM_INFO REPAIRITEM_INFO2
|
#define REPAIRITEM_INFO REPAIRITEM_INFO2
|
||||||
struct PACKET_ZC_REPAIRITEMLIST {
|
struct PACKET_ZC_REPAIRITEMLIST {
|
||||||
int16 packetType;
|
int16 packetType;
|
||||||
@ -3312,7 +3305,7 @@ struct PACKET_ZC_REPAIRITEMLIST {
|
|||||||
struct REPAIRITEM_INFO items[];
|
struct REPAIRITEM_INFO items[];
|
||||||
} __attribute__((packed));
|
} __attribute__((packed));
|
||||||
DEFINE_PACKET_HEADER(ZC_REPAIRITEMLIST, 0x0b65);
|
DEFINE_PACKET_HEADER(ZC_REPAIRITEMLIST, 0x0b65);
|
||||||
#else // PACKETVER_MAIN_NUM >= 20200916 || PACKETVER_RE_NUM >= 20200723
|
#else // PACKETVER_MAIN_NUM >= 20200916 || PACKETVER_RE_NUM >= 20200723 || PACKETVER_ZERO_NUM >= 20221024
|
||||||
#define REPAIRITEM_INFO REPAIRITEM_INFO1
|
#define REPAIRITEM_INFO REPAIRITEM_INFO1
|
||||||
struct PACKET_ZC_REPAIRITEMLIST {
|
struct PACKET_ZC_REPAIRITEMLIST {
|
||||||
int16 packetType;
|
int16 packetType;
|
||||||
@ -3320,7 +3313,7 @@ struct PACKET_ZC_REPAIRITEMLIST {
|
|||||||
struct REPAIRITEM_INFO items[];
|
struct REPAIRITEM_INFO items[];
|
||||||
} __attribute__((packed));
|
} __attribute__((packed));
|
||||||
DEFINE_PACKET_HEADER(ZC_REPAIRITEMLIST, 0x01fc);
|
DEFINE_PACKET_HEADER(ZC_REPAIRITEMLIST, 0x01fc);
|
||||||
#endif // PACKETVER_MAIN_NUM >= 20200916 || PACKETVER_RE_NUM >= 20200723
|
#endif // PACKETVER_MAIN_NUM >= 20200916 || PACKETVER_RE_NUM >= 20200723 || PACKETVER_ZERO_NUM >= 20221024
|
||||||
|
|
||||||
struct PACKET_ZC_NOTIFY_WEAPONITEMLIST_sub {
|
struct PACKET_ZC_NOTIFY_WEAPONITEMLIST_sub {
|
||||||
int16 index;
|
int16 index;
|
||||||
@ -3428,7 +3421,7 @@ struct PACKET_CZ_SEARCH_STORE_INFO {
|
|||||||
*/
|
*/
|
||||||
} __attribute__((packed));
|
} __attribute__((packed));
|
||||||
|
|
||||||
#if PACKETVER_MAIN_NUM >= 20200916 || PACKETVER_RE_NUM >= 20200723
|
#if PACKETVER_MAIN_NUM >= 20200916 || PACKETVER_RE_NUM >= 20200723 || PACKETVER_ZERO_NUM >= 20221024
|
||||||
struct PACKET_ZC_SEARCH_STORE_INFO_ACK_sub {
|
struct PACKET_ZC_SEARCH_STORE_INFO_ACK_sub {
|
||||||
uint32 storeId;
|
uint32 storeId;
|
||||||
uint32 AID;
|
uint32 AID;
|
||||||
@ -3710,7 +3703,7 @@ struct PACKET_ZC_AUTOSPELLLIST {
|
|||||||
DEFINE_PACKET_HEADER(ZC_AUTOSPELLLIST, 0x01cd);
|
DEFINE_PACKET_HEADER(ZC_AUTOSPELLLIST, 0x01cd);
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
#if PACKETVER_MAIN_NUM >= 20200916 || PACKETVER_RE_NUM >= 20200723
|
#if PACKETVER_MAIN_NUM >= 20200916 || PACKETVER_RE_NUM >= 20200723 || PACKETVER_ZERO_NUM >= 20221024
|
||||||
struct PACKET_ZC_CHANGE_ITEM_OPTION {
|
struct PACKET_ZC_CHANGE_ITEM_OPTION {
|
||||||
int16 packetType;
|
int16 packetType;
|
||||||
int16 index;
|
int16 index;
|
||||||
@ -3840,7 +3833,7 @@ struct PACKET_CZ_PARTY_CONFIG {
|
|||||||
} __attribute__((packed));
|
} __attribute__((packed));
|
||||||
DEFINE_PACKET_HEADER(CZ_PARTY_CONFIG, 0x02c8);
|
DEFINE_PACKET_HEADER(CZ_PARTY_CONFIG, 0x02c8);
|
||||||
|
|
||||||
#if PACKETVER_MAIN_NUM >= 20210203 || PACKETVER_RE_NUM >= 20211103
|
#if PACKETVER_MAIN_NUM >= 20210203 || PACKETVER_RE_NUM >= 20211103 || PACKETVER_ZERO_NUM >= 20221024
|
||||||
struct PACKET_ZC_NPC_BARTER_MARKET_ITEMINFO_sub {
|
struct PACKET_ZC_NPC_BARTER_MARKET_ITEMINFO_sub {
|
||||||
#if PACKETVER_MAIN_NUM >= 20181121 || PACKETVER_RE_NUM >= 20180704 || PACKETVER_ZERO_NUM >= 20181114
|
#if PACKETVER_MAIN_NUM >= 20181121 || PACKETVER_RE_NUM >= 20180704 || PACKETVER_ZERO_NUM >= 20181114
|
||||||
uint32 nameid;
|
uint32 nameid;
|
||||||
@ -4523,7 +4516,7 @@ struct PACKET_CZ_NPC_EXPANDED_BARTER_MARKET_CLOSE {
|
|||||||
DEFINE_PACKET_HEADER(CZ_NPC_EXPANDED_BARTER_MARKET_CLOSE, 0x0b58);
|
DEFINE_PACKET_HEADER(CZ_NPC_EXPANDED_BARTER_MARKET_CLOSE, 0x0b58);
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
#if PACKETVER_MAIN_NUM >= 20210203 || PACKETVER_RE_NUM >= 20211103
|
#if PACKETVER_MAIN_NUM >= 20210203 || PACKETVER_RE_NUM >= 20211103 || PACKETVER_ZERO_NUM >= 20221024
|
||||||
struct PACKET_ZC_NPC_EXPANDED_BARTER_MARKET_ITEMINFO_sub2 {
|
struct PACKET_ZC_NPC_EXPANDED_BARTER_MARKET_ITEMINFO_sub2 {
|
||||||
#if PACKETVER_MAIN_NUM >= 20181121 || PACKETVER_RE_NUM >= 20180704 || PACKETVER_ZERO_NUM >= 20181114
|
#if PACKETVER_MAIN_NUM >= 20181121 || PACKETVER_RE_NUM >= 20180704 || PACKETVER_ZERO_NUM >= 20181114
|
||||||
uint32 nameid;
|
uint32 nameid;
|
||||||
@ -5264,13 +5257,13 @@ struct PACKET_CZ_REQ_TAKEOFF_EQUIP_ALL {
|
|||||||
DEFINE_PACKET_HEADER(CZ_REQ_TAKEOFF_EQUIP_ALL, 0x0bad);
|
DEFINE_PACKET_HEADER(CZ_REQ_TAKEOFF_EQUIP_ALL, 0x0bad);
|
||||||
#endif // PACKETVER_MAIN_NUM >= 20210818 || PACKETVER_RE_NUM >= 20211103 || PACKETVER_ZERO_NUM >= 20210818
|
#endif // PACKETVER_MAIN_NUM >= 20210818 || PACKETVER_RE_NUM >= 20211103 || PACKETVER_ZERO_NUM >= 20210818
|
||||||
|
|
||||||
#if PACKETVER_MAIN_NUM >= 20210818 || PACKETVER_RE_NUM >= 20211103
|
#if PACKETVER_MAIN_NUM >= 20210818 || PACKETVER_RE_NUM >= 20211103 || PACKETVER_ZERO_NUM >= 20221024
|
||||||
struct PACKET_ZC_ACK_TAKEOFF_EQUIP_ALL {
|
struct PACKET_ZC_ACK_TAKEOFF_EQUIP_ALL {
|
||||||
int16 PacketType;
|
int16 PacketType;
|
||||||
uint8 result;
|
uint8 result;
|
||||||
} __attribute__((packed));
|
} __attribute__((packed));
|
||||||
DEFINE_PACKET_HEADER(ZC_ACK_TAKEOFF_EQUIP_ALL, 0x0bae);
|
DEFINE_PACKET_HEADER(ZC_ACK_TAKEOFF_EQUIP_ALL, 0x0bae);
|
||||||
#endif // PACKETVER_MAIN_NUM >= 20210818 || PACKETVER_RE_NUM >= 20211103
|
#endif // PACKETVER_MAIN_NUM >= 20210818 || PACKETVER_RE_NUM >= 20211103 || PACKETVER_ZERO_NUM >= 20221024
|
||||||
|
|
||||||
#if PACKETVER_ZERO_NUM >= 20210504
|
#if PACKETVER_ZERO_NUM >= 20210504
|
||||||
struct PACKET_ZC_BATTLEFIELD_NOTIFY_HP {
|
struct PACKET_ZC_BATTLEFIELD_NOTIFY_HP {
|
||||||
@ -5340,13 +5333,13 @@ struct PACKET_CZ_CHOOSE_MENU_ZERO {
|
|||||||
DEFINE_PACKET_HEADER(CZ_CHOOSE_MENU_ZERO, 0x0ba8);
|
DEFINE_PACKET_HEADER(CZ_CHOOSE_MENU_ZERO, 0x0ba8);
|
||||||
#endif // PACKETVER_MAIN_NUM >= 20210317 || PACKETVER_RE_NUM >= 20211103 || PACKETVER_ZERO_NUM >= 20210317
|
#endif // PACKETVER_MAIN_NUM >= 20210317 || PACKETVER_RE_NUM >= 20211103 || PACKETVER_ZERO_NUM >= 20210317
|
||||||
|
|
||||||
#if PACKETVER_MAIN_NUM >= 20210203 || PACKETVER_RE_NUM >= 20211103
|
#if PACKETVER_MAIN_NUM >= 20210203 || PACKETVER_RE_NUM >= 20211103 || PACKETVER_ZERO_NUM >= 20221024
|
||||||
struct PACKET_ZC_DIALOG_TEXT_ALIGN {
|
struct PACKET_ZC_DIALOG_TEXT_ALIGN {
|
||||||
int16 PacketType;
|
int16 PacketType;
|
||||||
uint8 align;
|
uint8 align;
|
||||||
} __attribute__((packed));
|
} __attribute__((packed));
|
||||||
DEFINE_PACKET_HEADER(ZC_DIALOG_TEXT_ALIGN, 0x0ba1);
|
DEFINE_PACKET_HEADER(ZC_DIALOG_TEXT_ALIGN, 0x0ba1);
|
||||||
#endif // PACKETVER_MAIN_NUM >= 20210203 || PACKETVER_RE_NUM >= 20211103
|
#endif // PACKETVER_MAIN_NUM >= 20210203 || PACKETVER_RE_NUM >= 20211103 || PACKETVER_ZERO_NUM >= 20221024
|
||||||
|
|
||||||
#if PACKETVER_MAIN_NUM >= 20191016 || PACKETVER_RE_NUM >= 20191016 || PACKETVER_ZERO_NUM >= 20191008
|
#if PACKETVER_MAIN_NUM >= 20191016 || PACKETVER_RE_NUM >= 20191016 || PACKETVER_ZERO_NUM >= 20191008
|
||||||
struct PACKET_CZ_GRADE_ENCHANT_SELECT_EQUIPMENT {
|
struct PACKET_CZ_GRADE_ENCHANT_SELECT_EQUIPMENT {
|
||||||
@ -5356,7 +5349,7 @@ struct PACKET_CZ_GRADE_ENCHANT_SELECT_EQUIPMENT {
|
|||||||
DEFINE_PACKET_HEADER(CZ_GRADE_ENCHANT_SELECT_EQUIPMENT, 0x0b59);
|
DEFINE_PACKET_HEADER(CZ_GRADE_ENCHANT_SELECT_EQUIPMENT, 0x0b59);
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
#if PACKETVER_MAIN_NUM >= 20200916 || PACKETVER_RE_NUM >= 20200723
|
#if PACKETVER_MAIN_NUM >= 20200916 || PACKETVER_RE_NUM >= 20200723 || PACKETVER_ZERO_NUM >= 20221024
|
||||||
struct GRADE_ENCHANT_BLESSING {
|
struct GRADE_ENCHANT_BLESSING {
|
||||||
int32 id;
|
int32 id;
|
||||||
int32 amount;
|
int32 amount;
|
||||||
@ -5404,7 +5397,7 @@ struct PACKET_CZ_GRADE_ENCHANT_CLOSE_UI {
|
|||||||
DEFINE_PACKET_HEADER(CZ_GRADE_ENCHANT_CLOSE_UI, 0x0b5c);
|
DEFINE_PACKET_HEADER(CZ_GRADE_ENCHANT_CLOSE_UI, 0x0b5c);
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
#if PACKETVER_MAIN_NUM >= 20200916 || PACKETVER_RE_NUM >= 20200723
|
#if PACKETVER_MAIN_NUM >= 20200916 || PACKETVER_RE_NUM >= 20200723 || PACKETVER_ZERO_NUM >= 20221024
|
||||||
struct PACKET_ZC_GRADE_ENCHANT_ACK {
|
struct PACKET_ZC_GRADE_ENCHANT_ACK {
|
||||||
int16 PacketType;
|
int16 PacketType;
|
||||||
int16 index;
|
int16 index;
|
||||||
@ -5414,7 +5407,7 @@ struct PACKET_ZC_GRADE_ENCHANT_ACK {
|
|||||||
DEFINE_PACKET_HEADER(ZC_GRADE_ENCHANT_ACK, 0x0b5d);
|
DEFINE_PACKET_HEADER(ZC_GRADE_ENCHANT_ACK, 0x0b5d);
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
#if PACKETVER_MAIN_NUM >= 20200916 || PACKETVER_RE_NUM >= 20200723
|
#if PACKETVER_MAIN_NUM >= 20200916 || PACKETVER_RE_NUM >= 20200723 || PACKETVER_ZERO_NUM >= 20221024
|
||||||
struct PACKET_ZC_GRADE_ENCHANT_BROADCAST_RESULT {
|
struct PACKET_ZC_GRADE_ENCHANT_BROADCAST_RESULT {
|
||||||
int16 packetType;
|
int16 packetType;
|
||||||
char name[NAME_LENGTH];
|
char name[NAME_LENGTH];
|
||||||
@ -5462,7 +5455,7 @@ struct PACKET_ZC_WHISPER {
|
|||||||
DEFINE_PACKET_HEADER(ZC_WHISPER, 0x0097)
|
DEFINE_PACKET_HEADER(ZC_WHISPER, 0x0097)
|
||||||
#endif // PACKETVER_MAIN_NUM >= 20131204 || PACKETVER_RE_NUM >= 20131120 || defined(PACKETVER_ZERO)
|
#endif // PACKETVER_MAIN_NUM >= 20131204 || PACKETVER_RE_NUM >= 20131120 || defined(PACKETVER_ZERO)
|
||||||
|
|
||||||
#if PACKETVER_MAIN_NUM >= 20220216
|
#if PACKETVER_MAIN_NUM >= 20220216 || PACKETVER_ZERO_NUM >= 20221024
|
||||||
struct PACKET_ZC_UPDATE_GDID {
|
struct PACKET_ZC_UPDATE_GDID {
|
||||||
int16 PacketType;
|
int16 PacketType;
|
||||||
uint32 guildId;
|
uint32 guildId;
|
||||||
@ -5474,7 +5467,7 @@ struct PACKET_ZC_UPDATE_GDID {
|
|||||||
uint32 masterGID;
|
uint32 masterGID;
|
||||||
} __attribute__((packed));
|
} __attribute__((packed));
|
||||||
DEFINE_PACKET_HEADER(ZC_UPDATE_GDID, 0x02f7)
|
DEFINE_PACKET_HEADER(ZC_UPDATE_GDID, 0x02f7)
|
||||||
#else // PACKETVER_MAIN_NUM >= 20220216
|
#else // PACKETVER_MAIN_NUM >= 20220216 || PACKETVER_ZERO_NUM >= 20221024
|
||||||
struct PACKET_ZC_UPDATE_GDID {
|
struct PACKET_ZC_UPDATE_GDID {
|
||||||
int16 PacketType;
|
int16 PacketType;
|
||||||
uint32 guildId;
|
uint32 guildId;
|
||||||
@ -5485,9 +5478,9 @@ struct PACKET_ZC_UPDATE_GDID {
|
|||||||
char guildName[NAME_LENGTH];
|
char guildName[NAME_LENGTH];
|
||||||
} __attribute__((packed));
|
} __attribute__((packed));
|
||||||
DEFINE_PACKET_HEADER(ZC_UPDATE_GDID, 0x016c)
|
DEFINE_PACKET_HEADER(ZC_UPDATE_GDID, 0x016c)
|
||||||
#endif // PACKETVER_MAIN_NUM >= 20220216
|
#endif // PACKETVER_MAIN_NUM >= 20220216 || PACKETVER_ZERO_NUM >= 20221024
|
||||||
|
|
||||||
#if PACKETVER_MAIN_NUM >= 20220216
|
#if PACKETVER_MAIN_NUM >= 20220216 || PACKETVER_ZERO_NUM >= 20221024
|
||||||
struct PACKET_CZ_APPROXIMATE_ACTOR {
|
struct PACKET_CZ_APPROXIMATE_ACTOR {
|
||||||
int16 PacketType;
|
int16 PacketType;
|
||||||
uint32 masterGID;
|
uint32 masterGID;
|
||||||
@ -5495,7 +5488,7 @@ struct PACKET_CZ_APPROXIMATE_ACTOR {
|
|||||||
uint8 unused2;
|
uint8 unused2;
|
||||||
} __attribute__((packed));
|
} __attribute__((packed));
|
||||||
DEFINE_PACKET_HEADER(CZ_APPROXIMATE_ACTOR, 0x0bb0)
|
DEFINE_PACKET_HEADER(CZ_APPROXIMATE_ACTOR, 0x0bb0)
|
||||||
#endif // PACKETVER_MAIN_NUM >= 20220216
|
#endif // PACKETVER_MAIN_NUM >= 20220216 || PACKETVER_ZERO_NUM >= 20221024
|
||||||
|
|
||||||
struct PACKET_CZ_CONTACTNPC {
|
struct PACKET_CZ_CONTACTNPC {
|
||||||
int16 PacketType;
|
int16 PacketType;
|
||||||
@ -5708,6 +5701,269 @@ struct PACKET_ZC_DISAPPEAR_BUYING_STORE_ENTRY {
|
|||||||
DEFINE_PACKET_HEADER(ZC_DISAPPEAR_BUYING_STORE_ENTRY, 0x0816);
|
DEFINE_PACKET_HEADER(ZC_DISAPPEAR_BUYING_STORE_ENTRY, 0x0816);
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
#if PACKETVER_MAIN_NUM >= 20201118 || PACKETVER_RE_NUM >= 20211103 || PACKETVER_ZERO_NUM >= 20221024
|
||||||
|
struct PACKET_ZC_OPEN_REFORM_UI {
|
||||||
|
int16 PacketType;
|
||||||
|
int32 ITID;
|
||||||
|
} __attribute__((packed));
|
||||||
|
DEFINE_PACKET_HEADER(ZC_OPEN_REFORM_UI, 0x0b8f);
|
||||||
|
#endif // PACKETVER_MAIN_NUM >= 20201118 || PACKETVER_RE_NUM >= 20211103 || PACKETVER_ZERO_NUM >= 20221024
|
||||||
|
|
||||||
|
#if PACKETVER_MAIN_NUM >= 20200916 || PACKETVER_RE_NUM >= 20211103 || PACKETVER_ZERO_NUM >= 20221024
|
||||||
|
struct PACKET_CZ_CLOSE_REFORM_UI {
|
||||||
|
int16 PacketType;
|
||||||
|
} __attribute__((packed));
|
||||||
|
DEFINE_PACKET_HEADER(CZ_CLOSE_REFORM_UI, 0x0b90);
|
||||||
|
#endif // PACKETVER_MAIN_NUM >= 20200916 || PACKETVER_RE_NUM >= 20211103 || PACKETVER_ZERO_NUM >= 20221024
|
||||||
|
|
||||||
|
#if PACKETVER_MAIN_NUM >= 20200916 || PACKETVER_RE_NUM >= 20211103 || PACKETVER_ZERO_NUM >= 20221024
|
||||||
|
struct PACKET_CZ_ITEM_REFORM {
|
||||||
|
int16 PacketType;
|
||||||
|
int32 ITID;
|
||||||
|
int16 index;
|
||||||
|
} __attribute__((packed));
|
||||||
|
DEFINE_PACKET_HEADER(CZ_ITEM_REFORM, 0x0b91);
|
||||||
|
#endif // PACKETVER_MAIN_NUM >= 20200916 || PACKETVER_RE_NUM >= 20211103 || PACKETVER_ZERO_NUM >= 20221024
|
||||||
|
|
||||||
|
#if PACKETVER_MAIN_NUM >= 20201118 || PACKETVER_RE_NUM >= 20211103 || PACKETVER_ZERO_NUM >= 20221024
|
||||||
|
struct PACKET_ZC_ITEM_REFORM_ACK {
|
||||||
|
int16 PacketType;
|
||||||
|
int16 index;
|
||||||
|
int8 result;
|
||||||
|
} __attribute__((packed));
|
||||||
|
DEFINE_PACKET_HEADER(ZC_ITEM_REFORM_ACK, 0x0b92);
|
||||||
|
#endif // PACKETVER_MAIN_NUM >= 20201118 || PACKETVER_RE_NUM >= 20211103 || PACKETVER_ZERO_NUM >= 20221024
|
||||||
|
|
||||||
|
#if PACKETVER_MAIN_NUM >= 20220216 || PACKETVER_ZERO_NUM >= 20220316
|
||||||
|
struct PACKET_CZ_USE_PACKAGEITEM {
|
||||||
|
int16 PacketType;
|
||||||
|
uint16 index;
|
||||||
|
uint32 AID;
|
||||||
|
uint32 itemID;
|
||||||
|
uint32 BoxIndex;
|
||||||
|
} __attribute__((packed));
|
||||||
|
DEFINE_PACKET_HEADER(CZ_USE_PACKAGEITEM, 0x0baf)
|
||||||
|
#endif // PACKETVER_MAIN_NUM >= 20220216 || PACKETVER_ZERO_NUM >= 20220316
|
||||||
|
|
||||||
|
#if PACKETVER_MAIN_NUM >= 20201118 || PACKETVER_RE_NUM >= 20211103 || PACKETVER_ZERO_NUM >= 20221024
|
||||||
|
struct PACKET_CZ_REQUEST_RANDOM_ENCHANT {
|
||||||
|
int16 PacketType;
|
||||||
|
int64 enchant_group;
|
||||||
|
int16 index;
|
||||||
|
} __attribute__((packed));
|
||||||
|
DEFINE_PACKET_HEADER(CZ_REQUEST_RANDOM_ENCHANT, 0x0b9b);
|
||||||
|
#endif // PACKETVER_MAIN_NUM >= 20201118 || PACKETVER_RE_NUM >= 20211103 || PACKETVER_ZERO_NUM >= 20221024
|
||||||
|
|
||||||
|
#if PACKETVER_MAIN_NUM >= 20201118 || PACKETVER_RE_NUM >= 20211103 || PACKETVER_ZERO_NUM >= 20221024
|
||||||
|
struct PACKET_CZ_REQUEST_PERFECT_ENCHANT {
|
||||||
|
int16 PacketType;
|
||||||
|
int64 enchant_group;
|
||||||
|
int16 index;
|
||||||
|
uint32 ITID;
|
||||||
|
} __attribute__((packed));
|
||||||
|
DEFINE_PACKET_HEADER(CZ_REQUEST_PERFECT_ENCHANT, 0x0b9c);
|
||||||
|
#endif // PACKETVER_MAIN_NUM >= 20201118 || PACKETVER_RE_NUM >= 20211103 || PACKETVER_ZERO_NUM >= 20221024
|
||||||
|
|
||||||
|
#if PACKETVER_MAIN_NUM >= 20201118 || PACKETVER_RE_NUM >= 20211103 || PACKETVER_ZERO_NUM >= 20221024
|
||||||
|
struct PACKET_CZ_REQUEST_UPGRADE_ENCHANT {
|
||||||
|
int16 PacketType;
|
||||||
|
int64 enchant_group;
|
||||||
|
int16 index;
|
||||||
|
int16 slot;
|
||||||
|
} __attribute__((packed));
|
||||||
|
DEFINE_PACKET_HEADER(CZ_REQUEST_UPGRADE_ENCHANT, 0x0b9d);
|
||||||
|
#endif // PACKETVER_MAIN_NUM >= 20201118 || PACKETVER_RE_NUM >= 20211103 || PACKETVER_ZERO_NUM >= 20221024
|
||||||
|
|
||||||
|
#if PACKETVER_MAIN_NUM >= 20201118 || PACKETVER_RE_NUM >= 20211103 || PACKETVER_ZERO_NUM >= 20221024
|
||||||
|
struct PACKET_CZ_REQUEST_RESET_ENCHANT {
|
||||||
|
int16 PacketType;
|
||||||
|
int64 enchant_group;
|
||||||
|
int16 index;
|
||||||
|
} __attribute__((packed));
|
||||||
|
DEFINE_PACKET_HEADER(CZ_REQUEST_RESET_ENCHANT, 0x0b9e);
|
||||||
|
#endif // PACKETVER_MAIN_NUM >= 20201118 || PACKETVER_RE_NUM >= 20211103 || PACKETVER_ZERO_NUM >= 20221024
|
||||||
|
|
||||||
|
#if PACKETVER_MAIN_NUM >= 20210203 || PACKETVER_RE_NUM >= 20211103 || PACKETVER_ZERO_NUM >= 20221024
|
||||||
|
struct PACKET_ZC_RESPONSE_ENCHANT {
|
||||||
|
int16 PacketType;
|
||||||
|
int32 msgId;
|
||||||
|
uint32 ITID;
|
||||||
|
} __attribute__((packed));
|
||||||
|
DEFINE_PACKET_HEADER(ZC_RESPONSE_ENCHANT, 0x0b9f);
|
||||||
|
#endif // PACKETVER_MAIN_NUM >= 20201118 || PACKETVER_RE_NUM >= 20211103 || PACKETVER_ZERO_NUM >= 20221024
|
||||||
|
|
||||||
|
#if PACKETVER_MAIN_NUM >= 20201118 || PACKETVER_RE_NUM >= 20211103 || PACKETVER_ZERO_NUM >= 20221024
|
||||||
|
struct PACKET_CZ_CLOSE_UI_ENCHANT {
|
||||||
|
int16 PacketType;
|
||||||
|
} __attribute__((packed));
|
||||||
|
DEFINE_PACKET_HEADER(CZ_CLOSE_UI_ENCHANT, 0x0ba0);
|
||||||
|
#endif // PACKETVER_MAIN_NUM >= 20201118 || PACKETVER_RE_NUM >= 20211103 || PACKETVER_ZERO_NUM >= 20221024
|
||||||
|
|
||||||
|
#if PACKETVER_MAIN_NUM >= 20221005
|
||||||
|
struct PACKET_ZC_SPECIALPOPUP {
|
||||||
|
int16 PacketType;
|
||||||
|
int32 ppId;
|
||||||
|
} __attribute__((packed));
|
||||||
|
DEFINE_PACKET_HEADER(ZC_SPECIALPOPUP, 0x0bbe);
|
||||||
|
#endif // PACKETVER_MAIN_NUM >= 20221005
|
||||||
|
|
||||||
|
#if PACKETVER >= 20140611
|
||||||
|
struct PACKET_ZC_GOLDPCCAFE_POINT {
|
||||||
|
// Note: 2014-04-30 has 1 byte less, but those packets are only functional after 2014-06-11Ragexe
|
||||||
|
uint16 PacketType;
|
||||||
|
int8 isActive; //< 1 = yes, 0 = no
|
||||||
|
int8 mode;
|
||||||
|
int32 point;
|
||||||
|
int32 playedTime;
|
||||||
|
} __attribute__((packed));
|
||||||
|
DEFINE_PACKET_HEADER(ZC_GOLDPCCAFE_POINT , 0x0a15);
|
||||||
|
#endif // PACKETVER >= 20140611
|
||||||
|
|
||||||
|
#if PACKETVER >= 20140430
|
||||||
|
struct PACKET_CZ_DYNAMICNPC_CREATE_REQUEST {
|
||||||
|
uint16 PacketType;
|
||||||
|
char name[NAME_LENGTH];
|
||||||
|
} __attribute__((packed));
|
||||||
|
DEFINE_PACKET_HEADER(CZ_DYNAMICNPC_CREATE_REQUEST, 0x0a16);
|
||||||
|
#endif // PACKETVER >= 20140430
|
||||||
|
|
||||||
|
#if PACKETVER_MAIN_NUM >= 20140430 || PACKETVER_RE_NUM >= 20140430 || defined(PACKETVER_ZERO)
|
||||||
|
struct PACKET_ZC_DYNAMICNPC_CREATE_RESULT {
|
||||||
|
uint16 PacketType;
|
||||||
|
uint32 result; // enum dynamicnpc_create_result
|
||||||
|
} __attribute__((packed));
|
||||||
|
DEFINE_PACKET_HEADER(ZC_DYNAMICNPC_CREATE_RESULT , 0x0a17);
|
||||||
|
#endif // PACKETVER_MAIN_NUM >= 20140430 || PACKETVER_RE_NUM >= 20140430 || defined(PACKETVER_ZERO)
|
||||||
|
|
||||||
|
struct PACKET_CZ_REQ_GUILD_EMBLEM_IMG1 {
|
||||||
|
int16 packetType;
|
||||||
|
int32 guild_id;
|
||||||
|
} __attribute__((packed));
|
||||||
|
DEFINE_PACKET_HEADER(CZ_REQ_GUILD_EMBLEM_IMG1, 0x0151);
|
||||||
|
|
||||||
|
#if PACKETVER >= 20190724
|
||||||
|
struct PACKET_CZ_REQ_GUILD_EMBLEM_IMG3 {
|
||||||
|
int16 packetType;
|
||||||
|
int32 guild_id;
|
||||||
|
int32 emblem_id;
|
||||||
|
} __attribute__((packed));
|
||||||
|
DEFINE_PACKET_HEADER(CZ_REQ_GUILD_EMBLEM_IMG3, 0x0b46);
|
||||||
|
#endif // PACKETVER >= 20190724
|
||||||
|
|
||||||
|
#if PACKETVER_MAIN_NUM >= 20190619 || PACKETVER_RE_NUM >= 20190605 || PACKETVER_ZERO_NUM >= 20190626
|
||||||
|
struct PACKET_CZ_REQ_GUILD_EMBLEM_IMG2 {
|
||||||
|
int16 packetType;
|
||||||
|
int32 guild_id;
|
||||||
|
int32 emblem_id;
|
||||||
|
int32 unused;
|
||||||
|
} __attribute__((packed));
|
||||||
|
DEFINE_PACKET_HEADER(CZ_REQ_GUILD_EMBLEM_IMG2, 0x0b1e);
|
||||||
|
#elif PACKETVER_MAIN_NUM >= 20190227 || PACKETVER_RE_NUM >= 20190227 || PACKETVER_ZERO_NUM >= 20190313
|
||||||
|
struct PACKET_CZ_REQ_GUILD_EMBLEM_IMG2 {
|
||||||
|
int16 packetType;
|
||||||
|
int32 guild_id;
|
||||||
|
int32 emblem_id;
|
||||||
|
} __attribute__((packed));
|
||||||
|
DEFINE_PACKET_HEADER(CZ_REQ_GUILD_EMBLEM_IMG2, 0x0b1e);
|
||||||
|
#endif // PACKETVER_MAIN_NUM >= 20190619 || PACKETVER_RE_NUM >= 20190605 || PACKETVER_ZERO_NUM >= 20190626
|
||||||
|
|
||||||
|
#if PACKETVER_MAIN_NUM >= 20190807 || PACKETVER_RE_NUM >= 20190731 || PACKETVER_ZERO_NUM >= 20190814
|
||||||
|
struct PACKET_ZC_CHANGE_GUILD {
|
||||||
|
int16 packetType;
|
||||||
|
int32 guild_id;
|
||||||
|
uint32 emblem_id;
|
||||||
|
uint32 AID;
|
||||||
|
} __attribute__((packed));
|
||||||
|
DEFINE_PACKET_HEADER(ZC_CHANGE_GUILD, 0x0b47);
|
||||||
|
// 20190619 main exists in first versions, then removed
|
||||||
|
// 20190605 re first versions with other packet size
|
||||||
|
#elif PACKETVER_MAIN_NUM >= 20190703 || PACKETVER_RE_NUM >= 20190605 || PACKETVER_ZERO_NUM >= 20190709
|
||||||
|
struct PACKET_ZC_CHANGE_GUILD {
|
||||||
|
int16 packetType;
|
||||||
|
int32 guild_id;
|
||||||
|
uint32 emblem_id;
|
||||||
|
uint32 AID;
|
||||||
|
} __attribute__((packed));
|
||||||
|
DEFINE_PACKET_HEADER(ZC_CHANGE_GUILD, 0x0b1f);
|
||||||
|
#else // PACKETVER_MAIN_NUM >= 20190807 || PACKETVER_RE_NUM >= 20190731 || PACKETVER_ZERO_NUM >= 20190814
|
||||||
|
struct PACKET_ZC_CHANGE_GUILD {
|
||||||
|
int16 packetType;
|
||||||
|
uint32 AID;
|
||||||
|
int32 guild_id;
|
||||||
|
uint16 emblem_id;
|
||||||
|
} __attribute__((packed));
|
||||||
|
DEFINE_PACKET_HEADER(ZC_CHANGE_GUILD, 0x01b4);
|
||||||
|
#endif // PACKETVER_MAIN_NUM >= 20190807 || PACKETVER_RE_NUM >= 20190731 || PACKETVER_ZERO_NUM >= 20190814
|
||||||
|
|
||||||
|
#if PACKETVER_MAIN_NUM >= 20190821 || PACKETVER_RE_NUM >= 20190807 || PACKETVER_ZERO_NUM >= 20190710
|
||||||
|
enum ZC_GUILD_EMBLEM_TYPE {
|
||||||
|
ZC_GUILD_EMBLEM_TYPE_CLEAR = 0,
|
||||||
|
ZC_GUILD_EMBLEM_TYPE_ADD = 1,
|
||||||
|
ZC_GUILD_EMBLEM_TYPE_COMPLETE = 2,
|
||||||
|
};
|
||||||
|
|
||||||
|
struct PACKET_ZC_GUILD_EMBLEM_IMG {
|
||||||
|
int16 packetType;
|
||||||
|
int16 packetLength;
|
||||||
|
uint16 result;
|
||||||
|
int32 guild_id;
|
||||||
|
uint32 emblem_id;
|
||||||
|
char emblem_data[];
|
||||||
|
} __attribute__((packed));
|
||||||
|
DEFINE_PACKET_HEADER(ZC_GUILD_EMBLEM_IMG, 0x0b36);
|
||||||
|
#else // PACKETVER_MAIN_NUM >= 20190821 || PACKETVER_RE_NUM >= 20190807 || PACKETVER_ZERO_NUM >= 20190710
|
||||||
|
struct PACKET_ZC_GUILD_EMBLEM_IMG {
|
||||||
|
int16 packetType;
|
||||||
|
int16 packetLength;
|
||||||
|
int32 guild_id;
|
||||||
|
uint32 emblem_id;
|
||||||
|
char emblem_data[];
|
||||||
|
} __attribute__((packed));
|
||||||
|
DEFINE_PACKET_HEADER(ZC_GUILD_EMBLEM_IMG, 0x0152);
|
||||||
|
#endif // PACKETVER_MAIN_NUM >= 20190821 || PACKETVER_RE_NUM >= 20190807 || PACKETVER_ZERO_NUM >= 20190710
|
||||||
|
|
||||||
|
#if PACKETVER_MAIN_NUM >= 20171213 || PACKETVER_RE_NUM >= 20171213 || PACKETVER_ZERO_NUM >= 20171214
|
||||||
|
struct PACKET_CZ_ADVENTURER_AGENCY_JOIN_REQ {
|
||||||
|
int16 packetType;
|
||||||
|
int GID;
|
||||||
|
int AID;
|
||||||
|
} __attribute__((packed));
|
||||||
|
DEFINE_PACKET_HEADER(CZ_ADVENTURER_AGENCY_JOIN_REQ, 0x0ae6);
|
||||||
|
#endif // PACKETVER_MAIN_NUM >= 20171213 || PACKETVER_RE_NUM >= 20171213 || PACKETVER_ZERO_NUM >= 20171214
|
||||||
|
|
||||||
|
#if PACKETVER_MAIN_NUM >= 20191218 || PACKETVER_RE_NUM >= 20191211 || PACKETVER_ZERO_NUM >= 20191224
|
||||||
|
struct PACKET_ZC_ADVENTURER_AGENCY_JOIN_RESULT {
|
||||||
|
int16 packetType;
|
||||||
|
char player_name[NAME_LENGTH];
|
||||||
|
char party_name[NAME_LENGTH];
|
||||||
|
int AID;
|
||||||
|
int result;
|
||||||
|
} __attribute__((packed));
|
||||||
|
DEFINE_PACKET_HEADER(ZC_ADVENTURER_AGENCY_JOIN_RESULT, 0x0afa);
|
||||||
|
#endif // PACKETVER_MAIN_NUM >= 20191218 || PACKETVER_RE_NUM >= 20191211 || PACKETVER_ZERO_NUM >= 20191224
|
||||||
|
|
||||||
|
#if PACKETVER_MAIN_NUM >= 20191218 || PACKETVER_RE_NUM >= 20191211 || PACKETVER_ZERO_NUM >= 20191224
|
||||||
|
struct PACKET_ZC_ADVENTURER_AGENCY_JOIN_REQ {
|
||||||
|
int16 packetType;
|
||||||
|
int GRID;
|
||||||
|
int AID;
|
||||||
|
char groupName[NAME_LENGTH];
|
||||||
|
int16 level;
|
||||||
|
int16 job;
|
||||||
|
} __attribute__((packed));
|
||||||
|
DEFINE_PACKET_HEADER(ZC_ADVENTURER_AGENCY_JOIN_REQ, 0x0ae7);
|
||||||
|
#endif // PACKETVER_MAIN_NUM >= 20191218 || PACKETVER_RE_NUM >= 20191211 || PACKETVER_ZERO_NUM >= 20191224
|
||||||
|
|
||||||
|
#if PACKETVER_MAIN_NUM >= 20191218 || PACKETVER_RE_NUM >= 20191211 || PACKETVER_ZERO_NUM >= 20191224
|
||||||
|
struct PACKET_CZ_ADVENTURER_AGENCY_JOIN_RESULT {
|
||||||
|
int16 packetType;
|
||||||
|
int GRID;
|
||||||
|
int AID;
|
||||||
|
int8 result;
|
||||||
|
} __attribute__((packed));
|
||||||
|
DEFINE_PACKET_HEADER(CZ_ADVENTURER_AGENCY_JOIN_RESULT, 0x0af8);
|
||||||
|
#endif // PACKETVER_MAIN_NUM >= 20191218 || PACKETVER_RE_NUM >= 20191211 || PACKETVER_ZERO_NUM >= 20191224
|
||||||
|
|
||||||
#if !defined(sun) && (!defined(__NETBSD__) || __NetBSD_Version__ >= 600000000) // NetBSD 5 and Solaris don't like pragma pack but accept the packed attribute
|
#if !defined(sun) && (!defined(__NETBSD__) || __NetBSD_Version__ >= 600000000) // NetBSD 5 and Solaris don't like pragma pack but accept the packed attribute
|
||||||
#pragma pack(pop)
|
#pragma pack(pop)
|
||||||
#endif // not NetBSD < 6 / Solaris
|
#endif // not NetBSD < 6 / Solaris
|
||||||
|
|||||||
@ -145,8 +145,8 @@ bool path_search_long(struct shootpath_data *spd,int16 m,int16 x0,int16 y0,int16
|
|||||||
|
|
||||||
dx = (x1 - x0);
|
dx = (x1 - x0);
|
||||||
if (dx < 0) {
|
if (dx < 0) {
|
||||||
SWAP(x0, x1);
|
std::swap(x0, x1);
|
||||||
SWAP(y0, y1);
|
std::swap(y0, y1);
|
||||||
dx = -dx;
|
dx = -dx;
|
||||||
}
|
}
|
||||||
dy = (y1 - y0);
|
dy = (y1 - y0);
|
||||||
@ -198,13 +198,11 @@ bool path_search_long(struct shootpath_data *spd,int16 m,int16 x0,int16 y0,int16
|
|||||||
/// Pushes path_node to the binary node_heap.
|
/// Pushes path_node to the binary node_heap.
|
||||||
/// Ensures there is enough space in array to store new element.
|
/// Ensures there is enough space in array to store new element.
|
||||||
|
|
||||||
#define swap_ptrcast_pathnode(a, b) swap_ptrcast(struct path_node *, a, b)
|
|
||||||
|
|
||||||
static void heap_push_node(struct node_heap *heap, struct path_node *node)
|
static void heap_push_node(struct node_heap *heap, struct path_node *node)
|
||||||
{
|
{
|
||||||
#ifndef __clang_analyzer__ // TODO: Figure out why clang's static analyzer doesn't like this
|
#ifndef __clang_analyzer__ // TODO: Figure out why clang's static analyzer doesn't like this
|
||||||
BHEAP_ENSURE2(*heap, 1, 256, struct path_node **);
|
BHEAP_ENSURE2(*heap, 1, 256, struct path_node **);
|
||||||
BHEAP_PUSH2(*heap, node, NODE_MINTOPCMP, swap_ptrcast_pathnode);
|
BHEAP_PUSH2(*heap, node, NODE_MINTOPCMP);
|
||||||
#endif // __clang_analyzer__
|
#endif // __clang_analyzer__
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -217,7 +215,7 @@ static int heap_update_node(struct node_heap *heap, struct path_node *node)
|
|||||||
ShowError("heap_update_node: node not found\n");
|
ShowError("heap_update_node: node not found\n");
|
||||||
return 1;
|
return 1;
|
||||||
}
|
}
|
||||||
BHEAP_UPDATE(*heap, i, NODE_MINTOPCMP, swap_ptrcast_pathnode);
|
BHEAP_UPDATE(*heap, i, NODE_MINTOPCMP);
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -372,7 +370,7 @@ bool path_search(struct walkpath_data *wpd, int16 m, int16 x0, int16 y0, int16 x
|
|||||||
}
|
}
|
||||||
|
|
||||||
current = BHEAP_PEEK(g_open_set); // Look for the lowest f_cost node in the 'open' set
|
current = BHEAP_PEEK(g_open_set); // Look for the lowest f_cost node in the 'open' set
|
||||||
BHEAP_POP2(g_open_set, NODE_MINTOPCMP, swap_ptrcast_pathnode); // Remove it from 'open' set
|
BHEAP_POP2(g_open_set, NODE_MINTOPCMP); // Remove it from 'open' set
|
||||||
|
|
||||||
x = current->x;
|
x = current->x;
|
||||||
y = current->y;
|
y = current->y;
|
||||||
|
|||||||
@ -4288,6 +4288,7 @@ void pc_bonus(map_session_data *sd,int type,int val)
|
|||||||
case SP_LONG_SP_GAIN_VALUE:
|
case SP_LONG_SP_GAIN_VALUE:
|
||||||
if(!sd->state.lr_flag)
|
if(!sd->state.lr_flag)
|
||||||
sd->bonus.long_sp_gain_value += val;
|
sd->bonus.long_sp_gain_value += val;
|
||||||
|
break;
|
||||||
case SP_LONG_HP_GAIN_VALUE:
|
case SP_LONG_HP_GAIN_VALUE:
|
||||||
if(!sd->state.lr_flag)
|
if(!sd->state.lr_flag)
|
||||||
sd->bonus.long_hp_gain_value += val;
|
sd->bonus.long_hp_gain_value += val;
|
||||||
@ -8642,7 +8643,7 @@ int pc_need_status_point(map_session_data* sd, int type, int val)
|
|||||||
high = low + val;
|
high = low + val;
|
||||||
|
|
||||||
if ( val < 0 )
|
if ( val < 0 )
|
||||||
SWAP(low, high);
|
std::swap(low, high);
|
||||||
|
|
||||||
for ( ; low < high; low++ )
|
for ( ; low < high; low++ )
|
||||||
sp += PC_STATUS_POINT_COST(low);
|
sp += PC_STATUS_POINT_COST(low);
|
||||||
@ -8800,7 +8801,7 @@ int pc_need_trait_point(map_session_data* sd, int type, int val)
|
|||||||
int high = low + val, sp = 0;
|
int high = low + val, sp = 0;
|
||||||
|
|
||||||
if (val < 0)
|
if (val < 0)
|
||||||
SWAP(low, high);
|
std::swap(low, high);
|
||||||
|
|
||||||
for (; low < high; low++)
|
for (; low < high; low++)
|
||||||
sp += 1;
|
sp += 1;
|
||||||
@ -14104,19 +14105,11 @@ const std::string PlayerStatPointDatabase::getDefaultLocation() {
|
|||||||
}
|
}
|
||||||
|
|
||||||
uint64 PlayerStatPointDatabase::parseBodyNode(const ryml::NodeRef& node) {
|
uint64 PlayerStatPointDatabase::parseBodyNode(const ryml::NodeRef& node) {
|
||||||
if (!this->nodesExist(node, { "Level", "Points" })) {
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
uint16 level;
|
uint16 level;
|
||||||
|
|
||||||
if (!this->asUInt16(node, "Level", level))
|
if (!this->asUInt16(node, "Level", level))
|
||||||
return 0;
|
return 0;
|
||||||
|
|
||||||
uint32 point;
|
|
||||||
|
|
||||||
if (!this->asUInt32(node, "Points", point))
|
|
||||||
return 0;
|
|
||||||
|
|
||||||
if (level == 0) {
|
if (level == 0) {
|
||||||
this->invalidWarning(node["Level"], "The minimum level is 1.\n");
|
this->invalidWarning(node["Level"], "The minimum level is 1.\n");
|
||||||
@ -14132,19 +14125,32 @@ uint64 PlayerStatPointDatabase::parseBodyNode(const ryml::NodeRef& node) {
|
|||||||
bool exists = entry != nullptr;
|
bool exists = entry != nullptr;
|
||||||
|
|
||||||
if( !exists ){
|
if( !exists ){
|
||||||
entry = std::make_shared<s_statpoint_entry>();
|
if( !this->nodesExist( node, { "Points" } ) ){
|
||||||
entry->level = level;
|
return 0;
|
||||||
entry->statpoints = point;
|
}
|
||||||
|
|
||||||
|
entry = std::make_shared<s_statpoint_entry>();
|
||||||
|
entry->level = level;
|
||||||
}
|
}
|
||||||
|
|
||||||
if( this->nodeExists( node, "TraitPoints" ) ){
|
if( this->nodeExists( node, "Points" ) ){
|
||||||
uint32 traitpoints;
|
uint32 points;
|
||||||
|
|
||||||
if( !this->asUInt32( node, "TraitPoints", traitpoints ) ){
|
if( !this->asUInt32( node, "Points", points ) ){
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
entry->traitpoints = traitpoints;
|
entry->statpoints = points;
|
||||||
|
}
|
||||||
|
|
||||||
|
if( this->nodeExists( node, "TraitPoints" ) ){
|
||||||
|
uint32 traitpoints;
|
||||||
|
|
||||||
|
if( !this->asUInt32( node, "TraitPoints", traitpoints ) ){
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
entry->traitpoints = traitpoints;
|
||||||
}else{
|
}else{
|
||||||
if( !exists ){
|
if( !exists ){
|
||||||
entry->traitpoints = 0;
|
entry->traitpoints = 0;
|
||||||
|
|||||||
@ -2472,8 +2472,7 @@ void script_warning(const char* src, const char* file, int start_line, const cha
|
|||||||
/*==========================================
|
/*==========================================
|
||||||
* Analysis of the script
|
* Analysis of the script
|
||||||
*------------------------------------------*/
|
*------------------------------------------*/
|
||||||
struct script_code* parse_script(const char *src,const char *file,int line,int options)
|
struct script_code* parse_script_( const char *src, const char *file, int line, int options, const char* src_file, int src_line, const char* src_func ){
|
||||||
{
|
|
||||||
const char *p,*tmpp;
|
const char *p,*tmpp;
|
||||||
int i;
|
int i;
|
||||||
struct script_code* code = NULL;
|
struct script_code* code = NULL;
|
||||||
@ -2653,7 +2652,7 @@ struct script_code* parse_script(const char *src,const char *file,int line,int o
|
|||||||
}
|
}
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
CREATE(code,struct script_code,1);
|
CREATE2( code, struct script_code, 1, src_file, src_line, src_func );
|
||||||
code->script_buf = script_buf;
|
code->script_buf = script_buf;
|
||||||
code->script_size = script_size;
|
code->script_size = script_size;
|
||||||
code->local.vars = NULL;
|
code->local.vars = NULL;
|
||||||
@ -5566,33 +5565,51 @@ BUILDIN_FUNC(return)
|
|||||||
return SCRIPT_CMD_SUCCESS;
|
return SCRIPT_CMD_SUCCESS;
|
||||||
}
|
}
|
||||||
|
|
||||||
/// Returns a random number from 0 to <range>-1.
|
/// Returns a random number.
|
||||||
/// Or returns a random number from <min> to <max>.
|
/// rand(<range>) -> <int64> in the mathematical range [0, <range - 1>]
|
||||||
/// If <min> is greater than <max>, their numbers are switched.
|
/// rand(<min>,<max>) -> <int64> in the mathematical range [<min>, <max>]
|
||||||
/// rand(<range>) -> <int>
|
|
||||||
/// rand(<min>,<max>) -> <int>
|
|
||||||
BUILDIN_FUNC(rand)
|
BUILDIN_FUNC(rand)
|
||||||
{
|
{
|
||||||
int range;
|
int64 minimum;
|
||||||
int min;
|
int64 maximum;
|
||||||
|
|
||||||
if( script_hasdata(st,3) )
|
// min,max
|
||||||
{// min,max
|
if( script_hasdata( st, 3 ) ){
|
||||||
int max = script_getnum(st,3);
|
minimum = script_getnum64( st, 2 );
|
||||||
min = script_getnum(st,2);
|
maximum = script_getnum64( st, 3 );
|
||||||
if( max < min )
|
|
||||||
SWAP(min, max);
|
if( minimum > maximum ){
|
||||||
range = max;
|
ShowWarning( "buildin_rand: minimum (%" PRId64 ") is bigger than maximum (%" PRId64 ").\n", minimum, maximum );
|
||||||
|
// rnd_value already fixes this by swapping minimum and maximum automatically
|
||||||
|
}
|
||||||
|
// range
|
||||||
|
}else{
|
||||||
|
minimum = 0;
|
||||||
|
maximum = script_getnum64( st, 2 );
|
||||||
|
|
||||||
|
if( maximum < 0 ){
|
||||||
|
ShowError( "buildin_rand: range (%" PRId64 ") is negative.\n", maximum );
|
||||||
|
st->state = END;
|
||||||
|
return SCRIPT_CMD_FAILURE;
|
||||||
|
}
|
||||||
|
|
||||||
|
// The range version is exclusive maximum
|
||||||
|
maximum -= 1;
|
||||||
|
|
||||||
|
if( maximum < 1 ){
|
||||||
|
ShowError( "buildin_rand: range (%" PRId64 ") is too small. No randomness possible.\n", maximum );
|
||||||
|
st->state = END;
|
||||||
|
return SCRIPT_CMD_FAILURE;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
else
|
|
||||||
{// range
|
if( minimum == maximum ){
|
||||||
min = 0;
|
ShowError( "buildin_rand: minimum (%" PRId64 ") and maximum (%" PRId64 ") are equal. No randomness possible.\n", minimum, maximum );
|
||||||
range = script_getnum( st, 2 ) - 1;
|
st->state = END;
|
||||||
|
return SCRIPT_CMD_FAILURE;
|
||||||
}
|
}
|
||||||
if( range <= 1 )
|
|
||||||
script_pushint(st, min);
|
script_pushint64( st, rnd_value( minimum, maximum ) );
|
||||||
else
|
|
||||||
script_pushint( st, rnd_value( min, range ) );
|
|
||||||
|
|
||||||
return SCRIPT_CMD_SUCCESS;
|
return SCRIPT_CMD_SUCCESS;
|
||||||
}
|
}
|
||||||
@ -5690,8 +5707,8 @@ BUILDIN_FUNC(areawarp)
|
|||||||
y3 = 0;
|
y3 = 0;
|
||||||
} else if( x3 && y3 ) {
|
} else if( x3 && y3 ) {
|
||||||
// normalize x3/y3 coordinates
|
// normalize x3/y3 coordinates
|
||||||
if( x3 < x2 ) SWAP(x3,x2);
|
if( x3 < x2 ) std::swap(x3,x2);
|
||||||
if( y3 < y2 ) SWAP(y3,y2);
|
if( y3 < y2 ) std::swap(y3,y2);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -5865,13 +5882,13 @@ BUILDIN_FUNC(warpparty)
|
|||||||
case WARPPARTY_LEADER:
|
case WARPPARTY_LEADER:
|
||||||
if (p->party.member[i].leader)
|
if (p->party.member[i].leader)
|
||||||
continue;
|
continue;
|
||||||
// Fall through
|
[[fallthrough]];
|
||||||
case WARPPARTY_RANDOMALL:
|
case WARPPARTY_RANDOMALL:
|
||||||
if (pl_sd == sd) {
|
if (pl_sd == sd) {
|
||||||
ret = pc_setpos(pl_sd, mapindex, x, y, CLR_TELEPORT);
|
ret = pc_setpos(pl_sd, mapindex, x, y, CLR_TELEPORT);
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
// Fall through
|
[[fallthrough]];
|
||||||
case WARPPARTY_RANDOMALLAREA:
|
case WARPPARTY_RANDOMALLAREA:
|
||||||
if(!mapdata->getMapFlag(MF_NORETURN) && !mapdata->getMapFlag(MF_NOWARP) && pc_job_can_entermap((enum e_job)pl_sd->status.class_, m, pc_get_group_level(pl_sd))){
|
if(!mapdata->getMapFlag(MF_NORETURN) && !mapdata->getMapFlag(MF_NOWARP) && pc_job_can_entermap((enum e_job)pl_sd->status.class_, m, pc_get_group_level(pl_sd))){
|
||||||
if (rx || ry) {
|
if (rx || ry) {
|
||||||
@ -15713,6 +15730,7 @@ BUILDIN_FUNC(recovery)
|
|||||||
map_idx = sd->bl.m;
|
map_idx = sd->bl.m;
|
||||||
if(map_idx < 1)
|
if(map_idx < 1)
|
||||||
return SCRIPT_CMD_FAILURE; //No sd and no map given - return
|
return SCRIPT_CMD_FAILURE; //No sd and no map given - return
|
||||||
|
[[fallthrough]];
|
||||||
case 4:
|
case 4:
|
||||||
{
|
{
|
||||||
struct s_mapiterator *iter;
|
struct s_mapiterator *iter;
|
||||||
@ -17940,15 +17958,25 @@ BUILDIN_FUNC(npcshopitem)
|
|||||||
nd->u.shop.count = 0;
|
nd->u.shop.count = 0;
|
||||||
for (n = 0, i = 3; n < amount; n++, i+=offs) {
|
for (n = 0, i = 3; n < amount; n++, i+=offs) {
|
||||||
t_itemid nameid = script_getnum( st, i );
|
t_itemid nameid = script_getnum( st, i );
|
||||||
|
std::shared_ptr<item_data> id = item_db.find(nameid);
|
||||||
|
|
||||||
if( !item_db.exists( nameid ) ){
|
if( !id ){
|
||||||
ShowError( "builtin_npcshopitem: Item ID %u does not exist.\n", nameid );
|
ShowError( "builtin_npcshopitem: Item ID %u does not exist.\n", nameid );
|
||||||
script_pushint( st, 0 );
|
script_pushint( st, 0 );
|
||||||
return SCRIPT_CMD_FAILURE;
|
return SCRIPT_CMD_FAILURE;
|
||||||
}
|
}
|
||||||
|
int32 price = script_getnum(st, i + 1);
|
||||||
|
if (price < 0) {
|
||||||
|
if (nd->subtype == NPCTYPE_CASHSHOP || nd->subtype == NPCTYPE_POINTSHOP || nd->subtype == NPCTYPE_ITEMSHOP) {
|
||||||
|
ShowError("builtin_npcshopitem: Invalid price in shop '%s'.\n", nd->exname);
|
||||||
|
script_pushint(st, 0);
|
||||||
|
return SCRIPT_CMD_FAILURE;
|
||||||
|
}
|
||||||
|
price = id->value_buy;
|
||||||
|
}
|
||||||
|
|
||||||
nd->u.shop.shop_item[n].nameid = nameid;
|
nd->u.shop.shop_item[n].nameid = nameid;
|
||||||
nd->u.shop.shop_item[n].value = script_getnum(st,i+1);
|
nd->u.shop.shop_item[n].value = price;
|
||||||
#if PACKETVER >= 20131223
|
#if PACKETVER >= 20131223
|
||||||
if (nd->subtype == NPCTYPE_MARKETSHOP) {
|
if (nd->subtype == NPCTYPE_MARKETSHOP) {
|
||||||
nd->u.shop.shop_item[n].qty = script_getnum(st,i+2);
|
nd->u.shop.shop_item[n].qty = script_getnum(st,i+2);
|
||||||
@ -17985,8 +18013,9 @@ BUILDIN_FUNC(npcshopadditem)
|
|||||||
for (int n = 0, i = 3; n < amount; n++, i += offs) {
|
for (int n = 0, i = 3; n < amount; n++, i += offs) {
|
||||||
t_itemid nameid = script_getnum(st,i);
|
t_itemid nameid = script_getnum(st,i);
|
||||||
uint16 j;
|
uint16 j;
|
||||||
|
std::shared_ptr<item_data> id = item_db.find(nameid);
|
||||||
|
|
||||||
if( !item_db.exists( nameid ) ){
|
if( !id ){
|
||||||
ShowError( "builtin_npcshopadditem: Item ID %u does not exist.\n", nameid );
|
ShowError( "builtin_npcshopadditem: Item ID %u does not exist.\n", nameid );
|
||||||
script_pushint( st, 0 );
|
script_pushint( st, 0 );
|
||||||
return SCRIPT_CMD_FAILURE;
|
return SCRIPT_CMD_FAILURE;
|
||||||
@ -18001,8 +18030,12 @@ BUILDIN_FUNC(npcshopadditem)
|
|||||||
nd->u.shop.count++;
|
nd->u.shop.count++;
|
||||||
}
|
}
|
||||||
|
|
||||||
int32 stock = script_getnum( st, i + 2 );
|
int32 price = script_getnum(st, i + 1);
|
||||||
|
if (price < 0) {
|
||||||
|
price = id->value_buy;
|
||||||
|
}
|
||||||
|
|
||||||
|
int32 stock = script_getnum(st, i + 2);
|
||||||
if( stock < -1 ){
|
if( stock < -1 ){
|
||||||
ShowError( "builtin_npcshopadditem: Invalid stock amount in marketshop '%s'.\n", nd->exname );
|
ShowError( "builtin_npcshopadditem: Invalid stock amount in marketshop '%s'.\n", nd->exname );
|
||||||
script_pushint( st, 0 );
|
script_pushint( st, 0 );
|
||||||
@ -18010,7 +18043,7 @@ BUILDIN_FUNC(npcshopadditem)
|
|||||||
}
|
}
|
||||||
|
|
||||||
nd->u.shop.shop_item[j].nameid = nameid;
|
nd->u.shop.shop_item[j].nameid = nameid;
|
||||||
nd->u.shop.shop_item[j].value = script_getnum(st,i+1);
|
nd->u.shop.shop_item[j].value = price;
|
||||||
nd->u.shop.shop_item[j].qty = stock;
|
nd->u.shop.shop_item[j].qty = stock;
|
||||||
|
|
||||||
npc_market_tosql(nd->exname, &nd->u.shop.shop_item[j]);
|
npc_market_tosql(nd->exname, &nd->u.shop.shop_item[j]);
|
||||||
@ -18025,15 +18058,24 @@ BUILDIN_FUNC(npcshopadditem)
|
|||||||
for (int n = nd->u.shop.count, i = 3, j = 0; j < amount; n++, i+=offs, j++)
|
for (int n = nd->u.shop.count, i = 3, j = 0; j < amount; n++, i+=offs, j++)
|
||||||
{
|
{
|
||||||
t_itemid nameid = script_getnum( st, i );
|
t_itemid nameid = script_getnum( st, i );
|
||||||
|
std::shared_ptr<item_data> id = item_db.find(nameid);
|
||||||
|
|
||||||
if( !item_db.exists( nameid ) ){
|
if( !id ){
|
||||||
ShowError( "builtin_npcshopadditem: Item ID %u does not exist.\n", nameid );
|
ShowError( "builtin_npcshopadditem: Item ID %u does not exist.\n", nameid );
|
||||||
script_pushint( st, 0 );
|
script_pushint( st, 0 );
|
||||||
return SCRIPT_CMD_FAILURE;
|
return SCRIPT_CMD_FAILURE;
|
||||||
}
|
}
|
||||||
|
int32 price = script_getnum(st, i + 1);
|
||||||
|
if (price < 0) {
|
||||||
|
if (nd->subtype == NPCTYPE_CASHSHOP || nd->subtype == NPCTYPE_POINTSHOP || nd->subtype == NPCTYPE_ITEMSHOP) {
|
||||||
|
ShowError("builtin_npcshopadditem: Invalid price in shop '%s'.\n", nd->exname);
|
||||||
|
script_pushint(st, 0);
|
||||||
|
return SCRIPT_CMD_FAILURE;
|
||||||
|
}
|
||||||
|
price = id->value_buy;
|
||||||
|
}
|
||||||
nd->u.shop.shop_item[n].nameid = nameid;
|
nd->u.shop.shop_item[n].nameid = nameid;
|
||||||
nd->u.shop.shop_item[n].value = script_getnum(st,i+1);
|
nd->u.shop.shop_item[n].value = price;
|
||||||
nd->u.shop.count++;
|
nd->u.shop.count++;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -20326,8 +20368,8 @@ BUILDIN_FUNC(setcell)
|
|||||||
|
|
||||||
int x,y;
|
int x,y;
|
||||||
|
|
||||||
if( x1 > x2 ) SWAP(x1,x2);
|
if( x1 > x2 ) std::swap(x1,x2);
|
||||||
if( y1 > y2 ) SWAP(y1,y2);
|
if( y1 > y2 ) std::swap(y1,y2);
|
||||||
|
|
||||||
for( y = y1; y <= y2; ++y )
|
for( y = y1; y <= y2; ++y )
|
||||||
for( x = x1; x <= x2; ++x )
|
for( x = x1; x <= x2; ++x )
|
||||||
@ -23802,9 +23844,23 @@ BUILDIN_FUNC(npcshopupdate) {
|
|||||||
|
|
||||||
for (i = 0; i < nd->u.shop.count; i++) {
|
for (i = 0; i < nd->u.shop.count; i++) {
|
||||||
if (nd->u.shop.shop_item[i].nameid == nameid) {
|
if (nd->u.shop.shop_item[i].nameid == nameid) {
|
||||||
|
if (price != 0) {
|
||||||
if (price != 0)
|
if (price < 0) {
|
||||||
|
if (nd->subtype == NPCTYPE_CASHSHOP || nd->subtype == NPCTYPE_POINTSHOP || nd->subtype == NPCTYPE_ITEMSHOP) {
|
||||||
|
ShowError("builtin_npcshopupdate: Invalid price in shop '%s'.\n", nd->exname);
|
||||||
|
script_pushint(st, 0);
|
||||||
|
return SCRIPT_CMD_FAILURE;
|
||||||
|
}
|
||||||
|
std::shared_ptr<item_data> id = item_db.find(nameid);
|
||||||
|
if (!id) {
|
||||||
|
ShowError("buildin_npcshopupdate: Item ID %u does not exist.\n", nameid);
|
||||||
|
script_pushint(st, 0);
|
||||||
|
return SCRIPT_CMD_FAILURE;
|
||||||
|
}
|
||||||
|
price = id->value_buy;
|
||||||
|
}
|
||||||
nd->u.shop.shop_item[i].value = price;
|
nd->u.shop.shop_item[i].value = price;
|
||||||
|
}
|
||||||
#if PACKETVER >= 20131223
|
#if PACKETVER >= 20131223
|
||||||
if (nd->subtype == NPCTYPE_MARKETSHOP) {
|
if (nd->subtype == NPCTYPE_MARKETSHOP) {
|
||||||
nd->u.shop.shop_item[i].qty = stock;
|
nd->u.shop.shop_item[i].qty = stock;
|
||||||
|
|||||||
@ -10,6 +10,7 @@
|
|||||||
#include <common/database.hpp>
|
#include <common/database.hpp>
|
||||||
#include <common/cbasetypes.hpp>
|
#include <common/cbasetypes.hpp>
|
||||||
#include <common/db.hpp>
|
#include <common/db.hpp>
|
||||||
|
#include <common/malloc.hpp>
|
||||||
#include <common/mmo.hpp>
|
#include <common/mmo.hpp>
|
||||||
#include <common/timer.hpp>
|
#include <common/timer.hpp>
|
||||||
|
|
||||||
@ -2205,7 +2206,8 @@ void script_error(const char* src, const char* file, int start_line, const char*
|
|||||||
void script_warning(const char* src, const char* file, int start_line, const char* error_msg, const char* error_pos);
|
void script_warning(const char* src, const char* file, int start_line, const char* error_msg, const char* error_pos);
|
||||||
|
|
||||||
bool is_number(const char *p);
|
bool is_number(const char *p);
|
||||||
struct script_code* parse_script(const char* src,const char* file,int line,int options);
|
struct script_code* parse_script_( const char *src, const char *file, int line, int options, const char* src_file, int src_line, const char* src_func );
|
||||||
|
#define parse_script( src, file, line, options ) parse_script_( ( src ), ( file ), ( line ), ( options ), ALC_MARK )
|
||||||
void run_script(struct script_code *rootscript,int pos,int rid,int oid);
|
void run_script(struct script_code *rootscript,int pos,int rid,int oid);
|
||||||
|
|
||||||
bool set_reg_num(struct script_state* st, map_session_data* sd, int64 num, const char* name, const int64 value, struct reg_db *ref);
|
bool set_reg_num(struct script_state* st, map_session_data* sd, int64 num, const char* name, const int64 value, struct reg_db *ref);
|
||||||
|
|||||||
@ -1894,6 +1894,12 @@
|
|||||||
export_constant(SC_RUSH_QUAKE1);
|
export_constant(SC_RUSH_QUAKE1);
|
||||||
export_constant(SC_RUSH_QUAKE2);
|
export_constant(SC_RUSH_QUAKE2);
|
||||||
export_constant(SC_G_LIFEPOTION);
|
export_constant(SC_G_LIFEPOTION);
|
||||||
|
export_constant(SC_HNNOWEAPON);
|
||||||
|
export_constant(SC_SHIELDCHAINRUSH);
|
||||||
|
export_constant(SC_MISTYFROST);
|
||||||
|
export_constant(SC_GROUNDGRAVITY);
|
||||||
|
export_constant(SC_BREAKINGLIMIT);
|
||||||
|
export_constant(SC_RULEBREAK);
|
||||||
|
|
||||||
#ifdef RENEWAL
|
#ifdef RENEWAL
|
||||||
export_constant(SC_EXTREMITYFIST2);
|
export_constant(SC_EXTREMITYFIST2);
|
||||||
@ -10065,12 +10071,21 @@
|
|||||||
export_constant(UNT_LIGHTNING_LAND);
|
export_constant(UNT_LIGHTNING_LAND);
|
||||||
export_constant(UNT_VENOM_SWAMP);
|
export_constant(UNT_VENOM_SWAMP);
|
||||||
export_constant(UNT_CONFLAGRATION);
|
export_constant(UNT_CONFLAGRATION);
|
||||||
|
|
||||||
export_constant(UNT_DEEPBLINDTRAP);
|
export_constant(UNT_DEEPBLINDTRAP);
|
||||||
export_constant(UNT_SOLIDTRAP);
|
export_constant(UNT_SOLIDTRAP);
|
||||||
export_constant(UNT_SWIFTTRAP);
|
export_constant(UNT_SWIFTTRAP);
|
||||||
export_constant(UNT_FLAMETRAP);
|
export_constant(UNT_FLAMETRAP);
|
||||||
|
export_constant(UNT_TWINKLING_GALAXY);
|
||||||
|
export_constant(UNT_STAR_CANNON);
|
||||||
|
export_constant(UNT_GRENADES_DROPPING);
|
||||||
|
export_constant(UNT_FUUMASHOUAKU);
|
||||||
|
export_constant(UNT_MISSION_BOMBARD);
|
||||||
|
export_constant(UNT_TOTEM_OF_TUTELARY);
|
||||||
|
export_constant(UNT_HYUN_ROKS_BREEZE);
|
||||||
|
export_constant(UNT_SHINKIROU);
|
||||||
|
export_constant(UNT_JACK_FROST_NOVA);
|
||||||
|
export_constant(UNT_GROUND_GRAVITATION);
|
||||||
|
export_constant(UNT_KUNAIWAIKYOKU);
|
||||||
export_constant(UNT_GD_LEADERSHIP);
|
export_constant(UNT_GD_LEADERSHIP);
|
||||||
export_constant(UNT_GD_GLORYWOUNDS);
|
export_constant(UNT_GD_GLORYWOUNDS);
|
||||||
export_constant(UNT_GD_SOULCOLD);
|
export_constant(UNT_GD_SOULCOLD);
|
||||||
|
|||||||
@ -187,7 +187,7 @@ void searchstore_query(map_session_data* sd, unsigned char type, unsigned int mi
|
|||||||
}
|
}
|
||||||
|
|
||||||
if( max_price < min_price )
|
if( max_price < min_price )
|
||||||
SWAP(min_price, max_price);
|
std::swap(min_price, max_price);
|
||||||
|
|
||||||
sd->searchstore.uses--;
|
sd->searchstore.uses--;
|
||||||
sd->searchstore.type = type;
|
sd->searchstore.type = type;
|
||||||
|
|||||||
@ -1424,6 +1424,7 @@ int skill_additional_effect( struct block_list* src, struct block_list *bl, uint
|
|||||||
case AS_VENOMKNIFE:
|
case AS_VENOMKNIFE:
|
||||||
if (sd) //Poison chance must be that of Envenom. [Skotlex]
|
if (sd) //Poison chance must be that of Envenom. [Skotlex]
|
||||||
skill_lv = pc_checkskill(sd, TF_POISON);
|
skill_lv = pc_checkskill(sd, TF_POISON);
|
||||||
|
[[fallthrough]];
|
||||||
case TF_POISON:
|
case TF_POISON:
|
||||||
case AS_SPLASHER:
|
case AS_SPLASHER:
|
||||||
if(!sc_start2(src,bl,SC_POISON,(4*skill_lv+10),skill_lv,src->id,skill_get_time2(skill_id,skill_lv))
|
if(!sc_start2(src,bl,SC_POISON,(4*skill_lv+10),skill_lv,src->id,skill_get_time2(skill_id,skill_lv))
|
||||||
@ -1433,6 +1434,7 @@ int skill_additional_effect( struct block_list* src, struct block_list *bl, uint
|
|||||||
break;
|
break;
|
||||||
|
|
||||||
case AS_SONICBLOW:
|
case AS_SONICBLOW:
|
||||||
|
case HN_MEGA_SONIC_BLOW:
|
||||||
sc_start(src,bl,SC_STUN,(2*skill_lv+10),skill_lv,skill_get_time2(skill_id,skill_lv));
|
sc_start(src,bl,SC_STUN,(2*skill_lv+10),skill_lv,skill_get_time2(skill_id,skill_lv));
|
||||||
break;
|
break;
|
||||||
|
|
||||||
@ -1479,6 +1481,7 @@ int skill_additional_effect( struct block_list* src, struct block_list *bl, uint
|
|||||||
break;
|
break;
|
||||||
|
|
||||||
case WZ_METEOR:
|
case WZ_METEOR:
|
||||||
|
case HN_METEOR_STORM_BUSTER:
|
||||||
sc_start(src,bl,SC_STUN,3*skill_lv,skill_lv,skill_get_time2(skill_id,skill_lv));
|
sc_start(src,bl,SC_STUN,3*skill_lv,skill_lv,skill_get_time2(skill_id,skill_lv));
|
||||||
break;
|
break;
|
||||||
|
|
||||||
@ -1568,7 +1571,7 @@ int skill_additional_effect( struct block_list* src, struct block_list *bl, uint
|
|||||||
#ifndef RENEWAL
|
#ifndef RENEWAL
|
||||||
case PA_PRESSURE:
|
case PA_PRESSURE:
|
||||||
status_percent_damage(src, bl, 0, 15+5*skill_lv, false);
|
status_percent_damage(src, bl, 0, 15+5*skill_lv, false);
|
||||||
//Fall through
|
[[fallthrough]];
|
||||||
case HW_GRAVITATION:
|
case HW_GRAVITATION:
|
||||||
//Pressure and Gravitation can trigger physical autospells
|
//Pressure and Gravitation can trigger physical autospells
|
||||||
attack_type |= BF_NORMAL;
|
attack_type |= BF_NORMAL;
|
||||||
@ -1695,6 +1698,7 @@ int skill_additional_effect( struct block_list* src, struct block_list *bl, uint
|
|||||||
|
|
||||||
case LK_SPIRALPIERCE:
|
case LK_SPIRALPIERCE:
|
||||||
case ML_SPIRALPIERCE:
|
case ML_SPIRALPIERCE:
|
||||||
|
case HN_SPIRAL_PIERCE_MAX:
|
||||||
if( dstsd || ( dstmd && !status_bl_has_mode(bl,MD_STATUSIMMUNE) ) ) //Does not work on status immune
|
if( dstsd || ( dstmd && !status_bl_has_mode(bl,MD_STATUSIMMUNE) ) ) //Does not work on status immune
|
||||||
sc_start(src,bl,SC_STOP,100,0,skill_get_time2(skill_id,skill_lv));
|
sc_start(src,bl,SC_STOP,100,0,skill_get_time2(skill_id,skill_lv));
|
||||||
break;
|
break;
|
||||||
@ -1728,6 +1732,7 @@ int skill_additional_effect( struct block_list* src, struct block_list *bl, uint
|
|||||||
break;
|
break;
|
||||||
|
|
||||||
case HW_NAPALMVULCAN:
|
case HW_NAPALMVULCAN:
|
||||||
|
case HN_NAPALM_VULCAN_STRIKE:
|
||||||
sc_start(src,bl,SC_CURSE,5*skill_lv,skill_lv,skill_get_time2(skill_id,skill_lv));
|
sc_start(src,bl,SC_CURSE,5*skill_lv,skill_lv,skill_get_time2(skill_id,skill_lv));
|
||||||
break;
|
break;
|
||||||
|
|
||||||
@ -2179,10 +2184,9 @@ int skill_additional_effect( struct block_list* src, struct block_list *bl, uint
|
|||||||
break;
|
break;
|
||||||
case TR_ROSEBLOSSOM:// Rose blossom seed can only bloom if the target is hit.
|
case TR_ROSEBLOSSOM:// Rose blossom seed can only bloom if the target is hit.
|
||||||
sc_start4(src, bl, SC_ROSEBLOSSOM, 100, skill_lv, TR_ROSEBLOSSOM_ATK, src->id, 0, skill_get_time(skill_id, skill_lv));
|
sc_start4(src, bl, SC_ROSEBLOSSOM, 100, skill_lv, TR_ROSEBLOSSOM_ATK, src->id, 0, skill_get_time(skill_id, skill_lv));
|
||||||
|
[[fallthrough]];
|
||||||
case WM_METALICSOUND:
|
case WM_METALICSOUND:
|
||||||
case WM_REVERBERATION:
|
case WM_REVERBERATION:
|
||||||
case TR_RHYTHMSHOOTING:
|
|
||||||
case TR_METALIC_FURY:
|
|
||||||
status_change_end(bl, SC_SOUNDBLEND);
|
status_change_end(bl, SC_SOUNDBLEND);
|
||||||
break;
|
break;
|
||||||
case EM_DIAMOND_STORM:
|
case EM_DIAMOND_STORM:
|
||||||
@ -2203,6 +2207,11 @@ int skill_additional_effect( struct block_list* src, struct block_list *bl, uint
|
|||||||
case MT_RUSH_QUAKE:
|
case MT_RUSH_QUAKE:
|
||||||
sc_start( src, bl, SC_RUSH_QUAKE1, 100, skill_lv, skill_get_time( skill_id, skill_lv ) );
|
sc_start( src, bl, SC_RUSH_QUAKE1, 100, skill_lv, skill_get_time( skill_id, skill_lv ) );
|
||||||
break;
|
break;
|
||||||
|
case HN_SHIELD_CHAIN_RUSH:
|
||||||
|
case HN_JACK_FROST_NOVA:
|
||||||
|
case HN_GROUND_GRAVITATION:
|
||||||
|
sc_start(src, bl, skill_get_sc(skill_id), 100, 0, skill_get_time2(skill_id, skill_lv));
|
||||||
|
break;
|
||||||
} //end switch skill_id
|
} //end switch skill_id
|
||||||
|
|
||||||
if (md && battle_config.summons_trigger_autospells && md->master_id && md->special_state.ai && md->special_state.ai != AI_ABR && md->special_state.ai != AI_BIONIC)
|
if (md && battle_config.summons_trigger_autospells && md->master_id && md->special_state.ai && md->special_state.ai != AI_ABR && md->special_state.ai != AI_BIONIC)
|
||||||
@ -3305,11 +3314,13 @@ void skill_combo(struct block_list* src,struct block_list *dsrc, struct block_li
|
|||||||
duration = 1;
|
duration = 1;
|
||||||
target_id = 0; // Will target current auto-target instead
|
target_id = 0; // Will target current auto-target instead
|
||||||
}
|
}
|
||||||
|
[[fallthrough]]; // so we can possibly cast TigerFist or straight to ExtremityFist
|
||||||
case CH_TIGERFIST:
|
case CH_TIGERFIST:
|
||||||
if (!duration && pc_checkskill(sd, CH_CHAINCRUSH) > 0 && sd->spiritball > 1) {
|
if (!duration && pc_checkskill(sd, CH_CHAINCRUSH) > 0 && sd->spiritball > 1) {
|
||||||
duration = 1;
|
duration = 1;
|
||||||
target_id = 0; // Will target current auto-target instead
|
target_id = 0; // Will target current auto-target instead
|
||||||
}
|
}
|
||||||
|
[[fallthrough]]; // so we can possibly cast ChainCrush or straight to ExtremityFist
|
||||||
case CH_CHAINCRUSH:
|
case CH_CHAINCRUSH:
|
||||||
if (!duration && pc_checkskill(sd, MO_EXTREMITYFIST) > 0 && sd->spiritball > 0 && sd->sc.getSCE(SC_EXPLOSIONSPIRITS)) {
|
if (!duration && pc_checkskill(sd, MO_EXTREMITYFIST) > 0 && sd->spiritball > 0 && sd->sc.getSCE(SC_EXPLOSIONSPIRITS)) {
|
||||||
duration = 1;
|
duration = 1;
|
||||||
@ -3814,7 +3825,7 @@ int64 skill_attack (int attack_type, struct block_list* src, struct block_list *
|
|||||||
if(src->type == BL_PC)
|
if(src->type == BL_PC)
|
||||||
dmg.blewcount = 10;
|
dmg.blewcount = 10;
|
||||||
dmg.amotion = 0; //Disable delay or attack will do no damage since source is dead by the time it takes effect. [Skotlex]
|
dmg.amotion = 0; //Disable delay or attack will do no damage since source is dead by the time it takes effect. [Skotlex]
|
||||||
// fall through
|
[[fallthrough]];
|
||||||
case KN_AUTOCOUNTER:
|
case KN_AUTOCOUNTER:
|
||||||
case NPC_CRITICALSLASH:
|
case NPC_CRITICALSLASH:
|
||||||
case TF_DOUBLE:
|
case TF_DOUBLE:
|
||||||
@ -3896,7 +3907,7 @@ int64 skill_attack (int attack_type, struct block_list* src, struct block_list *
|
|||||||
dmg.dmotion = clif_skill_damage(src, bl, tick, dmg.amotion, dmg.dmotion, damage, dmg.div_, skill_id, (flag&SD_LEVEL) ? -1 : skill_lv, DMG_SPLASH);
|
dmg.dmotion = clif_skill_damage(src, bl, tick, dmg.amotion, dmg.dmotion, damage, dmg.div_, skill_id, (flag&SD_LEVEL) ? -1 : skill_lv, DMG_SPLASH);
|
||||||
if( dsrc != src ) // avoid damage display redundancy
|
if( dsrc != src ) // avoid damage display redundancy
|
||||||
break;
|
break;
|
||||||
//Fall through
|
[[fallthrough]];
|
||||||
case HT_LANDMINE:
|
case HT_LANDMINE:
|
||||||
dmg.dmotion = clif_skill_damage(dsrc,bl,tick, dmg.amotion, dmg.dmotion, damage, dmg.div_, skill_id, -1, dmg_type);
|
dmg.dmotion = clif_skill_damage(dsrc,bl,tick, dmg.amotion, dmg.dmotion, damage, dmg.div_, skill_id, -1, dmg_type);
|
||||||
break;
|
break;
|
||||||
@ -3917,7 +3928,7 @@ int64 skill_attack (int attack_type, struct block_list* src, struct block_list *
|
|||||||
type = DMG_SPLASH;
|
type = DMG_SPLASH;
|
||||||
if (!(flag&SD_ANIMATION))
|
if (!(flag&SD_ANIMATION))
|
||||||
clif_skill_nodamage(dsrc, bl, skill_id, skill_lv, 1);
|
clif_skill_nodamage(dsrc, bl, skill_id, skill_lv, 1);
|
||||||
// Fall through
|
[[fallthrough]];
|
||||||
case WM_REVERBERATION:
|
case WM_REVERBERATION:
|
||||||
dmg.dmotion = clif_skill_damage(dsrc, bl, tick, dmg.amotion, dmg.dmotion, damage, dmg.div_, skill_id, -2, dmg_type);
|
dmg.dmotion = clif_skill_damage(dsrc, bl, tick, dmg.amotion, dmg.dmotion, damage, dmg.div_, skill_id, -2, dmg_type);
|
||||||
break;
|
break;
|
||||||
@ -3948,6 +3959,7 @@ int64 skill_attack (int attack_type, struct block_list* src, struct block_list *
|
|||||||
case AB_DUPLELIGHT_MELEE:
|
case AB_DUPLELIGHT_MELEE:
|
||||||
case AB_DUPLELIGHT_MAGIC:
|
case AB_DUPLELIGHT_MAGIC:
|
||||||
dmg.amotion = 300;/* makes the damage value not overlap with previous damage (when displayed by the client) */
|
dmg.amotion = 300;/* makes the damage value not overlap with previous damage (when displayed by the client) */
|
||||||
|
[[fallthrough]];
|
||||||
default:
|
default:
|
||||||
if( flag&SD_ANIMATION && dmg.div_ < 2 ) //Disabling skill animation doesn't works on multi-hit.
|
if( flag&SD_ANIMATION && dmg.div_ < 2 ) //Disabling skill animation doesn't works on multi-hit.
|
||||||
dmg_type = DMG_SPLASH;
|
dmg_type = DMG_SPLASH;
|
||||||
@ -4143,10 +4155,6 @@ int64 skill_attack (int attack_type, struct block_list* src, struct block_list *
|
|||||||
if (status_get_lv(src) > 29 && rnd() % 100 < 10 * status_get_lv(src) / 30)
|
if (status_get_lv(src) > 29 && rnd() % 100 < 10 * status_get_lv(src) / 30)
|
||||||
skill_addtimerskill(src, tick + dmg.amotion + skill_get_delay(skill_id, skill_lv), bl->id, 0, 0, skill_id, skill_lv, attack_type, flag|2);
|
skill_addtimerskill(src, tick + dmg.amotion + skill_get_delay(skill_id, skill_lv), bl->id, 0, 0, skill_id, skill_lv, attack_type, flag|2);
|
||||||
break;
|
break;
|
||||||
case ABC_DEFT_STAB:
|
|
||||||
if (skill_area_temp[1] == bl->id && rnd()%100 < 4 * skill_lv)// Need official autocast chance. [Rytech]
|
|
||||||
skill_addtimerskill(src, tick + dmg.amotion, bl->id, 0, 0, skill_id, skill_lv, BF_WEAPON, 2);
|
|
||||||
break;
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -4217,7 +4225,7 @@ static int skill_check_unit_range_sub(struct block_list *bl, va_list ap)
|
|||||||
case AL_PNEUMA: //Pneuma doesn't work even if just one cell overlaps with Land Protector
|
case AL_PNEUMA: //Pneuma doesn't work even if just one cell overlaps with Land Protector
|
||||||
if(g_skill_id == SA_LANDPROTECTOR)
|
if(g_skill_id == SA_LANDPROTECTOR)
|
||||||
break;
|
break;
|
||||||
//Fall through
|
[[fallthrough]];
|
||||||
case MH_STEINWAND:
|
case MH_STEINWAND:
|
||||||
case MG_SAFETYWALL:
|
case MG_SAFETYWALL:
|
||||||
case SC_MAELSTROM:
|
case SC_MAELSTROM:
|
||||||
@ -4604,7 +4612,8 @@ static TIMER_FUNC(skill_timerskill){
|
|||||||
if (unit)
|
if (unit)
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
} // Fall through
|
}
|
||||||
|
[[fallthrough]];
|
||||||
case WZ_JUPITEL:
|
case WZ_JUPITEL:
|
||||||
// Official behaviour is to hit as long as there is a line of sight, regardless of distance
|
// Official behaviour is to hit as long as there is a line of sight, regardless of distance
|
||||||
if (skl->type > 0 && !status_isdead(target) && path_search_long(NULL,src->m,src->x,src->y,target->x,target->y,CELL_CHKWALL)) {
|
if (skl->type > 0 && !status_isdead(target) && path_search_long(NULL,src->m,src->x,src->y,target->x,target->y,CELL_CHKWALL)) {
|
||||||
@ -4753,6 +4762,7 @@ static TIMER_FUNC(skill_timerskill){
|
|||||||
int dummy = 1, i = skill_get_unit_range(skl->skill_id,skl->skill_lv);
|
int dummy = 1, i = skill_get_unit_range(skl->skill_id,skl->skill_lv);
|
||||||
map_foreachinarea(skill_cell_overlap, src->m, skl->x-i, skl->y-i, skl->x+i, skl->y+i, BL_SKILL, skl->skill_id, &dummy, src);
|
map_foreachinarea(skill_cell_overlap, src->m, skl->x-i, skl->y-i, skl->x+i, skl->y+i, BL_SKILL, skl->skill_id, &dummy, src);
|
||||||
}
|
}
|
||||||
|
[[fallthrough]];
|
||||||
case WL_EARTHSTRAIN:
|
case WL_EARTHSTRAIN:
|
||||||
skill_unitsetting(src,skl->skill_id,skl->skill_lv,skl->x,skl->y,(skl->type<<16)|skl->flag);
|
skill_unitsetting(src,skl->skill_id,skl->skill_lv,skl->x,skl->y,(skl->type<<16)|skl->flag);
|
||||||
break;
|
break;
|
||||||
@ -4768,6 +4778,22 @@ static TIMER_FUNC(skill_timerskill){
|
|||||||
case NC_MAGMA_ERUPTION:
|
case NC_MAGMA_ERUPTION:
|
||||||
skill_unitsetting(src,skl->skill_id,skl->skill_lv,skl->x,skl->y,0);
|
skill_unitsetting(src,skl->skill_id,skl->skill_lv,skl->x,skl->y,0);
|
||||||
break;
|
break;
|
||||||
|
case HN_METEOR_STORM_BUSTER: {
|
||||||
|
int16 area = 4;
|
||||||
|
int16 tmpx = rnd_value( skl->x - area, skl->x + area );
|
||||||
|
int16 tmpy = rnd_value( skl->y - area, skl->y + area );
|
||||||
|
|
||||||
|
if( map_getcell(src->m, tmpx, tmpy, CELL_CHKLANDPROTECTOR) ) {
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
int splash = skill_get_splash(skl->skill_id, skl->skill_lv);
|
||||||
|
|
||||||
|
clif_skill_poseffect(src, skl->skill_id, skl->skill_lv, tmpx, tmpy, tick);
|
||||||
|
map_foreachinarea(skill_area_sub, src->m, tmpx - splash, tmpy - splash, tmpx + splash, tmpy + splash, BL_CHAR, src, skl->skill_id, skl->skill_lv, tick, skl->flag | BCT_ENEMY | SD_SPLASH | SKILL_ALTDMG_FLAG | 1, skill_castend_damage_id);
|
||||||
|
skill_unitsetting(src, skl->skill_id, skl->skill_lv, tmpx, tmpy, skill_get_unit_interval(skl->skill_id));
|
||||||
|
}
|
||||||
|
break;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
} while (0);
|
} while (0);
|
||||||
@ -5211,27 +5237,20 @@ int skill_castend_damage_id (struct block_list* src, struct block_list *bl, uint
|
|||||||
case MT_TRIPLE_LASER:
|
case MT_TRIPLE_LASER:
|
||||||
skill_attack(BF_WEAPON,src,src,bl,skill_id,skill_lv,tick,flag);
|
skill_attack(BF_WEAPON,src,src,bl,skill_id,skill_lv,tick,flag);
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case IG_SHIELD_SHOOTING:
|
|
||||||
clif_skill_nodamage(src, bl, skill_id, skill_lv, 1);
|
|
||||||
skill_attack(BF_WEAPON, src, src, bl, skill_id, skill_lv, tick, flag);
|
|
||||||
sc_start(src, src, SC_SHIELD_POWER, 100, skill_lv, skill_get_time(skill_id, skill_lv));
|
|
||||||
break;
|
|
||||||
case DK_DRAGONIC_AURA:
|
case DK_DRAGONIC_AURA:
|
||||||
case DK_STORMSLASH:
|
case DK_STORMSLASH:
|
||||||
case IG_GRAND_JUDGEMENT:
|
|
||||||
case CD_EFFLIGO:
|
case CD_EFFLIGO:
|
||||||
case ABC_FRENZY_SHOT:
|
case ABC_FRENZY_SHOT:
|
||||||
case WH_HAWKRUSH:
|
case WH_HAWKRUSH:
|
||||||
case WH_HAWKBOOMERANG:
|
case WH_HAWKBOOMERANG:
|
||||||
case TR_ROSEBLOSSOM:
|
case TR_ROSEBLOSSOM:
|
||||||
case TR_RHYTHMSHOOTING:
|
case TR_RHYTHMSHOOTING:
|
||||||
|
case HN_MEGA_SONIC_BLOW:
|
||||||
|
case HN_SPIRAL_PIERCE_MAX:
|
||||||
clif_skill_nodamage(src, bl, skill_id, skill_lv, 1);
|
clif_skill_nodamage(src, bl, skill_id, skill_lv, 1);
|
||||||
skill_attack(BF_WEAPON, src, src, bl, skill_id, skill_lv, tick, flag);
|
skill_attack(BF_WEAPON, src, src, bl, skill_id, skill_lv, tick, flag);
|
||||||
if (skill_id == DK_DRAGONIC_AURA)
|
if (skill_id == DK_DRAGONIC_AURA)
|
||||||
sc_start(src, src, SC_DRAGONIC_AURA, 100, skill_lv, skill_get_time(skill_id,skill_lv));
|
sc_start(src, src, SC_DRAGONIC_AURA, 100, skill_lv, skill_get_time(skill_id,skill_lv));
|
||||||
else if (skill_id == IG_GRAND_JUDGEMENT)
|
|
||||||
sc_start(src, src, SC_SPEAR_SCAR, 100, skill_lv, skill_get_time(skill_id, skill_lv));
|
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case SHC_ETERNAL_SLASH:
|
case SHC_ETERNAL_SLASH:
|
||||||
@ -5244,8 +5263,8 @@ int skill_castend_damage_id (struct block_list* src, struct block_list *bl, uint
|
|||||||
break;
|
break;
|
||||||
|
|
||||||
case SHC_SHADOW_STAB:
|
case SHC_SHADOW_STAB:
|
||||||
if (sc && (sc->getSCE(SC_CLOAKING) || sc->getSCE(SC_CLOAKINGEXCEED)))
|
if (sc && sc->getSCE(SC_CLOAKINGEXCEED))
|
||||||
flag |= 2;// Flag to deal 2 hits.
|
flag |= 2;// Flag to deal 3 hits.
|
||||||
|
|
||||||
status_change_end(src, SC_CLOAKING);
|
status_change_end(src, SC_CLOAKING);
|
||||||
status_change_end(src, SC_CLOAKINGEXCEED);
|
status_change_end(src, SC_CLOAKINGEXCEED);
|
||||||
@ -5360,6 +5379,7 @@ int skill_castend_damage_id (struct block_list* src, struct block_list *bl, uint
|
|||||||
#ifndef RENEWAL
|
#ifndef RENEWAL
|
||||||
case SN_SHARPSHOOTING:
|
case SN_SHARPSHOOTING:
|
||||||
flag |= 2; // Flag for specific mob damage formula
|
flag |= 2; // Flag for specific mob damage formula
|
||||||
|
[[fallthrough]];
|
||||||
#endif
|
#endif
|
||||||
case MA_SHARPSHOOTING:
|
case MA_SHARPSHOOTING:
|
||||||
case NJ_KAMAITACHI:
|
case NJ_KAMAITACHI:
|
||||||
@ -5515,6 +5535,7 @@ int skill_castend_damage_id (struct block_list* src, struct block_list *bl, uint
|
|||||||
|
|
||||||
case SU_PICKYPECK:
|
case SU_PICKYPECK:
|
||||||
clif_skill_nodamage(src, bl, skill_id, skill_lv, 1);
|
clif_skill_nodamage(src, bl, skill_id, skill_lv, 1);
|
||||||
|
[[fallthrough]];
|
||||||
case SU_BITE:
|
case SU_BITE:
|
||||||
skill_attack(BF_WEAPON, src, src, bl, skill_id, skill_lv, tick, flag);
|
skill_attack(BF_WEAPON, src, src, bl, skill_id, skill_lv, tick, flag);
|
||||||
break;
|
break;
|
||||||
@ -5530,6 +5551,7 @@ int skill_castend_damage_id (struct block_list* src, struct block_list *bl, uint
|
|||||||
case MC_CARTREVOLUTION:
|
case MC_CARTREVOLUTION:
|
||||||
case NPC_SPLASHATTACK:
|
case NPC_SPLASHATTACK:
|
||||||
flag |= SD_PREAMBLE; // a fake packet will be sent for the first target to be hit
|
flag |= SD_PREAMBLE; // a fake packet will be sent for the first target to be hit
|
||||||
|
[[fallthrough]];
|
||||||
case AS_SPLASHER:
|
case AS_SPLASHER:
|
||||||
case HT_BLITZBEAT:
|
case HT_BLITZBEAT:
|
||||||
case AC_SHOWER:
|
case AC_SHOWER:
|
||||||
@ -5671,6 +5693,10 @@ int skill_castend_damage_id (struct block_list* src, struct block_list *bl, uint
|
|||||||
case BO_EXPLOSIVE_POWDER:
|
case BO_EXPLOSIVE_POWDER:
|
||||||
case BO_MAYHEMIC_THORNS:
|
case BO_MAYHEMIC_THORNS:
|
||||||
case NPC_WIDECRITICALWOUND:
|
case NPC_WIDECRITICALWOUND:
|
||||||
|
case IG_SHIELD_SHOOTING:
|
||||||
|
case TR_METALIC_FURY:
|
||||||
|
case IG_GRAND_JUDGEMENT:
|
||||||
|
case HN_JUPITEL_THUNDER_STORM:
|
||||||
if( flag&1 ) {//Recursive invocation
|
if( flag&1 ) {//Recursive invocation
|
||||||
int sflag = skill_area_temp[0] & 0xFFF;
|
int sflag = skill_area_temp[0] & 0xFFF;
|
||||||
int heal = 0;
|
int heal = 0;
|
||||||
@ -5741,6 +5767,7 @@ int skill_castend_damage_id (struct block_list* src, struct block_list *bl, uint
|
|||||||
case DK_DRAGONIC_BREATH:
|
case DK_DRAGONIC_BREATH:
|
||||||
case DK_HACKANDSLASHER:
|
case DK_HACKANDSLASHER:
|
||||||
case MT_SPARK_BLASTER:
|
case MT_SPARK_BLASTER:
|
||||||
|
case HN_JUPITEL_THUNDER_STORM:
|
||||||
clif_skill_nodamage(src,bl,skill_id,skill_lv,1);
|
clif_skill_nodamage(src,bl,skill_id,skill_lv,1);
|
||||||
break;
|
break;
|
||||||
#ifdef RENEWAL
|
#ifdef RENEWAL
|
||||||
@ -5867,6 +5894,11 @@ int skill_castend_damage_id (struct block_list* src, struct block_list *bl, uint
|
|||||||
// TODO: does this buff start before or after dealing damage? [Muh]
|
// TODO: does this buff start before or after dealing damage? [Muh]
|
||||||
sc_start( src, src, SC_RUSH_QUAKE2, 100, skill_lv, skill_get_time2( skill_id, skill_lv ) );
|
sc_start( src, src, SC_RUSH_QUAKE2, 100, skill_lv, skill_get_time2( skill_id, skill_lv ) );
|
||||||
break;
|
break;
|
||||||
|
case IG_SHIELD_SHOOTING:
|
||||||
|
case IG_GRAND_JUDGEMENT:
|
||||||
|
clif_skill_nodamage(src, bl, skill_id, skill_lv, 1);
|
||||||
|
sc_start(src, src, skill_get_sc(skill_id), 100, skill_lv, skill_get_time(skill_id, skill_lv));
|
||||||
|
break;
|
||||||
}
|
}
|
||||||
|
|
||||||
// if skill damage should be split among targets, count them
|
// if skill damage should be split among targets, count them
|
||||||
@ -5886,24 +5918,6 @@ int skill_castend_damage_id (struct block_list* src, struct block_list *bl, uint
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
case TR_METALIC_FURY:
|
|
||||||
{
|
|
||||||
if (flag & 1) {
|
|
||||||
clif_skill_nodamage(src, bl, skill_id, skill_lv, 1);
|
|
||||||
skill_attack(skill_get_type(skill_id), src, src, bl, skill_id, skill_lv, tick, flag);
|
|
||||||
} else {
|
|
||||||
int area = skill_get_splash(skill_id, skill_lv);
|
|
||||||
int count = map_forcountinarea(skill_check_bl_sc,bl->m,bl->x - area,bl->y - area,bl->x + area,bl->y + area,5,BL_MOB,SC_SOUNDBLEND);
|
|
||||||
if (count > 0){
|
|
||||||
map_foreachinarea(skill_area_sub, bl->m, bl->x - area, bl->y - area, bl->x + area, bl->y + area, BL_CHAR,
|
|
||||||
src, skill_id, skill_lv, tick, flag | BCT_ENEMY | SD_SPLASH | 1, skill_castend_damage_id);
|
|
||||||
} else{
|
|
||||||
clif_skill_nodamage(src, bl, skill_id, skill_lv, 1);
|
|
||||||
skill_attack(skill_get_type(skill_id), src, src, bl, skill_id, skill_lv, tick, flag);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
break;
|
|
||||||
|
|
||||||
//Place units around target
|
//Place units around target
|
||||||
case NJ_BAKUENRYU:
|
case NJ_BAKUENRYU:
|
||||||
@ -6073,6 +6087,7 @@ int skill_castend_damage_id (struct block_list* src, struct block_list *bl, uint
|
|||||||
|
|
||||||
case AL_HOLYLIGHT:
|
case AL_HOLYLIGHT:
|
||||||
status_change_end(bl, SC_P_ALTER);
|
status_change_end(bl, SC_P_ALTER);
|
||||||
|
[[fallthrough]];
|
||||||
case MG_SOULSTRIKE:
|
case MG_SOULSTRIKE:
|
||||||
case NPC_DARKSTRIKE:
|
case NPC_DARKSTRIKE:
|
||||||
case MG_COLDBOLT:
|
case MG_COLDBOLT:
|
||||||
@ -6101,6 +6116,7 @@ int skill_castend_damage_id (struct block_list* src, struct block_list *bl, uint
|
|||||||
case AG_ASTRAL_STRIKE_ATK:
|
case AG_ASTRAL_STRIKE_ATK:
|
||||||
case AG_DESTRUCTIVE_HURRICANE_CLIMAX:
|
case AG_DESTRUCTIVE_HURRICANE_CLIMAX:
|
||||||
case CD_ARBITRIUM:
|
case CD_ARBITRIUM:
|
||||||
|
case HN_METEOR_STORM_BUSTER:
|
||||||
skill_attack(BF_MAGIC,src,src,bl,skill_id,skill_lv,tick,flag);
|
skill_attack(BF_MAGIC,src,src,bl,skill_id,skill_lv,tick,flag);
|
||||||
break;
|
break;
|
||||||
|
|
||||||
@ -6175,6 +6191,7 @@ int skill_castend_damage_id (struct block_list* src, struct block_list *bl, uint
|
|||||||
|
|
||||||
case SL_SMA:
|
case SL_SMA:
|
||||||
status_change_end(src, SC_SMA);
|
status_change_end(src, SC_SMA);
|
||||||
|
[[fallthrough]];
|
||||||
case SL_STIN:
|
case SL_STIN:
|
||||||
case SL_STUN:
|
case SL_STUN:
|
||||||
case SP_SPA:
|
case SP_SPA:
|
||||||
@ -6190,6 +6207,7 @@ int skill_castend_damage_id (struct block_list* src, struct block_list *bl, uint
|
|||||||
clif_emotion(src,ET_ANGER);
|
clif_emotion(src,ET_ANGER);
|
||||||
if (rnd() % 2 == 0)
|
if (rnd() % 2 == 0)
|
||||||
break; // 50% chance
|
break; // 50% chance
|
||||||
|
[[fallthrough]];
|
||||||
case SN_FALCONASSAULT:
|
case SN_FALCONASSAULT:
|
||||||
#ifndef RENEWAL
|
#ifndef RENEWAL
|
||||||
case PA_PRESSURE:
|
case PA_PRESSURE:
|
||||||
@ -6246,6 +6264,7 @@ int skill_castend_damage_id (struct block_list* src, struct block_list *bl, uint
|
|||||||
case NPC_SELFDESTRUCTION:
|
case NPC_SELFDESTRUCTION:
|
||||||
if( tsc && tsc->getSCE(SC_HIDING) )
|
if( tsc && tsc->getSCE(SC_HIDING) )
|
||||||
break;
|
break;
|
||||||
|
[[fallthrough]];
|
||||||
case HVAN_EXPLOSION:
|
case HVAN_EXPLOSION:
|
||||||
if (src != bl)
|
if (src != bl)
|
||||||
skill_attack(BF_MISC,src,src,bl,skill_id,skill_lv,tick,flag);
|
skill_attack(BF_MISC,src,src,bl,skill_id,skill_lv,tick,flag);
|
||||||
@ -6568,6 +6587,7 @@ int skill_castend_damage_id (struct block_list* src, struct block_list *bl, uint
|
|||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
[[fallthrough]];
|
||||||
case RA_WUGBITE:
|
case RA_WUGBITE:
|
||||||
if( path_search(NULL,src->m,src->x,src->y,bl->x,bl->y,1,CELL_CHKNOREACH) ) {
|
if( path_search(NULL,src->m,src->x,src->y,bl->x,bl->y,1,CELL_CHKNOREACH) ) {
|
||||||
skill_attack(BF_WEAPON,src,src,bl,skill_id,skill_lv,tick,flag);
|
skill_attack(BF_WEAPON,src,src,bl,skill_id,skill_lv,tick,flag);
|
||||||
@ -7021,6 +7041,44 @@ int skill_castend_damage_id (struct block_list* src, struct block_list *bl, uint
|
|||||||
sc_start(src, bl, SC_VENOMIMPRESS, 100, skill_lv, skill_get_time(skill_id,skill_lv));
|
sc_start(src, bl, SC_VENOMIMPRESS, 100, skill_lv, skill_get_time(skill_id,skill_lv));
|
||||||
break;
|
break;
|
||||||
|
|
||||||
|
case HN_DOUBLEBOWLINGBASH:
|
||||||
|
if (flag & 1) {
|
||||||
|
skill_attack(skill_get_type(skill_id), src, src, bl, skill_id, skill_lv, tick, skill_area_temp[0] & 0xFFF);
|
||||||
|
} else {
|
||||||
|
int splash = skill_get_splash(skill_id, skill_lv);
|
||||||
|
clif_skill_nodamage(src, bl, skill_id, skill_lv, 1);
|
||||||
|
skill_area_temp[0] = map_foreachinallrange(skill_area_sub, bl, splash, BL_CHAR, src, skill_id, skill_lv, tick, BCT_ENEMY, skill_area_sub_count);
|
||||||
|
map_foreachinrange(skill_area_sub, bl, splash, BL_CHAR, src, skill_id, skill_lv, tick, flag | BCT_ENEMY | SD_SPLASH | 1, skill_castend_damage_id);
|
||||||
|
sc_start(src, src, SC_HNNOWEAPON, 100, skill_lv, skill_get_time2(skill_id, skill_lv));
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
|
||||||
|
case HN_SHIELD_CHAIN_RUSH:
|
||||||
|
if (flag & 1) {
|
||||||
|
skill_attack(skill_get_type(skill_id), src, src, bl, skill_id, skill_lv, tick, flag);
|
||||||
|
} else {
|
||||||
|
clif_skill_nodamage(src, bl, skill_id, skill_lv, 1);
|
||||||
|
map_foreachinrange(skill_area_sub, bl, skill_get_splash(skill_id, skill_lv), BL_CHAR, src, skill_id, skill_lv, tick, flag | BCT_ENEMY | SD_SPLASH | 1, skill_castend_damage_id);
|
||||||
|
sc_start(src, src, SC_HNNOWEAPON, 100, skill_lv, skill_get_time2(skill_id, skill_lv));
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
|
||||||
|
case HN_JACK_FROST_NOVA:
|
||||||
|
case HN_HELLS_DRIVE:
|
||||||
|
case HN_GROUND_GRAVITATION:
|
||||||
|
if (flag & 1)
|
||||||
|
skill_attack(skill_get_type(skill_id), src, src, bl, skill_id, skill_lv, tick, flag);
|
||||||
|
break;
|
||||||
|
|
||||||
|
case HN_NAPALM_VULCAN_STRIKE:
|
||||||
|
if (flag & 1) {
|
||||||
|
skill_attack(skill_get_type(skill_id), src, src, bl, skill_id, skill_lv, tick, flag);
|
||||||
|
} else {
|
||||||
|
clif_skill_nodamage(src, bl, skill_id, skill_lv, 1);
|
||||||
|
map_foreachinrange(skill_area_sub, bl, skill_get_splash(skill_id, skill_lv), BL_CHAR, src, skill_id, skill_lv, tick, flag | BCT_ENEMY | SD_SPLASH | 1, skill_castend_damage_id);
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
|
||||||
default:
|
default:
|
||||||
ShowWarning("skill_castend_damage_id: Unknown skill used:%d\n",skill_id);
|
ShowWarning("skill_castend_damage_id: Unknown skill used:%d\n",skill_id);
|
||||||
clif_skill_damage(src, bl, tick, status_get_amotion(src), tstatus->dmotion,
|
clif_skill_damage(src, bl, tick, status_get_amotion(src), tstatus->dmotion,
|
||||||
@ -7204,6 +7262,7 @@ int skill_castend_nodamage_id (struct block_list *src, struct block_list *bl, ui
|
|||||||
if (sd) clif_skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0) ;
|
if (sd) clif_skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0) ;
|
||||||
break ;
|
break ;
|
||||||
}
|
}
|
||||||
|
[[fallthrough]];
|
||||||
case AL_HEAL:
|
case AL_HEAL:
|
||||||
case ALL_RESURRECTION:
|
case ALL_RESURRECTION:
|
||||||
case PR_ASPERSIO:
|
case PR_ASPERSIO:
|
||||||
@ -7332,11 +7391,14 @@ int skill_castend_nodamage_id (struct block_list *src, struct block_list *bl, ui
|
|||||||
#endif
|
#endif
|
||||||
status_set_hp(src, 1, 0);
|
status_set_hp(src, 1, 0);
|
||||||
break;
|
break;
|
||||||
} else if (status_isdead(bl) && flag&1) { //Revive
|
} else if (!(status_isdead(bl) && flag&1)) {
|
||||||
skill_area_temp[0]++; //Count it in, then fall-through to the Resurrection code.
|
//Invalid target, skip resurrection.
|
||||||
skill_lv = 3; //Resurrection level 3 is used
|
|
||||||
} else //Invalid target, skip resurrection.
|
|
||||||
break;
|
break;
|
||||||
|
}
|
||||||
|
//Revive
|
||||||
|
skill_area_temp[0]++; //Count it in, then fall-through to the Resurrection code.
|
||||||
|
skill_lv = 3; //Resurrection level 3 is used
|
||||||
|
[[fallthrough]];
|
||||||
|
|
||||||
case ALL_RESURRECTION:
|
case ALL_RESURRECTION:
|
||||||
if(sd && (map_flag_gvg2(bl->m) || map_getmapflag(bl->m, MF_BATTLEGROUND)))
|
if(sd && (map_flag_gvg2(bl->m) || map_getmapflag(bl->m, MF_BATTLEGROUND)))
|
||||||
@ -7506,7 +7568,8 @@ int skill_castend_nodamage_id (struct block_list *src, struct block_list *bl, ui
|
|||||||
break;
|
break;
|
||||||
case SA_SUMMONMONSTER:
|
case SA_SUMMONMONSTER:
|
||||||
clif_skill_nodamage(src,bl,skill_id,skill_lv,1);
|
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);
|
if (sd)
|
||||||
|
mob_once_spawn(sd, src->m, src->x, src->y,"--ja--", -1, 1, "", SZ_SMALL, AI_NONE);
|
||||||
break;
|
break;
|
||||||
case SA_LEVELUP:
|
case SA_LEVELUP:
|
||||||
clif_skill_nodamage(src,bl,skill_id,skill_lv,1);
|
clif_skill_nodamage(src,bl,skill_id,skill_lv,1);
|
||||||
@ -7519,6 +7582,7 @@ int skill_castend_nodamage_id (struct block_list *src, struct block_list *bl, ui
|
|||||||
break;
|
break;
|
||||||
case SA_QUESTION:
|
case SA_QUESTION:
|
||||||
clif_emotion(src,ET_QUESTION);
|
clif_emotion(src,ET_QUESTION);
|
||||||
|
[[fallthrough]];
|
||||||
case SA_GRAVITY:
|
case SA_GRAVITY:
|
||||||
clif_skill_nodamage(src,bl,skill_id,skill_lv,1);
|
clif_skill_nodamage(src,bl,skill_id,skill_lv,1);
|
||||||
break;
|
break;
|
||||||
@ -7774,6 +7838,7 @@ int skill_castend_nodamage_id (struct block_list *src, struct block_list *bl, ui
|
|||||||
clif_skill_fail(sd, skill_id, USESKILL_FAIL, 0);
|
clif_skill_fail(sd, skill_id, USESKILL_FAIL, 0);
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
[[fallthrough]];
|
||||||
case PR_SLOWPOISON:
|
case PR_SLOWPOISON:
|
||||||
case PR_LEXAETERNA:
|
case PR_LEXAETERNA:
|
||||||
#ifndef RENEWAL
|
#ifndef RENEWAL
|
||||||
@ -7903,6 +7968,8 @@ int skill_castend_nodamage_id (struct block_list *src, struct block_list *bl, ui
|
|||||||
case NPC_DAMAGE_HEAL:
|
case NPC_DAMAGE_HEAL:
|
||||||
case NPC_RELIEVE_ON:
|
case NPC_RELIEVE_ON:
|
||||||
case NPC_RELIEVE_OFF:
|
case NPC_RELIEVE_OFF:
|
||||||
|
case HN_BREAKINGLIMIT:
|
||||||
|
case HN_RULEBREAK:
|
||||||
clif_skill_nodamage(src,bl,skill_id,skill_lv,
|
clif_skill_nodamage(src,bl,skill_id,skill_lv,
|
||||||
sc_start(src,bl,type,100,skill_lv,skill_get_time(skill_id,skill_lv)));
|
sc_start(src,bl,type,100,skill_lv,skill_get_time(skill_id,skill_lv)));
|
||||||
break;
|
break;
|
||||||
@ -7969,7 +8036,7 @@ int skill_castend_nodamage_id (struct block_list *src, struct block_list *bl, ui
|
|||||||
if (skill_id == AG_DESTRUCTIVE_HURRICANE)
|
if (skill_id == AG_DESTRUCTIVE_HURRICANE)
|
||||||
splash_size = 9; // 19x19
|
splash_size = 9; // 19x19
|
||||||
else if(skill_id == AG_CRYSTAL_IMPACT)
|
else if(skill_id == AG_CRYSTAL_IMPACT)
|
||||||
splash_size = AREA_SIZE; // 29x29 - Entire screen.
|
splash_size = 7; // 15x15
|
||||||
}
|
}
|
||||||
|
|
||||||
skill_area_temp[1] = 0;
|
skill_area_temp[1] = 0;
|
||||||
@ -8627,6 +8694,7 @@ int skill_castend_nodamage_id (struct block_list *src, struct block_list *bl, ui
|
|||||||
case SR_WINDMILL:
|
case SR_WINDMILL:
|
||||||
case GN_CART_TORNADO:
|
case GN_CART_TORNADO:
|
||||||
clif_skill_nodamage(src,bl,skill_id,skill_lv,1);
|
clif_skill_nodamage(src,bl,skill_id,skill_lv,1);
|
||||||
|
[[fallthrough]];
|
||||||
case SR_EARTHSHAKER:
|
case SR_EARTHSHAKER:
|
||||||
case NC_INFRAREDSCAN:
|
case NC_INFRAREDSCAN:
|
||||||
case NPC_VAMPIRE_GIFT:
|
case NPC_VAMPIRE_GIFT:
|
||||||
@ -9125,6 +9193,7 @@ int skill_castend_nodamage_id (struct block_list *src, struct block_list *bl, ui
|
|||||||
if( !mer )
|
if( !mer )
|
||||||
break;
|
break;
|
||||||
sd = mer->master;
|
sd = mer->master;
|
||||||
|
[[fallthrough]];
|
||||||
case WZ_ESTIMATION:
|
case WZ_ESTIMATION:
|
||||||
if( sd == NULL )
|
if( sd == NULL )
|
||||||
break;
|
break;
|
||||||
@ -9716,6 +9785,7 @@ int skill_castend_nodamage_id (struct block_list *src, struct block_list *bl, ui
|
|||||||
case SA_ELEMENTWIND:
|
case SA_ELEMENTWIND:
|
||||||
if (sd && (!dstmd || status_has_mode(tstatus,MD_STATUSIMMUNE))) // Only works on monsters (Except status immune monsters).
|
if (sd && (!dstmd || status_has_mode(tstatus,MD_STATUSIMMUNE))) // Only works on monsters (Except status immune monsters).
|
||||||
break;
|
break;
|
||||||
|
[[fallthrough]];
|
||||||
case NPC_ATTRICHANGE:
|
case NPC_ATTRICHANGE:
|
||||||
case NPC_CHANGEWATER:
|
case NPC_CHANGEWATER:
|
||||||
case NPC_CHANGEGROUND:
|
case NPC_CHANGEGROUND:
|
||||||
@ -10068,7 +10138,7 @@ int skill_castend_nodamage_id (struct block_list *src, struct block_list *bl, ui
|
|||||||
// if it is already trapping something don't spring it,
|
// if it is already trapping something don't spring it,
|
||||||
// remove trap should be used instead
|
// remove trap should be used instead
|
||||||
break;
|
break;
|
||||||
// otherwise fallthrough to below
|
[[fallthrough]];
|
||||||
case UNT_BLASTMINE:
|
case UNT_BLASTMINE:
|
||||||
case UNT_SKIDTRAP:
|
case UNT_SKIDTRAP:
|
||||||
case UNT_LANDMINE:
|
case UNT_LANDMINE:
|
||||||
@ -10348,6 +10418,7 @@ int skill_castend_nodamage_id (struct block_list *src, struct block_list *bl, ui
|
|||||||
status_change_end(bl, SC_SWOO);
|
status_change_end(bl, SC_SWOO);
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
[[fallthrough]];
|
||||||
case SL_SKA: // [marquis007]
|
case SL_SKA: // [marquis007]
|
||||||
case SL_SKE:
|
case SL_SKE:
|
||||||
if (sd && !battle_config.allow_es_magic_pc && bl->type != BL_MOB) {
|
if (sd && !battle_config.allow_es_magic_pc && bl->type != BL_MOB) {
|
||||||
@ -10600,6 +10671,7 @@ int skill_castend_nodamage_id (struct block_list *src, struct block_list *bl, ui
|
|||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
[[fallthrough]];
|
||||||
case NPC_WIDEBLEEDING:
|
case NPC_WIDEBLEEDING:
|
||||||
case NPC_WIDEBLEEDING2:
|
case NPC_WIDEBLEEDING2:
|
||||||
case NPC_WIDECONFUSE:
|
case NPC_WIDECONFUSE:
|
||||||
@ -12149,6 +12221,7 @@ int skill_castend_nodamage_id (struct block_list *src, struct block_list *bl, ui
|
|||||||
clif_skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0);
|
clif_skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0);
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
[[fallthrough]];
|
||||||
case KO_IZAYOI:
|
case KO_IZAYOI:
|
||||||
case OB_ZANGETSU:
|
case OB_ZANGETSU:
|
||||||
case KG_KYOMU:
|
case KG_KYOMU:
|
||||||
@ -12789,6 +12862,11 @@ int skill_castend_nodamage_id (struct block_list *src, struct block_list *bl, ui
|
|||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
|
|
||||||
|
case HN_HELLS_DRIVE:
|
||||||
|
clif_skill_nodamage(src, bl, skill_id, skill_lv, 1);
|
||||||
|
map_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_damage_id);
|
||||||
|
break;
|
||||||
|
|
||||||
default: {
|
default: {
|
||||||
std::shared_ptr<s_skill_db> skill = skill_db.find(skill_id);
|
std::shared_ptr<s_skill_db> skill = skill_db.find(skill_id);
|
||||||
ShowWarning("skill_castend_nodamage_id: missing code case for skill %s(%d)\n", skill ? skill->name : "UNKNOWN", skill_id);
|
ShowWarning("skill_castend_nodamage_id: missing code case for skill %s(%d)\n", skill ? skill->name : "UNKNOWN", skill_id);
|
||||||
@ -13526,6 +13604,7 @@ int skill_castend_pos2(struct block_list* src, int x, int y, uint16 skill_id, ui
|
|||||||
case SC_ESCAPE:
|
case SC_ESCAPE:
|
||||||
case SU_CN_METEOR:
|
case SU_CN_METEOR:
|
||||||
case NPC_RAINOFMETEOR:
|
case NPC_RAINOFMETEOR:
|
||||||
|
case HN_METEOR_STORM_BUSTER:
|
||||||
break; //Effect is displayed on respective switch case.
|
break; //Effect is displayed on respective switch case.
|
||||||
default:
|
default:
|
||||||
if(skill_get_inf(skill_id)&INF_SELF_SKILL)
|
if(skill_get_inf(skill_id)&INF_SELF_SKILL)
|
||||||
@ -13605,6 +13684,7 @@ int skill_castend_pos2(struct block_list* src, int x, int y, uint16 skill_id, ui
|
|||||||
return 0; // Don't consume gems if cast on Land Protector
|
return 0; // Don't consume gems if cast on Land Protector
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
[[fallthrough]];
|
||||||
case MG_FIREWALL:
|
case MG_FIREWALL:
|
||||||
case MG_THUNDERSTORM:
|
case MG_THUNDERSTORM:
|
||||||
case AL_PNEUMA:
|
case AL_PNEUMA:
|
||||||
@ -13738,6 +13818,7 @@ int skill_castend_pos2(struct block_list* src, int x, int y, uint16 skill_id, ui
|
|||||||
case EM_CONFLAGRATION:
|
case EM_CONFLAGRATION:
|
||||||
case EM_TERRA_DRIVE:
|
case EM_TERRA_DRIVE:
|
||||||
flag|=1;//Set flag to 1 to prevent deleting ammo (it will be deleted on group-delete).
|
flag|=1;//Set flag to 1 to prevent deleting ammo (it will be deleted on group-delete).
|
||||||
|
[[fallthrough]];
|
||||||
case GS_GROUNDDRIFT: //Ammo should be deleted right away.
|
case GS_GROUNDDRIFT: //Ammo should be deleted right away.
|
||||||
case GN_WALLOFTHORN:
|
case GN_WALLOFTHORN:
|
||||||
case GN_DEMONIC_FIRE:
|
case GN_DEMONIC_FIRE:
|
||||||
@ -13813,7 +13894,7 @@ int skill_castend_pos2(struct block_list* src, int x, int y, uint16 skill_id, ui
|
|||||||
if (pc_checkskill(sd, SU_SPIRITOFLAND))
|
if (pc_checkskill(sd, SU_SPIRITOFLAND))
|
||||||
sc_start(src, src, SC_DORAM_SVSP, 100, 100, skill_get_time(SU_SPIRITOFLAND, 1));
|
sc_start(src, src, SC_DORAM_SVSP, 100, 100, skill_get_time(SU_SPIRITOFLAND, 1));
|
||||||
}
|
}
|
||||||
// Fall through
|
[[fallthrough]];
|
||||||
case WZ_METEOR:
|
case WZ_METEOR:
|
||||||
{
|
{
|
||||||
int area = skill_get_splash(skill_id, skill_lv);
|
int area = skill_get_splash(skill_id, skill_lv);
|
||||||
@ -14054,6 +14135,7 @@ int skill_castend_pos2(struct block_list* src, int x, int y, uint16 skill_id, ui
|
|||||||
|
|
||||||
case AC_SHOWER:
|
case AC_SHOWER:
|
||||||
status_change_end(src, SC_CAMOUFLAGE);
|
status_change_end(src, SC_CAMOUFLAGE);
|
||||||
|
[[fallthrough]];
|
||||||
case MA_SHOWER:
|
case MA_SHOWER:
|
||||||
case NC_COLDSLOWER:
|
case NC_COLDSLOWER:
|
||||||
case RK_DRAGONBREATH:
|
case RK_DRAGONBREATH:
|
||||||
@ -14430,6 +14512,41 @@ int skill_castend_pos2(struct block_list* src, int x, int y, uint16 skill_id, ui
|
|||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
|
|
||||||
|
case HN_JACK_FROST_NOVA:
|
||||||
|
case HN_GROUND_GRAVITATION: {
|
||||||
|
if( map_getcell(src->m, x, y, CELL_CHKLANDPROTECTOR) ) {
|
||||||
|
clif_skill_fail(sd,skill_id,USESKILL_FAIL,0);
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
int splash = skill_get_splash(skill_id, skill_lv);
|
||||||
|
|
||||||
|
map_foreachinarea(skill_area_sub, src->m, x - splash, y - splash, x + splash, y + splash, BL_CHAR, src, skill_id, skill_lv, tick, flag | BCT_ENEMY | SD_SPLASH | SKILL_ALTDMG_FLAG | 1, skill_castend_damage_id);
|
||||||
|
skill_unitsetting(src, skill_id, skill_lv, x, y, flag);
|
||||||
|
|
||||||
|
for (i = 1; i <= (skill_get_time(skill_id, skill_lv) / skill_get_unit_interval(skill_id)); i++) {
|
||||||
|
skill_addtimerskill(src, tick + (t_tick)i*skill_get_unit_interval(skill_id), 0, x, y, skill_id, skill_lv, 0, flag);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
|
||||||
|
case HN_METEOR_STORM_BUSTER: {
|
||||||
|
if( map_getcell(src->m, x, y, CELL_CHKLANDPROTECTOR) ) {
|
||||||
|
clif_skill_fail(sd,skill_id,USESKILL_FAIL,0);
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
int splash = skill_get_splash(skill_id, skill_lv);
|
||||||
|
|
||||||
|
map_foreachinarea(skill_area_sub, src->m, x - splash, y - splash, x + splash, y + splash, BL_CHAR, src, skill_id, skill_lv, tick, flag | BCT_ENEMY | SD_SPLASH | SKILL_ALTDMG_FLAG | 1, skill_castend_damage_id);
|
||||||
|
skill_unitsetting(src, skill_id, skill_lv, x, y, skill_get_unit_interval(skill_id));
|
||||||
|
|
||||||
|
for (i = 1; i <= (skill_get_time(skill_id, skill_lv) / skill_get_time2(skill_id, skill_lv)); i++) {
|
||||||
|
skill_addtimerskill(src, tick + (t_tick)i*skill_get_time2(skill_id, skill_lv), 0, x, y, skill_id, skill_lv, 0, flag);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
|
||||||
default:
|
default:
|
||||||
ShowWarning("skill_castend_pos2: Unknown skill used:%d\n",skill_id);
|
ShowWarning("skill_castend_pos2: Unknown skill used:%d\n",skill_id);
|
||||||
return 1;
|
return 1;
|
||||||
@ -14769,6 +14886,7 @@ std::shared_ptr<s_skill_unit_group> skill_unitsetting(struct block_list *src, ui
|
|||||||
case SU_CN_METEOR:
|
case SU_CN_METEOR:
|
||||||
case SU_CN_METEOR2:
|
case SU_CN_METEOR2:
|
||||||
case NPC_RAINOFMETEOR:
|
case NPC_RAINOFMETEOR:
|
||||||
|
case HN_METEOR_STORM_BUSTER:
|
||||||
limit = flag;
|
limit = flag;
|
||||||
flag = 0; // Flag should not influence anything else for these skills
|
flag = 0; // Flag should not influence anything else for these skills
|
||||||
break;
|
break;
|
||||||
@ -14788,6 +14906,7 @@ std::shared_ptr<s_skill_unit_group> skill_unitsetting(struct block_list *src, ui
|
|||||||
case MA_SKIDTRAP:
|
case MA_SKIDTRAP:
|
||||||
//Save position of caster
|
//Save position of caster
|
||||||
val1 = ((src->x)<<16)|(src->y);
|
val1 = ((src->x)<<16)|(src->y);
|
||||||
|
[[fallthrough]];
|
||||||
case HT_ANKLESNARE:
|
case HT_ANKLESNARE:
|
||||||
case HT_SHOCKWAVE:
|
case HT_SHOCKWAVE:
|
||||||
case HT_SANDMAN:
|
case HT_SANDMAN:
|
||||||
@ -14960,12 +15079,16 @@ std::shared_ptr<s_skill_unit_group> skill_unitsetting(struct block_list *src, ui
|
|||||||
switch (val1) {
|
switch (val1) {
|
||||||
case ELE_FIRE:
|
case ELE_FIRE:
|
||||||
subunt++;
|
subunt++;
|
||||||
|
[[fallthrough]];
|
||||||
case ELE_WATER:
|
case ELE_WATER:
|
||||||
subunt++;
|
subunt++;
|
||||||
|
[[fallthrough]];
|
||||||
case ELE_POISON:
|
case ELE_POISON:
|
||||||
subunt++;
|
subunt++;
|
||||||
|
[[fallthrough]];
|
||||||
case ELE_DARK:
|
case ELE_DARK:
|
||||||
subunt++;
|
subunt++;
|
||||||
|
[[fallthrough]];
|
||||||
case ELE_WIND:
|
case ELE_WIND:
|
||||||
break;
|
break;
|
||||||
default:
|
default:
|
||||||
@ -15001,6 +15124,7 @@ std::shared_ptr<s_skill_unit_group> skill_unitsetting(struct block_list *src, ui
|
|||||||
case WM_POEMOFNETHERWORLD: // Can't be placed on top of Land Protector.
|
case WM_POEMOFNETHERWORLD: // Can't be placed on top of Land Protector.
|
||||||
if( skill_id == WM_POEMOFNETHERWORLD && map_flag_gvg2(src->m) )
|
if( skill_id == WM_POEMOFNETHERWORLD && map_flag_gvg2(src->m) )
|
||||||
target = BCT_ALL;
|
target = BCT_ALL;
|
||||||
|
[[fallthrough]];
|
||||||
case WM_SEVERE_RAINSTORM:
|
case WM_SEVERE_RAINSTORM:
|
||||||
case SO_WATER_INSIGNIA:
|
case SO_WATER_INSIGNIA:
|
||||||
case SO_FIRE_INSIGNIA:
|
case SO_FIRE_INSIGNIA:
|
||||||
@ -15470,6 +15594,7 @@ static int skill_unit_onplace(struct skill_unit *unit, struct block_list *bl, t_
|
|||||||
case UNT_HERMODE:
|
case UNT_HERMODE:
|
||||||
if (sg->src_id!=bl->id && battle_check_target(&unit->bl,bl,BCT_PARTY|BCT_GUILD) > 0)
|
if (sg->src_id!=bl->id && battle_check_target(&unit->bl,bl,BCT_PARTY|BCT_GUILD) > 0)
|
||||||
status_change_clear_buffs(bl, SCCB_HERMODE); //Should dispell only allies.
|
status_change_clear_buffs(bl, SCCB_HERMODE); //Should dispell only allies.
|
||||||
|
[[fallthrough]];
|
||||||
case UNT_RICHMANKIM:
|
case UNT_RICHMANKIM:
|
||||||
case UNT_ETERNALCHAOS:
|
case UNT_ETERNALCHAOS:
|
||||||
case UNT_DRUMBATTLEFIELD:
|
case UNT_DRUMBATTLEFIELD:
|
||||||
@ -15947,11 +16072,13 @@ int skill_unit_onplace_timer(struct skill_unit *unit, struct block_list *bl, t_t
|
|||||||
case UNT_VERDURETRAP:
|
case UNT_VERDURETRAP:
|
||||||
if( bl->type == BL_PC )// it won't work on players
|
if( bl->type == BL_PC )// it won't work on players
|
||||||
break;
|
break;
|
||||||
|
[[fallthrough]];
|
||||||
case UNT_FIRINGTRAP:
|
case UNT_FIRINGTRAP:
|
||||||
case UNT_ICEBOUNDTRAP:
|
case UNT_ICEBOUNDTRAP:
|
||||||
case UNT_CLUSTERBOMB:
|
case UNT_CLUSTERBOMB:
|
||||||
if( bl->id == ss->id )// it won't trigger on caster
|
if( bl->id == ss->id )// it won't trigger on caster
|
||||||
break;
|
break;
|
||||||
|
[[fallthrough]];
|
||||||
case UNT_BLASTMINE:
|
case UNT_BLASTMINE:
|
||||||
case UNT_SHOCKWAVE:
|
case UNT_SHOCKWAVE:
|
||||||
case UNT_SANDMAN:
|
case UNT_SANDMAN:
|
||||||
@ -16469,6 +16596,7 @@ int skill_unit_onout(struct skill_unit *src, struct block_list *bl, t_tick tick)
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
[[fallthrough]];
|
||||||
case UNT_WHISTLE:
|
case UNT_WHISTLE:
|
||||||
case UNT_ASSASSINCROSS:
|
case UNT_ASSASSINCROSS:
|
||||||
case UNT_POEMBRAGI:
|
case UNT_POEMBRAGI:
|
||||||
@ -16528,6 +16656,7 @@ int skill_unit_onleft(uint16 skill_id, struct block_list *bl, t_tick tick)
|
|||||||
//your own. Let's pray that scenario is pretty unlikely and noone will complain too much about it.
|
//your own. Let's pray that scenario is pretty unlikely and noone will complain too much about it.
|
||||||
status_change_end(bl, SC_DANCING);
|
status_change_end(bl, SC_DANCING);
|
||||||
}
|
}
|
||||||
|
[[fallthrough]];
|
||||||
case MH_STEINWAND:
|
case MH_STEINWAND:
|
||||||
case MG_SAFETYWALL:
|
case MG_SAFETYWALL:
|
||||||
case AL_PNEUMA:
|
case AL_PNEUMA:
|
||||||
@ -17168,15 +17297,15 @@ bool skill_check_condition_castbegin(map_session_data* sd, uint16 skill_id, uint
|
|||||||
// perform skill-group checks
|
// perform skill-group checks
|
||||||
if(skill_id != WM_GREAT_ECHO && inf2[INF2_ISCHORUS]) {
|
if(skill_id != WM_GREAT_ECHO && inf2[INF2_ISCHORUS]) {
|
||||||
if (skill_check_pc_partner(sd, skill_id, &skill_lv, AREA_SIZE, 0) < 1) {
|
if (skill_check_pc_partner(sd, skill_id, &skill_lv, AREA_SIZE, 0) < 1) {
|
||||||
clif_skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0);
|
clif_skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0);
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
else if(inf2[INF2_ISENSEMBLE]) {
|
else if(inf2[INF2_ISENSEMBLE]) {
|
||||||
if (skill_check_pc_partner(sd, skill_id, &skill_lv, 1, 0) < 1 && !(sc && sc->getSCE(SC_KVASIR_SONATA))) {
|
if (skill_check_pc_partner(sd, skill_id, &skill_lv, 1, 0) < 1 && !(sc && sc->getSCE(SC_KVASIR_SONATA))) {
|
||||||
clif_skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0);
|
clif_skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0);
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
// perform skill-specific checks (and actions)
|
// perform skill-specific checks (and actions)
|
||||||
switch( skill_id ) {
|
switch( skill_id ) {
|
||||||
@ -17191,6 +17320,7 @@ bool skill_check_condition_castbegin(map_session_data* sd, uint16 skill_id, uint
|
|||||||
clif_skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0);
|
clif_skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0);
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
[[fallthrough]];
|
||||||
case SA_CASTCANCEL:
|
case SA_CASTCANCEL:
|
||||||
if(sd->ud.skilltimer == INVALID_TIMER) {
|
if(sd->ud.skilltimer == INVALID_TIMER) {
|
||||||
clif_skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0);
|
clif_skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0);
|
||||||
@ -17478,6 +17608,7 @@ bool skill_check_condition_castbegin(map_session_data* sd, uint16 skill_id, uint
|
|||||||
clif_skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0);
|
clif_skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0);
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
[[fallthrough]];
|
||||||
case GD_EMERGENCYCALL:
|
case GD_EMERGENCYCALL:
|
||||||
case GD_ITEMEMERGENCYCALL:
|
case GD_ITEMEMERGENCYCALL:
|
||||||
// other checks were already done in skill_isNotOk()
|
// other checks were already done in skill_isNotOk()
|
||||||
@ -17501,6 +17632,7 @@ bool skill_check_condition_castbegin(map_session_data* sd, uint16 skill_id, uint
|
|||||||
clif_skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0);
|
clif_skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0);
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
[[fallthrough]];
|
||||||
case NJ_BUNSINJYUTSU:
|
case NJ_BUNSINJYUTSU:
|
||||||
if (!(sc && sc->getSCE(SC_NEN))) {
|
if (!(sc && sc->getSCE(SC_NEN))) {
|
||||||
clif_skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0);
|
clif_skill_fail(sd,skill_id,USESKILL_FAIL_LEVEL,0);
|
||||||
@ -18363,7 +18495,7 @@ void skill_consume_requirement(map_session_data *sd, uint16 skill_id, uint16 ski
|
|||||||
case MO_KITRANSLATION:
|
case MO_KITRANSLATION:
|
||||||
//Spiritual Bestowment only uses spirit sphere when giving it to someone
|
//Spiritual Bestowment only uses spirit sphere when giving it to someone
|
||||||
require.spiritball = 0;
|
require.spiritball = 0;
|
||||||
//Fall through
|
[[fallthrough]];
|
||||||
default:
|
default:
|
||||||
if(sd->state.autocast)
|
if(sd->state.autocast)
|
||||||
require.sp = 0;
|
require.sp = 0;
|
||||||
@ -18602,7 +18734,7 @@ struct s_skill_condition skill_get_requirement(map_session_data* sd, uint16 skil
|
|||||||
case NC_REPAIR: // NOTE: Repair_Kit must be last in the ItemCost list depending on the skill's max level
|
case NC_REPAIR: // NOTE: Repair_Kit must be last in the ItemCost list depending on the skill's max level
|
||||||
req.itemid[1] = skill->require.itemid[skill->max];
|
req.itemid[1] = skill->require.itemid[skill->max];
|
||||||
req.amount[1] = skill->require.amount[skill->max];
|
req.amount[1] = skill->require.amount[skill->max];
|
||||||
// Fall through
|
[[fallthrough]];
|
||||||
|
|
||||||
/* Normal skill requirements and gemstone checks */
|
/* Normal skill requirements and gemstone checks */
|
||||||
default:
|
default:
|
||||||
@ -19697,7 +19829,7 @@ int skill_attack_area(struct block_list *bl, va_list ap)
|
|||||||
return 0; //Does not hit current cell
|
return 0; //Does not hit current cell
|
||||||
if (map_getcell(bl->m, bl->x, bl->y, CELL_CHKLANDPROTECTOR)) // Attack should not happen if the target is on Land Protector
|
if (map_getcell(bl->m, bl->x, bl->y, CELL_CHKLANDPROTECTOR)) // Attack should not happen if the target is on Land Protector
|
||||||
return 0;
|
return 0;
|
||||||
//Fall through
|
[[fallthrough]];
|
||||||
case NPC_ACIDBREATH:
|
case NPC_ACIDBREATH:
|
||||||
case NPC_DARKNESSBREATH:
|
case NPC_DARKNESSBREATH:
|
||||||
case NPC_FIREBREATH:
|
case NPC_FIREBREATH:
|
||||||
@ -19979,6 +20111,7 @@ static int skill_cell_overlap(struct block_list *bl, va_list ap)
|
|||||||
case GN_CRAZYWEED_ATK:
|
case GN_CRAZYWEED_ATK:
|
||||||
if (skill_get_unit_flag(unit->group->skill_id, UF_CRAZYWEEDIMMUNE))
|
if (skill_get_unit_flag(unit->group->skill_id, UF_CRAZYWEEDIMMUNE))
|
||||||
break;
|
break;
|
||||||
|
[[fallthrough]];
|
||||||
case HW_GANBANTEIN:
|
case HW_GANBANTEIN:
|
||||||
case LG_EARTHDRIVE:
|
case LG_EARTHDRIVE:
|
||||||
// Officially songs/dances are removed
|
// Officially songs/dances are removed
|
||||||
@ -20161,6 +20294,7 @@ static int skill_trap_splash(struct block_list *bl, va_list ap)
|
|||||||
if (su && su->group->unit_id == UNT_USED_TRAPS)
|
if (su && su->group->unit_id == UNT_USED_TRAPS)
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
[[fallthrough]];
|
||||||
case UNT_CLUSTERBOMB:
|
case UNT_CLUSTERBOMB:
|
||||||
if( ss != bl )
|
if( ss != bl )
|
||||||
skill_attack(BF_MISC,ss,src,bl,sg->skill_id,sg->skill_lv,tick,sg->val1|SD_LEVEL);
|
skill_attack(BF_MISC,ss,src,bl,sg->skill_id,sg->skill_lv,tick,sg->val1|SD_LEVEL);
|
||||||
@ -20189,6 +20323,7 @@ static int skill_trap_splash(struct block_list *bl, va_list ap)
|
|||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
[[fallthrough]];
|
||||||
default: {
|
default: {
|
||||||
int split_count = 0;
|
int split_count = 0;
|
||||||
|
|
||||||
@ -20948,7 +21083,7 @@ static int skill_unit_timer_sub(DBKey key, DBData *data, va_list ap)
|
|||||||
unit->limit = DIFF_TICK(tick + group->interval,group->tick);
|
unit->limit = DIFF_TICK(tick + group->interval,group->tick);
|
||||||
if( unit->val1 <= 0 )
|
if( unit->val1 <= 0 )
|
||||||
skill_delunit(unit);
|
skill_delunit(unit);
|
||||||
break;
|
break;
|
||||||
case UNT_BLASTMINE:
|
case UNT_BLASTMINE:
|
||||||
#ifdef RENEWAL
|
#ifdef RENEWAL
|
||||||
case UNT_CLAYMORETRAP:
|
case UNT_CLAYMORETRAP:
|
||||||
@ -20962,7 +21097,7 @@ static int skill_unit_timer_sub(DBKey key, DBData *data, va_list ap)
|
|||||||
//clif_changetraplook(bl, UNT_FIREPILLAR_ACTIVE);
|
//clif_changetraplook(bl, UNT_FIREPILLAR_ACTIVE);
|
||||||
group->limit=DIFF_TICK(tick+1500,group->tick);
|
group->limit=DIFF_TICK(tick+1500,group->tick);
|
||||||
unit->limit=DIFF_TICK(tick+1500,group->tick);
|
unit->limit=DIFF_TICK(tick+1500,group->tick);
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case UNT_ANKLESNARE:
|
case UNT_ANKLESNARE:
|
||||||
case UNT_ELECTRICSHOCKER:
|
case UNT_ELECTRICSHOCKER:
|
||||||
@ -20970,6 +21105,7 @@ static int skill_unit_timer_sub(DBKey key, DBData *data, va_list ap)
|
|||||||
skill_delunit(unit);
|
skill_delunit(unit);
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
[[fallthrough]];
|
||||||
case UNT_SKIDTRAP:
|
case UNT_SKIDTRAP:
|
||||||
case UNT_LANDMINE:
|
case UNT_LANDMINE:
|
||||||
case UNT_SHOCKWAVE:
|
case UNT_SHOCKWAVE:
|
||||||
@ -20999,7 +21135,7 @@ static int skill_unit_timer_sub(DBKey key, DBData *data, va_list ap)
|
|||||||
}
|
}
|
||||||
skill_delunit(unit);
|
skill_delunit(unit);
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case UNT_WARP_ACTIVE:
|
case UNT_WARP_ACTIVE:
|
||||||
// warp portal opens (morph to a UNT_WARP_WAITING cell)
|
// warp portal opens (morph to a UNT_WARP_WAITING cell)
|
||||||
@ -21010,7 +21146,7 @@ static int skill_unit_timer_sub(DBKey key, DBData *data, va_list ap)
|
|||||||
unit->limit = skill_get_time(group->skill_id,group->skill_lv);
|
unit->limit = skill_get_time(group->skill_id,group->skill_lv);
|
||||||
// apply effect to all units standing on it
|
// apply effect to all units standing on it
|
||||||
map_foreachincell(skill_unit_effect,unit->bl.m,unit->bl.x,unit->bl.y,group->bl_flag,&unit->bl,gettick(),1);
|
map_foreachincell(skill_unit_effect,unit->bl.m,unit->bl.x,unit->bl.y,group->bl_flag,&unit->bl,gettick(),1);
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case UNT_CALLFAMILY:
|
case UNT_CALLFAMILY:
|
||||||
{
|
{
|
||||||
@ -21029,7 +21165,7 @@ static int skill_unit_timer_sub(DBKey key, DBData *data, va_list ap)
|
|||||||
}
|
}
|
||||||
skill_delunit(unit);
|
skill_delunit(unit);
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case UNT_REVERBERATION:
|
case UNT_REVERBERATION:
|
||||||
case UNT_NETHERWORLD:
|
case UNT_NETHERWORLD:
|
||||||
@ -21052,7 +21188,7 @@ static int skill_unit_timer_sub(DBKey key, DBData *data, va_list ap)
|
|||||||
map_foreachinrange(skill_area_sub, &unit->bl, unit->range, BL_CHAR|BL_SKILL, src, group->skill_id, group->skill_lv, tick, BCT_ENEMY|SD_ANIMATION|5, skill_castend_damage_id);
|
map_foreachinrange(skill_area_sub, &unit->bl, unit->range, BL_CHAR|BL_SKILL, src, group->skill_id, group->skill_lv, tick, BCT_ENEMY|SD_ANIMATION|5, skill_castend_damage_id);
|
||||||
skill_delunit(unit);
|
skill_delunit(unit);
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case UNT_BANDING:
|
case UNT_BANDING:
|
||||||
{
|
{
|
||||||
@ -21066,7 +21202,7 @@ static int skill_unit_timer_sub(DBKey key, DBData *data, va_list ap)
|
|||||||
group->limit = DIFF_TICK(tick+group->interval,group->tick);
|
group->limit = DIFF_TICK(tick+group->interval,group->tick);
|
||||||
unit->limit = DIFF_TICK(tick+group->interval,group->tick);
|
unit->limit = DIFF_TICK(tick+group->interval,group->tick);
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case UNT_B_TRAP:
|
case UNT_B_TRAP:
|
||||||
{
|
{
|
||||||
@ -21084,7 +21220,8 @@ static int skill_unit_timer_sub(DBKey key, DBData *data, va_list ap)
|
|||||||
|
|
||||||
default:
|
default:
|
||||||
if (group->val2 == 1 && (group->skill_id == WZ_METEOR || group->skill_id == SU_CN_METEOR || group->skill_id == SU_CN_METEOR2 ||
|
if (group->val2 == 1 && (group->skill_id == WZ_METEOR || group->skill_id == SU_CN_METEOR || group->skill_id == SU_CN_METEOR2 ||
|
||||||
group->skill_id == AG_VIOLENT_QUAKE_ATK || group->skill_id == AG_ALL_BLOOM_ATK || group->skill_id == AG_ALL_BLOOM_ATK2 || group->skill_id == NPC_RAINOFMETEOR)) {
|
group->skill_id == AG_VIOLENT_QUAKE_ATK || group->skill_id == AG_ALL_BLOOM_ATK || group->skill_id == AG_ALL_BLOOM_ATK2 || group->skill_id == NPC_RAINOFMETEOR ||
|
||||||
|
group->skill_id == HN_METEOR_STORM_BUSTER)) {
|
||||||
// Deal damage before expiration
|
// Deal damage before expiration
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
@ -21140,7 +21277,8 @@ static int skill_unit_timer_sub(DBKey key, DBData *data, va_list ap)
|
|||||||
break;
|
break;
|
||||||
default:
|
default:
|
||||||
if (group->skill_id == WZ_METEOR || group->skill_id == SU_CN_METEOR || group->skill_id == SU_CN_METEOR2 ||
|
if (group->skill_id == WZ_METEOR || group->skill_id == SU_CN_METEOR || group->skill_id == SU_CN_METEOR2 ||
|
||||||
group->skill_id == AG_VIOLENT_QUAKE_ATK || group->skill_id == AG_ALL_BLOOM_ATK || group->skill_id == AG_ALL_BLOOM_ATK2 || group->skill_id == NPC_RAINOFMETEOR) {
|
group->skill_id == AG_VIOLENT_QUAKE_ATK || group->skill_id == AG_ALL_BLOOM_ATK || group->skill_id == AG_ALL_BLOOM_ATK2 || group->skill_id == NPC_RAINOFMETEOR ||
|
||||||
|
group->skill_id == HN_METEOR_STORM_BUSTER) {
|
||||||
if (group->val2 == 0 && (DIFF_TICK(tick, group->tick) >= group->limit - group->interval || DIFF_TICK(tick, group->tick) >= unit->limit - group->interval)) {
|
if (group->val2 == 0 && (DIFF_TICK(tick, group->tick) >= group->limit - group->interval || DIFF_TICK(tick, group->tick) >= unit->limit - group->interval)) {
|
||||||
// Unit will expire the next interval, start dropping Meteor
|
// Unit will expire the next interval, start dropping Meteor
|
||||||
block_list *src = map_id2bl(group->src_id);
|
block_list *src = map_id2bl(group->src_id);
|
||||||
@ -21182,6 +21320,7 @@ static int skill_unit_timer_sub(DBKey key, DBData *data, va_list ap)
|
|||||||
}
|
}
|
||||||
else if (group->skill_id == WZ_METEOR || group->skill_id == SU_CN_METEOR || group->skill_id == SU_CN_METEOR2 ||
|
else if (group->skill_id == WZ_METEOR || group->skill_id == SU_CN_METEOR || group->skill_id == SU_CN_METEOR2 ||
|
||||||
group->skill_id == AG_VIOLENT_QUAKE_ATK || group->skill_id == AG_ALL_BLOOM_ATK || group->skill_id == AG_ALL_BLOOM_ATK2 || group->skill_id == NPC_RAINOFMETEOR ||
|
group->skill_id == AG_VIOLENT_QUAKE_ATK || group->skill_id == AG_ALL_BLOOM_ATK || group->skill_id == AG_ALL_BLOOM_ATK2 || group->skill_id == NPC_RAINOFMETEOR ||
|
||||||
|
group->skill_id == HN_METEOR_STORM_BUSTER ||
|
||||||
((group->skill_id == CR_GRANDCROSS || group->skill_id == NPC_GRANDDARKNESS) && unit->val1 <= 0)) {
|
((group->skill_id == CR_GRANDCROSS || group->skill_id == NPC_GRANDDARKNESS) && unit->val1 <= 0)) {
|
||||||
skill_delunit(unit);
|
skill_delunit(unit);
|
||||||
return 0;
|
return 0;
|
||||||
@ -22129,6 +22268,7 @@ bool skill_produce_mix(map_session_data *sd, uint16 skill_id, t_itemid nameid, i
|
|||||||
switch (skill_id) {
|
switch (skill_id) {
|
||||||
case ASC_CDP: //25% Damage yourself, and display same effect as failed potion.
|
case ASC_CDP: //25% Damage yourself, and display same effect as failed potion.
|
||||||
status_percent_damage(NULL, &sd->bl, -25, 0, true);
|
status_percent_damage(NULL, &sd->bl, -25, 0, true);
|
||||||
|
[[fallthrough]];
|
||||||
case AM_PHARMACY:
|
case AM_PHARMACY:
|
||||||
case AM_TWILIGHT1:
|
case AM_TWILIGHT1:
|
||||||
case AM_TWILIGHT2:
|
case AM_TWILIGHT2:
|
||||||
@ -23333,6 +23473,7 @@ int skill_block_check(struct block_list *bl, sc_type type , uint16 skill_id) {
|
|||||||
case SC_KAGEHUMI:
|
case SC_KAGEHUMI:
|
||||||
if (skill_get_inf2(skill_id, INF2_IGNOREKAGEHUMI))
|
if (skill_get_inf2(skill_id, INF2_IGNOREKAGEHUMI))
|
||||||
return 1;
|
return 1;
|
||||||
|
break;
|
||||||
case SC_BITE:
|
case SC_BITE:
|
||||||
if (skill_get_inf2(skill_id, INF2_IGNOREWUGBITE))
|
if (skill_get_inf2(skill_id, INF2_IGNOREWUGBITE))
|
||||||
return 1;
|
return 1;
|
||||||
|
|||||||
@ -39,6 +39,9 @@ class status_change;
|
|||||||
/// Used with tracking the hitcount of Earthquake for skills that can avoid the first attack
|
/// Used with tracking the hitcount of Earthquake for skills that can avoid the first attack
|
||||||
#define NPC_EARTHQUAKE_FLAG 0x800
|
#define NPC_EARTHQUAKE_FLAG 0x800
|
||||||
|
|
||||||
|
/// To control alternative skill scalings
|
||||||
|
#define SKILL_ALTDMG_FLAG 0x10
|
||||||
|
|
||||||
/// Constants to identify a skill's nk value (damage properties)
|
/// Constants to identify a skill's nk value (damage properties)
|
||||||
/// The NK value applies only to non INF_GROUND_SKILL skills
|
/// The NK value applies only to non INF_GROUND_SKILL skills
|
||||||
/// when determining skill castend function to invoke.
|
/// when determining skill castend function to invoke.
|
||||||
|
|||||||
@ -2017,11 +2017,24 @@ bool status_check_skilluse(struct block_list *src, struct block_list *target, ui
|
|||||||
|
|
||||||
if (sc->getSCE(SC_BLADESTOP)) {
|
if (sc->getSCE(SC_BLADESTOP)) {
|
||||||
switch (sc->getSCE(SC_BLADESTOP)->val1) {
|
switch (sc->getSCE(SC_BLADESTOP)->val1) {
|
||||||
case 5: if (skill_id == MO_EXTREMITYFIST) break;
|
case 5:
|
||||||
case 4: if (skill_id == MO_CHAINCOMBO) break;
|
if (skill_id == MO_EXTREMITYFIST)
|
||||||
case 3: if (skill_id == MO_INVESTIGATE) break;
|
break;
|
||||||
case 2: if (skill_id == MO_FINGEROFFENSIVE) break;
|
[[fallthrough]];
|
||||||
default: return false;
|
case 4:
|
||||||
|
if (skill_id == MO_CHAINCOMBO)
|
||||||
|
break;
|
||||||
|
[[fallthrough]];
|
||||||
|
case 3:
|
||||||
|
if (skill_id == MO_INVESTIGATE)
|
||||||
|
break;
|
||||||
|
[[fallthrough]];
|
||||||
|
case 2:
|
||||||
|
if (skill_id == MO_FINGEROFFENSIVE)
|
||||||
|
break;
|
||||||
|
[[fallthrough]];
|
||||||
|
default:
|
||||||
|
return false;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -2157,6 +2170,7 @@ bool status_check_skilluse(struct block_list *src, struct block_list *target, ui
|
|||||||
return false; // Can't use Potion Pitcher on Mercenaries
|
return false; // Can't use Potion Pitcher on Mercenaries
|
||||||
if (tsc && tsc->getSCE(SC_ELEMENTAL_VEIL) && !(src && status_get_class_(src) == CLASS_BOSS) && !status_has_mode(status, MD_DETECTOR))
|
if (tsc && tsc->getSCE(SC_ELEMENTAL_VEIL) && !(src && status_get_class_(src) == CLASS_BOSS) && !status_has_mode(status, MD_DETECTOR))
|
||||||
return false;
|
return false;
|
||||||
|
[[fallthrough]];
|
||||||
default:
|
default:
|
||||||
// Check for chase-walk/hiding/cloaking opponents.
|
// Check for chase-walk/hiding/cloaking opponents.
|
||||||
if( tsc ) {
|
if( tsc ) {
|
||||||
@ -4365,6 +4379,10 @@ int status_calc_pc_sub(map_session_data* sd, uint8 opt)
|
|||||||
base_status->patk += skill * 3;
|
base_status->patk += skill * 3;
|
||||||
base_status->smatk += skill * 3;
|
base_status->smatk += skill * 3;
|
||||||
}
|
}
|
||||||
|
if ((skill = pc_checkskill(sd, HN_SELFSTUDY_TATICS)) > 0)
|
||||||
|
base_status->patk += skill;
|
||||||
|
if ((skill = pc_checkskill(sd, HN_SELFSTUDY_SOCERY)) > 0)
|
||||||
|
base_status->smatk += skill;
|
||||||
|
|
||||||
// 2-Handed Staff Mastery
|
// 2-Handed Staff Mastery
|
||||||
if( sd->status.weapon == W_2HSTAFF && ( skill = pc_checkskill( sd, AG_TWOHANDSTAFF ) ) > 0 ){
|
if( sd->status.weapon == W_2HSTAFF && ( skill = pc_checkskill( sd, AG_TWOHANDSTAFF ) ) > 0 ){
|
||||||
@ -4489,15 +4507,19 @@ int status_calc_pc_sub(map_session_data* sd, uint8 opt)
|
|||||||
skill = skill * 4;
|
skill = skill * 4;
|
||||||
|
|
||||||
sd->right_weapon.addrace[RC_DRAGON]+=skill;
|
sd->right_weapon.addrace[RC_DRAGON]+=skill;
|
||||||
sd->left_weapon.addrace[RC_DRAGON]+=skill;
|
if( !battle_config.left_cardfix_to_right ){
|
||||||
|
sd->left_weapon.addrace[RC_DRAGON] += skill;
|
||||||
|
}
|
||||||
sd->indexed_bonus.magic_addrace[RC_DRAGON]+=dragon_matk;
|
sd->indexed_bonus.magic_addrace[RC_DRAGON]+=dragon_matk;
|
||||||
sd->indexed_bonus.subrace[RC_DRAGON]+=skill;
|
sd->indexed_bonus.subrace[RC_DRAGON]+=skill;
|
||||||
}
|
}
|
||||||
if ((skill = pc_checkskill(sd, AB_EUCHARISTICA)) > 0) {
|
if ((skill = pc_checkskill(sd, AB_EUCHARISTICA)) > 0) {
|
||||||
sd->right_weapon.addrace[RC_DEMON] += skill;
|
sd->right_weapon.addrace[RC_DEMON] += skill;
|
||||||
sd->right_weapon.addele[ELE_DARK] += skill;
|
sd->right_weapon.addele[ELE_DARK] += skill;
|
||||||
sd->left_weapon.addrace[RC_DEMON] += skill;
|
if( !battle_config.left_cardfix_to_right ){
|
||||||
sd->left_weapon.addele[ELE_DARK] += skill;
|
sd->left_weapon.addrace[RC_DEMON] += skill;
|
||||||
|
sd->left_weapon.addele[ELE_DARK] += skill;
|
||||||
|
}
|
||||||
sd->indexed_bonus.magic_addrace[RC_DEMON] += skill;
|
sd->indexed_bonus.magic_addrace[RC_DEMON] += skill;
|
||||||
sd->indexed_bonus.magic_addele[ELE_DARK] += skill;
|
sd->indexed_bonus.magic_addele[ELE_DARK] += skill;
|
||||||
sd->indexed_bonus.subrace[RC_DEMON] += skill;
|
sd->indexed_bonus.subrace[RC_DEMON] += skill;
|
||||||
@ -4521,8 +4543,10 @@ int status_calc_pc_sub(map_session_data* sd, uint8 opt)
|
|||||||
|
|
||||||
sd->right_weapon.addrace[RC_UNDEAD] += race_atk[skill - 1];
|
sd->right_weapon.addrace[RC_UNDEAD] += race_atk[skill - 1];
|
||||||
sd->right_weapon.addrace[RC_DEMON] += race_atk[skill - 1];
|
sd->right_weapon.addrace[RC_DEMON] += race_atk[skill - 1];
|
||||||
sd->left_weapon.addrace[RC_UNDEAD] += race_atk[skill - 1];
|
if( !battle_config.left_cardfix_to_right ){
|
||||||
sd->left_weapon.addrace[RC_DEMON] += race_atk[skill - 1];
|
sd->left_weapon.addrace[RC_UNDEAD] += race_atk[skill - 1];
|
||||||
|
sd->left_weapon.addrace[RC_DEMON] += race_atk[skill - 1];
|
||||||
|
}
|
||||||
sd->indexed_bonus.subrace[RC_UNDEAD] += race_def[skill - 1];
|
sd->indexed_bonus.subrace[RC_UNDEAD] += race_def[skill - 1];
|
||||||
sd->indexed_bonus.subrace[RC_DEMON] += race_def[skill - 1];
|
sd->indexed_bonus.subrace[RC_DEMON] += race_def[skill - 1];
|
||||||
}
|
}
|
||||||
@ -4536,7 +4560,9 @@ int status_calc_pc_sub(map_session_data* sd, uint8 opt)
|
|||||||
|
|
||||||
for( uint8 size = SZ_SMALL; size < SZ_MAX; size++ ){
|
for( uint8 size = SZ_SMALL; size < SZ_MAX; size++ ){
|
||||||
sd->right_weapon.addsize[size] += attack_bonus[size][skill - 1];
|
sd->right_weapon.addsize[size] += attack_bonus[size][skill - 1];
|
||||||
sd->left_weapon.addsize[size] += attack_bonus[size][skill - 1];
|
if( !battle_config.left_cardfix_to_right ){
|
||||||
|
sd->left_weapon.addsize[size] += attack_bonus[size][skill - 1];
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
if ((skill = pc_checkskill(sd, CD_FIDUS_ANIMUS)) > 0) {
|
if ((skill = pc_checkskill(sd, CD_FIDUS_ANIMUS)) > 0) {
|
||||||
@ -4566,7 +4592,9 @@ int status_calc_pc_sub(map_session_data* sd, uint8 opt)
|
|||||||
|
|
||||||
for( uint8 size = SZ_SMALL; size < SZ_MAX; size++ ){
|
for( uint8 size = SZ_SMALL; size < SZ_MAX; size++ ){
|
||||||
sd->right_weapon.addsize[size] += attack_bonus[size][skill - 1];
|
sd->right_weapon.addsize[size] += attack_bonus[size][skill - 1];
|
||||||
sd->left_weapon.addsize[size] += attack_bonus[size][skill - 1];
|
if( !battle_config.left_cardfix_to_right ){
|
||||||
|
sd->left_weapon.addsize[size] += attack_bonus[size][skill - 1];
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
if ((skill = pc_checkskill(sd, ABC_MAGIC_SWORD_M)) > 0 && (sd->status.weapon == W_DAGGER || sd->status.weapon == W_1HSWORD || sd->status.weapon == W_DOUBLE_DD || sd->status.weapon == W_DOUBLE_SS || sd->status.weapon == W_DOUBLE_DS || sd->status.weapon == W_DOUBLE_DA || sd->status.weapon == W_DOUBLE_SA)) {
|
if ((skill = pc_checkskill(sd, ABC_MAGIC_SWORD_M)) > 0 && (sd->status.weapon == W_DAGGER || sd->status.weapon == W_1HSWORD || sd->status.weapon == W_DOUBLE_DD || sd->status.weapon == W_DOUBLE_SS || sd->status.weapon == W_DOUBLE_DS || sd->status.weapon == W_DOUBLE_DA || sd->status.weapon == W_DOUBLE_SA)) {
|
||||||
@ -4613,8 +4641,10 @@ int status_calc_pc_sub(map_session_data* sd, uint8 opt)
|
|||||||
i = sc->getSCE(SC_BASILICA)->val1 * 5;
|
i = sc->getSCE(SC_BASILICA)->val1 * 5;
|
||||||
sd->right_weapon.addele[ELE_DARK] += i;
|
sd->right_weapon.addele[ELE_DARK] += i;
|
||||||
sd->right_weapon.addele[ELE_UNDEAD] += i;
|
sd->right_weapon.addele[ELE_UNDEAD] += i;
|
||||||
sd->left_weapon.addele[ELE_DARK] += i;
|
if( !battle_config.left_cardfix_to_right ){
|
||||||
sd->left_weapon.addele[ELE_UNDEAD] += i;
|
sd->left_weapon.addele[ELE_DARK] += i;
|
||||||
|
sd->left_weapon.addele[ELE_UNDEAD] += i;
|
||||||
|
}
|
||||||
sd->indexed_bonus.magic_atk_ele[ELE_HOLY] += sc->getSCE(SC_BASILICA)->val1 * 3;
|
sd->indexed_bonus.magic_atk_ele[ELE_HOLY] += sc->getSCE(SC_BASILICA)->val1 * 3;
|
||||||
}
|
}
|
||||||
if (sc->getSCE(SC_FIREWEAPON))
|
if (sc->getSCE(SC_FIREWEAPON))
|
||||||
@ -4630,20 +4660,22 @@ int status_calc_pc_sub(map_session_data* sd, uint8 opt)
|
|||||||
sd->indexed_bonus.subele[ELE_HOLY] += sc->getSCE(SC_PROVIDENCE)->val2;
|
sd->indexed_bonus.subele[ELE_HOLY] += sc->getSCE(SC_PROVIDENCE)->val2;
|
||||||
sd->indexed_bonus.subrace[RC_DEMON] += sc->getSCE(SC_PROVIDENCE)->val2;
|
sd->indexed_bonus.subrace[RC_DEMON] += sc->getSCE(SC_PROVIDENCE)->val2;
|
||||||
}
|
}
|
||||||
if (sc->getSCE(SC_GEFFEN_MAGIC1)) {
|
if (sc->getSCE(SC_GEFFEN_MAGIC1)) {
|
||||||
sd->right_weapon.addrace[RC_PLAYER_HUMAN] += sc->getSCE(SC_GEFFEN_MAGIC1)->val1;
|
sd->right_weapon.addrace[RC_PLAYER_HUMAN] += sc->getSCE(SC_GEFFEN_MAGIC1)->val1;
|
||||||
sd->right_weapon.addrace[RC_DEMIHUMAN] += sc->getSCE(SC_GEFFEN_MAGIC1)->val1;
|
sd->right_weapon.addrace[RC_DEMIHUMAN] += sc->getSCE(SC_GEFFEN_MAGIC1)->val1;
|
||||||
sd->left_weapon.addrace[RC_PLAYER_HUMAN] += sc->getSCE(SC_GEFFEN_MAGIC1)->val1;
|
if( !battle_config.left_cardfix_to_right ){
|
||||||
sd->left_weapon.addrace[RC_DEMIHUMAN] += sc->getSCE(SC_GEFFEN_MAGIC1)->val1;
|
sd->left_weapon.addrace[RC_PLAYER_HUMAN] += sc->getSCE( SC_GEFFEN_MAGIC1 )->val1;
|
||||||
}
|
sd->left_weapon.addrace[RC_DEMIHUMAN] += sc->getSCE( SC_GEFFEN_MAGIC1 )->val1;
|
||||||
if (sc->getSCE(SC_GEFFEN_MAGIC2)) {
|
}
|
||||||
sd->indexed_bonus.magic_addrace[RC_PLAYER_HUMAN] += sc->getSCE(SC_GEFFEN_MAGIC2)->val1;
|
}
|
||||||
sd->indexed_bonus.magic_addrace[RC_DEMIHUMAN] += sc->getSCE(SC_GEFFEN_MAGIC2)->val1;
|
if (sc->getSCE(SC_GEFFEN_MAGIC2)) {
|
||||||
}
|
sd->indexed_bonus.magic_addrace[RC_PLAYER_HUMAN] += sc->getSCE(SC_GEFFEN_MAGIC2)->val1;
|
||||||
if(sc->getSCE(SC_GEFFEN_MAGIC3)) {
|
sd->indexed_bonus.magic_addrace[RC_DEMIHUMAN] += sc->getSCE(SC_GEFFEN_MAGIC2)->val1;
|
||||||
sd->indexed_bonus.subrace[RC_PLAYER_HUMAN] += sc->getSCE(SC_GEFFEN_MAGIC3)->val1;
|
}
|
||||||
sd->indexed_bonus.subrace[RC_DEMIHUMAN] += sc->getSCE(SC_GEFFEN_MAGIC3)->val1;
|
if(sc->getSCE(SC_GEFFEN_MAGIC3)) {
|
||||||
}
|
sd->indexed_bonus.subrace[RC_PLAYER_HUMAN] += sc->getSCE(SC_GEFFEN_MAGIC3)->val1;
|
||||||
|
sd->indexed_bonus.subrace[RC_DEMIHUMAN] += sc->getSCE(SC_GEFFEN_MAGIC3)->val1;
|
||||||
|
}
|
||||||
if(sc->getSCE(SC_ARMOR_ELEMENT_WATER)) { // This status change should grant card-type elemental resist.
|
if(sc->getSCE(SC_ARMOR_ELEMENT_WATER)) { // This status change should grant card-type elemental resist.
|
||||||
sd->indexed_bonus.subele[ELE_WATER] += sc->getSCE(SC_ARMOR_ELEMENT_WATER)->val1;
|
sd->indexed_bonus.subele[ELE_WATER] += sc->getSCE(SC_ARMOR_ELEMENT_WATER)->val1;
|
||||||
sd->indexed_bonus.subele[ELE_EARTH] += sc->getSCE(SC_ARMOR_ELEMENT_WATER)->val2;
|
sd->indexed_bonus.subele[ELE_EARTH] += sc->getSCE(SC_ARMOR_ELEMENT_WATER)->val2;
|
||||||
@ -7984,6 +8016,10 @@ static unsigned short status_calc_speed(struct block_list *bl, status_change *sc
|
|||||||
val = max(val, sc->getSCE(SC_SP_SHA)->val2);
|
val = max(val, sc->getSCE(SC_SP_SHA)->val2);
|
||||||
if (sc->getSCE(SC_CREATINGSTAR))
|
if (sc->getSCE(SC_CREATINGSTAR))
|
||||||
val = max(val, 90);
|
val = max(val, 90);
|
||||||
|
if (sc->getSCE(SC_SHIELDCHAINRUSH))
|
||||||
|
val = max(val, 20);
|
||||||
|
if (sc->getSCE(SC_GROUNDGRAVITY))
|
||||||
|
val = max(val, 20);
|
||||||
|
|
||||||
if( sd && sd->bonus.speed_rate + sd->bonus.speed_add_rate > 0 ) // Permanent item-based speedup
|
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 );
|
val = max( val, sd->bonus.speed_rate + sd->bonus.speed_add_rate );
|
||||||
@ -9384,6 +9420,7 @@ static int status_get_sc_interval(enum sc_type type)
|
|||||||
case SC_DEATHHURT:
|
case SC_DEATHHURT:
|
||||||
case SC_GRADUAL_GRAVITY:
|
case SC_GRADUAL_GRAVITY:
|
||||||
case SC_KILLING_AURA:
|
case SC_KILLING_AURA:
|
||||||
|
case SC_BOSSMAPINFO:
|
||||||
return 1000;
|
return 1000;
|
||||||
case SC_BURNING:
|
case SC_BURNING:
|
||||||
case SC_PYREXIA:
|
case SC_PYREXIA:
|
||||||
@ -10398,6 +10435,7 @@ int status_change_start(struct block_list* src, struct block_list* bl,enum sc_ty
|
|||||||
case SC_BERSERK:
|
case SC_BERSERK:
|
||||||
case SC_SATURDAYNIGHTFEVER:
|
case SC_SATURDAYNIGHTFEVER:
|
||||||
sc->getSCE(rem_sc)->val2 = 0; // Mark to not lose hp
|
sc->getSCE(rem_sc)->val2 = 0; // Mark to not lose hp
|
||||||
|
[[fallthrough]];
|
||||||
default:
|
default:
|
||||||
status_change_end(bl, rem_sc);
|
status_change_end(bl, rem_sc);
|
||||||
break;
|
break;
|
||||||
@ -10502,6 +10540,7 @@ int status_change_start(struct block_list* src, struct block_list* bl,enum sc_ty
|
|||||||
if (sc && sc->getSCE(type)->val2 & BREAK_NECK)
|
if (sc && sc->getSCE(type)->val2 & BREAK_NECK)
|
||||||
return 0; // BREAK_NECK cannot be stacked with new breaks until the status is over.
|
return 0; // BREAK_NECK cannot be stacked with new breaks until the status is over.
|
||||||
val2 |= sce->val2; // Stackable ailments
|
val2 |= sce->val2; // Stackable ailments
|
||||||
|
[[fallthrough]];
|
||||||
default:
|
default:
|
||||||
if (scdb->flag[SCF_OVERLAPIGNORELEVEL])
|
if (scdb->flag[SCF_OVERLAPIGNORELEVEL])
|
||||||
break;
|
break;
|
||||||
@ -10868,7 +10907,7 @@ int status_change_start(struct block_list* src, struct block_list* bl,enum sc_ty
|
|||||||
diff = status->hp - (status->max_hp / 4);
|
diff = status->hp - (status->max_hp / 4);
|
||||||
status_zap(bl, diff, 0);
|
status_zap(bl, diff, 0);
|
||||||
}
|
}
|
||||||
// Fall through
|
[[fallthrough]];
|
||||||
case SC_STONE:
|
case SC_STONE:
|
||||||
case SC_POISON:
|
case SC_POISON:
|
||||||
case SC_BLEEDING:
|
case SC_BLEEDING:
|
||||||
@ -10889,6 +10928,7 @@ int status_change_start(struct block_list* src, struct block_list* bl,enum sc_ty
|
|||||||
break;
|
break;
|
||||||
tick_time = status_get_sc_interval(type);
|
tick_time = status_get_sc_interval(type);
|
||||||
val4 = tick - tick_time; // Remaining time
|
val4 = tick - tick_time; // Remaining time
|
||||||
|
break;
|
||||||
case SC_LEECHESEND:
|
case SC_LEECHESEND:
|
||||||
if (val3 == 0)
|
if (val3 == 0)
|
||||||
break;
|
break;
|
||||||
@ -10960,16 +11000,21 @@ int status_change_start(struct block_list* src, struct block_list* bl,enum sc_ty
|
|||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
case SC_BOSSMAPINFO:
|
case SC_BOSSMAPINFO:
|
||||||
if( sd != NULL ) {
|
if( sd == nullptr ){
|
||||||
struct mob_data *boss_md = map_getmob_boss(bl->m); // Search for Boss on this Map
|
return 0;
|
||||||
|
}else{
|
||||||
|
// Search for Boss on this Map
|
||||||
|
mob_data* boss_md = map_getmob_boss( bl->m );
|
||||||
|
|
||||||
if( boss_md == NULL ) { // No MVP on this map
|
// No MVP on this map
|
||||||
clif_bossmapinfo(sd, NULL, BOSS_INFO_NOT);
|
if( boss_md == nullptr ){
|
||||||
|
clif_bossmapinfo( *sd, nullptr, BOSS_INFO_NOT );
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
val1 = boss_md->bl.id;
|
val1 = boss_md->bl.id;
|
||||||
tick_time = 1000; // [GodLesZ] tick time
|
tick_time = status_get_sc_interval( type );
|
||||||
val4 = tick / tick_time;
|
val4 = tick - tick_time; // Remaining time
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
case SC_HIDING:
|
case SC_HIDING:
|
||||||
@ -11227,6 +11272,7 @@ int status_change_start(struct block_list* src, struct block_list* bl,enum sc_ty
|
|||||||
switch (val1) {
|
switch (val1) {
|
||||||
case 3: // 33*3 + 1 -> 100%
|
case 3: // 33*3 + 1 -> 100%
|
||||||
val2++;
|
val2++;
|
||||||
|
[[fallthrough]];
|
||||||
case 1:
|
case 1:
|
||||||
case 2: // 33, 66%
|
case 2: // 33, 66%
|
||||||
val2 += 33*val1;
|
val2 += 33*val1;
|
||||||
@ -11454,6 +11500,7 @@ int status_change_start(struct block_list* src, struct block_list* bl,enum sc_ty
|
|||||||
// Level 1 ~ 5 & 6 ~ 10 has different duration
|
// Level 1 ~ 5 & 6 ~ 10 has different duration
|
||||||
// Level 6 ~ 10 use effect of level 1 ~ 5
|
// Level 6 ~ 10 use effect of level 1 ~ 5
|
||||||
val1 = 1 + ((val1-1)%5);
|
val1 = 1 + ((val1-1)%5);
|
||||||
|
[[fallthrough]];
|
||||||
case SC_SLOWCAST:
|
case SC_SLOWCAST:
|
||||||
val2 = 20*val1; // Magic reflection/cast rate
|
val2 = 20*val1; // Magic reflection/cast rate
|
||||||
break;
|
break;
|
||||||
@ -11975,17 +12022,20 @@ int status_change_start(struct block_list* src, struct block_list* bl,enum sc_ty
|
|||||||
case SC_WILD_STORM:
|
case SC_WILD_STORM:
|
||||||
case SC_UPHEAVAL:
|
case SC_UPHEAVAL:
|
||||||
val2 += 10;
|
val2 += 10;
|
||||||
|
[[fallthrough]];
|
||||||
case SC_HEATER:
|
case SC_HEATER:
|
||||||
case SC_COOLER:
|
case SC_COOLER:
|
||||||
case SC_BLAST:
|
case SC_BLAST:
|
||||||
case SC_CURSED_SOIL:
|
case SC_CURSED_SOIL:
|
||||||
val2 += 10;
|
val2 += 10;
|
||||||
|
[[fallthrough]];
|
||||||
case SC_PYROTECHNIC:
|
case SC_PYROTECHNIC:
|
||||||
case SC_AQUAPLAY:
|
case SC_AQUAPLAY:
|
||||||
case SC_GUST:
|
case SC_GUST:
|
||||||
case SC_PETROLOGY:
|
case SC_PETROLOGY:
|
||||||
val2 += 5;
|
val2 += 5;
|
||||||
val3 += 9000;
|
val3 += 9000;
|
||||||
|
[[fallthrough]];
|
||||||
case SC_CIRCLE_OF_FIRE:
|
case SC_CIRCLE_OF_FIRE:
|
||||||
case SC_FIRE_CLOAK:
|
case SC_FIRE_CLOAK:
|
||||||
case SC_WATER_DROP:
|
case SC_WATER_DROP:
|
||||||
@ -12729,6 +12779,7 @@ int status_change_start(struct block_list* src, struct block_list* bl,enum sc_ty
|
|||||||
break;
|
break;
|
||||||
tick_time = tick;
|
tick_time = tick;
|
||||||
tick = tick_time + max(val4, 0);
|
tick = tick_time + max(val4, 0);
|
||||||
|
[[fallthrough]];
|
||||||
case SC_MAGICMUSHROOM:
|
case SC_MAGICMUSHROOM:
|
||||||
case SC_PYREXIA:
|
case SC_PYREXIA:
|
||||||
case SC_LEECHESEND:
|
case SC_LEECHESEND:
|
||||||
@ -12951,8 +13002,28 @@ int status_change_start(struct block_list* src, struct block_list* bl,enum sc_ty
|
|||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
case SC_BOSSMAPINFO:
|
case SC_BOSSMAPINFO:
|
||||||
if (sd)
|
if( sd == nullptr ){
|
||||||
clif_bossmapinfo(sd, map_id2boss(sce->val1), BOSS_INFO_ALIVE_WITHMSG); // First Message
|
return 0;
|
||||||
|
}else{
|
||||||
|
mob_data* boss_md = map_id2boss( sce->val1 );
|
||||||
|
|
||||||
|
if( boss_md == nullptr ){
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Not on same map anymore
|
||||||
|
if( sd->bl.m != boss_md->bl.m ){
|
||||||
|
return 0;
|
||||||
|
// Boss is alive
|
||||||
|
}else if( boss_md->bl.prev != nullptr ){
|
||||||
|
sce->val2 = 0;
|
||||||
|
clif_bossmapinfo( *sd, boss_md, BOSS_INFO_ALIVE_WITHMSG );
|
||||||
|
// Boss is dead
|
||||||
|
}else if( boss_md->spawn_timer != INVALID_TIMER ){
|
||||||
|
sce->val2 = 1;
|
||||||
|
clif_bossmapinfo( *sd, boss_md, BOSS_INFO_DEAD );
|
||||||
|
}
|
||||||
|
}
|
||||||
break;
|
break;
|
||||||
case SC_FULL_THROTTLE:
|
case SC_FULL_THROTTLE:
|
||||||
case SC_MERC_HPUP:
|
case SC_MERC_HPUP:
|
||||||
@ -13332,16 +13403,18 @@ int status_change_end(struct block_list* bl, enum sc_type type, int tid)
|
|||||||
skill_castend_damage_id(src, bl, sce->val2, sce->val1, gettick(), SD_LEVEL );
|
skill_castend_damage_id(src, bl, sce->val2, sce->val1, gettick(), SD_LEVEL );
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
case SC_CLOSECONFINE2:{
|
case SC_CLOSECONFINE2:
|
||||||
struct block_list *src = sce->val2?map_id2bl(sce->val2):NULL;
|
{
|
||||||
status_change *sc2 = src?status_get_sc(src):NULL;
|
struct block_list *src = sce->val2?map_id2bl(sce->val2):nullptr;
|
||||||
if (src && sc2 && sc2->getSCE(SC_CLOSECONFINE)) {
|
status_change *sc2 = src?status_get_sc(src):nullptr;
|
||||||
// If status was already ended, do nothing.
|
if (src && sc2 && sc2->getSCE(SC_CLOSECONFINE)) {
|
||||||
// Decrease count
|
// If status was already ended, do nothing.
|
||||||
if (--(sc2->getSCE(SC_CLOSECONFINE)->val1) <= 0) // No more holds, free him up.
|
// Decrease count
|
||||||
status_change_end(src, SC_CLOSECONFINE);
|
if (--(sc2->getSCE(SC_CLOSECONFINE)->val1) <= 0) // No more holds, free him up.
|
||||||
|
status_change_end(src, SC_CLOSECONFINE);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
[[fallthrough]];
|
||||||
case SC_CLOSECONFINE:
|
case SC_CLOSECONFINE:
|
||||||
if (sce->val2 > 0) {
|
if (sce->val2 > 0) {
|
||||||
// Caster has been unlocked... nearby chars need to be unlocked.
|
// Caster has been unlocked... nearby chars need to be unlocked.
|
||||||
@ -14043,22 +14116,27 @@ TIMER_FUNC(status_change_timer){
|
|||||||
break;
|
break;
|
||||||
|
|
||||||
case SC_BOSSMAPINFO:
|
case SC_BOSSMAPINFO:
|
||||||
if( sd && --(sce->val4) >= 0 ) {
|
if( sd && sce->val4 >= 0 ){
|
||||||
struct mob_data *boss_md = map_id2boss(sce->val1);
|
mob_data* boss_md = map_id2boss( sce->val1 );
|
||||||
|
|
||||||
if (boss_md) {
|
if( boss_md == nullptr ){
|
||||||
if (sd->bl.m != boss_md->bl.m) // Not on same map anymore
|
sce->val4 = 0;
|
||||||
return 0;
|
break;
|
||||||
else if (boss_md->bl.prev != NULL) { // Boss is alive - Update X, Y on minimap
|
}
|
||||||
sce->val2 = 0;
|
|
||||||
clif_bossmapinfo(sd, boss_md, BOSS_INFO_ALIVE);
|
// Not on same map anymore
|
||||||
} else if (boss_md->spawn_timer != INVALID_TIMER && !sce->val2) { // Boss is dead
|
if( sd->bl.m != boss_md->bl.m ){
|
||||||
sce->val2 = 1;
|
sce->val4 = 0;
|
||||||
clif_bossmapinfo(sd, boss_md, BOSS_INFO_DEAD);
|
break;
|
||||||
}
|
// Boss is alive - Update X, Y on minimap
|
||||||
|
}else if( boss_md->bl.prev != nullptr ){
|
||||||
|
sce->val2 = 0;
|
||||||
|
clif_bossmapinfo( *sd, boss_md, BOSS_INFO_ALIVE );
|
||||||
|
// Boss is dead
|
||||||
|
}else if( boss_md->spawn_timer != INVALID_TIMER && sce->val2 == 0 ){
|
||||||
|
sce->val2 = 1;
|
||||||
|
clif_bossmapinfo( *sd, boss_md, BOSS_INFO_DEAD );
|
||||||
}
|
}
|
||||||
sc_timer_next(1000 + tick);
|
|
||||||
return 0;
|
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
|
|
||||||
@ -14102,6 +14180,7 @@ TIMER_FUNC(status_change_timer){
|
|||||||
sp= 4*(sce->val1>>16);
|
sp= 4*(sce->val1>>16);
|
||||||
// Upkeep is also every 10 secs.
|
// Upkeep is also every 10 secs.
|
||||||
#ifndef RENEWAL
|
#ifndef RENEWAL
|
||||||
|
[[fallthrough]];
|
||||||
case DC_DONTFORGETME:
|
case DC_DONTFORGETME:
|
||||||
#endif
|
#endif
|
||||||
s=10;
|
s=10;
|
||||||
|
|||||||
@ -1284,6 +1284,15 @@ enum sc_type : int16 {
|
|||||||
SC_RUSH_QUAKE2,
|
SC_RUSH_QUAKE2,
|
||||||
|
|
||||||
SC_G_LIFEPOTION,
|
SC_G_LIFEPOTION,
|
||||||
|
|
||||||
|
// Hyper Novice
|
||||||
|
SC_HNNOWEAPON,
|
||||||
|
SC_SHIELDCHAINRUSH,
|
||||||
|
SC_MISTYFROST,
|
||||||
|
SC_GROUNDGRAVITY,
|
||||||
|
SC_BREAKINGLIMIT,
|
||||||
|
SC_RULEBREAK,
|
||||||
|
|
||||||
#ifdef RENEWAL
|
#ifdef RENEWAL
|
||||||
SC_EXTREMITYFIST2, //! NOTE: This SC should be right before SC_MAX, so it doesn't disturb if RENEWAL is disabled
|
SC_EXTREMITYFIST2, //! NOTE: This SC should be right before SC_MAX, so it doesn't disturb if RENEWAL is disabled
|
||||||
#endif
|
#endif
|
||||||
|
|||||||
@ -3290,7 +3290,7 @@ int unit_remove_map_(struct block_list *bl, clr_type clrtype, const char* file,
|
|||||||
map_delblock(bl);
|
map_delblock(bl);
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
// Fall through
|
[[fallthrough]];
|
||||||
default:
|
default:
|
||||||
clif_clearunit_area(bl, clrtype);
|
clif_clearunit_area(bl, clrtype);
|
||||||
map_delblock(bl);
|
map_delblock(bl);
|
||||||
|
|||||||
@ -44,26 +44,26 @@ struct Web_Config web_config {};
|
|||||||
struct Inter_Config inter_config {};
|
struct Inter_Config inter_config {};
|
||||||
std::shared_ptr<httplib::Server> http_server;
|
std::shared_ptr<httplib::Server> http_server;
|
||||||
|
|
||||||
int login_server_port = 3306;
|
|
||||||
std::string login_server_ip = "127.0.0.1";
|
std::string login_server_ip = "127.0.0.1";
|
||||||
|
uint16 login_server_port = 3306;
|
||||||
std::string login_server_id = "ragnarok";
|
std::string login_server_id = "ragnarok";
|
||||||
std::string login_server_pw = "";
|
std::string login_server_pw = "";
|
||||||
std::string login_server_db = "ragnarok";
|
std::string login_server_db = "ragnarok";
|
||||||
|
|
||||||
int char_server_port = 3306;
|
|
||||||
std::string char_server_ip = "127.0.0.1";
|
std::string char_server_ip = "127.0.0.1";
|
||||||
|
uint16 char_server_port = 3306;
|
||||||
std::string char_server_id = "ragnarok";
|
std::string char_server_id = "ragnarok";
|
||||||
std::string char_server_pw = "";
|
std::string char_server_pw = "";
|
||||||
std::string char_server_db = "ragnarok";
|
std::string char_server_db = "ragnarok";
|
||||||
|
|
||||||
int map_server_port = 3306;
|
|
||||||
std::string map_server_ip = "127.0.0.1";
|
std::string map_server_ip = "127.0.0.1";
|
||||||
|
uint16 map_server_port = 3306;
|
||||||
std::string map_server_id = "ragnarok";
|
std::string map_server_id = "ragnarok";
|
||||||
std::string map_server_pw = "";
|
std::string map_server_pw = "";
|
||||||
std::string map_server_db = "ragnarok";
|
std::string map_server_db = "ragnarok";
|
||||||
|
|
||||||
int web_server_port = 3306;
|
|
||||||
std::string web_server_ip = "127.0.0.1";
|
std::string web_server_ip = "127.0.0.1";
|
||||||
|
uint16 web_server_port = 3306;
|
||||||
std::string web_server_id = "ragnarok";
|
std::string web_server_id = "ragnarok";
|
||||||
std::string web_server_pw = "";
|
std::string web_server_pw = "";
|
||||||
std::string web_server_db = "ragnarok";
|
std::string web_server_db = "ragnarok";
|
||||||
@ -188,7 +188,7 @@ int inter_config_read(const char* cfgName)
|
|||||||
else if(!strcmpi(w1,"login_server_ip"))
|
else if(!strcmpi(w1,"login_server_ip"))
|
||||||
login_server_ip = w2;
|
login_server_ip = w2;
|
||||||
else if(!strcmpi(w1,"login_server_port"))
|
else if(!strcmpi(w1,"login_server_port"))
|
||||||
login_server_port = atoi(w2);
|
login_server_port = (uint16)strtoul( w2, nullptr, 10 );
|
||||||
else if(!strcmpi(w1,"login_server_id"))
|
else if(!strcmpi(w1,"login_server_id"))
|
||||||
login_server_id = w2;
|
login_server_id = w2;
|
||||||
else if(!strcmpi(w1,"login_server_pw"))
|
else if(!strcmpi(w1,"login_server_pw"))
|
||||||
@ -198,7 +198,7 @@ int inter_config_read(const char* cfgName)
|
|||||||
else if(!strcmpi(w1,"char_server_ip"))
|
else if(!strcmpi(w1,"char_server_ip"))
|
||||||
char_server_ip = w2;
|
char_server_ip = w2;
|
||||||
else if(!strcmpi(w1,"char_server_port"))
|
else if(!strcmpi(w1,"char_server_port"))
|
||||||
char_server_port = atoi(w2);
|
char_server_port = (uint16)strtoul( w2, nullptr, 10 );
|
||||||
else if(!strcmpi(w1,"char_server_id"))
|
else if(!strcmpi(w1,"char_server_id"))
|
||||||
char_server_id = w2;
|
char_server_id = w2;
|
||||||
else if(!strcmpi(w1,"char_server_pw"))
|
else if(!strcmpi(w1,"char_server_pw"))
|
||||||
@ -208,7 +208,7 @@ int inter_config_read(const char* cfgName)
|
|||||||
else if(!strcmpi(w1,"map_server_ip"))
|
else if(!strcmpi(w1,"map_server_ip"))
|
||||||
map_server_ip = w2;
|
map_server_ip = w2;
|
||||||
else if(!strcmpi(w1,"map_server_port"))
|
else if(!strcmpi(w1,"map_server_port"))
|
||||||
map_server_port = atoi(w2);
|
map_server_port = (uint16)strtoul( w2, nullptr, 10 );
|
||||||
else if(!strcmpi(w1,"map_server_id"))
|
else if(!strcmpi(w1,"map_server_id"))
|
||||||
map_server_id = w2;
|
map_server_id = w2;
|
||||||
else if(!strcmpi(w1,"map_server_pw"))
|
else if(!strcmpi(w1,"map_server_pw"))
|
||||||
@ -218,7 +218,7 @@ int inter_config_read(const char* cfgName)
|
|||||||
else if(!strcmpi(w1,"web_server_ip"))
|
else if(!strcmpi(w1,"web_server_ip"))
|
||||||
web_server_ip = w2;
|
web_server_ip = w2;
|
||||||
else if(!strcmpi(w1,"web_server_port"))
|
else if(!strcmpi(w1,"web_server_port"))
|
||||||
web_server_port = atoi(w2);
|
web_server_port = (uint16)strtoul( w2, nullptr, 10 );
|
||||||
else if(!strcmpi(w1,"web_server_id"))
|
else if(!strcmpi(w1,"web_server_id"))
|
||||||
web_server_id = w2;
|
web_server_id = w2;
|
||||||
else if(!strcmpi(w1,"web_server_pw"))
|
else if(!strcmpi(w1,"web_server_pw"))
|
||||||
@ -276,7 +276,7 @@ int web_sql_init(void) {
|
|||||||
ShowInfo("Connecting to the Login DB server.....\n");
|
ShowInfo("Connecting to the Login DB server.....\n");
|
||||||
|
|
||||||
if (SQL_ERROR == Sql_Connect(login_handle, login_server_id.c_str(), login_server_pw.c_str(), login_server_ip.c_str(), login_server_port, login_server_db.c_str())) {
|
if (SQL_ERROR == Sql_Connect(login_handle, login_server_id.c_str(), login_server_pw.c_str(), login_server_ip.c_str(), login_server_port, login_server_db.c_str())) {
|
||||||
ShowError("Couldn't connect with uname='%s',host='%s',port='%d',database='%s'\n",
|
ShowError("Couldn't connect with uname='%s',host='%s',port='%hu',database='%s'\n",
|
||||||
login_server_id.c_str(), login_server_ip.c_str(), login_server_port, login_server_db.c_str());
|
login_server_id.c_str(), login_server_ip.c_str(), login_server_port, login_server_db.c_str());
|
||||||
Sql_ShowDebug(login_handle);
|
Sql_ShowDebug(login_handle);
|
||||||
Sql_Free(login_handle);
|
Sql_Free(login_handle);
|
||||||
@ -293,7 +293,7 @@ int web_sql_init(void) {
|
|||||||
ShowInfo("Connecting to the Char DB server.....\n");
|
ShowInfo("Connecting to the Char DB server.....\n");
|
||||||
|
|
||||||
if (SQL_ERROR == Sql_Connect(char_handle, char_server_id.c_str(), char_server_pw.c_str(), char_server_ip.c_str(), char_server_port, char_server_db.c_str())) {
|
if (SQL_ERROR == Sql_Connect(char_handle, char_server_id.c_str(), char_server_pw.c_str(), char_server_ip.c_str(), char_server_port, char_server_db.c_str())) {
|
||||||
ShowError("Couldn't connect with uname='%s',host='%s',port='%d',database='%s'\n",
|
ShowError("Couldn't connect with uname='%s',host='%s',port='%hu',database='%s'\n",
|
||||||
char_server_id.c_str(), char_server_ip.c_str(), char_server_port, char_server_db.c_str());
|
char_server_id.c_str(), char_server_ip.c_str(), char_server_port, char_server_db.c_str());
|
||||||
Sql_ShowDebug(char_handle);
|
Sql_ShowDebug(char_handle);
|
||||||
Sql_Free(char_handle);
|
Sql_Free(char_handle);
|
||||||
@ -310,7 +310,7 @@ int web_sql_init(void) {
|
|||||||
ShowInfo("Connecting to the Map DB server.....\n");
|
ShowInfo("Connecting to the Map DB server.....\n");
|
||||||
|
|
||||||
if (SQL_ERROR == Sql_Connect(map_handle, map_server_id.c_str(), map_server_pw.c_str(), map_server_ip.c_str(), map_server_port, map_server_db.c_str())) {
|
if (SQL_ERROR == Sql_Connect(map_handle, map_server_id.c_str(), map_server_pw.c_str(), map_server_ip.c_str(), map_server_port, map_server_db.c_str())) {
|
||||||
ShowError("Couldn't connect with uname='%s',host='%s',port='%d',database='%s'\n",
|
ShowError("Couldn't connect with uname='%s',host='%s',port='%hu',database='%s'\n",
|
||||||
map_server_id.c_str(), map_server_ip.c_str(), map_server_port, map_server_db.c_str());
|
map_server_id.c_str(), map_server_ip.c_str(), map_server_port, map_server_db.c_str());
|
||||||
Sql_ShowDebug(map_handle);
|
Sql_ShowDebug(map_handle);
|
||||||
Sql_Free(map_handle);
|
Sql_Free(map_handle);
|
||||||
@ -327,7 +327,7 @@ int web_sql_init(void) {
|
|||||||
ShowInfo("Connecting to the Web DB server.....\n");
|
ShowInfo("Connecting to the Web DB server.....\n");
|
||||||
|
|
||||||
if (SQL_ERROR == Sql_Connect(web_handle, web_server_id.c_str(), web_server_pw.c_str(), web_server_ip.c_str(), web_server_port, web_server_db.c_str())) {
|
if (SQL_ERROR == Sql_Connect(web_handle, web_server_id.c_str(), web_server_pw.c_str(), web_server_ip.c_str(), web_server_port, web_server_db.c_str())) {
|
||||||
ShowError("Couldn't connect with uname='%s',host='%s',port='%d',database='%s'\n",
|
ShowError("Couldn't connect with uname='%s',host='%s',port='%hu',database='%s'\n",
|
||||||
web_server_id.c_str(), web_server_ip.c_str(), web_server_port, web_server_db.c_str());
|
web_server_id.c_str(), web_server_ip.c_str(), web_server_port, web_server_db.c_str());
|
||||||
Sql_ShowDebug(web_handle);
|
Sql_ShowDebug(web_handle);
|
||||||
Sql_Free(web_handle);
|
Sql_Free(web_handle);
|
||||||
|
|||||||
Loading…
x
Reference in New Issue
Block a user