PVS and DCLN bug fixes

This commit is contained in:
Jack Andersen 2018-06-27 20:47:34 -10:00
parent 680cb7b353
commit 3a9e7b2f9b
14 changed files with 44 additions and 44 deletions

View File

@ -337,7 +337,7 @@ bool MREA::Extract(const SpecBase& dataSpec,
for (int i=0 ; i<entityCount ; ++i) for (int i=0 ; i<entityCount ; ++i)
{ {
uint32_t entityId = rs.readUint32Big(); uint32_t entityId = rs.readUint32Big();
visiWriter.writeUint16(nullptr, entityId & 0xffff); visiWriter.writeUint32(nullptr, entityId);
} }
} }
hecl::ProjectPath visiMetadataPath(outPath.getParentPath(), _S("!visi.yaml")); hecl::ProjectPath visiMetadataPath(outPath.getParentPath(), _S("!visi.yaml"));
@ -681,12 +681,12 @@ bool MREA::Cook(const hecl::ProjectPath& outPath,
entities.reserve(entityCount); entities.reserve(entityCount);
for (size_t i=0 ; i<entityCount ; ++i) for (size_t i=0 ; i<entityCount ; ++i)
{ {
uint16_t entityId = r.readUint16(nullptr); uint32_t entityId = r.readUint32(nullptr);
for (const SCLY::ScriptLayer& layer : sclyData.layers) for (const SCLY::ScriptLayer& layer : sclyData.layers)
{ {
for (const std::unique_ptr<IScriptObject>& obj : layer.objects) for (const std::unique_ptr<IScriptObject>& obj : layer.objects)
{ {
if ((obj->id & 0xffff) == entityId) if ((obj->id & ~0x03FF0000) == entityId)
{ {
zeus::CAABox entAABB = obj->getVISIAABB(btok); zeus::CAABox entAABB = obj->getVISIAABB(btok);
if (!entAABB.invalid()) if (!entAABB.invalid())

View File

@ -32,7 +32,7 @@ struct CameraHint : IScriptObject
Value<bool> hintDistanceSelfPos; // 0x100 Value<bool> hintDistanceSelfPos; // 0x100
Value<bool> controlInterpolation; // 0x200 Value<bool> controlInterpolation; // 0x200
Value<bool> sinusoidalInterpolation; // 0x400 Value<bool> sinusoidalInterpolation; // 0x400
Value<bool> unknown12; // 0x800 Value<bool> sinusoidalInterpolationHintless; // 0x800
Value<bool> clampVelocity; // 0x1000 Value<bool> clampVelocity; // 0x1000
Value<bool> skipCinematic; // 0x2000 Value<bool> skipCinematic; // 0x2000
Value<bool> noElevationInterp; // 0x4000 Value<bool> noElevationInterp; // 0x4000

View File

@ -231,7 +231,6 @@ void CCameraManager::RestoreHintlessCamera(CStateManager& mgr)
TCastToPtr<CScriptCameraHint> hint = mgr.ObjectById(xa6_camHintId); TCastToPtr<CScriptCameraHint> hint = mgr.ObjectById(xa6_camHintId);
zeus::CTransform ballCamXf = x80_ballCamera->GetTransform(); zeus::CTransform ballCamXf = x80_ballCamera->GetTransform();
xa6_camHintId = kInvalidUniqueId; xa6_camHintId = kInvalidUniqueId;
printf("Setting NULL\n");
xa8_hintPriority = 1000; xa8_hintPriority = 1000;
if (hint) if (hint)
{ {
@ -285,7 +284,6 @@ void CCameraManager::ApplyCameraHint(const CScriptCameraHint& hint, CStateManage
TCastToPtr<CScriptCameraHint> oldHint = mgr.ObjectById(xa6_camHintId); TCastToPtr<CScriptCameraHint> oldHint = mgr.ObjectById(xa6_camHintId);
xa6_camHintId = hint.GetUniqueId(); xa6_camHintId = hint.GetUniqueId();
printf("Setting %08X %s\n", hint.GetEditorId().id, hint.GetName().data());
xa8_hintPriority = hint.GetPriority(); xa8_hintPriority = hint.GetPriority();
zeus::CTransform camXf = GetCurrentCameraTransform(mgr); zeus::CTransform camXf = GetCurrentCameraTransform(mgr);
@ -350,7 +348,6 @@ void CCameraManager::UpdateCameraHints(float, CStateManager& mgr)
{ {
if (it->second == id) if (it->second == id)
{ {
printf("ERASE %08X %s\n", hint->GetEditorId().id, hint->GetName().data());
xac_cameraHints.erase(it); xac_cameraHints.erase(it);
if (xa6_camHintId == id) if (xa6_camHintId == id)
{ {
@ -779,10 +776,7 @@ void CCameraManager::DeleteCameraHint(TUniqueId id, CStateManager& mgr)
hint->ClearIdList(); hint->ClearIdList();
hint->SetInactive(true); hint->SetInactive(true);
if (x2b0_inactiveCameraHints.size() != 64) if (x2b0_inactiveCameraHints.size() != 64)
{
x2b0_inactiveCameraHints.push_back(id); x2b0_inactiveCameraHints.push_back(id);
printf("Delete %08X %s\n", hint->GetEditorId().id, hint->GetName().data());
}
} }
} }
} }
@ -795,10 +789,7 @@ void CCameraManager::AddInactiveCameraHint(TUniqueId id, CStateManager& mgr)
[id](TUniqueId tid) { return tid == id; }); [id](TUniqueId tid) { return tid == id; });
if (search == x2b0_inactiveCameraHints.end() && if (search == x2b0_inactiveCameraHints.end() &&
x2b0_inactiveCameraHints.size() != 64) x2b0_inactiveCameraHints.size() != 64)
{
x2b0_inactiveCameraHints.push_back(id); x2b0_inactiveCameraHints.push_back(id);
printf("Inactive %08X %s\n", hint->GetEditorId().id, hint->GetName().data());
}
} }
} }
@ -810,10 +801,7 @@ void CCameraManager::AddActiveCameraHint(TUniqueId id, CStateManager& mgr)
[id](TUniqueId tid) { return tid == id; }); [id](TUniqueId tid) { return tid == id; });
if (search == x334_activeCameraHints.end() && xac_cameraHints.size() != 64 && if (search == x334_activeCameraHints.end() && xac_cameraHints.size() != 64 &&
x334_activeCameraHints.size() != 64) x334_activeCameraHints.size() != 64)
{
x334_activeCameraHints.push_back(id); x334_activeCameraHints.push_back(id);
printf("Active %08X %s\n", hint->GetEditorId().id, hint->GetName().data());
}
} }
} }

