Switch portal plane normal convention

This commit is contained in:
lawnjelly 2020-01-08 19:18:06 +00:00 committed by GitHub
parent 969abe8092
commit ddb9e39586
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
5 changed files with 52 additions and 8 deletions

View File

@ -229,7 +229,7 @@ LPortal::eClipResult LPortal::ClipWithPlane(const Plane &p) const
}
void LPortal::CreateGeometry(PoolVector<Vector3> p_vertices, const Transform &trans)
void LPortal::CreateGeometry(PoolVector<Vector3> p_vertices, const Transform &trans, bool bPortalPlane_Convention)
{
int nPoints = p_vertices.size();
ERR_FAIL_COND(nPoints < 3);
@ -238,10 +238,16 @@ void LPortal::CreateGeometry(PoolVector<Vector3> p_vertices, const Transform &tr
//print("\t\t\tLPortal::CreateGeometry nPoints : " + itos(nPoints));
//Vector3 ptFirstThree[3];
for (int n=0; n<nPoints; n++)
{
Vector3 ptWorld = trans.xform(p_vertices[n]);
// store the first three to make the plane, irrespective of duplicates
// if (n < 3)
// ptFirstThree[n] = ptWorld;
// new!! test for duplicates. Some geometry may contain duplicate verts in portals which will muck up
// the winding etc...
bool bDuplicate = false;
@ -264,17 +270,25 @@ void LPortal::CreateGeometry(PoolVector<Vector3> p_vertices, const Transform &tr
//print("\t\t\t\t" + itos(n) + "\tLocal : " + Variant(p_vertices[n]) + "\tWorld : " + ptWorld);
}
SortVertsClockwise();
// Plane portal_plane = Plane(ptFirstThree[0], ptFirstThree[1], ptFirstThree[2]);
SortVertsClockwise(bPortalPlane_Convention);
PlaneFromPoints();
}
// assume first 3 determine the desired normal
void LPortal::SortVertsClockwise()
void LPortal::SortVertsClockwise(bool bPortalPlane_Convention)
{
Vector<Vector3> &verts = m_ptsWorld;
// We first assumed first 3 determine the desired normal
// find normal
Plane plane = Plane(verts[0], verts[1], verts[2]);
Plane plane;
if (bPortalPlane_Convention)
plane = Plane(verts[0], verts[2], verts[1]);
else
plane = Plane(verts[0], verts[1], verts[2]);
Vector3 ptNormal = plane.normal;
// find centroid

View File

@ -76,9 +76,9 @@ public:
LPortal();
void CopyReversedGeometry(const LPortal &source);
void CreateGeometry(PoolVector<Vector3> p_vertices, const Transform &trans);
void CreateGeometry(PoolVector<Vector3> p_vertices, const Transform &trans, bool bPortalPlane_Convention);
void PlaneFromPoints();
void SortVertsClockwise();
void SortVertsClockwise(bool bPortalPlane_Convention);
void ReverseWindingOrder();
// useful funcs

View File

@ -1388,7 +1388,7 @@ void LRoomConverter::LRoom_DetectedPortalMesh(LRoom &lroom, LTempRoom &troom, Me
lport.m_iRoomNum = iLinkRoom;
// create the portal geometry
lport.CreateGeometry(p_vertices, pMeshInstance->get_global_transform());
lport.CreateGeometry(p_vertices, pMeshInstance->get_global_transform(), LMAN->m_bPortalPlane_Convention);
// LPRINT(2, "\t\t\tnum portals now " + itos(troom.m_Portals.size()));

View File

@ -56,6 +56,8 @@ LRoomManager::LRoomManager()
m_bActive = true;
m_bFrustumOnly = false;
m_bPortalPlane_Convention = false;
// to know which rooms to hide we keep track of which were shown this, and the previous frame
m_pCurr_VisibleRoomList = &m_VisibleRoomList_A;
m_pPrev_VisibleRoomList = &m_VisibleRoomList_B;
@ -1025,6 +1027,17 @@ int LRoomManager::rooms_get_num_rooms() const
return m_Rooms.size();
}
Vector3 LRoomManager::rooms_get_room_centre(int room_id) const
{
const LRoom * pRoom = GetRoom(room_id);
if (!pRoom)
return Vector3(0, 0, 0);
return pRoom->m_ptCentre;
}
bool LRoomManager::rooms_is_room_visible(int room_id) const
{
if (room_id >= m_Rooms.size())
@ -1218,6 +1231,12 @@ bool LRoomManager::rooms_single_room_convert(bool bVerbose, bool bDeleteLights)
return RoomsConvert(bVerbose, bDeleteLights, true);
}
void LRoomManager::rooms_set_portal_plane_convention(bool bFlip)
{
m_bPortalPlane_Convention = bFlip;
}
// convert empties and meshes to rooms and portals
bool LRoomManager::rooms_convert(bool bVerbose, bool bDeleteLights)
{
@ -1983,6 +2002,8 @@ void LRoomManager::_bind_methods()
// main functions
ClassDB::bind_method(D_METHOD("rooms_convert", "verbose", "delete lights"), &LRoomManager::rooms_convert);
ClassDB::bind_method(D_METHOD("rooms_single_room_convert", "verbose", "delete lights"), &LRoomManager::rooms_single_room_convert);
ClassDB::bind_method(D_METHOD("rooms_set_portal_plane_convention", "flip"), &LRoomManager::rooms_set_portal_plane_convention);
ClassDB::bind_method(D_METHOD("rooms_release"), &LRoomManager::rooms_release);
ClassDB::bind_method(D_METHOD("rooms_set_camera", "camera"), &LRoomManager::rooms_set_camera);
@ -2015,6 +2036,7 @@ void LRoomManager::_bind_methods()
ClassDB::bind_method(D_METHOD("rooms_set_debug_frame_string", "active"), &LRoomManager::rooms_set_debug_frame_string);
ClassDB::bind_method(D_METHOD("rooms_get_debug_frame_string"), &LRoomManager::rooms_get_debug_frame_string);
ClassDB::bind_method(D_METHOD("rooms_get_room_centre", "room_id"), &LRoomManager::rooms_get_room_centre);
// functions to add dynamic objects to the culling system
// Note that these should not be placed directly in rooms, the system will 'soft link' to them

View File

@ -60,6 +60,7 @@ public:
// convert empties and meshes to rooms and portals
bool rooms_convert(bool bVerbose, bool bDeleteLights);
bool rooms_single_room_convert(bool bVerbose, bool bDeleteLights);
void rooms_set_portal_plane_convention(bool bFlip);
// free memory for current set of rooms, prepare for converting a new game level
void rooms_release();
@ -141,6 +142,9 @@ public:
void rooms_set_debug_frustums(bool bActive);
void rooms_set_debug_frame_string(bool bActive);
// rough .. for debugging
Vector3 rooms_get_room_centre(int room_id) const;
// 0 to 6 .. less to more
// defaults to 4 which is (2) in our priorities (i.e. 6 - level)
void rooms_set_logging(int level);
@ -208,6 +212,10 @@ private:
// already to prevent multiple hits on rooms and objects
unsigned int m_uiFrameCounter;
// the portal plane determined by the artwork geometry for room conversion can either point in or out,
// this convention is switchable
bool m_bPortalPlane_Convention;
private:
// lists of rooms and portals, contiguous list so cache friendly
LVector<LRoom> m_Rooms;