aboutsummaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
authorsilinoron <none@none>2010-08-24 15:04:34 -0700
committersilinoron <none@none>2010-08-24 15:04:34 -0700
commitaaaeecc916cf567877fbf835fb9e805f5227e3f6 (patch)
tree701d747297f9da0437237405f3a546020e3fbbb4 /src
parentc0dda8b492d073472f1a4de9641b882ac6b90211 (diff)
Add support for vehicle scaling based on item level.
Requires database data. Fixes issue #2754 --HG-- branch : trunk
Diffstat (limited to 'src')
-rw-r--r--src/server/game/Entities/Item/ItemPrototype.h23
-rw-r--r--src/server/game/Entities/Player/Player.cpp20
-rw-r--r--src/server/game/Entities/Player/Player.h2
-rw-r--r--src/server/game/Entities/Player/SocialMgr.h2
-rw-r--r--src/server/game/Entities/Vehicle/Vehicle.cpp28
-rw-r--r--src/server/game/Entities/Vehicle/Vehicle.h9
-rw-r--r--src/server/game/Globals/ObjectMgr.cpp45
-rw-r--r--src/server/game/Globals/ObjectMgr.h10
-rw-r--r--src/server/game/World/World.cpp3
9 files changed, 119 insertions, 23 deletions
diff --git a/src/server/game/Entities/Item/ItemPrototype.h b/src/server/game/Entities/Item/ItemPrototype.h
index 5941aea792f..ecdbbe7cafe 100644
--- a/src/server/game/Entities/Item/ItemPrototype.h
+++ b/src/server/game/Entities/Item/ItemPrototype.h
@@ -703,6 +703,29 @@ struct ItemPrototype
return 0;
}
+ float GetItemLevelIncludingQuality() const
+ {
+ float itemLevel = (float)ItemLevel;
+ switch (Quality)
+ {
+ case ITEM_QUALITY_POOR:
+ case ITEM_QUALITY_NORMAL:
+ case ITEM_QUALITY_UNCOMMON:
+ case ITEM_QUALITY_ARTIFACT:
+ case ITEM_QUALITY_HEIRLOOM:
+ itemLevel -= 13; // leaving this as a separate statement since we do not know the real behavior in this case
+ break;
+ case ITEM_QUALITY_RARE:
+ itemLevel -= 13;
+ break;
+ case ITEM_QUALITY_EPIC:
+ case ITEM_QUALITY_LEGENDARY:
+ default:
+ break;
+ }
+ return itemLevel;
+ }
+
bool IsPotion() const { return Class == ITEM_CLASS_CONSUMABLE && SubClass == ITEM_SUBCLASS_POTION; }
bool IsWeaponVellum() const { return Class == ITEM_CLASS_TRADE_GOODS && SubClass == ITEM_SUBCLASS_WEAPON_ENCHANTMENT; }
bool IsArmorVellum() const { return Class == ITEM_CLASS_TRADE_GOODS && SubClass == ITEM_SUBCLASS_ARMOR_ENCHANTMENT; }
diff --git a/src/server/game/Entities/Player/Player.cpp b/src/server/game/Entities/Player/Player.cpp
index 775489c2266..978078e5b85 100644
--- a/src/server/game/Entities/Player/Player.cpp
+++ b/src/server/game/Entities/Player/Player.cpp
@@ -13577,22 +13577,6 @@ void Player::PrepareGossipMenu(WorldObject *pSource, uint32 menuId, bool showQue
pMenu->GetGossipMenu().AddGossipMenuItemData(itr->second.action_menu_id, itr->second.action_poi_id, itr->second.action_script_id);
}
}
-
- // some gossips aren't handled in normal way ... so we need to do it this way .. TODO: handle it in normal way ;-)
- /*if (pMenu->Empty())
- {
- if (pCreature->HasFlag(UNIT_NPC_FLAGS,UNIT_NPC_FLAG_TRAINER))
- {
- // output error message if need
- pCreature->isCanTrainingOf(this, true);
- }
-
- if (pCreature->HasFlag(UNIT_NPC_FLAGS,UNIT_NPC_FLAG_BATTLEMASTER))
- {
- // output error message if need
- pCreature->isCanInteractWithBattleMaster(this, true);
- }
- }*/
}
void Player::SendPreparedGossip(WorldObject *pSource)
@@ -24137,7 +24121,7 @@ void Player::_LoadRandomBGStatus(QueryResult_AutoPtr result)
float Player::GetAverageItemLevel()
{
- uint32 sum = 0;
+ float sum = 0;
uint32 count = 0;
for (int i = EQUIPMENT_SLOT_START; i < EQUIPMENT_SLOT_END; ++i)
@@ -24147,7 +24131,7 @@ float Player::GetAverageItemLevel()
continue;
if (m_items[i] && m_items[i]->GetProto())
- sum += m_items[i]->GetProto()->ItemLevel;
+ sum += m_items[i]->GetProto()->GetItemLevelIncludingQuality();
count++;
}
diff --git a/src/server/game/Entities/Player/Player.h b/src/server/game/Entities/Player/Player.h
index 5e9a89d31d6..1f35aed6799 100644
--- a/src/server/game/Entities/Player/Player.h
+++ b/src/server/game/Entities/Player/Player.h
@@ -238,7 +238,7 @@ typedef std::list<PlayerCreateInfoAction> PlayerCreateInfoActions;
struct PlayerInfo
{
- // existence checked by displayId != 0 // existence checked by displayId != 0
+ // existence checked by displayId != 0
PlayerInfo() : displayId_m(0),displayId_f(0),levelInfo(NULL)
{
}
diff --git a/src/server/game/Entities/Player/SocialMgr.h b/src/server/game/Entities/Player/SocialMgr.h
index 30789ca0e02..4ac6154a3c1 100644
--- a/src/server/game/Entities/Player/SocialMgr.h
+++ b/src/server/game/Entities/Player/SocialMgr.h
@@ -44,7 +44,7 @@ enum SocialFlag
SOCIAL_FLAG_FRIEND = 0x01,
SOCIAL_FLAG_IGNORED = 0x02,
SOCIAL_FLAG_MUTED = 0x04, // guessed
- SOCIAL_FLAG_RAF = 0x08 // Recruit A Friend
+ SOCIAL_FLAG_UNK = 0x08 // Unknown - does not appear to be RaF
};
struct FriendInfo
diff --git a/src/server/game/Entities/Vehicle/Vehicle.cpp b/src/server/game/Entities/Vehicle/Vehicle.cpp
index 58036eb454b..4cc20680cd9 100644
--- a/src/server/game/Entities/Vehicle/Vehicle.cpp
+++ b/src/server/game/Entities/Vehicle/Vehicle.cpp
@@ -27,7 +27,7 @@
#include "CreatureAI.h"
#include "ZoneScript.h"
-Vehicle::Vehicle(Unit *unit, VehicleEntry const *vehInfo) : me(unit), m_vehicleInfo(vehInfo), m_usableSeatNum(0)
+Vehicle::Vehicle(Unit *unit, VehicleEntry const *vehInfo) : me(unit), m_vehicleInfo(vehInfo), m_usableSeatNum(0), m_bonusHP(0)
{
for (uint32 i = 0; i < 8; ++i)
{
@@ -306,8 +306,6 @@ bool Vehicle::AddPassenger(Unit *unit, int8 seatId)
if (seat->second.seatInfo->m_flags && !(seat->second.seatInfo->m_flags & 0x400))
unit->addUnitState(UNIT_STAT_ONVEHICLE);
- //SetFlag(UNIT_FIELD_FLAGS, UNIT_FLAG_PLAYER_CONTROLLED);
-
unit->AddUnitMovementFlag(MOVEMENTFLAG_ONTRANSPORT);
VehicleSeatEntry const *veSeat = seat->second.seatInfo;
unit->m_movementInfo.t_pos.m_positionX = veSeat->m_attachmentOffsetX;
@@ -320,9 +318,24 @@ bool Vehicle::AddPassenger(Unit *unit, int8 seatId)
if (me->GetTypeId() == TYPEID_UNIT
&& unit->GetTypeId() == TYPEID_PLAYER
&& seat->first == 0 && seat->second.seatInfo->m_flags & 0x800) // not right
+ {
if (!me->SetCharmedBy(unit, CHARM_TYPE_VEHICLE))
ASSERT(false);
+ if (VehicleScalingInfo const *scalingInfo = sObjectMgr.GetVehicleScalingInfo(m_vehicleInfo->m_ID))
+ {
+ Player *plr = unit->ToPlayer();
+ float averageItemLevel = plr->GetAverageItemLevel();
+ if (averageItemLevel < scalingInfo->baseItemLevel)
+ averageItemLevel = scalingInfo->baseItemLevel;
+ averageItemLevel -= scalingInfo->baseItemLevel;
+
+ m_bonusHP = uint32(me->GetMaxHealth() * (averageItemLevel * scalingInfo->scalingFactor));
+ me->SetMaxHealth(me->GetMaxHealth() + m_bonusHP);
+ me->SetHealth(me->GetHealth() + m_bonusHP);
+ }
+ }
+
if (me->IsInWorld())
{
unit->SendMonsterMoveTransport(me);
@@ -377,8 +390,17 @@ void Vehicle::RemovePassenger(Unit *unit)
if (me->GetTypeId() == TYPEID_UNIT
&& unit->GetTypeId() == TYPEID_PLAYER
&& seat->first == 0 && seat->second.seatInfo->m_flags & 0x800)
+ {
me->RemoveCharmedBy(unit);
+ if (m_bonusHP)
+ {
+ me->SetHealth(me->GetHealth() - m_bonusHP);
+ me->SetMaxHealth(me->GetMaxHealth() - m_bonusHP);
+ m_bonusHP = 0;
+ }
+ }
+
if (me->GetTypeId() == TYPEID_UNIT && me->ToCreature()->IsAIEnabled)
me->ToCreature()->AI()->PassengerBoarded(unit, seat->first, false);
diff --git a/src/server/game/Entities/Vehicle/Vehicle.h b/src/server/game/Entities/Vehicle/Vehicle.h
index 339ab1ad188..93464b3699e 100644
--- a/src/server/game/Entities/Vehicle/Vehicle.h
+++ b/src/server/game/Entities/Vehicle/Vehicle.h
@@ -46,8 +46,16 @@ struct VehicleAccessory
uint32 bMinion;
};
+struct VehicleScalingInfo
+{
+ uint32 ID;
+ float baseItemLevel;
+ float scalingFactor;
+};
+
typedef std::vector<VehicleAccessory> VehicleAccessoryList;
typedef std::map<uint32, VehicleAccessoryList> VehicleAccessoryMap;
+typedef std::map<uint32, VehicleScalingInfo> VehicleScalingMap;
typedef std::map<int8, VehicleSeat> SeatMap;
@@ -82,6 +90,7 @@ class Vehicle
Unit *me;
VehicleEntry const *m_vehicleInfo;
uint32 m_usableSeatNum;
+ uint32 m_bonusHP;
void InstallAccessory(uint32 entry, int8 seatId, bool minion = true);
};
diff --git a/src/server/game/Globals/ObjectMgr.cpp b/src/server/game/Globals/ObjectMgr.cpp
index 4ea4b1ca033..80dfedc357d 100644
--- a/src/server/game/Globals/ObjectMgr.cpp
+++ b/src/server/game/Globals/ObjectMgr.cpp
@@ -2647,6 +2647,51 @@ void ObjectMgr::LoadVehicleAccessories()
sLog.outString(">> Loaded %u Vehicle Accessories", count);
}
+void ObjectMgr::LoadVehicleScaling()
+{
+ m_VehicleScalingMap.clear(); // needed for reload case
+
+ uint32 count = 0;
+
+ QueryResult_AutoPtr result = WorldDatabase.Query("SELECT `entry`,`baseItemLevel`,`scalingFactor` FROM `vehicle_scaling_info`");
+
+ if (!result)
+ {
+ barGoLink bar(1);
+ bar.step();
+ sLog.outString();
+ sLog.outErrorDb(">> Loaded 0 vehicle scaling entries. DB table `vehicle_scaling_info` is empty.");
+ return;
+ }
+
+ barGoLink bar(result->GetRowCount());
+
+ do
+ {
+ Field *fields = result->Fetch();
+ bar.step();
+
+ uint32 vehicleEntry = fields[0].GetUInt32();
+ float baseItemLevel = fields[1].GetFloat();
+ float scalingFactor = fields[2].GetFloat();
+
+ if (!sVehicleStore.LookupEntry(vehicleEntry))
+ {
+ sLog.outErrorDb("Table `vehicle_scaling_info`: vehicle entry %u does not exist.", vehicleEntry);
+ continue;
+ }
+
+ m_VehicleScalingMap[vehicleEntry].ID = vehicleEntry;
+ m_VehicleScalingMap[vehicleEntry].baseItemLevel = baseItemLevel;
+ m_VehicleScalingMap[vehicleEntry].scalingFactor = scalingFactor;
+
+ ++count;
+ } while (result->NextRow());
+
+ sLog.outString();
+ sLog.outString(">> Loaded %u vehicle scaling entries.", count);
+}
+
void ObjectMgr::LoadPetLevelInfo()
{
// Loading levels data
diff --git a/src/server/game/Globals/ObjectMgr.h b/src/server/game/Globals/ObjectMgr.h
index 4394280625b..46b10e1b171 100644
--- a/src/server/game/Globals/ObjectMgr.h
+++ b/src/server/game/Globals/ObjectMgr.h
@@ -599,6 +599,14 @@ class ObjectMgr
return NULL;
}
+ VehicleScalingInfo const* GetVehicleScalingInfo(uint32 vehicleEntry) const
+ {
+ VehicleScalingMap::const_iterator itr = m_VehicleScalingMap.find(vehicleEntry);
+ if (itr != m_VehicleScalingMap.end())
+ return &itr->second;
+ return NULL;
+ }
+
void LoadGuilds();
void LoadArenaTeams();
void LoadGroups();
@@ -665,6 +673,7 @@ class ObjectMgr
void LoadInstanceTemplate();
void LoadMailLevelRewards();
void LoadVehicleAccessories();
+ void LoadVehicleScaling();
void LoadGossipText();
@@ -1056,6 +1065,7 @@ class ObjectMgr
ItemRequiredTargetMap m_ItemRequiredTarget;
VehicleAccessoryMap m_VehicleAccessoryMap;
+ VehicleScalingMap m_VehicleScalingMap;
typedef std::vector<LocaleConstant> LocalForIndex;
LocalForIndex m_LocalForIndex;
diff --git a/src/server/game/World/World.cpp b/src/server/game/World/World.cpp
index 0927794122b..64d4fd02c7d 100644
--- a/src/server/game/World/World.cpp
+++ b/src/server/game/World/World.cpp
@@ -1359,6 +1359,9 @@ void World::SetInitialWorldSettings()
sLog.outString("Loading Creature templates...");
sObjectMgr.LoadCreatureTemplates();
+ sLog.outString("Loading Vehicle scaling information...");
+ sObjectMgr.LoadVehicleScaling();
+
sLog.outString("Loading Reputation Reward Rates...");
sObjectMgr.LoadReputationRewardRate();