View File

@ -204,7 +204,7 @@ zeus::CVector3f CGameCollision::GetActorRelativeVelocities(const CPhysicsActor&
if (TCastToConstPtr<CScriptPlatform> plat = act1) if (TCastToConstPtr<CScriptPlatform> plat = act1)
rider = plat->IsRider(act0.GetUniqueId()); rider = plat->IsRider(act0.GetUniqueId());
if (!rider) if (!rider)
ret =- act1->GetVelocity(); ret -= act1->GetVelocity();
} }
return ret; return ret;
} }
@ -1035,6 +1035,7 @@ CGameCollision::FindNonIntersectingVector(const CStateManager& mgr, CAreaCollisi
const rstl::reserved_vector<TUniqueId, 1024>& nearList) const rstl::reserved_vector<TUniqueId, 1024>& nearList)
{ {
zeus::CTransform xf = actor.GetPrimitiveTransform(); zeus::CTransform xf = actor.GetPrimitiveTransform();
zeus::CVector3f origOrigin = xf.origin;
zeus::CVector3f center = prim.CalculateAABox(xf).center(); zeus::CVector3f center = prim.CalculateAABox(xf).center();
for (int i=2 ; i<1000 ; i+=(i/2)) for (int i=2 ; i<1000 ; i+=(i/2))
{ {
@ -1126,12 +1127,13 @@ CGameCollision::FindNonIntersectingVector(const CStateManager& mgr, CAreaCollisi
default: break; default: break;
} }
zeus::CVector3f worldPoint = vec + xf.origin; zeus::CVector3f worldPoint = vec + origOrigin;
if (mgr.GetWorld()->GetAreaAlways(mgr.GetNextAreaId())->GetAABB().pointInside(worldPoint)) if (mgr.GetWorld()->GetAreaAlways(mgr.GetNextAreaId())->GetAABB().pointInside(worldPoint))
{ {
if (mgr.RayCollideWorld(center, center + vec, nearList, if (mgr.RayCollideWorld(center, center + vec, nearList,
CMaterialFilter::skPassEverything, &actor)) CMaterialFilter::skPassEverything, &actor))
{ {
xf.origin = worldPoint;
if (!DetectCollisionBoolean_Cached(mgr, cache, prim, xf, actor.GetMaterialFilter(), nearList)) if (!DetectCollisionBoolean_Cached(mgr, cache, prim, xf, actor.GetMaterialFilter(), nearList))
return {vec}; return {vec};
} }

View File

@ -82,15 +82,15 @@ void COBBTree::GetTriangleVertexIndices(u16 idx, u16 indicesOut[3]) const
CCollisionSurface COBBTree::GetTransformedSurface(u16 idx, const zeus::CTransform& xf) const CCollisionSurface COBBTree::GetTransformedSurface(u16 idx, const zeus::CTransform& xf) const
{ {
u32 surfIdx = idx * 3; int surfIdx = idx * 3;
CCollisionEdge edge1 = x18_indexData.x40_edges[x18_indexData.x50_surfaceIndices[surfIdx]]; CCollisionEdge e0 = x18_indexData.x40_edges[x18_indexData.x50_surfaceIndices[surfIdx]];
CCollisionEdge edge2 = x18_indexData.x40_edges[x18_indexData.x50_surfaceIndices[surfIdx + 1]]; CCollisionEdge e1 = x18_indexData.x40_edges[x18_indexData.x50_surfaceIndices[surfIdx + 1]];
u16 vert1 = edge2.GetVertIndex1(); u16 vert1 = e0.GetVertIndex1();
u16 vert2 = edge2.GetVertIndex2(); u16 vert2 = e0.GetVertIndex2();
u16 vert3 = edge1.GetVertIndex1(); u16 vert3 = e1.GetVertIndex1();
if (vert3 == vert1 || vert3 == edge2.GetVertIndex2()) if (vert3 == vert1 || vert3 == vert2)
vert3 = edge1.GetVertIndex2(); vert3 = e1.GetVertIndex2();
u32 mat = x18_indexData.x0_materials[x18_indexData.x30_surfaceMaterials[idx]]; u32 mat = x18_indexData.x0_materials[x18_indexData.x30_surfaceMaterials[idx]];

View File

@ -12,8 +12,10 @@ CPVSAreaSet::CPVSAreaSet(const u8* data, u32 len)
xc_numActors = r.readUint32Big(); xc_numActors = r.readUint32Big();
x10_leafSize = r.readUint32Big(); x10_leafSize = r.readUint32Big();
x14_lightIndexCount = r.readUint32Big(); x14_lightIndexCount = r.readUint32Big();
x18_entityIndex = data + r.position(); x18_entityIndex.reserve(xc_numActors);
x1c_lightLeaves = x18_entityIndex + xc_numActors * 4; for (int i=0 ; i<xc_numActors ; ++i)
x18_entityIndex.push_back(r.readUint32Big());
x1c_lightLeaves = data + r.position();
const u8* octreeData = x1c_lightLeaves + x14_lightIndexCount * x10_leafSize; const u8* octreeData = x1c_lightLeaves + x14_lightIndexCount * x10_leafSize;
x20_octree = CPVSVisOctree::MakePVSVisOctree(octreeData); x20_octree = CPVSVisOctree::MakePVSVisOctree(octreeData);
} }

View File

@ -15,14 +15,14 @@ class CPVSAreaSet
u32 xc_numActors; u32 xc_numActors;
u32 x10_leafSize; u32 x10_leafSize;
u32 x14_lightIndexCount; u32 x14_lightIndexCount;
const u8* x18_entityIndex; std::vector<u32> x18_entityIndex;
const u8* x1c_lightLeaves; const u8* x1c_lightLeaves;
CPVSVisOctree x20_octree; CPVSVisOctree x20_octree;
CPVSVisSet _GetLightSet(u32 lightIdx) const CPVSVisSet _GetLightSet(u32 lightIdx) const
{ {
CPVSVisSet ret; CPVSVisSet ret;
ret.SetFromMemory(x20_octree.GetTotalBits(), x20_octree.GetLightBits(), ret.SetFromMemory(x20_octree.GetNumObjects(), x20_octree.GetNumLights(),
x1c_lightLeaves + x10_leafSize * lightIdx); x1c_lightLeaves + x10_leafSize * lightIdx);
return ret; return ret;
} }

View File

@ -7,14 +7,14 @@ CPVSVisOctree CPVSVisOctree::MakePVSVisOctree(const u8* data)
{ {
CMemoryInStream r(data, 68); CMemoryInStream r(data, 68);
zeus::CAABox aabb = aabb.ReadBoundingBoxBig(r); zeus::CAABox aabb = aabb.ReadBoundingBoxBig(r);
u32 a = r.readUint32Big(); u32 numObjects = r.readUint32Big();
u32 b = r.readUint32Big(); u32 numLights = r.readUint32Big();
r.readUint32Big(); r.readUint32Big();
return CPVSVisOctree(aabb, a, b, data + r.position()); return CPVSVisOctree(aabb, numObjects, numLights, data + r.position());
} }
CPVSVisOctree::CPVSVisOctree(const zeus::CAABox& aabb, u32 a, u32 b, const u8* c) CPVSVisOctree::CPVSVisOctree(const zeus::CAABox& aabb, u32 numObjects, u32 numLights, const u8* c)
: x0_aabb(aabb), x18_totalBits(a), x1c_lightBits(b), x20_bufferFlag(c != nullptr), x24_octreeData(c) : x0_aabb(aabb), x18_numObjects(numObjects), x1c_numLights(numLights), x20_bufferFlag(c != nullptr), x24_octreeData(c)
{ {
x2c_searchAabb = x0_aabb; x2c_searchAabb = x0_aabb;
x20_bufferFlag = 0; x20_bufferFlag = 0;

View File

@ -11,22 +11,22 @@ namespace urde
class CPVSVisOctree class CPVSVisOctree
{ {
zeus::CAABox x0_aabb; zeus::CAABox x0_aabb;
u32 x18_totalBits; u32 x18_numObjects;
u32 x1c_lightBits; u32 x1c_numLights;
bool x20_bufferFlag; bool x20_bufferFlag;
const u8* x24_octreeData; const u8* x24_octreeData;
zeus::CAABox x2c_searchAabb; zeus::CAABox x2c_searchAabb;
public: public:
static CPVSVisOctree MakePVSVisOctree(const u8* data); static CPVSVisOctree MakePVSVisOctree(const u8* data);
CPVSVisOctree() = default; CPVSVisOctree() = default;
CPVSVisOctree(const zeus::CAABox& aabb, u32 a, u32 b, const u8* c); CPVSVisOctree(const zeus::CAABox& aabb, u32 numObjects, u32 numLights, const u8* c);
u32 GetNumChildren(u8 byte) const; u32 GetNumChildren(u8 byte) const;
u32 GetChildIndex(const u8*, const zeus::CVector3f&) const; u32 GetChildIndex(const u8*, const zeus::CVector3f&) const;
const zeus::CAABox& GetBounds() const { return x0_aabb; } const zeus::CAABox& GetBounds() const { return x0_aabb; }
const u8* GetOctreeData() const { return x24_octreeData; } const u8* GetOctreeData() const { return x24_octreeData; }
u32 GetTotalBits() const { return x18_totalBits; } u32 GetNumObjects() const { return x18_numObjects; }
u32 GetLightBits() const { return x1c_lightBits; } u32 GetNumLights() const { return x1c_numLights; }
void ResetSearch() const { const_cast<CPVSVisOctree&>(*this).x2c_searchAabb = x0_aabb; } void ResetSearch() const { const_cast<CPVSVisOctree&>(*this).x2c_searchAabb = x0_aabb; }
s32 IterateSearch(u8 nodeData, const zeus::CVector3f& tp) const; s32 IterateSearch(u8 nodeData, const zeus::CVector3f& tp) const;
}; };

View File

@ -95,7 +95,7 @@ void CPVSVisSet::SetTestPoint(const CPVSVisOctree& octree, const zeus::CVector3f
switch (curNode & 0x18) switch (curNode & 0x18)
{ {
case 0x18: case 0x18:
SetFromMemory(octree.GetTotalBits(), octree.GetLightBits(), octCur); SetFromMemory(octree.GetNumObjects(), octree.GetNumLights(), octCur);
break; break;
case 0x10: case 0x10:
Reset(EPVSVisSetState::EndOfTree); Reset(EPVSVisSetState::EndOfTree);

View File

@ -1040,7 +1040,7 @@ void CGameArea::Validate(CStateManager& mgr)
LoadScriptObjects(mgr); LoadScriptObjects(mgr);
CPVSAreaSet* pvs = x12c_postConstructed->xa0_pvs.get(); CPVSAreaSet* pvs = x12c_postConstructed->xa0_pvs.get();
if (pvs && x12c_postConstructed->x1108_29_) if (pvs && x12c_postConstructed->x1108_29_pvsHasActors)
{ {
for (int i=0 ; i<pvs->GetNumActors() ; ++i) for (int i=0 ; i<pvs->GetNumActors() ; ++i)
{ {
@ -1168,7 +1168,7 @@ void CGameArea::PostConstructArea()
x12c_postConstructed->x10a8_pvsVersion = r.readUint32Big(); x12c_postConstructed->x10a8_pvsVersion = r.readUint32Big();
if (x12c_postConstructed->x10a8_pvsVersion == 2) if (x12c_postConstructed->x10a8_pvsVersion == 2)
{ {
x12c_postConstructed->x1108_29_ = r.readBool(); x12c_postConstructed->x1108_29_pvsHasActors = r.readBool();
x12c_postConstructed->x1108_30_ = r.readBool(); x12c_postConstructed->x1108_30_ = r.readBool();
x12c_postConstructed->xa0_pvs = std::make_unique<CPVSAreaSet>(secIt->first + r.position(), x12c_postConstructed->xa0_pvs = std::make_unique<CPVSAreaSet>(secIt->first + r.position(),
secIt->second - r.position()); secIt->second - r.position());

View File

@ -246,7 +246,7 @@ public:
bool x1108_26_ : 1; bool x1108_26_ : 1;
bool x1108_27_ : 1; bool x1108_27_ : 1;
bool x1108_28_occlusionPinged : 1; bool x1108_28_occlusionPinged : 1;
bool x1108_29_ : 1; bool x1108_29_pvsHasActors : 1;
bool x1108_30_ : 1; bool x1108_30_ : 1;
}; };
u32 _dummy = 0; u32 _dummy = 0;

View File

@ -406,6 +406,13 @@ void CScriptDoor::SetDoorAnimation(CScriptDoor::EDoorAnimType type)
modelData->AnimationData()->SetAnimation(CAnimPlaybackParms(s32(type), -1, 1.f, true), false); modelData->AnimationData()->SetAnimation(CAnimPlaybackParms(s32(type), -1, 1.f, true), false);
} }
std::experimental::optional<zeus::CAABox> CScriptDoor::GetTouchBounds() const
{
if (GetActive() && GetMaterialList().HasMaterial(EMaterialTypes::Solid))
return {CPhysicsActor::GetBoundingBox()};
return {};
}
std::experimental::optional<zeus::CAABox> CScriptDoor::GetProjectileBounds() const std::experimental::optional<zeus::CAABox> CScriptDoor::GetProjectileBounds() const
{ {
if (x2a8_28_projectilesCollide) if (x2a8_28_projectilesCollide)

View File

@ -51,6 +51,7 @@ public:
void OpenDoor(TUniqueId, CStateManager&); void OpenDoor(TUniqueId, CStateManager&);
u32 GetDoorOpenCondition(CStateManager& mgr); u32 GetDoorOpenCondition(CStateManager& mgr);
void SetDoorAnimation(EDoorAnimType); void SetDoorAnimation(EDoorAnimType);
std::experimental::optional<zeus::CAABox> GetTouchBounds() const;
std::experimental::optional<zeus::CAABox> GetProjectileBounds() const; std::experimental::optional<zeus::CAABox> GetProjectileBounds() const;
bool IsOpen() const { return x2a8_26_isOpen; } bool IsOpen() const { return x2a8_26_isOpen; }
}; };