Merge pull request #285 from 0lvin/particles_size

Fixes scale particles in soft render
This commit is contained in:
Yamagi 2018-04-17 20:52:15 +02:00 committed by GitHub
commit d4b6e936ef
No known key found for this signature in database
GPG key ID: 4AEE18F83AFDEB23
11 changed files with 219 additions and 239 deletions

View file

@ -34,14 +34,21 @@ void
GetWalInfo(char *name, int *width, int *height)
{
miptex_t *mt;
int size;
ri.FS_LoadFile(name, (void **)&mt);
size = ri.FS_LoadFile(name, (void **)&mt);
if (!mt)
{
return;
}
if (size < sizeof(miptex_t))
{
ri.FS_FreeFile((void *)mt);
return;
}
*width = LittleLong(mt->width);
*height = LittleLong(mt->height);

View file

@ -1013,10 +1013,10 @@ R_LoadPic(char *name, byte *pic, int width, int realwidth,
}
static image_t *
LoadWal(char *origname)
LoadWal(char *origname, imagetype_t type)
{
miptex_t *mt;
int width, height, ofs;
int width, height, ofs, size;
image_t *image;
char name[256];
@ -1028,7 +1028,7 @@ LoadWal(char *origname)
Q_strlcat(name, ".wal", sizeof(name));
}
ri.FS_LoadFile(name, (void **)&mt);
size = ri.FS_LoadFile(name, (void **)&mt);
if (!mt)
{
@ -1036,11 +1036,26 @@ LoadWal(char *origname)
return r_notexture;
}
if (size < sizeof(miptex_t))
{
R_Printf(PRINT_ALL, "LoadWal: can't load %s, small header\n", name);
ri.FS_FreeFile((void *)mt);
return r_notexture;
}
width = LittleLong(mt->width);
height = LittleLong(mt->height);
ofs = LittleLong(mt->offsets[0]);
image = R_LoadPic(name, (byte *)mt + ofs, width, 0, height, 0, it_wall, 8);
if ((ofs <= 0) || (width <= 0) || (height <= 0) ||
(((size - ofs) / height) < width))
{
R_Printf(PRINT_ALL, "LoadWal: can't load %s, small body\n", name);
ri.FS_FreeFile((void *)mt);
return r_notexture;
}
image = R_LoadPic(name, (byte *)mt + ofs, width, 0, height, 0, type, 8);
ri.FS_FreeFile((void *)mt);
@ -1078,7 +1093,7 @@ R_FindImage(char *name, imagetype_t type)
/* Remove the extension */
memset(namewe, 0, 256);
memcpy(namewe, name, len - 4);
memcpy(namewe, name, len - (strlen(ext) + 1));
if (len < 5)
{
@ -1175,7 +1190,7 @@ R_FindImage(char *name, imagetype_t type)
else
{
/* WAL if no TGA/PNG/JPEG available (exists always) */
image = LoadWal(namewe);
image = LoadWal(namewe, type);
}
if (!image)
@ -1186,7 +1201,7 @@ R_FindImage(char *name, imagetype_t type)
}
else /* gl_retexture is not set */
{
image = LoadWal(name);
image = LoadWal(name, type);
if (!image)
{

View file

@ -550,10 +550,10 @@ GL3_LoadPic(char *name, byte *pic, int width, int realwidth,
}
static gl3image_t *
LoadWal(char *origname)
LoadWal(char *origname, imagetype_t type)
{
miptex_t *mt;
int width, height, ofs;
int width, height, ofs, size;
gl3image_t *image;
char name[256];
@ -565,7 +565,7 @@ LoadWal(char *origname)
Q_strlcat(name, ".wal", sizeof(name));
}
ri.FS_LoadFile(name, (void **)&mt);
size = ri.FS_LoadFile(name, (void **)&mt);
if (!mt)
{
@ -573,11 +573,26 @@ LoadWal(char *origname)
return gl3_notexture;
}
if (size < sizeof(miptex_t))
{
R_Printf(PRINT_ALL, "LoadWal: can't load %s, small header\n", name);
ri.FS_FreeFile((void *)mt);
return gl3_notexture;
}
width = LittleLong(mt->width);
height = LittleLong(mt->height);
ofs = LittleLong(mt->offsets[0]);
image = GL3_LoadPic(name, (byte *)mt + ofs, width, 0, height, 0, it_wall, 8);
if ((ofs <= 0) || (width <= 0) || (height <= 0) ||
(((size - ofs) / height) < width))
{
R_Printf(PRINT_ALL, "LoadWal: can't load %s, small body\n", name);
ri.FS_FreeFile((void *)mt);
return gl3_notexture;
}
image = GL3_LoadPic(name, (byte *)mt + ofs, width, 0, height, 0, type, 8);
ri.FS_FreeFile((void *)mt);
@ -615,7 +630,7 @@ GL3_FindImage(char *name, imagetype_t type)
/* Remove the extension */
memset(namewe, 0, 256);
memcpy(namewe, name, len - 4);
memcpy(namewe, name, len - (strlen(ext) + 1));
if (len < 5)
{
@ -711,7 +726,7 @@ GL3_FindImage(char *name, imagetype_t type)
else
{
/* WAL if no TGA/PNG/JPEG available (exists always) */
image = LoadWal(namewe);
image = LoadWal(namewe, type);
}
if (!image)
@ -722,7 +737,7 @@ GL3_FindImage(char *name, imagetype_t type)
}
else /* gl_retexture is not set */
{
image = LoadWal(name);
image = LoadWal(name, type);
if (!image)
{

View file

@ -361,7 +361,6 @@ extern qboolean r_dowarp;
extern affinetridesc_t r_affinetridesc;
void R_DrawParticle(void);
void D_WarpScreen(void);
void R_PolysetUpdateTables(void);
@ -390,7 +389,7 @@ surfcache_t *D_CacheSurface (msurface_t *surface, int miplevel);
extern int d_vrectx, d_vrecty, d_vrectright_particle, d_vrectbottom_particle;
extern int d_pix_min, d_pix_max, d_pix_shift;
extern int d_pix_min, d_pix_max, d_pix_mul;
extern pixel_t *d_viewbuffer;
extern zvalue_t *d_pzbuffer;

View file

@ -133,41 +133,80 @@ R_LoadPic (char *name, byte *pic, int width, int height, imagetype_t type)
return image;
}
static void
R_Restore_Mip(unsigned char* src, unsigned char *dst, int height, int width)
{
int x, y;
for (y=0; y<height; y++)
{
for (x=0; x<width; x++)
{
dst[x + y * width] = src[(x + y * width)*2];
}
}
}
/*
================
R_LoadWal
================
*/
static image_t *
R_LoadWal (char *name)
R_LoadWal (char *name, imagetype_t type)
{
miptex_t *mt;
int ofs;
int ofs;
image_t *image;
int size;
int size, file_size;
ri.FS_LoadFile (name, (void **)&mt);
file_size = ri.FS_LoadFile (name, (void **)&mt);
if (!mt)
{
R_Printf(PRINT_ALL, "R_LoadWal: can't load %s\n", name);
return r_notexture_mip;
}
if (file_size < sizeof(miptex_t))
{
R_Printf(PRINT_ALL, "R_LoadWal: can't load %s, small header\n", name);
ri.FS_FreeFile ((void *)mt);
return r_notexture_mip;
}
image = R_FindFreeImage ();
strcpy (image->name, name);
image->width = LittleLong (mt->width);
image->height = LittleLong (mt->height);
image->type = it_wall;
image->type = type;
image->registration_sequence = registration_sequence;
ofs = LittleLong (mt->offsets[0]);
size = image->width * image->height * (256+64+16+4)/256;
if ((ofs <= 0) || (image->width <= 0) || (image->height <= 0) ||
((file_size - ofs) / image->width < image->height))
{
R_Printf(PRINT_ALL, "LoadWal: can't load %s, small body\n", name);
ri.FS_FreeFile((void *)mt);
return r_notexture_mip;
}
size = image->width*image->height * (256+64+16+4)/256;
image->pixels[0] = malloc (size);
image->pixels[1] = image->pixels[0] + image->width*image->height;
image->pixels[2] = image->pixels[1] + image->width*image->height/4;
image->pixels[3] = image->pixels[2] + image->width*image->height/16;
ofs = LittleLong (mt->offsets[0]);
memcpy ( image->pixels[0], (byte *)mt + ofs, size);
if (size > (file_size - ofs))
{
memcpy ( image->pixels[0], (byte *)mt + ofs, file_size - ofs);
// looks to short restore everything from first image
R_Restore_Mip(image->pixels[0], image->pixels[1], image->height/2, image->width/2);
R_Restore_Mip(image->pixels[1], image->pixels[2], image->height/4, image->width/4);
R_Restore_Mip(image->pixels[2], image->pixels[3], image->height/8, image->width/8);
}
else
{
memcpy ( image->pixels[0], (byte *)mt + ofs, size);
}
ri.FS_FreeFile ((void *)mt);
@ -228,7 +267,7 @@ image_t *R_FindImage (char *name, imagetype_t type)
}
else if (!strcmp(name+len-4, ".wal"))
{
image = R_LoadWal (name);
image = R_LoadWal (name, type);
}
else if (!strcmp(name+len-4, ".tga"))
return NULL; // ri.Sys_Error (ERR_DROP, "R_FindImage: can't load %s in software renderer", name);

View file

@ -122,6 +122,7 @@ cvar_t *sw_stipplealpha;
cvar_t *sw_surfcacheoverride;
cvar_t *sw_waterwarp;
static cvar_t *sw_overbrightbits;
cvar_t *sw_custom_particles;
cvar_t *r_drawworld;
static cvar_t *r_drawentities;
@ -269,6 +270,7 @@ R_Register (void)
sw_surfcacheoverride = ri.Cvar_Get ("sw_surfcacheoverride", "0", 0);
sw_waterwarp = ri.Cvar_Get ("sw_waterwarp", "1", 0);
sw_overbrightbits = ri.Cvar_Get("sw_overbrightbits", "1.0", CVAR_ARCHIVE);
sw_custom_particles = ri.Cvar_Get("sw_custom_particles", "0", CVAR_ARCHIVE);
r_mode = ri.Cvar_Get( "r_mode", "0", CVAR_ARCHIVE );
r_lefthand = ri.Cvar_Get( "hand", "0", CVAR_USERINFO | CVAR_ARCHIVE );

View file

@ -40,7 +40,7 @@ static int r_frustum_indexes[4*6];
static float basemip[NUM_MIPS-1] = {1.0, 0.5*0.8, 0.25*0.8};
int d_vrectx, d_vrecty, d_vrectright_particle, d_vrectbottom_particle;
float xcenter, ycenter;
int d_pix_min, d_pix_max, d_pix_shift;
int d_pix_min, d_pix_max, d_pix_mul;
/*
================
@ -56,15 +56,16 @@ D_ViewChanged (void)
d_zwidth = vid.width;
d_pix_min = r_refdef.vrect.width / 320;
d_pix_min = r_refdef.vrect.height / 240;
if (d_pix_min < 1)
d_pix_min = 1;
d_pix_max = (int)((float)r_refdef.vrect.width / (320.0 / 4.0) + 0.5);
d_pix_shift = 8 - (int)((float)r_refdef.vrect.width / 320.0 + 0.5);
d_pix_max = (int)((float)r_refdef.vrect.height / (240.0 / 4.0) + 0.5);
if (d_pix_max < 1)
d_pix_max = 1;
d_pix_mul = (int)((float)r_refdef.vrect.height / 240.0 + 0.5);
d_vrectx = r_refdef.vrect.x;
d_vrecty = r_refdef.vrect.y;
d_vrectright_particle = r_refdef.vrectright - d_pix_max;

View file

@ -20,6 +20,7 @@ Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
#include "header/local.h"
static vec3_t r_pright, r_pup, r_ppn;
extern cvar_t *sw_custom_particles;
#define PARTICLE_33 0
#define PARTICLE_66 1
@ -32,8 +33,6 @@ typedef struct
int color;
} partparms_t;
static partparms_t partparms;
/*
** R_DrawParticle
**
@ -47,16 +46,17 @@ static partparms_t partparms;
** function pointer route. This exacts some overhead, but
** it pays off in clean and easy to understand code.
*/
void R_DrawParticle( void )
static void R_DrawParticle(partparms_t *partparms)
{
particle_t *pparticle = partparms.particle;
int level = partparms.level;
particle_t *pparticle = partparms->particle;
int level = partparms->level;
vec3_t local, transformed;
float zi;
byte *pdest;
zvalue_t *pz;
int color = pparticle->color;
int i, izi, pix, count, u, v;
int custom_particle = (int)sw_custom_particles->value;
/*
** transform the particle
@ -98,7 +98,7 @@ void R_DrawParticle( void )
** determine the screen area covered by the particle,
** which also means clamping to a min and max
*/
pix = izi >> d_pix_shift;
pix = (izi * d_pix_mul) >> 7;
if (pix < d_pix_min)
pix = d_pix_min;
else if (pix > d_pix_max)
@ -109,49 +109,112 @@ void R_DrawParticle( void )
*/
count = pix;
switch (level) {
case PARTICLE_33 :
for ( ; count ; count--, pz += d_zwidth, pdest += r_screenwidth)
{
//FIXME--do it in blocks of 8?
for (i=0 ; i<pix ; i++)
if (custom_particle == 0)
{
switch (level) {
case PARTICLE_33 :
for ( ; count ; count--, pz += d_zwidth, pdest += r_screenwidth)
{
if (pz[i] <= izi)
//FIXME--do it in blocks of 8?
for (i=0 ; i<pix ; i++)
{
pz[i] = izi;
pdest[i] = vid_alphamap[color + ((int)pdest[i]<<8)];
if (pz[i] <= izi)
{
pz[i] = izi;
pdest[i] = vid_alphamap[color + ((int)pdest[i]<<8)];
}
}
}
}
break;
break;
case PARTICLE_66 :
for ( ; count ; count--, pz += d_zwidth, pdest += r_screenwidth)
case PARTICLE_66 :
{
for (i=0 ; i<pix ; i++)
int color_part = (color<<8);
for ( ; count ; count--, pz += d_zwidth, pdest += r_screenwidth)
{
if (pz[i] <= izi)
for (i=0 ; i<pix ; i++)
{
pz[i] = izi;
pdest[i] = vid_alphamap[(color<<8) + (int)pdest[i]];
if (pz[i] <= izi)
{
pz[i] = izi;
pdest[i] = vid_alphamap[color_part + (int)pdest[i]];
}
}
}
break;
}
break;
default: //100
for ( ; count ; count--, pz += d_zwidth, pdest += r_screenwidth)
{
for (i=0 ; i<pix ; i++)
default: //100
for ( ; count ; count--, pz += d_zwidth, pdest += r_screenwidth)
{
if (pz[i] <= izi)
for (i=0 ; i<pix ; i++)
{
pz[i] = izi;
pdest[i] = color;
if (pz[i] <= izi)
{
pz[i] = izi;
pdest[i] = color;
}
}
}
break;
}
}
else
{
int min_int, max_int;
min_int = pix / 2;
max_int = (pix * 2) - min_int;
switch (level) {
case PARTICLE_33 :
for ( ; count ; count--, pz += d_zwidth, pdest += r_screenwidth)
{
//FIXME--do it in blocks of 8?
for (i=0 ; i<pix ; i++)
{
int pos = i + count;
if (pos >= min_int && pos <= max_int && pz[i] <= izi)
{
pz[i] = izi;
pdest[i] = vid_alphamap[color + ((int)pdest[i]<<8)];
}
}
}
break;
case PARTICLE_66 :
{
int color_part = (color<<8);
for ( ; count ; count--, pz += d_zwidth, pdest += r_screenwidth)
{
for (i=0 ; i<pix ; i++)
{
int pos = i + count;
if (pos >= min_int && pos <= max_int && pz[i] <= izi)
{
pz[i] = izi;
pdest[i] = vid_alphamap[color_part + (int)pdest[i]];
}
}
}
break;
}
default: //100
for ( ; count ; count--, pz += d_zwidth, pdest += r_screenwidth)
{
for (i=0 ; i<pix ; i++)
{
int pos = i + count;
if (pos >= min_int && pos <= max_int && pz[i] <= izi)
{
pz[i] = izi;
pdest[i] = color;
}
}
}
break;
}
break;
}
}
@ -165,6 +228,8 @@ void R_DrawParticle( void )
*/
void R_DrawParticles (void)
{
partparms_t partparms;
particle_t *p;
int i;
@ -185,6 +250,6 @@ void R_DrawParticles (void)
partparms.particle = p;
partparms.color = p->color;
R_DrawParticle();
R_DrawParticle(&partparms);
}
}

View file

@ -33,18 +33,7 @@ static int r_numhblocks, r_numvblocks;
static unsigned char *r_source, *r_sourcemax;
static unsigned *r_lightptr;
static void R_DrawSurfaceBlock8_mip0 (void);
static void R_DrawSurfaceBlock8_mip1 (void);
static void R_DrawSurfaceBlock8_mip2 (void);
static void R_DrawSurfaceBlock8_mip3 (void);
static void (*surfmiptable[4])(void) = {
R_DrawSurfaceBlock8_mip0,
R_DrawSurfaceBlock8_mip1,
R_DrawSurfaceBlock8_mip2,
R_DrawSurfaceBlock8_mip3
};
static void R_DrawSurfaceBlock8_anymip (int level);
void R_BuildLightMap (void);
extern unsigned blocklights[1024]; // allow some very large lightmaps
@ -93,7 +82,6 @@ static void R_DrawSurface (void)
int soffset, basetoffset, texwidth;
int horzblockstep;
unsigned char *pcolumndest;
void (*pblockdrawer)(void);
image_t *mt;
surfrowbytes = r_drawsurf.rowbytes;
@ -117,7 +105,6 @@ static void R_DrawSurface (void)
//==============================
pblockdrawer = surfmiptable[r_drawsurf.surfmip];
// TODO: only needs to be set when there is a display settings change
horzblockstep = blocksize;
@ -147,7 +134,7 @@ static void R_DrawSurface (void)
pbasesource = basetptr + soffset;
(*pblockdrawer)();
R_DrawSurfaceBlock8_anymip(4-r_drawsurf.surfmip);
soffset = soffset + blocksize;
if (soffset >= smax)
@ -162,14 +149,15 @@ static void R_DrawSurface (void)
/*
================
R_DrawSurfaceBlock8_mip0
R_DrawSurfaceBlock8_anymip
================
*/
static void R_DrawSurfaceBlock8_mip0 (void)
static void R_DrawSurfaceBlock8_anymip (int level)
{
int v, i, b, lightstep, lighttemp, light;
int v, i, b, lightstep, lighttemp, light, size;
unsigned char pix, *psource, *prowdest;
size = 1 << level;
psource = pbasesource;
prowdest = prowdestbase;
@ -180,17 +168,17 @@ static void R_DrawSurfaceBlock8_mip0 (void)
lightleft = r_lightptr[0];
lightright = r_lightptr[1];
r_lightptr += r_lightwidth;
lightleftstep = (r_lightptr[0] - lightleft) >> 4;
lightrightstep = (r_lightptr[1] - lightright) >> 4;
lightleftstep = (r_lightptr[0] - lightleft) >> level;
lightrightstep = (r_lightptr[1] - lightright) >> level;
for (i=0 ; i<16 ; i++)
for (i=0 ; i<size ; i++)
{
lighttemp = lightleft - lightright;
lightstep = lighttemp >> 4;
lightstep = lighttemp >> level;
light = lightright;
for (b=15; b>=0; b--)
for (b=(size-1); b>=0; b--)
{
pix = psource[b];
prowdest[b] = ((unsigned char *)vid_colormap)
@ -209,157 +197,6 @@ static void R_DrawSurfaceBlock8_mip0 (void)
}
}
/*
================
R_DrawSurfaceBlock8_mip1
================
*/
static void R_DrawSurfaceBlock8_mip1 (void)
{
int v, i, b, lightstep, lighttemp, light;
unsigned char pix, *psource, *prowdest;
psource = pbasesource;
prowdest = prowdestbase;
for (v=0 ; v<r_numvblocks ; v++)
{
// FIXME: make these locals?
// FIXME: use delta rather than both right and left, like ASM?
lightleft = r_lightptr[0];
lightright = r_lightptr[1];
r_lightptr += r_lightwidth;
lightleftstep = (r_lightptr[0] - lightleft) >> 3;
lightrightstep = (r_lightptr[1] - lightright) >> 3;
for (i=0 ; i<8 ; i++)
{
lighttemp = lightleft - lightright;
lightstep = lighttemp >> 3;
light = lightright;
for (b=7; b>=0; b--)
{
pix = psource[b];
prowdest[b] = ((unsigned char *)vid_colormap)
[(light & 0xFF00) + pix];
light += lightstep;
}
psource += sourcetstep;
lightright += lightrightstep;
lightleft += lightleftstep;
prowdest += surfrowbytes;
}
if (psource >= r_sourcemax)
psource -= r_stepback;
}
}
/*
================
R_DrawSurfaceBlock8_mip2
================
*/
static void R_DrawSurfaceBlock8_mip2 (void)
{
int v, i, b, lightstep, lighttemp, light;
unsigned char pix, *psource, *prowdest;
psource = pbasesource;
prowdest = prowdestbase;
for (v=0 ; v<r_numvblocks ; v++)
{
// FIXME: make these locals?
// FIXME: use delta rather than both right and left, like ASM?
lightleft = r_lightptr[0];
lightright = r_lightptr[1];
r_lightptr += r_lightwidth;
lightleftstep = (r_lightptr[0] - lightleft) >> 2;
lightrightstep = (r_lightptr[1] - lightright) >> 2;
for (i=0 ; i<4 ; i++)
{
lighttemp = lightleft - lightright;
lightstep = lighttemp >> 2;
light = lightright;
for (b=3; b>=0; b--)
{
pix = psource[b];
prowdest[b] = ((unsigned char *)vid_colormap)
[(light & 0xFF00) + pix];
light += lightstep;
}
psource += sourcetstep;
lightright += lightrightstep;
lightleft += lightleftstep;
prowdest += surfrowbytes;
}
if (psource >= r_sourcemax)
psource -= r_stepback;
}
}
/*
================
R_DrawSurfaceBlock8_mip3
================
*/
static void R_DrawSurfaceBlock8_mip3 (void)
{
int v, i, b, lightstep, lighttemp, light;
unsigned char pix, *psource, *prowdest;
psource = pbasesource;
prowdest = prowdestbase;
for (v=0 ; v<r_numvblocks ; v++)
{
// FIXME: make these locals?
// FIXME: use delta rather than both right and left, like ASM?
lightleft = r_lightptr[0];
lightright = r_lightptr[1];
r_lightptr += r_lightwidth;
lightleftstep = (r_lightptr[0] - lightleft) >> 1;
lightrightstep = (r_lightptr[1] - lightright) >> 1;
for (i=0 ; i<2 ; i++)
{
lighttemp = lightleft - lightright;
lightstep = lighttemp >> 1;
light = lightright;
for (b=1; b>=0; b--)
{
pix = psource[b];
prowdest[b] = ((unsigned char *)vid_colormap)
[(light & 0xFF00) + pix];
light += lightstep;
}
psource += sourcetstep;
lightright += lightrightstep;
lightleft += lightleftstep;
prowdest += surfrowbytes;
}
if (psource >= r_sourcemax)
psource -= r_stepback;
}
}
//============================================================================

View file

@ -41,7 +41,7 @@ static int rd_buffersize;
static void (*rd_flush)(int target, char *buffer);
void
Com_BeginRedirect(int target, char *buffer, int buffersize, void (*flush))
Com_BeginRedirect(int target, char *buffer, int buffersize, void (*flush)(int, char *))
{
if (!target || !buffer || !buffersize || !flush)
{

View file

@ -708,7 +708,7 @@ void FS_CreatePath(char *path);
#define PRINT_ALL 0
#define PRINT_DEVELOPER 1 /* only print when "developer 1" */
void Com_BeginRedirect(int target, char *buffer, int buffersize, void (*flush));
void Com_BeginRedirect(int target, char *buffer, int buffersize, void (*flush)(int, char *));
void Com_EndRedirect(void);
void Com_Printf(char *fmt, ...) __attribute__ ((format (printf, 1, 2)));
void Com_DPrintf(char *fmt, ...) __attribute__ ((format (printf, 1, 2)));