diff --git a/src/textures/formats/automaptexture.cpp b/src/textures/formats/automaptexture.cpp index 80395b8ee..299727d83 100644 --- a/src/textures/formats/automaptexture.cpp +++ b/src/textures/formats/automaptexture.cpp @@ -64,11 +64,11 @@ public: // //========================================================================== -FTexture *AutomapTexture_TryCreate(FileReader &data, int lumpnum) +FImageSource *AutomapImage_TryCreate(FileReader &data, int lumpnum) { if (data.GetLength() < 320) return nullptr; if (!Wads.CheckLumpName(lumpnum, "AUTOPAGE")) return nullptr; - return new FImageTexture(new FAutomapTexture(lumpnum)); + return new FAutomapTexture(lumpnum); } //========================================================================== diff --git a/src/textures/formats/ddstexture.cpp b/src/textures/formats/ddstexture.cpp index 31ec4f01f..810f91fe2 100644 --- a/src/textures/formats/ddstexture.cpp +++ b/src/textures/formats/ddstexture.cpp @@ -218,7 +218,7 @@ static bool CheckDDS (FileReader &file) // //========================================================================== -FTexture *DDSTexture_TryCreate (FileReader &data, int lumpnum) +FImageSource *DDSImage_TryCreate (FileReader &data, int lumpnum) { union { @@ -273,7 +273,7 @@ FTexture *DDSTexture_TryCreate (FileReader &data, int lumpnum) { return NULL; } - return new FImageTexture(new FDDSTexture (data, lumpnum, &surfdesc)); + return new FDDSTexture (data, lumpnum, &surfdesc); } //========================================================================== diff --git a/src/textures/formats/emptytexture.cpp b/src/textures/formats/emptytexture.cpp index fe8c1e901..11710f226 100644 --- a/src/textures/formats/emptytexture.cpp +++ b/src/textures/formats/emptytexture.cpp @@ -60,7 +60,7 @@ public: // //========================================================================== -FTexture *EmptyTexture_TryCreate(FileReader & file, int lumpnum) +FImageSource *EmptyImage_TryCreate(FileReader & file, int lumpnum) { char check[8]; if (file.GetLength() != 8) return NULL; @@ -68,7 +68,7 @@ FTexture *EmptyTexture_TryCreate(FileReader & file, int lumpnum) if (file.Read(check, 8) != 8) return NULL; if (memcmp(check, "\0\0\0\0\0\0\0\0", 8)) return NULL; - return new FImageTexture(new FEmptyTexture(lumpnum)); + return new FEmptyTexture(lumpnum); } //========================================================================== diff --git a/src/textures/formats/flattexture.cpp b/src/textures/formats/flattexture.cpp index c6ce44fb8..a0982645f 100644 --- a/src/textures/formats/flattexture.cpp +++ b/src/textures/formats/flattexture.cpp @@ -62,9 +62,9 @@ public: // //========================================================================== -FTexture *FlatTexture_TryCreate(FileReader & file, int lumpnum) +FImageSource *FlatImage_TryCreate(FileReader & file, int lumpnum) { - return new FImageTexture(new FFlatTexture(lumpnum)); + return new FFlatTexture(lumpnum); } //========================================================================== diff --git a/src/textures/formats/imgztexture.cpp b/src/textures/formats/imgztexture.cpp index e505c0714..681f39d97 100644 --- a/src/textures/formats/imgztexture.cpp +++ b/src/textures/formats/imgztexture.cpp @@ -79,7 +79,7 @@ public: // //========================================================================== -FTexture *IMGZTexture_TryCreate(FileReader & file, int lumpnum) +FImageSource *IMGZImage_TryCreate(FileReader & file, int lumpnum) { uint32_t magic = 0; uint16_t w, h; @@ -94,7 +94,7 @@ FTexture *IMGZTexture_TryCreate(FileReader & file, int lumpnum) l = file.ReadInt16(); t = file.ReadInt16(); ispalette = checkIMGZPalette(file); - return new FImageTexture(new FIMGZTexture(lumpnum, w, h, l, t, !ispalette)); + return new FIMGZTexture(lumpnum, w, h, l, t, !ispalette); } //========================================================================== diff --git a/src/textures/formats/jpegtexture.cpp b/src/textures/formats/jpegtexture.cpp index b41549c02..451f91f15 100644 --- a/src/textures/formats/jpegtexture.cpp +++ b/src/textures/formats/jpegtexture.cpp @@ -195,7 +195,7 @@ public: // //========================================================================== -FTexture *JPEGTexture_TryCreate(FileReader & data, int lumpnum) +FImageSource *JPEGImage_TryCreate(FileReader & data, int lumpnum) { union { @@ -236,7 +236,7 @@ FTexture *JPEGTexture_TryCreate(FileReader & data, int lumpnum) { return NULL; } - return new FImageTexture(new FJPEGTexture (lumpnum, BigShort(first4bytes.w[1]), BigShort(first4bytes.w[0]))); + return new FJPEGTexture (lumpnum, BigShort(first4bytes.w[1]), BigShort(first4bytes.w[0])); } //========================================================================== diff --git a/src/textures/formats/patchtexture.cpp b/src/textures/formats/patchtexture.cpp index ca6e54755..7a5de9c31 100644 --- a/src/textures/formats/patchtexture.cpp +++ b/src/textures/formats/patchtexture.cpp @@ -125,7 +125,7 @@ static bool CheckIfPatch(FileReader & file, bool &isalpha) // //========================================================================== -FTexture *PatchTexture_TryCreate(FileReader & file, int lumpnum) +FImageSource *PatchImage_TryCreate(FileReader & file, int lumpnum) { patch_t header; bool isalpha; @@ -136,7 +136,7 @@ FTexture *PatchTexture_TryCreate(FileReader & file, int lumpnum) header.height = file.ReadUInt16(); header.leftoffset = file.ReadInt16(); header.topoffset = file.ReadInt16(); - return new FImageTexture(new FPatchTexture(lumpnum, &header, isalpha)); + return new FPatchTexture(lumpnum, &header, isalpha); } //========================================================================== diff --git a/src/textures/formats/pcxtexture.cpp b/src/textures/formats/pcxtexture.cpp index f2e9f828d..708f36d81 100644 --- a/src/textures/formats/pcxtexture.cpp +++ b/src/textures/formats/pcxtexture.cpp @@ -103,7 +103,7 @@ protected: // //========================================================================== -FTexture * PCXTexture_TryCreate(FileReader & file, int lumpnum) +FImageSource * PCXImage_TryCreate(FileReader & file, int lumpnum) { PCXHeader hdr; @@ -132,7 +132,7 @@ FTexture * PCXTexture_TryCreate(FileReader & file, int lumpnum) file.Seek(0, FileReader::SeekSet); file.Read(&hdr, sizeof(hdr)); - return new FImageTexture(new FPCXTexture(lumpnum, hdr)); + return new FPCXTexture(lumpnum, hdr); } //========================================================================== diff --git a/src/textures/formats/pngtexture.cpp b/src/textures/formats/pngtexture.cpp index 1990aa6cb..37272125e 100644 --- a/src/textures/formats/pngtexture.cpp +++ b/src/textures/formats/pngtexture.cpp @@ -82,7 +82,7 @@ protected: // //========================================================================== -FTexture *PNGTexture_TryCreate(FileReader & data, int lumpnum) +FImageSource *PNGImage_TryCreate(FileReader & data, int lumpnum) { union { @@ -141,7 +141,7 @@ FTexture *PNGTexture_TryCreate(FileReader & data, int lumpnum) } } - return new FImageTexture(new FPNGTexture (data, lumpnum, FString(), width, height, bitdepth, colortype, interlace)); + return new FPNGTexture (data, lumpnum, FString(), width, height, bitdepth, colortype, interlace); } //========================================================================== diff --git a/src/textures/formats/rawpagetexture.cpp b/src/textures/formats/rawpagetexture.cpp index 6fd805ff5..0edaa9497 100644 --- a/src/textures/formats/rawpagetexture.cpp +++ b/src/textures/formats/rawpagetexture.cpp @@ -137,10 +137,10 @@ static bool CheckIfRaw(FileReader & data) // //========================================================================== -FTexture *RawPageTexture_TryCreate(FileReader & file, int lumpnum) +FImageSource *RawPageImage_TryCreate(FileReader & file, int lumpnum) { if (!CheckIfRaw(file)) return nullptr; - return new FImageTexture(new FRawPageTexture(lumpnum)); + return new FRawPageTexture(lumpnum); } diff --git a/src/textures/formats/tgatexture.cpp b/src/textures/formats/tgatexture.cpp index 9bc8500f8..cfb0f4890 100644 --- a/src/textures/formats/tgatexture.cpp +++ b/src/textures/formats/tgatexture.cpp @@ -94,7 +94,7 @@ protected: // //========================================================================== -FTexture *TGATexture_TryCreate(FileReader & file, int lumpnum) +FImageSource *TGAImage_TryCreate(FileReader & file, int lumpnum) { TGAHeader hdr; @@ -119,7 +119,7 @@ FTexture *TGATexture_TryCreate(FileReader & file, int lumpnum) hdr.width = LittleShort(hdr.width); hdr.height = LittleShort(hdr.height); - return new FImageTexture(new FTGATexture(lumpnum, &hdr)); + return new FTGATexture(lumpnum, &hdr); } //========================================================================== diff --git a/src/textures/hires/hirestex.cpp b/src/textures/hires/hirestex.cpp index 7f65341ea..b2edce48c 100644 --- a/src/textures/hires/hirestex.cpp +++ b/src/textures/hires/hirestex.cpp @@ -367,8 +367,7 @@ unsigned char *FTexture::LoadHiresTexture(int *width, int *height) if (HiresLump >= 0) { - HiresTexture = FTexture::CreateTexture(HiresLump, ETextureType::Any); - HiresTexture->Name = ""; + HiresTexture = FTexture::CreateTexture("", HiresLump, ETextureType::Any); TexMan.AddTexture(HiresTexture); // let the texture manager manage this. } } diff --git a/src/textures/image.cpp b/src/textures/image.cpp index 7f246ba02..c5d29ae5f 100644 --- a/src/textures/image.cpp +++ b/src/textures/image.cpp @@ -37,8 +37,13 @@ #include "v_video.h" #include "bitmap.h" #include "image.h" +#include "w_wad.h" +#include "files.h" FMemArena FImageSource::ImageArena(32768); +TArrayFImageSource::ImageForLump; +int FImageSource::NextID; + //=========================================================================== // // the default just returns an empty texture. @@ -82,3 +87,78 @@ int FImageSource::CopyTranslatedPixels(FBitmap *bmp, PalEntry *remap) bmp->CopyPixelData(0, 0, ppix.Data(), Width, Height, Height, 1, 0, remap, nullptr); return 0; } + + +//========================================================================== +// +// +// +//========================================================================== + +typedef FImageSource * (*CreateFunc)(FileReader & file, int lumpnum); + +struct TexCreateInfo +{ + CreateFunc TryCreate; + ETextureType usetype; +}; + +FImageSource *IMGZImage_TryCreate(FileReader &, int lumpnum); +FImageSource *PNGImage_TryCreate(FileReader &, int lumpnum); +FImageSource *JPEGImage_TryCreate(FileReader &, int lumpnum); +FImageSource *DDSImage_TryCreate(FileReader &, int lumpnum); +FImageSource *PCXImage_TryCreate(FileReader &, int lumpnum); +FImageSource *TGAImage_TryCreate(FileReader &, int lumpnum); +FImageSource *RawPageImage_TryCreate(FileReader &, int lumpnum); +FImageSource *FlatImage_TryCreate(FileReader &, int lumpnum); +FImageSource *PatchImage_TryCreate(FileReader &, int lumpnum); +FImageSource *EmptyImage_TryCreate(FileReader &, int lumpnum); +FImageSource *AutomapImage_TryCreate(FileReader &, int lumpnum); + + +// Examines the lump contents to decide what type of texture to create, +// and creates the texture. +FImageSource * FImageSource::GetImage(int lumpnum, ETextureType usetype) +{ + static TexCreateInfo CreateInfo[] = { + { IMGZImage_TryCreate, ETextureType::Any }, + { PNGImage_TryCreate, ETextureType::Any }, + { JPEGImage_TryCreate, ETextureType::Any }, + { DDSImage_TryCreate, ETextureType::Any }, + { PCXImage_TryCreate, ETextureType::Any }, + { TGAImage_TryCreate, ETextureType::Any }, + { RawPageImage_TryCreate, ETextureType::MiscPatch }, + { FlatImage_TryCreate, ETextureType::Flat }, + { PatchImage_TryCreate, ETextureType::Any }, + { EmptyImage_TryCreate, ETextureType::Any }, + { AutomapImage_TryCreate, ETextureType::MiscPatch }, + }; + + if (lumpnum == -1) return nullptr; + + unsigned size = ImageForLump.Size(); + if (size <= (unsigned)lumpnum) + { + // Hires textures can be added dynamically to the end of the lump array, so this must be checked each time. + ImageForLump.Resize(lumpnum + 1); + for (; size < ImageForLump.Size(); size++) ImageForLump[size] = nullptr; + } + // An image for this lump already exists. We do not need another one. + if (ImageForLump[lumpnum] != nullptr) return ImageForLump[lumpnum]; + + auto data = Wads.OpenLumpReader(lumpnum); + + for (size_t i = 0; i < countof(CreateInfo); i++) + { + if ((CreateInfo[i].usetype == usetype || CreateInfo[i].usetype == ETextureType::Any)) + { + auto image = CreateInfo[i].TryCreate(data, lumpnum); + if (image != nullptr) + { + ImageForLump[lumpnum] = image; + return image; + } + } + } + return nullptr; +} diff --git a/src/textures/image.h b/src/textures/image.h index 8c9b314b6..7101c2816 100644 --- a/src/textures/image.h +++ b/src/textures/image.h @@ -14,10 +14,14 @@ class FImageSource protected: static FMemArena ImageArena; + static TArrayImageForLump; + static int NextID; + int SourceLump; int Width = 0, Height = 0; int LeftOffset = 0, TopOffset = 0; // Offsets stored in the image. bool bUseGamePalette = false; // true if this is an image without its own color set. + int ImageID = -1; public: @@ -41,8 +45,9 @@ public: virtual TArray GetPalettedPixels(int conversion); // 'noremap0' will only be looked at by FPatchTexture and forwarded by FMultipatchTexture. virtual int CopyPixels(FBitmap *bmp, int conversion); // This will always ignore 'luminance'. int CopyTranslatedPixels(FBitmap *bmp, PalEntry *remap); - static void ClearImages() { ImageArena.FreeAll(); } - + static void ClearImages() { ImageArena.FreeAll(); ImageForLump.Clear(); NextID = 0; } + static FImageSource * FImageSource::GetImage(int lumpnum, ETextureType usetype); + // Conversion option enum EType { @@ -51,7 +56,7 @@ public: noremap0 = 2 }; - FImageSource(int sourcelump = -1) : SourceLump(sourcelump) {} + FImageSource(int sourcelump = -1) : SourceLump(sourcelump) { ImageID = ++NextID; } virtual ~FImageSource() {} // Creates an image from the given lump. diff --git a/src/textures/texture.cpp b/src/textures/texture.cpp index 934f585b3..55fe8334e 100644 --- a/src/textures/texture.cpp +++ b/src/textures/texture.cpp @@ -85,91 +85,45 @@ void FTexture::InitGrayMap() // //========================================================================== -typedef FTexture * (*CreateFunc)(FileReader & file, int lumpnum); - -struct TexCreateInfo -{ - CreateFunc TryCreate; - ETextureType usetype; -}; - -FTexture *IMGZTexture_TryCreate(FileReader &, int lumpnum); -FTexture *PNGTexture_TryCreate(FileReader &, int lumpnum); -FTexture *JPEGTexture_TryCreate(FileReader &, int lumpnum); -FTexture *DDSTexture_TryCreate(FileReader &, int lumpnum); -FTexture *PCXTexture_TryCreate(FileReader &, int lumpnum); -FTexture *TGATexture_TryCreate(FileReader &, int lumpnum); -FTexture *RawPageTexture_TryCreate(FileReader &, int lumpnum); -FTexture *FlatTexture_TryCreate(FileReader &, int lumpnum); -FTexture *PatchTexture_TryCreate(FileReader &, int lumpnum); -FTexture *EmptyTexture_TryCreate(FileReader &, int lumpnum); -FTexture *AutomapTexture_TryCreate(FileReader &, int lumpnum); - // Examines the lump contents to decide what type of texture to create, // and creates the texture. -FTexture * FTexture::CreateTexture (int lumpnum, ETextureType usetype) +FTexture * FTexture::CreateTexture(const char *name, int lumpnum, ETextureType usetype) { - static TexCreateInfo CreateInfo[]={ - { IMGZTexture_TryCreate, ETextureType::Any }, - { PNGTexture_TryCreate, ETextureType::Any }, - { JPEGTexture_TryCreate, ETextureType::Any }, - { DDSTexture_TryCreate, ETextureType::Any }, - { PCXTexture_TryCreate, ETextureType::Any }, - { TGATexture_TryCreate, ETextureType::Any }, - { RawPageTexture_TryCreate, ETextureType::MiscPatch }, - { FlatTexture_TryCreate, ETextureType::Flat }, - { PatchTexture_TryCreate, ETextureType::Any }, - { EmptyTexture_TryCreate, ETextureType::Any }, - { AutomapTexture_TryCreate, ETextureType::MiscPatch }, - }; + if (lumpnum == -1) return nullptr; - if (lumpnum == -1) return NULL; - - auto data = Wads.OpenLumpReader (lumpnum); - - for(size_t i = 0; i < countof(CreateInfo); i++) + auto image = FImageSource::GetImage(lumpnum, usetype); + if (image != nullptr) { - if ((CreateInfo[i].usetype == usetype || CreateInfo[i].usetype == ETextureType::Any)) + FTexture *tex = new FImageTexture(image); + if (tex != nullptr) { - FTexture * tex = CreateInfo[i].TryCreate(data, lumpnum); - if (tex != NULL) + tex->UseType = usetype; + if (usetype == ETextureType::Flat) { - tex->UseType = usetype; - if (usetype == ETextureType::Flat) - { - int w = tex->GetWidth(); - int h = tex->GetHeight(); + int w = tex->GetWidth(); + int h = tex->GetHeight(); - // Auto-scale flats with dimensions 128x128 and 256x256. - // In hindsight, a bad idea, but RandomLag made it sound better than it really is. - // Now we're stuck with this stupid behaviour. - if (w==128 && h==128) - { - tex->Scale.X = tex->Scale.Y = 2; - tex->bWorldPanning = true; - } - else if (w==256 && h==256) - { - tex->Scale.X = tex->Scale.Y = 4; - tex->bWorldPanning = true; - } + // Auto-scale flats with dimensions 128x128 and 256x256. + // In hindsight, a bad idea, but RandomLag made it sound better than it really is. + // Now we're stuck with this stupid behaviour. + if (w==128 && h==128) + { + tex->Scale.X = tex->Scale.Y = 2; + tex->bWorldPanning = true; + } + else if (w==256 && h==256) + { + tex->Scale.X = tex->Scale.Y = 4; + tex->bWorldPanning = true; } - return tex; } + tex->Name = name; + tex->Name.ToUpper(); + return tex; } } - return NULL; -} - -FTexture * FTexture::CreateTexture (const char *name, int lumpnum, ETextureType usetype) -{ - FTexture *tex = CreateTexture(lumpnum, usetype); - if (tex != NULL && name != NULL) { - tex->Name = name; - tex->Name.ToUpper(); - } - return tex; + return nullptr; } //========================================================================== diff --git a/src/textures/texturemanager.cpp b/src/textures/texturemanager.cpp index c21d9c623..66c43ac62 100644 --- a/src/textures/texturemanager.cpp +++ b/src/textures/texturemanager.cpp @@ -412,7 +412,9 @@ FTextureID FTextureManager::CreateTexture (int lumpnum, ETextureType usetype) { if (lumpnum != -1) { - FTexture *out = FTexture::CreateTexture(lumpnum, usetype); + FString str; + Wads.GetLumpName(str, lumpnum); + FTexture *out = FTexture::CreateTexture(str, lumpnum, usetype); if (out != NULL) return AddTexture (out); else @@ -559,7 +561,7 @@ void FTextureManager::AddHiresTextures (int wadnum) if (amount == 0) { // A texture with this name does not yet exist - FTexture * newtex = FTexture::CreateTexture (firsttx, ETextureType::Any); + FTexture * newtex = FTexture::CreateTexture (Name, firsttx, ETextureType::Any); if (newtex != NULL) { newtex->UseType=ETextureType::Override; @@ -570,7 +572,7 @@ void FTextureManager::AddHiresTextures (int wadnum) { for(unsigned int i = 0; i < tlist.Size(); i++) { - FTexture * newtex = FTexture::CreateTexture (firsttx, ETextureType::Any); + FTexture * newtex = FTexture::CreateTexture ("", firsttx, ETextureType::Any); if (newtex != NULL) { FTexture * oldtex = Textures[tlist[i].GetIndex()].Texture; @@ -669,7 +671,7 @@ void FTextureManager::ParseTextureDef(int lump, FMultipatchTextureBuilder &build (sl=oldtex->GetSourceLump()) >= 0 && Wads.GetLumpNamespace(sl) == ns_sprites) ) { - FTexture * newtex = FTexture::CreateTexture (lumpnum, ETextureType::Any); + FTexture * newtex = FTexture::CreateTexture ("", lumpnum, ETextureType::Any); if (newtex != NULL) { // Replace the entire texture and adjust the scaling and offset factors. @@ -708,14 +710,13 @@ void FTextureManager::ParseTextureDef(int lump, FMultipatchTextureBuilder &build if (lumpnum>=0) { - FTexture *newtex = FTexture::CreateTexture(lumpnum, ETextureType::Override); + FTexture *newtex = FTexture::CreateTexture(src, lumpnum, ETextureType::Override); if (newtex != NULL) { // Replace the entire texture and adjust the scaling and offset factors. newtex->bWorldPanning = true; newtex->SetScaledSize(width, height); - newtex->Name = src; FTextureID oldtex = TexMan.CheckForTexture(src, ETextureType::MiscPatch); if (oldtex.isValid()) @@ -911,7 +912,7 @@ void FTextureManager::AddTexturesForWad(int wadnum, FMultipatchTextureBuilder &b // Try to create a texture from this lump and add it. // Unfortunately we have to look at everything that comes through here... - FTexture *out = FTexture::CreateTexture(i, skin ? ETextureType::SkinGraphic : ETextureType::MiscPatch); + FTexture *out = FTexture::CreateTexture(Name, i, skin ? ETextureType::SkinGraphic : ETextureType::MiscPatch); if (out != NULL) { diff --git a/src/textures/textures.h b/src/textures/textures.h index c1a08abca..ef154a9f6 100644 --- a/src/textures/textures.h +++ b/src/textures/textures.h @@ -252,7 +252,6 @@ class FTexture public: static FTexture *CreateTexture(const char *name, int lumpnum, ETextureType usetype); - static FTexture *CreateTexture(int lumpnum, ETextureType usetype); virtual ~FTexture (); virtual FImageSource *GetImage() const { return nullptr; } void AddAutoMaterials(); diff --git a/src/w_wad.h b/src/w_wad.h index a7009d65e..c223a6bd0 100644 --- a/src/w_wad.h +++ b/src/w_wad.h @@ -180,7 +180,6 @@ public: int GetNumWads () const; int AddExternalFile(const char *filename); - int AddData(const char *filename, int length); protected: