From f1b9e6830591e4ff7e3742cdddc485ae61cb26b4 Mon Sep 17 00:00:00 2001 From: Magnus Norddahl Date: Sun, 11 Aug 2024 01:15:44 +0200 Subject: [PATCH] Add more dynamic update code to level mesh --- .../rendering/hwrenderer/data/hw_levelmesh.h | 13 +- .../hwrenderer/data/hw_levelmeshsurface.h | 2 - .../hwrenderer/data/hw_lightmaptile.h | 2 + src/g_levellocals.h | 2 +- src/gamedata/r_defs.h | 4 +- src/maploader/maploader.cpp | 11 +- src/rendering/hwrenderer/doom_levelmesh.cpp | 119 +++++++++++------- src/rendering/hwrenderer/doom_levelmesh.h | 25 ++-- src/rendering/hwrenderer/hw_vertexbuilder.cpp | 12 +- src/rendering/hwrenderer/scene/hw_decal.cpp | 4 +- src/rendering/hwrenderer/scene/hw_drawinfo.h | 10 +- .../hwrenderer/scene/hw_drawstructs.h | 2 +- src/rendering/hwrenderer/scene/hw_flats.cpp | 4 +- src/rendering/hwrenderer/scene/hw_walls.cpp | 34 ++--- .../hwrenderer/scene/hw_walls_vertex.cpp | 4 +- 15 files changed, 147 insertions(+), 101 deletions(-) diff --git a/src/common/rendering/hwrenderer/data/hw_levelmesh.h b/src/common/rendering/hwrenderer/data/hw_levelmesh.h index a1569c8d7..16b424bb0 100644 --- a/src/common/rendering/hwrenderer/data/hw_levelmesh.h +++ b/src/common/rendering/hwrenderer/data/hw_levelmesh.h @@ -77,6 +77,7 @@ class LevelMesh info.Vertices = &Mesh.Vertices[info.VertexStart]; info.UniformIndexes = &Mesh.UniformIndexes[info.VertexStart]; info.Indexes = &Mesh.Indexes[info.IndexStart]; + // To do: mark range as dirty return info; } @@ -89,6 +90,7 @@ class LevelMesh Mesh.Materials.Resize(info.Start + count); info.Uniforms = &Mesh.Uniforms[info.Start]; info.Materials = &Mesh.Materials[info.Start]; + // To do: mark range as dirty return info; } @@ -96,10 +98,19 @@ class LevelMesh { for (int i = 0; i < indexCount; i++) Mesh.Indexes[indexStart + i] = 0; + // To do: add to a free list + // To do: mark range as dirty } void FreeUniforms(int start, int count) { + // To do: add to a free list + } + + void FreeSurface(unsigned int surfaceIndex) + { + // To do: remove the surface from the surface tile, if attached + // To do: add to a free list } struct @@ -121,7 +132,7 @@ class LevelMesh TArray SurfaceIndexes; int DynamicIndexStart = 0; - // Above data must not be resized beyond these limits as that's the size of the GPU buffers) + // Above data must not be resized beyond these limits as that's the size of the GPU buffers int MaxVertices = 0; int MaxIndexes = 0; int MaxSurfaces = 0; diff --git a/src/common/rendering/hwrenderer/data/hw_levelmeshsurface.h b/src/common/rendering/hwrenderer/data/hw_levelmeshsurface.h index 5dae14107..898237da3 100644 --- a/src/common/rendering/hwrenderer/data/hw_levelmeshsurface.h +++ b/src/common/rendering/hwrenderer/data/hw_levelmeshsurface.h @@ -24,8 +24,6 @@ struct LevelMeshSurface FVector4 Plane = FVector4(0.0f, 0.0f, 1.0f, 0.0f); int LightmapTileIndex = -1; - bool AlwaysUpdate = false; - FGameTexture* Texture = nullptr; float Alpha = 1.0; diff --git a/src/common/rendering/hwrenderer/data/hw_lightmaptile.h b/src/common/rendering/hwrenderer/data/hw_lightmaptile.h index dd41928f6..2793252ac 100644 --- a/src/common/rendering/hwrenderer/data/hw_lightmaptile.h +++ b/src/common/rendering/hwrenderer/data/hw_lightmaptile.h @@ -54,6 +54,8 @@ struct LightmapTile // True if the tile needs to be rendered into the lightmap texture before it can be used bool NeedsUpdate = true; + bool AlwaysUpdate = false; + FVector2 ToUV(const FVector3& vert) const { FVector3 localPos = vert - Transform.TranslateWorldToLocal; diff --git a/src/g_levellocals.h b/src/g_levellocals.h index 2a9c41af6..b54a91ea0 100644 --- a/src/g_levellocals.h +++ b/src/g_levellocals.h @@ -467,7 +467,7 @@ struct FLevelLocals // Lightmaps bool lightmaps = false; - TArray Surfaces; + TArray LightmapTiles; FVector3 SunDirection; FVector3 SunColor; uint16_t LightmapSampleDistance; diff --git a/src/gamedata/r_defs.h b/src/gamedata/r_defs.h index efdbd4959..04e32c748 100644 --- a/src/gamedata/r_defs.h +++ b/src/gamedata/r_defs.h @@ -1257,7 +1257,7 @@ struct side_t uint16_t Flags; int UDMFIndex; // needed to access custom UDMF fields which are stored in loading order. FLightNode * lighthead; // all dynamic lights that may affect this wall - TArrayView surface; // all mesh surfaces belonging to this sidedef + TArrayView LightmapTiles; // all lightmap tiles belonging to this sidedef seg_t **segs; // all segs belonging to this sidedef in ascending order. Used for precise rendering int numsegs; int sidenum; @@ -1674,7 +1674,7 @@ struct subsector_t // 2: has one-sided walls FPortalCoverage portalcoverage[2]; TArray sprites; - TArrayView surface[2]; // all mesh surfaces belonging to this subsector + TArrayView LightmapTiles[2]; // all lightmap tiles belonging to this subsector }; diff --git a/src/maploader/maploader.cpp b/src/maploader/maploader.cpp index a62bf1c30..51faf97a1 100644 --- a/src/maploader/maploader.cpp +++ b/src/maploader/maploader.cpp @@ -2989,23 +2989,24 @@ void MapLoader::InitLevelMesh(MapData* map) for (unsigned int i = 0; i < Level->subsectors.Size(); i++) allSurfaces += 2 + Level->subsectors[i].sector->e->XFloor.ffloors.Size() * 2; - Level->Surfaces.Resize(allSurfaces); - memset(Level->Surfaces.Data(), 0, sizeof(DoomLevelMeshSurface*) * allSurfaces); + Level->LightmapTiles.Resize(allSurfaces); + for (int& value : Level->LightmapTiles) + value = -1; unsigned int offset = 0; for (unsigned int i = 0; i < Level->sides.Size(); i++) { auto& side = Level->sides[i]; int count = 4 + side.sector->e->XFloor.ffloors.Size(); - side.surface = TArrayView(&Level->Surfaces[offset], count); + side.LightmapTiles = TArrayView(&Level->LightmapTiles[offset], count); offset += count; } for (unsigned int i = 0; i < Level->subsectors.Size(); i++) { auto& subsector = Level->subsectors[i]; unsigned int count = 1 + subsector.sector->e->XFloor.ffloors.Size(); - subsector.surface[0] = TArrayView(&Level->Surfaces[offset], count); - subsector.surface[1] = TArrayView(&Level->Surfaces[offset + count], count); + subsector.LightmapTiles[0] = TArrayView(&Level->LightmapTiles[offset], count); + subsector.LightmapTiles[1] = TArrayView(&Level->LightmapTiles[offset + count], count); offset += count * 2; } diff --git a/src/rendering/hwrenderer/doom_levelmesh.cpp b/src/rendering/hwrenderer/doom_levelmesh.cpp index a1e4fc0db..a21576a5c 100644 --- a/src/rendering/hwrenderer/doom_levelmesh.cpp +++ b/src/rendering/hwrenderer/doom_levelmesh.cpp @@ -95,8 +95,8 @@ void PrintSurfaceInfo(const DoomLevelMeshSurface* surface) Printf(" Pixels: %dx%d (area: %d)\n", tile->AtlasLocation.Width, tile->AtlasLocation.Height, tile->AtlasLocation.Area()); Printf(" Sample dimension: %d\n", tile->SampleDimension); Printf(" Needs update?: %d\n", tile->NeedsUpdate); + Printf(" Always update?: %d\n", tile->AlwaysUpdate); } - Printf(" Always update?: %d\n", surface->AlwaysUpdate); Printf(" Sector group: %d\n", surface->SectorGroup); Printf(" Texture: '%s'\n", gameTexture ? gameTexture->GetName().GetChars() : ""); Printf(" Alpha: %f\n", surface->Alpha); @@ -345,8 +345,44 @@ void DoomLevelMesh::CreateSurfaces(FLevelLocals& doomMap) } } +void DoomLevelMesh::FreeSide(FLevelLocals& doomMap, unsigned int sideIndex) +{ + if (sideIndex < 0 || sideIndex >= Sides.Size()) + return; + + int surf = Sides[sideIndex].FirstSurface; + while (surf != -1) + { + unsigned int next = Surfaces[surf].NextSurface; + FreeSurface(surf); + surf = next; + } + Sides[sideIndex].FirstSurface = -1; + + // To do: call FreeGeometry and FreeUniforms +} + +void DoomLevelMesh::FreeFlat(FLevelLocals& doomMap, unsigned int sectorIndex) +{ + if (sectorIndex < 0 || sectorIndex >= Flats.Size()) + return; + + int surf = Flats[sectorIndex].FirstSurface; + while (surf != -1) + { + unsigned int next = Surfaces[surf].NextSurface; + FreeSurface(surf - 1); + surf = next; + } + Flats[sectorIndex].FirstSurface = -1; + + // To do: call FreeGeometry and FreeUniforms +} + void DoomLevelMesh::UpdateSide(FLevelLocals& doomMap, unsigned int sideIndex) { + FreeSide(doomMap, sideIndex); + side_t* side = &doomMap.sides[sideIndex]; seg_t* seg = side->segs[0]; if (!seg) @@ -369,20 +405,20 @@ void DoomLevelMesh::UpdateSide(FLevelLocals& doomMap, unsigned int sideIndex) state.EnableTexture(true); state.EnableBrightmap(true); state.AlphaFunc(Alpha_GEqual, 0.f); - CreateWallSurface(side, disp, state, result.list, false, true); + CreateWallSurface(side, disp, state, result.list, false, true, sideIndex); for (HWWall& portal : result.portals) { WallPortals.Push(portal); } - CreateWallSurface(side, disp, state, result.portals, true, false); + CreateWallSurface(side, disp, state, result.portals, true, false, sideIndex); /* // final pass: translucent stuff state.AlphaFunc(Alpha_GEqual, gl_mask_sprite_threshold); state.SetRenderStyle(STYLE_Translucent); - CreateWallSurface(side, disp, state, result.translucent, false, true); + CreateWallSurface(side, disp, state, result.translucent, false, true, sideIndex); state.AlphaFunc(Alpha_GEqual, 0.f); state.SetRenderStyle(STYLE_Normal); */ @@ -390,6 +426,8 @@ void DoomLevelMesh::UpdateSide(FLevelLocals& doomMap, unsigned int sideIndex) void DoomLevelMesh::UpdateFlat(FLevelLocals& doomMap, unsigned int sectorIndex) { + FreeSide(doomMap, sectorIndex); + sector_t* sector = &doomMap.sectors[sectorIndex]; for (FSection& section : doomMap.sections.SectionsForSector(sectorIndex)) { @@ -405,23 +443,23 @@ void DoomLevelMesh::UpdateFlat(FLevelLocals& doomMap, unsigned int sectorIndex) state.ClearDepthBias(); state.EnableTexture(true); state.EnableBrightmap(true); - CreateFlatSurface(disp, state, result.list, false, false); + CreateFlatSurface(disp, state, result.list, false, false, sectorIndex); - CreateFlatSurface(disp, state, result.portals, true, false); + CreateFlatSurface(disp, state, result.portals, true, false, sectorIndex); // final pass: translucent stuff state.AlphaFunc(Alpha_GEqual, gl_mask_sprite_threshold); state.SetRenderStyle(STYLE_Translucent); - CreateFlatSurface(disp, state, result.translucentborder, false, true); + CreateFlatSurface(disp, state, result.translucentborder, false, true, sectorIndex); state.SetDepthMask(false); - CreateFlatSurface(disp, state, result.translucent, false, true); + CreateFlatSurface(disp, state, result.translucent, false, true, sectorIndex); state.AlphaFunc(Alpha_GEqual, 0.f); state.SetDepthMask(true); state.SetRenderStyle(STYLE_Normal); } } -void DoomLevelMesh::CreateWallSurface(side_t* side, HWWallDispatcher& disp, MeshBuilder& state, TArray& list, bool isPortal, bool translucent) +void DoomLevelMesh::CreateWallSurface(side_t* side, HWWallDispatcher& disp, MeshBuilder& state, TArray& list, bool isPortal, bool translucent, unsigned int sideIndex) { for (HWWall& wallpart : list) { @@ -534,7 +572,6 @@ void DoomLevelMesh::CreateWallSurface(side_t* side, HWWallDispatcher& disp, Mesh surf.ControlSector = wallpart.LevelMeshInfo.ControlSector; surf.TypeIndex = side->Index(); surf.Side = side; - surf.AlwaysUpdate = !!(side->sector->Flags & SECF_LM_DYNAMIC); surf.SectorGroup = sectorGroup[side->sector->Index()]; surf.Alpha = float(side->linedef->alpha); surf.MeshLocation.StartVertIndex = ginfo.VertexStart; @@ -547,12 +584,19 @@ void DoomLevelMesh::CreateWallSurface(side_t* side, HWWallDispatcher& disp, Mesh surf.PortalIndex = isPortal ? linePortals[side->linedef->Index()] : 0; surf.IsSky = isPortal ? (wallpart.portaltype == PORTALTYPE_SKY || wallpart.portaltype == PORTALTYPE_SKYBOX || wallpart.portaltype == PORTALTYPE_HORIZON) : false; surf.Bounds = GetBoundsFromSurface(surf); - surf.LightmapTileIndex = disp.Level->lightmaps ? AddSurfaceToTile(surf, sampleDimension) : -1; + surf.LightmapTileIndex = disp.Level->lightmaps ? AddSurfaceToTile(surf, sampleDimension, !!(side->sector->Flags & SECF_LM_DYNAMIC)) : -1; + + if (sideIndex < Sides.Size()) + { + surf.NextSurface = Sides[sideIndex].FirstSurface; + Sides[sideIndex].FirstSurface = Surfaces.Size(); + } + Surfaces.Push(surf); } } -int DoomLevelMesh::AddSurfaceToTile(const DoomLevelMeshSurface& surf, uint16_t sampleDimension) +int DoomLevelMesh::AddSurfaceToTile(const DoomLevelMeshSurface& surf, uint16_t sampleDimension, bool alwaysUpdate) { if (surf.IsSky) return -1; @@ -574,6 +618,7 @@ int DoomLevelMesh::AddSurfaceToTile(const DoomLevelMeshSurface& surf, uint16_t s tile.Bounds.max.X = std::max(tile.Bounds.max.X, surf.Bounds.max.X); tile.Bounds.max.Y = std::max(tile.Bounds.max.Y, surf.Bounds.max.Y); tile.Bounds.max.Z = std::max(tile.Bounds.max.Z, surf.Bounds.max.Z); + tile.AlwaysUpdate = tile.AlwaysUpdate || alwaysUpdate; return index; } @@ -586,6 +631,7 @@ int DoomLevelMesh::AddSurfaceToTile(const DoomLevelMeshSurface& surf, uint16_t s tile.Bounds = surf.Bounds; tile.Plane = surf.Plane; tile.SampleDimension = GetSampleDimension(surf, sampleDimension); + tile.AlwaysUpdate = alwaysUpdate; LightmapTiles.Push(tile); bindings[binding] = index; @@ -614,7 +660,7 @@ int DoomLevelMesh::GetSampleDimension(const DoomLevelMeshSurface& surf, uint16_t return sampleDimension; } -void DoomLevelMesh::CreateFlatSurface(HWFlatDispatcher& disp, MeshBuilder& state, TArray& list, bool isSky, bool translucent) +void DoomLevelMesh::CreateFlatSurface(HWFlatDispatcher& disp, MeshBuilder& state, TArray& list, bool isSky, bool translucent, unsigned int sectorIndex) { for (HWFlat& flatpart : list) { @@ -702,7 +748,6 @@ void DoomLevelMesh::CreateFlatSurface(HWFlatDispatcher& disp, MeshBuilder& state DoomLevelMeshSurface surf; surf.Type = flatpart.ceiling ? ST_CEILING : ST_FLOOR; surf.ControlSector = flatpart.controlsector ? flatpart.controlsector->model : nullptr; - surf.AlwaysUpdate = !!(flatpart.sector->Flags & SECF_LM_DYNAMIC); surf.SectorGroup = sectorGroup[flatpart.sector->Index()]; surf.Alpha = flatpart.alpha; surf.Texture = flatpart.texture; @@ -775,36 +820,18 @@ void DoomLevelMesh::CreateFlatSurface(HWFlatDispatcher& disp, MeshBuilder& state surf.MeshLocation.NumVerts = sub->numlines; surf.MeshLocation.NumElements = (sub->numlines - 2) * 3; surf.Bounds = GetBoundsFromSurface(surf); - surf.LightmapTileIndex = disp.Level->lightmaps ? AddSurfaceToTile(surf, sampleDimension) : -1; - Surfaces.Push(surf); - } - } -} + surf.LightmapTileIndex = disp.Level->lightmaps ? AddSurfaceToTile(surf, sampleDimension, !!(flatpart.sector->Flags & SECF_LM_DYNAMIC)) : -1; -#if 0 -void DoomLevelMesh::CreateDynamicSurfaces(FLevelLocals& doomMap) -{ - // Look for polyobjects - for (unsigned int i = 0; i < doomMap.lines.Size(); i++) - { - side_t* side = doomMap.lines[i].sidedef[0]; - bool isPolyLine = !!(side->Flags & WALLF_POLYOBJ); - if (!isPolyLine) - continue; + if (sectorIndex < Flats.Size()) + { + surf.NextSurface = Flats[sectorIndex].FirstSurface; + Flats[sectorIndex].FirstSurface = Surfaces.Size(); + } - // Make sure we have a surface array on the polyobj sidedef - if (!side->surface) - { - auto array = std::make_unique(4); - memset(array.get(), 0, sizeof(DoomLevelMeshSurface*)); - side->surface = array.get(); - PolyLMSurfaces.Push(std::move(array)); + Surfaces.Push(surf); } - - CreateSideSurfaces(doomMap, side); } } -#endif void DoomLevelMesh::SortIndexes() { @@ -879,7 +906,7 @@ void DoomLevelMesh::SetSubsectorLightmap(DoomLevelMeshSurface* surface) if (!surface->ControlSector) { int index = surface->Type == ST_CEILING ? 1 : 0; - surface->Subsector->surface[index][0] = surface; + surface->Subsector->LightmapTiles[index][0] = surface->LightmapTileIndex; } else { @@ -889,7 +916,7 @@ void DoomLevelMesh::SetSubsectorLightmap(DoomLevelMeshSurface* surface) { if (ffloors[i]->model == surface->ControlSector) { - surface->Subsector->surface[index][i + 1] = surface; + surface->Subsector->LightmapTiles[index][i + 1] = surface->LightmapTileIndex; } } } @@ -901,16 +928,16 @@ void DoomLevelMesh::SetSideLightmap(DoomLevelMeshSurface* surface) { if (surface->Type == ST_UPPERSIDE) { - surface->Side->surface[0] = surface; + surface->Side->LightmapTiles[0] = surface->LightmapTileIndex; } else if (surface->Type == ST_MIDDLESIDE) { - surface->Side->surface[1] = surface; - surface->Side->surface[2] = surface; + surface->Side->LightmapTiles[1] = surface->LightmapTileIndex; + surface->Side->LightmapTiles[2] = surface->LightmapTileIndex; } else if (surface->Type == ST_LOWERSIDE) { - surface->Side->surface[3] = surface; + surface->Side->LightmapTiles[3] = surface->LightmapTileIndex; } } else @@ -921,7 +948,7 @@ void DoomLevelMesh::SetSideLightmap(DoomLevelMeshSurface* surface) { if (ffloors[i]->model == surface->ControlSector) { - backside->surface[4 + i] = surface; + backside->LightmapTiles[4 + i] = surface->LightmapTileIndex; } } } diff --git a/src/rendering/hwrenderer/doom_levelmesh.h b/src/rendering/hwrenderer/doom_levelmesh.h index 9b407f7b9..75eba0693 100644 --- a/src/rendering/hwrenderer/doom_levelmesh.h +++ b/src/rendering/hwrenderer/doom_levelmesh.h @@ -27,18 +27,18 @@ struct DoomLevelMeshSurface : public LevelMeshSurface sector_t* ControlSector = nullptr; int PipelineID = 0; + + int NextSurface = -1; }; -struct SideSurfaceRange +struct SideSurfaceBlock { - int StartSurface = 0; - int SurfaceCount = 0; + int FirstSurface = -1; }; -struct FlatSurfaceRange +struct FlatSurfaceBlock { - int StartSurface = 0; - int SurfaceCount = 0; + int FirstSurface = -1; }; class DoomLevelMesh : public LevelMesh @@ -72,19 +72,22 @@ class DoomLevelMesh : public LevelMesh void UpdateSide(FLevelLocals& doomMap, unsigned int sideIndex); void UpdateFlat(FLevelLocals& doomMap, unsigned int sectorIndex); + void FreeSide(FLevelLocals& doomMap, unsigned int sideIndex); + void FreeFlat(FLevelLocals& doomMap, unsigned int sectorIndex); + void SetSubsectorLightmap(DoomLevelMeshSurface* surface); void SetSideLightmap(DoomLevelMeshSurface* surface); void SortIndexes(); - void CreateWallSurface(side_t* side, HWWallDispatcher& disp, MeshBuilder& state, TArray& list, bool isPortal, bool translucent); - void CreateFlatSurface(HWFlatDispatcher& disp, MeshBuilder& state, TArray& list, bool isSky, bool translucent); + void CreateWallSurface(side_t* side, HWWallDispatcher& disp, MeshBuilder& state, TArray& list, bool isPortal, bool translucent, unsigned int sectorIndex); + void CreateFlatSurface(HWFlatDispatcher& disp, MeshBuilder& state, TArray& list, bool isSky, bool translucent, unsigned int sectorIndex); void LinkSurfaces(FLevelLocals& doomMap); BBox GetBoundsFromSurface(const LevelMeshSurface& surface) const; - int AddSurfaceToTile(const DoomLevelMeshSurface& surf, uint16_t sampleDimension); + int AddSurfaceToTile(const DoomLevelMeshSurface& surf, uint16_t sampleDimension, bool alwaysUpdate); int GetSampleDimension(const DoomLevelMeshSurface& surf, uint16_t sampleDimension); void CreatePortals(FLevelLocals& doomMap); @@ -92,8 +95,8 @@ class DoomLevelMesh : public LevelMesh int GetLightIndex(FDynamicLight* light, int portalgroup); - TArray Sides; - TArray Flats; + TArray Sides; + TArray Flats; std::map bindings; MeshBuilder state; }; diff --git a/src/rendering/hwrenderer/hw_vertexbuilder.cpp b/src/rendering/hwrenderer/hw_vertexbuilder.cpp index 2e64a07ed..8db2dacee 100644 --- a/src/rendering/hwrenderer/hw_vertexbuilder.cpp +++ b/src/rendering/hwrenderer/hw_vertexbuilder.cpp @@ -243,13 +243,17 @@ static int CreateIndexedSectorVerticesLM(sector_t* sec, const secplane_t& plane, for(auto& sub : section.subsectors) { // vertices - DoomLevelMeshSurface* lightmap = sub->surface[h].Size() > lightmapIndex ? sub->surface[h][lightmapIndex] : nullptr; - if (lightmap && lightmap->Type != ST_NONE) // surface may be missing if the subsector is degenerate triangle + int lightmap = sub->LightmapTiles[h].Size() > lightmapIndex ? sub->LightmapTiles[h][lightmapIndex] : -1; + if (lightmap >= 0) // tile may be missing if the subsector is degenerate triangle { - FFlatVertex* luvs = &level.levelMesh->Mesh.Vertices[lightmap->MeshLocation.StartVertIndex]; + const auto& tile = level.levelMesh->LightmapTiles[lightmap]; + float textureSize = (float)level.levelMesh->LMTextureSize; + float lindex = (float)tile.AtlasLocation.ArrayIndex; for (unsigned int j = 0, end = sub->numlines; j < end; j++) { - SetFlatVertex(vbo_shadowdata[vi + pos], sub->firstline[j].v1, plane, luvs[end - 1 - j].lu, luvs[end - 1 - j].lv, luvs[end - 1 - j].lindex); + vertex_t* vt = sub->firstline[j].v1; + FVector2 luv = tile.ToUV(FVector3((float)vt->fX(), (float)vt->fY(), (float)plane.ZatPoint(vt)), textureSize); + SetFlatVertex(vbo_shadowdata[vi + pos], vt, plane, luv.X, luv.Y, lindex); vbo_shadowdata[vi + pos].z += diff; pos++; } diff --git a/src/rendering/hwrenderer/scene/hw_decal.cpp b/src/rendering/hwrenderer/scene/hw_decal.cpp index cc0dd456c..944ce6c8b 100644 --- a/src/rendering/hwrenderer/scene/hw_decal.cpp +++ b/src/rendering/hwrenderer/scene/hw_decal.cpp @@ -422,9 +422,9 @@ void HWWall::ProcessDecal(HWDrawInfo *di, FRenderState& state, DBaseDecal *decal auto verts = state.AllocVertices(4); gldecal->vertindex = verts.second; - if (surface && surface->LightmapTileIndex >= 0) + if (lightmaptile >= 0) { - LightmapTile* tile = &di->Level->levelMesh->LightmapTiles[surface->LightmapTileIndex]; + LightmapTile* tile = &di->Level->levelMesh->LightmapTiles[lightmaptile]; float lightmapindex = (float)tile->AtlasLocation.ArrayIndex; for (i = 0; i < 4; i++) diff --git a/src/rendering/hwrenderer/scene/hw_drawinfo.h b/src/rendering/hwrenderer/scene/hw_drawinfo.h index e67bb77a6..900104345 100644 --- a/src/rendering/hwrenderer/scene/hw_drawinfo.h +++ b/src/rendering/hwrenderer/scene/hw_drawinfo.h @@ -225,19 +225,19 @@ struct HWDrawInfo VPUniforms.mClipHeight = 0; } - void PushVisibleSurface(LevelMeshSurface* surface) + void PushVisibleTile(int tileIndex) { if (outer) { - outer->PushVisibleSurface(surface); + outer->PushVisibleTile(tileIndex); return; } - if (surface->LightmapTileIndex < 0) + if (tileIndex < 0) return; - LightmapTile* tile = &Level->levelMesh->LightmapTiles[surface->LightmapTileIndex]; - if (lm_always_update || surface->AlwaysUpdate) + LightmapTile* tile = &Level->levelMesh->LightmapTiles[tileIndex]; + if (lm_always_update || tile->AlwaysUpdate) { tile->NeedsUpdate = true; } diff --git a/src/rendering/hwrenderer/scene/hw_drawstructs.h b/src/rendering/hwrenderer/scene/hw_drawstructs.h index fa0f098ea..0395d954b 100644 --- a/src/rendering/hwrenderer/scene/hw_drawstructs.h +++ b/src/rendering/hwrenderer/scene/hw_drawstructs.h @@ -174,7 +174,7 @@ class HWWall vertex_t* vertexes[2]; // required for polygon splitting FGameTexture* texture; TArray* lightlist; - DoomLevelMeshSurface* surface; + int lightmaptile; HWSeg glseg; float ztop[2], zbottom[2]; diff --git a/src/rendering/hwrenderer/scene/hw_flats.cpp b/src/rendering/hwrenderer/scene/hw_flats.cpp index 123675a73..9e1a58bfe 100644 --- a/src/rendering/hwrenderer/scene/hw_flats.cpp +++ b/src/rendering/hwrenderer/scene/hw_flats.cpp @@ -535,9 +535,9 @@ void HWFlat::ProcessSector(HWFlatDispatcher *di, FRenderState& state, sector_t * unsigned int count = sector->e->XFloor.ffloors.Size() + 1; for (unsigned int j = 0; j < count; j++) { - if (auto surface = sector->subsectors[i]->surface[plane].Size() > j ? sector->subsectors[i]->surface[plane][j] : nullptr) + if (int tile = sector->subsectors[i]->LightmapTiles[plane].Size() > j ? sector->subsectors[i]->LightmapTiles[plane][j] : -1) { - di->di->PushVisibleSurface(surface); + di->di->PushVisibleTile(tile); } } } diff --git a/src/rendering/hwrenderer/scene/hw_walls.cpp b/src/rendering/hwrenderer/scene/hw_walls.cpp index fa4c0adfa..ecb5661ea 100644 --- a/src/rendering/hwrenderer/scene/hw_walls.cpp +++ b/src/rendering/hwrenderer/scene/hw_walls.cpp @@ -1125,17 +1125,17 @@ void HWWall::DoTexture(HWWallDispatcher *di, FRenderState& state, int _type,seg_ if (di->di) { - if (seg->sidedef->surface.Size() >= 4 && type >= RENDERWALL_TOP && type <= RENDERWALL_BOTTOM) + if (seg->sidedef->LightmapTiles.Size() >= 4 && type >= RENDERWALL_TOP && type <= RENDERWALL_BOTTOM) { - surface = seg->sidedef->surface[type - RENDERWALL_TOP]; - if (surface && di->di) + lightmaptile = seg->sidedef->LightmapTiles[type - RENDERWALL_TOP]; + if (lightmaptile && di->di) { - di->di->PushVisibleSurface(surface); + di->di->PushVisibleTile(lightmaptile); } } else { - surface = nullptr; + lightmaptile = -1; } } else @@ -1150,7 +1150,7 @@ void HWWall::DoTexture(HWWallDispatcher *di, FRenderState& state, int _type,seg_ LevelMeshInfo.Type = ST_NONE; } LevelMeshInfo.ControlSector = nullptr; - surface = nullptr; + lightmaptile = -1; } float floatceilingref = ceilingrefheight + tci.RowOffset(seg->sidedef->GetTextureYOffset(texpos)); @@ -1209,12 +1209,12 @@ void HWWall::DoMidTexture(HWWallDispatcher *di, FRenderState& state, seg_t * seg { if (di->di) { - if (seg->sidedef->surface.Size() >= 4) + if (seg->sidedef->LightmapTiles.Size() >= 4) { - surface = seg->sidedef->surface[side_t::mid]; - if (surface && di->di) + lightmaptile = seg->sidedef->LightmapTiles[side_t::mid]; + if (lightmaptile >= 0 && di->di) { - di->di->PushVisibleSurface(surface); + di->di->PushVisibleTile(lightmaptile); } } } @@ -1222,7 +1222,7 @@ void HWWall::DoMidTexture(HWWallDispatcher *di, FRenderState& state, seg_t * seg { LevelMeshInfo.Type = ST_MIDDLESIDE; LevelMeshInfo.ControlSector = nullptr; - surface = nullptr; + lightmaptile = -1; } // Align the texture to the ORIGINAL sector's height!! @@ -1557,20 +1557,20 @@ void HWWall::BuildFFBlock(HWWallDispatcher *di, FRenderState& state, seg_t * seg if (di->di) { if (seg->sidedef == seg->linedef->sidedef[0]) - surface = seg->linedef->sidedef[1]->surface.Size() > 4 + roverIndex ? seg->linedef->sidedef[1]->surface[4 + roverIndex] : nullptr; + lightmaptile = seg->linedef->sidedef[1]->LightmapTiles.Size() > 4 + roverIndex ? seg->linedef->sidedef[1]->LightmapTiles[4 + roverIndex] : -1; else - surface = seg->linedef->sidedef[0]->surface.Size() > 4 + roverIndex ? seg->linedef->sidedef[0]->surface[4 + roverIndex] : nullptr; + lightmaptile = seg->linedef->sidedef[0]->LightmapTiles.Size() > 4 + roverIndex ? seg->linedef->sidedef[0]->LightmapTiles[4 + roverIndex] : -1; - if (surface) + if (lightmaptile > 0) { - di->di->PushVisibleSurface(surface); + di->di->PushVisibleTile(lightmaptile); } } else { LevelMeshInfo.Type = ST_MIDDLESIDE; LevelMeshInfo.ControlSector = rover->model; - surface = nullptr; + lightmaptile = -1; } if (rover->flags&FF_FOG) @@ -1936,7 +1936,7 @@ void HWWall::Process(HWWallDispatcher *di, FRenderState& state, seg_t *seg, sect } #endif - surface = nullptr; + lightmaptile = -1; LevelMeshInfo.Type = ST_NONE; LevelMeshInfo.ControlSector = nullptr; diff --git a/src/rendering/hwrenderer/scene/hw_walls_vertex.cpp b/src/rendering/hwrenderer/scene/hw_walls_vertex.cpp index 52b13763c..abace2bb3 100644 --- a/src/rendering/hwrenderer/scene/hw_walls_vertex.cpp +++ b/src/rendering/hwrenderer/scene/hw_walls_vertex.cpp @@ -195,9 +195,9 @@ void HWWall::SplitRightEdge(FFlatVertex *&ptr) int HWWall::CreateVertices(FFlatVertex *&ptr, bool split) { - if (surface && surface->LightmapTileIndex >= 0) + if (lightmaptile >= 0) { - LightmapTile* tile = &level.levelMesh->LightmapTiles[surface->LightmapTileIndex]; + LightmapTile* tile = &level.levelMesh->LightmapTiles[lightmaptile]; FVector2 lolft = tile->ToUV(FVector3(glseg.x1, glseg.y1, zbottom[0]), level.levelMesh->LMTextureSize); FVector2 uplft = tile->ToUV(FVector3(glseg.x1, glseg.y1, ztop[0]), level.levelMesh->LMTextureSize); FVector2 uprgt = tile->ToUV(FVector3(glseg.x2, glseg.y2, ztop[1]), level.levelMesh->LMTextureSize);