From 612411e492a50684e7b5e94b698ff49449311e6a Mon Sep 17 00:00:00 2001 From: Alexei Kotov Date: Tue, 4 Mar 2025 00:42:56 +0300 Subject: [PATCH] Allow non-actor spell projectiles to fire underwater (#8303) --- apps/openmw/mwworld/projectilemanager.cpp | 16 ++++++++++------ 1 file changed, 10 insertions(+), 6 deletions(-) diff --git a/apps/openmw/mwworld/projectilemanager.cpp b/apps/openmw/mwworld/projectilemanager.cpp index b019dabdfe..6ea510e1e2 100644 --- a/apps/openmw/mwworld/projectilemanager.cpp +++ b/apps/openmw/mwworld/projectilemanager.cpp @@ -274,8 +274,8 @@ namespace MWWorld pos.z() += mPhysics->getRenderingHalfExtents(caster).z() * 2 * Constants::TorsoHeight; } - if (MWBase::Environment::get().getWorld()->isUnderwater( - caster.getCell(), pos)) // Underwater casting not possible + // Actors can't cast target spells underwater + if (caster.getClass().isActor() && MWBase::Environment::get().getWorld()->isUnderwater(caster.getCell(), pos)) return; osg::Quat orient; @@ -564,15 +564,19 @@ namespace MWWorld for (const auto& sound : magicBoltState.mSounds) sound->setPosition(pos); - if (projectile->isActive()) + const Ptr caster = magicBoltState.getCaster(); + + const MWBase::World& world = *MWBase::Environment::get().getWorld(); + const bool active = projectile->isActive(); + if (active && !world.isUnderwater(caster.getCell(), pos)) continue; - const auto target = projectile->getTarget(); - const auto caster = magicBoltState.getCaster(); + const Ptr target = !active ? projectile->getTarget() : Ptr(); + assert(target != caster); MWMechanics::CastSpell cast(caster, target); - cast.mHitPosition = Misc::Convert::toOsg(projectile->getHitPosition()); + cast.mHitPosition = !active ? Misc::Convert::toOsg(projectile->getHitPosition()) : pos; cast.mId = magicBoltState.mSpellId; cast.mSourceName = magicBoltState.mSourceName; cast.mItem = magicBoltState.mItem;