2017-04-17 10:27:19 +00:00
|
|
|
/*
|
|
|
|
** textures.h
|
|
|
|
**
|
|
|
|
**---------------------------------------------------------------------------
|
|
|
|
** Copyright 2005-2016 Randy Heit
|
|
|
|
** Copyright 2005-2016 Christoph Oelckers
|
|
|
|
** All rights reserved.
|
|
|
|
**
|
|
|
|
** Redistribution and use in source and binary forms, with or without
|
|
|
|
** modification, are permitted provided that the following conditions
|
|
|
|
** are met:
|
|
|
|
**
|
|
|
|
** 1. Redistributions of source code must retain the above copyright
|
|
|
|
** notice, this list of conditions and the following disclaimer.
|
|
|
|
** 2. Redistributions in binary form must reproduce the above copyright
|
|
|
|
** notice, this list of conditions and the following disclaimer in the
|
|
|
|
** documentation and/or other materials provided with the distribution.
|
|
|
|
** 3. The name of the author may not be used to endorse or promote products
|
|
|
|
** derived from this software without specific prior written permission.
|
|
|
|
**
|
|
|
|
** THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
|
|
|
|
** IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
|
|
|
|
** OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
|
|
|
|
** IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
|
|
|
|
** INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
|
|
|
|
** NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
|
|
|
|
** DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
|
|
|
|
** THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
|
|
|
|
** (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
|
|
|
|
** THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
|
|
|
**---------------------------------------------------------------------------
|
|
|
|
**
|
|
|
|
*/
|
|
|
|
|
2016-03-01 15:47:10 +00:00
|
|
|
#ifndef __TEXTURES_H
|
|
|
|
#define __TEXTURES_H
|
|
|
|
|
2016-03-30 14:30:22 +00:00
|
|
|
#include "doomtype.h"
|
2016-03-26 12:37:44 +00:00
|
|
|
#include "vectors.h"
|
2016-06-10 11:50:34 +00:00
|
|
|
#include <vector>
|
2016-03-01 15:47:10 +00:00
|
|
|
|
2016-03-01 17:50:45 +00:00
|
|
|
struct FloatRect
|
|
|
|
{
|
|
|
|
float left,top;
|
|
|
|
float width,height;
|
|
|
|
|
|
|
|
|
|
|
|
void Offset(float xofs,float yofs)
|
|
|
|
{
|
|
|
|
left+=xofs;
|
|
|
|
top+=yofs;
|
|
|
|
}
|
|
|
|
void Scale(float xfac,float yfac)
|
|
|
|
{
|
|
|
|
left*=xfac;
|
|
|
|
width*=xfac;
|
|
|
|
top*=yfac;
|
|
|
|
height*=yfac;
|
|
|
|
}
|
|
|
|
};
|
|
|
|
|
|
|
|
|
2016-03-01 15:47:10 +00:00
|
|
|
class FBitmap;
|
|
|
|
struct FRemapTable;
|
|
|
|
struct FCopyInfo;
|
|
|
|
class FScanner;
|
|
|
|
|
|
|
|
// Texture IDs
|
|
|
|
class FTextureManager;
|
|
|
|
class FTerrainTypeArray;
|
2016-03-01 17:50:45 +00:00
|
|
|
class FGLTexture;
|
|
|
|
class FMaterial;
|
2016-03-01 15:47:10 +00:00
|
|
|
|
|
|
|
class FNullTextureID : public FTextureID
|
|
|
|
{
|
|
|
|
public:
|
|
|
|
FNullTextureID() : FTextureID(0) {}
|
|
|
|
};
|
|
|
|
|
|
|
|
//
|
|
|
|
// Animating textures and planes
|
|
|
|
//
|
|
|
|
// [RH] Expanded to work with a Hexen ANIMDEFS lump
|
|
|
|
//
|
|
|
|
|
|
|
|
struct FAnimDef
|
|
|
|
{
|
|
|
|
FTextureID BasePic;
|
2017-03-09 18:54:41 +00:00
|
|
|
uint16_t NumFrames;
|
|
|
|
uint16_t CurFrame;
|
|
|
|
uint8_t AnimType;
|
2016-03-01 15:47:10 +00:00
|
|
|
bool bDiscrete; // taken out of AnimType to have better control
|
2017-03-09 19:19:55 +00:00
|
|
|
uint32_t SwitchTime; // Time to advance to next frame
|
2016-03-01 15:47:10 +00:00
|
|
|
struct FAnimFrame
|
|
|
|
{
|
2017-03-09 19:19:55 +00:00
|
|
|
uint32_t SpeedMin; // Speeds are in ms, not tics
|
|
|
|
uint32_t SpeedRange;
|
2016-03-01 15:47:10 +00:00
|
|
|
FTextureID FramePic;
|
|
|
|
} Frames[1];
|
|
|
|
enum
|
|
|
|
{
|
|
|
|
ANIM_Forward,
|
|
|
|
ANIM_Backward,
|
|
|
|
ANIM_OscillateUp,
|
|
|
|
ANIM_OscillateDown,
|
|
|
|
ANIM_Random
|
|
|
|
};
|
|
|
|
|
2017-03-09 19:19:55 +00:00
|
|
|
void SetSwitchTime (uint32_t mstime);
|
2016-03-01 15:47:10 +00:00
|
|
|
};
|
|
|
|
|
|
|
|
struct FSwitchDef
|
|
|
|
{
|
|
|
|
FTextureID PreTexture; // texture to switch from
|
|
|
|
FSwitchDef *PairDef; // switch def to use to return to PreTexture
|
2017-03-09 18:54:41 +00:00
|
|
|
uint16_t NumFrames; // # of animation frames
|
2016-03-01 15:47:10 +00:00
|
|
|
bool QuestPanel; // Special texture for Strife mission
|
|
|
|
int Sound; // sound to play at start of animation. Changed to int to avoiud having to include s_sound here.
|
|
|
|
struct frame // Array of times followed by array of textures
|
|
|
|
{ // actual length of each array is <NumFrames>
|
2017-03-09 18:54:41 +00:00
|
|
|
uint16_t TimeMin;
|
|
|
|
uint16_t TimeRnd;
|
2016-03-01 15:47:10 +00:00
|
|
|
FTextureID Texture;
|
|
|
|
} frames[1];
|
|
|
|
};
|
|
|
|
|
|
|
|
struct FDoorAnimation
|
|
|
|
{
|
|
|
|
FTextureID BaseTexture;
|
|
|
|
FTextureID *TextureFrames;
|
|
|
|
int NumTextureFrames;
|
|
|
|
FName OpenSound;
|
|
|
|
FName CloseSound;
|
|
|
|
};
|
|
|
|
|
|
|
|
// Patches.
|
|
|
|
// A patch holds one or more columns.
|
|
|
|
// Patches are used for sprites and all masked pictures, and we compose
|
|
|
|
// textures from the TEXTURE1/2 lists of patches.
|
|
|
|
struct patch_t
|
|
|
|
{
|
2017-03-09 18:31:45 +00:00
|
|
|
int16_t width; // bounding box size
|
|
|
|
int16_t height;
|
|
|
|
int16_t leftoffset; // pixels to the left of origin
|
|
|
|
int16_t topoffset; // pixels below the origin
|
2017-03-09 19:19:55 +00:00
|
|
|
uint32_t columnofs[]; // only [width] used
|
2016-03-01 15:47:10 +00:00
|
|
|
// the [0] is &columnofs[width]
|
|
|
|
};
|
|
|
|
|
|
|
|
class FileReader;
|
|
|
|
|
|
|
|
// All FTextures present their data to the world in 8-bit format, but if
|
|
|
|
// the source data is something else, this is it.
|
|
|
|
enum FTextureFormat
|
|
|
|
{
|
|
|
|
TEX_Pal,
|
|
|
|
TEX_Gray,
|
|
|
|
TEX_RGB, // Actually ARGB
|
|
|
|
TEX_DXT1,
|
|
|
|
TEX_DXT2,
|
|
|
|
TEX_DXT3,
|
|
|
|
TEX_DXT4,
|
|
|
|
TEX_DXT5,
|
|
|
|
};
|
|
|
|
|
|
|
|
class FNativeTexture;
|
|
|
|
|
|
|
|
// Base texture class
|
|
|
|
class FTexture
|
|
|
|
{
|
|
|
|
public:
|
|
|
|
static FTexture *CreateTexture(const char *name, int lumpnum, int usetype);
|
|
|
|
static FTexture *CreateTexture(int lumpnum, int usetype);
|
|
|
|
virtual ~FTexture ();
|
|
|
|
|
2017-03-09 18:31:45 +00:00
|
|
|
int16_t LeftOffset, TopOffset;
|
2016-03-01 15:47:10 +00:00
|
|
|
|
2017-03-09 18:54:41 +00:00
|
|
|
uint8_t WidthBits, HeightBits;
|
2016-03-01 15:47:10 +00:00
|
|
|
|
2016-03-26 12:37:44 +00:00
|
|
|
DVector2 Scale;
|
2016-03-01 15:47:10 +00:00
|
|
|
|
|
|
|
int SourceLump;
|
|
|
|
FTextureID id;
|
|
|
|
|
|
|
|
FString Name;
|
2017-03-09 18:54:41 +00:00
|
|
|
uint8_t UseType; // This texture's primary purpose
|
|
|
|
|
|
|
|
uint8_t bNoDecals:1; // Decals should not stick to texture
|
|
|
|
uint8_t bNoRemap0:1; // Do not remap color 0 (used by front layer of parallax skies)
|
|
|
|
uint8_t bWorldPanning:1; // Texture is panned in world units rather than texels
|
|
|
|
uint8_t bMasked:1; // Texture (might) have holes
|
|
|
|
uint8_t bAlphaTexture:1; // Texture is an alpha channel without color information
|
|
|
|
uint8_t bHasCanvas:1; // Texture is based off FCanvasTexture
|
|
|
|
uint8_t bWarped:2; // This is a warped texture. Used to avoid multiple warps on one texture
|
|
|
|
uint8_t bComplex:1; // Will be used to mark extended MultipatchTextures that have to be
|
2016-03-01 15:47:10 +00:00
|
|
|
// fully composited before subjected to any kind of postprocessing instead of
|
|
|
|
// doing it per patch.
|
2017-03-09 18:54:41 +00:00
|
|
|
uint8_t bMultiPatch:1; // This is a multipatch texture (we really could use real type info for textures...)
|
|
|
|
uint8_t bKeepAround:1; // This texture was used as part of a multi-patch texture. Do not free it.
|
2016-03-01 15:47:10 +00:00
|
|
|
|
2017-03-09 18:54:41 +00:00
|
|
|
uint16_t Rotations;
|
2017-03-09 18:31:45 +00:00
|
|
|
int16_t SkyOffset;
|
2016-03-01 15:47:10 +00:00
|
|
|
|
|
|
|
enum // UseTypes
|
|
|
|
{
|
|
|
|
TEX_Any,
|
|
|
|
TEX_Wall,
|
|
|
|
TEX_Flat,
|
|
|
|
TEX_Sprite,
|
|
|
|
TEX_WallPatch,
|
|
|
|
TEX_Build,
|
|
|
|
TEX_SkinSprite,
|
|
|
|
TEX_Decal,
|
|
|
|
TEX_MiscPatch,
|
|
|
|
TEX_FontChar,
|
|
|
|
TEX_Override, // For patches between TX_START/TX_END
|
|
|
|
TEX_Autopage, // Automap background - used to enable the use of FAutomapTexture
|
|
|
|
TEX_SkinGraphic,
|
|
|
|
TEX_Null,
|
|
|
|
TEX_FirstDefined,
|
|
|
|
};
|
|
|
|
|
|
|
|
struct Span
|
|
|
|
{
|
2017-03-09 18:54:41 +00:00
|
|
|
uint16_t TopOffset;
|
|
|
|
uint16_t Length; // A length of 0 terminates this column
|
2016-03-01 15:47:10 +00:00
|
|
|
};
|
|
|
|
|
|
|
|
// Returns a single column of the texture
|
2017-03-09 18:54:41 +00:00
|
|
|
virtual const uint8_t *GetColumn (unsigned int column, const Span **spans_out) = 0;
|
2016-03-01 15:47:10 +00:00
|
|
|
|
2016-06-10 11:50:34 +00:00
|
|
|
// Returns a single column of the texture, in BGRA8 format
|
|
|
|
virtual const uint32_t *GetColumnBgra(unsigned int column, const Span **spans_out);
|
|
|
|
|
2016-03-01 15:47:10 +00:00
|
|
|
// Returns the whole texture, stored in column-major order
|
2017-03-09 18:54:41 +00:00
|
|
|
virtual const uint8_t *GetPixels () = 0;
|
2016-06-10 11:50:34 +00:00
|
|
|
|
|
|
|
// Returns the whole texture, stored in column-major order, in BGRA8 format
|
|
|
|
virtual const uint32_t *GetPixelsBgra();
|
|
|
|
|
2016-06-25 08:33:35 +00:00
|
|
|
// Returns true if GetPixelsBgra includes mipmaps
|
|
|
|
virtual bool Mipmapped() { return true; }
|
|
|
|
|
2016-03-01 15:47:10 +00:00
|
|
|
virtual int CopyTrueColorPixels(FBitmap *bmp, int x, int y, int rotate=0, FCopyInfo *inf = NULL);
|
|
|
|
int CopyTrueColorTranslated(FBitmap *bmp, int x, int y, int rotate, FRemapTable *remap, FCopyInfo *inf = NULL);
|
|
|
|
virtual bool UseBasePalette();
|
|
|
|
virtual int GetSourceLump() { return SourceLump; }
|
|
|
|
virtual FTexture *GetRedirect(bool wantwarped);
|
|
|
|
virtual FTexture *GetRawTexture(); // for FMultiPatchTexture to override
|
|
|
|
|
2016-06-13 19:39:55 +00:00
|
|
|
virtual void Unload ();
|
2016-03-01 15:47:10 +00:00
|
|
|
|
|
|
|
// Returns the native pixel format for this image
|
|
|
|
virtual FTextureFormat GetFormat();
|
|
|
|
|
|
|
|
// Returns a native 3D representation of the texture
|
|
|
|
FNativeTexture *GetNative(bool wrapping);
|
|
|
|
|
|
|
|
// Frees the native 3D representation of the texture
|
|
|
|
void KillNative();
|
|
|
|
|
|
|
|
// Fill the native texture buffer with pixel data for this image
|
2017-03-09 18:54:41 +00:00
|
|
|
virtual void FillBuffer(uint8_t *buff, int pitch, int height, FTextureFormat fmt);
|
2016-03-01 15:47:10 +00:00
|
|
|
|
|
|
|
int GetWidth () { return Width; }
|
|
|
|
int GetHeight () { return Height; }
|
|
|
|
|
2016-03-26 12:37:44 +00:00
|
|
|
int GetScaledWidth () { int foo = int((Width * 2) / Scale.X); return (foo >> 1) + (foo & 1); }
|
|
|
|
int GetScaledHeight () { int foo = int((Height * 2) / Scale.Y); return (foo >> 1) + (foo & 1); }
|
|
|
|
double GetScaledWidthDouble () { return Width / Scale.X; }
|
|
|
|
double GetScaledHeightDouble () { return Height / Scale.Y; }
|
|
|
|
double GetScaleY() const { return Scale.Y; }
|
2016-03-01 15:47:10 +00:00
|
|
|
|
2016-03-26 12:37:44 +00:00
|
|
|
int GetScaledLeftOffset () { int foo = int((LeftOffset * 2) / Scale.X); return (foo >> 1) + (foo & 1); }
|
|
|
|
int GetScaledTopOffset () { int foo = int((TopOffset * 2) / Scale.Y); return (foo >> 1) + (foo & 1); }
|
|
|
|
double GetScaledLeftOffsetDouble() { return LeftOffset / Scale.X; }
|
|
|
|
double GetScaledTopOffsetDouble() { return TopOffset / Scale.Y; }
|
2016-10-24 21:35:18 +00:00
|
|
|
virtual void ResolvePatches() {}
|
2016-03-01 15:47:10 +00:00
|
|
|
|
|
|
|
virtual void SetFrontSkyLayer();
|
|
|
|
|
2017-03-09 18:54:41 +00:00
|
|
|
void CopyToBlock (uint8_t *dest, int dwidth, int dheight, int x, int y, const uint8_t *translation=NULL)
|
2016-03-01 15:47:10 +00:00
|
|
|
{
|
|
|
|
CopyToBlock(dest, dwidth, dheight, x, y, 0, translation);
|
|
|
|
}
|
|
|
|
|
2017-03-09 18:54:41 +00:00
|
|
|
void CopyToBlock (uint8_t *dest, int dwidth, int dheight, int x, int y, int rotate, const uint8_t *translation=NULL);
|
2016-03-01 15:47:10 +00:00
|
|
|
|
|
|
|
// Returns true if the next call to GetPixels() will return an image different from the
|
|
|
|
// last call to GetPixels(). This should be considered valid only if a call to CheckModified()
|
|
|
|
// is immediately followed by a call to GetPixels().
|
|
|
|
virtual bool CheckModified ();
|
|
|
|
|
|
|
|
static void InitGrayMap();
|
|
|
|
|
|
|
|
void CopySize(FTexture *BaseTexture)
|
|
|
|
{
|
|
|
|
Width = BaseTexture->GetWidth();
|
|
|
|
Height = BaseTexture->GetHeight();
|
|
|
|
TopOffset = BaseTexture->TopOffset;
|
|
|
|
LeftOffset = BaseTexture->LeftOffset;
|
|
|
|
WidthBits = BaseTexture->WidthBits;
|
|
|
|
HeightBits = BaseTexture->HeightBits;
|
2016-03-26 12:37:44 +00:00
|
|
|
Scale = BaseTexture->Scale;
|
2016-03-01 15:47:10 +00:00
|
|
|
WidthMask = (1 << WidthBits) - 1;
|
|
|
|
}
|
|
|
|
|
|
|
|
void SetScaledSize(int fitwidth, int fitheight);
|
2016-10-20 07:08:07 +00:00
|
|
|
PalEntry GetSkyCapColor(bool bottom);
|
2016-03-01 15:47:10 +00:00
|
|
|
|
|
|
|
virtual void HackHack (int newheight); // called by FMultipatchTexture to discover corrupt patches.
|
|
|
|
|
|
|
|
protected:
|
2017-03-09 18:54:41 +00:00
|
|
|
uint16_t Width, Height, WidthMask;
|
|
|
|
static uint8_t GrayMap[256];
|
2016-03-01 15:47:10 +00:00
|
|
|
FNativeTexture *Native;
|
|
|
|
|
|
|
|
FTexture (const char *name = NULL, int lumpnum = -1);
|
|
|
|
|
2017-03-09 18:54:41 +00:00
|
|
|
Span **CreateSpans (const uint8_t *pixels) const;
|
2016-03-01 15:47:10 +00:00
|
|
|
void FreeSpans (Span **spans) const;
|
|
|
|
void CalcBitSize ();
|
|
|
|
void CopyInfo(FTexture *other)
|
|
|
|
{
|
|
|
|
CopySize(other);
|
|
|
|
bNoDecals = other->bNoDecals;
|
|
|
|
Rotations = other->Rotations;
|
2016-03-01 17:50:45 +00:00
|
|
|
gl_info = other->gl_info;
|
|
|
|
gl_info.Brightmap = NULL;
|
|
|
|
gl_info.areas = NULL;
|
2016-03-01 15:47:10 +00:00
|
|
|
}
|
|
|
|
|
2016-06-13 19:39:55 +00:00
|
|
|
std::vector<uint32_t> PixelsBgra;
|
2016-06-10 11:50:34 +00:00
|
|
|
|
2016-08-06 20:59:16 +00:00
|
|
|
void GenerateBgraFromBitmap(const FBitmap &bitmap);
|
2016-06-21 19:55:08 +00:00
|
|
|
void CreatePixelsBgraWithMipmaps();
|
|
|
|
void GenerateBgraMipmaps();
|
2016-06-25 10:14:15 +00:00
|
|
|
void GenerateBgraMipmapsFast();
|
2016-06-21 19:55:08 +00:00
|
|
|
int MipmapLevels() const;
|
|
|
|
|
2016-10-19 21:52:09 +00:00
|
|
|
private:
|
|
|
|
bool bSWSkyColorDone = false;
|
2016-10-20 07:08:07 +00:00
|
|
|
PalEntry FloorSkyColor;
|
|
|
|
PalEntry CeilingSkyColor;
|
2016-10-19 21:52:09 +00:00
|
|
|
|
2016-03-01 15:47:10 +00:00
|
|
|
public:
|
2017-03-09 18:54:41 +00:00
|
|
|
static void FlipSquareBlock (uint8_t *block, int x, int y);
|
2016-06-13 01:16:48 +00:00
|
|
|
static void FlipSquareBlockBgra (uint32_t *block, int x, int y);
|
2017-03-09 18:54:41 +00:00
|
|
|
static void FlipSquareBlockRemap (uint8_t *block, int x, int y, const uint8_t *remap);
|
|
|
|
static void FlipNonSquareBlock (uint8_t *blockto, const uint8_t *blockfrom, int x, int y, int srcpitch);
|
2016-06-13 01:16:48 +00:00
|
|
|
static void FlipNonSquareBlockBgra (uint32_t *blockto, const uint32_t *blockfrom, int x, int y, int srcpitch);
|
2017-03-09 18:54:41 +00:00
|
|
|
static void FlipNonSquareBlockRemap (uint8_t *blockto, const uint8_t *blockfrom, int x, int y, int srcpitch, const uint8_t *remap);
|
2016-03-01 15:47:10 +00:00
|
|
|
|
|
|
|
friend class D3DTex;
|
2016-10-09 10:50:57 +00:00
|
|
|
friend class OpenGLSWFrameBuffer;
|
2016-03-01 15:47:10 +00:00
|
|
|
|
2016-03-01 17:50:45 +00:00
|
|
|
public:
|
|
|
|
|
|
|
|
struct MiscGLInfo
|
|
|
|
{
|
|
|
|
FMaterial *Material[2];
|
|
|
|
FGLTexture *SystemTexture[2];
|
|
|
|
FTexture *Brightmap;
|
|
|
|
PalEntry GlowColor;
|
|
|
|
int GlowHeight;
|
|
|
|
FloatRect *areas;
|
|
|
|
int areacount;
|
|
|
|
int shaderindex;
|
|
|
|
float shaderspeed;
|
|
|
|
int mIsTransparent:2;
|
|
|
|
bool bGlowing:1; // Texture glows
|
2016-12-28 20:35:42 +00:00
|
|
|
bool bAutoGlowing : 1; // Glow info is determined from texture image.
|
2016-03-01 17:50:45 +00:00
|
|
|
bool bFullbright:1; // always draw fullbright
|
|
|
|
bool bSkybox:1; // This is a skybox
|
|
|
|
char bBrightmapChecked:1; // Set to 1 if brightmap has been checked
|
|
|
|
bool bDisableFullbright:1; // This texture will not be displayed as fullbright sprite
|
|
|
|
bool bNoFilter:1;
|
|
|
|
bool bNoCompress:1;
|
|
|
|
bool bNoExpand:1;
|
|
|
|
|
|
|
|
MiscGLInfo() throw ();
|
|
|
|
~MiscGLInfo();
|
|
|
|
};
|
|
|
|
MiscGLInfo gl_info;
|
|
|
|
|
|
|
|
void GetGlowColor(float *data);
|
|
|
|
bool isGlowing() { return gl_info.bGlowing; }
|
|
|
|
bool isFullbright() { return gl_info.bFullbright; }
|
|
|
|
void CreateDefaultBrightmap();
|
|
|
|
bool FindHoles(const unsigned char * buffer, int w, int h);
|
|
|
|
static bool SmoothEdges(unsigned char * buffer,int w, int h);
|
|
|
|
void CheckTrans(unsigned char * buffer, int size, int trans);
|
|
|
|
bool ProcessData(unsigned char * buffer, int w, int h, bool ispatch);
|
2017-03-17 22:08:22 +00:00
|
|
|
int CheckRealHeight();
|
2016-03-01 17:50:45 +00:00
|
|
|
};
|
2016-03-01 15:47:10 +00:00
|
|
|
|
2017-01-15 22:21:38 +00:00
|
|
|
class FxAddSub;
|
2016-03-01 15:47:10 +00:00
|
|
|
// Texture manager
|
|
|
|
class FTextureManager
|
|
|
|
{
|
2017-01-15 22:21:38 +00:00
|
|
|
friend class FxAddSub; // needs access to do a bounds check on the texture ID.
|
2016-03-01 15:47:10 +00:00
|
|
|
public:
|
|
|
|
FTextureManager ();
|
|
|
|
~FTextureManager ();
|
|
|
|
|
|
|
|
// Get texture without translation
|
|
|
|
FTexture *operator[] (FTextureID texnum)
|
|
|
|
{
|
|
|
|
if ((unsigned)texnum.GetIndex() >= Textures.Size()) return NULL;
|
|
|
|
return Textures[texnum.GetIndex()].Texture;
|
|
|
|
}
|
|
|
|
FTexture *operator[] (const char *texname)
|
|
|
|
{
|
|
|
|
FTextureID texnum = GetTexture (texname, FTexture::TEX_MiscPatch);
|
|
|
|
if (!texnum.Exists()) return NULL;
|
|
|
|
return Textures[texnum.GetIndex()].Texture;
|
|
|
|
}
|
|
|
|
FTexture *ByIndex(int i)
|
|
|
|
{
|
|
|
|
if (unsigned(i) >= Textures.Size()) return NULL;
|
|
|
|
return Textures[i].Texture;
|
|
|
|
}
|
|
|
|
FTexture *FindTexture(const char *texname, int usetype = FTexture::TEX_MiscPatch, BITFIELD flags = TEXMAN_TryAny);
|
|
|
|
|
|
|
|
// Get texture with translation
|
|
|
|
FTexture *operator() (FTextureID texnum, bool withpalcheck=false)
|
|
|
|
{
|
|
|
|
if ((size_t)texnum.texnum >= Textures.Size()) return NULL;
|
|
|
|
int picnum = Translation[texnum.texnum];
|
|
|
|
if (withpalcheck)
|
|
|
|
{
|
|
|
|
picnum = PalCheck(picnum).GetIndex();
|
|
|
|
}
|
|
|
|
return Textures[picnum].Texture;
|
|
|
|
}
|
|
|
|
FTexture *operator() (const char *texname)
|
|
|
|
{
|
|
|
|
FTextureID texnum = GetTexture (texname, FTexture::TEX_MiscPatch);
|
|
|
|
if (texnum.texnum == -1) return NULL;
|
|
|
|
return Textures[Translation[texnum.texnum]].Texture;
|
|
|
|
}
|
|
|
|
|
|
|
|
FTexture *ByIndexTranslated(int i)
|
|
|
|
{
|
|
|
|
if (unsigned(i) >= Textures.Size()) return NULL;
|
|
|
|
return Textures[Translation[i]].Texture;
|
|
|
|
}
|
|
|
|
|
|
|
|
FTextureID PalCheck(FTextureID tex);
|
|
|
|
|
|
|
|
enum
|
|
|
|
{
|
|
|
|
TEXMAN_TryAny = 1,
|
|
|
|
TEXMAN_Overridable = 2,
|
|
|
|
TEXMAN_ReturnFirst = 4,
|
|
|
|
TEXMAN_AllowSkins = 8,
|
|
|
|
TEXMAN_ShortNameOnly = 16,
|
|
|
|
TEXMAN_DontCreate = 32
|
|
|
|
};
|
|
|
|
|
|
|
|
enum
|
|
|
|
{
|
|
|
|
HIT_Wall = 1,
|
|
|
|
HIT_Flat = 2,
|
|
|
|
HIT_Sky = 4,
|
|
|
|
HIT_Sprite = 8,
|
|
|
|
|
|
|
|
HIT_Columnmode = HIT_Wall|HIT_Sky|HIT_Sprite
|
|
|
|
};
|
|
|
|
|
|
|
|
FTextureID CheckForTexture (const char *name, int usetype, BITFIELD flags=TEXMAN_TryAny);
|
|
|
|
FTextureID GetTexture (const char *name, int usetype, BITFIELD flags=0);
|
2016-10-26 09:56:15 +00:00
|
|
|
int ListTextures (const char *name, TArray<FTextureID> &list, bool listall = false);
|
2016-03-01 15:47:10 +00:00
|
|
|
|
|
|
|
void AddTexturesLump (const void *lumpdata, int lumpsize, int deflumpnum, int patcheslump, int firstdup=0, bool texture1=false);
|
|
|
|
void AddTexturesLumps (int lump1, int lump2, int patcheslump);
|
|
|
|
void AddGroup(int wadnum, int ns, int usetype);
|
|
|
|
void AddPatches (int lumpnum);
|
|
|
|
void AddHiresTextures (int wadnum);
|
|
|
|
void LoadTextureDefs(int wadnum, const char *lumpname);
|
|
|
|
void ParseXTexture(FScanner &sc, int usetype);
|
|
|
|
void SortTexturesByType(int start, int end);
|
|
|
|
bool AreTexturesCompatible (FTextureID picnum1, FTextureID picnum2);
|
|
|
|
|
|
|
|
FTextureID CreateTexture (int lumpnum, int usetype=FTexture::TEX_Any); // Also calls AddTexture
|
|
|
|
FTextureID AddTexture (FTexture *texture);
|
|
|
|
FTextureID GetDefaultTexture() const { return DefaultTexture; }
|
|
|
|
|
|
|
|
void LoadTextureX(int wadnum);
|
|
|
|
void AddTexturesForWad(int wadnum);
|
|
|
|
void Init();
|
|
|
|
void DeleteAll();
|
|
|
|
|
|
|
|
// Replaces one texture with another. The new texture will be assigned
|
|
|
|
// the same name, slot, and use type as the texture it is replacing.
|
|
|
|
// The old texture will no longer be managed. Set free true if you want
|
|
|
|
// the old texture to be deleted or set it false if you want it to
|
|
|
|
// be left alone in memory. You will still need to delete it at some
|
|
|
|
// point, because the texture manager no longer knows about it.
|
|
|
|
// This function can be used for such things as warping textures.
|
|
|
|
void ReplaceTexture (FTextureID picnum, FTexture *newtexture, bool free);
|
|
|
|
|
|
|
|
void UnloadAll ();
|
|
|
|
|
|
|
|
int NumTextures () const { return (int)Textures.Size(); }
|
|
|
|
|
2017-03-09 19:19:55 +00:00
|
|
|
void UpdateAnimations (uint32_t mstime);
|
2016-03-01 15:47:10 +00:00
|
|
|
int GuesstimateNumTextures ();
|
|
|
|
|
|
|
|
FSwitchDef *FindSwitch (FTextureID texture);
|
|
|
|
FDoorAnimation *FindAnimatedDoor (FTextureID picnum);
|
|
|
|
|
|
|
|
private:
|
|
|
|
|
|
|
|
// texture counting
|
|
|
|
int CountTexturesX ();
|
|
|
|
int CountLumpTextures (int lumpnum);
|
|
|
|
|
|
|
|
// Build tiles
|
|
|
|
void AddTiles (void *tiles);
|
|
|
|
int CountTiles (void *tiles);
|
|
|
|
int CountBuildTiles ();
|
|
|
|
void InitBuildTiles ();
|
|
|
|
|
|
|
|
// Animation stuff
|
|
|
|
FAnimDef *AddAnim (FAnimDef *anim);
|
|
|
|
void FixAnimations ();
|
|
|
|
void InitAnimated ();
|
|
|
|
void InitAnimDefs ();
|
2017-03-09 19:19:55 +00:00
|
|
|
FAnimDef *AddSimpleAnim (FTextureID picnum, int animcount, uint32_t speedmin, uint32_t speedrange=0);
|
2016-03-01 15:47:10 +00:00
|
|
|
FAnimDef *AddComplexAnim (FTextureID picnum, const TArray<FAnimDef::FAnimFrame> &frames);
|
|
|
|
void ParseAnim (FScanner &sc, int usetype);
|
|
|
|
FAnimDef *ParseRangeAnim (FScanner &sc, FTextureID picnum, int usetype, bool missing);
|
|
|
|
void ParsePicAnim (FScanner &sc, FTextureID picnum, int usetype, bool missing, TArray<FAnimDef::FAnimFrame> &frames);
|
|
|
|
void ParseWarp(FScanner &sc);
|
|
|
|
void ParseCameraTexture(FScanner &sc);
|
|
|
|
FTextureID ParseFramenum (FScanner &sc, FTextureID basepicnum, int usetype, bool allowMissing);
|
2017-03-09 19:19:55 +00:00
|
|
|
void ParseTime (FScanner &sc, uint32_t &min, uint32_t &max);
|
2016-03-01 15:47:10 +00:00
|
|
|
FTexture *Texture(FTextureID id) { return Textures[id.GetIndex()].Texture; }
|
|
|
|
void SetTranslation (FTextureID fromtexnum, FTextureID totexnum);
|
|
|
|
void ParseAnimatedDoor(FScanner &sc);
|
|
|
|
|
|
|
|
void InitPalettedVersions();
|
|
|
|
|
|
|
|
// Switches
|
|
|
|
|
|
|
|
void InitSwitchList ();
|
|
|
|
void ProcessSwitchDef (FScanner &sc);
|
|
|
|
FSwitchDef *ParseSwitchDef (FScanner &sc, bool ignoreBad);
|
|
|
|
void AddSwitchPair (FSwitchDef *def1, FSwitchDef *def2);
|
|
|
|
|
|
|
|
struct TextureHash
|
|
|
|
{
|
|
|
|
FTexture *Texture;
|
|
|
|
int HashNext;
|
|
|
|
};
|
|
|
|
enum { HASH_END = -1, HASH_SIZE = 1027 };
|
|
|
|
TArray<TextureHash> Textures;
|
|
|
|
TArray<int> Translation;
|
|
|
|
int HashFirst[HASH_SIZE];
|
|
|
|
FTextureID DefaultTexture;
|
|
|
|
TArray<int> FirstTextureForFile;
|
|
|
|
TMap<int,int> PalettedVersions; // maps from normal -> paletted version
|
|
|
|
|
|
|
|
TArray<FAnimDef *> mAnimations;
|
|
|
|
TArray<FSwitchDef *> mSwitchDefs;
|
|
|
|
TArray<FDoorAnimation> mAnimatedDoors;
|
2017-03-09 18:54:41 +00:00
|
|
|
TArray<uint8_t *> BuildTileFiles;
|
2016-04-28 13:59:37 +00:00
|
|
|
public:
|
|
|
|
short sintable[2048]; // for texture warping
|
|
|
|
enum
|
|
|
|
{
|
|
|
|
SINMASK = 2047
|
|
|
|
};
|
2016-03-01 15:47:10 +00:00
|
|
|
};
|
|
|
|
|
|
|
|
// A texture that doesn't really exist
|
|
|
|
class FDummyTexture : public FTexture
|
|
|
|
{
|
|
|
|
public:
|
|
|
|
FDummyTexture ();
|
2017-03-09 18:54:41 +00:00
|
|
|
const uint8_t *GetColumn (unsigned int column, const Span **spans_out);
|
|
|
|
const uint8_t *GetPixels ();
|
2016-03-01 15:47:10 +00:00
|
|
|
void SetSize (int width, int height);
|
|
|
|
};
|
|
|
|
|
|
|
|
// A texture that returns a wiggly version of another texture.
|
|
|
|
class FWarpTexture : public FTexture
|
|
|
|
{
|
|
|
|
public:
|
2016-04-30 10:36:55 +00:00
|
|
|
FWarpTexture (FTexture *source, int warptype);
|
2016-03-01 15:47:10 +00:00
|
|
|
~FWarpTexture ();
|
|
|
|
|
|
|
|
virtual int CopyTrueColorPixels(FBitmap *bmp, int x, int y, int rotate=0, FCopyInfo *inf = NULL);
|
2017-03-09 18:54:41 +00:00
|
|
|
const uint8_t *GetColumn (unsigned int column, const Span **spans_out);
|
|
|
|
const uint8_t *GetPixels ();
|
2016-06-17 08:47:30 +00:00
|
|
|
const uint32_t *GetPixelsBgra() override;
|
2016-03-01 15:47:10 +00:00
|
|
|
void Unload ();
|
|
|
|
bool CheckModified ();
|
|
|
|
|
|
|
|
float GetSpeed() const { return Speed; }
|
|
|
|
int GetSourceLump() { return SourcePic->GetSourceLump(); }
|
|
|
|
void SetSpeed(float fac) { Speed = fac; }
|
|
|
|
FTexture *GetRedirect(bool wantwarped);
|
|
|
|
|
2017-03-09 19:19:55 +00:00
|
|
|
uint32_t GenTime;
|
2017-03-13 17:02:44 +00:00
|
|
|
uint32_t GenTimeBgra;
|
2016-04-28 17:04:01 +00:00
|
|
|
float Speed;
|
|
|
|
int WidthOffsetMultiplier, HeightOffsetMultiplier; // [mxd]
|
2016-03-01 15:47:10 +00:00
|
|
|
protected:
|
|
|
|
FTexture *SourcePic;
|
2017-03-09 18:54:41 +00:00
|
|
|
uint8_t *Pixels;
|
2016-03-01 15:47:10 +00:00
|
|
|
Span **Spans;
|
|
|
|
|
2017-03-09 19:19:55 +00:00
|
|
|
virtual void MakeTexture (uint32_t time);
|
2016-03-01 15:47:10 +00:00
|
|
|
int NextPo2 (int v); // [mxd]
|
|
|
|
void SetupMultipliers (int width, int height); // [mxd]
|
|
|
|
};
|
|
|
|
|
|
|
|
// A texture that can be drawn to.
|
|
|
|
class DSimpleCanvas;
|
|
|
|
class AActor;
|
|
|
|
|
|
|
|
class FCanvasTexture : public FTexture
|
|
|
|
{
|
|
|
|
public:
|
|
|
|
FCanvasTexture (const char *name, int width, int height);
|
|
|
|
~FCanvasTexture ();
|
|
|
|
|
2017-03-09 18:54:41 +00:00
|
|
|
const uint8_t *GetColumn (unsigned int column, const Span **spans_out);
|
|
|
|
const uint8_t *GetPixels ();
|
2016-06-13 01:16:48 +00:00
|
|
|
const uint32_t *GetPixelsBgra() override;
|
2016-03-01 15:47:10 +00:00
|
|
|
void Unload ();
|
|
|
|
bool CheckModified ();
|
|
|
|
void NeedUpdate() { bNeedsUpdate=true; }
|
|
|
|
void SetUpdated() { bNeedsUpdate = false; bDidUpdate = true; bFirstUpdate = false; }
|
|
|
|
DSimpleCanvas *GetCanvas() { return Canvas; }
|
2016-06-13 01:16:48 +00:00
|
|
|
DSimpleCanvas *GetCanvasBgra() { return CanvasBgra; }
|
2016-06-25 08:33:35 +00:00
|
|
|
bool Mipmapped() override { return false; }
|
2016-03-01 15:47:10 +00:00
|
|
|
void MakeTexture ();
|
2016-06-13 01:16:48 +00:00
|
|
|
void MakeTextureBgra ();
|
2016-03-01 15:47:10 +00:00
|
|
|
|
|
|
|
protected:
|
|
|
|
|
2016-06-13 01:16:48 +00:00
|
|
|
DSimpleCanvas *Canvas = nullptr;
|
|
|
|
DSimpleCanvas *CanvasBgra = nullptr;
|
2017-03-09 18:54:41 +00:00
|
|
|
uint8_t *Pixels = nullptr;
|
2016-06-13 01:16:48 +00:00
|
|
|
uint32_t *PixelsBgra = nullptr;
|
2016-03-01 15:47:10 +00:00
|
|
|
Span DummySpans[2];
|
2016-06-13 01:16:48 +00:00
|
|
|
bool bNeedsUpdate = true;
|
|
|
|
bool bDidUpdate = false;
|
|
|
|
bool bPixelsAllocated = false;
|
|
|
|
bool bPixelsAllocatedBgra = false;
|
2016-03-01 15:47:10 +00:00
|
|
|
public:
|
|
|
|
bool bFirstUpdate;
|
|
|
|
|
|
|
|
|
|
|
|
friend struct FCanvasTextureInfo;
|
|
|
|
};
|
|
|
|
|
|
|
|
extern FTextureManager TexMan;
|
|
|
|
|
|
|
|
#endif
|
|
|
|
|
|
|
|
|