forked from mirror/openmw-tes3mp
Merged pull request #1572
This commit is contained in:
commit
f62df90960
9 changed files with 108 additions and 64 deletions
42
.gitlab-ci.yml
Normal file
42
.gitlab-ci.yml
Normal file
|
@ -0,0 +1,42 @@
|
|||
# use the official gcc image, based on debian
|
||||
# can use verions as well, like gcc:5.2
|
||||
# see https://hub.docker.com/_/gcc/
|
||||
image: gcc
|
||||
|
||||
cache:
|
||||
key: apt-cache
|
||||
paths:
|
||||
- apt-cache/
|
||||
|
||||
before_script:
|
||||
- export APT_CACHE_DIR=`pwd`/apt-cache && mkdir -pv $APT_CACHE_DIR
|
||||
- apt-get update -yq
|
||||
- apt-get -o dir::cache::archives="$APT_CACHE_DIR" install -y cmake libboost-filesystem-dev libboost-program-options-dev libboost-system-dev libavcodec-dev libavformat-dev libavutil-dev libswscale-dev libswresample-dev libsdl2-dev libqt4-dev libopenal-dev libopenscenegraph-3.4-dev libunshield-dev libtinyxml-dev
|
||||
# - apt-get install -y libmygui-dev libbullet-dev # to be updated to latest below because stretch is too old
|
||||
- curl http://ftp.us.debian.org/debian/pool/main/b/bullet/libbullet-dev_2.87+dfsg-2_amd64.deb -o libbullet-dev_2.87+dfsg-2_amd64.deb
|
||||
- curl http://ftp.us.debian.org/debian/pool/main/b/bullet/libbullet2.87_2.87+dfsg-2_amd64.deb -o libbullet2.87_2.87+dfsg-2_amd64.deb
|
||||
- curl http://ftp.us.debian.org/debian/pool/main/m/mygui/libmygui.openglplatform0debian1v5_3.2.2+dfsg-1_amd64.deb -o libmygui.openglplatform0debian1v5_3.2.2+dfsg-1_amd64.deb
|
||||
- curl http://ftp.us.debian.org/debian/pool/main/m/mygui/libmyguiengine3debian1v5_3.2.2+dfsg-1_amd64.deb -o libmyguiengine3debian1v5_3.2.2+dfsg-1_amd64.deb
|
||||
- curl http://ftp.us.debian.org/debian/pool/main/m/mygui/libmygui-dev_3.2.2+dfsg-1_amd64.deb -o libmygui-dev_3.2.2+dfsg-1_amd64.deb
|
||||
- dpkg --ignore-depends=libmygui.ogreplatform0debian1v5 -i *.deb
|
||||
|
||||
build:
|
||||
stage: build
|
||||
script:
|
||||
- nproc
|
||||
- mkdir build; cd build; cmake -DCMAKE_BUILD_TYPE=MinSizeRel ../
|
||||
- make -j2
|
||||
- DESTDIR=artifacts make install
|
||||
artifacts:
|
||||
paths:
|
||||
- build/artifacts/
|
||||
# depending on your build setup it's most likely a good idea to cache outputs to reduce the build time
|
||||
cache:
|
||||
paths:
|
||||
- "*.o"
|
||||
|
||||
# run tests using the binary built before
|
||||
test:
|
||||
stage: test
|
||||
script:
|
||||
- ls
|
|
@ -24,6 +24,7 @@
|
|||
Bug #4429: [Windows] Error on build INSTALL.vcxproj project (debug) with cmake 3.7.2
|
||||
Bug #4432: Guards behaviour is incorrect if they do not have AI packages
|
||||
Bug #4433: Guard behaviour is incorrect with Alarm = 0
|
||||
Bug #4454: AI opens doors too slow
|
||||
Feature #3276: Editor: Search- Show number of (remaining) search results and indicate a search without any results
|
||||
Feature #4324: Add CFBundleIdentifier in Info.plist to allow for macOS function key shortcuts
|
||||
Feature #4345: Add equivalents for the command line commands to Launcher
|
||||
|
|
|
@ -139,24 +139,21 @@ namespace MWClass
|
|||
const std::string trapActivationSound = "Disarm Trap Fail";
|
||||
|
||||
MWWorld::Ptr player = MWBase::Environment::get().getWorld ()->getPlayerPtr();
|
||||
const MWWorld::InventoryStore& invStore = player.getClass().getInventoryStore(player);
|
||||
MWWorld::InventoryStore& invStore = player.getClass().getInventoryStore(player);
|
||||
|
||||
bool isLocked = ptr.getCellRef().getLockLevel() > 0;
|
||||
bool isTrapped = !ptr.getCellRef().getTrap().empty();
|
||||
bool hasKey = false;
|
||||
std::string keyName;
|
||||
|
||||
// make key id lowercase
|
||||
std::string keyId = ptr.getCellRef().getKey();
|
||||
Misc::StringUtils::lowerCaseInPlace(keyId);
|
||||
for (MWWorld::ConstContainerStoreIterator it = invStore.cbegin(); it != invStore.cend(); ++it)
|
||||
const std::string keyId = ptr.getCellRef().getKey();
|
||||
if (!keyId.empty())
|
||||
{
|
||||
std::string refId = it->getCellRef().getRefId();
|
||||
Misc::StringUtils::lowerCaseInPlace(refId);
|
||||
if (refId == keyId)
|
||||
MWWorld::Ptr keyPtr = invStore.search(keyId);
|
||||
if (!keyPtr.isEmpty())
|
||||
{
|
||||
hasKey = true;
|
||||
keyName = it->getClass().getName(*it);
|
||||
keyName = keyPtr.getClass().getName(keyPtr);
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
@ -114,7 +114,7 @@ namespace MWClass
|
|||
const std::string lockedSound = "LockedDoor";
|
||||
const std::string trapActivationSound = "Disarm Trap Fail";
|
||||
|
||||
const MWWorld::ContainerStore &invStore = actor.getClass().getContainerStore(actor);
|
||||
MWWorld::ContainerStore &invStore = actor.getClass().getContainerStore(actor);
|
||||
|
||||
bool isLocked = ptr.getCellRef().getLockLevel() > 0;
|
||||
bool isTrapped = !ptr.getCellRef().getTrap().empty();
|
||||
|
@ -135,21 +135,14 @@ namespace MWClass
|
|||
animation->addSpellCastGlow(effect, 1); // 1 second glow to match the time taken for a door opening or closing
|
||||
}
|
||||
|
||||
// make key id lowercase
|
||||
std::string keyId = ptr.getCellRef().getKey();
|
||||
const std::string keyId = ptr.getCellRef().getKey();
|
||||
if (!keyId.empty())
|
||||
{
|
||||
Misc::StringUtils::lowerCaseInPlace(keyId);
|
||||
for (MWWorld::ConstContainerStoreIterator it = invStore.cbegin(); it != invStore.cend(); ++it)
|
||||
{
|
||||
std::string refId = it->getCellRef().getRefId();
|
||||
Misc::StringUtils::lowerCaseInPlace(refId);
|
||||
if (refId == keyId)
|
||||
MWWorld::Ptr keyPtr = invStore.search(keyId);
|
||||
if (!keyPtr.isEmpty())
|
||||
{
|
||||
hasKey = true;
|
||||
keyName = it->getClass().getName(*it);
|
||||
break;
|
||||
}
|
||||
keyName = keyPtr.getClass().getName(keyPtr);
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
@ -120,6 +120,9 @@ bool MWMechanics::AiPackage::pathTo(const MWWorld::Ptr& actor, const ESM::Pathgr
|
|||
|
||||
if (!isDestReached && mTimer > AI_REACTION_TIME)
|
||||
{
|
||||
if (actor.getClass().isBipedal(actor))
|
||||
openDoors(actor);
|
||||
|
||||
bool wasShortcutting = mIsShortcutting;
|
||||
bool destInLOS = false;
|
||||
|
||||
|
@ -209,9 +212,25 @@ void MWMechanics::AiPackage::evadeObstacles(const MWWorld::Ptr& actor, float dur
|
|||
// first check if obstacle is a door
|
||||
static float distance = MWBase::Environment::get().getWorld()->getMaxActivationDistance();
|
||||
|
||||
MWWorld::Ptr door = getNearbyDoor(actor, distance);
|
||||
if (door != MWWorld::Ptr() && actor.getClass().isBipedal(actor))
|
||||
const MWWorld::Ptr door = getNearbyDoor(actor, distance);
|
||||
if (!door.isEmpty() && actor.getClass().isBipedal(actor))
|
||||
{
|
||||
openDoors(actor);
|
||||
}
|
||||
else
|
||||
{
|
||||
mObstacleCheck.takeEvasiveAction(movement);
|
||||
}
|
||||
}
|
||||
|
||||
void MWMechanics::AiPackage::openDoors(const MWWorld::Ptr& actor)
|
||||
{
|
||||
static float distance = MWBase::Environment::get().getWorld()->getMaxActivationDistance();
|
||||
|
||||
const MWWorld::Ptr door = getNearbyDoor(actor, distance);
|
||||
if (door == MWWorld::Ptr())
|
||||
return;
|
||||
|
||||
// note: AiWander currently does not open doors
|
||||
if (getTypeId() != TypeIdWander && !door.getCellRef().getTeleport() && door.getClass().getDoorState(door) == 0)
|
||||
{
|
||||
|
@ -221,34 +240,16 @@ void MWMechanics::AiPackage::evadeObstacles(const MWWorld::Ptr& actor, float dur
|
|||
return;
|
||||
}
|
||||
|
||||
std::string keyId = door.getCellRef().getKey();
|
||||
const std::string keyId = door.getCellRef().getKey();
|
||||
if (keyId.empty())
|
||||
return;
|
||||
|
||||
bool hasKey = false;
|
||||
const MWWorld::ContainerStore &invStore = actor.getClass().getContainerStore(actor);
|
||||
MWWorld::ContainerStore &invStore = actor.getClass().getContainerStore(actor);
|
||||
MWWorld::Ptr keyPtr = invStore.search(keyId);
|
||||
|
||||
// make key id lowercase
|
||||
Misc::StringUtils::lowerCaseInPlace(keyId);
|
||||
for (MWWorld::ConstContainerStoreIterator it = invStore.cbegin(); it != invStore.cend(); ++it)
|
||||
{
|
||||
std::string refId = it->getCellRef().getRefId();
|
||||
Misc::StringUtils::lowerCaseInPlace(refId);
|
||||
if (refId == keyId)
|
||||
{
|
||||
hasKey = true;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
if (hasKey)
|
||||
if (!keyPtr.isEmpty())
|
||||
MWBase::Environment::get().getWorld()->activate(door, actor);
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
mObstacleCheck.takeEvasiveAction(movement);
|
||||
}
|
||||
}
|
||||
|
||||
const MWMechanics::PathgridGraph& MWMechanics::AiPackage::getPathGridGraph(const MWWorld::CellStore *cell)
|
||||
|
|
|
@ -123,6 +123,7 @@ namespace MWMechanics
|
|||
virtual bool doesPathNeedRecalc(const ESM::Pathgrid::Point& newDest, const MWWorld::CellStore* currentCell);
|
||||
|
||||
void evadeObstacles(const MWWorld::Ptr& actor, float duration, const ESM::Position& pos);
|
||||
void openDoors(const MWWorld::Ptr& actor);
|
||||
|
||||
const PathgridGraph& getPathGridGraph(const MWWorld::CellStore* cell);
|
||||
|
||||
|
|
|
@ -26,13 +26,13 @@ namespace MWMechanics
|
|||
|
||||
bool proximityToDoor(const MWWorld::Ptr& actor, float minDist)
|
||||
{
|
||||
if(getNearbyDoor(actor, minDist)!=MWWorld::Ptr())
|
||||
return true;
|
||||
else
|
||||
if(getNearbyDoor(actor, minDist).isEmpty())
|
||||
return false;
|
||||
else
|
||||
return true;
|
||||
}
|
||||
|
||||
MWWorld::Ptr getNearbyDoor(const MWWorld::Ptr& actor, float minDist)
|
||||
const MWWorld::Ptr getNearbyDoor(const MWWorld::Ptr& actor, float minDist)
|
||||
{
|
||||
MWWorld::CellStore *cell = actor.getCell();
|
||||
|
||||
|
@ -50,6 +50,16 @@ namespace MWMechanics
|
|||
const MWWorld::LiveCellRef<ESM::Door>& ref = *it;
|
||||
|
||||
osg::Vec3f doorPos(ref.mData.getPosition().asVec3());
|
||||
|
||||
// FIXME: cast
|
||||
const MWWorld::Ptr doorPtr = MWWorld::Ptr(&const_cast<MWWorld::LiveCellRef<ESM::Door> &>(ref), actor.getCell());
|
||||
|
||||
int doorState = doorPtr.getClass().getDoorState(doorPtr);
|
||||
float doorRot = ref.mData.getPosition().rot[2] - doorPtr.getCellRef().getPosition().rot[2];
|
||||
|
||||
if (doorState != 0 || doorRot != 0)
|
||||
continue; // the door is already opened/opening
|
||||
|
||||
doorPos.z() = 0;
|
||||
|
||||
float angle = std::acos(actorDir * (doorPos - pos) / (actorDir.length() * (doorPos - pos).length()));
|
||||
|
@ -62,8 +72,7 @@ namespace MWMechanics
|
|||
if ((pos - doorPos).length2() > minDist*minDist)
|
||||
continue;
|
||||
|
||||
// FIXME cast
|
||||
return MWWorld::Ptr(&const_cast<MWWorld::LiveCellRef<ESM::Door> &>(ref), actor.getCell()); // found, stop searching
|
||||
return doorPtr; // found, stop searching
|
||||
}
|
||||
|
||||
return MWWorld::Ptr(); // none found
|
||||
|
|
|
@ -17,7 +17,7 @@ namespace MWMechanics
|
|||
|
||||
/// Returns door pointer within range. No guarantee is given as to which one
|
||||
/** \return Pointer to the door, or NULL if none exists **/
|
||||
MWWorld::Ptr getNearbyDoor(const MWWorld::Ptr& actor, float minDist);
|
||||
const MWWorld::Ptr getNearbyDoor(const MWWorld::Ptr& actor, float minDist);
|
||||
|
||||
class ObstacleCheck
|
||||
{
|
||||
|
|
|
@ -47,7 +47,7 @@ namespace
|
|||
for (typename MWWorld::CellRefList<T>::List::iterator iter (list.mList.begin());
|
||||
iter!=list.mList.end(); ++iter)
|
||||
{
|
||||
if (Misc::StringUtils::ciEqual(iter->mBase->mId, id2))
|
||||
if (Misc::StringUtils::ciEqual(iter->mBase->mId, id2) && iter->mData.getCount())
|
||||
{
|
||||
MWWorld::Ptr ptr (&*iter, 0);
|
||||
ptr.setContainerStore (store);
|
||||
|
|
Loading…
Reference in a new issue