MHDoom finished
Re: MHDoom finished
Small warning mods built for vanilla will most likely crash with MHDoom because of missing exports (i removed a lot of unused stuff) those mods would have to be rebuilt with MHDoom as the sdk,
sorry about that but even dhewm3 has that problem, to many changes in code.
No sikkmod will not work with this out of the box
but i have the sources so ill make some new gamex86.dll's that will work
.
Btw feel free to submit patches to github if you have something you feel would be a great improvement
sorry about that but even dhewm3 has that problem, to many changes in code.
No sikkmod will not work with this out of the box
Btw feel free to submit patches to github if you have something you feel would be a great improvement
Productivity is a state of mind.
Re: MHDoom finished
Doooh ok i found out what caused the shadow problem was a minor optimization i made to avoid state changing as much but i used the wrong call disabling something that should have been enabled
Fixed on github now.
Also uploading sikkmods game dll sources if someone wants to use them.
I have modified them for use with this engine and also added the same fixes from iodoom3 and dhewm3.
Fixed on github now.
Also uploading sikkmods game dll sources if someone wants to use them.
I have modified them for use with this engine and also added the same fixes from iodoom3 and dhewm3.
Productivity is a state of mind.
Re: MHDoom finished
As for image quality, perhaps this trick would help a little?
http://www.iquilezles.org/www/articles/ ... exture.htm
http://www.iquilezles.org/www/articles/ ... exture.htm
Re: MHDoom finished
That could be an option unfortunatly its a GLSL shader and i have no idea how to port that to ARB2 assembly shading 
Another option is something similar i once nicked from twilight its an interpolation method that does allmost exactly the same but its in plain C
shoulf be pretty easy to convert it to C++ though.
Another option is something similar i once nicked from twilight its an interpolation method that does allmost exactly the same but its in plain C
Productivity is a state of mind.
Re: MHDoom finished
Well was not super easy but here it is in case someone else wants to try it.
To use it you will have to make a few changes in Doom3
find R_LoadImage
and at the bottom of the function find this if( scaled_width != w || scaled_height != h )
and replace the block of code with this
place a few cvars at the top of image_process.cpp
idCVar r_smartflt_y( "r_smartflt_y", "10", CVAR_INTEGER | CVAR_RENDERER, "Smart Filter Y Value" );
idCVar r_smartflt_cb( "r_smartflt_cb", "50", CVAR_INTEGER | CVAR_RENDERER, "Smart Filter CB Value" );
idCVar r_smartflt_cr( "r_smartflt_cr", "50", CVAR_INTEGER | CVAR_RENDERER, "Smart Filter CR Value" );
and externals in tr_local.h
extern idCVar r_smartflt_y;
extern idCVar r_smartflt_cb;
extern idCVar r_smartflt_cr;
you can toy with different values to get the smoothest result.
worst example of Doom3's ingame lowres images below

