- add back support for writing a level

This commit is contained in:
Magnus Norddahl 2018-10-27 11:34:18 +02:00
parent 5a8927506a
commit 484737bb66
4 changed files with 1275 additions and 113 deletions

File diff suppressed because it is too large Load diff

View file

@ -7,20 +7,21 @@
#include "framework/tarray.h"
#include "nodebuilder/nodebuild.h"
#include "blockmapbuilder/blockmapbuilder.h"
#include "lightmap/lightmap.h"
#include <zlib.h>
class ZLibOut
{
public:
ZLibOut (FWadWriter &out);
~ZLibOut ();
ZLibOut(FWadWriter &out);
~ZLibOut();
ZLibOut &operator << (BYTE);
ZLibOut &operator << (WORD);
ZLibOut &operator << (SWORD);
ZLibOut &operator << (DWORD);
ZLibOut &operator << (fixed_t);
void Write (BYTE *data, int len);
void Write(BYTE *data, int len);
private:
enum { BUFFER_SIZE = 8192 };
@ -31,31 +32,70 @@ private:
FWadWriter &Out;
};
class FLevelLoader
class FProcessor
{
public:
FLevelLoader (FWadReader &inwad, int lump);
FProcessor(FWadReader &inwad, int lump);
void BuildNodes ();
FLevel Level;
void BuildNodes();
void BuildLightmaps(const char *configFile);
void Write(FWadWriter &out);
private:
void LoadUDMF();
void LoadThings ();
void LoadLines ();
void LoadVertices ();
void LoadSides ();
void LoadSectors ();
void GetPolySpots ();
void LoadThings();
void LoadLines();
void LoadVertices();
void LoadSides();
void LoadSectors();
void GetPolySpots();
MapNodeEx *NodesToEx (const MapNode *nodes, int count);
MapSubsectorEx *SubsectorsToEx (const MapSubsector *ssec, int count);
MapSegGLEx *SegGLsToEx (const MapSegGL *segs, int count);
MapNodeEx *NodesToEx(const MapNode *nodes, int count);
MapSubsectorEx *SubsectorsToEx(const MapSubsector *ssec, int count);
MapSegGLEx *SegGLsToEx(const MapSegGL *segs, int count);
BYTE *FixReject (const BYTE *oldreject);
BYTE *FixReject(const BYTE *oldreject);
bool CheckForFracSplitters(const MapNodeEx *nodes, int count);
void WriteLines(FWadWriter &out);
void WriteVertices(FWadWriter &out, int count);
void WriteSectors(FWadWriter &out);
void WriteSides(FWadWriter &out);
void WriteSegs(FWadWriter &out);
void WriteSSectors(FWadWriter &out) const;
void WriteNodes(FWadWriter &out) const;
void WriteBlockmap(FWadWriter &out);
void WriteReject(FWadWriter &out);
void WriteGLVertices(FWadWriter &out, bool v5);
void WriteGLSegs(FWadWriter &out, bool v5);
void WriteGLSegs5(FWadWriter &out);
void WriteGLSSect(FWadWriter &out, bool v5);
void WriteGLNodes(FWadWriter &out, bool v5);
void WriteBSPZ(FWadWriter &out, const char *label);
void WriteGLBSPZ(FWadWriter &out, const char *label);
void WriteVerticesZ(ZLibOut &out, const WideVertex *verts, int orgverts, int newverts);
void WriteSubsectorsZ(ZLibOut &out, const MapSubsectorEx *subs, int numsubs);
void WriteSegsZ(ZLibOut &out, const MapSegEx *segs, int numsegs);
void WriteGLSegsZ(ZLibOut &out, const MapSegGLEx *segs, int numsegs, int nodever);
void WriteNodesZ(ZLibOut &out, const MapNodeEx *nodes, int numnodes, int nodever);
void WriteBSPX(FWadWriter &out, const char *label);
void WriteGLBSPX(FWadWriter &out, const char *label);
void WriteVerticesX(FWadWriter &out, const WideVertex *verts, int orgverts, int newverts);
void WriteSubsectorsX(FWadWriter &out, const MapSubsectorEx *subs, int numsubs);
void WriteSegsX(FWadWriter &out, const MapSegEx *segs, int numsegs);
void WriteGLSegsX(FWadWriter &out, const MapSegGLEx *segs, int numsegs, int nodever);
void WriteNodesX(FWadWriter &out, const MapNodeEx *nodes, int numnodes, int nodever);
void WriteNodes2(FWadWriter &out, const char *name, const MapNodeEx *zaNodes, int count) const;
void WriteSSectors2(FWadWriter &out, const char *name, const MapSubsectorEx *zaSubs, int count) const;
void WriteNodes5(FWadWriter &out, const char *name, const MapNodeEx *zaNodes, int count) const;
void WriteSSectors5(FWadWriter &out, const char *name, const MapSubsectorEx *zaSubs, int count) const;
const char *ParseKey(const char *&value);
bool CheckKey(const char *&key, const char *&value);
void ParseThing(IntThing *th);
@ -66,6 +106,18 @@ private:
void ParseMapProperties();
void ParseTextMap(int lump);
void WriteProps(FWadWriter &out, TArray<UDMFKey> &props);
void WriteIntProp(FWadWriter &out, const char *key, int value);
void WriteThingUDMF(FWadWriter &out, IntThing *th, int num);
void WriteLinedefUDMF(FWadWriter &out, IntLineDef *ld, int num);
void WriteSidedefUDMF(FWadWriter &out, IntSideDef *sd, int num);
void WriteSectorUDMF(FWadWriter &out, IntSector *sec, int num);
void WriteVertexUDMF(FWadWriter &out, IntVertex *vt, int num);
void WriteTextMap(FWadWriter &out);
void WriteUDMF(FWadWriter &out);
FLevel Level;
TArray<FNodeBuilder::FPolyStart> PolyStarts;
TArray<FNodeBuilder::FPolyStart> PolyAnchors;
@ -74,4 +126,8 @@ private:
FWadReader &Wad;
int Lump;
bool NodesBuilt = false;
bool LightmapsBuilt = false;
kexLightmapBuilder LMBuilder;
};

