mirror of
https://github.com/ZDoom/gzdoom.git
synced 2025-02-17 01:31:25 +00:00
Merge all sectors into one mesh
This commit is contained in:
parent
1a64adf2be
commit
34470aa588
6 changed files with 212 additions and 191 deletions
|
@ -33,23 +33,23 @@ void Mesh::Draw(FRenderState& renderstate)
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
MeshApplyState origState;
|
MeshApplyState origState;
|
||||||
origState.RenderStyle = renderstate.mRenderStyle;
|
origState.applyData.RenderStyle = renderstate.mRenderStyle;
|
||||||
origState.SpecialEffect = renderstate.mSpecialEffect;
|
origState.applyData.SpecialEffect = renderstate.mSpecialEffect;
|
||||||
origState.TextureEnabled = renderstate.mTextureEnabled;
|
origState.applyData.TextureEnabled = renderstate.mTextureEnabled;
|
||||||
origState.AlphaThreshold = renderstate.mAlphaThreshold;
|
origState.applyData.AlphaThreshold = renderstate.mAlphaThreshold;
|
||||||
|
origState.applyData.FogEnabled = renderstate.mFogEnabled;
|
||||||
|
origState.applyData.BrightmapEnabled = renderstate.mBrightmapEnabled;
|
||||||
|
origState.applyData.TextureClamp = renderstate.mTextureClamp;
|
||||||
|
origState.applyData.TextureMode = renderstate.mTextureMode;
|
||||||
|
origState.applyData.TextureModeFlags = renderstate.mTextureModeFlags;
|
||||||
|
origState.applyData.uLightDist = renderstate.mLightParms[0];
|
||||||
|
origState.applyData.uLightFactor = renderstate.mLightParms[1];
|
||||||
|
origState.applyData.uFogDensity = renderstate.mLightParms[2];
|
||||||
|
origState.applyData.uClipSplit[0] = renderstate.mClipSplit[0];
|
||||||
|
origState.applyData.uClipSplit[1] = renderstate.mClipSplit[1];
|
||||||
|
origState.uLightLevel = renderstate.mLightParms[3];
|
||||||
origState.streamData = renderstate.mStreamData;
|
origState.streamData = renderstate.mStreamData;
|
||||||
origState.material = renderstate.mMaterial;
|
origState.material = renderstate.mMaterial;
|
||||||
origState.FogEnabled = renderstate.mFogEnabled;
|
|
||||||
origState.BrightmapEnabled = renderstate.mBrightmapEnabled;
|
|
||||||
origState.TextureClamp = renderstate.mTextureClamp;
|
|
||||||
origState.TextureMode = renderstate.mTextureMode;
|
|
||||||
origState.TextureModeFlags = renderstate.mTextureModeFlags;
|
|
||||||
origState.uLightDist = renderstate.mLightParms[0];
|
|
||||||
origState.uLightFactor = renderstate.mLightParms[1];
|
|
||||||
origState.uFogDensity = renderstate.mLightParms[2];
|
|
||||||
origState.uLightLevel = renderstate.mLightParms[3];
|
|
||||||
origState.uClipSplit[0] = renderstate.mClipSplit[0];
|
|
||||||
origState.uClipSplit[1] = renderstate.mClipSplit[1];
|
|
||||||
|
|
||||||
int applyIndex = -1;
|
int applyIndex = -1;
|
||||||
int depthFunc = -1;
|
int depthFunc = -1;
|
||||||
|
@ -58,7 +58,7 @@ void Mesh::Draw(FRenderState& renderstate)
|
||||||
bool apply = applyIndex != cmd.ApplyIndex;
|
bool apply = applyIndex != cmd.ApplyIndex;
|
||||||
if (apply)
|
if (apply)
|
||||||
{
|
{
|
||||||
int newDepthFunc = mApplys[cmd.ApplyIndex].DepthFunc;
|
int newDepthFunc = mApplys[cmd.ApplyIndex].applyData.DepthFunc;
|
||||||
if (depthFunc != newDepthFunc)
|
if (depthFunc != newDepthFunc)
|
||||||
{
|
{
|
||||||
depthFunc = newDepthFunc;
|
depthFunc = newDepthFunc;
|
||||||
|
@ -86,7 +86,7 @@ void Mesh::Draw(FRenderState& renderstate)
|
||||||
bool apply = applyIndex != cmd.ApplyIndex;
|
bool apply = applyIndex != cmd.ApplyIndex;
|
||||||
if (apply)
|
if (apply)
|
||||||
{
|
{
|
||||||
int newDepthFunc = mApplys[cmd.ApplyIndex].DepthFunc;
|
int newDepthFunc = mApplys[cmd.ApplyIndex].applyData.DepthFunc;
|
||||||
if (depthFunc != newDepthFunc)
|
if (depthFunc != newDepthFunc)
|
||||||
{
|
{
|
||||||
depthFunc = newDepthFunc;
|
depthFunc = newDepthFunc;
|
||||||
|
@ -104,21 +104,21 @@ void Mesh::Draw(FRenderState& renderstate)
|
||||||
|
|
||||||
void Mesh::Apply(FRenderState& renderstate, const MeshApplyState& state)
|
void Mesh::Apply(FRenderState& renderstate, const MeshApplyState& state)
|
||||||
{
|
{
|
||||||
renderstate.mRenderStyle = state.RenderStyle;
|
renderstate.mRenderStyle = state.applyData.RenderStyle;
|
||||||
renderstate.mSpecialEffect = state.SpecialEffect;
|
renderstate.mSpecialEffect = state.applyData.SpecialEffect;
|
||||||
renderstate.mTextureEnabled = state.TextureEnabled;
|
renderstate.mTextureEnabled = state.applyData.TextureEnabled;
|
||||||
renderstate.mAlphaThreshold = state.AlphaThreshold;
|
renderstate.mAlphaThreshold = state.applyData.AlphaThreshold;
|
||||||
|
renderstate.mFogEnabled = state.applyData.FogEnabled;
|
||||||
|
renderstate.mBrightmapEnabled = state.applyData.BrightmapEnabled;
|
||||||
|
renderstate.mTextureClamp = state.applyData.TextureClamp;
|
||||||
|
renderstate.mTextureMode = state.applyData.TextureMode;
|
||||||
|
renderstate.mTextureModeFlags = state.applyData.TextureModeFlags;
|
||||||
|
renderstate.mLightParms[0] = state.applyData.uLightDist;
|
||||||
|
renderstate.mLightParms[1] = state.applyData.uLightFactor;
|
||||||
|
renderstate.mLightParms[2] = state.applyData.uFogDensity;
|
||||||
|
renderstate.mClipSplit[0] = state.applyData.uClipSplit[0];
|
||||||
|
renderstate.mClipSplit[1] = state.applyData.uClipSplit[1];
|
||||||
|
renderstate.mLightParms[3] = state.uLightLevel;
|
||||||
renderstate.mStreamData = state.streamData;
|
renderstate.mStreamData = state.streamData;
|
||||||
renderstate.mMaterial = state.material;
|
renderstate.mMaterial = state.material;
|
||||||
renderstate.mFogEnabled = state.FogEnabled;
|
|
||||||
renderstate.mBrightmapEnabled = state.BrightmapEnabled;
|
|
||||||
renderstate.mTextureClamp = state.TextureClamp;
|
|
||||||
renderstate.mTextureMode = state.TextureMode;
|
|
||||||
renderstate.mTextureModeFlags = state.TextureModeFlags;
|
|
||||||
renderstate.mLightParms[0] = state.uLightDist;
|
|
||||||
renderstate.mLightParms[1] = state.uLightFactor;
|
|
||||||
renderstate.mLightParms[2] = state.uFogDensity;
|
|
||||||
renderstate.mLightParms[3] = state.uLightLevel;
|
|
||||||
renderstate.mClipSplit[0] = state.uClipSplit[0];
|
|
||||||
renderstate.mClipSplit[1] = state.uClipSplit[1];
|
|
||||||
}
|
}
|
||||||
|
|
|
@ -27,8 +27,8 @@ void MeshBuilder::Draw(int dt, int index, int count, bool apply)
|
||||||
command.DrawType = dt;
|
command.DrawType = dt;
|
||||||
command.Start = index;
|
command.Start = index;
|
||||||
command.Count = count;
|
command.Count = count;
|
||||||
command.ApplyIndex = mApplys.Size() - 1;
|
command.ApplyIndex = -1;
|
||||||
mDraws.Push(command);
|
mDrawLists->mDraws.Push(command);
|
||||||
}
|
}
|
||||||
|
|
||||||
void MeshBuilder::DrawIndexed(int dt, int index, int count, bool apply)
|
void MeshBuilder::DrawIndexed(int dt, int index, int count, bool apply)
|
||||||
|
@ -40,8 +40,8 @@ void MeshBuilder::DrawIndexed(int dt, int index, int count, bool apply)
|
||||||
command.DrawType = dt;
|
command.DrawType = dt;
|
||||||
command.Start = index;
|
command.Start = index;
|
||||||
command.Count = count;
|
command.Count = count;
|
||||||
command.ApplyIndex = mApplys.Size() - 1;
|
command.ApplyIndex = -1;
|
||||||
mIndexedDraws.Push(command);
|
mDrawLists->mIndexedDraws.Push(command);
|
||||||
}
|
}
|
||||||
|
|
||||||
void MeshBuilder::SetDepthFunc(int func)
|
void MeshBuilder::SetDepthFunc(int func)
|
||||||
|
@ -53,45 +53,54 @@ void MeshBuilder::Apply()
|
||||||
{
|
{
|
||||||
MeshApplyState state;
|
MeshApplyState state;
|
||||||
|
|
||||||
state.RenderStyle = mRenderStyle;
|
state.applyData.RenderStyle = mRenderStyle;
|
||||||
state.SpecialEffect = mSpecialEffect;
|
state.applyData.SpecialEffect = mSpecialEffect;
|
||||||
state.TextureEnabled = mTextureEnabled;
|
state.applyData.TextureEnabled = mTextureEnabled;
|
||||||
state.AlphaThreshold = mAlphaThreshold;
|
state.applyData.AlphaThreshold = mAlphaThreshold;
|
||||||
state.DepthFunc = mDepthFunc;
|
state.applyData.DepthFunc = mDepthFunc;
|
||||||
|
state.applyData.FogEnabled = mFogEnabled;
|
||||||
|
state.applyData.BrightmapEnabled = mBrightmapEnabled;
|
||||||
|
state.applyData.TextureClamp = mTextureClamp;
|
||||||
|
state.applyData.TextureMode = mTextureMode;
|
||||||
|
state.applyData.TextureModeFlags = mTextureModeFlags;
|
||||||
|
state.applyData.uLightDist = mLightParms[0];
|
||||||
|
state.applyData.uLightFactor = mLightParms[1];
|
||||||
|
state.applyData.uFogDensity = mLightParms[2];
|
||||||
|
state.applyData.uClipSplit = { mClipSplit[0], mClipSplit[1] };
|
||||||
|
state.uLightLevel = mLightParms[3];
|
||||||
state.streamData = mStreamData;
|
state.streamData = mStreamData;
|
||||||
state.material = mMaterial;
|
state.material = mMaterial;
|
||||||
|
|
||||||
state.FogEnabled = mFogEnabled;
|
state.streamData.uVertexNormal = FVector4(0.0f, 0.0f, 0.0f, 0.0f); // Grr, this should be part of the vertex!!
|
||||||
state.BrightmapEnabled = mBrightmapEnabled;
|
|
||||||
state.TextureClamp = mTextureClamp;
|
|
||||||
state.TextureMode = mTextureMode;
|
|
||||||
state.TextureModeFlags = mTextureModeFlags;
|
|
||||||
|
|
||||||
state.uLightDist = mLightParms[0];
|
mDrawLists = &mSortedLists[state];
|
||||||
state.uLightFactor = mLightParms[1];
|
|
||||||
state.uFogDensity = mLightParms[2];
|
|
||||||
state.uLightLevel = mLightParms[3];
|
|
||||||
|
|
||||||
state.uClipSplit = { mClipSplit[0], mClipSplit[1] };
|
|
||||||
|
|
||||||
mApplys.Push(state);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
std::unique_ptr<Mesh> MeshBuilder::Create()
|
std::unique_ptr<Mesh> MeshBuilder::Create()
|
||||||
{
|
{
|
||||||
if (mDraws.Size() == 0 && mIndexedDraws.Size() == 0)
|
if (mSortedLists.empty())
|
||||||
return {};
|
return {};
|
||||||
|
|
||||||
auto mesh = std::make_unique<Mesh>();
|
auto mesh = std::make_unique<Mesh>();
|
||||||
mesh->mApplys = std::move(mApplys);
|
|
||||||
mesh->mDraws = std::move(mDraws);
|
|
||||||
mesh->mIndexedDraws = std::move(mIndexedDraws);
|
|
||||||
mesh->mVertices = std::move(mVertices);
|
|
||||||
|
|
||||||
mApplys.Clear();
|
int applyIndex = 0;
|
||||||
mDraws.Clear();
|
for (auto& it : mSortedLists)
|
||||||
mIndexedDraws.Clear();
|
{
|
||||||
|
mesh->mApplys.Push(it.first);
|
||||||
|
for (MeshDrawCommand& command : it.second.mDraws)
|
||||||
|
{
|
||||||
|
command.ApplyIndex = applyIndex;
|
||||||
|
mesh->mDraws.Push(command);
|
||||||
|
}
|
||||||
|
for (MeshDrawCommand& command : it.second.mIndexedDraws)
|
||||||
|
{
|
||||||
|
command.ApplyIndex = applyIndex;
|
||||||
|
mesh->mIndexedDraws.Push(command);
|
||||||
|
}
|
||||||
|
applyIndex++;
|
||||||
|
}
|
||||||
|
|
||||||
|
mesh->mVertices = std::move(mVertices);
|
||||||
mVertices.Clear();
|
mVertices.Clear();
|
||||||
|
|
||||||
return mesh;
|
return mesh;
|
||||||
|
|
|
@ -3,33 +3,55 @@
|
||||||
#include "hw_renderstate.h"
|
#include "hw_renderstate.h"
|
||||||
#include "hw_material.h"
|
#include "hw_material.h"
|
||||||
#include "flatvertices.h"
|
#include "flatvertices.h"
|
||||||
|
#include <map>
|
||||||
|
|
||||||
class Mesh;
|
class Mesh;
|
||||||
|
|
||||||
class MeshApplyState
|
class MeshApplyState
|
||||||
{
|
{
|
||||||
public:
|
public:
|
||||||
FRenderStyle RenderStyle;
|
struct ApplyData
|
||||||
int SpecialEffect;
|
{
|
||||||
bool TextureEnabled;
|
FRenderStyle RenderStyle;
|
||||||
float AlphaThreshold;
|
int SpecialEffect;
|
||||||
int DepthFunc;
|
int TextureEnabled;
|
||||||
|
float AlphaThreshold;
|
||||||
|
int DepthFunc;
|
||||||
|
int FogEnabled;
|
||||||
|
int BrightmapEnabled;
|
||||||
|
int TextureClamp;
|
||||||
|
int TextureMode;
|
||||||
|
int TextureModeFlags;
|
||||||
|
float uFogDensity;
|
||||||
|
float uLightFactor;
|
||||||
|
float uLightDist;
|
||||||
|
FVector2 uClipSplit;
|
||||||
|
};
|
||||||
|
|
||||||
|
float uLightLevel;
|
||||||
|
|
||||||
|
ApplyData applyData;
|
||||||
StreamData streamData;
|
StreamData streamData;
|
||||||
FMaterialState material;
|
FMaterialState material;
|
||||||
|
|
||||||
uint8_t FogEnabled;
|
bool operator<(const MeshApplyState& other) const
|
||||||
uint8_t BrightmapEnabled;
|
{
|
||||||
int TextureClamp;
|
if (material.mMaterial != other.material.mMaterial)
|
||||||
int TextureMode;
|
return material.mMaterial < other.material.mMaterial;
|
||||||
int TextureModeFlags;
|
if (material.mClampMode != other.material.mClampMode)
|
||||||
|
return material.mClampMode < other.material.mClampMode;
|
||||||
|
if (material.mTranslation != other.material.mTranslation)
|
||||||
|
return material.mTranslation < other.material.mTranslation;
|
||||||
|
if (material.mOverrideShader != other.material.mOverrideShader)
|
||||||
|
return material.mOverrideShader < other.material.mOverrideShader;
|
||||||
|
|
||||||
float uLightLevel;
|
int result = memcmp(&applyData, &other.applyData, sizeof(ApplyData));
|
||||||
float uFogDensity;
|
if (result != 0)
|
||||||
float uLightFactor;
|
return result < 0;
|
||||||
float uLightDist;
|
|
||||||
|
|
||||||
FVector2 uClipSplit;
|
result = memcmp(&streamData, &other.streamData, sizeof(StreamData));
|
||||||
|
return result < 0;
|
||||||
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
class MeshDrawCommand
|
class MeshDrawCommand
|
||||||
|
@ -79,9 +101,14 @@ public:
|
||||||
private:
|
private:
|
||||||
void Apply();
|
void Apply();
|
||||||
|
|
||||||
TArray<MeshApplyState> mApplys;
|
struct DrawLists
|
||||||
TArray<MeshDrawCommand> mDraws;
|
{
|
||||||
TArray<MeshDrawCommand> mIndexedDraws;
|
TArray<MeshDrawCommand> mDraws;
|
||||||
|
TArray<MeshDrawCommand> mIndexedDraws;
|
||||||
|
};
|
||||||
|
std::map<MeshApplyState, DrawLists> mSortedLists;
|
||||||
|
DrawLists* mDrawLists = nullptr;
|
||||||
|
|
||||||
TArray<FFlatVertex> mVertices;
|
TArray<FFlatVertex> mVertices;
|
||||||
int mDepthFunc = 0;
|
int mDepthFunc = 0;
|
||||||
};
|
};
|
||||||
|
|
|
@ -512,13 +512,9 @@ void HWDrawInfo::RenderScene(FRenderState &state)
|
||||||
drawlists[GLDL_PLAINWALLS].DrawWalls(this, state, false);
|
drawlists[GLDL_PLAINWALLS].DrawWalls(this, state, false);
|
||||||
drawlists[GLDL_PLAINFLATS].DrawFlats(this, state, false);
|
drawlists[GLDL_PLAINFLATS].DrawFlats(this, state, false);
|
||||||
|
|
||||||
if (gl_meshcache)
|
if (gl_meshcache && meshcache.Opaque)
|
||||||
{
|
{
|
||||||
for (HWCachedSector& cachedsector : meshcache.Sectors)
|
meshcache.Opaque->Draw(state);
|
||||||
{
|
|
||||||
if (cachedsector.Opaque)
|
|
||||||
cachedsector.Opaque->Draw(state);
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
// Part 2: masked geometry. This is set up so that only pixels with alpha>gl_mask_threshold will show
|
// Part 2: masked geometry. This is set up so that only pixels with alpha>gl_mask_threshold will show
|
||||||
|
@ -526,13 +522,9 @@ void HWDrawInfo::RenderScene(FRenderState &state)
|
||||||
drawlists[GLDL_MASKEDWALLS].DrawWalls(this, state, false);
|
drawlists[GLDL_MASKEDWALLS].DrawWalls(this, state, false);
|
||||||
drawlists[GLDL_MASKEDFLATS].DrawFlats(this, state, false);
|
drawlists[GLDL_MASKEDFLATS].DrawFlats(this, state, false);
|
||||||
|
|
||||||
if (gl_meshcache)
|
if (gl_meshcache && meshcache.Translucent)
|
||||||
{
|
{
|
||||||
for (HWCachedSector& cachedsector : meshcache.Sectors)
|
meshcache.Translucent->Draw(state);
|
||||||
{
|
|
||||||
if (cachedsector.Translucent)
|
|
||||||
cachedsector.Translucent->Draw(state);
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
// Part 3: masked geometry with polygon offset. This list is empty most of the time so only waste time on it when in use.
|
// Part 3: masked geometry with polygon offset. This list is empty most of the time so only waste time on it when in use.
|
||||||
|
@ -543,14 +535,10 @@ void HWDrawInfo::RenderScene(FRenderState &state)
|
||||||
state.ClearDepthBias();
|
state.ClearDepthBias();
|
||||||
}
|
}
|
||||||
|
|
||||||
if (gl_meshcache)
|
if (gl_meshcache && meshcache.TranslucentDepthBiased)
|
||||||
{
|
{
|
||||||
state.SetDepthBias(-1, -128);
|
state.SetDepthBias(-1, -128);
|
||||||
for (HWCachedSector& cachedsector : meshcache.Sectors)
|
meshcache.TranslucentDepthBiased->Draw(state);
|
||||||
{
|
|
||||||
if (cachedsector.TranslucentDepthBiased)
|
|
||||||
cachedsector.TranslucentDepthBiased->Draw(state);
|
|
||||||
}
|
|
||||||
state.ClearDepthBias();
|
state.ClearDepthBias();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -16,8 +16,12 @@ HWMeshCache meshcache;
|
||||||
|
|
||||||
void HWMeshCache::Clear()
|
void HWMeshCache::Clear()
|
||||||
{
|
{
|
||||||
|
#if 0
|
||||||
Sectors.Reset();
|
Sectors.Reset();
|
||||||
nextRefresh = 0;
|
#endif
|
||||||
|
Opaque.reset();
|
||||||
|
Translucent.reset();
|
||||||
|
TranslucentDepthBiased.reset();
|
||||||
}
|
}
|
||||||
|
|
||||||
void HWMeshCache::Update(FRenderViewpoint& vp)
|
void HWMeshCache::Update(FRenderViewpoint& vp)
|
||||||
|
@ -26,6 +30,9 @@ void HWMeshCache::Update(FRenderViewpoint& vp)
|
||||||
return;
|
return;
|
||||||
|
|
||||||
auto level = vp.ViewLevel;
|
auto level = vp.ViewLevel;
|
||||||
|
|
||||||
|
#if 0
|
||||||
|
|
||||||
unsigned int count = level->sectors.Size();
|
unsigned int count = level->sectors.Size();
|
||||||
Sectors.Resize(count);
|
Sectors.Resize(count);
|
||||||
|
|
||||||
|
@ -48,19 +55,6 @@ void HWMeshCache::Update(FRenderViewpoint& vp)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
#if 0
|
|
||||||
// Refresh 10 sectors per frame.
|
|
||||||
for (int i = 0; i < 10; i++)
|
|
||||||
{
|
|
||||||
if (nextRefresh < count)
|
|
||||||
{
|
|
||||||
Sectors[nextRefresh].NeedsUpdate = true;
|
|
||||||
}
|
|
||||||
if (count > 0)
|
|
||||||
nextRefresh = (nextRefresh + 1) % count;
|
|
||||||
}
|
|
||||||
#endif
|
|
||||||
|
|
||||||
// Update changed sectors
|
// Update changed sectors
|
||||||
for (unsigned int i = 0; i < count; i++)
|
for (unsigned int i = 0; i < count; i++)
|
||||||
{
|
{
|
||||||
|
@ -75,87 +69,91 @@ void HWMeshCache::Update(FRenderViewpoint& vp)
|
||||||
cacheitem->Update(vp);
|
cacheitem->Update(vp);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
|
||||||
|
|
||||||
void HWCachedSector::Update(FRenderViewpoint& vp)
|
#endif
|
||||||
{
|
|
||||||
Opaque.reset();
|
|
||||||
Translucent.reset();
|
|
||||||
TranslucentDepthBiased.reset();
|
|
||||||
|
|
||||||
HWDrawInfo* di = HWDrawInfo::StartDrawInfo(vp.ViewLevel, nullptr, vp, nullptr);
|
if (!Opaque)
|
||||||
di->MeshBuilding = true;
|
|
||||||
|
|
||||||
// Add to the draw lists
|
|
||||||
|
|
||||||
CheckUpdate(screen->mVertexData, Sector);
|
|
||||||
std::unordered_set<FSection*> seenSections;
|
|
||||||
for (int i = 0, count = Sector->subsectorcount; i < count; i++)
|
|
||||||
{
|
{
|
||||||
subsector_t* subsector = Sector->subsectors[i];
|
HWDrawInfo* di = HWDrawInfo::StartDrawInfo(vp.ViewLevel, nullptr, vp, nullptr);
|
||||||
if (seenSections.find(subsector->section) == seenSections.end())
|
di->MeshBuilding = true;
|
||||||
|
|
||||||
|
// Add to the draw lists
|
||||||
|
|
||||||
|
unsigned int count = level->sectors.Size();
|
||||||
|
for (unsigned int i = 0; i < count; i++)
|
||||||
{
|
{
|
||||||
seenSections.insert(subsector->section);
|
auto sector = &level->sectors[i];
|
||||||
|
|
||||||
HWFlat flat;
|
CheckUpdate(screen->mVertexData, sector);
|
||||||
flat.section = subsector->section;
|
std::unordered_set<FSection*> seenSections;
|
||||||
sector_t* front = hw_FakeFlat(subsector->render_sector, area_default, false);
|
for (int i = 0, count = sector->subsectorcount; i < count; i++)
|
||||||
flat.ProcessSector(di, front);
|
{
|
||||||
|
subsector_t* subsector = sector->subsectors[i];
|
||||||
|
if (seenSections.find(subsector->section) == seenSections.end())
|
||||||
|
{
|
||||||
|
seenSections.insert(subsector->section);
|
||||||
|
|
||||||
|
HWFlat flat;
|
||||||
|
flat.section = subsector->section;
|
||||||
|
sector_t* front = hw_FakeFlat(subsector->render_sector, area_default, false);
|
||||||
|
flat.ProcessSector(di, front);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
for (line_t* line : sector->Lines)
|
||||||
|
{
|
||||||
|
side_t* side = (line->sidedef[0]->sector == sector) ? line->sidedef[0] : line->sidedef[1];
|
||||||
|
|
||||||
|
HWWall wall;
|
||||||
|
wall.sub = sector->subsectors[0];
|
||||||
|
wall.Process(di, side->segs[0], sector, (line->sidedef[0]->sector == sector) ? line->backsector : line->frontsector);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
|
||||||
|
|
||||||
for (line_t* line : Sector->Lines)
|
// Convert draw lists to meshes
|
||||||
{
|
|
||||||
side_t* side = (line->sidedef[0]->sector == Sector) ? line->sidedef[0] : line->sidedef[1];
|
|
||||||
|
|
||||||
HWWall wall;
|
MeshBuilder state;
|
||||||
wall.sub = Sector->subsectors[0];
|
|
||||||
wall.Process(di, side->segs[0], Sector, (line->sidedef[0]->sector == Sector) ? line->backsector : line->frontsector);
|
|
||||||
}
|
|
||||||
|
|
||||||
// Convert draw lists to meshes
|
state.SetDepthMask(true);
|
||||||
|
state.EnableFog(true);
|
||||||
|
state.SetRenderStyle(STYLE_Source);
|
||||||
|
|
||||||
MeshBuilder state;
|
di->drawlists[GLDL_PLAINWALLS].SortWalls();
|
||||||
|
di->drawlists[GLDL_PLAINFLATS].SortFlats();
|
||||||
|
di->drawlists[GLDL_MASKEDWALLS].SortWalls();
|
||||||
|
di->drawlists[GLDL_MASKEDFLATS].SortFlats();
|
||||||
|
di->drawlists[GLDL_MASKEDWALLSOFS].SortWalls();
|
||||||
|
|
||||||
state.SetDepthMask(true);
|
// Part 1: solid geometry. This is set up so that there are no transparent parts
|
||||||
state.EnableFog(true);
|
state.SetDepthFunc(DF_Less);
|
||||||
state.SetRenderStyle(STYLE_Source);
|
state.AlphaFunc(Alpha_GEqual, 0.f);
|
||||||
|
|
||||||
di->drawlists[GLDL_PLAINWALLS].SortWalls();
|
|
||||||
di->drawlists[GLDL_PLAINFLATS].SortFlats();
|
|
||||||
di->drawlists[GLDL_MASKEDWALLS].SortWalls();
|
|
||||||
di->drawlists[GLDL_MASKEDFLATS].SortFlats();
|
|
||||||
di->drawlists[GLDL_MASKEDWALLSOFS].SortWalls();
|
|
||||||
|
|
||||||
// Part 1: solid geometry. This is set up so that there are no transparent parts
|
|
||||||
state.SetDepthFunc(DF_Less);
|
|
||||||
state.AlphaFunc(Alpha_GEqual, 0.f);
|
|
||||||
state.ClearDepthBias();
|
|
||||||
state.EnableTexture(gl_texture);
|
|
||||||
state.EnableBrightmap(true);
|
|
||||||
di->drawlists[GLDL_PLAINWALLS].DrawWalls(di, state, false);
|
|
||||||
di->drawlists[GLDL_PLAINFLATS].DrawFlats(di, state, false);
|
|
||||||
Opaque = state.Create();
|
|
||||||
|
|
||||||
// Part 2: masked geometry. This is set up so that only pixels with alpha>gl_mask_threshold will show
|
|
||||||
state.AlphaFunc(Alpha_GEqual, gl_mask_threshold);
|
|
||||||
di->drawlists[GLDL_MASKEDWALLS].DrawWalls(di, state, false);
|
|
||||||
di->drawlists[GLDL_MASKEDFLATS].DrawFlats(di, state, false);
|
|
||||||
Translucent = state.Create();
|
|
||||||
|
|
||||||
// Part 3: masked geometry with polygon offset. This list is empty most of the time so only waste time on it when in use.
|
|
||||||
if (di->drawlists[GLDL_MASKEDWALLSOFS].Size() > 0)
|
|
||||||
{
|
|
||||||
state.SetDepthBias(-1, -128);
|
|
||||||
di->drawlists[GLDL_MASKEDWALLSOFS].DrawWalls(di, state, false);
|
|
||||||
state.ClearDepthBias();
|
state.ClearDepthBias();
|
||||||
TranslucentDepthBiased = state.Create();
|
state.EnableTexture(gl_texture);
|
||||||
}
|
state.EnableBrightmap(true);
|
||||||
else
|
di->drawlists[GLDL_PLAINWALLS].DrawWalls(di, state, false);
|
||||||
{
|
di->drawlists[GLDL_PLAINFLATS].DrawFlats(di, state, false);
|
||||||
TranslucentDepthBiased.reset();
|
Opaque = state.Create();
|
||||||
}
|
|
||||||
|
|
||||||
di->MeshBuilding = false;
|
// Part 2: masked geometry. This is set up so that only pixels with alpha>gl_mask_threshold will show
|
||||||
di->EndDrawInfo();
|
state.AlphaFunc(Alpha_GEqual, gl_mask_threshold);
|
||||||
|
di->drawlists[GLDL_MASKEDWALLS].DrawWalls(di, state, false);
|
||||||
|
di->drawlists[GLDL_MASKEDFLATS].DrawFlats(di, state, false);
|
||||||
|
Translucent = state.Create();
|
||||||
|
|
||||||
|
// Part 3: masked geometry with polygon offset. This list is empty most of the time so only waste time on it when in use.
|
||||||
|
if (di->drawlists[GLDL_MASKEDWALLSOFS].Size() > 0)
|
||||||
|
{
|
||||||
|
state.SetDepthBias(-1, -128);
|
||||||
|
di->drawlists[GLDL_MASKEDWALLSOFS].DrawWalls(di, state, false);
|
||||||
|
state.ClearDepthBias();
|
||||||
|
TranslucentDepthBiased = state.Create();
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
TranslucentDepthBiased.reset();
|
||||||
|
}
|
||||||
|
|
||||||
|
di->MeshBuilding = false;
|
||||||
|
di->EndDrawInfo();
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -5,6 +5,7 @@
|
||||||
|
|
||||||
struct FRenderViewpoint;
|
struct FRenderViewpoint;
|
||||||
|
|
||||||
|
#if 0
|
||||||
class HWCachedSector
|
class HWCachedSector
|
||||||
{
|
{
|
||||||
public:
|
public:
|
||||||
|
@ -13,13 +14,8 @@ public:
|
||||||
sector_t* Sector = nullptr;
|
sector_t* Sector = nullptr;
|
||||||
secplane_t Floorplane;
|
secplane_t Floorplane;
|
||||||
secplane_t Ceilingplane;
|
secplane_t Ceilingplane;
|
||||||
|
|
||||||
std::unique_ptr<Mesh> Opaque;
|
|
||||||
std::unique_ptr<Mesh> Translucent;
|
|
||||||
std::unique_ptr<Mesh> TranslucentDepthBiased;
|
|
||||||
|
|
||||||
void Update(FRenderViewpoint& vp);
|
|
||||||
};
|
};
|
||||||
|
#endif
|
||||||
|
|
||||||
class HWMeshCache
|
class HWMeshCache
|
||||||
{
|
{
|
||||||
|
@ -27,10 +23,13 @@ public:
|
||||||
void Clear();
|
void Clear();
|
||||||
void Update(FRenderViewpoint& vp);
|
void Update(FRenderViewpoint& vp);
|
||||||
|
|
||||||
|
#if 0
|
||||||
TArray<HWCachedSector> Sectors;
|
TArray<HWCachedSector> Sectors;
|
||||||
|
#endif
|
||||||
|
|
||||||
private:
|
std::unique_ptr<Mesh> Opaque;
|
||||||
unsigned int nextRefresh = 0;
|
std::unique_ptr<Mesh> Translucent;
|
||||||
|
std::unique_ptr<Mesh> TranslucentDepthBiased;
|
||||||
};
|
};
|
||||||
|
|
||||||
extern HWMeshCache meshcache;
|
extern HWMeshCache meshcache;
|
||||||
|
|
Loading…
Reference in a new issue