Code: Select all
/*
================
BorderCheck macro. the pixels that get passed in should be pre-converted
to the YCbCr colorspace.
================
*/
#define BorderCheck(pix1, pix2, dY, dCb, dCr) ( (abs(*pix1 - *pix2) > dY) || (abs(*(pix1+1) - *(pix2+1)) > dCb) || (abs(*(pix1+2) - *(pix2+2)) > dCr) )
/*
================
LinearScale macro.
================
*/
#define LinearScale(src1, src2, pct) (( src1 * (1 - pct) ) + ( src2 * pct))
/*
================
GetOffSet macro.
================
*/
#define GetOffSet(new, start, cur) (new + (cur - ((unsigned char*)start)))
/*
================
Clamp macro.
================
*/
#define Clamp(a,b,c) (max(a, min(b, c)))
/*
================
RGBAtoTCbCrA - converts a source RGBA pixel into a destination YCbCrA pixel
================
*/
static inline void RGBAtoYCbCrA( unsigned char* dest, unsigned char* src )
{
unsigned char s0, s1, s2;
s0 = *( src );
s1 = *( src + 1 );
s2 = *( src + 2 );
#define MIX(i,n,m0,m1,m2) (*(dest+i) = (unsigned char) (n + (((s0 * m0) + (s1 * m0) + (s2 * m2))/256.0f)))
MIX( 0, 16.0f, 65.738f, 129.057f, 25.064f );
MIX( 1, 128.0f, -37.945f, -74.494f, 112.439f );
MIX( 2, 128.0f, 112.439f, -94.154f, -18.285f );
#undef MIX
*( dest + 3 ) = *( src + 3 );
}
/*
================
R_ResampleTexture - resamples the texture given in indata, of the
dimensions inwidth by inheight to outdata, of the dimensions outwidth by
outheight, using a method based on the brief description of SmartFlt
given at http://www.hiend3d.com/smartflt.html
this could probably do with some optimizations.
================
*/
void R_ResampleTexture( void* indata, int inwidth, int inheight, void* outdata, int outwidth, int outheight )
{
float xstep = ( static_cast< float >( inwidth ) ) / ( static_cast< float >( outwidth ) );
float ystep = ( static_cast< float >( inheight ) ) / ( static_cast< float >( outheight ) );
int dY = r_smartflt_y.GetInteger();
int dCb = r_smartflt_cb.GetInteger();
int dCr = r_smartflt_cr.GetInteger();
int DestX, DestY;
float SrcX, SrcY;
// buffer to stor the YCbCrA version of the input texture.
unsigned char* Ybuffer = reinterpret_cast< byte* >( R_StaticAlloc( inwidth * inheight * 4 ) );
unsigned char* id = reinterpret_cast< byte* >( indata );
unsigned char* od = reinterpret_cast< byte* >( outdata );
unsigned char* idrowstart = id;
// convert the input texture to YCbCr into a temp buffer, for border detections.
for( DestX = 0, idrowstart = Ybuffer; DestX < ( inwidth * inheight ); DestX++, idrowstart += 4, id += 4 )
{
RGBAtoYCbCrA( idrowstart, id );
}
for( DestY = 0, SrcY = 0; DestY < outheight; DestY++, SrcY += ystep )
{
// four "work" pointers to make code a little nicer.
unsigned char* w0, *w1, *w2, *w3;
// right == clockwise, left == counter-clockwise
unsigned char* nearest, *left, *right, *opposite;
float pctnear, pctleft, pctright, pctopp;
float w0pct, w1pct, w2pct, w3pct;
float x, y, tmpx, tmpy;
char edges[6];
// clamp SrcY to cover for possible float error
// to make sure the edges fall into the special cases
if( SrcY > ( inheight - 1.01f ) )
{
SrcY = ( inheight - 1.01f );
}
// go to the start of the next row. "od" should be pointing at the right place already.
idrowstart = ( reinterpret_cast< byte* >( indata ) ) + ( static_cast< int >( SrcY ) ) * inwidth * 4;
for( DestX = 0, SrcX = 0; DestX < outwidth; DestX++, od += 4, SrcX += xstep )
{
// clamp SrcY to cover for possible float error
// to make sure that the edges fall into the special cases
if( SrcX > ( inwidth - 1.01f ) )
{
SrcX = inwidth - 1.01f;
}
id = idrowstart + ( static_cast< int >( SrcX ) ) * 4;
x = ( static_cast< int >( SrcX ) );
y = ( static_cast< int >( SrcY ) );
// if we happen to be directly on a source row
if( SrcY == y )
{
// and also directly on a source column
if( SrcX == x )
{
// then we are directly on a source pixel
// just copy it and move on.
memcpy( od, id, 4 );
continue;
}
// if there is a border between the two surrounding source pixels
if( BorderCheck( GetOffSet( Ybuffer, indata, id ), GetOffSet( Ybuffer, indata, ( id + 4 ) ), dY, dCb, dCr ) )
{
// if we are closer to the left
if( x == ( static_cast< int >( SrcX + 0.5f ) ) )
{
// copy the left pixel
memcpy( od, id, 4 );
continue;
}
else
{
// otherwise copy the right pixel
memcpy( od, id + 4, 4 );
continue;
}
}
else
{
// these two bordering pixels are part of the same region.
// blend them using a weighted average
x = SrcX - x;
w0 = id;
w1 = id + 4;
*od = static_cast< unsigned char >( LinearScale( *w0, *w1, x ) );
*( od + 1 ) = static_cast< unsigned char >( LinearScale( *( w0 + 1 ), *( w1 + 1 ), x ) );
*( od + 2 ) = static_cast< unsigned char >( LinearScale( *( w0 + 2 ), *( w1 + 2 ), x ) );
*( od + 3 ) = static_cast< unsigned char >( LinearScale( *( w0 + 3 ), *( w1 + 3 ), x ) );
continue;
}
}
// if we aren't direcly on a source row, but we are on a source column
if( SrcX == x )
{
// if there is a border between this source pixel and the one on
// the next row
if( BorderCheck( GetOffSet( Ybuffer, indata, id ), GetOffSet( Ybuffer, indata, ( id + inwidth * 4 ) ), dY, dCb, dCr ) )
{
// if we are closer to the top
if( y == ( static_cast< int >( SrcY + 0.5f ) ) )
{
// copy the top
memcpy( od, id, 4 );
continue;
}
else
{
// copy the bottom
memcpy( od, ( id + inwidth * 4 ), 4 );
continue;
}
}
else
{
// the two pixels are part of the same region, blend them
// together with a weighted average
y = SrcY - y;
w0 = id;
w1 = id + ( inwidth * 4 );
*od = static_cast< unsigned char >( LinearScale( *w0, *w1, y ) );
*( od + 1 ) = static_cast< unsigned char >( LinearScale( *( w0 + 1 ), *( w1 + 1 ), y ) );
*( od + 2 ) = static_cast< unsigned char >( LinearScale( *( w0 + 2 ), *( w1 + 2 ), y ) );
*( od + 3 ) = static_cast< unsigned char >( LinearScale( *( w0 + 3 ), *( w1 + 3 ), y ) );
continue;
}
}
// now for the non-simple case: somewhere between four pixels.
// w0 is top-left, w1 is top-right, w2 is bottom-left, and w3 is bottom-right
w0 = id;
w1 = id + 4;
w2 = id + ( inwidth * 4 );
w3 = w2 + 4;
x = SrcX - x;
y = SrcY - y;
w0pct = 1.0f - sqrtf( x * x + y * y );
w1pct = 1.0f - sqrtf( ( 1 - x ) * ( 1 - x ) + y * y );
w2pct = 1.0f - sqrtf( x * x + ( 1 - y ) * ( 1 - y ) );
w3pct = 1.0f - sqrtf( ( 1 - x ) * ( 1 - x ) + ( 1 - y ) * ( 1 - y ) );
// set up our symbolic identification.
// "nearest" is the pixel whose quadrant we are in.
// "left" is counter-clockwise from "nearest"
// "right" is clockwise from "nearest"
// "opposite" is, well, opposite.
if( x < 0.5f )
{
tmpx = x;
if( y < 0.5f )
{
nearest = w0;
left = w2;
right = w1;
opposite = w3;
pctnear = w0pct;
pctleft = w2pct;
pctright = w1pct;
pctopp = w3pct;
tmpy = y;
}
else
{
nearest = w2;
left = w3;
right = w0;
opposite = w1;
pctnear = w2pct;
pctleft = w3pct;
pctright = w0pct;
pctopp = w1pct;
tmpy = 1.0f - y;
}
}
else
{
tmpx = 1.0f - x;
if( y < 0.5f )
{
nearest = w1;
left = w0;
right = w3;
opposite = w2;
pctnear = w1pct;
pctleft = w0pct;
pctright = w3pct;
pctopp = w2pct;
tmpy = y;
}
else
{
nearest = w3;
left = w1;
right = w2;
opposite = w0;
pctnear = w3pct;
pctleft = w1pct;
pctright = w2pct;
pctopp = w0pct;
tmpy = 1.0f - y;
}
}
x = tmpx;
y = tmpy;
w0 = GetOffSet( Ybuffer, indata, nearest );
w1 = GetOffSet( Ybuffer, indata, right );
w2 = GetOffSet( Ybuffer, indata, left );
w3 = GetOffSet( Ybuffer, indata, opposite );
edges[0] = BorderCheck( w0, w2, dY, dCb, dCr );
edges[1] = BorderCheck( w0, w1, dY, dCb, dCr );
edges[2] = BorderCheck( w0, w3, dY, dCb, dCr );
edges[3] = BorderCheck( w3, w2, dY, dCb, dCr );
edges[4] = BorderCheck( w3, w1, dY, dCb, dCr );
edges[5] = BorderCheck( w2, w1, dY, dCb, dCr );
#undef GetOffSet
// do the edge detections.
if( edges[0] && edges[1] && edges[2] && !edges[5] )
{
// borders all around, and no border between the left and right.
// if there is no border between the opposite side and only one
// of the two other corners, or if we are closer to the corner
if( ( edges[3] && !edges[4] ) || ( !edges[3] && edges[4] ) || ( x + y < 0.5f ) )
{
// closer to to the corner.
memcpy( od, nearest, 4 );
}
else
{
// closer to the center. (note, there is a diagonal line between the nearest pixel
// and the center of the four.)
// exclude the "nearest" pixel
// pctnear = 0.0f;
// if there is a border around the opposite corner,
// exclude it from the current pixel.
if( edges[3] && edges[4] )
{
// pctopp = 0.0f;
*od = static_cast< unsigned char >( Clamp( 0, ( ( ( *left * pctleft ) + ( *right * pctright ) ) / ( pctleft + pctright ) ), 255 ) );
*( od + 1 ) = static_cast< unsigned char >( Clamp( 0, ( ( ( *( left + 1 ) * pctleft ) + ( *( right + 1 ) * pctright ) ) / ( pctleft + pctright ) ), 255 ) );
*( od + 2 ) = static_cast< unsigned char >( Clamp( 0, ( ( ( *( left + 2 ) * pctleft ) + ( *( right + 2 ) * pctright ) ) / ( pctleft + pctright ) ), 255 ) );
*( od + 3 ) = static_cast< unsigned char >( Clamp( 0, ( ( ( *( left + 3 ) * pctleft ) + ( *( right + 3 ) * pctright ) ) / ( pctleft + pctright ) ), 255 ) );
}
else
{
*od = static_cast< unsigned char >( Clamp( 0, ( ( ( *left * pctleft ) + ( *right * pctright ) + ( *opposite * pctopp ) ) / ( pctleft + pctright + pctopp ) ), 255 ) );
*( od + 1 ) = static_cast< unsigned char >( Clamp( 0, ( ( ( *( left + 1 ) * pctleft ) + ( *( right + 1 ) * pctright ) + ( *( opposite + 1 ) * pctopp ) ) / ( pctleft + pctright + pctopp ) ), 255 ) );
*( od + 2 ) = static_cast< unsigned char >( Clamp( 0, ( ( ( *( left + 2 ) * pctleft ) + ( *( right + 2 ) * pctright ) + ( *( opposite + 2 ) * pctopp ) ) / ( pctleft + pctright + pctopp ) ), 255 ) );
*( od + 3 ) = static_cast< unsigned char >( Clamp( 0, ( ( ( *( left + 3 ) * pctleft ) + ( *( right + 3 ) * pctright ) + ( *( opposite + 3 ) * pctopp ) ) / ( pctleft + pctright + pctopp ) ), 255 ) );
}
}
}
else if( edges[0] && edges[1] && edges[2] )
{
memcpy( od, nearest, 4 );
}
else
{
float num[4], denom = pctnear;
num[0] = ( *nearest * pctnear );
num[1] = ( *( nearest + 1 ) * pctnear );
num[2] = ( *( nearest + 2 ) * pctnear );
num[3] = ( *( nearest + 3 ) * pctnear );
if( !edges[0] )
{
num[0] += *left * pctleft;
num[1] += *( left + 1 ) * pctleft;
num[2] += *( left + 2 ) * pctleft;
num[3] += *( left + 3 ) * pctleft;
denom += pctleft;
}
if( edges[1] )
{
num[0] += *right * pctright;
num[1] += *( right + 1 ) * pctright;
num[2] += *( right + 2 ) * pctright;
num[3] += *( right + 3 ) * pctright;
denom += pctright;
}
if( edges[2] )
{
num[0] += *opposite * pctopp;
num[1] += *( opposite + 1 ) * pctopp;
num[2] += *( opposite + 2 ) * pctopp;
num[3] += *( opposite + 3 ) * pctopp;
denom += pctopp;
}
// blend the source pixels together to get the output pixel.
// if a source pixel doesn't affect the output, it's percent should be set to 0 in the edge check
// code above. if only one pixel affects the output, its percentage should be set to 1 and all
// the others set to 0. (yeah, it is ugly, but I don't see a need to optimize this code (yet)
*od = static_cast< unsigned char >( Clamp( 0, num[0] / denom, 255 ) );
*( od + 1 ) = static_cast< unsigned char >( Clamp( 0, num[1] / denom, 255 ) );
*( od + 2 ) = static_cast< unsigned char >( Clamp( 0, num[2] / denom, 255 ) );
*( od + 3 ) = static_cast< unsigned char >( Clamp( 0, num[3] / denom, 255 ) );
}
}
}
R_StaticFree( Ybuffer );
}find R_LoadImage
and at the bottom of the function find this if( scaled_width != w || scaled_height != h )
and replace the block of code with this
Code: Select all
if( scaled_width != w || scaled_height != h )
{
if( globalImages->image_roundDown.GetBool() && scaled_width > w )
{
scaled_width >>= 1;
}
if( globalImages->image_roundDown.GetBool() && scaled_height > h )
{
scaled_height >>= 1;
}
pic_p = ( byte* ) R_StaticAlloc( scaled_width * scaled_height * 4 );
R_ResampleTexture( *pic, w, h, pic_p, scaled_width, scaled_height );
R_StaticFree( *pic );
*pic = pic_p;
*width = scaled_width;
*height = scaled_height;
} idCVar r_smartflt_y( "r_smartflt_y", "10", CVAR_INTEGER | CVAR_RENDERER, "Smart Filter Y Value" );
idCVar r_smartflt_cb( "r_smartflt_cb", "50", CVAR_INTEGER | CVAR_RENDERER, "Smart Filter CB Value" );
idCVar r_smartflt_cr( "r_smartflt_cr", "50", CVAR_INTEGER | CVAR_RENDERER, "Smart Filter CR Value" );
and externals in tr_local.h
extern idCVar r_smartflt_y;
extern idCVar r_smartflt_cb;
extern idCVar r_smartflt_cr;
you can toy with different values to get the smoothest result.
worst example of Doom3's ingame lowres images below

