aboutsummaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
Diffstat (limited to 'src')
-rw-r--r--src/server/game/Entities/Unit/Unit.cpp49
-rw-r--r--src/server/game/Entities/Unit/Unit.h1
-rwxr-xr-xsrc/server/game/Entities/Vehicle/Vehicle.cpp9
-rw-r--r--src/server/game/Entities/Vehicle/Vehicle.h2
-rw-r--r--src/server/game/Spells/Auras/SpellAuraEffects.cpp7
5 files changed, 37 insertions, 31 deletions
diff --git a/src/server/game/Entities/Unit/Unit.cpp b/src/server/game/Entities/Unit/Unit.cpp
index 4ad2a06a61e..b62b5124987 100644
--- a/src/server/game/Entities/Unit/Unit.cpp
+++ b/src/server/game/Entities/Unit/Unit.cpp
@@ -16816,29 +16816,23 @@ void Unit::EnterVehicle(Unit* base, int8 seatId)
void Unit::_EnterVehicle(Vehicle* vehicle, int8 seatId, AuraApplication const* aurApp)
{
// Must be called only from aura handler
+ ASSERT(aurApp);
+
if (!isAlive() || GetVehicleKit() == vehicle || vehicle->GetBase()->IsOnVehicle(this))
return;
if (m_vehicle)
{
- if (m_vehicle == vehicle)
- {
- if (seatId >= 0 && seatId != GetTransSeat())
- {
- TC_LOG_DEBUG(LOG_FILTER_VEHICLES, "EnterVehicle: %u leave vehicle %u seat %d and enter %d.", GetEntry(), m_vehicle->GetBase()->GetEntry(), GetTransSeat(), seatId);
- ChangeSeat(seatId);
- }
-
- return;
- }
- else
+ if (m_vehicle != vehicle)
{
TC_LOG_DEBUG(LOG_FILTER_VEHICLES, "EnterVehicle: %u exit %u and enter %u.", GetEntry(), m_vehicle->GetBase()->GetEntry(), vehicle->GetBase()->GetEntry());
ExitVehicle();
}
+ else if (seatId >= 0 && seatId == GetTransSeat())
+ return;
}
- if (!aurApp || aurApp->GetRemoveMode())
+ if (aurApp->GetRemoveMode())
return;
if (Player* player = ToPlayer())
@@ -16868,16 +16862,22 @@ void Unit::ChangeSeat(int8 seatId, bool next)
if (seat == m_vehicle->Seats.end() || seat->second.Passenger)
return;
- // Todo: the functions below could be consolidated and refactored to take
- // SeatMap::const_iterator as parameter, to save redundant map lookups.
- m_vehicle->RemovePassenger(this);
+ AuraEffect* rideVehicleEffect = NULL;
+ AuraEffectList const& vehicleAuras = m_vehicle->GetBase()->GetAuraEffectsByType(SPELL_AURA_CONTROL_VEHICLE);
+ for (AuraEffectList::const_iterator itr = vehicleAuras.begin(); itr != vehicleAuras.end(); ++itr)
+ {
+ if ((*itr)->GetCasterGUID() != GetGUID())
+ continue;
+
+ // Make sure there is only one ride vehicle aura on target cast by the unit changing seat
+ ASSERT(!rideVehicleEffect);
+ rideVehicleEffect = *itr;
+ }
- // Set m_vehicle to NULL before adding passenger as adding new passengers is handled asynchronously
- // and someone may call ExitVehicle again before passenger is added to new seat
- Vehicle* veh = m_vehicle;
- m_vehicle = NULL;
- if (!veh->AddPassenger(this, seatId))
- ASSERT(false);
+ // Unit riding a vehicle must always have control vehicle aura on target
+ ASSERT(rideVehicleEffect);
+
+ rideVehicleEffect->ChangeAmount(seat->first + 1);
}
void Unit::ExitVehicle(Position const* /*exitPosition*/)
@@ -16907,7 +16907,8 @@ void Unit::_ExitVehicle(Position const* exitPosition)
if (!m_vehicle)
return;
- m_vehicle->RemovePassenger(this);
+ // This should be done before dismiss, because there may be some aura removal
+ Vehicle* vehicle = m_vehicle->RemovePassenger(this);
Player* player = ToPlayer();
@@ -16915,10 +16916,6 @@ void Unit::_ExitVehicle(Position const* exitPosition)
if (player && player->duel && player->duel->isMounted)
player->DuelComplete(DUEL_FLED);
- // This should be done before dismiss, because there may be some aura removal
- Vehicle* vehicle = m_vehicle;
- m_vehicle = NULL;
-
SetControlled(false, UNIT_STATE_ROOT); // SMSG_MOVE_FORCE_UNROOT, ~MOVEMENTFLAG_ROOT
Position pos;
diff --git a/src/server/game/Entities/Unit/Unit.h b/src/server/game/Entities/Unit/Unit.h
index 67a6fa2a994..c65f08ffa6f 100644
--- a/src/server/game/Entities/Unit/Unit.h
+++ b/src/server/game/Entities/Unit/Unit.h
@@ -2082,6 +2082,7 @@ class Unit : public WorldObject
void RemoveVehicleKit();
Vehicle* GetVehicleKit()const { return m_vehicleKit; }
Vehicle* GetVehicle() const { return m_vehicle; }
+ void SetVehicle(Vehicle* vehicle) { m_vehicle = vehicle; }
bool IsOnVehicle(const Unit* vehicle) const;
Unit* GetVehicleBase() const;
Creature* GetVehicleCreatureBase() const;
diff --git a/src/server/game/Entities/Vehicle/Vehicle.cpp b/src/server/game/Entities/Vehicle/Vehicle.cpp
index 86ea67c2d0f..5cfb9cc2fae 100755
--- a/src/server/game/Entities/Vehicle/Vehicle.cpp
+++ b/src/server/game/Entities/Vehicle/Vehicle.cpp
@@ -496,10 +496,10 @@ bool Vehicle::AddPassenger(Unit* unit, int8 seatId)
* @param [in, out] unit The passenger to remove.
*/
-void Vehicle::RemovePassenger(Unit* unit)
+Vehicle* Vehicle::RemovePassenger(Unit* unit)
{
if (unit->GetVehicle() != this)
- return;
+ return NULL;
SeatMap::iterator seat = GetSeatIteratorForPassenger(unit);
ASSERT(seat != Seats.end());
@@ -531,6 +531,9 @@ void Vehicle::RemovePassenger(Unit* unit)
if (GetBase()->GetTypeId() == TYPEID_UNIT)
sScriptMgr->OnRemovePassenger(this, unit);
+
+ unit->SetVehicle(NULL);
+ return this;
}
/**
@@ -801,7 +804,7 @@ bool VehicleJoinEvent::Execute(uint64, uint32)
Target->RemovePendingEventsForSeat(Seat->first);
- Passenger->m_vehicle = Target;
+ Passenger->SetVehicle(Target);
Seat->second.Passenger = Passenger->GetGUID();
if (Seat->second.SeatInfo->CanEnterOrExit())
{
diff --git a/src/server/game/Entities/Vehicle/Vehicle.h b/src/server/game/Entities/Vehicle/Vehicle.h
index c83a9fa5f33..9fb1b6614b5 100644
--- a/src/server/game/Entities/Vehicle/Vehicle.h
+++ b/src/server/game/Entities/Vehicle/Vehicle.h
@@ -59,7 +59,7 @@ class Vehicle : public TransportBase
bool AddPassenger(Unit* passenger, int8 seatId = -1);
void EjectPassenger(Unit* passenger, Unit* controller);
- void RemovePassenger(Unit* passenger);
+ Vehicle* RemovePassenger(Unit* passenger);
void RelocatePassengers();
void RemoveAllPassengers();
bool IsVehicleInUse() const;
diff --git a/src/server/game/Spells/Auras/SpellAuraEffects.cpp b/src/server/game/Spells/Auras/SpellAuraEffects.cpp
index b65213e134d..0f1950bc860 100644
--- a/src/server/game/Spells/Auras/SpellAuraEffects.cpp
+++ b/src/server/game/Spells/Auras/SpellAuraEffects.cpp
@@ -2926,7 +2926,12 @@ void AuraEffect::HandleAuraControlVehicle(AuraApplication const* aurApp, uint8 m
if (caster->GetTypeId() == TYPEID_UNIT)
caster->ToCreature()->RemoveCorpse();
}
- caster->_ExitVehicle();
+
+ if (!(mode & AURA_EFFECT_HANDLE_CHANGE_AMOUNT))
+ caster->_ExitVehicle();
+ else
+ target->GetVehicleKit()->RemovePassenger(caster); // Only remove passenger from vehicle without launching exit movement or despawning the vehicle
+
// some SPELL_AURA_CONTROL_VEHICLE auras have a dummy effect on the player - remove them
caster->RemoveAurasDueToSpell(GetId());
}