mirror of
https://github.com/EQEmu/Server.git
synced 2026-05-30 11:45:46 +00:00
Compare commits
15 Commits
| Author | SHA1 | Date | |
|---|---|---|---|
| a7e9af2d27 | |||
| 7a72d5d67e | |||
| 25872203ff | |||
| 6396a6fbef | |||
| 6db0a5c3f0 | |||
| 4fa9e1d66f | |||
| 556af8c5e9 | |||
| f3ef8a0993 | |||
| 267c280db8 | |||
| e06c7d7735 | |||
| 028ebc3a0c | |||
| b3bd44cd76 | |||
| 75a627a3a2 | |||
| 0194aedc92 | |||
| 5cc87cbda7 |
@@ -1,3 +1,42 @@
|
||||
## [22.38.0] - 12/26/2023
|
||||
|
||||
### Bots
|
||||
|
||||
* Remove unnecessary error on SetItemReuse ([#3795](https://github.com/EQEmu/Server/pull/3795)) @nytmyr 2023-12-20
|
||||
|
||||
### Code
|
||||
|
||||
* Consolidate GetHateRandom(), GetHateRandomBot(), GetHateRandomClient(), and GetHateRandomNPC() ([#3794](https://github.com/EQEmu/Server/pull/3794)) @Kinglykrab 2023-12-25
|
||||
* Race constants refactor ([#3782](https://github.com/EQEmu/Server/pull/3782)) @Akkadius 2023-12-23
|
||||
|
||||
### Database
|
||||
|
||||
* Fix issue with saylinks query in MySQL 8.0+ ([#3800](https://github.com/EQEmu/Server/pull/3800)) @Akkadius 2023-12-24
|
||||
* Update faction mods with Live data ([#3799](https://github.com/EQEmu/Server/pull/3799)) @joligario 2023-12-23
|
||||
|
||||
### Fixes
|
||||
|
||||
* Disable Hide/Improved Hide on Trap damage ([#3791](https://github.com/EQEmu/Server/pull/3791)) @Kinglykrab 2023-12-19
|
||||
* Fix Bard Invisibility Songs breaking every 4 ticks ([#3783](https://github.com/EQEmu/Server/pull/3783)) @Kinglykrab 2023-12-19
|
||||
* Fix can_riposte parameter in DoMeleeSkillAttackDmg ([#3792](https://github.com/EQEmu/Server/pull/3792)) @Kinglykrab 2023-12-19
|
||||
|
||||
### Forage
|
||||
|
||||
* Add a rule to disabled using common_food_ids from the list in forage.cpp. currently set to enabled. ([#3796](https://github.com/EQEmu/Server/pull/3796)) @regneq 2023-12-22
|
||||
|
||||
### NPC
|
||||
|
||||
* Support for multiple emotes per type, emote variables ([#3801](https://github.com/EQEmu/Server/pull/3801)) @regneq 2023-12-25
|
||||
|
||||
### Quest API
|
||||
|
||||
* Add GetHateTopBot(), GetHateTopClient(), and GetHateTopNPC() to Perl/Lua ([#3793](https://github.com/EQEmu/Server/pull/3793)) @Kinglykrab 2023-12-22
|
||||
* Add SummonItemIntoInventory() to Perl/Lua ([#3797](https://github.com/EQEmu/Server/pull/3797)) @Kinglykrab 2023-12-22
|
||||
|
||||
### Repositories
|
||||
|
||||
* Add ReplaceOne and ReplaceMany ([#3802](https://github.com/EQEmu/Server/pull/3802)) @Akkadius 2023-12-26
|
||||
|
||||
## [22.37.0] - 12/18/2023
|
||||
|
||||
### Bots
|
||||
|
||||
@@ -5133,6 +5133,16 @@ CHANGE COLUMN `slot` `inventory_slot` mediumint(9) NOT NULL DEFAULT -1 AFTER `st
|
||||
|
||||
ALTER TABLE `starting_items`
|
||||
CHANGE COLUMN `temporary` `class_list` text CHARACTER SET latin1 COLLATE latin1_swedish_ci NULL DEFAULT NULL AFTER `id`;
|
||||
)"
|
||||
},
|
||||
ManifestEntry{
|
||||
.version = 9248,
|
||||
.description = "2023_12_22_drop_npc_emotes_index.sql",
|
||||
.check = "show index from npc_emotes where key_name = 'emoteid'",
|
||||
.condition = "not_empty",
|
||||
.match = "",
|
||||
.sql = R"(
|
||||
ALTER TABLE `npc_emotes` DROP INDEX `emoteid`;
|
||||
)"
|
||||
}
|
||||
|
||||
|
||||
+2
-2
@@ -96,12 +96,12 @@ bool IsOfEqualRace(int r1, int r2)
|
||||
// TODO: add more values
|
||||
switch (r1) {
|
||||
case DARK_ELF:
|
||||
if (r2 == RACE_NERIAK_CITIZEN_77) {
|
||||
if (r2 == Race::NeriakCitizen) {
|
||||
return true;
|
||||
}
|
||||
break;
|
||||
case BARBARIAN:
|
||||
if (r2 == RACE_HALAS_CITIZEN_90) {
|
||||
if (r2 == Race::HalasCitizen) {
|
||||
return true;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -801,34 +801,35 @@ int16 EQ::InventoryProfile::HasItemByLoreGroup(uint32 loregroup, uint8 where)
|
||||
// Returns slot_id when there's one available, else SLOT_INVALID
|
||||
int16 EQ::InventoryProfile::FindFreeSlot(bool for_bag, bool try_cursor, uint8 min_size, bool is_arrow)
|
||||
{
|
||||
// Check basic inventory
|
||||
for (int16 i = invslot::GENERAL_BEGIN; i <= invslot::GENERAL_END; i++) {
|
||||
if ((((uint64)1 << i) & m_lookup->PossessionsBitmask) == 0)
|
||||
continue;
|
||||
const int16 last_bag_slot = RuleI(World, ExpansionSettings) & EQ::expansions::bitHoT ? EQ::invslot::slotGeneral10 : EQ::invslot::slotGeneral8;
|
||||
|
||||
if (!GetItem(i))
|
||||
// Found available slot in personal inventory
|
||||
return i;
|
||||
for (int16 i = invslot::GENERAL_BEGIN; i <= last_bag_slot; i++) { // Check basic inventory
|
||||
if ((((uint64) 1 << i) & m_lookup->PossessionsBitmask) == 0) {
|
||||
continue;
|
||||
}
|
||||
|
||||
if (!GetItem(i)) {
|
||||
return i; // Found available slot in personal inventory
|
||||
}
|
||||
}
|
||||
|
||||
if (!for_bag) {
|
||||
for (int16 i = invslot::GENERAL_BEGIN; i <= invslot::GENERAL_END; i++) {
|
||||
if ((((uint64)1 << i) & m_lookup->PossessionsBitmask) == 0)
|
||||
for (int16 i = invslot::GENERAL_BEGIN; i <= last_bag_slot; i++) {
|
||||
if ((((uint64) 1 << i) & m_lookup->PossessionsBitmask) == 0) {
|
||||
continue;
|
||||
}
|
||||
|
||||
const ItemInstance* inst = GetItem(i);
|
||||
if (inst && inst->IsClassBag() && inst->GetItem()->BagSize >= min_size)
|
||||
{
|
||||
if (inst->GetItem()->BagType == item::BagTypeQuiver && inst->GetItem()->ItemType != item::ItemTypeArrow)
|
||||
{
|
||||
const auto *inst = GetItem(i);
|
||||
if (inst && inst->IsClassBag() && inst->GetItem()->BagSize >= min_size) {
|
||||
if (inst->GetItem()->BagType == item::BagTypeQuiver &&
|
||||
inst->GetItem()->ItemType != item::ItemTypeArrow) {
|
||||
continue;
|
||||
}
|
||||
|
||||
int16 base_slot_id = InventoryProfile::CalcSlotId(i, invbag::SLOT_BEGIN);
|
||||
const int16 base_slot_id = InventoryProfile::CalcSlotId(i, invbag::SLOT_BEGIN);
|
||||
|
||||
uint8 slots = inst->GetItem()->BagSlots;
|
||||
uint8 j;
|
||||
for (j = invbag::SLOT_BEGIN; j<slots; j++) {
|
||||
const uint8 slots = inst->GetItem()->BagSlots;
|
||||
for (uint8 j = invbag::SLOT_BEGIN; j < slots; j++) {
|
||||
if (!GetItem(base_slot_id + j)) {
|
||||
// Found available slot within bag
|
||||
return (base_slot_id + j);
|
||||
|
||||
@@ -132,7 +132,7 @@ namespace EQ
|
||||
|
||||
// Swap items in inventory
|
||||
enum SwapItemFailState : int8 { swapInvalid = -1, swapPass = 0, swapNotAllowed, swapNullData, swapRaceClass, swapDeity, swapLevel };
|
||||
bool SwapItem(int16 source_slot, int16 destination_slot, SwapItemFailState& fail_state, uint16 race_id = RACE_DOUG_0, uint8 class_id = Class::None, uint16 deity_id = deity::DeityType::DeityUnknown, uint8 level = 0);
|
||||
bool SwapItem(int16 source_slot, int16 destination_slot, SwapItemFailState& fail_state, uint16 race_id = Race::Doug, uint8 class_id = Class::None, uint16 deity_id = deity::DeityType::DeityUnknown, uint8 level = 0);
|
||||
|
||||
// Remove item from inventory
|
||||
bool DeleteItem(int16 slot_id, int16 quantity = 0);
|
||||
|
||||
@@ -1273,7 +1273,7 @@ int EQ::ItemInstance::GetItemBaneDamageBody(bool augments) const
|
||||
|
||||
int EQ::ItemInstance::GetItemBaneDamageRace(bool augments) const
|
||||
{
|
||||
int race = RACE_DOUG_0;
|
||||
int race = Race::Doug;
|
||||
const auto item = GetItem();
|
||||
if (item) {
|
||||
race = item->BaneDmgRace;
|
||||
|
||||
@@ -3868,8 +3868,8 @@ namespace RoF
|
||||
}
|
||||
|
||||
float SpawnSize = emu->size;
|
||||
if (!((emu->NPC == 0) || (emu->race <= RACE_GNOME_12) || (emu->race == RACE_IKSAR_128) ||
|
||||
(emu->race == RACE_VAH_SHIR_130) || (emu->race == RACE_FROGLOK_330) || (emu->race == RACE_DRAKKIN_522))
|
||||
if (!((emu->NPC == 0) || (emu->race <= Race::Gnome) || (emu->race == Race::Iksar) ||
|
||||
(emu->race == Race::VahShir) || (emu->race == Race::Froglok2) || (emu->race == Race::Drakkin))
|
||||
)
|
||||
{
|
||||
PacketSize += 60;
|
||||
@@ -4002,8 +4002,8 @@ namespace RoF
|
||||
VARSTRUCT_ENCODE_TYPE(uint32, Buffer, 0xffffffff); // unknown18
|
||||
VARSTRUCT_ENCODE_TYPE(uint32, Buffer, 0xffffffff); // unknown19
|
||||
|
||||
if ((emu->NPC == 0) || (emu->race <= RACE_GNOME_12) || (emu->race == RACE_IKSAR_128) ||
|
||||
(emu->race == RACE_VAH_SHIR_130) || (emu->race == RACE_FROGLOK_330) || (emu->race == RACE_DRAKKIN_522)
|
||||
if ((emu->NPC == 0) || (emu->race <= Race::Gnome) || (emu->race == Race::Iksar) ||
|
||||
(emu->race == Race::VahShir) || (emu->race == Race::Froglok2) || (emu->race == Race::Drakkin)
|
||||
)
|
||||
{
|
||||
for (k = EQ::textures::textureBegin; k < EQ::textures::materialCount; ++k)
|
||||
|
||||
@@ -4007,8 +4007,8 @@ namespace RoF2
|
||||
}
|
||||
|
||||
float SpawnSize = emu->size;
|
||||
if (!((emu->NPC == 0) || (emu->race <= RACE_GNOME_12) || (emu->race == RACE_IKSAR_128) ||
|
||||
(emu->race == RACE_VAH_SHIR_130) || (emu->race == RACE_FROGLOK_330) || (emu->race == RACE_DRAKKIN_522))
|
||||
if (!((emu->NPC == 0) || (emu->race <= Race::Gnome) || (emu->race == Race::Iksar) ||
|
||||
(emu->race == Race::VahShir) || (emu->race == Race::Froglok2) || (emu->race == Race::Drakkin))
|
||||
)
|
||||
{
|
||||
PacketSize += 60;
|
||||
@@ -4212,8 +4212,8 @@ namespace RoF2
|
||||
VARSTRUCT_ENCODE_TYPE(uint32, Buffer, 0xffffffff); // These do something with OP_WeaponEquip1
|
||||
VARSTRUCT_ENCODE_TYPE(uint32, Buffer, 0xffffffff); // ^
|
||||
|
||||
if ((emu->NPC == 0) || (emu->race <= RACE_GNOME_12) || (emu->race == RACE_IKSAR_128) ||
|
||||
(emu->race == RACE_VAH_SHIR_130) || (emu->race == RACE_FROGLOK_330) || (emu->race == RACE_DRAKKIN_522)
|
||||
if ((emu->NPC == 0) || (emu->race <= Race::Gnome) || (emu->race == Race::Iksar) ||
|
||||
(emu->race == Race::VahShir) || (emu->race == Race::Froglok2) || (emu->race == Race::Drakkin)
|
||||
)
|
||||
{
|
||||
for (k = EQ::textures::textureBegin; k < EQ::textures::materialCount; ++k)
|
||||
|
||||
@@ -2507,8 +2507,8 @@ namespace SoD
|
||||
}
|
||||
|
||||
float SpawnSize = emu->size;
|
||||
if (!((emu->NPC == 0) || (emu->race <= RACE_GNOME_12) || (emu->race == RACE_IKSAR_128) ||
|
||||
(emu->race == RACE_VAH_SHIR_130) || (emu->race == RACE_FROGLOK_330) || (emu->race == RACE_DRAKKIN_522))
|
||||
if (!((emu->NPC == 0) || (emu->race <= Race::Gnome) || (emu->race == Race::Iksar) ||
|
||||
(emu->race == Race::VahShir) || (emu->race == Race::Froglok2) || (emu->race == Race::Drakkin))
|
||||
)
|
||||
{
|
||||
PacketSize -= (sizeof(structs::Texture_Struct) * EQ::textures::materialCount);
|
||||
@@ -2706,8 +2706,8 @@ namespace SoD
|
||||
|
||||
Buffer += sizeof(structs::Spawn_Struct_Position);
|
||||
|
||||
if ((emu->NPC == 0) || (emu->race <= RACE_GNOME_12) || (emu->race == RACE_IKSAR_128) ||
|
||||
(emu->race == RACE_VAH_SHIR_130) || (emu->race == RACE_FROGLOK_330) || (emu->race == RACE_DRAKKIN_522)
|
||||
if ((emu->NPC == 0) || (emu->race <= Race::Gnome) || (emu->race == Race::Iksar) ||
|
||||
(emu->race == Race::VahShir) || (emu->race == Race::Froglok2) || (emu->race == Race::Drakkin)
|
||||
)
|
||||
{
|
||||
for (k = EQ::textures::textureBegin; k < EQ::textures::materialCount; ++k)
|
||||
@@ -2733,8 +2733,8 @@ namespace SoD
|
||||
}
|
||||
|
||||
|
||||
if ((emu->NPC == 0) || (emu->race <= RACE_GNOME_12) || (emu->race == RACE_IKSAR_128) ||
|
||||
(emu->race == RACE_VAH_SHIR_130) || (emu->race == RACE_FROGLOK_330) || (emu->race == RACE_DRAKKIN_522)
|
||||
if ((emu->NPC == 0) || (emu->race <= Race::Gnome) || (emu->race == Race::Iksar) ||
|
||||
(emu->race == Race::VahShir) || (emu->race == Race::Froglok2) || (emu->race == Race::Drakkin)
|
||||
)
|
||||
{
|
||||
structs::Texture_Struct *Equipment = (structs::Texture_Struct *)Buffer;
|
||||
|
||||
@@ -2779,8 +2779,8 @@ namespace UF
|
||||
}
|
||||
|
||||
float SpawnSize = emu->size;
|
||||
if (!((emu->NPC == 0) || (emu->race <= RACE_GNOME_12) || (emu->race == RACE_IKSAR_128) ||
|
||||
(emu->race == RACE_VAH_SHIR_130) || (emu->race == RACE_FROGLOK_330) || (emu->race == RACE_DRAKKIN_522))
|
||||
if (!((emu->NPC == 0) || (emu->race <= Race::Gnome) || (emu->race == Race::Iksar) ||
|
||||
(emu->race == Race::VahShir) || (emu->race == Race::Froglok2) || (emu->race == Race::Drakkin))
|
||||
)
|
||||
{
|
||||
PacketSize -= (sizeof(structs::Texture_Struct) * EQ::textures::materialCount);
|
||||
@@ -2982,8 +2982,8 @@ namespace UF
|
||||
|
||||
Buffer += sizeof(structs::Spawn_Struct_Position);
|
||||
|
||||
if ((emu->NPC == 0) || (emu->race <= RACE_GNOME_12) || (emu->race == RACE_IKSAR_128) ||
|
||||
(emu->race == RACE_VAH_SHIR_130) || (emu->race == RACE_FROGLOK_330) || (emu->race == RACE_DRAKKIN_522)
|
||||
if ((emu->NPC == 0) || (emu->race <= Race::Gnome) || (emu->race == Race::Iksar) ||
|
||||
(emu->race == Race::VahShir) || (emu->race == Race::Froglok2) || (emu->race == Race::Drakkin)
|
||||
)
|
||||
{
|
||||
for (k = EQ::textures::textureBegin; k < EQ::textures::materialCount; ++k)
|
||||
@@ -3018,8 +3018,8 @@ namespace UF
|
||||
VARSTRUCT_ENCODE_TYPE(uint32, Buffer, 0);
|
||||
}
|
||||
|
||||
if ((emu->NPC == 0) || (emu->race <= RACE_GNOME_12) || (emu->race == RACE_IKSAR_128) ||
|
||||
(emu->race == RACE_VAH_SHIR_130) || (emu->race == RACE_FROGLOK_330) || (emu->race == RACE_DRAKKIN_522)
|
||||
if ((emu->NPC == 0) || (emu->race <= Race::Gnome) || (emu->race == Race::Iksar) ||
|
||||
(emu->race == Race::VahShir) || (emu->race == Race::Froglok2) || (emu->race == Race::Drakkin)
|
||||
)
|
||||
{
|
||||
structs::Texture_Struct *Equipment = (structs::Texture_Struct *)Buffer;
|
||||
|
||||
+755
-755
File diff suppressed because it is too large
Load Diff
+739
-1471
File diff suppressed because it is too large
Load Diff
@@ -16,6 +16,7 @@
|
||||
#include "../../strings.h"
|
||||
#include <ctime>
|
||||
|
||||
|
||||
class BaseNpcEmotesRepository {
|
||||
public:
|
||||
struct NpcEmotes {
|
||||
@@ -120,8 +121,9 @@ public:
|
||||
{
|
||||
auto results = db.QueryDatabase(
|
||||
fmt::format(
|
||||
"{} WHERE id = {} LIMIT 1",
|
||||
"{} WHERE {} = {} LIMIT 1",
|
||||
BaseSelect(),
|
||||
PrimaryKey(),
|
||||
npc_emotes_id
|
||||
)
|
||||
);
|
||||
|
||||
@@ -6,7 +6,7 @@
|
||||
* Any modifications to base repositories are to be made by the generator only
|
||||
*
|
||||
* @generator ./utils/scripts/generators/repository-generator.pl
|
||||
* @docs https://eqemu.gitbook.io/server/in-development/developer-area/repositories
|
||||
* @docs https://docs.eqemu.io/developer/repositories
|
||||
*/
|
||||
|
||||
#ifndef EQEMU_BASE_{{TABLE_NAME_UPPER}}_REPOSITORY_H
|
||||
@@ -319,6 +319,62 @@ public:
|
||||
return (results.Success() && results.begin()[0] ? strtoll(results.begin()[0], nullptr, 10) : 0);
|
||||
}
|
||||
|
||||
static std::string BaseReplace()
|
||||
{
|
||||
return fmt::format(
|
||||
"REPLACE INTO {} ({}) ",
|
||||
TableName(),
|
||||
ColumnsRaw()
|
||||
);
|
||||
}
|
||||
|
||||
static int ReplaceOne(
|
||||
Database& db,
|
||||
const {{TABLE_NAME_STRUCT}} &e
|
||||
)
|
||||
{
|
||||
std::vector<std::string> v;
|
||||
|
||||
{{INSERT_ONE_ENTRIES}}
|
||||
|
||||
auto results = db.QueryDatabase(
|
||||
fmt::format(
|
||||
"{} VALUES ({})",
|
||||
BaseReplace(),
|
||||
Strings::Implode(",", v)
|
||||
)
|
||||
);
|
||||
|
||||
return (results.Success() ? results.RowsAffected() : 0);
|
||||
}
|
||||
|
||||
static int ReplaceMany(
|
||||
Database& db,
|
||||
const std::vector<{{TABLE_NAME_STRUCT}}> &entries
|
||||
)
|
||||
{
|
||||
std::vector<std::string> insert_chunks;
|
||||
|
||||
for (auto &e: entries) {
|
||||
std::vector<std::string> v;
|
||||
|
||||
{{INSERT_MANY_ENTRIES}}
|
||||
|
||||
insert_chunks.push_back("(" + Strings::Implode(",", v) + ")");
|
||||
}
|
||||
|
||||
std::vector<std::string> v;
|
||||
|
||||
auto results = db.QueryDatabase(
|
||||
fmt::format(
|
||||
"{} VALUES {}",
|
||||
BaseReplace(),
|
||||
Strings::Implode(",", insert_chunks)
|
||||
)
|
||||
);
|
||||
|
||||
return (results.Success() ? results.RowsAffected() : 0);
|
||||
}
|
||||
};
|
||||
|
||||
#endif //EQEMU_BASE_{{TABLE_NAME_UPPER}}_REPOSITORY_H
|
||||
|
||||
@@ -215,6 +215,7 @@ RULE_BOOL(Character, EnableRaidEXPModifier, true, "Enable or disable the raid ex
|
||||
RULE_BOOL(Character, EnableRaidMemberEXPModifier, true, "Enable or disable the raid experience modifier based on members in raid, default is true")
|
||||
RULE_BOOL(Character, LeaveCursorMoneyOnCorpse, false, "Enable or disable leaving cursor money on player corpses")
|
||||
RULE_BOOL(Character, ItemExtraSkillDamageCalcAsPercent, false, "If enabled, apply Item Extra Skill Damage as Percentage-based modifiers")
|
||||
RULE_BOOL(Character, UseForageCommonFood, true, "If enabled, use the common foods specified in the code.")
|
||||
RULE_CATEGORY_END()
|
||||
|
||||
RULE_CATEGORY(Mercs)
|
||||
|
||||
+1
-1
@@ -376,7 +376,7 @@ std::string EQ::SayLinkEngine::InjectSaylinksIfNotExist(const char *message)
|
||||
|
||||
void EQ::SayLinkEngine::LoadCachedSaylinks()
|
||||
{
|
||||
auto saylinks = SaylinkRepository::GetWhere(database, "phrase not REGEXP BINARY '[A-Z]' and phrase not REGEXP '[0-9]'");
|
||||
auto saylinks = SaylinkRepository::GetWhere(database, "phrase not REGEXP '[A-Z]' and phrase not REGEXP '[0-9]'");
|
||||
LogSaylink("Loaded [{}] saylinks into cache", saylinks.size());
|
||||
g_cached_saylinks = saylinks;
|
||||
}
|
||||
|
||||
+2
-2
@@ -25,7 +25,7 @@
|
||||
|
||||
// Build variables
|
||||
// these get injected during the build pipeline
|
||||
#define CURRENT_VERSION "22.37.0-dev" // always append -dev to the current version for custom-builds
|
||||
#define CURRENT_VERSION "22.38.0-dev" // always append -dev to the current version for custom-builds
|
||||
#define LOGIN_VERSION "0.8.0"
|
||||
#define COMPILE_DATE __DATE__
|
||||
#define COMPILE_TIME __TIME__
|
||||
@@ -42,7 +42,7 @@
|
||||
* Manifest: https://github.com/EQEmu/Server/blob/master/utils/sql/db_update_manifest.txt
|
||||
*/
|
||||
|
||||
#define CURRENT_BINARY_DATABASE_VERSION 9247
|
||||
#define CURRENT_BINARY_DATABASE_VERSION 9248
|
||||
|
||||
#define CURRENT_BINARY_BOTS_DATABASE_VERSION 9041
|
||||
|
||||
|
||||
+1
-1
@@ -1,6 +1,6 @@
|
||||
{
|
||||
"name": "eqemu-server",
|
||||
"version": "22.37.0",
|
||||
"version": "22.38.0",
|
||||
"repository": {
|
||||
"type": "git",
|
||||
"url": "https://github.com/EQEmu/Server.git"
|
||||
|
||||
@@ -0,0 +1,8 @@
|
||||
module constantconvert
|
||||
|
||||
go 1.18
|
||||
|
||||
require (
|
||||
github.com/gammazero/deque v0.2.0 // indirect
|
||||
github.com/gammazero/workerpool v1.1.3 // indirect
|
||||
)
|
||||
@@ -0,0 +1,4 @@
|
||||
github.com/gammazero/deque v0.2.0 h1:SkieyNB4bg2/uZZLxvya0Pq6diUlwx7m2TeT7GAIWaA=
|
||||
github.com/gammazero/deque v0.2.0/go.mod h1:LFroj8x4cMYCukHJDbxFCkT+r9AndaJnFMuZDV34tuU=
|
||||
github.com/gammazero/workerpool v1.1.3 h1:WixN4xzukFoN0XSeXF6puqEqFTl2mECI9S6W44HWy9Q=
|
||||
github.com/gammazero/workerpool v1.1.3/go.mod h1:wPjyBLDbyKnUn2XwwyD3EEwo9dHutia9/fwNmSHWACc=
|
||||
@@ -0,0 +1,313 @@
|
||||
package main
|
||||
|
||||
import (
|
||||
"fmt"
|
||||
"github.com/gammazero/workerpool"
|
||||
"io/fs"
|
||||
"log"
|
||||
"os"
|
||||
"os/exec"
|
||||
"path/filepath"
|
||||
"runtime"
|
||||
"strconv"
|
||||
"strings"
|
||||
)
|
||||
|
||||
func main() {
|
||||
loadDefinitions()
|
||||
|
||||
// get processor count
|
||||
wp := workerpool.New(runtime.NumCPU())
|
||||
|
||||
// loop through all files in current dir that are cpp files or h files
|
||||
err := filepath.WalkDir("../../", func(path string, d fs.DirEntry, err error) error {
|
||||
if d.IsDir() {
|
||||
return nil
|
||||
}
|
||||
|
||||
if !strings.Contains(path, ".cpp") && !strings.Contains(path, ".h") {
|
||||
return nil
|
||||
}
|
||||
|
||||
// if file ends with ".o" skip it
|
||||
if strings.HasSuffix(path, ".o") {
|
||||
return nil
|
||||
}
|
||||
|
||||
var ignoreFiles = []string{
|
||||
"submodules", "/libs", "utils/", "races.h", "backward", "database_update_manifest.cpp", "zonedb.h",
|
||||
}
|
||||
|
||||
ignore := false
|
||||
for _, ignoreString := range ignoreFiles {
|
||||
if strings.Contains(path, ignoreString) {
|
||||
ignore = true
|
||||
break
|
||||
}
|
||||
}
|
||||
if ignore {
|
||||
return nil
|
||||
}
|
||||
|
||||
wp.Submit(func() {
|
||||
|
||||
// open file for reading
|
||||
// get file contents
|
||||
contents, err := os.ReadFile(path)
|
||||
if err != nil {
|
||||
log.Fatalf("impossible to read file: %s", err)
|
||||
}
|
||||
|
||||
content := string(contents)
|
||||
|
||||
wroteChanges := false
|
||||
|
||||
var newLines []string
|
||||
for _, line := range strings.Split(content, "\n") {
|
||||
newLine := line
|
||||
|
||||
// loop through oldDefs and see if any of them are in contents
|
||||
for key, value := range oldDefs {
|
||||
// combine all of the above contains into a slice
|
||||
// loop through slice and if any of them are in line, continue
|
||||
var ignoreMatches = []string{
|
||||
"#define ", "MALE", "FEMALE", "_BIT", "LANG_",
|
||||
}
|
||||
|
||||
ignore := false
|
||||
for _, ignoreString := range ignoreMatches {
|
||||
if strings.Contains(newLine, ignoreString) && !strings.Contains(newLine, "NPC_") {
|
||||
ignore = true
|
||||
break
|
||||
}
|
||||
}
|
||||
if ignore {
|
||||
continue
|
||||
}
|
||||
|
||||
// below we hackishly use a series of specific string contains to avoid
|
||||
// making blind and wrong replacements
|
||||
// but hey - at least its 100% accurate :)
|
||||
if strings.Contains(line, "case "+key+":") {
|
||||
for key2, value2 := range newDefs {
|
||||
if value == value2 {
|
||||
newLine = strings.ReplaceAll(newLine, " "+key+":", " "+key2+":")
|
||||
wroteChanges = true
|
||||
break
|
||||
}
|
||||
}
|
||||
}
|
||||
if strings.Contains(line, "\t"+key) {
|
||||
for key2, value2 := range newDefs {
|
||||
if value == value2 {
|
||||
newLine = strings.ReplaceAll(newLine, "\t"+key, "\t"+key2)
|
||||
wroteChanges = true
|
||||
break
|
||||
}
|
||||
}
|
||||
}
|
||||
if strings.Contains(line, key+",") {
|
||||
for key2, value2 := range newDefs {
|
||||
if value == value2 {
|
||||
newLine = strings.ReplaceAll(newLine, key+",", key2+",")
|
||||
wroteChanges = true
|
||||
break
|
||||
}
|
||||
}
|
||||
}
|
||||
if strings.Contains(line, ", "+key) {
|
||||
for key2, value2 := range newDefs {
|
||||
if value == value2 {
|
||||
newLine = strings.ReplaceAll(newLine, ", "+key, ", "+key2)
|
||||
wroteChanges = true
|
||||
break
|
||||
}
|
||||
}
|
||||
}
|
||||
if strings.Contains(line, "= "+key+" ") {
|
||||
for key2, value2 := range newDefs {
|
||||
if value == value2 {
|
||||
newLine = strings.ReplaceAll(newLine, "= "+key+" ", "= "+key2+" ")
|
||||
wroteChanges = true
|
||||
break
|
||||
}
|
||||
}
|
||||
}
|
||||
if strings.Contains(line, "= "+key+")") {
|
||||
for key2, value2 := range newDefs {
|
||||
if value == value2 {
|
||||
newLine = strings.ReplaceAll(newLine, "= "+key+")", "= "+key2+")")
|
||||
wroteChanges = true
|
||||
break
|
||||
}
|
||||
}
|
||||
}
|
||||
if strings.Contains(line, "= "+key+";") {
|
||||
for key2, value2 := range newDefs {
|
||||
if value == value2 {
|
||||
newLine = strings.ReplaceAll(newLine, "= "+key+";", "= "+key2+";")
|
||||
wroteChanges = true
|
||||
break
|
||||
}
|
||||
}
|
||||
}
|
||||
if strings.Contains(line, "= "+key+" ||") {
|
||||
for key2, value2 := range newDefs {
|
||||
if value == value2 {
|
||||
newLine = strings.ReplaceAll(newLine, "= "+key+" ||", "= "+key2+" ||")
|
||||
wroteChanges = true
|
||||
break
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// match cases where our match is on the last line and last column
|
||||
// we need to be exact in the last column and not do a partial because we can
|
||||
// accidentally rename say OGRE to OGRE2 mistakenly
|
||||
if strings.Contains(line, key) {
|
||||
columns := strings.Split(line, " ")
|
||||
// get the last column
|
||||
lastColumn := strings.TrimSpace(columns[len(columns)-1])
|
||||
if lastColumn == key {
|
||||
for key2, value2 := range newDefs {
|
||||
if value == value2 {
|
||||
newLine = strings.ReplaceAll(newLine, lastColumn, key2)
|
||||
wroteChanges = true
|
||||
break
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
//if strings.Contains(line, "race == "+key) {
|
||||
// for key2, value2 := range newDefs {
|
||||
// if value == value2 {
|
||||
// newLine = strings.ReplaceAll(newLine, "race == "+key, "race == "+key2)
|
||||
// wroteChanges = true
|
||||
// break
|
||||
// }
|
||||
// }
|
||||
//}
|
||||
}
|
||||
|
||||
newLines = append(newLines, newLine)
|
||||
}
|
||||
|
||||
// write contents back to file
|
||||
if wroteChanges {
|
||||
fmt.Printf("wrote changes to file [%v]\n", path)
|
||||
err = os.WriteFile(path, []byte(strings.Join(newLines, "\n")), 0644)
|
||||
if err != nil {
|
||||
log.Fatalf("impossible to write file: %s", err)
|
||||
}
|
||||
}
|
||||
|
||||
return
|
||||
})
|
||||
return nil
|
||||
})
|
||||
if err != nil {
|
||||
log.Fatalf("impossible to walk directories: %s", err)
|
||||
}
|
||||
|
||||
wp.StopWait()
|
||||
}
|
||||
|
||||
var newDefs = make(map[string]int)
|
||||
var oldDefs = make(map[string]int)
|
||||
|
||||
func loadDefinitions() {
|
||||
// git show master:common/races.h
|
||||
cmd := exec.Command("git", "show", "master:common/races.h")
|
||||
out, err := cmd.Output()
|
||||
if err != nil {
|
||||
println(err.Error())
|
||||
return
|
||||
}
|
||||
|
||||
// load into a string -> int map
|
||||
for _, line := range strings.Split(string(out), "\n") {
|
||||
if strings.Contains(line, "#define ") {
|
||||
if len(strings.Split(line, " ")) <= 2 {
|
||||
continue
|
||||
}
|
||||
|
||||
// ignore
|
||||
// #define MALE 0
|
||||
// #define FEMALE 1
|
||||
// #define NEUTER 2
|
||||
if strings.Contains(line, "#define MALE") {
|
||||
continue
|
||||
}
|
||||
if strings.Contains(line, "#define FEMALE") {
|
||||
continue
|
||||
}
|
||||
if strings.Contains(line, "#define NEUTER") {
|
||||
continue
|
||||
}
|
||||
|
||||
// load "#define RACE_FLYING_CARPET_720 720" into map
|
||||
|
||||
key := strings.Split(line, " ")[1]
|
||||
value := strings.Split(line, " ")[2]
|
||||
value = strings.ReplaceAll(value, "//", "")
|
||||
value = strings.TrimSpace(value)
|
||||
//fmt.Printf("key [%v] value [%v]\n", key, value)
|
||||
|
||||
if !strings.HasPrefix(key, "RACE_") && !strings.HasPrefix(key, "RT_") {
|
||||
continue
|
||||
}
|
||||
|
||||
// convert value to int
|
||||
intValue, err := strconv.Atoi(value)
|
||||
if err != nil {
|
||||
println(err.Error())
|
||||
return
|
||||
}
|
||||
|
||||
oldDefs[key] = intValue
|
||||
|
||||
fmt.Printf("oldDefs key [%v] value [%v]\n", key, intValue)
|
||||
}
|
||||
}
|
||||
|
||||
// cleanup/races_cpp_h
|
||||
cmd = exec.Command("git", "show", "cleanup/races_cpp_h:common/races.h")
|
||||
out, err = cmd.Output()
|
||||
if err != nil {
|
||||
println(err.Error())
|
||||
return
|
||||
}
|
||||
|
||||
// load into a string -> int map
|
||||
for _, line := range strings.Split(string(out), "\n") {
|
||||
if strings.Contains(line, "constexpr uint16") {
|
||||
if len(strings.Split(line, " ")) <= 2 {
|
||||
continue
|
||||
}
|
||||
|
||||
// remove all extra spaces in between characters in line
|
||||
line = strings.Join(strings.Fields(line), " ")
|
||||
|
||||
// load " constexpr uint16 Doug = 0;" into map
|
||||
key := strings.Split(line, " ")[2]
|
||||
value := strings.Split(line, " ")[4]
|
||||
value = strings.ReplaceAll(value, "//", "")
|
||||
value = strings.ReplaceAll(value, ";", "")
|
||||
value = strings.TrimSpace(value)
|
||||
|
||||
// convert value to int
|
||||
intValue, err := strconv.Atoi(value)
|
||||
if err != nil {
|
||||
println(err.Error())
|
||||
return
|
||||
}
|
||||
|
||||
mapKey := "Race::" + key
|
||||
|
||||
newDefs[mapKey] = intValue
|
||||
|
||||
fmt.Printf("newDefs key [%v] value [%v]\n", mapKey, value)
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -10,7 +10,7 @@ require (
|
||||
require (
|
||||
github.com/golang/protobuf v1.3.2 // indirect
|
||||
github.com/google/go-querystring v1.1.0 // indirect
|
||||
golang.org/x/crypto v0.14.0 // indirect
|
||||
golang.org/x/crypto v0.17.0 // indirect
|
||||
golang.org/x/net v0.17.0 // indirect
|
||||
google.golang.org/appengine v1.6.7 // indirect
|
||||
)
|
||||
|
||||
@@ -10,8 +10,8 @@ github.com/google/go-querystring v1.1.0 h1:AnCroh3fv4ZBgVIf1Iwtovgjaw/GiKJo8M8yD
|
||||
github.com/google/go-querystring v1.1.0/go.mod h1:Kcdr2DB4koayq7X8pmAG4sNG59So17icRSOU623lUBU=
|
||||
golang.org/x/crypto v0.0.0-20190308221718-c2843e01d9a2/go.mod h1:djNgcEr1/C05ACkg1iLfiJU5Ep61QUkGW8qpdssI0+w=
|
||||
golang.org/x/crypto v0.0.0-20210817164053-32db794688a5/go.mod h1:GvvjBRRGRdwPK5ydBHafDWAxML/pGHZbMvKqRZ5+Abc=
|
||||
golang.org/x/crypto v0.14.0 h1:wBqGXzWJW6m1XrIKlAH0Hs1JJ7+9KBwnIO8v66Q9cHc=
|
||||
golang.org/x/crypto v0.14.0/go.mod h1:MVFd36DqK4CsrnJYDkBA3VC4m2GkXAM0PvzMCn4JQf4=
|
||||
golang.org/x/crypto v0.17.0 h1:r8bRNjWL3GshPW3gkd+RpvzWrZAwPS49OmTGZ/uhM4k=
|
||||
golang.org/x/crypto v0.17.0/go.mod h1:gCAAfMLgwOJRpTjQ2zCCt2OcSfYMTeZVSRtQlPC7Nq4=
|
||||
golang.org/x/net v0.0.0-20190603091049-60506f45cf65/go.mod h1:HSz+uSET+XFnRR8LxR5pz3Of3rY3CfYBVs4xY44aLks=
|
||||
golang.org/x/net v0.0.0-20210226172049-e18ecbb05110/go.mod h1:m0MpNAwzfU5UDzcl9v0D8zg8gWTRqZa9RBIspLL5mdg=
|
||||
golang.org/x/net v0.17.0 h1:pVaXccu2ozPjCXewfr1S7xza/zcXTity9cCdXQYSjIM=
|
||||
|
||||
File diff suppressed because it is too large
Load Diff
+4
-4
@@ -983,14 +983,14 @@ bool Mob::CombatRange(Mob* other, float fixed_size_mod, bool aeRampage, ExtraAtt
|
||||
float size_mod = GetSize();
|
||||
float other_size_mod = other->GetSize();
|
||||
|
||||
if (GetRace() == RACE_LAVA_DRAGON_49 || GetRace() == RACE_WURM_158 || GetRace() == RACE_GHOST_DRAGON_196) { //For races with a fixed size
|
||||
if (GetRace() == Race::LavaDragon || GetRace() == Race::Wurm || GetRace() == Race::GhostDragon) { //For races with a fixed size
|
||||
size_mod = 60.0f;
|
||||
}
|
||||
else if (size_mod < 6.0) {
|
||||
size_mod = 8.0f;
|
||||
}
|
||||
|
||||
if (other->GetRace() == RACE_LAVA_DRAGON_49 || other->GetRace() == RACE_WURM_158 || other->GetRace() == RACE_GHOST_DRAGON_196) { //For races with a fixed size
|
||||
if (other->GetRace() == Race::LavaDragon || other->GetRace() == Race::Wurm || other->GetRace() == Race::GhostDragon) { //For races with a fixed size
|
||||
other_size_mod = 60.0f;
|
||||
}
|
||||
else if (other_size_mod < 6.0) {
|
||||
@@ -1011,11 +1011,11 @@ bool Mob::CombatRange(Mob* other, float fixed_size_mod, bool aeRampage, ExtraAtt
|
||||
size_mod *= size_mod * 4;
|
||||
}
|
||||
|
||||
if (other->GetRace() == RACE_VELIOUS_DRAGON_184) // Lord Vyemm and other velious dragons
|
||||
if (other->GetRace() == Race::VeliousDragon) // Lord Vyemm and other velious dragons
|
||||
{
|
||||
size_mod *= 1.75;
|
||||
}
|
||||
if (other->GetRace() == RACE_DRAGON_SKELETON_122) // Dracoliche in Fear. Skeletal Dragon
|
||||
if (other->GetRace() == Race::DragonSkeleton) // Dracoliche in Fear. Skeletal Dragon
|
||||
{
|
||||
size_mod *= 2.25;
|
||||
}
|
||||
|
||||
+6
-6
@@ -1820,7 +1820,7 @@ bool Client::Death(Mob* killerMob, int64 damage, uint16 spell, EQ::skills::Skill
|
||||
|
||||
auto emote_id = killerMob->GetEmoteID();
|
||||
if (emote_id) {
|
||||
killerMob->CastToNPC()->DoNPCEmote(EQ::constants::EmoteEventTypes::KilledPC, emoteid);
|
||||
killerMob->CastToNPC()->DoNPCEmote(EQ::constants::EmoteEventTypes::KilledPC, emoteid, this);
|
||||
}
|
||||
|
||||
killerMob->TrySpellOnKill(killed_level, spell);
|
||||
@@ -2710,7 +2710,7 @@ bool NPC::Death(Mob* killer_mob, int64 damage, uint16 spell, EQ::skills::SkillTy
|
||||
if (IsNPC()) {
|
||||
auto emote_id = GetEmoteID();
|
||||
if (emote_id) {
|
||||
DoNPCEmote(EQ::constants::EmoteEventTypes::OnDeath, emoteid);
|
||||
DoNPCEmote(EQ::constants::EmoteEventTypes::OnDeath, emoteid, killer_mob);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -2721,7 +2721,7 @@ bool NPC::Death(Mob* killer_mob, int64 damage, uint16 spell, EQ::skills::SkillTy
|
||||
|
||||
auto emote_id = oos->GetEmoteID();
|
||||
if (emote_id) {
|
||||
oos->CastToNPC()->DoNPCEmote(EQ::constants::EmoteEventTypes::KilledNPC, emote_id);
|
||||
oos->CastToNPC()->DoNPCEmote(EQ::constants::EmoteEventTypes::KilledNPC, emote_id, this);
|
||||
}
|
||||
if (killer_mob) {
|
||||
killer_mob->TrySpellOnKill(killed_level, spell);
|
||||
@@ -2799,7 +2799,7 @@ bool NPC::Death(Mob* killer_mob, int64 damage, uint16 spell, EQ::skills::SkillTy
|
||||
ApplyIllusionToCorpse(illusion_spell_id, corpse);
|
||||
|
||||
if (killer != 0 && emoteid != 0)
|
||||
corpse->CastToNPC()->DoNPCEmote(EQ::constants::EmoteEventTypes::AfterDeath, emoteid);
|
||||
corpse->CastToNPC()->DoNPCEmote(EQ::constants::EmoteEventTypes::AfterDeath, emoteid, killer);
|
||||
if (killer != 0 && killer->IsClient()) {
|
||||
corpse->AllowPlayerLoot(killer, 0);
|
||||
if (killer->IsGrouped()) {
|
||||
@@ -4087,7 +4087,7 @@ void Mob::CommonDamage(Mob* attacker, int64 &damage, const uint16 spell_id, cons
|
||||
IsPlayerRace(GetBaseRace()) &&
|
||||
RuleI(Combat, FrontalStunImmunityRaces) & GetPlayerRaceBit(GetBaseRace())
|
||||
) ||
|
||||
GetBaseRace() == RACE_OGGOK_CITIZEN_93
|
||||
GetBaseRace() == Race::OggokCitizen
|
||||
) {
|
||||
is_immune_to_frontal_stun = true;
|
||||
}
|
||||
@@ -4107,7 +4107,7 @@ void Mob::CommonDamage(Mob* attacker, int64 &damage, const uint16 spell_id, cons
|
||||
IsPlayerRace(GetBaseRace()) &&
|
||||
RuleI(Combat, FrontalStunImmunityRaces) & GetPlayerRaceBit(GetBaseRace())
|
||||
) ||
|
||||
GetBaseRace() == RACE_OGGOK_CITIZEN_93
|
||||
GetBaseRace() == Race::OggokCitizen
|
||||
)
|
||||
) {
|
||||
is_immune_to_frontal_stun = true;
|
||||
|
||||
+4
-4
@@ -2681,7 +2681,7 @@ void Bot::CalcMeleeDistances(const Mob* tar, const EQ::ItemInstance* const& p_it
|
||||
float other_size_mod = tar->GetSize();
|
||||
|
||||
// For races with a fixed size
|
||||
if (GetRace() == RT_DRAGON || GetRace() == RT_WURM || GetRace() == RT_DRAGON_7) {
|
||||
if (GetRace() == Race::LavaDragon || GetRace() == Race::Wurm || GetRace() == Race::GhostDragon) {
|
||||
// size_mod = 60.0f;
|
||||
}
|
||||
|
||||
@@ -2690,7 +2690,7 @@ void Bot::CalcMeleeDistances(const Mob* tar, const EQ::ItemInstance* const& p_it
|
||||
}
|
||||
|
||||
// For races with a fixed size
|
||||
if (tar->GetRace() == RT_DRAGON || tar->GetRace() == RT_WURM || tar->GetRace() == RT_DRAGON_7) {
|
||||
if (tar->GetRace() == Race::LavaDragon || tar->GetRace() == Race::Wurm || tar->GetRace() == Race::GhostDragon) {
|
||||
other_size_mod = 60.0f;
|
||||
}
|
||||
|
||||
@@ -2902,12 +2902,12 @@ void Bot::AcquireBotTarget(Group* bot_group, Raid* raid, Client* leash_owner, fl
|
||||
}
|
||||
} else {
|
||||
// This will keep bots on target for now..but, future updates will allow for rooting/stunning
|
||||
if (auto escaping = hate_list.GetEscapingEntOnHateList(leash_owner, leash_distance)) {
|
||||
if (auto escaping = hate_list.GetEscapingMobOnHateList(leash_owner, leash_distance)) {
|
||||
SetTarget(escaping);
|
||||
}
|
||||
|
||||
if (!GetTarget()) {
|
||||
auto most_hate = hate_list.GetEntWithMostHateOnList(this, nullptr, true);
|
||||
auto most_hate = hate_list.GetMobWithMostHateOnList(this, nullptr, true);
|
||||
if (most_hate) {
|
||||
SetTarget(most_hate);
|
||||
}
|
||||
|
||||
+10
-10
@@ -5913,11 +5913,11 @@ void bot_command_view_combos(Client *c, const Seperator *sep)
|
||||
};
|
||||
|
||||
const uint16 race_values[17] = {
|
||||
RACE_DOUG_0,
|
||||
RACE_HUMAN_1, RACE_BARBARIAN_2, RACE_ERUDITE_3, RACE_WOOD_ELF_4,
|
||||
RACE_HIGH_ELF_5, RACE_DARK_ELF_6, RACE_HALF_ELF_7, RACE_DWARF_8,
|
||||
RACE_TROLL_9, RACE_OGRE_10, RACE_HALFLING_11, RACE_GNOME_12,
|
||||
RACE_IKSAR_128, RACE_VAH_SHIR_130, RACE_FROGLOK_330, RACE_DRAKKIN_522
|
||||
Race::Doug,
|
||||
Race::Human, Race::Barbarian, Race::Erudite, Race::WoodElf,
|
||||
Race::HighElf, Race::DarkElf, Race::HalfElf, Race::Dwarf,
|
||||
Race::Troll, Race::Ogre, Race::Halfling, Race::Gnome,
|
||||
Race::Iksar, Race::VahShir, Race::Froglok2, Race::Drakkin
|
||||
};
|
||||
|
||||
if (helper_command_alias_fail(c, "bot_command_view_combos", sep->arg[0], "viewcombos")) {
|
||||
@@ -6028,11 +6028,11 @@ void bot_subcommand_bot_create(Client *c, const Seperator *sep)
|
||||
};
|
||||
|
||||
const uint16 race_values[17] = {
|
||||
RACE_DOUG_0,
|
||||
RACE_HUMAN_1, RACE_BARBARIAN_2, RACE_ERUDITE_3, RACE_WOOD_ELF_4,
|
||||
RACE_HIGH_ELF_5, RACE_DARK_ELF_6, RACE_HALF_ELF_7, RACE_DWARF_8,
|
||||
RACE_TROLL_9, RACE_OGRE_10, RACE_HALFLING_11, RACE_GNOME_12,
|
||||
RACE_IKSAR_128, RACE_VAH_SHIR_130, RACE_FROGLOK_330, RACE_DRAKKIN_522
|
||||
Race::Doug,
|
||||
Race::Human, Race::Barbarian, Race::Erudite, Race::WoodElf,
|
||||
Race::HighElf, Race::DarkElf, Race::HalfElf, Race::Dwarf,
|
||||
Race::Troll, Race::Ogre, Race::Halfling, Race::Gnome,
|
||||
Race::Iksar, Race::VahShir, Race::Froglok2, Race::Drakkin
|
||||
};
|
||||
|
||||
const std::string gender_substrs[2] = {
|
||||
|
||||
+43
-43
@@ -6172,7 +6172,7 @@ void Client::CheckEmoteHail(NPC* n, const char* message)
|
||||
|
||||
const auto emote_id = n->GetEmoteID();
|
||||
if (emote_id) {
|
||||
n->DoNPCEmote(EQ::constants::EmoteEventTypes::Hailed, emote_id);
|
||||
n->DoNPCEmote(EQ::constants::EmoteEventTypes::Hailed, emote_id, this);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -8632,8 +8632,8 @@ void Client::InitInnates()
|
||||
m_pp.InnateSkills[InnateInspect] = InnateEnabled;
|
||||
m_pp.InnateSkills[InnateOpen] = InnateEnabled;
|
||||
|
||||
if (race >= RT_FROGLOK_3) {
|
||||
if (race == RT_SKELETON_2 || race == RT_FROGLOK_3) {
|
||||
if (race >= Race::Froglok2) {
|
||||
if (race == Race::Skeleton2 || race == Race::Froglok2) {
|
||||
m_pp.InnateSkills[InnateUltraVision] = InnateEnabled;
|
||||
} else {
|
||||
m_pp.InnateSkills[InnateInfravision] = InnateEnabled;
|
||||
@@ -8641,75 +8641,75 @@ void Client::InitInnates()
|
||||
}
|
||||
|
||||
switch (race) {
|
||||
case RT_BARBARIAN:
|
||||
case RT_BARBARIAN_2:
|
||||
case Race::Barbarian:
|
||||
case Race::HalasCitizen:
|
||||
m_pp.InnateSkills[InnateSlam] = InnateEnabled;
|
||||
break;
|
||||
case RT_ERUDITE:
|
||||
case RT_ERUDITE_2:
|
||||
case Race::Erudite:
|
||||
case Race::EruditeCitizen:
|
||||
m_pp.InnateSkills[InnateLore] = InnateEnabled;
|
||||
break;
|
||||
case RT_WOOD_ELF:
|
||||
case RT_GUARD_3:
|
||||
case Race::WoodElf:
|
||||
case Race::Fayguard:
|
||||
m_pp.InnateSkills[InnateInfravision] = InnateEnabled;
|
||||
break;
|
||||
case RT_GNOME:
|
||||
case RT_HIGH_ELF:
|
||||
case RT_GUARD_2:
|
||||
case Race::Gnome:
|
||||
case Race::HighElf:
|
||||
case Race::Felguard:
|
||||
m_pp.InnateSkills[InnateInfravision] = InnateEnabled;
|
||||
m_pp.InnateSkills[InnateLore] = InnateEnabled;
|
||||
break;
|
||||
case RT_TROLL:
|
||||
case RT_TROLL_2:
|
||||
case Race::Troll:
|
||||
case Race::GrobbCitizen:
|
||||
m_pp.InnateSkills[InnateRegen] = InnateEnabled;
|
||||
m_pp.InnateSkills[InnateSlam] = InnateEnabled;
|
||||
m_pp.InnateSkills[InnateInfravision] = InnateEnabled;
|
||||
break;
|
||||
case RT_DWARF:
|
||||
case RT_DWARF_2:
|
||||
case Race::Dwarf:
|
||||
case Race::KaladimCitizen:
|
||||
m_pp.InnateSkills[InnateInfravision] = InnateEnabled;
|
||||
break;
|
||||
case RT_OGRE:
|
||||
case RT_OGRE_2:
|
||||
case Race::Ogre:
|
||||
case Race::OggokCitizen:
|
||||
m_pp.InnateSkills[InnateInfravision] = InnateEnabled;
|
||||
m_pp.InnateSkills[InnateSlam] = InnateEnabled;
|
||||
m_pp.InnateSkills[InnateNoBash] = InnateEnabled;
|
||||
m_pp.InnateSkills[InnateBashDoor] = InnateEnabled;
|
||||
break;
|
||||
case RT_HALFLING:
|
||||
case RT_HALFLING_2:
|
||||
case Race::Halfling:
|
||||
case Race::RivervaleCitizen:
|
||||
m_pp.InnateSkills[InnateInfravision] = InnateEnabled;
|
||||
break;
|
||||
case RT_IKSAR:
|
||||
case Race::Iksar:
|
||||
m_pp.InnateSkills[InnateRegen] = InnateEnabled;
|
||||
m_pp.InnateSkills[InnateInfravision] = InnateEnabled;
|
||||
break;
|
||||
case RT_VAH_SHIR:
|
||||
case Race::VahShir:
|
||||
m_pp.InnateSkills[InnateInfravision] = InnateEnabled;
|
||||
break;
|
||||
case RT_DARK_ELF:
|
||||
case RT_DARK_ELF_2:
|
||||
case RT_VAMPIRE_2:
|
||||
case RT_FROGLOK_2:
|
||||
case RT_GHOST:
|
||||
case RT_GHOUL:
|
||||
case RT_SKELETON:
|
||||
case RT_VAMPIRE:
|
||||
case RT_WILL_O_WISP:
|
||||
case RT_ZOMBIE:
|
||||
case RT_SPECTRE:
|
||||
case RT_GHOST_2:
|
||||
case RT_GHOST_3:
|
||||
case RT_DRAGON_2:
|
||||
case RT_INNORUUK:
|
||||
case Race::DarkElf:
|
||||
case Race::NeriakCitizen:
|
||||
case Race::ElfVampire:
|
||||
case Race::FroglokGhoul:
|
||||
case Race::Ghost:
|
||||
case Race::Ghoul:
|
||||
case Race::Skeleton:
|
||||
case Race::Vampire:
|
||||
case Race::Wisp:
|
||||
case Race::Zombie:
|
||||
case Race::Spectre:
|
||||
case Race::DwarfGhost:
|
||||
case Race::EruditeGhost:
|
||||
case Race::DragonSkeleton:
|
||||
case Race::Innoruuk:
|
||||
m_pp.InnateSkills[InnateUltraVision] = InnateEnabled;
|
||||
break;
|
||||
case RT_HUMAN:
|
||||
case RT_GUARD:
|
||||
case RT_BEGGAR:
|
||||
case RT_HUMAN_2:
|
||||
case RT_HUMAN_3:
|
||||
case RT_FROGLOK_3: // client does froglok weird, but this should work out fine
|
||||
case Race::Human:
|
||||
case Race::FreeportGuard:
|
||||
case Race::HumanBeggar:
|
||||
case Race::HighpassCitizen:
|
||||
case Race::QeynosCitizen:
|
||||
case Race::Froglok2: // client does froglok weird, but this should work out fine
|
||||
break;
|
||||
default:
|
||||
m_pp.InnateSkills[InnateInfravision] = InnateEnabled;
|
||||
|
||||
@@ -982,6 +982,7 @@ public:
|
||||
void PutLootInInventory(int16 slot_id, const EQ::ItemInstance &inst, ServerLootItem_Struct** bag_item_data = 0);
|
||||
bool AutoPutLootInInventory(EQ::ItemInstance& inst, bool try_worn = false, bool try_cursor = true, ServerLootItem_Struct** bag_item_data = 0);
|
||||
bool SummonItem(uint32 item_id, int16 charges = -1, uint32 aug1 = 0, uint32 aug2 = 0, uint32 aug3 = 0, uint32 aug4 = 0, uint32 aug5 = 0, uint32 aug6 = 0, bool attuned = false, uint16 to_slot = EQ::invslot::slotCursor, uint32 ornament_icon = 0, uint32 ornament_idfile = 0, uint32 ornament_hero_model = 0);
|
||||
void SummonItemIntoInventory(uint32 item_id, int16 charges = -1, uint32 aug1 = 0, uint32 aug2 = 0, uint32 aug3 = 0, uint32 aug4 = 0, uint32 aug5 = 0, uint32 aug6 = 0, bool is_attuned = false);
|
||||
void SummonBaggedItems(uint32 bag_item_id, const std::vector<ServerLootItem_Struct>& bag_items);
|
||||
void SetStats(uint8 type,int16 set_val);
|
||||
void IncStats(uint8 type,int16 increase_val);
|
||||
|
||||
@@ -6287,6 +6287,7 @@ void Client::Handle_OP_EnvDamage(const EQApplicationPacket *app)
|
||||
|
||||
if (ed->dmgtype == EQ::constants::EnvironmentalDamage::Trap) {
|
||||
BreakInvisibleSpells();
|
||||
CancelSneakHide();
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
+2
-2
@@ -4920,7 +4920,7 @@ void EntityList::ZoneWho(Client *c, Who_All_Struct *Who)
|
||||
FormatMSGID = 5023; // 5023 %T1[ANONYMOUS] %2 %3 %4
|
||||
uint32 PlayerClass = Class::None;
|
||||
uint32 PlayerLevel = 0;
|
||||
uint32 PlayerRace = RACE_DOUG_0;
|
||||
uint32 PlayerRace = Race::Doug;
|
||||
uint32 ZoneMSGID = 0xFFFFFFFF;
|
||||
|
||||
if (ClientEntry->GetAnon()==0) {
|
||||
@@ -5750,7 +5750,7 @@ void EntityList::DespawnGridNodes(int32 grid_id) {
|
||||
Mob *mob = m.second;
|
||||
if (
|
||||
mob->IsNPC() &&
|
||||
mob->GetRace() == RACE_NODE_2254 &&
|
||||
mob->GetRace() == Race::Node &&
|
||||
mob->EntityVariableExists("grid_id") &&
|
||||
Strings::ToInt(mob->GetEntityVariable("grid_id")) == grid_id)
|
||||
{
|
||||
|
||||
+1
-1
@@ -456,7 +456,7 @@ void Client::ForageItem(bool guarantee) {
|
||||
}
|
||||
|
||||
//not an else in case theres no DB food
|
||||
if (foragedfood == 0) {
|
||||
if (foragedfood == 0 && RuleB(Character, UseForageCommonFood)) {
|
||||
uint8 index = 0;
|
||||
index = zone->random.Int(0, MAX_COMMON_FOOD_IDS-1);
|
||||
foragedfood = common_food_ids[index];
|
||||
|
||||
@@ -7,10 +7,7 @@ void FindEmote(Client *c, const Seperator *sep)
|
||||
if (sep->IsNumber(2)) {
|
||||
auto emote_id = Strings::ToUnsignedInt(sep->arg[2]);
|
||||
|
||||
LinkedListIterator<NPC_Emote_Struct *> iterator(zone->NPCEmoteList);
|
||||
iterator.Reset();
|
||||
while (iterator.MoreElements()) {
|
||||
auto &e = iterator.GetData();
|
||||
for (auto& e : zone->npc_emote_list) {
|
||||
if (emote_id == e->emoteid) {
|
||||
c->Message(
|
||||
Chat::White,
|
||||
@@ -40,7 +37,6 @@ void FindEmote(Client *c, const Seperator *sep)
|
||||
break;
|
||||
}
|
||||
|
||||
iterator.Advance();
|
||||
}
|
||||
|
||||
if (found_count == 50) {
|
||||
@@ -70,10 +66,7 @@ void FindEmote(Client *c, const Seperator *sep)
|
||||
|
||||
const std::string& search_criteria = sep->argplus[2];
|
||||
|
||||
LinkedListIterator<NPC_Emote_Struct *> iterator(zone->NPCEmoteList);
|
||||
iterator.Reset();
|
||||
while (iterator.MoreElements()) {
|
||||
auto &e = iterator.GetData();
|
||||
for (auto& e : zone->npc_emote_list) {
|
||||
|
||||
const std::string& current_text = Strings::ToLower(e->text);
|
||||
|
||||
@@ -106,7 +99,6 @@ void FindEmote(Client *c, const Seperator *sep)
|
||||
break;
|
||||
}
|
||||
|
||||
iterator.Advance();
|
||||
}
|
||||
|
||||
if (found_count == 50) {
|
||||
|
||||
@@ -5,7 +5,7 @@ void FindRace(Client *c, const Seperator *sep)
|
||||
if (sep->IsNumber(2)) {
|
||||
const auto race_id = static_cast<uint16>(Strings::ToUnsignedInt(sep->arg[2]));
|
||||
const std::string& race_name = GetRaceIDName(race_id);
|
||||
if (EQ::ValueWithin(race_id, RACE_HUMAN_1, RACE_PEGASUS_732)) {
|
||||
if (EQ::ValueWithin(race_id, Race::Human, Race::Pegasus3)) {
|
||||
c->Message(
|
||||
Chat::White,
|
||||
fmt::format(
|
||||
@@ -41,7 +41,7 @@ void FindRace(Client *c, const Seperator *sep)
|
||||
|
||||
auto found_count = 0;
|
||||
|
||||
for (uint16 race_id = RACE_HUMAN_1; race_id <= RACE_PEGASUS_732; race_id++) {
|
||||
for (uint16 race_id = Race::Human; race_id <= Race::Pegasus3; race_id++) {
|
||||
std::string race_name = GetRaceIDName(race_id);
|
||||
auto race_name_lower = Strings::ToLower(race_name);
|
||||
if (!Strings::Contains(race_name_lower, search_criteria)) {
|
||||
|
||||
@@ -23,7 +23,7 @@ void SetRace(Client *c, const Seperator *sep)
|
||||
const uint16 race_id = Strings::ToUnsignedInt(sep->arg[2]);
|
||||
|
||||
if (
|
||||
!EQ::ValueWithin(race_id, RACE_DOUG_0, RuleI(NPC, MaxRaceID)) &&
|
||||
!EQ::ValueWithin(race_id, Race::Doug, RuleI(NPC, MaxRaceID)) &&
|
||||
!EQ::ValueWithin(race_id, 2253, 2259)
|
||||
) {
|
||||
c->Message(
|
||||
|
||||
@@ -12,10 +12,7 @@ void ShowEmotes(Client *c, const Seperator *sep)
|
||||
uint32 emote_count = 0;
|
||||
const uint32 emote_id = t->GetEmoteID();
|
||||
|
||||
LinkedListIterator<NPC_Emote_Struct *> iterator(zone->NPCEmoteList);
|
||||
iterator.Reset();
|
||||
while (iterator.MoreElements()) {
|
||||
const auto& e = iterator.GetData();
|
||||
for (auto& e : zone->npc_emote_list) {
|
||||
if (emote_id == e->emoteid) {
|
||||
c->Message(
|
||||
Chat::White,
|
||||
@@ -41,7 +38,6 @@ void ShowEmotes(Client *c, const Seperator *sep)
|
||||
emote_count++;
|
||||
}
|
||||
|
||||
iterator.Advance();
|
||||
}
|
||||
|
||||
c->Message(
|
||||
|
||||
@@ -4,7 +4,7 @@ void ShowZonePoints(Client *c, const Seperator *sep)
|
||||
{
|
||||
for (const auto& m : entity_list.GetMobList()) {
|
||||
Mob* mob = m.second;
|
||||
if (mob->IsNPC() && mob->GetRace() == RACE_NODE_2254) {
|
||||
if (mob->IsNPC() && mob->GetRace() == Race::Node) {
|
||||
mob->Depop();
|
||||
}
|
||||
}
|
||||
|
||||
+126
-257
@@ -149,7 +149,7 @@ Mob* HateList::GetDamageTopOnHateList(Mob* hater)
|
||||
return current;
|
||||
}
|
||||
|
||||
Mob* HateList::GetClosestEntOnHateList(Mob *hater, bool skip_mezzed, EntityFilterType entity_type) {
|
||||
Mob* HateList::GetClosestEntOnHateList(Mob *hater, bool skip_mezzed, EntityFilterType filter_type) {
|
||||
Mob* close_entity = nullptr;
|
||||
float close_distance = 99999.9f;
|
||||
float this_distance;
|
||||
@@ -163,7 +163,7 @@ Mob* HateList::GetClosestEntOnHateList(Mob *hater, bool skip_mezzed, EntityFilte
|
||||
continue;
|
||||
}
|
||||
|
||||
switch (entity_type) {
|
||||
switch (filter_type) {
|
||||
case EntityFilterType::Bots:
|
||||
if (!e->entity_on_hatelist->IsBot()) {
|
||||
continue;
|
||||
@@ -344,191 +344,215 @@ int HateList::GetHateRatio(Mob *top, Mob *other)
|
||||
|
||||
// skip is used to ignore a certain mob on the list
|
||||
// Currently used for getting 2nd on list for aggro meter
|
||||
Mob *HateList::GetEntWithMostHateOnList(Mob *center, Mob *skip, bool skip_mezzed)
|
||||
Mob *HateList::GetMobWithMostHateOnList(
|
||||
Mob *center,
|
||||
Mob *skip,
|
||||
bool skip_mezzed,
|
||||
EntityFilterType filter_type
|
||||
)
|
||||
{
|
||||
// hack fix for zone shutdown crashes on some servers
|
||||
if (!zone->IsLoaded())
|
||||
if (!zone->IsLoaded()) { // hack fix for zone shutdown crashes on some servers
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
Mob* top_hate = nullptr;
|
||||
int64 hate = -1;
|
||||
Mob *top_hate = nullptr;
|
||||
int64 hate = -1;
|
||||
|
||||
if (center == nullptr)
|
||||
if (!center) {
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
if (RuleB(Aggro, SmartAggroList)){
|
||||
Mob* top_client_type_in_range = nullptr;
|
||||
if (RuleB(Aggro, SmartAggroList)) {
|
||||
Mob *top_client_type_in_range = nullptr;
|
||||
int64 hate_client_type_in_range = -1;
|
||||
int skipped_count = 0;
|
||||
int skipped_count = 0;
|
||||
|
||||
auto iterator = list.begin();
|
||||
while (iterator != list.end())
|
||||
{
|
||||
struct_HateList *cur = (*iterator);
|
||||
int16 aggro_mod = 0;
|
||||
while (iterator != list.end()) {
|
||||
struct_HateList *cur = (*iterator);
|
||||
int16 aggro_mod = 0;
|
||||
|
||||
if (!cur){
|
||||
if (!cur) {
|
||||
++iterator;
|
||||
continue;
|
||||
}
|
||||
|
||||
if (!cur->entity_on_hatelist){
|
||||
Mob *m = cur->entity_on_hatelist;
|
||||
|
||||
if (!m) {
|
||||
++iterator;
|
||||
continue;
|
||||
}
|
||||
|
||||
if (cur->entity_on_hatelist == skip) {
|
||||
if (m == skip) {
|
||||
++iterator;
|
||||
continue;
|
||||
}
|
||||
|
||||
if (skip_mezzed && cur->entity_on_hatelist->IsMezzed()) {
|
||||
if (skip_mezzed && m->IsMezzed()) {
|
||||
++iterator;
|
||||
continue;
|
||||
}
|
||||
|
||||
if (cur->entity_on_hatelist->Sanctuary()) {
|
||||
if (hate == -1)
|
||||
{
|
||||
top_hate = cur->entity_on_hatelist;
|
||||
hate = 1;
|
||||
if (
|
||||
(filter_type == EntityFilterType::Bots && !m->IsBot()) ||
|
||||
(filter_type == EntityFilterType::Clients && !m->IsClient()) ||
|
||||
(filter_type == EntityFilterType::NPCs && !m->IsNPC())
|
||||
) {
|
||||
++iterator;
|
||||
continue;
|
||||
}
|
||||
|
||||
if (m->Sanctuary()) {
|
||||
if (hate == -1) {
|
||||
top_hate = m;
|
||||
hate = 1;
|
||||
}
|
||||
|
||||
++iterator;
|
||||
continue;
|
||||
}
|
||||
|
||||
if (cur->entity_on_hatelist->DivineAura() || cur->entity_on_hatelist->IsMezzed() || cur->entity_on_hatelist->IsFeared()){
|
||||
if (hate == -1)
|
||||
{
|
||||
top_hate = cur->entity_on_hatelist;
|
||||
hate = 0;
|
||||
if (m->DivineAura() || m->IsMezzed() || m->IsFeared()) {
|
||||
if (hate == -1) {
|
||||
top_hate = m;
|
||||
hate = 0;
|
||||
}
|
||||
|
||||
++iterator;
|
||||
continue;
|
||||
}
|
||||
|
||||
int64 current_hate = cur->stored_hate_amount;
|
||||
|
||||
if (cur->entity_on_hatelist->IsClient() || cur->entity_on_hatelist->IsBot()){
|
||||
if (cur->entity_on_hatelist->IsClient() && cur->entity_on_hatelist->CastToClient()->IsSitting()){
|
||||
if (m->IsOfClientBot()) {
|
||||
if (m->IsClient() && m->CastToClient()->IsSitting()) {
|
||||
aggro_mod += RuleI(Aggro, SittingAggroMod);
|
||||
}
|
||||
|
||||
if (center){
|
||||
if (center->GetTarget() == cur->entity_on_hatelist)
|
||||
if (center) {
|
||||
if (center->GetTarget() == m) {
|
||||
aggro_mod += RuleI(Aggro, CurrentTargetAggroMod);
|
||||
if (RuleI(Aggro, MeleeRangeAggroMod) != 0)
|
||||
{
|
||||
if (center->CombatRange(cur->entity_on_hatelist)){
|
||||
}
|
||||
|
||||
if (RuleI(Aggro, MeleeRangeAggroMod) != 0) {
|
||||
if (center->CombatRange(m)) {
|
||||
aggro_mod += RuleI(Aggro, MeleeRangeAggroMod);
|
||||
|
||||
if (current_hate > hate_client_type_in_range || cur->is_entity_frenzy){
|
||||
if (current_hate > hate_client_type_in_range || cur->is_entity_frenzy) {
|
||||
hate_client_type_in_range = current_hate;
|
||||
top_client_type_in_range = cur->entity_on_hatelist;
|
||||
top_client_type_in_range = m;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
else{
|
||||
if (center){
|
||||
if (center->GetTarget() == cur->entity_on_hatelist)
|
||||
} else {
|
||||
if (center) {
|
||||
if (center->GetTarget() == m) {
|
||||
aggro_mod += RuleI(Aggro, CurrentTargetAggroMod);
|
||||
if (RuleI(Aggro, MeleeRangeAggroMod) != 0)
|
||||
{
|
||||
if (center->CombatRange(cur->entity_on_hatelist)){
|
||||
}
|
||||
|
||||
if (RuleI(Aggro, MeleeRangeAggroMod) != 0) {
|
||||
if (center->CombatRange(m)) {
|
||||
aggro_mod += RuleI(Aggro, MeleeRangeAggroMod);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if (cur->entity_on_hatelist->GetMaxHP() != 0 && ((cur->entity_on_hatelist->GetHP() * 100 / cur->entity_on_hatelist->GetMaxHP()) < 20)){
|
||||
if (m->GetMaxHP() != 0 && ((m->GetHP() * 100 / m->GetMaxHP()) < 20)) {
|
||||
aggro_mod += RuleI(Aggro, CriticallyWoundedAggroMod);
|
||||
}
|
||||
|
||||
if (aggro_mod){
|
||||
if (aggro_mod) {
|
||||
current_hate += (current_hate * aggro_mod / 100);
|
||||
}
|
||||
|
||||
if (current_hate > hate || cur->is_entity_frenzy){
|
||||
hate = current_hate;
|
||||
top_hate = cur->entity_on_hatelist;
|
||||
if (current_hate > hate || cur->is_entity_frenzy) {
|
||||
hate = current_hate;
|
||||
top_hate = m;
|
||||
}
|
||||
|
||||
++iterator;
|
||||
}
|
||||
|
||||
if (top_client_type_in_range != nullptr && top_hate != nullptr) {
|
||||
bool isTopClientType = top_hate->IsClient();
|
||||
if (!isTopClientType) {
|
||||
if (top_client_type_in_range && top_hate) {
|
||||
bool is_top_client_type = top_hate->IsClient();
|
||||
if (!is_top_client_type) {
|
||||
if (top_hate->IsBot()) {
|
||||
isTopClientType = true;
|
||||
is_top_client_type = true;
|
||||
top_client_type_in_range = top_hate;
|
||||
}
|
||||
}
|
||||
|
||||
if (!isTopClientType) {
|
||||
if (!is_top_client_type) {
|
||||
if (top_hate->IsMerc()) {
|
||||
isTopClientType = true;
|
||||
is_top_client_type = true;
|
||||
top_client_type_in_range = top_hate;
|
||||
}
|
||||
}
|
||||
|
||||
if (!isTopClientType) {
|
||||
if (top_hate->GetSpecialAbility(ALLOW_TO_TANK)){
|
||||
isTopClientType = true;
|
||||
if (!is_top_client_type) {
|
||||
if (top_hate->GetSpecialAbility(ALLOW_TO_TANK)) {
|
||||
is_top_client_type = true;
|
||||
top_client_type_in_range = top_hate;
|
||||
}
|
||||
}
|
||||
|
||||
if (!isTopClientType)
|
||||
if (!is_top_client_type) {
|
||||
return top_client_type_in_range ? top_client_type_in_range : nullptr;
|
||||
}
|
||||
|
||||
return top_hate ? top_hate : nullptr;
|
||||
}
|
||||
else {
|
||||
if (top_hate == nullptr && skipped_count > 0) {
|
||||
} else {
|
||||
if (!top_hate && skipped_count > 0) {
|
||||
return center->GetTarget() ? center->GetTarget() : nullptr;
|
||||
}
|
||||
|
||||
return top_hate ? top_hate : nullptr;
|
||||
}
|
||||
}
|
||||
else{
|
||||
auto iterator = list.begin();
|
||||
int skipped_count = 0;
|
||||
while (iterator != list.end())
|
||||
{
|
||||
} else {
|
||||
auto iterator = list.begin();
|
||||
int skipped_count = 0;
|
||||
while (iterator != list.end()) {
|
||||
struct_HateList *cur = (*iterator);
|
||||
if (cur) {
|
||||
if (cur->entity_on_hatelist == skip) {
|
||||
Mob *m = cur->entity_on_hatelist;
|
||||
|
||||
if (!m) {
|
||||
++iterator;
|
||||
continue;
|
||||
}
|
||||
|
||||
if (skip_mezzed && cur->entity_on_hatelist->IsMezzed()) {
|
||||
if (m == skip) {
|
||||
++iterator;
|
||||
continue;
|
||||
}
|
||||
|
||||
if (cur->entity_on_hatelist != nullptr && ((cur->stored_hate_amount > hate) || cur->is_entity_frenzy))
|
||||
{
|
||||
top_hate = cur->entity_on_hatelist;
|
||||
hate = cur->stored_hate_amount;
|
||||
if (skip_mezzed && m->IsMezzed()) {
|
||||
++iterator;
|
||||
continue;
|
||||
}
|
||||
|
||||
if ((cur->stored_hate_amount > hate) || cur->is_entity_frenzy) {
|
||||
top_hate = m;
|
||||
hate = cur->stored_hate_amount;
|
||||
}
|
||||
}
|
||||
++iterator;
|
||||
}
|
||||
if (top_hate == nullptr && skipped_count > 0) {
|
||||
|
||||
if (!top_hate && skipped_count > 0) {
|
||||
return center->GetTarget() ? center->GetTarget() : nullptr;
|
||||
}
|
||||
|
||||
return top_hate ? top_hate : nullptr;
|
||||
}
|
||||
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
Mob *HateList::GetEntWithMostHateOnList(bool skip_mezzed){
|
||||
Mob *HateList::GetMobWithMostHateOnList(bool skip_mezzed){
|
||||
Mob* top = nullptr;
|
||||
int64 hate = -1;
|
||||
|
||||
@@ -539,7 +563,7 @@ Mob *HateList::GetEntWithMostHateOnList(bool skip_mezzed){
|
||||
|
||||
if (cur) {
|
||||
LogHateDetail(
|
||||
"Looping GetEntWithMostHateOnList1 [{}] cur [{}] hate [{}] calc [{}]",
|
||||
"Looping GetMobWithMostHateOnList1 [{}] cur [{}] hate [{}] calc [{}]",
|
||||
cur->entity_on_hatelist->GetMobDescription(),
|
||||
cur->stored_hate_amount,
|
||||
hate,
|
||||
@@ -549,7 +573,7 @@ Mob *HateList::GetEntWithMostHateOnList(bool skip_mezzed){
|
||||
if (cur->entity_on_hatelist != nullptr && (cur->stored_hate_amount > hate))
|
||||
{
|
||||
LogHateDetail(
|
||||
"Looping GetEntWithMostHateOnList2 [{}]",
|
||||
"Looping GetMobWithMostHateOnList2 [{}]",
|
||||
cur->entity_on_hatelist->GetMobDescription()
|
||||
);
|
||||
|
||||
@@ -565,53 +589,45 @@ Mob *HateList::GetEntWithMostHateOnList(bool skip_mezzed){
|
||||
}
|
||||
|
||||
|
||||
Mob *HateList::GetRandomEntOnHateList(bool skip_mezzed)
|
||||
Mob *HateList::GetRandomMobOnHateList(EntityFilterType filter_type)
|
||||
{
|
||||
int count = list.size();
|
||||
if (count <= 0) //If we don't have any entries it'll crash getting a random 0, -1 position.
|
||||
return nullptr;
|
||||
|
||||
if (count == 1) //No need to do all that extra work if we only have one hate entry
|
||||
{
|
||||
if (*list.begin() && (!skip_mezzed || !(*list.begin())->entity_on_hatelist->IsMezzed())) // Just in case tHateEntry is invalidated somehow...
|
||||
return (*list.begin())->entity_on_hatelist;
|
||||
const auto &l = GetFilteredHateList(filter_type);
|
||||
|
||||
int count = l.size();
|
||||
if (count <= 0) { // If we don't have any entries it'll crash getting a random 0, -1 position.
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
if (skip_mezzed) {
|
||||
|
||||
for (auto iter : list) {
|
||||
if (iter->entity_on_hatelist->IsMezzed()) {
|
||||
--count;
|
||||
if (count == 1) { // No need to do all that extra work if we only have one hate entry
|
||||
auto c = *l.begin();
|
||||
if (c) {
|
||||
Mob *m = c->entity_on_hatelist;
|
||||
if (!m) {
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
return m;
|
||||
}
|
||||
if (count <= 0) {
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
int random = zone->random.Int(0, count - 1);
|
||||
int counter = 0;
|
||||
auto r = l.begin();
|
||||
int random_index = rand() % count;
|
||||
|
||||
for (auto iter : list) {
|
||||
std::advance(r, random_index);
|
||||
|
||||
if (skip_mezzed && iter->entity_on_hatelist->IsMezzed()) {
|
||||
continue;
|
||||
}
|
||||
if (counter < random) {
|
||||
auto e = *r;
|
||||
|
||||
++counter;
|
||||
continue;
|
||||
}
|
||||
|
||||
return iter->entity_on_hatelist;
|
||||
Mob *m = e->entity_on_hatelist;
|
||||
if (m) {
|
||||
return m;
|
||||
}
|
||||
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
Mob *HateList::GetEscapingEntOnHateList(Mob *center, float range, bool first) {
|
||||
Mob *HateList::GetEscapingMobOnHateList(Mob *center, float range, bool first) {
|
||||
// function is still in design stage
|
||||
|
||||
if (!center)
|
||||
@@ -853,153 +869,6 @@ void HateList::RemoveStaleEntries(int time_ms, float dist)
|
||||
}
|
||||
}
|
||||
|
||||
Bot* HateList::GetRandomBotOnHateList(bool skip_mezzed)
|
||||
{
|
||||
int count = list.size();
|
||||
if (count <= 0) { //If we don't have any entries it'll crash getting a random 0, -1 position.
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
if (count == 1) { //No need to do all that extra work if we only have one hate entry
|
||||
if (*list.begin() && (*list.begin())->entity_on_hatelist->IsBot() && (!skip_mezzed || !(*list.begin())->entity_on_hatelist->IsMezzed())) {
|
||||
return (*list.begin())->entity_on_hatelist->CastToBot();
|
||||
}
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
if (skip_mezzed) {
|
||||
for (auto iter : list) {
|
||||
if (iter->entity_on_hatelist->IsMezzed()) {
|
||||
--count;
|
||||
}
|
||||
}
|
||||
|
||||
if (count <= 0) {
|
||||
return nullptr;
|
||||
}
|
||||
}
|
||||
|
||||
int random = zone->random.Int(0, count - 1);
|
||||
int counter = 0;
|
||||
|
||||
for (auto iter : list) {
|
||||
if (!iter->entity_on_hatelist->IsBot()) {
|
||||
continue;
|
||||
}
|
||||
|
||||
if (skip_mezzed && iter->entity_on_hatelist->IsMezzed()) {
|
||||
continue;
|
||||
}
|
||||
|
||||
if (counter < random) {
|
||||
++counter;
|
||||
continue;
|
||||
}
|
||||
|
||||
return iter->entity_on_hatelist->CastToBot();
|
||||
}
|
||||
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
Client* HateList::GetRandomClientOnHateList(bool skip_mezzed)
|
||||
{
|
||||
int count = list.size();
|
||||
if (count <= 0) { //If we don't have any entries it'll crash getting a random 0, -1 position.
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
if (count == 1) { //No need to do all that extra work if we only have one hate entry
|
||||
if (*list.begin() && (*list.begin())->entity_on_hatelist->IsClient() && (!skip_mezzed || !(*list.begin())->entity_on_hatelist->IsMezzed())) {
|
||||
return (*list.begin())->entity_on_hatelist->CastToClient();
|
||||
}
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
if (skip_mezzed) {
|
||||
for (auto iter : list) {
|
||||
if (iter->entity_on_hatelist->IsMezzed()) {
|
||||
--count;
|
||||
}
|
||||
}
|
||||
|
||||
if (count <= 0) {
|
||||
return nullptr;
|
||||
}
|
||||
}
|
||||
|
||||
int random = zone->random.Int(0, count - 1);
|
||||
int counter = 0;
|
||||
|
||||
for (auto iter : list) {
|
||||
if (!iter->entity_on_hatelist->IsClient()) {
|
||||
continue;
|
||||
}
|
||||
|
||||
if (skip_mezzed && iter->entity_on_hatelist->IsMezzed()) {
|
||||
continue;
|
||||
}
|
||||
|
||||
if (counter < random) {
|
||||
++counter;
|
||||
continue;
|
||||
}
|
||||
|
||||
return iter->entity_on_hatelist->CastToClient();
|
||||
}
|
||||
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
NPC* HateList::GetRandomNPCOnHateList(bool skip_mezzed)
|
||||
{
|
||||
int count = list.size();
|
||||
if (count <= 0) { //If we don't have any entries it'll crash getting a random 0, -1 position.
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
if (count == 1) { //No need to do all that extra work if we only have one hate entry
|
||||
if (*list.begin() && (*list.begin())->entity_on_hatelist->IsNPC() && (!skip_mezzed || !(*list.begin())->entity_on_hatelist->IsMezzed())) {
|
||||
return (*list.begin())->entity_on_hatelist->CastToNPC();
|
||||
}
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
if (skip_mezzed) {
|
||||
for (auto iter : list) {
|
||||
if (iter->entity_on_hatelist->IsMezzed()) {
|
||||
--count;
|
||||
}
|
||||
}
|
||||
|
||||
if (count <= 0) {
|
||||
return nullptr;
|
||||
}
|
||||
}
|
||||
|
||||
int random = zone->random.Int(0, count - 1);
|
||||
int counter = 0;
|
||||
|
||||
for (auto iter : list) {
|
||||
if (!iter->entity_on_hatelist->IsNPC()) {
|
||||
continue;
|
||||
}
|
||||
|
||||
if (skip_mezzed && iter->entity_on_hatelist->IsMezzed()) {
|
||||
continue;
|
||||
}
|
||||
|
||||
if (counter < random) {
|
||||
++counter;
|
||||
continue;
|
||||
}
|
||||
|
||||
return iter->entity_on_hatelist->CastToNPC();
|
||||
}
|
||||
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
void HateList::DamageHateList(int64 damage, uint32 distance, EntityFilterType filter_type, bool is_percentage)
|
||||
{
|
||||
if (damage <= 0) {
|
||||
|
||||
+5
-9
@@ -41,16 +41,12 @@ public:
|
||||
HateList();
|
||||
~HateList();
|
||||
|
||||
Mob *GetClosestEntOnHateList(Mob *hater, bool skip_mezzed = false, EntityFilterType entity_type = EntityFilterType::All);
|
||||
Mob *GetClosestEntOnHateList(Mob *hater, bool skip_mezzed = false, EntityFilterType filter_type = EntityFilterType::All);
|
||||
Mob *GetDamageTopOnHateList(Mob *hater); // didn't add 'skip_mezzed' due to calls being in ::Death()
|
||||
Mob *GetEntWithMostHateOnList(Mob *center, Mob *skip = nullptr, bool skip_mezzed = false);
|
||||
Mob *GetRandomEntOnHateList(bool skip_mezzed = false);
|
||||
Mob *GetEntWithMostHateOnList(bool skip_mezzed = false);
|
||||
Mob *GetEscapingEntOnHateList(Mob *center, float range = 0.0f, bool first = false);
|
||||
|
||||
Bot* GetRandomBotOnHateList(bool skip_mezzed = false);
|
||||
Client *GetRandomClientOnHateList(bool skip_mezzed = false);
|
||||
NPC *GetRandomNPCOnHateList(bool skip_mezzed = false);
|
||||
Mob *GetMobWithMostHateOnList(Mob *center, Mob *skip = nullptr, bool skip_mezzed = false, EntityFilterType filter_type = EntityFilterType::All);
|
||||
Mob *GetRandomMobOnHateList(EntityFilterType filter_type = EntityFilterType::All);
|
||||
Mob *GetMobWithMostHateOnList(bool skip_mezzed = false);
|
||||
Mob *GetEscapingMobOnHateList(Mob *center, float range = 0.0f, bool first = false);
|
||||
|
||||
bool IsEntOnHateList(Mob *mob);
|
||||
bool IsHateListEmpty();
|
||||
|
||||
@@ -4739,3 +4739,53 @@ bool Client::IsAugmentRestricted(uint8 item_type, uint32 augment_restriction)
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
void Client::SummonItemIntoInventory(
|
||||
uint32 item_id,
|
||||
int16 charges,
|
||||
uint32 aug1,
|
||||
uint32 aug2,
|
||||
uint32 aug3,
|
||||
uint32 aug4,
|
||||
uint32 aug5,
|
||||
uint32 aug6,
|
||||
bool is_attuned
|
||||
)
|
||||
{
|
||||
auto *inst = database.CreateItem(
|
||||
item_id,
|
||||
charges,
|
||||
aug1,
|
||||
aug2,
|
||||
aug3,
|
||||
aug4,
|
||||
aug5,
|
||||
aug6,
|
||||
is_attuned
|
||||
);
|
||||
|
||||
if (!inst) {
|
||||
return;
|
||||
}
|
||||
|
||||
const bool is_arrow = inst->GetItem()->ItemType == EQ::item::ItemTypeArrow;
|
||||
const int16 slot_id = m_inv.FindFreeSlot(
|
||||
inst->IsClassBag(),
|
||||
true,
|
||||
inst->GetItem()->Size,
|
||||
is_arrow
|
||||
);
|
||||
|
||||
SummonItem(
|
||||
item_id,
|
||||
charges,
|
||||
aug1,
|
||||
aug2,
|
||||
aug3,
|
||||
aug4,
|
||||
aug5,
|
||||
aug6,
|
||||
is_attuned,
|
||||
slot_id
|
||||
);
|
||||
}
|
||||
|
||||
@@ -3217,6 +3217,35 @@ void Lua_Client::RemoveRadiantCrystals(uint32 amount)
|
||||
self->RemoveRadiantCrystals(amount);
|
||||
}
|
||||
|
||||
void Lua_Client::SummonItemIntoInventory(luabind::object item_table) {
|
||||
Lua_Safe_Call_Void();
|
||||
if (luabind::type(item_table) != LUA_TTABLE) {
|
||||
return;
|
||||
}
|
||||
|
||||
const uint32 item_id = luabind::object_cast<uint32>(item_table["item_id"]);
|
||||
const int16 charges = luabind::object_cast<uint32>(item_table["charges"]);
|
||||
const uint32 augment_one = luabind::type(item_table["augment_one"]) != LUA_TNIL ? luabind::object_cast<uint32>(item_table["augment_one"]) : 0;
|
||||
const uint32 augment_two = luabind::type(item_table["augment_two"]) != LUA_TNIL ? luabind::object_cast<uint32>(item_table["augment_two"]) : 0;
|
||||
const uint32 augment_three = luabind::type(item_table["augment_three"]) != LUA_TNIL ? luabind::object_cast<uint32>(item_table["augment_three"]) : 0;
|
||||
const uint32 augment_four = luabind::type(item_table["augment_four"]) != LUA_TNIL ? luabind::object_cast<uint32>(item_table["augment_four"]) : 0;
|
||||
const uint32 augment_five = luabind::type(item_table["augment_five"]) != LUA_TNIL ? luabind::object_cast<uint32>(item_table["augment_five"]) : 0;
|
||||
const uint32 augment_six = luabind::type(item_table["augment_six"]) != LUA_TNIL ? luabind::object_cast<uint32>(item_table["augment_six"]) : 0;
|
||||
const bool attuned = luabind::type(item_table["attuned"]) != LUA_TNIL ? luabind::object_cast<bool>(item_table["attuned"]) : false;
|
||||
|
||||
self->SummonItemIntoInventory(
|
||||
item_id,
|
||||
charges,
|
||||
augment_one,
|
||||
augment_two,
|
||||
augment_three,
|
||||
augment_four,
|
||||
augment_five,
|
||||
augment_six,
|
||||
attuned
|
||||
);
|
||||
}
|
||||
|
||||
luabind::scope lua_register_client() {
|
||||
return luabind::class_<Lua_Client, Lua_Mob>("Client")
|
||||
.def(luabind::constructor<>())
|
||||
@@ -3723,6 +3752,7 @@ luabind::scope lua_register_client() {
|
||||
.def("SummonItem", (void(Lua_Client::*)(uint32,int,uint32,uint32,uint32,uint32,uint32))&Lua_Client::SummonItem)
|
||||
.def("SummonItem", (void(Lua_Client::*)(uint32,int,uint32,uint32,uint32,uint32,uint32,bool))&Lua_Client::SummonItem)
|
||||
.def("SummonItem", (void(Lua_Client::*)(uint32,int,uint32,uint32,uint32,uint32,uint32,bool,int))&Lua_Client::SummonItem)
|
||||
.def("SummonItemIntoInventory", (void(Lua_Client::*)(luabind::adl::object))&Lua_Client::SummonItemIntoInventory)
|
||||
.def("TGB", (bool(Lua_Client::*)(void))&Lua_Client::TGB)
|
||||
.def("TakeMoneyFromPP", (bool(Lua_Client::*)(uint64))&Lua_Client::TakeMoneyFromPP)
|
||||
.def("TakeMoneyFromPP", (bool(Lua_Client::*)(uint64,bool))&Lua_Client::TakeMoneyFromPP)
|
||||
|
||||
@@ -486,6 +486,7 @@ public:
|
||||
void AddRadiantCrystals(uint32 amount);
|
||||
void RemoveEbonCrystals(uint32 amount);
|
||||
void RemoveRadiantCrystals(uint32 amount);
|
||||
void SummonItemIntoInventory(luabind::object item_table);
|
||||
|
||||
void ApplySpell(int spell_id);
|
||||
void ApplySpell(int spell_id, int duration);
|
||||
|
||||
@@ -1015,6 +1015,21 @@ Lua_Mob Lua_Mob::GetHateTop() {
|
||||
return Lua_Mob(self->GetHateTop());
|
||||
}
|
||||
|
||||
Lua_Bot Lua_Mob::GetHateTopBot() {
|
||||
Lua_Safe_Call_Class(Lua_Bot);
|
||||
return Lua_Bot(self->GetHateTopBot());
|
||||
}
|
||||
|
||||
Lua_Client Lua_Mob::GetHateTopClient() {
|
||||
Lua_Safe_Call_Class(Lua_Client);
|
||||
return Lua_Client(self->GetHateTopClient());
|
||||
}
|
||||
|
||||
Lua_NPC Lua_Mob::GetHateTopNPC() {
|
||||
Lua_Safe_Call_Class(Lua_NPC);
|
||||
return Lua_NPC(self->GetHateTopNPC());
|
||||
}
|
||||
|
||||
Lua_Mob Lua_Mob::GetHateDamageTop(Lua_Mob other) {
|
||||
Lua_Safe_Call_Class(Lua_Mob);
|
||||
return Lua_Mob(self->GetHateDamageTop(other));
|
||||
@@ -3456,6 +3471,9 @@ luabind::scope lua_register_mob() {
|
||||
.def("GetHateRandomClient", (Lua_Client(Lua_Mob::*)(void))&Lua_Mob::GetHateRandomClient)
|
||||
.def("GetHateRandomNPC", (Lua_NPC(Lua_Mob::*)(void))&Lua_Mob::GetHateRandomNPC)
|
||||
.def("GetHateTop", (Lua_Mob(Lua_Mob::*)(void))&Lua_Mob::GetHateTop)
|
||||
.def("GetHateTopBot", (Lua_Bot(Lua_Mob::*)(void))&Lua_Mob::GetHateTopBot)
|
||||
.def("GetHateTopClient", (Lua_Client(Lua_Mob::*)(void))&Lua_Mob::GetHateTopClient)
|
||||
.def("GetHateTopNPC", (Lua_NPC(Lua_Mob::*)(void))&Lua_Mob::GetHateTopNPC)
|
||||
.def("GetHeading", &Lua_Mob::GetHeading)
|
||||
.def("GetHelmTexture", &Lua_Mob::GetHelmTexture)
|
||||
.def("GetHerosForgeModel", (int32(Lua_Mob::*)(uint8))&Lua_Mob::GetHerosForgeModel)
|
||||
|
||||
@@ -225,6 +225,9 @@ public:
|
||||
Lua_HateList GetHateListByDistance();
|
||||
Lua_HateList GetHateListByDistance(uint32 distance);
|
||||
Lua_Mob GetHateTop();
|
||||
Lua_Bot GetHateTopBot();
|
||||
Lua_Client GetHateTopClient();
|
||||
Lua_NPC GetHateTopNPC();
|
||||
Lua_Mob GetHateDamageTop(Lua_Mob other);
|
||||
Lua_Mob GetHateRandom();
|
||||
Lua_Bot GetHateRandomBot();
|
||||
|
||||
+2
-2
@@ -3933,14 +3933,14 @@ float Merc::GetMaxMeleeRangeToTarget(Mob* target) {
|
||||
float size_mod = GetSize();
|
||||
float other_size_mod = target->GetSize();
|
||||
|
||||
if (GetRace() == RACE_LAVA_DRAGON_49 || GetRace() == RACE_WURM_158 || GetRace() == RACE_GHOST_DRAGON_196) //For races with a fixed size
|
||||
if (GetRace() == Race::LavaDragon || GetRace() == Race::Wurm || GetRace() == Race::GhostDragon) //For races with a fixed size
|
||||
{
|
||||
size_mod = 60.0f;
|
||||
} else if (size_mod < 6.0) {
|
||||
size_mod = 8.0f;
|
||||
}
|
||||
|
||||
if (target->GetRace() == RACE_LAVA_DRAGON_49 || target->GetRace() == RACE_WURM_158 || target->GetRace() == RACE_GHOST_DRAGON_196) //For races with a fixed size
|
||||
if (target->GetRace() == Race::LavaDragon || target->GetRace() == Race::Wurm || target->GetRace() == Race::GhostDragon) //For races with a fixed size
|
||||
{
|
||||
other_size_mod = 60.0f;
|
||||
} else if (other_size_mod < 6.0) {
|
||||
|
||||
+96
-96
@@ -2867,7 +2867,7 @@ void Mob::ShowStats(Client* c)
|
||||
);
|
||||
|
||||
// Drakkin Features
|
||||
if (t->GetRace() == RACE_DRAKKIN_522) {
|
||||
if (t->GetRace() == Race::Drakkin) {
|
||||
c->Message(
|
||||
Chat::White,
|
||||
fmt::format(
|
||||
@@ -3526,7 +3526,7 @@ void Mob::GMMove(const glm::vec4 &position, bool save_guard_spot) {
|
||||
void Mob::SendIllusionPacket(const AppearanceStruct& a)
|
||||
{
|
||||
uint16 new_race = (
|
||||
a.race_id != RACE_DOUG_0 ?
|
||||
a.race_id != Race::Doug ?
|
||||
a.race_id :
|
||||
(use_model ? use_model : GetBaseRace())
|
||||
);
|
||||
@@ -3558,7 +3558,7 @@ void Mob::SendIllusionPacket(const AppearanceStruct& a)
|
||||
uint32 new_drakkin_tattoo = a.drakkin_tattoo == UINT32_MAX ? GetDrakkinTattoo() : a.drakkin_tattoo;
|
||||
|
||||
// Reset features to Base from the Player Profile
|
||||
if (IsClient() && a.race_id == RACE_DOUG_0) {
|
||||
if (IsClient() && a.race_id == Race::Doug) {
|
||||
new_beard = CastToClient()->GetBaseBeard();
|
||||
new_beard_color = CastToClient()->GetBaseBeardColor();
|
||||
new_drakkin_details = CastToClient()->GetBaseDetails();
|
||||
@@ -3918,48 +3918,48 @@ uint16 Mob::GetFactionRace() {
|
||||
uint8 Mob::GetDefaultGender(uint16 in_race, uint8 in_gender) {
|
||||
if (
|
||||
IsPlayerRace(in_race) ||
|
||||
in_race == RACE_BROWNIE_15 ||
|
||||
in_race == RACE_KERRAN_23 ||
|
||||
in_race == RACE_LION_50 ||
|
||||
in_race == RACE_DRACNID_57 ||
|
||||
in_race == RACE_ZOMBIE_70 ||
|
||||
in_race == RACE_QEYNOS_CITIZEN_71 ||
|
||||
in_race == RACE_RIVERVALE_CITIZEN_81 ||
|
||||
in_race == RACE_HALAS_CITIZEN_90 ||
|
||||
in_race == RACE_GROBB_CITIZEN_92 ||
|
||||
in_race == RACE_OGGOK_CITIZEN_93 ||
|
||||
in_race == RACE_KALADIM_CITIZEN_94 ||
|
||||
in_race == RACE_ELF_VAMPIRE_98 ||
|
||||
in_race == RACE_FELGUARD_106 ||
|
||||
in_race == RACE_FAYGUARD_112 ||
|
||||
in_race == RACE_ERUDITE_GHOST_118 ||
|
||||
in_race == RACE_IKSAR_CITIZEN_139 ||
|
||||
in_race == RACE_SHADE_224 ||
|
||||
in_race == RACE_TROLL_CREW_MEMBER_331 ||
|
||||
in_race == RACE_PIRATE_DECKHAND_332 ||
|
||||
in_race == RACE_GNOME_PIRATE_338 ||
|
||||
in_race == RACE_DARK_ELF_PIRATE_339 ||
|
||||
in_race == RACE_OGRE_PIRATE_340 ||
|
||||
in_race == RACE_HUMAN_PIRATE_341 ||
|
||||
in_race == RACE_ERUDITE_PIRATE_342 ||
|
||||
in_race == RACE_UNDEAD_PIRATE_344 ||
|
||||
in_race == RACE_KNIGHT_OF_HATE_351 ||
|
||||
in_race == RACE_WARLOCK_OF_HATE_352 ||
|
||||
in_race == RACE_UNDEAD_VAMPIRE_359 ||
|
||||
in_race == RACE_VAMPIRE_360 ||
|
||||
in_race == RACE_SAND_ELF_364 ||
|
||||
in_race == RACE_TAELOSIAN_NATIVE_385 ||
|
||||
in_race == RACE_TAELOSIAN_EVOKER_386 ||
|
||||
in_race == RACE_DRACHNID_461 ||
|
||||
in_race == RACE_ZOMBIE_471 ||
|
||||
in_race == RACE_ELDDAR_489 ||
|
||||
in_race == RACE_VAMPIRE_497 ||
|
||||
in_race == RACE_KERRAN_562 ||
|
||||
in_race == RACE_BROWNIE_568 ||
|
||||
in_race == RACE_HUMAN_566 ||
|
||||
in_race == RACE_ELVEN_GHOST_587 ||
|
||||
in_race == RACE_HUMAN_GHOST_588 ||
|
||||
in_race == RACE_COLDAIN_645
|
||||
in_race == Race::Brownie ||
|
||||
in_race == Race::Kerran ||
|
||||
in_race == Race::Lion ||
|
||||
in_race == Race::Drachnid ||
|
||||
in_race == Race::Zombie ||
|
||||
in_race == Race::QeynosCitizen ||
|
||||
in_race == Race::RivervaleCitizen ||
|
||||
in_race == Race::HalasCitizen ||
|
||||
in_race == Race::GrobbCitizen ||
|
||||
in_race == Race::OggokCitizen ||
|
||||
in_race == Race::KaladimCitizen ||
|
||||
in_race == Race::ElfVampire ||
|
||||
in_race == Race::Felguard ||
|
||||
in_race == Race::Fayguard ||
|
||||
in_race == Race::EruditeGhost ||
|
||||
in_race == Race::IksarCitizen ||
|
||||
in_race == Race::Shade ||
|
||||
in_race == Race::TrollCrewMember ||
|
||||
in_race == Race::PirateDeckhand ||
|
||||
in_race == Race::GnomePirate ||
|
||||
in_race == Race::DarkElfPirate ||
|
||||
in_race == Race::OgrePirate ||
|
||||
in_race == Race::HumanPirate ||
|
||||
in_race == Race::EruditePirate ||
|
||||
in_race == Race::TrollZombie ||
|
||||
in_race == Race::KnightOfHate ||
|
||||
in_race == Race::ArcanistOfHate ||
|
||||
in_race == Race::UndeadVampire ||
|
||||
in_race == Race::Vampire3 ||
|
||||
in_race == Race::SandElf ||
|
||||
in_race == Race::Nihil ||
|
||||
in_race == Race::Trusik ||
|
||||
in_race == Race::Drachnid2 ||
|
||||
in_race == Race::Zombie2 ||
|
||||
in_race == Race::Elddar ||
|
||||
in_race == Race::Vampire4 ||
|
||||
in_race == Race::Kerran2 ||
|
||||
in_race == Race::Brownie2 ||
|
||||
in_race == Race::Human2 ||
|
||||
in_race == Race::ElvenGhost ||
|
||||
in_race == Race::HumanGhost ||
|
||||
in_race == Race::Coldain2
|
||||
) {
|
||||
if (in_gender >= 2) { // Male default for PC Races
|
||||
return 0;
|
||||
@@ -3967,33 +3967,33 @@ uint8 Mob::GetDefaultGender(uint16 in_race, uint8 in_gender) {
|
||||
return in_gender;
|
||||
}
|
||||
} else if (
|
||||
in_race == RACE_FREEPORT_GUARD_44 ||
|
||||
in_race == RACE_MIMIC_52 ||
|
||||
in_race == RACE_HUMAN_BEGGAR_55 ||
|
||||
in_race == RACE_VAMPIRE_65 ||
|
||||
in_race == RACE_HIGHPASS_CITIZEN_67 ||
|
||||
in_race == RACE_NERIAK_CITIZEN_77 ||
|
||||
in_race == RACE_ERUDITE_CITIZEN_78 ||
|
||||
in_race == RACE_CLOCKWORK_GNOME_88 ||
|
||||
in_race == RACE_DWARF_GHOST_117 ||
|
||||
in_race == RACE_SPECTRAL_IKSAR_147 ||
|
||||
in_race == RACE_INVISIBLE_MAN_127 ||
|
||||
in_race == RACE_VAMPYRE_208 ||
|
||||
in_race == RACE_RECUSO_237 ||
|
||||
in_race == RACE_BROKEN_SKULL_PIRATE_333 ||
|
||||
in_race == RACE_INVISIBLE_MAN_OF_ZOMM_600 ||
|
||||
in_race == RACE_OGRE_NPC_MALE_624 ||
|
||||
in_race == RACE_BEEFEATER_667 ||
|
||||
in_race == RACE_ERUDITE_678
|
||||
in_race == Race::FreeportGuard ||
|
||||
in_race == Race::Mimic ||
|
||||
in_race == Race::HumanBeggar ||
|
||||
in_race == Race::Vampire ||
|
||||
in_race == Race::HighpassCitizen ||
|
||||
in_race == Race::NeriakCitizen ||
|
||||
in_race == Race::EruditeCitizen ||
|
||||
in_race == Race::ClockworkGnome ||
|
||||
in_race == Race::DwarfGhost ||
|
||||
in_race == Race::IksarSpirit ||
|
||||
in_race == Race::InvisibleMan ||
|
||||
in_race == Race::Vampire2 ||
|
||||
in_race == Race::Recuso ||
|
||||
in_race == Race::BrokenSkullPirate ||
|
||||
in_race == Race::InvisibleManOfZomm ||
|
||||
in_race == Race::Ogre2 ||
|
||||
in_race == Race::RoyalGuard ||
|
||||
in_race == Race::Erudite2
|
||||
) { // Male only races
|
||||
return 0;
|
||||
} else if (
|
||||
in_race == RACE_FAIRY_25 ||
|
||||
in_race == RACE_PIXIE_56 ||
|
||||
in_race == RACE_BANSHEE_487 ||
|
||||
in_race == RACE_BANSHEE_488 ||
|
||||
in_race == RACE_AYONAE_RO_498 ||
|
||||
in_race == RACE_SULLON_ZEK_499
|
||||
in_race == Race::Fairy ||
|
||||
in_race == Race::Pixie ||
|
||||
in_race == Race::Banshee2 ||
|
||||
in_race == Race::Banshee3 ||
|
||||
in_race == Race::AyonaeRo ||
|
||||
in_race == Race::SullonZek
|
||||
) { // Female only races
|
||||
return 1;
|
||||
} else { // Neutral default for NPC Races
|
||||
@@ -4883,7 +4883,7 @@ bool Mob::RemoveFromHateList(Mob* mob)
|
||||
}
|
||||
if(GetTarget() == mob)
|
||||
{
|
||||
SetTarget(hate_list.GetEntWithMostHateOnList(this));
|
||||
SetTarget(hate_list.GetMobWithMostHateOnList(this));
|
||||
}
|
||||
|
||||
return bFound;
|
||||
@@ -6867,22 +6867,22 @@ void Mob::RemoveAllNimbusEffects()
|
||||
bool Mob::IsBoat() const {
|
||||
|
||||
return (
|
||||
race == RACE_SHIP_72 ||
|
||||
race == RACE_LAUNCH_73 ||
|
||||
race == RACE_GHOST_SHIP_114 ||
|
||||
race == RACE_SHIP_404 ||
|
||||
race == RACE_MERCHANT_SHIP_550 ||
|
||||
race == RACE_PIRATE_SHIP_551 ||
|
||||
race == RACE_GHOST_SHIP_552 ||
|
||||
race == RACE_BOAT_533
|
||||
race == Race::Ship ||
|
||||
race == Race::Launch ||
|
||||
race == Race::GhostShip ||
|
||||
race == Race::DiscordShip ||
|
||||
race == Race::MerchantShip ||
|
||||
race == Race::PirateShip ||
|
||||
race == Race::GhostShip2 ||
|
||||
race == Race::Boat2
|
||||
);
|
||||
}
|
||||
|
||||
bool Mob::IsControllableBoat() const {
|
||||
|
||||
return (
|
||||
race == RACE_BOAT_141 ||
|
||||
race == RACE_ROWBOAT_502
|
||||
race == Race::Boat ||
|
||||
race == Race::Rowboat
|
||||
);
|
||||
}
|
||||
|
||||
@@ -8218,37 +8218,37 @@ int Mob::DispatchZoneControllerEvent(
|
||||
std::string Mob::GetRacePlural()
|
||||
{
|
||||
switch (GetBaseRace()) {
|
||||
case RACE_HUMAN_1:
|
||||
case Race::Human:
|
||||
return "Humans";
|
||||
case RACE_BARBARIAN_2:
|
||||
case Race::Barbarian:
|
||||
return "Barbarians";
|
||||
case RACE_ERUDITE_3:
|
||||
case Race::Erudite:
|
||||
return "Erudites";
|
||||
case RACE_WOOD_ELF_4:
|
||||
case Race::WoodElf:
|
||||
return "Wood Elves";
|
||||
case RACE_HIGH_ELF_5:
|
||||
case Race::HighElf:
|
||||
return "High Elves";
|
||||
case RACE_DARK_ELF_6:
|
||||
case Race::DarkElf:
|
||||
return "Dark Elves";
|
||||
case RACE_HALF_ELF_7:
|
||||
case Race::HalfElf:
|
||||
return "Half Elves";
|
||||
case RACE_DWARF_8:
|
||||
case Race::Dwarf:
|
||||
return "Dwarves";
|
||||
case RACE_TROLL_9:
|
||||
case Race::Troll:
|
||||
return "Trolls";
|
||||
case RACE_OGRE_10:
|
||||
case Race::Ogre:
|
||||
return "Ogres";
|
||||
case RACE_HALFLING_11:
|
||||
case Race::Halfling:
|
||||
return "Halflings";
|
||||
case RACE_GNOME_12:
|
||||
case Race::Gnome:
|
||||
return "Gnomes";
|
||||
case RACE_IKSAR_128:
|
||||
case Race::Iksar:
|
||||
return "Iksar";
|
||||
case RACE_VAH_SHIR_130:
|
||||
case Race::VahShir:
|
||||
return "Vah Shir";
|
||||
case RACE_FROGLOK_330:
|
||||
case Race::Froglok2:
|
||||
return "Frogloks";
|
||||
case RACE_DRAKKIN_522:
|
||||
case Race::Drakkin:
|
||||
return "Drakkin";
|
||||
default:
|
||||
return "Races";
|
||||
|
||||
+12
-9
@@ -83,7 +83,7 @@ struct AppearanceStruct {
|
||||
uint8 hair = UINT8_MAX;
|
||||
uint8 hair_color = UINT8_MAX;
|
||||
uint8 helmet_texture = UINT8_MAX;
|
||||
uint16 race_id = RACE_DOUG_0;
|
||||
uint16 race_id = Race::Doug;
|
||||
bool send_effects = true;
|
||||
float size = -1.0f;
|
||||
Client *target = nullptr;
|
||||
@@ -748,14 +748,17 @@ public:
|
||||
int64 GetHateAmount(Mob* tmob, bool is_dam = false) { return hate_list.GetEntHateAmount(tmob,is_dam);}
|
||||
int64 GetDamageAmount(Mob* tmob) { return hate_list.GetEntHateAmount(tmob, true);}
|
||||
int GetHateRatio(Mob *first, Mob *with) { return hate_list.GetHateRatio(first, with); }
|
||||
Mob* GetHateTop() { return hate_list.GetEntWithMostHateOnList(this);}
|
||||
Mob* GetSecondaryHate(Mob *skip) { return hate_list.GetEntWithMostHateOnList(this, skip); }
|
||||
Mob* GetHateTop() { return hate_list.GetMobWithMostHateOnList(this);}
|
||||
Bot* GetHateTopBot() { return hate_list.GetMobWithMostHateOnList(this, nullptr, false, EntityFilterType::Bots)->CastToBot();}
|
||||
Client* GetHateTopClient() { return hate_list.GetMobWithMostHateOnList(this, nullptr, false, EntityFilterType::Clients)->CastToClient();}
|
||||
NPC* GetHateTopNPC() { return hate_list.GetMobWithMostHateOnList(this, nullptr, false, EntityFilterType::NPCs)->CastToNPC();}
|
||||
Mob* GetSecondaryHate(Mob *skip) { return hate_list.GetMobWithMostHateOnList(this, skip); }
|
||||
Mob* GetHateDamageTop(Mob* other) { return hate_list.GetDamageTopOnHateList(other);}
|
||||
Mob* GetHateRandom() { return hate_list.GetRandomEntOnHateList();}
|
||||
Client* GetHateRandomClient() { return hate_list.GetRandomClientOnHateList(); }
|
||||
NPC* GetHateRandomNPC() { return hate_list.GetRandomNPCOnHateList(); }
|
||||
Bot* GetHateRandomBot() { return hate_list.GetRandomBotOnHateList(); }
|
||||
Mob* GetHateMost() { return hate_list.GetEntWithMostHateOnList();}
|
||||
Mob* GetHateRandom() { return hate_list.GetRandomMobOnHateList(); }
|
||||
Bot* GetHateRandomBot() { return hate_list.GetRandomMobOnHateList(EntityFilterType::Bots)->CastToBot(); }
|
||||
Client* GetHateRandomClient() { return hate_list.GetRandomMobOnHateList(EntityFilterType::Clients)->CastToClient(); }
|
||||
NPC* GetHateRandomNPC() { return hate_list.GetRandomMobOnHateList(EntityFilterType::NPCs)->CastToNPC(); }
|
||||
Mob* GetHateMost() { return hate_list.GetMobWithMostHateOnList();}
|
||||
Mob* GetHateClosest(bool skip_mezzed = false) { return hate_list.GetClosestEntOnHateList(this, skip_mezzed); }
|
||||
Bot* GetHateClosestBot(bool skip_mezzed = false) { return hate_list.GetClosestEntOnHateList(this, skip_mezzed, EntityFilterType::Bots)->CastToBot(); }
|
||||
Client* GetHateClosestClient(bool skip_mezzed = false) { return hate_list.GetClosestEntOnHateList(this, skip_mezzed, EntityFilterType::Clients)->CastToClient(); }
|
||||
@@ -1121,7 +1124,7 @@ public:
|
||||
|
||||
void DoSpecialAttackDamage(Mob *who, EQ::skills::SkillType skill, int base_damage, int min_damage = 0, int32 hate_override = -1, int ReuseTime = 10);
|
||||
void DoThrowingAttackDmg(Mob* other, const EQ::ItemInstance* RangeWeapon = nullptr, const EQ::ItemData* AmmoItem = nullptr, int32 weapon_damage = 0, int16 chance_mod = 0, int16 focus = 0, int ReuseTime = 0, uint32 range_id = 0, int AmmoSlot = 0, float speed = 4.0f, bool DisableProcs = false);
|
||||
void DoMeleeSkillAttackDmg(Mob* other, int32 weapon_damage, EQ::skills::SkillType skillinuse, int16 chance_mod = 0, int16 focus = 0, bool CanRiposte = false, int ReuseTime = 0);
|
||||
void DoMeleeSkillAttackDmg(Mob* other, int32 weapon_damage, EQ::skills::SkillType skillinuse, int16 chance_mod = 0, int16 focus = 0, bool can_riposte = false, int ReuseTime = 0);
|
||||
void DoArcheryAttackDmg(Mob* other, const EQ::ItemInstance* RangeWeapon = nullptr, const EQ::ItemInstance* Ammo = nullptr, int32 weapon_damage = 0, int16 chance_mod = 0, int16 focus = 0, int ReuseTime = 0, uint32 range_id = 0, uint32 ammo_id = 0, const EQ::ItemData *AmmoItem = nullptr, int AmmoSlot = 0, float speed = 4.0f, bool DisableProcs = false);
|
||||
bool TryProjectileAttack(Mob* other, const EQ::ItemData *item, EQ::skills::SkillType skillInUse, uint64 weapon_dmg, const EQ::ItemInstance* RangeWeapon, const EQ::ItemInstance* Ammo, int AmmoSlot, float speed, bool DisableProcs = false);
|
||||
void ProjectileAttack();
|
||||
|
||||
+4
-4
@@ -769,7 +769,7 @@ void Client::AI_Process()
|
||||
{
|
||||
if(AI_target_check_timer->Check())
|
||||
{
|
||||
SetTarget(hate_list.GetEntWithMostHateOnList(this));
|
||||
SetTarget(hate_list.GetMobWithMostHateOnList(this));
|
||||
}
|
||||
}
|
||||
|
||||
@@ -1073,12 +1073,12 @@ void Mob::AI_Process() {
|
||||
|
||||
if (IsFocused()) {
|
||||
if (!target) {
|
||||
SetTarget(hate_list.GetEntWithMostHateOnList(this));
|
||||
SetTarget(hate_list.GetMobWithMostHateOnList(this));
|
||||
}
|
||||
}
|
||||
else {
|
||||
if (!ImprovedTaunt())
|
||||
SetTarget(hate_list.GetEntWithMostHateOnList(this));
|
||||
SetTarget(hate_list.GetMobWithMostHateOnList(this));
|
||||
}
|
||||
|
||||
}
|
||||
@@ -1800,7 +1800,7 @@ void Mob::AI_Event_Engaged(Mob *attacker, bool yell_for_help)
|
||||
|
||||
auto emote_id = GetEmoteID();
|
||||
if (emote_id) {
|
||||
CastToNPC()->DoNPCEmote(EQ::constants::EmoteEventTypes::EnterCombat, emoteid);
|
||||
CastToNPC()->DoNPCEmote(EQ::constants::EmoteEventTypes::EnterCombat, emoteid, attacker);
|
||||
}
|
||||
|
||||
std::string mob_name = GetCleanName();
|
||||
|
||||
+69
-39
@@ -155,10 +155,10 @@ NPC::NPC(const NPCType *npc_type_data, Spawn2 *in_respawn, const glm::vec4 &posi
|
||||
|
||||
// lava dragon is a fixed size model and should always use its default
|
||||
// otherwise pathing issues
|
||||
if (race == RACE_LAVA_DRAGON_49) {
|
||||
if (race == Race::LavaDragon) {
|
||||
size = 5;
|
||||
}
|
||||
if (race == RACE_WURM_158) {
|
||||
if (race == Race::Wurm) {
|
||||
size = 15;
|
||||
}
|
||||
|
||||
@@ -1058,7 +1058,7 @@ bool NPC::Process()
|
||||
NPCAssistCap() < RuleI(Combat, NPCAssistCap)) {
|
||||
// Some cases like flash of light used for aggro haven't set target
|
||||
if (!GetTarget()) {
|
||||
SetTarget(hate_list.GetEntWithMostHateOnList(this));
|
||||
SetTarget(hate_list.GetMobWithMostHateOnList(this));
|
||||
}
|
||||
AIYellForHelp(this, GetTarget());
|
||||
if (NPCAssistCap() > 0 && !assist_cap_timer.Enabled())
|
||||
@@ -3046,42 +3046,72 @@ void NPC::SendPayload(int payload_id, std::string payload_value)
|
||||
}
|
||||
|
||||
NPC_Emote_Struct* NPC::GetNPCEmote(uint32 emoteid, uint8 event_) {
|
||||
LinkedListIterator<NPC_Emote_Struct*> iterator(zone->NPCEmoteList);
|
||||
iterator.Reset();
|
||||
while(iterator.MoreElements())
|
||||
{
|
||||
NPC_Emote_Struct* nes = iterator.GetData();
|
||||
std::vector<NPC_Emote_Struct *> emotes;
|
||||
for (auto &e: zone->npc_emote_list) {
|
||||
NPC_Emote_Struct *nes = e;
|
||||
if (emoteid == nes->emoteid && event_ == nes->event_) {
|
||||
return nes;
|
||||
emotes.push_back(e);
|
||||
}
|
||||
iterator.Advance();
|
||||
}
|
||||
return nullptr;
|
||||
|
||||
if (emotes.empty()) {
|
||||
return nullptr;
|
||||
}
|
||||
else if (emotes.size() == 1) {
|
||||
return emotes[0];
|
||||
}
|
||||
|
||||
int index = zone->random.Roll0(emotes.size());
|
||||
|
||||
return emotes[index];
|
||||
}
|
||||
|
||||
void NPC::DoNPCEmote(uint8 event_, uint32 emoteid)
|
||||
void NPC::DoNPCEmote(uint8 event_, uint32 emoteid, Mob* target)
|
||||
{
|
||||
if (emoteid == 0)
|
||||
{
|
||||
if (emoteid == 0) {
|
||||
return;
|
||||
}
|
||||
|
||||
NPC_Emote_Struct* nes = GetNPCEmote(emoteid,event_);
|
||||
if(nes == nullptr)
|
||||
{
|
||||
NPC_Emote_Struct *nes = GetNPCEmote(emoteid, event_);
|
||||
if (nes == nullptr) {
|
||||
return;
|
||||
}
|
||||
|
||||
if(emoteid == nes->emoteid)
|
||||
{
|
||||
if(nes->type == 1)
|
||||
Emote("%s",nes->text);
|
||||
else if(nes->type == 2)
|
||||
Shout("%s",nes->text);
|
||||
else if(nes->type == 3)
|
||||
entity_list.MessageCloseString(this, true, 200, 10, GENERIC_STRING, nes->text);
|
||||
else
|
||||
Say("%s",nes->text);
|
||||
std::string processed = nes->text;
|
||||
Strings::FindReplace(processed, "$mname", GetCleanName());
|
||||
Strings::FindReplace(processed, "$mracep", GetRacePlural() = GetClass());
|
||||
Strings::FindReplace(processed, "$mrace", GetPlayerRaceName(GetRace()));
|
||||
Strings::FindReplace(processed, "$mclass", GetClassIDName(GetClass()));
|
||||
if (target) {
|
||||
Strings::FindReplace(processed, "$name", target->GetCleanName());
|
||||
Strings::FindReplace(processed, "$racep", GetRacePlural() = target->GetClass());
|
||||
Strings::FindReplace(processed, "$race", GetPlayerRaceName(target->GetRace()));
|
||||
Strings::FindReplace(processed, "$class", GetClassIDName(target->GetClass()));
|
||||
}
|
||||
else {
|
||||
Strings::FindReplace(processed, "$name", "foe");
|
||||
Strings::FindReplace(processed, "$race", "race");
|
||||
Strings::FindReplace(processed, "$racep", "races");
|
||||
Strings::FindReplace(processed, "$class", "class");
|
||||
}
|
||||
|
||||
if (emoteid == nes->emoteid) {
|
||||
if (event_ == EQ::constants::EmoteEventTypes::Hailed && target) {
|
||||
DoQuestPause(target);
|
||||
}
|
||||
|
||||
if (nes->type == 1) {
|
||||
Emote("%s", processed.c_str());
|
||||
}
|
||||
else if (nes->type == 2) {
|
||||
Shout("%s", processed.c_str());
|
||||
}
|
||||
else if (nes->type == 3) {
|
||||
entity_list.MessageCloseString(this, true, 200, 10, GENERIC_STRING, processed.c_str());
|
||||
}
|
||||
else {
|
||||
Say("%s", processed.c_str());
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -3691,25 +3721,25 @@ void NPC::ScaleNPC(uint8 npc_level, bool always_scale, bool override_special_abi
|
||||
bool NPC::IsGuard()
|
||||
{
|
||||
switch (GetRace()) {
|
||||
case RT_GUARD:
|
||||
case Race::FreeportGuard:
|
||||
if (GetTexture() == 1 || GetTexture() == 2)
|
||||
return true;
|
||||
break;
|
||||
case RT_IKSAR_2:
|
||||
case Race::IksarCitizen:
|
||||
if (GetTexture() == 1)
|
||||
return true;
|
||||
break;
|
||||
case RT_GUARD_2:
|
||||
case RT_GUARD_3:
|
||||
case RT_GUARD_4:
|
||||
case RT_HUMAN_3:
|
||||
case RT_HALFLING_2:
|
||||
case RT_ERUDITE_2:
|
||||
case RT_BARBARIAN_2:
|
||||
case RT_DARK_ELF_2:
|
||||
case RT_TROLL_2:
|
||||
case Race::Felguard:
|
||||
case Race::Fayguard:
|
||||
case Race::VahShirGuard:
|
||||
case Race::QeynosCitizen:
|
||||
case Race::RivervaleCitizen:
|
||||
case Race::EruditeCitizen:
|
||||
case Race::HalasCitizen:
|
||||
case Race::NeriakCitizen:
|
||||
case Race::GrobbCitizen:
|
||||
case OGGOK_CITIZEN:
|
||||
case RT_DWARF_2:
|
||||
case Race::KaladimCitizen:
|
||||
return true;
|
||||
default:
|
||||
break;
|
||||
|
||||
+1
-1
@@ -476,7 +476,7 @@ public:
|
||||
const uint32 GetAltCurrencyType() const { return NPCTypedata->alt_currency_type; }
|
||||
|
||||
NPC_Emote_Struct* GetNPCEmote(uint32 emoteid, uint8 event_);
|
||||
void DoNPCEmote(uint8 event_, uint32 emoteid);
|
||||
void DoNPCEmote(uint8 event_, uint32 emoteid, Mob* target = nullptr);
|
||||
bool CanTalk();
|
||||
void DoQuestPause(Mob *other);
|
||||
|
||||
|
||||
@@ -3028,6 +3028,36 @@ void Perl_Client_RemoveRadiantCrystals(Client* self, uint32 amount)
|
||||
self->RemoveRadiantCrystals(amount);
|
||||
}
|
||||
|
||||
void Perl_Client_SummonItemIntoInventory(Client* self, perl::reference table_ref)
|
||||
{
|
||||
perl::hash table = table_ref;
|
||||
if (!table.exists("item_id") || !table.exists("charges")) {
|
||||
return;
|
||||
}
|
||||
|
||||
const uint32 item_id = table["item_id"];
|
||||
const int16 charges = table["charges"];
|
||||
const uint32 augment_one = table.exists("augment_one") ? table["augment_one"] : 0;
|
||||
const uint32 augment_two = table.exists("augment_two") ? table["augment_two"] : 0;
|
||||
const uint32 augment_three = table.exists("augment_three") ? table["augment_three"] : 0;
|
||||
const uint32 augment_four = table.exists("augment_four") ? table["augment_four"] : 0;
|
||||
const uint32 augment_five = table.exists("augment_five") ? table["augment_five"] : 0;
|
||||
const uint32 augment_six = table.exists("augment_six") ? table["augment_six"] : 0;
|
||||
const bool attuned = table.exists("attuned") ? table["attuned"] : false;
|
||||
|
||||
self->SummonItemIntoInventory(
|
||||
item_id,
|
||||
charges,
|
||||
augment_one,
|
||||
augment_two,
|
||||
augment_three,
|
||||
augment_four,
|
||||
augment_five,
|
||||
augment_six,
|
||||
attuned
|
||||
);
|
||||
}
|
||||
|
||||
void perl_register_client()
|
||||
{
|
||||
perl::interpreter perl(PERL_GET_THX);
|
||||
@@ -3535,6 +3565,7 @@ void perl_register_client()
|
||||
package.add("SummonItem", (void(*)(Client*, uint32, int16, bool, uint32, uint32, uint32, uint32))&Perl_Client_SummonItem);
|
||||
package.add("SummonItem", (void(*)(Client*, uint32, int16, bool, uint32, uint32, uint32, uint32, uint32))&Perl_Client_SummonItem);
|
||||
package.add("SummonItem", (void(*)(Client*, uint32, int16, bool, uint32, uint32, uint32, uint32, uint32, uint16))&Perl_Client_SummonItem);
|
||||
package.add("SummonItemIntoInventory", &Perl_Client_SummonItemIntoInventory);
|
||||
package.add("TGB", &Perl_Client_TGB);
|
||||
package.add("TakeMoneyFromPP", (bool(*)(Client*, uint64_t))&Perl_Client_TakeMoneyFromPP);
|
||||
package.add("TakeMoneyFromPP", (bool(*)(Client*, uint64_t, bool))&Perl_Client_TakeMoneyFromPP);
|
||||
|
||||
@@ -1344,6 +1344,21 @@ Mob* Perl_Mob_GetHateTop(Mob* self) // @categories Hate and Aggro
|
||||
return self->GetHateTop();
|
||||
}
|
||||
|
||||
Bot* Perl_Mob_GetHateTopBot(Mob* self) // @categories Hate and Aggro
|
||||
{
|
||||
return self->GetHateTopBot();
|
||||
}
|
||||
|
||||
Client* Perl_Mob_GetHateTopClient(Mob* self) // @categories Hate and Aggro
|
||||
{
|
||||
return self->GetHateTopClient();
|
||||
}
|
||||
|
||||
NPC* Perl_Mob_GetHateTopNPC(Mob* self) // @categories Hate and Aggro
|
||||
{
|
||||
return self->GetHateTopNPC();
|
||||
}
|
||||
|
||||
Mob* Perl_Mob_GetHateDamageTop(Mob* self, Mob* other) // @categories Hate and Aggro
|
||||
{
|
||||
return self->GetHateDamageTop(other);
|
||||
@@ -3581,6 +3596,9 @@ void perl_register_mob()
|
||||
package.add("GetHateRandomClient", &Perl_Mob_GetHateRandomClient);
|
||||
package.add("GetHateRandomNPC", &Perl_Mob_GetHateRandomNPC);
|
||||
package.add("GetHateTop", &Perl_Mob_GetHateTop);
|
||||
package.add("GetHateTopBot", &Perl_Mob_GetHateTopBot);
|
||||
package.add("GetHateTopClient", &Perl_Mob_GetHateTopClient);
|
||||
package.add("GetHateTopNPC", &Perl_Mob_GetHateTopNPC);
|
||||
package.add("GetHeading", &Perl_Mob_GetHeading);
|
||||
package.add("GetHelmTexture", &Perl_Mob_GetHelmTexture);
|
||||
package.add("GetHerosForgeModel", &Perl_Mob_GetHerosForgeModel);
|
||||
|
||||
+1
-1
@@ -71,7 +71,7 @@ Petition::Petition(uint32 id)
|
||||
{
|
||||
petid = id;
|
||||
charclass = Class::None;
|
||||
charrace = RACE_DOUG_0;
|
||||
charrace = Race::Doug;
|
||||
charlevel = 0;
|
||||
checkouts = 0;
|
||||
unavailables = 0;
|
||||
|
||||
@@ -2385,7 +2385,7 @@ int Mob::TryAssassinate(Mob *defender, EQ::skills::SkillType skillInUse)
|
||||
}
|
||||
|
||||
void Mob::DoMeleeSkillAttackDmg(Mob *other, int32 weapon_damage, EQ::skills::SkillType skillinuse, int16 chance_mod,
|
||||
int16 focus, bool CanRiposte, int ReuseTime)
|
||||
int16 focus, bool can_riposte, int ReuseTime)
|
||||
{
|
||||
if (!CanDoSpecialAttack(other)) {
|
||||
return;
|
||||
@@ -2425,15 +2425,14 @@ void Mob::DoMeleeSkillAttackDmg(Mob *other, int32 weapon_damage, EQ::skills::Ski
|
||||
}
|
||||
|
||||
DamageHitInfo my_hit {};
|
||||
my_hit.base_damage = weapon_damage;
|
||||
my_hit.min_damage = 0;
|
||||
my_hit.damage_done = 1;
|
||||
|
||||
my_hit.skill = skillinuse;
|
||||
my_hit.offense = offense(my_hit.skill);
|
||||
my_hit.tohit = GetTotalToHit(my_hit.skill, chance_mod);
|
||||
// slot range exclude ripe etc ...
|
||||
my_hit.hand = CanRiposte ? EQ::invslot::slotRange : EQ::invslot::slotPrimary;
|
||||
my_hit.base_damage = weapon_damage;
|
||||
my_hit.min_damage = 0;
|
||||
my_hit.damage_done = 1;
|
||||
my_hit.skill = skillinuse;
|
||||
my_hit.offense = offense(my_hit.skill);
|
||||
my_hit.tohit = GetTotalToHit(my_hit.skill, chance_mod);
|
||||
my_hit.hand = can_riposte ? EQ::invslot::slotPrimary : EQ::invslot::slotRange;
|
||||
|
||||
if (IsNPC()) {
|
||||
my_hit.min_damage = CastToNPC()->GetMinDamage();
|
||||
|
||||
+16
-16
@@ -7430,42 +7430,42 @@ bool Mob::PassCastRestriction(int value)
|
||||
|
||||
case IS_BIXIE:
|
||||
case IS_BIXIE2:
|
||||
if ((GetRace() == RT_BIXIE) ||(GetRace() == RT_BIXIE_2))
|
||||
if ((GetRace() == Race::Bixie) ||(GetRace() == Race::Bixie2))
|
||||
return true;
|
||||
break;
|
||||
|
||||
case IS_HARPY:
|
||||
if ((GetRace() == RT_HARPY) ||(GetRace() == RT_HARPY_2))
|
||||
if ((GetRace() == Race::Harpy) ||(GetRace() == Race::Harpy2))
|
||||
return true;
|
||||
break;
|
||||
|
||||
case IS_GNOLL:
|
||||
if ((GetRace() == RT_GNOLL) || (GetRace() == RT_GNOLL_2) || (GetRace() == RT_GNOLL_3))
|
||||
if ((GetRace() == Race::Gnoll) || (GetRace() == Race::Gnoll2) || (GetRace() == Race::Gnoll3))
|
||||
return true;
|
||||
break;
|
||||
|
||||
case IS_SPORALI:
|
||||
if ((GetRace() == RT_SPORALI) ||(GetRace() == RT_FUNGUSMAN))
|
||||
if ((GetRace() == Race::Sporali) ||(GetRace() == Race::Fungusman))
|
||||
return true;
|
||||
break;
|
||||
|
||||
case IS_KOBOLD:
|
||||
if ((GetRace() == RT_KOBOLD) ||(GetRace() == RT_KOBOLD_2))
|
||||
if ((GetRace() == Race::Kobold) ||(GetRace() == Race::Kobold2))
|
||||
return true;
|
||||
break;
|
||||
|
||||
case IS_FROSTCRYPT_SHADE:
|
||||
if (GetRace() == RT_GIANT_SHADE)
|
||||
if (GetRace() == Race::GiantShade)
|
||||
return true;
|
||||
break;
|
||||
|
||||
case IS_DRAKKIN:
|
||||
if (GetRace() == RT_DRAKKIN)
|
||||
if (GetRace() == Race::Drakkin)
|
||||
return true;
|
||||
break;
|
||||
|
||||
case IS_UNDEAD_OR_VALDEHOLM_GIANT:
|
||||
if (GetBodyType() == BT_Undead || GetRace() == RT_GIANT_12 || GetRace() == RT_GIANT_13)
|
||||
if (GetBodyType() == BT_Undead || GetRace() == Race::Giant2 || GetRace() == Race::Giant3)
|
||||
return true;
|
||||
break;
|
||||
|
||||
@@ -7496,7 +7496,7 @@ bool Mob::PassCastRestriction(int value)
|
||||
break;
|
||||
|
||||
case IS_FAE_OR_PIXIE:
|
||||
if ((GetRace() == RT_PIXIE) || (GetRace() == RT_FAY_DRAKE))
|
||||
if ((GetRace() == Race::Pixie) || (GetRace() == Race::FayDrake))
|
||||
return true;
|
||||
break;
|
||||
|
||||
@@ -7511,12 +7511,12 @@ bool Mob::PassCastRestriction(int value)
|
||||
break;
|
||||
|
||||
case IS_CLOCKWORK_AND_HP_LESS_THAN_45_PCT:
|
||||
if ((GetRace() == RT_GNOMEWORK || GetRace() == RACE_CLOCKWORK_GNOME_88) && (GetHPRatio() < 45))
|
||||
if ((GetRace() == Race::Gnomework || GetRace() == Race::ClockworkGnome) && (GetHPRatio() < 45))
|
||||
return true;
|
||||
break;
|
||||
|
||||
case IS_WISP_AND_HP_LESS_THAN_10_PCT:
|
||||
if ((GetRace() == RT_WILL_O_WISP) && (GetHPRatio() < 10))
|
||||
if ((GetRace() == Race::Wisp) && (GetHPRatio() < 10))
|
||||
return true;
|
||||
break;
|
||||
|
||||
@@ -7889,12 +7889,12 @@ bool Mob::PassCastRestriction(int value)
|
||||
break;
|
||||
|
||||
case IS_TREANT:
|
||||
if (GetRace() == RT_TREANT || GetRace() == RT_TREANT_2 || GetRace() == RT_TREANT_3)
|
||||
if (GetRace() == Race::Treant || GetRace() == Race::Treant2 || GetRace() == Race::Treant3)
|
||||
return true;
|
||||
break;
|
||||
|
||||
case IS_SCARECROW:
|
||||
if (GetRace() == RT_SCARECROW || GetRace() == RT_SCARECROW_2)
|
||||
if (GetRace() == Race::Scarecrow || GetRace() == Race::Scarecrow2)
|
||||
return true;
|
||||
break;
|
||||
|
||||
@@ -10263,7 +10263,7 @@ void Mob::ApplySpellEffectIllusion(int32 spell_id, Mob *caster, int buffslot, in
|
||||
gender_id
|
||||
);
|
||||
|
||||
if (base != RACE_ELEMENTAL_75 && base != RACE_DRAKKIN_522) {
|
||||
if (base != Race::Elemental && base != Race::Drakkin) {
|
||||
if (max > 0) {
|
||||
if (limit == 0) {
|
||||
SendIllusionPacket(
|
||||
@@ -10303,7 +10303,7 @@ void Mob::ApplySpellEffectIllusion(int32 spell_id, Mob *caster, int buffslot, in
|
||||
}
|
||||
);
|
||||
}
|
||||
} else if (base == RACE_ELEMENTAL_75){
|
||||
} else if (base == Race::Elemental){
|
||||
SendIllusionPacket(
|
||||
AppearanceStruct{
|
||||
.gender_id = static_cast<uint8>(gender_id),
|
||||
@@ -10311,7 +10311,7 @@ void Mob::ApplySpellEffectIllusion(int32 spell_id, Mob *caster, int buffslot, in
|
||||
.texture = static_cast<uint8>(limit),
|
||||
}
|
||||
);
|
||||
} else if (base == RACE_DRAKKIN_522) {
|
||||
} else if (base == Race::Drakkin) {
|
||||
FaceChange_Struct f{
|
||||
.haircolor = GetHairColor(),
|
||||
.beardcolor = GetBeardColor(),
|
||||
|
||||
+1
-4
@@ -2765,9 +2765,6 @@ bool Mob::SpellFinished(uint16 spell_id, Mob *spell_target, CastingSlot slot, in
|
||||
CastToBot()->SetItemReuseTimer(item->ID);
|
||||
CastToBot()->SetIsUsingItemClick(false);
|
||||
}
|
||||
else {
|
||||
GetOwner()->Message(Chat::Red, "%s says, 'Failed to set item reuse timer for %s.", GetCleanName());
|
||||
}
|
||||
}
|
||||
|
||||
if (IsNPC()) {
|
||||
@@ -3885,7 +3882,7 @@ bool Mob::SpellOnTarget(
|
||||
// Prevent double invising, which made you uninvised
|
||||
// Not sure if all 3 should be stacking
|
||||
//This is not live like behavior (~Kayen confirmed 2/2/22)
|
||||
if (!RuleB(Spells, AllowDoubleInvis)) {
|
||||
if (!RuleB(Spells, AllowDoubleInvis) && !IsActiveBardSong(spell_id)) {
|
||||
if (IsEffectInSpell(spell_id, SE_Invisibility)) {
|
||||
if (spelltar->invisible) {
|
||||
spelltar->MessageString(Chat::SpellFailure, ALREADY_INVIS, GetCleanName());
|
||||
|
||||
+46
-46
@@ -880,118 +880,118 @@ float Mob::GetZOffset() const {
|
||||
float offset = 3.125f;
|
||||
|
||||
switch (GetModel()) {
|
||||
case RACE_BASILISK_436:
|
||||
case Race::Basilisk:
|
||||
offset = 0.577f;
|
||||
break;
|
||||
case RACE_DRAKE_430:
|
||||
case Race::Drake2:
|
||||
offset = 0.5f;
|
||||
break;
|
||||
case RACE_DRAKE_432:
|
||||
case Race::Drake3:
|
||||
offset = 1.9f;
|
||||
break;
|
||||
case RACE_DRAGON_435:
|
||||
case Race::Dragon:
|
||||
offset = 0.93f;
|
||||
break;
|
||||
case RACE_LAVA_SPIDER_450:
|
||||
case Race::LavaSpider:
|
||||
offset = 0.938f;
|
||||
break;
|
||||
case RACE_ALLIGATOR_479:
|
||||
case Race::Alligator2:
|
||||
offset = 0.8f;
|
||||
break;
|
||||
case RACE_LAVA_SPIDER_QUEEN_451:
|
||||
case Race::LavaSpiderQueen:
|
||||
offset = 0.816f;
|
||||
break;
|
||||
case RACE_DRAGON_437:
|
||||
case Race::Dragon2:
|
||||
offset = 0.527f;
|
||||
break;
|
||||
case RACE_PUMA_439:
|
||||
case Race::Puma2:
|
||||
offset = 1.536f;
|
||||
break;
|
||||
case RACE_RAT_415:
|
||||
case Race::Rat:
|
||||
offset = 1.0f;
|
||||
break;
|
||||
case RACE_DRAGON_438:
|
||||
case RACE_DRAGON_452:
|
||||
case Race::Dragon3:
|
||||
case Race::Dragon4:
|
||||
offset = 0.776f;
|
||||
break;
|
||||
case RACE_SPIDER_QUEEN_441:
|
||||
case Race::SpiderQueen:
|
||||
offset = 0.816f;
|
||||
break;
|
||||
case RACE_SPIDER_440:
|
||||
case Race::Spider:
|
||||
offset = 0.938f;
|
||||
break;
|
||||
case RACE_IMP_46:
|
||||
case RACE_SNAKE_468:
|
||||
case RACE_CORATHUS_459:
|
||||
case Race::Imp:
|
||||
case Race::Snake:
|
||||
case Race::Corathus:
|
||||
offset = 1.0f;
|
||||
break;
|
||||
case RACE_DRACHNID_COCOON_462:
|
||||
case Race::DrachnidCocoon:
|
||||
offset = 1.5f;
|
||||
break;
|
||||
case RACE_DRAGON_530:
|
||||
case Race::Dragon5:
|
||||
offset = 1.2f;
|
||||
break;
|
||||
case RACE_GOO_549:
|
||||
case RACE_GOO_548:
|
||||
case Race::Goo4:
|
||||
case Race::Goo3:
|
||||
offset = 0.5f;
|
||||
break;
|
||||
case RACE_GOO_547:
|
||||
case Race::Goo2:
|
||||
offset = 0.5f;
|
||||
break;
|
||||
case RACE_DRACOLICH_604:
|
||||
case Race::Dracolich:
|
||||
offset = 1.2f;
|
||||
break;
|
||||
case RACE_TELMIRA_653:
|
||||
case Race::Telmira:
|
||||
offset = 5.9f;
|
||||
break;
|
||||
case RACE_MORELL_THULE_658:
|
||||
case Race::MorellThule:
|
||||
offset = 4.0f;
|
||||
break;
|
||||
case RACE_ARMOR_OF_MARR_323:
|
||||
case RACE_AMYGDALAN_663:
|
||||
case Race::AnimatedArmor:
|
||||
case Race::Amygdalan:
|
||||
offset = 5.0f;
|
||||
break;
|
||||
case RACE_SPECTRAL_IKSAR_147:
|
||||
case RACE_SANDMAN_664:
|
||||
case Race::IksarSpirit:
|
||||
case Race::Sandman:
|
||||
offset = 4.0f;
|
||||
break;
|
||||
case RACE_LAVA_DRAGON_49:
|
||||
case RACE_ALARAN_SENTRY_STONE_703:
|
||||
case Race::LavaDragon:
|
||||
case Race::AlaranSentryStone:
|
||||
offset = 9.0f;
|
||||
break;
|
||||
case RACE_RABBIT_668:
|
||||
case Race::Rabbit:
|
||||
offset = 5.0f;
|
||||
break;
|
||||
case RACE_WURM_158:
|
||||
case RACE_BLIND_DREAMER_669:
|
||||
case Race::Wurm:
|
||||
case Race::BlindDreamer:
|
||||
offset = 7.0f;
|
||||
break;
|
||||
case RACE_SIREN_187:
|
||||
case RACE_HALAS_CITIZEN_90:
|
||||
case RACE_OTTERMAN_190:
|
||||
case Race::Siren:
|
||||
case Race::HalasCitizen:
|
||||
case Race::Othmir:
|
||||
offset = .5f;
|
||||
break;
|
||||
case RACE_COLDAIN_183:
|
||||
case Race::Coldain:
|
||||
offset = .6f;
|
||||
break;
|
||||
case RACE_WEREWOLF_14:
|
||||
case Race::Werewolf:
|
||||
offset = 1.2f;
|
||||
break;
|
||||
case RACE_DWARF_8:
|
||||
case Race::Dwarf:
|
||||
offset = .7f;
|
||||
break;
|
||||
case RACE_HORSE_216:
|
||||
case Race::Horse:
|
||||
offset = 1.4f;
|
||||
break;
|
||||
case RACE_ENCHANTED_ARMOR_175:
|
||||
case RACE_TIGER_63:
|
||||
case Race::EnchantedArmor:
|
||||
case Race::Tiger:
|
||||
offset = 1.75f;
|
||||
break;
|
||||
case RACE_STATUE_OF_RALLOS_ZEK_66:
|
||||
case Race::StatueOfRallosZek:
|
||||
offset = 1.0f;
|
||||
break;
|
||||
case RACE_GORAL_687:
|
||||
case RACE_SELYRAH_686:
|
||||
case Race::Goral:
|
||||
case Race::Selyrah:
|
||||
offset = 2.0f;
|
||||
break;
|
||||
default:
|
||||
|
||||
@@ -2015,7 +2015,7 @@ void WorldServer::HandleMessage(uint16 opcode, const EQ::Net::Packet &p)
|
||||
{
|
||||
if (zone && zone->IsLoaded()) {
|
||||
zone->SendReloadMessage("NPC Emotes");
|
||||
zone->LoadNPCEmotes(&zone->NPCEmoteList);
|
||||
zone->LoadNPCEmotes(&zone->npc_emote_list);
|
||||
}
|
||||
break;
|
||||
}
|
||||
|
||||
+7
-7
@@ -1056,7 +1056,7 @@ Zone::~Zone() {
|
||||
safe_delete_array(short_name);
|
||||
safe_delete_array(long_name);
|
||||
safe_delete(Weather_Timer);
|
||||
NPCEmoteList.Clear();
|
||||
npc_emote_list.clear();
|
||||
zone_point_list.Clear();
|
||||
entity_list.Clear();
|
||||
ClearBlockedSpells();
|
||||
@@ -1152,7 +1152,7 @@ bool Zone::Init(bool is_static) {
|
||||
LoadLDoNTrapEntries();
|
||||
LoadVeteranRewards();
|
||||
LoadAlternateCurrencies();
|
||||
LoadNPCEmotes(&NPCEmoteList);
|
||||
LoadNPCEmotes(&npc_emote_list);
|
||||
|
||||
LoadAlternateAdvancement();
|
||||
|
||||
@@ -1233,8 +1233,8 @@ void Zone::ReloadStaticData() {
|
||||
|
||||
LoadVeteranRewards();
|
||||
LoadAlternateCurrencies();
|
||||
NPCEmoteList.Clear();
|
||||
LoadNPCEmotes(&NPCEmoteList);
|
||||
npc_emote_list.clear();
|
||||
LoadNPCEmotes(&npc_emote_list);
|
||||
|
||||
//load the zone config file.
|
||||
if (!LoadZoneCFG(GetShortName(), GetInstanceVersion())) { // try loading the zone name...
|
||||
@@ -2548,10 +2548,10 @@ void Zone::DoAdventureActions()
|
||||
|
||||
}
|
||||
|
||||
void Zone::LoadNPCEmotes(LinkedList<NPC_Emote_Struct*>* NPCEmoteList)
|
||||
void Zone::LoadNPCEmotes(std::vector<NPC_Emote_Struct*>* NPCEmoteList)
|
||||
{
|
||||
|
||||
NPCEmoteList->Clear();
|
||||
NPCEmoteList->clear();
|
||||
const std::string query = "SELECT emoteid, event_, type, text FROM npc_emotes";
|
||||
auto results = content_db.QueryDatabase(query);
|
||||
if (!results.Success()) {
|
||||
@@ -2565,7 +2565,7 @@ void Zone::LoadNPCEmotes(LinkedList<NPC_Emote_Struct*>* NPCEmoteList)
|
||||
nes->event_ = Strings::ToInt(row[1]);
|
||||
nes->type = Strings::ToInt(row[2]);
|
||||
strn0cpy(nes->text, row[3], sizeof(nes->text));
|
||||
NPCEmoteList->Insert(nes);
|
||||
NPCEmoteList->push_back(nes);
|
||||
}
|
||||
|
||||
LogInfo("Loaded [{}] npc emotes", Strings::Commify(results.RowCount()));
|
||||
|
||||
+2
-2
@@ -185,7 +185,7 @@ public:
|
||||
DynamicZone *GetDynamicZone();
|
||||
|
||||
IPathfinder *pathing;
|
||||
LinkedList<NPC_Emote_Struct *> NPCEmoteList;
|
||||
std::vector<NPC_Emote_Struct *> npc_emote_list;
|
||||
LinkedList<Spawn2 *> spawn2_list;
|
||||
LinkedList<ZonePoint *> zone_point_list;
|
||||
std::vector<ZonePointsRepository::ZonePoints> virtual_zone_point_list;
|
||||
@@ -282,7 +282,7 @@ public:
|
||||
void LoadMercSpells();
|
||||
void LoadMercTemplates();
|
||||
void LoadNewMerchantData(uint32 merchantid);
|
||||
void LoadNPCEmotes(LinkedList<NPC_Emote_Struct *> *NPCEmoteList);
|
||||
void LoadNPCEmotes(std::vector<NPC_Emote_Struct *> *NPCEmoteList);
|
||||
void LoadTempMerchantData();
|
||||
void LoadTickItems();
|
||||
void LoadVeteranRewards();
|
||||
|
||||
Reference in New Issue
Block a user