summaryrefslogtreecommitdiff
path: root/src/engine/texture.h
diff options
context:
space:
mode:
authorxolatile2025-08-06 22:54:55 +0200
committerxolatile2025-08-06 22:54:55 +0200
commit0a1172b75f571685c264a8b9d8ee224bbf11381f (patch)
treed041fdc68a60f0ebb48a3852bbcce6d9432f83d5 /src/engine/texture.h
parentaffde05dc07a94643f1fd2751b2b441f57f73d7d (diff)
downloadxolatile-badassbug-0a1172b75f571685c264a8b9d8ee224bbf11381f.tar.xz
xolatile-badassbug-0a1172b75f571685c264a8b9d8ee224bbf11381f.tar.zst
Please do not hate me, it makes sense...
Diffstat (limited to 'src/engine/texture.h')
-rw-r--r--src/engine/texture.h294
1 files changed, 77 insertions, 217 deletions
diff --git a/src/engine/texture.h b/src/engine/texture.h
index 3679931..ef5a57b 100644
--- a/src/engine/texture.h
+++ b/src/engine/texture.h
@@ -1,43 +1,31 @@
-struct GlobalShaderParamState
-{
+struct GlobalShaderParamState {
const char *name;
- union
- {
+ union {
float fval[32];
int ival[32];
uint uval[32];
uchar buf[32*sizeof(float)];
};
int version;
-
static int nextversion;
-
void resetversions();
-
- void changed()
- {
+ void changed() {
if(++nextversion < 0) resetversions();
version = nextversion;
}
};
-struct ShaderParamBinding
-{
+struct ShaderParamBinding {
int loc, size;
GLenum format;
};
-struct GlobalShaderParamUse : ShaderParamBinding
-{
-
+struct GlobalShaderParamUse : ShaderParamBinding {
GlobalShaderParamState *param;
int version;
-
- void flush()
- {
+ void flush() {
if(version == param->version) return;
- switch(format)
- {
+ switch(format) {
case GL_BOOL:
case GL_FLOAT: glUniform1fv_(loc, size, param->fval); break;
case GL_BOOL_VEC2:
@@ -58,25 +46,20 @@ struct GlobalShaderParamUse : ShaderParamBinding
}
};
-struct LocalShaderParamState : ShaderParamBinding
-{
+struct LocalShaderParamState : ShaderParamBinding {
const char *name;
};
-struct SlotShaderParam
-{
+struct SlotShaderParam {
const char *name;
int loc;
float val[4];
};
-struct SlotShaderParamState : LocalShaderParamState
-{
+struct SlotShaderParamState : LocalShaderParamState {
float val[4];
-
SlotShaderParamState() {}
- SlotShaderParamState(const SlotShaderParam &p)
- {
+ SlotShaderParamState(const SlotShaderParam &p) {
name = p.name;
loc = -1;
size = 1;
@@ -85,12 +68,10 @@ struct SlotShaderParamState : LocalShaderParamState
}
};
-enum
-{
+enum {
SHADER_DEFAULT = 0,
SHADER_NORMALSLMS = 1<<0,
SHADER_OPTION = 1<<3,
-
SHADER_INVALID = 1<<8,
SHADER_DEFERRED = 1<<9
};
@@ -103,25 +84,21 @@ extern int shaderdetail;
struct Slot;
struct VSlot;
-struct UniformLoc
-{
+struct UniformLoc {
const char *name, *blockname;
int loc, version, binding, stride, offset, size;
void *data;
UniformLoc(const char *name = NULL, const char *blockname = NULL, int binding = -1, int stride = -1) : name(name), blockname(blockname), loc(-1), version(-1), binding(binding), stride(stride), offset(-1), size(-1), data(NULL) {}
};
-struct AttribLoc
-{
+struct AttribLoc {
const char *name;
int loc;
AttribLoc(const char *name = NULL, int loc = -1) : name(name), loc(loc) {}
};
-struct Shader
-{
+struct Shader {
static Shader *lastshader;
-
char *name, *vsstr, *psstr, *defer;
int type;
GLuint program, vsobj, psobj;
@@ -137,161 +114,115 @@ struct Shader
vector<UniformLoc> uniformlocs;
vector<AttribLoc> attriblocs;
const void *owner;
-
- Shader() : name(NULL), vsstr(NULL), psstr(NULL), defer(NULL), type(SHADER_DEFAULT), program(0), vsobj(0), psobj(0), detailshader(NULL), variantshader(NULL), altshader(NULL), variantrows(NULL), standard(false), forced(false), used(false), reusevs(NULL), reuseps(NULL), owner(NULL)
- {
+ Shader() : name(NULL), vsstr(NULL), psstr(NULL), defer(NULL), type(SHADER_DEFAULT), program(0), vsobj(0), psobj(0), detailshader(NULL), variantshader(NULL), altshader(NULL), variantrows(NULL), standard(false), forced(false), used(false), reusevs(NULL), reuseps(NULL), owner(NULL) {
loopi(MAXSHADERDETAIL) fastshader[i] = this;
}
-
- ~Shader()
- {
+ ~Shader() {
DELETEA(name);
DELETEA(vsstr);
DELETEA(psstr);
DELETEA(defer);
DELETEA(variantrows);
}
-
void fixdetailshader(bool force = true, bool recurse = true);
void allocparams(Slot *slot = NULL);
void setslotparams(Slot &slot);
void setslotparams(Slot &slot, VSlot &vslot);
void bindprograms();
-
- void flushparams(Slot *slot = NULL)
- {
+ void flushparams(Slot *slot = NULL) {
if(!used) { allocparams(slot); used = true; }
loopv(globalparams) globalparams[i].flush();
}
-
void force();
-
bool invalid() const { return (type&SHADER_INVALID)!=0; }
bool deferred() const { return (type&SHADER_DEFERRED)!=0; }
bool loaded() const { return detailshader!=NULL; }
-
static bool isnull(const Shader *s);
-
bool isnull() const { return isnull(this); }
-
- int numvariants(int row) const
- {
+ int numvariants(int row) const {
if(row < 0 || row >= MAXVARIANTROWS || !variantrows) return 0;
return variantrows[row+1] - variantrows[row];
}
-
- Shader *getvariant(int col, int row) const
- {
+ Shader *getvariant(int col, int row) const {
if(row < 0 || row >= MAXVARIANTROWS || col < 0 || !variantrows) return NULL;
int start = variantrows[row], end = variantrows[row+1];
return col < end - start ? variants[start + col] : NULL;
}
-
- bool hasoption(int row)
- {
- if(detailshader)
- {
+ bool hasoption(int row) {
+ if(detailshader) {
Shader *s = getvariant(0, row);
if(s) return (s->type&SHADER_OPTION)!=0;
}
return false;
}
-
- void addvariant(int row, Shader *s)
- {
+ void addvariant(int row, Shader *s) {
if(row < 0 || row >= MAXVARIANTROWS || variants.length() >= USHRT_MAX) return;
if(!variantrows) { variantrows = new ushort[MAXVARIANTROWS+1]; memset(variantrows, 0, (MAXVARIANTROWS+1)*sizeof(ushort)); }
variants.insert(variantrows[row+1], s);
for(int i = row+1; i <= MAXVARIANTROWS; ++i) ++variantrows[i];
}
-
- void setvariant_(int col, int row, Shader *fallbackshader)
- {
+ void setvariant_(int col, int row, Shader *fallbackshader) {
Shader *s = fallbackshader;
- if(detailshader->variantrows)
- {
+ if(detailshader->variantrows) {
int start = detailshader->variantrows[row], end = detailshader->variantrows[row+1];
- for(col = min(start + col, end-1); col >= start; --col)
- {
+ for(col = min(start + col, end-1); col >= start; --col) {
if(!detailshader->variants[col]->invalid()) { s = detailshader->variants[col]; break; }
}
}
if(lastshader!=s) s->bindprograms();
}
-
- void setvariant(int col, int row, Shader *fallbackshader)
- {
+ void setvariant(int col, int row, Shader *fallbackshader) {
if(isnull() || !loaded()) return;
setvariant_(col, row, fallbackshader);
lastshader->flushparams();
}
-
- void setvariant(int col, int row)
- {
+ void setvariant(int col, int row) {
if(isnull() || !loaded()) return;
setvariant_(col, row, detailshader);
lastshader->flushparams();
}
-
- void setvariant(int col, int row, Slot &slot, VSlot &vslot, Shader *fallbackshader)
- {
+ void setvariant(int col, int row, Slot &slot, VSlot &vslot, Shader *fallbackshader) {
if(isnull() || !loaded()) return;
setvariant_(col, row, fallbackshader);
lastshader->flushparams(&slot);
lastshader->setslotparams(slot, vslot);
}
-
- void setvariant(int col, int row, Slot &slot, VSlot &vslot)
- {
+ void setvariant(int col, int row, Slot &slot, VSlot &vslot) {
if(isnull() || !loaded()) return;
setvariant_(col, row, detailshader);
lastshader->flushparams(&slot);
lastshader->setslotparams(slot, vslot);
}
-
- void set_()
- {
+ void set_() {
if(lastshader!=detailshader) detailshader->bindprograms();
}
-
- void set()
- {
+ void set() {
if(isnull() || !loaded()) return;
set_();
lastshader->flushparams();
}
-
- void set(Slot &slot, VSlot &vslot)
- {
+ void set(Slot &slot, VSlot &vslot) {
if(isnull() || !loaded()) return;
set_();
lastshader->flushparams(&slot);
lastshader->setslotparams(slot, vslot);
}
-
bool compile();
void cleanup(bool invalid = false);
-
static int uniformlocversion();
};
-struct GlobalShaderParam
-{
+struct GlobalShaderParam {
const char *name;
GlobalShaderParamState *param;
-
GlobalShaderParam(const char *name) : name(name), param(NULL) {}
-
- GlobalShaderParamState *resolve()
- {
+ GlobalShaderParamState *resolve() {
extern GlobalShaderParamState *getglobalparam(const char *name);
if(!param) param = getglobalparam(name);
param->changed();
return param;
}
-
- void setf(float x = 0, float y = 0, float z = 0, float w = 0)
- {
+ void setf(float x = 0, float y = 0, float z = 0, float w = 0) {
GlobalShaderParamState *g = resolve();
g->fval[0] = x;
g->fval[1] = y;
@@ -305,12 +236,9 @@ struct GlobalShaderParam
void set(const matrix2 &m) { memcpy(resolve()->fval, m.a.v, sizeof(m)); }
void set(const matrix3 &m) { memcpy(resolve()->fval, m.a.v, sizeof(m)); }
void set(const matrix4 &m) { memcpy(resolve()->fval, m.a.v, sizeof(m)); }
-
template<class T>
void setv(const T *v, int n = 1) { memcpy(resolve()->buf, v, n*sizeof(T)); }
-
- void seti(int x = 0, int y = 0, int z = 0, int w = 0)
- {
+ void seti(int x = 0, int y = 0, int z = 0, int w = 0) {
GlobalShaderParamState *g = resolve();
g->ival[0] = x;
g->ival[1] = y;
@@ -320,33 +248,25 @@ struct GlobalShaderParam
void set(const ivec &v, int w = 0) { seti(v.x, v.y, v.z, w); }
void set(const ivec2 &v, int z = 0, int w = 0) { seti(v.x, v.y, z, w); }
void set(const ivec4 &v) { seti(v.x, v.y, v.z, v.w); }
-
- void setu(uint x = 0, uint y = 0, uint z = 0, uint w = 0)
- {
+ void setu(uint x = 0, uint y = 0, uint z = 0, uint w = 0) {
GlobalShaderParamState *g = resolve();
g->uval[0] = x;
g->uval[1] = y;
g->uval[2] = z;
g->uval[3] = w;
}
-
template<class T>
T *reserve(int n = 1) { return (T *)resolve()->buf; }
};
-struct LocalShaderParam
-{
+struct LocalShaderParam {
const char *name;
int loc;
-
LocalShaderParam(const char *name) : name(name), loc(-1) {}
-
- LocalShaderParamState *resolve()
- {
+ LocalShaderParamState *resolve() {
Shader *s = Shader::lastshader;
if(!s) return NULL;
- if(!s->localparamremap.inrange(loc))
- {
+ if(!s->localparamremap.inrange(loc)) {
extern int getlocalparam(const char *name);
if(loc == -1) loc = getlocalparam(name);
if(!s->localparamremap.inrange(loc)) return NULL;
@@ -354,12 +274,9 @@ struct LocalShaderParam
uchar remap = s->localparamremap[loc];
return s->localparams.inrange(remap) ? &s->localparams[remap] : NULL;
}
-
- void setf(float x = 0, float y = 0, float z = 0, float w = 0)
- {
+ void setf(float x = 0, float y = 0, float z = 0, float w = 0) {
ShaderParamBinding *b = resolve();
- if(b) switch(b->format)
- {
+ if(b) switch(b->format) {
case GL_BOOL:
case GL_FLOAT: glUniform1f_(b->loc, x); break;
case GL_BOOL_VEC2:
@@ -389,13 +306,10 @@ struct LocalShaderParam
void set(const matrix2 &m) { setv(&m); }
void set(const matrix3 &m) { setv(&m); }
void set(const matrix4 &m) { setv(&m); }
-
template<class T>
- void sett(T x, T y, T z, T w)
- {
+ void sett(T x, T y, T z, T w) {
ShaderParamBinding *b = resolve();
- if(b) switch(b->format)
- {
+ if(b) switch(b->format) {
case GL_FLOAT: glUniform1f_(b->loc, x); break;
case GL_FLOAT_VEC2: glUniform2f_(b->loc, x, y); break;
case GL_FLOAT_VEC3: glUniform3f_(b->loc, x, y, z); break;
@@ -442,35 +356,26 @@ struct LocalShaderParam
name##shader->setvariant(__VA_ARGS__); \
} while(0)
-struct ImageData
-{
+struct ImageData {
int w, h, bpp, levels, align, pitch;
GLenum compressed;
uchar *data;
void *owner;
void (*freefunc)(void *);
-
ImageData()
- : data(NULL), owner(NULL), freefunc(NULL)
- {}
-
+ : data(NULL), owner(NULL), freefunc(NULL) {
+ }
- ImageData(int nw, int nh, int nbpp, int nlevels = 1, int nalign = 0, GLenum ncompressed = GL_FALSE)
- {
+ ImageData(int nw, int nh, int nbpp, int nlevels = 1, int nalign = 0, GLenum ncompressed = GL_FALSE) {
setdata(NULL, nw, nh, nbpp, nlevels, nalign, ncompressed);
}
-
ImageData(int nw, int nh, int nbpp, uchar *data)
- : owner(NULL), freefunc(NULL)
- {
+ : owner(NULL), freefunc(NULL) {
setdata(data, nw, nh, nbpp);
}
-
ImageData(SDL_Surface *s) { wrap(s); }
~ImageData() { cleanup(); }
-
- void setdata(uchar *ndata, int nw, int nh, int nbpp, int nlevels = 1, int nalign = 0, GLenum ncompressed = GL_FALSE)
- {
+ void setdata(uchar *ndata, int nw, int nh, int nbpp, int nlevels = 1, int nalign = 0, GLenum ncompressed = GL_FALSE) {
w = nw;
h = nh;
bpp = nbpp;
@@ -481,16 +386,12 @@ struct ImageData
data = ndata ? ndata : new uchar[calcsize()];
if(!ndata) { owner = this; freefunc = NULL; }
}
-
int calclevelsize(int level) const { return ((max(w>>level, 1)+align-1)/align)*((max(h>>level, 1)+align-1)/align)*bpp; }
-
- int calcsize() const
- {
+ int calcsize() const {
if(!align) return w*h*bpp;
int lw = w, lh = h,
size = 0;
- loopi(levels)
- {
+ loopi(levels) {
if(lw<=0) lw = 1;
if(lh<=0) lh = 1;
size += ((lw+align-1)/align)*((lh+align-1)/align)*bpp;
@@ -500,31 +401,23 @@ struct ImageData
}
return size;
}
-
- void disown()
- {
+ void disown() {
data = NULL;
owner = NULL;
freefunc = NULL;
}
-
- void cleanup()
- {
+ void cleanup() {
if(owner==this) delete[] data;
else if(freefunc) (*freefunc)(owner);
disown();
}
-
- void replace(ImageData &d)
- {
+ void replace(ImageData &d) {
cleanup();
*this = d;
if(owner == &d) owner = this;
d.disown();
}
-
- void wrap(SDL_Surface *s)
- {
+ void wrap(SDL_Surface *s) {
setdata((uchar *)s->pixels, s->w, s->h, s->format->BytesPerPixel);
pitch = s->pitch;
owner = s;
@@ -536,14 +429,11 @@ struct ImageData
// each texture slot can have multiple texture frames, of which currently only the first is used
// additional frames can be used for various shaders
-struct Texture
-{
- enum
- {
+struct Texture {
+ enum {
IMAGE = 0,
CUBEMAP = 1,
TYPE = 0xFF,
-
STUB = 1<<8,
TRANSIENT = 1<<9,
COMPRESSED = 1<<10,
@@ -551,18 +441,15 @@ struct Texture
MIRROR = 1<<12,
FLAGS = 0xFF00
};
-
char *name;
int type, w, h, xs, ys, bpp, clamp;
bool mipmap, canreduce;
GLuint id;
uchar *alphamask;
-
Texture() : alphamask(NULL) {}
};
-enum
-{
+enum {
TEX_DIFFUSE = 0,
TEX_UNKNOWN,
TEX_DECAL,
@@ -572,8 +459,7 @@ enum
TEX_ALPHA
};
-enum
-{
+enum {
VSLOT_SHPARAM = 0,
VSLOT_SCALE,
VSLOT_ROTATION,
@@ -585,8 +471,7 @@ enum
VSLOT_NUM
};
-struct VSlot
-{
+struct VSlot {
Slot *slot;
VSlot *next;
int index, changed;
@@ -599,17 +484,12 @@ struct VSlot
int layer;
float alphafront, alphaback;
vec colorscale;
-
- VSlot(Slot *slot = NULL, int index = -1) : slot(slot), next(NULL), index(index), changed(0)
- {
+ VSlot(Slot *slot = NULL, int index = -1) : slot(slot), next(NULL), index(index), changed(0) {
reset();
if(slot) addvariant(slot);
}
-
void addvariant(Slot *slot);
-
- void reset()
- {
+ void reset() {
params.shrink(0);
linked = false;
scale = 1;
@@ -621,23 +501,18 @@ struct VSlot
alphaback = 0;
colorscale = vec(1, 1, 1);
}
-
- void cleanup()
- {
+ void cleanup() {
linked = false;
}
};
-struct Slot
-{
- struct Tex
- {
+struct Slot {
+ struct Tex {
int type;
Texture *t;
string name;
int combined;
};
-
int index;
vector<Tex> sts;
Shader *shader;
@@ -650,11 +525,8 @@ struct Slot
int layermaskmode;
float layermaskscale;
ImageData *layermask;
-
Slot(int index = -1) : index(index), variants(NULL), layermaskname(NULL), layermask(NULL) { reset(); }
-
- void reset()
- {
+ void reset() {
sts.shrink(0);
shader = NULL;
params.shrink(0);
@@ -666,13 +538,10 @@ struct Slot
layermaskscale = 1;
if(layermask) DELETEP(layermask);
}
-
- void cleanup()
- {
+ void cleanup() {
loaded = false;
thumbnail = NULL;
- loopv(sts)
- {
+ loopv(sts) {
Tex &t = sts[i];
t.t = NULL;
t.combined = -1;
@@ -680,41 +549,32 @@ struct Slot
}
};
-inline void VSlot::addvariant(Slot *slot)
-{
+inline void VSlot::addvariant(Slot *slot) {
if(!slot->variants) slot->variants = this;
- else
- {
+ else {
VSlot *prev = slot->variants;
while(prev->next) prev = prev->next;
prev->next = this;
}
}
-struct MSlot : Slot, VSlot
-{
+struct MSlot : Slot, VSlot {
MSlot() : VSlot(this) {}
-
- void reset()
- {
+ void reset() {
Slot::reset();
VSlot::reset();
}
-
- void cleanup()
- {
+ void cleanup() {
Slot::cleanup();
VSlot::cleanup();
}
};
-struct texrotation
-{
+struct texrotation {
bool flipx, flipy, swapxy;
};
-struct cubemapside
-{
+struct cubemapside {
GLenum target;
const char *name;
bool flipx, flipy, swapxy;