diff options
Diffstat (limited to 'src')
-rwxr-xr-x | src/server/game/DataStores/DBCStructure.h | 2 | ||||
-rwxr-xr-x | src/server/game/Entities/Unit/Unit.cpp | 2 | ||||
-rwxr-xr-x | src/server/game/Entities/Vehicle/Vehicle.cpp | 20 | ||||
-rwxr-xr-x | src/server/game/Entities/Vehicle/Vehicle.h | 6 | ||||
-rwxr-xr-x | src/server/game/Server/Protocol/Handlers/MovementHandler.cpp | 25 |
5 files changed, 42 insertions, 13 deletions
diff --git a/src/server/game/DataStores/DBCStructure.h b/src/server/game/DataStores/DBCStructure.h index b748d4dad26..40d68a3ea3f 100755 --- a/src/server/game/DataStores/DBCStructure.h +++ b/src/server/game/DataStores/DBCStructure.h @@ -1847,7 +1847,7 @@ struct VehicleSeatEntry uint32 m_flagsB; // 45 // 46-57 added in 3.1, floats mostly - bool IsUsableByPlayer() const { return m_flags & VEHICLE_SEAT_FLAG_USABLE; } + bool CanEnterOrExit() const { return m_flags & VEHICLE_SEAT_FLAG_CAN_ENTER_OR_EXIT; } bool IsUsableByAura() const { return m_flagsB & (VEHICLE_SEAT_FLAG_B_USABLE_FORCED | VEHICLE_SEAT_FLAG_B_USABLE_FORCED_2 | VEHICLE_SEAT_FLAG_B_USABLE_FORCED_3); } bool IsEjectable() const { return m_flagsB & VEHICLE_SEAT_FLAG_B_EJECTABLE; } }; diff --git a/src/server/game/Entities/Unit/Unit.cpp b/src/server/game/Entities/Unit/Unit.cpp index dcaea3186cc..2cb5a214cba 100755 --- a/src/server/game/Entities/Unit/Unit.cpp +++ b/src/server/game/Entities/Unit/Unit.cpp @@ -16435,7 +16435,7 @@ void Unit::ExitVehicle() SetControlled(false, UNIT_STAT_ROOT); - RemoveUnitMovementFlag(MOVEMENTFLAG_ONTRANSPORT); + RemoveUnitMovementFlag(MOVEMENTFLAG_ONTRANSPORT | MOVEMENTFLAG_ROOT); m_movementInfo.t_pos.Relocate(0, 0, 0, 0); m_movementInfo.t_time = 0; m_movementInfo.t_seat = 0; diff --git a/src/server/game/Entities/Vehicle/Vehicle.cpp b/src/server/game/Entities/Vehicle/Vehicle.cpp index 9438d477d35..8a60d5e7562 100755 --- a/src/server/game/Entities/Vehicle/Vehicle.cpp +++ b/src/server/game/Entities/Vehicle/Vehicle.cpp @@ -35,7 +35,7 @@ Vehicle::Vehicle(Unit *unit, VehicleEntry const *vehInfo) : me(unit), m_vehicleI if (VehicleSeatEntry const *veSeat = sVehicleSeatStore.LookupEntry(seatId)) { m_Seats.insert(std::make_pair(i, VehicleSeat(veSeat))); - if (veSeat->IsUsableByPlayer()) + if (veSeat->CanEnterOrExit()) ++m_usableSeatNum; } } @@ -219,7 +219,7 @@ int8 Vehicle::GetNextEmptySeat(int8 seatId, bool next, bool byAura) const if (seat == m_Seats.end()) return -1; - while (seat->second.passenger || (!byAura && !seat->second.seatInfo->IsUsableByPlayer()) || (byAura && !seat->second.seatInfo->IsUsableByAura())) + while (seat->second.passenger || (!byAura && !seat->second.seatInfo->CanEnterOrExit()) || (byAura && !seat->second.seatInfo->IsUsableByAura())) { sLog->outDebug("Vehicle::GetNextEmptySeat: m_flags: %u, m_flagsB:%u", seat->second.seatInfo->m_flags, seat->second.seatInfo->m_flagsB); if (next) @@ -280,7 +280,7 @@ bool Vehicle::AddPassenger(Unit *unit, int8 seatId, bool byAura) if (seatId < 0) // no specific seat requirement { for (seat = m_Seats.begin(); seat != m_Seats.end(); ++seat) - if (!seat->second.passenger && ((!(byAura && seat->second.seatInfo->IsUsableByPlayer()) || (byAura && seat->second.seatInfo->IsUsableByAura())))) + if (!seat->second.passenger && ((!(byAura && seat->second.seatInfo->CanEnterOrExit()) || (byAura && seat->second.seatInfo->IsUsableByAura())))) break; if (seat == m_Seats.end()) // no available seat @@ -301,7 +301,7 @@ bool Vehicle::AddPassenger(Unit *unit, int8 seatId, bool byAura) sLog->outDebug("Unit %s enter vehicle entry %u id %u dbguid %u seat %d", unit->GetName(), me->GetEntry(), m_vehicleInfo->m_ID, me->GetGUIDLow(), (int32)seat->first); seat->second.passenger = unit; - if (seat->second.seatInfo->IsUsableByPlayer()) + if (seat->second.seatInfo->CanEnterOrExit()) { ASSERT(m_usableSeatNum); --m_usableSeatNum; @@ -384,7 +384,7 @@ void Vehicle::RemovePassenger(Unit *unit) sLog->outDebug("Unit %s exit vehicle entry %u id %u dbguid %u seat %d", unit->GetName(), me->GetEntry(), m_vehicleInfo->m_ID, me->GetGUIDLow(), (int32)seat->first); seat->second.passenger = NULL; - if (seat->second.seatInfo->IsUsableByPlayer()) + if (seat->second.seatInfo->CanEnterOrExit()) { if (!m_usableSeatNum) { @@ -479,4 +479,14 @@ uint16 Vehicle::GetExtraMovementFlagsForBase() const sLog->outDebug("Vehicle::GetExtraMovementFlagsForBase() returned %u", movementMask); return movementMask; +} + +VehicleSeatEntry const* Vehicle::GetSeatForPassenger(Unit* passenger) +{ + SeatMap::iterator itr; + for (itr = m_Seats.begin(); itr != m_Seats.end(); ++itr) + if (itr->second.passenger = passenger) + return itr->second.seatInfo; + + return NULL; }
\ No newline at end of file diff --git a/src/server/game/Entities/Vehicle/Vehicle.h b/src/server/game/Entities/Vehicle/Vehicle.h index c5198d698b4..a536df991ae 100755 --- a/src/server/game/Entities/Vehicle/Vehicle.h +++ b/src/server/game/Entities/Vehicle/Vehicle.h @@ -53,7 +53,7 @@ enum VehicleSeatFlags VEHICLE_SEAT_FLAG_UNK11 = 0x00000400, // needed for CGCamera__SyncFreeLookFacing VEHICLE_SEAT_FLAG_CAN_CONTROL = 0x00000800, // Lua_UnitInVehicleControlSeat VEHICLE_SEAT_FLAG_CAN_ATTACK = 0x00004000, // Can attack, cast spells and use items from vehicle? - VEHICLE_SEAT_FLAG_USABLE = 0x02000000, // Lua_CanExitVehicle + VEHICLE_SEAT_FLAG_CAN_ENTER_OR_EXIT = 0x02000000, // Lua_CanExitVehicle - can enter and exit at free will VEHICLE_SEAT_FLAG_CAN_SWITCH = 0x04000000, // Lua_CanSwitchVehicleSeats VEHICLE_SEAT_FLAG_CAN_CAST = 0x20000000, // Lua_UnitHasVehicleUI }; @@ -106,6 +106,7 @@ typedef std::map<int8, VehicleSeat> SeatMap; class Vehicle { friend class Unit; + friend class WorldSession; public: explicit Vehicle(Unit *unit, VehicleEntry const *vehInfo); @@ -135,7 +136,8 @@ class Vehicle SeatMap m_Seats; protected: - uint16 GetExtraMovementFlagsForBase() const; + uint16 GetExtraMovementFlagsForBase() const; + VehicleSeatEntry const* GetSeatForPassenger(Unit* passenger); protected: Unit *me; diff --git a/src/server/game/Server/Protocol/Handlers/MovementHandler.cpp b/src/server/game/Server/Protocol/Handlers/MovementHandler.cpp index 25cfed8e3f1..0cd943ef9e7 100755 --- a/src/server/game/Server/Protocol/Handlers/MovementHandler.cpp +++ b/src/server/game/Server/Protocol/Handlers/MovementHandler.cpp @@ -631,7 +631,11 @@ void WorldSession::HandleEjectPassenger(WorldPacket &data) if (IS_PLAYER_GUID(guid)) { if (Player *plr = ObjectAccessor::FindPlayer(guid)) - vehicle->EjectPassenger(plr, GetPlayer()); + { + VehicleSeatEntry const* seat = vehicle->GetSeatForPassenger(plr); + if (seat->IsEjectable()) + plr->ExitVehicle(); + } else sLog->outError("Player %u tried to eject player %u from vehicle, but the latter was not found in world!", GetPlayer()->GetGUIDLow(), GUID_LOPART(guid)); } @@ -640,8 +644,12 @@ void WorldSession::HandleEjectPassenger(WorldPacket &data) { if (Unit *unit = ObjectAccessor::GetUnit(*_player, guid)) // creatures can be ejected too from player mounts { - vehicle->EjectPassenger(unit, GetPlayer()); - unit->ToCreature()->ForcedDespawn(1000); + VehicleSeatEntry const* seat = vehicle->GetSeatForPassenger(unit); + if (seat->IsEjectable()) + { + unit->ExitVehicle(); + unit->ToCreature()->ForcedDespawn(1000); + } } else sLog->outError("Player %u tried to eject creature guid %u from vehicle, but the latter was not found in world!", GetPlayer()->GetGUIDLow(), GUID_LOPART(guid)); @@ -657,7 +665,16 @@ void WorldSession::HandleRequestVehicleExit(WorldPacket &recv_data) { sLog->outDebug("WORLD: Recvd CMSG_REQUEST_VEHICLE_EXIT"); recv_data.hexlike(); - GetPlayer()->ExitVehicle(); + + if (Vehicle* vehicle = GetPlayer()->GetVehicle()) + { + if (VehicleSeatEntry const* seat = vehicle->GetSeatForPassenger(GetPlayer())) + if (seat->CanEnterOrExit()) + GetPlayer()->ExitVehicle(); + else + sLog->outError("Player %u tried to exit vehicle, but seatflags %u (ID: %u) don't permit that.", + GetPlayer()->GetGUIDLow(), seat->m_ID, seat->m_flags); + } } void WorldSession::HandleMountSpecialAnimOpcode(WorldPacket& /*recv_data*/) |