mirror of
https://github.com/nzp-team/fteqw.git
synced 2024-11-22 20:11:44 +00:00
fix player skins to be reliable.
git-svn-id: https://svn.code.sf.net/p/fteqw/code/trunk@4760 fc73d0e0-1445-4013-8a0c-d673dee63da5
This commit is contained in:
parent
9881bc3dd7
commit
a3d7f5aa40
3 changed files with 205 additions and 208 deletions
|
@ -21,17 +21,25 @@ Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
|
||||||
|
|
||||||
#include "particles.h"
|
#include "particles.h"
|
||||||
|
|
||||||
|
enum
|
||||||
|
{
|
||||||
|
SKIN_NOTLOADED, //not trying to load it. shouldn't really happen, but can.
|
||||||
|
SKIN_LOADING, //still loading. just do something else for now...
|
||||||
|
SKIN_LOADED,
|
||||||
|
SKIN_FAILED
|
||||||
|
};
|
||||||
typedef struct qwskin_s
|
typedef struct qwskin_s
|
||||||
{
|
{
|
||||||
char name[64];
|
char name[64];
|
||||||
|
int loadstate; // the name isn't a valid skin
|
||||||
|
|
||||||
|
//qw skin info
|
||||||
int width;
|
int width;
|
||||||
int height;
|
int height;
|
||||||
|
void *skindata;
|
||||||
|
|
||||||
//for hardware 32bit texture overrides
|
//for hardware 32bit texture overrides
|
||||||
texnums_t textures;
|
texnums_t textures;
|
||||||
|
|
||||||
qbyte failedload; // the name isn't a valid skin
|
|
||||||
void *skindata;
|
|
||||||
} qwskin_t;
|
} qwskin_t;
|
||||||
|
|
||||||
// player_state_t is the information needed by a player entity
|
// player_state_t is the information needed by a player entity
|
||||||
|
@ -170,6 +178,7 @@ typedef struct player_info_s
|
||||||
|
|
||||||
int spectator;
|
int spectator;
|
||||||
qwskin_t *qwskin;
|
qwskin_t *qwskin;
|
||||||
|
qwskin_t *lastskin; //last-known-good skin
|
||||||
skinid_t skinid;
|
skinid_t skinid;
|
||||||
|
|
||||||
struct model_s *model;
|
struct model_s *model;
|
||||||
|
|
|
@ -114,7 +114,6 @@ qwskin_t *Skin_Lookup (char *fullname)
|
||||||
qwskin_t *skin;
|
qwskin_t *skin;
|
||||||
char cleanname[sizeof(skin->name)];
|
char cleanname[sizeof(skin->name)];
|
||||||
COM_StripExtension (fullname, cleanname, sizeof(cleanname));
|
COM_StripExtension (fullname, cleanname, sizeof(cleanname));
|
||||||
|
|
||||||
for (i=0 ; i<numskins ; i++)
|
for (i=0 ; i<numskins ; i++)
|
||||||
{
|
{
|
||||||
if (!strcmp (cleanname, skins[i].name))
|
if (!strcmp (cleanname, skins[i].name))
|
||||||
|
@ -154,31 +153,21 @@ void Skin_Find (player_info_t *sc)
|
||||||
int i;
|
int i;
|
||||||
char name[128], *s;
|
char name[128], *s;
|
||||||
|
|
||||||
if (allskins[0])
|
|
||||||
s = allskins;
|
|
||||||
else
|
|
||||||
s = Info_ValueForKey (sc->userinfo, "skin");
|
|
||||||
|
|
||||||
sc->model = NULL;
|
sc->model = NULL;
|
||||||
sc->skinid = 0;
|
sc->skinid = 0;
|
||||||
sc->qwskin = NULL;
|
sc->qwskin = NULL;
|
||||||
|
|
||||||
if (!*s)
|
s = Skin_FindName(sc);
|
||||||
s = baseskin.string;
|
|
||||||
if (!*s)
|
if (!*s)
|
||||||
return;
|
return;
|
||||||
// s = "default";
|
|
||||||
|
|
||||||
s = Skin_FindName(sc);
|
|
||||||
COM_StripExtension (s, name, sizeof(name));
|
COM_StripExtension (s, name, sizeof(name));
|
||||||
|
|
||||||
|
|
||||||
for (i=0 ; i<numskins ; i++)
|
for (i=0 ; i<numskins ; i++)
|
||||||
{
|
{
|
||||||
if (!strcmp (name, skins[i].name))
|
if (!strcmp (name, skins[i].name))
|
||||||
{
|
{
|
||||||
sc->qwskin = &skins[i];
|
sc->qwskin = &skins[i];
|
||||||
Skin_Cache8 (sc->qwskin);
|
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -197,6 +186,162 @@ void Skin_Find (player_info_t *sc)
|
||||||
Q_strncpyz(skin->name, name, sizeof(skin->name));
|
Q_strncpyz(skin->name, name, sizeof(skin->name));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void Skin_WorkerDone(void *skinptr, void *skindata, size_t width, size_t height)
|
||||||
|
{
|
||||||
|
qwskin_t *skin = skinptr;
|
||||||
|
skin->width = width;
|
||||||
|
skin->height = height;
|
||||||
|
skin->skindata = skindata;
|
||||||
|
if (skindata)
|
||||||
|
skin->loadstate = SKIN_LOADED;
|
||||||
|
else
|
||||||
|
skin->loadstate = SKIN_FAILED;
|
||||||
|
}
|
||||||
|
void Skin_WorkerLoad(void *skinptr, void *data, size_t a, size_t b)
|
||||||
|
{
|
||||||
|
qwskin_t *skin = skinptr;
|
||||||
|
char name[MAX_QPATH];
|
||||||
|
qbyte *raw;
|
||||||
|
qbyte *out, *pix;
|
||||||
|
pcx_t *pcx;
|
||||||
|
int x, y, srcw, srch;
|
||||||
|
int dataByte;
|
||||||
|
int runLength;
|
||||||
|
int fbremap[256];
|
||||||
|
size_t pcxsize;
|
||||||
|
|
||||||
|
Q_snprintfz (name, sizeof(name), "skins/%s.pcx", skin->name);
|
||||||
|
raw = COM_LoadTempFile (name, &pcxsize);
|
||||||
|
if (!raw)
|
||||||
|
{
|
||||||
|
//use 24bit skins even if gl_load24bit is failed
|
||||||
|
if (strcmp(skin->name, baseskin.string))
|
||||||
|
{
|
||||||
|
//if its not already the base skin, try the base (and warn if anything not base couldn't load).
|
||||||
|
Con_Printf ("Couldn't load skin %s\n", name);
|
||||||
|
Q_snprintfz (name, sizeof(name), "skins/%s.pcx", baseskin.string);
|
||||||
|
raw = COM_LoadTempFile (name, &pcxsize);
|
||||||
|
}
|
||||||
|
if (!raw)
|
||||||
|
{
|
||||||
|
Skin_WorkerDone(skin, NULL, 0, 0);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
//
|
||||||
|
// parse the PCX file
|
||||||
|
//
|
||||||
|
pcx = (pcx_t *)raw;
|
||||||
|
raw = (qbyte *)(pcx+1);
|
||||||
|
|
||||||
|
//check format (sizes are checked later)
|
||||||
|
if (pcx->manufacturer != 0x0a
|
||||||
|
|| pcx->version != 5
|
||||||
|
|| pcx->encoding != 1
|
||||||
|
|| pcx->bits_per_pixel != 8)
|
||||||
|
{
|
||||||
|
Con_Printf ("Bad skin %s (unsupported format)\n", name);
|
||||||
|
Skin_WorkerDone(skin, NULL, 0, 0);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
pcx->xmax = (unsigned short)LittleShort(pcx->xmax);
|
||||||
|
pcx->ymax = (unsigned short)LittleShort(pcx->ymax);
|
||||||
|
pcx->xmin = (unsigned short)LittleShort(pcx->xmin);
|
||||||
|
pcx->ymin = (unsigned short)LittleShort(pcx->ymin);
|
||||||
|
|
||||||
|
srcw = pcx->xmax-pcx->xmin+1;
|
||||||
|
srch = pcx->ymax-pcx->ymin+1;
|
||||||
|
|
||||||
|
if (srcw < 1 || srch < 1 || srcw > 320 || srch > 200)
|
||||||
|
{
|
||||||
|
Con_Printf ("Bad skin %s (unsupported size)\n", name);
|
||||||
|
Skin_WorkerDone(skin, NULL, 0, 0);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
skin->width = srcw;
|
||||||
|
skin->height = srch;
|
||||||
|
|
||||||
|
out = BZ_Malloc(skin->width*skin->height);
|
||||||
|
if (!out)
|
||||||
|
Sys_Error ("Skin_Cache: couldn't allocate");
|
||||||
|
|
||||||
|
// TODO: we build a fullbright remap.. can we get rid of this?
|
||||||
|
for (x = 0; x < vid.fullbright; x++)
|
||||||
|
fbremap[x] = x + (256-vid.fullbright); //fullbrights don't exist, so don't loose palette info.
|
||||||
|
|
||||||
|
|
||||||
|
pix = out;
|
||||||
|
// memset (out, 0, skin->width*skin->height);
|
||||||
|
|
||||||
|
dataByte = 0; //typically black (this is in case a 0*0 file is loaded... which won't happen anyway)
|
||||||
|
for (y=0 ; y < srch ; y++, pix += skin->width)
|
||||||
|
{
|
||||||
|
for (x=0 ; x < srcw ; )
|
||||||
|
{
|
||||||
|
if (raw - (qbyte*)pcx > pcxsize)
|
||||||
|
{
|
||||||
|
BZ_Free(out);
|
||||||
|
Con_Printf ("Skin %s was malformed. You should delete it.\n", name);
|
||||||
|
Skin_WorkerDone(skin, NULL, 0, 0);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
dataByte = *raw++;
|
||||||
|
|
||||||
|
if((dataByte & 0xC0) == 0xC0)
|
||||||
|
{
|
||||||
|
runLength = dataByte & 0x3F;
|
||||||
|
if (raw - (qbyte*)pcx > pcxsize)
|
||||||
|
{
|
||||||
|
BZ_Free(out);
|
||||||
|
Con_Printf ("Skin %s was malformed. You should delete it.\n", name);
|
||||||
|
Skin_WorkerDone(skin, NULL, 0, 0);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
dataByte = *raw++;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
runLength = 1;
|
||||||
|
|
||||||
|
// skin sanity check
|
||||||
|
if (runLength + x > pcx->xmax + 2)
|
||||||
|
{
|
||||||
|
BZ_Free(out);
|
||||||
|
Con_Printf ("Skin %s was malformed. You should delete it.\n", name);
|
||||||
|
Skin_WorkerDone(skin, NULL, 0, 0);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (dataByte >= 256-vid.fullbright) //kill the fb componant
|
||||||
|
if (!r_fb_models.ival)
|
||||||
|
dataByte = fbremap[dataByte + vid.fullbright-256];
|
||||||
|
|
||||||
|
while(runLength-- > 0)
|
||||||
|
pix[x++] = dataByte;
|
||||||
|
}
|
||||||
|
|
||||||
|
//pad the end of the scan line with the trailing pixel
|
||||||
|
for ( ; x < skin->width ; )
|
||||||
|
pix[x++] = dataByte;
|
||||||
|
}
|
||||||
|
//pad the bottom of the skin with that final pixel
|
||||||
|
for ( ; y < skin->height; y++, pix += skin->width)
|
||||||
|
for (x = 0; x < skin->width; )
|
||||||
|
pix[x++] = dataByte;
|
||||||
|
|
||||||
|
if ( raw - (qbyte *)pcx > pcxsize)
|
||||||
|
{
|
||||||
|
BZ_Free(out);
|
||||||
|
Con_Printf ("Skin %s was malformed. You should delete it.\n", name);
|
||||||
|
Skin_WorkerDone(skin, NULL, 0, 0);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
Skin_WorkerDone(skin, out, srcw, srch);
|
||||||
|
skin->loadstate = SKIN_LOADED;
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
/*
|
/*
|
||||||
==========
|
==========
|
||||||
|
@ -208,25 +353,15 @@ Returns a pointer to the skin bitmap, or NULL to use the default
|
||||||
qbyte *Skin_Cache8 (qwskin_t *skin)
|
qbyte *Skin_Cache8 (qwskin_t *skin)
|
||||||
{
|
{
|
||||||
char name[1024];
|
char name[1024];
|
||||||
qbyte *raw;
|
|
||||||
qbyte *out, *pix;
|
|
||||||
pcx_t *pcx;
|
|
||||||
int x, y, srcw, srch;
|
|
||||||
int dataByte;
|
|
||||||
int runLength;
|
|
||||||
int fbremap[256];
|
|
||||||
char *skinpath;
|
char *skinpath;
|
||||||
size_t pcxsize;
|
|
||||||
|
|
||||||
if (noskins.value==1) // JACK: So NOSKINS > 1 will show skins, but
|
if (noskins.value==1) // JACK: So NOSKINS > 1 will show skins, but
|
||||||
return NULL; // not download new ones.
|
return NULL; // not download new ones.
|
||||||
|
|
||||||
if (skin->failedload==true)
|
if (skin->loadstate==SKIN_LOADING)
|
||||||
return NULL;
|
return NULL;
|
||||||
|
if (skin->loadstate==SKIN_LOADED)
|
||||||
out = skin->skindata;
|
return skin->skindata;
|
||||||
if (out)
|
|
||||||
return out;
|
|
||||||
|
|
||||||
//
|
//
|
||||||
// load the pic from disk
|
// load the pic from disk
|
||||||
|
@ -236,6 +371,7 @@ qbyte *Skin_Cache8 (qwskin_t *skin)
|
||||||
qbyte bv;
|
qbyte bv;
|
||||||
int col[3];
|
int col[3];
|
||||||
char *s;
|
char *s;
|
||||||
|
qbyte *out;
|
||||||
|
|
||||||
s = COM_Parse(skin->name);
|
s = COM_Parse(skin->name);
|
||||||
col[0] = atof(com_token);
|
col[0] = atof(com_token);
|
||||||
|
@ -253,22 +389,19 @@ qbyte *Skin_Cache8 (qwskin_t *skin)
|
||||||
|
|
||||||
memset (out, bv, 320*200);
|
memset (out, bv, 320*200);
|
||||||
|
|
||||||
skin->failedload = false;
|
skin->loadstate = SKIN_LOADED;
|
||||||
|
|
||||||
return out;
|
return out;
|
||||||
}
|
}
|
||||||
|
|
||||||
skinpath = "skins";
|
skinpath = "skins";
|
||||||
|
|
||||||
//2 is used to try to force the skin if it load24bit is false.
|
if (gl_load24bit.ival || skin->loadstate == SKIN_FAILED)
|
||||||
if (gl_load24bit.ival || skin->failedload==2)
|
|
||||||
{
|
{
|
||||||
if (!skin->textures.base)
|
if (!skin->textures.base)
|
||||||
skin->textures.base = R_LoadHiResTexture(skin->name, skinpath, IF_NOALPHA|IF_NOPCX);
|
skin->textures.base = R_LoadHiResTexture(skin->name, skinpath, IF_NOALPHA|IF_NOPCX);
|
||||||
if (skin->textures.base->status == TEX_LOADING)
|
if (skin->textures.base->status == TEX_LOADING)
|
||||||
return NULL; //don't spam the others until we actually know this one will load.
|
return NULL; //don't spam the others until we actually know this one will load.
|
||||||
if (skin->failedload == 2)
|
|
||||||
skin->failedload = 1;
|
|
||||||
if (TEXLOADED(skin->textures.base))
|
if (TEXLOADED(skin->textures.base))
|
||||||
{
|
{
|
||||||
if (!skin->textures.upperoverlay)
|
if (!skin->textures.upperoverlay)
|
||||||
|
@ -291,148 +424,18 @@ qbyte *Skin_Cache8 (qwskin_t *skin)
|
||||||
Q_snprintfz (name, sizeof(name), "%s_gloss", skin->name);
|
Q_snprintfz (name, sizeof(name), "%s_gloss", skin->name);
|
||||||
TEXASSIGN(skin->textures.specular, R_LoadHiResTexture(skin->name, skinpath, 0));
|
TEXASSIGN(skin->textures.specular, R_LoadHiResTexture(skin->name, skinpath, 0));
|
||||||
}
|
}
|
||||||
skin->failedload = 1;
|
skin->loadstate = SKIN_LOADED;
|
||||||
return NULL; //can use the high-res textures instead.
|
return NULL; //can use the high-res textures instead.
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
Q_snprintfz (name, sizeof(name), "%s/%s.pcx", skinpath, skin->name);
|
if (skin->loadstate == SKIN_FAILED)
|
||||||
raw = COM_LoadTempFile (name, &pcxsize);
|
|
||||||
if (!raw)
|
|
||||||
{
|
|
||||||
//use 24bit skins even if gl_load24bit is failed
|
|
||||||
if (strcmp(skin->name, baseskin.string))
|
|
||||||
{
|
|
||||||
//if its not already the base skin, try the base (and warn if anything not base couldn't load).
|
|
||||||
Con_Printf ("Couldn't load skin %s\n", name);
|
|
||||||
Q_snprintfz (name, sizeof(name), "skins/%s.pcx", baseskin.string);
|
|
||||||
raw = COM_LoadTempFile (name, &pcxsize);
|
|
||||||
}
|
|
||||||
if (!raw)
|
|
||||||
{
|
|
||||||
if (skin->failedload)
|
|
||||||
skin->failedload = true;
|
|
||||||
else
|
|
||||||
skin->failedload = 2;
|
|
||||||
return NULL;
|
return NULL;
|
||||||
}
|
skin->loadstate = SKIN_LOADING;
|
||||||
}
|
|
||||||
|
|
||||||
//
|
Skin_WorkerLoad(skin, NULL, 0, 0);
|
||||||
// parse the PCX file
|
|
||||||
//
|
|
||||||
pcx = (pcx_t *)raw;
|
|
||||||
raw = (qbyte *)(pcx+1);
|
|
||||||
|
|
||||||
//check format (sizes are checked later)
|
return skin->skindata;
|
||||||
if (pcx->manufacturer != 0x0a
|
|
||||||
|| pcx->version != 5
|
|
||||||
|| pcx->encoding != 1
|
|
||||||
|| pcx->bits_per_pixel != 8)
|
|
||||||
{
|
|
||||||
skin->failedload = true;
|
|
||||||
Con_Printf ("Bad skin %s (unsupported format)\n", name);
|
|
||||||
return NULL;
|
|
||||||
}
|
|
||||||
|
|
||||||
pcx->xmax = (unsigned short)LittleShort(pcx->xmax);
|
|
||||||
pcx->ymax = (unsigned short)LittleShort(pcx->ymax);
|
|
||||||
pcx->xmin = (unsigned short)LittleShort(pcx->xmin);
|
|
||||||
pcx->ymin = (unsigned short)LittleShort(pcx->ymin);
|
|
||||||
|
|
||||||
srcw = pcx->xmax-pcx->xmin+1;
|
|
||||||
srch = pcx->ymax-pcx->ymin+1;
|
|
||||||
|
|
||||||
if (srcw < 1 || srch < 1 || srcw > 320 || srch > 200)
|
|
||||||
{
|
|
||||||
skin->failedload = true;
|
|
||||||
Con_Printf ("Bad skin %s (unsupported size)\n", name);
|
|
||||||
return NULL;
|
|
||||||
}
|
|
||||||
skin->width = srcw;
|
|
||||||
skin->height = srch;
|
|
||||||
|
|
||||||
skin->skindata = out = BZ_Malloc(skin->width*skin->height);
|
|
||||||
if (!out)
|
|
||||||
Sys_Error ("Skin_Cache: couldn't allocate");
|
|
||||||
|
|
||||||
// TODO: we build a fullbright remap.. can we get rid of this?
|
|
||||||
for (x = 0; x < vid.fullbright; x++)
|
|
||||||
fbremap[x] = x + (256-vid.fullbright); //fullbrights don't exist, so don't loose palette info.
|
|
||||||
|
|
||||||
|
|
||||||
pix = out;
|
|
||||||
// memset (out, 0, skin->width*skin->height);
|
|
||||||
|
|
||||||
dataByte = 0; //typically black (this is in case a 0*0 file is loaded... which won't happen anyway)
|
|
||||||
for (y=0 ; y < srch ; y++, pix += skin->width)
|
|
||||||
{
|
|
||||||
for (x=0 ; x < srcw ; )
|
|
||||||
{
|
|
||||||
if (raw - (qbyte*)pcx > pcxsize)
|
|
||||||
{
|
|
||||||
BZ_Free(skin->skindata);
|
|
||||||
skin->skindata = NULL;
|
|
||||||
skin->failedload = true;
|
|
||||||
Con_Printf ("Skin %s was malformed. You should delete it.\n", name);
|
|
||||||
return NULL;
|
|
||||||
}
|
|
||||||
dataByte = *raw++;
|
|
||||||
|
|
||||||
if((dataByte & 0xC0) == 0xC0)
|
|
||||||
{
|
|
||||||
runLength = dataByte & 0x3F;
|
|
||||||
if (raw - (qbyte*)pcx > pcxsize)
|
|
||||||
{
|
|
||||||
BZ_Free(skin->skindata);
|
|
||||||
skin->skindata = NULL;
|
|
||||||
skin->failedload = true;
|
|
||||||
Con_Printf ("Skin %s was malformed. You should delete it.\n", name);
|
|
||||||
return NULL;
|
|
||||||
}
|
|
||||||
dataByte = *raw++;
|
|
||||||
}
|
|
||||||
else
|
|
||||||
runLength = 1;
|
|
||||||
|
|
||||||
// skin sanity check
|
|
||||||
if (runLength + x > pcx->xmax + 2) {
|
|
||||||
BZ_Free(skin->skindata);
|
|
||||||
skin->skindata = NULL;
|
|
||||||
skin->failedload = true;
|
|
||||||
Con_Printf ("Skin %s was malformed. You should delete it.\n", name);
|
|
||||||
return NULL;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (dataByte >= 256-vid.fullbright) //kill the fb componant
|
|
||||||
if (!r_fb_models.ival)
|
|
||||||
dataByte = fbremap[dataByte + vid.fullbright-256];
|
|
||||||
|
|
||||||
while(runLength-- > 0)
|
|
||||||
pix[x++] = dataByte;
|
|
||||||
}
|
|
||||||
|
|
||||||
//pad the end of the scan line with the trailing pixel
|
|
||||||
for ( ; x < skin->width ; )
|
|
||||||
pix[x++] = dataByte;
|
|
||||||
}
|
|
||||||
//pad the bottom of the skin with that final pixel
|
|
||||||
for ( ; y < skin->height; y++, pix += skin->width)
|
|
||||||
for (x = 0; x < skin->width; )
|
|
||||||
pix[x++] = dataByte;
|
|
||||||
|
|
||||||
if ( raw - (qbyte *)pcx > pcxsize)
|
|
||||||
{
|
|
||||||
BZ_Free(skin->skindata);
|
|
||||||
skin->skindata = NULL;
|
|
||||||
skin->failedload = true;
|
|
||||||
Con_Printf ("Skin %s was malformed. You should delete it.\n", name);
|
|
||||||
return NULL;
|
|
||||||
}
|
|
||||||
|
|
||||||
skin->failedload = false;
|
|
||||||
|
|
||||||
return out;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/*
|
/*
|
||||||
|
@ -482,9 +485,10 @@ void Skin_NextDownload (void)
|
||||||
}
|
}
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
for (i = 0; i != MAX_CLIENTS; i++)
|
for (i = 0; i < MAX_CLIENTS; i++)
|
||||||
{
|
{
|
||||||
sc = &cl.players[i];
|
sc = &cl.players[i];
|
||||||
|
sc->lastskin = NULL; //invalidate any 'safe' skins
|
||||||
if (!sc->name[0])
|
if (!sc->name[0])
|
||||||
continue;
|
continue;
|
||||||
Skin_Find (sc);
|
Skin_Find (sc);
|
||||||
|
@ -494,6 +498,7 @@ void Skin_NextDownload (void)
|
||||||
continue;
|
continue;
|
||||||
if (!*sc->qwskin->name)
|
if (!*sc->qwskin->name)
|
||||||
continue;
|
continue;
|
||||||
|
|
||||||
CL_CheckOrEnqueDownloadFile(va("skins/%s.pcx", sc->qwskin->name), NULL, 0);
|
CL_CheckOrEnqueDownloadFile(va("skins/%s.pcx", sc->qwskin->name), NULL, 0);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -524,11 +529,11 @@ void Skin_FlushAll(void)
|
||||||
{ //wipe the skin info
|
{ //wipe the skin info
|
||||||
int i;
|
int i;
|
||||||
for (i=0 ; i<numskins ; i++)
|
for (i=0 ; i<numskins ; i++)
|
||||||
{
|
|
||||||
if (skins[i].skindata)
|
if (skins[i].skindata)
|
||||||
BZ_Free(skins[i].skindata);
|
BZ_Free(skins[i].skindata);
|
||||||
}
|
|
||||||
numskins = 0;
|
numskins = 0;
|
||||||
|
for (i = 0; i < MAX_CLIENTS; i++)
|
||||||
|
cl.players[i].lastskin = NULL;
|
||||||
|
|
||||||
Skin_FlushPlayers();
|
Skin_FlushPlayers();
|
||||||
}
|
}
|
||||||
|
@ -552,11 +557,11 @@ void Skin_Skins_f (void)
|
||||||
|
|
||||||
R_GAliasFlushSkinCache(false);
|
R_GAliasFlushSkinCache(false);
|
||||||
for (i=0 ; i<numskins ; i++)
|
for (i=0 ; i<numskins ; i++)
|
||||||
{
|
|
||||||
if (skins[i].skindata)
|
if (skins[i].skindata)
|
||||||
BZ_Free(skins[i].skindata);
|
BZ_Free(skins[i].skindata);
|
||||||
}
|
|
||||||
numskins = 0;
|
numskins = 0;
|
||||||
|
for (i = 0; i < MAX_CLIENTS; i++)
|
||||||
|
cl.players[i].lastskin = NULL;
|
||||||
|
|
||||||
Skin_NextDownload ();
|
Skin_NextDownload ();
|
||||||
|
|
||||||
|
@ -593,7 +598,10 @@ int i;
|
||||||
for (i=0 ; i<numskins ; i++)
|
for (i=0 ; i<numskins ; i++)
|
||||||
{
|
{
|
||||||
if (!strcmp(skins[i].name, sname))
|
if (!strcmp(skins[i].name, sname))
|
||||||
skins[i].failedload = false;
|
{
|
||||||
|
skins[i].loadstate = SKIN_NOTLOADED;
|
||||||
|
memset(&skins[i].textures, 0, sizeof(skins[i].textures));
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -585,7 +585,9 @@ static shader_t *GL_ChooseSkin(galiasinfo_t *inf, model_t *model, int surfnum, e
|
||||||
|
|
||||||
if (!gl_nocolors.ival || forced)
|
if (!gl_nocolors.ival || forced)
|
||||||
{
|
{
|
||||||
if (!plskin || plskin->failedload)
|
tc = e->topcolour;
|
||||||
|
bc = e->bottomcolour;
|
||||||
|
if (!plskin || plskin->loadstate == SKIN_FAILED)
|
||||||
{
|
{
|
||||||
if (e->playerindex >= 0 && e->playerindex <= MAX_CLIENTS)
|
if (e->playerindex >= 0 && e->playerindex <= MAX_CLIENTS)
|
||||||
{
|
{
|
||||||
|
@ -595,17 +597,21 @@ static shader_t *GL_ChooseSkin(galiasinfo_t *inf, model_t *model, int surfnum, e
|
||||||
if (!cl.players[e->playerindex].qwskin)
|
if (!cl.players[e->playerindex].qwskin)
|
||||||
Skin_Find(&cl.players[e->playerindex]);
|
Skin_Find(&cl.players[e->playerindex]);
|
||||||
plskin = cl.players[e->playerindex].qwskin;
|
plskin = cl.players[e->playerindex].qwskin;
|
||||||
// if (plskin && plskin->failedload)
|
}
|
||||||
// plskin = NULL;
|
else
|
||||||
|
plskin = NULL;
|
||||||
|
|
||||||
|
if (plskin && plskin->loadstate != SKIN_LOADED)
|
||||||
|
{
|
||||||
|
Skin_Cache8(plskin); //we're not going to use it, but make sure its status is updated when it is finally loaded..
|
||||||
|
plskin = cl.players[e->playerindex].lastskin;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
cl.players[e->playerindex].lastskin = plskin;
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
plskin = NULL;
|
plskin = NULL;
|
||||||
}
|
}
|
||||||
else
|
|
||||||
plskin = NULL;
|
|
||||||
}
|
|
||||||
tc = e->topcolour;
|
|
||||||
bc = e->bottomcolour;
|
|
||||||
#ifdef HEXEN2
|
#ifdef HEXEN2
|
||||||
pc = e->h2playerclass;
|
pc = e->h2playerclass;
|
||||||
#else
|
#else
|
||||||
|
@ -714,37 +720,11 @@ static shader_t *GL_ChooseSkin(galiasinfo_t *inf, model_t *model, int surfnum, e
|
||||||
cm->texnum.loweroverlay = r_nulltex;
|
cm->texnum.loweroverlay = r_nulltex;
|
||||||
cm->texnum.upperoverlay = r_nulltex;
|
cm->texnum.upperoverlay = r_nulltex;
|
||||||
|
|
||||||
|
//q2 has no surfaces in its player models, so don't crash from that
|
||||||
|
//note that q2 should also always have a custom skin set. its not our problem (here) if it doesn't.
|
||||||
if (!shader)
|
if (!shader)
|
||||||
{ //model has no shaders, so just the skin directly
|
|
||||||
shader = R_RegisterSkin(skinname, NULL);
|
shader = R_RegisterSkin(skinname, NULL);
|
||||||
|
|
||||||
if (plskin)
|
|
||||||
{
|
|
||||||
original = Skin_Cache8(plskin);
|
|
||||||
if (original)
|
|
||||||
{
|
|
||||||
inwidth = plskin->width;
|
|
||||||
inheight = plskin->height;
|
|
||||||
cm->texnum.base = R_LoadTexture8(plskin->name, inwidth, inheight, original, IF_NOALPHA|IF_NOGAMMA, 1);
|
|
||||||
return shader;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (TEXVALID(plskin->textures.base))
|
|
||||||
{
|
|
||||||
cm->texnum.loweroverlay = plskin->textures.loweroverlay;
|
|
||||||
cm->texnum.upperoverlay = plskin->textures.upperoverlay;
|
|
||||||
cm->texnum.base = plskin->textures.base;
|
|
||||||
cm->texnum.fullbright = plskin->textures.fullbright;
|
|
||||||
cm->texnum.specular = plskin->textures.specular;
|
|
||||||
return shader;
|
|
||||||
}
|
|
||||||
|
|
||||||
cm->texnum.base = R_LoadHiResTexture(plskin->name, "skins", IF_NOALPHA);
|
|
||||||
return shader;
|
|
||||||
}
|
|
||||||
return shader;
|
|
||||||
}
|
|
||||||
|
|
||||||
cm->texnum.bump = shader->defaulttextures.bump; //can't colour bumpmapping
|
cm->texnum.bump = shader->defaulttextures.bump; //can't colour bumpmapping
|
||||||
if (plskin)
|
if (plskin)
|
||||||
{
|
{
|
||||||
|
|
Loading…
Reference in a new issue