View file

@ -73,7 +73,7 @@ StringBuffer stbuf;
//
//===========================================================================
const char *FLevelLoader::ParseKey(const char *&value)
const char *FProcessor::ParseKey(const char *&value)
{
SC_MustGetString();
const char *key = stbuf.Copy(sc_String);
@ -90,7 +90,7 @@ const char *FLevelLoader::ParseKey(const char *&value)
return key;
}
bool FLevelLoader::CheckKey(const char *&key, const char *&value)
bool FProcessor::CheckKey(const char *&key, const char *&value)
{
SC_SavePos();
SC_MustGetString();
@ -138,7 +138,7 @@ fixed_t CheckFixed(const char *key)
//
//===========================================================================
void FLevelLoader::ParseThing(IntThing *th)
void FProcessor::ParseThing(IntThing *th)
{
SC_MustGetStringName("{");
while (!SC_CheckString("}"))
@ -178,7 +178,7 @@ void FLevelLoader::ParseThing(IntThing *th)
//
//===========================================================================
void FLevelLoader::ParseLinedef(IntLineDef *ld)
void FProcessor::ParseLinedef(IntLineDef *ld)
{
SC_MustGetStringName("{");
ld->v1 = ld->v2 = ld->sidenum[0] = ld->sidenum[1] = NO_INDEX;
@ -229,7 +229,7 @@ void FLevelLoader::ParseLinedef(IntLineDef *ld)
//
//===========================================================================
void FLevelLoader::ParseSidedef(IntSideDef *sd)
void FProcessor::ParseSidedef(IntSideDef *sd)
{
SC_MustGetStringName("{");
sd->sector = NO_INDEX;
@ -256,7 +256,7 @@ void FLevelLoader::ParseSidedef(IntSideDef *sd)
//
//===========================================================================
void FLevelLoader::ParseSector(IntSector *sec)
void FProcessor::ParseSector(IntSector *sec)
{
SC_MustGetStringName("{");
while (!SC_CheckString("}"))
@ -279,7 +279,7 @@ void FLevelLoader::ParseSector(IntSector *sec)
//
//===========================================================================
void FLevelLoader::ParseVertex(WideVertex *vt, IntVertex *vtp)
void FProcessor::ParseVertex(WideVertex *vt, IntVertex *vtp)
{
vt->x = vt->y = 0;
SC_MustGetStringName("{");
@ -310,7 +310,7 @@ void FLevelLoader::ParseVertex(WideVertex *vt, IntVertex *vtp)
//
//===========================================================================
void FLevelLoader::ParseMapProperties()
void FProcessor::ParseMapProperties()
{
const char *key, *value;
@ -337,7 +337,7 @@ void FLevelLoader::ParseMapProperties()
//
//===========================================================================
void FLevelLoader::ParseTextMap(int lump)
void FProcessor::ParseTextMap(int lump)
{
char *buffer;
int buffersize;
@ -393,7 +393,214 @@ void FLevelLoader::ParseTextMap(int lump)
//
//===========================================================================
void FLevelLoader::LoadUDMF()
void FProcessor::LoadUDMF()
{
ParseTextMap(Lump+1);
}
//===========================================================================
//
// writes a property list
//
//===========================================================================
void FProcessor::WriteProps(FWadWriter &out, TArray<UDMFKey> &props)
{
for(unsigned i=0; i< props.Size(); i++)
{
out.AddToLump(props[i].key, (int)strlen(props[i].key));
out.AddToLump(" = ", 3);
out.AddToLump(props[i].value, (int)strlen(props[i].value));
out.AddToLump(";\n", 2);
}
}
//===========================================================================
//
// writes an integer property
//
//===========================================================================
void FProcessor::WriteIntProp(FWadWriter &out, const char *key, int value)
{
char buffer[20];
out.AddToLump(key, (int)strlen(key));
out.AddToLump(" = ", 3);
sprintf(buffer, "%d;\n", value);
out.AddToLump(buffer, (int)strlen(buffer));
}
//===========================================================================
//
// writes a UDMF thing
//
//===========================================================================
void FProcessor::WriteThingUDMF(FWadWriter &out, IntThing *th, int num)
{
out.AddToLump("thing", 5);
if (WriteComments)
{
char buffer[32];
int len = sprintf(buffer, " // %d", num);
out.AddToLump(buffer, len);
}
out.AddToLump("\n{\n", 3);
WriteProps(out, th->props);
out.AddToLump("}\n\n", 3);
}
//===========================================================================
//
// writes a UDMF linedef
//
//===========================================================================
void FProcessor::WriteLinedefUDMF(FWadWriter &out, IntLineDef *ld, int num)
{
out.AddToLump("linedef", 7);
if (WriteComments)
{
char buffer[32];
int len = sprintf(buffer, " // %d", num);
out.AddToLump(buffer, len);
}
out.AddToLump("\n{\n", 3);
WriteIntProp(out, "v1", ld->v1);
WriteIntProp(out, "v2", ld->v2);
if (ld->sidenum[0] != NO_INDEX) WriteIntProp(out, "sidefront", ld->sidenum[0]);
if (ld->sidenum[1] != NO_INDEX) WriteIntProp(out, "sideback", ld->sidenum[1]);
WriteProps(out, ld->props);
out.AddToLump("}\n\n", 3);
}
//===========================================================================
//
// writes a UDMF sidedef
//
//===========================================================================
void FProcessor::WriteSidedefUDMF(FWadWriter &out, IntSideDef *sd, int num)
{
out.AddToLump("sidedef", 7);
if (WriteComments)
{
char buffer[32];
int len = sprintf(buffer, " // %d", num);
out.AddToLump(buffer, len);
}
out.AddToLump("\n{\n", 3);
WriteIntProp(out, "sector", sd->sector);
WriteProps(out, sd->props);
out.AddToLump("}\n\n", 3);
}
//===========================================================================
//
// writes a UDMF sector
//
//===========================================================================
void FProcessor::WriteSectorUDMF(FWadWriter &out, IntSector *sec, int num)
{
out.AddToLump("sector", 6);
if (WriteComments)
{
char buffer[32];
int len = sprintf(buffer, " // %d", num);
out.AddToLump(buffer, len);
}
out.AddToLump("\n{\n", 3);
WriteProps(out, sec->props);
out.AddToLump("}\n\n", 3);
}
//===========================================================================
//
// writes a UDMF vertex
//
//===========================================================================
void FProcessor::WriteVertexUDMF(FWadWriter &out, IntVertex *vt, int num)
{
out.AddToLump("vertex", 6);
if (WriteComments)
{
char buffer[32];
int len = sprintf(buffer, " // %d", num);
out.AddToLump(buffer, len);
}
out.AddToLump("\n{\n", 3);
WriteProps(out, vt->props);
out.AddToLump("}\n\n", 3);
}
//===========================================================================
//
// writes a UDMF text map
//
//===========================================================================
void FProcessor::WriteTextMap(FWadWriter &out)
{
out.StartWritingLump("TEXTMAP");
WriteProps(out, Level.props);
for(int i = 0; i < Level.NumThings(); i++)
{
WriteThingUDMF(out, &Level.Things[i], i);
}
for(int i = 0; i < Level.NumOrgVerts; i++)
{
WideVertex *vt = &Level.Vertices[i];
if (vt->index <= 0)
{
// not valid!
throw std::runtime_error("Invalid vertex data.");
}
WriteVertexUDMF(out, &Level.VertexProps[vt->index-1], i);
}
for(int i = 0; i < Level.NumLines(); i++)
{
WriteLinedefUDMF(out, &Level.Lines[i], i);
}
for(int i = 0; i < Level.NumSides(); i++)
{
WriteSidedefUDMF(out, &Level.Sides[i], i);
}
for(int i = 0; i < Level.NumSectors(); i++)
{
WriteSectorUDMF(out, &Level.Sectors[i], i);
}
}
//===========================================================================
//
// writes an UDMF map
//
//===========================================================================
void FProcessor::WriteUDMF(FWadWriter &out)
{
out.CopyLump (Wad, Lump);
WriteTextMap(out);
if (ForceCompression) WriteGLBSPZ (out, "ZNODES");
else WriteGLBSPX (out, "ZNODES");
// copy everything except existing nodes, blockmap and reject
for(int i=Lump+2; stricmp(Wad.LumpName(i), "ENDMAP") && i < Wad.NumLumps(); i++)
{
const char *lumpname = Wad.LumpName(i);
if (stricmp(lumpname, "ZNODES") &&
stricmp(lumpname, "BLOCKMAP") &&
stricmp(lumpname, "REJECT"))
{
out.CopyLump(Wad, i);
}
}
out.CreateLabel("ENDMAP");
}

View file

@ -7,7 +7,6 @@
#include "framework/zdray.h"
#include "wad/wad.h"
#include "level/level.h"
#include "lightmap/lightmap.h"
static void ParseArgs(int argc, char **argv);
static void ShowUsage();
@ -19,6 +18,18 @@ const char *OutName = "zdray.bin";
bool ShowMap = false;
bool ShowWarnings = false;
bool BuildGLNodes = true;
bool ConformNodes = false;
bool GLOnly = true;
bool CompressNodes = true;
bool CompressGLNodes = true;
bool ForceCompression = true;
bool V5GLNodes = true;
bool HaveSSE1 = true;
bool HaveSSE2 = true;
int SSELevel = 2;
bool WriteComments = true;
// Constants that used to be args in zdbsp
bool NoPrune = false;
EBlockmapMode BlockmapMode = EBM_Rebuild;
@ -68,21 +79,9 @@ int main(int argc, char **argv)
{
if (inwad.IsMap(lump) && (!Map || stricmp(inwad.LumpName(lump), Map) == 0))
{
FLevelLoader loader(inwad, lump);
loader.BuildNodes();
loader.Level.ParseConfigFile("lightconfig.txt");
loader.Level.SetupDlight();
Surface_AllocateFromMap(loader.Level);
loader.Level.CreateLights();
kexLightmapBuilder builder;
builder.CreateLightmaps(loader.Level);
builder.WriteTexturesToTGA();
builder.WriteMeshToOBJ();
loader.Level.CleanupThingLights();
FProcessor processor(inwad, lump);
processor.BuildNodes();
processor.BuildLightmaps("lightconfig.txt");
lump = inwad.LumpAfterMap(lump);
}