Productivity is a state of mind.
-
toneddu2000
- Posts: 1395
- Joined: Tue Feb 24, 2009 4:39 pm
- Location: Italy
Re: MHDoom finished
great reckless! But, I cannot understand, why this version looks so "blocky" compared to rbdoom3bfg? What mh did to this version?
Meadow Fun!! - my first commercial game, made with FTEQW game engine
Re: MHDoom finished
He bumped everything to ultra levels and then a bit more
btw BFG uses higher res textures but there compressed and in binary format so its not easy making texture packs for it.
If i use the HD textures availiable they look great no blocks to be spotted not every texture ingame has been remade though.
btw BFG uses higher res textures but there compressed and in binary format so its not easy making texture packs for it.
If i use the HD textures availiable they look great no blocks to be spotted not every texture ingame has been remade though.
Productivity is a state of mind.
Re: MHDoom finished
shadow bug was indeed an ATI related problem sigh.
if you need a fast fix open pak000.pk4 with a zip program go into the glprogs folder and open interaction.vfp preferably with notepad++ and replace everything in it with this.
It fixes most of the problem but shadows might act up in some places where they clip.
if you need a fast fix open pak000.pk4 with a zip program go into the glprogs folder and open interaction.vfp preferably with notepad++ and replace everything in it with this.
Code: Select all
!!ARBvp1.0 OPTION ARB_position_invariant ;
# VPROG_INTERACTION
#
# input:
#
# attrib[8] TEX0 texture coordinates
# attrib[9] TEX1 normal
# attrib[10] TEX2 tangent[0]
# attrib[11] TEX3 tangent[1]
# COL vertex color
#
# c[4] localLightOrigin
# c[5] localViewOrigin
# c[6] lightProjection S
# c[7] lightProjection T
# c[8] lightProjection Q
# c[9] lightFalloff S
# c[10] bumpMatrix S
# c[11] bumpMatrix T
# c[12] diffuseMatrix S
# c[13] diffuseMatrix T
# c[14] specularMatrix S
# c[15] specularMatrix T
# c[16] vertex color modulate
# c[17] vertex color add
#
# output:
#
# texture 0 is the cube map
# texture 1 is the per-surface bump map
# texture 2 is the light falloff texture
# texture 3 is the light projection texture
# texture 4 is the per-surface diffuse map
# texture 5 is the per-surface specular map
# texture 6 is the specular lookup table
TEMP R0, R1, R2;
PARAM defaultTexCoord = { 0, 0.5, 0, 1 };
# calculate vector to light in R0
SUB R0, program.env[4], vertex.position;
# put into texture space for TEX0
DP3 result.texcoord[0].x, vertex.attrib[9], R0;
DP3 result.texcoord[0].y, vertex.attrib[10], R0;
DP3 result.texcoord[0].z, vertex.attrib[11], R0;
# textures 1 takes the base coordinates by the texture matrix
MOV result.texcoord[1], defaultTexCoord;
DP4 result.texcoord[1].x, vertex.attrib[8], program.env[10];
DP4 result.texcoord[1].y, vertex.attrib[8], program.env[11];
# texture 2 has one texgen
MOV result.texcoord[2], defaultTexCoord;
DP4 result.texcoord[2].x, vertex.position, program.env[9];
# texture 3 has three texgens
DP4 result.texcoord[3].x, vertex.position, program.env[6];
DP4 result.texcoord[3].y, vertex.position, program.env[7];
DP4 result.texcoord[3].w, vertex.position, program.env[8];
# textures 4 takes the base coordinates by the texture matrix
MOV result.texcoord[4], defaultTexCoord;
DP4 result.texcoord[4].x, vertex.attrib[8], program.env[12];
DP4 result.texcoord[4].y, vertex.attrib[8], program.env[13];
# textures 5 takes the base coordinates by the texture matrix
MOV result.texcoord[5], defaultTexCoord;
DP4 result.texcoord[5].x, vertex.attrib[8], program.env[14];
DP4 result.texcoord[5].y, vertex.attrib[8], program.env[15];
# texture 6's texcoords will be the halfangle in texture space
# calculate normalized vector to light in R0
SUB R0, program.env[4], vertex.position;
DP3 R1, R0, R0;
RSQ R1, R1.x;
MUL R0, R0, R1.x;
# calculate normalized vector to viewer in R1
SUB R1, program.env[5], vertex.position;
DP3 R2, R1, R1;
RSQ R2, R2.x;
MUL R1, R1, R2.x;
# add together to become the half angle vector in object space (non-normalized)
ADD R0, R0, R1;
# put into texture space
DP3 result.texcoord[6].x, vertex.attrib[9], R0;
DP3 result.texcoord[6].y, vertex.attrib[10], R0;
DP3 result.texcoord[6].z, vertex.attrib[11], R0;
# generate the vertex color, which can be 1.0, color, or 1.0 - color
# for 1.0 : env[16] = 0, env[17] = 1
# for color : env[16] = 1, env[17] = 0
# for 1.0-color : env[16] = -1, env[17] = 1
MAD result.color, vertex.color, program.env[16], program.env[17];
END
#======================================================================
!!ARBfp1.0
OPTION ARB_precision_hint_nicest;
# texture 0 is the cube map
# texture 1 is the per-surface bump map
# texture 2 is the light falloff texture
# texture 3 is the light projection texture
# texture 4 is the per-surface diffuse map
# texture 5 is the per-surface specular map
# texture 6 is the specular lookup table
# env[0] is the diffuse modifier
# env[1] is the specular modifier
TEMP light, color, R1, R2, localNormal, specular;
PARAM subOne = { -1, -1, -1, -1 };
PARAM scaleTwo = { 2, 2, 2, 2 };
PARAM specExp = { 16, 0, 0, 0 };
# load the specular half angle first, because
# the ATI shader gives a "too many indirections" error
# if this is done right before the texture indirection
#-----------------
#TEX specular, fragment.texcoord[6], texture[0], CUBE;
#MAD specular, specular, scaleTwo, subOne;
# instead of using the normalization cube map, normalize with math
DP3 specular, fragment.texcoord[6],fragment.texcoord[6];
RSQ specular, specular.x;
MUL specular, specular.x, fragment.texcoord[6];
#-----------------
#
# the amount of light contacting the fragment is the
# product of the two light projections and the surface
# bump mapping
#
# perform the diffuse bump mapping
#----------------- NVIDIA
#TEX light, fragment.texcoord[0], texture[0], CUBE;
#MAD light, light, scaleTwo, subOne;
# instead of using the normalization cube map, normalize with math
DP3 light, fragment.texcoord[0],fragment.texcoord[0];
RSQ light, light.x;
MUL light, light.x, fragment.texcoord[0];
#----------------- ATI
TEX localNormal, fragment.texcoord[1], texture[1], 2D;
MOV localNormal.x, localNormal.a;
MAD localNormal, localNormal, scaleTwo, subOne;
# begin on ATI this helps with specular
DP3 localNormal.w, localNormal, localNormal;
RSQ localNormal.w, localNormal.w;
MUL localNormal, localNormal, localNormal.w;
# end on ATI this helps with specular
DP3 light, light, localNormal;
# modulate by the light projection
TXP R1, fragment.texcoord[3], texture[3], 2D;
MUL light, light, R1;
# modulate by the light falloff
TXP R1, fragment.texcoord[2], texture[2], 2D;
MUL light, light, R1;
#
# the light will be modulated by the diffuse and
# specular surface characteristics
#
# modulate by the diffuse map and constant diffuse factor
TEX R1, fragment.texcoord[4], texture[4], 2D;
MUL color, R1, program.env[0];
# perform the specular bump mapping
DP3 specular, specular, localNormal;
# perform a dependent table read for the specular falloff
POW R1, specular.x, specExp.x;
# modulate by the constant specular factor
MUL R1, R1, program.env[1];
# modulate by the specular map * 2
TEX R2, fragment.texcoord[5], texture[5], 2D;
ADD R2, R2, R2;
MAD color, R1, R2, color;
MUL color, light, color;
# modify by the vertex color
#MUL result.color, color, fragment.color;
# this should be better on future hardware, but current drivers make it slower
MUL result.color.xyz, color, fragment.color;
END
Productivity is a state of mind.
Re: MHDoom finished
I also noticed some flickering/disappearing shadows at the cantina windows on Mars city and some other places. (GF GTX660, driver 320.49)
Did you change the texture filtering on those pics? That doesn't look right even for something that low res, could be block compression?
Iirc MH swapped the normalization lookup texture with math, giving cleaner/crisper results, like you now get specular inside the bilinear filtered crevices between adjacent texels.
Did you change the texture filtering on those pics? That doesn't look right even for something that low res, could be block compression?
Iirc MH swapped the normalization lookup texture with math, giving cleaner/crisper results, like you now get specular inside the bilinear filtered crevices between adjacent texels.
-
toneddu2000
- Posts: 1395
- Joined: Tue Feb 24, 2009 4:39 pm
- Location: Italy
Re: MHDoom finished
Ah, ok thanks.reckless wrote:He bumped everything to ultra levels and then a bit more![]()
What a shame. And the compression algorithm I suppose was not released with the source?reckless wrote:btw BFG uses higher res textures but there compressed and in binary format so its not easy making texture packs for it.
Meadow Fun!! - my first commercial game, made with FTEQW game engine
Re: MHDoom finished
Compression is DXT5 i think so its doable with the directx sdk atleast, worst part seems to be that the images uses a binary format so its a mess to craft new ones.
@spiney havent touched the texture filtering but i bumped the versions on TGA and Jpeg maybe a bug snuck in the TGA code hmm ?.
If anyone spots the bug feel free to submit patches its the only thing holding off atm else it runs great even on ATI.
@spiney havent touched the texture filtering but i bumped the versions on TGA and Jpeg maybe a bug snuck in the TGA code hmm ?.
If anyone spots the bug feel free to submit patches its the only thing holding off atm else it runs great even on ATI.
Productivity is a state of mind.
Re: MHDoom finished
Hmm so im not the only one noticing the shadows sometimes behave weird.
Also in some places with this bug i noticed i could see the outlines on the stencil shadows Oo (faint ghostly copy of the model casting the shadow).
Strangely enough the unmodified source does the same so its not something caused by the changes i have made atleast, bugger though as i have no idea whats causing it or where to start looking even
.
Also in some places with this bug i noticed i could see the outlines on the stencil shadows Oo (faint ghostly copy of the model casting the shadow).
Strangely enough the unmodified source does the same so its not something caused by the changes i have made atleast, bugger though as i have no idea whats causing it or where to start looking even
Productivity is a state of mind.
Re: MHDoom finished
Ok the plot thickens
after painfully going through the source comparing every single file to vanilla i was unable to find any change that would cause this,
today i updated the project to use msvc 2013 and ...shadows work fine again W.T.F @trademark !!! sadly the msvc 2013 build is a lot slower than the 2010 build (still playable but huh ?).
today i updated the project to use msvc 2013 and ...shadows work fine again W.T.F @trademark !!! sadly the msvc 2013 build is a lot slower than the 2010 build (still playable but huh ?).
Productivity is a state of mind.
Re: MHDoom finished
Did you update any libs after switching to VS2013? Sometimes I wonder if the toolset version difference between 2008, 2010, and 2013 releases (some range like V90 to V120) makes a difference for 3d performance, but never tested it.